Asterisk - The Open Source Telephony Project GIT-master-0bf3178
Macros | Functions
bridge_softmix_binaural.c File Reference

Multi-party software based binaural mixing. More...

#include "include/bridge_softmix_internal.h"
Include dependency graph for bridge_softmix_binaural.c:

Go to the source code of this file.

Macros

#define CONVOLUTION_SAMPLE_SIZE   960
 
#define CONVOLVE_CHANNEL_PREALLOC   3
 
#define CONVOLVE_MAX_BUFFER   4096
 

Functions

void add_binaural_mixing (struct ast_bridge *bridge, struct softmix_bridge_data *softmix_data, unsigned int softmix_samples, struct softmix_mixing_array *mixing_array, struct softmix_channel *sc, const char *channel_name)
 Processes audio data with the binaural synthesis and adds the result to the mixing array. More...
 
void binaural_mixing (struct ast_bridge *bridge, struct softmix_bridge_data *softmix_data, struct softmix_mixing_array *mixing_array, int16_t *bin_buf, int16_t *ann_buf)
 Mixes all binaural audio data contained in the mixing array. More...
 
void check_binaural_position_change (struct ast_bridge *bridge, struct softmix_bridge_data *softmix_data)
 Checks if a position change in the virtual enviroment is requested by one of the participants. More...
 
void create_binaural_frame (struct ast_bridge_channel *bridge_channel, struct softmix_channel *sc, int16_t *bin_buf, int16_t *ann_buf, unsigned int softmix_datalen, unsigned int softmix_samples, int16_t *buf)
 Creates a frame out of binaural audio data. More...
 
int do_convolve (struct convolve_channel *chan, int16_t *in_samples, unsigned int in_sample_size, unsigned int hrtf_length)
 Binaural convolving of audio data for a channel. More...
 
struct convolve_channel_pairdo_convolve_pair (struct convolve_data *data, unsigned int pos_id, int16_t *in_samples, unsigned int in_sample_size, const char *channel_name)
 Binaural convolving of audio data for a channel pair (left and right channel). More...
 
void free_convolve_channel (struct convolve_channel *cchan)
 Frees all data needed for binaural processing by an audio channel. More...
 
void free_convolve_channel_pair (struct convolve_channel_pair *cchan_pair)
 Frees all data needed for binaural processing by a pair of audio channels (left and right). More...
 
void free_convolve_data (struct convolve_data *data)
 Frees all channels and data needed for binaural audio processing. More...
 
float * get_hrir (unsigned int chan_pos, unsigned int chan_side)
 Provides a head related impulse response for the given position in the virtual enviroment. More...
 
int init_convolve_channel (struct convolve_channel *channel, unsigned int hrtf_len, unsigned int chan_pos, unsigned int chan_side, unsigned int default_sample_size)
 Initializes all data needed for binaural audio processing. More...
 
int init_convolve_channel_pair (struct convolve_channel_pair *cchan_pair, unsigned int hrtf_len, unsigned int chan_pos, unsigned int default_sample_size)
 Initializes all data needed for binaural audio processing of a channel pair (left and right). More...
 
int init_convolve_data (struct convolve_data *data, unsigned int default_sample_size)
 Preinits a specific number of channels (CONVOLVE_CHANNEL_PREALLOC) at the beginning of a conference. More...
 
void random_binaural_pos_change (struct softmix_bridge_data *softmix_data)
 Randomly changes the virtual positions of conference participants. More...
 
void reset_channel_pair (struct convolve_channel_pair *channel_pair, unsigned int default_sample_size)
 Deletes left over signals on a channel that it can be reused. More...
 
int set_binaural_data_join (struct convolve_data *data, unsigned int default_sample_size)
 Joins a channel into a virtual enviroment build with the help of binaural synthesis. More...
 
void set_binaural_data_leave (struct convolve_data *data, unsigned int pos, unsigned int default_sample_size)
 Removes a channel from the binaural conference bridge. Marks the position in the virtual room as unused that it can be reused by the next channel which enters the conference. More...
 
void softmix_process_write_binaural_audio (struct softmix_channel *sc, unsigned int default_sample_size)
 Writes the binaural audio to a channel. More...
 

Detailed Description

Multi-party software based binaural mixing.

Author
Frank Haase fra.h.nosp@m.aase.nosp@m.@goog.nosp@m.lema.nosp@m.il.co.nosp@m.m
Dennis Guse denni.nosp@m.s.gu.nosp@m.se@al.nosp@m.umni.nosp@m..tu-b.nosp@m.erli.nosp@m.n.de

Definition in file bridge_softmix_binaural.c.

Macro Definition Documentation

◆ CONVOLUTION_SAMPLE_SIZE

#define CONVOLUTION_SAMPLE_SIZE   960

The default sample size in an binaural environment with a two-channel codec at 48kHz is 960 samples.

Definition at line 43 of file bridge_softmix_binaural.c.

◆ CONVOLVE_CHANNEL_PREALLOC

#define CONVOLVE_CHANNEL_PREALLOC   3

The number of prealloced channels when a bridge will be created.

Definition at line 37 of file bridge_softmix_binaural.c.

◆ CONVOLVE_MAX_BUFFER

#define CONVOLVE_MAX_BUFFER   4096

Max size of the convolve buffer.

