[msan] Raise alignment of origin stores/loads when possible.
authorEvgeniy Stepanov <eugeni.stepanov@gmail.com>
Wed, 26 Dec 2012 11:55:09 +0000 (11:55 +0000)
committerEvgeniy Stepanov <eugeni.stepanov@gmail.com>
Wed, 26 Dec 2012 11:55:09 +0000 (11:55 +0000)
Origin alignment is as high as the alignment of the corresponding application
location, but never less than 4.

git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@171110 91177308-0d34-0410-b5e6-96231b3b80d8

lib/Transforms/Instrumentation/MemorySanitizer.cpp
test/Instrumentation/MemorySanitizer/msan_basic.ll

index 3993d887552e23776dcde82436c8b3fc5dc16476..5a954d401ebf1727c9e650393253d2a4bd342f77 100644 (file)
@@ -100,7 +100,8 @@ static const uint64_t kShadowMask32 = 1ULL << 31;
 static const uint64_t kShadowMask64 = 1ULL << 46;
 static const uint64_t kOriginOffset32 = 1ULL << 30;
 static const uint64_t kOriginOffset64 = 1ULL << 45;
-static const uint64_t kShadowTLSAlignment = 8;
+static const unsigned kMinOriginAlignment = 4;
+static const unsigned kShadowTLSAlignment = 8;
 
 /// \brief Track origins of uninitialized values.
 /// 
@@ -451,8 +452,10 @@ struct MemorySanitizerVisitor : public InstVisitor<MemorySanitizerVisitor> {
         insertCheck(Addr, &I);
 
       if (MS.TrackOrigins) {
+        unsigned Alignment = std::max(kMinOriginAlignment, I.getAlignment());
         if (ClStoreCleanOrigin || isa<StructType>(Shadow->getType())) {
-          IRB.CreateStore(getOrigin(Val), getOriginPtr(Addr, IRB));
+          IRB.CreateAlignedStore(getOrigin(Val), getOriginPtr(Addr, IRB),
+                                 Alignment);
         } else {
           Value *ConvertedShadow = convertToShadowTyNoVec(Shadow, IRB);
 
@@ -469,7 +472,8 @@ struct MemorySanitizerVisitor : public InstVisitor<MemorySanitizerVisitor> {
             SplitBlockAndInsertIfThen(cast<Instruction>(Cmp), false,
                                       MS.OriginStoreWeights);
           IRBuilder<> IRBNew(CheckTerm);
-          IRBNew.CreateStore(getOrigin(Val), getOriginPtr(Addr, IRBNew));
+          IRBNew.CreateAlignedStore(getOrigin(Val), getOriginPtr(Addr, IRBNew),
+                                    Alignment);
         }
       }
     }
@@ -827,8 +831,10 @@ struct MemorySanitizerVisitor : public InstVisitor<MemorySanitizerVisitor> {
     if (ClCheckAccessAddress)
       insertCheck(I.getPointerOperand(), &I);
 
-    if (MS.TrackOrigins)
-      setOrigin(&I, IRB.CreateLoad(getOriginPtr(Addr, IRB)));
+    if (MS.TrackOrigins) {
+      unsigned Alignment = std::max(kMinOriginAlignment, I.getAlignment());
+      setOrigin(&I, IRB.CreateAlignedLoad(getOriginPtr(Addr, IRB), Alignment));
+    }
   }
 
   /// \brief Instrument StoreInst
index cd20329933655ef75bfc3496ba400c1ef3d75757..20957fb36f4e91a79ad2c448edb7832727bc6c71 100644 (file)
@@ -56,7 +56,7 @@ entry:
 ; CHECK-ORIGINS: icmp
 ; CHECK-ORIGINS: br i1
 ; CHECK-ORIGINS: <label>
-; CHECK-ORIGINS-NOT: store {{.*}} align
+; CHECK-ORIGINS: store {{.*}} align 32
 ; CHECK-ORIGINS: br label
 ; CHECK-ORIGINS: <label>
 ; CHECK-ORIGINS: store {{.*}} align 32
@@ -362,7 +362,8 @@ define zeroext i1 @ICmpSLE(i32 %x) nounwind uwtable readnone {
 ; CHECK: ret i1
 
 
-; Check that loads from shadow have the same aligment as the original loads.
+; Check that loads of shadow have the same aligment as the original loads.
+; Check that loads of origin have the aligment of max(4, original alignment).
 
 define i32 @ShadowLoadAlignmentLarge() nounwind uwtable {
   %y = alloca i32, align 64
@@ -386,6 +387,12 @@ define i32 @ShadowLoadAlignmentSmall() nounwind uwtable {
 ; CHECK: load volatile i32* {{.*}} align 2
 ; CHECK: ret i32
 
+; CHECK-ORIGINS: @ShadowLoadAlignmentSmall
+; CHECK-ORIGINS: load i32* {{.*}} align 2
+; CHECK-ORIGINS: load i32* {{.*}} align 4
+; CHECK-ORIGINS: load volatile i32* {{.*}} align 2
+; CHECK-ORIGINS: ret i32
+
 
 ; Test vector manipulation instructions.
 ; Check that the same bit manipulation is applied to the shadow values.