龙芯3B6000M运行Yolov8+FastApi

龙芯近日发布支持自研通用GPU的龙芯加速计算平台(Loongson Accelerated Computing Platform)首个软件版本。 该平台基于龙芯2K3000(3B6000M) 及9A1000内集成的自研LG200系列通用GPU核心打造,实现了对算力芯片驱动、算力编程环境、AI模型推理等功能的全栈一体支持。开发者可低成本将CUDA应用迁移至龙芯,大幅降低国产算力生态门槛,并服务于工业视觉、智能安防等广泛领域。

手头有一款3B6000M龙芯派,抛砖引玉,搭建了一个yolov8+FastApi的Demo,可以流畅运行,将搭建步骤分享一下:

1、硬件准备

  CPU:2K3000或3B6000M( 7.2 TOPS @ INT8 )

  内存空间:至少 8GB RAM

  显存要求:大于等于 2GB

  操作系统:Loongnix25.2

2、驱动安装

**  2.1 gpu驱动:**

复制代码
wget https://repos.loongson.cn/loonggpu/loongnix25/local_installers/loonggpu-repo-loongnix25-local_1.0.2-lnd25.1_loong64.deb
sudo dpkg -i loonggpu-repo-loongnix25-local_1.0.2-lnd25.1_loong64.deb
sudo apt-get update
sudo apt-get -y install loonggpu-drive

  安装后可以在终端验证一下,正常会出现如下结果:

复制代码
$ lspci -s 00:06.0 -vvv
00:06.0 Multimedia video controller: Loongson Technology LLC Device 7a35 (rev 10)
Control: I/O+ Mem+ BusMaster+ SpecCycle- MemWINV- VGASnoop+ ParErr- Stepping- SERR- FastB2B- DisINTx-
Status: Cap- 66MHz- UDF- FastB2B- ParErr- DEVSEL=fast >TAbort- <TAbort- <MAbort- >SERR- <PERR- INTx-
Latency: 0
Interrupt: pin A routed to IRQ 102
NUMA node: 0
Region 0: Memory at 408125e000 (64-bit, non-prefetchable) [size=256]
Region 2: Memory at 4000000000 (64-bit, non-prefetchable) [size=2G]
Region 4: Memory at 4081200000 (64-bit, non-prefetchable) [size=64K]
Kernel driver in use: loonggpu
$

**  2.2 算力栈软件安装**

