1010//
1111// ===----------------------------------------------------------------------===//
1212
13+ #include " llvm/ProfileData/DataAccessProf.h"
1314#include " llvm/ProfileData/InstrProf.h"
1415#include " llvm/ProfileData/InstrProfReader.h"
1516#include " llvm/ProfileData/MemProf.h"
@@ -216,7 +217,9 @@ static Error writeMemProfV2(ProfOStream &OS,
216217
217218static Error writeMemProfRadixTreeBased (
218219 ProfOStream &OS, memprof::IndexedMemProfData &MemProfData,
219- memprof::IndexedVersion Version, bool MemProfFullSchema) {
220+ memprof::IndexedVersion Version, bool MemProfFullSchema,
221+ std::optional<std::reference_wrapper<data_access_prof::DataAccessProfData>>
222+ DataAccessProfileData) {
220223 assert ((Version == memprof::Version3 || Version == memprof::Version4) &&
221224 " Unsupported version for radix tree format" );
222225
@@ -225,6 +228,8 @@ static Error writeMemProfRadixTreeBased(
225228 OS.write (0ULL ); // Reserve space for the memprof call stack payload offset.
226229 OS.write (0ULL ); // Reserve space for the memprof record payload offset.
227230 OS.write (0ULL ); // Reserve space for the memprof record table offset.
231+ if (Version == memprof::Version4)
232+ OS.write (0ULL ); // Reserve space for the data access profile offset.
228233
229234 auto Schema = memprof::getHotColdSchema ();
230235 if (MemProfFullSchema)
@@ -251,17 +256,26 @@ static Error writeMemProfRadixTreeBased(
251256 uint64_t RecordTableOffset = writeMemProfRecords (
252257 OS, MemProfData.Records , &Schema, Version, &MemProfCallStackIndexes);
253258
259+ uint64_t DataAccessProfOffset = 0 ;
260+ if (DataAccessProfileData.has_value ()) {
261+ DataAccessProfOffset = OS.tell ();
262+ if (Error E = (*DataAccessProfileData).get ().serialize (OS))
263+ return E;
264+ }
265+
254266 // Verify that the computation for the number of elements in the call stack
255267 // array works.
256268 assert (CallStackPayloadOffset +
257269 NumElements * sizeof (memprof::LinearFrameId) ==
258270 RecordPayloadOffset);
259271
260- uint64_t Header[] = {
272+ SmallVector< uint64_t , 4 > Header = {
261273 CallStackPayloadOffset,
262274 RecordPayloadOffset,
263275 RecordTableOffset,
264276 };
277+ if (Version == memprof::Version4)
278+ Header.push_back (DataAccessProfOffset);
265279 OS.patch ({{HeaderUpdatePos, Header}});
266280
267281 return Error::success ();
@@ -272,28 +286,33 @@ static Error writeMemProfV3(ProfOStream &OS,
272286 memprof::IndexedMemProfData &MemProfData,
273287 bool MemProfFullSchema) {
274288 return writeMemProfRadixTreeBased (OS, MemProfData, memprof::Version3,
275- MemProfFullSchema);
289+ MemProfFullSchema, std:: nullopt );
276290}
277291
278292// Write out MemProf Version4
279- static Error writeMemProfV4 (ProfOStream &OS,
280- memprof::IndexedMemProfData &MemProfData,
281- bool MemProfFullSchema) {
293+ static Error writeMemProfV4 (
294+ ProfOStream &OS, memprof::IndexedMemProfData &MemProfData,
295+ bool MemProfFullSchema,
296+ std::optional<std::reference_wrapper<data_access_prof::DataAccessProfData>>
297+ DataAccessProfileData) {
282298 return writeMemProfRadixTreeBased (OS, MemProfData, memprof::Version4,
283- MemProfFullSchema);
299+ MemProfFullSchema, DataAccessProfileData );
284300}
285301
286302// Write out the MemProf data in a requested version.
287- Error writeMemProf (ProfOStream &OS, memprof::IndexedMemProfData &MemProfData,
288- memprof::IndexedVersion MemProfVersionRequested,
289- bool MemProfFullSchema) {
303+ Error writeMemProf (
304+ ProfOStream &OS, memprof::IndexedMemProfData &MemProfData,
305+ memprof::IndexedVersion MemProfVersionRequested, bool MemProfFullSchema,
306+ std::optional<std::reference_wrapper<data_access_prof::DataAccessProfData>>
307+ DataAccessProfileData) {
290308 switch (MemProfVersionRequested) {
291309 case memprof::Version2:
292310 return writeMemProfV2 (OS, MemProfData, MemProfFullSchema);
293311 case memprof::Version3:
294312 return writeMemProfV3 (OS, MemProfData, MemProfFullSchema);
295313 case memprof::Version4:
296- return writeMemProfV4 (OS, MemProfData, MemProfFullSchema);
314+ return writeMemProfV4 (OS, MemProfData, MemProfFullSchema,
315+ DataAccessProfileData);
297316 }
298317
299318 return make_error<InstrProfError>(
@@ -357,7 +376,10 @@ Error IndexedMemProfReader::deserializeV2(const unsigned char *Start,
357376}
358377
359378Error IndexedMemProfReader::deserializeRadixTreeBased (
360- const unsigned char *Start, const unsigned char *Ptr) {
379+ const unsigned char *Start, const unsigned char *Ptr,
380+ memprof::IndexedVersion Version) {
381+ assert ((Version == memprof::Version3 || Version == memprof::Version4) &&
382+ " Unsupported version for radix tree format" );
361383 // The offset in the stream right before invoking
362384 // CallStackTableGenerator.Emit.
363385 const uint64_t CallStackPayloadOffset =
@@ -369,6 +391,11 @@ Error IndexedMemProfReader::deserializeRadixTreeBased(
369391 const uint64_t RecordTableOffset =
370392 support::endian::readNext<uint64_t , llvm::endianness::little>(Ptr);
371393
394+ uint64_t DataAccessProfOffset = 0 ;
395+ if (Version == memprof::Version4)
396+ DataAccessProfOffset =
397+ support::endian::readNext<uint64_t , llvm::endianness::little>(Ptr);
398+
372399 // Read the schema.
373400 auto SchemaOr = memprof::readMemProfSchema (Ptr);
374401 if (!SchemaOr)
@@ -390,6 +417,14 @@ Error IndexedMemProfReader::deserializeRadixTreeBased(
390417 /* Payload=*/ Start + RecordPayloadOffset,
391418 /* Base=*/ Start, memprof::RecordLookupTrait (Version, Schema)));
392419
420+ if (DataAccessProfOffset > RecordTableOffset) {
421+ DataAccessProfileData =
422+ std::make_unique<data_access_prof::DataAccessProfData>();
423+ const unsigned char *DAPPtr = Start + DataAccessProfOffset;
424+ if (Error E = DataAccessProfileData->deserialize (DAPPtr))
425+ return E;
426+ }
427+
393428 return Error::success ();
394429}
395430
@@ -423,7 +458,7 @@ Error IndexedMemProfReader::deserialize(const unsigned char *Start,
423458 case memprof::Version3:
424459 case memprof::Version4:
425460 // V3 and V4 share the same high-level structure (radix tree, linear IDs).
426- if (Error E = deserializeRadixTreeBased (Start, Ptr))
461+ if (Error E = deserializeRadixTreeBased (Start, Ptr, Version ))
427462 return E;
428463 break ;
429464 }
0 commit comments