[经验分享] 拆·应用丨第6期:基于Vulkan的端侧AI运算

开源鸿蒙知行录 显示全部楼层 发表于 2026-1-22 14:19:26

【拆·应用】是为开源鸿蒙应用开发者打造的技术分享平台,是汇聚开发者的技术洞见与实践经验、提供开发心得与创新成果的展示窗口。诚邀您踊跃发声,期待您的真知灼见与技术火花! 引言 本期内容由AI Model SIG提供,介绍了在开源鸿蒙中,利用图形接口Vulkan的计算着色器能力,在端侧部署大模型的的整体思路和实践分享。

开源鸿蒙是由开放原子开源基金会孵化及运营的开源项目,目标是面向全场景、全连接、全智能时代,搭建一个智能终端设备操作系统的框架和平台,促进万物互联产业的繁荣发展。在人工智能时代下,与其它成熟的操作系统相比,开源鸿蒙部署AI LLM模型的能力欠缺。为了补齐开源鸿蒙在端侧部署大模型的能力,笔者将分享如何在端侧打通大模型部署的整体思路和实践。

软硬件选型

在硬件上选取国产CPU飞腾D2000,显卡选用AMD GPU。目前能够在 OpenHarmony5.0.0 Release上点亮AMD GPU,包括RX 550、RX 580和RX 7900 XTX。 其次是推理框架的选择,笔者选取了 llama.cpp这个开源的推理框架。目前很火的 ollama,其也是选用了 llama.cpp作为推理后端。llama.cpp是一个专注于在边缘设备、个人PC上进行llm部署的高性能推理框架。其相比于vllm等主流llm推理框架来说,有以下明显的优点:

  • 纯 C++/C 实现,在 WindowsmacLinux等多种系统下编译都非常简单。
  • 丰富的后端支持:如图所示,支持 x86armNvidia_GPUAMD_GPUVulkan甚至 华为昇腾NPU_CANN
  • 支持CPU AVX指令集进行矢量计算加速、CPU多核并行计算、CPU+GPU混合计算
  • 支持低精度量化:1.5bit、2 bit、3 bit、4 bit、5 bit、6 bit和 8 bit整数量化,可加快推理速度并减少内存使用。

<div align="center"><img src="https://forums-obs.openharmony.cn/forum/202601/22/142413ic8esmg8egvcgmim.png" alt="表格"></div> <div align="center">llama.cpp支持的后端及其硬件</div>

在上图中,llama.cpp支持 Vulkan后端。笔者通过查阅相关资料和阅读 llama.cpp关于 Vulkan的相关代码,发现其是利用图形接口 Vulkan的计算着色器(Compute Shader)的能力来运行大模型的。计算着色器(Compute Shader) 是GPU上用于通用计算(GPGPU) 的特殊程序,与传统图形渲染管线解耦,可直接操作GPU并行处理非图形任务(如AI推理、物理模拟、数据处理)等。下表是计算着色器的特点:

2.jpg

综合多因素的考量,在软硬件上最终选用 飞腾D2000 + AMD GPU + OpenHarmony 5.0.0 Release的组合,利用图形接口 Vulkan的计算着色器能力,在终端设备上高效运行大模型。

在开源鸿蒙部署大模型的难点

在第一部分提到将利用图形接口Vulkan的计算着色器的能力,在端侧高效运行大模型。在开源鸿蒙社区有个 Vulkandemo样例,通过笔者的实践,目前在 HarmonyOS能跑通该样例,但是在开源鸿蒙上尚不能跑通该样例。通过阅读该例子的文档说明,如下图,发现核心原因是缺少AMD GPU的 Vulkan用户态驱动库 libvulkan_radeon.so以及 Vulkan的sdk。因此核心难点是要能将 Vulkan的计算着色器在开源鸿蒙上正常跑起来。

<div align="center"><img src="https://forums-obs.openharmony.cn/forum/202601/22/142438y6xx1sfaezyk6e0a.jpg" alt="图片描述"></div> <div align="center">NdkVulkan例子</div>

整体思路

为了能够利用图形接口 Vulkan的计算着色器的能力跑大模型。笔者总结了以下四个的关键步骤:

  1. 在开源鸿蒙上正常点亮AMD GPU。
  2. 交叉编译出AMD的 Vulkan用户态驱动。
  3. 交叉编译出Vulkan sdk。
  4. 移植 llama.cppOpenHarmony上。

实践要点

点亮AMD GPU

  1. 确保AMD GPU 内核态是正常的选用的内核版本为 linux 6.6.22,需要将内核的以下选项打开。

4.jpg

系统正常启动后,采用 modetest工具进行测试,在测试前需要关闭 render_servicecomposer_hostallocator_host这三个进程,具体的命令如下:

5.jpg

hdc shell中运行以下命令:

6.jpg

如果能够在显示屏上看到彩色的条纹,如下图,说明AMD GPU的内核态是正常的。

<div align="center"><img src="https://forums-obs.openharmony.cn/forum/202601/22/142527tthavqzyathvah9b.jpg" alt="图片描述"></div> <div align="center">modetest测试结果</div>

  1. 确保AMD GPU的用户态是正常的

首先通过 mesa3d交叉编译出AMD GPU的用户态驱动,主要为 libEGL.so.1.0.0libgallium_dri.solibgbm.so.1.0.0libglapi.so.0.0.0libGLESv1_CM.so.1.1.0libGLESv2.so.2.0.0这个5个动态库。

