Skip to content

Commit ba607b2

Browse files
committed
Auto merge of #11368 - dtolnay-contrib:partial, r=Muscraft
Fix failure to parse rustc's JSON output if it is too nested
2 parents 995f5ef + 9d7a3b2 commit ba607b2

File tree

1 file changed

+21
-3
lines changed

1 file changed

+21
-3
lines changed

src/cargo/core/compiler/mod.rs

Lines changed: 21 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -61,7 +61,7 @@ use crate::util::interning::InternedString;
6161
use crate::util::machine_message::{self, Message};
6262
use crate::util::{add_path_args, internal, iter_join_onto, profile};
6363
use cargo_util::{paths, ProcessBuilder, ProcessError};
64-
use rustfix::diagnostics::{Applicability, Diagnostic};
64+
use rustfix::diagnostics::Applicability;
6565

6666
const RUSTDOC_CRATE_VERSION_FLAG: &str = "--crate-version";
6767

@@ -1421,8 +1421,26 @@ fn on_stderr_line_inner(
14211421
rendered: String,
14221422
message: String,
14231423
level: String,
1424-
// `children: Vec<Diagnostic>` if we need to check them recursively
1425-
children: Vec<Diagnostic>,
1424+
children: Vec<PartialDiagnostic>,
1425+
}
1426+
1427+
// A partial rustfix::diagnostics::Diagnostic. We deserialize only a
1428+
// subset of the fields because rustc's output can be extremely
1429+
// deeply nested JSON in pathological cases involving macro
1430+
// expansion. Rustfix's Diagnostic struct is recursive containing a
1431+
// field `children: Vec<Self>`, and it can cause deserialization to
1432+
// hit serde_json's default recursion limit, or overflow the stack
1433+
// if we turn that off. Cargo only cares about the 1 field listed
1434+
// here.
1435+
#[derive(serde::Deserialize)]
1436+
struct PartialDiagnostic {
1437+
spans: Vec<PartialDiagnosticSpan>,
1438+
}
1439+
1440+
// A partial rustfix::diagnostics::DiagnosticSpan.
1441+
#[derive(serde::Deserialize)]
1442+
struct PartialDiagnosticSpan {
1443+
suggestion_applicability: Option<Applicability>,
14261444
}
14271445

14281446
if let Ok(mut msg) = serde_json::from_str::<CompilerMessage>(compiler_message.get()) {

0 commit comments

Comments
 (0)