use of com.oracle.truffle.espresso.classfile.attributes.Local in project graal by oracle.
the class ClassfileParser method validateLocalTables.
private void validateLocalTables(Attribute[] codeAttributes) {
if (getMajorVersion() < JAVA_1_5_VERSION) {
return;
}
EconomicMap<Local, Boolean> table = EconomicMap.create(Local.localEquivalence);
ArrayList<LocalVariableTable> typeTables = new ArrayList<>();
for (Attribute attr : codeAttributes) {
if (attr.getName() == Name.LocalVariableTable) {
LocalVariableTable localTable = (LocalVariableTable) attr;
for (Local local : localTable.getLocals()) {
if (table.put(local, false) != null) {
throw ConstantPool.classFormatError("Duplicate local in local variable table: " + local);
}
}
} else if (attr.getName() == Name.LocalVariableTypeTable) {
typeTables.add((LocalVariableTable) attr);
}
}
for (LocalVariableTable typeTable : typeTables) {
for (Local local : typeTable.getLocals()) {
Boolean present = table.put(local, true);
if (present == null) {
throw ConstantPool.classFormatError("Local in local variable type table does not match any local variable table entry: " + local);
}
if (present) {
throw ConstantPool.classFormatError("Duplicate local in local variable type table: " + local);
}
}
}
}
use of com.oracle.truffle.espresso.classfile.attributes.Local in project graal by oracle.
the class EspressoInstrumentableNode method getScope.
@ExportMessage
@TruffleBoundary
@SuppressWarnings("static-method")
public final Object getScope(Frame frame, @SuppressWarnings("unused") boolean nodeEnter) {
// construct the current scope with valid local variables information
Method method = getMethod();
Local[] liveLocals = method.getLocalVariableTable().getLocalsAt(getBci(frame));
if (liveLocals.length == 0) {
// class was compiled without a local variable table
// include "this" in method arguments throughout the method
boolean hasReceiver = !method.isStatic();
int localCount = hasReceiver ? 1 : 0;
localCount += method.getParameterCount();
liveLocals = new Local[localCount];
Klass[] parameters = (Klass[]) method.getParameters();
Utf8ConstantTable utf8Constants = getContext().getLanguage().getUtf8ConstantTable();
int startslot = 0;
if (hasReceiver) {
// include 'this' and method arguments
liveLocals[0] = new Local(utf8Constants.getOrCreate(Symbol.Name.thiz), utf8Constants.getOrCreate(method.getDeclaringKlass().getType()), 0, 65536, 0);
startslot++;
}
// include method parameters
for (int i = startslot; i < localCount; i++) {
Klass param = hasReceiver ? parameters[i - 1] : parameters[i];
liveLocals[i] = new Local(utf8Constants.getOrCreate(ByteSequence.create("param_" + (i))), utf8Constants.getOrCreate(param.getType()), 0, 65536, i);
}
}
return EspressoScope.createVariables(liveLocals, frame, method.getName());
}
use of com.oracle.truffle.espresso.classfile.attributes.Local in project graal by oracle.
the class ClassRedefinition method checkLocalVariableTable.
private static boolean checkLocalVariableTable(LocalVariableTable table1, LocalVariableTable table2) {
Local[] oldLocals = table1.getLocals();
Local[] newLocals = table2.getLocals();
if (oldLocals.length != newLocals.length) {
return true;
}
for (int i = 0; i < oldLocals.length; i++) {
Local oldLocal = oldLocals[i];
Local newLocal = newLocals[i];
if (!oldLocal.getNameAsString().equals(newLocal.getNameAsString()) || oldLocal.getSlot() != newLocal.getSlot() || oldLocal.getStartBCI() != newLocal.getStartBCI() || oldLocal.getEndBCI() != newLocal.getEndBCI()) {
return true;
}
}
return false;
}
use of com.oracle.truffle.espresso.classfile.attributes.Local in project graal by oracle.
the class ClassfileParser method parseLocalVariableTable.
private LocalVariableTable parseLocalVariableTable(Symbol<Name> name, int codeLength, int maxLocals) {
boolean isLVTT = Name.LocalVariableTypeTable.equals(name);
int entryCount = stream.readU2();
if (entryCount == 0) {
return isLVTT ? LocalVariableTable.EMPTY_LVTT : LocalVariableTable.EMPTY_LVT;
}
Local[] locals = new Local[entryCount];
for (int i = 0; i < entryCount; i++) {
int bci = stream.readU2();
int length = stream.readU2();
int nameIndex = stream.readU2();
int descIndex = stream.readU2();
int slot = stream.readU2();
if (bci < 0 || bci >= codeLength) {
throw ConstantPool.classFormatError("Invalid local variable table attribute entry: start_pc out of bounds: " + bci);
}
if (bci + length > codeLength) {
throw ConstantPool.classFormatError("Invalid local variable table attribute entry: start_pc + length out of bounds: " + (bci + length));
}
Utf8Constant poolName = pool.utf8At(nameIndex);
Utf8Constant typeName = pool.utf8At(descIndex);
typeName.validateUTF8();
poolName.validateFieldName();
int extraSlot = 0;
if (!isLVTT) {
typeName.validateType(false);
Symbol<Type> type = typeName.value();
if (type == Type._long || type == Type._double) {
extraSlot = 1;
}
}
if (slot + extraSlot >= maxLocals) {
throw ConstantPool.classFormatError("Invalid local variable table attribute entry: index points to an invalid frame slot: " + slot);
}
locals[i] = new Local(poolName, typeName, bci, bci + length, slot);
}
return new LocalVariableTable(name, locals);
}
Aggregations