Example usage for org.eclipse.jdt.internal.compiler.codegen Opcodes OPC_invokevirtual

List of usage examples for org.eclipse.jdt.internal.compiler.codegen Opcodes OPC_invokevirtual

Introduction

In this page you can find the example usage for org.eclipse.jdt.internal.compiler.codegen Opcodes OPC_invokevirtual.

Prototype

byte OPC_invokevirtual

To view the source code for org.eclipse.jdt.internal.compiler.codegen Opcodes OPC_invokevirtual.

Click Source Link

Usage

From source file:org.eclipse.objectteams.otdt.internal.core.compiler.bytecode.BytecodeTransformer.java

License:Open Source License

/** Look for the nop pattern of a local var that is used to
  *  prepare for lifting. If the pattern is found, patch all those
  *  opcodes, that are constant (see class comment in Lifting).
 *//* w ww. j ava  2 s  .  c  om*/
private int checkPatchLiftingNops(byte[] code, int idx) {
    int i;

    // Expecting 6 nops:
    for (i = idx + 1; i < idx + 6; i++)
        if (code[i] != Opcodes.OPC_nop)
            return -1;

    // Expecting aload_<loadPos>:
    int loadPos = OTByteCodes.getAloadPos(code[idx + 6], code[idx + 7]);
    if (loadPos == -1)
        return -1;
    int storeStart = (loadPos > 3) ? 8 : 7; // depends on space for pos operand

    // Expecting 3 nops:
    for (i = idx + storeStart; i < idx + storeStart + 3; i++)
        if (code[i] != Opcodes.OPC_nop)
            return -1;

    // Expecting astore_<storePos>:
    int storePos = OTByteCodes.getAstorePos(code[idx + 10], code[idx + 11]);
    if (storePos == -1)
        return -1;

    // Full match, start patching:

    // patching 6 nops:
    code[idx + 0] = Opcodes.OPC_aload_0;
    code[idx + 1] = Opcodes.OPC_invokevirtual;
    //  [idx+2/3]: space for "_OT$initCaches"
    code[idx + 4] = Opcodes.OPC_pop;

    code[idx + 5] = Opcodes.OPC_aload_0;

    // leave aload<loadPos>
    if (loadPos > 3)
        idx++;

    // patching 3 nops:
    code[idx + 7] = Opcodes.OPC_invokevirtual;
    //  [idx+8/9]: space for _OT$liftTo<Role>

    // leave astore<storePos>
    if (storePos > 3)
        loadPos += 0x2000; // flag to client that longer byte code is used
    return loadPos;
}

From source file:org.eclipse.objectteams.otdt.internal.core.compiler.lifting.Lifting.java

License:Open Source License

/**
* API for AbstractMethodDeclaration://  www  .  jav a  2  s.co  m
*
 *  Create a byte code sequence for a runtime check in a creation method:
 *  R _OT$create_OT$R(B b) {
 *       if (this._OT$cache_OT$R.contains(b))
 *       throw new DuplicateRoleException("R");
 *     // continue regular code.
 *  }
 *
 * Note, the need for this runtime check is detected quite late.
 * At this point it is easier to create the byte code sequence directly,
 * rather the creating AST first.
 */
public static void createDuplicateRoleCheck(CodeStream codeStream, AbstractMethodDeclaration method) {
    MethodBinding binding = method.binding;
    Scope scope = method.scope;

    ReferenceBinding roleType = (ReferenceBinding) binding.returnType;
    String roleName = new String(roleType.readableName());
    // TODO(SH): check why roleType.getRoleModel().getClassPartBinding().roleModel may yield a different result.
    // I think it occured in haeder/stopwatch from smile-CVS.
    //RoleModel role = roleType.getRealClass().roleModel;
    char[] cacheName = LiftingEnvironment.getCacheName(roleType.roleModel.getBoundRootRole());

    ReferenceBinding teamBinding = roleType.enclosingType();//role.getTeamModel().getBinding();
    FieldBinding cache = TypeAnalyzer.findField(teamBinding, cacheName, /*static*/false, /*outer*/false,
            ITranslationStates.STATE_FULL_LIFTING); // generated by this state
    if (cache == null)
        throw new InternalCompilerError("generated cache field not found: " + new String(cacheName)); //$NON-NLS-1$
    ReferenceBinding map = (ReferenceBinding) scope.getType(IOTConstants.WEAK_HASH_MAP, 3);
    MethodBinding contains = map.getMethod(scope, IOTConstants.CONTAINS_KEY);

    ReferenceBinding exc = (ReferenceBinding) scope.getType(IOTConstants.ORG_OBJECTTEAMS_DUPLICATE_ROLE, 3);
    TypeBinding[] types = new TypeBinding[] { scope.getJavaLangString() };
    MethodBinding excInit = exc.getExactConstructor(types);

    BranchLabel normalCase = new BranchLabel(codeStream);

    codeStream.aload_0(); // this
    codeStream.fieldAccess(Opcodes.OPC_getfield, cache, teamBinding); // getfield      MyTeam._OT$cache_OT$R Ljava/util/WeakHashMap;
    codeStream.aload_1(); // arg0
    codeStream.invoke(Opcodes.OPC_invokevirtual, contains, map); // invokevirtual java.util.WeakHashMap.containsKey (Ljava/lang/Object;)Z
    codeStream.ifeq(normalCase); // false -> #endif
    codeStream.new_(exc); // new           <org.objectteams.DuplicateRoleException>
    codeStream.dup(); // dup
    codeStream.ldc(roleName); // ldc "R"
    codeStream.invoke(Opcodes.OPC_invokespecial, excInit, exc); // invokespecial org.objectteams.DuplicateRoleException.<init> (Ljava/lang/String;)V
    codeStream.athrow(); // athrow
    normalCase.place(); // #endif
}

