mirror of
https://gitlab.com/camelot/kickc.git
synced 2024-10-21 02:24:34 +00:00
Added -Wfragment option that replaces error with warning when a fragment is missing.
This commit is contained in:
parent
01008ccb26
commit
f09b1616c2
@ -33,6 +33,9 @@ public class Compiler {
|
|||||||
* Currently the optimization is flaky and results in NPE's and wrong values in some programs. */
|
* Currently the optimization is flaky and results in NPE's and wrong values in some programs. */
|
||||||
private boolean enableLoopHeadConstant = false;
|
private boolean enableLoopHeadConstant = false;
|
||||||
|
|
||||||
|
/** Missing fragments produce a warning instead of an error */
|
||||||
|
private boolean warnFragmentMissing = false;
|
||||||
|
|
||||||
/** File name of link script to use (from command line parameter). */
|
/** File name of link script to use (from command line parameter). */
|
||||||
private String linkScriptFileName;
|
private String linkScriptFileName;
|
||||||
|
|
||||||
@ -40,6 +43,14 @@ public class Compiler {
|
|||||||
this.program = new Program();
|
this.program = new Program();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public boolean isWarnFragmentMissing() {
|
||||||
|
return warnFragmentMissing;
|
||||||
|
}
|
||||||
|
|
||||||
|
public void setWarnFragmentMissing(boolean warnFragmentMissing) {
|
||||||
|
this.warnFragmentMissing = warnFragmentMissing;
|
||||||
|
}
|
||||||
|
|
||||||
public void setLinkScriptFileName(String linkScript) {
|
public void setLinkScriptFileName(String linkScript) {
|
||||||
linkScriptFileName = linkScript;
|
linkScriptFileName = linkScript;
|
||||||
}
|
}
|
||||||
@ -475,7 +486,7 @@ public class Compiler {
|
|||||||
new Pass4RegistersFinalize(program).allocate(true);
|
new Pass4RegistersFinalize(program).allocate(true);
|
||||||
|
|
||||||
// Initial Code generation
|
// Initial Code generation
|
||||||
new Pass4CodeGeneration(program, false).generate();
|
new Pass4CodeGeneration(program, false, warnFragmentMissing).generate();
|
||||||
new Pass4AssertNoCpuClobber(program).check();
|
new Pass4AssertNoCpuClobber(program).check();
|
||||||
getLog().append("\nINITIAL ASM");
|
getLog().append("\nINITIAL ASM");
|
||||||
getLog().append("Target platform is " + program.getTargetPlatform().getName());
|
getLog().append("Target platform is " + program.getTargetPlatform().getName());
|
||||||
@ -521,7 +532,7 @@ public class Compiler {
|
|||||||
|
|
||||||
// Final ASM code generation before optimization
|
// Final ASM code generation before optimization
|
||||||
program.clearPhiTransitions();
|
program.clearPhiTransitions();
|
||||||
new Pass4CodeGeneration(program, false).generate();
|
new Pass4CodeGeneration(program, false, warnFragmentMissing).generate();
|
||||||
new Pass4AssertNoCpuClobber(program).check();
|
new Pass4AssertNoCpuClobber(program).check();
|
||||||
|
|
||||||
// Remove unnecessary register savings from interrupts {@link InterruptType#HARDWARE_NOCLOBBER}
|
// Remove unnecessary register savings from interrupts {@link InterruptType#HARDWARE_NOCLOBBER}
|
||||||
|
@ -111,6 +111,9 @@ public class KickC implements Callable<Void> {
|
|||||||
@CommandLine.Option(names = {"-vasmoptimize"}, description = "Verbosity Option. Assembler optimization.")
|
@CommandLine.Option(names = {"-vasmoptimize"}, description = "Verbosity Option. Assembler optimization.")
|
||||||
private boolean verboseAsmOptimize = false;
|
private boolean verboseAsmOptimize = false;
|
||||||
|
|
||||||
|
@CommandLine.Option(names = {"-Wfragment"}, description = "Warning Option. Missing fragments produces a warning instead of an error.")
|
||||||
|
private boolean warnFragmentMissing = false;
|
||||||
|
|
||||||
@CommandLine.Option(names = {"-fragment"}, description = "Print the ASM code for a named fragment. The fragment is loaded/synthesized and the ASM variations are written to the output.")
|
@CommandLine.Option(names = {"-fragment"}, description = "Print the ASM code for a named fragment. The fragment is loaded/synthesized and the ASM variations are written to the output.")
|
||||||
private String fragment = null;
|
private String fragment = null;
|
||||||
|
|
||||||
@ -227,6 +230,10 @@ public class KickC implements Callable<Void> {
|
|||||||
compiler.disableLoopHeadConstant();
|
compiler.disableLoopHeadConstant();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if(warnFragmentMissing) {
|
||||||
|
compiler.setWarnFragmentMissing(true);
|
||||||
|
}
|
||||||
|
|
||||||
if(linkScript!=null) {
|
if(linkScript!=null) {
|
||||||
compiler.setLinkScriptFileName(linkScript);
|
compiler.setLinkScriptFileName(linkScript);
|
||||||
}
|
}
|
||||||
|
@ -78,5 +78,10 @@ public class LiveRangeVariables {
|
|||||||
return liveRanges.get(variable);
|
return liveRanges.get(variable);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public int size() {
|
||||||
|
return liveRanges.size();
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
}
|
}
|
||||||
|
@ -25,6 +25,9 @@ public class Pass4CodeGeneration {
|
|||||||
/** Should the generated ASM contain verbose alive info for the statements (costs a bit more to generate). */
|
/** Should the generated ASM contain verbose alive info for the statements (costs a bit more to generate). */
|
||||||
boolean verboseAliveInfo;
|
boolean verboseAliveInfo;
|
||||||
|
|
||||||
|
/** Missing fragments produce a warning instead of an error. */
|
||||||
|
boolean warnFragmentMissing;
|
||||||
|
|
||||||
/** The program being generated. */
|
/** The program being generated. */
|
||||||
private Program program;
|
private Program program;
|
||||||
|
|
||||||
@ -57,9 +60,10 @@ public class Pass4CodeGeneration {
|
|||||||
transitionsGenerated.put(transition, Boolean.TRUE);
|
transitionsGenerated.put(transition, Boolean.TRUE);
|
||||||
}
|
}
|
||||||
|
|
||||||
public Pass4CodeGeneration(Program program, boolean verboseAliveInfo) {
|
public Pass4CodeGeneration(Program program, boolean verboseAliveInfo, boolean warnFragmentMissing) {
|
||||||
this.program = program;
|
this.program = program;
|
||||||
this.verboseAliveInfo = verboseAliveInfo;
|
this.verboseAliveInfo = verboseAliveInfo;
|
||||||
|
this.warnFragmentMissing = warnFragmentMissing;
|
||||||
}
|
}
|
||||||
|
|
||||||
ControlFlowGraph getGraph() {
|
ControlFlowGraph getGraph() {
|
||||||
@ -644,7 +648,12 @@ public class Pass4CodeGeneration {
|
|||||||
try {
|
try {
|
||||||
generateStatementAsm(asm, block, statement, aluState, true);
|
generateStatementAsm(asm, block, statement, aluState, true);
|
||||||
} catch(AsmFragmentTemplateSynthesizer.UnknownFragmentException e) {
|
} catch(AsmFragmentTemplateSynthesizer.UnknownFragmentException e) {
|
||||||
throw new CompileError("Unknown fragment for statement " + statement.toString(program, false) + "\nMissing ASM fragment " + e.getFragmentSignature(), statement.getSource());
|
if(warnFragmentMissing) {
|
||||||
|
program.getLog().append("Warning! Unknown fragment for statement " + statement.toString(program, false) + "\nMissing ASM fragment " + e.getFragmentSignature()+"\n"+statement.getSource().toString());
|
||||||
|
asm.addLine(new AsmInlineKickAsm(".assert \"Missing ASM fragment "+ e.getFragmentSignature()+"\", 0, 1", 0L, 0L));
|
||||||
|
} else {
|
||||||
|
throw new CompileError("Unknown fragment for statement " + statement.toString(program, false) + "\nMissing ASM fragment " + e.getFragmentSignature(), statement.getSource());
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -110,7 +110,7 @@ public class Pass4RegisterUpliftCombinations extends Pass2Base {
|
|||||||
// Generate ASM
|
// Generate ASM
|
||||||
try {
|
try {
|
||||||
program.clearPhiTransitions();
|
program.clearPhiTransitions();
|
||||||
new Pass4CodeGeneration(program, false).generate();
|
new Pass4CodeGeneration(program, false, false).generate();
|
||||||
} catch(AsmFragmentTemplateSynthesizer.UnknownFragmentException e) {
|
} catch(AsmFragmentTemplateSynthesizer.UnknownFragmentException e) {
|
||||||
unknownFragments.add(e.getFragmentSignature());
|
unknownFragments.add(e.getFragmentSignature());
|
||||||
if(program.getLog().isVerboseUplift()) {
|
if(program.getLog().isVerboseUplift()) {
|
||||||
|
@ -163,7 +163,7 @@ public class Pass4RegisterUpliftPotentialRegisterAnalysis extends Pass2Base {
|
|||||||
asm.startChunk(block.getScope(), statement.getIndex(), statement.toString(getProgram(), false));
|
asm.startChunk(block.getScope(), statement.getIndex(), statement.toString(getProgram(), false));
|
||||||
Pass4CodeGeneration.AsmCodegenAluState aluState = new Pass4CodeGeneration.AsmCodegenAluState();
|
Pass4CodeGeneration.AsmCodegenAluState aluState = new Pass4CodeGeneration.AsmCodegenAluState();
|
||||||
try {
|
try {
|
||||||
(new Pass4CodeGeneration(getProgram(), false)).generateStatementAsm(asm, block, statement, aluState, false);
|
(new Pass4CodeGeneration(getProgram(), false, false)).generateStatementAsm(asm, block, statement, aluState, false);
|
||||||
} catch(AsmFragmentTemplateSynthesizer.UnknownFragmentException e) {
|
} catch(AsmFragmentTemplateSynthesizer.UnknownFragmentException e) {
|
||||||
unknownFragments.add(e.getFragmentSignature());
|
unknownFragments.add(e.getFragmentSignature());
|
||||||
StringBuilder msg = new StringBuilder();
|
StringBuilder msg = new StringBuilder();
|
||||||
|
@ -40,14 +40,11 @@ public class PassNCalcLiveRangeVariables extends PassNCalcBase<LiveRangeVariable
|
|||||||
|
|
||||||
/** Variables referenced inside each procedure and all it's sub-calls. */
|
/** Variables referenced inside each procedure and all it's sub-calls. */
|
||||||
private Map<ProcedureRef, Collection<VariableRef>> procedureReferencedVars;
|
private Map<ProcedureRef, Collection<VariableRef>> procedureReferencedVars;
|
||||||
|
|
||||||
static int callCount = 0;
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Calculate the variables referenced inside each procedure and all it's sub-calls.
|
* Calculate the variables referenced inside each procedure and all it's sub-calls.
|
||||||
*/
|
*/
|
||||||
private void calculateProcedureReferencedVars() {
|
private void calculateProcedureReferencedVars() {
|
||||||
//getLog().append("calculateLiveRanges starting "+callCount);
|
|
||||||
VariableReferenceInfos referenceInfo = getProgram().getVariableReferenceInfos();
|
VariableReferenceInfos referenceInfo = getProgram().getVariableReferenceInfos();
|
||||||
Collection<Procedure> allProcedures = getScope().getAllProcedures(true);
|
Collection<Procedure> allProcedures = getScope().getAllProcedures(true);
|
||||||
Map<ProcedureRef, Collection<VariableRef>> procReferencedVars = new LinkedHashMap<>();
|
Map<ProcedureRef, Collection<VariableRef>> procReferencedVars = new LinkedHashMap<>();
|
||||||
@ -55,8 +52,6 @@ public class PassNCalcLiveRangeVariables extends PassNCalcBase<LiveRangeVariable
|
|||||||
Collection<VariableRef> referencedVars = referenceInfo.getReferencedVars(procedure.getRef().getLabelRef());
|
Collection<VariableRef> referencedVars = referenceInfo.getReferencedVars(procedure.getRef().getLabelRef());
|
||||||
procReferencedVars.put(procedure.getRef(), referencedVars);
|
procReferencedVars.put(procedure.getRef(), referencedVars);
|
||||||
}
|
}
|
||||||
//getLog().append("calculateLiveRanges done "+callCount);
|
|
||||||
callCount++;
|
|
||||||
this.procedureReferencedVars = procReferencedVars;
|
this.procedureReferencedVars = procReferencedVars;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -83,9 +78,7 @@ public class PassNCalcLiveRangeVariables extends PassNCalcBase<LiveRangeVariable
|
|||||||
* @return true if any live ranges was modified. false if no modification was performed (and the propagation is complete)
|
* @return true if any live ranges was modified. false if no modification was performed (and the propagation is complete)
|
||||||
*/
|
*/
|
||||||
private boolean calculateLiveRanges(LiveRangeVariables liveRanges) {
|
private boolean calculateLiveRanges(LiveRangeVariables liveRanges) {
|
||||||
|
|
||||||
VariableReferenceInfos referenceInfo = getProgram().getVariableReferenceInfos();
|
VariableReferenceInfos referenceInfo = getProgram().getVariableReferenceInfos();
|
||||||
|
|
||||||
boolean modified = false;
|
boolean modified = false;
|
||||||
for(ControlFlowBlock block : getProgram().getGraph().getAllBlocks()) {
|
for(ControlFlowBlock block : getProgram().getGraph().getAllBlocks()) {
|
||||||
for(Statement stmt : block.getStatements()) {
|
for(Statement stmt : block.getStatements()) {
|
||||||
|
Loading…
Reference in New Issue
Block a user