Solo mine on a CPU
You need:
- An installed
exferbinary (Install) - A wallet (we only need the pubkey, not the private key — see below)
- A machine with at least a few hundred MB of RAM and a routable network
Get a payout pubkey
Generate a wallet on a different machine (not the mining host):
exfer wallet generate --output ~/payout.key --json
Grab the pubkey field. The mining host needs only this 64-hex pubkey —
the private key never leaves the wallet machine. This protects funds if
the mining host is compromised.
{
"pubkey": "fcbd5a818501cd5439ebe8c0c5ff244c0f1475333e226b7f998e6eb80552c69d",
"address": "8d896d64864f53214acb49aeb44a09a03d5bb23d19a417a6ce7b0da65c7bd750"
}
Start mining
exfer mine \
--datadir ~/.exfer \
--miner-pubkey fcbd5a818501cd5439ebe8c0c5ff244c0f1475333e226b7f998e6eb80552c69d \
--rpc-bind 127.0.0.1:9334 \
--repair-perms
| Flag | What it does |
|---|---|
--datadir | Where chain + state live. Same as exfer node |
--miner-pubkey | The pubkey that gets the coinbase reward. No private key needed on this host. |
--rpc-bind | Optional: expose RPC on the given address. Use 127.0.0.1 only. |
--repair-perms | Auto-fix node_identity.key permissions if stripped by the filesystem |
exfer mine is a superset of exfer node — it syncs the chain, accepts
peer connections, and additionally tries to win blocks.
Watch it work
# new tip every ~10 s under normal network conditions
journalctl -fu exfer | grep -E 'New tip|Mined block'
If you find a block, you'll see a Mined block at height H line. The
reward output goes to your --miner-pubkey and is immature for the
next 360 blocks before you can spend it.
Confirming coinbase rewards arrived
Coinbase outputs are returned with is_coinbase: true by
get_address_utxos. Use the get_address_utxos try-it
widget with your address to see them.
The is_coinbase flag plus the height field tell you whether the
output is spendable yet (tip_height - height >= 360).
Run as a service
See Run as a service for systemd, launchd, and
Docker templates. Substitute exfer node with exfer mine --miner-pubkey YOUR_PUBKEY_HEX.
Important: the systemd User=exfer should not be the user that holds
your wallet. The mining service is intended to be unprivileged and own
only the chain database.
Running on a low-RAM box
Each parallel Argon2id attempt needs 64 MiB. Today the miner uses a fixed number of worker threads tuned for the host's logical CPU count. On a tight VPS:
- Make sure the box has at least 512 MiB free RAM after the OS.
- Avoid running the miner alongside other memory-hungry processes (the Argon2id working set is random-access; if it spills to swap, hash rate collapses).
- If the host is shared (e.g. a tiny VPS), prefer pool mining — solo on a tiny box is mostly heat.
Stopping cleanly
sudo systemctl stop exfer
# or, if running in the foreground:
^C
The miner persists its state on the way out; no chain-database corruption from a clean shutdown.
Sanity checks before leaving it running for days
- Disk has headroom:
df -h $DATADIRshows growth, no full filesystem. - Time is correct: out-of-sync clocks cause peers to reject your
blocks.
timedatectl statusshould say "NTP synchronized: yes". - Pubkey is right: a typo in
--miner-pubkeymeans any blocks you find pay an address you don't control. - Backups in place: see Backup & recovery.