From source file:org.eclipse.objectteams.otdt.internal.core.compiler.lookup.SyntheticRoleFieldAccess.java

License:Open Source License

/**
 * Generate the sequence for invoking this accessor.
 *
 * PRE: the role instance is on the stack, for write access also the new value
 * POST: values from PRE have been consumed, for read access the value is on the stack
 *
 * @param codeStream/*from  www .ja v a 2  s . c o m*/
 */
public byte prepareOrGenerateInvocation(CodeStream codeStream, byte opcode) {
    ReferenceBinding roleType = (ReferenceBinding) this.parameters[0];
    if (roleType instanceof UnresolvedReferenceBinding) {
        try {
            roleType = ((UnresolvedReferenceBinding) roleType).resolve(Config.getLookupEnvironment(), false);
        } catch (NotConfiguredException e) {
            e.logWarning("Failed to generate accessor"); //$NON-NLS-1$
            return opcode;
        }
        this.parameters[0] = roleType;
    }
    if (this.purpose == FieldReadAccess || this.purpose == SuperFieldReadAccess) {
        insertOuterAccess(codeStream, roleType); // role -> role,team
        codeStream.swap(); // role,team -> team,role
        codeStream.invoke(Opcodes.OPC_invokevirtual, this, // team,role -> result
                this.declaringClass);
    } else {
        TypeBinding targetType = this.targetWriteField.type;
        LocalVariableBinding arg = new LocalVariableBinding("<tmp>".toCharArray(), //$NON-NLS-1$
                targetType, 0, false);
        arg.resolvedPosition = codeStream.maxLocals;
        arg.useFlag = LocalVariableBinding.USED;
        codeStream.record(arg);
        arg.recordInitializationStartPC(codeStream.position);
        codeStream.store(arg, false/*valueRequired*/); // role, arg -> role
        insertOuterAccess(codeStream, roleType); // role -> role,team
        codeStream.swap(); // role,team -> team,role
        codeStream.load(arg); //            -> team,role,arg
        codeStream.invoke(Opcodes.OPC_invokevirtual, this, //           -> <empty>
                this.declaringClass);
        if (arg.initializationPCs != null) // null checking is asymmetric in LocalVariableBinding.
            arg.recordInitializationEndPC(codeStream.position);
    }
    return 0; // done
}

From source file:org.eclipse.objectteams.otdt.internal.core.compiler.statemachine.transformer.RoleMigrationImplementor.java

License:Open Source License

static void genMigrateToBaseInstructions(CodeStream codeStream, SourceTypeBinding roleBinding, Scope scope,
        char[] cacheName) {
    FieldBinding baseField = roleBinding.getField(IOTConstants._OT_BASE, true);
    // accessing the cache (using remove() and put()):
    ReferenceBinding cacheTypeBinding = (ReferenceBinding) scope.getType(IOTConstants.WEAK_HASH_MAP, 3);
    MethodBinding remove = getMethod(cacheTypeBinding, "remove".toCharArray(), 1); //$NON-NLS-1$
    MethodBinding put = cacheTypeBinding.getMethod(scope, "put".toCharArray()); //$NON-NLS-1$
    // accessing the base object (using _OT$removeRole() and _OT$addRole()):
    WeavingScheme weavingScheme = scope.compilerOptions().weavingScheme;
    ReferenceBinding iboundBase = (ReferenceBinding) scope
            .getType(weavingScheme == WeavingScheme.OTDRE ? IOTConstants.ORG_OBJECTTEAMS_IBOUNDBASE2
                    : IOTConstants.ORG_OBJECTTEAMS_IBOUNDBASE, 3);

    // remove old from cache
    codeStream.aload_0(); // this
    codeStream.fieldAccess(Opcodes.OPC_getfield, enclosingInstanceField(roleBinding), // this.this$n
            roleBinding);//from w  ww.ja v a 2s. c  o  m
    codeStream.fieldAccess(Opcodes.OPC_getfield, roleBinding.enclosingType().getField(cacheName, true), // this.this$n._OT$cache$R
            roleBinding.enclosingType());
    codeStream.dup(); // for use in put() below
    codeStream.aload_0(); // this
    codeStream.fieldAccess(Opcodes.OPC_getfield, baseField, // this._OT$base
            roleBinding);
    codeStream.dup(); // share for nested method call         // this._OT$base
    // remove role from this (old) base
    genAddOrRemoveRole(codeStream, scope, iboundBase, false);// -> void      // -> base._OT$removeRole(this)
    codeStream.invoke(Opcodes.OPC_invokevirtual, remove, // -> cache.remove(base)
            cacheTypeBinding);
    codeStream.pop(); // discard result

    // this._OT$base = (MyBase)otherBase
    codeStream.aload_0(); // this
    codeStream.aload_1(); // otherBase
    codeStream.checkcast(roleBinding.baseclass());
    codeStream.fieldAccess(Opcodes.OPC_putfield, baseField, roleBinding);

    // add new to cache (cache is still on the stack)
    codeStream.aload_1(); // otherBase
    codeStream.aload_0(); // this (role)
    codeStream.invoke(Opcodes.OPC_invokevirtual, put, cacheTypeBinding);

    // add to new base:
    codeStream.aload_1(); // otherBase
    genAddOrRemoveRole(codeStream, scope, iboundBase, true); // -> void      // -> base._OT$addRemoveRole(this, false)

    codeStream.return_();
}