Static Value-Flow Analysis
Loading...
Searching...
No Matches
Public Types | Public Member Functions | Private Member Functions | Private Attributes | List of all members
SVF::CHGBuilder Class Reference

#include <CHGBuilder.h>

Public Types

typedef CHGraph::CHNodeSetTy CHNodeSetTy
 
typedef CHGraph::WorkList WorkList
 

Public Member Functions

 CHGBuilder (CHGraph *c)
 
void buildCHG ()
 
void buildCHGNodes (const GlobalValue *V)
 
void buildCHGNodes (const Function *F)
 
void buildCHGEdges (const Function *F)
 
void buildInternalMaps ()
 
void readInheritanceMetadataFromModule (const Module &M)
 
CHNodecreateNode (const std::string &name)
 
void connectInheritEdgeViaCall (const Function *caller, const CallBase *cs)
 
void connectInheritEdgeViaStore (const Function *caller, const StoreInst *store)
 
void buildClassNameToAncestorsDescendantsMap ()
 
const CHGraph::CHNodeSetTygetInstancesAndDescendants (const std::string &className)
 
void analyzeVTables (const Module &M)
 
void buildVirtualFunctionToIDMap ()
 
void buildCSToCHAVtblsAndVfnsMap ()
 
const CHNodeSetTygetCSClasses (const CallBase *cs)
 
void addFuncToFuncVector (CHNode::FuncVector &v, const Function *f)
 

Private Member Functions

LLVMModuleSetllvmModuleSet ()
 

Private Attributes

CHGraphchg
 

Detailed Description

Definition at line 38 of file CHGBuilder.h.

Member Typedef Documentation

◆ CHNodeSetTy

Definition at line 45 of file CHGBuilder.h.

◆ WorkList

Definition at line 46 of file CHGBuilder.h.

Constructor & Destructor Documentation

◆ CHGBuilder()

SVF::CHGBuilder::CHGBuilder ( CHGraph c)
inline

Definition at line 48 of file CHGBuilder.h.

48 : chg(c)
49 {
50
51 }
CHGraph * chg
Definition CHGBuilder.h:42
llvm::IRBuilder IRBuilder
Definition BasicTypes.h:74

Member Function Documentation

◆ addFuncToFuncVector()

void CHGBuilder::addFuncToFuncVector ( CHNode::FuncVector v,
const Function f 
)

Definition at line 741 of file CHGBuilder.cpp.

742{
744 {
745 const auto* tf = cppUtil::getThunkTarget(lf);
746 const FunObjVar* pFunction =
748 v.push_back(pFunction);
749 }
750 else
751 {
752 const FunObjVar* pFunction =
754 v.push_back(pFunction);
755 }
756}
LLVMModuleSet * llvmModuleSet()
const FunObjVar * getFunObjVar(const Function *fun) const
Definition LLVMModule.h:267
bool isCPPThunkFunction(const Function *F)
Definition CppUtil.cpp:383
const Function * getThunkTarget(const Function *F)
Definition CppUtil.cpp:389

◆ analyzeVTables()

void CHGBuilder::analyzeVTables ( const Module M)

vtable in llvm 16 does not have bitcast: e.g., @_ZTV1B = linkonce_odr dso_local unnamed_addr constant { [4 x ptr] } { [4 x ptr] [ptr null, ptr @_ZTI1B, ptr @_ZN1B1fEPi, ptr @_ZN1B1gEPi] }, comdat, align 8 compared to its llvm 13 version: @_ZTV1B = linkonce_odr dso_local unnamed_addr constant { [4 x i8*] } { [4 x i8*] [i8* null, i8* bitcast ({ i8*, i8*, i8* }* @_ZTI1B to i8*), i8* bitcast (void (class.B*, i32*)* @_ZN1B1fEPi to i8*), i8* bitcast (void (class.B*, i32*)* @_ZN1B1gEPi to i8*)] }, comdat, align 8

For llvm 13, we need to cast the operand into a constant expr and then process the first operand of that constant expr For llvm 16, things get simpler. We can directly process each operand

for inttoptr in llvm 16, the handling method is the same as before

Definition at line 369 of file CHGBuilder.cpp.