Definition at line 39 of file bridge_softmix_binaural.c.

Function Documentation

◆ add_binaural_mixing()

void add_binaural_mixing ( struct ast_bridge bridge,
struct softmix_bridge_data softmix_data,
unsigned int  softmix_samples,
struct softmix_mixing_array mixing_array,
struct softmix_channel sc,
const char *  channel_name 
)

Processes audio data with the binaural synthesis and adds the result to the mixing array.

Parameters
bridgeThe conference bridge needed to check if binaural processing is active or not.
softmix_dataContains all data for the softmix bridge and for the binaural processing.
softmix_samplesThe sample size.
mixing_arrayThe array which holds all audio data for mixing.
scThe channel which contains the audio data to process.
channel_nameThe name of the channel

Definition at line 500 of file bridge_softmix_binaural.c.

503{
505
506 pair = NULL;
507 /* We only check binaural things if at least one binaural channel joined. */
508 if (!(bridge->softmix.binaural_active && softmix_data->convolve.binaural_active
509 && (softmix_samples % CONVOLUTION_SAMPLE_SIZE) == 0)) {
510 return;
511 }
512
513 if (!sc->is_announcement) {
514 pair = do_convolve_pair(&softmix_data->convolve, sc->binaural_pos,
515 mixing_array->buffers[mixing_array->used_entries], softmix_samples, channel_name);
516 }
517 sc->our_chan_pair = pair;
518 mixing_array->chan_pairs[mixing_array->used_entries] = pair;
519}
#define CONVOLUTION_SAMPLE_SIZE
struct convolve_channel_pair * do_convolve_pair(struct convolve_data *data, unsigned int pos_id, int16_t *in_samples, unsigned int in_sample_size, const char *channel_name)
Binaural convolving of audio data for a channel pair (left and right channel).
#define NULL
Definition: resample.c:96
unsigned int binaural_active
Definition: bridge.h:295
struct ast_bridge_softmix softmix
Definition: bridge.h:367
struct convolve_data convolve
struct convolve_channel_pair * our_chan_pair
struct convolve_channel_pair ** chan_pairs

References convolve_data::binaural_active, ast_bridge_softmix::binaural_active, softmix_channel::binaural_pos, softmix_mixing_array::buffers, softmix_mixing_array::chan_pairs, CONVOLUTION_SAMPLE_SIZE, softmix_bridge_data::convolve, do_convolve_pair(), softmix_channel::is_announcement, NULL, softmix_channel::our_chan_pair, ast_bridge::softmix, and softmix_mixing_array::used_entries.

Referenced by softmix_mixing_loop().

◆ binaural_mixing()

void binaural_mixing ( struct ast_bridge bridge,
struct softmix_bridge_data softmix_data,
struct softmix_mixing_array mixing_array,
int16_t bin_buf,
int16_t ann_buf 
)

Mixes all binaural audio data contained in the mixing array.

Parameters
bridgeThe conference bridge needed to check if binaural processing is active or not.
softmix_dataContains all data for the softmix bridge and for the binaural processing.
mixing_arrayThe array which holds all audio data for mixing.
bin_bufThe buffer that will contain the mixing results.
ann_bufThe buffer that will contain mixed announcements in an interleaved format.

Definition at line 521 of file bridge_softmix_binaural.c.

523{
524 unsigned int idx;
525 unsigned int x;
526
527 if (!(bridge->softmix.binaural_active && softmix_data->convolve.binaural_active)) {
528 return;
529 }
530 /* mix it like crazy (binaural channels) */
531 memset(bin_buf, 0, MAX_DATALEN);
532 memset(ann_buf, 0, MAX_DATALEN);
533
534 for (idx = 0; idx < mixing_array->used_entries; idx++) {
535 if (mixing_array->chan_pairs[idx] == NULL) {
536 for (x = 0; x < softmix_data->default_sample_size; x++) {
537 ast_slinear_saturated_add(bin_buf + (x * 2), mixing_array->buffers[idx] + x);
538 ast_slinear_saturated_add(bin_buf + (x * 2) + 1, mixing_array->buffers[idx] + x);
539 ann_buf[x * 2] = mixing_array->buffers[idx][x];
540 ann_buf[(x * 2) + 1] = mixing_array->buffers[idx][x];
541 }
542 } else {
543 for (x = 0; x < softmix_data->default_sample_size; x++) {
544 ast_slinear_saturated_add(bin_buf + (x * 2),
545 mixing_array->chan_pairs[idx]->chan_left.out_data + x);
546 ast_slinear_saturated_add(bin_buf + (x * 2) + 1,
547 mixing_array->chan_pairs[idx]->chan_right.out_data + x);
548 }
549 }
550 }
551}
#define MAX_DATALEN
struct convolve_channel chan_left
struct convolve_channel chan_right
static force_inline void ast_slinear_saturated_add(short *input, short *value)
Definition: utils.h:450

References ast_slinear_saturated_add(), convolve_data::binaural_active, ast_bridge_softmix::binaural_active, softmix_mixing_array::buffers, convolve_channel_pair::chan_left, softmix_mixing_array::chan_pairs, convolve_channel_pair::chan_right, softmix_bridge_data::convolve, softmix_bridge_data::default_sample_size, MAX_DATALEN, NULL, convolve_channel::out_data, ast_bridge::softmix, and softmix_mixing_array::used_entries.

