1
0
mirror of https://github.com/KarolS/millfork.git synced 2024-07-05 09:28:54 +00:00

6502: Check if memset is over actual pointers

This commit is contained in:
Karol Stasiak 2018-08-07 22:15:50 +02:00
parent 02d6b5b71c
commit 46df8a6f21
3 changed files with 10 additions and 9 deletions

View File

@ -17,6 +17,7 @@ object MosBulkMemoryOperations {
target.index.containsVariable(f.variable) ||
!target.index.isPure ||
f.direction == ForDirection.DownTo) return MosStatementCompiler.compileForStatement(ctx, f)
ctx.env.getPointy(target.name)
val sizeExpr = f.direction match {
case ForDirection.DownTo =>
SumExpression(List(false -> f.start, true -> f.end, false -> LiteralExpression(1, 1)), decimal = false)

View File

@ -297,15 +297,13 @@ class Environment(val parent: Option[Environment], val prefix: String, val cpuFa
case th@InitializedArray(_, _, cs, _, i, e, _) => ConstantPointy(th.toAddress, Some(name), Some(cs.length), i, e)
case th@UninitializedArray(_, size, _, i, e, _) => ConstantPointy(th.toAddress, Some(name), Some(size), i, e)
case th@RelativeArray(_, _, size, _, i, e) => ConstantPointy(th.toAddress, Some(name), Some(size), i, e)
case ConstantThing(_, value, typ) if typ.size <= 2 =>
case ConstantThing(_, value, typ) if typ.size <= 2 && typ.isPointy =>
val b = get[VariableType]("byte")
val w = get[VariableType]("word")
// TODO:
ConstantPointy(value, None, None, w, b)
case th:VariableInMemory =>
case th:VariableInMemory if th.typ.isPointy=>
val b = get[VariableType]("byte")
val w = get[VariableType]("word")
// TODO:
VariablePointy(th.toAddress, w, b)
case _ =>
log.error(s"$name is not a valid pointer or array")
@ -340,11 +338,11 @@ class Environment(val parent: Option[Environment], val prefix: String, val cpuFa
addThing(BasicPlainType("int112", 14), None)
addThing(BasicPlainType("int120", 15), None)
addThing(BasicPlainType("int128", 16), None)
val p = DerivedPlainType("pointer", w, isSigned = false)
val p = DerivedPlainType("pointer", w, isSigned = false, isPointy = true)
addThing(p, None)
// addThing(DerivedPlainType("farpointer", get[PlainType]("farword"), isSigned = false), None)
addThing(DerivedPlainType("ubyte", b, isSigned = false), None)
addThing(DerivedPlainType("sbyte", b, isSigned = true), None)
addThing(DerivedPlainType("ubyte", b, isSigned = false, isPointy = false), None)
addThing(DerivedPlainType("sbyte", b, isSigned = true, isPointy = false), None)
addThing(Alias("unsigned8", "ubyte"), None)
addThing(Alias("signed8", "sbyte"), None)
val trueType = ConstantBooleanType("true$", value = true)

View File

@ -32,6 +32,8 @@ sealed trait Type extends CallableThing {
def isAssignableTo(targetType: Type): Boolean = isCompatible(targetType)
def isArithmetic = false
def isPointy = false
}
sealed trait VariableType extends Type
@ -49,7 +51,7 @@ sealed trait PlainType extends VariableType {
override def isAssignableTo(targetType: Type): Boolean = isCompatible(targetType) || (targetType match {
case BasicPlainType(_, size) => size > this.size // TODO
case DerivedPlainType(_, parent, size) => isAssignableTo(parent)
case DerivedPlainType(_, parent, size, _) => isAssignableTo(parent)
case _ => false
})
@ -62,7 +64,7 @@ case class BasicPlainType(name: String, size: Int) extends PlainType {
override def isSubtypeOf(other: Type): Boolean = this == other
}
case class DerivedPlainType(name: String, parent: PlainType, isSigned: Boolean) extends PlainType {
case class DerivedPlainType(name: String, parent: PlainType, isSigned: Boolean, override val isPointy: Boolean) extends PlainType {
def size: Int = parent.size
override def isSubtypeOf(other: Type): Boolean = parent == other || parent.isSubtypeOf(other)