370{
371 for (Module::const_global_iterator I = M.global_begin(),
372 E = M.global_end(); I != E; ++I)
373 {
374 const GlobalValue *globalvalue = SVFUtil::dyn_cast<const GlobalValue>(&(*I));
375 if (cppUtil::isValVtbl(globalvalue) && globalvalue->getNumOperands() > 0)
376 {
378
379 string vtblClassName = getClassNameFromVtblObj(globalvalue->getName().str());
381 assert(node && "node not found?");
384 GlobalObjVar* globalObjVar = SVFUtil::cast<GlobalObjVar>(pVar);
385 globalObjVar->setName(vtblClassName);
386 node->setVTable(globalObjVar);
387
388 for (unsigned int ei = 0; ei < vtblStruct->getNumOperands(); ++ei)
389 {
390 const ConstantArray *vtbl =
391 SVFUtil::dyn_cast<ConstantArray>(vtblStruct->getOperand(ei));
392 assert(vtbl && "Element of initializer not an array?");
393
394 /*
395 * items in vtables can be classified into 3 categories:
396 * 1. i8* null
397 * 2. i8* inttoptr xxx
398 * 3. i8* bitcast xxx
399 */
400 bool pure_abstract = true;
401 u32_t i = 0;
403 {
405 bool is_virtual = false; // virtual inheritance
406 int null_ptr_num = 0;
407 for (; i < vtbl->getNumOperands(); ++i)
408 {
409 Constant* operand = vtbl->getOperand(i);
410 if (SVFUtil::isa<ConstantPointerNull>(operand))
411 {
412 if (i > 0 && !SVFUtil::isa<ConstantPointerNull>(vtbl->getOperand(i-1)))
413 {
414 auto foo = [&is_virtual, &null_ptr_num, &vtbl, &i](const Value* val)
415 {
416 if (val->getName().str().compare(0, ztiLabel.size(), ztiLabel) == 0)
417 {
418 is_virtual = true;
419 null_ptr_num = 1;
421 {
422 if (SVFUtil::isa<ConstantPointerNull>(vtbl->getOperand(i+null_ptr_num)))
423 null_ptr_num++;
424 else
425 break;
426 }
427 }
428 };
429 if (const ConstantExpr *ce =
430 SVFUtil::dyn_cast<ConstantExpr>(vtbl->getOperand(i-1)))
431 {
432 if(ce->getOpcode() == Instruction::BitCast)
433 foo(ce->getOperand(0));
434 }
435 else
436 {
437 // opaque pointer mode
438 foo(vtbl->getOperand(i - 1));
439 }
440 }
441 continue;
442 }
443
444 auto foo = [this, &virtualFunctions, &pure_abstract, &vtblClassName](const Value* operand)
445 {
446 if (const Function* f = SVFUtil::dyn_cast<Function>(operand))
447 {
449 if (f->getName().str().compare(pureVirtualFunName) == 0)
450 {
451 pure_abstract &= true;
452 }
453 else
454 {
455 pure_abstract &= false;
456 }
457 struct DemangledName dname = demangle(f->getName().str());
458 if (dname.className.size() > 0 &&
459 vtblClassName.compare(dname.className) != 0)
460 {
461 if(!chg->getNode(dname.className)) createNode(dname.className);
463 }
464 }
465 else
466 {
467 if (const GlobalAlias *alias =
468 SVFUtil::dyn_cast<GlobalAlias>(operand))
469 {
470 const Constant *aliasValue = alias->getAliasee();
471 if (const Function* aliasFunc =
472 SVFUtil::dyn_cast<Function>(aliasValue))
473 {
475 }
476 else if (const ConstantExpr *aliasconst =
477 SVFUtil::dyn_cast<ConstantExpr>(aliasValue))
478 {
479 (void)aliasconst; // Suppress warning of unused variable under release build
480 assert(aliasconst->getOpcode() == Instruction::BitCast &&
481 "aliased constantexpr in vtable not a bitcast");
483 SVFUtil::dyn_cast<Function>(aliasconst->getOperand(0));
485 "aliased bitcast in vtable not a function");
487 }
488 else
489 {
490 assert(false && "alias not function or bitcast");
491 }
492
493 pure_abstract &= false;
494 }
495 else if (operand->getName().str().compare(0, ztiLabel.size(),
496 ztiLabel) == 0)
497 {
498 }
499 else
500 {
501 assert("what else can be in bitcast of a vtable?");
502 }
503 }
504 };
505
521 if (const ConstantExpr *ce =
522 SVFUtil::dyn_cast<ConstantExpr>(operand))
523 {
524 u32_t opcode = ce->getOpcode();
525 assert(opcode == Instruction::IntToPtr);
526 assert(ce->getNumOperands() == 1 &&
527 "inttptr operand num not 1");
528 if (opcode == Instruction::IntToPtr)
529 {
530 node->setMultiInheritance();
531 ++i;
532 break;
533 }
534 }
535 else
536 {
537 foo(operand);
538 }
539 }
540 if (is_virtual && virtualFunctions.size() > 0)
541 {
542 for (int i = 0; i < null_ptr_num; ++i)
543 {
544 const FunObjVar* fun = virtualFunctions[i];
545 virtualFunctions.insert(virtualFunctions.begin(), fun);
546 }
547 }
548 if (virtualFunctions.size() > 0)
550 }
551 if (pure_abstract == true)
552 {
553 node->setPureAbstract();
554 }
555 }
556 }
557 }
558}
const string ztiLabel
const string pureVirtualFunName
unsigned u32_t
Definition CommandLine.h:18
@ INHERITANCE
Definition CHG.h:84
void addFuncToFuncVector(CHNode::FuncVector &v, const Function *f)
CHNode * createNode(const std::string &name)
void addEdge(const std::string className, const std::string baseClassName, CHEdge::CHEDGETYPE edgeType)
Definition CHG.cpp:97
CHNode * getNode(const std::string name) const
Definition CHG.cpp:112
void setVTable(const GlobalObjVar *vtbl)
Definition CHG.h:186
void setMultiInheritance()
Definition CHG.h:149
void addVirtualFunctionVector(FuncVector vfuncvec)
Definition CHG.h:171
void setPureAbstract()
Attribute.
Definition CHG.h:145
std::vector< const FunObjVar * > FuncVector
Definition CHG.h:118
NodeType * getGNode(NodeID id) const
Get a node.
NodeID getObjectNode(const Value *V)
static SVFIR * getPAG(bool buildFromFile=false)
Singleton design here to make sure we only have one instance during any analysis.
Definition SVFIR.h:116
struct DemangledName demangle(const std::string &name)
Definition CppUtil.cpp:195
const ConstantStruct * getVtblStruct(const GlobalValue *vtbl)
Definition CppUtil.cpp:323
std::string getClassNameFromVtblObj(const std::string &vtblName)
Definition CppUtil.cpp:304
bool isValVtbl(const Value *val)
Definition CppUtil.cpp:336
llvm::GlobalAlias GlobalAlias
Definition BasicTypes.h:130
llvm::ConstantStruct ConstantStruct
Definition BasicTypes.h:108
u32_t NodeID
Definition GeneralType.h:56
llvm::ConstantArray ConstantArray
Definition BasicTypes.h:125
llvm::Function Function
Definition BasicTypes.h:87
llvm::GlobalValue GlobalValue
Definition BasicTypes.h:90
llvm::Constant Constant
Definition BasicTypes.h:126
llvm::Value Value
LLVM Basic classes.
Definition BasicTypes.h:84
llvm::ConstantExpr ConstantExpr
Definition BasicTypes.h:122

