From 416399dc1028545ea0ac6d68fb0b5cc5fa97d393 Mon Sep 17 00:00:00 2001 From: Nicholas Nethercote Date: Tue, 18 Jan 2022 13:22:50 +1100 Subject: Make `Decodable` and `Decoder` infallible. `Decoder` has two impls: - opaque: this impl is already partly infallible, i.e. in some places it currently panics on failure (e.g. if the input is too short, or on a bad `Result` discriminant), and in some places it returns an error (e.g. on a bad `Option` discriminant). The number of places where either happens is surprisingly small, just because the binary representation has very little redundancy and a lot of input reading can occur even on malformed data. - json: this impl is fully fallible, but it's only used (a) for the `.rlink` file production, and there's a `FIXME` comment suggesting it should change to a binary format, and (b) in a few tests in non-fundamental ways. Indeed #85993 is open to remove it entirely. And the top-level places in the compiler that call into decoding just abort on error anyway. So the fallibility is providing little value, and getting rid of it leads to some non-trivial performance improvements. Much of this commit is pretty boring and mechanical. Some notes about a few interesting parts: - The commit removes `Decoder::{Error,error}`. - `InternIteratorElement::intern_with`: the impl for `T` now has the same optimization for small counts that the impl for `Result` has, because it's now much hotter. - Decodable impls for SmallVec, LinkedList, VecDeque now all use `collect`, which is nice; the one for `Vec` uses unsafe code, because that gave better perf on some benchmarks. --- compiler/rustc_errors/src/json/tests.rs | 2 +- compiler/rustc_errors/src/lib.rs | 4 ++-- 2 files changed, 3 insertions(+), 3 deletions(-) (limited to 'compiler/rustc_errors/src') diff --git a/compiler/rustc_errors/src/json/tests.rs b/compiler/rustc_errors/src/json/tests.rs index d055937ac36..c5b3d204407 100644 --- a/compiler/rustc_errors/src/json/tests.rs +++ b/compiler/rustc_errors/src/json/tests.rs @@ -64,7 +64,7 @@ fn test_positions(code: &str, span: (u32, u32), expected_output: SpanTestData) { let bytes = output.lock().unwrap(); let actual_output = str::from_utf8(&bytes).unwrap(); - let actual_output: TestData = decode(actual_output).unwrap(); + let actual_output: TestData = decode(actual_output); assert_eq!(expected_output, actual_output) }) diff --git a/compiler/rustc_errors/src/lib.rs b/compiler/rustc_errors/src/lib.rs index a681298301a..dbacbba2ce0 100644 --- a/compiler/rustc_errors/src/lib.rs +++ b/compiler/rustc_errors/src/lib.rs @@ -99,8 +99,8 @@ impl Hash for ToolMetadata { // Doesn't really need to round-trip impl Decodable for ToolMetadata { - fn decode(_d: &mut D) -> Result { - Ok(ToolMetadata(None)) + fn decode(_d: &mut D) -> Self { + ToolMetadata(None) } } -- cgit 1.4.1-3-g733a5