Skip to content

Commit df7f853

Browse files
committed
Add Eval step in debug check file
1 parent af582f1 commit df7f853

File tree

3 files changed

+59
-9
lines changed

3 files changed

+59
-9
lines changed

compiler/test/dotty/tools/debug/DebugStepAssert.scala

Lines changed: 48 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -19,14 +19,45 @@ private[debug] object DebugStepAssert:
1919
val break = s"break ($sym) ($line)$trailing".r
2020
val step = s"step ($sym|$line)$trailing".r
2121
val next = s"next ($sym|$line)$trailing".r
22-
readLines(checkFile).flatMap:
23-
case break(className , lineStr) =>
24-
val line = lineStr.toInt
25-
Some(DebugStepAssert(Break(className, line), checkClassAndLine(className, line)))
26-
case step(pattern) => Some(DebugStepAssert(Step, checkLineOrMethod(pattern)))
27-
case next(pattern) => Some(DebugStepAssert(Next, checkLineOrMethod(pattern)))
28-
case trailing() => None
29-
case invalid => throw new Exception(s"Cannot parse debug step: $invalid")
22+
val multiLineEval = s"eval$trailing".r
23+
val eval = s"eval (.*)".r
24+
val result = "result (.*)".r
25+
val error = "error (.*)".r
26+
27+
def loop(lines: List[String], acc: List[DebugStepAssert[?]]): List[DebugStepAssert[?]] =
28+
lines match
29+
case Nil => acc.reverse
30+
case break(className , lineStr) :: tail =>
31+
val line = lineStr.toInt
32+
val step = DebugStepAssert(Break(className, line), checkClassAndLine(className, line))
33+
loop(tail, step :: acc)
34+
case step(pattern) :: tail =>
35+
val step = DebugStepAssert(Step, checkLineOrMethod(pattern))
36+
loop(tail, step :: acc)
37+
case next(pattern) :: tail =>
38+
val step = DebugStepAssert(Next, checkLineOrMethod(pattern))
39+
loop(tail, step :: acc)
40+
case eval(expr) :: resOrError :: tail =>
41+
val expected = parseResultOrError(resOrError)
42+
val step = DebugStepAssert(Eval(expr), checkEval(expected))
43+
loop(tail, step :: acc)
44+
case multiLineEval() :: tail0 =>
45+
val (exprLines, tail1) = tail0.span(_.startsWith(" "))
46+
val expr = exprLines.map(s => s.stripPrefix(" ")).mkString("\n")
47+
val expected = parseResultOrError(tail1.head)
48+
val step = DebugStepAssert(Eval(expr), checkEval(expected))
49+
loop(tail1.tail, step :: acc)
50+
case trailing() :: tail => loop(tail, acc)
51+
case invalid :: tail => throw new Exception(s"Cannot parse debug step: $invalid")
52+
53+
def parseResultOrError(line: String): Either[String, String] =
54+
line match
55+
case result(expected) => Right(expected)
56+
case error(expected) => Left(expected)
57+
case invalid => throw new Exception(s"Cannot parse as result or error: $invalid")
58+
59+
loop(readLines(checkFile), Nil)
60+
end parseCheckFile
3061

3162
private def checkClassAndLine(className: String, line: Int)(location: Location): Unit =
3263
assert(className == location.declaringType.name, s"obtained ${location.declaringType.name}, expected ${className}")
@@ -39,12 +70,21 @@ private[debug] object DebugStepAssert:
3970
assert(location.lineNumber == line, s"obtained ${location.lineNumber}, expected $line")
4071

4172
private def checkMethod(methodName: String)(location: Location): Unit = assert(methodName == location.method.name)
73+
74+
private def checkEval(expected: Either[String, String])(obtained: Either[String, String]): Unit =
75+
(expected, obtained) match
76+
case (Left(expected), Left(obtained)) => assert(expected.r.matches(obtained), s"obtained $obtained, expected $expected")
77+
case (Right(expected), Right(obtained)) => assert(expected.r.matches(obtained.toString), s"obtained $obtained, expected $expected")
78+
case (Left(_), Right(_)) => throw new AssertionError("evaluation succeeded but error expected")
79+
case (Right(_), Left(_)) => throw new AssertionError("evaluation failed")
80+
4281
end DebugStepAssert
4382

4483
private[debug] enum DebugStep[T]:
4584
case Break(className: String, line: Int) extends DebugStep[Location]
4685
case Step extends DebugStep[Location]
4786
case Next extends DebugStep[Location]
87+
case Eval(expression: String) extends DebugStep[Either[String, String]]
4888

4989

5090

compiler/test/dotty/tools/debug/DebugTests.scala

Lines changed: 5 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -13,7 +13,7 @@ class DebugTests:
1313
import DebugTests.*
1414
@Test def debug: Unit =
1515
implicit val testGroup: TestGroup = TestGroup("debug")
16-
// compileFile("tests/debug/tailrec.scala", TestConfiguration.defaultOptions).checkDebug()
16+
// compileFile("tests/debug/for.scala", TestConfiguration.defaultOptions).checkDebug()
1717
compileFilesInDir("tests/debug", TestConfiguration.defaultOptions).checkDebug()
1818

1919
object DebugTests extends ParallelTesting:
@@ -100,5 +100,9 @@ object DebugTests extends ParallelTesting:
100100
thread = debugger.step(thread)
101101
if verbose then println(s"step ${location.lineNumber}")
102102
assert(location)
103+
case DebugStepAssert(Eval(expr), assert) =>
104+
val result = debugger.evaluate(expr, thread)
105+
if verbose then println(s"eval $expr $result")
106+
assert(result)
103107
end playDebugSteps
104108
end DebugTest

tests/debug/for.check

Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1,3 +1,9 @@
11
break Test$ 3
22
step 4
3+
eval b
4+
result 72
5+
eval
6+
val c = b + 1
7+
c + 1
8+
result 74
39
step 10

0 commit comments

Comments
 (0)