From 105dbdc38a3f99569507f321fcb8590c98baa517 Mon Sep 17 00:00:00 2001 From: Hugo Date: Mon, 26 Oct 2026 04:06:42 +0100 Subject: [PATCH] docs(readme): restructure the README with a project header, an overview and collapsible sections --- README.md | 564 +++++++++++++++++++++++++++++++++++++++++------------- 1 file changed, 428 insertions(+), 136 deletions(-) diff --git a/README.md b/README.md index 46f7bb2..b73bb2b 100644 --- a/README.md +++ b/README.md @@ -1,4 +1,37 @@ -# ctrace +
+ +# CoreTrace + +**Static and dynamic analysis. Unified diagnostics.** + +Analyze C/C++ with `ctrace`, add optional Python analysis, and bring findings
+to your terminal, SARIF reports or HTTP workflows. + +[**Website**](https://coretrace.fr) · [**Web app**](https://app.coretrace.fr/) · [**Releases**](https://github.com/CoreTrace/coretrace/releases) · [**Configuration**](docs/configuration.md) · [**Contributing**](CONTRIBUTING.md) + +[![CI](https://github.com/CoreTrace/coretrace/actions/workflows/build.yml/badge.svg?branch=main)](https://github.com/CoreTrace/coretrace/actions/workflows/build.yml) +[![Formatting](https://github.com/CoreTrace/coretrace/actions/workflows/clang-format.yml/badge.svg?branch=main)](https://github.com/CoreTrace/coretrace/actions/workflows/clang-format.yml) +[![License checks](https://github.com/CoreTrace/coretrace/actions/workflows/license-compliance.yml/badge.svg?branch=main)](https://github.com/CoreTrace/coretrace/actions/workflows/license-compliance.yml) +[![Line coverage: 89.56%, measured on 2026-10-04](https://img.shields.io/badge/coverage-89.56%25-brightgreen)](#coverage) + +Coverage snapshot: [2026-10-04 on main](#coverage). CI badges update automatically. + +[![Release](https://img.shields.io/github/v/release/CoreTrace/coretrace)](https://github.com/CoreTrace/coretrace/releases) +[![License: Apache-2.0](https://img.shields.io/badge/License-Apache--2.0-green.svg)](LICENSE) +[![Stars](https://img.shields.io/github/stars/CoreTrace/coretrace?style=flat&logo=github)](https://github.com/CoreTrace/coretrace/stargazers) +[![Community: issues](https://img.shields.io/badge/community-issues-blue?logo=github)](https://github.com/CoreTrace/coretrace/issues) + +[![C++20](https://img.shields.io/badge/C%2B%2B-20-blue?logo=cplusplus&logoColor=white)](#build) +[![LLVM 20](https://img.shields.io/badge/LLVM-20-8F0000?logo=llvm&logoColor=white)](#build) +[![Clang 20](https://img.shields.io/badge/Clang-20-00599C?logo=llvm&logoColor=white)](#build) + +
+ +--- + +[Quick start](#quick-start) · [Build](#build) · [Analyzers](#analyzers) · [Releases](#releases) · [Configuration](#configuration) · [SARIF](#sarif-output) · [Exit codes](#exit-codes) · [HTTP API](#server-mode) · [Development](#development) + +## Overview `ctrace` finds bugs in C and C++ code before it runs: stack buffer overflows, data races, deadlocks, uninitialized reads, memory errors at run time. It runs several analyzers on your @@ -8,7 +41,13 @@ that can fail a CI pipeline. It also checks Python projects. It is for C and C++ developers and the CI pipelines of their projects. Part of [CoreTrace](https://github.com/CoreTrace); see the [roadmap](ROADMAP.md) for where it is going. -### Quick start +| Capability | What you get | +| :--- | :--- | +| **Code analysis** | Static and dynamic analysis for C/C++, plus an optional Python analyzer. | +| **Unified findings** | Consistent diagnostics across tools, with SARIF 2.1.0 export. | +| **Workflow integration** | A command-line interface, configurable CI failure thresholds and an HTTP API. | + +## Quick start On Linux (x86-64 or arm64, glibc 2.34 or newer), the release archive needs neither a compiler nor LLVM; only the C library headers (`libc6-dev` on Debian and Ubuntu, `glibc-devel` on RHEL). @@ -47,29 +86,49 @@ at line 5, column 19 ↳ (this is a write access) ``` -The exit code is 2: a finding at or above `--fail-on`. Add `--sarif-format --report-file -ctrace.sarif` for a report that GitHub Code Scanning reads. On macOS (Apple silicon, macOS 14 or -newer), take the disk image of the release instead ([RELEASES](#releases)). To change the code, +The exit code is 2: a finding at or above `--fail-on`. On macOS (Apple silicon, macOS 14 or +newer), take the disk image of the release instead ([Releases](#releases)). To change the code, [build from source](#build). -### Contribute +Export the findings as SARIF for your CI workflow, a report that GitHub Code Scanning reads: -Start with an issue labelled -[`good first issue`](https://github.com/CoreTrace/coretrace/issues?q=is%3Aissue%20state%3Aopen%20label%3A%22good%20first%20issue%22), -and read [CONTRIBUTING.md](CONTRIBUTING.md): a maintainer answers within three business days. +```bash +./coretrace-v0.85.0-linux-amd64/bin/ctrace --input demo.c --invoke ctrace_stack_analyzer \ + --sarif-format --report-file ctrace.sarif +``` -### Repository documents +### Use a configuration file + +Save the equivalent settings as `coretrace.json` at your project root, adjusting `files.input` +to match your source files: + +```json +{ + "schema_version": 1, + "analysis": { + "invoke": ["ctrace_stack_analyzer"] + }, + "files": { + "input": ["src/main.c"] + }, + "output": { + "sarif_format": true, + "report_file": "ctrace.sarif" + } +} +``` -- [CONTRIBUTING.md](CONTRIBUTING.md) -- [CODE_OF_CONDUCT.md](CODE_OF_CONDUCT.md) -- [AUTHORS.md](AUTHORS.md) -- [CHANGELOG.md](CHANGELOG.md) -- [LICENSE](LICENSE) -- [SECURITY.md](SECURITY.md) -- [GOVERNANCE.md](GOVERNANCE.md) -- [ROADMAP.md](ROADMAP.md) +Pass the file to the orchestrator from your project root: -### BUILD +```bash +ctrace --config coretrace.json +``` + +Relative input paths are resolved from the configuration file's directory. Omitted settings +keep their defaults, and command-line options override the file's values. +See the [configuration reference](docs/configuration.md) for all available settings. + +## Build Builds from source need Git, CMake 3.28 or newer, Ninja, a C++20 compiler whose standard library provides `` (GCC 13 or newer, or Clang with libstdc++ 13 or libc++), and the LLVM 20 and @@ -80,6 +139,11 @@ LLVM and Clang installations: `LLVM_DIR` and `Clang_DIR` select their CMake pack `ctrace`. These paths are build-time settings; an installed or released `ctrace` does not need LLVM or Clang on the machine where it runs. +### Configure + +
+Ubuntu 24.04 · LLVM/Clang 20 + On Ubuntu 24.04, install the build tools and the same LLVM/Clang 20 packages as CI, then configure from the repository root: @@ -94,6 +158,11 @@ cmake -S . -B build -G Ninja \ -DENABLE_PYTHON_ANALYZER=OFF ``` +
+ +
+Ubuntu 22.04 · GCC 13 · LLVM/Clang 20 + On Ubuntu 22.04, the system's GCC 11 lacks `` and its CMake is 3.22: take GCC 13 from the toolchain PPA, as the release build does, and a CMake release from Kitware. The PPA also updates the system's `libstdc++6` and `libgcc-s1`. @@ -113,6 +182,11 @@ CC=gcc-13 CXX=g++-13 cmake -S . -B build -G Ninja \ -DENABLE_PYTHON_ANALYZER=OFF ``` +
+ +
+macOS · Homebrew LLVM/Clang 20 + On macOS, use Homebrew's versioned LLVM formula: ```bash @@ -124,6 +198,11 @@ cmake -S . -B build -G Ninja \ -DENABLE_PYTHON_ANALYZER=OFF ``` +
+ +
+Optional Python analyzer · Python 3.11+ + Python is optional: the configuration above builds `ctrace` without the Python analyzer, so it needs no Python virtual environment or Nuitka. `ENABLE_PYTHON_ANALYZER` defaults to `OFF`; passing it explicitly also turns it off when reusing a build directory configured with Python. @@ -148,6 +227,10 @@ needs Python and a C compiler, but the resulting standalone analyzer includes it It is staged in `build/libexec/coretrace/` and installed to `/libexec/coretrace/`; users of the built or installed `ctrace` need no Python installation. +
+ +### Build and verify + Build and verify the selected configuration: ```bash @@ -156,43 +239,48 @@ cmake --build build --parallel 4 ctest --test-dir build --output-on-failure ``` -With the Python analyzer enabled, for example: +## Analyzers -```bash -./build/ctrace --input app.py --invoke coretrace-python-analyzer -``` +Select one or more analyzers with `--invoke`, use `--static` for the static tool set, or `--dyn` +for runtime analysis. Each tool receives the inputs of its language. -Each input goes to the tools of its language: `.py` files to `coretrace-python-analyzer`, C -and C++ files to the others. The Python analyzer checks the whole project a file belongs to, -so it follows data across modules, but it only reports findings located in the files given to -`--input`, plus those about the project itself, such as a vulnerable version pinned in -`requirements.txt`. The project root is the nearest directory above the file that holds -`pyproject.toml`, `setup.py`, `setup.cfg` or `.git`, else the file's own directory. +| Analyzer | Analysis | Integration | +| :--- | :--- | :--- | +| [CoreTrace Stack Analyzer](#coretrace-stack-analyzer) | Static C/C++ | Built into `ctrace` | +| [CoreTrace Concurrency Analyzer](#coretrace-concurrency-analyzer) | Static C/C++ | Built into `ctrace` | +| [CoreTrace Runtime Analyzer](#coretrace-runtime-analyzer) | Dynamic C/C++ | Optional executable | +| [CoreTrace Python Analyzer](#coretrace-python-analyzer) | Static Python | Optional executable | +| [Cppcheck](#cppcheck) | Static C/C++ | External executable | +| [Flawfinder](#flawfinder) | Static C/C++ | External executable | +| [TscanCode](#tscancode) | Static C/C++ | External executable | +| [IKOS](#ikos) | Static C/C++ | External executable | -The Linux release archives (amd64, arm64) run on any distribution with glibc 2.34 or newer: -RHEL 9 and its rebuilds (Rocky, Alma), Amazon Linux 2023, Ubuntu 22.04+, Debian 12+, Fedora -35+. ctrace is built on Ubuntu 22.04 and carries its own libstdc++; the Python analyzer is -built on Rocky Linux 9. Each archive is unpacked and run on bare Rocky Linux 9, Ubuntu 22.04, -Debian 12 and Ubuntu 24.04 images, with no compiler or LLVM, before it is published. +External executables are resolved from `tools..path`, then the copy bundled with +`ctrace`, then `PATH`. `--static` also selects the external static tools, so they must be +installed. For C/C++ inputs, `--static` includes IKOS. Since CoreTrace does not interpret its +findings, these runs end incomplete (exit code 3). Use `--invoke` to select the tools available +on your machine and gate on a verdict. See [tool configuration](docs/configuration.md#tools) for +executable paths, additional arguments and timeouts. -The macOS disk image runs on Apple silicon with macOS 14 or newer. It holds one folder laid out -as the Linux archive, with the Homebrew libraries `ctrace` and the Python analyzer load (LLVM and -Clang, Python and OpenSSL...): copy the folder anywhere, Homebrew is not needed. Before it is -published, the image is mounted, its folder copied out, and run with Homebrew moved away. Its -third-party libraries are listed in `scripts/release/third-party-macos.txt`, and their licenses, -with each Homebrew formula's version, are under `licenses/homebrew/`. +### CoreTrace Stack Analyzer -Each archive carries the license of every third-party component it ships. `licenses/` holds -those of the code compiled into `ctrace` and of the Ubuntu libraries in `lib/`, with each -package's exact version. Each bundled analyzer holds its own under `libexec/coretrace/`. -`scripts/release/third-party.txt` lists what ships and where its license is. The packaging, and -the verification on each distribution, fail on a library or an executable it does not list. +[coretrace-stack-analyzer](https://github.com/CoreTrace/coretrace-stack-analyzer) analyzes C/C++ +through LLVM IR to report stack usage, recursion risks, buffer errors, escaping stack addresses +and resource-lifetime issues. It is linked into `ctrace` and compiles inputs in process; +no separate analyzer executable is needed. -Analyzing C and C++ needs no LLVM or clang installation either: Clang's own headers ship in -`lib/clang//include` next to `bin/ctrace`, and the stack analyzer compiles in process. -Only the C library's headers come from the system (`libc6-dev` on Debian and Ubuntu, -`glibc-devel` on RHEL, the SDK of the Command Line Tools on macOS: `xcode-select --install`), as -for any C build. `CT_CLANG` still selects another clang when set. +```bash +ctrace --input src/main.c --invoke ctrace_stack_analyzer +``` + +The orchestrator's tool name is `ctrace_stack_analyzer`. Configure its analysis profile, +models, stack limit and SMT settings in the +[`stack_analyzer` section](docs/configuration.md#stack_analyzer). Use `--compile-commands` +to supply your project's compilation database. + + + +### CoreTrace Concurrency Analyzer [coretrace-concurrency-analyzer](https://github.com/CoreTrace/coretrace-concurrency-analyzer) is linked into `ctrace` like the stack analyzer, and compiles in process too @@ -204,6 +292,17 @@ related location. With `--compile-commands`, the inputs are analyzed as one prog as the database says, so a thread started in one file is related to its body in another. `tools.coretrace-concurrency-analyzer.rules` selects its rules. +```bash +ctrace --input src/main.c --invoke coretrace-concurrency-analyzer +``` + +Configure rule selection and project analysis limits under +[`tools.coretrace-concurrency-analyzer`](docs/configuration.md#tools). + + + +### CoreTrace Runtime Analyzer + `--dyn` runs [coretrace-runtime-analyzer](https://github.com/CoreTrace/coretrace-runtime-analyzer) on each C/C++ input, which must be a whole program: it is built with CoreTrace instrumentation and run, and the memory errors that happen (heap and stack overflows, uses after free, double @@ -217,125 +316,187 @@ environment (`g++` on Debian and Ubuntu, `gcc-c++` on RHEL). The program runs wi privileges, in a separate process but not in a sandbox, so the HTTP server refuses dynamic analysis unless it is started with `--serve-allow-dynamic`. -### RELEASES - -Each release attaches the Linux archives and the macOS disk image with their `.sha256`, and a -build provenance attestation for each: a signed statement that this repository's release -workflow built it from the tagged commit. Check a downloaded archive with the GitHub CLI: - ```bash -gh attestation verify coretrace--linux-amd64.tar.gz -R CoreTrace/coretrace +ctrace --input src/main.c --invoke coretrace-runtime-analyzer ``` -The disk image is signed ad hoc, not with an Apple Developer ID, and is not notarized: macOS -refuses to run a `ctrace` that a browser downloaded. Download it with `curl`, which does not mark -the file, or remove the mark before opening it: +Use [`tools.coretrace-runtime-analyzer`](docs/configuration.md#tools) to configure its executable, +execution timeout and additional compiler arguments. `--dyn` selects the same analyzer. -```bash -curl -fsSLO https://github.com/CoreTrace/coretrace/releases/download//coretrace--macos-arm64.dmg -# or, after a download in a browser: -xattr -d com.apple.quarantine coretrace--macos-arm64.dmg -``` + -Every dependency the build fetches is pinned to a version tag or a commit, and every download -to its SHA-256 (`scripts/release/check-pinned-dependencies.sh`, run by `ctest`). +### CoreTrace Python Analyzer + +[coretrace-python-analyzer](https://github.com/CoreTrace/coretrace-python-analyzer) checks Python +projects for injection vulnerabilities, dangerous API usage, exposed secrets and vulnerable +dependencies. It follows data across functions and modules without executing the project. -### TESTS +Enable its standalone build as described in [Build](#build), or install the package from PyPI +and make its command available through `PATH` or `tools.coretrace-python-analyzer.path`. +The standalone bundle includes Python; installing from PyPI requires Python 3.11 or newer. + +[![Python analyzer on PyPI](https://img.shields.io/pypi/v/coretrace-python-analyzer?label=Python%20analyzer&logo=pypi&logoColor=white)](https://pypi.org/project/coretrace-python-analyzer/) +[![Python versions](https://img.shields.io/pypi/pyversions/coretrace-python-analyzer?logo=python&logoColor=white)](https://pypi.org/project/coretrace-python-analyzer/) + +With the Python analyzer enabled, for example: ```bash -ctest --test-dir build # every test -ctest --test-dir build -L unit # one component, in process -ctest --test-dir build -L integration # ctrace, a server, a socket peer or a real tool +./build/ctrace --input app.py --invoke coretrace-python-analyzer ``` -Coverage of CoreTrace's own code (`src/`, `include/`, `main.cpp`) needs a Clang build with -`-DCORETRACE_COVERAGE=ON`. `scripts/ci/coverage.sh ` then runs the tests and -writes a report for the unit tests, the integration tests and both, with an HTML report in -`/html`. CI publishes the same report as the `coverage-report` artifact. On Linux, the -build links Clang's profile runtime (`libclang-rt-20-dev` from apt.llvm.org), and `LLVM_PROFDATA` -and `LLVM_COV` name the tools of your Clang (`/usr/lib/llvm-20/bin/llvm-profdata`, `llvm-cov`). +Each input goes to the tools of its language: `.py` files to `coretrace-python-analyzer`, C +and C++ files to the others. The Python analyzer checks the whole project a file belongs to, +so it follows data across modules, but it only reports findings located in the files given to +`--input`, plus those about the project itself, such as a vulnerable version pinned in +`requirements.txt`. The project root is the nearest directory above the file that holds +`pyproject.toml`, `setup.py`, `setup.cfg` or `.git`, else the file's own directory. -### CODE STYLE (clang-format) +Configure its executable, additional arguments and timeout under +[`tools.coretrace-python-analyzer`](docs/configuration.md#tools). -- Version cible : `clang-format` 17 (utilisée dans la CI). -- Formater localement : `./scripts/format.sh` -- Vérifier sans modifier : `./scripts/format-check.sh` -- CMake : `cmake --build build --target format` ou `--target format-check` -- CI : le job GitHub Actions `clang-format` échoue si un fichier n’est pas formaté. +### Cppcheck -### DEBUG +[Cppcheck](https://github.com/cppcheck-opensource/cppcheck) provides general-purpose static +analysis for C/C++, including memory errors, null-pointer issues and coding mistakes. +CoreTrace enables its warning, style, performance and portability checks, forwards project +include directories and defines, and collects findings from all C/C++ inputs in one run. -You can pass arguments to CMake and invoke ASan. +Install `cppcheck` separately and make it available through `PATH` or `tools.cppcheck.path`. ```bash --DUSE_THREAD_SANITIZER=ON +ctrace --input src/main.c --invoke cppcheck ``` -or + +Use [`tools.cppcheck`](docs/configuration.md#tools) for extra arguments, suppressions and the +tool's worker count (`jobs`). Shared project settings belong in +[`build.include_dirs` and `build.defines`](docs/configuration.md#build). + +### Flawfinder + +[Flawfinder](https://github.com/david-a-wheeler/flawfinder) scans C/C++ source for potentially +unsafe function calls and security-sensitive API usage. CoreTrace reads its SARIF output +and includes the findings in the unified diagnostics. + +Install Flawfinder **2.0.16 or newer**, the first version with SARIF output, and expose its +executable through `PATH` or `tools.flawfinder.path`. + ```bash --DUSE_ADDRESS_SANITIZER=ON +ctrace --input src/main.c --invoke flawfinder ``` -> ⚠️ **Warning**: You cannot use `-DUSE_THREAD_SANITIZER=ON` and `-DUSE_ADDRESS_SANITIZER=ON` at the same time. +Configure extra arguments and the timeout under +[`tools.flawfinder`](docs/configuration.md#tools), preserving the SARIF output expected by +the integration. -### ARGUMENT +### TscanCode -The option list is generated from the binary and is the single source of truth: +[TscanCode](https://github.com/CoreTrace/coretrace-TscanCode) checks C/C++ code for defects such +as null-pointer dereferences. CoreTrace runs it with `--enable=all` over the input file list +and converts its text diagnostics into the common reporting format. + +Build or install the executable from the CoreTrace fork, then make `tscancode` available +through `PATH` or `tools.tscancode.path`. ```bash -./ctrace --help +ctrace --input src/main.c --invoke tscancode ``` -### VERSION +Configure its executable, additional arguments and timeout under +[`tools.tscancode`](docs/configuration.md#tools). + +### IKOS + +[IKOS](https://github.com/NASA-SW-VnV/ikos) is a static C/C++ analyzer based on abstract +interpretation. CoreTrace invokes it once per source file and forwards the configured entry +points. Install IKOS and its required toolchain using the upstream instructions, then make +`ikos` available through `PATH` or `tools.ikos.path`. ```bash -./ctrace --version +ctrace --input src/main.c --invoke ikos ``` -Version resolution is centralized at configure time: +Set entry points with `--entry-points` or `files.entry_points`. Executable paths, additional +arguments and timeouts are configured under [`tools.ikos`](docs/configuration.md#tools). -- release builds pass an explicit version string from CI, so published binaries print the exact GitHub release tag -- local Git builds resolve the version from `git describe --tags --dirty --always --match 'v*'` -- if Git metadata is unavailable, the build falls back to `dev` +**Current integration limit:** IKOS output is not yet converted into CoreTrace diagnostics. +It is displayed as raw output in console mode; its findings are excluded from the merged SARIF +report, diagnostic counts and the `--fail-on` findings threshold. Whenever IKOS runs, the +analysis ends incomplete (exit code 3), because CoreTrace does not interpret its findings. -You can also override the embedded version manually: +## Releases + +The Linux release archives (amd64, arm64) run on any distribution with glibc 2.34 or newer: +RHEL 9 and its rebuilds (Rocky, Alma), Amazon Linux 2023, Ubuntu 22.04+, Debian 12+, Fedora +35+. ctrace is built on Ubuntu 22.04 and carries its own libstdc++; the Python analyzer is +built on Rocky Linux 9. Each archive is unpacked and run on bare Rocky Linux 9, Ubuntu 22.04, +Debian 12 and Ubuntu 24.04 images, with no compiler or LLVM, before it is published. + +The macOS disk image runs on Apple silicon with macOS 14 or newer. It holds one folder laid out +as the Linux archive, with the Homebrew libraries `ctrace` and the Python analyzer load (LLVM and +Clang, Python and OpenSSL...): copy the folder anywhere, Homebrew is not needed. Before it is +published, the image is mounted, its folder copied out, and run with Homebrew moved away. Its +third-party libraries are listed in `scripts/release/third-party-macos.txt`, and their licenses, +with each Homebrew formula's version, are under `licenses/homebrew/`. + +Each archive carries the license of every third-party component it ships. `licenses/` holds +those of the code compiled into `ctrace` and of the Ubuntu libraries in `lib/`, with each +package's exact version. Each bundled analyzer holds its own under `libexec/coretrace/`. +`scripts/release/third-party.txt` lists what ships and where its license is. The packaging, and +the verification on each distribution, fail on a library or an executable it does not list. + +Analyzing C and C++ needs no LLVM or clang installation either: Clang's own headers ship in +`lib/clang//include` next to `bin/ctrace`, and the stack analyzer compiles in process. +Only the C library's headers come from the system (`libc6-dev` on Debian and Ubuntu, +`glibc-devel` on RHEL, the SDK of the Command Line Tools on macOS: `xcode-select --install`), as +for any C build. `CT_CLANG` still selects another clang when set. + +### Verify a release + +Each release attaches the Linux archives and the macOS disk image with their `.sha256`, and a +build provenance attestation for each: a signed statement that this repository's release +workflow built it from the tagged commit. Check a downloaded archive with the GitHub CLI: ```bash -cmake .. -DCORETRACE_VERSION_OVERRIDE=v0.74.0 +gh attestation verify coretrace--linux-amd64.tar.gz -R CoreTrace/coretrace ``` -### EXIT CODES +The disk image is signed ad hoc, not with an Apple Developer ID, and is not notarized: macOS +refuses to run a `ctrace` that a browser downloaded. Download it with `curl`, which does not mark +the file, or remove the mark before opening it: -`ctrace` is meant to gate a CI pipeline, so its exit code is a verdict on the run: +```bash +curl -fsSLO https://github.com/CoreTrace/coretrace/releases/download//coretrace--macos-arm64.dmg +# or, after a download in a browser: +xattr -d com.apple.quarantine coretrace--macos-arm64.dmg +``` -| Code | Meaning | -|---|---| -| `0` | Analysis complete, no finding at or above `--fail-on` | -| `1` | Usage or configuration error, including a run with no analysis selected (`--static`, `--dyn` or `--invoke`) | -| `2` | Findings at or above `--fail-on` (default: `error`) | -| `3` | Analysis incomplete: a tool could not be started, crashed or exited abnormally, or `ctrace` could not read its findings | +Every dependency the build fetches is pinned to a version tag or a commit, and every download +to its SHA-256 (`scripts/release/check-pinned-dependencies.sh`, run by `ctest`). -`--fail-on error|warning|none` (config: `analysis.fail_on`) sets the threshold. `none` never -fails on findings but still returns `3` on an incomplete analysis. Code `3` takes precedence over -`2`. + -`ctrace` cannot read the findings of `ikos`, of `flawfinder` when it prints no SARIF, or of -`cppcheck` and `tscancode` when a line of their output cites a source location (`file:line`, in -any format and any file, a header included) but does not parse. Such a run exits `3` and names -the tool, since its counts would be a guess; the findings read still count, and the tool's raw -output is shown. `--static` includes `ikos`, so its runs always end incomplete: to gate on a -verdict, pick the tools with `--invoke`. +## Command-line options -Interrupting a run (Ctrl+C, SIGINT or SIGTERM) stops the external tools it runs, with what they -started, and removes their run directories. The run gives no report, and `ctrace` ends by the -signal it received: the shell shows `130` or `143`. No tool starts after the interrupt. The -stack and concurrency analyzers are linked into `ctrace` and cannot be stopped, so `ctrace` waits -for one already running; interrupt again to quit at once. +The option list is generated from the binary and is the single source of truth: ```bash -./ctrace --fail-on warning --input src/main.c --invoke cppcheck,ctrace_stack_analyzer +ctrace --help ``` -### SARIF OUTPUT +## Configuration + +- Canonical default config: [`config/tool-config.json`](config/tool-config.json) +- Full schema and semantics: [Configuration reference](docs/configuration.md) +- Precedence: built-in defaults < config file < CLI + +For example, from the repository root with a local build: + +```bash +./build/ctrace --input tests/EmptyForStatement.cc --entry-points=main --verbose \ + --invoke cppcheck,ctrace_stack_analyzer +``` + +## SARIF output `--sarif-format` reports the whole run as **one** SARIF 2.1.0 log, whatever tools ran: one `run` per tool, rules collected per tool, a `coretrace/v1` partial fingerprint per result for @@ -343,7 +504,7 @@ stable alerts across runs, and the CWE as a result property. The document is pri stdout and written to `--report-file`, ready for `github/codeql-action/upload-sarif`. ```bash -./ctrace --sarif-format --invoke cppcheck,flawfinder,ctrace_stack_analyzer \ +ctrace --sarif-format --invoke cppcheck,flawfinder,ctrace_stack_analyzer \ --input src/main.c --report-file ctrace.sarif ``` @@ -374,22 +535,46 @@ most severe report is kept in its tool's run, and its `alsoReportedBy` property tools and rules. Reports without a CWE cannot be matched and are all kept; the console output and the counters still show every tool's report. -### CONFIGURATION +## Exit codes -- Canonical default config: `config/tool-config.json` -- Full schema and semantics: `docs/configuration.md` -- Precedence: built-in defaults < config file < CLI +`ctrace` is meant to gate a CI pipeline, so its exit code is a verdict on the run: + +| Code | Meaning | +|---|---| +| `0` | Analysis complete, no finding at or above `--fail-on` | +| `1` | Usage or configuration error, including a run with no analysis selected (`--static`, `--dyn` or `--invoke`) | +| `2` | Findings at or above `--fail-on` (default: `error`) | +| `3` | Analysis incomplete: a tool could not be started, crashed or exited abnormally, or `ctrace` could not read its findings | + +`--fail-on error|warning|none` (config: `analysis.fail_on`) sets the threshold. `none` never +fails on findings but still returns `3` on an incomplete analysis. Code `3` takes precedence over +`2`. + +`ctrace` cannot read the findings of `ikos`, of `flawfinder` when it prints no SARIF, or of +`cppcheck` and `tscancode` when a line of their output cites a source location (`file:line`, in +any format and any file, a header included) but does not parse. Such a run exits `3` and names +the tool, since its counts would be a guess; the findings read still count, and the tool's raw +output is shown. For C/C++ inputs, `--static` includes `ikos`, so these runs end incomplete: to +gate on a verdict, pick the tools with `--invoke`. + +Interrupting a run (Ctrl+C, SIGINT or SIGTERM) stops the external tools it runs, with what they +started, and removes their run directories. The run gives no report, and `ctrace` ends by the +signal it received: the shell shows `130` or `143`. No tool starts after the interrupt. The +stack and concurrency analyzers are linked into `ctrace` and cannot be stopped, so `ctrace` waits +for one already running; interrupt again to quit at once. ```bash -./ctrace --input ../tests/EmptyForStatement.cc --entry-points=main --verbose --static --dyn +ctrace --fail-on warning --input src/main.c --invoke cppcheck,ctrace_stack_analyzer ``` -### SERVER MODE +## Server mode -Start the HTTP server: +### Start the server + +Start the HTTP server from the repository root, where the request below finds its input: ```bash -./ctrace --ipc serve --serve-host 127.0.0.1 --serve-port 8080 --shutdown-token mytoken +./build/ctrace --ipc serve --serve-host 127.0.0.1 --serve-port 8080 --shutdown-token mytoken ``` If the address and port are already in use, the server exits with code 1. A host name is @@ -398,6 +583,9 @@ log gives: connect to that address, or use the same name. On macOS, a server on another on `127.0.0.1` can still share a port; details in [Input validation](docs/quality/input-validation.md#6-http-server). +
+Request example and response fields + Send a request: ```bash @@ -411,11 +599,11 @@ curl -X POST http://127.0.0.1:8080/api \ "params": { "input": ["./tests/buffer_overflow.cc"], "entry_points": ["main"], - "static_analysis": true, + "static_analysis": false, "dynamic_analysis": false, "invoke": ["flawfinder"], "sarif_format": true, - "report_file": "ctrace-report.txt", + "report_file": "ctrace.sarif", "output_file": "ctrace.out", "ipc": "serve", "ipc_path": "/tmp/coretrace_ipc", @@ -426,6 +614,7 @@ curl -X POST http://127.0.0.1:8080/api \ ``` Response notes: + - `status` is `ok` or `error`. An error carries `error.code` and `error.message`, and the HTTP status tells its kind: 400 for an invalid request (malformed JSON, a `proto` other than `coretrace-1.0`, an unknown method or parameter, a wrong value), 403 for a refused one @@ -434,11 +623,15 @@ Response notes: request or in a tool's output, are replaced by U+FFFD in the answer. - `result.diagnostics` lists every finding in one model (`tool`, `rule_id`, `file`, `line`, `column`, `severity`, `message`, `cwe`), whatever tool produced it; `result.diagnostics_summary_total` counts them by severity. - `result.sarif` is the merged SARIF log when `sarif_format` is true (also written to `report_file`). -- `result.gate` carries the verdict the CLI would exit with: `fail_on`, `exit_code` (see EXIT CODES), `failed_tools` and `unread_tools` (the tools that ran but whose findings CoreTrace could not read). +- `result.gate` carries the verdict the CLI would exit with: `fail_on`, `exit_code` (see [Exit codes](#exit-codes)), `failed_tools` and `unread_tools` (the tools that ran but whose findings CoreTrace could not read). - `result.uninterpreted_tools` names the tools whose output CoreTrace could not interpret: their findings are shown in `result.outputs` but are not counted. - `result.outputs` groups tool output by tool name. - Each output entry has `stream` and `message`. If a tool emits JSON, `message` is returned as a JSON object. +
+ +### Shutdown + Shutdown the server (HTTP request): ```bash @@ -461,8 +654,86 @@ Each `run_analysis` request gets the same shipped defaults as the CLI: the stack models and the bundled tools found next to the server's `ctrace` binary fill whatever the request and its `config` file leave empty. +## Development + +### Tests + +```bash +ctest --test-dir build # every test +ctest --test-dir build -L unit # one component, in process +ctest --test-dir build -L integration # ctrace, a server, a socket peer or a real tool +``` + +### Coverage + +The coverage badge shows the combined line coverage measured by the +[successful CI run on 2026-10-04](https://github.com/CoreTrace/coretrace/actions/runs/37216001843) +for commit [`42ae800`](https://github.com/CoreTrace/coretrace/commit/42ae8007c9528e95230ad8f2d44e4a38c60ad33a) +on `main`. This is a dated snapshot; the percentage is not updated automatically. + +| Tests | Lines | Functions | Branches | +| :--- | ---: | ---: | ---: | +| Unit | 64.58% | 73.11% | 62.10% | +| Integration | 79.36% | 91.90% | 66.54% | +| **Combined** | **89.56%** | **96.09%** | **81.08%** | + +The values come from `summary.md` in that run's `coverage-report` artifact. The coverage job +reports measurements without enforcing a minimum coverage threshold. + +Coverage of CoreTrace's own code (`src/`, `include/`, `main.cpp`) needs a Clang build with +`-DCORETRACE_COVERAGE=ON`. `scripts/ci/coverage.sh ` then runs the tests and +writes a report for the unit tests, the integration tests and both, with an HTML report in +`/html`. CI publishes the same report as the `coverage-report` artifact. On Linux, the +build links Clang's profile runtime (`libclang-rt-20-dev` from apt.llvm.org), and `LLVM_PROFDATA` +and `LLVM_COV` name the tools of your Clang (`/usr/lib/llvm-20/bin/llvm-profdata`, `llvm-cov`). + +### Code style (clang-format) + +- **Formatter:** `clang-format` 20, matching CI. +- **Format locally:** `./scripts/format.sh` +- **Check formatting:** `./scripts/format-check.sh` +- **CMake targets:** `cmake --build build --target format` or `--target format-check` +- **CI:** the `clang-format` workflow fails if a source file is not formatted. + +### Debug + +Enable a sanitizer when configuring CMake: + +```bash +-DUSE_THREAD_SANITIZER=ON +``` + +or + +```bash +-DUSE_ADDRESS_SANITIZER=ON +``` + +> **Warning:** You cannot use `-DUSE_THREAD_SANITIZER=ON` and `-DUSE_ADDRESS_SANITIZER=ON` at the same time. + +### Version + +```bash +./build/ctrace --version +``` + +Version resolution is centralized at configure time: + +- release builds pass an explicit version string from CI, so published binaries print the exact GitHub release tag +- local Git builds resolve the version from `git describe --tags --dirty --always --match 'v*'` +- if Git metadata is unavailable, the build falls back to `dev` + +You can also override the embedded version manually: + +```bash +cmake -S . -B build -DCORETRACE_VERSION_OVERRIDE=v0.74.0 +``` + ### Mangle/Demangle API +
+View the C++ API examples + ```c++ bool hasMangled = ctrace_tools::mangle::isMangled(entry_points); @@ -486,3 +757,24 @@ std::string mangled3 = ctrace_tools::mangle::mangleFunction("utils", "init", par std::cout << "Mangled utils::init(): " << mangled3 << "\n"; ``` + +
+ +## Contributing + +Bug reports, fixes, tests and documentation improvements are welcome. +Start with an issue labelled [`good first issue`](https://github.com/CoreTrace/coretrace/issues?q=is%3Aissue%20state%3Aopen%20label%3A%22good%20first%20issue%22) or browse the [open issues](https://github.com/CoreTrace/coretrace/issues), and read the [contribution guide](CONTRIBUTING.md): a maintainer answers within three business days. +For security concerns, follow the [private reporting process](SECURITY.md). + +### Repository documents + +| Document | Purpose | +| :--- | :--- | +| [Contributing](CONTRIBUTING.md) | Development setup and contribution guidelines. | +| [Code of conduct](CODE_OF_CONDUCT.md) | Community expectations. | +| [Authors](AUTHORS.md) | Project contributors. | +| [Changelog](CHANGELOG.md) | Release history. | +| [Security](SECURITY.md) | Vulnerability reporting. | +| [Governance](GOVERNANCE.md) | Roles and decision-making. | +| [Roadmap](ROADMAP.md) | Planned work, by priority. | +| [License](LICENSE) | Apache License 2.0. |