Add a getstringifcomplete function to hpackdecoderstringbuffer to return string only when state is complete. used in error details, not protected.
PiperOrigin-RevId: 323777904
Change-Id: I9beb5ace10f4ceb0aeed76bb8c37015ce808a8f6
diff --git a/http2/hpack/decoder/hpack_decoder_string_buffer.cc b/http2/hpack/decoder/hpack_decoder_string_buffer.cc
index d38ea9f..f461c1e 100644
--- a/http2/hpack/decoder/hpack_decoder_string_buffer.cc
+++ b/http2/hpack/decoder/hpack_decoder_string_buffer.cc
@@ -194,6 +194,14 @@
return value_;
}
+quiche::QuicheStringPiece HpackDecoderStringBuffer::GetStringIfComplete()
+ const {
+ if (state_ != State::COMPLETE) {
+ return {};
+ }
+ return str();
+}
+
std::string HpackDecoderStringBuffer::ReleaseString() {
HTTP2_DVLOG(3) << "HpackDecoderStringBuffer::ReleaseString";
DCHECK_EQ(state_, State::COMPLETE);
diff --git a/http2/hpack/decoder/hpack_decoder_string_buffer.h b/http2/hpack/decoder/hpack_decoder_string_buffer.h
index 1ae8e6b..1341e79 100644
--- a/http2/hpack/decoder/hpack_decoder_string_buffer.h
+++ b/http2/hpack/decoder/hpack_decoder_string_buffer.h
@@ -53,6 +53,9 @@
// transport buffers).
quiche::QuicheStringPiece str() const;
+ // Same as str() if state_ is COMPLETE. Otherwise, returns empty string piece.
+ quiche::QuicheStringPiece GetStringIfComplete() const;
+
// Returns the completely collected string by value, using std::move in an
// effort to avoid unnecessary copies. ReleaseString() must not be called
// unless the string has been buffered (to avoid forcing a potentially
diff --git a/http2/hpack/decoder/hpack_whole_entry_buffer.cc b/http2/hpack/decoder/hpack_whole_entry_buffer.cc
index dc93d1e..f8d5e9d 100644
--- a/http2/hpack/decoder/hpack_whole_entry_buffer.cc
+++ b/http2/hpack/decoder/hpack_whole_entry_buffer.cc
@@ -93,7 +93,7 @@
if (!error_detected_) {
if (len > max_string_size_bytes_) {
std::string detailed_error = quiche::QuicheStrCat(
- "Value length (", len, ") of [", name_.str(),
+ "Value length (", len, ") of [", name_.GetStringIfComplete(),
"] is longer than permitted (", max_string_size_bytes_, ")");
HTTP2_DVLOG(1) << detailed_error;
ReportError(HpackDecodingError::kValueTooLong, detailed_error);
diff --git a/http2/hpack/decoder/hpack_whole_entry_buffer_test.cc b/http2/hpack/decoder/hpack_whole_entry_buffer_test.cc
index 2396bd6..70e1350 100644
--- a/http2/hpack/decoder/hpack_whole_entry_buffer_test.cc
+++ b/http2/hpack/decoder/hpack_whole_entry_buffer_test.cc
@@ -180,6 +180,16 @@
entry_buffer_.OnValueStart(false, kMaxStringSize + 1);
}
+// Regression test for b/162141899.
+TEST_F(HpackWholeEntryBufferTest, ValueTooLongWithoutName) {
+ entry_buffer_.OnStartLiteralHeader(HpackEntryType::kIndexedLiteralHeader, 1);
+ EXPECT_CALL(listener_,
+ OnHpackDecodeError(
+ HpackDecodingError::kValueTooLong,
+ "Value length (21) of [] is longer than permitted (20)"));
+ entry_buffer_.OnValueStart(false, kMaxStringSize + 1);
+}
+
// Verify that a Huffman encoded name with an explicit EOS generates an error
// for an explicit EOS.
TEST_F(HpackWholeEntryBufferTest, NameHuffmanError) {