◆ buildCHG()

void CHGBuilder::buildCHG ( )

Definition at line 64 of file CHGBuilder.cpp.

65{
66
67 double timeStart, timeEnd;
69 for (Module &M : llvmModuleSet()->getLLVMModules())
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}
#define DBOUT(TYPE, X)
LLVM debug macros, define type of your DBUG model of each pass.
Definition SVFType.h:593
#define TIMEINTERVAL
Definition SVFType.h:621
#define DGENERAL
Definition SVFType.h:599
void analyzeVTables(const Module &M)
void readInheritanceMetadataFromModule(const Module &M)
void buildCHGNodes(const GlobalValue *V)
void buildCHGEdges(const Function *F)
void buildInternalMaps()
void dump(const std::string &filename)
Definition CHG.cpp:242
double buildingCHGTime
Definition CHG.h:328
static const Option< bool > DumpCHA
Definition Options.h:173
static double getClk(bool mark=false)
Definition SVFStat.cpp:48
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
llvm::Module Module
Definition BasicTypes.h:86

◆ buildCHGEdges()

void CHGBuilder::buildCHGEdges ( const Function F)

Definition at line 135 of file CHGBuilder.cpp.

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}
void connectInheritEdgeViaStore(const Function *caller, const StoreInst *store)
void connectInheritEdgeViaCall(const Function *caller, const CallBase *cs)
bool isCallSite(const Instruction *inst)
Whether an instruction is a call or invoke instruction.
Definition LLVMUtil.h:44
bool isConstructor(const Function *F)
Definition CppUtil.cpp:564
bool isDestructor(const Function *F)
Definition CppUtil.cpp:584
llvm::StoreInst StoreInst
Definition BasicTypes.h:150

