[llvm] [SamplePGO] Handle "sequence too long" errors more gracefully (PR #114982)
Krzysztof Pszeniczny via llvm-commits
llvm-commits at lists.llvm.org
Tue Nov 5 05:08:35 PST 2024
https://github.com/amharc created https://github.com/llvm/llvm-project/pull/114982
Currently the `SampleProfileReader` calls `std::vector::reserve` directly with the `size_t` it reads from the binary format. `std::vector::reserve` will throw `std::length_error` if the value is larger than `max_size()` (which results in an `abort()` in the `-fno-exceptions` mode). Having a function return `std::error_code` in some cases of malformed inputs, but throw an exception in others is confusing. Let's return `sampleprof_error::too_large` instead.
>From f68510d23db377d99ca5b02db137de71de70da67 Mon Sep 17 00:00:00 2001
From: Krzysztof Pszeniczny <kpszeniczny at google.com>
Date: Tue, 5 Nov 2024 13:59:32 +0100
Subject: [PATCH] [SamplePGO] Handle "sequence too long" errors more gracefully
Currently the `SampleProfileReader` calls `std::vector::reserve` directly with the `size_t` it reads from the binary format. `std::vector::reserve` will throw `std::length_error` if the value is larger than `max_size()` (which results in an `abort()` in `-fno-exceptions` mode). Having a function return `std::error_code` in some cases of malformed inputs, but throw an exception in others is confusing. Let's return `sampleprof_error::too_large` instead.
---
llvm/lib/ProfileData/SampleProfReader.cpp | 16 ++++++++++++++--
1 file changed, 14 insertions(+), 2 deletions(-)
diff --git a/llvm/lib/ProfileData/SampleProfReader.cpp b/llvm/lib/ProfileData/SampleProfReader.cpp
index 98c78443785275..70ae87dd22cd9a 100644
--- a/llvm/lib/ProfileData/SampleProfReader.cpp
+++ b/llvm/lib/ProfileData/SampleProfReader.cpp
@@ -857,9 +857,11 @@ std::error_code SampleProfileReaderExtBinaryBase::readFuncOffsetTable() {
return EC;
bool UseFuncOffsetList = useFuncOffsetList();
- if (UseFuncOffsetList)
+ if (UseFuncOffsetList) {
+ if (*Size > FuncOffsetList.max_size())
+ return sampleprof_error::too_large;
FuncOffsetList.reserve(*Size);
- else
+ } else
FuncOffsetTable.reserve(*Size);
for (uint64_t I = 0; I < *Size; ++I) {
@@ -1112,9 +1114,13 @@ std::error_code SampleProfileReaderBinary::readNameTable() {
bool UseMD5 = useMD5();
NameTable.clear();
+ if (*Size > NameTable.max_size())
+ return sampleprof_error::too_large;
NameTable.reserve(*Size);
if (!ProfileIsCS) {
MD5SampleContextTable.clear();
+ if (*Size > MD5SampleContextTable.max_size())
+ return sampleprof_error::too_large;
if (UseMD5)
MD5SampleContextTable.reserve(*Size);
else
@@ -1157,6 +1163,8 @@ SampleProfileReaderExtBinaryBase::readNameTableSec(bool IsMD5,
return sampleprof_error::truncated;
NameTable.clear();
+ if (*Size > NameTable.max_size())
+ return sampleprof_error::too_large;
NameTable.reserve(*Size);
for (size_t I = 0; I < *Size; ++I) {
using namespace support;
@@ -1177,6 +1185,8 @@ SampleProfileReaderExtBinaryBase::readNameTableSec(bool IsMD5,
return EC;
NameTable.clear();
+ if (*Size > NameTable.max_size())
+ return sampleprof_error::too_large;
NameTable.reserve(*Size);
if (!ProfileIsCS)
MD5SampleContextTable.resize(*Size);
@@ -1206,6 +1216,8 @@ std::error_code SampleProfileReaderExtBinaryBase::readCSNameTableSec() {
return EC;
CSNameTable.clear();
+ if (*Size > CSNameTable.max_size())
+ return sampleprof_error::too_large;
CSNameTable.reserve(*Size);
if (ProfileIsCS) {
// Delay MD5 computation of CS context until they are needed. Use 0 to
More information about the llvm-commits
mailing list