1
0
mirror of https://gitlab.com/camelot/kickc.git synced 2024-11-27 19:50:10 +00:00

Fixed signed word greater-than fragments with errors. Progress on structs containing arrays elements. #312

This commit is contained in:
jespergravgaard 2019-09-12 23:48:12 +02:00
parent f110b86ee1
commit 24e40b9083
46 changed files with 7018 additions and 2481 deletions

View File

@ -0,0 +1,5 @@
lda {c1}
sta $fe
lda {c1}+1
sta $ff
lda ($fe),y

View File

@ -1,10 +1,9 @@
lda {z1}
cmp {c1},x
lda {z1}+1
sbc {c1}+1,x
lda {c1},x
cmp {z1}
lda {c1}+1,x
sbc {z1}+1
bvc !+
eor #$80
!:
beq !e+
bpl {la1}
bmi {la1}
!e:

View File

@ -1,10 +1,9 @@
lda {z1}
cmp {c1},y
lda {z1}+1
sbc {c1}+1,y
lda {c1},y
cmp {z1}
lda {c1}+1,y
sbc {z1}+1
bvc !+
eor #$80
!:
beq !e+
bpl {la1}
bmi {la1}
!e:

View File

@ -1,10 +1,8 @@
lda {z1}
cmp #<{c1}
lda {z1}+1
sbc #>{c1}
lda #<{c1}
cmp {z1}
lda #>{c1}
sbc {z1}+1
bvc !+
eor #$80
!:
beq !e+
bpl {la1}
!e:
bmi {la1}

View File

@ -1,10 +1,9 @@
lda {z1}
cmp {z2}
lda {z1}+1
sbc {z2}+1
lda {z2}
cmp {z1}
lda {z2}+1
sbc {z1}+1
bvc !+
eor #$80
!:
beq !e+
bpl {la1}
bmi {la1}
!e:

View File

@ -0,0 +1,158 @@
package dk.camelot64.kickc.asm;
import java.util.ArrayList;
import java.util.List;
/** A sequence of data elements to add to the ASM program. */
public class AsmDataChunk {
public interface AsmDataElement {
}
/** A single numeric data element. */
public static class AsmDataNumericElement implements AsmDataElement {
/** The type of the data element. */
AsmDataNumeric.Type type;
/** The value of the data element. */
String value;
public AsmDataNumericElement(AsmDataNumeric.Type type, String value) {
this.type = type;
this.value = value;
}
public AsmDataNumeric.Type getType() {
return type;
}
public String getValue() {
return value;
}
}
/** A number of identical numerical data elements. */
public static class AsmDataFilledElement implements AsmDataElement {
AsmDataNumeric.Type type;
String sizeAsm;
int size;
String fillValue;
public AsmDataFilledElement(AsmDataNumeric.Type type, String sizeAsm, int size, String fillValue) {
this.type = type;
this.sizeAsm = sizeAsm;
this.size = size;
this.fillValue = fillValue;
}
public AsmDataNumeric.Type getType() {
return type;
}
public String getSizeAsm() {
return sizeAsm;
}
public int getSize() {
return size;
}
public String getFillValue() {
return fillValue;
}
}
/** A string data elements. */
public static class AsmDataStringElement implements AsmDataElement {
String value;
public AsmDataStringElement(String value) {
this.value = value;
}
public String getValue() {
return value;
}
}
/** A sequence of data elements. */
List<AsmDataElement> elements;
public AsmDataChunk() {
this.elements = new ArrayList<>();
}
public void addDataNumeric(AsmDataNumeric.Type type, String value) {
elements.add(new AsmDataNumericElement(type, value));
}
public void addDataFilled(AsmDataNumeric.Type type, String sizeAsm, int size, String fillValue) {
elements.add(new AsmDataFilledElement(type, sizeAsm, size, fillValue));
}
public void addDataString(String string) {
elements.add(new AsmDataStringElement(string));
}
public List<AsmDataElement> getElements() {
return elements;
}
/**
* Add BYTE/WORD/DWORD data declaration to the ASM for a whole chunk of numeric data.
* Produces 1-N ASM lines depending on the number of and types of data added.
*
* @param label The label of the data. Can be null.
* @param dataChunk The chunk of numeric data to add.
*/
public void addToAsm(String label, AsmProgram asm) {
AsmDataNumeric.Type currentNumericType = null;
List<String> currentNumericElements = null;
for(AsmDataChunk.AsmDataElement element : this.getElements()) {
if(element instanceof AsmDataFilledElement) {
if(currentNumericElements.size()>0) {
asm.addDataNumeric(label, currentNumericType, currentNumericElements);
currentNumericElements = null;
currentNumericType = null;
}
AsmDataFilledElement filledElement = (AsmDataFilledElement) element;
asm.addDataFilled(label, filledElement.getType(), filledElement.getSizeAsm(), filledElement.getSize(), filledElement.getFillValue());
label = null; // Only output label once
} else if(element instanceof AsmDataStringElement) {
if(currentNumericElements.size()>0) {
asm.addDataNumeric(label, currentNumericType, currentNumericElements);
currentNumericElements = null;
currentNumericType = null;
}
asm.addDataString(label, ((AsmDataStringElement) element).getValue());
label = null; // Only output label once
} else if(element instanceof AsmDataNumericElement) {
AsmDataNumericElement numericElement = (AsmDataNumericElement) element;
AsmDataNumeric.Type type = numericElement.getType();
if(currentNumericType == null) {
// First element - initialize current
currentNumericType = type;
currentNumericElements = new ArrayList<>();
currentNumericElements.add(numericElement.getValue());
} else if(currentNumericType.equals(type)) {
// An element with the same type as the current - add it to the current list
currentNumericElements.add(numericElement.getValue());
} else {
// Another type of element - output the current list and initialize a new list
asm.addDataNumeric(label, currentNumericType, currentNumericElements);
label = null; // Only output label once
currentNumericType = type;
currentNumericElements = new ArrayList<>();
currentNumericElements.add(numericElement.getValue());
}
}
}
// Output final list if present
if(currentNumericElements!=null && currentNumericElements.size()>0) {
asm.addDataNumeric(label, currentNumericType, currentNumericElements);
}
}
}

View File