Referenced by softmix_mixing_loop().

◆ check_binaural_position_change()

void check_binaural_position_change ( struct ast_bridge bridge,
struct softmix_bridge_data softmix_data 
)

Checks if a position change in the virtual enviroment is requested by one of the participants.

Parameters
bridgeThe conference bridge.
softmix_dataThe data used by the softmix bridge.

Definition at line 467 of file bridge_softmix_binaural.c.

469{
470 unsigned int pos_change;
471 struct ast_bridge_channel *bridge_channel;
472
473 /*
474 * We only check binaural things if binaural is activated by the config
475 * and at least one binaural channel joined.
476 */
477 if (!(bridge->softmix.binaural_active && softmix_data->convolve.binaural_active)) {
478 return;
479 }
480 /*
481 * Before we pull any audio, we must check if any channel requests a
482 * change of binaural positions.
483 */
484 pos_change = 0;
485 AST_LIST_TRAVERSE(&bridge->channels, bridge_channel, entry) {
486 if (!bridge_channel->binaural_pos_change) {
487 continue;
488 }
489 ast_bridge_channel_lock_bridge(bridge_channel);
490 bridge_channel->binaural_pos_change = 0;
491 ast_bridge_unlock(bridge_channel->bridge);
492 pos_change = 1;
493 }
494
495 if (pos_change) {
496 random_binaural_pos_change(softmix_data);
497 }
498}
#define ast_bridge_unlock(bridge)
Unlock the bridge.
Definition: bridge.h:481
void ast_bridge_channel_lock_bridge(struct ast_bridge_channel *bridge_channel)
Lock the bridge associated with the bridge channel.
void random_binaural_pos_change(struct softmix_bridge_data *softmix_data)
Randomly changes the virtual positions of conference participants.
#define AST_LIST_TRAVERSE(head, var, field)
Loops over (traverses) the entries in a list.
Definition: linkedlists.h:491
Structure that contains information regarding a channel in a bridge.
struct ast_bridge * bridge
Bridge this channel is participating in.
unsigned int binaural_pos_change
struct ast_bridge_channels_list channels
Definition: bridge.h:363
Definition: search.h:40

References ast_bridge_channel_lock_bridge(), ast_bridge_unlock, AST_LIST_TRAVERSE, convolve_data::binaural_active, ast_bridge_softmix::binaural_active, ast_bridge_channel::binaural_pos_change, ast_bridge_channel::bridge, ast_bridge::channels, softmix_bridge_data::convolve, random_binaural_pos_change(), and ast_bridge::softmix.

Referenced by softmix_mixing_loop().

◆ create_binaural_frame()

void create_binaural_frame ( struct ast_bridge_channel bridge_channel,
struct softmix_channel sc,
int16_t bin_buf,
int16_t ann_buf,
unsigned int  softmix_datalen,
unsigned int  softmix_samples,
int16_t buf 
)

Creates a frame out of binaural audio data.

Parameters
bridge_channelContains the information if binaural processing is active or not. If active binaural audio data will be copied, if not mono data will be provided in an interleaved format.
scThe softmix channel holding all informations for the process.
bin_bufThe buffer that contains all mixing results.
ann_bufThe buffer that contains mixed announcements in an interleaved format.
softmix_datalenThe size of the audio data.
softmix_samplesThe number of audio samples.
bufThe buffer that contains all mono mixing results, used if binaural processing is inactive.

Definition at line 553 of file bridge_softmix_binaural.c.

556{
557 unsigned int i;
558
559 sc->write_frame.datalen = softmix_datalen * 2;
560 sc->write_frame.samples = softmix_samples * 2;
561 if (!bridge_channel->binaural_suspended) {
562 sc->binaural_suspended = 0;
563 if (sc->is_announcement) {
564 memcpy(sc->final_buf, ann_buf, softmix_datalen * 2);
565 } else {
566 memcpy(sc->final_buf, bin_buf, softmix_datalen * 2);
567 }
568 return;
569 }
570
571 /*
572 * Mark that binaural output is suspended, since we use two channel audio
573 * we copy the same signals into both channels.
574 */
575 sc->binaural_suspended = 1;
576 for (i = 0; i < softmix_samples; i++) {
577 sc->final_buf[i * 2] = buf[i];
578 sc->final_buf[(i * 2) + 1] = buf[i];
579 }
580}
char buf[BUFSIZE]
Definition: eagi_proxy.c:66
unsigned int binaural_suspended
unsigned int binaural_suspended
short final_buf[MAX_DATALEN]
struct ast_frame write_frame

References softmix_channel::binaural_suspended, ast_bridge_channel::binaural_suspended, buf, ast_frame::datalen, softmix_channel::final_buf, softmix_channel::is_announcement, ast_frame::samples, and softmix_channel::write_frame.

Referenced by softmix_mixing_loop().

◆ do_convolve()

int do_convolve ( struct convolve_channel chan,
int16_t in_samples,
unsigned int  in_sample_size,
unsigned int  hrtf_length 
)

Binaural convolving of audio data for a channel.

Parameters
chanThe channel that will contain the binaural audio data as result.
in_samplesThe audio data which will be convolved.
in_sample_sizeThe size of the audio data.
hrtf_lengthThe length of the head related transfer function used to convolve the audio.
Return values
0success
-1failure

