mirror of
https://gitlab.freedesktop.org/pipewire/pipewire.git
synced 2025-11-01 22:58:50 -04:00
audioconvert: pass state to functions
Pass some state to convert and channelmix functions. This makes it possible to select per channel optimized convert functions but also makes it possible to implement noise shaping later. Pass the channelmix matrix and volume in the state. Handle specialized 2 channel s16 -> f32 conversion
This commit is contained in:
parent
d47353c0e6
commit
d8e399dee9
17 changed files with 952 additions and 685 deletions
|
|
@ -63,6 +63,9 @@ static void run_test1(const char *name, const char *impl, bool in_packed, bool o
|
||||||
void *op[n_channels];
|
void *op[n_channels];
|
||||||
struct timespec ts;
|
struct timespec ts;
|
||||||
uint64_t count, t1, t2;
|
uint64_t count, t1, t2;
|
||||||
|
struct convert conv;
|
||||||
|
|
||||||
|
conv.n_channels = n_channels;
|
||||||
|
|
||||||
for (j = 0; j < n_channels; j++) {
|
for (j = 0; j < n_channels; j++) {
|
||||||
ip[j] = &samp_in[j * n_samples * 4];
|
ip[j] = &samp_in[j * n_samples * 4];
|
||||||
|
|
@ -74,7 +77,7 @@ static void run_test1(const char *name, const char *impl, bool in_packed, bool o
|
||||||
|
|
||||||
count = 0;
|
count = 0;
|
||||||
for (i = 0; i < MAX_COUNT; i++) {
|
for (i = 0; i < MAX_COUNT; i++) {
|
||||||
func(NULL, op, ip, n_channels, n_samples);
|
func(&conv, op, ip, n_samples);
|
||||||
count++;
|
count++;
|
||||||
}
|
}
|
||||||
clock_gettime(CLOCK_MONOTONIC, &ts);
|
clock_gettime(CLOCK_MONOTONIC, &ts);
|
||||||
|
|
@ -223,8 +226,6 @@ int main(int argc, char *argv[])
|
||||||
{
|
{
|
||||||
uint32_t i;
|
uint32_t i;
|
||||||
|
|
||||||
find_conv_info(0, 0, 0);
|
|
||||||
|
|
||||||
test_f32_u8();
|
test_f32_u8();
|
||||||
test_u8_f32();
|
test_u8_f32();
|
||||||
test_f32_s16();
|
test_f32_s16();
|
||||||
|
|
|
||||||
|
|
@ -25,13 +25,13 @@
|
||||||
#include "channelmix-ops.h"
|
#include "channelmix-ops.h"
|
||||||
|
|
||||||
void
|
void
|
||||||
channelmix_copy_c(void *data, int n_dst, void * SPA_RESTRICT dst[n_dst],
|
channelmix_copy_c(struct channelmix *mix, uint32_t n_dst, void * SPA_RESTRICT dst[n_dst],
|
||||||
int n_src, const void * SPA_RESTRICT src[n_src],
|
uint32_t n_src, const void * SPA_RESTRICT src[n_src], uint32_t n_samples)
|
||||||
const void *matrix, float v, int n_samples)
|
|
||||||
{
|
{
|
||||||
int i, n;
|
uint32_t i, n;
|
||||||
float **d = (float **)dst;
|
float **d = (float **)dst;
|
||||||
const float **s = (const float **)src;
|
const float **s = (const float **)src;
|
||||||
|
float v = mix->volume;
|
||||||
|
|
||||||
if (v <= VOLUME_MIN) {
|
if (v <= VOLUME_MIN) {
|
||||||
for (i = 0; i < n_dst; i++)
|
for (i = 0; i < n_dst; i++)
|
||||||
|
|
@ -51,14 +51,14 @@ channelmix_copy_c(void *data, int n_dst, void * SPA_RESTRICT dst[n_dst],
|
||||||
#define _M(ch) (1UL << SPA_AUDIO_CHANNEL_ ## ch)
|
#define _M(ch) (1UL << SPA_AUDIO_CHANNEL_ ## ch)
|
||||||
|
|
||||||
void
|
void
|
||||||
channelmix_f32_n_m_c(void *data, int n_dst, void * SPA_RESTRICT dst[n_dst],
|
channelmix_f32_n_m_c(struct channelmix *mix, uint32_t n_dst, void * SPA_RESTRICT dst[n_dst],
|
||||||
int n_src, const void * SPA_RESTRICT src[n_src],
|
uint32_t n_src, const void * SPA_RESTRICT src[n_src], uint32_t n_samples)
|
||||||
const void *matrix, float v, int n_samples)
|
|
||||||
{
|
{
|
||||||
int i, j, n;
|
uint32_t i, j, n;
|
||||||
float **d = (float **) dst;
|
float **d = (float **) dst;
|
||||||
const float **s = (const float **) src;
|
const float **s = (const float **) src;
|
||||||
const float *m = matrix;
|
const float *m = mix->matrix;
|
||||||
|
float v = mix->volume;
|
||||||
|
|
||||||
for (n = 0; n < n_samples; n++) {
|
for (n = 0; n < n_samples; n++) {
|
||||||
for (i = 0; i < n_dst; i++) {
|
for (i = 0; i < n_dst; i++) {
|
||||||
|
|
@ -74,13 +74,13 @@ channelmix_f32_n_m_c(void *data, int n_dst, void * SPA_RESTRICT dst[n_dst],
|
||||||
#define MASK_STEREO _M(FL)|_M(FR)|_M(UNKNOWN)
|
#define MASK_STEREO _M(FL)|_M(FR)|_M(UNKNOWN)
|
||||||
|
|
||||||
void
|
void
|
||||||
channelmix_f32_1_2_c(void *data, int n_dst, void * SPA_RESTRICT dst[n_dst],
|
channelmix_f32_1_2_c(struct channelmix *mix, uint32_t n_dst, void * SPA_RESTRICT dst[n_dst],
|
||||||
int n_src, const void * SPA_RESTRICT src[n_src],
|
uint32_t n_src, const void * SPA_RESTRICT src[n_src], uint32_t n_samples)
|
||||||
const void *matrix, float v, int n_samples)
|
|
||||||
{
|
{
|
||||||
int n;
|
uint32_t n;
|
||||||
float **d = (float **)dst;
|
float **d = (float **)dst;
|
||||||
const float **s = (const float **)src;
|
const float **s = (const float **)src;
|
||||||
|
float v = mix->volume;
|
||||||
|
|
||||||
if (v <= VOLUME_MIN) {
|
if (v <= VOLUME_MIN) {
|
||||||
memset(d[0], 0, n_samples * sizeof(float));
|
memset(d[0], 0, n_samples * sizeof(float));
|
||||||
|
|
@ -97,13 +97,13 @@ channelmix_f32_1_2_c(void *data, int n_dst, void * SPA_RESTRICT dst[n_dst],
|
||||||
}
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
channelmix_f32_2_1_c(void *data, int n_dst, void * SPA_RESTRICT dst[n_dst],
|
channelmix_f32_2_1_c(struct channelmix *mix, uint32_t n_dst, void * SPA_RESTRICT dst[n_dst],
|
||||||
int n_src, const void * SPA_RESTRICT src[n_src],
|
uint32_t n_src, const void * SPA_RESTRICT src[n_src], uint32_t n_samples)
|
||||||
const void *matrix, float v, int n_samples)
|
|
||||||
{
|
{
|
||||||
int n;
|
uint32_t n;
|
||||||
float **d = (float **)dst;
|
float **d = (float **)dst;
|
||||||
const float **s = (const float **)src;
|
const float **s = (const float **)src;
|
||||||
|
float v = mix->volume;
|
||||||
|
|
||||||
if (v <= VOLUME_MIN) {
|
if (v <= VOLUME_MIN) {
|
||||||
memset(d[0], 0, n_samples * sizeof(float));
|
memset(d[0], 0, n_samples * sizeof(float));
|
||||||
|
|
@ -116,13 +116,13 @@ channelmix_f32_2_1_c(void *data, int n_dst, void * SPA_RESTRICT dst[n_dst],
|
||||||
}
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
channelmix_f32_4_1_c(void *data, int n_dst, void * SPA_RESTRICT dst[n_dst],
|
channelmix_f32_4_1_c(struct channelmix *mix, uint32_t n_dst, void * SPA_RESTRICT dst[n_dst],
|
||||||
int n_src, const void * SPA_RESTRICT src[n_src],
|
uint32_t n_src, const void * SPA_RESTRICT src[n_src], uint32_t n_samples)
|
||||||
const void *matrix, float v, int n_samples)
|
|
||||||
{
|
{
|
||||||
int n;
|
uint32_t n;
|
||||||
float **d = (float **)dst;
|
float **d = (float **)dst;
|
||||||
const float **s = (const float **)src;
|
const float **s = (const float **)src;
|
||||||
|
float v = mix->volume;
|
||||||
|
|
||||||
if (v <= VOLUME_MIN) {
|
if (v <= VOLUME_MIN) {
|
||||||
memset(d[0], 0, n_samples * sizeof(float));
|
memset(d[0], 0, n_samples * sizeof(float));
|
||||||
|
|
@ -135,13 +135,13 @@ channelmix_f32_4_1_c(void *data, int n_dst, void * SPA_RESTRICT dst[n_dst],
|
||||||
}
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
channelmix_f32_3p1_1_c(void *data, int n_dst, void * SPA_RESTRICT dst[n_dst],
|
channelmix_f32_3p1_1_c(struct channelmix *mix, uint32_t n_dst, void * SPA_RESTRICT dst[n_dst],
|
||||||
int n_src, const void * SPA_RESTRICT src[n_src],
|
uint32_t n_src, const void * SPA_RESTRICT src[n_src], uint32_t n_samples)
|
||||||
const void *matrix, float v, int n_samples)
|
|
||||||
{
|
{
|
||||||
int n;
|
uint32_t n;
|
||||||
float **d = (float **)dst;
|
float **d = (float **)dst;
|
||||||
const float **s = (const float **)src;
|
const float **s = (const float **)src;
|
||||||
|
float v = mix->volume;
|
||||||
|
|
||||||
if (v <= VOLUME_MIN) {
|
if (v <= VOLUME_MIN) {
|
||||||
memset(d[0], 0, n_samples * sizeof(float));
|
memset(d[0], 0, n_samples * sizeof(float));
|
||||||
|
|
@ -157,13 +157,13 @@ channelmix_f32_3p1_1_c(void *data, int n_dst, void * SPA_RESTRICT dst[n_dst],
|
||||||
#define MASK_QUAD _M(FL)|_M(FR)|_M(RL)|_M(RR)|_M(UNKNOWN)
|
#define MASK_QUAD _M(FL)|_M(FR)|_M(RL)|_M(RR)|_M(UNKNOWN)
|
||||||
|
|
||||||
void
|
void
|
||||||
channelmix_f32_2_4_c(void *data, int n_dst, void * SPA_RESTRICT dst[n_dst],
|
channelmix_f32_2_4_c(struct channelmix *mix, uint32_t n_dst, void * SPA_RESTRICT dst[n_dst],
|
||||||
int n_src, const void * SPA_RESTRICT src[n_src],
|
uint32_t n_src, const void * SPA_RESTRICT src[n_src], uint32_t n_samples)
|
||||||
const void *matrix, float v, int n_samples)
|
|
||||||
{
|
{
|
||||||
int i, n;
|
uint32_t i, n;
|
||||||
float **d = (float **)dst;
|
float **d = (float **)dst;
|
||||||
const float **s = (const float **)src;
|
const float **s = (const float **)src;
|
||||||
|
float v = mix->volume;
|
||||||
|
|
||||||
if (v <= VOLUME_MIN) {
|
if (v <= VOLUME_MIN) {
|
||||||
for (i = 0; i < n_dst; i++)
|
for (i = 0; i < n_dst; i++)
|
||||||
|
|
@ -185,13 +185,13 @@ channelmix_f32_2_4_c(void *data, int n_dst, void * SPA_RESTRICT dst[n_dst],
|
||||||
|
|
||||||
#define MASK_3_1 _M(FL)|_M(FR)|_M(FC)|_M(LFE)
|
#define MASK_3_1 _M(FL)|_M(FR)|_M(FC)|_M(LFE)
|
||||||
void
|
void
|
||||||
channelmix_f32_2_3p1_c(void *data, int n_dst, void * SPA_RESTRICT dst[n_dst],
|
channelmix_f32_2_3p1_c(struct channelmix *mix, uint32_t n_dst, void * SPA_RESTRICT dst[n_dst],
|
||||||
int n_src, const void * SPA_RESTRICT src[n_src],
|
uint32_t n_src, const void * SPA_RESTRICT src[n_src], uint32_t n_samples)
|
||||||
const void *matrix, float v, int n_samples)
|
|
||||||
{
|
{
|
||||||
int i, n;
|
uint32_t i, n;
|
||||||
float **d = (float **)dst;
|
float **d = (float **)dst;
|
||||||
const float **s = (const float **)src;
|
const float **s = (const float **)src;
|
||||||
|
float v = mix->volume;
|
||||||
|
|
||||||
if (v <= VOLUME_MIN) {
|
if (v <= VOLUME_MIN) {
|
||||||
for (i = 0; i < n_dst; i++)
|
for (i = 0; i < n_dst; i++)
|
||||||
|
|
@ -218,13 +218,13 @@ channelmix_f32_2_3p1_c(void *data, int n_dst, void * SPA_RESTRICT dst[n_dst],
|
||||||
|
|
||||||
#define MASK_5_1 _M(FL)|_M(FR)|_M(FC)|_M(LFE)|_M(SL)|_M(SR)|_M(RL)|_M(RR)
|
#define MASK_5_1 _M(FL)|_M(FR)|_M(FC)|_M(LFE)|_M(SL)|_M(SR)|_M(RL)|_M(RR)
|
||||||
void
|
void
|
||||||
channelmix_f32_2_5p1_c(void *data, int n_dst, void * SPA_RESTRICT dst[n_dst],
|
channelmix_f32_2_5p1_c(struct channelmix *mix, uint32_t n_dst, void * SPA_RESTRICT dst[n_dst],
|
||||||
int n_src, const void * SPA_RESTRICT src[n_src],
|
uint32_t n_src, const void * SPA_RESTRICT src[n_src], uint32_t n_samples)
|
||||||
const void *matrix, float v, int n_samples)
|
|
||||||
{
|
{
|
||||||
int i, n;
|
uint32_t i, n;
|
||||||
float **d = (float **)dst;
|
float **d = (float **)dst;
|
||||||
const float **s = (const float **)src;
|
const float **s = (const float **)src;
|
||||||
|
float v = mix->volume;
|
||||||
|
|
||||||
if (v <= VOLUME_MIN) {
|
if (v <= VOLUME_MIN) {
|
||||||
for (i = 0; i < n_dst; i++)
|
for (i = 0; i < n_dst; i++)
|
||||||
|
|
@ -251,17 +251,17 @@ channelmix_f32_2_5p1_c(void *data, int n_dst, void * SPA_RESTRICT dst[n_dst],
|
||||||
|
|
||||||
/* FL+FR+FC+LFE+SL+SR -> FL+FR */
|
/* FL+FR+FC+LFE+SL+SR -> FL+FR */
|
||||||
void
|
void
|
||||||
channelmix_f32_5p1_2_c(void *data, int n_dst, void * SPA_RESTRICT dst[n_dst],
|
channelmix_f32_5p1_2_c(struct channelmix *mix, uint32_t n_dst, void * SPA_RESTRICT dst[n_dst],
|
||||||
int n_src, const void * SPA_RESTRICT src[n_src],
|
uint32_t n_src, const void * SPA_RESTRICT src[n_src], uint32_t n_samples)
|
||||||
const void *matrix, float v, int n_samples)
|
|
||||||
{
|
{
|
||||||
int n;
|
uint32_t n;
|
||||||
float **d = (float **) dst;
|
float **d = (float **) dst;
|
||||||
const float **s = (const float **) src;
|
const float **s = (const float **) src;
|
||||||
const float *m = matrix;
|
const float *m = mix->matrix;
|
||||||
const float clev = m[2];
|
const float clev = m[2];
|
||||||
const float llev = m[3];
|
const float llev = m[3];
|
||||||
const float slev = m[4];
|
const float slev = m[4];
|
||||||
|
float v = mix->volume;
|
||||||
|
|
||||||
if (v <= VOLUME_MIN) {
|
if (v <= VOLUME_MIN) {
|
||||||
memset(d[0], 0, n_samples * sizeof(float));
|
memset(d[0], 0, n_samples * sizeof(float));
|
||||||
|
|
@ -285,13 +285,13 @@ channelmix_f32_5p1_2_c(void *data, int n_dst, void * SPA_RESTRICT dst[n_dst],
|
||||||
|
|
||||||
/* FL+FR+FC+LFE+SL+SR -> FL+FR+FC+LFE*/
|
/* FL+FR+FC+LFE+SL+SR -> FL+FR+FC+LFE*/
|
||||||
void
|
void
|
||||||
channelmix_f32_5p1_3p1_c(void *data, int n_dst, void * SPA_RESTRICT dst[n_dst],
|
channelmix_f32_5p1_3p1_c(struct channelmix *mix, uint32_t n_dst, void * SPA_RESTRICT dst[n_dst],
|
||||||
int n_src, const void * SPA_RESTRICT src[n_src],
|
uint32_t n_src, const void * SPA_RESTRICT src[n_src], uint32_t n_samples)
|
||||||
const void *matrix, float v, int n_samples)
|
|
||||||
{
|
{
|
||||||
int i, n;
|
uint32_t i, n;
|
||||||
float **d = (float **) dst;
|
float **d = (float **) dst;
|
||||||
const float **s = (const float **) src;
|
const float **s = (const float **) src;
|
||||||
|
float v = mix->volume;
|
||||||
|
|
||||||
if (v <= VOLUME_MIN) {
|
if (v <= VOLUME_MIN) {
|
||||||
for (i = 0; i < n_dst; i++)
|
for (i = 0; i < n_dst; i++)
|
||||||
|
|
@ -310,16 +310,16 @@ channelmix_f32_5p1_3p1_c(void *data, int n_dst, void * SPA_RESTRICT dst[n_dst],
|
||||||
|
|
||||||
/* FL+FR+FC+LFE+SL+SR -> FL+FR+RL+RR*/
|
/* FL+FR+FC+LFE+SL+SR -> FL+FR+RL+RR*/
|
||||||
void
|
void
|
||||||
channelmix_f32_5p1_4_c(void *data, int n_dst, void * SPA_RESTRICT dst[n_dst],
|
channelmix_f32_5p1_4_c(struct channelmix *mix, uint32_t n_dst, void * SPA_RESTRICT dst[n_dst],
|
||||||
int n_src, const void * SPA_RESTRICT src[n_src],
|
uint32_t n_src, const void * SPA_RESTRICT src[n_src], uint32_t n_samples)
|
||||||
const void *matrix, float v, int n_samples)
|
|
||||||
{
|
{
|
||||||
int i, n;
|
uint32_t i, n;
|
||||||
float **d = (float **) dst;
|
float **d = (float **) dst;
|
||||||
const float **s = (const float **) src;
|
const float **s = (const float **) src;
|
||||||
const float *m = matrix;
|
const float *m = mix->matrix;
|
||||||
const float clev = m[2];
|
const float clev = m[2];
|
||||||
const float llev = m[3];
|
const float llev = m[3];
|
||||||
|
float v = mix->volume;
|
||||||
|
|
||||||
if (v <= VOLUME_MIN) {
|
if (v <= VOLUME_MIN) {
|
||||||
for (i = 0; i < n_dst; i++)
|
for (i = 0; i < n_dst; i++)
|
||||||
|
|
@ -349,17 +349,17 @@ channelmix_f32_5p1_4_c(void *data, int n_dst, void * SPA_RESTRICT dst[n_dst],
|
||||||
|
|
||||||
/* FL+FR+FC+LFE+SL+SR+RL+RR -> FL+FR */
|
/* FL+FR+FC+LFE+SL+SR+RL+RR -> FL+FR */
|
||||||
void
|
void
|
||||||
channelmix_f32_7p1_2_c(void *data, int n_dst, void * SPA_RESTRICT dst[n_dst],
|
channelmix_f32_7p1_2_c(struct channelmix *mix, uint32_t n_dst, void * SPA_RESTRICT dst[n_dst],
|
||||||
int n_src, const void * SPA_RESTRICT src[n_src],
|
uint32_t n_src, const void * SPA_RESTRICT src[n_src], uint32_t n_samples)
|
||||||
const void *matrix, float v, int n_samples)
|
|
||||||
{
|
{
|
||||||
int n;
|
uint32_t n;
|
||||||
float **d = (float **) dst;
|
float **d = (float **) dst;
|
||||||
const float **s = (const float **) src;
|
const float **s = (const float **) src;
|
||||||
const float *m = matrix;
|
const float *m = mix->matrix;
|
||||||
const float clev = m[2];
|
const float clev = m[2];
|
||||||
const float llev = m[3];
|
const float llev = m[3];
|
||||||
const float slev = m[4];
|
const float slev = m[4];
|
||||||
|
float v = mix->volume;
|
||||||
|
|
||||||
if (v <= VOLUME_MIN) {
|
if (v <= VOLUME_MIN) {
|
||||||
memset(d[0], 0, n_samples * sizeof(float));
|
memset(d[0], 0, n_samples * sizeof(float));
|
||||||
|
|
@ -383,13 +383,13 @@ channelmix_f32_7p1_2_c(void *data, int n_dst, void * SPA_RESTRICT dst[n_dst],
|
||||||
|
|
||||||
/* FL+FR+FC+LFE+SL+SR+RL+RR -> FL+FR+FC+LFE*/
|
/* FL+FR+FC+LFE+SL+SR+RL+RR -> FL+FR+FC+LFE*/
|
||||||
void
|
void
|
||||||
channelmix_f32_7p1_3p1_c(void *data, int n_dst, void * SPA_RESTRICT dst[n_dst],
|
channelmix_f32_7p1_3p1_c(struct channelmix *mix, uint32_t n_dst, void * SPA_RESTRICT dst[n_dst],
|
||||||
int n_src, const void * SPA_RESTRICT src[n_src],
|
uint32_t n_src, const void * SPA_RESTRICT src[n_src], uint32_t n_samples)
|
||||||
const void *matrix, float v, int n_samples)
|
|
||||||
{
|
{
|
||||||
int i, n;
|
uint32_t i, n;
|
||||||
float **d = (float **) dst;
|
float **d = (float **) dst;
|
||||||
const float **s = (const float **) src;
|
const float **s = (const float **) src;
|
||||||
|
float v = mix->volume;
|
||||||
|
|
||||||
if (v <= VOLUME_MIN) {
|
if (v <= VOLUME_MIN) {
|
||||||
for (i = 0; i < n_dst; i++)
|
for (i = 0; i < n_dst; i++)
|
||||||
|
|
@ -408,17 +408,17 @@ channelmix_f32_7p1_3p1_c(void *data, int n_dst, void * SPA_RESTRICT dst[n_dst],
|
||||||
|
|
||||||
/* FL+FR+FC+LFE+SL+SR+RL+RR -> FL+FR+RL+RR*/
|
/* FL+FR+FC+LFE+SL+SR+RL+RR -> FL+FR+RL+RR*/
|
||||||
void
|
void
|
||||||
channelmix_f32_7p1_4_c(void *data, int n_dst, void * SPA_RESTRICT dst[n_dst],
|
channelmix_f32_7p1_4_c(struct channelmix *mix, uint32_t n_dst, void * SPA_RESTRICT dst[n_dst],
|
||||||
int n_src, const void * SPA_RESTRICT src[n_src],
|
uint32_t n_src, const void * SPA_RESTRICT src[n_src], uint32_t n_samples)
|
||||||
const void *matrix, float v, int n_samples)
|
|
||||||
{
|
{
|
||||||
int i, n;
|
uint32_t i, n;
|
||||||
float **d = (float **) dst;
|
float **d = (float **) dst;
|
||||||
const float **s = (const float **) src;
|
const float **s = (const float **) src;
|
||||||
const float *m = matrix;
|
const float *m = mix->matrix;
|
||||||
const float clev = m[2];
|
const float clev = m[2];
|
||||||
const float llev = m[3];
|
const float llev = m[3];
|
||||||
const float slev = m[4];
|
const float slev = m[4];
|
||||||
|
float v = mix->volume;
|
||||||
|
|
||||||
if (v <= VOLUME_MIN) {
|
if (v <= VOLUME_MIN) {
|
||||||
for (i = 0; i < n_dst; i++)
|
for (i = 0; i < n_dst; i++)
|
||||||
|
|
|
||||||
|
|
@ -26,14 +26,13 @@
|
||||||
|
|
||||||
#include <xmmintrin.h>
|
#include <xmmintrin.h>
|
||||||
|
|
||||||
void
|
void channelmix_copy_sse(struct channelmix *mix, uint32_t n_dst, void * SPA_RESTRICT dst[n_dst],
|
||||||
channelmix_copy_sse(void *data, int n_dst, void * SPA_RESTRICT dst[n_dst],
|
uint32_t n_src, const void * SPA_RESTRICT src[n_src], uint32_t n_samples)
|
||||||
int n_src, const void * SPA_RESTRICT src[n_src],
|
|
||||||
const void *matrix, float v, int n_samples)
|
|
||||||
{
|
{
|
||||||
int i, n, unrolled;
|
uint32_t i, n, unrolled;
|
||||||
float **d = (float **)dst;
|
float **d = (float **)dst;
|
||||||
const float **s = (const float **)src;
|
const float **s = (const float **)src;
|
||||||
|
float v = mix->volume;
|
||||||
const __m128 vol = _mm_set1_ps(v);
|
const __m128 vol = _mm_set1_ps(v);
|
||||||
|
|
||||||
if (v <= VOLUME_MIN) {
|
if (v <= VOLUME_MIN) {
|
||||||
|
|
@ -73,13 +72,13 @@ channelmix_copy_sse(void *data, int n_dst, void * SPA_RESTRICT dst[n_dst],
|
||||||
}
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
channelmix_f32_2_4_sse(void *data, int n_dst, void * SPA_RESTRICT dst[n_dst],
|
channelmix_f32_2_4_sse(struct channelmix *mix, uint32_t n_dst, void * SPA_RESTRICT dst[n_dst],
|
||||||
int n_src, const void * SPA_RESTRICT src[n_src],
|
uint32_t n_src, const void * SPA_RESTRICT src[n_src], uint32_t n_samples)
|
||||||
const void *matrix, float v, int n_samples)
|
|
||||||
{
|
{
|
||||||
int i, n, unrolled;
|
uint32_t i, n, unrolled;
|
||||||
float **d = (float **)dst;
|
float **d = (float **)dst;
|
||||||
const float **s = (const float **)src;
|
const float **s = (const float **)src;
|
||||||
|
float v = mix->volume;
|
||||||
const __m128 vol = _mm_set1_ps(v);
|
const __m128 vol = _mm_set1_ps(v);
|
||||||
__m128 in;
|
__m128 in;
|
||||||
const float *sFL = s[0], *sFR = s[1];
|
const float *sFL = s[0], *sFR = s[1];
|
||||||
|
|
@ -139,14 +138,14 @@ channelmix_f32_2_4_sse(void *data, int n_dst, void * SPA_RESTRICT dst[n_dst],
|
||||||
|
|
||||||
/* FL+FR+FC+LFE+SL+SR -> FL+FR */
|
/* FL+FR+FC+LFE+SL+SR -> FL+FR */
|
||||||
void
|
void
|
||||||
channelmix_f32_5p1_2_sse(void *data, int n_dst, void * SPA_RESTRICT dst[n_dst],
|
channelmix_f32_5p1_2_sse(struct channelmix *mix, uint32_t n_dst, void * SPA_RESTRICT dst[n_dst],
|
||||||
int n_src, const void * SPA_RESTRICT src[n_src],
|
uint32_t n_src, const void * SPA_RESTRICT src[n_src], uint32_t n_samples)
|
||||||
const void *matrix, float v, int n_samples)
|
|
||||||
{
|
{
|
||||||
int n, unrolled;
|
uint32_t n, unrolled;
|
||||||
float **d = (float **) dst;
|
float **d = (float **) dst;
|
||||||
const float **s = (const float **) src;
|
const float **s = (const float **) src;
|
||||||
const float *m = matrix;
|
float v = mix->volume;
|
||||||
|
const float *m = mix->matrix;
|
||||||
const __m128 clev = _mm_set1_ps(m[2]);
|
const __m128 clev = _mm_set1_ps(m[2]);
|
||||||
const __m128 llev = _mm_set1_ps(m[3]);
|
const __m128 llev = _mm_set1_ps(m[3]);
|
||||||
const __m128 slev = _mm_set1_ps(m[4]);
|
const __m128 slev = _mm_set1_ps(m[4]);
|
||||||
|
|
@ -231,14 +230,14 @@ channelmix_f32_5p1_2_sse(void *data, int n_dst, void * SPA_RESTRICT dst[n_dst],
|
||||||
|
|
||||||
/* FL+FR+FC+LFE+SL+SR -> FL+FR+FC+LFE*/
|
/* FL+FR+FC+LFE+SL+SR -> FL+FR+FC+LFE*/
|
||||||
void
|
void
|
||||||
channelmix_f32_5p1_3p1_sse(void *data, int n_dst, void * SPA_RESTRICT dst[n_dst],
|
channelmix_f32_5p1_3p1_sse(struct channelmix *mix, uint32_t n_dst, void * SPA_RESTRICT dst[n_dst],
|
||||||
int n_src, const void * SPA_RESTRICT src[n_src],
|
uint32_t n_src, const void * SPA_RESTRICT src[n_src], uint32_t n_samples)
|
||||||
const void *matrix, float v, int n_samples)
|
|
||||||
{
|
{
|
||||||
int i, n, unrolled;
|
uint32_t i, n, unrolled;
|
||||||
float **d = (float **) dst;
|
float **d = (float **) dst;
|
||||||
const float **s = (const float **) src;
|
const float **s = (const float **) src;
|
||||||
const __m128 mix = _mm_set1_ps(v * 0.5f);
|
float v = mix->volume;
|
||||||
|
const __m128 slev = _mm_set1_ps(v * 0.5f);
|
||||||
const __m128 vol = _mm_set1_ps(v);
|
const __m128 vol = _mm_set1_ps(v);
|
||||||
__m128 avg[2];
|
__m128 avg[2];
|
||||||
const float *sFL = s[0], *sFR = s[1], *sFC = s[2], *sLFE = s[3], *sSL = s[4], *sSR = s[5];
|
const float *sFL = s[0], *sFR = s[1], *sFC = s[2], *sLFE = s[3], *sSL = s[4], *sSR = s[5];
|
||||||
|
|
@ -266,12 +265,12 @@ channelmix_f32_5p1_3p1_sse(void *data, int n_dst, void * SPA_RESTRICT dst[n_dst]
|
||||||
for(n = 0; n < unrolled; n += 8) {
|
for(n = 0; n < unrolled; n += 8) {
|
||||||
avg[0] = _mm_add_ps(_mm_load_ps(&sFL[n]), _mm_load_ps(&sSL[n]));
|
avg[0] = _mm_add_ps(_mm_load_ps(&sFL[n]), _mm_load_ps(&sSL[n]));
|
||||||
avg[1] = _mm_add_ps(_mm_load_ps(&sFL[n+4]), _mm_load_ps(&sSL[n+4]));
|
avg[1] = _mm_add_ps(_mm_load_ps(&sFL[n+4]), _mm_load_ps(&sSL[n+4]));
|
||||||
_mm_store_ps(&dFL[n], _mm_mul_ps(avg[0], mix));
|
_mm_store_ps(&dFL[n], _mm_mul_ps(avg[0], slev));
|
||||||
_mm_store_ps(&dFL[n+4], _mm_mul_ps(avg[1], mix));
|
_mm_store_ps(&dFL[n+4], _mm_mul_ps(avg[1], slev));
|
||||||
avg[0] = _mm_add_ps(_mm_load_ps(&sFR[n]), _mm_load_ps(&sSR[n]));
|
avg[0] = _mm_add_ps(_mm_load_ps(&sFR[n]), _mm_load_ps(&sSR[n]));
|
||||||
avg[1] = _mm_add_ps(_mm_load_ps(&sFR[n+4]), _mm_load_ps(&sSR[n+4]));
|
avg[1] = _mm_add_ps(_mm_load_ps(&sFR[n+4]), _mm_load_ps(&sSR[n+4]));
|
||||||
_mm_store_ps(&dFR[n], _mm_mul_ps(avg[0], mix));
|
_mm_store_ps(&dFR[n], _mm_mul_ps(avg[0], slev));
|
||||||
_mm_store_ps(&dFR[n+4], _mm_mul_ps(avg[1], mix));
|
_mm_store_ps(&dFR[n+4], _mm_mul_ps(avg[1], slev));
|
||||||
_mm_store_ps(&dFC[n], _mm_load_ps(&sFC[n]));
|
_mm_store_ps(&dFC[n], _mm_load_ps(&sFC[n]));
|
||||||
_mm_store_ps(&dFC[n+4], _mm_load_ps(&sFC[n+4]));
|
_mm_store_ps(&dFC[n+4], _mm_load_ps(&sFC[n+4]));
|
||||||
_mm_store_ps(&dLFE[n], _mm_load_ps(&sLFE[n]));
|
_mm_store_ps(&dLFE[n], _mm_load_ps(&sLFE[n]));
|
||||||
|
|
@ -279,9 +278,9 @@ channelmix_f32_5p1_3p1_sse(void *data, int n_dst, void * SPA_RESTRICT dst[n_dst]
|
||||||
}
|
}
|
||||||
for(; n < n_samples; n++) {
|
for(; n < n_samples; n++) {
|
||||||
avg[0] = _mm_add_ss(_mm_load_ss(&sFL[n]), _mm_load_ss(&sSL[n]));
|
avg[0] = _mm_add_ss(_mm_load_ss(&sFL[n]), _mm_load_ss(&sSL[n]));
|
||||||
_mm_store_ss(&dFL[n], _mm_mul_ss(avg[0], mix));
|
_mm_store_ss(&dFL[n], _mm_mul_ss(avg[0], slev));
|
||||||
avg[0] = _mm_add_ss(_mm_load_ss(&sFR[n]), _mm_load_ss(&sSR[n]));
|
avg[0] = _mm_add_ss(_mm_load_ss(&sFR[n]), _mm_load_ss(&sSR[n]));
|
||||||
_mm_store_ss(&dFR[n], _mm_mul_ss(avg[0], mix));
|
_mm_store_ss(&dFR[n], _mm_mul_ss(avg[0], slev));
|
||||||
_mm_store_ss(&dFC[n], _mm_load_ss(&sFC[n]));
|
_mm_store_ss(&dFC[n], _mm_load_ss(&sFC[n]));
|
||||||
_mm_store_ss(&dLFE[n], _mm_load_ss(&sLFE[n]));
|
_mm_store_ss(&dLFE[n], _mm_load_ss(&sLFE[n]));
|
||||||
}
|
}
|
||||||
|
|
@ -290,12 +289,12 @@ channelmix_f32_5p1_3p1_sse(void *data, int n_dst, void * SPA_RESTRICT dst[n_dst]
|
||||||
for(n = 0; n < unrolled; n += 8) {
|
for(n = 0; n < unrolled; n += 8) {
|
||||||
avg[0] = _mm_add_ps(_mm_load_ps(&sFL[n]), _mm_load_ps(&sSL[n]));
|
avg[0] = _mm_add_ps(_mm_load_ps(&sFL[n]), _mm_load_ps(&sSL[n]));
|
||||||
avg[1] = _mm_add_ps(_mm_load_ps(&sFL[n+4]), _mm_load_ps(&sSL[n+4]));
|
avg[1] = _mm_add_ps(_mm_load_ps(&sFL[n+4]), _mm_load_ps(&sSL[n+4]));
|
||||||
_mm_store_ps(&dFL[n], _mm_mul_ps(avg[0], mix));
|
_mm_store_ps(&dFL[n], _mm_mul_ps(avg[0], slev));
|
||||||
_mm_store_ps(&dFL[n+4], _mm_mul_ps(avg[1], mix));
|
_mm_store_ps(&dFL[n+4], _mm_mul_ps(avg[1], slev));
|
||||||
avg[0] = _mm_add_ps(_mm_load_ps(&sFR[n]), _mm_load_ps(&sSR[n]));
|
avg[0] = _mm_add_ps(_mm_load_ps(&sFR[n]), _mm_load_ps(&sSR[n]));
|
||||||
avg[1] = _mm_add_ps(_mm_load_ps(&sFR[n+4]), _mm_load_ps(&sSR[n+4]));
|
avg[1] = _mm_add_ps(_mm_load_ps(&sFR[n+4]), _mm_load_ps(&sSR[n+4]));
|
||||||
_mm_store_ps(&dFR[n], _mm_mul_ps(avg[0], mix));
|
_mm_store_ps(&dFR[n], _mm_mul_ps(avg[0], slev));
|
||||||
_mm_store_ps(&dFR[n+4], _mm_mul_ps(avg[1], mix));
|
_mm_store_ps(&dFR[n+4], _mm_mul_ps(avg[1], slev));
|
||||||
_mm_store_ps(&dFC[n], _mm_mul_ps(_mm_load_ps(&sFC[n]), vol));
|
_mm_store_ps(&dFC[n], _mm_mul_ps(_mm_load_ps(&sFC[n]), vol));
|
||||||
_mm_store_ps(&dFC[n+4], _mm_mul_ps(_mm_load_ps(&sFC[n+4]), vol));
|
_mm_store_ps(&dFC[n+4], _mm_mul_ps(_mm_load_ps(&sFC[n+4]), vol));
|
||||||
_mm_store_ps(&dLFE[n], _mm_mul_ps(_mm_load_ps(&sLFE[n]), vol));
|
_mm_store_ps(&dLFE[n], _mm_mul_ps(_mm_load_ps(&sLFE[n]), vol));
|
||||||
|
|
@ -303,9 +302,9 @@ channelmix_f32_5p1_3p1_sse(void *data, int n_dst, void * SPA_RESTRICT dst[n_dst]
|
||||||
}
|
}
|
||||||
for(; n < n_samples; n++) {
|
for(; n < n_samples; n++) {
|
||||||
avg[0] = _mm_add_ss(_mm_load_ss(&sFL[n]), _mm_load_ss(&sSL[n]));
|
avg[0] = _mm_add_ss(_mm_load_ss(&sFL[n]), _mm_load_ss(&sSL[n]));
|
||||||
_mm_store_ss(&dFL[n], _mm_mul_ss(avg[0], mix));
|
_mm_store_ss(&dFL[n], _mm_mul_ss(avg[0], slev));
|
||||||
avg[0] = _mm_add_ss(_mm_load_ss(&sFR[n]), _mm_load_ss(&sSR[n]));
|
avg[0] = _mm_add_ss(_mm_load_ss(&sFR[n]), _mm_load_ss(&sSR[n]));
|
||||||
_mm_store_ss(&dFR[n], _mm_mul_ss(avg[0], mix));
|
_mm_store_ss(&dFR[n], _mm_mul_ss(avg[0], slev));
|
||||||
_mm_store_ss(&dFC[n], _mm_mul_ss(_mm_load_ss(&sFC[n]), vol));
|
_mm_store_ss(&dFC[n], _mm_mul_ss(_mm_load_ss(&sFC[n]), vol));
|
||||||
_mm_store_ss(&dLFE[n], _mm_mul_ss(_mm_load_ss(&sLFE[n]), vol));
|
_mm_store_ss(&dLFE[n], _mm_mul_ss(_mm_load_ss(&sLFE[n]), vol));
|
||||||
}
|
}
|
||||||
|
|
@ -314,14 +313,14 @@ channelmix_f32_5p1_3p1_sse(void *data, int n_dst, void * SPA_RESTRICT dst[n_dst]
|
||||||
|
|
||||||
/* FL+FR+FC+LFE+SL+SR -> FL+FR+RL+RR*/
|
/* FL+FR+FC+LFE+SL+SR -> FL+FR+RL+RR*/
|
||||||
void
|
void
|
||||||
channelmix_f32_5p1_4_sse(void *data, int n_dst, void * SPA_RESTRICT dst[n_dst],
|
channelmix_f32_5p1_4_sse(struct channelmix *mix, uint32_t n_dst, void * SPA_RESTRICT dst[n_dst],
|
||||||
int n_src, const void * SPA_RESTRICT src[n_src],
|
uint32_t n_src, const void * SPA_RESTRICT src[n_src], uint32_t n_samples)
|
||||||
const void *matrix, float v, int n_samples)
|
|
||||||
{
|
{
|
||||||
int i, n, unrolled;
|
uint32_t i, n, unrolled;
|
||||||
float **d = (float **) dst;
|
float **d = (float **) dst;
|
||||||
const float **s = (const float **) src;
|
const float **s = (const float **) src;
|
||||||
const float *m = matrix;
|
const float *m = mix->matrix;
|
||||||
|
float v = mix->volume;
|
||||||
const __m128 clev = _mm_set1_ps(m[2]);
|
const __m128 clev = _mm_set1_ps(m[2]);
|
||||||
const __m128 llev = _mm_set1_ps(m[3]);
|
const __m128 llev = _mm_set1_ps(m[3]);
|
||||||
const __m128 vol = _mm_set1_ps(v);
|
const __m128 vol = _mm_set1_ps(v);
|
||||||
|
|
|
||||||
|
|
@ -24,8 +24,11 @@
|
||||||
|
|
||||||
#include <string.h>
|
#include <string.h>
|
||||||
#include <stdio.h>
|
#include <stdio.h>
|
||||||
|
#include <math.h>
|
||||||
|
|
||||||
|
#include <spa/param/audio/format-utils.h>
|
||||||
#include <spa/support/cpu.h>
|
#include <spa/support/cpu.h>
|
||||||
|
#include <spa/support/log.h>
|
||||||
#include <spa/utils/defs.h>
|
#include <spa/utils/defs.h>
|
||||||
|
|
||||||
#define VOLUME_MIN 0.0f
|
#define VOLUME_MIN 0.0f
|
||||||
|
|
@ -41,29 +44,26 @@
|
||||||
#define MASK_5_1 _M(FL)|_M(FR)|_M(FC)|_M(LFE)|_M(SL)|_M(SR)|_M(RL)|_M(RR)
|
#define MASK_5_1 _M(FL)|_M(FR)|_M(FC)|_M(LFE)|_M(SL)|_M(SR)|_M(RL)|_M(RR)
|
||||||
#define MASK_7_1 _M(FL)|_M(FR)|_M(FC)|_M(LFE)|_M(SL)|_M(SR)|_M(RL)|_M(RR)
|
#define MASK_7_1 _M(FL)|_M(FR)|_M(FC)|_M(LFE)|_M(SL)|_M(SR)|_M(RL)|_M(RR)
|
||||||
|
|
||||||
typedef void (*channelmix_func_t) (void *data, int n_dst, void * SPA_RESTRICT dst[n_dst],
|
|
||||||
int n_src, const void * SPA_RESTRICT src[n_src],
|
|
||||||
const void * SPA_RESTRICT matrix, float v, int n_samples);
|
|
||||||
|
|
||||||
|
|
||||||
#define ANY ((uint32_t)-1)
|
#define ANY ((uint32_t)-1)
|
||||||
#define EQ ((uint32_t)-2)
|
#define EQ ((uint32_t)-2)
|
||||||
|
|
||||||
|
typedef void (*channelmix_func_t) (struct channelmix *mix, uint32_t n_dst, void * SPA_RESTRICT dst[n_dst],
|
||||||
|
uint32_t n_src, const void * SPA_RESTRICT src[n_src], uint32_t n_samples);
|
||||||
|
|
||||||
static const struct channelmix_info {
|
static const struct channelmix_info {
|
||||||
uint32_t src_chan;
|
uint32_t src_chan;
|
||||||
uint64_t src_mask;
|
uint64_t src_mask;
|
||||||
uint32_t dst_chan;
|
uint32_t dst_chan;
|
||||||
uint64_t dst_mask;
|
uint64_t dst_mask;
|
||||||
|
|
||||||
channelmix_func_t func;
|
channelmix_func_t process;
|
||||||
#define FEATURE_SSE SPA_CPU_FLAG_SSE
|
uint32_t cpu_flags;
|
||||||
uint32_t features;
|
|
||||||
} channelmix_table[] =
|
} channelmix_table[] =
|
||||||
{
|
{
|
||||||
#if defined (HAVE_SSE)
|
#if defined (HAVE_SSE)
|
||||||
{ 2, MASK_MONO, 2, MASK_MONO, channelmix_copy_sse, FEATURE_SSE },
|
{ 2, MASK_MONO, 2, MASK_MONO, channelmix_copy_sse, SPA_CPU_FLAG_SSE },
|
||||||
{ 2, MASK_STEREO, 2, MASK_STEREO, channelmix_copy_sse, FEATURE_SSE },
|
{ 2, MASK_STEREO, 2, MASK_STEREO, channelmix_copy_sse, SPA_CPU_FLAG_SSE },
|
||||||
{ EQ, 0, EQ, 0, channelmix_copy_sse, FEATURE_SSE },
|
{ EQ, 0, EQ, 0, channelmix_copy_sse, SPA_CPU_FLAG_SSE },
|
||||||
#endif
|
#endif
|
||||||
{ 2, MASK_MONO, 2, MASK_MONO, channelmix_copy_c, 0 },
|
{ 2, MASK_MONO, 2, MASK_MONO, channelmix_copy_c, 0 },
|
||||||
{ 2, MASK_STEREO, 2, MASK_STEREO, channelmix_copy_c, 0 },
|
{ 2, MASK_STEREO, 2, MASK_STEREO, channelmix_copy_c, 0 },
|
||||||
|
|
@ -74,22 +74,22 @@ static const struct channelmix_info {
|
||||||
{ 4, MASK_QUAD, 1, MASK_MONO, channelmix_f32_4_1_c, 0 },
|
{ 4, MASK_QUAD, 1, MASK_MONO, channelmix_f32_4_1_c, 0 },
|
||||||
{ 4, MASK_3_1, 1, MASK_MONO, channelmix_f32_3p1_1_c, 0 },
|
{ 4, MASK_3_1, 1, MASK_MONO, channelmix_f32_3p1_1_c, 0 },
|
||||||
#if defined (HAVE_SSE)
|
#if defined (HAVE_SSE)
|
||||||
{ 2, MASK_STEREO, 4, MASK_QUAD, channelmix_f32_2_4_sse, FEATURE_SSE },
|
{ 2, MASK_STEREO, 4, MASK_QUAD, channelmix_f32_2_4_sse, SPA_CPU_FLAG_SSE },
|
||||||
#endif
|
#endif
|
||||||
{ 2, MASK_STEREO, 4, MASK_QUAD, channelmix_f32_2_4_c, 0 },
|
{ 2, MASK_STEREO, 4, MASK_QUAD, channelmix_f32_2_4_c, 0 },
|
||||||
{ 2, MASK_STEREO, 4, MASK_3_1, channelmix_f32_2_3p1_c, 0 },
|
{ 2, MASK_STEREO, 4, MASK_3_1, channelmix_f32_2_3p1_c, 0 },
|
||||||
{ 2, MASK_STEREO, 6, MASK_5_1, channelmix_f32_2_5p1_c, 0 },
|
{ 2, MASK_STEREO, 6, MASK_5_1, channelmix_f32_2_5p1_c, 0 },
|
||||||
#if defined (HAVE_SSE)
|
#if defined (HAVE_SSE)
|
||||||
{ 6, MASK_5_1, 2, MASK_STEREO, channelmix_f32_5p1_2_sse, FEATURE_SSE },
|
{ 6, MASK_5_1, 2, MASK_STEREO, channelmix_f32_5p1_2_sse, SPA_CPU_FLAG_SSE },
|
||||||
#endif
|
#endif
|
||||||
{ 6, MASK_5_1, 2, MASK_STEREO, channelmix_f32_5p1_2_c, 0 },
|
{ 6, MASK_5_1, 2, MASK_STEREO, channelmix_f32_5p1_2_c, 0 },
|
||||||
#if defined (HAVE_SSE)
|
#if defined (HAVE_SSE)
|
||||||
{ 6, MASK_5_1, 4, MASK_QUAD, channelmix_f32_5p1_4_sse, FEATURE_SSE },
|
{ 6, MASK_5_1, 4, MASK_QUAD, channelmix_f32_5p1_4_sse, SPA_CPU_FLAG_SSE },
|
||||||
#endif
|
#endif
|
||||||
{ 6, MASK_5_1, 4, MASK_QUAD, channelmix_f32_5p1_4_c, 0 },
|
{ 6, MASK_5_1, 4, MASK_QUAD, channelmix_f32_5p1_4_c, 0 },
|
||||||
|
|
||||||
#if defined (HAVE_SSE)
|
#if defined (HAVE_SSE)
|
||||||
{ 6, MASK_5_1, 4, MASK_3_1, channelmix_f32_5p1_3p1_sse, FEATURE_SSE },
|
{ 6, MASK_5_1, 4, MASK_3_1, channelmix_f32_5p1_3p1_sse, SPA_CPU_FLAG_SSE },
|
||||||
#endif
|
#endif
|
||||||
{ 6, MASK_5_1, 4, MASK_3_1, channelmix_f32_5p1_3p1_c, 0 },
|
{ 6, MASK_5_1, 4, MASK_3_1, channelmix_f32_5p1_3p1_c, 0 },
|
||||||
|
|
||||||
|
|
@ -101,15 +101,15 @@ static const struct channelmix_info {
|
||||||
};
|
};
|
||||||
|
|
||||||
#define MATCH_CHAN(a,b) ((a) == ANY || (a) == (b))
|
#define MATCH_CHAN(a,b) ((a) == ANY || (a) == (b))
|
||||||
#define MATCH_FEATURES(a,b) ((a) == 0 || ((a) & (b)) != 0)
|
#define MATCH_CPU_FLAGS(a,b) ((a) == 0 || ((a) & (b)) == a)
|
||||||
#define MATCH_MASK(a,b) ((a) == 0 || ((a) & (b)) == (b))
|
#define MATCH_MASK(a,b) ((a) == 0 || ((a) & (b)) == (b))
|
||||||
|
|
||||||
static const struct channelmix_info *find_channelmix_info(uint32_t src_chan, uint64_t src_mask,
|
static const struct channelmix_info *find_channelmix_info(uint32_t src_chan, uint64_t src_mask,
|
||||||
uint32_t dst_chan, uint64_t dst_mask, uint32_t features)
|
uint32_t dst_chan, uint64_t dst_mask, uint32_t cpu_flags)
|
||||||
{
|
{
|
||||||
size_t i;
|
size_t i;
|
||||||
for (i = 0; i < SPA_N_ELEMENTS(channelmix_table); i++) {
|
for (i = 0; i < SPA_N_ELEMENTS(channelmix_table); i++) {
|
||||||
if (!MATCH_FEATURES(channelmix_table[i].features, features))
|
if (!MATCH_CPU_FLAGS(channelmix_table[i].cpu_flags, cpu_flags))
|
||||||
continue;
|
continue;
|
||||||
|
|
||||||
if (src_chan == dst_chan && src_mask == dst_mask)
|
if (src_chan == dst_chan && src_mask == dst_mask)
|
||||||
|
|
@ -123,3 +123,253 @@ static const struct channelmix_info *find_channelmix_info(uint32_t src_chan, uin
|
||||||
}
|
}
|
||||||
return NULL;
|
return NULL;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
#define M 0
|
||||||
|
#define FL 1
|
||||||
|
#define FR 2
|
||||||
|
#define FC 3
|
||||||
|
#define LFE 4
|
||||||
|
#define SL 5
|
||||||
|
#define SR 6
|
||||||
|
#define FLC 7
|
||||||
|
#define FRC 8
|
||||||
|
#define RC 9
|
||||||
|
#define RL 10
|
||||||
|
#define RR 11
|
||||||
|
#define TC 12
|
||||||
|
#define TFL 13
|
||||||
|
#define TFC 14
|
||||||
|
#define TFR 15
|
||||||
|
#define TRL 16
|
||||||
|
#define TRC 17
|
||||||
|
#define TRR 18
|
||||||
|
#define NUM_CHAN 19
|
||||||
|
|
||||||
|
#define SQRT3_2 1.224744871f /* sqrt(3/2) */
|
||||||
|
#define SQRT1_2 0.707106781f
|
||||||
|
#define SQRT2 1.414213562f
|
||||||
|
|
||||||
|
#define MATRIX_NORMAL 0
|
||||||
|
#define MATRIX_DOLBY 1
|
||||||
|
#define MATRIX_DPLII 2
|
||||||
|
|
||||||
|
#define _MASK(ch) (1ULL << SPA_AUDIO_CHANNEL_ ## ch)
|
||||||
|
#define STEREO (_MASK(FL)|_MASK(FR))
|
||||||
|
|
||||||
|
static int make_matrix(struct channelmix *mix)
|
||||||
|
{
|
||||||
|
float matrix[NUM_CHAN][NUM_CHAN] = {{ 0.0f }};
|
||||||
|
uint32_t src_chan = mix->src_chan;
|
||||||
|
uint64_t src_mask = mix->src_mask;
|
||||||
|
uint32_t dst_chan = mix->dst_chan;
|
||||||
|
uint64_t dst_mask = mix->dst_mask;
|
||||||
|
uint64_t unassigned;
|
||||||
|
uint32_t i, j, matrix_encoding = MATRIX_NORMAL, c;
|
||||||
|
float clev = SQRT1_2;
|
||||||
|
float slev = SQRT1_2;
|
||||||
|
float llev = 0.5f;
|
||||||
|
float max = 0.0f;
|
||||||
|
|
||||||
|
for (i = 0; i < NUM_CHAN; i++) {
|
||||||
|
if (src_mask & dst_mask & (1ULL << (i + 2)))
|
||||||
|
matrix[i][i]= 1.0f;
|
||||||
|
}
|
||||||
|
|
||||||
|
if ((dst_mask & _MASK(MONO)) == _MASK(MONO))
|
||||||
|
dst_mask = _MASK(FC);
|
||||||
|
|
||||||
|
unassigned = src_mask & ~dst_mask;
|
||||||
|
|
||||||
|
spa_log_debug(mix->log, "unassigned %08lx", unassigned);
|
||||||
|
|
||||||
|
if (unassigned & _MASK(FC)){
|
||||||
|
if ((dst_mask & STEREO) == STEREO){
|
||||||
|
if(src_mask & STEREO) {
|
||||||
|
matrix[FL][FC] += clev;
|
||||||
|
matrix[FR][FC] += clev;
|
||||||
|
} else {
|
||||||
|
matrix[FL][FC] += SQRT1_2;
|
||||||
|
matrix[FR][FC] += SQRT1_2;
|
||||||
|
}
|
||||||
|
} else {
|
||||||
|
spa_log_warn(mix->log, "can't assign FC");
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
if (unassigned & STEREO){
|
||||||
|
if (dst_mask & _MASK(FC)) {
|
||||||
|
matrix[FC][FL] += SQRT1_2;
|
||||||
|
matrix[FC][FR] += SQRT1_2;
|
||||||
|
if (src_mask & _MASK(FC))
|
||||||
|
matrix[FC][FC] = clev * SQRT2;
|
||||||
|
} else {
|
||||||
|
spa_log_warn(mix->log, "can't assign STEREO");
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
if (unassigned & _MASK(RC)) {
|
||||||
|
if (dst_mask & _MASK(RL)){
|
||||||
|
matrix[RL][RC] += SQRT1_2;
|
||||||
|
matrix[RR][RC] += SQRT1_2;
|
||||||
|
} else if (dst_mask & _MASK(SL)) {
|
||||||
|
matrix[SL][RC] += SQRT1_2;
|
||||||
|
matrix[SR][RC] += SQRT1_2;
|
||||||
|
} else if(dst_mask & _MASK(FL)) {
|
||||||
|
if (matrix_encoding == MATRIX_DOLBY ||
|
||||||
|
matrix_encoding == MATRIX_DPLII) {
|
||||||
|
if (unassigned & (_MASK(RL)|_MASK(RR))) {
|
||||||
|
matrix[FL][RC] -= slev * SQRT1_2;
|
||||||
|
matrix[FR][RC] += slev * SQRT1_2;
|
||||||
|
} else {
|
||||||
|
matrix[FL][RC] -= slev;
|
||||||
|
matrix[FR][RC] += slev;
|
||||||
|
}
|
||||||
|
} else {
|
||||||
|
matrix[FL][RC] += slev * SQRT1_2;
|
||||||
|
matrix[FR][RC] += slev * SQRT1_2;
|
||||||
|
}
|
||||||
|
} else if (dst_mask & _MASK(FC)) {
|
||||||
|
matrix[FC][RC] += slev * SQRT1_2;
|
||||||
|
} else {
|
||||||
|
spa_log_warn(mix->log, "can't assign RC");
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
if (unassigned & _MASK(RL)) {
|
||||||
|
if (dst_mask & _MASK(RC)) {
|
||||||
|
matrix[RC][RL] += SQRT1_2;
|
||||||
|
matrix[RC][RR] += SQRT1_2;
|
||||||
|
} else if (dst_mask & _MASK(SL)) {
|
||||||
|
if (src_mask & _MASK(SL)) {
|
||||||
|
matrix[SL][RL] += SQRT1_2;
|
||||||
|
matrix[SR][RR] += SQRT1_2;
|
||||||
|
} else {
|
||||||
|
matrix[SL][RL] += 1.0f;
|
||||||
|
matrix[SR][RR] += 1.0f;
|
||||||
|
}
|
||||||
|
} else if (dst_mask & _MASK(FL)) {
|
||||||
|
if (matrix_encoding == MATRIX_DOLBY) {
|
||||||
|
matrix[FL][RL] -= slev * SQRT1_2;
|
||||||
|
matrix[FL][RR] -= slev * SQRT1_2;
|
||||||
|
matrix[FR][RL] += slev * SQRT1_2;
|
||||||
|
matrix[FR][RR] += slev * SQRT1_2;
|
||||||
|
} else if (matrix_encoding == MATRIX_DPLII) {
|
||||||
|
matrix[FL][RL] -= slev * SQRT3_2;
|
||||||
|
matrix[FL][RR] -= slev * SQRT1_2;
|
||||||
|
matrix[FR][RL] += slev * SQRT1_2;
|
||||||
|
matrix[FR][RR] += slev * SQRT3_2;
|
||||||
|
} else {
|
||||||
|
matrix[FL][RL] += slev;
|
||||||
|
matrix[FR][RR] += slev;
|
||||||
|
}
|
||||||
|
} else if (dst_mask & _MASK(FC)) {
|
||||||
|
matrix[FC][RL]+= slev * SQRT1_2;
|
||||||
|
matrix[FC][RR]+= slev * SQRT1_2;
|
||||||
|
} else {
|
||||||
|
spa_log_warn(mix->log, "can't assign RL");
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
if (unassigned & _MASK(SL)) {
|
||||||
|
if (dst_mask & _MASK(RL)) {
|
||||||
|
if (src_mask & _MASK(RL)) {
|
||||||
|
matrix[RL][SL] += SQRT1_2;
|
||||||
|
matrix[RR][SR] += SQRT1_2;
|
||||||
|
} else {
|
||||||
|
matrix[RL][SL] += 1.0f;
|
||||||
|
matrix[RR][SR] += 1.0f;
|
||||||
|
}
|
||||||
|
} else if (dst_mask & _MASK(RC)) {
|
||||||
|
matrix[RC][SL]+= SQRT1_2;
|
||||||
|
matrix[RC][SR]+= SQRT1_2;
|
||||||
|
} else if (dst_mask & _MASK(FL)) {
|
||||||
|
if (matrix_encoding == MATRIX_DOLBY) {
|
||||||
|
matrix[FL][SL] -= slev * SQRT1_2;
|
||||||
|
matrix[FL][SR] -= slev * SQRT1_2;
|
||||||
|
matrix[FR][SL] += slev * SQRT1_2;
|
||||||
|
matrix[FR][SR] += slev * SQRT1_2;
|
||||||
|
} else if (matrix_encoding == MATRIX_DPLII) {
|
||||||
|
matrix[FL][SL] -= slev * SQRT3_2;
|
||||||
|
matrix[FL][SR] -= slev * SQRT1_2;
|
||||||
|
matrix[FR][SL] += slev * SQRT1_2;
|
||||||
|
matrix[FR][SR] += slev * SQRT3_2;
|
||||||
|
} else {
|
||||||
|
matrix[FL][SL] += slev;
|
||||||
|
matrix[FR][SR] += slev;
|
||||||
|
}
|
||||||
|
} else if (dst_mask & _MASK(FC)) {
|
||||||
|
matrix[FC][SL] += slev * SQRT1_2;
|
||||||
|
matrix[FC][SR] += slev * SQRT1_2;
|
||||||
|
} else {
|
||||||
|
spa_log_warn(mix->log, "can't assign SL");
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
if (unassigned & _MASK(FLC)) {
|
||||||
|
if (dst_mask & _MASK(FL)) {
|
||||||
|
matrix[FC][FLC]+= 1.0f;
|
||||||
|
matrix[FC][FRC]+= 1.0f;
|
||||||
|
} else if(dst_mask & _MASK(FC)) {
|
||||||
|
matrix[FC][FLC]+= SQRT1_2;
|
||||||
|
matrix[FC][FRC]+= SQRT1_2;
|
||||||
|
} else {
|
||||||
|
spa_log_warn(mix->log, "can't assign FLC");
|
||||||
|
}
|
||||||
|
}
|
||||||
|
if (unassigned & _MASK(LFE)) {
|
||||||
|
if (dst_mask & _MASK(FC)) {
|
||||||
|
matrix[FC][LFE] += llev;
|
||||||
|
} else if (dst_mask & _MASK(FL)) {
|
||||||
|
matrix[FL][LFE] += llev * SQRT1_2;
|
||||||
|
matrix[FR][LFE] += llev * SQRT1_2;
|
||||||
|
} else {
|
||||||
|
spa_log_warn(mix->log, "can't assign LFE");
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
c = 0;
|
||||||
|
for (i = 0; i < NUM_CHAN; i++) {
|
||||||
|
float sum = 0.0f;
|
||||||
|
if ((dst_mask & (1UL << (i + 2))) == 0)
|
||||||
|
continue;
|
||||||
|
for (j = 0; j < NUM_CHAN; j++) {
|
||||||
|
if ((src_mask & (1UL << (j + 2))) == 0)
|
||||||
|
continue;
|
||||||
|
mix->matrix[c++] = matrix[i][j];
|
||||||
|
sum += fabs(matrix[i][j]);
|
||||||
|
}
|
||||||
|
max = SPA_MAX(max, sum);
|
||||||
|
}
|
||||||
|
|
||||||
|
mix->is_identity = dst_chan == src_chan;
|
||||||
|
for (i = 0; i < dst_chan; i++) {
|
||||||
|
for (j = 0; j < src_chan; j++) {
|
||||||
|
float v = mix->matrix[i * src_chan + j];
|
||||||
|
spa_log_debug(mix->log, "%d %d: %f", i, j, v);
|
||||||
|
if ((i == j && v != 1.0f) ||
|
||||||
|
(i != j && v != 0.0f))
|
||||||
|
mix->is_identity = false;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
static void impl_channelmix_free(struct channelmix *mix)
|
||||||
|
{
|
||||||
|
mix->process = NULL;
|
||||||
|
}
|
||||||
|
|
||||||
|
int channelmix_init(struct channelmix *mix)
|
||||||
|
{
|
||||||
|
const struct channelmix_info *info;
|
||||||
|
|
||||||
|
info = find_channelmix_info(mix->src_chan, mix->src_mask, mix->dst_chan, mix->dst_mask,
|
||||||
|
mix->cpu_flags);
|
||||||
|
if (info == NULL)
|
||||||
|
return -ENOTSUP;
|
||||||
|
|
||||||
|
mix->free = impl_channelmix_free;
|
||||||
|
mix->process = info->process;
|
||||||
|
mix->cpu_flags = info->cpu_flags;
|
||||||
|
return make_matrix(mix);
|
||||||
|
}
|
||||||
|
|
|
||||||
|
|
@ -30,6 +30,8 @@
|
||||||
#define VOLUME_MIN 0.0f
|
#define VOLUME_MIN 0.0f
|
||||||
#define VOLUME_NORM 1.0f
|
#define VOLUME_NORM 1.0f
|
||||||
|
|
||||||
|
#define MAX_CHANNELS 64
|
||||||
|
|
||||||
#define _M(ch) (1UL << SPA_AUDIO_CHANNEL_ ## ch)
|
#define _M(ch) (1UL << SPA_AUDIO_CHANNEL_ ## ch)
|
||||||
#define MASK_MONO _M(FC)|_M(MONO)|_M(UNKNOWN)
|
#define MASK_MONO _M(FC)|_M(MONO)|_M(UNKNOWN)
|
||||||
#define MASK_STEREO _M(FL)|_M(FR)|_M(UNKNOWN)
|
#define MASK_STEREO _M(FL)|_M(FR)|_M(UNKNOWN)
|
||||||
|
|
@ -38,15 +40,37 @@
|
||||||
#define MASK_5_1 _M(FL)|_M(FR)|_M(FC)|_M(LFE)|_M(SL)|_M(SR)|_M(RL)|_M(RR)
|
#define MASK_5_1 _M(FL)|_M(FR)|_M(FC)|_M(LFE)|_M(SL)|_M(SR)|_M(RL)|_M(RR)
|
||||||
#define MASK_7_1 _M(FL)|_M(FR)|_M(FC)|_M(LFE)|_M(SL)|_M(SR)|_M(RL)|_M(RR)
|
#define MASK_7_1 _M(FL)|_M(FR)|_M(FC)|_M(LFE)|_M(SL)|_M(SR)|_M(RL)|_M(RR)
|
||||||
|
|
||||||
typedef void (*channelmix_func_t) (void *data, int n_dst, void * SPA_RESTRICT dst[n_dst],
|
|
||||||
int n_src, const void * SPA_RESTRICT src[n_src],
|
struct channelmix {
|
||||||
const void * SPA_RESTRICT matrix, float v, int n_samples);
|
uint32_t src_chan;
|
||||||
|
uint32_t dst_chan;
|
||||||
|
uint64_t src_mask;
|
||||||
|
uint64_t dst_mask;
|
||||||
|
uint32_t cpu_flags;
|
||||||
|
|
||||||
|
struct spa_log *log;
|
||||||
|
|
||||||
|
int is_identity:1;
|
||||||
|
float volume;
|
||||||
|
float matrix[MAX_CHANNELS * MAX_CHANNELS];
|
||||||
|
|
||||||
|
void (*process) (struct channelmix *mix, uint32_t n_dst, void * SPA_RESTRICT dst[n_dst],
|
||||||
|
uint32_t n_src, const void * SPA_RESTRICT src[n_src], uint32_t n_samples);
|
||||||
|
void (*free) (struct channelmix *mix);
|
||||||
|
|
||||||
|
void *data;
|
||||||
|
};
|
||||||
|
|
||||||
|
int channelmix_init(struct channelmix *mix);
|
||||||
|
|
||||||
|
#define channelmix_process(mix,...) (mix)->process(mix, __VA_ARGS__)
|
||||||
|
#define channelmix_free(mix) (mix)->free(mix)
|
||||||
|
|
||||||
#define DEFINE_FUNCTION(name,arch) \
|
#define DEFINE_FUNCTION(name,arch) \
|
||||||
void channelmix_##name##_##arch(void *data, \
|
void channelmix_##name##_##arch(struct channelmix *mix, \
|
||||||
int n_dst, void * SPA_RESTRICT dst[n_dst], \
|
uint32_t n_dst, void * SPA_RESTRICT dst[n_dst], \
|
||||||
int n_src, const void * SPA_RESTRICT src[n_src], \
|
uint32_t n_src, const void * SPA_RESTRICT src[n_src], \
|
||||||
const void *matrix, float v, int n_samples);
|
uint32_t n_samples);
|
||||||
|
|
||||||
DEFINE_FUNCTION(copy, c);
|
DEFINE_FUNCTION(copy, c);
|
||||||
DEFINE_FUNCTION(f32_n_m, c);
|
DEFINE_FUNCTION(f32_n_m, c);
|
||||||
|
|
|
||||||
|
|
@ -25,9 +25,10 @@
|
||||||
#include <errno.h>
|
#include <errno.h>
|
||||||
#include <string.h>
|
#include <string.h>
|
||||||
#include <stdio.h>
|
#include <stdio.h>
|
||||||
#include <math.h>
|
//#include <math.h>
|
||||||
|
|
||||||
#include <spa/support/log.h>
|
#include <spa/support/log.h>
|
||||||
|
#include <spa/support/cpu.h>
|
||||||
#include <spa/utils/list.h>
|
#include <spa/utils/list.h>
|
||||||
#include <spa/node/node.h>
|
#include <spa/node/node.h>
|
||||||
#include <spa/node/io.h>
|
#include <spa/node/io.h>
|
||||||
|
|
@ -95,7 +96,7 @@ struct port {
|
||||||
struct spa_list queue;
|
struct spa_list queue;
|
||||||
};
|
};
|
||||||
|
|
||||||
#include "channelmix-ops.c"
|
#include "channelmix-ops.h"
|
||||||
|
|
||||||
struct impl {
|
struct impl {
|
||||||
struct spa_handle handle;
|
struct spa_handle handle;
|
||||||
|
|
@ -115,12 +116,10 @@ struct impl {
|
||||||
struct port in_port;
|
struct port in_port;
|
||||||
struct port out_port;
|
struct port out_port;
|
||||||
|
|
||||||
channelmix_func_t convert;
|
struct channelmix mix;
|
||||||
int started:1;
|
int started:1;
|
||||||
int is_passthrough:1;
|
int is_passthrough:1;
|
||||||
uint32_t cpu_flags;
|
uint32_t cpu_flags;
|
||||||
uint32_t n_matrix;
|
|
||||||
float matrix[4096];
|
|
||||||
};
|
};
|
||||||
|
|
||||||
#define CHECK_PORT(this,d,id) (id == 0)
|
#define CHECK_PORT(this,d,id) (id == 0)
|
||||||
|
|
@ -131,35 +130,6 @@ struct impl {
|
||||||
#define _MASK(ch) (1ULL << SPA_AUDIO_CHANNEL_ ## ch)
|
#define _MASK(ch) (1ULL << SPA_AUDIO_CHANNEL_ ## ch)
|
||||||
#define STEREO (_MASK(FL)|_MASK(FR))
|
#define STEREO (_MASK(FL)|_MASK(FR))
|
||||||
|
|
||||||
#define M 0
|
|
||||||
#define FL 1
|
|
||||||
#define FR 2
|
|
||||||
#define FC 3
|
|
||||||
#define LFE 4
|
|
||||||
#define SL 5
|
|
||||||
#define SR 6
|
|
||||||
#define FLC 7
|
|
||||||
#define FRC 8
|
|
||||||
#define RC 9
|
|
||||||
#define RL 10
|
|
||||||
#define RR 11
|
|
||||||
#define TC 12
|
|
||||||
#define TFL 13
|
|
||||||
#define TFC 14
|
|
||||||
#define TFR 15
|
|
||||||
#define TRL 16
|
|
||||||
#define TRC 17
|
|
||||||
#define TRR 18
|
|
||||||
#define NUM_CHAN 19
|
|
||||||
|
|
||||||
#define SQRT3_2 1.224744871f /* sqrt(3/2) */
|
|
||||||
#define SQRT1_2 0.707106781f
|
|
||||||
#define SQRT2 1.414213562f
|
|
||||||
|
|
||||||
#define MATRIX_NORMAL 0
|
|
||||||
#define MATRIX_DOLBY 1
|
|
||||||
#define MATRIX_DPLII 2
|
|
||||||
|
|
||||||
static uint64_t default_mask(uint32_t channels)
|
static uint64_t default_mask(uint32_t channels)
|
||||||
{
|
{
|
||||||
uint64_t mask = 0;
|
uint64_t mask = 0;
|
||||||
|
|
@ -193,210 +163,14 @@ static uint64_t default_mask(uint32_t channels)
|
||||||
return mask;
|
return mask;
|
||||||
}
|
}
|
||||||
|
|
||||||
static int make_matrix(struct impl *this,
|
|
||||||
uint32_t src_chan, uint64_t src_mask,
|
|
||||||
uint32_t dst_chan, uint64_t dst_mask)
|
|
||||||
{
|
|
||||||
float matrix[NUM_CHAN][NUM_CHAN] = {{ 0.0f }};
|
|
||||||
uint64_t unassigned;
|
|
||||||
uint32_t i, j, matrix_encoding = MATRIX_NORMAL, c;
|
|
||||||
float clev = SQRT1_2;
|
|
||||||
float slev = SQRT1_2;
|
|
||||||
float llev = 0.5f;
|
|
||||||
float max = 0.0f;
|
|
||||||
|
|
||||||
for (i = 0; i < NUM_CHAN; i++) {
|
|
||||||
if (src_mask & dst_mask & (1ULL << (i + 2)))
|
|
||||||
matrix[i][i]= 1.0f;
|
|
||||||
}
|
|
||||||
|
|
||||||
if ((dst_mask & _MASK(MONO)) == _MASK(MONO))
|
|
||||||
dst_mask = _MASK(FC);
|
|
||||||
|
|
||||||
unassigned = src_mask & ~dst_mask;
|
|
||||||
|
|
||||||
spa_log_debug(this->log, "unassigned %08lx", unassigned);
|
|
||||||
|
|
||||||
if (unassigned & _MASK(FC)){
|
|
||||||
if ((dst_mask & STEREO) == STEREO){
|
|
||||||
if(src_mask & STEREO) {
|
|
||||||
matrix[FL][FC] += clev;
|
|
||||||
matrix[FR][FC] += clev;
|
|
||||||
} else {
|
|
||||||
matrix[FL][FC] += SQRT1_2;
|
|
||||||
matrix[FR][FC] += SQRT1_2;
|
|
||||||
}
|
|
||||||
} else {
|
|
||||||
spa_log_warn(this->log, "can't assign FC");
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
if (unassigned & STEREO){
|
|
||||||
if (dst_mask & _MASK(FC)) {
|
|
||||||
matrix[FC][FL] += SQRT1_2;
|
|
||||||
matrix[FC][FR] += SQRT1_2;
|
|
||||||
if (src_mask & _MASK(FC))
|
|
||||||
matrix[FC][FC] = clev * SQRT2;
|
|
||||||
} else {
|
|
||||||
spa_log_warn(this->log, "can't assign STEREO");
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
if (unassigned & _MASK(RC)) {
|
|
||||||
if (dst_mask & _MASK(RL)){
|
|
||||||
matrix[RL][RC] += SQRT1_2;
|
|
||||||
matrix[RR][RC] += SQRT1_2;
|
|
||||||
} else if (dst_mask & _MASK(SL)) {
|
|
||||||
matrix[SL][RC] += SQRT1_2;
|
|
||||||
matrix[SR][RC] += SQRT1_2;
|
|
||||||
} else if(dst_mask & _MASK(FL)) {
|
|
||||||
if (matrix_encoding == MATRIX_DOLBY ||
|
|
||||||
matrix_encoding == MATRIX_DPLII) {
|
|
||||||
if (unassigned & (_MASK(RL)|_MASK(RR))) {
|
|
||||||
matrix[FL][RC] -= slev * SQRT1_2;
|
|
||||||
matrix[FR][RC] += slev * SQRT1_2;
|
|
||||||
} else {
|
|
||||||
matrix[FL][RC] -= slev;
|
|
||||||
matrix[FR][RC] += slev;
|
|
||||||
}
|
|
||||||
} else {
|
|
||||||
matrix[FL][RC] += slev * SQRT1_2;
|
|
||||||
matrix[FR][RC] += slev * SQRT1_2;
|
|
||||||
}
|
|
||||||
} else if (dst_mask & _MASK(FC)) {
|
|
||||||
matrix[FC][RC] += slev * SQRT1_2;
|
|
||||||
} else {
|
|
||||||
spa_log_warn(this->log, "can't assign RC");
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
if (unassigned & _MASK(RL)) {
|
|
||||||
if (dst_mask & _MASK(RC)) {
|
|
||||||
matrix[RC][RL] += SQRT1_2;
|
|
||||||
matrix[RC][RR] += SQRT1_2;
|
|
||||||
} else if (dst_mask & _MASK(SL)) {
|
|
||||||
if (src_mask & _MASK(SL)) {
|
|
||||||
matrix[SL][RL] += SQRT1_2;
|
|
||||||
matrix[SR][RR] += SQRT1_2;
|
|
||||||
} else {
|
|
||||||
matrix[SL][RL] += 1.0f;
|
|
||||||
matrix[SR][RR] += 1.0f;
|
|
||||||
}
|
|
||||||
} else if (dst_mask & _MASK(FL)) {
|
|
||||||
if (matrix_encoding == MATRIX_DOLBY) {
|
|
||||||
matrix[FL][RL] -= slev * SQRT1_2;
|
|
||||||
matrix[FL][RR] -= slev * SQRT1_2;
|
|
||||||
matrix[FR][RL] += slev * SQRT1_2;
|
|
||||||
matrix[FR][RR] += slev * SQRT1_2;
|
|
||||||
} else if (matrix_encoding == MATRIX_DPLII) {
|
|
||||||
matrix[FL][RL] -= slev * SQRT3_2;
|
|
||||||
matrix[FL][RR] -= slev * SQRT1_2;
|
|
||||||
matrix[FR][RL] += slev * SQRT1_2;
|
|
||||||
matrix[FR][RR] += slev * SQRT3_2;
|
|
||||||
} else {
|
|
||||||
matrix[FL][RL] += slev;
|
|
||||||
matrix[FR][RR] += slev;
|
|
||||||
}
|
|
||||||
} else if (dst_mask & _MASK(FC)) {
|
|
||||||
matrix[FC][RL]+= slev * SQRT1_2;
|
|
||||||
matrix[FC][RR]+= slev * SQRT1_2;
|
|
||||||
} else {
|
|
||||||
spa_log_warn(this->log, "can't assign RL");
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
if (unassigned & _MASK(SL)) {
|
|
||||||
if (dst_mask & _MASK(RL)) {
|
|
||||||
if (src_mask & _MASK(RL)) {
|
|
||||||
matrix[RL][SL] += SQRT1_2;
|
|
||||||
matrix[RR][SR] += SQRT1_2;
|
|
||||||
} else {
|
|
||||||
matrix[RL][SL] += 1.0f;
|
|
||||||
matrix[RR][SR] += 1.0f;
|
|
||||||
}
|
|
||||||
} else if (dst_mask & _MASK(RC)) {
|
|
||||||
matrix[RC][SL]+= SQRT1_2;
|
|
||||||
matrix[RC][SR]+= SQRT1_2;
|
|
||||||
} else if (dst_mask & _MASK(FL)) {
|
|
||||||
if (matrix_encoding == MATRIX_DOLBY) {
|
|
||||||
matrix[FL][SL] -= slev * SQRT1_2;
|
|
||||||
matrix[FL][SR] -= slev * SQRT1_2;
|
|
||||||
matrix[FR][SL] += slev * SQRT1_2;
|
|
||||||
matrix[FR][SR] += slev * SQRT1_2;
|
|
||||||
} else if (matrix_encoding == MATRIX_DPLII) {
|
|
||||||
matrix[FL][SL] -= slev * SQRT3_2;
|
|
||||||
matrix[FL][SR] -= slev * SQRT1_2;
|
|
||||||
matrix[FR][SL] += slev * SQRT1_2;
|
|
||||||
matrix[FR][SR] += slev * SQRT3_2;
|
|
||||||
} else {
|
|
||||||
matrix[FL][SL] += slev;
|
|
||||||
matrix[FR][SR] += slev;
|
|
||||||
}
|
|
||||||
} else if (dst_mask & _MASK(FC)) {
|
|
||||||
matrix[FC][SL] += slev * SQRT1_2;
|
|
||||||
matrix[FC][SR] += slev * SQRT1_2;
|
|
||||||
} else {
|
|
||||||
spa_log_warn(this->log, "can't assign SL");
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
if (unassigned & _MASK(FLC)) {
|
|
||||||
if (dst_mask & _MASK(FL)) {
|
|
||||||
matrix[FC][FLC]+= 1.0f;
|
|
||||||
matrix[FC][FRC]+= 1.0f;
|
|
||||||
} else if(dst_mask & _MASK(FC)) {
|
|
||||||
matrix[FC][FLC]+= SQRT1_2;
|
|
||||||
matrix[FC][FRC]+= SQRT1_2;
|
|
||||||
} else {
|
|
||||||
spa_log_warn(this->log, "can't assign FLC");
|
|
||||||
}
|
|
||||||
}
|
|
||||||
if (unassigned & _MASK(LFE)) {
|
|
||||||
if (dst_mask & _MASK(FC)) {
|
|
||||||
matrix[FC][LFE] += llev;
|
|
||||||
} else if (dst_mask & _MASK(FL)) {
|
|
||||||
matrix[FL][LFE] += llev * SQRT1_2;
|
|
||||||
matrix[FR][LFE] += llev * SQRT1_2;
|
|
||||||
} else {
|
|
||||||
spa_log_warn(this->log, "can't assign LFE");
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
c = 0;
|
|
||||||
for (i = 0; i < NUM_CHAN; i++) {
|
|
||||||
float sum = 0.0f;
|
|
||||||
if ((dst_mask & (1UL << (i + 2))) == 0)
|
|
||||||
continue;
|
|
||||||
for (j = 0; j < NUM_CHAN; j++) {
|
|
||||||
if ((src_mask & (1UL << (j + 2))) == 0)
|
|
||||||
continue;
|
|
||||||
this->matrix[c++] = matrix[i][j];
|
|
||||||
sum += fabs(matrix[i][j]);
|
|
||||||
}
|
|
||||||
max = SPA_MAX(max, sum);
|
|
||||||
}
|
|
||||||
this->n_matrix = c;
|
|
||||||
this->is_passthrough = dst_chan == src_chan;
|
|
||||||
for (i = 0; i < dst_chan; i++) {
|
|
||||||
for (j = 0; j < src_chan; j++) {
|
|
||||||
float v = this->matrix[i * src_chan + j];
|
|
||||||
spa_log_debug(this->log, "%d %d: %f", i, j, v);
|
|
||||||
if (i == j && v != 1.0f)
|
|
||||||
this->is_passthrough = false;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
return 0;
|
|
||||||
}
|
|
||||||
|
|
||||||
static int setup_convert(struct impl *this,
|
static int setup_convert(struct impl *this,
|
||||||
enum spa_direction direction,
|
enum spa_direction direction,
|
||||||
const struct spa_audio_info *info)
|
const struct spa_audio_info *info)
|
||||||
{
|
{
|
||||||
const struct spa_audio_info *src_info, *dst_info;
|
const struct spa_audio_info *src_info, *dst_info;
|
||||||
uint32_t i, src_chan, dst_chan;
|
uint32_t i, src_chan, dst_chan;
|
||||||
const struct channelmix_info *chanmix_info;
|
|
||||||
uint64_t src_mask, dst_mask;
|
uint64_t src_mask, dst_mask;
|
||||||
|
int res;
|
||||||
|
|
||||||
if (direction == SPA_DIRECTION_INPUT) {
|
if (direction == SPA_DIRECTION_INPUT) {
|
||||||
src_info = info;
|
src_info = info;
|
||||||
|
|
@ -431,17 +205,21 @@ static int setup_convert(struct impl *this,
|
||||||
if (src_info->info.raw.rate != dst_info->info.raw.rate)
|
if (src_info->info.raw.rate != dst_info->info.raw.rate)
|
||||||
return -EINVAL;
|
return -EINVAL;
|
||||||
|
|
||||||
/* find convert function */
|
this->mix.src_chan = src_chan;
|
||||||
if ((chanmix_info = find_channelmix_info(src_chan, src_mask,
|
this->mix.src_mask = src_mask;
|
||||||
dst_chan, dst_mask, this->cpu_flags)) == NULL)
|
this->mix.dst_chan = dst_chan;
|
||||||
return -ENOTSUP;
|
this->mix.dst_mask = dst_mask;
|
||||||
|
this->mix.cpu_flags = this->cpu_flags;
|
||||||
|
this->mix.log = this->log;
|
||||||
|
this->mix.volume = this->props.mute ? 0.0f : this->props.volume;
|
||||||
|
|
||||||
|
if ((res = channelmix_init(&this->mix)) < 0)
|
||||||
|
return res;
|
||||||
|
|
||||||
spa_log_info(this->log, NAME " %p: got channelmix features %08x:%08x",
|
spa_log_info(this->log, NAME " %p: got channelmix features %08x:%08x",
|
||||||
this, this->cpu_flags, chanmix_info->features);
|
this, this->cpu_flags, this->mix.cpu_flags);
|
||||||
|
|
||||||
this->convert = chanmix_info->func;
|
return 0;
|
||||||
|
|
||||||
return make_matrix(this, src_chan, src_mask, dst_chan, dst_mask);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
static int impl_node_enum_params(struct spa_node *node, int seq,
|
static int impl_node_enum_params(struct spa_node *node, int seq,
|
||||||
|
|
@ -544,6 +322,9 @@ static int apply_props(struct impl *this, const struct spa_pod *param)
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
if (changed)
|
||||||
|
this->mix.volume = p->mute ? 0.0f : p->volume;
|
||||||
|
|
||||||
return changed;
|
return changed;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -850,7 +631,7 @@ static int port_set_format(struct spa_node *node,
|
||||||
port->have_format = false;
|
port->have_format = false;
|
||||||
clear_buffers(this, port);
|
clear_buffers(this, port);
|
||||||
}
|
}
|
||||||
this->convert = NULL;
|
channelmix_free(&this->mix);
|
||||||
} else {
|
} else {
|
||||||
struct spa_audio_info info = { 0 };
|
struct spa_audio_info info = { 0 };
|
||||||
|
|
||||||
|
|
@ -1131,10 +912,11 @@ static int impl_node_process(struct spa_node *node)
|
||||||
const void *src_datas[n_src_datas];
|
const void *src_datas[n_src_datas];
|
||||||
void *dst_datas[n_dst_datas];
|
void *dst_datas[n_dst_datas];
|
||||||
bool is_passthrough;
|
bool is_passthrough;
|
||||||
float v;
|
|
||||||
|
|
||||||
v = this->props.mute ? 0.0f : this->props.volume;
|
is_passthrough = this->is_passthrough &&
|
||||||
is_passthrough = this->is_passthrough && v == 1.0f;
|
this->mix.volume == 1.0f &&
|
||||||
|
this->mix.is_identity;
|
||||||
|
|
||||||
n_samples = sb->datas[0].chunk->size / inport->stride;
|
n_samples = sb->datas[0].chunk->size / inport->stride;
|
||||||
|
|
||||||
for (i = 0; i < n_src_datas; i++)
|
for (i = 0; i < n_src_datas; i++)
|
||||||
|
|
@ -1146,9 +928,8 @@ static int impl_node_process(struct spa_node *node)
|
||||||
}
|
}
|
||||||
|
|
||||||
if (!is_passthrough)
|
if (!is_passthrough)
|
||||||
this->convert(this, n_dst_datas, dst_datas,
|
channelmix_process(&this->mix, n_dst_datas, dst_datas,
|
||||||
n_src_datas, src_datas,
|
n_src_datas, src_datas, n_samples);
|
||||||
this->matrix, v, n_samples);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
outio->status = SPA_STATUS_HAVE_BUFFER;
|
outio->status = SPA_STATUS_HAVE_BUFFER;
|
||||||
|
|
|
||||||
|
|
@ -33,66 +33,75 @@
|
||||||
#include "fmt-ops.h"
|
#include "fmt-ops.h"
|
||||||
|
|
||||||
void
|
void
|
||||||
conv_copy8d_c(void *data, void * SPA_RESTRICT dst[], const void * SPA_RESTRICT src[], uint32_t n_channels, uint32_t n_samples)
|
conv_copy8d_c(struct convert *conv, void * SPA_RESTRICT dst[], const void * SPA_RESTRICT src[],
|
||||||
|
uint32_t n_samples)
|
||||||
{
|
{
|
||||||
uint32_t i;
|
uint32_t i, n_channels = conv->n_channels;
|
||||||
for (i = 0; i < n_channels; i++)
|
for (i = 0; i < n_channels; i++)
|
||||||
spa_memcpy(dst[i], src[i], n_samples);
|
spa_memcpy(dst[i], src[i], n_samples);
|
||||||
}
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
conv_copy8_c(void *data, void * SPA_RESTRICT dst[], const void * SPA_RESTRICT src[], uint32_t n_channels, uint32_t n_samples)
|
conv_copy8_c(struct convert *conv, void * SPA_RESTRICT dst[], const void * SPA_RESTRICT src[],
|
||||||
|
uint32_t n_samples)
|
||||||
{
|
{
|
||||||
spa_memcpy(dst[0], src[0], n_samples * n_channels);
|
spa_memcpy(dst[0], src[0], n_samples * conv->n_channels);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
void
|
void
|
||||||
conv_copy16d_c(void *data, void * SPA_RESTRICT dst[], const void * SPA_RESTRICT src[], uint32_t n_channels, uint32_t n_samples)
|
conv_copy16d_c(struct convert *conv, void * SPA_RESTRICT dst[], const void * SPA_RESTRICT src[],
|
||||||
|
uint32_t n_samples)
|
||||||
{
|
{
|
||||||
uint32_t i;
|
uint32_t i, n_channels = conv->n_channels;
|
||||||
for (i = 0; i < n_channels; i++)
|
for (i = 0; i < n_channels; i++)
|
||||||
spa_memcpy(dst[i], src[i], n_samples * sizeof(int16_t));
|
spa_memcpy(dst[i], src[i], n_samples * sizeof(int16_t));
|
||||||
}
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
conv_copy16_c(void *data, void * SPA_RESTRICT dst[], const void * SPA_RESTRICT src[], uint32_t n_channels, uint32_t n_samples)
|
conv_copy16_c(struct convert *conv, void * SPA_RESTRICT dst[], const void * SPA_RESTRICT src[],
|
||||||
|
uint32_t n_samples)
|
||||||
{
|
{
|
||||||
spa_memcpy(dst[0], src[0], n_samples * sizeof(int16_t) * n_channels);
|
spa_memcpy(dst[0], src[0], n_samples * sizeof(int16_t) * conv->n_channels);
|
||||||
}
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
conv_copy24d_c(void *data, void * SPA_RESTRICT dst[], const void * SPA_RESTRICT src[], uint32_t n_channels, uint32_t n_samples)
|
conv_copy24d_c(struct convert *conv, void * SPA_RESTRICT dst[], const void * SPA_RESTRICT src[],
|
||||||
|
uint32_t n_samples)
|
||||||
{
|
{
|
||||||
uint32_t i;
|
uint32_t i, n_channels = conv->n_channels;
|
||||||
for (i = 0; i < n_channels; i++)
|
for (i = 0; i < n_channels; i++)
|
||||||
spa_memcpy(dst[i], src[i], n_samples * 3);
|
spa_memcpy(dst[i], src[i], n_samples * 3);
|
||||||
}
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
conv_copy24_c(void *data, void * SPA_RESTRICT dst[], const void * SPA_RESTRICT src[], uint32_t n_channels, uint32_t n_samples)
|
conv_copy24_c(struct convert *conv, void * SPA_RESTRICT dst[], const void * SPA_RESTRICT src[],
|
||||||
|
uint32_t n_samples)
|
||||||
{
|
{
|
||||||
spa_memcpy(dst[0], src[0], n_samples * 3 * n_channels);
|
spa_memcpy(dst[0], src[0], n_samples * 3 * conv->n_channels);
|
||||||
}
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
conv_copy32d_c(void *data, void * SPA_RESTRICT dst[], const void * SPA_RESTRICT src[], uint32_t n_channels, uint32_t n_samples)
|
conv_copy32d_c(struct convert *conv, void * SPA_RESTRICT dst[], const void * SPA_RESTRICT src[],
|
||||||
|
uint32_t n_samples)
|
||||||
{
|
{
|
||||||
uint32_t i;
|
uint32_t i, n_channels = conv->n_channels;
|
||||||
for (i = 0; i < n_channels; i++)
|
for (i = 0; i < n_channels; i++)
|
||||||
spa_memcpy(dst[i], src[i], n_samples * sizeof(int32_t));
|
spa_memcpy(dst[i], src[i], n_samples * sizeof(int32_t));
|
||||||
}
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
conv_copy32_c(void *data, void * SPA_RESTRICT dst[], const void * SPA_RESTRICT src[], uint32_t n_channels, uint32_t n_samples)
|
conv_copy32_c(struct convert *conv, void * SPA_RESTRICT dst[], const void * SPA_RESTRICT src[],
|
||||||
|
uint32_t n_samples)
|
||||||
{
|
{
|
||||||
spa_memcpy(dst[0], src[0], n_samples * sizeof(int32_t) * n_channels);
|
spa_memcpy(dst[0], src[0], n_samples * sizeof(int32_t) * conv->n_channels);
|
||||||
}
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
conv_u8d_to_f32d_c(void *data, void * SPA_RESTRICT dst[], const void * SPA_RESTRICT src[], uint32_t n_channels, uint32_t n_samples)
|
conv_u8d_to_f32d_c(struct convert *conv, void * SPA_RESTRICT dst[], const void * SPA_RESTRICT src[],
|
||||||
|
uint32_t n_samples)
|
||||||
{
|
{
|
||||||
uint32_t i, j;
|
uint32_t i, j, n_channels = conv->n_channels;
|
||||||
|
|
||||||
for (i = 0; i < n_channels; i++) {
|
for (i = 0; i < n_channels; i++) {
|
||||||
const uint8_t *s = src[i];
|
const uint8_t *s = src[i];
|
||||||
|
|
@ -104,17 +113,26 @@ conv_u8d_to_f32d_c(void *data, void * SPA_RESTRICT dst[], const void * SPA_RESTR
|
||||||
}
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
conv_u8_to_f32_c(void *data, void * SPA_RESTRICT dst[], const void * SPA_RESTRICT src[], uint32_t n_channels, uint32_t n_samples)
|
conv_u8_to_f32_c(struct convert *conv, void * SPA_RESTRICT dst[], const void * SPA_RESTRICT src[],
|
||||||
|
uint32_t n_samples)
|
||||||
{
|
{
|
||||||
conv_u8d_to_f32d_c(data, dst, src, 1, n_samples * n_channels);
|
uint32_t i, n_channels = conv->n_channels;;
|
||||||
|
const uint8_t *s = src[0];
|
||||||
|
float *d = dst[0];
|
||||||
|
|
||||||
|
n_samples *= n_channels;
|
||||||
|
|
||||||
|
for (i = 0; i < n_samples; i++)
|
||||||
|
d[i] = U8_TO_F32(s[i]);
|
||||||
}
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
conv_u8_to_f32d_c(void *data, void * SPA_RESTRICT dst[], const void * SPA_RESTRICT src[], uint32_t n_channels, uint32_t n_samples)
|
conv_u8_to_f32d_c(struct convert *conv, void * SPA_RESTRICT dst[], const void * SPA_RESTRICT src[],
|
||||||
|
uint32_t n_samples)
|
||||||
{
|
{
|
||||||
const uint8_t *s = src[0];
|
const uint8_t *s = src[0];
|
||||||
float **d = (float **) dst;
|
float **d = (float **) dst;
|
||||||
uint32_t i, j;
|
uint32_t i, j, n_channels = conv->n_channels;
|
||||||
|
|
||||||
for (j = 0; j < n_samples; j++) {
|
for (j = 0; j < n_samples; j++) {
|
||||||
for (i = 0; i < n_channels; i++)
|
for (i = 0; i < n_channels; i++)
|
||||||
|
|
@ -123,11 +141,12 @@ conv_u8_to_f32d_c(void *data, void * SPA_RESTRICT dst[], const void * SPA_RESTRI
|
||||||
}
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
conv_u8d_to_f32_c(void *data, void * SPA_RESTRICT dst[], const void * SPA_RESTRICT src[], uint32_t n_channels, uint32_t n_samples)
|
conv_u8d_to_f32_c(struct convert *conv, void * SPA_RESTRICT dst[], const void * SPA_RESTRICT src[],
|
||||||
|
uint32_t n_samples)
|
||||||
{
|
{
|
||||||
const uint8_t **s = (const uint8_t **) src;
|
const uint8_t **s = (const uint8_t **) src;
|
||||||
float *d = dst[0];
|
float *d = dst[0];
|
||||||
uint32_t i, j;
|
uint32_t i, j, n_channels = conv->n_channels;
|
||||||
|
|
||||||
for (j = 0; j < n_samples; j++) {
|
for (j = 0; j < n_samples; j++) {
|
||||||
for (i = 0; i < n_channels; i++)
|
for (i = 0; i < n_channels; i++)
|
||||||
|
|
@ -136,9 +155,10 @@ conv_u8d_to_f32_c(void *data, void * SPA_RESTRICT dst[], const void * SPA_RESTRI
|
||||||
}
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
conv_s16d_to_f32d_c(void *data, void * SPA_RESTRICT dst[], const void * SPA_RESTRICT src[], uint32_t n_channels, uint32_t n_samples)
|
conv_s16d_to_f32d_c(struct convert *conv, void * SPA_RESTRICT dst[], const void * SPA_RESTRICT src[],
|
||||||
|
uint32_t n_samples)
|
||||||
{
|
{
|
||||||
uint32_t i, j;
|
uint32_t i, j, n_channels = conv->n_channels;
|
||||||
|
|
||||||
for (i = 0; i < n_channels; i++) {
|
for (i = 0; i < n_channels; i++) {
|
||||||
const int16_t *s = src[i];
|
const int16_t *s = src[i];
|
||||||
|
|
@ -149,17 +169,26 @@ conv_s16d_to_f32d_c(void *data, void * SPA_RESTRICT dst[], const void * SPA_REST
|
||||||
}
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
conv_s16_to_f32_c(void *data, void * SPA_RESTRICT dst[], const void * SPA_RESTRICT src[], uint32_t n_channels, uint32_t n_samples)
|
conv_s16_to_f32_c(struct convert *conv, void * SPA_RESTRICT dst[], const void * SPA_RESTRICT src[],
|
||||||
|
uint32_t n_samples)
|
||||||
{
|
{
|
||||||
conv_s16d_to_f32d_c(data, dst, src, 1, n_samples * n_channels);
|
uint32_t i, n_channels = conv->n_channels;
|
||||||
|
const int16_t *s = src[0];
|
||||||
|
float *d = dst[0];
|
||||||
|
|
||||||
|
n_samples *= n_channels;
|
||||||
|
|
||||||
|
for (i = 0; i < n_samples; i++)
|
||||||
|
d[i] = S16_TO_F32(s[i]);
|
||||||
}
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
conv_s16_to_f32d_c(void *data, void * SPA_RESTRICT dst[], const void * SPA_RESTRICT src[], uint32_t n_channels, uint32_t n_samples)
|
conv_s16_to_f32d_c(struct convert *conv, void * SPA_RESTRICT dst[], const void * SPA_RESTRICT src[],
|
||||||
|
uint32_t n_samples)
|
||||||
{
|
{
|
||||||
const int16_t *s = src[0];
|
const int16_t *s = src[0];
|
||||||
float **d = (float **) dst;
|
float **d = (float **) dst;
|
||||||
uint32_t i, j;
|
uint32_t i, j, n_channels = conv->n_channels;
|
||||||
|
|
||||||
for (j = 0; j < n_samples; j++) {
|
for (j = 0; j < n_samples; j++) {
|
||||||
for (i = 0; i < n_channels; i++)
|
for (i = 0; i < n_channels; i++)
|
||||||
|
|
@ -168,11 +197,12 @@ conv_s16_to_f32d_c(void *data, void * SPA_RESTRICT dst[], const void * SPA_RESTR
|
||||||
}
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
conv_s16d_to_f32_c(void *data, void * SPA_RESTRICT dst[], const void * SPA_RESTRICT src[], uint32_t n_channels, uint32_t n_samples)
|
conv_s16d_to_f32_c(struct convert *conv, void * SPA_RESTRICT dst[], const void * SPA_RESTRICT src[],
|
||||||
|
uint32_t n_samples)
|
||||||
{
|
{
|
||||||
const int16_t **s = (const int16_t **) src;
|
const int16_t **s = (const int16_t **) src;
|
||||||
float *d = dst[0];
|
float *d = dst[0];
|
||||||
uint32_t i, j;
|
uint32_t i, j, n_channels = conv->n_channels;
|
||||||
|
|
||||||
for (j = 0; j < n_samples; j++) {
|
for (j = 0; j < n_samples; j++) {
|
||||||
for (i = 0; i < n_channels; i++)
|
for (i = 0; i < n_channels; i++)
|
||||||
|
|
@ -181,9 +211,10 @@ conv_s16d_to_f32_c(void *data, void * SPA_RESTRICT dst[], const void * SPA_RESTR
|
||||||
}
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
conv_s32d_to_f32d_c(void *data, void * SPA_RESTRICT dst[], const void * SPA_RESTRICT src[], uint32_t n_channels, uint32_t n_samples)
|
conv_s32d_to_f32d_c(struct convert *conv, void * SPA_RESTRICT dst[], const void * SPA_RESTRICT src[],
|
||||||
|
uint32_t n_samples)
|
||||||
{
|
{
|
||||||
uint32_t i, j;
|
uint32_t i, j, n_channels = conv->n_channels;
|
||||||
|
|
||||||
for (i = 0; i < n_channels; i++) {
|
for (i = 0; i < n_channels; i++) {
|
||||||
const int32_t *s = src[i];
|
const int32_t *s = src[i];
|
||||||
|
|
@ -195,17 +226,26 @@ conv_s32d_to_f32d_c(void *data, void * SPA_RESTRICT dst[], const void * SPA_REST
|
||||||
}
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
conv_s32_to_f32_c(void *data, void * SPA_RESTRICT dst[], const void * SPA_RESTRICT src[], uint32_t n_channels, uint32_t n_samples)
|
conv_s32_to_f32_c(struct convert *conv, void * SPA_RESTRICT dst[], const void * SPA_RESTRICT src[],
|
||||||
|
uint32_t n_samples)
|
||||||
{
|
{
|
||||||
conv_s32d_to_f32d_c(data, dst, src, 1, n_samples * n_channels);
|
uint32_t i, n_channels = conv->n_channels;
|
||||||
|
const int32_t *s = src[0];
|
||||||
|
float *d = dst[0];
|
||||||
|
|
||||||
|
n_samples *= n_channels;
|
||||||
|
|
||||||
|
for (i = 0; i < n_samples; i++)
|
||||||
|
d[i] = S32_TO_F32(s[i]);
|
||||||
}
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
conv_s32_to_f32d_c(void *data, void * SPA_RESTRICT dst[], const void * SPA_RESTRICT src[], uint32_t n_channels, uint32_t n_samples)
|
conv_s32_to_f32d_c(struct convert *conv, void * SPA_RESTRICT dst[], const void * SPA_RESTRICT src[],
|
||||||
|
uint32_t n_samples)
|
||||||
{
|
{
|
||||||
const int32_t *s = src[0];
|
const int32_t *s = src[0];
|
||||||
float **d = (float **) dst;
|
float **d = (float **) dst;
|
||||||
uint32_t i, j;
|
uint32_t i, j, n_channels = conv->n_channels;
|
||||||
|
|
||||||
for (j = 0; j < n_samples; j++) {
|
for (j = 0; j < n_samples; j++) {
|
||||||
for (i = 0; i < n_channels; i++)
|
for (i = 0; i < n_channels; i++)
|
||||||
|
|
@ -214,11 +254,12 @@ conv_s32_to_f32d_c(void *data, void * SPA_RESTRICT dst[], const void * SPA_RESTR
|
||||||
}
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
conv_s32d_to_f32_c(void *data, void * SPA_RESTRICT dst[], const void * SPA_RESTRICT src[], uint32_t n_channels, uint32_t n_samples)
|
conv_s32d_to_f32_c(struct convert *conv, void * SPA_RESTRICT dst[], const void * SPA_RESTRICT src[],
|
||||||
|
uint32_t n_samples)
|
||||||
{
|
{
|
||||||
const int32_t **s = (const int32_t **) src;
|
const int32_t **s = (const int32_t **) src;
|
||||||
float *d = dst[0];
|
float *d = dst[0];
|
||||||
uint32_t i, j;
|
uint32_t i, j, n_channels = conv->n_channels;
|
||||||
|
|
||||||
for (j = 0; j < n_samples; j++) {
|
for (j = 0; j < n_samples; j++) {
|
||||||
for (i = 0; i < n_channels; i++)
|
for (i = 0; i < n_channels; i++)
|
||||||
|
|
@ -227,9 +268,10 @@ conv_s32d_to_f32_c(void *data, void * SPA_RESTRICT dst[], const void * SPA_RESTR
|
||||||
}
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
conv_s24d_to_f32d_c(void *data, void * SPA_RESTRICT dst[], const void * SPA_RESTRICT src[], uint32_t n_channels, uint32_t n_samples)
|
conv_s24d_to_f32d_c(struct convert *conv, void * SPA_RESTRICT dst[], const void * SPA_RESTRICT src[],
|
||||||
|
uint32_t n_samples)
|
||||||
{
|
{
|
||||||
uint32_t i, j;
|
uint32_t i, j, n_channels = conv->n_channels;
|
||||||
|
|
||||||
for (i = 0; i < n_channels; i++) {
|
for (i = 0; i < n_channels; i++) {
|
||||||
const int8_t *s = src[i];
|
const int8_t *s = src[i];
|
||||||
|
|
@ -243,17 +285,28 @@ conv_s24d_to_f32d_c(void *data, void * SPA_RESTRICT dst[], const void * SPA_REST
|
||||||
}
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
conv_s24_to_f32_c(void *data, void * SPA_RESTRICT dst[], const void * SPA_RESTRICT src[], uint32_t n_channels, uint32_t n_samples)
|
conv_s24_to_f32_c(struct convert *conv, void * SPA_RESTRICT dst[], const void * SPA_RESTRICT src[],
|
||||||
|
uint32_t n_samples)
|
||||||
{
|
{
|
||||||
conv_s24d_to_f32d_c(data, dst, src, 1, n_samples * n_channels);
|
uint32_t i, n_channels = conv->n_channels;
|
||||||
|
const int8_t *s = src[0];
|
||||||
|
float *d = dst[0];
|
||||||
|
|
||||||
|
n_samples *= n_channels;
|
||||||
|
|
||||||
|
for (i = 0; i < n_samples; i++) {
|
||||||
|
d[i] = S24_TO_F32(read_s24(s));
|
||||||
|
s += 3;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
conv_s24_to_f32d_c(void *data, void * SPA_RESTRICT dst[], const void * SPA_RESTRICT src[], uint32_t n_channels, uint32_t n_samples)
|
conv_s24_to_f32d_c(struct convert *conv, void * SPA_RESTRICT dst[], const void * SPA_RESTRICT src[],
|
||||||
|
uint32_t n_samples)
|
||||||
{
|
{
|
||||||
const uint8_t *s = src[0];
|
const uint8_t *s = src[0];
|
||||||
float **d = (float **) dst;
|
float **d = (float **) dst;
|
||||||
uint32_t i, j;
|
uint32_t i, j, n_channels = conv->n_channels;
|
||||||
|
|
||||||
for (j = 0; j < n_samples; j++) {
|
for (j = 0; j < n_samples; j++) {
|
||||||
for (i = 0; i < n_channels; i++) {
|
for (i = 0; i < n_channels; i++) {
|
||||||
|
|
@ -264,11 +317,12 @@ conv_s24_to_f32d_c(void *data, void * SPA_RESTRICT dst[], const void * SPA_RESTR
|
||||||
}
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
conv_s24d_to_f32_c(void *data, void * SPA_RESTRICT dst[], const void * SPA_RESTRICT src[], uint32_t n_channels, uint32_t n_samples)
|
conv_s24d_to_f32_c(struct convert *conv, void * SPA_RESTRICT dst[], const void * SPA_RESTRICT src[],
|
||||||
|
uint32_t n_samples)
|
||||||
{
|
{
|
||||||
const uint8_t **s = (const uint8_t **) src;
|
const uint8_t **s = (const uint8_t **) src;
|
||||||
float *d = dst[0];
|
float *d = dst[0];
|
||||||
uint32_t i, j;
|
uint32_t i, j, n_channels = conv->n_channels;
|
||||||
|
|
||||||
for (j = 0; j < n_samples; j++) {
|
for (j = 0; j < n_samples; j++) {
|
||||||
for (i = 0; i < n_channels; i++) {
|
for (i = 0; i < n_channels; i++) {
|
||||||
|
|
@ -278,9 +332,10 @@ conv_s24d_to_f32_c(void *data, void * SPA_RESTRICT dst[], const void * SPA_RESTR
|
||||||
}
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
conv_s24_32d_to_f32d_c(void *data, void * SPA_RESTRICT dst[], const void * SPA_RESTRICT src[], uint32_t n_channels, uint32_t n_samples)
|
conv_s24_32d_to_f32d_c(struct convert *conv, void * SPA_RESTRICT dst[], const void * SPA_RESTRICT src[],
|
||||||
|
uint32_t n_samples)
|
||||||
{
|
{
|
||||||
uint32_t i, j;
|
uint32_t i, j, n_channels = conv->n_channels;
|
||||||
|
|
||||||
for (i = 0; i < n_channels; i++) {
|
for (i = 0; i < n_channels; i++) {
|
||||||
const int32_t *s = src[i];
|
const int32_t *s = src[i];
|
||||||
|
|
@ -292,17 +347,26 @@ conv_s24_32d_to_f32d_c(void *data, void * SPA_RESTRICT dst[], const void * SPA_R
|
||||||
}
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
conv_s24_32_to_f32_c(void *data, void * SPA_RESTRICT dst[], const void * SPA_RESTRICT src[], uint32_t n_channels, uint32_t n_samples)
|
conv_s24_32_to_f32_c(struct convert *conv, void * SPA_RESTRICT dst[], const void * SPA_RESTRICT src[],
|
||||||
|
uint32_t n_samples)
|
||||||
{
|
{
|
||||||
conv_s24_32d_to_f32d_c(data, dst, src, 1, n_samples * n_channels);
|
uint32_t i, n_channels = conv->n_channels;
|
||||||
|
const int32_t *s = src[0];
|
||||||
|
float *d = dst[0];
|
||||||
|
|
||||||
|
n_samples *= n_channels;
|
||||||
|
|
||||||
|
for (i = 0; i < n_samples; i++)
|
||||||
|
d[i] = S24_TO_F32(s[i]);
|
||||||
}
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
conv_s24_32_to_f32d_c(void *data, void * SPA_RESTRICT dst[], const void * SPA_RESTRICT src[], uint32_t n_channels, uint32_t n_samples)
|
conv_s24_32_to_f32d_c(struct convert *conv, void * SPA_RESTRICT dst[], const void * SPA_RESTRICT src[],
|
||||||
|
uint32_t n_samples)
|
||||||
{
|
{
|
||||||
const int32_t *s = src[0];
|
const int32_t *s = src[0];
|
||||||
float **d = (float **) dst;
|
float **d = (float **) dst;
|
||||||
uint32_t i, j;
|
uint32_t i, j, n_channels = conv->n_channels;
|
||||||
|
|
||||||
for (j = 0; j < n_samples; j++) {
|
for (j = 0; j < n_samples; j++) {
|
||||||
for (i = 0; i < n_channels; i++)
|
for (i = 0; i < n_channels; i++)
|
||||||
|
|
@ -311,11 +375,12 @@ conv_s24_32_to_f32d_c(void *data, void * SPA_RESTRICT dst[], const void * SPA_RE
|
||||||
}
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
conv_s24_32d_to_f32_c(void *data, void * SPA_RESTRICT dst[], const void * SPA_RESTRICT src[], uint32_t n_channels, uint32_t n_samples)
|
conv_s24_32d_to_f32_c(struct convert *conv, void * SPA_RESTRICT dst[], const void * SPA_RESTRICT src[],
|
||||||
|
uint32_t n_samples)
|
||||||
{
|
{
|
||||||
const int32_t **s = (const int32_t **) src;
|
const int32_t **s = (const int32_t **) src;
|
||||||
float *d = dst[0];
|
float *d = dst[0];
|
||||||
uint32_t i, j;
|
uint32_t i, j, n_channels = conv->n_channels;
|
||||||
|
|
||||||
for (j = 0; j < n_samples; j++) {
|
for (j = 0; j < n_samples; j++) {
|
||||||
for (i = 0; i < n_channels; i++)
|
for (i = 0; i < n_channels; i++)
|
||||||
|
|
@ -324,9 +389,10 @@ conv_s24_32d_to_f32_c(void *data, void * SPA_RESTRICT dst[], const void * SPA_RE
|
||||||
}
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
conv_f32d_to_u8d_c(void *data, void * SPA_RESTRICT dst[], const void * SPA_RESTRICT src[], uint32_t n_channels, uint32_t n_samples)
|
conv_f32d_to_u8d_c(struct convert *conv, void * SPA_RESTRICT dst[], const void * SPA_RESTRICT src[],
|
||||||
|
uint32_t n_samples)
|
||||||
{
|
{
|
||||||
uint32_t i, j;
|
uint32_t i, j, n_channels = conv->n_channels;
|
||||||
|
|
||||||
for (i = 0; i < n_channels; i++) {
|
for (i = 0; i < n_channels; i++) {
|
||||||
const float *s = src[i];
|
const float *s = src[i];
|
||||||
|
|
@ -338,17 +404,26 @@ conv_f32d_to_u8d_c(void *data, void * SPA_RESTRICT dst[], const void * SPA_RESTR
|
||||||
}
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
conv_f32_to_u8_c(void *data, void * SPA_RESTRICT dst[], const void * SPA_RESTRICT src[], uint32_t n_channels, uint32_t n_samples)
|
conv_f32_to_u8_c(struct convert *conv, void * SPA_RESTRICT dst[], const void * SPA_RESTRICT src[],
|
||||||
|
uint32_t n_samples)
|
||||||
{
|
{
|
||||||
conv_f32d_to_u8d_c(data, dst, src, 1, n_samples * n_channels);
|
uint32_t i, n_channels = conv->n_channels;
|
||||||
|
const float *s = src[0];
|
||||||
|
uint8_t *d = dst[0];
|
||||||
|
|
||||||
|
n_samples *= n_channels;
|
||||||
|
|
||||||
|
for (i = 0; i < n_samples; i++)
|
||||||
|
d[i] = F32_TO_U8(s[i]);
|
||||||
}
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
conv_f32_to_u8d_c(void *data, void * SPA_RESTRICT dst[], const void * SPA_RESTRICT src[], uint32_t n_channels, uint32_t n_samples)
|
conv_f32_to_u8d_c(struct convert *conv, void * SPA_RESTRICT dst[], const void * SPA_RESTRICT src[],
|
||||||
|
uint32_t n_samples)
|
||||||
{
|
{
|
||||||
const float *s = src[0];
|
const float *s = src[0];
|
||||||
uint8_t **d = (uint8_t **) dst;
|
uint8_t **d = (uint8_t **) dst;
|
||||||
uint32_t i, j;
|
uint32_t i, j, n_channels = conv->n_channels;
|
||||||
|
|
||||||
for (j = 0; j < n_samples; j++) {
|
for (j = 0; j < n_samples; j++) {
|
||||||
for (i = 0; i < n_channels; i++)
|
for (i = 0; i < n_channels; i++)
|
||||||
|
|
@ -357,11 +432,12 @@ conv_f32_to_u8d_c(void *data, void * SPA_RESTRICT dst[], const void * SPA_RESTRI
|
||||||
}
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
conv_f32d_to_u8_c(void *data, void * SPA_RESTRICT dst[], const void * SPA_RESTRICT src[], uint32_t n_channels, uint32_t n_samples)
|
conv_f32d_to_u8_c(struct convert *conv, void * SPA_RESTRICT dst[], const void * SPA_RESTRICT src[],
|
||||||
|
uint32_t n_samples)
|
||||||
{
|
{
|
||||||
const float **s = (const float **) src;
|
const float **s = (const float **) src;
|
||||||
uint8_t *d = dst[0];
|
uint8_t *d = dst[0];
|
||||||
uint32_t i, j;
|
uint32_t i, j, n_channels = conv->n_channels;
|
||||||
|
|
||||||
for (j = 0; j < n_samples; j++) {
|
for (j = 0; j < n_samples; j++) {
|
||||||
for (i = 0; i < n_channels; i++)
|
for (i = 0; i < n_channels; i++)
|
||||||
|
|
@ -370,9 +446,10 @@ conv_f32d_to_u8_c(void *data, void * SPA_RESTRICT dst[], const void * SPA_RESTRI
|
||||||
}
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
conv_f32d_to_s16d_c(void *data, void * SPA_RESTRICT dst[], const void * SPA_RESTRICT src[], uint32_t n_channels, uint32_t n_samples)
|
conv_f32d_to_s16d_c(struct convert *conv, void * SPA_RESTRICT dst[], const void * SPA_RESTRICT src[],
|
||||||
|
uint32_t n_samples)
|
||||||
{
|
{
|
||||||
uint32_t i, j;
|
uint32_t i, j, n_channels = conv->n_channels;
|
||||||
|
|
||||||
for (i = 0; i < n_channels; i++) {
|
for (i = 0; i < n_channels; i++) {
|
||||||
const float *s = src[i];
|
const float *s = src[i];
|
||||||
|
|
@ -384,17 +461,26 @@ conv_f32d_to_s16d_c(void *data, void * SPA_RESTRICT dst[], const void * SPA_REST
|
||||||
}
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
conv_f32_to_s16_c(void *data, void * SPA_RESTRICT dst[], const void * SPA_RESTRICT src[], uint32_t n_channels, uint32_t n_samples)
|
conv_f32_to_s16_c(struct convert *conv, void * SPA_RESTRICT dst[], const void * SPA_RESTRICT src[],
|
||||||
|
uint32_t n_samples)
|
||||||
{
|
{
|
||||||
conv_f32d_to_s16d_c(data, dst, src, 1, n_samples * n_channels);
|
uint32_t i, n_channels = conv->n_channels;
|
||||||
|
const float *s = src[0];
|
||||||
|
int16_t *d = dst[0];
|
||||||
|
|
||||||
|
n_samples *= n_channels;
|
||||||
|
|
||||||
|
for (i = 0; i < n_samples; i++)
|
||||||
|
d[i] = F32_TO_S16(s[i]);
|
||||||
}
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
conv_f32_to_s16d_c(void *data, void * SPA_RESTRICT dst[], const void * SPA_RESTRICT src[], uint32_t n_channels, uint32_t n_samples)
|
conv_f32_to_s16d_c(struct convert *conv, void * SPA_RESTRICT dst[], const void * SPA_RESTRICT src[],
|
||||||
|
uint32_t n_samples)
|
||||||
{
|
{
|
||||||
const float *s = src[0];
|
const float *s = src[0];
|
||||||
int16_t **d = (int16_t **) dst;
|
int16_t **d = (int16_t **) dst;
|
||||||
uint32_t i, j;
|
uint32_t i, j, n_channels = conv->n_channels;
|
||||||
|
|
||||||
for (j = 0; j < n_samples; j++) {
|
for (j = 0; j < n_samples; j++) {
|
||||||
for (i = 0; i < n_channels; i++)
|
for (i = 0; i < n_channels; i++)
|
||||||
|
|
@ -403,11 +489,12 @@ conv_f32_to_s16d_c(void *data, void * SPA_RESTRICT dst[], const void * SPA_RESTR
|
||||||
}
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
conv_f32d_to_s16_c(void *data, void * SPA_RESTRICT dst[], const void * SPA_RESTRICT src[], uint32_t n_channels, uint32_t n_samples)
|
conv_f32d_to_s16_c(struct convert *conv, void * SPA_RESTRICT dst[], const void * SPA_RESTRICT src[],
|
||||||
|
uint32_t n_samples)
|
||||||
{
|
{
|
||||||
const float **s = (const float **) src;
|
const float **s = (const float **) src;
|
||||||
int16_t *d = dst[0];
|
int16_t *d = dst[0];
|
||||||
uint32_t i, j;
|
uint32_t i, j, n_channels = conv->n_channels;
|
||||||
|
|
||||||
for (j = 0; j < n_samples; j++) {
|
for (j = 0; j < n_samples; j++) {
|
||||||
for (i = 0; i < n_channels; i++)
|
for (i = 0; i < n_channels; i++)
|
||||||
|
|
@ -416,9 +503,10 @@ conv_f32d_to_s16_c(void *data, void * SPA_RESTRICT dst[], const void * SPA_RESTR
|
||||||
}
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
conv_f32d_to_s32d_c(void *data, void * SPA_RESTRICT dst[], const void * SPA_RESTRICT src[], uint32_t n_channels, uint32_t n_samples)
|
conv_f32d_to_s32d_c(struct convert *conv, void * SPA_RESTRICT dst[], const void * SPA_RESTRICT src[],
|
||||||
|
uint32_t n_samples)
|
||||||
{
|
{
|
||||||
uint32_t i, j;
|
uint32_t i, j, n_channels = conv->n_channels;
|
||||||
|
|
||||||
for (i = 0; i < n_channels; i++) {
|
for (i = 0; i < n_channels; i++) {
|
||||||
const float *s = src[i];
|
const float *s = src[i];
|
||||||
|
|
@ -430,17 +518,26 @@ conv_f32d_to_s32d_c(void *data, void * SPA_RESTRICT dst[], const void * SPA_REST
|
||||||
}
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
conv_f32_to_s32_c(void *data, void * SPA_RESTRICT dst[], const void * SPA_RESTRICT src[], uint32_t n_channels, uint32_t n_samples)
|
conv_f32_to_s32_c(struct convert *conv, void * SPA_RESTRICT dst[], const void * SPA_RESTRICT src[],
|
||||||
|
uint32_t n_samples)
|
||||||
{
|
{
|
||||||
conv_f32d_to_s32d_c(data, dst, src, 1, n_samples * n_channels);
|
uint32_t i, n_channels = conv->n_channels;
|
||||||
|
const float *s = src[0];
|
||||||
|
int32_t *d = dst[0];
|
||||||
|
|
||||||
|
n_samples *= n_channels;
|
||||||
|
|
||||||
|
for (i = 0; i < n_samples; i++)
|
||||||
|
d[i] = F32_TO_S32(s[i]);
|
||||||
}
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
conv_f32_to_s32d_c(void *data, void * SPA_RESTRICT dst[], const void * SPA_RESTRICT src[], uint32_t n_channels, uint32_t n_samples)
|
conv_f32_to_s32d_c(struct convert *conv, void * SPA_RESTRICT dst[], const void * SPA_RESTRICT src[],
|
||||||
|
uint32_t n_samples)
|
||||||
{
|
{
|
||||||
const float *s = src[0];
|
const float *s = src[0];
|
||||||
int32_t **d = (int32_t **) dst;
|
int32_t **d = (int32_t **) dst;
|
||||||
uint32_t i, j;
|
uint32_t i, j, n_channels = conv->n_channels;
|
||||||
|
|
||||||
for (j = 0; j < n_samples; j++) {
|
for (j = 0; j < n_samples; j++) {
|
||||||
for (i = 0; i < n_channels; i++)
|
for (i = 0; i < n_channels; i++)
|
||||||
|
|
@ -449,11 +546,12 @@ conv_f32_to_s32d_c(void *data, void * SPA_RESTRICT dst[], const void * SPA_RESTR
|
||||||
}
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
conv_f32d_to_s32_c(void *data, void * SPA_RESTRICT dst[], const void * SPA_RESTRICT src[], uint32_t n_channels, uint32_t n_samples)
|
conv_f32d_to_s32_c(struct convert *conv, void * SPA_RESTRICT dst[], const void * SPA_RESTRICT src[],
|
||||||
|
uint32_t n_samples)
|
||||||
{
|
{
|
||||||
const float **s = (const float **) src;
|
const float **s = (const float **) src;
|
||||||
int32_t *d = dst[0];
|
int32_t *d = dst[0];
|
||||||
uint32_t i, j;
|
uint32_t i, j, n_channels = conv->n_channels;
|
||||||
|
|
||||||
for (j = 0; j < n_samples; j++) {
|
for (j = 0; j < n_samples; j++) {
|
||||||
for (i = 0; i < n_channels; i++)
|
for (i = 0; i < n_channels; i++)
|
||||||
|
|
@ -464,9 +562,10 @@ conv_f32d_to_s32_c(void *data, void * SPA_RESTRICT dst[], const void * SPA_RESTR
|
||||||
|
|
||||||
|
|
||||||
void
|
void
|
||||||
conv_f32d_to_s24d_c(void *data, void * SPA_RESTRICT dst[], const void * SPA_RESTRICT src[], uint32_t n_channels, uint32_t n_samples)
|
conv_f32d_to_s24d_c(struct convert *conv, void * SPA_RESTRICT dst[], const void * SPA_RESTRICT src[],
|
||||||
|
uint32_t n_samples)
|
||||||
{
|
{
|
||||||
uint32_t i, j;
|
uint32_t i, j, n_channels = conv->n_channels;
|
||||||
|
|
||||||
for (i = 0; i < n_channels; i++) {
|
for (i = 0; i < n_channels; i++) {
|
||||||
const float *s = src[i];
|
const float *s = src[i];
|
||||||
|
|
@ -480,17 +579,28 @@ conv_f32d_to_s24d_c(void *data, void * SPA_RESTRICT dst[], const void * SPA_REST
|
||||||
}
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
conv_f32_to_s24_c(void *data, void * SPA_RESTRICT dst[], const void * SPA_RESTRICT src[], uint32_t n_channels, uint32_t n_samples)
|
conv_f32_to_s24_c(struct convert *conv, void * SPA_RESTRICT dst[], const void * SPA_RESTRICT src[],
|
||||||
|
uint32_t n_samples)
|
||||||
{
|
{
|
||||||
conv_f32d_to_s24d_c(data, dst, src, 1, n_samples * n_channels);
|
uint32_t i, n_channels = conv->n_channels;
|
||||||
|
const float *s = src[0];
|
||||||
|
uint8_t *d = dst[0];
|
||||||
|
|
||||||
|
n_samples *= n_channels;
|
||||||
|
|
||||||
|
for (i = 0; i < n_samples; i++) {
|
||||||
|
write_s24(d, F32_TO_S24(s[i]));
|
||||||
|
d += 3;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
conv_f32_to_s24d_c(void *data, void * SPA_RESTRICT dst[], const void * SPA_RESTRICT src[], uint32_t n_channels, uint32_t n_samples)
|
conv_f32_to_s24d_c(struct convert *conv, void * SPA_RESTRICT dst[], const void * SPA_RESTRICT src[],
|
||||||
|
uint32_t n_samples)
|
||||||
{
|
{
|
||||||
const float *s = src[0];
|
const float *s = src[0];
|
||||||
uint8_t **d = (uint8_t **) dst;
|
uint8_t **d = (uint8_t **) dst;
|
||||||
uint32_t i, j;
|
uint32_t i, j, n_channels = conv->n_channels;
|
||||||
|
|
||||||
for (j = 0; j < n_samples; j++) {
|
for (j = 0; j < n_samples; j++) {
|
||||||
for (i = 0; i < n_channels; i++) {
|
for (i = 0; i < n_channels; i++) {
|
||||||
|
|
@ -500,11 +610,12 @@ conv_f32_to_s24d_c(void *data, void * SPA_RESTRICT dst[], const void * SPA_RESTR
|
||||||
}
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
conv_f32d_to_s24_c(void *data, void * SPA_RESTRICT dst[], const void * SPA_RESTRICT src[], uint32_t n_channels, uint32_t n_samples)
|
conv_f32d_to_s24_c(struct convert *conv, void * SPA_RESTRICT dst[], const void * SPA_RESTRICT src[],
|
||||||
|
uint32_t n_samples)
|
||||||
{
|
{
|
||||||
const float **s = (const float **) src;
|
const float **s = (const float **) src;
|
||||||
uint8_t *d = dst[0];
|
uint8_t *d = dst[0];
|
||||||
uint32_t i, j;
|
uint32_t i, j, n_channels = conv->n_channels;
|
||||||
|
|
||||||
for (j = 0; j < n_samples; j++) {
|
for (j = 0; j < n_samples; j++) {
|
||||||
for (i = 0; i < n_channels; i++) {
|
for (i = 0; i < n_channels; i++) {
|
||||||
|
|
@ -516,9 +627,10 @@ conv_f32d_to_s24_c(void *data, void * SPA_RESTRICT dst[], const void * SPA_RESTR
|
||||||
|
|
||||||
|
|
||||||
void
|
void
|
||||||
conv_f32d_to_s24_32d_c(void *data, void * SPA_RESTRICT dst[], const void * SPA_RESTRICT src[], uint32_t n_channels, uint32_t n_samples)
|
conv_f32d_to_s24_32d_c(struct convert *conv, void * SPA_RESTRICT dst[], const void * SPA_RESTRICT src[],
|
||||||
|
uint32_t n_samples)
|
||||||
{
|
{
|
||||||
uint32_t i, j;
|
uint32_t i, j, n_channels = conv->n_channels;
|
||||||
|
|
||||||
for (i = 0; i < n_channels; i++) {
|
for (i = 0; i < n_channels; i++) {
|
||||||
const float *s = src[i];
|
const float *s = src[i];
|
||||||
|
|
@ -530,17 +642,26 @@ conv_f32d_to_s24_32d_c(void *data, void * SPA_RESTRICT dst[], const void * SPA_R
|
||||||
}
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
conv_f32_to_s24_32_c(void *data, void * SPA_RESTRICT dst[], const void * SPA_RESTRICT src[], uint32_t n_channels, uint32_t n_samples)
|
conv_f32_to_s24_32_c(struct convert *conv, void * SPA_RESTRICT dst[], const void * SPA_RESTRICT src[],
|
||||||
|
uint32_t n_samples)
|
||||||
{
|
{
|
||||||
conv_f32d_to_s24_32d_c(data, dst, src, 1, n_samples * n_channels);
|
uint32_t i, n_channels = conv->n_channels;
|
||||||
|
const float *s = src[0];
|
||||||
|
int32_t *d = dst[0];
|
||||||
|
|
||||||
|
n_samples *= n_channels;
|
||||||
|
|
||||||
|
for (i = 0; i < n_samples; i++)
|
||||||
|
d[i] = F32_TO_S24(s[i]);
|
||||||
}
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
conv_f32_to_s24_32d_c(void *data, void * SPA_RESTRICT dst[], const void * SPA_RESTRICT src[], uint32_t n_channels, uint32_t n_samples)
|
conv_f32_to_s24_32d_c(struct convert *conv, void * SPA_RESTRICT dst[], const void * SPA_RESTRICT src[],
|
||||||
|
uint32_t n_samples)
|
||||||
{
|
{
|
||||||
const float *s = src[0];
|
const float *s = src[0];
|
||||||
int32_t **d = (int32_t **) dst;
|
int32_t **d = (int32_t **) dst;
|
||||||
uint32_t i, j;
|
uint32_t i, j, n_channels = conv->n_channels;
|
||||||
|
|
||||||
for (j = 0; j < n_samples; j++) {
|
for (j = 0; j < n_samples; j++) {
|
||||||
for (i = 0; i < n_channels; i++)
|
for (i = 0; i < n_channels; i++)
|
||||||
|
|
@ -549,11 +670,12 @@ conv_f32_to_s24_32d_c(void *data, void * SPA_RESTRICT dst[], const void * SPA_RE
|
||||||
}
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
conv_f32d_to_s24_32_c(void *data, void * SPA_RESTRICT dst[], const void * SPA_RESTRICT src[], uint32_t n_channels, uint32_t n_samples)
|
conv_f32d_to_s24_32_c(struct convert *conv, void * SPA_RESTRICT dst[], const void * SPA_RESTRICT src[],
|
||||||
|
uint32_t n_samples)
|
||||||
{
|
{
|
||||||
const float **s = (const float **) src;
|
const float **s = (const float **) src;
|
||||||
int32_t *d = dst[0];
|
int32_t *d = dst[0];
|
||||||
uint32_t i, j;
|
uint32_t i, j, n_channels = conv->n_channels;
|
||||||
|
|
||||||
for (j = 0; j < n_samples; j++) {
|
for (j = 0; j < n_samples; j++) {
|
||||||
for (i = 0; i < n_channels; i++)
|
for (i = 0; i < n_channels; i++)
|
||||||
|
|
@ -562,11 +684,12 @@ conv_f32d_to_s24_32_c(void *data, void * SPA_RESTRICT dst[], const void * SPA_RE
|
||||||
}
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
conv_deinterleave_8_c(void *data, void * SPA_RESTRICT dst[], const void * SPA_RESTRICT src[], uint32_t n_channels, uint32_t n_samples)
|
conv_deinterleave_8_c(struct convert *conv, void * SPA_RESTRICT dst[], const void * SPA_RESTRICT src[],
|
||||||
|
uint32_t n_samples)
|
||||||
{
|
{
|
||||||
const uint8_t *s = src[0];
|
const uint8_t *s = src[0];
|
||||||
uint8_t **d = (uint8_t **) dst;
|
uint8_t **d = (uint8_t **) dst;
|
||||||
uint32_t i, j;
|
uint32_t i, j, n_channels = conv->n_channels;
|
||||||
|
|
||||||
for (j = 0; j < n_samples; j++) {
|
for (j = 0; j < n_samples; j++) {
|
||||||
for (i = 0; i < n_channels; i++)
|
for (i = 0; i < n_channels; i++)
|
||||||
|
|
@ -575,11 +698,12 @@ conv_deinterleave_8_c(void *data, void * SPA_RESTRICT dst[], const void * SPA_RE
|
||||||
}
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
conv_deinterleave_16_c(void *data, void * SPA_RESTRICT dst[], const void * SPA_RESTRICT src[], uint32_t n_channels, uint32_t n_samples)
|
conv_deinterleave_16_c(struct convert *conv, void * SPA_RESTRICT dst[], const void * SPA_RESTRICT src[],
|
||||||
|
uint32_t n_samples)
|
||||||
{
|
{
|
||||||
const uint16_t *s = src[0];
|
const uint16_t *s = src[0];
|
||||||
uint16_t **d = (uint16_t **) dst;
|
uint16_t **d = (uint16_t **) dst;
|
||||||
uint32_t i, j;
|
uint32_t i, j, n_channels = conv->n_channels;
|
||||||
|
|
||||||
for (j = 0; j < n_samples; j++) {
|
for (j = 0; j < n_samples; j++) {
|
||||||
for (i = 0; i < n_channels; i++)
|
for (i = 0; i < n_channels; i++)
|
||||||
|
|
@ -588,11 +712,12 @@ conv_deinterleave_16_c(void *data, void * SPA_RESTRICT dst[], const void * SPA_R
|
||||||
}
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
conv_deinterleave_24_c(void *data, void * SPA_RESTRICT dst[], const void * SPA_RESTRICT src[], uint32_t n_channels, uint32_t n_samples)
|
conv_deinterleave_24_c(struct convert *conv, void * SPA_RESTRICT dst[], const void * SPA_RESTRICT src[],
|
||||||
|
uint32_t n_samples)
|
||||||
{
|
{
|
||||||
const uint8_t *s = src[0];
|
const uint8_t *s = src[0];
|
||||||
uint8_t **d = (uint8_t **) dst;
|
uint8_t **d = (uint8_t **) dst;
|
||||||
uint32_t i, j;
|
uint32_t i, j, n_channels = conv->n_channels;
|
||||||
|
|
||||||
for (j = 0; j < n_samples; j++) {
|
for (j = 0; j < n_samples; j++) {
|
||||||
for (i = 0; i < n_channels; i++) {
|
for (i = 0; i < n_channels; i++) {
|
||||||
|
|
@ -603,11 +728,12 @@ conv_deinterleave_24_c(void *data, void * SPA_RESTRICT dst[], const void * SPA_R
|
||||||
}
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
conv_deinterleave_32_c(void *data, void * SPA_RESTRICT dst[], const void * SPA_RESTRICT src[], uint32_t n_channels, uint32_t n_samples)
|
conv_deinterleave_32_c(struct convert *conv, void * SPA_RESTRICT dst[], const void * SPA_RESTRICT src[],
|
||||||
|
uint32_t n_samples)
|
||||||
{
|
{
|
||||||
const uint32_t *s = src[0];
|
const uint32_t *s = src[0];
|
||||||
uint32_t **d = (uint32_t **) dst;
|
uint32_t **d = (uint32_t **) dst;
|
||||||
uint32_t i, j;
|
uint32_t i, j, n_channels = conv->n_channels;
|
||||||
|
|
||||||
for (j = 0; j < n_samples; j++) {
|
for (j = 0; j < n_samples; j++) {
|
||||||
for (i = 0; i < n_channels; i++)
|
for (i = 0; i < n_channels; i++)
|
||||||
|
|
@ -616,11 +742,12 @@ conv_deinterleave_32_c(void *data, void * SPA_RESTRICT dst[], const void * SPA_R
|
||||||
}
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
conv_interleave_8_c(void *data, void * SPA_RESTRICT dst[], const void * SPA_RESTRICT src[], uint32_t n_channels, uint32_t n_samples)
|
conv_interleave_8_c(struct convert *conv, void * SPA_RESTRICT dst[], const void * SPA_RESTRICT src[],
|
||||||
|
uint32_t n_samples)
|
||||||
{
|
{
|
||||||
const int8_t **s = (const int8_t **) src;
|
const int8_t **s = (const int8_t **) src;
|
||||||
uint8_t *d = dst[0];
|
uint8_t *d = dst[0];
|
||||||
uint32_t i, j;
|
uint32_t i, j, n_channels = conv->n_channels;
|
||||||
|
|
||||||
for (j = 0; j < n_samples; j++) {
|
for (j = 0; j < n_samples; j++) {
|
||||||
for (i = 0; i < n_channels; i++)
|
for (i = 0; i < n_channels; i++)
|
||||||
|
|
@ -629,11 +756,12 @@ conv_interleave_8_c(void *data, void * SPA_RESTRICT dst[], const void * SPA_REST
|
||||||
}
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
conv_interleave_16_c(void *data, void * SPA_RESTRICT dst[], const void * SPA_RESTRICT src[], uint32_t n_channels, uint32_t n_samples)
|
conv_interleave_16_c(struct convert *conv, void * SPA_RESTRICT dst[], const void * SPA_RESTRICT src[],
|
||||||
|
uint32_t n_samples)
|
||||||
{
|
{
|
||||||
const int16_t **s = (const int16_t **) src;
|
const int16_t **s = (const int16_t **) src;
|
||||||
uint16_t *d = dst[0];
|
uint16_t *d = dst[0];
|
||||||
uint32_t i, j;
|
uint32_t i, j, n_channels = conv->n_channels;
|
||||||
|
|
||||||
for (j = 0; j < n_samples; j++) {
|
for (j = 0; j < n_samples; j++) {
|
||||||
for (i = 0; i < n_channels; i++)
|
for (i = 0; i < n_channels; i++)
|
||||||
|
|
@ -642,11 +770,12 @@ conv_interleave_16_c(void *data, void * SPA_RESTRICT dst[], const void * SPA_RES
|
||||||
}
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
conv_interleave_24_c(void *data, void * SPA_RESTRICT dst[], const void * SPA_RESTRICT src[], uint32_t n_channels, uint32_t n_samples)
|
conv_interleave_24_c(struct convert *conv, void * SPA_RESTRICT dst[], const void * SPA_RESTRICT src[],
|
||||||
|
uint32_t n_samples)
|
||||||
{
|
{
|
||||||
const int8_t **s = (const int8_t **) src;
|
const int8_t **s = (const int8_t **) src;
|
||||||
uint8_t *d = dst[0];
|
uint8_t *d = dst[0];
|
||||||
uint32_t i, j;
|
uint32_t i, j, n_channels = conv->n_channels;
|
||||||
|
|
||||||
for (j = 0; j < n_samples; j++) {
|
for (j = 0; j < n_samples; j++) {
|
||||||
for (i = 0; i < n_channels; i++) {
|
for (i = 0; i < n_channels; i++) {
|
||||||
|
|
@ -657,11 +786,12 @@ conv_interleave_24_c(void *data, void * SPA_RESTRICT dst[], const void * SPA_RES
|
||||||
}
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
conv_interleave_32_c(void *data, void * SPA_RESTRICT dst[], const void * SPA_RESTRICT src[], uint32_t n_channels, uint32_t n_samples)
|
conv_interleave_32_c(struct convert *conv, void * SPA_RESTRICT dst[], const void * SPA_RESTRICT src[],
|
||||||
|
uint32_t n_samples)
|
||||||
{
|
{
|
||||||
const int32_t **s = (const int32_t **) src;
|
const int32_t **s = (const int32_t **) src;
|
||||||
uint32_t *d = dst[0];
|
uint32_t *d = dst[0];
|
||||||
uint32_t i, j;
|
uint32_t i, j, n_channels = conv->n_channels;
|
||||||
|
|
||||||
for (j = 0; j < n_samples; j++) {
|
for (j = 0; j < n_samples; j++) {
|
||||||
for (i = 0; i < n_channels; i++)
|
for (i = 0; i < n_channels; i++)
|
||||||
|
|
|
||||||
|
|
@ -27,7 +27,8 @@
|
||||||
#include <emmintrin.h>
|
#include <emmintrin.h>
|
||||||
|
|
||||||
static void
|
static void
|
||||||
conv_s16_to_f32d_1_sse2(void *data, void * SPA_RESTRICT dst[], const void * SPA_RESTRICT src, uint32_t n_channels, uint32_t n_samples)
|
conv_s16_to_f32d_1s_sse2(void *data, void * SPA_RESTRICT dst[], const void * SPA_RESTRICT src,
|
||||||
|
uint32_t n_channels, uint32_t n_samples)
|
||||||
{
|
{
|
||||||
const int16_t *s = src;
|
const int16_t *s = src;
|
||||||
float **d = (float **) dst;
|
float **d = (float **) dst;
|
||||||
|
|
@ -60,18 +61,29 @@ conv_s16_to_f32d_1_sse2(void *data, void * SPA_RESTRICT dst[], const void * SPA_
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
static void
|
void
|
||||||
conv_s16_to_f32d_2_sse2(void *data, void * SPA_RESTRICT dst[], const void * SPA_RESTRICT src, uint32_t n_channels, uint32_t n_samples)
|
conv_s16_to_f32d_sse2(struct convert *conv, void * SPA_RESTRICT dst[], const void * SPA_RESTRICT src[],
|
||||||
|
uint32_t n_samples)
|
||||||
{
|
{
|
||||||
const int16_t *s = src;
|
const int16_t *s = src[0];
|
||||||
|
uint32_t i = 0, n_channels = conv->n_channels;
|
||||||
|
|
||||||
|
for(; i < n_channels; i++)
|
||||||
|
conv_s16_to_f32d_1s_sse2(conv, &dst[i], &s[i], n_channels, n_samples);
|
||||||
|
}
|
||||||
|
|
||||||
|
void
|
||||||
|
conv_s16_to_f32d_2_sse2(struct convert *conv, void * SPA_RESTRICT dst[], const void * SPA_RESTRICT src[],
|
||||||
|
uint32_t n_samples)
|
||||||
|
{
|
||||||
|
const int16_t *s = src[0];
|
||||||
float **d = (float **) dst;
|
float **d = (float **) dst;
|
||||||
float *d0 = d[0], *d1 = d[1];
|
float *d0 = d[0], *d1 = d[1];
|
||||||
uint32_t n, unrolled;
|
uint32_t n, unrolled;
|
||||||
__m128i in, t[2];
|
__m128i in, t[2];
|
||||||
__m128 out[2], factor = _mm_set1_ps(1.0f / S16_SCALE);
|
__m128 out[2], factor = _mm_set1_ps(1.0f / S16_SCALE);
|
||||||
|
|
||||||
if (n_channels == 2 &&
|
if (SPA_IS_ALIGNED(s, 16) &&
|
||||||
SPA_IS_ALIGNED(s, 16) &&
|
|
||||||
SPA_IS_ALIGNED(d0, 16) &&
|
SPA_IS_ALIGNED(d0, 16) &&
|
||||||
SPA_IS_ALIGNED(d1, 16))
|
SPA_IS_ALIGNED(d1, 16))
|
||||||
unrolled = n_samples & ~3;
|
unrolled = n_samples & ~3;
|
||||||
|
|
@ -93,7 +105,7 @@ conv_s16_to_f32d_2_sse2(void *data, void * SPA_RESTRICT dst[], const void * SPA_
|
||||||
_mm_store_ps(&d0[n], out[0]);
|
_mm_store_ps(&d0[n], out[0]);
|
||||||
_mm_store_ps(&d1[n], out[1]);
|
_mm_store_ps(&d1[n], out[1]);
|
||||||
|
|
||||||
s += 4*n_channels;
|
s += 8;
|
||||||
}
|
}
|
||||||
for(; n < n_samples; n++) {
|
for(; n < n_samples; n++) {
|
||||||
out[0] = _mm_cvtsi32_ss(out[0], s[0]);
|
out[0] = _mm_cvtsi32_ss(out[0], s[0]);
|
||||||
|
|
@ -102,24 +114,13 @@ conv_s16_to_f32d_2_sse2(void *data, void * SPA_RESTRICT dst[], const void * SPA_
|
||||||
out[1] = _mm_mul_ss(out[1], factor);
|
out[1] = _mm_mul_ss(out[1], factor);
|
||||||
_mm_store_ss(&d0[n], out[0]);
|
_mm_store_ss(&d0[n], out[0]);
|
||||||
_mm_store_ss(&d1[n], out[1]);
|
_mm_store_ss(&d1[n], out[1]);
|
||||||
s += n_channels;
|
s += 2;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
conv_s16_to_f32d_sse2(void *data, void * SPA_RESTRICT dst[], const void * SPA_RESTRICT src[], uint32_t n_channels, uint32_t n_samples)
|
conv_s24_to_f32d_1s_sse2(void *data, void * SPA_RESTRICT dst[], const void * SPA_RESTRICT src,
|
||||||
{
|
uint32_t n_channels, uint32_t n_samples)
|
||||||
const int16_t *s = src[0];
|
|
||||||
uint32_t i = 0;
|
|
||||||
|
|
||||||
for(; i + 1 < n_channels; i += 2)
|
|
||||||
conv_s16_to_f32d_2_sse2(data, &dst[i], &s[i], n_channels, n_samples);
|
|
||||||
for(; i < n_channels; i++)
|
|
||||||
conv_s16_to_f32d_1_sse2(data, &dst[i], &s[i], n_channels, n_samples);
|
|
||||||
}
|
|
||||||
|
|
||||||
void
|
|
||||||
conv_s24_to_f32d_1_sse2(void *data, void * SPA_RESTRICT dst[], const void * SPA_RESTRICT src, uint32_t n_channels, uint32_t n_samples)
|
|
||||||
{
|
{
|
||||||
const uint8_t *s = src;
|
const uint8_t *s = src;
|
||||||
float **d = (float **) dst;
|
float **d = (float **) dst;
|
||||||
|
|
@ -158,7 +159,8 @@ conv_s24_to_f32d_1_sse2(void *data, void * SPA_RESTRICT dst[], const void * SPA_
|
||||||
}
|
}
|
||||||
|
|
||||||
static void
|
static void
|
||||||
conv_s24_to_f32d_2_sse2(void *data, void * SPA_RESTRICT dst[], const void * SPA_RESTRICT src, uint32_t n_channels, uint32_t n_samples)
|
conv_s24_to_f32d_2s_sse2(void *data, void * SPA_RESTRICT dst[], const void * SPA_RESTRICT src,
|
||||||
|
uint32_t n_channels, uint32_t n_samples)
|
||||||
{
|
{
|
||||||
const uint8_t *s = src;
|
const uint8_t *s = src;
|
||||||
float **d = (float **) dst;
|
float **d = (float **) dst;
|
||||||
|
|
@ -217,7 +219,8 @@ conv_s24_to_f32d_2_sse2(void *data, void * SPA_RESTRICT dst[], const void * SPA_
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
static void
|
static void
|
||||||
conv_s24_to_f32d_4_sse2(void *data, void * SPA_RESTRICT dst[], const void * SPA_RESTRICT src, uint32_t n_channels, uint32_t n_samples)
|
conv_s24_to_f32d_4s_sse2(void *data, void * SPA_RESTRICT dst[], const void * SPA_RESTRICT src,
|
||||||
|
uint32_t n_channels, uint32_t n_samples)
|
||||||
{
|
{
|
||||||
const uint8_t *s = src;
|
const uint8_t *s = src;
|
||||||
float **d = (float **) dst;
|
float **d = (float **) dst;
|
||||||
|
|
@ -305,21 +308,23 @@ conv_s24_to_f32d_4_sse2(void *data, void * SPA_RESTRICT dst[], const void * SPA_
|
||||||
}
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
conv_s24_to_f32d_sse2(void *data, void * SPA_RESTRICT dst[], const void * SPA_RESTRICT src[], uint32_t n_channels, uint32_t n_samples)
|
conv_s24_to_f32d_sse2(struct convert *conv, void * SPA_RESTRICT dst[], const void * SPA_RESTRICT src[],
|
||||||
|
uint32_t n_samples)
|
||||||
{
|
{
|
||||||
const int8_t *s = src[0];
|
const int8_t *s = src[0];
|
||||||
uint32_t i = 0;
|
uint32_t i = 0, n_channels = conv->n_channels;
|
||||||
|
|
||||||
for(; i + 3 < n_channels; i += 4)
|
for(; i + 3 < n_channels; i += 4)
|
||||||
conv_s24_to_f32d_4_sse2(data, &dst[i], &s[3*i], n_channels, n_samples);
|
conv_s24_to_f32d_4s_sse2(conv, &dst[i], &s[3*i], n_channels, n_samples);
|
||||||
for(; i + 1 < n_channels; i += 2)
|
for(; i + 1 < n_channels; i += 2)
|
||||||
conv_s24_to_f32d_2_sse2(data, &dst[i], &s[3*i], n_channels, n_samples);
|
conv_s24_to_f32d_2s_sse2(conv, &dst[i], &s[3*i], n_channels, n_samples);
|
||||||
for(; i < n_channels; i++)
|
for(; i < n_channels; i++)
|
||||||
conv_s24_to_f32d_1_sse2(data, &dst[i], &s[3*i], n_channels, n_samples);
|
conv_s24_to_f32d_1s_sse2(conv, &dst[i], &s[3*i], n_channels, n_samples);
|
||||||
}
|
}
|
||||||
|
|
||||||
static void
|
static void
|
||||||
conv_f32d_to_s32_1_sse2(void *data, void * SPA_RESTRICT dst, const void * SPA_RESTRICT src[], uint32_t n_channels, uint32_t n_samples)
|
conv_f32d_to_s32_1s_sse2(void *data, void * SPA_RESTRICT dst, const void * SPA_RESTRICT src[],
|
||||||
|
uint32_t n_channels, uint32_t n_samples)
|
||||||
{
|
{
|
||||||
const float **s = (const float **) src;
|
const float **s = (const float **) src;
|
||||||
const float *s0 = s[0];
|
const float *s0 = s[0];
|
||||||
|
|
@ -359,7 +364,8 @@ conv_f32d_to_s32_1_sse2(void *data, void * SPA_RESTRICT dst, const void * SPA_RE
|
||||||
}
|
}
|
||||||
|
|
||||||
static void
|
static void
|
||||||
conv_f32d_to_s32_2_sse2(void *data, void * SPA_RESTRICT dst, const void * SPA_RESTRICT src[], uint32_t n_channels, uint32_t n_samples)
|
conv_f32d_to_s32_2s_sse2(void *data, void * SPA_RESTRICT dst, const void * SPA_RESTRICT src[],
|
||||||
|
uint32_t n_channels, uint32_t n_samples)
|
||||||
{
|
{
|
||||||
const float **s = (const float **) src;
|
const float **s = (const float **) src;
|
||||||
const float *s0 = s[0], *s1 = s[1];
|
const float *s0 = s[0], *s1 = s[1];
|
||||||
|
|
@ -410,7 +416,8 @@ conv_f32d_to_s32_2_sse2(void *data, void * SPA_RESTRICT dst, const void * SPA_RE
|
||||||
}
|
}
|
||||||
|
|
||||||
static void
|
static void
|
||||||
conv_f32d_to_s32_4_sse2(void *data, void * SPA_RESTRICT dst, const void * SPA_RESTRICT src[], uint32_t n_channels, uint32_t n_samples)
|
conv_f32d_to_s32_4s_sse2(void *data, void * SPA_RESTRICT dst, const void * SPA_RESTRICT src[],
|
||||||
|
uint32_t n_channels, uint32_t n_samples)
|
||||||
{
|
{
|
||||||
const float **s = (const float **) src;
|
const float **s = (const float **) src;
|
||||||
const float *s0 = s[0], *s1 = s[1], *s2 = s[2], *s3 = s[3];
|
const float *s0 = s[0], *s1 = s[1], *s2 = s[2], *s3 = s[3];
|
||||||
|
|
@ -472,21 +479,23 @@ conv_f32d_to_s32_4_sse2(void *data, void * SPA_RESTRICT dst, const void * SPA_RE
|
||||||
}
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
conv_f32d_to_s32_sse2(void *data, void * SPA_RESTRICT dst[], const void * SPA_RESTRICT src[], uint32_t n_channels, uint32_t n_samples)
|
conv_f32d_to_s32_sse2(struct convert *conv, void * SPA_RESTRICT dst[], const void * SPA_RESTRICT src[],
|
||||||
|
uint32_t n_samples)
|
||||||
{
|
{
|
||||||
int32_t *d = dst[0];
|
int32_t *d = dst[0];
|
||||||
uint32_t i = 0;
|
uint32_t i = 0, n_channels = conv->n_channels;
|
||||||
|
|
||||||
for(; i + 3 < n_channels; i += 4)
|
for(; i + 3 < n_channels; i += 4)
|
||||||
conv_f32d_to_s32_4_sse2(data, &d[i], &src[i], n_channels, n_samples);
|
conv_f32d_to_s32_4s_sse2(conv, &d[i], &src[i], n_channels, n_samples);
|
||||||
for(; i + 1 < n_channels; i += 2)
|
for(; i + 1 < n_channels; i += 2)
|
||||||
conv_f32d_to_s32_2_sse2(data, &d[i], &src[i], n_channels, n_samples);
|
conv_f32d_to_s32_2s_sse2(conv, &d[i], &src[i], n_channels, n_samples);
|
||||||
for(; i < n_channels; i++)
|
for(; i < n_channels; i++)
|
||||||
conv_f32d_to_s32_1_sse2(data, &d[i], &src[i], n_channels, n_samples);
|
conv_f32d_to_s32_1s_sse2(conv, &d[i], &src[i], n_channels, n_samples);
|
||||||
}
|
}
|
||||||
|
|
||||||
static void
|
static void
|
||||||
conv_f32d_to_s16_1_sse2(void *data, void * SPA_RESTRICT dst, const void * SPA_RESTRICT src[], uint32_t n_channels, uint32_t n_samples)
|
conv_f32d_to_s16_1s_sse2(void *data, void * SPA_RESTRICT dst, const void * SPA_RESTRICT src[],
|
||||||
|
uint32_t n_channels, uint32_t n_samples)
|
||||||
{
|
{
|
||||||
const float **s = (const float **) src;
|
const float **s = (const float **) src;
|
||||||
const float *s0 = s[0];
|
const float *s0 = s[0];
|
||||||
|
|
@ -528,7 +537,8 @@ conv_f32d_to_s16_1_sse2(void *data, void * SPA_RESTRICT dst, const void * SPA_RE
|
||||||
}
|
}
|
||||||
|
|
||||||
static void
|
static void
|
||||||
conv_f32d_to_s16_2_sse2(void *data, void * SPA_RESTRICT dst, const void * SPA_RESTRICT src[], uint32_t n_channels, uint32_t n_samples)
|
conv_f32d_to_s16_2s_sse2(void *data, void * SPA_RESTRICT dst, const void * SPA_RESTRICT src[],
|
||||||
|
uint32_t n_channels, uint32_t n_samples)
|
||||||
{
|
{
|
||||||
const float **s = (const float **) src;
|
const float **s = (const float **) src;
|
||||||
const float *s0 = s[0], *s1 = s[1];
|
const float *s0 = s[0], *s1 = s[1];
|
||||||
|
|
@ -578,7 +588,8 @@ conv_f32d_to_s16_2_sse2(void *data, void * SPA_RESTRICT dst, const void * SPA_RE
|
||||||
}
|
}
|
||||||
|
|
||||||
static void
|
static void
|
||||||
conv_f32d_to_s16_4_sse2(void *data, void * SPA_RESTRICT dst, const void * SPA_RESTRICT src[], uint32_t n_channels, uint32_t n_samples)
|
conv_f32d_to_s16_4s_sse2(void *data, void * SPA_RESTRICT dst, const void * SPA_RESTRICT src[],
|
||||||
|
uint32_t n_channels, uint32_t n_samples)
|
||||||
{
|
{
|
||||||
const float **s = (const float **) src;
|
const float **s = (const float **) src;
|
||||||
const float *s0 = s[0], *s1 = s[1], *s2 = s[2], *s3 = s[3];
|
const float *s0 = s[0], *s1 = s[1], *s2 = s[2], *s3 = s[3];
|
||||||
|
|
@ -641,15 +652,16 @@ conv_f32d_to_s16_4_sse2(void *data, void * SPA_RESTRICT dst, const void * SPA_RE
|
||||||
}
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
conv_f32d_to_s16_sse2(void *data, void * SPA_RESTRICT dst[], const void * SPA_RESTRICT src[], uint32_t n_channels, uint32_t n_samples)
|
conv_f32d_to_s16_sse2(struct convert *conv, void * SPA_RESTRICT dst[], const void * SPA_RESTRICT src[],
|
||||||
|
uint32_t n_samples)
|
||||||
{
|
{
|
||||||
int16_t *d = dst[0];
|
int16_t *d = dst[0];
|
||||||
uint32_t i = 0;
|
uint32_t i = 0, n_channels = conv->n_channels;
|
||||||
|
|
||||||
for(; i + 3 < n_channels; i += 4)
|
for(; i + 3 < n_channels; i += 4)
|
||||||
conv_f32d_to_s16_4_sse2(data, &d[i], &src[i], n_channels, n_samples);
|
conv_f32d_to_s16_4s_sse2(conv, &d[i], &src[i], n_channels, n_samples);
|
||||||
for(; i + 1 < n_channels; i += 2)
|
for(; i + 1 < n_channels; i += 2)
|
||||||
conv_f32d_to_s16_2_sse2(data, &d[i], &src[i], n_channels, n_samples);
|
conv_f32d_to_s16_2s_sse2(conv, &d[i], &src[i], n_channels, n_samples);
|
||||||
for(; i < n_channels; i++)
|
for(; i < n_channels; i++)
|
||||||
conv_f32d_to_s16_1_sse2(data, &d[i], &src[i], n_channels, n_samples);
|
conv_f32d_to_s16_1s_sse2(conv, &d[i], &src[i], n_channels, n_samples);
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -27,7 +27,8 @@
|
||||||
#include <smmintrin.h>
|
#include <smmintrin.h>
|
||||||
|
|
||||||
static void
|
static void
|
||||||
conv_s24_to_f32d_1_sse41(void *data, void * SPA_RESTRICT dst[], const void * SPA_RESTRICT src, uint32_t n_channels, uint32_t n_samples)
|
conv_s24_to_f32d_1s_sse41(void *data, void * SPA_RESTRICT dst[], const void * SPA_RESTRICT src,
|
||||||
|
uint32_t n_channels, uint32_t n_samples)
|
||||||
{
|
{
|
||||||
const uint8_t *s = src;
|
const uint8_t *s = src;
|
||||||
float **d = (float **) dst;
|
float **d = (float **) dst;
|
||||||
|
|
@ -61,23 +62,26 @@ conv_s24_to_f32d_1_sse41(void *data, void * SPA_RESTRICT dst[], const void * SPA
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
extern void conv_s24_to_f32d_2_sse2(void *data, void * SPA_RESTRICT dst[], const void * SPA_RESTRICT src, uint32_t n_channels, uint32_t n_samples);
|
extern void conv_s24_to_f32d_2s_sse2(void *data, void * SPA_RESTRICT dst[], const void * SPA_RESTRICT src,
|
||||||
extern void conv_s24_to_f32d_4_ssse3(void *data, void * SPA_RESTRICT dst[], const void * SPA_RESTRICT src, uint32_t n_channels, uint32_t n_samples);
|
uint32_t n_channels, uint32_t n_samples);
|
||||||
|
extern void conv_s24_to_f32d_4s_ssse3(void *data, void * SPA_RESTRICT dst[], const void * SPA_RESTRICT src,
|
||||||
|
uint32_t n_channels, uint32_t n_samples);
|
||||||
|
|
||||||
void
|
void
|
||||||
conv_s24_to_f32d_sse41(void *data, void * SPA_RESTRICT dst[], const void * SPA_RESTRICT src[], uint32_t n_channels, uint32_t n_samples)
|
conv_s24_to_f32d_sse41(struct convert *conv, void * SPA_RESTRICT dst[], const void * SPA_RESTRICT src[],
|
||||||
|
uint32_t n_samples)
|
||||||
{
|
{
|
||||||
const int8_t *s = src[0];
|
const int8_t *s = src[0];
|
||||||
uint32_t i = 0;
|
uint32_t i = 0, n_channels = conv->n_channels;
|
||||||
|
|
||||||
#if defined (HAVE_SSSE3)
|
#if defined (HAVE_SSSE3)
|
||||||
for(; i + 3 < n_channels; i += 4)
|
for(; i + 3 < n_channels; i += 4)
|
||||||
conv_s24_to_f32d_4_ssse3(data, &dst[i], &s[3*i], n_channels, n_samples);
|
conv_s24_to_f32d_4s_ssse3(conv, &dst[i], &s[3*i], n_channels, n_samples);
|
||||||
#endif
|
#endif
|
||||||
#if defined (HAVE_SSE2)
|
#if defined (HAVE_SSE2)
|
||||||
for(; i + 1 < n_channels; i += 2)
|
for(; i + 1 < n_channels; i += 2)
|
||||||
conv_s24_to_f32d_2_sse2(data, &dst[i], &s[3*i], n_channels, n_samples);
|
conv_s24_to_f32d_2s_sse2(conv, &dst[i], &s[3*i], n_channels, n_samples);
|
||||||
#endif
|
#endif
|
||||||
for(; i < n_channels; i++)
|
for(; i < n_channels; i++)
|
||||||
conv_s24_to_f32d_1_sse41(data, &dst[i], &s[3*i], n_channels, n_samples);
|
conv_s24_to_f32d_1s_sse41(conv, &dst[i], &s[3*i], n_channels, n_samples);
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -27,7 +27,8 @@
|
||||||
#include <tmmintrin.h>
|
#include <tmmintrin.h>
|
||||||
|
|
||||||
static void
|
static void
|
||||||
conv_s24_to_f32d_4_ssse3(void *data, void * SPA_RESTRICT dst[], const void * SPA_RESTRICT src, uint32_t n_channels, uint32_t n_samples)
|
conv_s24_to_f32d_4s_ssse3(void *data, void * SPA_RESTRICT dst[], const void * SPA_RESTRICT src,
|
||||||
|
uint32_t n_channels, uint32_t n_samples)
|
||||||
{
|
{
|
||||||
const uint8_t *s = src;
|
const uint8_t *s = src;
|
||||||
float **d = (float **) dst;
|
float **d = (float **) dst;
|
||||||
|
|
@ -94,16 +95,18 @@ conv_s24_to_f32d_4_ssse3(void *data, void * SPA_RESTRICT dst[], const void * SPA
|
||||||
}
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
conv_s24_to_f32d_1_sse2(void *data, void * SPA_RESTRICT dst[], const void * SPA_RESTRICT src, uint32_t n_channels, uint32_t n_samples);
|
conv_s24_to_f32d_1s_sse2(void *data, void * SPA_RESTRICT dst[], const void * SPA_RESTRICT src,
|
||||||
|
uint32_t n_channels, uint32_t n_samples);
|
||||||
|
|
||||||
void
|
void
|
||||||
conv_s24_to_f32d_ssse3(void *data, void * SPA_RESTRICT dst[], const void * SPA_RESTRICT src[], uint32_t n_channels, uint32_t n_samples)
|
conv_s24_to_f32d_ssse3(struct convert *conv, void * SPA_RESTRICT dst[], const void * SPA_RESTRICT src[],
|
||||||
|
uint32_t n_samples)
|
||||||
{
|
{
|
||||||
const int8_t *s = src[0];
|
const int8_t *s = src[0];
|
||||||
uint32_t i = 0;
|
uint32_t i = 0, n_channels = conv->n_channels;
|
||||||
|
|
||||||
for(; i + 3 < n_channels; i += 4)
|
for(; i + 3 < n_channels; i += 4)
|
||||||
conv_s24_to_f32d_4_ssse3(data, &dst[i], &s[3*i], n_channels, n_samples);
|
conv_s24_to_f32d_4s_ssse3(conv, &dst[i], &s[3*i], n_channels, n_samples);
|
||||||
for(; i < n_channels; i++)
|
for(; i < n_channels; i++)
|
||||||
conv_s24_to_f32d_1_sse2(data, &dst[i], &s[3*i], n_channels, n_samples);
|
conv_s24_to_f32d_1s_sse2(conv, &dst[i], &s[3*i], n_channels, n_samples);
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -32,135 +32,163 @@
|
||||||
|
|
||||||
#include "fmt-ops.h"
|
#include "fmt-ops.h"
|
||||||
|
|
||||||
|
typedef void (*convert_func_t) (struct convert *conv, void * SPA_RESTRICT dst[],
|
||||||
|
const void * SPA_RESTRICT src[], uint32_t n_samples);
|
||||||
|
|
||||||
struct conv_info {
|
struct conv_info {
|
||||||
uint32_t src_fmt;
|
uint32_t src_fmt;
|
||||||
uint32_t dst_fmt;
|
uint32_t dst_fmt;
|
||||||
#define FEATURE_SSE2 SPA_CPU_FLAG_SSE2
|
uint32_t n_channels;
|
||||||
#define FEATURE_SSE41 SPA_CPU_FLAG_SSE41
|
uint32_t cpu_flags;
|
||||||
#define FEATURE_SSSE3 SPA_CPU_FLAG_SSSE3
|
|
||||||
uint32_t features;
|
|
||||||
|
|
||||||
convert_func_t func;
|
convert_func_t process;
|
||||||
};
|
};
|
||||||
|
|
||||||
static struct conv_info conv_table[] =
|
static struct conv_info conv_table[] =
|
||||||
{
|
{
|
||||||
/* to f32 */
|
/* to f32 */
|
||||||
{ SPA_AUDIO_FORMAT_U8, SPA_AUDIO_FORMAT_F32, 0, conv_u8_to_f32_c },
|
{ SPA_AUDIO_FORMAT_U8, SPA_AUDIO_FORMAT_F32, 0, 0, conv_u8_to_f32_c },
|
||||||
{ SPA_AUDIO_FORMAT_U8P, SPA_AUDIO_FORMAT_F32P, 0, conv_u8d_to_f32d_c },
|
{ SPA_AUDIO_FORMAT_U8P, SPA_AUDIO_FORMAT_F32P, 0, 0, conv_u8d_to_f32d_c },
|
||||||
{ SPA_AUDIO_FORMAT_U8, SPA_AUDIO_FORMAT_F32P, 0, conv_u8_to_f32d_c },
|
{ SPA_AUDIO_FORMAT_U8, SPA_AUDIO_FORMAT_F32P, 0, 0, conv_u8_to_f32d_c },
|
||||||
{ SPA_AUDIO_FORMAT_U8P, SPA_AUDIO_FORMAT_F32, 0, conv_u8d_to_f32_c },
|
{ SPA_AUDIO_FORMAT_U8P, SPA_AUDIO_FORMAT_F32, 0, 0, conv_u8d_to_f32_c },
|
||||||
|
|
||||||
|
|
||||||
{ SPA_AUDIO_FORMAT_S16, SPA_AUDIO_FORMAT_F32, 0, conv_s16_to_f32_c },
|
{ SPA_AUDIO_FORMAT_S16, SPA_AUDIO_FORMAT_F32, 0, 0, conv_s16_to_f32_c },
|
||||||
{ SPA_AUDIO_FORMAT_S16P, SPA_AUDIO_FORMAT_F32P, 0, conv_s16d_to_f32d_c },
|
{ SPA_AUDIO_FORMAT_S16P, SPA_AUDIO_FORMAT_F32P, 0, 0, conv_s16d_to_f32d_c },
|
||||||
#if defined (HAVE_SSE2)
|
#if defined (HAVE_SSE2)
|
||||||
{ SPA_AUDIO_FORMAT_S16, SPA_AUDIO_FORMAT_F32P, FEATURE_SSE2, conv_s16_to_f32d_sse2 },
|
{ SPA_AUDIO_FORMAT_S16, SPA_AUDIO_FORMAT_F32P, 2, SPA_CPU_FLAG_SSE2, conv_s16_to_f32d_2_sse2 },
|
||||||
|
{ SPA_AUDIO_FORMAT_S16, SPA_AUDIO_FORMAT_F32P, 0, SPA_CPU_FLAG_SSE2, conv_s16_to_f32d_sse2 },
|
||||||
#endif
|
#endif
|
||||||
{ SPA_AUDIO_FORMAT_S16, SPA_AUDIO_FORMAT_F32P, 0, conv_s16_to_f32d_c },
|
{ SPA_AUDIO_FORMAT_S16, SPA_AUDIO_FORMAT_F32P, 0, 0, conv_s16_to_f32d_c },
|
||||||
{ SPA_AUDIO_FORMAT_S16P, SPA_AUDIO_FORMAT_F32, 0, conv_s16d_to_f32_c },
|
{ SPA_AUDIO_FORMAT_S16P, SPA_AUDIO_FORMAT_F32, 0, 0, conv_s16d_to_f32_c },
|
||||||
|
|
||||||
{ SPA_AUDIO_FORMAT_F32, SPA_AUDIO_FORMAT_F32, 0, conv_copy32_c },
|
{ SPA_AUDIO_FORMAT_F32, SPA_AUDIO_FORMAT_F32, 0, 0, conv_copy32_c },
|
||||||
{ SPA_AUDIO_FORMAT_F32P, SPA_AUDIO_FORMAT_F32P, 0, conv_copy32d_c },
|
{ SPA_AUDIO_FORMAT_F32P, SPA_AUDIO_FORMAT_F32P, 0, 0, conv_copy32d_c },
|
||||||
{ SPA_AUDIO_FORMAT_F32, SPA_AUDIO_FORMAT_F32P, 0, conv_deinterleave_32_c },
|
{ SPA_AUDIO_FORMAT_F32, SPA_AUDIO_FORMAT_F32P, 0, 0, conv_deinterleave_32_c },
|
||||||
{ SPA_AUDIO_FORMAT_F32P, SPA_AUDIO_FORMAT_F32, 0, conv_interleave_32_c },
|
{ SPA_AUDIO_FORMAT_F32P, SPA_AUDIO_FORMAT_F32, 0, 0, conv_interleave_32_c },
|
||||||
|
|
||||||
{ SPA_AUDIO_FORMAT_S32, SPA_AUDIO_FORMAT_F32, 0, conv_s32_to_f32_c },
|
{ SPA_AUDIO_FORMAT_S32, SPA_AUDIO_FORMAT_F32, 0, 0, conv_s32_to_f32_c },
|
||||||
{ SPA_AUDIO_FORMAT_S32P, SPA_AUDIO_FORMAT_F32P, 0, conv_s32d_to_f32d_c },
|
{ SPA_AUDIO_FORMAT_S32P, SPA_AUDIO_FORMAT_F32P, 0, 0, conv_s32d_to_f32d_c },
|
||||||
{ SPA_AUDIO_FORMAT_S32, SPA_AUDIO_FORMAT_F32P, 0, conv_s32_to_f32d_c },
|
{ SPA_AUDIO_FORMAT_S32, SPA_AUDIO_FORMAT_F32P, 0, 0, conv_s32_to_f32d_c },
|
||||||
{ SPA_AUDIO_FORMAT_S32P, SPA_AUDIO_FORMAT_F32, 0, conv_s32d_to_f32_c },
|
{ SPA_AUDIO_FORMAT_S32P, SPA_AUDIO_FORMAT_F32, 0, 0, conv_s32d_to_f32_c },
|
||||||
|
|
||||||
{ SPA_AUDIO_FORMAT_S24, SPA_AUDIO_FORMAT_F32, 0, conv_s24_to_f32_c },
|
{ SPA_AUDIO_FORMAT_S24, SPA_AUDIO_FORMAT_F32, 0, 0, conv_s24_to_f32_c },
|
||||||
{ SPA_AUDIO_FORMAT_S24P, SPA_AUDIO_FORMAT_F32P, 0, conv_s24d_to_f32d_c },
|
{ SPA_AUDIO_FORMAT_S24P, SPA_AUDIO_FORMAT_F32P, 0, 0, conv_s24d_to_f32d_c },
|
||||||
#if defined (HAVE_SSSE3)
|
#if defined (HAVE_SSSE3)
|
||||||
// { SPA_AUDIO_FORMAT_S24, SPA_AUDIO_FORMAT_F32P, FEATURE_SSSE3, conv_s24_to_f32d_ssse3 },
|
// { SPA_AUDIO_FORMAT_S24, SPA_AUDIO_FORMAT_F32P, 0, SPA_CPU_FLAG_SSSE3, conv_s24_to_f32d_ssse3 },
|
||||||
#endif
|
#endif
|
||||||
#if defined (HAVE_SSE41)
|
#if defined (HAVE_SSE41)
|
||||||
{ SPA_AUDIO_FORMAT_S24, SPA_AUDIO_FORMAT_F32P, FEATURE_SSE41, conv_s24_to_f32d_sse41 },
|
{ SPA_AUDIO_FORMAT_S24, SPA_AUDIO_FORMAT_F32P, 0, SPA_CPU_FLAG_SSE41, conv_s24_to_f32d_sse41 },
|
||||||
#endif
|
#endif
|
||||||
#if defined (HAVE_SSE2)
|
#if defined (HAVE_SSE2)
|
||||||
{ SPA_AUDIO_FORMAT_S24, SPA_AUDIO_FORMAT_F32P, FEATURE_SSE2, conv_s24_to_f32d_sse2 },
|
{ SPA_AUDIO_FORMAT_S24, SPA_AUDIO_FORMAT_F32P, 0, SPA_CPU_FLAG_SSE2, conv_s24_to_f32d_sse2 },
|
||||||
#endif
|
#endif
|
||||||
{ SPA_AUDIO_FORMAT_S24, SPA_AUDIO_FORMAT_F32P, 0, conv_s24_to_f32d_c },
|
{ SPA_AUDIO_FORMAT_S24, SPA_AUDIO_FORMAT_F32P, 0, 0, conv_s24_to_f32d_c },
|
||||||
{ SPA_AUDIO_FORMAT_S24P, SPA_AUDIO_FORMAT_F32, 0, conv_s24d_to_f32_c },
|
{ SPA_AUDIO_FORMAT_S24P, SPA_AUDIO_FORMAT_F32, 0, 0, conv_s24d_to_f32_c },
|
||||||
|
|
||||||
{ SPA_AUDIO_FORMAT_S24_32, SPA_AUDIO_FORMAT_F32, 0, conv_s24_32_to_f32_c },
|
{ SPA_AUDIO_FORMAT_S24_32, SPA_AUDIO_FORMAT_F32, 0, 0, conv_s24_32_to_f32_c },
|
||||||
{ SPA_AUDIO_FORMAT_S24_32P, SPA_AUDIO_FORMAT_F32P, 0, conv_s24_32d_to_f32d_c },
|
{ SPA_AUDIO_FORMAT_S24_32P, SPA_AUDIO_FORMAT_F32P, 0, 0, conv_s24_32d_to_f32d_c },
|
||||||
{ SPA_AUDIO_FORMAT_S24_32, SPA_AUDIO_FORMAT_F32P, 0, conv_s24_32_to_f32d_c },
|
{ SPA_AUDIO_FORMAT_S24_32, SPA_AUDIO_FORMAT_F32P, 0, 0, conv_s24_32_to_f32d_c },
|
||||||
{ SPA_AUDIO_FORMAT_S24_32P, SPA_AUDIO_FORMAT_F32, 0, conv_s24_32d_to_f32_c },
|
{ SPA_AUDIO_FORMAT_S24_32P, SPA_AUDIO_FORMAT_F32, 0, 0, conv_s24_32d_to_f32_c },
|
||||||
|
|
||||||
/* from f32 */
|
/* from f32 */
|
||||||
{ SPA_AUDIO_FORMAT_F32, SPA_AUDIO_FORMAT_U8, 0, conv_f32_to_u8_c },
|
{ SPA_AUDIO_FORMAT_F32, SPA_AUDIO_FORMAT_U8, 0, 0, conv_f32_to_u8_c },
|
||||||
{ SPA_AUDIO_FORMAT_F32P, SPA_AUDIO_FORMAT_U8P, 0, conv_f32d_to_u8d_c },
|
{ SPA_AUDIO_FORMAT_F32P, SPA_AUDIO_FORMAT_U8P, 0, 0, conv_f32d_to_u8d_c },
|
||||||
{ SPA_AUDIO_FORMAT_F32, SPA_AUDIO_FORMAT_U8P, 0, conv_f32_to_u8d_c },
|
{ SPA_AUDIO_FORMAT_F32, SPA_AUDIO_FORMAT_U8P, 0, 0, conv_f32_to_u8d_c },
|
||||||
{ SPA_AUDIO_FORMAT_F32P, SPA_AUDIO_FORMAT_U8, 0, conv_f32d_to_u8_c },
|
{ SPA_AUDIO_FORMAT_F32P, SPA_AUDIO_FORMAT_U8, 0, 0, conv_f32d_to_u8_c },
|
||||||
|
|
||||||
{ SPA_AUDIO_FORMAT_F32, SPA_AUDIO_FORMAT_S16, 0, conv_f32_to_s16_c },
|
{ SPA_AUDIO_FORMAT_F32, SPA_AUDIO_FORMAT_S16, 0, 0, conv_f32_to_s16_c },
|
||||||
{ SPA_AUDIO_FORMAT_F32P, SPA_AUDIO_FORMAT_S16P, 0, conv_f32d_to_s16d_c },
|
{ SPA_AUDIO_FORMAT_F32P, SPA_AUDIO_FORMAT_S16P, 0, 0, conv_f32d_to_s16d_c },
|
||||||
{ SPA_AUDIO_FORMAT_F32, SPA_AUDIO_FORMAT_S16P, 0, conv_f32_to_s16d_c },
|
{ SPA_AUDIO_FORMAT_F32, SPA_AUDIO_FORMAT_S16P, 0, 0, conv_f32_to_s16d_c },
|
||||||
#if defined (HAVE_SSE2)
|
#if defined (HAVE_SSE2)
|
||||||
{ SPA_AUDIO_FORMAT_F32P, SPA_AUDIO_FORMAT_S16, FEATURE_SSE2, conv_f32d_to_s16_sse2 },
|
{ SPA_AUDIO_FORMAT_F32P, SPA_AUDIO_FORMAT_S16, 0, SPA_CPU_FLAG_SSE2, conv_f32d_to_s16_sse2 },
|
||||||
#endif
|
#endif
|
||||||
{ SPA_AUDIO_FORMAT_F32P, SPA_AUDIO_FORMAT_S16, 0, conv_f32d_to_s16_c },
|
{ SPA_AUDIO_FORMAT_F32P, SPA_AUDIO_FORMAT_S16, 0, 0, conv_f32d_to_s16_c },
|
||||||
|
|
||||||
{ SPA_AUDIO_FORMAT_F32, SPA_AUDIO_FORMAT_S32, 0, conv_f32_to_s32_c },
|
{ SPA_AUDIO_FORMAT_F32, SPA_AUDIO_FORMAT_S32, 0, 0, conv_f32_to_s32_c },
|
||||||
{ SPA_AUDIO_FORMAT_F32P, SPA_AUDIO_FORMAT_S32P, 0, conv_f32d_to_s32d_c },
|
{ SPA_AUDIO_FORMAT_F32P, SPA_AUDIO_FORMAT_S32P, 0, 0, conv_f32d_to_s32d_c },
|
||||||
{ SPA_AUDIO_FORMAT_F32, SPA_AUDIO_FORMAT_S32P, 0, conv_f32_to_s32d_c },
|
{ SPA_AUDIO_FORMAT_F32, SPA_AUDIO_FORMAT_S32P, 0, 0, conv_f32_to_s32d_c },
|
||||||
#if defined (HAVE_SSE2)
|
#if defined (HAVE_SSE2)
|
||||||
{ SPA_AUDIO_FORMAT_F32P, SPA_AUDIO_FORMAT_S32, FEATURE_SSE2, conv_f32d_to_s32_sse2 },
|
{ SPA_AUDIO_FORMAT_F32P, SPA_AUDIO_FORMAT_S32, 0, SPA_CPU_FLAG_SSE2, conv_f32d_to_s32_sse2 },
|
||||||
#endif
|
#endif
|
||||||
{ SPA_AUDIO_FORMAT_F32P, SPA_AUDIO_FORMAT_S32, 0, conv_f32d_to_s32_c },
|
{ SPA_AUDIO_FORMAT_F32P, SPA_AUDIO_FORMAT_S32, 0, 0, conv_f32d_to_s32_c },
|
||||||
|
|
||||||
{ SPA_AUDIO_FORMAT_F32, SPA_AUDIO_FORMAT_S24, 0, conv_f32_to_s24_c },
|
{ SPA_AUDIO_FORMAT_F32, SPA_AUDIO_FORMAT_S24, 0, 0, conv_f32_to_s24_c },
|
||||||
{ SPA_AUDIO_FORMAT_F32P, SPA_AUDIO_FORMAT_S24P, 0, conv_f32d_to_s24d_c },
|
{ SPA_AUDIO_FORMAT_F32P, SPA_AUDIO_FORMAT_S24P, 0, 0, conv_f32d_to_s24d_c },
|
||||||
{ SPA_AUDIO_FORMAT_F32, SPA_AUDIO_FORMAT_S24P, 0, conv_f32_to_s24d_c },
|
{ SPA_AUDIO_FORMAT_F32, SPA_AUDIO_FORMAT_S24P, 0, 0, conv_f32_to_s24d_c },
|
||||||
{ SPA_AUDIO_FORMAT_F32P, SPA_AUDIO_FORMAT_S24, 0, conv_f32d_to_s24_c },
|
{ SPA_AUDIO_FORMAT_F32P, SPA_AUDIO_FORMAT_S24, 0, 0, conv_f32d_to_s24_c },
|
||||||
|
|
||||||
{ SPA_AUDIO_FORMAT_F32, SPA_AUDIO_FORMAT_S24_32, 0, conv_f32_to_s24_32_c },
|
{ SPA_AUDIO_FORMAT_F32, SPA_AUDIO_FORMAT_S24_32, 0, 0, conv_f32_to_s24_32_c },
|
||||||
{ SPA_AUDIO_FORMAT_F32P, SPA_AUDIO_FORMAT_S24_32P, 0, conv_f32d_to_s24_32d_c },
|
{ SPA_AUDIO_FORMAT_F32P, SPA_AUDIO_FORMAT_S24_32P, 0, 0, conv_f32d_to_s24_32d_c },
|
||||||
{ SPA_AUDIO_FORMAT_F32, SPA_AUDIO_FORMAT_S24_32P, 0, conv_f32_to_s24_32d_c },
|
{ SPA_AUDIO_FORMAT_F32, SPA_AUDIO_FORMAT_S24_32P, 0, 0, conv_f32_to_s24_32d_c },
|
||||||
{ SPA_AUDIO_FORMAT_F32P, SPA_AUDIO_FORMAT_S24_32, 0, conv_f32d_to_s24_32_c },
|
{ SPA_AUDIO_FORMAT_F32P, SPA_AUDIO_FORMAT_S24_32, 0, 0, conv_f32d_to_s24_32_c },
|
||||||
|
|
||||||
/* u8 */
|
/* u8 */
|
||||||
{ SPA_AUDIO_FORMAT_U8, SPA_AUDIO_FORMAT_U8, 0, conv_copy8_c },
|
{ SPA_AUDIO_FORMAT_U8, SPA_AUDIO_FORMAT_U8, 0, 0, conv_copy8_c },
|
||||||
{ SPA_AUDIO_FORMAT_U8P, SPA_AUDIO_FORMAT_U8P, 0, conv_copy8d_c },
|
{ SPA_AUDIO_FORMAT_U8P, SPA_AUDIO_FORMAT_U8P, 0, 0, conv_copy8d_c },
|
||||||
{ SPA_AUDIO_FORMAT_U8, SPA_AUDIO_FORMAT_U8P, 0, conv_deinterleave_8_c },
|
{ SPA_AUDIO_FORMAT_U8, SPA_AUDIO_FORMAT_U8P, 0, 0, conv_deinterleave_8_c },
|
||||||
{ SPA_AUDIO_FORMAT_U8P, SPA_AUDIO_FORMAT_U8, 0, conv_interleave_8_c },
|
{ SPA_AUDIO_FORMAT_U8P, SPA_AUDIO_FORMAT_U8, 0, 0, conv_interleave_8_c },
|
||||||
|
|
||||||
/* s16 */
|
/* s16 */
|
||||||
{ SPA_AUDIO_FORMAT_S16, SPA_AUDIO_FORMAT_S16, 0, conv_copy16_c },
|
{ SPA_AUDIO_FORMAT_S16, SPA_AUDIO_FORMAT_S16, 0, 0, conv_copy16_c },
|
||||||
{ SPA_AUDIO_FORMAT_S16P, SPA_AUDIO_FORMAT_S16P, 0, conv_copy16d_c },
|
{ SPA_AUDIO_FORMAT_S16P, SPA_AUDIO_FORMAT_S16P, 0, 0, conv_copy16d_c },
|
||||||
{ SPA_AUDIO_FORMAT_S16, SPA_AUDIO_FORMAT_S16P, 0, conv_deinterleave_16_c },
|
{ SPA_AUDIO_FORMAT_S16, SPA_AUDIO_FORMAT_S16P, 0, 0, conv_deinterleave_16_c },
|
||||||
{ SPA_AUDIO_FORMAT_S16P, SPA_AUDIO_FORMAT_S16, 0, conv_interleave_16_c },
|
{ SPA_AUDIO_FORMAT_S16P, SPA_AUDIO_FORMAT_S16, 0, 0, conv_interleave_16_c },
|
||||||
|
|
||||||
/* s32 */
|
/* s32 */
|
||||||
{ SPA_AUDIO_FORMAT_S32, SPA_AUDIO_FORMAT_S32, 0, conv_copy32_c },
|
{ SPA_AUDIO_FORMAT_S32, SPA_AUDIO_FORMAT_S32, 0, 0, conv_copy32_c },
|
||||||
{ SPA_AUDIO_FORMAT_S32P, SPA_AUDIO_FORMAT_S32P, 0, conv_copy32d_c },
|
{ SPA_AUDIO_FORMAT_S32P, SPA_AUDIO_FORMAT_S32P, 0, 0, conv_copy32d_c },
|
||||||
{ SPA_AUDIO_FORMAT_S32, SPA_AUDIO_FORMAT_S32P, 0, conv_deinterleave_32_c },
|
{ SPA_AUDIO_FORMAT_S32, SPA_AUDIO_FORMAT_S32P, 0, 0, conv_deinterleave_32_c },
|
||||||
{ SPA_AUDIO_FORMAT_S32P, SPA_AUDIO_FORMAT_S32, 0, conv_interleave_32_c },
|
{ SPA_AUDIO_FORMAT_S32P, SPA_AUDIO_FORMAT_S32, 0, 0, conv_interleave_32_c },
|
||||||
|
|
||||||
/* s24 */
|
/* s24 */
|
||||||
{ SPA_AUDIO_FORMAT_S24, SPA_AUDIO_FORMAT_S24, 0, conv_copy24_c },
|
{ SPA_AUDIO_FORMAT_S24, SPA_AUDIO_FORMAT_S24, 0, 0, conv_copy24_c },
|
||||||
{ SPA_AUDIO_FORMAT_S24P, SPA_AUDIO_FORMAT_S24P, 0, conv_copy24d_c },
|
{ SPA_AUDIO_FORMAT_S24P, SPA_AUDIO_FORMAT_S24P, 0, 0, conv_copy24d_c },
|
||||||
{ SPA_AUDIO_FORMAT_S24, SPA_AUDIO_FORMAT_S24P, 0, conv_deinterleave_24_c },
|
{ SPA_AUDIO_FORMAT_S24, SPA_AUDIO_FORMAT_S24P, 0, 0, conv_deinterleave_24_c },
|
||||||
{ SPA_AUDIO_FORMAT_S24P, SPA_AUDIO_FORMAT_S24, 0, conv_interleave_24_c },
|
{ SPA_AUDIO_FORMAT_S24P, SPA_AUDIO_FORMAT_S24, 0, 0, conv_interleave_24_c },
|
||||||
|
|
||||||
/* s24_32 */
|
/* s24_32 */
|
||||||
{ SPA_AUDIO_FORMAT_S24_32, SPA_AUDIO_FORMAT_S24_32, 0, conv_copy32_c },
|
{ SPA_AUDIO_FORMAT_S24_32, SPA_AUDIO_FORMAT_S24_32, 0, 0, conv_copy32_c },
|
||||||
{ SPA_AUDIO_FORMAT_S24_32P, SPA_AUDIO_FORMAT_S24_32P, 0, conv_copy32d_c },
|
{ SPA_AUDIO_FORMAT_S24_32P, SPA_AUDIO_FORMAT_S24_32P, 0, 0, conv_copy32d_c },
|
||||||
{ SPA_AUDIO_FORMAT_S24_32, SPA_AUDIO_FORMAT_S24_32P, 0, conv_deinterleave_32_c },
|
{ SPA_AUDIO_FORMAT_S24_32, SPA_AUDIO_FORMAT_S24_32P, 0, 0, conv_deinterleave_32_c },
|
||||||
{ SPA_AUDIO_FORMAT_S24_32P, SPA_AUDIO_FORMAT_S24_32, 0, conv_interleave_32_c },
|
{ SPA_AUDIO_FORMAT_S24_32P, SPA_AUDIO_FORMAT_S24_32, 0, 0, conv_interleave_32_c },
|
||||||
};
|
};
|
||||||
|
|
||||||
static const struct conv_info *find_conv_info(uint32_t src_fmt, uint32_t dst_fmt, uint32_t features)
|
#define MATCH_CHAN(a,b) ((a) == 0 || (a) == (b))
|
||||||
|
#define MATCH_CPU_FLAGS(a,b) ((a) == 0 || ((a) & (b)) == a)
|
||||||
|
|
||||||
|
static const struct conv_info *find_conv_info(uint32_t src_fmt, uint32_t dst_fmt,
|
||||||
|
uint32_t n_channels, uint32_t cpu_flags)
|
||||||
{
|
{
|
||||||
size_t i;
|
size_t i;
|
||||||
|
|
||||||
for (i = 0; i < SPA_N_ELEMENTS(conv_table); i++) {
|
for (i = 0; i < SPA_N_ELEMENTS(conv_table); i++) {
|
||||||
if (conv_table[i].src_fmt == src_fmt &&
|
if (conv_table[i].src_fmt == src_fmt &&
|
||||||
conv_table[i].dst_fmt == dst_fmt &&
|
conv_table[i].dst_fmt == dst_fmt &&
|
||||||
(conv_table[i].features == 0 || (conv_table[i].features & features) != 0))
|
MATCH_CHAN(conv_table[i].n_channels, n_channels) &&
|
||||||
|
MATCH_CPU_FLAGS(conv_table[i].cpu_flags, cpu_flags))
|
||||||
return &conv_table[i];
|
return &conv_table[i];
|
||||||
}
|
}
|
||||||
return NULL;
|
return NULL;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
static void impl_convert_free(struct convert *conv)
|
||||||
|
{
|
||||||
|
conv->process = NULL;
|
||||||
|
}
|
||||||
|
|
||||||
|
int convert_init(struct convert *conv)
|
||||||
|
{
|
||||||
|
const struct conv_info *info;
|
||||||
|
|
||||||
|
info = find_conv_info(conv->src_fmt, conv->dst_fmt, conv->n_channels, conv->cpu_flags);
|
||||||
|
if (info == NULL)
|
||||||
|
return -ENOTSUP;
|
||||||
|
|
||||||
|
conv->is_passthrough = conv->src_fmt == conv->dst_fmt;
|
||||||
|
conv->cpu_flags = info->cpu_flags;
|
||||||
|
conv->process = info->process;
|
||||||
|
conv->free = impl_convert_free;
|
||||||
|
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
|
||||||
|
|
@ -77,13 +77,32 @@ static inline void write_s24(void *dst, int32_t val)
|
||||||
#endif
|
#endif
|
||||||
}
|
}
|
||||||
|
|
||||||
typedef void (*convert_func_t) (void *data, void * SPA_RESTRICT dst[], const void * SPA_RESTRICT src[],
|
#define MAX_NS 64
|
||||||
uint32_t n_channels, uint32_t n_samples);
|
|
||||||
|
struct convert {
|
||||||
|
uint32_t src_fmt;
|
||||||
|
uint32_t dst_fmt;
|
||||||
|
uint32_t n_channels;
|
||||||
|
uint32_t cpu_flags;
|
||||||
|
|
||||||
|
int is_passthrough:1;
|
||||||
|
float ns_data[MAX_NS];
|
||||||
|
uint32_t ns_idx;
|
||||||
|
uint32_t ns_size;
|
||||||
|
|
||||||
|
void (*process) (struct convert *conv, void * SPA_RESTRICT dst[], const void * SPA_RESTRICT src[],
|
||||||
|
uint32_t n_samples);
|
||||||
|
void (*free) (struct convert *conv);
|
||||||
|
};
|
||||||
|
|
||||||
|
int convert_init(struct convert *conv);
|
||||||
|
|
||||||
|
#define convert_process(conv,...) (conv)->process(conv, __VA_ARGS__)
|
||||||
|
#define convert_free(conv) (conv)->free(conv)
|
||||||
|
|
||||||
#define DEFINE_FUNCTION(name,arch) \
|
#define DEFINE_FUNCTION(name,arch) \
|
||||||
void conv_##name##_##arch(void *data, void * SPA_RESTRICT dst[], \
|
void conv_##name##_##arch(struct convert *conv, void * SPA_RESTRICT dst[], \
|
||||||
const void * SPA_RESTRICT src[], \
|
const void * SPA_RESTRICT src[], uint32_t n_samples) \
|
||||||
uint32_t n_channels, uint32_t n_samples)
|
|
||||||
|
|
||||||
DEFINE_FUNCTION(copy8d, c);
|
DEFINE_FUNCTION(copy8d, c);
|
||||||
DEFINE_FUNCTION(copy8, c);
|
DEFINE_FUNCTION(copy8, c);
|
||||||
|
|
@ -143,6 +162,7 @@ DEFINE_FUNCTION(interleave_24, c);
|
||||||
DEFINE_FUNCTION(interleave_32, c);
|
DEFINE_FUNCTION(interleave_32, c);
|
||||||
|
|
||||||
#if defined(HAVE_SSE2)
|
#if defined(HAVE_SSE2)
|
||||||
|
DEFINE_FUNCTION(s16_to_f32d_2, sse2);
|
||||||
DEFINE_FUNCTION(s16_to_f32d, sse2);
|
DEFINE_FUNCTION(s16_to_f32d, sse2);
|
||||||
DEFINE_FUNCTION(s24_to_f32d, sse2);
|
DEFINE_FUNCTION(s24_to_f32d, sse2);
|
||||||
DEFINE_FUNCTION(f32d_to_s32, sse2);
|
DEFINE_FUNCTION(f32d_to_s32, sse2);
|
||||||
|
|
|
||||||
|
|
@ -39,6 +39,8 @@
|
||||||
#include <spa/debug/types.h>
|
#include <spa/debug/types.h>
|
||||||
#include <spa/debug/format.h>
|
#include <spa/debug/format.h>
|
||||||
|
|
||||||
|
#include "fmt-ops.h"
|
||||||
|
|
||||||
#define NAME "fmtconvert"
|
#define NAME "fmtconvert"
|
||||||
|
|
||||||
#define DEFAULT_RATE 48000
|
#define DEFAULT_RATE 48000
|
||||||
|
|
@ -97,8 +99,6 @@ struct port {
|
||||||
struct spa_list queue;
|
struct spa_list queue;
|
||||||
};
|
};
|
||||||
|
|
||||||
#include "fmt-ops.c"
|
|
||||||
|
|
||||||
struct impl {
|
struct impl {
|
||||||
struct spa_handle handle;
|
struct spa_handle handle;
|
||||||
struct spa_node node;
|
struct spa_node node;
|
||||||
|
|
@ -120,7 +120,7 @@ struct impl {
|
||||||
bool started;
|
bool started;
|
||||||
|
|
||||||
uint32_t cpu_flags;
|
uint32_t cpu_flags;
|
||||||
convert_func_t convert;
|
struct convert conv;
|
||||||
int is_passthrough:1;
|
int is_passthrough:1;
|
||||||
};
|
};
|
||||||
|
|
||||||
|
|
@ -143,8 +143,8 @@ static int setup_convert(struct impl *this)
|
||||||
uint32_t src_fmt, dst_fmt;
|
uint32_t src_fmt, dst_fmt;
|
||||||
struct spa_audio_info informat, outformat;
|
struct spa_audio_info informat, outformat;
|
||||||
struct port *inport, *outport;
|
struct port *inport, *outport;
|
||||||
const struct conv_info *conv;
|
|
||||||
uint32_t i, j;
|
uint32_t i, j;
|
||||||
|
int res;
|
||||||
|
|
||||||
inport = GET_IN_PORT(this, 0);
|
inport = GET_IN_PORT(this, 0);
|
||||||
outport = GET_OUT_PORT(this, 0);
|
outport = GET_OUT_PORT(this, 0);
|
||||||
|
|
@ -181,16 +181,19 @@ static int setup_convert(struct impl *this)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
/* find fast path */
|
this->conv.src_fmt = src_fmt;
|
||||||
conv = find_conv_info(src_fmt, dst_fmt, this->cpu_flags);
|
this->conv.dst_fmt = dst_fmt;
|
||||||
if (conv == NULL)
|
this->conv.n_channels = outformat.info.raw.channels;
|
||||||
return -ENOTSUP;
|
this->conv.cpu_flags = this->cpu_flags;
|
||||||
|
|
||||||
|
if ((res = convert_init(&this->conv)) < 0)
|
||||||
|
return res;
|
||||||
|
|
||||||
spa_log_info(this->log, NAME " %p: got converter features %08x:%08x", this,
|
spa_log_info(this->log, NAME " %p: got converter features %08x:%08x", this,
|
||||||
this->cpu_flags, conv->features);
|
this->cpu_flags, this->conv.cpu_flags);
|
||||||
|
|
||||||
|
this->is_passthrough = this->conv.is_passthrough;
|
||||||
|
|
||||||
this->convert = conv->func;
|
|
||||||
this->is_passthrough = src_fmt == dst_fmt;
|
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -556,7 +559,7 @@ static int port_set_format(struct spa_node *node,
|
||||||
if (port->have_format) {
|
if (port->have_format) {
|
||||||
port->have_format = false;
|
port->have_format = false;
|
||||||
clear_buffers(this, port);
|
clear_buffers(this, port);
|
||||||
this->convert = NULL;
|
convert_free(&this->conv);
|
||||||
}
|
}
|
||||||
} else {
|
} else {
|
||||||
struct spa_audio_info info = { 0 };
|
struct spa_audio_info info = { 0 };
|
||||||
|
|
@ -801,7 +804,7 @@ static int impl_node_process(struct spa_node *node)
|
||||||
struct spa_buffer *inb, *outb;
|
struct spa_buffer *inb, *outb;
|
||||||
const void **src_datas;
|
const void **src_datas;
|
||||||
void **dst_datas;
|
void **dst_datas;
|
||||||
uint32_t i, n_src_datas, n_dst_datas, n_datas;
|
uint32_t i, n_src_datas, n_dst_datas;
|
||||||
int res = 0;
|
int res = 0;
|
||||||
uint32_t n_samples, size, maxsize, offs;
|
uint32_t n_samples, size, maxsize, offs;
|
||||||
|
|
||||||
|
|
@ -863,8 +866,6 @@ static int impl_node_process(struct spa_node *node)
|
||||||
spa_log_trace_fp(this->log, NAME " %p: n_src:%d n_dst:%d size:%d maxsize:%d n_samples:%d",
|
spa_log_trace_fp(this->log, NAME " %p: n_src:%d n_dst:%d size:%d maxsize:%d n_samples:%d",
|
||||||
this, n_src_datas, n_dst_datas, size, maxsize, n_samples);
|
this, n_src_datas, n_dst_datas, size, maxsize, n_samples);
|
||||||
|
|
||||||
n_datas = SPA_MAX(n_src_datas, n_dst_datas);
|
|
||||||
|
|
||||||
for (i = 0; i < n_dst_datas; i++) {
|
for (i = 0; i < n_dst_datas; i++) {
|
||||||
dst_datas[i] = this->is_passthrough ?
|
dst_datas[i] = this->is_passthrough ?
|
||||||
(void*)src_datas[i] :
|
(void*)src_datas[i] :
|
||||||
|
|
@ -875,7 +876,7 @@ static int impl_node_process(struct spa_node *node)
|
||||||
}
|
}
|
||||||
|
|
||||||
if (!this->is_passthrough)
|
if (!this->is_passthrough)
|
||||||
this->convert(this, dst_datas, src_datas, n_datas, n_samples);
|
convert_process(&this->conv, dst_datas, src_datas, n_samples);
|
||||||
|
|
||||||
inio->status = SPA_STATUS_NEED_BUFFER;
|
inio->status = SPA_STATUS_NEED_BUFFER;
|
||||||
res |= SPA_STATUS_NEED_BUFFER;
|
res |= SPA_STATUS_NEED_BUFFER;
|
||||||
|
|
|
||||||
|
|
@ -27,6 +27,7 @@
|
||||||
#include <stdio.h>
|
#include <stdio.h>
|
||||||
#include <limits.h>
|
#include <limits.h>
|
||||||
|
|
||||||
|
#include <spa/support/cpu.h>
|
||||||
#include <spa/support/log.h>
|
#include <spa/support/log.h>
|
||||||
#include <spa/utils/list.h>
|
#include <spa/utils/list.h>
|
||||||
#include <spa/node/node.h>
|
#include <spa/node/node.h>
|
||||||
|
|
@ -39,6 +40,8 @@
|
||||||
#include <spa/debug/mem.h>
|
#include <spa/debug/mem.h>
|
||||||
#include <spa/debug/pod.h>
|
#include <spa/debug/pod.h>
|
||||||
|
|
||||||
|
#include "fmt-ops.h"
|
||||||
|
|
||||||
#define NAME "merger"
|
#define NAME "merger"
|
||||||
|
|
||||||
#define DEFAULT_RATE 48000
|
#define DEFAULT_RATE 48000
|
||||||
|
|
@ -81,8 +84,6 @@ struct port {
|
||||||
struct spa_list queue;
|
struct spa_list queue;
|
||||||
};
|
};
|
||||||
|
|
||||||
#include "fmt-ops.c"
|
|
||||||
|
|
||||||
struct impl {
|
struct impl {
|
||||||
struct spa_handle handle;
|
struct spa_handle handle;
|
||||||
struct spa_node node;
|
struct spa_node node;
|
||||||
|
|
@ -101,7 +102,7 @@ struct impl {
|
||||||
struct port in_ports[MAX_PORTS];
|
struct port in_ports[MAX_PORTS];
|
||||||
struct port out_ports[MAX_PORTS + 1];
|
struct port out_ports[MAX_PORTS + 1];
|
||||||
|
|
||||||
convert_func_t convert;
|
struct convert conv;
|
||||||
uint32_t cpu_flags;
|
uint32_t cpu_flags;
|
||||||
int is_passthrough:1;
|
int is_passthrough:1;
|
||||||
int started:1;
|
int started:1;
|
||||||
|
|
@ -543,9 +544,9 @@ static int clear_buffers(struct impl *this, struct port *port)
|
||||||
|
|
||||||
static int setup_convert(struct impl *this)
|
static int setup_convert(struct impl *this)
|
||||||
{
|
{
|
||||||
const struct conv_info *conv;
|
|
||||||
struct port *outport;
|
struct port *outport;
|
||||||
uint32_t src_fmt, dst_fmt;
|
uint32_t src_fmt, dst_fmt;
|
||||||
|
int res;
|
||||||
|
|
||||||
outport = GET_OUT_PORT(this, 0);
|
outport = GET_OUT_PORT(this, 0);
|
||||||
|
|
||||||
|
|
@ -561,16 +562,20 @@ static int setup_convert(struct impl *this)
|
||||||
outport->format.info.raw.channels,
|
outport->format.info.raw.channels,
|
||||||
outport->format.info.raw.rate);
|
outport->format.info.raw.rate);
|
||||||
|
|
||||||
conv = find_conv_info(src_fmt, dst_fmt, this->cpu_flags);
|
this->conv.src_fmt = src_fmt;
|
||||||
if (conv != NULL) {
|
this->conv.dst_fmt = dst_fmt;
|
||||||
spa_log_info(this->log, NAME " %p: got converter features %08x:%08x", this,
|
this->conv.n_channels = outport->format.info.raw.channels;
|
||||||
this->cpu_flags, conv->features);
|
this->conv.cpu_flags = this->cpu_flags;
|
||||||
|
|
||||||
this->convert = conv->func;
|
if ((res = convert_init(&this->conv)) < 0)
|
||||||
this->is_passthrough = src_fmt == dst_fmt;
|
return res;
|
||||||
return 0;
|
|
||||||
}
|
spa_log_info(this->log, NAME " %p: got converter features %08x:%08x", this,
|
||||||
return -ENOTSUP;
|
this->cpu_flags, this->conv.cpu_flags);
|
||||||
|
|
||||||
|
this->is_passthrough = src_fmt == dst_fmt;
|
||||||
|
|
||||||
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
static int calc_width(struct spa_audio_info *info)
|
static int calc_width(struct spa_audio_info *info)
|
||||||
|
|
@ -942,7 +947,7 @@ static int impl_node_process(struct spa_node *node)
|
||||||
outport = GET_OUT_PORT(this, 0);
|
outport = GET_OUT_PORT(this, 0);
|
||||||
outio = outport->io;
|
outio = outport->io;
|
||||||
spa_return_val_if_fail(outio != NULL, -EIO);
|
spa_return_val_if_fail(outio != NULL, -EIO);
|
||||||
spa_return_val_if_fail(this->convert != NULL, -EIO);
|
spa_return_val_if_fail(this->conv.process != NULL, -EIO);
|
||||||
|
|
||||||
spa_log_trace_fp(this->log, NAME " %p: status %d %d", this, outio->status, outio->buffer_id);
|
spa_log_trace_fp(this->log, NAME " %p: status %d %d", this, outio->status, outio->buffer_id);
|
||||||
|
|
||||||
|
|
@ -995,7 +1000,7 @@ static int impl_node_process(struct spa_node *node)
|
||||||
n_samples * outport->stride);
|
n_samples * outport->stride);
|
||||||
}
|
}
|
||||||
if (!this->is_passthrough)
|
if (!this->is_passthrough)
|
||||||
this->convert(this, dst_datas, src_datas, SPA_MAX(n_dst_datas, n_src_datas), n_samples);
|
convert_process(&this->conv, dst_datas, src_datas, n_samples);
|
||||||
|
|
||||||
return res | SPA_STATUS_HAVE_BUFFER;
|
return res | SPA_STATUS_HAVE_BUFFER;
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -1,5 +1,7 @@
|
||||||
audioconvert_sources = ['fmtconvert.c',
|
audioconvert_sources = ['fmtconvert.c',
|
||||||
|
'fmt-ops.c',
|
||||||
'channelmix.c',
|
'channelmix.c',
|
||||||
|
'channelmix-ops.c',
|
||||||
'resample.c',
|
'resample.c',
|
||||||
'splitter.c',
|
'splitter.c',
|
||||||
'merger.c',
|
'merger.c',
|
||||||
|
|
@ -23,7 +25,7 @@ if have_sse
|
||||||
audioconvert_sse = static_library('audioconvert_sse',
|
audioconvert_sse = static_library('audioconvert_sse',
|
||||||
['resample-native-sse.c',
|
['resample-native-sse.c',
|
||||||
'channelmix-ops-sse.c' ],
|
'channelmix-ops-sse.c' ],
|
||||||
c_args : [sse_args, '-O3'],
|
c_args : [sse_args, '-O3', '-DHAVE_SSE'],
|
||||||
include_directories : [spa_inc],
|
include_directories : [spa_inc],
|
||||||
install : false
|
install : false
|
||||||
)
|
)
|
||||||
|
|
@ -33,7 +35,7 @@ endif
|
||||||
if have_sse2
|
if have_sse2
|
||||||
audioconvert_sse2 = static_library('audioconvert_sse2',
|
audioconvert_sse2 = static_library('audioconvert_sse2',
|
||||||
['fmt-ops-sse2.c' ],
|
['fmt-ops-sse2.c' ],
|
||||||
c_args : [sse2_args, '-O3'],
|
c_args : [sse2_args, '-O3', '-DHAVE_SSE2'],
|
||||||
include_directories : [spa_inc],
|
include_directories : [spa_inc],
|
||||||
install : false
|
install : false
|
||||||
)
|
)
|
||||||
|
|
@ -44,7 +46,7 @@ if have_ssse3
|
||||||
audioconvert_ssse3 = static_library('audioconvert_ssse3',
|
audioconvert_ssse3 = static_library('audioconvert_ssse3',
|
||||||
['fmt-ops-ssse3.c',
|
['fmt-ops-ssse3.c',
|
||||||
'resample-native-ssse3.c' ],
|
'resample-native-ssse3.c' ],
|
||||||
c_args : [ssse3_args, '-O3'],
|
c_args : [ssse3_args, '-O3', '-DHAVE_SSSE3'],
|
||||||
include_directories : [spa_inc],
|
include_directories : [spa_inc],
|
||||||
install : false
|
install : false
|
||||||
)
|
)
|
||||||
|
|
@ -54,7 +56,7 @@ endif
|
||||||
if have_sse41
|
if have_sse41
|
||||||
audioconvert_sse41 = static_library('audioconvert_sse41',
|
audioconvert_sse41 = static_library('audioconvert_sse41',
|
||||||
['fmt-ops-sse41.c'],
|
['fmt-ops-sse41.c'],
|
||||||
c_args : [sse41_args, '-O3'],
|
c_args : [sse41_args, '-O3', '-DHAVE_SSE41'],
|
||||||
include_directories : [spa_inc],
|
include_directories : [spa_inc],
|
||||||
install : false
|
install : false
|
||||||
)
|
)
|
||||||
|
|
@ -64,7 +66,7 @@ endif
|
||||||
if have_avx and have_fma
|
if have_avx and have_fma
|
||||||
audioconvert_avx = static_library('audioconvert_avx',
|
audioconvert_avx = static_library('audioconvert_avx',
|
||||||
['resample-native-avx.c'],
|
['resample-native-avx.c'],
|
||||||
c_args : [avx2_args, fma_args, '-O3'],
|
c_args : [avx2_args, fma_args, '-O3', '-DHAVE_AVX', '-DHAVE_FMA'],
|
||||||
include_directories : [spa_inc],
|
include_directories : [spa_inc],
|
||||||
install : false
|
install : false
|
||||||
)
|
)
|
||||||
|
|
|
||||||
|
|
@ -27,6 +27,7 @@
|
||||||
#include <stdio.h>
|
#include <stdio.h>
|
||||||
#include <limits.h>
|
#include <limits.h>
|
||||||
|
|
||||||
|
#include <spa/support/cpu.h>
|
||||||
#include <spa/support/log.h>
|
#include <spa/support/log.h>
|
||||||
#include <spa/utils/list.h>
|
#include <spa/utils/list.h>
|
||||||
#include <spa/node/node.h>
|
#include <spa/node/node.h>
|
||||||
|
|
@ -38,6 +39,8 @@
|
||||||
#include <spa/debug/mem.h>
|
#include <spa/debug/mem.h>
|
||||||
#include <spa/debug/pod.h>
|
#include <spa/debug/pod.h>
|
||||||
|
|
||||||
|
#include "fmt-ops.h"
|
||||||
|
|
||||||
#define NAME "splitter"
|
#define NAME "splitter"
|
||||||
|
|
||||||
#define DEFAULT_RATE 48000
|
#define DEFAULT_RATE 48000
|
||||||
|
|
@ -84,8 +87,6 @@ struct port {
|
||||||
struct spa_list queue;
|
struct spa_list queue;
|
||||||
};
|
};
|
||||||
|
|
||||||
#include "fmt-ops.c"
|
|
||||||
|
|
||||||
struct impl {
|
struct impl {
|
||||||
struct spa_handle handle;
|
struct spa_handle handle;
|
||||||
struct spa_node node;
|
struct spa_node node;
|
||||||
|
|
@ -104,7 +105,7 @@ struct impl {
|
||||||
uint32_t port_count;
|
uint32_t port_count;
|
||||||
|
|
||||||
uint32_t cpu_flags;
|
uint32_t cpu_flags;
|
||||||
convert_func_t convert;
|
struct convert conv;
|
||||||
int is_passthrough:1;
|
int is_passthrough:1;
|
||||||
int started:1;
|
int started:1;
|
||||||
|
|
||||||
|
|
@ -530,9 +531,9 @@ static int clear_buffers(struct impl *this, struct port *port)
|
||||||
|
|
||||||
static int setup_convert(struct impl *this)
|
static int setup_convert(struct impl *this)
|
||||||
{
|
{
|
||||||
const struct conv_info *conv;
|
|
||||||
struct port *inport;
|
struct port *inport;
|
||||||
uint32_t src_fmt, dst_fmt;
|
uint32_t src_fmt, dst_fmt;
|
||||||
|
int res;
|
||||||
|
|
||||||
inport = GET_IN_PORT(this, 0);
|
inport = GET_IN_PORT(this, 0);
|
||||||
|
|
||||||
|
|
@ -548,16 +549,21 @@ static int setup_convert(struct impl *this)
|
||||||
inport->format.info.raw.rate,
|
inport->format.info.raw.rate,
|
||||||
this->port_count);
|
this->port_count);
|
||||||
|
|
||||||
conv = find_conv_info(src_fmt, dst_fmt, this->cpu_flags);
|
|
||||||
if (conv != NULL) {
|
|
||||||
spa_log_info(this->log, NAME " %p: got converter features %08x:%08x", this,
|
|
||||||
this->cpu_flags, conv->features);
|
|
||||||
|
|
||||||
this->convert = conv->func;
|
this->conv.src_fmt = src_fmt;
|
||||||
this->is_passthrough = src_fmt == dst_fmt;
|
this->conv.dst_fmt = dst_fmt;
|
||||||
return 0;
|
this->conv.n_channels = inport->format.info.raw.channels;
|
||||||
}
|
this->conv.cpu_flags = this->cpu_flags;
|
||||||
return -ENOTSUP;
|
|
||||||
|
if ((res = convert_init(&this->conv)) < 0)
|
||||||
|
return res;
|
||||||
|
|
||||||
|
spa_log_info(this->log, NAME " %p: got converter features %08x:%08x", this,
|
||||||
|
this->cpu_flags, this->conv.cpu_flags);
|
||||||
|
|
||||||
|
this->is_passthrough = this->conv.is_passthrough;
|
||||||
|
|
||||||
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
static int calc_width(struct spa_audio_info *info)
|
static int calc_width(struct spa_audio_info *info)
|
||||||
|
|
@ -846,7 +852,7 @@ static int impl_node_process(struct spa_node *node)
|
||||||
inport = GET_IN_PORT(this, 0);
|
inport = GET_IN_PORT(this, 0);
|
||||||
inio = inport->io;
|
inio = inport->io;
|
||||||
spa_return_val_if_fail(inio != NULL, -EIO);
|
spa_return_val_if_fail(inio != NULL, -EIO);
|
||||||
spa_return_val_if_fail(this->convert != NULL, -EIO);
|
spa_return_val_if_fail(this->conv.process != NULL, -EIO);
|
||||||
|
|
||||||
spa_log_trace_fp(this->log, NAME " %p: status %p %d %d", this,
|
spa_log_trace_fp(this->log, NAME " %p: status %p %d %d", this,
|
||||||
inio, inio->status, inio->buffer_id);
|
inio, inio->status, inio->buffer_id);
|
||||||
|
|
@ -924,7 +930,7 @@ static int impl_node_process(struct spa_node *node)
|
||||||
n_src_datas, n_dst_datas, n_samples, maxsize, inport->stride);
|
n_src_datas, n_dst_datas, n_samples, maxsize, inport->stride);
|
||||||
|
|
||||||
if (!this->is_passthrough)
|
if (!this->is_passthrough)
|
||||||
this->convert(this, dst_datas, src_datas, SPA_MAX(n_dst_datas, n_src_datas), n_samples);
|
convert_process(&this->conv, dst_datas, src_datas, n_samples);
|
||||||
|
|
||||||
inio->status = SPA_STATUS_NEED_BUFFER;
|
inio->status = SPA_STATUS_NEED_BUFFER;
|
||||||
res |= SPA_STATUS_NEED_BUFFER;
|
res |= SPA_STATUS_NEED_BUFFER;
|
||||||
|
|
|
||||||
|
|
@ -49,6 +49,9 @@ static void run_test(const char *name,
|
||||||
void *tp[N_CHANNELS];
|
void *tp[N_CHANNELS];
|
||||||
int i, j;
|
int i, j;
|
||||||
const uint8_t *in8 = in, *out8 = out;
|
const uint8_t *in8 = in, *out8 = out;
|
||||||
|
struct convert conv;
|
||||||
|
|
||||||
|
conv.n_channels = N_CHANNELS;
|
||||||
|
|
||||||
for (j = 0; j < N_SAMPLES; j++) {
|
for (j = 0; j < N_SAMPLES; j++) {
|
||||||
memcpy(&samp_in[j * in_size], &in8[(j % n_samples) * in_size], in_size);
|
memcpy(&samp_in[j * in_size], &in8[(j % n_samples) * in_size], in_size);
|
||||||
|
|
@ -62,16 +65,16 @@ static void run_test(const char *name,
|
||||||
tp[0] = temp_in;
|
tp[0] = temp_in;
|
||||||
switch(in_size) {
|
switch(in_size) {
|
||||||
case 1:
|
case 1:
|
||||||
conv_interleave_8_c(NULL, tp, ip, N_CHANNELS, N_SAMPLES);
|
conv_interleave_8_c(&conv, tp, ip, N_SAMPLES);
|
||||||
break;
|
break;
|
||||||
case 2:
|
case 2:
|
||||||
conv_interleave_16_c(NULL, tp, ip, N_CHANNELS, N_SAMPLES);
|
conv_interleave_16_c(&conv, tp, ip, N_SAMPLES);
|
||||||
break;
|
break;
|
||||||
case 3:
|
case 3:
|
||||||
conv_interleave_24_c(NULL, tp, ip, N_CHANNELS, N_SAMPLES);
|
conv_interleave_24_c(&conv, tp, ip, N_SAMPLES);
|
||||||
break;
|
break;
|
||||||
case 4:
|
case 4:
|
||||||
conv_interleave_32_c(NULL, tp, ip, N_CHANNELS, N_SAMPLES);
|
conv_interleave_32_c(&conv, tp, ip, N_SAMPLES);
|
||||||
break;
|
break;
|
||||||
default:
|
default:
|
||||||
fprintf(stderr, "unknown size %zd\n", in_size);
|
fprintf(stderr, "unknown size %zd\n", in_size);
|
||||||
|
|
@ -84,7 +87,7 @@ static void run_test(const char *name,
|
||||||
for (j = 0; j < N_CHANNELS; j++)
|
for (j = 0; j < N_CHANNELS; j++)
|
||||||
tp[j] = &temp_out[j * N_SAMPLES * out_size];
|
tp[j] = &temp_out[j * N_SAMPLES * out_size];
|
||||||
|
|
||||||
func(NULL, tp, ip, N_CHANNELS, N_SAMPLES);
|
func(&conv, tp, ip, N_SAMPLES);
|
||||||
|
|
||||||
fprintf(stderr, "test %s:\n", name);
|
fprintf(stderr, "test %s:\n", name);
|
||||||
if (out_packed) {
|
if (out_packed) {
|
||||||
|
|
@ -260,8 +263,6 @@ static void test_s24_32_f32(void)
|
||||||
int main(int argc, char *argv[])
|
int main(int argc, char *argv[])
|
||||||
{
|
{
|
||||||
|
|
||||||
find_conv_info(0, 0, 0);
|
|
||||||
|
|
||||||
test_f32_u8();
|
test_f32_u8();
|
||||||
test_u8_f32();
|
test_u8_f32();
|
||||||
test_f32_s16();
|
test_f32_s16();
|
||||||
|
|
|
||||||
Loading…
Add table
Add a link
Reference in a new issue