1 //=-- MemProfSummary.cpp - MemProf summary support ---------------=// 2 // 3 // Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. 4 // See https://llvm.org/LICENSE.txt for license information. 5 // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception 6 // 7 //===----------------------------------------------------------------------===// 8 // 9 // This file contains MemProf summary support. 10 // 11 //===----------------------------------------------------------------------===// 12 13 #include "llvm/ProfileData/MemProfSummary.h" 14 15 using namespace llvm; 16 using namespace llvm::memprof; 17 18 void MemProfSummary::printSummaryYaml(raw_ostream &OS) const { 19 // For now emit as YAML comments, since they aren't read on input. 20 OS << "---\n"; 21 OS << "# MemProfSummary:\n"; 22 OS << "# Total contexts: " << NumContexts << "\n"; 23 OS << "# Total cold contexts: " << NumColdContexts << "\n"; 24 OS << "# Total hot contexts: " << NumHotContexts << "\n"; 25 OS << "# Maximum cold context total size: " << MaxColdTotalSize << "\n"; 26 OS << "# Maximum warm context total size: " << MaxWarmTotalSize << "\n"; 27 OS << "# Maximum hot context total size: " << MaxHotTotalSize << "\n"; 28 } 29 30 void MemProfSummary::write(ProfOStream &OS) const { 31 // Write the current number of fields first, which helps enable backwards and 32 // forwards compatibility (see comment in header). 33 OS.write32(memprof::MemProfSummary::getNumSummaryFields()); 34 auto StartPos = OS.tell(); 35 (void)StartPos; 36 OS.write(NumContexts); 37 OS.write(NumColdContexts); 38 OS.write(NumHotContexts); 39 OS.write(MaxColdTotalSize); 40 OS.write(MaxWarmTotalSize); 41 OS.write(MaxHotTotalSize); 42 // Sanity check that the number of fields was kept in sync with actual fields. 43 assert((OS.tell() - StartPos) / 8 == MemProfSummary::getNumSummaryFields()); 44 } 45 46 std::unique_ptr<MemProfSummary> 47 MemProfSummary::deserialize(const unsigned char *&Ptr) { 48 auto NumSummaryFields = 49 support::endian::readNext<uint32_t, llvm::endianness::little>(Ptr); 50 // The initial version of the summary contains 6 fields. To support backwards 51 // compatibility with older profiles, if new summary fields are added (until a 52 // version bump) this code will need to check NumSummaryFields against the 53 // current value of MemProfSummary::getNumSummaryFields(). If NumSummaryFields 54 // is lower then default values will need to be filled in for the newer fields 55 // instead of trying to read them from the profile. 56 // 57 // For now, assert that the profile contains at least as many fields as 58 // expected by the code. 59 assert(NumSummaryFields >= MemProfSummary::getNumSummaryFields()); 60 61 auto MemProfSum = std::make_unique<MemProfSummary>( 62 support::endian::read<uint64_t, llvm::endianness::little>(Ptr), 63 support::endian::read<uint64_t, llvm::endianness::little>(Ptr + 8), 64 support::endian::read<uint64_t, llvm::endianness::little>(Ptr + 16), 65 support::endian::read<uint64_t, llvm::endianness::little>(Ptr + 24), 66 support::endian::read<uint64_t, llvm::endianness::little>(Ptr + 32), 67 support::endian::read<uint64_t, llvm::endianness::little>(Ptr + 40)); 68 69 // Enable forwards compatibility by skipping past any additional fields in the 70 // profile's summary. 71 Ptr += NumSummaryFields * sizeof(uint64_t); 72 73 return MemProfSum; 74 } 75