]> granicus.if.org Git - llvm/commitdiff
Bitcode: Correctly handle Fixed and VBR arrays in BitstreamCursor::skipRecord().
authorPeter Collingbourne <peter@pcc.me.uk>
Thu, 1 Dec 2016 05:47:58 +0000 (05:47 +0000)
committerPeter Collingbourne <peter@pcc.me.uk>
Thu, 1 Dec 2016 05:47:58 +0000 (05:47 +0000)
The assertions were wrong; we need to call getEncodingData() on the element,
not the array. While here, simplify the skipRecord() implementation for Fixed
and Char6 arrays. This is tested by the code I added to llvm-bcanalyzer
which makes sure that we can skip any record.

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

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

lib/Bitcode/Reader/BitstreamReader.cpp
tools/llvm-bcanalyzer/llvm-bcanalyzer.cpp

index f1237069f7b889fbc1abebcc039843310a2a3ac6..43c9aebd79ef7845eeee32b9c1281997b5373c24 100644 (file)
@@ -131,18 +131,16 @@ void BitstreamCursor::skipRecord(unsigned AbbrevID) {
       default:
         report_fatal_error("Array element type can't be an Array or a Blob");
       case BitCodeAbbrevOp::Fixed:
-        assert((unsigned)Op.getEncodingData() <= MaxChunkSize);
-        for (; NumElts; --NumElts)
-          Read((unsigned)EltEnc.getEncodingData());
+        assert((unsigned)EltEnc.getEncodingData() <= MaxChunkSize);
+        JumpToBit(GetCurrentBitNo() + NumElts * EltEnc.getEncodingData());
         break;
       case BitCodeAbbrevOp::VBR:
-        assert((unsigned)Op.getEncodingData() <= MaxChunkSize);
+        assert((unsigned)EltEnc.getEncodingData() <= MaxChunkSize);
         for (; NumElts; --NumElts)
           ReadVBR64((unsigned)EltEnc.getEncodingData());
         break;
       case BitCodeAbbrevOp::Char6:
-        for (; NumElts; --NumElts)
-          Read(6);
+        JumpToBit(GetCurrentBitNo() + NumElts * 6);
         break;
       }
       continue;
index 14957e60b2be45b21331cbb2ee7e3c3c69baec20..d866201723a8eed0fe81bc3260da80b7c31da584 100644 (file)
@@ -567,7 +567,7 @@ static bool ParseBlock(BitstreamCursor &Stream, BitstreamBlockInfo &BlockInfo,
     ++BlockStats.NumRecords;
 
     StringRef Blob;
-    unsigned CurrentRecordPos = Stream.getCurrentByteNo();
+    unsigned CurrentRecordPos = Stream.GetCurrentBitNo();
     unsigned Code = Stream.readRecord(Entry.ID, Record, &Blob);
 
     // Increment the # occurrences of this code.
@@ -608,7 +608,7 @@ static bool ParseBlock(BitstreamCursor &Stream, BitstreamBlockInfo &BlockInfo,
           SHA1 Hasher;
           StringRef Hash;
           {
-            int BlockSize = CurrentRecordPos - BlockEntryPos;
+            int BlockSize = (CurrentRecordPos / 8) - BlockEntryPos;
             auto Ptr = Stream.getPointerToByte(BlockEntryPos, BlockSize);
             Hasher.update(ArrayRef<uint8_t>(Ptr, BlockSize));
             Hash = Hasher.result();
@@ -675,6 +675,10 @@ static bool ParseBlock(BitstreamCursor &Stream, BitstreamBlockInfo &BlockInfo,
 
       outs() << "\n";
     }
+
+    // Make sure that we can skip the current record.
+    Stream.JumpToBit(CurrentRecordPos);
+    Stream.skipRecord(Entry.ID);
   }
 }