static void loadMethods(Env* env, Class* clazz) { ClassInfoHeader* header = lookupClassInfo(env, clazz->name, !clazz->classLoader || !clazz->classLoader->parent ? _bcBootClassesHash : _bcClassesHash); if (!header) return; ClassInfo ci; jint i; void* p = header; readClassInfo(&p, &ci); skipInterfaceNames(&p, &ci); skipFieldInfos(&p, &ci); for (i = 0; i < ci.methodCount; i++) { MethodInfo mi; readMethodInfo(&p, &mi); if (mi.targetFnPtr) { if (!rvmAddBridgeMethod(env, clazz, mi.name, mi.desc, mi.access, mi.size, mi.impl, mi.synchronizedImpl, mi.targetFnPtr, mi.attributes)) return; } else if (mi.callbackImpl) { if (!rvmAddCallbackMethod(env, clazz, mi.name, mi.desc, mi.access, mi.size, mi.impl, mi.synchronizedImpl, mi.callbackImpl, mi.attributes)) return; } else { if (!rvmAddMethod(env, clazz, mi.name, mi.desc, mi.access, mi.size, mi.impl, mi.synchronizedImpl, mi.attributes)) return; } } }
static void iterateClassInfos(Env* env, jboolean (*callback)(Env*, ClassInfoHeader*, MethodInfo*, void*), void* hash, void* data) { ClassInfoHeader** base = getClassInfosBase(hash); jint count = getClassInfosCount(hash); jint i = 0; for (i = 0; i < count; i++) { ClassInfo ci; void* p = base[i]; readClassInfo(&p, &ci); skipInterfaceNames(&p, &ci); skipFieldInfos(&p, &ci); jint j; for (j = 0; j < ci.methodCount; j++) { MethodInfo mi; readMethodInfo(&p, &mi); if (!callback(env, base[i], &mi, data)) { break; } } } }
static Method* loadMethods(Env* env, Class* clazz) { ClassInfoHeader* header = lookupClassInfo(env, clazz->name, !clazz->classLoader || !rvmGetParentClassLoader(env, clazz->classLoader) ? _bcBootClassesHash : _bcClassesHash); if (!header) return NULL; ClassInfo ci; jint i; void* p = header; readClassInfo(&p, &ci); skipInterfaceNames(&p, &ci); skipFieldInfos(&p, &ci); Method* first = NULL; for (i = 0; i < ci.methodCount; i++) { MethodInfo mi; readMethodInfo(&p, &mi); if (!isStrippedMethod(&mi)) { Method* m = NULL; if (mi.targetFnPtr) { m = (Method*) rvmAllocateBridgeMethod(env, clazz, mi.name, mi.desc, mi.vtableIndex, mi.access, mi.size, mi.impl, mi.synchronizedImpl, mi.targetFnPtr, mi.attributes); } else if (mi.callbackImpl) { m = (Method*) rvmAllocateCallbackMethod(env, clazz, mi.name, mi.desc, mi.vtableIndex, mi.access, mi.size, mi.impl, mi.synchronizedImpl, mi.linetable, mi.callbackImpl, mi.attributes); } else { m = rvmAllocateMethod(env, clazz, mi.name, mi.desc, mi.vtableIndex, mi.access, mi.size, mi.impl, mi.synchronizedImpl, mi.linetable, mi.attributes); } if (!m) goto error; LL_PREPEND(first, m); } } return first; error: while (first) { Method* next = first->next; rvmFreeMemoryUncollectable(env, first); first = next; } return NULL; }
void BinReader::readClass(Type *type) { readMemberInfo(type); MetaInfo *meta = type->getMetaInfo("Native"); if (meta) { type->attr.isNative = true; if (meta->keys.find("managed") != UT_NPOS) { type->attr.isNativeManaged = true; } } int numClassAttr = bytes->readInt(); for (int i = 0; i < numClassAttr; i++) { const char *cattr = readPoolString(); if (!strcmp(cattr, "public")) { type->attr.isPublic = true; } if (!strcmp(cattr, "static")) { type->attr.isStatic = true; } if (!strcmp(cattr, "final")) { type->attr.isFinal = true; } } // base type Type *baseType = getType(readPoolString()); if (baseType) { type->setBaseType(baseType); } // interfaces int numInterfaces = bytes->readInt(); for (int i = 0; i < numInterfaces; i++) { Type *interface = getType(readPoolString()); type->addInterface(interface); } // delegate types int numDelegateTypes = bytes->readInt(); for (int i = 0; i < numDelegateTypes; i++) { Type *delegateType = getType(readPoolString()); type->addDelegateType(delegateType); } // delegateReturnType Type *delegateReturnType = getType(readPoolString()); if (delegateReturnType) { type->setDelegateReturnType(delegateReturnType); } // imports int numImports = bytes->readInt(); for (int i = 0; i < numImports; i++) { Type *import = getType(readPoolString()); type->addImport(import); } // read constructor if (bytes->readBoolean()) { ConstructorInfo *cinfo = readConstructor(type); type->addMember(cinfo); } // read fields int numFields = bytes->readInt(); for (int i = 0; i < numFields; i++) { FieldInfo *fieldInfo = readField(type); type->addMember(fieldInfo); } // read properties int numProps = bytes->readInt(); for (int i = 0; i < numProps; i++) { PropertyInfo *propertyInfo = readProperty(type); type->addMember(propertyInfo); } // read methods int numMethods = bytes->readInt(); for (int i = 0; i < numMethods; i++) { MethodInfo *methodInfo = readMethodInfo(type); type->addMember(methodInfo); } type->setBCStaticInitializer(ByteCode::decode64(bytes->readString())); type->setBCInstanceInitializer(ByteCode::decode64(bytes->readString())); }
PropertyInfo *BinReader::readProperty(Type *type) { PropertyInfo *prop = lmNew(NULL) PropertyInfo(); readMemberInfo(prop); // read attributes int numAttr = bytes->readInt(); for (int i = 0; i < numAttr; i++) { const char *attr = readPoolString(); if (!strcmp(attr, "static")) { prop->attr.isStatic = true; } else if (!strcmp(attr, "public")) { prop->attr.isPublic = true; } else if (!strcmp(attr, "private")) { prop->attr.isPrivate = true; } else if (!strcmp(attr, "protected")) { prop->attr.isProtected = true; } else if (!strcmp(attr, "native")) { prop->attr.isNative = true; } } Type *ptype = NULL; if (bytes->readBoolean()) { ptype = getType(readPoolString()); } prop->type = ptype; // getter MethodInfo *getter = NULL; if (bytes->readBoolean()) { getter = readMethodInfo(type); prop->getter = getter; getter->setPropertyInfo(prop); } // setter MethodInfo *setter = NULL; if (bytes->readBoolean()) { setter = readMethodInfo(type); prop->setter = setter; setter->setPropertyInfo(prop); } return prop; }