Skip to content

Commit 26a4a14

Browse files
committed
Improve test failure reporting + fix nested annotations
1 parent 46ae8a7 commit 26a4a14

File tree

6 files changed

+112
-63
lines changed

6 files changed

+112
-63
lines changed

hkmc2/shared/src/main/scala/hkmc2/Diagnostic.scala

Lines changed: 23 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -1,15 +1,21 @@
11
package hkmc2
22

33
import scala.util.chaining._
4+
import sourcecode.{Name, Line, FileName}
5+
46
import mlscript.utils._, shorthands._
57

68
import Diagnostic._
79

8-
sealed abstract class Diagnostic(val theMsg: String) extends Exception(theMsg):
10+
sealed abstract class Diagnostic
11+
(val theMsg: String)
12+
(using val srcLine: Line, val srcName: Name, val srcFile: FileName)
13+
extends Exception(theMsg):
914
val allMsgs: Ls[Message -> Opt[Loc]]
1015
val kind: Kind
1116
val source: Source
1217
val mkExtraInfo: () => Opt[Any]
18+
def srcLoc: Str = s"${srcName.value} (${srcFile.value}:${srcLine.value})"
1319
object Diagnostic:
1420

1521
enum Kind:
@@ -30,28 +36,38 @@ final case class ErrorReport(
3036
allMsgs: Ls[Message -> Opt[Loc]],
3137
mkExtraInfo: () => Opt[Any],
3238
source: Source,
33-
) extends Diagnostic(mainMsg):
39+
)(using Line, Name, FileName) extends Diagnostic(mainMsg):
3440
val kind: Kind = Kind.Error
3541
object ErrorReport:
36-
def apply(msgs: Ls[Message -> Opt[Loc]], extraInfo: => Opt[Any] = N, source: Source = Source.Typing): ErrorReport =
42+
def apply(using Line, FileName)
43+
(msgs: Ls[Message -> Opt[Loc]], extraInfo: => Opt[Any] = N, source: Source = Source.Typing)
44+
(using Name): ErrorReport =
3745
ErrorReport(msgs.head._1.show, msgs, () => extraInfo, source)
3846

3947
final case class WarningReport(
4048
mainMsg: Str,
4149
allMsgs: Ls[Message -> Opt[Loc]],
4250
mkExtraInfo: () => Opt[Any],
4351
source: Source,
44-
) extends Diagnostic(mainMsg):
52+
)(using Line, Name, FileName) extends Diagnostic(mainMsg):
4553
val kind: Kind = Kind.Warning
4654
object WarningReport:
47-
def apply(msgs: Ls[Message -> Opt[Loc]], extraInfo: => Opt[Any] = N, source: Source = Source.Typing): WarningReport =
55+
def apply(using Line, FileName)
56+
(msgs: Ls[Message -> Opt[Loc]], extraInfo: => Opt[Any] = N, source: Source = Source.Typing)
57+
(using Name): WarningReport =
4858
WarningReport(msgs.head._1.show, msgs, () => extraInfo, source)
4959

50-
final case class InternalError(mainMsg: Str, allMsgs: Ls[Message -> Opt[Loc]], source: Source) extends Diagnostic(mainMsg):
60+
final case class InternalError(
61+
mainMsg: Str,
62+
allMsgs: Ls[Message -> Opt[Loc]],
63+
source: Source
64+
)(using Line, Name, FileName) extends Diagnostic(mainMsg):
5165
val kind: Kind = Kind.Internal
5266
val mkExtraInfo: () => Opt[Any] = () => N
5367
object InternalError:
54-
def apply(msgs: Ls[Message -> Opt[Loc]], source: Source = Source.Typing): InternalError =
68+
def apply(using Line, FileName)
69+
(msgs: Ls[Message -> Opt[Loc]], source: Source = Source.Typing)
70+
(using Name): InternalError =
5571
InternalError(msgs.head._1.show, msgs, source)
5672

5773

hkmc2/shared/src/main/scala/hkmc2/codegen/Lowering.scala

Lines changed: 5 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -619,13 +619,11 @@ class Lowering()(using Config, TL, Raise, State, Ctx):
619619
(using Subst): (List[ParamList], Block) =
620620
(paramLists, returnedTerm(bodyTerm))
621621

622-
def reportAnnotations(target: Statement, annotations: Ls[Annot]): Unit = if annotations.nonEmpty then
623-
raise(WarningReport(
624-
(msg"This annotation has no effect." -> annotations.foldLeft[Opt[Loc]](N):
625-
case (acc, term) => acc match
626-
case N => term.toLoc
627-
case S(loc) => S(loc ++ term.toLoc)) ::
628-
Nil))
622+
def reportAnnotations(target: Statement, annotations: Ls[Annot]): Unit =
623+
annotations.foreach:
624+
case Annot.Untyped => ()
625+
case annot => raise:
626+
WarningReport(msg"This annotation has no effect." -> annot.toLoc :: Nil)
629627

