Static Value-Flow Analysis
Loading...
Searching...
No Matches
VFG.cpp
Go to the documentation of this file.
1//===- VFG.cpp -- Sparse value-flow graph-----------------------------------//
2//
3// SVF: Static Value-Flow Analysis
4//
5// Copyright (C) <2013-2018> <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 * VFG.cpp
25 *
26 * Created on: Sep 11, 2018
27 * Author: Yulei Sui
28 */
29
30
31#include <Graphs/SVFGNode.h>
32#include "Util/Options.h"
33#include "Graphs/VFG.h"
34#include "Util/SVFUtil.h"
35
36using namespace SVF;
37using namespace SVFUtil;
38
39const std::string VFGNode::toString() const
40{
41 std::string str;
42 std::stringstream rawstr(str);
43 rawstr << "VFGNode ID: " << getId() << " ";
44 return rawstr.str();
45}
46
47const std::string StmtVFGNode::toString() const
48{
49 std::string str;
50 std::stringstream rawstr(str);
51 rawstr << "StmtVFGNode ID: " << getId() << " ";
53 return rawstr.str();
54}
55
57{
58 NodeBS nb;
60 return nb;
61}
62
63const std::string LoadVFGNode::toString() const
64{
65 std::string str;
66 std::stringstream rawstr(str);
67 rawstr << "LoadVFGNode ID: " << getId() << " ";
69 return rawstr.str();
70}
71
73{
74 NodeBS nb;
75 for (auto edge: getOutEdges())
76 {
77 if (IndirectSVFGEdge *iedge = SVFUtil::dyn_cast<IndirectSVFGEdge>(edge))
78 {
79 nb |= iedge->getPointsTo();
80 }
81 }
82 return nb;
83}
84
85const std::string StoreVFGNode::toString() const
86{
87 std::string str;
88 std::stringstream rawstr(str);
89 rawstr << "StoreVFGNode ID: " << getId() << " ";
91 return rawstr.str();
92}
93
95{
96 NodeBS nb;
98 return nb;
99}
100
101const std::string CopyVFGNode::toString() const
102{
103 std::string str;
104 std::stringstream rawstr(str);
105 rawstr << "CopyVFGNode ID: " << getId() << " ";
106 rawstr << getSVFStmt()->toString();
107 return rawstr.str();
108}
109
111{
112 NodeBS nb;
113 nb.set(getRes()->getId());
114 return nb;
115}
116
117const std::string CmpVFGNode::toString() const
118{
119 std::string str;
120 std::stringstream rawstr(str);
121 rawstr << "CmpVFGNode ID: " << getId() << " ";
122 rawstr << "SVFStmt: [" << res->getId() << " = cmp(";
123 for(CmpVFGNode::OPVers::const_iterator it = opVerBegin(), eit = opVerEnd();
124 it != eit; it++)
125 rawstr << it->second->getId() << ", ";
126 rawstr << ")]\n";
127 rawstr << " " << res->valueOnlyToString();
128 return rawstr.str();
129}
130
132{
133 NodeBS nb;
134 nb.set(getRes()->getId());
135 return nb;
136}
137
138const std::string BinaryOPVFGNode::toString() const
139{
140 std::string str;
141 std::stringstream rawstr(str);
142 rawstr << "BinaryOPVFGNode ID: " << getId() << " ";
143 rawstr << "SVFStmt: [" << res->getId() << " = Binary(";
144 for(BinaryOPVFGNode::OPVers::const_iterator it = opVerBegin(), eit = opVerEnd();
145 it != eit; it++)
146 rawstr << it->second->getId() << ", ";
147 rawstr << ")]\t";
148 rawstr << " " << res->valueOnlyToString();
149 return rawstr.str();
150}
151
153{
154 NodeBS nb;
155 nb.set(getRes()->getId());
156 return nb;
157}
158
159const std::string UnaryOPVFGNode::toString() const
160{
161 std::string str;
162 std::stringstream rawstr(str);
163 rawstr << "UnaryOPVFGNode ID: " << getId() << " ";
164 rawstr << "SVFStmt: [" << res->getId() << " = Unary(";
165 for(UnaryOPVFGNode::OPVers::const_iterator it = opVerBegin(), eit = opVerEnd();
166 it != eit; it++)
167 rawstr << it->second->getId() << ", ";
168 rawstr << ")]\t";
169 rawstr << " " << res->valueOnlyToString();
170 return rawstr.str();
171}
172
174{
175 return NodeBS();
176}
177
178const std::string BranchVFGNode::toString() const
179{
180 std::string str;
181 std::stringstream rawstr(str);
182 rawstr << "BranchVFGNode ID: " << getId() << " ";
183 rawstr << "SVFStmt: [" << brstmt->toString() << "\t";
184 return rawstr.str();
185}
186
188{
189 NodeBS nb;
191 return nb;
192}
193
194const std::string GepVFGNode::toString() const
195{
196 std::string str;
197 std::stringstream rawstr(str);
198 rawstr << "GepVFGNode ID: " << getId() << " ";
199 rawstr << getSVFStmt()->toString();
200 return rawstr.str();
201}
202
204{
205 NodeBS nb;
206 nb.set(getRes()->getId());
207 return nb;
208}
209
210const std::string PHIVFGNode::toString() const
211{
212 std::string str;
213 std::stringstream rawstr(str);
214 rawstr << "PHIVFGNode ID: " << getId() << " ";
215 rawstr << "SVFVar: [" << res->getId() << " = PHI(";
216 for(PHIVFGNode::OPVers::const_iterator it = opVerBegin(), eit = opVerEnd();
217 it != eit; it++)
218 rawstr << it->second->getId() << ", ";
219 rawstr << ")]\t";
220 rawstr << " " << res->valueOnlyToString();
221 return rawstr.str();
222}
223
224
225const std::string IntraPHIVFGNode::toString() const
226{
227 std::string str;
228 std::stringstream rawstr(str);
229 rawstr << "IntraPHIVFGNode ID: " << getId() << " ";
230 rawstr << "SVFVar: [" << res->getId() << " = PHI(";
231 for(PHIVFGNode::OPVers::const_iterator it = opVerBegin(), eit = opVerEnd();
232 it != eit; it++)
233 rawstr << it->second->getId() << ", ";
234 rawstr << ")]\t";
235 rawstr << " " << res->valueOnlyToString();
236 return rawstr.str();
237}
238
240{
241 NodeBS nb;
243 return nb;
244}
245
246const std::string AddrVFGNode::toString() const
247{
248 std::string str;
249 std::stringstream rawstr(str);
250 rawstr << "AddrVFGNode ID: " << getId() << " ";
251 rawstr << getSVFStmt()->toString();
252 return rawstr.str();
253}
254
255
256const std::string ArgumentVFGNode::toString() const
257{
258 std::string str;
259 std::stringstream rawstr(str);
260 rawstr << "ArgumentVFGNode ID: " << getId() << " ";
261 rawstr << param->toString();
262 return rawstr.str();
263}
264
266{
267 NodeBS nb;
268 nb.set(getParam()->getId());
269 return nb;
270}
271
272const std::string ActualParmVFGNode::toString() const
273{
274 std::string str;
275 std::stringstream rawstr(str);
276 rawstr << "ActualParmVFGNode ID: " << getId() << " ";
277 rawstr << "CS[" << getCallSite()->getSourceLoc() << "]";
278 rawstr << param->toString();
279 return rawstr.str();
280}
281
283{
284 NodeBS nb;
285 nb.set(getParam()->getId());
286 return nb;
287}
288
289const std::string FormalParmVFGNode::toString() const
290{
291 std::string str;
292 std::stringstream rawstr(str);
293 rawstr << "FormalParmVFGNode ID: " << getId() << " ";
294 rawstr << "Fun[" << getFun()->getName() << "]";
295 rawstr << param->toString();
296 return rawstr.str();
297}
298
300{
301 NodeBS nb;
302 nb.set(getRev()->getId());
303 return nb;
304}
305
306const std::string ActualRetVFGNode::toString() const
307{
308 std::string str;
309 std::stringstream rawstr(str);
310 rawstr << "ActualRetVFGNode ID: " << getId() << " ";
311 rawstr << "CS[" << getCallSite()->getSourceLoc() << "]";
312 rawstr << param->toString();
313 return rawstr.str();
314}
315
316
318{
319 NodeBS nb;
320 nb.set(getRet()->getId());
321 return nb;
322}
323
324const std::string FormalRetVFGNode::toString() const
325{
326 std::string str;
327 std::stringstream rawstr(str);
328 rawstr << "FormalRetVFGNode ID: " << getId() << " ";
329 rawstr << "Fun[" << getFun()->getName() << "]";
330 rawstr << param->toString();
331 return rawstr.str();
332}
333
334
335const std::string InterPHIVFGNode::toString() const
336{
337 std::string str;
338 std::stringstream rawstr(str);
339 if(isFormalParmPHI())
340 rawstr << "FormalParmPHI ID: " << getId() << " SVFVar ID: " << res->getId() << "\n" << res->valueOnlyToString();
341 else
342 rawstr << "ActualRetPHI ID: " << getId() << " SVFVar ID: " << res->getId() << "\n" << res->valueOnlyToString();
343 return rawstr.str();
344}
345
347{
348 NodeBS nb;
349 nb.set(getSVFVar()->getId());
350 return nb;
351}
352
353const std::string NullPtrVFGNode::toString() const
354{
355 std::string str;
356 std::stringstream rawstr(str);
357 rawstr << "NullPtrVFGNode ID: " << getId();
358 rawstr << " SVFVar ID: " << node->getId() << "\n";
359 return rawstr.str();
360}
361
362
363const std::string VFGEdge::toString() const
364{
365 std::string str;
366 std::stringstream rawstr(str);
367 rawstr << "VFGEdge: [" << getDstID() << "<--" << getSrcID() << "]\t";
368 return rawstr.str();
369}
370
371const std::string DirectSVFGEdge::toString() const
372{
373 std::string str;
374 std::stringstream rawstr(str);
375 rawstr << "DirectVFGEdge: [" << getDstID() << "<--" << getSrcID() << "]\t";
376 return rawstr.str();
377}
378
379const std::string IntraDirSVFGEdge::toString() const
380{
381 std::string str;
382 std::stringstream rawstr(str);
383 rawstr << "IntraDirSVFGEdge: [" << getDstID() << "<--" << getSrcID() << "]\t";
384 return rawstr.str();
385}
386
387const std::string CallDirSVFGEdge::toString() const
388{
389 std::string str;
390 std::stringstream rawstr(str);
391 rawstr << "CallDirSVFGEdge CallSite ID: " << getCallSiteId() << " [";
392 rawstr << getDstID() << "<--" << getSrcID() << "]\t";
393 return rawstr.str();
394}
395
396const std::string RetDirSVFGEdge::toString() const
397{
398 std::string str;
399 std::stringstream rawstr(str);
400 rawstr << "RetDirSVFGEdge CallSite ID: " << getCallSiteId() << " [";
401 rawstr << getDstID() << "<--" << getSrcID() << "]\t";
402 return rawstr.str();
403}
404
405
406
408 ArgumentVFGNode(id, n, FRet), fun(f)
409{
410}
411
413{
414
415}
416
425VFG::VFG(CallGraph* cg, VFGK k): totalVFGNode(0), callgraph(cg), pag(SVFIR::getPAG()), kind(k)
426{
427
428 DBOUT(DGENERAL, outs() << pasMsg("\tCreate VFG Top Level Node\n"));
429 addVFGNodes();
430
431 DBOUT(DGENERAL, outs() << pasMsg("\tCreate SVFG Direct Edge\n"));
433}
434
439{
440 pag = nullptr;
441}
442
443
448{
449
450 // initialize dummy definition null pointers in order to uniform the construction
451 // to be noted for black hole pointer it has already has address edge connected,
452 // and its definition will be set when processing addr SVFIR edge.
454
455 // initialize address nodes
457 for (SVFStmt::SVFStmtSetTy::iterator iter = addrs.begin(), eiter =
458 addrs.end(); iter != eiter; ++iter)
459 {
460 addAddrVFGNode(SVFUtil::cast<AddrStmt>(*iter));
461 }
462
463 // initialize copy nodes
465 for (SVFStmt::SVFStmtSetTy::iterator iter = copys.begin(), eiter =
466 copys.end(); iter != eiter; ++iter)
467 {
468 const CopyStmt* edge = SVFUtil::cast<CopyStmt>(*iter);
469 assert(!isPhiCopyEdge(edge) && "Copy edges can not be a PhiNode (or from PhiNode)");
471 }
472
473 // initialize gep nodes
475 for (SVFStmt::SVFStmtSetTy::iterator iter = ngeps.begin(), eiter =
476 ngeps.end(); iter != eiter; ++iter)
477 {
478 addGepVFGNode(SVFUtil::cast<GepStmt>(*iter));
479 }
480
481 // initialize load nodes
483 for (SVFStmt::SVFStmtSetTy::iterator iter = loads.begin(), eiter =
484 loads.end(); iter != eiter; ++iter)
485 {
486 addLoadVFGNode(SVFUtil::cast<LoadStmt>(*iter));
487 }
488
489 // initialize store nodes
491 for (SVFStmt::SVFStmtSetTy::iterator iter = stores.begin(), eiter =
492 stores.end(); iter != eiter; ++iter)
493 {
494 addStoreVFGNode(SVFUtil::cast<StoreStmt>(*iter));
495 }
496
498 for (SVFStmt::SVFStmtSetTy::iterator iter = forks.begin(), eiter =
499 forks.end(); iter != eiter; ++iter)
500 {
501 TDForkPE* forkedge = SVFUtil::cast<TDForkPE>(*iter);
502 for(u32_t i = 0; i < forkedge->getOpVarNum(); i++)
503 addActualParmVFGNode(forkedge->getOpVar(i), forkedge->getOpCallICFGNode(i));
504 }
505
506 // initialize actual parameter nodes
507 for(SVFIR::CSToArgsListMap::iterator it = pag->getCallSiteArgsMap().begin(), eit = pag->getCallSiteArgsMap().end(); it !=eit; ++it)
508 {
509
510 for(SVFIR::ValVarList::iterator pit = it->second.begin(), epit = it->second.end(); pit!=epit; ++pit)
511 {
512 const ValVar* svfVar = *pit;
515 }
516 }
517
518 // initialize actual return nodes (callsite return)
519 for(SVFIR::CSToRetMap::iterator it = pag->getCallSiteRets().begin(), eit = pag->getCallSiteRets().end(); it !=eit; ++it)
520 {
521
525 if(isInterestedSVFVar(it->second) == false || hasDef(it->second))
526 continue;
527
528 addActualRetVFGNode(it->second,it->first->getCallICFGNode());
529 }
530
531 // initialize formal parameter nodes
532 for(SVFIR::FunToArgsListMap::iterator it = pag->getFunArgsMap().begin(), eit = pag->getFunArgsMap().end(); it !=eit; ++it)
533 {
534 const FunObjVar* func = it->first;
535
536 for(SVFIR::ValVarList::iterator pit = it->second.begin(), epit = it->second.end(); pit!=epit; ++pit)
537 {
538 const ValVar* param = *pit;
539 if (isInterestedSVFVar(param) == false || hasBlackHoleConstObjAddrAsDef(param))
540 continue;
541
542 const CallPE* callPE = pag->getCallPEForFormalParm(param);
543 addFormalParmVFGNode(param,func,callPE);
544 }
545
546 if (func->isVarArg())
547 {
550 continue;
551
554 }
555 }
556
557 // initialize formal return nodes (callee return)
558 for (SVFIR::FunToRetMap::iterator it = pag->getFunRets().begin(), eit = pag->getFunRets().end(); it != eit; ++it)
559 {
560 const FunObjVar* func = it->first;
561
562 const ValVar* uniqueFunRetNode = it->second;
563
564 RetPESet retPEs;
565 if (uniqueFunRetNode->hasOutgoingEdges(SVFStmt::Ret))
566 {
567 for (SVFStmt::SVFStmtSetTy::const_iterator cit = uniqueFunRetNode->getOutgoingEdgesBegin(SVFStmt::Ret),
568 ecit = uniqueFunRetNode->getOutgoingEdgesEnd(SVFStmt::Ret);
569 cit != ecit; ++cit)
570 {
571 const RetPE* retPE = SVFUtil::cast<RetPE>(*cit);
572 if (isInterestedSVFVar(retPE->getLHSVar()))
573 retPEs.insert(retPE);
574 }
575 }
576
579 }
580
581 // initialize llvm phi nodes (phi of top level pointers)
583 for (SVFStmt::SVFStmtSetTy::iterator iter = phis.begin(), eiter =
584 phis.end(); iter != eiter; ++iter)
585 {
586 const PhiStmt* edge = SVFUtil::cast<PhiStmt>(*iter);
587 if(isInterestedSVFVar(edge->getRes()))
589 }
590 // initialize select statement
592 for (SVFStmt::SVFStmtSetTy::iterator iter = selects.begin(), eiter =
593 selects.end(); iter != eiter; ++iter)
594 {
595 const MultiOpndStmt* edge = SVFUtil::cast<MultiOpndStmt>(*iter);
596 if(isInterestedSVFVar(edge->getRes()))
598 }
599 // initialize llvm binary nodes (binary operators)
601 for (SVFStmt::SVFStmtSetTy::iterator iter = binaryops.begin(), eiter =
602 binaryops.end(); iter != eiter; ++iter)
603 {
604 const BinaryOPStmt* edge = SVFUtil::cast<BinaryOPStmt>(*iter);
605 if(isInterestedSVFVar(edge->getRes()))
607 }
608 // initialize llvm unary nodes (unary operators)
610 for (SVFStmt::SVFStmtSetTy::iterator iter = unaryops.begin(), eiter =
611 unaryops.end(); iter != eiter; ++iter)
612 {
613 const UnaryOPStmt* edge = SVFUtil::cast<UnaryOPStmt>(*iter);
614 if(isInterestedSVFVar(edge->getRes()))
616 }
617 // initialize llvm unary nodes (unary operators)
619 for (SVFStmt::SVFStmtSetTy::iterator iter = brs.begin(), eiter =
620 brs.end(); iter != eiter; ++iter)
621 {
622 const BranchStmt* edge = SVFUtil::cast<BranchStmt>(*iter);
623 if(isInterestedSVFVar(edge->getBranchInst()))
625 }
626 // initialize llvm cmp nodes (comparison)
628 for (SVFStmt::SVFStmtSetTy::iterator iter = cmps.begin(), eiter =
629 cmps.end(); iter != eiter; ++iter)
630 {
631 const CmpStmt* edge = SVFUtil::cast<CmpStmt>(*iter);
632 if(isInterestedSVFVar(edge->getRes()))
634 }
635}
636
641{
646 if (edge != nullptr)
647 {
648 assert(edge->isDirectVFGEdge() && "this should be a direct value flow edge!");
649 return nullptr;
650 }
651 else
652 {
653 if(srcNode!=dstNode)
654 {
656 return (addVFGEdge(directEdge) ? directEdge : nullptr);
657 }
658 else
659 return nullptr;
660 }
661}
662
667{
671 if (edge != nullptr)
672 {
673 assert(edge->isCallDirectVFGEdge() && "this should be a direct value flow edge!");
674 return nullptr;
675 }
676 else
677 {
679 return (addVFGEdge(callEdge) ? callEdge : nullptr);
680 }
681}
682
687{
691 if (edge != nullptr)
692 {
693 assert(edge->isRetDirectVFGEdge() && "this should be a direct value flow edge!");
694 return nullptr;
695 }
696 else
697 {
699 return (addVFGEdge(retEdge) ? retEdge : nullptr);
700 }
701}
702
703
708{
709
710 for(iterator it = begin(), eit = end(); it!=eit; ++it)
711 {
712 NodeID nodeId = it->first;
713 VFGNode* node = it->second;
714
715 if(StmtVFGNode* stmtNode = SVFUtil::dyn_cast<StmtVFGNode>(node))
716 {
718 if(SVFUtil::isa<AddrVFGNode>(stmtNode))
719 continue;
721 if (stmtNode->getSrcNode()->isConstDataOrAggDataButNotNullPtr() == false)
722 // for ptr vfg, we skip src node of integer type if it is at a int2ptr copystmt
723 if(isInterestedSVFVar(stmtNode->getSrcNode()))
724 addIntraDirectVFEdge(getDef(SVFUtil::cast<ValVar>(stmtNode->getSrcNode())), nodeId);
725 if (const GepStmt* gepStmt = SVFUtil::dyn_cast<GepStmt>(stmtNode->getSVFStmt()))
726 {
727 for (const auto &varType: gepStmt->getOffsetVarAndGepTypePairVec())
728 {
729 if(varType.first->isConstDataOrAggDataButNotNullPtr() || isInterestedSVFVar(varType.first) == false)
730 continue;
732 }
733 }
735 if(SVFUtil::isa<StoreVFGNode>(stmtNode) && (stmtNode->getDstNode()->isConstDataOrAggDataButNotNullPtr() == false))
736 {
737 addIntraDirectVFEdge(getDef(SVFUtil::cast<ValVar>(stmtNode->getDstNode())), nodeId);
738 }
739
740 }
741 else if(PHIVFGNode* phiNode = SVFUtil::dyn_cast<PHIVFGNode>(node))
742 {
743 for (PHIVFGNode::OPVers::const_iterator it = phiNode->opVerBegin(), eit = phiNode->opVerEnd(); it != eit; it++)
744 {
745 if (it->second->isConstDataOrAggDataButNotNullPtr() == false)
747 }
748 }
749 else if(BinaryOPVFGNode* binaryNode = SVFUtil::dyn_cast<BinaryOPVFGNode>(node))
750 {
751 for (BinaryOPVFGNode::OPVers::const_iterator it = binaryNode->opVerBegin(), eit = binaryNode->opVerEnd(); it != eit; it++)
752 {
753 if (it->second->isConstDataOrAggDataButNotNullPtr() == false)
755 }
756 }
757 else if(UnaryOPVFGNode* unaryNode = SVFUtil::dyn_cast<UnaryOPVFGNode>(node))
758 {
759 for (UnaryOPVFGNode::OPVers::const_iterator it = unaryNode->opVerBegin(), eit = unaryNode->opVerEnd(); it != eit; it++)
760 {
761 if (it->second->isConstDataOrAggDataButNotNullPtr() == false)
763 }
764 }
765 else if(CmpVFGNode* cmpNode = SVFUtil::dyn_cast<CmpVFGNode>(node))
766 {
767 for (CmpVFGNode::OPVers::const_iterator it = cmpNode->opVerBegin(), eit = cmpNode->opVerEnd(); it != eit; it++)
768 {
769 if (it->second->isConstDataOrAggDataButNotNullPtr() == false)
771 }
772 }
773 else if(BranchVFGNode* branchNode = SVFUtil::dyn_cast<BranchVFGNode>(node))
774 {
775 const ValVar* cond = branchNode->getBranchStmt()->getCondition();
776 if (cond->isConstDataOrAggDataButNotNullPtr() == false)
778 }
779 else if(ActualParmVFGNode* actualParm = SVFUtil::dyn_cast<ActualParmVFGNode>(node))
780 {
781 if (actualParm->getParam()->isConstDataOrAggDataButNotNullPtr() == false)
783 }
784 else if(FormalParmVFGNode* formalParm = SVFUtil::dyn_cast<FormalParmVFGNode>(node))
785 {
786 if(const CallPE* callPE = formalParm->getCallPE())
787 {
788 for(u32_t i = 0; i < callPE->getOpVarNum(); i++)
789 {
790 if(isInterestedSVFVar(callPE->getOpVar(i)))
791 {
792 const CallICFGNode* cs = callPE->getOpCallICFGNode(i);
793 ActualParmVFGNode* acutalParm = getActualParmVFGNode(callPE->getOpVar(i), cs);
795 }
796 }
797 }
798 }
799 else if(FormalRetVFGNode* calleeRet = SVFUtil::dyn_cast<FormalRetVFGNode>(node))
800 {
803
805 for(RetPESet::const_iterator it = calleeRet->retPEBegin(), eit = calleeRet->retPEEnd(); it!=eit; ++it)
806 {
807 ActualRetVFGNode* callsiteRev = getActualRetVFGNode((*it)->getLHSVar());
808 const CallICFGNode* callBlockNode = (*it)->getCallSite();
810 }
811 }
814 }
815
818 {
821 for (SVFStmt::SVFStmtSetTy::iterator iter = forks.begin(), eiter =
822 forks.end(); iter != eiter; ++iter)
823 {
824 TDForkPE* forkedge = SVFUtil::cast<TDForkPE>(*iter);
826 for(u32_t i = 0; i < forkedge->getOpVarNum(); i++)
827 {
828 if(isInterestedSVFVar(forkedge->getOpVar(i)))
829 {
830 const CallICFGNode* cs = forkedge->getOpCallICFGNode(i);
833 }
834 }
835 }
838 for (SVFStmt::SVFStmtSetTy::iterator iter = joins.begin(), eiter =
839 joins.end(); iter != eiter; ++iter)
840 {
841 TDJoinPE* joinedge = SVFUtil::cast<TDJoinPE>(*iter);
842 NodeID callsiteRev = getDef(joinedge->getLHSVar());
844 addRetEdge(calleeRet->getId(),callsiteRev, getCallSiteID(joinedge->getCallSite(), calleeRet->getFun()));
845 }
846 }
847}
848
853{
854 VFGEdge edge(src,dst,kind);
857 if (outEdge && inEdge)
858 {
859 assert(outEdge == inEdge && "edges not match");
860 return outEdge;
861 }
862 else
863 return nullptr;
864}
865
866
871{
872 VFGEdge edge(src,dst,kind);
875 if (outEdge && inEdge)
876 {
877 assert(outEdge == inEdge && "edges not match");
878 return outEdge;
879 }
880 else
881 return nullptr;
882}
883
888{
892 if (outEdge && inEdge)
893 {
894 assert(outEdge == inEdge && "edges not match");
895 return outEdge;
896 }
897 else
898 return nullptr;
899}
900
901
906{
907 return hasIntraVFGEdge(const_cast<VFGNode*>(src),const_cast<VFGNode*>(dst),kind);
908}
909
910
914void VFG::dump(const std::string& file, bool simple)
915{
917}
918
923{
924 SVF::ViewGraph(this, "Value Flow Graph");
925}
926
927
929{
930 VFGEdgeSetTy vfEdgesAtIndCallSite;
931 PointerAnalysis::CallEdgeMap::const_iterator iter = pta->getIndCallMap().begin();
932 PointerAnalysis::CallEdgeMap::const_iterator eiter = pta->getIndCallMap().end();
933 for (; iter != eiter; iter++)
934 {
935 const CallICFGNode* newcs = iter->first;
936 assert(newcs->isIndirectCall() && "this is not an indirect call?");
938 for (PointerAnalysis::FunctionSet::const_iterator func_iter = functions.begin(); func_iter != functions.end(); func_iter++)
939 {
940 const FunObjVar* func = *func_iter;
941 connectCallerAndCallee(newcs, func, vfEdgesAtIndCallSite);
942 }
943 }
944}
945
951{
952 SVFIR * pag = SVFIR::getPAG();
953 CallSiteID csId = getCallSiteID(callBlockNode, callee);
954 const RetICFGNode* retBlockNode = callBlockNode->getRetICFGNode();
955 // connect actual and formal param
956 if (pag->hasCallSiteArgsMap(callBlockNode) && pag->hasFunArgsList(callee) &&
957 matchArgs(callBlockNode, callee))
958 {
959 const SVFIR::ValVarList& csArgList = pag->getCallSiteArgsList(callBlockNode);
961 SVFIR::ValVarList::const_iterator csArgIt = csArgList.begin(), csArgEit = csArgList.end();
962 SVFIR::ValVarList::const_iterator funArgIt = funArgList.begin(), funArgEit = funArgList.end();
963 for (; funArgIt != funArgEit && csArgIt != csArgEit; funArgIt++, csArgIt++)
964 {
965 const ValVar *cs_arg = *csArgIt;
966 const ValVar *fun_arg = *funArgIt;
968 connectAParamAndFParam(cs_arg, fun_arg, callBlockNode, csId, edges);
969 }
970 assert(funArgIt == funArgEit && "function has more arguments than call site");
971
972 if (callee->isVarArg())
973 {
977 {
978 for (; csArgIt != csArgEit; csArgIt++)
979 {
980 const ValVar *cs_arg = *csArgIt;
982 connectAParamAndFParam(cs_arg, varFunArgNode, callBlockNode, csId, edges);
983 }
984 }
985 }
986 }
987
988 // connect actual return and formal return
990 {
995 }
996}
997
1001const SVFVar* VFG::getLHSTopLevPtr(const VFGNode* node) const
1002{
1003
1004 if(const AddrVFGNode* addr = SVFUtil::dyn_cast<AddrVFGNode>(node))
1005 return addr->getDstNode();
1006 else if(const CopyVFGNode* copy = SVFUtil::dyn_cast<CopyVFGNode>(node))
1007 return copy->getDstNode();
1008 else if(const GepVFGNode* gep = SVFUtil::dyn_cast<GepVFGNode>(node))
1009 return gep->getDstNode();
1010 else if(const LoadVFGNode* load = SVFUtil::dyn_cast<LoadVFGNode>(node))
1011 return load->getDstNode();
1012 else if(const PHIVFGNode* phi = SVFUtil::dyn_cast<PHIVFGNode>(node))
1013 return phi->getRes();
1014 else if(const CmpVFGNode* cmp = SVFUtil::dyn_cast<CmpVFGNode>(node))
1015 return cmp->getRes();
1016 else if(const BinaryOPVFGNode* bop = SVFUtil::dyn_cast<BinaryOPVFGNode>(node))
1017 return bop->getRes();
1018 else if(const UnaryOPVFGNode* uop = SVFUtil::dyn_cast<UnaryOPVFGNode>(node))
1019 return uop->getRes();
1020 else if(const ActualParmVFGNode* ap = SVFUtil::dyn_cast<ActualParmVFGNode>(node))
1021 return ap->getParam();
1022 else if(const FormalParmVFGNode*fp = SVFUtil::dyn_cast<FormalParmVFGNode>(node))
1023 return fp->getParam();
1024 else if(const ActualRetVFGNode* ar = SVFUtil::dyn_cast<ActualRetVFGNode>(node))
1025 return ar->getRev();
1026 else if(const FormalRetVFGNode* fr = SVFUtil::dyn_cast<FormalRetVFGNode>(node))
1027 return fr->getRet();
1028 else if(const NullPtrVFGNode* nullVFG = SVFUtil::dyn_cast<NullPtrVFGNode>(node))
1029 return nullVFG->getSVFVar();
1030 else
1031 assert(false && "unexpected node kind!");
1032 return nullptr;
1033}
1034
1039{
1040 if(const FormalParmVFGNode* fp = SVFUtil::dyn_cast<FormalParmVFGNode>(node))
1041 {
1042 return fp->getFun();
1043 }
1044 else if(const InterPHIVFGNode* phi = SVFUtil::dyn_cast<InterPHIVFGNode>(node))
1045 {
1046 if(phi->isFormalParmPHI())
1047 return phi->getFun();
1048 }
1049 return nullptr;
1050}
1051
1052
1054{
1055 return getSVFStmt()->getValue();
1056}
1057
1059{
1060 return getRes();
1061}
1062
1064{
1065 return getRes();
1066}
1067
1069{
1070 return getRes();
1071}
1072
1074{
1075 return param;
1076}
1077
1081namespace SVF
1082{
1083template<>
1085{
1086
1088 DOTGraphTraits(bool isSimple = false) :
1089 DOTGraphTraits<SVFIR*>(isSimple)
1090 {
1091 }
1092
1094 static std::string getGraphName(VFG*)
1095 {
1096 return "VFG";
1097 }
1098
1099 std::string getNodeLabel(NodeType *node, VFG *graph)
1100 {
1101 if (isSimple())
1102 return getSimpleNodeLabel(node, graph);
1103 else
1104 return getCompleteNodeLabel(node, graph);
1105 }
1106
1108 static std::string getSimpleNodeLabel(NodeType *node, VFG*)
1109 {
1110 std::string str;
1111 std::stringstream rawstr(str);
1112 if(StmtVFGNode* stmtNode = SVFUtil::dyn_cast<StmtVFGNode>(node))
1113 {
1114 rawstr << stmtNode->toString();
1115 }
1116 else if(PHIVFGNode* tphi = SVFUtil::dyn_cast<PHIVFGNode>(node))
1117 {
1118 rawstr << tphi->toString();
1119 }
1120 else if(FormalParmVFGNode* fp = SVFUtil::dyn_cast<FormalParmVFGNode>(node))
1121 {
1122 rawstr << fp->toString();
1123 }
1124 else if(ActualParmVFGNode* ap = SVFUtil::dyn_cast<ActualParmVFGNode>(node))
1125 {
1126 rawstr << ap->toString();
1127 }
1128 else if (ActualRetVFGNode* ar = SVFUtil::dyn_cast<ActualRetVFGNode>(node))
1129 {
1130 rawstr << ar->toString();
1131 }
1132 else if (FormalRetVFGNode* fr = SVFUtil::dyn_cast<FormalRetVFGNode>(node))
1133 {
1134 rawstr << fr->toString();
1135 }
1136 else if(SVFUtil::isa<NullPtrVFGNode>(node))
1137 {
1138 rawstr << "NullPtr";
1139 }
1140 else if(BinaryOPVFGNode* bop = SVFUtil::dyn_cast<BinaryOPVFGNode>(node))
1141 {
1142 rawstr << bop->toString();
1143 }
1144 else if(UnaryOPVFGNode* uop = SVFUtil::dyn_cast<UnaryOPVFGNode>(node))
1145 {
1146 rawstr << uop->toString();
1147 }
1148 else if(CmpVFGNode* cmp = SVFUtil::dyn_cast<CmpVFGNode>(node))
1149 {
1150 rawstr << cmp->toString();;
1151 }
1152 else if (BranchVFGNode* branchNode = SVFUtil::dyn_cast<BranchVFGNode>(node))
1153 {
1154 rawstr << branchNode->toString();
1155 }
1156 else
1157 assert(false && "what else kinds of nodes do we have??");
1158
1159 return rawstr.str();
1160 }
1161
1163 static std::string getCompleteNodeLabel(NodeType *node, VFG*)
1164 {
1165
1166 std::string str;
1167 std::stringstream rawstr(str);
1168 if(StmtVFGNode* stmtNode = SVFUtil::dyn_cast<StmtVFGNode>(node))
1169 {
1170 rawstr << stmtNode->toString();
1171 }
1172 else if(BinaryOPVFGNode* bop = SVFUtil::dyn_cast<BinaryOPVFGNode>(node))
1173 {
1174 rawstr << bop->toString();
1175 }
1176 else if(UnaryOPVFGNode* uop = SVFUtil::dyn_cast<UnaryOPVFGNode>(node))
1177 {
1178 rawstr << uop->toString();
1179 }
1180 else if(CmpVFGNode* cmp = SVFUtil::dyn_cast<CmpVFGNode>(node))
1181 {
1182 rawstr << cmp->toString();
1183 }
1184 else if(PHIVFGNode* phi = SVFUtil::dyn_cast<PHIVFGNode>(node))
1185 {
1186 rawstr << phi->toString();
1187 }
1188 else if(FormalParmVFGNode* fp = SVFUtil::dyn_cast<FormalParmVFGNode>(node))
1189 {
1190 rawstr << fp->toString();
1191 }
1192 else if(ActualParmVFGNode* ap = SVFUtil::dyn_cast<ActualParmVFGNode>(node))
1193 {
1194 rawstr << ap->toString();
1195 }
1196 else if(NullPtrVFGNode* nptr = SVFUtil::dyn_cast<NullPtrVFGNode>(node))
1197 {
1198 rawstr << nptr->toString();
1199 }
1200 else if (ActualRetVFGNode* ar = SVFUtil::dyn_cast<ActualRetVFGNode>(node))
1201 {
1202 rawstr << ar->toString();
1203 }
1204 else if (FormalRetVFGNode* fr = SVFUtil::dyn_cast<FormalRetVFGNode>(node))
1205 {
1206 rawstr << fr->toString();
1207 }
1208 else if (MRSVFGNode* mr = SVFUtil::dyn_cast<MRSVFGNode>(node))
1209 {
1210 rawstr << mr->toString();
1211 }
1212 else if (BranchVFGNode* branchNode = SVFUtil::dyn_cast<BranchVFGNode>(node))
1213 {
1214 rawstr << branchNode->toString();
1215 }
1216 else
1217 assert(false && "what else kinds of nodes do we have??");
1218
1219 return rawstr.str();
1220 }
1221
1222 static std::string getNodeAttributes(NodeType *node, VFG*)
1223 {
1224 std::string str;
1225 std::stringstream rawstr(str);
1226
1227 if(StmtVFGNode* stmtNode = SVFUtil::dyn_cast<StmtVFGNode>(node))
1228 {
1229 const SVFStmt* edge = stmtNode->getSVFStmt();
1230 if (SVFUtil::isa<AddrStmt>(edge))
1231 {
1232 rawstr << "color=green";
1233 }
1234 else if (SVFUtil::isa<CopyStmt>(edge))
1235 {
1236 rawstr << "color=black";
1237 }
1238 else if (SVFUtil::isa<RetPE>(edge))
1239 {
1240 rawstr << "color=black,style=dotted";
1241 }
1242 else if (SVFUtil::isa<GepStmt>(edge))
1243 {
1244 rawstr << "color=purple";
1245 }
1246 else if (SVFUtil::isa<StoreStmt>(edge))
1247 {
1248 rawstr << "color=blue";
1249 }
1250 else if (SVFUtil::isa<LoadStmt>(edge))
1251 {
1252 rawstr << "color=red";
1253 }
1254 else
1255 {
1256 assert(0 && "No such kind edge!!");
1257 }
1258 rawstr << "";
1259 }
1260 else if (SVFUtil::isa<CmpVFGNode>(node))
1261 {
1262 rawstr << "color=grey";
1263 }
1264 else if (SVFUtil::isa<BinaryOPVFGNode>(node))
1265 {
1266 rawstr << "color=grey";
1267 }
1268 else if (SVFUtil::isa<UnaryOPVFGNode>(node))
1269 {
1270 rawstr << "color=grey";
1271 }
1272 else if(SVFUtil::isa<PHIVFGNode>(node))
1273 {
1274 rawstr << "color=black";
1275 }
1276 else if(SVFUtil::isa<NullPtrVFGNode>(node))
1277 {
1278 rawstr << "color=grey";
1279 }
1280 else if(SVFUtil::isa<FormalParmVFGNode>(node))
1281 {
1282 rawstr << "color=yellow,penwidth=2";
1283 }
1284 else if(SVFUtil::isa<ActualParmVFGNode>(node))
1285 {
1286 rawstr << "color=yellow,penwidth=2";
1287 }
1288 else if (SVFUtil::isa<ActualRetVFGNode>(node))
1289 {
1290 rawstr << "color=yellow,penwidth=2";
1291 }
1292 else if (SVFUtil::isa<FormalRetVFGNode>(node))
1293 {
1294 rawstr << "color=yellow,penwidth=2";
1295 }
1296 else if (SVFUtil::isa<MRSVFGNode>(node))
1297 {
1298 rawstr << "color=orange,penwidth=2";
1299 }
1300 else if (SVFUtil::isa<BranchVFGNode>(node))
1301 {
1302 rawstr << "color=gold,penwidth=2";
1303 }
1304 else
1305 assert(false && "no such kind of node!!");
1306
1307 rawstr << "";
1308
1309 return rawstr.str();
1310 }
1311
1312 template<class EdgeIter>
1313 static std::string getEdgeAttributes(NodeType*, EdgeIter EI, VFG*)
1314 {
1315 VFGEdge* edge = *(EI.getCurrent());
1316 assert(edge && "No edge found!!");
1317 if (SVFUtil::isa<DirectSVFGEdge>(edge))
1318 {
1319 if (SVFUtil::isa<CallDirSVFGEdge>(edge))
1320 return "style=solid,color=red";
1321 else if (SVFUtil::isa<RetDirSVFGEdge>(edge))
1322 return "style=solid,color=blue";
1323 else
1324 return "style=solid";
1325 }
1326 else if (SVFUtil::isa<IndirectSVFGEdge>(edge))
1327 {
1328 if (SVFUtil::isa<CallIndSVFGEdge>(edge))
1329 return "style=dashed,color=red";
1330 else if (SVFUtil::isa<RetIndSVFGEdge>(edge))
1331 return "style=dashed,color=blue";
1332 else
1333 return "style=dashed";
1334 }
1335 else
1336 {
1337 assert(false && "what else edge we have?");
1338 }
1339 return "";
1340 }
1341
1342 template<class EdgeIter>
1344 {
1345 VFGEdge* edge = *(EI.getCurrent());
1346 assert(edge && "No edge found!!");
1347
1348 std::string str;
1349 std::stringstream rawstr(str);
1350 if (CallDirSVFGEdge* dirCall = SVFUtil::dyn_cast<CallDirSVFGEdge>(edge))
1351 rawstr << dirCall->getCallSiteId();
1352 else if (RetDirSVFGEdge* dirRet = SVFUtil::dyn_cast<RetDirSVFGEdge>(edge))
1353 rawstr << dirRet->getCallSiteId();
1354
1355 return rawstr.str();
1356 }
1357};
1358} // End namespace llvm
#define DBOUT(TYPE, X)
LLVM debug macros, define type of your DBUG model of each pass.
Definition SVFType.h:593
#define DGENERAL
Definition SVFType.h:599
copy
Definition cJSON.cpp:414
cJSON * n
Definition cJSON.cpp:2558
const std::string toString() const override
Definition VFG.cpp:272
const ValVar * getParam() const
Return parameter.
Definition VFGNode.h:989
const NodeBS getDefSVFVars() const override
Return the left hand side SVF Vars.
Definition VFG.cpp:265
const CallICFGNode * getCallSite() const
Return callsite.
Definition VFGNode.h:983
const CallICFGNode * getCallSite() const
Return callsite.
Definition VFGNode.h:1111
const std::string toString() const override
Definition VFG.cpp:306
const NodeBS getDefSVFVars() const override
Return the left hand side SVF Vars.
Definition VFG.cpp:299
const ValVar * getRev() const
Receive parameter at callsite.
Definition VFGNode.h:1121
const NodeBS getDefSVFVars() const override
Return the left hand side SVF Vars.
Definition VFG.cpp:239
const std::string toString() const override
Definition VFG.cpp:246
const std::string toString() const override
Definition VFG.cpp:256
const ValVar * param
Definition VFGNode.h:930
const SVFVar * getValue() const override
Return the corresponding LLVM value, if possible, nullptr otherwise.
Definition VFG.cpp:1073
const NodeBS getDefSVFVars() const override
Return the left hand side SVF Vars.
Definition VFG.cpp:131
const ValVar * getRes() const
Definition VFGNode.h:509
const SVFVar * getValue() const override
Return the corresponding LLVM value, if possible, nullptr otherwise.
Definition VFG.cpp:1063
const std::string toString() const override
Definition VFG.cpp:138
const ValVar * res
Definition VFGNode.h:467
OPVers::const_iterator opVerBegin() const
Definition VFGNode.h:517
OPVers::const_iterator opVerEnd() const
Definition VFGNode.h:521
virtual const std::string toString() const override
virtual const std::string toString() const override
Definition VFG.cpp:178
const NodeBS getDefSVFVars() const override
Return the left hand side SVF Vars.
Definition VFG.cpp:173
const BranchStmt * brstmt
Definition VFGNode.h:620
CallSiteID getCallSiteId() const
Return callsite ID.
Definition VFGEdge.h:223
virtual const std::string toString() const
Definition VFG.cpp:387
const RetICFGNode * getRetICFGNode() const
Return callsite.
Definition ICFGNode.h:439
const std::string getSourceLoc() const override
Definition ICFGNode.h:570
OPVers::const_iterator opVerBegin() const
Definition VFGNode.h:440
const ValVar * res
Definition VFGNode.h:390
const std::string toString() const override
Definition VFG.cpp:117
const ValVar * getRes() const
Definition VFGNode.h:432
const NodeBS getDefSVFVars() const override
Return the left hand side SVF Vars.
Definition VFG.cpp:110
OPVers::const_iterator opVerEnd() const
Definition VFGNode.h:444
const SVFVar * getValue() const override
Return the corresponding LLVM value, if possible, nullptr otherwise.
Definition VFG.cpp:1058
const NodeBS getDefSVFVars() const override
Return the left hand side SVF Vars.
Definition VFG.cpp:94
const std::string toString() const override
Definition VFG.cpp:101
virtual const std::string toString() const
Definition VFG.cpp:371
const ValVar * getParam() const
Return parameter.
Definition VFGNode.h:1041
const FunObjVar * getFun() const override
Return function.
Definition VFGNode.h:1047
const NodeBS getDefSVFVars() const override
Return the left hand side SVF Vars.
Definition VFG.cpp:282
const std::string toString() const override
Definition VFG.cpp:289
FormalRetVFGNode()
place holder
const FunObjVar * getFun() const override
Function.
Definition VFGNode.h:1177
const ValVar * getRet() const
Return value at callee.
Definition VFGNode.h:1172
const NodeBS getDefSVFVars() const override
Return the left hand side SVF Vars.
Definition VFG.cpp:317
const std::string toString() const override
Definition VFG.cpp:324
NodeID getDstID() const
NodeID getSrcID() const
get methods of the components
iterator begin()
Iterators.
bool hasIncomingEdge() const
Has incoming/outgoing edge set.
bool hasOutgoingEdge() const
const GEdgeSetTy & getOutEdges() const
const NodeBS getDefSVFVars() const override
Return the left hand side SVF Vars.
Definition VFG.cpp:187
const std::string toString() const override
Definition VFG.cpp:194
static void WriteGraphToFile(SVF::OutStream &O, const std::string &GraphName, const GraphType &GT, bool simple=false)
virtual const FunObjVar * getFun() const
Return the function of this ICFGNode.
Definition ICFGNode.h:74
NodeID getNullPtr() const
Definition IRGraph.h:259
NodeID getVarargNode(const FunObjVar *func) const
getVarargNode - Return the unique node representing the variadic argument of a variadic function.
Definition IRGraph.cpp:67
bool isFormalParmPHI() const
Definition VFGNode.h:1236
const std::string toString() const override
Definition VFG.cpp:335
virtual const std::string toString() const
Definition VFG.cpp:379
const std::string toString() const override
Definition VFG.cpp:225
const std::string toString() const override
Definition VFG.cpp:63
const NodeBS getDefSVFVars() const override
Return the left hand side SVF Vars.
Definition VFG.cpp:56
const SVFVar * getSVFVar() const
Return corresponding SVFVar.
Definition VFGNode.h:1310
const SVFVar * node
Definition VFGNode.h:1297
const std::string toString() const override
Definition VFG.cpp:353
const NodeBS getDefSVFVars() const override
Return the left hand side SVF Vars.
Definition VFG.cpp:346
static const Option< bool > EnableThreadCallGraph
Definition Options.h:129
OPVers::const_iterator opVerBegin() const
Definition VFGNode.h:773
PHIVFGNode(NodeID id, const ValVar *r, VFGNodeK k=TPhi)
Constructor.
Definition VFG.cpp:412
const NodeBS getDefSVFVars() const override
Return the left hand side SVF Vars.
Definition VFG.cpp:203
const std::string toString() const override
Definition VFG.cpp:210
const ValVar * res
Definition VFGNode.h:740
OPVers::const_iterator opVerEnd() const
Definition VFGNode.h:777
const ValVar * getRes() const
Definition VFGNode.h:765
const SVFVar * getValue() const override
Return the corresponding LLVM value, if possible, nullptr otherwise.
Definition VFG.cpp:1068
Set< const FunObjVar * > FunctionSet
CallEdgeMap & getIndCallMap()
Get callees from an indirect callsite.
virtual const std::string toString() const
Definition VFG.cpp:396
CallSiteID getCallSiteId() const
Return callsite ID.
Definition VFGEdge.h:266
const ValVar * getLHSVar() const
CSToArgsListMap & getCallSiteArgsMap()
Get callsite argument list.
Definition SVFIR.h:388
bool funHasRet(const FunObjVar *func) const
Definition SVFIR.h:427
bool hasFunArgsList(const FunObjVar *func) const
Function has arguments list.
Definition SVFIR.h:366
const ValVar * getCallSiteRet(const RetICFGNode *cs) const
Get callsite return.
Definition SVFIR.h:405
const ValVarList & getFunArgsList(const FunObjVar *func) const
Get function arguments list.
Definition SVFIR.h:376
std::vector< const ValVar * > ValVarList
Definition SVFIR.h:58
CSToRetMap & getCallSiteRets()
Get callsite return.
Definition SVFIR.h:400
FunToRetMap & getFunRets()
Get function return list.
Definition SVFIR.h:416
bool hasCallSiteArgsMap(const CallICFGNode *cs) const
Callsite has argument list.
Definition SVFIR.h:383
bool callsiteHasRet(const RetICFGNode *cs) const
Definition SVFIR.h:411
const ValVar * getFunRet(const FunObjVar *func) const
Get function return list.
Definition SVFIR.h:421
static SVFIR * getPAG(bool buildFromFile=false)
Singleton design here to make sure we only have one instance during any analysis.
Definition SVFIR.h:118
const ValVarList & getCallSiteArgsList(const CallICFGNode *cs) const
Get callsite argument list.
Definition SVFIR.h:393
const ValVar * getValVar(NodeID id) const
Definition SVFIR.h:137
CallPE * getCallPEForFormalParm(const SVFVar *param) const
Get the CallPE for a formal parameter (phi-like, nullptr if not found)
Definition SVFIR.h:359
FunToArgsListMap & getFunArgsMap()
Get function arguments list.
Definition SVFIR.h:371
const SVFVar * getValue() const
GenericNode< SVFVar, SVFStmt >::GEdgeSetTy SVFStmtSetTy
virtual const std::string toString() const
NodeID getId() const
Get ID.
Definition SVFValue.h:163
virtual const std::string & getName() const
Definition SVFValue.h:189
const std::string valueOnlyToString() const
Definition LLVMUtil.cpp:739
virtual bool isConstDataOrAggDataButNotNullPtr() const
Check if this variable represents constant data/metadata but not null pointer.
void set(unsigned Idx)
const SVFVar * getValue() const override
Return the corresponding LLVM value, if possible, nullptr otherwise.
Definition VFG.cpp:1053
const SVFStmt * getSVFStmt() const
Definition VFGNode.h:147
const std::string toString() const override
Definition VFG.cpp:47
NodeID getDstNodeID() const
Definition VFGNode.h:157
const NodeBS getDefSVFVars() const override
Return the left hand side SVF Vars.
Definition VFG.cpp:72
const std::string toString() const override
Definition VFG.cpp:85
const NodeBS getDefSVFVars() const override
Return the left hand side SVF Vars.
Definition VFG.cpp:152
const ValVar * getRes() const
Definition VFGNode.h:583
OPVers::const_iterator opVerBegin() const
Definition VFGNode.h:596
const ValVar * res
Definition VFGNode.h:541
virtual const std::string toString() const override
Definition VFG.cpp:159
OPVers::const_iterator opVerEnd() const
Definition VFGNode.h:600
@ IntraDirectVF
Definition VFGEdge.h:53
static GEdgeFlag makeEdgeFlagWithInvokeID(GEdgeKind k, CallSiteID cs)
Compute the unique edgeFlag value from edge kind and CallSiteID.
Definition VFGEdge.h:120
virtual const std::string toString() const
Definition VFG.cpp:363
virtual const std::string toString() const
Definition VFG.cpp:39
Definition VFG.h:51
FormalRetVFGNode * getFormalRetVFGNode(const SVFVar *fret) const
Definition VFG.h:315
VFGEdge::VFGEdgeSetTy VFGEdgeSetTy
Definition VFG.h:77
void updateCallGraph(PointerAnalysis *pta)
Update VFG based on pointer analysis results.
Definition VFG.cpp:928
NodeID getDef(const ValVar *valVar) const
Definition VFG.h:482
VFGEdge * addInterEdgeFromAPToFP(ActualParmVFGNode *src, FormalParmVFGNode *dst, CallSiteID csId)
Add inter VF edge from actual to formal parameters.
Definition VFG.h:424
void addStoreVFGNode(const StoreStmt *store)
Definition VFG.h:583
VFGEdge * addInterEdgeFromFRToAR(FormalRetVFGNode *src, ActualRetVFGNode *dst, CallSiteID csId)
Add inter VF edge from callee return to callsite receive parameter.
Definition VFG.h:429
void addBranchVFGNode(const BranchStmt *edge)
Add a BranchVFGNode.
Definition VFG.h:690
ActualParmVFGNode * getActualParmVFGNode(const SVFVar *aparm, const CallICFGNode *cs) const
Definition VFG.h:297
const SVFVar * getLHSTopLevPtr(const VFGNode *node) const
Definition VFG.cpp:1001
VFGNodeIDToNodeMapTy::iterator iterator
Definition VFG.h:80
SVFIR * pag
Definition VFG.h:104
VFGEdge * addRetEdge(NodeID srcId, NodeID dstId, CallSiteID csId)
Definition VFG.cpp:686
virtual void connectAParamAndFParam(const ValVar *csArg, const ValVar *funArg, const CallICFGNode *cbn, CallSiteID csId, VFGEdgeSetTy &edges)
Connect VFG nodes between caller and callee for indirect call site.
Definition VFG.h:448
void addVFGNodes()
Create VFG nodes.
Definition VFG.cpp:447
void addLoadVFGNode(const LoadStmt *load)
Add a Load VFG node.
Definition VFG.h:575
CallSiteID getCallSiteID(const CallICFGNode *cs, const FunObjVar *func) const
Get callsite given a callsiteID.
Definition VFG.h:178
VFGK kind
Definition VFG.h:105
VFGEdge * addIntraDirectVFEdge(NodeID srcId, NodeID dstId)
Definition VFG.cpp:640
void checkIntraEdgeParents(const VFGNode *srcNode, const VFGNode *dstNode)
sanitize Intra edges, verify that both nodes belong to the same function.
Definition VFG.h:413
void addCopyVFGNode(const CopyStmt *copy)
Add a Copy VFG node.
Definition VFG.h:561
void addGepVFGNode(const GepStmt *gep)
Add a Gep VFG node.
Definition VFG.h:568
bool isPhiCopyEdge(const SVFStmt *copy) const
Definition VFG.h:520
bool hasDef(const ValVar *valVar) const
Definition VFG.h:488
void addFormalParmVFGNode(const ValVar *fparm, const FunObjVar *fun, const CallPE *callPE)
Add a formal parameter VFG node.
Definition VFG.h:600
virtual void connectFRetAndARet(const ValVar *funReturn, const ValVar *csReturn, CallSiteID csId, VFGEdgeSetTy &edges)
Connect formal-ret and actual ret.
Definition VFG.h:457
void addUnaryOPVFGNode(const UnaryOPStmt *edge)
Add a UnaryOperator VFG node.
Definition VFG.h:681
void addCmpVFGNode(const CmpStmt *edge)
Add a Compare VFG node.
Definition VFG.h:653
FormalParmVFGNode * getFormalParmVFGNode(const SVFVar *fparm) const
Definition VFG.h:309
bool addVFGEdge(VFGEdge *edge)
Add VFG edge.
Definition VFG.h:401
VFGNode * getVFGNode(NodeID id) const
Get a VFG node.
Definition VFG.h:145
void addActualParmVFGNode(const ValVar *aparm, const CallICFGNode *cs)
Definition VFG.h:592
const FunObjVar * isFunEntryVFGNode(const VFGNode *node) const
Whether a node is function entry VFGNode.
Definition VFG.cpp:1038
VFG(CallGraph *callgraph, VFGK k=FULLSVFG)
Constructor.
Definition VFG.cpp:425
VFGEdge * addCallEdge(NodeID srcId, NodeID dstId, CallSiteID csId)
Definition VFG.cpp:666
void addNullPtrVFGNode(const ValVar *svfVar)
Definition VFG.h:547
virtual SVFStmt::SVFStmtSetTy & getSVFStmtSet(SVFStmt::PEDGEK kind)
Get SVFStmt set.
Definition VFG.h:498
void addFormalRetVFGNode(const ValVar *uniqueFunRet, const FunObjVar *fun, RetPESet &retPEs)
Definition VFG.h:612
FormalRetVFGNode::RetPESet RetPESet
Definition VFG.h:76
VFGK
VFG kind.
Definition VFG.h:56
VFGEdge * hasIntraVFGEdge(VFGNode *src, VFGNode *dst, VFGEdge::VFGEdgeK kind)
Whether we has a SVFG edge.
Definition VFG.cpp:852
void addBinaryOPVFGNode(const BinaryOPStmt *edge)
Add a BinaryOperator VFG node.
Definition VFG.h:667
void addAddrVFGNode(const AddrStmt *addr)
Add an Address VFG node.
Definition VFG.h:554
void addActualRetVFGNode(const ValVar *ret, const CallICFGNode *cs)
Add a callsite Receive VFG node.
Definition VFG.h:631
VFGEdge * hasInterVFGEdge(VFGNode *src, VFGNode *dst, VFGEdge::VFGEdgeK kind, CallSiteID csId)
Definition VFG.cpp:887
virtual bool isInterestedSVFVar(const SVFVar *node) const
Definition VFG.h:506
void connectDirectVFGEdges()
Create edges between VFG nodes within a function.
Definition VFG.cpp:707
VFGEdge * getIntraVFGEdge(const VFGNode *src, const VFGNode *dst, VFGEdge::VFGEdgeK kind)
Get a SVFG edge according to src and dst.
Definition VFG.cpp:905
ActualRetVFGNode * getActualRetVFGNode(const SVFVar *aret) const
Definition VFG.h:303
void view()
Dump graph into dot file.
Definition VFG.cpp:922
VFGEdge * hasThreadVFGEdge(VFGNode *src, VFGNode *dst, VFGEdge::VFGEdgeK kind)
Definition VFG.cpp:870
void dump(const std::string &file, bool simple=false)
Dump graph into dot file.
Definition VFG.cpp:914
bool hasBlackHoleConstObjAddrAsDef(const ValVar *valVar) const
Whether a SVFVar has a blackhole or const object as its definition.
Definition VFG.h:327
virtual void connectCallerAndCallee(const CallICFGNode *cs, const FunObjVar *callee, VFGEdgeSetTy &edges)
Connect VFG nodes between caller and callee for indirect call site.
Definition VFG.cpp:950
void destroy()
Clean up memory.
Definition VFG.cpp:438
void addIntraPHIVFGNode(const MultiOpndStmt *edge)
Add an llvm PHI VFG node.
Definition VFG.h:639
virtual const std::string toString() const
Get string representation.
std::string pasMsg(const std::string &msg)
Print each pass/phase message by converting a string into blue string output.
Definition SVFUtil.cpp:101
bool matchArgs(const CallICFGNode *cs, const FunObjVar *callee)
Definition SVFUtil.cpp:308
std::ostream & outs()
Overwrite llvm::outs()
Definition SVFUtil.h:52
for isBitcode
Definition BasicTypes.h:70
unsigned CallSiteID
Definition GeneralType.h:58
u32_t NodeID
Definition GeneralType.h:56
void ViewGraph(const GraphType &G, const std::string &name, bool ShortNames=false, GraphProgram::Name Program=GraphProgram::DOT)
llvm::IRBuilder IRBuilder
Definition BasicTypes.h:76
SparseBitVector NodeBS
Definition GeneralType.h:62
unsigned u32_t
Definition GeneralType.h:47
static std::string getCompleteNodeLabel(NodeType *node, VFG *)
Return label of a VFG node with MemSSA information.
Definition VFG.cpp:1163
static std::string getNodeAttributes(NodeType *node, VFG *)
Definition VFG.cpp:1222
static std::string getEdgeSourceLabel(NodeType *, EdgeIter EI)
Definition VFG.cpp:1343
DOTGraphTraits(bool isSimple=false)
Definition VFG.cpp:1088
static std::string getEdgeAttributes(NodeType *, EdgeIter EI, VFG *)
Definition VFG.cpp:1313
std::string getNodeLabel(NodeType *node, VFG *graph)
Definition VFG.cpp:1099
static std::string getSimpleNodeLabel(NodeType *node, VFG *)
Return label of a VFG node without MemSSA information.
Definition VFG.cpp:1108
static std::string getGraphName(VFG *)
Return name of the graph.
Definition VFG.cpp:1094