1
+ #!/usr/bin/env -S scala-cli shebang
2
+
1
3
// Usage
2
- // > scala-cli project/scripts/dottyCompileBisect.scala -- File1. scala File2 .scala
4
+ // > ./ project/scripts/dottyCompileBisect.sc [--run <main.class.name>] [<compiler-option> ...] <file1. scala> [<fileN .scala> ...]
3
5
//
4
6
// This script will bisect the compilation failure starting with a fast bisection on released nightly builds.
5
7
// Then it will bisect the commits between the last nightly that worked and the first nightly that failed.
8
10
import sys .process ._
9
11
import scala .io .Source
10
12
import Releases .Release
13
+ import java .io .File
14
+ import java .nio .file .{Files , Paths , StandardCopyOption }
15
+
16
+
17
+ // main
18
+ dottyCompileBisect(args.toSeq)
11
19
12
- @ main def dottyCompileBisect (files : String * ): Unit =
13
- val releaseBisect = ReleaseBisect (files.toList)
14
- val fistBadRelease = releaseBisect.bisect(Releases .allReleases)
20
+ def dottyCompileBisect (args : Seq [String ]): Unit =
21
+ val (mainClass, compilerArgs) = args match
22
+ case Seq (" --run" , mainClass, compilerArgs* ) =>
23
+ (Some (mainClass), compilerArgs)
24
+ case _ =>
25
+ (None , args)
26
+
27
+ val releaseBisect = ReleaseBisect (mainClass, compilerArgs.toList)
28
+ val bisectedBadRelease = releaseBisect.bisectedBadRelease(Releases .allReleases)
15
29
println(" \n Finished bisecting releases\n " )
16
- fistBadRelease.previous match
17
- case Some (lastGoodRelease) =>
18
- println(s " Last good release: $lastGoodRelease\n First bad release: $fistBadRelease\n " )
19
- val commitBisect = CommitBisect (files.toList)
20
- commitBisect.bisect(lastGoodRelease.hash, fistBadRelease.hash)
30
+
31
+ bisectedBadRelease match
32
+ case Some (firstBadRelease) =>
33
+ firstBadRelease.previous match
34
+ case Some (lastGoodRelease) =>
35
+ println(s " Last good release: $lastGoodRelease" )
36
+ println(s " First bad release: $firstBadRelease" )
37
+ val commitBisect = CommitBisect (mainClass, compilerArgs.toList)
38
+ commitBisect.bisect(lastGoodRelease.hash, firstBadRelease.hash)
39
+ case None =>
40
+ println(s " No good release found " )
21
41
case None =>
22
- println(s " No good release found " )
42
+ println(s " No bad release found " )
23
43
24
- class ReleaseBisect (files : List [String ]):
44
+ class ReleaseBisect (mainClass : Option [String ], compilerArgs : List [String ]):
45
+ def bisectedBadRelease (releases : Vector [Release ]): Option [Release ] =
46
+ Some (bisect(releases : Vector [Release ]))
47
+ .filter(! isGoodRelease(_))
25
48
26
49
def bisect (releases : Vector [Release ]): Release =
27
50
assert(releases.length > 1 , " Need at least 2 releases to bisect" )
@@ -35,7 +58,12 @@ class ReleaseBisect(files: List[String]):
35
58
36
59
private def isGoodRelease (release : Release ): Boolean =
37
60
println(s " Testing ${release.version}" )
38
- val res = s """ scala-cli compile ${files.mkString(" " )} -S " ${release.version}" """ .!
61
+ val testCommand = mainClass match
62
+ case Some (className) =>
63
+ s " run --main-class ' $className' "
64
+ case None =>
65
+ " compile"
66
+ val res = s """ scala-cli $testCommand -S ' ${release.version}' ${compilerArgs.mkString(" " )}""" .!
39
67
val isGood = res == 0
40
68
println(s " Test result: ${release.version} is a ${if isGood then " good" else " bad" } release \n " )
41
69
isGood
@@ -64,10 +92,14 @@ object Releases:
64
92
65
93
override def toString : String = version
66
94
67
- class CommitBisect (files : List [String ]):
95
+ class CommitBisect (mainClass : Option [ String ], compilerArgs : List [String ]):
68
96
def bisect (lastGoodHash : String , fistBadHash : String ): Unit =
69
97
println(s " Starting bisecting commits $lastGoodHash.. $fistBadHash\n " )
98
+ val runOption = mainClass.map(className => s " --run $className" ).getOrElse(" " )
99
+ val scriptFile = Paths .get(" project" , " scripts" , " dottyCompileBisect.sh" )
100
+ val tempScriptFile = File .createTempFile(" dottyCompileBisect" , " sh" ).toPath
101
+ Files .copy(scriptFile, tempScriptFile, StandardCopyOption .REPLACE_EXISTING )
70
102
" git bisect start" .!
71
103
s " git bisect bad $fistBadHash" .!
72
104
s " git bisect good $lastGoodHash" .!
73
- s " git bisect run sh project/scripts/dottyCompileBisect.sh ${files .mkString(" " )}" .!
105
+ s " git bisect run sh ${tempScriptFile.toAbsolutePath} ${runOption} ${compilerArgs .mkString(" " )}" .!
0 commit comments