630628

631629
trait LoweringSelSanityChecks(using Config, TL, Raise, State)

hkmc2/shared/src/main/scala/hkmc2/syntax/Tree.scala

Lines changed: 15 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -181,15 +181,22 @@ enum Tree extends AutoLocated:
181181
case LetLike(kw, und @ Under(), r, b) =>
182182
LetLike(kw, Ident("_").withLocOf(und), r, b)
183183

184-
case Modified(Keyword.`declare`, modLoc, s) =>
185-
Annotated(Keywrd(Keyword.`declare`), s) // TODO properly attach location
186-
case Modified(Keyword.`abstract`, modLoc, s) =>
187-
Annotated(Keywrd(Keyword.`abstract`), s) // TODO properly attach location
188-
case Modified(Keyword.`mut`, modLoc, TermDef(ImmutVal, anme, rhs)) =>
189-
TermDef(MutVal, anme, rhs).withLocOf(this).desugared
190-
case LetLike(letLike, App(f @ Ident(nme), Tup((id: Ident) :: r :: Nil)), N, bodo)
184+
case PossiblyAnnotated(anns, m: Modified) =>
185+
PossiblyAnnotated(anns,
186+
m match
187+
case Modified(Keyword.`declare`, modLoc, s) =>
188+
Annotated(Keywrd(Keyword.`declare`), s.desugared) // TODO properly attach location
189+
case Modified(Keyword.`abstract`, modLoc, s) =>
190+
Annotated(Keywrd(Keyword.`abstract`), s.desugared) // TODO properly attach location
191+
case Modified(Keyword.`mut`, modLoc, TermDef(ImmutVal, anme, rhs)) =>
192+
TermDef(MutVal, anme, rhs).withLocOf(this).desugared
193+
case _ => m
194+
)
195+
196+
case PossiblyAnnotated(anns, LetLike(letLike, App(f @ Ident(nme), Tup((id: Ident) :: r :: Nil)), N, bodo))
191197
if nme.endsWith("=") =>
192-
LetLike(letLike, id, S(App(Ident(nme.init), Tup(id :: r :: Nil))), bodo).withLocOf(this).desugared
198+
PossiblyAnnotated(anns, LetLike(letLike, id, S(App(Ident(nme.init), Tup(id :: r :: Nil))), bodo).withLocOf(this).desugared)
199+
193200
case _ => this
194201

