[llvm] 2c196bb - Add an assertion in SmallVector::push_back()

Mehdi Amini via llvm-commits llvm-commits at lists.llvm.org
Fri Nov 13 16:56:26 PST 2020


Author: Mehdi Amini
Date: 2020-11-14T00:55:34Z
New Revision: 2c196bbc6bd897b3dcc1d87a3baac28e1e88df41

URL: https://github.com/llvm/llvm-project/commit/2c196bbc6bd897b3dcc1d87a3baac28e1e88df41
DIFF: https://github.com/llvm/llvm-project/commit/2c196bbc6bd897b3dcc1d87a3baac28e1e88df41.diff

LOG: Add an assertion in SmallVector::push_back()

This assertion ensures the input value isn't part of the vector when
growing is required. In such cases the vector will grow and the input
value is invalidated before being read from.

This found 14 failed Tests.

Reviewed By: bkramer

Differential Revision: https://reviews.llvm.org/D84293

Added: 
    

Modified: 
    llvm/include/llvm/ADT/SmallVector.h
    llvm/include/llvm/MC/MCInst.h

Removed: 
    


################################################################################
diff  --git a/llvm/include/llvm/ADT/SmallVector.h b/llvm/include/llvm/ADT/SmallVector.h
index e042497473db2..fbc8ede255d2b 100644
--- a/llvm/include/llvm/ADT/SmallVector.h
+++ b/llvm/include/llvm/ADT/SmallVector.h
@@ -136,6 +136,13 @@ class SmallVectorTemplateCommon
     this->Size = this->Capacity = 0; // FIXME: Setting Capacity to 0 is suspect.
   }
 
+  void assertSafeToPush(const void *Elt) {
+    assert(
+        (Elt < begin() || Elt >= end() || this->size() < this->capacity()) &&
+        "Attempting to push_back to the vector an element of the vector without"
+        " enough space reserved");
+  }
+
 public:
   using size_type = size_t;
   using 
diff erence_type = ptr
diff _t;
@@ -251,6 +258,7 @@ class SmallVectorTemplateBase : public SmallVectorTemplateCommon<T> {
 
 public:
   void push_back(const T &Elt) {
+    this->assertSafeToPush(&Elt);
     if (LLVM_UNLIKELY(this->size() >= this->capacity()))
       this->grow();
     ::new ((void*) this->end()) T(Elt);
@@ -258,6 +266,7 @@ class SmallVectorTemplateBase : public SmallVectorTemplateCommon<T> {
   }
 
   void push_back(T &&Elt) {
+    this->assertSafeToPush(&Elt);
     if (LLVM_UNLIKELY(this->size() >= this->capacity()))
       this->grow();
     ::new ((void*) this->end()) T(::std::move(Elt));
@@ -353,6 +362,7 @@ class SmallVectorTemplateBase<T, true> : public SmallVectorTemplateCommon<T> {
 
 public:
   void push_back(const T &Elt) {
+    this->assertSafeToPush(&Elt);
     if (LLVM_UNLIKELY(this->size() >= this->capacity()))
       this->grow();
     memcpy(reinterpret_cast<void *>(this->end()), &Elt, sizeof(T));

diff  --git a/llvm/include/llvm/MC/MCInst.h b/llvm/include/llvm/MC/MCInst.h
index 360dbda58fcbd..2ce2ee063daa7 100644
--- a/llvm/include/llvm/MC/MCInst.h
+++ b/llvm/include/llvm/MC/MCInst.h
@@ -181,7 +181,7 @@ class MCInst {
   MCOperand &getOperand(unsigned i) { return Operands[i]; }
   unsigned getNumOperands() const { return Operands.size(); }
 
-  void addOperand(const MCOperand &Op) { Operands.push_back(Op); }
+  void addOperand(const MCOperand Op) { Operands.push_back(Op); }
 
   using iterator = SmallVectorImpl<MCOperand>::iterator;
   using const_iterator = SmallVectorImpl<MCOperand>::const_iterator;


        


More information about the llvm-commits mailing list