1
0
mirror of https://gitlab.com/camelot/kickc.git synced 2025-08-08 13:25:12 +00:00

Added support for snprintf(). Closes #698

This commit is contained in:
jespergravgaard
2021-08-13 20:06:59 +02:00
parent 72471bbcd0
commit ea760e4731
43 changed files with 19483 additions and 9176 deletions

View File

@@ -1168,6 +1168,18 @@ stz {c1}
lda {c1} lda {c1}
inc inc
sta {z1} sta {z1}
//FRAGMENT vbuz1=_stackidxbyte_vbuc1
tsx
lda STACK_BASE+{c1},x
sta {z1}
//FRAGMENT pbuz1_derefidx_vbuz2=vbuz3
lda {z3}
ldz {z2}
sta ({z1}),z
//FRAGMENT pbuz1_derefidx_vbuz2=vbuc1
lda #{c1}
ldz {z2}
sta ({z1}),z
//FRAGMENT vwuz1=_word_vbuz2 //FRAGMENT vwuz1=_word_vbuz2
lda {z2} lda {z2}
sta {z1} sta {z1}
@@ -1216,17 +1228,6 @@ lda {z2}
sta {z1} sta {z1}
lda {z2}+1 lda {z2}+1
sta {z1}+1 sta {z1}+1
//FRAGMENT 0_neq_vbuz1_then_la1
lda {z1}
bne {la1}
//FRAGMENT pbuz1_derefidx_vbuz2=vbuz3
lda {z3}
ldz {z2}
sta ({z1}),z
//FRAGMENT pbuz1_derefidx_vbuz2=vbuc1
lda #{c1}
ldz {z2}
sta ({z1}),z
//FRAGMENT pbuz1=pbuz1_plus_vbuc1 //FRAGMENT pbuz1=pbuz1_plus_vbuc1
lda #{c1} lda #{c1}
clc clc
@@ -1235,6 +1236,16 @@ sta {z1}
bcc !+ bcc !+
inc {z1}+1 inc {z1}+1
!: !:
//FRAGMENT 0_neq_vbuz1_then_la1
lda {z1}
bne {la1}
//FRAGMENT _stackpushbyte_=vbuz1
lda {z1}
pha
//FRAGMENT call_vprc1
jsr {c1}
//FRAGMENT _stackpullbyte_1
pla
//FRAGMENT pvoz1=pvoc1 //FRAGMENT pvoz1=pvoc1
lda #<{c1} lda #<{c1}
sta {z1} sta {z1}
@@ -1286,6 +1297,36 @@ inc
//FRAGMENT vbuxx=_deref_pbuc1_plus_1 //FRAGMENT vbuxx=_deref_pbuc1_plus_1
ldx {c1} ldx {c1}
inx inx
//FRAGMENT vbuaa=_stackidxbyte_vbuc1
tsx
lda STACK_BASE+{c1},x
//FRAGMENT vbuxx=_stackidxbyte_vbuc1
tsx
lda STACK_BASE+{c1},x
tax
//FRAGMENT vbuyy=_stackidxbyte_vbuc1
tsx
lda STACK_BASE+{c1},x
tay
//FRAGMENT vbuzz=_stackidxbyte_vbuc1
tsx
lda STACK_BASE+{c1},x
taz
//FRAGMENT pbuz1_derefidx_vbuz2=vbuaa
ldz {z2}
sta ({z1}),z
//FRAGMENT pbuz1_derefidx_vbuz2=vbuxx
txa
ldz {z2}
sta ({z1}),z
//FRAGMENT pbuz1_derefidx_vbuz2=vbuyy
tya
ldz {z2}
sta ({z1}),z
//FRAGMENT pbuz1_derefidx_vbuz2=vbuzz
tza
ldz {z2}
sta ({z1}),z
//FRAGMENT vbuz1=vbuxx //FRAGMENT vbuz1=vbuxx
stx {z1} stx {z1}
//FRAGMENT vwuz1=_word_vbuxx //FRAGMENT vwuz1=_word_vbuxx
@@ -1306,23 +1347,8 @@ sta {z1}+1
//FRAGMENT 0_neq_vbuaa_then_la1 //FRAGMENT 0_neq_vbuaa_then_la1
cmp #0 cmp #0
bne {la1} bne {la1}
//FRAGMENT vbuz1=vbuaa //FRAGMENT _stackpushbyte_=vbuaa
sta {z1} pha
//FRAGMENT pbuz1_derefidx_vbuz2=vbuaa
ldz {z2}
sta ({z1}),z
//FRAGMENT pbuz1_derefidx_vbuz2=vbuxx
txa
ldz {z2}
sta ({z1}),z
//FRAGMENT pbuz1_derefidx_vbuz2=vbuyy
tya
ldz {z2}
sta ({z1}),z
//FRAGMENT pbuz1_derefidx_vbuz2=vbuzz
tza
ldz {z2}
sta ({z1}),z
//FRAGMENT _deref_pbuz1=vbuxx //FRAGMENT _deref_pbuz1=vbuxx
txa txa
ldy #0 ldy #0
@@ -1338,18 +1364,21 @@ sta ({z1}),y
//FRAGMENT 0_neq_vbuxx_then_la1 //FRAGMENT 0_neq_vbuxx_then_la1
cpx #0 cpx #0
bne {la1} bne {la1}
//FRAGMENT vbuaa=vbuxx //FRAGMENT _stackpushbyte_=vbuxx
txa txa
pha
//FRAGMENT 0_neq_vbuyy_then_la1 //FRAGMENT 0_neq_vbuyy_then_la1
cpy #0 cpy #0
bne {la1} bne {la1}
//FRAGMENT vbuaa=vbuyy //FRAGMENT _stackpushbyte_=vbuyy
tya tya
pha
//FRAGMENT 0_neq_vbuzz_then_la1 //FRAGMENT 0_neq_vbuzz_then_la1
cpz #0 cpz #0
bne {la1} bne {la1}
//FRAGMENT vbuaa=vbuzz //FRAGMENT _stackpushbyte_=vbuzz
tza tza
pha
//FRAGMENT vbuz1=vbuyy //FRAGMENT vbuz1=vbuyy
sty {z1} sty {z1}
//FRAGMENT vbuz1=vbuzz //FRAGMENT vbuz1=vbuzz
@@ -2363,6 +2392,8 @@ taz
lda {z1}+1 lda {z1}+1
//FRAGMENT vbuxx=_byte1_vduz1 //FRAGMENT vbuxx=_byte1_vduz1
ldx {z1}+1 ldx {z1}+1
//FRAGMENT vbuz1=vbuaa
sta {z1}
//FRAGMENT vbuyy=_byte1_vduz1 //FRAGMENT vbuyy=_byte1_vduz1
ldy {z1}+1 ldy {z1}+1
//FRAGMENT vbuzz=_byte1_vduz1 //FRAGMENT vbuzz=_byte1_vduz1
@@ -2457,40 +2488,3 @@ sta {z1}+3
NO_SYNTHESIS NO_SYNTHESIS
//FRAGMENT vduz1=vwsc1 //FRAGMENT vduz1=vwsc1
NO_SYNTHESIS NO_SYNTHESIS
//FRAGMENT vbuz1=_stackidxbyte_vbuc1
tsx
lda STACK_BASE+{c1},x
sta {z1}
//FRAGMENT _stackpushbyte_=vbuz1
lda {z1}
pha
//FRAGMENT call_vprc1
jsr {c1}
//FRAGMENT _stackpullbyte_1
pla
//FRAGMENT vbuaa=_stackidxbyte_vbuc1
tsx
lda STACK_BASE+{c1},x
//FRAGMENT vbuxx=_stackidxbyte_vbuc1
tsx
lda STACK_BASE+{c1},x
tax
//FRAGMENT vbuyy=_stackidxbyte_vbuc1
tsx
lda STACK_BASE+{c1},x
tay
//FRAGMENT vbuzz=_stackidxbyte_vbuc1
tsx
lda STACK_BASE+{c1},x
taz
//FRAGMENT _stackpushbyte_=vbuaa
pha
//FRAGMENT _stackpushbyte_=vbuxx
txa
pha
//FRAGMENT _stackpushbyte_=vbuyy
tya
pha
//FRAGMENT _stackpushbyte_=vbuzz
tza
pha

File diff suppressed because it is too large Load Diff

View File

@@ -1,8 +1,8 @@
lda {m1}+1 lda {m2}+1
cmp {m2}+1 cmp {m1}+1
bne !+ bcc !+
lda {m1} bne {la1}
cmp {m2} lda {m2}
beq {la1} cmp {m1}
bcs {la1}
!: !:
bcc {la1}

View File

