fix: add missing .cxx/.cc/.hxx/.hh extensions to fmt; update docs for 0.7.0

This commit is contained in:
2026-05-30 15:32:16 +08:00
parent 865d8c52ff
commit e6788b4d71
20 changed files with 208 additions and 31 deletions

View File

@@ -1,10 +1,47 @@
# Changelog
## [0.7.0] - 2026-05-28
## [0.7.0] - 2026-05-30
Added:
- **FreeBSD, OpenBSD, NetBSD, DragonflyBSD target support** — full platform routing and dynamically generated target triples.
- **OpenBSD and NetBSD target support** — full platform routing with dynamically generated target triples using `std::env::consts::ARCH` and `std::env::consts::OS`. Affects `build`, `run`, `clean`, and the platform module.
- **`src/platform/bsd.rs`** — new dedicated BSD platform module shared by FreeBSD, OpenBSD, NetBSD, providing `bin_path`, `lib_path`, `elf_path`, `efi_path`, and `shared_lib_path`.
- **`build.out_dir` configuration option** — custom output directory that overrides the default `target/<triple>/<profile>` path for final artifacts. Supported in `build`, `run`, and config validation.
- **`dcr fmt` command** — new CLI command that formats all C/C++ source files (`*.c`, `*.cpp`, `*.h`, `*.hpp`) in `src/` and `tests/` using `clang-format`.
- **Incremental linking** — `needs_link()` function in `common.rs` that checks whether any object file is newer than the linked output, skipping unnecessary re-linking. Implemented for all backends (`unix_cc`, `msvc`, `gas`, `nasm`).
- **`build.kind = "none"` and `"custom"`** — two new project kind types for special build scenarios where no standard artifact is produced.
- **`install_bsd.sh`** — dedicated POSIX-compliant install script for BSD systems (FreeBSD, OpenBSD, NetBSD) with binary download and source build modes.
- **Linux ARM64 support in `install.sh`** — added `Linux:aarch64|Linux:arm64` target triple detection for pre-built binary downloads.
- **BSD OS detection in `install.sh`** — FreeBSD, OpenBSD, NetBSD detection and target triple resolution.
- **`rust-toolchain.toml`** — explicit `stable` channel toolchain pinning.
- **Integration tests** — `build_with_target_config` (verifies `build.target = "linux"`) and `build_with_out_dir` (verifies custom output directory).
- **`get_build_string_with_profile` made `pub`** — so `run.rs` can resolve custom output directory configuration.
Changed:
- **`build.target` semantics changed** — now strictly holds the target triple (e.g. `x86_64-unknown-linux-gnu`) or a short name (`linux`, `macos`, `windows`). No longer doubles as a custom output directory — that functionality moved to `build.out_dir`.
- **`build.standard` made optional** — changed from `String` to `Option<String>`. Validation only enforces non-empty for non-ASM languages. Skipped in `dcr.toml` output when empty.
- **`dcr run` with `out_dir`** — now resolves target directory respecting `build.out_dir` when configured, via `get_build_string_with_profile()` from `build.rs`.
- **`collect_sources()` returns empty vec** instead of error when no source files are found, allowing `kind = "none"` or `kind = "custom"` projects to have no source files.
- **CI/CD release workflow refactored** — `git2` made target-specific (no vendored-openssl on Windows), Zig-based cross-compilation for non-x86_64 Linux targets, Arch Linux package version sanitization (dashes → dots), NetBSD `gmake` symlink.
- **README compatibility table** — FreeBSD, OpenBSD, NetBSD build/runtime status upgraded from community/best-effort to officially supported.
- **Documentation updated** — `build-section.md` documents new `build.target` and `build.out_dir` fields. `target-directory.md` rewritten to clarify the distinction.
- **Dev channel dependency check in `install.sh`** — checks for `python3` or `jq` before attempting dev channel installations.
Fixed:
- **`dcr run` stdout/stderr not inherited** — child process output was captured and manually printed, breaking interactive programs. Fixed by switching to `Command::status()`.
- **Release CI race condition** — build matrix jobs could upload assets to a release that did not yet exist. Fixed by adding a dedicated `create-release` job.
- **GHA release — stable toolchain override** — resolved Rust toolchain override issues in CI.
- **Arch Linux package version sanitization** — version strings with dashes (e.g. `0.7.0-dev`) are invalid for Arch Linux `pkgver`. Fixed by replacing dashes with dots.
- **GPG permissions after Docker** — Docker operations changed GPG directory ownership. Fixed by running `chown` after Docker commands.
- **RPM package artifact paths** — RPM artifacts placed under `rpm/x86_64/` instead of `fedora/x86_64/`. Corrected in Dexoron Packages Index workflow.
- **`install.sh` JSON parsing robustness** — added `jq` as primary parser with `python3` fallback for dev channel release lookups.
Removed:
- **`format_roots()` helper** — removed from `common.rs`. Was only used by the old error path in `collect_sources()`.
- **Individual per-distro artifact download steps** — three separate `actions/download-artifact` steps replaced with unified `gh release download --clobber`.
## [0.6.9] - 2026-05-28

