[PATCH] D31868: [analyzer] Check NULL pointer dereference issue for memset function

2017-10-24 Thread Leslie Zhai via Phabricator via cfe-commits
xiangzhai added a comment.

Dear Henry,

Sorry for my poor English, please Create a New patch or provide Chinese 
translation :)

Regards,
Leslie Zhai


Repository:
  rL LLVM

https://reviews.llvm.org/D31868



___
cfe-commits mailing list
cfe-commits@lists.llvm.org
http://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[PATCH] D34353: [analyzer] Teach CloneDetection about Qt Meta-Object Compiler to filter auto generated files

2017-06-20 Thread Leslie Zhai via Phabricator via cfe-commits
This revision was automatically updated to reflect the committed changes.
Closed by commit rL305774: [analyzer] Teach CloneDetection about Qt Meta-Object 
Compiler to filter auto… (authored by xiangzhai).

Changed prior to commit:
  https://reviews.llvm.org/D34353?vs=103063=103162#toc

Repository:
  rL LLVM

https://reviews.llvm.org/D34353

Files:
  cfe/trunk/include/clang/Analysis/CloneDetection.h
  cfe/trunk/lib/Analysis/CloneDetection.cpp
  cfe/trunk/lib/StaticAnalyzer/Checkers/CloneChecker.cpp


Index: cfe/trunk/include/clang/Analysis/CloneDetection.h
===
--- cfe/trunk/include/clang/Analysis/CloneDetection.h
+++ cfe/trunk/include/clang/Analysis/CloneDetection.h
@@ -321,11 +321,11 @@
   void constrain(std::vector );
 };
 
