[llvm] [memprof] Introduce readMemProf (NFC) (PR #88095)

Snehasish Kumar via llvm-commits llvm-commits at lists.llvm.org
Tue Apr 9 09:58:14 PDT 2024


================
@@ -1206,6 +1206,143 @@ IndexedInstrProfReader::readSummary(IndexedInstrProf::ProfVersion Version,
   }
 }
 
+static Error
+readMemProfV0(const unsigned char *Start, const unsigned char *Ptr,
+              uint64_t FirstWord, memprof::MemProfSchema &Schema,
+              std::unique_ptr<MemProfRecordHashTable> &MemProfRecordTable,
+              std::unique_ptr<MemProfFrameHashTable> &MemProfFrameTable) {
+  using namespace support;
+
+  // The value returned from RecordTableGenerator.Emit.
+  const uint64_t RecordTableOffset = FirstWord;
+  // The offset in the stream right before invoking
+  // FrameTableGenerator.Emit.
+  const uint64_t FramePayloadOffset =
+      support::endian::readNext<uint64_t, llvm::endianness::little, unaligned>(
+          Ptr);
+  // The value returned from FrameTableGenerator.Emit.
+  const uint64_t FrameTableOffset =
+      support::endian::readNext<uint64_t, llvm::endianness::little, unaligned>(
+          Ptr);
+
+  // Read the schema.
+  auto SchemaOr = memprof::readMemProfSchema(Ptr);
+  if (!SchemaOr)
+    return SchemaOr.takeError();
+  Schema = SchemaOr.get();
+
+  // Now initialize the table reader with a pointer into data buffer.
+  MemProfRecordTable.reset(MemProfRecordHashTable::Create(
+      /*Buckets=*/Start + RecordTableOffset,
+      /*Payload=*/Ptr,
+      /*Base=*/Start, memprof::RecordLookupTrait(memprof::Version0, Schema)));
+
+  // Initialize the frame table reader with the payload and bucket offsets.
+  MemProfFrameTable.reset(MemProfFrameHashTable::Create(
+      /*Buckets=*/Start + FrameTableOffset,
+      /*Payload=*/Start + FramePayloadOffset,
+      /*Base=*/Start, memprof::FrameLookupTrait()));
+
+#ifdef EXPENSIVE_CHECKS
+  // Go through all the records and verify that CSId has been correctly
+  // populated.  Do this only under EXPENSIVE_CHECKS.  Otherwise, we
+  // would defeat the purpose of OnDiskIterableChainedHashTable.
+  for (const auto &Record : MemProfRecordTable->data())
+    verifyIndexedMemProfRecord(Record);
+#endif
+
+  return Error::success();
+}
+
+static Error
+readMemProfV1(const unsigned char *Start, const unsigned char *Ptr,
+              memprof::MemProfSchema &Schema,
+              std::unique_ptr<MemProfRecordHashTable> &MemProfRecordTable,
+              std::unique_ptr<MemProfFrameHashTable> &MemProfFrameTable) {
+  using namespace support;
+
+  // The value returned from RecordTableGenerator.Emit.
+  const uint64_t RecordTableOffset =
+      support::endian::readNext<uint64_t, llvm::endianness::little, unaligned>(
+          Ptr);
+  // The offset in the stream right before invoking
+  // FrameTableGenerator.Emit.
+  const uint64_t FramePayloadOffset =
+      support::endian::readNext<uint64_t, llvm::endianness::little, unaligned>(
+          Ptr);
+  // The value returned from FrameTableGenerator.Emit.
+  const uint64_t FrameTableOffset =
+      support::endian::readNext<uint64_t, llvm::endianness::little, unaligned>(
+          Ptr);
+
+  // Read the schema.
+  auto SchemaOr = memprof::readMemProfSchema(Ptr);
+  if (!SchemaOr)
+    return SchemaOr.takeError();
+  Schema = SchemaOr.get();
+
+  // Now initialize the table reader with a pointer into data buffer.
+  MemProfRecordTable.reset(MemProfRecordHashTable::Create(
+      /*Buckets=*/Start + RecordTableOffset,
+      /*Payload=*/Ptr,
+      /*Base=*/Start, memprof::RecordLookupTrait(memprof::Version1, Schema)));
+
+  // Initialize the frame table reader with the payload and bucket offsets.
+  MemProfFrameTable.reset(MemProfFrameHashTable::Create(
+      /*Buckets=*/Start + FrameTableOffset,
+      /*Payload=*/Start + FramePayloadOffset,
+      /*Base=*/Start, memprof::FrameLookupTrait()));
+
+#ifdef EXPENSIVE_CHECKS
+  // Go through all the records and verify that CSId has been correctly
+  // populated.  Do this only under EXPENSIVE_CHECKS.  Otherwise, we
+  // would defeat the purpose of OnDiskIterableChainedHashTable.
+  for (const auto &Record : MemProfRecordTable->data())
+    verifyIndexedMemProfRecord(Record);
+#endif
+
+  return Error::success();
+}
+
+static Error
+readMemProf(const unsigned char *Start, uint64_t MemProfOffset,
+            memprof::MemProfSchema &Schema,
+            std::unique_ptr<MemProfRecordHashTable> &MemProfRecordTable,
+            std::unique_ptr<MemProfFrameHashTable> &MemProfFrameTable) {
+  using namespace support;
+
+  const unsigned char *Ptr = Start + MemProfOffset;
+
+  // Read the first 64-bit word, which may be RecordTableOffset in
+  // memprof::MemProfVersion0 or the MemProf version number in
+  // memprof::MemProfVersion1.
+  const uint64_t FirstWord =
+      support::endian::readNext<uint64_t, llvm::endianness::little, unaligned>(
+          Ptr);
+
+  switch (FirstWord) {
----------------
snehasish wrote:

Maybe just use an if-condition until we have additional cases?

https://github.com/llvm/llvm-project/pull/88095


More information about the llvm-commits mailing list