ci: enforce strict Clippy across media targets

This commit is contained in:
DeFiDude 2026-08-06 18:49:06 -06:00
parent a381eab55c
commit 47827c9e2a
11 changed files with 139 additions and 77 deletions

View file

@ -42,9 +42,9 @@ jobs:
run: sudo apt-get update && sudo apt-get install -y libudev-dev libdbus-1-dev pkg-config libopus0 libogg0
- run: cargo fmt --all -- --check
working-directory: rsLXST
- run: cargo clippy --workspace -- -D warnings
- run: cargo clippy --workspace --all-targets --all-features --locked -- -D warnings
working-directory: rsLXST
- run: cargo doc --workspace --no-deps
- run: cargo doc --workspace --no-deps --locked
working-directory: rsLXST
env:
RUSTDOCFLAGS: "-D warnings"
@ -90,21 +90,13 @@ jobs:
run: brew install opus libogg
- name: Install Python interop deps
run: python -m pip install --upgrade pip && python -m pip install numpy cryptography pyserial cffi "audioop-lts; python_version >= '3.13'"
- run: cargo test --workspace
- run: cargo test --workspace --locked
working-directory: rsLXST
mobile-check:
name: Check (${{ matrix.target }})
runs-on: ${{ matrix.os }}
msrv:
name: Rust 1.85 MSRV
runs-on: ubuntu-latest
timeout-minutes: 30
strategy:
fail-fast: false
matrix:
include:
- os: ubuntu-latest
target: aarch64-linux-android
- os: macos-latest
target: aarch64-apple-ios
steps:
- uses: actions/checkout@v5
with:
@ -114,9 +106,61 @@ jobs:
repository: ${{ github.repository_owner }}/rsReticulum
ref: main
path: rsReticulum
- uses: dtolnay/rust-toolchain@stable
- uses: actions/checkout@v5
with:
repository: markqvist/LXST
path: upstream/LXST
- uses: actions/checkout@v5
with:
repository: markqvist/Reticulum
path: upstream/Reticulum
- uses: dtolnay/rust-toolchain@1.85.0
with:
components: clippy
- uses: Swatinem/rust-cache@v2
with:
workspaces: rsLXST -> target
cache-bin: false
- name: Install Linux system deps
run: sudo apt-get update && sudo apt-get install -y libudev-dev libdbus-1-dev pkg-config libopus0 libogg0
- name: Clippy (all targets and features)
run: cargo clippy --workspace --all-targets --all-features --locked -- -D warnings
working-directory: rsLXST
mobile-check:
name: Clippy (${{ matrix.target }}, ${{ matrix.toolchain }})
runs-on: ${{ matrix.os }}
timeout-minutes: 30
strategy:
fail-fast: false
matrix:
include:
- os: ubuntu-latest
target: aarch64-linux-android
toolchain: stable
- os: macos-latest
target: aarch64-apple-ios
toolchain: stable
- os: ubuntu-latest
target: aarch64-linux-android
toolchain: 1.85.0
- os: macos-latest
target: aarch64-apple-ios
toolchain: 1.85.0
steps:
- uses: actions/checkout@v5
with:
path: rsLXST
- uses: actions/checkout@v5
with:
repository: ${{ github.repository_owner }}/rsReticulum
ref: main
path: rsReticulum
- uses: dtolnay/rust-toolchain@master
with:
toolchain: ${{ matrix.toolchain }}
targets: ${{ matrix.target }}
components: clippy
- uses: Swatinem/rust-cache@v2
with:
workspaces: rsLXST -> target
@ -127,16 +171,16 @@ jobs:
with:
ndk-version: r27d
add-to-path: false
- name: Check Android
- name: Clippy Android
if: matrix.target == 'aarch64-linux-android'
env:
ANDROID_NDK_HOME: ${{ steps.setup-ndk.outputs.ndk-path }}
AR_aarch64_linux_android: ${{ steps.setup-ndk.outputs.ndk-path }}/toolchains/llvm/prebuilt/linux-x86_64/bin/llvm-ar
CC_aarch64_linux_android: ${{ steps.setup-ndk.outputs.ndk-path }}/toolchains/llvm/prebuilt/linux-x86_64/bin/aarch64-linux-android24-clang
CXX_aarch64_linux_android: ${{ steps.setup-ndk.outputs.ndk-path }}/toolchains/llvm/prebuilt/linux-x86_64/bin/aarch64-linux-android24-clang++
run: cargo check --workspace --target ${{ matrix.target }}
run: cargo clippy --workspace --all-targets --all-features --target ${{ matrix.target }} --locked -- -D warnings
working-directory: rsLXST
- name: Check iOS
- name: Clippy iOS
if: matrix.target == 'aarch64-apple-ios'
run: cargo check --workspace --target ${{ matrix.target }}
run: cargo clippy --workspace --all-targets --all-features --target ${{ matrix.target }} --locked -- -D warnings
working-directory: rsLXST

2
clippy.toml Normal file
View file

@ -0,0 +1,2 @@
# Keep Clippy suggestions aligned with the public MSRV in Cargo.toml.
msrv = "1.85"

View file

@ -1549,11 +1549,11 @@ impl TelephonyService {
return true;
};
if !frames.is_empty()
&& let Err(err) = self.send_opus_frames(profile, frames).await
{
self.media.opus_transmit_stream = None;
return emit_service_error(self.event_tx.clone(), err).await;
if !frames.is_empty() {
if let Err(err) = self.send_opus_frames(profile, frames).await {
self.media.opus_transmit_stream = None;
return emit_service_error(self.event_tx.clone(), err).await;
}
}
if source_closed {
@ -1725,10 +1725,10 @@ impl TelephonyService {
return false;
}
}
if let Some(event) = media_received
&& !emit_service_event(self.event_tx.clone(), event).await
{
return false;
if let Some(event) = media_received {
if !emit_service_event(self.event_tx.clone(), event).await {
return false;
}
}
for event in opus_received_events {
if !emit_service_event(self.event_tx.clone(), event).await {
@ -1839,12 +1839,14 @@ impl TelephonyService {
dropped,
});
}
if sink_closed && let Some(stream) = self.media.opus_receive_stream.take() {
events.push(TelephonyServiceEvent::OpusReceiveStreamStopped {
link_id: stream.link_id,
profile: stream.profile,
reason: OpusReceiveStreamStopReason::SinkClosed,
});
if sink_closed {
if let Some(stream) = self.media.opus_receive_stream.take() {
events.push(TelephonyServiceEvent::OpusReceiveStreamStopped {
link_id: stream.link_id,
profile: stream.profile,
reason: OpusReceiveStreamStopReason::SinkClosed,
});
}
}
events
}

View file

@ -55,7 +55,7 @@ fn kf_factor(n_orig: usize, factors: &mut [i16; 2 * MAXFACTORS]) -> bool {
let mut stages = 0;
loop {
while !n.is_multiple_of(p as usize) {
while n % p as usize != 0 {
p = match p {
4 => 2,
2 => 3,

View file

@ -817,7 +817,7 @@ impl OpusDecoder {
if data.len() < 2 {
return Err("Code 2 packet too short for 2-byte length");
}
(((data[0] & 0x7F) as usize) << 8 | data[1] as usize, 2)
((((data[0] & 0x7F) as usize) << 8) | data[1] as usize, 2)
} else {
(data[0] as usize, 1)
};
@ -889,7 +889,7 @@ impl OpusDecoder {
return Err("Code 3: short frame length");
}
(
((input[payload_ptr] & 0x7F) as usize) << 8
(((input[payload_ptr] & 0x7F) as usize) << 8)
| input[payload_ptr + 1] as usize,
2,
)

View file

@ -140,7 +140,7 @@ const LOG_N_400: [i16; 21] = [
];
const WINDOW_120: [f32; 120] = [
6.728_696_6e-05,
6.728_696_5e-5,
0.000_605_513_5,
0.001_681_597,
0.003_294_796_2,

View file

@ -22,10 +22,14 @@ pub fn silk_decode_core(
for i in 0..ps_dec.frame_length as usize {
rand_seed = silk_rand(rand_seed);
ps_dec.exc_q14[i] = (pulses[i] as i32) << 14;
if ps_dec.exc_q14[i] > 0 {
ps_dec.exc_q14[i] -= QUANT_LEVEL_ADJUST_Q10 << 4;
} else if ps_dec.exc_q14[i] < 0 {
ps_dec.exc_q14[i] += QUANT_LEVEL_ADJUST_Q10 << 4;
match ps_dec.exc_q14[i].cmp(&0) {
std::cmp::Ordering::Greater => {
ps_dec.exc_q14[i] -= QUANT_LEVEL_ADJUST_Q10 << 4;
}
std::cmp::Ordering::Less => {
ps_dec.exc_q14[i] += QUANT_LEVEL_ADJUST_Q10 << 4;
}
std::cmp::Ordering::Equal => {}
}
ps_dec.exc_q14[i] += offset_q10 << 4;
if rand_seed < 0 {

View file

@ -9,14 +9,16 @@ pub fn silk_lin2log(in_lin: i32) -> i32 {
let rot = 24 - lz;
let x = in_lin as u32;
let frac_q7 = if rot == 0 {
x & 0x7f
} else if rot < 0 {
let m = (-rot) as u32;
x.rotate_left(m) & 0x7f
} else {
let r = rot as u32;
x.rotate_right(r) & 0x7f
let frac_q7 = match rot.cmp(&0) {
std::cmp::Ordering::Equal => x & 0x7f,
std::cmp::Ordering::Less => {
let m = (-rot) as u32;
x.rotate_left(m) & 0x7f
}
std::cmp::Ordering::Greater => {
let r = rot as u32;
x.rotate_right(r) & 0x7f
}
} as i32;
let res = silk_smlawb(frac_q7, silk_mul(frac_q7, 128 - frac_q7), 179);

View file

@ -42,17 +42,21 @@ pub fn silk_find_ltp_fix(
);
extra_shifts = xx_shifts - xx_shifts_matrix;
if extra_shifts > 0 {
xx_shifts_vector = xx_shifts;
for i in 0..(LTP_ORDER * LTP_ORDER) {
xxlp_ptr[i] = silk_rshift32(xxlp_ptr[i], extra_shifts);
match extra_shifts.cmp(&0) {
std::cmp::Ordering::Greater => {
xx_shifts_vector = xx_shifts;
for item in xxlp_ptr.iter_mut().take(LTP_ORDER * LTP_ORDER) {
*item = silk_rshift32(*item, extra_shifts);
}
nrg = silk_rshift32(nrg, extra_shifts);
}
std::cmp::Ordering::Less => {
xx_shifts_vector = xx_shifts_matrix;
xx = silk_rshift32(xx, -extra_shifts);
}
std::cmp::Ordering::Equal => {
xx_shifts_vector = xx_shifts;
}
nrg = silk_rshift32(nrg, extra_shifts);
} else if extra_shifts < 0 {
xx_shifts_vector = xx_shifts_matrix;
xx = silk_rshift32(xx, -extra_shifts);
} else {
xx_shifts_vector = xx_shifts;
}
let xxlp_vec_ptr = &mut xxltp_q17_vector[k * LTP_ORDER..];

View file

@ -15,10 +15,10 @@ fn silk_nlsf_residual_dequant(
for i in (0..order as usize).rev() {
let pred_q10 = silk_smulbb(out_q10, pred_coef_q8[i] as i32) >> 8;
let mut current_out_q10 = (indices[i] as i32) << 10;
if current_out_q10 > 0 {
current_out_q10 -= NLSF_QUANT_LEVEL_ADJ;
} else if current_out_q10 < 0 {
current_out_q10 += NLSF_QUANT_LEVEL_ADJ;
match current_out_q10.cmp(&0) {
std::cmp::Ordering::Greater => current_out_q10 -= NLSF_QUANT_LEVEL_ADJ,
std::cmp::Ordering::Less => current_out_q10 += NLSF_QUANT_LEVEL_ADJ,
std::cmp::Ordering::Equal => {}
}
out_q10 = silk_smlawb(pred_q10, current_out_q10, quant_step_size_q16);

View file

@ -840,21 +840,25 @@ pub fn silk_schur(rc_q15: &mut [i16], c: &[i32], order: usize) -> i32 {
let lz = c[0].leading_zeros() as i32;
if lz < 2 {
for i in 0..=order {
c_inner[i][0] = c[i] >> 1;
c_inner[i][1] = c[i] >> 1;
match lz.cmp(&2) {
std::cmp::Ordering::Less => {
for i in 0..=order {
c_inner[i][0] = c[i] >> 1;
c_inner[i][1] = c[i] >> 1;
}
}
} else if lz > 2 {
let lz_adj = lz - 2;
for i in 0..=order {
c_inner[i][0] = c[i] << lz_adj;
c_inner[i][1] = c[i] << lz_adj;
std::cmp::Ordering::Greater => {
let lz_adj = lz - 2;
for i in 0..=order {
c_inner[i][0] = c[i] << lz_adj;
c_inner[i][1] = c[i] << lz_adj;
}
}
} else {
for i in 0..=order {
c_inner[i][0] = c[i];
c_inner[i][1] = c[i];
std::cmp::Ordering::Equal => {
for i in 0..=order {
c_inner[i][0] = c[i];
c_inner[i][1] = c[i];
}
}
}