-struct AutoGeneratedCloneConstraint {
+struct FilenamePatternConstraint {
   StringRef IgnoredFilesPattern;
   std::shared_ptr IgnoredFilesRegex;
 
-  AutoGeneratedCloneConstraint(StringRef IgnoredFilesPattern) 
+  FilenamePatternConstraint(StringRef IgnoredFilesPattern) 
   : IgnoredFilesPattern(IgnoredFilesPattern) {
 IgnoredFilesRegex = std::make_shared("^(" +
 IgnoredFilesPattern.str() + "$)");
Index: cfe/trunk/lib/StaticAnalyzer/Checkers/CloneChecker.cpp
===
--- cfe/trunk/lib/StaticAnalyzer/Checkers/CloneChecker.cpp
+++ cfe/trunk/lib/StaticAnalyzer/Checkers/CloneChecker.cpp
@@ -82,7 +82,7 @@
   std::vector AllCloneGroups;
 
   Detector.findClones(AllCloneGroups,
-  AutoGeneratedCloneConstraint(IgnoredFilesPattern),
+  FilenamePatternConstraint(IgnoredFilesPattern),
   RecursiveCloneTypeIIConstraint(),
   MinComplexityConstraint(MinComplexity),
   MinGroupSizeConstraint(2), OnlyLargestCloneConstraint());
Index: cfe/trunk/lib/Analysis/CloneDetection.cpp
===
--- cfe/trunk/lib/Analysis/CloneDetection.cpp
+++ cfe/trunk/lib/Analysis/CloneDetection.cpp
@@ -366,7 +366,7 @@
   }
 }
 
-bool AutoGeneratedCloneConstraint::isAutoGenerated(const 
CloneDetector::CloneGroup ) {
+bool FilenamePatternConstraint::isAutoGenerated(const 
CloneDetector::CloneGroup ) {
   std::string Error;
   if (IgnoredFilesPattern.empty() || Group.empty() || 
   !IgnoredFilesRegex->isValid(Error))


Index: cfe/trunk/include/clang/Analysis/CloneDetection.h
===
--- cfe/trunk/include/clang/Analysis/CloneDetection.h
+++ cfe/trunk/include/clang/Analysis/CloneDetection.h
@@ -321,11 +321,11 @@
   void constrain(std::vector );
 };
 
-struct AutoGeneratedCloneConstraint {
+struct FilenamePatternConstraint {
   StringRef IgnoredFilesPattern;
   std::shared_ptr IgnoredFilesRegex;
 
-  AutoGeneratedCloneConstraint(StringRef IgnoredFilesPattern) 
+  FilenamePatternConstraint(StringRef IgnoredFilesPattern) 
   : IgnoredFilesPattern(IgnoredFilesPattern) {
 IgnoredFilesRegex = std::make_shared("^(" +
 IgnoredFilesPattern.str() + "$)");
Index: cfe/trunk/lib/StaticAnalyzer/Checkers/CloneChecker.cpp
===
--- cfe/trunk/lib/StaticAnalyzer/Checkers/CloneChecker.cpp
+++ cfe/trunk/lib/StaticAnalyzer/Checkers/CloneChecker.cpp
@@ -82,7 +82,7 @@
   std::vector AllCloneGroups;
 
   Detector.findClones(AllCloneGroups,
-  AutoGeneratedCloneConstraint(IgnoredFilesPattern),
+  FilenamePatternConstraint(IgnoredFilesPattern),
   RecursiveCloneTypeIIConstraint(),
   MinComplexityConstraint(MinComplexity),
   MinGroupSizeConstraint(2), OnlyLargestCloneConstraint());
Index: cfe/trunk/lib/Analysis/CloneDetection.cpp
===
--- cfe/trunk/lib/Analysis/CloneDetection.cpp
+++ cfe/trunk/lib/Analysis/CloneDetection.cpp
@@ -366,7 +366,7 @@
   }
 }
 
-bool AutoGeneratedCloneConstraint::isAutoGenerated(const CloneDetector::CloneGroup ) {
+bool FilenamePatternConstraint::isAutoGenerated(const CloneDetector::CloneGroup ) {
   std::string Error;
   if (IgnoredFilesPattern.empty() || Group.empty() || 
   !IgnoredFilesRegex->isValid(Error))
___
cfe-commits mailing list
cfe-commits@lists.llvm.org
http://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[PATCH] D31868: [analyzer] Check NULL pointer dereference issue for memset function

2017-06-20 Thread Leslie Zhai via Phabricator via cfe-commits
This revision was automatically updated to reflect the committed changes.
Closed by commit rL305773: [analyzer] Check NULL pointer dereference issue for 
memset function (authored by xiangzhai).

Changed prior to commit:
  https://reviews.llvm.org/D31868?vs=101847=103161#toc

Repository:
  rL LLVM

https://reviews.llvm.org/D31868

Files:
  cfe/trunk/lib/StaticAnalyzer/Checkers/CStringChecker.cpp
  cfe/trunk/test/Analysis/null-deref-ps-region.c

Index: cfe/trunk/test/Analysis/null-deref-ps-region.c
===
--- cfe/trunk/test/Analysis/null-deref-ps-region.c
+++ cfe/trunk/test/Analysis/null-deref-ps-region.c
@@ -1,6 +1,11 @@
-// RUN: %clang_analyze_cc1 -analyzer-checker=core,alpha.core -std=gnu99 -analyzer-store=region -verify %s
-// expected-no-diagnostics
+// RUN: %clang_analyze_cc1 -analyzer-checker=core,alpha.core,unix,alpha.unix -std=gnu99 -analyzer-store=region -verify %s
 
+#include "Inputs/system-header-simulator.h"
+
+typedef __typeof(sizeof(int)) size_t;
+void *memset(void *__s, int __c, size_t __n);
+void *malloc(size_t __size);
+void free(void *__ptr);
 
 // The store for 'a[1]' should not be removed mistakenly. SymbolicRegions may
 // also be live roots.
@@ -13,3 +18,55 @@
 i = *p; // no-warning
   }
 }
+
+void foo() {
+  int *x = malloc(sizeof(int));
+  memset(x, 0, sizeof(int));
+  int n = 1 / *x; // FIXME: no-warning
+  free(x);
+}
+
+void bar() {
+  int *x = malloc(sizeof(int));
+  memset(x, 0, 1);
+  int n = 1 / *x; // no-warning
+  free(x);
+}
+
+void testConcreteNull() {
+  int *x = 0;
+  memset(x, 0, 1); // expected-warning {{Null pointer argument in call to memory set function}}
+}
+
+void testStackArray() {
+  char buf[13];
+  memset(buf, 0, 1); // no-warning
+}
+
+void testHeapSymbol() {
+  char *buf = (char *)malloc(13);
+  memset(buf, 0, 1); // no-warning
+  free(buf);
+}
+
+void testStackArrayOutOfBound() {
+  char buf[1];
+  memset(buf, 0, 1024); // expected-warning {{Memory set function accesses out-of-bound array element}}
+}
+
+void testHeapSymbolOutOfBound() {
+  char *buf = (char *)malloc(1);
+  memset(buf, 0, 1024); // expected-warning {{Memory set function accesses out-of-bound array element}}
+  free(buf);
+}
+
+void testStackArraySameSize() {
+  char buf[1];
+  memset(buf, 0, sizeof(buf)); // no-warning
+}
+
+void testHeapSymbolSameSize() {
+  char *buf = (char *)malloc(1);
+  memset(buf, 0, 1); // no-warning
+  free(buf);
+}
Index: cfe/trunk/lib/StaticAnalyzer/Checkers/CStringChecker.cpp
===
--- cfe/trunk/lib/StaticAnalyzer/Checkers/CStringChecker.cpp
+++ cfe/trunk/lib/StaticAnalyzer/Checkers/CStringChecker.cpp
@@ -120,6 +120,7 @@
   void evalStdCopy(CheckerContext , const CallExpr *CE) const;
   void evalStdCopyBackward(CheckerContext , const CallExpr *CE) const;
   void evalStdCopyCommon(CheckerContext , const CallExpr *CE) const;
+  void evalMemset(CheckerContext , const CallExpr *CE) const;
 
   // Utility methods
   std::pair
@@ -1999,6 +2000,54 @@
   C.addTransition(State);
 }
 
+void CStringChecker::evalMemset(CheckerContext , const CallExpr *CE) const {
+  if (CE->getNumArgs() != 3)
+return;
+
+  CurrentFunctionDescription = "memory set function";
+
+  const Expr *Mem = CE->getArg(0);
+  const Expr *Size = CE->getArg(2);
+  ProgramStateRef State = C.getState();
+
+  // See if the size argument is zero.
+  const LocationContext *LCtx = C.getLocationContext();
+  SVal SizeVal = State->getSVal(Size, LCtx);
+  QualType SizeTy = Size->getType();
+
+  ProgramStateRef StateZeroSize, StateNonZeroSize;
+  std::tie(StateZeroSize, StateNonZeroSize) =
+assumeZero(C, State, SizeVal, SizeTy);
+
+  // Get the value of the memory area.
+  SVal MemVal = State->getSVal(Mem, LCtx);
+
+  // If the size is zero, there won't be any actual memory access, so
+  // just bind the return value to the Mem buffer and return.
+  if (StateZeroSize && !StateNonZeroSize) {
+StateZeroSize = StateZeroSize->BindExpr(CE, LCtx, MemVal);
+C.addTransition(StateZeroSize);
+return;
+  }
+
+  // Ensure the memory area is not null.
+  // If it is NULL there will be a NULL pointer dereference.
+  State = checkNonNull(C, StateNonZeroSize, Mem, MemVal);
+  if (!State)
+return;
+
+  State = CheckBufferAccess(C, State, Size, Mem);
+  if (!State)
+return;
+  State = InvalidateBuffer(C, State, Mem, C.getSVal(Mem),
+   /*IsSourceBuffer*/false, Size);
+  if (!State)
+return;
+
+  State = State->BindExpr(CE, LCtx, MemVal);
+  C.addTransition(State);
+}
+
 static bool isCPPStdLibraryFunction(const FunctionDecl *FD, StringRef Name) {
   IdentifierInfo *II = FD->getIdentifier();
   if (!II)
@@ -2032,6 +2081,8 @@
 evalFunction =  ::evalMemcmp;
   else if (C.isCLibraryFunction(FDecl, "memmove"))
 evalFunction =  ::evalMemmove;
+  else if (C.isCLibraryFunction(FDecl, "memset"))
+evalFunction =  ::evalMemset;
   else if 

[PATCH] D34353: [analyzer] Teach CloneDetection about Qt Meta-Object Compiler to filter auto generated files

2017-06-19 Thread Leslie Zhai via Phabricator via cfe-commits
xiangzhai created this revision.
Herald added a subscriber: xazax.hun.

Hi LLVM developers,

As Raphael suggested in https://reviews.llvm.org/D31320 I renamed 
`AutoGeneratedCloneConstraint` to `FilenamePatternConstraint`, please review 
it, thanks a lot!

Regards,
Leslie Zhai


Repository:
  rL LLVM

https://reviews.llvm.org/D34353

Files:
  include/clang/Analysis/CloneDetection.h
  lib/Analysis/CloneDetection.cpp
  lib/StaticAnalyzer/Checkers/CloneChecker.cpp


Index: lib/StaticAnalyzer/Checkers/CloneChecker.cpp
===
--- lib/StaticAnalyzer/Checkers/CloneChecker.cpp
+++ lib/StaticAnalyzer/Checkers/CloneChecker.cpp
@@ -82,7 +82,7 @@
   std::vector AllCloneGroups;
 
   Detector.findClones(AllCloneGroups,
-  AutoGeneratedCloneConstraint(IgnoredFilesPattern),
+  FilenamePatternConstraint(IgnoredFilesPattern),
   RecursiveCloneTypeIIConstraint(),
   MinComplexityConstraint(MinComplexity),
   MinGroupSizeConstraint(2), OnlyLargestCloneConstraint());
Index: lib/Analysis/CloneDetection.cpp
===
--- lib/Analysis/CloneDetection.cpp
+++ lib/Analysis/CloneDetection.cpp
@@ -366,7 +366,7 @@
   }
 }
 
-bool AutoGeneratedCloneConstraint::isAutoGenerated(const 
CloneDetector::CloneGroup ) {
+bool FilenamePatternConstraint::isAutoGenerated(const 
CloneDetector::CloneGroup ) {
   std::string Error;
   if (IgnoredFilesPattern.empty() || Group.empty() || 
   !IgnoredFilesRegex->isValid(Error))
Index: include/clang/Analysis/CloneDetection.h
===
--- include/clang/Analysis/CloneDetection.h
+++ include/clang/Analysis/CloneDetection.h
@@ -321,11 +321,11 @@
   void constrain(std::vector );
 };
 
-struct AutoGeneratedCloneConstraint {
+struct FilenamePatternConstraint {
   StringRef IgnoredFilesPattern;
   std::shared_ptr IgnoredFilesRegex;
 
-  AutoGeneratedCloneConstraint(StringRef IgnoredFilesPattern) 
+  FilenamePatternConstraint(StringRef IgnoredFilesPattern) 
   : IgnoredFilesPattern(IgnoredFilesPattern) {
 IgnoredFilesRegex = std::make_shared("^(" +
 IgnoredFilesPattern.str() + "$)");


Index: lib/StaticAnalyzer/Checkers/CloneChecker.cpp
===
--- lib/StaticAnalyzer/Checkers/CloneChecker.cpp
+++ lib/StaticAnalyzer/Checkers/CloneChecker.cpp
@@ -82,7 +82,7 @@
   std::vector AllCloneGroups;
 
   Detector.findClones(AllCloneGroups,
-  AutoGeneratedCloneConstraint(IgnoredFilesPattern),
+  FilenamePatternConstraint(IgnoredFilesPattern),
   RecursiveCloneTypeIIConstraint(),
   MinComplexityConstraint(MinComplexity),
   MinGroupSizeConstraint(2), OnlyLargestCloneConstraint());
Index: lib/Analysis/CloneDetection.cpp
===
--- lib/Analysis/CloneDetection.cpp
+++ lib/Analysis/CloneDetection.cpp
@@ -366,7 +366,7 @@
   }
 }
 
-bool AutoGeneratedCloneConstraint::isAutoGenerated(const CloneDetector::CloneGroup ) {
+bool FilenamePatternConstraint::isAutoGenerated(const CloneDetector::CloneGroup ) {
   std::string Error;
   if (IgnoredFilesPattern.empty() || Group.empty() || 
   !IgnoredFilesRegex->isValid(Error))
Index: include/clang/Analysis/CloneDetection.h
===
--- include/clang/Analysis/CloneDetection.h
+++ include/clang/Analysis/CloneDetection.h
@@ -321,11 +321,11 @@
   void constrain(std::vector );
 };
 
-struct AutoGeneratedCloneConstraint {
+struct FilenamePatternConstraint {
   StringRef IgnoredFilesPattern;
   std::shared_ptr IgnoredFilesRegex;
 
-  AutoGeneratedCloneConstraint(StringRef IgnoredFilesPattern) 
+  FilenamePatternConstraint(StringRef IgnoredFilesPattern) 
   : IgnoredFilesPattern(IgnoredFilesPattern) {
 IgnoredFilesRegex = std::make_shared("^(" +
 IgnoredFilesPattern.str() + "$)");
___
cfe-commits mailing list
cfe-commits@lists.llvm.org
http://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[PATCH] D31320: [analyzer] Teach CloneDetection about Qt Meta-Object Compiler

2017-06-19 Thread Leslie Zhai via Phabricator via cfe-commits
xiangzhai added inline comments.



Comment at: cfe/trunk/include/clang/Analysis/CloneDetection.h:324
 
+struct AutoGeneratedCloneConstraint {
+  StringRef IgnoredFilesPattern;

v.g.vassilev wrote:
> Shouldn't the name be more generic. What this essentially does is to filter 
> out false positives according to a regex...
At the very beginning, it is by regex match the filename, it is still very 
rough! but in future it is able to filter by looking for 
`QT_BEGIN_MOC_NAMESPACE` macro or `qt_meta_ prefix` function in the ASTContext? 
and there might be other auto-generated mechanism for different framework, such 
as Gtk and sort of open source GUI libraries. so perhaps 
`AutoGeneratedCloneConstraint` is better name, I am not good at naming, it is 
difficult to name my little kid :)


Repository:
  rL LLVM

https://reviews.llvm.org/D31320



___
cfe-commits mailing list
cfe-commits@lists.llvm.org
http://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[PATCH] D31320: [analyzer] Teach CloneDetection about Qt Meta-Object Compiler

2017-06-18 Thread Leslie Zhai via Phabricator via cfe-commits
This revision was automatically updated to reflect the committed changes.
Closed by commit rL305659: [analyzer] Teach CloneDetection about Qt Meta-Object 
Compiler (authored by xiangzhai).

Changed prior to commit:
  https://reviews.llvm.org/D31320?vs=102840=102984#toc

Repository:
  rL LLVM

https://reviews.llvm.org/D31320

Files:
  cfe/trunk/include/clang/Analysis/CloneDetection.h
  cfe/trunk/lib/Analysis/CloneDetection.cpp
  cfe/trunk/lib/StaticAnalyzer/Checkers/CloneChecker.cpp
  cfe/trunk/test/Analysis/copypaste/autogenerated_automoc.cpp
  cfe/trunk/test/Analysis/copypaste/dbus_autogenerated.cpp
  cfe/trunk/test/Analysis/copypaste/moc_autogenerated.cpp
  cfe/trunk/test/Analysis/copypaste/not-autogenerated.cpp
  cfe/trunk/test/Analysis/copypaste/ui_autogenerated.cpp

Index: cfe/trunk/lib/Analysis/CloneDetection.cpp
===
--- cfe/trunk/lib/Analysis/CloneDetection.cpp
+++ cfe/trunk/lib/Analysis/CloneDetection.cpp
@@ -18,9 +18,9 @@
 #include "clang/AST/Stmt.h"
 #include "clang/AST/StmtVisitor.h"
 #include "clang/Lex/Lexer.h"
-#include "llvm/ADT/StringRef.h"
 #include "llvm/Support/MD5.h"
 #include "llvm/Support/raw_ostream.h"
+#include "llvm/Support/Path.h"
 
 using namespace clang;
 
@@ -366,6 +366,23 @@
   }
 }
 
+bool AutoGeneratedCloneConstraint::isAutoGenerated(const CloneDetector::CloneGroup ) {
+  std::string Error;
+  if (IgnoredFilesPattern.empty() || Group.empty() || 
+  !IgnoredFilesRegex->isValid(Error))
+return false;
+
+  for (const StmtSequence  : Group) {
+const SourceManager  = S.getASTContext().getSourceManager();
+StringRef Filename = llvm::sys::path::filename(SM.getFilename(
+S.getContainingDecl()->getLocation()));
+if (IgnoredFilesRegex->match(Filename))
+  return true;
+  }
+
+  return false;
+}
+
 static size_t createHash(llvm::MD5 ) {
   size_t HashCode;
 
Index: cfe/trunk/lib/StaticAnalyzer/Checkers/CloneChecker.cpp
===
--- cfe/trunk/lib/StaticAnalyzer/Checkers/CloneChecker.cpp
+++ cfe/trunk/lib/StaticAnalyzer/Checkers/CloneChecker.cpp
@@ -73,12 +73,17 @@
   bool ReportNormalClones = Mgr.getAnalyzerOptions().getBooleanOption(
   "ReportNormalClones", true, this);
 
+  StringRef IgnoredFilesPattern = Mgr.getAnalyzerOptions().getOptionAsString(
+  "IgnoredFilesPattern", "", this);
+
   // Let the CloneDetector create a list of clones from all the analyzed
   // statements. We don't filter for matching variable patterns at this point
   // because reportSuspiciousClones() wants to search them for errors.
   std::vector AllCloneGroups;
 
-  Detector.findClones(AllCloneGroups, RecursiveCloneTypeIIConstraint(),
+  Detector.findClones(AllCloneGroups,
+  AutoGeneratedCloneConstraint(IgnoredFilesPattern),
+  RecursiveCloneTypeIIConstraint(),
   MinComplexityConstraint(MinComplexity),
   MinGroupSizeConstraint(2), OnlyLargestCloneConstraint());
 
Index: cfe/trunk/include/clang/Analysis/CloneDetection.h
===
--- cfe/trunk/include/clang/Analysis/CloneDetection.h
+++ cfe/trunk/include/clang/Analysis/CloneDetection.h
@@ -17,6 +17,8 @@
 
 #include "clang/Basic/SourceLocation.h"
 #include "llvm/ADT/SmallVector.h"
+#include "llvm/ADT/StringRef.h"
+#include "llvm/Support/Regex.h"
 #include 
 
 namespace clang {
@@ -319,6 +321,26 @@
   void constrain(std::vector );
 };
 
+struct AutoGeneratedCloneConstraint {
+  StringRef IgnoredFilesPattern;
+  std::shared_ptr IgnoredFilesRegex;
+
+  AutoGeneratedCloneConstraint(StringRef IgnoredFilesPattern) 
+  : IgnoredFilesPattern(IgnoredFilesPattern) {
+IgnoredFilesRegex = std::make_shared("^(" +
+IgnoredFilesPattern.str() + "$)");
+  }
+
+  bool isAutoGenerated(const CloneDetector::CloneGroup );
+
+  void constrain(std::vector ) {
+CloneConstraint::filterGroups(
+CloneGroups, [this](const CloneDetector::CloneGroup ) {
+  return isAutoGenerated(Group);
+});
+  }
+};
+
 /// Analyzes the pattern of the referenced variables in a statement.
 class VariablePattern {
 
Index: cfe/trunk/test/Analysis/copypaste/dbus_autogenerated.cpp
===
--- cfe/trunk/test/Analysis/copypaste/dbus_autogenerated.cpp
+++ cfe/trunk/test/Analysis/copypaste/dbus_autogenerated.cpp
@@ -0,0 +1,19 @@
+// RUN: %clang_analyze_cc1 -std=c++11 -analyzer-checker=alpha.clone.CloneChecker -analyzer-config alpha.clone.CloneChecker:IgnoredFilesPattern="moc_|dbus_|.*_automoc" -verify %s
+
+// Because files that have `dbus_' in their names are most likely autogenerated,
+// we suppress copy-paste warnings here.
+
+// expected-no-diagnostics
+
+void f1() {
+  int *p1 = new int[1];
+  int *p2 = new int[1];
+  if (p1) {
+delete [] p1;
+p1 = nullptr;
+  }
+  if (p2) {
+delete [] p1; // 

[PATCH] D31320: [analyzer] Teach CloneDetection about Qt Meta-Object Compiler

2017-06-16 Thread Leslie Zhai via Phabricator via cfe-commits
xiangzhai updated this revision to Diff 102840.
xiangzhai added a comment.

Dear Raphael,

I updated my patch as you suggested, may I commit it? thanks!

Regards,
Leslie Zhai


Repository:
  rL LLVM

https://reviews.llvm.org/D31320

Files:
  include/clang/Analysis/CloneDetection.h
  lib/Analysis/CloneDetection.cpp
  lib/StaticAnalyzer/Checkers/CloneChecker.cpp
  test/Analysis/copypaste/autogenerated_automoc.cpp
  test/Analysis/copypaste/dbus_autogenerated.cpp
  test/Analysis/copypaste/moc_autogenerated.cpp
  test/Analysis/copypaste/not-autogenerated.cpp
  test/Analysis/copypaste/ui_autogenerated.cpp

Index: test/Analysis/copypaste/ui_autogenerated.cpp
===
--- test/Analysis/copypaste/ui_autogenerated.cpp
+++ test/Analysis/copypaste/ui_autogenerated.cpp
@@ -0,0 +1,19 @@
+// RUN: %clang_analyze_cc1 -std=c++11 -analyzer-checker=alpha.clone.CloneChecker -analyzer-config alpha.clone.CloneChecker:IgnoredFilesPattern="moc_|ui_|.*_automoc" -verify %s
+
+// Because files that have `ui_' in their names are most likely autogenerated,
+// we suppress copy-paste warnings here.
+
+// expected-no-diagnostics
+
+void f1() {
+  int *p1 = new int[1];
+  int *p2 = new int[1];
+  if (p1) {
+delete [] p1;
+p1 = nullptr;
+  }
+  if (p2) {
+delete [] p1; // no-warning
+p2 = nullptr;
+  }
+}
Index: test/Analysis/copypaste/not-autogenerated.cpp
===
--- test/Analysis/copypaste/not-autogenerated.cpp
+++ test/Analysis/copypaste/not-autogenerated.cpp
@@ -0,0 +1,14 @@
+// RUN: %clang_analyze_cc1 -std=c++11 -analyzer-checker=alpha.clone.CloneChecker -analyzer-config alpha.clone.CloneChecker:IgnoredFilesPattern="moc_|ui_|dbus_|.*_automoc" -verify %s
+
+void f1() {
+  int *p1 = new int[1];
+  int *p2 = new int[1];
+  if (p1) {
+delete [] p1; // expected-note{{Similar code using 'p1' here}}
+p1 = nullptr;
+  }
+  if (p2) {
+delete [] p1; // expected-warning{{Potential copy-paste error; did you really mean to use 'p1' here?}}
+p2 = nullptr;
+  }
+}
Index: test/Analysis/copypaste/moc_autogenerated.cpp
===
--- test/Analysis/copypaste/moc_autogenerated.cpp
+++ test/Analysis/copypaste/moc_autogenerated.cpp
@@ -0,0 +1,19 @@
+// RUN: %clang_analyze_cc1 -std=c++11 -analyzer-checker=alpha.clone.CloneChecker -analyzer-config alpha.clone.CloneChecker:IgnoredFilesPattern="moc_|.*_automoc" -verify %s
+
+// Because files that have `moc_' in their names are most likely autogenerated,
+// we suppress copy-paste warnings here.
+
+// expected-no-diagnostics
+
+void f1() {
+  int *p1 = new int[1];
+  int *p2 = new int[1];
+  if (p1) {
+delete [] p1;
+p1 = nullptr;
+  }
+  if (p2) {
+delete [] p1; // no-warning
+p2 = nullptr;
+  }
+}
Index: test/Analysis/copypaste/dbus_autogenerated.cpp
===
--- test/Analysis/copypaste/dbus_autogenerated.cpp
+++ test/Analysis/copypaste/dbus_autogenerated.cpp
@@ -0,0 +1,19 @@
+// RUN: %clang_analyze_cc1 -std=c++11 -analyzer-checker=alpha.clone.CloneChecker -analyzer-config alpha.clone.CloneChecker:IgnoredFilesPattern="moc_|dbus_|.*_automoc" -verify %s
+
+// Because files that have `dbus_' in their names are most likely autogenerated,
+// we suppress copy-paste warnings here.
+
+// expected-no-diagnostics
+
+void f1() {
+  int *p1 = new int[1];
+  int *p2 = new int[1];
+  if (p1) {
+delete [] p1;
+p1 = nullptr;
+  }
+  if (p2) {
+delete [] p1; // no-warning
+p2 = nullptr;
+  }
+}
Index: test/Analysis/copypaste/autogenerated_automoc.cpp
===
--- test/Analysis/copypaste/autogenerated_automoc.cpp
+++ test/Analysis/copypaste/autogenerated_automoc.cpp
@@ -0,0 +1,19 @@
+// RUN: %clang_analyze_cc1 -std=c++11 -analyzer-checker=alpha.clone.CloneChecker -analyzer-config alpha.clone.CloneChecker:IgnoredFilesPattern="moc_|.*_automoc.cpp" -verify %s
+
+// Because files that have `_automoc.' in their names are most likely autogenerated,
+// we suppress copy-paste warnings here.
+
+// expected-no-diagnostics
+
+void f1() {
+  int *p1 = new int[1];
+  int *p2 = new int[1];
+  if (p1) {
+delete [] p1;
+p1 = nullptr;
+  }
+  if (p2) {
+delete [] p1; // no-warning
+p2 = nullptr;
+  }
+}
Index: lib/StaticAnalyzer/Checkers/CloneChecker.cpp
===
--- lib/StaticAnalyzer/Checkers/CloneChecker.cpp
+++ lib/StaticAnalyzer/Checkers/CloneChecker.cpp
@@ -73,12 +73,17 @@
   bool ReportNormalClones = Mgr.getAnalyzerOptions().getBooleanOption(
   "ReportNormalClones", true, this);
 
+  StringRef IgnoredFilesPattern = Mgr.getAnalyzerOptions().getOptionAsString(
+  "IgnoredFilesPattern", "", this);
+
   // Let the CloneDetector create a list of clones from all the analyzed
   // statements. We don't 

[PATCH] D31320: [analyzer] Teach CloneDetection about Qt Meta-Object Compiler

2017-06-16 Thread Leslie Zhai via Phabricator via cfe-commits
xiangzhai added a comment.

Dear Raphael,

Sorry I am not available, I am looking after my little kid, see you next week, 
rebase perhaps.

Thanks,
Leslie Zhai


Repository:
  rL LLVM

https://reviews.llvm.org/D31320



___
cfe-commits mailing list
cfe-commits@lists.llvm.org
http://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[PATCH] D31320: [analyzer] Teach CloneDetection about Qt Meta-Object Compiler

2017-06-16 Thread Leslie Zhai via Phabricator via cfe-commits
xiangzhai updated this revision to Diff 102796.
xiangzhai added a comment.

Dear Raphael,

I updated my patch as you suggested, please review it, thanks a lot!

And I noticed that you are doing Performance optimizations for the CloneChecker 
https://reviews.llvm.org/D34182 I will rebase my patch if you kindly commit.

Regards,
Leslie Zhai


Repository:
  rL LLVM

https://reviews.llvm.org/D31320

Files:
  include/clang/Analysis/CloneDetection.h
  lib/Analysis/CloneDetection.cpp
  lib/StaticAnalyzer/Checkers/CloneChecker.cpp
  test/Analysis/copypaste/autogenerated_automoc.cpp
  test/Analysis/copypaste/dbus_autogenerated.cpp
  test/Analysis/copypaste/moc_autogenerated.cpp
  test/Analysis/copypaste/not-autogenerated.cpp
  test/Analysis/copypaste/ui_autogenerated.cpp

Index: test/Analysis/copypaste/ui_autogenerated.cpp
===
--- test/Analysis/copypaste/ui_autogenerated.cpp
+++ test/Analysis/copypaste/ui_autogenerated.cpp
@@ -0,0 +1,19 @@
+// RUN: %clang_analyze_cc1 -std=c++11 -analyzer-checker=alpha.clone.CloneChecker -analyzer-config alpha.clone.CloneChecker:IgnoredFilesPattern="moc_|ui_|.*_automoc" -verify %s
+
+// Because files that have `ui_' in their names are most likely autogenerated,
+// we suppress copy-paste warnings here.
+
+// expected-no-diagnostics
+
+void f1() {
+  int *p1 = new int[1];
+  int *p2 = new int[1];
+  if (p1) {
+delete [] p1;
+p1 = nullptr;
+  }
+  if (p2) {
+delete [] p1; // no-warning
+p2 = nullptr;
+  }
+}
Index: test/Analysis/copypaste/not-autogenerated.cpp
===
--- test/Analysis/copypaste/not-autogenerated.cpp
+++ test/Analysis/copypaste/not-autogenerated.cpp
@@ -0,0 +1,14 @@
+// RUN: %clang_analyze_cc1 -std=c++11 -analyzer-checker=alpha.clone.CloneChecker -analyzer-config alpha.clone.CloneChecker:IgnoredFilesPattern="moc_|ui_|dbus_|.*_automoc" -verify %s
+
+void f1() {
+  int *p1 = new int[1];
+  int *p2 = new int[1];
+  if (p1) {
+delete [] p1; // expected-note{{Similar code using 'p1' here}}
+p1 = nullptr;
+  }
+  if (p2) {
+delete [] p1; // expected-warning{{Potential copy-paste error; did you really mean to use 'p1' here?}}
+p2 = nullptr;
+  }
+}
Index: test/Analysis/copypaste/moc_autogenerated.cpp
===
--- test/Analysis/copypaste/moc_autogenerated.cpp
+++ test/Analysis/copypaste/moc_autogenerated.cpp
@@ -0,0 +1,19 @@
+// RUN: %clang_analyze_cc1 -std=c++11 -analyzer-checker=alpha.clone.CloneChecker -analyzer-config alpha.clone.CloneChecker:IgnoredFilesPattern="moc_|.*_automoc" -verify %s
+
+// Because files that have `moc_' in their names are most likely autogenerated,
+// we suppress copy-paste warnings here.
+
+// expected-no-diagnostics
+
+void f1() {
+  int *p1 = new int[1];
+  int *p2 = new int[1];
+  if (p1) {
+delete [] p1;
+p1 = nullptr;
+  }
+  if (p2) {
+delete [] p1; // no-warning
+p2 = nullptr;
+  }
+}
Index: test/Analysis/copypaste/dbus_autogenerated.cpp
===
--- test/Analysis/copypaste/dbus_autogenerated.cpp
+++ test/Analysis/copypaste/dbus_autogenerated.cpp
@@ -0,0 +1,19 @@
+// RUN: %clang_analyze_cc1 -std=c++11 -analyzer-checker=alpha.clone.CloneChecker -analyzer-config alpha.clone.CloneChecker:IgnoredFilesPattern="moc_|dbus_|.*_automoc" -verify %s
+
+// Because files that have `dbus_' in their names are most likely autogenerated,
+// we suppress copy-paste warnings here.
+
+// expected-no-diagnostics
+
+void f1() {
+  int *p1 = new int[1];
+  int *p2 = new int[1];
+  if (p1) {
+delete [] p1;
+p1 = nullptr;
+  }
+  if (p2) {
+delete [] p1; // no-warning
+p2 = nullptr;
+  }
+}
Index: test/Analysis/copypaste/autogenerated_automoc.cpp
===
--- test/Analysis/copypaste/autogenerated_automoc.cpp
+++ test/Analysis/copypaste/autogenerated_automoc.cpp
@@ -0,0 +1,19 @@
+// RUN: %clang_analyze_cc1 -std=c++11 -analyzer-checker=alpha.clone.CloneChecker -analyzer-config alpha.clone.CloneChecker:IgnoredFilesPattern="moc_|.*_automoc.cpp" -verify %s
+
+// Because files that have `_automoc.' in their names are most likely autogenerated,
+// we suppress copy-paste warnings here.
+
+// expected-no-diagnostics
+
+void f1() {
+  int *p1 = new int[1];
+  int *p2 = new int[1];
+  if (p1) {
+delete [] p1;
+p1 = nullptr;
+  }
+  if (p2) {
+delete [] p1; // no-warning
+p2 = nullptr;
+  }
+}
Index: lib/StaticAnalyzer/Checkers/CloneChecker.cpp
===
--- lib/StaticAnalyzer/Checkers/CloneChecker.cpp
+++ lib/StaticAnalyzer/Checkers/CloneChecker.cpp
@@ -73,12 +73,17 @@
   bool ReportNormalClones = Mgr.getAnalyzerOptions().getBooleanOption(
   "ReportNormalClones", true, this);
 
+  StringRef IgnoredFilesPattern = 

[PATCH] D31320: [analyzer] Teach CloneDetection about Qt Meta-Object Compiler

2017-06-15 Thread Leslie Zhai via Phabricator via cfe-commits
xiangzhai updated this revision to Diff 102777.
xiangzhai added a comment.
Herald added a subscriber: xazax.hun.

Dear Raphael,

Thanks for your suggestion!

> Would it solve your use case if allow specifying file patterns via the 
> command line like this -analyzer-config

Fixed!

  /home/zhaixiang/project/llvm/build/./bin/clang -cc1 -internal-isystem 
/home/zhaixiang/project/llvm/build/lib64/clang/5.0.0/include -nostdsysteminc 
-analyze -analyzer-constraints=range -std=c++11 
-analyzer-checker=alpha.clone.CloneChecker -analyzer-config 
alpha.clone.CloneChecker:IgnoredFilesPattern="moc_|ui_|dbus_|.*_automoc" 
-verify 
/home/zhaixiang/project/llvm/tools/clang/test/Analysis/copypaste/not-autogenerated.cpp

I ran `make check-clang-analysis` and tested it for checking the real K3B 
 project's Copy-paste issue to filter Meta Object 
Compiler , User Interface Compiler 
, D-Bus XML Compiler 
, worked!

And it is able to specify the `IgnoredFilesPattern` to filter auto-generated 
files for different frameworks, please review my patch, if LGTU, may I commit 
it? thanks a lot!

Regards,
Leslie Zhai


Repository:
  rL LLVM

https://reviews.llvm.org/D31320

Files:
  include/clang/Analysis/CloneDetection.h
  lib/Analysis/CloneDetection.cpp
  lib/StaticAnalyzer/Checkers/CloneChecker.cpp
  test/Analysis/copypaste/autogenerated_automoc.cpp
  test/Analysis/copypaste/dbus_autogenerated.cpp
  test/Analysis/copypaste/moc_autogenerated.cpp
  test/Analysis/copypaste/not-autogenerated.cpp
  test/Analysis/copypaste/ui_autogenerated.cpp

Index: test/Analysis/copypaste/ui_autogenerated.cpp
===
--- test/Analysis/copypaste/ui_autogenerated.cpp
+++ test/Analysis/copypaste/ui_autogenerated.cpp
@@ -0,0 +1,19 @@
+// RUN: %clang_analyze_cc1 -std=c++11 -analyzer-checker=alpha.clone.CloneChecker -analyzer-config alpha.clone.CloneChecker:IgnoredFilesPattern="moc_|ui_|.*_automoc" -verify %s
+
+// Because files that have `ui_' in their names are most likely autogenerated,
+// we suppress copy-paste warnings here.
+
+// expected-no-diagnostics
+
+void f1() {
+  int *p1 = new int[1];
+  int *p2 = new int[1];
+  if (p1) {
+delete [] p1;
+p1 = nullptr;
+  }
+  if (p2) {
+delete [] p1; // no-warning
+p2 = nullptr;
+  }
+}
Index: test/Analysis/copypaste/not-autogenerated.cpp
===
--- test/Analysis/copypaste/not-autogenerated.cpp
+++ test/Analysis/copypaste/not-autogenerated.cpp
@@ -0,0 +1,14 @@
+// RUN: %clang_analyze_cc1 -std=c++11 -analyzer-checker=alpha.clone.CloneChecker -analyzer-config alpha.clone.CloneChecker:IgnoredFilesPattern="moc_|ui_|dbus_|.*_automoc" -verify %s
+
+void f1() {
+  int *p1 = new int[1];
+  int *p2 = new int[1];
+  if (p1) {
+delete [] p1; // expected-note{{Similar code using 'p1' here}}
+p1 = nullptr;
+  }
+  if (p2) {
+delete [] p1; // expected-warning{{Potential copy-paste error; did you really mean to use 'p1' here?}}
+p2 = nullptr;
+  }
+}
Index: test/Analysis/copypaste/moc_autogenerated.cpp
===
--- test/Analysis/copypaste/moc_autogenerated.cpp
+++ test/Analysis/copypaste/moc_autogenerated.cpp
@@ -0,0 +1,19 @@
+// RUN: %clang_analyze_cc1 -std=c++11 -analyzer-checker=alpha.clone.CloneChecker -analyzer-config alpha.clone.CloneChecker:IgnoredFilesPattern="moc_|.*_automoc" -verify %s
+
+// Because files that have `moc_' in their names are most likely autogenerated,
+// we suppress copy-paste warnings here.
+
+// expected-no-diagnostics
+
+void f1() {
+  int *p1 = new int[1];
+  int *p2 = new int[1];
+  if (p1) {
+delete [] p1;
+p1 = nullptr;
+  }
+  if (p2) {
+delete [] p1; // no-warning
+p2 = nullptr;
+  }
+}
Index: test/Analysis/copypaste/dbus_autogenerated.cpp
===
--- test/Analysis/copypaste/dbus_autogenerated.cpp
+++ test/Analysis/copypaste/dbus_autogenerated.cpp
@@ -0,0 +1,19 @@
+// RUN: %clang_analyze_cc1 -std=c++11 -analyzer-checker=alpha.clone.CloneChecker -analyzer-config alpha.clone.CloneChecker:IgnoredFilesPattern="moc_|dbus_|.*_automoc" -verify %s
+
+// Because files that have `dbus_' in their names are most likely autogenerated,
+// we suppress copy-paste warnings here.
+
+// expected-no-diagnostics
+
+void f1() {
+  int *p1 = new int[1];
+  int *p2 = new int[1];
+  if (p1) {
+delete [] p1;
+p1 = nullptr;
+  }
+  if (p2) {
+delete [] p1; // no-warning
+p2 = nullptr;
+  }
+}
Index: test/Analysis/copypaste/autogenerated_automoc.cpp
===
--- test/Analysis/copypaste/autogenerated_automoc.cpp
+++ test/Analysis/copypaste/autogenerated_automoc.cpp
@@ -0,0 +1,19 @@
+// RUN: %clang_analyze_cc1 -std=c++11 

[PATCH] D31868: [analyzer] Check NULL pointer dereference issue for memset function

2017-06-14 Thread Leslie Zhai via Phabricator via cfe-commits
xiangzhai added a comment.

Kindly ping Artem and Anna :)


Repository:
  rL LLVM

https://reviews.llvm.org/D31868



___
cfe-commits mailing list
cfe-commits@lists.llvm.org
http://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[PATCH] D31320: [analyzer] Teach CloneDetection about Qt Meta-Object Compiler

2017-06-14 Thread Leslie Zhai via Phabricator via cfe-commits
xiangzhai added a comment.

Dear Anna,

Long time no see, miss you :)

> Should this revision be "abandoned" or is the plan to iterate on it?

I wanna the plan to iterate on it, Artem reviewed the patch, and I fixed the 
issue as he suggested, ran `make check-clang-analysis` also used it for 
checking real project K3b 's Copy-paste issue, 
worked!

> Hi Vassil,



> ... Thanks for your reply! Let's do it together and Happy International Labor 
> Day :)

But Vassil and Raphael dis not reply me.

Could you kindly review it, if LGTU, may I commit it? thanks a lot!

Regards,
Leslie Zhai


Repository:
  rL LLVM

https://reviews.llvm.org/D31320



___
cfe-commits mailing list
cfe-commits@lists.llvm.org
http://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[PATCH] D31868: [analyzer] Check NULL pointer dereference issue for memset function

2017-06-07 Thread Leslie Zhai via Phabricator via cfe-commits
xiangzhai updated this revision to Diff 101847.
xiangzhai added a comment.
Herald added a subscriber: xazax.hun.

Hi Artem,

I updated my patch please review it, thanks a lot!

Regards,
Leslie Zhai


Repository:
  rL LLVM

https://reviews.llvm.org/D31868

Files:
  lib/StaticAnalyzer/Checkers/CStringChecker.cpp
  test/Analysis/null-deref-ps-region.c

Index: test/Analysis/null-deref-ps-region.c
===
--- test/Analysis/null-deref-ps-region.c
+++ test/Analysis/null-deref-ps-region.c
@@ -1,6 +1,11 @@
-// RUN: %clang_analyze_cc1 -analyzer-checker=core,alpha.core -std=gnu99 -analyzer-store=region -verify %s
-// expected-no-diagnostics
+// RUN: %clang_analyze_cc1 -analyzer-checker=core,alpha.core,unix,alpha.unix -std=gnu99 -analyzer-store=region -verify %s
 
+#include "Inputs/system-header-simulator.h"
+
+typedef __typeof(sizeof(int)) size_t;
+void *memset(void *__s, int __c, size_t __n);
+void *malloc(size_t __size);
+void free(void *__ptr);
 
 // The store for 'a[1]' should not be removed mistakenly. SymbolicRegions may
 // also be live roots.
@@ -13,3 +18,55 @@
 i = *p; // no-warning
   }
 }
+
+void foo() {
+  int *x = malloc(sizeof(int));
+  memset(x, 0, sizeof(int));
+  int n = 1 / *x; // FIXME: no-warning
+  free(x);
+}
+
+void bar() {
+  int *x = malloc(sizeof(int));
+  memset(x, 0, 1);
+  int n = 1 / *x; // no-warning
+  free(x);
+}
+
+void testConcreteNull() {
+  int *x = 0;
+  memset(x, 0, 1); // expected-warning {{Null pointer argument in call to memory set function}}
+}
+
+void testStackArray() {
+  char buf[13];
+  memset(buf, 0, 1); // no-warning
+}
+
+void testHeapSymbol() {
+  char *buf = (char *)malloc(13);
+  memset(buf, 0, 1); // no-warning
+  free(buf);
+}
+
+void testStackArrayOutOfBound() {
+  char buf[1];
+  memset(buf, 0, 1024); // expected-warning {{Memory set function accesses out-of-bound array element}}
+}
+
+void testHeapSymbolOutOfBound() {
+  char *buf = (char *)malloc(1);
+  memset(buf, 0, 1024); // expected-warning {{Memory set function accesses out-of-bound array element}}
+  free(buf);
+}
+
+void testStackArraySameSize() {
+  char buf[1];
+  memset(buf, 0, sizeof(buf)); // no-warning
+}
+
+void testHeapSymbolSameSize() {
+  char *buf = (char *)malloc(1);
+  memset(buf, 0, 1); // no-warning
+  free(buf);
+}
Index: lib/StaticAnalyzer/Checkers/CStringChecker.cpp
===
--- lib/StaticAnalyzer/Checkers/CStringChecker.cpp
+++ lib/StaticAnalyzer/Checkers/CStringChecker.cpp
@@ -120,6 +120,7 @@
   void evalStdCopy(CheckerContext , const CallExpr *CE) const;
   void evalStdCopyBackward(CheckerContext , const CallExpr *CE) const;
   void evalStdCopyCommon(CheckerContext , const CallExpr *CE) const;
+  void evalMemset(CheckerContext , const CallExpr *CE) const;
 
   // Utility methods
   std::pair
@@ -1999,6 +2000,54 @@
   C.addTransition(State);
 }
 
+void CStringChecker::evalMemset(CheckerContext , const CallExpr *CE) const {
+  if (CE->getNumArgs() != 3)
+return;
+
+  CurrentFunctionDescription = "memory set function";
+
+  const Expr *Mem = CE->getArg(0);
+  const Expr *Size = CE->getArg(2);
+  ProgramStateRef State = C.getState();
+
+  // See if the size argument is zero.
+  const LocationContext *LCtx = C.getLocationContext();
+  SVal SizeVal = State->getSVal(Size, LCtx);
+  QualType SizeTy = Size->getType();
+
+  ProgramStateRef StateZeroSize, StateNonZeroSize;
+  std::tie(StateZeroSize, StateNonZeroSize) =
+assumeZero(C, State, SizeVal, SizeTy);
+
+  // Get the value of the memory area.
+  SVal MemVal = State->getSVal(Mem, LCtx);
+
+  // If the size is zero, there won't be any actual memory access, so
+  // just bind the return value to the Mem buffer and return.
+  if (StateZeroSize && !StateNonZeroSize) {
+StateZeroSize = StateZeroSize->BindExpr(CE, LCtx, MemVal);
+C.addTransition(StateZeroSize);
+return;
+  }
+
+  // Ensure the memory area is not null.
+  // If it is NULL there will be a NULL pointer dereference.
+  State = checkNonNull(C, StateNonZeroSize, Mem, MemVal);
+  if (!State)
+return;
+
+  State = CheckBufferAccess(C, State, Size, Mem);
+  if (!State)
+return;
+  State = InvalidateBuffer(C, State, Mem, C.getSVal(Mem),
+   /*IsSourceBuffer*/false, Size);
+  if (!State)
+return;
+
+  State = State->BindExpr(CE, LCtx, MemVal);
+  C.addTransition(State);
+}
+
 static bool isCPPStdLibraryFunction(const FunctionDecl *FD, StringRef Name) {
   IdentifierInfo *II = FD->getIdentifier();
   if (!II)
@@ -2032,6 +2081,8 @@
 evalFunction =  ::evalMemcmp;
   else if (C.isCLibraryFunction(FDecl, "memmove"))
 evalFunction =  ::evalMemmove;
+  else if (C.isCLibraryFunction(FDecl, "memset"))
+evalFunction =  ::evalMemset;
   else if (C.isCLibraryFunction(FDecl, "strcpy"))
 evalFunction =  ::evalStrcpy;
   else if (C.isCLibraryFunction(FDecl, "strncpy"))

[PATCH] D31868: [analyzer] Check NULL pointer dereference issue for memset function

2017-06-01 Thread Leslie Zhai via Phabricator via cfe-commits
xiangzhai added a comment.

Hi Artem,

Long time no see! miss you :)

I will update my patch next Thursday! I am doing my work assignment about L4 
 right now.

Regards,
Leslie Zhai


Repository:
  rL LLVM

https://reviews.llvm.org/D31868



___
cfe-commits mailing list
cfe-commits@lists.llvm.org
http://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[PATCH] D31320: [analyzer] Teach CloneDetection about Qt Meta-Object Compiler

2017-04-28 Thread Leslie Zhai via Phabricator via cfe-commits
xiangzhai added a comment.

Hi Vassil,

The first one considered about CopyPaste dection 
 Thanks for 
your reply! Let's do it together and Happy International Labor Day :)

Regards,
Leslie Zhai


Repository:
  rL LLVM

https://reviews.llvm.org/D31320



___
cfe-commits mailing list
cfe-commits@lists.llvm.org
http://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[PATCH] D31320: [analyzer] Teach CloneDetection about Qt Meta-Object Compiler

2017-04-28 Thread Leslie Zhai via Phabricator via cfe-commits
xiangzhai updated this revision to Diff 97059.
xiangzhai added a comment.

Hi Artem,

Thanks for your review!

> Because LLVM's Illinois license is rather permissive than copyleft, we try to 
> avoid stuff copied from GPL/LGPL software (such as Qt or K3B) in our 
> codebase. The code doesn't seem to have been copy-pasted from a copyleft 
> project, but I guess it's better to rename the file to avoid referencing to 
> K3B.

Sorry for my mistake! I have rename the testcase to moc_autogenerated.cpp and 
autogenerated_automoc.cpp. I am the maintainer of K3B, if you find any bug when 
burning ISO please report bug to me :)

> Other LLVM contributors are free to edit this file, and i doubt it was 
> autogenerated; i believe these comments should be removed.

Sorry for my fault!

  /* This file is autogenerated, do not edit*/

it is autogenerated by MOC, I removed it!

And I use a single line LLVM regex instead of std::string functions, please 
review my patch, thanks a lot!

Regards,
Leslie Zhai


Repository:
  rL LLVM

https://reviews.llvm.org/D31320

Files:
  include/clang/Analysis/CloneDetection.h
  lib/Analysis/CloneDetection.cpp
  lib/StaticAnalyzer/Checkers/CloneChecker.cpp
  test/Analysis/copypaste/autogenerated_automoc.cpp
  test/Analysis/copypaste/moc_autogenerated.cpp

Index: test/Analysis/copypaste/autogenerated_automoc.cpp
===
--- test/Analysis/copypaste/autogenerated_automoc.cpp
+++ test/Analysis/copypaste/autogenerated_automoc.cpp
@@ -0,0 +1,19 @@
+// RUN: %clang_analyze_cc1 -std=c++11 -analyzer-checker=alpha.clone.CloneChecker -verify %s
+
+// Because files that have `_automoc.' in their names are most likely autogenerated,
+// we suppress copy-paste warnings here.
+
+// expected-no-diagnostics
+
+void f1() {
+  int *p1 = new int[1];
+  int *p2 = new int[1];
+  if (p1) {
+delete [] p1;
+p1 = nullptr;
+  }
+  if (p2) {
+delete [] p1; // no-warning
+p2 = nullptr;
+  }
+}
Index: test/Analysis/copypaste/moc_autogenerated.cpp
===
--- test/Analysis/copypaste/moc_autogenerated.cpp
+++ test/Analysis/copypaste/moc_autogenerated.cpp
@@ -0,0 +1,19 @@
+// RUN: %clang_analyze_cc1 -std=c++11 -analyzer-checker=alpha.clone.CloneChecker -verify %s
+
+// Because files that have `moc_' in their names are most likely autogenerated,
+// we suppress copy-paste warnings here.
+
+// expected-no-diagnostics
+
+void f1() {
+  int *p1 = new int[1];
+  int *p2 = new int[1];
+  if (p1) {
+delete [] p1;
+p1 = nullptr;
+  }
+  if (p2) {
+delete [] p1; // no-warning
+p2 = nullptr;
+  }
+}
Index: lib/StaticAnalyzer/Checkers/CloneChecker.cpp
===
--- lib/StaticAnalyzer/Checkers/CloneChecker.cpp
+++ lib/StaticAnalyzer/Checkers/CloneChecker.cpp
@@ -78,7 +78,8 @@
   // because reportSuspiciousClones() wants to search them for errors.
   std::vector AllCloneGroups;
 
-  Detector.findClones(AllCloneGroups, RecursiveCloneTypeIIConstraint(),
+  Detector.findClones(AllCloneGroups, AutoGeneratedCloneConstraint(), 
+  RecursiveCloneTypeIIConstraint(),
   MinComplexityConstraint(MinComplexity),
   MinGroupSizeConstraint(2), OnlyLargestCloneConstraint());
 
Index: lib/Analysis/CloneDetection.cpp
===
--- lib/Analysis/CloneDetection.cpp
+++ lib/Analysis/CloneDetection.cpp
@@ -21,6 +21,7 @@
 #include "llvm/ADT/StringRef.h"
 #include "llvm/Support/MD5.h"
 #include "llvm/Support/raw_ostream.h"
+#include "llvm/Support/Regex.h"
 
 using namespace clang;
 
@@ -366,6 +367,29 @@
   }
 }
 
+bool AutoGeneratedCloneConstraint::isAutoGenerated(const CloneDetector::CloneGroup ) {
+  if (Group.empty())
+return false;
+
+  for (const StmtSequence  : Group) {
+const Decl *D = S.getContainingDecl();
+const SourceManager  = D->getASTContext().getSourceManager();
+std::string Filename = std::string(SM.getFilename(D->getLocation()));
+// Get Basename
+const size_t LastSlash = Filename.find_last_of("\\/");
+if (LastSlash != std::string::npos)
+  Filename.erase(0, LastSlash + 1);
+const size_t LastDot = Filename.rfind('.');
+if (LastDot != std::string::npos)
+  Filename.erase(LastDot);
+llvm::Regex R(StringRef("^(moc_|.*_automoc$)"));
+if (R.match(StringRef(Filename)))
+  return true;
+  }
+
+  return false;
+}
+
 static size_t createHash(llvm::MD5 ) {
   size_t HashCode;
 
Index: include/clang/Analysis/CloneDetection.h
===
--- include/clang/Analysis/CloneDetection.h
+++ include/clang/Analysis/CloneDetection.h
@@ -319,6 +319,17 @@
   void constrain(std::vector );
 };
 
+struct AutoGeneratedCloneConstraint {
+  bool isAutoGenerated(const CloneDetector::CloneGroup );
+
+  void constrain(std::vector ) {
+

[PATCH] D31320: [analyzer] Teach CloneDetection about Qt Meta-Object Compiler

2017-04-28 Thread Leslie Zhai via Phabricator via cfe-commits
xiangzhai updated this revision to Diff 97047.
xiangzhai added a subscriber: cfe-commits.
xiangzhai added a comment.

Hi Artem,

Please review my updated patch, I use SourceManager's getFilename and add some 
testcases, thanks a lot!

Regards,
Leslie Zhai


Repository:
  rL LLVM

https://reviews.llvm.org/D31320

Files:
  include/clang/Analysis/CloneDetection.h
  lib/Analysis/CloneDetection.cpp
  lib/StaticAnalyzer/Checkers/CloneChecker.cpp
  test/Analysis/copypaste/k3blib_automoc.cpp
  test/Analysis/copypaste/moc_k3bactivepipe.cpp

Index: test/Analysis/copypaste/k3blib_automoc.cpp
===
--- test/Analysis/copypaste/k3blib_automoc.cpp
+++ test/Analysis/copypaste/k3blib_automoc.cpp
@@ -0,0 +1,21 @@
+// RUN: %clang_analyze_cc1 -std=c++11 -analyzer-checker=alpha.clone.CloneChecker -verify %s
+
+// expected-no-diagnostics
+
+/* This file is autogenerated, do not edit*/
+
+// clang -E RealMetaObjectCompiler_automoc.cpp > ~/PreprocessedMOC_automoc.cpp
+
+void f1() {
+  int *p1 = new int[1];
+  int *p2 = new int[1];
+  if (p1) {
+delete [] p1;
+p1 = nullptr;
+  }
+  // Copy-paste above block but careless forget to change something
+  if (p2) {
+delete [] p1; // no-warning
+p2 = nullptr;
+  }
+}
Index: test/Analysis/copypaste/moc_k3bactivepipe.cpp
===
--- test/Analysis/copypaste/moc_k3bactivepipe.cpp
+++ test/Analysis/copypaste/moc_k3bactivepipe.cpp
@@ -0,0 +1,27 @@
+// RUN: %clang_analyze_cc1 -std=c++11 -analyzer-checker=alpha.clone.CloneChecker -verify %s
+
+// expected-no-diagnostics
+
+/
+** Meta object code from reading C++ file 'k3bactivepipe.h'
+**
+** Created by: The Qt Meta Object Compiler version 67 (Qt 5.8.0)
+**
+** WARNING! All changes made in this file will be lost!
+*/
+
+// clang -E moc_RealMetaObjectCompiler.cpp > ~/moc_PreprocessedMOC.cpp
+
+void f1() {
+  int *p1 = new int[1];
+  int *p2 = new int[1];
+  if (p1) {
+delete [] p1;
+p1 = nullptr;
+  }
+  // Copy-paste above block but careless forget to change something
+  if (p2) {
+delete [] p1; // no-warning
+p2 = nullptr;
+  }
+}
Index: lib/StaticAnalyzer/Checkers/CloneChecker.cpp
===
--- lib/StaticAnalyzer/Checkers/CloneChecker.cpp
+++ lib/StaticAnalyzer/Checkers/CloneChecker.cpp
@@ -78,7 +78,8 @@
   // because reportSuspiciousClones() wants to search them for errors.
   std::vector AllCloneGroups;
 
-  Detector.findClones(AllCloneGroups, RecursiveCloneTypeIIConstraint(),
+  Detector.findClones(AllCloneGroups, AutoGeneratedCloneConstraint(), 
+  RecursiveCloneTypeIIConstraint(),
   MinComplexityConstraint(MinComplexity),
   MinGroupSizeConstraint(2), OnlyLargestCloneConstraint());
 
Index: lib/Analysis/CloneDetection.cpp
===
--- lib/Analysis/CloneDetection.cpp
+++ lib/Analysis/CloneDetection.cpp
@@ -366,6 +366,24 @@
   }
 }
 
+bool AutoGeneratedCloneConstraint::isAutoGenerated(const CloneDetector::CloneGroup ) {
+  if (Group.empty())
+return false;
+
+  for (const StmtSequence  : Group) {
+const Decl *D = S.getContainingDecl();
+const SourceManager  = D->getASTContext().getSourceManager();
+StringRef Filename = SM.getFilename(D->getLocation());
+if (Filename.find(StringRef("moc_")) != StringRef::npos ||
+Filename.find(StringRef("_automoc.")) != StringRef::npos ||
+Filename.find(StringRef(".moc")) != StringRef::npos) {
+  return true;
+}
+  }
+
+  return false;
+}
+
 static size_t createHash(llvm::MD5 ) {
   size_t HashCode;
 
Index: include/clang/Analysis/CloneDetection.h
===
--- include/clang/Analysis/CloneDetection.h
+++ include/clang/Analysis/CloneDetection.h
@@ -319,6 +319,17 @@
   void constrain(std::vector );
 };
 
+struct AutoGeneratedCloneConstraint {
+  bool isAutoGenerated(const CloneDetector::CloneGroup );
+
+  void constrain(std::vector ) {
+CloneConstraint::filterGroups(
+CloneGroups, [this](const CloneDetector::CloneGroup ) {
+  return isAutoGenerated(Group);
+});
+  }
+};
+
 /// Analyzes the pattern of the referenced variables in a statement.
 class VariablePattern {
 
___
cfe-commits mailing list
cfe-commits@lists.llvm.org
http://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[PATCH] D31868: [analyzer] Check NULL pointer dereference issue for memset function

2017-04-27 Thread Leslie Zhai via Phabricator via cfe-commits
xiangzhai updated this revision to Diff 97042.
xiangzhai added a comment.

Hi Artem,

Please review my updated patch, thanks a lot!

Regards,
Leslie Zhai


Repository:
  rL LLVM

https://reviews.llvm.org/D31868

Files:
  lib/StaticAnalyzer/Checkers/CStringChecker.cpp
  test/Analysis/null-deref-ps-region.c

Index: test/Analysis/null-deref-ps-region.c
===
--- test/Analysis/null-deref-ps-region.c
+++ test/Analysis/null-deref-ps-region.c
@@ -1,6 +1,11 @@
-// RUN: %clang_analyze_cc1 -analyzer-checker=core,alpha.core -std=gnu99 -analyzer-store=region -verify %s
-// expected-no-diagnostics
+// RUN: %clang_analyze_cc1 -analyzer-checker=core,alpha.core,unix,alpha.unix -std=gnu99 -analyzer-store=region -verify %s
 
+#include "Inputs/system-header-simulator.h"
+
+typedef __typeof(sizeof(int)) size_t;
+void *memset(void *__s, int __c, size_t __n);
+void *malloc(size_t __size);
+void free(void *__ptr);
 
 // The store for 'a[1]' should not be removed mistakenly. SymbolicRegions may
 // also be live roots.
@@ -13,3 +18,55 @@
 i = *p; // no-warning
   }
 }
+
+void foo() {
+  int *x = malloc(sizeof(int));
+  memset(x, 0, sizeof(int));
+  int n = 1 / *x;
+  free(x);
+}
+
+void bar() {
+  int *x = malloc(sizeof(int));
+  memset(x, 0, 1);
+  int n = 1 / *x; // no-warning
+  free(x);
+}
+
+void f531() {
+  int *x = 0;
+  memset(x, 0, 1); // expected-warning {{Null pointer argument in call to memory set function}}
+}
+
+void f61() {
+  char buf[13];
+  memset(buf, 0, 1); // no-warning
+}
+
+void f611() {
+  char *buf = (char *)malloc(13);
+  memset(buf, 0, 1); // no-warning
+  free(buf);
+}
+
+void f66() {
+  char buf[1];
+  memset(buf, 0, 1024); // expected-warning {{Memory set function accesses out-of-bound array element}}
+}
+
+void f666() {
+  char *buf = (char *)malloc(1);
+  memset(buf, 0, 1024); // expected-warning {{Memory set function accesses out-of-bound array element}}
+  free(buf);
+}
+
+void f77() {
+  char buf[1];
+  memset(buf, 0, sizeof(buf)); // no-warning
+}
+
+void f777() {
+  char *buf = (char *)malloc(1);
+  memset(buf, 0, 1); // no-warning
+  free(buf);
+}
Index: lib/StaticAnalyzer/Checkers/CStringChecker.cpp
===
--- lib/StaticAnalyzer/Checkers/CStringChecker.cpp
+++ lib/StaticAnalyzer/Checkers/CStringChecker.cpp
@@ -120,6 +120,7 @@
   void evalStdCopy(CheckerContext , const CallExpr *CE) const;
   void evalStdCopyBackward(CheckerContext , const CallExpr *CE) const;
   void evalStdCopyCommon(CheckerContext , const CallExpr *CE) const;
+  void evalMemset(CheckerContext , const CallExpr *CE) const;
 
   // Utility methods
   std::pair
@@ -1999,6 +2000,55 @@
   C.addTransition(State);
 }
 
+void CStringChecker::evalMemset(CheckerContext , const CallExpr *CE) const {
+  if (CE->getNumArgs() != 3)
+return;
+
+  CurrentFunctionDescription = "memory set function";
+
+  const Expr *Mem = CE->getArg(0);
+  const Expr *Const = CE->getArg(1);
+  const Expr *Size = CE->getArg(2);
+  ProgramStateRef State = C.getState();
+
+  // See if the size argument is zero.
+  const LocationContext *LCtx = C.getLocationContext();
+  SVal SizeVal = State->getSVal(Size, LCtx);
+  QualType SizeTy = Size->getType();
+
+  ProgramStateRef StateZeroSize, StateNonZeroSize;
+  std::tie(StateZeroSize, StateNonZeroSize) =
+assumeZero(C, State, SizeVal, SizeTy);
+
+  // Get the value of the memory area.
+  SVal MemVal = State->getSVal(Mem, LCtx);
+
+  // If the size is zero, there won't be any actual memory access, so
+  // just bind the return value to the Mem buffer and return.
+  if (StateZeroSize && !StateNonZeroSize) {
+StateZeroSize = StateZeroSize->BindExpr(CE, LCtx, MemVal);
+C.addTransition(StateZeroSize);
+return;
+  }
+
+  // Ensure the memory area is not null.
+  // If it is NULL there will be a NULL pointer dereference.
+  State = checkNonNull(C, StateNonZeroSize, Mem, MemVal);
+  if (!State)
+return;
+
+  State = CheckBufferAccess(C, State, Size, Mem);
+  if (!State)
+return;
+  State = InvalidateBuffer(C, State, Mem, C.getSVal(Mem),
+   /*IsSourceBuffer*/false, Size);
+  if (!State)
+return;
+
+  State = State->BindExpr(CE, LCtx, MemVal);
+  C.addTransition(State);
+}
+
 static bool isCPPStdLibraryFunction(const FunctionDecl *FD, StringRef Name) {
   IdentifierInfo *II = FD->getIdentifier();
   if (!II)
@@ -2032,6 +2082,8 @@
 evalFunction =  ::evalMemcmp;
   else if (C.isCLibraryFunction(FDecl, "memmove"))
 evalFunction =  ::evalMemmove;
+  else if (C.isCLibraryFunction(FDecl, "memset"))
+evalFunction =  ::evalMemset;
   else if (C.isCLibraryFunction(FDecl, "strcpy"))
 evalFunction =  ::evalStrcpy;
   else if (C.isCLibraryFunction(FDecl, "strncpy"))
___
cfe-commits mailing list
cfe-commits@lists.llvm.org
http://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[PATCH] D31868: [analyzer] Check NULL pointer dereference issue for memset function

2017-04-27 Thread Leslie Zhai via Phabricator via cfe-commits
xiangzhai added a comment.

Hi Artem,

Thank you so much! you are my mentor teach me patiently and carefully, I will 
update my patch tomorrow, good night from my timezone:)

Regards,
Leslie Zhai


Repository:
  rL LLVM

https://reviews.llvm.org/D31868



___
cfe-commits mailing list
cfe-commits@lists.llvm.org
http://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[PATCH] D30771: [analyzer] Teach the MallocChecker about Glib API for two arguments

2017-04-25 Thread Leslie Zhai via Phabricator via cfe-commits
This revision was automatically updated to reflect the committed changes.
Closed by commit rL301384: [analyzer] Teach the MallocChecker about Glib API 
for two arguments (authored by xiangzhai).

Changed prior to commit:
  https://reviews.llvm.org/D30771?vs=96101=96670#toc

Repository:
  rL LLVM

https://reviews.llvm.org/D30771

Files:
  cfe/trunk/lib/StaticAnalyzer/Checkers/MallocChecker.cpp
  cfe/trunk/test/Analysis/gmalloc.c

Index: cfe/trunk/lib/StaticAnalyzer/Checkers/MallocChecker.cpp
===
--- cfe/trunk/lib/StaticAnalyzer/Checkers/MallocChecker.cpp
+++ cfe/trunk/lib/StaticAnalyzer/Checkers/MallocChecker.cpp
@@ -177,7 +177,10 @@
 II_wcsdup(nullptr), II_win_wcsdup(nullptr), II_g_malloc(nullptr),
 II_g_malloc0(nullptr), II_g_realloc(nullptr), II_g_try_malloc(nullptr), 
 II_g_try_malloc0(nullptr), II_g_try_realloc(nullptr), 
-II_g_free(nullptr), II_g_memdup(nullptr) {}
+II_g_free(nullptr), II_g_memdup(nullptr), II_g_malloc_n(nullptr), 
+II_g_malloc0_n(nullptr), II_g_realloc_n(nullptr), 
+II_g_try_malloc_n(nullptr), II_g_try_malloc0_n(nullptr), 
+II_g_try_realloc_n(nullptr) {}
 
   /// In pessimistic mode, the checker assumes that it does not know which
   /// functions might free the memory.
@@ -241,7 +244,10 @@
  *II_if_nameindex, *II_if_freenameindex, *II_wcsdup,
  *II_win_wcsdup, *II_g_malloc, *II_g_malloc0, 
  *II_g_realloc, *II_g_try_malloc, *II_g_try_malloc0, 
- *II_g_try_realloc, *II_g_free, *II_g_memdup;
+ *II_g_try_realloc, *II_g_free, *II_g_memdup, 
+ *II_g_malloc_n, *II_g_malloc0_n, *II_g_realloc_n, 
+ *II_g_try_malloc_n, *II_g_try_malloc0_n, 
+ *II_g_try_realloc_n;
   mutable Optional KernelZeroFlagVal;
 
   void initIdentifierInfo(ASTContext ) const;
@@ -321,9 +327,12 @@
  bool ,
  bool ReturnsNullOnFailure = false) const;
 
