Skip to content

Commit 2b27883

Browse files
authored
Add C++ support for UVR models (#2269)
1 parent e0ca224 commit 2b27883

35 files changed

Lines changed: 967 additions & 101 deletions
Lines changed: 58 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,58 @@
1+
#!/usr/bin/env bash
2+
3+
set -ex
4+
5+
log() {
6+
# This function is from espnet
7+
local fname=${BASH_SOURCE[1]##*/}
8+
echo -e "$(date '+%Y-%m-%d %H:%M:%S') (${fname}:${BASH_LINENO[0]}:${FUNCNAME[1]}) $*"
9+
}
10+
11+
if [ -z $EXE ]; then
12+
EXE=./build/bin/sherpa-onnx-offline-source-separation
13+
fi
14+
15+
echo "EXE is $EXE"
16+
echo "PATH: $PATH"
17+
18+
which $EXE
19+
20+
log "------------------------------------------------------------"
21+
log "Run spleeter"
22+
log "------------------------------------------------------------"
23+
curl -SL -O https://github.com/k2-fsa/sherpa-onnx/releases/download/source-separation-models/sherpa-onnx-spleeter-2stems-fp16.tar.bz2
24+
tar xvf sherpa-onnx-spleeter-2stems-fp16.tar.bz2
25+
rm sherpa-onnx-spleeter-2stems-fp16.tar.bz2
26+
27+
curl -SL -O https://github.com/k2-fsa/sherpa-onnx/releases/download/source-separation-models/qi-feng-le-zh.wav
28+
29+
$EXE \
30+
--spleeter-vocals=sherpa-onnx-spleeter-2stems-fp16/vocals.fp16.onnx \
31+
--spleeter-accompaniment=sherpa-onnx-spleeter-2stems-fp16/accompaniment.fp16.onnx \
32+
--num-threads=2 \
33+
--debug=1 \
34+
--input-wav=./qi-feng-le-zh.wav \
35+
--output-vocals-wav=spleeter_output_vocals.wav \
36+
--output-accompaniment-wav=spleeter_output_accompaniment.wav
37+
38+
rm -rf sherpa-onnx-spleeter-2stems-fp16
39+
40+
log "------------------------------------------------------------"
41+
log "Run UVR"
42+
log "------------------------------------------------------------"
43+
curl -SL -O https://github.com/k2-fsa/sherpa-onnx/releases/download/source-separation-models/UVR-MDX-NET-Voc_FT.onnx
44+
45+
$EXE \
46+
--debug=1 \
47+
--num-threads=2 \
48+
--uvr-model=./UVR-MDX-NET-Voc_FT.onnx \
49+
--input-wav=./qi-feng-le-zh.wav \
50+
--output-vocals-wav=uvr_output_vocals.wav \
51+
--output-accompaniment-wav=uvr_output_non_vocals.wav
52+
53+
rm ./UVR-MDX-NET-Voc_FT.onnx \
54+
55+
mkdir source-separation-wavs
56+
mv qi-feng-le-zh.wav source-separation-wavs
57+
mv spleeter_*.wav ./source-separation-wavs
58+
mv uvr_*.wav ./source-separation-wavs

.github/workflows/linux.yaml

Lines changed: 16 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -11,6 +11,7 @@ on:
1111
- '.github/scripts/test-kws.sh'
1212
- '.github/scripts/test-online-transducer.sh'
1313
- '.github/scripts/test-offline-speech-denoiser.sh'
14+
- '.github/scripts/test-offline-source-separation.sh'
1415
- '.github/scripts/test-online-paraformer.sh'
1516
- '.github/scripts/test-offline-transducer.sh'
1617
- '.github/scripts/test-offline-ctc.sh'
@@ -33,6 +34,7 @@ on:
3334
- '.github/workflows/linux.yaml'
3435
- '.github/scripts/test-kws.sh'
3536
- '.github/scripts/test-offline-speech-denoiser.sh'
37+
- '.github/scripts/test-offline-source-separation.sh'
3638
- '.github/scripts/test-online-transducer.sh'
3739
- '.github/scripts/test-online-paraformer.sh'
3840
- '.github/scripts/test-offline-transducer.sh'
@@ -205,6 +207,20 @@ jobs:
205207
overwrite: true
206208
file: sherpa-onnx-*.tar.bz2
207209

210+
- name: Test offline source separation
211+
shell: bash
212+
run: |
213+
du -h -d1 .
214+
export PATH=$PWD/build/bin:$PATH
215+
export EXE=sherpa-onnx-offline-source-separation
216+
217+
.github/scripts/test-offline-source-separation.sh
218+
219+
- uses: actions/upload-artifact@v4
220+
with:
221+
name: source-separation-${{ matrix.build_type }}-with-shared-lib-${{ matrix.shared_lib }}-with-tts-${{ matrix.with_tts }}
222+
path: ./source-separation-wavs/*.wav
223+
208224
- name: Test offline CTC
209225
shell: bash
210226
run: |

README.md

Lines changed: 13 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -1,8 +1,8 @@
11
### Supported functions
22

3-
|Speech recognition| Speech synthesis |
4-
|------------------|------------------|
5-
| ✔️ | ✔️ |
3+
|Speech recognition| Speech synthesis | Source separation |
4+
|------------------|------------------|-------------------|
5+
| ✔️ | ✔️ | ✔️ |
66

77
|Speaker identification| Speaker diarization | Speaker verification |
88
|----------------------|-------------------- |------------------------|
@@ -16,6 +16,7 @@
1616
|------------------|-----------------|--------------------|
1717
| ✔️ | ✔️ | ✔️ |
1818

19+
1920
### Supported platforms
2021

2122
|Architecture| Android | iOS | Windows | macOS | linux | HarmonyOS |
@@ -56,7 +57,9 @@ This repository supports running the following functions **locally**
5657
- Spoken language identification
5758
- Audio tagging
5859
- VAD (e.g., [silero-vad][silero-vad])
60+
- Speech enhancement (e.g., [gtcrn][gtcrn])
5961
- Keyword spotting
62+
- Source separation (e.g., [spleeter][spleeter], [UVR][UVR])
6063

6164
on the following platforms and operating systems:
6265

@@ -75,6 +78,7 @@ on the following platforms and operating systems:
7578
- [VisionFive 2][VisionFive 2]
7679
- [旭日X3派][旭日X3派]
7780
- [爱芯派][爱芯派]
81+
- [RK3588][RK3588]
7882
- etc
7983

8084
with the following APIs
@@ -200,6 +204,7 @@ We also have spaces built using WebAssembly. They are listed below:
200204
| Punctuation | [Address][punct-models] |
201205
| Speaker segmentation | [Address][speaker-segmentation-models] |
202206
| Speech enhancement | [Address][speech-enhancement-models] |
207+
| Source separation | [Address][source-separation-models] |
203208

204209
</details>
205210

@@ -481,3 +486,8 @@ It uses sherpa-onnx for speech-to-text and text-to-speech.
481486
[NVIDIA Jetson Orin NX]: https://developer.download.nvidia.com/assets/embedded/secure/jetson/orin_nx/docs/Jetson_Orin_NX_DS-10712-001_v0.5.pdf?RCPGu9Q6OVAOv7a7vgtwc9-BLScXRIWq6cSLuditMALECJ_dOj27DgnqAPGVnT2VpiNpQan9SyFy-9zRykR58CokzbXwjSA7Gj819e91AXPrWkGZR3oS1VLxiDEpJa_Y0lr7UT-N4GnXtb8NlUkP4GkCkkF_FQivGPrAucCUywL481GH_WpP_p7ziHU1Wg==&t=eyJscyI6ImdzZW8iLCJsc2QiOiJodHRwczovL3d3dy5nb29nbGUuY29tLmhrLyJ9
482487
[NVIDIA Jetson Nano B01]: https://www.seeedstudio.com/blog/2020/01/16/new-revision-of-jetson-nano-dev-kit-now-supports-new-jetson-nano-module/
483488
[speech-enhancement-models]: https://github.com/k2-fsa/sherpa-onnx/releases/tag/speech-enhancement-models
489+
[source-separation-models]: https://github.com/k2-fsa/sherpa-onnx/releases/tag/source-separation-models
490+
[RK3588]: https://www.rock-chips.com/uploads/pdf/2022.8.26/192/RK3588%20Brief%20Datasheet.pdf
491+
[spleeter]: https://github.com/deezer/spleeter
492+
[UVR]: https://github.com/Anjok07/ultimatevocalremovergui
493+
[gtcrn]: https://github.com/Xiaobin-Rong/gtcrn

cxx-api-examples/parakeet-tdt-simulate-streaming-microphone-cxx-api.cc

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -136,8 +136,8 @@ int32_t main() {
136136
fprintf(stderr, "Use sample rate %f for mic\n", mic_sample_rate);
137137
mic_sample_rate = atof(sample_rate_str);
138138
}
139-
if(!mic.OpenDevice(device_index, mic_sample_rate, 1, RecordCallback,
140-
nullptr) == false) {
139+
if (!mic.OpenDevice(device_index, mic_sample_rate, 1, RecordCallback,
140+
nullptr) == false) {
141141
std::cerr << "Failed to open microphone device\n";
142142
return -1;
143143
}

cxx-api-examples/sense-voice-simulate-streaming-alsa-cxx-api.cc

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -24,7 +24,7 @@
2424
#include <iostream>
2525
#include <mutex> // NOLINT
2626
#include <queue>
27-
#include <thread>
27+
#include <thread> // NOLINT
2828
#include <vector>
2929

3030
#include "portaudio.h" // NOLINT

cxx-api-examples/sense-voice-simulate-streaming-microphone-cxx-api.cc

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -143,7 +143,7 @@ int32_t main() {
143143
lowpass_cutoff, lowpass_filter_width);
144144
}
145145
if (mic.OpenDevice(device_index, mic_sample_rate, 1, RecordCallback,
146-
nullptr) == false) {
146+
nullptr) == false) {
147147
std::cerr << "Failed to open microphone device\n";
148148
return -1;
149149
}

cxx-api-examples/sherpa-display.h

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1,3 +1,5 @@
1+
// cxx-api-examples/sherpa-display.cc
2+
// Copyright (c) 2025 Xiaomi Corporation
13
#pragma once
24

35
#include <stdlib.h>
@@ -6,6 +8,8 @@
68
#include <iomanip>
79
#include <sstream>
810
#include <string>
11+
#include <utility>
12+
#include <vector>
913

1014
namespace sherpa_onnx::cxx {
1115

sherpa-onnx/c-api/c-api.cc

Lines changed: 8 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -159,14 +159,15 @@ static sherpa_onnx::OnlineRecognizerConfig GetOnlineRecognizerConfig(
159159
recognizer_config.hr.rule_fsts = SHERPA_ONNX_OR(config->hr.rule_fsts, "");
160160

161161
if (config->model_config.debug) {
162+
#if __OHOS__
162163
auto str_vec = sherpa_onnx::SplitString(recognizer_config.ToString(), 128);
163164
for (const auto &s : str_vec) {
164-
#if __OHOS__
165165
SHERPA_ONNX_LOGE("%{public}s\n", s.c_str());
166-
#else
167166
SHERPA_ONNX_LOGE("%s\n", s.c_str());
168-
#endif
169167
}
168+
#else
169+
SHERPA_ONNX_LOGE("%s", recognizer_config.ToString().c_str());
170+
#endif
170171
}
171172

172173
return recognizer_config;
@@ -507,14 +508,15 @@ static sherpa_onnx::OfflineRecognizerConfig GetOfflineRecognizerConfig(
507508
recognizer_config.hr.rule_fsts = SHERPA_ONNX_OR(config->hr.rule_fsts, "");
508509

509510
if (config->model_config.debug) {
511+
#if __OHOS__
510512
auto str_vec = sherpa_onnx::SplitString(recognizer_config.ToString(), 128);
511513
for (const auto &s : str_vec) {
512-
#if __OHOS__
513514
SHERPA_ONNX_LOGE("%{public}s\n", s.c_str());
514-
#else
515515
SHERPA_ONNX_LOGE("%s\n", s.c_str());
516-
#endif
517516
}
517+
#else
518+
SHERPA_ONNX_LOGE("%s", recognizer_config.ToString().c_str());
519+
#endif
518520
}
519521

520522
return recognizer_config;

sherpa-onnx/csrc/CMakeLists.txt

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -55,6 +55,8 @@ set(sources
5555
offline-source-separation-model-config.cc
5656
offline-source-separation-spleeter-model-config.cc
5757
offline-source-separation-spleeter-model.cc
58+
offline-source-separation-uvr-model-config.cc
59+
offline-source-separation-uvr-model.cc
5860
offline-source-separation.cc
5961

6062
offline-stream.cc

sherpa-onnx/csrc/microphone.cc

Lines changed: 5 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -25,9 +25,7 @@ Microphone::~Microphone() {
2525
}
2626
}
2727

28-
int Microphone::GetDeviceCount() const {
29-
return Pa_GetDeviceCount();
30-
}
28+
int Microphone::GetDeviceCount() const { return Pa_GetDeviceCount(); }
3129

3230
int Microphone::GetDefaultInputDevice() const {
3331
return Pa_GetDefaultInputDevice();
@@ -43,7 +41,8 @@ void Microphone::PrintDevices(int device_index) const {
4341
}
4442
}
4543

46-
bool Microphone::OpenDevice(int index, int sample_rate, int channel, PaStreamCallback cb, void* userdata) {
44+
bool Microphone::OpenDevice(int index, int sample_rate, int channel,
45+
PaStreamCallback cb, void *userdata) {
4746
if (index < 0 || index >= Pa_GetDeviceCount()) {
4847
fprintf(stderr, "Invalid device index: %d\n", index);
4948
return false;
@@ -68,7 +67,8 @@ bool Microphone::OpenDevice(int index, int sample_rate, int channel, PaStreamCal
6867
param.suggestedLatency = info->defaultLowInputLatency;
6968
param.hostApiSpecificStreamInfo = nullptr;
7069

71-
PaError err = Pa_OpenStream(&stream, &param, nullptr, /* &outputParameters, */
70+
PaError err =
71+
Pa_OpenStream(&stream, &param, nullptr, /* &outputParameters, */
7272
sample_rate,
7373
0, // frames per buffer
7474
paClipOff, // we won't output out of range samples

0 commit comments

Comments
 (0)