std::error_code RawInstrProfReader<IntPtrT>::readValueProfilingData( InstrProfRecord &Record) { Record.clearValueData(); if (!Data->Values || (ValueDataDelta == 0)) return success(); // Read value data. uint64_t NumVSites = 0; for (uint32_t Kind = IPVK_First; Kind <= ValueKindLast; ++Kind) NumVSites += swap(Data->NumValueSites[Kind]); NumVSites += getNumPaddingBytes(NumVSites); auto VDataCounts = makeArrayRef(getValueDataCounts(Data->Values), NumVSites); // Check bounds. if (VDataCounts.data() < ValueDataStart || VDataCounts.data() + VDataCounts.size() > reinterpret_cast<const uint8_t *>(ProfileEnd)) return error(instrprof_error::malformed); const InstrProfValueData *VDataPtr = getValueData(swap(Data->Values) + NumVSites); for (uint32_t Kind = IPVK_First; Kind <= ValueKindLast; ++Kind) { NumVSites = swap(Data->NumValueSites[Kind]); Record.reserveSites(Kind, NumVSites); for (uint32_t VSite = 0; VSite < NumVSites; ++VSite) { uint32_t VDataCount = VDataCounts[VSite]; if ((const char *)(VDataPtr + VDataCount) > ProfileEnd) return error(instrprof_error::malformed); std::vector<InstrProfValueData> CurrentValues; CurrentValues.reserve(VDataCount); for (uint32_t VIndex = 0; VIndex < VDataCount; ++VIndex) { uint64_t TargetValue = swap(VDataPtr->Value); uint64_t Count = swap(VDataPtr->Count); CurrentValues.push_back({TargetValue, Count}); ++VDataPtr; } Record.addValueData(Kind, VSite, CurrentValues.data(), VDataCount, &FunctionPtrToNameMap); } } return success(); }
std::error_code TextInstrProfReader::readValueProfileData(InstrProfRecord &Record) { #define CHECK_LINE_END(Line) \ if (Line.is_at_end()) \ return error(instrprof_error::truncated); #define READ_NUM(Str, Dst) \ if ((Str).getAsInteger(10, (Dst))) \ return error(instrprof_error::malformed); #define VP_READ_ADVANCE(Val) \ CHECK_LINE_END(Line); \ uint32_t Val; \ READ_NUM((*Line), (Val)); \ Line++; if (Line.is_at_end()) return success(); uint32_t NumValueKinds; if (Line->getAsInteger(10, NumValueKinds)) { // No value profile data return success(); } if (NumValueKinds == 0 || NumValueKinds > IPVK_Last + 1) return error(instrprof_error::malformed); Line++; for (uint32_t VK = 0; VK < NumValueKinds; VK++) { VP_READ_ADVANCE(ValueKind); if (ValueKind > IPVK_Last) return error(instrprof_error::malformed); VP_READ_ADVANCE(NumValueSites); if (!NumValueSites) continue; Record.reserveSites(VK, NumValueSites); for (uint32_t S = 0; S < NumValueSites; S++) { VP_READ_ADVANCE(NumValueData); std::vector<InstrProfValueData> CurrentValues; for (uint32_t V = 0; V < NumValueData; V++) { CHECK_LINE_END(Line); std::pair<StringRef, StringRef> VD = Line->split(':'); uint64_t TakenCount, Value; if (VK == IPVK_IndirectCallTarget) { Symtab->addFuncName(VD.first); Value = IndexedInstrProf::ComputeHash(VD.first); } else { READ_NUM(VD.first, Value); } READ_NUM(VD.second, TakenCount); CurrentValues.push_back({Value, TakenCount}); Line++; } Record.addValueData(VK, S, CurrentValues.data(), NumValueData, nullptr); } } return success(); #undef CHECK_LINE_END #undef READ_NUM #undef VP_READ_ADVANCE }