svf-tools 1.0.719 → 1.0.721

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/.gitignore CHANGED
@@ -2,7 +2,7 @@ Release*/
2
2
  Debug*/
3
3
  build/
4
4
  html/
5
- Test-Suite/
5
+ Test-Suite
6
6
  Release+Asserts/
7
7
  Debug+Asserts/
8
8
  autoconf/
@@ -21,3 +21,4 @@ doxygen/
21
21
  *.obj
22
22
  *.svf
23
23
  cmake-build-debug/
24
+ compile_commands.json
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "svf-tools",
3
- "version": "1.0.719",
3
+ "version": "1.0.721",
4
4
  "description": "* <b>[TypeClone](https://github.com/SVF-tools/SVF/wiki/TypeClone) published in our [ECOOP paper](https://yuleisui.github.io/publications/ecoop20.pdf) is now available in SVF </b> * <b>SVF now uses a single script for its build. Just type [`source ./build.sh`](https://github.com/SVF-tools/SVF/blob/master/build.sh) in your terminal, that's it!</b> * <b>SVF now supports LLVM-10.0.0! </b> * <b>We thank [bsauce](https://github.com/bsauce) for writing a user manual of SVF ([link1](https://www.jianshu.com/p/068a08ec749c) and [link2](https://www.jianshu.com/p/777c30d4240e)) in Chinese </b> * <b>SVF now supports LLVM-9.0.0 (Thank [Byoungyoung Lee](https://github.com/SVF-tools/SVF/issues/142) for his help!). </b> * <b>SVF now supports a set of [field-sensitive pointer analyses](https://yuleisui.github.io/publications/sas2019a.pdf). </b> * <b>[Use SVF as an external lib](https://github.com/SVF-tools/SVF/wiki/Using-SVF-as-a-lib-in-your-own-tool) for your own project (Contributed by [Hongxu Chen](https://github.com/HongxuChen)). </b> * <b>SVF now supports LLVM-7.0.0. </b> * <b>SVF now supports Docker. [Try SVF in Docker](https://github.com/SVF-tools/SVF/wiki/Try-SVF-in-Docker)! </b> * <b>SVF now supports [LLVM-6.0.0](https://github.com/svf-tools/SVF/pull/38) (Contributed by [Jack Anthony](https://github.com/jackanth)). </b> * <b>SVF now supports [LLVM-4.0.0](https://github.com/svf-tools/SVF/pull/23) (Contributed by Jared Carlson. Thank [Jared](https://github.com/jcarlson23) and [Will](https://github.com/dtzWill) for their in-depth [discussions](https://github.com/svf-tools/SVF/pull/18) about updating SVF!) </b> * <b>SVF now supports analysis for C++ programs.</b> <br />",
5
5
  "main": "index.js",
6
6
  "scripts": {
@@ -264,6 +264,7 @@ private:
264
264
  StInfo* typeinfo; ///< SVF's TypeInfo
265
265
  bool isSingleValTy; ///< The type represents a single value, not struct or
266
266
  ///< array
267
+
267
268
  protected:
268
269
  SVFType(bool svt, SVFTyKind k)
269
270
  : kind(k), getPointerToTy(nullptr), typeinfo(nullptr),
@@ -280,9 +281,11 @@ public:
280
281
  return kind;
281
282
  }
282
283
 
283
- /// Needs to be implemented by a specific SVF front end (e.g., the
284
- /// implementation in LLVMUtil)
285
- virtual const std::string toString() const;
284
+ /// Note: Use `os<<svfType` or `svfType.print(os)` when possible to avoid
285
+ /// string concatenation.
286
+ std::string toString() const;
287
+
288
+ virtual void print(std::ostream& OS) const = 0;
286
289
 
287
290
  inline void setPointerTo(const SVFPointerType* ty)
288
291
  {
@@ -323,6 +326,8 @@ public:
323
326
  }
324
327
  };
325
328
 
329
+ std::ostream& operator<<(std::ostream& OS, const SVFType& type);
330
+
326
331
  class SVFPointerType : public SVFType
