blob: fcd9caa304208470fbc168bd6dca333a5bc88ee8 [file] [log] [blame]
Douglas Gregor96e578d2010-02-05 17:54:41 +00001//===--- ASTImporter.cpp - Importing ASTs from other Contexts ---*- C++ -*-===//
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 file defines the ASTImporter class which imports AST nodes from one
11// context into another context.
12//
13//===----------------------------------------------------------------------===//
14#include "clang/AST/ASTImporter.h"
15
16#include "clang/AST/ASTContext.h"
Douglas Gregor811663e2010-02-10 00:15:17 +000017#include "clang/AST/ASTDiagnostic.h"
Douglas Gregor5c73e912010-02-11 00:48:18 +000018#include "clang/AST/DeclCXX.h"
Douglas Gregor96e578d2010-02-05 17:54:41 +000019#include "clang/AST/DeclObjC.h"
Douglas Gregor3aed6cd2010-02-08 21:09:39 +000020#include "clang/AST/DeclVisitor.h"
Douglas Gregor7eeb5972010-02-11 19:21:55 +000021#include "clang/AST/StmtVisitor.h"
Douglas Gregor96e578d2010-02-05 17:54:41 +000022#include "clang/AST/TypeVisitor.h"
Douglas Gregor811663e2010-02-10 00:15:17 +000023#include "clang/Basic/FileManager.h"
24#include "clang/Basic/SourceManager.h"
25#include "llvm/Support/MemoryBuffer.h"
Douglas Gregor3996e242010-02-15 22:01:00 +000026#include <deque>
Douglas Gregor96e578d2010-02-05 17:54:41 +000027
28using namespace clang;
29
30namespace {
Douglas Gregor3aed6cd2010-02-08 21:09:39 +000031 class ASTNodeImporter : public TypeVisitor<ASTNodeImporter, QualType>,
Douglas Gregor7eeb5972010-02-11 19:21:55 +000032 public DeclVisitor<ASTNodeImporter, Decl *>,
33 public StmtVisitor<ASTNodeImporter, Stmt *> {
Douglas Gregor96e578d2010-02-05 17:54:41 +000034 ASTImporter &Importer;
35
36 public:
37 explicit ASTNodeImporter(ASTImporter &Importer) : Importer(Importer) { }
38
39 using TypeVisitor<ASTNodeImporter, QualType>::Visit;
Douglas Gregor62d311f2010-02-09 19:21:46 +000040 using DeclVisitor<ASTNodeImporter, Decl *>::Visit;
Douglas Gregor7eeb5972010-02-11 19:21:55 +000041 using StmtVisitor<ASTNodeImporter, Stmt *>::Visit;
Douglas Gregor96e578d2010-02-05 17:54:41 +000042
43 // Importing types
Douglas Gregore4c83e42010-02-09 22:48:33 +000044 QualType VisitType(Type *T);
Douglas Gregor96e578d2010-02-05 17:54:41 +000045 QualType VisitBuiltinType(BuiltinType *T);
46 QualType VisitComplexType(ComplexType *T);
47 QualType VisitPointerType(PointerType *T);
48 QualType VisitBlockPointerType(BlockPointerType *T);
49 QualType VisitLValueReferenceType(LValueReferenceType *T);
50 QualType VisitRValueReferenceType(RValueReferenceType *T);
51 QualType VisitMemberPointerType(MemberPointerType *T);
52 QualType VisitConstantArrayType(ConstantArrayType *T);
53 QualType VisitIncompleteArrayType(IncompleteArrayType *T);
54 QualType VisitVariableArrayType(VariableArrayType *T);
55 // FIXME: DependentSizedArrayType
56 // FIXME: DependentSizedExtVectorType
57 QualType VisitVectorType(VectorType *T);
58 QualType VisitExtVectorType(ExtVectorType *T);
59 QualType VisitFunctionNoProtoType(FunctionNoProtoType *T);
60 QualType VisitFunctionProtoType(FunctionProtoType *T);
61 // FIXME: UnresolvedUsingType
62 QualType VisitTypedefType(TypedefType *T);
63 QualType VisitTypeOfExprType(TypeOfExprType *T);
64 // FIXME: DependentTypeOfExprType
65 QualType VisitTypeOfType(TypeOfType *T);
66 QualType VisitDecltypeType(DecltypeType *T);
67 // FIXME: DependentDecltypeType
68 QualType VisitRecordType(RecordType *T);
69 QualType VisitEnumType(EnumType *T);
Douglas Gregor96e578d2010-02-05 17:54:41 +000070 // FIXME: TemplateTypeParmType
71 // FIXME: SubstTemplateTypeParmType
72 // FIXME: TemplateSpecializationType
Abramo Bagnara6150c882010-05-11 21:36:43 +000073 QualType VisitElaboratedType(ElaboratedType *T);
Douglas Gregorc1d2d8a2010-03-31 17:34:00 +000074 // FIXME: DependentNameType
John McCallc392f372010-06-11 00:33:02 +000075 // FIXME: DependentTemplateSpecializationType
Douglas Gregor96e578d2010-02-05 17:54:41 +000076 QualType VisitObjCInterfaceType(ObjCInterfaceType *T);
John McCall8b07ec22010-05-15 11:32:37 +000077 QualType VisitObjCObjectType(ObjCObjectType *T);
Douglas Gregor96e578d2010-02-05 17:54:41 +000078 QualType VisitObjCObjectPointerType(ObjCObjectPointerType *T);
Douglas Gregor3aed6cd2010-02-08 21:09:39 +000079
80 // Importing declarations
Douglas Gregorbb7930c2010-02-10 19:54:31 +000081 bool ImportDeclParts(NamedDecl *D, DeclContext *&DC,
82 DeclContext *&LexicalDC, DeclarationName &Name,
Douglas Gregorf18a2c72010-02-21 18:26:36 +000083 SourceLocation &Loc);
Abramo Bagnarad6d2f182010-08-11 22:01:17 +000084 void ImportDeclarationNameLoc(const DeclarationNameInfo &From,
85 DeclarationNameInfo& To);
Douglas Gregor968d6332010-02-21 18:24:45 +000086 void ImportDeclContext(DeclContext *FromDC);
Douglas Gregor5c73e912010-02-11 00:48:18 +000087 bool IsStructuralMatch(RecordDecl *FromRecord, RecordDecl *ToRecord);
Douglas Gregor3996e242010-02-15 22:01:00 +000088 bool IsStructuralMatch(EnumDecl *FromEnum, EnumDecl *ToRecord);
Douglas Gregore4c83e42010-02-09 22:48:33 +000089 Decl *VisitDecl(Decl *D);
Douglas Gregorf18a2c72010-02-21 18:26:36 +000090 Decl *VisitNamespaceDecl(NamespaceDecl *D);
Douglas Gregor5fa74c32010-02-10 21:10:29 +000091 Decl *VisitTypedefDecl(TypedefDecl *D);
Douglas Gregor98c10182010-02-12 22:17:39 +000092 Decl *VisitEnumDecl(EnumDecl *D);
Douglas Gregor5c73e912010-02-11 00:48:18 +000093 Decl *VisitRecordDecl(RecordDecl *D);
Douglas Gregor98c10182010-02-12 22:17:39 +000094 Decl *VisitEnumConstantDecl(EnumConstantDecl *D);
Douglas Gregorbb7930c2010-02-10 19:54:31 +000095 Decl *VisitFunctionDecl(FunctionDecl *D);
Douglas Gregor00eace12010-02-21 18:29:16 +000096 Decl *VisitCXXMethodDecl(CXXMethodDecl *D);
97 Decl *VisitCXXConstructorDecl(CXXConstructorDecl *D);
98 Decl *VisitCXXDestructorDecl(CXXDestructorDecl *D);
99 Decl *VisitCXXConversionDecl(CXXConversionDecl *D);
Douglas Gregor5c73e912010-02-11 00:48:18 +0000100 Decl *VisitFieldDecl(FieldDecl *D);
Francois Pichet783dd6e2010-11-21 06:08:52 +0000101 Decl *VisitIndirectFieldDecl(IndirectFieldDecl *D);
Douglas Gregor7244b0b2010-02-17 00:34:30 +0000102 Decl *VisitObjCIvarDecl(ObjCIvarDecl *D);
Douglas Gregor3aed6cd2010-02-08 21:09:39 +0000103 Decl *VisitVarDecl(VarDecl *D);
Douglas Gregor8b228d72010-02-17 21:22:52 +0000104 Decl *VisitImplicitParamDecl(ImplicitParamDecl *D);
Douglas Gregorbb7930c2010-02-10 19:54:31 +0000105 Decl *VisitParmVarDecl(ParmVarDecl *D);
Douglas Gregor43f54792010-02-17 02:12:47 +0000106 Decl *VisitObjCMethodDecl(ObjCMethodDecl *D);
Douglas Gregor84c51c32010-02-18 01:47:50 +0000107 Decl *VisitObjCCategoryDecl(ObjCCategoryDecl *D);
Douglas Gregor98d156a2010-02-17 16:12:00 +0000108 Decl *VisitObjCProtocolDecl(ObjCProtocolDecl *D);
Douglas Gregor45635322010-02-16 01:20:57 +0000109 Decl *VisitObjCInterfaceDecl(ObjCInterfaceDecl *D);
Douglas Gregora11c4582010-02-17 18:02:10 +0000110 Decl *VisitObjCPropertyDecl(ObjCPropertyDecl *D);
Douglas Gregor8661a722010-02-18 02:12:22 +0000111 Decl *VisitObjCForwardProtocolDecl(ObjCForwardProtocolDecl *D);
Douglas Gregor06537af2010-02-18 02:04:09 +0000112 Decl *VisitObjCClassDecl(ObjCClassDecl *D);
113
Douglas Gregor7eeb5972010-02-11 19:21:55 +0000114 // Importing statements
115 Stmt *VisitStmt(Stmt *S);
116
117 // Importing expressions
118 Expr *VisitExpr(Expr *E);
Douglas Gregor52f820e2010-02-19 01:17:02 +0000119 Expr *VisitDeclRefExpr(DeclRefExpr *E);
Douglas Gregor7eeb5972010-02-11 19:21:55 +0000120 Expr *VisitIntegerLiteral(IntegerLiteral *E);
Douglas Gregor623421d2010-02-18 02:21:22 +0000121 Expr *VisitCharacterLiteral(CharacterLiteral *E);
Douglas Gregorc74247e2010-02-19 01:07:06 +0000122 Expr *VisitParenExpr(ParenExpr *E);
123 Expr *VisitUnaryOperator(UnaryOperator *E);
Douglas Gregord8552cd2010-02-19 01:24:23 +0000124 Expr *VisitSizeOfAlignOfExpr(SizeOfAlignOfExpr *E);
Douglas Gregorc74247e2010-02-19 01:07:06 +0000125 Expr *VisitBinaryOperator(BinaryOperator *E);
126 Expr *VisitCompoundAssignOperator(CompoundAssignOperator *E);
Douglas Gregor98c10182010-02-12 22:17:39 +0000127 Expr *VisitImplicitCastExpr(ImplicitCastExpr *E);
Douglas Gregor5481d322010-02-19 01:32:14 +0000128 Expr *VisitCStyleCastExpr(CStyleCastExpr *E);
Douglas Gregor96e578d2010-02-05 17:54:41 +0000129 };
130}
131
132//----------------------------------------------------------------------------
Douglas Gregor3996e242010-02-15 22:01:00 +0000133// Structural Equivalence
134//----------------------------------------------------------------------------
135
136namespace {
137 struct StructuralEquivalenceContext {
138 /// \brief AST contexts for which we are checking structural equivalence.
139 ASTContext &C1, &C2;
140
Douglas Gregor3996e242010-02-15 22:01:00 +0000141 /// \brief The set of "tentative" equivalences between two canonical
142 /// declarations, mapping from a declaration in the first context to the
143 /// declaration in the second context that we believe to be equivalent.
144 llvm::DenseMap<Decl *, Decl *> TentativeEquivalences;
145
146 /// \brief Queue of declarations in the first context whose equivalence
147 /// with a declaration in the second context still needs to be verified.
148 std::deque<Decl *> DeclsToCheck;
149
Douglas Gregorb4964f72010-02-15 23:54:17 +0000150 /// \brief Declaration (from, to) pairs that are known not to be equivalent
151 /// (which we have already complained about).
152 llvm::DenseSet<std::pair<Decl *, Decl *> > &NonEquivalentDecls;
153
Douglas Gregor3996e242010-02-15 22:01:00 +0000154 /// \brief Whether we're being strict about the spelling of types when
155 /// unifying two types.
156 bool StrictTypeSpelling;
157
158 StructuralEquivalenceContext(ASTContext &C1, ASTContext &C2,
Douglas Gregorb4964f72010-02-15 23:54:17 +0000159 llvm::DenseSet<std::pair<Decl *, Decl *> > &NonEquivalentDecls,
Douglas Gregor3996e242010-02-15 22:01:00 +0000160 bool StrictTypeSpelling = false)
Argyrios Kyrtzidisd0040642010-11-18 20:06:41 +0000161 : C1(C1), C2(C2), NonEquivalentDecls(NonEquivalentDecls),
Douglas Gregorb4964f72010-02-15 23:54:17 +0000162 StrictTypeSpelling(StrictTypeSpelling) { }
Douglas Gregor3996e242010-02-15 22:01:00 +0000163
164 /// \brief Determine whether the two declarations are structurally
165 /// equivalent.
166 bool IsStructurallyEquivalent(Decl *D1, Decl *D2);
167
168 /// \brief Determine whether the two types are structurally equivalent.
169 bool IsStructurallyEquivalent(QualType T1, QualType T2);
170
171 private:
172 /// \brief Finish checking all of the structural equivalences.
173 ///
174 /// \returns true if an error occurred, false otherwise.
175 bool Finish();
176
177 public:
178 DiagnosticBuilder Diag1(SourceLocation Loc, unsigned DiagID) {
Argyrios Kyrtzidisd0040642010-11-18 20:06:41 +0000179 return C1.getDiagnostics().Report(Loc, DiagID);
Douglas Gregor3996e242010-02-15 22:01:00 +0000180 }
181
182 DiagnosticBuilder Diag2(SourceLocation Loc, unsigned DiagID) {
Argyrios Kyrtzidisd0040642010-11-18 20:06:41 +0000183 return C2.getDiagnostics().Report(Loc, DiagID);
Douglas Gregor3996e242010-02-15 22:01:00 +0000184 }
185 };
186}
187
188static bool IsStructurallyEquivalent(StructuralEquivalenceContext &Context,
189 QualType T1, QualType T2);
190static bool IsStructurallyEquivalent(StructuralEquivalenceContext &Context,
191 Decl *D1, Decl *D2);
192
193/// \brief Determine if two APInts have the same value, after zero-extending
194/// one of them (if needed!) to ensure that the bit-widths match.
195static bool IsSameValue(const llvm::APInt &I1, const llvm::APInt &I2) {
196 if (I1.getBitWidth() == I2.getBitWidth())
197 return I1 == I2;
198
199 if (I1.getBitWidth() > I2.getBitWidth())
200 return I1 == llvm::APInt(I2).zext(I1.getBitWidth());
201
202 return llvm::APInt(I1).zext(I2.getBitWidth()) == I2;
203}
204
205/// \brief Determine if two APSInts have the same value, zero- or sign-extending
206/// as needed.
207static bool IsSameValue(const llvm::APSInt &I1, const llvm::APSInt &I2) {
208 if (I1.getBitWidth() == I2.getBitWidth() && I1.isSigned() == I2.isSigned())
209 return I1 == I2;
210
211 // Check for a bit-width mismatch.
212 if (I1.getBitWidth() > I2.getBitWidth())
213 return IsSameValue(I1, llvm::APSInt(I2).extend(I1.getBitWidth()));
214 else if (I2.getBitWidth() > I1.getBitWidth())
215 return IsSameValue(llvm::APSInt(I1).extend(I2.getBitWidth()), I2);
216
217 // We have a signedness mismatch. Turn the signed value into an unsigned
218 // value.
219 if (I1.isSigned()) {
220 if (I1.isNegative())
221 return false;
222
223 return llvm::APSInt(I1, true) == I2;
224 }
225
226 if (I2.isNegative())
227 return false;
228
229 return I1 == llvm::APSInt(I2, true);
230}
231
232/// \brief Determine structural equivalence of two expressions.
233static bool IsStructurallyEquivalent(StructuralEquivalenceContext &Context,
234 Expr *E1, Expr *E2) {
235 if (!E1 || !E2)
236 return E1 == E2;
237
238 // FIXME: Actually perform a structural comparison!
239 return true;
240}
241
242/// \brief Determine whether two identifiers are equivalent.
243static bool IsStructurallyEquivalent(const IdentifierInfo *Name1,
244 const IdentifierInfo *Name2) {
245 if (!Name1 || !Name2)
246 return Name1 == Name2;
247
248 return Name1->getName() == Name2->getName();
249}
250
251/// \brief Determine whether two nested-name-specifiers are equivalent.
252static bool IsStructurallyEquivalent(StructuralEquivalenceContext &Context,
253 NestedNameSpecifier *NNS1,
254 NestedNameSpecifier *NNS2) {
255 // FIXME: Implement!
256 return true;
257}
258
259/// \brief Determine whether two template arguments are equivalent.
260static bool IsStructurallyEquivalent(StructuralEquivalenceContext &Context,
261 const TemplateArgument &Arg1,
262 const TemplateArgument &Arg2) {
263 // FIXME: Implement!
264 return true;
265}
266
267/// \brief Determine structural equivalence for the common part of array
268/// types.
269static bool IsArrayStructurallyEquivalent(StructuralEquivalenceContext &Context,
270 const ArrayType *Array1,
271 const ArrayType *Array2) {
272 if (!IsStructurallyEquivalent(Context,
273 Array1->getElementType(),
274 Array2->getElementType()))
275 return false;
276 if (Array1->getSizeModifier() != Array2->getSizeModifier())
277 return false;
278 if (Array1->getIndexTypeQualifiers() != Array2->getIndexTypeQualifiers())
279 return false;
280
281 return true;
282}
283
284/// \brief Determine structural equivalence of two types.
285static bool IsStructurallyEquivalent(StructuralEquivalenceContext &Context,
286 QualType T1, QualType T2) {
287 if (T1.isNull() || T2.isNull())
288 return T1.isNull() && T2.isNull();
289
290 if (!Context.StrictTypeSpelling) {
291 // We aren't being strict about token-to-token equivalence of types,
292 // so map down to the canonical type.
293 T1 = Context.C1.getCanonicalType(T1);
294 T2 = Context.C2.getCanonicalType(T2);
295 }
296
297 if (T1.getQualifiers() != T2.getQualifiers())
298 return false;
299
Douglas Gregorb4964f72010-02-15 23:54:17 +0000300 Type::TypeClass TC = T1->getTypeClass();
Douglas Gregor3996e242010-02-15 22:01:00 +0000301
Douglas Gregorb4964f72010-02-15 23:54:17 +0000302 if (T1->getTypeClass() != T2->getTypeClass()) {
303 // Compare function types with prototypes vs. without prototypes as if
304 // both did not have prototypes.
305 if (T1->getTypeClass() == Type::FunctionProto &&
306 T2->getTypeClass() == Type::FunctionNoProto)
307 TC = Type::FunctionNoProto;
308 else if (T1->getTypeClass() == Type::FunctionNoProto &&
309 T2->getTypeClass() == Type::FunctionProto)
310 TC = Type::FunctionNoProto;
311 else
312 return false;
313 }
314
315 switch (TC) {
316 case Type::Builtin:
Douglas Gregor3996e242010-02-15 22:01:00 +0000317 // FIXME: Deal with Char_S/Char_U.
318 if (cast<BuiltinType>(T1)->getKind() != cast<BuiltinType>(T2)->getKind())
319 return false;
320 break;
321
322 case Type::Complex:
323 if (!IsStructurallyEquivalent(Context,
324 cast<ComplexType>(T1)->getElementType(),
325 cast<ComplexType>(T2)->getElementType()))
326 return false;
327 break;
328
329 case Type::Pointer:
330 if (!IsStructurallyEquivalent(Context,
331 cast<PointerType>(T1)->getPointeeType(),
332 cast<PointerType>(T2)->getPointeeType()))
333 return false;
334 break;
335
336 case Type::BlockPointer:
337 if (!IsStructurallyEquivalent(Context,
338 cast<BlockPointerType>(T1)->getPointeeType(),
339 cast<BlockPointerType>(T2)->getPointeeType()))
340 return false;
341 break;
342
343 case Type::LValueReference:
344 case Type::RValueReference: {
345 const ReferenceType *Ref1 = cast<ReferenceType>(T1);
346 const ReferenceType *Ref2 = cast<ReferenceType>(T2);
347 if (Ref1->isSpelledAsLValue() != Ref2->isSpelledAsLValue())
348 return false;
349 if (Ref1->isInnerRef() != Ref2->isInnerRef())
350 return false;
351 if (!IsStructurallyEquivalent(Context,
352 Ref1->getPointeeTypeAsWritten(),
353 Ref2->getPointeeTypeAsWritten()))
354 return false;
355 break;
356 }
357
358 case Type::MemberPointer: {
359 const MemberPointerType *MemPtr1 = cast<MemberPointerType>(T1);
360 const MemberPointerType *MemPtr2 = cast<MemberPointerType>(T2);
361 if (!IsStructurallyEquivalent(Context,
362 MemPtr1->getPointeeType(),
363 MemPtr2->getPointeeType()))
364 return false;
365 if (!IsStructurallyEquivalent(Context,
366 QualType(MemPtr1->getClass(), 0),
367 QualType(MemPtr2->getClass(), 0)))
368 return false;
369 break;
370 }
371
372 case Type::ConstantArray: {
373 const ConstantArrayType *Array1 = cast<ConstantArrayType>(T1);
374 const ConstantArrayType *Array2 = cast<ConstantArrayType>(T2);
375 if (!IsSameValue(Array1->getSize(), Array2->getSize()))
376 return false;
377
378 if (!IsArrayStructurallyEquivalent(Context, Array1, Array2))
379 return false;
380 break;
381 }
382
383 case Type::IncompleteArray:
384 if (!IsArrayStructurallyEquivalent(Context,
385 cast<ArrayType>(T1),
386 cast<ArrayType>(T2)))
387 return false;
388 break;
389
390 case Type::VariableArray: {
391 const VariableArrayType *Array1 = cast<VariableArrayType>(T1);
392 const VariableArrayType *Array2 = cast<VariableArrayType>(T2);
393 if (!IsStructurallyEquivalent(Context,
394 Array1->getSizeExpr(), Array2->getSizeExpr()))
395 return false;
396
397 if (!IsArrayStructurallyEquivalent(Context, Array1, Array2))
398 return false;
399
400 break;
401 }
402
403 case Type::DependentSizedArray: {
404 const DependentSizedArrayType *Array1 = cast<DependentSizedArrayType>(T1);
405 const DependentSizedArrayType *Array2 = cast<DependentSizedArrayType>(T2);
406 if (!IsStructurallyEquivalent(Context,
407 Array1->getSizeExpr(), Array2->getSizeExpr()))
408 return false;
409
410 if (!IsArrayStructurallyEquivalent(Context, Array1, Array2))
411 return false;
412
413 break;
414 }
415
416 case Type::DependentSizedExtVector: {
417 const DependentSizedExtVectorType *Vec1
418 = cast<DependentSizedExtVectorType>(T1);
419 const DependentSizedExtVectorType *Vec2
420 = cast<DependentSizedExtVectorType>(T2);
421 if (!IsStructurallyEquivalent(Context,
422 Vec1->getSizeExpr(), Vec2->getSizeExpr()))
423 return false;
424 if (!IsStructurallyEquivalent(Context,
425 Vec1->getElementType(),
426 Vec2->getElementType()))
427 return false;
428 break;
429 }
430
431 case Type::Vector:
432 case Type::ExtVector: {
433 const VectorType *Vec1 = cast<VectorType>(T1);
434 const VectorType *Vec2 = cast<VectorType>(T2);
435 if (!IsStructurallyEquivalent(Context,
436 Vec1->getElementType(),
437 Vec2->getElementType()))
438 return false;
439 if (Vec1->getNumElements() != Vec2->getNumElements())
440 return false;
Bob Wilsonaeb56442010-11-10 21:56:12 +0000441 if (Vec1->getVectorKind() != Vec2->getVectorKind())
Douglas Gregor3996e242010-02-15 22:01:00 +0000442 return false;
Douglas Gregor01cc4372010-02-19 01:36:36 +0000443 break;
Douglas Gregor3996e242010-02-15 22:01:00 +0000444 }
445
446 case Type::FunctionProto: {
447 const FunctionProtoType *Proto1 = cast<FunctionProtoType>(T1);
448 const FunctionProtoType *Proto2 = cast<FunctionProtoType>(T2);
449 if (Proto1->getNumArgs() != Proto2->getNumArgs())
450 return false;
451 for (unsigned I = 0, N = Proto1->getNumArgs(); I != N; ++I) {
452 if (!IsStructurallyEquivalent(Context,
453 Proto1->getArgType(I),
454 Proto2->getArgType(I)))
455 return false;
456 }
457 if (Proto1->isVariadic() != Proto2->isVariadic())
458 return false;
459 if (Proto1->hasExceptionSpec() != Proto2->hasExceptionSpec())
460 return false;
461 if (Proto1->hasAnyExceptionSpec() != Proto2->hasAnyExceptionSpec())
462 return false;
463 if (Proto1->getNumExceptions() != Proto2->getNumExceptions())
464 return false;
465 for (unsigned I = 0, N = Proto1->getNumExceptions(); I != N; ++I) {
466 if (!IsStructurallyEquivalent(Context,
467 Proto1->getExceptionType(I),
468 Proto2->getExceptionType(I)))
469 return false;
470 }
471 if (Proto1->getTypeQuals() != Proto2->getTypeQuals())
472 return false;
473
474 // Fall through to check the bits common with FunctionNoProtoType.
475 }
476
477 case Type::FunctionNoProto: {
478 const FunctionType *Function1 = cast<FunctionType>(T1);
479 const FunctionType *Function2 = cast<FunctionType>(T2);
480 if (!IsStructurallyEquivalent(Context,
481 Function1->getResultType(),
482 Function2->getResultType()))
483 return false;
Rafael Espindolac50c27c2010-03-30 20:24:48 +0000484 if (Function1->getExtInfo() != Function2->getExtInfo())
485 return false;
Douglas Gregor3996e242010-02-15 22:01:00 +0000486 break;
487 }
488
489 case Type::UnresolvedUsing:
490 if (!IsStructurallyEquivalent(Context,
491 cast<UnresolvedUsingType>(T1)->getDecl(),
492 cast<UnresolvedUsingType>(T2)->getDecl()))
493 return false;
494
495 break;
496
497 case Type::Typedef:
498 if (!IsStructurallyEquivalent(Context,
499 cast<TypedefType>(T1)->getDecl(),
500 cast<TypedefType>(T2)->getDecl()))
501 return false;
502 break;
503
504 case Type::TypeOfExpr:
505 if (!IsStructurallyEquivalent(Context,
506 cast<TypeOfExprType>(T1)->getUnderlyingExpr(),
507 cast<TypeOfExprType>(T2)->getUnderlyingExpr()))
508 return false;
509 break;
510
511 case Type::TypeOf:
512 if (!IsStructurallyEquivalent(Context,
513 cast<TypeOfType>(T1)->getUnderlyingType(),
514 cast<TypeOfType>(T2)->getUnderlyingType()))
515 return false;
516 break;
517
518 case Type::Decltype:
519 if (!IsStructurallyEquivalent(Context,
520 cast<DecltypeType>(T1)->getUnderlyingExpr(),
521 cast<DecltypeType>(T2)->getUnderlyingExpr()))
522 return false;
523 break;
524
525 case Type::Record:
526 case Type::Enum:
527 if (!IsStructurallyEquivalent(Context,
528 cast<TagType>(T1)->getDecl(),
529 cast<TagType>(T2)->getDecl()))
530 return false;
531 break;
Abramo Bagnara6150c882010-05-11 21:36:43 +0000532
Douglas Gregor3996e242010-02-15 22:01:00 +0000533 case Type::TemplateTypeParm: {
534 const TemplateTypeParmType *Parm1 = cast<TemplateTypeParmType>(T1);
535 const TemplateTypeParmType *Parm2 = cast<TemplateTypeParmType>(T2);
536 if (Parm1->getDepth() != Parm2->getDepth())
537 return false;
538 if (Parm1->getIndex() != Parm2->getIndex())
539 return false;
540 if (Parm1->isParameterPack() != Parm2->isParameterPack())
541 return false;
542
543 // Names of template type parameters are never significant.
544 break;
545 }
546
547 case Type::SubstTemplateTypeParm: {
548 const SubstTemplateTypeParmType *Subst1
549 = cast<SubstTemplateTypeParmType>(T1);
550 const SubstTemplateTypeParmType *Subst2
551 = cast<SubstTemplateTypeParmType>(T2);
552 if (!IsStructurallyEquivalent(Context,
553 QualType(Subst1->getReplacedParameter(), 0),
554 QualType(Subst2->getReplacedParameter(), 0)))
555 return false;
556 if (!IsStructurallyEquivalent(Context,
557 Subst1->getReplacementType(),
558 Subst2->getReplacementType()))
559 return false;
560 break;
561 }
562
563 case Type::TemplateSpecialization: {
564 const TemplateSpecializationType *Spec1
565 = cast<TemplateSpecializationType>(T1);
566 const TemplateSpecializationType *Spec2
567 = cast<TemplateSpecializationType>(T2);
568 if (!IsStructurallyEquivalent(Context,
569 Spec1->getTemplateName(),
570 Spec2->getTemplateName()))
571 return false;
572 if (Spec1->getNumArgs() != Spec2->getNumArgs())
573 return false;
574 for (unsigned I = 0, N = Spec1->getNumArgs(); I != N; ++I) {
575 if (!IsStructurallyEquivalent(Context,
576 Spec1->getArg(I), Spec2->getArg(I)))
577 return false;
578 }
579 break;
580 }
581
Abramo Bagnara6150c882010-05-11 21:36:43 +0000582 case Type::Elaborated: {
583 const ElaboratedType *Elab1 = cast<ElaboratedType>(T1);
584 const ElaboratedType *Elab2 = cast<ElaboratedType>(T2);
585 // CHECKME: what if a keyword is ETK_None or ETK_typename ?
586 if (Elab1->getKeyword() != Elab2->getKeyword())
587 return false;
Douglas Gregor3996e242010-02-15 22:01:00 +0000588 if (!IsStructurallyEquivalent(Context,
Abramo Bagnara6150c882010-05-11 21:36:43 +0000589 Elab1->getQualifier(),
590 Elab2->getQualifier()))
Douglas Gregor3996e242010-02-15 22:01:00 +0000591 return false;
592 if (!IsStructurallyEquivalent(Context,
Abramo Bagnara6150c882010-05-11 21:36:43 +0000593 Elab1->getNamedType(),
594 Elab2->getNamedType()))
Douglas Gregor3996e242010-02-15 22:01:00 +0000595 return false;
596 break;
597 }
598
John McCalle78aac42010-03-10 03:28:59 +0000599 case Type::InjectedClassName: {
600 const InjectedClassNameType *Inj1 = cast<InjectedClassNameType>(T1);
601 const InjectedClassNameType *Inj2 = cast<InjectedClassNameType>(T2);
602 if (!IsStructurallyEquivalent(Context,
John McCall2408e322010-04-27 00:57:59 +0000603 Inj1->getInjectedSpecializationType(),
604 Inj2->getInjectedSpecializationType()))
John McCalle78aac42010-03-10 03:28:59 +0000605 return false;
606 break;
607 }
608
Douglas Gregorc1d2d8a2010-03-31 17:34:00 +0000609 case Type::DependentName: {
610 const DependentNameType *Typename1 = cast<DependentNameType>(T1);
611 const DependentNameType *Typename2 = cast<DependentNameType>(T2);
Douglas Gregor3996e242010-02-15 22:01:00 +0000612 if (!IsStructurallyEquivalent(Context,
613 Typename1->getQualifier(),
614 Typename2->getQualifier()))
615 return false;
616 if (!IsStructurallyEquivalent(Typename1->getIdentifier(),
617 Typename2->getIdentifier()))
618 return false;
Douglas Gregor3996e242010-02-15 22:01:00 +0000619
620 break;
621 }
622
John McCallc392f372010-06-11 00:33:02 +0000623 case Type::DependentTemplateSpecialization: {
624 const DependentTemplateSpecializationType *Spec1 =
625 cast<DependentTemplateSpecializationType>(T1);
626 const DependentTemplateSpecializationType *Spec2 =
627 cast<DependentTemplateSpecializationType>(T2);
628 if (!IsStructurallyEquivalent(Context,
629 Spec1->getQualifier(),
630 Spec2->getQualifier()))
631 return false;
632 if (!IsStructurallyEquivalent(Spec1->getIdentifier(),
633 Spec2->getIdentifier()))
634 return false;
635 if (Spec1->getNumArgs() != Spec2->getNumArgs())
636 return false;
637 for (unsigned I = 0, N = Spec1->getNumArgs(); I != N; ++I) {
638 if (!IsStructurallyEquivalent(Context,
639 Spec1->getArg(I), Spec2->getArg(I)))
640 return false;
641 }
642 break;
643 }
644
Douglas Gregor3996e242010-02-15 22:01:00 +0000645 case Type::ObjCInterface: {
646 const ObjCInterfaceType *Iface1 = cast<ObjCInterfaceType>(T1);
647 const ObjCInterfaceType *Iface2 = cast<ObjCInterfaceType>(T2);
648 if (!IsStructurallyEquivalent(Context,
649 Iface1->getDecl(), Iface2->getDecl()))
650 return false;
John McCall8b07ec22010-05-15 11:32:37 +0000651 break;
652 }
653
654 case Type::ObjCObject: {
655 const ObjCObjectType *Obj1 = cast<ObjCObjectType>(T1);
656 const ObjCObjectType *Obj2 = cast<ObjCObjectType>(T2);
657 if (!IsStructurallyEquivalent(Context,
658 Obj1->getBaseType(),
659 Obj2->getBaseType()))
Douglas Gregor3996e242010-02-15 22:01:00 +0000660 return false;
John McCall8b07ec22010-05-15 11:32:37 +0000661 if (Obj1->getNumProtocols() != Obj2->getNumProtocols())
662 return false;
663 for (unsigned I = 0, N = Obj1->getNumProtocols(); I != N; ++I) {
Douglas Gregor3996e242010-02-15 22:01:00 +0000664 if (!IsStructurallyEquivalent(Context,
John McCall8b07ec22010-05-15 11:32:37 +0000665 Obj1->getProtocol(I),
666 Obj2->getProtocol(I)))
Douglas Gregor3996e242010-02-15 22:01:00 +0000667 return false;
668 }
669 break;
670 }
671
672 case Type::ObjCObjectPointer: {
673 const ObjCObjectPointerType *Ptr1 = cast<ObjCObjectPointerType>(T1);
674 const ObjCObjectPointerType *Ptr2 = cast<ObjCObjectPointerType>(T2);
675 if (!IsStructurallyEquivalent(Context,
676 Ptr1->getPointeeType(),
677 Ptr2->getPointeeType()))
678 return false;
Douglas Gregor3996e242010-02-15 22:01:00 +0000679 break;
680 }
681
682 } // end switch
683
684 return true;
685}
686
687/// \brief Determine structural equivalence of two records.
688static bool IsStructurallyEquivalent(StructuralEquivalenceContext &Context,
689 RecordDecl *D1, RecordDecl *D2) {
690 if (D1->isUnion() != D2->isUnion()) {
691 Context.Diag2(D2->getLocation(), diag::warn_odr_tag_type_inconsistent)
692 << Context.C2.getTypeDeclType(D2);
693 Context.Diag1(D1->getLocation(), diag::note_odr_tag_kind_here)
694 << D1->getDeclName() << (unsigned)D1->getTagKind();
695 return false;
696 }
697
Douglas Gregorb4964f72010-02-15 23:54:17 +0000698 // Compare the definitions of these two records. If either or both are
699 // incomplete, we assume that they are equivalent.
700 D1 = D1->getDefinition();
701 D2 = D2->getDefinition();
702 if (!D1 || !D2)
703 return true;
704
Douglas Gregor3996e242010-02-15 22:01:00 +0000705 if (CXXRecordDecl *D1CXX = dyn_cast<CXXRecordDecl>(D1)) {
706 if (CXXRecordDecl *D2CXX = dyn_cast<CXXRecordDecl>(D2)) {
707 if (D1CXX->getNumBases() != D2CXX->getNumBases()) {
708 Context.Diag2(D2->getLocation(), diag::warn_odr_tag_type_inconsistent)
709 << Context.C2.getTypeDeclType(D2);
710 Context.Diag2(D2->getLocation(), diag::note_odr_number_of_bases)
711 << D2CXX->getNumBases();
712 Context.Diag1(D1->getLocation(), diag::note_odr_number_of_bases)
713 << D1CXX->getNumBases();
714 return false;
715 }
716
717 // Check the base classes.
718 for (CXXRecordDecl::base_class_iterator Base1 = D1CXX->bases_begin(),
719 BaseEnd1 = D1CXX->bases_end(),
720 Base2 = D2CXX->bases_begin();
721 Base1 != BaseEnd1;
722 ++Base1, ++Base2) {
723 if (!IsStructurallyEquivalent(Context,
724 Base1->getType(), Base2->getType())) {
725 Context.Diag2(D2->getLocation(), diag::warn_odr_tag_type_inconsistent)
726 << Context.C2.getTypeDeclType(D2);
727 Context.Diag2(Base2->getSourceRange().getBegin(), diag::note_odr_base)
728 << Base2->getType()
729 << Base2->getSourceRange();
730 Context.Diag1(Base1->getSourceRange().getBegin(), diag::note_odr_base)
731 << Base1->getType()
732 << Base1->getSourceRange();
733 return false;
734 }
735
736 // Check virtual vs. non-virtual inheritance mismatch.
737 if (Base1->isVirtual() != Base2->isVirtual()) {
738 Context.Diag2(D2->getLocation(), diag::warn_odr_tag_type_inconsistent)
739 << Context.C2.getTypeDeclType(D2);
740 Context.Diag2(Base2->getSourceRange().getBegin(),
741 diag::note_odr_virtual_base)
742 << Base2->isVirtual() << Base2->getSourceRange();
743 Context.Diag1(Base1->getSourceRange().getBegin(), diag::note_odr_base)
744 << Base1->isVirtual()
745 << Base1->getSourceRange();
746 return false;
747 }
748 }
749 } else if (D1CXX->getNumBases() > 0) {
750 Context.Diag2(D2->getLocation(), diag::warn_odr_tag_type_inconsistent)
751 << Context.C2.getTypeDeclType(D2);
752 const CXXBaseSpecifier *Base1 = D1CXX->bases_begin();
753 Context.Diag1(Base1->getSourceRange().getBegin(), diag::note_odr_base)
754 << Base1->getType()
755 << Base1->getSourceRange();
756 Context.Diag2(D2->getLocation(), diag::note_odr_missing_base);
757 return false;
758 }
759 }
760
761 // Check the fields for consistency.
762 CXXRecordDecl::field_iterator Field2 = D2->field_begin(),
763 Field2End = D2->field_end();
764 for (CXXRecordDecl::field_iterator Field1 = D1->field_begin(),
765 Field1End = D1->field_end();
766 Field1 != Field1End;
767 ++Field1, ++Field2) {
768 if (Field2 == Field2End) {
769 Context.Diag2(D2->getLocation(), diag::warn_odr_tag_type_inconsistent)
770 << Context.C2.getTypeDeclType(D2);
771 Context.Diag1(Field1->getLocation(), diag::note_odr_field)
772 << Field1->getDeclName() << Field1->getType();
773 Context.Diag2(D2->getLocation(), diag::note_odr_missing_field);
774 return false;
775 }
776
777 if (!IsStructurallyEquivalent(Context,
778 Field1->getType(), Field2->getType())) {
779 Context.Diag2(D2->getLocation(), diag::warn_odr_tag_type_inconsistent)
780 << Context.C2.getTypeDeclType(D2);
781 Context.Diag2(Field2->getLocation(), diag::note_odr_field)
782 << Field2->getDeclName() << Field2->getType();
783 Context.Diag1(Field1->getLocation(), diag::note_odr_field)
784 << Field1->getDeclName() << Field1->getType();
785 return false;
786 }
787
788 if (Field1->isBitField() != Field2->isBitField()) {
789 Context.Diag2(D2->getLocation(), diag::warn_odr_tag_type_inconsistent)
790 << Context.C2.getTypeDeclType(D2);
791 if (Field1->isBitField()) {
792 llvm::APSInt Bits;
793 Field1->getBitWidth()->isIntegerConstantExpr(Bits, Context.C1);
794 Context.Diag1(Field1->getLocation(), diag::note_odr_bit_field)
795 << Field1->getDeclName() << Field1->getType()
796 << Bits.toString(10, false);
797 Context.Diag2(Field2->getLocation(), diag::note_odr_not_bit_field)
798 << Field2->getDeclName();
799 } else {
800 llvm::APSInt Bits;
801 Field2->getBitWidth()->isIntegerConstantExpr(Bits, Context.C2);
802 Context.Diag2(Field2->getLocation(), diag::note_odr_bit_field)
803 << Field2->getDeclName() << Field2->getType()
804 << Bits.toString(10, false);
805 Context.Diag1(Field1->getLocation(),
806 diag::note_odr_not_bit_field)
807 << Field1->getDeclName();
808 }
809 return false;
810 }
811
812 if (Field1->isBitField()) {
813 // Make sure that the bit-fields are the same length.
814 llvm::APSInt Bits1, Bits2;
815 if (!Field1->getBitWidth()->isIntegerConstantExpr(Bits1, Context.C1))
816 return false;
817 if (!Field2->getBitWidth()->isIntegerConstantExpr(Bits2, Context.C2))
818 return false;
819
820 if (!IsSameValue(Bits1, Bits2)) {
821 Context.Diag2(D2->getLocation(), diag::warn_odr_tag_type_inconsistent)
822 << Context.C2.getTypeDeclType(D2);
823 Context.Diag2(Field2->getLocation(), diag::note_odr_bit_field)
824 << Field2->getDeclName() << Field2->getType()
825 << Bits2.toString(10, false);
826 Context.Diag1(Field1->getLocation(), diag::note_odr_bit_field)
827 << Field1->getDeclName() << Field1->getType()
828 << Bits1.toString(10, false);
829 return false;
830 }
831 }
832 }
833
834 if (Field2 != Field2End) {
835 Context.Diag2(D2->getLocation(), diag::warn_odr_tag_type_inconsistent)
836 << Context.C2.getTypeDeclType(D2);
837 Context.Diag2(Field2->getLocation(), diag::note_odr_field)
838 << Field2->getDeclName() << Field2->getType();
839 Context.Diag1(D1->getLocation(), diag::note_odr_missing_field);
840 return false;
841 }
842
843 return true;
844}
845
846/// \brief Determine structural equivalence of two enums.
847static bool IsStructurallyEquivalent(StructuralEquivalenceContext &Context,
848 EnumDecl *D1, EnumDecl *D2) {
849 EnumDecl::enumerator_iterator EC2 = D2->enumerator_begin(),
850 EC2End = D2->enumerator_end();
851 for (EnumDecl::enumerator_iterator EC1 = D1->enumerator_begin(),
852 EC1End = D1->enumerator_end();
853 EC1 != EC1End; ++EC1, ++EC2) {
854 if (EC2 == EC2End) {
855 Context.Diag2(D2->getLocation(), diag::warn_odr_tag_type_inconsistent)
856 << Context.C2.getTypeDeclType(D2);
857 Context.Diag1(EC1->getLocation(), diag::note_odr_enumerator)
858 << EC1->getDeclName()
859 << EC1->getInitVal().toString(10);
860 Context.Diag2(D2->getLocation(), diag::note_odr_missing_enumerator);
861 return false;
862 }
863
864 llvm::APSInt Val1 = EC1->getInitVal();
865 llvm::APSInt Val2 = EC2->getInitVal();
866 if (!IsSameValue(Val1, Val2) ||
867 !IsStructurallyEquivalent(EC1->getIdentifier(), EC2->getIdentifier())) {
868 Context.Diag2(D2->getLocation(), diag::warn_odr_tag_type_inconsistent)
869 << Context.C2.getTypeDeclType(D2);
870 Context.Diag2(EC2->getLocation(), diag::note_odr_enumerator)
871 << EC2->getDeclName()
872 << EC2->getInitVal().toString(10);
873 Context.Diag1(EC1->getLocation(), diag::note_odr_enumerator)
874 << EC1->getDeclName()
875 << EC1->getInitVal().toString(10);
876 return false;
877 }
878 }
879
880 if (EC2 != EC2End) {
881 Context.Diag2(D2->getLocation(), diag::warn_odr_tag_type_inconsistent)
882 << Context.C2.getTypeDeclType(D2);
883 Context.Diag2(EC2->getLocation(), diag::note_odr_enumerator)
884 << EC2->getDeclName()
885 << EC2->getInitVal().toString(10);
886 Context.Diag1(D1->getLocation(), diag::note_odr_missing_enumerator);
887 return false;
888 }
889
890 return true;
891}
892
893/// \brief Determine structural equivalence of two declarations.
894static bool IsStructurallyEquivalent(StructuralEquivalenceContext &Context,
895 Decl *D1, Decl *D2) {
896 // FIXME: Check for known structural equivalences via a callback of some sort.
897
Douglas Gregorb4964f72010-02-15 23:54:17 +0000898 // Check whether we already know that these two declarations are not
899 // structurally equivalent.
900 if (Context.NonEquivalentDecls.count(std::make_pair(D1->getCanonicalDecl(),
901 D2->getCanonicalDecl())))
902 return false;
903
Douglas Gregor3996e242010-02-15 22:01:00 +0000904 // Determine whether we've already produced a tentative equivalence for D1.
905 Decl *&EquivToD1 = Context.TentativeEquivalences[D1->getCanonicalDecl()];
906 if (EquivToD1)
907 return EquivToD1 == D2->getCanonicalDecl();
908
909 // Produce a tentative equivalence D1 <-> D2, which will be checked later.
910 EquivToD1 = D2->getCanonicalDecl();
911 Context.DeclsToCheck.push_back(D1->getCanonicalDecl());
912 return true;
913}
914
915bool StructuralEquivalenceContext::IsStructurallyEquivalent(Decl *D1,
916 Decl *D2) {
917 if (!::IsStructurallyEquivalent(*this, D1, D2))
918 return false;
919
920 return !Finish();
921}
922
923bool StructuralEquivalenceContext::IsStructurallyEquivalent(QualType T1,
924 QualType T2) {
925 if (!::IsStructurallyEquivalent(*this, T1, T2))
926 return false;
927
928 return !Finish();
929}
930
931bool StructuralEquivalenceContext::Finish() {
932 while (!DeclsToCheck.empty()) {
933 // Check the next declaration.
934 Decl *D1 = DeclsToCheck.front();
935 DeclsToCheck.pop_front();
936
937 Decl *D2 = TentativeEquivalences[D1];
938 assert(D2 && "Unrecorded tentative equivalence?");
939
Douglas Gregorb4964f72010-02-15 23:54:17 +0000940 bool Equivalent = true;
941
Douglas Gregor3996e242010-02-15 22:01:00 +0000942 // FIXME: Switch on all declaration kinds. For now, we're just going to
943 // check the obvious ones.
944 if (RecordDecl *Record1 = dyn_cast<RecordDecl>(D1)) {
945 if (RecordDecl *Record2 = dyn_cast<RecordDecl>(D2)) {
946 // Check for equivalent structure names.
947 IdentifierInfo *Name1 = Record1->getIdentifier();
948 if (!Name1 && Record1->getTypedefForAnonDecl())
949 Name1 = Record1->getTypedefForAnonDecl()->getIdentifier();
950 IdentifierInfo *Name2 = Record2->getIdentifier();
951 if (!Name2 && Record2->getTypedefForAnonDecl())
952 Name2 = Record2->getTypedefForAnonDecl()->getIdentifier();
Douglas Gregorb4964f72010-02-15 23:54:17 +0000953 if (!::IsStructurallyEquivalent(Name1, Name2) ||
954 !::IsStructurallyEquivalent(*this, Record1, Record2))
955 Equivalent = false;
Douglas Gregor3996e242010-02-15 22:01:00 +0000956 } else {
957 // Record/non-record mismatch.
Douglas Gregorb4964f72010-02-15 23:54:17 +0000958 Equivalent = false;
Douglas Gregor3996e242010-02-15 22:01:00 +0000959 }
Douglas Gregorb4964f72010-02-15 23:54:17 +0000960 } else if (EnumDecl *Enum1 = dyn_cast<EnumDecl>(D1)) {
Douglas Gregor3996e242010-02-15 22:01:00 +0000961 if (EnumDecl *Enum2 = dyn_cast<EnumDecl>(D2)) {
962 // Check for equivalent enum names.
963 IdentifierInfo *Name1 = Enum1->getIdentifier();
964 if (!Name1 && Enum1->getTypedefForAnonDecl())
965 Name1 = Enum1->getTypedefForAnonDecl()->getIdentifier();
966 IdentifierInfo *Name2 = Enum2->getIdentifier();
967 if (!Name2 && Enum2->getTypedefForAnonDecl())
968 Name2 = Enum2->getTypedefForAnonDecl()->getIdentifier();
Douglas Gregorb4964f72010-02-15 23:54:17 +0000969 if (!::IsStructurallyEquivalent(Name1, Name2) ||
970 !::IsStructurallyEquivalent(*this, Enum1, Enum2))
971 Equivalent = false;
Douglas Gregor3996e242010-02-15 22:01:00 +0000972 } else {
973 // Enum/non-enum mismatch
Douglas Gregorb4964f72010-02-15 23:54:17 +0000974 Equivalent = false;
Douglas Gregor3996e242010-02-15 22:01:00 +0000975 }
Douglas Gregorb4964f72010-02-15 23:54:17 +0000976 } else if (TypedefDecl *Typedef1 = dyn_cast<TypedefDecl>(D1)) {
Douglas Gregor3996e242010-02-15 22:01:00 +0000977 if (TypedefDecl *Typedef2 = dyn_cast<TypedefDecl>(D2)) {
978 if (!::IsStructurallyEquivalent(Typedef1->getIdentifier(),
Douglas Gregorb4964f72010-02-15 23:54:17 +0000979 Typedef2->getIdentifier()) ||
980 !::IsStructurallyEquivalent(*this,
Douglas Gregor3996e242010-02-15 22:01:00 +0000981 Typedef1->getUnderlyingType(),
982 Typedef2->getUnderlyingType()))
Douglas Gregorb4964f72010-02-15 23:54:17 +0000983 Equivalent = false;
Douglas Gregor3996e242010-02-15 22:01:00 +0000984 } else {
985 // Typedef/non-typedef mismatch.
Douglas Gregorb4964f72010-02-15 23:54:17 +0000986 Equivalent = false;
Douglas Gregor3996e242010-02-15 22:01:00 +0000987 }
Douglas Gregor3996e242010-02-15 22:01:00 +0000988 }
Douglas Gregorb4964f72010-02-15 23:54:17 +0000989
990 if (!Equivalent) {
991 // Note that these two declarations are not equivalent (and we already
992 // know about it).
993 NonEquivalentDecls.insert(std::make_pair(D1->getCanonicalDecl(),
994 D2->getCanonicalDecl()));
995 return true;
996 }
Douglas Gregor3996e242010-02-15 22:01:00 +0000997 // FIXME: Check other declaration kinds!
998 }
999
1000 return false;
1001}
1002
1003//----------------------------------------------------------------------------
Douglas Gregor96e578d2010-02-05 17:54:41 +00001004// Import Types
1005//----------------------------------------------------------------------------
1006
Douglas Gregore4c83e42010-02-09 22:48:33 +00001007QualType ASTNodeImporter::VisitType(Type *T) {
1008 Importer.FromDiag(SourceLocation(), diag::err_unsupported_ast_node)
1009 << T->getTypeClassName();
1010 return QualType();
1011}
1012
Douglas Gregor96e578d2010-02-05 17:54:41 +00001013QualType ASTNodeImporter::VisitBuiltinType(BuiltinType *T) {
1014 switch (T->getKind()) {
1015 case BuiltinType::Void: return Importer.getToContext().VoidTy;
1016 case BuiltinType::Bool: return Importer.getToContext().BoolTy;
1017
1018 case BuiltinType::Char_U:
1019 // The context we're importing from has an unsigned 'char'. If we're
1020 // importing into a context with a signed 'char', translate to
1021 // 'unsigned char' instead.
1022 if (Importer.getToContext().getLangOptions().CharIsSigned)
1023 return Importer.getToContext().UnsignedCharTy;
1024
1025 return Importer.getToContext().CharTy;
1026
1027 case BuiltinType::UChar: return Importer.getToContext().UnsignedCharTy;
1028
1029 case BuiltinType::Char16:
1030 // FIXME: Make sure that the "to" context supports C++!
1031 return Importer.getToContext().Char16Ty;
1032
1033 case BuiltinType::Char32:
1034 // FIXME: Make sure that the "to" context supports C++!
1035 return Importer.getToContext().Char32Ty;
1036
1037 case BuiltinType::UShort: return Importer.getToContext().UnsignedShortTy;
1038 case BuiltinType::UInt: return Importer.getToContext().UnsignedIntTy;
1039 case BuiltinType::ULong: return Importer.getToContext().UnsignedLongTy;
1040 case BuiltinType::ULongLong:
1041 return Importer.getToContext().UnsignedLongLongTy;
1042 case BuiltinType::UInt128: return Importer.getToContext().UnsignedInt128Ty;
1043
1044 case BuiltinType::Char_S:
1045 // The context we're importing from has an unsigned 'char'. If we're
1046 // importing into a context with a signed 'char', translate to
1047 // 'unsigned char' instead.
1048 if (!Importer.getToContext().getLangOptions().CharIsSigned)
1049 return Importer.getToContext().SignedCharTy;
1050
1051 return Importer.getToContext().CharTy;
1052
1053 case BuiltinType::SChar: return Importer.getToContext().SignedCharTy;
1054 case BuiltinType::WChar:
1055 // FIXME: If not in C++, shall we translate to the C equivalent of
1056 // wchar_t?
1057 return Importer.getToContext().WCharTy;
1058
1059 case BuiltinType::Short : return Importer.getToContext().ShortTy;
1060 case BuiltinType::Int : return Importer.getToContext().IntTy;
1061 case BuiltinType::Long : return Importer.getToContext().LongTy;
1062 case BuiltinType::LongLong : return Importer.getToContext().LongLongTy;
1063 case BuiltinType::Int128 : return Importer.getToContext().Int128Ty;
1064 case BuiltinType::Float: return Importer.getToContext().FloatTy;
1065 case BuiltinType::Double: return Importer.getToContext().DoubleTy;
1066 case BuiltinType::LongDouble: return Importer.getToContext().LongDoubleTy;
1067
1068 case BuiltinType::NullPtr:
1069 // FIXME: Make sure that the "to" context supports C++0x!
1070 return Importer.getToContext().NullPtrTy;
1071
1072 case BuiltinType::Overload: return Importer.getToContext().OverloadTy;
1073 case BuiltinType::Dependent: return Importer.getToContext().DependentTy;
1074 case BuiltinType::UndeducedAuto:
1075 // FIXME: Make sure that the "to" context supports C++0x!
1076 return Importer.getToContext().UndeducedAutoTy;
1077
1078 case BuiltinType::ObjCId:
1079 // FIXME: Make sure that the "to" context supports Objective-C!
1080 return Importer.getToContext().ObjCBuiltinIdTy;
1081
1082 case BuiltinType::ObjCClass:
1083 return Importer.getToContext().ObjCBuiltinClassTy;
1084
1085 case BuiltinType::ObjCSel:
1086 return Importer.getToContext().ObjCBuiltinSelTy;
1087 }
1088
1089 return QualType();
1090}
1091
1092QualType ASTNodeImporter::VisitComplexType(ComplexType *T) {
1093 QualType ToElementType = Importer.Import(T->getElementType());
1094 if (ToElementType.isNull())
1095 return QualType();
1096
1097 return Importer.getToContext().getComplexType(ToElementType);
1098}
1099
1100QualType ASTNodeImporter::VisitPointerType(PointerType *T) {
1101 QualType ToPointeeType = Importer.Import(T->getPointeeType());
1102 if (ToPointeeType.isNull())
1103 return QualType();
1104
1105 return Importer.getToContext().getPointerType(ToPointeeType);
1106}
1107
1108QualType ASTNodeImporter::VisitBlockPointerType(BlockPointerType *T) {
1109 // FIXME: Check for blocks support in "to" context.
1110 QualType ToPointeeType = Importer.Import(T->getPointeeType());
1111 if (ToPointeeType.isNull())
1112 return QualType();
1113
1114 return Importer.getToContext().getBlockPointerType(ToPointeeType);
1115}
1116
1117QualType ASTNodeImporter::VisitLValueReferenceType(LValueReferenceType *T) {
1118 // FIXME: Check for C++ support in "to" context.
1119 QualType ToPointeeType = Importer.Import(T->getPointeeTypeAsWritten());
1120 if (ToPointeeType.isNull())
1121 return QualType();
1122
1123 return Importer.getToContext().getLValueReferenceType(ToPointeeType);
1124}
1125
1126QualType ASTNodeImporter::VisitRValueReferenceType(RValueReferenceType *T) {
1127 // FIXME: Check for C++0x support in "to" context.
1128 QualType ToPointeeType = Importer.Import(T->getPointeeTypeAsWritten());
1129 if (ToPointeeType.isNull())
1130 return QualType();
1131
1132 return Importer.getToContext().getRValueReferenceType(ToPointeeType);
1133}
1134
1135QualType ASTNodeImporter::VisitMemberPointerType(MemberPointerType *T) {
1136 // FIXME: Check for C++ support in "to" context.
1137 QualType ToPointeeType = Importer.Import(T->getPointeeType());
1138 if (ToPointeeType.isNull())
1139 return QualType();
1140
1141 QualType ClassType = Importer.Import(QualType(T->getClass(), 0));
1142 return Importer.getToContext().getMemberPointerType(ToPointeeType,
1143 ClassType.getTypePtr());
1144}
1145
1146QualType ASTNodeImporter::VisitConstantArrayType(ConstantArrayType *T) {
1147 QualType ToElementType = Importer.Import(T->getElementType());
1148 if (ToElementType.isNull())
1149 return QualType();
1150
1151 return Importer.getToContext().getConstantArrayType(ToElementType,
1152 T->getSize(),
1153 T->getSizeModifier(),
1154 T->getIndexTypeCVRQualifiers());
1155}
1156
1157QualType ASTNodeImporter::VisitIncompleteArrayType(IncompleteArrayType *T) {
1158 QualType ToElementType = Importer.Import(T->getElementType());
1159 if (ToElementType.isNull())
1160 return QualType();
1161
1162 return Importer.getToContext().getIncompleteArrayType(ToElementType,
1163 T->getSizeModifier(),
1164 T->getIndexTypeCVRQualifiers());
1165}
1166
1167QualType ASTNodeImporter::VisitVariableArrayType(VariableArrayType *T) {
1168 QualType ToElementType = Importer.Import(T->getElementType());
1169 if (ToElementType.isNull())
1170 return QualType();
1171
1172 Expr *Size = Importer.Import(T->getSizeExpr());
1173 if (!Size)
1174 return QualType();
1175
1176 SourceRange Brackets = Importer.Import(T->getBracketsRange());
1177 return Importer.getToContext().getVariableArrayType(ToElementType, Size,
1178 T->getSizeModifier(),
1179 T->getIndexTypeCVRQualifiers(),
1180 Brackets);
1181}
1182
1183QualType ASTNodeImporter::VisitVectorType(VectorType *T) {
1184 QualType ToElementType = Importer.Import(T->getElementType());
1185 if (ToElementType.isNull())
1186 return QualType();
1187
1188 return Importer.getToContext().getVectorType(ToElementType,
1189 T->getNumElements(),
Bob Wilsonaeb56442010-11-10 21:56:12 +00001190 T->getVectorKind());
Douglas Gregor96e578d2010-02-05 17:54:41 +00001191}
1192
1193QualType ASTNodeImporter::VisitExtVectorType(ExtVectorType *T) {
1194 QualType ToElementType = Importer.Import(T->getElementType());
1195 if (ToElementType.isNull())
1196 return QualType();
1197
1198 return Importer.getToContext().getExtVectorType(ToElementType,
1199 T->getNumElements());
1200}
1201
1202QualType ASTNodeImporter::VisitFunctionNoProtoType(FunctionNoProtoType *T) {
1203 // FIXME: What happens if we're importing a function without a prototype
1204 // into C++? Should we make it variadic?
1205 QualType ToResultType = Importer.Import(T->getResultType());
1206 if (ToResultType.isNull())
1207 return QualType();
Rafael Espindolac50c27c2010-03-30 20:24:48 +00001208
Douglas Gregor96e578d2010-02-05 17:54:41 +00001209 return Importer.getToContext().getFunctionNoProtoType(ToResultType,
Rafael Espindolac50c27c2010-03-30 20:24:48 +00001210 T->getExtInfo());
Douglas Gregor96e578d2010-02-05 17:54:41 +00001211}
1212
1213QualType ASTNodeImporter::VisitFunctionProtoType(FunctionProtoType *T) {
1214 QualType ToResultType = Importer.Import(T->getResultType());
1215 if (ToResultType.isNull())
1216 return QualType();
1217
1218 // Import argument types
1219 llvm::SmallVector<QualType, 4> ArgTypes;
1220 for (FunctionProtoType::arg_type_iterator A = T->arg_type_begin(),
1221 AEnd = T->arg_type_end();
1222 A != AEnd; ++A) {
1223 QualType ArgType = Importer.Import(*A);
1224 if (ArgType.isNull())
1225 return QualType();
1226 ArgTypes.push_back(ArgType);
1227 }
1228
1229 // Import exception types
1230 llvm::SmallVector<QualType, 4> ExceptionTypes;
1231 for (FunctionProtoType::exception_iterator E = T->exception_begin(),
1232 EEnd = T->exception_end();
1233 E != EEnd; ++E) {
1234 QualType ExceptionType = Importer.Import(*E);
1235 if (ExceptionType.isNull())
1236 return QualType();
1237 ExceptionTypes.push_back(ExceptionType);
1238 }
1239
1240 return Importer.getToContext().getFunctionType(ToResultType, ArgTypes.data(),
1241 ArgTypes.size(),
1242 T->isVariadic(),
1243 T->getTypeQuals(),
1244 T->hasExceptionSpec(),
1245 T->hasAnyExceptionSpec(),
1246 ExceptionTypes.size(),
1247 ExceptionTypes.data(),
Rafael Espindolac50c27c2010-03-30 20:24:48 +00001248 T->getExtInfo());
Douglas Gregor96e578d2010-02-05 17:54:41 +00001249}
1250
1251QualType ASTNodeImporter::VisitTypedefType(TypedefType *T) {
1252 TypedefDecl *ToDecl
1253 = dyn_cast_or_null<TypedefDecl>(Importer.Import(T->getDecl()));
1254 if (!ToDecl)
1255 return QualType();
1256
1257 return Importer.getToContext().getTypeDeclType(ToDecl);
1258}
1259
1260QualType ASTNodeImporter::VisitTypeOfExprType(TypeOfExprType *T) {
1261 Expr *ToExpr = Importer.Import(T->getUnderlyingExpr());
1262 if (!ToExpr)
1263 return QualType();
1264
1265 return Importer.getToContext().getTypeOfExprType(ToExpr);
1266}
1267
1268QualType ASTNodeImporter::VisitTypeOfType(TypeOfType *T) {
1269 QualType ToUnderlyingType = Importer.Import(T->getUnderlyingType());
1270 if (ToUnderlyingType.isNull())
1271 return QualType();
1272
1273 return Importer.getToContext().getTypeOfType(ToUnderlyingType);
1274}
1275
1276QualType ASTNodeImporter::VisitDecltypeType(DecltypeType *T) {
1277 Expr *ToExpr = Importer.Import(T->getUnderlyingExpr());
1278 if (!ToExpr)
1279 return QualType();
1280
1281 return Importer.getToContext().getDecltypeType(ToExpr);
1282}
1283
1284QualType ASTNodeImporter::VisitRecordType(RecordType *T) {
1285 RecordDecl *ToDecl
1286 = dyn_cast_or_null<RecordDecl>(Importer.Import(T->getDecl()));
1287 if (!ToDecl)
1288 return QualType();
1289
1290 return Importer.getToContext().getTagDeclType(ToDecl);
1291}
1292
1293QualType ASTNodeImporter::VisitEnumType(EnumType *T) {
1294 EnumDecl *ToDecl
1295 = dyn_cast_or_null<EnumDecl>(Importer.Import(T->getDecl()));
1296 if (!ToDecl)
1297 return QualType();
1298
1299 return Importer.getToContext().getTagDeclType(ToDecl);
1300}
1301
1302QualType ASTNodeImporter::VisitElaboratedType(ElaboratedType *T) {
Abramo Bagnara6150c882010-05-11 21:36:43 +00001303 NestedNameSpecifier *ToQualifier = 0;
1304 // Note: the qualifier in an ElaboratedType is optional.
1305 if (T->getQualifier()) {
1306 ToQualifier = Importer.Import(T->getQualifier());
1307 if (!ToQualifier)
1308 return QualType();
1309 }
Douglas Gregor96e578d2010-02-05 17:54:41 +00001310
1311 QualType ToNamedType = Importer.Import(T->getNamedType());
1312 if (ToNamedType.isNull())
1313 return QualType();
1314
Abramo Bagnara6150c882010-05-11 21:36:43 +00001315 return Importer.getToContext().getElaboratedType(T->getKeyword(),
1316 ToQualifier, ToNamedType);
Douglas Gregor96e578d2010-02-05 17:54:41 +00001317}
1318
1319QualType ASTNodeImporter::VisitObjCInterfaceType(ObjCInterfaceType *T) {
1320 ObjCInterfaceDecl *Class
1321 = dyn_cast_or_null<ObjCInterfaceDecl>(Importer.Import(T->getDecl()));
1322 if (!Class)
1323 return QualType();
1324
John McCall8b07ec22010-05-15 11:32:37 +00001325 return Importer.getToContext().getObjCInterfaceType(Class);
1326}
1327
1328QualType ASTNodeImporter::VisitObjCObjectType(ObjCObjectType *T) {
1329 QualType ToBaseType = Importer.Import(T->getBaseType());
1330 if (ToBaseType.isNull())
1331 return QualType();
1332
Douglas Gregor96e578d2010-02-05 17:54:41 +00001333 llvm::SmallVector<ObjCProtocolDecl *, 4> Protocols;
John McCall8b07ec22010-05-15 11:32:37 +00001334 for (ObjCObjectType::qual_iterator P = T->qual_begin(),
Douglas Gregor96e578d2010-02-05 17:54:41 +00001335 PEnd = T->qual_end();
1336 P != PEnd; ++P) {
1337 ObjCProtocolDecl *Protocol
1338 = dyn_cast_or_null<ObjCProtocolDecl>(Importer.Import(*P));
1339 if (!Protocol)
1340 return QualType();
1341 Protocols.push_back(Protocol);
1342 }
1343
John McCall8b07ec22010-05-15 11:32:37 +00001344 return Importer.getToContext().getObjCObjectType(ToBaseType,
1345 Protocols.data(),
1346 Protocols.size());
Douglas Gregor96e578d2010-02-05 17:54:41 +00001347}
1348
1349QualType ASTNodeImporter::VisitObjCObjectPointerType(ObjCObjectPointerType *T) {
1350 QualType ToPointeeType = Importer.Import(T->getPointeeType());
1351 if (ToPointeeType.isNull())
1352 return QualType();
1353
John McCall8b07ec22010-05-15 11:32:37 +00001354 return Importer.getToContext().getObjCObjectPointerType(ToPointeeType);
Douglas Gregor96e578d2010-02-05 17:54:41 +00001355}
1356
Douglas Gregor3aed6cd2010-02-08 21:09:39 +00001357//----------------------------------------------------------------------------
1358// Import Declarations
1359//----------------------------------------------------------------------------
Douglas Gregorbb7930c2010-02-10 19:54:31 +00001360bool ASTNodeImporter::ImportDeclParts(NamedDecl *D, DeclContext *&DC,
1361 DeclContext *&LexicalDC,
1362 DeclarationName &Name,
1363 SourceLocation &Loc) {
1364 // Import the context of this declaration.
1365 DC = Importer.ImportContext(D->getDeclContext());
1366 if (!DC)
1367 return true;
1368
1369 LexicalDC = DC;
1370 if (D->getDeclContext() != D->getLexicalDeclContext()) {
1371 LexicalDC = Importer.ImportContext(D->getLexicalDeclContext());
1372 if (!LexicalDC)
1373 return true;
1374 }
1375
1376 // Import the name of this declaration.
1377 Name = Importer.Import(D->getDeclName());
1378 if (D->getDeclName() && !Name)
1379 return true;
1380
1381 // Import the location of this declaration.
1382 Loc = Importer.Import(D->getLocation());
1383 return false;
1384}
1385
Abramo Bagnarad6d2f182010-08-11 22:01:17 +00001386void
1387ASTNodeImporter::ImportDeclarationNameLoc(const DeclarationNameInfo &From,
1388 DeclarationNameInfo& To) {
1389 // NOTE: To.Name and To.Loc are already imported.
1390 // We only have to import To.LocInfo.
1391 switch (To.getName().getNameKind()) {
1392 case DeclarationName::Identifier:
1393 case DeclarationName::ObjCZeroArgSelector:
1394 case DeclarationName::ObjCOneArgSelector:
1395 case DeclarationName::ObjCMultiArgSelector:
1396 case DeclarationName::CXXUsingDirective:
1397 return;
1398
1399 case DeclarationName::CXXOperatorName: {
1400 SourceRange Range = From.getCXXOperatorNameRange();
1401 To.setCXXOperatorNameRange(Importer.Import(Range));
1402 return;
1403 }
1404 case DeclarationName::CXXLiteralOperatorName: {
1405 SourceLocation Loc = From.getCXXLiteralOperatorNameLoc();
1406 To.setCXXLiteralOperatorNameLoc(Importer.Import(Loc));
1407 return;
1408 }
1409 case DeclarationName::CXXConstructorName:
1410 case DeclarationName::CXXDestructorName:
1411 case DeclarationName::CXXConversionFunctionName: {
1412 TypeSourceInfo *FromTInfo = From.getNamedTypeInfo();
1413 To.setNamedTypeInfo(Importer.Import(FromTInfo));
1414 return;
1415 }
1416 assert(0 && "Unknown name kind.");
1417 }
1418}
1419
Douglas Gregor968d6332010-02-21 18:24:45 +00001420void ASTNodeImporter::ImportDeclContext(DeclContext *FromDC) {
1421 for (DeclContext::decl_iterator From = FromDC->decls_begin(),
1422 FromEnd = FromDC->decls_end();
1423 From != FromEnd;
1424 ++From)
1425 Importer.Import(*From);
1426}
1427
Douglas Gregor5c73e912010-02-11 00:48:18 +00001428bool ASTNodeImporter::IsStructuralMatch(RecordDecl *FromRecord,
Douglas Gregor3996e242010-02-15 22:01:00 +00001429 RecordDecl *ToRecord) {
Benjamin Kramer26d19c52010-02-18 13:02:13 +00001430 StructuralEquivalenceContext Ctx(Importer.getFromContext(),
Douglas Gregor3996e242010-02-15 22:01:00 +00001431 Importer.getToContext(),
Douglas Gregorb4964f72010-02-15 23:54:17 +00001432 Importer.getNonEquivalentDecls());
Benjamin Kramer26d19c52010-02-18 13:02:13 +00001433 return Ctx.IsStructurallyEquivalent(FromRecord, ToRecord);
Douglas Gregor5c73e912010-02-11 00:48:18 +00001434}
1435
Douglas Gregor98c10182010-02-12 22:17:39 +00001436bool ASTNodeImporter::IsStructuralMatch(EnumDecl *FromEnum, EnumDecl *ToEnum) {
Benjamin Kramer26d19c52010-02-18 13:02:13 +00001437 StructuralEquivalenceContext Ctx(Importer.getFromContext(),
Douglas Gregor3996e242010-02-15 22:01:00 +00001438 Importer.getToContext(),
Douglas Gregorb4964f72010-02-15 23:54:17 +00001439 Importer.getNonEquivalentDecls());
Benjamin Kramer26d19c52010-02-18 13:02:13 +00001440 return Ctx.IsStructurallyEquivalent(FromEnum, ToEnum);
Douglas Gregor98c10182010-02-12 22:17:39 +00001441}
1442
Douglas Gregore4c83e42010-02-09 22:48:33 +00001443Decl *ASTNodeImporter::VisitDecl(Decl *D) {
Douglas Gregor811663e2010-02-10 00:15:17 +00001444 Importer.FromDiag(D->getLocation(), diag::err_unsupported_ast_node)
Douglas Gregore4c83e42010-02-09 22:48:33 +00001445 << D->getDeclKindName();
1446 return 0;
1447}
1448
Douglas Gregorf18a2c72010-02-21 18:26:36 +00001449Decl *ASTNodeImporter::VisitNamespaceDecl(NamespaceDecl *D) {
1450 // Import the major distinguishing characteristics of this namespace.
1451 DeclContext *DC, *LexicalDC;
1452 DeclarationName Name;
1453 SourceLocation Loc;
1454 if (ImportDeclParts(D, DC, LexicalDC, Name, Loc))
1455 return 0;
1456
1457 NamespaceDecl *MergeWithNamespace = 0;
1458 if (!Name) {
1459 // This is an anonymous namespace. Adopt an existing anonymous
1460 // namespace if we can.
1461 // FIXME: Not testable.
1462 if (TranslationUnitDecl *TU = dyn_cast<TranslationUnitDecl>(DC))
1463 MergeWithNamespace = TU->getAnonymousNamespace();
1464 else
1465 MergeWithNamespace = cast<NamespaceDecl>(DC)->getAnonymousNamespace();
1466 } else {
1467 llvm::SmallVector<NamedDecl *, 4> ConflictingDecls;
1468 for (DeclContext::lookup_result Lookup = DC->lookup(Name);
1469 Lookup.first != Lookup.second;
1470 ++Lookup.first) {
John McCalle87beb22010-04-23 18:46:30 +00001471 if (!(*Lookup.first)->isInIdentifierNamespace(Decl::IDNS_Namespace))
Douglas Gregorf18a2c72010-02-21 18:26:36 +00001472 continue;
1473
1474 if (NamespaceDecl *FoundNS = dyn_cast<NamespaceDecl>(*Lookup.first)) {
1475 MergeWithNamespace = FoundNS;
1476 ConflictingDecls.clear();
1477 break;
1478 }
1479
1480 ConflictingDecls.push_back(*Lookup.first);
1481 }
1482
1483 if (!ConflictingDecls.empty()) {
John McCalle87beb22010-04-23 18:46:30 +00001484 Name = Importer.HandleNameConflict(Name, DC, Decl::IDNS_Namespace,
Douglas Gregorf18a2c72010-02-21 18:26:36 +00001485 ConflictingDecls.data(),
1486 ConflictingDecls.size());
1487 }
1488 }
1489
1490 // Create the "to" namespace, if needed.
1491 NamespaceDecl *ToNamespace = MergeWithNamespace;
1492 if (!ToNamespace) {
1493 ToNamespace = NamespaceDecl::Create(Importer.getToContext(), DC, Loc,
1494 Name.getAsIdentifierInfo());
1495 ToNamespace->setLexicalDeclContext(LexicalDC);
1496 LexicalDC->addDecl(ToNamespace);
1497
1498 // If this is an anonymous namespace, register it as the anonymous
1499 // namespace within its context.
1500 if (!Name) {
1501 if (TranslationUnitDecl *TU = dyn_cast<TranslationUnitDecl>(DC))
1502 TU->setAnonymousNamespace(ToNamespace);
1503 else
1504 cast<NamespaceDecl>(DC)->setAnonymousNamespace(ToNamespace);
1505 }
1506 }
1507 Importer.Imported(D, ToNamespace);
1508
1509 ImportDeclContext(D);
1510
1511 return ToNamespace;
1512}
1513
Douglas Gregor5fa74c32010-02-10 21:10:29 +00001514Decl *ASTNodeImporter::VisitTypedefDecl(TypedefDecl *D) {
1515 // Import the major distinguishing characteristics of this typedef.
1516 DeclContext *DC, *LexicalDC;
1517 DeclarationName Name;
1518 SourceLocation Loc;
1519 if (ImportDeclParts(D, DC, LexicalDC, Name, Loc))
1520 return 0;
1521
Douglas Gregor5fa74c32010-02-10 21:10:29 +00001522 // If this typedef is not in block scope, determine whether we've
1523 // seen a typedef with the same name (that we can merge with) or any
1524 // other entity by that name (which name lookup could conflict with).
1525 if (!DC->isFunctionOrMethod()) {
1526 llvm::SmallVector<NamedDecl *, 4> ConflictingDecls;
1527 unsigned IDNS = Decl::IDNS_Ordinary;
1528 for (DeclContext::lookup_result Lookup = DC->lookup(Name);
1529 Lookup.first != Lookup.second;
1530 ++Lookup.first) {
1531 if (!(*Lookup.first)->isInIdentifierNamespace(IDNS))
1532 continue;
1533 if (TypedefDecl *FoundTypedef = dyn_cast<TypedefDecl>(*Lookup.first)) {
Douglas Gregorb4964f72010-02-15 23:54:17 +00001534 if (Importer.IsStructurallyEquivalent(D->getUnderlyingType(),
1535 FoundTypedef->getUnderlyingType()))
Douglas Gregor8cdbe642010-02-12 23:44:20 +00001536 return Importer.Imported(D, FoundTypedef);
Douglas Gregor5fa74c32010-02-10 21:10:29 +00001537 }
1538
1539 ConflictingDecls.push_back(*Lookup.first);
1540 }
1541
1542 if (!ConflictingDecls.empty()) {
1543 Name = Importer.HandleNameConflict(Name, DC, IDNS,
1544 ConflictingDecls.data(),
1545 ConflictingDecls.size());
1546 if (!Name)
1547 return 0;
1548 }
1549 }
1550
Douglas Gregorb4964f72010-02-15 23:54:17 +00001551 // Import the underlying type of this typedef;
1552 QualType T = Importer.Import(D->getUnderlyingType());
1553 if (T.isNull())
1554 return 0;
1555
Douglas Gregor5fa74c32010-02-10 21:10:29 +00001556 // Create the new typedef node.
1557 TypeSourceInfo *TInfo = Importer.Import(D->getTypeSourceInfo());
1558 TypedefDecl *ToTypedef = TypedefDecl::Create(Importer.getToContext(), DC,
1559 Loc, Name.getAsIdentifierInfo(),
1560 TInfo);
Douglas Gregordd483172010-02-22 17:42:47 +00001561 ToTypedef->setAccess(D->getAccess());
Douglas Gregor5fa74c32010-02-10 21:10:29 +00001562 ToTypedef->setLexicalDeclContext(LexicalDC);
Douglas Gregor8cdbe642010-02-12 23:44:20 +00001563 Importer.Imported(D, ToTypedef);
Douglas Gregor5fa74c32010-02-10 21:10:29 +00001564 LexicalDC->addDecl(ToTypedef);
Douglas Gregorb4964f72010-02-15 23:54:17 +00001565
Douglas Gregor5fa74c32010-02-10 21:10:29 +00001566 return ToTypedef;
1567}
1568
Douglas Gregor98c10182010-02-12 22:17:39 +00001569Decl *ASTNodeImporter::VisitEnumDecl(EnumDecl *D) {
1570 // Import the major distinguishing characteristics of this enum.
1571 DeclContext *DC, *LexicalDC;
1572 DeclarationName Name;
1573 SourceLocation Loc;
1574 if (ImportDeclParts(D, DC, LexicalDC, Name, Loc))
1575 return 0;
1576
1577 // Figure out what enum name we're looking for.
1578 unsigned IDNS = Decl::IDNS_Tag;
1579 DeclarationName SearchName = Name;
1580 if (!SearchName && D->getTypedefForAnonDecl()) {
1581 SearchName = Importer.Import(D->getTypedefForAnonDecl()->getDeclName());
1582 IDNS = Decl::IDNS_Ordinary;
1583 } else if (Importer.getToContext().getLangOptions().CPlusPlus)
1584 IDNS |= Decl::IDNS_Ordinary;
1585
1586 // We may already have an enum of the same name; try to find and match it.
1587 if (!DC->isFunctionOrMethod() && SearchName) {
1588 llvm::SmallVector<NamedDecl *, 4> ConflictingDecls;
1589 for (DeclContext::lookup_result Lookup = DC->lookup(Name);
1590 Lookup.first != Lookup.second;
1591 ++Lookup.first) {
1592 if (!(*Lookup.first)->isInIdentifierNamespace(IDNS))
1593 continue;
1594
1595 Decl *Found = *Lookup.first;
1596 if (TypedefDecl *Typedef = dyn_cast<TypedefDecl>(Found)) {
1597 if (const TagType *Tag = Typedef->getUnderlyingType()->getAs<TagType>())
1598 Found = Tag->getDecl();
1599 }
1600
1601 if (EnumDecl *FoundEnum = dyn_cast<EnumDecl>(Found)) {
Douglas Gregor8cdbe642010-02-12 23:44:20 +00001602 if (IsStructuralMatch(D, FoundEnum))
1603 return Importer.Imported(D, FoundEnum);
Douglas Gregor98c10182010-02-12 22:17:39 +00001604 }
1605
1606 ConflictingDecls.push_back(*Lookup.first);
1607 }
1608
1609 if (!ConflictingDecls.empty()) {
1610 Name = Importer.HandleNameConflict(Name, DC, IDNS,
1611 ConflictingDecls.data(),
1612 ConflictingDecls.size());
1613 }
1614 }
1615
1616 // Create the enum declaration.
Douglas Gregor3996e242010-02-15 22:01:00 +00001617 EnumDecl *D2 = EnumDecl::Create(Importer.getToContext(), DC, Loc,
Douglas Gregor98c10182010-02-12 22:17:39 +00001618 Name.getAsIdentifierInfo(),
1619 Importer.Import(D->getTagKeywordLoc()),
Douglas Gregor0bf31402010-10-08 23:50:27 +00001620 0, D->isScoped(), D->isFixed());
John McCall3e11ebe2010-03-15 10:12:16 +00001621 // Import the qualifier, if any.
1622 if (D->getQualifier()) {
1623 NestedNameSpecifier *NNS = Importer.Import(D->getQualifier());
1624 SourceRange NNSRange = Importer.Import(D->getQualifierRange());
1625 D2->setQualifierInfo(NNS, NNSRange);
1626 }
Douglas Gregordd483172010-02-22 17:42:47 +00001627 D2->setAccess(D->getAccess());
Douglas Gregor3996e242010-02-15 22:01:00 +00001628 D2->setLexicalDeclContext(LexicalDC);
1629 Importer.Imported(D, D2);
1630 LexicalDC->addDecl(D2);
Douglas Gregor98c10182010-02-12 22:17:39 +00001631
1632 // Import the integer type.
1633 QualType ToIntegerType = Importer.Import(D->getIntegerType());
1634 if (ToIntegerType.isNull())
1635 return 0;
Douglas Gregor3996e242010-02-15 22:01:00 +00001636 D2->setIntegerType(ToIntegerType);
Douglas Gregor98c10182010-02-12 22:17:39 +00001637
1638 // Import the definition
1639 if (D->isDefinition()) {
1640 QualType T = Importer.Import(Importer.getFromContext().getTypeDeclType(D));
1641 if (T.isNull())
1642 return 0;
1643
1644 QualType ToPromotionType = Importer.Import(D->getPromotionType());
1645 if (ToPromotionType.isNull())
1646 return 0;
1647
Douglas Gregor3996e242010-02-15 22:01:00 +00001648 D2->startDefinition();
Douglas Gregor968d6332010-02-21 18:24:45 +00001649 ImportDeclContext(D);
John McCall9aa35be2010-05-06 08:49:23 +00001650
1651 // FIXME: we might need to merge the number of positive or negative bits
1652 // if the enumerator lists don't match.
1653 D2->completeDefinition(T, ToPromotionType,
1654 D->getNumPositiveBits(),
1655 D->getNumNegativeBits());
Douglas Gregor98c10182010-02-12 22:17:39 +00001656 }
1657
Douglas Gregor3996e242010-02-15 22:01:00 +00001658 return D2;
Douglas Gregor98c10182010-02-12 22:17:39 +00001659}
1660
Douglas Gregor5c73e912010-02-11 00:48:18 +00001661Decl *ASTNodeImporter::VisitRecordDecl(RecordDecl *D) {
1662 // If this record has a definition in the translation unit we're coming from,
1663 // but this particular declaration is not that definition, import the
1664 // definition and map to that.
Douglas Gregor0a5a2212010-02-11 01:04:33 +00001665 TagDecl *Definition = D->getDefinition();
Douglas Gregor5c73e912010-02-11 00:48:18 +00001666 if (Definition && Definition != D) {
1667 Decl *ImportedDef = Importer.Import(Definition);
Douglas Gregor8cdbe642010-02-12 23:44:20 +00001668 if (!ImportedDef)
1669 return 0;
1670
1671 return Importer.Imported(D, ImportedDef);
Douglas Gregor5c73e912010-02-11 00:48:18 +00001672 }
1673
1674 // Import the major distinguishing characteristics of this record.
1675 DeclContext *DC, *LexicalDC;
1676 DeclarationName Name;
1677 SourceLocation Loc;
1678 if (ImportDeclParts(D, DC, LexicalDC, Name, Loc))
1679 return 0;
1680
1681 // Figure out what structure name we're looking for.
1682 unsigned IDNS = Decl::IDNS_Tag;
1683 DeclarationName SearchName = Name;
1684 if (!SearchName && D->getTypedefForAnonDecl()) {
1685 SearchName = Importer.Import(D->getTypedefForAnonDecl()->getDeclName());
1686 IDNS = Decl::IDNS_Ordinary;
1687 } else if (Importer.getToContext().getLangOptions().CPlusPlus)
1688 IDNS |= Decl::IDNS_Ordinary;
1689
1690 // We may already have a record of the same name; try to find and match it.
Douglas Gregor25791052010-02-12 00:09:27 +00001691 RecordDecl *AdoptDecl = 0;
Douglas Gregor5c73e912010-02-11 00:48:18 +00001692 if (!DC->isFunctionOrMethod() && SearchName) {
1693 llvm::SmallVector<NamedDecl *, 4> ConflictingDecls;
1694 for (DeclContext::lookup_result Lookup = DC->lookup(Name);
1695 Lookup.first != Lookup.second;
1696 ++Lookup.first) {
1697 if (!(*Lookup.first)->isInIdentifierNamespace(IDNS))
1698 continue;
1699
1700 Decl *Found = *Lookup.first;
1701 if (TypedefDecl *Typedef = dyn_cast<TypedefDecl>(Found)) {
1702 if (const TagType *Tag = Typedef->getUnderlyingType()->getAs<TagType>())
1703 Found = Tag->getDecl();
1704 }
1705
1706 if (RecordDecl *FoundRecord = dyn_cast<RecordDecl>(Found)) {
Douglas Gregor25791052010-02-12 00:09:27 +00001707 if (RecordDecl *FoundDef = FoundRecord->getDefinition()) {
1708 if (!D->isDefinition() || IsStructuralMatch(D, FoundDef)) {
1709 // The record types structurally match, or the "from" translation
1710 // unit only had a forward declaration anyway; call it the same
1711 // function.
1712 // FIXME: For C++, we should also merge methods here.
Douglas Gregor8cdbe642010-02-12 23:44:20 +00001713 return Importer.Imported(D, FoundDef);
Douglas Gregor25791052010-02-12 00:09:27 +00001714 }
1715 } else {
1716 // We have a forward declaration of this type, so adopt that forward
1717 // declaration rather than building a new one.
1718 AdoptDecl = FoundRecord;
1719 continue;
1720 }
Douglas Gregor5c73e912010-02-11 00:48:18 +00001721 }
1722
1723 ConflictingDecls.push_back(*Lookup.first);
1724 }
1725
1726 if (!ConflictingDecls.empty()) {
1727 Name = Importer.HandleNameConflict(Name, DC, IDNS,
1728 ConflictingDecls.data(),
1729 ConflictingDecls.size());
1730 }
1731 }
1732
1733 // Create the record declaration.
Douglas Gregor3996e242010-02-15 22:01:00 +00001734 RecordDecl *D2 = AdoptDecl;
1735 if (!D2) {
John McCall1c70e992010-06-03 19:28:45 +00001736 if (isa<CXXRecordDecl>(D)) {
Douglas Gregor3996e242010-02-15 22:01:00 +00001737 CXXRecordDecl *D2CXX = CXXRecordDecl::Create(Importer.getToContext(),
Douglas Gregor25791052010-02-12 00:09:27 +00001738 D->getTagKind(),
1739 DC, Loc,
1740 Name.getAsIdentifierInfo(),
Douglas Gregor5c73e912010-02-11 00:48:18 +00001741 Importer.Import(D->getTagKeywordLoc()));
Douglas Gregor3996e242010-02-15 22:01:00 +00001742 D2 = D2CXX;
Douglas Gregordd483172010-02-22 17:42:47 +00001743 D2->setAccess(D->getAccess());
Douglas Gregor25791052010-02-12 00:09:27 +00001744 } else {
Douglas Gregor3996e242010-02-15 22:01:00 +00001745 D2 = RecordDecl::Create(Importer.getToContext(), D->getTagKind(),
Douglas Gregor25791052010-02-12 00:09:27 +00001746 DC, Loc,
1747 Name.getAsIdentifierInfo(),
1748 Importer.Import(D->getTagKeywordLoc()));
Douglas Gregor5c73e912010-02-11 00:48:18 +00001749 }
John McCall3e11ebe2010-03-15 10:12:16 +00001750 // Import the qualifier, if any.
1751 if (D->getQualifier()) {
1752 NestedNameSpecifier *NNS = Importer.Import(D->getQualifier());
1753 SourceRange NNSRange = Importer.Import(D->getQualifierRange());
1754 D2->setQualifierInfo(NNS, NNSRange);
1755 }
Douglas Gregor3996e242010-02-15 22:01:00 +00001756 D2->setLexicalDeclContext(LexicalDC);
1757 LexicalDC->addDecl(D2);
Douglas Gregor5c73e912010-02-11 00:48:18 +00001758 }
Douglas Gregor8cdbe642010-02-12 23:44:20 +00001759
Douglas Gregor3996e242010-02-15 22:01:00 +00001760 Importer.Imported(D, D2);
Douglas Gregor25791052010-02-12 00:09:27 +00001761
Douglas Gregor5c73e912010-02-11 00:48:18 +00001762 if (D->isDefinition()) {
Douglas Gregor3996e242010-02-15 22:01:00 +00001763 D2->startDefinition();
John McCall1c70e992010-06-03 19:28:45 +00001764
1765 // Add base classes.
1766 if (CXXRecordDecl *D2CXX = dyn_cast<CXXRecordDecl>(D2)) {
1767 CXXRecordDecl *D1CXX = cast<CXXRecordDecl>(D);
1768
1769 llvm::SmallVector<CXXBaseSpecifier *, 4> Bases;
1770 for (CXXRecordDecl::base_class_iterator
1771 Base1 = D1CXX->bases_begin(),
1772 FromBaseEnd = D1CXX->bases_end();
1773 Base1 != FromBaseEnd;
1774 ++Base1) {
1775 QualType T = Importer.Import(Base1->getType());
1776 if (T.isNull())
1777 return 0;
1778
1779 Bases.push_back(
1780 new (Importer.getToContext())
1781 CXXBaseSpecifier(Importer.Import(Base1->getSourceRange()),
1782 Base1->isVirtual(),
1783 Base1->isBaseOfClass(),
1784 Base1->getAccessSpecifierAsWritten(),
Nick Lewycky19b9f952010-07-26 16:56:01 +00001785 Importer.Import(Base1->getTypeSourceInfo())));
John McCall1c70e992010-06-03 19:28:45 +00001786 }
1787 if (!Bases.empty())
1788 D2CXX->setBases(Bases.data(), Bases.size());
1789 }
1790
Douglas Gregor968d6332010-02-21 18:24:45 +00001791 ImportDeclContext(D);
Douglas Gregor3996e242010-02-15 22:01:00 +00001792 D2->completeDefinition();
Douglas Gregor5c73e912010-02-11 00:48:18 +00001793 }
1794
Douglas Gregor3996e242010-02-15 22:01:00 +00001795 return D2;
Douglas Gregor5c73e912010-02-11 00:48:18 +00001796}
1797
Douglas Gregor98c10182010-02-12 22:17:39 +00001798Decl *ASTNodeImporter::VisitEnumConstantDecl(EnumConstantDecl *D) {
1799 // Import the major distinguishing characteristics of this enumerator.
1800 DeclContext *DC, *LexicalDC;
1801 DeclarationName Name;
1802 SourceLocation Loc;
Douglas Gregorb4964f72010-02-15 23:54:17 +00001803 if (ImportDeclParts(D, DC, LexicalDC, Name, Loc))
Douglas Gregor98c10182010-02-12 22:17:39 +00001804 return 0;
Douglas Gregorb4964f72010-02-15 23:54:17 +00001805
1806 QualType T = Importer.Import(D->getType());
1807 if (T.isNull())
1808 return 0;
1809
Douglas Gregor98c10182010-02-12 22:17:39 +00001810 // Determine whether there are any other declarations with the same name and
1811 // in the same context.
1812 if (!LexicalDC->isFunctionOrMethod()) {
1813 llvm::SmallVector<NamedDecl *, 4> ConflictingDecls;
1814 unsigned IDNS = Decl::IDNS_Ordinary;
1815 for (DeclContext::lookup_result Lookup = DC->lookup(Name);
1816 Lookup.first != Lookup.second;
1817 ++Lookup.first) {
1818 if (!(*Lookup.first)->isInIdentifierNamespace(IDNS))
1819 continue;
1820
1821 ConflictingDecls.push_back(*Lookup.first);
1822 }
1823
1824 if (!ConflictingDecls.empty()) {
1825 Name = Importer.HandleNameConflict(Name, DC, IDNS,
1826 ConflictingDecls.data(),
1827 ConflictingDecls.size());
1828 if (!Name)
1829 return 0;
1830 }
1831 }
1832
1833 Expr *Init = Importer.Import(D->getInitExpr());
1834 if (D->getInitExpr() && !Init)
1835 return 0;
1836
1837 EnumConstantDecl *ToEnumerator
1838 = EnumConstantDecl::Create(Importer.getToContext(), cast<EnumDecl>(DC), Loc,
1839 Name.getAsIdentifierInfo(), T,
1840 Init, D->getInitVal());
Douglas Gregordd483172010-02-22 17:42:47 +00001841 ToEnumerator->setAccess(D->getAccess());
Douglas Gregor98c10182010-02-12 22:17:39 +00001842 ToEnumerator->setLexicalDeclContext(LexicalDC);
Douglas Gregor8cdbe642010-02-12 23:44:20 +00001843 Importer.Imported(D, ToEnumerator);
Douglas Gregor98c10182010-02-12 22:17:39 +00001844 LexicalDC->addDecl(ToEnumerator);
1845 return ToEnumerator;
1846}
Douglas Gregor5c73e912010-02-11 00:48:18 +00001847
Douglas Gregorbb7930c2010-02-10 19:54:31 +00001848Decl *ASTNodeImporter::VisitFunctionDecl(FunctionDecl *D) {
1849 // Import the major distinguishing characteristics of this function.
1850 DeclContext *DC, *LexicalDC;
1851 DeclarationName Name;
Douglas Gregorbb7930c2010-02-10 19:54:31 +00001852 SourceLocation Loc;
Douglas Gregorb4964f72010-02-15 23:54:17 +00001853 if (ImportDeclParts(D, DC, LexicalDC, Name, Loc))
Douglas Gregor3aed6cd2010-02-08 21:09:39 +00001854 return 0;
Abramo Bagnarad6d2f182010-08-11 22:01:17 +00001855
Douglas Gregorbb7930c2010-02-10 19:54:31 +00001856 // Try to find a function in our own ("to") context with the same name, same
1857 // type, and in the same context as the function we're importing.
1858 if (!LexicalDC->isFunctionOrMethod()) {
1859 llvm::SmallVector<NamedDecl *, 4> ConflictingDecls;
1860 unsigned IDNS = Decl::IDNS_Ordinary;
1861 for (DeclContext::lookup_result Lookup = DC->lookup(Name);
1862 Lookup.first != Lookup.second;
1863 ++Lookup.first) {
1864 if (!(*Lookup.first)->isInIdentifierNamespace(IDNS))
1865 continue;
Douglas Gregor3aed6cd2010-02-08 21:09:39 +00001866
Douglas Gregorbb7930c2010-02-10 19:54:31 +00001867 if (FunctionDecl *FoundFunction = dyn_cast<FunctionDecl>(*Lookup.first)) {
1868 if (isExternalLinkage(FoundFunction->getLinkage()) &&
1869 isExternalLinkage(D->getLinkage())) {
Douglas Gregorb4964f72010-02-15 23:54:17 +00001870 if (Importer.IsStructurallyEquivalent(D->getType(),
1871 FoundFunction->getType())) {
Douglas Gregorbb7930c2010-02-10 19:54:31 +00001872 // FIXME: Actually try to merge the body and other attributes.
Douglas Gregor8cdbe642010-02-12 23:44:20 +00001873 return Importer.Imported(D, FoundFunction);
Douglas Gregorbb7930c2010-02-10 19:54:31 +00001874 }
1875
1876 // FIXME: Check for overloading more carefully, e.g., by boosting
1877 // Sema::IsOverload out to the AST library.
1878
1879 // Function overloading is okay in C++.
1880 if (Importer.getToContext().getLangOptions().CPlusPlus)
1881 continue;
1882
1883 // Complain about inconsistent function types.
1884 Importer.ToDiag(Loc, diag::err_odr_function_type_inconsistent)
Douglas Gregorb4964f72010-02-15 23:54:17 +00001885 << Name << D->getType() << FoundFunction->getType();
Douglas Gregorbb7930c2010-02-10 19:54:31 +00001886 Importer.ToDiag(FoundFunction->getLocation(),
1887 diag::note_odr_value_here)
1888 << FoundFunction->getType();
1889 }
1890 }
1891
1892 ConflictingDecls.push_back(*Lookup.first);
1893 }
1894
1895 if (!ConflictingDecls.empty()) {
1896 Name = Importer.HandleNameConflict(Name, DC, IDNS,
1897 ConflictingDecls.data(),
1898 ConflictingDecls.size());
1899 if (!Name)
1900 return 0;
1901 }
Douglas Gregor62d311f2010-02-09 19:21:46 +00001902 }
Douglas Gregorb4964f72010-02-15 23:54:17 +00001903
Abramo Bagnarad6d2f182010-08-11 22:01:17 +00001904 DeclarationNameInfo NameInfo(Name, Loc);
1905 // Import additional name location/type info.
1906 ImportDeclarationNameLoc(D->getNameInfo(), NameInfo);
1907
Douglas Gregorb4964f72010-02-15 23:54:17 +00001908 // Import the type.
1909 QualType T = Importer.Import(D->getType());
1910 if (T.isNull())
1911 return 0;
Douglas Gregorbb7930c2010-02-10 19:54:31 +00001912
1913 // Import the function parameters.
1914 llvm::SmallVector<ParmVarDecl *, 8> Parameters;
1915 for (FunctionDecl::param_iterator P = D->param_begin(), PEnd = D->param_end();
1916 P != PEnd; ++P) {
1917 ParmVarDecl *ToP = cast_or_null<ParmVarDecl>(Importer.Import(*P));
1918 if (!ToP)
1919 return 0;
1920
1921 Parameters.push_back(ToP);
1922 }
1923
1924 // Create the imported function.
1925 TypeSourceInfo *TInfo = Importer.Import(D->getTypeSourceInfo());
Douglas Gregor00eace12010-02-21 18:29:16 +00001926 FunctionDecl *ToFunction = 0;
1927 if (CXXConstructorDecl *FromConstructor = dyn_cast<CXXConstructorDecl>(D)) {
1928 ToFunction = CXXConstructorDecl::Create(Importer.getToContext(),
1929 cast<CXXRecordDecl>(DC),
Abramo Bagnarad6d2f182010-08-11 22:01:17 +00001930 NameInfo, T, TInfo,
Douglas Gregor00eace12010-02-21 18:29:16 +00001931 FromConstructor->isExplicit(),
1932 D->isInlineSpecified(),
1933 D->isImplicit());
1934 } else if (isa<CXXDestructorDecl>(D)) {
1935 ToFunction = CXXDestructorDecl::Create(Importer.getToContext(),
1936 cast<CXXRecordDecl>(DC),
Craig Silversteinaf8808d2010-10-21 00:44:50 +00001937 NameInfo, T, TInfo,
Douglas Gregor00eace12010-02-21 18:29:16 +00001938 D->isInlineSpecified(),
1939 D->isImplicit());
1940 } else if (CXXConversionDecl *FromConversion
1941 = dyn_cast<CXXConversionDecl>(D)) {
1942 ToFunction = CXXConversionDecl::Create(Importer.getToContext(),
1943 cast<CXXRecordDecl>(DC),
Abramo Bagnarad6d2f182010-08-11 22:01:17 +00001944 NameInfo, T, TInfo,
Douglas Gregor00eace12010-02-21 18:29:16 +00001945 D->isInlineSpecified(),
1946 FromConversion->isExplicit());
1947 } else {
Abramo Bagnarad6d2f182010-08-11 22:01:17 +00001948 ToFunction = FunctionDecl::Create(Importer.getToContext(), DC,
1949 NameInfo, T, TInfo, D->getStorageClass(),
Douglas Gregorc4df4072010-04-19 22:54:31 +00001950 D->getStorageClassAsWritten(),
Douglas Gregor00eace12010-02-21 18:29:16 +00001951 D->isInlineSpecified(),
1952 D->hasWrittenPrototype());
1953 }
John McCall3e11ebe2010-03-15 10:12:16 +00001954
1955 // Import the qualifier, if any.
1956 if (D->getQualifier()) {
1957 NestedNameSpecifier *NNS = Importer.Import(D->getQualifier());
1958 SourceRange NNSRange = Importer.Import(D->getQualifierRange());
1959 ToFunction->setQualifierInfo(NNS, NNSRange);
1960 }
Douglas Gregordd483172010-02-22 17:42:47 +00001961 ToFunction->setAccess(D->getAccess());
Douglas Gregor43f54792010-02-17 02:12:47 +00001962 ToFunction->setLexicalDeclContext(LexicalDC);
1963 Importer.Imported(D, ToFunction);
Douglas Gregor62d311f2010-02-09 19:21:46 +00001964
Douglas Gregorbb7930c2010-02-10 19:54:31 +00001965 // Set the parameters.
1966 for (unsigned I = 0, N = Parameters.size(); I != N; ++I) {
Douglas Gregor43f54792010-02-17 02:12:47 +00001967 Parameters[I]->setOwningFunction(ToFunction);
1968 ToFunction->addDecl(Parameters[I]);
Douglas Gregorbb7930c2010-02-10 19:54:31 +00001969 }
Douglas Gregor43f54792010-02-17 02:12:47 +00001970 ToFunction->setParams(Parameters.data(), Parameters.size());
Douglas Gregorbb7930c2010-02-10 19:54:31 +00001971
1972 // FIXME: Other bits to merge?
Douglas Gregor0eaa2bf2010-10-01 23:55:07 +00001973
1974 // Add this function to the lexical context.
1975 LexicalDC->addDecl(ToFunction);
1976
Douglas Gregor43f54792010-02-17 02:12:47 +00001977 return ToFunction;
Douglas Gregorbb7930c2010-02-10 19:54:31 +00001978}
1979
Douglas Gregor00eace12010-02-21 18:29:16 +00001980Decl *ASTNodeImporter::VisitCXXMethodDecl(CXXMethodDecl *D) {
1981 return VisitFunctionDecl(D);
1982}
1983
1984Decl *ASTNodeImporter::VisitCXXConstructorDecl(CXXConstructorDecl *D) {
1985 return VisitCXXMethodDecl(D);
1986}
1987
1988Decl *ASTNodeImporter::VisitCXXDestructorDecl(CXXDestructorDecl *D) {
1989 return VisitCXXMethodDecl(D);
1990}
1991
1992Decl *ASTNodeImporter::VisitCXXConversionDecl(CXXConversionDecl *D) {
1993 return VisitCXXMethodDecl(D);
1994}
1995
Douglas Gregor5c73e912010-02-11 00:48:18 +00001996Decl *ASTNodeImporter::VisitFieldDecl(FieldDecl *D) {
1997 // Import the major distinguishing characteristics of a variable.
1998 DeclContext *DC, *LexicalDC;
1999 DeclarationName Name;
Douglas Gregor5c73e912010-02-11 00:48:18 +00002000 SourceLocation Loc;
Douglas Gregorb4964f72010-02-15 23:54:17 +00002001 if (ImportDeclParts(D, DC, LexicalDC, Name, Loc))
2002 return 0;
2003
2004 // Import the type.
2005 QualType T = Importer.Import(D->getType());
2006 if (T.isNull())
Douglas Gregor5c73e912010-02-11 00:48:18 +00002007 return 0;
2008
2009 TypeSourceInfo *TInfo = Importer.Import(D->getTypeSourceInfo());
2010 Expr *BitWidth = Importer.Import(D->getBitWidth());
2011 if (!BitWidth && D->getBitWidth())
2012 return 0;
2013
2014 FieldDecl *ToField = FieldDecl::Create(Importer.getToContext(), DC,
2015 Loc, Name.getAsIdentifierInfo(),
2016 T, TInfo, BitWidth, D->isMutable());
Douglas Gregordd483172010-02-22 17:42:47 +00002017 ToField->setAccess(D->getAccess());
Douglas Gregor5c73e912010-02-11 00:48:18 +00002018 ToField->setLexicalDeclContext(LexicalDC);
Douglas Gregor8cdbe642010-02-12 23:44:20 +00002019 Importer.Imported(D, ToField);
Douglas Gregor5c73e912010-02-11 00:48:18 +00002020 LexicalDC->addDecl(ToField);
2021 return ToField;
2022}
2023
Francois Pichet783dd6e2010-11-21 06:08:52 +00002024Decl *ASTNodeImporter::VisitIndirectFieldDecl(IndirectFieldDecl *D) {
2025 // Import the major distinguishing characteristics of a variable.
2026 DeclContext *DC, *LexicalDC;
2027 DeclarationName Name;
2028 SourceLocation Loc;
2029 if (ImportDeclParts(D, DC, LexicalDC, Name, Loc))
2030 return 0;
2031
2032 // Import the type.
2033 QualType T = Importer.Import(D->getType());
2034 if (T.isNull())
2035 return 0;
2036
2037 NamedDecl **NamedChain =
2038 new (Importer.getToContext())NamedDecl*[D->getChainingSize()];
2039
2040 unsigned i = 0;
2041 for (IndirectFieldDecl::chain_iterator PI = D->chain_begin(),
2042 PE = D->chain_end(); PI != PE; ++PI) {
2043 Decl* D = Importer.Import(*PI);
2044 if (!D)
2045 return 0;
2046 NamedChain[i++] = cast<NamedDecl>(D);
2047 }
2048
2049 IndirectFieldDecl *ToIndirectField = IndirectFieldDecl::Create(
2050 Importer.getToContext(), DC,
2051 Loc, Name.getAsIdentifierInfo(), T,
2052 NamedChain, D->getChainingSize());
2053 ToIndirectField->setAccess(D->getAccess());
2054 ToIndirectField->setLexicalDeclContext(LexicalDC);
2055 Importer.Imported(D, ToIndirectField);
2056 LexicalDC->addDecl(ToIndirectField);
2057 return ToIndirectField;
2058}
2059
Douglas Gregor7244b0b2010-02-17 00:34:30 +00002060Decl *ASTNodeImporter::VisitObjCIvarDecl(ObjCIvarDecl *D) {
2061 // Import the major distinguishing characteristics of an ivar.
2062 DeclContext *DC, *LexicalDC;
2063 DeclarationName Name;
2064 SourceLocation Loc;
2065 if (ImportDeclParts(D, DC, LexicalDC, Name, Loc))
2066 return 0;
2067
2068 // Determine whether we've already imported this ivar
2069 for (DeclContext::lookup_result Lookup = DC->lookup(Name);
2070 Lookup.first != Lookup.second;
2071 ++Lookup.first) {
2072 if (ObjCIvarDecl *FoundIvar = dyn_cast<ObjCIvarDecl>(*Lookup.first)) {
2073 if (Importer.IsStructurallyEquivalent(D->getType(),
2074 FoundIvar->getType())) {
2075 Importer.Imported(D, FoundIvar);
2076 return FoundIvar;
2077 }
2078
2079 Importer.ToDiag(Loc, diag::err_odr_ivar_type_inconsistent)
2080 << Name << D->getType() << FoundIvar->getType();
2081 Importer.ToDiag(FoundIvar->getLocation(), diag::note_odr_value_here)
2082 << FoundIvar->getType();
2083 return 0;
2084 }
2085 }
2086
2087 // Import the type.
2088 QualType T = Importer.Import(D->getType());
2089 if (T.isNull())
2090 return 0;
2091
2092 TypeSourceInfo *TInfo = Importer.Import(D->getTypeSourceInfo());
2093 Expr *BitWidth = Importer.Import(D->getBitWidth());
2094 if (!BitWidth && D->getBitWidth())
2095 return 0;
2096
Daniel Dunbarfe3ead72010-04-02 20:10:03 +00002097 ObjCIvarDecl *ToIvar = ObjCIvarDecl::Create(Importer.getToContext(),
2098 cast<ObjCContainerDecl>(DC),
Douglas Gregor7244b0b2010-02-17 00:34:30 +00002099 Loc, Name.getAsIdentifierInfo(),
2100 T, TInfo, D->getAccessControl(),
Fariborz Jahanianaea8e1e2010-07-17 18:35:47 +00002101 BitWidth, D->getSynthesize());
Douglas Gregor7244b0b2010-02-17 00:34:30 +00002102 ToIvar->setLexicalDeclContext(LexicalDC);
2103 Importer.Imported(D, ToIvar);
2104 LexicalDC->addDecl(ToIvar);
2105 return ToIvar;
2106
2107}
2108
Douglas Gregorbb7930c2010-02-10 19:54:31 +00002109Decl *ASTNodeImporter::VisitVarDecl(VarDecl *D) {
2110 // Import the major distinguishing characteristics of a variable.
2111 DeclContext *DC, *LexicalDC;
2112 DeclarationName Name;
Douglas Gregorbb7930c2010-02-10 19:54:31 +00002113 SourceLocation Loc;
Douglas Gregorb4964f72010-02-15 23:54:17 +00002114 if (ImportDeclParts(D, DC, LexicalDC, Name, Loc))
Douglas Gregor3aed6cd2010-02-08 21:09:39 +00002115 return 0;
2116
Douglas Gregor3aed6cd2010-02-08 21:09:39 +00002117 // Try to find a variable in our own ("to") context with the same name and
2118 // in the same context as the variable we're importing.
Douglas Gregor62d311f2010-02-09 19:21:46 +00002119 if (D->isFileVarDecl()) {
Douglas Gregor3aed6cd2010-02-08 21:09:39 +00002120 VarDecl *MergeWithVar = 0;
2121 llvm::SmallVector<NamedDecl *, 4> ConflictingDecls;
2122 unsigned IDNS = Decl::IDNS_Ordinary;
Douglas Gregor62d311f2010-02-09 19:21:46 +00002123 for (DeclContext::lookup_result Lookup = DC->lookup(Name);
Douglas Gregor3aed6cd2010-02-08 21:09:39 +00002124 Lookup.first != Lookup.second;
2125 ++Lookup.first) {
2126 if (!(*Lookup.first)->isInIdentifierNamespace(IDNS))
2127 continue;
2128
2129 if (VarDecl *FoundVar = dyn_cast<VarDecl>(*Lookup.first)) {
2130 // We have found a variable that we may need to merge with. Check it.
2131 if (isExternalLinkage(FoundVar->getLinkage()) &&
2132 isExternalLinkage(D->getLinkage())) {
Douglas Gregorb4964f72010-02-15 23:54:17 +00002133 if (Importer.IsStructurallyEquivalent(D->getType(),
2134 FoundVar->getType())) {
Douglas Gregor3aed6cd2010-02-08 21:09:39 +00002135 MergeWithVar = FoundVar;
2136 break;
2137 }
2138
Douglas Gregor56521c52010-02-12 17:23:39 +00002139 const ArrayType *FoundArray
2140 = Importer.getToContext().getAsArrayType(FoundVar->getType());
2141 const ArrayType *TArray
Douglas Gregorb4964f72010-02-15 23:54:17 +00002142 = Importer.getToContext().getAsArrayType(D->getType());
Douglas Gregor56521c52010-02-12 17:23:39 +00002143 if (FoundArray && TArray) {
2144 if (isa<IncompleteArrayType>(FoundArray) &&
2145 isa<ConstantArrayType>(TArray)) {
Douglas Gregorb4964f72010-02-15 23:54:17 +00002146 // Import the type.
2147 QualType T = Importer.Import(D->getType());
2148 if (T.isNull())
2149 return 0;
2150
Douglas Gregor56521c52010-02-12 17:23:39 +00002151 FoundVar->setType(T);
2152 MergeWithVar = FoundVar;
2153 break;
2154 } else if (isa<IncompleteArrayType>(TArray) &&
2155 isa<ConstantArrayType>(FoundArray)) {
2156 MergeWithVar = FoundVar;
2157 break;
Douglas Gregor2fbe5582010-02-10 17:16:49 +00002158 }
2159 }
2160
Douglas Gregor3aed6cd2010-02-08 21:09:39 +00002161 Importer.ToDiag(Loc, diag::err_odr_variable_type_inconsistent)
Douglas Gregorb4964f72010-02-15 23:54:17 +00002162 << Name << D->getType() << FoundVar->getType();
Douglas Gregor3aed6cd2010-02-08 21:09:39 +00002163 Importer.ToDiag(FoundVar->getLocation(), diag::note_odr_value_here)
2164 << FoundVar->getType();
2165 }
2166 }
2167
2168 ConflictingDecls.push_back(*Lookup.first);
2169 }
2170
2171 if (MergeWithVar) {
2172 // An equivalent variable with external linkage has been found. Link
2173 // the two declarations, then merge them.
Douglas Gregor8cdbe642010-02-12 23:44:20 +00002174 Importer.Imported(D, MergeWithVar);
Douglas Gregor3aed6cd2010-02-08 21:09:39 +00002175
2176 if (VarDecl *DDef = D->getDefinition()) {
2177 if (VarDecl *ExistingDef = MergeWithVar->getDefinition()) {
2178 Importer.ToDiag(ExistingDef->getLocation(),
2179 diag::err_odr_variable_multiple_def)
2180 << Name;
2181 Importer.FromDiag(DDef->getLocation(), diag::note_odr_defined_here);
2182 } else {
2183 Expr *Init = Importer.Import(DDef->getInit());
Douglas Gregord5058122010-02-11 01:19:42 +00002184 MergeWithVar->setInit(Init);
Douglas Gregor3aed6cd2010-02-08 21:09:39 +00002185 }
2186 }
2187
2188 return MergeWithVar;
2189 }
2190
2191 if (!ConflictingDecls.empty()) {
2192 Name = Importer.HandleNameConflict(Name, DC, IDNS,
2193 ConflictingDecls.data(),
2194 ConflictingDecls.size());
2195 if (!Name)
2196 return 0;
2197 }
2198 }
Douglas Gregorfa7a0e52010-02-10 17:47:19 +00002199
Douglas Gregorb4964f72010-02-15 23:54:17 +00002200 // Import the type.
2201 QualType T = Importer.Import(D->getType());
2202 if (T.isNull())
2203 return 0;
2204
Douglas Gregor3aed6cd2010-02-08 21:09:39 +00002205 // Create the imported variable.
Douglas Gregorfa7a0e52010-02-10 17:47:19 +00002206 TypeSourceInfo *TInfo = Importer.Import(D->getTypeSourceInfo());
Douglas Gregor3aed6cd2010-02-08 21:09:39 +00002207 VarDecl *ToVar = VarDecl::Create(Importer.getToContext(), DC, Loc,
2208 Name.getAsIdentifierInfo(), T, TInfo,
Douglas Gregorc4df4072010-04-19 22:54:31 +00002209 D->getStorageClass(),
2210 D->getStorageClassAsWritten());
John McCall3e11ebe2010-03-15 10:12:16 +00002211 // Import the qualifier, if any.
2212 if (D->getQualifier()) {
2213 NestedNameSpecifier *NNS = Importer.Import(D->getQualifier());
2214 SourceRange NNSRange = Importer.Import(D->getQualifierRange());
2215 ToVar->setQualifierInfo(NNS, NNSRange);
2216 }
Douglas Gregordd483172010-02-22 17:42:47 +00002217 ToVar->setAccess(D->getAccess());
Douglas Gregor62d311f2010-02-09 19:21:46 +00002218 ToVar->setLexicalDeclContext(LexicalDC);
Douglas Gregor8cdbe642010-02-12 23:44:20 +00002219 Importer.Imported(D, ToVar);
Douglas Gregor62d311f2010-02-09 19:21:46 +00002220 LexicalDC->addDecl(ToVar);
2221
Douglas Gregor3aed6cd2010-02-08 21:09:39 +00002222 // Merge the initializer.
2223 // FIXME: Can we really import any initializer? Alternatively, we could force
2224 // ourselves to import every declaration of a variable and then only use
2225 // getInit() here.
Douglas Gregord5058122010-02-11 01:19:42 +00002226 ToVar->setInit(Importer.Import(const_cast<Expr *>(D->getAnyInitializer())));
Douglas Gregor3aed6cd2010-02-08 21:09:39 +00002227
2228 // FIXME: Other bits to merge?
2229
2230 return ToVar;
2231}
2232
Douglas Gregor8b228d72010-02-17 21:22:52 +00002233Decl *ASTNodeImporter::VisitImplicitParamDecl(ImplicitParamDecl *D) {
2234 // Parameters are created in the translation unit's context, then moved
2235 // into the function declaration's context afterward.
2236 DeclContext *DC = Importer.getToContext().getTranslationUnitDecl();
2237
2238 // Import the name of this declaration.
2239 DeclarationName Name = Importer.Import(D->getDeclName());
2240 if (D->getDeclName() && !Name)
2241 return 0;
2242
2243 // Import the location of this declaration.
2244 SourceLocation Loc = Importer.Import(D->getLocation());
2245
2246 // Import the parameter's type.
2247 QualType T = Importer.Import(D->getType());
2248 if (T.isNull())
2249 return 0;
2250
2251 // Create the imported parameter.
2252 ImplicitParamDecl *ToParm
2253 = ImplicitParamDecl::Create(Importer.getToContext(), DC,
2254 Loc, Name.getAsIdentifierInfo(),
2255 T);
2256 return Importer.Imported(D, ToParm);
2257}
2258
Douglas Gregorbb7930c2010-02-10 19:54:31 +00002259Decl *ASTNodeImporter::VisitParmVarDecl(ParmVarDecl *D) {
2260 // Parameters are created in the translation unit's context, then moved
2261 // into the function declaration's context afterward.
2262 DeclContext *DC = Importer.getToContext().getTranslationUnitDecl();
2263
Douglas Gregorfa7a0e52010-02-10 17:47:19 +00002264 // Import the name of this declaration.
2265 DeclarationName Name = Importer.Import(D->getDeclName());
2266 if (D->getDeclName() && !Name)
2267 return 0;
2268
Douglas Gregorbb7930c2010-02-10 19:54:31 +00002269 // Import the location of this declaration.
2270 SourceLocation Loc = Importer.Import(D->getLocation());
2271
2272 // Import the parameter's type.
2273 QualType T = Importer.Import(D->getType());
2274 if (T.isNull())
2275 return 0;
2276
2277 // Create the imported parameter.
2278 TypeSourceInfo *TInfo = Importer.Import(D->getTypeSourceInfo());
2279 ParmVarDecl *ToParm = ParmVarDecl::Create(Importer.getToContext(), DC,
2280 Loc, Name.getAsIdentifierInfo(),
2281 T, TInfo, D->getStorageClass(),
Douglas Gregorc4df4072010-04-19 22:54:31 +00002282 D->getStorageClassAsWritten(),
Douglas Gregorbb7930c2010-02-10 19:54:31 +00002283 /*FIXME: Default argument*/ 0);
John McCallf3cd6652010-03-12 18:31:32 +00002284 ToParm->setHasInheritedDefaultArg(D->hasInheritedDefaultArg());
Douglas Gregor8cdbe642010-02-12 23:44:20 +00002285 return Importer.Imported(D, ToParm);
Douglas Gregorbb7930c2010-02-10 19:54:31 +00002286}
2287
Douglas Gregor43f54792010-02-17 02:12:47 +00002288Decl *ASTNodeImporter::VisitObjCMethodDecl(ObjCMethodDecl *D) {
2289 // Import the major distinguishing characteristics of a method.
2290 DeclContext *DC, *LexicalDC;
2291 DeclarationName Name;
2292 SourceLocation Loc;
2293 if (ImportDeclParts(D, DC, LexicalDC, Name, Loc))
2294 return 0;
2295
2296 for (DeclContext::lookup_result Lookup = DC->lookup(Name);
2297 Lookup.first != Lookup.second;
2298 ++Lookup.first) {
2299 if (ObjCMethodDecl *FoundMethod = dyn_cast<ObjCMethodDecl>(*Lookup.first)) {
2300 if (FoundMethod->isInstanceMethod() != D->isInstanceMethod())
2301 continue;
2302
2303 // Check return types.
2304 if (!Importer.IsStructurallyEquivalent(D->getResultType(),
2305 FoundMethod->getResultType())) {
2306 Importer.ToDiag(Loc, diag::err_odr_objc_method_result_type_inconsistent)
2307 << D->isInstanceMethod() << Name
2308 << D->getResultType() << FoundMethod->getResultType();
2309 Importer.ToDiag(FoundMethod->getLocation(),
2310 diag::note_odr_objc_method_here)
2311 << D->isInstanceMethod() << Name;
2312 return 0;
2313 }
2314
2315 // Check the number of parameters.
2316 if (D->param_size() != FoundMethod->param_size()) {
2317 Importer.ToDiag(Loc, diag::err_odr_objc_method_num_params_inconsistent)
2318 << D->isInstanceMethod() << Name
2319 << D->param_size() << FoundMethod->param_size();
2320 Importer.ToDiag(FoundMethod->getLocation(),
2321 diag::note_odr_objc_method_here)
2322 << D->isInstanceMethod() << Name;
2323 return 0;
2324 }
2325
2326 // Check parameter types.
2327 for (ObjCMethodDecl::param_iterator P = D->param_begin(),
2328 PEnd = D->param_end(), FoundP = FoundMethod->param_begin();
2329 P != PEnd; ++P, ++FoundP) {
2330 if (!Importer.IsStructurallyEquivalent((*P)->getType(),
2331 (*FoundP)->getType())) {
2332 Importer.FromDiag((*P)->getLocation(),
2333 diag::err_odr_objc_method_param_type_inconsistent)
2334 << D->isInstanceMethod() << Name
2335 << (*P)->getType() << (*FoundP)->getType();
2336 Importer.ToDiag((*FoundP)->getLocation(), diag::note_odr_value_here)
2337 << (*FoundP)->getType();
2338 return 0;
2339 }
2340 }
2341
2342 // Check variadic/non-variadic.
2343 // Check the number of parameters.
2344 if (D->isVariadic() != FoundMethod->isVariadic()) {
2345 Importer.ToDiag(Loc, diag::err_odr_objc_method_variadic_inconsistent)
2346 << D->isInstanceMethod() << Name;
2347 Importer.ToDiag(FoundMethod->getLocation(),
2348 diag::note_odr_objc_method_here)
2349 << D->isInstanceMethod() << Name;
2350 return 0;
2351 }
2352
2353 // FIXME: Any other bits we need to merge?
2354 return Importer.Imported(D, FoundMethod);
2355 }
2356 }
2357
2358 // Import the result type.
2359 QualType ResultTy = Importer.Import(D->getResultType());
2360 if (ResultTy.isNull())
2361 return 0;
2362
Douglas Gregor12852d92010-03-08 14:59:44 +00002363 TypeSourceInfo *ResultTInfo = Importer.Import(D->getResultTypeSourceInfo());
2364
Douglas Gregor43f54792010-02-17 02:12:47 +00002365 ObjCMethodDecl *ToMethod
2366 = ObjCMethodDecl::Create(Importer.getToContext(),
2367 Loc,
2368 Importer.Import(D->getLocEnd()),
2369 Name.getObjCSelector(),
Douglas Gregor12852d92010-03-08 14:59:44 +00002370 ResultTy, ResultTInfo, DC,
Douglas Gregor43f54792010-02-17 02:12:47 +00002371 D->isInstanceMethod(),
2372 D->isVariadic(),
2373 D->isSynthesized(),
Fariborz Jahanian6e7e8cc2010-07-22 18:24:20 +00002374 D->isDefined(),
Douglas Gregor43f54792010-02-17 02:12:47 +00002375 D->getImplementationControl());
2376
2377 // FIXME: When we decide to merge method definitions, we'll need to
2378 // deal with implicit parameters.
2379
2380 // Import the parameters
2381 llvm::SmallVector<ParmVarDecl *, 5> ToParams;
2382 for (ObjCMethodDecl::param_iterator FromP = D->param_begin(),
2383 FromPEnd = D->param_end();
2384 FromP != FromPEnd;
2385 ++FromP) {
2386 ParmVarDecl *ToP = cast_or_null<ParmVarDecl>(Importer.Import(*FromP));
2387 if (!ToP)
2388 return 0;
2389
2390 ToParams.push_back(ToP);
2391 }
2392
2393 // Set the parameters.
2394 for (unsigned I = 0, N = ToParams.size(); I != N; ++I) {
2395 ToParams[I]->setOwningFunction(ToMethod);
2396 ToMethod->addDecl(ToParams[I]);
2397 }
2398 ToMethod->setMethodParams(Importer.getToContext(),
Fariborz Jahaniancdabb312010-04-09 15:40:42 +00002399 ToParams.data(), ToParams.size(),
2400 ToParams.size());
Douglas Gregor43f54792010-02-17 02:12:47 +00002401
2402 ToMethod->setLexicalDeclContext(LexicalDC);
2403 Importer.Imported(D, ToMethod);
2404 LexicalDC->addDecl(ToMethod);
2405 return ToMethod;
2406}
2407
Douglas Gregor84c51c32010-02-18 01:47:50 +00002408Decl *ASTNodeImporter::VisitObjCCategoryDecl(ObjCCategoryDecl *D) {
2409 // Import the major distinguishing characteristics of a category.
2410 DeclContext *DC, *LexicalDC;
2411 DeclarationName Name;
2412 SourceLocation Loc;
2413 if (ImportDeclParts(D, DC, LexicalDC, Name, Loc))
2414 return 0;
2415
2416 ObjCInterfaceDecl *ToInterface
2417 = cast_or_null<ObjCInterfaceDecl>(Importer.Import(D->getClassInterface()));
2418 if (!ToInterface)
2419 return 0;
2420
2421 // Determine if we've already encountered this category.
2422 ObjCCategoryDecl *MergeWithCategory
2423 = ToInterface->FindCategoryDeclaration(Name.getAsIdentifierInfo());
2424 ObjCCategoryDecl *ToCategory = MergeWithCategory;
2425 if (!ToCategory) {
2426 ToCategory = ObjCCategoryDecl::Create(Importer.getToContext(), DC,
2427 Importer.Import(D->getAtLoc()),
2428 Loc,
2429 Importer.Import(D->getCategoryNameLoc()),
2430 Name.getAsIdentifierInfo());
2431 ToCategory->setLexicalDeclContext(LexicalDC);
2432 LexicalDC->addDecl(ToCategory);
2433 Importer.Imported(D, ToCategory);
2434
2435 // Link this category into its class's category list.
2436 ToCategory->setClassInterface(ToInterface);
2437 ToCategory->insertNextClassCategory();
2438
2439 // Import protocols
2440 llvm::SmallVector<ObjCProtocolDecl *, 4> Protocols;
2441 llvm::SmallVector<SourceLocation, 4> ProtocolLocs;
2442 ObjCCategoryDecl::protocol_loc_iterator FromProtoLoc
2443 = D->protocol_loc_begin();
2444 for (ObjCCategoryDecl::protocol_iterator FromProto = D->protocol_begin(),
2445 FromProtoEnd = D->protocol_end();
2446 FromProto != FromProtoEnd;
2447 ++FromProto, ++FromProtoLoc) {
2448 ObjCProtocolDecl *ToProto
2449 = cast_or_null<ObjCProtocolDecl>(Importer.Import(*FromProto));
2450 if (!ToProto)
2451 return 0;
2452 Protocols.push_back(ToProto);
2453 ProtocolLocs.push_back(Importer.Import(*FromProtoLoc));
2454 }
2455
2456 // FIXME: If we're merging, make sure that the protocol list is the same.
2457 ToCategory->setProtocolList(Protocols.data(), Protocols.size(),
2458 ProtocolLocs.data(), Importer.getToContext());
2459
2460 } else {
2461 Importer.Imported(D, ToCategory);
2462 }
2463
2464 // Import all of the members of this category.
Douglas Gregor968d6332010-02-21 18:24:45 +00002465 ImportDeclContext(D);
Douglas Gregor84c51c32010-02-18 01:47:50 +00002466
2467 // If we have an implementation, import it as well.
2468 if (D->getImplementation()) {
2469 ObjCCategoryImplDecl *Impl
2470 = cast<ObjCCategoryImplDecl>(Importer.Import(D->getImplementation()));
2471 if (!Impl)
2472 return 0;
2473
2474 ToCategory->setImplementation(Impl);
2475 }
2476
2477 return ToCategory;
2478}
2479
Douglas Gregor98d156a2010-02-17 16:12:00 +00002480Decl *ASTNodeImporter::VisitObjCProtocolDecl(ObjCProtocolDecl *D) {
Douglas Gregor84c51c32010-02-18 01:47:50 +00002481 // Import the major distinguishing characteristics of a protocol.
Douglas Gregor98d156a2010-02-17 16:12:00 +00002482 DeclContext *DC, *LexicalDC;
2483 DeclarationName Name;
2484 SourceLocation Loc;
2485 if (ImportDeclParts(D, DC, LexicalDC, Name, Loc))
2486 return 0;
2487
2488 ObjCProtocolDecl *MergeWithProtocol = 0;
2489 for (DeclContext::lookup_result Lookup = DC->lookup(Name);
2490 Lookup.first != Lookup.second;
2491 ++Lookup.first) {
2492 if (!(*Lookup.first)->isInIdentifierNamespace(Decl::IDNS_ObjCProtocol))
2493 continue;
2494
2495 if ((MergeWithProtocol = dyn_cast<ObjCProtocolDecl>(*Lookup.first)))
2496 break;
2497 }
2498
2499 ObjCProtocolDecl *ToProto = MergeWithProtocol;
2500 if (!ToProto || ToProto->isForwardDecl()) {
2501 if (!ToProto) {
2502 ToProto = ObjCProtocolDecl::Create(Importer.getToContext(), DC, Loc,
2503 Name.getAsIdentifierInfo());
2504 ToProto->setForwardDecl(D->isForwardDecl());
2505 ToProto->setLexicalDeclContext(LexicalDC);
2506 LexicalDC->addDecl(ToProto);
2507 }
2508 Importer.Imported(D, ToProto);
2509
2510 // Import protocols
2511 llvm::SmallVector<ObjCProtocolDecl *, 4> Protocols;
2512 llvm::SmallVector<SourceLocation, 4> ProtocolLocs;
2513 ObjCProtocolDecl::protocol_loc_iterator
2514 FromProtoLoc = D->protocol_loc_begin();
2515 for (ObjCProtocolDecl::protocol_iterator FromProto = D->protocol_begin(),
2516 FromProtoEnd = D->protocol_end();
2517 FromProto != FromProtoEnd;
2518 ++FromProto, ++FromProtoLoc) {
2519 ObjCProtocolDecl *ToProto
2520 = cast_or_null<ObjCProtocolDecl>(Importer.Import(*FromProto));
2521 if (!ToProto)
2522 return 0;
2523 Protocols.push_back(ToProto);
2524 ProtocolLocs.push_back(Importer.Import(*FromProtoLoc));
2525 }
2526
2527 // FIXME: If we're merging, make sure that the protocol list is the same.
2528 ToProto->setProtocolList(Protocols.data(), Protocols.size(),
2529 ProtocolLocs.data(), Importer.getToContext());
2530 } else {
2531 Importer.Imported(D, ToProto);
2532 }
2533
Douglas Gregor84c51c32010-02-18 01:47:50 +00002534 // Import all of the members of this protocol.
Douglas Gregor968d6332010-02-21 18:24:45 +00002535 ImportDeclContext(D);
Douglas Gregor98d156a2010-02-17 16:12:00 +00002536
2537 return ToProto;
2538}
2539
Douglas Gregor45635322010-02-16 01:20:57 +00002540Decl *ASTNodeImporter::VisitObjCInterfaceDecl(ObjCInterfaceDecl *D) {
2541 // Import the major distinguishing characteristics of an @interface.
2542 DeclContext *DC, *LexicalDC;
2543 DeclarationName Name;
2544 SourceLocation Loc;
2545 if (ImportDeclParts(D, DC, LexicalDC, Name, Loc))
2546 return 0;
2547
2548 ObjCInterfaceDecl *MergeWithIface = 0;
2549 for (DeclContext::lookup_result Lookup = DC->lookup(Name);
2550 Lookup.first != Lookup.second;
2551 ++Lookup.first) {
2552 if (!(*Lookup.first)->isInIdentifierNamespace(Decl::IDNS_Ordinary))
2553 continue;
2554
2555 if ((MergeWithIface = dyn_cast<ObjCInterfaceDecl>(*Lookup.first)))
2556 break;
2557 }
2558
2559 ObjCInterfaceDecl *ToIface = MergeWithIface;
2560 if (!ToIface || ToIface->isForwardDecl()) {
2561 if (!ToIface) {
2562 ToIface = ObjCInterfaceDecl::Create(Importer.getToContext(),
2563 DC, Loc,
2564 Name.getAsIdentifierInfo(),
Douglas Gregor1c283312010-08-11 12:19:30 +00002565 Importer.Import(D->getClassLoc()),
Douglas Gregor45635322010-02-16 01:20:57 +00002566 D->isForwardDecl(),
2567 D->isImplicitInterfaceDecl());
Douglas Gregor98d156a2010-02-17 16:12:00 +00002568 ToIface->setForwardDecl(D->isForwardDecl());
Douglas Gregor45635322010-02-16 01:20:57 +00002569 ToIface->setLexicalDeclContext(LexicalDC);
2570 LexicalDC->addDecl(ToIface);
2571 }
2572 Importer.Imported(D, ToIface);
2573
Douglas Gregor45635322010-02-16 01:20:57 +00002574 if (D->getSuperClass()) {
2575 ObjCInterfaceDecl *Super
2576 = cast_or_null<ObjCInterfaceDecl>(Importer.Import(D->getSuperClass()));
2577 if (!Super)
2578 return 0;
2579
2580 ToIface->setSuperClass(Super);
2581 ToIface->setSuperClassLoc(Importer.Import(D->getSuperClassLoc()));
2582 }
2583
2584 // Import protocols
2585 llvm::SmallVector<ObjCProtocolDecl *, 4> Protocols;
2586 llvm::SmallVector<SourceLocation, 4> ProtocolLocs;
2587 ObjCInterfaceDecl::protocol_loc_iterator
2588 FromProtoLoc = D->protocol_loc_begin();
Ted Kremenek0ef508d2010-09-01 01:21:15 +00002589
2590 // FIXME: Should we be usng all_referenced_protocol_begin() here?
Douglas Gregor45635322010-02-16 01:20:57 +00002591 for (ObjCInterfaceDecl::protocol_iterator FromProto = D->protocol_begin(),
2592 FromProtoEnd = D->protocol_end();
2593 FromProto != FromProtoEnd;
2594 ++FromProto, ++FromProtoLoc) {
2595 ObjCProtocolDecl *ToProto
2596 = cast_or_null<ObjCProtocolDecl>(Importer.Import(*FromProto));
2597 if (!ToProto)
2598 return 0;
2599 Protocols.push_back(ToProto);
2600 ProtocolLocs.push_back(Importer.Import(*FromProtoLoc));
2601 }
2602
2603 // FIXME: If we're merging, make sure that the protocol list is the same.
2604 ToIface->setProtocolList(Protocols.data(), Protocols.size(),
2605 ProtocolLocs.data(), Importer.getToContext());
2606
Douglas Gregor45635322010-02-16 01:20:57 +00002607 // Import @end range
2608 ToIface->setAtEndRange(Importer.Import(D->getAtEndRange()));
2609 } else {
2610 Importer.Imported(D, ToIface);
Douglas Gregor7244b0b2010-02-17 00:34:30 +00002611
2612 // Check for consistency of superclasses.
2613 DeclarationName FromSuperName, ToSuperName;
2614 if (D->getSuperClass())
2615 FromSuperName = Importer.Import(D->getSuperClass()->getDeclName());
2616 if (ToIface->getSuperClass())
2617 ToSuperName = ToIface->getSuperClass()->getDeclName();
2618 if (FromSuperName != ToSuperName) {
2619 Importer.ToDiag(ToIface->getLocation(),
2620 diag::err_odr_objc_superclass_inconsistent)
2621 << ToIface->getDeclName();
2622 if (ToIface->getSuperClass())
2623 Importer.ToDiag(ToIface->getSuperClassLoc(),
2624 diag::note_odr_objc_superclass)
2625 << ToIface->getSuperClass()->getDeclName();
2626 else
2627 Importer.ToDiag(ToIface->getLocation(),
2628 diag::note_odr_objc_missing_superclass);
2629 if (D->getSuperClass())
2630 Importer.FromDiag(D->getSuperClassLoc(),
2631 diag::note_odr_objc_superclass)
2632 << D->getSuperClass()->getDeclName();
2633 else
2634 Importer.FromDiag(D->getLocation(),
2635 diag::note_odr_objc_missing_superclass);
2636 return 0;
2637 }
Douglas Gregor45635322010-02-16 01:20:57 +00002638 }
2639
Douglas Gregor84c51c32010-02-18 01:47:50 +00002640 // Import categories. When the categories themselves are imported, they'll
2641 // hook themselves into this interface.
2642 for (ObjCCategoryDecl *FromCat = D->getCategoryList(); FromCat;
2643 FromCat = FromCat->getNextClassCategory())
2644 Importer.Import(FromCat);
2645
Douglas Gregor45635322010-02-16 01:20:57 +00002646 // Import all of the members of this class.
Douglas Gregor968d6332010-02-21 18:24:45 +00002647 ImportDeclContext(D);
Douglas Gregor45635322010-02-16 01:20:57 +00002648
2649 // If we have an @implementation, import it as well.
2650 if (D->getImplementation()) {
2651 ObjCImplementationDecl *Impl
2652 = cast<ObjCImplementationDecl>(Importer.Import(D->getImplementation()));
2653 if (!Impl)
2654 return 0;
2655
2656 ToIface->setImplementation(Impl);
2657 }
2658
Douglas Gregor98d156a2010-02-17 16:12:00 +00002659 return ToIface;
Douglas Gregor45635322010-02-16 01:20:57 +00002660}
2661
Douglas Gregora11c4582010-02-17 18:02:10 +00002662Decl *ASTNodeImporter::VisitObjCPropertyDecl(ObjCPropertyDecl *D) {
2663 // Import the major distinguishing characteristics of an @property.
2664 DeclContext *DC, *LexicalDC;
2665 DeclarationName Name;
2666 SourceLocation Loc;
2667 if (ImportDeclParts(D, DC, LexicalDC, Name, Loc))
2668 return 0;
2669
2670 // Check whether we have already imported this property.
2671 for (DeclContext::lookup_result Lookup = DC->lookup(Name);
2672 Lookup.first != Lookup.second;
2673 ++Lookup.first) {
2674 if (ObjCPropertyDecl *FoundProp
2675 = dyn_cast<ObjCPropertyDecl>(*Lookup.first)) {
2676 // Check property types.
2677 if (!Importer.IsStructurallyEquivalent(D->getType(),
2678 FoundProp->getType())) {
2679 Importer.ToDiag(Loc, diag::err_odr_objc_property_type_inconsistent)
2680 << Name << D->getType() << FoundProp->getType();
2681 Importer.ToDiag(FoundProp->getLocation(), diag::note_odr_value_here)
2682 << FoundProp->getType();
2683 return 0;
2684 }
2685
2686 // FIXME: Check property attributes, getters, setters, etc.?
2687
2688 // Consider these properties to be equivalent.
2689 Importer.Imported(D, FoundProp);
2690 return FoundProp;
2691 }
2692 }
2693
2694 // Import the type.
John McCall339bb662010-06-04 20:50:08 +00002695 TypeSourceInfo *T = Importer.Import(D->getTypeSourceInfo());
2696 if (!T)
Douglas Gregora11c4582010-02-17 18:02:10 +00002697 return 0;
2698
2699 // Create the new property.
2700 ObjCPropertyDecl *ToProperty
2701 = ObjCPropertyDecl::Create(Importer.getToContext(), DC, Loc,
2702 Name.getAsIdentifierInfo(),
2703 Importer.Import(D->getAtLoc()),
2704 T,
2705 D->getPropertyImplementation());
2706 Importer.Imported(D, ToProperty);
2707 ToProperty->setLexicalDeclContext(LexicalDC);
2708 LexicalDC->addDecl(ToProperty);
2709
2710 ToProperty->setPropertyAttributes(D->getPropertyAttributes());
Fariborz Jahanian3bf0ded2010-06-22 23:20:40 +00002711 ToProperty->setPropertyAttributesAsWritten(
2712 D->getPropertyAttributesAsWritten());
Douglas Gregora11c4582010-02-17 18:02:10 +00002713 ToProperty->setGetterName(Importer.Import(D->getGetterName()));
2714 ToProperty->setSetterName(Importer.Import(D->getSetterName()));
2715 ToProperty->setGetterMethodDecl(
2716 cast_or_null<ObjCMethodDecl>(Importer.Import(D->getGetterMethodDecl())));
2717 ToProperty->setSetterMethodDecl(
2718 cast_or_null<ObjCMethodDecl>(Importer.Import(D->getSetterMethodDecl())));
2719 ToProperty->setPropertyIvarDecl(
2720 cast_or_null<ObjCIvarDecl>(Importer.Import(D->getPropertyIvarDecl())));
2721 return ToProperty;
2722}
2723
Douglas Gregor8661a722010-02-18 02:12:22 +00002724Decl *
2725ASTNodeImporter::VisitObjCForwardProtocolDecl(ObjCForwardProtocolDecl *D) {
2726 // Import the context of this declaration.
2727 DeclContext *DC = Importer.ImportContext(D->getDeclContext());
2728 if (!DC)
2729 return 0;
2730
2731 DeclContext *LexicalDC = DC;
2732 if (D->getDeclContext() != D->getLexicalDeclContext()) {
2733 LexicalDC = Importer.ImportContext(D->getLexicalDeclContext());
2734 if (!LexicalDC)
2735 return 0;
2736 }
2737
2738 // Import the location of this declaration.
2739 SourceLocation Loc = Importer.Import(D->getLocation());
2740
2741 llvm::SmallVector<ObjCProtocolDecl *, 4> Protocols;
2742 llvm::SmallVector<SourceLocation, 4> Locations;
2743 ObjCForwardProtocolDecl::protocol_loc_iterator FromProtoLoc
2744 = D->protocol_loc_begin();
2745 for (ObjCForwardProtocolDecl::protocol_iterator FromProto
2746 = D->protocol_begin(), FromProtoEnd = D->protocol_end();
2747 FromProto != FromProtoEnd;
2748 ++FromProto, ++FromProtoLoc) {
2749 ObjCProtocolDecl *ToProto
2750 = cast_or_null<ObjCProtocolDecl>(Importer.Import(*FromProto));
2751 if (!ToProto)
2752 continue;
2753
2754 Protocols.push_back(ToProto);
2755 Locations.push_back(Importer.Import(*FromProtoLoc));
2756 }
2757
2758 ObjCForwardProtocolDecl *ToForward
2759 = ObjCForwardProtocolDecl::Create(Importer.getToContext(), DC, Loc,
2760 Protocols.data(), Protocols.size(),
2761 Locations.data());
2762 ToForward->setLexicalDeclContext(LexicalDC);
2763 LexicalDC->addDecl(ToForward);
2764 Importer.Imported(D, ToForward);
2765 return ToForward;
2766}
2767
Douglas Gregor06537af2010-02-18 02:04:09 +00002768Decl *ASTNodeImporter::VisitObjCClassDecl(ObjCClassDecl *D) {
2769 // Import the context of this declaration.
2770 DeclContext *DC = Importer.ImportContext(D->getDeclContext());
2771 if (!DC)
2772 return 0;
2773
2774 DeclContext *LexicalDC = DC;
2775 if (D->getDeclContext() != D->getLexicalDeclContext()) {
2776 LexicalDC = Importer.ImportContext(D->getLexicalDeclContext());
2777 if (!LexicalDC)
2778 return 0;
2779 }
2780
2781 // Import the location of this declaration.
2782 SourceLocation Loc = Importer.Import(D->getLocation());
2783
2784 llvm::SmallVector<ObjCInterfaceDecl *, 4> Interfaces;
2785 llvm::SmallVector<SourceLocation, 4> Locations;
2786 for (ObjCClassDecl::iterator From = D->begin(), FromEnd = D->end();
2787 From != FromEnd; ++From) {
2788 ObjCInterfaceDecl *ToIface
2789 = cast_or_null<ObjCInterfaceDecl>(Importer.Import(From->getInterface()));
2790 if (!ToIface)
2791 continue;
2792
2793 Interfaces.push_back(ToIface);
2794 Locations.push_back(Importer.Import(From->getLocation()));
2795 }
2796
2797 ObjCClassDecl *ToClass = ObjCClassDecl::Create(Importer.getToContext(), DC,
2798 Loc,
2799 Interfaces.data(),
2800 Locations.data(),
2801 Interfaces.size());
2802 ToClass->setLexicalDeclContext(LexicalDC);
2803 LexicalDC->addDecl(ToClass);
2804 Importer.Imported(D, ToClass);
2805 return ToClass;
2806}
2807
Douglas Gregor7eeb5972010-02-11 19:21:55 +00002808//----------------------------------------------------------------------------
2809// Import Statements
2810//----------------------------------------------------------------------------
2811
2812Stmt *ASTNodeImporter::VisitStmt(Stmt *S) {
2813 Importer.FromDiag(S->getLocStart(), diag::err_unsupported_ast_node)
2814 << S->getStmtClassName();
2815 return 0;
2816}
2817
2818//----------------------------------------------------------------------------
2819// Import Expressions
2820//----------------------------------------------------------------------------
2821Expr *ASTNodeImporter::VisitExpr(Expr *E) {
2822 Importer.FromDiag(E->getLocStart(), diag::err_unsupported_ast_node)
2823 << E->getStmtClassName();
2824 return 0;
2825}
2826
Douglas Gregor52f820e2010-02-19 01:17:02 +00002827Expr *ASTNodeImporter::VisitDeclRefExpr(DeclRefExpr *E) {
2828 NestedNameSpecifier *Qualifier = 0;
2829 if (E->getQualifier()) {
2830 Qualifier = Importer.Import(E->getQualifier());
2831 if (!E->getQualifier())
2832 return 0;
2833 }
2834
2835 ValueDecl *ToD = cast_or_null<ValueDecl>(Importer.Import(E->getDecl()));
2836 if (!ToD)
2837 return 0;
2838
2839 QualType T = Importer.Import(E->getType());
2840 if (T.isNull())
2841 return 0;
2842
2843 return DeclRefExpr::Create(Importer.getToContext(), Qualifier,
2844 Importer.Import(E->getQualifierRange()),
2845 ToD,
2846 Importer.Import(E->getLocation()),
John McCall7decc9e2010-11-18 06:31:45 +00002847 T, E->getValueKind(),
Douglas Gregor52f820e2010-02-19 01:17:02 +00002848 /*FIXME:TemplateArgs=*/0);
2849}
2850
Douglas Gregor7eeb5972010-02-11 19:21:55 +00002851Expr *ASTNodeImporter::VisitIntegerLiteral(IntegerLiteral *E) {
2852 QualType T = Importer.Import(E->getType());
2853 if (T.isNull())
2854 return 0;
2855
Argyrios Kyrtzidis43b20572010-08-28 09:06:06 +00002856 return IntegerLiteral::Create(Importer.getToContext(),
2857 E->getValue(), T,
2858 Importer.Import(E->getLocation()));
Douglas Gregor7eeb5972010-02-11 19:21:55 +00002859}
2860
Douglas Gregor623421d2010-02-18 02:21:22 +00002861Expr *ASTNodeImporter::VisitCharacterLiteral(CharacterLiteral *E) {
2862 QualType T = Importer.Import(E->getType());
2863 if (T.isNull())
2864 return 0;
2865
2866 return new (Importer.getToContext()) CharacterLiteral(E->getValue(),
2867 E->isWide(), T,
2868 Importer.Import(E->getLocation()));
2869}
2870
Douglas Gregorc74247e2010-02-19 01:07:06 +00002871Expr *ASTNodeImporter::VisitParenExpr(ParenExpr *E) {
2872 Expr *SubExpr = Importer.Import(E->getSubExpr());
2873 if (!SubExpr)
2874 return 0;
2875
2876 return new (Importer.getToContext())
2877 ParenExpr(Importer.Import(E->getLParen()),
2878 Importer.Import(E->getRParen()),
2879 SubExpr);
2880}
2881
2882Expr *ASTNodeImporter::VisitUnaryOperator(UnaryOperator *E) {
2883 QualType T = Importer.Import(E->getType());
2884 if (T.isNull())
2885 return 0;
2886
2887 Expr *SubExpr = Importer.Import(E->getSubExpr());
2888 if (!SubExpr)
2889 return 0;
2890
2891 return new (Importer.getToContext()) UnaryOperator(SubExpr, E->getOpcode(),
John McCall7decc9e2010-11-18 06:31:45 +00002892 T, E->getValueKind(),
2893 E->getObjectKind(),
Douglas Gregorc74247e2010-02-19 01:07:06 +00002894 Importer.Import(E->getOperatorLoc()));
2895}
2896
Douglas Gregord8552cd2010-02-19 01:24:23 +00002897Expr *ASTNodeImporter::VisitSizeOfAlignOfExpr(SizeOfAlignOfExpr *E) {
2898 QualType ResultType = Importer.Import(E->getType());
2899
2900 if (E->isArgumentType()) {
2901 TypeSourceInfo *TInfo = Importer.Import(E->getArgumentTypeInfo());
2902 if (!TInfo)
2903 return 0;
2904
2905 return new (Importer.getToContext()) SizeOfAlignOfExpr(E->isSizeOf(),
2906 TInfo, ResultType,
2907 Importer.Import(E->getOperatorLoc()),
2908 Importer.Import(E->getRParenLoc()));
2909 }
2910
2911 Expr *SubExpr = Importer.Import(E->getArgumentExpr());
2912 if (!SubExpr)
2913 return 0;
2914
2915 return new (Importer.getToContext()) SizeOfAlignOfExpr(E->isSizeOf(),
2916 SubExpr, ResultType,
2917 Importer.Import(E->getOperatorLoc()),
2918 Importer.Import(E->getRParenLoc()));
2919}
2920
Douglas Gregorc74247e2010-02-19 01:07:06 +00002921Expr *ASTNodeImporter::VisitBinaryOperator(BinaryOperator *E) {
2922 QualType T = Importer.Import(E->getType());
2923 if (T.isNull())
2924 return 0;
2925
2926 Expr *LHS = Importer.Import(E->getLHS());
2927 if (!LHS)
2928 return 0;
2929
2930 Expr *RHS = Importer.Import(E->getRHS());
2931 if (!RHS)
2932 return 0;
2933
2934 return new (Importer.getToContext()) BinaryOperator(LHS, RHS, E->getOpcode(),
John McCall7decc9e2010-11-18 06:31:45 +00002935 T, E->getValueKind(),
2936 E->getObjectKind(),
Douglas Gregorc74247e2010-02-19 01:07:06 +00002937 Importer.Import(E->getOperatorLoc()));
2938}
2939
2940Expr *ASTNodeImporter::VisitCompoundAssignOperator(CompoundAssignOperator *E) {
2941 QualType T = Importer.Import(E->getType());
2942 if (T.isNull())
2943 return 0;
2944
2945 QualType CompLHSType = Importer.Import(E->getComputationLHSType());
2946 if (CompLHSType.isNull())
2947 return 0;
2948
2949 QualType CompResultType = Importer.Import(E->getComputationResultType());
2950 if (CompResultType.isNull())
2951 return 0;
2952
2953 Expr *LHS = Importer.Import(E->getLHS());
2954 if (!LHS)
2955 return 0;
2956
2957 Expr *RHS = Importer.Import(E->getRHS());
2958 if (!RHS)
2959 return 0;
2960
2961 return new (Importer.getToContext())
2962 CompoundAssignOperator(LHS, RHS, E->getOpcode(),
John McCall7decc9e2010-11-18 06:31:45 +00002963 T, E->getValueKind(),
2964 E->getObjectKind(),
2965 CompLHSType, CompResultType,
Douglas Gregorc74247e2010-02-19 01:07:06 +00002966 Importer.Import(E->getOperatorLoc()));
2967}
2968
John McCallcf142162010-08-07 06:22:56 +00002969bool ImportCastPath(CastExpr *E, CXXCastPath &Path) {
2970 if (E->path_empty()) return false;
2971
2972 // TODO: import cast paths
2973 return true;
2974}
2975
Douglas Gregor98c10182010-02-12 22:17:39 +00002976Expr *ASTNodeImporter::VisitImplicitCastExpr(ImplicitCastExpr *E) {
2977 QualType T = Importer.Import(E->getType());
2978 if (T.isNull())
2979 return 0;
2980
2981 Expr *SubExpr = Importer.Import(E->getSubExpr());
2982 if (!SubExpr)
2983 return 0;
John McCallcf142162010-08-07 06:22:56 +00002984
2985 CXXCastPath BasePath;
2986 if (ImportCastPath(E, BasePath))
2987 return 0;
2988
2989 return ImplicitCastExpr::Create(Importer.getToContext(), T, E->getCastKind(),
John McCall2536c6d2010-08-25 10:28:54 +00002990 SubExpr, &BasePath, E->getValueKind());
Douglas Gregor98c10182010-02-12 22:17:39 +00002991}
2992
Douglas Gregor5481d322010-02-19 01:32:14 +00002993Expr *ASTNodeImporter::VisitCStyleCastExpr(CStyleCastExpr *E) {
2994 QualType T = Importer.Import(E->getType());
2995 if (T.isNull())
2996 return 0;
2997
2998 Expr *SubExpr = Importer.Import(E->getSubExpr());
2999 if (!SubExpr)
3000 return 0;
3001
3002 TypeSourceInfo *TInfo = Importer.Import(E->getTypeInfoAsWritten());
3003 if (!TInfo && E->getTypeInfoAsWritten())
3004 return 0;
3005
John McCallcf142162010-08-07 06:22:56 +00003006 CXXCastPath BasePath;
3007 if (ImportCastPath(E, BasePath))
3008 return 0;
3009
John McCall7decc9e2010-11-18 06:31:45 +00003010 return CStyleCastExpr::Create(Importer.getToContext(), T,
3011 E->getValueKind(), E->getCastKind(),
John McCallcf142162010-08-07 06:22:56 +00003012 SubExpr, &BasePath, TInfo,
3013 Importer.Import(E->getLParenLoc()),
3014 Importer.Import(E->getRParenLoc()));
Douglas Gregor5481d322010-02-19 01:32:14 +00003015}
3016
Argyrios Kyrtzidisd0040642010-11-18 20:06:41 +00003017ASTImporter::ASTImporter(ASTContext &ToContext, FileManager &ToFileManager,
Chris Lattner5159f612010-11-23 08:35:12 +00003018 ASTContext &FromContext, FileManager &FromFileManager)
Douglas Gregor96e578d2010-02-05 17:54:41 +00003019 : ToContext(ToContext), FromContext(FromContext),
Chris Lattner5159f612010-11-23 08:35:12 +00003020 ToFileManager(ToFileManager), FromFileManager(FromFileManager) {
Douglas Gregor62d311f2010-02-09 19:21:46 +00003021 ImportedDecls[FromContext.getTranslationUnitDecl()]
3022 = ToContext.getTranslationUnitDecl();
3023}
3024
3025ASTImporter::~ASTImporter() { }
Douglas Gregor96e578d2010-02-05 17:54:41 +00003026
3027QualType ASTImporter::Import(QualType FromT) {
3028 if (FromT.isNull())
3029 return QualType();
3030
Douglas Gregorf65bbb32010-02-08 15:18:58 +00003031 // Check whether we've already imported this type.
3032 llvm::DenseMap<Type *, Type *>::iterator Pos
3033 = ImportedTypes.find(FromT.getTypePtr());
3034 if (Pos != ImportedTypes.end())
3035 return ToContext.getQualifiedType(Pos->second, FromT.getQualifiers());
Douglas Gregor96e578d2010-02-05 17:54:41 +00003036
Douglas Gregorf65bbb32010-02-08 15:18:58 +00003037 // Import the type
Douglas Gregor96e578d2010-02-05 17:54:41 +00003038 ASTNodeImporter Importer(*this);
3039 QualType ToT = Importer.Visit(FromT.getTypePtr());
3040 if (ToT.isNull())
3041 return ToT;
3042
Douglas Gregorf65bbb32010-02-08 15:18:58 +00003043 // Record the imported type.
3044 ImportedTypes[FromT.getTypePtr()] = ToT.getTypePtr();
3045
Douglas Gregor96e578d2010-02-05 17:54:41 +00003046 return ToContext.getQualifiedType(ToT, FromT.getQualifiers());
3047}
3048
Douglas Gregor62d311f2010-02-09 19:21:46 +00003049TypeSourceInfo *ASTImporter::Import(TypeSourceInfo *FromTSI) {
Douglas Gregorfa7a0e52010-02-10 17:47:19 +00003050 if (!FromTSI)
3051 return FromTSI;
3052
3053 // FIXME: For now we just create a "trivial" type source info based
Nick Lewycky19b9f952010-07-26 16:56:01 +00003054 // on the type and a single location. Implement a real version of this.
Douglas Gregorfa7a0e52010-02-10 17:47:19 +00003055 QualType T = Import(FromTSI->getType());
3056 if (T.isNull())
3057 return 0;
3058
3059 return ToContext.getTrivialTypeSourceInfo(T,
Abramo Bagnara1108e7b2010-05-20 10:00:11 +00003060 FromTSI->getTypeLoc().getSourceRange().getBegin());
Douglas Gregor62d311f2010-02-09 19:21:46 +00003061}
3062
3063Decl *ASTImporter::Import(Decl *FromD) {
3064 if (!FromD)
3065 return 0;
3066
3067 // Check whether we've already imported this declaration.
3068 llvm::DenseMap<Decl *, Decl *>::iterator Pos = ImportedDecls.find(FromD);
3069 if (Pos != ImportedDecls.end())
3070 return Pos->second;
3071
3072 // Import the type
3073 ASTNodeImporter Importer(*this);
3074 Decl *ToD = Importer.Visit(FromD);
3075 if (!ToD)
3076 return 0;
3077
3078 // Record the imported declaration.
3079 ImportedDecls[FromD] = ToD;
Douglas Gregorb4964f72010-02-15 23:54:17 +00003080
3081 if (TagDecl *FromTag = dyn_cast<TagDecl>(FromD)) {
3082 // Keep track of anonymous tags that have an associated typedef.
3083 if (FromTag->getTypedefForAnonDecl())
3084 AnonTagsWithPendingTypedefs.push_back(FromTag);
3085 } else if (TypedefDecl *FromTypedef = dyn_cast<TypedefDecl>(FromD)) {
3086 // When we've finished transforming a typedef, see whether it was the
3087 // typedef for an anonymous tag.
3088 for (llvm::SmallVector<TagDecl *, 4>::iterator
3089 FromTag = AnonTagsWithPendingTypedefs.begin(),
3090 FromTagEnd = AnonTagsWithPendingTypedefs.end();
3091 FromTag != FromTagEnd; ++FromTag) {
3092 if ((*FromTag)->getTypedefForAnonDecl() == FromTypedef) {
3093 if (TagDecl *ToTag = cast_or_null<TagDecl>(Import(*FromTag))) {
3094 // We found the typedef for an anonymous tag; link them.
3095 ToTag->setTypedefForAnonDecl(cast<TypedefDecl>(ToD));
3096 AnonTagsWithPendingTypedefs.erase(FromTag);
3097 break;
3098 }
3099 }
3100 }
3101 }
3102
Douglas Gregor62d311f2010-02-09 19:21:46 +00003103 return ToD;
3104}
3105
3106DeclContext *ASTImporter::ImportContext(DeclContext *FromDC) {
3107 if (!FromDC)
3108 return FromDC;
3109
3110 return cast_or_null<DeclContext>(Import(cast<Decl>(FromDC)));
3111}
3112
3113Expr *ASTImporter::Import(Expr *FromE) {
3114 if (!FromE)
3115 return 0;
3116
3117 return cast_or_null<Expr>(Import(cast<Stmt>(FromE)));
3118}
3119
3120Stmt *ASTImporter::Import(Stmt *FromS) {
3121 if (!FromS)
3122 return 0;
3123
Douglas Gregor7eeb5972010-02-11 19:21:55 +00003124 // Check whether we've already imported this declaration.
3125 llvm::DenseMap<Stmt *, Stmt *>::iterator Pos = ImportedStmts.find(FromS);
3126 if (Pos != ImportedStmts.end())
3127 return Pos->second;
3128
3129 // Import the type
3130 ASTNodeImporter Importer(*this);
3131 Stmt *ToS = Importer.Visit(FromS);
3132 if (!ToS)
3133 return 0;
3134
3135 // Record the imported declaration.
3136 ImportedStmts[FromS] = ToS;
3137 return ToS;
Douglas Gregor62d311f2010-02-09 19:21:46 +00003138}
3139
3140NestedNameSpecifier *ASTImporter::Import(NestedNameSpecifier *FromNNS) {
3141 if (!FromNNS)
3142 return 0;
3143
3144 // FIXME: Implement!
3145 return 0;
3146}
3147
3148SourceLocation ASTImporter::Import(SourceLocation FromLoc) {
3149 if (FromLoc.isInvalid())
3150 return SourceLocation();
3151
Douglas Gregor811663e2010-02-10 00:15:17 +00003152 SourceManager &FromSM = FromContext.getSourceManager();
3153
3154 // For now, map everything down to its spelling location, so that we
3155 // don't have to import macro instantiations.
3156 // FIXME: Import macro instantiations!
3157 FromLoc = FromSM.getSpellingLoc(FromLoc);
3158 std::pair<FileID, unsigned> Decomposed = FromSM.getDecomposedLoc(FromLoc);
3159 SourceManager &ToSM = ToContext.getSourceManager();
3160 return ToSM.getLocForStartOfFile(Import(Decomposed.first))
3161 .getFileLocWithOffset(Decomposed.second);
Douglas Gregor62d311f2010-02-09 19:21:46 +00003162}
3163
3164SourceRange ASTImporter::Import(SourceRange FromRange) {
3165 return SourceRange(Import(FromRange.getBegin()), Import(FromRange.getEnd()));
3166}
3167
Douglas Gregor811663e2010-02-10 00:15:17 +00003168FileID ASTImporter::Import(FileID FromID) {
Sebastian Redl99219f12010-09-30 01:03:06 +00003169 llvm::DenseMap<FileID, FileID>::iterator Pos
3170 = ImportedFileIDs.find(FromID);
Douglas Gregor811663e2010-02-10 00:15:17 +00003171 if (Pos != ImportedFileIDs.end())
3172 return Pos->second;
3173
3174 SourceManager &FromSM = FromContext.getSourceManager();
3175 SourceManager &ToSM = ToContext.getSourceManager();
3176 const SrcMgr::SLocEntry &FromSLoc = FromSM.getSLocEntry(FromID);
3177 assert(FromSLoc.isFile() && "Cannot handle macro instantiations yet");
3178
3179 // Include location of this file.
3180 SourceLocation ToIncludeLoc = Import(FromSLoc.getFile().getIncludeLoc());
3181
3182 // Map the FileID for to the "to" source manager.
3183 FileID ToID;
3184 const SrcMgr::ContentCache *Cache = FromSLoc.getFile().getContentCache();
3185 if (Cache->Entry) {
3186 // FIXME: We probably want to use getVirtualFile(), so we don't hit the
3187 // disk again
3188 // FIXME: We definitely want to re-use the existing MemoryBuffer, rather
3189 // than mmap the files several times.
Chris Lattner5159f612010-11-23 08:35:12 +00003190 const FileEntry *Entry = ToFileManager.getFile(Cache->Entry->getName());
Douglas Gregor811663e2010-02-10 00:15:17 +00003191 ToID = ToSM.createFileID(Entry, ToIncludeLoc,
3192 FromSLoc.getFile().getFileCharacteristic());
3193 } else {
3194 // FIXME: We want to re-use the existing MemoryBuffer!
Argyrios Kyrtzidisd0040642010-11-18 20:06:41 +00003195 const llvm::MemoryBuffer *
3196 FromBuf = Cache->getBuffer(FromContext.getDiagnostics(), FromSM);
Douglas Gregor811663e2010-02-10 00:15:17 +00003197 llvm::MemoryBuffer *ToBuf
Chris Lattner58c79342010-04-05 22:42:27 +00003198 = llvm::MemoryBuffer::getMemBufferCopy(FromBuf->getBuffer(),
Douglas Gregor811663e2010-02-10 00:15:17 +00003199 FromBuf->getBufferIdentifier());
3200 ToID = ToSM.createFileIDForMemBuffer(ToBuf);
3201 }
3202
3203
Sebastian Redl99219f12010-09-30 01:03:06 +00003204 ImportedFileIDs[FromID] = ToID;
Douglas Gregor811663e2010-02-10 00:15:17 +00003205 return ToID;
3206}
3207
Douglas Gregor96e578d2010-02-05 17:54:41 +00003208DeclarationName ASTImporter::Import(DeclarationName FromName) {
3209 if (!FromName)
3210 return DeclarationName();
3211
3212 switch (FromName.getNameKind()) {
3213 case DeclarationName::Identifier:
3214 return Import(FromName.getAsIdentifierInfo());
3215
3216 case DeclarationName::ObjCZeroArgSelector:
3217 case DeclarationName::ObjCOneArgSelector:
3218 case DeclarationName::ObjCMultiArgSelector:
3219 return Import(FromName.getObjCSelector());
3220
3221 case DeclarationName::CXXConstructorName: {
3222 QualType T = Import(FromName.getCXXNameType());
3223 if (T.isNull())
3224 return DeclarationName();
3225
3226 return ToContext.DeclarationNames.getCXXConstructorName(
3227 ToContext.getCanonicalType(T));
3228 }
3229
3230 case DeclarationName::CXXDestructorName: {
3231 QualType T = Import(FromName.getCXXNameType());
3232 if (T.isNull())
3233 return DeclarationName();
3234
3235 return ToContext.DeclarationNames.getCXXDestructorName(
3236 ToContext.getCanonicalType(T));
3237 }
3238
3239 case DeclarationName::CXXConversionFunctionName: {
3240 QualType T = Import(FromName.getCXXNameType());
3241 if (T.isNull())
3242 return DeclarationName();
3243
3244 return ToContext.DeclarationNames.getCXXConversionFunctionName(
3245 ToContext.getCanonicalType(T));
3246 }
3247
3248 case DeclarationName::CXXOperatorName:
3249 return ToContext.DeclarationNames.getCXXOperatorName(
3250 FromName.getCXXOverloadedOperator());
3251
3252 case DeclarationName::CXXLiteralOperatorName:
3253 return ToContext.DeclarationNames.getCXXLiteralOperatorName(
3254 Import(FromName.getCXXLiteralIdentifier()));
3255
3256 case DeclarationName::CXXUsingDirective:
3257 // FIXME: STATICS!
3258 return DeclarationName::getUsingDirectiveName();
3259 }
3260
3261 // Silence bogus GCC warning
3262 return DeclarationName();
3263}
3264
3265IdentifierInfo *ASTImporter::Import(IdentifierInfo *FromId) {
3266 if (!FromId)
3267 return 0;
3268
3269 return &ToContext.Idents.get(FromId->getName());
3270}
Douglas Gregor3aed6cd2010-02-08 21:09:39 +00003271
Douglas Gregor43f54792010-02-17 02:12:47 +00003272Selector ASTImporter::Import(Selector FromSel) {
3273 if (FromSel.isNull())
3274 return Selector();
3275
3276 llvm::SmallVector<IdentifierInfo *, 4> Idents;
3277 Idents.push_back(Import(FromSel.getIdentifierInfoForSlot(0)));
3278 for (unsigned I = 1, N = FromSel.getNumArgs(); I < N; ++I)
3279 Idents.push_back(Import(FromSel.getIdentifierInfoForSlot(I)));
3280 return ToContext.Selectors.getSelector(FromSel.getNumArgs(), Idents.data());
3281}
3282
Douglas Gregor3aed6cd2010-02-08 21:09:39 +00003283DeclarationName ASTImporter::HandleNameConflict(DeclarationName Name,
3284 DeclContext *DC,
3285 unsigned IDNS,
3286 NamedDecl **Decls,
3287 unsigned NumDecls) {
3288 return Name;
3289}
3290
3291DiagnosticBuilder ASTImporter::ToDiag(SourceLocation Loc, unsigned DiagID) {
Argyrios Kyrtzidisd0040642010-11-18 20:06:41 +00003292 return ToContext.getDiagnostics().Report(Loc, DiagID);
Douglas Gregor3aed6cd2010-02-08 21:09:39 +00003293}
3294
3295DiagnosticBuilder ASTImporter::FromDiag(SourceLocation Loc, unsigned DiagID) {
Argyrios Kyrtzidisd0040642010-11-18 20:06:41 +00003296 return FromContext.getDiagnostics().Report(Loc, DiagID);
Douglas Gregor3aed6cd2010-02-08 21:09:39 +00003297}
Douglas Gregor8cdbe642010-02-12 23:44:20 +00003298
3299Decl *ASTImporter::Imported(Decl *From, Decl *To) {
3300 ImportedDecls[From] = To;
3301 return To;
Daniel Dunbar9ced5422010-02-13 20:24:39 +00003302}
Douglas Gregorb4964f72010-02-15 23:54:17 +00003303
3304bool ASTImporter::IsStructurallyEquivalent(QualType From, QualType To) {
3305 llvm::DenseMap<Type *, Type *>::iterator Pos
3306 = ImportedTypes.find(From.getTypePtr());
3307 if (Pos != ImportedTypes.end() && ToContext.hasSameType(Import(From), To))
3308 return true;
3309
Argyrios Kyrtzidisd0040642010-11-18 20:06:41 +00003310 StructuralEquivalenceContext Ctx(FromContext, ToContext, NonEquivalentDecls);
Benjamin Kramer26d19c52010-02-18 13:02:13 +00003311 return Ctx.IsStructurallyEquivalent(From, To);
Douglas Gregorb4964f72010-02-15 23:54:17 +00003312}