-  ProgramStateRef ReallocMem(CheckerContext , const CallExpr *CE,
- bool FreesMemOnFailure,
- ProgramStateRef State) const;
+  ProgramStateRef ReallocMemAux(CheckerContext , const CallExpr *CE,
+bool FreesMemOnFailure,
+ProgramStateRef State, 
+bool SuffixWithN = false) const;
+  static SVal evalMulForBufferSize(CheckerContext , const Expr *Blocks,
+   const Expr *BlockBytes);
   static ProgramStateRef CallocMem(CheckerContext , const CallExpr *CE,
ProgramStateRef State);
 
@@ -569,6 +578,12 @@
   II_g_try_realloc = ("g_try_realloc");
   II_g_free = ("g_free");
   II_g_memdup = ("g_memdup");
+  II_g_malloc_n = ("g_malloc_n");
+  II_g_malloc0_n = ("g_malloc0_n");
+  II_g_realloc_n = ("g_realloc_n");
+  II_g_try_malloc_n = ("g_try_malloc_n");
+  II_g_try_malloc0_n = ("g_try_malloc0_n");
+  II_g_try_realloc_n = ("g_try_realloc_n");
 }
 
 bool MallocChecker::isMemFunction(const FunctionDecl *FD, ASTContext ) const {
@@ -617,7 +632,10 @@
   FunI == II_g_malloc || FunI == II_g_malloc0 || 
   FunI == II_g_realloc || FunI == II_g_try_malloc || 
   FunI == II_g_try_malloc0 || FunI == II_g_try_realloc ||
-  FunI == II_g_memdup)
+  FunI == II_g_memdup || FunI == II_g_malloc_n || 
+  FunI == II_g_malloc0_n || FunI == II_g_realloc_n || 
+  FunI == II_g_try_malloc_n || FunI == II_g_try_malloc0_n || 
+  FunI == II_g_try_realloc_n)
 return true;
 }
 
@@ -767,6 +785,17 @@
   return None;
 }
 
+SVal MallocChecker::evalMulForBufferSize(CheckerContext , const Expr *Blocks,
+ const Expr *BlockBytes) {
+  SValBuilder  = C.getSValBuilder();
+  SVal BlocksVal = C.getSVal(Blocks);
+  SVal BlockBytesVal = C.getSVal(BlockBytes);
+  ProgramStateRef State = C.getState();
+  SVal TotalSize = SB.evalBinOp(State, BO_Mul, BlocksVal, BlockBytesVal,
+SB.getContext().getSizeType());
+  return TotalSize;
+}
+
 void MallocChecker::checkPostStmt(const CallExpr *CE, CheckerContext ) const {
   if (C.wasInlined)
 return;
@@ -813,10 +842,10 @@
   State = ProcessZeroAllocation(C, CE, 0, State);
 } else if (FunI == II_realloc || FunI == II_g_realloc || 
FunI == II_g_try_realloc) {
-  State = ReallocMem(C, CE, false, State);
+  State = ReallocMemAux(C, CE, false, State);
   State = ProcessZeroAllocation(C, CE, 1, State);
 } else if (FunI == II_reallocf) {
-  State = ReallocMem(C, CE, true, State);
+  State = ReallocMemAux(C, CE, true, State);
   State = ProcessZeroAllocation(C, CE, 1, State);
 } else if (FunI == II_calloc) {
 

[PATCH] D30771: [analyzer] Teach the MallocChecker about Glib API for two arguments

2017-04-25 Thread Leslie Zhai via Phabricator via cfe-commits
xiangzhai added a comment.

Hi Artem,

Could I commit this patch? thanks!

Regards,
Leslie Zhai


Repository:
  rL LLVM

https://reviews.llvm.org/D30771



___
cfe-commits mailing list
cfe-commits@lists.llvm.org
http://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[PATCH] D32269: [Driver] Add iSOFTLinux to GNU ToolChains X86Triple

2017-04-24 Thread Leslie Zhai via Phabricator via cfe-commits
xiangzhai updated this revision to Diff 96497.
xiangzhai added a comment.

Hi Saleem,

Please check whether or not "the correct GCC search dir" for x86_64-isoft-linux 
firstly, please point out my fault, thanks!

And sysroot structure shown as:

  $ tree clang/test/Driver/Inputs/isoft_linux_4_tree
  
  ├── lib
  └── usr
  ├── lib
  │   └── gcc
  │   └── x86_64-isoft-linux
  │   └── 6.3.0
  │   ├── crtbegin.o
  │   ├── crtbeginT.o
  │   └── crtfastmath.o
  └── x86_64-isoft-linux
  └── lib

Regards,
Leslie Zhai


Repository:
  rL LLVM

https://reviews.llvm.org/D32269

Files:
  lib/Driver/ToolChains/Gnu.cpp
  test/Driver/linux-ld.c


Index: test/Driver/linux-ld.c
===
--- test/Driver/linux-ld.c
+++ test/Driver/linux-ld.c
@@ -443,6 +443,33 @@
 // CHECK-BASIC-LIBCXX-C-LINK: "--sysroot=[[SYSROOT]]"
 // CHECK-BASIC-LIBCXX-C-LINK: "-L[[SYSROOT]]/usr/bin/../lib"
 //
+// Check iSOFTLinux v4.0 on x86
+// RUN: %clang -no-canonical-prefixes %s -### -o %t.o 2>&1 \
+// RUN: --target=x86_64-isoft-linux -rtlib=platform \
+// RUN: --gcc-toolchain="" \
+// RUN: --sysroot=%S/Inputs/isoft_linux_4_tree \
+// RUN:   | FileCheck --check-prefix=CHECK-ISOFT-4-X86_64 %s
+// CHECK-ISOFT-4-X86_64--NOT: warning:
+// CHECK-ISOFT-4-X86_64: "{{.*}}ld{{(.exe)?}}" "--sysroot=[[SYSROOT:[^"]+]]"
+// CHECK-ISOFT-4-X86_64: "--eh-frame-hdr"
+// CHECK-ISOFT-4-X86_64: "-m" "elf_x86_64"
+// CHECK-ISOFT-4-X86_64: "-dynamic-linker"
+// CHECK-ISOFT-4-X86_64: 
"{{.*}}/usr/lib/gcc/x86_64-isoft-linux/6.3.0{{/|}}crtbegin.o"
+// CHECK-ISOFT-4-X86_64: "-L[[SYSROOT]]/usr/lib/gcc/x86_64-isoft-linux/6.3.0"
+// CHECK-ISOFT-4-X86_64: 
"-L[[SYSROOT]]/usr/lib/gcc/x86_64-isoft-linux/6.3.0/../../../../x86_64-isoft-linux/lib"
+// CHECK-ISOFT-4-X86_64: 
"-L[[SYSROOT]]/usr/lib/gcc/x86_64-isoft-linux/6.3.0/../../.."
+// CHECK-ISOFT-4-X86_64: "-L[[SYSROOT]]/lib"
+// CHECK-ISOFT-4-X86_64: "-L[[SYSROOT]]/usr/lib"
+// CHECK-ISOFT-4-X86_64: "-lgcc" "--as-needed" "-lgcc_s" "--no-as-needed"
+// CHECK-ISOFT-4-X86_64: "-lc"
+// CHECK-ISOFT-4-X86_64: "-lgcc" "--as-needed" "-lgcc_s" "--no-as-needed"
+//
+// RUN: %clang %s -### -o %t.o 2>&1 --target=x86_64-everest-linux
+// RUN: %clang %s -### -o %t.o 2>&1 --target=x86_64-pure64-linux
+// RUN: %clang %s -### -o %t.o 2>&1 --target=i686-isoft-linux
+// RUN: %clang %s -### -o %t.o 2>&1 --target=i686-everest-linux
+// RUN: %clang %s -### -o %t.o 2>&1 --target=i686-pure64-linux
+//
 // Test a very broken version of multiarch that shipped in Ubuntu 11.04.
 // RUN: %clang -no-canonical-prefixes %s -### -o %t.o 2>&1 \
 // RUN: --target=i386-unknown-linux \
Index: lib/Driver/ToolChains/Gnu.cpp
===
--- lib/Driver/ToolChains/Gnu.cpp
+++ lib/Driver/ToolChains/Gnu.cpp
@@ -1759,6 +1759,9 @@
   static const char *const X86_64LibDirs[] = {"/lib64", "/lib"};
   static const char *const X86_64Triples[] = {
   "x86_64-linux-gnu",   "x86_64-unknown-linux-gnu",
+  "x86_64-isoft-linux", "x86_64-isoft-linux-gnu",
+  "x86_64-everest-linux",   "x86_64-everest-linux-gnu",
+  "x86_64-pure64-linux","x86_64-pure64-linux-gnu",
   "x86_64-pc-linux-gnu","x86_64-redhat-linux6E",
   "x86_64-redhat-linux","x86_64-suse-linux",
   "x86_64-manbo-linux-gnu", "x86_64-linux-gnu",
@@ -1768,6 +1771,9 @@
   static const char *const X86LibDirs[] = {"/lib32", "/lib"};
   static const char *const X86Triples[] = {
   "i686-linux-gnu",   "i686-pc-linux-gnu", "i486-linux-gnu",
+  "i686-isoft-linux", "i686-isoft-linux-gnu",
+  "i686-everest-linux",   "i686-everest-linux-gnu",
+  "i686-pure64-linux","i686-pure64-linux-gnu",
   "i386-linux-gnu",   "i386-redhat-linux6E",   "i686-redhat-linux",
   "i586-redhat-linux","i386-redhat-linux", "i586-suse-linux",
   "i486-slackware-linux", "i686-montavista-linux", "i686-linux-android",


Index: test/Driver/linux-ld.c
===
--- test/Driver/linux-ld.c
+++ test/Driver/linux-ld.c
@@ -443,6 +443,33 @@
 // CHECK-BASIC-LIBCXX-C-LINK: "--sysroot=[[SYSROOT]]"
 // CHECK-BASIC-LIBCXX-C-LINK: "-L[[SYSROOT]]/usr/bin/../lib"
 //
+// Check iSOFTLinux v4.0 on x86
+// RUN: %clang -no-canonical-prefixes %s -### -o %t.o 2>&1 \
+// RUN: --target=x86_64-isoft-linux -rtlib=platform \
+// RUN: --gcc-toolchain="" \
+// RUN: --sysroot=%S/Inputs/isoft_linux_4_tree \
+// RUN:   | FileCheck --check-prefix=CHECK-ISOFT-4-X86_64 %s
+// CHECK-ISOFT-4-X86_64--NOT: warning:
+// CHECK-ISOFT-4-X86_64: "{{.*}}ld{{(.exe)?}}" "--sysroot=[[SYSROOT:[^"]+]]"
+// CHECK-ISOFT-4-X86_64: "--eh-frame-hdr"
+// CHECK-ISOFT-4-X86_64: "-m" "elf_x86_64"
+// CHECK-ISOFT-4-X86_64: "-dynamic-linker"
+// CHECK-ISOFT-4-X86_64: "{{.*}}/usr/lib/gcc/x86_64-isoft-linux/6.3.0{{/|}}crtbegin.o"

[PATCH] D32269: [Driver] Add iSOFTLinux to GNU ToolChains X86Triple

2017-04-24 Thread Leslie Zhai via Phabricator via cfe-commits
xiangzhai added a comment.

Hi Saleem,

Thanks for pointing out my fault, I will update my patch to add, for example:

  -L[[SYSROOT]]/usr/lib/gcc/x86_64-isoft-linux/6.3.1

to the testcase.

Regards,
Leslie Zhai


Repository:
  rL LLVM

https://reviews.llvm.org/D32269



___
cfe-commits mailing list
cfe-commits@lists.llvm.org
http://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[PATCH] D31868: [analyzer] Check NULL pointer dereference issue for memset function

2017-04-23 Thread Leslie Zhai via Phabricator via cfe-commits
xiangzhai updated this revision to Diff 96344.
xiangzhai added a comment.

Hi Artem,

Because `memcpy` checked NULL pointer dereference for `src`:

  state = checkNonNull(C, state, Source, srcVal);
  ...

so such testcase can not point out my fault:

  void f15 () { 
 
int *x = malloc(sizeof(int));   
 
memcpy(x, 0, sizeof(int)); // expected-warning {{Null pointer argument in 
call to memory copy function}}
int n = 1 / *x; 
 
free(x);
 
  }

And I have no idea how to copy `RetVal` to Mem `s`:

  if (StateSameSize) {  
  
SVal ConstVal = State->getSVal(Const, LCtx);
  
State = State->BindExpr(CE, LCtx, RetVal);  
  
// Actually bind the second argument value to the buffer.   
  
State = State->bindDefault(RetVal, ConstVal, LCtx); 
  
// FIXME: Copy to Mem   
  
const MemRegion *MR = RetVal.getAsRegion(); 
  
if (!MR)
  
  return;   
  
MR = MR->StripCasts();  
  
if (const TypedValueRegion *TVR = MR->getAs()) {  
  
  MemVal = SB.makeLazyCompoundVal(StoreRef(State->getStore(),   
  
  State->getStateManager().getStoreManager()), TVR);
  
  State = State->BindExpr(CE, LCtx, MemVal);
  
}   
  
C.addTransition(State); 
  
  }

Please give me some advice, thanks a lot!

Regards,
Leslie Zhai


Repository:
  rL LLVM

https://reviews.llvm.org/D31868

Files:
  lib/StaticAnalyzer/Checkers/CStringChecker.cpp
  test/Analysis/null-deref-ps-region.c

Index: test/Analysis/null-deref-ps-region.c
===
--- test/Analysis/null-deref-ps-region.c
+++ test/Analysis/null-deref-ps-region.c
@@ -1,6 +1,11 @@
-// RUN: %clang_analyze_cc1 -analyzer-checker=core,alpha.core -std=gnu99 -analyzer-store=region -verify %s
-// expected-no-diagnostics
+// RUN: %clang_analyze_cc1 -analyzer-checker=core,alpha.core,unix,alpha.unix -std=gnu99 -analyzer-store=region -verify %s
 
+#include "Inputs/system-header-simulator.h"
+
+typedef __typeof(sizeof(int)) size_t;
+void *memset(void *__s, int __c, size_t __n);
+void *malloc(size_t __size);
+void free(void *__ptr);
 
 // The store for 'a[1]' should not be removed mistakenly. SymbolicRegions may
 // also be live roots.
@@ -13,3 +18,69 @@
 i = *p; // no-warning
   }
 }
+
+void f15 () {
+  int *x = malloc(sizeof(int));
+  memcpy(x, 0, sizeof(int)); // expected-warning {{Null pointer argument in call to memory copy function}}
+  int n = 1 / *x;
+  free(x);
+}
+
+void foo() {
+  int *x = malloc(sizeof(int));
+  int *r = memset(x, 0, sizeof(int));
+  int n = 1 / *r; // expected-warning {{Division by zero}}
+  free(x);
+}
+
+void foo2() {
+  int *x = malloc(sizeof(int));
+  memset(x, 0, sizeof(int));
+  int n = 1 / *x;
+  free(x);
+}
+
+void bar() {
+  int *x = malloc(sizeof(int));
+  memset(x, 0, 1);
+  int n = 1 / *x; // no-warning
+  free(x);
+}
+
+void f531() {
+  int *x = 0;
+  memset(x, 0, 1); // expected-warning {{Null pointer argument in call to memory set function}}
+}
+
+void f61() {
+  char buf[13];
+  memset(buf, 0, 1); // no-warning
+}
+
+void f611() {
+  char *buf = (char *)malloc(13);
+  memset(buf, 0, 1); // no-warning
+  free(buf);
+}
+
+void f66() {
+  char buf[1];
+  memset(buf, 0, 1024); // expected-warning {{Memory set function accesses out-of-bound array element}}
+}
+
+void f666() {
+  char *buf = (char *)malloc(1);
+  memset(buf, 0, 1024); // expected-warning {{Memory set function accesses out-of-bound array element}}
+  free(buf);
+}
+
+void f77() {
+  char buf[1];
+  memset(buf, 0, sizeof(buf)); // no-warning
+}
+
+void f777() {
+  char *buf = (char *)malloc(1);
+  memset(buf, 0, 1); // no-warning
+  free(buf);
+}
Index: lib/StaticAnalyzer/Checkers/CStringChecker.cpp
===
--- lib/StaticAnalyzer/Checkers/CStringChecker.cpp
+++ lib/StaticAnalyzer/Checkers/CStringChecker.cpp
@@ -120,6 +120,7 @@
   void evalStdCopy(CheckerContext , const CallExpr *CE) const;
   void evalStdCopyBackward(CheckerContext , const CallExpr *CE) const;
   void 

[PATCH] D30771: [analyzer] Teach the MallocChecker about Glib API for two arguments

2017-04-21 Thread Leslie Zhai via Phabricator via cfe-commits
xiangzhai added a comment.

Never mind :)


Repository:
  rL LLVM

https://reviews.llvm.org/D30771



___
cfe-commits mailing list
cfe-commits@lists.llvm.org
http://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[PATCH] D30771: [analyzer] Teach the MallocChecker about Glib API for two arguments

2017-04-21 Thread Leslie Zhai via Phabricator via cfe-commits
xiangzhai updated this revision to Diff 96101.
xiangzhai added a comment.

Further reduce redundant code.


Repository:
  rL LLVM

https://reviews.llvm.org/D30771

Files:
  lib/StaticAnalyzer/Checkers/MallocChecker.cpp
  test/Analysis/gmalloc.c

Index: test/Analysis/gmalloc.c
===
--- test/Analysis/gmalloc.c
+++ test/Analysis/gmalloc.c
@@ -13,6 +13,12 @@
 gpointer g_try_malloc(gsize n_bytes);
 gpointer g_try_malloc0(gsize n_bytes);
 gpointer g_try_realloc(gpointer mem, gsize n_bytes);
+gpointer g_malloc_n(gsize n_blocks, gsize n_block_bytes);
+gpointer g_malloc0_n(gsize n_blocks, gsize n_block_bytes);
+gpointer g_realloc_n(gpointer mem, gsize n_blocks, gsize n_block_bytes);
+gpointer g_try_malloc_n(gsize n_blocks, gsize n_block_bytes);
+gpointer g_try_malloc0_n(gsize n_blocks, gsize n_block_bytes);
+gpointer g_try_realloc_n(gpointer mem, gsize n_blocks, gsize n_block_bytes);
 void g_free(gpointer mem);
 gpointer g_memdup(gconstpointer mem, guint byte_size);
 
@@ -25,6 +31,12 @@
   gpointer g3 = g_try_malloc(n_bytes);
   gpointer g4 = g_try_malloc0(n_bytes);
   g3 = g_try_realloc(g3, n_bytes * 2);
+  gpointer g5 = g_malloc_n(n_bytes, sizeof(char));
+  gpointer g6 = g_malloc0_n(n_bytes, sizeof(char));
+  g5 = g_realloc_n(g5, n_bytes * 2, sizeof(char));
+  gpointer g7 = g_try_malloc_n(n_bytes, sizeof(char));
+  gpointer g8 = g_try_malloc0_n(n_bytes, sizeof(char));
+  g7 = g_try_realloc_n(g7, n_bytes * 2, sizeof(char));
 
   g_free(g1);
   g_free(g2);
@@ -38,6 +50,12 @@
   gpointer g3 = g_try_malloc(n_bytes);
   gpointer g4 = g_try_malloc0(n_bytes);
   g3 = g_try_realloc(g3, n_bytes * 2);
