ardour export + jamin
Kees van Veen <[email protected]> Wed, 13 Jan 2010 09:40:13 +0100
| Newsgroups | gmane.comp.audio.jamin.devel |
|---|---|
| Message-ID | <[email protected]> |
Hi, I've joined the mailing list because of topic http://ardour.org/node/3016 concerning Ardour export with Jamin as an insert on the master bus, which (on all Ubuntu versions I've tried: Hardy, Jaunty and Karmic) causes Jamin to abort mostly at the very end of the export. I have no problem with running Jamin as an insert in 'normal' mode. When debugging I found that the condition upon a Jack ringbuffer write of io_queue() in io.c, causes Jamin to panic and abort() when the number of bytes to write does not correspond to the bytes written. I am not familiar with audio programming, so I maybe completely off track, but I wondered why Jamin doesn't do a retry. For normal operation (as I gather from the comment before the abort()) that would probably not be a good idea, but when Ardour exports it goes into freewheeling mode, and I gather that in that case 'different rules' apply, i.e. Jack tries to run as fast as it can, but it waits for children to complete their task, if I'm phrasing that correctly. I fiddled around with retrying to write the remaining bytes to the ring buffer (in freewheeling mode), and from the several times I've tried it, it seems to work properly, i.e. Jamin does not abort and eventually succeeds in writing all the bytes to the ring buffer, without (to me) audible effects in the export. I've attached the io.c diff to the latest CVS tree. From the Ardour forum I was told that I could get away with it, but I was solving the problem by the wrong means, which very well may be true. This problem seems to have been around for quite some time, and keeps being reported. Would be nice to get that fixed. Could any of you comment or help me in the right direction ? Regards, Kees ------------------------------------------------------------------------------ This SF.Net email is sponsored by the Verizon Developer Community Take advantage of Verizon's best-in-class app development support A streamlined, 14 day to market process makes app distribution fast and easy Join now and get one step closer to millions of Verizon customers http://p.sf.net/sfu/verizon-dev2dev _______________________________________________ Jamin-devel mailing list [email protected] https://lists.sourceforge.net/lists/listinfo/jamin-devel
io.c.diff
(text/x-patch, 1.8 KB)
--- io.c_orig 2010-01-13 09:28:47.000000000 +0100
+++ io.c 2010-01-13 09:29:59.000000000 +0100
@@ -123,6 +123,7 @@
static int have_dsp_thread = 0; /* DSP thread exists? */
static size_t dsp_block_bytes; /* DSP chunk size in bytes */
+static int freewheeling = 0; /* in freewheeling mode ? */
#define DSP_PRIORITY_DIFF 1 /* DSP thread priority difference */
static pthread_t dsp_thread; /* DSP thread handle */
@@ -468,6 +469,22 @@
/* queue JACK input buffers for DSP thread */
for (chan = 0; chan < nchannels; chan++) {
count = jack_ringbuffer_write(in_rb[chan], (void *) in[chan], nbytes);
+
+ if (freewheeling && count < nbytes) {
+
+ /* In freewheeling mode, try to write the remaining bytes.
+ * Sometimes a count of 0 is returned, wait a small while
+ * and try again. */
+ int try;
+ for (try=0; try<10 && count < nbytes; try++) {
+ int cnt, nbt = nbytes - count;
+ cnt = jack_ringbuffer_write(in_rb[chan], (void *) in[chan]+count, nbt);
+ if (cnt==0) {
+ usleep(100);
+ }
+ count += cnt;
+ }
+ }
if (count != nbytes) { /* buffer overflow? */
/* This is a realtime bug. We have input audio with no
@@ -602,6 +619,16 @@
}
+/* io_freewheel -- JACK freewheel callback.
+ *
+ * Called in the JACK process thread.
+ */
+void io_freewheel(int starting, void *arg)
+{
+ freewheeling = starting;
+}
+
+
/* io_free_heap -- free heap entry, if allocated. */
static inline void io_free_heap(char **p)
{
@@ -917,6 +944,7 @@
jack_on_shutdown(client, io_shutdown, NULL);
jack_set_xrun_callback(client, io_xrun, NULL);
jack_set_buffer_size_callback(client, io_bufsize, NULL);
+ jack_set_freewheel_callback (client, io_freewheel, NULL);
/* set initial buffer size and sample rate */
dsp_block_bytes = dsp_block_size * sizeof(jack_default_audio_sample_t);