初始化 XXXig 打包部署脚本与 CI 流水线
Build and Release / build-and-test (amd64, ubuntu) (push) Successful in 1m12s
Build and Release / build-and-test (amd64, alpine) (push) Successful in 1m21s
Build and Release / build-and-test (arm64, ubuntu) (push) Successful in 5m24s
Build and Release / build-and-test (arm64, alpine) (push) Successful in 6m8s
Build and Release / release (push) Has been skipped
Build and Release / build-and-test (amd64, ubuntu) (push) Successful in 1m12s
Build and Release / build-and-test (amd64, alpine) (push) Successful in 1m21s
Build and Release / build-and-test (arm64, ubuntu) (push) Successful in 5m24s
Build and Release / build-and-test (arm64, alpine) (push) Successful in 6m8s
Build and Release / release (push) Has been skipped
Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
This commit is contained in:
@@ -0,0 +1,232 @@
|
|||||||
|
# .gitea/workflows/ci.yaml
|
||||||
|
name: Build and Release
|
||||||
|
|
||||||
|
on:
|
||||||
|
push:
|
||||||
|
branches: [main, develop]
|
||||||
|
tags: ['*']
|
||||||
|
|
||||||
|
env:
|
||||||
|
DOCKER_BUILDKIT: "1"
|
||||||
|
PRODUCT_NAME: "xxxig"
|
||||||
|
PACKAGE_VERSION: "6.26.0"
|
||||||
|
BUILDX_NO_DEFAULT_ATTESTATIONS: "1"
|
||||||
|
|
||||||
|
jobs:
|
||||||
|
build-and-test:
|
||||||
|
runs-on: ${{ matrix.arch == 'amd64' && 'ubuntu-latest-amd64' || 'ubuntu-latest-arm64' }}
|
||||||
|
strategy:
|
||||||
|
matrix:
|
||||||
|
arch: [amd64, arm64]
|
||||||
|
distro: [ubuntu, alpine]
|
||||||
|
steps:
|
||||||
|
- uses: actions/checkout@v4
|
||||||
|
|
||||||
|
- name: Setup Docker Buildx
|
||||||
|
run: |
|
||||||
|
# 创建 buildx builder(原生构建不需要 QEMU)
|
||||||
|
docker buildx create --use --name native-builder \
|
||||||
|
--driver docker-container \
|
||||||
|
--driver-opt network=host \
|
||||||
|
--driver-opt env.BUILDKIT_STEP_LOG_MAX_SIZE=50000000 \
|
||||||
|
--driver-opt env.BUILDKIT_STEP_LOG_MAX_SPEED=10000000 \
|
||||||
|
|| true
|
||||||
|
docker buildx inspect --bootstrap
|
||||||
|
|
||||||
|
- name: Build binaries
|
||||||
|
run: |
|
||||||
|
XXXIG_VERSION=v${PACKAGE_VERSION} # 上游源码 git tag 带 v 前缀,需补回
|
||||||
|
PLATFORM="linux/${{ matrix.arch }}"
|
||||||
|
|
||||||
|
echo "🏗️ Building ${PLATFORM} on native ${{ matrix.arch }} runner"
|
||||||
|
echo "📦 Distribution: ${{ matrix.distro }}"
|
||||||
|
|
||||||
|
# 设置 BuildKit 优化参数
|
||||||
|
export BUILDKIT_PROGRESS=plain
|
||||||
|
|
||||||
|
docker buildx build --pull \
|
||||||
|
--platform ${PLATFORM} \
|
||||||
|
--build-arg XXXIG_VERSION=${XXXIG_VERSION} \
|
||||||
|
--output type=local,dest=./output \
|
||||||
|
-f docker/Dockerfile.${{ matrix.distro }} .
|
||||||
|
|
||||||
|
- name: Package and test
|
||||||
|
run: |
|
||||||
|
DIR="./output/linux_${{ matrix.arch }}"
|
||||||
|
|
||||||
|
if [ ! -d "$DIR" ]; then
|
||||||
|
echo "❌ 构建输出目录不存在: $DIR"
|
||||||
|
exit 1
|
||||||
|
fi
|
||||||
|
|
||||||
|
TARGZ="${PRODUCT_NAME}-${{ matrix.arch }}-${{ matrix.distro }}-${PACKAGE_VERSION}.tar.gz"
|
||||||
|
tar -czf "${TARGZ}" -C "$DIR" .
|
||||||
|
|
||||||
|
echo "📦 Created package: ${TARGZ}"
|
||||||
|
ls -lh "${TARGZ}"
|
||||||
|
|
||||||
|
# 快速验证
|
||||||
|
mkdir -p test && tar -xzf "${TARGZ}" -C test
|
||||||
|
test/xxxigDaemon --version 2>/dev/null || echo "⚠️ 跳过版本检查"
|
||||||
|
rm -rf test
|
||||||
|
|
||||||
|
- name: Build Debian package
|
||||||
|
if: matrix.distro == 'ubuntu'
|
||||||
|
run: |
|
||||||
|
# 安装 dpkg-deb(如果需要)
|
||||||
|
sudo apt-get update && sudo apt-get install -y dpkg-dev
|
||||||
|
|
||||||
|
TARGZ="${PRODUCT_NAME}-${{ matrix.arch }}-${{ matrix.distro }}-${PACKAGE_VERSION}.tar.gz"
|
||||||
|
|
||||||
|
echo "📦 Building Debian package for ${{ matrix.arch }}..."
|
||||||
|
chmod +x debian/build-deb.sh
|
||||||
|
./debian/build-deb.sh ${{ matrix.arch }} ${PACKAGE_VERSION} "${TARGZ}"
|
||||||
|
|
||||||
|
ls -lh *.deb
|
||||||
|
|
||||||
|
- uses: https://github.com/ChristopherHX/gitea-upload-artifact@v4
|
||||||
|
with:
|
||||||
|
name: binaries-${{ matrix.arch }}-${{ matrix.distro }}
|
||||||
|
path: |
|
||||||
|
*.tar.gz
|
||||||
|
*.deb
|
||||||
|
retention-days: 1
|
||||||
|
|
||||||
|
release:
|
||||||
|
runs-on: ubuntu-latest-amd64
|
||||||
|
needs: build-and-test
|
||||||
|
if: startsWith(github.ref, 'refs/tags/')
|
||||||
|
steps:
|
||||||
|
- uses: https://github.com/ChristopherHX/gitea-download-artifact@v4
|
||||||
|
with:
|
||||||
|
pattern: binaries-*
|
||||||
|
path: ./packages
|
||||||
|
merge-multiple: true
|
||||||
|
|
||||||
|
- name: Upload packages and create release
|
||||||
|
env:
|
||||||
|
TOKEN: ${{ secrets.BUILD_TOKEN }}
|
||||||
|
TAG: ${{ github.ref_name }}
|
||||||
|
run: |
|
||||||
|
cd packages
|
||||||
|
|
||||||
|
# 提取仓库信息(移除 https:// 前缀和仓库路径)
|
||||||
|
REGISTRY=$(echo "${{ gitea.server_url }}" | sed 's|https\?://||')
|
||||||
|
OWNER="${{ gitea.repository_owner }}"
|
||||||
|
REPO_NAME=$(echo "${{ gitea.repository }}" | cut -d'/' -f2)
|
||||||
|
VERSION="${TAG#v}" # 包版本:去掉 git tag 的 v 前缀(registry 路径/下载名/Release 标题用)
|
||||||
|
|
||||||
|
echo "📦 上传包到 Generic Package Registry..."
|
||||||
|
echo " Registry: ${REGISTRY}"
|
||||||
|
echo " Owner: ${OWNER}"
|
||||||
|
echo " Package: ${PRODUCT_NAME}"
|
||||||
|
echo " Version: ${VERSION}"
|
||||||
|
|
||||||
|
# 上传所有 tar.gz 包到 Generic Package Registry
|
||||||
|
for file in *.tar.gz; do
|
||||||
|
[ ! -f "$file" ] && continue
|
||||||
|
echo " ⬆️ $file"
|
||||||
|
curl -fsSL -X PUT \
|
||||||
|
-H "Authorization: token ${TOKEN}" \
|
||||||
|
--upload-file "$file" \
|
||||||
|
"https://${REGISTRY}/api/packages/${OWNER}/generic/${PRODUCT_NAME}/${VERSION}/$file" || {
|
||||||
|
echo "❌ 上传失败: $file"
|
||||||
|
exit 1
|
||||||
|
}
|
||||||
|
done
|
||||||
|
|
||||||
|
# 上传 Debian 包到 Debian Package Registry (通用稳定版)
|
||||||
|
echo ""
|
||||||
|
echo "📦 上传 Debian 包到 Debian Package Registry..."
|
||||||
|
for file in *.deb; do
|
||||||
|
[ ! -f "$file" ] && continue
|
||||||
|
|
||||||
|
# 上传到 stable (通用稳定版)
|
||||||
|
echo " ⬆️ $file → stable"
|
||||||
|
curl -fsSL -X PUT \
|
||||||
|
-H "Authorization: token ${TOKEN}" \
|
||||||
|
--upload-file "$file" \
|
||||||
|
"https://${REGISTRY}/api/packages/${OWNER}/debian/pool/stable/main/upload" || {
|
||||||
|
echo "❌ Debian 包上传失败: $file (stable)"
|
||||||
|
exit 1
|
||||||
|
}
|
||||||
|
done
|
||||||
|
|
||||||
|
# 生成 Release 描述
|
||||||
|
echo ""
|
||||||
|
echo "📝 生成 Release..."
|
||||||
|
|
||||||
|
# 拼接 tar.gz 下载链接
|
||||||
|
ASSETS=$(for f in *.tar.gz; do
|
||||||
|
[ -f "$f" ] || continue
|
||||||
|
echo "- [\`$f\`](https://${REGISTRY}/api/packages/${OWNER}/generic/${PRODUCT_NAME}/${VERSION}/$f)"
|
||||||
|
done)
|
||||||
|
|
||||||
|
BODY=$(cat <<EOF
|
||||||
|
## Release ${VERSION}
|
||||||
|
|
||||||
|
### 📥 Debian/Ubuntu 安装
|
||||||
|
|
||||||
|
\`\`\`bash
|
||||||
|
sudo curl https://${REGISTRY}/api/packages/${OWNER}/debian/repository.key -o /etc/apt/keyrings/gitea-${OWNER}.asc
|
||||||
|
echo "deb [signed-by=/etc/apt/keyrings/gitea-${OWNER}.asc] https://${REGISTRY}/api/packages/${OWNER}/debian stable main" | sudo tee /etc/apt/sources.list.d/${OWNER}.list
|
||||||
|
sudo apt-get update && sudo apt-get install xxxig
|
||||||
|
\`\`\`
|
||||||
|
|
||||||
|
### 📦 tar.gz 下载
|
||||||
|
|
||||||
|
${ASSETS}
|
||||||
|
EOF
|
||||||
|
)
|
||||||
|
|
||||||
|
RELEASE_DATA=$(jq -n --arg tag "$TAG" --arg ver "$VERSION" --arg body "$BODY" \
|
||||||
|
'{tag_name: $tag, name: "Release \($ver)", body: $body, draft: false, prerelease: false}')
|
||||||
|
|
||||||
|
# 创建 Release
|
||||||
|
echo ""
|
||||||
|
echo "🎉 创建 Release..."
|
||||||
|
RESPONSE=$(curl -fsSL -w "\n%{http_code}" -X POST \
|
||||||
|
-H "Authorization: token ${TOKEN}" \
|
||||||
|
-H "Content-Type: application/json" \
|
||||||
|
"https://${REGISTRY}/api/v1/repos/${{ gitea.repository }}/releases" \
|
||||||
|
-d "${RELEASE_DATA}")
|
||||||
|
|
||||||
|
HTTP_CODE=$(echo "$RESPONSE" | tail -n1)
|
||||||
|
RESPONSE_BODY=$(echo "$RESPONSE" | head -n-1)
|
||||||
|
|
||||||
|
if [ "$HTTP_CODE" = "201" ]; then
|
||||||
|
echo "✅ Release 创建成功"
|
||||||
|
RELEASE_ID=$(echo "$RESPONSE_BODY" | grep -o '"id":[0-9]*' | head -1 | cut -d':' -f2)
|
||||||
|
echo " Release ID: ${RELEASE_ID}"
|
||||||
|
elif [ "$HTTP_CODE" = "409" ]; then
|
||||||
|
echo "⚠️ Release 已存在,获取现有 Release ID..."
|
||||||
|
RELEASE_ID=$(curl -fsSL \
|
||||||
|
-H "Authorization: token ${TOKEN}" \
|
||||||
|
"https://${REGISTRY}/api/v1/repos/${{ gitea.repository }}/releases/tags/${TAG}" | \
|
||||||
|
grep -o '"id":[0-9]*' | head -1 | cut -d':' -f2)
|
||||||
|
echo " Release ID: ${RELEASE_ID}"
|
||||||
|
else
|
||||||
|
echo "❌ 创建 Release 失败 (HTTP ${HTTP_CODE})"
|
||||||
|
echo "$RESPONSE_BODY"
|
||||||
|
exit 1
|
||||||
|
fi
|
||||||
|
|
||||||
|
# 上传文件作为 Release 附件
|
||||||
|
echo ""
|
||||||
|
echo "📎 上传文件作为 Release 附件..."
|
||||||
|
for file in *.tar.gz *.deb; do
|
||||||
|
[ ! -f "$file" ] && continue
|
||||||
|
echo " ⬆️ $file"
|
||||||
|
|
||||||
|
# 使用 multipart/form-data 上传附件
|
||||||
|
curl -fsSL -X POST \
|
||||||
|
-H "Authorization: token ${TOKEN}" \
|
||||||
|
-F "attachment=@${file}" \
|
||||||
|
"https://${REGISTRY}/api/v1/repos/${{ gitea.repository }}/releases/${RELEASE_ID}/assets?name=${file}" || {
|
||||||
|
echo " ⚠️ 附件上传失败: $file(可能已存在)"
|
||||||
|
}
|
||||||
|
done
|
||||||
|
|
||||||
|
echo ""
|
||||||
|
echo "✅ Release 创建完成!"
|
||||||
|
echo "🔗 访问: https://${REGISTRY}/${{ gitea.repository }}/releases/tag/${TAG}"
|
||||||
@@ -0,0 +1,8 @@
|
|||||||
|
.claude
|
||||||
|
.codex
|
||||||
|
|
||||||
|
.vscode
|
||||||
|
.idea
|
||||||
|
.DS_Store
|
||||||
|
|
||||||
|
CLAUDE.md
|
||||||
+93
@@ -0,0 +1,93 @@
|
|||||||
|
#!/bin/bash
|
||||||
|
set -e
|
||||||
|
|
||||||
|
# 参数检查
|
||||||
|
if [ $# -ne 3 ]; then
|
||||||
|
echo "Usage: $0 <ARCH> <VERSION> <TARGZ_FILE>"
|
||||||
|
echo "Example: $0 amd64 6.26.0 xxxig-amd64-ubuntu-6.26.0.tar.gz"
|
||||||
|
exit 1
|
||||||
|
fi
|
||||||
|
|
||||||
|
ARCH=$1
|
||||||
|
VERSION=$2
|
||||||
|
TARGZ_FILE=$3
|
||||||
|
PKG_NAME="xxxig"
|
||||||
|
DEB_VERSION="${VERSION#v}" # Debian 版本号必须以数字开头,去掉可能的 v 前缀
|
||||||
|
|
||||||
|
# 转换架构名称(Docker 使用的架构名到 Debian 架构名)
|
||||||
|
case "$ARCH" in
|
||||||
|
amd64)
|
||||||
|
DEB_ARCH="amd64"
|
||||||
|
;;
|
||||||
|
arm64)
|
||||||
|
DEB_ARCH="arm64"
|
||||||
|
;;
|
||||||
|
*)
|
||||||
|
echo "Unsupported architecture: $ARCH"
|
||||||
|
exit 1
|
||||||
|
;;
|
||||||
|
esac
|
||||||
|
|
||||||
|
DEB_FILE="${PKG_NAME}_${DEB_VERSION}_${DEB_ARCH}.deb"
|
||||||
|
|
||||||
|
echo "📦 Building Debian package: ${DEB_FILE}"
|
||||||
|
echo " Architecture: ${DEB_ARCH}"
|
||||||
|
echo " Version: ${DEB_VERSION}"
|
||||||
|
echo " Source: ${TARGZ_FILE}"
|
||||||
|
|
||||||
|
# 创建临时目录
|
||||||
|
BUILD_DIR=$(mktemp -d)
|
||||||
|
trap "rm -rf $BUILD_DIR" EXIT
|
||||||
|
|
||||||
|
# 创建包目录结构
|
||||||
|
PKG_DIR="${BUILD_DIR}/${PKG_NAME}_${DEB_VERSION}_${DEB_ARCH}"
|
||||||
|
mkdir -p "${PKG_DIR}/DEBIAN"
|
||||||
|
mkdir -p "${PKG_DIR}/opt/xxxig"
|
||||||
|
mkdir -p "${PKG_DIR}/lib/systemd/system"
|
||||||
|
|
||||||
|
# 解压二进制文件
|
||||||
|
echo "📂 Extracting binaries..."
|
||||||
|
tar -xzf "${TARGZ_FILE}" -C "${PKG_DIR}/opt/xxxig"
|
||||||
|
|
||||||
|
# 生成 control 文件
|
||||||
|
echo "📝 Generating control file..."
|
||||||
|
sed -e "s/{{VERSION}}/${DEB_VERSION}/" \
|
||||||
|
-e "s/{{ARCH}}/${DEB_ARCH}/" \
|
||||||
|
debian/control.template > "${PKG_DIR}/DEBIAN/control"
|
||||||
|
|
||||||
|
# 复制维护脚本
|
||||||
|
echo "📋 Copying maintainer scripts..."
|
||||||
|
cp debian/postinst "${PKG_DIR}/DEBIAN/postinst"
|
||||||
|
cp debian/prerm "${PKG_DIR}/DEBIAN/prerm"
|
||||||
|
cp debian/postrm "${PKG_DIR}/DEBIAN/postrm"
|
||||||
|
chmod 755 "${PKG_DIR}/DEBIAN/postinst"
|
||||||
|
chmod 755 "${PKG_DIR}/DEBIAN/prerm"
|
||||||
|
chmod 755 "${PKG_DIR}/DEBIAN/postrm"
|
||||||
|
|
||||||
|
# 复制 systemd service 文件
|
||||||
|
echo "🔧 Installing systemd services..."
|
||||||
|
cp debian/xxxig-server.service "${PKG_DIR}/lib/systemd/system/"
|
||||||
|
cp debian/xxxig-daemon.service "${PKG_DIR}/lib/systemd/system/"
|
||||||
|
|
||||||
|
# 设置权限
|
||||||
|
chmod 755 "${PKG_DIR}/opt/xxxig/xxxigServer"
|
||||||
|
chmod 755 "${PKG_DIR}/opt/xxxig/xxxigDaemon"
|
||||||
|
chmod 755 "${PKG_DIR}/opt/xxxig/xxxig"
|
||||||
|
chmod 644 "${PKG_DIR}/opt/xxxig/config.json"
|
||||||
|
chmod 644 "${PKG_DIR}/opt/xxxig/config_cc.json"
|
||||||
|
chmod 644 "${PKG_DIR}/opt/xxxig/index.html"
|
||||||
|
chmod 644 "${PKG_DIR}/lib/systemd/system/xxxig-server.service"
|
||||||
|
chmod 644 "${PKG_DIR}/lib/systemd/system/xxxig-daemon.service"
|
||||||
|
|
||||||
|
# 构建 deb 包
|
||||||
|
echo "🔨 Building package..."
|
||||||
|
dpkg-deb --build --root-owner-group "${PKG_DIR}" "${DEB_FILE}"
|
||||||
|
|
||||||
|
# 检查包
|
||||||
|
echo "✅ Package built successfully!"
|
||||||
|
echo "📦 Package: $(pwd)/${DEB_FILE}"
|
||||||
|
echo "📊 Package info:"
|
||||||
|
dpkg-deb --info "${DEB_FILE}"
|
||||||
|
|
||||||
|
echo ""
|
||||||
|
echo "🎉 Done!"
|
||||||
Vendored
+18
@@ -0,0 +1,18 @@
|
|||||||
|
Package: xxxig
|
||||||
|
Version: {{VERSION}}
|
||||||
|
Section: net
|
||||||
|
Priority: optional
|
||||||
|
Architecture: {{ARCH}}
|
||||||
|
Depends: libc6, libuv1, libssl3 | libssl1.1, libhwloc15 | libhwloc5
|
||||||
|
Maintainer: XXXig Team <noreply@example.com>
|
||||||
|
Homepage: https://github.com/wangdefaa/xxxig
|
||||||
|
Description: Cryptocurrency mining software suite
|
||||||
|
XXXig is a customized build of XMRig,
|
||||||
|
a cryptocurrency mining software with centralized management.
|
||||||
|
.
|
||||||
|
This package includes:
|
||||||
|
- xxxigServer: Central control server with web UI
|
||||||
|
- xxxigDaemon: Client daemon that connects to the server
|
||||||
|
- xxxig: Mining executable controlled by the daemon
|
||||||
|
- Systemd service configurations
|
||||||
|
- Default configuration files
|
||||||
+73
@@ -0,0 +1,73 @@
|
|||||||
|
#!/bin/sh
|
||||||
|
set -e
|
||||||
|
|
||||||
|
# Create user and group if they don't exist
|
||||||
|
if ! getent group xxxig >/dev/null; then
|
||||||
|
addgroup --system xxxig
|
||||||
|
fi
|
||||||
|
|
||||||
|
if ! getent passwd xxxig >/dev/null; then
|
||||||
|
adduser --system --ingroup xxxig --no-create-home \
|
||||||
|
--home /opt/xxxig --shell /usr/sbin/nologin \
|
||||||
|
--gecos "XXXig Service" xxxig
|
||||||
|
fi
|
||||||
|
|
||||||
|
# Create log directory
|
||||||
|
mkdir -p /var/log/xxxig
|
||||||
|
chown xxxig:xxxig /var/log/xxxig
|
||||||
|
chmod 750 /var/log/xxxig
|
||||||
|
|
||||||
|
# Create config directory
|
||||||
|
mkdir -p /etc/xxxig
|
||||||
|
|
||||||
|
# Copy default configs if they don't exist
|
||||||
|
if [ ! -f /etc/xxxig/config.json ]; then
|
||||||
|
cp /opt/xxxig/config.json /etc/xxxig/config.json
|
||||||
|
chown xxxig:xxxig /etc/xxxig/config.json
|
||||||
|
chmod 640 /etc/xxxig/config.json
|
||||||
|
fi
|
||||||
|
|
||||||
|
if [ ! -f /etc/xxxig/config_cc.json ]; then
|
||||||
|
cp /opt/xxxig/config_cc.json /etc/xxxig/config_cc.json
|
||||||
|
chown xxxig:xxxig /etc/xxxig/config_cc.json
|
||||||
|
chmod 640 /etc/xxxig/config_cc.json
|
||||||
|
fi
|
||||||
|
|
||||||
|
# Set permissions
|
||||||
|
chown -R root:root /opt/xxxig
|
||||||
|
chmod -R 755 /opt/xxxig
|
||||||
|
|
||||||
|
# Reload systemd
|
||||||
|
if [ -d /run/systemd/system ]; then
|
||||||
|
systemctl daemon-reload
|
||||||
|
|
||||||
|
# 升级时重启正在运行的服务以加载新二进制;try-restart 不会启动未运行的服务,
|
||||||
|
# 故首次安装仍保持"不自动启动"语义
|
||||||
|
systemctl try-restart xxxig-daemon.service xxxig-server.service 2>/dev/null || true
|
||||||
|
|
||||||
|
# Note: Services are NOT auto-enabled or auto-started
|
||||||
|
# Users should manually enable the services they need:
|
||||||
|
# systemctl enable xxxig-server.service
|
||||||
|
# systemctl start xxxig-server.service
|
||||||
|
# or
|
||||||
|
# systemctl enable xxxig-daemon.service
|
||||||
|
# systemctl start xxxig-daemon.service
|
||||||
|
fi
|
||||||
|
|
||||||
|
echo ""
|
||||||
|
echo "✅ XXXig installed successfully!"
|
||||||
|
echo ""
|
||||||
|
echo "📁 Important paths:"
|
||||||
|
echo " Config files: /etc/xxxig/config.json (daemon)"
|
||||||
|
echo " /etc/xxxig/config_cc.json (server)"
|
||||||
|
echo " Log directory: /var/log/xxxig"
|
||||||
|
echo " Binaries: /opt/xxxig/xxxigServer (control server)"
|
||||||
|
echo " /opt/xxxig/xxxigDaemon (mining daemon)"
|
||||||
|
echo " /opt/xxxig/xxxig (miner executable)"
|
||||||
|
echo " Systemd services: xxxig-server.service (control server)"
|
||||||
|
echo " xxxig-daemon.service (mining daemon)"
|
||||||
|
echo ""
|
||||||
|
echo "💡 Tip: Your config files will NOT be overwritten during package upgrades."
|
||||||
|
echo ""
|
||||||
|
|
||||||
|
exit 0
|
||||||
+35
@@ -0,0 +1,35 @@
|
|||||||
|
#!/bin/sh
|
||||||
|
set -e
|
||||||
|
|
||||||
|
case "$1" in
|
||||||
|
purge)
|
||||||
|
# Remove user and group
|
||||||
|
if getent passwd xxxig >/dev/null; then
|
||||||
|
deluser --quiet xxxig || true
|
||||||
|
fi
|
||||||
|
|
||||||
|
if getent group xxxig >/dev/null; then
|
||||||
|
delgroup --quiet xxxig || true
|
||||||
|
fi
|
||||||
|
|
||||||
|
# Remove data directories (only on purge)
|
||||||
|
rm -rf /var/log/xxxig
|
||||||
|
rm -rf /etc/xxxig
|
||||||
|
;;
|
||||||
|
|
||||||
|
remove|upgrade|failed-upgrade|abort-install|abort-upgrade|disappear)
|
||||||
|
# Do nothing
|
||||||
|
;;
|
||||||
|
|
||||||
|
*)
|
||||||
|
echo "postrm called with unknown argument \`$1'" >&2
|
||||||
|
exit 1
|
||||||
|
;;
|
||||||
|
esac
|
||||||
|
|
||||||
|
# Reload systemd
|
||||||
|
if [ -d /run/systemd/system ]; then
|
||||||
|
systemctl daemon-reload
|
||||||
|
fi
|
||||||
|
|
||||||
|
exit 0
|
||||||
+19
@@ -0,0 +1,19 @@
|
|||||||
|
#!/bin/sh
|
||||||
|
set -e
|
||||||
|
|
||||||
|
# 仅在卸载(remove)时停用服务;升级(upgrade)时保持运行与开机自启状态
|
||||||
|
if [ "$1" = "remove" ] && [ -d /run/systemd/system ]; then
|
||||||
|
for service in xxxig-server.service xxxig-daemon.service; do
|
||||||
|
if systemctl is-active --quiet "$service"; then
|
||||||
|
echo "Stopping $service..."
|
||||||
|
systemctl stop "$service"
|
||||||
|
fi
|
||||||
|
|
||||||
|
if systemctl is-enabled --quiet "$service"; then
|
||||||
|
echo "Disabling $service..."
|
||||||
|
systemctl disable "$service"
|
||||||
|
fi
|
||||||
|
done
|
||||||
|
fi
|
||||||
|
|
||||||
|
exit 0
|
||||||
Vendored
+40
@@ -0,0 +1,40 @@
|
|||||||
|
[Unit]
|
||||||
|
Description=XXXig Daemon (Miner Client)
|
||||||
|
After=network.target
|
||||||
|
|
||||||
|
[Service]
|
||||||
|
Type=simple
|
||||||
|
|
||||||
|
# 工作目录
|
||||||
|
WorkingDirectory=/opt/xxxig
|
||||||
|
|
||||||
|
# 执行命令
|
||||||
|
ExecStart=/opt/xxxig/xxxigDaemon --config /etc/xxxig/config.json --log-file=/var/log/xxxig/daemon.log
|
||||||
|
|
||||||
|
# 重启策略
|
||||||
|
Restart=always
|
||||||
|
RestartSec=10
|
||||||
|
|
||||||
|
# 用户和组
|
||||||
|
User=xxxig
|
||||||
|
Group=xxxig
|
||||||
|
|
||||||
|
# 安全设置
|
||||||
|
NoNewPrivileges=true
|
||||||
|
PrivateTmp=true
|
||||||
|
ProtectSystem=strict
|
||||||
|
ProtectHome=true
|
||||||
|
ReadWritePaths=/var/log/xxxig
|
||||||
|
|
||||||
|
# 日志设置
|
||||||
|
StandardOutput=journal
|
||||||
|
StandardError=journal
|
||||||
|
SyslogIdentifier=xxxig-daemon
|
||||||
|
|
||||||
|
# 资源限制
|
||||||
|
LimitNOFILE=65535
|
||||||
|
LimitMEMLOCK=infinity
|
||||||
|
AmbientCapabilities=CAP_IPC_LOCK
|
||||||
|
|
||||||
|
[Install]
|
||||||
|
WantedBy=multi-user.target
|
||||||
Vendored
+38
@@ -0,0 +1,38 @@
|
|||||||
|
[Unit]
|
||||||
|
Description=XXXig Server (Control Center)
|
||||||
|
After=network.target
|
||||||
|
|
||||||
|
[Service]
|
||||||
|
Type=simple
|
||||||
|
|
||||||
|
# 工作目录
|
||||||
|
WorkingDirectory=/opt/xxxig
|
||||||
|
|
||||||
|
# 执行命令
|
||||||
|
ExecStart=/opt/xxxig/xxxigServer --config /etc/xxxig/config_cc.json --log-file=/var/log/xxxig/server.log
|
||||||
|
|
||||||
|
# 重启策略
|
||||||
|
Restart=always
|
||||||
|
RestartSec=10
|
||||||
|
|
||||||
|
# 用户和组
|
||||||
|
User=xxxig
|
||||||
|
Group=xxxig
|
||||||
|
|
||||||
|
# 安全设置
|
||||||
|
NoNewPrivileges=true
|
||||||
|
PrivateTmp=true
|
||||||
|
ProtectSystem=strict
|
||||||
|
ProtectHome=true
|
||||||
|
ReadWritePaths=/var/log/xxxig
|
||||||
|
|
||||||
|
# 日志设置
|
||||||
|
StandardOutput=journal
|
||||||
|
StandardError=journal
|
||||||
|
SyslogIdentifier=xxxig-server
|
||||||
|
|
||||||
|
# 资源限制
|
||||||
|
LimitNOFILE=65535
|
||||||
|
|
||||||
|
[Install]
|
||||||
|
WantedBy=multi-user.target
|
||||||
@@ -0,0 +1,86 @@
|
|||||||
|
FROM alpine:latest AS base
|
||||||
|
|
||||||
|
# 根据目标架构设置构建参数
|
||||||
|
ARG TARGETARCH
|
||||||
|
|
||||||
|
RUN apk update && apk add --no-cache \
|
||||||
|
git \
|
||||||
|
make \
|
||||||
|
cmake \
|
||||||
|
libstdc++ \
|
||||||
|
gcc \
|
||||||
|
g++ \
|
||||||
|
automake \
|
||||||
|
libtool \
|
||||||
|
autoconf \
|
||||||
|
linux-headers \
|
||||||
|
libuv-dev \
|
||||||
|
openssl-dev \
|
||||||
|
hwloc-dev
|
||||||
|
|
||||||
|
FROM base AS build
|
||||||
|
|
||||||
|
ARG TARGZ_FILE
|
||||||
|
ARG XXXIG_VERSION
|
||||||
|
ARG TARGETARCH
|
||||||
|
ARG BUILDPLATFORM
|
||||||
|
ARG TARGETPLATFORM
|
||||||
|
|
||||||
|
RUN git clone --recursive https://github.com/wangdefaa/xxxig.git && \
|
||||||
|
cd xxxig && \
|
||||||
|
git checkout ${XXXIG_VERSION}
|
||||||
|
|
||||||
|
WORKDIR /xxxig
|
||||||
|
|
||||||
|
|
||||||
|
# 根据目标架构优化编译
|
||||||
|
RUN mkdir build && cd scripts && chmod +x ./*.sh && \
|
||||||
|
if [ "$BUILDPLATFORM" != "$TARGETPLATFORM" ]; then \
|
||||||
|
MAKE_JOBS="-j2"; \
|
||||||
|
else \
|
||||||
|
MAKE_JOBS="-j$(nproc)"; \
|
||||||
|
fi && \
|
||||||
|
echo "Building with parallel jobs: $MAKE_JOBS (cross-compile: $([ "$BUILDPLATFORM" != "$TARGETPLATFORM" ] && echo yes || echo no))" && \
|
||||||
|
./build_deps.sh $MAKE_JOBS && cd ../build && \
|
||||||
|
if [ "$TARGETARCH" = "arm64" ]; then \
|
||||||
|
cmake .. -DWITH_CC_CLIENT=ON \
|
||||||
|
-DWITH_CC_SERVER=ON \
|
||||||
|
-DCMAKE_BUILD_TYPE=Release \
|
||||||
|
-DXMRIG_DEPS=scripts/deps \
|
||||||
|
-DBUILD_STATIC=ON \
|
||||||
|
-DWITH_ZLIB=ON \
|
||||||
|
-DWITH_OPENCL=OFF \
|
||||||
|
-DWITH_CUDA=OFF \
|
||||||
|
-DARM_TARGET=8; \
|
||||||
|
elif [ "$TARGETARCH" = "arm" ]; then \
|
||||||
|
cmake .. -DWITH_CC_CLIENT=ON \
|
||||||
|
-DWITH_CC_SERVER=ON \
|
||||||
|
-DCMAKE_BUILD_TYPE=Release \
|
||||||
|
-DXMRIG_DEPS=scripts/deps \
|
||||||
|
-DBUILD_STATIC=ON \
|
||||||
|
-DWITH_ZLIB=ON \
|
||||||
|
-DWITH_OPENCL=OFF \
|
||||||
|
-DWITH_CUDA=OFF \
|
||||||
|
-DARM_TARGET=7; \
|
||||||
|
else \
|
||||||
|
cmake .. -DWITH_CC_CLIENT=ON \
|
||||||
|
-DWITH_CC_SERVER=ON \
|
||||||
|
-DCMAKE_BUILD_TYPE=Release \
|
||||||
|
-DXMRIG_DEPS=scripts/deps \
|
||||||
|
-DBUILD_STATIC=ON \
|
||||||
|
-DWITH_ZLIB=ON \
|
||||||
|
-DWITH_OPENCL=OFF \
|
||||||
|
-DWITH_CUDA=OFF; \
|
||||||
|
fi && \
|
||||||
|
make $MAKE_JOBS
|
||||||
|
|
||||||
|
FROM scratch
|
||||||
|
|
||||||
|
ARG TARGETARCH
|
||||||
|
|
||||||
|
COPY --from=build /xxxig/build/xxxigDaemon /linux_${TARGETARCH}/xxxigDaemon
|
||||||
|
COPY --from=build /xxxig/build/xxxig /linux_${TARGETARCH}/xxxig
|
||||||
|
COPY --from=build /xxxig/build/xxxigServer /linux_${TARGETARCH}/xxxigServer
|
||||||
|
COPY --from=build /xxxig/src/config_cc.json /linux_${TARGETARCH}/config_cc.json
|
||||||
|
COPY --from=build /xxxig/src/config.json /linux_${TARGETARCH}/config.json
|
||||||
|
COPY --from=build /xxxig/index.html /linux_${TARGETARCH}/index.html
|
||||||
@@ -0,0 +1,86 @@
|
|||||||
|
FROM ubuntu:20.04 AS base
|
||||||
|
|
||||||
|
ARG TARGETARCH
|
||||||
|
ARG BUILDPLATFORM
|
||||||
|
|
||||||
|
ENV DEBIAN_FRONTEND=noninteractive
|
||||||
|
|
||||||
|
# 根据目标架构安装相应的交叉编译工具链
|
||||||
|
RUN apt-get update && apt-get install -y \
|
||||||
|
git \
|
||||||
|
wget \
|
||||||
|
build-essential \
|
||||||
|
cmake \
|
||||||
|
libuv1-dev \
|
||||||
|
libssl-dev \
|
||||||
|
libhwloc-dev \
|
||||||
|
&& if [ "$TARGETARCH" = "arm64" ] && [ "$BUILDPLATFORM" != "linux/arm64" ]; then \
|
||||||
|
apt-get install -y gcc-aarch64-linux-gnu g++-aarch64-linux-gnu; \
|
||||||
|
elif [ "$TARGETARCH" = "arm" ] && [ "$BUILDPLATFORM" != "linux/arm/v7" ]; then \
|
||||||
|
apt-get install -y gcc-arm-linux-gnueabihf g++-arm-linux-gnueabihf; \
|
||||||
|
fi \
|
||||||
|
&& rm -rf /var/lib/apt/lists/*
|
||||||
|
|
||||||
|
FROM base AS build
|
||||||
|
|
||||||
|
ARG TARGZ_FILE
|
||||||
|
ARG TARGET_ARCH
|
||||||
|
ARG XXXIG_VERSION
|
||||||
|
ARG TARGETARCH
|
||||||
|
ARG BUILDPLATFORM
|
||||||
|
ARG TARGETPLATFORM
|
||||||
|
|
||||||
|
RUN git clone --recursive https://github.com/wangdefaa/xxxig.git && \
|
||||||
|
cd xxxig && \
|
||||||
|
git checkout ${XXXIG_VERSION}
|
||||||
|
|
||||||
|
WORKDIR /xxxig
|
||||||
|
|
||||||
|
# 根据目标架构设置编译环境和参数
|
||||||
|
RUN mkdir build && cd scripts && chmod +x ./*.sh && \
|
||||||
|
if [ "$BUILDPLATFORM" != "$TARGETPLATFORM" ]; then \
|
||||||
|
MAKE_JOBS="-j2"; \
|
||||||
|
else \
|
||||||
|
MAKE_JOBS="-j$(nproc)"; \
|
||||||
|
fi && \
|
||||||
|
echo "Building with parallel jobs: $MAKE_JOBS (cross-compile: $([ "$BUILDPLATFORM" != "$TARGETPLATFORM" ] && echo yes || echo no))" && \
|
||||||
|
./build_deps.sh $MAKE_JOBS && cd ../build && \
|
||||||
|
if [ "$TARGETARCH" = "arm64" ] && [ "$BUILDPLATFORM" != "linux/arm64" ]; then \
|
||||||
|
export CC=aarch64-linux-gnu-gcc CXX=aarch64-linux-gnu-g++; \
|
||||||
|
cmake .. -DWITH_CC_CLIENT=ON \
|
||||||
|
-DWITH_CC_SERVER=ON \
|
||||||
|
-DCMAKE_BUILD_TYPE=Release \
|
||||||
|
-DCMAKE_C_COMPILER=aarch64-linux-gnu-gcc \
|
||||||
|
-DCMAKE_CXX_COMPILER=aarch64-linux-gnu-g++ \
|
||||||
|
-DARM_TARGET=8 \
|
||||||
|
-DXMRIG_DEPS=scripts/deps \
|
||||||
|
-DWITH_ZLIB=ON; \
|
||||||
|
elif [ "$TARGETARCH" = "arm" ] && [ "$BUILDPLATFORM" != "linux/arm/v7" ]; then \
|
||||||
|
export CC=arm-linux-gnueabihf-gcc CXX=arm-linux-gnueabihf-g++; \
|
||||||
|
cmake .. -DWITH_CC_CLIENT=ON \
|
||||||
|
-DWITH_CC_SERVER=ON \
|
||||||
|
-DCMAKE_BUILD_TYPE=Release \
|
||||||
|
-DCMAKE_C_COMPILER=arm-linux-gnueabihf-gcc \
|
||||||
|
-DCMAKE_CXX_COMPILER=arm-linux-gnueabihf-g++ \
|
||||||
|
-DARM_TARGET=7 \
|
||||||
|
-DXMRIG_DEPS=scripts/deps \
|
||||||
|
-DWITH_ZLIB=ON; \
|
||||||
|
else \
|
||||||
|
cmake .. -DWITH_CC_CLIENT=ON \
|
||||||
|
-DWITH_CC_SERVER=ON \
|
||||||
|
-DCMAKE_BUILD_TYPE=Release \
|
||||||
|
-DXMRIG_DEPS=scripts/deps \
|
||||||
|
-DWITH_ZLIB=ON; \
|
||||||
|
fi && \
|
||||||
|
make $MAKE_JOBS
|
||||||
|
|
||||||
|
FROM scratch
|
||||||
|
|
||||||
|
ARG TARGETARCH
|
||||||
|
|
||||||
|
COPY --from=build /xxxig/build/xxxigDaemon /linux_${TARGETARCH}/xxxigDaemon
|
||||||
|
COPY --from=build /xxxig/build/xxxig /linux_${TARGETARCH}/xxxig
|
||||||
|
COPY --from=build /xxxig/build/xxxigServer /linux_${TARGETARCH}/xxxigServer
|
||||||
|
COPY --from=build /xxxig/src/config_cc.json /linux_${TARGETARCH}/config_cc.json
|
||||||
|
COPY --from=build /xxxig/src/config.json /linux_${TARGETARCH}/config.json
|
||||||
|
COPY --from=build /xxxig/index.html /linux_${TARGETARCH}/index.html
|
||||||
@@ -0,0 +1,255 @@
|
|||||||
|
# XXXig 安装脚本
|
||||||
|
|
||||||
|
本目录包含 XXXig 的安装和卸载脚本。
|
||||||
|
|
||||||
|
## 脚本列表
|
||||||
|
|
||||||
|
### 1. install.sh - 通用安装脚本
|
||||||
|
从 Gitea Generic Package Registry 下载 tar.gz 包并安装。
|
||||||
|
|
||||||
|
**支持系统:**
|
||||||
|
- Alpine Linux (OpenRC)
|
||||||
|
- Ubuntu/Debian (systemd)
|
||||||
|
|
||||||
|
**使用方法:**
|
||||||
|
```bash
|
||||||
|
# 基本安装
|
||||||
|
sudo ./install.sh -o pool.example.com:3333 -w YOUR_WALLET_ADDRESS
|
||||||
|
|
||||||
|
# 指定版本和线程数
|
||||||
|
sudo ./install.sh -v 6.26.0 -t 4 -o pool.example.com:3333 -w YOUR_WALLET
|
||||||
|
|
||||||
|
# 启用高级功能
|
||||||
|
sudo ./install.sh -o pool.example.com:3333 -w YOUR_WALLET \
|
||||||
|
--1gb-pages --tls --keepalive \
|
||||||
|
--cc --cc-url http://server:3344 --cc-token YOUR_TOKEN
|
||||||
|
```
|
||||||
|
|
||||||
|
### 2. install.deb.sh - DEB 包安装脚本
|
||||||
|
通过 APT 仓库直接安装。
|
||||||
|
|
||||||
|
**支持系统:**
|
||||||
|
- Ubuntu/Debian (systemd)
|
||||||
|
|
||||||
|
**使用方法:**
|
||||||
|
```bash
|
||||||
|
# 基本安装
|
||||||
|
sudo ./install.deb.sh -o pool.example.com:3333 -w YOUR_WALLET_ADDRESS
|
||||||
|
|
||||||
|
# 指定版本
|
||||||
|
sudo ./install.deb.sh -v 6.26.0 -o pool.example.com:3333 -w YOUR_WALLET
|
||||||
|
|
||||||
|
# 查看可用版本
|
||||||
|
apt-cache policy xxxig
|
||||||
|
```
|
||||||
|
|
||||||
|
### 3. uninstall.sh - 卸载脚本
|
||||||
|
通用卸载脚本,自动检测安装方式。
|
||||||
|
|
||||||
|
**使用方法:**
|
||||||
|
```bash
|
||||||
|
# 交互式卸载(推荐)
|
||||||
|
sudo ./uninstall.sh
|
||||||
|
|
||||||
|
# 直接卸载,不确认
|
||||||
|
sudo ./uninstall.sh -y
|
||||||
|
|
||||||
|
# 完全清除(包括配置文件和日志)
|
||||||
|
sudo ./uninstall.sh --purge -y
|
||||||
|
```
|
||||||
|
|
||||||
|
## 命令行参数
|
||||||
|
|
||||||
|
### 通用参数(两种安装脚本都支持)
|
||||||
|
|
||||||
|
| 参数 | 说明 | 默认值 |
|
||||||
|
|------|------|--------|
|
||||||
|
| `-v, --version` | 版本号 | latest |
|
||||||
|
| `-t, --threads` | 线程数 | 自动 (CPU 核心数) |
|
||||||
|
| `-a, --algo` | 算法 | rx/0 |
|
||||||
|
| `-o, --pool` | 矿池地址 | **必需** |
|
||||||
|
| `-w, --wallet` | 钱包地址 | 自动生成 |
|
||||||
|
| `-p, --password` | 矿池密码 | 自动生成 |
|
||||||
|
| `--1gb-pages` | 启用 1GB 大页 | false |
|
||||||
|
| `--tls` | 启用 TLS | false |
|
||||||
|
| `--keepalive` | 启用 KeepAlive | false |
|
||||||
|
| `--daemon` | 启用 SOLO 挖矿 | false |
|
||||||
|
| `--nicehash` | 启用 NiceHash 模式 | **true** |
|
||||||
|
| `--verbose` | 启用详细输出 | **true** |
|
||||||
|
| `--submit-to-origin` | 提交到原始矿池 | false |
|
||||||
|
| `--self-select` | 自选矿池地址 | - |
|
||||||
|
| `--cc` | 启用 CC | false |
|
||||||
|
| `--cc-url` | CC 服务器地址 | - |
|
||||||
|
| `--cc-work-id` | CC 工作 ID | 自动生成 |
|
||||||
|
| `--cc-token` | CC 访问令牌 | - |
|
||||||
|
| `--cc-tls` | 启用 CC TLS | false |
|
||||||
|
|
||||||
|
## 安装路径
|
||||||
|
|
||||||
|
### tar.gz 安装
|
||||||
|
```
|
||||||
|
/etc/miner/xxxig/
|
||||||
|
├── config.json # 配置文件
|
||||||
|
├── xxxigDaemon # 守护进程
|
||||||
|
├── xxxig # 挖矿程序
|
||||||
|
└── xxxig.log # 日志文件
|
||||||
|
```
|
||||||
|
|
||||||
|
**服务文件:**
|
||||||
|
- Alpine: `/etc/init.d/xxxig`
|
||||||
|
- Ubuntu/Debian: `/etc/systemd/system/xxxig.service`
|
||||||
|
|
||||||
|
### DEB 包安装
|
||||||
|
```
|
||||||
|
/etc/xxxig/
|
||||||
|
└── config.json # 配置文件
|
||||||
|
|
||||||
|
/var/log/xxxig/ # 日志目录
|
||||||
|
|
||||||
|
/opt/xxxig/
|
||||||
|
├── xxxigDaemon # 守护进程
|
||||||
|
├── xxxig # 挖矿程序
|
||||||
|
└── xxxigServer # 控制服务器
|
||||||
|
```
|
||||||
|
|
||||||
|
**服务文件:**
|
||||||
|
- `/etc/systemd/system/xxxig-daemon.service`
|
||||||
|
- `/etc/systemd/system/xxxig-server.service`
|
||||||
|
|
||||||
|
## 服务管理
|
||||||
|
|
||||||
|
### Alpine Linux
|
||||||
|
```bash
|
||||||
|
# 查看状态
|
||||||
|
rc-service xxxig status
|
||||||
|
|
||||||
|
# 启动/停止/重启
|
||||||
|
rc-service xxxig start
|
||||||
|
rc-service xxxig stop
|
||||||
|
rc-service xxxig restart
|
||||||
|
|
||||||
|
# 查看日志
|
||||||
|
tail -f /etc/miner/xxxig/xxxig.log
|
||||||
|
```
|
||||||
|
|
||||||
|
### Ubuntu/Debian
|
||||||
|
|
||||||
|
#### tar.gz 安装
|
||||||
|
```bash
|
||||||
|
# 查看状态
|
||||||
|
systemctl status xxxig
|
||||||
|
|
||||||
|
# 启动/停止/重启
|
||||||
|
systemctl start xxxig
|
||||||
|
systemctl stop xxxig
|
||||||
|
systemctl restart xxxig
|
||||||
|
|
||||||
|
# 查看日志
|
||||||
|
journalctl -u xxxig -f
|
||||||
|
```
|
||||||
|
|
||||||
|
#### DEB 包安装
|
||||||
|
```bash
|
||||||
|
# 查看状态
|
||||||
|
systemctl status xxxig-daemon
|
||||||
|
|
||||||
|
# 启动/停止/重启
|
||||||
|
systemctl start xxxig-daemon
|
||||||
|
systemctl stop xxxig-daemon
|
||||||
|
systemctl restart xxxig-daemon
|
||||||
|
|
||||||
|
# 查看日志
|
||||||
|
journalctl -u xxxig-daemon -f
|
||||||
|
```
|
||||||
|
|
||||||
|
## 配置文件
|
||||||
|
|
||||||
|
配置文件为 JSON 格式,位于:
|
||||||
|
- tar.gz: `/etc/miner/xxxig/config.json`
|
||||||
|
- DEB: `/etc/xxxig/config.json`
|
||||||
|
|
||||||
|
修改配置后需要重启服务:
|
||||||
|
```bash
|
||||||
|
# Alpine
|
||||||
|
rc-service xxxig restart
|
||||||
|
|
||||||
|
# Ubuntu/Debian (tar.gz)
|
||||||
|
systemctl restart xxxig
|
||||||
|
|
||||||
|
# Ubuntu/Debian (DEB)
|
||||||
|
systemctl restart xxxig-daemon
|
||||||
|
```
|
||||||
|
|
||||||
|
## 升级版本
|
||||||
|
|
||||||
|
### tar.gz 安装
|
||||||
|
重新运行安装脚本,指定新版本:
|
||||||
|
```bash
|
||||||
|
sudo ./install.sh -v 6.26.0 -o pool.example.com:3333 -w YOUR_WALLET
|
||||||
|
```
|
||||||
|
|
||||||
|
### DEB 包安装
|
||||||
|
使用 APT 升级:
|
||||||
|
```bash
|
||||||
|
sudo apt-get update
|
||||||
|
sudo apt-get install xxxig
|
||||||
|
```
|
||||||
|
|
||||||
|
## 故障排查
|
||||||
|
|
||||||
|
### 检查服务状态
|
||||||
|
```bash
|
||||||
|
# Alpine
|
||||||
|
rc-service xxxig status
|
||||||
|
|
||||||
|
# Ubuntu/Debian
|
||||||
|
systemctl status xxxig # 或 xxxig-daemon
|
||||||
|
```
|
||||||
|
|
||||||
|
### 查看日志
|
||||||
|
```bash
|
||||||
|
# Alpine / tar.gz
|
||||||
|
tail -f /etc/miner/xxxig/xxxig.log
|
||||||
|
|
||||||
|
# Ubuntu/Debian (tar.gz)
|
||||||
|
journalctl -u xxxig -f
|
||||||
|
|
||||||
|
# Ubuntu/Debian (DEB)
|
||||||
|
journalctl -u xxxig-daemon -f
|
||||||
|
```
|
||||||
|
|
||||||
|
### 手动测试
|
||||||
|
```bash
|
||||||
|
# tar.gz 安装
|
||||||
|
/etc/miner/xxxig/xxxigDaemon -c /etc/miner/xxxig/config.json
|
||||||
|
|
||||||
|
# DEB 包安装
|
||||||
|
xxxigDaemon -c /etc/xxxig/config.json
|
||||||
|
```
|
||||||
|
|
||||||
|
### 常见问题
|
||||||
|
|
||||||
|
**问题: 下载失败**
|
||||||
|
```bash
|
||||||
|
# 检查网络连接
|
||||||
|
curl -I https://gitea.bcde.io
|
||||||
|
|
||||||
|
# 手动下载测试
|
||||||
|
curl -O https://gitea.bcde.io/api/packages/wangdefa/generic/xxxig/6.26.0/xxxig-amd64-ubuntu-6.26.0.tar.gz
|
||||||
|
```
|
||||||
|
|
||||||
|
**问题: 服务无法启动**
|
||||||
|
```bash
|
||||||
|
# 检查配置文件
|
||||||
|
cat /etc/miner/xxxig/config.json | jq .
|
||||||
|
|
||||||
|
# 检查权限
|
||||||
|
ls -la /etc/miner/xxxig/
|
||||||
|
```
|
||||||
|
|
||||||
|
**问题: APT 更新失败 (DEB)**
|
||||||
|
```bash
|
||||||
|
# 清理并重新添加源
|
||||||
|
sudo rm /etc/apt/sources.list.d/xxxig.list
|
||||||
|
sudo ./install_deb.sh -o pool.example.com:3333 -w YOUR_WALLET
|
||||||
|
```
|
||||||
Executable
+285
@@ -0,0 +1,285 @@
|
|||||||
|
#!/bin/bash
|
||||||
|
#
|
||||||
|
# XXXigCC 安装脚本 - DEB 版本
|
||||||
|
# 通过 APT 从 Gitea Generic Package Registry 安装 XXXigCC
|
||||||
|
#
|
||||||
|
|
||||||
|
set -e
|
||||||
|
|
||||||
|
declare -r BLUE="\033[0;34m"
|
||||||
|
declare -r RED="\033[0;31m"
|
||||||
|
declare -r GREEN="\033[0;32m"
|
||||||
|
declare -r YELLOW="\033[0;33m"
|
||||||
|
declare -r RESET="\033[0m"
|
||||||
|
|
||||||
|
# 基本配置
|
||||||
|
CONFIG_DIR="/etc/xxxig"
|
||||||
|
LOG_DIR="/var/log/xxxig"
|
||||||
|
CONFIG_FILE="$CONFIG_DIR/config.json"
|
||||||
|
|
||||||
|
# Gitea 配置
|
||||||
|
GITEA_SERVER="gitea.bcde.io"
|
||||||
|
GITEA_OWNER="wangdefa"
|
||||||
|
|
||||||
|
# 默认参数
|
||||||
|
DEFAULT_VERSION="latest"
|
||||||
|
DEFAULT_THREADS=0
|
||||||
|
DEFAULT_POOL_ALGO="rx/0"
|
||||||
|
DEFAULT_POOL_TLS="false"
|
||||||
|
DEFAULT_POOL_KEEPALIVE="false"
|
||||||
|
DEFAULT_POOL_DAEMON="false"
|
||||||
|
DEFAULT_POOL_SUBMIT_TO_ORIGIN="false"
|
||||||
|
DEFAULT_POOL_NICEHASH="true"
|
||||||
|
DEFAULT_ONE_GB_PAGES="false"
|
||||||
|
DEFAULT_VERBOSE="true"
|
||||||
|
DEFAULT_CC_ENABLED="false"
|
||||||
|
DEFAULT_CC_TLS="false"
|
||||||
|
|
||||||
|
# 辅助函数
|
||||||
|
log() { echo -e "${1}${2}${RESET}"; }
|
||||||
|
error() { log "$RED" "错误: $1"; exit 1; }
|
||||||
|
|
||||||
|
check_os() {
|
||||||
|
grep -qiE 'debian|ubuntu' /etc/os-release || error "仅支持 Debian/Ubuntu 系统"
|
||||||
|
}
|
||||||
|
|
||||||
|
get_arch() {
|
||||||
|
case $(uname -m) in
|
||||||
|
x86_64) echo "amd64" ;;
|
||||||
|
aarch64) echo "arm64" ;;
|
||||||
|
*) error "不支持的架构: $(uname -m)" ;;
|
||||||
|
esac
|
||||||
|
}
|
||||||
|
|
||||||
|
# 添加 APT 源并更新
|
||||||
|
add_apt_repository() {
|
||||||
|
curl https://${GITEA_SERVER}/api/packages/${GITEA_OWNER}/debian/repository.key -o /etc/apt/keyrings/gitea-${GITEA_OWNER}.asc
|
||||||
|
echo "deb [signed-by=/etc/apt/keyrings/gitea-${GITEA_OWNER}.asc] https://${GITEA_SERVER}/api/packages/${GITEA_OWNER}/debian stable main" \
|
||||||
|
>/etc/apt/sources.list.d/${GITEA_OWNER}.list
|
||||||
|
apt-get update -qq
|
||||||
|
}
|
||||||
|
|
||||||
|
# 卸载旧版本
|
||||||
|
uninstall_xxxig() {
|
||||||
|
systemctl stop xxxig-daemon xxxig-server 2>/dev/null || true
|
||||||
|
systemctl disable xxxig-daemon xxxig-server 2>/dev/null || true
|
||||||
|
apt-get remove -y xxxig 2>/dev/null || true
|
||||||
|
rm -rf "$CONFIG_DIR" "$LOG_DIR" /etc/apt/sources.list.d/xxxig.list
|
||||||
|
systemctl daemon-reload 2>/dev/null || true
|
||||||
|
}
|
||||||
|
|
||||||
|
# 安装并启动服务
|
||||||
|
install_and_start() {
|
||||||
|
log "$BLUE" "安装 XXXig $version..."
|
||||||
|
if [[ "$version" == "latest" ]]; then
|
||||||
|
apt-get install -y xxxig
|
||||||
|
else
|
||||||
|
apt-get install -y xxxig="${version#v}"
|
||||||
|
fi
|
||||||
|
|
||||||
|
log "$BLUE" "启动服务..."
|
||||||
|
systemctl daemon-reload
|
||||||
|
systemctl enable --now xxxig-daemon.service
|
||||||
|
log "$GREEN" "安装完成"
|
||||||
|
}
|
||||||
|
|
||||||
|
# 配置 CPU 亲和性
|
||||||
|
configure_cpu_rx() {
|
||||||
|
local cpu_cores=$(nproc)
|
||||||
|
local rx_array="" step=1
|
||||||
|
|
||||||
|
[[ "$threads" -le $((cpu_cores / 2)) ]] && step=2
|
||||||
|
|
||||||
|
for ((i = 0; i < threads; i++)); do
|
||||||
|
[[ $i -gt 0 ]] && rx_array+=", "
|
||||||
|
rx_array+="$((i * step))"
|
||||||
|
done
|
||||||
|
|
||||||
|
local field="rx"
|
||||||
|
[[ "$pool_algo" == "panthera" ]] && field="panthera"
|
||||||
|
|
||||||
|
jq ".cpu.$field = [ $rx_array ]" "$CONFIG_FILE" >"$CONFIG_FILE.tmp" && mv "$CONFIG_FILE.tmp" "$CONFIG_FILE"
|
||||||
|
}
|
||||||
|
|
||||||
|
# 配置大页内存
|
||||||
|
configure_hugepages() {
|
||||||
|
if [[ "$one_gb_pages" == "true" ]]; then
|
||||||
|
log "$BLUE" "配置 大页内存..."
|
||||||
|
sysctl -w vm.nr_hugepages=3072
|
||||||
|
echo "vm.nr_hugepages=3072" >>/etc/sysctl.conf
|
||||||
|
log "$GREEN" "大页内存配置完成"
|
||||||
|
fi
|
||||||
|
}
|
||||||
|
|
||||||
|
# 更新配置文件
|
||||||
|
replace_config() {
|
||||||
|
[[ ! -f "$CONFIG_FILE" ]] && error "配置文件缺失"
|
||||||
|
|
||||||
|
local jq_cmd=".\"log-file\" = \"\"
|
||||||
|
| .\"donate-level\" = 0
|
||||||
|
| .\"donate-over-proxy\" = 0
|
||||||
|
| .pools[0].algo = \"$pool_algo\"
|
||||||
|
| .pools[0].url = \"$pool_address\"
|
||||||
|
| .pools[0].user = \"$wallet_address\"
|
||||||
|
| .pools[0].pass = \"$pool_password\"
|
||||||
|
| .pools[0].tls = $pool_tls
|
||||||
|
| .pools[0].nicehash = $pool_nicehash
|
||||||
|
| .\"verbose\" = $verbose"
|
||||||
|
|
||||||
|
[[ "$one_gb_pages" == "true" ]] && jq_cmd+=" | .randomx.\"1gb-pages\" = true"
|
||||||
|
[[ "$pool_keepalive" == "true" ]] && jq_cmd+=" | .pools[0].keepalive = true"
|
||||||
|
[[ -n "$pool_tls_fingerprint" ]] && jq_cmd+=" | .pools[0].\"tls-fingerprint\" = \"$pool_tls_fingerprint\""
|
||||||
|
[[ "$pool_daemon" == "true" ]] && jq_cmd+=" | .pools[0].daemon = true"
|
||||||
|
|
||||||
|
if [[ "$pool_submit_to_origin" == "true" ]]; then
|
||||||
|
jq_cmd+=" | .pools[0].\"submit-to-origin\" = true | .pools[0].\"self-select\" = \"$pool_self_select\""
|
||||||
|
fi
|
||||||
|
|
||||||
|
if [[ "$cc_enabled" == "true" ]]; then
|
||||||
|
jq_cmd+=" | .\"cc-client\".enabled = true
|
||||||
|
| .\"cc-client\".servers[0].url = \"$cc_url\"
|
||||||
|
| .\"cc-client\".servers[0].\"access-token\" = \"$cc_token\"
|
||||||
|
| .\"cc-client\".servers[0].\"use-tls\" = $cc_tls
|
||||||
|
| .\"cc-client\".\"worker-id\" = \"$cc_work_id\""
|
||||||
|
else
|
||||||
|
jq_cmd+=" | .\"cc-client\".enabled = false"
|
||||||
|
fi
|
||||||
|
|
||||||
|
jq "$jq_cmd" "$CONFIG_FILE" >"$CONFIG_FILE.tmp" && mv "$CONFIG_FILE.tmp" "$CONFIG_FILE"
|
||||||
|
configure_cpu_rx
|
||||||
|
configure_hugepages
|
||||||
|
}
|
||||||
|
|
||||||
|
show_usage() {
|
||||||
|
cat <<EOF
|
||||||
|
用法: $0 [选项]
|
||||||
|
|
||||||
|
选项:
|
||||||
|
-v, --version <版本> XXXig 版本 (默认: $DEFAULT_VERSION)
|
||||||
|
-t, --threads <数字> 线程数 (默认: 自动)
|
||||||
|
-a, --algo <算法> 矿池算法 (默认: $DEFAULT_POOL_ALGO)
|
||||||
|
-o, --pool <地址> 矿池地址 (必需)
|
||||||
|
-w, --wallet <地址> 钱包地址
|
||||||
|
-p, --password <密码> 矿池密码 (默认自动生成)
|
||||||
|
--1gb-pages 启用 1GB 大页
|
||||||
|
--tls 启用 TLS
|
||||||
|
--keepalive 启用 KeepAlive
|
||||||
|
--daemon 启用 SOLO 挖矿
|
||||||
|
--nicehash 启用 NiceHash 模式 (默认: 启用)
|
||||||
|
--submit-to-origin 提交到原始矿池
|
||||||
|
--self-select <地址> 自选矿池地址
|
||||||
|
--verbose 启用详细输出 (默认: 启用)
|
||||||
|
--cc 启用 CC
|
||||||
|
--cc-url <地址> CC 服务器地址
|
||||||
|
--cc-work-id <ID> CC 工作 ID
|
||||||
|
--cc-token <令牌> CC 访问令牌
|
||||||
|
--cc-tls 启用 CC TLS
|
||||||
|
-h, --help 显示帮助信息
|
||||||
|
|
||||||
|
示例:
|
||||||
|
$0 -o pool.example.com:3333 -w YOUR_WALLET_ADDRESS
|
||||||
|
EOF
|
||||||
|
exit 1
|
||||||
|
}
|
||||||
|
|
||||||
|
parse_args() {
|
||||||
|
version=$DEFAULT_VERSION
|
||||||
|
threads=$DEFAULT_THREADS
|
||||||
|
pool_algo=$DEFAULT_POOL_ALGO
|
||||||
|
pool_tls=$DEFAULT_POOL_TLS
|
||||||
|
pool_keepalive=$DEFAULT_POOL_KEEPALIVE
|
||||||
|
pool_submit_to_origin=$DEFAULT_POOL_SUBMIT_TO_ORIGIN
|
||||||
|
pool_daemon=$DEFAULT_POOL_DAEMON
|
||||||
|
pool_nicehash=$DEFAULT_POOL_NICEHASH
|
||||||
|
pool_self_select=""
|
||||||
|
pool_address=""
|
||||||
|
wallet_address=""
|
||||||
|
pool_password=""
|
||||||
|
pool_tls_fingerprint=""
|
||||||
|
verbose=$DEFAULT_VERBOSE
|
||||||
|
cc_enabled=$DEFAULT_CC_ENABLED
|
||||||
|
cc_url=""
|
||||||
|
cc_work_id=""
|
||||||
|
cc_token=""
|
||||||
|
cc_tls=$DEFAULT_CC_TLS
|
||||||
|
one_gb_pages=$DEFAULT_ONE_GB_PAGES
|
||||||
|
|
||||||
|
while [[ $# -gt 0 ]]; do
|
||||||
|
case "$1" in
|
||||||
|
-v | --version) version="$2"; shift 2 ;;
|
||||||
|
-t | --threads) threads="$2"; shift 2 ;;
|
||||||
|
-a | --algo) pool_algo="$2"; shift 2 ;;
|
||||||
|
-o | --pool) pool_address="$2"; shift 2 ;;
|
||||||
|
-w | --wallet) wallet_address="$2"; shift 2 ;;
|
||||||
|
-p | --password) pool_password="$2"; shift 2 ;;
|
||||||
|
--1gb-pages) one_gb_pages="true"; shift ;;
|
||||||
|
--cc-url) cc_url="$2"; shift 2 ;;
|
||||||
|
--cc-work-id) cc_work_id="$2"; shift 2 ;;
|
||||||
|
--cc-token) cc_token="$2"; shift 2 ;;
|
||||||
|
--tls-fingerprint) pool_tls_fingerprint="$2"; shift 2 ;;
|
||||||
|
--tls) pool_tls="true"; shift ;;
|
||||||
|
--keepalive) pool_keepalive="true"; shift ;;
|
||||||
|
--daemon) pool_daemon="true"; shift ;;
|
||||||
|
--nicehash) pool_nicehash="true"; shift ;;
|
||||||
|
--submit-to-origin) pool_submit_to_origin="true"; shift ;;
|
||||||
|
--self-select) pool_self_select="$2"; shift 2 ;;
|
||||||
|
--verbose) verbose="true"; shift ;;
|
||||||
|
--cc) cc_enabled="true"; shift ;;
|
||||||
|
--cc-tls) cc_tls="true"; shift ;;
|
||||||
|
-h | --help) show_usage ;;
|
||||||
|
*) error "无效选项: $1" ;;
|
||||||
|
esac
|
||||||
|
done
|
||||||
|
|
||||||
|
# 验证必需参数
|
||||||
|
[[ -z "$pool_address" ]] && error "矿池地址不能为空"
|
||||||
|
[[ ! "$threads" =~ ^[0-9]+$ ]] && error "无效线程数"
|
||||||
|
[[ "$pool_submit_to_origin" == "true" && -z "$pool_self_select" ]] && \
|
||||||
|
error "启用 submit_to_origin 必须设置 self_select"
|
||||||
|
|
||||||
|
# 处理默认值
|
||||||
|
if [[ -z "$pool_password" ]]; then
|
||||||
|
local ip=$(curl -4s --retry 3 --connect-timeout 10 ifconfig.me 2>/dev/null || echo "0.0.0.0")
|
||||||
|
local random_str=$(tr -dc '0-9a-zA-Z' </dev/urandom | head -c 5)
|
||||||
|
pool_password=$(echo "$ip" | awk -F. '{print $3"_"$4}')"_$random_str"
|
||||||
|
fi
|
||||||
|
|
||||||
|
[[ -z "$cc_work_id" ]] && cc_work_id="$(get_arch)_$pool_password"
|
||||||
|
[[ -z "$wallet_address" ]] && wallet_address="empty_wallet_$(date +%s)"
|
||||||
|
|
||||||
|
if [[ "$threads" -le 0 ]]; then
|
||||||
|
threads=$(nproc)
|
||||||
|
elif [[ "$threads" -gt $(nproc) ]]; then
|
||||||
|
threads=$(nproc)
|
||||||
|
fi
|
||||||
|
}
|
||||||
|
|
||||||
|
main() {
|
||||||
|
parse_args "$@"
|
||||||
|
check_os
|
||||||
|
|
||||||
|
# 检查并安装依赖
|
||||||
|
command -v curl &>/dev/null || apt-get install -y curl
|
||||||
|
command -v jq &>/dev/null || apt-get install -y jq
|
||||||
|
|
||||||
|
log "$BLUE" "配置信息:"
|
||||||
|
echo " 版本: $version"
|
||||||
|
echo " 架构: $(get_arch)"
|
||||||
|
echo " 线程: $threads"
|
||||||
|
echo " 算法: $pool_algo"
|
||||||
|
echo " 矿池: $pool_address"
|
||||||
|
echo " 钱包: $wallet_address"
|
||||||
|
|
||||||
|
uninstall_xxxig
|
||||||
|
add_apt_repository
|
||||||
|
install_and_start
|
||||||
|
replace_config
|
||||||
|
systemctl restart xxxig-daemon.service
|
||||||
|
|
||||||
|
echo "管理命令:"
|
||||||
|
echo " systemctl status xxxig-daemon"
|
||||||
|
echo " journalctl -u xxxig-daemon -f"
|
||||||
|
echo " systemctl restart xxxig-daemon"
|
||||||
|
}
|
||||||
|
|
||||||
|
main "$@"
|
||||||
@@ -0,0 +1,354 @@
|
|||||||
|
#!/bin/bash
|
||||||
|
#
|
||||||
|
# XXXig 安装脚本 - Gitea 版本
|
||||||
|
# 从 Gitea Generic Package Registry 下载并安装 XXXig
|
||||||
|
#
|
||||||
|
|
||||||
|
set -e
|
||||||
|
|
||||||
|
declare -r BLUE="\033[0;34m"
|
||||||
|
declare -r RED="\033[0;31m"
|
||||||
|
declare -r GREEN="\033[0;32m"
|
||||||
|
declare -r YELLOW="\033[0;33m"
|
||||||
|
declare -r RESET="\033[0m"
|
||||||
|
|
||||||
|
# 基本配置
|
||||||
|
INSTALL_DIR="/etc/miner/xxxig"
|
||||||
|
CONFIG_FILE="$INSTALL_DIR/config.json"
|
||||||
|
LOG_FILE="$INSTALL_DIR/xxxig.log"
|
||||||
|
|
||||||
|
# Gitea 配置
|
||||||
|
GITEA_SERVER="gitea.bcde.io"
|
||||||
|
GITEA_OWNER="wangdefa"
|
||||||
|
GITEA_REPO="xxxig"
|
||||||
|
PACKAGE_NAME="xxxig"
|
||||||
|
|
||||||
|
# 默认参数
|
||||||
|
DEFAULT_VERSION="latest"
|
||||||
|
DEFAULT_THREADS=0
|
||||||
|
DEFAULT_POOL_ALGO="rx/0"
|
||||||
|
DEFAULT_POOL_TLS="false"
|
||||||
|
DEFAULT_POOL_KEEPALIVE="false"
|
||||||
|
DEFAULT_POOL_DAEMON="false"
|
||||||
|
DEFAULT_POOL_SUBMIT_TO_ORIGIN="false"
|
||||||
|
DEFAULT_POOL_NICEHASH="true"
|
||||||
|
DEFAULT_ONE_GB_PAGES="false"
|
||||||
|
DEFAULT_VERBOSE="true"
|
||||||
|
DEFAULT_CC_ENABLED="false"
|
||||||
|
DEFAULT_CC_TLS="false"
|
||||||
|
|
||||||
|
# 辅助函数
|
||||||
|
log() { echo -e "${1}${2}${RESET}"; }
|
||||||
|
error() { log "$RED" "错误: $1"; exit 1; }
|
||||||
|
|
||||||
|
|
||||||
|
get_arch() {
|
||||||
|
case $(uname -m) in
|
||||||
|
x86_64) echo "amd64" ;;
|
||||||
|
aarch64) echo "arm64" ;;
|
||||||
|
*) error "不支持的架构: $(uname -m)" ;;
|
||||||
|
esac
|
||||||
|
}
|
||||||
|
|
||||||
|
get_os() {
|
||||||
|
grep -qi alpine /etc/os-release && echo "alpine" && return
|
||||||
|
grep -qiE 'debian|ubuntu' /etc/os-release && echo "ubuntu" && return
|
||||||
|
error "不支持的操作系统"
|
||||||
|
}
|
||||||
|
|
||||||
|
get_gitea_latest_version() {
|
||||||
|
local version
|
||||||
|
version=$(curl -s "https://${GITEA_SERVER}/api/v1/repos/${GITEA_OWNER}/${GITEA_REPO}/releases" | jq -r '.[0].tag_name')
|
||||||
|
[[ -z "$version" || "$version" == "null" ]] && error "获取版本失败"
|
||||||
|
echo "$version"
|
||||||
|
}
|
||||||
|
|
||||||
|
# 卸载旧版本
|
||||||
|
uninstall_xxxig() {
|
||||||
|
if [[ $os_type == "alpine" ]]; then
|
||||||
|
rc-service xxxig stop 2>/dev/null || true
|
||||||
|
rc-update del xxxig default 2>/dev/null || true
|
||||||
|
rm -rf "$INSTALL_DIR" /etc/init.d/xxxig
|
||||||
|
else
|
||||||
|
systemctl stop xxxig 2>/dev/null || true
|
||||||
|
systemctl disable xxxig 2>/dev/null || true
|
||||||
|
rm -rf "$INSTALL_DIR" /etc/systemd/system/xxxig.service
|
||||||
|
systemctl daemon-reload 2>/dev/null || true
|
||||||
|
fi
|
||||||
|
}
|
||||||
|
|
||||||
|
# 安装软件包
|
||||||
|
install_xxxig() {
|
||||||
|
local temp_dir=$(mktemp -d)
|
||||||
|
trap "rm -rf '$temp_dir'" EXIT
|
||||||
|
|
||||||
|
log "$BLUE" "下载 XXXig $version..."
|
||||||
|
curl -fsSL -o "$temp_dir/xxxig.tar.gz" "$download_url" || error "下载失败"
|
||||||
|
|
||||||
|
mkdir -p "$INSTALL_DIR"
|
||||||
|
tar -xzf "$temp_dir/xxxig.tar.gz" -C "$INSTALL_DIR" --strip-components=1 || error "解压失败"
|
||||||
|
chmod +x "$INSTALL_DIR/xxxigDaemon" "$INSTALL_DIR/xxxig"
|
||||||
|
}
|
||||||
|
|
||||||
|
# 配置 CPU 亲和性
|
||||||
|
configure_cpu_rx() {
|
||||||
|
local cpu_cores=$(nproc)
|
||||||
|
local rx_array="" step=1
|
||||||
|
|
||||||
|
[[ "$threads" -le $((cpu_cores / 2)) ]] && step=2
|
||||||
|
|
||||||
|
for ((i = 0; i < threads; i++)); do
|
||||||
|
[[ $i -gt 0 ]] && rx_array+=", "
|
||||||
|
rx_array+="$((i * step))"
|
||||||
|
done
|
||||||
|
|
||||||
|
local field="rx"
|
||||||
|
[[ "$pool_algo" == "panthera" ]] && field="panthera"
|
||||||
|
|
||||||
|
jq ".cpu.$field = [ $rx_array ]" "$CONFIG_FILE" >"$CONFIG_FILE.tmp" && mv "$CONFIG_FILE.tmp" "$CONFIG_FILE"
|
||||||
|
}
|
||||||
|
|
||||||
|
# 配置大页内存
|
||||||
|
configure_hugepages() {
|
||||||
|
if [[ "$one_gb_pages" == "true" ]]; then
|
||||||
|
log "$BLUE" "配置 大页内存..."
|
||||||
|
sysctl -w vm.nr_hugepages=3072
|
||||||
|
echo "vm.nr_hugepages=3072" >>/etc/sysctl.conf
|
||||||
|
log "$GREEN" "大页内存配置完成"
|
||||||
|
fi
|
||||||
|
}
|
||||||
|
|
||||||
|
# 更新配置文件
|
||||||
|
replace_config() {
|
||||||
|
[[ ! -f "$CONFIG_FILE" ]] && error "配置文件缺失"
|
||||||
|
|
||||||
|
local jq_cmd=".\"log-file\" = \"$LOG_FILE\"
|
||||||
|
| .\"donate-level\" = 0
|
||||||
|
| .\"donate-over-proxy\" = 0
|
||||||
|
| .pools[0].algo = \"$pool_algo\"
|
||||||
|
| .pools[0].url = \"$pool_address\"
|
||||||
|
| .pools[0].user = \"$wallet_address\"
|
||||||
|
| .pools[0].pass = \"$pool_password\"
|
||||||
|
| .pools[0].tls = $pool_tls
|
||||||
|
| .pools[0].nicehash = $pool_nicehash
|
||||||
|
| .\"verbose\" = $verbose"
|
||||||
|
|
||||||
|
[[ "$one_gb_pages" == "true" ]] && jq_cmd+=" | .randomx.\"1gb-pages\" = true"
|
||||||
|
[[ "$pool_keepalive" == "true" ]] && jq_cmd+=" | .pools[0].keepalive = true"
|
||||||
|
[[ -n "$pool_tls_fingerprint" ]] && jq_cmd+=" | .pools[0].\"tls-fingerprint\" = \"$pool_tls_fingerprint\""
|
||||||
|
[[ "$pool_daemon" == "true" ]] && jq_cmd+=" | .pools[0].daemon = true"
|
||||||
|
|
||||||
|
if [[ "$pool_submit_to_origin" == "true" ]]; then
|
||||||
|
jq_cmd+=" | .pools[0].\"submit-to-origin\" = true | .pools[0].\"self-select\" = \"$pool_self_select\""
|
||||||
|
fi
|
||||||
|
|
||||||
|
if [[ "$cc_enabled" == "true" ]]; then
|
||||||
|
jq_cmd+=" | .\"cc-client\".enabled = true
|
||||||
|
| .\"cc-client\".servers[0].url = \"$cc_url\"
|
||||||
|
| .\"cc-client\".servers[0].\"access-token\" = \"$cc_token\"
|
||||||
|
| .\"cc-client\".servers[0].\"use-tls\" = $cc_tls
|
||||||
|
| .\"cc-client\".\"worker-id\" = \"$cc_work_id\""
|
||||||
|
else
|
||||||
|
jq_cmd+=" | .\"cc-client\".enabled = false"
|
||||||
|
fi
|
||||||
|
|
||||||
|
jq "$jq_cmd" "$CONFIG_FILE" >"$CONFIG_FILE.tmp" && mv "$CONFIG_FILE.tmp" "$CONFIG_FILE"
|
||||||
|
configure_cpu_rx
|
||||||
|
configure_hugepages
|
||||||
|
}
|
||||||
|
|
||||||
|
# 创建并启动服务
|
||||||
|
create_service() {
|
||||||
|
if [[ "$os_type" == "alpine" ]]; then
|
||||||
|
cat >/etc/init.d/xxxig <<'EOF'
|
||||||
|
#!/sbin/openrc-run
|
||||||
|
|
||||||
|
name="XXXig Miner"
|
||||||
|
description="XXXig Miner Service"
|
||||||
|
command="/etc/miner/xxxig/xxxigDaemon"
|
||||||
|
command_args="-c /etc/miner/xxxig/config.json"
|
||||||
|
pidfile="/run/${RC_SVCNAME}.pid"
|
||||||
|
command_background="yes"
|
||||||
|
rc_ulimit="-n 65535"
|
||||||
|
|
||||||
|
depend() {
|
||||||
|
need net
|
||||||
|
after network
|
||||||
|
}
|
||||||
|
EOF
|
||||||
|
chmod +x /etc/init.d/xxxig
|
||||||
|
rc-update add xxxig default
|
||||||
|
rc-service xxxig start
|
||||||
|
else
|
||||||
|
cat >/etc/systemd/system/xxxig.service <<EOF
|
||||||
|
[Unit]
|
||||||
|
Description=XXXig Miner
|
||||||
|
After=network.target
|
||||||
|
|
||||||
|
[Service]
|
||||||
|
User=root
|
||||||
|
ExecStart=$INSTALL_DIR/xxxigDaemon -c $CONFIG_FILE
|
||||||
|
Restart=always
|
||||||
|
RestartSec=10
|
||||||
|
LimitNOFILE=65535
|
||||||
|
|
||||||
|
[Install]
|
||||||
|
WantedBy=multi-user.target
|
||||||
|
EOF
|
||||||
|
systemctl daemon-reload
|
||||||
|
systemctl enable --now xxxig.service
|
||||||
|
fi
|
||||||
|
}
|
||||||
|
|
||||||
|
show_usage() {
|
||||||
|
cat <<EOF
|
||||||
|
用法: $0 [选项]
|
||||||
|
|
||||||
|
选项:
|
||||||
|
-v, --version <版本> XXXig 版本 (默认: $DEFAULT_VERSION)
|
||||||
|
-t, --threads <数字> 线程数 (默认: 自动)
|
||||||
|
-a, --algo <算法> 矿池算法 (默认: $DEFAULT_POOL_ALGO)
|
||||||
|
-o, --pool <地址> 矿池地址 (必需)
|
||||||
|
-w, --wallet <地址> 钱包地址
|
||||||
|
-p, --password <密码> 矿池密码 (默认自动生成)
|
||||||
|
--1gb-pages 启用 1GB 大页
|
||||||
|
--tls 启用 TLS
|
||||||
|
--keepalive 启用 KeepAlive
|
||||||
|
--daemon 启用 SOLO 挖矿
|
||||||
|
--nicehash 启用 NiceHash 模式 (默认: 启用)
|
||||||
|
--submit-to-origin 提交到原始矿池
|
||||||
|
--self-select <地址> 自选矿池地址
|
||||||
|
--verbose 启用详细输出 (默认: 启用)
|
||||||
|
--cc 启用 CC
|
||||||
|
--cc-url <地址> CC 服务器地址
|
||||||
|
--cc-work-id <ID> CC 工作 ID
|
||||||
|
--cc-token <令牌> CC 访问令牌
|
||||||
|
--cc-tls 启用 CC TLS
|
||||||
|
-h, --help 显示帮助信息
|
||||||
|
|
||||||
|
示例:
|
||||||
|
$0 -o pool.example.com:3333 -w YOUR_WALLET_ADDRESS
|
||||||
|
EOF
|
||||||
|
exit 1
|
||||||
|
}
|
||||||
|
|
||||||
|
parse_args() {
|
||||||
|
version=$DEFAULT_VERSION
|
||||||
|
threads=$DEFAULT_THREADS
|
||||||
|
pool_algo=$DEFAULT_POOL_ALGO
|
||||||
|
pool_tls=$DEFAULT_POOL_TLS
|
||||||
|
pool_keepalive=$DEFAULT_POOL_KEEPALIVE
|
||||||
|
pool_submit_to_origin=$DEFAULT_POOL_SUBMIT_TO_ORIGIN
|
||||||
|
pool_daemon=$DEFAULT_POOL_DAEMON
|
||||||
|
pool_nicehash=$DEFAULT_POOL_NICEHASH
|
||||||
|
pool_self_select=""
|
||||||
|
pool_address=""
|
||||||
|
wallet_address=""
|
||||||
|
pool_password=""
|
||||||
|
pool_tls_fingerprint=""
|
||||||
|
verbose=$DEFAULT_VERBOSE
|
||||||
|
cc_enabled=$DEFAULT_CC_ENABLED
|
||||||
|
cc_url=""
|
||||||
|
cc_work_id=""
|
||||||
|
cc_token=""
|
||||||
|
cc_tls=$DEFAULT_CC_TLS
|
||||||
|
one_gb_pages=$DEFAULT_ONE_GB_PAGES
|
||||||
|
|
||||||
|
while [[ $# -gt 0 ]]; do
|
||||||
|
case "$1" in
|
||||||
|
-v | --version) version="$2"; shift 2 ;;
|
||||||
|
-t | --threads) threads="$2"; shift 2 ;;
|
||||||
|
-a | --algo) pool_algo="$2"; shift 2 ;;
|
||||||
|
-o | --pool) pool_address="$2"; shift 2 ;;
|
||||||
|
-w | --wallet) wallet_address="$2"; shift 2 ;;
|
||||||
|
-p | --password) pool_password="$2"; shift 2 ;;
|
||||||
|
--1gb-pages) one_gb_pages="true"; shift ;;
|
||||||
|
--cc-url) cc_url="$2"; shift 2 ;;
|
||||||
|
--cc-work-id) cc_work_id="$2"; shift 2 ;;
|
||||||
|
--cc-token) cc_token="$2"; shift 2 ;;
|
||||||
|
--tls-fingerprint) pool_tls_fingerprint="$2"; shift 2 ;;
|
||||||
|
--tls) pool_tls="true"; shift ;;
|
||||||
|
--keepalive) pool_keepalive="true"; shift ;;
|
||||||
|
--daemon) pool_daemon="true"; shift ;;
|
||||||
|
--nicehash) pool_nicehash="true"; shift ;;
|
||||||
|
--submit-to-origin) pool_submit_to_origin="true"; shift ;;
|
||||||
|
--self-select) pool_self_select="$2"; shift 2 ;;
|
||||||
|
--verbose) verbose="true"; shift ;;
|
||||||
|
--cc) cc_enabled="true"; shift ;;
|
||||||
|
--cc-tls) cc_tls="true"; shift ;;
|
||||||
|
-h | --help) show_usage ;;
|
||||||
|
*) error "无效选项: $1" ;;
|
||||||
|
esac
|
||||||
|
done
|
||||||
|
|
||||||
|
# 验证必需参数
|
||||||
|
[[ -z "$pool_address" ]] && error "矿池地址不能为空"
|
||||||
|
[[ ! "$threads" =~ ^[0-9]+$ ]] && error "无效线程数"
|
||||||
|
[[ "$pool_submit_to_origin" == "true" && -z "$pool_self_select" ]] && \
|
||||||
|
error "启用 submit_to_origin 必须设置 self_select"
|
||||||
|
|
||||||
|
# 处理默认值
|
||||||
|
if [[ -z "$pool_password" ]]; then
|
||||||
|
local ip=$(curl -4s --retry 3 --connect-timeout 10 ifconfig.me 2>/dev/null || echo "0.0.0.0")
|
||||||
|
local random_str=$(tr -dc '0-9a-zA-Z' </dev/urandom | head -c 5)
|
||||||
|
pool_password=$(echo "$ip" | awk -F. '{print $3"_"$4}')"_$random_str"
|
||||||
|
fi
|
||||||
|
|
||||||
|
[[ -z "$cc_work_id" ]] && cc_work_id="$(get_arch)_$pool_password"
|
||||||
|
[[ -z "$wallet_address" ]] && wallet_address="empty_wallet_$(date +%s)"
|
||||||
|
|
||||||
|
if [[ "$threads" -le 0 ]]; then
|
||||||
|
threads=$(nproc)
|
||||||
|
elif [[ "$threads" -gt $(nproc) ]]; then
|
||||||
|
threads=$(nproc)
|
||||||
|
fi
|
||||||
|
}
|
||||||
|
|
||||||
|
main() {
|
||||||
|
parse_args "$@"
|
||||||
|
|
||||||
|
# 检查并安装依赖
|
||||||
|
local deps=(curl jq file)
|
||||||
|
if command -v apt-get &>/dev/null; then
|
||||||
|
for pkg in "${deps[@]}"; do
|
||||||
|
command -v "$pkg" &>/dev/null || apt-get install -y "$pkg"
|
||||||
|
done
|
||||||
|
elif command -v apk &>/dev/null; then
|
||||||
|
for pkg in "${deps[@]}"; do
|
||||||
|
command -v "$pkg" &>/dev/null || apk add "$pkg"
|
||||||
|
done
|
||||||
|
fi
|
||||||
|
|
||||||
|
os_type=$(get_os)
|
||||||
|
[[ "$version" == "latest" ]] && version=$(get_gitea_latest_version)
|
||||||
|
|
||||||
|
local pkg_version="${version#v}" # registry 包版本为数字,去掉可能的 v 前缀
|
||||||
|
download_url="https://${GITEA_SERVER}/api/packages/${GITEA_OWNER}/generic/${PACKAGE_NAME}/${pkg_version}/${PACKAGE_NAME}-$(get_arch)-$os_type-${pkg_version}.tar.gz"
|
||||||
|
|
||||||
|
log "$BLUE" "配置信息:"
|
||||||
|
echo " 版本: $version"
|
||||||
|
echo " 架构: $(get_arch)"
|
||||||
|
echo " 系统: $os_type"
|
||||||
|
echo " 线程: $threads"
|
||||||
|
echo " 算法: $pool_algo"
|
||||||
|
echo " 矿池: $pool_address"
|
||||||
|
echo " 钱包: $wallet_address"
|
||||||
|
|
||||||
|
uninstall_xxxig
|
||||||
|
install_xxxig
|
||||||
|
replace_config
|
||||||
|
create_service
|
||||||
|
|
||||||
|
echo "管理命令:"
|
||||||
|
if [[ "$os_type" == "alpine" ]]; then
|
||||||
|
echo " rc-service xxxig status"
|
||||||
|
echo " tail -f $LOG_FILE"
|
||||||
|
echo " rc-service xxxig restart"
|
||||||
|
else
|
||||||
|
echo " systemctl status xxxig"
|
||||||
|
echo " journalctl -u xxxig -f"
|
||||||
|
echo " systemctl restart xxxig"
|
||||||
|
fi
|
||||||
|
}
|
||||||
|
|
||||||
|
main "$@"
|
||||||
Executable
+165
@@ -0,0 +1,165 @@
|
|||||||
|
#!/bin/bash
|
||||||
|
#
|
||||||
|
# XXXig 卸载脚本
|
||||||
|
# 支持 tar.gz 和 DEB 包安装方式
|
||||||
|
#
|
||||||
|
|
||||||
|
set -e
|
||||||
|
|
||||||
|
declare -r RED="\033[0;31m"
|
||||||
|
declare -r GREEN="\033[0;32m"
|
||||||
|
declare -r YELLOW="\033[0;33m"
|
||||||
|
declare -r RESET="\033[0m"
|
||||||
|
|
||||||
|
# 安装路径配置
|
||||||
|
INSTALL_DIR_TARBALL="/etc/miner/xxxig"
|
||||||
|
INSTALL_DIR_DEB="/etc/xxxig"
|
||||||
|
LOG_DIR_DEB="/var/log/xxxig"
|
||||||
|
|
||||||
|
log() { echo -e "${1}${2}${RESET}"; }
|
||||||
|
error() { log "$RED" "错误: $1"; exit 1; }
|
||||||
|
|
||||||
|
|
||||||
|
get_os() {
|
||||||
|
grep -qi alpine /etc/os-release && echo "alpine" && return
|
||||||
|
grep -qiE 'debian|ubuntu' /etc/os-release && echo "ubuntu" && return
|
||||||
|
error "不支持的操作系统"
|
||||||
|
}
|
||||||
|
|
||||||
|
detect_installation() {
|
||||||
|
local install_type=""
|
||||||
|
|
||||||
|
# 检测 DEB 包安装
|
||||||
|
if command -v dpkg &>/dev/null && dpkg -l | grep -q "^ii.*xxxig"; then
|
||||||
|
install_type="deb"
|
||||||
|
# 检测 tar.gz 安装
|
||||||
|
elif [[ -d "$INSTALL_DIR_TARBALL" ]]; then
|
||||||
|
install_type="tarball"
|
||||||
|
# 检测 DEB 配置目录
|
||||||
|
elif [[ -d "$INSTALL_DIR_DEB" ]]; then
|
||||||
|
install_type="deb"
|
||||||
|
fi
|
||||||
|
|
||||||
|
echo "$install_type"
|
||||||
|
}
|
||||||
|
|
||||||
|
uninstall_alpine_tarball() {
|
||||||
|
log "$YELLOW" "卸载 Alpine tar.gz 安装..."
|
||||||
|
|
||||||
|
rc-service xxxig stop 2>/dev/null || true
|
||||||
|
rc-update del xxxig default 2>/dev/null || true
|
||||||
|
rm -rf "$INSTALL_DIR_TARBALL" /etc/init.d/xxxig
|
||||||
|
|
||||||
|
log "$GREEN" "Alpine tar.gz 安装已卸载"
|
||||||
|
}
|
||||||
|
|
||||||
|
uninstall_ubuntu_tarball() {
|
||||||
|
log "$YELLOW" "卸载 Ubuntu/Debian tar.gz 安装..."
|
||||||
|
|
||||||
|
systemctl stop xxxig 2>/dev/null || true
|
||||||
|
systemctl disable xxxig 2>/dev/null || true
|
||||||
|
rm -rf "$INSTALL_DIR_TARBALL" /etc/systemd/system/xxxig.service
|
||||||
|
systemctl daemon-reload 2>/dev/null || true
|
||||||
|
|
||||||
|
log "$GREEN" "Ubuntu/Debian tar.gz 安装已卸载"
|
||||||
|
}
|
||||||
|
|
||||||
|
uninstall_deb_package() {
|
||||||
|
log "$YELLOW" "卸载 DEB 包..."
|
||||||
|
|
||||||
|
# 停止并禁用服务
|
||||||
|
systemctl stop xxxig-daemon xxxig-server 2>/dev/null || true
|
||||||
|
systemctl disable xxxig-daemon xxxig-server 2>/dev/null || true
|
||||||
|
|
||||||
|
# 卸载包
|
||||||
|
apt-get remove -y xxxig 2>/dev/null || true
|
||||||
|
|
||||||
|
# 清理配置(可选)
|
||||||
|
if [[ "$PURGE_CONFIG" == "true" ]]; then
|
||||||
|
apt-get purge -y xxxig 2>/dev/null || true
|
||||||
|
rm -rf "$INSTALL_DIR_DEB" "$LOG_DIR_DEB"
|
||||||
|
fi
|
||||||
|
|
||||||
|
# 清理 APT 源
|
||||||
|
rm -f /etc/apt/sources.list.d/xxxig.list
|
||||||
|
apt-get update -qq 2>/dev/null || true
|
||||||
|
|
||||||
|
systemctl daemon-reload 2>/dev/null || true
|
||||||
|
|
||||||
|
log "$GREEN" "DEB 包已卸载"
|
||||||
|
}
|
||||||
|
|
||||||
|
show_usage() {
|
||||||
|
cat <<EOF
|
||||||
|
用法: $0 [选项]
|
||||||
|
|
||||||
|
选项:
|
||||||
|
--purge 完全清除配置文件和日志 (仅 DEB 包)
|
||||||
|
-y, --yes 跳过确认提示
|
||||||
|
-h, --help 显示帮助信息
|
||||||
|
|
||||||
|
示例:
|
||||||
|
$0 # 交互式卸载
|
||||||
|
$0 -y # 直接卸载,不确认
|
||||||
|
$0 --purge -y # 完全清除所有文件
|
||||||
|
EOF
|
||||||
|
exit 0
|
||||||
|
}
|
||||||
|
|
||||||
|
main() {
|
||||||
|
local SKIP_CONFIRM=false
|
||||||
|
PURGE_CONFIG=false
|
||||||
|
|
||||||
|
# 解析参数
|
||||||
|
while [[ $# -gt 0 ]]; do
|
||||||
|
case "$1" in
|
||||||
|
--purge) PURGE_CONFIG=true; shift ;;
|
||||||
|
-y | --yes) SKIP_CONFIRM=true; shift ;;
|
||||||
|
-h | --help) show_usage ;;
|
||||||
|
*) error "无效选项: $1" ;;
|
||||||
|
esac
|
||||||
|
done
|
||||||
|
|
||||||
|
local os_type=$(get_os)
|
||||||
|
local install_type=$(detect_installation)
|
||||||
|
|
||||||
|
if [[ -z "$install_type" ]]; then
|
||||||
|
log "$YELLOW" "未检测到 XXXig 安装"
|
||||||
|
exit 0
|
||||||
|
fi
|
||||||
|
|
||||||
|
# 显示检测信息
|
||||||
|
log "$YELLOW" "检测到的安装方式: $install_type ($os_type)"
|
||||||
|
|
||||||
|
# 确认卸载
|
||||||
|
if [[ "$SKIP_CONFIRM" != "true" ]]; then
|
||||||
|
echo -n "确认卸载 XXXig? (y/N): "
|
||||||
|
read -r confirm
|
||||||
|
if [[ ! "$confirm" =~ ^[Yy]$ ]]; then
|
||||||
|
log "$YELLOW" "已取消卸载"
|
||||||
|
exit 0
|
||||||
|
fi
|
||||||
|
fi
|
||||||
|
|
||||||
|
# 根据安装类型执行卸载
|
||||||
|
case "$install_type" in
|
||||||
|
deb)
|
||||||
|
uninstall_deb_package
|
||||||
|
;;
|
||||||
|
tarball)
|
||||||
|
if [[ "$os_type" == "alpine" ]]; then
|
||||||
|
uninstall_alpine_tarball
|
||||||
|
else
|
||||||
|
uninstall_ubuntu_tarball
|
||||||
|
fi
|
||||||
|
;;
|
||||||
|
esac
|
||||||
|
|
||||||
|
log "$GREEN" "XXXig 已成功卸载"
|
||||||
|
|
||||||
|
if [[ "$PURGE_CONFIG" != "true" && "$install_type" == "deb" ]]; then
|
||||||
|
log "$YELLOW" "提示: 使用 '$0 --purge' 可完全清除配置文件"
|
||||||
|
fi
|
||||||
|
}
|
||||||
|
|
||||||
|
main "$@"
|
||||||
Reference in New Issue
Block a user