rust-lang/rust · error · anyhow::Error

unexpected base kind for gap region: {kind:?}

Error message

unexpected base kind for gap region: {kind:?}

What it means

Thrown by read_mapping_kind_and_region in coverage-dump's covfun parser when a mapping region has the gap high bit set (bit 31 of end_column) but the decoded kind is not MappingKind::Code. Per LLVM's coverage format, the gap bit converts a Code mapping into a Gap mapping; any other base kind (Expansion, Skip, Branch, MCDC*) with the gap bit is treated as a meaningless artifact and rejected rather than silently mishandled.

Source

Thrown at src/tools/coverage-dump/src/covfun.rs:189

impl<'a> Parser<'a> {
    fn read_simple_term(&mut self) -> anyhow::Result<CovTerm> {
        let raw_term = self.read_uleb128_u32()?;
        CovTerm::decode(raw_term).context("decoding term")
    }

    fn read_mapping_kind_and_region(&mut self) -> anyhow::Result<(MappingKind, MappingRegion)> {
        let mut kind = self.read_raw_mapping_kind()?;
        let mut region = self.read_raw_mapping_region()?;

        const HIGH_BIT: u32 = 1u32 << 31;
        if region.end_column & HIGH_BIT != 0 {
            region.end_column &= !HIGH_BIT;
            kind = match kind {
                MappingKind::Code(term) => MappingKind::Gap(term),
                // LLVM's coverage mapping reader will actually handle this
                // case without complaint, but the result is almost certainly
                // a meaningless implementation artifact.
                _ => return Err(anyhow!("unexpected base kind for gap region: {kind:?}")),
            }
        }

        Ok((kind, region))
    }

    fn read_raw_mapping_kind(&mut self) -> anyhow::Result<MappingKind> {
        let raw_mapping_kind = self.read_uleb128_u32()?;
        if let Some(term) = CovTerm::decode(raw_mapping_kind) {
            return Ok(MappingKind::Code(term));
        }

        assert_eq!(raw_mapping_kind & 0b11, 0);
        assert_ne!(raw_mapping_kind, 0);

        let (high, is_expansion) = (raw_mapping_kind >> 3, raw_mapping_kind & 0b100 != 0);
        if is_expansion {
            Ok(MappingKind::Expansion(high))

View on GitHub (pinned to 7088e4b63a)

Solutions

  1. Confirm the coverage artifact was produced by an LLVM version compatible with this coverage-dump parser.
  2. Re-generate the coverage data with the toolchain matching coverage-dump.
  3. If this is a new legitimate LLVM behavior, extend read_mapping_kind_and_region to handle the new kind combination rather than treating it as an error.
  4. Report the raw kind value (printed in the error) to identify which MappingKind variant collided.

Example fix

null
Defensive patterns

Strategy: try-catch

Validate before calling

// Before bulk parsing, this is an internal-format error; the best prevention is
// ensuring producer/dumper versions match. No caller-side validation is meaningful
// beyond checking the LLVM IR source toolchain version.

Try / catch

if let Err(e) = dump_covfun_mappings(llvm_ir, &filename_tables, &function_names) {
    if e.to_string().contains("unexpected base kind for gap region") {
        eprintln!("{e:#}. Likely version skew between coverage producer and coverage-dump.");
    }
    return Err(e);
}

Prevention

When it happens

Trigger: Parsing a coverage mapping record produced by an LLVM version that emits gap regions for non-Code mapping kinds, or by a malformed/corrupted coverage payload where the gap bit coincidentally collides with an already-specialized kind. Most commonly seen when coverage-dump is run against output from a newer/changed LLVM instrumentation.

Common situations: LLVM coverage instrumentation changed and now sets the gap bit on a branch/expansion region; a hand-crafted or truncated covfun payload; version skew between the rustc that produced the coverage and the coverage-dump parsing it.

Related errors


AI-assisted analysis of rust-lang/rust@7088e4b63a (2026-08-10). Data as JSON: /api/errors/6d8f43fb5b72bbe5. Report an issue: GitHub.