Static Value-Flow Analysis
Loading...
Searching...
No Matches
SVFStat.cpp
Go to the documentation of this file.
1//===- SVFStat.cpp -- Base class for statistics---------------------------------//
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 * SVFStat.cpp
25 *
26 * Created on: Sep 1, 2022
27 * Author: Xiao Cheng
28 */
29
30#include <chrono>
31#include <iomanip>
32
33#include "SVFIR/SVFIR.h"
34#include "Util/Options.h"
35#include "Util/SVFStat.h"
36#include "Graphs/CallGraph.h"
37
38using namespace SVF;
39using namespace std;
40
45
46SVFStat::SVFStat() : startTime(0), endTime(0)
47{
49 && "PTAStat: unknown clock type!");
50}
51
53{
54 if (Options::MarkedClocksOnly() && !mark) return 0.0;
55
57 {
58 return std::chrono::duration<double, std::milli>(
59 std::chrono::steady_clock::now().time_since_epoch()
60 ).count();
61 }
63 {
64 return CLOCK_IN_MS();
65 }
66
67 assert(false && "PTAStat::getClk: unknown clock type");
68 abort();
69}
70
72{
73
74 std::string moduleName(SVFIR::getPAG()->getModuleIdentifier());
75 std::vector<std::string> names = SVFUtil::split(moduleName,'/');
76 if (names.size() > 1)
77 {
78 moduleName = names[names.size() - 1];
79 }
80
81 SVFUtil::outs() << "\n*********" << statname << "***************\n";
82 SVFUtil::outs() << "################ (program : " << moduleName << ")###############\n";
83 SVFUtil::outs().flags(std::ios::left);
84 unsigned field_width = 20;
85
86 for(NUMStatMap::iterator it = generalNumMap.begin(), eit = generalNumMap.end(); it!=eit; ++it)
87 {
88 // format out put with width 20 space
89 std::cout << std::setw(field_width) << it->first << it->second << "\n";
90 }
91
92 if(!timeStatMap.empty())
93 SVFUtil::outs() << "----------------Time and memory stats--------------------\n";
94 for(TIMEStatMap::iterator it = timeStatMap.begin(), eit = timeStatMap.end(); it!=eit; ++it)
95 {
96 // format out put with width 20 space
97 SVFUtil::outs() << std::setw(field_width) << it->first << it->second << "\n";
98 }
99
100 if(!PTNumStatMap.empty())
101 SVFUtil::outs() << "----------------Numbers stats----------------------------\n";
102 for(NUMStatMap::iterator it = PTNumStatMap.begin(), eit = PTNumStatMap.end(); it!=eit; ++it)
103 {
104 // format out put with width 20 space
105 SVFUtil::outs() << std::setw(field_width) << it->first << it->second << "\n";
106 }
107 SVFUtil::outs() << "#######################################################" << std::endl;
108 SVFUtil::outs().flush();
109 generalNumMap.clear();
110 PTNumStatMap.clear();
111 timeStatMap.clear();
112}
113
115{
116
118 if(printGeneralStats == false)
119 return;
120
121 SVFIR* pag = SVFIR::getPAG();
123 u32_t numOfGlobal = 0;
124 u32_t numOfStack = 0;
125 u32_t numOfHeap = 0;
130 u32_t numOfScalar = 0;
132 u32_t fiObjNumber = 0;
133 u32_t fsObjNumber = 0;
135 for(SVFIR::iterator it = pag->begin(), eit = pag->end(); it!=eit; ++it)
136 {
137 PAGNode* node = it->second;
138 if(ObjVar* obj = SVFUtil::dyn_cast<ObjVar>(node))
139 {
140 const BaseObjVar* mem = pag->getBaseObject(obj->getId());
141 if (memObjSet.insert(mem->getId()).second == false)
142 continue;
143 if(mem->isBlackHoleObj())
144 continue;
145 if(mem->isFunction())
147 if(mem->isGlobalObj())
148 numOfGlobal++;
149 if (pag->getBaseObject(obj->getId()) &&
150 SVFUtil::isa<StackObjVar>(
151 pag->getBaseObject(obj->getId())))
152 numOfStack++;
153 if (pag->getBaseObject(obj->getId()) &&
154 SVFUtil::isa<HeapObjVar, DummyObjVar>(
155 pag->getBaseObject(obj->getId())))
156 {
157 numOfHeap++;
158 }
159 if(mem->isVarArray())
161 if(mem->isVarStruct())
163 if(mem->isConstantArray())
165 if(mem->isConstantStruct())
167 if(mem->getType()->isPointerTy() == false)
168 numOfScalar++;
169 if(mem->isConstDataOrConstGlobal())
171
172 if (mem->isFieldInsensitive())
173 fiObjNumber++;
174 else
175 fsObjNumber++;
176 }
177 }
178
179
180
181 generalNumMap["TotalPointers"] = pag->getValueNodeNum();
182 generalNumMap["TotalObjects"] = pag->getObjectNodeNum();
183 generalNumMap["TotalFieldObjects"] = pag->getFieldObjNodeNum();
184 generalNumMap["MaxStructSize"] = pag->getMaxStructSize();
185 generalNumMap["TotalSVFStmts"] = pag->getSVFStmtNum();
186 generalNumMap["TotalPTASVFStmts"] = pag->getPTAPAGEdgeNum();
187 generalNumMap["FIObjNum"] = fiObjNumber;
188 generalNumMap["FSObjNum"] = fsObjNumber;
189
190 generalNumMap["AddrsNum"] = pag->getSVFStmtSet(SVFStmt::Addr).size();
191 generalNumMap["LoadsNum"] = pag->getSVFStmtSet(SVFStmt::Load).size();
192 generalNumMap["StoresNum"] = pag->getSVFStmtSet(SVFStmt::Store).size();
193 generalNumMap["CopysNum"] = pag->getSVFStmtSet(SVFStmt::Copy).size();
194 generalNumMap["GepsNum"] = pag->getSVFStmtSet(SVFStmt::Gep).size();
195 generalNumMap["CallsNum"] = pag->getSVFStmtSet(SVFStmt::Call).size();
196 generalNumMap["ReturnsNum"] = pag->getSVFStmtSet(SVFStmt::Ret).size();
197
198 generalNumMap["FunctionObjs"] = numOfFunction;
199 generalNumMap["GlobalObjs"] = numOfGlobal;
200 generalNumMap["HeapObjs"] = numOfHeap;
201 generalNumMap["StackObjs"] = numOfStack;
202
203 generalNumMap["VarStructObj"] = numOfHasVarStruct;
204 generalNumMap["VarArrayObj"] = numOfHasVarArray;
205 generalNumMap["ConstStructObj"] = numOfHasConstStruct;
206 generalNumMap["ConstArrayObj"] = numOfHasConstArray;
207 generalNumMap["NonPtrObj"] = numOfScalar;
208 generalNumMap["ConstantObj"] = numOfConstant;
209
210 generalNumMap["IndCallSites"] = pag->getIndirectCallsites().size();
211 generalNumMap["TotalCallSite"] = pag->getCallSiteSet().size();
212
216
217 // REFACTOR-TODO bitcastInstStat();
218 branchStat();
219
220 printStat("General Stats");
221
222 printGeneralStats = false;
223}
224
225
227{
231 for (const auto& item: *svfirCallGraph)
232 {
233 const FunObjVar* func = item.second->getFunction();
234 for (FunObjVar::const_bb_iterator bbIt = func->begin(), bbEit = func->end();
235 bbIt != bbEit; ++bbIt)
236 {
237 const SVFBasicBlock* bb = bbIt->second;
239 if (numOfSucc == 2)
241 else if (numOfSucc > 2)
243 }
244 }
245
246 generalNumMap["BBWith2Succ"] = numOfBB_2Succ;
247 generalNumMap["BBWith3Succ"] = numOfBB_3Succ;
248}
249
250/* REFACTOR-TODO
251void PTAStat::bitcastInstStat()
252{
253 SVFModule* module = pta->getModule();
254 u32_t numberOfBitCast = 0;
255 for (SVFModule::llvm_const_iterator funIter = module->llvmFunBegin(), funEiter = module->llvmFunEnd();
256 funIter != funEiter; ++funIter)
257 {
258 const Function* func = *funIter;
259 for (Function::const_iterator bbIt = func->begin(), bbEit = func->end();
260 bbIt != bbEit; ++bbIt)
261 {
262 const BasicBlock& bb = *bbIt;
263 for (BasicBlock::const_iterator instIt = bb.begin(), instEit = bb.end();
264 instIt != instEit; ++instIt)
265 {
266 const Instruction& inst = *instIt;
267 if (const BitCastInst* bitcast = SVFUtil::dyn_cast<BitCastInst>(&inst))
268 {
269 if (SVFUtil::isa<PointerType>(bitcast->getSrcTy()))
270 numberOfBitCast++;
271 }
272 }
273 }
274 }
275
276 generalNumMap["BitCastNumber"] = numberOfBitCast;
277}
278*/
#define CLOCK_IN_MS()
Definition SVFType.h:605
cJSON * item
Definition cJSON.h:222
bool isFunction() const
object attributes methods
bool isConstDataOrConstGlobal() const
bool isGlobalObj() const
bool isConstantStruct() const
bool isVarStruct() const
NodeID getId() const
Get the memory object id.
bool isBlackHoleObj() const
Whether it is a black hole object.
bool isVarArray() const
bool isFieldInsensitive() const
Return true if its field limit is 0.
const SVFType * getType() const
Get obj type.
bool isConstantArray() const
BasicBlockGraph::IDToNodeMapTy::const_iterator const_bb_iterator
iterator begin()
Iterators.
IDToNodeMapTy::iterator iterator
Node Iterators.
u32_t getMaxStructSize() const
Definition IRGraph.h:203
u32_t getObjectNodeNum()
Definition IRGraph.cpp:360
u32_t getSVFStmtNum() const
Definition IRGraph.h:333
u32_t getPTAPAGEdgeNum() const
Definition IRGraph.h:337
u32_t getValueNodeNum()
Definition IRGraph.cpp:347
static const Option< bool > MarkedClocksOnly
Definition Options.h:27
static const OptionMap< SVFStat::ClockType > ClockType
Definition Options.h:20
u32_t getNumSuccessors() const
const CallSiteSet & getCallSiteSet() const
Get all callsites.
Definition SVFIR.h:352
SVFStmt::SVFStmtSetTy & getSVFStmtSet(SVFStmt::PEDGEK kind)
Get/set methods to get SVFStmts based on their kinds and ICFGNodes.
Definition SVFIR.h:299
u32_t getFieldObjNodeNum() const
Definition SVFIR.h:442
const BaseObjVar * getBaseObject(NodeID id) const
Definition SVFIR.h:499
const CallGraph * getCallGraph()
Get CG.
Definition SVFIR.h:249
const CallSiteToFunPtrMap & getIndirectCallsites() const
Add/get indirect callsites.
Definition SVFIR.h:454
static SVFIR * getPAG(bool buildFromFile=false)
Singleton design here to make sure we only have one instance during any analysis.
Definition SVFIR.h:121
NUMStatMap generalNumMap
Definition SVFStat.h:79
NUMStatMap PTNumStatMap
Definition SVFStat.h:80
virtual void printStat(std::string str="")
Definition SVFStat.cpp:71
void branchStat()
Definition SVFStat.cpp:226
static bool printGeneralStats
SVF's general statistics are only printed once even if you run multiple anayses.
Definition SVFStat.h:77
std::string moduleName
Definition SVFStat.h:102
TIMEStatMap timeStatMap
Definition SVFStat.h:81
virtual void performStat()=0
Definition SVFStat.cpp:114
static double timeOfBuildingLLVMModule
Definition SVFStat.h:96
static double getClk(bool mark=false)
Definition SVFStat.cpp:52
static double timeOfBuildingSymbolTable
Definition SVFStat.h:97
static double timeOfBuildingSVFIR
Definition SVFStat.h:98
bool isPointerTy() const
Definition SVFType.h:292
std::ostream & outs()
Overwrite llvm::outs()
Definition SVFUtil.h:58
std::vector< std::string > split(const std::string &s, char separator)
Split into two substrings around the first occurrence of a separator string.
Definition SVFUtil.h:204
for isBitcode
Definition BasicTypes.h:70
llvm::IRBuilder IRBuilder
Definition BasicTypes.h:76
unsigned u32_t
Definition GeneralType.h:67