aboutsummaryrefslogtreecommitdiff
path: root/lib/CodeGen/CGCXXExpr.cpp
diff options
context:
space:
mode:
authorMike Stump <mrs@apple.com>2009-11-15 08:09:41 +0000
committerMike Stump <mrs@apple.com>2009-11-15 08:09:41 +0000
commitc2e84ae9a6d25cea3e583c768e576b4c981ec028 (patch)
tree29b48802ad5ceeaafef5a900a5a983cd95d72bb2 /lib/CodeGen/CGCXXExpr.cpp
parent593564ba94ff854b7a410a4ca17ad34a90c5b761 (diff)
Implement typeid for class types.
git-svn-id: https://llvm.org/svn/llvm-project/cfe/trunk@88843 91177308-0d34-0410-b5e6-96231b3b80d8
Diffstat (limited to 'lib/CodeGen/CGCXXExpr.cpp')
-rw-r--r--lib/CodeGen/CGCXXExpr.cpp36
1 files changed, 36 insertions, 0 deletions
diff --git a/lib/CodeGen/CGCXXExpr.cpp b/lib/CodeGen/CGCXXExpr.cpp
index abf8d16524..565685c6d0 100644
--- a/lib/CodeGen/CGCXXExpr.cpp
+++ b/lib/CodeGen/CGCXXExpr.cpp
@@ -334,3 +334,39 @@ void CodeGenFunction::EmitCXXDeleteExpr(const CXXDeleteExpr *E) {
EmitBlock(DeleteEnd);
}
+
+llvm::Value * CodeGenFunction::EmitCXXTypeidExpr(const CXXTypeidExpr *E) {
+ QualType Ty = E->getType();
+ const llvm::Type *LTy = ConvertType(Ty)->getPointerTo();
+ if (E->isTypeOperand()) {
+ QualType Ty = E->getTypeOperand();
+ if (const RecordType *RT = Ty->getAs<RecordType>()) {
+ const CXXRecordDecl *RD = cast<CXXRecordDecl>(RT->getDecl());
+ if (RD->isPolymorphic())
+ return Builder.CreateBitCast(CGM.GenerateRttiRef(RD), LTy);
+ return Builder.CreateBitCast(CGM.GenerateRtti(RD), LTy);
+ }
+ // FIXME: return the rtti for the non-class static type.
+ ErrorUnsupported(E, "typeid expression");
+ return 0;
+ }
+ Expr *subE = E->getExprOperand();
+ if (const RecordType *RT = Ty->getAs<RecordType>()) {
+ const CXXRecordDecl *RD = cast<CXXRecordDecl>(RT->getDecl());
+ if (RD->isPolymorphic()) {
+ // FIXME: if subE is an lvalue do
+ LValue Obj = EmitLValue(subE);
+ llvm::Value *This = Obj.getAddress();
+ // FIXME: need to do a 0 check here for *p on This
+ llvm::Value *V = Builder.CreateBitCast(This, LTy->getPointerTo()->getPointerTo());
+ V = Builder.CreateLoad(V, "vtable");
+ V = Builder.CreateConstInBoundsGEP1_64(V, -1ULL);
+ V = Builder.CreateLoad(V);
+ return V;
+ }
+ return CGM.GenerateRtti(RD);
+ }
+ // FIXME: return rtti for the non-class static type.
+ ErrorUnsupported(E, "typeid expression");
+ return 0;
+}