38using namespace SVFUtil;
77 for (
const ICFGNode* icfgNode : bb->getICFGNodeList())
107 if (visited.find(
cgnode) == visited.end())
117 if (visited.find(
cgnode) == visited.end())
123 while (!worklist.
empty())
130 if (visited.find(
srcNode) == visited.end())
178 while (!worklist.empty())
180 const ICFGNode *I = worklist.back();
203 worklist.push_back(
outEdge->getDstNode());
223 worklist.push_back(*
it);
225 while (!worklist.empty())
227 const ICFGNode *I = worklist.back();
249 worklist.push_back(
inEdge->getSrcNode());
262 for (FunSet::const_iterator
it = entryFuncSet.begin(),
eit = entryFuncSet.end();
it !=
eit; ++
it)
283 for (PTACallGraphEdge::CallInstSet::const_iterator
cit =
cgEdge->directCallsBegin(),
ecit =
cgEdge->directCallsEnd();
287 outs() <<
"\nCollecting CxtLocks: handling direct call:" << **
cit <<
"\t" <<
cgEdge->getSrcNode()->getFunction()->getName()
288 <<
"-->" <<
cgEdge->getDstNode()->getFunction()->getName() <<
"\n");
291 for (PTACallGraphEdge::CallInstSet::const_iterator
ind =
cgEdge->indirectCallsBegin(),
eind =
cgEdge->indirectCallsEnd();
295 outs() <<
"\nCollecting CxtLocks: handling indirect call:" << **
ind <<
"\t"
296 <<
cgEdge->getSrcNode()->getFunction()->getName() <<
"-->" <<
cgEdge->getDstNode()->getFunction()->getName()
324 DBOUT(
DMTA,
outs() <<
"LockAnalysis Process CallRet old clp --";
clp.dump());
334 for (FunSet::const_iterator
it = entryFuncSet.begin(),
eit = entryFuncSet.end();
it !=
eit; ++
it)
397 outs() <<
"\nlock sets size = " <<
lockset.size() <<
"\n";
410 const CallICFGNode* call = SVFUtil::dyn_cast<CallICFGNode>(
cts.getStmt());
411 if(
getTCG()->hasThreadForkEdge(call))
413 for (ThreadCallGraph::ForkEdgeSet::const_iterator
cgIt =
getTCG()->getForkEdgeBegin(call),
432 const CallICFGNode* call = SVFUtil::dyn_cast<CallICFGNode>(
cts.getStmt());
433 if (
getTCG()->hasCallGraphEdge(call))
435 for (PTACallGraph::CallGraphEdgeSet::const_iterator
cgIt =
getTCG()->getCallEdgeBegin(call),
ecgIt =
getTCG()->getCallEdgeEnd(call);
462 if (SVFUtil::isa<ThreadForkEdge, ThreadJoinEdge>(
edge))
464 for (PTACallGraphEdge::CallInstSet::const_iterator
cit = (
edge)->directCallsBegin(),
ecit = (
edge)->directCallsEnd();
cit !=
ecit;
481 for (PTACallGraphEdge::CallInstSet::const_iterator
cit = (
edge)->indirectCallsBegin(),
ecit = (
edge)->indirectCallsEnd();
550 if (cxt.back() == csId)
#define DBOUT(TYPE, X)
LLVM debug macros, define type of your DBUG model of each pass.
bool push(const Data &data)
const GEdgeSetTy & getOutEdges() const
const GEdgeSetTy & getInEdges() const
GEdgeSetTy::const_iterator const_iterator
virtual const SVFFunction * getFun() const
Return the function of this ICFGNode.
void analyzeLockSpanCxtStmt()
Set< CxtLock > CxtLockSet
bool removeCxtStmtToSpan(CxtStmt &cts, const CxtLock &cl)
Add context-sensitive statement.
CxtStmtWorkList cxtStmtList
context-sensitive statement worklist
bool isProtectedByCommonCILock(const ICFGNode *i1, const ICFGNode *i2)
bool isInSameCSSpan(const ICFGNode *i1, const ICFGNode *i2) const
bool isProtectedByCommonLock(const ICFGNode *i1, const ICFGNode *i2)
bool isInSameSpan(const ICFGNode *I1, const ICFGNode *I2)
void buildCandidateFuncSetforLock()
void markCxtStmtFlag(const CxtStmt &tgr, const CxtStmt &src)
Mark thread flags for cxtStmt.
bool hasCxtLockfromCxtStmt(const CxtStmt &cts) const
bool isExtCall(const ICFGNode *inst)
Whether it is calling an external function.
Set< CxtStmt > CxtStmtSet
bool alias(const CxtLockSet &lockset1, const CxtLockSet &lockset2)
Return true if two locksets has at least one alias lock.
CxtStmt popFromCTSWorkList()
FunSet lockcandidateFuncSet
Candidate functions which relevant to locks/unlocks.
bool isInsideIntraLock(const ICFGNode *stmt) const
Return true if a statement is inside an intra-procedural lock.
void pushCxt(CallStrCxt &cxt, const CallICFGNode *call, const SVFFunction *callee)
Push calling context.
ThreadCallGraph * getTCG() const
ThreadCallGraph.
void handleFork(const CxtStmt &cts)
Handle fork.
bool isInsideCondIntraLock(const ICFGNode *stmt) const
Return true if a statement is inside a partial lock/unlock pair (conditional lock with unconditional ...
bool intraBackwardTraverse(const InstSet &unlockset, InstSet &backwardInsts)
void addCondIntraLock(const ICFGNode *lockSite, const InstSet &stmts)
Add intra-procedural lock.
bool hasCxtLock(const CxtLock &cxtLock) const
Get context-sensitive lock.
void handleIntra(const CxtStmt &cts)
Handle intra.
bool isTDRelease(const ICFGNode *call)
Whether it is a unlock site.
const CxtStmtSet & getCxtStmtfromInst(const ICFGNode *inst) const
bool addCxtStmtToSpan(const CxtStmt &cts, const CxtLock &cl)
Add context-sensitive statement.
bool isTDFork(const ICFGNode *call)
Whether it is a lock site.
InstSet locksites
Record all visited clps.
bool isProtectedByCommonCxtLock(const ICFGNode *i1, const ICFGNode *i2)
void analyzeIntraProcedualLock()
bool pushToCTPWorkList(const CxtLockProc &clp)
WorkList helper functions.
const InstSet & getIntraLockSet(const ICFGNode *stmt) const
void handleCall(const CxtStmt &cts)
Handle call.
bool pushToCTSWorkList(const CxtStmt &cs)
Worklist operations.
void addIntraLock(const ICFGNode *lockSite, const InstSet &stmts)
Add intra-procedural lock.
void collectLockUnlocksites()
void touchCxtStmt(CxtStmt &cts)
Touch this context statement.
Set< const ICFGNode * > InstSet
Set< const SVFFunction * > FunSet
bool intraForwardTraverse(const ICFGNode *lock, InstSet &unlockset, InstSet &forwardInsts)
bool matchCxt(CallStrCxt &cxt, const CallICFGNode *call, const SVFFunction *callee)
Match context.
void printLocks(const CxtStmt &cts)
Print locks and spans.
CxtLockProc popFromCTPWorkList()
void handleRet(const CxtStmt &cts)
Handle return.
void handleCallRelation(CxtLockProc &clp, const PTACallGraphEdge *cgEdge, const CallICFGNode *call)
Handle call relations.
bool isInSameCISpan(const ICFGNode *i1, const ICFGNode *i2) const
bool hasCxtStmtfromInst(const ICFGNode *inst) const
Context-sensitive statement and lock spans.
bool isAliasedLocks(const CxtLock &cl1, const CxtLock &cl2)
Return true it a lock matches an unlock.
bool isLockCandidateFun(const SVFFunction *fun) const
Return true if it is a candidate function.
InstToCxtStmtSet instToCxtStmtSet
Map a statement to all its context-sensitive statements.
const CxtLockSet & getCxtLockfromCxtStmt(const CxtStmt &cts) const
void addCxtLock(const CallStrCxt &cxt, const ICFGNode *inst)
Context-sensitive locks.
bool intersects(const CxtLockSet &lockset1, const CxtLockSet &lockset2) const
Return true if the intersection of two locksets is not empty.
bool isCallSite(const ICFGNode *inst)
Whether it is a callsite.
CxtLockProcVec clpList
Following data structures are used for collecting context-sensitive locks.
bool isTDAcquire(const ICFGNode *call)
Whether it is a lock site.
const SVFFunction * getFunction() const
Get function of this call node.
CallSiteID getCallSiteID(const CallICFGNode *cs, const SVFFunction *callee) const
Get CallSiteID.
PTACallGraphNode * getCallGraphNode(NodeID id) const
Get call graph node.
virtual const std::string getSourceLoc() const
const ICFGNode * back() const
const SVFBasicBlock * getEntryBlock() const
const FunctionSetType & getFunctionSet() const
static double getClk(bool mark=false)
void pushCxt(CallStrCxt &cxt, const CallICFGNode *call, const SVFFunction *callee)
Push calling context.
ThreadCallGraph * getThreadCallGraph() const
Get TCG.
SVFModule * getSVFModule() const
Get SVFFModule.
bool inSameCallGraphSCC(const PTACallGraphNode *src, const PTACallGraphNode *dst)
Whether two functions in the same callgraph scc.
void dumpCxt(CallStrCxt &cxt)
Dump calling context.
const FunSet & getEntryProcs() const
Get marked candidate functions.
Set< const PTACallGraphNode * > PTACGNodeSet
bool isTDRelease(const CallICFGNode *inst) const
Return true if this call release a lock.
bool isTDAcquire(const CallICFGNode *inst) const
Return true if this call acquire a lock.
ThreadAPI * getThreadAPI() const
Thread API.
bool isExtCall(const SVFFunction *fun)
bool isRetInstNode(const ICFGNode *node)
std::ostream & outs()
Overwrite llvm::outs()
llvm::IRBuilder IRBuilder
std::vector< u32_t > CallStrCxt