[PATCH] D35051: [clang-tidy] Add misc-undefined-memory-manipulation check.

2017-07-11 Thread Alexander Kornienko via Phabricator via cfe-commits
alexfh added a comment.

Another thing is that at this point I'd already create a `bugprone` module (if 
nobody has a better name) and place the check there (together with the other 
memset-related check).


https://reviews.llvm.org/D35051



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


[PATCH] D35051: [clang-tidy] Add misc-undefined-memory-manipulation check.

2017-07-11 Thread Alexander Kornienko via Phabricator via cfe-commits
alexfh added a comment.

As usual, please run the check at least on LLVM+Clang and include a brief 
summary of results into the description of the patch.


https://reviews.llvm.org/D35051



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


[PATCH] D35051: [clang-tidy] Add misc-undefined-memory-manipulation check.

2017-07-06 Thread Reka Kovacs via Phabricator via cfe-commits
rnkovacs created this revision.
rnkovacs added a project: clang-tools-extra.
Herald added subscribers: whisperity, JDevlieghere, mgorny.

Finds calls of memory manipulation functions `memset()`, `memcpy()` and 
`memmove()` on not TriviallyCopyable objects resulting in undefined behavior.

Related discussion .


https://reviews.llvm.org/D35051

Files:
  clang-tidy/misc/CMakeLists.txt
  clang-tidy/misc/MiscTidyModule.cpp
  clang-tidy/misc/UndefinedMemoryManipulationCheck.cpp
  clang-tidy/misc/UndefinedMemoryManipulationCheck.h
  docs/ReleaseNotes.rst
  docs/clang-tidy/checks/list.rst
  docs/clang-tidy/checks/misc-undefined-memory-manipulation.rst
  test/clang-tidy/misc-undefined-memory-manipulation.cpp

Index: test/clang-tidy/misc-undefined-memory-manipulation.cpp
===
--- /dev/null
+++ test/clang-tidy/misc-undefined-memory-manipulation.cpp
@@ -0,0 +1,178 @@
+// RUN: %check_clang_tidy %s misc-undefined-memory-manipulation %t
+
+void *memset(void *, int, __SIZE_TYPE__);
+void *memcpy(void *, const void *, __SIZE_TYPE__);
+void *memmove(void *, const void *, __SIZE_TYPE__);
+
+namespace std {
+using ::memcpy;
+using ::memmove;
+using ::memset;
+}
+
+// TriviallyCopyable types:
+struct Plain {
+  int n;
+};
+
+enum E {
+  X,
+  Y,
+  Z
+};
+
+struct Base {
+  float b;
+};
+
+struct Derived : Base {
+  bool d;
+};
+
+// not TriviallyCopyable types:
+struct Destruct {
+  ~Destruct() {};
+};
+
+struct Copy {
+  Copy() {};
+  Copy(const Copy &) {};
+};
+
+struct Move {
+  Move() {};
+  Move(Move &&) {};
+};
+
+struct VirtualFunc {
+  virtual void f() {};
+};
+
+struct VirtualBase : virtual Base {
+  int vb;
+};
+
+template 
+void memset_temp(T *b) {
+  memset(b, 0, sizeof(T));
+  // CHECK-MESSAGES: :[[@LINE-1]]:3: warning: undefined behavior, destination object is not TriviallyCopyable [misc-undefined-memory-manipulation]
+}
+
+template 
+void memcpy_temp(S *a, T *b) {
+  memcpy(a, b, sizeof(T));
+  // CHECK-MESSAGES: :[[@LINE-1]]:3: warning: undefined behavior, source object is not TriviallyCopyable [misc-undefined-memory-manipulation]
+}
+
+template 
+void memmove_temp(S *a, T *b) {
+  memmove(a, b, sizeof(T));
+  // CHECK-MESSAGES: :[[@LINE-1]]:3: warning: undefined behavior, source object is not TriviallyCopyable [misc-undefined-memory-manipulation]
+}
+
+void notTriviallyCopyable() {
+  Plain p; // TriviallyCopyable for variety
+  Destruct d;
+  Copy c;
+  Move m;
+  VirtualFunc vf;
+  VirtualBase vb;
+
+  memset(, 0, sizeof(int));
+  // CHECK-MESSAGES: :[[@LINE-1]]:3: warning: undefined behavior, destination object is not TriviallyCopyable [misc-undefined-memory-manipulation]
+  memset(, 0, sizeof(int));
+  // CHECK-MESSAGES: :[[@LINE-1]]:3: warning: undefined behavior, destination object is not TriviallyCopyable [misc-undefined-memory-manipulation]
+  memset(, 0, sizeof(int));
+  // CHECK-MESSAGES: :[[@LINE-1]]:3: warning: undefined behavior, destination object is not TriviallyCopyable [misc-undefined-memory-manipulation]
+  std::memset(, 0, sizeof(int));
+  // CHECK-MESSAGES: :[[@LINE-1]]:3: warning: undefined behavior, destination object is not TriviallyCopyable [misc-undefined-memory-manipulation]
+  ::memset(, 0, sizeof(int));
+  // CHECK-MESSAGES: :[[@LINE-1]]:3: warning: undefined behavior, destination object is not TriviallyCopyable [misc-undefined-memory-manipulation]
+
+  memcpy(, , sizeof(int));
+  // CHECK-MESSAGES: :[[@LINE-1]]:3: warning: undefined behavior, source object is not TriviallyCopyable [misc-undefined-memory-manipulation]
+  memcpy(, , sizeof(int));
+  // CHECK-MESSAGES: :[[@LINE-1]]:3: warning: undefined behavior, source object is not TriviallyCopyable [misc-undefined-memory-manipulation]
+  memcpy(, , sizeof(int));
+  // CHECK-MESSAGES: :[[@LINE-1]]:3: warning: undefined behavior, destination object is not TriviallyCopyable [misc-undefined-memory-manipulation]
+  std::memcpy(, , sizeof(int));
+  // CHECK-MESSAGES: :[[@LINE-1]]:3: warning: undefined behavior, destination object is not TriviallyCopyable [misc-undefined-memory-manipulation]
+  ::memcpy(, , sizeof(int));
+  // CHECK-MESSAGES: :[[@LINE-1]]:3: warning: undefined behavior, destination object is not TriviallyCopyable [misc-undefined-memory-manipulation]
+
+  memmove(, , sizeof(int));
+  // CHECK-MESSAGES: :[[@LINE-1]]:3: warning: undefined behavior, destination object is not TriviallyCopyable [misc-undefined-memory-manipulation]
+  memmove(, , sizeof(int));
+  // CHECK-MESSAGES: :[[@LINE-1]]:3: warning: undefined behavior, destination object is not TriviallyCopyable [misc-undefined-memory-manipulation]
+  memmove(, , sizeof(int));
+  // CHECK-MESSAGES: :[[@LINE-1]]:3: warning: undefined behavior, source object is not TriviallyCopyable [misc-undefined-memory-manipulation]
+  std::memmove(, , sizeof(int));
+  // CHECK-MESSAGES: :[[@LINE-1]]:3: warning: undefined behavior, source object is not TriviallyCopyable