Entrypoint persists the generated TLS cert fingerprint so the properties script can read it from the main volume. The screen shows the active network, plaintext and TLS stratum ports, the SHA-256 fingerprint for miner pinning, and the worker username format (BTC address plus optional worker label).
174 lines
6.4 KiB
Bash
Executable File
174 lines
6.4 KiB
Bash
Executable File
#!/bin/bash
|
|
# Kamado Pool StartOS entrypoint.
|
|
#
|
|
# Reads /root/.kamado/start9/config.yaml via yq, resolves the chosen
|
|
# bitcoind variant (mainnet vs testnet4), exports the env vars the
|
|
# upstream ckpool entrypoint expects, renders ckpool.conf from the
|
|
# template shipped alongside this script, and then supervises
|
|
# ckpool-solo + kamado-api as a pair.
|
|
set -euo pipefail
|
|
|
|
CONFIG_FILE="/root/.kamado/start9/config.yaml"
|
|
if [[ ! -f "${CONFIG_FILE}" ]]; then
|
|
echo "kamado-entrypoint: config file missing: ${CONFIG_FILE}" >&2
|
|
exit 1
|
|
fi
|
|
|
|
q() { yq -r "$1" "${CONFIG_FILE}"; }
|
|
|
|
BITCOIND_VARIANT=$(q '.bitcoind.type')
|
|
case "${BITCOIND_VARIANT}" in
|
|
bitcoind)
|
|
export BITCOIN_RPC_HOST="bitcoind.embassy"
|
|
export BITCOIN_RPC_PORT=8332
|
|
# Satoshi's genesis block coinbase address. Used only for
|
|
# ckpool's startup coinbase-builder self-test; never credited
|
|
# a satoshi since solo mode pays the worker's stratum address.
|
|
SELFTEST_ADDRESS="1A1zP1eP5QGefi2DMPTfTL5SLmv7DivfNa"
|
|
;;
|
|
bitcoind-testnet)
|
|
export BITCOIN_RPC_HOST="bitcoind-testnet.embassy"
|
|
export BITCOIN_RPC_PORT=48332
|
|
# Testnet genesis coinbase address — valid P2PKH on testnet4.
|
|
SELFTEST_ADDRESS="mipcBbFg9gMiCh81Kj8tqqdgoZub1ZJRfn"
|
|
;;
|
|
*)
|
|
echo "kamado-entrypoint: unknown bitcoind variant: ${BITCOIND_VARIANT}" >&2
|
|
exit 1
|
|
;;
|
|
esac
|
|
|
|
export BITCOIN_RPC_USER=$(q '.bitcoind.user')
|
|
export BITCOIN_RPC_PASSWORD=$(q '.bitcoind.password')
|
|
export STRATUM_PORT=$(q '.stratum-port // 3333')
|
|
export POOL_BTCSIG=$(q '.advanced.pool-identifier // "/Kamado/"')
|
|
export STARTDIFF=$(q '.advanced.startdiff // 16384')
|
|
export MINDIFF=$(q '.advanced.mindiff // 1000')
|
|
export MAXDIFF=$(q '.advanced.maxdiff // 0')
|
|
export DROPIDLE=$(q '.advanced.dropidle // 0')
|
|
LOG_LEVEL=$(q '.advanced.log-level // "info"')
|
|
ZMQ_ENABLED=$(q '.advanced.zmq-enabled // true')
|
|
TLS_ENABLED=$(q '.tls.enabled // "disabled"')
|
|
TLS_PORT=$(q '.tls.port // 3334')
|
|
|
|
# CKPool-solo uses the worker's stratum username as the payout
|
|
# address and refuses to authenticate workers whose username is not
|
|
# a valid address on the active network. The conf `btcaddress` is
|
|
# only consulted once at startup, for ckpool's coinbase-builder
|
|
# self-test: it builds and validates a sample coinbase transaction
|
|
# against bitcoind before accepting any workers. Since no worker has
|
|
# connected yet at that point, we hand it the genesis block coinbase
|
|
# address for the active network — it's always valid, and solo mode
|
|
# never credits it a satoshi.
|
|
export POOL_BTCADDRESS="${SELFTEST_ADDRESS}"
|
|
|
|
export LOGDIR=/var/log/ckpool
|
|
export SOCKET_DIR=/run/ckpool
|
|
export BITCOIN_NOTIFY=true
|
|
# ckpool itself doesn't use ZMQ in this build — zmqblock is stripped
|
|
# from the rendered conf below. kamado-api subscribes separately.
|
|
export ZMQ_BLOCK=""
|
|
export BLOCKPOLL_MS=100
|
|
export UPDATE_INTERVAL_S=30
|
|
mkdir -p "${LOGDIR}" "${SOCKET_DIR}" /etc/ckpool
|
|
|
|
# Render ckpool.conf using the same sed approach as the upstream
|
|
# KamadoPool ckpool entrypoint — the template is bundled into the
|
|
# image at build time.
|
|
TEMPLATE=/etc/ckpool/ckpool.conf.template
|
|
CONF=/etc/ckpool/ckpool.conf
|
|
sed \
|
|
-e "s|\${BITCOIN_RPC_HOST}|${BITCOIN_RPC_HOST}|g" \
|
|
-e "s|\${BITCOIN_RPC_PORT}|${BITCOIN_RPC_PORT}|g" \
|
|
-e "s|\${BITCOIN_RPC_USER}|${BITCOIN_RPC_USER}|g" \
|
|
-e "s|\${BITCOIN_RPC_PASSWORD}|${BITCOIN_RPC_PASSWORD}|g" \
|
|
-e "s|\${BITCOIN_NOTIFY}|${BITCOIN_NOTIFY}|g" \
|
|
-e "s|\${POOL_BTCADDRESS}|${POOL_BTCADDRESS}|g" \
|
|
-e "s|\${POOL_BTCSIG}|${POOL_BTCSIG}|g" \
|
|
-e "s|\${BLOCKPOLL_MS}|${BLOCKPOLL_MS}|g" \
|
|
-e "s|\${UPDATE_INTERVAL_S}|${UPDATE_INTERVAL_S}|g" \
|
|
-e "s|\${STRATUM_PORT}|${STRATUM_PORT}|g" \
|
|
-e "s|\${MINDIFF}|${MINDIFF}|g" \
|
|
-e "s|\${STARTDIFF}|${STARTDIFF}|g" \
|
|
-e "s|\${MAXDIFF}|${MAXDIFF}|g" \
|
|
-e "s|\${DROPIDLE}|${DROPIDLE}|g" \
|
|
-e "s|\${LOGDIR}|${LOGDIR}|g" \
|
|
-e "s|\${ZMQ_BLOCK}|${ZMQ_BLOCK}|g" \
|
|
"${TEMPLATE}" > "${CONF}"
|
|
sed -i '/"zmqblock":/d' "${CONF}"
|
|
|
|
echo "kamado-entrypoint: starting ckpool (solo, ${BITCOIND_VARIANT}) on port ${STRATUM_PORT}"
|
|
/usr/local/bin/ckpool --btcsolo --config "${CONF}" --sockdir "${SOCKET_DIR}" --log-shares &
|
|
CKPOOL_PID=$!
|
|
|
|
export LISTEN_ADDR=":8080"
|
|
export CKPOOL_SOCKDIR="${SOCKET_DIR}"
|
|
export CKPOOL_LOGFILE="${LOGDIR}/ckpool.log"
|
|
export BITCOIN_RPC_URL="http://${BITCOIN_RPC_HOST}:${BITCOIN_RPC_PORT}"
|
|
export POLL_INTERVAL=5s
|
|
export KAMADO_LOG_LEVEL="${LOG_LEVEL}"
|
|
if [[ "${ZMQ_ENABLED}" == "true" ]]; then
|
|
export BITCOIN_ZMQ_BLOCK="tcp://${BITCOIN_RPC_HOST}:28332"
|
|
else
|
|
export BITCOIN_ZMQ_BLOCK=""
|
|
fi
|
|
|
|
echo "kamado-entrypoint: starting kamado-api"
|
|
/usr/local/bin/kamado-api &
|
|
API_PID=$!
|
|
|
|
# Optional TLS stratum via stunnel sidecar.
|
|
STUNNEL_PID=""
|
|
if [[ "${TLS_ENABLED}" == "enabled" ]]; then
|
|
TLS_DIR=/root/.kamado/tls
|
|
CERT="${TLS_DIR}/stratum.pem"
|
|
mkdir -p "${TLS_DIR}"
|
|
if [[ ! -f "${CERT}" ]]; then
|
|
echo "kamado-entrypoint: generating self-signed stratum TLS cert"
|
|
openssl req -x509 -newkey rsa:2048 -sha256 -nodes \
|
|
-keyout "${TLS_DIR}/stratum.key" \
|
|
-out "${TLS_DIR}/stratum.crt" \
|
|
-days 3650 \
|
|
-subj "/CN=kamado-pool-stratum" >/dev/null 2>&1
|
|
cat "${TLS_DIR}/stratum.key" "${TLS_DIR}/stratum.crt" > "${CERT}"
|
|
chmod 600 "${TLS_DIR}/stratum.key" "${CERT}"
|
|
fi
|
|
FINGERPRINT=$(openssl x509 -in "${TLS_DIR}/stratum.crt" -noout -fingerprint -sha256 | cut -d= -f2)
|
|
printf '%s\n' "${FINGERPRINT}" > "${TLS_DIR}/fingerprint.txt"
|
|
echo "kamado-entrypoint: stratum TLS SHA256 fingerprint: ${FINGERPRINT}"
|
|
|
|
STUNNEL_CONF=/etc/stunnel/stratum.conf
|
|
mkdir -p /etc/stunnel
|
|
cat > "${STUNNEL_CONF}" <<EOF
|
|
foreground = yes
|
|
pid =
|
|
output = /dev/stdout
|
|
debug = 4
|
|
|
|
[stratum]
|
|
accept = 0.0.0.0:${TLS_PORT}
|
|
connect = 127.0.0.1:${STRATUM_PORT}
|
|
cert = ${CERT}
|
|
EOF
|
|
|
|
echo "kamado-entrypoint: starting stunnel on :${TLS_PORT} -> :${STRATUM_PORT}"
|
|
/usr/bin/stunnel4 "${STUNNEL_CONF}" &
|
|
STUNNEL_PID=$!
|
|
fi
|
|
|
|
term() {
|
|
echo "kamado-entrypoint: SIGTERM — shutting down"
|
|
kill -TERM "${API_PID}" "${CKPOOL_PID}" ${STUNNEL_PID:-} 2>/dev/null || true
|
|
wait "${API_PID}" "${CKPOOL_PID}" ${STUNNEL_PID:-} 2>/dev/null || true
|
|
exit 0
|
|
}
|
|
trap term TERM INT
|
|
|
|
# shellcheck disable=SC2086
|
|
wait -n ${CKPOOL_PID} ${API_PID} ${STUNNEL_PID:-}
|
|
EXIT_CODE=$?
|
|
echo "kamado-entrypoint: a supervised process exited (${EXIT_CODE}), stopping the rest"
|
|
kill -TERM "${API_PID}" "${CKPOOL_PID}" ${STUNNEL_PID:-} 2>/dev/null || true
|
|
wait || true
|
|
exit "${EXIT_CODE}"
|