@@ -45,6 +45,7 @@ public class Procedure extends Scope {
/** The names of all legal intrinsic procedures. */ /** The names of all legal intrinsic procedures. */
final public static List<String> INTRINSIC_PROCEDURES = Arrays.asList( final public static List<String> INTRINSIC_PROCEDURES = Arrays.asList(
Pass1PrintfIntrinsicRewrite.INTRINSIC_PRINTF_NAME, Pass1PrintfIntrinsicRewrite.INTRINSIC_PRINTF_NAME,
Pass1PrintfIntrinsicRewrite.INTRINSIC_SNPRINTF_NAME,
Pass1ByteXIntrinsicRewrite.INTRINSIC_MAKELONG4 Pass1ByteXIntrinsicRewrite.INTRINSIC_MAKELONG4
); );

View File

@@ -10,7 +10,6 @@ import dk.camelot64.kickc.model.symbols.Procedure;
import dk.camelot64.kickc.model.symbols.Symbol; import dk.camelot64.kickc.model.symbols.Symbol;
import dk.camelot64.kickc.model.types.SymbolType; import dk.camelot64.kickc.model.types.SymbolType;
import dk.camelot64.kickc.model.types.SymbolTypeInference; import dk.camelot64.kickc.model.types.SymbolTypeInference;
import dk.camelot64.kickc.model.types.SymbolTypeProcedure;
import dk.camelot64.kickc.model.values.*; import dk.camelot64.kickc.model.values.*;
import java.util.Arrays; import java.util.Arrays;
@@ -27,9 +26,17 @@ public class Pass1PrintfIntrinsicRewrite extends Pass2SsaOptimization {
/** The printf procedure name. */ /** The printf procedure name. */
public static final String INTRINSIC_PRINTF_NAME = "printf"; public static final String INTRINSIC_PRINTF_NAME = "printf";
/** The printf procedure name. */
public static final String INTRINSIC_SNPRINTF_NAME = "snprintf";
/** The printf routine used to print a raw char */ /** The printf routine used to print a raw char */
private static final String CPUTC = "cputc"; private static final String CPUTC = "cputc";
/** The snprintf routine used to print a raw char */
private static final String SNPUTC = "snputc";
/** The printf routine used to print a raw string */
private static final String SNPRINTF_INIT = "snprintf_init";
/** The printf routine used to print a raw string */ /** The printf routine used to print a raw string */
private static final String PRINTF_STR = "printf_str"; private static final String PRINTF_STR = "printf_str";
/** The printf routine used to print formatted strings. */ /** The printf routine used to print formatted strings. */
@@ -61,205 +68,229 @@ public class Pass1PrintfIntrinsicRewrite extends Pass2SsaOptimization {
@Override @Override
public boolean step() { public boolean step() {
for(ControlFlowBlock block : getGraph().getAllBlocks()) { for(ControlFlowBlock block : getGraph().getAllBlocks()) {
final ListIterator<Statement> stmtIt = block.getStatements().listIterator(); final ListIterator<Statement> stmtIt = block.getStatements().listIterator();
while(stmtIt.hasNext()) { while(stmtIt.hasNext()) {
Statement statement = stmtIt.next(); Statement statement = stmtIt.next();
if(statement instanceof StatementCall && ((StatementCall) statement).getProcedureName().equals(INTRINSIC_PRINTF_NAME)) { if(statement instanceof StatementCall) {
StatementCall printfCall = (StatementCall) statement; if(((StatementCall) statement).getProcedureName().equals(INTRINSIC_PRINTF_NAME)) {
final List<RValue> parameters = printfCall.getParameters(); StatementCall call = (StatementCall) statement;
final RValue formatParameter = getParameterValue(parameters, 0, printfCall); stmtIt.remove();
if(!(formatParameter instanceof ConstantValue)) List<RValue> callParameters = call.getParameters();
throw new CompileError("Only constant printf() format parameter supported!", statement); final RValue format = getParameterValue(callParameters, 0, call);
final ConstantLiteral formatLiteral = ((ConstantValue) formatParameter).calculateLiteral(getProgram().getScope()); List<RValue> formatParameters = callParameters.subList(1, callParameters.size());
if(!(formatLiteral instanceof ConstantString)) addPrintfFormatStatements(stmtIt, call, format, formatParameters, CPUTC);
throw new CompileError("printf() format parameter must be a string!", statement); } else if(((StatementCall) statement).getProcedureName().equals(INTRINSIC_SNPRINTF_NAME)) {
final String formatString = ((ConstantString) formatLiteral).getString(); StatementCall call = (StatementCall) statement;
final StringEncoding formatEncoding = ((ConstantString) formatLiteral).getEncoding(); stmtIt.remove();
List<RValue> callParameters = call.getParameters();
Symbol cputcSymbol = getScope().getGlobalSymbol(CPUTC); final RValue buffer = getParameterValue(callParameters, 0, call);
ConstantValue CPUTC_REF; final RValue capacity = getParameterValue(callParameters, 1, call);
if(cputcSymbol!=null) final RValue format = getParameterValue(callParameters, 2, call);
CPUTC_REF = new ConstantSymbolPointer(cputcSymbol.getRef()); List<RValue> formatParameters = callParameters.subList(3, callParameters.size());
else addPrintfCall(SNPRINTF_INIT, Arrays.asList(buffer, capacity), stmtIt, call);
CPUTC_REF = new ConstantPointer(0L, new SymbolTypeProcedure(SymbolType.VOID, Arrays.asList(SymbolType.BYTE))); addPrintfFormatStatements(stmtIt, call, format, formatParameters, SNPUTC);
addPrintfCall(SNPUTC, Arrays.asList(new ConstantInteger(0L, SymbolType.BYTE)), stmtIt, call);
// Remove the call to printf()
stmtIt.remove();
// Printf Placeholder Format String - source: https://en.wikipedia.org/wiki/Printf_format_string
// "%" start
// ([1-9][0-9]* "$")? parameter (gives the # of the parameter to use)
// [-+ 0'#]* flags (different flags affecting the formatting "-": left-align, "0": zero-prepend, "+": always sign)
// [1-9][0-9]* width (the minimum number of characters)
// ("hh" | "l" )? length (specifies the type of integer "hh": char "": int, "l": long)
// [%diuxXoscp] type (specifies the type of the parameter/output "d"/"i" decimal signed, "u": decimal unsigned, "x": hexadecimal unsigned (lowercase), "X": hexadecimal unsigned (uppercase), "o": octal unsigned, "s": string, "c": character, "p": pointer, "%": output "%" )
Pattern pattern = Pattern.compile("%([1-9][0-9]*[$])?([-+0#]*)([1-9][0-9]*)?(hh|l)?([%diuxXoscp])");
final Matcher matcher = pattern.matcher(formatString);
// The index for the format field within the string
int formatIdx = 0;
// The index of the parameter being used as value for formatting. Incremented automatically unless field parameter index syntax (eg. %2$d) is used.
int paramIdx = 1;
// True if field parameter index syntax (eg. %2$d) is used.
boolean fieldParamIdx = false;
while(true) {
// Find the next pattern match!
boolean found = matcher.find();
if(!found) {
// No more matching patterns
break;
}
final int start = matcher.start();
final int end = matcher.end();
final String typeField = matcher.group(5);
final String paramField = matcher.group(1);
// Ensure that all fields use parameter index syntax!
if(paramField == null && fieldParamIdx && !typeField.equals("%"))
throw new CompileError("If any single printf() placeholder specifies a parameter, all the rest of the placeholders must also specify a parameter!", statement);
if(paramField != null) {
if(!fieldParamIdx && paramIdx > 1)
throw new CompileError("If any single printf() placeholder specifies a parameter, all the rest of the placeholders must also specify a parameter!", statement);
fieldParamIdx = true;
paramIdx = Integer.parseInt(paramField.substring(0, paramField.length() - 1));
}
final String flagsField = matcher.group(2);
long leftJustify = (flagsField != null && flagsField.contains("-")) ? 1 : 0;
long signAlways = (flagsField != null && flagsField.contains("+")) ? 1 : 0;
long zeroPadding = (flagsField != null && flagsField.contains("0")) ? 1 : 0;
final String widthField = matcher.group(3);
long width = (widthField == null) ? 0 : Integer.parseInt(widthField);
final String lengthField = matcher.group(4);
long upperCase = 0L;
// First output the non-matching part before the pattern
String prefix = formatString.substring(formatIdx, start);
if(prefix.length() > 0) {
addPrintfCall(PRINTF_STR, Arrays.asList(CPUTC_REF, new ConstantString(prefix, formatEncoding, true)), stmtIt, printfCall);
}
formatIdx = end;
if(typeField.equals("%")) {
addPrintfCall(CPUTC, Arrays.asList(new ConstantChar('%', formatEncoding)), stmtIt, printfCall);
} else if(typeField.equals("s")) {
// A formatted string
//struct printf_format_string {
// char min_length; // The minimal number of chars to output (used for padding with spaces or 0).
// char justify_left; // Justify left instead of right, which is the default.
//};
final ValueList format_string_struct =
new ValueList(Arrays.asList(
new ConstantInteger(width, SymbolType.BYTE),
new ConstantInteger(leftJustify, SymbolType.BYTE)
));
addPrintfCall(PRINTF_STRING, Arrays.asList(CPUTC_REF, getParameterValue(parameters, paramIdx, printfCall), format_string_struct), stmtIt, printfCall);
paramIdx++;
} else if("diuxXo".contains(typeField)) {
// A formatted integer
SymbolVariableRef radix;
String printf_number_procedure;
boolean signed;
switch(typeField) {
case "d":
case "i":
radix = getScope().getLocalConstant(DECIMAL).getRef();
signed = true;
break;
case "u":
radix = getScope().getLocalConstant(DECIMAL).getRef();
signed = false;
break;
case "x":
radix = getScope().getLocalConstant(HEXADECIMAL).getRef();
signed = false;
break;
case "X":
radix = getScope().getLocalConstant(HEXADECIMAL).getRef();
signed = false;
upperCase = 1l;
break;
case "o":
radix = getScope().getLocalConstant(OCTAL).getRef();
signed = false;
break;
default:
throw new CompileError("printf type field not supported", printfCall);
}
if(lengthField == null) {
// Check if the parameter type is 8-bit or 32-bit
RValue paramValue = getParameterValue(parameters, paramIdx, printfCall);
SymbolType paramType = SymbolTypeInference.inferType(getScope(), paramValue);
if(SymbolType.BYTE.equals(paramType) || SymbolType.SBYTE.equals(paramType)) {
// Integer (8bit)
printf_number_procedure = signed ? PRINTF_SCHAR : PRINTF_UCHAR;
} else if(SymbolType.DWORD.equals(paramType) || SymbolType.SDWORD.equals(paramType)) {
// Integer (32bit)
printf_number_procedure = signed ? PRINTF_SLONG : PRINTF_ULONG;
} else {
// Integer (16bit)
printf_number_procedure = signed ? PRINTF_SINT : PRINTF_UINT;
}
} else if(lengthField.equals("hh")) {
// Integer (8bit)
printf_number_procedure = signed ? PRINTF_SCHAR : PRINTF_UCHAR;
} else if(lengthField.equals("l")) {
// Integer (32bit)
printf_number_procedure = signed ? PRINTF_SLONG : PRINTF_ULONG;
} else {
throw new CompileError("printf length field not supported", printfCall);
}
// Format specifying how to format a printed number
// struct printf_format_number {
// char min_length; // The minimal number of chars to output (used for padding with spaces or 0)
// char justify_left; // Justify left instead of right, which is the default.
// char sign_always; // Always show a sign for a number, even if is is positive. (Default is to only show sign for negative numbers)
// char zero_padding; // Pad the number with zeros to get the min width
// char upper_case; // Upper-case the letters in the number
// enum RADIX radix; // The number radix to use for formatting
// };
final ValueList format_number_struct =
new ValueList(Arrays.asList(
new ConstantInteger(width, SymbolType.BYTE),
new ConstantInteger(leftJustify, SymbolType.BYTE),
new ConstantInteger(signAlways, SymbolType.BYTE),
new ConstantInteger(zeroPadding, SymbolType.BYTE),
new ConstantInteger(upperCase, SymbolType.BYTE),
radix
));
addPrintfCall(printf_number_procedure, Arrays.asList(CPUTC_REF, getParameterValue(parameters, paramIdx, printfCall), format_number_struct), stmtIt, printfCall);
paramIdx++;
} else if(typeField.equals("c")) {
// Print char
addPrintfCall(CPUTC, Arrays.asList(getParameterValue(parameters, paramIdx, printfCall)), stmtIt, printfCall);
paramIdx++;
} else if(typeField.equals("p")) {
// Print a pointer
final ValueList format_number_struct =
new ValueList(Arrays.asList(
new ConstantInteger(width, SymbolType.BYTE),
new ConstantInteger(leftJustify, SymbolType.BYTE),
new ConstantInteger(signAlways, SymbolType.BYTE),
new ConstantInteger(zeroPadding, SymbolType.BYTE),
new ConstantInteger(upperCase, SymbolType.BYTE),
getScope().getLocalConstant(HEXADECIMAL).getRef()
));
addPrintfCall(PRINTF_UINT, Arrays.asList(CPUTC_REF, new CastValue(SymbolType.WORD, getParameterValue(parameters, paramIdx, printfCall)), format_number_struct), stmtIt, printfCall);
paramIdx++;
}
} }
// Grab the rest
String suffix = formatString.substring(formatIdx);
if(suffix.length() > 0)
addPrintfCall(PRINTF_STR, Arrays.asList(CPUTC_REF, new ConstantString(suffix, formatEncoding, true)), stmtIt, printfCall);
} }
} }
} }
return false; return false;
} }
/**
* Add statements to the program printing the formatted string specified
* @param stmtIt Iterator used to add statements
* @param printfCall The original printf() statement
* @param format The format string (must be constant)
* @param parameters The parameters to the printf function (only the ... parameters)
* @param putcName The name of the function to use to output a single character
*/
private StringEncoding addPrintfFormatStatements(ListIterator<Statement> stmtIt, StatementCall printfCall, RValue format, List<RValue> parameters, String putcName) {
if(!(format instanceof ConstantValue))
throw new CompileError("Only constant printf() format parameter supported!", printfCall);
final ConstantLiteral formatLiteral = ((ConstantValue) format).calculateLiteral(getProgram().getScope());
if(!(formatLiteral instanceof ConstantString))
throw new CompileError("printf() format parameter must be a string!", printfCall);
final String formatString = ((ConstantString) formatLiteral).getString();
final StringEncoding formatEncoding = ((ConstantString) formatLiteral).getEncoding();
Symbol putcSymbol = getScope().getGlobalSymbol(putcName);
if(putcSymbol==null)
throw new CompileError("Needed printf sub-procedure not found " + putcName + "().", ((Statement) printfCall).getSource());
ConstantValue putcRef = new ConstantSymbolPointer(putcSymbol.getRef());
// Printf Placeholder Format String - source: https://en.wikipedia.org/wiki/Printf_format_string
// "%" start
// ([1-9][0-9]* "$")? parameter (gives the # of the parameter to use)
// [-+ 0'#]* flags (different flags affecting the formatting "-": left-align, "0": zero-prepend, "+": always sign)
// [1-9][0-9]* width (the minimum number of characters)
// ("hh" | "l" )? length (specifies the type of integer "hh": char "": int, "l": long)
// [%diuxXoscp] type (specifies the type of the parameter/output "d"/"i" decimal signed, "u": decimal unsigned, "x": hexadecimal unsigned (lowercase), "X": hexadecimal unsigned (uppercase), "o": octal unsigned, "s": string, "c": character, "p": pointer, "%": output "%" )
Pattern pattern = Pattern.compile("%([1-9][0-9]*[$])?([-+0#]*)([1-9][0-9]*)?(hh|l)?([%diuxXoscp])");
final Matcher matcher = pattern.matcher(formatString);
// The index for the format field within the string
int formatIdx = 0;
// The index of the parameter being used as value for formatting. Incremented automatically unless field parameter index syntax (eg. %2$d) is used.
int paramIdx = 0;
// True if field parameter index syntax (eg. %2$d) is used.
boolean fieldParamIdx = false;
while(true) {
// Find the next pattern match!
boolean found = matcher.find();
if(!found) {
// No more matching patterns
break;
}
final int start = matcher.start();
final int end = matcher.end();
final String typeField = matcher.group(5);
final String paramField = matcher.group(1);
// Ensure that all fields use parameter index syntax!
if(paramField == null && fieldParamIdx && !typeField.equals("%"))
throw new CompileError("If any single printf() placeholder specifies a parameter, all the rest of the placeholders must also specify a parameter!", printfCall);
if(paramField != null) {
if(!fieldParamIdx && paramIdx > 0)
throw new CompileError("If any single printf() placeholder specifies a parameter, all the rest of the placeholders must also specify a parameter!", printfCall);
fieldParamIdx = true;
paramIdx = Integer.parseInt(paramField.substring(0, paramField.length() - 1))-1;
}
final String flagsField = matcher.group(2);
long leftJustify = (flagsField != null && flagsField.contains("-")) ? 1 : 0;
long signAlways = (flagsField != null && flagsField.contains("+")) ? 1 : 0;
long zeroPadding = (flagsField != null && flagsField.contains("0")) ? 1 : 0;
final String widthField = matcher.group(3);
long width = (widthField == null) ? 0 : Integer.parseInt(widthField);
final String lengthField = matcher.group(4);
long upperCase = 0L;
// First output the non-matching part before the pattern
String prefix = formatString.substring(formatIdx, start);
if(prefix.length() > 0) {
addPrintfCall(PRINTF_STR, Arrays.asList(putcRef, new ConstantString(prefix, formatEncoding, true)), stmtIt, printfCall);
}
formatIdx = end;
if(typeField.equals("%")) {
addPrintfCall(putcName, Arrays.asList(new ConstantChar('%', formatEncoding)), stmtIt, printfCall);
} else if(typeField.equals("s")) {
// A formatted string
//struct printf_format_string {
// char min_length; // The minimal number of chars to output (used for padding with spaces or 0).
// char justify_left; // Justify left instead of right, which is the default.
//};
final ValueList format_string_struct =
new ValueList(Arrays.asList(
new ConstantInteger(width, SymbolType.BYTE),
new ConstantInteger(leftJustify, SymbolType.BYTE)
));
addPrintfCall(PRINTF_STRING, Arrays.asList(putcRef, getParameterValue(parameters, paramIdx, printfCall), format_string_struct), stmtIt, printfCall);
paramIdx++;
} else if("diuxXo".contains(typeField)) {
// A formatted integer
SymbolVariableRef radix;
String printf_number_procedure;
boolean signed;
switch(typeField) {
case "d":
case "i":
radix = getScope().getLocalConstant(DECIMAL).getRef();
signed = true;
break;
case "u":
radix = getScope().getLocalConstant(DECIMAL).getRef();
signed = false;
break;
case "x":
radix = getScope().getLocalConstant(HEXADECIMAL).getRef();
signed = false;
break;
case "X":
radix = getScope().getLocalConstant(HEXADECIMAL).getRef();
signed = false;
upperCase = 1l;
break;
case "o":
radix = getScope().getLocalConstant(OCTAL).getRef();
signed = false;
break;
default:
throw new CompileError("printf type field not supported", printfCall);
}
if(lengthField == null) {
// Check if the parameter type is 8-bit or 32-bit
RValue paramValue = getParameterValue(parameters, paramIdx, printfCall);
SymbolType paramType = SymbolTypeInference.inferType(getScope(), paramValue);
if(SymbolType.BYTE.equals(paramType) || SymbolType.SBYTE.equals(paramType)) {
// Integer (8bit)
printf_number_procedure = signed ? PRINTF_SCHAR : PRINTF_UCHAR;
} else if(SymbolType.DWORD.equals(paramType) || SymbolType.SDWORD.equals(paramType)) {
// Integer (32bit)
printf_number_procedure = signed ? PRINTF_SLONG : PRINTF_ULONG;
} else {
// Integer (16bit)
printf_number_procedure = signed ? PRINTF_SINT : PRINTF_UINT;
}
} else if(lengthField.equals("hh")) {
// Integer (8bit)
printf_number_procedure = signed ? PRINTF_SCHAR : PRINTF_UCHAR;
} else if(lengthField.equals("l")) {
// Integer (32bit)
printf_number_procedure = signed ? PRINTF_SLONG : PRINTF_ULONG;
} else {
throw new CompileError("printf length field not supported", printfCall);
}
// Format specifying how to format a printed number
// struct printf_format_number {
// char min_length; // The minimal number of chars to output (used for padding with spaces or 0)
// char justify_left; // Justify left instead of right, which is the default.
// char sign_always; // Always show a sign for a number, even if is is positive. (Default is to only show sign for negative numbers)
// char zero_padding; // Pad the number with zeros to get the min width
// char upper_case; // Upper-case the letters in the number
// enum RADIX radix; // The number radix to use for formatting
// };
final ValueList format_number_struct =
new ValueList(Arrays.asList(
new ConstantInteger(width, SymbolType.BYTE),
new ConstantInteger(leftJustify, SymbolType.BYTE),
new ConstantInteger(signAlways, SymbolType.BYTE),
new ConstantInteger(zeroPadding, SymbolType.BYTE),
new ConstantInteger(upperCase, SymbolType.BYTE),
radix
));
addPrintfCall(printf_number_procedure, Arrays.asList(putcRef, getParameterValue(parameters, paramIdx, printfCall), format_number_struct), stmtIt, printfCall);
paramIdx++;
} else if(typeField.equals("c")) {
// Print char
addPrintfCall(putcName, Arrays.asList(getParameterValue(parameters, paramIdx, printfCall)), stmtIt, printfCall);
paramIdx++;
} else if(typeField.equals("p")) {
// Print a pointer
final ValueList format_number_struct =
new ValueList(Arrays.asList(
new ConstantInteger(width, SymbolType.BYTE),
new ConstantInteger(leftJustify, SymbolType.BYTE),
new ConstantInteger(signAlways, SymbolType.BYTE),
new ConstantInteger(zeroPadding, SymbolType.BYTE),
new ConstantInteger(upperCase, SymbolType.BYTE),
getScope().getLocalConstant(HEXADECIMAL).getRef()
));
addPrintfCall(PRINTF_UINT, Arrays.asList(putcRef, new CastValue(SymbolType.WORD, getParameterValue(parameters, paramIdx, printfCall)), format_number_struct), stmtIt, printfCall);
paramIdx++;
}
}
// Grab the rest
String suffix = formatString.substring(formatIdx);
if(suffix.length() > 0)
addPrintfCall(PRINTF_STR, Arrays.asList(putcRef, new ConstantString(suffix, formatEncoding, true)), stmtIt, printfCall);
return formatEncoding;
}
/** /**
* Get a specific parameter value. * Get a specific parameter value.
* @param parameters The list of parameters * @param parameters The list of parameters
@@ -271,7 +302,7 @@ public class Pass1PrintfIntrinsicRewrite extends Pass2SsaOptimization {
*/ */
private RValue getParameterValue(List<RValue> parameters, int paramIdx, StatementCall printfCall) { private RValue getParameterValue(List<RValue> parameters, int paramIdx, StatementCall printfCall) {
if(parameters.size()<=paramIdx) if(parameters.size()<=paramIdx)
throw new CompileError("printf missing parameter with index "+paramIdx, printfCall); throw new CompileError("printf missing parameter with index "+(paramIdx+1), printfCall);
return parameters.get(paramIdx); return parameters.get(paramIdx);
} }

View File

@@ -0,0 +1,26 @@
#include <stddef.h>
#include <printf.h>
/// Composes a string with the same text that would be printed if format was used on printf(),
/// but instead of being printed, the content is stored as a C string in the buffer pointed by s
/// (taking n as the maximum buffer capacity to fill).
/// @param s Pointer to a buffer where the resulting C-string is stored. The buffer should have a size of at least n characters.
/// @param n Maximum number of bytes to be used in the buffer. The generated string has a length of at most n-1, leaving space for the additional terminating null character.
/// @param format C string that contains a format string that follows the same specifications as format in printf (see printf for details).
/// @param ... Depending on the format string, the function may expect a sequence of additional arguments, each containing a value to be used to replace a format specifier in the format string (or a pointer to a storage location, for n).
/// There should be at least as many of these arguments as the number of values specified in the format specifiers. Additional arguments are ignored by the function.
/// @return The number of characters that would have been written if n had been sufficiently large, not counting the terminating null character.
/// Notice that only when this returned value is non-negative and less than n, the string has been completely written.
int snprintf ( char * s, size_t n, const char * format, ... );
/// Initialize the snprintf() state
/// @param s Pointer to a buffer where the resulting C-string is stored. The buffer should have a size of at least n characters.
/// @param n Maximum number of bytes to be used in the buffer. The generated string has a length of at most n-1, leaving space for the additional terminating null character.
void snprintf_init(char * s, size_t n);
/// Print a character into snprintf buffer
/// Used by snprintf()
/// @param c The character to print
void snputc(char c);

View File

@@ -0,0 +1,46 @@
/// Implementation of snprintf
/// Composes a string with the same text that would be printed if format was used on printf(),
/// but instead of being printed, the content is stored as a C string in the buffer pointed by s
/// (taking n as the maximum buffer capacity to fill).
/// @param s Pointer to a buffer where the resulting C-string is stored. The buffer should have a size of at least n characters.
/// @param n Maximum number of bytes to be used in the buffer. The generated string has a length of at most n-1, leaving space for the additional terminating null character.
/// @param format C string that contains a format string that follows the same specifications as format in printf (see printf for details).
/// @param ... Depending on the format string, the function may expect a sequence of additional arguments, each containing a value to be used to replace a format specifier in the format string (or a pointer to a storage location, for n).
/// There should be at least as many of these arguments as the number of values specified in the format specifiers. Additional arguments are ignored by the function.
/// @return The number of characters that would have been written if n had been sufficiently large, not counting the terminating null character.
/// Notice that only when this returned value is non-negative and less than n, the string has been completely written.
__intrinsic int snprintf ( char * s, size_t n, const char * format, ... );
/// The capacity of the buffer (n passed to snprintf())
/// Used to hold state while printing
volatile size_t __snprintf_capacity;
// The number of chars that would have been filled when printing without capacity. Grows even after size>capacity.
/// Used to hold state while printing
volatile size_t __snprintf_size;
/// Current position in the buffer being filled ( initially *s passed to snprintf()
/// Used to hold state while printing
char * __snprintf_buffer;
/// Initialize the snprintf() state
void snprintf_init(char * s, size_t n) {
__snprintf_capacity = n;
__snprintf_size = 0;
__snprintf_buffer = s;
}
/// Print a character into snprintf buffer
/// Used by snprintf()
/// @param c The character to print
void snputc(char c) {
// Increment size
++__snprintf_size;
// If buffer full - do nothing
if(__snprintf_size > __snprintf_capacity)
return;
// If capacity reached append '\0'
if(__snprintf_size==__snprintf_capacity)
c = 0;
// Append char
*(__snprintf_buffer++) = c;
}

View File

@@ -879,6 +879,11 @@ public class TestProgramsFast extends TestPrograms {
assertError("printf-error-1.c", "Needed printf sub-procedure not found"); assertError("printf-error-1.c", "Needed printf sub-procedure not found");
} }
@Test
public void testPrintf17() throws IOException {
compileAndCompare("printf-17.c");
}
@Test @Test
public void testPrintf15() throws IOException { public void testPrintf15() throws IOException {
compileAndCompare("printf-15.c"); compileAndCompare("printf-15.c");
@@ -889,6 +894,11 @@ public class TestProgramsFast extends TestPrograms {
compileAndCompare("printf-14.c"); compileAndCompare("printf-14.c");
} }
@Test
public void testPrintf12() throws IOException {
compileAndCompare("printf-12.c");
}
@Test @Test
public void testPrintf11() throws IOException { public void testPrintf11() throws IOException {
compileAndCompare("printf-11.c"); compileAndCompare("printf-11.c");

View File

@@ -12,6 +12,8 @@ void printf_str(void (*putc)(char), char* str) {
} }
} }
void cputc(char x) {}
// Format specifying how to format a printed string // Format specifying how to format a printed string
struct printf_format_string { struct printf_format_string {
// The minimal number of chars to output (used for padding with spaces or 0). // The minimal number of chars to output (used for padding with spaces or 0).

View File

@@ -42,6 +42,9 @@ void printf_uint(void (*putc)(char), unsigned int uvalue, struct printf_format_n
*screen++ = printf_hextab[BYTE0(uvalue)&0xf]; *screen++ = printf_hextab[BYTE0(uvalue)&0xf];
} }
void cputc(char x) {}
void main() { void main() {
unsigned int pct = 342; unsigned int pct = 342;
printf("Commodore is %x cool", pct); printf("Commodore is %x cool", pct);

31
src/test/kc/printf-17.c Normal file
View File

@@ -0,0 +1,31 @@
// Tests snprintf function call rewriting
// Test simple formats
#include <snprintf.h>
char BUF[20];
char * screen = (char*)0x0400;
void print(char* msg) {
while(*msg)
*(screen++) = *(msg++);
}
void main() {
// String - no format
snprintf(BUF, 20, "hello world! ");
print(BUF);
// String & char format
snprintf(BUF, 20, "hello %s%c ", "world", '!');
print(BUF);
// Number format
snprintf(BUF, 20, "hello %d+%x! ", 3,11);
print(BUF);
// Shortened
snprintf(BUF, 6, "hi %d! ", 22222);
print(BUF);
}

View File

@@ -293,13 +293,14 @@ bitmap_line: {
adc.z dx+1 adc.z dx+1
sta.z e+1 sta.z e+1
// if(dy<e) // if(dy<e)
cmp.z dy+1 lda.z dy+1
bne !+ cmp.z e+1
lda.z e bcc !+
cmp.z dy bne __b7
beq __b7 lda.z dy
cmp.z e
bcs __b7
!: !:
bcc __b7
// x += sx // x += sx
clc clc
lda.z x lda.z x
@@ -368,13 +369,14 @@ bitmap_line: {
adc.z dy+1 adc.z dy+1
sta.z e1+1 sta.z e1+1
// if(dx < e) // if(dx < e)
cmp.z dx+1 lda.z dx+1
bne !+ cmp.z e1+1
lda.z e1 bcc !+
cmp.z dx bne __b10
beq __b10 lda.z dx
cmp.z e1
bcs __b10
!: !:
bcc __b10
// y += sy // y += sy
clc clc
lda.z y lda.z y

View File

@@ -2743,14 +2743,14 @@ bitmap_line: {
adc.z dx+1 adc.z dx+1
sta.z e+1 sta.z e+1
// [70] if(bitmap_line::dy#0>=bitmap_line::e#1) goto bitmap_line::@7 -- vwuz1_ge_vwuz2_then_la1 // [70] if(bitmap_line::dy#0>=bitmap_line::e#1) goto bitmap_line::@7 -- vwuz1_ge_vwuz2_then_la1
lda.z e+1 lda.z dy+1
cmp.z dy+1 cmp.z e+1
bne !+ bcc !+
lda.z e bne __b7_from___b16
cmp.z dy lda.z dy
beq __b7_from___b16 cmp.z e
bcs __b7_from___b16
!: !:
bcc __b7_from___b16
jmp __b8 jmp __b8
// bitmap_line::@8 // bitmap_line::@8
__b8: __b8:
@@ -2868,14 +2868,14 @@ bitmap_line: {
adc.z dy+1 adc.z dy+1
sta.z e1+1 sta.z e1+1
// [87] if(bitmap_line::dx#0>=bitmap_line::e1#1) goto bitmap_line::@10 -- vwuz1_ge_vwuz2_then_la1 // [87] if(bitmap_line::dx#0>=bitmap_line::e1#1) goto bitmap_line::@10 -- vwuz1_ge_vwuz2_then_la1
lda.z e1+1 lda.z dx+1
cmp.z dx+1 cmp.z e1+1
bne !+ bcc !+
lda.z e1 bne __b10_from___b17
cmp.z dx lda.z dx
beq __b10_from___b17 cmp.z e1
bcs __b10_from___b17
!: !:
bcc __b10_from___b17
jmp __b11 jmp __b11
// bitmap_line::@11 // bitmap_line::@11
__b11: __b11:
@@ -3150,8 +3150,6 @@ Removing instruction jmp __breturn
Removing instruction jmp __breturn Removing instruction jmp __breturn
Succesful ASM optimization Pass5NextJumpElimination Succesful ASM optimization Pass5NextJumpElimination
Removing instruction lda #0 Removing instruction lda #0
Removing instruction lda.z e+1
Removing instruction lda.z e1+1
Removing instruction lda #>-1 Removing instruction lda #>-1
Succesful ASM optimization Pass5UnnecesaryLoadElimination Succesful ASM optimization Pass5UnnecesaryLoadElimination
Replacing label __b6_from___b1 with __b2 Replacing label __b6_from___b1 with __b2
@@ -3433,7 +3431,7 @@ reg byte x [ bitmap_plot::$2 ]
FINAL ASSEMBLER FINAL ASSEMBLER
Score: 30070 Score: 30670
// File Comments // File Comments
// Illustrates problem with bitmap-draw.kc line() // Illustrates problem with bitmap-draw.kc line()
@@ -3880,13 +3878,14 @@ bitmap_line: {
sta.z e+1 sta.z e+1
// if(dy<e) // if(dy<e)
// [70] if(bitmap_line::dy#0>=bitmap_line::e#1) goto bitmap_line::@7 -- vwuz1_ge_vwuz2_then_la1 // [70] if(bitmap_line::dy#0>=bitmap_line::e#1) goto bitmap_line::@7 -- vwuz1_ge_vwuz2_then_la1
cmp.z dy+1 lda.z dy+1
bne !+ cmp.z e+1
lda.z e bcc !+
cmp.z dy bne __b7
beq __b7 lda.z dy
cmp.z e
bcs __b7
!: !:
bcc __b7
// bitmap_line::@8 // bitmap_line::@8
// x += sx // x += sx
// [71] bitmap_line::x#1 = bitmap_line::x#13 + bitmap_line::sx#0 -- vwuz1=vwuz1_plus_vwuz2 // [71] bitmap_line::x#1 = bitmap_line::x#13 + bitmap_line::sx#0 -- vwuz1=vwuz1_plus_vwuz2
@@ -3996,13 +3995,14 @@ bitmap_line: {
sta.z e1+1 sta.z e1+1
// if(dx < e) // if(dx < e)
// [87] if(bitmap_line::dx#0>=bitmap_line::e1#1) goto bitmap_line::@10 -- vwuz1_ge_vwuz2_then_la1 // [87] if(bitmap_line::dx#0>=bitmap_line::e1#1) goto bitmap_line::@10 -- vwuz1_ge_vwuz2_then_la1
cmp.z dx+1 lda.z dx+1
bne !+ cmp.z e1+1
lda.z e1 bcc !+
cmp.z dx bne __b10
beq __b10 lda.z dx
cmp.z e1
bcs __b10
!: !:
bcc __b10
// bitmap_line::@11 // bitmap_line::@11
// y += sy // y += sy
// [88] bitmap_line::y#2 = bitmap_line::y#15 + bitmap_line::sy#0 -- vwuz1=vwuz1_plus_vwuz2 // [88] bitmap_line::y#2 = bitmap_line::y#15 + bitmap_line::sy#0 -- vwuz1=vwuz1_plus_vwuz2

View File

@@ -274,13 +274,14 @@ bitmap_line: {
adc.z dx+1 adc.z dx+1
sta.z e+1 sta.z e+1
// if(dy<e) // if(dy<e)
cmp.z dy+1 lda.z dy+1
bne !+ cmp.z e+1
lda.z e bcc !+
cmp.z dy bne __b7
beq __b7 lda.z dy
cmp.z e
bcs __b7
!: !:
bcc __b7
// x += sx // x += sx
clc clc
lda.z x lda.z x
@@ -349,13 +350,14 @@ bitmap_line: {
adc.z dy+1 adc.z dy+1
sta.z e1+1 sta.z e1+1
// if(dx < e) // if(dx < e)
cmp.z dx+1 lda.z dx+1
bne !+ cmp.z e1+1
lda.z e1 bcc !+
cmp.z dx bne __b10
beq __b10 lda.z dx
cmp.z e1
bcs __b10
!: !:
bcc __b10
// y += sy // y += sy
clc clc
lda.z y lda.z y

View File

@@ -2686,14 +2686,14 @@ bitmap_line: {
adc.z dx+1 adc.z dx+1
sta.z e+1 sta.z e+1
// [65] if(bitmap_line::dy#0>=bitmap_line::e#1) goto bitmap_line::@7 -- vwuz1_ge_vwuz2_then_la1 // [65] if(bitmap_line::dy#0>=bitmap_line::e#1) goto bitmap_line::@7 -- vwuz1_ge_vwuz2_then_la1
lda.z e+1 lda.z dy+1
cmp.z dy+1 cmp.z e+1
bne !+ bcc !+
lda.z e bne __b7_from___b16
cmp.z dy lda.z dy
beq __b7_from___b16 cmp.z e
bcs __b7_from___b16
!: !:
bcc __b7_from___b16
jmp __b8 jmp __b8
// bitmap_line::@8 // bitmap_line::@8
__b8: __b8:
@@ -2811,14 +2811,14 @@ bitmap_line: {
adc.z dy+1 adc.z dy+1
sta.z e1+1 sta.z e1+1
// [82] if(bitmap_line::dx#0>=bitmap_line::e1#1) goto bitmap_line::@10 -- vwuz1_ge_vwuz2_then_la1 // [82] if(bitmap_line::dx#0>=bitmap_line::e1#1) goto bitmap_line::@10 -- vwuz1_ge_vwuz2_then_la1
lda.z e1+1 lda.z dx+1
cmp.z dx+1 cmp.z e1+1
bne !+ bcc !+
lda.z e1 bne __b10_from___b17
cmp.z dx lda.z dx
beq __b10_from___b17 cmp.z e1
bcs __b10_from___b17
!: !:
bcc __b10_from___b17
jmp __b11 jmp __b11
// bitmap_line::@11 // bitmap_line::@11
__b11: __b11:
@@ -3094,8 +3094,6 @@ Succesful ASM optimization Pass5NextJumpElimination
Removing instruction lda #0 Removing instruction lda #0
Removing instruction lda #>0 Removing instruction lda #>0
Removing instruction lda #>0 Removing instruction lda #>0
Removing instruction lda.z e+1
Removing instruction lda.z e1+1
Removing instruction lda #>-1 Removing instruction lda #>-1
Succesful ASM optimization Pass5UnnecesaryLoadElimination Succesful ASM optimization Pass5UnnecesaryLoadElimination
Replacing label __b5_from___b4 with __b2 Replacing label __b5_from___b4 with __b2
@@ -3381,7 +3379,7 @@ reg byte x [ bitmap_plot::$2 ]
FINAL ASSEMBLER FINAL ASSEMBLER
Score: 29778 Score: 30378
// File Comments // File Comments
// Shows that c64-bitmap.kc line() does not have the same problem as bitmap-draw.kc // Shows that c64-bitmap.kc line() does not have the same problem as bitmap-draw.kc
@@ -3801,13 +3799,14 @@ bitmap_line: {
sta.z e+1 sta.z e+1
// if(dy<e) // if(dy<e)
// [65] if(bitmap_line::dy#0>=bitmap_line::e#1) goto bitmap_line::@7 -- vwuz1_ge_vwuz2_then_la1 // [65] if(bitmap_line::dy#0>=bitmap_line::e#1) goto bitmap_line::@7 -- vwuz1_ge_vwuz2_then_la1
cmp.z dy+1 lda.z dy+1
bne !+ cmp.z e+1
lda.z e bcc !+
cmp.z dy bne __b7
beq __b7 lda.z dy
cmp.z e
bcs __b7
!: !:
bcc __b7
// bitmap_line::@8 // bitmap_line::@8
// x += sx // x += sx
// [66] bitmap_line::x#1 = bitmap_line::x#13 + bitmap_line::sx#0 -- vwuz1=vwuz1_plus_vwuz2 // [66] bitmap_line::x#1 = bitmap_line::x#13 + bitmap_line::sx#0 -- vwuz1=vwuz1_plus_vwuz2
@@ -3917,13 +3916,14 @@ bitmap_line: {
sta.z e1+1 sta.z e1+1
// if(dx < e) // if(dx < e)
// [82] if(bitmap_line::dx#0>=bitmap_line::e1#1) goto bitmap_line::@10 -- vwuz1_ge_vwuz2_then_la1 // [82] if(bitmap_line::dx#0>=bitmap_line::e1#1) goto bitmap_line::@10 -- vwuz1_ge_vwuz2_then_la1
cmp.z dx+1 lda.z dx+1
bne !+ cmp.z e1+1
lda.z e1 bcc !+
cmp.z dx bne __b10
beq __b10 lda.z dx
cmp.z e1
bcs __b10
!: !:
bcc __b10
// bitmap_line::@11 // bitmap_line::@11
// y += sy // y += sy
// [83] bitmap_line::y#2 = bitmap_line::y#15 + bitmap_line::sy#0 -- vwuz1=vwuz1_plus_vwuz2 // [83] bitmap_line::y#2 = bitmap_line::y#15 + bitmap_line::sy#0 -- vwuz1=vwuz1_plus_vwuz2

View File

@@ -312,13 +312,14 @@ bitmap_line: {
adc.z dx+1 adc.z dx+1
sta.z e+1 sta.z e+1
// if(dy<e) // if(dy<e)
cmp.z dy+1 lda.z dy+1
bne !+ cmp.z e+1
lda.z e bcc !+
cmp.z dy bne __b7
beq __b7 lda.z dy
cmp.z e
bcs __b7
!: !:
bcc __b7
// x += sx // x += sx
clc clc
lda.z x lda.z x
@@ -379,13 +380,14 @@ bitmap_line: {
adc.z dy+1 adc.z dy+1
sta.z e1+1 sta.z e1+1
// if(dx < e) // if(dx < e)
cmp.z dx+1 lda.z dx+1
bne !+ cmp.z e1+1
lda.z e1 bcc !+
cmp.z dx bne __b10
beq __b10 lda.z dx
cmp.z e1
bcs __b10
!: !:
bcc __b10
// y += sy // y += sy
clc clc
lda.z y lda.z y

View File

@@ -2961,14 +2961,14 @@ bitmap_line: {
adc.z dx+1 adc.z dx+1
sta.z e+1 sta.z e+1
// [72] if(bitmap_line::dy#0>=bitmap_line::e#1) goto bitmap_line::@7 -- vwuz1_ge_vwuz2_then_la1 // [72] if(bitmap_line::dy#0>=bitmap_line::e#1) goto bitmap_line::@7 -- vwuz1_ge_vwuz2_then_la1
lda.z e+1 lda.z dy+1
cmp.z dy+1 cmp.z e+1
bne !+ bcc !+
lda.z e bne __b7_from___b16
cmp.z dy lda.z dy
beq __b7_from___b16 cmp.z e
bcs __b7_from___b16
!: !:
bcc __b7_from___b16
jmp __b8 jmp __b8
// bitmap_line::@8 // bitmap_line::@8
__b8: __b8:
@@ -3073,14 +3073,14 @@ bitmap_line: {
adc.z dy+1 adc.z dy+1
sta.z e1+1 sta.z e1+1
// [89] if(bitmap_line::dx#0>=bitmap_line::e1#1) goto bitmap_line::@10 -- vwuz1_ge_vwuz2_then_la1 // [89] if(bitmap_line::dx#0>=bitmap_line::e1#1) goto bitmap_line::@10 -- vwuz1_ge_vwuz2_then_la1
lda.z e1+1 lda.z dx+1
cmp.z dx+1 cmp.z e1+1
bne !+ bcc !+
lda.z e1 bne __b10_from___b17
cmp.z dx lda.z dx
beq __b10_from___b17 cmp.z e1
bcs __b10_from___b17
!: !:
bcc __b10_from___b17
jmp __b11 jmp __b11
// bitmap_line::@11 // bitmap_line::@11
__b11: __b11:
@@ -3354,8 +3354,6 @@ Removing instruction jmp __breturn
Succesful ASM optimization Pass5NextJumpElimination Succesful ASM optimization Pass5NextJumpElimination
Removing instruction lda #0 Removing instruction lda #0
Removing instruction ldy.z a Removing instruction ldy.z a
Removing instruction lda.z e+1
Removing instruction lda.z e1+1
Removing instruction lda #>-1 Removing instruction lda #>-1
Succesful ASM optimization Pass5UnnecesaryLoadElimination Succesful ASM optimization Pass5UnnecesaryLoadElimination
Replacing label __b6_from___b1 with __b2 Replacing label __b6_from___b1 with __b2
@@ -3647,7 +3645,7 @@ reg byte x [ bitmap_plot::$2 ]
FINAL ASSEMBLER FINAL ASSEMBLER
Score: 26875 Score: 27475
// File Comments // File Comments
// Tests the simple bitmap plotter // Tests the simple bitmap plotter
@@ -4109,13 +4107,14 @@ bitmap_line: {
sta.z e+1 sta.z e+1
// if(dy<e) // if(dy<e)
// [72] if(bitmap_line::dy#0>=bitmap_line::e#1) goto bitmap_line::@7 -- vwuz1_ge_vwuz2_then_la1 // [72] if(bitmap_line::dy#0>=bitmap_line::e#1) goto bitmap_line::@7 -- vwuz1_ge_vwuz2_then_la1
cmp.z dy+1 lda.z dy+1
bne !+ cmp.z e+1
lda.z e bcc !+
cmp.z dy bne __b7
beq __b7 lda.z dy
cmp.z e
bcs __b7
!: !:
bcc __b7
// bitmap_line::@8 // bitmap_line::@8
// x += sx // x += sx
// [73] bitmap_line::x#1 = bitmap_line::x#13 + bitmap_line::sx#0 -- vwuz1=vwuz1_plus_vwuz2 // [73] bitmap_line::x#1 = bitmap_line::x#13 + bitmap_line::sx#0 -- vwuz1=vwuz1_plus_vwuz2
@@ -4213,13 +4212,14 @@ bitmap_line: {
sta.z e1+1 sta.z e1+1
// if(dx < e) // if(dx < e)
// [89] if(bitmap_line::dx#0>=bitmap_line::e1#1) goto bitmap_line::@10 -- vwuz1_ge_vwuz2_then_la1 // [89] if(bitmap_line::dx#0>=bitmap_line::e1#1) goto bitmap_line::@10 -- vwuz1_ge_vwuz2_then_la1
cmp.z dx+1 lda.z dx+1
bne !+ cmp.z e1+1
lda.z e1 bcc !+
cmp.z dx bne __b10
beq __b10 lda.z dx
cmp.z e1
bcs __b10
!: !:
bcc __b10
// bitmap_line::@11 // bitmap_line::@11
// y += sy // y += sy
// [90] bitmap_line::y#2 = bitmap_line::y#15 + bitmap_line::sy#0 -- vwuz1=vwuz1_plus_vwuz2 // [90] bitmap_line::y#2 = bitmap_line::y#15 + bitmap_line::sy#0 -- vwuz1=vwuz1_plus_vwuz2

View File

@@ -570,13 +570,14 @@ utoa: {
// if (started || value >= digit_value) // if (started || value >= digit_value)
cpx #0 cpx #0
bne __b5 bne __b5
cmp.z value+1 lda.z value+1
bne !+ cmp.z digit_value+1
lda.z digit_value bcc !+
cmp.z value bne __b5
beq __b5 lda.z value
cmp.z digit_value
bcs __b5
!: !:
bcc __b5
__b4: __b4:
// for( char digit=0; digit<max_digits-1; digit++ ) // for( char digit=0; digit<max_digits-1; digit++ )
inc.z digit inc.z digit
@@ -637,14 +638,14 @@ utoa_append: {
ldx #0 ldx #0
__b1: __b1:
// while (value >= sub) // while (value >= sub)
lda.z sub+1 lda.z value+1
cmp.z value+1 cmp.z sub+1
bne !+ bcc !+
lda.z sub bne __b2
cmp.z value lda.z value
beq __b2 cmp.z sub
bcs __b2
!: !:
bcc __b2
// *buffer = DIGITS[digit] // *buffer = DIGITS[digit]
lda DIGITS,x lda DIGITS,x
ldy #0 ldy #0

View File

@@ -4605,14 +4605,14 @@ utoa: {
// utoa::@7 // utoa::@7
__b7: __b7:
// [137] if(utoa::value#2>=utoa::digit_value#0) goto utoa::@5 -- vwuz1_ge_vwuz2_then_la1 // [137] if(utoa::value#2>=utoa::digit_value#0) goto utoa::@5 -- vwuz1_ge_vwuz2_then_la1
lda.z digit_value+1 lda.z value+1
cmp.z value+1 cmp.z digit_value+1
bne !+ bcc !+
lda.z digit_value bne __b5
cmp.z value lda.z value
beq __b5 cmp.z digit_value
bcs __b5
!: !:
bcc __b5
// [138] phi from utoa::@7 to utoa::@4 [phi:utoa::@7->utoa::@4] // [138] phi from utoa::@7 to utoa::@4 [phi:utoa::@7->utoa::@4]
__b4_from___b7: __b4_from___b7:
// [138] phi utoa::buffer#14 = utoa::buffer#11 [phi:utoa::@7->utoa::@4#0] -- register_copy // [138] phi utoa::buffer#14 = utoa::buffer#11 [phi:utoa::@7->utoa::@4#0] -- register_copy
@@ -4728,14 +4728,14 @@ utoa_append: {
// utoa_append::@1 // utoa_append::@1
__b1: __b1:
// [157] if(utoa_append::value#2>=utoa_append::sub#0) goto utoa_append::@2 -- vwuz1_ge_vwuz2_then_la1 // [157] if(utoa_append::value#2>=utoa_append::sub#0) goto utoa_append::@2 -- vwuz1_ge_vwuz2_then_la1
lda.z sub+1 lda.z value+1
cmp.z value+1 cmp.z sub+1
bne !+ bcc !+
lda.z sub bne __b2
cmp.z value lda.z value
beq __b2 cmp.z sub
bcs __b2
!: !:
bcc __b2
jmp __b3 jmp __b3
// utoa_append::@3 // utoa_append::@3
__b3: __b3:
@@ -4938,8 +4938,6 @@ Removing instruction jmp __b1
Removing instruction jmp __b2 Removing instruction jmp __b2
Removing instruction jmp __b2 Removing instruction jmp __b2
Succesful ASM optimization Pass5NextJumpElimination Succesful ASM optimization Pass5NextJumpElimination
Removing instruction lda.z digit_value+1
Succesful ASM optimization Pass5UnnecesaryLoadElimination
Removing instruction __b3: Removing instruction __b3:
Succesful ASM optimization Pass5UnusedLabelElimination Succesful ASM optimization Pass5UnusedLabelElimination
@@ -5149,7 +5147,7 @@ mem[12] [ printf_buffer ]
FINAL ASSEMBLER FINAL ASSEMBLER
Score: 74644 Score: 74944
// File Comments // File Comments
// Demonstrates problem with Casting of negative signed values // Demonstrates problem with Casting of negative signed values
@@ -5970,13 +5968,14 @@ utoa: {
bne __b5 bne __b5
// utoa::@7 // utoa::@7
// [137] if(utoa::value#2>=utoa::digit_value#0) goto utoa::@5 -- vwuz1_ge_vwuz2_then_la1 // [137] if(utoa::value#2>=utoa::digit_value#0) goto utoa::@5 -- vwuz1_ge_vwuz2_then_la1
cmp.z value+1 lda.z value+1
bne !+ cmp.z digit_value+1
lda.z digit_value bcc !+
cmp.z value bne __b5
beq __b5 lda.z value
cmp.z digit_value
bcs __b5
!: !:
bcc __b5
// [138] phi from utoa::@7 to utoa::@4 [phi:utoa::@7->utoa::@4] // [138] phi from utoa::@7 to utoa::@4 [phi:utoa::@7->utoa::@4]
// [138] phi utoa::buffer#14 = utoa::buffer#11 [phi:utoa::@7->utoa::@4#0] -- register_copy // [138] phi utoa::buffer#14 = utoa::buffer#11 [phi:utoa::@7->utoa::@4#0] -- register_copy
// [138] phi utoa::started#4 = utoa::started#2 [phi:utoa::@7->utoa::@4#1] -- register_copy // [138] phi utoa::started#4 = utoa::started#2 [phi:utoa::@7->utoa::@4#1] -- register_copy
@@ -6083,14 +6082,14 @@ utoa_append: {
__b1: __b1:
// while (value >= sub) // while (value >= sub)
// [157] if(utoa_append::value#2>=utoa_append::sub#0) goto utoa_append::@2 -- vwuz1_ge_vwuz2_then_la1 // [157] if(utoa_append::value#2>=utoa_append::sub#0) goto utoa_append::@2 -- vwuz1_ge_vwuz2_then_la1
lda.z sub+1 lda.z value+1
cmp.z value+1 cmp.z sub+1
bne !+ bcc !+
lda.z sub bne __b2
cmp.z value lda.z value
beq __b2 cmp.z sub
bcs __b2
!: !:
bcc __b2
// utoa_append::@3 // utoa_append::@3
// *buffer = DIGITS[digit] // *buffer = DIGITS[digit]
// [158] *utoa_append::buffer#0 = DIGITS[utoa_append::digit#2] -- _deref_pbuz1=pbuc1_derefidx_vbuxx // [158] *utoa_append::buffer#0 = DIGITS[utoa_append::digit#2] -- _deref_pbuz1=pbuc1_derefidx_vbuxx

View File

@@ -372,13 +372,14 @@ bitmap_line: {
adc.z dx+1 adc.z dx+1
sta.z e+1 sta.z e+1
// if(dy<e) // if(dy<e)
cmp.z dy+1 lda.z dy+1
bne !+ cmp.z e+1
lda.z e bcc !+
cmp.z dy bne __b7
beq __b7 lda.z dy
cmp.z e
bcs __b7
!: !:
bcc __b7
// x += sx // x += sx
clc clc
lda.z x lda.z x
@@ -439,13 +440,14 @@ bitmap_line: {
adc.z dy+1 adc.z dy+1
sta.z e1+1 sta.z e1+1
// if(dx < e) // if(dx < e)
cmp.z dx+1 lda.z dx+1
bne !+ cmp.z e1+1
lda.z e1 bcc !+
cmp.z dx bne __b10
beq __b10 lda.z dx
cmp.z e1
bcs __b10
!: !:
bcc __b10
// y += sy // y += sy
clc clc
lda.z y lda.z y

View File

@@ -2899,14 +2899,14 @@ bitmap_line: {
adc.z dx+1 adc.z dx+1
sta.z e+1 sta.z e+1
// [89] if(bitmap_line::dy#0>=bitmap_line::e#1) goto bitmap_line::@7 -- vwuz1_ge_vwuz2_then_la1 // [89] if(bitmap_line::dy#0>=bitmap_line::e#1) goto bitmap_line::@7 -- vwuz1_ge_vwuz2_then_la1
lda.z e+1 lda.z dy+1
cmp.z dy+1 cmp.z e+1
bne !+ bcc !+
lda.z e bne __b7_from___b16
cmp.z dy lda.z dy
beq __b7_from___b16 cmp.z e
bcs __b7_from___b16
!: !:
bcc __b7_from___b16
jmp __b8 jmp __b8
// bitmap_line::@8 // bitmap_line::@8
__b8: __b8:
@@ -3011,14 +3011,14 @@ bitmap_line: {
adc.z dy+1 adc.z dy+1
sta.z e1+1 sta.z e1+1
// [106] if(bitmap_line::dx#0>=bitmap_line::e1#1) goto bitmap_line::@10 -- vwuz1_ge_vwuz2_then_la1 // [106] if(bitmap_line::dx#0>=bitmap_line::e1#1) goto bitmap_line::@10 -- vwuz1_ge_vwuz2_then_la1
lda.z e1+1 lda.z dx+1
cmp.z dx+1 cmp.z e1+1
bne !+ bcc !+
lda.z e1 bne __b10_from___b17
cmp.z dx lda.z dx
beq __b10_from___b17 cmp.z e1
bcs __b10_from___b17
!: !:
bcc __b10_from___b17
jmp __b11 jmp __b11
// bitmap_line::@11 // bitmap_line::@11
__b11: __b11:
@@ -3236,8 +3236,6 @@ Removing instruction lda #0
Removing instruction ldy.z l Removing instruction ldy.z l
Removing instruction ldy.z l Removing instruction ldy.z l
Removing instruction ldy.z l Removing instruction ldy.z l
Removing instruction lda.z e+1
Removing instruction lda.z e1+1
Removing instruction lda #>-1 Removing instruction lda #>-1
Succesful ASM optimization Pass5UnnecesaryLoadElimination Succesful ASM optimization Pass5UnnecesaryLoadElimination
Replacing label __b1_from___b1 with __b1 Replacing label __b1_from___b1 with __b1
@@ -3530,7 +3528,7 @@ reg byte x [ bitmap_plot::$2 ]
FINAL ASSEMBLER FINAL ASSEMBLER
Score: 246362 Score: 252362
// File Comments // File Comments
/// @file /// @file
@@ -4080,13 +4078,14 @@ bitmap_line: {
sta.z e+1 sta.z e+1
// if(dy<e) // if(dy<e)
// [89] if(bitmap_line::dy#0>=bitmap_line::e#1) goto bitmap_line::@7 -- vwuz1_ge_vwuz2_then_la1 // [89] if(bitmap_line::dy#0>=bitmap_line::e#1) goto bitmap_line::@7 -- vwuz1_ge_vwuz2_then_la1
cmp.z dy+1 lda.z dy+1
bne !+ cmp.z e+1
lda.z e bcc !+
cmp.z dy bne __b7
beq __b7 lda.z dy
cmp.z e
bcs __b7
!: !:
bcc __b7
// bitmap_line::@8 // bitmap_line::@8
// x += sx // x += sx
// [90] bitmap_line::x#1 = bitmap_line::x#13 + bitmap_line::sx#0 -- vwuz1=vwuz1_plus_vwuz2 // [90] bitmap_line::x#1 = bitmap_line::x#13 + bitmap_line::sx#0 -- vwuz1=vwuz1_plus_vwuz2
@@ -4184,13 +4183,14 @@ bitmap_line: {
sta.z e1+1 sta.z e1+1
// if(dx < e) // if(dx < e)
// [106] if(bitmap_line::dx#0>=bitmap_line::e1#1) goto bitmap_line::@10 -- vwuz1_ge_vwuz2_then_la1 // [106] if(bitmap_line::dx#0>=bitmap_line::e1#1) goto bitmap_line::@10 -- vwuz1_ge_vwuz2_then_la1
cmp.z dx+1 lda.z dx+1
bne !+ cmp.z e1+1
lda.z e1 bcc !+
cmp.z dx bne __b10
beq __b10 lda.z dx
cmp.z e1
bcs __b10
!: !:
bcc __b10
// bitmap_line::@11 // bitmap_line::@11
// y += sy // y += sy
// [107] bitmap_line::y#2 = bitmap_line::y#15 + bitmap_line::sy#0 -- vwuz1=vwuz1_plus_vwuz2 // [107] bitmap_line::y#2 = bitmap_line::y#15 + bitmap_line::sy#0 -- vwuz1=vwuz1_plus_vwuz2

View File

@@ -256,13 +256,14 @@ utoa: {
// if (started || value >= digit_value) // if (started || value >= digit_value)
cpx #0 cpx #0
bne __b5 bne __b5
cmp.z value+1 lda.z value+1
bne !+ cmp.z digit_value+1
lda.z digit_value bcc !+
cmp.z value bne __b5
beq __b5 lda.z value
cmp.z digit_value
bcs __b5
!: !:
bcc __b5
__b4: __b4:
// for( char digit=0; digit<max_digits-1; digit++ ) // for( char digit=0; digit<max_digits-1; digit++ )
inc.z digit inc.z digit
@@ -348,14 +349,14 @@ utoa_append: {
ldx #0 ldx #0
__b1: __b1:
// while (value >= sub) // while (value >= sub)
lda.z sub+1 lda.z value+1
cmp.z value+1 cmp.z sub+1
bne !+ bcc !+
lda.z sub bne __b2
cmp.z value lda.z value
beq __b2 cmp.z sub
bcs __b2
!: !:
bcc __b2
// *buffer = DIGITS[digit] // *buffer = DIGITS[digit]
lda DIGITS,x lda DIGITS,x
ldy #0 ldy #0

View File

@@ -2475,14 +2475,14 @@ utoa: {
// utoa::@7 // utoa::@7
__b7: __b7:
// [69] if(utoa::value#2>=utoa::digit_value#0) goto utoa::@5 -- vwuz1_ge_vwuz2_then_la1 // [69] if(utoa::value#2>=utoa::digit_value#0) goto utoa::@5 -- vwuz1_ge_vwuz2_then_la1
lda.z digit_value+1 lda.z value+1
cmp.z value+1 cmp.z digit_value+1
bne !+ bcc !+
lda.z digit_value bne __b5
cmp.z value lda.z value
beq __b5 cmp.z digit_value
bcs __b5
!: !:
bcc __b5
// [70] phi from utoa::@7 to utoa::@4 [phi:utoa::@7->utoa::@4] // [70] phi from utoa::@7 to utoa::@4 [phi:utoa::@7->utoa::@4]
__b4_from___b7: __b4_from___b7:
// [70] phi utoa::buffer#14 = utoa::buffer#11 [phi:utoa::@7->utoa::@4#0] -- register_copy // [70] phi utoa::buffer#14 = utoa::buffer#11 [phi:utoa::@7->utoa::@4#0] -- register_copy
@@ -2642,14 +2642,14 @@ utoa_append: {
// utoa_append::@1 // utoa_append::@1
__b1: __b1:
// [96] if(utoa_append::value#2>=utoa_append::sub#0) goto utoa_append::@2 -- vwuz1_ge_vwuz2_then_la1 // [96] if(utoa_append::value#2>=utoa_append::sub#0) goto utoa_append::@2 -- vwuz1_ge_vwuz2_then_la1
lda.z sub+1 lda.z value+1
cmp.z value+1 cmp.z sub+1
bne !+ bcc !+
lda.z sub bne __b2
cmp.z value lda.z value
beq __b2 cmp.z sub
bcs __b2
!: !:
bcc __b2
jmp __b3 jmp __b3
// utoa_append::@3 // utoa_append::@3
__b3: __b3:
@@ -2828,8 +2828,6 @@ Relabelling long label __b2_from___b1 to __b3
Succesful ASM optimization Pass5RelabelLongLabels Succesful ASM optimization Pass5RelabelLongLabels
Removing instruction jmp __b2 Removing instruction jmp __b2
Succesful ASM optimization Pass5NextJumpElimination Succesful ASM optimization Pass5NextJumpElimination
Removing instruction lda.z digit_value+1
Succesful ASM optimization Pass5UnnecesaryLoadElimination
FINAL SYMBOL TABLE FINAL SYMBOL TABLE
__constant char DIGITS[] = "0123456789abcdef"z __constant char DIGITS[] = "0123456789abcdef"z
@@ -2971,7 +2969,7 @@ reg byte x [ print_uchar::$2 ]
FINAL ASSEMBLER FINAL ASSEMBLER
Score: 99334 Score: 99634
// File Comments // File Comments
/// @file /// @file
@@ -3375,13 +3373,14 @@ utoa: {
bne __b5 bne __b5
// utoa::@7 // utoa::@7
// [69] if(utoa::value#2>=utoa::digit_value#0) goto utoa::@5 -- vwuz1_ge_vwuz2_then_la1 // [69] if(utoa::value#2>=utoa::digit_value#0) goto utoa::@5 -- vwuz1_ge_vwuz2_then_la1
cmp.z value+1 lda.z value+1
bne !+ cmp.z digit_value+1
lda.z digit_value bcc !+
cmp.z value bne __b5
beq __b5 lda.z value
cmp.z digit_value
bcs __b5
!: !:
bcc __b5
// [70] phi from utoa::@7 to utoa::@4 [phi:utoa::@7->utoa::@4] // [70] phi from utoa::@7 to utoa::@4 [phi:utoa::@7->utoa::@4]
// [70] phi utoa::buffer#14 = utoa::buffer#11 [phi:utoa::@7->utoa::@4#0] -- register_copy // [70] phi utoa::buffer#14 = utoa::buffer#11 [phi:utoa::@7->utoa::@4#0] -- register_copy
// [70] phi utoa::started#4 = utoa::started#2 [phi:utoa::@7->utoa::@4#1] -- register_copy // [70] phi utoa::started#4 = utoa::started#2 [phi:utoa::@7->utoa::@4#1] -- register_copy
@@ -3533,14 +3532,14 @@ utoa_append: {
__b1: __b1:
// while (value >= sub) // while (value >= sub)
// [96] if(utoa_append::value#2>=utoa_append::sub#0) goto utoa_append::@2 -- vwuz1_ge_vwuz2_then_la1 // [96] if(utoa_append::value#2>=utoa_append::sub#0) goto utoa_append::@2 -- vwuz1_ge_vwuz2_then_la1
lda.z sub+1 lda.z value+1
cmp.z value+1 cmp.z sub+1
bne !+ bcc !+
lda.z sub bne __b2
cmp.z value lda.z value
beq __b2 cmp.z sub
bcs __b2
!: !:
bcc __b2
// utoa_append::@3 // utoa_append::@3
// *buffer = DIGITS[digit] // *buffer = DIGITS[digit]
// [97] *utoa_append::buffer#0 = DIGITS[utoa_append::digit#2] -- _deref_pbuz1=pbuc1_derefidx_vbuxx // [97] *utoa_append::buffer#0 = DIGITS[utoa_append::digit#2] -- _deref_pbuz1=pbuc1_derefidx_vbuxx

View File

@@ -59,14 +59,14 @@ main: {
tax tax
jsr mul8u jsr mul8u
// if(potential > mul8u(p, p)) // if(potential > mul8u(p, p))
lda.z potential+1 lda.z __0+1
cmp.z __0+1 cmp.z potential+1
bne !+ bcc !+
lda.z potential bne __b2
cmp.z __0 lda.z __0
beq __b2 cmp.z potential
bcs __b2
!: !:
bcc __b2
// test_last++; // test_last++;
inc.z test_last inc.z test_last
__b2: __b2:
@@ -348,13 +348,14 @@ utoa: {
// if (started || value >= digit_value) // if (started || value >= digit_value)
cpx #0 cpx #0
bne __b5 bne __b5
cmp.z value+1 lda.z value+1
bne !+ cmp.z digit_value+1
lda.z digit_value bcc !+
cmp.z value bne __b5
beq __b5 lda.z value
cmp.z digit_value
bcs __b5
!: !:
bcc __b5
__b4: __b4:
// for( char digit=0; digit<max_digits-1; digit++ ) // for( char digit=0; digit<max_digits-1; digit++ )
inc.z digit inc.z digit
@@ -417,14 +418,14 @@ utoa_append: {
ldx #0 ldx #0
__b1: __b1:
// while (value >= sub) // while (value >= sub)
lda.z sub+1 lda.z value+1
cmp.z value+1 cmp.z sub+1
bne !+ bcc !+
lda.z sub bne __b2
cmp.z value lda.z value
beq __b2 cmp.z sub
bcs __b2
!: !:
bcc __b2
// *buffer = DIGITS[digit] // *buffer = DIGITS[digit]
lda DIGITS,x lda DIGITS,x
ldy #0 ldy #0

View File

@@ -2578,14 +2578,14 @@ main: {
__b8: __b8:
// [9] main::$0 = mul8u::return#2 // [9] main::$0 = mul8u::return#2
// [10] if(potential#15<=main::$0) goto main::@2 -- vwuz1_le_vwuz2_then_la1 // [10] if(potential#15<=main::$0) goto main::@2 -- vwuz1_le_vwuz2_then_la1
lda.z potential+1 lda.z __0+1
cmp.z __0+1 cmp.z potential+1
bne !+ bcc !+
lda.z potential bne __b2_from___b8
cmp.z __0 lda.z __0
beq __b2_from___b8 cmp.z potential
bcs __b2_from___b8
!: !:
bcc __b2_from___b8
jmp __b7 jmp __b7
// main::@7 // main::@7
__b7: __b7:
@@ -3055,14 +3055,14 @@ utoa: {
// utoa::@7 // utoa::@7
__b7: __b7:
// [89] if(utoa::value#2>=utoa::digit_value#0) goto utoa::@5 -- vwuz1_ge_vwuz2_then_la1 // [89] if(utoa::value#2>=utoa::digit_value#0) goto utoa::@5 -- vwuz1_ge_vwuz2_then_la1
lda.z digit_value+1 lda.z value+1
cmp.z value+1 cmp.z digit_value+1
bne !+ bcc !+
lda.z digit_value bne __b5
cmp.z value lda.z value
beq __b5 cmp.z digit_value
bcs __b5
!: !:
bcc __b5
// [90] phi from utoa::@7 to utoa::@4 [phi:utoa::@7->utoa::@4] // [90] phi from utoa::@7 to utoa::@4 [phi:utoa::@7->utoa::@4]
__b4_from___b7: __b4_from___b7:
// [90] phi utoa::buffer#14 = utoa::buffer#11 [phi:utoa::@7->utoa::@4#0] -- register_copy // [90] phi utoa::buffer#14 = utoa::buffer#11 [phi:utoa::@7->utoa::@4#0] -- register_copy
@@ -3181,14 +3181,14 @@ utoa_append: {
// utoa_append::@1 // utoa_append::@1
__b1: __b1:
// [108] if(utoa_append::value#2>=utoa_append::sub#0) goto utoa_append::@2 -- vwuz1_ge_vwuz2_then_la1 // [108] if(utoa_append::value#2>=utoa_append::sub#0) goto utoa_append::@2 -- vwuz1_ge_vwuz2_then_la1
lda.z sub+1 lda.z value+1
cmp.z value+1 cmp.z sub+1
bne !+ bcc !+
lda.z sub bne __b2
cmp.z value lda.z value
beq __b2 cmp.z sub
bcs __b2
!: !:
bcc __b2
jmp __b3 jmp __b3
// utoa_append::@3 // utoa_append::@3
__b3: __b3:
@@ -3357,7 +3357,6 @@ Removing instruction jmp __b4
Removing instruction jmp __b1 Removing instruction jmp __b1
Succesful ASM optimization Pass5NextJumpElimination Succesful ASM optimization Pass5NextJumpElimination
Removing instruction lda #<0 Removing instruction lda #<0
Removing instruction lda.z digit_value+1
Succesful ASM optimization Pass5UnnecesaryLoadElimination Succesful ASM optimization Pass5UnnecesaryLoadElimination
Fixing long branch [126] bcc __b1 to bcs Fixing long branch [126] bcc __b1 to bcs
Fixing long branch [132] bcc __b1 to bcs Fixing long branch [132] bcc __b1 to bcs
@@ -3544,7 +3543,7 @@ zp[2]:19 [ utoa::digit_value#0 utoa_append::sub#0 ]
FINAL ASSEMBLER FINAL ASSEMBLER
Score: 139370 Score: 139670
// File Comments // File Comments
// Calculates the 1000 first primes // Calculates the 1000 first primes
@@ -3633,14 +3632,14 @@ main: {
// [9] main::$0 = mul8u::return#2 // [9] main::$0 = mul8u::return#2
// if(potential > mul8u(p, p)) // if(potential > mul8u(p, p))
// [10] if(potential#15<=main::$0) goto main::@2 -- vwuz1_le_vwuz2_then_la1 // [10] if(potential#15<=main::$0) goto main::@2 -- vwuz1_le_vwuz2_then_la1
lda.z potential+1 lda.z __0+1
cmp.z __0+1 cmp.z potential+1
bne !+ bcc !+
lda.z potential bne __b2
cmp.z __0 lda.z __0
beq __b2 cmp.z potential
bcs __b2
!: !:
bcc __b2
// main::@7 // main::@7
// test_last++; // test_last++;
// [11] test_last#1 = ++ test_last#13 -- vbuz1=_inc_vbuz1 // [11] test_last#1 = ++ test_last#13 -- vbuz1=_inc_vbuz1
@@ -4083,13 +4082,14 @@ utoa: {
bne __b5 bne __b5
// utoa::@7 // utoa::@7
// [89] if(utoa::value#2>=utoa::digit_value#0) goto utoa::@5 -- vwuz1_ge_vwuz2_then_la1 // [89] if(utoa::value#2>=utoa::digit_value#0) goto utoa::@5 -- vwuz1_ge_vwuz2_then_la1
cmp.z value+1 lda.z value+1
bne !+ cmp.z digit_value+1
lda.z digit_value bcc !+
cmp.z value bne __b5
beq __b5 lda.z value
cmp.z digit_value
bcs __b5
!: !:
bcc __b5
// [90] phi from utoa::@7 to utoa::@4 [phi:utoa::@7->utoa::@4] // [90] phi from utoa::@7 to utoa::@4 [phi:utoa::@7->utoa::@4]
// [90] phi utoa::buffer#14 = utoa::buffer#11 [phi:utoa::@7->utoa::@4#0] -- register_copy // [90] phi utoa::buffer#14 = utoa::buffer#11 [phi:utoa::@7->utoa::@4#0] -- register_copy
// [90] phi utoa::started#4 = utoa::started#2 [phi:utoa::@7->utoa::@4#1] -- register_copy // [90] phi utoa::started#4 = utoa::started#2 [phi:utoa::@7->utoa::@4#1] -- register_copy
@@ -4201,14 +4201,14 @@ utoa_append: {
__b1: __b1:
// while (value >= sub) // while (value >= sub)
// [108] if(utoa_append::value#2>=utoa_append::sub#0) goto utoa_append::@2 -- vwuz1_ge_vwuz2_then_la1 // [108] if(utoa_append::value#2>=utoa_append::sub#0) goto utoa_append::@2 -- vwuz1_ge_vwuz2_then_la1
lda.z sub+1 lda.z value+1
cmp.z value+1 cmp.z sub+1
bne !+ bcc !+
lda.z sub bne __b2
cmp.z value lda.z value
beq __b2 cmp.z sub
bcs __b2
!: !:
bcc __b2
// utoa_append::@3 // utoa_append::@3
// *buffer = DIGITS[digit] // *buffer = DIGITS[digit]
// [109] *utoa_append::buffer#0 = DIGITS[utoa_append::digit#2] -- _deref_pbuz1=pbuc1_derefidx_vbuxx // [109] *utoa_append::buffer#0 = DIGITS[utoa_append::digit#2] -- _deref_pbuz1=pbuc1_derefidx_vbuxx

View File

@@ -8,6 +8,7 @@
.segmentdef Data [startAfter="Code"] .segmentdef Data [startAfter="Code"]
.segment Basic .segment Basic
:BasicUpstart(main) :BasicUpstart(main)
.const STACK_BASE = $103
.label screen = 2 .label screen = 2
.segment Code .segment Code
main: { main: {

View File

@@ -1,6 +1,11 @@
Added struct type cast to parameter value list call printf_string((void (*)(char)) 0, main::name, (struct printf_format_string){ 0, 0 }) Setting inferred __stackcall on procedure affected by address-of __stackcall void cputc(char x) caused by statement call printf_str(&cputc, "Hello, I am ")
Setting inferred __stackcall on procedure affected by address-of __stackcall void cputc(char x) caused by statement call printf_string(&cputc, main::name, { 0, 0 })
Setting inferred __stackcall on procedure affected by address-of __stackcall void cputc(char x) caused by statement call printf_str(&cputc, ". who are you?")
Adding parameter assignment in __stackcall procedure cputc::x = param(cputc::x)
Added struct type cast to parameter value list call printf_string(&cputc, main::name, (struct printf_format_string){ 0, 0 })
Inlined call call __init Inlined call call __init
Eliminating unused variable with no statement main::$0 Eliminating unused variable with no statement main::$0
Calling convention STACK_CALL replacing param(cputc::x) with stackidx(char,cputc::OFFSET_STACK_X)
CONTROL FLOW GRAPH SSA CONTROL FLOW GRAPH SSA
@@ -28,6 +33,14 @@ printf_str::@return: scope:[printf_str] from printf_str::@1
return return
to:@return to:@return
__stackcall void cputc(char x)
cputc: scope:[cputc] from
cputc::x#0 = stackidx(char,cputc::OFFSET_STACK_X)
to:cputc::@return
cputc::@return: scope:[cputc] from cputc
return
to:@return
void printf_string(void (*putc)(char) , char *str , char format_min_length , char format_justify_left) void printf_string(void (*putc)(char) , char *str , char format_min_length , char format_justify_left)
printf_string: scope:[printf_string] from main::@1 printf_string: scope:[printf_string] from main::@1
screen#22 = phi( main::@1/screen#4 ) screen#22 = phi( main::@1/screen#4 )
@@ -50,14 +63,14 @@ printf_string::@return: scope:[printf_string] from printf_string::@1
void main() void main()
main: scope:[main] from __start::@1 main: scope:[main] from __start::@1
screen#23 = phi( __start::@1/screen#24 ) screen#23 = phi( __start::@1/screen#24 )
printf_str::putc#1 = (void (*)(char)) 0 printf_str::putc#1 = &cputc
printf_str::str#2 = main::str printf_str::str#2 = main::str
call printf_str call printf_str
to:main::@1 to:main::@1
main::@1: scope:[main] from main main::@1: scope:[main] from main
screen#15 = phi( main/screen#1 ) screen#15 = phi( main/screen#1 )
screen#4 = screen#15 screen#4 = screen#15
printf_string::putc#0 = (void (*)(char)) 0 printf_string::putc#0 = &cputc
printf_string::str#0 = main::name printf_string::str#0 = main::name
printf_string::format_min_length#0 = 0 printf_string::format_min_length#0 = 0
printf_string::format_justify_left#0 = 0 printf_string::format_justify_left#0 = 0
@@ -66,7 +79,7 @@ main::@1: scope:[main] from main
main::@2: scope:[main] from main::@1 main::@2: scope:[main] from main::@1
screen#16 = phi( main::@1/screen#3 ) screen#16 = phi( main::@1/screen#3 )
screen#5 = screen#16 screen#5 = screen#16
printf_str::putc#2 = (void (*)(char)) 0 printf_str::putc#2 = &cputc
printf_str::str#3 = main::str1 printf_str::str#3 = main::str1
call printf_str call printf_str
to:main::@3 to:main::@3
@@ -101,7 +114,12 @@ __start::@return: scope:[__start] from __start::@2
to:@return to:@return
SYMBOL TABLE SSA SYMBOL TABLE SSA
__constant unsigned int STACK_BASE = $103
void __start() void __start()
__stackcall void cputc(char x)
__constant char cputc::OFFSET_STACK_X = 0
char cputc::x
char cputc::x#0
void main() void main()
__constant char *main::name = "Jesper" __constant char *main::name = "Jesper"
__constant char main::str[$d] = "Hello, I am " __constant char main::str[$d] = "Hello, I am "
@@ -188,27 +206,33 @@ Identical Phi Values screen#10 screen#17
Successful SSA optimization Pass2IdenticalPhiElimination Successful SSA optimization Pass2IdenticalPhiElimination
Simple Condition printf_str::$0 [3] if(0!=*printf_str::str#4) goto printf_str::@2 Simple Condition printf_str::$0 [3] if(0!=*printf_str::str#4) goto printf_str::@2
Successful SSA optimization Pass2ConditionalJumpSimplification Successful SSA optimization Pass2ConditionalJumpSimplification
Constant printf_str::putc#1 = (void (*)(char)) 0 Constant printf_str::putc#1 = &cputc
Constant printf_str::str#2 = main::str Constant printf_str::str#2 = main::str
Constant printf_string::putc#0 = (void (*)(char)) 0 Constant printf_string::putc#0 = &cputc
Constant printf_string::str#0 = main::name Constant printf_string::str#0 = main::name
Constant printf_string::format_min_length#0 = 0 Constant printf_string::format_min_length#0 = 0
Constant printf_string::format_justify_left#0 = 0 Constant printf_string::format_justify_left#0 = 0
Constant printf_str::putc#2 = (void (*)(char)) 0 Constant printf_str::putc#2 = &cputc
Constant printf_str::str#3 = main::str1 Constant printf_str::str#3 = main::str1
Constant screen#24 = (char *) 1024 Constant screen#24 = (char *) 1024
Successful SSA optimization Pass2ConstantIdentification Successful SSA optimization Pass2ConstantIdentification
Constant printf_str::putc#0 = printf_string::putc#0 Constant printf_str::putc#0 = printf_string::putc#0
Constant printf_str::str#1 = printf_string::str#0 Constant printf_str::str#1 = printf_string::str#0
Successful SSA optimization Pass2ConstantIdentification Successful SSA optimization Pass2ConstantIdentification
Eliminating unused variable cputc::x#0 and assignment [7] cputc::x#0 = stackidx(char,cputc::OFFSET_STACK_X)
Eliminating unused constant printf_str::putc#1 Eliminating unused constant printf_str::putc#1
Eliminating unused constant printf_str::putc#2 Eliminating unused constant printf_str::putc#2
Eliminating unused constant printf_str::putc#0 Eliminating unused constant printf_str::putc#0
Eliminating unused constant printf_string::format_min_length#0 Eliminating unused constant printf_string::format_min_length#0
Eliminating unused constant printf_string::format_justify_left#0 Eliminating unused constant printf_string::format_justify_left#0
Successful SSA optimization PassNEliminateUnusedVars Successful SSA optimization PassNEliminateUnusedVars
Eliminating unused constant cputc::OFFSET_STACK_X
Eliminating unused constant printf_string::putc#0 Eliminating unused constant printf_string::putc#0
Successful SSA optimization PassNEliminateUnusedVars Successful SSA optimization PassNEliminateUnusedVars
Removing unused procedure cputc
Removing unused procedure block cputc
Removing unused procedure block cputc::@return
Successful SSA optimization PassNEliminateEmptyProcedure
Removing unused procedure __start Removing unused procedure __start
Removing unused procedure block __start Removing unused procedure block __start
Removing unused procedure block __start::__init1 Removing unused procedure block __start::__init1
@@ -357,6 +381,7 @@ ASSEMBLER BEFORE OPTIMIZATION
.segment Basic .segment Basic
:BasicUpstart(main) :BasicUpstart(main)
// Global Constants & labels // Global Constants & labels
.const STACK_BASE = $103
.label screen = 2 .label screen = 2
.segment Code .segment Code
// main // main
@@ -505,6 +530,7 @@ Removing instruction __breturn:
Succesful ASM optimization Pass5UnusedLabelElimination Succesful ASM optimization Pass5UnusedLabelElimination
FINAL SYMBOL TABLE FINAL SYMBOL TABLE
__constant unsigned int STACK_BASE = $103
void main() void main()
__constant char *main::name = "Jesper" __constant char *main::name = "Jesper"
__constant char main::str[$d] = "Hello, I am " __constant char main::str[$d] = "Hello, I am "
@@ -546,6 +572,7 @@ Score: 617
.segment Basic .segment Basic
:BasicUpstart(main) :BasicUpstart(main)
// Global Constants & labels // Global Constants & labels
.const STACK_BASE = $103
.label screen = 2 .label screen = 2
.segment Code .segment Code
// main // main

View File

@@ -1,3 +1,4 @@
__constant unsigned int STACK_BASE = $103
void main() void main()
__constant char *main::name = "Jesper" __constant char *main::name = "Jesper"
__constant char main::str[$d] = "Hello, I am " __constant char main::str[$d] = "Hello, I am "

View File

@@ -8,6 +8,7 @@
.segmentdef Data [startAfter="Code"] .segmentdef Data [startAfter="Code"]
.segment Basic .segment Basic
:BasicUpstart(main) :BasicUpstart(main)
.const STACK_BASE = $103
.label screen = 4 .label screen = 4
.segment Code .segment Code
main: { main: {

View File

@@ -1,6 +1,11 @@
Added struct type cast to parameter value list call printf_uint((void (*)(char)) 0, main::pct, (struct printf_format_number){ 0, 0, 0, 0, 0, HEXADECIMAL }) Setting inferred __stackcall on procedure affected by address-of __stackcall void cputc(char x) caused by statement call printf_str(&cputc, "Commodore is ")
Setting inferred __stackcall on procedure affected by address-of __stackcall void cputc(char x) caused by statement call printf_uint(&cputc, main::pct, { 0, 0, 0, 0, 0, HEXADECIMAL })
Setting inferred __stackcall on procedure affected by address-of __stackcall void cputc(char x) caused by statement call printf_str(&cputc, " cool")
Adding parameter assignment in __stackcall procedure cputc::x = param(cputc::x)
Added struct type cast to parameter value list call printf_uint(&cputc, main::pct, (struct printf_format_number){ 0, 0, 0, 0, 0, HEXADECIMAL })
Inlined call call __init Inlined call call __init
Eliminating unused variable with no statement main::$0 Eliminating unused variable with no statement main::$0
Calling convention STACK_CALL replacing param(cputc::x) with stackidx(char,cputc::OFFSET_STACK_X)
CONTROL FLOW GRAPH SSA CONTROL FLOW GRAPH SSA
@@ -55,17 +60,25 @@ printf_uint::@return: scope:[printf_uint] from printf_uint
return return
to:@return to:@return
__stackcall void cputc(char x)
cputc: scope:[cputc] from
cputc::x#0 = stackidx(char,cputc::OFFSET_STACK_X)
to:cputc::@return
cputc::@return: scope:[cputc] from cputc
return
to:@return
void main() void main()
main: scope:[main] from __start::@1 main: scope:[main] from __start::@1
screen#25 = phi( __start::@1/screen#26 ) screen#25 = phi( __start::@1/screen#26 )
printf_str::putc#0 = (void (*)(char)) 0 printf_str::putc#0 = &cputc
printf_str::str#1 = main::str printf_str::str#1 = main::str
call printf_str call printf_str
to:main::@1 to:main::@1
main::@1: scope:[main] from main main::@1: scope:[main] from main
screen#18 = phi( main/screen#1 ) screen#18 = phi( main/screen#1 )
screen#7 = screen#18 screen#7 = screen#18
printf_uint::putc#0 = (void (*)(char)) 0 printf_uint::putc#0 = &cputc
printf_uint::uvalue#0 = main::pct printf_uint::uvalue#0 = main::pct
printf_uint::format_min_length#0 = 0 printf_uint::format_min_length#0 = 0
printf_uint::format_justify_left#0 = 0 printf_uint::format_justify_left#0 = 0
@@ -78,7 +91,7 @@ main::@1: scope:[main] from main
main::@2: scope:[main] from main::@1 main::@2: scope:[main] from main::@1
screen#19 = phi( main::@1/screen#6 ) screen#19 = phi( main::@1/screen#6 )
screen#8 = screen#19 screen#8 = screen#19
printf_str::putc#1 = (void (*)(char)) 0 printf_str::putc#1 = &cputc
printf_str::str#2 = main::str1 printf_str::str#2 = main::str1
call printf_str call printf_str
to:main::@3 to:main::@3
@@ -118,7 +131,12 @@ __constant char RADIX::BINARY = 2
__constant char RADIX::DECIMAL = $a __constant char RADIX::DECIMAL = $a
__constant char RADIX::HEXADECIMAL = $10 __constant char RADIX::HEXADECIMAL = $10
__constant char RADIX::OCTAL = 8 __constant char RADIX::OCTAL = 8
__constant unsigned int STACK_BASE = $103
void __start() void __start()
__stackcall void cputc(char x)
__constant char cputc::OFFSET_STACK_X = 0
char cputc::x
char cputc::x#0
void main() void main()
__constant unsigned int main::pct = $156 __constant unsigned int main::pct = $156
__constant char main::str[$e] = "Commodore is " __constant char main::str[$e] = "Commodore is "
@@ -235,9 +253,9 @@ Identical Phi Values screen#12 screen#10
Successful SSA optimization Pass2IdenticalPhiElimination Successful SSA optimization Pass2IdenticalPhiElimination
Simple Condition printf_str::$0 [3] if(0!=*printf_str::str#3) goto printf_str::@2 Simple Condition printf_str::$0 [3] if(0!=*printf_str::str#3) goto printf_str::@2
Successful SSA optimization Pass2ConditionalJumpSimplification Successful SSA optimization Pass2ConditionalJumpSimplification
Constant printf_str::putc#0 = (void (*)(char)) 0 Constant printf_str::putc#0 = &cputc
Constant printf_str::str#1 = main::str Constant printf_str::str#1 = main::str
Constant printf_uint::putc#0 = (void (*)(char)) 0 Constant printf_uint::putc#0 = &cputc
Constant printf_uint::uvalue#0 = main::pct Constant printf_uint::uvalue#0 = main::pct
Constant printf_uint::format_min_length#0 = 0 Constant printf_uint::format_min_length#0 = 0
Constant printf_uint::format_justify_left#0 = 0 Constant printf_uint::format_justify_left#0 = 0
@@ -245,10 +263,11 @@ Constant printf_uint::format_sign_always#0 = 0
Constant printf_uint::format_zero_padding#0 = 0 Constant printf_uint::format_zero_padding#0 = 0
Constant printf_uint::format_upper_case#0 = 0 Constant printf_uint::format_upper_case#0 = 0
Constant printf_uint::format_radix#0 = HEXADECIMAL Constant printf_uint::format_radix#0 = HEXADECIMAL
Constant printf_str::putc#1 = (void (*)(char)) 0 Constant printf_str::putc#1 = &cputc
Constant printf_str::str#2 = main::str1 Constant printf_str::str#2 = main::str1
Constant screen#11 = (char *) 1024 Constant screen#11 = (char *) 1024
Successful SSA optimization Pass2ConstantIdentification Successful SSA optimization Pass2ConstantIdentification
Eliminating unused variable cputc::x#0 and assignment [24] cputc::x#0 = stackidx(char,cputc::OFFSET_STACK_X)
Eliminating unused constant printf_str::putc#0 Eliminating unused constant printf_str::putc#0
Eliminating unused constant printf_str::putc#1 Eliminating unused constant printf_str::putc#1
Eliminating unused constant printf_uint::putc#0 Eliminating unused constant printf_uint::putc#0
@@ -260,7 +279,12 @@ Eliminating unused constant printf_uint::format_upper_case#0
Eliminating unused constant printf_uint::format_radix#0 Eliminating unused constant printf_uint::format_radix#0
Successful SSA optimization PassNEliminateUnusedVars Successful SSA optimization PassNEliminateUnusedVars
Eliminating unused constant HEXADECIMAL Eliminating unused constant HEXADECIMAL
Eliminating unused constant cputc::OFFSET_STACK_X
Successful SSA optimization PassNEliminateUnusedVars Successful SSA optimization PassNEliminateUnusedVars
Removing unused procedure cputc
Removing unused procedure block cputc
Removing unused procedure block cputc::@return
Successful SSA optimization PassNEliminateEmptyProcedure
Removing unused procedure __start Removing unused procedure __start
Removing unused procedure block __start Removing unused procedure block __start
Removing unused procedure block __start::__init1 Removing unused procedure block __start::__init1
@@ -483,6 +507,7 @@ ASSEMBLER BEFORE OPTIMIZATION
.segment Basic .segment Basic
:BasicUpstart(main) :BasicUpstart(main)
// Global Constants & labels // Global Constants & labels
.const STACK_BASE = $103
.label screen = 4 .label screen = 4
.segment Code .segment Code
// main // main
@@ -658,6 +683,7 @@ __constant char RADIX::BINARY = 2
__constant char RADIX::DECIMAL = $a __constant char RADIX::DECIMAL = $a
__constant char RADIX::HEXADECIMAL = $10 __constant char RADIX::HEXADECIMAL = $10
__constant char RADIX::OCTAL = 8 __constant char RADIX::OCTAL = 8
__constant unsigned int STACK_BASE = $103
void main() void main()
__constant unsigned int main::pct = $156 __constant unsigned int main::pct = $156
__constant char main::str[$e] = "Commodore is " __constant char main::str[$e] = "Commodore is "
@@ -708,6 +734,7 @@ Score: 697
.segment Basic .segment Basic
:BasicUpstart(main) :BasicUpstart(main)
// Global Constants & labels // Global Constants & labels
.const STACK_BASE = $103
.label screen = 4 .label screen = 4
.segment Code .segment Code
// main // main

View File

@@ -2,6 +2,7 @@ __constant char RADIX::BINARY = 2
__constant char RADIX::DECIMAL = $a __constant char RADIX::DECIMAL = $a
__constant char RADIX::HEXADECIMAL = $10 __constant char RADIX::HEXADECIMAL = $10
__constant char RADIX::OCTAL = 8 __constant char RADIX::OCTAL = 8
__constant unsigned int STACK_BASE = $103
void main() void main()
__constant unsigned int main::pct = $156 __constant unsigned int main::pct = $156
__constant char main::str[$e] = "Commodore is " __constant char main::str[$e] = "Commodore is "

File diff suppressed because it is too large Load Diff

File diff suppressed because it is too large Load Diff

File diff suppressed because one or more lines are too long

View File

@@ -1,442 +1,463 @@
constant byte BINARY = 2 __constant char BINARY = 2
constant byte* const COLORRAM = (byte*) 55296 __constant char * const COLORRAM = (char *) 55296
constant byte DECIMAL = $a __constant char DECIMAL = $a
constant byte* const DEFAULT_SCREEN = (byte*) 1024 __constant char * const DEFAULT_SCREEN = (char *) 1024
constant byte* DIGITS[] = "0123456789abcdef"z __constant char DIGITS[] = "0123456789abcdef"z
constant byte HEXADECIMAL = $10 __constant char HEXADECIMAL = $10
constant const byte LIGHT_BLUE = $e __constant const char LIGHT_BLUE = $e
constant byte OCTAL = 8 __constant char OCTAL = 8
constant byte OFFSET_STRUCT_PRINTF_BUFFER_NUMBER_DIGITS = 1 __constant char OFFSET_STRUCT_PRINTF_BUFFER_NUMBER_DIGITS = 1
constant byte RADIX::BINARY = 2 __constant char RADIX::BINARY = 2
constant byte RADIX::DECIMAL = $a __constant char RADIX::DECIMAL = $a
constant byte RADIX::HEXADECIMAL = $10 __constant char RADIX::HEXADECIMAL = $10
constant byte RADIX::OCTAL = 8 __constant char RADIX::OCTAL = 8
constant word* RADIX_BINARY_VALUES[] = { $8000, $4000, $2000, $1000, $800, $400, $200, $100, $80, $40, $20, $10, 8, 4, 2 } __constant unsigned int RADIX_BINARY_VALUES[] = { $8000, $4000, $2000, $1000, $800, $400, $200, $100, $80, $40, $20, $10, 8, 4, 2 }
constant word* RADIX_DECIMAL_VALUES[] = { $2710, $3e8, $64, $a } __constant unsigned int RADIX_DECIMAL_VALUES[] = { $2710, $3e8, $64, $a }
constant byte* RADIX_DECIMAL_VALUES_CHAR[] = { $64, $a } __constant char RADIX_DECIMAL_VALUES_CHAR[] = { $64, $a }
constant dword* RADIX_DECIMAL_VALUES_LONG[] = { $3b9aca00, $5f5e100, $989680, $f4240, $186a0, $2710, $3e8, $64, $a } __constant unsigned long RADIX_DECIMAL_VALUES_LONG[] = { $3b9aca00, $5f5e100, $989680, $f4240, $186a0, $2710, $3e8, $64, $a }
constant word* RADIX_HEXADECIMAL_VALUES[] = { $1000, $100, $10 } __constant unsigned int RADIX_HEXADECIMAL_VALUES[] = { $1000, $100, $10 }
constant word* RADIX_OCTAL_VALUES[] = { $8000, $1000, $200, $40, 8 } __constant unsigned int RADIX_OCTAL_VALUES[] = { $8000, $1000, $200, $40, 8 }
constant byte SIZEOF_STRUCT_PRINTF_BUFFER_NUMBER = $c __constant char SIZEOF_STRUCT_PRINTF_BUFFER_NUMBER = $c
__constant unsigned int STACK_BASE = $103
void __start() void __start()
void clrscr() void clrscr()
byte clrscr::c char clrscr::c
byte clrscr::c#1 reg byte y 20002.0 char clrscr::c#1 // reg byte y 20002.0
byte clrscr::c#2 reg byte y 12501.25 char clrscr::c#2 // reg byte y 12501.25
byte clrscr::l char clrscr::l
byte clrscr::l#1 reg byte x 2002.0 char clrscr::l#1 // reg byte x 2002.0
byte clrscr::l#2 reg byte x 333.6666666666667 char clrscr::l#2 // reg byte x 333.6666666666667
byte* clrscr::line_cols char *clrscr::line_cols
byte* clrscr::line_cols#1 line_cols zp[2]:2 1001.0 char *clrscr::line_cols#1 // line_cols zp[2]:13 1001.0
byte* clrscr::line_cols#5 line_cols zp[2]:2 1500.375 char *clrscr::line_cols#5 // line_cols zp[2]:13 1500.375
byte* clrscr::line_text char *clrscr::line_text
byte* clrscr::line_text#1 line_text zp[2]:8 667.3333333333334 char *clrscr::line_text#1 // line_text zp[2]:6 667.3333333333334
byte* clrscr::line_text#5 line_text zp[2]:8 1714.7142857142858 char *clrscr::line_text#5 // line_text zp[2]:6 1714.7142857142858
void conio_c64_init() void conio_c64_init()
constant byte* const conio_c64_init::BASIC_CURSOR_LINE = (byte*) 214 __constant char * const conio_c64_init::BASIC_CURSOR_LINE = (char *) 214
byte conio_c64_init::line char conio_c64_init::line
byte conio_c64_init::line#0 reg byte x 11.0 char conio_c64_init::line#0 // reg byte x 11.0
byte conio_c64_init::line#2 reg byte x 22.0 char conio_c64_init::line#2 // reg byte x 22.0
byte conio_cursor_x loadstore zp[1]:17 90910.36363636363 __loadstore char conio_cursor_x // zp[1]:21 50.294117647058826
byte conio_cursor_y loadstore zp[1]:18 1767956.9558011051 __loadstore char conio_cursor_y // zp[1]:22 644.1800000000001
byte* conio_line_color loadstore zp[2]:21 1234638.039106145 __loadstore char *conio_line_color // zp[2]:25 464.77083333333326
byte* conio_line_text loadstore zp[2]:19 1227778.9388888888 __loadstore char *conio_line_text // zp[2]:23 455.28571428571433
void cputc(byte cputc::c) __stackcall void cputc(char c)
byte cputc::c __constant char cputc::OFFSET_STACK_C = 0
byte cputc::c#0 reg byte a 200002.0 char cputc::c
byte cputc::c#1 reg byte a 200002.0 char cputc::c#0 // reg byte a 151.5
byte cputc::c#2 reg byte a 2002.0
byte cputc::c#3 reg byte a 22.0
byte cputc::c#5 reg byte a 1100508.0
void cputln() void cputln()
void cputs(const byte* cputs::s)
byte cputs::c
byte cputs::c#1 reg byte a 100001.0
const byte* cputs::s
const byte* cputs::s#0 s zp[2]:8 50000.5
const byte* cputs::s#20 s zp[2]:8 155002.0
const byte* cputs::s#21 s zp[2]:8 10001.0
void cscroll() void cscroll()
void gotoxy(byte gotoxy::x , byte gotoxy::y) void gotoxy(char x , char y)
byte*~ gotoxy::$5 zp[2]:28 202.0 char *gotoxy::$5 // zp[2]:32 202.0
byte*~ gotoxy::$6 zp[2]:24 202.0 char *gotoxy::$6 // zp[2]:28 202.0
word~ gotoxy::$7 zp[2]:24 151.5 unsigned int gotoxy::$7 // zp[2]:28 151.5
word~ gotoxy::$8 zp[2]:26 202.0 unsigned int gotoxy::$8 // zp[2]:30 202.0
word~ gotoxy::$9 zp[2]:24 202.0 unsigned int gotoxy::$9 // zp[2]:28 202.0
word gotoxy::line_offset unsigned int gotoxy::line_offset
word gotoxy::line_offset#0 line_offset zp[2]:24 101.0 unsigned int gotoxy::line_offset#0 // line_offset zp[2]:28 101.0
byte gotoxy::x char gotoxy::x
constant byte gotoxy::x#2 x = 0 __constant char gotoxy::x#2 = 0 // x
byte gotoxy::y char gotoxy::y
byte gotoxy::y#2 reg byte x 71.0 char gotoxy::y#2 // reg byte x 71.0
byte gotoxy::y#4 reg byte x 67.33333333333333 char gotoxy::y#4 // reg byte x 67.33333333333333
void main() void main()
volatile byte main::c loadstore zp[1]:23 11.0 __loadstore volatile char main::c // zp[1]:27 11.0
constant byte* main::s[9] = "A char: " __constant char main::s[9] = "A char: "
constant byte* main::s1[2] = " __constant char main::s1[2] = "
" "
constant byte* main::s10[$f] = "A signed int: " __constant char main::s10[$f] = "A signed int: "
constant byte* main::s12[$12] = "An unsigned int: " __constant char main::s12[$12] = "An unsigned int: "
constant byte* main::s14[$10] = "A signed long: " __constant char main::s14[$10] = "A signed long: "
constant byte* main::s16[$13] = "An unsigned long: " __constant char main::s16[$13] = "An unsigned long: "
constant byte* main::s2[$c] = "A pointer: " __constant char main::s2[$c] = "A pointer: "
constant byte* main::s4[$c] = "A percent: " __constant char main::s4[$c] = "A percent: "
constant byte* main::s6[$10] = "A signed char: " __constant char main::s6[$10] = "A signed char: "
constant byte* main::s8[$13] = "An unsigned char: " __constant char main::s8[$13] = "An unsigned char: "
constant signed byte main::sc = -$c __constant signed char main::sc = -$c
constant signed word main::si = -$4d2 __constant int main::si = -$4d2
constant signed dword main::sl = -$1e240 __constant long main::sl = -$1e240
constant byte main::uc = $22 __constant char main::uc = $22
constant word main::ui = $162e __constant unsigned int main::ui = $162e
constant dword main::ul = $8aa52 __constant unsigned long main::ul = $8aa52
void* memcpy(void* memcpy::destination , void* memcpy::source , word memcpy::num) void * memcpy(void *destination , void *source , unsigned int num)
void* memcpy::destination void *memcpy::destination
void* memcpy::destination#2 destination zp[2]:39 void *memcpy::destination#2 // destination zp[2]:43
byte* memcpy::dst char *memcpy::dst
byte* memcpy::dst#1 dst zp[2]:39 1.00000000001E11 char *memcpy::dst#1 // dst zp[2]:43 1000001.0
byte* memcpy::dst#2 dst zp[2]:39 1.0033333333466667E11 char *memcpy::dst#2 // dst zp[2]:43 1033334.6666666667
byte* memcpy::dst#4 dst zp[2]:39 2.000000002E9 char *memcpy::dst#4 // dst zp[2]:43 200002.0
word memcpy::num unsigned int memcpy::num
void* memcpy::return void *memcpy::return
void* memcpy::source void *memcpy::source
void* memcpy::source#2 source zp[2]:30 void *memcpy::source#2 // source zp[2]:15
byte* memcpy::src char *memcpy::src
byte* memcpy::src#1 src zp[2]:30 2.00000000002E11 char *memcpy::src#1 // src zp[2]:15 2000002.0
byte* memcpy::src#2 src zp[2]:30 1.0025000000125E11 char *memcpy::src#2 // src zp[2]:15 1025001.25
byte* memcpy::src#4 src zp[2]:30 1.000000001E9 char *memcpy::src#4 // src zp[2]:15 100001.0
byte* memcpy::src_end char *memcpy::src_end
byte* memcpy::src_end#0 src_end zp[2]:37 1.262500000025E10 char *memcpy::src_end#0 // src_end zp[2]:41 137500.25
void* memset(void* memset::str , byte memset::c , word memset::num) void * memset(void *str , char c , unsigned int num)
byte memset::c char memset::c
byte memset::c#4 reg byte x 1.4285714285857143E10 char memset::c#4 // reg byte x 142857.2857142857
byte* memset::dst char *memset::dst
byte* memset::dst#1 dst zp[2]:30 2.00000000002E11 char *memset::dst#1 // dst zp[2]:15 2000002.0
byte* memset::dst#2 dst zp[2]:30 1.3366666666833334E11 char *memset::dst#2 // dst zp[2]:15 1366668.3333333335
byte* memset::dst#4 dst zp[2]:30 2.000000002E9 char *memset::dst#4 // dst zp[2]:15 200002.0
byte* memset::end char *memset::end
byte* memset::end#0 end zp[2]:39 1.6833333333666668E10 char *memset::end#0 // end zp[2]:43 183333.6666666667
word memset::num unsigned int memset::num
void* memset::return void *memset::return
void* memset::str void *memset::str
void* memset::str#3 str zp[2]:30 void *memset::str#3 // str zp[2]:15
struct printf_buffer_number printf_buffer loadstore mem[12] = {} __loadstore struct printf_buffer_number printf_buffer = {} // mem[12]
void printf_number_buffer(byte printf_number_buffer::buffer_sign , byte* printf_number_buffer::buffer_digits , byte printf_number_buffer::format_min_length , byte printf_number_buffer::format_justify_left , byte printf_number_buffer::format_sign_always , byte printf_number_buffer::format_zero_padding , byte printf_number_buffer::format_upper_case , byte printf_number_buffer::format_radix) void printf_number_buffer(void (*putc)(char) , char buffer_sign , char *buffer_digits , char format_min_length , char format_justify_left , char format_sign_always , char format_zero_padding , char format_upper_case , char format_radix)
word~ printf_number_buffer::$19 zp[2]:30 1001.0 unsigned int printf_number_buffer::$19 // zp[2]:34 1001.0
struct printf_buffer_number printf_number_buffer::buffer struct printf_buffer_number printf_number_buffer::buffer
byte* printf_number_buffer::buffer_digits char *printf_number_buffer::buffer_digits
byte printf_number_buffer::buffer_sign char printf_number_buffer::buffer_sign
byte printf_number_buffer::buffer_sign#0 buffer_sign zp[1]:6 202.0 char printf_number_buffer::buffer_sign#0 // buffer_sign zp[1]:4 202.0
byte printf_number_buffer::buffer_sign#1 buffer_sign zp[1]:6 202.0 char printf_number_buffer::buffer_sign#1 // buffer_sign zp[1]:4 202.0
byte printf_number_buffer::buffer_sign#10 buffer_sign zp[1]:6 180.45 char printf_number_buffer::buffer_sign#10 // buffer_sign zp[1]:4 171.85714285714283
byte printf_number_buffer::buffer_sign#2 buffer_sign zp[1]:6 202.0 char printf_number_buffer::buffer_sign#2 // buffer_sign zp[1]:4 202.0
byte printf_number_buffer::buffer_sign#3 buffer_sign zp[1]:6 202.0 char printf_number_buffer::buffer_sign#3 // buffer_sign zp[1]:4 202.0
byte printf_number_buffer::buffer_sign#4 buffer_sign zp[1]:6 202.0 char printf_number_buffer::buffer_sign#4 // buffer_sign zp[1]:4 202.0
byte printf_number_buffer::buffer_sign#5 buffer_sign zp[1]:6 202.0 char printf_number_buffer::buffer_sign#5 // buffer_sign zp[1]:4 202.0
struct printf_format_number printf_number_buffer::format struct printf_format_number printf_number_buffer::format
byte printf_number_buffer::format_justify_left char printf_number_buffer::format_justify_left
byte printf_number_buffer::format_justify_left#10 format_justify_left zp[1]:4 64.58064516129032 char printf_number_buffer::format_justify_left#10 // format_justify_left zp[1]:2 60.666666666666664
byte printf_number_buffer::format_min_length char printf_number_buffer::format_min_length
byte printf_number_buffer::format_min_length#10 reg byte x 100.1 char printf_number_buffer::format_min_length#10 // reg byte x 100.1
byte printf_number_buffer::format_radix char printf_number_buffer::format_radix
byte printf_number_buffer::format_sign_always char printf_number_buffer::format_sign_always
byte printf_number_buffer::format_upper_case char printf_number_buffer::format_upper_case
byte printf_number_buffer::format_upper_case#10 format_upper_case zp[1]:7 38.5 char printf_number_buffer::format_upper_case#10 // format_upper_case zp[1]:5 35.75
byte printf_number_buffer::format_zero_padding char printf_number_buffer::format_zero_padding
byte printf_number_buffer::format_zero_padding#10 format_zero_padding zp[1]:5 93.84375 char printf_number_buffer::format_zero_padding#10 // format_zero_padding zp[1]:3 88.32352941176471
signed byte printf_number_buffer::len signed char printf_number_buffer::len
signed byte printf_number_buffer::len#0 reg byte y 1501.5 signed char printf_number_buffer::len#0 // reg byte y 1501.5
signed byte printf_number_buffer::len#1 reg byte y 2002.0 signed char printf_number_buffer::len#1 // reg byte y 2002.0
signed byte printf_number_buffer::len#2 reg byte y 3003.0 signed char printf_number_buffer::len#2 // reg byte y 3003.0
signed byte printf_number_buffer::padding signed char printf_number_buffer::padding
signed byte printf_number_buffer::padding#1 padding zp[1]:10 1001.0 signed char printf_number_buffer::padding#1 // padding zp[1]:8 1001.0
signed byte printf_number_buffer::padding#10 padding zp[1]:10 190.66666666666666 signed char printf_number_buffer::padding#10 // padding zp[1]:8 166.83333333333334
void printf_padding(byte printf_padding::pad , byte printf_padding::length) void (*printf_number_buffer::putc)(char)
byte printf_padding::i void (*printf_number_buffer::putc#10)(char) // putc zp[2]:6 111.22222222222223
byte printf_padding::i#1 i zp[1]:16 200002.0 void printf_padding(void (*putc)(char) , char pad , char length)
byte printf_padding::i#2 i zp[1]:16 75000.75 char printf_padding::i
byte printf_padding::length char printf_padding::i#1 // i zp[1]:18 200002.0
byte printf_padding::length#0 length zp[1]:32 2002.0 char printf_padding::i#2 // i zp[1]:18 100001.0
byte printf_padding::length#1 length zp[1]:32 2002.0 char printf_padding::length
byte printf_padding::length#2 length zp[1]:32 2002.0 char printf_padding::length#0 // length zp[1]:36 2002.0
byte printf_padding::length#4 length zp[1]:32 17167.333333333332 char printf_padding::length#1 // length zp[1]:36 2002.0
byte printf_padding::pad char printf_padding::length#2 // length zp[1]:36 2002.0
byte printf_padding::pad#5 pad zp[1]:15 16666.833333333332 char printf_padding::length#4 // length zp[1]:36 20600.8
void printf_schar(signed byte printf_schar::value , byte printf_schar::format_min_length , byte printf_schar::format_justify_left , byte printf_schar::format_sign_always , byte printf_schar::format_zero_padding , byte printf_schar::format_upper_case , byte printf_schar::format_radix) char printf_padding::pad
char printf_padding::pad#5 // pad zp[1]:17 16666.833333333332
void (*printf_padding::putc)(char)
void (*printf_padding::putc#0)(char) // putc zp[2]:6 1001.0
void (*printf_padding::putc#1)(char) // putc zp[2]:6 1001.0
void (*printf_padding::putc#2)(char) // putc zp[2]:6 1001.0
void (*printf_padding::putc#5)(char) // putc zp[2]:6 30030.0
void printf_schar(void (*putc)(char) , signed char value , char format_min_length , char format_justify_left , char format_sign_always , char format_zero_padding , char format_upper_case , char format_radix)
struct printf_format_number printf_schar::format struct printf_format_number printf_schar::format
byte printf_schar::format_justify_left char printf_schar::format_justify_left
constant byte printf_schar::format_justify_left#0 format_justify_left = 0 __constant char printf_schar::format_justify_left#0 = 0 // format_justify_left
byte printf_schar::format_min_length char printf_schar::format_min_length
constant byte printf_schar::format_min_length#0 format_min_length = 0 __constant char printf_schar::format_min_length#0 = 0 // format_min_length
byte printf_schar::format_radix char printf_schar::format_radix
byte printf_schar::format_sign_always char printf_schar::format_sign_always
byte printf_schar::format_upper_case char printf_schar::format_upper_case
constant byte printf_schar::format_upper_case#0 format_upper_case = 0 __constant char printf_schar::format_upper_case#0 = 0 // format_upper_case
byte printf_schar::format_zero_padding char printf_schar::format_zero_padding
constant byte printf_schar::format_zero_padding#0 format_zero_padding = 0 __constant char printf_schar::format_zero_padding#0 = 0 // format_zero_padding
byte printf_schar::uvalue void (*printf_schar::putc)(char)
constant byte printf_schar::uvalue#0 uvalue = (byte)printf_schar::value#0 __constant void (*printf_schar::putc#0)(char) = &cputc // putc
signed byte printf_schar::value char printf_schar::uvalue
constant signed byte printf_schar::value#0 value = -main::sc __constant char printf_schar::uvalue#0 = (char)printf_schar::value#0 // uvalue
void printf_sint(signed word printf_sint::value , byte printf_sint::format_min_length , byte printf_sint::format_justify_left , byte printf_sint::format_sign_always , byte printf_sint::format_zero_padding , byte printf_sint::format_upper_case , byte printf_sint::format_radix) signed char printf_schar::value
__constant signed char printf_schar::value#0 = -main::sc // value
void printf_sint(void (*putc)(char) , int value , char format_min_length , char format_justify_left , char format_sign_always , char format_zero_padding , char format_upper_case , char format_radix)
struct printf_format_number printf_sint::format struct printf_format_number printf_sint::format
byte printf_sint::format_justify_left char printf_sint::format_justify_left
constant byte printf_sint::format_justify_left#0 format_justify_left = 0 __constant char printf_sint::format_justify_left#0 = 0 // format_justify_left
byte printf_sint::format_min_length char printf_sint::format_min_length
constant byte printf_sint::format_min_length#0 format_min_length = 0 __constant char printf_sint::format_min_length#0 = 0 // format_min_length
byte printf_sint::format_radix char printf_sint::format_radix
byte printf_sint::format_sign_always char printf_sint::format_sign_always
byte printf_sint::format_upper_case char printf_sint::format_upper_case
constant byte printf_sint::format_upper_case#0 format_upper_case = 0 __constant char printf_sint::format_upper_case#0 = 0 // format_upper_case
byte printf_sint::format_zero_padding char printf_sint::format_zero_padding
constant byte printf_sint::format_zero_padding#0 format_zero_padding = 0 __constant char printf_sint::format_zero_padding#0 = 0 // format_zero_padding
word printf_sint::uvalue void (*printf_sint::putc)(char)
constant word printf_sint::uvalue#0 uvalue = (word)printf_sint::value#0 __constant void (*printf_sint::putc#0)(char) = &cputc // putc
signed word printf_sint::value unsigned int printf_sint::uvalue
constant signed word printf_sint::value#0 value = -main::si __constant unsigned int printf_sint::uvalue#0 = (unsigned int)printf_sint::value#0 // uvalue
void printf_slong(signed dword printf_slong::value , byte printf_slong::format_min_length , byte printf_slong::format_justify_left , byte printf_slong::format_sign_always , byte printf_slong::format_zero_padding , byte printf_slong::format_upper_case , byte printf_slong::format_radix) int printf_sint::value
__constant int printf_sint::value#0 = -main::si // value
void printf_slong(void (*putc)(char) , long value , char format_min_length , char format_justify_left , char format_sign_always , char format_zero_padding , char format_upper_case , char format_radix)
struct printf_format_number printf_slong::format struct printf_format_number printf_slong::format
byte printf_slong::format_justify_left char printf_slong::format_justify_left
constant byte printf_slong::format_justify_left#0 format_justify_left = 0 __constant char printf_slong::format_justify_left#0 = 0 // format_justify_left
byte printf_slong::format_min_length char printf_slong::format_min_length
constant byte printf_slong::format_min_length#0 format_min_length = 0 __constant char printf_slong::format_min_length#0 = 0 // format_min_length
byte printf_slong::format_radix char printf_slong::format_radix
byte printf_slong::format_sign_always char printf_slong::format_sign_always
byte printf_slong::format_upper_case char printf_slong::format_upper_case
constant byte printf_slong::format_upper_case#0 format_upper_case = 0 __constant char printf_slong::format_upper_case#0 = 0 // format_upper_case
byte printf_slong::format_zero_padding char printf_slong::format_zero_padding
constant byte printf_slong::format_zero_padding#0 format_zero_padding = 0 __constant char printf_slong::format_zero_padding#0 = 0 // format_zero_padding
dword printf_slong::uvalue void (*printf_slong::putc)(char)
constant dword printf_slong::uvalue#0 uvalue = (dword)printf_slong::value#0 __constant void (*printf_slong::putc#0)(char) = &cputc // putc
signed dword printf_slong::value unsigned long printf_slong::uvalue
constant signed dword printf_slong::value#0 value = -main::sl __constant unsigned long printf_slong::uvalue#0 = (unsigned long)printf_slong::value#0 // uvalue
void printf_uchar(byte printf_uchar::uvalue , byte printf_uchar::format_min_length , byte printf_uchar::format_justify_left , byte printf_uchar::format_sign_always , byte printf_uchar::format_zero_padding , byte printf_uchar::format_upper_case , byte printf_uchar::format_radix) long printf_slong::value
__constant long printf_slong::value#0 = -main::sl // value
void printf_str(void (*putc)(char) , const char *s)
char printf_str::c
char printf_str::c#1 // reg byte a 100001.0
void (*printf_str::putc)(char)
void (*printf_str::putc#0)(char) // putc zp[2]:6 2002.0
void (*printf_str::putc#21)(char) // putc zp[2]:6 10010.0
const char *printf_str::s
const char *printf_str::s#0 // s zp[2]:13 100001.0
const char *printf_str::s#20 // s zp[2]:13 155002.0
const char *printf_str::s#21 // s zp[2]:13 10001.0
void printf_uchar(void (*putc)(char) , char uvalue , char format_min_length , char format_justify_left , char format_sign_always , char format_zero_padding , char format_upper_case , char format_radix)
struct printf_format_number printf_uchar::format struct printf_format_number printf_uchar::format
byte printf_uchar::format_justify_left char printf_uchar::format_justify_left
constant byte printf_uchar::format_justify_left#0 format_justify_left = 0 __constant char printf_uchar::format_justify_left#0 = 0 // format_justify_left
byte printf_uchar::format_min_length char printf_uchar::format_min_length
constant byte printf_uchar::format_min_length#0 format_min_length = 0 __constant char printf_uchar::format_min_length#0 = 0 // format_min_length
byte printf_uchar::format_radix char printf_uchar::format_radix
byte printf_uchar::format_sign_always char printf_uchar::format_sign_always
byte printf_uchar::format_upper_case char printf_uchar::format_upper_case
constant byte printf_uchar::format_upper_case#0 format_upper_case = 0 __constant char printf_uchar::format_upper_case#0 = 0 // format_upper_case
byte printf_uchar::format_zero_padding char printf_uchar::format_zero_padding
constant byte printf_uchar::format_zero_padding#0 format_zero_padding = 0 __constant char printf_uchar::format_zero_padding#0 = 0 // format_zero_padding
byte printf_uchar::uvalue void (*printf_uchar::putc)(char)
void printf_uint(word printf_uint::uvalue , byte printf_uint::format_min_length , byte printf_uint::format_justify_left , byte printf_uint::format_sign_always , byte printf_uint::format_zero_padding , byte printf_uint::format_upper_case , byte printf_uint::format_radix) __constant void (*printf_uchar::putc#0)(char) = &cputc // putc
char printf_uchar::uvalue
void printf_uint(void (*putc)(char) , unsigned int uvalue , char format_min_length , char format_justify_left , char format_sign_always , char format_zero_padding , char format_upper_case , char format_radix)
struct printf_format_number printf_uint::format struct printf_format_number printf_uint::format
byte printf_uint::format_justify_left char printf_uint::format_justify_left
byte printf_uint::format_min_length char printf_uint::format_min_length
byte printf_uint::format_radix char printf_uint::format_radix
byte printf_uint::format_radix#2 reg byte x 33.666666666666664 char printf_uint::format_radix#2 // reg byte x 33.666666666666664
byte printf_uint::format_sign_always char printf_uint::format_sign_always
byte printf_uint::format_upper_case char printf_uint::format_upper_case
byte printf_uint::format_zero_padding char printf_uint::format_zero_padding
word printf_uint::uvalue void (*printf_uint::putc)(char)
word printf_uint::uvalue#2 uvalue zp[2]:2 50.5 unsigned int printf_uint::uvalue
void printf_ulong(dword printf_ulong::uvalue , byte printf_ulong::format_min_length , byte printf_ulong::format_justify_left , byte printf_ulong::format_sign_always , byte printf_ulong::format_zero_padding , byte printf_ulong::format_upper_case , byte printf_ulong::format_radix) unsigned int printf_uint::uvalue#2 // uvalue zp[2]:6 50.5
void printf_ulong(void (*putc)(char) , unsigned long uvalue , char format_min_length , char format_justify_left , char format_sign_always , char format_zero_padding , char format_upper_case , char format_radix)
struct printf_format_number printf_ulong::format struct printf_format_number printf_ulong::format
byte printf_ulong::format_justify_left char printf_ulong::format_justify_left
constant byte printf_ulong::format_justify_left#0 format_justify_left = 0 __constant char printf_ulong::format_justify_left#0 = 0 // format_justify_left
byte printf_ulong::format_min_length char printf_ulong::format_min_length
constant byte printf_ulong::format_min_length#0 format_min_length = 0 __constant char printf_ulong::format_min_length#0 = 0 // format_min_length
byte printf_ulong::format_radix char printf_ulong::format_radix
byte printf_ulong::format_sign_always char printf_ulong::format_sign_always
byte printf_ulong::format_upper_case char printf_ulong::format_upper_case
constant byte printf_ulong::format_upper_case#0 format_upper_case = 0 __constant char printf_ulong::format_upper_case#0 = 0 // format_upper_case
byte printf_ulong::format_zero_padding char printf_ulong::format_zero_padding
constant byte printf_ulong::format_zero_padding#0 format_zero_padding = 0 __constant char printf_ulong::format_zero_padding#0 = 0 // format_zero_padding
dword printf_ulong::uvalue void (*printf_ulong::putc)(char)
word strlen(byte* strlen::str) __constant void (*printf_ulong::putc#0)(char) = &cputc // putc
word strlen::len unsigned long printf_ulong::uvalue
word strlen::len#1 len zp[2]:30 100001.0 unsigned int strlen(char *str)
word strlen::len#2 len zp[2]:30 50250.75 unsigned int strlen::len
word strlen::return unsigned int strlen::len#1 // len zp[2]:34 100001.0
word strlen::return#2 return zp[2]:30 2002.0 unsigned int strlen::len#2 // len zp[2]:34 50250.75
byte* strlen::str unsigned int strlen::return
byte* strlen::str#0 str zp[2]:37 200002.0 unsigned int strlen::return#2 // return zp[2]:34 2002.0
byte* strlen::str#2 str zp[2]:37 100001.0 char *strlen::str
byte* strupr(byte* strupr::str) char *strlen::str#0 // str zp[2]:19 200002.0
byte~ strupr::$0 reg byte a 200002.0 char *strlen::str#2 // str zp[2]:19 100001.0
byte* strupr::return char * strupr(char *str)
byte* strupr::src char strupr::$0 // reg byte a 200002.0
byte* strupr::src#1 src zp[2]:37 200002.0 char *strupr::return
byte* strupr::src#2 src zp[2]:37 71429.28571428571 char *strupr::src
byte* strupr::str char *strupr::src#1 // src zp[2]:19 200002.0
constant byte* strupr::str#0 str = (byte*)&printf_buffer+OFFSET_STRUCT_PRINTF_BUFFER_NUMBER_DIGITS char *strupr::src#2 // src zp[2]:19 71429.28571428571
byte toupper(byte toupper::ch) char *strupr::str
byte toupper::ch __constant char *strupr::str#0 = (char *)&printf_buffer+OFFSET_STRUCT_PRINTF_BUFFER_NUMBER_DIGITS // str
byte toupper::ch#0 reg byte a 1700002.0000000002 char toupper(char ch)
byte toupper::return char toupper::ch
byte toupper::return#0 reg byte a 2000002.0 char toupper::ch#0 // reg byte a 1700002.0000000002
byte toupper::return#2 reg byte a 1033334.6666666667 char toupper::return
byte toupper::return#3 reg byte a 200002.0 char toupper::return#0 // reg byte a 2000002.0
void uctoa(byte uctoa::value , byte* uctoa::buffer , byte uctoa::radix) char toupper::return#2 // reg byte a 1033334.6666666667
byte* uctoa::buffer char toupper::return#3 // reg byte a 200002.0
byte* uctoa::buffer#10 buffer zp[2]:8 3500.4999999999995 void uctoa(char value , char *buffer , char radix)
byte* uctoa::buffer#15 buffer zp[2]:8 15001.5 char *uctoa::buffer
byte* uctoa::buffer#3 buffer zp[2]:8 2002.0 char *uctoa::buffer#10 // buffer zp[2]:6 3500.4999999999995
byte* uctoa::buffer#4 buffer zp[2]:8 20002.0 char *uctoa::buffer#15 // buffer zp[2]:6 15001.5
byte uctoa::digit char *uctoa::buffer#3 // buffer zp[2]:6 2002.0
byte uctoa::digit#1 digit zp[1]:6 20002.0 char *uctoa::buffer#4 // buffer zp[2]:6 20002.0
byte uctoa::digit#2 digit zp[1]:6 3077.230769230769 char uctoa::digit
byte uctoa::digit_value char uctoa::digit#1 // digit zp[1]:4 20002.0
byte uctoa::digit_value#0 digit_value zp[1]:32 6000.6 char uctoa::digit#2 // digit zp[1]:4 3077.230769230769
byte* uctoa::digit_values char uctoa::digit_value
byte uctoa::max_digits char uctoa::digit_value#0 // digit_value zp[1]:36 6000.6
byte uctoa::radix char *uctoa::digit_values
byte uctoa::started char uctoa::max_digits
byte uctoa::started#2 started zp[1]:7 6000.6 char uctoa::radix
byte uctoa::started#4 started zp[1]:7 10001.0 char uctoa::started
byte uctoa::value char uctoa::started#2 // started zp[1]:5 6000.6
byte uctoa::value#0 reg byte x 10001.0 char uctoa::started#4 // started zp[1]:5 10001.0
byte uctoa::value#10 reg byte x 1001.0 char uctoa::value
byte uctoa::value#3 reg byte x 7000.999999999999 char uctoa::value#0 // reg byte x 10001.0
byte uctoa::value#7 reg byte x 15001.5 char uctoa::value#10 // reg byte x 1001.0
byte uctoa_append(byte* uctoa_append::buffer , byte uctoa_append::value , byte uctoa_append::sub) char uctoa::value#3 // reg byte x 7000.999999999999
byte* uctoa_append::buffer char uctoa::value#7 // reg byte x 15001.5
byte* uctoa_append::buffer#0 buffer zp[2]:8 13750.25 char uctoa_append(char *buffer , char value , char sub)
byte uctoa_append::digit char *uctoa_append::buffer
byte uctoa_append::digit#1 reg byte y 1.0000001E7 char *uctoa_append::buffer#0 // buffer zp[2]:6 13750.25
byte uctoa_append::digit#2 reg byte y 1.00500015E7 char uctoa_append::digit
byte uctoa_append::return char uctoa_append::digit#1 // reg byte y 1.0000001E7
byte uctoa_append::return#0 reg byte x 20002.0 char uctoa_append::digit#2 // reg byte y 1.00500015E7
byte uctoa_append::sub char uctoa_append::return
byte uctoa_append::sub#0 sub zp[1]:32 3335000.5 char uctoa_append::return#0 // reg byte x 20002.0
byte uctoa_append::value char uctoa_append::sub
byte uctoa_append::value#0 reg byte x 36667.33333333333 char uctoa_append::sub#0 // sub zp[1]:36 3335000.5
byte uctoa_append::value#1 reg byte x 2.0000002E7 char uctoa_append::value
byte uctoa_append::value#2 reg byte x 5018334.166666666 char uctoa_append::value#0 // reg byte x 36667.33333333333
void ultoa(dword ultoa::value , byte* ultoa::buffer , byte ultoa::radix) char uctoa_append::value#1 // reg byte x 2.0000002E7
byte~ ultoa::$10 reg byte a 20002.0 char uctoa_append::value#2 // reg byte x 5018334.166666666
byte~ ultoa::$11 reg byte a 2002.0 void ultoa(unsigned long value , char *buffer , char radix)
byte* ultoa::buffer char ultoa::$10 // reg byte a 20002.0
byte* ultoa::buffer#10 buffer zp[2]:37 3000.4285714285716 char ultoa::$11 // reg byte a 2002.0
byte* ultoa::buffer#15 buffer zp[2]:37 15001.5 char *ultoa::buffer
byte* ultoa::buffer#3 buffer zp[2]:37 2002.0 char *ultoa::buffer#10 // buffer zp[2]:13 3000.4285714285716
byte* ultoa::buffer#4 buffer zp[2]:37 20002.0 char *ultoa::buffer#15 // buffer zp[2]:13 15001.5
byte ultoa::digit char *ultoa::buffer#3 // buffer zp[2]:13 2002.0
byte ultoa::digit#1 digit zp[1]:10 20002.0 char *ultoa::buffer#4 // buffer zp[2]:13 20002.0
byte ultoa::digit#2 digit zp[1]:10 2857.4285714285716 char ultoa::digit
dword ultoa::digit_value char ultoa::digit#1 // digit zp[1]:8 20002.0
dword ultoa::digit_value#0 digit_value zp[4]:33 6000.6 char ultoa::digit#2 // digit zp[1]:8 2857.4285714285716
dword* ultoa::digit_values unsigned long ultoa::digit_value
byte ultoa::max_digits unsigned long ultoa::digit_value#0 // digit_value zp[4]:37 6000.6
byte ultoa::radix unsigned long *ultoa::digit_values
byte ultoa::started char ultoa::max_digits
byte ultoa::started#2 reg byte x 5000.5 char ultoa::radix
byte ultoa::started#4 reg byte x 10001.0 char ultoa::started
dword ultoa::value char ultoa::started#2 // reg byte x 5000.5
dword ultoa::value#0 value zp[4]:11 10001.0 char ultoa::started#4 // reg byte x 10001.0
dword ultoa::value#10 value zp[4]:11 1001.0 unsigned long ultoa::value
dword ultoa::value#3 value zp[4]:11 5857.857142857143 unsigned long ultoa::value#0 // value zp[4]:9 10001.0
dword ultoa::value#7 value zp[4]:11 15001.5 unsigned long ultoa::value#10 // value zp[4]:9 1001.0
dword ultoa_append(byte* ultoa_append::buffer , dword ultoa_append::value , dword ultoa_append::sub) unsigned long ultoa::value#3 // value zp[4]:9 5857.857142857143
byte* ultoa_append::buffer unsigned long ultoa::value#7 // value zp[4]:9 15001.5
byte* ultoa_append::buffer#0 buffer zp[2]:37 13750.25 unsigned long ultoa_append(char *buffer , unsigned long value , unsigned long sub)
byte ultoa_append::digit char *ultoa_append::buffer
byte ultoa_append::digit#1 reg byte x 1.0000001E7 char *ultoa_append::buffer#0 // buffer zp[2]:13 13750.25
byte ultoa_append::digit#2 reg byte x 1.00500015E7 char ultoa_append::digit
dword ultoa_append::return char ultoa_append::digit#1 // reg byte x 1.0000001E7
dword ultoa_append::return#0 return zp[4]:11 20002.0 char ultoa_append::digit#2 // reg byte x 1.00500015E7
dword ultoa_append::sub unsigned long ultoa_append::return
dword ultoa_append::sub#0 sub zp[4]:33 3335000.5 unsigned long ultoa_append::return#0 // return zp[4]:9 20002.0
dword ultoa_append::value unsigned long ultoa_append::sub
dword ultoa_append::value#0 value zp[4]:11 36667.33333333333 unsigned long ultoa_append::sub#0 // sub zp[4]:37 3335000.5
dword ultoa_append::value#1 value zp[4]:11 2.0000002E7 unsigned long ultoa_append::value
dword ultoa_append::value#2 value zp[4]:11 5018334.166666666 unsigned long ultoa_append::value#0 // value zp[4]:9 36667.33333333333
void utoa(word utoa::value , byte* utoa::buffer , byte utoa::radix) unsigned long ultoa_append::value#1 // value zp[4]:9 2.0000002E7
byte~ utoa::$10 reg byte a 20002.0 unsigned long ultoa_append::value#2 // value zp[4]:9 5018334.166666666
byte~ utoa::$11 reg byte x 2002.0 void utoa(unsigned int value , char *buffer , char radix)
byte~ utoa::$4 reg byte a 20002.0 char utoa::$10 // reg byte a 20002.0
byte* utoa::buffer char utoa::$11 // reg byte x 2002.0
byte* utoa::buffer#10 buffer zp[2]:37 2800.4000000000005 char utoa::$4 // reg byte a 20002.0
byte* utoa::buffer#15 buffer zp[2]:37 15001.5 char *utoa::buffer
byte* utoa::buffer#3 buffer zp[2]:37 2002.0 char *utoa::buffer#10 // buffer zp[2]:19 2800.4000000000005
byte* utoa::buffer#4 buffer zp[2]:37 20002.0 char *utoa::buffer#15 // buffer zp[2]:19 15001.5
byte utoa::digit char *utoa::buffer#3 // buffer zp[2]:19 2002.0
byte utoa::digit#1 digit zp[1]:5 20002.0 char *utoa::buffer#4 // buffer zp[2]:19 20002.0
byte utoa::digit#2 digit zp[1]:5 2666.9333333333334 char utoa::digit
word utoa::digit_value char utoa::digit#1 // digit zp[1]:3 20002.0
word utoa::digit_value#0 digit_value zp[2]:30 6000.6 char utoa::digit#2 // digit zp[1]:3 2666.9333333333334
word* utoa::digit_values unsigned int utoa::digit_value
word* utoa::digit_values#8 digit_values zp[2]:8 588.2941176470588 unsigned int utoa::digit_value#0 // digit_value zp[2]:34 6000.6
byte utoa::max_digits unsigned int *utoa::digit_values
byte utoa::max_digits#7 max_digits zp[1]:4 588.2941176470588 unsigned int *utoa::digit_values#8 // digit_values zp[2]:13 588.2941176470588
byte utoa::radix char utoa::max_digits
byte utoa::radix#1 reg byte x 202.0 char utoa::max_digits#7 // max_digits zp[1]:2 588.2941176470588
byte utoa::radix#2 reg byte x 1026.25 char utoa::radix
byte utoa::started char utoa::radix#1 // reg byte x 202.0
byte utoa::started#2 reg byte x 4286.142857142857 char utoa::radix#2 // reg byte x 1026.25
byte utoa::started#4 reg byte x 10001.0 char utoa::started
word utoa::value char utoa::started#2 // reg byte x 4286.142857142857
word utoa::value#0 value zp[2]:2 10001.0 char utoa::started#4 // reg byte x 10001.0
word utoa::value#10 value zp[2]:2 183.66666666666669 unsigned int utoa::value
word utoa::value#2 value zp[2]:2 101.0 unsigned int utoa::value#0 // value zp[2]:6 10001.0
word utoa::value#3 value zp[2]:2 5125.625 unsigned int utoa::value#10 // value zp[2]:6 183.66666666666669
word utoa::value#7 value zp[2]:2 15001.5 unsigned int utoa::value#2 // value zp[2]:6 101.0
word utoa_append(byte* utoa_append::buffer , word utoa_append::value , word utoa_append::sub) unsigned int utoa::value#3 // value zp[2]:6 5125.625
byte* utoa_append::buffer unsigned int utoa::value#7 // value zp[2]:6 15001.5
byte* utoa_append::buffer#0 buffer zp[2]:37 13750.25 unsigned int utoa_append(char *buffer , unsigned int value , unsigned int sub)
byte utoa_append::digit char *utoa_append::buffer
byte utoa_append::digit#1 reg byte x 1.0000001E7 char *utoa_append::buffer#0 // buffer zp[2]:19 13750.25
byte utoa_append::digit#2 reg byte x 1.00500015E7 char utoa_append::digit
word utoa_append::return char utoa_append::digit#1 // reg byte x 1.0000001E7
word utoa_append::return#0 return zp[2]:2 20002.0 char utoa_append::digit#2 // reg byte x 1.00500015E7
word utoa_append::sub unsigned int utoa_append::return
word utoa_append::sub#0 sub zp[2]:30 3335000.5 unsigned int utoa_append::return#0 // return zp[2]:6 20002.0
word utoa_append::value unsigned int utoa_append::sub
word utoa_append::value#0 value zp[2]:2 36667.33333333333 unsigned int utoa_append::sub#0 // sub zp[2]:34 3335000.5
word utoa_append::value#1 value zp[2]:2 2.0000002E7 unsigned int utoa_append::value
word utoa_append::value#2 value zp[2]:2 5018334.166666666 unsigned int utoa_append::value#0 // value zp[2]:6 36667.33333333333
unsigned int utoa_append::value#1 // value zp[2]:6 2.0000002E7
unsigned int utoa_append::value#2 // value zp[2]:6 5018334.166666666
reg byte x [ conio_c64_init::line#2 conio_c64_init::line#0 ] reg byte x [ conio_c64_init::line#2 conio_c64_init::line#0 ]
reg byte x [ gotoxy::y#4 gotoxy::y#2 ] reg byte x [ gotoxy::y#4 gotoxy::y#2 ]
reg byte x [ clrscr::l#2 clrscr::l#1 ] reg byte x [ clrscr::l#2 clrscr::l#1 ]
reg byte y [ clrscr::c#2 clrscr::c#1 ] reg byte y [ clrscr::c#2 clrscr::c#1 ]
reg byte a [ cputc::c#5 cputc::c#0 cputc::c#3 cputc::c#2 cputc::c#1 ]
zp[2]:2 [ printf_uint::uvalue#2 utoa::value#3 utoa::value#7 utoa::value#10 utoa::value#2 utoa::value#0 utoa_append::value#2 utoa_append::value#0 utoa_append::value#1 utoa_append::return#0 clrscr::line_cols#5 clrscr::line_cols#1 ]
reg byte x [ printf_uint::format_radix#2 ] reg byte x [ printf_uint::format_radix#2 ]
reg byte x [ utoa::radix#2 utoa::radix#1 ] reg byte x [ utoa::radix#2 utoa::radix#1 ]
reg byte x [ utoa::started#2 utoa::started#4 ] reg byte x [ utoa::started#2 utoa::started#4 ]
reg byte x [ printf_number_buffer::format_min_length#10 ] reg byte x [ printf_number_buffer::format_min_length#10 ]
zp[1]:4 [ printf_number_buffer::format_justify_left#10 utoa::max_digits#7 ] zp[1]:2 [ printf_number_buffer::format_justify_left#10 utoa::max_digits#7 ]
zp[1]:5 [ printf_number_buffer::format_zero_padding#10 utoa::digit#2 utoa::digit#1 ] zp[1]:3 [ printf_number_buffer::format_zero_padding#10 utoa::digit#2 utoa::digit#1 ]
reg byte y [ printf_number_buffer::len#2 printf_number_buffer::len#0 printf_number_buffer::len#1 ] reg byte y [ printf_number_buffer::len#2 printf_number_buffer::len#0 printf_number_buffer::len#1 ]
zp[1]:6 [ uctoa::digit#2 uctoa::digit#1 printf_number_buffer::buffer_sign#10 printf_number_buffer::buffer_sign#4 printf_number_buffer::buffer_sign#2 printf_number_buffer::buffer_sign#0 printf_number_buffer::buffer_sign#5 printf_number_buffer::buffer_sign#3 printf_number_buffer::buffer_sign#1 ] zp[1]:4 [ uctoa::digit#2 uctoa::digit#1 printf_number_buffer::buffer_sign#10 printf_number_buffer::buffer_sign#4 printf_number_buffer::buffer_sign#2 printf_number_buffer::buffer_sign#0 printf_number_buffer::buffer_sign#5 printf_number_buffer::buffer_sign#3 printf_number_buffer::buffer_sign#1 ]
reg byte x [ uctoa::value#3 uctoa::value#7 uctoa::value#10 uctoa::value#0 ] reg byte x [ uctoa::value#3 uctoa::value#7 uctoa::value#10 uctoa::value#0 ]
zp[1]:7 [ uctoa::started#2 uctoa::started#4 printf_number_buffer::format_upper_case#10 ] zp[1]:5 [ uctoa::started#2 uctoa::started#4 printf_number_buffer::format_upper_case#10 ]
zp[2]:8 [ uctoa::buffer#10 uctoa::buffer#15 uctoa::buffer#4 uctoa::buffer#3 uctoa_append::buffer#0 utoa::digit_values#8 cputs::s#20 cputs::s#21 cputs::s#0 clrscr::line_text#5 clrscr::line_text#1 ] zp[2]:6 [ uctoa::buffer#10 uctoa::buffer#15 uctoa::buffer#4 uctoa::buffer#3 uctoa_append::buffer#0 printf_uint::uvalue#2 utoa::value#3 utoa::value#7 utoa::value#10 utoa::value#2 utoa::value#0 utoa_append::value#2 utoa_append::value#0 utoa_append::value#1 utoa_append::return#0 printf_str::putc#21 printf_str::putc#0 printf_number_buffer::putc#10 printf_padding::putc#5 printf_padding::putc#1 printf_padding::putc#2 printf_padding::putc#0 clrscr::line_text#5 clrscr::line_text#1 ]
zp[1]:10 [ ultoa::digit#2 ultoa::digit#1 printf_number_buffer::padding#10 printf_number_buffer::padding#1 ] zp[1]:8 [ ultoa::digit#2 ultoa::digit#1 printf_number_buffer::padding#10 printf_number_buffer::padding#1 ]
zp[4]:11 [ ultoa::value#3 ultoa::value#7 ultoa::value#10 ultoa::value#0 ultoa_append::value#2 ultoa_append::value#0 ultoa_append::value#1 ultoa_append::return#0 ] zp[4]:9 [ ultoa::value#3 ultoa::value#7 ultoa::value#10 ultoa::value#0 ultoa_append::value#2 ultoa_append::value#0 ultoa_append::value#1 ultoa_append::return#0 ]
reg byte x [ ultoa::started#2 ultoa::started#4 ] reg byte x [ ultoa::started#2 ultoa::started#4 ]
zp[2]:13 [ ultoa::buffer#10 ultoa::buffer#15 ultoa::buffer#4 ultoa::buffer#3 ultoa_append::buffer#0 utoa::digit_values#8 printf_str::s#20 printf_str::s#21 printf_str::s#0 clrscr::line_cols#5 clrscr::line_cols#1 ]
zp[2]:15 [ memset::str#3 memset::dst#2 memset::dst#4 memset::dst#1 memcpy::source#2 memcpy::src#2 memcpy::src#4 memcpy::src#1 ]
reg byte x [ memset::c#4 ]
reg byte x [ utoa_append::digit#2 utoa_append::digit#1 ] reg byte x [ utoa_append::digit#2 utoa_append::digit#1 ]
zp[1]:15 [ printf_padding::pad#5 ] zp[1]:17 [ printf_padding::pad#5 ]
zp[1]:16 [ printf_padding::i#2 printf_padding::i#1 ] zp[1]:18 [ printf_padding::i#2 printf_padding::i#1 ]
zp[2]:19 [ strupr::src#2 strupr::src#1 strlen::str#2 strlen::str#0 utoa::buffer#10 utoa::buffer#15 utoa::buffer#4 utoa::buffer#3 utoa_append::buffer#0 ]
reg byte x [ uctoa_append::value#2 uctoa_append::value#0 uctoa_append::value#1 ] reg byte x [ uctoa_append::value#2 uctoa_append::value#0 uctoa_append::value#1 ]
reg byte y [ uctoa_append::digit#2 uctoa_append::digit#1 ] reg byte y [ uctoa_append::digit#2 uctoa_append::digit#1 ]
reg byte x [ ultoa_append::digit#2 ultoa_append::digit#1 ] reg byte x [ ultoa_append::digit#2 ultoa_append::digit#1 ]
reg byte x [ memset::c#4 ]
reg byte a [ toupper::return#2 toupper::return#0 toupper::ch#0 ] reg byte a [ toupper::return#2 toupper::return#0 toupper::ch#0 ]
zp[1]:17 [ conio_cursor_x ] zp[1]:21 [ conio_cursor_x ]
zp[1]:18 [ conio_cursor_y ] zp[1]:22 [ conio_cursor_y ]
zp[2]:19 [ conio_line_text ] zp[2]:23 [ conio_line_text ]
zp[2]:21 [ conio_line_color ] zp[2]:25 [ conio_line_color ]
zp[1]:23 [ main::c ] reg byte a [ cputc::c#0 ]
zp[2]:24 [ gotoxy::$7 gotoxy::$9 gotoxy::line_offset#0 gotoxy::$6 ] zp[1]:27 [ main::c ]
zp[2]:26 [ gotoxy::$8 ] zp[2]:28 [ gotoxy::$7 gotoxy::$9 gotoxy::line_offset#0 gotoxy::$6 ]
zp[2]:28 [ gotoxy::$5 ] zp[2]:30 [ gotoxy::$8 ]
reg byte a [ cputs::c#1 ] zp[2]:32 [ gotoxy::$5 ]
reg byte a [ printf_str::c#1 ]
reg byte a [ utoa::$4 ] reg byte a [ utoa::$4 ]
reg byte x [ utoa::$11 ] reg byte x [ utoa::$11 ]
reg byte a [ utoa::$10 ] reg byte a [ utoa::$10 ]
zp[2]:30 [ utoa::digit_value#0 utoa_append::sub#0 strlen::len#2 strlen::len#1 strlen::return#2 printf_number_buffer::$19 memset::str#3 memset::dst#2 memset::dst#4 memset::dst#1 memcpy::source#2 memcpy::src#2 memcpy::src#4 memcpy::src#1 ] zp[2]:34 [ utoa::digit_value#0 utoa_append::sub#0 strlen::len#2 strlen::len#1 strlen::return#2 printf_number_buffer::$19 ]
zp[1]:32 [ uctoa::digit_value#0 uctoa_append::sub#0 printf_padding::length#4 printf_padding::length#1 printf_padding::length#2 printf_padding::length#0 ] zp[1]:36 [ uctoa::digit_value#0 uctoa_append::sub#0 printf_padding::length#4 printf_padding::length#1 printf_padding::length#2 printf_padding::length#0 ]
reg byte x [ uctoa_append::return#0 ] reg byte x [ uctoa_append::return#0 ]
reg byte a [ ultoa::$11 ] reg byte a [ ultoa::$11 ]
reg byte a [ ultoa::$10 ] reg byte a [ ultoa::$10 ]
zp[4]:33 [ ultoa::digit_value#0 ultoa_append::sub#0 ] zp[4]:37 [ ultoa::digit_value#0 ultoa_append::sub#0 ]
zp[2]:41 [ memcpy::src_end#0 ]
zp[2]:43 [ memset::end#0 memcpy::destination#2 memcpy::dst#2 memcpy::dst#4 memcpy::dst#1 ]
reg byte a [ toupper::return#3 ] reg byte a [ toupper::return#3 ]
reg byte a [ strupr::$0 ] reg byte a [ strupr::$0 ]
zp[2]:37 [ memcpy::src_end#0 strupr::src#2 strupr::src#1 strlen::str#2 strlen::str#0 ultoa::buffer#10 ultoa::buffer#15 ultoa::buffer#4 ultoa::buffer#3 ultoa_append::buffer#0 utoa::buffer#10 utoa::buffer#15 utoa::buffer#4 utoa::buffer#3 utoa_append::buffer#0 ]
zp[2]:39 [ memset::end#0 memcpy::destination#2 memcpy::dst#2 memcpy::dst#4 memcpy::dst#1 ]
mem[12] [ printf_buffer ] mem[12] [ printf_buffer ]

871
src/test/ref/printf-17.asm Normal file
View File

@@ -0,0 +1,871 @@
// Tests snprintf function call rewriting
// Test simple formats
// Commodore 64 PRG executable file
.file [name="printf-17.prg", type="prg", segments="Program"]
.segmentdef Program [segments="Basic, Code, Data"]
.segmentdef Basic [start=$0801]
.segmentdef Code [start=$80d]
.segmentdef Data [startAfter="Code"]
.segment Basic
:BasicUpstart(__start)
.const BINARY = 2
.const OCTAL = 8
.const DECIMAL = $a
.const HEXADECIMAL = $10
.const OFFSET_STRUCT_PRINTF_BUFFER_NUMBER_DIGITS = 1
.const STACK_BASE = $103
.const SIZEOF_STRUCT_PRINTF_BUFFER_NUMBER = $c
/// The capacity of the buffer (n passed to snprintf())
/// Used to hold state while printing
.label __snprintf_capacity = $12
// The number of chars that would have been filled when printing without capacity. Grows even after size>capacity.
/// Used to hold state while printing
.label __snprintf_size = $14
/// Current position in the buffer being filled ( initially *s passed to snprintf()
/// Used to hold state while printing
.label __snprintf_buffer = $16
.label screen = 2
.segment Code
__start: {
// volatile size_t __snprintf_capacity
lda #<0
sta.z __snprintf_capacity
sta.z __snprintf_capacity+1
// volatile size_t __snprintf_size
sta.z __snprintf_size
sta.z __snprintf_size+1
// char * __snprintf_buffer
sta.z __snprintf_buffer
sta.z __snprintf_buffer+1
jsr main
rts
}
/// Print a character into snprintf buffer
/// Used by snprintf()
/// @param c The character to print
// void snputc(__register(X) char c)
snputc: {
.const OFFSET_STACK_C = 0
tsx
lda STACK_BASE+OFFSET_STACK_C,x
tax
// ++__snprintf_size;
inc.z __snprintf_size
bne !+
inc.z __snprintf_size+1
!:
// if(__snprintf_size > __snprintf_capacity)
lda.z __snprintf_capacity+1
cmp.z __snprintf_size+1
bcc !+
bne __b1
lda.z __snprintf_capacity
cmp.z __snprintf_size
bcs __b1
!:
// }
rts
__b1:
// if(__snprintf_size==__snprintf_capacity)
lda.z __snprintf_size+1
cmp.z __snprintf_capacity+1
bne __b2
lda.z __snprintf_size
cmp.z __snprintf_capacity
bne __b2
ldx #0
__b2:
// *(__snprintf_buffer++) = c
// Append char
txa
ldy #0
sta (__snprintf_buffer),y
// *(__snprintf_buffer++) = c;
inc.z __snprintf_buffer
bne !+
inc.z __snprintf_buffer+1
!:
rts
}
main: {
// snprintf(BUF, 20, "hello world! ")
lda #<$14
sta.z snprintf_init.n
lda #>$14
sta.z snprintf_init.n+1
jsr snprintf_init
// snprintf(BUF, 20, "hello world! ")
lda #<snputc
sta.z printf_str.putc
lda #>snputc
sta.z printf_str.putc+1
lda #<s
sta.z printf_str.s
lda #>s
sta.z printf_str.s+1
jsr printf_str
// snprintf(BUF, 20, "hello world! ")
lda #0
pha
jsr snputc
pla
// print(BUF)
lda #<$400
sta.z screen
lda #>$400
sta.z screen+1
jsr print
// snprintf(BUF, 20, "hello %s%c ", "world", '!')
lda #<$14
sta.z snprintf_init.n
lda #>$14
sta.z snprintf_init.n+1
jsr snprintf_init
// snprintf(BUF, 20, "hello %s%c ", "world", '!')
lda #<snputc
sta.z printf_str.putc
lda #>snputc
sta.z printf_str.putc+1
lda #<s1
sta.z printf_str.s
lda #>s1
sta.z printf_str.s+1
jsr printf_str
// snprintf(BUF, 20, "hello %s%c ", "world", '!')
jsr printf_string
// snprintf(BUF, 20, "hello %s%c ", "world", '!')
lda #'!'
pha
jsr snputc
pla
lda #<snputc
sta.z printf_str.putc
lda #>snputc
sta.z printf_str.putc+1
lda #<s2
sta.z printf_str.s
lda #>s2
sta.z printf_str.s+1
jsr printf_str
// snprintf(BUF, 20, "hello %s%c ", "world", '!')
lda #0
pha
jsr snputc
pla
// print(BUF)
jsr print
// snprintf(BUF, 20, "hello %d+%x! ", 3,11)
lda #<$14
sta.z snprintf_init.n
lda #>$14
sta.z snprintf_init.n+1
jsr snprintf_init
// snprintf(BUF, 20, "hello %d+%x! ", 3,11)
lda #<snputc
sta.z printf_str.putc
lda #>snputc
sta.z printf_str.putc+1
lda #<s1
sta.z printf_str.s
lda #>s1
sta.z printf_str.s+1
jsr printf_str
// snprintf(BUF, 20, "hello %d+%x! ", 3,11)
lda #<3
sta.z printf_sint.value
lda #>3
sta.z printf_sint.value+1
jsr printf_sint
// snprintf(BUF, 20, "hello %d+%x! ", 3,11)
lda #<snputc
sta.z printf_str.putc
lda #>snputc
sta.z printf_str.putc+1
lda #<s4
sta.z printf_str.s
lda #>s4
sta.z printf_str.s+1
jsr printf_str
// snprintf(BUF, 20, "hello %d+%x! ", 3,11)
jsr printf_uint
// snprintf(BUF, 20, "hello %d+%x! ", 3,11)
lda #<snputc
sta.z printf_str.putc
lda #>snputc
sta.z printf_str.putc+1
lda #<s5
sta.z printf_str.s
lda #>s5
sta.z printf_str.s+1
jsr printf_str
// snprintf(BUF, 20, "hello %d+%x! ", 3,11)
lda #0
pha
jsr snputc
pla
// print(BUF)
jsr print
// snprintf(BUF, 6, "hi %d! ", 22222)
lda #<6
sta.z snprintf_init.n
lda #>6
sta.z snprintf_init.n+1
jsr snprintf_init
// snprintf(BUF, 6, "hi %d! ", 22222)
lda #<snputc
sta.z printf_str.putc
lda #>snputc
sta.z printf_str.putc+1
lda #<s6
sta.z printf_str.s
lda #>s6
sta.z printf_str.s+1
jsr printf_str
// snprintf(BUF, 6, "hi %d! ", 22222)
lda #<$56ce
sta.z printf_sint.value
lda #>$56ce
sta.z printf_sint.value+1
jsr printf_sint
// snprintf(BUF, 6, "hi %d! ", 22222)
lda #<snputc
sta.z printf_str.putc
lda #>snputc
sta.z printf_str.putc+1
lda #<s5
sta.z printf_str.s
lda #>s5
sta.z printf_str.s+1
jsr printf_str
// snprintf(BUF, 6, "hi %d! ", 22222)
lda #0
pha
jsr snputc
pla
// print(BUF)
jsr print
// }
rts
.segment Data
s: .text "hello world! "
.byte 0
s1: .text "hello "
.byte 0
str: .text "world"
.byte 0
s2: .text " "
.byte 0
s4: .text "+"
.byte 0
s5: .text "! "
.byte 0
s6: .text "hi "
.byte 0
}
.segment Code
/// Initialize the snprintf() state
// void snprintf_init(char *s, __zp(4) unsigned int n)
snprintf_init: {
.label n = 4
// __snprintf_capacity = n
lda.z n
sta.z __snprintf_capacity
lda.z n+1
sta.z __snprintf_capacity+1
// __snprintf_size = 0
lda #<0
sta.z __snprintf_size
sta.z __snprintf_size+1
// __snprintf_buffer = s
lda #<BUF
sta.z __snprintf_buffer
lda #>BUF
sta.z __snprintf_buffer+1
// }
rts
}
/// Print a NUL-terminated string
// void printf_str(__zp(4) void (*putc)(char), __zp($b) const char *s)
printf_str: {
.label s = $b
.label putc = 4
__b1:
// while(c=*s++)
ldy #0
lda (s),y
inc.z s
bne !+
inc.z s+1
!:
cmp #0
bne __b2
// }
rts
__b2:
// putc(c)
pha
jsr icall6
pla
jmp __b1
icall6:
jmp (putc)
}
// void print(__zp($b) char *msg)
print: {
.label msg = $b
lda #<BUF
sta.z msg
lda #>BUF
sta.z msg+1
__b1:
// while(*msg)
ldy #0
lda (msg),y
cmp #0
bne __b2
// }
rts
__b2:
// *(screen++) = *(msg++)
ldy #0
lda (msg),y
sta (screen),y
// *(screen++) = *(msg++);
inc.z screen
bne !+
inc.z screen+1
!:
inc.z msg
bne !+
inc.z msg+1
!:
jmp __b1
}
// Print a string value using a specific format
// Handles justification and min length
// void printf_string(void (*putc)(char), char *str, char format_min_length, char format_justify_left)
printf_string: {
.label putc = snputc
// printf_str(putc, str)
lda #<putc
sta.z printf_str.putc
lda #>putc
sta.z printf_str.putc+1
lda #<main.str
sta.z printf_str.s
lda #>main.str
sta.z printf_str.s+1
jsr printf_str
// }
rts
}
// Print a signed integer using a specific format
// void printf_sint(void (*putc)(char), __zp(4) int value, char format_min_length, char format_justify_left, char format_sign_always, char format_zero_padding, char format_upper_case, char format_radix)
printf_sint: {
.label value = 4
// printf_buffer.sign = 0
// Handle any sign
lda #0
sta printf_buffer
// if(value<0)
lda.z value+1
bmi __b1
jmp __b2
__b1:
// value = -value
lda #0
sec
sbc.z value
sta.z value
lda #0
sbc.z value+1
sta.z value+1
// printf_buffer.sign = '-'
lda #'-'
sta printf_buffer
__b2:
// utoa(uvalue, printf_buffer.digits, format.radix)
ldx #DECIMAL
jsr utoa
// printf_number_buffer(putc, printf_buffer, format)
lda printf_buffer
sta.z printf_number_buffer.buffer_sign
// Print using format
lda #0
sta.z printf_number_buffer.format_upper_case
lda #<snputc
sta.z printf_number_buffer.putc
lda #>snputc
sta.z printf_number_buffer.putc+1
lda #0
sta.z printf_number_buffer.format_zero_padding
sta.z printf_number_buffer.format_justify_left
tax
jsr printf_number_buffer
// }
rts
}
// Print an unsigned int using a specific format
// void printf_uint(void (*putc)(char), unsigned int uvalue, char format_min_length, char format_justify_left, char format_sign_always, char format_zero_padding, char format_upper_case, char format_radix)
printf_uint: {
.const uvalue = $b
.const format_min_length = 0
.const format_justify_left = 0
.const format_zero_padding = 0
.const format_upper_case = 0
.label putc = snputc
// printf_buffer.sign = format.sign_always?'+':0
// Handle any sign
lda #0
sta printf_buffer
// utoa(uvalue, printf_buffer.digits, format.radix)
// Format number into buffer
lda #<uvalue
sta.z utoa.value
lda #>uvalue
sta.z utoa.value+1
ldx #HEXADECIMAL
jsr utoa
// printf_number_buffer(putc, printf_buffer, format)
lda printf_buffer
sta.z printf_number_buffer.buffer_sign
// Print using format
lda #format_upper_case
sta.z printf_number_buffer.format_upper_case
lda #<putc
sta.z printf_number_buffer.putc
lda #>putc
sta.z printf_number_buffer.putc+1
lda #format_zero_padding
sta.z printf_number_buffer.format_zero_padding
lda #format_justify_left
sta.z printf_number_buffer.format_justify_left
ldx #format_min_length
jsr printf_number_buffer
// }
rts
}
// Converts unsigned number value to a string representing it in RADIX format.
// If the leading digits are zero they are not included in the string.
// - value : The number to be converted to RADIX
// - buffer : receives the string representing the number and zero-termination.
// - radix : The radix to convert the number to (from the enum RADIX)
// void utoa(__zp(4) unsigned int value, __zp($d) char *buffer, __register(X) char radix)
utoa: {
.label digit_value = $18
.label buffer = $d
.label digit = 7
.label value = 4
.label max_digits = 6
.label digit_values = $b
// if(radix==DECIMAL)
cpx #DECIMAL
beq __b2
// if(radix==HEXADECIMAL)
cpx #HEXADECIMAL
beq __b3
// if(radix==OCTAL)
cpx #OCTAL
beq __b4
// if(radix==BINARY)
cpx #BINARY
beq __b5
// *buffer++ = 'e'
// Unknown radix
lda #'e'
sta printf_buffer+OFFSET_STRUCT_PRINTF_BUFFER_NUMBER_DIGITS
// *buffer++ = 'r'
lda #'r'
sta printf_buffer+OFFSET_STRUCT_PRINTF_BUFFER_NUMBER_DIGITS+1
sta printf_buffer+OFFSET_STRUCT_PRINTF_BUFFER_NUMBER_DIGITS+2
// *buffer = 0
lda #0
sta printf_buffer+OFFSET_STRUCT_PRINTF_BUFFER_NUMBER_DIGITS+3
// }
rts
__b2:
lda #<RADIX_DECIMAL_VALUES
sta.z digit_values
lda #>RADIX_DECIMAL_VALUES
sta.z digit_values+1
lda #5
sta.z max_digits
jmp __b1
__b3:
lda #<RADIX_HEXADECIMAL_VALUES
sta.z digit_values
lda #>RADIX_HEXADECIMAL_VALUES
sta.z digit_values+1
lda #4
sta.z max_digits
jmp __b1
__b4:
lda #<RADIX_OCTAL_VALUES
sta.z digit_values
lda #>RADIX_OCTAL_VALUES
sta.z digit_values+1
lda #6
sta.z max_digits
jmp __b1
__b5:
lda #<RADIX_BINARY_VALUES
sta.z digit_values
lda #>RADIX_BINARY_VALUES
sta.z digit_values+1
lda #$10
sta.z max_digits
__b1:
lda #<printf_buffer+OFFSET_STRUCT_PRINTF_BUFFER_NUMBER_DIGITS
sta.z buffer
lda #>printf_buffer+OFFSET_STRUCT_PRINTF_BUFFER_NUMBER_DIGITS
sta.z buffer+1
ldx #0
txa
sta.z digit
__b6:
// max_digits-1
lda.z max_digits
sec
sbc #1
// for( char digit=0; digit<max_digits-1; digit++ )
cmp.z digit
beq !+
bcs __b7
!:
// *buffer++ = DIGITS[(char)value]
ldx.z value
lda DIGITS,x
ldy #0
sta (buffer),y
// *buffer++ = DIGITS[(char)value];
inc.z buffer
bne !+
inc.z buffer+1
!:
// *buffer = 0
lda #0
tay
sta (buffer),y
rts
__b7:
// unsigned int digit_value = digit_values[digit]
lda.z digit
asl
tay
lda (digit_values),y
sta.z digit_value
iny
lda (digit_values),y
sta.z digit_value+1
// if (started || value >= digit_value)
cpx #0
bne __b10
lda.z value+1
cmp.z digit_value+1
bcc !+
bne __b10
lda.z value
cmp.z digit_value
bcs __b10
!:
__b9:
// for( char digit=0; digit<max_digits-1; digit++ )
inc.z digit
jmp __b6
__b10:
// utoa_append(buffer++, value, digit_value)
jsr utoa_append
// utoa_append(buffer++, value, digit_value)
// value = utoa_append(buffer++, value, digit_value)
// value = utoa_append(buffer++, value, digit_value);
inc.z buffer
bne !+
inc.z buffer+1
!:
ldx #1
jmp __b9
}
// Print the contents of the number buffer using a specific format.
// This handles minimum length, zero-filling, and left/right justification from the format
// void printf_number_buffer(__zp(4) void (*putc)(char), __zp(8) char buffer_sign, char *buffer_digits, __register(X) char format_min_length, __zp(6) char format_justify_left, char format_sign_always, __zp(7) char format_zero_padding, __zp(9) char format_upper_case, char format_radix)
printf_number_buffer: {
.label __19 = $d
.label buffer_sign = 8
.label padding = $a
.label putc = 4
.label format_zero_padding = 7
.label format_justify_left = 6
.label format_upper_case = 9
// if(format.min_length)
cpx #0
beq __b6
// strlen(buffer.digits)
jsr strlen
// strlen(buffer.digits)
// signed char len = (signed char)strlen(buffer.digits)
// There is a minimum length - work out the padding
ldy.z __19
// if(buffer.sign)
lda.z buffer_sign
beq __b13
// len++;
iny
__b13:
// padding = (signed char)format.min_length - len
txa
sty.z $ff
sec
sbc.z $ff
sta.z padding
// if(padding<0)
cmp #0
bpl __b1
__b6:
lda #0
sta.z padding
__b1:
// if(!format.justify_left && !format.zero_padding && padding)
lda.z format_justify_left
bne __b2
lda.z format_zero_padding
bne __b2
lda.z padding
cmp #0
bne __b8
jmp __b2
__b8:
// printf_padding(putc, ' ',(char)padding)
lda.z padding
sta.z printf_padding.length
lda #' '
sta.z printf_padding.pad
jsr printf_padding
__b2:
// if(buffer.sign)
lda.z buffer_sign
beq __b3
// putc(buffer.sign)
pha
jsr icall7
pla
__b3:
// if(format.zero_padding && padding)
lda.z format_zero_padding
beq __b4
lda.z padding
cmp #0
bne __b10
jmp __b4
__b10:
// printf_padding(putc, '0',(char)padding)
lda.z padding
sta.z printf_padding.length
lda #'0'
sta.z printf_padding.pad
jsr printf_padding
__b4:
// if(format.upper_case)
lda.z format_upper_case
beq __b5
// strupr(buffer.digits)
jsr strupr
__b5:
// printf_str(putc, buffer.digits)
lda #<printf_buffer+OFFSET_STRUCT_PRINTF_BUFFER_NUMBER_DIGITS
sta.z printf_str.s
lda #>printf_buffer+OFFSET_STRUCT_PRINTF_BUFFER_NUMBER_DIGITS
sta.z printf_str.s+1
jsr printf_str
// if(format.justify_left && !format.zero_padding && padding)
lda.z format_justify_left
beq __breturn
lda.z format_zero_padding
bne __breturn
lda.z padding
cmp #0
bne __b12
rts
__b12:
// printf_padding(putc, ' ',(char)padding)
lda.z padding
sta.z printf_padding.length
lda #' '
sta.z printf_padding.pad
jsr printf_padding
__breturn:
// }
rts
icall7:
jmp (putc)
}
// Used to convert a single digit of an unsigned number value to a string representation
// Counts a single digit up from '0' as long as the value is larger than sub.
// Each time the digit is increased sub is subtracted from value.
// - buffer : pointer to the char that receives the digit
// - value : The value where the digit will be derived from
// - sub : the value of a '1' in the digit. Subtracted continually while the digit is increased.
// (For decimal the subs used are 10000, 1000, 100, 10, 1)
// returns : the value reduced by sub * digit so that it is less than sub.
// __zp(4) unsigned int utoa_append(__zp($d) char *buffer, __zp(4) unsigned int value, __zp($18) unsigned int sub)
utoa_append: {
.label buffer = $d
.label value = 4
.label sub = $18
.label return = 4
ldx #0
__b1:
// while (value >= sub)
lda.z value+1
cmp.z sub+1
bcc !+
bne __b2
lda.z value
cmp.z sub
bcs __b2
!:
// *buffer = DIGITS[digit]
lda DIGITS,x
ldy #0
sta (buffer),y
// }
rts
__b2:
// digit++;
inx
// value -= sub
lda.z value
sec
sbc.z sub
sta.z value
lda.z value+1
sbc.z sub+1
sta.z value+1
jmp __b1
}
// Computes the length of the string str up to but not including the terminating null character.
// __zp($d) unsigned int strlen(__zp($b) char *str)
strlen: {
.label len = $d
.label str = $b
.label return = $d
lda #<0
sta.z len
sta.z len+1
lda #<printf_buffer+OFFSET_STRUCT_PRINTF_BUFFER_NUMBER_DIGITS
sta.z str
lda #>printf_buffer+OFFSET_STRUCT_PRINTF_BUFFER_NUMBER_DIGITS
sta.z str+1
__b1:
// while(*str)
ldy #0
lda (str),y
cmp #0
bne __b2
// }
rts
__b2:
// len++;
inc.z len
bne !+
inc.z len+1
!:
// str++;
inc.z str
bne !+
inc.z str+1
!:
jmp __b1
}
// Print a padding char a number of times
// void printf_padding(__zp(4) void (*putc)(char), __zp($10) char pad, __zp($f) char length)
printf_padding: {
.label i = $11
.label putc = 4
.label length = $f
.label pad = $10
lda #0
sta.z i
__b1:
// for(char i=0;i<length; i++)
lda.z i
cmp.z length
bcc __b2
// }
rts
__b2:
// putc(pad)
lda.z pad
pha
jsr icall8
pla
// for(char i=0;i<length; i++)
inc.z i
jmp __b1
icall8:
jmp (putc)
}
// Converts a string to uppercase.
// char * strupr(char *str)
strupr: {
.label str = printf_buffer+OFFSET_STRUCT_PRINTF_BUFFER_NUMBER_DIGITS
.label src = $18
lda #<str
sta.z src
lda #>str
sta.z src+1
__b1:
// while(*src)
ldy #0
lda (src),y
cmp #0
bne __b2
// }
rts
__b2:
// toupper(*src)
ldy #0
lda (src),y
jsr toupper
// *src = toupper(*src)
ldy #0
sta (src),y
// src++;
inc.z src
bne !+
inc.z src+1
!:
jmp __b1
}
// Convert lowercase alphabet to uppercase
// Returns uppercase equivalent to c, if such value exists, else c remains unchanged
// __register(A) char toupper(__register(A) char ch)
toupper: {
// if(ch>='a' && ch<='z')
cmp #'a'
bcc __breturn
cmp #'z'
bcc __b1
beq __b1
rts
__b1:
// return ch + ('A'-'a');
clc
adc #'A'-'a'
__breturn:
// }
rts
}
.segment Data
// The digits used for numbers
DIGITS: .text "0123456789abcdef"
// Values of binary digits
RADIX_BINARY_VALUES: .word $8000, $4000, $2000, $1000, $800, $400, $200, $100, $80, $40, $20, $10, 8, 4, 2
// Values of octal digits
RADIX_OCTAL_VALUES: .word $8000, $1000, $200, $40, 8
// Values of decimal digits
RADIX_DECIMAL_VALUES: .word $2710, $3e8, $64, $a
// Values of hexadecimal digits
RADIX_HEXADECIMAL_VALUES: .word $1000, $100, $10
BUF: .fill $14, 0
// Buffer used for stringified number being printed
printf_buffer: .fill SIZEOF_STRUCT_PRINTF_BUFFER_NUMBER, 0

491
src/test/ref/printf-17.cfg Normal file
View File

@@ -0,0 +1,491 @@
void __start()
__start: scope:[__start] from
[0] phi()
to:__start::__init1
__start::__init1: scope:[__start] from __start
[1] __snprintf_capacity = 0
[2] __snprintf_size = 0
[3] __snprintf_buffer = (char *) 0
to:__start::@1
__start::@1: scope:[__start] from __start::__init1
[4] phi()
[5] call main
to:__start::@return
__start::@return: scope:[__start] from __start::@1
[6] return
to:@return
__stackcall void snputc(char c)
snputc: scope:[snputc] from
[7] snputc::c#0 = stackidx(char,snputc::OFFSET_STACK_C)
[8] __snprintf_size = ++ __snprintf_size
[9] if(__snprintf_size<=__snprintf_capacity) goto snputc::@1
to:snputc::@return
snputc::@return: scope:[snputc] from snputc snputc::@2
[10] return
to:@return
snputc::@1: scope:[snputc] from snputc
[11] if(__snprintf_size!=__snprintf_capacity) goto snputc::@3
to:snputc::@2
snputc::@3: scope:[snputc] from snputc::@1
[12] phi()
to:snputc::@2
snputc::@2: scope:[snputc] from snputc::@1 snputc::@3
[13] snputc::c#2 = phi( snputc::@3/snputc::c#0, snputc::@1/0 )
[14] *__snprintf_buffer = snputc::c#2
[15] __snprintf_buffer = ++ __snprintf_buffer
to:snputc::@return
void main()
main: scope:[main] from __start::@1
[16] phi()
[17] call snprintf_init
to:main::@1
main::@1: scope:[main] from main
[18] phi()
[19] call printf_str
to:main::@2
main::@2: scope:[main] from main::@1
[20] stackpush(char) = 0
[21] callexecute snputc
sideeffect stackpullbytes(1)
[23] call print
to:main::@3
main::@3: scope:[main] from main::@2
[24] phi()
[25] call snprintf_init
to:main::@4
main::@4: scope:[main] from main::@3
[26] phi()
[27] call printf_str
to:main::@5
main::@5: scope:[main] from main::@4
[28] phi()
[29] call printf_string
to:main::@6
main::@6: scope:[main] from main::@5
[30] stackpush(char) = '!'
[31] callexecute snputc
sideeffect stackpullbytes(1)
[33] call printf_str
to:main::@7
main::@7: scope:[main] from main::@6
[34] stackpush(char) = 0
[35] callexecute snputc
sideeffect stackpullbytes(1)
[37] call print
to:main::@8
main::@8: scope:[main] from main::@7
[38] phi()
[39] call snprintf_init
to:main::@9
main::@9: scope:[main] from main::@8
[40] phi()
[41] call printf_str
to:main::@10
main::@10: scope:[main] from main::@9
[42] phi()
[43] call printf_sint
to:main::@11
main::@11: scope:[main] from main::@10
[44] phi()
[45] call printf_str
to:main::@12
main::@12: scope:[main] from main::@11
[46] phi()
[47] call printf_uint
to:main::@13
main::@13: scope:[main] from main::@12
[48] phi()
[49] call printf_str
to:main::@14
main::@14: scope:[main] from main::@13
[50] stackpush(char) = 0
[51] callexecute snputc
sideeffect stackpullbytes(1)
[53] call print
to:main::@15
main::@15: scope:[main] from main::@14
[54] phi()
[55] call snprintf_init
to:main::@16
main::@16: scope:[main] from main::@15
[56] phi()
[57] call printf_str
to:main::@17
main::@17: scope:[main] from main::@16
[58] phi()
[59] call printf_sint
to:main::@18
main::@18: scope:[main] from main::@17
[60] phi()
[61] call printf_str
to:main::@19
main::@19: scope:[main] from main::@18
[62] stackpush(char) = 0
[63] callexecute snputc
sideeffect stackpullbytes(1)
[65] call print
to:main::@return
main::@return: scope:[main] from main::@19
[66] return
to:@return
void snprintf_init(char *s , unsigned int n)
snprintf_init: scope:[snprintf_init] from main main::@15 main::@3 main::@8
[67] snprintf_init::n#4 = phi( main/$14, main::@15/6, main::@3/$14, main::@8/$14 )
[68] __snprintf_capacity = snprintf_init::n#4
[69] __snprintf_size = 0
[70] __snprintf_buffer = BUF
to:snprintf_init::@return
snprintf_init::@return: scope:[snprintf_init] from snprintf_init
[71] return
to:@return
void printf_str(void (*putc)(char) , const char *s)
printf_str: scope:[printf_str] from main::@1 main::@11 main::@13 main::@16 main::@18 main::@4 main::@6 main::@9 printf_number_buffer::@5 printf_string::@1
[72] printf_str::putc#12 = phi( main::@1/&snputc, main::@11/&snputc, main::@13/&snputc, main::@16/&snputc, main::@18/&snputc, main::@4/&snputc, main::@6/&snputc, main::@9/&snputc, printf_number_buffer::@5/printf_str::putc#0, printf_string::@1/printf_string::putc#0 )
[72] printf_str::s#12 = phi( main::@1/main::s, main::@11/main::s4, main::@13/main::s5, main::@16/main::s6, main::@18/main::s5, main::@4/main::s1, main::@6/main::s2, main::@9/main::s1, printf_number_buffer::@5/(char *)&printf_buffer+OFFSET_STRUCT_PRINTF_BUFFER_NUMBER_DIGITS, printf_string::@1/main::str )
to:printf_str::@1
printf_str::@1: scope:[printf_str] from printf_str printf_str::@2
[73] printf_str::s#11 = phi( printf_str/printf_str::s#12, printf_str::@2/printf_str::s#0 )
[74] printf_str::c#1 = *printf_str::s#11
[75] printf_str::s#0 = ++ printf_str::s#11
[76] if(0!=printf_str::c#1) goto printf_str::@2
to:printf_str::@return
printf_str::@return: scope:[printf_str] from printf_str::@1
[77] return
to:@return
printf_str::@2: scope:[printf_str] from printf_str::@1
[78] stackpush(char) = printf_str::c#1
[79] callexecute *printf_str::putc#12
sideeffect stackpullbytes(1)
to:printf_str::@1
void print(char *msg)
print: scope:[print] from main::@14 main::@19 main::@2 main::@7
[81] screen#25 = phi( main::@14/screen#1, main::@19/screen#1, main::@2/(char *) 1024, main::@7/screen#1 )
to:print::@1
print::@1: scope:[print] from print print::@2
[82] screen#1 = phi( print/screen#25, print::@2/screen#0 )
[82] print::msg#5 = phi( print/BUF, print::@2/print::msg#0 )
[83] if(0!=*print::msg#5) goto print::@2
to:print::@return
print::@return: scope:[print] from print::@1
[84] return
to:@return
print::@2: scope:[print] from print::@1
[85] *screen#1 = *print::msg#5
[86] screen#0 = ++ screen#1
[87] print::msg#0 = ++ print::msg#5
to:print::@1
void printf_string(void (*putc)(char) , char *str , char format_min_length , char format_justify_left)
printf_string: scope:[printf_string] from main::@5
[88] phi()
to:printf_string::@1
printf_string::@1: scope:[printf_string] from printf_string
[89] phi()
[90] call printf_str
to:printf_string::@return
printf_string::@return: scope:[printf_string] from printf_string::@1
[91] return
to:@return
void printf_sint(void (*putc)(char) , int value , char format_min_length , char format_justify_left , char format_sign_always , char format_zero_padding , char format_upper_case , char format_radix)
printf_sint: scope:[printf_sint] from main::@10 main::@17
[92] printf_sint::value#3 = phi( main::@10/3, main::@17/$56ce )
[93] *((char *)&printf_buffer) = 0
[94] if(printf_sint::value#3<0) goto printf_sint::@1
to:printf_sint::@2
printf_sint::@1: scope:[printf_sint] from printf_sint
[95] printf_sint::value#0 = - printf_sint::value#3
[96] *((char *)&printf_buffer) = '-'
to:printf_sint::@2
printf_sint::@2: scope:[printf_sint] from printf_sint printf_sint::@1
[97] printf_sint::value#5 = phi( printf_sint::@1/printf_sint::value#0, printf_sint/printf_sint::value#3 )
[98] utoa::value#1 = (unsigned int)printf_sint::value#5
[99] call utoa
to:printf_sint::@3
printf_sint::@3: scope:[printf_sint] from printf_sint::@2
[100] printf_number_buffer::buffer_sign#0 = *((char *)&printf_buffer)
[101] call printf_number_buffer
to:printf_sint::@return
printf_sint::@return: scope:[printf_sint] from printf_sint::@3
[102] return
to:@return
void printf_uint(void (*putc)(char) , unsigned int uvalue , char format_min_length , char format_justify_left , char format_sign_always , char format_zero_padding , char format_upper_case , char format_radix)
printf_uint: scope:[printf_uint] from main::@12
[103] phi()
to:printf_uint::@1
printf_uint::@1: scope:[printf_uint] from printf_uint
[104] *((char *)&printf_buffer) = 0
[105] call utoa
to:printf_uint::@2
printf_uint::@2: scope:[printf_uint] from printf_uint::@1
[106] printf_number_buffer::buffer_sign#1 = *((char *)&printf_buffer)
[107] call printf_number_buffer
to:printf_uint::@return
printf_uint::@return: scope:[printf_uint] from printf_uint::@2
[108] return
to:@return
void utoa(unsigned int value , char *buffer , char radix)
utoa: scope:[utoa] from printf_sint::@2 printf_uint::@1
[109] utoa::value#10 = phi( printf_sint::@2/utoa::value#1, printf_uint::@1/printf_uint::uvalue#0 )
[109] utoa::radix#2 = phi( printf_sint::@2/DECIMAL, printf_uint::@1/HEXADECIMAL )
[110] if(utoa::radix#2==DECIMAL) goto utoa::@1
to:utoa::@2
utoa::@2: scope:[utoa] from utoa
[111] if(utoa::radix#2==HEXADECIMAL) goto utoa::@1
to:utoa::@3
utoa::@3: scope:[utoa] from utoa::@2
[112] if(utoa::radix#2==OCTAL) goto utoa::@1
to:utoa::@4
utoa::@4: scope:[utoa] from utoa::@3
[113] if(utoa::radix#2==BINARY) goto utoa::@1
to:utoa::@5
utoa::@5: scope:[utoa] from utoa::@4
[114] *((char *)&printf_buffer+OFFSET_STRUCT_PRINTF_BUFFER_NUMBER_DIGITS) = 'e'
[115] *((char *)&printf_buffer+OFFSET_STRUCT_PRINTF_BUFFER_NUMBER_DIGITS+1) = 'r'
[116] *((char *)&printf_buffer+OFFSET_STRUCT_PRINTF_BUFFER_NUMBER_DIGITS+2) = 'r'
[117] *((char *)&printf_buffer+OFFSET_STRUCT_PRINTF_BUFFER_NUMBER_DIGITS+3) = 0
to:utoa::@return
utoa::@return: scope:[utoa] from utoa::@5 utoa::@8
[118] return
to:@return
utoa::@1: scope:[utoa] from utoa utoa::@2 utoa::@3 utoa::@4
[119] utoa::digit_values#8 = phi( utoa/RADIX_DECIMAL_VALUES, utoa::@2/RADIX_HEXADECIMAL_VALUES, utoa::@3/RADIX_OCTAL_VALUES, utoa::@4/RADIX_BINARY_VALUES )
[119] utoa::max_digits#7 = phi( utoa/5, utoa::@2/4, utoa::@3/6, utoa::@4/$10 )
to:utoa::@6
utoa::@6: scope:[utoa] from utoa::@1 utoa::@9
[120] utoa::buffer#10 = phi( utoa::@9/utoa::buffer#15, utoa::@1/(char *)&printf_buffer+OFFSET_STRUCT_PRINTF_BUFFER_NUMBER_DIGITS )
[120] utoa::started#2 = phi( utoa::@9/utoa::started#4, utoa::@1/0 )
[120] utoa::value#3 = phi( utoa::@9/utoa::value#7, utoa::@1/utoa::value#10 )
[120] utoa::digit#2 = phi( utoa::@9/utoa::digit#1, utoa::@1/0 )
[121] utoa::$4 = utoa::max_digits#7 - 1
[122] if(utoa::digit#2<utoa::$4) goto utoa::@7
to:utoa::@8
utoa::@8: scope:[utoa] from utoa::@6
[123] utoa::$11 = (char)utoa::value#3
[124] *utoa::buffer#10 = DIGITS[utoa::$11]
[125] utoa::buffer#3 = ++ utoa::buffer#10
[126] *utoa::buffer#3 = 0
to:utoa::@return
utoa::@7: scope:[utoa] from utoa::@6
[127] utoa::$10 = utoa::digit#2 << 1
[128] utoa::digit_value#0 = utoa::digit_values#8[utoa::$10]
[129] if(0!=utoa::started#2) goto utoa::@10
to:utoa::@12
utoa::@12: scope:[utoa] from utoa::@7
[130] if(utoa::value#3>=utoa::digit_value#0) goto utoa::@10
to:utoa::@9
utoa::@9: scope:[utoa] from utoa::@11 utoa::@12
[131] utoa::buffer#15 = phi( utoa::@12/utoa::buffer#10, utoa::@11/utoa::buffer#4 )
[131] utoa::started#4 = phi( utoa::@12/utoa::started#2, utoa::@11/1 )
[131] utoa::value#7 = phi( utoa::@12/utoa::value#3, utoa::@11/utoa::value#0 )
[132] utoa::digit#1 = ++ utoa::digit#2
to:utoa::@6
utoa::@10: scope:[utoa] from utoa::@12 utoa::@7
[133] utoa_append::buffer#0 = utoa::buffer#10
[134] utoa_append::value#0 = utoa::value#3
[135] utoa_append::sub#0 = utoa::digit_value#0
[136] call utoa_append
[137] utoa_append::return#0 = utoa_append::value#2
to:utoa::@11
utoa::@11: scope:[utoa] from utoa::@10
[138] utoa::value#0 = utoa_append::return#0
[139] utoa::buffer#4 = ++ utoa::buffer#10
to:utoa::@9
void printf_number_buffer(void (*putc)(char) , char buffer_sign , char *buffer_digits , char format_min_length , char format_justify_left , char format_sign_always , char format_zero_padding , char format_upper_case , char format_radix)
printf_number_buffer: scope:[printf_number_buffer] from printf_sint::@3 printf_uint::@2
[140] printf_number_buffer::format_upper_case#10 = phi( printf_sint::@3/0, printf_uint::@2/printf_uint::format_upper_case#0 )
[140] printf_number_buffer::putc#10 = phi( printf_sint::@3/&snputc, printf_uint::@2/printf_uint::putc#0 )
[140] printf_number_buffer::buffer_sign#10 = phi( printf_sint::@3/printf_number_buffer::buffer_sign#0, printf_uint::@2/printf_number_buffer::buffer_sign#1 )
[140] printf_number_buffer::format_zero_padding#10 = phi( printf_sint::@3/0, printf_uint::@2/printf_uint::format_zero_padding#0 )
[140] printf_number_buffer::format_justify_left#10 = phi( printf_sint::@3/0, printf_uint::@2/printf_uint::format_justify_left#0 )
[140] printf_number_buffer::format_min_length#2 = phi( printf_sint::@3/0, printf_uint::@2/printf_uint::format_min_length#0 )
[141] if(0==printf_number_buffer::format_min_length#2) goto printf_number_buffer::@1
to:printf_number_buffer::@6
printf_number_buffer::@6: scope:[printf_number_buffer] from printf_number_buffer
[142] phi()
[143] call strlen
[144] strlen::return#2 = strlen::len#2
to:printf_number_buffer::@14
printf_number_buffer::@14: scope:[printf_number_buffer] from printf_number_buffer::@6
[145] printf_number_buffer::$19 = strlen::return#2
[146] printf_number_buffer::len#0 = (signed char)printf_number_buffer::$19
[147] if(0==printf_number_buffer::buffer_sign#10) goto printf_number_buffer::@13
to:printf_number_buffer::@7
printf_number_buffer::@7: scope:[printf_number_buffer] from printf_number_buffer::@14
[148] printf_number_buffer::len#1 = ++ printf_number_buffer::len#0
to:printf_number_buffer::@13
printf_number_buffer::@13: scope:[printf_number_buffer] from printf_number_buffer::@14 printf_number_buffer::@7
[149] printf_number_buffer::len#2 = phi( printf_number_buffer::@14/printf_number_buffer::len#0, printf_number_buffer::@7/printf_number_buffer::len#1 )
[150] printf_number_buffer::padding#1 = (signed char)printf_number_buffer::format_min_length#2 - printf_number_buffer::len#2
[151] if(printf_number_buffer::padding#1>=0) goto printf_number_buffer::@21
to:printf_number_buffer::@1
printf_number_buffer::@21: scope:[printf_number_buffer] from printf_number_buffer::@13
[152] phi()
to:printf_number_buffer::@1
printf_number_buffer::@1: scope:[printf_number_buffer] from printf_number_buffer printf_number_buffer::@13 printf_number_buffer::@21
[153] printf_number_buffer::padding#10 = phi( printf_number_buffer/0, printf_number_buffer::@21/printf_number_buffer::padding#1, printf_number_buffer::@13/0 )
[154] if(0!=printf_number_buffer::format_justify_left#10) goto printf_number_buffer::@2
to:printf_number_buffer::@17
printf_number_buffer::@17: scope:[printf_number_buffer] from printf_number_buffer::@1
[155] if(0!=printf_number_buffer::format_zero_padding#10) goto printf_number_buffer::@2
to:printf_number_buffer::@16
printf_number_buffer::@16: scope:[printf_number_buffer] from printf_number_buffer::@17
[156] if(0!=printf_number_buffer::padding#10) goto printf_number_buffer::@8
to:printf_number_buffer::@2
printf_number_buffer::@8: scope:[printf_number_buffer] from printf_number_buffer::@16
[157] printf_padding::putc#0 = printf_number_buffer::putc#10
[158] printf_padding::length#0 = (char)printf_number_buffer::padding#10
[159] call printf_padding
to:printf_number_buffer::@2
printf_number_buffer::@2: scope:[printf_number_buffer] from printf_number_buffer::@1 printf_number_buffer::@16 printf_number_buffer::@17 printf_number_buffer::@8
[160] if(0==printf_number_buffer::buffer_sign#10) goto printf_number_buffer::@3
to:printf_number_buffer::@9
printf_number_buffer::@9: scope:[printf_number_buffer] from printf_number_buffer::@2
[161] stackpush(char) = printf_number_buffer::buffer_sign#10
[162] callexecute *printf_number_buffer::putc#10
sideeffect stackpullbytes(1)
to:printf_number_buffer::@3
printf_number_buffer::@3: scope:[printf_number_buffer] from printf_number_buffer::@2 printf_number_buffer::@9
[164] if(0==printf_number_buffer::format_zero_padding#10) goto printf_number_buffer::@4
to:printf_number_buffer::@18
printf_number_buffer::@18: scope:[printf_number_buffer] from printf_number_buffer::@3
[165] if(0!=printf_number_buffer::padding#10) goto printf_number_buffer::@10
to:printf_number_buffer::@4
printf_number_buffer::@10: scope:[printf_number_buffer] from printf_number_buffer::@18
[166] printf_padding::putc#1 = printf_number_buffer::putc#10
[167] printf_padding::length#1 = (char)printf_number_buffer::padding#10
[168] call printf_padding
to:printf_number_buffer::@4
printf_number_buffer::@4: scope:[printf_number_buffer] from printf_number_buffer::@10 printf_number_buffer::@18 printf_number_buffer::@3
[169] if(0==printf_number_buffer::format_upper_case#10) goto printf_number_buffer::@5
to:printf_number_buffer::@11
printf_number_buffer::@11: scope:[printf_number_buffer] from printf_number_buffer::@4
[170] phi()
[171] call strupr
to:printf_number_buffer::@5
printf_number_buffer::@5: scope:[printf_number_buffer] from printf_number_buffer::@11 printf_number_buffer::@4
[172] printf_str::putc#0 = printf_number_buffer::putc#10
[173] call printf_str
to:printf_number_buffer::@15
printf_number_buffer::@15: scope:[printf_number_buffer] from printf_number_buffer::@5
[174] if(0==printf_number_buffer::format_justify_left#10) goto printf_number_buffer::@return
to:printf_number_buffer::@20
printf_number_buffer::@20: scope:[printf_number_buffer] from printf_number_buffer::@15
[175] if(0!=printf_number_buffer::format_zero_padding#10) goto printf_number_buffer::@return
to:printf_number_buffer::@19
printf_number_buffer::@19: scope:[printf_number_buffer] from printf_number_buffer::@20
[176] if(0!=printf_number_buffer::padding#10) goto printf_number_buffer::@12
to:printf_number_buffer::@return
printf_number_buffer::@12: scope:[printf_number_buffer] from printf_number_buffer::@19
[177] printf_padding::putc#2 = printf_number_buffer::putc#10
[178] printf_padding::length#2 = (char)printf_number_buffer::padding#10
[179] call printf_padding
to:printf_number_buffer::@return
printf_number_buffer::@return: scope:[printf_number_buffer] from printf_number_buffer::@12 printf_number_buffer::@15 printf_number_buffer::@19 printf_number_buffer::@20
[180] return
to:@return
unsigned int utoa_append(char *buffer , unsigned int value , unsigned int sub)
utoa_append: scope:[utoa_append] from utoa::@10
[181] phi()
to:utoa_append::@1
utoa_append::@1: scope:[utoa_append] from utoa_append utoa_append::@2
[182] utoa_append::digit#2 = phi( utoa_append/0, utoa_append::@2/utoa_append::digit#1 )
[182] utoa_append::value#2 = phi( utoa_append/utoa_append::value#0, utoa_append::@2/utoa_append::value#1 )
[183] if(utoa_append::value#2>=utoa_append::sub#0) goto utoa_append::@2
to:utoa_append::@3
utoa_append::@3: scope:[utoa_append] from utoa_append::@1
[184] *utoa_append::buffer#0 = DIGITS[utoa_append::digit#2]
to:utoa_append::@return
utoa_append::@return: scope:[utoa_append] from utoa_append::@3
[185] return
to:@return
utoa_append::@2: scope:[utoa_append] from utoa_append::@1
[186] utoa_append::digit#1 = ++ utoa_append::digit#2
[187] utoa_append::value#1 = utoa_append::value#2 - utoa_append::sub#0
to:utoa_append::@1
unsigned int strlen(char *str)
strlen: scope:[strlen] from printf_number_buffer::@6
[188] phi()
to:strlen::@1
strlen::@1: scope:[strlen] from strlen strlen::@2
[189] strlen::len#2 = phi( strlen/0, strlen::@2/strlen::len#1 )
[189] strlen::str#3 = phi( strlen/(char *)&printf_buffer+OFFSET_STRUCT_PRINTF_BUFFER_NUMBER_DIGITS, strlen::@2/strlen::str#0 )
[190] if(0!=*strlen::str#3) goto strlen::@2
to:strlen::@return
strlen::@return: scope:[strlen] from strlen::@1
[191] return
to:@return
strlen::@2: scope:[strlen] from strlen::@1
[192] strlen::len#1 = ++ strlen::len#2
[193] strlen::str#0 = ++ strlen::str#3
to:strlen::@1
void printf_padding(void (*putc)(char) , char pad , char length)
printf_padding: scope:[printf_padding] from printf_number_buffer::@10 printf_number_buffer::@12 printf_number_buffer::@8
[194] printf_padding::putc#7 = phi( printf_number_buffer::@10/printf_padding::putc#1, printf_number_buffer::@12/printf_padding::putc#2, printf_number_buffer::@8/printf_padding::putc#0 )
[194] printf_padding::pad#7 = phi( printf_number_buffer::@10/'0', printf_number_buffer::@12/' ', printf_number_buffer::@8/' ' )
[194] printf_padding::length#6 = phi( printf_number_buffer::@10/printf_padding::length#1, printf_number_buffer::@12/printf_padding::length#2, printf_number_buffer::@8/printf_padding::length#0 )
to:printf_padding::@1
printf_padding::@1: scope:[printf_padding] from printf_padding printf_padding::@3
[195] printf_padding::i#2 = phi( printf_padding/0, printf_padding::@3/printf_padding::i#1 )
[196] if(printf_padding::i#2<printf_padding::length#6) goto printf_padding::@2
to:printf_padding::@return
printf_padding::@return: scope:[printf_padding] from printf_padding::@1
[197] return
to:@return
printf_padding::@2: scope:[printf_padding] from printf_padding::@1
[198] stackpush(char) = printf_padding::pad#7
[199] callexecute *printf_padding::putc#7
sideeffect stackpullbytes(1)
to:printf_padding::@3
printf_padding::@3: scope:[printf_padding] from printf_padding::@2
[201] printf_padding::i#1 = ++ printf_padding::i#2
to:printf_padding::@1
char * strupr(char *str)
strupr: scope:[strupr] from printf_number_buffer::@11
[202] phi()
to:strupr::@1
strupr::@1: scope:[strupr] from strupr strupr::@3
[203] strupr::src#2 = phi( strupr/strupr::str#0, strupr::@3/strupr::src#1 )
[204] if(0!=*strupr::src#2) goto strupr::@2
to:strupr::@return
strupr::@return: scope:[strupr] from strupr::@1
[205] return
to:@return
strupr::@2: scope:[strupr] from strupr::@1
[206] toupper::ch#0 = *strupr::src#2
[207] call toupper
[208] toupper::return#3 = toupper::return#2
to:strupr::@3
strupr::@3: scope:[strupr] from strupr::@2
[209] strupr::$0 = toupper::return#3
[210] *strupr::src#2 = strupr::$0
[211] strupr::src#1 = ++ strupr::src#2
to:strupr::@1
char toupper(char ch)
toupper: scope:[toupper] from strupr::@2
[212] if(toupper::ch#0<'a') goto toupper::@return
to:toupper::@2
toupper::@2: scope:[toupper] from toupper
[213] if(toupper::ch#0<='z') goto toupper::@1
to:toupper::@return
toupper::@1: scope:[toupper] from toupper::@2
[214] toupper::return#0 = toupper::ch#0 + 'A'-'a'
to:toupper::@return
toupper::@return: scope:[toupper] from toupper toupper::@1 toupper::@2
[215] toupper::return#2 = phi( toupper::@1/toupper::return#0, toupper/toupper::ch#0, toupper::@2/toupper::ch#0 )
[216] return
to:@return

7762
src/test/ref/printf-17.log Normal file

File diff suppressed because one or more lines are too long

238
src/test/ref/printf-17.sym Normal file
View File

@@ -0,0 +1,238 @@
__constant char BINARY = 2
__constant char BUF[$14] = { fill( $14, 0) }
__constant char DECIMAL = $a
__constant char DIGITS[] = "0123456789abcdef"z
__constant char HEXADECIMAL = $10
__constant char OCTAL = 8
__constant char OFFSET_STRUCT_PRINTF_BUFFER_NUMBER_DIGITS = 1
__constant char RADIX::BINARY = 2
__constant char RADIX::DECIMAL = $a
__constant char RADIX::HEXADECIMAL = $10
__constant char RADIX::OCTAL = 8
__constant unsigned int RADIX_BINARY_VALUES[] = { $8000, $4000, $2000, $1000, $800, $400, $200, $100, $80, $40, $20, $10, 8, 4, 2 }
__constant unsigned int RADIX_DECIMAL_VALUES[] = { $2710, $3e8, $64, $a }
__constant unsigned int RADIX_HEXADECIMAL_VALUES[] = { $1000, $100, $10 }
__constant unsigned int RADIX_OCTAL_VALUES[] = { $8000, $1000, $200, $40, 8 }
__constant char SIZEOF_STRUCT_PRINTF_BUFFER_NUMBER = $c
__constant unsigned int STACK_BASE = $103
__loadstore char *__snprintf_buffer // zp[2]:22 9.022222222222222
__loadstore volatile unsigned int __snprintf_capacity // zp[2]:18 6.48936170212766
__loadstore volatile unsigned int __snprintf_size // zp[2]:20 11.021739130434781
void __start()
void main()
__constant char main::s[$e] = "hello world! "
__constant char main::s1[7] = "hello "
__constant char main::s2[2] = " "
__constant char main::s4[2] = "+"
__constant char main::s5[3] = "! "
__constant char main::s6[4] = "hi "
__constant char main::str[6] = "world"
void print(char *msg)
char *print::msg
char *print::msg#0 // msg zp[2]:11 2002.0
char *print::msg#5 // msg zp[2]:11 1001.0
__loadstore struct printf_buffer_number printf_buffer = {} // mem[12]
void printf_number_buffer(void (*putc)(char) , char buffer_sign , char *buffer_digits , char format_min_length , char format_justify_left , char format_sign_always , char format_zero_padding , char format_upper_case , char format_radix)
unsigned int printf_number_buffer::$19 // zp[2]:13 1001.0
struct printf_buffer_number printf_number_buffer::buffer
char *printf_number_buffer::buffer_digits
char printf_number_buffer::buffer_sign
char printf_number_buffer::buffer_sign#0 // buffer_sign zp[1]:8 202.0
char printf_number_buffer::buffer_sign#1 // buffer_sign zp[1]:8 202.0
char printf_number_buffer::buffer_sign#10 // buffer_sign zp[1]:8 152.61904761904762
struct printf_format_number printf_number_buffer::format
char printf_number_buffer::format_justify_left
char printf_number_buffer::format_justify_left#10 // format_justify_left zp[1]:6 60.666666666666664
char printf_number_buffer::format_min_length
char printf_number_buffer::format_min_length#2 // reg byte x 100.1
char printf_number_buffer::format_radix
char printf_number_buffer::format_sign_always
char printf_number_buffer::format_upper_case
char printf_number_buffer::format_upper_case#10 // format_upper_case zp[1]:9 35.75
char printf_number_buffer::format_zero_padding
char printf_number_buffer::format_zero_padding#10 // format_zero_padding zp[1]:7 88.32352941176471
signed char printf_number_buffer::len
signed char printf_number_buffer::len#0 // reg byte y 1501.5
signed char printf_number_buffer::len#1 // reg byte y 2002.0
signed char printf_number_buffer::len#2 // reg byte y 3003.0
signed char printf_number_buffer::padding
signed char printf_number_buffer::padding#1 // padding zp[1]:10 1001.0
signed char printf_number_buffer::padding#10 // padding zp[1]:10 166.83333333333334
void (*printf_number_buffer::putc)(char)
void (*printf_number_buffer::putc#10)(char) // putc zp[2]:4 111.22222222222223
void printf_padding(void (*putc)(char) , char pad , char length)
char printf_padding::i
char printf_padding::i#1 // i zp[1]:17 200002.0
char printf_padding::i#2 // i zp[1]:17 100001.0
char printf_padding::length
char printf_padding::length#0 // length zp[1]:15 2002.0
char printf_padding::length#1 // length zp[1]:15 2002.0
char printf_padding::length#2 // length zp[1]:15 2002.0
char printf_padding::length#6 // length zp[1]:15 20600.8
char printf_padding::pad
char printf_padding::pad#7 // pad zp[1]:16 16666.833333333332
void (*printf_padding::putc)(char)
void (*printf_padding::putc#0)(char) // putc zp[2]:4 1001.0
void (*printf_padding::putc#1)(char) // putc zp[2]:4 1001.0
void (*printf_padding::putc#2)(char) // putc zp[2]:4 1001.0
void (*printf_padding::putc#7)(char) // putc zp[2]:4 30030.0
void printf_sint(void (*putc)(char) , int value , char format_min_length , char format_justify_left , char format_sign_always , char format_zero_padding , char format_upper_case , char format_radix)
struct printf_format_number printf_sint::format
char printf_sint::format_justify_left
char printf_sint::format_min_length
char printf_sint::format_radix
char printf_sint::format_sign_always
char printf_sint::format_upper_case
char printf_sint::format_zero_padding
void (*printf_sint::putc)(char)
unsigned int printf_sint::uvalue
int printf_sint::value
int printf_sint::value#0 // value zp[2]:4 101.0
int printf_sint::value#3 // value zp[2]:4 101.0
int printf_sint::value#5 // value zp[2]:4 202.0
void printf_str(void (*putc)(char) , const char *s)
char printf_str::c
char printf_str::c#1 // reg byte a 100001.0
void (*printf_str::putc)(char)
void (*printf_str::putc#0)(char) // putc zp[2]:4 2002.0
void (*printf_str::putc#12)(char) // putc zp[2]:4 10010.0
const char *printf_str::s
const char *printf_str::s#0 // s zp[2]:11 100001.0
const char *printf_str::s#11 // s zp[2]:11 155002.0
const char *printf_str::s#12 // s zp[2]:11 10001.0
void printf_string(void (*putc)(char) , char *str , char format_min_length , char format_justify_left)
struct printf_format_string printf_string::format
char printf_string::format_justify_left
char printf_string::format_min_length
signed char printf_string::len
signed char printf_string::padding
void (*printf_string::putc)(char)
__constant void (*printf_string::putc#0)(char) = &snputc // putc
char *printf_string::str
void printf_uint(void (*putc)(char) , unsigned int uvalue , char format_min_length , char format_justify_left , char format_sign_always , char format_zero_padding , char format_upper_case , char format_radix)
struct printf_format_number printf_uint::format
char printf_uint::format_justify_left
__constant char printf_uint::format_justify_left#0 = 0 // format_justify_left
char printf_uint::format_min_length
__constant char printf_uint::format_min_length#0 = 0 // format_min_length
char printf_uint::format_radix
char printf_uint::format_sign_always
char printf_uint::format_upper_case
__constant char printf_uint::format_upper_case#0 = 0 // format_upper_case
char printf_uint::format_zero_padding
__constant char printf_uint::format_zero_padding#0 = 0 // format_zero_padding
void (*printf_uint::putc)(char)
__constant void (*printf_uint::putc#0)(char) = &snputc // putc
unsigned int printf_uint::uvalue
__constant unsigned int printf_uint::uvalue#0 = $b // uvalue
char *screen
char *screen#0 // screen zp[2]:2 1001.0
char *screen#1 // screen zp[2]:2 68.19565217391305
char *screen#25 // screen zp[2]:2 134.0
void snprintf_init(char *s , unsigned int n)
unsigned int snprintf_init::n
unsigned int snprintf_init::n#4 // n zp[2]:4 101.0
char *snprintf_init::s
__stackcall void snputc(char c)
__constant char snputc::OFFSET_STACK_C = 0
char snputc::c
char snputc::c#0 // reg byte x 40.4
char snputc::c#2 // reg byte x 202.0
unsigned int strlen(char *str)
unsigned int strlen::len
unsigned int strlen::len#1 // len zp[2]:13 100001.0
unsigned int strlen::len#2 // len zp[2]:13 50250.75
unsigned int strlen::return
unsigned int strlen::return#2 // return zp[2]:13 2002.0
char *strlen::str
char *strlen::str#0 // str zp[2]:11 200002.0
char *strlen::str#3 // str zp[2]:11 100001.0
char * strupr(char *str)
char strupr::$0 // reg byte a 200002.0
char *strupr::return
char *strupr::src
char *strupr::src#1 // src zp[2]:24 200002.0
char *strupr::src#2 // src zp[2]:24 71429.28571428571
char *strupr::str
__constant char *strupr::str#0 = (char *)&printf_buffer+OFFSET_STRUCT_PRINTF_BUFFER_NUMBER_DIGITS // str
char toupper(char ch)
char toupper::ch
char toupper::ch#0 // reg byte a 1700002.0000000002
char toupper::return
char toupper::return#0 // reg byte a 2000002.0
char toupper::return#2 // reg byte a 1033334.6666666667
char toupper::return#3 // reg byte a 200002.0
void utoa(unsigned int value , char *buffer , char radix)
char utoa::$10 // reg byte a 20002.0
char utoa::$11 // reg byte x 2002.0
char utoa::$4 // reg byte a 20002.0
char *utoa::buffer
char *utoa::buffer#10 // buffer zp[2]:13 2800.4000000000005
char *utoa::buffer#15 // buffer zp[2]:13 15001.5
char *utoa::buffer#3 // buffer zp[2]:13 2002.0
char *utoa::buffer#4 // buffer zp[2]:13 20002.0
char utoa::digit
char utoa::digit#1 // digit zp[1]:7 20002.0
char utoa::digit#2 // digit zp[1]:7 2666.9333333333334
unsigned int utoa::digit_value
unsigned int utoa::digit_value#0 // digit_value zp[2]:24 6000.6
unsigned int *utoa::digit_values
unsigned int *utoa::digit_values#8 // digit_values zp[2]:11 588.2941176470588
char utoa::max_digits
char utoa::max_digits#7 // max_digits zp[1]:6 588.2941176470588
char utoa::radix
char utoa::radix#2 // reg byte x 1001.0
char utoa::started
char utoa::started#2 // reg byte x 4286.142857142857
char utoa::started#4 // reg byte x 10001.0
unsigned int utoa::value
unsigned int utoa::value#0 // value zp[2]:4 10001.0
unsigned int utoa::value#1 // value zp[2]:4 202.0
unsigned int utoa::value#10 // value zp[2]:4 183.66666666666669
unsigned int utoa::value#3 // value zp[2]:4 5125.625
unsigned int utoa::value#7 // value zp[2]:4 15001.5
unsigned int utoa_append(char *buffer , unsigned int value , unsigned int sub)
char *utoa_append::buffer
char *utoa_append::buffer#0 // buffer zp[2]:13 13750.25
char utoa_append::digit
char utoa_append::digit#1 // reg byte x 1.0000001E7
char utoa_append::digit#2 // reg byte x 1.00500015E7
unsigned int utoa_append::return
unsigned int utoa_append::return#0 // return zp[2]:4 20002.0
unsigned int utoa_append::sub
unsigned int utoa_append::sub#0 // sub zp[2]:24 3335000.5
unsigned int utoa_append::value
unsigned int utoa_append::value#0 // value zp[2]:4 36667.33333333333
unsigned int utoa_append::value#1 // value zp[2]:4 2.0000002E7
unsigned int utoa_append::value#2 // value zp[2]:4 5018334.166666666
reg byte x [ snputc::c#2 snputc::c#0 ]
zp[2]:2 [ screen#25 screen#1 screen#0 ]
zp[2]:4 [ printf_sint::value#5 printf_sint::value#0 printf_sint::value#3 utoa::value#3 utoa::value#7 utoa::value#10 utoa::value#1 utoa::value#0 utoa_append::value#2 utoa_append::value#0 utoa_append::value#1 utoa_append::return#0 printf_str::putc#12 printf_str::putc#0 printf_number_buffer::putc#10 printf_padding::putc#7 printf_padding::putc#1 printf_padding::putc#2 printf_padding::putc#0 snprintf_init::n#4 ]
reg byte x [ utoa::radix#2 ]
reg byte x [ utoa::started#2 utoa::started#4 ]
reg byte x [ printf_number_buffer::format_min_length#2 ]
zp[1]:6 [ printf_number_buffer::format_justify_left#10 utoa::max_digits#7 ]
zp[1]:7 [ printf_number_buffer::format_zero_padding#10 utoa::digit#2 utoa::digit#1 ]
zp[1]:8 [ printf_number_buffer::buffer_sign#10 printf_number_buffer::buffer_sign#0 printf_number_buffer::buffer_sign#1 ]
zp[1]:9 [ printf_number_buffer::format_upper_case#10 ]
reg byte y [ printf_number_buffer::len#2 printf_number_buffer::len#0 printf_number_buffer::len#1 ]
zp[1]:10 [ printf_number_buffer::padding#10 printf_number_buffer::padding#1 ]
reg byte x [ utoa_append::digit#2 utoa_append::digit#1 ]
zp[2]:11 [ strlen::str#3 strlen::str#0 utoa::digit_values#8 print::msg#5 print::msg#0 printf_str::s#11 printf_str::s#12 printf_str::s#0 ]
zp[2]:13 [ strlen::len#2 strlen::len#1 strlen::return#2 printf_number_buffer::$19 utoa::buffer#10 utoa::buffer#15 utoa::buffer#4 utoa::buffer#3 utoa_append::buffer#0 ]
zp[1]:15 [ printf_padding::length#6 printf_padding::length#1 printf_padding::length#2 printf_padding::length#0 ]
zp[1]:16 [ printf_padding::pad#7 ]
zp[1]:17 [ printf_padding::i#2 printf_padding::i#1 ]
reg byte a [ toupper::return#2 toupper::return#0 toupper::ch#0 ]
zp[2]:18 [ __snprintf_capacity ]
zp[2]:20 [ __snprintf_size ]
zp[2]:22 [ __snprintf_buffer ]
reg byte a [ printf_str::c#1 ]
reg byte a [ utoa::$4 ]
reg byte x [ utoa::$11 ]
reg byte a [ utoa::$10 ]
zp[2]:24 [ utoa::digit_value#0 utoa_append::sub#0 strupr::src#2 strupr::src#1 ]
reg byte a [ toupper::return#3 ]
reg byte a [ strupr::$0 ]
mem[12] [ printf_buffer ]

View File

@@ -230,14 +230,14 @@ compare: {
jmp __b6 jmp __b6
__b3: __b3:
// if(w1>w2) // if(w1>w2)
lda.z w1+1 lda.z w2+1
cmp.z w2+1 cmp.z w1+1
bne !+ bcc !+
lda.z w1 bne __b11
cmp.z w2 lda.z w2
beq __b11 cmp.z w1
bcs __b11
!: !:
bcc __b11
lda #TT lda #TT
sta.z r sta.z r
jmp __b22 jmp __b22
@@ -274,14 +274,14 @@ compare: {
jmp __b6 jmp __b6
__b1: __b1:
// if(w1<w2) // if(w1<w2)
lda.z w2+1 lda.z w1+1
cmp.z w1+1 cmp.z w2+1
bne !+ bcc !+
lda.z w2 bne __b13
cmp.z w1 lda.z w1
beq __b13 cmp.z w2
bcs __b13
!: !:
bcc __b13
lda #TT lda #TT
sta.z r sta.z r
jmp __b24 jmp __b24

View File

@@ -2480,14 +2480,14 @@ compare: {
// compare::@3 // compare::@3
__b3: __b3:
// [56] if(compare::w1#0<=compare::w2#0) goto compare::@22 -- vwuz1_le_vwuz2_then_la1 // [56] if(compare::w1#0<=compare::w2#0) goto compare::@22 -- vwuz1_le_vwuz2_then_la1
lda.z w1+1 lda.z w2+1
cmp.z w2+1 cmp.z w1+1
bne !+ bcc !+
lda.z w1 bne __b22_from___b3
cmp.z w2 lda.z w2
beq __b22_from___b3 cmp.z w1
bcs __b22_from___b3
!: !:
bcc __b22_from___b3
// [57] phi from compare::@3 to compare::@16 [phi:compare::@3->compare::@16] // [57] phi from compare::@3 to compare::@16 [phi:compare::@3->compare::@16]
__b16_from___b3: __b16_from___b3:
jmp __b16 jmp __b16
@@ -2558,14 +2558,14 @@ compare: {
// compare::@1 // compare::@1
__b1: __b1:
// [62] if(compare::w1#0>=compare::w2#0) goto compare::@24 -- vwuz1_ge_vwuz2_then_la1 // [62] if(compare::w1#0>=compare::w2#0) goto compare::@24 -- vwuz1_ge_vwuz2_then_la1
lda.z w2+1 lda.z w1+1
cmp.z w1+1 cmp.z w2+1
bne !+ bcc !+
lda.z w2 bne __b24_from___b1
cmp.z w1 lda.z w1
beq __b24_from___b1 cmp.z w2
bcs __b24_from___b1
!: !:
bcc __b24_from___b1
// [63] phi from compare::@1 to compare::@18 [phi:compare::@1->compare::@18] // [63] phi from compare::@1 to compare::@18 [phi:compare::@1->compare::@18]
__b18_from___b1: __b18_from___b1:
jmp __b18 jmp __b18
@@ -3517,14 +3517,14 @@ compare: {
__b3: __b3:
// if(w1>w2) // if(w1>w2)
// [56] if(compare::w1#0<=compare::w2#0) goto compare::@22 -- vwuz1_le_vwuz2_then_la1 // [56] if(compare::w1#0<=compare::w2#0) goto compare::@22 -- vwuz1_le_vwuz2_then_la1
lda.z w1+1 lda.z w2+1
cmp.z w2+1 cmp.z w1+1
bne !+ bcc !+
lda.z w1 bne __b11
cmp.z w2 lda.z w2
beq __b11 cmp.z w1
bcs __b11
!: !:
bcc __b11
// [57] phi from compare::@3 to compare::@16 [phi:compare::@3->compare::@16] // [57] phi from compare::@3 to compare::@16 [phi:compare::@3->compare::@16]
// compare::@16 // compare::@16
// [58] phi from compare::@16 to compare::@22 [phi:compare::@16->compare::@22] // [58] phi from compare::@16 to compare::@22 [phi:compare::@16->compare::@22]
@@ -3585,14 +3585,14 @@ compare: {
__b1: __b1:
// if(w1<w2) // if(w1<w2)
// [62] if(compare::w1#0>=compare::w2#0) goto compare::@24 -- vwuz1_ge_vwuz2_then_la1 // [62] if(compare::w1#0>=compare::w2#0) goto compare::@24 -- vwuz1_ge_vwuz2_then_la1
lda.z w2+1 lda.z w1+1
cmp.z w1+1 cmp.z w2+1
bne !+ bcc !+
lda.z w2 bne __b13
cmp.z w1 lda.z w1
beq __b13 cmp.z w2
bcs __b13
!: !:
bcc __b13
// [63] phi from compare::@1 to compare::@18 [phi:compare::@1->compare::@18] // [63] phi from compare::@1 to compare::@18 [phi:compare::@1->compare::@18]
// compare::@18 // compare::@18
// [64] phi from compare::@18 to compare::@24 [phi:compare::@18->compare::@24] // [64] phi from compare::@18 to compare::@24 [phi:compare::@18->compare::@24]

View File

@@ -466,13 +466,14 @@ utoa: {
// if (started || value >= digit_value) // if (started || value >= digit_value)
cpx #0 cpx #0
bne __b5 bne __b5
cmp.z value+1 lda.z value+1
bne !+ cmp.z digit_value+1
lda.z digit_value bcc !+
cmp.z value bne __b5
beq __b5 lda.z value
cmp.z digit_value
bcs __b5
!: !:
bcc __b5
__b4: __b4:
// for( char digit=0; digit<max_digits-1; digit++ ) // for( char digit=0; digit<max_digits-1; digit++ )
inc.z digit inc.z digit
@@ -612,14 +613,14 @@ utoa_append: {
ldx #0 ldx #0
__b1: __b1:
// while (value >= sub) // while (value >= sub)
lda.z sub+1 lda.z value+1
cmp.z value+1 cmp.z sub+1
bne !+ bcc !+
lda.z sub bne __b2
cmp.z value lda.z value
beq __b2 cmp.z sub
bcs __b2
!: !:
bcc __b2
// *buffer = DIGITS[digit] // *buffer = DIGITS[digit]
lda DIGITS,x lda DIGITS,x
ldy #0 ldy #0

View File

@@ -4762,14 +4762,14 @@ utoa: {
// utoa::@7 // utoa::@7
__b7: __b7:
// [108] if(utoa::value#2>=utoa::digit_value#0) goto utoa::@5 -- vwuz1_ge_vwuz2_then_la1 // [108] if(utoa::value#2>=utoa::digit_value#0) goto utoa::@5 -- vwuz1_ge_vwuz2_then_la1
lda.z digit_value+1 lda.z value+1
cmp.z value+1 cmp.z digit_value+1
bne !+ bcc !+
lda.z digit_value bne __b5
cmp.z value lda.z value
beq __b5 cmp.z digit_value
bcs __b5
!: !:
bcc __b5
// [109] phi from utoa::@7 to utoa::@4 [phi:utoa::@7->utoa::@4] // [109] phi from utoa::@7 to utoa::@4 [phi:utoa::@7->utoa::@4]
__b4_from___b7: __b4_from___b7:
// [109] phi utoa::buffer#14 = utoa::buffer#11 [phi:utoa::@7->utoa::@4#0] -- register_copy // [109] phi utoa::buffer#14 = utoa::buffer#11 [phi:utoa::@7->utoa::@4#0] -- register_copy
@@ -4995,14 +4995,14 @@ utoa_append: {
// utoa_append::@1 // utoa_append::@1
__b1: __b1:
// [146] if(utoa_append::value#2>=utoa_append::sub#0) goto utoa_append::@2 -- vwuz1_ge_vwuz2_then_la1 // [146] if(utoa_append::value#2>=utoa_append::sub#0) goto utoa_append::@2 -- vwuz1_ge_vwuz2_then_la1
lda.z sub+1 lda.z value+1
cmp.z value+1 cmp.z sub+1
bne !+ bcc !+
lda.z sub bne __b2
cmp.z value lda.z value
beq __b2 cmp.z sub
bcs __b2
!: !:
bcc __b2
jmp __b3 jmp __b3
// utoa_append::@3 // utoa_append::@3
__b3: __b3:
@@ -5310,8 +5310,6 @@ Succesful ASM optimization Pass5DoubleJumpElimination
Removing instruction jmp __b1 Removing instruction jmp __b1
Removing instruction jmp __b2 Removing instruction jmp __b2
Succesful ASM optimization Pass5NextJumpElimination Succesful ASM optimization Pass5NextJumpElimination
Removing instruction lda.z digit_value+1
Succesful ASM optimization Pass5UnnecesaryLoadElimination
FINAL SYMBOL TABLE FINAL SYMBOL TABLE
__constant char * const COLORRAM = (char *) 55296 __constant char * const COLORRAM = (char *) 55296
@@ -5567,7 +5565,7 @@ mem[12] [ printf_buffer ]
FINAL ASSEMBLER FINAL ASSEMBLER
Score: 71978 Score: 72278
// File Comments // File Comments
// Test initialization of array of struct with char* elements // Test initialization of array of struct with char* elements
@@ -6244,13 +6242,14 @@ utoa: {
bne __b5 bne __b5
// utoa::@7 // utoa::@7
// [108] if(utoa::value#2>=utoa::digit_value#0) goto utoa::@5 -- vwuz1_ge_vwuz2_then_la1 // [108] if(utoa::value#2>=utoa::digit_value#0) goto utoa::@5 -- vwuz1_ge_vwuz2_then_la1
cmp.z value+1 lda.z value+1
bne !+ cmp.z digit_value+1
lda.z digit_value bcc !+
cmp.z value bne __b5
beq __b5 lda.z value
cmp.z digit_value
bcs __b5
!: !:
bcc __b5
// [109] phi from utoa::@7 to utoa::@4 [phi:utoa::@7->utoa::@4] // [109] phi from utoa::@7 to utoa::@4 [phi:utoa::@7->utoa::@4]
// [109] phi utoa::buffer#14 = utoa::buffer#11 [phi:utoa::@7->utoa::@4#0] -- register_copy // [109] phi utoa::buffer#14 = utoa::buffer#11 [phi:utoa::@7->utoa::@4#0] -- register_copy
// [109] phi utoa::started#4 = utoa::started#2 [phi:utoa::@7->utoa::@4#1] -- register_copy // [109] phi utoa::started#4 = utoa::started#2 [phi:utoa::@7->utoa::@4#1] -- register_copy
@@ -6464,14 +6463,14 @@ utoa_append: {
__b1: __b1:
// while (value >= sub) // while (value >= sub)
// [146] if(utoa_append::value#2>=utoa_append::sub#0) goto utoa_append::@2 -- vwuz1_ge_vwuz2_then_la1 // [146] if(utoa_append::value#2>=utoa_append::sub#0) goto utoa_append::@2 -- vwuz1_ge_vwuz2_then_la1
lda.z sub+1 lda.z value+1
cmp.z value+1 cmp.z sub+1
bne !+ bcc !+
lda.z sub bne __b2
cmp.z value lda.z value
beq __b2 cmp.z sub
bcs __b2
!: !:
bcc __b2
// utoa_append::@3 // utoa_append::@3
// *buffer = DIGITS[digit] // *buffer = DIGITS[digit]
// [147] *utoa_append::buffer#0 = DIGITS[utoa_append::digit#2] -- _deref_pbuz1=pbuc1_derefidx_vbuxx // [147] *utoa_append::buffer#0 = DIGITS[utoa_append::digit#2] -- _deref_pbuz1=pbuc1_derefidx_vbuxx