Definition at line 86 of file bridge_softmix_binaural.c.

88{
89#ifdef BINAURAL_RENDERING
90 unsigned int i;
91
92 if (in_sample_size != CONVOLUTION_SAMPLE_SIZE) {
93 return -1;
94 }
95
96 /* FFT setting real part */
97 for (i = 0; i < CONVOLUTION_SAMPLE_SIZE; i++) {
98 chan->fftw_in[i] = in_samples[i] * (FLT_MAX / SHRT_MAX);
99 }
100
101 for (i = CONVOLUTION_SAMPLE_SIZE; i < hrtf_length; i++) {
102 chan->fftw_in[i] = 0;
103 }
104 fftw_execute(chan->fftw_plan);
105
106 /* Imaginary multiplication (frequency space). */
107 /* First FFTW result has never an imaginary part. */
108 chan->fftw_in[0] = chan->fftw_out[0] * chan->hrtf[0];
109 for (i = 1; i < (hrtf_length / 2); i++) {
110 /* Real part */
111 chan->fftw_in[i] = (chan->fftw_out[i] * chan->hrtf[i]) -
112 (chan->fftw_out[hrtf_length - i] * chan->hrtf[hrtf_length - i]);
113 /* Imaginary part */
114 chan->fftw_in[hrtf_length - i] = (chan->fftw_out[i] * chan->hrtf[hrtf_length - i]) +
115 (chan->fftw_out[hrtf_length - i] * chan->hrtf[i]);
116 }
117
118 /* The last (if even) FFTW result has never an imaginary part. */
119 if (hrtf_length % 2 == 0) {
120 chan->fftw_in[hrtf_length / 2] = chan->fftw_out[hrtf_length / 2] *
121 chan->hrtf[hrtf_length / 2];
122 }
123
124 /* iFFT */
125 fftw_execute(chan->fftw_plan_inverse);
126 /* Remove signal increase due to iFFT. */
127 for (i = 0; i < hrtf_length; i++) {
128 chan->fftw_out[i] = chan->fftw_out[i] / (hrtf_length / 2);
129 }
130
131 /* Save the block for overlap add in the next iteration. */
132 for (i = 0; i < in_sample_size; i++) {
133 chan->overlap_add[i] += chan->fftw_out[i];
134 }
135
136 /* Copy real part to the output, ignore the complex part. */
137 for (i = 0; i < in_sample_size; i++) {
138 chan->out_data[i] = chan->overlap_add[i] * (SHRT_MAX / FLT_MAX);
139 chan->overlap_add[i] = chan->fftw_out[i + in_sample_size];
140 }
141#endif
142 return 0;
143}

References CONVOLUTION_SAMPLE_SIZE, convolve_channel::fftw_in, convolve_channel::fftw_out, convolve_channel::hrtf, convolve_channel::out_data, and convolve_channel::overlap_add.

Referenced by do_convolve_pair().

◆ do_convolve_pair()

struct convolve_channel_pair * do_convolve_pair ( struct convolve_data data,
unsigned int  pos_id,
int16_t in_samples,
unsigned int  in_sample_size,
const char *  channel_name 
)

Binaural convolving of audio data for a channel pair (left and right channel).

Parameters
dataContains the left and right audio channel.
pos_idThe position the channel has in the virtual enviroment.
in_samplesThe audio data which will be convolved for both channels.
in_sample_sizeThe size of the audio data.
channel_nameThe name of the channel
Return values
Thechannel pair with convolved audio on success.
NULLfailure

Definition at line 145 of file bridge_softmix_binaural.c.

148{
149 struct convolve_channel_pair *chan_pair;
150
151 /* If a position has no active member we will not convolve. */
152 if (data->pos_ids[pos_id] != 1) {
153 ast_log(LOG_ERROR, "Channel %s: Channel pair has no active member! (pos id = %d)\n",
154 channel_name, pos_id);
155 return NULL;
156 }
157
158 chan_pair = data->cchan_pair[pos_id];
159 if (do_convolve(&chan_pair->chan_left, in_samples, in_sample_size, data->hrtf_length)) {
160 ast_log(LOG_ERROR, "Channel %s: Binaural processing failed.", channel_name);
161 return NULL;
162 }
163
164 if (do_convolve(&chan_pair->chan_right, in_samples, in_sample_size, data->hrtf_length)) {
165 ast_log(LOG_ERROR, "Channel %s: Binaural processing failed.", channel_name);
166 return NULL;
167 }
168
169 return chan_pair;
170}
#define ast_log
Definition: astobj2.c:42
int do_convolve(struct convolve_channel *chan, int16_t *in_samples, unsigned int in_sample_size, unsigned int hrtf_length)
Binaural convolving of audio data for a channel.
#define LOG_ERROR
struct convolve_channel_pair ** cchan_pair

References ast_log, convolve_data::cchan_pair, convolve_channel_pair::chan_left, convolve_channel_pair::chan_right, do_convolve(), convolve_data::hrtf_length, LOG_ERROR, NULL, and convolve_data::pos_ids.

Referenced by add_binaural_mixing().

◆ free_convolve_channel()

void free_convolve_channel ( struct convolve_channel cchan)

