Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
13 changes: 8 additions & 5 deletions .github/workflows/ci.yml
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
# CI workflow for darwin-timeout.
# CI workflow for procguard.
#
# Fast feedback on every push/PR: lint first (fast fail), then test.
# See CONTRIBUTING.md "CI Auto-Verification Rules" for the full test matrix.
Expand All @@ -17,7 +17,7 @@ on:
push:
branches: [main, dev]
tags-ignore:
- 'v*'
- "v*"
pull_request:
# run on all PRs, not just main

Expand Down Expand Up @@ -85,12 +85,15 @@ jobs:
- name: Verify binary
run: |
cargo build --release
# create timeout symlink for testing
ln -sf procguard target/release/timeout
./target/release/procguard --version
./target/release/timeout --version
./target/release/timeout 0.1s sleep 60 || true
./target/release/procguard 0.1s sleep 60 || true

- name: Verify binary size
run: |
SIZE=$(stat -f%z target/release/timeout)
SIZE=$(stat -f%z target/release/procguard)
echo "Binary size: $SIZE bytes ($(($SIZE / 1024))KB)"
if [ $SIZE -gt 150000 ]; then
echo "ERROR: Binary too large (>150KB)"
Expand All @@ -99,7 +102,7 @@ jobs:

- name: Verify symbol count
run: |
SYMBOLS=$(nm -U target/release/timeout 2>/dev/null | wc -l)
SYMBOLS=$(nm -U target/release/procguard 2>/dev/null | wc -l)
echo "Exported symbols: $SYMBOLS"
if [ $SYMBOLS -gt 100 ]; then
echo "ERROR: Too many symbols (>100), check strip settings"
Expand Down
2 changes: 1 addition & 1 deletion .github/workflows/homebrew.yml
Original file line number Diff line number Diff line change
Expand Up @@ -14,7 +14,7 @@ jobs:
- name: Get SHA256 of universal binary
id: sha
run: |
URL="https://github.com/denispol/darwin-timeout/releases/download/${{ github.ref_name }}/timeout-macos-universal.tar.gz"
URL="https://github.com/denispol/procguard/releases/download/${{ github.ref_name }}/procguard-macos-universal.tar.gz"
SHA=$(curl -sL "$URL" | shasum -a 256 | cut -d' ' -f1)
echo "sha256=$SHA" >> $GITHUB_OUTPUT
echo "SHA256: $SHA"
Expand Down
75 changes: 40 additions & 35 deletions .github/workflows/release.yml
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
# Release workflow for darwin-timeout.
# Release workflow for procguard.
#
# Triggered when a version tag (v*) is pushed. Builds binaries for all
# platforms and creates a GitHub release.
Expand All @@ -8,9 +8,9 @@
# have passed CI.
#
# Produces:
# - timeout-macos-arm64.tar.gz (Apple Silicon)
# - timeout-macos-x86_64.tar.gz (Intel)
# - timeout-macos-universal.tar.gz (Universal binary, used by Homebrew)
# - procguard-macos-arm64.tar.gz (Apple Silicon)
# - procguard-macos-x86_64.tar.gz (Intel)
# - procguard-macos-universal.tar.gz (Universal binary, used by Homebrew)
#
# Usage:
# git tag -a v1.0.0 -m "v1.0.0"
Expand All @@ -21,7 +21,7 @@ name: Release
on:
push:
tags:
- 'v*'
- "v*"

env:
CARGO_TERM_COLOR: always
Expand Down Expand Up @@ -54,44 +54,48 @@ jobs:
- name: Create binaries
run: |
mkdir -p dist staging

# ARM64 (Apple Silicon)
cp target/aarch64-apple-darwin/release/timeout staging/timeout
strip staging/timeout
codesign -s - staging/timeout
cp target/aarch64-apple-darwin/release/procguard staging/procguard
strip staging/procguard
codesign -s - staging/procguard
ln -s procguard staging/timeout
cp -r completions staging/
tar -C staging -czvf dist/timeout-macos-arm64.tar.gz timeout completions
rm staging/timeout
tar -C staging -czvf dist/procguard-macos-arm64.tar.gz procguard timeout completions
rm staging/procguard staging/timeout

# x86_64 (Intel)
cp target/x86_64-apple-darwin/release/timeout staging/timeout
strip staging/timeout
codesign -s - staging/timeout
tar -C staging -czvf dist/timeout-macos-x86_64.tar.gz timeout completions
rm staging/timeout

cp target/x86_64-apple-darwin/release/procguard staging/procguard
strip staging/procguard
codesign -s - staging/procguard
ln -s procguard staging/timeout
tar -C staging -czvf dist/procguard-macos-x86_64.tar.gz procguard timeout completions
rm staging/procguard staging/timeout

# Universal (unversioned name for stable Homebrew URL)
lipo -create \
target/aarch64-apple-darwin/release/timeout \
target/x86_64-apple-darwin/release/timeout \
-output staging/timeout
strip staging/timeout
codesign -s - staging/timeout
tar -C staging -czvf dist/timeout-macos-universal.tar.gz timeout completions
rm staging/timeout

