blob: 46882422e1ccfdc1e9cb688ace609378bca4d56d [file] [log] [blame]
Ted Kremenek9caf8b12007-10-18 00:24:38 +00001//===--- StmtIterator.cpp - Iterators for Statements ------------------------===//
2//
3// The LLVM Compiler Infrastructure
4//
Chris Lattner0bc735f2007-12-29 19:59:25 +00005// This file is distributed under the University of Illinois Open Source
6// License. See LICENSE.TXT for details.
Ted Kremenek9caf8b12007-10-18 00:24:38 +00007//
8//===----------------------------------------------------------------------===//
9//
10// This file defines internal methods for StmtIterator.
11//
12//===----------------------------------------------------------------------===//
13
14#include "clang/AST/StmtIterator.h"
Ted Kremenek9caf8b12007-10-18 00:24:38 +000015#include "clang/AST/Decl.h"
16
17using namespace clang;
18
Ted Kremenek92866e22007-10-29 20:50:16 +000019static inline VariableArrayType* FindVA(Type* t) {
20 while (ArrayType* vt = dyn_cast<ArrayType>(t)) {
21 if (VariableArrayType* vat = dyn_cast<VariableArrayType>(vt))
22 if (vat->getSizeExpr())
23 return vat;
24
25 t = vt->getElementType().getTypePtr();
Ted Kremenekc325e7f2007-10-18 18:19:31 +000026 }
27
Ted Kremenek92866e22007-10-29 20:50:16 +000028 return NULL;
29}
30
31void StmtIteratorBase::NextVA() {
32 assert (getVAPtr());
33
34 VariableArrayType* p = getVAPtr();
35 p = FindVA(p->getElementType().getTypePtr());
36 setVAPtr(p);
37
Ted Kremenek8a213de2008-10-07 23:35:42 +000038 if (p)
39 return;
40
41 if (inDecl()) {
42 if (VarDecl* VD = dyn_cast<VarDecl>(decl))
43 if (VD->Init)
44 return;
45
46 NextDecl();
47 }
48 else if (inDeclGroup()) {
49 if (VarDecl* VD = dyn_cast<VarDecl>(*DGI))
50 if (VD->Init)
51 return;
52
53 NextDecl();
54 }
55 else {
56 assert (inSizeOfTypeVA());
Eli Friedmanb0c05542008-05-21 05:06:46 +000057 assert(!decl);
Ted Kremenek699e9fb2007-12-14 22:52:23 +000058 RawVAPtr = 0;
Eli Friedmanb0c05542008-05-21 05:06:46 +000059 }
Ted Kremenek92866e22007-10-29 20:50:16 +000060}
61
62void StmtIteratorBase::NextDecl(bool ImmediateAdvance) {
Ted Kremenek92866e22007-10-29 20:50:16 +000063 assert (getVAPtr() == NULL);
Ted Kremenek92866e22007-10-29 20:50:16 +000064
Ted Kremenek3e6d1202008-10-07 23:04:14 +000065 if (inDecl()) {
66 assert (decl);
67
68 if (ImmediateAdvance)
69 decl = decl->getNextDeclarator();
70
71 for ( ; decl ; decl = decl->getNextDeclarator())
72 if (HandleDecl(decl))
73 return;
74 }
75 else {
76 assert (inDeclGroup());
77
78 if (ImmediateAdvance)
79 ++DGI;
80
81 for ( ; DGI != DGE; ++DGI)
82 if (HandleDecl(*DGI))
83 return;
84 }
Ted Kremenek92866e22007-10-29 20:50:16 +000085
Ted Kremenek3e6d1202008-10-07 23:04:14 +000086 RawVAPtr = 0;
87}
88
89bool StmtIteratorBase::HandleDecl(Decl* D) {
90
91 if (VarDecl* VD = dyn_cast<VarDecl>(D)) {
92 if (VariableArrayType* VAPtr = FindVA(VD->getType().getTypePtr())) {
93 setVAPtr(VAPtr);
94 return true;
Ted Kremenek92866e22007-10-29 20:50:16 +000095 }
Ted Kremenek3e6d1202008-10-07 23:04:14 +000096
97 if (VD->getInit())
98 return true;
Ted Kremenek92866e22007-10-29 20:50:16 +000099 }
Ted Kremenek3e6d1202008-10-07 23:04:14 +0000100 else if (TypedefDecl* TD = dyn_cast<TypedefDecl>(D)) {
101 if (VariableArrayType* VAPtr =
102 FindVA(TD->getUnderlyingType().getTypePtr())) {
103 setVAPtr(VAPtr);
104 return true;
105 }
Ted Kremenek103a1b42007-10-29 21:23:58 +0000106 }
Ted Kremenek3e6d1202008-10-07 23:04:14 +0000107 else if (EnumConstantDecl* ECD = dyn_cast<EnumConstantDecl>(D)) {
108 if (ECD->getInitExpr())
109 return true;
110 }
111
112 return false;
Ted Kremenek92866e22007-10-29 20:50:16 +0000113}
114
115StmtIteratorBase::StmtIteratorBase(ScopedDecl* d)
116 : decl(d), RawVAPtr(DeclMode) {
117 assert (decl);
118 NextDecl(false);
Ted Kremenekc7c326a2007-10-18 16:25:40 +0000119}
Ted Kremenek9caf8b12007-10-18 00:24:38 +0000120
Ted Kremenek3e6d1202008-10-07 23:04:14 +0000121StmtIteratorBase::StmtIteratorBase(Decl** dgi, Decl** dge)
122 : DGI(dgi), RawVAPtr(DeclGroupMode), DGE(dge) {
123 NextDecl(false);
124}
125
Ted Kremenek699e9fb2007-12-14 22:52:23 +0000126StmtIteratorBase::StmtIteratorBase(VariableArrayType* t)
Ted Kremenek3e6d1202008-10-07 23:04:14 +0000127: decl(0), RawVAPtr(SizeOfTypeVAMode) {
Ted Kremenek699e9fb2007-12-14 22:52:23 +0000128 RawVAPtr |= reinterpret_cast<uintptr_t>(t);
129}
130
Ted Kremenekb990f182007-10-25 22:24:19 +0000131Stmt*& StmtIteratorBase::GetDeclExpr() const {
Ted Kremenek3e6d1202008-10-07 23:04:14 +0000132
133 if (inDeclGroup()) {
134 VarDecl* VD = cast<VarDecl>(*DGI);
135 return VD->Init;
136 }
137
138 assert (inDecl() || inSizeOfTypeVA());
139
Ted Kremenek92866e22007-10-29 20:50:16 +0000140 if (VariableArrayType* VAPtr = getVAPtr()) {
141 assert (VAPtr->SizeExpr);
Ted Kremenekb3064042008-05-30 16:14:41 +0000142 return VAPtr->SizeExpr;
Ted Kremenekb990f182007-10-25 22:24:19 +0000143 }
Ted Kremenek3e6d1202008-10-07 23:04:14 +0000144
145 assert (inDecl());
Ted Kremenek92866e22007-10-29 20:50:16 +0000146
147 if (VarDecl* VD = dyn_cast<VarDecl>(decl)) {
148 assert (VD->Init);
Ted Kremenekb3064042008-05-30 16:14:41 +0000149 return VD->Init;
Ted Kremenek92866e22007-10-29 20:50:16 +0000150 }
151
152 EnumConstantDecl* ECD = cast<EnumConstantDecl>(decl);
Ted Kremenekb3064042008-05-30 16:14:41 +0000153 return ECD->Init;
Ted Kremenek9caf8b12007-10-18 00:24:38 +0000154}