blob: 920b833b25d1ae06b155faf3fd4d5a901264c795 [file] [log] [blame]
Charles Davis4e786dd2010-05-25 19:52:27 +00001//===------- ItaniumCXXABI.cpp - Emit LLVM Code from ASTs for a Module ----===//
2//
3// The LLVM Compiler Infrastructure
4//
5// This file is distributed under the University of Illinois Open Source
6// License. See LICENSE.TXT for details.
7//
8//===----------------------------------------------------------------------===//
9//
10// This provides C++ code generation targetting the Itanium C++ ABI. The class
11// in this file generates structures that follow the Itanium C++ ABI, which is
12// documented at:
13// http://www.codesourcery.com/public/cxx-abi/abi.html
14// http://www.codesourcery.com/public/cxx-abi/abi-eh.html
John McCall86353412010-08-21 22:46:04 +000015//
16// It also supports the closely-related ARM ABI, documented at:
17// http://infocenter.arm.com/help/topic/com.arm.doc.ihi0041c/IHI0041C_cppabi.pdf
18//
Charles Davis4e786dd2010-05-25 19:52:27 +000019//===----------------------------------------------------------------------===//
20
21#include "CGCXXABI.h"
John McCall7a9aac22010-08-23 01:21:21 +000022#include "CGRecordLayout.h"
John McCall475999d2010-08-22 00:05:51 +000023#include "CodeGenFunction.h"
Charles Davis4e786dd2010-05-25 19:52:27 +000024#include "CodeGenModule.h"
25#include "Mangle.h"
John McCall475999d2010-08-22 00:05:51 +000026#include <clang/AST/Type.h>
John McCall7a9aac22010-08-23 01:21:21 +000027#include <llvm/Target/TargetData.h>
John McCall475999d2010-08-22 00:05:51 +000028#include <llvm/Value.h>
Charles Davis4e786dd2010-05-25 19:52:27 +000029
30using namespace clang;
John McCall475999d2010-08-22 00:05:51 +000031using namespace CodeGen;
Charles Davis4e786dd2010-05-25 19:52:27 +000032
33namespace {
Charles Davis53c59df2010-08-16 03:33:14 +000034class ItaniumCXXABI : public CodeGen::CGCXXABI {
John McCall7a9aac22010-08-23 01:21:21 +000035private:
36 const llvm::IntegerType *PtrDiffTy;
John McCall475999d2010-08-22 00:05:51 +000037protected:
Charles Davis4e786dd2010-05-25 19:52:27 +000038 CodeGen::MangleContext MangleCtx;
John McCalld9c6c0b2010-08-22 00:59:17 +000039 bool IsARM;
John McCall7a9aac22010-08-23 01:21:21 +000040
41 // It's a little silly for us to cache this.
42 const llvm::IntegerType *getPtrDiffTy() {
43 if (!PtrDiffTy) {
44 QualType T = CGM.getContext().getPointerDiffType();
45 const llvm::Type *Ty = CGM.getTypes().ConvertTypeRecursive(T);
46 PtrDiffTy = cast<llvm::IntegerType>(Ty);
47 }
48 return PtrDiffTy;
49 }
50
Charles Davis4e786dd2010-05-25 19:52:27 +000051public:
John McCalld9c6c0b2010-08-22 00:59:17 +000052 ItaniumCXXABI(CodeGen::CodeGenModule &CGM, bool IsARM = false) :
John McCall7a9aac22010-08-23 01:21:21 +000053 CGCXXABI(CGM), PtrDiffTy(0), MangleCtx(CGM.getContext(), CGM.getDiags()),
54 IsARM(IsARM) { }
Charles Davis4e786dd2010-05-25 19:52:27 +000055
56 CodeGen::MangleContext &getMangleContext() {
57 return MangleCtx;
58 }
John McCall475999d2010-08-22 00:05:51 +000059
John McCall614dbdc2010-08-22 21:01:12 +000060 bool isZeroInitializable(const MemberPointerType *MPT);
John McCall84fa5102010-08-22 04:16:24 +000061
John McCall7a9aac22010-08-23 01:21:21 +000062 const llvm::Type *ConvertMemberPointerType(const MemberPointerType *MPT);
63
John McCall475999d2010-08-22 00:05:51 +000064 llvm::Value *EmitLoadOfMemberFunctionPointer(CodeGenFunction &CGF,
65 llvm::Value *&This,
66 llvm::Value *MemFnPtr,
67 const MemberPointerType *MPT);
John McCalla8bbb822010-08-22 03:04:22 +000068
John McCall7a9aac22010-08-23 01:21:21 +000069 llvm::Value *EmitMemberPointerConversion(CodeGenFunction &CGF,
70 const CastExpr *E,
71 llvm::Value *Src);
John McCall84fa5102010-08-22 04:16:24 +000072
John McCall7a9aac22010-08-23 01:21:21 +000073 llvm::Constant *EmitMemberPointerConversion(llvm::Constant *C,
74 const CastExpr *E);
John McCall84fa5102010-08-22 04:16:24 +000075
John McCall7a9aac22010-08-23 01:21:21 +000076 llvm::Constant *EmitNullMemberPointer(const MemberPointerType *MPT);
John McCall84fa5102010-08-22 04:16:24 +000077
John McCall7a9aac22010-08-23 01:21:21 +000078 llvm::Constant *EmitMemberPointer(const CXXMethodDecl *MD);
79 llvm::Constant *EmitMemberPointer(const FieldDecl *FD);
John McCall1c456c82010-08-22 06:43:33 +000080
John McCall7a9aac22010-08-23 01:21:21 +000081 llvm::Value *EmitMemberPointerComparison(CodeGenFunction &CGF,
82 llvm::Value *L,
83 llvm::Value *R,
84 const MemberPointerType *MPT,
85 bool Inequality);
John McCall131d97d2010-08-22 08:30:07 +000086
John McCall7a9aac22010-08-23 01:21:21 +000087 llvm::Value *EmitMemberPointerIsNotNull(CodeGenFunction &CGF,
88 llvm::Value *Addr,
89 const MemberPointerType *MPT);
John McCall5d865c322010-08-31 07:33:07 +000090
91 void BuildConstructorSignature(const CXXConstructorDecl *Ctor,
92 CXXCtorType T,
93 CanQualType &ResTy,
94 llvm::SmallVectorImpl<CanQualType> &ArgTys);
95
96 void BuildDestructorSignature(const CXXDestructorDecl *Dtor,
97 CXXDtorType T,
98 CanQualType &ResTy,
99 llvm::SmallVectorImpl<CanQualType> &ArgTys);
100
101 void BuildInstanceFunctionParams(CodeGenFunction &CGF,
102 QualType &ResTy,
103 FunctionArgList &Params);
104
105 void EmitInstanceFunctionProlog(CodeGenFunction &CGF);
Charles Davis4e786dd2010-05-25 19:52:27 +0000106};
John McCall86353412010-08-21 22:46:04 +0000107
108class ARMCXXABI : public ItaniumCXXABI {
109public:
John McCalld9c6c0b2010-08-22 00:59:17 +0000110 ARMCXXABI(CodeGen::CodeGenModule &CGM) : ItaniumCXXABI(CGM, /*ARM*/ true) {}
John McCall5d865c322010-08-31 07:33:07 +0000111
112 void BuildConstructorSignature(const CXXConstructorDecl *Ctor,
113 CXXCtorType T,
114 CanQualType &ResTy,
115 llvm::SmallVectorImpl<CanQualType> &ArgTys);
116
117 void BuildDestructorSignature(const CXXDestructorDecl *Dtor,
118 CXXDtorType T,
119 CanQualType &ResTy,
120 llvm::SmallVectorImpl<CanQualType> &ArgTys);
121
122 void BuildInstanceFunctionParams(CodeGenFunction &CGF,
123 QualType &ResTy,
124 FunctionArgList &Params);
125
126 void EmitInstanceFunctionProlog(CodeGenFunction &CGF);
127
128 void EmitReturnFromThunk(CodeGenFunction &CGF, RValue RV, QualType ResTy);
129
130
131private:
132 /// \brief Returns true if the given instance method is one of the
133 /// kinds that the ARM ABI says returns 'this'.
134 static bool HasThisReturn(GlobalDecl GD) {
135 const CXXMethodDecl *MD = cast<CXXMethodDecl>(GD.getDecl());
136 return ((isa<CXXDestructorDecl>(MD) && GD.getDtorType() != Dtor_Deleting) ||
137 (isa<CXXConstructorDecl>(MD)));
138 }
John McCall86353412010-08-21 22:46:04 +0000139};
Charles Davis4e786dd2010-05-25 19:52:27 +0000140}
141
Charles Davis53c59df2010-08-16 03:33:14 +0000142CodeGen::CGCXXABI *CodeGen::CreateItaniumCXXABI(CodeGenModule &CGM) {
Charles Davis4e786dd2010-05-25 19:52:27 +0000143 return new ItaniumCXXABI(CGM);
144}
145
John McCall86353412010-08-21 22:46:04 +0000146CodeGen::CGCXXABI *CodeGen::CreateARMCXXABI(CodeGenModule &CGM) {
147 return new ARMCXXABI(CGM);
148}
149
John McCall7a9aac22010-08-23 01:21:21 +0000150const llvm::Type *
151ItaniumCXXABI::ConvertMemberPointerType(const MemberPointerType *MPT) {
152 if (MPT->isMemberDataPointer())
153 return getPtrDiffTy();
154 else
155 return llvm::StructType::get(CGM.getLLVMContext(),
156 getPtrDiffTy(), getPtrDiffTy(), NULL);
John McCall1c456c82010-08-22 06:43:33 +0000157}
158
John McCalld9c6c0b2010-08-22 00:59:17 +0000159/// In the Itanium and ARM ABIs, method pointers have the form:
160/// struct { ptrdiff_t ptr; ptrdiff_t adj; } memptr;
161///
162/// In the Itanium ABI:
163/// - method pointers are virtual if (memptr.ptr & 1) is nonzero
164/// - the this-adjustment is (memptr.adj)
165/// - the virtual offset is (memptr.ptr - 1)
166///
167/// In the ARM ABI:
168/// - method pointers are virtual if (memptr.adj & 1) is nonzero
169/// - the this-adjustment is (memptr.adj >> 1)
170/// - the virtual offset is (memptr.ptr)
171/// ARM uses 'adj' for the virtual flag because Thumb functions
172/// may be only single-byte aligned.
173///
174/// If the member is virtual, the adjusted 'this' pointer points
175/// to a vtable pointer from which the virtual offset is applied.
176///
177/// If the member is non-virtual, memptr.ptr is the address of
178/// the function to call.
John McCall475999d2010-08-22 00:05:51 +0000179llvm::Value *
180ItaniumCXXABI::EmitLoadOfMemberFunctionPointer(CodeGenFunction &CGF,
181 llvm::Value *&This,
182 llvm::Value *MemFnPtr,
183 const MemberPointerType *MPT) {
184 CGBuilderTy &Builder = CGF.Builder;
185
186 const FunctionProtoType *FPT =
187 MPT->getPointeeType()->getAs<FunctionProtoType>();
188 const CXXRecordDecl *RD =
189 cast<CXXRecordDecl>(MPT->getClass()->getAs<RecordType>()->getDecl());
190
191 const llvm::FunctionType *FTy =
192 CGM.getTypes().GetFunctionType(CGM.getTypes().getFunctionInfo(RD, FPT),
193 FPT->isVariadic());
194
John McCall7a9aac22010-08-23 01:21:21 +0000195 const llvm::IntegerType *ptrdiff = getPtrDiffTy();
John McCalld9c6c0b2010-08-22 00:59:17 +0000196 llvm::Constant *ptrdiff_1 = llvm::ConstantInt::get(ptrdiff, 1);
John McCall475999d2010-08-22 00:05:51 +0000197
John McCalld9c6c0b2010-08-22 00:59:17 +0000198 llvm::BasicBlock *FnVirtual = CGF.createBasicBlock("memptr.virtual");
199 llvm::BasicBlock *FnNonVirtual = CGF.createBasicBlock("memptr.nonvirtual");
200 llvm::BasicBlock *FnEnd = CGF.createBasicBlock("memptr.end");
201
John McCalla1dee5302010-08-22 10:59:02 +0000202 // Extract memptr.adj, which is in the second field.
203 llvm::Value *RawAdj = Builder.CreateExtractValue(MemFnPtr, 1, "memptr.adj");
John McCalld9c6c0b2010-08-22 00:59:17 +0000204
205 // Compute the true adjustment.
206 llvm::Value *Adj = RawAdj;
207 if (IsARM)
208 Adj = Builder.CreateAShr(Adj, ptrdiff_1, "memptr.adj.shifted");
John McCall475999d2010-08-22 00:05:51 +0000209
210 // Apply the adjustment and cast back to the original struct type
211 // for consistency.
John McCalld9c6c0b2010-08-22 00:59:17 +0000212 llvm::Value *Ptr = Builder.CreateBitCast(This, Builder.getInt8PtrTy());
213 Ptr = Builder.CreateInBoundsGEP(Ptr, Adj);
214 This = Builder.CreateBitCast(Ptr, This->getType(), "this.adjusted");
John McCall475999d2010-08-22 00:05:51 +0000215
216 // Load the function pointer.
John McCalla1dee5302010-08-22 10:59:02 +0000217 llvm::Value *FnAsInt = Builder.CreateExtractValue(MemFnPtr, 0, "memptr.ptr");
John McCall475999d2010-08-22 00:05:51 +0000218
219 // If the LSB in the function pointer is 1, the function pointer points to
220 // a virtual function.
John McCalld9c6c0b2010-08-22 00:59:17 +0000221 llvm::Value *IsVirtual;
222 if (IsARM)
223 IsVirtual = Builder.CreateAnd(RawAdj, ptrdiff_1);
224 else
225 IsVirtual = Builder.CreateAnd(FnAsInt, ptrdiff_1);
226 IsVirtual = Builder.CreateIsNotNull(IsVirtual, "memptr.isvirtual");
John McCall475999d2010-08-22 00:05:51 +0000227 Builder.CreateCondBr(IsVirtual, FnVirtual, FnNonVirtual);
228
229 // In the virtual path, the adjustment left 'This' pointing to the
230 // vtable of the correct base subobject. The "function pointer" is an
John McCalld9c6c0b2010-08-22 00:59:17 +0000231 // offset within the vtable (+1 for the virtual flag on non-ARM).
John McCall475999d2010-08-22 00:05:51 +0000232 CGF.EmitBlock(FnVirtual);
233
234 // Cast the adjusted this to a pointer to vtable pointer and load.
235 const llvm::Type *VTableTy = Builder.getInt8PtrTy();
236 llvm::Value *VTable = Builder.CreateBitCast(This, VTableTy->getPointerTo());
John McCalld9c6c0b2010-08-22 00:59:17 +0000237 VTable = Builder.CreateLoad(VTable, "memptr.vtable");
John McCall475999d2010-08-22 00:05:51 +0000238
239 // Apply the offset.
John McCalld9c6c0b2010-08-22 00:59:17 +0000240 llvm::Value *VTableOffset = FnAsInt;
241 if (!IsARM) VTableOffset = Builder.CreateSub(VTableOffset, ptrdiff_1);
242 VTable = Builder.CreateGEP(VTable, VTableOffset);
John McCall475999d2010-08-22 00:05:51 +0000243
244 // Load the virtual function to call.
245 VTable = Builder.CreateBitCast(VTable, FTy->getPointerTo()->getPointerTo());
John McCalld9c6c0b2010-08-22 00:59:17 +0000246 llvm::Value *VirtualFn = Builder.CreateLoad(VTable, "memptr.virtualfn");
John McCall475999d2010-08-22 00:05:51 +0000247 CGF.EmitBranch(FnEnd);
248
249 // In the non-virtual path, the function pointer is actually a
250 // function pointer.
251 CGF.EmitBlock(FnNonVirtual);
252 llvm::Value *NonVirtualFn =
John McCalld9c6c0b2010-08-22 00:59:17 +0000253 Builder.CreateIntToPtr(FnAsInt, FTy->getPointerTo(), "memptr.nonvirtualfn");
John McCall475999d2010-08-22 00:05:51 +0000254
255 // We're done.
256 CGF.EmitBlock(FnEnd);
257 llvm::PHINode *Callee = Builder.CreatePHI(FTy->getPointerTo());
258 Callee->reserveOperandSpace(2);
259 Callee->addIncoming(VirtualFn, FnVirtual);
260 Callee->addIncoming(NonVirtualFn, FnNonVirtual);
261 return Callee;
262}
John McCalla8bbb822010-08-22 03:04:22 +0000263
264/// Perform a derived-to-base or base-to-derived member pointer conversion.
John McCall7a9aac22010-08-23 01:21:21 +0000265///
266/// Obligatory offset/adjustment diagram:
267/// <-- offset --> <-- adjustment -->
268/// |--------------------------|----------------------|--------------------|
269/// ^Derived address point ^Base address point ^Member address point
270///
271/// So when converting a base member pointer to a derived member pointer,
272/// we add the offset to the adjustment because the address point has
273/// decreased; and conversely, when converting a derived MP to a base MP
274/// we subtract the offset from the adjustment because the address point
275/// has increased.
276///
277/// The standard forbids (at compile time) conversion to and from
278/// virtual bases, which is why we don't have to consider them here.
279///
280/// The standard forbids (at run time) casting a derived MP to a base
281/// MP when the derived MP does not point to a member of the base.
282/// This is why -1 is a reasonable choice for null data member
283/// pointers.
John McCalla1dee5302010-08-22 10:59:02 +0000284llvm::Value *
John McCall7a9aac22010-08-23 01:21:21 +0000285ItaniumCXXABI::EmitMemberPointerConversion(CodeGenFunction &CGF,
286 const CastExpr *E,
287 llvm::Value *Src) {
John McCalle3027922010-08-25 11:45:40 +0000288 assert(E->getCastKind() == CK_DerivedToBaseMemberPointer ||
289 E->getCastKind() == CK_BaseToDerivedMemberPointer);
John McCalla8bbb822010-08-22 03:04:22 +0000290
John McCalla1dee5302010-08-22 10:59:02 +0000291 if (isa<llvm::Constant>(Src))
John McCall7a9aac22010-08-23 01:21:21 +0000292 return EmitMemberPointerConversion(cast<llvm::Constant>(Src), E);
John McCalla1dee5302010-08-22 10:59:02 +0000293
John McCalla8bbb822010-08-22 03:04:22 +0000294 CGBuilderTy &Builder = CGF.Builder;
295
296 const MemberPointerType *SrcTy =
297 E->getSubExpr()->getType()->getAs<MemberPointerType>();
298 const MemberPointerType *DestTy = E->getType()->getAs<MemberPointerType>();
299
300 const CXXRecordDecl *SrcDecl = SrcTy->getClass()->getAsCXXRecordDecl();
301 const CXXRecordDecl *DestDecl = DestTy->getClass()->getAsCXXRecordDecl();
302
John McCalla8bbb822010-08-22 03:04:22 +0000303 bool DerivedToBase =
John McCalle3027922010-08-25 11:45:40 +0000304 E->getCastKind() == CK_DerivedToBaseMemberPointer;
John McCalla8bbb822010-08-22 03:04:22 +0000305
306 const CXXRecordDecl *BaseDecl, *DerivedDecl;
307 if (DerivedToBase)
308 DerivedDecl = SrcDecl, BaseDecl = DestDecl;
309 else
310 BaseDecl = SrcDecl, DerivedDecl = DestDecl;
311
John McCalla1dee5302010-08-22 10:59:02 +0000312 llvm::Constant *Adj =
313 CGF.CGM.GetNonVirtualBaseClassOffset(DerivedDecl,
314 E->path_begin(),
315 E->path_end());
316 if (!Adj) return Src;
John McCall1c456c82010-08-22 06:43:33 +0000317
John McCall7a9aac22010-08-23 01:21:21 +0000318 // For member data pointers, this is just a matter of adding the
319 // offset if the source is non-null.
320 if (SrcTy->isMemberDataPointer()) {
321 llvm::Value *Dst;
322 if (DerivedToBase)
323 Dst = Builder.CreateNSWSub(Src, Adj, "adj");
324 else
325 Dst = Builder.CreateNSWAdd(Src, Adj, "adj");
326
327 // Null check.
328 llvm::Value *Null = llvm::Constant::getAllOnesValue(Src->getType());
329 llvm::Value *IsNull = Builder.CreateICmpEQ(Src, Null, "memptr.isnull");
330 return Builder.CreateSelect(IsNull, Src, Dst);
331 }
332
John McCalla1dee5302010-08-22 10:59:02 +0000333 // The this-adjustment is left-shifted by 1 on ARM.
334 if (IsARM) {
335 uint64_t Offset = cast<llvm::ConstantInt>(Adj)->getZExtValue();
336 Offset <<= 1;
337 Adj = llvm::ConstantInt::get(Adj->getType(), Offset);
338 }
339
John McCallc29eb8a2010-08-22 11:04:31 +0000340 llvm::Value *SrcAdj = Builder.CreateExtractValue(Src, 1, "src.adj");
John McCalla1dee5302010-08-22 10:59:02 +0000341 llvm::Value *DstAdj;
342 if (DerivedToBase)
John McCall7a9aac22010-08-23 01:21:21 +0000343 DstAdj = Builder.CreateNSWSub(SrcAdj, Adj, "adj");
John McCalla1dee5302010-08-22 10:59:02 +0000344 else
John McCall7a9aac22010-08-23 01:21:21 +0000345 DstAdj = Builder.CreateNSWAdd(SrcAdj, Adj, "adj");
John McCalla1dee5302010-08-22 10:59:02 +0000346
John McCallc29eb8a2010-08-22 11:04:31 +0000347 return Builder.CreateInsertValue(Src, DstAdj, 1);
John McCalla8bbb822010-08-22 03:04:22 +0000348}
John McCall84fa5102010-08-22 04:16:24 +0000349
350llvm::Constant *
John McCall7a9aac22010-08-23 01:21:21 +0000351ItaniumCXXABI::EmitMemberPointerConversion(llvm::Constant *C,
352 const CastExpr *E) {
John McCall84fa5102010-08-22 04:16:24 +0000353 const MemberPointerType *SrcTy =
354 E->getSubExpr()->getType()->getAs<MemberPointerType>();
355 const MemberPointerType *DestTy =
356 E->getType()->getAs<MemberPointerType>();
357
358 bool DerivedToBase =
John McCalle3027922010-08-25 11:45:40 +0000359 E->getCastKind() == CK_DerivedToBaseMemberPointer;
John McCall84fa5102010-08-22 04:16:24 +0000360
361 const CXXRecordDecl *DerivedDecl;
362 if (DerivedToBase)
363 DerivedDecl = SrcTy->getClass()->getAsCXXRecordDecl();
364 else
365 DerivedDecl = DestTy->getClass()->getAsCXXRecordDecl();
366
367 // Calculate the offset to the base class.
368 llvm::Constant *Offset =
369 CGM.GetNonVirtualBaseClassOffset(DerivedDecl,
370 E->path_begin(),
371 E->path_end());
372 // If there's no offset, we're done.
373 if (!Offset) return C;
374
John McCall7a9aac22010-08-23 01:21:21 +0000375 // If the source is a member data pointer, we have to do a null
376 // check and then add the offset. In the common case, we can fold
377 // away the offset.
378 if (SrcTy->isMemberDataPointer()) {
379 assert(C->getType() == getPtrDiffTy());
380
381 // If it's a constant int, just create a new constant int.
382 if (llvm::ConstantInt *CI = dyn_cast<llvm::ConstantInt>(C)) {
383 int64_t Src = CI->getSExtValue();
384
385 // Null converts to null.
386 if (Src == -1) return CI;
387
388 // Otherwise, just add the offset.
389 int64_t OffsetV = cast<llvm::ConstantInt>(Offset)->getSExtValue();
390 int64_t Dst = (DerivedToBase ? Src - OffsetV : Src + OffsetV);
391 return llvm::ConstantInt::get(CI->getType(), Dst, /*signed*/ true);
392 }
393
394 // Otherwise, we have to form a constant select expression.
395 llvm::Constant *Null = llvm::Constant::getAllOnesValue(C->getType());
396
397 llvm::Constant *IsNull =
398 llvm::ConstantExpr::getICmp(llvm::ICmpInst::ICMP_EQ, C, Null);
399
400 llvm::Constant *Dst;
401 if (DerivedToBase)
402 Dst = llvm::ConstantExpr::getNSWSub(C, Offset);
403 else
404 Dst = llvm::ConstantExpr::getNSWAdd(C, Offset);
405
406 return llvm::ConstantExpr::getSelect(IsNull, Null, Dst);
407 }
408
John McCall1c456c82010-08-22 06:43:33 +0000409 // The this-adjustment is left-shifted by 1 on ARM.
410 if (IsARM) {
John McCall7a9aac22010-08-23 01:21:21 +0000411 int64_t OffsetV = cast<llvm::ConstantInt>(Offset)->getSExtValue();
John McCall1c456c82010-08-22 06:43:33 +0000412 OffsetV <<= 1;
413 Offset = llvm::ConstantInt::get(Offset->getType(), OffsetV);
414 }
415
John McCall84fa5102010-08-22 04:16:24 +0000416 llvm::ConstantStruct *CS = cast<llvm::ConstantStruct>(C);
417
John McCall7a9aac22010-08-23 01:21:21 +0000418 llvm::Constant *Values[2] = { CS->getOperand(0), 0 };
419 if (DerivedToBase)
420 Values[1] = llvm::ConstantExpr::getSub(CS->getOperand(1), Offset);
421 else
422 Values[1] = llvm::ConstantExpr::getAdd(CS->getOperand(1), Offset);
423
John McCall84fa5102010-08-22 04:16:24 +0000424 return llvm::ConstantStruct::get(CGM.getLLVMContext(), Values, 2,
425 /*Packed=*/false);
426}
427
428
John McCall84fa5102010-08-22 04:16:24 +0000429llvm::Constant *
John McCall7a9aac22010-08-23 01:21:21 +0000430ItaniumCXXABI::EmitNullMemberPointer(const MemberPointerType *MPT) {
431 const llvm::Type *ptrdiff_t = getPtrDiffTy();
432
433 // Itanium C++ ABI 2.3:
434 // A NULL pointer is represented as -1.
435 if (MPT->isMemberDataPointer())
436 return llvm::ConstantInt::get(ptrdiff_t, -1ULL, /*isSigned=*/true);
John McCalla1dee5302010-08-22 10:59:02 +0000437
438 llvm::Constant *Zero = llvm::ConstantInt::get(ptrdiff_t, 0);
439 llvm::Constant *Values[2] = { Zero, Zero };
440 return llvm::ConstantStruct::get(CGM.getLLVMContext(), Values, 2,
441 /*Packed=*/false);
John McCall84fa5102010-08-22 04:16:24 +0000442}
443
John McCall7a9aac22010-08-23 01:21:21 +0000444llvm::Constant *ItaniumCXXABI::EmitMemberPointer(const FieldDecl *FD) {
445 // Itanium C++ ABI 2.3:
446 // A pointer to data member is an offset from the base address of
447 // the class object containing it, represented as a ptrdiff_t
448
449 QualType ClassType = CGM.getContext().getTypeDeclType(FD->getParent());
450 const llvm::StructType *ClassLTy =
451 cast<llvm::StructType>(CGM.getTypes().ConvertType(ClassType));
452
453 const CGRecordLayout &RL = CGM.getTypes().getCGRecordLayout(FD->getParent());
454 unsigned FieldNo = RL.getLLVMFieldNo(FD);
455 uint64_t Offset =
456 CGM.getTargetData().getStructLayout(ClassLTy)->getElementOffset(FieldNo);
457
458 return llvm::ConstantInt::get(getPtrDiffTy(), Offset);
459}
460
461llvm::Constant *ItaniumCXXABI::EmitMemberPointer(const CXXMethodDecl *MD) {
John McCalla1dee5302010-08-22 10:59:02 +0000462 assert(MD->isInstance() && "Member function must not be static!");
463 MD = MD->getCanonicalDecl();
464
465 CodeGenTypes &Types = CGM.getTypes();
John McCall7a9aac22010-08-23 01:21:21 +0000466 const llvm::Type *ptrdiff_t = getPtrDiffTy();
John McCalla1dee5302010-08-22 10:59:02 +0000467
468 // Get the function pointer (or index if this is a virtual function).
469 llvm::Constant *MemPtr[2];
470 if (MD->isVirtual()) {
471 uint64_t Index = CGM.getVTables().getMethodVTableIndex(MD);
472
473 // FIXME: We shouldn't use / 8 here.
474 uint64_t PointerWidthInBytes =
475 CGM.getContext().Target.getPointerWidth(0) / 8;
476 uint64_t VTableOffset = (Index * PointerWidthInBytes);
477
478 if (IsARM) {
479 // ARM C++ ABI 3.2.1:
480 // This ABI specifies that adj contains twice the this
481 // adjustment, plus 1 if the member function is virtual. The
482 // least significant bit of adj then makes exactly the same
483 // discrimination as the least significant bit of ptr does for
484 // Itanium.
485 MemPtr[0] = llvm::ConstantInt::get(ptrdiff_t, VTableOffset);
486 MemPtr[1] = llvm::ConstantInt::get(ptrdiff_t, 1);
487 } else {
488 // Itanium C++ ABI 2.3:
489 // For a virtual function, [the pointer field] is 1 plus the
490 // virtual table offset (in bytes) of the function,
491 // represented as a ptrdiff_t.
492 MemPtr[0] = llvm::ConstantInt::get(ptrdiff_t, VTableOffset + 1);
493 MemPtr[1] = llvm::ConstantInt::get(ptrdiff_t, 0);
494 }
495 } else {
496 const FunctionProtoType *FPT = MD->getType()->getAs<FunctionProtoType>();
497 const llvm::Type *Ty;
498 // Check whether the function has a computable LLVM signature.
499 if (!CodeGenTypes::VerifyFuncTypeComplete(FPT)) {
500 // The function has a computable LLVM signature; use the correct type.
501 Ty = Types.GetFunctionType(Types.getFunctionInfo(MD), FPT->isVariadic());
502 } else {
503 // Use an arbitrary non-function type to tell GetAddrOfFunction that the
504 // function type is incomplete.
505 Ty = ptrdiff_t;
506 }
507
508 llvm::Constant *Addr = CGM.GetAddrOfFunction(MD, Ty);
509 MemPtr[0] = llvm::ConstantExpr::getPtrToInt(Addr, ptrdiff_t);
510 MemPtr[1] = llvm::ConstantInt::get(ptrdiff_t, 0);
511 }
John McCall1c456c82010-08-22 06:43:33 +0000512
513 return llvm::ConstantStruct::get(CGM.getLLVMContext(),
John McCalla1dee5302010-08-22 10:59:02 +0000514 MemPtr, 2, /*Packed=*/false);
John McCall1c456c82010-08-22 06:43:33 +0000515}
516
John McCall131d97d2010-08-22 08:30:07 +0000517/// The comparison algorithm is pretty easy: the member pointers are
518/// the same if they're either bitwise identical *or* both null.
519///
520/// ARM is different here only because null-ness is more complicated.
521llvm::Value *
John McCall7a9aac22010-08-23 01:21:21 +0000522ItaniumCXXABI::EmitMemberPointerComparison(CodeGenFunction &CGF,
523 llvm::Value *L,
524 llvm::Value *R,
525 const MemberPointerType *MPT,
526 bool Inequality) {
John McCall131d97d2010-08-22 08:30:07 +0000527 CGBuilderTy &Builder = CGF.Builder;
528
John McCall131d97d2010-08-22 08:30:07 +0000529 llvm::ICmpInst::Predicate Eq;
530 llvm::Instruction::BinaryOps And, Or;
531 if (Inequality) {
532 Eq = llvm::ICmpInst::ICMP_NE;
533 And = llvm::Instruction::Or;
534 Or = llvm::Instruction::And;
535 } else {
536 Eq = llvm::ICmpInst::ICMP_EQ;
537 And = llvm::Instruction::And;
538 Or = llvm::Instruction::Or;
539 }
540
John McCall7a9aac22010-08-23 01:21:21 +0000541 // Member data pointers are easy because there's a unique null
542 // value, so it just comes down to bitwise equality.
543 if (MPT->isMemberDataPointer())
544 return Builder.CreateICmp(Eq, L, R);
545
546 // For member function pointers, the tautologies are more complex.
547 // The Itanium tautology is:
John McCall61a14882010-08-23 06:56:36 +0000548 // (L == R) <==> (L.ptr == R.ptr && (L.ptr == 0 || L.adj == R.adj))
John McCall7a9aac22010-08-23 01:21:21 +0000549 // The ARM tautology is:
John McCall61a14882010-08-23 06:56:36 +0000550 // (L == R) <==> (L.ptr == R.ptr &&
551 // (L.adj == R.adj ||
552 // (L.ptr == 0 && ((L.adj|R.adj) & 1) == 0)))
John McCall7a9aac22010-08-23 01:21:21 +0000553 // The inequality tautologies have exactly the same structure, except
554 // applying De Morgan's laws.
555
556 llvm::Value *LPtr = Builder.CreateExtractValue(L, 0, "lhs.memptr.ptr");
557 llvm::Value *RPtr = Builder.CreateExtractValue(R, 0, "rhs.memptr.ptr");
558
John McCall131d97d2010-08-22 08:30:07 +0000559 // This condition tests whether L.ptr == R.ptr. This must always be
560 // true for equality to hold.
561 llvm::Value *PtrEq = Builder.CreateICmp(Eq, LPtr, RPtr, "cmp.ptr");
562
563 // This condition, together with the assumption that L.ptr == R.ptr,
564 // tests whether the pointers are both null. ARM imposes an extra
565 // condition.
566 llvm::Value *Zero = llvm::Constant::getNullValue(LPtr->getType());
567 llvm::Value *EqZero = Builder.CreateICmp(Eq, LPtr, Zero, "cmp.ptr.null");
568
569 // This condition tests whether L.adj == R.adj. If this isn't
570 // true, the pointers are unequal unless they're both null.
John McCalla1dee5302010-08-22 10:59:02 +0000571 llvm::Value *LAdj = Builder.CreateExtractValue(L, 1, "lhs.memptr.adj");
572 llvm::Value *RAdj = Builder.CreateExtractValue(R, 1, "rhs.memptr.adj");
John McCall131d97d2010-08-22 08:30:07 +0000573 llvm::Value *AdjEq = Builder.CreateICmp(Eq, LAdj, RAdj, "cmp.adj");
574
575 // Null member function pointers on ARM clear the low bit of Adj,
576 // so the zero condition has to check that neither low bit is set.
577 if (IsARM) {
578 llvm::Value *One = llvm::ConstantInt::get(LPtr->getType(), 1);
579
580 // Compute (l.adj | r.adj) & 1 and test it against zero.
581 llvm::Value *OrAdj = Builder.CreateOr(LAdj, RAdj, "or.adj");
582 llvm::Value *OrAdjAnd1 = Builder.CreateAnd(OrAdj, One);
583 llvm::Value *OrAdjAnd1EqZero = Builder.CreateICmp(Eq, OrAdjAnd1, Zero,
584 "cmp.or.adj");
585 EqZero = Builder.CreateBinOp(And, EqZero, OrAdjAnd1EqZero);
586 }
587
588 // Tie together all our conditions.
589 llvm::Value *Result = Builder.CreateBinOp(Or, EqZero, AdjEq);
590 Result = Builder.CreateBinOp(And, PtrEq, Result,
591 Inequality ? "memptr.ne" : "memptr.eq");
592 return Result;
593}
594
595llvm::Value *
John McCall7a9aac22010-08-23 01:21:21 +0000596ItaniumCXXABI::EmitMemberPointerIsNotNull(CodeGenFunction &CGF,
597 llvm::Value *MemPtr,
598 const MemberPointerType *MPT) {
John McCall131d97d2010-08-22 08:30:07 +0000599 CGBuilderTy &Builder = CGF.Builder;
John McCall7a9aac22010-08-23 01:21:21 +0000600
601 /// For member data pointers, this is just a check against -1.
602 if (MPT->isMemberDataPointer()) {
603 assert(MemPtr->getType() == getPtrDiffTy());
604 llvm::Value *NegativeOne =
605 llvm::Constant::getAllOnesValue(MemPtr->getType());
606 return Builder.CreateICmpNE(MemPtr, NegativeOne, "memptr.tobool");
607 }
John McCall131d97d2010-08-22 08:30:07 +0000608
609 // In Itanium, a member function pointer is null if 'ptr' is null.
John McCalla1dee5302010-08-22 10:59:02 +0000610 llvm::Value *Ptr = Builder.CreateExtractValue(MemPtr, 0, "memptr.ptr");
John McCall131d97d2010-08-22 08:30:07 +0000611
612 llvm::Constant *Zero = llvm::ConstantInt::get(Ptr->getType(), 0);
613 llvm::Value *Result = Builder.CreateICmpNE(Ptr, Zero, "memptr.tobool");
614
615 // In ARM, it's that, plus the low bit of 'adj' must be zero.
616 if (IsARM) {
617 llvm::Constant *One = llvm::ConstantInt::get(Ptr->getType(), 1);
John McCalla1dee5302010-08-22 10:59:02 +0000618 llvm::Value *Adj = Builder.CreateExtractValue(MemPtr, 1, "memptr.adj");
John McCall131d97d2010-08-22 08:30:07 +0000619 llvm::Value *VirtualBit = Builder.CreateAnd(Adj, One, "memptr.virtualbit");
620 llvm::Value *IsNotVirtual = Builder.CreateICmpEQ(VirtualBit, Zero,
621 "memptr.notvirtual");
622 Result = Builder.CreateAnd(Result, IsNotVirtual);
623 }
624
625 return Result;
626}
John McCall1c456c82010-08-22 06:43:33 +0000627
John McCall614dbdc2010-08-22 21:01:12 +0000628/// The Itanium ABI requires non-zero initialization only for data
629/// member pointers, for which '0' is a valid offset.
630bool ItaniumCXXABI::isZeroInitializable(const MemberPointerType *MPT) {
631 return MPT->getPointeeType()->isFunctionType();
John McCall84fa5102010-08-22 04:16:24 +0000632}
John McCall5d865c322010-08-31 07:33:07 +0000633
634/// The generic ABI passes 'this', plus a VTT if it's initializing a
635/// base subobject.
636void ItaniumCXXABI::BuildConstructorSignature(const CXXConstructorDecl *Ctor,
637 CXXCtorType Type,
638 CanQualType &ResTy,
639 llvm::SmallVectorImpl<CanQualType> &ArgTys) {
640 ASTContext &Context = CGM.getContext();
641
642 // 'this' is already there.
643
644 // Check if we need to add a VTT parameter (which has type void **).
645 if (Type == Ctor_Base && Ctor->getParent()->getNumVBases() != 0)
646 ArgTys.push_back(Context.getPointerType(Context.VoidPtrTy));
647}
648
649/// The ARM ABI does the same as the Itanium ABI, but returns 'this'.
650void ARMCXXABI::BuildConstructorSignature(const CXXConstructorDecl *Ctor,
651 CXXCtorType Type,
652 CanQualType &ResTy,
653 llvm::SmallVectorImpl<CanQualType> &ArgTys) {
654 ItaniumCXXABI::BuildConstructorSignature(Ctor, Type, ResTy, ArgTys);
655 ResTy = ArgTys[0];
656}
657
658/// The generic ABI passes 'this', plus a VTT if it's destroying a
659/// base subobject.
660void ItaniumCXXABI::BuildDestructorSignature(const CXXDestructorDecl *Dtor,
661 CXXDtorType Type,
662 CanQualType &ResTy,
663 llvm::SmallVectorImpl<CanQualType> &ArgTys) {
664 ASTContext &Context = CGM.getContext();
665
666 // 'this' is already there.
667
668 // Check if we need to add a VTT parameter (which has type void **).
669 if (Type == Dtor_Base && Dtor->getParent()->getNumVBases() != 0)
670 ArgTys.push_back(Context.getPointerType(Context.VoidPtrTy));
671}
672
673/// The ARM ABI does the same as the Itanium ABI, but returns 'this'
674/// for non-deleting destructors.
675void ARMCXXABI::BuildDestructorSignature(const CXXDestructorDecl *Dtor,
676 CXXDtorType Type,
677 CanQualType &ResTy,
678 llvm::SmallVectorImpl<CanQualType> &ArgTys) {
679 ItaniumCXXABI::BuildDestructorSignature(Dtor, Type, ResTy, ArgTys);
680
681 if (Type != Dtor_Deleting)
682 ResTy = ArgTys[0];
683}
684
685void ItaniumCXXABI::BuildInstanceFunctionParams(CodeGenFunction &CGF,
686 QualType &ResTy,
687 FunctionArgList &Params) {
688 /// Create the 'this' variable.
689 BuildThisParam(CGF, Params);
690
691 const CXXMethodDecl *MD = cast<CXXMethodDecl>(CGF.CurGD.getDecl());
692 assert(MD->isInstance());
693
694 // Check if we need a VTT parameter as well.
695 if (CodeGenVTables::needsVTTParameter(CGF.CurGD)) {
696 ASTContext &Context = CGF.getContext();
697
698 // FIXME: avoid the fake decl
699 QualType T = Context.getPointerType(Context.VoidPtrTy);
700 ImplicitParamDecl *VTTDecl
701 = ImplicitParamDecl::Create(Context, 0, MD->getLocation(),
702 &Context.Idents.get("vtt"), T);
703 Params.push_back(std::make_pair(VTTDecl, VTTDecl->getType()));
704 getVTTDecl(CGF) = VTTDecl;
705 }
706}
707
708void ARMCXXABI::BuildInstanceFunctionParams(CodeGenFunction &CGF,
709 QualType &ResTy,
710 FunctionArgList &Params) {
711 ItaniumCXXABI::BuildInstanceFunctionParams(CGF, ResTy, Params);
712
713 // Return 'this' from certain constructors and destructors.
714 if (HasThisReturn(CGF.CurGD))
715 ResTy = Params[0].second;
716}
717
718void ItaniumCXXABI::EmitInstanceFunctionProlog(CodeGenFunction &CGF) {
719 /// Initialize the 'this' slot.
720 EmitThisParam(CGF);
721
722 /// Initialize the 'vtt' slot if needed.
723 if (getVTTDecl(CGF)) {
724 getVTTValue(CGF)
725 = CGF.Builder.CreateLoad(CGF.GetAddrOfLocalVar(getVTTDecl(CGF)),
726 "vtt");
727 }
728}
729
730void ARMCXXABI::EmitInstanceFunctionProlog(CodeGenFunction &CGF) {
731 ItaniumCXXABI::EmitInstanceFunctionProlog(CGF);
732
733 /// Initialize the return slot to 'this' at the start of the
734 /// function.
735 if (HasThisReturn(CGF.CurGD))
736 CGF.Builder.CreateStore(CGF.LoadCXXThis(), CGF.ReturnValue);
737}
738
739void ARMCXXABI::EmitReturnFromThunk(CodeGenFunction &CGF,
740 RValue RV, QualType ResultType) {
741 if (!isa<CXXDestructorDecl>(CGF.CurGD.getDecl()))
742 return ItaniumCXXABI::EmitReturnFromThunk(CGF, RV, ResultType);
743
744 // Destructor thunks in the ARM ABI have indeterminate results.
745 const llvm::Type *T =
746 cast<llvm::PointerType>(CGF.ReturnValue->getType())->getElementType();
747 RValue Undef = RValue::get(llvm::UndefValue::get(T));
748 return ItaniumCXXABI::EmitReturnFromThunk(CGF, Undef, ResultType);
749}