target/aarch64-apple-darwin/release/procguard \
target/x86_64-apple-darwin/release/procguard \
-output staging/procguard
strip staging/procguard
codesign -s - staging/procguard
ln -s procguard staging/timeout
tar -C staging -czvf dist/procguard-macos-universal.tar.gz procguard timeout completions
rm staging/procguard staging/timeout

# Show results
ls -lh dist/

- name: Verify binaries
run: |
for f in dist/timeout-macos-*.tar.gz; do
for f in dist/procguard-macos-*.tar.gz; do
echo "=== $f ==="
tar -tzf "$f"
tar -xzf "$f" -C /tmp
file /tmp/timeout
file /tmp/procguard
/tmp/procguard --version
/tmp/timeout --version
rm -rf /tmp/timeout /tmp/completions
rm -rf /tmp/procguard /tmp/timeout /tmp/completions
done

- name: Create Release
Expand All @@ -106,17 +110,18 @@ jobs:

| Platform | File |
|----------|------|
| Apple Silicon | `timeout-macos-arm64.tar.gz` |
| Intel | `timeout-macos-x86_64.tar.gz` |
| Universal | `timeout-macos-universal.tar.gz` |
| Apple Silicon | `procguard-macos-arm64.tar.gz` |
| Intel | `procguard-macos-x86_64.tar.gz` |
| Universal | `procguard-macos-universal.tar.gz` |

```bash
# Example: Install universal binary
tar -xzf timeout-macos-universal.tar.gz
sudo mv timeout /usr/local/bin/
tar -xzf procguard-macos-universal.tar.gz
sudo mv procguard timeout /usr/local/bin/
```

Verify with `timeout --version`.
Both `procguard` and `timeout` commands are included.
Verify with `procguard --version`.
files: dist/*.tar.gz
draft: false
prerelease: false
12 changes: 6 additions & 6 deletions CONTRIBUTING.md
Original file line number Diff line number Diff line change
@@ -1,15 +1,15 @@
# Contributing to darwin-timeout
# Contributing to procguard

Thank you for your interest in contributing! This guide covers the development workflow and verification requirements.

darwin-timeout is both a **CLI tool** and a **Rust library**. The same codebase powers both—`src/main.rs` is the CLI entry point, `src/lib.rs` exposes the public library API.
procguard is both a **CLI tool** and a **Rust library**. The same codebase powers both—`src/main.rs` is the CLI entry point, `src/lib.rs` exposes the public library API.

## Quick Start

```bash
# clone and build
git clone https://github.com/denispol/darwin-timeout.git
cd darwin-timeout
git clone https://github.com/denispol/procguard.git
cd procguard
cargo build --release

# run all tests (unit, integration, library API)
Expand Down Expand Up @@ -85,7 +85,7 @@ CI automatically triggers extra verification based on which files you change. **
- `cargo fmt --check`
- `cargo clippy -- -D warnings`
- `cargo test --lib` (154 unit tests)
- `cargo test --test integration` (179 tests)
- `cargo test --test integration` (185 tests)
- `cargo test --test library_api` (10 tests)
- `cargo test --test proptest` (30 properties)
- Binary size check (≤150KB)
Expand Down Expand Up @@ -225,7 +225,7 @@ src/
└── allocator.rs # thin libc malloc wrapper

tests/
├── integration.rs # CLI integration tests (179 tests)
├── integration.rs # CLI integration tests (185 tests)
├── library_api.rs # library API tests (10 tests)
├── proptest.rs # property-based tests (30 properties)
└── benchmarks.rs # performance benchmarks
Expand Down
20 changes: 10 additions & 10 deletions Cargo.lock

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

22 changes: 15 additions & 7 deletions Cargo.toml
Original file line number Diff line number Diff line change
@@ -1,15 +1,15 @@
[package]
name = "darwin-timeout"
version = "1.4.0"
name = "procguard"
version = "1.5.0"
edition = "2024"
rust-version = "1.91"
authors = ["denispol"]
description = "Run a command with a time limit (GNU timeout clone for Darwin/Apple platforms)"
description = "The formally verified process supervisor for macOS. Enforces time limits, memory quotas, and CPU throttling."
license = "MIT"
repository = "https://github.com/denispol/darwin-timeout"
repository = "https://github.com/denispol/procguard"
readme = "README.md"
documentation = "https://docs.rs/darwin-timeout"
keywords = ["cli", "timeout", "process", "macos", "darwin"]
documentation = "https://docs.rs/procguard"
keywords = ["cli", "timeout", "process", "macos", "supervisor"]
categories = ["command-line-utilities", "os::macos-apis"]

# publish allowlist - keep crates.io package small and deterministic
Expand All @@ -25,7 +25,7 @@ include = [
]

[lib]
name = "darwin_timeout"
name = "procguard"
path = "src/lib.rs"

[dependencies]
Expand Down Expand Up @@ -67,6 +67,14 @@ opt-level = 3
debug-assertions = true
overflow-checks = true

# Both binaries share the same source - behavior detected via argv[0] at runtime:
# - "procguard": defaults to --confine wall (sleep-aware)
# - "timeout": defaults to --confine active (GNU-compatible)
# Note: Cargo warns about shared main.rs; this is intentional for cargo install support.
[[bin]]
name = "procguard"
path = "src/main.rs"

[[bin]]
name = "timeout"
path = "src/main.rs"
Expand Down
Loading