├── example ├── image.png ├── image-1.png ├── nonebot.md └── koishi.md ├── step-by-step └── readme.md ├── napcat.sh ├── onekey.sh ├── README.md ├── start.sh └── debian.sh /example/image.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/NapNeko/NapCat-Termux/HEAD/example/image.png -------------------------------------------------------------------------------- /example/image-1.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/NapNeko/NapCat-Termux/HEAD/example/image-1.png -------------------------------------------------------------------------------- /step-by-step/readme.md: -------------------------------------------------------------------------------- 1 | # 安装 proot 容器 2 | 3 | ```shell 4 | bash -c "$(curl -L https://github.com/NapNeko/NapCat-Termux/raw/main/debian.sh)" 5 | exit 6 | ``` 7 | 8 | # 安装 NapCat 9 | 10 | ```shell 11 | bash bookworm-arm64.sh 12 | bash -c "$(curl -L https://github.com/NapNeko/NapCat-Termux/raw/main/napcat.sh)" 13 | exit 14 | ``` -------------------------------------------------------------------------------- /example/nonebot.md: -------------------------------------------------------------------------------- 1 | # Nonebot 接入 NapCat-Termux 2 | 3 | ## 1. 安装 Nonebot 4 | 在 Termux 终端中执行下面的脚本 5 | ```shell 6 | pkg updage 7 | # 一路回车 8 | pkg i python3 9 | ## 这一步可能会报错,考虑在 proot 容器内安装 Nonebot 10 | python3 -m pip install nb-cli 11 | nb create 12 | ``` 13 | 14 | 启动 Nonebot 15 | ```shell 16 | nb run 17 | ``` 18 | 19 | ## 2. 安装 NapCat-Termux 20 | 21 | 按音量下键,点击`切换会话` -> `新会话` -> `点击切换新创建的会话` 22 | 在新的终端中执行下面的脚本 23 | ```shell 24 | bash -c "$(curl -L https://github.com/NapNeko/NapCat-Termux/raw/main/onekey.sh)" 25 | ``` 26 | 27 | ## 3. 扫码登录 28 | 29 | ```shell 30 | # 启动容器后会自启 31 | bash bookworm-arm64.sh 32 | ``` 33 | 修改NapCat配置 34 | ![alt text](image-1.png) 35 | 36 | 扫码登录 37 | 38 | ## 4. 接入 Nonebot 39 | 40 | 浏览器打开 `http://127.0.0.1:5140` 41 | 42 | [接入 Nonebot](https://napneko.github.io/zh-CN/guide/integration) -------------------------------------------------------------------------------- /example/koishi.md: -------------------------------------------------------------------------------- 1 | # Koishi-Termux 接入 NapCat-Termux 2 | 3 | ## 1. 安装 Koishi ([koimux_bot](https://github.com/initialencounter/koimux_bot)) 4 | 在 Termux 终端中执行下面的脚本 5 | ```shell 6 | bash -c "$(curl -L https://gitee.com/initencunter/koimux_bot/raw/master/script/koishi.sh)" 7 | ``` 8 | 9 | 启动 Koishi 10 | ```shell 11 | koi start 12 | ``` 13 | 14 | ## 2. 安装 NapCat-Termux 15 | 16 | 按音量下键,点击`切换会话` -> `新会话` -> `点击切换新创建的会话` 17 | 在新的终端中执行下面的脚本 18 | ```shell 19 | bash -c "$(curl -L https://github.com/NapNeko/NapCat-Termux/raw/main/onekey.sh)" 20 | ``` 21 | 22 | ## 3. 扫码登录 23 | 24 | ```shell 25 | # 启动容器后会自启 26 | bash bookworm-arm64.sh 27 | ``` 28 | 修改NapCat配置 29 | ![alt text](image.png) 30 | 31 | 扫码登录 32 | 33 | ## 4. 接入 Koishi 34 | 35 | 浏览器打开 `http://127.0.0.1:5140` 36 | 37 | [接入 Koishi](https://napneko.github.io/zh-CN/guide/integration) -------------------------------------------------------------------------------- /napcat.sh: -------------------------------------------------------------------------------- 1 | # 设置环境变量 2 | export DEBIAN_FRONTEND=noninteractive 3 | 4 | # 安装必要的软件包 5 | apt-get update && apt-get install -y libnss3 libnotify4 libsecret-1-0 libgbm1 libasound2 fonts-wqy-zenhei gnutls-bin libglib2.0-dev libdbus-1-3 libgtk-3-0 libxss1 libxtst6 libatspi2.0-0 libx11-xcb1 ffmpeg unzip jq curl whiptail jq xvfb 6 | apt autoremove -y 7 | apt clean 8 | rm -rf /var/lib/apt/lists/* /tmp/* /var/tmp/* 9 | 10 | # 安装Linux QQ 11 | curl -o linuxqq.deb https://dldir1.qq.com/qqfile/qq/QQNT/Linux/QQ_3.2.12_240819_arm64_01.deb 12 | dpkg -i --force-depends linuxqq.deb && rm linuxqq.deb 13 | 14 | # 安装NapCat 15 | version=$(curl "https://api.github.com/repos/NapNeko/NapCatQQ/releases/latest" | jq -r '.tag_name') 16 | curl -L "https://github.com/NapNeko/NapCatQQ/releases/download/$version/NapCat.Shell.zip" -o "NapCat.linux.arm64.zip" 17 | unzip NapCat.linux.arm64.zip -d NapCat.linux.arm64 18 | chmod +x NapCat.linux.arm64/napcat.sh 19 | echo "(async () => {await import('file:///root/NapCat.linux.arm64/napcat.mjs');})();" > /opt/QQ/resources/app/app_launcher/index.js -------------------------------------------------------------------------------- /onekey.sh: -------------------------------------------------------------------------------- 1 | # 安装 debian 容器 2 | bash -c "$(curl -L https://github.com/NapNeko/NapCat-Termux/raw/main/debian.sh)" 3 | 4 | # 安装脚本 5 | curl -L -o bookworm-arm64/root/napcat.sh https://github.com/NapNeko/NapCat-Termux/raw/main/napcat.sh 6 | curl -L -o bookworm-arm64/root/start.sh https://github.com/NapNeko/NapCat-Termux/raw/main/start.sh 7 | # 启动容器并安装 8 | unset LD_PRELOAD 9 | proot --bind=/vendor --bind=/system --bind=/data/data/com.termux/files/usr --bind=/storage --bind=/storage/self/primary:/sdcard --bind=/data/data/com.termux/files/home --bind=/data/data/com.termux/cache --bind=/data/dalvik-cache --bind=bookworm-arm64/tmp:/dev/shm --bind=bookworm-arm64/etc/proc/.sysctl_entry_cap_last_cap:/proc/sys/kernel/cap_last_cap --bind=bookworm-arm64/etc/proc/.vmstat:/proc/vmstat --bind=bookworm-arm64/etc/proc/.version:/proc/version --bind=bookworm-arm64/etc/proc/.uptime:/proc/uptime --bind=bookworm-arm64/etc/proc/.stat:/proc/stat --bind=bookworm-arm64/etc/proc/.loadavg:/proc/loadavg --bind=bookworm-arm64/etc/proc/.bus/input/devices:/proc/bus/input/devices --bind=bookworm-arm64/etc/proc/.modules:/proc/modules --bind=/sys --bind=/proc/self/fd/2:/dev/stderr --bind=/proc/self/fd/1:/dev/stdout --bind=/proc/self/fd/0:/dev/stdin --bind=/proc/self/fd:/dev/fd --bind=/proc --bind=/dev/urandom:/dev/random --bind=/data/data/com.termux/files/usr/tmp:/tmp --bind=/data/data/com.termux/files:bookworm-arm64/termux --bind=/dev --root-id --cwd=/root -L --kernel-release=6.2.1-perf --sysvipc --link2symlink --kill-on-exit --rootfs=bookworm-arm64/ /usr/bin/env -i HOME=/root LANG=zh_CN.UTF-8 TERM=xterm-256color /bin/su -l root /root/napcat.sh 10 | 11 | echo "bash bookworm-arm64.sh" >> ~/.bashrc 12 | echo "bash start.sh" >> ~/bookworm-arm64/root/.bashrc 13 | -------------------------------------------------------------------------------- /README.md: -------------------------------------------------------------------------------- 1 | # 在手机上部署 NapCat 2 | 3 | 本项目提供了在安卓手机上安装 [NapCat](https://github.com/NapNeko/NapCatQQ) 的方法 4 | 使用 [ZeroTermux](https://github.com/hanxinhao000/ZeroTermux) + bookworm + linuxqq 制作 5 | 6 | - 基于 Linux QQ 7 | - 运行内存大于 100M 8 | - 支持持久化 QQ 登录状态和数据 9 | 10 | # 目录: 11 | 12 | - 1. 安装 Termux 13 | - 2. 安装 NapCat 14 | - 2.1 方法 1. 使用恢复包安装 15 | - 2.2 方法 2. 使用一键脚本 16 | - 3. 启动 17 | 18 | ## 1. 安装 ZeroTermux 19 | 20 | 前往[hanxinhao000/ZeroTermux](https://github.com/hanxinhao000/ZeroTermux/releases)下载 ZeroTermux 安装包并安装 21 | 22 | - 注意事项: 23 | 直接从 GitHub 下载 ZeroTermux 速度可能会很慢,建议使用 [ghproxy.com](https://mirror.ghproxy.com/) 代理 24 | 25 | ## 2. 安装 NapCat 26 | 27 | ### 2.1 使用恢复包安装 28 | 29 |
30 | 点击展开内容! 31 | 32 | #### 2.1.1 下载恢复包 33 | 34 | 前往 [Github releases](https://github.com/NapNeko/NapCat-Termux/releases) 下载 ZeroTermux 恢复包, 并将恢复包放在 手机的 `内部存储/xinhao/data/` 目录 35 | 36 | - 注意事项: 37 | - 恢复包要放在 `内部存储/xinhao/data/`目录或者 `/sdcard/xinhao/data`目录,否则在恢复容器的时候无法找到恢复包 38 | 39 | #### 2.1.2 恢复容器 40 | 41 | - 打开 ZeroTermux 42 | - 恢复 43 | 进入 ZeroTermux 点击音量上键 呼出菜单栏 点击菜单栏的 `备份/恢复` 选择下载的恢复包 44 | 输入一个容器名字点击恢复 这个过程需要等待几分钟 45 | - 切换容器 46 | 再次点击音量上键, 呼出菜单栏,点击菜单栏的 `容器切换` 选择刚才创建的容器 询问你是否需要重启时, 选择立即重启,接下你将进入启动界面 47 | 48 | - 注意事项: - 如果音量上键无法呼出菜单,说明你的 ZeroTermux 版本比较旧,可以使用右滑左侧的屏幕边缘来呼出菜单栏 49 |
50 | 51 | ### 2.2 使用一键脚本 52 | 53 | ```shell 54 | bash -c "$(curl -L https://github.com/NapNeko/NapCat-Termux/raw/main/onekey.sh)" 55 | ``` 56 | 57 | ### 3. 启动 58 | 59 | 如果你还没有进入容器 60 | 判断方法输入 `uname -a` ,如果输出信息以 `Android` 结尾,则未进入 proot 容器 61 | 62 | ```shell 63 | # 启动 64 | bash bookworm-arm64.sh 65 | ``` 66 | 67 | ```shell 68 | # 启动 69 | cd NapCat.linux.arm64 && ./napcat.sh 70 | ``` 71 | 72 | ### 4. 修改 NapCat 配置 73 | 74 | #### 直接修改 75 | 76 | 按音量下键,调出目录管理 77 | 编辑 `~/home/bookworm-arm64/root/config/oonbot11_.json` 文件 78 | 79 | #### WebUI 修改 80 | 81 | 浏览器访问 `http://localhost:6099/webui/login.html` 82 | token 位于容器内 /root/NapCat.linux.arm64/config/webui.json 目录 83 | 84 | ## 参考与基础 85 | 86 | [NapNeko/NapCatQQ](https://github.com/NapNeko/NapCatQQ) 87 | 88 | [yudezeng/yutools](https://gitee.com/yudezeng/yutools) 89 | -------------------------------------------------------------------------------- /start.sh: -------------------------------------------------------------------------------- 1 | #!/bin/bash 2 | # Create a temporary file to store the JSON data 3 | function main() { 4 | if [ ! -f "/root/.env" ]; then 5 | temp_file=$(mktemp) 6 | 7 | # Initialize the JSON structure with default values 8 | cat >$temp_file <$temp_file.tmp && mv $temp_file.tmp $temp_file 45 | } 46 | 47 | ACCOUNT=$(whiptail --inputbox "请输入机器人QQ号:" 8 30 --title "基础设置" 3>&1 1>&2 2>&3) 48 | if [ -z "$ACCOUNT" ]; then 49 | echo "机器人QQ号不能为空" 50 | rm $temp_file 51 | main 52 | else 53 | echo "机器人QQ号: $ACCOUNT" 54 | echo ACCOUNT=$ACCOUNT > /root/.env 55 | # Reverse WebSocket 设置 56 | reverse_ws_enable=$(whiptail --title "反向 ws 设置" --radiolist "启用反向 WS?" 15 30 2 \ 57 | "true" "" ON \ 58 | "false" "" OFF 3>&1 1>&2 2>&3) 59 | update_json '.reverseWs.enable = '"$reverse_ws_enable"'' 60 | 61 | if [ "$reverse_ws_enable" = "true" ]; then 62 | reverse_ws_urls=$(whiptail --inputbox "请输入反向 ws URLs (comma separated):" 8 30 --title "反向 ws 设置" 3>&1 1>&2 2>&3) 63 | IFS=',' read -r -a reverse_ws_urls_array <<<"$reverse_ws_urls" 64 | reverse_ws_urls_json=$(printf '%s\n' "${reverse_ws_urls_array[@]}" | jq -R . | jq -s .) 65 | update_json '.reverseWs.urls = '"$reverse_ws_urls_json"'' 66 | fi 67 | 68 | # WebSocket 设置 69 | ws_enable=$(whiptail --title "WebSocket 设置" --radiolist "启用 WebSocket?" 15 30 2 \ 70 | "true" "" OFF \ 71 | "false" "" ON 3>&1 1>&2 2>&3) 72 | update_json '.ws.enable = '"$ws_enable"'' 73 | 74 | if [ "$ws_enable" = "true" ]; then 75 | ws_host=$(whiptail --inputbox "请输入 WebSocket host:" 8 30 --title "WebSocket 设置" 3>&1 1>&2 2>&3) 76 | update_json '.ws.host = "'"$ws_host"'"' 77 | 78 | ws_port=$(whiptail --inputbox "请输入 WebSocket 端口:" 8 30 --title "WebSocket 设置" 3>&1 1>&2 2>&3) 79 | update_json '.ws.port = '"$ws_port"'' 80 | fi 81 | 82 | # HTTP 设置 83 | http_enable=$(whiptail --title "HTTP 设置" --radiolist "启用 HTTP?" 15 30 2 \ 84 | "true" "" OFF \ 85 | "false" "" ON 3>&1 1>&2 2>&3) 86 | update_json '.http.enable = '"$http_enable"'' 87 | 88 | if [ "$http_enable" = "true" ]; then 89 | http_host=$(whiptail --inputbox "请输入 HTTP host:" 8 30 --title "HTTP 设置" 3>&1 1>&2 2>&3) 90 | update_json '.http.host = "'"$http_host"'"' 91 | 92 | http_port=$(whiptail --inputbox "请输入 HTTP 端口:" 8 30 --title "HTTP 设置" 3>&1 1>&2 2>&3) 93 | update_json '.http.port = '"$http_port"'' 94 | 95 | http_secret=$(whiptail --inputbox "请输入 HTTP secret:" 8 30 --title "HTTP 设置" 3>&1 1>&2 2>&3) 96 | update_json '.http.secret = "'"$http_secret"'"' 97 | 98 | http_enable_heart=$(whiptail --title "HTTP 设置" --radiolist "启用 HTTP 心跳?" 15 30 2 \ 99 | "true" "" ON \ 100 | "false" "" OFF 3>&1 1>&2 2>&3) 101 | update_json '.http.enableHeart = '"$http_enable_heart"'' 102 | 103 | http_enable_post=$(whiptail --title "HTTP 设置" --radiolist "启用 HTTP 消息上报?" 15 30 2 \ 104 | "true" "" ON \ 105 | "false" "" OFF 3>&1 1>&2 2>&3) 106 | update_json '.http.enablePost = '"$http_enable_post"'' 107 | 108 | http_post_urls=$(whiptail --inputbox "请输入 HTTP post URLs (comma separated):" 8 30 --title "HTTP 设置" 3>&1 1>&2 2>&3) 109 | IFS=',' read -r -a http_post_urls_array <<<"$http_post_urls" 110 | http_post_urls_json=$(printf '%s\n' "${http_post_urls_array[@]}" | jq -R . | jq -s .) 111 | update_json '.http.postUrls = '"$http_post_urls_json"'' 112 | fi 113 | 114 | advanced_setting=$(whiptail --title "高级设置" --radiolist "高级设置" 15 30 2 \ 115 | "true" "" OFF \ 116 | "false" "" ON 3>&1 1>&2 2>&3) 117 | 118 | if [ "$advanced_setting" = "true" ]; then 119 | # GroupLocalTime 设置 120 | group_local_time_record=$(whiptail --title "Group Local Time 设置" --radiolist "Record Group Local Time?" 15 30 2 \ 121 | "true" "" ON \ 122 | "false" "" OFF 3>&1 1>&2 2>&3) 123 | update_json '.GroupLocalTime.Record = '"$group_local_time_record"'' 124 | 125 | # Other 设置 126 | debug=$(whiptail --title "Debug 设置" --radiolist "Enable Debug?" 15 30 2 \ 127 | "true" "" ON \ 128 | "false" "" OFF 3>&1 1>&2 2>&3) 129 | update_json '.debug = '"$debug"'' 130 | 131 | heart_interval=$(whiptail --inputbox "请输入心跳间隔 (ms):" 8 30 --title "其他设置" 3>&1 1>&2 2>&3) 132 | update_json '.heartInterval = '"$heart_interval"'' 133 | 134 | message_post_format=$(whiptail --title "消息上报格式" --radiolist "消息上报格式" 15 30 2 \ 135 | "array" "" ON \ 136 | "object" "" OFF 3>&1 1>&2 2>&3) 137 | update_json '.messagePostFormat = "'"$message_post_format"'"' 138 | 139 | enable_local_file2url=$(whiptail --title "本地文件转Url" --radiolist "启用本地文件转Url?" 15 30 2 \ 140 | "true" "" ON \ 141 | "false" "" OFF 3>&1 1>&2 2>&3) 142 | update_json '.enableLocalFile2Url = '"$enable_local_file2url"'' 143 | 144 | music_sign_url=$(whiptail --inputbox "音乐签名url:" 8 30 --title "其他设置" 3>&1 1>&2 2>&3) 145 | update_json '.musicSignUrl = "'"$music_sign_url"'"' 146 | 147 | report_self_message=$(whiptail --title "上报自身消息" --radiolist "上报自身消息?" 15 30 2 \ 148 | "true" "" ON \ 149 | "false" "" OFF 3>&1 1>&2 2>&3) 150 | update_json '.reportSelfMessage = '"$report_self_message"'' 151 | 152 | token=$(whiptail --inputbox "请输入Token:" 8 30 --title "其他设置" 3>&1 1>&2 2>&3) 153 | update_json '.token = "'"$token"'"' 154 | fi 155 | 156 | # Output the final JSON to the user 157 | mv $temp_file /root/NapCat.linux.arm64/config/onebot11_$ACCOUNT.json 158 | fi 159 | fi 160 | START 161 | } 162 | 163 | function START() { 164 | source /root/.env 165 | Xvfb :1 -screen 0 1080x760x16 +extension GLX +render & 166 | sleep 2 167 | export DISPLAY=:1 168 | cd /root/NapCat.linux.arm64 && qq --no-sandbox -q $ACCOUNT 169 | } 170 | main 171 | -------------------------------------------------------------------------------- /debian.sh: -------------------------------------------------------------------------------- 1 | #!@TERMUX_PREFIX@/bin/bash 2 | AH=$(uname -m | sed s/aarch64/arm64/ | sed s/x86_64/amd64/) 3 | SYS_NAME="bookworm" 4 | ROOTFS_DIR="$SYS_NAME-$AH" 5 | BAGNAME="rootfs.tar.xz" 6 | SLEEP_TIME=0.1 7 | DEFAULT_FAKE_KERNEL_VERSION="6.2.1-perf" 8 | 9 | if uname -a | grep -q "Android"; then 10 | echo "运行环境正确" 11 | else 12 | echo "您的会话正处于 proot 容器内, 请退出" 13 | exit 1 14 | fi 15 | 16 | # 检测是否安装过 17 | if [ -f "$ROOTFS_DIR/root/.bashrc" ]; then 18 | echo -e "现在可以执行 ./$ROOTFS_DIR.sh 运行 $ROOTFS_DIR系统" 19 | exit 1 20 | fi 21 | 22 | # Fork from https://github.com/termux/proot-distro 23 | setup_fake_proc() { 24 | mkdir -p "$ROOTFS_DIR/etc/proc" 25 | chmod 700 "$ROOTFS_DIR/etc/proc" 26 | 27 | if [ ! -f "$ROOTFS_DIR/etc/proc/.loadavg" ]; then 28 | cat <<- EOF > "$ROOTFS_DIR/etc/proc/.loadavg" 29 | 0.12 0.07 0.02 2/165 765 30 | EOF 31 | fi 32 | 33 | if [ ! -f "$ROOTFS_DIR/etc/proc/.stat" ]; then 34 | cat <<- EOF > "$ROOTFS_DIR/etc/proc/.stat" 35 | cpu 1957 0 2877 93280 262 342 254 87 0 0 36 | cpu0 31 0 226 12027 82 10 4 9 0 0 37 | cpu1 45 0 664 11144 21 263 233 12 0 0 38 | cpu2 494 0 537 11283 27 10 3 8 0 0 39 | cpu3 359 0 234 11723 24 26 5 7 0 0 40 | cpu4 295 0 268 11772 10 12 2 12 0 0 41 | cpu5 270 0 251 11833 15 3 1 10 0 0 42 | cpu6 430 0 520 11386 30 8 1 12 0 0 43 | cpu7 30 0 172 12108 50 8 1 13 0 0 44 | intr 127541 38 290 0 0 0 0 4 0 1 0 0 25329 258 0 5777 277 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 45 | ctxt 140223 46 | btime 1680020856 47 | processes 772 48 | procs_running 2 49 | procs_blocked 0 50 | softirq 75663 0 5903 6 25375 10774 0 243 11685 0 21677 51 | EOF 52 | fi 53 | 54 | if [ ! -f "$ROOTFS_DIR/etc/proc/.uptime" ]; then 55 | cat <<- EOF > "$ROOTFS_DIR/etc/proc/.uptime" 56 | 124.08 932.80 57 | EOF 58 | fi 59 | 60 | if [ ! -f "$ROOTFS_DIR/etc/proc/.version" ]; then 61 | cat <<- EOF > "$ROOTFS_DIR/etc/proc/.version" 62 | Linux version ${DEFAULT_FAKE_KERNEL_VERSION} (proot@termux) (gcc (GCC) 12.2.1 20230201, GNU ld (GNU Binutils) 2.40) #1 SMP PREEMPT_DYNAMIC Wed, 01 Mar 2023 00:00:00 +0000 63 | EOF 64 | fi 65 | 66 | if [ ! -f "$ROOTFS_DIR/etc/proc/.vmstat" ]; then 67 | cat <<- EOF > "$ROOTFS_DIR/etc/proc/.vmstat" 68 | nr_free_pages 1743136 69 | nr_zone_inactive_anon 179281 70 | nr_zone_active_anon 7183 71 | nr_zone_inactive_file 22858 72 | nr_zone_active_file 51328 73 | nr_zone_unevictable 642 74 | nr_zone_write_pending 0 75 | nr_mlock 0 76 | nr_bounce 0 77 | nr_zspages 0 78 | nr_free_cma 0 79 | numa_hit 1259626 80 | numa_miss 0 81 | numa_foreign 0 82 | numa_interleave 720 83 | numa_local 1259626 84 | numa_other 0 85 | nr_inactive_anon 179281 86 | nr_active_anon 7183 87 | nr_inactive_file 22858 88 | nr_active_file 51328 89 | nr_unevictable 642 90 | nr_slab_reclaimable 8091 91 | nr_slab_unreclaimable 7804 92 | nr_isolated_anon 0 93 | nr_isolated_file 0 94 | workingset_nodes 0 95 | workingset_refault_anon 0 96 | workingset_refault_file 0 97 | workingset_activate_anon 0 98 | workingset_activate_file 0 99 | workingset_restore_anon 0 100 | workingset_restore_file 0 101 | workingset_nodereclaim 0 102 | nr_anon_pages 7723 103 | nr_mapped 8905 104 | nr_file_pages 253569 105 | nr_dirty 0 106 | nr_writeback 0 107 | nr_writeback_temp 0 108 | nr_shmem 178741 109 | nr_shmem_hugepages 0 110 | nr_shmem_pmdmapped 0 111 | nr_file_hugepages 0 112 | nr_file_pmdmapped 0 113 | nr_anon_transparent_hugepages 1 114 | nr_vmscan_write 0 115 | nr_vmscan_immediate_reclaim 0 116 | nr_dirtied 0 117 | nr_written 0 118 | nr_throttled_written 0 119 | nr_kernel_misc_reclaimable 0 120 | nr_foll_pin_acquired 0 121 | nr_foll_pin_released 0 122 | nr_kernel_stack 2780 123 | nr_page_table_pages 344 124 | nr_sec_page_table_pages 0 125 | nr_swapcached 0 126 | pgpromote_success 0 127 | pgpromote_candidate 0 128 | nr_dirty_threshold 356564 129 | nr_dirty_background_threshold 178064 130 | pgpgin 890508 131 | pgpgout 0 132 | pswpin 0 133 | pswpout 0 134 | pgalloc_dma 272 135 | pgalloc_dma32 261 136 | pgalloc_normal 1328079 137 | pgalloc_movable 0 138 | pgalloc_device 0 139 | allocstall_dma 0 140 | allocstall_dma32 0 141 | allocstall_normal 0 142 | allocstall_movable 0 143 | allocstall_device 0 144 | pgskip_dma 0 145 | pgskip_dma32 0 146 | pgskip_normal 0 147 | pgskip_movable 0 148 | pgskip_device 0 149 | pgfree 3077011 150 | pgactivate 0 151 | pgdeactivate 0 152 | pglazyfree 0 153 | pgfault 176973 154 | pgmajfault 488 155 | pglazyfreed 0 156 | pgrefill 0 157 | pgreuse 19230 158 | pgsteal_kswapd 0 159 | pgsteal_direct 0 160 | pgsteal_khugepaged 0 161 | pgdemote_kswapd 0 162 | pgdemote_direct 0 163 | pgdemote_khugepaged 0 164 | pgscan_kswapd 0 165 | pgscan_direct 0 166 | pgscan_khugepaged 0 167 | pgscan_direct_throttle 0 168 | pgscan_anon 0 169 | pgscan_file 0 170 | pgsteal_anon 0 171 | pgsteal_file 0 172 | zone_reclaim_failed 0 173 | pginodesteal 0 174 | slabs_scanned 0 175 | kswapd_inodesteal 0 176 | kswapd_low_wmark_hit_quickly 0 177 | kswapd_high_wmark_hit_quickly 0 178 | pageoutrun 0 179 | pgrotated 0 180 | drop_pagecache 0 181 | drop_slab 0 182 | oom_kill 0 183 | numa_pte_updates 0 184 | numa_huge_pte_updates 0 185 | numa_hint_faults 0 186 | numa_hint_faults_local 0 187 | numa_pages_migrated 0 188 | pgmigrate_success 0 189 | pgmigrate_fail 0 190 | thp_migration_success 0 191 | thp_migration_fail 0 192 | thp_migration_split 0 193 | compact_migrate_scanned 0 194 | compact_free_scanned 0 195 | compact_isolated 0 196 | compact_stall 0 197 | compact_fail 0 198 | compact_success 0 199 | compact_daemon_wake 0 200 | compact_daemon_migrate_scanned 0 201 | compact_daemon_free_scanned 0 202 | htlb_buddy_alloc_success 0 203 | htlb_buddy_alloc_fail 0 204 | cma_alloc_success 0 205 | cma_alloc_fail 0 206 | unevictable_pgs_culled 27002 207 | unevictable_pgs_scanned 0 208 | unevictable_pgs_rescued 744 209 | unevictable_pgs_mlocked 744 210 | unevictable_pgs_munlocked 744 211 | unevictable_pgs_cleared 0 212 | unevictable_pgs_stranded 0 213 | thp_fault_alloc 13 214 | thp_fault_fallback 0 215 | thp_fault_fallback_charge 0 216 | thp_collapse_alloc 4 217 | thp_collapse_alloc_failed 0 218 | thp_file_alloc 0 219 | thp_file_fallback 0 220 | thp_file_fallback_charge 0 221 | thp_file_mapped 0 222 | thp_split_page 0 223 | thp_split_page_failed 0 224 | thp_deferred_split_page 1 225 | thp_split_pmd 1 226 | thp_scan_exceed_none_pte 0 227 | thp_scan_exceed_swap_pte 0 228 | thp_scan_exceed_share_pte 0 229 | thp_split_pud 0 230 | thp_zero_page_alloc 0 231 | thp_zero_page_alloc_failed 0 232 | thp_swpout 0 233 | thp_swpout_fallback 0 234 | balloon_inflate 0 235 | balloon_deflate 0 236 | balloon_migrate 0 237 | swap_ra 0 238 | swap_ra_hit 0 239 | ksm_swpin_copy 0 240 | cow_ksm 0 241 | zswpin 0 242 | zswpout 0 243 | direct_map_level2_splits 29 244 | direct_map_level3_splits 0 245 | nr_unstable 0 246 | EOF 247 | fi 248 | 249 | if [ ! -f "$ROOTFS_DIR/etc/proc/.sysctl_entry_cap_last_cap" ]; then 250 | cat <<- EOF > "$ROOTFS_DIR/etc/proc/.sysctl_entry_cap_last_cap" 251 | 40 252 | EOF 253 | fi 254 | 255 | if [ ! -f "$ROOTFS_DIR/etc/proc/.sysctl_entry_cap_last_cap" ]; then 256 | cat <<- EOF > "$ROOTFS_DIR/etc/proc/.sysctl_entry_cap_last_cap" 257 | 40 258 | EOF 259 | fi 260 | 261 | if [ ! -f "$ROOTFS_DIR/etc/proc/.bus/input/devices" ]; then 262 | mkdir -p "$ROOTFS_DIR/etc/proc/.bus/input" 263 | cat <<- EOF > "$ROOTFS_DIR/etc/proc/.bus/input/devices" 264 | I: Bus=0019 Vendor=0000 Product=0001 Version=0000 265 | N: Name="Power Button" 266 | P: Phys=LNXPWRBN/button/input0 267 | S: Sysfs=/devices/LNXSYSTM:00/LNXPWRBN:00/input/input0 268 | U: Uniq= 269 | H: Handlers=kbd event0 270 | B: PROP=0 271 | B: EV=3 272 | B: KEY=10000000000000 0 273 | 274 | I: Bus=0003 Vendor=0627 Product=0001 Version=0001 275 | N: Name="QEMU QEMU USB Tablet" 276 | P: Phys=usb-0000:00:01.2-1/input0 277 | S: Sysfs=/devices/pci0000:00/0000:00:01.2/usb1/1-1/1-1:1.0/0003:0627:0001.0001/input/input1 278 | U: Uniq=28754-0000:00:01.2-1 279 | H: Handlers=mouse0 event1 js0 280 | B: PROP=0 281 | B: EV=1f 282 | B: KEY=70000 0 0 0 0 283 | B: REL=100 284 | B: ABS=3 285 | B: MSC=10 286 | 287 | I: Bus=0011 Vendor=0001 Product=0001 Version=ab41 288 | N: Name="AT Translated Set 2 keyboard" 289 | P: Phys=isa0060/serio0/input0 290 | S: Sysfs=/devices/platform/i8042/serio0/input/input2 291 | U: Uniq= 292 | H: Handlers=kbd leds event2 293 | B: PROP=0 294 | B: EV=120013 295 | B: KEY=402000000 3803078f800d001 feffffdfffefffff fffffffffffffffe 296 | B: MSC=10 297 | B: LED=7 298 | 299 | I: Bus=0011 Vendor=0002 Product=0013 Version=0006 300 | N: Name="VirtualPS/2 VMware VMMouse" 301 | P: Phys=isa0060/serio1/input1 302 | S: Sysfs=/devices/platform/i8042/serio1/input/input5 303 | U: Uniq= 304 | H: Handlers=mouse1 event3 js1 305 | B: PROP=0 306 | B: EV=f 307 | B: KEY=70000 0 0 0 0 308 | B: REL=100 309 | B: ABS=3 310 | 311 | I: Bus=0011 Vendor=0002 Product=0013 Version=0006 312 | N: Name="VirtualPS/2 VMware VMMouse" 313 | P: Phys=isa0060/serio1/input0 314 | S: Sysfs=/devices/platform/i8042/serio1/input/input4 315 | U: Uniq= 316 | H: Handlers=mouse2 event4 317 | B: PROP=1 318 | B: EV=7 319 | B: KEY=30000 0 0 0 0 320 | B: REL=3 321 | 322 | I: Bus=0010 Vendor=001f Product=0001 Version=0100 323 | N: Name="PC Speaker" 324 | P: Phys=isa0061/input0 325 | S: Sysfs=/devices/platform/pcspkr/input/input6 326 | U: Uniq= 327 | H: Handlers=kbd event5 328 | B: PROP=0 329 | B: EV=40001 330 | B: SND=6 331 | 332 | I: Bus=0000 Vendor=0000 Product=0000 Version=0000 333 | N: Name="Android Power Button" 334 | P: Phys= 335 | S: Sysfs=/devices/virtual/input/input7 336 | U: Uniq= 337 | H: Handlers=kbd event6 338 | B: PROP=0 339 | B: EV=3 340 | B: KEY=8000 10000000000000 0 341 | EOF 342 | fi 343 | 344 | if [ ! -f "$ROOTFS_DIR/etc/proc/.modules" ]; then 345 | cat <<- EOF > "$ROOTFS_DIR/etc/proc/.modules" 346 | bluetooth 552960 0 - Live 0x0000000000000000 347 | ecdh_generic 24576 1 bluetooth, Live 0x0000000000000000 348 | tcp_diag 16384 0 - Live 0x0000000000000000 349 | inet_diag 24576 1 tcp_diag, Live 0x0000000000000000 350 | virt_wifi 20480 0 - Live 0x0000000000000000 351 | cfg80211 671744 1 virt_wifi, Live 0x0000000000000000 352 | sdcardfs 61440 191 - Live 0x0000000000000000 353 | parport_pc 24576 0 - Live 0x0000000000000000 354 | parport 32768 1 parport_pc, Live 0x0000000000000000 355 | crc32c_intel 24576 0 - Live 0x0000000000000000 356 | crc32_pclmul 16384 0 - Live 0x0000000000000000 357 | ghash_clmulni_intel 16384 0 - Live 0x0000000000000000 358 | e1000 139264 0 - Live 0x0000000000000000 359 | i2c_piix4 24576 0 - Live 0x0000000000000000 360 | 9pnet_virtio 20480 0 - Live 0x0000000000000000 361 | 9pnet 81920 1 9pnet_virtio, Live 0x0000000000000000 362 | pcspkr 16384 0 - Live 0x0000000000000000 363 | joydev 20480 0 - Live 0x0000000000000000 364 | psmouse 147456 0 - Live 0x0000000000000000 365 | mac_hid 16384 0 - Live 0x0000000000000000 366 | atkbd 28672 0 - Live 0x0000000000000000 367 | efi_pstore 16384 0 - Live 0x0000000000000000 368 | efivars 20480 1 efi_pstore, Live 0x0000000000000000 369 | EOF 370 | fi 371 | echo "为了兼容性考虑, 已将内核信息伪造成$DEFAULT_FAKE_KERNEL_VERSION" 372 | } 373 | setup_time_zone(){ 374 | echo "设置时区" 375 | sleep $SLEEP_TIME 376 | echo "export TZ='Asia/Shanghai'" >> $ROOTFS_DIR/root/.bashrc 377 | echo "export TZ='Asia/Shanghai'" >> $ROOTFS_DIR/etc/profile 378 | echo "export PULSE_SERVER=tcp:127.0.0.1:4173" >> $ROOTFS_DIR/etc/profile 379 | echo "export PULSE_SERVER=tcp:127.0.0.1:4173" >> $ROOTFS_DIR/root/.bashrc 380 | echo 检测到你没有权限读取/proc内的所有文件 381 | echo 将自动伪造新文件 382 | } 383 | update_dns(){ 384 | echo "更新DNS" 385 | sleep $SLEEP_TIME 386 | echo "127.0.0.1 localhost" > $ROOTFS_DIR/etc/hosts 387 | rm -rf $ROOTFS_DIR/etc/resolv.conf 388 | echo "nameserver 223.5.5.5 389 | nameserver 223.6.6.6 390 | nameserver 114.114.114.114" > $ROOTFS_DIR/etc/resolv.conf 391 | } 392 | 393 | get_distro_link(){ 394 | DATE=$(curl -SL "https://mirrors.bfsu.edu.cn/lxc-images/images/debian/$SYS_NAME/$AH/default" | \ 395 | grep -m 1 -o ' $PREFIX/etc/apt/sources.list 427 | apt update 428 | apt install proot -y 429 | } 430 | 431 | setup_start_script(){ 432 | echo "写入启动脚本" 433 | sleep $SLEEP_TIME 434 | echo "#!/bin/bash 435 | unset LD_PRELOAD 436 | proot \ 437 | --bind=/vendor \ 438 | --bind=/system \ 439 | --bind=/data/data/com.termux/files/usr \ 440 | --bind=/storage \ 441 | --bind=/storage/self/primary:/sdcard \ 442 | --bind=/data/data/com.termux/files/home \ 443 | --bind=/data/data/com.termux/cache \ 444 | --bind=/data/dalvik-cache \ 445 | --bind=$ROOTFS_DIR/tmp:/dev/shm \ 446 | --bind=$ROOTFS_DIR/etc/proc/.sysctl_entry_cap_last_cap:/proc/sys/kernel/cap_last_cap \ 447 | --bind=$ROOTFS_DIR/etc/proc/.vmstat:/proc/vmstat \ 448 | --bind=$ROOTFS_DIR/etc/proc/.version:/proc/version \ 449 | --bind=$ROOTFS_DIR/etc/proc/.uptime:/proc/uptime \ 450 | --bind=$ROOTFS_DIR/etc/proc/.stat:/proc/stat \ 451 | --bind=$ROOTFS_DIR/etc/proc/.loadavg:/proc/loadavg \ 452 | --bind=$ROOTFS_DIR/etc/proc/.bus/input/devices:/proc/bus/input/devices \ 453 | --bind=$ROOTFS_DIR/etc/proc/.modules:/proc/modules \ 454 | --bind=/sys \ 455 | --bind=/proc/self/fd/2:/dev/stderr \ 456 | --bind=/proc/self/fd/1:/dev/stdout \ 457 | --bind=/proc/self/fd/0:/dev/stdin \ 458 | --bind=/proc/self/fd:/dev/fd \ 459 | --bind=/proc \ 460 | --bind=/dev/urandom:/dev/random \ 461 | --bind=/data/data/com.termux/files/usr/tmp:/tmp \ 462 | --bind=/data/data/com.termux/files:$ROOTFS_DIR/termux \ 463 | --bind=/dev \ 464 | --root-id \ 465 | --cwd=/root \ 466 | -L \ 467 | --kernel-release=$DEFAULT_FAKE_KERNEL_VERSION \ 468 | --sysvipc \ 469 | --link2symlink \ 470 | --kill-on-exit \ 471 | --rootfs=$ROOTFS_DIR/ /usr/bin/env -i HOME=/root LANG=zh_CN.UTF-8 TERM=xterm-256color /bin/su -l root" > "$ROOTFS_DIR.sh" 472 | 473 | echo "授予启动脚本执行权限" 474 | chmod +x $ROOTFS_DIR.sh 475 | echo -e "现在可以执行 ./$ROOTFS_DIR.sh 运行 $ROOTFS_DIR系统" 476 | } 477 | 478 | # 安装依赖 479 | init_dependencies 480 | 481 | # 安装发行版本 482 | install_distro 483 | 484 | # 配置容器 485 | 486 | ## 更新DNS 487 | update_dns 488 | 489 | ## 设置时区 490 | setup_time_zone 491 | 492 | ## 伪造/proc 493 | setup_fake_proc 494 | 495 | ## 写入启动脚本 496 | setup_start_script --------------------------------------------------------------------------------