summaryrefslogtreecommitdiffstats
path: root/vendor/nom/src/multi/mod.rs
diff options
context:
space:
mode:
Diffstat (limited to 'vendor/nom/src/multi/mod.rs')
-rw-r--r--vendor/nom/src/multi/mod.rs152
1 files changed, 110 insertions, 42 deletions
diff --git a/vendor/nom/src/multi/mod.rs b/vendor/nom/src/multi/mod.rs
index a1191346d..73129084e 100644
--- a/vendor/nom/src/multi/mod.rs
+++ b/vendor/nom/src/multi/mod.rs
@@ -11,15 +11,28 @@ use crate::lib::std::vec::Vec;
use crate::traits::{InputLength, InputTake, ToUsize};
use core::num::NonZeroUsize;
-/// Repeats the embedded parser until it fails
-/// and returns the results in a `Vec`.
+/// Don't pre-allocate more than 64KiB when calling `Vec::with_capacity`.
+///
+/// Pre-allocating memory is a nice optimization but count fields can't
+/// always be trusted. We should clamp initial capacities to some reasonable
+/// amount. This reduces the risk of a bogus count value triggering a panic
+/// due to an OOM error.
+///
+/// This does not affect correctness. Nom will always read the full number
+/// of elements regardless of the capacity cap.
+#[cfg(feature = "alloc")]
+const MAX_INITIAL_CAPACITY_BYTES: usize = 65536;
+
+/// Repeats the embedded parser, gathering the results in a `Vec`.
+///
+/// This stops on [`Err::Error`] and returns the results that were accumulated. To instead chain an error up, see
+/// [`cut`][crate::combinator::cut].
///
/// # Arguments
/// * `f` The parser to apply.
///
-/// *Note*: if the parser passed to `many0` accepts empty inputs
-/// (like `alpha0` or `digit0`), `many0` will return an error,
-/// to prevent going into an infinite loop
+/// *Note*: if the parser passed in accepts empty inputs (like `alpha0` or `digit0`), `many0` will
+/// return an error, to prevent going into an infinite loop
///
/// ```rust
/// # use nom::{Err, error::ErrorKind, Needed, IResult};
@@ -64,10 +77,10 @@ where
}
}
-/// Runs the embedded parser until it fails and
-/// returns the results in a `Vec`. Fails if
-/// the embedded parser does not produce at least
-/// one result.
+/// Runs the embedded parser, gathering the results in a `Vec`.
+///
+/// This stops on [`Err::Error`] if there is at least one result, and returns the results that were accumulated. To instead chain an error up,
+/// see [`cut`][crate::combinator::cut].
///
/// # Arguments
/// * `f` The parser to apply.
@@ -126,9 +139,12 @@ where
}
}
-/// Applies the parser `f` until the parser `g` produces
-/// a result. Returns a pair consisting of the results of
-/// `f` in a `Vec` and the result of `g`.
+/// Applies the parser `f` until the parser `g` produces a result.
+///
+/// Returns a tuple of the results of `f` in a `Vec` and the result of `g`.
+///
+/// `f` keeps going so long as `g` produces [`Err::Error`]. To instead chain an error up, see [`cut`][crate::combinator::cut].
+///
/// ```rust
/// # use nom::{Err, error::{Error, ErrorKind}, Needed, IResult};
/// use nom::multi::many_till;
@@ -183,8 +199,11 @@ where
}
}
-/// Alternates between two parsers to produce
-/// a list of elements.
+/// Alternates between two parsers to produce a list of elements.
+///
+/// This stops when either parser returns [`Err::Error`] and returns the results that were accumulated. To instead chain an error up, see
+/// [`cut`][crate::combinator::cut].
+///
/// # Arguments
/// * `sep` Parses the separator between list elements.
/// * `f` Parses the elements of the list.
@@ -253,9 +272,13 @@ where
}
}
-/// Alternates between two parsers to produce
-/// a list of elements. Fails if the element
-/// parser does not produce at least one element.
+/// Alternates between two parsers to produce a list of elements until [`Err::Error`].
+///
+/// Fails if the element parser does not produce at least one element.$
+///
+/// This stops when either parser returns [`Err::Error`] and returns the results that were accumulated. To instead chain an error up, see
+/// [`cut`][crate::combinator::cut].
+///
/// # Arguments
/// * `sep` Parses the separator between list elements.
/// * `f` Parses the elements of the list.
@@ -323,13 +346,20 @@ where
}
}
-/// Repeats the embedded parser `n` times or until it fails
-/// and returns the results in a `Vec`. Fails if the
-/// embedded parser does not succeed at least `m` times.
+/// Repeats the embedded parser `m..=n` times
+///
+/// This stops before `n` when the parser returns [`Err::Error`] and returns the results that were accumulated. To instead chain an error up, see
+/// [`cut`][crate::combinator::cut].
+///
/// # Arguments
/// * `m` The minimum number of iterations.
/// * `n` The maximum number of iterations.
/// * `f` The parser to apply.
+///
+/// *Note*: If the parser passed to `many1` accepts empty inputs
+/// (like `alpha0` or `digit0`), `many1` will return an error,
+/// to prevent going into an infinite loop.
+///
/// ```rust
/// # use nom::{Err, error::ErrorKind, Needed, IResult};
/// use nom::multi::many_m_n;
@@ -362,7 +392,9 @@ where
return Err(Err::Failure(E::from_error_kind(input, ErrorKind::ManyMN)));
}
- let mut res = crate::lib::std::vec::Vec::with_capacity(min);
+ let max_initial_capacity =
+ MAX_INITIAL_CAPACITY_BYTES / crate::lib::std::mem::size_of::<O>().max(1);
+ let mut res = crate::lib::std::vec::Vec::with_capacity(min.min(max_initial_capacity));
for count in 0..max {
let len = input.input_len();
match parse.parse(input.clone()) {
@@ -392,10 +424,17 @@ where
}
}
-/// Repeats the embedded parser until it fails
-/// and returns the number of successful iterations.
+/// Repeats the embedded parser, counting the results
+///
+/// This stops on [`Err::Error`]. To instead chain an error up, see
+/// [`cut`][crate::combinator::cut].
+///
/// # Arguments
/// * `f` The parser to apply.
+///
+/// *Note*: if the parser passed in accepts empty inputs (like `alpha0` or `digit0`), `many0` will
+/// return an error, to prevent going into an infinite loop
+///
/// ```rust
/// # use nom::{Err, error::ErrorKind, Needed, IResult};
/// use nom::multi::many0_count;
@@ -442,12 +481,18 @@ where
}
}
-/// Repeats the embedded parser until it fails
-/// and returns the number of successful iterations.
-/// Fails if the embedded parser does not succeed
-/// at least once.
+/// Runs the embedded parser, counting the results.
+///
+/// This stops on [`Err::Error`] if there is at least one result. To instead chain an error up,
+/// see [`cut`][crate::combinator::cut].
+///
/// # Arguments
/// * `f` The parser to apply.
+///
+/// *Note*: If the parser passed to `many1` accepts empty inputs
+/// (like `alpha0` or `digit0`), `many1` will return an error,
+/// to prevent going into an infinite loop.
+///
/// ```rust
/// # use nom::{Err, error::{Error, ErrorKind}, Needed, IResult};
/// use nom::multi::many1_count;
@@ -499,8 +544,8 @@ where
}
}
-/// Runs the embedded parser a specified number
-/// of times. Returns the results in a `Vec`.
+/// Runs the embedded parser `count` times, gathering the results in a `Vec`
+///
/// # Arguments
/// * `f` The parser to apply.
/// * `count` How often to apply the parser.
@@ -529,7 +574,9 @@ where
{
move |i: I| {
let mut input = i.clone();
- let mut res = crate::lib::std::vec::Vec::with_capacity(count);
+ let max_initial_capacity =
+ MAX_INITIAL_CAPACITY_BYTES / crate::lib::std::mem::size_of::<O>().max(1);
+ let mut res = crate::lib::std::vec::Vec::with_capacity(count.min(max_initial_capacity));
for _ in 0..count {
let input_ = input.clone();
@@ -551,8 +598,10 @@ where
}
}
-/// Runs the embedded parser repeatedly, filling the given slice with results. This parser fails if
-/// the input runs out before the given slice is full.
+/// Runs the embedded parser repeatedly, filling the given slice with results.
+///
+/// This parser fails if the input runs out before the given slice is full.
+///
/// # Arguments
/// * `f` The parser to apply.
/// * `buf` The slice to fill
@@ -602,13 +651,20 @@ where
}
}
-/// Applies a parser until it fails and accumulates
-/// the results using a given function and initial value.
+/// Repeats the embedded parser, calling `g` to gather the results.
+///
+/// This stops on [`Err::Error`]. To instead chain an error up, see
+/// [`cut`][crate::combinator::cut].
+///
/// # Arguments
/// * `f` The parser to apply.
/// * `init` A function returning the initial value.
/// * `g` The function that combines a result of `f` with
/// the current accumulator.
+///
+/// *Note*: if the parser passed in accepts empty inputs (like `alpha0` or `digit0`), `many0` will
+/// return an error, to prevent going into an infinite loop
+///
/// ```rust
/// # use nom::{Err, error::ErrorKind, Needed, IResult};
/// use nom::multi::fold_many0;
@@ -670,15 +726,21 @@ where
}
}
-/// Applies a parser until it fails and accumulates
-/// the results using a given function and initial value.
-/// Fails if the embedded parser does not succeed at least
-/// once.
+/// Repeats the embedded parser, calling `g` to gather the results.
+///
+/// This stops on [`Err::Error`] if there is at least one result. To instead chain an error up,
+/// see [`cut`][crate::combinator::cut].
+///
/// # Arguments
/// * `f` The parser to apply.
/// * `init` A function returning the initial value.
/// * `g` The function that combines a result of `f` with
/// the current accumulator.
+///
+/// *Note*: If the parser passed to `many1` accepts empty inputs
+/// (like `alpha0` or `digit0`), `many1` will return an error,
+/// to prevent going into an infinite loop.
+///
/// ```rust
/// # use nom::{Err, error::{Error, ErrorKind}, Needed, IResult};
/// use nom::multi::fold_many1;
@@ -748,10 +810,11 @@ where
}
}
-/// Applies a parser `n` times or until it fails and accumulates
-/// the results using a given function and initial value.
-/// Fails if the embedded parser does not succeed at least `m`
-/// times.
+/// Repeats the embedded parser `m..=n` times, calling `g` to gather the results
+///
+/// This stops before `n` when the parser returns [`Err::Error`]. To instead chain an error up, see
+/// [`cut`][crate::combinator::cut].
+///
/// # Arguments
/// * `m` The minimum number of iterations.
/// * `n` The maximum number of iterations.
@@ -759,6 +822,11 @@ where
/// * `init` A function returning the initial value.
/// * `g` The function that combines a result of `f` with
/// the current accumulator.
+///
+/// *Note*: If the parser passed to `many1` accepts empty inputs
+/// (like `alpha0` or `digit0`), `many1` will return an error,
+/// to prevent going into an infinite loop.
+///
/// ```rust
/// # use nom::{Err, error::ErrorKind, Needed, IResult};
/// use nom::multi::fold_many_m_n;