github rizsotto/Bear 4.2.1

6 hours ago

Bear 4.2.1 is a bug-fix release. It repairs compiler recognition for MSVC's
glued option spellings, clang's separated -F, and the way an output flag is
written back into an entry, and it teaches Bear about TI's classic Code
Generation Tools.

Features

  • TI Code Generation Tools recognized - armcl, cl6x, cl7x, cl2000,
    cl430, and clpru, the drivers Code Composer Studio still generates
    makefiles for. Bear previously produced no entry at all for these, and
    forcing one through as gcc did not work either, because the dialect
    differs where it matters most: an output file is --output_file=main.obj
    rather than -o main.obj.

Bug Fixes

  • MSVC glued option spellings - cl.exe glues the value to every
    /F-family and /Y-family option, and only the : spelling was in the
    flag table. A glued /FoCMakeFiles\x.obj, which is what both CMake and
    Meson emit, fell through to /F (set stack size), was classified as a
    link-stage option, and was stripped, so a real MSVC build lost its object
    name and its output field on every entry. A bare /Yc was worse: it
    consumed the source that followed it, and the compilation vanished from the
    database entirely. All four spellings of an output option - glued,
    colon-glued, colon-separated, and bare - are now handled.
  • Clang -F with a separated framework path - -F /Frameworks and
    -F/Frameworks name the same framework search path, but only the joined
    form was matched. Given the separated form, the path was rejected as a
    binary source and dropped, leaving a standalone -F in the recorded command
    that no compiler can consume. SwiftPM emits the separated spelling on macOS.
    (#715)
  • The output flag is recorded the way the build wrote it - Bear stored the
    flag and its path apart and always emitted them as two tokens, so
    -omain.o came back as -o main.o. Harmless for GCC, wrong for everyone
    else: cl.exe documents that /Fo takes no space before its value, and
    TI's long options glue theirs after =, so the database recorded a command
    line those compilers would reject. Rewriting a path under format.paths
    now lands inside the glued token.
  • One entry, one answer for a path - an extension-less relative output
    such as -o program was left untouched in arguments while the output
    field of the same entry was resolved, so a single entry gave two different
    answers for one path. Every output path now reaches the same resolver.

Internal Refactoring

  • Semantic analysis moved into its own crate, crates/semantic, which owns
    compiler recognition, flag parsing, and the compilers/*.yaml definitions.
    The application's configuration schema is no longer a dependency of the
    analysis core, so a back-edge from the driver is now a build error rather
    than a review finding. Two diagnostics change as a result: as: ccache
    echoes back verbatim instead of as wrapper, and the configuration echo
    prints before a bad compiler spelling is reported rather than after.
  • serde-saphyr moved to 1.1, taking the workspace from 135 packages to 127.
    The refreshed lock also clears RUSTSEC-2026-0204 in crossbeam-epoch, which
    reached Bear only through the integration-test dev-dependencies; no shipped
    binary was exposed.
  • CI now runs the security audit on every branch instead of master only, gates
    the dependency licenses through cargo-deny rather than printing a report
    nothing read, builds the documentation site once instead of twice, and runs
    compile and test in parallel behind lint.

Documentation

  • Configured compilers replace PATH discovery - in wrapper mode, listing a
    compiler does more than hint at recognition: it switches interception from
    scanning PATH to wrapping exactly the listed executables. Adding one
    unusual compiler therefore stops gcc and clang from being intercepted.
    This is intended, was documented nowhere, and is now stated in both the man
    page and the configuration reference.
  • Capturing a complete dry run - a new recipe covers why bear parse-sh
    produces a short or empty database, separating the causes a flag can fix (an
    already-built tree, a stopped build, an unannounced top-level directory, a
    translated locale) from the ones no flag can.
  • Wildcards in a dry run - a recipe spelling its sources *.c reaches
    parse-sh as an unexpanded glob, so the database gets an entry whose file is
    *.c. $(wildcard *.c) expands before the recipe is printed and comes out
    right.
  • The output-path-format requirement claimed that paths inside arguments
    are not transformed. Both halves of that were false, and the code was the
    half that was right. The real contract is now written down and pinned by a
    test.

Closed Issues

  • #715 - Clang semantic analysis drops operand from separated -F <path>

Thanks

Thanks to @harukawu for reporting the separated -F bug with a reproducer.

Thanks to the downstream packagers who keep Bear available and current -
chronically invisible work that this project depends on:

  • Alpine - @rtmongold
  • ALT Linux - Mikhail Tergoev
  • Termux - @nguynkhn
  • Arch, Artix, Fedora, Homebrew, Manjaro, MSYS2, and Parabola maintainers

Full Changelog: 4.2.0...4.2.1

Don't miss a new Bear release

NewReleases is sending notifications on new releases.