diff options
| author | Argyrios Kyrtzidis <akyrtzi@gmail.com> | 2009-07-14 03:20:21 +0000 |
|---|---|---|
| committer | Argyrios Kyrtzidis <akyrtzi@gmail.com> | 2009-07-14 03:20:21 +0000 |
| commit | 1506d9bc2580f0fa4a4b4e128c462864ae8aa9e1 (patch) | |
| tree | 2a1bc026f2efe6a073b258b971b516bc44ebc601 /clang/lib/AST/Decl.cpp | |
| parent | 0736c5ca3b6d98d0b2d9df76e6e6c98c8ea45938 (diff) | |
| download | bcm5719-llvm-1506d9bc2580f0fa4a4b4e128c462864ae8aa9e1.tar.gz bcm5719-llvm-1506d9bc2580f0fa4a4b4e128c462864ae8aa9e1.zip | |
Introduce redecl_iterator, used for iterating over the redeclarations of a FunctionDecl or VarDecl.
It iterates over all the redeclarations, regardless of the starting point. For example:
1) int f();
2) int f();
3) int f();
if you have the (2) FunctionDecl and call redecls_begin/redecls_end to iterate, you'll get this sequence:
(2)
(1)
(3)
The motivation to introduce this was that, previously, if (3) was a function definition,
and you called getBody() at (2), it would not return it, since getBody() iterated over the previous declarations only,
so it would only check (2) and (1).
llvm-svn: 75604
Diffstat (limited to 'clang/lib/AST/Decl.cpp')
| -rw-r--r-- | clang/lib/AST/Decl.cpp | 38 |
1 files changed, 19 insertions, 19 deletions
diff --git a/clang/lib/AST/Decl.cpp b/clang/lib/AST/Decl.cpp index ae1df920125..19f17184185 100644 --- a/clang/lib/AST/Decl.cpp +++ b/clang/lib/AST/Decl.cpp @@ -351,11 +351,15 @@ bool VarDecl::isTentativeDefinition(ASTContext &Context) const { } const Expr *VarDecl::getDefinition(const VarDecl *&Def) const { - Def = this; - while (Def && !Def->getInit()) - Def = Def->getPreviousDeclaration(); + redecl_iterator I = redecls_begin(), E = redecls_end(); + while (I != E && !I->getInit()) + ++I; - return Def? Def->getInit() : 0; + if (I != E) { + Def = *I; + return I->getInit(); + } + return 0; } void VarDecl::setPreviousDeclaration(VarDecl *PrevDecl) { @@ -405,11 +409,10 @@ void FunctionDecl::Destroy(ASTContext& C) { Stmt *FunctionDecl::getBody(const FunctionDecl *&Definition) const { - for (const FunctionDecl *FD = this; - FD != 0; FD = FD->getPreviousDeclaration()) { - if (FD->Body) { - Definition = FD; - return FD->Body.get(getASTContext().getExternalSource()); + for (redecl_iterator I = redecls_begin(), E = redecls_end(); I != E; ++I) { + if (I->Body) { + Definition = *I; + return I->Body.get(getASTContext().getExternalSource()); } } @@ -417,10 +420,9 @@ Stmt *FunctionDecl::getBody(const FunctionDecl *&Definition) const { } Stmt *FunctionDecl::getBodyIfAvailable() const { - for (const FunctionDecl *FD = this; - FD != 0; FD = FD->getPreviousDeclaration()) { - if (FD->Body && !FD->Body.isOffset()) { - return FD->Body.get(0); + for (redecl_iterator I = redecls_begin(), E = redecls_end(); I != E; ++I) { + if (I->Body && !I->Body.isOffset()) { + return I->Body.get(0); } } @@ -568,11 +570,9 @@ bool FunctionDecl::hasActiveGNUInlineAttribute(ASTContext &Context) const { if (!isInline() || !hasAttr<GNUInlineAttr>()) return false; - for (const FunctionDecl *FD = getPreviousDeclaration(); FD; - FD = FD->getPreviousDeclaration()) { - if (FD->isInline() && !FD->hasAttr<GNUInlineAttr>()) + for (redecl_iterator I = redecls_begin(), E = redecls_end(); I != E; ++I) + if (I->isInline() && !I->hasAttr<GNUInlineAttr>()) return false; - } return true; } @@ -581,8 +581,8 @@ bool FunctionDecl::isExternGNUInline(ASTContext &Context) const { if (!hasActiveGNUInlineAttribute(Context)) return false; - for (const FunctionDecl *FD = this; FD; FD = FD->getPreviousDeclaration()) - if (FD->getStorageClass() == Extern && FD->hasAttr<GNUInlineAttr>()) + for (redecl_iterator I = redecls_begin(), E = redecls_end(); I != E; ++I) + if (I->getStorageClass() == Extern && I->hasAttr<GNUInlineAttr>()) return true; return false; |