8.png

大家可以参考laval社区的《开源鸿蒙开源GPU库Mesa3D适配说明》这篇文章,了解GPU的适配过程。这篇文章主要讲的是 mali gpumesa3d点亮过程。由于跑 Vulkan的计算着色器可以不用到显示的功能,因此在这里具体的适配过程就不展开,感兴趣的读者可在AI Model SIG的 ohos_vulkan仓库获取相关的AMD GPU 的mesa用户态驱动的库。 成功适配后,可以在显示屏正常看到开源鸿蒙的桌面。

Vulkan用户态驱动

这一步的核心是能够获得 libvulkan_radeon.so这个动态库。在 mesa3d中有 Vulkan用户态驱动的实现,因此通过编译 mesa3d这个开源项目编译出 libvulkan_radeon.so这个 Vulkan用户态驱动库。 在 build_ohos.py文件中需要指定 -Dgallium-drivers=amd-Dvulkan-drivers=amd这两个参数,如下图:

9.jpg

通过以下指令:

10.png

便可以编译出 libvulkan_radeon.so这个动态库,如下图所示

11.jpg

Vulkan sdk

Vulkan sdk的构成主要包含以下11个项目:

https://github.com/KhronosGroup/glslang.git https://github.com/KhronosGroup/SPIRV-Headers.git https://github.com/KhronosGroup/SPIRV-Tools.git https://github.com/zeux/volk.git https://github.com/KhronosGroup/Vulkan-ExtensionLayer.git https://github.com/KhronosGroup/Vulkan-Headers.git https://github.com/KhronosGroup/Vulkan-Loader.git https://github.com/KhronosGroup/Vulkan-Tools.git https://github.com/KhronosGroup/Vulkan-Utility-Libraries.git https://github.com/KhronosGroup/Vulkan-ValidationLayers.git

在这里需要通过交叉编译的方式获得 aarch64版本的产物,如下图所示。

12.png

Vulkan sdk的编译比较复杂,可在这里了解详情。 下面介绍一下如何将 Vulkan sdk部署在开源鸿蒙上: 13.jpg

通过运行 vulkaninfo可以获取 vulkan的相关信息,也能获取我们所用GPU的型号。 14.jpg

15.png

目前我们能将 Vulkan在开源鸿蒙上正式跑起来了,接下来需要写一个简单的例子来验证 Vulkan的计算着色器是否正常。笔者提供了一个简单的利用计算着色器来进行矩阵并行计算。该例子的核心就是矩阵A和矩阵B相乘的到矩阵C,矩阵C的每个元素需要做256次乘法255次加法

<div align="center"> <img src="https://forums-obs.openharmony.cn/forum/202601/22/142823i3peiqpq1pmj5357.png" alt="图片描述"> </div> <div align="center">计算着色器</div>

下面是例子的具体内容:

整体流程:初始化Vulkan → 创建矩阵缓冲区 → 构建计算管线 → 提交计算任务 → 同步获取结果 → 验证输出 → 资源释放;

编写计算着色器,如下图; 并行策略:每个线程计算输出矩阵的一个元素; 工作组配置:每个工作组包含16x16=256个并行线程; 执行粒度:与主程序中的 vkCmdDispatch(MATRIX_SIZE/16, MATRIX_SIZE/16, 1)配合,共调度 (256/16)^2 = 256个工作组覆盖整个矩阵; 线程总数:256 * 256 = 65536 个并行线程。

<div align="center"> <img src="https://forums-obs.openharmony.cn/forum/202601/22/142834os5tjukz63kxtw6x.jpg" alt="图片描述"> </div> <div align="center">计算着色器</div>

假设矩阵A的元素全为1,矩阵B的元素全为2,那么矩阵C的计算结果应该全为512。如下图可见矩阵C的计算结果正确,总耗时大概在5毫秒左右。通过对比矩阵C的结果和耗时,初步可以确认 Vulkan的计算着色器能在开源鸿蒙上正常运行。

<div align="center"> <img src="https://forums-obs.openharmony.cn/forum/202601/22/142858x350lj06lqleqqel.jpg" alt="图片描述"> </div>

<div align="center">矩阵C的计算结果</div>

推理框架 llama.cpp

利用前一步得到的 Vulkan sdk,接下来需要交叉编译出 llama.cpp。下面是交叉编译的命令。

19.jpg

最终我们将编译的产物拷贝至开源鸿蒙设备上,然后运行。可以看到 llama.cpp能够正确识别我们的AMD GPU并将模型的权重加载至显卡上。 20.jpg

21.jpg

总结

本文主要分享了如何在端侧打通大模型部署的整体思路和实践,从而补齐开源鸿蒙在端侧部署大模型的能力。目前能够利用图形接口 Vulkan的计算着色器的能力,能够在端侧的AMD的消费级显卡 AMD 7900XTX上部署类似 DeepSeek 32B这类的大模型,从而打造了AI能力的算力底座,为AI应用提供支撑。

©著作权归作者所有,转载或内容合作请联系作者

您尚未登录,无法参与评论,登录后可以:
参与开源共建问题交流
认同或收藏高质量问答
获取积分成为开源共建先驱

Copyright   ©2025  OpenHarmony开发者论坛  京ICP备2020036654号-3 | 京公网安备11030102011662号 |技术支持 Discuz!

返回顶部