327
332
  {
328
333
  friend class SVFIRWriter;
@@ -344,6 +349,8 @@ public:
344
349
  {
345
350
  return ptrElementType;
346
351
  }
352
+
353
+ void print(std::ostream& OS) const override;
347
354
  };
348
355
 
349
356
  class SVFIntegerType : public SVFType
@@ -354,6 +361,8 @@ public:
354
361
  {
355
362
  return node->getKind() == SVFIntegerTy;
356
363
  }
364
+
365
+ void print(std::ostream& OS) const override;
357
366
  };
358
367
 
359
368
  class SVFFunctionType : public SVFType
@@ -377,36 +386,89 @@ public:
377
386
  {
378
387
  return retTy;
379
388
  }
389
+
390
+ void print(std::ostream& OS) const override;
380
391
  };
381
392
 
382
393
  class SVFStructType : public SVFType
383
394
  {
395
+ friend class SVFIRWriter;
396
+ friend class SVFIRReader;
397
+
398
+ private:
399
+ std::string name;
400
+
384
401
  public:
385
402
  SVFStructType() : SVFType(false, SVFStructTy) {}
403
+
386
404
  static inline bool classof(const SVFType* node)
387
405
  {
388
406
  return node->getKind() == SVFStructTy;
389
407
  }
408
+
409
+ void print(std::ostream& OS) const override;
410
+
411
+ std::string& getName()
412
+ {
413
+ return name;
414
+ }
390
415
  };
391
416
 
392
417
  class SVFArrayType : public SVFType
393
418
  {
419
+ friend class SVFIRWriter;
420
+ friend class SVFIRReader;
421
+
422
+ private:
423
+ unsigned numOfElement; /// For printing
424
+ SVFType* typeOfElement; /// For printing
425
+
394
426
  public:
395
- SVFArrayType() : SVFType(false, SVFArrayTy) {}
427
+ SVFArrayType()
428
+ : SVFType(false, SVFArrayTy), numOfElement(0), typeOfElement(nullptr)
429
+ {
430
+ }
431
+
396
432
  static inline bool classof(const SVFType* node)
397
433
  {
398
434
  return node->getKind() == SVFArrayTy;
399
435
  }
436
+
437
+ void print(std::ostream& OS) const override;
438
+
439
+ void setTypeOfElement(SVFType* elemType)
440
+ {
441
+ typeOfElement = elemType;
442
+ }
443
+
444
+ void setNumOfElement(unsigned elemNum)
445
+ {
446
+ numOfElement = elemNum;
447
+ }
400
448
  };
401
449
 
402
450
  class SVFOtherType : public SVFType
403
451
  {
452
+ friend class SVFIRWriter;
453
+ friend class SVFIRReader;
454
+
455
+ private:
456
+ std::string repr; /// Field representation for printing
457
+
404
458
  public:
405
459
  SVFOtherType(bool isSingleValueTy) : SVFType(isSingleValueTy, SVFOtherTy) {}
460
+
406
461
  static inline bool classof(const SVFType* node)
407
462
  {
408
463
  return node->getKind() == SVFOtherTy;
409
464
  }
465
+
466
+ std::string& getRepr()
467
+ {
468
+ return repr;
469
+ }
470
+
471
+ void print(std::ostream& OS) const override;
410
472
  };
411
473
 
412
474
  // TODO: be explicit that this is a pair of 32-bit unsigneds?
@@ -300,7 +300,7 @@ void SVFIR2ItvExeState::initValVar(const ValVar *valVar, u32_t varId)
300
300
  else
301
301
  {
302
302
 
303
- SVFUtil::errs() << valVar->getValue()->toString() << "\n" << " type: " << type->toString() << "\n";
303
+ SVFUtil::errs() << valVar->getValue()->toString() << "\n" << " type: " << *type << "\n";
304
304
  assert(false && "what other types we have");
305
305
  }
306
306
  }
@@ -81,7 +81,7 @@ u32_t LocationSet::getElementNum(const SVFType* type) const
81
81
  }