+  gpointer g5 = g_malloc_n(n_bytes, sizeof(char));
+  gpointer g6 = g_malloc0_n(n_bytes, sizeof(char));
+  g5 = g_realloc_n(g5, n_bytes * 2, sizeof(char));
+  gpointer g7 = g_try_malloc_n(n_bytes, sizeof(char));
+  gpointer g8 = g_try_malloc0_n(n_bytes, sizeof(char));
+  g7 = g_try_realloc_n(g7, n_bytes * 2, sizeof(char));
 
   g_free(g1);
   g_free(g2);
@@ -52,8 +70,100 @@
   gpointer g3 = g_try_malloc(n_bytes);
   gpointer g4 = g_try_malloc0(n_bytes);
   g3 = g_try_realloc(g3, n_bytes * 2); // expected-warning{{Potential leak of memory pointed to by 'g4'}}
+  gpointer g5 = g_malloc_n(n_bytes, sizeof(char));
+  gpointer g6 = g_malloc0_n(n_bytes, sizeof(char));
+  g5 = g_realloc_n(g5, n_bytes * 2, sizeof(char)); // expected-warning{{Potential leak of memory pointed to by 'g6'}}
+  gpointer g7 = g_try_malloc_n(n_bytes, sizeof(char)); // expected-warning{{Potential leak of memory pointed to by 'g5'}}
+  gpointer g8 = g_try_malloc0_n(n_bytes, sizeof(char));
+  g7 = g_try_realloc_n(g7, n_bytes * 2, sizeof(char)); // expected-warning{{Potential leak of memory pointed to by 'g8'}}
+
+  g_free(g1); // expected-warning{{Potential leak of memory pointed to by 'g7'}}
+  g_free(g2);
+  g_free(g3);
+}
+
+void f4() {
+  gpointer g1 = g_malloc(n_bytes);
+  gpointer g2 = g_malloc0(n_bytes);
+  g1 = g_realloc(g1, n_bytes * 2);
+  gpointer g3 = g_try_malloc(n_bytes);
+  gpointer g4 = g_try_malloc0(n_bytes);
+  g3 = g_try_realloc(g3, n_bytes * 2);
+  gpointer g5 = g_malloc_n(n_bytes, sizeof(char));
+  gpointer g6 = g_malloc0_n(n_bytes, sizeof(char));
+  g5 = g_realloc_n(g5, n_bytes * 2, sizeof(char)); // expected-warning{{Potential leak of memory pointed to by 'g6'}}
+  gpointer g7 = g_try_malloc_n(n_bytes, sizeof(char)); // expected-warning{{Potential leak of memory pointed to by 'g5'}}
+  gpointer g8 = g_try_malloc0_n(n_bytes, sizeof(char));
+  g7 = g_try_realloc_n(g7, n_bytes * 2, sizeof(char)); // expected-warning{{Potential leak of memory pointed to by 'g8'}}
+
+  g_free(g1); // expected-warning{{Potential leak of memory pointed to by 'g7'}}
+  g_free(g2);
+  g_free(g3);
+  g_free(g4);
+}
+
+void f5() {
+  gpointer g1 = g_malloc(n_bytes);
+  gpointer g2 = g_malloc0(n_bytes);
+  g1 = g_realloc(g1, n_bytes * 2);
+  gpointer g3 = g_try_malloc(n_bytes);
+  gpointer g4 = g_try_malloc0(n_bytes);
+  g3 = g_try_realloc(g3, n_bytes * 2);
+  gpointer g5 = g_malloc_n(n_bytes, sizeof(char));
+  gpointer g6 = g_malloc0_n(n_bytes, sizeof(char));
+  g5 = g_realloc_n(g5, n_bytes * 2, sizeof(char)); // expected-warning{{Potential leak of memory pointed to by 'g6'}}
+  gpointer g7 = g_try_malloc_n(n_bytes, sizeof(char));
+  gpointer g8 = g_try_malloc0_n(n_bytes, sizeof(char));
+  g7 = g_try_realloc_n(g7, n_bytes * 2, sizeof(char)); // expected-warning{{Potential leak of memory pointed to by 'g8'}}
+
+  g_free(g1); // expected-warning{{Potential leak of memory pointed to by 'g7'}}
+  g_free(g2);
+  g_free(g3);
+  g_free(g4);
+  g_free(g5);
+}
+
+void f6() {
+  gpointer g1 = g_malloc(n_bytes);
+  gpointer g2 = g_malloc0(n_bytes);
+  g1 = g_realloc(g1, n_bytes * 2);
+  gpointer g3 = g_try_malloc(n_bytes);
+  gpointer g4 = g_try_malloc0(n_bytes);
+  g3 = g_try_realloc(g3, n_bytes * 2);
+  gpointer g5 = g_malloc_n(n_bytes, sizeof(char));
+  gpointer g6 = g_malloc0_n(n_bytes, sizeof(char));
+  g5 = 

[PATCH] D32269: [Driver] Add iSOFTLinux to GNU ToolChains X86Triple

2017-04-20 Thread Leslie Zhai via Phabricator via cfe-commits
xiangzhai updated this revision to Diff 96088.
xiangzhai added a comment.

Hi Richard,

Thanks for your review!

I updated my patch as you suggested: add some test coverage for these triples, 
and I run `make check-clang-driver` for verification, please point out my 
fault, thanks!

Regards,
Leslie Zhai


Repository:
  rL LLVM

https://reviews.llvm.org/D32269

Files:
  lib/Driver/ToolChains/Gnu.cpp
  test/Driver/linux-ld.c


Index: test/Driver/linux-ld.c
===
--- test/Driver/linux-ld.c
+++ test/Driver/linux-ld.c
@@ -443,6 +443,14 @@
 // CHECK-BASIC-LIBCXX-C-LINK: "--sysroot=[[SYSROOT]]"
 // CHECK-BASIC-LIBCXX-C-LINK: "-L[[SYSROOT]]/usr/bin/../lib"
 //
+// Check iSOFTLinux v4.0 on x86
+// RUN: %clang %s -### -o %t.o 2>&1 --target=x86_64-isoft-linux
+// RUN: %clang %s -### -o %t.o 2>&1 --target=x86_64-everest-linux
+// RUN: %clang %s -### -o %t.o 2>&1 --target=x86_64-pure64-linux
+// RUN: %clang %s -### -o %t.o 2>&1 --target=i686-isoft-linux
+// RUN: %clang %s -### -o %t.o 2>&1 --target=i686-everest-linux
+// RUN: %clang %s -### -o %t.o 2>&1 --target=i686-pure64-linux
+//
 // Test a very broken version of multiarch that shipped in Ubuntu 11.04.
 // RUN: %clang -no-canonical-prefixes %s -### -o %t.o 2>&1 \
 // RUN: --target=i386-unknown-linux \
Index: lib/Driver/ToolChains/Gnu.cpp
===
--- lib/Driver/ToolChains/Gnu.cpp
+++ lib/Driver/ToolChains/Gnu.cpp
@@ -1757,6 +1757,9 @@
   static const char *const X86_64LibDirs[] = {"/lib64", "/lib"};
   static const char *const X86_64Triples[] = {
   "x86_64-linux-gnu",   "x86_64-unknown-linux-gnu",
+  "x86_64-isoft-linux", "x86_64-isoft-linux-gnu",
+  "x86_64-everest-linux",   "x86_64-everest-linux-gnu",
+  "x86_64-pure64-linux","x86_64-pure64-linux-gnu",
   "x86_64-pc-linux-gnu","x86_64-redhat-linux6E",
   "x86_64-redhat-linux","x86_64-suse-linux",
   "x86_64-manbo-linux-gnu", "x86_64-linux-gnu",
@@ -1766,6 +1769,9 @@
   static const char *const X86LibDirs[] = {"/lib32", "/lib"};
   static const char *const X86Triples[] = {
   "i686-linux-gnu",   "i686-pc-linux-gnu", "i486-linux-gnu",
+  "i686-isoft-linux", "i686-isoft-linux-gnu",
+  "i686-everest-linux",   "i686-everest-linux-gnu",
+  "i686-pure64-linux","i686-pure64-linux-gnu",
   "i386-linux-gnu",   "i386-redhat-linux6E",   "i686-redhat-linux",
   "i586-redhat-linux","i386-redhat-linux", "i586-suse-linux",
   "i486-slackware-linux", "i686-montavista-linux", "i686-linux-android",


Index: test/Driver/linux-ld.c
===
--- test/Driver/linux-ld.c
+++ test/Driver/linux-ld.c
@@ -443,6 +443,14 @@
 // CHECK-BASIC-LIBCXX-C-LINK: "--sysroot=[[SYSROOT]]"
 // CHECK-BASIC-LIBCXX-C-LINK: "-L[[SYSROOT]]/usr/bin/../lib"
 //
+// Check iSOFTLinux v4.0 on x86
+// RUN: %clang %s -### -o %t.o 2>&1 --target=x86_64-isoft-linux
+// RUN: %clang %s -### -o %t.o 2>&1 --target=x86_64-everest-linux
+// RUN: %clang %s -### -o %t.o 2>&1 --target=x86_64-pure64-linux
+// RUN: %clang %s -### -o %t.o 2>&1 --target=i686-isoft-linux
+// RUN: %clang %s -### -o %t.o 2>&1 --target=i686-everest-linux
+// RUN: %clang %s -### -o %t.o 2>&1 --target=i686-pure64-linux
+//
 // Test a very broken version of multiarch that shipped in Ubuntu 11.04.
 // RUN: %clang -no-canonical-prefixes %s -### -o %t.o 2>&1 \
 // RUN: --target=i386-unknown-linux \
Index: lib/Driver/ToolChains/Gnu.cpp
===
--- lib/Driver/ToolChains/Gnu.cpp
+++ lib/Driver/ToolChains/Gnu.cpp
@@ -1757,6 +1757,9 @@
   static const char *const X86_64LibDirs[] = {"/lib64", "/lib"};
   static const char *const X86_64Triples[] = {
   "x86_64-linux-gnu",   "x86_64-unknown-linux-gnu",
+  "x86_64-isoft-linux", "x86_64-isoft-linux-gnu",
+  "x86_64-everest-linux",   "x86_64-everest-linux-gnu",
+  "x86_64-pure64-linux","x86_64-pure64-linux-gnu",
   "x86_64-pc-linux-gnu","x86_64-redhat-linux6E",
   "x86_64-redhat-linux","x86_64-suse-linux",
   "x86_64-manbo-linux-gnu", "x86_64-linux-gnu",
@@ -1766,6 +1769,9 @@
   static const char *const X86LibDirs[] = {"/lib32", "/lib"};
   static const char *const X86Triples[] = {
   "i686-linux-gnu",   "i686-pc-linux-gnu", "i486-linux-gnu",
+  "i686-isoft-linux", "i686-isoft-linux-gnu",
+  "i686-everest-linux",   "i686-everest-linux-gnu",
+  "i686-pure64-linux","i686-pure64-linux-gnu",
   "i386-linux-gnu",   "i386-redhat-linux6E",   "i686-redhat-linux",
   "i586-redhat-linux","i386-redhat-linux", "i586-suse-linux",
   "i486-slackware-linux", "i686-montavista-linux", "i686-linux-android",
___
cfe-commits mailing list
cfe-commits@lists.llvm.org

[PATCH] D30771: [analyzer] Teach the MallocChecker about Glib API for two arguments

2017-04-20 Thread Leslie Zhai via Phabricator via cfe-commits
xiangzhai updated this revision to Diff 96084.
xiangzhai added a comment.

Further reduce redundant code.


Repository:
  rL LLVM

https://reviews.llvm.org/D30771

Files:
  lib/StaticAnalyzer/Checkers/MallocChecker.cpp
  test/Analysis/gmalloc.c

Index: test/Analysis/gmalloc.c
===
--- test/Analysis/gmalloc.c
+++ test/Analysis/gmalloc.c
@@ -13,6 +13,12 @@
 gpointer g_try_malloc(gsize n_bytes);
 gpointer g_try_malloc0(gsize n_bytes);
 gpointer g_try_realloc(gpointer mem, gsize n_bytes);
+gpointer g_malloc_n(gsize n_blocks, gsize n_block_bytes);
+gpointer g_malloc0_n(gsize n_blocks, gsize n_block_bytes);
+gpointer g_realloc_n(gpointer mem, gsize n_blocks, gsize n_block_bytes);
+gpointer g_try_malloc_n(gsize n_blocks, gsize n_block_bytes);
+gpointer g_try_malloc0_n(gsize n_blocks, gsize n_block_bytes);
+gpointer g_try_realloc_n(gpointer mem, gsize n_blocks, gsize n_block_bytes);
 void g_free(gpointer mem);
 gpointer g_memdup(gconstpointer mem, guint byte_size);
 
@@ -25,6 +31,12 @@
   gpointer g3 = g_try_malloc(n_bytes);
   gpointer g4 = g_try_malloc0(n_bytes);
   g3 = g_try_realloc(g3, n_bytes * 2);
+  gpointer g5 = g_malloc_n(n_bytes, sizeof(char));
+  gpointer g6 = g_malloc0_n(n_bytes, sizeof(char));
+  g5 = g_realloc_n(g5, n_bytes * 2, sizeof(char));
+  gpointer g7 = g_try_malloc_n(n_bytes, sizeof(char));
+  gpointer g8 = g_try_malloc0_n(n_bytes, sizeof(char));
+  g7 = g_try_realloc_n(g7, n_bytes * 2, sizeof(char));
 
   g_free(g1);
   g_free(g2);
@@ -38,6 +50,12 @@
   gpointer g3 = g_try_malloc(n_bytes);
   gpointer g4 = g_try_malloc0(n_bytes);
   g3 = g_try_realloc(g3, n_bytes * 2);
+  gpointer g5 = g_malloc_n(n_bytes, sizeof(char));
+  gpointer g6 = g_malloc0_n(n_bytes, sizeof(char));
+  g5 = g_realloc_n(g5, n_bytes * 2, sizeof(char));
+  gpointer g7 = g_try_malloc_n(n_bytes, sizeof(char));
+  gpointer g8 = g_try_malloc0_n(n_bytes, sizeof(char));
+  g7 = g_try_realloc_n(g7, n_bytes * 2, sizeof(char));
 
   g_free(g1);
   g_free(g2);
@@ -52,8 +70,100 @@
   gpointer g3 = g_try_malloc(n_bytes);
   gpointer g4 = g_try_malloc0(n_bytes);
   g3 = g_try_realloc(g3, n_bytes * 2); // expected-warning{{Potential leak of memory pointed to by 'g4'}}
+  gpointer g5 = g_malloc_n(n_bytes, sizeof(char));
+  gpointer g6 = g_malloc0_n(n_bytes, sizeof(char));
+  g5 = g_realloc_n(g5, n_bytes * 2, sizeof(char)); // expected-warning{{Potential leak of memory pointed to by 'g6'}}
+  gpointer g7 = g_try_malloc_n(n_bytes, sizeof(char)); // expected-warning{{Potential leak of memory pointed to by 'g5'}}
+  gpointer g8 = g_try_malloc0_n(n_bytes, sizeof(char));
+  g7 = g_try_realloc_n(g7, n_bytes * 2, sizeof(char)); // expected-warning{{Potential leak of memory pointed to by 'g8'}}
+
+  g_free(g1); // expected-warning{{Potential leak of memory pointed to by 'g7'}}
+  g_free(g2);
+  g_free(g3);
+}
+
+void f4() {
+  gpointer g1 = g_malloc(n_bytes);
+  gpointer g2 = g_malloc0(n_bytes);
+  g1 = g_realloc(g1, n_bytes * 2);
+  gpointer g3 = g_try_malloc(n_bytes);
+  gpointer g4 = g_try_malloc0(n_bytes);
+  g3 = g_try_realloc(g3, n_bytes * 2);
+  gpointer g5 = g_malloc_n(n_bytes, sizeof(char));
+  gpointer g6 = g_malloc0_n(n_bytes, sizeof(char));
+  g5 = g_realloc_n(g5, n_bytes * 2, sizeof(char)); // expected-warning{{Potential leak of memory pointed to by 'g6'}}
+  gpointer g7 = g_try_malloc_n(n_bytes, sizeof(char)); // expected-warning{{Potential leak of memory pointed to by 'g5'}}
+  gpointer g8 = g_try_malloc0_n(n_bytes, sizeof(char));
+  g7 = g_try_realloc_n(g7, n_bytes * 2, sizeof(char)); // expected-warning{{Potential leak of memory pointed to by 'g8'}}
+
+  g_free(g1); // expected-warning{{Potential leak of memory pointed to by 'g7'}}
+  g_free(g2);
+  g_free(g3);
+  g_free(g4);
+}
+
+void f5() {
+  gpointer g1 = g_malloc(n_bytes);
+  gpointer g2 = g_malloc0(n_bytes);
+  g1 = g_realloc(g1, n_bytes * 2);
+  gpointer g3 = g_try_malloc(n_bytes);
+  gpointer g4 = g_try_malloc0(n_bytes);
+  g3 = g_try_realloc(g3, n_bytes * 2);
+  gpointer g5 = g_malloc_n(n_bytes, sizeof(char));
+  gpointer g6 = g_malloc0_n(n_bytes, sizeof(char));
+  g5 = g_realloc_n(g5, n_bytes * 2, sizeof(char)); // expected-warning{{Potential leak of memory pointed to by 'g6'}}
+  gpointer g7 = g_try_malloc_n(n_bytes, sizeof(char));
+  gpointer g8 = g_try_malloc0_n(n_bytes, sizeof(char));
+  g7 = g_try_realloc_n(g7, n_bytes * 2, sizeof(char)); // expected-warning{{Potential leak of memory pointed to by 'g8'}}
+
+  g_free(g1); // expected-warning{{Potential leak of memory pointed to by 'g7'}}
+  g_free(g2);
+  g_free(g3);
+  g_free(g4);
+  g_free(g5);
+}
+
+void f6() {
+  gpointer g1 = g_malloc(n_bytes);
+  gpointer g2 = g_malloc0(n_bytes);
+  g1 = g_realloc(g1, n_bytes * 2);
+  gpointer g3 = g_try_malloc(n_bytes);
+  gpointer g4 = g_try_malloc0(n_bytes);
+  g3 = g_try_realloc(g3, n_bytes * 2);
+  gpointer g5 = g_malloc_n(n_bytes, sizeof(char));
+  gpointer g6 = g_malloc0_n(n_bytes, sizeof(char));
+  g5 = 

[PATCH] D30771: [analyzer] Teach the MallocChecker about Glib API for two arguments

2017-04-20 Thread Leslie Zhai via Phabricator via cfe-commits
xiangzhai added inline comments.



Comment at: lib/StaticAnalyzer/Checkers/MallocChecker.cpp:337
+   const Expr *BlockBytes,
+   ProgramStateRef State);
   static ProgramStateRef CallocMem(CheckerContext , const CallExpr *CE,

danielmarjamaki wrote:
> Thanks for renaming the function I am happy now with that name. :-)
> 
> hmm.. if you have CheckerContext parameter already then ProgramStateRef 
> parameter seems redundant. You should be able to use C.getState().
> 
> However looking at surrounding code it seems you can provide ProgramStateRef 
> for consistency.
> 
> I don't have a strong opinion, but I would remove this State.
> 
I will update it tomorrow! I have to gotta home to look after my kid :)


Repository:
  rL LLVM

https://reviews.llvm.org/D30771



___
cfe-commits mailing list
cfe-commits@lists.llvm.org
http://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[PATCH] D30771: [analyzer] Teach the MallocChecker about Glib API for two arguments

2017-04-20 Thread Leslie Zhai via Phabricator via cfe-commits
xiangzhai marked an inline comment as done.
xiangzhai added inline comments.



Comment at: lib/StaticAnalyzer/Checkers/MallocChecker.cpp:788
 
+SVal MallocChecker::SValBinMulOp(CheckerContext , const Expr *Blocks,
+ const Expr *BlockBytes, ProgramStateRef 
State) {

danielmarjamaki wrote:
> danielmarjamaki wrote:
> > I have the feeling this should be renamed. Since its purpose is to 
> > calculate the total size maybe MallocChecker::calculateBufferSize()
> please respond to comments by clicking on the "Reply" button for the comment. 
> So your responce will be shown near my comment.
> 
> yes it can be hard to figure out a good name.
> 
> alright, you didn't like my suggestion then let's skip that.
> 
> do you need to start the name with "sval". does that indicate that a "sval" 
> is returned? then that would be unusual imho.
> 
> I guess I don't have a strong opinion but I would also remove "Bin". The 
> "Mul" says that imho.
> 
> how about evalMulForBufferSize?
> 
renamed to `evalMulForBufferSize` :)


Repository:
  rL LLVM

https://reviews.llvm.org/D30771



___
cfe-commits mailing list
cfe-commits@lists.llvm.org
http://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[PATCH] D30771: [analyzer] Teach the MallocChecker about Glib API for two arguments

2017-04-20 Thread Leslie Zhai via Phabricator via cfe-commits
xiangzhai updated this revision to Diff 95894.
xiangzhai added a comment.

`SValBinMulOp` -> `evalMulForBufferSize`


Repository:
  rL LLVM

https://reviews.llvm.org/D30771

Files:
  lib/StaticAnalyzer/Checkers/MallocChecker.cpp
  test/Analysis/gmalloc.c

Index: test/Analysis/gmalloc.c
===
--- test/Analysis/gmalloc.c
+++ test/Analysis/gmalloc.c
@@ -13,6 +13,12 @@
 gpointer g_try_malloc(gsize n_bytes);
 gpointer g_try_malloc0(gsize n_bytes);
 gpointer g_try_realloc(gpointer mem, gsize n_bytes);
+gpointer g_malloc_n(gsize n_blocks, gsize n_block_bytes);
+gpointer g_malloc0_n(gsize n_blocks, gsize n_block_bytes);
+gpointer g_realloc_n(gpointer mem, gsize n_blocks, gsize n_block_bytes);
+gpointer g_try_malloc_n(gsize n_blocks, gsize n_block_bytes);
+gpointer g_try_malloc0_n(gsize n_blocks, gsize n_block_bytes);
+gpointer g_try_realloc_n(gpointer mem, gsize n_blocks, gsize n_block_bytes);
 void g_free(gpointer mem);
 gpointer g_memdup(gconstpointer mem, guint byte_size);
 
@@ -25,6 +31,12 @@
   gpointer g3 = g_try_malloc(n_bytes);
   gpointer g4 = g_try_malloc0(n_bytes);
   g3 = g_try_realloc(g3, n_bytes * 2);
+  gpointer g5 = g_malloc_n(n_bytes, sizeof(char));
+  gpointer g6 = g_malloc0_n(n_bytes, sizeof(char));
+  g5 = g_realloc_n(g5, n_bytes * 2, sizeof(char));
+  gpointer g7 = g_try_malloc_n(n_bytes, sizeof(char));
+  gpointer g8 = g_try_malloc0_n(n_bytes, sizeof(char));
+  g7 = g_try_realloc_n(g7, n_bytes * 2, sizeof(char));
 
   g_free(g1);
   g_free(g2);
@@ -38,6 +50,12 @@
   gpointer g3 = g_try_malloc(n_bytes);
   gpointer g4 = g_try_malloc0(n_bytes);
   g3 = g_try_realloc(g3, n_bytes * 2);
+  gpointer g5 = g_malloc_n(n_bytes, sizeof(char));
+  gpointer g6 = g_malloc0_n(n_bytes, sizeof(char));
+  g5 = g_realloc_n(g5, n_bytes * 2, sizeof(char));
+  gpointer g7 = g_try_malloc_n(n_bytes, sizeof(char));
+  gpointer g8 = g_try_malloc0_n(n_bytes, sizeof(char));
+  g7 = g_try_realloc_n(g7, n_bytes * 2, sizeof(char));
 
   g_free(g1);
   g_free(g2);
@@ -52,8 +70,100 @@
   gpointer g3 = g_try_malloc(n_bytes);
   gpointer g4 = g_try_malloc0(n_bytes);
   g3 = g_try_realloc(g3, n_bytes * 2); // expected-warning{{Potential leak of memory pointed to by 'g4'}}
+  gpointer g5 = g_malloc_n(n_bytes, sizeof(char));
+  gpointer g6 = g_malloc0_n(n_bytes, sizeof(char));
+  g5 = g_realloc_n(g5, n_bytes * 2, sizeof(char)); // expected-warning{{Potential leak of memory pointed to by 'g6'}}
+  gpointer g7 = g_try_malloc_n(n_bytes, sizeof(char)); // expected-warning{{Potential leak of memory pointed to by 'g5'}}
+  gpointer g8 = g_try_malloc0_n(n_bytes, sizeof(char));
+  g7 = g_try_realloc_n(g7, n_bytes * 2, sizeof(char)); // expected-warning{{Potential leak of memory pointed to by 'g8'}}
+
+  g_free(g1); // expected-warning{{Potential leak of memory pointed to by 'g7'}}
+  g_free(g2);
+  g_free(g3);
+}
+
+void f4() {
+  gpointer g1 = g_malloc(n_bytes);
+  gpointer g2 = g_malloc0(n_bytes);
+  g1 = g_realloc(g1, n_bytes * 2);
+  gpointer g3 = g_try_malloc(n_bytes);
+  gpointer g4 = g_try_malloc0(n_bytes);
+  g3 = g_try_realloc(g3, n_bytes * 2);
+  gpointer g5 = g_malloc_n(n_bytes, sizeof(char));
+  gpointer g6 = g_malloc0_n(n_bytes, sizeof(char));
+  g5 = g_realloc_n(g5, n_bytes * 2, sizeof(char)); // expected-warning{{Potential leak of memory pointed to by 'g6'}}
+  gpointer g7 = g_try_malloc_n(n_bytes, sizeof(char)); // expected-warning{{Potential leak of memory pointed to by 'g5'}}
+  gpointer g8 = g_try_malloc0_n(n_bytes, sizeof(char));
+  g7 = g_try_realloc_n(g7, n_bytes * 2, sizeof(char)); // expected-warning{{Potential leak of memory pointed to by 'g8'}}
+
+  g_free(g1); // expected-warning{{Potential leak of memory pointed to by 'g7'}}
+  g_free(g2);
+  g_free(g3);
+  g_free(g4);
+}
+
+void f5() {
+  gpointer g1 = g_malloc(n_bytes);
+  gpointer g2 = g_malloc0(n_bytes);
+  g1 = g_realloc(g1, n_bytes * 2);
+  gpointer g3 = g_try_malloc(n_bytes);
+  gpointer g4 = g_try_malloc0(n_bytes);
+  g3 = g_try_realloc(g3, n_bytes * 2);
+  gpointer g5 = g_malloc_n(n_bytes, sizeof(char));
+  gpointer g6 = g_malloc0_n(n_bytes, sizeof(char));
+  g5 = g_realloc_n(g5, n_bytes * 2, sizeof(char)); // expected-warning{{Potential leak of memory pointed to by 'g6'}}
+  gpointer g7 = g_try_malloc_n(n_bytes, sizeof(char));
+  gpointer g8 = g_try_malloc0_n(n_bytes, sizeof(char));
+  g7 = g_try_realloc_n(g7, n_bytes * 2, sizeof(char)); // expected-warning{{Potential leak of memory pointed to by 'g8'}}
+
+  g_free(g1); // expected-warning{{Potential leak of memory pointed to by 'g7'}}
+  g_free(g2);
+  g_free(g3);
+  g_free(g4);
+  g_free(g5);
+}
+
+void f6() {
+  gpointer g1 = g_malloc(n_bytes);
+  gpointer g2 = g_malloc0(n_bytes);
+  g1 = g_realloc(g1, n_bytes * 2);
+  gpointer g3 = g_try_malloc(n_bytes);
+  gpointer g4 = g_try_malloc0(n_bytes);
+  g3 = g_try_realloc(g3, n_bytes * 2);
+  gpointer g5 = g_malloc_n(n_bytes, sizeof(char));
+  gpointer g6 = g_malloc0_n(n_bytes, 

[PATCH] D30771: [analyzer] Teach the MallocChecker about Glib API for two arguments

2017-04-20 Thread Leslie Zhai via Phabricator via cfe-commits
xiangzhai added a comment.

Hi Daniel,

I respect you! the father of cppcheck  and 
KDE's buildbot use cppcheck for example Static Analysis K3B 
 thanks for your great 
job!

Regards,
Leslie Zhai


Repository:
  rL LLVM

https://reviews.llvm.org/D30771



___
cfe-commits mailing list
cfe-commits@lists.llvm.org
http://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[PATCH] D30771: [analyzer] Teach the MallocChecker about Glib API for two arguments

2017-04-19 Thread Leslie Zhai via Phabricator via cfe-commits
xiangzhai updated this revision to Diff 95887.
xiangzhai added a comment.

Hi Artem,

Thanks for your review! I updated my patch, please review it.

Regards,
Leslie Zhai


Repository:
  rL LLVM

https://reviews.llvm.org/D30771

Files:
  lib/StaticAnalyzer/Checkers/MallocChecker.cpp
  test/Analysis/gmalloc.c

Index: test/Analysis/gmalloc.c
===
--- test/Analysis/gmalloc.c
+++ test/Analysis/gmalloc.c
@@ -13,6 +13,12 @@
 gpointer g_try_malloc(gsize n_bytes);
 gpointer g_try_malloc0(gsize n_bytes);
 gpointer g_try_realloc(gpointer mem, gsize n_bytes);
+gpointer g_malloc_n(gsize n_blocks, gsize n_block_bytes);
+gpointer g_malloc0_n(gsize n_blocks, gsize n_block_bytes);
+gpointer g_realloc_n(gpointer mem, gsize n_blocks, gsize n_block_bytes);
+gpointer g_try_malloc_n(gsize n_blocks, gsize n_block_bytes);
+gpointer g_try_malloc0_n(gsize n_blocks, gsize n_block_bytes);
+gpointer g_try_realloc_n(gpointer mem, gsize n_blocks, gsize n_block_bytes);
 void g_free(gpointer mem);
 gpointer g_memdup(gconstpointer mem, guint byte_size);
 
@@ -25,6 +31,12 @@
   gpointer g3 = g_try_malloc(n_bytes);
   gpointer g4 = g_try_malloc0(n_bytes);
   g3 = g_try_realloc(g3, n_bytes * 2);
+  gpointer g5 = g_malloc_n(n_bytes, sizeof(char));
+  gpointer g6 = g_malloc0_n(n_bytes, sizeof(char));
+  g5 = g_realloc_n(g5, n_bytes * 2, sizeof(char));
+  gpointer g7 = g_try_malloc_n(n_bytes, sizeof(char));
+  gpointer g8 = g_try_malloc0_n(n_bytes, sizeof(char));
+  g7 = g_try_realloc_n(g7, n_bytes * 2, sizeof(char));
 
   g_free(g1);
   g_free(g2);
@@ -38,6 +50,12 @@
   gpointer g3 = g_try_malloc(n_bytes);
   gpointer g4 = g_try_malloc0(n_bytes);
   g3 = g_try_realloc(g3, n_bytes * 2);
+  gpointer g5 = g_malloc_n(n_bytes, sizeof(char));
+  gpointer g6 = g_malloc0_n(n_bytes, sizeof(char));
+  g5 = g_realloc_n(g5, n_bytes * 2, sizeof(char));
+  gpointer g7 = g_try_malloc_n(n_bytes, sizeof(char));
+  gpointer g8 = g_try_malloc0_n(n_bytes, sizeof(char));
+  g7 = g_try_realloc_n(g7, n_bytes * 2, sizeof(char));
 
   g_free(g1);
   g_free(g2);
@@ -52,8 +70,100 @@
   gpointer g3 = g_try_malloc(n_bytes);
   gpointer g4 = g_try_malloc0(n_bytes);
   g3 = g_try_realloc(g3, n_bytes * 2); // expected-warning{{Potential leak of memory pointed to by 'g4'}}
+  gpointer g5 = g_malloc_n(n_bytes, sizeof(char));
+  gpointer g6 = g_malloc0_n(n_bytes, sizeof(char));
+  g5 = g_realloc_n(g5, n_bytes * 2, sizeof(char)); // expected-warning{{Potential leak of memory pointed to by 'g6'}}
+  gpointer g7 = g_try_malloc_n(n_bytes, sizeof(char)); // expected-warning{{Potential leak of memory pointed to by 'g5'}}
+  gpointer g8 = g_try_malloc0_n(n_bytes, sizeof(char));
+  g7 = g_try_realloc_n(g7, n_bytes * 2, sizeof(char)); // expected-warning{{Potential leak of memory pointed to by 'g8'}}
+
+  g_free(g1); // expected-warning{{Potential leak of memory pointed to by 'g7'}}
+  g_free(g2);
+  g_free(g3);
+}
+
+void f4() {
+  gpointer g1 = g_malloc(n_bytes);
+  gpointer g2 = g_malloc0(n_bytes);
+  g1 = g_realloc(g1, n_bytes * 2);
+  gpointer g3 = g_try_malloc(n_bytes);
+  gpointer g4 = g_try_malloc0(n_bytes);
+  g3 = g_try_realloc(g3, n_bytes * 2);
+  gpointer g5 = g_malloc_n(n_bytes, sizeof(char));
+  gpointer g6 = g_malloc0_n(n_bytes, sizeof(char));
+  g5 = g_realloc_n(g5, n_bytes * 2, sizeof(char)); // expected-warning{{Potential leak of memory pointed to by 'g6'}}
+  gpointer g7 = g_try_malloc_n(n_bytes, sizeof(char)); // expected-warning{{Potential leak of memory pointed to by 'g5'}}
+  gpointer g8 = g_try_malloc0_n(n_bytes, sizeof(char));
+  g7 = g_try_realloc_n(g7, n_bytes * 2, sizeof(char)); // expected-warning{{Potential leak of memory pointed to by 'g8'}}
+
+  g_free(g1); // expected-warning{{Potential leak of memory pointed to by 'g7'}}
+  g_free(g2);
+  g_free(g3);
+  g_free(g4);
+}
+
+void f5() {
+  gpointer g1 = g_malloc(n_bytes);
+  gpointer g2 = g_malloc0(n_bytes);
+  g1 = g_realloc(g1, n_bytes * 2);
+  gpointer g3 = g_try_malloc(n_bytes);
+  gpointer g4 = g_try_malloc0(n_bytes);
+  g3 = g_try_realloc(g3, n_bytes * 2);
+  gpointer g5 = g_malloc_n(n_bytes, sizeof(char));
+  gpointer g6 = g_malloc0_n(n_bytes, sizeof(char));
+  g5 = g_realloc_n(g5, n_bytes * 2, sizeof(char)); // expected-warning{{Potential leak of memory pointed to by 'g6'}}
+  gpointer g7 = g_try_malloc_n(n_bytes, sizeof(char));
+  gpointer g8 = g_try_malloc0_n(n_bytes, sizeof(char));
+  g7 = g_try_realloc_n(g7, n_bytes * 2, sizeof(char)); // expected-warning{{Potential leak of memory pointed to by 'g8'}}
+
+  g_free(g1); // expected-warning{{Potential leak of memory pointed to by 'g7'}}
+  g_free(g2);
+  g_free(g3);
+  g_free(g4);
+  g_free(g5);
+}
+
+void f6() {
+  gpointer g1 = g_malloc(n_bytes);
+  gpointer g2 = g_malloc0(n_bytes);
+  g1 = g_realloc(g1, n_bytes * 2);
+  gpointer g3 = g_try_malloc(n_bytes);
+  gpointer g4 = g_try_malloc0(n_bytes);
+  g3 = g_try_realloc(g3, n_bytes * 2);
+  gpointer g5 = g_malloc_n(n_bytes, 

[PATCH] D32269: [Driver] Add iSOFTLinux to GNU ToolChains X86Triple

2017-04-19 Thread Leslie Zhai via Phabricator via cfe-commits
xiangzhai created this revision.

Hi LLVM developers,

I am a Linux engineer of operating system department at iSOFT 
, I want to add iSOFTLinux to GNU 
ToolChains X86Triple, please review my patch, thanks a lot!

Regards,
Leslie Zhai


Repository:
  rL LLVM

https://reviews.llvm.org/D32269

Files:
  lib/Driver/ToolChains/Gnu.cpp


Index: lib/Driver/ToolChains/Gnu.cpp
===
--- lib/Driver/ToolChains/Gnu.cpp
+++ lib/Driver/ToolChains/Gnu.cpp
@@ -1757,6 +1757,9 @@
   static const char *const X86_64LibDirs[] = {"/lib64", "/lib"};
   static const char *const X86_64Triples[] = {
   "x86_64-linux-gnu",   "x86_64-unknown-linux-gnu",
+  "x86_64-isoft-linux", "x86_64-isoft-linux-gnu",
+  "x86_64-everest-linux",   "x86_64-everest-linux-gnu",
+  "x86_64-pure64-linux","x86_64-pure64-linux-gnu",
   "x86_64-pc-linux-gnu","x86_64-redhat-linux6E",
   "x86_64-redhat-linux","x86_64-suse-linux",
   "x86_64-manbo-linux-gnu", "x86_64-linux-gnu",
@@ -1766,6 +1769,9 @@
   static const char *const X86LibDirs[] = {"/lib32", "/lib"};
   static const char *const X86Triples[] = {
   "i686-linux-gnu",   "i686-pc-linux-gnu", "i486-linux-gnu",
+  "i686-isoft-linux", "i686-isoft-linux-gnu",
+  "i686-everest-linux",   "i686-everest-linux-gnu",
+  "i686-pure64-linux","i686-pure64-linux-gnu",
   "i386-linux-gnu",   "i386-redhat-linux6E",   "i686-redhat-linux",
   "i586-redhat-linux","i386-redhat-linux", "i586-suse-linux",
   "i486-slackware-linux", "i686-montavista-linux", "i686-linux-android",


Index: lib/Driver/ToolChains/Gnu.cpp
===
--- lib/Driver/ToolChains/Gnu.cpp
+++ lib/Driver/ToolChains/Gnu.cpp
@@ -1757,6 +1757,9 @@
   static const char *const X86_64LibDirs[] = {"/lib64", "/lib"};
   static const char *const X86_64Triples[] = {
   "x86_64-linux-gnu",   "x86_64-unknown-linux-gnu",
+  "x86_64-isoft-linux", "x86_64-isoft-linux-gnu",
+  "x86_64-everest-linux",   "x86_64-everest-linux-gnu",
+  "x86_64-pure64-linux","x86_64-pure64-linux-gnu",
   "x86_64-pc-linux-gnu","x86_64-redhat-linux6E",
   "x86_64-redhat-linux","x86_64-suse-linux",
   "x86_64-manbo-linux-gnu", "x86_64-linux-gnu",
@@ -1766,6 +1769,9 @@
   static const char *const X86LibDirs[] = {"/lib32", "/lib"};
   static const char *const X86Triples[] = {
   "i686-linux-gnu",   "i686-pc-linux-gnu", "i486-linux-gnu",
+  "i686-isoft-linux", "i686-isoft-linux-gnu",
+  "i686-everest-linux",   "i686-everest-linux-gnu",
+  "i686-pure64-linux","i686-pure64-linux-gnu",
   "i386-linux-gnu",   "i386-redhat-linux6E",   "i686-redhat-linux",
   "i586-redhat-linux","i386-redhat-linux", "i586-suse-linux",
   "i486-slackware-linux", "i686-montavista-linux", "i686-linux-android",
___
cfe-commits mailing list
cfe-commits@lists.llvm.org
http://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[PATCH] D30771: [analyzer] Teach the MallocChecker about Glib API for two arguments

2017-04-19 Thread Leslie Zhai via Phabricator via cfe-commits
xiangzhai updated this revision to Diff 95880.

Repository:
  rL LLVM

https://reviews.llvm.org/D30771

Files:
  lib/StaticAnalyzer/Checkers/MallocChecker.cpp
  test/Analysis/gmalloc.c

Index: test/Analysis/gmalloc.c
===
--- test/Analysis/gmalloc.c
+++ test/Analysis/gmalloc.c
@@ -13,6 +13,12 @@
 gpointer g_try_malloc(gsize n_bytes);
 gpointer g_try_malloc0(gsize n_bytes);
 gpointer g_try_realloc(gpointer mem, gsize n_bytes);
+gpointer g_malloc_n(gsize n_blocks, gsize n_block_bytes);
+gpointer g_malloc0_n(gsize n_blocks, gsize n_block_bytes);
+gpointer g_realloc_n(gpointer mem, gsize n_blocks, gsize n_block_bytes);
+gpointer g_try_malloc_n(gsize n_blocks, gsize n_block_bytes);
+gpointer g_try_malloc0_n(gsize n_blocks, gsize n_block_bytes);
+gpointer g_try_realloc_n(gpointer mem, gsize n_blocks, gsize n_block_bytes);
 void g_free(gpointer mem);
 gpointer g_memdup(gconstpointer mem, guint byte_size);
 
@@ -25,6 +31,12 @@
   gpointer g3 = g_try_malloc(n_bytes);
   gpointer g4 = g_try_malloc0(n_bytes);
   g3 = g_try_realloc(g3, n_bytes * 2);
+  gpointer g5 = g_malloc_n(n_bytes, sizeof(char));
+  gpointer g6 = g_malloc0_n(n_bytes, sizeof(char));
+  g5 = g_realloc_n(g5, n_bytes * 2, sizeof(char));
+  gpointer g7 = g_try_malloc_n(n_bytes, sizeof(char));
+  gpointer g8 = g_try_malloc0_n(n_bytes, sizeof(char));
+  g7 = g_try_realloc_n(g7, n_bytes * 2, sizeof(char));
 
   g_free(g1);
   g_free(g2);
@@ -38,6 +50,12 @@
   gpointer g3 = g_try_malloc(n_bytes);
   gpointer g4 = g_try_malloc0(n_bytes);
   g3 = g_try_realloc(g3, n_bytes * 2);
+  gpointer g5 = g_malloc_n(n_bytes, sizeof(char));
+  gpointer g6 = g_malloc0_n(n_bytes, sizeof(char));
+  g5 = g_realloc_n(g5, n_bytes * 2, sizeof(char));
+  gpointer g7 = g_try_malloc_n(n_bytes, sizeof(char));
+  gpointer g8 = g_try_malloc0_n(n_bytes, sizeof(char));
+  g7 = g_try_realloc_n(g7, n_bytes * 2, sizeof(char));
 
   g_free(g1);
   g_free(g2);
@@ -52,8 +70,100 @@
   gpointer g3 = g_try_malloc(n_bytes);
   gpointer g4 = g_try_malloc0(n_bytes);
   g3 = g_try_realloc(g3, n_bytes * 2); // expected-warning{{Potential leak of memory pointed to by 'g4'}}
+  gpointer g5 = g_malloc_n(n_bytes, sizeof(char));
+  gpointer g6 = g_malloc0_n(n_bytes, sizeof(char));
+  g5 = g_realloc_n(g5, n_bytes * 2, sizeof(char)); // expected-warning{{Potential leak of memory pointed to by 'g6'}}
+  gpointer g7 = g_try_malloc_n(n_bytes, sizeof(char)); // expected-warning{{Potential leak of memory pointed to by 'g5'}}
+  gpointer g8 = g_try_malloc0_n(n_bytes, sizeof(char));
+  g7 = g_try_realloc_n(g7, n_bytes * 2, sizeof(char)); // expected-warning{{Potential leak of memory pointed to by 'g8'}}
+
+  g_free(g1); // expected-warning{{Potential leak of memory pointed to by 'g7'}}
+  g_free(g2);
+  g_free(g3);
+}
+
+void f4() {
+  gpointer g1 = g_malloc(n_bytes);
+  gpointer g2 = g_malloc0(n_bytes);
+  g1 = g_realloc(g1, n_bytes * 2);
+  gpointer g3 = g_try_malloc(n_bytes);
+  gpointer g4 = g_try_malloc0(n_bytes);
+  g3 = g_try_realloc(g3, n_bytes * 2);
+  gpointer g5 = g_malloc_n(n_bytes, sizeof(char));
+  gpointer g6 = g_malloc0_n(n_bytes, sizeof(char));
+  g5 = g_realloc_n(g5, n_bytes * 2, sizeof(char)); // expected-warning{{Potential leak of memory pointed to by 'g6'}}
+  gpointer g7 = g_try_malloc_n(n_bytes, sizeof(char)); // expected-warning{{Potential leak of memory pointed to by 'g5'}}
+  gpointer g8 = g_try_malloc0_n(n_bytes, sizeof(char));
+  g7 = g_try_realloc_n(g7, n_bytes * 2, sizeof(char)); // expected-warning{{Potential leak of memory pointed to by 'g8'}}
+
+  g_free(g1); // expected-warning{{Potential leak of memory pointed to by 'g7'}}
+  g_free(g2);
+  g_free(g3);
+  g_free(g4);
+}
+
+void f5() {
+  gpointer g1 = g_malloc(n_bytes);
+  gpointer g2 = g_malloc0(n_bytes);
+  g1 = g_realloc(g1, n_bytes * 2);
+  gpointer g3 = g_try_malloc(n_bytes);
+  gpointer g4 = g_try_malloc0(n_bytes);
+  g3 = g_try_realloc(g3, n_bytes * 2);
+  gpointer g5 = g_malloc_n(n_bytes, sizeof(char));
+  gpointer g6 = g_malloc0_n(n_bytes, sizeof(char));
+  g5 = g_realloc_n(g5, n_bytes * 2, sizeof(char)); // expected-warning{{Potential leak of memory pointed to by 'g6'}}
+  gpointer g7 = g_try_malloc_n(n_bytes, sizeof(char));
+  gpointer g8 = g_try_malloc0_n(n_bytes, sizeof(char));
+  g7 = g_try_realloc_n(g7, n_bytes * 2, sizeof(char)); // expected-warning{{Potential leak of memory pointed to by 'g8'}}
+
+  g_free(g1); // expected-warning{{Potential leak of memory pointed to by 'g7'}}
+  g_free(g2);
+  g_free(g3);
+  g_free(g4);
+  g_free(g5);
+}
+
+void f6() {
+  gpointer g1 = g_malloc(n_bytes);
+  gpointer g2 = g_malloc0(n_bytes);
+  g1 = g_realloc(g1, n_bytes * 2);
+  gpointer g3 = g_try_malloc(n_bytes);
+  gpointer g4 = g_try_malloc0(n_bytes);
+  g3 = g_try_realloc(g3, n_bytes * 2);
+  gpointer g5 = g_malloc_n(n_bytes, sizeof(char));
+  gpointer g6 = g_malloc0_n(n_bytes, sizeof(char));
+  g5 = g_realloc_n(g5, n_bytes * 2, sizeof(char));
+  gpointer g7 

[PATCH] D29827: [AVR] Add -mmcu option to the driver

2017-04-19 Thread Leslie Zhai via Phabricator via cfe-commits
This revision was automatically updated to reflect the committed changes.
Closed by commit rL300818: [AVR] Add -mmcu option to the driver (authored by 
xiangzhai).

Changed prior to commit:
  https://reviews.llvm.org/D29827?vs=95707=95879#toc

Repository:
  rL LLVM

https://reviews.llvm.org/D29827

Files:
  cfe/trunk/include/clang/Driver/Options.td
  cfe/trunk/lib/Driver/ToolChains/CommonArgs.cpp
  cfe/trunk/test/Driver/avr-mmcu.c


Index: cfe/trunk/lib/Driver/ToolChains/CommonArgs.cpp
===
--- cfe/trunk/lib/Driver/ToolChains/CommonArgs.cpp
+++ cfe/trunk/lib/Driver/ToolChains/CommonArgs.cpp
@@ -261,6 +261,12 @@
 arm::getARMArchCPUFromArgs(Args, MArch, MCPU, FromAs);
 return arm::getARMTargetCPU(MCPU, MArch, T);
   }
+
+  case llvm::Triple::avr:
+if (const Arg *A = Args.getLastArg(options::OPT_mmcu_EQ))
+  return A->getValue();
+return "";
+
   case llvm::Triple::mips:
   case llvm::Triple::mipsel:
   case llvm::Triple::mips64:
Index: cfe/trunk/include/clang/Driver/Options.td
===
--- cfe/trunk/include/clang/Driver/Options.td
+++ cfe/trunk/include/clang/Driver/Options.td
@@ -1661,6 +1661,7 @@
 def municode : Joined<["-"], "municode">, Group, 
Flags<[DriverOption]>;
 def mthreads : Joined<["-"], "mthreads">, Group, 
Flags<[DriverOption]>;
 def mcpu_EQ : Joined<["-"], "mcpu=">, Group;
+def mmcu_EQ : Joined<["-"], "mmcu=">, Group;
 def mdynamic_no_pic : Joined<["-"], "mdynamic-no-pic">, Group;
 def mfix_and_continue : Flag<["-"], "mfix-and-continue">, 
Group;
 def mieee_fp : Flag<["-"], "mieee-fp">, Group;
Index: cfe/trunk/test/Driver/avr-mmcu.c
===
--- cfe/trunk/test/Driver/avr-mmcu.c
+++ cfe/trunk/test/Driver/avr-mmcu.c
@@ -0,0 +1,5 @@
+// A test for the propagation of the -mmcu option to -cc1 and -cc1as
+
+// RUN: %clang -### -target avr -mmcu=atmega328p -save-temps %s 2>&1 | 
FileCheck %s
+// CHECK: clang{{.*}} "-cc1" {{.*}} "-target-cpu" "atmega328p"
+// CHECK: clang{{.*}} "-cc1as" {{.*}} "-target-cpu" "atmega328p"


Index: cfe/trunk/lib/Driver/ToolChains/CommonArgs.cpp
===
--- cfe/trunk/lib/Driver/ToolChains/CommonArgs.cpp
+++ cfe/trunk/lib/Driver/ToolChains/CommonArgs.cpp
@@ -261,6 +261,12 @@
 arm::getARMArchCPUFromArgs(Args, MArch, MCPU, FromAs);
 return arm::getARMTargetCPU(MCPU, MArch, T);
   }
+
+  case llvm::Triple::avr:
+if (const Arg *A = Args.getLastArg(options::OPT_mmcu_EQ))
+  return A->getValue();
+return "";
+
   case llvm::Triple::mips:
   case llvm::Triple::mipsel:
   case llvm::Triple::mips64:
Index: cfe/trunk/include/clang/Driver/Options.td
===
--- cfe/trunk/include/clang/Driver/Options.td
+++ cfe/trunk/include/clang/Driver/Options.td
@@ -1661,6 +1661,7 @@
 def municode : Joined<["-"], "municode">, Group, Flags<[DriverOption]>;
 def mthreads : Joined<["-"], "mthreads">, Group, Flags<[DriverOption]>;
 def mcpu_EQ : Joined<["-"], "mcpu=">, Group;
+def mmcu_EQ : Joined<["-"], "mmcu=">, Group;
 def mdynamic_no_pic : Joined<["-"], "mdynamic-no-pic">, Group;
 def mfix_and_continue : Flag<["-"], "mfix-and-continue">, Group;
 def mieee_fp : Flag<["-"], "mieee-fp">, Group;
Index: cfe/trunk/test/Driver/avr-mmcu.c
===
--- cfe/trunk/test/Driver/avr-mmcu.c
+++ cfe/trunk/test/Driver/avr-mmcu.c
@@ -0,0 +1,5 @@
+// A test for the propagation of the -mmcu option to -cc1 and -cc1as
+
+// RUN: %clang -### -target avr -mmcu=atmega328p -save-temps %s 2>&1 | FileCheck %s
+// CHECK: clang{{.*}} "-cc1" {{.*}} "-target-cpu" "atmega328p"
+// CHECK: clang{{.*}} "-cc1as" {{.*}} "-target-cpu" "atmega328p"
___
cfe-commits mailing list
cfe-commits@lists.llvm.org
http://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[PATCH] D30771: [analyzer] Teach the MallocChecker about Glib API for two arguments

2017-04-19 Thread Leslie Zhai via Phabricator via cfe-commits
xiangzhai updated this revision to Diff 95874.
xiangzhai added a comment.

Hi David,

Thanks for your review!

I updated my patch as you suggested! Please review it, thanks a lot! but I 
argue that:

> I have the feeling this should be renamed. Since its purpose is to calculate 
> the total size maybe MallocChecker::calculateBufferSize()

Yes! it is difficult to suitably name variable, function, project, and even my 
kid :) but `calculateBufferSize` is not make sense:

1. how to calculate? by `evalBinOp` do `BO_Mul` operation.
2. for what? for bytes size 
 so 
`forBufferSize` is ok.

> Capital variable: arg0Expr, arg0Val

I hold the view that I need to respect original developers' code, and it need a 
Global Patch for Capital variable, just like KDE's Use nullptr everywhere 


> is this "if (!Arg1)" needed? It seems to me that if CE->getNumArgs() returns 
> >= 2 then CE->getArg(1) should be non-NULL. Does it crash/assert if you 
> remove this condition?

The same story.

Regards,
Leslie Zhai


Repository:
  rL LLVM

https://reviews.llvm.org/D30771

Files:
  lib/StaticAnalyzer/Checkers/MallocChecker.cpp
  test/Analysis/gmalloc.c

Index: test/Analysis/gmalloc.c
===
--- test/Analysis/gmalloc.c
+++ test/Analysis/gmalloc.c
@@ -13,6 +13,12 @@
 gpointer g_try_malloc(gsize n_bytes);
 gpointer g_try_malloc0(gsize n_bytes);
 gpointer g_try_realloc(gpointer mem, gsize n_bytes);
+gpointer g_malloc_n(gsize n_blocks, gsize n_block_bytes);
+gpointer g_malloc0_n(gsize n_blocks, gsize n_block_bytes);
+gpointer g_realloc_n(gpointer mem, gsize n_blocks, gsize n_block_bytes);
+gpointer g_try_malloc_n(gsize n_blocks, gsize n_block_bytes);
+gpointer g_try_malloc0_n(gsize n_blocks, gsize n_block_bytes);
+gpointer g_try_realloc_n(gpointer mem, gsize n_blocks, gsize n_block_bytes);
 void g_free(gpointer mem);
 gpointer g_memdup(gconstpointer mem, guint byte_size);
 
@@ -25,6 +31,12 @@
   gpointer g3 = g_try_malloc(n_bytes);
   gpointer g4 = g_try_malloc0(n_bytes);
   g3 = g_try_realloc(g3, n_bytes * 2);
+  gpointer g5 = g_malloc_n(n_bytes, sizeof(char));
+  gpointer g6 = g_malloc0_n(n_bytes, sizeof(char));
+  g5 = g_realloc_n(g5, n_bytes * 2, sizeof(char));
+  gpointer g7 = g_try_malloc_n(n_bytes, sizeof(char));
+  gpointer g8 = g_try_malloc0_n(n_bytes, sizeof(char));
+  g7 = g_try_realloc_n(g7, n_bytes * 2, sizeof(char));
 
   g_free(g1);
   g_free(g2);
@@ -38,6 +50,12 @@
   gpointer g3 = g_try_malloc(n_bytes);
   gpointer g4 = g_try_malloc0(n_bytes);
   g3 = g_try_realloc(g3, n_bytes * 2);
+  gpointer g5 = g_malloc_n(n_bytes, sizeof(char));
+  gpointer g6 = g_malloc0_n(n_bytes, sizeof(char));
+  g5 = g_realloc_n(g5, n_bytes * 2, sizeof(char));
+  gpointer g7 = g_try_malloc_n(n_bytes, sizeof(char));
+  gpointer g8 = g_try_malloc0_n(n_bytes, sizeof(char));
+  g7 = g_try_realloc_n(g7, n_bytes * 2, sizeof(char));
 
   g_free(g1);
   g_free(g2);
@@ -52,8 +70,100 @@
   gpointer g3 = g_try_malloc(n_bytes);
   gpointer g4 = g_try_malloc0(n_bytes);
   g3 = g_try_realloc(g3, n_bytes * 2); // expected-warning{{Potential leak of memory pointed to by 'g4'}}
+  gpointer g5 = g_malloc_n(n_bytes, sizeof(char));
+  gpointer g6 = g_malloc0_n(n_bytes, sizeof(char));
+  g5 = g_realloc_n(g5, n_bytes * 2, sizeof(char)); // expected-warning{{Potential leak of memory pointed to by 'g6'}}
+  gpointer g7 = g_try_malloc_n(n_bytes, sizeof(char)); // expected-warning{{Potential leak of memory pointed to by 'g5'}}
+  gpointer g8 = g_try_malloc0_n(n_bytes, sizeof(char));
+  g7 = g_try_realloc_n(g7, n_bytes * 2, sizeof(char)); // expected-warning{{Potential leak of memory pointed to by 'g8'}}
+
+  g_free(g1); // expected-warning{{Potential leak of memory pointed to by 'g7'}}
+  g_free(g2);
+  g_free(g3);
+}
+
+void f4() {
+  gpointer g1 = g_malloc(n_bytes);
+  gpointer g2 = g_malloc0(n_bytes);
+  g1 = g_realloc(g1, n_bytes * 2);
+  gpointer g3 = g_try_malloc(n_bytes);
+  gpointer g4 = g_try_malloc0(n_bytes);
+  g3 = g_try_realloc(g3, n_bytes * 2);
+  gpointer g5 = g_malloc_n(n_bytes, sizeof(char));
+  gpointer g6 = g_malloc0_n(n_bytes, sizeof(char));
+  g5 = g_realloc_n(g5, n_bytes * 2, sizeof(char)); // expected-warning{{Potential leak of memory pointed to by 'g6'}}
+  gpointer g7 = g_try_malloc_n(n_bytes, sizeof(char)); // expected-warning{{Potential leak of memory pointed to by 'g5'}}
+  gpointer g8 = g_try_malloc0_n(n_bytes, sizeof(char));
+  g7 = g_try_realloc_n(g7, n_bytes * 2, sizeof(char)); // expected-warning{{Potential leak of memory pointed to by 'g8'}}
+
+  g_free(g1); // expected-warning{{Potential leak of memory pointed to by 'g7'}}
+  g_free(g2);
+  g_free(g3);
+  g_free(g4);
+}
+
+void f5() {
+  gpointer g1 = g_malloc(n_bytes);
+  gpointer g2 = g_malloc0(n_bytes);
+  g1 = g_realloc(g1, n_bytes * 2);
+  gpointer g3 = g_try_malloc(n_bytes);
+  gpointer g4 = g_try_malloc0(n_bytes);
+ 

[PATCH] D29827: [AVR] Add -mmcu option to the driver

2017-04-19 Thread Leslie Zhai via Phabricator via cfe-commits
xiangzhai accepted this revision.
xiangzhai added a comment.
This revision is now accepted and ready to land.

Hi Peter,

Thanks for your rebase! LGTM!

> Based on the context, the change from lib/Driver/Tools.cpp -> 
> lib/Driver/ToolChains/CommonArgs.cpp seems most appropriate (Gnu.cpp seems to 
> be about mapping LLVM options to GCC?)

Sorry for my mistake! yes, I am maintaining similar patch 

 for GCC toolchain triples :) also rebased to 
lib/Driver/ToolChains/CommonArgs.cpp for packaging llvm-4.0.0 
.

> And please do commit on my behalf, I haven't requested an account yet. Thanks!

I will commit it for you tomorrow if no **Need Review**!

Regards,
Leslie Zhai


https://reviews.llvm.org/D29827



___
cfe-commits mailing list
cfe-commits@lists.llvm.org
http://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[PATCH] D29827: [AVR] Add -mmcu option to the driver

2017-04-19 Thread Leslie Zhai via Phabricator via cfe-commits
xiangzhai added a comment.

Hi Jonathan,

Peter might do not have commit access, please commit it on his behalf, thanks a 
lot!

Regards,
Leslie Zhai


https://reviews.llvm.org/D29827



___
cfe-commits mailing list
cfe-commits@lists.llvm.org
http://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[PATCH] D31868: [analyzer] Check NULL pointer dereference issue for memset function

2017-04-19 Thread Leslie Zhai via Phabricator via cfe-commits
xiangzhai updated this revision to Diff 95690.
xiangzhai added a comment.

Hi Artem,

> so you're doing the binding thing now?

No! it only works for `RetVal` for example `int *ret = memset(x, 0, 
sizeof(int));`, please see my testcase:

  void foo() {
int *x = malloc(sizeof(int));
int *ret = memset(x, 0, sizeof(int));
int n = 1 / *ret; // expected-warning {{Division by zero}}
free(x);
  }

but not work for `MemVal` for example `int n = 1 / *x;`

Please carefully review my patch to point out my fault: wrongly use 
`bindDefault`? thanks a lot!

Regards,
Leslie Zhai


Repository:
  rL LLVM

https://reviews.llvm.org/D31868

Files:
  lib/StaticAnalyzer/Checkers/CStringChecker.cpp
  test/Analysis/null-deref-ps-region.c

Index: test/Analysis/null-deref-ps-region.c
===
--- test/Analysis/null-deref-ps-region.c
+++ test/Analysis/null-deref-ps-region.c
@@ -1,6 +1,11 @@
-// RUN: %clang_analyze_cc1 -analyzer-checker=core,alpha.core -std=gnu99 -analyzer-store=region -verify %s
-// expected-no-diagnostics
+// RUN: %clang_analyze_cc1 -analyzer-checker=core,alpha.core,unix,alpha.unix -std=gnu99 -analyzer-store=region -verify %s
 
+#include "Inputs/system-header-simulator.h"
+
+typedef __typeof(sizeof(int)) size_t;
+void *memset(void *__s, int __c, size_t __n);
+void *malloc(size_t __size);
+void free(void *__ptr);
 
 // The store for 'a[1]' should not be removed mistakenly. SymbolicRegions may
 // also be live roots.
@@ -13,3 +18,55 @@
 i = *p; // no-warning
   }
 }
+
+void foo() {
+  int *x = malloc(sizeof(int));
+  int *r = memset(x, 0, sizeof(int));
+  int n = 1 / *r; // expected-warning {{Division by zero}}
+  free(x);
+}
+
+void bar() {
+  int *x = malloc(sizeof(int));
+  memset(x, 0, 1);
+  int n = 1 / *x; // no-warning
+  free(x);
+}
+
+void f531() {
+  int *x = 0;
+  memset(x, 0, 1); // expected-warning {{Null pointer argument in call to memory set function}}
+}
+
+void f61() {
+  char buf[13];
+  memset(buf, 0, 1); // no-warning
+}
+
+void f611() {
+  char *buf = (char *)malloc(13);
+  memset(buf, 0, 1); // no-warning
+  free(buf);
+}
+
+void f66() {
+  char buf[1];
+  memset(buf, 0, 1024); // expected-warning {{Memory set function accesses out-of-bound array element}}
+}
+
+void f666() {
+  char *buf = (char *)malloc(1);
+  memset(buf, 0, 1024); // expected-warning {{Memory set function accesses out-of-bound array element}}
+  free(buf);
+}
+
+void f77() {
+  char buf[1];
+  memset(buf, 0, sizeof(buf)); // no-warning
+}
+
+void f777() {
+  char *buf = (char *)malloc(1);
+  memset(buf, 0, 1); // no-warning
+  free(buf);
+}
Index: lib/StaticAnalyzer/Checkers/CStringChecker.cpp
===
--- lib/StaticAnalyzer/Checkers/CStringChecker.cpp
+++ lib/StaticAnalyzer/Checkers/CStringChecker.cpp
@@ -120,6 +120,7 @@
   void evalStdCopy(CheckerContext , const CallExpr *CE) const;
   void evalStdCopyBackward(CheckerContext , const CallExpr *CE) const;
   void evalStdCopyCommon(CheckerContext , const CallExpr *CE) const;
+  void evalMemset(CheckerContext , const CallExpr *CE) const;
 
   // Utility methods
   std::pair
@@ -1999,6 +2000,79 @@
   C.addTransition(State);
 }
 
+void CStringChecker::evalMemset(CheckerContext , const CallExpr *CE) const {
+  if (CE->getNumArgs() != 3)
+return;
+
+  CurrentFunctionDescription = "memory set function";
+
+  const Expr *Mem = CE->getArg(0);
+  const Expr *Const = CE->getArg(1);
+  const Expr *Size = CE->getArg(2);
+  ProgramStateRef State = C.getState();
+
+  // See if the size argument is zero.
+  const LocationContext *LCtx = C.getLocationContext();
+  SVal SizeVal = State->getSVal(Size, LCtx);
+  QualType SizeTy = Size->getType();
+
+  ProgramStateRef StateZeroSize, StateNonZeroSize;
+  std::tie(StateZeroSize, StateNonZeroSize) =
+assumeZero(C, State, SizeVal, SizeTy);
+
+  // Get the value of the memory area.
+  SVal MemVal = State->getSVal(Mem, LCtx);
+
+  // If the size is zero, there won't be any actual memory access, so
+  // just bind the return value to the Mem buffer and return.
+  if (StateZeroSize && !StateNonZeroSize) {
+StateZeroSize = StateZeroSize->BindExpr(CE, LCtx, MemVal);
+C.addTransition(StateZeroSize);
+return;
+  }
+
+  if (!StateNonZeroSize)
+return;
+
+  // Ensure the memory area is not null.
+  // If it is NULL there will be a NULL pointer dereference.
+  State = checkNonNull(C, StateNonZeroSize, Mem, MemVal);
+  if (!State)
+return;
+
+  SValBuilder  = C.getSValBuilder();
+  // Check the region's extent is equal to the Size parameter.
+  SVal RetVal = SB.conjureSymbolVal(nullptr, CE, LCtx, C.blockCount());
+  const SymbolicRegion *R =
+  dyn_cast_or_null(RetVal.getAsRegion());
+  if (!R)
+return;
+  if (Optional DefinedSize =
+  SizeVal.getAs()) {
+DefinedOrUnknownSVal Extent = R->getExtent(SB);
+ProgramStateRef StateSameSize, StateNotSameSize;
+

[PATCH] D30771: [analyzer] Teach the MallocChecker about Glib API for two arguments

2017-04-18 Thread Leslie Zhai via Phabricator via cfe-commits
xiangzhai updated this revision to Diff 95684.
xiangzhai added a subscriber: cfe-commits.
xiangzhai added a comment.

Hi Artem,

I updated my patch as you suggested: never using `Arg1Val` after `TotalSize` is 
computed, on all branches. please review it, thanks a lot!

Regards,
Leslie Zhai


Repository:
  rL LLVM

https://reviews.llvm.org/D30771

Files:
  lib/StaticAnalyzer/Checkers/MallocChecker.cpp
  test/Analysis/gmalloc.c

Index: test/Analysis/gmalloc.c
===
--- test/Analysis/gmalloc.c
+++ test/Analysis/gmalloc.c
@@ -13,6 +13,12 @@
 gpointer g_try_malloc(gsize n_bytes);
 gpointer g_try_malloc0(gsize n_bytes);
 gpointer g_try_realloc(gpointer mem, gsize n_bytes);
+gpointer g_malloc_n(gsize n_blocks, gsize n_block_bytes);
+gpointer g_malloc0_n(gsize n_blocks, gsize n_block_bytes);
+gpointer g_realloc_n(gpointer mem, gsize n_blocks, gsize n_block_bytes);
+gpointer g_try_malloc_n(gsize n_blocks, gsize n_block_bytes);
+gpointer g_try_malloc0_n(gsize n_blocks, gsize n_block_bytes);
+gpointer g_try_realloc_n(gpointer mem, gsize n_blocks, gsize n_block_bytes);
 void g_free(gpointer mem);
 gpointer g_memdup(gconstpointer mem, guint byte_size);
 
@@ -25,6 +31,12 @@
   gpointer g3 = g_try_malloc(n_bytes);
   gpointer g4 = g_try_malloc0(n_bytes);
   g3 = g_try_realloc(g3, n_bytes * 2);
+  gpointer g5 = g_malloc_n(n_bytes, sizeof(char));
+  gpointer g6 = g_malloc0_n(n_bytes, sizeof(char));
+  g5 = g_realloc_n(g5, n_bytes * 2, sizeof(char));
+  gpointer g7 = g_try_malloc_n(n_bytes, sizeof(char));
+  gpointer g8 = g_try_malloc0_n(n_bytes, sizeof(char));
+  g7 = g_try_realloc_n(g7, n_bytes * 2, sizeof(char));
 
   g_free(g1);
   g_free(g2);
@@ -38,6 +50,12 @@
   gpointer g3 = g_try_malloc(n_bytes);
   gpointer g4 = g_try_malloc0(n_bytes);
   g3 = g_try_realloc(g3, n_bytes * 2);
+  gpointer g5 = g_malloc_n(n_bytes, sizeof(char));
+  gpointer g6 = g_malloc0_n(n_bytes, sizeof(char));
+  g5 = g_realloc_n(g5, n_bytes * 2, sizeof(char));
+  gpointer g7 = g_try_malloc_n(n_bytes, sizeof(char));
+  gpointer g8 = g_try_malloc0_n(n_bytes, sizeof(char));
+  g7 = g_try_realloc_n(g7, n_bytes * 2, sizeof(char));
 
   g_free(g1);
   g_free(g2);
@@ -52,8 +70,100 @@
   gpointer g3 = g_try_malloc(n_bytes);
   gpointer g4 = g_try_malloc0(n_bytes);
   g3 = g_try_realloc(g3, n_bytes * 2); // expected-warning{{Potential leak of memory pointed to by 'g4'}}
+  gpointer g5 = g_malloc_n(n_bytes, sizeof(char));
+  gpointer g6 = g_malloc0_n(n_bytes, sizeof(char));
+  g5 = g_realloc_n(g5, n_bytes * 2, sizeof(char)); // expected-warning{{Potential leak of memory pointed to by 'g6'}}
+  gpointer g7 = g_try_malloc_n(n_bytes, sizeof(char)); // expected-warning{{Potential leak of memory pointed to by 'g5'}}
+  gpointer g8 = g_try_malloc0_n(n_bytes, sizeof(char));
+  g7 = g_try_realloc_n(g7, n_bytes * 2, sizeof(char)); // expected-warning{{Potential leak of memory pointed to by 'g8'}}
+
+  g_free(g1); // expected-warning{{Potential leak of memory pointed to by 'g7'}}
+  g_free(g2);
+  g_free(g3);
+}
+
+void f4() {
+  gpointer g1 = g_malloc(n_bytes);
+  gpointer g2 = g_malloc0(n_bytes);
+  g1 = g_realloc(g1, n_bytes * 2);
+  gpointer g3 = g_try_malloc(n_bytes);
+  gpointer g4 = g_try_malloc0(n_bytes);
+  g3 = g_try_realloc(g3, n_bytes * 2);
+  gpointer g5 = g_malloc_n(n_bytes, sizeof(char));
+  gpointer g6 = g_malloc0_n(n_bytes, sizeof(char));
+  g5 = g_realloc_n(g5, n_bytes * 2, sizeof(char)); // expected-warning{{Potential leak of memory pointed to by 'g6'}}
+  gpointer g7 = g_try_malloc_n(n_bytes, sizeof(char)); // expected-warning{{Potential leak of memory pointed to by 'g5'}}
+  gpointer g8 = g_try_malloc0_n(n_bytes, sizeof(char));
+  g7 = g_try_realloc_n(g7, n_bytes * 2, sizeof(char)); // expected-warning{{Potential leak of memory pointed to by 'g8'}}
+
+  g_free(g1); // expected-warning{{Potential leak of memory pointed to by 'g7'}}
+  g_free(g2);
+  g_free(g3);
+  g_free(g4);
+}
+
+void f5() {
+  gpointer g1 = g_malloc(n_bytes);
+  gpointer g2 = g_malloc0(n_bytes);
+  g1 = g_realloc(g1, n_bytes * 2);
+  gpointer g3 = g_try_malloc(n_bytes);
+  gpointer g4 = g_try_malloc0(n_bytes);
+  g3 = g_try_realloc(g3, n_bytes * 2);
+  gpointer g5 = g_malloc_n(n_bytes, sizeof(char));
+  gpointer g6 = g_malloc0_n(n_bytes, sizeof(char));
+  g5 = g_realloc_n(g5, n_bytes * 2, sizeof(char)); // expected-warning{{Potential leak of memory pointed to by 'g6'}}
+  gpointer g7 = g_try_malloc_n(n_bytes, sizeof(char));
+  gpointer g8 = g_try_malloc0_n(n_bytes, sizeof(char));
+  g7 = g_try_realloc_n(g7, n_bytes * 2, sizeof(char)); // expected-warning{{Potential leak of memory pointed to by 'g8'}}
+
+  g_free(g1); // expected-warning{{Potential leak of memory pointed to by 'g7'}}
+  g_free(g2);
+  g_free(g3);
+  g_free(g4);
+  g_free(g5);
+}
+
+void f6() {
+  gpointer g1 = g_malloc(n_bytes);
+  gpointer g2 = g_malloc0(n_bytes);
+  g1 = g_realloc(g1, n_bytes * 2);
+  gpointer g3 = g_try_malloc(n_bytes);
+  

[PATCH] D31868: [analyzer] Check NULL pointer dereference issue for memset function

2017-04-18 Thread Leslie Zhai via Phabricator via cfe-commits
xiangzhai added a comment.

Hi All,

Thanks for your review! I will update my patch tomorrow! Almost 4+ days no see, 
I miss you :)

Regards,
Leslie Zhaii


Repository:
  rL LLVM

https://reviews.llvm.org/D31868



___
cfe-commits mailing list
cfe-commits@lists.llvm.org
http://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[PATCH] D31868: [analyzer] Check NULL pointer dereference issue for memset function

2017-04-18 Thread Leslie Zhai via Phabricator via cfe-commits
xiangzhai added a comment.

Hi Artem,

If it looks good to you, I want to try commit by myself for testing commit, 
thanks!

Regards,
Leslie Zhai


Repository:
  rL LLVM

https://reviews.llvm.org/D31868



___
cfe-commits mailing list
cfe-commits@lists.llvm.org
http://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[PATCH] D29827: [AVR] Add -mmcu option to the driver

2017-04-16 Thread Leslie Zhai via Phabricator via cfe-commits
xiangzhai added a comment.

ping :)


https://reviews.llvm.org/D29827



___
cfe-commits mailing list
cfe-commits@lists.llvm.org
http://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[PATCH] D31868: [analyzer] Check NULL pointer dereference issue for memset function

2017-04-14 Thread Leslie Zhai via Phabricator via cfe-commits
xiangzhai updated this revision to Diff 95273.
xiangzhai added a comment.

Hi All,

I have updated my patch as your suggestion, please review it, thanks a lot!

Regards,
Leslie Zhai


Repository:
  rL LLVM

https://reviews.llvm.org/D31868

Files:
  lib/StaticAnalyzer/Checkers/CStringChecker.cpp
  test/Analysis/null-deref-ps-region.c

Index: test/Analysis/null-deref-ps-region.c
===
--- test/Analysis/null-deref-ps-region.c
+++ test/Analysis/null-deref-ps-region.c
@@ -1,6 +1,11 @@
-// RUN: %clang_analyze_cc1 -analyzer-checker=core,alpha.core -std=gnu99 -analyzer-store=region -verify %s
-// expected-no-diagnostics
+// RUN: %clang_analyze_cc1 -analyzer-checker=core,alpha.core,unix,alpha.unix -std=gnu99 -analyzer-store=region -verify %s
 
+#include "Inputs/system-header-simulator.h"
+
+typedef __typeof(sizeof(int)) size_t;
+void *memset(void *__s, int __c, size_t __n);
+void *malloc(size_t __size);
+void free(void *__ptr);
 
 // The store for 'a[1]' should not be removed mistakenly. SymbolicRegions may
 // also be live roots.
@@ -13,3 +18,41 @@
 i = *p; // no-warning
   }
 }
