@@ -3,8 +3,9 @@ package tools
33
44import java .io .File
55import java .nio .charset .StandardCharsets .UTF_8
6+ import java .nio .file .{Files , Path => JPath }
67
7- import scala .io .Source
8+ import scala .io .{ Codec , Source }
89import scala .reflect .ClassTag
910import scala .util .Using .resource
1011import scala .util .chaining .given
@@ -25,11 +26,10 @@ extension (f: File) def absPath =
2526extension (str : String ) def dropExtension =
2627 str.reverse.dropWhile(_ != '.' ).drop(1 ).reverse
2728
28- private def withFile [T ](file : File )(action : Source => T ): T =
29- resource(Source .fromFile(file, UTF_8 .name))(action)
30-
31- def readLines (f : File ): List [String ] = withFile(f)(_.getLines.toList)
32- def readFile (f : File ): String = withFile(f)(_.mkString)
29+ private
30+ def withFile [T ](file : File )(action : Source => T )(using Codec ): T = resource(Source .fromFile(file))(action)
31+ def readLines (f : File )(using codec : Codec = Codec .UTF8 ): List [String ] = withFile(f)(_.getLines.toList)
32+ def readFile (f : File )(using codec : Codec = Codec .UTF8 ): String = withFile(f)(_.mkString)
3333
3434private object Unthrown extends ControlThrowable
3535
@@ -43,3 +43,24 @@ def assertThrows[T <: Throwable: ClassTag](p: T => Boolean)(body: => Any): Unit
4343 case failed : T => throw AssertionError (s " Exception failed check: $failed" ).tap(_.addSuppressed(failed))
4444 case NonFatal (other) => throw AssertionError (s " Wrong exception: expected ${implicitly[ClassTag [T ]]} but was ${other.getClass.getName}" ).tap(_.addSuppressed(other))
4545end assertThrows
46+
47+ def toolArgsFor (files : List [JPath ])(using codec : Codec = Codec .UTF8 ): List [String ] =
48+ files.flatMap(path => toolArgsParse(readLines(path.toFile)))
49+
50+ // Inspect the first 10 of the given lines for compiler options of the form
51+ // `// scalac: args`, `/* scalac: args`, ` * scalac: args`.
52+ // If args string ends in close comment, drop the `*` `/`.
53+ // If split, parse the args string as a command line.
54+ // (from scala.tools.partest.nest.Runner#toolArgsFor)
55+ def toolArgsParse (lines : List [String ]): List [String ] = {
56+ val tag = " scalac:"
57+ val endc = " *" + " /" // be forgiving of /* scalac: ... */
58+ def stripped (s : String ) = s.substring(s.indexOf(tag) + tag.length).stripSuffix(endc)
59+ val args = lines.to(LazyList ).take(10 ).filter { s =>
60+ s.contains(" // " + tag)
61+ || s.contains(" /* " + tag)
62+ || s.contains(" * " + tag)
63+ // but avoid picking up comments like "% scalac ./a.scala" and "$ scalac a.scala"
64+ }.map(stripped).headOption
65+ args.map(dotc.config.CommandLineParser .tokenize).getOrElse(Nil )
66+ }
0 commit comments