View File

@@ -33,7 +33,7 @@ DCR supports cross-compilation via `--target <triple>` or short names:
- Configure multiple targets in `dcr.toml`:
```toml
[build.targets]
[build]
targets = ["linux", "macos"]
[build.linux]

View File

@@ -33,6 +33,32 @@
<table>
<tr>
<td><b>Linux (Dexoron Packages)</b></td>
<td>
See https://dcr.dexoron.su for settings youre packages manager
**Arch Linux:**
```sh
sudo pacman -Sy dcr
```
**Debian/Ubuntu:**
```sh
sudo apt update && sudo apt install dcr
```
**Fedora/RHEL:**
```sh
sudo dnf install dcr
```
</td>
</tr>
<tr>
<td><b>Arch Linux (AUR)</b></td>
<td>
@@ -78,7 +104,7 @@ curl -fsSL https://dcr.dexoron.su/install.sh | bash
<td>
```sh
curl -fsSL https://raw.githubusercontent.com/dexoron/dcr/dev/install_bsd.sh | bash
curl -fsSL https://dcr.dexoron.su/install_bsd.sh | bash
```
</td>
@@ -152,15 +178,21 @@ kind = "bin"
|---|---|
| `dcr new <name>` | Create a new project |
| `dcr init` | Initialize current directory |
| `dcr add <dep>` | Add a dependency |
| `dcr build [--release]` | Build the project |
| `dcr run [--release]` | Build and run |
| `dcr clean` | Remove build artifacts |
| `dcr test` | Run project tests |
| `dcr fmt` | Format C/C++ sources (clang-format) |
| `dcr tree` | View dependency tree |
| `dcr gen <vscode\|clion\|compile-commands>` | Generate IDE integration |
| `dcr setup` | Initialize DCR registry |
other in [docs/](docs/) and `dcr --help`
---
## Platforms
## Platforms(pre-build source)
<div align="center">
@@ -169,9 +201,9 @@ other in [docs/](docs/) and `dcr --help`
| Linux | ✅ | ✅ | ❌ | ❌ | ❌ | ✅ | ✅ | ❌ | ❌ |
| macOS | ✅ | ✅ | ❌ | ❌ | ❌ | ❌ | ❌ | ❌ | ❌ |
| Windows | ✅ | ✅ | ❌ | ❌ | ❌ | ❌ | ❌ | ✅ | ✅ |
| FreeBSD | ✅ | ⚠️ | ❌ | ❌ | ❌ | ✅ | ❌ | ❌ | ❌ |
| OpenBSD | ✅ | ⚠️ | ❌ | ❌ | ❌ | ✅ | ❌ | ❌ | ❌ |
| NetBSD | ✅ | ⚠️ | ❌ | ❌ | ❌ | ✅ | ❌ | ❌ | ❌ |
| FreeBSD | ✅ | ❌ | ❌ | ❌ | ❌ | ✅ | ❌ | ❌ | ❌ |
| OpenBSD | ✅ | ❌ | ❌ | ❌ | ❌ | ✅ | ❌ | ❌ | ❌ |
| NetBSD | ✅ | ❌ | ❌ | ❌ | ❌ | ✅ | ❌ | ❌ | ❌ |
✅ officially supported · ⚠️ community / best-effort · ❌ not supported

View File

@@ -27,6 +27,7 @@
* [dcr clean](commands/dcr-clean.md)
* [dcr gen](commands/dcr-gen.md)
* [dcr test](commands/dcr-test.md)
* [dcr fmt](commands/dcr-fmt.md)
* [dcr tree](commands/dcr-tree.md)
## Dependencies & Build

View File

@@ -30,9 +30,12 @@ dcr build --debug --clean
- `build.compiler`
- `build.language`
- `build.standard`
- `build.cxx_standard`
- `build.kind`
- `build.target`
- `build.out_dir`
- `build.platform`
- `package.type`
- `build.cflags`
- `build.ldflags`
- `build.ldscript`
@@ -58,8 +61,9 @@ dcr build --debug --clean
- Profile flag (`--debug` / `--release`) can appear in any argument position (duplicates are rejected).
- Unknown profile flags return an error.
- `--target <triple>` builds for specified target (short names: `linux`, `macos`, `windows`).
- `--target <triple>` builds for specified target (short names: `linux`, `macos`, `windows`, `freebsd`, `openbsd`, `netbsd`).
- `--verbose` prints the compiler/linker command lines to stderr (also works via `DCR_DEBUG` env var).
- `--workspace <name>` filters build to a specific workspace member.
- If no `--target`, builds for `build.targets` or native.
- Incremental rebuild checks source/object mtime and tracked header dependencies.
- `--force` skips build cache checks and recompiles.

19
docs/commands/dcr-fmt.md Normal file
View File

@@ -0,0 +1,19 @@
# dcr fmt
Formats all C/C++ source files using `clang-format`.
## Usage
```sh
dcr fmt
```
## Behavior
1. Scans `src/` and `tests/` directories recursively.
2. Formats all C/C++ source and header files (`.c`, `.cpp`, `.cxx`, `.cc`, `.h`, `.hpp`, `.hxx`, `.hh`) using `clang-format`.
3. Uses `.clang-format` if present in the project root, otherwise falls back to LLVM style.
## Requirements
- `clang-format` must be installed and available in PATH.

View File

@@ -23,11 +23,12 @@ dcr run --debug --clean
## Restrictions
- If `build.kind` (or `build.{profile}.kind`) is `"staticlib"` or `"sharedlib"`, `run` exits with error.
- If `build.kind` (or `build.{profile}.kind`) is `"staticlib"`, `"sharedlib"`, `"efi"`, or `"elf"`, `run` exits with error.
- The profile is selected from the first argument.
- `--target <triple>` runs the binary for specified target (short names: `linux`, `macos`, `windows`).
- `--target <triple>` runs the binary for specified target (short names: `linux`, `macos`, `windows`, `freebsd`, `openbsd`, `netbsd`).
- `--force` skips build cache checks and recompiles.
- `--clean` removes `target/<profile>` and `build.clean` paths before building.
- `--workspace <name>` filters build to a specific workspace member.
## `run.cmd` variables

View File

@@ -30,10 +30,13 @@ You can also add `--force` or `--clean` to `build`/`run`.
## Artifacts
By default:
By default (for `kind = "bin"`):
- `target/debug/<name>` (or `.exe` on Windows)
- `target/release/<name>` (or `.exe` on Windows)
- `target/<target>/debug/<name>` (or `.exe` on Windows)
- `target/<target>/release/<name>` (or `.exe` on Windows)
Where `<target>` is `native` or a target triple.
Use `build.out_dir` to override the output directory.
Default compiler flags:
@@ -58,6 +61,14 @@ Shared library mode (`kind = "sharedlib"`):
- macOS: `lib<name>.dylib`
- Windows: `<name>.dll`
UEFI executable mode (`kind = "efi"`):
- All platforms: `<name>.efi`
Bare-metal ELF mode (`kind = "elf"`):
- All platforms: `<name>` (no extension)
## Profile overrides
Use `[build.debug]` and `[build.release]` to override build settings per profile.

View File

@@ -32,11 +32,11 @@ kind = "bin"
- `language` (string or array, required): `c`, `c++`, `cpp`, `cxx`, or `asm`.
Mixed languages can be specified as an array, for example `["c", "c++", "asm"]`.
- `standard` (string, required): C language standard passed to compiler (e.g. `c11`, `c17`, `gnu11`).
- `standard` (string, optional): C language standard passed to compiler (e.g. `c11`, `c17`, `gnu11`). Defaults to `c11`.
- `cxx_standard` (string, optional): C++ language standard passed to compiler for `.cpp`/`.cxx`/`.cc` files
(e.g. `c++17`, `gnu++17`, `c++20`). When set, overrides `standard` for C++ sources.
- `compiler` (string, required): compiler command (for example `clang`, `gcc`, `cl`).
- `kind` (string, required): `bin`, `staticlib`, `sharedlib`, `efi`, or `elf`.
- `kind` (string, optional): `bin`, `staticlib`, `sharedlib`, `efi`, `elf`, `none`, or `custom`. Defaults to `bin`.
- `filename` (string, optional): custom output filename (without extension). Overrides `package.name` for the final artifact.
- `extension` (string, optional): custom file extension without the leading dot (e.g. `BIN`, `efi`, `EFI`). Combined with `filename`.
- `inherit` (bool, optional): inherit settings from base `[build]` (default `true`). If `false`, only use target/profile specific settings.

View File

@@ -35,17 +35,16 @@ Workspace-only root:
- `package.name`
- `package.version`
- `build.language`
- `build.standard`
- `build.compiler`
- `build.kind`
`build.kind` must be either `bin`, `staticlib`, or `sharedlib`.
## Optional keys
- `build.standard` (default: `c11`)
- `build.kind` (default: `bin`; valid: `bin`, `staticlib`, `sharedlib`, `efi`, `elf`, `none`, `custom`)
- `build.inherit`
- `build.targets`
- `build.target`
- `build.out_dir`
- `build.platform`
- `build.cflags`
- `build.ldflags`

View File

@@ -18,6 +18,8 @@ frecli = { path = "./lib/frecli", include = ["."], lib = ["."], libs = ["frecli"
### Registry dependencies
Defined by name and version string. DCR automatically resolves the package from the configured registry index.
- `version` (string, required): version requirement.
- `features` (string array, optional): enable specific features.
### Git dependencies
Defined by repository URL and optionally branch, tag, or revision.

View File

@@ -23,6 +23,9 @@ dcr run --target linux --release
- `linux` → `x86_64-unknown-linux-gnu`
- `macos` → `x86_64-apple-darwin`
- `windows` → `x86_64-pc-windows-msvc`
- `freebsd` → `x86_64-unknown-freebsd`
- `openbsd` → `x86_64-unknown-openbsd`
- `netbsd` → `x86_64-unknown-netbsd`
### Full Target Triples
DCR supports any valid target triple in the format `<arch>-<vendor>-<os>-<abi>`. Common examples:
@@ -32,6 +35,9 @@ DCR supports any valid target triple in the format `<arch>-<vendor>-<os>-<abi>`.
- `aarch64-apple-darwin`
- `x86_64-pc-windows-msvc`
- `i686-pc-windows-gnu`
- `x86_64-unknown-freebsd`
- `x86_64-unknown-openbsd`
- `x86_64-unknown-netbsd`
## Configuration
@@ -40,11 +46,11 @@ DCR supports any valid target triple in the format `<arch>-<vendor>-<os>-<abi>`.
Configure multiple targets to build simultaneously:
```toml
[build.targets]
[build]
targets = ["linux", "macos", "windows"]
# Or per profile
[build.release.targets]
[build.release]
targets = ["linux", "macos"]
```
@@ -66,6 +72,10 @@ cflags = ["-Wall", "-O2", "-arch", "x86_64"]
[build.windows]
compiler = "x86_64-w64-mingw32-gcc"
ldflags = ["-static"]
[build.freebsd]
compiler = "clang"
cflags = ["-Wall", "-O2"]
```
### Target-Specific Toolchain
@@ -99,6 +109,9 @@ cmd = "open ./target/macos/release/myapp.app"
[run.windows]
cmd = "wine ./target/windows/release/myapp.exe"
[run.freebsd]
cmd = "./target/freebsd/release/myapp"
```
## Workspace and Dependencies Inheritance
@@ -151,7 +164,10 @@ target/
├── x86_64-unknown-linux-gnu/
│ ├── debug/
│ └── release/
└── aarch64-linux-gnu/
├── aarch64-linux-gnu/
│ ├── debug/
│ └── release/
└── x86_64-unknown-freebsd/
├── debug/
└── release/
```

