| 307 | } |
| 308 | |
| 309 | bool TraverseDecl(clang::Decl *d) { |
| 310 | if (!d) return true; |
| 311 | auto saved = currentContext; |
| 312 | if (clang::FunctionDecl::classof(d) || clang::RecordDecl::classof(d) || |
| 313 | clang::NamespaceDecl::classof(d) || clang::TemplateDecl::classof(d)) { |
| 314 | currentContext = llvm::dyn_cast<clang::NamedDecl>(d); |
| 315 | } |
| 316 | if (auto v = llvm::dyn_cast_or_null<clang::VarDecl>(d)) { |
| 317 | if (v->getInit() && !expr_stack.topExpr) { |
| 318 | expr_stack.topExpr = v->getInit(); |
| 319 | auto t = v->getType(); |
| 320 | expr_stack.topType = (t->isReferenceType() && !t.getNonReferenceType().isConstQualified()) ? |
| 321 | Annotator::Use_Address : Annotator::Use_Read; |
| 322 | } |
| 323 | } |
| 324 | Base::TraverseDecl(d); |
| 325 | currentContext = saved; |
| 326 | return true; |
| 327 | } |
| 328 | |
| 329 | // Since we cannot find up the parent of a node, we keep a stack of parents |
| 330 | bool TraverseStmt(clang::Stmt *s) { |
no outgoing calls
no test coverage detected