rust-lang/rust · error
non-UTF8 diagnostic
Error message
non-UTF8 diagnostic
What it means
Thrown by `.expect("non-UTF8 diagnostic")` on `llvm::build_string(...)` for the `PGO`/`Linker` diagnostic branch in `diagnostic_handler` (write.rs:481). When LLVM emits a Profile-Guided-Optimization or linker diagnostic, rustc asks LLVM to render it to a string; if that rendered string is not valid UTF-8 this expect panics. The diagnostic is later emitted as a warning (`emit_warn`), but reaching the expect means the message bytes were malformed.
Source
Thrown at compiler/rustc_codegen_llvm/src/back/write.rs:481
line: opt.line,
column: opt.column,
pass_name: &opt.pass_name,
kind: match opt.kind {
OptimizationRemark => "success",
OptimizationMissed | OptimizationFailure => "missed",
OptimizationAnalysis
| OptimizationAnalysisFPCommute
| OptimizationAnalysisAliasing => "analysis",
OptimizationRemarkOther => "other",
},
message: &opt.message,
});
}
llvm::diagnostic::PGO(diagnostic_ref) | llvm::diagnostic::Linker(diagnostic_ref) => {
let message = llvm::build_string(|s| unsafe {
llvm::LLVMRustWriteDiagnosticInfoToString(diagnostic_ref, s)
})
.expect("non-UTF8 diagnostic");
dcx.emit_warn(FromLlvmDiag { message });
}
llvm::diagnostic::Unsupported(diagnostic_ref) => {
let message = llvm::build_string(|s| unsafe {
llvm::LLVMRustWriteDiagnosticInfoToString(diagnostic_ref, s)
})
.expect("non-UTF8 diagnostic");
dcx.emit_err(FromLlvmDiag { message });
}
llvm::diagnostic::UnknownDiagnostic(..) => {}
}
}
fn get_pgo_gen_path(config: &ModuleConfig) -> Option<CString> {
match config.pgo_gen {
SwitchWithOptPath::Enabled(ref opt_dir_path) => {
let path = if let Some(dir_path) = opt_dir_path {
dir_path.join("default_%m.profraw")View on GitHub (pinned to 22057b88b0)
Solutions
- Force a UTF-8/C locale for the build: `LC_ALL=C LANG=C cargo build`.
- If using PGO, regenerate the profile data (`-C profile-generate`) and confirm the `.profdata` is valid (`llvm-profdata show`).
- Switch to the official rustup toolchain to rule out a custom-LLVM diagnostic bug.
- Change linker (e.g. `rustflags = ["-C", "linker=clang", "-C", "link-arg=-fuse-ld=lld"]`) to see if the malformed diagnostic came from a specific linker.
- Report to rustc with the linker/LLVM version and the exact flags if reproducible.
Example fix
# before: localized linker diagnostic produces non-UTF-8 bytes cargo build --release # panic: non-UTF8 diagnostic # after: force C locale and a UTF-8-safe linker export LC_ALL=C LANG=C cargo build --release
Defensive patterns
Strategy: try-catch
Try / catch
let res = std::panic::catch_unwind(|| run_codegen_with_pgo_or_linker_diag());
if res.is_err() {
// PGO/Linker diagnostic string was non-UTF-8; fall back to a build without that diagnostic path.
run_codegen_silent();
} Prevention
- Use a UTF-8-capable linker (lld) and ensure its diagnostic output is UTF-8.
- Set LANG/LC_ALL to a UTF-8 locale so linker error text is decoded correctly.
- Avoid object/source paths containing non-UTF-8 bytes when PGO (-Cprofile-generate) is on.
- Keep linker and rustc from the same platform target; mismatched linkers emit localized non-UTF-8 messages.
When it happens
Trigger: Triggered during codegen/linking with PGO (`-C profile-use`/`-C profile-generate`) or when LLVM produces a linker diagnostic, AND the bytes LLVM writes via `LLVMRustWriteDiagnosticInfoToString` are not valid UTF-8 — e.g. a linker error containing locale-specific/non-UTF-8 characters, or memory corruption of the diagnostic buffer.
Common situations: Linker (`ld`/`lld`) emitting a localized or garbage message under PGO; using a non-UTF-8 locale (`LANG`/`LC_ALL`) that influences linker output; corrupt PGO profile data causing LLVM to emit a malformed diagnostic; custom/botched LLVM build. Rare with stock toolchains and C locales.
Related errors
AI-assisted analysis of rust-lang/rust@22057b88b0 (2026-08-03).
Data as JSON: /data/errors/fb06e0371fbf4ca7.json.
Report an issue: GitHub.