block names in asm now prefixed with p8b_ (instead of p8_)

as part of fixing var versus block symbol conflict handling
This commit is contained in:
Irmen de Jong 2023-12-19 22:59:01 +01:00
parent b7279a3d9e
commit 69f6afe420
7 changed files with 47 additions and 30 deletions

View File

@ -64,9 +64,9 @@ class PtProgram(
children.asSequence().filterIsInstance<PtBlock>()
fun entrypoint(): PtSub? =
allBlocks().firstOrNull { it.name == "main" || it.name=="p8_main" }
allBlocks().firstOrNull { it.name == "main" || it.name=="p8b_main" }
?.children
?.firstOrNull { it is PtSub && (it.name == "start" || it.name=="main.start" || it.name=="p8_start" || it.name=="p8_main.p8_start") } as PtSub?
?.firstOrNull { it is PtSub && (it.name == "start" || it.name=="main.start" || it.name=="p8_start" || it.name=="p8b_main.p8_start") } as PtSub?
}

View File

@ -33,7 +33,11 @@ class AsmGen6502(val prefixSymbols: Boolean): ICodeGeneratorBackend {
val functionCallsToPrefix = mutableListOf<Pair<PtNode, Int>>() // parent + index
fun prefixNamedNode(node: PtNamedNode) {
node.name = "p8_${node.name}"
when(node) {
is PtBlock -> node.name = "p8b_${node.name}"
else -> node.name = "p8_${node.name}"
// TODO: more special prefixes for the other node types?
}
}
fun prefixSymbols(node: PtNode) {
@ -116,8 +120,16 @@ class AsmGen6502(val prefixSymbols: Boolean): ICodeGeneratorBackend {
}
}
private fun prefixScopedName(name: String): String {
if('.' !in name) return "p8_$name"
// fully scoped, first part is block
val parts = name.split('.')
val prefixed = listOf("p8b_${parts[0]}") + parts.drop(1).map{"p8_$it"}
return prefixed.joinToString(".")
}
private fun PtVariable.prefix(st: SymbolTable): PtVariable {
name = name.split('.').map {"p8_$it" }.joinToString(".")
name = prefixScopedName(name)
if(value==null)
return this
@ -154,7 +166,7 @@ private fun PtJump.prefix(parent: PtNode, st: SymbolTable): PtJump {
}
private fun PtFunctionCall.prefix(parent: PtNode): PtFunctionCall {
val newName = name.split('.').map {"p8_$it" }.joinToString(".")
val newName = prefixScopedName(name)
val call = PtFunctionCall(newName, void, type, position)
call.children.addAll(children)
call.children.forEach { it.parent = call }
@ -167,7 +179,7 @@ private fun PtIdentifier.prefix(parent: PtNode, st: SymbolTable): PtIdentifier {
if(target?.astNode?.definingBlock()?.noSymbolPrefixing==true)
return this
val newName = name.split('.').map { "p8_$it" }.joinToString(".")
val newName = prefixScopedName(name)
val node = PtIdentifier(newName, type, position)
node.parent = parent
return node

View File

@ -34,8 +34,8 @@ internal class ProgramAndVarsGen(
header()
val allBlocks = program.allBlocks()
if(allBlocks.first().name != "p8_main" && allBlocks.first().name != "main")
throw AssemblyError("first block should be 'main' or 'p8_main'")
if(allBlocks.first().name != "p8b_main" && allBlocks.first().name != "main")
throw AssemblyError("first block should be 'main' or 'p8b_main'")
if(errors.noErrors()) {
program.allBlocks().forEach { block2asm(it) }
@ -138,24 +138,24 @@ internal class ProgramAndVarsGen(
"cx16" -> {
if(options.floats)
asmgen.out(" lda #4 | sta $01") // to use floats, make sure Basic rom is banked in
asmgen.out(" jsr p8_main.p8_start")
asmgen.out(" jsr p8b_main.p8_start")
asmgen.out(" jmp sys.cleanup_at_exit")
}
"c64" -> {
asmgen.out(" jsr p8_main.p8_start | lda #31 | sta $01")
asmgen.out(" jsr p8b_main.p8_start | lda #31 | sta $01")
if(!options.noSysInit)
asmgen.out(" jmp sys.cleanup_at_exit")
else
asmgen.out(" rts")
}
"c128" -> {
asmgen.out(" jsr p8_main.p8_start | lda #0 | sta ${"$"}ff00")
asmgen.out(" jsr p8b_main.p8_start | lda #0 | sta ${"$"}ff00")
if(!options.noSysInit)
asmgen.out(" jmp sys.cleanup_at_exit")
else
asmgen.out(" rts")
}
else -> asmgen.jmp("p8_main.p8_start")
else -> asmgen.jmp("p8b_main.p8_start")
}
}
@ -331,7 +331,7 @@ internal class ProgramAndVarsGen(
asmsubs2asm(sub.children)
// the main.start subroutine is the program's entrypoint and should perform some initialization logic
if((sub.name=="start" || sub.name=="p8_start") && (sub.definingBlock()!!.name=="main" || sub.definingBlock()!!.name=="p8_main"))
if((sub.name=="start" || sub.name=="p8_start") && (sub.definingBlock()!!.name=="main" || sub.definingBlock()!!.name=="p8b_main"))
entrypointInitialization()
if(functioncallAsmGen.optimizeIntArgsViaRegisters(sub)) {

View File

@ -163,7 +163,7 @@ class CallGraph(private val program: Program) : IAstVisitor {
return allIdentifiersAndTargets.filter { decl===it.value }.map{ it.key }
}
private fun nameInAssemblyCode(name: String) = allAssemblyNodes.any { "p8_$name" in it.names || name in it.names }
private fun nameInAssemblyCode(name: String) = allAssemblyNodes.any { "p8_$name" in it.names || "p8b_$name" in it.names || name in it.names }
inline fun unused(label: Label) = false // just always output labels

View File

@ -30,12 +30,18 @@ so that more system ram is available for the program code itself.
Symbol prefixing in generated Assembly code
-------------------------------------------
*All* symbols in the prog8 program will be prefixed with ``p8_`` in the generated assembly code.
*All* symbols in the prog8 program will be prefixed in the generated assembly code:
Block names
will be prefixed with ``p8b_``
All other names
will be prefixed with ``p8_``
This is to avoid naming conflicts with CPU registers, assembly instructions, etc.
So if you're referencing symbols from the prog8 program in inlined assembly code, you have to take
this into account. Stick a ``p8_`` in front of everything that you want to reference that is coming
this into account. Stick a ``p8_`` in front of everything (``p8b_`` for block names) that you want to reference that is coming
from a prog8 source file.
All elements in scoped names such as ``main.routine.var1`` are prefixed so this becomes ``p8_main.p8_routine.p8_var1``.
All elements in scoped names such as ``main.routine.var1`` are prefixed so this becomes ``p8b_main.p8_routine.p8_var1``.
.. attention::
Symbols from library modules are *not* prefixed and can be used

View File

@ -41,12 +41,12 @@ mcf {
%asm {{
lda cx16.r0
ldy cx16.r0+1
sta p8_mcf.p8_stream.getbuffer_call+1
sty p8_mcf.p8_stream.getbuffer_call+2
sta p8b_mcf.p8_stream.getbuffer_call+1
sty p8b_mcf.p8_stream.getbuffer_call+2
lda cx16.r1
ldy cx16.r1+1
sta p8_mcf.p8_stream.processchunk_call+1
sty p8_mcf.p8_stream.processchunk_call+2
sta p8b_mcf.p8_stream.processchunk_call+1
sty p8b_mcf.p8_stream.processchunk_call+2
rts
}}
}
@ -113,7 +113,7 @@ mcf {
; custom chunk
uword @shared chunksize = peekw(loadlist_ptr+1)
%asm {{
lda (p8_mcf.p8_loadlist_ptr)
lda (p8b_mcf.p8_loadlist_ptr)
ldx p8_chunksize
ldy p8_chunksize+1
getbuffer_call jsr $ffff ; modified

View File

@ -3,13 +3,12 @@
main {
sub start() {
ubyte bank = cx16.search_x16edit()
txt.print_ub(bank)
if bank<255 {
cx16.rombank(bank)
cx16.x16edit_default()
cx16.rombank(0)
}
txt.print("back from editor!\n")
uword module ; TODO shadow warning
module++
module.test++ ; TODO compiler error
}
}
module {
ubyte @shared test
}