85 lines
2.8 KiB
Plaintext
85 lines
2.8 KiB
Plaintext
|
package slangc.model.expressions;
|
||
|
|
||
|
import slangc.api.BytecodeInstructionWriter;
|
||
|
import slangc.api.Reporter;
|
||
|
import slangc.bytecode.TypeSignature;
|
||
|
import slangc.model.ExpressionModel;
|
||
|
import slangc.model.ExpressionOwner;
|
||
|
import slangc.model.ExpressionResult;
|
||
|
import slangc.model.TypeLevel;
|
||
|
import slangc.model.TypeModel;
|
||
|
import slangc.model.UserTypeModel;
|
||
|
import slangc.parser.Branch;
|
||
|
import slangc.parser.Node;
|
||
|
|
||
|
public class OuterThisExpression extends ExpressionModel implements ExpressionOwner {
|
||
|
private TypeModel leftHandSide;
|
||
|
|
||
|
public OuterThisExpression(ExpressionOwner owner, Node source) {
|
||
|
super(owner, source);
|
||
|
Node t = ((Branch)source).getSubnode(0);
|
||
|
leftHandSide = owner.resolveType(t);//ExpressionModel.construct(this, ((Branch)sourceFile).getSubnode(0));
|
||
|
}
|
||
|
|
||
|
@Override
|
||
|
public void dump(Reporter reporter, String indent, String incr) {
|
||
|
reporter.note("DUMP", indent + "> Outer this expression of " + leftHandSide);
|
||
|
dumpResolved(reporter, indent + incr, incr);
|
||
|
}
|
||
|
|
||
|
@Override
|
||
|
public TypeModel getExpectedResult(ExpressionModel e) {
|
||
|
// TODO Auto-generated method stub
|
||
|
return null;
|
||
|
}
|
||
|
|
||
|
public TypeModel getType() {
|
||
|
return leftHandSide;
|
||
|
}
|
||
|
|
||
|
@Override
|
||
|
public ExpressionModel[] getSubexpressions() {
|
||
|
return NO_SUBEXPRESSIONS;
|
||
|
}
|
||
|
|
||
|
@Override
|
||
|
protected ExpressionResult resolveResult() {
|
||
|
// TODO Should probably check that the outer this actually makes sense first
|
||
|
return new ExpressionResult.TypedValue(getType());
|
||
|
}
|
||
|
|
||
|
public static TypeSignature generatePossibleOuterThis(BytecodeInstructionWriter w, UserTypeModel thisThis, TypeModel desiredOuter) {
|
||
|
return generatePossibleOuterThis(w, thisThis, desiredOuter, false);
|
||
|
}
|
||
|
|
||
|
private static TypeSignature generatePossibleOuterThis(BytecodeInstructionWriter w, UserTypeModel thisThis, TypeModel desiredOuter, boolean alreadyRecursing) {
|
||
|
if ((thisThis == desiredOuter || thisThis.inherits(desiredOuter)) && !alreadyRecursing) {
|
||
|
w.genThis();
|
||
|
return thisThis.getTypeSignature();
|
||
|
} else if (thisThis.isNonStaticInnerType()) {
|
||
|
TypeModel outer = thisThis.getOwner().getNearestType();
|
||
|
if (!alreadyRecursing) {
|
||
|
w.genThis();
|
||
|
}
|
||
|
w.genOuterThis();
|
||
|
if (outer == desiredOuter || outer.inherits(desiredOuter)) {
|
||
|
return outer.getTypeSignature();
|
||
|
} else {
|
||
|
return generatePossibleOuterThis(w, (UserTypeModel) outer, desiredOuter, true);
|
||
|
}
|
||
|
} else {
|
||
|
w.genError("Bad outer this, can't get to " + desiredOuter + " from " + thisThis);
|
||
|
return null;
|
||
|
}
|
||
|
}
|
||
|
|
||
|
@Override
|
||
|
public TypeSignature innerGenerate(BytecodeInstructionWriter w) {
|
||
|
return generatePossibleOuterThis(w, (UserTypeModel)getMethodOrField().getOwner(), leftHandSide);
|
||
|
}
|
||
|
|
||
|
public TypeModel resolveType(Node n) {
|
||
|
return super.resolveType(n); // TODO: Better support for interfaces
|
||
|
}
|
||
|
}
|