◆ buildCHGNodes() [1/2]

void CHGBuilder::buildCHGNodes ( const Function F)

Definition at line 124 of file CHGBuilder.cpp.

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}
#define DCHA
Definition SVFType.h:615

◆ buildCHGNodes() [2/2]

void CHGBuilder::buildCHGNodes ( const GlobalValue V)

Definition at line 94 of file CHGBuilder.cpp.

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}
const ConstantExpr * isCastConstantExpr(const Value *val)
Definition LLVMUtil.h:245

◆ buildClassNameToAncestorsDescendantsMap()

void CHGBuilder::buildClassNameToAncestorsDescendantsMap ( )

Definition at line 270 of file CHGBuilder.cpp.

271{
272
273 for (CHGraph::const_iterator it = chg->begin(), eit = chg->end();
274 it != eit; ++it)
275 {
276 const CHNode *node = it->second;
277 WorkList worklist;
279 worklist.push(node);
280 while (!worklist.empty())
281 {
282 const CHNode *curnode = worklist.pop();
283 if (visitedNodes.find(curnode) == visitedNodes.end())
284 {
285 for (CHEdge::CHEdgeSetTy::const_iterator it =
286 curnode->getOutEdges().begin(), eit =
287 curnode->getOutEdges().end(); it != eit; ++it)
288 {
289 if ((*it)->getEdgeType() == CHEdge::INHERITANCE)
290 {
291 CHNode *succnode = (*it)->getDstNode();
293 chg->classNameToDescendantsMap[succnode->getName()].insert(node);
294 worklist.push(succnode);
295 }
296 }
297 visitedNodes.insert(curnode);
298 }
299 }
300 }
301}
CHGraph::WorkList WorkList
Definition CHGBuilder.h:46
CHGraph::CHNodeSetTy CHNodeSetTy
Definition CHGBuilder.h:45
NameToCHNodesMap classNameToAncestorsMap
Definition CHG.h:331
NameToCHNodesMap classNameToDescendantsMap
Definition CHG.h:330
virtual const std::string & getName() const
Definition CHG.h:127
iterator begin()
Iterators.
IDToNodeMapTy::const_iterator const_iterator

◆ buildCSToCHAVtblsAndVfnsMap()

void CHGBuilder::buildCSToCHAVtblsAndVfnsMap ( )

Definition at line 660 of file CHGBuilder.cpp.

661{
662
663 for (Module &M : llvmModuleSet()->getLLVMModules())
664 {
665 for (Module::const_iterator F = M.begin(), E = M.end(); F != E; ++F)
666 {
667 for (const_inst_iterator II = inst_begin(*F), E = inst_end(*F); II != E; ++II)
668 {
669 if(const CallBase* callInst = SVFUtil::dyn_cast<CallBase>(&*II))
670 {
671 if (cppUtil::isVirtualCallSite(callInst) == false)
672 continue;
673
675 const CHNodeSetTy& chClasses = getCSClasses(callInst);
676 for (CHNodeSetTy::const_iterator it = chClasses.begin(), eit = chClasses.end(); it != eit; ++it)
677 {
678 const CHNode *child = *it;
679 const GlobalObjVar *vtbl = child->getVTable();
680 if (vtbl != nullptr)
681 {
682 vtbls.insert(vtbl);
683 }
684 }
685 if (vtbls.size() > 0)
686 {
687 ICFGNode* icfgNode =
688 llvmModuleSet()->getICFGNode(callInst);
689 chg->callNodeToCHAVtblsMap[icfgNode] = vtbls;
691 chg->getVFnsFromVtbls(SVFUtil::cast<CallICFGNode>(icfgNode), vtbls, virtualFunctions);
692 if (virtualFunctions.size() > 0)
694 }
695 }
696 }
697 }
698 }
699}
cJSON * child
Definition cJSON.cpp:2723
const CHNodeSetTy & getCSClasses(const CallBase *cs)
CallNodeToVFunSetMap callNodeToCHAVFnsMap
Definition CHG.h:339
void getVFnsFromVtbls(const CallICFGNode *cs, const VTableSet &vtbls, VFunSet &virtualFunctions) override
Definition CHG.cpp:124
CallNodeToVTableSetMap callNodeToCHAVtblsMap
Definition CHG.h:338
ICFGNode * getICFGNode(const Instruction *inst)
Get a basic block ICFGNode.
bool isVirtualCallSite(const CallBase *cs)
Definition CppUtil.cpp:352
llvm::const_inst_iterator const_inst_iterator
Definition BasicTypes.h:252
llvm::CallBase CallBase
Definition BasicTypes.h:148
Set< const GlobalObjVar * > VTableSet
Definition CHG.h:46
Set< const FunObjVar * > VFunSet
Definition CHG.h:47

