Please check the build logs for more information.
See Builds for ideas on how to fix a failed build, or Metadata for how to configure docs.rs builds.
If you believe this is docs.rs' fault, open an issue.
audio-cpp
audio.cpp(基于 ggml 的本地音频推理引擎)的高层安全 Rust 封装。
底层 FFI 位于 audio-cpp-sys;本 crate 在其之上提供类型安全的
注册表 / 模型 / 会话 API,并把所有跨 C 边界的资源管理(句柄释放、
字符串所有权、事件回调)封装进安全的 Drop 与类型系统。两者共享同一份
C++ engine_runtime,不重写 audio.cpp。
依赖与构建
[]
= { = "../audio-cpp" } # 或版本号
首次构建前需先补齐 git submodule(见工作区 README):
模型组合与计算后端通过 features 选择,全部转发给 audio-cpp-sys(含义见
该 crate 的 Cargo.toml):
cargo build # core-models(内置 VAD,开箱即用)
cargo build --features model-qwen3-asr # 按需编译单个模型族(无需环境变量)
cargo build --features model-citrinet-asr,model-moss,openmp # 多族 + 后端
cargo build --features full-models,cuda # 全量 + GPU 后端
模型族 feature 命名约定
model-<上游 target 名>(-/_等价,如model-qwen3-asr或model-qwen3_asr)。已内置一组常用族(ASR/TTS/分离, 见[features]表);未覆盖的族仍可$env:AUDIOCPP_MODELS="..."配合--features custom-models使用,两者可混用(取并集)。
架构:一次调用的完整链路
Registry::new() # 枚举已编译的模型族/loader/设备
└─ registry.load(path, family_hint, options) → Model
└─ model.create_task_session(task, mode, backend, device, threads, opts) → Session
├─ 离线: session.run_offline(request_json) → TaskResult
└─ 流式: session.set_event_callback(cb)
session.start(json) → process_audio(&[f32], ...) → ... → finish() → TaskResult
session.reset() # 复用会话开始新一轮
各对象持有 C 句柄并在 Drop 中释放;Model 不管理 Registry 的生命周期,
注册表应存活于所有派生模型的使用期之内。
基本用法
1. 枚举引擎能力
use Registry;
let registry = new?;
println!; // ["silero_vad","marblenet_vad",...]
println!; // [Device{ backend:"CPU", ... }]
for loader in registry.loaders?
2. 离线 VAD(silero_vad,内置权重开箱即用)
use ;
let registry = new?;
let model = registry.load?;
let session = model.create_task_session?;
let request = r#"{"audio_path":"./sample.wav","options":{"vad_threshold":0.5}}"#;
let result = session.run_offline?;
for seg in &result.speech_segments
3. 流式 VAD(分块送入 + 事件回调)
use ;
use ;
let registry = new?;
let model = registry.load?;
let wav = load_wav?;
let mut session = model.create_task_session?;
let policy = session.streaming_policy?; // 推荐分块大小
let chunk = policy.preferred_audio_chunk_samples.max;
let events = new;
let collector = clone;
session.set_event_callback;
session.start?;
for block in wav.samples.chunks
let result = session.finish?; // 最终语音片段
session.reset; // 复用会话重新开始
注意:silero_vad 流式要求每块恰好
preferred_audio_chunk_samples(512)个采样,末尾不足块必须补零。回调可能来自 C++ 侧线程,回调内不得 再调用本会话的方法。
4. 离线 ASR(Citrinet,需按需编译)
use ;
let registry = new?;
// GGUF 无法自动探测族别(会误判为 silero_vad),必须显式 family_hint。
let model = registry.load?;
let session = model.create_task_session?;
let request = r#"{"audio_path":"./speech.wav"}"#;
let result = session.run_offline?;
if let Some = &result.text_output
5. 流式 ASR(Qwen3 ASR,需按需编译)
Qwen3 ASR 同时支持离线与流式。流式会话与 VAD 类似:
start(请求) → 分块 process_audio() → finish();窗口边界会经事件回调
产出 partial_text 部分转录。streaming 的 start 请求需带 audio_path(或
audio 对象)以建立音频契约,否则 prepare 会报错。
use ;
use ;
let registry = new?;
let model = registry.load?;
let wav = load_wav?;
let mut session = model.create_task_session?;
let policy = session.streaming_policy?;
let partial = new;
let collector = clone;
session.set_event_callback;
// streaming 的 start 请求须含音频契约(audio_path 或 audio 对象)。
let request = r#"{"audio_path":"./speech.wav","options":{"audio_chunk_seconds":3.0}}"#;
session.start?;
let chunk = .round as usize;
for block in wav.samples.chunks
let result = session.finish?; // 最终完整文本
session.reset;
注意:
preferred_audio_chunk_samples可能为 0,Qwen3 ASR 只填preferred_audio_chunk_seconds,分块大小按秒数 × 采样率换算即可。
6. 离线 TTS(MOSS-TTS-Nano,需 custom-models 构建)
use ;
let registry = new?;
let model = registry.load?;
let session = model.create_task_session?;
let request = r#"{"text":"Hello from Rust and audio.cpp!"}"#;
let result = session.run_offline?;
// 合成音频在 audio_output.samples(f32,交错存放),值域 -1..1。
let audio = result.audio_output.expect;
let samples = audio.samples.expect;
println!;
关键类型速查
| 类型 | 说明 |
|---|---|
Registry |
枚举模型族 / loader / 设备;load() 加载模型 |
Model |
已加载模型:metadata() / capabilities() / create_task_session() |
Session |
任务会话:离线 run_offline();流式 start/process_audio/finish/reset |
TaskKind |
Vad / Asr / Tts / Diar / SourceSeparation |
ModelFamily |
模型族枚举(Qwen3Asr / CitrinetAsr / Htdemucs / …;未收录族用 Custom(String)) |
RunMode |
Offline / Streaming |
Backend |
Cpu / Cuda / Hip / Vulkan / Metal / Best |
TaskResult |
speech_segments / text_output / audio_output / named_audio_outputs |
StreamEvent |
流式事件:voice_activity / partial_text / audio_output / named_audio_outputs / is_final |
load_wav |
读 WAV 为 WavAudio { sample_rate, channels, samples } |
所有枚举的 as_str() 返回传给 C 边界的字符串;结构化数据一律走 JSON
(request_json 为任意 JSON 对象,如 {"audio_path":...,"options":{...}})。
注意事项
- family_hint 必填场景:NeMo safetensors(如 marblenet_vad)与 GGUF
(如 citrinet_asr / moss_tts_nano / htdemucs / sortformer_diar / qwen3_asr)
无法被引擎自动探测族别,会误判为 silero_vad,必须显式传
family_hint。 用ModelFamily枚举代替裸字符串(如Some(ModelFamily::Qwen3Asr))可避免拼写错误;内置 silero_vad 可省略。 - 阈值选项键:silero_vad 用
vad_threshold,marblenet_vad 用threshold。 - Windows 路径:请求 JSON 中的反斜杠必须转义(
\\),建议改用正斜杠;\a等非法转义会让 shim 解析失败。 - 线程:
Session为Send;事件回调要求Send闭包,可能从 C++ 线程调用。 - 错误:所有方法返回
Error,底层错误信息经audiocpp_last_error()透传,为类型化枚举,可用?传播。
完整可运行示例见 examples/(vad_offline / vad_streaming /
asr_offline / asr_streaming / tts_offline / tts_streaming / diar_offline /
sep_offline / registry_inspect)。其中 vad_streaming / asr_streaming /
tts_streaming / registry_inspect 已在本机 win32/MSVC 验证运行;其余离线示例
此前已验证。测试权重文件可放在 F:\models 下。