mirror of
https://github.com/irmen/prog8.git
synced 2024-09-07 19:54:26 +00:00
fix regression compiler crash in string comparison
This commit is contained in:
parent
fef52c0112
commit
dad5b17ac8
@ -27,7 +27,11 @@ internal class LiteralsToAutoVars(private val program: Program,
|
||||
errors.err("compilation target doesn't support this text encoding", string.position)
|
||||
return noModifications
|
||||
}
|
||||
if(string.parent !is VarDecl && string.parent !is WhenChoice && string.parent !is BinaryExpression) {
|
||||
if(string.parent !is VarDecl && string.parent !is WhenChoice) {
|
||||
val binExpr = string.parent as? BinaryExpression
|
||||
if(binExpr!=null &&(binExpr.operator=="+" || binExpr.operator=="*"))
|
||||
return noModifications // allow string concatenation or repeats later, based on just string literals
|
||||
|
||||
// replace the literal string by an identifier reference to the interned string
|
||||
val parentFunc = (string.parent as? IFunctionCall)?.target
|
||||
if(parentFunc!=null) {
|
||||
|
@ -3,7 +3,6 @@ package prog8tests
|
||||
import io.kotest.assertions.fail
|
||||
import io.kotest.assertions.withClue
|
||||
import io.kotest.core.spec.style.FunSpec
|
||||
import io.kotest.matchers.collections.shouldStartWith
|
||||
import io.kotest.matchers.shouldBe
|
||||
import io.kotest.matchers.shouldNotBe
|
||||
import io.kotest.matchers.string.shouldContain
|
||||
@ -753,7 +752,6 @@ class TestOptimization: FunSpec({
|
||||
}
|
||||
}"""
|
||||
val result = compileText(C64Target(), optimize=true, src, writeAssembly=false)!!
|
||||
printProgram(result.program)
|
||||
val stmts = result.program.entrypoint.statements
|
||||
stmts.size shouldBe 5
|
||||
val ifStmt = stmts[4] as IfElse
|
||||
|
@ -3,9 +3,15 @@ package prog8tests.ast
|
||||
import io.kotest.core.spec.style.FunSpec
|
||||
import io.kotest.matchers.shouldBe
|
||||
import io.kotest.matchers.shouldNotBe
|
||||
import prog8.ast.IFunctionCall
|
||||
import prog8.ast.expressions.IdentifierReference
|
||||
import prog8.ast.expressions.StringLiteral
|
||||
import prog8.ast.statements.Assignment
|
||||
import prog8.ast.statements.InlineAssembly
|
||||
import prog8.ast.statements.VarDecl
|
||||
import prog8.code.core.Position
|
||||
import prog8.code.target.C64Target
|
||||
import prog8.compiler.printProgram
|
||||
import prog8tests.helpers.compileText
|
||||
|
||||
class TestVarious: FunSpec({
|
||||
@ -61,5 +67,53 @@ main {
|
||||
}"""
|
||||
compileText(C64Target(), false, text, writeAssembly = false) shouldBe null
|
||||
}
|
||||
|
||||
test("simple string comparison still works") {
|
||||
val src="""
|
||||
main {
|
||||
sub start() {
|
||||
ubyte @shared value
|
||||
str thing = "????"
|
||||
|
||||
if thing=="name" {
|
||||
value++
|
||||
}
|
||||
|
||||
if thing!="name" {
|
||||
value++
|
||||
}
|
||||
}
|
||||
}"""
|
||||
val result = compileText(C64Target(), optimize=false, src, writeAssembly=true)!!
|
||||
val stmts = result.program.entrypoint.statements
|
||||
stmts.size shouldBe 6
|
||||
}
|
||||
|
||||
test("string concatenation and repeats") {
|
||||
val src="""
|
||||
main {
|
||||
sub start() {
|
||||
str @shared name = "part1" + "part2"
|
||||
str @shared rept = "rep"*4
|
||||
const ubyte times = 3
|
||||
name = "xx1" + "xx2"
|
||||
rept = "xyz" * (times+1)
|
||||
}
|
||||
}"""
|
||||
val result = compileText(C64Target(), optimize=false, src, writeAssembly=true)!!
|
||||
printProgram(result.program)
|
||||
val stmts = result.program.entrypoint.statements
|
||||
stmts.size shouldBe 6
|
||||
val name1 = stmts[0] as VarDecl
|
||||
val rept1 = stmts[1] as VarDecl
|
||||
(name1.value as StringLiteral).value shouldBe "part1part2"
|
||||
(rept1.value as StringLiteral).value shouldBe "reprepreprep"
|
||||
val name2strcopy = stmts[3] as IFunctionCall
|
||||
val rept2strcopy = stmts[4] as IFunctionCall
|
||||
val name2 = name2strcopy.args.first() as IdentifierReference
|
||||
val rept2 = rept2strcopy.args.first() as IdentifierReference
|
||||
(name2.targetVarDecl(result.program)!!.value as StringLiteral).value shouldBe "xx1xx2"
|
||||
(rept2.targetVarDecl(result.program)!!.value as StringLiteral).value shouldBe "xyzxyzxyzxyz"
|
||||
}
|
||||
})
|
||||
|
||||
|
@ -3,7 +3,6 @@ TODO
|
||||
|
||||
For next release
|
||||
^^^^^^^^^^^^^^^^
|
||||
- fix compiler crash when comparing strings
|
||||
- make it possible to inline non-asmsub routines that just contain a single statement (return, functioncall, assignment)
|
||||
Only if the arguments are simple expressions, and the inlined subroutine cannot contain further nested subroutines!
|
||||
This requires all identifiers in the inlined expression to be changed to fully scoped names (because their scope changes).
|
||||
|
Loading…
Reference in New Issue
Block a user