Frees all data needed for binaural processing by an audio channel.

Parameters
cchanThe channel to clean up.

Definition at line 341 of file bridge_softmix_binaural.c.

342{
343#ifdef BINAURAL_RENDERING
344 fftw_free(cchan->fftw_out);
345 fftw_free(cchan->fftw_in);
346 fftw_free(cchan->hrtf);
347 ast_free(cchan->overlap_add);
348 ast_free(cchan->out_data);
349 fftw_destroy_plan(cchan->fftw_plan);
350 fftw_destroy_plan(cchan->fftw_plan_inverse);
351#endif
352}
#define ast_free(a)
Definition: astmm.h:180

References ast_free, convolve_channel::fftw_in, convolve_channel::fftw_out, convolve_channel::hrtf, convolve_channel::out_data, and convolve_channel::overlap_add.

Referenced by free_convolve_channel_pair(), and init_convolve_channel_pair().

◆ free_convolve_channel_pair()

void free_convolve_channel_pair ( struct convolve_channel_pair cchan_pair)

Frees all data needed for binaural processing by a pair of audio channels (left and right).

Parameters
cchan_pairThe channel pair to clean up.

Definition at line 354 of file bridge_softmix_binaural.c.

355{
356 free_convolve_channel(&cchan_pair->chan_left);
357 free_convolve_channel(&cchan_pair->chan_right);
358}
void free_convolve_channel(struct convolve_channel *cchan)
Frees all data needed for binaural processing by an audio channel.

References convolve_channel_pair::chan_left, convolve_channel_pair::chan_right, and free_convolve_channel().

Referenced by free_convolve_data(), and init_convolve_data().

◆ free_convolve_data()

void free_convolve_data ( struct convolve_data data)

Frees all channels and data needed for binaural audio processing.

Parameters
dataContains all channels and data for the cleanup process.

Definition at line 360 of file bridge_softmix_binaural.c.

361{
362 unsigned int i;
363 ast_free(data->pos_ids);
364 for (i = 0; i < data->chan_size; i++) {
366 ast_free(data->cchan_pair[i]);
367 }
368 ast_free(data->cchan_pair);
369}
void free_convolve_channel_pair(struct convolve_channel_pair *cchan_pair)
Frees all data needed for binaural processing by a pair of audio channels (left and right).

References ast_free, convolve_data::cchan_pair, convolve_data::chan_size, free_convolve_channel_pair(), and convolve_data::pos_ids.

Referenced by softmix_bridge_destroy().

◆ get_hrir()

float * get_hrir ( unsigned int  chan_pos,
unsigned int  chan_side 
)

Provides a head related impulse response for the given position in the virtual enviroment.

Parameters
chan_posThe position of the channel in the virtual enviroment.
chan_side0 for the left audio channel, 1 for the right.
Return values
Thehrir for the given position in the virtual room for either the left or right channels.
NULLon failure.

Definition at line 172 of file bridge_softmix_binaural.c.

173{
174#ifdef BINAURAL_RENDERING
175 if (chan_side == HRIRS_CHANNEL_LEFT) {
176 return hrirs_left[ast_binaural_positions[chan_pos]];
177 } else if (chan_side == HRIRS_CHANNEL_RIGHT) {
178 return hrirs_right[ast_binaural_positions[chan_pos]];
179 }
180#else
181 ast_log(LOG_ERROR, "Requesting data for the binaural conference feature without "
182 "it beeing active.\n");
183#endif
184
185 return NULL;
186}
float hrirs_right[HRIRS_IMPULSE_SIZE][HRIRS_IMPULSE_LEN]
Definition: hrirs.h:25390
float hrirs_left[HRIRS_IMPULSE_SIZE][HRIRS_IMPULSE_LEN]
Definition: hrirs.h:49
static unsigned int ast_binaural_positions[POSITION_SIZE]
#define HRIRS_CHANNEL_RIGHT
#define HRIRS_CHANNEL_LEFT

References ast_binaural_positions, ast_log, HRIRS_CHANNEL_LEFT, HRIRS_CHANNEL_RIGHT, hrirs_left, hrirs_right, LOG_ERROR, and NULL.

Referenced by init_convolve_channel().

◆ init_convolve_channel()

int init_convolve_channel ( struct convolve_channel channel,
unsigned int  hrtf_len,
unsigned int  chan_pos,
unsigned int  chan_side,
unsigned int  default_sample_size 
)

Initializes all data needed for binaural audio processing.

Parameters
channelThe channel used for binaural audio processing.
hrtf_lenThe length of the head related impulse response used for binaural processing.
chan_posThe position of the channel in the virtual enviroment.
chan_side0 for the left audio channel, 1 for the right.
default_sample_sizeThe default size of audio samples.
Return values
0on success
-1on failure

Definition at line 188 of file bridge_softmix_binaural.c.