复制代码
wget https://repos.loongson.cn/loongacm/loongnix25/local_installers/v0.1.0-lnd25.5/loongac-0.1.0-lnd25.5.tgz
tar -xf loongac-0.1.0-lnd25.5.tgz
cd loongac-0.1.0-lnd25.5
sudo apt install ./*.deb

# 将当前用户加入 render 和 video 组中,其中 $LOGNAME 可以换成自己想要添加的用户名,配置后需重新注销登录生效。
sudo usermod -a -G render,video $LOGNAME

**  2.3 验证安装**

复制代码
/opt/lacm/bin/clinfo

#出现以下内容即可
Number of platforms: 1
Platform Profile: FULL_PROFILE
Platform Version: OpenCL 3.0 LS-APP (3581.0)
Platform Name: LS Accelerated Parallel Processing
Platform Vendor: Loongson Technology
Platform Extensions: cl_khr_icd cl_ls_event_callback

Platform Name: LS Accelerated Parallel Processing
Number of devices: 1
Device Type: CL_DEVICE_TYPE_GPU
Vendor ID: 14h
Board name: LOONGSON LoongGPU (TM) LG200
Device Topology: PCI[ B#0, D#6, F#0 ]
......

3、yolov8n配置测试

**  3.1 代码下载解压**

复制代码
lftp https://repos.loongson.cn/loongacm/
mirror lacinfer-model-zoo
sudo cd ./lacinfer-model-zoo/yolov8
sudo mkdir /opt/lsai/demo
sudo mkdir /opt/lsai/demo/int8_model
sudo mkdir /opt/lsai/demo/fp32_model
sudo mkdir /opt/lsai/demo/images

sudo cp lacinfer_subprocess_pipeline.py /opt/lsai/demo/
sudo cp -r ./python/yolov8_infer_lacinfer.py /opt/lsai/demo/
sudo mv /opt/lsai/demo/yolov8_infer_lacinfer.py detector.py
sudo cp -r ./models/fp32_model /opt/lsai/demo/fp32_model
sudo cp -r ./images/ /opt/lsai/demo/images
sudo cd /opt/lsai/demo/models

**  3.2. INT8量化:**

复制代码
sudo cd /opt/lsai/demo
python3 ./detector.py \
--staticModelPath ./f32_model/yolov8n.onnx \
--action quant-int8 \
--calibrationPath ./images \
--saveLirs

sudo mv yolov8n-quant-int8-compiled.lir ./int8_model
sudo mv yolov8n-quant-int8.lir ./int8_model

**  3.3.调用量化后的模型:**

复制代码
python3 detector.py \
--staticModelPath ./int8_model/yolov8n-quant-int8-compiled.lir \
--modelFormat lir-compiled \
--imgPath ../images/person.jpg \
--cocoClassPath ../int8_model/coco.names \
--action infer

4.部署运行FastApi

  建立python虚拟环境,然后部署fastapi:

复制代码
sudo apt install python3.13-venv
python3 -m venv venv
sudo chown -R $USER:$USER /opt/lsai/demo/venv
source venv/bin/activate

pip install fastapi uvicorn
#pip install opencv-python
pip install opencv-contrib-python numpy
pip install python-multipart

  新建app.py文件,定义几个简单访问接口(我这里只创建了上传和访问、下载接口),代码如下:

复制代码
mport io
import cv2
import numpy as np
from fastapi import FastAPI, File, UploadFile, HTTPException
from fastapi.responses import JSONResponse, Response
from detector import YOLOv8

app = FastAPI(title="YOLOv8 LacInfer 检测服务")
detector = None

@app.on_event("startup")
def load_model():
    global detector
    detector = YOLOv8(
        cocopath="./int8_model/coco.names",
        modelpath="./int8_model/yolov8n-quant-int8-compiled.lir",
        calpath="",
        action="infer",
        modelformat="lir-compiled",
        quantonly=False,
        savelirs=False,
    )
    print("模型加载完成,服务准备就绪。")

def _read_upload_image(file: UploadFile) -> np.ndarray:
    if not file.content_type.startswith("image/"):
        raise HTTPException(status_code=400, detail="请上传图片文件")
    contents = file.file.read()
    nparr = np.frombuffer(contents, np.uint8)
    img = cv2.imdecode(nparr, cv2.IMREAD_COLOR)
    if img is None:
        raise HTTPException(status_code=400, detail="无法解码图片")
    return img

def _detect_and_draw(img: np.ndarray):
    boxes, scores, class_ids = detector.detect(img)
    dst = img.copy()
    if boxes is not None:
        detector.draw_detections(dst, boxes, scores, class_ids)
    return dst, boxes, scores, class_ids

@app.post("/detect")
def detect_objects(file: UploadFile = File(...)):
    img = _read_upload_image(file)
  _, boxes, scores, class_ids = _detect_and_draw(img)
    if boxes is None:
        return {"detections": []}

    results = []
    for box, score, cl in zip(boxes, scores, class_ids):
        results.append({
            "bbox": [float(x) for x in box],
            "score": float(score),
            "class_id": int(cl),
            "class_name": detector.classNames[int(cl)] if int(cl) < len(detector.classNames) else str(cl)
        })
    return JSONResponse(content={"detections": results})

@app.post("/detect/download")
def detect_and_download(file: UploadFile = File(...)):
    """检测并在响应中直接返回标注后的图片,触发浏览器下载。"""
    img = _read_upload_image(file)
    dst, boxes, _, _ = _detect_and_draw(img)

    # 编码为 JPEG 字节流(在内存中完成,不落盘)
    ok, buf = cv2.imencode(".jpg", dst, [int(cv2.IMWRITE_JPEG_QUALITY), 95])
    if not ok:
        raise HTTPException(status_code=500, detail="结果图编码失败")

    # 生成下载文件名:基于上传文件名
    original_name = file.filename or "upload"
    stem = original_name.rsplit(".", 1)[0]
    download_name = f"{stem}_detected.jpg"

    headers = {
        # 关键:attachment 触发下载,filename 指定保存名
        "Content-Disposition": f'attachment; filename="{download_name}"'
    }
    return Response(content=buf.tobytes(), media_type="image/jpeg", headers=headers)

@app.post("/detect/view")
def detect_and_view(file: UploadFile = File(...)):
    """检测并直接返回图片字节流,浏览器会内联显示(不下载)。"""
    img = _read_upload_image(file)
    dst, _, _, _ = _detect_and_draw(img)

    ok, buf = cv2.imencode(".jpg", dst)
    if not ok:
        raise HTTPException(status_code=500, detail="结果图编码失败")
    return Response(content=buf.tobytes(), media_type="image/jpeg")

@app.get("/health")
def health():
    return {"status": "ok", "model_loaded": detector is not None}(

  部署完成后通过以下命令进行启动:

复制代码
python3 -m uvicorn app:app --host 0.0.0.0 --port 8000

#如果出现报错 ModuleNotFoundError: No module named 'lacinfer'
需要找到 lacinfer 实际所在的 site-packages 或 dist-packages 目录,然后把它加到虚拟环境的搜索路径里,本代码执行:
echo "/opt/lacm-0.1.0/lib" > /opt/lsai/demo/venv/lib/python3.13/site-packages/lacinfer_path.pth

5.运行效果如下:(原图来源与互联网)

相关推荐
西西弗Sisyphus1 小时前
理解 Linux 动态库加载:LD_LIBRARY_PATH
linux
AR-26710-1 小时前
Linux Day31——实操启停服务改端口重启
linux·运维
叼烟扛炮2 小时前
Linux 学习笔记(五十八):IO 多路复用封神——epoll 底层原理揭秘
linux·运维·服务器·网络·笔记·学习·php
叼烟扛炮2 小时前
Linux 学习笔记(五十一):数据链路层与 ARP 协议——局域网寻址与黑客骗局
linux·网络·网络协议·php·tcpdump
星恒随风3 小时前
Linux网络编程:彻底理解IO多路复用select!从fd_set位图、读写就绪到手写TCP多客户端字典服务器
linux·服务器·网络
陈布衣3 小时前
MySQL(1)_MySQL 5.7.21 Linux 安装笔记
linux·笔记·mysql
Oiiouui5 小时前
linux服务器部署Logto后端与对应前端的实现
linux·服务器·前端·后端
ITKEY_5 小时前
用 Emacs Dired 实现 em:退出文件管理器后,让终端自动切换目录
linux·服务器·emacs
wt95276 小时前
VMware 虚拟机磁盘扩容实战文档(Ubuntu 22.04 + LVM)
linux·后端