use of org.mapleir.ir.code.expr.VarExpr in project maple-ir by LLVM-but-worse.
the class ControlFlowGraph method overwrite.
/**
* Replaces an expression and updates def/use information accordingly.
* @param parent Statement containing expression to be replaced.
* @param from Statement to be replaced.
* @param to Statement to replace old statement with.
*/
public void overwrite(CodeUnit parent, Expr from, Expr to) {
// remove uses in from
for (Expr e : from.enumerateWithSelf()) {
if (e.getOpcode() == Opcode.LOCAL_LOAD) {
VersionedLocal l = (VersionedLocal) ((VarExpr) e).getLocal();
locals.uses.get(l).remove(e);
}
}
// add uses in to
for (Expr e : to.enumerateWithSelf()) {
if (e.getOpcode() == Opcode.LOCAL_LOAD) {
VarExpr var = (VarExpr) e;
locals.uses.get((VersionedLocal) var.getLocal()).add(var);
}
}
parent.overwrite(to, parent.indexOf(from));
}
use of org.mapleir.ir.code.expr.VarExpr in project maple-ir by LLVM-but-worse.
the class ControlFlowGraph method exciseEdge.
/**
* Properly removes the edge, and cleans up phi uses in fe.dst of phi arguments from fe.src.
* @param fe Edge to excise phi uses.
*/
public void exciseEdge(FlowEdge<BasicBlock> fe) {
if (!this.containsEdge(fe.src(), fe))
throw new IllegalArgumentException("Graph does not contain the specified edge");
removeEdge(fe.src(), fe);
for (Stmt stmt : fe.dst()) {
if (stmt.getOpcode() == PHI_STORE) {
CopyPhiStmt phs = (CopyPhiStmt) stmt;
PhiExpr phi = phs.getExpression();
BasicBlock pred = fe.src();
VarExpr arg = (VarExpr) phi.getArgument(pred);
VersionedLocal l = (VersionedLocal) arg.getLocal();
locals.uses.get(l).remove(arg);
phi.removeArgument(pred);
} else {
return;
}
}
}
use of org.mapleir.ir.code.expr.VarExpr in project maple-ir by LLVM-but-worse.
the class SSAGenPass method pruneStatements.
private int pruneStatements() {
int s = pool.uses.size();
Iterator<Entry<VersionedLocal, Set<VarExpr>>> it = pool.uses.entrySet().iterator();
while (it.hasNext()) {
Entry<VersionedLocal, Set<VarExpr>> e = it.next();
VersionedLocal vl = e.getKey();
if (e.getValue().size() == 0) {
AbstractCopyStmt def = pool.defs.get(vl);
/* i.e. it has not been shadowed. */
if (def != null && def.getBlock() != null && prune(def)) {
if (vl != def.getVariable().getLocal()) {
throw new RuntimeException(vl + ", " + def);
}
/* use pool remove */
it.remove();
pool.defs.remove(vl);
}
}
}
return s - pool.uses.size();
}
use of org.mapleir.ir.code.expr.VarExpr in project maple-ir by LLVM-but-worse.
the class SSAGenPass method aggregateInitialisers.
private void aggregateInitialisers() {
for (BasicBlock b : builder.graph.vertices()) {
for (Stmt stmt : new ArrayList<>(b)) {
if (stmt.getOpcode() == Opcode.POP) {
PopStmt pop = (PopStmt) stmt;
Expr expr = pop.getExpression();
if (expr.getOpcode() == Opcode.INVOKE) {
InvocationExpr invoke = (InvocationExpr) expr;
if (invoke.getCallType() == InvocationExpr.CallType.SPECIAL && invoke.getName().equals("<init>")) {
Expr inst = invoke.getPhysicalReceiver();
if (inst.getOpcode() == Opcode.LOCAL_LOAD) {
VarExpr var = (VarExpr) inst;
VersionedLocal local = (VersionedLocal) var.getLocal();
AbstractCopyStmt def = pool.defs.get(local);
Expr rhs = def.getExpression();
if (rhs.getOpcode() == Opcode.ALLOC_OBJ) {
// replace pop(x.<init>()) with x := new Klass();
// remove x := new Klass;
// here we are assuming that the new object
// can't be used until it is initialised.
Expr[] args = invoke.getParameterExprs();
// we want to reuse the exprs, so free it first.
pop.deleteAt(0);
Expr[] newArgs = Arrays.copyOf(args, args.length);
for (int i = args.length - 1; i >= 0; i--) {
args[i].unlink();
}
// remove the old def
def.delete();
int index = b.indexOf(pop);
// add a copy statement before the pop (x = newExpr)
InitialisedObjectExpr newExpr = new InitialisedObjectExpr(invoke.getOwner(), invoke.getDesc(), newArgs);
CopyVarStmt newCvs = new CopyVarStmt(var, newExpr);
pool.defs.put(local, newCvs);
pool.uses.get(local).remove(var);
b.add(index, newCvs);
// remove the pop statement
b.remove(pop);
// update the latestval constraints
LatestValue lval = latest.get(local);
if (lval.hasConstraints()) {
/* need to check this out (shouldn't happen) */
System.out.println("Constraints:");
for (Constraint c : lval.getConstraints()) {
System.out.println(" " + c);
}
throw new IllegalStateException(lval.toString());
} else {
lval.makeConstraints(newExpr);
}
}
} else if (inst.getOpcode() == Opcode.ALLOC_OBJ) {
// replace pop(new Klass.<init>(args)) with pop(new Klass(args))
// UninitialisedObjectExpr obj = (UninitialisedObjectExpr) inst;
Expr[] args = invoke.getParameterExprs();
// we want to reuse the exprs, so free it first.
invoke.unlink();
for (Expr e : args) {
e.unlink();
}
Expr[] newArgs = Arrays.copyOf(args, args.length);
InitialisedObjectExpr newExpr = new InitialisedObjectExpr(invoke.getOwner(), invoke.getDesc(), newArgs);
// replace pop contents
// no changes to defs or uses
pop.setExpression(newExpr);
} else {
System.err.println(b);
System.err.println("Stmt: " + stmt.getDisplayName() + ". " + stmt);
System.err.println("Inst: " + inst);
System.err.println(builder.graph);
throw new RuntimeException("interesting1 " + inst.getClass());
}
}
}
}
}
}
}
use of org.mapleir.ir.code.expr.VarExpr in project maple-ir by LLVM-but-worse.
the class SSAGenPass method removeSimpleCopy.
private void removeSimpleCopy(AbstractCopyStmt copy) {
VarExpr v = (VarExpr) copy.getExpression();
VersionedLocal vl = (VersionedLocal) v.getLocal();
copy.delete();
pool.uses.get(vl).remove(v);
}
Aggregations