190{
191#ifdef BINAURAL_RENDERING
192 unsigned int j;
193 float *hrir;
194
195 /* Prepare FFTW. */
196 channel->fftw_in = (double *) fftw_malloc(sizeof(double) * (hrtf_len + 1));
197 if (channel->fftw_in == NULL) {
198 return -1;
199 }
200
201 channel->fftw_out = (double *) fftw_malloc(sizeof(double) * (hrtf_len + 1));
202 if (channel->fftw_out == NULL) {
203 fftw_free(channel->fftw_in);
204 return -1;
205 }
206
207 memset(channel->fftw_in, 0, sizeof(double) * (hrtf_len + 1));
208 memset(channel->fftw_out, 0, sizeof(double) * (hrtf_len + 1));
209
210 channel->fftw_plan = fftw_plan_r2r_1d(hrtf_len, channel->fftw_in, channel->fftw_out,
211 FFTW_R2HC, FFTW_PATIENT);
212 channel->fftw_plan_inverse = fftw_plan_r2r_1d(hrtf_len, channel->fftw_in, channel->fftw_out,
213 FFTW_HC2R, FFTW_PATIENT);
214 channel->out_data = ast_calloc(CONVOLVE_MAX_BUFFER, sizeof(int16_t));
215 if (channel->out_data == NULL) {
216 fftw_free(channel->fftw_in);
217 fftw_free(channel->fftw_out);
218 return -1;
219 }
220
221 /* Reuse positions if all positions are already used. */
222 chan_pos = chan_pos % HRIRS_IMPULSE_SIZE;
223
224 /* Get HRTF for the channels spatial position. */
225 hrir = get_hrir(chan_pos, chan_side);
226 if (hrir == NULL) {
227 fftw_free(channel->fftw_in);
228 fftw_free(channel->fftw_out);
229 ast_free(channel->out_data);
230 return -1;
231 }
232
233 for (j = 0; j < HRIRS_IMPULSE_LEN; j++) {
234 channel->fftw_in[j] = hrir[j];
235 }
236
237 for (j = HRIRS_IMPULSE_LEN; j < hrtf_len; j++) {
238 channel->fftw_in[j] = 0;
239 }
240
241 fftw_execute(channel->fftw_plan);
242 channel->hrtf = (double *) fftw_malloc(sizeof(double) * hrtf_len);
243 if (channel->hrtf == NULL) {
244 fftw_free(channel->fftw_in);
245 fftw_free(channel->fftw_out);
246 ast_free(channel->out_data);
247 return -1;
248 }
249
250 for (j = 0; j < hrtf_len; j++) {
251 channel->hrtf[j] = channel->fftw_out[j];
252 }
253 channel->overlap_add = ast_calloc(default_sample_size, sizeof(float));
254
255 return 0;
256#endif
257 return -1;
258}
#define ast_calloc(num, len)
A wrapper for calloc()
Definition: astmm.h:202
float * get_hrir(unsigned int chan_pos, unsigned int chan_side)
Provides a head related impulse response for the given position in the virtual enviroment.
#define CONVOLVE_MAX_BUFFER
short int16_t
Definition: db.h:59
#define HRIRS_IMPULSE_SIZE
Definition: hrirs.h:46
#define HRIRS_IMPULSE_LEN
Definition: hrirs.h:45

References ast_calloc, ast_free, CONVOLVE_MAX_BUFFER, convolve_channel::fftw_in, convolve_channel::fftw_out, get_hrir(), HRIRS_IMPULSE_LEN, HRIRS_IMPULSE_SIZE, convolve_channel::hrtf, NULL, convolve_channel::out_data, and convolve_channel::overlap_add.

Referenced by init_convolve_channel_pair().

◆ init_convolve_channel_pair()

int init_convolve_channel_pair ( struct convolve_channel_pair cchan_pair,
unsigned int  hrtf_len,
unsigned int  chan_pos,
unsigned int  default_sample_size 
)

Initializes all data needed for binaural audio processing of a channel pair (left and right).

Parameters
cchan_pairThe channel pair used for binaural audio processing.
hrtf_lenThe length of the head related impulse response used for binaural processing.
chan_posThe position of the channel in the virtual enviroment.
default_sample_sizeThe default size of audio samples.
Return values
0on success
-1on failure

Definition at line 260 of file bridge_softmix_binaural.c.

262{
263#ifdef BINAURAL_RENDERING
264 unsigned int hrirs_pos = chan_pos * 2;
265 int success = 0;
266
267 ast_debug(3, "Binaural pos for the new channel pair will be L: %d R: %d (pos id = %d)\n",
268 hrirs_pos, hrirs_pos + 1, chan_pos);
269 success = init_convolve_channel(&cchan_pair->chan_left, hrtf_len, chan_pos, HRIRS_CHANNEL_LEFT,
270 default_sample_size);
271 if (success == -1) {
272 return success;
273 }
274
275 success = init_convolve_channel(&cchan_pair->chan_right, hrtf_len, chan_pos,
276 HRIRS_CHANNEL_RIGHT, default_sample_size);
277 if (success == -1) {
278 free_convolve_channel(&cchan_pair->chan_left);
279 }
280
281 return success;
282#else
283 ast_log(LOG_ERROR, "Requesting data for the binaural conference feature "
284 "without it beeing active.\n");
285
286 return -1;
287#endif
288}
int init_convolve_channel(struct convolve_channel *channel, unsigned int hrtf_len, unsigned int chan_pos, unsigned int chan_side, unsigned int default_sample_size)
Initializes all data needed for binaural audio processing.
#define ast_debug(level,...)
Log a DEBUG message.

