Static Value-Flow Analysis
Loading...
Searching...
No Matches
CHGBuilder.cpp
Go to the documentation of this file.
1//===----- CHGBuilder.cpp -- Class hierarchy graph builder ---------------------------//
2//
3// SVF: Static Value-Flow Analysis
4//
5// Copyright (C) <2013-> <Yulei Sui>
6//
7
8// This program is free software: you can redistribute it and/or modify
9// it under the terms of the GNU Affero General Public License as published by
10// the Free Software Foundation, either version 3 of the License, or
11// (at your option) any later version.
12
13// This program is distributed in the hope that it will be useful,
14// but WITHOUT ANY WARRANTY; without even the implied warranty of
15// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
16// GNU Affero General Public License for more details.
17
18// You should have received a copy of the GNU Affero General Public License
19// along with this program. If not, see <http://www.gnu.org/licenses/>.
20//
21//===----------------------------------------------------------------------===//
22
23/*
24 * CHGBuilder.cpp
25 *
26 * Created on: Jun 4, 2021
27 * Author: Yulei Sui
28 */
29
30#include <set>
31#include <vector>
32#include <map>
33#include <fstream>
34#include <iostream>
35#include <iomanip> // setw() for formatting cout
36#include <assert.h>
37#include <stack>
38
39#include "SVF-LLVM/CHGBuilder.h"
40#include "Util/Options.h"
41#include "SVF-LLVM/CppUtil.h"
42#include "SVFIR/ObjTypeInfo.h"
43#include "Util/SVFUtil.h"
44#include "SVF-LLVM/LLVMUtil.h"
45#include "Util/PTAStat.h"
46#include "SVF-LLVM/LLVMModule.h"
48
49using namespace SVF;
50using namespace SVFUtil;
51using namespace cppUtil;
52using namespace LLVMUtil;
53using namespace std;
54
55const string pureVirtualFunName = "__cxa_pure_virtual";
56
57const string ztiLabel = "_ZTI";
58
63
65{
66
67 double timeStart, timeEnd;
70 {
71 DBOUT(DGENERAL, outs() << SVFUtil::pasMsg("construct CHGraph From module "
72 + M.getName().str() + "...\n"));
74 for (Module::const_global_iterator I = M.global_begin(), E = M.global_end(); I != E; ++I)
75 buildCHGNodes(&(*I));
76 for (Module::const_iterator F = M.begin(), E = M.end(); F != E; ++F)
77 buildCHGNodes(&(*F));
78 for (Module::const_iterator F = M.begin(), E = M.end(); F != E; ++F)
79 buildCHGEdges(&(*F));
80
82 }
83
84 DBOUT(DGENERAL, outs() << SVFUtil::pasMsg("build Internal Maps ...\n"));
86
89
90 if (Options::DumpCHA())
91 chg->dump("cha");
92}
93
95{
96 if (cppUtil::isValVtbl(globalvalue) && globalvalue->getNumOperands() > 0)
97 {
99 string className = getClassNameFromVtblObj(globalvalue->getName().str());
100 if (!chg->getNode(className))
101 createNode(className);
102
103 for (unsigned int ei = 0; ei < vtblStruct->getNumOperands(); ++ei)
104 {
105 const ConstantArray *vtbl = SVFUtil::dyn_cast<ConstantArray>(vtblStruct->getOperand(ei));
106 assert(vtbl && "Element of initializer not an array?");
107 for (u32_t i = 0; i < vtbl->getNumOperands(); ++i)
108 {
109 if(const ConstantExpr *ce = isCastConstantExpr(vtbl->getOperand(i)))
110 {
111 const Value* bitcastValue = ce->getOperand(0);
112 if (const Function* func = SVFUtil::dyn_cast<Function>(bitcastValue))
113 {
114 struct DemangledName dname = demangle(func->getName().str());
115 if (!chg->getNode(dname.className))
116 createNode(dname.className);
117 }
118 }
119 }
120 }
121 }
122}
123
125{
126 if (isConstructor(F) || isDestructor(F))
127 {
128 struct DemangledName dname = demangle(F->getName().str());
129 DBOUT(DCHA, outs() << "\t build CHANode for class " + dname.className + "...\n");
130 if (!chg->getNode(dname.className))
131 createNode(dname.className);
132 }
133}
134
136{
137 if (isConstructor(F) || isDestructor(F))
138 {
139 for (Function::const_iterator B = F->begin(), E = F->end(); B != E; ++B)
140 {
141 for (BasicBlock::const_iterator I = B->begin(), E = B->end(); I != E; ++I)
142 {
143 if (LLVMUtil::isCallSite(&(*I)))
144 {
145 connectInheritEdgeViaCall(F, SVFUtil::cast<CallBase>(&(*I)));
146 }
147 else if (const StoreInst *store = SVFUtil::dyn_cast<StoreInst>(&(*I)))
148 {
150 }
151 }
152 }
153 }
154}
155
156
163
165{
166 if (getCallee(cs) == nullptr)
167 return;
168
169 const Function* callee = getCallee(cs);
170
171 struct DemangledName dname = demangle(caller->getName().str());
173 {
174 if (cs->arg_size() < 1 || (cs->arg_size() < 2 && cs->paramHasAttr(0, llvm::Attribute::StructRet)))
175 return;
177 //const Argument* consThisPtr = getConstructorThisPtr(caller);
178 //bool samePtr = isSameThisPtrInConstructor(consThisPtr, csThisPtr);
179 bool samePtrTrue = true;
180 if (csThisPtr != nullptr && samePtrTrue)
181 {
182 struct DemangledName basename = demangle(callee->getName().str());
184 basename.className.size() > 0)
185 {
186 chg->addEdge(dname.className, basename.className, CHEdge::INHERITANCE);
187 }
188 }
189 }
190}
191
193{
194 struct DemangledName dname = demangle(caller->getName().str());
195 if (const ConstantExpr *ce = SVFUtil::dyn_cast<ConstantExpr>(storeInst->getValueOperand()))
196 {
197 if (ce->getOpcode() == Instruction::BitCast)
198 {
199 const Value* bitcastval = ce->getOperand(0);
200 if (const ConstantExpr *bcce = SVFUtil::dyn_cast<ConstantExpr>(bitcastval))
201 {
202 if (bcce->getOpcode() == Instruction::GetElementPtr)
203 {
204 const Value* gepval = bcce->getOperand(0);
206 {
207 string vtblClassName = getClassNameFromVtblObj(gepval->getName().str());
208 if (vtblClassName.size() > 0 && dname.className.compare(vtblClassName) != 0)
209 {
211 }
212 }
213 }
214 }
215 }
216 }
217}
218
220{
221 for (Module::const_named_metadata_iterator mdit = M.named_metadata_begin(),
222 mdeit = M.named_metadata_end(); mdit != mdeit; ++mdit)
223 {
224 const NamedMDNode *md = &*mdit;
225 string mdname = md->getName().str();
226 if (mdname.compare(0, 15, "__cxx_bases_of_") != 0)
227 continue;
228 string className = mdname.substr(15);
229 for (NamedMDNode::const_op_iterator opit = md->op_begin(),
230 opeit = md->op_end(); opit != opeit; ++opit)
231 {
232 const MDNode *N = *opit;
233 const MDString* mdstr = SVFUtil::cast<MDString>(N->getOperand(0).get());
234 string baseName = mdstr->getString().str();
236 }
237 }
238}
239
240CHNode *CHGBuilder::createNode(const std::string& className)
241{
242 assert(!chg->getNode(className) && "this node should never be created before!");
243 CHNode * node = new CHNode(className, chg->classNum++);
244 chg->classNameToNodeMap[className] = node;
245 chg->addGNode(node->getId(), node);
246 if (className.size() > 0 && className[className.size() - 1] == '>')
247 {
248 string templateName = getBeforeBrackets(className);
250 if (!templateNode)
251 {
252 DBOUT(DCHA, outs() << "\t Create Template CHANode " + templateName + " for class " + className + "...\n");
254 templateNode->setTemplate();
255 }
258 }
259 return node;
260}
261
262/*
263 * build the following two maps:
264 * classNameToDescendantsMap
265 * chg->classNameToAncestorsMap
266 */
268{
269
270 for (CHGraph::const_iterator it = chg->begin(), eit = chg->end();
271 it != eit; ++it)
272 {
273 const CHNode *node = it->second;
274 WorkList worklist;
276 worklist.push(node);
277 while (!worklist.empty())
278 {
279 const CHNode *curnode = worklist.pop();
280 if (visitedNodes.find(curnode) == visitedNodes.end())
281 {
282 for (CHEdge::CHEdgeSetTy::const_iterator it =
283 curnode->getOutEdges().begin(), eit =
284 curnode->getOutEdges().end(); it != eit; ++it)
285 {
286 if ((*it)->getEdgeType() == CHEdge::INHERITANCE)
287 {
288 CHNode *succnode = (*it)->getDstNode();
290 chg->classNameToDescendantsMap[succnode->getName()].insert(node);
291 worklist.push(succnode);
292 }
293 }
294 visitedNodes.insert(curnode);
295 }
296 }
297 }
298}
299
301 const string& className)
302{
303
304 CHGraph::NameToCHNodesMap::const_iterator it = chg->classNameToInstAndDescsMap.find(className);
305 if (it != chg->classNameToInstAndDescsMap.end())
306 {
307 return it->second;
308 }
309 else
310 {
311 chg->classNameToInstAndDescsMap[className] = chg->getDescendants(className);
312 if (chg->getNode(className)->isTemplate())
313 {
314 const CHNodeSetTy& instances = chg->getInstances(className);
315 for (CHNodeSetTy::const_iterator it = instances.begin(), eit = instances.end(); it != eit; ++it)
316 {
317 const CHNode *node = *it;
318 chg->classNameToInstAndDescsMap[className].insert(node);
320 for (CHNodeSetTy::const_iterator dit =
321 instance_descendants.begin(), deit =
322 instance_descendants.end(); dit != deit; ++dit)
323 {
324 chg->classNameToInstAndDescsMap[className].insert(*dit);
325 }
326 }
327 }
328 return chg->classNameToInstAndDescsMap[className];
329 }
330}
331
332
333
334
335/*
336 * do the following things:
337 * 1. initialize virtualFunctions for each class
338 * 2. mark multi-inheritance classes
339 * 3. mark pure abstract classes
340 *
341 * Layout of VTables:
342 *
343 * 1. single inheritance
344 * class A {...};
345 * class B: public A {...};
346 * B's vtable: {i8 *null, _ZTI1B, ...}
347 *
348 * 2. normal multiple inheritance
349 * class A {...};
350 * class B {...};
351 * class C: public A, public B {...};
352 * C's vtable: {i8 *null, _ZTI1C, ..., inttoptr xxx, _ZTI1C, ...}
353 * "inttoptr xxx" servers as a delimiter for dividing virtual methods inherited
354 * from "class A" and "class B"
355 *
356 * 3. virtual diamond inheritance
357 * class A {...};
358 * class B: public virtual A {...};
359 * class C: public virtual A {...};
360 * class D: public B, public C {...};
361 * D's vtable: {i8 *null, _ZTI1C, ..., inttoptr xxx, _ZTI1C, i8 *null, ...}
362 * there will several "i8 *null" following "inttoptr xxx, _ZTI1C,", and the
363 * number of "i8 *null" is the same as the number of virtual methods in
364 * "class A"
365 */
367{
368 for (Module::const_global_iterator I = M.global_begin(),
369 E = M.global_end(); I != E; ++I)
370 {
371 const GlobalValue *globalvalue = SVFUtil::dyn_cast<const GlobalValue>(&(*I));
372 if (cppUtil::isValVtbl(globalvalue) && globalvalue->getNumOperands() > 0)
373 {
375
376 string vtblClassName = getClassNameFromVtblObj(globalvalue->getName().str());
378 assert(node && "node not found?");
381 GlobalObjVar* globalObjVar = SVFUtil::cast<GlobalObjVar>(pVar);
382 globalObjVar->setName(vtblClassName);
383 node->setVTable(globalObjVar);
384
385 for (unsigned int ei = 0; ei < vtblStruct->getNumOperands(); ++ei)
386 {
387 const ConstantArray *vtbl =
388 SVFUtil::dyn_cast<ConstantArray>(vtblStruct->getOperand(ei));
389 assert(vtbl && "Element of initializer not an array?");
390
391 /*
392 * items in vtables can be classified into 3 categories:
393 * 1. i8* null
394 * 2. i8* inttoptr xxx
395 * 3. i8* bitcast xxx
396 */
397 bool pure_abstract = true;
398 u32_t i = 0;
400 {
402 bool is_virtual = false; // virtual inheritance
403 int null_ptr_num = 0;
404 for (; i < vtbl->getNumOperands(); ++i)
405 {
406 Constant* operand = vtbl->getOperand(i);
407 if (SVFUtil::isa<ConstantPointerNull>(operand))
408 {
409 if (i > 0 && !SVFUtil::isa<ConstantPointerNull>(vtbl->getOperand(i-1)))
410 {
411 auto foo = [&is_virtual, &null_ptr_num, &vtbl, &i](const Value* val)
412 {
413 if (val->getName().str().compare(0, ztiLabel.size(), ztiLabel) == 0)
414 {
415 is_virtual = true;
416 null_ptr_num = 1;
418 {
419 if (SVFUtil::isa<ConstantPointerNull>(vtbl->getOperand(i+null_ptr_num)))
420 null_ptr_num++;
421 else
422 break;
423 }
424 }
425 };
426 if (const ConstantExpr *ce =
427 SVFUtil::dyn_cast<ConstantExpr>(vtbl->getOperand(i-1)))
428 {
429 if(ce->getOpcode() == Instruction::BitCast)
430 foo(ce->getOperand(0));
431 }
432 else
433 {
434 // opaque pointer mode
435 foo(vtbl->getOperand(i - 1));
436 }
437 }
438 continue;
439 }
440
441 auto foo = [this, &virtualFunctions, &pure_abstract, &vtblClassName](const Value* operand)
442 {
443 if (const Function* f = SVFUtil::dyn_cast<Function>(operand))
444 {
446 if (f->getName().str().compare(pureVirtualFunName) == 0)
447 {
448 pure_abstract &= true;
449 }
450 else
451 {
452 pure_abstract &= false;
453 }
454 struct DemangledName dname = demangle(f->getName().str());
455 if (dname.className.size() > 0 &&
456 vtblClassName.compare(dname.className) != 0)
457 {
458 if(!chg->getNode(dname.className)) createNode(dname.className);
460 }
461 }
462 else
463 {
464 if (const GlobalAlias *alias =
465 SVFUtil::dyn_cast<GlobalAlias>(operand))
466 {
467 const Constant *aliasValue = alias->getAliasee();
468 if (const Function* aliasFunc =
469 SVFUtil::dyn_cast<Function>(aliasValue))
470 {
472 }
473 else if (const ConstantExpr *aliasconst =
474 SVFUtil::dyn_cast<ConstantExpr>(aliasValue))
475 {
476 (void)aliasconst; // Suppress warning of unused variable under release build
477 assert(aliasconst->getOpcode() == Instruction::BitCast &&
478 "aliased constantexpr in vtable not a bitcast");
480 SVFUtil::dyn_cast<Function>(aliasconst->getOperand(0));
482 "aliased bitcast in vtable not a function");
484 }
485 else
486 {
487 assert(false && "alias not function or bitcast");
488 }
489
490 pure_abstract &= false;
491 }
492 else if (operand->getName().str().compare(0, ztiLabel.size(),
493 ztiLabel) == 0)
494 {
495 }
496 else
497 {
498 assert("what else can be in bitcast of a vtable?");
499 }
500 }
501 };
502
518 if (const ConstantExpr *ce =
519 SVFUtil::dyn_cast<ConstantExpr>(operand))
520 {
521 u32_t opcode = ce->getOpcode();
522 assert(opcode == Instruction::IntToPtr);
523 assert(ce->getNumOperands() == 1 &&
524 "inttptr operand num not 1");
525 if (opcode == Instruction::IntToPtr)
526 {
527 node->setMultiInheritance();
528 ++i;
529 break;
530 }
531 }
532 else
533 {
534 foo(operand);
535 }
536 }
537 if (is_virtual && virtualFunctions.size() > 0)
538 {
539 for (int i = 0; i < null_ptr_num; ++i)
540 {
541 const FunObjVar* fun = virtualFunctions[i];
542 virtualFunctions.insert(virtualFunctions.begin(), fun);
543 }
544 }
545 if (virtualFunctions.size() > 0)
547 }
548 if (pure_abstract == true)
549 {
550 node->setPureAbstract();
551 }
552 }
553 }
554 }
555}
556
557
559{
560 /*
561 * 1. Divide classes into groups
562 * 2. Get all virtual functions in a group
563 * 3. Assign consecutive IDs to virtual functions that have
564 * the same name (after demangling) in a group
565 */
568 neit = chg->end(); nit != neit; ++nit)
569 {
570 CHNode *node = nit->second;
571 if (visitedNodes.find(node) != visitedNodes.end())
572 continue;
573
574 string className = node->getName();
575
576 /*
577 * get all the classes in a specific group
578 */
580 stack<const CHNode*> nodeStack;
581 nodeStack.push(node);
582 while (!nodeStack.empty())
583 {
584 const CHNode *curnode = nodeStack.top();
585 nodeStack.pop();
586 group.insert(curnode);
587 if (visitedNodes.find(curnode) != visitedNodes.end())
588 continue;
589 for (CHEdge::CHEdgeSetTy::const_iterator it = curnode->getOutEdges().begin(),
590 eit = curnode->getOutEdges().end(); it != eit; ++it)
591 {
592 CHNode *tmpnode = (*it)->getDstNode();
593 nodeStack.push(tmpnode);
594 group.insert(tmpnode);
595 }
596 for (CHEdge::CHEdgeSetTy::const_iterator it = curnode->getInEdges().begin(),
597 eit = curnode->getInEdges().end(); it != eit; ++it)
598 {
599 CHNode *tmpnode = (*it)->getSrcNode();
600 nodeStack.push(tmpnode);
601 group.insert(tmpnode);
602 }
603 visitedNodes.insert(curnode);
604 }
605
606 /*
607 * get all virtual functions in a specific group
608 */
610 for (CHGraph::CHNodeSetTy::iterator it = group.begin(),
611 eit = group.end(); it != eit; ++it)
612 {
615 veit = vecs.end(); vit != veit; ++vit)
616 {
617 for (vector<const FunObjVar*>::const_iterator fit = (*vit).begin(),
618 feit = (*vit).end(); fit != feit; ++fit)
619 {
620 virtualFunctions.insert(*fit);
621 }
622 }
623 }
624
625 /*
626 * build a set of pairs of demangled function name and function in a
627 * specific group, items in the set will be sort by the first item of the
628 * pair, so all the virtual functions in a group will be sorted by the
629 * demangled function name
630 * <f, A::f>
631 * <f, B::f>
632 * <g, A::g>
633 * <g, B::g>
634 * <g, C::g>
635 * <~A, A::~A>
636 * <~B, B::~B>
637 * <~C, C::~C>
638 * ...
639 */
641 for (set<const FunObjVar*>::iterator fit = virtualFunctions.begin(),
642 feit = virtualFunctions.end(); fit != feit; ++fit)
643 {
644 const FunObjVar* f = *fit;
645 struct DemangledName dname = demangle(f->getName());
647 }
648 for (set<pair<string, const FunObjVar*>>::iterator it = fNameSet.begin(),
649 eit = fNameSet.end(); it != eit; ++it)
650 {
651 chg->virtualFunctionToIDMap[it->second] = chg->vfID++;
652 }
653 }
654}
655
656
658{
659
661 {
662 for (Module::const_iterator F = M.begin(), E = M.end(); F != E; ++F)
663 {
664 for (const_inst_iterator II = inst_begin(*F), E = inst_end(*F); II != E; ++II)
665 {
666 if(const CallBase* callInst = SVFUtil::dyn_cast<CallBase>(&*II))
667 {
668 if (cppUtil::isVirtualCallSite(callInst) == false)
669 continue;
670
672 const CHNodeSetTy& chClasses = getCSClasses(callInst);
673 for (CHNodeSetTy::const_iterator it = chClasses.begin(), eit = chClasses.end(); it != eit; ++it)
674 {
675 const CHNode *child = *it;
676 const GlobalObjVar *vtbl = child->getVTable();
677 if (vtbl != nullptr)
678 {
679 vtbls.insert(vtbl);
680 }
681 }
682 if (vtbls.size() > 0)
683 {
684 ICFGNode* icfgNode =
685 llvmModuleSet()->getICFGNode(callInst);
686 chg->callNodeToCHAVtblsMap[icfgNode] = vtbls;
688 chg->getVFnsFromVtbls(SVFUtil::cast<CallICFGNode>(icfgNode), vtbls, virtualFunctions);
689 if (virtualFunctions.size() > 0)
691 }
692 }
693 }
694 }
695 }
696}
697
698
700{
701 assert(cppUtil::isVirtualCallSite(cs) && "not virtual callsite!");
702
703 ICFGNode* icfgNode = llvmModuleSet()->getICFGNode(cs);
704
705 CHGraph::CallNodeToCHNodesMap::const_iterator it = chg->callNodeToClassesMap.find(icfgNode);
706 if (it != chg->callNodeToClassesMap.end())
707 {
708 return it->second;
709 }
710 else
711 {
713
714 if(thisPtrClassNames.empty())
715 {
716 // if we cannot infer classname, conservatively push all class nodes
717 for (const auto &node: *chg)
718 {
719 chg->callNodeToClassesMap[icfgNode].insert(node.second);
720 }
721 return chg->callNodeToClassesMap[icfgNode];
722 }
723
724 for (const auto &thisPtrClassName: thisPtrClassNames)
725 {
727 {
729 chg->callNodeToClassesMap[icfgNode].insert(thisNode);
730 for (CHGraph::CHNodeSetTy::const_iterator it2 = instAndDesces.begin(), eit = instAndDesces.end(); it2 != eit; ++it2)
731 chg->callNodeToClassesMap[icfgNode].insert(*it2);
732 }
733 }
734 return chg->callNodeToClassesMap[icfgNode];
735 }
736}
737
739{
741 {
742 if (const auto* tf = cppUtil::getThunkTarget(lf))
743 {
744 const FunObjVar* pFunction =
746 v.push_back(pFunction);
747 }
748 }
749 else
750 {
751 const FunObjVar* pFunction =
753 v.push_back(pFunction);
754 }
755}
const string ztiLabel
const string pureVirtualFunName
#define DBOUT(TYPE, X)
LLVM debug macros, define type of your DBUG model of each pass.
Definition SVFType.h:498
#define TIMEINTERVAL
Definition SVFType.h:526
#define DCHA
Definition SVFType.h:520
#define DGENERAL
Definition SVFType.h:504
set(THREADS_PREFER_PTHREAD_FLAG ON) find_package(Threads REQUIRED) add_llvm_executable(wpa wpa.cpp) target_link_libraries(wpa PUBLIC $
Definition CMakeLists.txt:1
cJSON * child
Definition cJSON.cpp:2723
@ INHERITANCE
Definition CHG.h:86
@ INSTANTCE
Definition CHG.h:87
void analyzeVTables(const Module &M)
void connectInheritEdgeViaStore(const Function *caller, const StoreInst *store)
LLVMModuleSet * llvmModuleSet()
void readInheritanceMetadataFromModule(const Module &M)
void buildCHGNodes(const GlobalValue *V)
const CHGraph::CHNodeSetTy & getInstancesAndDescendants(const std::string &className)
CHGraph::WorkList WorkList
Definition CHGBuilder.h:46
void addFuncToFuncVector(CHNode::FuncVector &v, const Function *f)
void buildCHGEdges(const Function *F)
void buildVirtualFunctionToIDMap()
CHGraph * chg
Definition CHGBuilder.h:42
void buildCSToCHAVtblsAndVfnsMap()
void buildInternalMaps()
CHGraph::CHNodeSetTy CHNodeSetTy
Definition CHGBuilder.h:45
const CHNodeSetTy & getCSClasses(const CallBase *cs)
CHNode * createNode(const std::string &name)
void connectInheritEdgeViaCall(const Function *caller, const CallBase *cs)
void buildClassNameToAncestorsDescendantsMap()
NameToCHNodesMap classNameToAncestorsMap
Definition CHG.h:325
CallNodeToCHNodesMap callNodeToClassesMap
Definition CHG.h:328
CallNodeToVFunSetMap callNodeToCHAVFnsMap
Definition CHG.h:333
void dump(const std::string &filename)
Definition CHG.cpp:242
const CHNodeSetTy & getInstances(const std::string className)
Definition CHG.h:303
void addEdge(const std::string className, const std::string baseClassName, CHEdge::CHEDGETYPE edgeType)
Definition CHG.cpp:97
Map< const FunObjVar *, u32_t > virtualFunctionToIDMap
Definition CHG.h:330
void addInstances(const std::string templateName, CHNode *node)
Definition CHG.h:290
void getVFnsFromVtbls(const CallICFGNode *cs, const VTableSet &vtbls, VFunSet &virtualFunctions) override
Definition CHG.cpp:124
CHNode * getNode(const std::string name) const
Definition CHG.cpp:112
NameToCHNodesMap classNameToInstAndDescsMap
Definition CHG.h:326
u32_t vfID
Definition CHG.h:321
double buildingCHGTime
Definition CHG.h:322
NameToCHNodesMap classNameToDescendantsMap
Definition CHG.h:324
Set< const CHNode * > CHNodeSetTy
Definition CHG.h:240
u32_t classNum
Definition CHG.h:320
Map< std::string, CHNode * > classNameToNodeMap
Definition CHG.h:323
CallNodeToVTableSetMap callNodeToCHAVtblsMap
Definition CHG.h:332
const CHNodeSetTy & getDescendants(const std::string className)
Definition CHG.h:299
virtual const std::string & getName() const
Definition CHG.h:130
void setVTable(const GlobalObjVar *vtbl)
Definition CHG.h:189
void setMultiInheritance()
Definition CHG.h:152
void addVirtualFunctionVector(FuncVector vfuncvec)
Definition CHG.h:174
const std::vector< FuncVector > & getVirtualFunctionVectors() const
Definition CHG.h:178
void setPureAbstract()
Attribute.
Definition CHG.h:148
std::vector< const FunObjVar * > FuncVector
Definition CHG.h:121
bool isTemplate() const
Definition CHG.h:168
void addGNode(NodeID id, NodeType *node)
Add a Node.
iterator begin()
Iterators.
IDToNodeMapTy::const_iterator const_iterator
NodeType * getGNode(NodeID id) const
Get a node.
const FunObjVar * getFunObjVar(const Function *fun) const
Definition LLVMModule.h:260
static LLVMModuleSet * getLLVMModuleSet()
Definition LLVMModule.h:129
ICFGNode * getICFGNode(const Instruction *inst)
Get a basic block ICFGNode.
NodeID getObjectNode(const Value *V)
const std::vector< std::reference_wrapper< Module > > & getLLVMModules() const
Definition LLVMModule.h:155
static const Option< bool > DumpCHA
Definition Options.h:176
static SVFIR * getPAG(bool buildFromFile=false)
Singleton design here to make sure we only have one instance during any analysis.
Definition SVFIR.h:116
static double getClk(bool mark=false)
Definition SVFStat.cpp:48
NodeID getId() const
Get ID.
Definition SVFValue.h:158
bool isCallSite(const Instruction *inst)
Whether an instruction is a call or invoke instruction.
Definition LLVMUtil.h:44
const ConstantExpr * isCastConstantExpr(const Value *val)
Definition LLVMUtil.h:245
const Function * getCallee(const CallBase *cs)
Definition LLVMUtil.h:97
std::string pasMsg(const std::string &msg)
Print each pass/phase message by converting a string into blue string output.
Definition SVFUtil.cpp:101
std::ostream & outs()
Overwrite llvm::outs()
Definition SVFUtil.h:52
std::string getBeforeBrackets(const std::string &name)
Definition CppUtil.cpp:127
const Value * getVCallThisPtr(const CallBase *cs)
Definition CppUtil.cpp:411
struct DemangledName demangle(const std::string &name)
Definition CppUtil.cpp:195
Set< std::string > getClassNameOfThisPtr(const CallBase *cs)
Definition CppUtil.cpp:601
bool isCPPThunkFunction(const Function *F)
Definition CppUtil.cpp:383
bool isVirtualCallSite(const CallBase *cs)
Definition CppUtil.cpp:352
const Function * getThunkTarget(const Function *F)
Definition CppUtil.cpp:389
const ConstantStruct * getVtblStruct(const GlobalValue *vtbl)
Definition CppUtil.cpp:323
bool isConstructor(const Function *F)
Definition CppUtil.cpp:489
std::string getClassNameFromVtblObj(const std::string &vtblName)
Definition CppUtil.cpp:304
bool isValVtbl(const Value *val)
Definition CppUtil.cpp:336
bool isDestructor(const Function *F)
Definition CppUtil.cpp:509
for isBitcode
Definition BasicTypes.h:68
llvm::const_inst_iterator const_inst_iterator
Definition BasicTypes.h:250
llvm::GlobalAlias GlobalAlias
Definition BasicTypes.h:128
llvm::CallBase CallBase
Definition BasicTypes.h:146
llvm::MDString MDString
Definition BasicTypes.h:101
llvm::ConstantStruct ConstantStruct
Definition BasicTypes.h:106
llvm::NamedMDNode NamedMDNode
LLVM metadata and debug information.
Definition BasicTypes.h:111
u32_t NodeID
Definition GeneralType.h:56
Set< const GlobalObjVar * > VTableSet
Definition CHG.h:46
llvm::ConstantArray ConstantArray
Definition BasicTypes.h:123
llvm::Function Function
Definition BasicTypes.h:85
llvm::GlobalValue GlobalValue
Definition BasicTypes.h:88
llvm::Constant Constant
Definition BasicTypes.h:124
llvm::Value Value
LLVM Basic classes.
Definition BasicTypes.h:82
llvm::ConstantExpr ConstantExpr
Definition BasicTypes.h:120
llvm::IRBuilder IRBuilder
Definition BasicTypes.h:74
llvm::Module Module
Definition BasicTypes.h:84
llvm::StoreInst StoreInst
Definition BasicTypes.h:148
llvm::MDNode MDNode
Definition BasicTypes.h:112
unsigned u32_t
Definition GeneralType.h:47
Set< const FunObjVar * > VFunSet
Definition CHG.h:47