Compare commits

..

28 Commits

Author SHA1 Message Date
shenmo7192 89d17eb5f1 update src/var/lib/apm/apm/files/bin/ace-init.
Signed-off-by: shenmo <jifengshenmo@outlook.com>
2025-12-19 07:03:45 +00:00
shenmo7192 60ff1c1ec8 fix 报错 2025-12-19 08:34:04 +08:00
shenmo7192 3a8a8e2f14 dummy update 2025-12-19 08:32:41 +08:00
shenmo7192 270fa875f8 修正上游链接 2025-12-18 16:00:02 +08:00
shenmo7192 301079a999 add: apm 上游更新源 2025-12-18 15:56:03 +08:00
shenmo7192 705c16937d update doc 2025-12-18 15:27:12 +08:00
shenmo7192 869d11d351 version bump to 1.1.6 2025-12-18 15:22:18 +08:00
shenmo7192 3b25a62a54 支持info_env功能 2025-12-18 15:21:52 +08:00
shenmo7192 e373ae7bde 修复:在btrfs上convert时无法挂载多层layer 2025-12-11 10:12:04 +08:00
shenmo7192 6abdb10a7c update src/usr/bin/amber-pm-convert.
Signed-off-by: shenmo <jifengshenmo@outlook.com>
2025-12-09 09:16:14 +00:00
shenmo7192 9b1e435f4f Revert "update src/usr/bin/amber-pm-convert."
This reverts commit 61e747ba088d398c4e6401110803146e203f81aa.
2025-12-09 09:10:29 +00:00
shenmo7192 306416d2e4 update src/usr/bin/amber-pm-convert.
Signed-off-by: shenmo <jifengshenmo@outlook.com>
2025-12-03 08:27:54 +00:00
shenmo7192 1865d994ce update src/usr/bin/amber-pm-convert.
Signed-off-by: shenmo <jifengshenmo@outlook.com>
2025-12-03 05:36:35 +00:00
shenmo7192 b6bf96817e bump apm dummy version to 1.1.1
Signed-off-by: shenmo <jifengshenmo@outlook.com>
2025-11-28 14:01:32 +00:00
shenmo7192 6cfd4a9931 fix: Can't handle space line
Signed-off-by: shenmo <jifengshenmo@outlook.com>
2025-11-28 14:00:05 +00:00
shenmo7192 ddcd6ae421 新增 templates 直通
Signed-off-by: shenmo <jifengshenmo@outlook.com>
2025-11-27 08:36:01 +00:00
shenmo7192 b1f72c8984 update src/usr/bin/amber-pm-convert.
Signed-off-by: shenmo <jifengshenmo@outlook.com>
2025-11-27 07:12:03 +00:00
shenmo7192 891b9b3f52 update src/usr/bin/amber-pm-convert.
Signed-off-by: shenmo <jifengshenmo@outlook.com>
2025-11-27 07:04:09 +00:00
shenmo7192 609f2a051d update src/usr/bin/amber-pm-convert.
Signed-off-by: shenmo <jifengshenmo@outlook.com>
2025-11-26 02:46:02 +00:00
shenmo7192 08be97227d update src/usr/bin/amber-pm-convert.
Signed-off-by: shenmo <jifengshenmo@outlook.com>
2025-11-26 02:41:56 +00:00
shenmo7192 3a0094f2c3 适配 ACE
Signed-off-by: shenmo <jifengshenmo@outlook.com>
2025-11-25 12:10:23 +00:00
shenmo7192 d65c89b9e2 fix: 把错误的版本号传上来了 2025-11-23 20:18:54 +08:00
shenmo7192 866f8490bb fix: can not initialize apm 2025-11-21 15:55:04 +08:00
shenmo7192 35083b569f update README.md.
Signed-off-by: shenmo <jifengshenmo@outlook.com>
2025-11-21 07:43:39 +00:00
shenmo7192 3aaae488c8 新增功能: info_layer_override 2025-11-21 15:41:05 +08:00
shenmo7192 4d993ea308 AOSC Compatible : xz-utils
Signed-off-by: shenmo <jifengshenmo@outlook.com>
2025-11-21 07:12:29 +00:00
shenmo7192 5affba8f59 bump version to 115 2025-11-21 10:57:12 +08:00
shenmo7192 8b06b2a71f 不再频繁提示NVIDIA信息,添加autopurge相关的内容 2025-11-21 10:56:42 +08:00
16 changed files with 552 additions and 143 deletions
+291 -60
View File
@@ -1,22 +1,45 @@
# APM 软件包打包流程 # APM 软件包打包流程
本文档为开发者准备,若您只是想从 deb 软件包打包 APM 软件包,您可以通过 `amber-pm-convert`指令进行全自动一键转换 本文档为开发者准备,若您只是想从 deb 软件包打包 APM 软件包,您可以通过 `amber-pm-convert` 指令进行全自动一键转换
通过 `apm search amber-pm- ` 即可搜索到所有可用的 base 列表 通过 `apm search amber-pm-` 即可搜索到所有可用的 base 列表
--- ---
## APM 软件包结构规范 ## APM 软件包结构规范
在阅读前,请确保您对overlayfs有了基本的了解 在阅读前,请确保您对 OverlayFS 有了基本的了解
overlayfs 原理解析:https://www.cnblogs.com/arnoldlu/p/13055501.html
OverlayFS 原理解析:
[https://www.cnblogs.com/arnoldlu/p/13055501.html](https://www.cnblogs.com/arnoldlu/p/13055501.html)
--- ---
## OverlayFS 层叠顺序说明
一个典型的 APM 软件/中层依赖包应当包含以下内容 APM 使用 OverlayFS 来管理软件包的文件系统层级,从上到下的层叠顺序为:
1. **Upperdir**
当前包的可写层:`files/core/`
2. **Info Layer Override**
`info_layer_override` 指定的覆盖层,位于所有依赖层之上
3. **依赖层**
`info` 文件递归解析出的所有依赖包
4. **底层 Runtime**
最基础的运行时环境(如 `amber-pm-bookworm`
这种层叠结构允许上层文件覆盖下层文件,实现灵活、高效的依赖管理与环境定制。
---
## APM 软件包目录结构示例
一个典型的 APM 应用或中层依赖包应当包含以下内容:
``` ```
├── DEBIAN ├── DEBIAN
@@ -35,15 +58,17 @@ overlayfs 原理解析:https://www.cnblogs.com/arnoldlu/p/13055501.html
│ ├── core │ ├── core
│ └── work │ └── work
├── info ├── info
── info_debug ── info_layer_override # 可选
└── info_env # 可选(高级功能)
``` ```
* DEBIAN目录包含了软件包的基本信息和依赖的环境信息 ---
1. 以下是 control 文件的内容 ## DEBIAN 目录说明
包含软件包的基本信息和依赖环境声明。
### control 文件示例
``` ```
Package: eom Package: eom
@@ -53,21 +78,33 @@ Maintainer: APM Converter <apm-convert@spark-app.store>
Depends: amber-pm-bookworm Depends: amber-pm-bookworm
Installed-Size: 45228 Installed-Size: 45228
Description: APM converted package from eom Description: APM converted package from eom
This package was automatically converted from the original deb package. This package was automatically converted from the original deb package.
Based on: amber-pm-bookworm Based on: amber-pm-bookworm
``` ```
Package: 包名。应当唯一。若使用转换器进行转换,默认和原包名一致 字段说明:
Version: 版本号。若使用转换器进行转换,默认在原版本号后加`-apm`
Architecture: 软件包架构。同 dpkg 进行填写即可。若使用转换器进行转换,默认和原包架构一致
Depends: 依赖包。填写直接依赖的base即可
Installed-Size: 安装后的大小。若使用转换器进行转换,会自动填写
Description: 包描述。若使用转换器进行转换,会自动填写
* **Package**
包名,应当唯一。使用转换器时默认与原 deb 包名一致
2. 以下是 postinst 文件内容 * **Version**
软件包版本号,转换器会自动追加 `-apm`
* **Architecture**
架构信息,遵循 dpkg 规范
* **Depends**
直接依赖的 base 包名
* **Installed-Size**
安装后大小,转换器自动计算
* **Description**
软件包描述信息
---
### postinst 文件
``` ```
#!/bin/bash #!/bin/bash
@@ -76,74 +113,268 @@ PACKAGE_NAME="$DPKG_MAINTSCRIPT_PACKAGE"
if [ "$1" = "remove" ] || [ "$1" = "purge" ]; then if [ "$1" = "remove" ] || [ "$1" = "purge" ]; then
echo "清理卸载残留" echo "清理卸载残留"
rm -rf "/var/lib/apm/$PACKAGE_NAME" rm -rf "/var/lib/apm/$PACKAGE_NAME"
for username in $(ls /home)
do for username in $(ls /home); do
echo /home/$username if [ -d "/home/$username/.apm/$PACKAGE_NAME" ]; then
if [ -d "/home/$username/.apm/$PACKAGE_NAME" ] rm -rf "/home/$username/.apm/$PACKAGE_NAME"
then
rm -fr "/home/$username/.apm/$PACKAGE_NAME"
fi fi
done done
else else
echo "非卸载,跳过清理" echo "非卸载,跳过清理"
fi fi
```
若无特殊需求,保持该内容即可,用于卸载时清理残留环境。
---
## /var/lib/apm 目录结构说明
该目录包含 APM 软件包的运行环境与元数据。
### 必须目录
* **files/**
* `core/`upperdir,可写层
* `work/`OverlayFS 工作目录
* **info**
* 声明直接依赖的 base 包
* 支持多层递归解析
### 可选目录 / 文件
* **entries/**
* `applications/``.desktop` 文件
* `doc/`:文档
* `glib-2.0/`GLib 相关文件
* `man/`:手册页
> ⚠ `.desktop` 文件中 **必须** 添加:
>
> ```
> X-APM-APPID=包名
> ```
>
> 以允许软件管理器正确识别和管理应用。
---
## info 文件说明(依赖解析)
`info` 文件用于声明当前包直接依赖的 base 包,每行一个包名:
``` ```
若无特殊需求,内容保持一致即可,用于在卸载软件包后清理环境 amber-pm-bookworm-spark-wine10
```
* /var/lib/apm 包含了APM 软件容器的文件和信息 APM 会递归解析该 base 的 `info` 文件,直到找到最底层 runtime(如 `amber-pm-bookworm`)。
> 使用多层依赖并非强制,但合理拆分 base 能显著减小包体积。
> 可用的 base 列表可通过:
>
> ```
> apm search amber-pm-
> ```
>
> 查看。
---
软件应当被放置在 /var/lib/apm/软件包名/ 处 ## info_layer_override 文件(覆盖层)
此处有两个目录,两个文件
entries 可选,包含了软件包需要被放到 /usr/share/ 的文件,如 desktop icon 等 `info_layer_override` 是一个可选文件,用于在**所有依赖层之上**插入额外覆盖层。
files 必须,包含了软件包的 upperdir 和 workdir
info 必须,包含了直接依赖的base信息。若应用使用了多层的依赖,会一层一层寻找info信息,直到找到底层依赖
info_debug 可选,包含了打包时解析的依赖信息
entries下的内容同软件需要放置到 /usr/share/ 下的内容 ### 使用场景
> 注意: .desktop 文件应当新加一行 X-APM-APPID=包名 来允许软件管理器管理 1. 覆盖依赖中的特定库版本(如 mesa)
2. 覆盖默认配置文件
3. 提供特殊运行环境
files的内容请见下一节 ### 规则说明
## APM upperdir 制作流程 * 语法与 `info` 完全一致
* 每行一个包名
* 层级位置:
以下为手动制作 upperdir 的流程 ```
upperdir
info_layer_override
info 递归依赖
```
首先,安装 apm 并使用`sudo apm install` 安装你所需要的 base ### 示例
随后,新建三个文件夹,corework 和 ace-env ,执行 `info`
`sudo mount -t overlay overlay -o lowerdir='/var/lib/apm/apm/files/ace-env/var/lib/apm/base包的包名(如amber-pm-trixie/files/ace-env',upperdir=core/,workdir=work/ ./ace-env` ```
amber-pm-bookworm
```
随后chroot进入进行安装操作,直接进行 apt install 或者其他都可以,完成后解除挂载 ./ace-env `info_layer_override`
你便得到了: ```
amber-pm-bookworm-mesa
```
* core: 保存新增文件 最终 lowerdir 顺序:
* work: 保存变更信息
```
amber-pm-bookworm-mesa:amber-pm-bookworm
```
需把这两个目录重新拥有并权限换成755后放入对应的目录进行 apm 打包 ---
你也可以测试一下刚刚打包的软件 ## info_env(环境变量层 · 高级功能)
fuse-overlayfs -o lowerdir='/var/lib/apm/apm/files/ace-env/var/lib/apm/base包的包名(如amber-pm-trixie/files/ace-env',upperdir=core/,workdir=work/ ./ace-env `info_env` 是一个 **可选的高级特性**,用于为 APM 容器运行时提供**分层的环境变量配置能力**。
即可只读挂载。这一步 apm run 包名 会帮你做好。 ### 功能概述
> apm run 包名: 寻找 /var/lib/apm/包名/是否存在。若存在,根据info文件合成 fuser-overlayfs 参数进行挂载,随后用ACE工具chroot进入进行启动 * 为软件包及其依赖提供环境变量
* 支持 **多层叠加**
* **上层自动覆盖下层**
* 与 OverlayFS 层级顺序完全一致
* 不执行 shell 代码,仅解析键值对,安全可靠
./ace-run 即可进入,可以尝试启动一下刚刚安装的应用 ---
## APM 打包 ### info_env 文件位置
使用 `dpkg-deb --build 软件包目录 输出目录` 即可进行打包 ```
/var/lib/apm/<包名>/info_env
```
## APM 底层 Base Runtime 的构建 ---
### info_env 应用顺序(重要)
环境变量的加载顺序为:
1. 底层 runtime 的 `info_env`
2. 中间依赖包的 `info_env`
3. 当前包的 `info_env`
4. `info_layer_override` 中包的 `info_env`(最高优先级)
**后加载的变量会覆盖之前的同名变量。**
---
### info_env 文件格式
每行一条环境变量定义:
```
KEY=VALUE
```
示例:
```
QT_QPA_PLATFORM=dxcb;xcb
LANG=zh_CN.UTF-8
XMODIFIERS="@im=fcitx"
PATH="/custom/bin:$PATH"
```
#### 规则说明
* 支持分号 `;`
* 支持带引号的值
* 支持引用已有环境变量(如 `$PATH`
* 支持注释行(`#`
* 不允许执行任何 shell 语句
❌ 以下内容将被忽略:
```
export A=1
rm -rf /
$(whoami)
```
---
### 使用场景示例
* 指定 Qt / GTK 平台插件
* 设置输入法变量
* 调整运行时 PATH / LD_LIBRARY_PATH
* 为特定应用注入兼容性环境变量
---
## APM upperdir 制作流程(手动)
1. 安装 APM 并安装所需 base
```bash
sudo apm install amber-pm-xxx
```
2. 创建目录结构:
```bash
mkdir -p core work ace-env
```
3. 挂载 OverlayFS
```bash
sudo mount -t overlay overlay \
-o lowerdir='/var/lib/apm/apm/files/ace-env/var/lib/apm/amber-pm-xxx/files/ace-env',upperdir=core/,workdir=work/ \
./ace-env
```
4. chroot 进入 `ace-env` 进行安装
5. 卸载并打包
---
## APM 软件包测试
```bash
fuse-overlayfs -o lowerdir='...',upperdir=core/,workdir=work/ ./ace-env
```
或直接使用:
```bash
apm run 包名
```
APM 会自动完成:
* 解析 `info` / `info_layer_override`
* 应用 `info_env`
* 构建 OverlayFS
* 进入容器并运行应用
---
## APM 软件包打包
```bash
dpkg-deb --build 软件包目录 输出目录
```
---
## APM 底层 Base Runtime 构建
详见:
[https://gitee.com/amber-ce/amber-pm-common](https://gitee.com/amber-ce/amber-pm-common)
---
### 备注
APM 的打包工具与转换器会自动处理绝大多数复杂操作。
手动打包与 `info_env` 主要用于 **特殊运行环境、深度定制或调试用途**
详见 https://gitee.com/amber-ce/amber-pm-common
+2
View File
@@ -91,6 +91,8 @@ Commands:
详见 [Packaging-demo](Packaging-demo)。 详见 [Packaging-demo](Packaging-demo)。
> 1.1.5+ 版本支持了覆盖 base 功能,相见 https://gitee.com/amber-ce/amber-pm/blob/master/Packaging-demo/README.md#info_layer_override-%E6%96%87%E4%BB%B6
## APM 构建 Tips ## APM 构建 Tips
> 请 `cp -vr src pkg` 来创建一个准备配置的环境,随后 `./build.sh pkg` 即可进行进一步的打包操作 > 请 `cp -vr src pkg` 来创建一个准备配置的环境,随后 `./build.sh pkg` 即可进行进一步的打包操作
+1 -1
View File
@@ -1,5 +1,5 @@
Package: apm Package: apm
Version: 1.1 Version: 1.1.2
Maintainer: shenmo <jifengshenmo@outlook.com> Maintainer: shenmo <jifengshenmo@outlook.com>
Priority: optional Priority: optional
Section: utils Section: utils
+2 -2
View File
@@ -30,7 +30,7 @@ linkDir() {
ensureTargetDir "$targetFile" ensureTargetDir "$targetFile"
sourceFile=$(realpath --relative-to="$(dirname $targetFile)" "$sourceFile" ) sourceFile=$(realpath --relative-to="$(dirname $targetFile)" "$sourceFile" )
if [ ! -e ${targetFile} ];then if [ ! -e "${targetFile}" ];then
ln -sv "$sourceFile" "$targetFile" ln -sv "$sourceFile" "$targetFile"
fi fi
done done
@@ -98,7 +98,7 @@ function exec_link_clean(){
find /usr/share/fcitx -xtype l -exec echo '{} is invalid now and going to be cleaned' \; -exec unlink {} \; 2>/dev/null & find /usr/share/fcitx -xtype l -exec echo '{} is invalid now and going to be cleaned' \; -exec unlink {} \; 2>/dev/null &
find /usr/share/help -xtype l -exec echo '{} is invalid now and going to be cleaned' \; -exec unlink {} \; 2>/dev/null & find /usr/share/help -xtype l -exec echo '{} is invalid now and going to be cleaned' \; -exec unlink {} \; 2>/dev/null &
find /usr/share/locale -xtype l -exec echo '{} is invalid now and going to be cleaned' \; -exec unlink {} \; 2>/dev/null & find /usr/share/locale -xtype l -exec echo '{} is invalid now and going to be cleaned' \; -exec unlink {} \; 2>/dev/null &
find /usr/lib/$(gcc -dumpmachine)/fcitx -xtype l -exec echo '{} is invalid now and going to be cleaned' \; -exec unlink {} \; 2>/dev/null & # find /usr/lib/$(gcc -dumpmachine)/fcitx -xtype l -exec echo '{} is invalid now and going to be cleaned' \; -exec unlink {} \; 2>/dev/null &
find /usr/lib/mozilla/plugins -xtype l -exec echo '{} is invalid now and going to be cleaned' \; -exec unlink {} \; 2>/dev/null & find /usr/lib/mozilla/plugins -xtype l -exec echo '{} is invalid now and going to be cleaned' \; -exec unlink {} \; 2>/dev/null &
find /usr/share/polkit-1/actions -xtype l -exec echo '{} is invalid now and going to be cleaned' \; -exec unlink {} \; 2>/dev/null & find /usr/share/polkit-1/actions -xtype l -exec echo '{} is invalid now and going to be cleaned' \; -exec unlink {} \; 2>/dev/null &
find /usr/share/fonts -xtype l -exec echo '{} is invalid now and going to be cleaned' \; -exec unlink {} \; 2>/dev/null & find /usr/share/fonts -xtype l -exec echo '{} is invalid now and going to be cleaned' \; -exec unlink {} \; 2>/dev/null &
+1 -1
View File
@@ -1 +1 @@
@VERSION@=1.1.4 @VERSION@=1.1.6
+1 -1
View File
@@ -4,7 +4,7 @@ Version: @VERSION@
Architecture: amd64 Architecture: amd64
Maintainer: shenmo <shenmo@spark-app.store> Maintainer: shenmo <shenmo@spark-app.store>
Installed-Size: 49000 Installed-Size: 49000
Depends: bubblewrap, flatpak, policykit-1 | pkexec | polkit-1 | polkit, systemd, procps,coreutils,fuse-overlayfs,xz-utils,libnotify-bin,curl,xdg-user-dirs,bash Depends: bubblewrap, flatpak, policykit-1 | pkexec | polkit-1 | polkit, systemd, procps,coreutils,fuse-overlayfs,xz-utils | xz,libnotify-bin,curl,xdg-user-dirs,bash
Recommends: dpkg, fakeroot, busybox Recommends: dpkg, fakeroot, busybox
Section: misc Section: misc
Conflicts: ace-host-integration Conflicts: ace-host-integration
+2
View File
@@ -0,0 +1,2 @@
deb [signed-by=/etc/apt/trusted.gpg.d/apm.gpg] https://d.spark-app.store/apm-deb-source /
# 上面这行配置可在4.1.2+版本普及后启用,可以做到分不同目录
Binary file not shown.
+101 -20
View File
@@ -233,7 +233,7 @@ log.debug "最终 lowerdir: $LOWERDIR"
# 3. 进行融合挂载 # 3. 进行融合挂载
log.info "正在进行融合挂载..." log.info "正在进行融合挂载..."
sudo mount -t overlay overlay \ sudo fuse-overlayfs \
-o "lowerdir=$LOWERDIR,upperdir=$CRAFT_DIR/core/,workdir=$CRAFT_DIR/work/" \ -o "lowerdir=$LOWERDIR,upperdir=$CRAFT_DIR/core/,workdir=$CRAFT_DIR/work/" \
"$CRAFT_DIR/mergedir" "$CRAFT_DIR/mergedir"
@@ -322,6 +322,7 @@ resolve_symlink() {
echo "$file" echo "$file"
} }
# 函数:交互式选择文件复制到entries目录(用于手动模式无DEB情况)
# 函数:交互式选择文件复制到entries目录(用于手动模式无DEB情况) # 函数:交互式选择文件复制到entries目录(用于手动模式无DEB情况)
interactive_copy_entries() { interactive_copy_entries() {
local core_dir="$CRAFT_DIR/core" local core_dir="$CRAFT_DIR/core"
@@ -330,13 +331,13 @@ interactive_copy_entries() {
log.info "开始交互式选择文件复制到 entries 目录..." log.info "开始交互式选择文件复制到 entries 目录..."
mkdir -p "$entries_dir/applications" "$entries_dir/icons" mkdir -p "$entries_dir/applications" "$entries_dir/icons"
# 查找桌面文件 # 查找桌面文件(保留完整路径)
local desktop_files=() local desktop_files=()
while IFS= read -r -d '' file; do while IFS= read -r -d '' file; do
[[ -f "$file" ]] && desktop_files+=("$file") [[ -f "$file" ]] && desktop_files+=("$file")
done < <(find "$core_dir/usr/share" -name "*.desktop" -print0 2>/dev/null || true) done < <(find "$core_dir/usr/share" -name "*.desktop" -print0 2>/dev/null || true)
# 查找图标文件 # 查找图标文件(保留完整路径)
local icon_files=() local icon_files=()
while IFS= read -r -d '' file; do while IFS= read -r -d '' file; do
[[ -f "$file" ]] && icon_files+=("$file") [[ -f "$file" ]] && icon_files+=("$file")
@@ -347,8 +348,9 @@ interactive_copy_entries() {
log.info "找到 ${#desktop_files[@]} 个桌面文件:" log.info "找到 ${#desktop_files[@]} 个桌面文件:"
for i in "${!desktop_files[@]}"; do for i in "${!desktop_files[@]}"; do
local file="${desktop_files[$i]}" local file="${desktop_files[$i]}"
local filename=$(basename "$file") # 显示完整路径(相对于 core_dir)
echo " $((i+1)). $filename" local relative_path="${file#$core_dir}"
echo " $((i+1)). $relative_path"
# 检查是否是符号链接 # 检查是否是符号链接
if [ -L "$file" ]; then if [ -L "$file" ]; then
@@ -357,7 +359,8 @@ interactive_copy_entries() {
# 解析符号链接获取实际文件 # 解析符号链接获取实际文件
local resolved_file=$(resolve_symlink "$file" "$core_dir") local resolved_file=$(resolve_symlink "$file" "$core_dir")
if [ "$resolved_file" != "$file" ] && [ -f "$resolved_file" ]; then if [ "$resolved_file" != "$file" ] && [ -f "$resolved_file" ]; then
echo " → 解析为: $(basename "$resolved_file")" local resolved_relative="${resolved_file#$core_dir}"
echo " → 解析为: $resolved_relative"
desktop_files[$i]="$resolved_file" desktop_files[$i]="$resolved_file"
fi fi
fi fi
@@ -367,10 +370,22 @@ interactive_copy_entries() {
read -r -p "请选择要复制的桌面文件编号(多个用逗号分隔,all=全部,none=跳过): " desktop_choice read -r -p "请选择要复制的桌面文件编号(多个用逗号分隔,all=全部,none=跳过): " desktop_choice
if [[ "$desktop_choice" =~ ^[Aa][Ll][Ll]$ ]]; then if [[ "$desktop_choice" =~ ^[Aa][Ll][Ll]$ ]]; then
# 复制所有桌面文件到 entries/applications # 复制所有桌面文件到 entries/applications,但保持目录结构
for file in "${desktop_files[@]}"; do for file in "${desktop_files[@]}"; do
local filename=$(basename "$file") local relative_path="${file#$core_dir}"
local dest_path="$entries_dir/applications/$filename" local dest_filename=$(basename "$file")
# 如果文件在 applications 目录下,直接复制到 entries/applications
if [[ "$relative_path" == /usr/share/applications/* ]]; then
local dest_path="$entries_dir/applications/$dest_filename"
else
# 其他位置的桌面文件,保持相对路径结构
local path_dir=$(dirname "$relative_path")
local dest_dir="$entries_dir/applications$path_dir"
mkdir -p "$dest_dir"
local dest_path="$dest_dir/$dest_filename"
fi
cp -v "$file" "$dest_path" cp -v "$file" "$dest_path"
# 处理桌面文件内容 # 处理桌面文件内容
@@ -384,8 +399,19 @@ interactive_copy_entries() {
if [[ "$choice" =~ ^[0-9]+$ ]] && [ "$choice" -ge 1 ] && [ "$choice" -le ${#desktop_files[@]} ]; then if [[ "$choice" =~ ^[0-9]+$ ]] && [ "$choice" -ge 1 ] && [ "$choice" -le ${#desktop_files[@]} ]; then
local idx=$((choice-1)) local idx=$((choice-1))
local file="${desktop_files[$idx]}" local file="${desktop_files[$idx]}"
local filename=$(basename "$file") local relative_path="${file#$core_dir}"
local dest_path="$entries_dir/applications/$filename" local dest_filename=$(basename "$file")
# 根据路径决定目标位置
if [[ "$relative_path" == /usr/share/applications/* ]]; then
local dest_path="$entries_dir/applications/$dest_filename"
else
local path_dir=$(dirname "$relative_path")
local dest_dir="$entries_dir/applications$path_dir"
mkdir -p "$dest_dir"
local dest_path="$dest_dir/$dest_filename"
fi
cp -v "$file" "$dest_path" cp -v "$file" "$dest_path"
# 处理桌面文件内容 # 处理桌面文件内容
@@ -406,8 +432,8 @@ interactive_copy_entries() {
log.info "找到 ${#icon_files[@]} 个图标文件:" log.info "找到 ${#icon_files[@]} 个图标文件:"
for i in "${!icon_files[@]}"; do for i in "${!icon_files[@]}"; do
local file="${icon_files[$i]}" local file="${icon_files[$i]}"
local filename=$(basename "$file") local relative_path="${file#$core_dir}"
echo " $((i+1)). $filename" echo " $((i+1)). $relative_path"
# 检查是否是符号链接 # 检查是否是符号链接
if [ -L "$file" ]; then if [ -L "$file" ]; then
@@ -416,7 +442,8 @@ interactive_copy_entries() {
# 解析符号链接获取实际文件 # 解析符号链接获取实际文件
local resolved_file=$(resolve_symlink "$file" "$core_dir") local resolved_file=$(resolve_symlink "$file" "$core_dir")
if [ "$resolved_file" != "$file" ] && [ -f "$resolved_file" ]; then if [ "$resolved_file" != "$file" ] && [ -f "$resolved_file" ]; then
echo " → 解析为: $(basename "$resolved_file")" local resolved_relative="${resolved_file#$core_dir}"
echo " → 解析为: $resolved_relative"
icon_files[$i]="$resolved_file" icon_files[$i]="$resolved_file"
fi fi
fi fi
@@ -426,10 +453,23 @@ interactive_copy_entries() {
read -r -p "请选择要复制的图标文件编号(多个用逗号分隔,all=全部,none=跳过): " icon_choice read -r -p "请选择要复制的图标文件编号(多个用逗号分隔,all=全部,none=跳过): " icon_choice
if [[ "$icon_choice" =~ ^[Aa][Ll][Ll]$ ]]; then if [[ "$icon_choice" =~ ^[Aa][Ll][Ll]$ ]]; then
# 复制所有图标文件到 entries/icons # 复制所有图标文件到 entries/icons,保持目录结构
for file in "${icon_files[@]}"; do for file in "${icon_files[@]}"; do
local filename=$(basename "$file") local relative_path="${file#$core_dir}"
local dest_path="$entries_dir/icons/$filename" local dest_filename=$(basename "$file")
# 如果文件在 icons 主题目录下,直接复制到 entries/icons
if [[ "$relative_path" == /usr/share/icons/* ]] ||
[[ "$relative_path" == /usr/share/pixmaps/* ]]; then
local dest_path="$entries_dir/icons/$dest_filename"
else
# 其他位置的图标文件,保持相对路径结构
local path_dir=$(dirname "$relative_path")
local dest_dir="$entries_dir/icons$path_dir"
mkdir -p "$dest_dir"
local dest_path="$dest_dir/$dest_filename"
fi
cp -v "$file" "$dest_path" cp -v "$file" "$dest_path"
done done
elif [[ ! "$icon_choice" =~ ^[Nn][Oo][Nn][Ee]$ ]] && [ -n "$icon_choice" ]; then elif [[ ! "$icon_choice" =~ ^[Nn][Oo][Nn][Ee]$ ]] && [ -n "$icon_choice" ]; then
@@ -440,8 +480,20 @@ interactive_copy_entries() {
if [[ "$choice" =~ ^[0-9]+$ ]] && [ "$choice" -ge 1 ] && [ "$choice" -le ${#icon_files[@]} ]; then if [[ "$choice" =~ ^[0-9]+$ ]] && [ "$choice" -ge 1 ] && [ "$choice" -le ${#icon_files[@]} ]; then
local idx=$((choice-1)) local idx=$((choice-1))
local file="${icon_files[$idx]}" local file="${icon_files[$idx]}"
local filename=$(basename "$file") local relative_path="${file#$core_dir}"
local dest_path="$entries_dir/icons/$filename" local dest_filename=$(basename "$file")
# 根据路径决定目标位置
if [[ "$relative_path" == /usr/share/icons/* ]] ||
[[ "$relative_path" == /usr/share/pixmaps/* ]]; then
local dest_path="$entries_dir/icons/$dest_filename"
else
local path_dir=$(dirname "$relative_path")
local dest_dir="$entries_dir/icons$path_dir"
mkdir -p "$dest_dir"
local dest_path="$dest_dir/$dest_filename"
fi
cp -v "$file" "$dest_path" cp -v "$file" "$dest_path"
else else
log.warn "无效的选择: $choice" log.warn "无效的选择: $choice"
@@ -456,13 +508,39 @@ interactive_copy_entries() {
} }
# 函数:处理桌面文件内容 # 函数:处理桌面文件内容
# 函数:处理桌面文件内容(安全版本,避免重复处理)
process_desktop_file() { process_desktop_file() {
local desktop_file="$1" local desktop_file="$1"
local pkgname="$2" local pkgname="$2"
# 新增:精确路径检查
local apps_path1="/usr/share/applications"
local apps_path2="/opt/apps/${ORIG_PKGNAME}/entries/applications"
local apps_path3="/usr/local/share/applications"
if [[ ! "$desktop_file" =~ ^.*${apps_path1}/.*\.desktop$ ]] &&
[[ ! "$desktop_file" =~ ^.*${apps_path2}/.*\.desktop$ ]] &&
[[ ! "$desktop_file" =~ ^.*${apps_path3}/.*\.desktop$ ]]; then
log.debug "跳过非应用程序 desktop 文件: $desktop_file"
return 0
fi
log.info "处理桌面文件: $desktop_file" log.info "处理桌面文件: $desktop_file"
# 检查文件是否已经处理过(避免重复添加 apm run)
if grep -q "^Exec=apm run $pkgname " "$desktop_file"; then
log.info "桌面文件已经处理过,跳过: $desktop_file"
return 0
fi
# 检查是否有其他包的 apm run 前缀(清理旧的)
if grep -q "^Exec=apm run [^ ]* " "$desktop_file"; then
log.info "发现旧的 apm run 前缀,清理后重新添加"
# 移除所有 apm run 前缀
sed -i "s|^Exec=apm run [^ ]* ||" "$desktop_file"
fi
# 尝试用 busybox dos2unix(若不存在则跳过转换) # 尝试用 busybox dos2unix(若不存在则跳过转换)
if command -v busybox >/dev/null 2>&1; then if command -v busybox >/dev/null 2>&1; then
busybox dos2unix "$desktop_file" 2>/dev/null || true busybox dos2unix "$desktop_file" 2>/dev/null || true
@@ -486,8 +564,9 @@ process_desktop_file() {
sed -i "s|^Icon=/|Icon=/var/lib/apm/apm/files/ace-env/var/lib/apm/$pkgname/files/core/|" "$desktop_file" sed -i "s|^Icon=/|Icon=/var/lib/apm/apm/files/ace-env/var/lib/apm/$pkgname/files/core/|" "$desktop_file"
fi fi
# 添加 X-APM-APPID # 添加 X-APM-APPID(如果不存在)
if ! grep -q "X-APM-APPID" "$desktop_file"; then if ! grep -q "X-APM-APPID" "$desktop_file"; then
echo "" >> "$desktop_file"
echo "X-APM-APPID=$pkgname" >> "$desktop_file" echo "X-APM-APPID=$pkgname" >> "$desktop_file"
fi fi
@@ -499,6 +578,7 @@ process_desktop_file() {
fi fi
} }
# 4. 如果有 DEB 文件,进行自动化的检查、解包与修改 # 4. 如果有 DEB 文件,进行自动化的检查、解包与修改
if [ -n "$DEB_PATH" ]; then if [ -n "$DEB_PATH" ]; then
@@ -511,6 +591,7 @@ if [ -n "$DEB_PATH" ]; then
exit 1 exit 1
fi fi
log.info "安装前检查通过,准备进行提取与修改..." log.info "安装前检查通过,准备进行提取与修改..."
sudo -E chrootEnvPath="$chrootEnvPath" /var/lib/apm/apm/files/ace-run-pkg mkdir -p /var/cache/apt/archives/partial
# 提取 DEB 包内容并准备修改 # 提取 DEB 包内容并准备修改
log.info "提取并修改原DEB包..." log.info "提取并修改原DEB包..."
+2 -2
View File
@@ -30,7 +30,7 @@ linkDir() {
ensureTargetDir "$targetFile" ensureTargetDir "$targetFile"
sourceFile=$(realpath --relative-to="$(dirname $targetFile)" "$sourceFile" ) sourceFile=$(realpath --relative-to="$(dirname $targetFile)" "$sourceFile" )
if [ ! -e ${targetFile} ];then if [ ! -e "${targetFile}" ];then
ln -sv "$sourceFile" "$targetFile" ln -sv "$sourceFile" "$targetFile"
fi fi
done done
@@ -98,7 +98,7 @@ function exec_link_clean(){
find /usr/share/fcitx -xtype l -exec echo '{} is invalid now and going to be cleaned' \; -exec unlink {} \; 2>/dev/null & find /usr/share/fcitx -xtype l -exec echo '{} is invalid now and going to be cleaned' \; -exec unlink {} \; 2>/dev/null &
find /usr/share/help -xtype l -exec echo '{} is invalid now and going to be cleaned' \; -exec unlink {} \; 2>/dev/null & find /usr/share/help -xtype l -exec echo '{} is invalid now and going to be cleaned' \; -exec unlink {} \; 2>/dev/null &
find /usr/share/locale -xtype l -exec echo '{} is invalid now and going to be cleaned' \; -exec unlink {} \; 2>/dev/null & find /usr/share/locale -xtype l -exec echo '{} is invalid now and going to be cleaned' \; -exec unlink {} \; 2>/dev/null &
find /usr/lib/`dpkg-architecture -qDEB_HOST_MULTIARCH`/fcitx -xtype l -exec echo '{} is invalid now and going to be cleaned' \; -exec unlink {} \; 2>/dev/null & # find /usr/lib/$(gcc -dumpmachine)/fcitx -xtype l -exec echo '{} is invalid now and going to be cleaned' \; -exec unlink {} \; 2>/dev/null &
find /usr/lib/mozilla/plugins -xtype l -exec echo '{} is invalid now and going to be cleaned' \; -exec unlink {} \; 2>/dev/null & find /usr/lib/mozilla/plugins -xtype l -exec echo '{} is invalid now and going to be cleaned' \; -exec unlink {} \; 2>/dev/null &
find /usr/share/polkit-1/actions -xtype l -exec echo '{} is invalid now and going to be cleaned' \; -exec unlink {} \; 2>/dev/null & find /usr/share/polkit-1/actions -xtype l -exec echo '{} is invalid now and going to be cleaned' \; -exec unlink {} \; 2>/dev/null &
find /usr/share/fonts -xtype l -exec echo '{} is invalid now and going to be cleaned' \; -exec unlink {} \; 2>/dev/null & find /usr/share/fonts -xtype l -exec echo '{} is invalid now and going to be cleaned' \; -exec unlink {} \; 2>/dev/null &
+110 -32
View File
@@ -50,34 +50,36 @@ Commands:
EOF EOF
} }
apm_exec(){ apm_exec(){
# 递归读取info文件并构建lowerdir # ===============================
# 基础变量
# ===============================
local lowerdirs=() local lowerdirs=()
local current_dir="${PATH_PREFIX}/var/lib/apm/${coredir}" # 当前目录开始 local env_layers=()
local current_dir="${PATH_PREFIX}/var/lib/apm/${coredir}"
local next_info_file="" local next_info_file=""
local APM_RUN_EXEC=/var/lib/apm/apm/files/ace-run
# 使用统一的 ace-run 脚本 # ===============================
APM_RUN_EXEC=/var/lib/apm/apm/files/ace-run # 递归读取 info / info_env
# ===============================
while : ; do while : ; do
# 构建info文件的路径
next_info_file="${current_dir}/info" next_info_file="${current_dir}/info"
# echo "${current_dir}/info"
# 检查info文件是否存在 # 记录 info_env(底层优先)
if [[ ! -f "$next_info_file" ]]; then if [[ -f "${current_dir}/info_env" ]]; then
# log.debug "No more info files found, stopping recursion." env_layers+=("${current_dir}/info_env")
break
fi fi
# 读取info文件的每一行并构建lowerdir # 没有 info 就停止
while IFS= read -r basedir; do [[ ! -f "$next_info_file" ]] && break
[[ -z "$basedir" ]] && continue # 跳过空行
# 读取依赖层
while IFS= read -r basedir; do
[[ -z "$basedir" ]] && continue
# 检查ace-env目录是否存在
if [[ -d "${PATH_PREFIX}/var/lib/apm/${basedir}/files/ace-env" ]]; then if [[ -d "${PATH_PREFIX}/var/lib/apm/${basedir}/files/ace-env" ]]; then
lowerdirs+=("${PATH_PREFIX}/var/lib/apm/${basedir}/files/ace-env") lowerdirs+=("${PATH_PREFIX}/var/lib/apm/${basedir}/files/ace-env")
# 如果ace-env不存在,检查core目录
elif [[ -d "${PATH_PREFIX}/var/lib/apm/${basedir}/files/core" ]]; then elif [[ -d "${PATH_PREFIX}/var/lib/apm/${basedir}/files/core" ]]; then
lowerdirs+=("${PATH_PREFIX}/var/lib/apm/${basedir}/files/core") lowerdirs+=("${PATH_PREFIX}/var/lib/apm/${basedir}/files/core")
else else
@@ -85,35 +87,111 @@ apm_exec(){
fi fi
done < "$next_info_file" done < "$next_info_file"
# 尝试获取下一个依赖信息的路径 # 递归到下一个
local next_basedir=$(tail -n 1 "$next_info_file") local next_basedir
if [[ -z "$next_basedir" || ! -d "${PATH_PREFIX}/var/lib/apm/${next_basedir}" ]]; then next_basedir="$(tail -n 1 "$next_info_file")"
log.debug "No further dependencies found, ending recursion." [[ -z "$next_basedir" || ! -d "${PATH_PREFIX}/var/lib/apm/${next_basedir}" ]] && break
break
fi
# 更新当前目录,递归处理下一个依赖
current_dir="${PATH_PREFIX}/var/lib/apm/${next_basedir}" current_dir="${PATH_PREFIX}/var/lib/apm/${next_basedir}"
done done
# 检查是否找到了有效的lowerdir # ===============================
# info_layer_override(最高优先级)
# ===============================
local override_file="${PATH_PREFIX}/var/lib/apm/${coredir}/info_layer_override"
if [[ -f "$override_file" ]]; then
log.debug "Found info_layer_override: $override_file"
local override_dirs=()
local override_envs=()
while IFS= read -r basedir; do
[[ -z "$basedir" ]] && continue
local base="${PATH_PREFIX}/var/lib/apm/${basedir}"
if [[ -d "${base}/files/ace-env" ]]; then
override_dirs+=("${base}/files/ace-env")
elif [[ -d "${base}/files/core" ]]; then
override_dirs+=("${base}/files/core")
else
log.warn "Override layer not found: $basedir"
fi
if [[ -f "${base}/info_env" ]]; then
override_envs+=("${base}/info_env")
fi
done < "$override_file"
# override 层放最前(最高)
if [[ ${#override_dirs[@]} -gt 0 ]]; then
lowerdirs=("${override_dirs[@]}" "${lowerdirs[@]}")
fi
# override env 最后应用(最高)
if [[ ${#override_envs[@]} -gt 0 ]]; then
env_layers+=("${override_envs[@]}")
fi
fi
# ===============================
# 检查 lowerdir
# ===============================
if [[ ${#lowerdirs[@]} -eq 0 ]]; then if [[ ${#lowerdirs[@]} -eq 0 ]]; then
log.error "No valid lower directories found for package: $coredir" log.error "No valid lower directories found for package: $coredir"
return 1 return 1
fi fi
# 将lowerdirs数组用冒号连接起来 local lowerdir
local lowerdir=$(IFS=:; echo "${lowerdirs[*]}") lowerdir=$(IFS=:; echo "${lowerdirs[*]}")
# 创建挂载点目录
mkdir -p "/tmp/apm/${coredir}" mkdir -p "/tmp/apm/${coredir}"
# 使用fuse-overlayfs挂载 # ===============================
log.debug "Mounting with lowerdir: $lowerdir" # 应用 info_env(从下到上)
fuse-overlayfs -o lowerdir="$lowerdir",upperdir="${PATH_PREFIX}/var/lib/apm/${coredir}/files/core/",workdir="${PATH_PREFIX}/var/lib/apm/${coredir}/files/work/" "/tmp/apm/${coredir}" # ===============================
for env_file in "${env_layers[@]}"; do
log.debug "Applying env: $env_file"
# 执行命令 while IFS= read -r line || [[ -n "$line" ]]; do
[[ -z "$line" || "$line" =~ ^[[:space:]]*# ]] && continue
if [[ "$line" =~ ^[A-Za-z_][A-Za-z0-9_]*= ]]; then
local key="${line%%=*}"
local val="${line#*=}"
# 去首尾空白
val="${val#"${val%%[![:space:]]*}"}"
val="${val%"${val##*[![:space:]]}"}"
# 去外层引号
if [[ "$val" =~ ^\".*\"$ || "$val" =~ ^\'.*\'$ ]]; then
val="${val:1:-1}"
fi
export "$key=$val"
else
log.warn "Invalid env line ignored: $line"
fi
done < "$env_file"
done
# ===============================
# 挂载 overlay
# ===============================
log.debug "Mounting overlayfs"
log.debug "lowerdir=$lowerdir"
fuse-overlayfs \
-o lowerdir="$lowerdir",upperdir="${PATH_PREFIX}/var/lib/apm/${coredir}/files/core/",workdir="${PATH_PREFIX}/var/lib/apm/${coredir}/files/work/" \
"/tmp/apm/${coredir}"
# ===============================
# 执行
# ===============================
chrootEnvPath="/tmp/apm/${coredir}" "${APM_RUN_EXEC}" "$@" chrootEnvPath="/tmp/apm/${coredir}" "${APM_RUN_EXEC}" "$@"
# ===============================
# 卸载 # 卸载
# ===============================
umount "/tmp/apm/${coredir}" umount "/tmp/apm/${coredir}"
} }
@@ -70,7 +70,7 @@ _apm()
# supported options per command # supported options per command
if [[ "$cur" == -* ]]; then if [[ "$cur" == -* ]]; then
case $command in case $command in
install|remove|purge|upgrade|dist-upgrade|full-upgrade|autoremove) install|remove|purge|upgrade|dist-upgrade|full-upgrade|autoremove|autopurge)
COMPREPLY=( $( compgen -W '--show-progress COMPREPLY=( $( compgen -W '--show-progress
--fix-broken --purge --verbose-versions --auto-remove --fix-broken --purge --verbose-versions --auto-remove
-s --simulate --dry-run -s --simulate --dry-run
+1 -1
View File
@@ -27,7 +27,7 @@ function ensure_dir() {
return 0 return 0
fi fi
} }
chrootEnvPath="${chrootEnvPath:-$(pwd)/ace-env}" chrootEnvPath="${chrootEnvPath:-$(dirname $0)/ace-env}"
APM_PKG_NAME="${APM_PKG_NAME:-apm-general}" APM_PKG_NAME="${APM_PKG_NAME:-apm-general}"
+4
View File
@@ -112,6 +112,10 @@ chown -R root $chrootEnvPath
mkdir -p $chrootEnvPath/amber-ce-tools/data-dir mkdir -p $chrootEnvPath/amber-ce-tools/data-dir
ln -sv ../../usr/share/applications $chrootEnvPath/amber-ce-tools/data-dir/ ln -sv ../../usr/share/applications $chrootEnvPath/amber-ce-tools/data-dir/
ln -sv ../../usr/share/icons $chrootEnvPath/amber-ce-tools/data-dir/ ln -sv ../../usr/share/icons $chrootEnvPath/amber-ce-tools/data-dir/
mkdir -p $chrootEnvPath/usr/share/templates
ln -sfv ../../usr/share/templates/ $chrootEnvPath/amber-ce-tools/data-dir/
chmod 777 -R $chrootEnvPath/usr/share/icons chmod 777 -R $chrootEnvPath/usr/share/icons
rm -vfr $chrootEnvPath/dev/* rm -vfr $chrootEnvPath/dev/*
true true
@@ -14,29 +14,39 @@ log.error "需要把ace-env所在的路径设置为第一个参数"
exit 1 exit 1
fi fi
# 1\. 获取宿主机 NVIDIA 驱动版本 # 1. 获取宿主机 NVIDIA 驱动版本
nvidia_version=$(cat /sys/module/nvidia/version 2>/dev/null) nvidia_version=$(cat /sys/module/nvidia/version 2>/dev/null)
if [ -z "$nvidia_version" ]; then if [ -z "$nvidia_version" ]; then
log.warn "无法获取 NVIDIA 驱动版本 Can not determine NVIDIA Driver version" # log.warn "无法获取 NVIDIA 驱动版本 Can not determine NVIDIA Driver version"
exit 1 exit 1
fi fi
# 2\. 目标目录准备 # 2. 目标目录准备
ACE_DIR="$1" ACE_DIR="$1"
if [[ ! -e "${ACE_DIR}" ]];then if [[ ! -e "${ACE_DIR}" ]];then
log.error "未检测到 apm安装,请安装后再试 apm is not detected. Please try again after installation" log.error "未检测到 apm安装,请安装后再试 apm is not detected. Please try again after installation"
log.info "请按回车关闭... Press Enter to close..."
read
exit 1 exit 1
fi fi
mkdir -p "$ACE_DIR/usr/lib" "$ACE_DIR/usr/lib32" mkdir -p "$ACE_DIR/usr/lib" "$ACE_DIR/usr/lib32"
# 检查版本是否已存在且匹配
if [ -f "$ACE_DIR/current_version" ]; then
existing_version=$(cat "$ACE_DIR/current_version")
if [ "$existing_version" = "$nvidia_version" ]; then
# log.info "NVIDIA 驱动版本未变化,跳过链接操作 NVIDIA Driver version unchanged, skipping linking."
exit 0
else
log.info "检测到 NVIDIA 驱动版本变化: $existing_version -> $nvidia_version"
log.info "NVIDIA Driver version changed: $existing_version -> $nvidia_version"
fi
fi
log.info "正在链接 NVIDIA 驱动库 Linking NVIDIA Driver Libs" log.info "正在链接 NVIDIA 驱动库 Linking NVIDIA Driver Libs"
# 3\. 收集库文件路径 # 3. 收集库文件路径
lib_list=$(ldconfig -p | grep -Ei "nvidia|libcuda" | cut -d'>' -f2) lib_list=$(ldconfig -p | grep -Ei "nvidia|libcuda" | cut -d'>' -f2)
# 4\. 复制库文件 # 4. 复制库文件
copied=0 copied=0
for lib in $lib_list; do for lib in $lib_list; do
resolved=$(readlink -f "$lib") # 解析符号链接 resolved=$(readlink -f "$lib") # 解析符号链接
@@ -48,7 +58,7 @@ for lib in $lib_list; do
fi fi
done done
# 5\. 复制辅助文件 # 5. 复制辅助文件
additional_files=( additional_files=(
/usr/share/vulkan/icd.d/nvidia_icd.json /usr/share/vulkan/icd.d/nvidia_icd.json
/usr/share/egl/egl_external_platform.d/20_nvidia_xcb.json /usr/share/egl/egl_external_platform.d/20_nvidia_xcb.json
@@ -62,7 +72,7 @@ for file in "${additional_files[@]}"; do
fi fi
done done
# 6\. 标记版本 # 6. 标记版本
if [ $copied -eq 1 ]; then if [ $copied -eq 1 ]; then
echo "$nvidia_version" > "$ACE_DIR/current_version" echo "$nvidia_version" > "$ACE_DIR/current_version"
log.info "NVIDIA 驱动库已成功链接 Nvidia Driver Libs are successfully linked. " log.info "NVIDIA 驱动库已成功链接 Nvidia Driver Libs are successfully linked. "
+3 -2
View File
@@ -1,9 +1,10 @@
#!/bin/bash #!/bin/bash
# 提取配置信息 # 提取配置信息
VERSION=@VERSION@-apm VERSION_FEEDBACK=@VERSION@-apm
UUID=$(cat /etc/machine-id 2>/dev/null || echo "unknown") UUID=$(cat /etc/machine-id 2>/dev/null || echo "unknown")
# 获取系统信息 - 不依赖 lsb_release # 获取系统信息 - 不依赖 lsb_release
if [ -f /etc/os-release ]; then if [ -f /etc/os-release ]; then
# 现代 Linux 系统使用 /etc/os-release # 现代 Linux 系统使用 /etc/os-release
@@ -35,7 +36,7 @@ JSON_DATA=$(cat <<EOF
"Distributor ID": "$DISTRIBUTOR_ID", "Distributor ID": "$DISTRIBUTOR_ID",
"Release": "$RELEASE", "Release": "$RELEASE",
"Architecture": "$ARCHITECTURE", "Architecture": "$ARCHITECTURE",
"Store_Version": "$VERSION", "Store_Version": "$VERSION_FEEDBACK",
"UUID": "$UUID", "UUID": "$UUID",
"TIME": "$CURRENT_TIME" "TIME": "$CURRENT_TIME"
} }