◆ buildInternalMaps()

void CHGBuilder::buildInternalMaps ( )

Definition at line 157 of file CHGBuilder.cpp.

◆ buildVirtualFunctionToIDMap()

void CHGBuilder::buildVirtualFunctionToIDMap ( )

Definition at line 561 of file CHGBuilder.cpp.

562{
563 /*
564 * 1. Divide classes into groups
565 * 2. Get all virtual functions in a group
566 * 3. Assign consecutive IDs to virtual functions that have
567 * the same name (after demangling) in a group
568 */
571 neit = chg->end(); nit != neit; ++nit)
572 {
573 CHNode *node = nit->second;
574 if (visitedNodes.find(node) != visitedNodes.end())
575 continue;
576
577 string className = node->getName();
578
579 /*
580 * get all the classes in a specific group
581 */
583 stack<const CHNode*> nodeStack;
584 nodeStack.push(node);
585 while (!nodeStack.empty())
586 {
587 const CHNode *curnode = nodeStack.top();
588 nodeStack.pop();
589 group.insert(curnode);
590 if (visitedNodes.find(curnode) != visitedNodes.end())
591 continue;
592 for (CHEdge::CHEdgeSetTy::const_iterator it = curnode->getOutEdges().begin(),
593 eit = curnode->getOutEdges().end(); it != eit; ++it)
594 {
595 CHNode *tmpnode = (*it)->getDstNode();
596 nodeStack.push(tmpnode);
597 group.insert(tmpnode);
598 }
599 for (CHEdge::CHEdgeSetTy::const_iterator it = curnode->getInEdges().begin(),
600 eit = curnode->getInEdges().end(); it != eit; ++it)
601 {
602 CHNode *tmpnode = (*it)->getSrcNode();
603 nodeStack.push(tmpnode);
604 group.insert(tmpnode);
605 }
606 visitedNodes.insert(curnode);
607 }
608
609 /*
610 * get all virtual functions in a specific group
611 */
613 for (CHGraph::CHNodeSetTy::iterator it = group.begin(),
614 eit = group.end(); it != eit; ++it)
615 {
618 veit = vecs.end(); vit != veit; ++vit)
619 {
620 for (vector<const FunObjVar*>::const_iterator fit = (*vit).begin(),
621 feit = (*vit).end(); fit != feit; ++fit)
622 {
623 virtualFunctions.insert(*fit);
624 }
625 }
626 }
627
628 /*
629 * build a set of pairs of demangled function name and function in a
630 * specific group, items in the set will be sort by the first item of the
631 * pair, so all the virtual functions in a group will be sorted by the
632 * demangled function name
633 * <f, A::f>
634 * <f, B::f>
635 * <g, A::g>
636 * <g, B::g>
637 * <g, C::g>
638 * <~A, A::~A>
639 * <~B, B::~B>
640 * <~C, C::~C>
641 * ...
642 */
644 for (set<const FunObjVar*>::iterator fit = virtualFunctions.begin(),
645 feit = virtualFunctions.end(); fit != feit; ++fit)
646 {
647 const FunObjVar* f = *fit;
648 struct DemangledName dname = demangle(f->getName());
650 }
651 for (set<pair<string, const FunObjVar*>>::iterator it = fNameSet.begin(),
652 eit = fNameSet.end(); it != eit; ++it)
653 {
654 chg->virtualFunctionToIDMap[it->second] = chg->vfID++;
655 }
656 }
657}
Map< const FunObjVar *, u32_t > virtualFunctionToIDMap
Definition CHG.h:336
u32_t vfID
Definition CHG.h:327
Set< const CHNode * > CHNodeSetTy
Definition CHG.h:246
const std::vector< FuncVector > & getVirtualFunctionVectors() const
Definition CHG.h:175

