--- url: /aipod/package/spec.md --- # AI 应用 首先,我们先理解下下面几个概念 1. `lzc-cli` 懒猫微服中用来开发微服应用的脚手架,通过 `lzc-cli` 可以快速的打包应用、安装应用、调试应用、发布应用等。 2. 通过 `lzc-cli` 打包后产生的包就为 `lpk` 格式,这个是微服中应用的格式。 3. 懒猫AI浏览器中可以安装插件,支持 `PC` 和 `Android` 平台。 `AI应用` 是指在微服应用的基础上,添加 `AI服务` 或者 `AI浏览器插件` 的应用。这一类应用的下载和安装都和正常的微服应用一样,区别在于以下的两点: * **支持添加AI服务**,在应用安装后,会自动部署相关的服务到算力舱上。 * **支持添加AI浏览器插件**,在应用安装后,AI浏览器上会自动加载对应的插件。 ## 添加 `AI服务` 在 `lzc-build.yml` 文件中添加 `ai-pod-service`这个字段,如下所示: ```yml ... # ai-pod-service: 指定算力舱的服务目录,会将里面的内容打包到lpk中 ai-pod-service: ./ai-pod-service ... ``` `ai-pod-service` 字段需要指定一个目录,这个目录下需要包含 `docker-compose.yml` 文件。 这个目录将会作为 `docker-compose` 的运行服务,所以在 `docker-compose.yml` 中可以通过路径使用你当前目录下的资源。在服务运行的时候,算力舱中会提供以下环境变量: 1. 数据持久化路径 * 定义: `/ssd/lzc-ai-agent/data/` * 环境变量: `LZC_AGENT_DATA_DIR` * 示例: `/ssd/lzc-ai-agent/data/cloud.lazycat.aipod.ai` ```yml ollama: volumes: - /etc/timezone:/etc/timezone:ro - ${LZC_AGENT_DATA_DIR}/data:/root/.ollama - ./check_ollama.py:/check_ollama.py:ro ``` 2. 数据缓存路径 * 定义: `/ssd/lzc-ai-agent/cache/` * 环境变量: `LZC_AGENT_CACHE_DIR` * 示例: `/ssd/lzc-ai-agent/cache/cloud.lazycat.aipod.ai` ```yml ollama: volumes: - ${LZC_AGENT_CACHE_DIR}/cache:/root/.cache ``` 3. 服务ID(对应LPK中的appId) * 定义: `` * 环境变量: `LZC_SERVICE_ID` * 示例: `cloudlazycataipodfishspeech` * 注意: 这个环境变量和 LPK 中的 `appId` 不一致,`LZC_SERVICE_ID` 会将 `.` 去掉 ```yml ollama: labels: - "traefik.http.routers.${LZC_SERVICE_ID}-ollama.rule=Host(`ollama-ai`)" ``` :::info 算力舱中的 `docker` 默认是使用 `nvidia-runtime`,在容器中能直接使用 `gpus`,不需要显式的指定 `gpus` 相关的配置。更详细的说明,[点击连接](https://forums.developer.nvidia.com/t/whats-difference-between-gpus-and-runtime-nvidia-for-the-docker-container/283468/4) ::: ### 配置AI服务访问规则 算力舱中的服务是使用 `traefik` 结合 `Host` 的规则做服务的转发,一个服务能正常的被访问,需要配置下面的两个部分 1. `Host` 规则 `Host` 定义的值**必须**要 `-ai` 结尾,要不然会无法转发到正确的服务上。 规则表现为: `traefik.http.routers..rule=Host(-ai)` * `` 为服务名称,这个是 `traefik` 中路由标识使用,正常情况下,各个服务填写的都是唯一的。 * `-ai`为微服中访问服务的域名地址。 下面是一个示例: ```yml services: ollama: labels: - "traefik.enable=true" - "traefik.http.routers.${LZC_SERVICE_ID}-ollama.rule=Host(`ollama-ai`)" ``` 关于 `traefik` 的更多使用方法可以查看 [Host Rule](https://doc.traefik.io/traefik/routing/routers/#host-and-hostregexp) 2. `配置 traefik 网络` 只有添加了 `traefik` 网络的服务才能被 `traefik` 接管. `traefik-shared-network` 这个网络是 `lzc-ai-agent` 运行起来之后就会被创建。 ```yml networks: - traefik-shared-network ``` 或者在 `docker-compose.yml` 中的将 `traefik-shared-network` 网络指定为默认的网络配置. ```yml networks: default: external: true name: traefik-shared-network ``` 下面是一个示例: ```yml services: whoami: image: registry.lazycat.cloud/traefik/whoami:ab541801c8cc labels: - "traefik.http.routers.whoami.rule=Host(`whoami-ai`)" networks: default: external: true name: traefik-shared-network ``` ## 添加 `AI浏览器插件` 在 `lzc-build.yml` 文件中添加 `browser-extension`这个字段,如下所示: ```yml ... # browser-extension: 指定浏览器插件的目录,如果这个路径为一个文件,将直接复制作 # 为扩展的zip包打包,如果是为一个目录,将打包成zip,再打包到 lpk 中 browser-extension: ./my-awesome-chrome-extension.zip ... ``` `zip` 为浏览器兼容的插件格式,如果插件是 [wxt](https://wxt.dev/) 开发的,那可以很简单的打包插件为一个zip包,或者手动把插件目录打包成一个zip包。 ## 配置 在微服应用中的 `lzc-manifest.yml` 中添加 `aipod` 来配置应用是否创建快捷方式等选项。 ### 快捷方式 安装到微服中的 `AI应用` 会默认显示在 `AI浏览器` 的快捷方式上,但可以通过下面的方式配置禁用 ```lzc-manifest.yml aipod: shortcut: disable: true ``` 在 `aipod` 的字段中,仅仅支持 `.SysParams(.S)` 参数中的 `.BoxName` 和 `.BoxDomain` 更多的信息查看[模板参数](https://developer.lazycat.cloud/advanced-manifest-render.html#%E6%A8%A1%E6%9D%BF%E5%8F%82%E6%95%B0) ## `AI应用`的`lpk`目录结构 ``` M Mode Size Date&time Filename - ---------- ------ -------------------- ---------------- drwxrwxr-x 0 16-May-2025 08:01:18 ai-pod-service/ -rw-rw-r-- 13 16-May-2025 08:01:18 ai-pod-service/README.md -rw-rw-r-- 529 16-May-2025 08:01:18 ai-pod-service/docker-compose.yml -rw-rw-r-- 1536 16-May-2025 08:01:18 content.tar -rw-rw-r-- 440469 16-May-2025 08:01:18 extension.zip -rw-rw-r-- 16532 16-May-2025 08:01:18 icon.png -rw-rw-r-- 276 16-May-2025 08:01:18 manifest.yml - ---------- ------ -------------------- ---------------- 459355 7 files ``` 这个是通过 `lzc-cli` 打包出来的 `AI应用` 里面包含了 `extension.zip` 浏览器插件,以及 `ai-pod-service` AI服务,其他的为微服应用相关的文件。 ## `AI应用` 中添加进度提示 AI应用在本质上是一个懒猫微服的应用 + 算力舱中的服务,懒猫微服的应用是有下载进度和启动进度的,但并没有显示算力舱中的服务进度。针对这种情况,需要单独的对 `AI应用` 做一个兼容层。我们提供了一个 `caddy-aipod` 的中间件,您需要把这个作为 `AI应用` 的入口,类似下面的做法 * lzc-manifest.yml ```yml name: ComfyUI package: cloud.lazycat.aipod.comfyui version: 1.0.5 description: 最强大的开源基于节点的生成式人工智能应用程序 license: https://github.com/comfyanonymous/ComfyUI/blob/master/LICENSE homepage: https://www.comfy.org author: x usage: 这个应用需要结合算力舱使用 locales: en: title: ComfyUI description: "The most powerful open source node-based application for generative AI" usage: "This application needs to be used in conjunction with AI Pod" aipod: shortcut: disable: false application: subdomain: comfyui routes: - /=http://caddy:80 services: caddy: image: registry.lazycat.cloud/catdogai/caddy-aipod:65e058ce setup_script: | cat <<'EOF' > /etc/caddy/Caddyfile { auto_https off http_port 80 https_port 0 } :80 { handle { route { lzcaipod root * /lzcapp/pkg/content/ui/ try_files {path} /index.html header Cache-Control "max-age=60, private, must-revalidate" file_server } } } EOF cat /etc/caddy/Caddyfile ``` 主要的关键在于 `Caddyfile` 中的 `lzcaipod` 指令,在这个指令中会将进来的流量做判断,检测当前的服务是否已经运行,从而给出相应的提示。 ## 指定某一个算力舱上的服务 在具有多个算力舱的情况下,可以通过 `f-{算力舱的序列号}-{服务名称}-ai.{微服名称}.heiyu.space` 来访问。如 `https://f-1420225016421-dozzle-ai.catdog.heiyu.space` --- --- url: /aipod/issues/lzc-app-dependon-pod-service-health.md --- # AI 应用依赖算力舱服务的状态检测 在微服系统 `1.3.8` 之后,可以使用 `upstreams` 的特性去访问算力舱中的 `health check` 接口。如下所示 ```yml name: ComfyUI package: cloud.lazycat.aipod.comfyui version: 0.2.0 description: ComfyUI is a web UI for AI Art. license: https://choosealicense.com/licenses/mit/ homepage: author: application: subdomain: comfyui gpu_accel: true routes: - /=file:///lzcapp/pkg/content/dist health_check: test_url: http://127.0.0.1/version start_period: 5m upstreams: - location: /version backend: https://comfyui-ai.{{ .S.BoxDomain }}/api/manager/version trim_url_suffix: / use_backend_host: true dump_http_headers_when_5xx: true ``` --- --- url: /aipod/olddocs/todo.md --- # AI 算力评测 1. 文档翻译类 1. 总结 2. 翻译图书 3. 翻译字幕 4. 电话纪要 2. 摄像头 1. 语义理解 2. 3. 智能音箱 1. 语音合成 2. 多合一模型 4. 视频搜索 1. 结合上下文的语义理解 5. 跨国交流 1. 实时翻译 2. 音色合成(将翻译后的文字使用自己的音色合成语音) 6. 网页转播客 1. 内容识别 2. 文字转语音 7. RAG 全文搜索 1. 可以先支持相似搜索 2. 在相似搜索的基础上做文档召回、文档总结、文档理解 * \[x] 2024-09-18 11:35:35 过一遍 jetson 的文档,看有那些东西有用 * \[] 2024-09-24 16:12:43 在模型多个 engine 同时使用的情况下,是否会有功率的限制从而导致性能下降 * \[] fish-speech 模型 --- --- url: /aipod/asr.md --- # ASR(语音识别) 算力舱内置了一个高性能的语音识别服务. 当前使用的大模型是 `Systran/faster-whisper-large-v2`,较原版 `openai/whisper-large-v2` 模型优化了运行速度,并且默认支持多国语言。 实测 whisper-large-v3 相较于 whisper-large-v2 更频繁的出现错误识别和幻觉的情况,所以并未在算力舱中默认使用。 ## 文档 `asr` 服务的 api 可以通过 查看。 接口兼容 OpenAI API 格式,可直接作为 OpenAI API 调用。模型名可以随意指定,在后端会自动转换为实际模型名。 > 注意受限于 HTTP 协议规范,不能直接在 Swagger UI 网页发起携带音频文件的请求,会报错 422 Unprocessable Entity,这是正常的,可通过 API 调用、`curl` 等工具发起请求。 ## 本地使用示例(依赖微服) ```bash curl -X 'POST' \ 'https://asr-ai.13gxg.heiyu.space/v1/audio/transcriptions' \ -F 'stream=false' \ -F 'timestamp_granularities=segment' \ -F 'prompt=よろしくお願いします. 你好,请多关照。 hello, please take care of me.' \ -F 'batch_size=1' \ -F 'model=Systran/faster-whisper-large-v2' \ -F 'temperature=0' \ -F 'response_format=text' \ -F 'file=@/home/nvidia/Videos/a.mp4' \ -F 'hotwords=string' \ -F 'vad_filter=false' ``` ## 单独部署使用 1. 将下面的内容保存到一个 docker-compose.yml 文件中 ``` services: asr: image: registry.lazycat.cloud/x/videorag/asr:c21af88 ports: - 3000:3000 healthcheck: test: ["CMD", "curl", "-f", "http://localhost:3000/health"] interval: 10s timeout: 30s retries: 100 start_period: 1s ``` 2. 然后在目录上使用 docker-compose up -d 启动 3. 使用 http://127.0.0.1:3000/docs --- --- url: /aipod/ollama/benchmark.md --- # Benchmark | Model | Tokens | |:----------------|:-------| | qwen3-coder:30b | 31.84 | | | | | | | --- --- url: /aipod/benchmark/bgem3.md --- # bge-m3 ### vllm ``` bge-m3-vllm-1 | INFO: Application startup complete. bge-m3-vllm-1 | INFO 08-20 03:40:32 [metrics.py:481] Avg prompt throughput: 3698.0 tokens/s, Avg generation throughput: 5.9 tokens/s, Running: 0 reqs, Swapped: 0 reqs, Pending: 953 reqs, GPU KV cache usage: 0.0%, CPU KV cache usage: 0.0%. bge-m3-vllm-1 | INFO 08-20 03:40:38 [metrics.py:481] Avg prompt throughput: 28348.0 tokens/s, Avg generation throughput: 44.4 tokens/s, Running: 0 reqs, Swapped: 0 reqs, Pending: 698 reqs, GPU KV cache usage: 0.0%, CPU KV cache usage: 0.0%. bge-m3-vllm-1 | INFO 08-20 03:40:43 [metrics.py:481] Avg prompt throughput: 29275.2 tokens/s, Avg generation throughput: 46.4 tokens/s, Running: 0 reqs, Swapped: 0 reqs, Pending: 441 reqs, GPU KV cache usage: 0.0%, CPU KV cache usage: 0.0%. bge-m3-vllm-1 | INFO 08-20 03:40:49 [metrics.py:481] Avg prompt throughput: 29540.3 tokens/s, Avg generation throughput: 46.1 tokens/s, Running: 0 reqs, Swapped: 0 reqs, Pending: 188 reqs, GPU KV cache usage: 0.0%, CPU KV cache usage: 0.0%. bge-m3-vllm-1 | INFO: 172.20.0.4:45788 - "POST /v1/embeddings HTTP/1.1" 200 OK ``` 并发250多个请求,输出的 token 可以达到 29540 多 token/s ``` python3 ollama_perf.py --file GuiMiZhiZhuu.txt --url https://bgem3vllm-ai.13gxg.heiyu.space/v1/embeddings --model bge-m3 --- 测试参数 --- 文件路径: GuiMiZhiZhuu.txt 模型名称: bge-m3 API URL: https://bgem3vllm-ai.13gxg.heiyu.space/v1/embeddings 切片长度: 1024 字符 总字数: 4775359 总切片数: 4664 注意: 所有切片将在一个 API 请求中发送。 ------------------ 开始发送单个大请求,请稍候... 请求完成! --- 性能测试结果 --- 总耗时: 132.80 秒 总字数: 4775359 总处理 Tokens: 3384888 请求状态: 成功 (HTTP 200) --- 核心指标 --- 平均 Token 速度: 25489.00 tokens/秒 平均吞吐量: 35959.57 字/秒 -------------------- ``` ### ollama ``` $ python3 ollama_perf.py --file GuiMiZhiZhuu.txt --url https://ollama-ai.13gxg.heiyu.space/v1/embeddings --model bge-m3:latest --- 测试参数 --- 文件路径: GuiMiZhiZhuu.txt 模型名称: bge-m3:latest API URL: https://ollama-ai.13gxg.heiyu.space/v1/embeddings 切片长度: 1024 字符 总字数: 4775359 总切片数: 4664 注意: 所有切片将在一个 API 请求中发送。 ------------------ 开始发送单个大请求,请稍候... 请求完成! --- 性能测试结果 --- 总耗时: 529.10 秒 总字数: 4775359 总处理 Tokens: 3375250 请求状态: 成功 (HTTP 200) --- 核心指标 --- 平均 Token 速度: 6379.19 tokens/秒 平均吞吐量: 9025.38 字/秒 -------------------- ``` 小文件 ``` python3 ollama_perf.py --file xce --url https://ollama-ai.13gxg.heiyu.space/v1/embeddings --model bge-m3:latest --- 测试参数 --- 文件路径: xce 模型名称: bge-m3:latest API URL: https://ollama-ai.13gxg.heiyu.space/v1/embeddings 切片长度: 1024 字符 总字数: 41648 总切片数: 41 注意: 所有切片将在一个 API 请求中发送。 ------------------ 开始发送单个大请求,请稍候... 请求完成! --- 性能测试结果 --- 总耗时: 4.95 秒 总字数: 41648 总处理 Tokens: 29539 请求状态: 成功 (HTTP 200) --- 核心指标 --- 平均 Token 速度: 5968.35 tokens/秒 平均吞吐量: 8414.97 字/秒 -------------------- ``` --- --- url: /aipod/comfyui.md --- # comfyui Q:如果遇到 ksampler 不支持 sm87 cuda 指令? A:这个其实是 segeatention 库中没有适配 sm87 指令,通过更改 `/opt/venv/lib/python3.12/site-packages/sageattention/core.py` 和 sm89 同样的逻辑即可。 # 添加代理 在算力舱的 `/ssd/lzc-ai-agent/services/cloud.lazycat.aipod.comfyui` 目录下创建一个 `compose.override.yml` ```yml services: app: environment: - https_proxy=http://代理ip:代理端口 ``` 注意: 如果不要将代理 ip 写成 `127.0.0.1`,在容器内部是访问不到这个地址的. --- --- url: /aipod/olddocs/mlc.md --- 可以使用 jetson 官方封装好的 mlc 来测试 mlc llm 的速度 ```sh jetson-containers run dustynv/mlc:0.1.1-r36.3.0 ``` 或者直接使用 docker 命令,将对应的位置绑定进去 ``` cd /ssd/lnks/jetson-containers docker run -d --runtime nvidia -it --rm --network host --shm-size=8g -v `pwd`:/workspace --volume /tmp/argus_socket:/tmp/argus_socket --volume /etc/enctune.conf:/etc/enctune.conf --volume /etc/nv_tegra_release:/etc/nv_tegra_release --volume /tmp/nv_jetson_model:/tmp/nv_jetson_model --volume /var/run/dbus:/var/run/dbus --volume /var/run/avahi-daemon/socket:/var/run/avahi-daemon/socket --volume /var/run/docker.sock:/var/run/docker.sock --volume /ssd/lnks/jetson-containers/data:/data --device /dev/snd --device /dev/bus/usb --device /dev/i2c-0 --device /dev/i2c-1 --device /dev/i2c-2 --device /dev/i2c-3 --device /dev/i2c-4 --device /dev/i2c-5 --device /dev/i2c-6 --device /dev/i2c-7 --device /dev/i2c-8 dustynv/mlc:0.1.1-r36.3.0 cd /workspace/mymodels/mlc-ai mlc chat Qwen2.5-72B-Instruct-q4f16_1-MLC ``` # config 问题 从 huggingface 中下载的 `mlc Qwen2.5-XB` 在加载的时候会出现 `mean_gen_len` 或者 `isArray` 等错误,这个需要将 `mlc-chat-config.json` 添加缺失的字段。 ``` "shift_fill_factor": 0.3, "mean_gen_len": 128, "max_gen_len": 512, ... "system_prefix_token_ids": [], ``` # 使用官方的 benchmark 脚本测试 ``` root@nvidia-desktop:/workspace/packages/llm/mlc# python3 benchmark.py --model /workspace/mymodels/mlc-ai/Qwen2.5-32B-Instruct-q4f16_1-MLC/ --max-new-tokens 128 --max-num-prompts 4 --prompt /data/prompts/completion_16.json --save /workspace/myresults/mlc.csv ``` # mlc 中的 mlc\_llm 版本比较低,运行 Qwen2-1.5B 的时候会出现 lm\_head.weight https://github.com/mlc-ai/mlc-llm/issues/2458 ``` ln -s /usr/bin/python3 /usr/bin/python cd /opt/mlc-llm git pull origin main # create build directory mkdir -p build && cd build # generate build configuration python ../cmake/gen_cmake_config.py # build mlc_llm libraries cmake .. && cmake --build . --parallel $(nproc) && cd .. ``` 貌似也不能解决这个问题 --- --- url: /aipod/deepseed.md --- # deepseed ``` docker run --gpus all --network=host --shm-size 10.24g --name deepseed -d -ti -v `pwd`:/models -v `pwd`/cache:/root/.cache/huggingface dustynv/pytorch:2.7-r36.4.0-cu128-24.04 bash docker exec -ti deepseed bash ``` --- --- url: /aipod/issues/dhcp.md --- # DHCP 表现就是有线网络一直没有获取到 `ip` 地址,从经常 connecting 到 no connected 状态切换 1. 排查当前是否接收到 dhcp 的广播 ``` sudo apt install nmap sudo nmap --script broadcast-dhcp-discover ``` 如果可以接收到 dhcp 包,说明路由器和设备是通的,只是算力舱中系统配置出了问题,可以往 NetworkManager 方向排查。 * 查看 NetworkManager 的日志 ``` sudo journalctl -u NetworkManager -b 0 -r # -r 反序查看, 最新的在最上面 ``` * 也可以试下手动分配ip地址,然后使用 ping 检测这个网卡是否已经连通 2. 查看特定的网卡上是否接收到发过来的数据包 ``` sudo apt install arp-scan sudo arp-scan -I eno1 -l # sudo /usr/sbin/arp-scan -l ``` 这里要 `-I` 执行对应的有线网络网卡接口,要不然收到的可能是wifi发过来的。 如果可以收到包,说明不是网线和设备的问题,可能是路由器上的问题,最方便的方法就是 * 先拔掉网线,然后重启下路由器 * 重新插上网线 3. ping 指定网卡 ``` ping -I eno1 192.168.1.1 ping -I eno1 www.baidu.com ``` --- --- url: /aipod/issues/docker.md --- # docker 启动 traefik 错误? 详细的报错信息如下: ``` May 16 06:06:57 lzc-pod-juyIZt dockerd[1391]: time="2025-05-16T06:06:57.617540160Z" level=error msg="failed to start container" container=675c06f1d672ee0c36441d4e0fcd69d48e38355a40a4e85b7a42d0019467ffc4 error="failed to set up container networking: driver failed programming external connectivity on endpoint monitoring-grafana (02c852b6417b0a591b3b22838f3fd71452fd32bf386bf1c186cb0ba5f256b398): Unable to enable DIRECT ACCESS FILTERING - DROP rule: (iptables failed: iptables --wait -t raw -A PREROUTING -p tcp -d 172.20.0.6 --dport 3000 ! -i br-8321df9162d9 -j DROP: iptables v1.8.7 (legacy): can't initialize iptables table `raw': Table does not exist (do you need to insmod?)\nPerhaps iptables or your kernel needs to be upgraded.\n (exit status 3))" ``` 解决: https://forums.developer.nvidia.com/t/problems-with-docker-version-28-0-1-on-jetson-orin-nx/325541/26 在 `/etc/systemd/system/docker.service.d/` 添加一个 `override.conf` 文件,里面是的内容是 ```override.conf [Service] Environment="DOCKER_INSECURE_NO_IPTABLES_RAW=1" ``` 添加后,执行下面的命令重启相关的服务 ``` sudo systemctl daemon-reload sudo systemctl restart docker sudo systemctl restart lzc-ai-agent ``` docker 重启后,可以使用 `docker info` 查看 ``` > docker info | grep DOCKER_INSECURE_NO_IPTABLES_RAW WARNING: DOCKER_INSECURE_NO_IPTABLES_RAW is set ``` --- --- url: /aipod/benchmark.md --- # Embedding Model ![embedding model](/assets/embedding-model.CO-xauOF.png) --- --- url: /aipod/ffmpeg/compile.md --- # FFmpeg ## jetson 官方提供的 ffmpeg 4.4 ```sh echo "deb https://repo.download.nvidia.com/jetson/ffmpeg main main" | sudo tee -a /etc/apt/sources.list echo "deb-src https://repo.download.nvidia.com/jetson/ffmpeg main main" | sudo tee -a /etc/apt/sources.list sudo apt update sudo apt install ffmpeg ``` ## compile ffmpeg ``` LD_LIBRARY_PATH=$HOME/ffmpeg_build/lib ./ffmpeg --version LD_LIBRARY_PATH=$HOME/ffmpeg_build/lib ./ffmpeg -decoders LD_LIBRARY_PATH=$HOME/ffmpeg_build/lib ./ffmpeg -decoders | grep av1 LD_LIBRARY_PATH=$HOME/ffmpeg_build/lib ./ffmpeg -decoders | grep h264_nvv4l2dec ``` * https://github.com/HandBrake/HandBrake/commit/75f9c84c140c8841cfe1324ef59452025899ad8b.patch?full\_index=1 --- --- url: /aipod/olddocs/fish-speech.md --- # fish-speech * 从现有的wav声音中采集声色 * fish-speech 要求 3.10 的 python 版本, 而 jetson pytorch 中只有在 jetpack 6.0 后 才有 3.10 pytorch 的版本,否则需要自己构建。所以这个模型尽量在 ubuntu 22.40 jetpack 6.0 cuda 12.x 以上运行。 1. 系统安装 libopenblas-dev ``` sudo apt-get -y update; sudo apt-get -y install libopenblas-dev; ``` 2. 下载 jetpack 6 对应的 pytorch 2.3 的版本 whl [link](https://forums.developer.nvidia.com/t/pytorch-for-jetson/72048/1414) 下载 torchaudio, torchvision, torch 进行安装即可 ``` conda create -n fish-speech python=3.10 gcc=12.1.0 pip3 install ./torch-2.3.0-cp310-cp310-linux_aarch64.whl ./torchaudio-2.3.0+952ea74-cp310-cp310-linux_aarch64.whl ./torchvision-0.18.0a0+6043bc2-cp310-cp310-linux_aarch64.whl ``` 3. 根据 fish-speech 的[教程](https://github.com/fishaudio/fish-speech/blob/main/docs/zh/index.md)安装 ``` pip install -e . ``` 没有加速的情况下,在生成语义 token 的阶段中 5.5 tokens/s 的速度 4. 编译 fish-speech 中的 模型进行加速。这个是通过将模型使用 torch.compile 进行编 译成类似 jit 加速一样. nvidia pytorch 中有一个 `Torch-TensorRt` 的 torch compile backend,但这个没有提 供 aarch64 的预编译的包,需要自己构建。 jetson agx orin 有一个 jetpack 5.x 构建好的容器,没有提供 jetpack 6 的版本(这个 容器在 jetpack 6 上使用会加载报 libc 等错误) ``` root@tegra-ubuntu:/workspace# python3 -c 'import torch_tensorrt; print(torch_tensorrt.__version__)' Traceback (most recent call last): File "/usr/local/lib/python3.8/dist-packages/torch_tensorrt/__init__.py", line 39, in import tensorrt File "/usr/lib/python3.8/dist-packages/tensorrt/__init__.py", line 68, in from .tensorrt import * ImportError: /lib/aarch64-linux-gnu/libstdc++.so.6: version `GLIBCXX_3.4.29' not found (required by /usr/lib/aarch64-linux-gnu/nvidia/libnvdla_compiler.so) During handling of the above exception, another exception occurred: Traceback (most recent call last): File "", line 1, in File "/usr/local/lib/python3.8/dist-packages/torch_tensorrt/__init__.py", line 82, in ctypes.CDLL(_find_lib(lib, LINUX_PATHS)) File "/usr/lib/python3.8/ctypes/__init__.py", line 373, in __init__ self._handle = _dlopen(self._name, mode) OSError: /lib/aarch64-linux-gnu/libstdc++.so.6: version `GLIBCXX_3.4.29' not found (required by /usr/lib/aarch64-linux-gnu/nvidia/libnvdla_compiler.so) ``` 5. 在 ubuntu 20.0 jetpack 5.x 系统上使用构建好的容器(但由于 fish-speech 使用 python3.10 ,而容器中提供的包只有 3.8,也还是需要自己构建 3.8 的版本 torch\_tensorrt,而且像 pytorch 这些包也需要自己构建,因为没有 pytorch aarch64 3.10 jetson 的提前编好的) ``` sudo docker run -d --runtime nvidia -it --rm --network host --env HF_ENDPOINT=https://hf-mirror.com -v `pwd`:/workspace --shm-size=8g --volume /tmp/argus_socket:/tmp/argus_socket --volume /etc/enctune.conf:/etc/enctune.conf --volume /etc/nv_tegra_release:/etc/nv_tegra_release --volume /tmp/nv_jetson_model:/tmp/nv_jetson_model --volume /var/run/dbus:/var/run/dbus --volume /var/run/avahi-daemon/socket:/var/run/avahi-daemon/socket --volume /var/run/docker.sock:/var/run/docker.sock --volume /home/nvidia/lnks/jetson-containers/data:/data --device /dev/snd --device /dev/bus/usb --device /dev/i2c-0 --device /dev/i2c-1 --device /dev/i2c-2 --device /dev/i2c-3 --device /dev/i2c-4 --device /dev/i2c-5 --device /dev/i2c-6 --device /dev/i2c-7 --device /dev/i2c-8 --device /dev/i2c-9 -v /run/jtop.sock:/run/jtop.sock dustynv/torch_tensorrt:r35.3.1 ``` 6. 在 ubuntu 22.04 jetpack 6.0 conda python 3.10 环境下构建 torch tensorrt 模块 * dpkg -l | grep tensorrt -i 查看当前系统的 Tensorrt 版本,不要切换到一个不一样的版本上 * 根据当前的各个系统组件版本, 使用 git checkout 到一个指定的支持的 commit 中去 * git fetch --depth=1 origin commit-xxx * git checkout commit-xxx * 根据错误更改 BUILD 或者 WORKSPACE 中的 cuda 版本 * 需要指定 LD 的目录,否则会出现ld连接不了,导致构建失败。(bazel 中指定环境变量需要显示指定参数) * bazel build --action\_env=LD\_LIBRARY\_PATH=/path/to/lib your\_target ``` git clone --branch=main --depth=1 https://github.com/pytorch/TensorRT torch_tensorrt git fetch --depth=1 origin 4c3d026ea64bd646a840bf174ef9d1818f10c20f git checkout 4c3d026ea64bd646a840bf174ef9d1818f10c20f python3 setup.py bdist_wheel --use-cxx11-abi ``` 7. 重新构建 triton 包(需要在conda环境中指定 gcc 的版本,否则会出现 libstdc++的版 本低问题)。也可以通过下面的方式手动临时更改下 ``` git clone https://github.com/triton-lang/triton.git; cd triton; pip install ninja cmake wheel pybind11; # build-time dependencies pip install -e python --verbose mv /ssd/miniconda3/envs/fish-speech/lib/libstdc++.so.6 /ssd/miniconda3/envs/fish-speech/lib/libstdc++.so.6.old ln -s /usr/lib/aarch64-linux-gnu/libstdc++.so.6 /ssd/miniconda3/envs/fish-speech/lib/libstdc++.so.6 ``` 如果遇到 `triton.common` not found, 需要切换到 `2.3.x` 分支 ``` git switch release/2.3.x ``` 8. triton 3.0 需要在 torch 2.5 版本才能使用, 而 jetson agx orin 目前官方给出的只 有 2.4 的版本. 在 torch 2.3 中使用 triton 3.0 会出现 triton.common 缺失的问题。torch 2.3 版本需 要使用 triton 2.3.x 的分支版本,但 triton 2.3.x 分支中没有 aarch64 的适配. 9. torch 构建成功后,需要重新构建 torchaudio 库 [link](https://pytorch.org/audio/stable/build.jetson.html) ``` USE_CUDA=1 python setup.py bdist_wheel ``` 10. torch 构建成功后,需要重新构建 torchvision 库 ``` git clone https://github.com/pytorch/vision.git python setup.py bdist_wheel ``` 11. https://github.com/triton-lang/triton/issues/3505 --- --- url: /aipod/olddocs/tts.md --- # fish-speech | 模型 | 文字 | 输出声音时间 | 推理时间 | 比率(1s的推理时间,可以生成多少声音) | |:------------|:---------------------|:-------------|-----------|--------------------------------------| | fish-speech | 大白鹅故事(2522个字) | 9分10秒 | 37m8.903s | 0.24 | 需要从引用的音频中采集声色,这个采集完成后,就可以保存起来,后面可以继续使用。 # f5-tts 内存要求: 4GB (所以像内存 8GB 的卡也可以运行这个模型) 模型代码本身是 MIT 的开源协议,但模型权重数据是CC-BY-NC的 支持通过标点符合或者空白来添加停顿,这个在 fish-speech 中没有支持的。可以指定一 个示例音频,从音频中克隆音色。 | 模型 | 文字 | 输出声音时间 | 推理时间 | 比率(1s的推理时间,可以生成多少声音) | |:-------|:---------------------|:-------------|----------|--------------------------------------| | E2-TTS | 大白鹅故事(2522个字) | 8分44秒 | 23分50 | 0.36 | | F5-TTS | 大白鹅故事 | 8分44秒 | 17分3 | 0.51 | ``` conda activate f5-tts cd /ssd/lnks/tts/F5-TTS bash example/run2.sh ``` `E2-TTS` 比 `F5-TTS` 更有情感些, `F5-TTS` 的语音质量和 `fish-speech` 的效果差不 多。 # chattts # 测试文件: 大白鹅故事 ```txt 一 从前,有一只胖胖的母鹅。她已经到了做妈妈的年龄,可是她一直没做成妈妈。因为,这只鹅从来没有下过一只蛋,没有孵出过一只鹅来。 可怜的胖鹅,她是一只孤单单的鹅。 她多么希望能孵出一只胖胖的小鹅,听小鹅脆生生地叫她一声妈妈。她多么希望街坊邻居也能尊敬地叫她一声鹅妈妈。 可这一切离开她是多么的遥远,简直不可能。每当夜深人静的时候,胖鹅常常会独自流下伤心的泪,孤独的泪。 一天,胖鹅告别了乡亲们独个儿出外旅行去了。 胖鹅在蜿蜒的小路上,步履蹒跚地走着。她在晶亮的小河上,划动着一双红红的脚掌,体态悠闲地游着。 她看看山,看看水,看看变幻莫测的白云,看看盛开在原野、田梗上的小花。美丽的风景慰藉了她孤独的心灵,胖鹅渐渐变得开朗和愉快起来。 一天傍晚的时候,胖鹅爬上了河岸,她在田埂上一摇一摆地走着。田埂边上,是一片已经收获过的瓜田。瓜田里除了爪藤外,已经看不到西瓜了。 胖鹅走着走着,忽然她看见在几张瓜叶前,有半个看来是被刺猬啃破的西瓜,就在这只被啃破的西瓜对面,居然有个十分完整的圆西瓜。胖鹅高兴极了。她想正好用这只西瓜来解旅途的饥渴。 胖鹅抱住这只西瓜,不知为什么,她有一种感觉,觉得这只西瓜不同于一般的西瓜,它像一只蛋,一只圆圆的、硬硬的有生命的蛋。 也许,胖鹅太想有一个蛋了,她说什么也摆脱不了这个奇怪的想法,她认定这只西瓜是一只蛋。 胖鹅小心翼翼地,把这只“西瓜蛋”搬到了不远处,那儿有看瓜人留下的破草棚。胖鹅在草棚里,她围着“西瓜蛋”转了几圈,她毫不怀疑自己的眼光,这一定是个“西瓜蛋”。胖鹅细心地伏在“西瓜蛋”上,她满怀着热情和信心,在这个破草棚里孵起蛋来了。 胖鹅的体温,渐渐传到了“西瓜蛋”里。 二 一天、两天、三天、五天。 西瓜并没有被胖鹅孵烂。 恰恰相反,“西瓜蛋”的壳硬得很,只是变得很暖和很暖和了。 八天、九天、十天,胖鹅似乎感觉到“西瓜蛋”有了动静,她已经能听到嚓嚓的声响了。 “天哪,我的宝宝快出壳了,我好像听到它在啄蛋壳了!”胖鹅喃喃自语地说着,“我要当妈妈了,我要让宝宝自己啄破蛋壳,当它的可爱的小脑袋从破蛋壳里伸出来时,我一定要亲亲它。” 又过了几天,只听到格拉一声响,“西瓜蛋”的壳破了一个洞——只见一只小秃脑袋,从这个“窗户”里伸了出来,他长着一只尖尖的嘴,他张开一对小小的眼睛,惊奇地注视着这个有趣的世界。 胖鹅激动地伸长脖子,去亲了亲这个小秃脑袋一下,小东西吓得把头缩进了蛋壳。 由于小东西一惊慌,“西瓜蛋”格拉格拉一阵响,整个儿破了。这只被胖鹅从“西瓜蛋”里孵出来的,不知道姓名的小怪物,降临到这个世界上了。 胖鹅当妈妈了,她终于有了自己的孩子。 三 鹅妈妈给自己的孩子取了个名字,叫“小尖嘴”。小尖嘴出壳不久,就会站立,就会走路,还会发出呱呱叽叽的声音。这真是个讨人喜欢的小宝宝。 鹅妈妈是这样的疼爱自己的孩子。 她给小尖嘴找东西吃,她帮小尖嘴梳理几根刚出来的羽毛,还给他讲好听的故事。 鹅妈妈带着她的孩子回到了家乡,街坊邻居不再叫她胖鹅,而改口叫她鹅妈妈了。你说,鹅妈妈心里有多甜蜜——她终于有了孩子,她是个十足的妈妈了。 可惜的是她的孩子,长得越来越不像她。 小尖嘴的腿越长越长,以至于他看自己妈妈的时候,必须低下头来。他的脖子也越长越长,小小的脑袋、尖尖的嘴儿,显得有几分滑稽。 街坊们议论鹅妈妈的儿子,说他不像鸡,不像鸭,也不像鹅。 每当听到这样的话,鹅妈妈就有点不高兴,她会大声地说:“可他像我的儿子。不,就是我的儿子,他多有男子汉的气概!” 鹅妈妈几次想教他的宝贝游泳,不过都没有成功,小家伙站在小河里,河水刚浸到他的肚皮,可是当他蜷起腿来,像他的鹅妈妈那样游泳,就几乎被水呛死。 这是鹅妈妈最伤心的——她的儿子没法学会游泳。 四 有一天,鹅妈妈闲来无聊,因为儿子出门玩去了,她买来一本刚出版的杂志读着。它刊登来自世界各地的新闻和趣事。其中有一篇旅行家爱尔莎太大的回忆文章,吸引了她。 有一次爱尔莎太太和丈夫画家雷诺先生出门旅行。他们在一片异国的瓜田里走着。爱尔莎太太文章里有这样一段: “走着,走着,我的肚子忽然剧痛起来,我当时怀着孕,我就在瓜田里下了我这辈子的第一个,也是唯一的一个蛋,那是一个圆滚滚的,非常惹人喜爱的大蛋。” “可是,我的丈夫雷诺,他看见瓜田里有个可爱的小西瓜,突然画兴大发,他要让我们的孩子知道,他是降生在瓜田里的,雷诺要在蛋上留下一张有意义的写生画。于是,他就挤出了颜料,把对面西瓜的色彩画在了我刚下的那只可爱的蛋上,我的蛋就变成了一只活灵活现的小西瓜了。” “就在这时,”爱尔莎太太伤心地说,“突然,从远处跑来了一个黑点儿,根据我们在草原上生活多年的经验,可以断定,那是一只狼。我们不得不暂时躲一躲,撒腿离开了瓜田。” “过了好久,当我们回来时,瓜田里只剩下半只被啃过的西瓜,我们被画成西瓜的蛋,无影无踪了。” 爱尔莎太太在文章最后说:“我抬头四望,田野上除了一个看瓜人留下的破草棚,什么也没有,我伤心透了——我的唯一的孩子,就这样失去了⋯⋯” 看到这里,鹅妈妈眼前一阵黑。这场面她太熟悉了,鹅妈妈想说:“爱尔莎太太,你当时为什么不到草棚里来看看呢?可怜的人。” 鹅妈妈再看看文章后面,那里印着爱尔莎太太的照片,原来她和雷诺先生是一对驼鸟夫妻,他们的家乡在澳大利亚。 瞧,她那高高的腿,她那长长的脖子和小脑袋,这不和小尖嘴一模一样吗? “天哪。”鹅妈妈说,“我的小尖嘴是只小驼鸟。” 五 接下来的日子,是鹅妈妈一生最难忘的日子。她翻来覆去地想这件事。 鹅妈妈想把小尖嘴留在身边,她完全可以隐瞒这件事。是她从“西瓜蛋”里孵出了小尖嘴,是她喂养大了小尖嘴。也是小尖嘴给了她妈妈的称呼,赶走了她的孤单和寂寞。她怎么可以让小尖嘴离开自己,去到一个遥远而又陌生的地方,管一对陌生的夫妻,叫做爸爸妈妈呢⋯⋯ 可她再一想,小尖嘴毕竟是一只小驼鸟,他是个学不会游泳的小家伙,他的天地是在草原上,他会成为鸟类中的长跑冠军。 鹅妈妈想象着,小尖嘴张开翅膀,迈开长腿,像一匹骏马似地在草原上奔驰着,这多威风,多有男子汉气概⋯⋯ “唉,这才像个驼鸟。”鹅妈妈叹口气说,“要是老在我这儿,准会变得鹅不像鹅,驼鸟不像驼鸟的。” 鹅妈妈的心里乱极了。 六 电报毕竟还是发出去了。 “孤独”,这难忘的滋味,让鹅妈妈下定了决心。鹅妈妈想起,小尖嘴没来到她身边以前,她是多么的孤独,多么的寂寞啊。是小尖嘴给她带来了希望、愉快和热热闹闹的生活。 可是如今呢,鹅妈妈说:“我把‘孤独’送给了爱尔莎太太和她的丈夫了,这多么自私。” 是的,鹅妈妈早就从爱尔莎文章的字里行间,读到了孤独,读到了寂寞,读到了懊恨和思念⋯⋯反正,读到了一颗妈妈的破碎的心。 鹅妈妈在给爱尔莎太太的电报中写着:“我再也不会孤独了,因为我有过小尖嘴这个宝贝,他让我成了妈妈,他会永远记住我的。他在我心中,我也在他的心中,他应该成为我们共同的儿子。” 写到这里,鹅妈妈好像看见了爱尔莎太太和雷诺先生喜出望外的模样。 不知怎么的,鹅妈妈突然在电报的最后,想出了一句只有诗人才会想出来的话: “让孤独永远从我们中间离开吧!” 七 如今,当人们敲敲鹅妈妈的门,而一直没有动静的时候,你就会知道—— 鹅妈妈是在给大草原上的小尖嘴写信,而忘了周围的一切。 要么,就是她出远门,去探望那只当年她从“西瓜蛋”里孵出的,如今奔驰在澳大利亚大草原上的小尖嘴了⋯⋯ ``` --- --- url: /aipod/os/gpio.md --- # GPIO 键 1. 可编程按键 (开机键旁边的功能键) ``` sudo su gpioget $(gpiofind PM.07) # 安装后会输出 0, 松开后会输出 1 ``` 2. LED 灯 ``` sudo su gpioset -m signal $(gpiofind PP.04)=1 # 点亮红色 gpioset -m signal $(gpiofind PP.04)=0 # 关闭红色 gpioset -m signal $(gpiofind PR.00)=1 # 点亮白色 gpioset -m signal $(gpiofind PR.00)=0 # 关闭白色 ``` --- --- url: /aipod/olddocs/jetson.md --- # Jetson AGX orin `LLM` 模型速度的关键在内存的带宽速度。假设推断的时候,每个token都会被查询一次。 像 NousResearch/Llama-2-7b-chat-hf 这个模型,官方发布的是 fp16 (模型大小为 14G), 量化成 int8 为7G。最后在 200/7 ~ 30 tokens/s 的速度. jetson 中的 PCIE 有两个 PCIE 4.0 8通道,根据网上的数据 PCIE 4.0x8 通道的速度大约为 (16 GB/s) --- --- url: /aipod/benchmark/llama-3.1-70b.md --- # llama.cpp build: 716301d1 (5757) ## Meta-Llama-3.1-70B-Instruct-IQ4\_XS.gguf ``` ./build/bin/llama-batched-bench -ngl 999 -m ../Meta-Llama-3.1-70B-Instruct-IQ4_XS.gguf -fa -npl 1,2,4,6,8,10,12 -npp 512 -ntg 128 -c 16384 ggml_cuda_init: GGML_CUDA_FORCE_MMQ: no ggml_cuda_init: GGML_CUDA_FORCE_CUBLAS: no ggml_cuda_init: found 1 CUDA devices: Device 0: Orin, compute capability 8.7, VMM: yes build: 5757 (716301d1) with cc (Ubuntu 13.3.0-6ubuntu2~24.04) 13.3.0 for aarch64-linux-gnu llama_model_load_from_file_impl: using device CUDA0 (Orin) - 58814 MiB free llama_model_loader: loaded meta data with 33 key-value pairs and 724 tensors from ../Meta-Llama-3.1-70B-Instruct-IQ4_XS.gguf (version GGUF V3 (latest)) llama_model_loader: Dumping metadata keys/values. Note: KV overrides do not apply in this output. llama_model_loader: - kv 0: general.architecture str = llama llama_model_loader: - kv 1: general.type str = model llama_model_loader: - kv 2: general.name str = Meta Llama 3.1 70B Instruct llama_model_loader: - kv 3: general.finetune str = Instruct llama_model_loader: - kv 4: general.basename str = Meta-Llama-3.1 llama_model_loader: - kv 5: general.size_label str = 70B llama_model_loader: - kv 6: general.license str = llama3.1 llama_model_loader: - kv 7: general.tags arr[str,6] = ["facebook", "meta", "pytorch", "llam... llama_model_loader: - kv 8: general.languages arr[str,8] = ["en", "de", "fr", "it", "pt", "hi", ... llama_model_loader: - kv 9: llama.block_count u32 = 80 llama_model_loader: - kv 10: llama.context_length u32 = 131072 llama_model_loader: - kv 11: llama.embedding_length u32 = 8192 llama_model_loader: - kv 12: llama.feed_forward_length u32 = 28672 llama_model_loader: - kv 13: llama.attention.head_count u32 = 64 llama_model_loader: - kv 14: llama.attention.head_count_kv u32 = 8 llama_model_loader: - kv 15: llama.rope.freq_base f32 = 500000.000000 llama_model_loader: - kv 16: llama.attention.layer_norm_rms_epsilon f32 = 0.000010 llama_model_loader: - kv 17: general.file_type u32 = 30 llama_model_loader: - kv 18: llama.vocab_size u32 = 128256 llama_model_loader: - kv 19: llama.rope.dimension_count u32 = 128 llama_model_loader: - kv 20: tokenizer.ggml.model str = gpt2 llama_model_loader: - kv 21: tokenizer.ggml.pre str = llama-bpe llama_model_loader: - kv 22: tokenizer.ggml.tokens arr[str,128256] = ["!", "\"", "#", "$", "%", "&", "'", ... llama_model_loader: - kv 23: tokenizer.ggml.token_type arr[i32,128256] = [1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, ... llama_model_loader: - kv 24: tokenizer.ggml.merges arr[str,280147] = ["Ġ Ġ", "Ġ ĠĠĠ", "ĠĠ ĠĠ", "... llama_model_loader: - kv 25: tokenizer.ggml.bos_token_id u32 = 128000 llama_model_loader: - kv 26: tokenizer.ggml.eos_token_id u32 = 128009 llama_model_loader: - kv 27: tokenizer.chat_template str = {{- bos_token }}\n{%- if custom_tools ... llama_model_loader: - kv 28: general.quantization_version u32 = 2 llama_model_loader: - kv 29: quantize.imatrix.file str = /models_out/Meta-Llama-3.1-70B-Instru... llama_model_loader: - kv 30: quantize.imatrix.dataset str = /training_dir/calibration_datav3.txt llama_model_loader: - kv 31: quantize.imatrix.entries_count i32 = 560 llama_model_loader: - kv 32: quantize.imatrix.chunks_count i32 = 125 llama_model_loader: - type f32: 162 tensors llama_model_loader: - type q5_K: 80 tensors llama_model_loader: - type q6_K: 1 tensors llama_model_loader: - type iq4_xs: 481 tensors print_info: file format = GGUF V3 (latest) print_info: file type = IQ4_XS - 4.25 bpw print_info: file size = 35.29 GiB (4.30 BPW) load: special tokens cache size = 256 load: token to piece cache size = 0.7999 MB print_info: arch = llama print_info: vocab_only = 0 print_info: n_ctx_train = 131072 print_info: n_embd = 8192 print_info: n_layer = 80 print_info: n_head = 64 print_info: n_head_kv = 8 print_info: n_rot = 128 print_info: n_swa = 0 print_info: is_swa_any = 0 print_info: n_embd_head_k = 128 print_info: n_embd_head_v = 128 print_info: n_gqa = 8 print_info: n_embd_k_gqa = 1024 print_info: n_embd_v_gqa = 1024 print_info: f_norm_eps = 0.0e+00 print_info: f_norm_rms_eps = 1.0e-05 print_info: f_clamp_kqv = 0.0e+00 print_info: f_max_alibi_bias = 0.0e+00 print_info: f_logit_scale = 0.0e+00 print_info: f_attn_scale = 0.0e+00 print_info: n_ff = 28672 print_info: n_expert = 0 print_info: n_expert_used = 0 print_info: causal attn = 1 print_info: pooling type = 0 print_info: rope type = 0 print_info: rope scaling = linear print_info: freq_base_train = 500000.0 print_info: freq_scale_train = 1 print_info: n_ctx_orig_yarn = 131072 print_info: rope_finetuned = unknown print_info: ssm_d_conv = 0 print_info: ssm_d_inner = 0 print_info: ssm_d_state = 0 print_info: ssm_dt_rank = 0 print_info: ssm_dt_b_c_rms = 0 print_info: model type = 70B print_info: model params = 70.55 B print_info: general.name = Meta Llama 3.1 70B Instruct print_info: vocab type = BPE print_info: n_vocab = 128256 print_info: n_merges = 280147 print_info: BOS token = 128000 '<|begin_of_text|>' print_info: EOS token = 128009 '<|eot_id|>' print_info: EOT token = 128009 '<|eot_id|>' print_info: EOM token = 128008 '<|eom_id|>' print_info: LF token = 198 'Ċ' print_info: EOG token = 128001 '<|end_of_text|>' print_info: EOG token = 128008 '<|eom_id|>' print_info: EOG token = 128009 '<|eot_id|>' print_info: max token length = 256 load_tensors: loading model tensors, this can take a while... (mmap = true) load_tensors: offloading 80 repeating layers to GPU load_tensors: offloading output layer to GPU load_tensors: offloaded 81/81 layers to GPU load_tensors: CUDA0 model buffer size = 35606.98 MiB load_tensors: CPU_Mapped model buffer size = 532.31 MiB .................................................................................................. llama_context: constructing llama_context llama_context: n_seq_max = 12 llama_context: n_ctx = 16384 llama_context: n_ctx_per_seq = 1365 llama_context: n_batch = 2048 llama_context: n_ubatch = 512 llama_context: causal_attn = 1 llama_context: flash_attn = 1 llama_context: freq_base = 500000.0 llama_context: freq_scale = 1 llama_context: n_ctx_per_seq (1365) < n_ctx_train (131072) -- the full capacity of the model will not be utilized llama_context: CUDA_Host output buffer size = 5.87 MiB llama_kv_cache_unified: CUDA0 KV buffer size = 5120.00 MiB llama_kv_cache_unified: size = 5120.00 MiB ( 16384 cells, 80 layers, 12 seqs), K (f16): 2560.00 MiB, V (f16): 2560.00 MiB llama_context: CUDA0 compute buffer size = 266.50 MiB llama_context: CUDA_Host compute buffer size = 52.13 MiB llama_context: graph nodes = 2567 llama_context: graph splits = 2 main: n_kv_max = 16384, n_batch = 2048, n_ubatch = 512, flash_attn = 1, is_pp_shared = 0, n_gpu_layers = 999, n_threads = 12, n_threads_batch = 12 | PP | TG | B | N_KV | T_PP s | S_PP t/s | T_TG s | S_TG t/s | T s | S t/s | |-------|--------|------|--------|----------|----------|----------|----------|----------|----------| | 512 | 128 | 1 | 640 | 14.184 | 36.10 | 42.285 | 3.03 | 56.468 | 11.33 | | 512 | 128 | 2 | 1280 | 8.941 | 114.53 | 50.120 | 5.11 | 59.060 | 21.67 | | 512 | 128 | 4 | 2560 | 17.983 | 113.88 | 71.604 | 7.15 | 89.587 | 28.58 | | 512 | 128 | 6 | 3840 | 27.168 | 113.07 | 81.013 | 9.48 | 108.181 | 35.50 | | 512 | 128 | 8 | 5120 | 36.480 | 112.28 | 93.166 | 10.99 | 129.646 | 39.49 | | 512 | 128 | 10 | 6400 | 45.901 | 111.54 | 95.976 | 13.34 | 141.877 | 45.11 | | 512 | 128 | 12 | 7680 | 55.496 | 110.71 | 78.255 | 19.63 | 133.751 | 57.42 | llama_perf_context_print: load time = 148042.28 ms llama_perf_context_print: prompt eval time = 718462.74 ms / 27408 tokens ( 26.21 ms per token, 38.15 tokens per second) llama_perf_context_print: eval time = 42280.79 ms / 128 runs ( 330.32 ms per token, 3.03 tokens per second) llama_perf_context_print: total time = 866615.25 ms / 27536 tokens ``` ``` ./build/bin/llama-bench -m ../Meta-Llama-3.1-70B-Instruct-IQ4_XS.gguf -ngl 999 -fa 1 -n 0 -p 64,128,256,512 ggml_cuda_init: GGML_CUDA_FORCE_MMQ: no ggml_cuda_init: GGML_CUDA_FORCE_CUBLAS: no ggml_cuda_init: found 1 CUDA devices: Device 0: Orin, compute capability 8.7, VMM: yes | model | size | params | backend | ngl | fa | test | t/s | | ------------------------------ | ---------: | ---------: | ---------- | --: | -: | --------------: | -------------------: | | llama 70B IQ4_XS - 4.25 bpw | 35.29 GiB | 70.55 B | CUDA | 999 | 1 | pp64 | 71.54 ± 0.06 | | llama 70B IQ4_XS - 4.25 bpw | 35.29 GiB | 70.55 B | CUDA | 999 | 1 | pp128 | 109.25 ± 0.26 | | llama 70B IQ4_XS - 4.25 bpw | 35.29 GiB | 70.55 B | CUDA | 999 | 1 | pp256 | 91.70 ± 46.86 | | llama 70B IQ4_XS - 4.25 bpw | 35.29 GiB | 70.55 B | CUDA | 999 | 1 | pp512 | 113.74 ± 0.19 | build: 716301d1 (5757) ``` --- --- url: /aipod/olddocs/benchmark.md --- # LLM 随着上下文的变长,生成 tokens 的速度会稍微变慢。 ## llama.cpp 加载器 | 模型 | CPU | GPU (cuda) | |:----------------------------------------|:--------------|:--------------------------| | Meta-Llama-3.1-70B-Instruct-Q5\_K\_S.gguf | 0.29 tokens/s | 3.04 tokens/s (电源: 60W) | | llama-2-7b-chat.Q4\_0.gguf | | 28 tokens/s (电源: 43W) | | | | | ## 使用 MLC 加载器, 使用 MLC 加载会比 llama.cpp 和 直接用 python transformers 要快 这个是正常使用,提问问题的速度,随着问题的变长而有所变慢. | 模型 | CPU | GPU (cuda) | |:----------------------------------------|:----|:--------------------------| | mlc-ai/Qwen2.5-72B-Instruct-q4f16\_1-MLC | | 3.3 tokens/s (电源: 56W) | | mlc-ai/Qwen2.5-32B-Instruct-q4f16\_1-MLC | | 7.5 tokens/s (电源: 53W) | | mlc-ai/Qwen2.5-14B-Instruct-q4f16\_1-MLC | | 16.3 tokens/s (电源: 55w) | | mlc-ai/Llama-2-13b-chat-hf-q4f16\_1-MLC | | 16.4 tokens/s (电源: 58w) | 官方在给出的 [benchmark](https://www.jetson-ai-lab.com/benchmarks.html) 中,限制 了生成的 token 长度,和 prompt 的长度,并都是第一次加载,没有上下文的。下面是用 官方的测试出来的结果. | 模型 | CPU | GPU (cuda) | |:-----------------------------------------|:----|:------------------------------------| | mlc-ai/Qwen2.5-72B-Instruct-q4f16\_1-MLC | | 3.49 tokens/s | | mlc-ai/Llama-3-70B-Instruct-q4f16\_1-MLC | | 4.1 tokens/s (电源: 62W) | | mlc-ai/Qwen2.5-32B-Instruct-q4f16\_1-MLC | | 8.2 tokens/s | | mlc-ai/Qwen2.5-14B-Instruct-q4f16\_1-MLC | | 17.6 tokens/s | | mlc-ai/Llama-2-13b-chat-hf-q4f16\_1-MLC | | 20.6 tokens/s (官方: 25.1 tokens/s) | | mlc-ai/Llama-3.1-8B-Instruct-q4f16\_1-MLC | | 32.3 tokens/s (电源: 55W) | | mlc-ai/Llama-3-8B-Instruct-q4f16\_1-MLC | | 32.2 tokens/s (官方: 40 tokens/s) | | mlc-ai/Qwen2.5-7B-Instruct-q4f32\_1-MLC | | 25.73 tokens/s | # ASR 语言识别 测试声音: 一个17分钟晨会的录音(中文) | 模型 | 框架 | 推理时间 | 比率(处理长度/s) | 效果 | |:--------------|:--------|:---------|:-------------------|--------------------------------| | whisper turbo | whisper | 192.298s | 5.3125 | | | paraformer-zh | funasr | 81.551s | 12.59 | | | SenseVoice | funasr | 37.49 | 27.20 | | 测试声音: 一个22分32秒电影声音(中文) | 模型 | 框架 | 推理时间 | 比率(处理长度/s) | 效果 | |:--------------|:--------|:---------|:-------------------|----------------------------------------------------------| | whisper turbo | whisper | 230s | 5.878 | 部分中文错误,但大部分台词都能识别 | | whisper tiny | whisper | 252s | 5.36 | 大部分的中文错误,质量太差 | | paraformer-zh | funasr | 86.384 | 15.65 | 感觉生成的质量比较好 | | SenseVoice | funasr | 44.83 | 30.15 | 生成的速度最快,但感觉少了很多,只有比较突出的声音被识别 | 测试声音: 一个14分钟的英语up说话 | 模型 | 框架 | 推理时间 | 比率(处理长度/s) | 效果 | |:----------------|:--------|:---------|:-------------------|--------------------------------------------| | whisper turbo | whisper | 162.48s | 5.16 | 在英语上,turbo 的效果和 tiny 的差别也不大 | | whisper tiny | whisper | 127s | 6.614 | 对英文来说, tiny.en 和 tiny 没有太多的区别 | | whisper tiny.en | whisper | 123s | 6.82 | | | SenseVoice | funasr | 36.12s | 23.25 | | `whisper turbo` 和 `whisper tiny` 的差别在 `turbo` 模型的学习能力更强(更强的泛化 能力),可以面对更多的未知的情况,而 `tiny` 在英语上很好,但在其他语言上就不行了。 `whisper` 非常适合英语环境中 `up主说话` 或者电影这些数据,断句和句子,以及标点符 合都非常好. `paraformer-zh` 和 `SenseVoice` 在输出上,都会输出成一个长句,(这个估计是 funasr 相关的都会在识别后,做一次词的重新整理,重新组合文本). 但也会导致在长语 音中,把本来应该分开的两个放在一个句子中。 ```sh ssh nvidia2 cd lnks jetson-containers run -v `pwd`:/workspace funasr_whisper_test:latest cd /workspace/funasr python3 funasr_paraformer-zh_test.py python3 funasr_sense_voice-test.py ``` --- --- url: /aipod/issues/lzc-app-forward-to-ai-service.md --- # LZC路由中转发到AI服务 一个简单的AI应用,只有一个算力舱中部署的服务,一些服务把界面这些也包括进去了。 服务在算力舱中部署后,可以通过 `https://${服务名称}-ai.${微服名称}.heiyu.space` 访问。 而在 LPK 应用的路由中,您可能会像下面这样子写 ```yml routers: - /=https://${服务名称}-ai.${微服名称}.heiyu.space ``` ## 微服 1.3.8+ 系统 使用 微服系统的 1.3.8 [upstreams](https://developer.lazycat.cloud/spec/manifest.html#%E5%8D%81%E3%80%81upstreamconfig-%E9%85%8D%E7%BD%AE) 特性实现 ```yml application: upstreams: - location: / backend: https://comfyui-ai.{{ .S.BoxDomain }} use_backend_host: true dump_http_headers_when_5xx: true ``` 使用模板[manifest.yml](https://developer.lazycat.cloud/advanced-manifest-render.html#%E6%A8%A1%E6%9D%BF%E5%8F%82%E6%95%B0) ## 微服 1.3.8 之前的系统 这种情况下,您在路由中不能知道当前访问的 `${微服名称}`,所以需要一个转发工具来处理,比如 `nginx` 或者 `caddy` ```yml application: routes: - /=http://caddy:80 services: caddy: image: registry.lazycat.cloud/caddy:2.9.1-alpine setup_script: | cat <<'EOF' > /etc/caddy/Caddyfile { auto_https off http_port 80 https_port 0 } :80 { redir https://${服务名称}-ai.{$LAZYCAT_BOX_DOMAIN} permanent } EOF cat /etc/caddy/Caddyfile ``` --- --- url: /aipod/issues/mdns_notfound.md --- # MDNS 发现不了设备 场景: 算力舱在插着有线的情况下,微服不能通过 mdns 发现算力舱。 解决方法: 1. 在微服中使用 `hc ustc` 更改 `apt` 源(如果所处的环境能直接从 apt 更新,则跳过这一步). 2. 微服中终端中使用 `apt install avahi-utils` 3. 安装后,使用 `avahi-browser -a` 查询局域网中的广播(如果能接收到 `_ai_jetson` 的广播,则表示可以 mdns 正常,可以排除 mdns 因素) 4. 使用 `avahi-daemon -r` 尝试重启 `daemon`,成功后,再确认步骤3 --- --- url: /aipod/ocr.md --- # OCR 在算力舱中部署了一个基于 `paddleocr` 的 `ocr` 服务. ## 文档 `ocr` 服务的 api 可以通过 查看。 ## 本地使用 ```bash curl -X 'POST' \ 'https://ocr-ai.13gxg.heiyu.space/ocr' \ -H 'accept: application/json' \ -H 'Content-Type: multipart/form-data' \ -F 'file=@ocr-4.png;type=image/png' \ -F 'request={"max_size":1920,"overlap":100,"memory_limit_mb":1024,"det":true,"rec":true,"cls":true}' ``` --- --- url: /aipod/ollama/app-use-ollama-api.md --- # Ollama API 算力舱中默认部署了 `Ollama`,对于微服中的应用可以通过直接使用算力舱暴露的 `Ollama API` 来使用。 * `ollama` 地址为 * `ollama` 兼容 `OpenAI API` 地址为 如果您本地也安装了微服客户端,您也可以使用上面的连接给您本地的应用调用。比如可以直接使用本地的 curl 访问。 ```sh curl https://ollama-ai.${微服名称}.heiyu.space/v1/chat/completions \ -H "Content-Type: application/json" \ -d '{"model": "qwen3:4b", "messages": [{"role": "user", "content": "Hello!"}]}' ``` 算力舱中的 `ollama` 也将端口暴露在局域网中了,您可以通过 `http://算力舱ip:11434` 来访问 `ollama` 服务. 算力舱的局域网ip可以在设备列表中[查看](/os/introduction.html#ssh)。 ## python 示例 ```python import base64 import requests import json # 获取图片并进行 base64 编码 image_url = "https://i-blog.csdnimg.cn/direct/7184675ec6ad495e8b7469c17edd56d9.png" try: response = requests.get(image_url) response.raise_for_status() # 检查请求是否成功 image_data = response.content encoded_image = base64.b64encode(image_data).decode('utf-8') except requests.exceptions.RequestException as e: print(f"Error downloading image: {e}") exit(1) # 构建请求的 JSON 数据 request_data = { "model": "qwen3-vl:2b-instruct", "messages": [ { "role": "user", "content": [ { "type": "text", "text": "提取文字为 Markdown 格式,要求格式正确。" }, { "type": "image_url", "image_url": { "url": f"data:image/jpeg;base64,{encoded_image}" } } ] } ] } ollama_api_url = "https://ollama-ai.${微服名称}.heiyu.space/v1/chat/completions" headers = { "Content-Type": "application/json" } try: response = requests.post(ollama_api_url, headers=headers, data=json.dumps(request_data)) response.raise_for_status() # 检查请求是否成功 # 打印响应 print(response.json()) except requests.exceptions.RequestException as e: print(f"Error sending request to Ollama API: {e}") ``` --- --- url: /aipod/benchmark/deepseek-r1.md --- # ollama deepseek-r1:70b ollama 中的 deepseek-r1:70b 模型镜像为 43GB, 加载到内测中的后占用内测为 46GB. ``` deepseek-r1:70b d37b54d01a76 46 GB 100% GPU 8192 4 minutes from now total duration: 7m10.425334424s load duration: 56.463007ms prompt eval count: 25 token(s) prompt eval duration: 44.639105ms prompt eval rate: 560.05 tokens/s eval count: 1480 token(s) eval duration: 7m10.322503313s eval rate: 3.44 tokens/s ``` --- --- url: /aipod/ollama/delete-model.md --- # ollama 中删除模型 ## Open WebUI 中删除模型 ![open webui delete model](/assets/openwebui-delete-model.DUAKooED.png) 1. 点击右下角的图标,在弹出的菜单栏中选择 “管理员设置” 2. 点击管理员设置中的 “设置” 标签 3. 点击模型管理 4. 选择您选删除的模型 5. 点击删除模型按钮 ## webollama 中删除模型 ![webollama delete model](/assets/webollama-delete-model.Djuidkww.png) 1. 点击模型列表,查看当前的模型。 2. 选择需要删除的模型,点击右边的删除图标 ## ollama 命令行删除 1. ssh 到算力舱中,比如 `ssh nvidia@192.168.1.130` 2. 执行 `docker exec -ti ollama-ollama-1 bash` 3. 执行 `ollama ls` 列出当前的所有模型 ```bash NAME ID SIZE MODIFIED qwen3-vl:8b 901cae732162 6.1 GB 37 minutes ago qwen3:30b-a3b-instruct-2507-q4_K_M 19e422b02313 18 GB 5 hours ago qwen3-vl:30b eda0be100877 19 GB 25 hours ago phi3:14b cf611a26b048 7.9 GB 3 weeks ago qwen3:4b-instruct-2507-q4_K_M 088c6bc07f1d 2.5 GB 5 weeks ago qwen3:4b e55aed6fe643 2.5 GB 2 months ago qwen3:14b 7d7da67570e2 9.3 GB 6 months ago qwen3:8b e4b5fd7f8af0 5.2 GB 6 months ago qwen3:1.7b 458ce03a2187 1.4 GB 6 months ago ``` 4. 执行您需要删除的模型,比如 `ollama rm qwen3:1.7b` ![ollama cli delete model](/assets/ollama-cli-delete-model.DVyOOvN0.png) --- --- url: /aipod/ollama/download-model.md --- # ollama 中添加模型 打开 `https://ollama.com/search` 查看 `ollama` 支持的模型,选择一个您想拉取的模型。比如我现在想拉取 `deepseek-r1:70b` 模型 ## 使用 Open-WebUI 中拉取模型 * 安装 Open WebUI 应用,[点击跳转](https://appstore.lazycat.cloud/#/shop/detail/cloud.lazycat.aipod.openwebui) * 点击 `Open-WebUI` 左上角的模型名称,点击后会弹出一个下拉框,让您切换模型。 ![Open-WebUI切换模型下拉框](/assets/Open-WebUI-switch-model-dropdown.Dc7KeYiF.png) * 当下拉的列表中没有您需要的模型时,您可以手动填写一个 `deepseek-r1:70b` 到搜索框中,这个时候会提示您 "从 Ollama.com 中拉取 deepseek-r1:70b" ![Open-WebUI从ollama拉取模型](/assets/Open-WebUI-pull-model-from-ollama.BL_diF36.png) * 点击 "从 Ollama.com 中拉取 deepseek-r1:70b",就会到后台拉取模型,界面上也会显示进度 ![Open-WebUI拉取模型进度](/assets/Open-WebUI-pull-model-progress.BpV013X4.png) ## 使用 ollama 命令行下载模型 * 首先,您需要通过 ssh 或者 显示屏 进去到算力舱的系统中 * 执行 `docker exec -ti ollama-ollama-1 bash` 进去到 `ollama` 的容器中 * 执行 `ollama pull deepseek-r1:70b` 即可 ## 使用 webollama 拉取模型 1. 安装 `webollama` 应用,[点击跳转](https://appstore.lazycat.cloud/#/shop/detail/cloud.lazycat.aipod.webollama) 2. 打开后,您可以看到以下界面,根据提示拉取模型 ![webollama-pull-model.png](/assets/webollama-pull-model.DaN_sFWR.png) 使用 `webollama` 拉取模型中,目前没有进度,请耐心等待(建议使用上面两种方法拉取,可以查看进度) --- --- url: /aipod/thor/benchmark.md --- # onnx 查看onnx的输入和输出 ``` python -c " import onnx model = onnx.load('zh-clip-vit-roberta-large-patch14-vision-openvino.onnx') for input in model.graph.input: print(f'Input name: {input.name}') for dim in input.type.tensor_type.shape.dim: print(f' Dimension: {dim.dim_value}') " ``` # ollama 1. 镜像使用: ghcr.io/nvidia-ai-iot/ollama:r38.2.arm64-sbsa-cu130-24.04 2. ```sh docker run --gpus all --runtime nvidia --rm -ti -v /ssd/lzc-ai-agent/data/ollama/data:/data/models/ollama ghcr.io/nvidia-ai-iot/ollama:r38.2.arm64-sbsa-cu130-24.04 ``` | Models | Thor Tokens/s | Orin Tokens/s | |:----------|:---------------|:---------------| | qwen3:14b | 20.44 tokens/s | 13.36 tokens/s | | | | | | | | | # Resnet50 1. 数据来源: /usr/src/tensorrt/data/resnet50 2. 执行命令: ```sh curl -L -O https://media.githubusercontent.com/media/onnx/models/refs/heads/main/validated/vision/classification/resnet/model/resnet50-v1-12.onnx /usr/src/tensorrt/bin/trtexec --onnx=resnet50-v1-12.onnx --shapes=data:4x3x224x224 --stronglyTyped --noDataTransfers --useCudaGraph --useSpinWait --duration=300 ``` | 设备 | 类型 | 批量 | 吞吐量 每秒/张 | 延迟性能 每张/秒 | 温度 | 电源 | 输入尺寸 | |------|--------|------|--------------------|------------------|------|-------|-------------| | Orin | 源类型 | 4 | 238.496 x 4 = 953 | 4.1875 ms | | 62.3w | 4×3×224×224 | | Thor | 源类型 | 4 | 588.473 x 4 = 2353 | 1.59375 ms | | - | 4×3×224×224 | | | | | | | | | | | Orin | 源类型 | 8 | 129.226 x 8 = 1033 | 7.73438 ms | 70 | 63.4w | 8×3×224×224 | | Thor | 源类型 | 8 | 317.383 x 8 = 2539 | 3.07031 ms | 78 | - | 8×3×224×224 | | | | | | | | | | | Orin | int4 | 8 | 129.157 x 8 = 1033 | 7.73438 ms | 72 | 63.4w | 8×3×224×224 | | Thor | int4 | 8 | 319.255 x 8 = 2554 | 3.07031 ms | 78 | 195w | 8×3×224×224 | | | | | | | | | | | Orin | int8 | 8 | 493.355 x 8 = 3946 | 2.02734 ms | 72 | 63.4w | 8×3×224×224 | | Thor | int8 | 8 | 486.597 x 8 = 3892 | 3.07031 ms | 78 | - | 8×3×224×224 | | | | | | | | | | | Orin | best | 8 | 129.797 x 8 = 1038 | 7.70264 ms | - | - | 8×3×224×224 | | Thor | best | 8 | 645.349 x 8 = 5162 | 1.51562 ms | - | - | 8×3×224×224 | # clip vision 1. 数据来源: curl -L -O http://dl.corp.linakesi.cn/lzc-image-search-model/onnx-export/vision/zh-clip-vit-roberta-large-patch14-vision-openvino.onnx 2. 执行命令 ```sh /usr/src/tensorrt/bin/trtexec --onnx=zh-clip-vit-roberta-large-patch14-vision-openvino.onnx --shapes=pixel_values:8x3x224x224 --int8 --noDataTransfers --useCudaGraph --useSpinWait --duration=300 ``` | 设备 | 类型 | 批量 | 吞吐量 每秒/张 | 延迟性能 每张/秒 | 温度 | 电源 | 输入尺寸 | |------|------|------|-------------------|------------------|------|-----------------------|-------------| | Orin | int8 | 8 | 8.72568 x 8 = 64 | 114.576 ms | - | - | 8×3×224×224 | | Thor | int8 | 8 | 54.6192 x 8 = 436 | 17.9922 ms | - | - | 8×3×224×224 | | | | | | | | | | | Orin | int4 | 8 | 7.25669 x 8 = 56 | 137.828 ms | 72 | 71W | 8×3×224×224 | | Thor | int4 | 8 | 16.6125 x 8 = 128 | 60.0859 ms | 82 | 平均 112W(瞬时到120W) | 8×3×224×224 | | | | | | | | | | | Orin | fp16 | 8 | 17.639 x 8 = 141 | 56.8906 ms | 75 | 74W | 8×3×224×224 | | Thor | fp16 | 8 | 60.4162 x 8 = 480 | 16.4219 ms | 100 | 平均 150W(瞬时到180W) | 8×3×224×224 | | | | | | | | | | | Orin | best | 8 | 18.39 x 8 = 147 | 54.1875 ms | - | - | 8×3×224×224 | | Thor | best | 8 | 87.641 x 8 = 701 | 11.0312 ms | - | - | 8×3×224×224 | thor 的温度下降的很快,从80度下载到60只用几秒, 但 thor 的功率会有时候达到 180 W多 # clip text 1. 数据来源: curl -L -O https://dl.corp.linakesi.cn/lzc-image-search-model/onnx-export/text/zh-clip-vit-roberta-large-patch14-text-openvino.onnx 2. 执行命令 ```sh /usr/src/tensorrt/bin/trtexec \ --onnx=zh-clip-vit-roberta-large-patch14-text-openvino.onnx \ --minShapes=input_ids:1x77,attention_mask:1x77 \ --optShapes=input_ids:8x77,attention_mask:8x77 \ --maxShapes=input_ids:32x77,attention_mask:32x77 \ --shapes=input_ids:8x77,attention_mask:8x77 \ --best \ --noDataTransfers \ --useCudaGraph \ --useSpinWait \ --duration=300 ``` | 设备 | 类型 | 批量 | 吞吐量 每秒/张 | 延迟性能 每张/秒 | 温度 | 电源 | 输入尺寸 | |------|------|------|--------------------|------------------|------|------|----------| | Orin | best | 8 | 70.645 x 8 = 565 | 14.1562 ms | - | - | 8×77 | | Thor | best | 8 | 277.171 x 8 = 2217 | 3.57812 ms | - | - | 8x77 | | | | | | | | | | | Orin | fp16 | 8 | 70.6059 x 8 = 565 | 14.1562 ms | - | - | 8x77 | | Thor | fp16 | 8 | 177.429 x 8 = 1419 | 5.625 ms | - | - | 8×77 | | | | | | | | | | | Orin | int8 | 8 | 38.5414 x 8 = 208 | 25.9375 ms | - | - | 8x77 | | Thor | int8 | 8 | 246.038 x 8 = 1968 | 4.06298 ms | - | - | 8×77 | # yolov8s 1. 数据来源: curl -L -O http://dl.corp.linakesi.cn/lzc-ai/onnx/yolo/yolov8s.onnx (静态类型的 onnx,不能指定输入形状,默认为 1x3x640x640) 2. 执行命令 ```sh /usr/src/tensorrt/bin/trtexec \ --onnx=yolov8s.onnx \ --best \ --noDataTransfers \ --useCudaGraph \ --useSpinWait \ --duration=300 ``` | 设备 | 类型 | 批量 | 吞吐量 每秒/张 | 延迟性能 每张/秒 | 温度 | 电源 | 输入尺寸 | |------|------|------|--------------------|------------------|------|------|-------------| | Orin | best | 1 | 559.474 x 1 = 559 | 1.78125 ms | - | - | 1x3x640x640 | | Thor | best | 1 | 1320.01 x 1 = 1320 | 0.720703 ms | - | - | 1x3x640x640 | | | | | | | | | | | Orin | int4 | 1 | 188.694 x 1 = 188 | 5.29688 ms | - | - | 1x3x640x640 | | Thor | int4 | 1 | 565.56 x 1 = 565 | 1.73438 ms | - | - | 1x3x640x640 | | | | | | | | | | | Orin | int8 | 1 | 542.293 x 1 = 542 | 1.84375 ms | - | - | 1x3x640x640 | | Thor | int8 | 1 | 1203.38 x 1 = 1203 | 0.820312 ms | - | - | 1x3x640x640 | | | | | | | | | | | Orin | fp16 | 1 | 372.599 x 1 = 372 | 2.68652 ms | - | - | 1x3x640x640 | | Thor | fp16 | 1 | 1116.32 x 1 = 1116 | 0.890625 ms | - | - | 1x3x640x640 | # dino-v2 1. 数据来源: curl -L -O http://dl.corp.linakesi.cn/lzc-ai/onnx/dinov2.onnx 2. 执行命令 ```sh /usr/src/tensorrt/bin/trtexec \ --onnx=dinov2.onnx \ --minShapes=pixel_values:1x3x518x518 \ --optShapes=pixel_values:8x3x518x518 \ --maxShapes=pixel_values:32x3x518x518 \ --shapes=pixel_values:8x3x518x518 \ --best \ --noDataTransfers \ --useCudaGraph \ --useSpinWait \ --duration=300 ``` | 设备 | 类型 | 批量 | 吞吐量 每秒/张 | 延迟性能 每张/秒 | 温度 | 电源 | 输入尺寸 | |------|------|------|------------------|------------------|------|------|-------------| | Orin | best | 8 | 3.01077 x 8 = 24 | 332.203 ms | - | - | 8x3x518x518 | | Thor | best | 8 | 3.48498 x 8 = 24 | 283.906 ms | - | - | 8x3x518x518 | | | | | | | | | | | Orin | int4 | 8 | 0.793952 x 8 = 6 | 1260.28 ms | - | - | 8x3x518x518 | | Thor | int4 | 8 | 1.60084 x 8 = 12 | 622.144 ms | - | - | 8x3x518x518 | | | | | | | | | | | Orin | int8 | 8 | 0.974057 x 8 = 8 | - ms | - | - | 8x3x518x518 | | Thor | int8 | 8 | 2.41794 x 8 = 16 | 397.922 ms | - | - | 8x3x518x518 | | | | | | | | | | | Orin | fp16 | 8 | 3.10437 x 8 = 18 | 322.125 ms | - | - | 8x3x518x518 | | Thor | fp16 | 8 | 9.98557 x 8 = 80 | 98.1719 ms | - | - | 8x3x518x518 | | | | | | | | | | | Orin | bf16 | 8 | 2.99196 x 8 = 24 | 334.617 ms | - | - | 8x3x518x518 | | Thor | bf16 | 8 | 10.9799 x 8 = 88 | 90.6172 ms | - | - | 8x3x518x518 | --- --- url: /aipod/olddocs/chattts.md --- # pynini 这个库在 jetson 下没有,需要自己构建 --- --- url: /aipod/quantum/cuda-q.md --- # Quantum Computing `jetson agx orin` 理论上是支持 `CUDA-Q`,但 `nvidia` 现在主推 `dgx`,在 `jetson` 上估计适配的概率不大。 ## Test 根据这个 [Quick Start](https://nvidia.github.io/cuda-quantum/latest/using/quick_start.html#quick-start) 中的例子,能编译,但运行的时候会出现错误。 https://forums.developer.nvidia.com/t/cuda-q-sample-code-initialization-error/340400 ## Links 1. [NVIDIA CUDA-Q](https://nvidia.github.io/cuda-quantum/latest/using/quick_start.html) 2. [quantum-computing](https://www.nvidia.com/en-us/glossary/quantum-computing/) 3. [Low-Cost, Low-Power, High-Capacity Quantum Simulation Device](https://www.ezchips.org/low-cost-low-power-high-capacity-quantum-simulation-device/) 4. [dependencies-and-compatibility](https://nvidia.github.io/cuda-quantum/latest/using/install/local_installation.html#dependencies-and-compatibility) 5. [NVIDIA CUDA Quantum](https://catalog.ngc.nvidia.com/orgs/nvidia/teams/quantum/containers/cuda-quantum) --- --- url: /aipod/olddocs/rag.md --- # qwen-agent 1. 使用 ollama 加载 llm 模型(都是量化成 4bit 的模型) 2. 测试文档: 阿基米德的报复.pdf 3. 需要将 qwen2.5 在模型在 ollama 中更改上下文为 32k (qwen2.5 的支持上下文为 128k) pdf页数: 124页 解析pdf花费: 25.250 秒 ![qwen agent assistant](/assets/qwen-agent-assistant.I4RjEvL6.png) ![qwen agent assistant 3b](/assets/qwen-agent-assistant2.DrNnniHr.png) ![qwen agent assistant 3b](/assets/qwen-agent-assistant3.DvCdUSxL.png) qwen-agent assistant:解析较快 qwen-agent docqa:解析成本高,但准确率高,可用在超长文档问答 | 模型 | 方案 | 解析pdf总tokens数 | 推理时间 | 回答是否正确 | |:-----------------|:---------------------|-------------------|:---------|--------------| | qwen2.5:0.5b 32k | qwen-agent assistant | 128829(约13万) | 15s | No | | qwen2.5:0.5b 32k | qwen-agent docqa | 149482(约15万) | 150s | No | | qwen2.5:1.5b 32k | qwen-agent assistant | 128829 | 20s | Yes | | qwen2.5:1.5b 32k | qwen-agent docqa | 149482 | 160s | No | | qwen2.5:3b 32k | qwen-agent assistant | 128829 | 21s | Yes | | qwen2.5:3b 32k | qwen-agent docqa | 149482 | 230s | Yes | | qwen2.5:14b 32k | qwen-agent assistant | 128829 | 50s | Yes | | qwen2.5:14b 32k | qwen-agent docqa | 149482 | 750s | Yes | ## 使用llm从查询的信息部分推导出多语言关键词 qwen2.5:0.5b: {"keywords\_zh": \["伏尔泰", "vulgate"], "text": "伏尔泰\n在书中说了"} qwen2.5:1.5b: {"keywords\_zh": \["伏尔泰书", "伏尔泰的书籍"], "keywords\_en": \["Voltaire's book"], "text": "伏尔泰书中的内容是什么"} qwen2.5:3b: {"keywords\_zh": \["伏尔泰", "书", "话", "内容"], "keywords\_en": \["Voltaire", "book", "sentence", "content"], "text": "伏尔泰在书中说了什么话?"} qwen2.5:14b: {"keywords\_zh": \["伏尔泰", "书", "说话", "内容"], "keywords\_en": \["Voltaire", "book", "quote", "content"], "text": "伏尔泰在书中说了什么话"} 做 RAG 的时候,需要将模型的上下文长度调整,否则会不准确,在测试中,发现 qwen2.5:14b 在 ollama 模型的默认的2048上下文中,不能回答正确,但在 32k 的上下文中回答正确. llm 越大,其对关键词的描述(或者整理后的结果)就越接近实际的问题,匹配出来的结果也越精准。 [使用ollama本地服务时问答效果不佳](https://github.com/netease-youdao/QAnything/blob/qanything-v2/FAQ_zh.md#%E4%BD%BF%E7%94%A8ollama%E6%9C%AC%E5%9C%B0%E6%9C%8D%E5%8A%A1%E6%97%B6%E9%97%AE%E7%AD%94%E6%95%88%E6%9E%9C%E4%B8%8D%E4%BD%B3) --- --- url: /aipod/benchmark/qwen3-coder-next.md --- # Qwen3 Coder Next | Model | Name | Ctx | Memory | Token/s | |:----------------|:---------------------------------|:-----|--------|:--------| | Thor | Qwen3-Coder-Next-UD-Q4\_K\_XL.gguf | 256k | 55G | 22.28 | | Jetson agx orin | Qwen3-Coder-Next-UD-Q4\_K\_XL.gguf | 256k | 58.3G | 17.88 | | | | | | | ::: info jetson agx orin 64G 中跑需要先把 lzc-earlyoom 服务停止掉,否则会触发杀服务 `sudo systemctl stop lzc-earlyoom` ::: --- --- url: /aipod/benchmark/qwen3-8b-embedding.md --- # qwen3-embedding-8b ### ollama ``` python3 ollama_perf.py --file GuiMiZhiZhuu.txt --url https://ollama-ai.13gxg.heiyu.space/v1/embeddings --model dengcao/Qwen3-Embedding-8B:Q8_0 --- 测试参数 --- 文件路径: GuiMiZhiZhuu.txt 模型名称: dengcao/Qwen3-Embedding-8B:Q8_0 API URL: https://ollama-ai.13gxg.heiyu.space/v1/embeddings 切片长度: 1024 字符 总字数: 4775359 总切片数: 4664 注意: 所有切片将在一个 API 请求中发送。 ------------------ 开始发送单个大请求,请稍候... 请求完成! --- 性能测试结果 --- 总耗时: 3763.11 秒 总字数: 4775359 总处理 Tokens: 3325333 请求状态: 成功 (HTTP 200) --- 核心指标 --- 平均 Token 速度: 883.67 tokens/秒 平均吞吐量: 1268.99 字/秒 -------------------- ``` 小文件 ``` $ python3 ollama_perf.py --file xce --url https://ollama-ai.13gxg.heiyu.space/v1/embeddings --model dengcao/Qwen3-Embedding-8B:Q5_K_M --- 测试参数 --- 文件路径: xce 模型名称: dengcao/Qwen3-Embedding-8B:Q5_K_M API URL: https://ollama-ai.13gxg.heiyu.space/v1/embeddings 切片长度: 1024 字符 总字数: 41648 总切片数: 41 注意: 所有切片将在一个 API 请求中发送。 ------------------ 开始发送单个大请求,请稍候... 请求完成! --- 性能测试结果 --- 总耗时: 34.52 秒 总字数: 41648 总处理 Tokens: 29006 请求状态: 成功 (HTTP 200) --- 核心指标 --- 平均 Token 速度: 840.33 tokens/秒 平均吞吐量: 1206.59 字/秒 -------------------- ``` ### vllm 默认为官方的 Qwen/Qwen3-Embedding-8B bfloat16 类型 ``` $ python3 ollama_perf.py --file GuiMiZhiZhuu.txt --url http://192.168.1.209:8999/v1/embeddings --model qwen3-embedding-8b --- 测试参数 --- 文件路径: GuiMiZhiZhuu.txt 模型名称: qwen3-embedding-8b API URL: http://192.168.1.209:8999/v1/embeddings 切片长度: 1024 字符 总字数: 4775359 总切片数: 4664 注意: 所有切片将在一个 API 请求中发送。 ------------------ 开始发送单个大请求,请稍候... 请求完成! --- 性能测试结果 --- 总耗时: 2312.80 秒 总字数: 4775359 总处理 Tokens: 3329997 请求状态: 成功 (HTTP 200) --- 核心指标 --- 平均 Token 速度: 1439.81 tokens/秒 平均吞吐量: 2064.75 字/秒 -------------------- ``` 占用内存需要 25 GB --- --- url: /aipod/tts/tts_api.md --- # TTS (文本生成语音) 在算力舱中部署了一个 `Kokoro` 的 `tts` 服务,这个服务的速度比较快。 ## 在线演示 您可以通过 访问在线演示。 ## 文档 `tts` 服务的 api 可以通过 查看。 ::: details 示例 ```vue ``` ::: --- --- url: /aipod/issues/video-to-webm.md --- 1. 在搜索微服中,视频的格式需要为 webm (VP9 编码),验证的方法可以将视频拖到AI浏览器中,检测是否能正常播放。 2. 您可以在网络上下载webm的视频,也可以按照下面提供的教程将视频转变成webm格式。 3. 方法1使用在线的网站转换, https://cloudconvert.com/mp4-to-webm/, https://video.online-convert.com/convert-to-webm, https://convertio.co/mp4-webm/ 4. 方法2使用本地的工具转换, windows 上看 https://videoconvert.minitool.com/video-converter/mp4-to-webm.html 里面介绍几个工具。MacOS https://www.winxdvd.com/video-transcoder/convert-webm-to-mp4-vlc.htm 5. 方法3使用懒猫微服中的 vp9convert,在懒猫微服的应用商店中搜索 `vp9convert` 这个应用,然后安装。安装后可以在网盘中上传您的素材,上传成功后,在 vp9convert 中将可以看到对应的文件。点击 `转换` 即可等待视频转码完成。(转码成功后,记得把不是 webm 的视频从网盘中删除) --- --- url: /aipod/olddocs/llama.cpp.md --- 可以使用 jetson 官方封装好的 text-generation-webui 来测试 llm ```sh jetson-containers run dustynv/text-generation-webui:r36.2.0 ``` `r36.2.0` 是最新提供的版本,但里面的 `llama.cpp python` 这个是比较旧的,会在加载 `llama3.1` 模型和 `70b` 的模型的时候出现 `Attributte: model` 的错误。 需要在 `r36.2.0` 容器中重新构建 `llama.cpp python whl` ```sh pip config set global.index-url https://mirrors.tuna.tsinghua.edu.cn/pypi/web/simple sed -i 's@//.*ports.ubuntu.com@//mirrors.ustc.edu.cn@g' /etc/apt/sources.list apt update && apt install vim pip install poetry cd /opt/llama-cpp-python make update.vendor make build.cuda ``` 构建出来后,可以使用以下命令将 whl 包构建出来,方便其他地方直接安装。 ``` CMAKE_ARGS="-DGGML_CUDA=on" python3 -m pip wheel --verbose -e . ``` --- --- url: /aipod/olddocs/video-understanding.md --- 现在大部分的视频搜索是基于从视频中抽帧实现,比较简单的实现是直接把提取出来图片和 用户提问放在一个 vlm 模型中;稍微复杂一点则除了图片还微调把图片的时间戳信息带进 去,这样就可以在询问中要求模型返回相对应的视频时间点。 但这个时间不能处理太长的视频,因为机器的内存的限制,太长的视频,上下文太多内存会 爆掉(现在的大部分视觉模型都不能处理太长的视频也就是这个原因)。 [Vlog: Video as a Long Document](https://github.com/showlab/VLog?tab=readme-ov-file) 这个项目中,是把视 频的片段先识别成文字(视频的语音通过语音识别成文字,视频的帧图片通过图片描述模型 识别成文字)。最后整个长的视频都变成一个长的文档,这样在用户询问的时候就是类似 RAG 的技术,从数据库中获取数据,然后总结。 另外一个做法是,对于长视频,特别是监控这种视频,大部分场景内视图中是没有物体动的, 导致关键帧很少,可以大大节省模型的上下文。 [LVNet](https://github.com/showlab/VLog?tab=readme-ov-file)就是从解决信息的冗余 度来出发点解决上下文会爆的问题。 但可以根据特定的场景去优化,像下面的场景 ## 场景1: 家庭监控,下班回家后,问AI,今天家里发生了什么? 家庭监控的场景下,视频长度不可控,大部分情况下很长,如果通过把视频的内容都丢到视觉模型中(如 qwen2-vl, llava, 带vision的语言模型)去理解,会导致内存爆掉。 这个场景我觉得可以 1. 摄像头在实时监控的时候,就使用类似 yolo 物体探测 或者 类似监控人体活动 的比较成熟的小模型来记录有人在动(如回家,坐下,站起来等时间) 2. 在做活动监控的时候,也通过语言识别的模型,可以查看当前时间点的声音 3. 把识别到的数据统一记录到数据库 4. 在用户询问的时候就是从数据库中查找数据,然后在总结(这就又类似于 RAG 的实现了) 在这个情况下,像家庭监控这个需求,就可以不需要多高算力 [ChatVideo](https://www.wangjunke.info/ChatVideo/) 是一个类似的做法. ![ChatVideo](/assets/ChatVideo.Bw9QiBTk.png) ## 场景2: 视频搜索 视频搜索,类似图片搜索,它不需要将所有的帧都给到一个大语言模型中让大语言模型理解, 只需要从图片中获取特征,然后根据特征进行匹配,这种就可以通过抽帧的方式实现,然后 将每一帧都向量化后存在数据库中。 这个情况下,就可以使用 CLIP 或者 其他图片编码模型都可以 ## 场景3: 视频理解 类似鸿蒙小艺这种,就用户当前的屏幕(单一图片),或者某一段比较短的视频进行理解。这些就可以使用带视觉的大模型实现(如 qwen2-vl, 内部也是通过对视频抽帧,然后把图片给大模型来理解,大模型理解后,就可以根据图片的内容来问答) ## Demo: Multimodal-RAG-on-Jetson 1. 通过 ffmpeg 将声音从视频中提取出来 2. 将声音进行切片,然后使用 `whisper turbo` 识别出来文字 3. 将视频抽帧,然后使用 `ollama llava-llama3` 总结图片中的内容,输出文字保存 4. 然后通过 `bge-m3` 做向量化 5. 最后使用 `llama-index` 结合 `llava-llama3` 做 `RAG` 搜索 jetson 上的 ffmpeg 需要单独编译,才能使用 jetson 的硬件加速 [jetson-ffmpeg](https://github.com/Keylost/jetson-ffmpeg) ## Qwen2-VL 模型测试 一个 12s 的视频,根据 fps=1 的处理,在处理后,具有 12 帧,放到 Qwen2-VL-7B-Instruct 中处理,然后对这个这个视频进行总结 模型只能根据视频中的帧,然后总结(或者理解)帧中出现的内容,不能输出在那一秒,出现了什么物体或者别的特征 | 模型 | 帧数 | 编码时间 | 推理时间 | |:---------------------|:-----|----------|:---------| | Qwen2-VL-7B-Instruct | 12 | 1.35s | 13s | | Qwen2-VL-2B-Instruct | 12 | 1.15s | 6.92s | Qwen2-VL-7B-Instruct 测试输出: 这个视频展示了一个繁忙的城市街道场景。在画面中, 可以看到许多车辆在道路上行驶,包括汽车、摩托车和自行车。街道两旁有树木和建筑物, 显示出这是一个城市环境。视频中还出现了两个共享单车,它们的颜色是黄色和蓝色,停放 在路边。 Qwen2-VL-2B-Instruct 测试输出: 在视频中,有一秒中出现了两个共享单车。 --- --- url: /aipod/vllm.md --- # VLLM 在算力舱中默认使用 `ollama` 来提供大模型服务,这个是为了可以很方便的切换各种各样的模型。如果您的需求固定,没有频繁切换和释放模型的情况下,您可以使用 `vllm` 来部署您的服务。 jetson 官方有打包最新的 `vllm` [镜像](https://hub.docker.com/r/dustynv/vllm/tags),您可以通过使用 `docker pull dustynv/vllm:r36.4-cu129-24.04` 拉取镜像。 ## 额外的资源 1. https://hub.docker.com/r/mitakad/vllm ## 例子 下面以算力舱中自带的翻译模型为例(Qwen/Qwen3-4B-Instruct-2507 + vllm) 1. 算力舱直接运行下面的命令 `docker run --rm -p 9999:3000 -ti registry.lazycat.cloud/x/lzc-aipod-trans:a84895c` 2. 局域网中使用 ``` curl http://192.168.1.167:9999/v1/chat/completions \ -H "Content-Type: application/json" \ -d '{"model": "aipod-trans", "messages": [{"role": "user", "content": "hello!"}]}' ``` 注意: 记得将上面的ip地址(`192.168.1.167`)更改成您本地的ip地址 --- --- url: /aipod/vllm/Distributed_Distributed.md --- # vLLM Distributed Inference on Jetson Orin AGX [官方文档](https://github.com/dusty-nv/jetson-containers/blob/master/docs/distributed-inference.md) ## 测试镜像 1. mitakad/vllm:0.11.2-r36.4.tegra-aarch64-cp310-cu126-22.04-truncated 2. mitakad/vllm:0.12.0-r36.4.tegra-aarch64-cp310-cu126-22.04-truncated 3. mitakad/vllm:0.13.0-r36.4.tegra-aarch64-cp312-cu129-24.04-pre-release ## 步骤 注意点: 模型需要自己下载,下载到当前的目录下。在主节点上执行 ``` pip install modelscope ~/.local/bin/modelscope download --model openai-mirror/gpt-oss-120b --local_dir ./openai-mirror/gpt-oss-120b ``` 将主节点上的 10G 网口和另外一台的算力舱 10G 通过网线连接起来。 1. 主节点 ``` sudo ip addr add 192.168.38.1/24 dev eno1 VLLM_HOST_IP=192.168.38.1 && \ VLLM_IFNAME=eno1 && \ docker run -d --rm --runtime nvidia -it \ --network host \ --shm-size=8g \ --privileged \ --ipc=host \ -v /dev/shm:/dev/shm \ -e NVIDIA_DRIVER_CAPABILITIES=all \ -e VLLM_HOST_IP=${VLLM_HOST_IP} \ -e UCX_NET_DEVICES=${VLLM_IFNAME} \ -e NCCL_SOCKET_IFNAME=${VLLM_IFNAME} \ -e GLOO_SOCKET_IFNAME=${VLLM_IFNAME} \ -e TP_SOCKET_IFNAME=${VLLM_IFNAME} \ -v `pwd`/:/models \ -v `pwd`/cache:/root/.cache/huggingface \ --name vllm_xray \ mitakad/vllm:0.11.2-r36.4.tegra-aarch64-cp310-cu126-22.04-truncated docker exec -ti vllm_xray bash ray start -v --head --port 6379 --node-ip-address 192.168.38.1 --num-gpus 1 sysctl vm.drop_caches=3 ``` 2. 其他节点 ``` sudo ip addr add 192.168.38.2/24 dev eno1 VLLM_HOST_IP=192.168.38.2 && \ VLLM_IFNAME=eno1 && \ docker run -d --rm --runtime nvidia -it \ --network host \ --shm-size=8g \ --privileged \ --ipc=host \ -v /dev/shm:/dev/shm \ -e NVIDIA_DRIVER_CAPABILITIES=all \ -e VLLM_HOST_IP=${VLLM_HOST_IP} \ -e UCX_NET_DEVICES=${VLLM_IFNAME} \ -e NCCL_SOCKET_IFNAME=${VLLM_IFNAME} \ -e GLOO_SOCKET_IFNAME=${VLLM_IFNAME} \ -e TP_SOCKET_IFNAME=${VLLM_IFNAME} \ -v `pwd`/:/models \ -v `pwd`/cache:/root/.cache/huggingface \ --name vllm_xray \ mitakad/vllm:0.11.2-r36.4.tegra-aarch64-cp310-cu126-22.04-truncated docker exec -ti vllm_xray bash ray start -v --address 192.168.38.1:6379 --node-ip-address 192.168.38.2 --num-gpus 1 sysctl vm.drop_caches=3 ``` 3. 拷贝模型到另外的worker节点上,同样的目录,我放置的目录是 `~` ``` rsync -aP ~/openai-mirror nvidia@192.168.38.2:~ ``` 4. 在主节点的机器上执行下面的命令 ``` docker exec -ti vllm_xray bash # http://192.168.1.128:1085 是我本地的代理,您可以去掉或者更改成您的 curl -x http://192.168.1.128:1085 -L https://openaipublic.blob.core.windows.net/encodings/o200k_base.tiktoken -o fb374d419588a4632f3f557e76b4b70aebbca790 # 测试是否正常 TIKTOKEN_RS_CACHE_DIR=$(pwd) python -c 'from openai_harmony import load_harmony_encoding; load_harmony_encoding("HarmonyGptOss")' # 启动模型 sysctl vm.drop_caches=3 TIKTOKEN_RS_CACHE_DIR=$(pwd) TRANSFORMERS_OFFLINE=1 vllm serve /models/openai-mirror/gpt-oss-120b --port 8000 \ --served-model-name gpt-oss-120b \ --max-model-len 2048 \ --max-num-batched-tokens 2048 \ --kv-cache-memory-bytes 3000M \ --max-num-seqs 10 \ --tensor-parallel-size 2 \ --enable-expert-parallel \ --gpu-memory-utilization 0.8 \ --distributed-executor-backend ray ``` 5. 访问 通过终端上的 curl 进行访问。`192.168.1.175` 是我局域网中的地址,您需要更改成您机器的ip。 ``` curl 'http://192.168.1.175:8000/v1/chat/completions' \ --header 'Content-Type: application/json' \ --data '{ "model": "gpt-oss-120b", "messages": [ { "role": "user", "content": "who are you?" } ], "stream": false }' ``` ## 测试数据 | 模型 | Tokens/s | |:---------------------------|:---------| | Qwen3-4B-Instruct-2507-FP8 | 10.5 | | openai/gpt-oss-120b | 10.1 | ## 问题 1. 如果您遇到加载本地的模型,vllm 报 repo\_id 不对之类的错误,最简单的方法就是手动把那个 huggingface\_hub 的校验脚本中的校验函数更改。 --- --- url: /aipod/vllm/xray.md --- # vllm-xray 1. 主节点 ``` sudo ip addr add 192.168.38.2/24 dev eno1 docker run --gpus all --network=host --shm-size 10.24g --name vllm-xray -d -ti -v `pwd`:/models -v `pwd`/cache:/root/.cache/huggingface -e VLLM_HOST_IP=192.168.38.2 dustynv/vllm:r36.4-cu129-24.04 bash docker exec -ti vllm-xray bash ray start --block --head --port=6379 --node-ip-address=192.168.38.2 ``` 2. 其他节点 ``` sudo ip addr add 192.168.38.1/24 dev eno1 docker run --gpus all --network=host --shm-size 10.24g --name vllm-xray -d -ti -v `pwd`:/models -v `pwd`/cache:/root/.cache/huggingface -e VLLM_HOST_IP=192.168.38.1 dustynv/vllm:r36.4-cu129-24.04 bash docker exec -ti vllm-xray bash ray start --block --address=192.168.38.2:6379 ``` 3. 主节点启动模型 ``` pip install pandas -i https://mirrors.ustc.edu.cn/pypi/simple # 下载最新版本的 cupy 才支持 aarch64 all_proxy=http://192.168.1.128:1085 curl -L https://github.com/cupy/cupy/releases/download/v13.5.0/cupy_cuda12x-13.5.0-cp312-cp312-manylinux2014_aarch64.whl -O VLLM_HOST_IP=192.168.38.2 vllm serve /models/models/Qwen/Qwen3-30B-A3B-GPTQ-Int4 --enable-auto-tool-choice --tool-call-parser hermes --reasoning_parser deepseek_r1 --tensor-parallel-size 1 --pipeline-parallel-size 2 ``` 4. 测试 ``` time curl http://192.168.38.2:8000/v1/chat/completions \ -H "Content-Type: application/json" \ -d '{"model": "/models/models/Qwen/Qwen3-30B-A3B-GPTQ-Int4", "stream": true, "messages": [{"role": "user", "content": "你觉得中国和美国的差异性在什么地方?"}]}' ``` --- --- url: /aipod/olddocs/onnx/whisper.md --- # whisper ``` providers = [ ('TensorrtExecutionProvider', { 'device_id': 0, # Select GPU to execute 'trt_max_workspace_size': 2147483648, # Set GPU memory usage limit 'trt_fp16_enable': True, # Enable FP16 precision for faster inference 'trt_dla_enable': True, 'trt_int8_enable': True, }), ('CUDAExecutionProvider', { 'device_id': 0, 'arena_extend_strategy': 'kNextPowerOfTwo', 'gpu_mem_limit': 2 * 1024 * 1024 * 1024, 'cudnn_conv_algo_search': 'EXHAUSTIVE', 'do_copy_in_default_stream': True, }) ] ``` ```python import torch import torchaudio import numpy as np import onnxruntime as ort from scipy.io import wavfile from transformers import WhisperProcessor, WhisperTokenizer import os # 加载 ONNX 模型 sess_encoder = ort.InferenceSession("/ssd/lnks/onnx/turbo-encoder.onnx", providers=['TensorrtExecutionProvider', 'CUDAExecutionProvider']) sess_decoder = ort.InferenceSession("/ssd/lnks/onnx/turbo-decoder.onnx", providers=['TensorrtExecutionProvider', 'CUDAExecutionProvider']) os.environ['all_proxy'] = 'http://127.0.0.1:1080' processor = WhisperProcessor.from_pretrained("openai/whisper-large-v3-turbo") tokenizer = WhisperTokenizer.from_pretrained("openai/whisper-large-v3-turbo") audio_path = "/ssd/lnks/assets/speech.wav" # 替换为您的音频文件路径 sample_rate, waveform = wavfile.read(audio_path) waveform = waveform.astype(np.float32) / 32768.0 # 归一化到 [-1, 1] # 确保音频是单声道的 if len(waveform.shape) > 1: waveform = np.mean(waveform, axis=1) # 重采样到16kHz if sample_rate != 16000: waveform = torchaudio.functional.resample(torch.from_numpy(waveform), sample_rate, 16000).numpy() # 使用处理器准备输入 input_features = processor(waveform, sampling_rate=16000, return_tensors="np").input_features out_encoder = sess_encoder.run(None, {"mel": input_features}) tokens = list(tokenizer.sot_sequence_including_notimestamps) session = ort.InferenceSession("/ssd/lnks/onnx/model.onnx", ) # 运行推理 output = session.run(None, {"x": input_features})[0] # 解码输出 predicted_ids = np.argmax(output, axis=-1) transcription = processor.batch_decode(predicted_ids, skip_special_tokens=True)[0] # 使用示例 result = transcribe_audio(audio_path) ``` --- --- url: /aipod/olddocs/asr.md --- # Whisper turbo ## onnx 1. 测试声音时长 14分05秒 [mp3](https://anchor.fm/s/f7cac464/podcast/play/92312327/https%3A%2F%2Fd3ctxlq1ktw2nl.cloudfront.net%2Fstaging%2F2024-8-28%2F387196719-44100-2-f0f9be974d84c.mp3) | 后端 | 模型 | 声音长度 | 推理时间 | 比率 | |--------------------------|:-----------|--------------------|:----------|-----------------------------------| | whisper (指官方原生实现) | large-v3 | 14分05秒 英文 | 349.49秒 | 2.42(大概1秒可以推理2.42秒的声音) | | onnx + CUDA | turbo | 同上 | 141.05秒 | 5.99 | | onnx + Tensorrt | turbo | 同上 | 测试中... | | | whisper | turbo | 同上 | 89.90秒 | 9.38 | | whisper\_trt | tiny.en | 同上 | 26.38 | 32.03 | | whisper | tiny.en | 同上 | 70.12 | 12.05 | | funasr框架 | SenseVoice | 同上 | 24.11 | 35.04 | | funasr框架 | SenseVoice | 20分 普通话和粤语 | 34.31s | 34.97 | 2. 测试声音时长 30秒 | 后端 | 模型 | 声音长度 | 推理时间 | |-----------------|:-----------|----------|:----------| | whisper | turbo | 30s | 3.51秒 | | onnx + CUDA | turbo | 30s | 5.54秒 | | onnx + Tensorrt | turbo | 30s | 测试中... | | whisper\_trt | tiny.en | 30秒 | 1.80秒 | | whisper | tiny.en | 30秒 | 3.00秒 | | funasr | SenseVoice | 30s | 1.08秒 | | | | | | --- --- url: /aipod/os/introduction.md --- # 介绍 算力舱中系统是 `Ubuntu 22.04.5 LTS` 版本,您可以将算力舱接入键盘和鼠标,以及显示屏就可以作为一个独立的主机使用。和微服中联动是通过 `lzc-ai-agent` 这个服务,负责去下发和启动相关的AI应用服务。在算力舱中服务运行的环境为 `docker` 。 ```/etc/os-release PRETTY_NAME="Ubuntu 22.04.5 LTS" NAME="Ubuntu" VERSION_ID="22.04" VERSION="22.04.5 LTS (Jammy Jellyfish)" VERSION_CODENAME=jammy ID=ubuntu ID_LIKE=debian HOME_URL="https://www.ubuntu.com/" SUPPORT_URL="https://help.ubuntu.com/" BUG_REPORT_URL="https://bugs.launchpad.net/ubuntu/" PRIVACY_POLICY_URL="https://www.ubuntu.com/legal/terms-and-policies/privacy-policy" UBUNTU_CODENAME=jammy ``` ::: warning 算力舱中的 `Linux` 系统不能换成其他的发行版,这个 `Ubuntu` 是 `nvidia jetson` 官方适配的,如果您更改 `Linux` 到其他发行版,不确定会遇到那些问题。 如果您先恢复到出厂前的环境,您可以通过刷系统的方式来将系统还原。 ::: ## SSH 算力舱默认的帐号密码为 `nvidia:nvidia`. 1. 您可以在算力舱的管理列表中查看您当前的ip地址 ![ip address](/assets/aipod-ip-address.GKlPcpdK.png) 2. 您可以通过 `ssh nvidia@ip` 进到 算力舱的系统中去。 3. 如果您和算力舱不在一个局域网中,您也可以通过微服作为跳板机器,比如 `ssh -J root@微服名称.heiyu.space nvidia@ip` 进行连接。 --- --- url: /aipod/os/use-microserver-network.md --- # 使用微服网络连接外网 在算力舱中需要连接外网来下载镜像,如果您的环境网络有限制,在同一个局域网中,您可以使用以下的方式来将算力舱中的流量都转发到微服中去,使用微服作为出口。 1. 微服中执行 ssh到微服后执行(192.168.31.0替换为实际的局域网网段) ```sh iptables -t nat -I POSTROUTING --source 192.168.31.0/24 -j MASQUERADE iptables -P FORWARD ACCEPT ``` 2. 算力仓执行(192.168.31.60替换为微服的IP) ```sh sudo ip route add default via 192.168.31.60 ``` 3. 测试下 ```sh curl -v https://registry-static.lazycat.cloud ``` --- --- url: /aipod/ollama/standalone.md --- # 单独使用 您可以使用 docker-compose 在算力舱中单独部署服务 ```yml services: ollama: image: registry.lazycat.cloud/catdogai/jetson-ollama:0.15.2-290526 volumes: - /etc/timezone:/etc/timezone:ro - ./data:/root/.ollama environment: - LANGUAGE=en_US:en - LANG=en_US.UTF-8 - LC_ALL=en_US.UTF-8 - OLLAMA_DEBUG=1 - OLLAMA_ORIGINS=* - OLLAMA_HOST=0.0.0.0 - OLLAMA_FLASH_ATTENTION=1 - OLLAMA_GPU_OVERHEAD=4294967296 # 4G - OLLAMA_CONTEXT_LENGTH=8192 ports: - 11434:11434 mem_limit: 60G memswap_limit: 60G ``` 将上面的文件保存为一个 `docker-compose.yml` 文件,然后在同目录下使用 `docker-compose up -d ` 启动。 在启动成功后,可以通过局域网中的 `11434` 端口进行访问. :::info 如果您的算力舱上不能访问到 `registry.lazycat.cloud`,您可以切换到 `dockerhub` 上,可以通过 `docker pull catdogai/jetson-ollama:0.15.2-290526` ollama 经常更新,可能文档上没有及时更新,新的 ollama 版本 tag 可以在 `https://hub.docker.com/r/catdogai/jetson-ollama/tags` 页面中查看. ::: --- --- url: /aipod/package/publish.md --- # 发布AI应用 1. [算力舱分类](https://appstore.lazycat.cloud/#/shop/category/27) 2. [懒猫微服发布应用](https://developer.lazycat.cloud/publish-app.html) 发布AI应用和发布懒猫微服应用一样,同样是通过 `lzc-cli` 或者在懒猫微服的开发者平台上提交。发布应用的时候,记得写上 `AI Pod` 或者 `算力舱` 或者相关的说明,方便审核的时候将应用添加到 `算力舱` 分类中去. --- --- url: /aipod/ai-browser/image-trans.md --- # 图片翻译 ![image result](/assets/aipod-image-trans-result.DGZcHmE0.png) AI插件助手中,支持对图片进行翻译,您可以在 AIPOD 的配置选项中选择您的常用语言。 ![image config](/assets/aipod-config-image-trans-options.BlspQvSF.png) 当您配置好了后,您可以在浏览网站时,将鼠标放置在图片上方,在图片的右下角会有一个翻译的图标浮现出来,您点击后就可以对当前的图片进行翻译。 ![image trans icon](/assets/image-trans-tips.Ch1LT4Oy.png) 当翻译处理完成后,结果会直接覆盖上原来的图片上,同样您可以点击右下角的还原图标,进行恢复之前的格式。 --- --- url: /aipod/issues/ubuntu-dont-entry.md --- # 如果遇到 ubuntu 系统不能进去,但是通过 hdmi 切换 tty 却能正常使用 ## 第1步:查看当前的系统信息 1. **查看Ubuntu版本**: 在TTY中,输入以下命令: ```bash $ lsb_release -a No LSB modules are available. Distributor ID: Ubuntu Description: Ubuntu 22.04.5 LTS Release: 22.04 Codename: jammy ``` 这会显示您的Ubuntu发行版号和代号(例如 Ubuntu 22.04.5 LTS)。 2. **查看Jetson L4T版本**: L4T是NVIDIA为Jetson定制的底层驱动和系统软件。运行以下命令: ```bash $ cat /etc/nv_tegra_release # R36 (release), REVISION: 4.3, GCID: 38968081, BOARD: generic, EABI: aarch64, DATE: Wed Jan 8 01:49:37 UTC 2025 # KERNEL_VARIANT: oot TARGET_USERSPACE_LIB_DIR=nvidia TARGET_USERSPACE_LIB_DIR_PATH=usr/lib/aarch64-linux-gnu/nvidia ``` 这会显示您的L4T版本信息,这对于确定兼容的软件包至关重要。 3. **查看JetPack版本 (如果已安装)**: JetPack是一个包含L4T和各种NVIDIA SDK(如CUDA, cuDNN)的捆绑包。可以通过以下命令查看: ```bash $ sudo apt-cache show nvidia-jetpack | grep "Version" Version: 6.2.1+b38 Version: 6.2+b77 Version: 6.1+b123 ``` ## 第2步:检查桌面环境依赖包是否完整 图形界面无法启动最常见的原因是桌面环境的元软件包(meta-package)或其依赖项损坏或未安装完整。Ubuntu的默认桌面环境是GNOME,其对应的元软件包通常是 `ubuntu-desktop`。 1. **检查 `ubuntu-desktop` 包的状态**: ```bash dpkg -l | grep ubuntu-desktop ``` 如果该软件包已安装,您会看到一行信息,开头是 `ii`。如果未安装或状态异常,这里可能会有提示。 2. **检查系统是否有损坏的依赖项**: 运行apt的检查工具来发现任何未满足的依赖关系。 ```bash sudo apt-get check ``` 如果这个命令有任何输出,说明存在依赖问题。您可以尝试用以下命令修复它: ```bash sudo apt-get -f install ``` 3. **尝试重新安装桌面环境**: 这是解决依赖包问题的最有效方法。它会重新安装所有缺失的桌面组件。 ```bash sudo apt-get update sudo apt-get install --reinstall ubuntu-desktop sudo systemctl status gdm3 sudo systemctl restart gdm3 ``` 安装过程可能会需要一些时间。完成后,重启您的Jetson设备: ```bash sudo reboot ``` --- --- url: /aipod/knowledge/install.md --- # 安装方式 ## 商店安装 敬请期待 ## 内测安装 在新的版本中,`AI POD` 应用中会添加一个 `Testflight` 的图标,里面是算力舱应用的内测版本。如果您的 `AI POD` 版本是旧的,没有在首页出现 `Testflight` 图标,您可以在微服的启动器中 -> 内测工具 -> 算力舱测试组 查看。 ![Testflight](/assets/knowledge-testflight-icon-2025-11-04_11-32.pcpH11dy.png) 点击打开后,您会看到里面有很多的内测AI应用,知识库对应 `Knowledge Base` 名称。(记得结合最新版的 `AI POD` 使用) ![Knowledge Base](/assets/knowledge-2025-11-04_11-34.DrYHlHHz.png) 点击右边的按钮可以进行安装或者更新。您也可以点击图标查看当前提交的日志。 ![Knowledge Base Detail](/assets/knowledge-detail-2025-11-04_11-37.CtwpsgPy.png) 当您安装完成后,在您的`AI POD`应用或者AI浏览器首页,您可以看到一个 `Knowledge` 的图标。 ![Knowledge Base Detail](/assets/knowledge-shortcuts-2025-11-04_11-42.neqGd81Q.png) 点击打开后,会检测算力舱中相关的服务是否在运行中,您可能会看到下面的启动进度页面,请您耐心等待下(模型需要下载和启动) ![prepare-running](/assets/prepare-running.C1b21RvL.png) --- --- url: /aipod/os/install_software.md --- # 安装软件 ## lzc-earlyoom 算力舱是 `jetson agx orin` 属于 `iGPU` 的架构,默认版本的 `earlyoom` 不能检测到 `GPU` 的使用内存。我们修改后的 `lzc-earlyoom` 解决了这个问题, 您可以根据以下连接的文档进行安装 https://gitee.com/lazycatcloud/lzc-aipod-resources#lazycat-aipod-early-oom-killer ## lzc-thermal https://gitee.com/lazycatcloud/lzc-aipod-resources#lazycat-aipod-thermal-control-module ## 安装 firefox ``` sudo apt install snap snap download snapd --revision=24724 sudo snap ack snapd_24724.assert sudo snap install snapd_24724.snap sudo sudo snap refresh --hold snapd sudo snap install firefox ``` 相关问题见 https://elinux.org/Jetson/L4T/r36.4.x\_patches#Web\_Browser ## 安装输入法 ``` sudo apt install fcitx5 fcitx5-rime fcitx5-pinyin ``` ## todesk ``` curl 'https://dl.todesk.com/linux/todesk-v4.7.2.0-arm64.deb' \ -H 'DNT: 1' \ -H 'Referer: https://www.todesk.com/' \ -H 'Upgrade-Insecure-Requests: 1' \ -H 'User-Agent: Mozilla/5.0 (X11; Linux x86_64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/139.0.0.0 Safari/537.36' \ -H 'sec-ch-ua: "Not;A=Brand";v="99", "Google Chrome";v="139", "Chromium";v="139"' \ -H 'sec-ch-ua-mobile: ?0' \ -H 'sec-ch-ua-platform: "Linux"' -O sudo dpkg -i todesk-v4.7.2.0-arm64.deb ``` --- --- url: /aipod/aipod/port-forward.md --- # 微服端口转发 算力舱中的部署的服务,您可以通过 `https://xxx-ai.$微服名称.heiyu.space` 的方式进行访问。但这个方式访问需要依赖懒猫微服客户端,为了解决您局域网中访问,或者其他不能装客户端的机器,或者有一些特定的环境就是不能访问到 `heiyu.space` 的网络。 `AIPOD` 应用中的端口转发只是将 `xxxx-ai` 的 `http` 请求暴露到 *微服* 的网络上,您可以通过 `http://微服名称.heiyu.space:$端口号` 进行访问,也可以直接使用 `http://微服ip:端口` 进行访问。 1. 打开 `AIPOD` 的设置界面,点击端口转发 ![port-forward-page](/assets/port-forward-page.CgaTfgca.jpg) 2. 添加您需要转发的服务,比如 `ollama` ![port-forward-create-ollama](/assets/port-forward-create-ollama.CWtXaXnp.jpg) 3. 测试 打开 `http://微服名称.heiyu.space:端口`,比如我上面的是 `ollama` 和 `8888` 端口. ![port-forward-ollama.jpg](/assets/port-forward-ollama.BddNiLGU.jpg) 或者直接在局域网中使用微服的ip进行访问. ``` > curl http://192.168.1.246:8888 Ollama is running⏎ ``` ::: info 如果您需要将服务暴露到其他微服的设备上,您可以使用 `局域网转发工具` [商店地址](https://appstore.lazycat.cloud/#/shop/detail/cloud.lazycat.app.forward) ![local-port-forward-tools.jpg](/assets/local-port-forward-tools.DJ-rVSfw.jpg) ::: # 算力舱端口转发 请查看 [算力舱端口转发](../os/port-forward.md) --- --- url: /aipod/trans/mtrans.md --- # 快速翻译(神经网络翻译) 算力舱中内置了一个高性能神经网络翻译模型,具有极快的翻译速度,适合对响应时间有严格要求的场景。虽然翻译质量相比大语言模型略有不足,但在实时翻译、批量处理等对速度敏感的应用中表现优异。微服中的应用可以通过算力舱暴露的 `mtrans` API 直接调用该服务。 内置 92 个双向翻译模型,支持 47 种语言之间的翻译。支持自动语言检测(源语言代码使用 `auto` 表示)。 ## 服务信息 * `mtrans` 地址为 * `mtrans` 详细说明可查看 `https://github.com/xxnuo/MTranServer` ## 支持的语言 ### 完全支持双向翻译的语言(42种) 阿拉伯语、阿塞拜疆语、保加利亚语、孟加拉语、加泰罗尼亚语、捷克语、丹麦语、德语、希腊语、西班牙语、爱沙尼亚语、波斯语、芬兰语、法语、古吉拉特语、希伯来语、印地语、克罗地亚语、匈牙利语、印尼语、意大利语、日语、卡纳达语、韩语、立陶宛语、拉脱维亚语、马拉雅拉姆语、马来语、荷兰语、波兰语、葡萄牙语、罗马尼亚语、俄语、斯洛伐克语、斯洛文尼亚语、阿尔巴尼亚语、瑞典语、泰米尔语、泰卢固语、土耳其语、乌克兰语、简体中文、英语 ### 仅支持翻译到英语的语言(8种) 白俄罗斯语、波斯尼亚语、冰岛语、马耳他语、挪威语(博克马尔)、挪威语(尼诺斯克)、塞尔维亚语、越南语 ::: tip 提示 这些语言只能作为源语言翻译成英语,不能作为要翻译到的目标语言。 ::: ## 语言代码对照表 代码规则遵循 BCP47 标准 [IETF Language Tag](https://en.wikipedia.org/wiki/IETF_language_tag) ### 支持双向翻译的语言(42种 + 英语) | 语言代码 | 语言名称(中文) | 语言名称(英文) | |---------|-----------------|-----------------| | ar | 阿拉伯语 | Arabic | | az | 阿塞拜疆语 | Azerbaijani | | bg | 保加利亚语 | Bulgarian | | bn | 孟加拉语 | Bengali | | ca | 加泰罗尼亚语 | Catalan | | cs | 捷克语 | Czech | | da | 丹麦语 | Danish | | de | 德语 | German | | el | 希腊语 | Greek | | en | 英语 | English | | es | 西班牙语 | Spanish | | et | 爱沙尼亚语 | Estonian | | fa | 波斯语 | Persian | | fi | 芬兰语 | Finnish | | fr | 法语 | French | | gu | 古吉拉特语 | Gujarati | | he | 希伯来语 | Hebrew | | hi | 印地语 | Hindi | | hr | 克罗地亚语 | Croatian | | hu | 匈牙利语 | Hungarian | | id | 印尼语 | Indonesian | | it | 意大利语 | Italian | | ja | 日语 | Japanese | | kn | 卡纳达语 | Kannada | | ko | 韩语 | Korean | | lt | 立陶宛语 | Lithuanian | | lv | 拉脱维亚语 | Latvian | | ml | 马拉雅拉姆语 | Malayalam | | ms | 马来语 | Malay | | nl | 荷兰语 | Dutch | | pl | 波兰语 | Polish | | pt | 葡萄牙语 | Portuguese | | ro | 罗马尼亚语 | Romanian | | ru | 俄语 | Russian | | sk | 斯洛伐克语 | Slovak | | sl | 斯洛文尼亚语 | Slovenian | | sq | 阿尔巴尼亚语 | Albanian | | sv | 瑞典语 | Swedish | | ta | 泰米尔语 | Tamil | | te | 泰卢固语 | Telugu | | tr | 土耳其语 | Turkish | | uk | 乌克兰语 | Ukrainian | | zh | 简体中文 | Simplified Chinese | ### 仅支持翻译到英语的语言(8种) | 语言代码 | 语言名称(中文) | 语言名称(英文) | |---------|-----------------|-----------------| | be | 白俄罗斯语 | Belarusian | | bs | 波斯尼亚语 | Bosnian | | is | 冰岛语 | Icelandic | | mt | 马耳他语 | Maltese | | nb | 挪威语(博克马尔) | Norwegian (Bokmål) | | nn | 挪威语(尼诺斯克) | Norwegian (Nynorsk) | | sr | 塞尔维亚语 | Serbian | | vi | 越南语 | Vietnamese | --- --- url: /aipod/aipod/extenstion-chrome.md --- # 懒猫AI助手插件 :::info 懒猫AI助手插件通过 `AI POD` 应用下发,所以需要确保懒猫微服客户端已经打开,并且微服在线。插件的版本会保持和当前的 `AI POD` 版本一致 ::: ## 插件更新 在各个端的 AI 浏览器中,当您重启浏览器就会自动拉取当前最新的浏览器插件,并进行安装。在 `chrome://extensions` 界面中您可以看到当前的插件版本。 ![](/assets/chrome-extension-version.DOQyb3dz.png) 您也可以在 `AI POD` 的设置界面上查看当前的插件版本 ![](/assets/ai-extenstion-version.B_my8yc6.png) ## 把 AI 插件安装到 Chrome 中 0. 打开 `AI POD` -> 插件 -> 选中 `cloud.lazycat.app.ai.zip` 点击下载 ![](/assets/extenstions-shortcut.DBNTZv5q.png) 1. 打开 `Chrome` 浏览器, 确保您使用的是最新版本的 `Chrome` 浏览器 2. 访问扩展程序页面, 在地址栏中输入 `chrome://extensions` 并按回车 3. 启用开发者模式, 在页面右上角找到 "开发者模式" 开关,确保它已启用 4. 拖拽安装插件, 将 `cloud.lazycat.app.ai.zip` 文件直接拖拽到 `Chrome` 扩展页面中 5. 打开一个新标签页,可以看到插件已经安装(首页变成了 `AI POD` 的页面) --- --- url: /aipod/package/pack-extenstion.md --- # 打包浏览器插件 如果您的 AI应用 中具有插件,AI浏览器中在重启后会自动拉取并加载。下面以一个简单的打包 `darkreader` 插件为例 ## darkreader AI 应用 ```bash mkdir lzc-darkreader-demo cd lzc-darkreader-demo/ lzc-cli project init ``` 在 `init` 之后,目录下会有三个文件 `lzc-build.yml`, `lzc-icon.png`, `lzc-manifest.yml` * `lzc-build.yml` 是 `lpk` 的构建配置。 * `lzc-manifest.yml` 是 `lpk` 的配置文件。 * `lzc-icon.png` 是 `lpk` 的图标(限制为 png 格式) 从 `Github` 上下载 `darkreader` 插件。 1. 打开 https://github.com/darkreader/darkreader/releases/tag/v4.9.113 下载 2. 或者使用 `curl` 下载 ```bash curl -L -O https://github.com/darkreader/darkreader/releases/download/v4.9.113/darkreader-chrome.zip ``` 得到一个 `darkreader-chrome.zip` 文件。 下载 `darkreader` 的图标 1. 打开 https://raw.githubusercontent.com/darkreader/darkreader/refs/heads/main/src/icons/dr\_128.png 保存为 `lzc-icon.png` 文件 2. 或者使用 `curl` 下载 ```bash curl -L https://raw.githubusercontent.com/darkreader/darkreader/refs/heads/main/src/icons/dr_128.png -o lzc-icon.png ``` ### 更改 lzc-manifest.yml 文件 ```lzc-manifest.yml name: darkreader demo package: cloud.lazycat.aibrowser.darkreader-demo version: 0.0.1 description: license: https://choosealicense.com/licenses/mit/ homepage: author: application: subdomain: darkreader-demo routes: - /=https://darkreader.org/ ``` ### 更改 lzc-build.yml 文件 ```lzc-build.yml # manifest: 指定 lpk 包的 manifest.yml 文件路径 manifest: ./lzc-manifest.yml # pkgout: lpk 包的输出路径 pkgout: ./ # icon 指定 lpk 包 icon 的路径路径,如果不指定将会警告 # icon 仅仅允许 png 后缀的文件 icon: ./lzc-icon.png # browser-extension: 指定浏览器插件的目录,如果这个路径为一个文件,将直接复制作 # 为扩展的zip包打包,如果是为一个目录,将打包成zip,再打包到 lpk 中 browser-extension: ./darkreader-chrome.zip ``` ### 构建并安装 ```bash lzc-cli project build lzc-cli app install ./ ``` ### 安装后 1. 在 `Android` 的 `AI 浏览器` 中点击菜单栏中的 `Exit` 退出重启。[快速跳转](https://lazycat.cloud/download)下载, 需要最新版 `Android` 浏览器。 2. `AI 浏览器` 在启动的过程中会自动从微服中拉取插件并加载。 --- --- url: /aipod/imagen/api.md --- # 文生图 下面的接口调用依赖于您已经安装了 `文生图` 应用,[点击跳转安装](https://appstore.lazycat.cloud/#/shop/detail/cloud.lazycat.aipod.imagen) 文生图的接口是兼容 OpenAI 的 API 格式。 1. 获取模型接口(目前仅有一个默认模型 sd-cpp-local 对应 z-image-turbo) `curl https://imagen-ai.$微服名称.heiyu.space/v1/models` 2. 生成图片接口(https://platform.openai.com/docs/api-reference/images/create) ``` curl https://imagen-ai.微服.heiyu.space/v1/images/generations \ -H "Content-Type: application/json" \ -d '{ "model": "sd-cpp-local", "prompt": "A lovely cat", "n": 1, "size": "512x512", "response_format": "b64_json" }' \ -o >(jq -r '.data[0].b64_json' | base64 --decode > output.png) ``` 参数用法同 OpenAI: * prompt 提示词 * n 生成图片数量 * size 图片尺寸,长和宽都必须是 16 的整数倍否则不合法 * response\_format 目前仅支持这个固定格式 模型特定参数:因为 OpenAI 格式未预留额外参数接口,因此当前版本可以将 Z-Image-Turbo 的一些高级参数放到提示词里 ``` "prompt": "A lovely cat{\"seed\": 357925}", ``` 当前主要有: * steps 迭代步数,当前版本后端设置的默认值是 7, 模型推荐值是 9,取值范围 0-9,步数越少生成越快,比如演示测试时可以指定为 4 步来快速生成,不用等太久。另外这个 turbo 是蒸馏过的模型,步数不能超过 20,否则会过渲染图像无法使用 * seed 生成种子,默认值是随机值,可以手动指定同一个种子以得到稳定一致的结果,特殊需求下需要这个参数 --- --- url: /aipod/issues/traefik-dashboard.md --- # 查看算力舱中运行的服务转发规则 算力舱中使用 `traefik` 做转发,匹配的规则通过 `Host` 来匹配,当您通过 访问的时候,会自动根据 `ollama-ai` 转发到 `ollama` 的容器中去,而端口则是您容器中填写的 `expose` 端口。 :::info 当您的服务如果具有多个 expose 端口的话,会导致转发不成功,可以通过 `docker inspect` 查看,也可以检查 `Dockerfile` 中是否已经定义了 `expose` 字段。 ::: 您可以打开 来查看算力舱上的 `traefik` 转发情况。 ![traefik http router screenshot](/assets/traefik-dashboard-http-router.Ct9i6PnB.png) --- --- url: /aipod/os/clean_data.md --- # 清理数据 在算力舱结合微服使用的过程中,`lzc-ai-agent` 服务启动的时候,会自动将旧版本的docker镜像清理掉。 在微服中将对应的 `AI应用` 卸载掉后,会自动将算力舱中的镜像已经对应模型数据清理。 ## 清理AI应用服务旧镜像 智能扫描您服务安装的位置,判断没有使用的旧版本镜像并删除。 ```sh /ssd/lzc-ai-agent/bin/client.arm64 -clean-lzc-images ``` ## 清理异常状态的容器 以下不影响系统正常运行 ```sh docker ps -a | grep '[Dead|Exited]' | awk '{print $2}' | xargs -i docker rm {} ``` ## 清理镜像 ::: warning 这个命令不影响系统当前运行, 执行以下命令可以清理未使用到的镜像,如果有镜像被容器占用,docker会自动跳过。但要注意,如果您本地构建或者拉取的镜像如果没有正在运行,也会被删除。 ::: ```sh docker images | awk '{print $3}' | xargs -i docker rmi {} ``` ## docker 清理 清理docker的缓存以及没有用到的数据 ```sh docker system prune ``` --- --- url: /aipod/aipod/resources.md --- # 相关资源 ## Nvidia Jetson 镜像 AI 领域常用的一些基础镜像,在 jetson 的官方都有支持,并且更新也是挺频繁的。 1. https://hub.docker.com/u/dustynv 2. https://github.com/dusty-nv/jetson-containers 3. https://pypi.jetson-ai-lab.io/ 4. https://pypi.jetson-ai-lab.io/jp6/cu129 5. https://pypi.jetson-ai-lab.io/jp6/cu128 6. https://pypi.jetson-ai-lab.io/jp6/cu126 额外的使用场景: 1. https://www.jetson-ai-lab.com/tutorial-intro.html ## 封装的镜像 官方打包的镜像一般会比较旧,版本没有及时更新,我们也会在这些基础的镜像上更新软件的版本。 1. ollama https://hub.docker.com/r/catdogai/jetson-ollama/tags ## 常用镜像 1. CUDA 镜像 `dustynv/cuda:12.8-samples-r36.4.0-cu128-24.04` 2. PyTorch 镜像 `dustynv/pytorch:2.6-r36.4.0-cu128-24.04` ## pypi 代理 ### proxpi 缓存代理 1. 在一个机器上启动一个 pypi 的代理服务,避免代理和重复下载问题 ``` services: proxpi: restart: unless-stopped network_mode: host environment: - all_proxy=http://127.0.0.1:10807 - PROXPI_CACHE_DIR=/pypi_cache - PROXPI_INDEX_URL=https://pypi.jetson-ai-lab.io/jp6/cu129/+simple/ - PROXPI_EXTRA_INDEX_URLS=https://pypi.jetson-ai-lab.io/jp6/cu128/+simple/,https://pypi.jetson-ai-lab.io/jp6/cu126/+simple/,https://mirrors.ustc.edu.cn/pypi/simple/ volumes: - ./pypi_cache:/pypi_cache image: epicwink/proxpi:latest ``` 2. 在算力舱中使用 ``` pip install --trusted-host 192.168.1.133:5000 --index-url http://192.168.1.133:5000/index/ torch==2.8.0 ``` 假设您的 `pypi` 代理机器的ip为 `192.168.1.133` --- --- url: /aipod/os/disk.md --- # 硬盘 算力舱默认携带的硬盘是 `1T` 版本的固态硬盘。但算力舱具有两个 `pcie4` 的接口,您可以按照您的需求来更换硬盘。 ## 换硬盘 1. 将换下来的硬盘的数据拷贝到新硬盘上(原来的硬盘上有一些模型的数据和算力舱的客户端) 2. 换上新的硬盘即可 ::: warning 换硬盘时需要确保 `/etc/fstab` 中的挂载路径是对应上的,要不然系统进不去。 下面这个是一个示例,里面将固态盘挂载到 `/ssd` 这个目录下。 ``` UUID=942a4d75-e509-4fa2-8d3a-23cb6925b68c /ssd ext4 defaults 0 2 /ssd/home /home none bind 0 0 ``` ::: ## 迁移系统到固态 在算力舱现在系统中,系统是在 64G 的 `emmc` 存储上的,而 `docker` 和 `home` 是在 `SSD` 存储上的,您可以按照下面的命令来将系统迁移到 `SSD` 上。 1. /ssd 目录 这个目录是现在 1T 硬盘的挂载路径,您可以在里面看到 `docker`, `home`, `lzc-ai-agent` 等目录。 2. 拷贝当前的系统到 nvme 硬盘中, 假设您的 nvme 为 nvme0n1p1 ``` sudo mount /dev/nvme0n1p1 /mnt sudo rsync -axHAWX --numeric-ids --info=progress2 --exclude={"/dev/","/proc/","/sys/","/tmp/","/run/","/mnt/","/media/*","/lost+found", "/ssd/", "/home/"} / /mnt sudo mkdir -p /mnt/ssd # 迁移之前的 /ssd 到新的目录 sudo systemctl stop lzc-ai-agent sudo systemctl stop docker systemctl stop nvzramconfig systemctl disable nvzramconfig mkdir -p /mnt/ssd mv /mnt/docker /mnt/ssd/ mv /mnt/lzc-ai-agent /mnt/ssd/lzc-ai-agent ``` 3. 更改 `/etc/fstab` 需要将 /ssd/ 相关的行注释掉,更新后的 `/etc/fstab` 看起来类似下面的文本 ``` # /etc/fstab: static file system information. # # These are the filesystems that are always mounted on boot, you can # override any of these by copying the appropriate line from this file into # /etc/fstab and tweaking it as you see fit. See fstab(5). # # /dev/root / ext4 defaults 0 1 UUID=A9EE-ABCF /boot/efi vfat defaults 0 1 ``` 4. 写入 `/etc/systemd/system/setssdroot.service` ``` [Unit] Description=Change rootfs to SSD in M.2 key M slot (nvme0n1p1) DefaultDependencies=no Conflicts=shutdown.target After=dev-nvme0n1p1.device Requires=dev-nvme0n1p1.device Before=shutdown.target ConditionPathExists=/dev/nvme0n1p1 ConditionPathExists=/etc/setssdroot.conf ConditionVirtualization=!container [Service] Type=oneshot RemainAfterExit=yes ExecStart=/sbin/setssdroot.sh [Install] WantedBy=default.target ``` 5. 写入 `/sbin/setssdroot.sh` ``` #!/bin/sh # Runs at startup, switches rootfs to the SSD on nvme0 (M.2 Key M slot) NVME_DRIVE="/dev/nvme0n1p1" CHROOT_PATH="/nvmeroot" INITBIN=/lib/systemd/systemd EXT4_OPT="-o defaults -o errors=remount-ro -o discard" modprobe ext4 mkdir -p ${CHROOT_PATH} mount -t ext4 ${EXT4_OPT} ${NVME_DRIVE} ${CHROOT_PATH} cd ${CHROOT_PATH} /bin/systemctl --no-block switch-root ${CHROOT_PATH} ``` 6. 执行命令 ``` sudo chmod 777 /sbin/setssdroot.sh systemctl daemon-reload sudo systemctl enable setssdroot.service sudo cp /etc/systemd/system/setssdroot.service /mnt/etc/systemd/system/setssdroot.service sudo cp /sbin/setssdroot.sh /mnt/sbin/setssdroot.sh sudo cp /etc/fstab /mnt/etc/fstab sudo touch /etc/setssdroot.conf ``` `/etc/setssdroot.conf` 为一个标识文件,这个文件存在才会使用 nvme 上的 rootfs 启动。所以如果您需要切换会 `emmc` 系统,您可以 * 将 nvme 硬盘拔掉 * 手动 mount emmc 硬盘,然后将里面的 `/etc/setssdroot.conf` 文件删除重启即可 7. 重启生效 ### 配置 Swapfile 在您迁移系统后,重启系统,lsblk 可以看到当前系统已经在 nvme 上,配置 swapfile ``` fallocate -l 32G /swapfile mkswap /swapfile ``` 创建一个 `/etc/systemd/system/swapfile.swap` 文件写入下面的内容 ``` [Swap] What=/swapfile [Install] WantedBy=swap.target ``` 执行下面的命令进行启动 ``` systemctl daemon-reload systemctl status swapfile.swap systemctl enable swapfile.swap systemctl start swapfile.swap ``` ## 修复 apt man 数据库错误 ``` # 修复权限 sudo chown -R man:root /var/cache/man sudo chmod -R 755 /var/cache/man # 重建数据库 sudo mandb ``` --- --- url: /aipod/aipod/testflight.md --- # 算力舱内测应用 ::: info 非常感谢您安装内测版本中的应用,如果您在使用中有什么问题,您可以在VIP群中和我们联系,感谢您的反馈。 ::: 在新的版本中,`AI POD` 应用中会添加一个 `Testflight` 的图标,里面是算力舱应用的内测版本。 ![Testflight](/assets/aipod-testflight.2tSSu3uO.png) 如果您的 `AI POD` 版本是旧的,没有在首页出现 `Testflight` 图标,您可以在微服的启动器中 -> 内测工具 -> 算力舱测试组 查看。 ![lzc-testflight](/assets/lzc-testflight.D3Rj46Do.png) 打开后,选择 “算力舱内测组” ![lzc-testflight-select-aipod.png](/assets/lzc-testflight-select-aipod.MHPALmzG.png) 即能看到内测版本中的应用。 --- --- url: /aipod/os/flash-jetson.md --- # 算力舱刷机 下面有两种方式进行刷机 1. 通过微服中安装 “算力舱刷机工具” 应用来刷机 2. 直接通过您本地的机器,启动算力舱刷机镜像来刷机 ::: warning 在构建系统镜像的时候,会需要较大的硬盘空间,请确保您的机器所剩余的空间大于 60GB ::: ## jetson刷机应用运行刷机系统 1. 在内测工具中的算力舱内测组中安装这个应用,由于这个应用中的包含了 `jetson` 系统镜像和 `cuda` 相关的驱动,比较大(20G)需要您耐心等候 2. 等待应用安装完成后,打开这个应用会出现一个 `terminal`,这个 `terminal` 就是用来刷机的系统 3. 以下步骤和直接使用本地机器运行 `docker` 镜像一样 (请看下面的 "在刷机系统中刷算力舱系统") ## 直接使用本地的机器,运行刷机镜像系统 1. 首先拉取镜像 `docker pull registry.cn-hangzhou.aliyuncs.com/catdogai/jetson-flash:t912-6.2-0.0.7` 2. 执行 `docker run -it --rm --privileged --network host -v /dev/bus/usb:/dev/bus/usb -v /dev:/dev registry.cn-hangzhou.aliyuncs.com/catdogai/jetson-flash:t912-6.2-0.0.7 bash` 3. 等待 `docker` 启动后,将会出现一个 `terminal`,这个 `terminal` 就是用来刷机的系统 4. 以下步骤和直接使用微服应用刷机一样(请看下面的 "在刷机系统中刷算力舱系统") ## 在刷机系统中刷算力舱系统 1. 确保算力舱和刷机系统通过 `typec` 连接起来 * 如果您是使用微服应用进行刷系统,您需要把算力舱上的 `typec` 口和微服上的 `usb` 连接起来。 * 如果您是使用本地的机器进行刷系统,您需要把算力舱上的 `typec` 口和您的机器`usb`连接起来。 2. 确保算力舱处于 `recovery mode` * 通过点击算力舱的管理列表中的 `recovery` 键来进入 `recovery` 模式。 * 在算力舱刷机工具的系统中,可以直接使用 `ssh nvidia@192.168.55.1` 进去到算力舱的系统,然后执行 `sudo reboot --force forced-recovery` 进去到 `recovery` 模式。 ::: info 在拆开算力舱的外壳后,靠近电源按钮的键为 `recovery` 另外一个为 `reset` 键。在这两个键的下发会有两个小字标识。分别为 `RECY` 和 `RST`。 1. 在关机的情况下,通过按住 `recovery` 按钮,然后再按开机键2秒,再松开开机键,然后才松开 `recovery` 键 2. 开机的情况下,先按住 `recovery` 键,再按压 `reset` 键,最后松开 `reset` 键,再松开 `recovery` 键 ::: 在做了上面的操作后,机器会进入 `recovery` 模式,这种情况下风扇不转。在刷机系统的 `terminal` 上的执行 `lsusb` 如果显示的结果中出现 `ID 0955:7023 Nvidia Corp.APX` (注意不是 `NVIDIA Linux for Tegra` 这个表示还在正常的运行系统 `Tegra`) 则表示算力舱已经成功的进入到 `recovery` 模式 3. 在刷机系统上执行 ``` cd /Linux_for_Tegra sudo ./flash.sh jetson-agx-orin-devkit internal # 重复可以刷可以使用 sudo ./flash.sh -r jetson-agx-orin-devkit internal ``` 等待运行结束后,会显示以下的内容 ``` [ 1100.2456 ] Coldbooting the device [ 1100.2459 ] tegrarcm_v2 --chip 0x23 0 --ismb2 [ 1100.2462 ] MB2 version 01.00.0000 [ 1100.3052 ] Coldbooting the device [ 1100.3056 ] tegrarcm_v2 --chip 0x23 0 --reboot coldboot [ 1100.3057 ] MB2 version 01.00.0000 *** The target generic has been flashed successfully. *** Reset the board to boot from internal eMMC. ``` 算力舱会自动重启,重启成功后,系统已经正常运行,下面是继续配置 `docker` 和 微服的AI客户端服务。 4. 配置微服AI服务客户端和 `docker` 存储目录, 有两种方式进去到算力舱中 * 使用 `Type-C` 连接 `Type-C` 口还连接的情况下,您可以使用 `ssh nvidia@192.168.55.1` (如果您 `ping 192.168.55.1` 不通的话,那需要您本地配置下,要将一个usb口的 `ip` 配置成 `192.168.55.x` 同一个网段的地址) 进入到算力舱中去,帐号密码为 `nvidia:nvidia` * 通过显示屏 直接在界面上登录用户 `nvidia`,密码为 `nvidia` * 插上网线,通过路由器查看 `ip` 地址 当您知道算力舱的 `ip` 地址后,您可以通过 `ssh nvidia@ip` 来进入到算力舱系统中。 进去后,打开终端,在家目录下,有一个 `sudo ./lzc-jetson-installer.sh` 的脚本,执行 `sudo ./lzc-jetson-installer.sh`. 1. 在安装 `docker` 的时候会需要连接网络,如果您有代理,速度将会快很多. `DOCKER_PROXY=http://127.0.0.1:1080` 2. 如果您不需要安装 `lzc-ai-agent` 您可以使用 `DISABLE_LZC_AIAGENT=1` 比如 `sudo DOCKER_PROXY=http://127.0.0.1:1080 ./lzc-jetson-installer.sh` 安装成功后,算力舱会自动重启,到此算力舱的系统部署好了! --- --- url: /aipod/aipod/firemare.md --- # 算力舱固件 在算力舱中有一个固件,负责和微服中进行通讯,固件的版本号和微服中的 `AI POD` 版本号保持一致。 固件更新有两种方式: * 在 AI 浏览器中会自动检测当前是否有可用的更新,如果有可用更新,将会弹出一个可以升级的弹窗。点击升级后也会将固件进行升级。 ![update tips](/assets/firemare-update.D0StsBzo.png) * 在算力舱的管理列表中,当有可用的更新后,也会有一个更新提示。 ![device list firemare update](/assets/device-list-firemare.CqlsinH-.png) --- --- url: /aipod/os/port-forward.md --- # 算力舱端口转发 在算力舱的系统中,默认具有一个 `lzc-ai-agent` 的 `systemd` 服务,这个服务负责拉取镜像、管理容器启动、还有和微服连接。 在一些情况下,您可以需要直接使用算力舱的 ip 进行返回一个里面 docker 部署的服务。但因为内部的服务都是没有暴露端口,所以您需要一个端口转发,将服务的端口暴露到算力舱的局域网地址中去。 0. 算力舱的 ip 地址可以在 `aipod` 设备管理列表中查看 ![copy-aipod-ip](/assets/copy-aipod-ip.CZxL-fUT.jpg) 1. 打开地址 `http://算力舱的ip:40793/ui` 地址。如果您是在算力舱上的浏览器访问,您可以 `http://127.0.0.1:40793/ui` 打开。并添加您需要转发的服务,比如 `bgem3vllm-ai` ![client-port-forward.jpg](/assets/client-port-forward.CLsbHSw5.jpg) 3. 测试 打开 `http://ip:端口`,比如我上面的是 `bgem3vllm-ai` 和 `5666` 端口. ![client-port-forward-test.jpg](/assets/client-port-forward-test.DM0Pk5TI.jpg) 或者直接在算力舱中进行访问. ``` > curl http://127.0.0.1:5666/v1/models ``` ::: info 注意: 目前不会自动拉起对应的服务,在处理中 ::: --- --- url: /aipod/trans/trans.md --- # 精准翻译(大语言模型) 算力舱中内置了一个优化过的高性能大语言模型,专门用于高质量翻译任务,能够提供准确、流畅、符合语境的翻译结果,特别适合对翻译质量要求较高的场景。微服中的应用可以通过算力舱暴露的 `trans` API 直接调用该服务。 ## 模型特点 * **高质量翻译**:基于大语言模型,提供准确且符合语境的翻译 * **多语言支持**:支持主流语言之间的相互翻译 * **灵活配置**:支持自定义翻译要求,如语言对、翻译风格等 * **兼容性强**:完全兼容 OpenAI API 格式,易于集成 * **高性能部署**:基于 vLLM 框架优化部署,响应速度快 * **优秀基础模型**:基于 Qwen3 模型,翻译任务效果优秀 ## 服务信息 * **API 地址**: * **OpenAI 兼容地址**: * **默认模型名**:`aipod-trans`(当前版本指向 Qwen3 模型,推荐使用此别名 `aipod-trans` 方便 API 调用和后续无感升级) * **响应模式**:支持流式和非流式响应 * **自定义配置**:支持通过 system prompt 指定翻译语言、风格等要求 --- --- url: /aipod/aisearch.md --- # 网络搜索 AI 应用现在内置了网络搜索功能,可提供给应用调用搜索引擎和获取网页内容的能力。 支持 API 和 MCP 两种使用方式。 > 搜索结果数据来源为多种搜索引擎混合数据,会根据可用性自动启用。 ## 文档 ### MCP 服务器协议:`Streamable HTTP` 服务器地址: 可以在支持 MCP 的 AI 应用中直接调用。 点击跳转到 [MCP 样例](#mcp-样例) ### API 详细文档 可以通过 查看。 点击跳转到 [API 调用样例](#api-调用样例) ## MCP 样例 > 注意将下面 url 中的 xxx 替换为你的微服名称 ### Claude Code 配置 编辑 Claude Code 的配置文件 `~/.claude.json` 添加如下 MCP 服务器配置: ```json { ... "mcpServers": { "aisearch": { "type": "http", "url": "https://aisearch-ai.xxx.heiyu.space/mcp/" } }, ... } ``` ### Codex 配置 编辑 Codex 的配置文件 `~/.codex/config.toml` 添加如下 MCP 服务器配置: ```toml [mcp_servers] [mcp_servers.aisearch] type = "http" url = "https://aisearch-ai.xxx.heiyu.space/mcp/" ``` ### AI 对话客户端配置 以 Cherry Studio 配置为例,在 设置 -> MCP 服务器中添加如下配置: * 名称:aisearch * 类型:可流式传输的 HTTP (streamableHttp) * URL:https://aisearch-ai.xxx.heiyu.space/mcp/ 点击右上角的保存并打开启用开关,在`工具`页面可以看到各种 MCP 工具说明启用成功。 ![tools](/assets/tools.DCoeirLz.png) 在对话界面底部手动启用 MCP 工具 `aisearch`,就可以在对话中使用微服提供的网络搜索功能了。 ## API 调用样例 > 注意将下面 url 中的 xxx 替换为你的微服名称 ### 搜索 ```bash curl -X 'POST' \ 'https://aisearch-ai.xxx.heiyu.space/search?query=LazyCat%20Cloud%20Website&include_raw_content=false&max_results=10&include_answer=false&include_usage=false' \ -H 'accept: application/json' \ -d '' ``` 返回: ```json { "query": "LazyCat Cloud Website", "answer": null, "images": [], "results": [ { "title": "懒猫微服", "url": "https://lazycat.cloud/download/", "content": "2 天之前 · 懒猫微服是一款专为开发者和技术爱好者打造的私有云解决方案。它结合了强大的AI计算能力和领先的LZCOS操作系统,提供超安全内网穿透、NAT穿透、零信任硬件设计,以及一站式应用商 …", "score": 1, "raw_content": null, "favicon": null }, { "title": "AI 服务器, 开源开发者专属福利! - GitHub Pages", "url": "https://manateelazycat.github.io/2024/08/17/lazycat-microserver/", "content": "2024年8月17日 · 🚀 重磅发布: #懒猫微服 - 你的专属 AI 私有云服务器! 👨‍💻 源自国内顶尖操作系统团队 🛠️ 三年匠心打磨, 底层架构精心设计 🎉 流浪地球机甲风, 今天终于量产啦! 🔥 产品亮点, 降低开发者创作 …", "score": 0.8, "raw_content": null, "favicon": null }, { "title": "懒猫微服开发简明教程 | 虫子樱桃", "url": "https://czyt.tech/post/simple-guide-for-developing-for-lazycat-nas/", "content": "2025年2月7日 · 最近入手了懒猫微服,简单记录下开发相关的内容。 环境配置 先决条件 你必须有一台懒猫微服,购买地址 安装基本环境lzc-cli,请参考官方说明地址 如果你要发布程序,必须要申请成为懒 …", "score": 0.7, "raw_content": null, "favicon": null } ], "response_time": "1.19", "usage": null, "request_id": null } ``` ### 获取网页内容 ```bash curl -X 'POST' \ 'https://aisearch-ai.xxx.heiyu.space/extract?urls=https%3A%2F%2Flazycat.cloud%2F&include_images=false&extract_depth=basic&chunks_per_source=3&include_favicon=false&format=markdown&timeout=60&include_usage=false' \ -H 'accept: application/json' \ -d '' ``` 返回: ```json { "results": [ { "url": "https://lazycat.cloud/", "raw_content": "[首页](https://lazycat.cloud/)[懒猫微服](https://lazycat.cloud/lcmd)[懒猫AI算力舱](https://lazycat.cloud/ai-pod)[应用商店](https://lazycat.cloud/appstore)[攻略](https://lazycat.cloud/playground)[下载](https://lazycat.cloud/download)[AI 助手](https://lazycat.cloud/chat)[开发者](https://lazycat.cloud/developer)[关于](https://lazycat.cloud/about)\n(太长在文档中省略)", "images": [], "favicon": null } ], "failed_results": [], "response_time": 1.6488618850708008, "usage": null, "request_id": null } ``` --- --- url: /aipod/os/network-config.md --- # 网络配置 算力舱的支持 wifi 和 有线连接,其中有线连接支持 `2.5G` 和 `10G` 网络。 ## 通过 `HDMI + 鼠标键盘` 配置 wifi 将显示屏连接到算力舱后,点击屏幕右上角的 wifi 图标进行连接。 ## 通过微服 `AI POD` 配置 wifi ::: warning 在算力舱中已经存在机器是不会被扫描到的,如果您想重新添加,您需要先在算力舱的管理列表中,将算力舱删除。 ::: 1. 打开 `AIPOD` 的配置界面,点击 `添加算力舱` 2. 确保手机打开蓝牙,并且已经授予 `懒猫微服` 客户端访问附近蓝牙设备的权限。 3. 查找设备,在找到的列表中,如果具有ip地址,则是通过网线找到的,否则就是蓝牙找到的。 ![scan device list](/assets/scan-devices-list.5EUJjVKd.jpg) 4. 选择您需要绑定的设备,点击 “开始绑定”。 5. 会弹出一个 wifi 选择列表,在这个列表中,您可以选择您的 wifi,填写 wifi 密码进行连接。 ![join wifi](/assets/join-wifi.CH4DrK92.jpg) --- --- url: /aipod/os/jtop.md --- # 资源占用 ## 在微服中查看算力舱的资源占用 1. 打开 AIPOD 应用 点击快速跳转 ![起动器](/assets/aipod-launcher.-kD8R7-R.png) 2. 点击右上角的设置按钮。 ![设置](/assets/aipod-home.DKlbcO9Y.png) 3. 点击算力舱管理列表中的查看详情。 ![查看详情](/assets/aipod-vram-detail.DKS7Ylzf.png) 4. 点击后会跳转到一个新的页面,里面展示您当前算力舱各个服务的占用显存。(注意:这里只会显示AI应用占用的,如果您手动部署的,将不会显示出来) ![显存列表](/assets/aipod-vram-list.DsIkTiEL.png) ## jtop 查看算力舱占用 1. 打开 jtop连接 ![jtop-ai](/assets/aipod-jtop.97yc_x6X.png) 其中底部的菜单栏是可以点击的或者按 `1, 2, 3, 4, 5, 6, 7` 进行切换。 ![jtop-ai-mem](/assets/aipod-jtop-mem.Bxm8G06C.png) 2. ssh 到算力舱后,执行 `jtop` 命令查看 ![jtop-ai-cpu](/assets/aipod-jtop-cpu.D5I9Y9LD.png) ## 算力舱中为什么不用使用 nvidia-smi? > It is not possible to use nvidia-smi on a Jetson. This program/utility requires a PCI bus. Jetsons have an integrated GPU (iGPU) which is wired directly to the memory controller. Only a discrete GPU (dGPU) on a PCI slot can use that utility. > 在Jetson上无法使用nvidia-smi。该程序/工具需要PCI总线。Jetson配备的集成显卡(iGPU)直接连接到内存控制器。只有安装在PCI插槽上的独立显卡(dGPU)才能使用该工具。 > An interesting proposal for NVIDIA: Make a surrogate nvidia-smi program which looks like the original nvidia-smi to programs performing a GPU query, but have it talk instead to the iGPU. Probably not practical, but if it worked, it would make the GPU much more flexible and interchangeable with other software. > 一个有趣的想法,针对NVIDIA:制作一个代理程序nvidia-smi,它在执行GPU查询的程序看来就像原始程序nvidia-smi,但实际上却与iGPU通信。这可能不切实际,但如果能实现,将使GPU在与其他软件的兼容性和灵活性上大大提升。 > EDIT (August, 2024): The above is still true, except that Orin is able to use L4T R36.x, and there is a partial surrogate nvidia-smi with this. This is an nvidia-smi with limited functionality which might suffice in some cases, but the iGPU is still an iGPU without any PCI bus function on Orin plus R36.x. > 编辑(2024年8月):上述内容仍然成立,只是Orin可以使用L4T R36.x,并且为此提供了一个部分替代方案nvidia-smi。这是一个nvidia-smi,功能有限,可能在某些情况下足够使用,但Orin加上R36.x的iGPU仍然没有PCI总线功能。 1. https://forums.developer.nvidia.com/t/nvidia-smi-not-present-in-jetson-linux/239757/2 --- --- url: /aipod/issues/traefik-gateway-timeout.md --- # 通过https访问服务超时 当您使用 `https://${服务名称}-ai.${微服名称}.heiyu.space` 提示 `Gateway timeout`,这个可能是您在 `docker-compose.yml` 中定义的服务,没有添加 `traefik` 的网卡,您可以在 `docker-compose.yml` 中添加默认的网卡,也可以只对其中暴露的服务指定网卡。 1. 默认网卡 ```yml networks: default: external: true name: traefik-shared-network ``` 2. 指定网卡 ```yml services: xxx: networks: - traefik-shared-network ``` --- --- url: /aipod/ai-browser/config-flags.md --- # 配置浏览器Flags ## 配置 Local Network Access Checks 在最新版的 `Chrome (142+)` 中可能会出现以下问题 * 网页总结的页面中,会出现 `Failed to fetch` 的错误 * 在开发者工具中控制台中可以看到 `...has been blocked by CORS policy: Permission was denied for this request to access the 'unknown' address space.` 1. 在 `Chrome` 中打开 `chrome://flags/#local-network-access-check` 2. 将配置项从 `Default` 更改成 `Disabled`,默认的选项为 `Blocking` ![local network access checks](/assets/config-local-access-network.DIKIIl8X.png) 相关连接: * https://chromestatus.com/feature/5152728072060928 * https://developer.chrome.com/blog/local-network-access ## 配置网络 1. 打开地址 `chrome://proxy` ![config network](/assets/config-network.Dwz38CV0.png) 2. 在底部的填写框中,将 `*.heiyu.space;*.lazycat.cloud;` 写进去,允许访问 `*.heiyu.space` 和 `*.lazycat.cloud` 地址。 3. 点击 `Apply` 按钮应用。 --- --- url: /aipod/os/firmware.md --- # 驱动 # Wifi网卡 AW-XB560NF ``` sudo modprobe cfg80211 sudo insmod 8852ce_20250707.ko mv rtl8852bu_config rtl8852bu_fw rtl8852cu_config rtl8852cu_fw /lib/firmware sudo rmmod rtk_btusb sudo insmod rtk_btusb.ko ```