From eb5e602e3e427b4ec3b36b96b25f2b84d77b499d Mon Sep 17 00:00:00 2001 From: Sean Linsley Date: Mon, 12 Dec 2022 17:58:50 -0600 Subject: [PATCH 1/5] first pass implementing a macro-based approach --- prost-build/src/code_generator.rs | 2 +- prost-derive/src/lib.rs | 14 +++++++++++++- src/encoding.rs | 2 +- src/message.rs | 7 +++++-- src/types.rs | 12 ++++++++++++ 5 files changed, 32 insertions(+), 5 deletions(-) diff --git a/prost-build/src/code_generator.rs b/prost-build/src/code_generator.rs index 69a80ed3c..c06567a80 100644 --- a/prost-build/src/code_generator.rs +++ b/prost-build/src/code_generator.rs @@ -181,7 +181,6 @@ impl<'a> CodeGenerator<'a> { }); self.append_doc(&fq_message_name, None); - self.append_type_attributes(&fq_message_name); self.push_indent(); self.buf .push_str("#[allow(clippy::derive_partial_eq_without_eq)]\n"); @@ -189,6 +188,7 @@ impl<'a> CodeGenerator<'a> { "#[derive(Clone, PartialEq, {}::Message)]\n", self.config.prost_path.as_deref().unwrap_or("::prost") )); + self.append_type_attributes(&fq_message_name); self.push_indent(); self.buf.push_str("pub struct "); self.buf.push_str(&to_upper_camel(&message_name)); diff --git a/prost-derive/src/lib.rs b/prost-derive/src/lib.rs index b90c9df5a..7fb41dd44 100644 --- a/prost-derive/src/lib.rs +++ b/prost-derive/src/lib.rs @@ -23,6 +23,16 @@ fn try_message(input: TokenStream) -> Result { let ident = input.ident; + let recursion_limit: u32 = if let Some(attr) = input.attrs.iter().find(|attr| attr.path.is_ident("RecursionLimit")) { + if let syn::Lit::Int(attr) = attr.parse_args().unwrap() { + attr.base10_parse().unwrap() + } else { + panic!("unexpected RecursionLimit type: {attr:?}") + } + } else { + 100 + }; + let variant_data = match input.data { Data::Struct(variant_data) => variant_data, Data::Enum(..) => bail!("Message can not be derived for an enum"), @@ -187,6 +197,8 @@ fn try_message(input: TokenStream) -> Result { let expanded = quote! { impl #impl_generics ::prost::Message for #ident #ty_generics #where_clause { + const RECURSION_LIMIT: u32 = #recursion_limit; + #[allow(unused_variables)] fn encode_raw(&self, buf: &mut B) where B: ::prost::bytes::BufMut { #(#encode)* @@ -238,7 +250,7 @@ fn try_message(input: TokenStream) -> Result { Ok(expanded.into()) } -#[proc_macro_derive(Message, attributes(prost))] +#[proc_macro_derive(Message, attributes(prost, RecursionLimit))] pub fn message(input: TokenStream) -> TokenStream { try_message(input).unwrap() } diff --git a/src/encoding.rs b/src/encoding.rs index 60b55204a..344d2dc86 100644 --- a/src/encoding.rs +++ b/src/encoding.rs @@ -199,7 +199,7 @@ pub struct DecodeContext { /// customized. The recursion limit can be ignored by building the Prost /// crate with the `no-recursion-limit` feature. #[cfg(not(feature = "no-recursion-limit"))] - recurse_count: u32, + pub recurse_count: u32, } #[cfg(not(feature = "no-recursion-limit"))] diff --git a/src/message.rs b/src/message.rs index a190f6b47..244c3b46f 100644 --- a/src/message.rs +++ b/src/message.rs @@ -14,6 +14,8 @@ use crate::EncodeError; /// A Protocol Buffers message. pub trait Message: Debug + Send + Sync { + const RECURSION_LIMIT: u32; + /// Encodes the message to a buffer. /// /// This method will panic if the buffer has insufficient capacity. @@ -135,7 +137,7 @@ pub trait Message: Debug + Send + Sync { B: Buf, Self: Sized, { - let ctx = DecodeContext::default(); + let ctx = DecodeContext { recurse_count: Self::RECURSION_LIMIT }; while buf.has_remaining() { let (tag, wire_type) = decode_key(&mut buf)?; self.merge_field(tag, wire_type, &mut buf, ctx.clone())?; @@ -154,7 +156,7 @@ pub trait Message: Debug + Send + Sync { WireType::LengthDelimited, self, &mut buf, - DecodeContext::default(), + DecodeContext { recurse_count: Self::RECURSION_LIMIT }, ) } @@ -166,6 +168,7 @@ impl Message for Box where M: Message, { + const RECURSION_LIMIT: u32 = M::RECURSION_LIMIT; fn encode_raw(&self, buf: &mut B) where B: BufMut, diff --git a/src/types.rs b/src/types.rs index 864a2adda..6abe7a323 100644 --- a/src/types.rs +++ b/src/types.rs @@ -20,6 +20,7 @@ use crate::{ /// `google.protobuf.BoolValue` impl Message for bool { + const RECURSION_LIMIT: u32 = 0; fn encode_raw(&self, buf: &mut B) where B: BufMut, @@ -58,6 +59,7 @@ impl Message for bool { /// `google.protobuf.UInt32Value` impl Message for u32 { + const RECURSION_LIMIT: u32 = 0; fn encode_raw(&self, buf: &mut B) where B: BufMut, @@ -96,6 +98,7 @@ impl Message for u32 { /// `google.protobuf.UInt64Value` impl Message for u64 { + const RECURSION_LIMIT: u32 = 0; fn encode_raw(&self, buf: &mut B) where B: BufMut, @@ -134,6 +137,8 @@ impl Message for u64 { /// `google.protobuf.Int32Value` impl Message for i32 { + const RECURSION_LIMIT: u32 = 0; + fn encode_raw(&self, buf: &mut B) where B: BufMut, @@ -172,6 +177,7 @@ impl Message for i32 { /// `google.protobuf.Int64Value` impl Message for i64 { + const RECURSION_LIMIT: u32 = 0; fn encode_raw(&self, buf: &mut B) where B: BufMut, @@ -210,6 +216,7 @@ impl Message for i64 { /// `google.protobuf.FloatValue` impl Message for f32 { + const RECURSION_LIMIT: u32 = 0; fn encode_raw(&self, buf: &mut B) where B: BufMut, @@ -248,6 +255,7 @@ impl Message for f32 { /// `google.protobuf.DoubleValue` impl Message for f64 { + const RECURSION_LIMIT: u32 = 0; fn encode_raw(&self, buf: &mut B) where B: BufMut, @@ -286,6 +294,7 @@ impl Message for f64 { /// `google.protobuf.StringValue` impl Message for String { + const RECURSION_LIMIT: u32 = 0; fn encode_raw(&self, buf: &mut B) where B: BufMut, @@ -324,6 +333,7 @@ impl Message for String { /// `google.protobuf.BytesValue` impl Message for Vec { + const RECURSION_LIMIT: u32 = 0; fn encode_raw(&self, buf: &mut B) where B: BufMut, @@ -362,6 +372,7 @@ impl Message for Vec { /// `google.protobuf.BytesValue` impl Message for Bytes { + const RECURSION_LIMIT: u32 = 0; fn encode_raw(&self, buf: &mut B) where B: BufMut, @@ -400,6 +411,7 @@ impl Message for Bytes { /// `google.protobuf.Empty` impl Message for () { + const RECURSION_LIMIT: u32 = 0; fn encode_raw(&self, _buf: &mut B) where B: BufMut, From f4604c4691e3b520e37b18a54ef38c07dd0a2d8c Mon Sep 17 00:00:00 2001 From: Sean Linsley Date: Thu, 15 Dec 2022 16:16:07 -0600 Subject: [PATCH 2/5] switch to an associated function --- prost-build/src/code_generator.rs | 12 ++++++++- prost-build/src/lib.rs | 21 +++++++++++++++ prost-derive/src/lib.rs | 10 +++++-- src/encoding.rs | 24 +++++++---------- src/lib.rs | 5 ---- src/message.rs | 15 ++++++++--- src/types.rs | 44 +++++++++++++++++++++++-------- tests/src/build.rs | 5 ++-- tests/src/lib.rs | 21 +++++++++++++++ tests/src/nesting.proto | 10 +++++++ 10 files changed, 128 insertions(+), 39 deletions(-) diff --git a/prost-build/src/code_generator.rs b/prost-build/src/code_generator.rs index c06567a80..ca8de06c5 100644 --- a/prost-build/src/code_generator.rs +++ b/prost-build/src/code_generator.rs @@ -181,6 +181,7 @@ impl<'a> CodeGenerator<'a> { }); self.append_doc(&fq_message_name, None); + self.append_type_attributes(&fq_message_name); self.push_indent(); self.buf .push_str("#[allow(clippy::derive_partial_eq_without_eq)]\n"); @@ -188,7 +189,7 @@ impl<'a> CodeGenerator<'a> { "#[derive(Clone, PartialEq, {}::Message)]\n", self.config.prost_path.as_deref().unwrap_or("::prost") )); - self.append_type_attributes(&fq_message_name); + self.append_recursion_limit(&fq_message_name); self.push_indent(); self.buf.push_str("pub struct "); self.buf.push_str(&to_upper_camel(&message_name)); @@ -272,6 +273,15 @@ impl<'a> CodeGenerator<'a> { } } + fn append_recursion_limit(&mut self, fq_message_name: &str) { + assert_eq!(b'.', fq_message_name.as_bytes()[0]); + if let Some(limit) = self.config.recursion_limits.get_first(fq_message_name) { + push_indent(self.buf, self.depth); + self.buf.push_str(&format!("#[RecursionLimit({limit})]")); + self.buf.push('\n'); + } + } + fn append_field_attributes(&mut self, fq_message_name: &str, field_name: &str) { assert_eq!(b'.', fq_message_name.as_bytes()[0]); for attribute in self diff --git a/prost-build/src/lib.rs b/prost-build/src/lib.rs index 99f084963..5c2046776 100644 --- a/prost-build/src/lib.rs +++ b/prost-build/src/lib.rs @@ -245,6 +245,7 @@ pub struct Config { bytes_type: PathMap, type_attributes: PathMap, field_attributes: PathMap, + recursion_limits: PathMap, prost_types: bool, strip_enum_prefix: bool, out_dir: Option, @@ -468,6 +469,25 @@ impl Config { self } + /// Configure a custom recursion limit for certain messages. + /// + /// This defaults to 100, and can be disabled with the no-recursion-limit crate feature. + /// + /// # Example + /// + /// ```rust + /// # let mut config = prost_build::Config::new(); + /// config.recursion_limit("my_messages.MyMessageType", 1000); + /// ``` + pub fn recursion_limit

(&mut self, path: P, limit: u32) -> &mut Self + where + P: AsRef, + { + self.recursion_limits + .insert(path.as_ref().to_string(), limit); + self + } + /// Configures the code generator to use the provided service generator. pub fn service_generator(&mut self, service_generator: Box) -> &mut Self { self.service_generator = Some(service_generator); @@ -1101,6 +1121,7 @@ impl default::Default for Config { bytes_type: PathMap::default(), type_attributes: PathMap::default(), field_attributes: PathMap::default(), + recursion_limits: PathMap::default(), prost_types: true, strip_enum_prefix: true, out_dir: None, diff --git a/prost-derive/src/lib.rs b/prost-derive/src/lib.rs index 7fb41dd44..b3b1fb373 100644 --- a/prost-derive/src/lib.rs +++ b/prost-derive/src/lib.rs @@ -23,7 +23,11 @@ fn try_message(input: TokenStream) -> Result { let ident = input.ident; - let recursion_limit: u32 = if let Some(attr) = input.attrs.iter().find(|attr| attr.path.is_ident("RecursionLimit")) { + let recursion_limit: u32 = if let Some(attr) = input + .attrs + .iter() + .find(|attr| attr.path.is_ident("RecursionLimit")) + { if let syn::Lit::Int(attr) = attr.parse_args().unwrap() { attr.base10_parse().unwrap() } else { @@ -197,7 +201,9 @@ fn try_message(input: TokenStream) -> Result { let expanded = quote! { impl #impl_generics ::prost::Message for #ident #ty_generics #where_clause { - const RECURSION_LIMIT: u32 = #recursion_limit; + fn recursion_limit() -> u32 { + #recursion_limit + } #[allow(unused_variables)] fn encode_raw(&self, buf: &mut B) where B: ::prost::bytes::BufMut { diff --git a/src/encoding.rs b/src/encoding.rs index 344d2dc86..76550e19c 100644 --- a/src/encoding.rs +++ b/src/encoding.rs @@ -195,29 +195,25 @@ pub struct DecodeContext { /// How many times we can recurse in the current decode stack before we hit /// the recursion limit. /// - /// The recursion limit is defined by `RECURSION_LIMIT` and cannot be - /// customized. The recursion limit can be ignored by building the Prost - /// crate with the `no-recursion-limit` feature. + /// It defaults to 100 and can be changed using `prost_build::recursion_limit`, + /// or it can be disabled entirely using the `no-recursion-limit` feature. #[cfg(not(feature = "no-recursion-limit"))] pub recurse_count: u32, } -#[cfg(not(feature = "no-recursion-limit"))] -impl Default for DecodeContext { - #[inline] - fn default() -> DecodeContext { +impl DecodeContext { + pub(crate) fn new(recursion_limit: u32) -> DecodeContext { DecodeContext { - recurse_count: crate::RECURSION_LIMIT, + #[cfg(not(feature = "no-recursion-limit"))] + recurse_count: recursion_limit, } } -} -impl DecodeContext { /// Call this function before recursively decoding. /// /// There is no `exit` function since this function creates a new `DecodeContext` /// to be used at the next level of recursion. Continue to use the old context - // at the previous level of recursion. + /// at the previous level of recursion. #[cfg(not(feature = "no-recursion-limit"))] #[inline] pub(crate) fn enter_recursion(&self) -> DecodeContext { @@ -1503,7 +1499,7 @@ mod test { wire_type, &mut roundtrip_value, &mut buf, - DecodeContext::default(), + DecodeContext::new(100), ) .map_err(|error| TestCaseError::fail(error.to_string()))?; @@ -1575,7 +1571,7 @@ mod test { wire_type, &mut roundtrip_value, &mut buf, - DecodeContext::default(), + DecodeContext::new(100), ) .map_err(|error| TestCaseError::fail(error.to_string()))?; } @@ -1594,7 +1590,7 @@ mod test { WireType::LengthDelimited, &mut s, &mut &buf[..], - DecodeContext::default(), + DecodeContext::new(100), ); r.expect_err("must be an error"); assert!(s.is_empty()); diff --git a/src/lib.rs b/src/lib.rs index 437e32621..07ec72e52 100644 --- a/src/lib.rs +++ b/src/lib.rs @@ -23,11 +23,6 @@ use bytes::{Buf, BufMut}; use crate::encoding::{decode_varint, encode_varint, encoded_len_varint}; -// See `encoding::DecodeContext` for more info. -// 100 is the default recursion limit in the C++ implementation. -#[cfg(not(feature = "no-recursion-limit"))] -const RECURSION_LIMIT: u32 = 100; - /// Encodes a length delimiter to the buffer. /// /// See [Message.encode_length_delimited] for more info. diff --git a/src/message.rs b/src/message.rs index 244c3b46f..59c2597fc 100644 --- a/src/message.rs +++ b/src/message.rs @@ -14,7 +14,12 @@ use crate::EncodeError; /// A Protocol Buffers message. pub trait Message: Debug + Send + Sync { - const RECURSION_LIMIT: u32; + /// The recursion limit for decoding protobuf messages. + /// + /// Defaults to 100. Can be customized in your build.rs or by using the no-recursion-limit crate feature. + fn recursion_limit() -> u32 + where + Self: Sized; /// Encodes the message to a buffer. /// @@ -137,7 +142,7 @@ pub trait Message: Debug + Send + Sync { B: Buf, Self: Sized, { - let ctx = DecodeContext { recurse_count: Self::RECURSION_LIMIT }; + let ctx = DecodeContext::new(Self::recursion_limit()); while buf.has_remaining() { let (tag, wire_type) = decode_key(&mut buf)?; self.merge_field(tag, wire_type, &mut buf, ctx.clone())?; @@ -156,7 +161,7 @@ pub trait Message: Debug + Send + Sync { WireType::LengthDelimited, self, &mut buf, - DecodeContext { recurse_count: Self::RECURSION_LIMIT }, + DecodeContext::new(Self::recursion_limit()), ) } @@ -168,7 +173,9 @@ impl Message for Box where M: Message, { - const RECURSION_LIMIT: u32 = M::RECURSION_LIMIT; + fn recursion_limit() -> u32 { + M::recursion_limit() + } fn encode_raw(&self, buf: &mut B) where B: BufMut, diff --git a/src/types.rs b/src/types.rs index 6abe7a323..fa349c427 100644 --- a/src/types.rs +++ b/src/types.rs @@ -20,7 +20,9 @@ use crate::{ /// `google.protobuf.BoolValue` impl Message for bool { - const RECURSION_LIMIT: u32 = 0; + fn recursion_limit() -> u32 { + 0 + } fn encode_raw(&self, buf: &mut B) where B: BufMut, @@ -59,7 +61,9 @@ impl Message for bool { /// `google.protobuf.UInt32Value` impl Message for u32 { - const RECURSION_LIMIT: u32 = 0; + fn recursion_limit() -> u32 { + 0 + } fn encode_raw(&self, buf: &mut B) where B: BufMut, @@ -98,7 +102,9 @@ impl Message for u32 { /// `google.protobuf.UInt64Value` impl Message for u64 { - const RECURSION_LIMIT: u32 = 0; + fn recursion_limit() -> u32 { + 0 + } fn encode_raw(&self, buf: &mut B) where B: BufMut, @@ -137,7 +143,9 @@ impl Message for u64 { /// `google.protobuf.Int32Value` impl Message for i32 { - const RECURSION_LIMIT: u32 = 0; + fn recursion_limit() -> u32 { + 0 + } fn encode_raw(&self, buf: &mut B) where @@ -177,7 +185,9 @@ impl Message for i32 { /// `google.protobuf.Int64Value` impl Message for i64 { - const RECURSION_LIMIT: u32 = 0; + fn recursion_limit() -> u32 { + 0 + } fn encode_raw(&self, buf: &mut B) where B: BufMut, @@ -216,7 +226,9 @@ impl Message for i64 { /// `google.protobuf.FloatValue` impl Message for f32 { - const RECURSION_LIMIT: u32 = 0; + fn recursion_limit() -> u32 { + 0 + } fn encode_raw(&self, buf: &mut B) where B: BufMut, @@ -255,7 +267,9 @@ impl Message for f32 { /// `google.protobuf.DoubleValue` impl Message for f64 { - const RECURSION_LIMIT: u32 = 0; + fn recursion_limit() -> u32 { + 0 + } fn encode_raw(&self, buf: &mut B) where B: BufMut, @@ -294,7 +308,9 @@ impl Message for f64 { /// `google.protobuf.StringValue` impl Message for String { - const RECURSION_LIMIT: u32 = 0; + fn recursion_limit() -> u32 { + 0 + } fn encode_raw(&self, buf: &mut B) where B: BufMut, @@ -333,7 +349,9 @@ impl Message for String { /// `google.protobuf.BytesValue` impl Message for Vec { - const RECURSION_LIMIT: u32 = 0; + fn recursion_limit() -> u32 { + 0 + } fn encode_raw(&self, buf: &mut B) where B: BufMut, @@ -372,7 +390,9 @@ impl Message for Vec { /// `google.protobuf.BytesValue` impl Message for Bytes { - const RECURSION_LIMIT: u32 = 0; + fn recursion_limit() -> u32 { + 0 + } fn encode_raw(&self, buf: &mut B) where B: BufMut, @@ -411,7 +431,9 @@ impl Message for Bytes { /// `google.protobuf.Empty` impl Message for () { - const RECURSION_LIMIT: u32 = 0; + fn recursion_limit() -> u32 { + 0 + } fn encode_raw(&self, _buf: &mut B) where B: BufMut, diff --git a/tests/src/build.rs b/tests/src/build.rs index 5f66a5d4a..5bde2f987 100644 --- a/tests/src/build.rs +++ b/tests/src/build.rs @@ -54,8 +54,9 @@ fn main() { .compile_protos(&[src.join("ident_conversion.proto")], includes) .unwrap(); - config - .compile_protos(&[src.join("nesting.proto")], includes) + let mut c = prost_build::Config::new(); + c.recursion_limit("E", 200); + c.compile_protos(&[src.join("nesting.proto")], includes) .unwrap(); config diff --git a/tests/src/lib.rs b/tests/src/lib.rs index 65d393c36..b5af595e2 100644 --- a/tests/src/lib.rs +++ b/tests/src/lib.rs @@ -405,6 +405,27 @@ mod tests { assert!(build_and_roundtrip(101).is_err()); } + #[test] + fn test_deep_nesting_with_custom_recursion_limit() { + fn build_and_roundtrip(depth: usize) -> Result<(), prost::DecodeError> { + use crate::nesting::E; + + let mut e = Box::new(E::default()); + for _ in 0..depth { + let mut next = Box::new(E::default()); + next.e = Some(e); + e = next; + } + + let mut buf = Vec::new(); + e.encode(&mut buf).unwrap(); + E::decode(&*buf).map(|_| ()) + } + + assert!(build_and_roundtrip(200).is_ok()); + assert!(build_and_roundtrip(201).is_err()); + } + #[test] fn test_deep_nesting_oneof() { fn build_and_roundtrip(depth: usize) -> Result<(), prost::DecodeError> { diff --git a/tests/src/nesting.proto b/tests/src/nesting.proto index 2c61979df..6b027ad1a 100644 --- a/tests/src/nesting.proto +++ b/tests/src/nesting.proto @@ -23,3 +23,13 @@ message C { message D { map m = 1; } + +message E { + E e = 1; + repeated E repeated_e = 2; + map map_e = 3; + + B b = 4; + repeated B repeated_b = 5; + map map_b = 6; +} From 9a50224a594ca219ee141ab90dbddd1aa6f5d775 Mon Sep 17 00:00:00 2001 From: Sean Linsley Date: Thu, 15 Dec 2022 16:33:04 -0600 Subject: [PATCH 3/5] CI fixes --- prost-build/src/code_generator.rs | 2 +- prost-derive/src/lib.rs | 2 +- tests/src/build.rs | 6 +++--- 3 files changed, 5 insertions(+), 5 deletions(-) diff --git a/prost-build/src/code_generator.rs b/prost-build/src/code_generator.rs index ca8de06c5..6baa52b30 100644 --- a/prost-build/src/code_generator.rs +++ b/prost-build/src/code_generator.rs @@ -277,7 +277,7 @@ impl<'a> CodeGenerator<'a> { assert_eq!(b'.', fq_message_name.as_bytes()[0]); if let Some(limit) = self.config.recursion_limits.get_first(fq_message_name) { push_indent(self.buf, self.depth); - self.buf.push_str(&format!("#[RecursionLimit({limit})]")); + self.buf.push_str(&format!("#[RecursionLimit({})]", limit)); self.buf.push('\n'); } } diff --git a/prost-derive/src/lib.rs b/prost-derive/src/lib.rs index b3b1fb373..3604f60c4 100644 --- a/prost-derive/src/lib.rs +++ b/prost-derive/src/lib.rs @@ -31,7 +31,7 @@ fn try_message(input: TokenStream) -> Result { if let syn::Lit::Int(attr) = attr.parse_args().unwrap() { attr.base10_parse().unwrap() } else { - panic!("unexpected RecursionLimit type: {attr:?}") + panic!("unexpected RecursionLimit type: {:?}", attr) } } else { 100 diff --git a/tests/src/build.rs b/tests/src/build.rs index 5bde2f987..11f7ba523 100644 --- a/tests/src/build.rs +++ b/tests/src/build.rs @@ -54,9 +54,9 @@ fn main() { .compile_protos(&[src.join("ident_conversion.proto")], includes) .unwrap(); - let mut c = prost_build::Config::new(); - c.recursion_limit("E", 200); - c.compile_protos(&[src.join("nesting.proto")], includes) + config.recursion_limit("nesting.E", 200); + config + .compile_protos(&[src.join("nesting.proto")], includes) .unwrap(); config From 03c544e4dcfea62231fc1e992677edc0d0831f58 Mon Sep 17 00:00:00 2001 From: Sean Linsley Date: Tue, 10 Jan 2023 21:57:06 -0600 Subject: [PATCH 4/5] provide a default function impl --- src/message.rs | 5 ++++- 1 file changed, 4 insertions(+), 1 deletion(-) diff --git a/src/message.rs b/src/message.rs index 59c2597fc..23dcfa1ca 100644 --- a/src/message.rs +++ b/src/message.rs @@ -19,7 +19,10 @@ pub trait Message: Debug + Send + Sync { /// Defaults to 100. Can be customized in your build.rs or by using the no-recursion-limit crate feature. fn recursion_limit() -> u32 where - Self: Sized; + Self: Sized, + { + 100 + } /// Encodes the message to a buffer. /// From 836a0c6a6f3d584ccae8335a490232c6204c62de Mon Sep 17 00:00:00 2001 From: Sean Linsley Date: Mon, 27 Feb 2023 09:06:15 -0600 Subject: [PATCH 5/5] doc(hidden) and drop unneeded recursion_limit() impls --- src/encoding.rs | 1 + src/types.rs | 34 ---------------------------------- 2 files changed, 1 insertion(+), 34 deletions(-) diff --git a/src/encoding.rs b/src/encoding.rs index 2d61b76c0..41b74ae2d 100644 --- a/src/encoding.rs +++ b/src/encoding.rs @@ -198,6 +198,7 @@ pub struct DecodeContext { /// It defaults to 100 and can be changed using `prost_build::recursion_limit`, /// or it can be disabled entirely using the `no-recursion-limit` feature. #[cfg(not(feature = "no-recursion-limit"))] + #[doc(hidden)] pub recurse_count: u32, } diff --git a/src/types.rs b/src/types.rs index fa349c427..864a2adda 100644 --- a/src/types.rs +++ b/src/types.rs @@ -20,9 +20,6 @@ use crate::{ /// `google.protobuf.BoolValue` impl Message for bool { - fn recursion_limit() -> u32 { - 0 - } fn encode_raw(&self, buf: &mut B) where B: BufMut, @@ -61,9 +58,6 @@ impl Message for bool { /// `google.protobuf.UInt32Value` impl Message for u32 { - fn recursion_limit() -> u32 { - 0 - } fn encode_raw(&self, buf: &mut B) where B: BufMut, @@ -102,9 +96,6 @@ impl Message for u32 { /// `google.protobuf.UInt64Value` impl Message for u64 { - fn recursion_limit() -> u32 { - 0 - } fn encode_raw(&self, buf: &mut B) where B: BufMut, @@ -143,10 +134,6 @@ impl Message for u64 { /// `google.protobuf.Int32Value` impl Message for i32 { - fn recursion_limit() -> u32 { - 0 - } - fn encode_raw(&self, buf: &mut B) where B: BufMut, @@ -185,9 +172,6 @@ impl Message for i32 { /// `google.protobuf.Int64Value` impl Message for i64 { - fn recursion_limit() -> u32 { - 0 - } fn encode_raw(&self, buf: &mut B) where B: BufMut, @@ -226,9 +210,6 @@ impl Message for i64 { /// `google.protobuf.FloatValue` impl Message for f32 { - fn recursion_limit() -> u32 { - 0 - } fn encode_raw(&self, buf: &mut B) where B: BufMut, @@ -267,9 +248,6 @@ impl Message for f32 { /// `google.protobuf.DoubleValue` impl Message for f64 { - fn recursion_limit() -> u32 { - 0 - } fn encode_raw(&self, buf: &mut B) where B: BufMut, @@ -308,9 +286,6 @@ impl Message for f64 { /// `google.protobuf.StringValue` impl Message for String { - fn recursion_limit() -> u32 { - 0 - } fn encode_raw(&self, buf: &mut B) where B: BufMut, @@ -349,9 +324,6 @@ impl Message for String { /// `google.protobuf.BytesValue` impl Message for Vec { - fn recursion_limit() -> u32 { - 0 - } fn encode_raw(&self, buf: &mut B) where B: BufMut, @@ -390,9 +362,6 @@ impl Message for Vec { /// `google.protobuf.BytesValue` impl Message for Bytes { - fn recursion_limit() -> u32 { - 0 - } fn encode_raw(&self, buf: &mut B) where B: BufMut, @@ -431,9 +400,6 @@ impl Message for Bytes { /// `google.protobuf.Empty` impl Message for () { - fn recursion_limit() -> u32 { - 0 - } fn encode_raw(&self, _buf: &mut B) where B: BufMut,