195202
/**
Lines changed: 19 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1,13 +1,32 @@
11
:bbml
22
//│ Type: ⊤
3+
:js
34

45
//│ Type: ⊤
56

67

78
@untyped 1
9+
//│ = 1
810
//│ Type: ⊥
911

12+
:re
1013
(@untyped 1)(2)
14+
//│ ═══[RUNTIME ERROR] TypeError: 1 is not a function
1115
//│ Type: ⊥
1216

17+
@untyped
18+
fun f: Int
19+
//│ Type: ⊤
20+
21+
@untyped declare fun f: Int
22+
//│ Type: ⊤
23+
24+
@untyped
25+
@untyped
26+
declare fun f: Int
27+
//│ Type: ⊤
28+
29+
@untyped fun f() = 1
30+
//│ Type: ⊤
31+
1332

hkmc2/shared/src/test/mlscript/syntax/annotations/Declarations.mls

Lines changed: 33 additions & 27 deletions
Original file line numberDiff line numberDiff line change
@@ -110,7 +110,10 @@ let
110110
if n < 2 then n else fib(n - 1) + fib(n - 2)
111111
//│ ╔══[WARNING] This annotation has no effect.
112112
//│ ║ l.109: @inline @tailrec fun fib(n) =
113-
//│ ╙── ^^^^^^^^^^^^^^^
113+
//│ ╙── ^^^^^^
114+
//│ ╔══[WARNING] This annotation has no effect.
115+
//│ ║ l.109: @inline @tailrec fun fib(n) =
116+
//│ ╙── ^^^^^^^
114117

115118
module internal
116119

@@ -121,16 +124,16 @@ module internal
121124
transient
122125
volatile
123126
//│ ╔══[WARNING] This annotation has no effect.
124-
//│ ║ l.118: @internal object
127+
//│ ║ l.121: @internal object
125128
//│ ╙── ^^^^^^^^
126129
//│ ╔══[WARNING] This annotation has no effect.
127-
//│ ║ l.118: @internal object
130+
//│ ║ l.121: @internal object
128131
//│ ╙── ^^^^^^^^
129132
//│ ╔══[WARNING] This annotation has no effect.
130-
//│ ║ l.118: @internal object
133+
//│ ║ l.121: @internal object
131134
//│ ╙── ^^^^^^^^
132135
//│ ╔══[WARNING] This annotation has no effect.
133-
//│ ║ l.118: @internal object
136+
//│ ║ l.121: @internal object
134137
//│ ╙── ^^^^^^^^
135138

136139
:w
@@ -140,28 +143,31 @@ module internal
140143
@volatile @transient empty = ""
141144
normal = ()
142145
//│ ╔══[WARNING] This annotation has no effect.
143-
//│ ║ l.137: @volatile let
144-
//│ ║ ^^^^^^^^^^^^
145-
//│ ║ l.138: @shared counter = 0
146-
//│ ╙── ^^^^^^^^^
147-
//│ ╔══[WARNING] This annotation has no effect.
148-
//│ ║ l.137: @volatile let
149-
//│ ║ ^^^^^^^^^^^^
150-
//│ ║ l.138: @shared counter = 0
151-
//│ ║ ^^^^^^^^^^^^^^^^^^^^^
152-
//│ ║ l.139: @transient @thread_local cache = ()
153-
//│ ╙── ^^^^^^^^^^^^^^^^^^^^^^^^^^
154-
//│ ╔══[WARNING] This annotation has no effect.
155-
//│ ║ l.137: @volatile let
156-
//│ ║ ^^^^^^^^^^^^
157-
//│ ║ l.138: @shared counter = 0
158-
//│ ║ ^^^^^^^^^^^^^^^^^^^^^
159-
//│ ║ l.139: @transient @thread_local cache = ()
160-
//│ ║ ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
161-
//│ ║ l.140: @volatile @transient empty = ""
162-
//│ ╙── ^^^^^^^^^^^^^^^^^^^^^^
163-
//│ ╔══[WARNING] This annotation has no effect.
164-
//│ ║ l.137: @volatile let
146+
//│ ║ l.140: @volatile let
147+
//│ ╙── ^^^^^^^^
148+
//│ ╔══[WARNING] This annotation has no effect.
149+
//│ ║ l.141: @shared counter = 0
150+
//│ ╙── ^^^^^^
151+
//│ ╔══[WARNING] This annotation has no effect.
152+
//│ ║ l.140: @volatile let
153+
//│ ╙── ^^^^^^^^
154+
//│ ╔══[WARNING] This annotation has no effect.
155+
//│ ║ l.142: @transient @thread_local cache = ()
156+
//│ ╙── ^^^^^^^^^
157+
//│ ╔══[WARNING] This annotation has no effect.
158+
//│ ║ l.142: @transient @thread_local cache = ()
159+
//│ ╙── ^^^^^^^^^^^^
160+
//│ ╔══[WARNING] This annotation has no effect.
161+
//│ ║ l.140: @volatile let
162+
//│ ╙── ^^^^^^^^
163+
//│ ╔══[WARNING] This annotation has no effect.
164+
//│ ║ l.143: @volatile @transient empty = ""
165+
//│ ╙── ^^^^^^^^
166+
//│ ╔══[WARNING] This annotation has no effect.
167+
//│ ║ l.143: @volatile @transient empty = ""
168+
//│ ╙── ^^^^^^^^^
169+
//│ ╔══[WARNING] This annotation has no effect.
170+
//│ ║ l.140: @volatile let
165171
//│ ╙── ^^^^^^^^
166172
//│ counter = 0
167173
//│ empty = ""

hkmc2DiffTests/src/test/scala/hkmc2/DiffMaker.scala

Lines changed: 17 additions & 14 deletions
Original file line numberDiff line numberDiff line change
@@ -38,10 +38,13 @@ abstract class DiffMaker:
3838
def doFail(blockLineNum: Int, msg: String): Unit =
3939
System.err.println(fansi.Color.Red("FAILURE: ").toString + msg)
4040
def unhandled(blockLineNum: Int, exc: Throwable): Unit =
41-
unexpected("exception", blockLineNum, () => N)
41+
unexpected("exception", blockLineNum, N, () => N)
4242

43-
final def unexpected(what: Str, blockLineNum: Int, mkExtraInfo: () => Opt[Any]): Unit =
43+
final def unexpected(what: Str, blockLineNum: Int, srcLoc: Opt[Str], mkExtraInfo: () => Opt[Any]): Unit =
4444
output(s"FAILURE: Unexpected $what")
45+
srcLoc match
46+
case S(loc) => output(s"FAILURE LOCATION: $loc")
47+
case N => ()
4548
mkExtraInfo() match
4649
case S(info: Product) => output(s"FAILURE INFO: ${info.showAsTree}")
4750
case S(info) => output(s"FAILURE INFO: $info")
@@ -174,34 +177,34 @@ abstract class DiffMaker:
174177
parseErrors += 1
175178
if expectParseErrors.isUnset && !tolerateErrors then
176179
failures += globalStartLineNum
177-
unexpected("lexing error", blockLineNum, d.mkExtraInfo)
180+
unexpected("lexing error", blockLineNum, S(d.srcLoc), d.mkExtraInfo)
178181
case Diagnostic.Source.Parsing =>
179182
parseErrors += 1
180183
if expectParseErrors.isUnset && !tolerateErrors then
181184
failures += globalStartLineNum
182185
// doFail(fileName, blockLineNum, "unexpected parse error at ")
183-
unexpected("parse error", blockLineNum, d.mkExtraInfo)
186+
unexpected("parse error", blockLineNum, S(d.srcLoc), d.mkExtraInfo)
184187
// report(blockLineNum, d :: Nil, showRelativeLineNums.isSet)
185188
case Diagnostic.Source.Typing =>
186189
typeErrors += 1
187190
if expectTypeErrors.isUnset && !tolerateErrors then
188191
failures += globalStartLineNum
189-
unexpected("type error", blockLineNum, d.mkExtraInfo)
192+
unexpected("type error", blockLineNum, S(d.srcLoc), d.mkExtraInfo)
190193
case Diagnostic.Source.Compilation =>
191194
compilationErrors += 1
192195
if expectCodeGenErrors.isUnset && !tolerateErrors then
193196
failures += globalStartLineNum
194-
unexpected("compilation error", blockLineNum, d.mkExtraInfo)
197+
unexpected("compilation error", blockLineNum, S(d.srcLoc), d.mkExtraInfo)
195198
case Diagnostic.Source.Runtime =>
196199
runtimeErrors += 1
197200
if !expectRuntimeOrCodeGenErrors && !tolerateErrors then
198201
failures += globalStartLineNum
199-
unexpected("runtime error", blockLineNum, d.mkExtraInfo)
202+
unexpected("runtime error", blockLineNum, S(d.srcLoc), d.mkExtraInfo)
200203
case Diagnostic.Kind.Warning =>
201204
warnings += 1
202205
if expectWarnings.isUnset && !tolerateErrors then
203206
failures += globalStartLineNum
204-
unexpected("warning", blockLineNum, d.mkExtraInfo)
207+
unexpected("warning", blockLineNum, S(d.srcLoc), d.mkExtraInfo)
205208
case Diagnostic.Kind.Internal =>
206209
if !tolerateErrors then
207210
failures += globalStartLineNum
@@ -215,23 +218,23 @@ abstract class DiffMaker:
215218
// Use `todo` when the errors are expected but not yet implemented.
216219
if expectParseErrors.isSet && parseErrors == 0 && todo.isUnset && breakme.isUnset then
217220
failures += globalStartLineNum
218-
unexpected("lack of parse error", blockLineNum, () => N)
221+
unexpected("lack of parse error", blockLineNum, N, () => N)
219222
if expectTypeErrors.isSet && typeErrors == 0 && todo.isUnset && breakme.isUnset then
220223
failures += globalStartLineNum
221-
unexpected("lack of type error", blockLineNum, () => N)
224+
unexpected("lack of type error", blockLineNum, N, () => N)
222225
if expectCodeGenErrors.isSet && compilationErrors == 0 && todo.isUnset && breakme.isUnset then
223226
failures += globalStartLineNum
224-
unexpected("lack of compilation error", blockLineNum, () => N)
227+
unexpected("lack of compilation error", blockLineNum, N, () => N)
225228
if expectRuntimeErrors.isSet && runtimeErrors == 0 && todo.isUnset && breakme.isUnset then
226229
failures += globalStartLineNum
227-
unexpected("lack of runtime error", blockLineNum, () => N)
230+
unexpected("lack of runtime error", blockLineNum, N, () => N)
228231
if expectWarnings.isSet && warnings == 0 && todo.isUnset && breakme.isUnset then
229232
failures += globalStartLineNum
230-
unexpected("lack of warnings", blockLineNum, () => N)
233+
unexpected("lack of warnings", blockLineNum, N, () => N)
231234

232235
if fixme.isSet && (parseErrors + typeErrors + compilationErrors + runtimeErrors) == 0 then
233236
failures += globalStartLineNum
234-
unexpected("lack of error to fix", blockLineNum, () => N)
237+
unexpected("lack of error to fix", blockLineNum, N, () => N)
235238

236239

237240

0 commit comments

Comments
 (0)