@ -63,7 +63,7 @@ public class AsmDataNumeric implements AsmLine {
this.index = index;
}
public static enum Type {
public enum Type {
BYTE("byte", 1),
WORD("word", 2),
DWORD("dword", 4);

View File

@ -106,84 +106,6 @@ public class AsmProgram {
addLine(new AsmDataNumeric(label, type, asmElements));
}
/** A sequence of numeric data elements to add to the ASM program.*/
public static class AsmDataNumericChunk {
/** A single data element. */
public static class AsmDataNumericElement {
/** The type of the data element. */
AsmDataNumeric.Type type;
/** The value of the data element. */
String value;
public AsmDataNumericElement(AsmDataNumeric.Type type, String value) {
this.type = type;
this.value = value;
}
public AsmDataNumeric.Type getType() {
return type;
}
public String getValue() {
return value;
}
}
/** A sequence of numeric data elements. */
List<AsmDataNumericElement> elements;
public AsmDataNumericChunk() {
this.elements = new ArrayList<>();
}
public void addData(AsmDataNumeric.Type type, String value) {
elements.add(new AsmDataNumericElement(type, value));
}
public List<AsmDataNumericElement> getElements() {
return elements;
}
}
/**
* Add BYTE/WORD/DWORD data declaration to the ASM for a whole chunk of numeric data.
* Produces 1-N ASM lines depending on the number of and types of data added.
*
* @param label The label of the data. Can be null.
* @param dataChunk The chunk of numeric data to add.
*/
public void addDataNumeric(String label, AsmDataNumericChunk dataChunk ) {
AsmDataNumeric.Type currentType = null;
List<String> currentElements = null;
for(AsmDataNumericChunk.AsmDataNumericElement element : dataChunk.getElements()) {
AsmDataNumeric.Type type = element.getType();
if(currentType==null) {
// First element - initialize current
currentType = type;
currentElements = new ArrayList<>();
currentElements.add(element.getValue());
} else if(currentType.equals(type)) {
// An element with the same type as the current - add it to the current list
currentElements.add(element.getValue());
} else {
// Another type of element - output the current list and initialize a new list
addDataNumeric(label, currentType, currentElements);
label = null; // Only output label once
currentType = type;
currentElements = new ArrayList<>();
currentElements.add(element.getValue());
}
}
// Output final list if present
if(currentElements.size()>0) {
addDataNumeric(label, currentType, currentElements);
}
}
/**
* Add a FILL data declaration to the ASM
*

View File

@ -37,13 +37,13 @@ public class StructDefinition extends Scope {
* @param member The member to find offset for
* @return The byte offset of the start of the member data
*/
public long getMemberByteOffset(Variable member) {
public long getMemberByteOffset(Variable member, ProgramScope programScope) {
long byteOffset=0;
for(Variable structMember : getAllVariables(false)) {
if(structMember.equals(member)) {
break;
} else {
byteOffset += structMember.getType().getSizeBytes();
byteOffset += SymbolTypeStruct.getMemberSizeBytes(structMember.getType(), programScope);
}
}
return byteOffset;

View File

@ -3,6 +3,10 @@ package dk.camelot64.kickc.model.types;
import dk.camelot64.kickc.model.symbols.ProgramScope;
import dk.camelot64.kickc.model.symbols.StructDefinition;
import dk.camelot64.kickc.model.symbols.Variable;
import dk.camelot64.kickc.model.values.ConstantInteger;
import dk.camelot64.kickc.model.values.ConstantLiteral;
import dk.camelot64.kickc.model.values.ConstantValue;
import dk.camelot64.kickc.model.values.RValue;
import java.util.Objects;
@ -17,7 +21,7 @@ public class SymbolTypeStruct implements SymbolType {
public SymbolTypeStruct(StructDefinition structDefinition) {
this.name = structDefinition.getLocalName();
this.sizeBytes = calculateSizeBytes(structDefinition);
this.sizeBytes = calculateSizeBytes(structDefinition, null);
}
@Override
@ -47,14 +51,35 @@ public class SymbolTypeStruct implements SymbolType {
* @param structDefinition The struct definition (get using getStructDefinition)
* @return The number of bytes a struct value require
*/
public int calculateSizeBytes(StructDefinition structDefinition) {
public int calculateSizeBytes(StructDefinition structDefinition, ProgramScope programScope) {
int sizeBytes = 0;
for(Variable member : structDefinition.getAllVariables(false)) {
sizeBytes += member.getType().getSizeBytes();
SymbolType memberType = member.getType();
int memberSize = getMemberSizeBytes(memberType, programScope);
sizeBytes += memberSize;
}
return sizeBytes;
}
public static int getMemberSizeBytes(SymbolType memberType, ProgramScope programScope) {
if(memberType instanceof SymbolTypeArray && ((SymbolTypeArray) memberType).getSize()!=null) {
if(programScope!=null) {
RValue memberArraySize = ((SymbolTypeArray) memberType).getSize();
if(memberArraySize instanceof ConstantValue) {
ConstantLiteral sizeLiteral = ((ConstantValue) memberArraySize).calculateLiteral(programScope);
if(sizeLiteral instanceof ConstantInteger) {
return ((ConstantInteger) sizeLiteral).getInteger().intValue();
}
}
} else {
return 5; // Add a token size
}
} else {
return memberType.getSizeBytes();
}
throw new InternalError("Memeber type not handled "+memberType);
}
@Override
public boolean equals(Object o) {
if(this == o) return true;

View File

@ -12,7 +12,6 @@ import java.util.Objects;
*/
public class ConstantString implements ConstantLiteral<String> {
/** String encoding. */
public static enum Encoding {
PETSCII_MIXED("petscii_mixed", "pm"),
@ -67,6 +66,14 @@ public class ConstantString implements ConstantLiteral<String> {
return zeroTerminated;
}
/**
* Get the length of the string - including zero-termination if present.
* @return The length
*/
public int getStringLength() {
return value.length() + (zeroTerminated?1:0);
}
@Override
public String toString() {
return toString(null);

View File

@ -36,7 +36,7 @@ public class Pass1StructTypeSizeFix extends Pass2SsaOptimization {
if(type instanceof SymbolTypeStruct) {
SymbolTypeStruct typeStruct = (SymbolTypeStruct) type;
StructDefinition structDefinition = typeStruct.getStructDefinition(getScope());
int sizeBytes = typeStruct.calculateSizeBytes(structDefinition);
int sizeBytes = typeStruct.calculateSizeBytes(structDefinition, getScope());
if(sizeBytes!=typeStruct.getSizeBytes()) {
getLog().append("Fixing struct type size "+type.getTypeName() + " to "+sizeBytes);
typeStruct.setSizeBytes(sizeBytes);

View File

@ -9,6 +9,7 @@ import dk.camelot64.kickc.model.symbols.StructDefinition;
import dk.camelot64.kickc.model.symbols.Variable;
import dk.camelot64.kickc.model.types.SymbolType;
import dk.camelot64.kickc.model.types.SymbolTypeArray;
import dk.camelot64.kickc.model.types.SymbolTypeConversion;
import dk.camelot64.kickc.model.types.SymbolTypeStruct;
import dk.camelot64.kickc.model.values.*;
@ -28,7 +29,7 @@ public class Pass2ConstantInitializerValueLists extends Pass2SsaOptimization {
*
* @return true optimization was performed. false if no optimization was possible.
*/
@Override
@Override
public boolean step() {
final boolean[] modified = {false};
ProgramValueIterator.execute(getGraph(), (programValue, currentStmt, stmtIt, currentBlock) -> {
@ -100,7 +101,7 @@ public class Pass2ConstantInitializerValueLists extends Pass2SsaOptimization {
SymbolType declaredElementType = memberDef.getType();
ConstantValue memberValue = constantValues.get(i);
SymbolType elmType = memberValue.getType(getScope());
if(!elmType.equals(declaredElementType)) {
if(!SymbolTypeConversion.assignmentTypeMatch(declaredElementType, elmType)) {
throw new CompileError("Initializer element "+ memberValue.toString(getProgram())+" does not match struct member type "+memberDef.toString(getProgram()), currentStmt);
}
memberValues.put(memberDef.getRef(), memberValue);

View File

@ -58,7 +58,7 @@ public class Pass3AssertArrayLengths extends Pass2SsaAssertion {
} else {
ConstantLiteral constantLiteral = constantValue.calculateLiteral(getScope());
if(constantLiteral instanceof ConstantString) {
Integer assignedSizeVal = ((ConstantString) constantLiteral).getString().length();
Integer assignedSizeVal = ((ConstantString) constantLiteral).getStringLength();
if(assignedSizeVal > declaredSizeInt) {
throw new CompileError("Error! Array length mismatch " + constantVar.toString(getProgram()));
}

View File

@ -462,10 +462,10 @@ public class Pass4CodeGeneration {
// Constant array of structs - output each struct as a separate chunk
asm.addLabel(asmName).setDontOptimize(true);
for(ConstantValue element : constantArrayList.getElements()) {
AsmProgram.AsmDataNumericChunk asmDataChunk = new AsmProgram.AsmDataNumericChunk();
AsmDataChunk asmDataChunk = new AsmDataChunk();
ensureEncoding(asm, element);
addChunkData(asmDataChunk, element, scopeRef);
asm.addDataNumeric(null, asmDataChunk);
asmDataChunk.addToAsm(null, asm);
}
// Pad output to match declared size (if larger than the data list)
int dataSize = constantArrayList.getElements().size();
@ -474,9 +474,9 @@ public class Pass4CodeGeneration {
int padding = declaredSize - dataSize;
ConstantStructValue zeroStructValue = (ConstantStructValue) ZeroConstantValues.zeroValue(elementType, program.getScope());
for(int i=0; i<padding; i++) {
AsmProgram.AsmDataNumericChunk asmDataChunk = new AsmProgram.AsmDataNumericChunk();
AsmDataChunk asmDataChunk = new AsmDataChunk();
addChunkData(asmDataChunk, zeroStructValue, scopeRef);
asm.addDataNumeric(null, asmDataChunk);
asmDataChunk.addToAsm(null, asm);
}
}
} else if(elementType instanceof SymbolTypeArray) {
@ -484,12 +484,12 @@ public class Pass4CodeGeneration {
throw new InternalError("Array of array not supported");
} else {
// Constant array of a "simple" type - add to a single chunk
AsmProgram.AsmDataNumericChunk asmDataChunk = new AsmProgram.AsmDataNumericChunk();
AsmDataChunk asmDataChunk = new AsmDataChunk();
for(ConstantValue element : constantArrayList.getElements()) {
ensureEncoding(asm, element);
addChunkData(asmDataChunk, element, scopeRef);
}
asm.addDataNumeric(asmName, asmDataChunk);
asmDataChunk.addToAsm(asmName, asm);
// Pad output to match declared size (if larger than the data list)
int dataSize = constantArrayList.getElements().size();
Integer declaredSize = getArrayDeclaredSize(constantVar);
@ -586,13 +586,12 @@ public class Pass4CodeGeneration {
ensureEncoding(asm, constantValue);
String asmConstant = AsmFormat.getAsmConstant(program, constantValue, 99, scopeRef);
asm.addDataString(AsmFormat.asmFix(asmName), asmConstant);
int dataSize = ((ConstantString) literal).getString().length();
if(((ConstantString) literal).isZeroTerminated()) {
asm.addDataNumeric(null, AsmDataNumeric.Type.BYTE, Collections.singletonList(AsmFormat.getAsmNumber(0L)));
dataSize++;
}
// Pad output to match declared size (if larger than the data list)
Integer declaredSize = getArrayDeclaredSize(constantVar);
int dataSize = ((ConstantString) literal).getStringLength();
if(declaredSize!=null && declaredSize>dataSize) {
int padding = declaredSize-dataSize;
asm.addDataFilled(null, AsmDataNumeric.Type.BYTE, Integer.toString(padding), padding, "0");
@ -637,7 +636,7 @@ public class Pass4CodeGeneration {
* @param dataChunk The data chunk
* @param value The constant value
*/
private void addChunkData(AsmProgram.AsmDataNumericChunk dataChunk, ConstantValue value, ScopeRef scopeRef) {
private void addChunkData(AsmDataChunk dataChunk, ConstantValue value, ScopeRef scopeRef) {
SymbolType elementType = value.getType(program.getScope());
if(elementType instanceof SymbolTypeStruct) {
// Add each struct member recursively
@ -647,13 +646,13 @@ public class Pass4CodeGeneration {
addChunkData(dataChunk, memberValue, scopeRef);
}
} else if(SymbolType.BYTE.equals(elementType) || SymbolType.SBYTE.equals(elementType)) {
dataChunk.addData(AsmDataNumeric.Type.BYTE, AsmFormat.getAsmConstant(program, value, 99, scopeRef));
dataChunk.addDataNumeric(AsmDataNumeric.Type.BYTE, AsmFormat.getAsmConstant(program, value, 99, scopeRef));
} else if(SymbolType.WORD.equals(elementType) || SymbolType.SWORD.equals(elementType)) {
dataChunk.addData(AsmDataNumeric.Type.WORD, AsmFormat.getAsmConstant(program, value, 99, scopeRef));
dataChunk.addDataNumeric(AsmDataNumeric.Type.WORD, AsmFormat.getAsmConstant(program, value, 99, scopeRef));
} else if(SymbolType.DWORD.equals(elementType) || SymbolType.SDWORD.equals(elementType)) {
dataChunk.addData(AsmDataNumeric.Type.DWORD, AsmFormat.getAsmConstant(program, value, 99, scopeRef));
dataChunk.addDataNumeric(AsmDataNumeric.Type.DWORD, AsmFormat.getAsmConstant(program, value, 99, scopeRef));
} else if(elementType instanceof SymbolTypePointer) {
dataChunk.addData(AsmDataNumeric.Type.WORD, AsmFormat.getAsmConstant(program, value, 99, scopeRef));
dataChunk.addDataNumeric(AsmDataNumeric.Type.WORD, AsmFormat.getAsmConstant(program, value, 99, scopeRef));
} else {
throw new InternalError("Unhandled array element type " + elementType.toString() + " value " + value.toString(program));
}

View File

@ -96,7 +96,7 @@ public class PassNSizeOfSimplification extends Pass2SsaOptimization {
}
if(stringLiteral instanceof ConstantString) {
ConstantString constString = (ConstantString) stringLiteral;
int length = constString.getString().length();
int length = constString.getStringLength();
getLog().append("Resolving string sizeof() " + unary.toString(getProgram()));
ConstantRef sizeOfChar = OperatorSizeOf.getSizeOfConstantVar(getScope(), SymbolType.BYTE);
programValue.set(new ConstantBinary(new ConstantInteger((long) length), Operators.MULTIPLY, sizeOfChar));

View File

@ -6,10 +6,7 @@ import dk.camelot64.kickc.model.iterator.ProgramValueIterator;
import dk.camelot64.kickc.model.operators.Operators;
import dk.camelot64.kickc.model.statements.StatementAssignment;
import dk.camelot64.kickc.model.symbols.*;
import dk.camelot64.kickc.model.types.SymbolType;
import dk.camelot64.kickc.model.types.SymbolTypeInference;
import dk.camelot64.kickc.model.types.SymbolTypePointer;
import dk.camelot64.kickc.model.types.SymbolTypeStruct;
import dk.camelot64.kickc.model.types.*;
import dk.camelot64.kickc.model.values.*;
import java.util.Locale;
@ -42,18 +39,33 @@ public class PassNStructPointerRewriting extends Pass2SsaOptimization {
ConstantRef memberOffsetConstant = getMemberOffsetConstant(getScope(), structDefinition, structMemberRef.getMemberName());
SymbolType memberType = SymbolTypeInference.inferType(getScope(), structMemberRef);
getLog().append("Rewriting struct pointer member access " + programValue.get().toString(getProgram()));
// Cast struct pointer to the type of the member
CastValue structTypedPointer = new CastValue(new SymbolTypePointer(memberType), structPointer);
// Create temporary variable to hold pointer to member ($1)
Scope scope = getScope().getScope(currentBlock.getScope());
VariableIntermediate memberAddress = scope.addVariableIntermediate();
memberAddress.setType(new SymbolTypePointer(memberType));
// Add statement $1 = ptr_struct + OFFSET_STRUCT_NAME_MEMBER
stmtIt.previous();
stmtIt.add(new StatementAssignment(memberAddress.getRef(), structTypedPointer, Operators.PLUS, memberOffsetConstant, currentStmt.getSource(), currentStmt.getComments()));
stmtIt.next();
// Replace (*ptr_struct).x with *($1)
programValue.set(new PointerDereferenceSimple(memberAddress.getRef()));
if(memberType instanceof SymbolTypeArray && ((SymbolTypeArray) memberType).getSize()!=null) {
// Cast struct pointer to the type of the member
CastValue structTypedPointer = new CastValue(memberType, structPointer);
// Create temporary variable to hold pointer to member ($1)
Scope scope = getScope().getScope(currentBlock.getScope());
VariableIntermediate memberAddress1 = scope.addVariableIntermediate();
memberAddress1.setType(memberType);
// Add statement $1 = ptr_struct + OFFSET_STRUCT_NAME_MEMBER
stmtIt.previous();
stmtIt.add(new StatementAssignment(memberAddress1.getRef(), structTypedPointer, Operators.PLUS, memberOffsetConstant, currentStmt.getSource(), currentStmt.getComments()));
stmtIt.next();
// Replace (*ptr_struct).x with *($1)
programValue.set(memberAddress1.getRef());
} else {
// Cast struct pointer to the type of the member
CastValue structTypedPointer = new CastValue(new SymbolTypePointer(memberType), structPointer);
// Create temporary variable to hold pointer to member ($1)
Scope scope = getScope().getScope(currentBlock.getScope());
VariableIntermediate memberAddress = scope.addVariableIntermediate();
memberAddress.setType(new SymbolTypePointer(memberType));
// Add statement $1 = ptr_struct + OFFSET_STRUCT_NAME_MEMBER
stmtIt.previous();
stmtIt.add(new StatementAssignment(memberAddress.getRef(), structTypedPointer, Operators.PLUS, memberOffsetConstant, currentStmt.getSource(), currentStmt.getComments()));
stmtIt.next();
// Replace (*ptr_struct).x with *($1)
programValue.set(new PointerDereferenceSimple(memberAddress.getRef()));
}
modified.set(true);
} else if(struct instanceof PointerDereferenceIndexed) {
RValue structPointer = ((PointerDereferenceIndexed) struct).getPointer();
@ -66,18 +78,37 @@ public class PassNStructPointerRewriting extends Pass2SsaOptimization {
ConstantRef memberOffsetConstant = getMemberOffsetConstant(getScope(), structDefinition, structMemberRef.getMemberName());
SymbolType memberType = SymbolTypeInference.inferType(getScope(), structMemberRef);
getLog().append("Rewriting struct pointer member access " + programValue.get().toString(getProgram()));
// Cast struct pointer to the type of the member
CastValue structTypedPointer = new CastValue(new SymbolTypePointer(memberType), structPointer);
// Create temporary variable to hold pointer to member ($1)
Scope scope = getScope().getScope(currentBlock.getScope());
VariableIntermediate memberAddress = scope.addVariableIntermediate();
memberAddress.setType(new SymbolTypePointer(memberType));
// Add statement $1 = ptr_struct + OFFSET_STRUCT_NAME_MEMBER
stmtIt.previous();
stmtIt.add(new StatementAssignment(memberAddress.getRef(), structTypedPointer, Operators.PLUS, memberOffsetConstant, currentStmt.getSource(), currentStmt.getComments()));
stmtIt.next();
// Replace ptr_struct[idx].x with ($1)[idx]
programValue.set(new PointerDereferenceIndexed(memberAddress.getRef(), ((PointerDereferenceIndexed) struct).getIndex()));
if(memberType instanceof SymbolTypeArray && ((SymbolTypeArray) memberType).getSize()!=null) {
// Cast struct pointer to the type of the member
CastValue structTypedPointer = new CastValue(memberType, structPointer);
// Create temporary variable to hold pointer to member ($1)
Scope scope = getScope().getScope(currentBlock.getScope());
VariableIntermediate memberAddress1 = scope.addVariableIntermediate();
memberAddress1.setType(memberType);
VariableIntermediate memberAddress2 = scope.addVariableIntermediate();
memberAddress2.setType(memberType);
// Add statement $1 = ptr_struct + OFFSET_STRUCT_NAME_MEMBER
stmtIt.previous();
stmtIt.add(new StatementAssignment(memberAddress1.getRef(), structTypedPointer, Operators.PLUS, ((PointerDereferenceIndexed) struct).getIndex(), currentStmt.getSource(), currentStmt.getComments()));
stmtIt.add(new StatementAssignment(memberAddress2.getRef(), memberAddress1.getRef(), Operators.PLUS, memberOffsetConstant, currentStmt.getSource(), currentStmt.getComments()));
stmtIt.next();
// Replace ptr_struct[idx].x with ($1)[idx]
programValue.set(memberAddress2.getRef());
//throw new InternalError("Fixed size arrays not supported inside structs used through pointers/arrays", currentStmt);
} else {
// Cast struct pointer to the type of the member
CastValue structTypedPointer = new CastValue(new SymbolTypePointer(memberType), structPointer);
// Create temporary variable to hold pointer to member ($1)
Scope scope = getScope().getScope(currentBlock.getScope());
VariableIntermediate memberAddress = scope.addVariableIntermediate();
memberAddress.setType(new SymbolTypePointer(memberType));
// Add statement $1 = ptr_struct + OFFSET_STRUCT_NAME_MEMBER
stmtIt.previous();
stmtIt.add(new StatementAssignment(memberAddress.getRef(), structTypedPointer, Operators.PLUS, memberOffsetConstant, currentStmt.getSource(), currentStmt.getComments()));
stmtIt.next();
// Replace ptr_struct[idx].x with ($1)[idx]
programValue.set(new PointerDereferenceIndexed(memberAddress.getRef(), ((PointerDereferenceIndexed) struct).getIndex()));
}
modified.set(true);
}
}
@ -99,7 +130,7 @@ public class PassNStructPointerRewriting extends Pass2SsaOptimization {
if(memberOffsetConstant == null) {
// Constant not found - create it
Variable memberDef = structDefinition.getMember(memberName);
long memberByteOffset = structDefinition.getMemberByteOffset(memberDef);
long memberByteOffset = structDefinition.getMemberByteOffset(memberDef, programScope);
memberOffsetConstant = new ConstantVar(typeConstName, programScope, SymbolType.BYTE, new ConstantInteger(memberByteOffset & 0xff, SymbolType.BYTE), Scope.SEGMENT_DATA_DEFAULT);
programScope.add(memberOffsetConstant);
}

View File

@ -99,6 +99,11 @@ public class TestPrograms {
*/
@Test
public void testBitmapCircle2() throws IOException, URISyntaxException {
compileAndCompare("bitmap-circle-2");
}
@Test
public void testBitmapCircle() throws IOException, URISyntaxException {
compileAndCompare("bitmap-circle");
@ -650,9 +655,15 @@ public class TestPrograms {
*/
// TODO: FIX problem with initializers of array-elements inside structs
//@Test
//public void testStructPtr33() throws IOException, URISyntaxException {
// compileAndCompare("struct-ptr-33", log());
//}
@Test
public void testStructPtr32() throws IOException, URISyntaxException {
compileAndCompare("struct-ptr-32", log());
compileAndCompare("struct-ptr-32");
}
//@Test
@ -670,10 +681,11 @@ public class TestPrograms {
compileAndCompare("struct-ptr-29");
}
@Test
public void testStructPtr28() throws IOException, URISyntaxException {
compileAndCompare("struct-ptr-28");
}
// TODO: Fix problem with object-allocated structs that contain arrays!
//@Test
//public void testStructPtr28() throws IOException, URISyntaxException {
// compileAndCompare("struct-ptr-28");
//}
@Test
public void testStructPtr26() throws IOException, URISyntaxException {

View File

@ -0,0 +1,67 @@
import "c64"
const byte* SCREEN = $400;
const byte* BITMAP = $2000;
const byte* COLORS = $d800;
byte[] bitmask = { 128, 64, 32, 16, 8, 4, 2, 1 };
void main() {
fill(BITMAP,40*25*8,0);
fill(SCREEN,40*25,$16);
*BORDERCOL = BLUE;
*D011 = VIC_BMM|VIC_DEN|VIC_RSEL|3;
*VIC_MEMORY = (byte)((((word)SCREEN&$3fff)/$40)|(((word)BITMAP&$3fff)/$400));
for (int i = 1; i < 180; i += 5) {
circle(160,100,i);
}
do {} while (true);
}
void circle(int xc, int yc, int r) {
int x = 0;
int y = r;
int p = 3-(r << 1);
for(int x = 0; x <= y; x ++) {
if(p < 0) {
p = p + (x << 2) + 6;
} else {
y=y-1;
p = p + ((x-y) << 2) + 10;
}
plot(xc+x,yc-y);
plot(xc-x,yc-y);
plot(xc+x,yc+y);
plot(xc-x,yc+y);
plot(xc+y,yc-x);
plot(xc-y,yc-x);
plot(xc+y,yc+x);
plot(xc-y,yc+x);
}
}
void plot(int x, int y) {
if (x < 0 || x > 319 || y < 0 || y > 199) {
return; // bounds check
}
byte* location = BITMAP;
location += x & $fff8;
location += <y & 7;
location += ((y >> 3) * 320);
(*location) = (*location) | bitmask[x & 7];
}
// Fill some memory with a value
void fill(byte* start, int size, byte val) {
byte* end = start + size;
for(byte* addr = start; addr!=end; addr++) {
*addr = val;
}
}

View File

@ -5,7 +5,7 @@ import "print"
struct Person {
unsigned long id;
char[2] initials;
char[3] initials;
};
struct Person jesper = { 111172, "jg" };

View File

@ -14,7 +14,7 @@ void main() {
struct Person henriette;
henriette.id = 7;
henriette.name = "repsej";
henriette.name = "henriette";
print_person(henriette);
}

View File

@ -1,22 +1,26 @@
// Example of a struct containing an array
// Fails (by displaying "BB" ) because the memory layout is wrong - and the name is treated like a pointer (to 0x0000) instead of a value.
// https://gitlab.com/camelot/kickc/issues/312
struct Person {
char id;
char[16] name;
char[13] name;
unsigned int age;
};
struct Person[2] persons;
void main() {
persons[0].name[0] = 'a';
persons[1].name[0] = 'b';
persons[0].id = 7;
persons[1].id = 9;
persons[0].name[8] = 'a';
persons[1].name[8] = 'b';
persons[0].age = 321;
persons[1].age = 123;
const char* SCREEN = 0x0400;
struct Person* person = persons;
SCREEN[0] = person->name[0];
SCREEN[0] = person->name[8];
person++;
SCREEN[1] = person->name[0];
SCREEN[1] = person->name[8];
}

View File

@ -0,0 +1,25 @@
// Example of a struct containing an array
// Fails (by displaying "BB" ) because the memory layout is wrong - and the name is treated like a pointer (to 0x0000) instead of a value.
// https://gitlab.com/camelot/kickc/issues/312
struct Person {
char id;
char[13] name;
unsigned int age;
};
struct Person[2] persons = {
{ 7, "jesper", 321 },
{ 9, "henry", 123}
};
void main() {
const char* SCREEN = 0x0400;
struct Person* person = persons;
SCREEN[0] = person->name[8];
person++;
SCREEN[1] = person->name[8];
}

View File

@ -67,10 +67,8 @@ void compare(signed word w1, signed word w2, byte op) {
if(w1!=w2) r = TT;
ops = "!=";
}
if(w1>=0) print_char(' ');
print_sword(w1);
print_str(ops);
if(w2>=0) print_char(' ');
print_sword(w2);
print_char(r);
}

View File

@ -0,0 +1,445 @@
.pc = $801 "Basic"
:BasicUpstart(main)
.pc = $80d "Program"
.label BORDERCOL = $d020
.label D011 = $d011
.const VIC_BMM = $20
.const VIC_DEN = $10
.const VIC_RSEL = 8
.label VIC_MEMORY = $d018
.const BLUE = 6
.label SCREEN = $400
.label BITMAP = $2000
main: {
.label i = 6
ldx #0
lda #<$28*$19*8
sta.z fill.size
lda #>$28*$19*8
sta.z fill.size+1
lda #<BITMAP
sta.z fill.addr
lda #>BITMAP
sta.z fill.addr+1
jsr fill
ldx #$16
lda #<$28*$19
sta.z fill.size
lda #>$28*$19
sta.z fill.size+1
lda #<SCREEN
sta.z fill.addr
lda #>SCREEN
sta.z fill.addr+1
jsr fill
lda #BLUE
sta BORDERCOL
lda #VIC_BMM|VIC_DEN|VIC_RSEL|3
sta D011
lda #(SCREEN&$3fff)/$40|(BITMAP&$3fff)/$400
sta VIC_MEMORY
lda #<1
sta.z i
lda #>1
sta.z i+1
b1:
lda.z i
cmp #<$b4
lda.z i+1
sbc #>$b4
bvc !+
eor #$80
!:
bmi b2
b3:
jmp b3
b2:
lda.z i
sta.z circle.r
lda.z i+1
sta.z circle.r+1
jsr circle
lda.z i
clc
adc #<5
sta.z i
lda.z i+1
adc #>5
sta.z i+1
jmp b1
}
// circle(signed word zeropage(2) r)
circle: {
.const xc = $a0
.const yc = $64
.label _0 = 4
.label _5 = $a
.label _6 = $a
.label _7 = 4
.label _9 = $c
.label _10 = 4
.label r = 2
.label p = 4
.label y = 2
.label x1 = 8
lda.z r
asl
sta.z _0
lda.z r+1
rol
sta.z _0+1
lda #<3
sec
sbc.z p
sta.z p
lda #>3
sbc.z p+1
sta.z p+1
lda #<0
sta.z x1
sta.z x1+1
b1:
lda.z y
cmp.z x1
lda.z y+1
sbc.z x1+1
bvc !+
eor #$80
!:
bpl b2
rts
b2:
lda.z p+1
bpl !b3+
jmp b3
!b3:
sec
lda.z y
sbc #1
sta.z y
bcs !+
dec.z y+1
!:
lda.z x1
sec
sbc.z y
sta.z _5
lda.z x1+1
sbc.z y+1
sta.z _5+1
asl.z _6
rol.z _6+1
asl.z _6
rol.z _6+1
lda.z _7
clc
adc.z _6
sta.z _7
lda.z _7+1
adc.z _6+1
sta.z _7+1
lda.z p
clc
adc #<$a
sta.z p
lda.z p+1
adc #>$a
sta.z p+1
b4:
lda.z x1
clc
adc #<xc
sta.z plot.x
lda.z x1+1
adc #>xc
sta.z plot.x+1
lda #<yc
sec
sbc.z y
sta.z plot.y
lda #>yc
sbc.z y+1
sta.z plot.y+1
jsr plot
lda #<xc
sec
sbc.z x1
sta.z plot.x
lda #>xc
sbc.z x1+1
sta.z plot.x+1
lda #<yc
sec
sbc.z y
sta.z plot.y
lda #>yc
sbc.z y+1
sta.z plot.y+1
jsr plot
lda.z x1
clc
adc #<xc
sta.z plot.x
lda.z x1+1
adc #>xc
sta.z plot.x+1
lda.z y
clc
adc #<yc
sta.z plot.y
lda.z y+1
adc #>yc
sta.z plot.y+1
jsr plot
lda #<xc
sec
sbc.z x1
sta.z plot.x
lda #>xc
sbc.z x1+1
sta.z plot.x+1
lda.z y
clc
adc #<yc
sta.z plot.y
lda.z y+1
adc #>yc
sta.z plot.y+1
jsr plot
lda.z y
clc
adc #<xc
sta.z plot.x
lda.z y+1
adc #>xc
sta.z plot.x+1
lda #<yc
sec
sbc.z x1
sta.z plot.y
lda #>yc
sbc.z x1+1
sta.z plot.y+1
jsr plot
lda #<xc
sec
sbc.z y
sta.z plot.x
lda #>xc
sbc.z y+1
sta.z plot.x+1
lda #<yc
sec
sbc.z x1
sta.z plot.y
lda #>yc
sbc.z x1+1
sta.z plot.y+1
jsr plot
lda.z y
clc
adc #<xc
sta.z plot.x
lda.z y+1
adc #>xc
sta.z plot.x+1
lda.z x1
clc
adc #<yc
sta.z plot.y
lda.z x1+1
adc #>yc
sta.z plot.y+1
jsr plot
lda #<xc
sec
sbc.z y
sta.z plot.x
lda #>xc
sbc.z y+1
sta.z plot.x+1
lda.z x1
clc
adc #<yc
sta.z plot.y
lda.z x1+1
adc #>yc
sta.z plot.y+1
jsr plot
inc.z x1
bne !+
inc.z x1+1
!:
jmp b1
b3:
lda.z x1
asl
sta.z _9
lda.z x1+1
rol
sta.z _9+1
asl.z _9
rol.z _9+1
lda.z _10
clc
adc.z _9
sta.z _10
lda.z _10+1
adc.z _9+1
sta.z _10+1
lda.z p
clc
adc #<6
sta.z p
lda.z p+1
adc #>6
sta.z p+1
jmp b4
}
// plot(signed word zeropage($a) x, signed word zeropage($c) y)
plot: {
.label _8 = $e
.label _11 = $c
.label _12 = $10
.label x = $a
.label y = $c
.label location = $e
.label _15 = $10
.label _16 = $10
lda.z x+1
bpl !breturn+
jmp breturn
!breturn:
lda #<$13f
cmp.z x
lda #>$13f
sbc.z x+1
bvc !+
eor #$80
!:
bpl !breturn+
jmp breturn
!breturn:
lda.z y+1
bpl !breturn+
jmp breturn
!breturn:
lda.z y
cmp #<$c7+1
lda.z y+1
sbc #>$c7+1
bvc !+
eor #$80
!:
bmi !breturn+
jmp breturn
!breturn:
lda.z x
and #<$fff8
sta.z _8
lda.z x+1
and #>$fff8
sta.z _8+1
lda #<BITMAP
clc
adc.z location
sta.z location
lda #>BITMAP
adc.z location+1
sta.z location+1
lda.z y
and #7
clc
adc.z location
sta.z location
bcc !+
inc.z location+1
!:
lda.z _11+1
cmp #$80
ror.z _11+1
ror.z _11
lda.z _11+1
cmp #$80
ror.z _11+1
ror.z _11
lda.z _11+1
cmp #$80
ror.z _11+1
ror.z _11
lda.z _11
asl
sta.z _15
lda.z _11+1
rol
sta.z _15+1
asl.z _15
rol.z _15+1
lda.z _16
clc
adc.z _11
sta.z _16
lda.z _16+1
adc.z _11+1
sta.z _16+1
lda.z _12+1
sta.z $ff
lda.z _12
sta.z _12+1
lda #0
sta.z _12
lsr.z $ff
ror.z _12+1
ror.z _12
lsr.z $ff
ror.z _12+1
ror.z _12
lda.z location
clc
adc.z _12
sta.z location
lda.z location+1
adc.z _12+1
sta.z location+1
lda #7
and.z x
tay
lda bitmask,y
ldy #0
ora (location),y
sta (location),y
breturn:
rts
}
// Fill some memory with a value
// fill(signed word zeropage(6) size, byte register(X) val)
fill: {
.label end = 6
.label addr = 8
.label size = 6
lda.z addr
clc
adc.z end
sta.z end
lda.z addr+1
adc.z end+1
sta.z end+1
b1:
lda.z addr+1
cmp.z end+1
bne b2
lda.z addr
cmp.z end
bne b2
rts
b2:
txa
ldy #0
sta (addr),y
inc.z addr
bne !+
inc.z addr+1
!:
jmp b1
}
bitmask: .byte $80, $40, $20, $10, 8, 4, 2, 1

View File

@ -0,0 +1,158 @@
@begin: scope:[] from
[0] phi()
to:@1
@1: scope:[] from @begin
[1] phi()
[2] call main
to:@end
@end: scope:[] from @1
[3] phi()
main: scope:[main] from @1
[4] phi()
[5] call fill
to:main::@4
main::@4: scope:[main] from main
[6] phi()
[7] call fill
to:main::@5
main::@5: scope:[main] from main::@4
[8] *((const byte*) BORDERCOL#0) ← (const byte) BLUE#0
[9] *((const byte*) D011#0) ← (const byte) VIC_BMM#0|(const byte) VIC_DEN#0|(const byte) VIC_RSEL#0|(byte) 3
[10] *((const byte*) VIC_MEMORY#0) ← (byte)(word)(const byte*) SCREEN#0&(word) $3fff/(byte) $40|(word)(const byte*) BITMAP#0&(word) $3fff/(word) $400
to:main::@1
main::@1: scope:[main] from main::@5 main::@6
[11] (signed word) main::i#2 ← phi( main::@5/(signed byte) 1 main::@6/(signed word) main::i#1 )
[12] if((signed word) main::i#2<(signed word) $b4) goto main::@2
to:main::@3
main::@3: scope:[main] from main::@1 main::@3
[13] phi()
to:main::@3
main::@2: scope:[main] from main::@1
[14] (signed word) circle::r#0 ← (signed word) main::i#2
[15] call circle
to:main::@6
main::@6: scope:[main] from main::@2
[16] (signed word) main::i#1 ← (signed word) main::i#2 + (signed byte) 5
to:main::@1
circle: scope:[circle] from main::@2
[17] (signed word~) circle::$0 ← (signed word) circle::r#0 << (signed byte) 1
[18] (signed word) circle::p#0 ← (signed byte) 3 - (signed word~) circle::$0
to:circle::@1
circle::@1: scope:[circle] from circle circle::@13
[19] (signed word) circle::p#3 ← phi( circle/(signed word) circle::p#0 circle::@13/(signed word) circle::p#10 )
[19] (signed word) circle::y#13 ← phi( circle/(signed word) circle::r#0 circle::@13/(signed word) circle::y#10 )
[19] (signed word) circle::x1#10 ← phi( circle/(signed byte) 0 circle::@13/(signed word) circle::x1#1 )
[20] if((signed word) circle::x1#10<=(signed word) circle::y#13) goto circle::@2
to:circle::@return
circle::@return: scope:[circle] from circle::@1
[21] return
to:@return
circle::@2: scope:[circle] from circle::@1
[22] if((signed word) circle::p#3<(signed byte) 0) goto circle::@3
to:circle::@5
circle::@5: scope:[circle] from circle::@2
[23] (signed word) circle::y#1 ← (signed word) circle::y#13 - (signed byte) 1
[24] (signed word~) circle::$5 ← (signed word) circle::x1#10 - (signed word) circle::y#1
[25] (signed word~) circle::$6 ← (signed word~) circle::$5 << (signed byte) 2
[26] (signed word~) circle::$7 ← (signed word) circle::p#3 + (signed word~) circle::$6
[27] (signed word) circle::p#2 ← (signed word~) circle::$7 + (signed byte) $a
to:circle::@4
circle::@4: scope:[circle] from circle::@3 circle::@5
[28] (signed word) circle::p#10 ← phi( circle::@3/(signed word) circle::p#1 circle::@5/(signed word) circle::p#2 )
[28] (signed word) circle::y#10 ← phi( circle::@3/(signed word) circle::y#13 circle::@5/(signed word) circle::y#1 )
[29] (signed word) plot::x#0 ← (const signed word) circle::xc#0 + (signed word) circle::x1#10
[30] (signed word) plot::y#0 ← (const signed word) circle::yc#0 - (signed word) circle::y#10
[31] call plot
to:circle::@6
circle::@6: scope:[circle] from circle::@4
[32] (signed word) plot::x#1 ← (const signed word) circle::xc#0 - (signed word) circle::x1#10
[33] (signed word) plot::y#1 ← (const signed word) circle::yc#0 - (signed word) circle::y#10
[34] call plot
to:circle::@7
circle::@7: scope:[circle] from circle::@6
[35] (signed word) plot::x#2 ← (const signed word) circle::xc#0 + (signed word) circle::x1#10
[36] (signed word) plot::y#2 ← (const signed word) circle::yc#0 + (signed word) circle::y#10
[37] call plot
to:circle::@8
circle::@8: scope:[circle] from circle::@7
[38] (signed word) plot::x#3 ← (const signed word) circle::xc#0 - (signed word) circle::x1#10
[39] (signed word) plot::y#3 ← (const signed word) circle::yc#0 + (signed word) circle::y#10
[40] call plot
to:circle::@9
circle::@9: scope:[circle] from circle::@8
[41] (signed word) plot::x#4 ← (const signed word) circle::xc#0 + (signed word) circle::y#10
[42] (signed word) plot::y#4 ← (const signed word) circle::yc#0 - (signed word) circle::x1#10
[43] call plot
to:circle::@10
circle::@10: scope:[circle] from circle::@9
[44] (signed word) plot::x#5 ← (const signed word) circle::xc#0 - (signed word) circle::y#10
[45] (signed word) plot::y#5 ← (const signed word) circle::yc#0 - (signed word) circle::x1#10
[46] call plot
to:circle::@11
circle::@11: scope:[circle] from circle::@10
[47] (signed word) plot::x#6 ← (const signed word) circle::xc#0 + (signed word) circle::y#10
[48] (signed word) plot::y#6 ← (const signed word) circle::yc#0 + (signed word) circle::x1#10
[49] call plot
to:circle::@12
circle::@12: scope:[circle] from circle::@11
[50] (signed word) plot::x#7 ← (const signed word) circle::xc#0 - (signed word) circle::y#10
[51] (signed word) plot::y#7 ← (const signed word) circle::yc#0 + (signed word) circle::x1#10
[52] call plot
to:circle::@13
circle::@13: scope:[circle] from circle::@12
[53] (signed word) circle::x1#1 ← ++ (signed word) circle::x1#10
to:circle::@1
circle::@3: scope:[circle] from circle::@2
[54] (signed word~) circle::$9 ← (signed word) circle::x1#10 << (signed byte) 2
[55] (signed word~) circle::$10 ← (signed word) circle::p#3 + (signed word~) circle::$9
[56] (signed word) circle::p#1 ← (signed word~) circle::$10 + (signed byte) 6
to:circle::@4
plot: scope:[plot] from circle::@10 circle::@11 circle::@12 circle::@4 circle::@6 circle::@7 circle::@8 circle::@9
[57] (signed word) plot::y#8 ← phi( circle::@6/(signed word) plot::y#1 circle::@7/(signed word) plot::y#2 circle::@8/(signed word) plot::y#3 circle::@9/(signed word) plot::y#4 circle::@10/(signed word) plot::y#5 circle::@11/(signed word) plot::y#6 circle::@12/(signed word) plot::y#7 circle::@4/(signed word) plot::y#0 )
[57] (signed word) plot::x#8 ← phi( circle::@6/(signed word) plot::x#1 circle::@7/(signed word) plot::x#2 circle::@8/(signed word) plot::x#3 circle::@9/(signed word) plot::x#4 circle::@10/(signed word) plot::x#5 circle::@11/(signed word) plot::x#6 circle::@12/(signed word) plot::x#7 circle::@4/(signed word) plot::x#0 )
[58] if((signed word) plot::x#8<(signed byte) 0) goto plot::@return
to:plot::@4
plot::@4: scope:[plot] from plot
[59] if((signed word) plot::x#8>(signed word) $13f) goto plot::@return
to:plot::@3
plot::@3: scope:[plot] from plot::@4
[60] if((signed word) plot::y#8<(signed byte) 0) goto plot::@return
to:plot::@2
plot::@2: scope:[plot] from plot::@3
[61] if((signed word) plot::y#8>=(signed word) $c7+(signed byte) 1) goto plot::@return
to:plot::@1
plot::@1: scope:[plot] from plot::@2
[62] (signed word~) plot::$8 ← (signed word) plot::x#8 & (signed dword) $fff8
[63] (byte*) plot::location#1 ← (const byte*) BITMAP#0 + (signed word~) plot::$8
[64] (byte~) plot::$9 ← < (signed word) plot::y#8
[65] (byte~) plot::$10 ← (byte~) plot::$9 & (byte) 7
[66] (byte*) plot::location#2 ← (byte*) plot::location#1 + (byte~) plot::$10
[67] (signed word~) plot::$11 ← (signed word) plot::y#8 >> (signed byte) 3
[68] (signed word) plot::$15 ← (signed word~) plot::$11 << (byte) 2
[69] (signed word) plot::$16 ← (signed word) plot::$15 + (signed word~) plot::$11
[70] (signed word~) plot::$12 ← (signed word) plot::$16 << (byte) 6
[71] (byte*) plot::location#3 ← (byte*) plot::location#2 + (signed word~) plot::$12
[72] (signed byte~) plot::$13 ← (signed word) plot::x#8 & (signed byte) 7
[73] (byte~) plot::$14 ← *((byte*) plot::location#3) | *((const byte[]) bitmask#0 + (signed byte~) plot::$13)
[74] *((byte*) plot::location#3) ← (byte~) plot::$14
to:plot::@return
plot::@return: scope:[plot] from plot plot::@1 plot::@2 plot::@3 plot::@4
[75] return
to:@return
fill: scope:[fill] from main main::@4
[76] (byte) fill::val#4 ← phi( main/(byte) 0 main::@4/(byte) $16 )
[76] (signed word) fill::size#2 ← phi( main/(signed word)(number) $28*(number) $19*(number) 8 main::@4/(signed word)(number) $28*(number) $19 )
[76] (byte*) fill::addr#0 ← phi( main/(const byte*) BITMAP#0 main::@4/(const byte*) SCREEN#0 )
[77] (byte*) fill::end#0 ← (byte*) fill::addr#0 + (signed word) fill::size#2
to:fill::@1
fill::@1: scope:[fill] from fill fill::@2
[78] (byte*) fill::addr#2 ← phi( fill/(byte*) fill::addr#0 fill::@2/(byte*) fill::addr#1 )
[79] if((byte*) fill::addr#2!=(byte*) fill::end#0) goto fill::@2
to:fill::@return
fill::@return: scope:[fill] from fill::@1
[80] return
to:@return
fill::@2: scope:[fill] from fill::@1
[81] *((byte*) fill::addr#2) ← (byte) fill::val#4
[82] (byte*) fill::addr#1 ← ++ (byte*) fill::addr#2
to:fill::@1

File diff suppressed because it is too large Load Diff

View File

@ -0,0 +1,141 @@
(label) @1
(label) @begin
(label) @end
(byte*) BITMAP
(const byte*) BITMAP#0 BITMAP = (byte*) 8192
(byte) BLUE
(const byte) BLUE#0 BLUE = (byte) 6
(byte*) BORDERCOL
(const byte*) BORDERCOL#0 BORDERCOL = (byte*) 53280
(byte*) D011
(const byte*) D011#0 D011 = (byte*) 53265
(byte*) SCREEN
(const byte*) SCREEN#0 SCREEN = (byte*) 1024
(byte) VIC_BMM
(const byte) VIC_BMM#0 VIC_BMM = (byte) $20
(byte) VIC_DEN
(const byte) VIC_DEN#0 VIC_DEN = (byte) $10
(byte*) VIC_MEMORY
(const byte*) VIC_MEMORY#0 VIC_MEMORY = (byte*) 53272
(byte) VIC_RSEL
(const byte) VIC_RSEL#0 VIC_RSEL = (byte) 8
(byte[]) bitmask
(const byte[]) bitmask#0 bitmask = { (byte) $80, (byte) $40, (byte) $20, (byte) $10, (byte) 8, (byte) 4, (byte) 2, (byte) 1 }
(void()) circle((signed word) circle::xc , (signed word) circle::yc , (signed word) circle::r)
(signed word~) circle::$0 $0 zp ZP_WORD:4 4.0
(signed word~) circle::$10 $10 zp ZP_WORD:4 202.0
(signed word~) circle::$5 $5 zp ZP_WORD:10 202.0
(signed word~) circle::$6 $6 zp ZP_WORD:10 202.0
(signed word~) circle::$7 $7 zp ZP_WORD:4 202.0
(signed word~) circle::$9 $9 zp ZP_WORD:12 202.0
(label) circle::@1
(label) circle::@10
(label) circle::@11
(label) circle::@12
(label) circle::@13
(label) circle::@2
(label) circle::@3
(label) circle::@4
(label) circle::@5
(label) circle::@6
(label) circle::@7
(label) circle::@8
(label) circle::@9
(label) circle::@return
(signed word) circle::p
(signed word) circle::p#0 p zp ZP_WORD:4 4.0
(signed word) circle::p#1 p zp ZP_WORD:4 202.0
(signed word) circle::p#10 p zp ZP_WORD:4 11.653846153846153
(signed word) circle::p#2 p zp ZP_WORD:4 202.0
(signed word) circle::p#3 p zp ZP_WORD:4 58.00000000000001
(signed word) circle::r
(signed word) circle::r#0 r zp ZP_WORD:2 5.0
(signed word) circle::x1
(signed word) circle::x1#1 x1 zp ZP_WORD:8 202.0
(signed word) circle::x1#10 x1 zp ZP_WORD:8 36.47222222222223
(signed word) circle::xc
(const signed word) circle::xc#0 xc = (signed word) $a0
(signed word) circle::y
(signed word) circle::y#1 y zp ZP_WORD:2 60.599999999999994
(signed word) circle::y#10 y zp ZP_WORD:2 42.73076923076923
(signed word) circle::y#13 y zp ZP_WORD:2 67.66666666666666
(signed word) circle::yc
(const signed word) circle::yc#0 yc = (signed byte) $64
(void()) fill((byte*) fill::start , (signed word) fill::size , (byte) fill::val)
(label) fill::@1
(label) fill::@2
(label) fill::@return
(byte*) fill::addr
(byte*) fill::addr#0 addr zp ZP_WORD:8 2.0
(byte*) fill::addr#1 addr zp ZP_WORD:8 22.0
(byte*) fill::addr#2 addr zp ZP_WORD:8 15.333333333333332
(byte*) fill::end
(byte*) fill::end#0 end zp ZP_WORD:6 2.6
(signed word) fill::size
(signed word) fill::size#2 size zp ZP_WORD:6 2.0
(byte*) fill::start
(byte) fill::val
(byte) fill::val#4 reg byte x 1.8333333333333333
(void()) main()
(label) main::@1
(label) main::@2
(label) main::@3
(label) main::@4
(label) main::@5
(label) main::@6
(signed word) main::i
(signed word) main::i#1 i zp ZP_WORD:6 22.0
(signed word) main::i#2 i zp ZP_WORD:6 11.0
(void()) plot((signed word) plot::x , (signed word) plot::y)
(byte~) plot::$10 reg byte a 4.0
(signed word~) plot::$11 $11 zp ZP_WORD:12 3.0
(signed word~) plot::$12 $12 zp ZP_WORD:16 4.0
(signed byte~) plot::$13 reg byte a 4.0
(byte~) plot::$14 reg byte a 4.0
(signed word) plot::$15 $15 zp ZP_WORD:16 4.0
(signed word) plot::$16 $16 zp ZP_WORD:16 4.0
(signed word~) plot::$8 $8 zp ZP_WORD:14 4.0
(byte~) plot::$9 reg byte a 4.0
(label) plot::@1
(label) plot::@2
(label) plot::@3
(label) plot::@4
(label) plot::@return
(byte*) plot::location
(byte*) plot::location#1 location zp ZP_WORD:14 1.3333333333333333
(byte*) plot::location#2 location zp ZP_WORD:14 0.8
(byte*) plot::location#3 location zp ZP_WORD:14 2.0
(signed word) plot::x
(signed word) plot::x#0 x zp ZP_WORD:10 101.0
(signed word) plot::x#1 x zp ZP_WORD:10 101.0
(signed word) plot::x#2 x zp ZP_WORD:10 101.0
(signed word) plot::x#3 x zp ZP_WORD:10 101.0
(signed word) plot::x#4 x zp ZP_WORD:10 101.0
(signed word) plot::x#5 x zp ZP_WORD:10 101.0
(signed word) plot::x#6 x zp ZP_WORD:10 101.0
(signed word) plot::x#7 x zp ZP_WORD:10 101.0
(signed word) plot::x#8 x zp ZP_WORD:10 54.4
(signed word) plot::y
(signed word) plot::y#0 y zp ZP_WORD:12 202.0
(signed word) plot::y#1 y zp ZP_WORD:12 202.0
(signed word) plot::y#2 y zp ZP_WORD:12 202.0
(signed word) plot::y#3 y zp ZP_WORD:12 202.0
(signed word) plot::y#4 y zp ZP_WORD:12 202.0
(signed word) plot::y#5 y zp ZP_WORD:12 202.0
(signed word) plot::y#6 y zp ZP_WORD:12 202.0
(signed word) plot::y#7 y zp ZP_WORD:12 202.0
(signed word) plot::y#8 y zp ZP_WORD:12 81.60000000000001
zp ZP_WORD:2 [ circle::y#13 circle::r#0 circle::y#10 circle::y#1 ]
zp ZP_WORD:4 [ circle::p#3 circle::p#0 circle::p#10 circle::p#1 circle::p#2 circle::$7 circle::$10 circle::$0 ]
zp ZP_WORD:6 [ fill::size#2 fill::end#0 main::i#2 main::i#1 ]
reg byte x [ fill::val#4 ]
zp ZP_WORD:8 [ fill::addr#2 fill::addr#0 fill::addr#1 circle::x1#10 circle::x1#1 ]
zp ZP_WORD:10 [ circle::$5 circle::$6 plot::x#8 plot::x#1 plot::x#2 plot::x#3 plot::x#4 plot::x#5 plot::x#6 plot::x#7 plot::x#0 ]
zp ZP_WORD:12 [ circle::$9 plot::y#8 plot::y#1 plot::y#2 plot::y#3 plot::y#4 plot::y#5 plot::y#6 plot::y#7 plot::y#0 plot::$11 ]
zp ZP_WORD:14 [ plot::$8 plot::location#1 plot::location#2 plot::location#3 ]
reg byte a [ plot::$9 ]
reg byte a [ plot::$10 ]
zp ZP_WORD:16 [ plot::$15 plot::$16 plot::$12 ]
reg byte a [ plot::$13 ]
reg byte a [ plot::$14 ]

View File

@ -15,7 +15,7 @@ main: {
sta SCREEN+2
lda #'0'+4*SIZEOF_WORD/SIZEOF_WORD
sta SCREEN+3
lda #'0'+7*SIZEOF_BYTE/SIZEOF_BYTE
lda #'0'+8*SIZEOF_BYTE/SIZEOF_BYTE
sta SCREEN+4
lda #'0'+4*SIZEOF_BYTE/SIZEOF_BYTE
sta SCREEN+5

View File

@ -12,7 +12,7 @@ main: scope:[main] from @1
[5] *((const byte*) SCREEN#0+(byte) 1) ← (byte) '0'+(byte) 3*(const byte) SIZEOF_WORD/(const byte) SIZEOF_WORD
[6] *((const byte*) SCREEN#0+(byte) 2) ← (byte) '0'+(const byte) main::sz#0+(byte) 2*(const byte) SIZEOF_BYTE/(const byte) SIZEOF_BYTE
[7] *((const byte*) SCREEN#0+(byte) 3) ← (byte) '0'+(byte) 4*(const byte) SIZEOF_WORD/(const byte) SIZEOF_WORD
[8] *((const byte*) SCREEN#0+(byte) 4) ← (byte) '0'+(byte) 7*(const byte) SIZEOF_BYTE/(const byte) SIZEOF_BYTE
[8] *((const byte*) SCREEN#0+(byte) 4) ← (byte) '0'+(byte) 8*(const byte) SIZEOF_BYTE/(const byte) SIZEOF_BYTE
[9] *((const byte*) SCREEN#0+(byte) 5) ← (byte) '0'+(byte) 4*(const byte) SIZEOF_BYTE/(const byte) SIZEOF_BYTE
to:main::@return
main::@return: scope:[main] from main

View File

@ -205,19 +205,19 @@ Successful SSA optimization PassNEliminateUnusedVars
Adding number conversion cast (unumber) 3 in
Adding number conversion cast (unumber) 3 in
Adding number conversion cast (unumber) 4 in
Adding number conversion cast (unumber) 7 in
Adding number conversion cast (unumber) 8 in
Adding number conversion cast (unumber) 4 in
Successful SSA optimization PassNAddNumberTypeConversions
Simplifying constant integer cast 3
Simplifying constant integer cast 3
Simplifying constant integer cast 4
Simplifying constant integer cast 7
Simplifying constant integer cast 8
Simplifying constant integer cast 4
Successful SSA optimization PassNCastSimplification
Finalized unsigned number type (byte) 3
Finalized unsigned number type (byte) 3
Finalized unsigned number type (byte) 4
Finalized unsigned number type (byte) 7
Finalized unsigned number type (byte) 8
Finalized unsigned number type (byte) 4
Successful SSA optimization PassNFinalizeNumberTypeConversions
Constant right-side identified [0] (byte~) main::$2 ← (byte) '0' + (const byte) main::$1
@ -259,9 +259,9 @@ Inlining constant with different constant siblings (const byte) main::idx#3
Inlining constant with different constant siblings (const byte) main::idx#4
Inlining constant with different constant siblings (const byte) main::idx#5
Constant inlined main::$12 = (byte) '0'+(byte) 4*(const byte) SIZEOF_WORD/(const byte) SIZEOF_WORD
Constant inlined main::$13 = (byte) 7*(const byte) SIZEOF_BYTE
Constant inlined main::$14 = (byte) 7*(const byte) SIZEOF_BYTE/(const byte) SIZEOF_BYTE
Constant inlined main::$15 = (byte) '0'+(byte) 7*(const byte) SIZEOF_BYTE/(const byte) SIZEOF_BYTE
Constant inlined main::$13 = (byte) 8*(const byte) SIZEOF_BYTE
Constant inlined main::$14 = (byte) 8*(const byte) SIZEOF_BYTE/(const byte) SIZEOF_BYTE
Constant inlined main::$15 = (byte) '0'+(byte) 8*(const byte) SIZEOF_BYTE/(const byte) SIZEOF_BYTE
Constant inlined main::$10 = (byte) 4*(const byte) SIZEOF_WORD
Constant inlined main::$11 = (byte) 4*(const byte) SIZEOF_WORD/(const byte) SIZEOF_WORD
Constant inlined main::$16 = (byte) 4*(const byte) SIZEOF_BYTE
@ -330,7 +330,7 @@ main: scope:[main] from @1
[5] *((const byte*) SCREEN#0+(byte) 1) ← (byte) '0'+(byte) 3*(const byte) SIZEOF_WORD/(const byte) SIZEOF_WORD
[6] *((const byte*) SCREEN#0+(byte) 2) ← (byte) '0'+(const byte) main::sz#0+(byte) 2*(const byte) SIZEOF_BYTE/(const byte) SIZEOF_BYTE
[7] *((const byte*) SCREEN#0+(byte) 3) ← (byte) '0'+(byte) 4*(const byte) SIZEOF_WORD/(const byte) SIZEOF_WORD
[8] *((const byte*) SCREEN#0+(byte) 4) ← (byte) '0'+(byte) 7*(const byte) SIZEOF_BYTE/(const byte) SIZEOF_BYTE
[8] *((const byte*) SCREEN#0+(byte) 4) ← (byte) '0'+(byte) 8*(const byte) SIZEOF_BYTE/(const byte) SIZEOF_BYTE
[9] *((const byte*) SCREEN#0+(byte) 5) ← (byte) '0'+(byte) 4*(const byte) SIZEOF_BYTE/(const byte) SIZEOF_BYTE
to:main::@return
main::@return: scope:[main] from main
@ -394,8 +394,8 @@ main: {
// [7] *((const byte*) SCREEN#0+(byte) 3) ← (byte) '0'+(byte) 4*(const byte) SIZEOF_WORD/(const byte) SIZEOF_WORD -- _deref_pbuc1=vbuc2
lda #'0'+4*SIZEOF_WORD/SIZEOF_WORD
sta SCREEN+3
// [8] *((const byte*) SCREEN#0+(byte) 4) ← (byte) '0'+(byte) 7*(const byte) SIZEOF_BYTE/(const byte) SIZEOF_BYTE -- _deref_pbuc1=vbuc2
lda #'0'+7*SIZEOF_BYTE/SIZEOF_BYTE
// [8] *((const byte*) SCREEN#0+(byte) 4) ← (byte) '0'+(byte) 8*(const byte) SIZEOF_BYTE/(const byte) SIZEOF_BYTE -- _deref_pbuc1=vbuc2
lda #'0'+8*SIZEOF_BYTE/SIZEOF_BYTE
sta SCREEN+4
// [9] *((const byte*) SCREEN#0+(byte) 5) ← (byte) '0'+(byte) 4*(const byte) SIZEOF_BYTE/(const byte) SIZEOF_BYTE -- _deref_pbuc1=vbuc2
lda #'0'+4*SIZEOF_BYTE/SIZEOF_BYTE
@ -413,7 +413,7 @@ Statement [4] *((const byte*) SCREEN#0) ← (byte) '0'+(byte) 3*(const byte) SIZ
Statement [5] *((const byte*) SCREEN#0+(byte) 1) ← (byte) '0'+(byte) 3*(const byte) SIZEOF_WORD/(const byte) SIZEOF_WORD [ ] ( main:2 [ ] ) always clobbers reg byte a
Statement [6] *((const byte*) SCREEN#0+(byte) 2) ← (byte) '0'+(const byte) main::sz#0+(byte) 2*(const byte) SIZEOF_BYTE/(const byte) SIZEOF_BYTE [ ] ( main:2 [ ] ) always clobbers reg byte a
Statement [7] *((const byte*) SCREEN#0+(byte) 3) ← (byte) '0'+(byte) 4*(const byte) SIZEOF_WORD/(const byte) SIZEOF_WORD [ ] ( main:2 [ ] ) always clobbers reg byte a
Statement [8] *((const byte*) SCREEN#0+(byte) 4) ← (byte) '0'+(byte) 7*(const byte) SIZEOF_BYTE/(const byte) SIZEOF_BYTE [ ] ( main:2 [ ] ) always clobbers reg byte a
Statement [8] *((const byte*) SCREEN#0+(byte) 4) ← (byte) '0'+(byte) 8*(const byte) SIZEOF_BYTE/(const byte) SIZEOF_BYTE [ ] ( main:2 [ ] ) always clobbers reg byte a
Statement [9] *((const byte*) SCREEN#0+(byte) 5) ← (byte) '0'+(byte) 4*(const byte) SIZEOF_BYTE/(const byte) SIZEOF_BYTE [ ] ( main:2 [ ] ) always clobbers reg byte a
REGISTER UPLIFT SCOPES
@ -463,8 +463,8 @@ main: {
// [7] *((const byte*) SCREEN#0+(byte) 3) ← (byte) '0'+(byte) 4*(const byte) SIZEOF_WORD/(const byte) SIZEOF_WORD -- _deref_pbuc1=vbuc2
lda #'0'+4*SIZEOF_WORD/SIZEOF_WORD
sta SCREEN+3
// [8] *((const byte*) SCREEN#0+(byte) 4) ← (byte) '0'+(byte) 7*(const byte) SIZEOF_BYTE/(const byte) SIZEOF_BYTE -- _deref_pbuc1=vbuc2
lda #'0'+7*SIZEOF_BYTE/SIZEOF_BYTE
// [8] *((const byte*) SCREEN#0+(byte) 4) ← (byte) '0'+(byte) 8*(const byte) SIZEOF_BYTE/(const byte) SIZEOF_BYTE -- _deref_pbuc1=vbuc2
lda #'0'+8*SIZEOF_BYTE/SIZEOF_BYTE
sta SCREEN+4
// [9] *((const byte*) SCREEN#0+(byte) 5) ← (byte) '0'+(byte) 4*(const byte) SIZEOF_BYTE/(const byte) SIZEOF_BYTE -- _deref_pbuc1=vbuc2
lda #'0'+4*SIZEOF_BYTE/SIZEOF_BYTE
@ -556,8 +556,8 @@ main: {
lda #'0'+4*SIZEOF_WORD/SIZEOF_WORD
sta SCREEN+3
// SCREEN[idx++] = '0'+sizeof(sa)/sizeof(byte)
// [8] *((const byte*) SCREEN#0+(byte) 4) ← (byte) '0'+(byte) 7*(const byte) SIZEOF_BYTE/(const byte) SIZEOF_BYTE -- _deref_pbuc1=vbuc2
lda #'0'+7*SIZEOF_BYTE/SIZEOF_BYTE
// [8] *((const byte*) SCREEN#0+(byte) 4) ← (byte) '0'+(byte) 8*(const byte) SIZEOF_BYTE/(const byte) SIZEOF_BYTE -- _deref_pbuc1=vbuc2
lda #'0'+8*SIZEOF_BYTE/SIZEOF_BYTE
sta SCREEN+4
// SCREEN[idx++] = '0'+sizeof(sb)/sizeof(byte)
// [9] *((const byte*) SCREEN#0+(byte) 5) ← (byte) '0'+(byte) 4*(const byte) SIZEOF_BYTE/(const byte) SIZEOF_BYTE -- _deref_pbuc1=vbuc2

View File

@ -47,7 +47,7 @@ main: {
jsr print_person
rts
}
// print_person(dword zeropage(2) person_id, byte[2] zeropage(6) person_initials)
// print_person(dword zeropage(2) person_id, byte[3] zeropage(6) person_initials)
print_person: {
.label person_id = 2
.label person_initials = 6

View File

@ -20,7 +20,7 @@ main::@return: scope:[main] from main::@1
to:@return
print_person: scope:[print_person] from main main::@1
[9] (byte*) print_line_cursor#20 ← phi( main/(byte*) 1024 main::@1/(byte*) print_line_cursor#1 )
[9] (byte[2]) print_person::person_initials#2 ← phi( main/(const byte[2]) jesper_initials#0 main::@1/(const byte[2]) henry_initials#0 )
[9] (byte[3]) print_person::person_initials#2 ← phi( main/(const byte[3]) jesper_initials#0 main::@1/(const byte[3]) henry_initials#0 )
[9] (byte*) print_char_cursor#39 ← phi( main/(byte*) 1024 main::@1/(byte*~) print_char_cursor#49 )
[9] (dword) print_person::person_id#2 ← phi( main/(const dword) jesper_id#0 main::@1/(const dword) henry_id#0 )
[10] (dword) print_dword_decimal::w#0 ← (dword) print_person::person_id#2
@ -31,7 +31,7 @@ print_person::@1: scope:[print_person] from print_person
[13] call print_char
to:print_person::@2
print_person::@2: scope:[print_person] from print_person::@1
[14] (byte*) print_str::str#2 ← (byte[2]) print_person::person_initials#2
[14] (byte*) print_str::str#2 ← (byte[3]) print_person::person_initials#2
[15] call print_str
to:print_person::@3
print_person::@3: scope:[print_person] from print_person::@2

View File

@ -1,26 +1,29 @@
Fixing struct type size struct Person to 7
Fixing struct type size struct Person to 7
Fixing struct type size struct Person to 7
Fixing pointer addition (word*~) bsearch16u::$7 ← (word*) bsearch16u::items + (byte~) bsearch16u::$6
Fixing pointer addition (word*~) bsearch16u::$15 ← (word*) bsearch16u::pivot + (number) 1
Fixing pointer addition (word*~) bsearch16u::$1 ← (word*) bsearch16u::items - (number) 1
Fixing pointer array-indexing *((word*) utoa::digit_values + (byte) utoa::digit)
Fixing pointer array-indexing *((dword*) ultoa::digit_values + (byte) ultoa::digit)
Created struct value member variable (dword) jesper_id
Created struct value member variable (byte[2]) jesper_initials
Created struct value member variable (byte[3]) jesper_initials
Converted struct value to member variables (struct Person) jesper
Created struct value member variable (dword) henry_id
Created struct value member variable (byte[2]) henry_initials
Created struct value member variable (byte[3]) henry_initials
Converted struct value to member variables (struct Person) henry
Created struct value member variable (dword) print_person::person_id
Created struct value member variable (byte[2]) print_person::person_initials
Created struct value member variable (byte[3]) print_person::person_initials
Converted struct value to member variables (struct Person) print_person::person
Converted procedure struct value parameter to member unwinding (void()) print_person((dword) print_person::person_id , (byte[2]) print_person::person_initials)
Converted procedure struct value parameter to member unwinding (void()) print_person((dword) print_person::person_id , (byte[3]) print_person::person_initials)
Adding struct value list initializer (dword) jesper_id ← (number) $1b244
Adding struct value list initializer (byte[2]) jesper_initials ← (string) "jg"
Adding struct value list initializer (byte[3]) jesper_initials ← (string) "jg"
Adding struct value list initializer (dword) henry_id ← (number) $4466d
Adding struct value list initializer (byte[2]) henry_initials ← (string) "hg"
Converted procedure struct value parameter to member unwinding in call (void~) main::$0 ← call print_person (dword) jesper_id (byte[2]) jesper_initials
Converted procedure struct value parameter to member unwinding in call (void~) main::$1 ← call print_person (dword) henry_id (byte[2]) henry_initials
Adding struct value list initializer (byte[3]) henry_initials ← (string) "hg"
Converted procedure struct value parameter to member unwinding in call (void~) main::$0 ← call print_person (dword) jesper_id (byte[3]) jesper_initials
Converted procedure struct value parameter to member unwinding in call (void~) main::$1 ← call print_person (dword) henry_id (byte[3]) henry_initials
Replacing struct member reference (struct Person) print_person::person.id with member unwinding reference (dword) print_person::person_id
Replacing struct member reference (struct Person) print_person::person.initials with member unwinding reference (byte[2]) print_person::person_initials
Replacing struct member reference (struct Person) print_person::person.initials with member unwinding reference (byte[3]) print_person::person_initials
Warning! Adding boolean cast to non-boolean condition *((byte*) strcpy::src)
Warning! Adding boolean cast to non-boolean condition *((byte*) print_str_lines::str)
Warning! Adding boolean cast to non-boolean condition (byte) print_str_lines::ch
@ -29,9 +32,9 @@ Warning! Adding boolean cast to non-boolean condition *((byte*) print_str_at::st
Warning! Adding boolean cast to non-boolean sub-expression (byte) print_str_lines::ch
Identified constant variable (byte*) HEAP_TOP
Identified constant variable (dword) jesper_id
Identified constant variable (byte[2]) jesper_initials
Identified constant variable (byte[3]) jesper_initials
Identified constant variable (dword) henry_id
Identified constant variable (byte[2]) henry_initials
Identified constant variable (byte[3]) henry_initials
Culled Empty Block (label) @1
Culled Empty Block (label) @2
Culled Empty Block (label) @3
@ -363,15 +366,15 @@ print_char::@return: scope:[print_char] from print_char
(byte*) print_line_cursor#23 ← phi( @26/(byte*) print_line_cursor#24 )
(byte*) print_char_cursor#43 ← phi( @26/(byte*) print_char_cursor#44 )
(dword) jesper_id#0 ← (number) $1b244
(byte[2]) jesper_initials#0 ← (const string) $1
(byte[3]) jesper_initials#0 ← (const string) $1
(dword) henry_id#0 ← (number) $4466d
(byte[2]) henry_initials#0 ← (const string) $2
(byte[3]) henry_initials#0 ← (const string) $2
to:@38
main: scope:[main] from @38
(byte*) print_line_cursor#19 ← phi( @38/(byte*) print_line_cursor#21 )
(byte*) print_char_cursor#38 ← phi( @38/(byte*) print_char_cursor#40 )
(dword) print_person::person_id#0 ← (dword) jesper_id#0
(byte[2]) print_person::person_initials#0 ← (byte[2]) jesper_initials#0
(byte[3]) print_person::person_initials#0 ← (byte[3]) jesper_initials#0
call print_person
to:main::@1
main::@1: scope:[main] from main
@ -380,7 +383,7 @@ main::@1: scope:[main] from main
(byte*) print_char_cursor#9 ← (byte*) print_char_cursor#26
(byte*) print_line_cursor#3 ← (byte*) print_line_cursor#12
(dword) print_person::person_id#1 ← (dword) henry_id#0
(byte[2]) print_person::person_initials#1 ← (byte[2]) henry_initials#0
(byte[3]) print_person::person_initials#1 ← (byte[3]) henry_initials#0
call print_person
to:main::@2
main::@2: scope:[main] from main::@1
@ -398,7 +401,7 @@ main::@return: scope:[main] from main::@2
to:@return
print_person: scope:[print_person] from main main::@1
(byte*) print_line_cursor#26 ← phi( main/(byte*) print_line_cursor#19 main::@1/(byte*) print_line_cursor#3 )
(byte[2]) print_person::person_initials#4 ← phi( main/(byte[2]) print_person::person_initials#0 main::@1/(byte[2]) print_person::person_initials#1 )
(byte[3]) print_person::person_initials#4 ← phi( main/(byte[3]) print_person::person_initials#0 main::@1/(byte[3]) print_person::person_initials#1 )
(byte*) print_char_cursor#39 ← phi( main/(byte*) print_char_cursor#38 main::@1/(byte*) print_char_cursor#9 )
(dword) print_person::person_id#2 ← phi( main/(dword) print_person::person_id#0 main::@1/(dword) print_person::person_id#1 )
(dword) print_dword_decimal::w#0 ← (dword) print_person::person_id#2
@ -406,7 +409,7 @@ print_person: scope:[print_person] from main main::@1
to:print_person::@1
print_person::@1: scope:[print_person] from print_person
(byte*) print_line_cursor#25 ← phi( print_person/(byte*) print_line_cursor#26 )
(byte[2]) print_person::person_initials#3 ← phi( print_person/(byte[2]) print_person::person_initials#4 )
(byte[3]) print_person::person_initials#3 ← phi( print_person/(byte[3]) print_person::person_initials#4 )
(byte*) print_char_cursor#29 ← phi( print_person/(byte*) print_char_cursor#6 )
(byte*) print_char_cursor#12 ← (byte*) print_char_cursor#29
(byte) print_char::ch#0 ← (byte) ' '
@ -414,10 +417,10 @@ print_person::@1: scope:[print_person] from print_person
to:print_person::@2
print_person::@2: scope:[print_person] from print_person::@1
(byte*) print_line_cursor#22 ← phi( print_person::@1/(byte*) print_line_cursor#25 )
(byte[2]) print_person::person_initials#2 ← phi( print_person::@1/(byte[2]) print_person::person_initials#3 )
(byte[3]) print_person::person_initials#2 ← phi( print_person::@1/(byte[3]) print_person::person_initials#3 )
(byte*) print_char_cursor#30 ← phi( print_person::@1/(byte*) print_char_cursor#8 )
(byte*) print_char_cursor#13 ← (byte*) print_char_cursor#30
(byte*) print_str::str#2 ← (byte[2]) print_person::person_initials#2
(byte*) print_str::str#2 ← (byte[3]) print_person::person_initials#2
call print_str
to:print_person::@3
print_person::@3: scope:[print_person] from print_person::@2
@ -472,7 +475,7 @@ SYMBOL TABLE SSA
(const byte) HEXADECIMAL = (number) $10
(const byte) OCTAL = (number) 8
(dword) Person::id
(byte[2]) Person::initials
(byte[3]) Person::initials
(const byte) RADIX::BINARY = (number) 2
(const byte) RADIX::DECIMAL = (number) $a
(const byte) RADIX::HEXADECIMAL = (number) $10
@ -490,12 +493,12 @@ SYMBOL TABLE SSA
(byte[$b]) decimal_digits_long#0
(dword) henry_id
(dword) henry_id#0
(byte[2]) henry_initials
(byte[2]) henry_initials#0
(byte[3]) henry_initials
(byte[3]) henry_initials#0
(dword) jesper_id
(dword) jesper_id#0
(byte[2]) jesper_initials
(byte[2]) jesper_initials#0
(byte[3]) jesper_initials
(byte[3]) jesper_initials#0
(void()) main()
(label) main::@1
(label) main::@2
@ -592,7 +595,7 @@ SYMBOL TABLE SSA
(label) print_ln::@1
(label) print_ln::@2
(label) print_ln::@return
(void()) print_person((dword) print_person::person_id , (byte[2]) print_person::person_initials)
(void()) print_person((dword) print_person::person_id , (byte[3]) print_person::person_initials)
(label) print_person::@1
(label) print_person::@2
(label) print_person::@3
@ -603,12 +606,12 @@ SYMBOL TABLE SSA
(dword) print_person::person_id#0
(dword) print_person::person_id#1
(dword) print_person::person_id#2
(byte[2]) print_person::person_initials
(byte[2]) print_person::person_initials#0
(byte[2]) print_person::person_initials#1
(byte[2]) print_person::person_initials#2
(byte[2]) print_person::person_initials#3
(byte[2]) print_person::person_initials#4
(byte[3]) print_person::person_initials
(byte[3]) print_person::person_initials#0
(byte[3]) print_person::person_initials#1
(byte[3]) print_person::person_initials#2
(byte[3]) print_person::person_initials#3
(byte[3]) print_person::person_initials#4
(byte*) print_screen
(byte*) print_screen#0
(void()) print_str((byte*) print_str::str)
@ -931,7 +934,7 @@ Alias (byte*) print_char_cursor#26 = (byte*) print_char_cursor#9
Alias (byte*) print_line_cursor#12 = (byte*) print_line_cursor#3
Alias (byte*) print_char_cursor#10 = (byte*) print_char_cursor#27 (byte*) print_char_cursor#28 (byte*) print_char_cursor#11
Alias (byte*) print_line_cursor#13 = (byte*) print_line_cursor#4 (byte*) print_line_cursor#14 (byte*) print_line_cursor#5
Alias (byte[2]) print_person::person_initials#2 = (byte[2]) print_person::person_initials#3 (byte[2]) print_person::person_initials#4
Alias (byte[3]) print_person::person_initials#2 = (byte[3]) print_person::person_initials#3 (byte[3]) print_person::person_initials#4
Alias (byte*) print_line_cursor#20 = (byte*) print_line_cursor#25 (byte*) print_line_cursor#26 (byte*) print_line_cursor#22
Alias (byte*) print_char_cursor#12 = (byte*) print_char_cursor#29
Alias (byte*) print_char_cursor#13 = (byte*) print_char_cursor#30
@ -1018,9 +1021,9 @@ Constant (const byte*) print_char_cursor#0 = (byte*) 1024
Constant (const byte[$b]) decimal_digits_long#0 = { fill( $b, 0) }
Constant (const byte) ultoa::radix#0 = DECIMAL
Constant (const dword) jesper_id#0 = $1b244
Constant (const byte[2]) jesper_initials#0 = $1
Constant (const byte[3]) jesper_initials#0 = $1
Constant (const dword) henry_id#0 = $4466d
Constant (const byte[2]) henry_initials#0 = $2
Constant (const byte[3]) henry_initials#0 = $2
Constant (const byte) print_char::ch#0 = ' '
Successful SSA optimization Pass2ConstantIdentification
Constant (const dword*) ultoa::digit_values#1 = RADIX_DECIMAL_VALUES_LONG#0
@ -1030,9 +1033,9 @@ Constant (const dword*) ultoa::digit_values#4 = RADIX_BINARY_VALUES_LONG#0
Constant (const byte*) ultoa::buffer#5 = decimal_digits_long#0
Constant (const byte*) print_str::str#1 = decimal_digits_long#0
Constant (const dword) print_person::person_id#0 = jesper_id#0
Constant (const byte[2]) print_person::person_initials#0 = jesper_initials#0
Constant (const byte[3]) print_person::person_initials#0 = jesper_initials#0
Constant (const dword) print_person::person_id#1 = henry_id#0
Constant (const byte[2]) print_person::person_initials#1 = henry_initials#0
Constant (const byte[3]) print_person::person_initials#1 = henry_initials#0
Successful SSA optimization Pass2ConstantIdentification
if() condition always true - replacing block destination [9] if((const byte) ultoa::radix#0==(const byte) DECIMAL) goto ultoa::@1
if() condition always false - eliminating [15] if((const byte) ultoa::radix#0==(const byte) HEXADECIMAL) goto ultoa::@2
@ -1101,15 +1104,15 @@ Inlining constant with var siblings (const byte*) ultoa::buffer#5
Inlining constant with var siblings (const byte) ultoa_append::digit#0
Inlining constant with var siblings (const byte*) print_str::str#1
Inlining constant with var siblings (const dword) print_person::person_id#0
Inlining constant with var siblings (const byte[2]) print_person::person_initials#0
Inlining constant with var siblings (const byte[3]) print_person::person_initials#0
Inlining constant with var siblings (const dword) print_person::person_id#1
Inlining constant with var siblings (const byte[2]) print_person::person_initials#1
Inlining constant with var siblings (const byte[3]) print_person::person_initials#1
Inlining constant with var siblings (const byte*) print_char_cursor#0
Constant inlined print_person::person_initials#1 = (const byte[2]) henry_initials#0
Constant inlined print_person::person_initials#1 = (const byte[3]) henry_initials#0
Constant inlined ultoa::started#1 = (byte) 1
Constant inlined $0 = (const byte[]) DIGITS#0
Constant inlined $1 = (const byte[2]) jesper_initials#0
Constant inlined $2 = (const byte[2]) henry_initials#0
Constant inlined $1 = (const byte[3]) jesper_initials#0
Constant inlined $2 = (const byte[3]) henry_initials#0
Constant inlined print_char_cursor#0 = (byte*) 1024
Constant inlined ultoa::buffer#5 = (const byte[$b]) decimal_digits_long#0
Constant inlined print_person::person_id#1 = (const dword) henry_id#0
@ -1120,7 +1123,7 @@ Constant inlined ultoa::digit#0 = (byte) 0
Constant inlined ultoa_append::digit#0 = (byte) 0
Constant inlined ultoa::digit_values#1 = (const dword[]) RADIX_DECIMAL_VALUES_LONG#0
Constant inlined print_str::str#1 = (const byte[$b]) decimal_digits_long#0
Constant inlined print_person::person_initials#0 = (const byte[2]) jesper_initials#0
Constant inlined print_person::person_initials#0 = (const byte[3]) jesper_initials#0
Successful SSA optimization Pass2ConstantInlining
Eliminating unused constant (const byte) SIZEOF_DWORD
Successful SSA optimization PassNEliminateUnusedVars
@ -1233,7 +1236,7 @@ main::@return: scope:[main] from main::@1
to:@return
print_person: scope:[print_person] from main main::@1
[9] (byte*) print_line_cursor#20 ← phi( main/(byte*) 1024 main::@1/(byte*) print_line_cursor#1 )
[9] (byte[2]) print_person::person_initials#2 ← phi( main/(const byte[2]) jesper_initials#0 main::@1/(const byte[2]) henry_initials#0 )
[9] (byte[3]) print_person::person_initials#2 ← phi( main/(const byte[3]) jesper_initials#0 main::@1/(const byte[3]) henry_initials#0 )
[9] (byte*) print_char_cursor#39 ← phi( main/(byte*) 1024 main::@1/(byte*~) print_char_cursor#49 )
[9] (dword) print_person::person_id#2 ← phi( main/(const dword) jesper_id#0 main::@1/(const dword) henry_id#0 )
[10] (dword) print_dword_decimal::w#0 ← (dword) print_person::person_id#2
@ -1244,7 +1247,7 @@ print_person::@1: scope:[print_person] from print_person
[13] call print_char
to:print_person::@2
print_person::@2: scope:[print_person] from print_person::@1
[14] (byte*) print_str::str#2 ← (byte[2]) print_person::person_initials#2
[14] (byte*) print_str::str#2 ← (byte[3]) print_person::person_initials#2
[15] call print_str
to:print_person::@3
print_person::@3: scope:[print_person] from print_person::@2
@ -1367,16 +1370,16 @@ ultoa_append::@2: scope:[ultoa_append] from ultoa_append::@1
VARIABLE REGISTER WEIGHTS
(byte[]) DIGITS
(dword) Person::id
(byte[2]) Person::initials
(byte[3]) Person::initials
(dword[]) RADIX_BINARY_VALUES_LONG
(dword[]) RADIX_DECIMAL_VALUES_LONG
(dword[]) RADIX_HEXADECIMAL_VALUES_LONG
(dword[]) RADIX_OCTAL_VALUES_LONG
(byte[$b]) decimal_digits_long
(dword) henry_id
(byte[2]) henry_initials
(byte[3]) henry_initials
(dword) jesper_id
(byte[2]) jesper_initials
(byte[3]) jesper_initials
(void()) main()
(void()) print_char((byte) print_char::ch)
(byte) print_char::ch
@ -1395,12 +1398,12 @@ VARIABLE REGISTER WEIGHTS
(byte*) print_line_cursor#20 0.4444444444444444
(byte*) print_line_cursor#9 24.0
(void()) print_ln()
(void()) print_person((dword) print_person::person_id , (byte[2]) print_person::person_initials)
(void()) print_person((dword) print_person::person_id , (byte[3]) print_person::person_initials)
(struct Person) print_person::person
(dword) print_person::person_id
(dword) print_person::person_id#2 2.0
(byte[2]) print_person::person_initials
(byte[2]) print_person::person_initials#2 0.4
(byte[3]) print_person::person_initials
(byte[3]) print_person::person_initials#2 0.4
(byte*) print_screen
(void()) print_str((byte*) print_str::str)
(byte*) print_str::str
@ -1546,7 +1549,7 @@ main: {
sta.z print_line_cursor
lda #>$400
sta.z print_line_cursor+1
// [9] phi (byte[2]) print_person::person_initials#2 = (const byte[2]) jesper_initials#0 [phi:main->print_person#1] -- pbuz1=pbuc1
// [9] phi (byte[3]) print_person::person_initials#2 = (const byte[3]) jesper_initials#0 [phi:main->print_person#1] -- pbuz1=pbuc1
lda #<jesper_initials
sta.z print_person.person_initials
lda #>jesper_initials
@ -1578,7 +1581,7 @@ main: {
// [9] phi from main::@1 to print_person [phi:main::@1->print_person]
print_person_from_b1:
// [9] phi (byte*) print_line_cursor#20 = (byte*) print_line_cursor#1 [phi:main::@1->print_person#0] -- register_copy
// [9] phi (byte[2]) print_person::person_initials#2 = (const byte[2]) henry_initials#0 [phi:main::@1->print_person#1] -- pbuz1=pbuc1
// [9] phi (byte[3]) print_person::person_initials#2 = (const byte[3]) henry_initials#0 [phi:main::@1->print_person#1] -- pbuz1=pbuc1
lda #<henry_initials
sta.z print_person.person_initials
lda #>henry_initials
@ -1601,7 +1604,7 @@ main: {
rts
}
// print_person
// print_person(dword zeropage(2) person_id, byte[2] zeropage(6) person_initials)
// print_person(dword zeropage(2) person_id, byte[3] zeropage(6) person_initials)
print_person: {
.label person_id = 2
.label person_initials = 6
@ -1626,7 +1629,7 @@ print_person: {
jmp b2
// print_person::@2
b2:
// [14] (byte*) print_str::str#2 ← (byte[2]) print_person::person_initials#2 -- pbuz1=pbuz2
// [14] (byte*) print_str::str#2 ← (byte[3]) print_person::person_initials#2 -- pbuz1=pbuz2
lda.z person_initials
sta.z print_str.str
lda.z person_initials+1
@ -2069,7 +2072,7 @@ ultoa_append: {
REGISTER UPLIFT POTENTIAL REGISTERS
Statement [6] (byte*~) print_char_cursor#49 ← (byte*) print_line_cursor#1 [ print_char_cursor#49 print_line_cursor#1 ] ( main:2 [ print_char_cursor#49 print_line_cursor#1 ] ) always clobbers reg byte a
Statement [10] (dword) print_dword_decimal::w#0 ← (dword) print_person::person_id#2 [ print_char_cursor#39 print_person::person_initials#2 print_line_cursor#20 print_dword_decimal::w#0 ] ( main:2::print_person:5 [ print_char_cursor#39 print_person::person_initials#2 print_line_cursor#20 print_dword_decimal::w#0 ] main:2::print_person:7 [ print_char_cursor#39 print_person::person_initials#2 print_line_cursor#20 print_dword_decimal::w#0 ] ) always clobbers reg byte a
Statement [14] (byte*) print_str::str#2 ← (byte[2]) print_person::person_initials#2 [ print_line_cursor#20 print_str::str#2 print_char_cursor#25 ] ( main:2::print_person:5 [ print_line_cursor#20 print_str::str#2 print_char_cursor#25 ] main:2::print_person:7 [ print_line_cursor#20 print_str::str#2 print_char_cursor#25 ] ) always clobbers reg byte a
Statement [14] (byte*) print_str::str#2 ← (byte[3]) print_person::person_initials#2 [ print_line_cursor#20 print_str::str#2 print_char_cursor#25 ] ( main:2::print_person:5 [ print_line_cursor#20 print_str::str#2 print_char_cursor#25 ] main:2::print_person:7 [ print_line_cursor#20 print_str::str#2 print_char_cursor#25 ] ) always clobbers reg byte a
Statement [21] (byte*) print_line_cursor#1 ← (byte*) print_line_cursor#9 + (byte) $28 [ print_line_cursor#1 print_char_cursor#18 ] ( main:2::print_person:5::print_ln:17 [ print_line_cursor#1 print_char_cursor#18 ] main:2::print_person:7::print_ln:17 [ print_line_cursor#1 print_char_cursor#18 ] ) always clobbers reg byte a
Statement [22] if((byte*) print_line_cursor#1<(byte*) print_char_cursor#18) goto print_ln::@1 [ print_line_cursor#1 print_char_cursor#18 ] ( main:2::print_person:5::print_ln:17 [ print_line_cursor#1 print_char_cursor#18 ] main:2::print_person:7::print_ln:17 [ print_line_cursor#1 print_char_cursor#18 ] ) always clobbers reg byte a
Statement [26] if((byte) 0!=*((byte*) print_str::str#3)) goto print_str::@2 [ print_char_cursor#18 print_str::str#3 ] ( main:2::print_person:5::print_str:15 [ print_line_cursor#20 print_char_cursor#18 print_str::str#3 ] main:2::print_person:7::print_str:15 [ print_line_cursor#20 print_char_cursor#18 print_str::str#3 ] main:2::print_person:5::print_dword_decimal:11::print_str:37 [ print_person::person_initials#2 print_line_cursor#20 print_char_cursor#18 print_str::str#3 ] main:2::print_person:7::print_dword_decimal:11::print_str:37 [ print_person::person_initials#2 print_line_cursor#20 print_char_cursor#18 print_str::str#3 ] ) always clobbers reg byte a reg byte y
@ -2097,7 +2100,7 @@ Removing always clobbered register reg byte y as potential for zp ZP_BYTE:14 [ u
Statement [66] (dword) ultoa_append::value#1 ← (dword) ultoa_append::value#2 - (dword) ultoa_append::sub#0 [ ultoa_append::buffer#0 ultoa_append::sub#0 ultoa_append::value#1 ultoa_append::digit#1 ] ( main:2::print_person:5::print_dword_decimal:11::ultoa:35::ultoa_append:56 [ print_person::person_initials#2 print_line_cursor#20 print_char_cursor#39 ultoa::digit#2 ultoa::buffer#11 ultoa_append::buffer#0 ultoa_append::sub#0 ultoa_append::value#1 ultoa_append::digit#1 ] main:2::print_person:7::print_dword_decimal:11::ultoa:35::ultoa_append:56 [ print_person::person_initials#2 print_line_cursor#20 print_char_cursor#39 ultoa::digit#2 ultoa::buffer#11 ultoa_append::buffer#0 ultoa_append::sub#0 ultoa_append::value#1 ultoa_append::digit#1 ] ) always clobbers reg byte a
Statement [6] (byte*~) print_char_cursor#49 ← (byte*) print_line_cursor#1 [ print_char_cursor#49 print_line_cursor#1 ] ( main:2 [ print_char_cursor#49 print_line_cursor#1 ] ) always clobbers reg byte a
Statement [10] (dword) print_dword_decimal::w#0 ← (dword) print_person::person_id#2 [ print_char_cursor#39 print_person::person_initials#2 print_line_cursor#20 print_dword_decimal::w#0 ] ( main:2::print_person:5 [ print_char_cursor#39 print_person::person_initials#2 print_line_cursor#20 print_dword_decimal::w#0 ] main:2::print_person:7 [ print_char_cursor#39 print_person::person_initials#2 print_line_cursor#20 print_dword_decimal::w#0 ] ) always clobbers reg byte a
Statement [14] (byte*) print_str::str#2 ← (byte[2]) print_person::person_initials#2 [ print_line_cursor#20 print_str::str#2 print_char_cursor#25 ] ( main:2::print_person:5 [ print_line_cursor#20 print_str::str#2 print_char_cursor#25 ] main:2::print_person:7 [ print_line_cursor#20 print_str::str#2 print_char_cursor#25 ] ) always clobbers reg byte a
Statement [14] (byte*) print_str::str#2 ← (byte[3]) print_person::person_initials#2 [ print_line_cursor#20 print_str::str#2 print_char_cursor#25 ] ( main:2::print_person:5 [ print_line_cursor#20 print_str::str#2 print_char_cursor#25 ] main:2::print_person:7 [ print_line_cursor#20 print_str::str#2 print_char_cursor#25 ] ) always clobbers reg byte a
Statement [21] (byte*) print_line_cursor#1 ← (byte*) print_line_cursor#9 + (byte) $28 [ print_line_cursor#1 print_char_cursor#18 ] ( main:2::print_person:5::print_ln:17 [ print_line_cursor#1 print_char_cursor#18 ] main:2::print_person:7::print_ln:17 [ print_line_cursor#1 print_char_cursor#18 ] ) always clobbers reg byte a
Statement [22] if((byte*) print_line_cursor#1<(byte*) print_char_cursor#18) goto print_ln::@1 [ print_line_cursor#1 print_char_cursor#18 ] ( main:2::print_person:5::print_ln:17 [ print_line_cursor#1 print_char_cursor#18 ] main:2::print_person:7::print_ln:17 [ print_line_cursor#1 print_char_cursor#18 ] ) always clobbers reg byte a
Statement [26] if((byte) 0!=*((byte*) print_str::str#3)) goto print_str::@2 [ print_char_cursor#18 print_str::str#3 ] ( main:2::print_person:5::print_str:15 [ print_line_cursor#20 print_char_cursor#18 print_str::str#3 ] main:2::print_person:7::print_str:15 [ print_line_cursor#20 print_char_cursor#18 print_str::str#3 ] main:2::print_person:5::print_dword_decimal:11::print_str:37 [ print_person::person_initials#2 print_line_cursor#20 print_char_cursor#18 print_str::str#3 ] main:2::print_person:7::print_dword_decimal:11::print_str:37 [ print_person::person_initials#2 print_line_cursor#20 print_char_cursor#18 print_str::str#3 ] ) always clobbers reg byte a reg byte y
@ -2216,7 +2219,7 @@ main: {
sta.z print_line_cursor
lda #>$400
sta.z print_line_cursor+1
// [9] phi (byte[2]) print_person::person_initials#2 = (const byte[2]) jesper_initials#0 [phi:main->print_person#1] -- pbuz1=pbuc1
// [9] phi (byte[3]) print_person::person_initials#2 = (const byte[3]) jesper_initials#0 [phi:main->print_person#1] -- pbuz1=pbuc1
lda #<jesper_initials
sta.z print_person.person_initials
lda #>jesper_initials
@ -2248,7 +2251,7 @@ main: {
// [9] phi from main::@1 to print_person [phi:main::@1->print_person]
print_person_from_b1:
// [9] phi (byte*) print_line_cursor#20 = (byte*) print_line_cursor#1 [phi:main::@1->print_person#0] -- register_copy
// [9] phi (byte[2]) print_person::person_initials#2 = (const byte[2]) henry_initials#0 [phi:main::@1->print_person#1] -- pbuz1=pbuc1
// [9] phi (byte[3]) print_person::person_initials#2 = (const byte[3]) henry_initials#0 [phi:main::@1->print_person#1] -- pbuz1=pbuc1
lda #<henry_initials
sta.z print_person.person_initials
lda #>henry_initials
@ -2271,7 +2274,7 @@ main: {
rts
}
// print_person
// print_person(dword zeropage(2) person_id, byte[2] zeropage(6) person_initials)
// print_person(dword zeropage(2) person_id, byte[3] zeropage(6) person_initials)
print_person: {
.label person_id = 2
.label person_initials = 6
@ -2288,7 +2291,7 @@ print_person: {
jmp b2
// print_person::@2
b2:
// [14] (byte*) print_str::str#2 ← (byte[2]) print_person::person_initials#2 -- pbuz1=pbuz2
// [14] (byte*) print_str::str#2 ← (byte[3]) print_person::person_initials#2 -- pbuz1=pbuz2
lda.z person_initials
sta.z print_str.str
lda.z person_initials+1
@ -2757,7 +2760,7 @@ FINAL SYMBOL TABLE
(byte[]) DIGITS
(const byte[]) DIGITS#0 DIGITS = (string) "0123456789abcdef"z
(dword) Person::id
(byte[2]) Person::initials
(byte[3]) Person::initials
(const byte) RADIX::BINARY BINARY = (number) 2
(const byte) RADIX::DECIMAL DECIMAL = (number) $a
(const byte) RADIX::HEXADECIMAL HEXADECIMAL = (number) $10
@ -2771,12 +2774,12 @@ FINAL SYMBOL TABLE
(const byte[$b]) decimal_digits_long#0 decimal_digits_long = { fill( $b, 0) }
(dword) henry_id
(const dword) henry_id#0 henry_id = (dword) $4466d
(byte[2]) henry_initials
(const byte[2]) henry_initials#0 henry_initials = (string) "hg"
(byte[3]) henry_initials
(const byte[3]) henry_initials#0 henry_initials = (string) "hg"
(dword) jesper_id
(const dword) jesper_id#0 jesper_id = (dword) $1b244
(byte[2]) jesper_initials
(const byte[2]) jesper_initials#0 jesper_initials = (string) "jg"
(byte[3]) jesper_initials
(const byte[3]) jesper_initials#0 jesper_initials = (string) "jg"
(void()) main()
(label) main::@1
(label) main::@return
@ -2803,7 +2806,7 @@ FINAL SYMBOL TABLE
(void()) print_ln()
(label) print_ln::@1
(label) print_ln::@return
(void()) print_person((dword) print_person::person_id , (byte[2]) print_person::person_initials)
(void()) print_person((dword) print_person::person_id , (byte[3]) print_person::person_initials)
(label) print_person::@1
(label) print_person::@2
(label) print_person::@3
@ -2811,8 +2814,8 @@ FINAL SYMBOL TABLE
(struct Person) print_person::person
(dword) print_person::person_id
(dword) print_person::person_id#2 person_id zp ZP_DWORD:2 2.0
(byte[2]) print_person::person_initials
(byte[2]) print_person::person_initials#2 person_initials zp ZP_WORD:6 0.4
(byte[3]) print_person::person_initials
(byte[3]) print_person::person_initials#2 person_initials zp ZP_WORD:6 0.4
(byte*) print_screen
(void()) print_str((byte*) print_str::str)
(label) print_str::@1
@ -2919,7 +2922,7 @@ main: {
sta.z print_line_cursor
lda #>$400
sta.z print_line_cursor+1
// [9] phi (byte[2]) print_person::person_initials#2 = (const byte[2]) jesper_initials#0 [phi:main->print_person#1] -- pbuz1=pbuc1
// [9] phi (byte[3]) print_person::person_initials#2 = (const byte[3]) jesper_initials#0 [phi:main->print_person#1] -- pbuz1=pbuc1
lda #<jesper_initials
sta.z print_person.person_initials
lda #>jesper_initials
@ -2949,7 +2952,7 @@ main: {
// [7] call print_person
// [9] phi from main::@1 to print_person [phi:main::@1->print_person]
// [9] phi (byte*) print_line_cursor#20 = (byte*) print_line_cursor#1 [phi:main::@1->print_person#0] -- register_copy
// [9] phi (byte[2]) print_person::person_initials#2 = (const byte[2]) henry_initials#0 [phi:main::@1->print_person#1] -- pbuz1=pbuc1
// [9] phi (byte[3]) print_person::person_initials#2 = (const byte[3]) henry_initials#0 [phi:main::@1->print_person#1] -- pbuz1=pbuc1
lda #<henry_initials
sta.z print_person.person_initials
lda #>henry_initials
@ -2971,7 +2974,7 @@ main: {
rts
}
// print_person
// print_person(dword zeropage(2) person_id, byte[2] zeropage(6) person_initials)
// print_person(dword zeropage(2) person_id, byte[3] zeropage(6) person_initials)
print_person: {
.label person_id = 2
.label person_initials = 6
@ -2986,7 +2989,7 @@ print_person: {
jsr print_char
// print_person::@2
// print_str(person.initials)
// [14] (byte*) print_str::str#2 ← (byte[2]) print_person::person_initials#2 -- pbuz1=pbuz2
// [14] (byte*) print_str::str#2 ← (byte[3]) print_person::person_initials#2 -- pbuz1=pbuz2
lda.z person_initials
sta.z print_str.str
lda.z person_initials+1

View File

@ -4,7 +4,7 @@
(byte[]) DIGITS
(const byte[]) DIGITS#0 DIGITS = (string) "0123456789abcdef"z
(dword) Person::id
(byte[2]) Person::initials
(byte[3]) Person::initials
(const byte) RADIX::BINARY BINARY = (number) 2
(const byte) RADIX::DECIMAL DECIMAL = (number) $a
(const byte) RADIX::HEXADECIMAL HEXADECIMAL = (number) $10
@ -18,12 +18,12 @@
(const byte[$b]) decimal_digits_long#0 decimal_digits_long = { fill( $b, 0) }
(dword) henry_id
(const dword) henry_id#0 henry_id = (dword) $4466d
(byte[2]) henry_initials
(const byte[2]) henry_initials#0 henry_initials = (string) "hg"
(byte[3]) henry_initials
(const byte[3]) henry_initials#0 henry_initials = (string) "hg"
(dword) jesper_id
(const dword) jesper_id#0 jesper_id = (dword) $1b244
(byte[2]) jesper_initials
(const byte[2]) jesper_initials#0 jesper_initials = (string) "jg"
(byte[3]) jesper_initials
(const byte[3]) jesper_initials#0 jesper_initials = (string) "jg"
(void()) main()
(label) main::@1
(label) main::@return
@ -50,7 +50,7 @@
(void()) print_ln()
(label) print_ln::@1
(label) print_ln::@return
(void()) print_person((dword) print_person::person_id , (byte[2]) print_person::person_initials)
(void()) print_person((dword) print_person::person_id , (byte[3]) print_person::person_initials)
(label) print_person::@1
(label) print_person::@2
(label) print_person::@3
@ -58,8 +58,8 @@
(struct Person) print_person::person
(dword) print_person::person_id
(dword) print_person::person_id#2 person_id zp ZP_DWORD:2 2.0
(byte[2]) print_person::person_initials
(byte[2]) print_person::person_initials#2 person_initials zp ZP_WORD:6 0.4
(byte[3]) print_person::person_initials
(byte[3]) print_person::person_initials#2 person_initials zp ZP_WORD:6 0.4
(byte*) print_screen
(void()) print_str((byte*) print_str::str)
(label) print_str::@1

View File

@ -24,9 +24,9 @@ main: {
jesper_name: .text "jesper"
.byte 0
.fill 57, 0
henriette_name: .text "repsej"
henriette_name: .text "henriette"
.byte 0
.fill 57, 0
.fill 54, 0
}
// print_person(byte register(X) person_id, byte[$40] zeropage(2) person_name)
print_person: {

View File

@ -1,3 +1,6 @@
Fixing struct type size struct Person to 65
Fixing struct type size struct Person to 65
Fixing struct type size struct Person to 65
Created struct value member variable (byte) main::jesper_id
Created struct value member variable (byte[$40]) main::jesper_name
Converted struct value to member variables (struct Person) main::jesper
@ -146,7 +149,7 @@ SYMBOL TABLE SSA
(byte) idx#9
(void()) main()
(const string) main::$2 = (string) "jesper"
(const string) main::$3 = (string) "repsej"
(const string) main::$3 = (string) "henriette"
(label) main::@1
(label) main::@2
(label) main::@return
@ -471,9 +474,9 @@ main: {
jesper_name: .text "jesper"
.byte 0
.fill 57, 0
henriette_name: .text "repsej"
henriette_name: .text "henriette"
.byte 0
.fill 57, 0
.fill 54, 0
}
// print_person
// print_person(byte zeropage(2) person_id, byte[$40] zeropage(4) person_name)
@ -651,9 +654,9 @@ main: {
jesper_name: .text "jesper"
.byte 0
.fill 57, 0
henriette_name: .text "repsej"
henriette_name: .text "henriette"
.byte 0
.fill 57, 0
.fill 54, 0
}
// print_person
// print_person(byte register(X) person_id, byte[$40] zeropage(2) person_name)
@ -771,7 +774,7 @@ FINAL SYMBOL TABLE
(byte) main::henriette_id
(const byte) main::henriette_id#1 henriette_id = (byte) 7
(byte[$40]) main::henriette_name
(const byte[$40]) main::henriette_name#1 henriette_name = (string) "repsej"
(const byte[$40]) main::henriette_name#1 henriette_name = (string) "henriette"
(byte) main::jesper_id
(const byte) main::jesper_id#1 jesper_id = (byte) 4
(byte[$40]) main::jesper_name
@ -855,9 +858,9 @@ main: {
jesper_name: .text "jesper"
.byte 0
.fill 57, 0
henriette_name: .text "repsej"
henriette_name: .text "henriette"
.byte 0
.fill 57, 0
.fill 54, 0
}
// print_person
// print_person(byte register(X) person_id, byte[$40] zeropage(2) person_name)

View File

@ -20,7 +20,7 @@
(byte) main::henriette_id
(const byte) main::henriette_id#1 henriette_id = (byte) 7
(byte[$40]) main::henriette_name
(const byte[$40]) main::henriette_name#1 henriette_name = (string) "repsej"
(const byte[$40]) main::henriette_name#1 henriette_name = (string) "henriette"
(byte) main::jesper_id
(const byte) main::jesper_id#1 jesper_id = (byte) 4
(byte[$40]) main::jesper_name

View File

@ -1,42 +1,34 @@
// Example of a struct containing an array
// Fails (by displaying "BB" ) because the memory layout is wrong - and the name is treated like a pointer (to 0x0000) instead of a value.
// https://gitlab.com/camelot/kickc/issues/312
.pc = $801 "Basic"
:BasicUpstart(main)
.pc = $80d "Program"
.const SIZEOF_STRUCT_PERSON = 3
.const SIZEOF_STRUCT_PERSON = $10
.const OFFSET_STRUCT_PERSON_NAME = 1
.const OFFSET_STRUCT_PERSON_AGE = $e
main: {
.label SCREEN = $400
.label person = persons+SIZEOF_STRUCT_PERSON
lda #7
sta persons
lda #9
sta persons+1*SIZEOF_STRUCT_PERSON
lda #'a'
ldy persons+OFFSET_STRUCT_PERSON_NAME
sty.z $fe
ldy persons+OFFSET_STRUCT_PERSON_NAME+1
sty.z $ff
ldy #0
sta ($fe),y
sta persons+OFFSET_STRUCT_PERSON_NAME+8
lda #'b'
ldy persons+OFFSET_STRUCT_PERSON_NAME+1*SIZEOF_STRUCT_PERSON
sty.z $fe
ldy persons+OFFSET_STRUCT_PERSON_NAME+1*SIZEOF_STRUCT_PERSON+1
sty.z $ff
ldy #0
sta ($fe),y
ldy persons+OFFSET_STRUCT_PERSON_NAME
sty.z $fe
ldy persons+OFFSET_STRUCT_PERSON_NAME+1
sty.z $ff
ldy #0
lda ($fe),y
sta persons+1*SIZEOF_STRUCT_PERSON+OFFSET_STRUCT_PERSON_NAME+8
lda #<$141
sta persons+OFFSET_STRUCT_PERSON_AGE
lda #>$141
sta persons+OFFSET_STRUCT_PERSON_AGE+1
lda #0
sta persons+OFFSET_STRUCT_PERSON_AGE+1*SIZEOF_STRUCT_PERSON+1
lda #<$7b
sta persons+OFFSET_STRUCT_PERSON_AGE+1*SIZEOF_STRUCT_PERSON
lda persons+OFFSET_STRUCT_PERSON_NAME+8
sta SCREEN
ldy person+OFFSET_STRUCT_PERSON_NAME
sty.z $fe
ldy person+OFFSET_STRUCT_PERSON_NAME+1
sty.z $ff
ldy #0
lda ($fe),y
lda person+OFFSET_STRUCT_PERSON_NAME+8
sta SCREEN+1
rts
}
persons: .fill 3*2, 0
persons: .fill $10*2, 0

View File

@ -8,11 +8,15 @@
@end: scope:[] from @1
[3] phi()
main: scope:[main] from @1
[4] *(*((byte[$10]*)(const struct Person[2]) persons#0+(const byte) OFFSET_STRUCT_PERSON_NAME)) ← (byte) 'a'
[5] *(*((byte[$10]*)(const struct Person[2]) persons#0+(const byte) OFFSET_STRUCT_PERSON_NAME+(byte) 1*(const byte) SIZEOF_STRUCT_PERSON)) ← (byte) 'b'
[6] *((const byte*) main::SCREEN#0) ← *(*((byte[$10]*)(const struct Person[2]) persons#0+(const byte) OFFSET_STRUCT_PERSON_NAME))
[7] *((const byte*) main::SCREEN#0+(byte) 1) ← *(*((byte[$10]*)(const struct Person*) main::person#1+(const byte) OFFSET_STRUCT_PERSON_NAME))
[4] *((byte*)(const struct Person[2]) persons#0) ← (byte) 7
[5] *((byte*)(const struct Person[2]) persons#0+(byte) 1*(const byte) SIZEOF_STRUCT_PERSON) ← (byte) 9
[6] *((byte[$d])(const struct Person[2]) persons#0+(const byte) OFFSET_STRUCT_PERSON_NAME+(byte) 8) ← (byte) 'a'
[7] *((byte[$d])(const struct Person[2]) persons#0+(byte) 1*(const byte) SIZEOF_STRUCT_PERSON+(const byte) OFFSET_STRUCT_PERSON_NAME+(byte) 8) ← (byte) 'b'
[8] *((word*)(const struct Person[2]) persons#0+(const byte) OFFSET_STRUCT_PERSON_AGE) ← (word) $141
[9] *((word*)(const struct Person[2]) persons#0+(const byte) OFFSET_STRUCT_PERSON_AGE+(byte) 1*(const byte) SIZEOF_STRUCT_PERSON) ← (byte) $7b
[10] *((const byte*) main::SCREEN#0) ← *((byte[$d])(const struct Person[2]) persons#0+(const byte) OFFSET_STRUCT_PERSON_NAME+(byte) 8)
[11] *((const byte*) main::SCREEN#0+(byte) 1) ← *((byte[$d])(const struct Person*) main::person#1+(const byte) OFFSET_STRUCT_PERSON_NAME+(byte) 8)
to:main::@return
main::@return: scope:[main] from main
[8] return
[12] return
to:@return

View File

@ -1,8 +1,18 @@
Fixing struct type size struct Person to 16
Fixing struct type size struct Person to 16
Fixing pointer increment (struct Person*) main::person ← ++ (struct Person*) main::person
Fixing pointer array-indexing *((struct Person[2]) persons + (number) 0)
Fixing pointer array-indexing *((struct Person[2]) persons + (number) 1)
Rewriting struct pointer member access *((struct Person[2]) persons + (number~) main::$0).name
Rewriting struct pointer member access *((struct Person[2]) persons + (number~) main::$1).name
Fixing pointer array-indexing *((struct Person[2]) persons + (number) 0)
Fixing pointer array-indexing *((struct Person[2]) persons + (number) 1)
Fixing pointer array-indexing *((struct Person[2]) persons + (number) 0)
Fixing pointer array-indexing *((struct Person[2]) persons + (number) 1)
Rewriting struct pointer member access *((struct Person[2]) persons + (number~) main::$0).id
Rewriting struct pointer member access *((struct Person[2]) persons + (number~) main::$1).id
Rewriting struct pointer member access *((struct Person[2]) persons + (number~) main::$2).name
Rewriting struct pointer member access *((struct Person[2]) persons + (number~) main::$3).name
Rewriting struct pointer member access *((struct Person[2]) persons + (number~) main::$4).age
Rewriting struct pointer member access *((struct Person[2]) persons + (number~) main::$5).age
Rewriting struct pointer member access *((struct Person*) main::person).name
Rewriting struct pointer member access *((struct Person*) main::person).name
@ -12,18 +22,32 @@ CONTROL FLOW GRAPH SSA
to:@1
main: scope:[main] from @1
(number~) main::$0 ← (number) 0 * (const byte) SIZEOF_STRUCT_PERSON
(byte[$10]*) main::$2 ← (byte[$10]*)(struct Person[2]) persons#0 + (const byte) OFFSET_STRUCT_PERSON_NAME
*(*((byte[$10]*) main::$2 + (number~) main::$0) + (number) 0) ← (byte) 'a'
(byte*) main::$6 ← (byte*)(struct Person[2]) persons#0 + (const byte) OFFSET_STRUCT_PERSON_ID
*((byte*) main::$6 + (number~) main::$0) ← (number) 7
(number~) main::$1 ← (number) 1 * (const byte) SIZEOF_STRUCT_PERSON
(byte[$10]*) main::$3 ← (byte[$10]*)(struct Person[2]) persons#0 + (const byte) OFFSET_STRUCT_PERSON_NAME
*(*((byte[$10]*) main::$3 + (number~) main::$1) + (number) 0) ← (byte) 'b'
(byte*) main::$7 ← (byte*)(struct Person[2]) persons#0 + (const byte) OFFSET_STRUCT_PERSON_ID
*((byte*) main::$7 + (number~) main::$1) ← (number) 9
(number~) main::$2 ← (number) 0 * (const byte) SIZEOF_STRUCT_PERSON
(byte[$d]) main::$8 ← (byte[$d])(struct Person[2]) persons#0 + (number~) main::$2
(byte[$d]) main::$9 ← (byte[$d]) main::$8 + (const byte) OFFSET_STRUCT_PERSON_NAME
*((byte[$d]) main::$9 + (number) 8) ← (byte) 'a'
(number~) main::$3 ← (number) 1 * (const byte) SIZEOF_STRUCT_PERSON
(byte[$d]) main::$10 ← (byte[$d])(struct Person[2]) persons#0 + (number~) main::$3
(byte[$d]) main::$11 ← (byte[$d]) main::$10 + (const byte) OFFSET_STRUCT_PERSON_NAME
*((byte[$d]) main::$11 + (number) 8) ← (byte) 'b'
(number~) main::$4 ← (number) 0 * (const byte) SIZEOF_STRUCT_PERSON
(word*) main::$12 ← (word*)(struct Person[2]) persons#0 + (const byte) OFFSET_STRUCT_PERSON_AGE
*((word*) main::$12 + (number~) main::$4) ← (number) $141
(number~) main::$5 ← (number) 1 * (const byte) SIZEOF_STRUCT_PERSON
(word*) main::$13 ← (word*)(struct Person[2]) persons#0 + (const byte) OFFSET_STRUCT_PERSON_AGE
*((word*) main::$13 + (number~) main::$5) ← (number) $7b
(byte*) main::SCREEN#0 ← ((byte*)) (number) $400
(struct Person*) main::person#0 ← (struct Person[2]) persons#0
(byte[$10]*) main::$4 ← (byte[$10]*)(struct Person*) main::person#0 + (const byte) OFFSET_STRUCT_PERSON_NAME
*((byte*) main::SCREEN#0 + (number) 0) ← *(*((byte[$10]*) main::$4) + (number) 0)
(byte[$d]) main::$14 ← (byte[$d])(struct Person*) main::person#0 + (const byte) OFFSET_STRUCT_PERSON_NAME
*((byte*) main::SCREEN#0 + (number) 0) ← *((byte[$d]) main::$14 + (number) 8)
(struct Person*) main::person#1 ← (struct Person*) main::person#0 + (const byte) SIZEOF_STRUCT_PERSON
(byte[$10]*) main::$5 ← (byte[$10]*)(struct Person*) main::person#1 + (const byte) OFFSET_STRUCT_PERSON_NAME
*((byte*) main::SCREEN#0 + (number) 1) ← *(*((byte[$10]*) main::$5) + (number) 0)
(byte[$d]) main::$15 ← (byte[$d])(struct Person*) main::person#1 + (const byte) OFFSET_STRUCT_PERSON_NAME
*((byte*) main::SCREEN#0 + (number) 1) ← *((byte[$d]) main::$15 + (number) 8)
to:main::@return
main::@return: scope:[main] from main
return
@ -40,17 +64,30 @@ SYMBOL TABLE SSA
(label) @2
(label) @begin
(label) @end
(const byte) OFFSET_STRUCT_PERSON_AGE = (byte) $e
(const byte) OFFSET_STRUCT_PERSON_ID = (byte) 0
(const byte) OFFSET_STRUCT_PERSON_NAME = (byte) 1
(word) Person::age
(byte) Person::id
(byte[$10]) Person::name
(const byte) SIZEOF_STRUCT_PERSON = (byte) 3
(byte[$d]) Person::name
(const byte) SIZEOF_STRUCT_PERSON = (byte) $10
(void()) main()
(number~) main::$0
(number~) main::$1
(byte[$10]*) main::$2
(byte[$10]*) main::$3
(byte[$10]*) main::$4
(byte[$10]*) main::$5
(byte[$d]) main::$10
(byte[$d]) main::$11
(word*) main::$12
(word*) main::$13
(byte[$d]) main::$14
(byte[$d]) main::$15
(number~) main::$2
(number~) main::$3
(number~) main::$4
(number~) main::$5
(byte*) main::$6
(byte*) main::$7
(byte[$d]) main::$8
(byte[$d]) main::$9
(label) main::@return
(byte*) main::SCREEN
(byte*) main::SCREEN#0
@ -62,88 +99,164 @@ SYMBOL TABLE SSA
Adding number conversion cast (unumber) 0 in (number~) main::$0 ← (number) 0 * (const byte) SIZEOF_STRUCT_PERSON
Adding number conversion cast (unumber) main::$0 in (number~) main::$0 ← (unumber)(number) 0 * (const byte) SIZEOF_STRUCT_PERSON
Adding number conversion cast (unumber) 0 in *(*((byte[$10]*) main::$2 + (unumber~) main::$0) + (number) 0) ← (byte) 'a'
Adding number conversion cast (unumber) 7 in *((byte*) main::$6 + (unumber~) main::$0) ← (number) 7
Adding number conversion cast (unumber) 1 in (number~) main::$1 ← (number) 1 * (const byte) SIZEOF_STRUCT_PERSON
Adding number conversion cast (unumber) main::$1 in (number~) main::$1 ← (unumber)(number) 1 * (const byte) SIZEOF_STRUCT_PERSON
Adding number conversion cast (unumber) 0 in *(*((byte[$10]*) main::$3 + (unumber~) main::$1) + (number) 0) ← (byte) 'b'
Adding number conversion cast (unumber) 0 in *((byte*) main::SCREEN#0 + (number) 0) ← *(*((byte[$10]*) main::$4) + (number) 0)
Adding number conversion cast (unumber) 0 in *((byte*) main::SCREEN#0 + (number) 0) ← *(*((byte[$10]*) main::$4) + (unumber)(number) 0)
Adding number conversion cast (unumber) 0 in *((byte*) main::SCREEN#0 + (number) 1) ← *(*((byte[$10]*) main::$5) + (number) 0)
Adding number conversion cast (unumber) 1 in *((byte*) main::SCREEN#0 + (number) 1) ← *(*((byte[$10]*) main::$5) + (unumber)(number) 0)
Adding number conversion cast (unumber) 9 in *((byte*) main::$7 + (unumber~) main::$1) ← (number) 9
Adding number conversion cast (unumber) 0 in (number~) main::$2 ← (number) 0 * (const byte) SIZEOF_STRUCT_PERSON
Adding number conversion cast (unumber) main::$2 in (number~) main::$2 ← (unumber)(number) 0 * (const byte) SIZEOF_STRUCT_PERSON
Adding number conversion cast (unumber) 8 in *((byte[$d]) main::$9 + (number) 8) ← (byte) 'a'
Adding number conversion cast (unumber) 1 in (number~) main::$3 ← (number) 1 * (const byte) SIZEOF_STRUCT_PERSON
Adding number conversion cast (unumber) main::$3 in (number~) main::$3 ← (unumber)(number) 1 * (const byte) SIZEOF_STRUCT_PERSON
Adding number conversion cast (unumber) 8 in *((byte[$d]) main::$11 + (number) 8) ← (byte) 'b'
Adding number conversion cast (unumber) 0 in (number~) main::$4 ← (number) 0 * (const byte) SIZEOF_STRUCT_PERSON
Adding number conversion cast (unumber) main::$4 in (number~) main::$4 ← (unumber)(number) 0 * (const byte) SIZEOF_STRUCT_PERSON
Adding number conversion cast (unumber) $141 in *((word*) main::$12 + (unumber~) main::$4) ← (number) $141
Adding number conversion cast (unumber) 1 in (number~) main::$5 ← (number) 1 * (const byte) SIZEOF_STRUCT_PERSON
Adding number conversion cast (unumber) main::$5 in (number~) main::$5 ← (unumber)(number) 1 * (const byte) SIZEOF_STRUCT_PERSON
Adding number conversion cast (unumber) $7b in *((word*) main::$13 + (unumber~) main::$5) ← (number) $7b
Adding number conversion cast (unumber) 8 in *((byte*) main::SCREEN#0 + (number) 0) ← *((byte[$d]) main::$14 + (number) 8)
Adding number conversion cast (unumber) 0 in *((byte*) main::SCREEN#0 + (number) 0) ← *((byte[$d]) main::$14 + (unumber)(number) 8)
Adding number conversion cast (unumber) 8 in *((byte*) main::SCREEN#0 + (number) 1) ← *((byte[$d]) main::$15 + (number) 8)
Adding number conversion cast (unumber) 1 in *((byte*) main::SCREEN#0 + (number) 1) ← *((byte[$d]) main::$15 + (unumber)(number) 8)
Successful SSA optimization PassNAddNumberTypeConversions
Inlining cast *((byte*) main::$6 + (unumber~) main::$0) ← (unumber)(number) 7
Inlining cast *((byte*) main::$7 + (unumber~) main::$1) ← (unumber)(number) 9
Inlining cast *((word*) main::$12 + (unumber~) main::$4) ← (unumber)(number) $141
Inlining cast *((word*) main::$13 + (unumber~) main::$5) ← (unumber)(number) $7b
Inlining cast (byte*) main::SCREEN#0 ← (byte*)(number) $400
Successful SSA optimization Pass2InlineCast
Simplifying constant integer cast 0
Simplifying constant integer cast 0
Simplifying constant integer cast 7
Simplifying constant integer cast 1
Simplifying constant integer cast 9
Simplifying constant integer cast 0
Simplifying constant integer cast 8
Simplifying constant integer cast 1
Simplifying constant integer cast 8
Simplifying constant integer cast 0
Simplifying constant integer cast $141
Simplifying constant integer cast 1
Simplifying constant integer cast $7b
Simplifying constant pointer cast (byte*) 1024
Simplifying constant integer cast 8
Simplifying constant integer cast 0
Simplifying constant integer cast 0
Simplifying constant integer cast 0
Simplifying constant integer cast 8
Simplifying constant integer cast 1
Successful SSA optimization PassNCastSimplification
Finalized unsigned number type (byte) 0
Finalized unsigned number type (byte) 0
Finalized unsigned number type (byte) 7
Finalized unsigned number type (byte) 1
Finalized unsigned number type (byte) 9
Finalized unsigned number type (byte) 0
Finalized unsigned number type (byte) 8
Finalized unsigned number type (byte) 1
Finalized unsigned number type (byte) 8
Finalized unsigned number type (byte) 0
Finalized unsigned number type (word) $141
Finalized unsigned number type (byte) 1
Finalized unsigned number type (byte) $7b
Finalized unsigned number type (byte) 8
Finalized unsigned number type (byte) 0
Finalized unsigned number type (byte) 0
Finalized unsigned number type (byte) 8
Finalized unsigned number type (byte) 1
Successful SSA optimization PassNFinalizeNumberTypeConversions
Inferred type updated to byte in (unumber~) main::$0 ← (byte) 0 * (const byte) SIZEOF_STRUCT_PERSON
Inferred type updated to byte in (unumber~) main::$1 ← (byte) 1 * (const byte) SIZEOF_STRUCT_PERSON
Inferred type updated to byte in (unumber~) main::$2 ← (byte) 0 * (const byte) SIZEOF_STRUCT_PERSON
Inferred type updated to byte in (unumber~) main::$3 ← (byte) 1 * (const byte) SIZEOF_STRUCT_PERSON
Inferred type updated to byte in (unumber~) main::$4 ← (byte) 0 * (const byte) SIZEOF_STRUCT_PERSON
Inferred type updated to byte in (unumber~) main::$5 ← (byte) 1 * (const byte) SIZEOF_STRUCT_PERSON
Constant right-side identified [0] (struct Person[2]) persons#0 ← { fill( 2, 0) }
Constant right-side identified [1] (byte~) main::$0 ← (byte) 0 * (const byte) SIZEOF_STRUCT_PERSON
Constant right-side identified [4] (byte~) main::$1 ← (byte) 1 * (const byte) SIZEOF_STRUCT_PERSON
Constant right-side identified [7] (byte~) main::$2 ← (byte) 0 * (const byte) SIZEOF_STRUCT_PERSON
Constant right-side identified [11] (byte~) main::$3 ← (byte) 1 * (const byte) SIZEOF_STRUCT_PERSON
Constant right-side identified [15] (byte~) main::$4 ← (byte) 0 * (const byte) SIZEOF_STRUCT_PERSON
Constant right-side identified [18] (byte~) main::$5 ← (byte) 1 * (const byte) SIZEOF_STRUCT_PERSON
Successful SSA optimization Pass2ConstantRValueConsolidation
Constant (const struct Person[2]) persons#0 = { fill( 2, 0) }
Constant (const byte) main::$0 = 0*SIZEOF_STRUCT_PERSON
Constant (const byte) main::$1 = 1*SIZEOF_STRUCT_PERSON
Constant (const byte) main::$2 = 0*SIZEOF_STRUCT_PERSON
Constant (const byte) main::$3 = 1*SIZEOF_STRUCT_PERSON
Constant (const byte) main::$4 = 0*SIZEOF_STRUCT_PERSON
Constant (const byte) main::$5 = 1*SIZEOF_STRUCT_PERSON
Constant (const byte*) main::SCREEN#0 = (byte*) 1024
Successful SSA optimization Pass2ConstantIdentification
Constant (const struct Person*) main::person#0 = persons#0
Successful SSA optimization Pass2ConstantIdentification
Constant value identified (byte[$10]*)persons#0 in [2] (byte[$10]*) main::$2 ← (byte[$10]*)(const struct Person[2]) persons#0 + (const byte) OFFSET_STRUCT_PERSON_NAME
Constant value identified (byte[$10]*)persons#0 in [5] (byte[$10]*) main::$3 ← (byte[$10]*)(const struct Person[2]) persons#0 + (const byte) OFFSET_STRUCT_PERSON_NAME
Constant value identified (byte[$10]*)main::person#0 in [9] (byte[$10]*) main::$4 ← (byte[$10]*)(const struct Person*) main::person#0 + (const byte) OFFSET_STRUCT_PERSON_NAME
Constant value identified (byte*)persons#0 in [2] (byte*) main::$6 ← (byte*)(const struct Person[2]) persons#0 + (const byte) OFFSET_STRUCT_PERSON_ID
Constant value identified (byte*)persons#0 in [5] (byte*) main::$7 ← (byte*)(const struct Person[2]) persons#0 + (const byte) OFFSET_STRUCT_PERSON_ID
Constant value identified (byte[$d])persons#0 in [8] (byte[$d]) main::$8 ← (byte[$d])(const struct Person[2]) persons#0 + (const byte) main::$2
Constant value identified (byte[$d])persons#0 in [12] (byte[$d]) main::$10 ← (byte[$d])(const struct Person[2]) persons#0 + (const byte) main::$3
Constant value identified (word*)persons#0 in [16] (word*) main::$12 ← (word*)(const struct Person[2]) persons#0 + (const byte) OFFSET_STRUCT_PERSON_AGE
Constant value identified (word*)persons#0 in [19] (word*) main::$13 ← (word*)(const struct Person[2]) persons#0 + (const byte) OFFSET_STRUCT_PERSON_AGE
Constant value identified (byte[$d])main::person#0 in [23] (byte[$d]) main::$14 ← (byte[$d])(const struct Person*) main::person#0 + (const byte) OFFSET_STRUCT_PERSON_NAME
Successful SSA optimization Pass2ConstantValues
Converting *(pointer+n) to pointer[n] [10] *((const byte*) main::SCREEN#0 + (byte) 0) ← *(*((byte[$10]*) main::$4) + (byte) 0) -- *((byte[$10]*)main::person#0 + OFFSET_STRUCT_PERSON_NAME)
Converting *(pointer+n) to pointer[n] [13] *((const byte*) main::SCREEN#0 + (byte) 1) ← *(*((byte[$10]*) main::$5) + (byte) 0) -- *((byte[$10]*)main::person#1 + OFFSET_STRUCT_PERSON_NAME)
Successful SSA optimization Pass2InlineDerefIdx
Simplifying constant evaluating to zero (byte) 0*(const byte) SIZEOF_STRUCT_PERSON in
Simplifying constant evaluating to zero (byte) 0*(const byte) SIZEOF_STRUCT_PERSON in
Simplifying constant evaluating to zero (byte) 0*(const byte) SIZEOF_STRUCT_PERSON in
Successful SSA optimization PassNSimplifyConstantZero
Simplifying expression containing zero *(main::$2 + main::$0) in [3] *(*((byte[$10]*) main::$2 + (const byte) main::$0) + (byte) 0) ← (byte) 'a'
Simplifying expression containing zero main::$2 in [3] *(*((byte[$10]*) main::$2 + (const byte) main::$0)) ← (byte) 'a'
Simplifying expression containing zero *(main::$3 + main::$1) in [6] *(*((byte[$10]*) main::$3 + (const byte) main::$1) + (byte) 0) ← (byte) 'b'
Simplifying expression containing zero *((byte[$10]*)main::person#0 + OFFSET_STRUCT_PERSON_NAME) in [10] *((const byte*) main::SCREEN#0 + (byte) 0) ← *(*((byte[$10]*)(const struct Person*) main::person#0 + (const byte) OFFSET_STRUCT_PERSON_NAME) + (byte) 0)
Simplifying expression containing zero main::SCREEN#0 in [10] *((const byte*) main::SCREEN#0 + (byte) 0) ← *(*((byte[$10]*)(const struct Person*) main::person#0 + (const byte) OFFSET_STRUCT_PERSON_NAME))
Simplifying expression containing zero *((byte[$10]*)main::person#1 + OFFSET_STRUCT_PERSON_NAME) in [13] *((const byte*) main::SCREEN#0 + (byte) 1) ← *(*((byte[$10]*)(struct Person*) main::person#1 + (const byte) OFFSET_STRUCT_PERSON_NAME) + (byte) 0)
Simplifying expression containing zero (byte*)persons#0 in [2] (byte*) main::$6 ← (byte*)(const struct Person[2]) persons#0 + (const byte) OFFSET_STRUCT_PERSON_ID
Simplifying expression containing zero main::$6 in [3] *((byte*) main::$6 + (const byte) main::$0) ← (byte) 7
Simplifying expression containing zero (byte*)persons#0 in [5] (byte*) main::$7 ← (byte*)(const struct Person[2]) persons#0 + (const byte) OFFSET_STRUCT_PERSON_ID
Simplifying expression containing zero (byte[$d])persons#0 in [8] (byte[$d]) main::$8 ← (byte[$d])(const struct Person[2]) persons#0 + (const byte) main::$2
Simplifying expression containing zero main::$12 in [17] *((word*) main::$12 + (const byte) main::$4) ← (word) $141
Simplifying expression containing zero main::SCREEN#0 in [24] *((const byte*) main::SCREEN#0 + (byte) 0) ← *((byte[$d]) main::$14 + (byte) 8)
Successful SSA optimization PassNSimplifyExpressionWithZero
Eliminating unused variable (byte[$10]*) main::$4 and assignment [4] (byte[$10]*) main::$4 ← (byte[$10]*)(const struct Person*) main::person#0 + (const byte) OFFSET_STRUCT_PERSON_NAME
Eliminating unused variable (byte[$10]*) main::$5 and assignment [7] (byte[$10]*) main::$5 ← (byte[$10]*)(struct Person*) main::person#1 + (const byte) OFFSET_STRUCT_PERSON_NAME
Eliminating unused constant (const byte) main::$0
Eliminating unused constant (const byte) main::$2
Eliminating unused constant (const byte) main::$4
Eliminating unused constant (const byte) OFFSET_STRUCT_PERSON_ID
Successful SSA optimization PassNEliminateUnusedVars
Constant right-side identified [0] (byte[$10]*) main::$2 ← (byte[$10]*)(const struct Person[2]) persons#0 + (const byte) OFFSET_STRUCT_PERSON_NAME
Constant right-side identified [2] (byte[$10]*) main::$3 ← (byte[$10]*)(const struct Person[2]) persons#0 + (const byte) OFFSET_STRUCT_PERSON_NAME
Constant right-side identified [5] (struct Person*) main::person#1 ← (const struct Person*) main::person#0 + (const byte) SIZEOF_STRUCT_PERSON
Constant right-side identified [7] (byte[$d]) main::$10 ← (byte[$d])(const struct Person[2]) persons#0 + (const byte) main::$3
Constant right-side identified [10] (word*) main::$12 ← (word*)(const struct Person[2]) persons#0 + (const byte) OFFSET_STRUCT_PERSON_AGE
Constant right-side identified [12] (word*) main::$13 ← (word*)(const struct Person[2]) persons#0 + (const byte) OFFSET_STRUCT_PERSON_AGE
Constant right-side identified [14] (byte[$d]) main::$14 ← (byte[$d])(const struct Person*) main::person#0 + (const byte) OFFSET_STRUCT_PERSON_NAME
Constant right-side identified [16] (struct Person*) main::person#1 ← (const struct Person*) main::person#0 + (const byte) SIZEOF_STRUCT_PERSON
Successful SSA optimization Pass2ConstantRValueConsolidation
Constant (const byte[$10]*) main::$2 = (byte[$10]*)persons#0+OFFSET_STRUCT_PERSON_NAME
Constant (const byte[$10]*) main::$3 = (byte[$10]*)persons#0+OFFSET_STRUCT_PERSON_NAME
Constant (const byte*) main::$6 = (byte*)persons#0
Constant (const byte*) main::$7 = (byte*)persons#0
Constant (const byte[$d]) main::$8 = (byte[$d])persons#0
Constant (const byte[$d]) main::$10 = (byte[$d])persons#0+main::$3
Constant (const word*) main::$12 = (word*)persons#0+OFFSET_STRUCT_PERSON_AGE
Constant (const word*) main::$13 = (word*)persons#0+OFFSET_STRUCT_PERSON_AGE
Constant (const byte[$d]) main::$14 = (byte[$d])main::person#0+OFFSET_STRUCT_PERSON_NAME
Constant (const struct Person*) main::person#1 = main::person#0+SIZEOF_STRUCT_PERSON
Successful SSA optimization Pass2ConstantIdentification
Constant value identified (byte[$10]*)main::person#1 in [6] *((const byte*) main::SCREEN#0 + (byte) 1) ← *(*((byte[$10]*)(const struct Person*) main::person#1 + (const byte) OFFSET_STRUCT_PERSON_NAME))
Constant value identified (byte[$d])main::person#1 in [17] (byte[$d]) main::$15 ← (byte[$d])(const struct Person*) main::person#1 + (const byte) OFFSET_STRUCT_PERSON_NAME
Successful SSA optimization Pass2ConstantValues
Constant right-side identified [2] (byte[$d]) main::$9 ← (const byte[$d]) main::$8 + (const byte) OFFSET_STRUCT_PERSON_NAME
Constant right-side identified [4] (byte[$d]) main::$11 ← (const byte[$d]) main::$10 + (const byte) OFFSET_STRUCT_PERSON_NAME
Constant right-side identified [9] (byte[$d]) main::$15 ← (byte[$d])(const struct Person*) main::person#1 + (const byte) OFFSET_STRUCT_PERSON_NAME
Successful SSA optimization Pass2ConstantRValueConsolidation
Constant (const byte[$d]) main::$9 = main::$8+OFFSET_STRUCT_PERSON_NAME
Constant (const byte[$d]) main::$11 = main::$10+OFFSET_STRUCT_PERSON_NAME
Constant (const byte[$d]) main::$15 = (byte[$d])main::person#1+OFFSET_STRUCT_PERSON_NAME
Successful SSA optimization Pass2ConstantIdentification
Inlining constant with different constant siblings (const struct Person*) main::person#0
Constant inlined main::$3 = (byte[$10]*)(const struct Person[2]) persons#0+(const byte) OFFSET_STRUCT_PERSON_NAME
Constant inlined main::$12 = (word*)(const struct Person[2]) persons#0+(const byte) OFFSET_STRUCT_PERSON_AGE
Constant inlined main::$13 = (word*)(const struct Person[2]) persons#0+(const byte) OFFSET_STRUCT_PERSON_AGE
Constant inlined main::$14 = (byte[$d])(const struct Person[2]) persons#0+(const byte) OFFSET_STRUCT_PERSON_NAME
Constant inlined main::$15 = (byte[$d])(const struct Person*) main::person#1+(const byte) OFFSET_STRUCT_PERSON_NAME
Constant inlined main::$10 = (byte[$d])(const struct Person[2]) persons#0+(byte) 1*(const byte) SIZEOF_STRUCT_PERSON
Constant inlined main::$11 = (byte[$d])(const struct Person[2]) persons#0+(byte) 1*(const byte) SIZEOF_STRUCT_PERSON+(const byte) OFFSET_STRUCT_PERSON_NAME
Constant inlined main::$1 = (byte) 1*(const byte) SIZEOF_STRUCT_PERSON
Constant inlined main::$2 = (byte[$10]*)(const struct Person[2]) persons#0+(const byte) OFFSET_STRUCT_PERSON_NAME
Constant inlined main::$5 = (byte) 1*(const byte) SIZEOF_STRUCT_PERSON
Constant inlined main::$6 = (byte*)(const struct Person[2]) persons#0
Constant inlined main::$3 = (byte) 1*(const byte) SIZEOF_STRUCT_PERSON
Constant inlined main::$9 = (byte[$d])(const struct Person[2]) persons#0+(const byte) OFFSET_STRUCT_PERSON_NAME
Constant inlined main::$7 = (byte*)(const struct Person[2]) persons#0
Constant inlined main::person#0 = (const struct Person[2]) persons#0
Constant inlined main::$8 = (byte[$d])(const struct Person[2]) persons#0
Successful SSA optimization Pass2ConstantInlining
Consolidated array index constant in *((byte[$10]*)persons#0+OFFSET_STRUCT_PERSON_NAME+1*SIZEOF_STRUCT_PERSON)
Consolidated array index constant in *((byte[$10]*)persons#0+OFFSET_STRUCT_PERSON_NAME)
Consolidated array index constant in *((byte[$10]*)main::person#1+OFFSET_STRUCT_PERSON_NAME)
Consolidated array index constant in *((byte*)persons#0+1*SIZEOF_STRUCT_PERSON)
Consolidated array index constant in *((byte[$d])persons#0+OFFSET_STRUCT_PERSON_NAME+8)
Consolidated array index constant in *((byte[$d])persons#0+1*SIZEOF_STRUCT_PERSON+OFFSET_STRUCT_PERSON_NAME+8)
Consolidated array index constant in *((word*)persons#0+OFFSET_STRUCT_PERSON_AGE+1*SIZEOF_STRUCT_PERSON)
Consolidated array index constant in *((byte[$d])persons#0+OFFSET_STRUCT_PERSON_NAME+8)
Consolidated array index constant in *((byte[$d])main::person#1+OFFSET_STRUCT_PERSON_NAME+8)
Consolidated array index constant in *(main::SCREEN#0+1)
Successful SSA optimization Pass2ConstantAdditionElimination
Adding NOP phi() at start of @begin
@ -171,19 +284,24 @@ FINAL CONTROL FLOW GRAPH
@end: scope:[] from @1
[3] phi()
main: scope:[main] from @1
[4] *(*((byte[$10]*)(const struct Person[2]) persons#0+(const byte) OFFSET_STRUCT_PERSON_NAME)) ← (byte) 'a'
[5] *(*((byte[$10]*)(const struct Person[2]) persons#0+(const byte) OFFSET_STRUCT_PERSON_NAME+(byte) 1*(const byte) SIZEOF_STRUCT_PERSON)) ← (byte) 'b'
[6] *((const byte*) main::SCREEN#0) ← *(*((byte[$10]*)(const struct Person[2]) persons#0+(const byte) OFFSET_STRUCT_PERSON_NAME))
[7] *((const byte*) main::SCREEN#0+(byte) 1) ← *(*((byte[$10]*)(const struct Person*) main::person#1+(const byte) OFFSET_STRUCT_PERSON_NAME))
[4] *((byte*)(const struct Person[2]) persons#0) ← (byte) 7
[5] *((byte*)(const struct Person[2]) persons#0+(byte) 1*(const byte) SIZEOF_STRUCT_PERSON) ← (byte) 9
[6] *((byte[$d])(const struct Person[2]) persons#0+(const byte) OFFSET_STRUCT_PERSON_NAME+(byte) 8) ← (byte) 'a'
[7] *((byte[$d])(const struct Person[2]) persons#0+(byte) 1*(const byte) SIZEOF_STRUCT_PERSON+(const byte) OFFSET_STRUCT_PERSON_NAME+(byte) 8) ← (byte) 'b'
[8] *((word*)(const struct Person[2]) persons#0+(const byte) OFFSET_STRUCT_PERSON_AGE) ← (word) $141
[9] *((word*)(const struct Person[2]) persons#0+(const byte) OFFSET_STRUCT_PERSON_AGE+(byte) 1*(const byte) SIZEOF_STRUCT_PERSON) ← (byte) $7b
[10] *((const byte*) main::SCREEN#0) ← *((byte[$d])(const struct Person[2]) persons#0+(const byte) OFFSET_STRUCT_PERSON_NAME+(byte) 8)
[11] *((const byte*) main::SCREEN#0+(byte) 1) ← *((byte[$d])(const struct Person*) main::person#1+(const byte) OFFSET_STRUCT_PERSON_NAME+(byte) 8)
to:main::@return
main::@return: scope:[main] from main
[8] return
[12] return
to:@return
VARIABLE REGISTER WEIGHTS
(word) Person::age
(byte) Person::id
(byte[$10]) Person::name
(byte[$d]) Person::name
(void()) main()
(byte*) main::SCREEN
(struct Person*) main::person
@ -196,15 +314,15 @@ INITIAL ASM
Target platform is c64basic / MOS6502X
// File Comments
// Example of a struct containing an array
// Fails (by displaying "BB" ) because the memory layout is wrong - and the name is treated like a pointer (to 0x0000) instead of a value.
// https://gitlab.com/camelot/kickc/issues/312
// Upstart
.pc = $801 "Basic"
:BasicUpstart(bbegin)
.pc = $80d "Program"
// Global Constants & labels
.const SIZEOF_STRUCT_PERSON = 3
.const SIZEOF_STRUCT_PERSON = $10
.const OFFSET_STRUCT_PERSON_NAME = 1
.const OFFSET_STRUCT_PERSON_AGE = $e
// @begin
bbegin:
// [1] phi from @begin to @1 [phi:@begin->@1]
@ -223,74 +341,74 @@ bend:
main: {
.label SCREEN = $400
.label person = persons+SIZEOF_STRUCT_PERSON
// [4] *(*((byte[$10]*)(const struct Person[2]) persons#0+(const byte) OFFSET_STRUCT_PERSON_NAME)) ← (byte) 'a' -- _deref_(_deref_pptc1)=vbuc2
// [4] *((byte*)(const struct Person[2]) persons#0) ← (byte) 7 -- _deref_pbuc1=vbuc2
lda #7
sta persons
// [5] *((byte*)(const struct Person[2]) persons#0+(byte) 1*(const byte) SIZEOF_STRUCT_PERSON) ← (byte) 9 -- _deref_pbuc1=vbuc2
lda #9
sta persons+1*SIZEOF_STRUCT_PERSON
// [6] *((byte[$d])(const struct Person[2]) persons#0+(const byte) OFFSET_STRUCT_PERSON_NAME+(byte) 8) ← (byte) 'a' -- _deref_pbuc1=vbuc2
lda #'a'
ldy persons+OFFSET_STRUCT_PERSON_NAME
sty.z $fe
ldy persons+OFFSET_STRUCT_PERSON_NAME+1
sty.z $ff
ldy #0
sta ($fe),y
// [5] *(*((byte[$10]*)(const struct Person[2]) persons#0+(const byte) OFFSET_STRUCT_PERSON_NAME+(byte) 1*(const byte) SIZEOF_STRUCT_PERSON)) ← (byte) 'b' -- _deref_(_deref_pptc1)=vbuc2
sta persons+OFFSET_STRUCT_PERSON_NAME+8
// [7] *((byte[$d])(const struct Person[2]) persons#0+(byte) 1*(const byte) SIZEOF_STRUCT_PERSON+(const byte) OFFSET_STRUCT_PERSON_NAME+(byte) 8) ← (byte) 'b' -- _deref_pbuc1=vbuc2
lda #'b'
ldy persons+OFFSET_STRUCT_PERSON_NAME+1*SIZEOF_STRUCT_PERSON
sty.z $fe
ldy persons+OFFSET_STRUCT_PERSON_NAME+1*SIZEOF_STRUCT_PERSON+1
sty.z $ff
ldy #0
sta ($fe),y
// [6] *((const byte*) main::SCREEN#0) ← *(*((byte[$10]*)(const struct Person[2]) persons#0+(const byte) OFFSET_STRUCT_PERSON_NAME)) -- _deref_pbuc1=_deref_(_deref_pptc2)
ldy persons+OFFSET_STRUCT_PERSON_NAME
sty.z $fe
ldy persons+OFFSET_STRUCT_PERSON_NAME+1
sty.z $ff
ldy #0
lda ($fe),y
sta persons+1*SIZEOF_STRUCT_PERSON+OFFSET_STRUCT_PERSON_NAME+8
// [8] *((word*)(const struct Person[2]) persons#0+(const byte) OFFSET_STRUCT_PERSON_AGE) ← (word) $141 -- _deref_pwuc1=vwuc2
lda #<$141
sta persons+OFFSET_STRUCT_PERSON_AGE
lda #>$141
sta persons+OFFSET_STRUCT_PERSON_AGE+1
// [9] *((word*)(const struct Person[2]) persons#0+(const byte) OFFSET_STRUCT_PERSON_AGE+(byte) 1*(const byte) SIZEOF_STRUCT_PERSON) ← (byte) $7b -- _deref_pwuc1=vbuc2
lda #0
sta persons+OFFSET_STRUCT_PERSON_AGE+1*SIZEOF_STRUCT_PERSON+1
lda #<$7b
sta persons+OFFSET_STRUCT_PERSON_AGE+1*SIZEOF_STRUCT_PERSON
// [10] *((const byte*) main::SCREEN#0) ← *((byte[$d])(const struct Person[2]) persons#0+(const byte) OFFSET_STRUCT_PERSON_NAME+(byte) 8) -- _deref_pbuc1=_deref_pbuc2
lda persons+OFFSET_STRUCT_PERSON_NAME+8
sta SCREEN
// [7] *((const byte*) main::SCREEN#0+(byte) 1) ← *(*((byte[$10]*)(const struct Person*) main::person#1+(const byte) OFFSET_STRUCT_PERSON_NAME)) -- _deref_pbuc1=_deref_(_deref_pptc2)
ldy person+OFFSET_STRUCT_PERSON_NAME
sty.z $fe
ldy person+OFFSET_STRUCT_PERSON_NAME+1
sty.z $ff
ldy #0
lda ($fe),y
// [11] *((const byte*) main::SCREEN#0+(byte) 1) ← *((byte[$d])(const struct Person*) main::person#1+(const byte) OFFSET_STRUCT_PERSON_NAME+(byte) 8) -- _deref_pbuc1=_deref_pbuc2
lda person+OFFSET_STRUCT_PERSON_NAME+8
sta SCREEN+1
jmp breturn
// main::@return
breturn:
// [8] return
// [12] return
rts
}
// File Data
persons: .fill 3*2, 0
persons: .fill $10*2, 0
REGISTER UPLIFT POTENTIAL REGISTERS
Statement [4] *(*((byte[$10]*)(const struct Person[2]) persons#0+(const byte) OFFSET_STRUCT_PERSON_NAME)) ← (byte) 'a' [ ] ( main:2 [ ] ) always clobbers reg byte a reg byte y
Statement [5] *(*((byte[$10]*)(const struct Person[2]) persons#0+(const byte) OFFSET_STRUCT_PERSON_NAME+(byte) 1*(const byte) SIZEOF_STRUCT_PERSON)) ← (byte) 'b' [ ] ( main:2 [ ] ) always clobbers reg byte a reg byte y
Statement [6] *((const byte*) main::SCREEN#0) ← *(*((byte[$10]*)(const struct Person[2]) persons#0+(const byte) OFFSET_STRUCT_PERSON_NAME)) [ ] ( main:2 [ ] ) always clobbers reg byte a reg byte y
Statement [7] *((const byte*) main::SCREEN#0+(byte) 1) ← *(*((byte[$10]*)(const struct Person*) main::person#1+(const byte) OFFSET_STRUCT_PERSON_NAME)) [ ] ( main:2 [ ] ) always clobbers reg byte a reg byte y
Statement [4] *((byte*)(const struct Person[2]) persons#0) ← (byte) 7 [ ] ( main:2 [ ] ) always clobbers reg byte a
Statement [5] *((byte*)(const struct Person[2]) persons#0+(byte) 1*(const byte) SIZEOF_STRUCT_PERSON) ← (byte) 9 [ ] ( main:2 [ ] ) always clobbers reg byte a
Statement [6] *((byte[$d])(const struct Person[2]) persons#0+(const byte) OFFSET_STRUCT_PERSON_NAME+(byte) 8) ← (byte) 'a' [ ] ( main:2 [ ] ) always clobbers reg byte a
Statement [7] *((byte[$d])(const struct Person[2]) persons#0+(byte) 1*(const byte) SIZEOF_STRUCT_PERSON+(const byte) OFFSET_STRUCT_PERSON_NAME+(byte) 8) ← (byte) 'b' [ ] ( main:2 [ ] ) always clobbers reg byte a
Statement [8] *((word*)(const struct Person[2]) persons#0+(const byte) OFFSET_STRUCT_PERSON_AGE) ← (word) $141 [ ] ( main:2 [ ] ) always clobbers reg byte a
Statement [9] *((word*)(const struct Person[2]) persons#0+(const byte) OFFSET_STRUCT_PERSON_AGE+(byte) 1*(const byte) SIZEOF_STRUCT_PERSON) ← (byte) $7b [ ] ( main:2 [ ] ) always clobbers reg byte a
Statement [10] *((const byte*) main::SCREEN#0) ← *((byte[$d])(const struct Person[2]) persons#0+(const byte) OFFSET_STRUCT_PERSON_NAME+(byte) 8) [ ] ( main:2 [ ] ) always clobbers reg byte a
Statement [11] *((const byte*) main::SCREEN#0+(byte) 1) ← *((byte[$d])(const struct Person*) main::person#1+(const byte) OFFSET_STRUCT_PERSON_NAME+(byte) 8) [ ] ( main:2 [ ] ) always clobbers reg byte a
REGISTER UPLIFT SCOPES
Uplift Scope [Person]
Uplift Scope [main]
Uplift Scope []
Uplifting [Person] best 119 combination
Uplifting [main] best 119 combination
Uplifting [] best 119 combination
Uplifting [Person] best 85 combination
Uplifting [main] best 85 combination
Uplifting [] best 85 combination
ASSEMBLER BEFORE OPTIMIZATION
// File Comments
// Example of a struct containing an array
// Fails (by displaying "BB" ) because the memory layout is wrong - and the name is treated like a pointer (to 0x0000) instead of a value.
// https://gitlab.com/camelot/kickc/issues/312
// Upstart
.pc = $801 "Basic"
:BasicUpstart(bbegin)
.pc = $80d "Program"
// Global Constants & labels
.const SIZEOF_STRUCT_PERSON = 3
.const SIZEOF_STRUCT_PERSON = $10
.const OFFSET_STRUCT_PERSON_NAME = 1
.const OFFSET_STRUCT_PERSON_AGE = $e
// @begin
bbegin:
// [1] phi from @begin to @1 [phi:@begin->@1]
@ -309,46 +427,42 @@ bend:
main: {
.label SCREEN = $400
.label person = persons+SIZEOF_STRUCT_PERSON
// [4] *(*((byte[$10]*)(const struct Person[2]) persons#0+(const byte) OFFSET_STRUCT_PERSON_NAME)) ← (byte) 'a' -- _deref_(_deref_pptc1)=vbuc2
// [4] *((byte*)(const struct Person[2]) persons#0) ← (byte) 7 -- _deref_pbuc1=vbuc2
lda #7
sta persons
// [5] *((byte*)(const struct Person[2]) persons#0+(byte) 1*(const byte) SIZEOF_STRUCT_PERSON) ← (byte) 9 -- _deref_pbuc1=vbuc2
lda #9
sta persons+1*SIZEOF_STRUCT_PERSON
// [6] *((byte[$d])(const struct Person[2]) persons#0+(const byte) OFFSET_STRUCT_PERSON_NAME+(byte) 8) ← (byte) 'a' -- _deref_pbuc1=vbuc2
lda #'a'
ldy persons+OFFSET_STRUCT_PERSON_NAME
sty.z $fe
ldy persons+OFFSET_STRUCT_PERSON_NAME+1
sty.z $ff
ldy #0
sta ($fe),y
// [5] *(*((byte[$10]*)(const struct Person[2]) persons#0+(const byte) OFFSET_STRUCT_PERSON_NAME+(byte) 1*(const byte) SIZEOF_STRUCT_PERSON)) ← (byte) 'b' -- _deref_(_deref_pptc1)=vbuc2
sta persons+OFFSET_STRUCT_PERSON_NAME+8
// [7] *((byte[$d])(const struct Person[2]) persons#0+(byte) 1*(const byte) SIZEOF_STRUCT_PERSON+(const byte) OFFSET_STRUCT_PERSON_NAME+(byte) 8) ← (byte) 'b' -- _deref_pbuc1=vbuc2
lda #'b'
ldy persons+OFFSET_STRUCT_PERSON_NAME+1*SIZEOF_STRUCT_PERSON
sty.z $fe
ldy persons+OFFSET_STRUCT_PERSON_NAME+1*SIZEOF_STRUCT_PERSON+1
sty.z $ff
ldy #0
sta ($fe),y
// [6] *((const byte*) main::SCREEN#0) ← *(*((byte[$10]*)(const struct Person[2]) persons#0+(const byte) OFFSET_STRUCT_PERSON_NAME)) -- _deref_pbuc1=_deref_(_deref_pptc2)
ldy persons+OFFSET_STRUCT_PERSON_NAME
sty.z $fe
ldy persons+OFFSET_STRUCT_PERSON_NAME+1
sty.z $ff
ldy #0
lda ($fe),y
sta persons+1*SIZEOF_STRUCT_PERSON+OFFSET_STRUCT_PERSON_NAME+8
// [8] *((word*)(const struct Person[2]) persons#0+(const byte) OFFSET_STRUCT_PERSON_AGE) ← (word) $141 -- _deref_pwuc1=vwuc2
lda #<$141
sta persons+OFFSET_STRUCT_PERSON_AGE
lda #>$141
sta persons+OFFSET_STRUCT_PERSON_AGE+1
// [9] *((word*)(const struct Person[2]) persons#0+(const byte) OFFSET_STRUCT_PERSON_AGE+(byte) 1*(const byte) SIZEOF_STRUCT_PERSON) ← (byte) $7b -- _deref_pwuc1=vbuc2
lda #0
sta persons+OFFSET_STRUCT_PERSON_AGE+1*SIZEOF_STRUCT_PERSON+1
lda #<$7b
sta persons+OFFSET_STRUCT_PERSON_AGE+1*SIZEOF_STRUCT_PERSON
// [10] *((const byte*) main::SCREEN#0) ← *((byte[$d])(const struct Person[2]) persons#0+(const byte) OFFSET_STRUCT_PERSON_NAME+(byte) 8) -- _deref_pbuc1=_deref_pbuc2
lda persons+OFFSET_STRUCT_PERSON_NAME+8
sta SCREEN
// [7] *((const byte*) main::SCREEN#0+(byte) 1) ← *(*((byte[$10]*)(const struct Person*) main::person#1+(const byte) OFFSET_STRUCT_PERSON_NAME)) -- _deref_pbuc1=_deref_(_deref_pptc2)
ldy person+OFFSET_STRUCT_PERSON_NAME
sty.z $fe
ldy person+OFFSET_STRUCT_PERSON_NAME+1
sty.z $ff
ldy #0
lda ($fe),y
// [11] *((const byte*) main::SCREEN#0+(byte) 1) ← *((byte[$d])(const struct Person*) main::person#1+(const byte) OFFSET_STRUCT_PERSON_NAME+(byte) 8) -- _deref_pbuc1=_deref_pbuc2
lda person+OFFSET_STRUCT_PERSON_NAME+8
sta SCREEN+1
jmp breturn
// main::@return
breturn:
// [8] return
// [12] return
rts
}
// File Data
persons: .fill 3*2, 0
persons: .fill $10*2, 0
ASSEMBLER OPTIMIZATIONS
Removing instruction jmp b1
@ -372,10 +486,12 @@ FINAL SYMBOL TABLE
(label) @1
(label) @begin
(label) @end
(const byte) OFFSET_STRUCT_PERSON_AGE OFFSET_STRUCT_PERSON_AGE = (byte) $e
(const byte) OFFSET_STRUCT_PERSON_NAME OFFSET_STRUCT_PERSON_NAME = (byte) 1
(word) Person::age
(byte) Person::id
(byte[$10]) Person::name
(const byte) SIZEOF_STRUCT_PERSON SIZEOF_STRUCT_PERSON = (byte) 3
(byte[$d]) Person::name
(const byte) SIZEOF_STRUCT_PERSON SIZEOF_STRUCT_PERSON = (byte) $10
(void()) main()
(label) main::@return
(byte*) main::SCREEN
@ -388,19 +504,19 @@ FINAL SYMBOL TABLE
FINAL ASSEMBLER
Score: 104
Score: 70
// File Comments
// Example of a struct containing an array
// Fails (by displaying "BB" ) because the memory layout is wrong - and the name is treated like a pointer (to 0x0000) instead of a value.
// https://gitlab.com/camelot/kickc/issues/312
// Upstart
.pc = $801 "Basic"
:BasicUpstart(main)
.pc = $80d "Program"
// Global Constants & labels
.const SIZEOF_STRUCT_PERSON = 3
.const SIZEOF_STRUCT_PERSON = $10
.const OFFSET_STRUCT_PERSON_NAME = 1
.const OFFSET_STRUCT_PERSON_AGE = $e
// @begin
// [1] phi from @begin to @1 [phi:@begin->@1]
// @1
@ -411,47 +527,47 @@ Score: 104
main: {
.label SCREEN = $400
.label person = persons+SIZEOF_STRUCT_PERSON
// persons[0].name[0] = 'a'
// [4] *(*((byte[$10]*)(const struct Person[2]) persons#0+(const byte) OFFSET_STRUCT_PERSON_NAME)) ← (byte) 'a' -- _deref_(_deref_pptc1)=vbuc2
// persons[0].id = 7
// [4] *((byte*)(const struct Person[2]) persons#0) ← (byte) 7 -- _deref_pbuc1=vbuc2
lda #7
sta persons
// persons[1].id = 9
// [5] *((byte*)(const struct Person[2]) persons#0+(byte) 1*(const byte) SIZEOF_STRUCT_PERSON) ← (byte) 9 -- _deref_pbuc1=vbuc2
lda #9
sta persons+1*SIZEOF_STRUCT_PERSON
// persons[0].name[8] = 'a'
// [6] *((byte[$d])(const struct Person[2]) persons#0+(const byte) OFFSET_STRUCT_PERSON_NAME+(byte) 8) ← (byte) 'a' -- _deref_pbuc1=vbuc2
lda #'a'
ldy persons+OFFSET_STRUCT_PERSON_NAME
sty.z $fe
ldy persons+OFFSET_STRUCT_PERSON_NAME+1
sty.z $ff
ldy #0
sta ($fe),y
// persons[1].name[0] = 'b'
// [5] *(*((byte[$10]*)(const struct Person[2]) persons#0+(const byte) OFFSET_STRUCT_PERSON_NAME+(byte) 1*(const byte) SIZEOF_STRUCT_PERSON)) ← (byte) 'b' -- _deref_(_deref_pptc1)=vbuc2
sta persons+OFFSET_STRUCT_PERSON_NAME+8
// persons[1].name[8] = 'b'
// [7] *((byte[$d])(const struct Person[2]) persons#0+(byte) 1*(const byte) SIZEOF_STRUCT_PERSON+(const byte) OFFSET_STRUCT_PERSON_NAME+(byte) 8) ← (byte) 'b' -- _deref_pbuc1=vbuc2
lda #'b'
ldy persons+OFFSET_STRUCT_PERSON_NAME+1*SIZEOF_STRUCT_PERSON
sty.z $fe
ldy persons+OFFSET_STRUCT_PERSON_NAME+1*SIZEOF_STRUCT_PERSON+1
sty.z $ff
ldy #0
sta ($fe),y
// SCREEN[0] = person->name[0]
// [6] *((const byte*) main::SCREEN#0) ← *(*((byte[$10]*)(const struct Person[2]) persons#0+(const byte) OFFSET_STRUCT_PERSON_NAME)) -- _deref_pbuc1=_deref_(_deref_pptc2)
ldy persons+OFFSET_STRUCT_PERSON_NAME
sty.z $fe
ldy persons+OFFSET_STRUCT_PERSON_NAME+1
sty.z $ff
ldy #0
lda ($fe),y
sta persons+1*SIZEOF_STRUCT_PERSON+OFFSET_STRUCT_PERSON_NAME+8
// persons[0].age = 321
// [8] *((word*)(const struct Person[2]) persons#0+(const byte) OFFSET_STRUCT_PERSON_AGE) ← (word) $141 -- _deref_pwuc1=vwuc2
lda #<$141
sta persons+OFFSET_STRUCT_PERSON_AGE
lda #>$141
sta persons+OFFSET_STRUCT_PERSON_AGE+1
// persons[1].age = 123
// [9] *((word*)(const struct Person[2]) persons#0+(const byte) OFFSET_STRUCT_PERSON_AGE+(byte) 1*(const byte) SIZEOF_STRUCT_PERSON) ← (byte) $7b -- _deref_pwuc1=vbuc2
lda #0
sta persons+OFFSET_STRUCT_PERSON_AGE+1*SIZEOF_STRUCT_PERSON+1
lda #<$7b
sta persons+OFFSET_STRUCT_PERSON_AGE+1*SIZEOF_STRUCT_PERSON
// SCREEN[0] = person->name[8]
// [10] *((const byte*) main::SCREEN#0) ← *((byte[$d])(const struct Person[2]) persons#0+(const byte) OFFSET_STRUCT_PERSON_NAME+(byte) 8) -- _deref_pbuc1=_deref_pbuc2
lda persons+OFFSET_STRUCT_PERSON_NAME+8
sta SCREEN
// SCREEN[1] = person->name[0]
// [7] *((const byte*) main::SCREEN#0+(byte) 1) ← *(*((byte[$10]*)(const struct Person*) main::person#1+(const byte) OFFSET_STRUCT_PERSON_NAME)) -- _deref_pbuc1=_deref_(_deref_pptc2)
ldy person+OFFSET_STRUCT_PERSON_NAME
sty.z $fe
ldy person+OFFSET_STRUCT_PERSON_NAME+1
sty.z $ff
ldy #0
lda ($fe),y
// SCREEN[1] = person->name[8]
// [11] *((const byte*) main::SCREEN#0+(byte) 1) ← *((byte[$d])(const struct Person*) main::person#1+(const byte) OFFSET_STRUCT_PERSON_NAME+(byte) 8) -- _deref_pbuc1=_deref_pbuc2
lda person+OFFSET_STRUCT_PERSON_NAME+8
sta SCREEN+1
// main::@return
// }
// [8] return
// [12] return
rts
}
// File Data
persons: .fill 3*2, 0
persons: .fill $10*2, 0

View File

@ -1,10 +1,12 @@
(label) @1
(label) @begin
(label) @end
(const byte) OFFSET_STRUCT_PERSON_AGE OFFSET_STRUCT_PERSON_AGE = (byte) $e
(const byte) OFFSET_STRUCT_PERSON_NAME OFFSET_STRUCT_PERSON_NAME = (byte) 1
(word) Person::age
(byte) Person::id
(byte[$10]) Person::name
(const byte) SIZEOF_STRUCT_PERSON SIZEOF_STRUCT_PERSON = (byte) 3
(byte[$d]) Person::name
(const byte) SIZEOF_STRUCT_PERSON SIZEOF_STRUCT_PERSON = (byte) $10
(void()) main()
(label) main::@return
(byte*) main::SCREEN

View File

@ -128,45 +128,35 @@ compare: {
cpx #EQ
beq b5
cpx #NE
bne b10
bne b8
lda.z w1
cmp.z w2
bne !+
lda.z w1+1
cmp.z w2+1
beq b9
beq b7
!:
lda #TT
sta.z r
jmp b23
b9:
jmp b19
b7:
lda #FF
sta.z r
b23:
b19:
lda #<ops_1
sta.z ops
lda #>ops_1
sta.z ops+1
jmp b6
b10:
b8:
lda #FF
sta.z r
lda #<0
sta.z ops
sta.z ops+1
b6:
lda.z w1+1
bmi b7
lda #' '
jsr print_char
b7:
jsr print_sword
jsr print_str
lda.z w2+1
bmi b8
lda #' '
jsr print_char
b8:
lda.z w2
sta.z print_sword.w
lda.z w2+1
@ -178,40 +168,39 @@ compare: {
b5:
lda.z w1+1
cmp.z w2+1
bne b11
bne b9
lda.z w1
cmp.z w2
bne b11
bne b9
lda #TT
sta.z r
jmp b24
b11:
jmp b20
b9:
lda #FF
sta.z r
b24:
b20:
lda #<ops_2
sta.z ops
lda #>ops_2
sta.z ops+1
jmp b6
b4:
lda.z w2
cmp.z w1
lda.z w2+1
sbc.z w1+1
lda.z w1
cmp.z w2
lda.z w1+1
sbc.z w2+1
bvc !+
eor #$80
!:
beq !e+
bpl b12
bmi b10
!e:
lda #TT
sta.z r
jmp b25
b12:
jmp b21
b10:
lda #FF
sta.z r
b25:
b21:
lda #<ops_3
sta.z ops
lda #>ops_3
@ -225,37 +214,36 @@ compare: {
bvc !+
eor #$80
!:
bpl b13
bpl b11
lda #TT
sta.z r
jmp b26
b13:
jmp b22
b11:
lda #FF
sta.z r
b26:
b22:
lda #<ops_4
sta.z ops
lda #>ops_4
sta.z ops+1
jmp b6
b2:
lda.z w1
cmp.z w2
lda.z w1+1
sbc.z w2+1
lda.z w2
cmp.z w1
lda.z w2+1
sbc.z w1+1
bvc !+
eor #$80
!:
beq !e+
bpl b14
bmi b12
!e:
lda #TT
sta.z r
jmp b27
b14:
jmp b23
b12:
lda #FF
sta.z r
b27:
b23:
lda #<ops_5
sta.z ops
lda #>ops_5
@ -269,14 +257,14 @@ compare: {
bvc !+
eor #$80
!:
bpl b15
bpl b13
lda #TT
sta.z r
jmp b28
b15:
jmp b24
b13:
lda #FF
sta.z r
b28:
b24:
lda #<ops_6
sta.z ops
lda #>ops_6

View File

@ -14,7 +14,7 @@ main: scope:[main] from @1
main::@1: scope:[main] from main main::@7
[6] (byte*) print_line_cursor#31 ← phi( main/(byte*) 1024 main::@7/(byte*) print_line_cursor#23 )
[6] (byte) main::s#7 ← phi( main/(byte) 0 main::@7/(byte) main::s#10 )
[6] (byte*) print_char_cursor#83 ← phi( main/(byte*) 1024 main::@7/(byte*) print_char_cursor#79 )
[6] (byte*) print_char_cursor#82 ← phi( main/(byte*) 1024 main::@7/(byte*) print_char_cursor#72 )
[6] (byte) main::i#2 ← phi( main/(byte) 0 main::@7/(byte) main::i#1 )
[7] (byte~) main::$8 ← (byte) main::i#2 << (byte) 1
[8] (signed word) main::w1#0 ← *((const signed word[]) swords#0 + (byte~) main::$8)
@ -22,7 +22,7 @@ main::@1: scope:[main] from main main::@7
main::@2: scope:[main] from main::@1 main::@6
[9] (byte*) print_line_cursor#29 ← phi( main::@1/(byte*) print_line_cursor#31 main::@6/(byte*) print_line_cursor#23 )
[9] (byte) main::s#5 ← phi( main::@1/(byte) main::s#7 main::@6/(byte) main::s#10 )
[9] (byte*) print_char_cursor#78 ← phi( main::@1/(byte*) print_char_cursor#83 main::@6/(byte*) print_char_cursor#79 )
[9] (byte*) print_char_cursor#71 ← phi( main::@1/(byte*) print_char_cursor#82 main::@6/(byte*) print_char_cursor#72 )
[9] (byte) main::j#2 ← phi( main::@1/(byte) 0 main::@6/(byte) main::j#1 )
[10] (byte~) main::$9 ← (byte) main::j#2 << (byte) 1
[11] (signed word) main::w2#0 ← *((const signed word[]) swords#0 + (byte~) main::$9)
@ -30,7 +30,7 @@ main::@2: scope:[main] from main::@1 main::@6
main::@3: scope:[main] from main::@2 main::@4
[12] (byte*) print_line_cursor#19 ← phi( main::@2/(byte*) print_line_cursor#29 main::@4/(byte*) print_line_cursor#23 )
[12] (byte) main::s#3 ← phi( main::@2/(byte) main::s#5 main::@4/(byte) main::s#10 )
[12] (byte*) print_char_cursor#70 ← phi( main::@2/(byte*) print_char_cursor#78 main::@4/(byte*) print_char_cursor#79 )
[12] (byte*) print_char_cursor#64 ← phi( main::@2/(byte*) print_char_cursor#71 main::@4/(byte*) print_char_cursor#72 )
[12] (byte) main::op#2 ← phi( main::@2/(byte) 0 main::@4/(byte) main::op#1 )
[13] (signed word) compare::w1#0 ← (signed word) main::w1#0
[14] (signed word) compare::w2#0 ← (signed word) main::w2#0
@ -46,12 +46,12 @@ main::@5: scope:[main] from main::@9
[20] call print_ln
to:main::@10
main::@10: scope:[main] from main::@5
[21] (byte*~) print_char_cursor#128 ← (byte*) print_line_cursor#1
[21] (byte*~) print_char_cursor#118 ← (byte*) print_line_cursor#1
to:main::@4
main::@4: scope:[main] from main::@10 main::@9
[22] (byte*) print_line_cursor#23 ← phi( main::@9/(byte*) print_line_cursor#19 main::@10/(byte*) print_line_cursor#1 )
[22] (byte) main::s#10 ← phi( main::@9/(byte) main::s#1 main::@10/(byte) 0 )
[22] (byte*) print_char_cursor#79 ← phi( main::@9/(byte*) print_char_cursor#15 main::@10/(byte*~) print_char_cursor#128 )
[22] (byte*) print_char_cursor#72 ← phi( main::@9/(byte*) print_char_cursor#15 main::@10/(byte*~) print_char_cursor#118 )
[23] (byte) main::op#1 ← ++ (byte) main::op#2
[24] if((byte) main::op#1!=(byte) 6) goto main::@3
to:main::@6
@ -79,205 +79,189 @@ print_ln::@return: scope:[print_ln] from print_ln::@1
to:@return
compare: scope:[compare] from main::@3
[35] if((byte) compare::op#0==(const byte) LT#0) goto compare::@1
to:compare::@9
compare::@9: scope:[compare] from compare
to:compare::@7
compare::@7: scope:[compare] from compare
[36] if((byte) compare::op#0==(const byte) LE#0) goto compare::@2
to:compare::@8
compare::@8: scope:[compare] from compare::@7
[37] if((byte) compare::op#0==(const byte) GT#0) goto compare::@3
to:compare::@9
compare::@9: scope:[compare] from compare::@8
[38] if((byte) compare::op#0==(const byte) GE#0) goto compare::@4
to:compare::@10
compare::@10: scope:[compare] from compare::@9
[37] if((byte) compare::op#0==(const byte) GT#0) goto compare::@3
[39] if((byte) compare::op#0==(const byte) EQ#0) goto compare::@5
to:compare::@11
compare::@11: scope:[compare] from compare::@10
[38] if((byte) compare::op#0==(const byte) GE#0) goto compare::@4
[40] if((byte) compare::op#0!=(const byte) NE#0) goto compare::@6
to:compare::@12
compare::@12: scope:[compare] from compare::@11
[39] if((byte) compare::op#0==(const byte) EQ#0) goto compare::@5
[41] if((signed word) compare::w1#0==(signed word) compare::w2#0) goto compare::@19
to:compare::@13
compare::@13: scope:[compare] from compare::@12
[40] if((byte) compare::op#0!=(const byte) NE#0) goto compare::@6
to:compare::@14
compare::@14: scope:[compare] from compare::@13
[41] if((signed word) compare::w1#0==(signed word) compare::w2#0) goto compare::@23
to:compare::@15
compare::@15: scope:[compare] from compare::@14
[42] phi()
to:compare::@23
compare::@23: scope:[compare] from compare::@14 compare::@15
[43] (byte) compare::r#17 ← phi( compare::@14/(const byte) FF#0 compare::@15/(const byte) TT#0 )
to:compare::@6
compare::@6: scope:[compare] from compare::@13 compare::@23 compare::@24 compare::@25 compare::@26 compare::@27 compare::@28
[44] (byte) compare::r#10 ← phi( compare::@13/(const byte) FF#0 compare::@23/(byte) compare::r#17 compare::@24/(byte) compare::r#18 compare::@25/(byte) compare::r#19 compare::@26/(byte) compare::r#20 compare::@27/(byte) compare::r#21 compare::@28/(byte) compare::r#22 )
[44] (byte*) compare::ops#10 ← phi( compare::@13/(byte*) 0 compare::@23/(const byte*) compare::ops#1 compare::@24/(const byte*) compare::ops#2 compare::@25/(const byte*) compare::ops#3 compare::@26/(const byte*) compare::ops#4 compare::@27/(const byte*) compare::ops#5 compare::@28/(const byte*) compare::ops#6 )
[45] if((signed word) compare::w1#0<(signed byte) 0) goto compare::@7
to:compare::@21
compare::@21: scope:[compare] from compare::@6
[46] phi()
[47] call print_char
to:compare::@7
compare::@7: scope:[compare] from compare::@21 compare::@6
[48] (byte*) print_char_cursor#73 ← phi( compare::@6/(byte*) print_char_cursor#70 compare::@21/(byte*) print_char_cursor#15 )
[49] (signed word) print_sword::w#1 ← (signed word) compare::w1#0
[50] call print_sword
to:compare::@29
compare::@29: scope:[compare] from compare::@7
[51] (byte*) print_str::str#1 ← (byte*) compare::ops#10
[52] call print_str
to:compare::@30
compare::@30: scope:[compare] from compare::@29
[53] if((signed word) compare::w2#0<(signed byte) 0) goto compare::@8
to:compare::@22
compare::@22: scope:[compare] from compare::@30
[54] phi()
[55] call print_char
to:compare::@8
compare::@8: scope:[compare] from compare::@22 compare::@30
[56] (byte*) print_char_cursor#74 ← phi( compare::@30/(byte*) print_char_cursor#2 compare::@22/(byte*) print_char_cursor#15 )
[57] (signed word) print_sword::w#2 ← (signed word) compare::w2#0
[58] call print_sword
to:compare::@31
compare::@31: scope:[compare] from compare::@8
[59] (byte) print_char::ch#5 ← (byte) compare::r#10
[60] call print_char
to:compare::@return
compare::@return: scope:[compare] from compare::@31
[61] return
to:@return
compare::@5: scope:[compare] from compare::@12
[62] if((signed word) compare::w1#0!=(signed word) compare::w2#0) goto compare::@24
to:compare::@16
compare::@16: scope:[compare] from compare::@5
[63] phi()
to:compare::@24
compare::@24: scope:[compare] from compare::@16 compare::@5
[64] (byte) compare::r#18 ← phi( compare::@16/(const byte) TT#0 compare::@5/(const byte) FF#0 )
to:compare::@6
compare::@4: scope:[compare] from compare::@11
[65] if((signed word) compare::w1#0<(signed word) compare::w2#0) goto compare::@25
to:compare::@17
compare::@17: scope:[compare] from compare::@4
[66] phi()
to:compare::@25
compare::@25: scope:[compare] from compare::@17 compare::@4
[67] (byte) compare::r#19 ← phi( compare::@17/(const byte) TT#0 compare::@4/(const byte) FF#0 )
to:compare::@6
compare::@3: scope:[compare] from compare::@10
[68] if((signed word) compare::w1#0<=(signed word) compare::w2#0) goto compare::@26
to:compare::@18
compare::@18: scope:[compare] from compare::@3
[69] phi()
to:compare::@26
compare::@26: scope:[compare] from compare::@18 compare::@3
[70] (byte) compare::r#20 ← phi( compare::@18/(const byte) TT#0 compare::@3/(const byte) FF#0 )
to:compare::@6
compare::@2: scope:[compare] from compare::@9
[71] if((signed word) compare::w1#0>(signed word) compare::w2#0) goto compare::@27
to:compare::@19
compare::@19: scope:[compare] from compare::@2
[72] phi()
compare::@19: scope:[compare] from compare::@12 compare::@13
[43] (byte) compare::r#12 ← phi( compare::@12/(const byte) FF#0 compare::@13/(const byte) TT#0 )
to:compare::@6
compare::@6: scope:[compare] from compare::@11 compare::@19 compare::@20 compare::@21 compare::@22 compare::@23 compare::@24
[44] (byte) compare::r#10 ← phi( compare::@11/(const byte) FF#0 compare::@19/(byte) compare::r#12 compare::@20/(byte) compare::r#13 compare::@21/(byte) compare::r#14 compare::@22/(byte) compare::r#15 compare::@23/(byte) compare::r#16 compare::@24/(byte) compare::r#17 )
[44] (byte*) compare::ops#7 ← phi( compare::@11/(byte*) 0 compare::@19/(const byte*) compare::ops#1 compare::@20/(const byte*) compare::ops#2 compare::@21/(const byte*) compare::ops#3 compare::@22/(const byte*) compare::ops#4 compare::@23/(const byte*) compare::ops#5 compare::@24/(const byte*) compare::ops#6 )
[45] (signed word) print_sword::w#1 ← (signed word) compare::w1#0
[46] call print_sword
to:compare::@25
compare::@25: scope:[compare] from compare::@6
[47] (byte*) print_str::str#1 ← (byte*) compare::ops#7
[48] call print_str
to:compare::@26
compare::@26: scope:[compare] from compare::@25
[49] (signed word) print_sword::w#2 ← (signed word) compare::w2#0
[50] call print_sword
to:compare::@27
compare::@27: scope:[compare] from compare::@19 compare::@2
[73] (byte) compare::r#21 ← phi( compare::@2/(const byte) FF#0 compare::@19/(const byte) TT#0 )
compare::@27: scope:[compare] from compare::@26
[51] (byte) print_char::ch#4 ← (byte) compare::r#10
[52] call print_char
to:compare::@return
compare::@return: scope:[compare] from compare::@27
[53] return
to:@return
compare::@5: scope:[compare] from compare::@10
[54] if((signed word) compare::w1#0!=(signed word) compare::w2#0) goto compare::@20
to:compare::@14
compare::@14: scope:[compare] from compare::@5
[55] phi()
to:compare::@20
compare::@20: scope:[compare] from compare::@14 compare::@5
[56] (byte) compare::r#13 ← phi( compare::@14/(const byte) TT#0 compare::@5/(const byte) FF#0 )
to:compare::@6
compare::@4: scope:[compare] from compare::@9
[57] if((signed word) compare::w1#0<(signed word) compare::w2#0) goto compare::@21
to:compare::@15
compare::@15: scope:[compare] from compare::@4
[58] phi()
to:compare::@21
compare::@21: scope:[compare] from compare::@15 compare::@4
[59] (byte) compare::r#14 ← phi( compare::@15/(const byte) TT#0 compare::@4/(const byte) FF#0 )
to:compare::@6
compare::@3: scope:[compare] from compare::@8
[60] if((signed word) compare::w1#0<=(signed word) compare::w2#0) goto compare::@22
to:compare::@16
compare::@16: scope:[compare] from compare::@3
[61] phi()
to:compare::@22
compare::@22: scope:[compare] from compare::@16 compare::@3
[62] (byte) compare::r#15 ← phi( compare::@16/(const byte) TT#0 compare::@3/(const byte) FF#0 )
to:compare::@6
compare::@2: scope:[compare] from compare::@7
[63] if((signed word) compare::w1#0>(signed word) compare::w2#0) goto compare::@23
to:compare::@17
compare::@17: scope:[compare] from compare::@2
[64] phi()
to:compare::@23
compare::@23: scope:[compare] from compare::@17 compare::@2
[65] (byte) compare::r#16 ← phi( compare::@2/(const byte) FF#0 compare::@17/(const byte) TT#0 )
to:compare::@6
compare::@1: scope:[compare] from compare
[74] if((signed word) compare::w1#0>=(signed word) compare::w2#0) goto compare::@28
to:compare::@20
compare::@20: scope:[compare] from compare::@1
[75] phi()
to:compare::@28
compare::@28: scope:[compare] from compare::@1 compare::@20
[76] (byte) compare::r#22 ← phi( compare::@1/(const byte) FF#0 compare::@20/(const byte) TT#0 )
[66] if((signed word) compare::w1#0>=(signed word) compare::w2#0) goto compare::@24
to:compare::@18
compare::@18: scope:[compare] from compare::@1
[67] phi()
to:compare::@24
compare::@24: scope:[compare] from compare::@1 compare::@18
[68] (byte) compare::r#17 ← phi( compare::@1/(const byte) FF#0 compare::@18/(const byte) TT#0 )
to:compare::@6
print_char: scope:[print_char] from compare::@21 compare::@22 compare::@31 print_byte print_byte::@1 print_sword::@1 print_sword::@3
[77] (byte*) print_char_cursor#45 ← phi( compare::@21/(byte*) print_char_cursor#70 compare::@22/(byte*) print_char_cursor#2 compare::@31/(byte*) print_char_cursor#15 print_byte/(byte*) print_char_cursor#15 print_byte::@1/(byte*) print_char_cursor#15 print_sword::@1/(byte*) print_char_cursor#62 print_sword::@3/(byte*) print_char_cursor#62 )
[77] (byte) print_char::ch#7 ← phi( compare::@21/(byte) ' ' compare::@22/(byte) ' ' compare::@31/(byte) print_char::ch#5 print_byte/(byte) print_char::ch#2 print_byte::@1/(byte) print_char::ch#3 print_sword::@1/(byte) '-' print_sword::@3/(byte) ' ' )
[78] *((byte*) print_char_cursor#45) ← (byte) print_char::ch#7
[79] (byte*) print_char_cursor#15 ← ++ (byte*) print_char_cursor#45
print_char: scope:[print_char] from compare::@27 print_byte print_byte::@1 print_sword::@1 print_sword::@3
[69] (byte*) print_char_cursor#43 ← phi( compare::@27/(byte*) print_char_cursor#15 print_byte/(byte*) print_char_cursor#15 print_byte::@1/(byte*) print_char_cursor#15 print_sword::@1/(byte*) print_char_cursor#58 print_sword::@3/(byte*) print_char_cursor#58 )
[69] (byte) print_char::ch#5 ← phi( compare::@27/(byte) print_char::ch#4 print_byte/(byte) print_char::ch#2 print_byte::@1/(byte) print_char::ch#3 print_sword::@1/(byte) '-' print_sword::@3/(byte) ' ' )
[70] *((byte*) print_char_cursor#43) ← (byte) print_char::ch#5
[71] (byte*) print_char_cursor#15 ← ++ (byte*) print_char_cursor#43
to:print_char::@return
print_char::@return: scope:[print_char] from print_char
[80] return
[72] return
to:@return
print_sword: scope:[print_sword] from compare::@7 compare::@8
[81] (byte*) print_char_cursor#62 ← phi( compare::@7/(byte*) print_char_cursor#73 compare::@8/(byte*) print_char_cursor#74 )
[81] (signed word) print_sword::w#3 ← phi( compare::@7/(signed word) print_sword::w#1 compare::@8/(signed word) print_sword::w#2 )
[82] if((signed word) print_sword::w#3<(signed byte) 0) goto print_sword::@1
print_sword: scope:[print_sword] from compare::@26 compare::@6
[73] (byte*) print_char_cursor#58 ← phi( compare::@6/(byte*) print_char_cursor#64 compare::@26/(byte*) print_char_cursor#2 )
[73] (signed word) print_sword::w#3 ← phi( compare::@6/(signed word) print_sword::w#1 compare::@26/(signed word) print_sword::w#2 )
[74] if((signed word) print_sword::w#3<(signed byte) 0) goto print_sword::@1
to:print_sword::@3
print_sword::@3: scope:[print_sword] from print_sword
[83] phi()
[84] call print_char
[75] phi()
[76] call print_char
to:print_sword::@2
print_sword::@2: scope:[print_sword] from print_sword::@3 print_sword::@4
[85] (signed word) print_sword::w#5 ← phi( print_sword::@4/(signed word) print_sword::w#0 print_sword::@3/(signed word) print_sword::w#3 )
[86] (word) print_word::w#0 ← (word)(signed word) print_sword::w#5
[87] call print_word
[77] (signed word) print_sword::w#5 ← phi( print_sword::@4/(signed word) print_sword::w#0 print_sword::@3/(signed word) print_sword::w#3 )
[78] (word) print_word::w#0 ← (word)(signed word) print_sword::w#5
[79] call print_word
to:print_sword::@return
print_sword::@return: scope:[print_sword] from print_sword::@2
[88] return
[80] return
to:@return
print_sword::@1: scope:[print_sword] from print_sword
[89] phi()
[90] call print_char
[81] phi()
[82] call print_char
to:print_sword::@4
print_sword::@4: scope:[print_sword] from print_sword::@1
[91] (signed word) print_sword::w#0 ← - (signed word) print_sword::w#3
[83] (signed word) print_sword::w#0 ← - (signed word) print_sword::w#3
to:print_sword::@2
print_word: scope:[print_word] from print_sword::@2
[92] (byte) print_byte::b#0 ← > (word) print_word::w#0
[93] call print_byte
[84] (byte) print_byte::b#0 ← > (word) print_word::w#0
[85] call print_byte
to:print_word::@1
print_word::@1: scope:[print_word] from print_word
[94] (byte) print_byte::b#1 ← < (word) print_word::w#0
[95] call print_byte
[86] (byte) print_byte::b#1 ← < (word) print_word::w#0
[87] call print_byte
to:print_word::@return
print_word::@return: scope:[print_word] from print_word::@1
[96] return
[88] return
to:@return
print_byte: scope:[print_byte] from print_word print_word::@1
[97] (byte) print_byte::b#2 ← phi( print_word/(byte) print_byte::b#0 print_word::@1/(byte) print_byte::b#1 )
[98] (byte~) print_byte::$0 ← (byte) print_byte::b#2 >> (byte) 4
[99] (byte) print_char::ch#2 ← *((const byte[]) print_hextab#0 + (byte~) print_byte::$0)
[100] call print_char
[89] (byte) print_byte::b#2 ← phi( print_word/(byte) print_byte::b#0 print_word::@1/(byte) print_byte::b#1 )
[90] (byte~) print_byte::$0 ← (byte) print_byte::b#2 >> (byte) 4
[91] (byte) print_char::ch#2 ← *((const byte[]) print_hextab#0 + (byte~) print_byte::$0)
[92] call print_char
to:print_byte::@1
print_byte::@1: scope:[print_byte] from print_byte
[101] (byte~) print_byte::$2 ← (byte) print_byte::b#2 & (byte) $f
[102] (byte) print_char::ch#3 ← *((const byte[]) print_hextab#0 + (byte~) print_byte::$2)
[103] call print_char
[93] (byte~) print_byte::$2 ← (byte) print_byte::b#2 & (byte) $f
[94] (byte) print_char::ch#3 ← *((const byte[]) print_hextab#0 + (byte~) print_byte::$2)
[95] call print_char
to:print_byte::@return
print_byte::@return: scope:[print_byte] from print_byte::@1
[104] return
[96] return
to:@return
print_str: scope:[print_str] from compare::@29
[105] phi()
print_str: scope:[print_str] from compare::@25
[97] phi()
to:print_str::@1
print_str::@1: scope:[print_str] from print_str print_str::@2
[106] (byte*) print_char_cursor#2 ← phi( print_str/(byte*) print_char_cursor#15 print_str::@2/(byte*) print_char_cursor#1 )
[106] (byte*) print_str::str#2 ← phi( print_str/(byte*) print_str::str#1 print_str::@2/(byte*) print_str::str#0 )
[107] if((byte) 0!=*((byte*) print_str::str#2)) goto print_str::@2
[98] (byte*) print_char_cursor#2 ← phi( print_str/(byte*) print_char_cursor#15 print_str::@2/(byte*) print_char_cursor#1 )
[98] (byte*) print_str::str#2 ← phi( print_str/(byte*) print_str::str#1 print_str::@2/(byte*) print_str::str#0 )
[99] if((byte) 0!=*((byte*) print_str::str#2)) goto print_str::@2
to:print_str::@return
print_str::@return: scope:[print_str] from print_str::@1
[108] return
[100] return
to:@return
print_str::@2: scope:[print_str] from print_str::@1
[109] *((byte*) print_char_cursor#2) ← *((byte*) print_str::str#2)
[110] (byte*) print_char_cursor#1 ← ++ (byte*) print_char_cursor#2
[111] (byte*) print_str::str#0 ← ++ (byte*) print_str::str#2
[101] *((byte*) print_char_cursor#2) ← *((byte*) print_str::str#2)
[102] (byte*) print_char_cursor#1 ← ++ (byte*) print_char_cursor#2
[103] (byte*) print_str::str#0 ← ++ (byte*) print_str::str#2
to:print_str::@1
print_cls: scope:[print_cls] from main
[112] phi()
[113] call memset
[104] phi()
[105] call memset
to:print_cls::@return
print_cls::@return: scope:[print_cls] from print_cls
[114] return
[106] return
to:@return
memset: scope:[memset] from print_cls
[115] phi()
[107] phi()
to:memset::@1
memset::@1: scope:[memset] from memset memset::@2
[116] (byte*) memset::dst#2 ← phi( memset/(byte*)(const void*) memset::str#0 memset::@2/(byte*) memset::dst#1 )
[117] if((byte*) memset::dst#2!=(const byte*) memset::end#0) goto memset::@2
[108] (byte*) memset::dst#2 ← phi( memset/(byte*)(const void*) memset::str#0 memset::@2/(byte*) memset::dst#1 )
[109] if((byte*) memset::dst#2!=(const byte*) memset::end#0) goto memset::@2
to:memset::@return
memset::@return: scope:[memset] from memset::@1
[118] return
[110] return
to:@return
memset::@2: scope:[memset] from memset::@1
[119] *((byte*) memset::dst#2) ← (const byte) memset::c#0
[120] (byte*) memset::dst#1 ← ++ (byte*) memset::dst#2
[111] *((byte*) memset::dst#2) ← (const byte) memset::c#0
[112] (byte*) memset::dst#1 ← ++ (byte*) memset::dst#2
to:memset::@1

File diff suppressed because it is too large Load Diff

View File

@ -42,11 +42,7 @@
(label) compare::@25
(label) compare::@26
(label) compare::@27
(label) compare::@28
(label) compare::@29
(label) compare::@3
(label) compare::@30
(label) compare::@31
(label) compare::@4
(label) compare::@5
(label) compare::@6
@ -58,24 +54,24 @@
(byte) compare::op#0 reg byte x 168.8333333333334
(byte*) compare::ops
(const byte*) compare::ops#1 ops#1 = (string) "!="
(byte*) compare::ops#10 ops zp ZP_WORD:5 0.2857142857142857
(const byte*) compare::ops#2 ops#2 = (string) "=="
(const byte*) compare::ops#3 ops#3 = (string) ">="
(const byte*) compare::ops#4 ops#4 = (string) "> "
(const byte*) compare::ops#5 ops#5 = (string) "<="
(const byte*) compare::ops#6 ops#6 = (string) "< "
(byte*) compare::ops#7 ops zp ZP_WORD:5 0.6666666666666666
(byte) compare::r
(byte) compare::r#10 r zp ZP_BYTE:7 0.9333333333333332
(byte) compare::r#10 r zp ZP_BYTE:7 1.9999999999999996
(byte) compare::r#12 r zp ZP_BYTE:7 2.0
(byte) compare::r#13 r zp ZP_BYTE:7 2.0
(byte) compare::r#14 r zp ZP_BYTE:7 2.0
(byte) compare::r#15 r zp ZP_BYTE:7 2.0
(byte) compare::r#16 r zp ZP_BYTE:7 2.0
(byte) compare::r#17 r zp ZP_BYTE:7 2.0
(byte) compare::r#18 r zp ZP_BYTE:7 2.0
(byte) compare::r#19 r zp ZP_BYTE:7 2.0
(byte) compare::r#20 r zp ZP_BYTE:7 2.0
(byte) compare::r#21 r zp ZP_BYTE:7 2.0
(byte) compare::r#22 r zp ZP_BYTE:7 2.0
(signed word) compare::w1
(signed word) compare::w1#0 w1 zp ZP_WORD:10 31.78125
(signed word) compare::w1#0 w1 zp ZP_WORD:10 36.249999999999986
(signed word) compare::w2
(signed word) compare::w2#0 w2 zp ZP_WORD:17 26.076923076923077
(signed word) compare::w2#0 w2 zp ZP_WORD:17 32.741935483870954
(void()) main()
(byte~) main::$8 reg byte a 22.0
(byte~) main::$9 reg byte a 202.0
@ -138,21 +134,19 @@
(byte) print_char::ch
(byte) print_char::ch#2 reg byte a 4.0
(byte) print_char::ch#3 reg byte a 4.0
(byte) print_char::ch#5 reg byte a 4.0
(byte) print_char::ch#7 reg byte a 8.0
(byte) print_char::ch#4 reg byte a 4.0
(byte) print_char::ch#5 reg byte a 8.0
(byte*) print_char_cursor
(byte*) print_char_cursor#1 print_char_cursor zp ZP_WORD:8 10001.0
(byte*~) print_char_cursor#128 print_char_cursor zp ZP_WORD:8 2002.0
(byte*) print_char_cursor#15 print_char_cursor zp ZP_WORD:8 282.46153846153845
(byte*) print_char_cursor#2 print_char_cursor zp ZP_WORD:8 4287.0
(byte*) print_char_cursor#45 print_char_cursor zp ZP_WORD:8 9.0
(byte*) print_char_cursor#62 print_char_cursor zp ZP_WORD:8 2.0
(byte*) print_char_cursor#70 print_char_cursor zp ZP_WORD:8 35.677419354838705
(byte*) print_char_cursor#73 print_char_cursor zp ZP_WORD:8 3.0
(byte*) print_char_cursor#74 print_char_cursor zp ZP_WORD:8 3.0
(byte*) print_char_cursor#78 print_char_cursor zp ZP_WORD:8 71.0
(byte*) print_char_cursor#79 print_char_cursor zp ZP_WORD:8 445.0
(byte*) print_char_cursor#83 print_char_cursor zp ZP_WORD:8 7.333333333333333
(byte*~) print_char_cursor#118 print_char_cursor zp ZP_WORD:8 2002.0
(byte*) print_char_cursor#15 print_char_cursor zp ZP_WORD:8 297.62162162162167
(byte*) print_char_cursor#2 print_char_cursor zp ZP_WORD:8 5001.166666666666
(byte*) print_char_cursor#43 print_char_cursor zp ZP_WORD:8 7.0
(byte*) print_char_cursor#58 print_char_cursor zp ZP_WORD:8 2.0
(byte*) print_char_cursor#64 print_char_cursor zp ZP_WORD:8 36.800000000000004
(byte*) print_char_cursor#71 print_char_cursor zp ZP_WORD:8 71.0
(byte*) print_char_cursor#72 print_char_cursor zp ZP_WORD:8 445.0
(byte*) print_char_cursor#82 print_char_cursor zp ZP_WORD:8 7.333333333333333
(void()) print_cls()
(label) print_cls::@return
(byte[]) print_hextab
@ -200,10 +194,10 @@ zp ZP_BYTE:2 [ main::i#2 main::i#1 ]
zp ZP_BYTE:3 [ main::j#2 main::j#1 ]
reg byte x [ main::op#2 main::op#1 ]
zp ZP_BYTE:4 [ main::s#3 main::s#5 main::s#7 main::s#10 main::s#1 ]
zp ZP_WORD:5 [ compare::ops#10 print_str::str#2 print_str::str#1 print_str::str#0 ]
zp ZP_BYTE:7 [ compare::r#10 compare::r#17 compare::r#18 compare::r#19 compare::r#20 compare::r#21 compare::r#22 ]
reg byte a [ print_char::ch#7 print_char::ch#5 print_char::ch#2 print_char::ch#3 ]
zp ZP_WORD:8 [ print_char_cursor#45 print_char_cursor#74 print_char_cursor#2 print_char_cursor#73 print_char_cursor#70 print_char_cursor#78 print_char_cursor#83 print_char_cursor#79 print_char_cursor#15 print_char_cursor#128 print_char_cursor#62 print_char_cursor#1 ]
zp ZP_WORD:5 [ compare::ops#7 print_str::str#2 print_str::str#1 print_str::str#0 ]
zp ZP_BYTE:7 [ compare::r#10 compare::r#12 compare::r#13 compare::r#14 compare::r#15 compare::r#16 compare::r#17 ]
reg byte a [ print_char::ch#5 print_char::ch#4 print_char::ch#2 print_char::ch#3 ]
zp ZP_WORD:8 [ print_char_cursor#43 print_char_cursor#64 print_char_cursor#71 print_char_cursor#82 print_char_cursor#72 print_char_cursor#15 print_char_cursor#118 print_char_cursor#58 print_char_cursor#2 print_char_cursor#1 ]
zp ZP_WORD:10 [ print_sword::w#5 print_sword::w#0 print_sword::w#3 print_sword::w#1 print_sword::w#2 compare::w1#0 print_word::w#0 ]
zp ZP_BYTE:12 [ print_byte::b#2 print_byte::b#0 print_byte::b#1 ]
zp ZP_WORD:13 [ memset::dst#2 memset::dst#1 print_line_cursor#9 print_line_cursor#19 print_line_cursor#29 print_line_cursor#31 print_line_cursor#23 print_line_cursor#1 ]