References ast_debug, ast_log, convolve_channel_pair::chan_left, convolve_channel_pair::chan_right, free_convolve_channel(), HRIRS_CHANNEL_LEFT, HRIRS_CHANNEL_RIGHT, init_convolve_channel(), and LOG_ERROR.

Referenced by init_convolve_data(), and set_binaural_data_join().

◆ init_convolve_data()

int init_convolve_data ( struct convolve_data data,
unsigned int  default_sample_size 
)

Preinits a specific number of channels (CONVOLVE_CHANNEL_PREALLOC) at the beginning of a conference.

Parameters
dataContains all channels and data needed for binaural processing (e.g. head related transfer functions).
default_sample_sizeThe default size of audio samples.
Return values
0on success
-1on failure

Definition at line 290 of file bridge_softmix_binaural.c.

291{
292 unsigned int i;
293 unsigned int j;
294 int success;
295 success = 0;
296
297 data->pos_ids = ast_calloc(sizeof(int), sizeof(int) * CONVOLVE_CHANNEL_PREALLOC);
298 if (data->pos_ids == NULL) {
299 return -1;
300 }
302 data->number_channels = 0;
303 data->cchan_pair = ast_malloc(sizeof(struct convolve_channel_pair *) *
305 if (data->cchan_pair == NULL) {
306 ast_free(data->pos_ids);
307 return -1;
308 }
309
310 for (i = 0; i < CONVOLVE_CHANNEL_PREALLOC; i++) {
311 data->cchan_pair[i] = ast_malloc(sizeof(struct convolve_channel_pair));
312 if (data->cchan_pair[i] == NULL) {
313 ast_free(data->pos_ids);
314 for (j = 0; j < i; j++) {
315 ast_free(data->cchan_pair[j]);
316 }
317 ast_free(data->cchan_pair);
318 return -1;
319 }
320 }
321
322 data->hrtf_length = (default_sample_size * 2) - 1;
323 for (i = 0; i < CONVOLVE_CHANNEL_PREALLOC; i++) {
324 success = init_convolve_channel_pair(data->cchan_pair[i], data->hrtf_length, i,
325 default_sample_size);
326 if (success == -1) {
327 ast_free(data->pos_ids);
328 for (j = 0; j < i; j++) {
330 }
331 for (j = 0; j < CONVOLVE_CHANNEL_PREALLOC; j++) {
332 ast_free(data->cchan_pair[j]);
333 }
334 return -1;
335 }
336 }
337
338 return success;
339}
#define ast_malloc(len)
A wrapper for malloc()
Definition: astmm.h:191
#define CONVOLVE_CHANNEL_PREALLOC
int init_convolve_channel_pair(struct convolve_channel_pair *cchan_pair, unsigned int hrtf_len, unsigned int chan_pos, unsigned int default_sample_size)
Initializes all data needed for binaural audio processing of a channel pair (left and right).

References ast_calloc, ast_free, ast_malloc, convolve_data::cchan_pair, convolve_data::chan_size, CONVOLVE_CHANNEL_PREALLOC, free_convolve_channel_pair(), convolve_data::hrtf_length, init_convolve_channel_pair(), NULL, convolve_data::number_channels, and convolve_data::pos_ids.

Referenced by softmix_mixing_thread().

◆ random_binaural_pos_change()

void random_binaural_pos_change ( struct softmix_bridge_data softmix_data)

Randomly changes the virtual positions of conference participants.

Parameters
softmix_dataThe structure containing all position informations.

Definition at line 61 of file bridge_softmix_binaural.c.

62{
63 /*
64 * We perform a shuffle of all channels, even the ones that aren't used at the
65 * moment of shuffling now. This has the efect that new members will be placed
66 * randomly too.
67 */
68 unsigned int i;
69 unsigned int j;
71
72 if (softmix_data->convolve.chan_size < 2) {
73 return;
74 }
75
76 srand(time(NULL));
77 for (i = softmix_data->convolve.chan_size - 1; i > 0; i--) {
78 j = rand() % (i + 1);
79 tmp = softmix_data->convolve.cchan_pair[i];
81 softmix_data->convolve.cchan_pair[i] = softmix_data->convolve.cchan_pair[j];
82 softmix_data->convolve.cchan_pair[j] = tmp;
83 }
84}
void reset_channel_pair(struct convolve_channel_pair *channel_pair, unsigned int default_sample_size)
Deletes left over signals on a channel that it can be reused.
static int tmp()
Definition: bt_open.c:389

References convolve_data::cchan_pair, convolve_data::chan_size, softmix_bridge_data::convolve, softmix_bridge_data::default_sample_size, NULL, reset_channel_pair(), and tmp().

Referenced by check_binaural_position_change().

◆ reset_channel_pair()

void reset_channel_pair ( struct convolve_channel_pair channel_pair,
unsigned int  default_sample_size 
)

Deletes left over signals on a channel that it can be reused.

Parameters
channel_pairThe channel pair which contains the left and right audio channel.
default_sample_sizeThe sample size which the channel pair uses.

Definition at line 54 of file bridge_softmix_binaural.c.

56{
57 memset(channel_pair->chan_left.overlap_add, 0, sizeof(float) * default_sample_size);
58 memset(channel_pair->chan_right.overlap_add, 0, sizeof(float) * default_sample_size);
59}

References convolve_channel_pair::chan_left, convolve_channel_pair::chan_right, and convolve_channel::overlap_add.

Referenced by random_binaural_pos_change(), and set_binaural_data_leave().

◆ set_binaural_data_join()

int set_binaural_data_join ( struct convolve_data data,
unsigned int  default_sample_size 
)

Joins a channel into a virtual enviroment build with the help of binaural synthesis.

Parameters
dataContains all channels and data needed for binaural processing (e.g. head related transfer functions).
default_sample_sizeThe default size of audio samples.
Return values
Theposition of the channel in the virtual enviroment.
-1on failure

Definition at line 371 of file bridge_softmix_binaural.c.

372{
373 struct convolve_channel_pair **cchan_pair_tmp;
374 unsigned int i;
375 int *pos_ids_tmp;
376
377 /* Raise the number of input channels. */
378 data->number_channels++;
379 /* We realloc another channel pair if we are out of prealloced ones. */
380 /* We have prealloced one at the beginning of a conference and if a member leaves. */
381 if (data->chan_size < data->number_channels) {
382 data->chan_size += 1;
383
384 pos_ids_tmp = ast_realloc(data->pos_ids, data->chan_size * sizeof(int));
385 if (pos_ids_tmp) {
386 data->pos_ids = pos_ids_tmp;
387 } else {
388 goto binaural_join_fails;
389 }
390
391 data->pos_ids[data->chan_size - 1] = 0;
392 cchan_pair_tmp = ast_realloc(data->cchan_pair,
393 data->chan_size * sizeof(struct convolve_channel_pair *));
394 if (cchan_pair_tmp) {
395 data->cchan_pair = cchan_pair_tmp;
396 } else {
397 goto binaural_join_fails;
398 }
399
400 data->cchan_pair[data->chan_size - 1] = ast_malloc(sizeof(struct convolve_channel_pair));
401 if (data->cchan_pair[data->chan_size - 1] == NULL) {
402 goto binaural_join_fails;
403 }
404
406 data->chan_size - 1, default_sample_size);
407 if (i == -1) {
408 goto binaural_join_fails;
409 }
410 }
411
412 for (i = 0; i < data->chan_size; i++) {
413 if (data->pos_ids[i] == 0) {
414 data->pos_ids[i] = 1;
415 break;
416 }
417 }
418
419 return i;
420
421binaural_join_fails:
422 data->number_channels--;
423 data->chan_size -= 1;
424
425 return -1;
426}
#define ast_realloc(p, len)
A wrapper for realloc()
Definition: astmm.h:226

