Permalink
Browse files

[IR] Some API cleanup in IRScope.java -- the original instruction list

cannot be used after CFG has been build since the CFG now has the
canonical copy of instructions.  Fixed JVM.java to use the CFG to
compile code.
  • Loading branch information...
1 parent 97db2fc commit c445895b184400dd24227f29fc2450c36c014a1f @subbuss subbuss committed Jan 27, 2012
Showing with 46 additions and 31 deletions.
  1. +34 −24 src/org/jruby/compiler/ir/IRScope.java
  2. +12 −7 src/org/jruby/compiler/ir/targets/JVM.java
@@ -95,7 +95,7 @@
private RubyModule containerModule;
/** List of IR instructions for this method */
- private List<Instr> instructions;
+ private List<Instr> instrList;
/** Control flow graph representation of this method's instructions */
private CFG cfg = null;
@@ -115,7 +115,7 @@
/** Map of name -> dataflow problem */
private Map<String, DataFlowProblem> dfProbs = new HashMap<String, DataFlowProblem>();
- private Instr[] instrs = null;
+ private Instr[] linearizedInstrArray = null;
private List<BasicBlock> linearizedBBList = null;
private int scopeExitPC = -1;
protected int temporaryVariableIndex = -1;
@@ -213,9 +213,9 @@ public IRScope(IRScope lexicalParent, String name, String fileName, int lineNumb
this.lexicalParent = lexicalParent;
this.name = name;
this.fileName = fileName;
- this.lineNumber = lineNumber;
+ this.lineNumber = lineNumber;
this.staticScope = staticScope;
- instructions = new ArrayList<Instr>();
+ instrList = new ArrayList<Instr>();
closures = new ArrayList<IRClosure>();
// All flags are true by default!
@@ -233,11 +233,11 @@ public void addClosure(IRClosure c) {
}
public Instr getLastInstr() {
- return instructions.get(instructions.size() - 1);
+ return instrList.get(instrList.size() - 1);
}
public void addInstr(Instr i) {
- instructions.add(i);
+ instrList.add(i);
}
public LocalVariable getNewFlipStateVariable() {
@@ -246,7 +246,7 @@ public LocalVariable getNewFlipStateVariable() {
public void initFlipStateVariable(Variable v, Operand initState) {
// Add it to the beginning
- instructions.add(0, new CopyInstr(v, initState));
+ instrList.add(0, new CopyInstr(v, initState));
}
public boolean isForLoopBody() {
@@ -387,7 +387,9 @@ public boolean canCaptureCallersBinding() {
public CFG buildCFG() {
cfg = new CFG(this);
- cfg.build(instructions);
+ cfg.build(instrList);
+ // Clear out instruction list after CFG has been built.
+ this.instrList = null;
return cfg;
}
@@ -410,7 +412,7 @@ public void runCompilerPass(CompilerPass p) {
}
private Instr[] prepareInstructionsForInterpretation() {
- if (instrs != null) return instrs; // Already prepared
+ if (linearizedInstrArray != null) return linearizedInstrArray; // Already prepared
try {
buildLinearization(); // FIXME: compiler passes should have done this
@@ -448,8 +450,8 @@ public void runCompilerPass(CompilerPass p) {
cfg().getExitBB().getLabel().setTargetPC(ipc + 1);
this.scopeExitPC = ipc+1;
- instrs = newInstrs.toArray(new Instr[newInstrs.size()]);
- return instrs;
+ linearizedInstrArray = newInstrs.toArray(new Instr[newInstrs.size()]);
+ return linearizedInstrArray;
}
private void printPass(String message) {
@@ -498,7 +500,7 @@ private void runCompilerPasses() {
/** Run any necessary passes to get the IR ready for interpretation */
public synchronized Instr[] prepareForInterpretation() {
// If the instruction array exists, someone has taken care of setting up the CFG and preparing the instructions
- if (instrs != null) return instrs;
+ if (linearizedInstrArray != null) return linearizedInstrArray;
// Build CFG and run compiler passes, if necessary
if (getCFG() == null) runCompilerPasses();
@@ -507,6 +509,12 @@ private void runCompilerPasses() {
return prepareInstructionsForInterpretation();
}
+ /** Run any necessary passes to get the IR ready for compilation */
+ public synchronized void prepareForCompilation() {
+ // Build CFG and run compiler passes, if necessary
+ if (getCFG() == null) runCompilerPasses();
+ }
+
// SSS FIXME: This method does nothing useful right now.
// hasEscapedBinding is the crucial flag and it continues to be unconditionally true.
public void computeScopeFlags() {
@@ -562,7 +570,7 @@ public String toStringInstrs() {
StringBuilder b = new StringBuilder();
int i = 0;
- for (Instr instr : instructions) {
+ for (Instr instr : instrList) {
if (i > 0) b.append("\n");
b.append(" ").append(i).append('\t').append(instr);
@@ -585,8 +593,8 @@ public String toStringVariables() {
Map<Variable, Integer> starts = new HashMap<Variable, Integer>();
SortedSet<Variable> variables = new TreeSet<Variable>();
- for (int i = instructions.size() - 1; i >= 0; i--) {
- Instr instr = instructions.get(i);
+ for (int i = instrList.size() - 1; i >= 0; i--) {
+ Instr instr = instrList.get(i);
if (instr instanceof ResultInstr) {
Variable var = ((ResultInstr) instr).getResult();
@@ -625,8 +633,8 @@ public String toStringVariables() {
Map<LocalVariable, Integer> starts = new HashMap<LocalVariable, Integer>();
Set<LocalVariable> variables = new TreeSet<LocalVariable>();
- for (int i = instructions.size() - 1; i >= 0; i--) {
- Instr instr = instructions.get(i);
+ for (int i = instrList.size() - 1; i >= 0; i--) {
+ Instr instr = instrList.get(i);
// TODO: Instruction encode whether arguments are optional/required/block
// TODO: PErhaps this should be part of allocate and not have a generic
@@ -694,8 +702,8 @@ public StaticScope allocateStaticScope(StaticScope parent) {
* SSS FIXME: What is this method for?
@Interp
public void calculateParameterCounts() {
- for (int i = instructions.size() - 1; i >= 0; i--) {
- Instr instr = instructions.get(i);
+ for (int i = instrList.size() - 1; i >= 0; i--) {
+ Instr instr = instrList.get(i);
}
}
------------------------------------------ **/
@@ -831,13 +839,15 @@ public DataFlowProblem getDataFlowSolution(String name) {
return dfProbs.get(name);
}
- // SSS FIXME: Deprecated! Going forward, all instructions should come from the CFG
+ // This should only be used to do pre-cfg opts and to build the CFG.
+ // Everyone else should use the CFG.
public List<Instr> getInstrs() {
- return instructions;
+ if (cfg != null) throw new RuntimeException("Please use the CFG to access this scope's instructions.");
+ return instrList;
}
public Instr[] getInstrsForInterpretation() {
- return instrs;
+ return linearizedInstrArray;
}
public int getScopeExitPC() {
@@ -945,9 +955,9 @@ public void inlineMethod(IRScope method, BasicBlock basicBlock, CallBase call) {
}
- public void buildCFG(List<Instr> instructions) {
+ public void buildCFG(List<Instr> instrList) {
CFG newBuild = new CFG(this);
- newBuild.build(instructions);
+ newBuild.build(instrList);
cfg = newBuild;
}
@@ -24,6 +24,7 @@
import org.jruby.compiler.ir.operands.Label;
import org.jruby.compiler.ir.operands.Operand;
import org.jruby.compiler.ir.operands.Variable;
+import org.jruby.compiler.ir.representations.BasicBlock;
import org.jruby.runtime.ThreadContext;
import org.jruby.runtime.builtin.IRubyObject;
import org.jruby.util.JRubyClassLoader;
@@ -139,7 +140,7 @@ public static Class compile(Ruby ruby, Node ast, JRubyClassLoader jrubyClassLoad
// run compiler
CompilerTarget target = new JDK7();
- scope.prepareForInterpretation();
+ scope.prepareForCompilation();
target.codegen(scope);
@@ -220,8 +221,10 @@ public void emit(IRScriptBody script) {
pushmethod("__script__", 0);
- for (Instr instr: script.getInstrs()) {
- emit(instr);
+ for (BasicBlock b : script.getCFG().getBasicBlocks()) {
+ for (Instr instr: b.getInstrs()) {
+ emit(instr);
+ }
}
popmethod();
@@ -233,10 +236,12 @@ public void emit(IRScriptBody script) {
public void emit(IRMethod method) {
pushmethod(method.getName(), method.getCallArgs().length);
- for (Instr instr: method.getInstrs()) {
- System.out.println(instr);
- System.out.println(instr.getClass());
- emit(instr);
+ for (BasicBlock b : method.getCFG().getBasicBlocks()) {
+ for (Instr instr: b.getInstrs()) {
+ System.out.println(instr);
+ System.out.println(instr.getClass());
+ emit(instr);
+ }
}
popmethod();

0 comments on commit c445895

Please sign in to comment.