+
+void f531() {
+  int *x = 0;
+  memset(x, 0, 1); // expected-warning {{Null pointer argument in call to memory set function}}
+}
+
+void f61() {
+  char buf[13];
+  memset(buf, 0, 1); // no-warning
+}
+
+void f611() {
+  char *buf = (char *)malloc(13);
+  memset(buf, 0, 1); // no-warning
+  free(buf);
+}
+
+void f66() {
+  char buf[1];
+  memset(buf, 0, 1024); // expected-warning {{Memory set function accesses out-of-bound array element}}
+}
+
+void f666() {
+  char *buf = (char *)malloc(1);
+  memset(buf, 0, 1024); // expected-warning {{Memory set function accesses out-of-bound array element}}
+  free(buf);
+}
+
+void f77() {
+  char buf[1];
+  memset(buf, 0, sizeof(buf)); // no-warning
+}
+
+void f777() {
+  char *buf = (char *)malloc(1);
+  memset(buf, 0, 1); // no-warning
+  free(buf);
+}
Index: lib/StaticAnalyzer/Checkers/CStringChecker.cpp
===
--- lib/StaticAnalyzer/Checkers/CStringChecker.cpp
+++ lib/StaticAnalyzer/Checkers/CStringChecker.cpp
@@ -120,6 +120,7 @@
   void evalStdCopy(CheckerContext , const CallExpr *CE) const;
   void evalStdCopyBackward(CheckerContext , const CallExpr *CE) const;
   void evalStdCopyCommon(CheckerContext , const CallExpr *CE) const;
