Skip to content

Commit

Permalink
Audiobridge: added ability play announcement only to specific partici…
Browse files Browse the repository at this point in the history
…pant

or exclude some participant from announcement
  • Loading branch information
RSATom committed Dec 7, 2023
1 parent 86e1f25 commit 2a50e8a
Showing 1 changed file with 91 additions and 4 deletions.
95 changes: 91 additions & 4 deletions src/plugins/janus_audiobridge.c
Original file line number Diff line number Diff line change
Expand Up @@ -1366,7 +1366,9 @@ static struct janus_json_parameter play_file_parameters[] = {
{"filename", JSON_STRING, JANUS_JSON_PARAM_REQUIRED},
{"file_id", JSON_STRING, 0},
{"group", JSON_STRING, 0},
{"loop", JANUS_JSON_BOOL, 0}
{"loop", JANUS_JSON_BOOL, 0},
{"to", JSON_STRING, 0},
{"exclude", JSON_STRING, 0}
};
static struct janus_json_parameter checkstop_file_parameters[] = {
{"file_id", JSON_STRING, JANUS_JSON_PARAM_REQUIRED}
Expand Down Expand Up @@ -1498,6 +1500,8 @@ typedef struct janus_audiobridge_file {
char *oggbuf;
gboolean started, loop;
gint state, headers;
char *to;
char *exclude;
} janus_audiobridge_file;
/* Helper method to open an Opus file, and make sure it's valid */
static int janus_audiobridge_file_init(janus_audiobridge_file *ctx) {
Expand Down Expand Up @@ -1633,6 +1637,8 @@ static void janus_audiobridge_file_free(janus_audiobridge_file *ctx) {
if(ctx->headers > 0)
ogg_stream_clear(&ctx->stream);
ogg_sync_clear(&ctx->sync);
g_free(ctx->to);
g_free(ctx->exclude);
g_free(ctx);
}
#endif
Expand Down Expand Up @@ -5169,6 +5175,13 @@ static json_t *janus_audiobridge_process_synchronous_request(janus_audiobridge_s
g_snprintf(error_cause, 512, "Error creating Opus decoder");
goto prepare_response;
}
const char *to = json_string_value(json_object_get(root, "to"));
if(to)
p->annc->to = g_strdup(to);
const char *exclude = json_string_value(json_object_get(root, "exclude"));
if(exclude)
p->annc->exclude = g_strdup(exclude);

/* We're done, add the announcement to the room */
g_hash_table_insert(audiobridge->anncs, g_strdup(p->user_id_str), p);
janus_mutex_unlock(&audiobridge->mutex);
Expand Down Expand Up @@ -8297,7 +8310,7 @@ static void *janus_audiobridge_mixer_thread(void *data) {
gateway->notify_event(&janus_audiobridge_plugin, NULL, info);
}
}
if(groups_num == 0) {
if(groups_num == 0 && !p->annc->to) {
/* Add to the main mix */
for(i=0; i<samples; i++) {
if(p->volume_gain == 100) {
Expand All @@ -8306,7 +8319,7 @@ static void *janus_audiobridge_mixer_thread(void *data) {
buffer[i] += (resampled[i]*p->volume_gain)/100;
}
}
} else {
} else if(groups_num != 0) {
/* Add to the group submix */
index = p->group-1;
for(i=0; i<samples; i++) {
Expand All @@ -8317,9 +8330,24 @@ static void *janus_audiobridge_mixer_thread(void *data) {
}
}
}
if(p->annc->to || (p->annc->exclude && groups_num == 0)) {
janus_audiobridge_rtp_relay_packet *pkt = g_malloc(sizeof(janus_audiobridge_rtp_relay_packet));
pkt->data = g_malloc(sizeof(resampled));
memcpy(pkt->data, resampled, sizeof(resampled));
pkt->ssrc = 0;
pkt->timestamp = 0;
pkt->seq_number = 0;
pkt->silence = FALSE;
pkt->length = read;

janus_mutex_lock(&p->qmutex);
/* Insert packets sorting by sequence number */
p->inbuf = g_list_prepend(p->inbuf, pkt);
janus_mutex_unlock(&p->qmutex);
}

ps = ps->next;
}
g_list_free_full(anncs_list, (GDestroyNotify)janus_audiobridge_participant_unref);
}
#endif
/* If groups are in use, put them together in the main mix */
Expand Down Expand Up @@ -8403,6 +8431,47 @@ static void *janus_audiobridge_mixer_thread(void *data) {
}
}
}

#if HAVE_LIBOGG
for(GList *annc = anncs_list; annc; annc = annc->next) {
janus_audiobridge_participant *anncp = (janus_audiobridge_participant *)annc->data;

if(anncp->annc == NULL || g_atomic_int_get(&anncp->destroyed))
continue;

if(!anncp->annc->to && (!anncp->annc->exclude || groups_num != 0))
continue; /* already mixed */

GList *first = g_list_first(anncp->inbuf);
janus_audiobridge_rtp_relay_packet *pkt = (janus_audiobridge_rtp_relay_packet *)(first ? first->data : NULL);
curBuffer = (opus_int16 *)((pkt && pkt->length && !pkt->silence) ? pkt->data : NULL);
if(!curBuffer)
continue;

const char *to = anncp->annc->to;
const char *exclude = anncp->annc->exclude;
if(to) {
if(0 == g_strcmp0(p->display, to)) {
for(i = 0; i < samples; ++i) {
if(anncp->volume_gain == 100)
sumBuffer[i] += curBuffer[i];
else
sumBuffer[i] += (curBuffer[i]*anncp->volume_gain)/100;
}
}
} else {
if(0 == g_strcmp0(p->display, exclude)) {
for(i = 0; i < samples; ++i) {
if(anncp->volume_gain == 100)
sumBuffer[i] -= curBuffer[i];
else
sumBuffer[i] -= (curBuffer[i]*anncp->volume_gain)/100;
}
}
}
}
#endif

for(i=0; i<samples; i++)
/* FIXME Smoothen/Normalize instead of truncating? */
outBuffer[i] = sumBuffer[i];
Expand Down Expand Up @@ -8439,6 +8508,24 @@ static void *janus_audiobridge_mixer_thread(void *data) {
janus_refcount_decrease(&p->ref);
ps = ps->next;
}

#if HAVE_LIBOGG
for(GList *annc = anncs_list; annc; annc = annc->next) {
janus_audiobridge_participant *anncp = (janus_audiobridge_participant *)annc->data;

GList *first = g_list_first(anncp->inbuf);
if(first) {
janus_audiobridge_rtp_relay_packet *pkt = (janus_audiobridge_rtp_relay_packet *)first->data;
g_free(pkt->data);
g_free(pkt);

anncp->inbuf = g_list_delete_link(anncp->inbuf, first);
}
}
if(anncs_list != NULL)
g_list_free_full(anncs_list, (GDestroyNotify)janus_audiobridge_participant_unref);
#endif

g_list_free(participants_list);
/* Forward the mixed packet as RTP to any RTP forwarder that may be listening */
janus_mutex_lock(&audiobridge->rtp_mutex);
Expand Down

0 comments on commit 2a50e8a

Please sign in to comment.