References ast_malloc, ast_realloc, convolve_data::cchan_pair, convolve_data::chan_size, convolve_data::hrtf_length, init_convolve_channel_pair(), NULL, convolve_data::number_channels, and convolve_data::pos_ids.

Referenced by softmix_bridge_join().

◆ set_binaural_data_leave()

void set_binaural_data_leave ( struct convolve_data data,
unsigned int  pos,
unsigned int  default_sample_size 
)

Removes a channel from the binaural conference bridge. Marks the position in the virtual room as unused that it can be reused by the next channel which enters the conference.

Parameters
dataContains all channels and data needed for binaural processing (e.g. head related transfer functions).
posThe position of the channel in the virtual enviroment.
default_sample_sizeThe default size of audio samples.

Definition at line 428 of file bridge_softmix_binaural.c.

430{
431 if (pos >= data->chan_size || data->pos_ids[pos] == 0) {
432 return;
433 }
434
435 reset_channel_pair(data->cchan_pair[pos], default_sample_size);
436 data->number_channels--;
437 data->pos_ids[pos] = 0;
438}

References convolve_data::cchan_pair, convolve_data::chan_size, convolve_data::number_channels, convolve_data::pos_ids, and reset_channel_pair().

Referenced by softmix_bridge_leave().

◆ softmix_process_write_binaural_audio()

void softmix_process_write_binaural_audio ( struct softmix_channel sc,
unsigned int  default_sample_size 
)

Writes the binaural audio to a channel.

Parameters
scThe softmix channel.
default_sample_sizeThe default size of audio samples.

Definition at line 440 of file bridge_softmix_binaural.c.

442{
443 unsigned int i;
444
445 if (sc->write_frame.samples % default_sample_size != 0) {
446 return;
447 }
448
449 /* If binaural is suspended, the source audio (mono) will be removed. */
450 if (sc->binaural_suspended) {
451 for (i = 0; i < default_sample_size; i++) {
453 ast_slinear_saturated_subtract(&sc->final_buf[(i * 2) + 1], &sc->our_buf[i]);
454 }
455 return;
456 }
457
458 /* If binaural is NOT suspended, the source audio (binaural) will be removed. */
459 for (i = 0; i < default_sample_size; i++) {
464 }
465}
short our_buf[MAX_DATALEN]
static force_inline void ast_slinear_saturated_subtract(short *input, short *value)
Definition: utils.h:463

References ast_slinear_saturated_subtract(), softmix_channel::binaural_suspended, convolve_channel_pair::chan_left, convolve_channel_pair::chan_right, softmix_channel::final_buf, softmix_channel::our_buf, softmix_channel::our_chan_pair, convolve_channel::out_data, ast_frame::samples, and softmix_channel::write_frame.

Referenced by softmix_process_write_audio().