◆ connectInheritEdgeViaCall()

void CHGBuilder::connectInheritEdgeViaCall ( const Function caller,
const CallBase cs 
)

Definition at line 164 of file CHGBuilder.cpp.

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;
176 if(caller->arg_size() == 0)
177 {
178 return;
179 }
183 if (csThisPtr != nullptr && samePtr)
184 {
185 struct DemangledName basename = demangle(callee->getName().str());
187 basename.className.size() > 0)
188 {
189 chg->addEdge(dname.className, basename.className, CHEdge::INHERITANCE);
190 }
191 }
192 }
193}
const Function * getCallee(const CallBase *cs)
Definition LLVMUtil.h:97
const Argument * getConstructorThisPtr(const Function *fun)
Definition CppUtil.cpp:528
bool isSameThisPtrInConstructor(const Argument *thisPtr1, const Value *thisPtr2)
Definition CppUtil.cpp:484
const Value * getVCallThisPtr(const CallBase *cs)
Definition CppUtil.cpp:411
llvm::Argument Argument
Definition BasicTypes.h:147

◆ connectInheritEdgeViaStore()

void CHGBuilder::connectInheritEdgeViaStore ( const Function caller,
const StoreInst store 
)

Definition at line 195 of file CHGBuilder.cpp.

196{
197 struct DemangledName dname = demangle(caller->getName().str());
198 if (const ConstantExpr *ce = SVFUtil::dyn_cast<ConstantExpr>(storeInst->getValueOperand()))
199 {
200 if (ce->getOpcode() == Instruction::BitCast)
201 {
202 const Value* bitcastval = ce->getOperand(0);
203 if (const ConstantExpr *bcce = SVFUtil::dyn_cast<ConstantExpr>(bitcastval))
204 {
205 if (bcce->getOpcode() == Instruction::GetElementPtr)
206 {
207 const Value* gepval = bcce->getOperand(0);
209 {
210 string vtblClassName = getClassNameFromVtblObj(gepval->getName().str());
211 if (vtblClassName.size() > 0 && dname.className.compare(vtblClassName) != 0)
212 {
214 }
215 }
216 }
217 }
218 }
219 }
220}

◆ createNode()

CHNode * CHGBuilder::createNode ( const std::string &  name)

Definition at line 243 of file CHGBuilder.cpp.

244{
245 assert(!chg->getNode(className) && "this node should never be created before!");
246 CHNode * node = new CHNode(className, chg->classNum++);
247 chg->classNameToNodeMap[className] = node;
248 chg->addGNode(node->getId(), node);
249 if (className.size() > 0 && className[className.size() - 1] == '>')
250 {
251 string templateName = getBeforeBrackets(className);
253 if (!templateNode)
254 {
255 DBOUT(DCHA, outs() << "\t Create Template CHANode " + templateName + " for class " + className + "...\n");
257 templateNode->setTemplate();
258 }
261 }
262 return node;
263}
@ INSTANTCE
Definition CHG.h:85
void addInstances(const std::string templateName, CHNode *node)
Definition CHG.h:296
u32_t classNum
Definition CHG.h:326
Map< std::string, CHNode * > classNameToNodeMap
Definition CHG.h:329
void addGNode(NodeID id, NodeType *node)
Add a Node.
NodeID getId() const
Get ID.
Definition SVFValue.h:160
std::string getBeforeBrackets(const std::string &name)
Definition CppUtil.cpp:127

◆ getCSClasses()

const CHGraph::CHNodeSetTy & CHGBuilder::getCSClasses ( const CallBase cs)

Definition at line 702 of file CHGBuilder.cpp.

