Static Value-Flow Analysis
Loading...
Searching...
No Matches
MutablePointsToDS.h
Go to the documentation of this file.
1//===- MutablePointsToDS.h -- Mutable points-to data structure-------------//
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
25
26/*
27 * MutablePointsToDS.h
28 *
29 * Authors: Mohamad Barbar and Yulei Sui
30 *
31 * The implementation is based on
32 * Mohamad Barbar and Yulei Sui. Hash Consed Points-To Sets.
33 * 28th Static Analysis Symposium (SAS'21)
34 */
35
36#ifndef MUTABLE_POINTSTO_H_
37#define MUTABLE_POINTSTO_H_
38
39#include<fstream>
40
42#include "SVFIR/SVFType.h"
43#include "Util/SVFUtil.h"
44
45namespace SVF
46{
47
48template <typename Key, typename KeySet, typename Data, typename DataSet>
49class MutableDFPTData;
50
52template <typename Key, typename KeySet, typename Data, typename DataSet>
53class MutablePTData : public PTData<Key, KeySet, Data, DataSet>
54{
55 friend class MutableDFPTData<Key, KeySet, Data, DataSet>;
56public:
59
62 typedef typename PtsMap::iterator PtsMapIter;
63 typedef typename PtsMap::const_iterator PtsMapConstIter;
64 typedef typename DataSet::iterator iterator;
65
67 MutablePTData(bool reversePT = true, PTDataTy ty = PTDataTy::MutBase) : BasePTData(reversePT, ty) { }
68
69 virtual ~MutablePTData() { }
70
72 virtual inline const PtsMap& getPtsMap() const
73 {
74 return ptsMap;
75 }
76
77 virtual inline void clear() override
78 {
79 ptsMap.clear();
80 revPtsMap.clear();
81 }
82
83 virtual inline const DataSet& getPts(const Key& var) override
84 {
85 return ptsMap[var];
86 }
87
88 virtual inline const KeySet& getRevPts(const Data& datum) override
89 {
90 assert(this->rev && "MutablePTData::getRevPts: constructed without reverse PT support!");
91 return revPtsMap[datum];
92 }
93
94 virtual inline bool addPts(const Key &dstKey, const Data& element) override
95 {
97 return addPts(ptsMap[dstKey], element);
98 }
99
100 virtual inline bool unionPts(const Key& dstKey, const Key& srcKey) override
101 {
104 }
105
106 virtual inline bool unionPts(const Key& dstKey, const DataSet& srcDataSet) override
107 {
110 }
111
112 virtual inline void dumpPTData() override
113 {
115 }
116
117 virtual void clearPts(const Key& var, const Data& element) override
118 {
120 ptsMap[var].reset(element);
121 }
122
123 virtual void clearFullPts(const Key& var) override
124 {
125 DataSet &pts = ptsMap[var];
127 pts.clear();
128 }
129
130 virtual void remapAllPts(void) override
131 {
132 for (typename PtsMap::value_type &ppt : ptsMap) ppt.second.checkAndRemap();
133 }
134
135 virtual inline Map<DataSet, unsigned> getAllPts(bool liveOnly) const override
136 {
138 for (typename PtsMap::value_type ppt : ptsMap)
139 {
140 const DataSet &pt = ppt.second;
141 ++allPts[pt];
142 }
143
144 return allPts;
145 }
146
150 {
151 return true;
152 }
153
155 {
156 return ptd->getPTDTY() == PTDataTy::MutBase;
157 }
159
160protected:
161 virtual inline void dumpPts(const PtsMap & ptsSet,OutStream & O = SVFUtil::outs()) const
162 {
163 for (PtsMapConstIter nodeIt = ptsSet.begin(); nodeIt != ptsSet.end(); nodeIt++)
164 {
165 const Key& var = nodeIt->first;
166 const DataSet & pts = nodeIt->second;
167 if (pts.empty())
168 continue;
169 O << var << " ==> { ";
170 for(typename DataSet::iterator cit = pts.begin(), ecit=pts.end(); cit!=ecit; ++cit)
171 {
172 O << *cit << " ";
173 }
174 O << "}\n";
175 }
176 }
177
178private:
181 inline bool unionPts(DataSet& dstDataSet, const DataSet& srcDataSet)
182 {
183 return dstDataSet |= srcDataSet;
184 }
185 inline bool addPts(DataSet &d, const Data& e)
186 {
187 return d.test_and_set(e);
188 }
189 inline void addSingleRevPts(KeySet &revData, const Key& tgr)
190 {
191 if (this->rev)
192 {
194 }
195 }
196 inline void addRevPts(const DataSet &ptsData, const Key& tgr)
197 {
198 if (this->rev)
199 {
200 for(iterator it = ptsData.begin(), eit = ptsData.end(); it!=eit; ++it)
202 }
203 }
204 inline void clearSingleRevPts(KeySet &revSet, const Key &k)
205 {
206 if (this->rev)
207 {
209 }
210 }
211 inline void clearRevPts(const DataSet &pts, const Key &k)
212 {
213 if (this->rev)
214 {
215 for (const Data &d : pts) clearSingleRevPts(revPtsMap[d], k);
216 }
217 }
219
220protected:
223};
224
226template <typename Key, typename KeySet, typename Data, typename DataSet>
227class MutableDiffPTData : public DiffPTData<Key, KeySet, Data, DataSet>
228{
229public:
233
235
237 explicit MutableDiffPTData(bool reversePT = true, PTDataTy ty = PTDataTy::Diff) : BaseDiffPTData(reversePT, ty), mutPTData(reversePT) { }
238
239 ~MutableDiffPTData() override = default;
240
241 virtual inline const PtsMap& getPtsMap() const
242 {
243 return mutPTData.getPtsMap();
244 }
245
246 inline void clear() override
247 {
248 mutPTData.clear();
249 }
250
251 virtual inline const DataSet& getPts(const Key& var) override
252 {
253 return mutPTData.getPts(var);
254 }
255
256 virtual inline const KeySet& getRevPts(const Data& datum) override
257 {
258 assert(this->rev && "MutableDiffPTData::getRevPts: constructed without reverse PT support!");
259 return mutPTData.getRevPts(datum);
260 }
261
262 virtual inline bool addPts(const Key &dstKey, const Data& element) override
263 {
264 return mutPTData.addPts(dstKey, element);
265 }
266
267 virtual inline bool unionPts(const Key& dstKey, const Key& srcKey) override
268 {
269 return mutPTData.unionPts(dstKey, srcKey);
270 }
271
272 virtual inline bool unionPts(const Key& dstKey, const DataSet& srcDataSet) override
273 {
274 return mutPTData.unionPts(dstKey, srcDataSet);
275 }
276
277 virtual void clearPts(const Key& var, const Data& element) override
278 {
279 mutPTData.clearPts(var, element);
280 }
281
282 virtual void clearFullPts(const Key& var) override
283 {
284 mutPTData.clearFullPts(var);
285 }
286
287 virtual void remapAllPts(void) override
288 {
289 mutPTData.remapAllPts();
290 for (typename PtsMap::value_type &ppt : diffPtsMap) ppt.second.checkAndRemap();
291 for (typename PtsMap::value_type &ppt : propaPtsMap) ppt.second.checkAndRemap();
292 }
293
294 virtual inline void dumpPTData() override
295 {
296 mutPTData.dumpPTData();
297 }
298
299 virtual inline const DataSet &getDiffPts(Key &var) override
300 {
301 return diffPtsMap[var];
302 }
303
304 virtual inline bool computeDiffPts(Key &var, const DataSet &all) override
305 {
307 DataSet& diff = diffPtsMap[var];
308 diff.clear();
310 DataSet& propa = getPropaPts(var);
311 diff.intersectWithComplement(all, propa);
312 propa = all;
313 return !diff.empty();
314 }
315
316 virtual inline void updatePropaPtsMap(Key &src, Key &dst) override
317 {
318 DataSet& srcPropa = getPropaPts(src);
319 DataSet& dstPropa = getPropaPts(dst);
321 }
322
323 virtual inline void clearPropaPts(Key &var) override
324 {
325 getPropaPts(var).clear();
326 }
327
328 virtual inline Map<DataSet, unsigned> getAllPts(bool liveOnly) const override
329 {
330 return mutPTData.getAllPts(liveOnly);
331 }
332
336 {
337 return true;
338 }
339
341 {
342 return ptd->getPTDTY() == PTDataTy::MutDiff;
343 }
345
346protected:
348 inline DataSet &getPropaPts(Key &var)
349 {
350 return propaPtsMap[var];
351 }
352
353private:
360};
361
362template <typename Key, typename KeySet, typename Data, typename DataSet>
363class MutableDFPTData : public DFPTData<Key, KeySet, Data, DataSet>
364{
365public:
370
371 typedef typename BaseDFPTData::LocID LocID;
375 typedef typename DFPtsMap::iterator DFPtsMapIter;
376 typedef typename DFPtsMap::const_iterator DFPtsMapconstIter;
377
380
381 virtual ~MutableDFPTData() { }
382
383 virtual inline const PtsMap& getPtsMap() const
384 {
385 return mutPTData.getPtsMap();
386 }
387
388 virtual inline void clear() override
389 {
390 mutPTData.clear();
391 }
392
393 virtual inline const DataSet& getPts(const Key& var) override
394 {
395 return mutPTData.getPts(var);
396 }
397
398 virtual inline const KeySet& getRevPts(const Data& datum) override
399 {
400 assert(this->rev && "MutableDFPTData::getRevPts: constructed without reverse PT support!");
401 return mutPTData.getRevPts(datum);
402 }
403
404 virtual inline bool hasDFInSet(LocID loc) const override
405 {
406 return (dfInPtsMap.find(loc) != dfInPtsMap.end());
407 }
408
409 virtual inline bool hasDFOutSet(LocID loc) const override
410 {
411 return (dfOutPtsMap.find(loc) != dfOutPtsMap.end());
412 }
413
414 virtual inline bool hasDFInSet(LocID loc,const Key& var) const override
415 {
417 if ( it == dfInPtsMap.end())
418 return false;
419 const PtsMap& ptsMap = it->second;
420 return (ptsMap.find(var) != ptsMap.end());
421 }
422
423 virtual inline bool hasDFOutSet(LocID loc, const Key& var) const override
424 {
426 if ( it == dfOutPtsMap.end())
427 return false;
428 const PtsMap& ptsMap = it->second;
429 return (ptsMap.find(var) != ptsMap.end());
430 }
431
432 virtual inline DataSet& getDFInPtsSet(LocID loc, const Key& var) override
433 {
435 return inSet[var];
436 }
437
438 virtual inline DataSet& getDFOutPtsSet(LocID loc, const Key& var) override
439 {
441 return outSet[var];
442 }
443
447 {
448 return dfInPtsMap[loc];
449 }
451 {
452 return dfOutPtsMap[loc];
453 }
454 inline const DFPtsMap& getDFIn()
455 {
456 return dfInPtsMap;
457 }
458 inline const DFPtsMap& getDFOut()
459 {
460 return dfOutPtsMap;
461 }
463
464 virtual inline bool updateDFInFromIn(LocID srcLoc, const Key& srcVar, LocID dstLoc, const Key& dstVar) override
465 {
466 return this->unionPts(getDFInPtsSet(dstLoc,dstVar), getDFInPtsSet(srcLoc,srcVar));
467 }
468
469 virtual inline bool updateDFInFromOut(LocID srcLoc, const Key& srcVar, LocID dstLoc, const Key& dstVar) override
470 {
472 }
473
474 virtual inline bool updateDFOutFromIn(LocID srcLoc, const Key& srcVar, LocID dstLoc, const Key& dstVar) override
475 {
477 }
478
479 virtual inline bool updateAllDFInFromOut(LocID srcLoc, const Key& srcVar, LocID dstLoc, const Key& dstVar) override
480 {
481 return this->updateDFInFromOut(srcLoc,srcVar,dstLoc,dstVar);
482 }
483
484 virtual inline bool updateAllDFInFromIn(LocID srcLoc, const Key& srcVar, LocID dstLoc, const Key& dstVar) override
485 {
486 return this->updateDFInFromIn(srcLoc,srcVar,dstLoc,dstVar);
487 }
488
489 virtual inline bool updateAllDFOutFromIn(LocID loc, const Key& singleton, bool strongUpdates) override
490 {
491 bool changed = false;
492 if (this->hasDFInSet(loc))
493 {
495 const PtsMap & ptsMap = getDFInPtsMap(loc);
496 for (typename PtsMap::const_iterator ptsIt = ptsMap.begin(), ptsEit = ptsMap.end(); ptsIt != ptsEit; ++ptsIt)
497 {
498 const Key var = ptsIt->first;
500 if (strongUpdates && var == singleton)
501 continue;
503 changed = true;
504 }
505 }
506 return changed;
507 }
508
509 virtual inline bool updateTLVPts(LocID srcLoc, const Key& srcVar, const Key& dstVar) override
510 {
511 return this->unionPts(dstVar, this->getDFInPtsSet(srcLoc,srcVar));
512 }
513
514 virtual inline bool updateATVPts(const Key& srcVar, LocID dstLoc, const Key& dstVar) override
515 {
516 return (this->unionPts(this->getDFOutPtsSet(dstLoc, dstVar), this->getPts(srcVar)));
517 }
518
519 virtual inline void clearAllDFOutUpdatedVar(LocID) override
520 {
521 }
522
526 virtual inline bool addPts(const Key &dstKey, const Key& srcKey) override
527 {
528 return addPts(mutPTData.ptsMap[dstKey], srcKey);
529 }
530 virtual inline bool unionPts(const Key& dstKey, const Key& srcKey) override
531 {
532 return unionPts(mutPTData.ptsMap[dstKey], getPts(srcKey));
533 }
534 virtual inline bool unionPts(const Key& dstKey, const DataSet& srcDataSet) override
535 {
536 return unionPts(mutPTData.ptsMap[dstKey], srcDataSet);
537 }
538 virtual void clearPts(const Key& var, const Data& element) override
539 {
540 mutPTData.clearPts(var, element);
541 }
542 virtual void clearFullPts(const Key& var) override
543 {
544 mutPTData.clearFullPts(var);
545 }
546 virtual void remapAllPts(void) override
547 {
548 mutPTData.remapAllPts();
549 for (typename DFPtsMap::value_type &lopt : dfInPtsMap)
550 {
551 for (typename PtsMap::value_type &opt : lopt.second) opt.second.checkAndRemap();
552 }
553
554 for (typename DFPtsMap::value_type &lopt : dfOutPtsMap)
555 {
556 for (typename PtsMap::value_type &opt : lopt.second) opt.second.checkAndRemap();
557 }
558 }
560
561 virtual inline Map<DataSet, unsigned> getAllPts(bool liveOnly) const override
562 {
564 for (typename DFPtsMap::value_type lptsmap : dfInPtsMap)
565 {
566 for (typename PtsMap::value_type vpt : lptsmap.second)
567 {
568 ++allPts[vpt.second];
569 }
570 }
571
572 for (typename DFPtsMap::value_type lptm : dfOutPtsMap)
573 {
574 for (typename PtsMap::value_type vpt : lptm.second)
575 {
576 ++allPts[vpt.second];
577 }
578 }
579
580 return allPts;
581 }
582
586 {
587 return true;
588 }
590 {
591 return ptd->getPTDTY() == BaseDFPTData::MutDataFlow
592 || ptd->getPTDTY() == BaseDFPTData::MutIncDataFlow;
593 }
595
596protected:
599 inline bool unionPts(DataSet& dstDataSet, const DataSet& srcDataSet)
600 {
601 return dstDataSet |= srcDataSet;
602 }
603 inline bool addPts(DataSet &d, const Data& e)
604 {
605 return d.test_and_set(e);
606 }
608
609public:
612 virtual inline void dumpPTData() override
613 {
615 mutPTData.dumpPTData();
617 std::error_code ErrInfo;
618 std::fstream f("svfg_pts.data", std::ios_base::out);
619 if (f.good())
620 {
621 NodeBS locs;
622 for(DFPtsMapconstIter it = dfInPtsMap.begin(), eit = dfInPtsMap.end(); it!=eit; ++it)
623 locs.set(it->first);
624
625 for(DFPtsMapconstIter it = dfOutPtsMap.begin(), eit = dfOutPtsMap.end(); it!=eit; ++it)
626 locs.set(it->first);
627
628 for (NodeBS::iterator it = locs.begin(), eit = locs.end(); it != eit; it++)
629 {
630 LocID loc = *it;
631 if (this->hasDFInSet(loc))
632 {
633 f << "Loc:" << loc << " IN:{";
634 this->dumpPts(this->getDFInPtsMap(loc), f);
635 f << "}\n";
636 }
637
638 if (this->hasDFOutSet(loc))
639 {
640 f << "Loc:" << loc << " OUT:{";
641 this->dumpPts(this->getDFOutPtsMap(loc), f);
642 f << "}\n";
643 }
644 }
645 f.close();
646 if (f.good())
647 {
648 SVFUtil::outs() << "\n";
649 return;
650 }
651 }
652 SVFUtil::outs() << " error opening file for writing!\n";
653 }
654
655 virtual inline void dumpPts(const PtsMap & ptsSet,OutStream & O = SVFUtil::outs()) const
656 {
657 for (PtsMapConstIter nodeIt = ptsSet.begin(); nodeIt != ptsSet.end(); nodeIt++)
658 {
659 const Key& var = nodeIt->first;
660 const DataSet & pts = nodeIt->second;
661 if (pts.empty())
662 continue;
663 O << "<" << var << ",{";
665 O << "}> ";
666 }
667 }
669
670protected:
678};
679
681template <typename Key, typename KeySet, typename Data, typename DataSet>
682class MutableIncDFPTData : public MutableDFPTData<Key, KeySet, Data, DataSet>
683{
684public:
690
691 typedef typename BaseDFPTData::LocID LocID;
693 typedef typename UpdatedVarMap::iterator UpdatedVarMapIter;
694 typedef typename UpdatedVarMap::const_iterator UpdatedVarconstIter;
695 typedef typename DataSet::iterator DataIter;
696
697private:
700
701public:
704
706
707 virtual inline bool updateDFInFromIn(LocID srcLoc, const Key& srcVar, LocID dstLoc, const Key& dstVar) override
708 {
710 this->unionPts(this->getDFInPtsSet(dstLoc,dstVar), this->getDFInPtsSet(srcLoc,srcVar)))
711 {
713 return true;
714 }
715 return false;
716 }
717
718 virtual inline bool updateDFInFromOut(LocID srcLoc, const Key& srcVar, LocID dstLoc, const Key& dstVar) override
719 {
721 this->unionPts(this->getDFInPtsSet(dstLoc,dstVar), this->getDFOutPtsSet(srcLoc,srcVar)))
722 {
724 return true;
725 }
726 return false;
727 }
728
729 virtual inline bool updateDFOutFromIn(LocID srcLoc, const Key& srcVar, LocID dstLoc, const Key& dstVar) override
730 {
732 {
734 if (this->unionPts(this->getDFOutPtsSet(dstLoc,dstVar), this->getDFInPtsSet(srcLoc,srcVar)))
735 {
737 return true;
738 }
739 }
740 return false;
741 }
742
743 virtual inline bool updateAllDFInFromOut(LocID srcLoc, const Key& srcVar, LocID dstLoc, const Key& dstVar) override
744 {
745 if(this->unionPts(this->getDFInPtsSet(dstLoc,dstVar), this->getDFOutPtsSet(srcLoc,srcVar)))
746 {
748 return true;
749 }
750 return false;
751 }
752
753 virtual inline bool updateAllDFInFromIn(LocID srcLoc, const Key& srcVar, LocID dstLoc, const Key& dstVar) override
754 {
755 if(this->unionPts(this->getDFInPtsSet(dstLoc,dstVar), this->getDFInPtsSet(srcLoc,srcVar)))
756 {
758 return true;
759 }
760 return false;
761 }
762
763 virtual inline bool updateAllDFOutFromIn(LocID loc, const Key& singleton, bool strongUpdates) override
764 {
765 bool changed = false;
766 if (this->hasDFInSet(loc))
767 {
769 DataSet pts = getDFInUpdatedVar(loc);
770 for (DataIter ptsIt = pts.begin(), ptsEit = pts.end(); ptsIt != ptsEit; ++ptsIt)
771 {
772 const Key var = *ptsIt;
774 if (strongUpdates && var == singleton)
775 continue;
777 changed = true;
778 }
779 }
780 return changed;
781 }
782
783 virtual inline bool updateTLVPts(LocID srcLoc, const Key& srcVar, const Key& dstVar) override
784 {
786 {
788 return this->mutPTData.unionPts(dstVar, this->getDFInPtsSet(srcLoc,srcVar));
789 }
790 return false;
791 }
792
793 virtual inline bool updateATVPts(const Key& srcVar, LocID dstLoc, const Key& dstVar) override
794 {
795 if (this->unionPts(this->getDFOutPtsSet(dstLoc, dstVar), this->mutPTData.getPts(srcVar)))
796 {
798 return true;
799 }
800 return false;
801 }
802
803 virtual inline void clearAllDFOutUpdatedVar(LocID loc) override
804 {
805 if (this->hasDFOutSet(loc))
806 {
807 DataSet pts = getDFOutUpdatedVar(loc);
808 for (DataIter ptsIt = pts.begin(), ptsEit = pts.end(); ptsIt != ptsEit; ++ptsIt)
809 {
810 const Key var = *ptsIt;
812 }
813 }
814 }
815
819 {
820 return true;
821 }
822
824 {
825 return ptd->getPTDTY() == BasePTData::MutIncDataFlow;
826 }
828private:
830
831
833 {
834 inUpdatedVarMap[loc].set(var);
835 }
838 {
840 if (it != inUpdatedVarMap.end())
841 it->second.reset(var);
842 }
844 inline bool varHasNewDFInPts(LocID loc,const Key& var)
845 {
847 if (it != inUpdatedVarMap.end())
848 return it->second.test(var);
849 return false;
850 }
852 inline const DataSet& getDFInUpdatedVar(LocID loc)
853 {
854 return inUpdatedVarMap[loc];
855 }
857
859
860
862 {
864 }
867 {
869 if (it != outUpdatedVarMap.end())
870 it->second.reset(var);
871 }
873 inline bool varHasNewDFOutPts(LocID loc,const Key& var)
874 {
876 if (it != outUpdatedVarMap.end())
877 return it->second.test(var);
878 return false;
879 }
881 inline const DataSet& getDFOutUpdatedVar(LocID loc)
882 {
883 return outUpdatedVarMap[loc];
884 }
886};
887
891template <typename Key, typename KeySet, typename Data, typename DataSet, typename VersionedKey, typename VersionedKeySet>
892class MutableVersionedPTData : public VersionedPTData<Key, KeySet, Data, DataSet, VersionedKey, VersionedKeySet>
893{
894public:
898
901
903
904 virtual inline void clear() override
905 {
906 tlPTData.clear();
907 atPTData.clear();
908 }
909
910 virtual const DataSet& getPts(const Key& vk) override
911 {
912 return tlPTData.getPts(vk);
913 }
914 virtual const DataSet& getPts(const VersionedKey& vk) override
915 {
916 return atPTData.getPts(vk);
917 }
918
919 virtual const KeySet& getRevPts(const Data& datum) override
920 {
921 assert(this->rev && "MutableVersionedPTData::getRevPts: constructed without reverse PT support!");
922 return tlPTData.getRevPts(datum);
923 }
924 virtual const VersionedKeySet& getVersionedKeyRevPts(const Data& datum) override
925 {
926 assert(this->rev && "MutableVersionedPTData::getVersionedKeyRevPts: constructed without reverse PT support!");
927 return atPTData.getRevPts(datum);
928 }
929
930 virtual bool addPts(const Key& k, const Data& element) override
931 {
932 return tlPTData.addPts(k, element);
933 }
934 virtual bool addPts(const VersionedKey& vk, const Data& element) override
935 {
936 return atPTData.addPts(vk, element);
937 }
938
939 virtual bool unionPts(const Key& dstVar, const Key& srcVar) override
940 {
941 return tlPTData.unionPts(dstVar, srcVar);
942 }
943 virtual bool unionPts(const VersionedKey& dstVar, const VersionedKey& srcVar) override
944 {
946 }
947 virtual bool unionPts(const VersionedKey& dstVar, const Key& srcVar) override
948 {
949 return atPTData.unionPts(dstVar, tlPTData.getPts(srcVar));
950 }
951 virtual bool unionPts(const Key& dstVar, const VersionedKey& srcVar) override
952 {
953 return tlPTData.unionPts(dstVar, atPTData.getPts(srcVar));
954 }
955 virtual bool unionPts(const Key& dstVar, const DataSet& srcDataSet) override
956 {
957 return tlPTData.unionPts(dstVar, srcDataSet);
958 }
959 virtual bool unionPts(const VersionedKey& dstVar, const DataSet& srcDataSet) override
960 {
962 }
963
964 virtual void clearPts(const Key& k, const Data& element) override
965 {
966 tlPTData.clearPts(k, element);
967 }
968 virtual void clearPts(const VersionedKey& vk, const Data& element) override
969 {
971 }
972
973 virtual void clearFullPts(const Key& k) override
974 {
975 tlPTData.clearFullPts(k);
976 }
977 virtual void clearFullPts(const VersionedKey& vk) override
978 {
980 }
981
982 virtual void remapAllPts(void) override
983 {
984 tlPTData.remapAllPts();
986 }
987
988 virtual inline Map<DataSet, unsigned> getAllPts(bool liveOnly) const override
989 {
991 SVFUtil::mergePtsOccMaps<DataSet>(allPts, atPTData.getAllPts(liveOnly));
992 return allPts;
993 }
994
995 virtual inline void dumpPTData() override
996 {
997 SVFUtil::outs() << "== Top-level points-to information\n";
998 tlPTData.dumpPTData();
999 SVFUtil::outs() << "== Address-taken points-to information\n";
1001 }
1002
1006 {
1007 return true;
1008 }
1009
1011 {
1012 return ptd->getPTDTY() == PTDataTy::MutVersioned;
1013 }
1015
1016private:
1021};
1022
1023} // End namespace SVF
1024
1025#endif // MUTABLE_POINTSTO_H_
Map< LocID, PtsMap > DFPtsMap
Data-flow point-to map.
virtual bool updateATVPts(const Key &srcVar, LocID dstLoc, const Key &dstVar) override
Update address-taken variables OUT[dstLoc:dstVar] with points-to of top-level pointers.
virtual DataSet & getDFOutPtsSet(LocID loc, const Key &var) override
DFPTData< Key, KeySet, Data, DataSet > BaseDFPTData
const PtsMap & getDFInPtsMap(LocID loc)
virtual bool updateTLVPts(LocID srcLoc, const Key &srcVar, const Key &dstVar) override
Update points-to set of top-level pointers with IN[srcLoc:srcVar].
const PtsMap & getDFOutPtsMap(LocID loc)
virtual bool updateAllDFInFromIn(LocID srcLoc, const Key &srcVar, LocID dstLoc, const Key &dstVar) override
Union (IN[dstLoc::dstVar], IN[srcLoc:srcVar]. There is no flag check, unlike the above.
PTData< Key, KeySet, Data, DataSet > BasePTData
DFPtsMap::iterator DFPtsMapIter
BaseMutPTData::PtsMapConstIter PtsMapConstIter
virtual void clearAllDFOutUpdatedVar(LocID) override
virtual void clear() override
Clears all points-to sets as if nothing is stored.
virtual bool updateAllDFOutFromIn(LocID loc, const Key &singleton, bool strongUpdates) override
For each variable var in IN at loc, do updateDFOutFromIn(loc, var, loc, var).
static bool classof(const MutableDFPTData< Key, KeySet, Data, DataSet > *)
const DFPtsMap & getDFIn()
virtual bool updateAllDFInFromOut(LocID srcLoc, const Key &srcVar, LocID dstLoc, const Key &dstVar) override
Union (IN[dstLoc::dstVar], OUT[srcLoc:srcVar]. There is no flag check, unlike the above.
virtual bool updateDFInFromOut(LocID srcLoc, const Key &srcVar, LocID dstLoc, const Key &dstVar) override
Union (IN[dstLoc:dstVar], OUT[srcLoc:srcVar]).
bool unionPts(DataSet &dstDataSet, const DataSet &srcDataSet)
virtual void dumpPTData() override
virtual const DataSet & getPts(const Key &var) override
Get points-to set of var.
virtual bool hasDFInSet(LocID loc) const override
const DFPtsMap & getDFOut()
virtual bool hasDFInSet(LocID loc, const Key &var) const override
virtual DataSet & getDFInPtsSet(LocID loc, const Key &var) override
virtual void clearFullPts(const Key &var) override
Fully clears the points-to set of var.
virtual Map< DataSet, unsigned > getAllPts(bool liveOnly) const override
virtual bool updateDFOutFromIn(LocID srcLoc, const Key &srcVar, LocID dstLoc, const Key &dstVar) override
Union (OUT[dstLoc:dstVar], IN[srcLoc:srcVar]).
virtual bool unionPts(const Key &dstKey, const DataSet &srcDataSet) override
Performs pts(dstVar) = pts(dstVar) U srcDataSet.
virtual bool addPts(const Key &dstKey, const Key &srcKey) override
bool addPts(DataSet &d, const Data &e)
DFPtsMap dfInPtsMap
Data-flow IN set.
virtual const PtsMap & getPtsMap() const
virtual bool updateDFInFromIn(LocID srcLoc, const Key &srcVar, LocID dstLoc, const Key &dstVar) override
virtual const KeySet & getRevPts(const Data &datum) override
Get reverse points-to set of a datum.
virtual bool hasDFOutSet(LocID loc) const override
static bool classof(const PTData< Key, KeySet, Data, DataSet > *ptd)
MutablePTData< Key, KeySet, Data, DataSet > mutPTData
MutablePTData< Key, KeySet, Data, DataSet > BaseMutPTData
virtual void remapAllPts(void) override
Remaps all points-to sets to use the current mapping.
DFPtsMap dfOutPtsMap
Data-flow OUT set.
virtual bool unionPts(const Key &dstKey, const Key &srcKey) override
Performs pts(dstVar) = pts(dstVar) U pts(srcVar).
DFPtsMap::const_iterator DFPtsMapconstIter
virtual void clearPts(const Key &var, const Data &element) override
Clears element from the points-to set of var.
BaseMutPTData::PtsMap PtsMap
BaseDFPTData::LocID LocID
virtual void dumpPts(const PtsMap &ptsSet, OutStream &O=SVFUtil::outs()) const
MutableDFPTData(bool reversePT=true, PTDataTy ty=BaseDFPTData::MutDataFlow)
Constructor.
BasePTData::PTDataTy PTDataTy
virtual bool hasDFOutSet(LocID loc, const Key &var) const override
DiffPTData implemented with points-to sets which are updated continuously.
virtual bool unionPts(const Key &dstKey, const Key &srcKey) override
Performs pts(dstVar) = pts(dstVar) U pts(srcVar).
DataSet & getPropaPts(Key &var)
Get propagated points to.
MutablePTData< Key, KeySet, Data, DataSet >::PtsMap PtsMap
static bool classof(const MutableDiffPTData< Key, KeySet, Data, DataSet > *)
virtual void updatePropaPtsMap(Key &src, Key &dst) override
virtual const PtsMap & getPtsMap() const
MutablePTData< Key, KeySet, Data, DataSet > mutPTData
Backing to implement the basic PTData methods. This allows us to avoid multiple-inheritance.
virtual void clearPropaPts(Key &var) override
Clear propagated points-to set of var.
~MutableDiffPTData() override=default
virtual Map< DataSet, unsigned > getAllPts(bool liveOnly) const override
PTData< Key, KeySet, Data, DataSet > BasePTData
virtual void clearPts(const Key &var, const Data &element) override
Clears element from the points-to set of var.
void clear() override
Clears all points-to sets as if nothing is stored.
virtual bool addPts(const Key &dstKey, const Data &element) override
Adds element to the points-to set associated with var.
virtual bool unionPts(const Key &dstKey, const DataSet &srcDataSet) override
Performs pts(dstVar) = pts(dstVar) U srcDataSet.
virtual void remapAllPts(void) override
Remaps all points-to sets to use the current mapping.
virtual void clearFullPts(const Key &var) override
Fully clears the points-to set of var.
virtual const DataSet & getPts(const Key &var) override
Get points-to set of var.
BasePTData::PTDataTy PTDataTy
PtsMap diffPtsMap
Diff points-to to be propagated.
DiffPTData< Key, KeySet, Data, DataSet > BaseDiffPTData
virtual const KeySet & getRevPts(const Data &datum) override
Get reverse points-to set of a datum.
virtual bool computeDiffPts(Key &var, const DataSet &all) override
PtsMap propaPtsMap
Points-to already propagated.
virtual void dumpPTData() override
Dump stored keys and points-to sets.
MutableDiffPTData(bool reversePT=true, PTDataTy ty=PTDataTy::Diff)
Constructor.
virtual const DataSet & getDiffPts(Key &var) override
Get diff points to.
static bool classof(const PTData< Key, KeySet, Data, DataSet > *ptd)
Incremental version of the mutable data-flow points-to data structure.
PTData< Key, KeySet, Data, DataSet > BasePTData
virtual bool updateAllDFInFromOut(LocID srcLoc, const Key &srcVar, LocID dstLoc, const Key &dstVar) override
Union (IN[dstLoc::dstVar], OUT[srcLoc:srcVar]. There is no flag check, unlike the above.
void setVarDFInSetUpdated(LocID loc, const Key &var)
Handle address-taken variables whose IN pts changed.
const DataSet & getDFOutUpdatedVar(LocID loc)
Get all var which have new pts information in loc's OUT set.
virtual bool updateAllDFOutFromIn(LocID loc, const Key &singleton, bool strongUpdates) override
For each variable var in IN at loc, do updateDFOutFromIn(loc, var, loc, var).
DFPTData< Key, KeySet, Data, DataSet > BaseDFPTData
bool varHasNewDFOutPts(LocID loc, const Key &var)
Return TRUE if var has new pts in loc's OUT set.
MutableDFPTData< Key, KeySet, Data, DataSet > BaseMutDFPTData
BasePTData::PTDataTy PTDataTy
Map< LocID, DataSet > UpdatedVarMap
for propagating only newly added variable in IN/OUT set
BaseDFPTData::LocID LocID
virtual bool updateDFInFromIn(LocID srcLoc, const Key &srcVar, LocID dstLoc, const Key &dstVar) override
virtual bool updateTLVPts(LocID srcLoc, const Key &srcVar, const Key &dstVar) override
Update points-to set of top-level pointers with IN[srcLoc:srcVar].
void setVarDFOutSetUpdated(LocID loc, const Key &var)
Handle address-taken variables whose OUT pts changed.
static bool classof(const MutableIncDFPTData< Key, KeySet, Data, DataSet > *)
UpdatedVarMap::iterator UpdatedVarMapIter
const DataSet & getDFInUpdatedVar(LocID loc)
Get all var which have new pts information in loc's IN set.
void removeVarFromDFInUpdatedSet(LocID loc, const Key &var)
Remove var from loc's IN updated set.
MutablePTData< Key, KeySet, Data, DataSet > BaseMutPTData
MutableIncDFPTData(bool reversePT=true, PTDataTy ty=BasePTData::MutIncDataFlow)
Constructor.
virtual bool updateDFOutFromIn(LocID srcLoc, const Key &srcVar, LocID dstLoc, const Key &dstVar) override
Union (OUT[dstLoc:dstVar], IN[srcLoc:srcVar]).
static bool classof(const PTData< Key, KeySet, Data, DataSet > *ptd)
virtual bool updateATVPts(const Key &srcVar, LocID dstLoc, const Key &dstVar) override
Update address-taken variables OUT[dstLoc:dstVar] with points-to of top-level pointers.
void removeVarFromDFOutUpdatedSet(LocID loc, const Key &var)
Remove var from loc's OUT updated set.
virtual void clearAllDFOutUpdatedVar(LocID loc) override
virtual bool updateDFInFromOut(LocID srcLoc, const Key &srcVar, LocID dstLoc, const Key &dstVar) override
Union (IN[dstLoc:dstVar], OUT[srcLoc:srcVar]).
virtual bool updateAllDFInFromIn(LocID srcLoc, const Key &srcVar, LocID dstLoc, const Key &dstVar) override
Union (IN[dstLoc::dstVar], IN[srcLoc:srcVar]. There is no flag check, unlike the above.
bool varHasNewDFInPts(LocID loc, const Key &var)
Return TRUE if var has new pts in loc's IN set.
UpdatedVarMap::const_iterator UpdatedVarconstIter
PTData implemented using points-to sets which are created once and updated continuously.
virtual const KeySet & getRevPts(const Data &datum) override
Get reverse points-to set of a datum.
virtual bool unionPts(const Key &dstKey, const Key &srcKey) override
Performs pts(dstVar) = pts(dstVar) U pts(srcVar).
virtual bool unionPts(const Key &dstKey, const DataSet &srcDataSet) override
Performs pts(dstVar) = pts(dstVar) U srcDataSet.
virtual void dumpPTData() override
Dump stored keys and points-to sets.
virtual void remapAllPts(void) override
Remaps all points-to sets to use the current mapping.
virtual void clearFullPts(const Key &var) override
Fully clears the points-to set of var.
void addSingleRevPts(KeySet &revData, const Key &tgr)
MutablePTData(bool reversePT=true, PTDataTy ty=PTDataTy::MutBase)
Constructor.
void clearSingleRevPts(KeySet &revSet, const Key &k)
static bool classof(const PTData< Key, KeySet, Data, DataSet > *ptd)
static bool classof(const MutablePTData< Key, KeySet, Data, DataSet > *)
virtual void clearPts(const Key &var, const Data &element) override
Clears element from the points-to set of var.
virtual Map< DataSet, unsigned > getAllPts(bool liveOnly) const override
Map< Data, KeySet > RevPtsMap
void clearRevPts(const DataSet &pts, const Key &k)
bool addPts(DataSet &d, const Data &e)
virtual const DataSet & getPts(const Key &var) override
Get points-to set of var.
BasePTData::PTDataTy PTDataTy
virtual bool addPts(const Key &dstKey, const Data &element) override
Adds element to the points-to set associated with var.
PTData< Key, KeySet, Data, DataSet > BasePTData
bool unionPts(DataSet &dstDataSet, const DataSet &srcDataSet)
virtual void clear() override
Clears all points-to sets as if nothing is stored.
PtsMap::iterator PtsMapIter
void addRevPts(const DataSet &ptsData, const Key &tgr)
virtual const PtsMap & getPtsMap() const
Return Points-to map.
Map< Key, DataSet > PtsMap
DataSet::iterator iterator
PtsMap::const_iterator PtsMapConstIter
virtual void dumpPts(const PtsMap &ptsSet, OutStream &O=SVFUtil::outs()) const
virtual bool addPts(const Key &k, const Data &element) override
Adds element to the points-to set associated with var.
MutablePTData< Key, KeySet, Data, DataSet > tlPTData
PTData for Keys (top-level pointers, generally).
virtual const DataSet & getPts(const Key &vk) override
Get points-to set of var.
virtual void clearPts(const VersionedKey &vk, const Data &element) override
PTData< Key, KeySet, Data, DataSet > BasePTData
MutablePTData< VersionedKey, VersionedKeySet, Data, DataSet > atPTData
PTData for VersionedKeys (address-taken objects, generally).
virtual bool unionPts(const VersionedKey &dstVar, const Key &srcVar) override
virtual bool unionPts(const VersionedKey &dstVar, const VersionedKey &srcVar) override
virtual const DataSet & getPts(const VersionedKey &vk) override
static bool classof(const PTData< Key, KeySet, Data, DataSet > *ptd)
static bool classof(const MutableVersionedPTData< Key, KeySet, Data, DataSet, VersionedKey, VersionedKeySet > *)
virtual void remapAllPts(void) override
Remaps all points-to sets to use the current mapping.
virtual Map< DataSet, unsigned > getAllPts(bool liveOnly) const override
virtual void dumpPTData() override
Dump stored keys and points-to sets.
virtual const VersionedKeySet & getVersionedKeyRevPts(const Data &datum) override
virtual bool unionPts(const Key &dstVar, const VersionedKey &srcVar) override
virtual void clearFullPts(const Key &k) override
Fully clears the points-to set of var.
VersionedPTData< Key, KeySet, Data, DataSet, VersionedKey, VersionedKeySet > BaseVersionedPTData
virtual bool unionPts(const Key &dstVar, const DataSet &srcDataSet) override
Performs pts(dstVar) = pts(dstVar) U srcDataSet.
virtual bool unionPts(const VersionedKey &dstVar, const DataSet &srcDataSet) override
virtual void clearFullPts(const VersionedKey &vk) override
virtual void clearPts(const Key &k, const Data &element) override
Clears element from the points-to set of var.
virtual void clear() override
Clears all points-to sets as if nothing is stored.
virtual const KeySet & getRevPts(const Data &datum) override
Get reverse points-to set of a datum.
MutableVersionedPTData(bool reversePT=true, PTDataTy ty=PTDataTy::MutVersioned)
virtual bool unionPts(const Key &dstVar, const Key &srcVar) override
Performs pts(dstVar) = pts(dstVar) U pts(srcVar).
virtual bool addPts(const VersionedKey &vk, const Data &element) override
BasePTData::PTDataTy PTDataTy
bool rev
Whether we maintain reverse points-to sets or not.
PTDataTy
Types of a points-to data structures.
void set(unsigned Idx)
std::ostream & outs()
Overwrite llvm::outs()
Definition SVFUtil.h:50
void dumpSet(NodeBS To, OutStream &O=SVFUtil::outs())
Dump sparse bitvector set.
Definition SVFUtil.cpp:148
void removeKey(const Key &key, KeySet &keySet)
Removes an element from a Set/CondSet (or anything implementing ::erase).
Definition SVFUtil.h:252
void insertKey(const Key &key, KeySet &keySet)
Inserts an element into a Set/CondSet (with ::insert).
Definition SVFUtil.h:239
for isBitcode
Definition BasicTypes.h:68
std::ostream OutStream
Definition GeneralType.h:45
llvm::IRBuilder IRBuilder
Definition BasicTypes.h:74