feat: implement .loc, .file and .func debug directives

This commit is contained in:
2025-03-14 15:40:09 +00:00
parent 07f02e61d7
commit 8f7c902ed5
5 changed files with 81 additions and 7 deletions

View File

@@ -36,11 +36,18 @@ object asmGenerator {
given labelGenerator: LabelGenerator = LabelGenerator()
val Program(funcs, main) = microProg
val progAsm = Chain(LabelDef("main")).concatAll(
val mainLabel = LabelDef("main")
val mainAsm = main.headOption match {
case Some(stmt) =>
labelGenerator.getDebugFunc(stmt.pos, "$main", mainLabel) + mainLabel
case None => Chain.one(mainLabel)
}
val progAsm = mainAsm.concatAll(
funcPrologue(),
main.foldMap(generateStmt(_)),
Chain.one(Xor(RAX, RAX)),
funcEpilogue(),
Chain(Directive.Size(mainLabel, SizeExpr.Relative(mainLabel)), Directive.EndFunc),
generateBuiltInFuncs(),
RuntimeError.all.foldMap(_.generate),
funcs.foldMap(generateUserFunc(_))
@@ -51,6 +58,7 @@ object asmGenerator {
Directive.Global("main"),
Directive.RoData
).concatAll(
labelGenerator.generateDebug,
labelGenerator.generateConstants,
Chain.one(Directive.Text),
progAsm
@@ -75,7 +83,10 @@ object asmGenerator {
// Setup the stack with param 7 and up
func.params.drop(argRegs.size).foreach(stack.reserve(_))
stack.reserve(Size.Q64) // Reserve return pointer slot
var asm = Chain.one[AsmLine](labelGenerator.getLabelDef(func.name))
val funcLabel = labelGenerator.getLabelDef(func.name)
var asm = labelGenerator.getDebugFunc(func.pos, func.name.name, funcLabel)
val debugFunc = asm.size > 0
asm += funcLabel
asm ++= funcPrologue()
// Push the rest of params onto the stack for simplicity
argRegs.zip(func.params).foreach { (reg, param) =>
@@ -83,6 +94,10 @@ object asmGenerator {
}
asm ++= func.body.foldMap(generateStmt(_))
// No need for epilogue here since all user functions must return explicitly
if (debugFunc) {
asm += Directive.Size(funcLabel, SizeExpr.Relative(funcLabel))
asm += Directive.EndFunc
}
asm
}
@@ -159,8 +174,8 @@ object asmGenerator {
stack: Stack,
labelGenerator: LabelGenerator
): Chain[AsmLine] = {
var asm = Chain.empty[AsmLine]
asm += Comment(stmt.toString)
val fileNo = labelGenerator.getDebugFile(stmt.pos.file)
var asm = Chain.one[AsmLine](Directive.Location(fileNo, stmt.pos.line, None))
stmt match {
case Assign(lhs, rhs) =>
lhs match {