82
82
  else
83
83
  {
84
- SVFUtil::outs() << "GepIter Type" << type->toString() << "\n";
84
+ SVFUtil::outs() << "GepIter Type" << *type << "\n";
85
85
  assert(false && "What other types for this gep?");
86
86
  abort();
87
87
  }
@@ -228,7 +228,8 @@ std::string LocationSet::dump() const
228
228
  OffsetVarAndGepTypePairs::const_iterator eit = vec.end();
229
229
  for (; it != eit; ++it)
230
230
  {
231
- rawstr << " (Svf var: " << it->first->toString() << ", Iter type: " << it->second->toString() << ")";
231
+ const SVFType* ty = it->second;
232
+ rawstr << " (Svf var: " << it->first->toString() << ", Iter type: " << *ty << ")";
232
233
  }
233
234
  rawstr << " }\n";
234
235
  return rawstr.str();
@@ -498,17 +498,24 @@ cJSON* SVFIRWriter::contentToJson(const SVFFunctionType* type)
498
498
 
499
499
  cJSON* SVFIRWriter::contentToJson(const SVFStructType* type)
500
500
  {
501
- return contentToJson(static_cast<const SVFType*>(type));
501
+ cJSON* root = contentToJson(static_cast<const SVFType*>(type));
502
+ JSON_WRITE_FIELD(root, type, name);
503
+ return root;
502
504
  }
503
505
 
504
506
  cJSON* SVFIRWriter::contentToJson(const SVFArrayType* type)
505
507
  {
506
- return contentToJson(static_cast<const SVFType*>(type));
508
+ cJSON* root = contentToJson(static_cast<const SVFType*>(type));
509
+ JSON_WRITE_FIELD(root, type, numOfElement);
510
+ JSON_WRITE_FIELD(root, type, typeOfElement);
511
+ return root;
507
512
  }
508
513
 
509
514
  cJSON* SVFIRWriter::contentToJson(const SVFOtherType* type)
510
515
  {
511
- return contentToJson(static_cast<const SVFType*>(type));
516
+ cJSON* root = contentToJson(static_cast<const SVFType*>(type));
517
+ JSON_WRITE_FIELD(root, type, repr);
518
+ return root;
512
519
  }
513
520
 
514
521
  cJSON* SVFIRWriter::contentToJson(const SVFValue* value)
@@ -2492,16 +2499,20 @@ void SVFIRReader::fill(const cJSON*& fieldJson, SVFFunctionType* type)
2492
2499
  void SVFIRReader::fill(const cJSON*& fieldJson, SVFStructType* type)
2493
2500
  {
2494
2501
  fill(fieldJson, static_cast<SVFType*>(type));
2502
+ JSON_READ_FIELD_FWD(fieldJson, type, name);
2495
2503
  }
2496
2504
 
2497
2505
  void SVFIRReader::fill(const cJSON*& fieldJson, SVFArrayType* type)
2498
2506
  {
2499
2507
  fill(fieldJson, static_cast<SVFType*>(type));
2508
+ JSON_READ_FIELD_FWD(fieldJson, type, numOfElement);
2509
+ JSON_READ_FIELD_FWD(fieldJson, type, typeOfElement);
2500
2510
  }
2501
2511
 
2502
2512
  void SVFIRReader::fill(const cJSON*& fieldJson, SVFOtherType* type)
2503
2513
  {
2504
2514
  fill(fieldJson, static_cast<SVFType*>(type));
2515
+ JSON_READ_FIELD_FWD(fieldJson, type, repr);
2505
2516
  }
2506
2517
 
2507
2518
  SVFIR* SVFIRReader::read(const std::string& path)
