Static Value-Flow Analysis
Loading...
Searching...
No Matches
SVFStatements.h
Go to the documentation of this file.
1//===- SVFStatements.h -- SVF statements-------------------------------------------//
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/*
25 * SVFStatements.h
26 *
27 * Created on: Nov 10, 2013
28 * Author: Yulei Sui
29 */
30
31#ifndef INCLUDE_SVFIR_SVFSTATEMENT_H_
32#define INCLUDE_SVFIR_SVFSTATEMENT_H_
33
34#include "Graphs/GenericGraph.h"
36
37namespace SVF
38{
39
40class SVFVar;
41class ValVar;
42class ObjVar;
43class ICFGNode;
44class IntraICFGNode;
45class CallICFGNode;
46class FunEntryICFGNode;
47class FunExitICFGNode;
48class SVFBasicBlock;
49
50/*
51 * SVFIR program statements (PAGEdges)
52 */
55{
56 friend class GraphDBClient;
57
58public:
81
82private:
83 const SVFVar* value;
87
88protected:
91 : GenericPAGEdgeTy({}, {}, k), value{}, basicBlock{}, icfgNode{}
92 {
93 }
94
95 SVFStmt(SVFVar* s, SVFVar* d, GEdgeFlag k, EdgeID eid, SVFVar* value, ICFGNode* icfgNode, bool real = true);
96
100 inline void setBasicBlock(const SVFBasicBlock* bb)
101 {
102 basicBlock = bb;
103 }
104
112
120
128
132 static inline void addInst2Labeled(const ICFGNode* cs, u32_t label)
133 {
134 inst2LabelMap.emplace(cs, label);
135 }
136
137 static inline void addVar2Labeled(const SVFVar* var, u32_t label)
138 {
139 var2LabelMap.emplace(var, label);
140 }
141
142public:
143
145 SVFStmt(SVFVar* s, SVFVar* d, GEdgeFlag k, bool real = true);
148
150
151 static inline bool classof(const SVFStmt*)
152 {
153 return true;
154 }
155 static inline bool classof(const GenericPAGEdgeTy* edge)
156 {
157 return edge->getEdgeKind() == SVFStmt::Addr ||
158 edge->getEdgeKind() == SVFStmt::Copy ||
159 edge->getEdgeKind() == SVFStmt::Store ||
160 edge->getEdgeKind() == SVFStmt::Load ||
161 edge->getEdgeKind() == SVFStmt::Call ||
162 edge->getEdgeKind() == SVFStmt::Ret ||
163 edge->getEdgeKind() == SVFStmt::Gep ||
164 edge->getEdgeKind() == SVFStmt::Phi ||
165 edge->getEdgeKind() == SVFStmt::Select ||
166 edge->getEdgeKind() == SVFStmt::Cmp ||
167 edge->getEdgeKind() == SVFStmt::BinaryOp ||
168 edge->getEdgeKind() == SVFStmt::UnaryOp ||
169 edge->getEdgeKind() == SVFStmt::Branch ||
170 edge->getEdgeKind() == SVFStmt::ThreadFork ||
171 edge->getEdgeKind() == SVFStmt::ThreadJoin;
172 }
174
176 inline EdgeID getEdgeID() const
177 {
178 return edgeId;
179 }
181 virtual bool isPTAEdge() const;
182
184
185
186 inline void setValue(const SVFVar* val)
187 {
188 value = val;
189 }
190 inline const SVFVar* getValue() const
191 {
192 return value;
193 }
194
195 inline void setBB(const SVFBasicBlock* bb)
196 {
197 basicBlock = bb;
198 }
199 inline const SVFBasicBlock* getBB() const
200 {
201 return basicBlock;
202 }
203 inline void setICFGNode(ICFGNode* node)
204 {
205 icfgNode = node;
206 }
207 inline ICFGNode* getICFGNode() const
208 {
209 return icfgNode;
210 }
212
216 const SVFVar* var)
217 {
219 if (it_inserted.second)
221 u64_t label = it_inserted.first->second;
222 return (label << EdgeKindMaskBits) | k;
223 }
224
228 const ICFGNode* cs)
229 {
231 if (it_inserted.second)
233 u64_t label = it_inserted.first->second;
234 return (label << EdgeKindMaskBits) | k;
235 }
236
240 const ICFGNode* store)
241 {
242 auto it_inserted = inst2LabelMap.emplace(store, storeEdgeLabelCounter);
243 if (it_inserted.second)
245 u64_t label = it_inserted.first->second;
246 return (label << EdgeKindMaskBits) | k;
247 }
248
249 virtual const std::string toString() const;
250
252
255 {
256 o << edge.toString();
257 return o;
258 }
260
265
266private:
274
275public:
276 static inline const Inst2LabelMap* getInst2LabelMap()
277 {
278 return &inst2LabelMap;
279 }
280
281 static inline const Var2LabelMap* getVar2LabelMap()
282 {
283 return &var2LabelMap;
284 }
285
286 static inline const u64_t* getCallEdgeLabelCounter()
287 {
288 return &callEdgeLabelCounter;
289 }
290
291 static inline const u64_t* getStoreEdgeLabelCounter()
292 {
293 return &storeEdgeLabelCounter;
294 }
295
296 static inline const u64_t* getMultiOpndLabelCounter()
297 {
298 return &multiOpndLabelCounter;
299 }
300
301};
302
303/*
304 Parent class of Addr, Copy, Store, Load, Call, Ret, NormalGep, VariantGep, ThreadFork, ThreadJoin
305 connecting RHS expression and LHS expression with an assignment (e.g., LHSExpr = RHSExpr)
306 Only one operand on the right hand side of an assignment
307*/
308class AssignStmt : public SVFStmt
309{
310 friend class GraphDBClient;
311
312private:
315 void operator=(const AssignStmt &);
320
321protected:
324
325public:
327
328 static inline bool classof(const AssignStmt*)
329 {
330 return true;
331 }
332 static inline bool classof(const SVFStmt* edge)
333 {
334 return edge->getEdgeKind() == SVFStmt::Addr ||
335 edge->getEdgeKind() == SVFStmt::Copy ||
336 edge->getEdgeKind() == SVFStmt::Store ||
337 edge->getEdgeKind() == SVFStmt::Load ||
338 edge->getEdgeKind() == SVFStmt::Call ||
339 edge->getEdgeKind() == SVFStmt::Ret ||
340 edge->getEdgeKind() == SVFStmt::Gep ||
341 edge->getEdgeKind() == SVFStmt::ThreadFork ||
342 edge->getEdgeKind() == SVFStmt::ThreadJoin;
343 }
344 static inline bool classof(const GenericPAGEdgeTy* edge)
345 {
346 return edge->getEdgeKind() == SVFStmt::Addr ||
347 edge->getEdgeKind() == SVFStmt::Copy ||
348 edge->getEdgeKind() == SVFStmt::Store ||
349 edge->getEdgeKind() == SVFStmt::Load ||
350 edge->getEdgeKind() == SVFStmt::Call ||
351 edge->getEdgeKind() == SVFStmt::Ret ||
352 edge->getEdgeKind() == SVFStmt::Gep ||
353 edge->getEdgeKind() == SVFStmt::ThreadFork ||
354 edge->getEdgeKind() == SVFStmt::ThreadJoin;
355 }
357
358 inline SVFVar* getRHSVar() const
359 {
360 return SVFStmt::getSrcNode();
361 }
362 inline SVFVar* getLHSVar() const
363 {
364 return SVFStmt::getDstNode();
365 }
366 inline NodeID getRHSVarID() const
367 {
368 return SVFStmt::getSrcID();
369 }
370 inline NodeID getLHSVarID() const
371 {
372 return SVFStmt::getDstID();
373 }
374
375 virtual const std::string toString() const = 0;
376};
377
381class AddrStmt: public AssignStmt
382{
383 friend class GraphDBClient;
384
385private:
387 void operator=(const AddrStmt&);
388
389 std::vector<SVFVar*> arrSize;
390
391public:
393
394 static inline bool classof(const AddrStmt*)
395 {
396 return true;
397 }
398 static inline bool classof(const SVFStmt* edge)
399 {
400 return edge->getEdgeKind() == SVFStmt::Addr;
401 }
402 static inline bool classof(const GenericPAGEdgeTy* edge)
403 {
404 return edge->getEdgeKind() == SVFStmt::Addr;
405 }
407
410
411 virtual const std::string toString() const override;
412
413 inline void addArrSize(SVFVar* size) //TODO:addSizeVar
414 {
415 arrSize.push_back(size);
416 }
417
419 inline const std::vector<SVFVar*>& getArrSize() const //TODO:getSizeVars
420 {
421 return arrSize;
422 }
423
424 virtual bool isPTAEdge() const override
425 {
426 return true;
427 }
428
429 const ValVar* getLHSVar() const;
430 const ObjVar* getRHSVar() const;
431 const ValVar* getDstNode() const;
432 const ObjVar* getSrcNode() const;
433};
434
438class CopyStmt: public AssignStmt
439{
440
441 friend class GraphDBClient;
442
443private:
445 void operator=(const CopyStmt&);
446public:
448 {
449 COPYVAL, // Value copies (default one)
450 ZEXT, // Zero extend integers
451 SEXT, // Sign extend integers
452 BITCAST, // Type cast
453 TRUNC, // Truncate integers
454 FPTRUNC, // Truncate floating point
455 FPTOUI, // floating point -> UInt
456 FPTOSI, // floating point -> SInt
457 UITOFP, // UInt -> floating point
458 SITOFP, // SInt -> floating point
459 INTTOPTR, // Integer -> Pointer
460 PTRTOINT // Pointer -> Integer
461 };
463
464 static inline bool classof(const CopyStmt*)
465 {
466 return true;
467 }
468 static inline bool classof(const SVFStmt* edge)
469 {
470 return edge->getEdgeKind() == SVFStmt::Copy;
471 }
472 static inline bool classof(const GenericPAGEdgeTy* edge)
473 {
474 return edge->getEdgeKind() == SVFStmt::Copy;
475 }
477
479 inline u32_t getCopyKind() const
480 {
481 return copyKind;
482 }
483
484 inline bool isBitCast() const
485 {
486 return copyKind == BITCAST;
487 }
488
489 inline bool isValueCopy() const
490 {
491 return copyKind == COPYVAL;
492 }
493
494 inline bool isInt2Ptr() const
495 {
496 return copyKind == INTTOPTR;
497 }
498
499 inline bool isPtr2Int() const
500 {
501 return copyKind == PTRTOINT;
502 }
503
504 inline bool isZext() const
505 {
506 return copyKind == ZEXT;
507 }
508
509 inline bool isSext() const
510 {
511 return copyKind == SEXT;
512 }
513
516
517 const ValVar* getRHSVar() const;
518 const ValVar* getLHSVar() const;
519 const ValVar* getSrcNode() const;
520 const ValVar* getDstNode() const;
521
522 virtual const std::string toString() const override;
523
524private:
526};
527
532{
533 friend class GraphDBClient;
534
535private:
537 void operator=(const StoreStmt&);
538
539public:
541
542 static inline bool classof(const StoreStmt*)
543 {
544 return true;
545 }
546 static inline bool classof(const SVFStmt* edge)
547 {
548 return edge->getEdgeKind() == SVFStmt::Store;
549 }
550 static inline bool classof(const GenericPAGEdgeTy* edge)
551 {
552 return edge->getEdgeKind() == SVFStmt::Store;
553 }
555
557 StoreStmt(SVFVar* s, SVFVar* d, const ICFGNode* st);
558
559 const ValVar* getRHSVar() const;
560 const ValVar* getLHSVar() const;
561 const ValVar* getSrcNode() const;
562 const ValVar* getDstNode() const;
563
564 virtual const std::string toString() const override;
565
566};
567
571class LoadStmt: public AssignStmt
572{
573 friend class GraphDBClient;
574
575private:
577 void operator=(const LoadStmt&);
578
579public:
581
582 static inline bool classof(const LoadStmt*)
583 {
584 return true;
585 }
586 static inline bool classof(const SVFStmt* edge)
587 {
588 return edge->getEdgeKind() == SVFStmt::Load;
589 }
590 static inline bool classof(const GenericPAGEdgeTy* edge)
591 {
592 return edge->getEdgeKind() == SVFStmt::Load;
593 }
595
598
599 const ValVar* getRHSVar() const;
600 const ValVar* getLHSVar() const;
601 const ValVar* getSrcNode() const;
602 const ValVar* getDstNode() const;
603
604 virtual const std::string toString() const override;
605};
606
610class GepStmt: public AssignStmt
611{
612 friend class GraphDBClient;
613
614
615private:
616 GepStmt(const GepStmt &);
617 void operator=(const GepStmt &);
618
621public:
623
624 static inline bool classof(const GepStmt*)
625 {
626 return true;
627 }
628 static inline bool classof(const SVFStmt* edge)
629 {
630 return edge->getEdgeKind() == SVFStmt::Gep;
631 }
632 static inline bool classof(const GenericPAGEdgeTy* edge)
633 {
634 return edge->getEdgeKind() == SVFStmt::Gep;
635 }
637
638 inline const AccessPath& getAccessPath() const
639 {
640 return ap;
641 }
647 inline bool isConstantOffset() const
648 {
650 }
651
661
664 {
666 }
669 {
670 assert(isVariantFieldGep()==false && "Can't retrieve the AccessPath if using a variable field index (pointer arithmetic) for struct field access ");
672 }
674 inline bool isVariantFieldGep() const
675 {
676 return variantField;
677 }
678
680 GepStmt(SVFVar* s, SVFVar* d, const AccessPath& ap, bool varfld = false)
682 {
683 }
684
685 const ValVar* getRHSVar() const;
686 const ValVar* getLHSVar() const;
687 const ValVar* getSrcNode() const;
688 const ValVar* getDstNode() const;
689
690 virtual const std::string toString() const;
691
692
693};
694
695
699class CallPE: public AssignStmt
700{
701 friend class GraphDBClient;
702
703private:
704 CallPE(const CallPE&);
705 void operator=(const CallPE&);
706
709
710public:
712
713 static inline bool classof(const CallPE*)
714 {
715 return true;
716 }
717 static inline bool classof(const SVFStmt* edge)
718 {
719 return edge->getEdgeKind() == SVFStmt::Call ||
720 edge->getEdgeKind() == SVFStmt::ThreadFork;
721 }
722 static inline bool classof(const GenericPAGEdgeTy* edge)
723 {
724 return edge->getEdgeKind() == SVFStmt::Call ||
725 edge->getEdgeKind() == SVFStmt::ThreadFork;
726 }
728
730 CallPE(SVFVar* s, SVFVar* d, const CallICFGNode* i,
732
734
735 inline const CallICFGNode* getCallInst() const
736 {
737 return call;
738 }
739 inline const CallICFGNode* getCallSite() const
740 {
741 return call;
742 }
744 {
745 return entry;
746 }
748
749 const ValVar* getRHSVar() const;
750 const ValVar* getLHSVar() const;
751 const ValVar* getSrcNode() const;
752 const ValVar* getDstNode() const;
753
754 virtual const std::string toString() const override;
755};
756
760class RetPE: public AssignStmt
761{
762 friend class GraphDBClient;
763
764private:
765 RetPE(const RetPE&);
766 void operator=(const RetPE&);
767
770
771public:
773
774 static inline bool classof(const RetPE*)
775 {
776 return true;
777 }
778 static inline bool classof(const SVFStmt* edge)
779 {
780 return edge->getEdgeKind() == SVFStmt::Ret ||
781 edge->getEdgeKind() == SVFStmt::ThreadJoin;
782 }
783 static inline bool classof(const GenericPAGEdgeTy* edge)
784 {
785 return edge->getEdgeKind() == SVFStmt::Ret ||
786 edge->getEdgeKind() == SVFStmt::ThreadJoin;
787 }
789
791 RetPE(SVFVar* s, SVFVar* d, const CallICFGNode* i, const FunExitICFGNode* e,
793
795
796 inline const CallICFGNode* getCallInst() const
797 {
798 return call;
799 }
800 inline const CallICFGNode* getCallSite() const
801 {
802 return call;
803 }
805 {
806 return exit;
807 }
809
810 const ValVar* getRHSVar() const;
811 const ValVar* getLHSVar() const;
812 const ValVar* getSrcNode() const;
813 const ValVar* getDstNode() const;
814
815 virtual const std::string toString() const override;
816
817};
818
819/*
820* Program statements with multiple operands including BinaryOPStmt, CmpStmt and PhiStmt
821*/
822class MultiOpndStmt : public SVFStmt
823{
824 friend class GraphDBClient;
825
826public:
827 typedef std::vector<ValVar*> OPVars;
828
829private:
837
838protected:
842
843public:
845
846 static inline bool classof(const MultiOpndStmt*)
847 {
848 return true;
849 }
850 static inline bool classof(const SVFStmt* node)
851 {
852 return node->getEdgeKind() == Phi || node->getEdgeKind() == Select ||
853 node->getEdgeKind() == BinaryOp || node->getEdgeKind() == Cmp;
854 }
855 static inline bool classof(const GenericPAGEdgeTy* node)
856 {
857 return node->getEdgeKind() == Phi || node->getEdgeKind() == Select ||
858 node->getEdgeKind() == BinaryOp || node->getEdgeKind() == Cmp;
859 }
861
863
864
865 inline const ValVar* getOpVar(u32_t pos) const
866 {
867 return opVars.at(pos);
868 }
870 const ValVar* getRes() const;
871
872 NodeID getOpVarID(u32_t pos) const;
873 NodeID getResID() const;
874
875 inline u32_t getOpVarNum() const
876 {
877 return opVars.size();
878 }
879 inline const OPVars& getOpndVars() const
880 {
881 return opVars;
882 }
883 inline OPVars::const_iterator opVarBegin() const
884 {
885 return opVars.begin();
886 }
887 inline OPVars::const_iterator opVerEnd() const
888 {
889 return opVars.end();
890 }
892};
893
899{
900 friend class GraphDBClient;
901public:
902 typedef std::vector<const ICFGNode*> OpICFGNodeVec;
903
904private:
905 PhiStmt(const PhiStmt&);
906 void operator=(const PhiStmt&);
907
909
910public:
912
913 static inline bool classof(const PhiStmt*)
914 {
915 return true;
916 }
917 static inline bool classof(const SVFStmt* edge)
918 {
919 return edge->getEdgeKind() == SVFStmt::Phi;
920 }
921 static inline bool classof(const MultiOpndStmt* edge)
922 {
923 return edge->getEdgeKind() == SVFStmt::Phi;
924 }
925 static inline bool classof(const GenericPAGEdgeTy* edge)
926 {
927 return edge->getEdgeKind() == SVFStmt::Phi;
928 }
930
932 PhiStmt(ValVar* res, const OPVars& opnds, const OpICFGNodeVec& icfgNodes)
933 : MultiOpndStmt(res, opnds, SVFStmt::Phi), opICFGNodes(icfgNodes)
934 {
935 assert(opnds.size() == icfgNodes.size() &&
936 "Numbers of operands and their ICFGNodes are not consistent?");
937 }
939 {
940 opVars.push_back(op);
941 opICFGNodes.push_back(inode);
942 assert(opVars.size() == opICFGNodes.size() &&
943 "Numbers of operands and their ICFGNodes are not consistent?");
944 }
945
947 {
948 assert(opVars.size() == icfgNodes.size() &&
949 "Numbers of operands and their ICFGNodes are not consistent?");
950 opICFGNodes = icfgNodes;
951 }
952
953 inline const OpICFGNodeVec* getOpICFGNodeVec() const
954 {
955 return &opICFGNodes;
956 }
957
959 inline const ICFGNode* getOpICFGNode(u32_t op_idx) const
960 {
961 return opICFGNodes.at(op_idx);
962 }
963
966 bool isFunctionRetPhi() const;
967
968 virtual const std::string toString() const override;
969
970};
971
976{
977 friend class GraphDBClient;
978private:
980 void operator=(const SelectStmt&);
981
983
984public:
986
987 static inline bool classof(const SelectStmt*)
988 {
989 return true;
990 }
991 static inline bool classof(const SVFStmt* edge)
992 {
993 return edge->getEdgeKind() == SVFStmt::Select;
994 }
995 static inline bool classof(const MultiOpndStmt* edge)
996 {
997 return edge->getEdgeKind() == SVFStmt::Select;
998 }
999 static inline bool classof(const GenericPAGEdgeTy* edge)
1000 {
1001 return edge->getEdgeKind() == SVFStmt::Select;
1002 }
1004
1006 SelectStmt(ValVar* res, const OPVars& opnds, const SVFVar* cond);
1007 virtual const std::string toString() const override;
1008
1009 inline const SVFVar* getCondition() const
1010 {
1011 return condition;
1012 }
1013 inline const ValVar* getTrueValue() const
1014 {
1015 return getOpVar(0);
1016 }
1017 inline const ValVar* getFalseValue() const
1018 {
1019 return getOpVar(1);
1020 }
1021
1022};
1023
1028{
1029 friend class GraphDBClient;
1030private:
1032 void operator=(const CmpStmt&);
1033
1035
1036public:
1074
1076
1077 static inline bool classof(const CmpStmt*)
1078 {
1079 return true;
1080 }
1081 static inline bool classof(const SVFStmt* edge)
1082 {
1083 return edge->getEdgeKind() == SVFStmt::Cmp;
1084 }
1085 static inline bool classof(const MultiOpndStmt* edge)
1086 {
1087 return edge->getEdgeKind() == SVFStmt::Cmp;
1088 }
1089 static inline bool classof(const GenericPAGEdgeTy* edge)
1090 {
1091 return edge->getEdgeKind() == SVFStmt::Cmp;
1092 }
1094
1096 CmpStmt(ValVar* res, const OPVars& opnds, u32_t pre);
1097
1099 {
1100 return predicate;
1101 }
1102
1103 virtual const std::string toString() const override;
1104
1105};
1106
1111{
1112 friend class GraphDBClient;
1113private:
1117
1118public:
1120 enum OpCode : unsigned
1121 {
1122 Add = 13, // Sum of integers
1123 FAdd = 14, // Sum of floats
1124 Sub = 15, // Subtraction of integers
1125 FSub = 16, // Subtraction of floats
1126 Mul = 17, // Product of integers.
1127 FMul = 18, // Product of floats.
1128 UDiv = 19, // Unsigned division.
1129 SDiv = 20, // Signed division.
1130 FDiv = 21, // Float division.
1131 URem = 22, // Unsigned remainder
1132 SRem = 23, // Signed remainder
1133 FRem = 24, // Float remainder
1134 Shl = 25, // Shift left (logical)
1135 LShr = 26, // Shift right (logical)
1136 AShr = 27, // Shift right (arithmetic)
1137 And = 28, // Logical and
1138 Or = 29, // Logical or
1139 Xor = 30 // Logical xor
1141
1143
1144 static inline bool classof(const BinaryOPStmt*)
1145 {
1146 return true;
1147 }
1148 static inline bool classof(const SVFStmt* edge)
1149 {
1150 return edge->getEdgeKind() == SVFStmt::BinaryOp;
1151 }
1152 static inline bool classof(const MultiOpndStmt* edge)
1153 {
1154 return edge->getEdgeKind() == SVFStmt::BinaryOp;
1155 }
1156 static inline bool classof(const GenericPAGEdgeTy* edge)
1157 {
1158 return edge->getEdgeKind() == SVFStmt::BinaryOp;
1159 }
1161
1163 BinaryOPStmt(ValVar* res, const OPVars& opnds, u32_t oc);
1164
1166 {
1167 return opcode;
1168 }
1169
1170 virtual const std::string toString() const override;
1171
1172};
1173
1178{
1179 friend class GraphDBClient;
1180
1181private:
1183 void operator=(const UnaryOPStmt&);
1188
1190
1191public:
1193 enum OpCode : unsigned
1194 {
1195 FNeg = 12
1197
1199
1200 static inline bool classof(const UnaryOPStmt*)
1201 {
1202 return true;
1203 }
1204 static inline bool classof(const SVFStmt* edge)
1205 {
1206 return edge->getEdgeKind() == SVFStmt::UnaryOp;
1207 }
1208 static inline bool classof(const GenericPAGEdgeTy* edge)
1209 {
1210 return edge->getEdgeKind() == SVFStmt::UnaryOp;
1211 }
1213
1216
1218 {
1219 return opcode;
1220 }
1221 const ValVar* getOpVar() const;
1222 const ValVar* getRes() const;
1223 NodeID getOpVarID() const;
1224 NodeID getResID() const;
1225
1226 virtual const std::string toString() const override;
1227
1228};
1229
1233class BranchStmt: public SVFStmt
1234{
1235 friend class GraphDBClient;
1236
1237public:
1238 typedef std::vector<std::pair<const ICFGNode*, s32_t>> SuccAndCondPairVec;
1239
1240private:
1242 void operator=(const BranchStmt&);
1247
1249 const ValVar* cond;
1251
1252public:
1254
1255 static inline bool classof(const BranchStmt*)
1256 {
1257 return true;
1258 }
1259 static inline bool classof(const SVFStmt* edge)
1260 {
1261 return edge->getEdgeKind() == SVFStmt::Branch;
1262 }
1263 static inline bool classof(const GenericPAGEdgeTy* edge)
1264 {
1265 return edge->getEdgeKind() == SVFStmt::Branch;
1266 }
1268
1271
1273 bool isUnconditional() const;
1275 bool isConditional() const;
1277 const ValVar* getCondition() const;
1278 const ValVar* getBranchInst() const
1279 {
1280 return brInst;
1281 }
1282
1286
1290
1294 {
1295 return successors.size();
1296 }
1298 {
1299 return successors;
1300 }
1302 {
1303 return successors.at(i).first;
1304 }
1306 {
1307 return successors.at(i).second;
1308 }
1310 virtual const std::string toString() const override;
1311
1312};
1313
1317class TDForkPE: public CallPE
1318{
1319 friend class GraphDBClient;
1320
1321private:
1323 void operator=(const TDForkPE&);
1324
1325public:
1327
1328 static inline bool classof(const TDForkPE*)
1329 {
1330 return true;
1331 }
1332 static inline bool classof(const SVFStmt* edge)
1333 {
1334 return edge->getEdgeKind() == SVFStmt::ThreadFork;
1335 }
1336 static inline bool classof(const GenericPAGEdgeTy* edge)
1337 {
1338 return edge->getEdgeKind() == SVFStmt::ThreadFork;
1339 }
1341
1344 const FunEntryICFGNode* entry)
1346 {
1347 }
1348
1349 const ValVar* getRHSVar() const;
1350 const ValVar* getLHSVar() const;
1351 const ValVar* getSrcNode() const;
1352 const ValVar* getDstNode() const;
1353
1354 virtual const std::string toString() const;
1355
1356};
1357
1361class TDJoinPE: public RetPE
1362{
1363 friend class GraphDBClient;
1364
1365private:
1367 void operator=(const TDJoinPE&);
1368
1369public:
1371
1372 static inline bool classof(const TDJoinPE*)
1373 {
1374 return true;
1375 }
1376 static inline bool classof(const SVFStmt* edge)
1377 {
1378 return edge->getEdgeKind() == SVFStmt::ThreadJoin;
1379 }
1380 static inline bool classof(const GenericPAGEdgeTy* edge)
1381 {
1382 return edge->getEdgeKind() == SVFStmt::ThreadJoin;
1383 }
1385
1388 const FunExitICFGNode* e)
1389 : RetPE(s, d, i, e, SVFStmt::ThreadJoin)
1390 {
1391 }
1392
1393 const ValVar* getRHSVar() const;
1394 const ValVar* getLHSVar() const;
1395 const ValVar* getSrcNode() const;
1396 const ValVar* getDstNode() const;
1397
1398 virtual const std::string toString() const;
1399
1400};
1401
1402} // End namespace SVF
1403
1404#endif /* INCLUDE_SVFIR_SVFSTATEMENT_H_ */
std::vector< IdxOperandPair > IdxOperandPairs
Definition AccessPath.h:63
bool isConstantOffset() const
Return TRUE if this is a constant location set.
APOffset computeConstantByteOffset() const
APOffset getConstantStructFldIdx() const
Get methods.
Definition AccessPath.h:98
const IdxOperandPairs & getIdxOperandPairVec() const
Definition AccessPath.h:106
APOffset computeConstantOffset() const
For example,.
const ObjVar * getSrcNode() const
void operator=(const AddrStmt &)
place holder
AddrStmt(const AddrStmt &)
place holder
void addArrSize(SVFVar *size)
get array size of the allocated memory
static bool classof(const AddrStmt *)
Methods for support type inquiry through isa, cast, and dyn_cast:
const ObjVar * getRHSVar() const
AddrStmt(SVFVar *s, SVFVar *d)
constructor
const ValVar * getLHSVar() const
static bool classof(const GenericPAGEdgeTy *edge)
const ValVar * getDstNode() const
friend class GraphDBClient
virtual bool isPTAEdge() const override
Whether src and dst nodes are both of pointer type.
virtual const std::string toString() const override
std::vector< SVFVar * > arrSize
Array size of the allocated memory.
const std::vector< SVFVar * > & getArrSize() const
static bool classof(const SVFStmt *edge)
SVFVar * getSrcNode()
not allowed, use getRHSVar() instead
SVFVar * getDstNode()
not allowed, use getLHSVar() instead
AssignStmt(const AssignStmt &)
place holder
NodeID getRHSVarID() const
static bool classof(const AssignStmt *)
Methods for support type inquiry through isa, cast, and dyn_cast:
static bool classof(const GenericPAGEdgeTy *edge)
NodeID getLHSVarID() const
NodeID getDstID()
not allowed, use getLHSVarID() instead
NodeID getSrcID()
not allowed, use getRHSVarID() instead
SVFVar * getLHSVar() const
friend class GraphDBClient
virtual const std::string toString() const =0
AssignStmt()
place holder
SVFVar * getRHSVar() const
void operator=(const AssignStmt &)
place holder
static bool classof(const SVFStmt *edge)
AssignStmt(SVFVar *s, SVFVar *d, GEdgeFlag k)
constructor
virtual const std::string toString() const override
OpCode
OpCode for BinaryOPStmt, enum value is same to llvm BinaryOperator (llvm/IR/Instruction....
static bool classof(const MultiOpndStmt *edge)
void operator=(const BinaryOPStmt &)
place holder
BinaryOPStmt(const BinaryOPStmt &)
place holder
friend class GraphDBClient
static bool classof(const BinaryOPStmt *)
Methods for support type inquiry through isa, cast, and dyn_cast:
static bool classof(const SVFStmt *edge)
static bool classof(const GenericPAGEdgeTy *edge)
u32_t getOpcode() const
u32_t getNumSuccessors() const
bool isUnconditional() const
The branch is unconditional if cond is a null value.
const ICFGNode * getSuccessor(u32_t i) const
const ValVar * getCondition() const
Return the condition.
SuccAndCondPairVec successors
const ValVar * getBranchInst() const
void operator=(const BranchStmt &)
place holder
static bool classof(const SVFStmt *edge)
std::vector< std::pair< const ICFGNode *, s32_t > > SuccAndCondPairVec
BranchStmt(const BranchStmt &)
place holder
bool isConditional() const
The branch is conditional if cond is not a null value.
static bool classof(const BranchStmt *)
Methods for support type inquiry through isa, cast, and dyn_cast:
s64_t getSuccessorCondValue(u32_t i) const
SVFVar * getDstNode()
place holder, not allowed
NodeID getSrcID()
place holder, use getOpVarID(pos) instead
const ValVar * cond
friend class GraphDBClient
SVFVar * getSrcNode()
place holder, not allowed
const SuccAndCondPairVec & getSuccessors() const
NodeID getDstID()
place holder, use getResID() instead
static bool classof(const GenericPAGEdgeTy *edge)
const ValVar * brInst
virtual const std::string toString() const override
static bool classof(const GenericPAGEdgeTy *edge)
static bool classof(const SVFStmt *edge)
CallPE(const CallPE &)
place holder
const CallICFGNode * getCallSite() const
const FunEntryICFGNode * getFunEntryICFGNode() const
static bool classof(const CallPE *)
the function exit statement calling to
const FunEntryICFGNode * entry
the callsite statement calling from
const ValVar * getDstNode() const
void operator=(const CallPE &)
place holder
friend class GraphDBClient
const CallICFGNode * call
const ValVar * getSrcNode() const
const CallICFGNode * getCallInst() const
Get method for the call instruction.
const ValVar * getLHSVar() const
virtual const std::string toString() const override
const ValVar * getRHSVar() const
static bool classof(const SVFStmt *edge)
virtual const std::string toString() const override
static bool classof(const MultiOpndStmt *edge)
void operator=(const CmpStmt &)
place holder
u32_t getPredicate() const
friend class GraphDBClient
CmpStmt(const CmpStmt &)
place holder
Predicate
OpCode for CmpStmt, enum value is same to llvm CmpInst.
@ ICMP_SGT
signed greater than
@ FCMP_UEQ
1 0 0 1 True if unordered or equal
@ FCMP_ONE
0 1 1 0 True if ordered and operands are unequal
@ ICMP_UGE
unsigned greater or equal
@ FCMP_UGT
1 0 1 0 True if unordered or greater than
@ ICMP_ULE
unsigned less or equal
@ FCMP_OGE
0 0 1 1 True if ordered and greater than or equal
@ FCMP_OLT
0 1 0 0 True if ordered and less than
@ FCMP_OGT
0 0 1 0 True if ordered and greater than
@ ICMP_NE
not equal
@ FCMP_TRUE
1 1 1 1 Always true (always folded)
@ ICMP_ULT
unsigned less than
@ FCMP_ULE
1 1 0 1 True if unordered, less than, or equal
@ ICMP_SLT
signed less than
@ ICMP_UGT
unsigned greater than
@ FCMP_OEQ
0 0 0 1 True if ordered and equal
@ FCMP_ORD
0 1 1 1 True if ordered (no nans)
@ FCMP_OLE
0 1 0 1 True if ordered and less than or equal
@ FCMP_FALSE
0 0 0 0 Always false (always folded)
@ FCMP_ULT
1 1 0 0 True if unordered or less than
@ FCMP_UNO
1 0 0 0 True if unordered: isnan(X) | isnan(Y)
@ FCMP_UGE
1 0 1 1 True if unordered, greater than, or equal
@ ICMP_SGE
signed greater or equal
@ FCMP_UNE
1 1 1 0 True if unordered or not equal
@ ICMP_SLE
signed less or equal
static bool classof(const CmpStmt *)
Methods for support type inquiry through isa, cast, and dyn_cast:
static bool classof(const GenericPAGEdgeTy *edge)
static bool classof(const GenericPAGEdgeTy *edge)
const ValVar * getRHSVar() const
const ValVar * getDstNode() const
const ValVar * getSrcNode() const
static bool classof(const CopyStmt *)
Methods for support type inquiry through isa, cast, and dyn_cast:
CopyStmt(SVFVar *s, SVFVar *d, CopyKind k)
constructor
u32_t getCopyKind() const
Return the kind of the copy statement.
bool isZext() const
bool isPtr2Int() const
static bool classof(const SVFStmt *edge)
bool isBitCast() const
void operator=(const CopyStmt &)
place holder
CopyStmt(const CopyStmt &)
place holder
friend class GraphDBClient
const ValVar * getLHSVar() const
bool isValueCopy() const
virtual const std::string toString() const override
bool isInt2Ptr() const
bool isSext() const
NodeType * getSrcNode() const
NodeType * getDstNode() const
GEdgeKind getEdgeKind() const
NodeID getDstID() const
NodeID getSrcID() const
get methods of the components
static constexpr unsigned char EdgeKindMaskBits
We use the lower 8 bits to denote edge kind.
OrderedSet< EdgeType *, typename EdgeType::equalGEdge > GEdgeSetTy
Edge kind.
bool isVariantFieldGep() const
Gep statement with a variant field index (pointer arithmetic) for struct field access.
const ValVar * getSrcNode() const
APOffset accumulateConstantOffset() const
Return accumulated constant offset (when accessing array or struct) if this offset is a constant.
APOffset accumulateConstantByteOffset() const
const AccessPath::IdxOperandPairs getOffsetVarAndGepTypePairVec() const
static bool classof(const GepStmt *)
Methods for support type inquiry through isa, cast, and dyn_cast:
const ValVar * getRHSVar() const
APOffset getConstantStructFldIdx() const
Field index of the gep statement if it access the field of a struct.
GepStmt(const GepStmt &)
place holder
GepStmt(SVFVar *s, SVFVar *d, const AccessPath &ap, bool varfld=false)
constructor
const ValVar * getDstNode() const
static bool classof(const SVFStmt *edge)
const AccessPath & getAccessPath() const
const ValVar * getLHSVar() const
void operator=(const GepStmt &)
place holder
friend class GraphDBClient
bool isConstantOffset() const
Return TRUE if this is a constant location set.
static bool classof(const GenericPAGEdgeTy *edge)
virtual const std::string toString() const
AccessPath ap
Access path of the GEP edge.
bool variantField
Gep statement with a variant field index (pointer arithmetic) for struct field access (e....
static bool classof(const LoadStmt *)
Methods for support type inquiry through isa, cast, and dyn_cast:
const ValVar * getLHSVar() const
const ValVar * getDstNode() const
LoadStmt(const LoadStmt &)
place holder
virtual const std::string toString() const override
const ValVar * getRHSVar() const
LoadStmt(SVFVar *s, SVFVar *d)
constructor
const ValVar * getSrcNode() const
friend class GraphDBClient
static bool classof(const GenericPAGEdgeTy *edge)
static bool classof(const SVFStmt *edge)
void operator=(const LoadStmt &)
place holder
const OPVars & getOpndVars() const
NodeID getDstID()
not allowed, use getResID() instead
const ValVar * getRes() const
Result SVFVar.
std::vector< ValVar * > OPVars
NodeID getOpVarID(u32_t pos) const
static bool classof(const SVFStmt *node)
MultiOpndStmt()
place holder
MultiOpndStmt(const MultiOpndStmt &)
place holder
NodeID getResID() const
SVFVar * getSrcNode()
not allowed, use getOpVar(idx) instead
static bool classof(const MultiOpndStmt *)
Methods for support type inquiry through isa, cast, and dyn_cast:
friend class GraphDBClient
OPVars::const_iterator opVarBegin() const
SVFVar * getDstNode()
not allowed, use getRes() instead
NodeID getSrcID()
not allowed, use getOpVarID(idx) instead
static bool classof(const GenericPAGEdgeTy *node)
OPVars::const_iterator opVerEnd() const
const ValVar * getOpVar(u32_t pos) const
Operand SVFVars.
u32_t getOpVarNum() const
void operator=(const MultiOpndStmt &)
place holder
virtual const std::string toString() const override
const ICFGNode * getOpICFGNode(u32_t op_idx) const
Return the corresponding ICFGNode of this operand.
void operator=(const PhiStmt &)
place holder
PhiStmt(ValVar *res, const OPVars &opnds, const OpICFGNodeVec &icfgNodes)
constructor
std::vector< const ICFGNode * > OpICFGNodeVec
OpICFGNodeVec opICFGNodes
PhiStmt(const PhiStmt &)
place holder
void addOpVar(ValVar *op, const ICFGNode *inode)
const OpICFGNodeVec * getOpICFGNodeVec() const
bool isFunctionRetPhi() const
static bool classof(const GenericPAGEdgeTy *edge)
friend class GraphDBClient
static bool classof(const PhiStmt *)
Methods for support type inquiry through isa, cast, and dyn_cast:
static bool classof(const SVFStmt *edge)
void setOpICFGNodeVec(OpICFGNodeVec &icfgNodes)
static bool classof(const MultiOpndStmt *edge)
RetPE(const RetPE &)
place holder
const CallICFGNode * getCallSite() const
static bool classof(const GenericPAGEdgeTy *edge)
static bool classof(const RetPE *)
the function exit statement returned from
const CallICFGNode * getCallInst() const
Get method for call instruction at caller.
virtual const std::string toString() const override
const FunExitICFGNode * exit
the callsite statement returning to
const FunExitICFGNode * getFunExitICFGNode() const
const ValVar * getDstNode() const
static bool classof(const SVFStmt *edge)
const CallICFGNode * call
const ValVar * getSrcNode() const
friend class GraphDBClient
void operator=(const RetPE &)
place holder
const ValVar * getRHSVar() const
const ValVar * getLHSVar() const
static bool classof(const GenericPAGEdgeTy *edge)
static void addInst2Labeled(const ICFGNode *cs, u32_t label)
ICFGNode * getICFGNode() const
virtual bool isPTAEdge() const
Whether src and dst nodes are both of pointer type.
void setBasicBlock(const SVFBasicBlock *bb)
void setBB(const SVFBasicBlock *bb)
friend OutStream & operator<<(OutStream &o, const SVFStmt &edge)
Overloading operator << for dumping SVFVar value.
void setMultiOpndLabelCounter(u64_t counter)
const SVFVar * getValue() const
void setValue(const SVFVar *val)
Get/set methods for llvm instruction.
Map< EdgeID, SVFStmtSetTy > PAGEdgeToSetMapTy
static u64_t callEdgeLabelCounter
Call site Instruction counter.
static Var2LabelMap var2LabelMap
Second operand of MultiOpndStmt to label map.
SVFStmtSetTy PAGEdgeSetTy
void setCallEdgeLabelCounter(u64_t counter)
static GEdgeFlag makeEdgeFlagWithAddionalOpnd(GEdgeKind k, const SVFVar *var)
const SVFBasicBlock * getBB() const
static GEdgeFlag makeEdgeFlagWithCallInst(GEdgeKind k, const ICFGNode *cs)
SVFStmt(GEdgeFlag k)
Private constructor for reading SVFIR from file without side-effect.
ICFGNode * icfgNode
ICFGNode.
static u64_t storeEdgeLabelCounter
Store Instruction counter.
EdgeID edgeId
Edge ID.
static const Inst2LabelMap * getInst2LabelMap()
Map< const ICFGNode *, u32_t > Inst2LabelMap
void setStoreEdgeLabelCounter(u64_t counter)
static const u64_t * getStoreEdgeLabelCounter()
const SVFBasicBlock * basicBlock
LLVM BasicBlock.
GenericNode< SVFVar, SVFStmt >::GEdgeSetTy SVFStmtSetTy
PAGEdgeToSetMapTy KindToSVFStmtMapTy
static u64_t multiOpndLabelCounter
MultiOpndStmt counter.
static const u64_t * getCallEdgeLabelCounter()
~SVFStmt()
Destructor.
friend class GraphDBClient
static Inst2LabelMap inst2LabelMap
Call site Instruction to label map.
static bool classof(const SVFStmt *)
ClassOf.
static const u64_t * getMultiOpndLabelCounter()
virtual const std::string toString() const
Map< const SVFVar *, u32_t > Var2LabelMap
static GEdgeFlag makeEdgeFlagWithStoreInst(GEdgeKind k, const ICFGNode *store)
const SVFVar * value
LLVM value.
void setICFGNode(ICFGNode *node)
static void addVar2Labeled(const SVFVar *var, u32_t label)
static const Var2LabelMap * getVar2LabelMap()
EdgeID getEdgeID() const
Return Edge ID.
static bool classof(const MultiOpndStmt *edge)
const SVFVar * getCondition() const
const SVFVar * condition
static bool classof(const SVFStmt *edge)
virtual const std::string toString() const override
static bool classof(const SelectStmt *)
Methods for support type inquiry through isa, cast, and dyn_cast:
const ValVar * getTrueValue() const
static bool classof(const GenericPAGEdgeTy *edge)
const ValVar * getFalseValue() const
friend class GraphDBClient
SelectStmt(const SelectStmt &)
place holder
void operator=(const SelectStmt &)
place holder
const ValVar * getDstNode() const
StoreStmt(const StoreStmt &)
place holder
const ValVar * getRHSVar() const
const ValVar * getLHSVar() const
static bool classof(const SVFStmt *edge)
virtual const std::string toString() const override
const ValVar * getSrcNode() const
friend class GraphDBClient
static bool classof(const GenericPAGEdgeTy *edge)
void operator=(const StoreStmt &)
place holder
static bool classof(const StoreStmt *)
Methods for support type inquiry through isa, cast, and dyn_cast:
void operator=(const TDForkPE &)
place holder
const ValVar * getDstNode() const
static bool classof(const SVFStmt *edge)
static bool classof(const TDForkPE *)
Methods for support type inquiry through isa, cast, and dyn_cast:
const ValVar * getRHSVar() const
static bool classof(const GenericPAGEdgeTy *edge)
virtual const std::string toString() const
const ValVar * getSrcNode() const
friend class GraphDBClient
const ValVar * getLHSVar() const
TDForkPE(const TDForkPE &)
place holder
TDForkPE(SVFVar *s, SVFVar *d, const CallICFGNode *i, const FunEntryICFGNode *entry)
constructor
const ValVar * getRHSVar() const
static bool classof(const SVFStmt *edge)
const ValVar * getLHSVar() const
static bool classof(const GenericPAGEdgeTy *edge)
const ValVar * getDstNode() const
void operator=(const TDJoinPE &)
place holder
TDJoinPE(const TDJoinPE &)
place holder
friend class GraphDBClient
virtual const std::string toString() const
static bool classof(const TDJoinPE *)
Methods for support type inquiry through isa, cast, and dyn_cast:
TDJoinPE(SVFVar *s, SVFVar *d, const CallICFGNode *i, const FunExitICFGNode *e)
Constructor.
const ValVar * getSrcNode() const
virtual const std::string toString() const override
static bool classof(const SVFStmt *edge)
NodeID getSrcID()
place holder, use getOpVarID(pos) instead
const ValVar * getRes() const
void operator=(const UnaryOPStmt &)
place holder
SVFVar * getSrcNode()
place holder, use getOpVar() instead
const ValVar * getOpVar() const
NodeID getOpVarID() const
SVFVar * getDstNode()
place holder, use getRes() instead
UnaryOPStmt(const UnaryOPStmt &)
place holder
friend class GraphDBClient
NodeID getDstID()
place holder, use getResID() instead
static bool classof(const UnaryOPStmt *)
Methods for support type inquiry through isa, cast, and dyn_cast:
OpCode
OpCode for UnaryOPStmt, enum value is same to llvm::UnaryOperator.
static bool classof(const GenericPAGEdgeTy *edge)
NodeID getResID() const
u32_t getOpcode() const
for isBitcode
Definition BasicTypes.h:70
unsigned long long u64_t
Definition GeneralType.h:49
u32_t NodeID
Definition GeneralType.h:56
s64_t APOffset
Definition GeneralType.h:60
std::ostream OutStream
Definition GeneralType.h:46
llvm::IRBuilder IRBuilder
Definition BasicTypes.h:76
GenericEdge< SVFVar > GenericPAGEdgeTy
unsigned u32_t
Definition GeneralType.h:47
signed long long s64_t
Definition GeneralType.h:50
u32_t EdgeID
Definition GeneralType.h:57