mirror of
https://gitlab.com/camelot/kickc.git
synced 2025-01-11 04:29:53 +00:00
Restructured Variable creation to make it more explicit what type is being created.
This commit is contained in:
parent
2bad8c915f
commit
cff815f5d7
@ -79,12 +79,13 @@ public class AsmFragmentTemplate {
|
||||
ProgramScope scope = new ProgramScope();
|
||||
LinkedHashMap<String, Value> bindings = new LinkedHashMap<>();
|
||||
{
|
||||
Variable v1 = new Variable( "z1", Variable.Kind.PHI_VERSION, SymbolType.BYTE, scope, Variable.MemoryArea.ZEROPAGE_MEMORY, null);
|
||||
Variable v2 = new Variable( "z2", Variable.Kind.PHI_VERSION, SymbolType.BYTE, scope, Variable.MemoryArea.ZEROPAGE_MEMORY, null);
|
||||
Variable v3 = new Variable( "z3", Variable.Kind.PHI_VERSION, SymbolType.BYTE, scope, Variable.MemoryArea.ZEROPAGE_MEMORY, null);
|
||||
Variable v4 = new Variable( "z4", Variable.Kind.PHI_VERSION, SymbolType.BYTE, scope, Variable.MemoryArea.ZEROPAGE_MEMORY, null);
|
||||
Variable v5 = new Variable( "z5", Variable.Kind.PHI_VERSION, SymbolType.BYTE, scope, Variable.MemoryArea.ZEROPAGE_MEMORY, null);
|
||||
Variable v6 = new Variable( "z6", Variable.Kind.PHI_VERSION, SymbolType.BYTE, scope, Variable.MemoryArea.ZEROPAGE_MEMORY, null);
|
||||
Variable master = Variable.createPhiMaster("z", SymbolType.BYTE, scope, Variable.MemoryArea.ZEROPAGE_MEMORY, null);
|
||||
Variable v1 = Variable.createPhiVersion(master, 1); v1.setName("z1");
|
||||
Variable v2 = Variable.createPhiVersion(master, 2); v2.setName("z2");
|
||||
Variable v3 = Variable.createPhiVersion(master, 3); v3.setName("z3");
|
||||
Variable v4 = Variable.createPhiVersion(master, 4); v4.setName("z4");
|
||||
Variable v5 = Variable.createPhiVersion(master, 5); v5.setName("z5");
|
||||
Variable v6 = Variable.createPhiVersion(master, 6); v6.setName("z6");
|
||||
v1.setAllocation(new Registers.RegisterZpMem(2, 1));
|
||||
v2.setAllocation(new Registers.RegisterZpMem(4, 1));
|
||||
v3.setAllocation(new Registers.RegisterZpMem(6, 1));
|
||||
@ -99,12 +100,12 @@ public class AsmFragmentTemplate {
|
||||
if(signature.contains("z6")) bindings.put("z6", v6);
|
||||
}
|
||||
{
|
||||
Variable v1 = new Variable( "m1", Variable.Kind.LOAD_STORE, SymbolType.BYTE, scope, Variable.MemoryArea.MAIN_MEMORY, null);
|
||||
Variable v2 = new Variable( "m2", Variable.Kind.LOAD_STORE, SymbolType.BYTE, scope, Variable.MemoryArea.MAIN_MEMORY, null);
|
||||
Variable v3 = new Variable( "m3", Variable.Kind.LOAD_STORE, SymbolType.BYTE, scope, Variable.MemoryArea.MAIN_MEMORY, null);
|
||||
Variable v4 = new Variable( "m4", Variable.Kind.LOAD_STORE, SymbolType.BYTE, scope, Variable.MemoryArea.MAIN_MEMORY, null);
|
||||
Variable v5 = new Variable( "m5", Variable.Kind.LOAD_STORE, SymbolType.BYTE, scope, Variable.MemoryArea.MAIN_MEMORY, null);
|
||||
Variable v6 = new Variable( "m6", Variable.Kind.LOAD_STORE, SymbolType.BYTE, scope, Variable.MemoryArea.MAIN_MEMORY, null);
|
||||
Variable v1 = Variable.createLoadStore("m1", SymbolType.BYTE, scope, Variable.MemoryArea.MAIN_MEMORY, null);
|
||||
Variable v2 = Variable.createLoadStore("m2", SymbolType.BYTE, scope, Variable.MemoryArea.MAIN_MEMORY, null);
|
||||
Variable v3 = Variable.createLoadStore("m3", SymbolType.BYTE, scope, Variable.MemoryArea.MAIN_MEMORY, null);
|
||||
Variable v4 = Variable.createLoadStore("m4", SymbolType.BYTE, scope, Variable.MemoryArea.MAIN_MEMORY, null);
|
||||
Variable v5 = Variable.createLoadStore("m5", SymbolType.BYTE, scope, Variable.MemoryArea.MAIN_MEMORY, null);
|
||||
Variable v6 = Variable.createLoadStore("m6", SymbolType.BYTE, scope, Variable.MemoryArea.MAIN_MEMORY, null);
|
||||
v1.setAllocation(new Registers.RegisterMainMem(v1.getVariableRef(), 1, null));
|
||||
v2.setAllocation(new Registers.RegisterMainMem(v2.getVariableRef(), 1, null));
|
||||
v3.setAllocation(new Registers.RegisterMainMem(v3.getVariableRef(), 1, null));
|
||||
|
@ -23,7 +23,7 @@ public class CallingConventionStack {
|
||||
if(returnOffsetConstant == null) {
|
||||
// Constant not found - create it
|
||||
long returnByteOffset = getReturnByteOffset(procedure);
|
||||
returnOffsetConstant = new Variable(returnOffsetConstantName, SymbolType.BYTE, null, procedure, Scope.SEGMENT_DATA_DEFAULT, new ConstantInteger(returnByteOffset & 0xff, SymbolType.BYTE));
|
||||
returnOffsetConstant = Variable.createConstant(returnOffsetConstantName, SymbolType.BYTE, procedure, null, new ConstantInteger(returnByteOffset & 0xff, SymbolType.BYTE), Scope.SEGMENT_DATA_DEFAULT);
|
||||
procedure.add(returnOffsetConstant);
|
||||
}
|
||||
return returnOffsetConstant.getConstantRef();
|
||||
@ -42,7 +42,7 @@ public class CallingConventionStack {
|
||||
if(paramOffsetConstant == null) {
|
||||
// Constant not found - create it
|
||||
long paramByteOffset = getParameterByteOffset(procedure, parameter);
|
||||
paramOffsetConstant = new Variable(paramOffsetConstantName, SymbolType.BYTE, null, procedure, Scope.SEGMENT_DATA_DEFAULT, new ConstantInteger(paramByteOffset & 0xff, SymbolType.BYTE));
|
||||
paramOffsetConstant = Variable.createConstant(paramOffsetConstantName, SymbolType.BYTE, procedure, null, new ConstantInteger(paramByteOffset & 0xff, SymbolType.BYTE), Scope.SEGMENT_DATA_DEFAULT);
|
||||
procedure.add(paramOffsetConstant);
|
||||
}
|
||||
return paramOffsetConstant.getConstantRef();
|
||||
@ -123,7 +123,7 @@ public class CallingConventionStack {
|
||||
*/
|
||||
public static ConstantRef getStackBaseConstant(ProgramScope programScope) {
|
||||
long STACK_BASE_ADDRESS = 0x103L;
|
||||
Variable stackBase = new Variable("STACK_BASE", SymbolType.WORD, null, programScope, Scope.SEGMENT_DATA_DEFAULT, new ConstantInteger(STACK_BASE_ADDRESS, SymbolType.WORD));
|
||||
Variable stackBase = Variable.createConstant("STACK_BASE", SymbolType.WORD, programScope, null, new ConstantInteger(STACK_BASE_ADDRESS, SymbolType.WORD), Scope.SEGMENT_DATA_DEFAULT);
|
||||
programScope.add(stackBase);
|
||||
return stackBase.getConstantRef();
|
||||
}
|
||||
|
@ -42,7 +42,7 @@ public class OperatorSizeOf extends OperatorUnary {
|
||||
if(typeSizeConstant == null) {
|
||||
// Constant not found - create it
|
||||
long typeSize = type.getSizeBytes();
|
||||
typeSizeConstant = new Variable(typeConstName, SymbolType.BYTE, null, programScope, Scope.SEGMENT_DATA_DEFAULT, new ConstantInteger(typeSize&0xff, SymbolType.BYTE));
|
||||
typeSizeConstant = Variable.createConstant(typeConstName, SymbolType.BYTE, programScope, null, new ConstantInteger(typeSize&0xff, SymbolType.BYTE), Scope.SEGMENT_DATA_DEFAULT);
|
||||
programScope.add(typeSizeConstant);
|
||||
}
|
||||
return typeSizeConstant.getConstantRef();
|
||||
|
@ -47,7 +47,7 @@ public class OperatorTypeId extends OperatorUnary {
|
||||
if(typeIdConstant == null) {
|
||||
// Constant not found - create it
|
||||
long typeSize = getTypeId(type);
|
||||
typeIdConstant = new Variable(typeConstName, SymbolType.BYTE, null, programScope, Scope.SEGMENT_DATA_DEFAULT, new ConstantInteger(typeSize));
|
||||
typeIdConstant = Variable.createConstant(typeConstName, SymbolType.BYTE, programScope, null, new ConstantInteger(typeSize), Scope.SEGMENT_DATA_DEFAULT);
|
||||
programScope.add(typeIdConstant);
|
||||
}
|
||||
return typeIdConstant.getConstantRef();
|
||||
|
@ -100,17 +100,9 @@ public abstract class Scope implements Symbol, Serializable {
|
||||
symbols.remove(symbol.getLocalName());
|
||||
}
|
||||
|
||||
public Variable addVariable(Variable.Kind kind, String name, SymbolType type, Variable.MemoryArea memoryArea, String dataSegment) {
|
||||
return add(new Variable( name, kind, type, this, memoryArea, dataSegment));
|
||||
}
|
||||
|
||||
public Variable addVariablePhiMaster(String name, SymbolType type, Variable.MemoryArea memoryArea, String dataSegment) {
|
||||
return add(new Variable( name, Variable.Kind.PHI_MASTER, type, this, memoryArea, dataSegment));
|
||||
}
|
||||
|
||||
public Variable addVariableIntermediate() {
|
||||
String name = allocateIntermediateVariableName();
|
||||
return add(new Variable( name, Variable.Kind.INTERMEDIATE, SymbolType.VAR, this, Variable.MemoryArea.ZEROPAGE_MEMORY, getSegmentData()));
|
||||
return add(Variable.createIntermediate( name, this, getSegmentData()));
|
||||
}
|
||||
|
||||
/**
|
||||
|
@ -5,6 +5,7 @@ import dk.camelot64.kickc.model.InternalError;
|
||||
import dk.camelot64.kickc.model.Program;
|
||||
import dk.camelot64.kickc.model.Registers;
|
||||
import dk.camelot64.kickc.model.types.SymbolType;
|
||||
import dk.camelot64.kickc.model.types.SymbolTypePointer;
|
||||
import dk.camelot64.kickc.model.values.ConstantRef;
|
||||
import dk.camelot64.kickc.model.values.ConstantValue;
|
||||
import dk.camelot64.kickc.model.values.SymbolVariableRef;
|
||||
@ -19,7 +20,7 @@ public class Variable implements Symbol {
|
||||
|
||||
/**
|
||||
* The kind of the variable. The kind is the most significant property of the variable since it drives most of the behavior.
|
||||
*
|
||||
* <p>
|
||||
* The value depends on the directives memory/register/volatile/const - and on the compilers optimization decisions.
|
||||
* <ul>
|
||||
* <li>PHI_MASTER variables are turned into PHI-versions and PHI-nodes are used for them throughout the entire program. The PHI-master itself is only an information container and does not live in memory at runtime.</li>
|
||||
@ -99,21 +100,26 @@ public class Variable implements Symbol {
|
||||
}
|
||||
|
||||
/**
|
||||
* Create a runtime variable
|
||||
* Create a variable (or constant)
|
||||
*
|
||||
* @param name The name
|
||||
* @param kind The storage strategy (PHI-master/PHI-version/Intermediate/load store/constant)
|
||||
* @param type The type
|
||||
* @param scope The scope
|
||||
* @param memoryArea The memory area (zeropage/main memory)
|
||||
* @param dataSegment The data segment (in main memory)
|
||||
* @param arraySpec The array specification of the variable (if it is an array)
|
||||
* @param constantValue The constant value of the variable (if it is constant)
|
||||
*/
|
||||
public Variable(String name, Kind kind, SymbolType type, Scope scope, MemoryArea memoryArea, String dataSegment) {
|
||||
private Variable(String name, Kind kind, SymbolType type, Scope scope, MemoryArea memoryArea, String dataSegment, ArraySpec arraySpec, ConstantValue constantValue) {
|
||||
this.name = name;
|
||||
this.kind = kind;
|
||||
if(Kind.PHI_MASTER.equals(kind))
|
||||
this.nextPhiVersionNumber = 0;
|
||||
this.type = type;
|
||||
this.scope = scope;
|
||||
this.arraySpec = arraySpec;
|
||||
this.constantValue = constantValue;
|
||||
this.dataSegment = dataSegment;
|
||||
this.memoryArea = memoryArea;
|
||||
this.comments = new ArrayList<>();
|
||||
@ -121,74 +127,132 @@ public class Variable implements Symbol {
|
||||
}
|
||||
|
||||
/**
|
||||
* Create a compile-time constant variable
|
||||
* Create an intermediate variable. The type will initially be set to {@link SymbolType#VAR}.
|
||||
*
|
||||
* @param name The name
|
||||
* @param type The type
|
||||
* @param scope The scope
|
||||
* @param dataSegment The data segment (in main memory)
|
||||
* @param value The constant value
|
||||
* @return The new intermediate variable
|
||||
*/
|
||||
public Variable(String name, SymbolType type, ArraySpec arraySpec, Scope scope, String dataSegment, ConstantValue value) {
|
||||
this(name, Kind.CONSTANT, type, scope, MemoryArea.MAIN_MEMORY, dataSegment);
|
||||
this.arraySpec = arraySpec;
|
||||
this.constantValue = value;
|
||||
public static Variable createIntermediate(String name, Scope scope, String dataSegment) {
|
||||
return new Variable(name, Kind.INTERMEDIATE, SymbolType.VAR, scope, MemoryArea.ZEROPAGE_MEMORY, dataSegment, null, null);
|
||||
}
|
||||
|
||||
/**
|
||||
* Create a constant version of a variable
|
||||
* @param variable The variable to create a constant version of
|
||||
* @param constVal The constant value
|
||||
* Create a load/store variable
|
||||
*
|
||||
* @param name The name
|
||||
* @param type The type
|
||||
* @param scope The scope
|
||||
* @param memoryArea The memory area (zeropage/main memory)
|
||||
* @param dataSegment The data segment (in main memory)
|
||||
* @return The new PHI-master variable
|
||||
*/
|
||||
public Variable(Variable variable, ConstantValue constVal) {
|
||||
this(variable.getName(),variable.getType(), variable.getArraySpec(), variable.getScope(), variable.getDataSegment(), constVal);
|
||||
this.setDeclaredAlignment(variable.getDeclaredAlignment());
|
||||
this.setDeclaredAsRegister(variable.isDeclaredAsRegister());
|
||||
this.setDeclaredConst(variable.isDeclaredConst());
|
||||
this.setDeclaredRegister(variable.getDeclaredRegister());
|
||||
this.setDeclaredVolatile(variable.isDeclaredVolatile());
|
||||
this.setDeclaredExport(variable.isDeclaredExport());
|
||||
this.setInferredVolatile(variable.isInferredVolatile());
|
||||
this.setComments(variable.getComments());
|
||||
public static Variable createLoadStore(String name, SymbolType type, Scope scope, Variable.MemoryArea memoryArea, String dataSegment) {
|
||||
return new Variable(name, Kind.LOAD_STORE, type, scope, memoryArea, dataSegment, null, null);
|
||||
}
|
||||
|
||||
/**
|
||||
* Create a PHI master variable
|
||||
*
|
||||
* @param name The name
|
||||
* @param type The type
|
||||
* @param scope The scope
|
||||
* @param memoryArea The memory area (zeropage/main memory)
|
||||
* @param dataSegment The data segment (in main memory)
|
||||
* @return The new PHI-master variable
|
||||
*/
|
||||
public static Variable createPhiMaster(String name, SymbolType type, Scope scope, Variable.MemoryArea memoryArea, String dataSegment) {
|
||||
return new Variable(name, Kind.PHI_MASTER, type, scope, memoryArea, dataSegment, null, null);
|
||||
}
|
||||
|
||||
/**
|
||||
* Create a version of a PHI master variable
|
||||
*
|
||||
* @param phiMaster The PHI master variable.
|
||||
* @param version The version number
|
||||
* @param versionNum The version number
|
||||
*/
|
||||
private Variable(Variable phiMaster, int version) {
|
||||
this(phiMaster.getName() + "#" + version, Kind.PHI_VERSION, phiMaster.getType(), phiMaster.getScope(), phiMaster.getMemoryArea(), phiMaster.getDataSegment());
|
||||
this.setArraySpec(phiMaster.getArraySpec());
|
||||
this.setDeclaredAlignment(phiMaster.getDeclaredAlignment());
|
||||
this.setDeclaredAsRegister(phiMaster.isDeclaredAsRegister());
|
||||
this.setDeclaredConst(phiMaster.isDeclaredConst());
|
||||
this.setDeclaredRegister(phiMaster.getDeclaredRegister());
|
||||
this.setDeclaredVolatile(phiMaster.isDeclaredVolatile());
|
||||
this.setDeclaredExport(phiMaster.isDeclaredExport());
|
||||
this.setInferredVolatile(phiMaster.isInferredVolatile());
|
||||
this.setComments(phiMaster.getComments());
|
||||
public static Variable createPhiVersion(Variable phiMaster, int versionNum) {
|
||||
Variable version = new Variable(phiMaster.getName() + "#" + versionNum, Kind.PHI_VERSION, phiMaster.getType(), phiMaster.getScope(), phiMaster.getMemoryArea(), phiMaster.getDataSegment(), phiMaster.getArraySpec(), null);
|
||||
version.setDeclaredAlignment(phiMaster.getDeclaredAlignment());
|
||||
version.setDeclaredAsRegister(phiMaster.isDeclaredAsRegister());
|
||||
version.setDeclaredConst(phiMaster.isDeclaredConst());
|
||||
version.setDeclaredRegister(phiMaster.getDeclaredRegister());
|
||||
version.setDeclaredVolatile(phiMaster.isDeclaredVolatile());
|
||||
version.setDeclaredExport(phiMaster.isDeclaredExport());
|
||||
version.setInferredVolatile(phiMaster.isInferredVolatile());
|
||||
version.setComments(phiMaster.getComments());
|
||||
return version;
|
||||
}
|
||||
|
||||
/**
|
||||
* Create a compile-time constant variable
|
||||
*
|
||||
* @param name The name
|
||||
* @param type The type
|
||||
* @param scope The scope
|
||||
* @param value The constant value
|
||||
* @param dataSegment The data segment (in main memory)
|
||||
*/
|
||||
public static Variable createConstant(String name, SymbolType type, Scope scope, ArraySpec arraySpec, ConstantValue value, String dataSegment) {
|
||||
return new Variable(name, Kind.CONSTANT, type, scope, MemoryArea.MAIN_MEMORY, dataSegment, arraySpec, value);
|
||||
}
|
||||
|
||||
/**
|
||||
* Create a constant version of a variable. Used when a variable is determined to be constant during the compile.
|
||||
*
|
||||
* @param variable The variable to create a constant version of
|
||||
* @param constVal The constant value
|
||||
*/
|
||||
public static Variable createConstant(Variable variable, ConstantValue constVal) {
|
||||
Variable constVar = createConstant(variable.getName(), variable.getType(), variable.getScope(), variable.getArraySpec(), constVal, variable.getDataSegment());
|
||||
constVar.setDeclaredAlignment(variable.getDeclaredAlignment());
|
||||
constVar.setDeclaredAsRegister(variable.isDeclaredAsRegister());
|
||||
constVar.setDeclaredConst(variable.isDeclaredConst());
|
||||
constVar.setDeclaredRegister(variable.getDeclaredRegister());
|
||||
constVar.setDeclaredVolatile(variable.isDeclaredVolatile());
|
||||
constVar.setDeclaredExport(variable.isDeclaredExport());
|
||||
constVar.setInferredVolatile(variable.isInferredVolatile());
|
||||
constVar.setComments(variable.getComments());
|
||||
return constVar;
|
||||
}
|
||||
|
||||
/**
|
||||
* Create a copy of a variable with a different name in a different scope
|
||||
*
|
||||
* @param name The name
|
||||
* @param scope The scope
|
||||
* @param name The name for the new variable
|
||||
* @param scope The scope for the new variable
|
||||
* @param original The original variable
|
||||
*/
|
||||
public Variable(String name, Scope scope, Variable original) {
|
||||
this(name, original.getKind(), original.getType(), scope, original.getMemoryArea(), original.getDataSegment());
|
||||
this.setArraySpec(original.getArraySpec());
|
||||
this.setDeclaredAlignment(original.getDeclaredAlignment());
|
||||
this.setDeclaredAsRegister(original.isDeclaredAsRegister());
|
||||
this.setDeclaredConst(original.isDeclaredConst());
|
||||
this.setDeclaredVolatile(original.isDeclaredVolatile());
|
||||
this.setDeclaredExport(original.isDeclaredExport());
|
||||
this.setDeclaredRegister(original.getDeclaredRegister());
|
||||
this.setInferredVolatile(original.isInferredVolatile());
|
||||
this.setComments(original.getComments());
|
||||
this.setConstantValue(original.getConstantValue());
|
||||
public static Variable createCopy(String name, Scope scope, Variable original) {
|
||||
Variable copy = new Variable(name, original.getKind(), original.getType(), scope, original.getMemoryArea(), original.getDataSegment(), original.getArraySpec(), original.getConstantValue());
|
||||
copy.setDeclaredAlignment(original.getDeclaredAlignment());
|
||||
copy.setDeclaredAsRegister(original.isDeclaredAsRegister());
|
||||
copy.setDeclaredConst(original.isDeclaredConst());
|
||||
copy.setDeclaredVolatile(original.isDeclaredVolatile());
|
||||
copy.setDeclaredExport(original.isDeclaredExport());
|
||||
copy.setDeclaredRegister(original.getDeclaredRegister());
|
||||
copy.setInferredVolatile(original.isInferredVolatile());
|
||||
copy.setComments(original.getComments());
|
||||
return copy;
|
||||
}
|
||||
|
||||
/**
|
||||
* Create a variable representing a single member of a struct variable.
|
||||
* @param structVar The variable that holds a struct value.
|
||||
* @param memberDefinition The definition of the struct member
|
||||
* @return The new unwound variable representing the member of the struct
|
||||
*/
|
||||
public static Variable createStructMemberUnwound(Variable structVar, Variable memberDefinition) {
|
||||
String name = structVar.getLocalName() + "_" + memberDefinition.getLocalName();
|
||||
Variable.MemoryArea memoryArea = (memberDefinition.getType() instanceof SymbolTypePointer) ? Variable.MemoryArea.ZEROPAGE_MEMORY : structVar.getMemoryArea();
|
||||
Variable memberVariable = new Variable(name, structVar.getKind(), memberDefinition.getType(), structVar.getScope(), memoryArea, structVar.getDataSegment(), null, null);
|
||||
memberVariable.setArraySpec(memberDefinition.getArraySpec());
|
||||
memberVariable.setDeclaredVolatile(structVar.isDeclaredVolatile());
|
||||
memberVariable.setInferredVolatile(structVar.isInferredVolatile());
|
||||
memberVariable.setDeclaredConst(structVar.isDeclaredConst());
|
||||
memberVariable.setDeclaredExport(structVar.isDeclaredExport());
|
||||
return memberVariable;
|
||||
}
|
||||
|
||||
public Kind getKind() {
|
||||
@ -252,7 +316,7 @@ public class Variable implements Symbol {
|
||||
public Variable createVersion() {
|
||||
if(!isKindPhiMaster())
|
||||
throw new InternalError("Cannot version non-PHI variable " + this.toString());
|
||||
Variable version = new Variable(this, nextPhiVersionNumber++);
|
||||
Variable version = Variable.createPhiVersion(this, nextPhiVersionNumber++);
|
||||
getScope().add(version);
|
||||
return version;
|
||||
}
|
||||
|
@ -4,6 +4,7 @@ import dk.camelot64.kickc.NumberParser;
|
||||
import dk.camelot64.kickc.SourceLoader;
|
||||
import dk.camelot64.kickc.asm.AsmClobber;
|
||||
import dk.camelot64.kickc.model.*;
|
||||
import dk.camelot64.kickc.model.InternalError;
|
||||
import dk.camelot64.kickc.model.iterator.ProgramValue;
|
||||
import dk.camelot64.kickc.model.operators.*;
|
||||
import dk.camelot64.kickc.model.statements.*;
|
||||
@ -208,7 +209,7 @@ public class Pass0GenerateStatementSequence extends KickCParserBaseVisitor<Objec
|
||||
Label procExit = procedure.addLabel(SymbolRef.PROCEXIT_BLOCK_NAME);
|
||||
Variable returnVar = null;
|
||||
if(!SymbolType.VOID.equals(type)) {
|
||||
returnVar = procedure.addVariablePhiMaster("return", type, defaultMemoryArea, procedure.getSegmentData());
|
||||
returnVar = procedure.add(Variable.createPhiMaster("return", type, procedure, defaultMemoryArea, procedure.getSegmentData()));
|
||||
}
|
||||
List<Variable> parameterList = new ArrayList<>();
|
||||
if(ctx.parameterListDecl() != null) {
|
||||
@ -267,7 +268,7 @@ public class Pass0GenerateStatementSequence extends KickCParserBaseVisitor<Objec
|
||||
this.visitDeclTypes(ctx.declTypes());
|
||||
SymbolType type = declVarType;
|
||||
List<Directive> directives = declVarDirectives;
|
||||
Variable param = new Variable( ctx.NAME().getText(), Variable.Kind.PHI_MASTER, type, getCurrentScope(), defaultMemoryArea, currentDataSegment);
|
||||
Variable param = Variable.createPhiMaster( ctx.NAME().getText(), type, getCurrentScope(), defaultMemoryArea, currentDataSegment);
|
||||
// Add directives
|
||||
directiveContext.applyDirectives(param, true, false, directives, new StatementSource(ctx));
|
||||
exitDeclTypes();
|
||||
@ -577,14 +578,22 @@ public class Pass0GenerateStatementSequence extends KickCParserBaseVisitor<Objec
|
||||
arraySpec = new ArraySpec(declArraySize);
|
||||
}
|
||||
Scope scope = getCurrentScope();
|
||||
Variable constVar = new Variable(varName, declVarType, arraySpec, scope, currentDataSegment, initConstantValue);
|
||||
Variable constVar = Variable.createConstant(varName, declVarType, scope, arraySpec, initConstantValue, currentDataSegment);
|
||||
scope.add(constVar);
|
||||
// Add comments to constant
|
||||
constVar.setComments(ensureUnusedComments(declVarComments));
|
||||
directiveContext.applyDirectives(constVar, false, declIsArray, declVarDirectives, statementSource);
|
||||
} else {
|
||||
// Create variable
|
||||
Variable lValue = getCurrentScope().addVariable(kind, varName, declVarType, defaultMemoryArea, currentDataSegment);
|
||||
Variable lValue;
|
||||
if(kind.equals(Variable.Kind.PHI_MASTER)) {
|
||||
lValue = Variable.createPhiMaster(varName, declVarType, getCurrentScope(), defaultMemoryArea, currentDataSegment);
|
||||
} else if (kind.equals(Variable.Kind.LOAD_STORE)) {
|
||||
lValue = Variable.createLoadStore(varName, declVarType, getCurrentScope(), defaultMemoryArea, currentDataSegment);
|
||||
} else {
|
||||
throw new InternalError("Unexpected variable kind! "+kind.name(), statementSource);
|
||||
}
|
||||
getCurrentScope().add(lValue);
|
||||
// Add directives
|
||||
directiveContext.applyDirectives(lValue, false, declIsArray, declVarDirectives, statementSource);
|
||||
if(declVarStructMember) {
|
||||
@ -715,7 +724,7 @@ public class Pass0GenerateStatementSequence extends KickCParserBaseVisitor<Objec
|
||||
}
|
||||
// Add a constant variable
|
||||
Scope scope = getCurrentScope();
|
||||
Variable constVar = new Variable(varName, declVarType, arraySpec, scope, currentDataSegment, constantArrayKickAsm);
|
||||
Variable constVar = Variable.createConstant(varName, declVarType, scope, arraySpec, constantArrayKickAsm, currentDataSegment);
|
||||
scope.add(constVar);
|
||||
// Add comments to constant
|
||||
constVar.setComments(ensureUnusedComments(declVarComments));
|
||||
@ -1236,7 +1245,7 @@ public class Pass0GenerateStatementSequence extends KickCParserBaseVisitor<Objec
|
||||
Variable lValue;
|
||||
if(varType != null) {
|
||||
try {
|
||||
lValue = getCurrentScope().addVariablePhiMaster(varName, varType, defaultMemoryArea, currentDataSegment);
|
||||
lValue = getCurrentScope().add(Variable.createPhiMaster(varName, varType, getCurrentScope(), defaultMemoryArea, currentDataSegment));
|
||||
} catch(CompileError e) {
|
||||
throw new CompileError(e.getMessage(), statementSource);
|
||||
}
|
||||
@ -1542,7 +1551,7 @@ public class Pass0GenerateStatementSequence extends KickCParserBaseVisitor<Objec
|
||||
Scope parentScope = getCurrentScope();
|
||||
while(parentScope instanceof StructDefinition) parentScope = parentScope.getScope();
|
||||
for(Variable member : enumDefinition.getAllConstants(false)) {
|
||||
parentScope.add(new Variable(member.getLocalName(), SymbolType.BYTE, null, parentScope, currentDataSegment, member.getConstantValue()));
|
||||
parentScope.add(Variable.createConstant(member.getLocalName(), SymbolType.BYTE, parentScope, null, member.getConstantValue(), currentDataSegment));
|
||||
}
|
||||
return SymbolType.BYTE;
|
||||
} catch(CompileError e) {
|
||||
@ -1576,7 +1585,7 @@ public class Pass0GenerateStatementSequence extends KickCParserBaseVisitor<Objec
|
||||
}
|
||||
}
|
||||
}
|
||||
currentEnum.add(new Variable(memberName, SymbolType.BYTE, null, getCurrentScope(), currentDataSegment, enumValue));
|
||||
currentEnum.add(Variable.createConstant(memberName, SymbolType.BYTE, getCurrentScope(), null, enumValue, currentDataSegment));
|
||||
return null;
|
||||
}
|
||||
|
||||
@ -1661,7 +1670,7 @@ public class Pass0GenerateStatementSequence extends KickCParserBaseVisitor<Objec
|
||||
scopeStack.push(typedefScope);
|
||||
SymbolType type = (SymbolType) this.visit(ctx.typeDecl());
|
||||
String typedefName = ctx.NAME().getText();
|
||||
typedefScope.addVariablePhiMaster(typedefName, type, defaultMemoryArea, currentDataSegment);
|
||||
typedefScope.add(Variable.createPhiMaster(typedefName, type, typedefScope, defaultMemoryArea, currentDataSegment));
|
||||
scopeStack.pop();
|
||||
return null;
|
||||
}
|
||||
|
@ -120,7 +120,7 @@ public class Pass1EarlyConstantIdentification extends Pass1Base {
|
||||
SymbolVariableRef variableRef = variable.getRef();
|
||||
Scope scope = variable.getScope();
|
||||
scope.remove(variable);
|
||||
Variable constVar = new Variable(variable, constantValue);
|
||||
Variable constVar = Variable.createConstant(variable, constantValue);
|
||||
constVar.getComments().addAll(assignment.getComments());
|
||||
SymbolVariableRef constRef = constVar.getRef();
|
||||
aliases.put(variableRef, constRef);
|
||||
|
@ -74,7 +74,7 @@ public class Pass1ExtractInlineStrings extends Pass1Base {
|
||||
name = nameHint + nameHintIdx++;
|
||||
}
|
||||
}
|
||||
Variable strConst = new Variable(name, SymbolType.STRING, new ArraySpec(), blockScope, blockScope.getSegmentData(), constantString);
|
||||
Variable strConst = Variable.createConstant(name, SymbolType.STRING, blockScope, new ArraySpec(), constantString, blockScope.getSegmentData());
|
||||
blockScope.add(strConst);
|
||||
if(getLog().isVerbosePass1CreateSsa()) {
|
||||
getLog().append("Creating constant string variable for inline " + strConst.toString(getProgram()) + " \"" + constantString.getValue() + "\"");
|
||||
|
@ -300,7 +300,7 @@ public class Pass1ProcedureInline extends Pass1Base {
|
||||
if(procSymbol instanceof Variable) {
|
||||
Variable procVar = (Variable) procSymbol;
|
||||
String inlineVarName = getInlineSymbolName(procedure, procSymbol, serial);
|
||||
Variable inlineVar = new Variable(inlineVarName, callScope, procVar);
|
||||
Variable inlineVar = Variable.createCopy(inlineVarName, callScope, procVar);
|
||||
callScope.add(inlineVar);
|
||||
} else if(procSymbol instanceof Label) {
|
||||
String inlineLabelName = getInlineSymbolName(procedure, procSymbol, serial);
|
||||
|
@ -72,17 +72,17 @@ public class Pass1UnwindBlockScopes extends Pass1Base {
|
||||
Variable variable = (Variable) symbol;
|
||||
if(variable.isKindConstant()) {
|
||||
String name = findLocalName(procedure, symbol);
|
||||
Variable unwound = new Variable(name, procedure, (Variable) symbol);
|
||||
Variable unwound = Variable.createCopy(name, procedure, (Variable) symbol);
|
||||
procedure.add(unwound);
|
||||
unwoundSymbols.put(symbol.getRef(), unwound.getRef());
|
||||
} else if(variable.isKindPhiMaster() || variable.isKindConstant()) {
|
||||
String name = findLocalName(procedure, symbol);
|
||||
Variable unwound = new Variable(name, procedure, (Variable) symbol);
|
||||
Variable unwound = Variable.createCopy(name, procedure, (Variable) symbol);
|
||||
procedure.add(unwound);
|
||||
unwoundSymbols.put(symbol.getRef(), unwound.getRef());
|
||||
} else if(variable.isKindIntermediate()) {
|
||||
String name = procedure.allocateIntermediateVariableName();
|
||||
Variable unwound = new Variable(name, procedure, (Variable) symbol);
|
||||
Variable unwound = Variable.createCopy(name, procedure, (Variable) symbol);
|
||||
procedure.add(unwound);
|
||||
unwoundSymbols.put(symbol.getRef(), unwound.getRef());
|
||||
} else {
|
||||
|
@ -207,14 +207,8 @@ public class Pass1UnwindStructValues extends Pass1Base {
|
||||
StructDefinition structDefinition = ((SymbolTypeStruct) variable.getType()).getStructDefinition(getProgram().getScope());
|
||||
StructUnwinding.VariableUnwinding variableUnwinding = structUnwinding.createVariableUnwinding(variable.getRef());
|
||||
for(Variable member : structDefinition.getAllVars(false)) {
|
||||
String name = variable.getLocalName() + "_" + member.getLocalName();
|
||||
Variable.MemoryArea memoryArea = (member.getType() instanceof SymbolTypePointer)?Variable.MemoryArea.ZEROPAGE_MEMORY:variable.getMemoryArea();
|
||||
Variable memberVariable = scope.add(new Variable( name, variable.getKind(), member.getType(), scope, memoryArea, variable.getDataSegment()));
|
||||
memberVariable.setArraySpec(member.getArraySpec());
|
||||
memberVariable.setDeclaredVolatile(variable.isDeclaredVolatile());
|
||||
memberVariable.setInferredVolatile(variable.isInferredVolatile());
|
||||
memberVariable.setDeclaredConst(variable.isDeclaredConst());
|
||||
memberVariable.setDeclaredExport(variable.isDeclaredExport());
|
||||
Variable memberVariable = Variable.createStructMemberUnwound(variable, member);
|
||||
scope.add(memberVariable);
|
||||
variableUnwinding.setMemberUnwinding(member.getLocalName(), memberVariable.getRef());
|
||||
getLog().append("Created struct value member variable " + memberVariable.toString(getProgram()));
|
||||
}
|
||||
|
@ -71,7 +71,7 @@ public class Pass2ConstantIdentification extends Pass2SsaOptimization {
|
||||
);
|
||||
}
|
||||
scope.remove(variable);
|
||||
Variable constVar = new Variable(variable, constVal);
|
||||
Variable constVar = Variable.createConstant(variable, constVal);
|
||||
constVar.getComments().addAll(constVarVal.getAssignment().getComments());
|
||||
scope.add(constVar);
|
||||
constAliases.put(constRef, constVar.getRef());
|
||||
|
@ -93,7 +93,7 @@ public class Pass2ConstantStringConsolidation extends Pass2SsaOptimization {
|
||||
// Create a new root - and roll around again
|
||||
ProgramScope rootScope = getScope();
|
||||
String localName = getRootName(constantVars);
|
||||
Variable newRootConstant = new Variable(localName, SymbolType.STRING, new ArraySpec(), rootScope, segmentData, constString);
|
||||
Variable newRootConstant = Variable.createConstant(localName, SymbolType.STRING, rootScope, new ArraySpec(), constString, segmentData);
|
||||
rootScope.add(newRootConstant);
|
||||
rootConstant = newRootConstant;
|
||||
}
|
||||
|
@ -133,7 +133,7 @@ public class PassNStructPointerRewriting extends Pass2SsaOptimization {
|
||||
// Constant not found - create it
|
||||
Variable memberDef = structDefinition.getMember(memberName);
|
||||
long memberByteOffset = structDefinition.getMemberByteOffset(memberDef, programScope);
|
||||
memberOffsetConstant = new Variable(typeConstName, SymbolType.BYTE, null, programScope, Scope.SEGMENT_DATA_DEFAULT, new ConstantInteger(memberByteOffset & 0xff, SymbolType.BYTE));
|
||||
memberOffsetConstant = Variable.createConstant(typeConstName, SymbolType.BYTE, programScope, null, new ConstantInteger(memberByteOffset & 0xff, SymbolType.BYTE), Scope.SEGMENT_DATA_DEFAULT);
|
||||
programScope.add(memberOffsetConstant);
|
||||
}
|
||||
return memberOffsetConstant.getConstantRef();
|
||||
|
@ -231,7 +231,7 @@ public class Unroller {
|
||||
if(definedVarRef.isIntermediate()) {
|
||||
Scope scope = definedVar.getScope();
|
||||
String name = scope.allocateIntermediateVariableName();
|
||||
newVar = new Variable(name, scope, definedVar);
|
||||
newVar = Variable.createCopy(name, scope, definedVar);
|
||||
scope.add(newVar);
|
||||
} else if(definedVarRef.isVersion()) {
|
||||
newVar = (definedVar).getVersionOf().createVersion();
|
||||
|
Loading…
x
Reference in New Issue
Block a user