@@ -0,0 +1,51 @@
1
+ #include "SVFIR/SVFType.h"
2
+ #include <sstream>
3
+
4
+ namespace SVF
5
+ {
6
+ std::string SVFType::toString() const
7
+ {
8
+ std::ostringstream os;
9
+ print(os);
10
+ return os.str();
11
+ }
12
+
13
+ std::ostream& operator<<(std::ostream& OS, const SVFType& type)
14
+ {
15
+ type.print(OS);
16
+ return OS;
17
+ }
18
+
19
+ void SVFPointerType::print(std::ostream& OS) const
20
+ {
21
+ getPtrElementType()->print(OS);
22
+ OS << "*";
23
+ }
24
+
25
+ void SVFIntegerType::print(std::ostream& OS) const
26
+ {
27
+ // Making it more informative?
28
+ OS << "I";
29
+ }
30
+
31
+ void SVFFunctionType::print(std::ostream& OS) const
32
+ {
33
+ OS << *getReturnType() << "()";
34
+ }
35
+
36
+ void SVFStructType::print(std::ostream& OS) const
37
+ {
38
+ OS << "S." << name;
39
+ }
40
+
41
+ void SVFArrayType::print(std::ostream& OS) const
42
+ {
43
+ OS << "[" << numOfElement << "x" << *typeOfElement << "]";
44
+ }
45
+
46
+ void SVFOtherType::print(std::ostream& OS) const
47
+ {
48
+ OS << repr;
49
+ }
50
+
51
+ } // namespace SVF
@@ -237,68 +237,49 @@ const std::vector<const SVFType*>& SymbolTableInfo::getFlattenFieldTypes(const S
237
237
  void SymbolTableInfo::printFlattenFields(const SVFType* type)
238
238
  {
239
239
 
240
- if(const SVFArrayType *at = SVFUtil::dyn_cast<SVFArrayType> (type))
240
+ if (const SVFArrayType* at = SVFUtil::dyn_cast<SVFArrayType>(type))
241
241
  {
242
- outs() <<" {Type: ";
243
- outs() << at->toString();
244
- outs() << "}\n";
245
- outs() << "\tarray type ";
246
- outs() << "\t [element size = " << getNumOfFlattenElements(at) << "]\n";
247
- outs() << "\n";
242
+ outs() << " {Type: " << *at << "}\n"
243
+ << "\tarray type "
244
+ << "\t [element size = " << getNumOfFlattenElements(at) << "]\n"
245
+ << "\n";
248
246
  }
249
-
250
- else if(const SVFStructType *st = SVFUtil::dyn_cast<SVFStructType> (type))
247
+ else if (const SVFStructType *st = SVFUtil::dyn_cast<SVFStructType>(type))
251
248
  {
252
- outs() <<" {Type: ";
253
- outs() << st->toString();
254
- outs() << "}\n";
249
+ outs() <<" {Type: " << *st << "}\n";
255
250
  const std::vector<const SVFType*>& finfo = getTypeInfo(st)->getFlattenFieldTypes();
256
251
  int field_idx = 0;
257
- for(std::vector<const SVFType*>::const_iterator it = finfo.begin(), eit = finfo.end();
258
- it!=eit; ++it, field_idx++)
252
+ for(const SVFType* type : finfo)
259
253
  {
260
- outs() << " \tField_idx = " << field_idx;
261
- outs() << ", field type: ";
262
- outs() << (*it)->toString();
263
- outs() << "\n";
254
+ outs() << " \tField_idx = " << ++field_idx
255
+ << ", field type: " << *type << "\n";
264
256
  }
265
257
  outs() << "\n";
266
258
  }
267
-
268
- else if (const SVFPointerType* pt= SVFUtil::dyn_cast<SVFPointerType> (type))
259
+ else if (const SVFPointerType* pt= SVFUtil::dyn_cast<SVFPointerType>(type))
269
260
  {
270
261
  u32_t eSize = getNumOfFlattenElements(pt->getPtrElementType());
271
- outs() << " {Type: ";
272
- outs() << pt->toString();
273
- outs() << "}\n";
274
- outs() <<"\t [target size = " << eSize << "]\n";
275
- outs() << "\n";
262
+ outs() << " {Type: " << *pt << "}\n"
263
+ << "\t [target size = " << eSize << "]\n"
264
+ << "\n";
276
265
  }
277
-
278
- else if ( const SVFFunctionType* fu= SVFUtil::dyn_cast<SVFFunctionType> (type))
266
+ else if (const SVFFunctionType* fu =
267
+ SVFUtil::dyn_cast<SVFFunctionType>(type))
279
268
  {
280
- outs() << " {Type: ";
281
- outs() << fu->getReturnType()->toString();
282
- outs() << "(Function)}\n\n";
269
+ outs() << " {Type: " << *fu << "}\n\n";
283
270
  }
284
-
285
- else if ( const SVFOtherType* ot= SVFUtil::dyn_cast<SVFOtherType> (type))
271
+ else if (const SVFOtherType* ot = SVFUtil::dyn_cast<SVFOtherType>(type))
286
272
  {
287
- outs() << " {Type: ";
288
- outs() << ot->toString();
289
- outs() << "(SVFOtherType)}\n\n";
273
+ outs() << " {Type: "<< *ot << "(SVFOtherType)}\n\n";
290
274
  }
291
-
292
275
  else
293
276
  {
294
277
  assert(type->isSingleValueType() && "not a single value type, then what else!!");
295
278
  /// All rest types are scalar type?
296
279
  u32_t eSize = getNumOfFlattenElements(type);
297
- outs() <<" {Type: ";
298
- outs() << type->toString();
299
- outs() << "}\n";
300
- outs() <<"\t [object size = " << eSize << "]\n";
301
- outs() << "\n";
280
+ outs() << " {Type: " << *type << "}\n"
281
+ << "\t [object size = " << eSize << "]\n"
282
+ << "\n";
302
283
  }
303
284
  }
304
285
 
@@ -593,4 +574,3 @@ bool SymbolTableInfo::hasValSym(const SVFValue* val)
593
574
  else
594
575
  return (valSymMap.find(val) != valSymMap.end());
595
576
  }
