static int read_file(struct ausrc_st *st) { struct mbuf *mb; int err; for (;;) { mb = mbuf_alloc(4096); if (!mb) return ENOMEM; mb->end = mb->size; err = aufile_read(st->aufile, mb->buf, &mb->end); if (err) break; if (mb->end == 0) { info("aufile: end of file\n"); break; } aubuf_append(st->aubuf, mb); mb = mem_deref(mb); } info("aufile: loaded %zu bytes\n", aubuf_cur_size(st->aubuf)); mem_deref(mb); return err; }
static void *tx_thread(void *arg) { struct audio *a = arg; struct autx *tx = &a->tx; unsigned i; /* Enable Real-time mode for this thread, if available */ if (a->cfg.txmode == AUDIO_MODE_THREAD_REALTIME) (void)realtime_enable(true, 1); while (a->tx.u.thr.run) { for (i=0; i<16; i++) { if (aubuf_cur_size(tx->aubuf) < tx->psize) break; poll_aubuf_tx(a); } sys_msleep(5); } return NULL; }
/** * Read samples from Audio Source * * @note This function has REAL-TIME properties * * @note This function may be called from any thread * * @param buf Buffer with audio samples * @param sz Number of bytes in buffer * @param arg Handler argument */ static void ausrc_read_handler(const int16_t *sampv, size_t sampc, void *arg) { struct audio *a = arg; struct autx *tx = &a->tx; if (tx->muted) memset((void *)sampv, 0, sampc*2); (void)aubuf_write_samp(tx->aubuf, sampv, sampc); if (a->cfg.txmode == AUDIO_MODE_POLL) { unsigned i; for (i=0; i<16; i++) { if (aubuf_cur_size(tx->aubuf) < tx->psize) break; poll_aubuf_tx(a); } } /* Exact timing: send Telephony-Events from here */ check_telev(a, tx); }
/* Expected format: 16-bit signed PCM */ static void packet_handler(struct ausrc_st *st, GstBuffer *buffer) { int err; if (!st->run) return; /* NOTE: When streaming from files, the buffer will be filled up * pretty quickly.. */ err = aubuf_write(st->aubuf, GST_BUFFER_DATA(buffer), GST_BUFFER_SIZE(buffer)); if (err) { DEBUG_WARNING("aubuf_write: %m\n", err); } /* Empty buffer now */ while (st->run) { const struct timespec delay = {0, st->ptime*1000000/2}; play_packet(st); if (aubuf_cur_size(st->aubuf) < st->psize) break; (void)nanosleep(&delay, NULL); } }
static void print_stats(struct audio_loop *al) { (void)re_fprintf(stderr, "\r%uHz %dch frame_size=%u" " n_read=%u n_write=%u" " aubuf=%5u codec=%s", al->srate, al->ch, al->fs, al->n_read, al->n_write, aubuf_cur_size(al->ab), aucodec); }
static void timeout(void *arg) { struct ausrc_st *st = arg; tmr_start(&st->tmr, 1000, timeout, st); /* check if audio buffer is empty */ if (aubuf_cur_size(st->aubuf) < (2 * st->sampc)) { info("aufile: end of file\n"); /* error handler must be called from re_main thread */ if (st->errh) st->errh(0, "end of file", st->arg); } }
static void timeout_tx(void *arg) { struct audio *a = arg; struct autx *tx = &a->tx; unsigned i; tmr_start(&a->tx.u.tmr, 5, timeout_tx, a); for (i=0; i<16; i++) { if (aubuf_cur_size(tx->aubuf) < tx->psize) break; poll_aubuf_tx(a); } }
static int read_file(struct ausrc_st *st) { struct mbuf *mb; int err; for (;;) { uint16_t *sampv; size_t i; mb = mbuf_alloc(4096); if (!mb) return ENOMEM; mb->end = mb->size; err = aufile_read(st->aufile, mb->buf, &mb->end); if (err) break; if (mb->end == 0) { info("aufile: end of file\n"); break; } /* convert from Little-Endian to Native-Endian */ sampv = (void *)mb->buf; for (i=0; i<mb->end/2; i++) { sampv[i] = sys_ltohs(sampv[i]); } aubuf_append(st->aubuf, mb); mb = mem_deref(mb); } info("aufile: loaded %zu bytes\n", aubuf_cur_size(st->aubuf)); mem_deref(mb); return err; }
/* Expected format: 16-bit signed PCM */ static void packet_handler(struct ausrc_st *st, GstBuffer *buffer) { GstMapInfo info; int err; if (!st->run) return; /* NOTE: When streaming from files, the buffer will be filled up * pretty quickly.. */ if (!gst_buffer_map(buffer, &info, GST_MAP_READ)) { warning("gst: gst_buffer_map failed\n"); return; } err = aubuf_write(st->aubuf, info.data, info.size); if (err) { warning("gst: aubuf_write: %m\n", err); } gst_buffer_unmap(buffer, &info); /* Empty buffer now */ while (st->run) { const struct timespec delay = {0, st->prm.ptime*1000000/2}; play_packet(st); if (aubuf_cur_size(st->aubuf) < st->psize) break; (void)nanosleep(&delay, NULL); } }