audioconvert: expose the selected function names

And debug them.
This commit is contained in:
Wim Taymans 2022-06-28 16:45:07 +02:00
parent 048e10ee3b
commit 51f4f1fb69
8 changed files with 77 additions and 48 deletions

View file

@ -1124,8 +1124,9 @@ static int setup_in_convert(struct impl *this)
if ((res = convert_init(&in->conv)) < 0)
return res;
spa_log_debug(this->log, "%p: got converter features %08x:%08x passthrough:%d", this,
this->cpu_flags, in->conv.cpu_flags, in->conv.is_passthrough);
spa_log_debug(this->log, "%p: got converter features %08x:%08x passthrough:%d %s", this,
this->cpu_flags, in->conv.cpu_flags, in->conv.is_passthrough,
in->conv.func_name);
return 0;
}
@ -1300,9 +1301,9 @@ static int setup_channelmix(struct impl *this)
set_volume(this);
spa_log_debug(this->log, "%p: got channelmix features %08x:%08x flags:%08x",
spa_log_debug(this->log, "%p: got channelmix features %08x:%08x flags:%08x %s",
this, this->cpu_flags, this->mix.cpu_flags,
this->mix.flags);
this->mix.flags, this->mix.func_name);
return 0;
}
@ -1335,6 +1336,9 @@ static int setup_resample(struct impl *this)
else
res = resample_native_init(&this->resample);
spa_log_debug(this->log, "%p: got resample features %08x:%08x %s",
this, this->cpu_flags, this->resample.cpu_flags,
this->resample.func_name);
return res;
}

View file