+  void evalMemset(CheckerContext , const CallExpr *CE) const;
 
   // Utility methods
   std::pair
@@ -1999,6 +2000,80 @@
   C.addTransition(State);
 }
 
+void CStringChecker::evalMemset(CheckerContext , const CallExpr *CE) const {
+  if (CE->getNumArgs() != 3)
+return;
+
+  CurrentFunctionDescription = "memory set function";
+
+  const Expr *Mem = CE->getArg(0);
+  const Expr *Const = CE->getArg(1);
+  const Expr *Size = CE->getArg(2);
+  ProgramStateRef State = C.getState();
+
+  // See if the size argument is zero.
+  const LocationContext *LCtx = C.getLocationContext();
+  SVal SizeVal = State->getSVal(Size, LCtx);
+  QualType SizeTy = Size->getType();
+
+  ProgramStateRef StateZeroSize, StateNonZeroSize;
+  std::tie(StateZeroSize, StateNonZeroSize) =
+assumeZero(C, State, SizeVal, SizeTy);
+
+  // Get the value of the memory area.
+  SVal MemVal = State->getSVal(Mem, LCtx);
+
+  // If the size is zero, there won't be any actual memory access, so
+  // just bind the return value to the Mem buffer and return.
+  if (StateZeroSize && !StateNonZeroSize) {
+StateZeroSize = StateZeroSize->BindExpr(CE, LCtx, MemVal);
+C.addTransition(StateZeroSize);
+return;
+  }
+
+  if (!StateNonZeroSize)
+return;
+
+  // If the size can be nonzero, we have to check the other arguments.
+  if (StateNonZeroSize) {
+State = StateNonZeroSize;
+
+// Ensure the memory area is not null.
+// If it is NULL there will be a NULL pointer dereference.
+State = checkNonNull(C, State, Mem, MemVal);
+if (!State)
+  return;
+
+SValBuilder  = C.getSValBuilder();
+// Check the region's extent is equal to the Size parameter.
+SVal RetVal = SB.conjureSymbolVal(nullptr, CE, LCtx, C.blockCount());
+const SymbolicRegion *R =
+dyn_cast_or_null(RetVal.getAsRegion());
+if (!R)
+  return;
+if (Optional DefinedSize =
+SizeVal.getAs()) {
+  DefinedOrUnknownSVal Extent = R->getExtent(SB);
+  ProgramStateRef StateSameSize, StateNotSameSize;
+  std::tie(StateSameSize, StateNotSameSize) =
+  State->assume(SB.evalEQ(State, Extent, *DefinedSize));
+  if (StateNotSameSize) {
+State = CheckBufferAccess(C, State, Size, Mem);
+if (!State)
+return;
+  }
+
+  if (StateSameSize) {
+SVal ConstVal = State->getSVal(Const, LCtx);
+State = State->BindExpr(CE, LCtx, RetVal);
+// Actually bind the second argument value to the buffer.
+State = State->bindDefault(RetVal, ConstVal, LCtx);
+C.addTransition(State);
+  

[PATCH] D31868: [analyzer] Check NULL pointer dereference issue for memset function

2017-04-13 Thread Leslie Zhai via Phabricator via cfe-commits
xiangzhai added a comment.

Hi Artem,

Thanks for your review! I will update my patch tomorrow :)

Regards,
Leslie Zhai


Repository:
  rL LLVM

https://reviews.llvm.org/D31868



___
cfe-commits mailing list
cfe-commits@lists.llvm.org
http://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[PATCH] D31868: [analyzer] Check NULL pointer dereference issue for memset function

2017-04-12 Thread Leslie Zhai via Phabricator via cfe-commits
xiangzhai added a comment.

Hi Daniel,

Thanks for your review!

Sorry I am not available until this Friday, then I will update my patch.

Regards,
Leslie Zhai


Repository:
  rL LLVM

https://reviews.llvm.org/D31868



___
cfe-commits mailing list
cfe-commits@lists.llvm.org
http://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[PATCH] D31868: [analyzer] Check NULL pointer dereference issue for memset function

2017-04-10 Thread Leslie Zhai via Phabricator via cfe-commits
xiangzhai created this revision.

Hi LLVM developers,

As Anna mentioned:

> One idea is to check that we do not pass a pointer that is known to be NULL 
> to functions that are known to dereference pointers such as memcpy. There is 
> a checker that determines if a null pointer could be dereferenced already, 
> but there is no extension to check if such a pointer could be passed to a 
> function tat could dereference it.

So I implemented `evalMemset` in the CStringChecker to detect null-deref issue. 
please review my patch, thanks a lot!

Regards,
Leslie Zhai


Repository:
  rL LLVM

https://reviews.llvm.org/D31868

Files:
  lib/StaticAnalyzer/Checkers/CStringChecker.cpp
  test/Analysis/null-deref-ps-region.c

Index: test/Analysis/null-deref-ps-region.c
===
--- test/Analysis/null-deref-ps-region.c
+++ test/Analysis/null-deref-ps-region.c
@@ -1,6 +1,9 @@
-// RUN: %clang_analyze_cc1 -analyzer-checker=core,alpha.core -std=gnu99 -analyzer-store=region -verify %s
-// expected-no-diagnostics
+// RUN: %clang_analyze_cc1 -analyzer-checker=core,alpha.core,unix,alpha.unix -std=gnu99 -analyzer-store=region -verify %s
 
+#include "Inputs/system-header-simulator.h"
+
+typedef __typeof(sizeof(int)) size_t;
+void *memset (void *__s, int __c, size_t __n);
 
 // The store for 'a[1]' should not be removed mistakenly. SymbolicRegions may
 // also be live roots.
@@ -13,3 +16,18 @@
 i = *p; // no-warning
   }
 }
+
+void f531() {
+  int *x = 0;
+  memset(x, 0, 1); // expected-warning {{Null pointer argument in call to memory set function}}
+}
+
+void f66() {
+  char buf[1];
+  memset(buf, 0, 1024); // expected-warning {{Memory set function accesses out-of-bound array element}}
+}
+
+void f77() {
+  char buf[1];
+  memset(buf, 0, sizeof(buf)); // no-warning
+}
Index: lib/StaticAnalyzer/Checkers/CStringChecker.cpp
===
--- lib/StaticAnalyzer/Checkers/CStringChecker.cpp
+++ lib/StaticAnalyzer/Checkers/CStringChecker.cpp
@@ -120,6 +120,7 @@
   void evalStdCopy(CheckerContext , const CallExpr *CE) const;
   void evalStdCopyBackward(CheckerContext , const CallExpr *CE) const;
   void evalStdCopyCommon(CheckerContext , const CallExpr *CE) const;
+  void evalMemset(CheckerContext , const CallExpr *CE) const;
 
   // Utility methods
   std::pair
@@ -1999,6 +2000,63 @@
   C.addTransition(State);
 }
 
+void CStringChecker::evalMemset(CheckerContext , const CallExpr *CE) const {
+  if (CE->getNumArgs() < 3)
+return;
+
+  CurrentFunctionDescription = "memory set function";
+
+  const Expr *S = CE->getArg(0);
+  const Expr *Size = CE->getArg(2);
+  ProgramStateRef state = C.getState();
+
+  // See if the size argument is zero.
+  const LocationContext *LCtx = C.getLocationContext();
+  SVal sizeVal = state->getSVal(Size, LCtx);
+  QualType sizeTy = Size->getType();
+
+  ProgramStateRef stateZeroSize, stateNonZeroSize;
+  std::tie(stateZeroSize, stateNonZeroSize) =
+assumeZero(C, state, sizeVal, sizeTy);
+
+  // Get the value of the memory area pointed to by S.
+  SVal sVal = state->getSVal(S, LCtx);
+
+  // If the size is zero, there won't be any actual memory access, so   
+  // just bind the return value to the destination buffer and return.
+  if (stateZeroSize && !stateNonZeroSize) {
+stateZeroSize = stateZeroSize->BindExpr(CE, LCtx, sVal);
+C.addTransition(stateZeroSize);
+return;
+  }
+
+  // If the size can be nonzero, we have to check the other arguments.
+  if (stateNonZeroSize) {
+state = stateNonZeroSize;
+
+// Ensure the memory area pointed to by s is not null. 
+// If it is NULL there will be a NULL pointer dereference.
+state = checkNonNull(C, state, S, sVal);
+if (!state)
+  return;
+
+// Ensure the accesses are valid.
+state = CheckBufferAccess(C, state, Size, S);
+if (!state)
+  return;
+
+// Return the memory area pointed to by s buffer.
+state = state->BindExpr(CE, LCtx, sVal);
+
+// Invalidate the memory area pointed to by s (regular invalidation without 
+// pointer-escaping the address of the top-level region). 
+state = InvalidateBuffer(C, state, S, C.getSVal(S),
+ /*IsSourceBuffer*/false, Size);
+
+C.addTransition(state);
+  }
+}
+
 static bool isCPPStdLibraryFunction(const FunctionDecl *FD, StringRef Name) {
   IdentifierInfo *II = FD->getIdentifier();
   if (!II)
@@ -2032,6 +2090,8 @@
 evalFunction =  ::evalMemcmp;
   else if (C.isCLibraryFunction(FDecl, "memmove"))
 evalFunction =  ::evalMemmove;
+  else if (C.isCLibraryFunction(FDecl, "memset"))
+evalFunction =  ::evalMemset;
   else if (C.isCLibraryFunction(FDecl, "strcpy"))
 evalFunction =  ::evalStrcpy;
   else if (C.isCLibraryFunction(FDecl, "strncpy"))
___
cfe-commits mailing list
cfe-commits@lists.llvm.org

[PATCH] D23418: [analyzer] Added a reusable constraint system to the CloneDetector

2017-03-31 Thread Leslie Zhai via Phabricator via cfe-commits
xiangzhai added a comment.

Hi Raphael,

Then I will rebase my patch https://reviews.llvm.org/D31320 please review it 
when you have free time, thanks a lot!

Regards,
Leslie Zhai


https://reviews.llvm.org/D23418



___
cfe-commits mailing list
cfe-commits@lists.llvm.org
http://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[PATCH] D23418: [analyzer] Added a reusable constraint system to the CloneDetector

2017-03-28 Thread Leslie Zhai via Phabricator via cfe-commits
xiangzhai added a comment.

Hi Raphael,

Congratulate the patch was accepted!

> Well this patch won't change a lot with the false-positives or performance 
> (it's more refactoring) :)

So may I Teach CloneDetection about Qt Meta-Object Compiler 
 and filter other auto-generated source files 
base your patch? thanks a lot!

Regards,
Leslie Zhai


https://reviews.llvm.org/D23418



___
cfe-commits mailing list
cfe-commits@lists.llvm.org
http://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[PATCH] D23418: [analyzer] Added a reusable constraint system to the CloneDetector

2017-03-28 Thread Leslie Zhai via Phabricator via cfe-commits
xiangzhai added a comment.

Hi Raphael,

Thanks for your reply!

> regarding performance: Last time I checked we spend most of the time on the 
> verification of the hash values. We can do some tricks to make this faster 
> (like delaying the verification to the end of the constraints where we have 
> much less clones and therefore less overhead with this)
> 
> regarding false-positives: We will do some basic stuff to reduce them 
> soon-ish (e.g. increasing the minimum clone size default value, filtering 
> those generated files). Afterwards we probably need some fancier way of 
> teaching the checker what is a valid clone and what not.
> 
> If you have some actual bugs that are found by the checker, please send them 
> to me (teemperor [AT] gmail.com) that we can add them to the regression tests 
> :)

I will test your updated patch tomorrow by testing with KDE/GNOME real projects.

Regards,
Leslie Zhai


https://reviews.llvm.org/D23418



___
cfe-commits mailing list
cfe-commits@lists.llvm.org
http://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[PATCH] D23418: [analyzer] Added a reusable constraint system to the CloneDetector

2017-03-26 Thread Leslie Zhai via Phabricator via cfe-commits
xiangzhai added a comment.

Hi Raphael,

Thanks for your awesome job!

I have read about the slide 
 of "LLVM: 
built-in scalable code clone detection based on semantic analysis", and sent 
email to Shamil for asking "Is Code clone detection in LLVM compiler 
infrastructure available?" he replied me that the implementation (in LLVM IR 
layer?) is unavailable - close source. so I pay more attention to your 
implementation without LLVM IR, but I am really really really care about:

1. Performance. I use `scan-build -k -v -enable-checker 
alpha.clone.CloneChecker` to static analysis K3B , 
it almost spend **one hour**! optimization plan?
2. False Positive. I use Coverity scan K3B 
 to compare with CloneDetector, there 
is **NO** false positive when detecting Copy-paste issue by setting **pattern** 
to ignore Qt Meta-Object Compiler  and other 
auto-generated source files. perhaps CloneChecker is able to learn this way to 
low false positive?

Thanks again for your great job!

Regards,
Leslie Zhai


https://reviews.llvm.org/D23418



___
cfe-commits mailing list
cfe-commits@lists.llvm.org
http://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[PATCH] D28348: [analyzer] Taught the analyzer about Glib API to check Memory-leak

2017-03-01 Thread Leslie Zhai via Phabricator via cfe-commits
xiangzhai added a comment.

Hi Anna,

Thanks for your review!

> The information generated by this checker is used for array bounds checking. 
> For example, see https://reviews.llvm.org/D24307

I will read carefully about that ;-)

> This patch looks good. Do you have commit access or should I commit it on 
> your behalf?

Please commit it on my behalf, thanks a lot!

Regards,
Leslie Zhai


Repository:
  rL LLVM

https://reviews.llvm.org/D28348



___
cfe-commits mailing list
cfe-commits@lists.llvm.org
http://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[PATCH] D28348: [analyzer] Taught the analyzer about Glib API to check Memory-leak

