[llvm-commits] CVS: llvm-java/lib/Compiler/Compiler.cpp
Alkis Evlogimenos
alkis at cs.uiuc.edu
Sun Jul 25 03:37:39 PDT 2004
Changes in directory llvm-java/lib/Compiler:
Compiler.cpp updated: 1.69 -> 1.70
---
Log message:
Implement getfield and putfield java opcodes.
---
Diffs of the changes: (+68 -18)
Index: llvm-java/lib/Compiler/Compiler.cpp
diff -u llvm-java/lib/Compiler/Compiler.cpp:1.69 llvm-java/lib/Compiler/Compiler.cpp:1.70
--- llvm-java/lib/Compiler/Compiler.cpp:1.69 Sat Jul 24 18:55:54 2004
+++ llvm-java/lib/Compiler/Compiler.cpp Sun Jul 25 05:37:29 2004
@@ -142,8 +142,14 @@
BasicBlock* prologue_;
typedef SetVector<Function*> FunctionSet;
FunctionSet toCompileFunctions_;
- typedef std::map<std::string, Type*> Class2TypeMap;
- Class2TypeMap c2tMap_;
+ struct ClassInfo {
+ explicit ClassInfo(Type* t) : type(t) { }
+ Type* type;
+ typedef std::map<std::string, unsigned> Field2IndexMap;
+ Field2IndexMap f2iMap;
+ };
+ typedef std::map<std::string, ClassInfo> Class2InfoMap;
+ Class2InfoMap c2ciMap_;
private:
BasicBlock* getBBAt(unsigned bcI) { return bc2bbMap_[bcI]; }
@@ -152,7 +158,7 @@
Type* getType(JType type) {
switch (type) {
case REFERENCE:
- return PointerType::get(getTypeForClass("java/lang/Object"));
+ return PointerType::get(getClassInfo("java/lang/Object").type);
case BOOLEAN: return Type::BoolTy;
case CHAR: return Type::UShortTy;
case FLOAT: return Type::FloatTy;
@@ -201,7 +207,7 @@
unsigned e = descr.find(';', i);
std::string className = descr.substr(i, e - i);
i = e + 1;
- return PointerType::get(getTypeForClass(className));
+ return PointerType::get(getClassInfo(className).type);
}
case '[':
// FIXME: this should really be a new class
@@ -220,28 +226,33 @@
}
}
- Type* getTypeForClass(const std::string& className) {
- Class2TypeMap::iterator it = c2tMap_.lower_bound(className);
- if (it == c2tMap_.end() || it->first != className) {
+ ClassInfo& getClassInfo(const std::string& className) {
+ Class2InfoMap::iterator it = c2ciMap_.lower_bound(className);
+ if (it == c2ciMap_.end() || it->first != className) {
ClassFile* cf = ClassFile::getClassFile(className);
OpaqueType* newType = OpaqueType::get();
- it = c2tMap_.insert(it, std::make_pair(className, newType));
+ it = c2ciMap_.insert(it, std::make_pair(className,
+ ClassInfo(newType)));
std::vector<const Type*> elements;
if (ConstantClass* super = cf->getSuperClass())
elements.push_back
- (getTypeForClass(super->getName()->str()));
+ (getClassInfo(super->getName()->str()).type);
const Fields& fields = cf->getFields();
for (unsigned i = 0, e = fields.size(); i != e; ++i) {
Field* field = fields[i];
- if (!field->isStatic())
+ if (!field->isStatic()) {
+ it->second.f2iMap.insert(
+ std::make_pair(field->getName()->str(),
+ elements.size()));
elements.push_back(getType(field->getDescriptor()));
+ }
}
PATypeHolder holder = newType;
newType->refineAbstractTypeTo(StructType::get(elements));
- it->second = holder.get();
+ it->second.type = holder.get();
DEBUG(std::cerr << "Adding " << className << " = "
- << *it->second << " to type map\n");
- module_->addTypeName(className, it->second);
+ << *it->second.type << " to type map\n");
+ module_->addTypeName(className, it->second.type);
}
return it->second;
}
@@ -271,6 +282,40 @@
return global;
}
+ Value* getField(unsigned bcI, unsigned index, Value* ptr) {
+ ConstantFieldRef* fieldRef =
+ (ConstantFieldRef*)(cf_->getConstantPool()[index]);
+ ConstantNameAndType* nameAndType = fieldRef->getNameAndType();
+
+ // Cast ptr to correct type
+ std::string className = fieldRef->getClass()->getName()->str();
+ ptr = new CastInst(ptr,
+ PointerType::get(getClassInfo(className).type),
+ TMP, getBBAt(bcI));
+ ClassFile* classfile = ClassFile::getClassFile(className);
+ std::string fieldName = nameAndType->getName()->str();
+
+ // deref pointer
+ std::vector<Value*> indices(1, ConstantUInt::get(Type::UIntTy, 0));
+ while (true) {
+ ClassInfo& info = getClassInfo(className);
+ ClassInfo::Field2IndexMap::iterator it =
+ info.f2iMap.find(fieldName);
+ if (it == info.f2iMap.end()) {
+ className = classfile->getSuperClass()->getName()->str();
+ classfile = ClassFile::getClassFile(className);
+ indices.push_back(ConstantUInt::get(Type::UIntTy, 0));
+ }
+ else {
+ indices.push_back(ConstantUInt::get(Type::UIntTy,
+ it->second));
+ break;
+ }
+ }
+
+ return new GetElementPtrInst(ptr, indices, TMP, getBBAt(bcI));
+ }
+
Function* compileMethodOnly(const std::string& classMethodDesc) {
DEBUG(std::cerr << "Compiling method: " << classMethodDesc << '\n');
@@ -394,9 +439,10 @@
// insert an opaque type for java.lang.Object. This is
// defined in runtime.ll
- c2tMap_.insert(std::make_pair("java/lang/Object",
- OpaqueType::get()));
- module.addTypeName("java/lang/Object", c2tMap_["java/lang/Object"]);
+ c2ciMap_.insert(std::make_pair("java/lang/Object",
+ ClassInfo(OpaqueType::get())));
+ module.addTypeName("java/lang/Object",
+ getClassInfo("java/lang/Object").type);
// compile the method requested
Function* function = compileMethodOnly(classMethodDesc);
@@ -766,11 +812,15 @@
}
void do_getfield(unsigned bcI, unsigned index) {
- assert(0 && "not implemented");
+ Value* p = opStack_.top(); opStack_.pop();
+ Value* v = new LoadInst(getField(bcI, index, p), TMP, getBBAt(bcI));
+ opStack_.push(v);
}
void do_putfield(unsigned bcI, unsigned index) {
- assert(0 && "not implemented");
+ Value* v = opStack_.top(); opStack_.pop();
+ Value* p = opStack_.top(); opStack_.pop();
+ new StoreInst(v, getField(bcI, index, p), getBBAt(bcI));
}
void do_invokevirtual(unsigned bcI, unsigned index) {
More information about the llvm-commits
mailing list