Static Value-Flow Analysis
Loading...
Searching...
No Matches
SymbolTableBuilder.cpp
Go to the documentation of this file.
1//===- SymbolTableBuilder.cpp -- Symbol Table builder---------------------//
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 * SymbolTableBuilder.cpp
25 *
26 * Created on: Apr 28, 2014
27 * Author: Yulei Sui
28 */
29
30#include <memory>
31
32#include "SVF-LLVM/BasicTypes.h"
33#include "SVF-LLVM/CppUtil.h"
34#include "SVF-LLVM/GEPTypeBridgeIterator.h" // include bridge_gep_iterator
35#include "SVF-LLVM/LLVMUtil.h"
38#include "Util/Options.h"
39#include "Util/SVFUtil.h"
41
42using namespace SVF;
43using namespace SVFUtil;
44using namespace LLVMUtil;
45
60
75
76
81{
83
84 // Pointer #0 always represents the null pointer.
85 assert(svfir->totalSymNum++ == IRGraph::NullPtr && "Something changed!");
86
87 // Pointer #1 always represents the pointer points-to black hole.
88 assert(svfir->totalSymNum++ == IRGraph::BlkPtr && "Something changed!");
89
90 // Object #2 is black hole the object that may point to any object
91 assert(svfir->totalSymNum++ == IRGraph::BlackHole && "Something changed!");
93
94 // Object #3 always represents the unique constant of a program (merging all constants if Options::ModelConsts is disabled)
95 assert(svfir->totalSymNum++ == IRGraph::ConstantObj && "Something changed!");
97
99 {
100 // Add symbols for all the globals .
101 for (const GlobalVariable& gv : M.globals())
102 {
103 collectSym(&gv);
104 }
105
106 // Add symbols for all the global aliases
107 for (const GlobalAlias& ga : M.aliases())
108 {
109 collectSym(&ga);
110 collectSym(ga.getAliasee());
111 }
112
113 // Add symbols for all of the functions and the instructions in them.
114 for (const Function& fun : M.functions())
115 {
116 collectSym(&fun);
117 collectRet(&fun);
118 if (fun.getFunctionType()->isVarArg())
119 collectVararg(&fun);
120
121 // Add symbols for all formal parameters.
122 for (const Argument& arg : fun.args())
123 {
124 collectSym(&arg);
125 }
126
127 // collect and create symbols inside the function body
128 for (const Instruction& inst : instructions(fun))
129 {
130 collectSym(&inst);
131
132 // initialization for some special instructions
133 //{@
134 if (const StoreInst* st = SVFUtil::dyn_cast<StoreInst>(&inst))
135 {
136 collectSym(st->getPointerOperand());
137 collectSym(st->getValueOperand());
138 }
139 else if (const LoadInst* ld =
140 SVFUtil::dyn_cast<LoadInst>(&inst))
141 {
142 collectSym(ld->getPointerOperand());
143 }
144 else if (const AllocaInst* alloc =
145 SVFUtil::dyn_cast<AllocaInst>(&inst))
146 {
147 collectSym(alloc->getArraySize());
148 }
149 else if (const PHINode* phi = SVFUtil::dyn_cast<PHINode>(&inst))
150 {
151 for (u32_t i = 0; i < phi->getNumIncomingValues(); ++i)
152 {
153 collectSym(phi->getIncomingValue(i));
154 }
155 }
156 else if (const GetElementPtrInst* gep =
157 SVFUtil::dyn_cast<GetElementPtrInst>(&inst))
158 {
159 collectSym(gep->getPointerOperand());
160 for (u32_t i = 0; i < gep->getNumOperands(); ++i)
161 {
162 collectSym(gep->getOperand(i));
163 }
164 }
165 else if (const SelectInst* sel =
166 SVFUtil::dyn_cast<SelectInst>(&inst))
167 {
168 collectSym(sel->getTrueValue());
169 collectSym(sel->getFalseValue());
170 collectSym(sel->getCondition());
171 }
172 else if (const BinaryOperator* binary =
173 SVFUtil::dyn_cast<BinaryOperator>(&inst))
174 {
175 for (u32_t i = 0; i < binary->getNumOperands(); i++)
176 collectSym(binary->getOperand(i));
177 }
178 else if (const UnaryOperator* unary =
179 SVFUtil::dyn_cast<UnaryOperator>(&inst))
180 {
181 for (u32_t i = 0; i < unary->getNumOperands(); i++)
182 collectSym(unary->getOperand(i));
183 }
184 else if (const CmpInst* cmp = SVFUtil::dyn_cast<CmpInst>(&inst))
185 {
186 for (u32_t i = 0; i < cmp->getNumOperands(); i++)
187 collectSym(cmp->getOperand(i));
188 }
189 else if (const CastInst* cast =
190 SVFUtil::dyn_cast<CastInst>(&inst))
191 {
192 collectSym(cast->getOperand(0));
193 }
194 else if (const ReturnInst* ret =
195 SVFUtil::dyn_cast<ReturnInst>(&inst))
196 {
197 if (ret->getReturnValue())
198 collectSym(ret->getReturnValue());
199 }
200 else if (const BranchInst* br =
201 SVFUtil::dyn_cast<BranchInst>(&inst))
202 {
203 Value* opnd = br->isConditional() ? br->getCondition() : br->getOperand(0);
205 }
206 else if (const SwitchInst* sw =
207 SVFUtil::dyn_cast<SwitchInst>(&inst))
208 {
209 collectSym(sw->getCondition());
210 }
211 else if (const FreezeInst* fz = SVFUtil::dyn_cast<FreezeInst>(&inst))
212 {
213
214 for (u32_t i = 0; i < fz->getNumOperands(); i++)
215 {
216 Value* opnd = inst.getOperand(i);
218 }
219 }
220 else if (isNonInstricCallSite(&inst))
221 {
222
223 const CallBase* cs = LLVMUtil::getLLVMCallSite(&inst);
224 for (u32_t i = 0; i < cs->arg_size(); i++)
225 {
226 collectSym(cs->getArgOperand(i));
227 }
228 // Calls to inline asm need to be added as well because the
229 // callee isn't referenced anywhere else.
230 const Value* Callee = cs->getCalledOperand();
232
233 // TODO handle inlineAsm
236 {
238 }
239 }
241 }
242 }
243 }
244
247 {
249 }
250}
251
253{
254 Type *valType = val->getType();
256 if(isGepConstantExpr(val) || SVFUtil::isa<GetElementPtrInst>(val))
257 {
259 gi = bridge_gep_begin(SVFUtil::cast<User>(val)),
260 ge = bridge_gep_end(SVFUtil::cast<User>(val));
261 gi != ge; ++gi)
262 {
263 const Type* gepTy = *gi;
265 }
266 }
267}
268
273{
274
275 //TODO: filter the non-pointer type // if (!SVFUtil::isa<PointerType>(val->getType())) return;
276
278 outs()
279 << "collect sym from ##"
280 << llvmModuleSet()->getSVFValue(val)->toString()
281 << " \n");
282 //TODO handle constant expression value here??
283 handleCE(val);
284
285 // create a value sym
287
290
291 // create an object If it is a heap, stack, global, function.
292 if (isObject(val))
293 {
295 }
296}
297
302{
303 // collect and record special sym here
305 {
306 return;
307 }
308 LLVMModuleSet::ValueToIDMapTy::iterator iter = llvmModuleSet()->valSymMap.find(val);
309 if (iter == llvmModuleSet()->valSymMap.end())
310 {
311 // create val sym and sym type
313 llvmModuleSet()->valSymMap.insert(std::make_pair(val, id));
315 outs() << "create a new value sym " << id << "\n");
317 if (const GlobalVariable* globalVar = SVFUtil::dyn_cast<GlobalVariable>(val))
319 }
320
323}
324
329{
331 LLVMModuleSet::ValueToIDMapTy::iterator iter = llvmModuleSet()->objSymMap.find(val);
332 if (iter == llvmModuleSet()->objSymMap.end())
333 {
334 // if the object pointed by the pointer is a constant data (e.g., i32 0) or a global constant object (e.g. string)
335 // then we treat them as one ConstantObj
337 {
338 llvmModuleSet()->objSymMap.insert(std::make_pair(val, svfir->constantSymID()));
339 }
340 // otherwise, we will create an object for each abstract memory location
341 else
342 {
343 // create obj sym and sym type
345 llvmModuleSet()->objSymMap.insert(std::make_pair(val, id));
347 outs() << "create a new obj sym " << id << "\n");
348
349 // create a memory object
351 assert(svfir->objTypeInfoMap.find(id) == svfir->objTypeInfoMap.end());
352 svfir->objTypeInfoMap[id] = ti;
353 }
354 }
355}
356
361{
362
363 LLVMModuleSet::FunToIDMapTy::iterator iter =
365 if (iter == llvmModuleSet()->returnSymMap.end())
366 {
368 llvmModuleSet()->returnSymMap.insert(std::make_pair(val, id));
369 DBOUT(DMemModel, outs() << "create a return sym " << id << "\n");
370 }
371}
372
377{
378 LLVMModuleSet::FunToIDMapTy::iterator iter =
380 if (iter == llvmModuleSet()->varargSymMap.end())
381 {
383 llvmModuleSet()->varargSymMap.insert(std::make_pair(val, id));
384 DBOUT(DMemModel, outs() << "create a vararg sym " << id << "\n");
385 }
386}
387
392{
393 if (const Constant* ref = SVFUtil::dyn_cast<Constant>(val))
394 {
395 if (const ConstantExpr* ce = isGepConstantExpr(ref))
396 {
397 DBOUT(DMemModelCE, outs() << "handle constant expression "
398 << llvmModuleSet()
400 ->toString()
401 << "\n");
402 collectVal(ce);
403
404 // handle the recursive constant express case
405 // like (gep (bitcast (gep X 1)) 1); the inner gep is ce->getOperand(0)
406 for (u32_t i = 0; i < ce->getNumOperands(); ++i)
407 {
408 collectVal(ce->getOperand(i));
409 handleCE(ce->getOperand(i));
410 }
411 }
412 else if (const ConstantExpr* ce = isCastConstantExpr(ref))
413 {
414 DBOUT(DMemModelCE, outs() << "handle constant expression "
415 << llvmModuleSet()
417 ->toString()
418 << "\n");
419 collectVal(ce);
420 collectVal(ce->getOperand(0));
421 // handle the recursive constant express case
422 // like (gep (bitcast (gep X 1)) 1); the inner gep is ce->getOperand(0)
423 handleCE(ce->getOperand(0));
424 }
425 else if (const ConstantExpr* ce = isSelectConstantExpr(ref))
426 {
427 DBOUT(DMemModelCE, outs() << "handle constant expression "
428 << llvmModuleSet()
430 ->toString()
431 << "\n");
432 collectVal(ce);
433 collectVal(ce->getOperand(0));
434 collectVal(ce->getOperand(1));
435 collectVal(ce->getOperand(2));
436 // handle the recursive constant express case
437 // like (gep (bitcast (gep X 1)) 1); the inner gep is ce->getOperand(0)
438 handleCE(ce->getOperand(0));
439 handleCE(ce->getOperand(1));
440 handleCE(ce->getOperand(2));
441 }
442 // if we meet a int2ptr, then it points-to black hole
444 {
446 const Constant* opnd = int2Ptrce->getOperand(0);
447 handleCE(opnd);
448 }
450 {
452 const Constant* opnd = ptr2Intce->getOperand(0);
453 handleCE(opnd);
454 }
456 {
458 }
459 else if (isBinaryConstantExpr(ref))
460 {
462 }
463 else if (isUnaryConstantExpr(ref))
464 {
465 // we don't handle unary constant expression like fneg(x) now
467 }
468 else if (SVFUtil::isa<ConstantAggregate>(ref))
469 {
470 // we don't handle constant aggregate like constant vectors
472 }
473 else
474 {
475 assert(!SVFUtil::isa<ConstantExpr>(val) &&
476 "we don't handle all other constant expression for now!");
478 }
479 }
480}
481
486{
487 assert(G);
488
489 //The type this global points to
490 const Type* T = G->getValueType();
491 bool is_array = 0;
492 //An array is considered a single variable of its type.
493 while (const ArrayType* AT = SVFUtil::dyn_cast<ArrayType>(T))
494 {
495 T = AT->getElementType();
496 is_array = true;
497 }
498
499 if (SVFUtil::isa<StructType>(T))
500 {
501 //A struct may be used in constant GEP expr.
502 for (const User* user : G->users())
503 {
504 handleCE(user);
505 }
506 }
507 else if (is_array)
508 {
509 for (const User* user : G->users())
510 {
511 handleCE(user);
512 }
513 }
514
515 if (G->hasInitializer())
516 {
517 handleGlobalInitializerCE(G->getInitializer());
518 }
519}
520
525{
526
527 if (C->getType()->isSingleValueType())
528 {
529 if (const ConstantExpr* E = SVFUtil::dyn_cast<ConstantExpr>(C))
530 {
531 handleCE(E);
532 }
533 else
534 {
535 collectVal(C);
536 }
537 }
538 else if (SVFUtil::isa<ConstantArray>(C))
539 {
540 for (u32_t i = 0, e = C->getNumOperands(); i != e; i++)
541 {
542 handleGlobalInitializerCE(SVFUtil::cast<Constant>(C->getOperand(i)));
543 }
544 }
545 else if (SVFUtil::isa<ConstantStruct>(C))
546 {
547 for (u32_t i = 0, e = C->getNumOperands(); i != e; i++)
548 {
549 handleGlobalInitializerCE(SVFUtil::cast<Constant>(C->getOperand(i)));
550 }
551 }
552 else if(const ConstantData* data = SVFUtil::dyn_cast<ConstantData>(C))
553 {
555 {
556 if (const ConstantDataSequential* seq =
557 SVFUtil::dyn_cast<ConstantDataSequential>(data))
558 {
559 for(u32_t i = 0; i < seq->getNumElements(); i++)
560 {
561 const Constant* ct = seq->getElementAsConstant(i);
563 }
564 }
565 else
566 {
567 assert(
568 (SVFUtil::isa<ConstantAggregateZero, UndefValue>(data)) &&
569 "Single value type data should have been handled!");
570 }
571 }
572 }
573 else
574 {
575 //TODO:assert(SVFUtil::isa<ConstantVector>(C),"what else do we have");
576 }
577}
578
583
584
589
594{
595 const Value* startValue = inst;
596 const PointerType *originalPType = SVFUtil::dyn_cast<PointerType>(inst->getType());
597 const Type* inferedType = nullptr;
598 assert(originalPType && "empty type?");
600 {
601 if(const Value* v = getFirstUseViaCastInst(inst))
602 {
603 if (const PointerType *newTy = SVFUtil::dyn_cast<PointerType>(v->getType()))
604 {
606 }
607 }
609 }
611 {
612 const CallBase* cs = LLVMUtil::getLLVMCallSite(inst);
613 u32_t arg_pos = LLVMUtil::getHeapAllocHoldingArgPosition(cs->getCalledFunction());
614 const Value* arg = cs->getArgOperand(arg_pos);
615 originalPType = SVFUtil::dyn_cast<PointerType>(arg->getType());
617 }
618 else
619 {
620 assert( false && "not a heap allocation instruction?");
621 }
622
624
625 return inferedType;
626}
627
628/*
629 * Initial the memory object here
630 */
632{
633 const Type* objTy = nullptr;
634
635 const Instruction* I = SVFUtil::dyn_cast<Instruction>(val);
636
637 // We consider two types of objects:
638 // (1) A heap/static object from a callsite
639 if (I && isNonInstricCallSite(I))
640 {
642 }
643 // (2) Other objects (e.g., alloca, global, etc.)
644 else
645 {
646 if (SVFUtil::isa<PointerType>(val->getType()))
647 {
648 if (const AllocaInst *allocaInst = SVFUtil::dyn_cast<AllocaInst>(val))
649 {
650 // get the type of the allocated memory
651 // e.g., for `%retval = alloca i64, align 4`, we return i64
652 objTy = allocaInst->getAllocatedType();
653 }
654 else if (const GlobalValue *global = SVFUtil::dyn_cast<GlobalValue>(val))
655 {
656 // get the pointee type of the global pointer (begins with @ symbol in llvm)
657 objTy = global->getValueType();
658 }
659 else
660 {
662 assert(false && "not an allocation or global?");
663 }
664 }
665 }
666
667 if (objTy)
668 {
670 ObjTypeInfo* typeInfo = new ObjTypeInfo(
671 llvmModuleSet()->getSVFType(objTy),
673 initTypeInfo(typeInfo,val, objTy);
674 return typeInfo;
675 }
676 else
677 {
678 writeWrnMsg("try to create an object with a non-pointer type.");
679 writeWrnMsg(val->getName().str());
680 writeWrnMsg("(" + getSourceLoc(val) + ")");
682 {
683 ObjTypeInfo* typeInfo = new ObjTypeInfo(
684 llvmModuleSet()->getSVFType(val->getType()),
685 0);
686 initTypeInfo(typeInfo,val, val->getType());
687 return typeInfo;
688 }
689 else
690 {
691 assert(false && "Memory object must be either (1) held by a pointer-typed ref value or (2) a constant value (e.g., 10).");
692 abort();
693 }
694 }
695}
696
701{
702 const Type *elemTy = llvmModuleSet()->getLLVMType(typeinfo->getType());
703 // Find the inter nested array element
704 while (const ArrayType* AT = SVFUtil::dyn_cast<ArrayType>(elemTy))
705 {
706 elemTy = AT->getElementType();
707 if (SVFUtil::isa<GlobalVariable>(val) &&
708 SVFUtil::cast<GlobalVariable>(val)->hasInitializer() &&
709 SVFUtil::isa<ConstantArray>(
710 SVFUtil::cast<GlobalVariable>(val)->getInitializer()))
712 else
714 }
715 if (SVFUtil::isa<StructType>(elemTy))
716 {
717 if (SVFUtil::isa<GlobalVariable>(val) &&
718 SVFUtil::cast<GlobalVariable>(val)->hasInitializer() &&
719 SVFUtil::isa<ConstantStruct>(
720 SVFUtil::cast<GlobalVariable>(val)->getInitializer()))
722 else
724 }
725}
726
742{
743 if(const llvm::CallInst* callInst = llvm::dyn_cast<llvm::CallInst>(val))
744 {
745 if (const llvm::Function* calledFunction =
746 callInst->getCalledFunction())
747 {
748 std::vector<const Value*> args;
749 // Heap alloc functions have annoation like "AllocSize:Arg1"
751 {
752 if (annotation.find("AllocSize:") != std::string::npos)
753 {
754 std::string allocSize = annotation.substr(10);
755 std::stringstream ss(allocSize);
756 std::string token;
757 // Analyaze annotation string and attract Arg list
758 while (std::getline(ss, token, '*'))
759 {
760 if (token.rfind("Arg", 0) == 0)
761 {
763 std::istringstream(token.substr(3)) >> argIndex;
765 {
766 args.push_back(
767 callInst->getArgOperand(argIndex));
768 }
769 }
770 }
771 }
772 }
773 u64_t product = 1;
774 if (args.size() > 0)
775 {
776 // for annotations like "AllocSize:Arg0*Arg1"
777 for (const llvm::Value* arg : args)
778 {
779 if (const llvm::ConstantInt* constIntArg =
780 llvm::dyn_cast<llvm::ConstantInt>(arg))
781 {
782 // Multiply the constant Value if all Args are const
784 }
785 else
786 {
787 // if Arg list has non-const value, return 0 to indicate it is non const byte size
788 return 0;
789 }
790 }
791 // If all the Args are const, return product
792 return product;
793 }
794 else
795 {
796 // for annotations like "AllocSize:UNKNOWN"
797 return 0;
798 }
799 }
800 }
801 // if it is not CallInst or CallInst has no CalledFunction, return 0 to indicate it is non const byte size
802 return 0;
803}
804
809{
811 analyzeObjType(typeinfo, val);
812 const Type* objTy = llvmModuleSet()->getLLVMType(typeinfo->getType());
813 if(SVFUtil::isa<ArrayType>(objTy))
814 return getNumOfElements(objTy);
815 else if(const StructType* st = SVFUtil::dyn_cast<StructType>(objTy))
816 {
820 typeinfo->resetTypeForHeapStaticObj(llvmModuleSet()->getSVFType(
821 llvmModuleSet()->getTypeInference()->ptrType()));
822 else
823 return getNumOfElements(objTy);
824 }
825 return typeinfo->getMaxFieldOffsetLimit();
826}
827
832{
834 {
836 analyzeObjType(typeinfo,castUse);
837 }
838 else
839 {
841 }
842}
843
848 const Type* objTy)
849{
850
851 u32_t elemNum = 1;
852 // init byteSize = 0, If byteSize is changed in the following process,
853 // it means that ObjTypeInfo has a Constant Byte Size
854 u32_t byteSize = 0;
855 // Global variable
856 // if val is Function Obj, byteSize is not set
857 if (SVFUtil::isa<Function>(val))
858 {
860 analyzeObjType(typeinfo,val);
861 elemNum = 0;
862 }
865 else if(const AllocaInst* allocaInst = SVFUtil::dyn_cast<AllocaInst>(val))
866 {
868 analyzeObjType(typeinfo,val);
871 if(const ConstantInt* sz = SVFUtil::dyn_cast<ConstantInt>(allocaInst->getArraySize()))
872 {
874 byteSize = LLVMUtil::getIntegerValue(sz).second * typeinfo->getType()->getByteSize();
875 }
877 else
878 {
879 elemNum = getNumOfElements(objTy);
880 byteSize = 0;
881 }
882 }
885 else if(SVFUtil::isa<GlobalVariable>(val))
886 {
890 analyzeObjType(typeinfo,val);
891 elemNum = getNumOfElements(objTy);
892 byteSize = typeinfo->getType()->getByteSize();
893 }
895 else if (SVFUtil::isa<Instruction>(val) &&
897 SVFUtil::cast<Instruction>(val)))
898 {
899 elemNum = analyzeHeapObjType(typeinfo,val);
900 // analyze heap alloc like (malloc/calloc/...), the alloc functions have
901 // annotation like "AllocSize:Arg1". Please refer to extapi.c.
902 // e.g. calloc(4, 10), annotation is "AllocSize:Arg0*Arg1",
903 // it means byteSize = 4 (Arg0) * 10 (Arg1) = 40
904 byteSize = analyzeHeapAllocByteSize(val);
905 }
907 {
908 analyzeStaticObjType(typeinfo,val);
909 // user input data, label its field as infinite here
910 elemNum = typeinfo->getMaxFieldOffsetLimit();
911 byteSize = typeinfo->getType()->getByteSize();
912 }
914 {
916 elemNum = getNumOfFlattenElements(val->getType());
917 byteSize = typeinfo->getType()->getByteSize();
918 }
919 else
920 {
921 assert("what other object do we have??");
922 abort();
923 }
924
925 // Reset maxOffsetLimit if it is over the total fieldNum of this object
926 if(typeinfo->getMaxFieldOffsetLimit() > elemNum)
927 typeinfo->setNumOfElements(elemNum);
928
929 // set ByteSize. If ByteSize > 0, this typeinfo has constant type.
930 // If ByteSize == 0, this typeinfo has 1) zero byte 2) non-const byte size
931 // If ByteSize>MaxFieldLimit, set MaxFieldLimit to the byteSize;
932 byteSize = Options::MaxFieldLimit() > byteSize? byteSize: Options::MaxFieldLimit();
933 typeinfo->setByteSizeOfObj(byteSize);
934}
935
940{
941 assert(ety && "type is null?");
942 u32_t numOfFields = 1;
943 if (SVFUtil::isa<StructType, ArrayType>(ety))
944 {
946 }
947 return numOfFields;
948}
949
958
#define DBOUT(TYPE, X)
LLVM debug macros, define type of your DBUG model of each pass.
Definition SVFType.h:498
#define DMemModelCE
Definition SVFType.h:508
#define DMemModel
Definition SVFType.h:507
NodeID constantSymID() const
Definition IRGraph.h:188
ObjTypeInfo * createObjTypeInfo(const SVFType *type)
Create an objectInfo based on LLVM type (value is null, and type could be null, representing a dummy ...
Definition IRGraph.cpp:231
static bool isBlkObj(NodeID id)
Definition IRGraph.h:165
IDToTypeInfoMapTy objTypeInfoMap
map a memory sym id to its obj
Definition IRGraph.h:88
NodeID totalSymNum
total number of symbols
Definition IRGraph.h:101
static bool isConstantSym(NodeID id)
Definition IRGraph.h:169
ValueToIDMapTy valSymMap
map a value to its sym id
Definition LLVMModule.h:112
FunToIDMapTy varargSymMap
vararg map
Definition LLVMModule.h:115
const std::vector< std::string > & getExtFuncAnnotations(const Function *fun)
SVFType * getSVFType(const Type *T)
Get or create SVFType and typeinfo.
const Type * getLLVMType(const SVFType *T) const
Get LLVM Type.
ValueToIDMapTy objSymMap
map a obj reference to its sym id
Definition LLVMModule.h:113
FunToIDMapTy returnSymMap
return map
Definition LLVMModule.h:114
const std::vector< std::reference_wrapper< Module > > & getLLVMModules() const
Definition LLVMModule.h:155
ObjTypeInference * getTypeInference()
NodeID allocateValueId(void)
Allocate a value ID as determined by the strategy.
static NodeIDAllocator * get(void)
Return (singleton) allocator.
NodeID allocateObjectId(void)
Allocate an object ID as determined by the strategy.
NodeID endSymbolAllocation(void)
Notify the allocator that all symbols have had IDs allocated.
void typeSizeDiffTest(const PointerType *oPTy, const Type *iTy, const Value *val)
const Type * inferObjType(const Value *var)
get or infer the type of the object pointed by the value
void validateTypeCheck(const CallBase *cs)
validate type inference
void resetTypeForHeapStaticObj(const SVFType *t)
Definition ObjTypeInfo.h:79
u32_t getMaxFieldOffsetLimit()
Get max field offset limit.
const SVFType * getType() const
Get LLVM type.
Definition ObjTypeInfo.h:98
void setByteSizeOfObj(u32_t size)
Set the byte size of this object.
void setFlag(MEMTYPE mask)
Flag for this object type.
void setNumOfElements(u32_t num)
Set the number of elements of this object.
static Option< bool > ModelArrays
Definition Options.h:189
static const Option< bool > EnableTypeCheck
Definition Options.h:132
static const Option< bool > SymTabPrint
Definition Options.h:191
static Option< bool > ModelConsts
Definition Options.h:188
static const Option< u32_t > MaxFieldLimit
Maximum number of field derivations for an object.
Definition Options.h:39
StInfo * getTypeInfo()
Definition SVFType.h:230
u32_t getByteSize() const
Definition SVFType.h:244
u32_t getNumOfFlattenElements() const
Return number of elements after flattening (including array elements)
Definition SVFType.h:139
u32_t getNumOfFlattenFields() const
Return the number of fields after flattening (ignoring array elements)
Definition SVFType.h:145
const Type * inferTypeOfHeapObjOrStaticObj(const Instruction *inst)
Get the reference type of heap/static object from an allocation site.
void handleGlobalInitializerCE(const Constant *C)
void collectRet(const Function *val)
ObjTypeInfo * createObjTypeInfo(const Value *val)
Create an objectInfo based on LLVM value.
const Type * inferObjType(const Value *startValue)
Forward collect all possible infer sites starting from a value.
void collectSVFTypeInfo(const Value *val)
collect the syms
LLVMModuleSet * llvmModuleSet()
ObjTypeInference * getTypeInference()
ObjTypeInfo * createBlkObjTypeInfo(NodeID symId)
u32_t getNumOfFlattenElements(const Type *T)
Number of flattened elements of an array or struct.
u32_t getNumOfElements(const Type *ety)
Return size of this object based on LLVM value.
void handleGlobalCE(const GlobalVariable *G)
Handle constant expression.
u32_t analyzeHeapObjType(ObjTypeInfo *typeinfo, const Value *val)
Analyse types of heap and static objects.
u32_t analyzeHeapAllocByteSize(const Value *val)
Analyze byte size of heap alloc function (e.g. malloc/calloc/...)
void collectObj(const Value *val)
void buildMemModel()
Start building memory model.
ObjTypeInfo * createConstantObjTypeInfo(NodeID symId)
void collectVal(const Value *val)
void handleCE(const Value *val)
void collectSym(const Value *val)
void collectVararg(const Function *val)
void initTypeInfo(ObjTypeInfo *typeinfo, const Value *value, const Type *ty)
Initialize TypeInfo based on LLVM Value.
void analyzeObjType(ObjTypeInfo *typeinfo, const Value *val)
Analyse types of all flattened fields of this object.
StInfo * getOrAddSVFTypeInfo(const Type *T)
Get a reference to StructInfo.
void analyzeStaticObjType(ObjTypeInfo *typeinfo, const Value *val)
Analyse types of heap and static objects.
bool isHeapAllocExtCallViaRet(const Instruction *inst)
Definition LLVMUtil.cpp:633
const Value * getFirstUseViaCastInst(const Value *val)
Definition LLVMUtil.cpp:277
const CallBase * getLLVMCallSite(const Value *value)
Return LLVM callsite given a value.
Definition LLVMUtil.h:91
const ConstantExpr * isBinaryConstantExpr(const Value *val)
Definition LLVMUtil.h:290
bool isHeapAllocExtCall(const Instruction *inst)
Definition LLVMUtil.h:396
bool isConstantObjSym(const Value *val)
Check whether this value points-to a constant object.
Definition CppUtil.cpp:672
const ConstantExpr * isInt2PtrConstantExpr(const Value *val)
Definition LLVMUtil.h:225
const ConstantExpr * isSelectConstantExpr(const Value *val)
Definition LLVMUtil.h:255
const ConstantExpr * isTruncConstantExpr(const Value *val)
Definition LLVMUtil.h:265
std::pair< s64_t, u64_t > getIntegerValue(const ConstantInt *intValue)
Definition LLVMUtil.h:82
bool isNullPtrSym(const Value *val)
Check whether this value is a black hole.
Definition LLVMUtil.h:125
std::string dumpValueAndDbgInfo(const Value *val)
Definition LLVMUtil.cpp:622
bool isConstDataOrAggData(const Value *val)
Return true if the value refers to constant data, e.g., i32 0.
Definition LLVMUtil.h:368
const std::string getSourceLoc(const Value *val)
Definition LLVMUtil.cpp:452
const ConstantExpr * isPtr2IntConstantExpr(const Value *val)
Definition LLVMUtil.h:235
const Value * getGlobalRep(const Value *val)
find the unique defined global across multiple modules
Definition LLVMUtil.cpp:439
const ConstantExpr * isUnaryConstantExpr(const Value *val)
Definition LLVMUtil.h:301
const ConstantExpr * isCastConstantExpr(const Value *val)
Definition LLVMUtil.h:245
bool isBlackholeSym(const Value *val)
Check whether this value is a black hole.
Definition LLVMUtil.h:119
bool isHeapAllocExtCallViaArg(const Instruction *inst)
Definition LLVMUtil.cpp:648
bool isObject(const Value *ref)
Return true if this value refers to a object.
Definition LLVMUtil.cpp:59
bool ArgInProgEntryFunction(const Value *val)
Return true if this is an argument of a program entry function (e.g. main)
Definition LLVMUtil.h:164
const ConstantExpr * isGepConstantExpr(const Value *val)
Return corresponding constant expression, otherwise return nullptr.
Definition LLVMUtil.h:215
u32_t getHeapAllocHoldingArgPosition(const Function *fun)
Definition LLVMUtil.cpp:400
bool isNonInstricCallSite(const Instruction *inst)
Whether an instruction is a callsite in the application code, excluding llvm intrinsic calls.
Definition LLVMUtil.cpp:720
const ConstantExpr * isCmpConstantExpr(const Value *val)
Definition LLVMUtil.h:279
void increaseStackSize()
Increase the stack size limit.
Definition SVFUtil.cpp:229
std::enable_if_t<!is_simple_type< Y >::value, typename cast_retty< X, const Y >::ret_type > cast(const Y &Val)
Definition Casting.h:360
std::ostream & errs()
Overwrite llvm::errs()
Definition SVFUtil.h:58
void writeWrnMsg(const std::string &msg)
Writes a message run through wrnMsg.
Definition SVFUtil.cpp:68
std::ostream & outs()
Overwrite llvm::outs()
Definition SVFUtil.h:52
bool classTyHasVTable(const StructType *ty)
Definition CppUtil.cpp:569
for isBitcode
Definition BasicTypes.h:68
llvm::GlobalVariable GlobalVariable
Definition BasicTypes.h:130
llvm::GlobalAlias GlobalAlias
Definition BasicTypes.h:128
llvm::ArrayType ArrayType
Definition BasicTypes.h:95
llvm::Type Type
Definition BasicTypes.h:83
llvm::CallBase CallBase
Definition BasicTypes.h:146
llvm::UnaryOperator UnaryOperator
Definition BasicTypes.h:180
llvm::StructType StructType
LLVM types.
Definition BasicTypes.h:94
unsigned long long u64_t
Definition GeneralType.h:49
llvm::AllocaInst AllocaInst
Definition BasicTypes.h:150
llvm::SwitchInst SwitchInst
Definition BasicTypes.h:155
u32_t NodeID
Definition GeneralType.h:56
llvm::Argument Argument
Definition BasicTypes.h:145
llvm::LoadInst LoadInst
Definition BasicTypes.h:149
llvm::CmpInst CmpInst
Definition BasicTypes.h:159
llvm::Function Function
Definition BasicTypes.h:85
llvm::GlobalValue GlobalValue
Definition BasicTypes.h:88
llvm::ConstantData ConstantData
Definition BasicTypes.h:116
llvm::Instruction Instruction
Definition BasicTypes.h:87
llvm::Constant Constant
Definition BasicTypes.h:124
llvm::ConstantDataSequential ConstantDataSequential
Definition BasicTypes.h:119
llvm::Value Value
LLVM Basic classes.
Definition BasicTypes.h:82
llvm::ConstantExpr ConstantExpr
Definition BasicTypes.h:120
llvm::IRBuilder IRBuilder
Definition BasicTypes.h:74
llvm::CastInst CastInst
Definition BasicTypes.h:158
llvm::FreezeInst FreezeInst
Definition BasicTypes.h:169
llvm::Module Module
Definition BasicTypes.h:84
llvm::PointerType PointerType
Definition BasicTypes.h:96
llvm::BinaryOperator BinaryOperator
Definition BasicTypes.h:179
llvm::StoreInst StoreInst
Definition BasicTypes.h:148
llvm::SelectInst SelectInst
Definition BasicTypes.h:174
llvm::GetElementPtrInst GetElementPtrInst
Definition BasicTypes.h:162
llvm::ReturnInst ReturnInst
Definition BasicTypes.h:157
llvm::PHINode PHINode
Definition BasicTypes.h:165
llvm::BranchInst BranchInst
Definition BasicTypes.h:154
unsigned u32_t
Definition GeneralType.h:47
llvm::ConstantInt ConstantInt
Definition BasicTypes.h:125
llvm::User User
Definition BasicTypes.h:142