2017-02-26 Thread Leslie Zhai via Phabricator via cfe-commits
xiangzhai updated this revision to Diff 89825.
xiangzhai added a comment.

Hi Anna,

Thanks for your review!

I updated the Glib-MallocChecker-single-size-value.patch to use **zeroVal** for 
**g_malloc0** and **g_try_malloc0**

and Yes, I refer CallocMem to implement **SValBinMulOp** in the 
Glib-MallocChecker-all-in-one.patch 
 if this 
patch could be submitted to UPSTREAM, then I create another patch for XXX_n, 
thanks for your suggest!

Regards,
Leslie Zhai


Repository:
  rL LLVM

https://reviews.llvm.org/D28348

Files:
  lib/StaticAnalyzer/Checkers/MallocChecker.cpp
  test/Analysis/gmalloc.c

Index: test/Analysis/gmalloc.c
===
--- test/Analysis/gmalloc.c
+++ test/Analysis/gmalloc.c
@@ -0,0 +1,59 @@
+// RUN: %clang_cc1 -analyze -analyzer-checker=core,unix.Malloc -analyzer-store=region -verify %s
+
+#include "Inputs/system-header-simulator.h"
+
+typedef void* gpointer;
+typedef const void* gconstpointer;
+typedef unsigned long gsize;
+typedef unsigned int guint;
+
+gpointer g_malloc(gsize n_bytes);
+gpointer g_malloc0(gsize n_bytes);
+gpointer g_realloc(gpointer mem, gsize n_bytes);
+gpointer g_try_malloc(gsize n_bytes);
+gpointer g_try_malloc0(gsize n_bytes);
+gpointer g_try_realloc(gpointer mem, gsize n_bytes);
+void g_free(gpointer mem);
+gpointer g_memdup(gconstpointer mem, guint byte_size);
+
+static const gsize n_bytes = 1024;
+
+void f1() {
+  gpointer g1 = g_malloc(n_bytes);
+  gpointer g2 = g_malloc0(n_bytes);
+  g1 = g_realloc(g1, n_bytes * 2);
+  gpointer g3 = g_try_malloc(n_bytes);
+  gpointer g4 = g_try_malloc0(n_bytes);
+  g3 = g_try_realloc(g3, n_bytes * 2);
+
+  g_free(g1);
+  g_free(g2);
+  g_free(g2); // expected-warning{{Attempt to free released memory}}
+}
+
+void f2() {
+  gpointer g1 = g_malloc(n_bytes);
+  gpointer g2 = g_malloc0(n_bytes);
+  g1 = g_realloc(g1, n_bytes * 2);
+  gpointer g3 = g_try_malloc(n_bytes);
+  gpointer g4 = g_try_malloc0(n_bytes);
+  g3 = g_try_realloc(g3, n_bytes * 2);
+
+  g_free(g1);
+  g_free(g2);
+  g_free(g3);
+  g3 = g_memdup(g3, n_bytes); // expected-warning{{Use of memory after it is freed}}
+}
+
+void f3() {
+  gpointer g1 = g_malloc(n_bytes);
+  gpointer g2 = g_malloc0(n_bytes);
+  g1 = g_realloc(g1, n_bytes * 2);
+  gpointer g3 = g_try_malloc(n_bytes);
+  gpointer g4 = g_try_malloc0(n_bytes);
+  g3 = g_try_realloc(g3, n_bytes * 2); // expected-warning{{Potential leak of memory pointed to by 'g4'}}
+
+  g_free(g1);
+  g_free(g2);
+  g_free(g3);
+}
Index: lib/StaticAnalyzer/Checkers/MallocChecker.cpp
===
--- lib/StaticAnalyzer/Checkers/MallocChecker.cpp
+++ lib/StaticAnalyzer/Checkers/MallocChecker.cpp
@@ -174,7 +174,10 @@
 II_valloc(nullptr), II_reallocf(nullptr), II_strndup(nullptr),
 II_strdup(nullptr), II_win_strdup(nullptr), II_kmalloc(nullptr),
 II_if_nameindex(nullptr), II_if_freenameindex(nullptr),
-II_wcsdup(nullptr), II_win_wcsdup(nullptr) {}
+II_wcsdup(nullptr), II_win_wcsdup(nullptr), II_g_malloc(nullptr),
+II_g_malloc0(nullptr), II_g_realloc(nullptr), II_g_try_malloc(nullptr), 
+II_g_try_malloc0(nullptr), II_g_try_realloc(nullptr), 
+II_g_free(nullptr), II_g_memdup(nullptr) {}
 
   /// In pessimistic mode, the checker assumes that it does not know which
   /// functions might free the memory.
@@ -236,7 +239,9 @@
  *II_realloc, *II_calloc, *II_valloc, *II_reallocf,
  *II_strndup, *II_strdup, *II_win_strdup, *II_kmalloc,
  *II_if_nameindex, *II_if_freenameindex, *II_wcsdup,
- *II_win_wcsdup;
+ *II_win_wcsdup, *II_g_malloc, *II_g_malloc0, 
+ *II_g_realloc, *II_g_try_malloc, *II_g_try_malloc0, 
+ *II_g_try_realloc, *II_g_free, *II_g_memdup;
   mutable Optional KernelZeroFlagVal;
 
   void initIdentifierInfo(ASTContext ) const;
@@ -554,6 +559,16 @@
   II_win_strdup = ("_strdup");
   II_win_wcsdup = ("_wcsdup");
   II_win_alloca = ("_alloca");