View File

@@ -26,6 +26,8 @@ json = { git = "https://github.com/nlohmann/json", tag = "v3.11.2" }
- `include`: optional include subpaths (absolute or relative to dep root).
- `lib`: optional library subpaths (absolute or relative to dep root).
- `libs`: optional linker library names.
- `features`: optional feature flags for registry dependencies.
- `default-features`: whether to include default features (default `true`).
## Common valid compact forms
@@ -35,6 +37,8 @@ mylib = { path = "./libs/mylib" }
gitlib = { git = "https://github.com/user/repo" }
# Shortest form for path
simple = "./libs/simple"
# Registry with features
sdl2 = { version = "2.0.0", features = ["vulkan"] }
```
In these forms DCR will try defaults for include/lib dirs and use the dependency name as the linker library name.

View File

@@ -37,4 +37,4 @@ project/
- `target/<target>/<profile>/lib<name>.a` (or `<name>.lib` on Windows): output for `kind = "staticlib"`.
- `target/<target>/<profile>/lib<name>.so` (or `.dylib` on macOS, `<name>.dll` on Windows): output for `kind = "sharedlib"`.
If `build.target` is set, the final artifact is written to that custom directory, while object cache still stays in `target/<target>/<profile>/obj`.
If `build.out_dir` is set, the final artifact is written to that custom directory, while object cache still stays in `target/<target>/<profile>/obj`.

View File

@@ -13,6 +13,8 @@ dcr clean [--debug|--release] [--all]
dcr tree
dcr test
dcr gen <subcommand>
dcr fmt
dcr setup
dcr --help
dcr --version
dcr --update
@@ -20,11 +22,13 @@ dcr --update
## Notes on argument parsing
- `build`/`run` parse flags in any order (`--debug|--release`, `--force`, `--clean`, `--verbose`) and reject duplicates.
- `build`/`run` parse flags in any order (`--debug|--release`, `--force`, `--clean`, `--verbose`, `--workspace`) and reject duplicates.
- `new` requires exactly one argument.
- `init` and `--update` do not accept extra arguments.
- `clean` accepts `--debug|--release` and optional `--all`.
- `gen` supports `project-info`, `compile-commands`, `vscode`, `clion`.
- `fmt` formats C/C++ sources (`.c`, `.cpp`, `.cxx`, `.cc`, `.h`, `.hpp`, `.hxx`, `.hh`) in `src/` and `tests/` using `clang-format`.
- `setup` initializes DCR registries and local configuration.
- `tree` shows a dependency tree (similar to `cargo tree`).
- `test` / `tests` runs the project's tests.

View File

@@ -19,13 +19,14 @@ categories = ["string", "..."] # optional
[build]
language = "c|c++|cpp|cxx|asm" # required (string or array)
standard = "string" # required (e.g. "c11", "gnu11")
standard = "string" # optional (default "c11")
cxx_standard = "string" # optional (e.g. "c++17", "gnu++17")
compiler = "string" # required (e.g. "clang", "gcc")
kind = "bin|staticlib|sharedlib|efi|elf" # required
kind = "bin|staticlib|sharedlib|efi|elf|none|custom" # optional (default "bin")
target = "string" # optional (cross-compilation target triple)
out_dir = "string" # optional (custom output directory)
platform = "string" # optional (architecture hint, -march)
type = "string" # optional
cflags = ["string", "..."] # optional (supports {version} etc.)
ldflags = ["string", "..."] # optional (supports {version} etc.)
ldscript = "string" # optional (linker script path)
@@ -121,14 +122,15 @@ rev = "string" # optional (git commit)
include = ["string", "..."] # optional (include dirs)
lib = ["string", "..."] # optional (lib dirs)
libs = ["string", "..."] # optional (link libs)
features = ["string", "..."] # optional (registry features)
features = ["string", "..."] # optional (registry features)
default-features = true # optional (include default features)
```
## Validation rules
- `[package]`, `[build]`, `[dependencies]` must exist.
- Required string fields must be non-empty.
- `build.kind` must be `bin`, `staticlib`, `sharedlib`, `efi`, or `elf`.
- `build.kind` must be `bin`, `staticlib`, `sharedlib`, `efi`, `elf`, `none`, or `custom`.
- Dependency fields `include/lib/libs` must be string arrays when provided.
- `build.exclude`/`build.include` must be string arrays when provided.
- `build.roots` must be a string array when provided.