703{
704 assert(cppUtil::isVirtualCallSite(cs) && "not virtual callsite!");
705
706 ICFGNode* icfgNode = llvmModuleSet()->getICFGNode(cs);
707
708 CHGraph::CallNodeToCHNodesMap::const_iterator it = chg->callNodeToClassesMap.find(icfgNode);
709 if (it != chg->callNodeToClassesMap.end())
710 {
711 return it->second;
712 }
713 else
714 {
716
717 if(thisPtrClassNames.empty())
718 {
719 // if we cannot infer classname, conservatively push all class nodes
720 for (const auto &node: *chg)
721 {
722 chg->callNodeToClassesMap[icfgNode].insert(node.second);
723 }
724 return chg->callNodeToClassesMap[icfgNode];
725 }
726
727 for (const auto &thisPtrClassName: thisPtrClassNames)
728 {
730 {
732 chg->callNodeToClassesMap[icfgNode].insert(thisNode);
733 for (CHGraph::CHNodeSetTy::const_iterator it2 = instAndDesces.begin(), eit = instAndDesces.end(); it2 != eit; ++it2)
734 chg->callNodeToClassesMap[icfgNode].insert(*it2);
735 }
736 }
737 return chg->callNodeToClassesMap[icfgNode];
738 }
739}
const CHGraph::CHNodeSetTy & getInstancesAndDescendants(const std::string &className)
CallNodeToCHNodesMap callNodeToClassesMap
Definition CHG.h:334
Set< std::string > getClassNameOfThisPtr(const CallBase *cs)
Definition CppUtil.cpp:676

◆ getInstancesAndDescendants()

const CHGraph::CHNodeSetTy & CHGBuilder::getInstancesAndDescendants ( const std::string &  className)

Definition at line 303 of file CHGBuilder.cpp.

305{
306
307 CHGraph::NameToCHNodesMap::const_iterator it = chg->classNameToInstAndDescsMap.find(className);
308 if (it != chg->classNameToInstAndDescsMap.end())
309 {
310 return it->second;
311 }
312 else
313 {
314 chg->classNameToInstAndDescsMap[className] = chg->getDescendants(className);
315 if (chg->getNode(className)->isTemplate())
316 {
317 const CHNodeSetTy& instances = chg->getInstances(className);
318 for (CHNodeSetTy::const_iterator it = instances.begin(), eit = instances.end(); it != eit; ++it)
319 {
320 const CHNode *node = *it;
321 chg->classNameToInstAndDescsMap[className].insert(node);
323 for (CHNodeSetTy::const_iterator dit =
324 instance_descendants.begin(), deit =
325 instance_descendants.end(); dit != deit; ++dit)
326 {
327 chg->classNameToInstAndDescsMap[className].insert(*dit);
328 }
329 }
330 }
331 return chg->classNameToInstAndDescsMap[className];
332 }
333}
const CHNodeSetTy & getInstances(const std::string className)
Definition CHG.h:309
NameToCHNodesMap classNameToInstAndDescsMap
Definition CHG.h:332
const CHNodeSetTy & getDescendants(const std::string className)
Definition CHG.h:305
bool isTemplate() const
Definition CHG.h:165

◆ llvmModuleSet()

LLVMModuleSet * CHGBuilder::llvmModuleSet ( )
private

Definition at line 59 of file CHGBuilder.cpp.

60{
62}
static LLVMModuleSet * getLLVMModuleSet()
Definition LLVMModule.h:131

◆ readInheritanceMetadataFromModule()

void CHGBuilder::readInheritanceMetadataFromModule ( const Module M)

Definition at line 222 of file CHGBuilder.cpp.

223{
224 for (Module::const_named_metadata_iterator mdit = M.named_metadata_begin(),
225 mdeit = M.named_metadata_end(); mdit != mdeit; ++mdit)
226 {
227 const NamedMDNode *md = &*mdit;
228 string mdname = md->getName().str();
229 if (mdname.compare(0, 15, "__cxx_bases_of_") != 0)
230 continue;
231 string className = mdname.substr(15);
232 for (NamedMDNode::const_op_iterator opit = md->op_begin(),
233 opeit = md->op_end(); opit != opeit; ++opit)
234 {
235 const MDNode *N = *opit;
236 const MDString* mdstr = SVFUtil::cast<MDString>(N->getOperand(0).get());
237 string baseName = mdstr->getString().str();
239 }
240 }
241}
llvm::MDString MDString
Definition BasicTypes.h:103
llvm::NamedMDNode NamedMDNode
LLVM metadata and debug information.
Definition BasicTypes.h:113
llvm::MDNode MDNode
Definition BasicTypes.h:114

Member Data Documentation

◆ chg

CHGraph* SVF::CHGBuilder::chg
private

Definition at line 42 of file CHGBuilder.h.


The documentation for this class was generated from the following files: