There is no known (real) hardware with V and without the complete B
extension. B was indeed required in the RISC-V application profile from
2022, earlier than V. There should not be any relevant hardware in the
future either.
In practice, different R-V Vector optimisations in FFmpeg already depend on
every constituent of the B extension anyhow, so it would not work well.
This is pretty much the same as for lpc16, though it only improves half
as large prediction orders. With 128-bit vectors, this gives:
C V old V new
1 69.2 181.5 95.5
2 107.7 180.7 95.2
3 145.5 180.0 103.5
4 183.0 179.2 102.7
5 220.7 178.5 128.0
6 257.7 194.0 127.5
7 294.5 193.7 126.7
8 331.0 193.0 126.5
Larger prediction orders see no significant changes at that size.
This calculates the optimal vector type value at run-time based on the
hardware vector length and the FLAC LPC prediction order. In this
particular case, the additional computation is easily amortised over
the loop iterations:
T-Head C908:
C V before V after
1 48.0 214.7 95.2
2 64.7 214.2 94.7
3 79.7 213.5 94.5
4 96.2 196.5 94.2 #
5 111.0 195.7 118.5
6 127.0 211.2 102.0
7 143.7 194.2 101.5
8 175.7 193.2 101.2 #
9 176.2 224.2 126.0
10 191.5 192.0 125.5
11 224.5 191.2 124.7
12 223.0 190.2 124.2
13 239.2 189.5 123.7
14 253.7 188.7 139.5
15 286.2 188.0 122.7
16 284.0 187.0 122.5 #
17 300.2 186.5 186.5
18 314.0 185.5 185.7
19 329.7 184.7 185.0
20 343.0 184.2 184.2
21 358.7 199.2 183.7
22 371.7 182.7 182.7
23 387.5 181.7 182.0
24 400.7 181.0 181.2
25 431.5 180.2 196.5
26 443.7 195.5 196.0
27 459.0 178.7 196.2
28 470.7 177.7 194.2
29 470.0 177.0 193.5
30 481.2 176.2 176.5
31 496.2 175.5 175.7
32 507.2 174.7 191.0 #
# Power of two boundary.
With 128-bit vectors, improvements are expected for the first two
test cases only. For the other two, there is overhead but below noise.
Improvements should be better observable with prediction order of 8
and less, or on hardware with larger vector sizes.
In this case, the inner loop computing the scalar product can be reduced
to just one multiplication and one sum even with 128-bit vectors. The
result is a lot simpler, but also brings more modest performance gains:
flac_lpc_16_13_c: 15241.0
flac_lpc_16_13_rvv_i32: 11230.0
flac_lpc_16_16_c: 17884.0
flac_lpc_16_16_rvv_i32: 12125.7
flac_lpc_16_29_c: 27847.7
flac_lpc_16_29_rvv_i32: 10494.0
flac_lpc_16_32_c: 30051.5
flac_lpc_16_32_rvv_i32: 10355.0
The entire set of 32 coefficients and corresponding past 32 samples can
fit in a single vector (with LMUL=8) exactly, but... since widening
double the needed vector sizes, we still end up too short with 128-bit
vectors. This adds a very simple version for future 256+-bit hardware,
and for pred_orders values up to 16, and a bit more involved loop for
for 128-bit hardware with pred_orders between 17 and 32.
With 128-bit hardware, the benchmarks look like this:
flac_lpc_32_13_c: 30152.0
flac_lpc_32_13_rvv_i32: 10244.7
flac_lpc_32_16_c: 37314.2
flac_lpc_32_16_rvv_i32: 10126.2
flac_lpc_32_29_c: 61910.0
flac_lpc_32_29_rvv_i32: 14495.2
flac_lpc_32_32_c: 68204.0
flac_lpc_32_32_rvv_i32: 13273.7