596
-
@@ -1003,12 +1003,25 @@ SVFType* LLVMModuleSet::addSVFTypeInfo(const Type* T)
1003
1003
  svftype = new SVFIntegerType();
1004
1004
  else if (const FunctionType* ft = SVFUtil::dyn_cast<FunctionType>(T))
1005
1005
  svftype = new SVFFunctionType(getSVFType(ft->getReturnType()));
1006
- else if (SVFUtil::isa<StructType>(T))
1007
- svftype = new SVFStructType();
1008
- else if (SVFUtil::isa<ArrayType>(T))
1009
- svftype = new SVFArrayType();
1006
+ else if (const StructType* st = SVFUtil::dyn_cast<StructType>(T))
1007
+ {
1008
+ auto svfst = new SVFStructType;
1009
+ svfst->getName() = st->getName().str();
1010
+ svftype = svfst;
1011
+ }
1012
+ else if (const auto at = SVFUtil::dyn_cast<ArrayType>(T))
1013
+ {
1014
+ auto svfat = new SVFArrayType();
1015
+ svfat->setNumOfElement(at->getNumElements());
1016
+ svfat->setTypeOfElement(getSVFType(at->getElementType()));
1017
+ svftype = svfat;
1018
+ }
1010
1019
  else
1011
- svftype = new SVFOtherType(T->isSingleValueType());
1020
+ {
1021
+ auto ot = new SVFOtherType(T->isSingleValueType());
1022
+ llvm::raw_string_ostream(ot->getRepr()) << *T;
1023
+ svftype = ot;
1024
+ }
1012
1025
 
1013
1026
  symInfo->addTypeInfo(svftype);
1014
1027
  LLVMType2SVFType[T] = svftype;
@@ -1044,8 +1057,9 @@ StInfo* LLVMModuleSet::collectArrayInfo(const ArrayType* ty)
1044
1057
  /// Array's flatten field infor is the same as its element's
1045
1058
  /// flatten infor.
1046
1059
  StInfo* elemStInfo = collectTypeInfo(elemTy);
