Keyboard shortcuts

Press ← or → to navigate between chapters

Press S or / to search in the book

Press ? to show this help

Press Esc to hide this help

Installing cctop

← back to the README

cctop runs on Linux, including WSL. It reads Linux process tables and drives agents over ptys and unix sockets, and there is no macOS or Windows build.

cctop is a single binary. It links no system libraries and needs no runtime, so “installing” it means putting one file on your PATH. That includes the multiplexer its tabs’ agents run in: rmux is built in, so there is no rmux or tmux to install alongside it.

Let the script do it

curl -fsSL https://raw.githubusercontent.com/flolep2607/cctop/main/install.sh | sh

It works out your architecture from uname -m, fetches that archive from the latest release, verifies it against the .sha256 published beside it, and installs the binary into /usr/local/bin — or ~/.local/bin if that directory is not yours to write, printing the line to add to your profile when the fallback is not on your PATH either. sudo is used only if the install needs it, and a sudo that cannot run (no tty, no askpass, no sudo at all) falls back rather than stopping.

Then, if sshfs is missing, it offers to install it — what cctop sandbox needs — with [y/N], so pressing Enter changes nothing. The question is asked on the terminal even under curl | sh, and skipped where there is none. To answer it in advance:

curl -fsSL https://raw.githubusercontent.com/flolep2607/cctop/main/install.sh | CCTOP_WITH_SSHFS=1 sh
curl -fsSL https://raw.githubusercontent.com/flolep2607/cctop/main/install.sh | sh -s -- --with-sshfs

(CCTOP_WITH_SSHFS=0 or --without-sshfs to skip it.) It uses whichever of apt-get, dnf, yum, pacman, zypper and apk it finds, through sudo unless you are root, and prints the command before running it. A failed sshfs install is reported and does not undo the cctop one.

Nothing is unpacked until the checksum has been checked, and a mismatch stops the install instead of warning about it afterwards. To read it before running it, curl -fsSLO it and look.

Download a binary by hand

A release ships two archives, x86_64 and aarch64, both statically linked against musl — so either runs on any distro, glibc or not. Grab the one for your architecture from the latest release and put cctop somewhere on your PATH:

# x86_64
d=$(mktemp -d)
curl -fsSL https://github.com/flolep2607/cctop/releases/latest/download/cctop-x86_64-unknown-linux-musl.tar.gz | tar xz -C "$d"
sudo install -m755 "$d/cctop" /usr/local/bin/cctop && rm -rf "$d"
# aarch64
d=$(mktemp -d)
curl -fsSL https://github.com/flolep2607/cctop/releases/latest/download/cctop-aarch64-unknown-linux-musl.tar.gz | tar xz -C "$d"
sudo install -m755 "$d/cctop" /usr/local/bin/cctop && rm -rf "$d"

The archive holds one file, called cctop, which is why each of these unpacks into a temporary directory rather than into whatever directory you are standing in. Run one inside a cctop checkout and tar stops at Cannot open: File exists; the install that follows then finds the crate directory where it expected the binary, reports omitting directory 'cctop', and leaves nothing on your PATH.

Every archive ships with a .sha256 file next to it, named for the archive rather than after it — cctop-x86_64-unknown-linux-musl.sha256, not cctop-x86_64-unknown-linux-musl.tar.gz.sha256, which is a 404:

d=$(mktemp -d)
curl -fsSL -O --output-dir "$d" https://github.com/flolep2607/cctop/releases/latest/download/cctop-x86_64-unknown-linux-musl.sha256
curl -fsSL -O --output-dir "$d" https://github.com/flolep2607/cctop/releases/latest/download/cctop-x86_64-unknown-linux-musl.tar.gz
(cd "$d" && sha256sum -c cctop-x86_64-unknown-linux-musl.sha256)

Staying up to date

A downloaded binary has no package manager behind it, so cctop --update fetches the newest release for your architecture and replaces the running executable in place:

cctop --update

Replacing the binary needs write access to the directory it lives in. The install above puts it in /usr/local/bin with sudo, so updating it needs sudo too:

sudo cctop --update

An update that lands prints what it brought, one heading per version crossed, so a machine three versions behind sees all three rather than only the newest:

Updated 0.7.0 -> 0.7.3.

What changed since 0.7.0:

  0.7.1
    - Codex accounts per subscription, and a tab you can close without losing
      your place

  0.7.2
    - Fix the login hint for a named account, and add a run skill that drives
      the TUI

  0.7.3
    - the signals between cctop and its agents stop getting lost

Full notes: https://github.com/flolep2607/cctop/releases

The notes come from the GitHub releases themselves, fetched after the binary is already in place — so a network that fails at that moment costs you the summary and not the update, and you get the link instead.

cctop checks for a new release once an hour in the background and, when one exists, says so in the footer. The next time you start it, it installs that release before opening: the version was already known, so nothing is waited on to discover it, and the download is the only pause. It then prints what changed, waits for you to press Enter, and starts as the new version.

Startup is the only moment it will do this. Nothing is open yet — no terminal held, no agent hosted, no pane to lose — so the new binary can simply take the place of the old one. That is not true of any later moment, which is why an update that becomes available while cctop is running waits for the next start rather than interrupting the one you are in.

A release counts once its binary for your machine is attached, so cctop never offers one it cannot fetch yet. It installs a given version over a given binary at most once: if that version is installed and the old one still starts, it says so on each start instead of downloading again. Each update it attempts leaves a line in update.log in the cache directory, which is the thing to attach to a report about one that went wrong.

To start on the version you already have, pass --no-auto-update. To stop it happening at all, set "auto_update": false in ui-prefs.json under your cache directory (~/.cache/cctop); cctop --update still works whenever you want it. cctop claude and the other agent aliases skip it too — you are waiting on an agent, and a download between the command and the agent starting is not what you asked for.

If cargo installed cctop, it asks instead of acting:

cctop 0.7.6 is out, and cargo installed this one (0.7.5) — replacing the binary
here would leave `cargo install --list` naming a version that is gone.
Run `cargo install cctop --version 0.7.6 --locked`? It builds from source. [y] update / [n] not now:

Answering y runs exactly that command, with cargo’s own output on screen, and starts the new version when it finishes. The objection was never the file — ~/.cargo/bin is writable — but the bookkeeping, and cargo install is what keeps cargo’s record straight. It builds from source, so it takes minutes, which is why it is a question and not a default. With cargo-binstall on your PATH the command offered is cargo binstall cctop --version … --locked --no-confirm instead, which fetches the release archive in seconds and keeps the same record. Answering n is remembered against that version and the question waits for the next release; cctop --update asks again whenever you want it.

A package manager other than cargo is left alone entirely — cctop will not touch a binary something else is responsible for. Update it the way you installed it.

A cargo build output is left alone as well, for bookkeeping of a quieter kind: cargo’s fingerprint sits beside target/debug/cctop and would go on calling whatever replaced it the build it produced — the update would land, and cargo build would report the file fresh and never put the real one back. cargo install cctop --force is how the release reaches PATH.

With cargo

cargo binstall cctop

cargo-binstall downloads the release archive, the same static binary the script installs, and records it the way cargo install would — so nothing has to compile. Without binstall, cargo builds it from crates.io:

cargo install cctop

Or straight from the repository, without waiting for a release:

cargo install --git https://github.com/flolep2607/cctop

From source

git clone https://github.com/flolep2607/cctop
cd cctop
cargo build --release

The binary lands at target/release/cctop. It links no system libraries and needs no runtime — a single file you can copy anywhere.

Building requires Rust 1.89 or newer (the code uses let-chains and std’s file locks).