private int getOrInsertMethodRef(int classIndex, int nameAndTypeIndex) throws IOException {
   int methodRef = constantPool.lookForRef(classIndex, nameAndTypeIndex);
   if (methodRef == -1) {
     methodRef = constantPool.poolSize() + 1;
     MethodRefConstant methodRefConstant = new MethodRefConstant(classIndex, nameAndTypeIndex);
     constantPool.add(methodRefConstant);
     methodRefConstant.serializeToStream(constantStream);
   }
   return methodRef;
 }
 private int getOrInsertString(int utf8Index) throws IOException {
   int stringIndex = constantPool.lookForString(utf8Index);
   if (stringIndex == -1) {
     stringIndex = constantPool.poolSize() + 1;
     StringConstant stringConstant = new StringConstant(utf8Index);
     constantPool.add(stringConstant);
     stringConstant.serializeToStream(constantStream);
   }
   return stringIndex;
 }
 private int getOrInsertClass(int nameIndex) throws IOException {
   int classIndex = constantPool.lookForClass(nameIndex);
   if (classIndex == -1) {
     classIndex = constantPool.poolSize() + 1;
     ClassConstant classConstant = new ClassConstant(nameIndex);
     constantPool.add(classConstant);
     classConstant.serializeToStream(constantStream);
   }
   return classIndex;
 }
 private int getOrInsertNameAndType(int nameIndex, int typeIndex) throws IOException {
   int nameAndTypeIndex = constantPool.lookForNameAndTypeReference(nameIndex, typeIndex);
   if (nameAndTypeIndex == -1) {
     nameAndTypeIndex = constantPool.poolSize() + 1;
     NameAndTypeConstant nameAndType = new NameAndTypeConstant(nameIndex, typeIndex);
     constantPool.add(nameAndType);
     nameAndType.serializeToStream(constantStream);
   }
   return nameAndTypeIndex;
 }
 private int getOrInsertUtf8(String string) throws IOException {
   int nameIndex = constantPool.lookForUtf8Reference(string);
   if (nameIndex == -1) {
     nameIndex = constantPool.poolSize() + 1;
     Utf8Constant name = new Utf8Constant(string);
     constantPool.add(name);
     name.serializeToStream(constantStream);
   }
   return nameIndex;
 }
  private MethodInfo readMethod() throws IOException {
    MethodInfo methodInfo = new MethodInfo();

    methodInfo.setAccessFlags(is.readUnsignedShort());
    methodInfo.setNameIndex(is.readUnsignedShort());
    methodInfo.setDescriptorIndex(is.readUnsignedShort());
    int attributesCount = is.readUnsignedShort();

    methodInfo.setAttributes(new AbstractAttribute[attributesCount]);

    for (int i = 0; i < attributesCount; i++) {
      AbstractAttribute attribute = attributeFacility.readAttribute();
      if (isInterceptorAnnotation(attribute)) {
        methodInfo.setInterceptorClass(
            ((RuntimeInvisibleAnnotations) attribute).getInterceptorClass());
      }
      methodInfo.getAttributes()[i] = attribute;
      if (attribute.getClass() == Code.class) {
        methodInfo.setCode((Code) attribute);
      }
    }

    methodInfo.setSignature(getMethodSignature(methodInfo));
    methodInfo.setMethodName(constantPool.getUtf8(methodInfo.getNameIndex()).getString());

    return methodInfo;
  }
  private void fixupSignature(MethodSignature signature) throws IOException {
    int classNameIndex = signature.getClassNameIndex();
    String dottedName = constantPool.getUtf8(classNameIndex).getString().replace("/", ".");
    signature.setClassNameIndex(getOrInsertUtf8(dottedName));

    signature.setMethodNameIndex(
        getOrInsertString(signature.getMethodNameIndex())); // will be a String resource now
    signature.setClassNameIndex(
        getOrInsertString(signature.getClassNameIndex())); // will be a String resource now
  }
 private int getObjectClassIndex() {
   int objectClassName =
       constantPool.lookForUtf8Reference(Object.class.getName().replace(".", "/"));
   return constantPool.lookForClass(objectClassName);
 }