@ -52,6 +52,9 @@
typedef void (*channelmix_func_t) (struct channelmix *mix, void * SPA_RESTRICT dst[],
const void * SPA_RESTRICT src[], uint32_t n_samples);
#define MAKE(sc,sm,dc,dm,func,...) \
{ sc, sm, dc, dm, func, #func, __VA_ARGS__ }
static const struct channelmix_info {
uint32_t src_chan;
uint64_t src_mask;
@ -59,51 +62,53 @@ static const struct channelmix_info {
uint64_t dst_mask;
channelmix_func_t process;
uint32_t cpu_flags;
const char *name;
uint32_t cpu_flags;
} channelmix_table[] =
{
#if defined (HAVE_SSE)
{ 2, MASK_MONO, 2, MASK_MONO, channelmix_copy_sse, SPA_CPU_FLAG_SSE, "copy_sse" },
{ 2, MASK_STEREO, 2, MASK_STEREO, channelmix_copy_sse, SPA_CPU_FLAG_SSE, "copy_sse" },
{ EQ, 0, EQ, 0, channelmix_copy_sse, SPA_CPU_FLAG_SSE, "copy_sse" },
MAKE(2, MASK_MONO, 2, MASK_MONO, channelmix_copy_sse, SPA_CPU_FLAG_SSE),
MAKE(2, MASK_STEREO, 2, MASK_STEREO, channelmix_copy_sse, SPA_CPU_FLAG_SSE),
MAKE(EQ, 0, EQ, 0, channelmix_copy_sse, SPA_CPU_FLAG_SSE),
#endif
{ 2, MASK_MONO, 2, MASK_MONO, channelmix_copy_c, 0, "copy_c" },
{ 2, MASK_STEREO, 2, MASK_STEREO, channelmix_copy_c, 0, "copy_c" },
{ EQ, 0, EQ, 0, channelmix_copy_c, 0 },
MAKE(2, MASK_MONO, 2, MASK_MONO, channelmix_copy_c),
MAKE(2, MASK_STEREO, 2, MASK_STEREO, channelmix_copy_c),
MAKE(EQ, 0, EQ, 0, channelmix_copy_c),
{ 1, MASK_MONO, 2, MASK_STEREO, channelmix_f32_1_2_c, 0, "f32_1_2_c" },
{ 2, MASK_STEREO, 1, MASK_MONO, channelmix_f32_2_1_c, 0, "f32_2_1_c" },
{ 4, MASK_QUAD, 1, MASK_MONO, channelmix_f32_4_1_c, 0, "f32_4_1_c" },
{ 4, MASK_3_1, 1, MASK_MONO, channelmix_f32_4_1_c, 0, "f32_4_1_c" },
{ 2, MASK_STEREO, 4, MASK_QUAD, channelmix_f32_2_4_c, 0, "f32_2_4_c" },
{ 2, MASK_STEREO, 4, MASK_3_1, channelmix_f32_2_3p1_c, 0, "f32_2_3p1_c" },
{ 2, MASK_STEREO, 6, MASK_5_1, channelmix_f32_2_5p1_c, 0, "f32_2_5p1_c" },
{ 2, MASK_STEREO, 8, MASK_7_1, channelmix_f32_2_7p1_c, 0, "f32_2_7p1_c" },
MAKE(1, MASK_MONO, 2, MASK_STEREO, channelmix_f32_1_2_c),
MAKE(2, MASK_STEREO, 1, MASK_MONO, channelmix_f32_2_1_c),
MAKE(4, MASK_QUAD, 1, MASK_MONO, channelmix_f32_4_1_c),
MAKE(4, MASK_3_1, 1, MASK_MONO, channelmix_f32_4_1_c),
MAKE(2, MASK_STEREO, 4, MASK_QUAD, channelmix_f32_2_4_c),
MAKE(2, MASK_STEREO, 4, MASK_3_1, channelmix_f32_2_3p1_c),
MAKE(2, MASK_STEREO, 6, MASK_5_1, channelmix_f32_2_5p1_c),
MAKE(2, MASK_STEREO, 8, MASK_7_1, channelmix_f32_2_7p1_c),
#if defined (HAVE_SSE)
{ 4, MASK_3_1, 2, MASK_STEREO, channelmix_f32_3p1_2_sse, 0, "f32_3p1_2_sse" },
MAKE(4, MASK_3_1, 2, MASK_STEREO, channelmix_f32_3p1_2_sse, SPA_CPU_FLAG_SSE),
#endif
{ 4, MASK_3_1, 2, MASK_STEREO, channelmix_f32_3p1_2_c, 0, "f32_3p1_2_c" },
MAKE(4, MASK_3_1, 2, MASK_STEREO, channelmix_f32_3p1_2_c),
#if defined (HAVE_SSE)
{ 6, MASK_5_1, 2, MASK_STEREO, channelmix_f32_5p1_2_sse, SPA_CPU_FLAG_SSE, "f32_5p1_2_sse" },
MAKE(6, MASK_5_1, 2, MASK_STEREO, channelmix_f32_5p1_2_sse, SPA_CPU_FLAG_SSE),
#endif
{ 6, MASK_5_1, 2, MASK_STEREO, channelmix_f32_5p1_2_c, 0, "f32_5p1_2_c" },
MAKE(6, MASK_5_1, 2, MASK_STEREO, channelmix_f32_5p1_2_c),
#if defined (HAVE_SSE)
{ 6, MASK_5_1, 4, MASK_QUAD, channelmix_f32_5p1_4_sse, SPA_CPU_FLAG_SSE, "f32_5p1_4_sse" },
MAKE(6, MASK_5_1, 4, MASK_QUAD, channelmix_f32_5p1_4_sse, SPA_CPU_FLAG_SSE),
#endif
{ 6, MASK_5_1, 4, MASK_QUAD, channelmix_f32_5p1_4_c, 0, "f32_5p1_4_c" },
MAKE(6, MASK_5_1, 4, MASK_QUAD, channelmix_f32_5p1_4_c),
#if defined (HAVE_SSE)
{ 6, MASK_5_1, 4, MASK_3_1, channelmix_f32_5p1_3p1_sse, SPA_CPU_FLAG_SSE, "f32_5p1_3p1_sse" },
MAKE(6, MASK_5_1, 4, MASK_3_1, channelmix_f32_5p1_3p1_sse, SPA_CPU_FLAG_SSE),
#endif
{ 6, MASK_5_1, 4, MASK_3_1, channelmix_f32_5p1_3p1_c, 0, "f32_5p1_3p1_c" },
MAKE(6, MASK_5_1, 4, MASK_3_1, channelmix_f32_5p1_3p1_c),
{ 8, MASK_7_1, 2, MASK_STEREO, channelmix_f32_7p1_2_c, 0, "f32_7p1_2_c" },
{ 8, MASK_7_1, 4, MASK_QUAD, channelmix_f32_7p1_4_c, 0, "f32_7p1_4_c" },
{ 8, MASK_7_1, 4, MASK_3_1, channelmix_f32_7p1_3p1_c, 0, "f32_7p1_3p1_c" },
MAKE(8, MASK_7_1, 2, MASK_STEREO, channelmix_f32_7p1_2_c),
MAKE(8, MASK_7_1, 4, MASK_QUAD, channelmix_f32_7p1_4_c),
MAKE(8, MASK_7_1, 4, MASK_3_1, channelmix_f32_7p1_3p1_c),
{ ANY, 0, ANY, 0, channelmix_f32_n_m_c, 0, "f32_n_m_c" },
MAKE(ANY, 0, ANY, 0, channelmix_f32_n_m_c),
};
#undef MAKE
#define MATCH_CHAN(a,b) ((a) == ANY || (a) == (b))
#define MATCH_CPU_FLAGS(a,b) ((a) == 0 || ((a) & (b)) == a)
@ -563,6 +568,7 @@ int channelmix_init(struct channelmix *mix)
mix->set_volume = impl_channelmix_set_volume;
mix->cpu_flags = info->cpu_flags;
mix->delay = mix->rear_delay * mix->freq / 1000.0f;
mix->func_name = info->name;
spa_log_debug(mix->log, "selected %s delay:%d options:%08x", info->name, mix->delay,
mix->options);

View file

@ -62,6 +62,7 @@ struct channelmix {
uint32_t upmix;
struct spa_log *log;
const char *func_name;
#define CHANNELMIX_FLAG_ZERO (1<<0) /**< all zero components */
#define CHANNELMIX_FLAG_IDENTITY (1<<1) /**< identity matrix */

View file

@ -34,10 +34,13 @@ typedef void (*resample_func_t)(struct resample *r,
struct resample_info {
uint32_t format;
uint32_t cpu_flags;
resample_func_t process_copy;
const char *copy_name;
resample_func_t process_full;
const char *full_name;
resample_func_t process_inter;
const char *inter_name;
uint32_t cpu_flags;
};
struct native_data {

View file

@ -124,27 +124,27 @@ MAKE_RESAMPLER_COPY(c);
MAKE_RESAMPLER_FULL(c);
MAKE_RESAMPLER_INTER(c);
#define MAKE(fmt,copy,full,inter,...) \
{ SPA_AUDIO_FORMAT_ ##fmt, do_resample_ ##copy, #copy, \
do_resample_ ##full, #full, do_resample_ ##inter, #inter, __VA_ARGS__ }
static struct resample_info resample_table[] =
{
#if defined (HAVE_NEON)
{ SPA_AUDIO_FORMAT_F32, SPA_CPU_FLAG_NEON,
do_resample_copy_c, do_resample_full_neon, do_resample_inter_neon },
MAKE(F32, copy_c, full_neon, inter_neon, SPA_CPU_FLAG_NEON),
#endif
#if defined(HAVE_AVX) && defined(HAVE_FMA)
{ SPA_AUDIO_FORMAT_F32, SPA_CPU_FLAG_AVX | SPA_CPU_FLAG_FMA3,
do_resample_copy_c, do_resample_full_avx, do_resample_inter_avx },
MAKE(F32, copy_c, full_avx, inter_avx, SPA_CPU_FLAG_AVX | SPA_CPU_FLAG_FMA3),
#endif
#if defined (HAVE_SSSE3)
{ SPA_AUDIO_FORMAT_F32, SPA_CPU_FLAG_SSSE3 | SPA_CPU_FLAG_SLOW_UNALIGNED,
do_resample_copy_c, do_resample_full_ssse3, do_resample_inter_ssse3 },
MAKE(F32, copy_c, full_ssse3, inter_ssse3, SPA_CPU_FLAG_SSSE3 | SPA_CPU_FLAG_SLOW_UNALIGNED),
#endif
#if defined (HAVE_SSE)
{ SPA_AUDIO_FORMAT_F32, SPA_CPU_FLAG_SSE,
do_resample_copy_c, do_resample_full_sse, do_resample_inter_sse },
MAKE(F32, copy_c, full_sse, inter_sse, SPA_CPU_FLAG_SSE),
#endif
{ SPA_AUDIO_FORMAT_F32, 0,
do_resample_copy_c, do_resample_full_c, do_resample_inter_c },
MAKE(F32, copy_c, full_c, inter_c),
};
#undef MAKE
#define MATCH_CPU_FLAGS(a,b) ((a) == 0 || ((a) & (b)) == a)
static const struct resample_info *find_resample_info(uint32_t format, uint32_t cpu_flags)
@ -200,12 +200,18 @@ static void impl_native_update_rate(struct resample *r, double rate)
data->inc = data->in_rate / data->out_rate;
data->frac = data->in_rate % data->out_rate;
if (data->in_rate == data->out_rate)
if (data->in_rate == data->out_rate) {
data->func = data->info->process_copy;
else if (rate == 1.0)
r->func_name = data->info->copy_name;
}
else if (rate == 1.0) {
data->func = data->info->process_full;
else
r->func_name = data->info->full_name;
}
else {
data->func = data->info->process_inter;
r->func_name = data->info->inter_name;
}
spa_log_trace_fp(r->log, "native %p: rate:%f in:%d out:%d phase:%d inc:%d frac:%d", r,
rate, data->in_rate, data->out_rate, data->phase, data->inc, data->frac);

View file

@ -31,11 +31,13 @@
#define RESAMPLE_DEFAULT_QUALITY 4
struct resample {
struct spa_log *log;
uint32_t cpu_flags;
const char *func_name;
uint32_t channels;
uint32_t i_rate;
uint32_t o_rate;
struct spa_log *log;
double rate;
int quality;

View file

@ -36,16 +36,21 @@
typedef void (*volume_func_t) (struct volume *vol, void * SPA_RESTRICT dst,
const void * SPA_RESTRICT src, float volume, uint32_t n_samples);
#define MAKE(func,...) \
{ func, #func , __VA_ARGS__ }
static const struct volume_info {
volume_func_t process;
const char *name;
uint32_t cpu_flags;
} volume_table[] =
{
#if defined (HAVE_SSE)
{ volume_f32_sse, SPA_CPU_FLAG_SSE },
MAKE(volume_f32_sse, SPA_CPU_FLAG_SSE),
#endif
{ volume_f32_c, 0 },
MAKE(volume_f32_c),
};
#undef MAKE
#define MATCH_CPU_FLAGS(a,b) ((a) == 0 || ((a) & (b)) == a)
@ -74,6 +79,7 @@ int volume_init(struct volume *vol)
return -ENOTSUP;
vol->cpu_flags = info->cpu_flags;
vol->func_name = info->name;
vol->free = impl_volume_free;
vol->process = info->process;
return 0;

View file

@ -33,6 +33,7 @@
struct volume {
uint32_t cpu_flags;
const char *func_name;
struct spa_log *log;