1 /* 2 * reserved comment block 3 * DO NOT REMOVE OR ALTER! 4 */ 5 /* 6 * Licensed to the Apache Software Foundation (ASF) under one or more 7 * contributor license agreements. See the NOTICE file distributed with 8 * this work for additional information regarding copyright ownership. 9 * The ASF licenses this file to You under the Apache License, Version 2.0 10 * (the "License"); you may not use this file except in compliance with 11 * the License. You may obtain a copy of the License at 12 * 13 * http://www.apache.org/licenses/LICENSE-2.0 14 * 15 * Unless required by applicable law or agreed to in writing, software 16 * distributed under the License is distributed on an "AS IS" BASIS, 17 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 18 * See the License for the specific language governing permissions and 19 * limitations under the License. 20 */ 21 22 package com.sun.org.apache.bcel.internal.generic; 23 24 import com.sun.org.apache.bcel.internal.Constants; 25 import com.sun.org.apache.bcel.internal.classfile.*; 26 import java.util.StringTokenizer; 27 28 /** 29 * Super class for the INVOKExxx family of instructions. 30 * 31 * @author <A HREF="mailto:markus.dahm@berlin.de">M. Dahm</A> 32 */ 33 public abstract class InvokeInstruction extends FieldOrMethod 34 implements ExceptionThrower, TypedInstruction, StackConsumer, StackProducer { 35 /** 36 * Empty constructor needed for the Class.newInstance() statement in 37 * Instruction.readInstruction(). Not to be used otherwise. 38 */ 39 InvokeInstruction() {} 40 41 /** 42 * @param index to constant pool 43 */ 44 protected InvokeInstruction(short opcode, int index) { 45 super(opcode, index); 46 } 47 48 /** 49 * @return mnemonic for instruction with symbolic references resolved 50 */ 51 public String toString(ConstantPool cp) { 52 Constant c = cp.getConstant(index); 53 StringTokenizer tok = new StringTokenizer(cp.constantToString(c)); 54 55 return Constants.OPCODE_NAMES[opcode] + " " + 56 tok.nextToken().replace('.', '/') + tok.nextToken(); 57 } 58 59 /** 60 * Also works for instructions whose stack effect depends on the 61 * constant pool entry they reference. 62 * @return Number of words consumed from stack by this instruction 63 */ 64 public int consumeStack(ConstantPoolGen cpg) { 65 String signature = getSignature(cpg); 66 Type[] args = Type.getArgumentTypes(signature); 67 int sum; 68 69 if(opcode == Constants.INVOKESTATIC) 70 sum = 0; 71 else 72 sum = 1; // this reference 73 74 int n = args.length; 75 for (int i = 0; i < n; i++) 76 sum += args[i].getSize(); 77 78 return sum; 79 } 80 81 /** 82 * Also works for instructions whose stack effect depends on the 83 * constant pool entry they reference. 84 * @return Number of words produced onto stack by this instruction 85 */ 86 public int produceStack(ConstantPoolGen cpg) { 87 return getReturnType(cpg).getSize(); 88 } 89 90 /** @return return type of referenced method. 91 */ 92 public Type getType(ConstantPoolGen cpg) { 93 return getReturnType(cpg); 94 } 95 96 /** @return name of referenced method. 97 */ 98 public String getMethodName(ConstantPoolGen cpg) { 99 return getName(cpg); 100 } 101 102 /** @return return type of referenced method. 103 */ 104 public Type getReturnType(ConstantPoolGen cpg) { 105 return Type.getReturnType(getSignature(cpg)); 106 } 107 108 /** @return argument types of referenced method. 109 */ 110 public Type[] getArgumentTypes(ConstantPoolGen cpg) { 111 return Type.getArgumentTypes(getSignature(cpg)); 112 } 113 }