View File

@@ -2,7 +2,7 @@
## What commands are available?
`new`, `init`, `build`, `run`, `clean`, `gen`, `--help`, `--version`, `--update`.
`new`, `init`, `add`, `build`, `run`, `clean`, `test`, `fmt`, `tree`, `gen`, `setup`, `--help`, `--version`, `--update`.
## Is `dcr.toml` mandatory?

View File

@@ -8,8 +8,11 @@ Used with `dcr build` and `dcr run`:
- `--debug`: select debug profile.
- `--release`: select release profile.
- `--target <triple>`: build for specified target (short names: `linux`, `macos`, `windows`, `freebsd`, `openbsd`, `netbsd`).
- `--force`: ignore incremental cache checks and rebuild.
- `--clean`: remove `target/<profile>` and `build.clean` paths before build.
- `--verbose`: print compiler/linker command lines to stderr.
- `--workspace <name>`: filter build to a specific workspace member.
Notes:

View File

@@ -1,3 +1,20 @@
// DCR — Cargo-like C/C++ project manager.
//
// Copyright (C) 2026 Dexoron (Bezotechestvo Vladimir) <main@dexoron.su>
//
// This program is free software: you can redistribute it and/or modify
// it under the terms of the GNU General Public License as published by
// the Free Software Foundation, either version 3 of the License, or
// (at your option) any later version.
//
// This program is distributed in the hope that it will be useful,
// but WITHOUT ANY WARRANTY; without even the implied warranty of
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
// GNU General Public License for more details.
//
// You should have received a copy of the GNU General Public License
// along with this program. If not, see <https://www.gnu.org/licenses/>.
use crate::utils::log::error;
use crate::utils::text::{BOLD_GREEN, colored};
use glob::glob;
@@ -7,12 +24,20 @@ pub fn fmt(_args: &[String]) -> i32 {
let patterns = [
"src/**/*.c",
"src/**/*.cpp",
"src/**/*.cxx",
"src/**/*.cc",
"src/**/*.h",
"src/**/*.hpp",
"src/**/*.hxx",
"src/**/*.hh",
"tests/**/*.c",
"tests/**/*.cpp",
"tests/**/*.cxx",
"tests/**/*.cc",
"tests/**/*.h",
"tests/**/*.hpp",
"tests/**/*.hxx",
"tests/**/*.hh",
];
let mut files = Vec::new();

View File

@@ -1,3 +1,20 @@
// DCR — Cargo-like C/C++ project manager.
//
// Copyright (C) 2026 Dexoron (Bezotechestvo Vladimir) <main@dexoron.su>
//
// This program is free software: you can redistribute it and/or modify
// it under the terms of the GNU General Public License as published by
// the Free Software Foundation, either version 3 of the License, or
// (at your option) any later version.
//
// This program is distributed in the hope that it will be useful,
// but WITHOUT ANY WARRANTY; without even the implied warranty of
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
// GNU General Public License for more details.
//
// You should have received a copy of the GNU General Public License
// along with this program. If not, see <https://www.gnu.org/licenses/>.
pub fn bin_path(profile: &str, name: &str, target_dir: Option<&str>) -> String {
match target_dir {
Some(dir) => format!("{}/{}", dir.trim_end_matches('/'), name),