1047
- u32_t nfE = elemStInfo->getNumOfFlattenFields();
1048
- for (u32_t j = 0; j < nfE; j++)
1060
+ u32_t nfF = elemStInfo->getNumOfFlattenFields();
1061
+ u32_t nfE = elemStInfo->getNumOfFlattenElements();
1062
+ for (u32_t j = 0; j < nfF; j++)
1049
1063
  {
1050
1064
  const SVFType* fieldTy = elemStInfo->getFlattenFieldTypes()[j];
1051
1065
  stInfo->getFlattenFieldTypes().push_back(fieldTy);
@@ -1064,14 +1078,14 @@ StInfo* LLVMModuleSet::collectArrayInfo(const ArrayType* ty)
1064
1078
  {
1065
1079
  for (u32_t j = 0; j < nfE; ++j)
1066
1080
  {
1067
- const SVFType* et = elemStInfo->getFlattenFieldTypes()[j];
1081
+ const SVFType* et = elemStInfo->getFlattenElementTypes()[j];
1068
1082
  stInfo->getFlattenElementTypes().push_back(et);
1069
1083
  }
1070
1084
  }
1071
1085
 
1072
1086
  assert(stInfo->getFlattenElementTypes().size() == nfE * totalElemNum &&
1073
1087
  "typeForArray size incorrect!!!");
1074
- stInfo->setNumOfFieldsAndElems(nfE, nfE * totalElemNum);
1088
+ stInfo->setNumOfFieldsAndElems(nfF, nfE * totalElemNum);
1075
1089
 
1076
1090
  return stInfo;
1077
1091
  }
@@ -1099,23 +1113,22 @@ StInfo* LLVMModuleSet::collectStructInfo(const StructType* structTy,
1099
1113
  if (SVFUtil::isa<StructType, ArrayType>(elemTy))
1100
1114
  {
1101
1115
  StInfo* subStInfo = collectTypeInfo(elemTy);
1102
- u32_t nfE = subStInfo->getNumOfFlattenFields();
1116
+ u32_t nfF = subStInfo->getNumOfFlattenFields();
1117
+ u32_t nfE = subStInfo->getNumOfFlattenElements();
1103
1118
  // Copy ST's info, whose element 0 is the size of ST itself.
1104
- for (u32_t j = 0; j < nfE; ++j)
1119
+ for (u32_t j = 0; j < nfF; ++j)
1105
1120
  {
1106
1121
  const SVFType* elemTy = subStInfo->getFlattenFieldTypes()[j];
1107
1122
  stInfo->getFlattenFieldTypes().push_back(elemTy);
1108
1123
  }
1109
- numFields += nfE;
1110
- strideOffset += nfE * subStInfo->getStride();
1111
- for (u32_t tpi = 0; tpi < subStInfo->getStride(); ++tpi)
1124
+ numFields += nfF;
1125
+ strideOffset += nfE;
1126
+ for (u32_t tpj = 0; tpj < nfE; ++tpj)
1112
1127
  {
1113
- for (u32_t tpj = 0; tpj < nfE; ++tpj)
1114
- {
1115
- const SVFType* ty = subStInfo->getFlattenFieldTypes()[tpj];
1116
- stInfo->getFlattenElementTypes().push_back(ty);
1117
- }
1128
+ const SVFType* ty = subStInfo->getFlattenElementTypes()[tpj];
1129
+ stInfo->getFlattenElementTypes().push_back(ty);
1118
1130
  }
1131
+
1119
1132
  }
1120
1133
  else
1121
1134
  {
@@ -1048,12 +1048,4 @@ const std::string SVFValue::toString() const
1048
1048
  return rawstr.str();
1049
1049
  }
1050
1050
 
1051
- const std::string SVFType::toString() const
1052
- {
1053
- std::string str;
1054
- llvm::raw_string_ostream rawstr(str);
1055
- const Type* ty = LLVMModuleSet::getLLVMModuleSet()->getLLVMType(this);
1056
- rawstr << *ty;
1057
- return rawstr.str();
1058
1051
  }
1059
- }