+
+  // Glib
+  II_g_malloc = ("g_malloc");
+  II_g_malloc0 = ("g_malloc0");
+  II_g_realloc = ("g_realloc");
+  II_g_try_malloc = ("g_try_malloc");
+  II_g_try_malloc0 = ("g_try_malloc0");
+  II_g_try_realloc = ("g_try_realloc");
+  II_g_free = ("g_free");
+  II_g_memdup = ("g_memdup");
 }
 
 bool MallocChecker::isMemFunction(const FunctionDecl *FD, ASTContext ) const {
@@ -589,15 +604,20 @@
 initIdentifierInfo(C);
 
 if (Family == AF_Malloc && CheckFree) {
-  if (FunI == II_free || FunI == II_realloc || FunI == II_reallocf)
+  if (FunI == II_free || FunI == II_realloc || FunI == II_reallocf || 
+  FunI == II_g_free)
 return true;
 }
 
 if (Family == AF_Malloc && CheckAlloc) {
   if (FunI == II_malloc || FunI == II_realloc || FunI == 

[PATCH] D28348: [analyzer] Taught the analyzer about Glib API to check Memory-leak

2017-02-22 Thread Leslie Zhai via Phabricator via cfe-commits
xiangzhai updated this revision to Diff 89460.
xiangzhai added a comment.

Hi Anna,

Thanks for your suggest!

Firstly I uploaded Glib-MallocChecker-single-size-value.patch for code review, 
if submitted to UPSTREAM, then upload another one, correct?

Regards,
Leslie Zhai


Repository:
  rL LLVM

https://reviews.llvm.org/D28348

Files:
  lib/StaticAnalyzer/Checkers/MallocChecker.cpp
  test/Analysis/gmalloc.c

Index: test/Analysis/gmalloc.c
===
--- test/Analysis/gmalloc.c
+++ test/Analysis/gmalloc.c
@@ -0,0 +1,59 @@
+// RUN: %clang_cc1 -analyze -analyzer-checker=core,unix.Malloc -analyzer-store=region -verify %s
+
+#include "Inputs/system-header-simulator.h"
+
+typedef void* gpointer;
+typedef const void* gconstpointer;
+typedef unsigned long gsize;
+typedef unsigned int guint;
+
+gpointer g_malloc(gsize n_bytes);
+gpointer g_malloc0(gsize n_bytes);
+gpointer g_realloc(gpointer mem, gsize n_bytes);
+gpointer g_try_malloc(gsize n_bytes);
+gpointer g_try_malloc0(gsize n_bytes);
+gpointer g_try_realloc(gpointer mem, gsize n_bytes);
+void g_free(gpointer mem);
+gpointer g_memdup(gconstpointer mem, guint byte_size);
+
+static const gsize n_bytes = 1024;
+
+void f1() {
+  gpointer g1 = g_malloc(n_bytes);
+  gpointer g2 = g_malloc0(n_bytes);
+  g1 = g_realloc(g1, n_bytes * 2);
+  gpointer g3 = g_try_malloc(n_bytes);
+  gpointer g4 = g_try_malloc0(n_bytes);
+  g3 = g_try_realloc(g3, n_bytes * 2);
+
+  g_free(g1);
+  g_free(g2);
+  g_free(g2); // expected-warning{{Attempt to free released memory}}
+}
+
+void f2() {
+  gpointer g1 = g_malloc(n_bytes);
+  gpointer g2 = g_malloc0(n_bytes);
+  g1 = g_realloc(g1, n_bytes * 2);
+  gpointer g3 = g_try_malloc(n_bytes);
+  gpointer g4 = g_try_malloc0(n_bytes);
+  g3 = g_try_realloc(g3, n_bytes * 2);
+
+  g_free(g1);
+  g_free(g2);
+  g_free(g3);
+  g3 = g_memdup(g3, n_bytes); // expected-warning{{Use of memory after it is freed}}
+}
+
+void f3() {
+  gpointer g1 = g_malloc(n_bytes);
+  gpointer g2 = g_malloc0(n_bytes);
+  g1 = g_realloc(g1, n_bytes * 2);
+  gpointer g3 = g_try_malloc(n_bytes);
+  gpointer g4 = g_try_malloc0(n_bytes);
+  g3 = g_try_realloc(g3, n_bytes * 2); // expected-warning{{Potential leak of memory pointed to by 'g4'}}
+
+  g_free(g1);
+  g_free(g2);
+  g_free(g3);
+}
Index: lib/StaticAnalyzer/Checkers/MallocChecker.cpp
===
--- lib/StaticAnalyzer/Checkers/MallocChecker.cpp
+++ lib/StaticAnalyzer/Checkers/MallocChecker.cpp
@@ -174,7 +174,10 @@
 II_valloc(nullptr), II_reallocf(nullptr), II_strndup(nullptr),
 II_strdup(nullptr), II_win_strdup(nullptr), II_kmalloc(nullptr),
 II_if_nameindex(nullptr), II_if_freenameindex(nullptr),
-II_wcsdup(nullptr), II_win_wcsdup(nullptr) {}
+II_wcsdup(nullptr), II_win_wcsdup(nullptr), II_g_malloc(nullptr),
+II_g_malloc0(nullptr), II_g_realloc(nullptr), II_g_try_malloc(nullptr), 
+II_g_try_malloc0(nullptr), II_g_try_realloc(nullptr), 
+II_g_free(nullptr), II_g_memdup(nullptr) {}
 
   /// In pessimistic mode, the checker assumes that it does not know which
   /// functions might free the memory.
@@ -236,7 +239,9 @@
  *II_realloc, *II_calloc, *II_valloc, *II_reallocf,
  *II_strndup, *II_strdup, *II_win_strdup, *II_kmalloc,
  *II_if_nameindex, *II_if_freenameindex, *II_wcsdup,
- *II_win_wcsdup;
+ *II_win_wcsdup, *II_g_malloc, *II_g_malloc0, 
+ *II_g_realloc, *II_g_try_malloc, *II_g_try_malloc0, 
+ *II_g_try_realloc, *II_g_free, *II_g_memdup;
   mutable Optional KernelZeroFlagVal;
 
   void initIdentifierInfo(ASTContext ) const;
@@ -554,6 +559,16 @@
   II_win_strdup = ("_strdup");
   II_win_wcsdup = ("_wcsdup");
   II_win_alloca = ("_alloca");
+
+  // Glib
+  II_g_malloc = ("g_malloc");
+  II_g_malloc0 = ("g_malloc0");
+  II_g_realloc = ("g_realloc");
+  II_g_try_malloc = ("g_try_malloc");
+  II_g_try_malloc0 = ("g_try_malloc0");
+  II_g_try_realloc = ("g_try_realloc");
+  II_g_free = ("g_free");
+  II_g_memdup = ("g_memdup");
 }
 
 bool MallocChecker::isMemFunction(const FunctionDecl *FD, ASTContext ) const {
@@ -589,15 +604,20 @@
 initIdentifierInfo(C);
 
 if (Family == AF_Malloc && CheckFree) {
-  if (FunI == II_free || FunI == II_realloc || FunI == II_reallocf)
+  if (FunI == II_free || FunI == II_realloc || FunI == II_reallocf || 
+  FunI == II_g_free)
 return true;
 }
 
 if (Family == AF_Malloc && CheckAlloc) {
   if (FunI == II_malloc || FunI == II_realloc || FunI == II_reallocf ||
   FunI == II_calloc || FunI == II_valloc || FunI == II_strdup ||
   FunI == II_win_strdup || FunI == II_strndup || FunI == II_wcsdup ||
-  FunI == II_win_wcsdup || FunI == II_kmalloc)
+  FunI == II_win_wcsdup || 

[PATCH] D28348: [analyzer] Taught the analyzer about Glib API to check Memory-leak

2017-02-22 Thread Leslie Zhai via Phabricator via cfe-commits
xiangzhai updated this revision to Diff 89333.
xiangzhai added a comment.

Fixed the confused

  State->getSVal(CE->getArg(1), C.getLocationContext());

with

  CE->getArg(1)

issue.


Repository:
  rL LLVM

https://reviews.llvm.org/D28348

Files:
  lib/StaticAnalyzer/Checkers/MallocChecker.cpp
  test/Analysis/gmalloc.c

Index: test/Analysis/gmalloc.c
===
--- test/Analysis/gmalloc.c
+++ test/Analysis/gmalloc.c
@@ -0,0 +1,169 @@
+// RUN: %clang_cc1 -analyze -analyzer-checker=core,unix.Malloc -analyzer-store=region -verify %s
+
+#include "Inputs/system-header-simulator.h"
+
+typedef void* gpointer;
+typedef const void* gconstpointer;
+typedef unsigned long gsize;
+typedef unsigned int guint;
+
+gpointer g_malloc(gsize n_bytes);
+gpointer g_malloc0(gsize n_bytes);
+gpointer g_realloc(gpointer mem, gsize n_bytes);
+gpointer g_try_malloc(gsize n_bytes);
+gpointer g_try_malloc0(gsize n_bytes);
+gpointer g_try_realloc(gpointer mem, gsize n_bytes);
+gpointer g_malloc_n(gsize n_blocks, gsize n_block_bytes);
+gpointer g_malloc0_n(gsize n_blocks, gsize n_block_bytes);
+gpointer g_realloc_n(gpointer mem, gsize n_blocks, gsize n_block_bytes);
+gpointer g_try_malloc_n(gsize n_blocks, gsize n_block_bytes);
+gpointer g_try_malloc0_n(gsize n_blocks, gsize n_block_bytes);
+gpointer g_try_realloc_n(gpointer mem, gsize n_blocks, gsize n_block_bytes);
+void g_free(gpointer mem);
+gpointer g_memdup(gconstpointer mem, guint byte_size);
+
+static const gsize n_bytes = 1024;
+
+void f1() {
+  gpointer g1 = g_malloc(n_bytes);
+  gpointer g2 = g_malloc0(n_bytes);
+  g1 = g_realloc(g1, n_bytes * 2);
+  gpointer g3 = g_try_malloc(n_bytes);
+  gpointer g4 = g_try_malloc0(n_bytes);
+  g3 = g_try_realloc(g3, n_bytes * 2);
+  gpointer g5 = g_malloc_n(n_bytes, sizeof(char));
+  gpointer g6 = g_malloc0_n(n_bytes, sizeof(char));
+  g5 = g_realloc_n(g5, n_bytes * 2, sizeof(char));
+  gpointer g7 = g_try_malloc_n(n_bytes, sizeof(char));
+  gpointer g8 = g_try_malloc0_n(n_bytes, sizeof(char));
+  g7 = g_try_realloc_n(g7, n_bytes * 2, sizeof(char));
+
+  g_free(g1);
+  g_free(g2);
+  g_free(g2); // expected-warning{{Attempt to free released memory}}
+}
+
+void f2() {
+  gpointer g1 = g_malloc(n_bytes);
+  gpointer g2 = g_malloc0(n_bytes);
+  g1 = g_realloc(g1, n_bytes * 2);
+  gpointer g3 = g_try_malloc(n_bytes);
+  gpointer g4 = g_try_malloc0(n_bytes);
+  g3 = g_try_realloc(g3, n_bytes * 2);
+  gpointer g5 = g_malloc_n(n_bytes, sizeof(char));
+  gpointer g6 = g_malloc0_n(n_bytes, sizeof(char));
+  g5 = g_realloc_n(g5, n_bytes * 2, sizeof(char));
+  gpointer g7 = g_try_malloc_n(n_bytes, sizeof(char));
+  gpointer g8 = g_try_malloc0_n(n_bytes, sizeof(char));
+  g7 = g_try_realloc_n(g7, n_bytes * 2, sizeof(char));
+
+  g_free(g1);
+  g_free(g2);
+  g_free(g3);
+  g3 = g_memdup(g3, n_bytes); // expected-warning{{Use of memory after it is freed}}
+}
+
+void f3() {
+  gpointer g1 = g_malloc(n_bytes);
+  gpointer g2 = g_malloc0(n_bytes);
+  g1 = g_realloc(g1, n_bytes * 2);
+  gpointer g3 = g_try_malloc(n_bytes);
+  gpointer g4 = g_try_malloc0(n_bytes);
+  g3 = g_try_realloc(g3, n_bytes * 2); // expected-warning{{Potential leak of memory pointed to by 'g4'}}
+  gpointer g5 = g_malloc_n(n_bytes, sizeof(char));
+  gpointer g6 = g_malloc0_n(n_bytes, sizeof(char));
+  g5 = g_realloc_n(g5, n_bytes * 2, sizeof(char)); // expected-warning{{Potential leak of memory pointed to by 'g6'}}
+  gpointer g7 = g_try_malloc_n(n_bytes, sizeof(char)); // expected-warning{{Potential leak of memory pointed to by 'g5'}}
+  gpointer g8 = g_try_malloc0_n(n_bytes, sizeof(char));
+  g7 = g_try_realloc_n(g7, n_bytes * 2, sizeof(char)); // expected-warning{{Potential leak of memory pointed to by 'g8'}}
+
+  g_free(g1); // expected-warning{{Potential leak of memory pointed to by 'g7'}}
+  g_free(g2);
+  g_free(g3);
+}
+
+void f4() {
+  gpointer g1 = g_malloc(n_bytes);
+  gpointer g2 = g_malloc0(n_bytes);
+  g1 = g_realloc(g1, n_bytes * 2);
+  gpointer g3 = g_try_malloc(n_bytes);
+  gpointer g4 = g_try_malloc0(n_bytes);
+  g3 = g_try_realloc(g3, n_bytes * 2);
+  gpointer g5 = g_malloc_n(n_bytes, sizeof(char));
+  gpointer g6 = g_malloc0_n(n_bytes, sizeof(char));
+  g5 = g_realloc_n(g5, n_bytes * 2, sizeof(char)); // expected-warning{{Potential leak of memory pointed to by 'g6'}}
+  gpointer g7 = g_try_malloc_n(n_bytes, sizeof(char)); // expected-warning{{Potential leak of memory pointed to by 'g5'}}
+  gpointer g8 = g_try_malloc0_n(n_bytes, sizeof(char));
+  g7 = g_try_realloc_n(g7, n_bytes * 2, sizeof(char)); // expected-warning{{Potential leak of memory pointed to by 'g8'}}
+
+  g_free(g1); // expected-warning{{Potential leak of memory pointed to by 'g7'}}
+  g_free(g2);
+  g_free(g3);
+  g_free(g4);
+}
+
+void f5() {
+  gpointer g1 = g_malloc(n_bytes);
+  gpointer g2 = g_malloc0(n_bytes);
+  g1 = g_realloc(g1, n_bytes * 2);
+  gpointer g3 = g_try_malloc(n_bytes);
+  gpointer g4 = g_try_malloc0(n_bytes);
+  g3 = 

[PATCH] D28348: [analyzer] Taught the analyzer about Glib API to check Memory-leak

2017-02-22 Thread Leslie Zhai via Phabricator via cfe-commits
xiangzhai updated this revision to Diff 89331.
xiangzhai added a comment.

Hi Anna,

I added **svalBinMulOp**  to take BO_Mul evalBinOp for g_malloc_n's two 
arguments: CE->getArg(0) and CE->getArg(1), so it does **NOT** need to change 
**MallocMemAux** any more, but just use it in this way:

  State = MallocMemAux(C, CE,   
   svalBinMulOp(C, CE->getArg(0), 
CE->getArg(1), State),
   UndefinedVal(), State);

And I also added **ReallocMemN** for g_realloc_n, it also use svalBinMulOp for 
**!StateSizeIsZero** check.

Please indicate my mistake, thanks a lot!

Regards,
Leslie Zhai


Repository:
  rL LLVM

https://reviews.llvm.org/D28348

Files:
  lib/StaticAnalyzer/Checkers/MallocChecker.cpp
  test/Analysis/gmalloc.c

Index: test/Analysis/gmalloc.c
===
--- test/Analysis/gmalloc.c
+++ test/Analysis/gmalloc.c
@@ -0,0 +1,169 @@
+// RUN: %clang_cc1 -analyze -analyzer-checker=core,unix.Malloc -analyzer-store=region -verify %s
+
+#include "Inputs/system-header-simulator.h"
+
+typedef void* gpointer;
+typedef const void* gconstpointer;
+typedef unsigned long gsize;
+typedef unsigned int guint;
+
+gpointer g_malloc(gsize n_bytes);
+gpointer g_malloc0(gsize n_bytes);
+gpointer g_realloc(gpointer mem, gsize n_bytes);
+gpointer g_try_malloc(gsize n_bytes);
+gpointer g_try_malloc0(gsize n_bytes);
+gpointer g_try_realloc(gpointer mem, gsize n_bytes);
+gpointer g_malloc_n(gsize n_blocks, gsize n_block_bytes);
+gpointer g_malloc0_n(gsize n_blocks, gsize n_block_bytes);
+gpointer g_realloc_n(gpointer mem, gsize n_blocks, gsize n_block_bytes);
+gpointer g_try_malloc_n(gsize n_blocks, gsize n_block_bytes);
+gpointer g_try_malloc0_n(gsize n_blocks, gsize n_block_bytes);
+gpointer g_try_realloc_n(gpointer mem, gsize n_blocks, gsize n_block_bytes);
+void g_free(gpointer mem);
+gpointer g_memdup(gconstpointer mem, guint byte_size);
+
+static const gsize n_bytes = 1024;
+
+void f1() {
+  gpointer g1 = g_malloc(n_bytes);
+  gpointer g2 = g_malloc0(n_bytes);
+  g1 = g_realloc(g1, n_bytes * 2);
+  gpointer g3 = g_try_malloc(n_bytes);
+  gpointer g4 = g_try_malloc0(n_bytes);
+  g3 = g_try_realloc(g3, n_bytes * 2);
+  gpointer g5 = g_malloc_n(n_bytes, sizeof(char));
+  gpointer g6 = g_malloc0_n(n_bytes, sizeof(char));
+  g5 = g_realloc_n(g5, n_bytes * 2, sizeof(char));
+  gpointer g7 = g_try_malloc_n(n_bytes, sizeof(char));
+  gpointer g8 = g_try_malloc0_n(n_bytes, sizeof(char));
+  g7 = g_try_realloc_n(g7, n_bytes * 2, sizeof(char));
+
+  g_free(g1);
+  g_free(g2);
+  g_free(g2); // expected-warning{{Attempt to free released memory}}
+}
+
+void f2() {
+  gpointer g1 = g_malloc(n_bytes);
+  gpointer g2 = g_malloc0(n_bytes);
+  g1 = g_realloc(g1, n_bytes * 2);
+  gpointer g3 = g_try_malloc(n_bytes);
+  gpointer g4 = g_try_malloc0(n_bytes);
+  g3 = g_try_realloc(g3, n_bytes * 2);
+  gpointer g5 = g_malloc_n(n_bytes, sizeof(char));
+  gpointer g6 = g_malloc0_n(n_bytes, sizeof(char));
+  g5 = g_realloc_n(g5, n_bytes * 2, sizeof(char));
+  gpointer g7 = g_try_malloc_n(n_bytes, sizeof(char));
+  gpointer g8 = g_try_malloc0_n(n_bytes, sizeof(char));
+  g7 = g_try_realloc_n(g7, n_bytes * 2, sizeof(char));
+
+  g_free(g1);
+  g_free(g2);
+  g_free(g3);
+  g3 = g_memdup(g3, n_bytes); // expected-warning{{Use of memory after it is freed}}
+}
+
+void f3() {
+  gpointer g1 = g_malloc(n_bytes);
+  gpointer g2 = g_malloc0(n_bytes);
+  g1 = g_realloc(g1, n_bytes * 2);
+  gpointer g3 = g_try_malloc(n_bytes);
+  gpointer g4 = g_try_malloc0(n_bytes);
+  g3 = g_try_realloc(g3, n_bytes * 2); // expected-warning{{Potential leak of memory pointed to by 'g4'}}
+  gpointer g5 = g_malloc_n(n_bytes, sizeof(char));
+  gpointer g6 = g_malloc0_n(n_bytes, sizeof(char));
+  g5 = g_realloc_n(g5, n_bytes * 2, sizeof(char)); // expected-warning{{Potential leak of memory pointed to by 'g6'}}
+  gpointer g7 = g_try_malloc_n(n_bytes, sizeof(char)); // expected-warning{{Potential leak of memory pointed to by 'g5'}}
+  gpointer g8 = g_try_malloc0_n(n_bytes, sizeof(char));
+  g7 = g_try_realloc_n(g7, n_bytes * 2, sizeof(char)); // expected-warning{{Potential leak of memory pointed to by 'g8'}}
+
+  g_free(g1); // expected-warning{{Potential leak of memory pointed to by 'g7'}}
+  g_free(g2);
+  g_free(g3);
+}
+
+void f4() {
+  gpointer g1 = g_malloc(n_bytes);
+  gpointer g2 = g_malloc0(n_bytes);
+  g1 = g_realloc(g1, n_bytes * 2);
+  gpointer g3 = g_try_malloc(n_bytes);
+  gpointer g4 = g_try_malloc0(n_bytes);
+  g3 = g_try_realloc(g3, n_bytes * 2);
+  gpointer g5 = g_malloc_n(n_bytes, sizeof(char));
+  gpointer g6 = g_malloc0_n(n_bytes, sizeof(char));
+  g5 = g_realloc_n(g5, n_bytes * 2, sizeof(char)); // expected-warning{{Potential leak of memory pointed to by 'g6'}}
+  gpointer g7 = g_try_malloc_n(n_bytes, sizeof(char)); // expected-warning{{Potential leak of memory pointed to by 'g5'}}
+ 

[PATCH] D28348: [analyzer] Taught the analyzer about Glib API to check Memory-leak

2017-02-19 Thread Leslie Zhai via Phabricator via cfe-commits
xiangzhai added a comment.

Hi Anna,

I am not clear why need to calculate the precise allocated size? for example:

void *ptr = malloc(size);
void *gptr = g_malloc_n(n_blocks, n_block_bytes);

Memory-leak and Use-after-free issues' MallocChecker need the ***size*** or 
***n_blocks*** x ***n_block_bytes***, but if the size is inaccurate, the 
checker is also ***able*** to detect the issues.

Regards,
Leslie Zhai




Comment at: lib/StaticAnalyzer/Checkers/MallocChecker.cpp:889
+} else if (FunI == II_g_realloc_n || FunI == II_g_try_realloc_n) {
+  if (CE->getNumArgs() < 2)
+return;

zaks.anna wrote:
> Should this be 'getNumArgs() < 3' ?
sorry typo...


Repository:
  rL LLVM

https://reviews.llvm.org/D28348



___
cfe-commits mailing list
cfe-commits@lists.llvm.org
http://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[PATCH] D28348: [analyzer] Taught the analyzer about Glib API to check Memory-leak

2017-02-19 Thread Leslie Zhai via Phabricator via cfe-commits
xiangzhai marked 3 inline comments as done.
xiangzhai added a comment.

Hi Anna,

Thank you so much for the review!

I will try to implement extend MallocMemAux and ReallocMem in the follow up 
patch.

Regards,
Leslie Zhai




Comment at: lib/StaticAnalyzer/Checkers/MallocChecker.cpp:885
+return;
+  State = MallocMemAux(C, CE, CE->getArg(0), UndefinedVal(), State);
+  State = ProcessZeroAllocation(C, CE, 0, State);

zaks.anna wrote:
> I am not sure this is correct as the third argument is "size of allocation", 
> which in this case would be the value of CE->getArg(0) times the value of 
> CE->getArg(2).
> 
> The current implementation of MallocMemAux would need to be extended to 
> incorporate this:
> `  // Set the region's extent equal to the Size parameter.
>   const SymbolicRegion *R =
>   dyn_cast_or_null(RetVal.getAsRegion());
>   if (!R)
> return nullptr;
>   if (Optional DefinedSize =
>   Size.getAs()) {
> SValBuilder  = C.getSValBuilder();
> DefinedOrUnknownSVal Extent = R->getExtent(svalBuilder);
> DefinedOrUnknownSVal extentMatchesSize =
> svalBuilder.evalEQ(State, Extent, *DefinedSize);
> 
> State = State->assume(extentMatchesSize, true);
> assert(State);
>   }`
> 
> My suggestion is to submit the patch without the 'n' variants and extend 
> MallocMemAux to deal with them as a follow up patch.
Hi Anna,

Thanks for your review!

> I am not sure this is correct as the third argument is "size of allocation", 
> which in this case would be the value of CE->getArg(0) times the value of 
> CE->getArg(2).

```g_malloc_n``` just use two arguments 
https://developer.gnome.org/glib/stable/glib-Memory-Allocation.html#g-malloc-n

so in this case would be the value of CE->getArg(0) x CE->getArg(1)?

> My suggestion is to submit the patch without the 'n' variants and extend 
> MallocMemAux to deal with them as a follow up patch.

I will drop XXX_n from this patch, then implement them until extend 
MallocMemAux and ReallocMem implemented in the follow up patch.

Regards,
Leslie Zhai


Repository:
  rL LLVM

https://reviews.llvm.org/D28348



___
cfe-commits mailing list
cfe-commits@lists.llvm.org
http://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[PATCH] D28348: [analyzer] Taught the analyzer about Glib API to check Memory-leak

2017-01-12 Thread Leslie Zhai via Phabricator via cfe-commits
xiangzhai updated this revision to Diff 84209.
xiangzhai added a comment.

Hi Anna,

Thanks for your review!

I process them (for example, g_malloc_n, take a different number of arguments) 
separately.

And I run the testcases for Analysis/malloc.c and Analysis/gmalloc.c

Regards,
Leslie Zhai


Repository:
  rL LLVM

https://reviews.llvm.org/D28348

Files:
  lib/StaticAnalyzer/Checkers/MallocChecker.cpp
  test/Analysis/gmalloc.c

Index: test/Analysis/gmalloc.c
===
--- test/Analysis/gmalloc.c
+++ test/Analysis/gmalloc.c
@@ -0,0 +1,169 @@
+// RUN: %clang_cc1 -analyze -analyzer-checker=core,unix.Malloc -analyzer-store=region -verify %s
+
+#include "Inputs/system-header-simulator.h"
+
+typedef void* gpointer;
+typedef const void* gconstpointer;
+typedef unsigned long gsize;
+typedef unsigned int guint;
+
+gpointer g_malloc(gsize n_bytes);
+gpointer g_malloc0(gsize n_bytes);
+gpointer g_realloc(gpointer mem, gsize n_bytes);
+gpointer g_try_malloc(gsize n_bytes);
+gpointer g_try_malloc0(gsize n_bytes);
+gpointer g_try_realloc(gpointer mem, gsize n_bytes);
+gpointer g_malloc_n(gsize n_blocks, gsize n_block_bytes);
+gpointer g_malloc0_n(gsize n_blocks, gsize n_block_bytes);
+gpointer g_realloc_n(gpointer mem, gsize n_blocks, gsize n_block_bytes);
+gpointer g_try_malloc_n(gsize n_blocks, gsize n_block_bytes);
+gpointer g_try_malloc0_n(gsize n_blocks, gsize n_block_bytes);
+gpointer g_try_realloc_n(gpointer mem, gsize n_blocks, gsize n_block_bytes);
+void g_free(gpointer mem);
+gpointer g_memdup(gconstpointer mem, guint byte_size);
+
+static const gsize n_bytes = 1024;
+
+void f1() {
+  gpointer g1 = g_malloc(n_bytes);
+  gpointer g2 = g_malloc0(n_bytes);
+  g1 = g_realloc(g1, n_bytes * 2);
+  gpointer g3 = g_try_malloc(n_bytes);
+  gpointer g4 = g_try_malloc0(n_bytes);
+  g3 = g_try_realloc(g3, n_bytes * 2);
+  gpointer g5 = g_malloc_n(n_bytes, sizeof(char));
+  gpointer g6 = g_malloc0_n(n_bytes, sizeof(char));
+  g5 = g_realloc_n(g5, n_bytes * 2, sizeof(char));
+  gpointer g7 = g_try_malloc_n(n_bytes, sizeof(char));
+  gpointer g8 = g_try_malloc0_n(n_bytes, sizeof(char));
+  g7 = g_try_realloc_n(g7, n_bytes * 2, sizeof(char));
+
+  g_free(g1);
+  g_free(g2);
+  g_free(g2); // expected-warning{{Attempt to free released memory}}
+}
+
+void f2() {
+  gpointer g1 = g_malloc(n_bytes);
+  gpointer g2 = g_malloc0(n_bytes);
+  g1 = g_realloc(g1, n_bytes * 2);
+  gpointer g3 = g_try_malloc(n_bytes);
+  gpointer g4 = g_try_malloc0(n_bytes);
+  g3 = g_try_realloc(g3, n_bytes * 2);
+  gpointer g5 = g_malloc_n(n_bytes, sizeof(char));
+  gpointer g6 = g_malloc0_n(n_bytes, sizeof(char));
+  g5 = g_realloc_n(g5, n_bytes * 2, sizeof(char));
+  gpointer g7 = g_try_malloc_n(n_bytes, sizeof(char));
+  gpointer g8 = g_try_malloc0_n(n_bytes, sizeof(char));
+  g7 = g_try_realloc_n(g7, n_bytes * 2, sizeof(char));
+
+  g_free(g1);
+  g_free(g2);
+  g_free(g3);
+  g3 = g_memdup(g3, n_bytes); // expected-warning{{Use of memory after it is freed}}
+}
+
+void f3() {
+  gpointer g1 = g_malloc(n_bytes);
+  gpointer g2 = g_malloc0(n_bytes);
+  g1 = g_realloc(g1, n_bytes * 2);
+  gpointer g3 = g_try_malloc(n_bytes);
+  gpointer g4 = g_try_malloc0(n_bytes);
+  g3 = g_try_realloc(g3, n_bytes * 2); // expected-warning{{Potential leak of memory pointed to by 'g4'}}
+  gpointer g5 = g_malloc_n(n_bytes, sizeof(char));
+  gpointer g6 = g_malloc0_n(n_bytes, sizeof(char));
+  g5 = g_realloc_n(g5, n_bytes * 2, sizeof(char)); // expected-warning{{Potential leak of memory pointed to by 'g6'}}
+  gpointer g7 = g_try_malloc_n(n_bytes, sizeof(char)); // expected-warning{{Potential leak of memory pointed to by 'g5'}}
+  gpointer g8 = g_try_malloc0_n(n_bytes, sizeof(char));
+  g7 = g_try_realloc_n(g7, n_bytes * 2, sizeof(char)); // expected-warning{{Potential leak of memory pointed to by 'g8'}}
+
+  g_free(g1); // expected-warning{{Potential leak of memory pointed to by 'g7'}}
+  g_free(g2);
+  g_free(g3);
+}
+
+void f4() {
+  gpointer g1 = g_malloc(n_bytes);
+  gpointer g2 = g_malloc0(n_bytes);
+  g1 = g_realloc(g1, n_bytes * 2);
+  gpointer g3 = g_try_malloc(n_bytes);
+  gpointer g4 = g_try_malloc0(n_bytes);
+  g3 = g_try_realloc(g3, n_bytes * 2);
+  gpointer g5 = g_malloc_n(n_bytes, sizeof(char));
+  gpointer g6 = g_malloc0_n(n_bytes, sizeof(char));
+  g5 = g_realloc_n(g5, n_bytes * 2, sizeof(char)); // expected-warning{{Potential leak of memory pointed to by 'g6'}}
+  gpointer g7 = g_try_malloc_n(n_bytes, sizeof(char)); // expected-warning{{Potential leak of memory pointed to by 'g5'}}
+  gpointer g8 = g_try_malloc0_n(n_bytes, sizeof(char));
+  g7 = g_try_realloc_n(g7, n_bytes * 2, sizeof(char)); // expected-warning{{Potential leak of memory pointed to by 'g8'}}
+
+  g_free(g1); // expected-warning{{Potential leak of memory pointed to by 'g7'}}
+  g_free(g2);
+  g_free(g3);
+  g_free(g4);
+}
+
+void f5() {
+  gpointer g1 = g_malloc(n_bytes);
+  gpointer g2 = g_malloc0(n_bytes);
+  g1 = 

[PATCH] D28348: [analyzer] Taught the analyzer about Glib API to check Memory-leak

2017-01-09 Thread Leslie Zhai via Phabricator via cfe-commits
xiangzhai updated this revision to Diff 83758.
xiangzhai marked 2 inline comments as done.
xiangzhai added a comment.

make II_g_*malloc*_n sense


Repository:
  rL LLVM

https://reviews.llvm.org/D28348

Files:
  lib/StaticAnalyzer/Checkers/MallocChecker.cpp
  test/Analysis/gmalloc.c

Index: test/Analysis/gmalloc.c
===
--- test/Analysis/gmalloc.c
+++ test/Analysis/gmalloc.c
@@ -0,0 +1,169 @@
+// RUN: %clang_cc1 -analyze -analyzer-checker=core,unix.Malloc -analyzer-store=region -verify %s
+
+#include "Inputs/system-header-simulator.h"
+
+typedef void* gpointer;
+typedef const void* gconstpointer;
+typedef unsigned long gsize;
+typedef unsigned int guint;
+
+gpointer g_malloc(gsize n_bytes);
+gpointer g_malloc0(gsize n_bytes);
+gpointer g_realloc(gpointer mem, gsize n_bytes);
+gpointer g_try_malloc(gsize n_bytes);
+gpointer g_try_malloc0(gsize n_bytes);
+gpointer g_try_realloc(gpointer mem, gsize n_bytes);
+gpointer g_malloc_n(gsize n_blocks, gsize n_block_bytes);
+gpointer g_malloc0_n(gsize n_blocks, gsize n_block_bytes);
+gpointer g_realloc_n(gpointer mem, gsize n_blocks, gsize n_block_bytes);
+gpointer g_try_malloc_n(gsize n_blocks, gsize n_block_bytes);
+gpointer g_try_malloc0_n(gsize n_blocks, gsize n_block_bytes);
+gpointer g_try_realloc_n(gpointer mem, gsize n_blocks, gsize n_block_bytes);
+void g_free(gpointer mem);
+gpointer g_memdup(gconstpointer mem, guint byte_size);
+
+static const gsize n_bytes = 1024;
+
+void f1() {
+  gpointer g1 = g_malloc(n_bytes);
+  gpointer g2 = g_malloc0(n_bytes);
+  g1 = g_realloc(g1, n_bytes * 2);
+  gpointer g3 = g_try_malloc(n_bytes);
+  gpointer g4 = g_try_malloc0(n_bytes);
+  g3 = g_try_realloc(g3, n_bytes * 2);
+  gpointer g5 = g_malloc_n(n_bytes, sizeof(char));
+  gpointer g6 = g_malloc0_n(n_bytes, sizeof(char));
+  g5 = g_realloc_n(g5, n_bytes * 2, sizeof(char));
+  gpointer g7 = g_try_malloc_n(n_bytes, sizeof(char));
+  gpointer g8 = g_try_malloc0_n(n_bytes, sizeof(char));
+  g7 = g_try_realloc_n(g7, n_bytes * 2, sizeof(char));
+
+  g_free(g1);
+  g_free(g2);
+  g_free(g2); // expected-warning{{Attempt to free released memory}}
+}
+
+void f2() {
+  gpointer g1 = g_malloc(n_bytes);
+  gpointer g2 = g_malloc0(n_bytes);
+  g1 = g_realloc(g1, n_bytes * 2);
+  gpointer g3 = g_try_malloc(n_bytes);
+  gpointer g4 = g_try_malloc0(n_bytes);
+  g3 = g_try_realloc(g3, n_bytes * 2);
+  gpointer g5 = g_malloc_n(n_bytes, sizeof(char));
+  gpointer g6 = g_malloc0_n(n_bytes, sizeof(char));
+  g5 = g_realloc_n(g5, n_bytes * 2, sizeof(char));
+  gpointer g7 = g_try_malloc_n(n_bytes, sizeof(char));
+  gpointer g8 = g_try_malloc0_n(n_bytes, sizeof(char));
+  g7 = g_try_realloc_n(g7, n_bytes * 2, sizeof(char));
+
+  g_free(g1);
+  g_free(g2);
+  g_free(g3);
+  g3 = g_memdup(g3, n_bytes); // expected-warning{{Use of memory after it is freed}}
+}
+
+void f3() {
+  gpointer g1 = g_malloc(n_bytes);
+  gpointer g2 = g_malloc0(n_bytes);
+  g1 = g_realloc(g1, n_bytes * 2);
+  gpointer g3 = g_try_malloc(n_bytes);
+  gpointer g4 = g_try_malloc0(n_bytes);
+  g3 = g_try_realloc(g3, n_bytes * 2); // expected-warning{{Potential leak of memory pointed to by 'g4'}}
+  gpointer g5 = g_malloc_n(n_bytes, sizeof(char));
+  gpointer g6 = g_malloc0_n(n_bytes, sizeof(char));
+  g5 = g_realloc_n(g5, n_bytes * 2, sizeof(char)); // expected-warning{{Potential leak of memory pointed to by 'g6'}}
+  gpointer g7 = g_try_malloc_n(n_bytes, sizeof(char)); // expected-warning{{Potential leak of memory pointed to by 'g5'}}
+  gpointer g8 = g_try_malloc0_n(n_bytes, sizeof(char));
+  g7 = g_try_realloc_n(g7, n_bytes * 2, sizeof(char)); // expected-warning{{Potential leak of memory pointed to by 'g8'}}
+
+  g_free(g1); // expected-warning{{Potential leak of memory pointed to by 'g7'}}
+  g_free(g2);
+  g_free(g3);
+}
+
+void f4() {
+  gpointer g1 = g_malloc(n_bytes);
+  gpointer g2 = g_malloc0(n_bytes);
+  g1 = g_realloc(g1, n_bytes * 2);
+  gpointer g3 = g_try_malloc(n_bytes);
+  gpointer g4 = g_try_malloc0(n_bytes);
+  g3 = g_try_realloc(g3, n_bytes * 2);
+  gpointer g5 = g_malloc_n(n_bytes, sizeof(char));
+  gpointer g6 = g_malloc0_n(n_bytes, sizeof(char));
+  g5 = g_realloc_n(g5, n_bytes * 2, sizeof(char)); // expected-warning{{Potential leak of memory pointed to by 'g6'}}
+  gpointer g7 = g_try_malloc_n(n_bytes, sizeof(char)); // expected-warning{{Potential leak of memory pointed to by 'g5'}}
+  gpointer g8 = g_try_malloc0_n(n_bytes, sizeof(char));
+  g7 = g_try_realloc_n(g7, n_bytes * 2, sizeof(char)); // expected-warning{{Potential leak of memory pointed to by 'g8'}}
+
+  g_free(g1); // expected-warning{{Potential leak of memory pointed to by 'g7'}}
+  g_free(g2);
+  g_free(g3);
+  g_free(g4);
+}
+
+void f5() {
+  gpointer g1 = g_malloc(n_bytes);
+  gpointer g2 = g_malloc0(n_bytes);
+  g1 = g_realloc(g1, n_bytes * 2);
+  gpointer g3 = g_try_malloc(n_bytes);
+  gpointer g4 = g_try_malloc0(n_bytes);
+  g3 = g_try_realloc(g3, n_bytes * 2);
+  

[PATCH] D28348: [analyzer] Taught the analyzer about Glib API to check Memory-leak

2017-01-08 Thread Leslie Zhai via Phabricator via cfe-commits
xiangzhai updated this revision to Diff 83587.
xiangzhai added a comment.

Hi Anna,

Thanks for your review!

I use:

  svn diff --diff-cmd=diff -x -U99 
lib/StaticAnalyzer/Checkers/MallocChecker.cpp test/Analysis/gmalloc.c > 
Glib-MallocChecker.patch

to generate the patch, please check is it correct.

And I run:

  clang -cc1 -analyze -analyzer-checker=core,unix.Malloc -analyzer-store=region 
-verify gmalloc.c

There is *NO* issue, please check it, thanks a lot!

Regards,
Leslie Zhai


Repository:
  rL LLVM

https://reviews.llvm.org/D28348

Files:
  lib/StaticAnalyzer/Checkers/MallocChecker.cpp
  test/Analysis/gmalloc.c

Index: test/Analysis/gmalloc.c
===
--- test/Analysis/gmalloc.c
+++ test/Analysis/gmalloc.c
@@ -0,0 +1,169 @@
+// RUN: %clang_cc1 -analyze -analyzer-checker=core,unix.Malloc -analyzer-store=region -verify %s
+
+#include "Inputs/system-header-simulator.h"
+
+typedef void* gpointer;
+typedef const void *gconstpointer;
+typedef unsigned long gsize;
+typedef unsigned int guint;
+
+gpointer g_malloc(gsize n_bytes);
+gpointer g_malloc0(gsize n_bytes);
+gpointer g_realloc(gpointer mem, gsize n_bytes);
+gpointer g_try_malloc(gsize n_bytes);
+gpointer g_try_malloc0(gsize n_bytes);
+gpointer g_try_realloc(gpointer mem, gsize n_bytes);
+gpointer g_malloc_n(gsize n_blocks, gsize n_block_bytes);
+gpointer g_malloc0_n(gsize n_blocks, gsize n_block_bytes);
+gpointer g_realloc_n(gpointer mem, gsize n_blocks, gsize n_block_bytes);
+gpointer g_try_malloc_n(gsize n_blocks, gsize n_block_bytes);
+gpointer g_try_malloc0_n(gsize n_blocks, gsize n_block_bytes);
+gpointer g_try_realloc_n(gpointer mem, gsize n_blocks, gsize n_block_bytes);
+void g_free(gpointer mem);
+gpointer g_memdup(gconstpointer mem, guint byte_size);
+
+static const gsize n_bytes = 1024;
+
+void f1() {
+  gpointer g1 = g_malloc(n_bytes);
+  gpointer g2 = g_malloc0(n_bytes);
+  g1 = g_realloc(g1, n_bytes * 2);
+  gpointer g3 = g_try_malloc(n_bytes);
+  gpointer g4 = g_try_malloc0(n_bytes);
+  g3 = g_try_realloc(g3, n_bytes * 2);
+  gpointer g5 = g_malloc_n(n_bytes, sizeof(char));
+  gpointer g6 = g_malloc0_n(n_bytes, sizeof(char));
+  g5 = g_realloc_n(g5, n_bytes * 2, sizeof(char));
+  gpointer g7 = g_try_malloc_n(n_bytes, sizeof(char));
+  gpointer g8 = g_try_malloc0_n(n_bytes, sizeof(char));
+  g7 = g_try_realloc_n(g7, n_bytes * 2, sizeof(char));
+
+  g_free(g1);
+  g_free(g2);
+  g_free(g2); // expected-warning{{Attempt to free released memory}}
+}
+
+void f2() {
+  gpointer g1 = g_malloc(n_bytes);
+  gpointer g2 = g_malloc0(n_bytes);
+  g1 = g_realloc(g1, n_bytes * 2);
+  gpointer g3 = g_try_malloc(n_bytes);
+  gpointer g4 = g_try_malloc0(n_bytes);
+  g3 = g_try_realloc(g3, n_bytes * 2);
+  gpointer g5 = g_malloc_n(n_bytes, sizeof(char));
+  gpointer g6 = g_malloc0_n(n_bytes, sizeof(char));
+  g5 = g_realloc_n(g5, n_bytes * 2, sizeof(char));
+  gpointer g7 = g_try_malloc_n(n_bytes, sizeof(char));
+  gpointer g8 = g_try_malloc0_n(n_bytes, sizeof(char));
+  g7 = g_try_realloc_n(g7, n_bytes * 2, sizeof(char));
+
+  g_free(g1);
+  g_free(g2);
+  g_free(g3);
+  g3 = g_memdup(g3, n_bytes); // expected-warning{{Use of memory after it is freed}}
+}
+
+void f3() {
+  gpointer g1 = g_malloc(n_bytes);
+  gpointer g2 = g_malloc0(n_bytes);
+  g1 = g_realloc(g1, n_bytes * 2);
+  gpointer g3 = g_try_malloc(n_bytes);
+  gpointer g4 = g_try_malloc0(n_bytes);
+  g3 = g_try_realloc(g3, n_bytes * 2); // expected-warning{{Potential leak of memory pointed to by 'g4'}}
+  gpointer g5 = g_malloc_n(n_bytes, sizeof(char));
+  gpointer g6 = g_malloc0_n(n_bytes, sizeof(char));
+  g5 = g_realloc_n(g5, n_bytes * 2, sizeof(char)); // expected-warning{{Potential leak of memory pointed to by 'g6'}}
+  gpointer g7 = g_try_malloc_n(n_bytes, sizeof(char)); // expected-warning{{Potential leak of memory pointed to by 'g5'}}
+  gpointer g8 = g_try_malloc0_n(n_bytes, sizeof(char));
+  g7 = g_try_realloc_n(g7, n_bytes * 2, sizeof(char)); // expected-warning{{Potential leak of memory pointed to by 'g8'}}
+
+  g_free(g1); // expected-warning{{Potential leak of memory pointed to by 'g7'}}
+  g_free(g2);
+  g_free(g3);
+}
+
+void f4() {
+  gpointer g1 = g_malloc(n_bytes);
+  gpointer g2 = g_malloc0(n_bytes);
+  g1 = g_realloc(g1, n_bytes * 2);
+  gpointer g3 = g_try_malloc(n_bytes);
+  gpointer g4 = g_try_malloc0(n_bytes);
+  g3 = g_try_realloc(g3, n_bytes * 2);
+  gpointer g5 = g_malloc_n(n_bytes, sizeof(char));
+  gpointer g6 = g_malloc0_n(n_bytes, sizeof(char));
+  g5 = g_realloc_n(g5, n_bytes * 2, sizeof(char)); // expected-warning{{Potential leak of memory pointed to by 'g6'}}
+  gpointer g7 = g_try_malloc_n(n_bytes, sizeof(char)); // expected-warning{{Potential leak of memory pointed to by 'g5'}}
+  gpointer g8 = g_try_malloc0_n(n_bytes, sizeof(char));
+  g7 = g_try_realloc_n(g7, n_bytes * 2, sizeof(char)); // expected-warning{{Potential leak of memory pointed to by 'g8'}}
+
+  g_free(g1); // 

[PATCH] D28348: [analyzer] Taught the analyzer about Glib API to check Memory-leak

2017-01-05 Thread Leslie Zhai via Phabricator via cfe-commits
xiangzhai updated this revision to Diff 83339.
xiangzhai added a comment.

Hi Anna,

Thanks for your review!

I resubmit the patch with context, please check is it correct, thanks a lot!
And I add testcase: test/Analysis/gmalloc.c


Repository:
  rL LLVM

https://reviews.llvm.org/D28348

Files:
  lib/StaticAnalyzer/Checkers/MallocChecker.cpp
  test/Analysis/gmalloc.c

Index: test/Analysis/gmalloc.c
===
--- test/Analysis/gmalloc.c
+++ test/Analysis/gmalloc.c
@@ -0,0 +1,191 @@
+// RUN: %clang_cc1 -analyze -analyzer-checker=core,alpha.deadcode.UnreachableCode,alpha.core.CastSize,unix.Malloc,debug.ExprInspection -analyzer-store=region -verify %s
+
+#include "Inputs/system-header-simulator.h"
+
+typedef void* gpointer;
+typedef const void *gconstpointer;
+typedef unsigned long gsize;
+typedef unsigned int guint;
+
+gpointer g_malloc(gsize n_bytes);
+gpointer g_malloc0(gsize n_bytes);
+gpointer g_realloc(gpointer mem, gsize n_bytes);
+gpointer g_try_malloc(gsize n_bytes);
+gpointer g_try_malloc0(gsize n_bytes);
+gpointer g_try_realloc(gpointer mem, gsize n_bytes);
+gpointer g_malloc_n(gsize n_blocks, gsize n_block_bytes);
+gpointer g_malloc0_n(gsize n_blocks, gsize n_block_bytes);
+gpointer g_realloc_n(gpointer mem, gsize n_blocks, gsize n_block_bytes);
+gpointer g_try_malloc_n(gsize n_blocks, gsize n_block_bytes);
+gpointer g_try_malloc0_n(gsize n_blocks, gsize n_block_bytes);
+gpointer g_try_realloc_n(gpointer mem, gsize n_blocks, gsize n_block_bytes);
+void g_free(gpointer mem);
+gpointer g_memdup(gconstpointer mem, guint byte_size);
+
+static const gsize n_bytes = 1024;
+
+void f1() {
+  gpointer g1 = g_malloc(n_bytes);
+  gpointer g2 = g_malloc0(n_bytes);
+  g1 = g_realloc(g1, n_bytes * 2);
+  gpointer g3 = g_try_malloc(n_bytes);
+  gpointer g4 = g_try_malloc0(n_bytes);
+  g3 = g_try_realloc(g3, n_bytes * 2);
+  gpointer g5 = g_malloc_n(n_bytes, sizeof(char));
+  gpointer g6 = g_malloc0_n(n_bytes, sizeof(char));
+  g5 = g_realloc_n(g5, n_bytes * 2, sizeof(char));
+  gpointer g7 = g_try_malloc_n(n_bytes, sizeof(char));
+  gpointer g8 = g_try_malloc0_n(n_bytes, sizeof(char));
+  g7 = g_try_realloc_n(g7, n_bytes * 2, sizeof(char));
+
+  g_free(g1);
+  g_free(g2);
+  g_free(g2); // g2 Double-free
+  g_free(g3);
+  g3 = g_memdup(g3, n_bytes); // g3 Use-after-free
+  // g4 Memory-leak
+  // g5 Memory-leak
+  // g6 Memory-leak
+  // g7 Memory-leak
+  // g8 Memory-leak
+}
+
+void f2() {
+  gpointer g1 = g_malloc(n_bytes);
+  gpointer g2 = g_malloc0(n_bytes);
+  g1 = g_realloc(g1, n_bytes * 2);
+  gpointer g3 = g_try_malloc(n_bytes);
+  gpointer g4 = g_try_malloc0(n_bytes);
+  g3 = g_try_realloc(g3, n_bytes * 2);
+  gpointer g5 = g_malloc_n(n_bytes, sizeof(char));
+  gpointer g6 = g_malloc0_n(n_bytes, sizeof(char));
+  g5 = g_realloc_n(g5, n_bytes * 2, sizeof(char));
+  gpointer g7 = g_try_malloc_n(n_bytes, sizeof(char));
+  gpointer g8 = g_try_malloc0_n(n_bytes, sizeof(char));
+  g7 = g_try_realloc_n(g7, n_bytes * 2, sizeof(char));
+
+  g_free(g1);
+  g_free(g2);
+  g_free(g3);
+  g3 = g_memdup(g3, n_bytes); // g3 Use-after-free
+}
+
+void f3() {
+  gpointer g1 = g_malloc(n_bytes);
+  gpointer g2 = g_malloc0(n_bytes);
+  g1 = g_realloc(g1, n_bytes * 2);
+  gpointer g3 = g_try_malloc(n_bytes);
+  gpointer g4 = g_try_malloc0(n_bytes);
+  g3 = g_try_realloc(g3, n_bytes * 2);
+  gpointer g5 = g_malloc_n(n_bytes, sizeof(char));
+  gpointer g6 = g_malloc0_n(n_bytes, sizeof(char));
+  g5 = g_realloc_n(g5, n_bytes * 2, sizeof(char));
+  gpointer g7 = g_try_malloc_n(n_bytes, sizeof(char));
+  gpointer g8 = g_try_malloc0_n(n_bytes, sizeof(char));
+  g7 = g_try_realloc_n(g7, n_bytes * 2, sizeof(char));
+
+  g_free(g1);
+  g_free(g2);
+  g_free(g3);
+  // g4 Memory-leak
+  // g5 Memory-leak
+  // g6 Memory-leak
+  // g7 Memory-leak
+  // g8 Memory-leak
+}
+
+void f4() {
+  gpointer g1 = g_malloc(n_bytes);
+  gpointer g2 = g_malloc0(n_bytes);
+  g1 = g_realloc(g1, n_bytes * 2);
+  gpointer g3 = g_try_malloc(n_bytes);
+  gpointer g4 = g_try_malloc0(n_bytes);
+  g3 = g_try_realloc(g3, n_bytes * 2);
+  gpointer g5 = g_malloc_n(n_bytes, sizeof(char));
+  gpointer g6 = g_malloc0_n(n_bytes, sizeof(char));
+  g5 = g_realloc_n(g5, n_bytes * 2, sizeof(char));
+  gpointer g7 = g_try_malloc_n(n_bytes, sizeof(char));
+  gpointer g8 = g_try_malloc0_n(n_bytes, sizeof(char));
+  g7 = g_try_realloc_n(g7, n_bytes * 2, sizeof(char));
+
+  g_free(g1);
+  g_free(g2);
+  g_free(g3);
+  g_free(g4);
+  // g5 Memory-leak
+  // g6 Memory-leak
+  // g7 Memory-leak
+  // g8 Memory-leak
+}
+
+void f5() {
+  gpointer g1 = g_malloc(n_bytes);
+  gpointer g2 = g_malloc0(n_bytes);
+  g1 = g_realloc(g1, n_bytes * 2);
+  gpointer g3 = g_try_malloc(n_bytes);
+  gpointer g4 = g_try_malloc0(n_bytes);
+  g3 = g_try_realloc(g3, n_bytes * 2);
+  gpointer g5 = g_malloc_n(n_bytes, sizeof(char));
+  gpointer g6 = g_malloc0_n(n_bytes, sizeof(char));
+  g5 = g_realloc_n(g5, n_bytes * 2, sizeof(char));
+  

[PATCH] D16171: Warning on redeclaring with a conflicting asm label

2016-12-18 Thread Leslie Zhai via Phabricator via cfe-commits
xiangzhai added a comment.

LLVMBUG-31017 https://llvm.org/bugs/show_bug.cgi?id=31017#c4

In https://reviews.llvm.org/D16171#540261, @phabricss wrote:

> On 09/12/2016 01:26 PM, Nick Lewycky wrote:
>
> > Firstly, I thought glibc had applied a patch to fix this bug? As in, the 
> > error is correct and glibc fixed their bug?
>
> I can confirm that the bug still exists in glibc 2.24 and HEAD from glibc 
> git.  Also it appears that the issue on the llvm mailing list was just 
> dropped without any resolution:
>
> r255371 - Error on redeclaring with a conflicting asm label 
> 
>
>   ../include/sys/stat.h:16:15: error: cannot apply asm label to function 
> after its first use
>   hidden_proto (__fxstat)
>   ~~^
>   ./../include/libc-symbols.h:420:19: note: expanded from macro 'hidden_proto'
> __hidden_proto (name, , __GI_##name, ##attrs)
> ^
>   ./../include/libc-symbols.h:424:33: note: expanded from macro 
> '__hidden_proto'
> extern thread __typeof (name) name __asm__ (__hidden_asmname (#internal)) 
> \
>
>
> As far as your review of the patch by weimingz, that is beyond my skill level 
> so I will let him reply.  Thanks!





https://reviews.llvm.org/D16171



___
cfe-commits mailing list
cfe-commits@lists.llvm.org
http://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits