Browse Source

Update Solaris drivers.

git-svn-id: http://subversion.jackaudio.org/jack/jack2/trunk/jackmp@4252 0c269be4-1314-0410-8aa9-9f06e86f4224
tags/1.9.8
sletz 14 years ago
parent
commit
4789c74f37
8 changed files with 265 additions and 266 deletions
  1. +9
    -8
      example-clients/latent_client.c
  2. +1
    -1
      example-clients/thru_client.c
  3. +23
    -23
      example-clients/tw.c
  4. +1
    -1
      example-clients/wait.c
  5. +9
    -9
      example-clients/zombie.c
  6. +135
    -135
      solaris/oss/JackBoomerDriver.cpp
  7. +87
    -87
      solaris/oss/JackOSSDriver.cpp
  8. +0
    -2
      windows/portaudio/JackPortAudioDriver.cpp

+ 9
- 8
example-clients/latent_client.c View File

@@ -1,4 +1,4 @@
/** @file simple_client.c
/** @file latent_client.c
* *
* @brief This simple client demonstrates the most basic features of JACK * @brief This simple client demonstrates the most basic features of JACK
* as they would be used by many applications. * as they would be used by many applications.
@@ -8,7 +8,7 @@
#include <errno.h> #include <errno.h>
#include <unistd.h> #include <unistd.h>
#include <stdlib.h> #include <stdlib.h>
#include <string.h>
#include <string.h>
#include <inttypes.h> #include <inttypes.h>


#include <jack/jack.h> #include <jack/jack.h>
@@ -19,12 +19,12 @@ jack_client_t *client;


jack_default_audio_sample_t *delay_line; jack_default_audio_sample_t *delay_line;
jack_nframes_t delay_index; jack_nframes_t delay_index;
jack_nframes_t latency = 1024;
#ifdef WIN32
#define jack_sleep(val) Sleep((val))
#else
#define jack_sleep(val) usleep((val) * 1000)
jack_nframes_t latency = 1024;
#ifdef WIN32
#define jack_sleep(val) Sleep((val))
#else
#define jack_sleep(val) usleep((val) * 1000)
#endif #endif


/** /**
@@ -213,3 +213,4 @@ main (int argc, char *argv[])
jack_client_close (client); jack_client_close (client);
exit (0); exit (0);
} }


+ 1
- 1
example-clients/thru_client.c View File

@@ -1,4 +1,4 @@
/** @file simple_client.c
/** @file thru_client.c
* *
* @brief This simple through client demonstrates the basic features of JACK * @brief This simple through client demonstrates the basic features of JACK
* as they would be used by many applications. * as they would be used by many applications.


+ 23
- 23
example-clients/tw.c View File

@@ -1,4 +1,4 @@
/** @file simple_client.c
/** @file tw.c
* *
* @brief This simple client demonstrates the basic features of JACK * @brief This simple client demonstrates the basic features of JACK
* as they would be used by many applications. * as they would be used by many applications.
@@ -42,56 +42,56 @@ _process (jack_nframes_t nframes)
{ {
jack_default_audio_sample_t *in, *out; jack_default_audio_sample_t *in, *out;
jack_transport_state_t ts = jack_transport_query(client, NULL); jack_transport_state_t ts = jack_transport_query(client, NULL);
if (ts == JackTransportRolling) { if (ts == JackTransportRolling) {
if (client_state == Init) if (client_state == Init)
client_state = Run; client_state = Run;
in = jack_port_get_buffer (input_port, nframes); in = jack_port_get_buffer (input_port, nframes);
out = jack_port_get_buffer (output_port, nframes); out = jack_port_get_buffer (output_port, nframes);
memcpy (out, in, memcpy (out, in,
sizeof (jack_default_audio_sample_t) * nframes); sizeof (jack_default_audio_sample_t) * nframes);
} else if (ts == JackTransportStopped) { } else if (ts == JackTransportStopped) {
if (client_state == Run) { if (client_state == Run) {
client_state = Exit; client_state = Exit;
return -1; // to stop the thread return -1; // to stop the thread
} }
} }


return 0;
return 0;
} }


static void* jack_thread(void *arg)
static void* jack_thread(void *arg)
{ {
jack_client_t* client = (jack_client_t*) arg; jack_client_t* client = (jack_client_t*) arg;
while (1) { while (1) {
jack_nframes_t frames = jack_cycle_wait (client); jack_nframes_t frames = jack_cycle_wait (client);
int status = _process(frames); int status = _process(frames);
jack_cycle_signal (client, status); jack_cycle_signal (client, status);
/* /*
Possibly do something else after signaling next clients in the graph Possibly do something else after signaling next clients in the graph
*/ */
/* End condition */ /* End condition */
if (status != 0) if (status != 0)
return 0;
return 0;
} }
/* not reached*/ /* not reached*/
return 0; return 0;
} }


/* /*
static void* jack_thread(void *arg)
static void* jack_thread(void *arg)
{ {
jack_client_t* client = (jack_client_t*) arg; jack_client_t* client = (jack_client_t*) arg;
while (1) { while (1) {
jack_nframes_t frames; jack_nframes_t frames;
int status; int status;
@@ -103,7 +103,7 @@ static void* jack_thread(void *arg)
frames = jack_cycle_wait (client); frames = jack_cycle_wait (client);
status = _process(frames); status = _process(frames);
jack_cycle_signal (client, status); jack_cycle_signal (client, status);
// cycle 3
// cycle 3
frames = jack_cycle_wait (client); frames = jack_cycle_wait (client);
status = _process(frames); status = _process(frames);
jack_cycle_signal (client, status); jack_cycle_signal (client, status);
@@ -112,7 +112,7 @@ static void* jack_thread(void *arg)
status = _process(frames); status = _process(frames);
jack_cycle_signal (client, status); jack_cycle_signal (client, status);
} }
return 0; return 0;
} }
*/ */
@@ -172,8 +172,8 @@ main (int argc, char *argv[])


/* tell the JACK server to call `process()' whenever /* tell the JACK server to call `process()' whenever
there is work to be done. there is work to be done.
*/
if (jack_set_process_thread(client, jack_thread, client) < 0)
*/
if (jack_set_process_thread(client, jack_thread, client) < 0)
exit(1); exit(1);


/* tell the JACK server to call `jack_shutdown()' if /* tell the JACK server to call `jack_shutdown()' if
@@ -183,7 +183,7 @@ main (int argc, char *argv[])


jack_on_shutdown (client, jack_shutdown, 0); jack_on_shutdown (client, jack_shutdown, 0);


/* display the current sample rate.
/* display the current sample rate.
*/ */


printf ("engine sample rate: %" PRIu32 "\n", printf ("engine sample rate: %" PRIu32 "\n",
@@ -231,7 +231,7 @@ main (int argc, char *argv[])
} }


free (ports); free (ports);
ports = jack_get_ports (client, NULL, NULL, ports = jack_get_ports (client, NULL, NULL,
JackPortIsPhysical|JackPortIsInput); JackPortIsPhysical|JackPortIsInput);
if (ports == NULL) { if (ports == NULL) {
@@ -244,7 +244,7 @@ main (int argc, char *argv[])
} }


free (ports); free (ports);
/* install a signal handler to properly quits jack client */ /* install a signal handler to properly quits jack client */
signal(SIGQUIT, signal_handler); signal(SIGQUIT, signal_handler);
signal(SIGTERM, signal_handler); signal(SIGTERM, signal_handler);


+ 1
- 1
example-clients/wait.c View File

@@ -40,7 +40,7 @@ main (int argc, char *argv[])
int wait_timeout = 0; int wait_timeout = 0;
time_t start_timestamp; time_t start_timestamp;


struct option long_options[] = { struct option long_options[] = {
{ "server", 1, 0, 's' }, { "server", 1, 0, 's' },
{ "wait", 0, 0, 'w' }, { "wait", 0, 0, 'w' },


+ 9
- 9
example-clients/zombie.c View File

@@ -1,6 +1,6 @@
/* /*
Copyright (C) 2002 Jeremy Hall Copyright (C) 2002 Jeremy Hall
This program is free software; you can redistribute it and/or modify This program is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by it under the terms of the GNU General Public License as published by
the Free Software Foundation; either version 2 of the License, or the Free Software Foundation; either version 2 of the License, or
@@ -30,18 +30,18 @@ int count = 0;
jack_port_t* output_port; jack_port_t* output_port;


static int static int
process(jack_nframes_t nframes, void* arg)
process(jack_nframes_t nframes, void* arg)
{ {
if (count++ == 1000) { if (count++ == 1000) {
printf("process block\n"); printf("process block\n");
//while (1) {} //while (1) {}
sleep(1); sleep(1);
} }
return 0; return 0;
} }


static void
static void
shutdown (void *arg) shutdown (void *arg)
{ {
printf("shutdown \n"); printf("shutdown \n");
@@ -57,7 +57,7 @@ main (int argc, char *argv[])
fprintf (stderr, "jack server not running?\n"); fprintf (stderr, "jack server not running?\n");
goto error; goto error;
} }
jack_set_process_callback (client, process, NULL); jack_set_process_callback (client, process, NULL);
jack_on_shutdown(client, shutdown, NULL); jack_on_shutdown(client, shutdown, NULL);
output_port = jack_port_register (client, "port1", JACK_DEFAULT_AUDIO_TYPE, JackPortIsOutput, 0); output_port = jack_port_register (client, "port1", JACK_DEFAULT_AUDIO_TYPE, JackPortIsOutput, 0);
@@ -67,9 +67,9 @@ main (int argc, char *argv[])
fprintf (stderr, "cannot activate client"); fprintf (stderr, "cannot activate client");
goto error; goto error;
} }
jack_connect(client, jack_port_name(output_port), "coreaudio:Built-in Audio:in2"); jack_connect(client, jack_port_name(output_port), "coreaudio:Built-in Audio:in2");
while (running) { while (running) {
sleep(1); sleep(1);
printf ("run\n"); printf ("run\n");
@@ -78,9 +78,9 @@ main (int argc, char *argv[])
jack_deactivate (client); jack_deactivate (client);
jack_client_close (client); jack_client_close (client);
return 0; return 0;
error: error:
if (client)
if (client)
jack_client_close (client); jack_client_close (client);
return 1; return 1;
} }


+ 135
- 135
solaris/oss/JackBoomerDriver.cpp View File

@@ -106,14 +106,14 @@ static inline void CopyAndConvertOut(void *dst, jack_sample_t *src, size_t nfram
case 24: { case 24: {
signed int *s32dst = (signed int*)dst; signed int *s32dst = (signed int*)dst;
s32dst += channel; s32dst += channel;
sample_move_d24_sS((char*)s32dst, src, nframes, byte_skip, NULL);
sample_move_d24_sS((char*)s32dst, src, nframes, byte_skip, NULL);
break; break;
}
}
case 32: { case 32: {
signed int *s32dst = (signed int*)dst; signed int *s32dst = (signed int*)dst;
s32dst += channel; s32dst += channel;
sample_move_d32u24_sS((char*)s32dst, src, nframes, byte_skip, NULL); sample_move_d32u24_sS((char*)s32dst, src, nframes, byte_skip, NULL);
break;
break;
} }
} }
} }
@@ -127,7 +127,7 @@ void JackBoomerDriver::SetSampleFormat()
fSampleSize = 4; fSampleSize = 4;
break; break;
case 32: /* native-endian 32-bit integer */ case 32: /* native-endian 32-bit integer */
fSampleFormat = AFMT_S32_NE;
fSampleFormat = AFMT_S32_NE;
fSampleSize = 4; fSampleSize = 4;
break; break;
case 16: /* native-endian 16-bit integer */ case 16: /* native-endian 16-bit integer */
@@ -144,13 +144,13 @@ void JackBoomerDriver::DisplayDeviceInfo()
oss_audioinfo ai_in, ai_out; oss_audioinfo ai_in, ai_out;
memset(&info, 0, sizeof(audio_buf_info)); memset(&info, 0, sizeof(audio_buf_info));
int cap = 0; int cap = 0;
// Duplex cards : http://manuals.opensound.com/developer/full_duplex.html // Duplex cards : http://manuals.opensound.com/developer/full_duplex.html
jack_info("Audio Interface Description :"); jack_info("Audio Interface Description :");
jack_info("Sampling Frequency : %d, Sample Format : %d, Mode : %d", fEngineControl->fSampleRate, fSampleFormat, fRWMode); jack_info("Sampling Frequency : %d, Sample Format : %d, Mode : %d", fEngineControl->fSampleRate, fSampleFormat, fRWMode);
if (fRWMode & kWrite) { if (fRWMode & kWrite) {
oss_sysinfo si; oss_sysinfo si;
if (ioctl(fOutFD, OSS_SYSINFO, &si) == -1) { if (ioctl(fOutFD, OSS_SYSINFO, &si) == -1) {
jack_error("JackBoomerDriver::DisplayDeviceInfo OSS_SYSINFO failed : %s@%i, errno = %d", __FILE__, __LINE__, errno); jack_error("JackBoomerDriver::DisplayDeviceInfo OSS_SYSINFO failed : %s@%i, errno = %d", __FILE__, __LINE__, errno);
@@ -162,18 +162,18 @@ void JackBoomerDriver::DisplayDeviceInfo()
jack_info("OSS numaudioengines %d", si.numaudioengines); jack_info("OSS numaudioengines %d", si.numaudioengines);
jack_info("OSS numcards %d", si.numcards); jack_info("OSS numcards %d", si.numcards);
} }
jack_info("Output capabilities - %d channels : ", fPlaybackChannels); jack_info("Output capabilities - %d channels : ", fPlaybackChannels);
jack_info("Output block size = %d", fOutputBufferSize); jack_info("Output block size = %d", fOutputBufferSize);
if (ioctl(fOutFD, SNDCTL_DSP_GETOSPACE, &info) == -1) { if (ioctl(fOutFD, SNDCTL_DSP_GETOSPACE, &info) == -1) {
jack_error("JackBoomerDriver::DisplayDeviceInfo SNDCTL_DSP_GETOSPACE failed : %s@%i, errno = %d", __FILE__, __LINE__, errno); jack_error("JackBoomerDriver::DisplayDeviceInfo SNDCTL_DSP_GETOSPACE failed : %s@%i, errno = %d", __FILE__, __LINE__, errno);
} else { } else {
jack_info("output space info: fragments = %d, fragstotal = %d, fragsize = %d, bytes = %d",
jack_info("output space info: fragments = %d, fragstotal = %d, fragsize = %d, bytes = %d",
info.fragments, info.fragstotal, info.fragsize, info.bytes); info.fragments, info.fragstotal, info.fragsize, info.bytes);
fFragmentSize = info.fragsize; fFragmentSize = info.fragsize;
} }
if (ioctl(fOutFD, SNDCTL_DSP_GETCAPS, &cap) == -1) { if (ioctl(fOutFD, SNDCTL_DSP_GETCAPS, &cap) == -1) {
jack_error("JackBoomerDriver::DisplayDeviceInfo SNDCTL_DSP_GETCAPS failed : %s@%i, errno = %d", __FILE__, __LINE__, errno); jack_error("JackBoomerDriver::DisplayDeviceInfo SNDCTL_DSP_GETCAPS failed : %s@%i, errno = %d", __FILE__, __LINE__, errno);
} else { } else {
@@ -186,10 +186,10 @@ void JackBoomerDriver::DisplayDeviceInfo()
if (cap & DSP_CAP_MULTI) jack_info(" DSP_CAP_MULTI"); if (cap & DSP_CAP_MULTI) jack_info(" DSP_CAP_MULTI");
if (cap & DSP_CAP_BIND) jack_info(" DSP_CAP_BIND"); if (cap & DSP_CAP_BIND) jack_info(" DSP_CAP_BIND");
} }
}
}
if (fRWMode & kRead) { if (fRWMode & kRead) {
oss_sysinfo si; oss_sysinfo si;
if (ioctl(fInFD, OSS_SYSINFO, &si) == -1) { if (ioctl(fInFD, OSS_SYSINFO, &si) == -1) {
jack_error("JackBoomerDriver::DisplayDeviceInfo OSS_SYSINFO failed : %s@%i, errno = %d", __FILE__, __LINE__, errno); jack_error("JackBoomerDriver::DisplayDeviceInfo OSS_SYSINFO failed : %s@%i, errno = %d", __FILE__, __LINE__, errno);
@@ -201,14 +201,14 @@ void JackBoomerDriver::DisplayDeviceInfo()
jack_info("OSS numaudioengines %d", si.numaudioengines); jack_info("OSS numaudioengines %d", si.numaudioengines);
jack_info("OSS numcards %d", si.numcards); jack_info("OSS numcards %d", si.numcards);
} }
jack_info("Input capabilities - %d channels : ", fCaptureChannels); jack_info("Input capabilities - %d channels : ", fCaptureChannels);
jack_info("Input block size = %d", fInputBufferSize); jack_info("Input block size = %d", fInputBufferSize);
if (ioctl(fInFD, SNDCTL_DSP_GETISPACE, &info) == -1) {
if (ioctl(fInFD, SNDCTL_DSP_GETISPACE, &info) == -1) {
jack_error("JackBoomerDriver::DisplayDeviceInfo SNDCTL_DSP_GETOSPACE failed : %s@%i, errno = %d", __FILE__, __LINE__, errno); jack_error("JackBoomerDriver::DisplayDeviceInfo SNDCTL_DSP_GETOSPACE failed : %s@%i, errno = %d", __FILE__, __LINE__, errno);
} else { } else {
jack_info("input space info: fragments = %d, fragstotal = %d, fragsize = %d, bytes = %d",
jack_info("input space info: fragments = %d, fragstotal = %d, fragsize = %d, bytes = %d",
info.fragments, info.fragstotal, info.fragsize, info.bytes); info.fragments, info.fragstotal, info.fragsize, info.bytes);
} }


@@ -225,31 +225,30 @@ void JackBoomerDriver::DisplayDeviceInfo()
if (cap & DSP_CAP_BIND) jack_info(" DSP_CAP_BIND"); if (cap & DSP_CAP_BIND) jack_info(" DSP_CAP_BIND");
} }
} }
if (ai_in.rate_source != ai_out.rate_source) { if (ai_in.rate_source != ai_out.rate_source) {
jack_info("Warning : input and output are not necessarily driven by the same clock!"); jack_info("Warning : input and output are not necessarily driven by the same clock!");
} }
} }


JackBoomerDriver::JackBoomerDriver(const char* name, const char* alias, JackLockedEngine* engine, JackSynchro* table) JackBoomerDriver::JackBoomerDriver(const char* name, const char* alias, JackLockedEngine* engine, JackSynchro* table)
: JackAudioDriver(name, alias, engine, table),
fInFD(-1), fOutFD(-1), fBits(0),
fSampleFormat(0), fNperiods(0), fSampleSize(0), fFragmentSize(0),
fRWMode(0), fExcl(false), fSyncIO(false),
fInputBufferSize(0), fOutputBufferSize(0),
fInputBuffer(NULL), fOutputBuffer(NULL),
fInputThread(&fInputHandler), fOutputThread(&fOutputHandler),
fInputHandler(this), fOutputHandler(this)
: JackAudioDriver(name, alias, engine, table),
fInFD(-1), fOutFD(-1), fBits(0),
fSampleFormat(0), fNperiods(0), fSampleSize(0), fFragmentSize(0),
fRWMode(0), fExcl(false), fSyncIO(false),
fInputBufferSize(0), fOutputBufferSize(0),
fInputBuffer(NULL), fOutputBuffer(NULL),
fInputThread(&fInputHandler), fOutputThread(&fOutputHandler),
fInputHandler(this), fOutputHandler(this)
{ {
sem_init(&fReadSema, 0, 0);
sem_init(&fWriteSema, 0, 0);
sem_init(&fReadSema, 0, 0);
sem_init(&fWriteSema, 0, 0);
} }


JackBoomerDriver::~JackBoomerDriver() JackBoomerDriver::~JackBoomerDriver()
{ {
sem_destroy(&fReadSema);
sem_destroy(&fWriteSema);
sem_destroy(&fReadSema);
sem_destroy(&fWriteSema);
} }


int JackBoomerDriver::OpenInput() int JackBoomerDriver::OpenInput()
@@ -260,8 +259,9 @@ int JackBoomerDriver::OpenInput()
int cur_sample_format; int cur_sample_format;
jack_nframes_t cur_sample_rate; jack_nframes_t cur_sample_rate;


if (fCaptureChannels == 0) fCaptureChannels = 2;
if (fCaptureChannels == 0)
fCaptureChannels = 2;

if ((fInFD = open(fCaptureDriverName, O_RDONLY | ((fExcl) ? O_EXCL : 0))) < 0) { if ((fInFD = open(fCaptureDriverName, O_RDONLY | ((fExcl) ? O_EXCL : 0))) < 0) {
jack_error("JackBoomerDriver::OpenInput failed to open device : %s@%i, errno = %d", __FILE__, __LINE__, errno); jack_error("JackBoomerDriver::OpenInput failed to open device : %s@%i, errno = %d", __FILE__, __LINE__, errno);
return -1; return -1;
@@ -276,7 +276,7 @@ int JackBoomerDriver::OpenInput()
} }
} }


gFragFormat = (2 << 16) + int2pow2(fEngineControl->fBufferSize * fSampleSize * fCaptureChannels);
gFragFormat = (2 << 16) + int2pow2(fEngineControl->fBufferSize * fSampleSize * fCaptureChannels);
if (ioctl(fInFD, SNDCTL_DSP_SETFRAGMENT, &gFragFormat) == -1) { if (ioctl(fInFD, SNDCTL_DSP_SETFRAGMENT, &gFragFormat) == -1) {
jack_error("JackBoomerDriver::OpenInput failed to set fragments : %s@%i, errno = %d", __FILE__, __LINE__, errno); jack_error("JackBoomerDriver::OpenInput failed to set fragments : %s@%i, errno = %d", __FILE__, __LINE__, errno);
goto error; goto error;
@@ -290,7 +290,7 @@ int JackBoomerDriver::OpenInput()
if (cur_sample_format != fSampleFormat) { if (cur_sample_format != fSampleFormat) {
jack_info("JackBoomerDriver::OpenInput driver forced the sample format %ld", fSampleFormat); jack_info("JackBoomerDriver::OpenInput driver forced the sample format %ld", fSampleFormat);
} }
cur_capture_channels = fCaptureChannels; cur_capture_channels = fCaptureChannels;
if (ioctl(fInFD, SNDCTL_DSP_CHANNELS, &fCaptureChannels) == -1) { if (ioctl(fInFD, SNDCTL_DSP_CHANNELS, &fCaptureChannels) == -1) {
jack_error("JackBoomerDriver::OpenInput failed to set channels : %s@%i, errno = %d", __FILE__, __LINE__, errno); jack_error("JackBoomerDriver::OpenInput failed to set channels : %s@%i, errno = %d", __FILE__, __LINE__, errno);
@@ -299,7 +299,7 @@ int JackBoomerDriver::OpenInput()
if (cur_capture_channels != fCaptureChannels) { if (cur_capture_channels != fCaptureChannels) {
jack_info("JackBoomerDriver::OpenInput driver forced the number of capture channels %ld", fCaptureChannels); jack_info("JackBoomerDriver::OpenInput driver forced the number of capture channels %ld", fCaptureChannels);
} }
cur_sample_rate = fEngineControl->fSampleRate; cur_sample_rate = fEngineControl->fSampleRate;
if (ioctl(fInFD, SNDCTL_DSP_SPEED, &fEngineControl->fSampleRate) == -1) { if (ioctl(fInFD, SNDCTL_DSP_SPEED, &fEngineControl->fSampleRate) == -1) {
jack_error("JackBoomerDriver::OpenInput failed to set sample rate : %s@%i, errno = %d", __FILE__, __LINE__, errno); jack_error("JackBoomerDriver::OpenInput failed to set sample rate : %s@%i, errno = %d", __FILE__, __LINE__, errno);
@@ -315,7 +315,7 @@ int JackBoomerDriver::OpenInput()
fInputBuffer = (void*)calloc(fInputBufferSize, 1); fInputBuffer = (void*)calloc(fInputBufferSize, 1);
assert(fInputBuffer); assert(fInputBuffer);
return 0; return 0;
error: error:
::close(fInFD); ::close(fInFD);
return -1; return -1;
@@ -329,28 +329,29 @@ int JackBoomerDriver::OpenOutput()
int cur_playback_channels; int cur_playback_channels;
jack_nframes_t cur_sample_rate; jack_nframes_t cur_sample_rate;


if (fPlaybackChannels == 0) fPlaybackChannels = 2;
if (fPlaybackChannels == 0)
fPlaybackChannels = 2;

if ((fOutFD = open(fPlaybackDriverName, O_WRONLY | ((fExcl) ? O_EXCL : 0))) < 0) { if ((fOutFD = open(fPlaybackDriverName, O_WRONLY | ((fExcl) ? O_EXCL : 0))) < 0) {
jack_error("JackBoomerDriver::OpenOutput failed to open device : %s@%i, errno = %d", __FILE__, __LINE__, errno); jack_error("JackBoomerDriver::OpenOutput failed to open device : %s@%i, errno = %d", __FILE__, __LINE__, errno);
return -1; return -1;
} }


jack_log("JackBoomerDriver::OpenOutput output fOutFD = %d", fOutFD); jack_log("JackBoomerDriver::OpenOutput output fOutFD = %d", fOutFD);
if (fExcl) { if (fExcl) {
if (ioctl(fOutFD, SNDCTL_DSP_COOKEDMODE, &flags) == -1) { if (ioctl(fOutFD, SNDCTL_DSP_COOKEDMODE, &flags) == -1) {
jack_error("JackBoomerDriver::OpenOutput failed to set cooked mode : %s@%i, errno = %d", __FILE__, __LINE__, errno); jack_error("JackBoomerDriver::OpenOutput failed to set cooked mode : %s@%i, errno = %d", __FILE__, __LINE__, errno);
goto error; goto error;
}
}
}
}


gFragFormat = (2 << 16) + int2pow2(fEngineControl->fBufferSize * fSampleSize * fPlaybackChannels);
gFragFormat = (2 << 16) + int2pow2(fEngineControl->fBufferSize * fSampleSize * fPlaybackChannels);
if (ioctl(fOutFD, SNDCTL_DSP_SETFRAGMENT, &gFragFormat) == -1) { if (ioctl(fOutFD, SNDCTL_DSP_SETFRAGMENT, &gFragFormat) == -1) {
jack_error("JackBoomerDriver::OpenOutput failed to set fragments : %s@%i, errno = %d", __FILE__, __LINE__, errno); jack_error("JackBoomerDriver::OpenOutput failed to set fragments : %s@%i, errno = %d", __FILE__, __LINE__, errno);
goto error; goto error;
} }
cur_sample_format = fSampleFormat; cur_sample_format = fSampleFormat;
if (ioctl(fOutFD, SNDCTL_DSP_SETFMT, &fSampleFormat) == -1) { if (ioctl(fOutFD, SNDCTL_DSP_SETFMT, &fSampleFormat) == -1) {
jack_error("JackBoomerDriver::OpenOutput failed to set format : %s@%i, errno = %d", __FILE__, __LINE__, errno); jack_error("JackBoomerDriver::OpenOutput failed to set format : %s@%i, errno = %d", __FILE__, __LINE__, errno);
@@ -359,7 +360,7 @@ int JackBoomerDriver::OpenOutput()
if (cur_sample_format != fSampleFormat) { if (cur_sample_format != fSampleFormat) {
jack_info("JackBoomerDriver::OpenOutput driver forced the sample format %ld", fSampleFormat); jack_info("JackBoomerDriver::OpenOutput driver forced the sample format %ld", fSampleFormat);
} }
cur_playback_channels = fPlaybackChannels; cur_playback_channels = fPlaybackChannels;
if (ioctl(fOutFD, SNDCTL_DSP_CHANNELS, &fPlaybackChannels) == -1) { if (ioctl(fOutFD, SNDCTL_DSP_CHANNELS, &fPlaybackChannels) == -1) {
jack_error("JackBoomerDriver::OpenOutput failed to set channels : %s@%i, errno = %d", __FILE__, __LINE__, errno); jack_error("JackBoomerDriver::OpenOutput failed to set channels : %s@%i, errno = %d", __FILE__, __LINE__, errno);
@@ -380,33 +381,33 @@ int JackBoomerDriver::OpenOutput()


// Just set the write size to the value we want... // Just set the write size to the value we want...
fOutputBufferSize = fEngineControl->fBufferSize * fSampleSize * fPlaybackChannels; fOutputBufferSize = fEngineControl->fBufferSize * fSampleSize * fPlaybackChannels;
fOutputBuffer = (void*)calloc(fOutputBufferSize, 1); fOutputBuffer = (void*)calloc(fOutputBufferSize, 1);
assert(fOutputBuffer); assert(fOutputBuffer);
return 0; return 0;
error: error:
::close(fOutFD); ::close(fOutFD);
return -1; return -1;
} }


int JackBoomerDriver::Open(jack_nframes_t nframes, int JackBoomerDriver::Open(jack_nframes_t nframes,
int user_nperiods,
jack_nframes_t samplerate,
bool capturing,
bool playing,
int inchannels,
int outchannels,
bool excl,
bool monitor,
const char* capture_driver_uid,
const char* playback_driver_uid,
jack_nframes_t capture_latency,
jack_nframes_t playback_latency,
int bits, bool syncio)
int user_nperiods,
jack_nframes_t samplerate,
bool capturing,
bool playing,
int inchannels,
int outchannels,
bool excl,
bool monitor,
const char* capture_driver_uid,
const char* playback_driver_uid,
jack_nframes_t capture_latency,
jack_nframes_t playback_latency,
int bits, bool syncio)
{ {
// Generic JackAudioDriver Open // Generic JackAudioDriver Open
if (JackAudioDriver::Open(nframes, samplerate, capturing, playing, inchannels, outchannels, monitor,
if (JackAudioDriver::Open(nframes, samplerate, capturing, playing, inchannels, outchannels, monitor,
capture_driver_uid, playback_driver_uid, capture_latency, playback_latency) != 0) { capture_driver_uid, playback_driver_uid, capture_latency, playback_latency) != 0) {
return -1; return -1;
} else { } else {
@@ -422,12 +423,12 @@ int JackBoomerDriver::Open(jack_nframes_t nframes,
fExcl = excl; fExcl = excl;
fNperiods = (user_nperiods == 0) ? 1 : user_nperiods ; fNperiods = (user_nperiods == 0) ? 1 : user_nperiods ;
fSyncIO = syncio; fSyncIO = syncio;
#ifdef JACK_MONITOR #ifdef JACK_MONITOR
// Force memory page in // Force memory page in
memset(&gCycleTable, 0, sizeof(gCycleTable)); memset(&gCycleTable, 0, sizeof(gCycleTable));
#endif #endif
if (OpenAux() < 0) { if (OpenAux() < 0) {
Close(); Close();
return -1; return -1;
@@ -441,14 +442,14 @@ int JackBoomerDriver::Close()
{ {
#ifdef JACK_MONITOR #ifdef JACK_MONITOR
FILE* file = fopen("OSSProfiling.log", "w"); FILE* file = fopen("OSSProfiling.log", "w");
if (file) { if (file) {
jack_info("Writing OSS driver timing data...."); jack_info("Writing OSS driver timing data....");
for (int i = 1; i < std::min(gCycleReadCount, gCycleWriteCount); i++) { for (int i = 1; i < std::min(gCycleReadCount, gCycleWriteCount); i++) {
int d1 = gCycleTable.fTable[i].fAfterRead - gCycleTable.fTable[i].fBeforeRead; int d1 = gCycleTable.fTable[i].fAfterRead - gCycleTable.fTable[i].fBeforeRead;
int d2 = gCycleTable.fTable[i].fAfterReadConvert - gCycleTable.fTable[i].fAfterRead; int d2 = gCycleTable.fTable[i].fAfterReadConvert - gCycleTable.fTable[i].fAfterRead;
int d3 = gCycleTable.fTable[i].fAfterWrite - gCycleTable.fTable[i].fBeforeWrite; int d3 = gCycleTable.fTable[i].fAfterWrite - gCycleTable.fTable[i].fBeforeWrite;
int d4 = gCycleTable.fTable[i].fBeforeWrite - gCycleTable.fTable[i].fBeforeWriteConvert;
int d4 = gCycleTable.fTable[i].fBeforeWrite - gCycleTable.fTable[i].fBeforeWriteConvert;
fprintf(file, "%d \t %d \t %d \t %d \t \n", d1, d2, d3, d4); fprintf(file, "%d \t %d \t %d \t %d \t \n", d1, d2, d3, d4);
} }
fclose(file); fclose(file);
@@ -461,7 +462,7 @@ int JackBoomerDriver::Close()
if (file == NULL) { if (file == NULL) {
jack_error("JackBoomerDriver::Close cannot open TimingOSS.plot file"); jack_error("JackBoomerDriver::Close cannot open TimingOSS.plot file");
} else { } else {
fprintf(file, "set grid\n"); fprintf(file, "set grid\n");
fprintf(file, "set title \"OSS audio driver timing\"\n"); fprintf(file, "set title \"OSS audio driver timing\"\n");
fprintf(file, "set xlabel \"audio cycles\"\n"); fprintf(file, "set xlabel \"audio cycles\"\n");
@@ -470,10 +471,10 @@ int JackBoomerDriver::Close()
\"OSSProfiling.log\" using 2 title \"Driver read convert duration\" with lines, \ \"OSSProfiling.log\" using 2 title \"Driver read convert duration\" with lines, \
\"OSSProfiling.log\" using 3 title \"Driver write wait\" with lines, \ \"OSSProfiling.log\" using 3 title \"Driver write wait\" with lines, \
\"OSSProfiling.log\" using 4 title \"Driver write convert duration\" with lines\n"); \"OSSProfiling.log\" using 4 title \"Driver write convert duration\" with lines\n");
fprintf(file, "set output 'TimingOSS.pdf\n"); fprintf(file, "set output 'TimingOSS.pdf\n");
fprintf(file, "set terminal pdf\n"); fprintf(file, "set terminal pdf\n");
fprintf(file, "set grid\n"); fprintf(file, "set grid\n");
fprintf(file, "set title \"OSS audio driver timing\"\n"); fprintf(file, "set title \"OSS audio driver timing\"\n");
fprintf(file, "set xlabel \"audio cycles\"\n"); fprintf(file, "set xlabel \"audio cycles\"\n");
@@ -482,12 +483,12 @@ int JackBoomerDriver::Close()
\"OSSProfiling.log\" using 2 title \"Driver read convert duration\" with lines, \ \"OSSProfiling.log\" using 2 title \"Driver read convert duration\" with lines, \
\"OSSProfiling.log\" using 3 title \"Driver write wait\" with lines, \ \"OSSProfiling.log\" using 3 title \"Driver write wait\" with lines, \
\"OSSProfiling.log\" using 4 title \"Driver write convert duration\" with lines\n"); \"OSSProfiling.log\" using 4 title \"Driver write convert duration\" with lines\n");
fclose(file); fclose(file);
} }
#endif #endif
int res = JackAudioDriver::Close(); int res = JackAudioDriver::Close();
CloseAux();
CloseAux();
return res; return res;
} }


@@ -498,12 +499,12 @@ int JackBoomerDriver::OpenAux()
if ((fRWMode & kRead) && (OpenInput() < 0)) { if ((fRWMode & kRead) && (OpenInput() < 0)) {
return -1; return -1;
} }
if ((fRWMode & kWrite) && (OpenOutput() < 0)) {
if ((fRWMode & kWrite) && (OpenOutput() < 0)) {
return -1; return -1;
} }
DisplayDeviceInfo();
DisplayDeviceInfo();
return 0; return 0;
} }


@@ -513,16 +514,16 @@ void JackBoomerDriver::CloseAux()
close(fInFD); close(fInFD);
fInFD = -1; fInFD = -1;
} }
if (fRWMode & kWrite && fOutFD >= 0) { if (fRWMode & kWrite && fOutFD >= 0) {
close(fOutFD); close(fOutFD);
fOutFD = -1; fOutFD = -1;
} }
if (fInputBuffer) if (fInputBuffer)
free(fInputBuffer); free(fInputBuffer);
fInputBuffer = NULL; fInputBuffer = NULL;
if (fOutputBuffer) if (fOutputBuffer)
free(fOutputBuffer); free(fOutputBuffer);
fOutputBuffer = NULL; fOutputBuffer = NULL;
@@ -533,29 +534,29 @@ int JackBoomerDriver::Start()
jack_log("JackBoomerDriver::Start"); jack_log("JackBoomerDriver::Start");
JackAudioDriver::Start(); JackAudioDriver::Start();


// Input/output synchronisation
// Input/output synchronisation
if (fInFD >= 0 && fOutFD >= 0 && fSyncIO) { if (fInFD >= 0 && fOutFD >= 0 && fSyncIO) {


jack_log("JackBoomerDriver::Start sync input/output");
jack_log("JackBoomerDriver::Start sync input/output");


// Create and fill synch group // Create and fill synch group
int id; int id;
oss_syncgroup group; oss_syncgroup group;
group.id = 0; group.id = 0;
group.mode = PCM_ENABLE_INPUT; group.mode = PCM_ENABLE_INPUT;
if (ioctl(fInFD, SNDCTL_DSP_SYNCGROUP, &group) == -1)
if (ioctl(fInFD, SNDCTL_DSP_SYNCGROUP, &group) == -1)
jack_error("JackBoomerDriver::Start failed to use SNDCTL_DSP_SYNCGROUP : %s@%i, errno = %d", __FILE__, __LINE__, errno); jack_error("JackBoomerDriver::Start failed to use SNDCTL_DSP_SYNCGROUP : %s@%i, errno = %d", __FILE__, __LINE__, errno);
group.mode = PCM_ENABLE_OUTPUT; group.mode = PCM_ENABLE_OUTPUT;
if (ioctl(fOutFD, SNDCTL_DSP_SYNCGROUP, &group) == -1)
if (ioctl(fOutFD, SNDCTL_DSP_SYNCGROUP, &group) == -1)
jack_error("JackBoomerDriver::Start failed to use SNDCTL_DSP_SYNCGROUP : %s@%i, errno = %d", __FILE__, __LINE__, errno); jack_error("JackBoomerDriver::Start failed to use SNDCTL_DSP_SYNCGROUP : %s@%i, errno = %d", __FILE__, __LINE__, errno);


// Prefill output buffer : 2 fragments of silence as described in http://manuals.opensound.com/developer/synctest.c.html#LOC6 // Prefill output buffer : 2 fragments of silence as described in http://manuals.opensound.com/developer/synctest.c.html#LOC6
char* silence_buf = (char*)malloc(fFragmentSize); char* silence_buf = (char*)malloc(fFragmentSize);
memset(silence_buf, 0, fFragmentSize); memset(silence_buf, 0, fFragmentSize);


jack_log ("JackBoomerDriver::Start prefill size = %d", fFragmentSize);
jack_log ("JackBoomerDriver::Start prefill size = %d", fFragmentSize);


for (int i = 0; i < 2; i++) { for (int i = 0; i < 2; i++) {
ssize_t count = ::write(fOutFD, silence_buf, fFragmentSize); ssize_t count = ::write(fOutFD, silence_buf, fFragmentSize);
@@ -569,12 +570,12 @@ int JackBoomerDriver::Start()
// Start input/output in sync // Start input/output in sync
id = group.id; id = group.id;


if (ioctl(fInFD, SNDCTL_DSP_SYNCSTART, &id) == -1)
if (ioctl(fInFD, SNDCTL_DSP_SYNCSTART, &id) == -1)
jack_error("JackBoomerDriver::Start failed to use SNDCTL_DSP_SYNCSTART : %s@%i, errno = %d", __FILE__, __LINE__, errno); jack_error("JackBoomerDriver::Start failed to use SNDCTL_DSP_SYNCSTART : %s@%i, errno = %d", __FILE__, __LINE__, errno);


} else if (fOutFD >= 0) { } else if (fOutFD >= 0) {
// Maybe necessary to write an empty output buffer first time : see http://manuals.opensound.com/developer/fulldup.c.html
// Maybe necessary to write an empty output buffer first time : see http://manuals.opensound.com/developer/fulldup.c.html
memset(fOutputBuffer, 0, fOutputBufferSize); memset(fOutputBuffer, 0, fOutputBufferSize);


// Prefill ouput buffer // Prefill ouput buffer
@@ -584,8 +585,8 @@ int JackBoomerDriver::Start()
jack_error("JackBoomerDriver::Start error bytes written = %ld", count); jack_error("JackBoomerDriver::Start error bytes written = %ld", count);
} }
} }
}
}
// Start input thread only when needed // Start input thread only when needed
if (fInFD >= 0) { if (fInFD >= 0) {
if (fInputThread.StartSync() < 0) { if (fInputThread.StartSync() < 0) {
@@ -627,44 +628,44 @@ bool JackBoomerDriver::JackBoomerDriverInput::Init()
if (fDriver->fInputThread.AcquireRealTime(GetEngineControl()->fServerPriority) < 0) { if (fDriver->fInputThread.AcquireRealTime(GetEngineControl()->fServerPriority) < 0) {
jack_error("AcquireRealTime error"); jack_error("AcquireRealTime error");
} else { } else {
set_threaded_log_function();
set_threaded_log_function();
} }
} }
return true; return true;
} }


// TODO : better error handling // TODO : better error handling
bool JackBoomerDriver::JackBoomerDriverInput::Execute() bool JackBoomerDriver::JackBoomerDriverInput::Execute()
{ {
#ifdef JACK_MONITOR #ifdef JACK_MONITOR
gCycleTable.fTable[gCycleReadCount].fBeforeRead = GetMicroSeconds(); gCycleTable.fTable[gCycleReadCount].fBeforeRead = GetMicroSeconds();
#endif #endif


audio_errinfo ei_in; audio_errinfo ei_in;
ssize_t count = ::read(fDriver->fInFD, fDriver->fInputBuffer, fDriver->fInputBufferSize);
ssize_t count = ::read(fDriver->fInFD, fDriver->fInputBuffer, fDriver->fInputBufferSize);
#ifdef JACK_MONITOR #ifdef JACK_MONITOR
if (count > 0 && count != (int)fDriver->fInputBufferSize) if (count > 0 && count != (int)fDriver->fInputBufferSize)
jack_log("JackBoomerDriverInput::Execute count = %ld", count / (fDriver->fSampleSize * fDriver->fCaptureChannels)); jack_log("JackBoomerDriverInput::Execute count = %ld", count / (fDriver->fSampleSize * fDriver->fCaptureChannels));
gCycleTable.fTable[gCycleReadCount].fAfterRead = GetMicroSeconds(); gCycleTable.fTable[gCycleReadCount].fAfterRead = GetMicroSeconds();
#endif #endif
// XRun detection // XRun detection
if (ioctl(fDriver->fInFD, SNDCTL_DSP_GETERROR, &ei_in) == 0) { if (ioctl(fDriver->fInFD, SNDCTL_DSP_GETERROR, &ei_in) == 0) {


if (ei_in.rec_overruns > 0 ) { if (ei_in.rec_overruns > 0 ) {
jack_error("JackBoomerDriverInput::Execute overruns"); jack_error("JackBoomerDriverInput::Execute overruns");
jack_time_t cur_time = GetMicroSeconds(); jack_time_t cur_time = GetMicroSeconds();
fDriver->NotifyXRun(cur_time, float(cur_time - fDriver->fBeginDateUst)); // Better this value than nothing...
fDriver->NotifyXRun(cur_time, float(cur_time - fDriver->fBeginDateUst)); // Better this value than nothing...
} }


if (ei_in.rec_errorcount > 0 && ei_in.rec_lasterror != 0) { if (ei_in.rec_errorcount > 0 && ei_in.rec_lasterror != 0) {
jack_error("%d OSS rec event(s), last=%05d:%d", ei_in.rec_errorcount, ei_in.rec_lasterror, ei_in.rec_errorparm); jack_error("%d OSS rec event(s), last=%05d:%d", ei_in.rec_errorcount, ei_in.rec_lasterror, ei_in.rec_errorparm);
} }
}
}
if (count < 0) { if (count < 0) {
jack_log("JackBoomerDriverInput::Execute error = %s", strerror(errno)); jack_log("JackBoomerDriverInput::Execute error = %s", strerror(errno));
} else if (count < (int)fDriver->fInputBufferSize) { } else if (count < (int)fDriver->fInputBufferSize) {
@@ -675,11 +676,11 @@ bool JackBoomerDriver::JackBoomerDriverInput::Execute()
fDriver->CycleTakeBeginTime(); fDriver->CycleTakeBeginTime();
for (int i = 0; i < fDriver->fCaptureChannels; i++) { for (int i = 0; i < fDriver->fCaptureChannels; i++) {
if (fDriver->fGraphManager->GetConnectionsNum(fDriver->fCapturePortList[i]) > 0) { if (fDriver->fGraphManager->GetConnectionsNum(fDriver->fCapturePortList[i]) > 0) {
CopyAndConvertIn(fDriver->GetInputBuffer(i),
fDriver->fInputBuffer,
fDriver->fEngineControl->fBufferSize,
i,
fDriver->fCaptureChannels * fDriver->fSampleSize,
CopyAndConvertIn(fDriver->GetInputBuffer(i),
fDriver->fInputBuffer,
fDriver->fEngineControl->fBufferSize,
i,
fDriver->fCaptureChannels * fDriver->fSampleSize,
fDriver->fBits); fDriver->fBits);
} }
} }
@@ -707,18 +708,18 @@ bool JackBoomerDriver::JackBoomerDriverOutput::Init()
if (fDriver->fOutputThread.AcquireRealTime(GetEngineControl()->fServerPriority) < 0) { if (fDriver->fOutputThread.AcquireRealTime(GetEngineControl()->fServerPriority) < 0) {
jack_error("AcquireRealTime error"); jack_error("AcquireRealTime error");
} else { } else {
set_threaded_log_function();
set_threaded_log_function();
} }
} }
int delay; int delay;
if (ioctl(fDriver->fOutFD, SNDCTL_DSP_GETODELAY, &delay) == -1) { if (ioctl(fDriver->fOutFD, SNDCTL_DSP_GETODELAY, &delay) == -1) {
jack_error("JackBoomerDriverOutput::Init error get out delay : %s@%i, errno = %d", __FILE__, __LINE__, errno); jack_error("JackBoomerDriverOutput::Init error get out delay : %s@%i, errno = %d", __FILE__, __LINE__, errno);
} }
delay /= fDriver->fSampleSize * fDriver->fPlaybackChannels; delay /= fDriver->fSampleSize * fDriver->fPlaybackChannels;
jack_info("JackBoomerDriverOutput::Init output latency frames = %ld", delay); jack_info("JackBoomerDriverOutput::Init output latency frames = %ld", delay);
return true; return true;
} }


@@ -730,21 +731,21 @@ bool JackBoomerDriver::JackBoomerDriverOutput::Execute()
#ifdef JACK_MONITOR #ifdef JACK_MONITOR
gCycleTable.fTable[gCycleWriteCount].fBeforeWriteConvert = GetMicroSeconds(); gCycleTable.fTable[gCycleWriteCount].fBeforeWriteConvert = GetMicroSeconds();
#endif #endif
for (int i = 0; i < fDriver->fPlaybackChannels; i++) { for (int i = 0; i < fDriver->fPlaybackChannels; i++) {
if (fDriver->fGraphManager->GetConnectionsNum(fDriver->fPlaybackPortList[i]) > 0) { if (fDriver->fGraphManager->GetConnectionsNum(fDriver->fPlaybackPortList[i]) > 0) {
CopyAndConvertOut(fDriver->fOutputBuffer,
fDriver->GetOutputBuffer(i),
fDriver->fEngineControl->fBufferSize,
i,
fDriver->fPlaybackChannels * fDriver->fSampleSize,
CopyAndConvertOut(fDriver->fOutputBuffer,
fDriver->GetOutputBuffer(i),
fDriver->fEngineControl->fBufferSize,
i,
fDriver->fPlaybackChannels * fDriver->fSampleSize,
fDriver->fBits); fDriver->fBits);
} }
} }
#ifdef JACK_MONITOR #ifdef JACK_MONITOR
gCycleTable.fTable[gCycleWriteCount].fBeforeWrite = GetMicroSeconds(); gCycleTable.fTable[gCycleWriteCount].fBeforeWrite = GetMicroSeconds();
#endif
#endif


ssize_t count = ::write(fDriver->fOutFD, fDriver->fOutputBuffer, fDriver->fOutputBufferSize); ssize_t count = ::write(fDriver->fOutFD, fDriver->fOutputBuffer, fDriver->fOutputBufferSize);


@@ -762,20 +763,20 @@ bool JackBoomerDriver::JackBoomerDriverOutput::Execute()
if (ei_out.play_underruns > 0) { if (ei_out.play_underruns > 0) {
jack_error("JackBoomerDriverOutput::Execute underruns"); jack_error("JackBoomerDriverOutput::Execute underruns");
jack_time_t cur_time = GetMicroSeconds(); jack_time_t cur_time = GetMicroSeconds();
fDriver->NotifyXRun(cur_time, float(cur_time - fDriver->fBeginDateUst)); // Better this value than nothing...
fDriver->NotifyXRun(cur_time, float(cur_time - fDriver->fBeginDateUst)); // Better this value than nothing...
} }


if (ei_out.play_errorcount > 0 && ei_out.play_lasterror != 0) { if (ei_out.play_errorcount > 0 && ei_out.play_lasterror != 0) {
jack_error("%d OSS play event(s), last=%05d:%d",ei_out.play_errorcount, ei_out.play_lasterror, ei_out.play_errorparm); jack_error("%d OSS play event(s), last=%05d:%d",ei_out.play_errorcount, ei_out.play_lasterror, ei_out.play_errorparm);
} }
} }
if (count < 0) { if (count < 0) {
jack_log("JackBoomerDriverOutput::Execute error = %s", strerror(errno)); jack_log("JackBoomerDriverOutput::Execute error = %s", strerror(errno));
} else if (count < (int)fDriver->fOutputBufferSize) { } else if (count < (int)fDriver->fOutputBufferSize) {
jack_error("JackBoomerDriverOutput::Execute error bytes written = %ld", count); jack_error("JackBoomerDriverOutput::Execute error bytes written = %ld", count);
} }
// Duplex : sync with read thread // Duplex : sync with read thread
if (fDriver->fInFD >= 0 && fDriver->fOutFD >= 0) { if (fDriver->fInFD >= 0 && fDriver->fOutFD >= 0) {
fDriver->SynchronizeWrite(); fDriver->SynchronizeWrite();
@@ -802,12 +803,11 @@ void JackBoomerDriver::SynchronizeWrite()


int JackBoomerDriver::SetBufferSize(jack_nframes_t buffer_size) int JackBoomerDriver::SetBufferSize(jack_nframes_t buffer_size)
{ {
CloseAux();
JackAudioDriver::SetBufferSize(buffer_size); // never fails
CloseAux();
JackAudioDriver::SetBufferSize(buffer_size); // Generic change, never fails
return OpenAux(); return OpenAux();
} }



} // end of namespace } // end of namespace


#ifdef __cplusplus #ifdef __cplusplus
@@ -823,7 +823,7 @@ SERVER_EXPORT jack_driver_desc_t* driver_get_descriptor()


strcpy(desc->name, "boomer"); // size MUST be less then JACK_DRIVER_NAME_MAX + 1 strcpy(desc->name, "boomer"); // size MUST be less then JACK_DRIVER_NAME_MAX + 1
strcpy(desc->desc, "Boomer/OSS API based audio backend"); // size MUST be less then JACK_DRIVER_PARAM_DESC + 1 strcpy(desc->desc, "Boomer/OSS API based audio backend"); // size MUST be less then JACK_DRIVER_PARAM_DESC + 1
desc->nparams = OSS_DRIVER_N_PARAMS; desc->nparams = OSS_DRIVER_N_PARAMS;
desc->params = (jack_driver_param_desc_t*)calloc(desc->nparams, sizeof(jack_driver_param_desc_t)); desc->params = (jack_driver_param_desc_t*)calloc(desc->nparams, sizeof(jack_driver_param_desc_t));


@@ -866,7 +866,7 @@ SERVER_EXPORT jack_driver_desc_t* driver_get_descriptor()
desc->params[i].value.ui = OSS_DRIVER_DEF_INS; desc->params[i].value.ui = OSS_DRIVER_DEF_INS;
strcpy(desc->params[i].short_desc, "Capture channels"); strcpy(desc->params[i].short_desc, "Capture channels");
strcpy(desc->params[i].long_desc, desc->params[i].short_desc); strcpy(desc->params[i].long_desc, desc->params[i].short_desc);
i++; i++;
strcpy(desc->params[i].name, "outchannels"); strcpy(desc->params[i].name, "outchannels");
desc->params[i].character = 'o'; desc->params[i].character = 'o';
@@ -874,7 +874,7 @@ SERVER_EXPORT jack_driver_desc_t* driver_get_descriptor()
desc->params[i].value.ui = OSS_DRIVER_DEF_OUTS; desc->params[i].value.ui = OSS_DRIVER_DEF_OUTS;
strcpy(desc->params[i].short_desc, "Playback channels"); strcpy(desc->params[i].short_desc, "Playback channels");
strcpy(desc->params[i].long_desc, desc->params[i].short_desc); strcpy(desc->params[i].long_desc, desc->params[i].short_desc);
i++; i++;
strcpy(desc->params[i].name, "excl"); strcpy(desc->params[i].name, "excl");
desc->params[i].character = 'e'; desc->params[i].character = 'e';
@@ -890,7 +890,7 @@ SERVER_EXPORT jack_driver_desc_t* driver_get_descriptor()
strcpy(desc->params[i].value.str, OSS_DRIVER_DEF_DEV); strcpy(desc->params[i].value.str, OSS_DRIVER_DEF_DEV);
strcpy(desc->params[i].short_desc, "Input device"); strcpy(desc->params[i].short_desc, "Input device");
strcpy(desc->params[i].long_desc, desc->params[i].short_desc); strcpy(desc->params[i].long_desc, desc->params[i].short_desc);
i++; i++;
strcpy(desc->params[i].name, "playback"); strcpy(desc->params[i].name, "playback");
desc->params[i].character = 'P'; desc->params[i].character = 'P';
@@ -906,7 +906,7 @@ SERVER_EXPORT jack_driver_desc_t* driver_get_descriptor()
strcpy(desc->params[i].value.str, OSS_DRIVER_DEF_DEV); strcpy(desc->params[i].value.str, OSS_DRIVER_DEF_DEV);
strcpy(desc->params[i].short_desc, "OSS device name"); strcpy(desc->params[i].short_desc, "OSS device name");
strcpy(desc->params[i].long_desc, desc->params[i].short_desc); strcpy(desc->params[i].long_desc, desc->params[i].short_desc);
i++; i++;
strcpy(desc->params[i].name, "input-latency"); strcpy(desc->params[i].name, "input-latency");
desc->params[i].character = 'I'; desc->params[i].character = 'I';
@@ -953,13 +953,13 @@ EXPORT Jack::JackDriverClientInterface* driver_initialize(Jack::JackLockedEngine
const jack_driver_param_t *param; const jack_driver_param_t *param;
jack_nframes_t systemic_input_latency = 0; jack_nframes_t systemic_input_latency = 0;
jack_nframes_t systemic_output_latency = 0; jack_nframes_t systemic_output_latency = 0;
for (node = params; node; node = jack_slist_next(node)) { for (node = params; node; node = jack_slist_next(node)) {
param = (const jack_driver_param_t *)node->data; param = (const jack_driver_param_t *)node->data;


switch (param->character) { switch (param->character) {
case 'r': case 'r':
srate = param->value.ui; srate = param->value.ui;
break; break;
@@ -983,7 +983,7 @@ EXPORT Jack::JackDriverClientInterface* driver_initialize(Jack::JackLockedEngine
case 'o': case 'o':
chan_out = (int)param->value.ui; chan_out = (int)param->value.ui;
break; break;
case 'C': case 'C':
capture = true; capture = true;
if (strcmp(param->value.str, "none") != 0) { if (strcmp(param->value.str, "none") != 0) {
@@ -1002,11 +1002,11 @@ EXPORT Jack::JackDriverClientInterface* driver_initialize(Jack::JackLockedEngine
playback_pcm_name = param->value.str; playback_pcm_name = param->value.str;
capture_pcm_name = param->value.str; capture_pcm_name = param->value.str;
break; break;
case 'e': case 'e':
excl = true; excl = true;
break; break;
case 'I': case 'I':
systemic_input_latency = param->value.ui; systemic_input_latency = param->value.ui;
break; break;
@@ -1028,9 +1028,9 @@ EXPORT Jack::JackDriverClientInterface* driver_initialize(Jack::JackLockedEngine
} }


Jack::JackBoomerDriver* boomer_driver = new Jack::JackBoomerDriver("system", "boomer", engine, table); Jack::JackBoomerDriver* boomer_driver = new Jack::JackBoomerDriver("system", "boomer", engine, table);
// Special open for Boomer driver... // Special open for Boomer driver...
if (boomer_driver->Open(frames_per_interrupt, nperiods, srate, capture, playback, chan_in, chan_out, excl,
if (boomer_driver->Open(frames_per_interrupt, nperiods, srate, capture, playback, chan_in, chan_out, excl,
monitor, capture_pcm_name, playback_pcm_name, systemic_input_latency, systemic_output_latency, bits, syncio) == 0) { monitor, capture_pcm_name, playback_pcm_name, systemic_input_latency, systemic_output_latency, bits, syncio) == 0) {
return boomer_driver; return boomer_driver;
} else { } else {


+ 87
- 87
solaris/oss/JackOSSDriver.cpp View File

@@ -107,12 +107,12 @@ static inline void CopyAndConvertOut(void *dst, jack_sample_t *src, size_t nfram
s32dst += channel; s32dst += channel;
sample_move_d24_sS((char*)s32dst, src, nframes, chcount<<2, NULL); // No dithering for now... sample_move_d24_sS((char*)s32dst, src, nframes, chcount<<2, NULL); // No dithering for now...
break; break;
}
}
case 32: { case 32: {
signed int *s32dst = (signed int*)dst; signed int *s32dst = (signed int*)dst;
s32dst += channel; s32dst += channel;
sample_move_d32u24_sS((char*)s32dst, src, nframes, chcount<<2, NULL); sample_move_d32u24_sS((char*)s32dst, src, nframes, chcount<<2, NULL);
break;
break;
} }
} }
} }
@@ -126,7 +126,7 @@ void JackOSSDriver::SetSampleFormat()
fSampleSize = sizeof(int); fSampleSize = sizeof(int);
break; break;
case 32: /* native-endian 32-bit integer */ case 32: /* native-endian 32-bit integer */
fSampleFormat = AFMT_S32_NE;
fSampleFormat = AFMT_S32_NE;
fSampleSize = sizeof(int); fSampleSize = sizeof(int);
break; break;
case 16: /* native-endian 16-bit integer */ case 16: /* native-endian 16-bit integer */
@@ -143,13 +143,13 @@ void JackOSSDriver::DisplayDeviceInfo()
oss_audioinfo ai_in, ai_out; oss_audioinfo ai_in, ai_out;
memset(&info, 0, sizeof(audio_buf_info)); memset(&info, 0, sizeof(audio_buf_info));
int cap = 0; int cap = 0;
// Duplex cards : http://manuals.opensound.com/developer/full_duplex.html // Duplex cards : http://manuals.opensound.com/developer/full_duplex.html
jack_info("Audio Interface Description :"); jack_info("Audio Interface Description :");
jack_info("Sampling Frequency : %d, Sample Format : %d, Mode : %d", fEngineControl->fSampleRate, fSampleFormat, fRWMode); jack_info("Sampling Frequency : %d, Sample Format : %d, Mode : %d", fEngineControl->fSampleRate, fSampleFormat, fRWMode);
if (fRWMode & kWrite) { if (fRWMode & kWrite) {
oss_sysinfo si; oss_sysinfo si;
if (ioctl(fOutFD, OSS_SYSINFO, &si) == -1) { if (ioctl(fOutFD, OSS_SYSINFO, &si) == -1) {
jack_error("JackOSSDriver::DisplayDeviceInfo OSS_SYSINFO failed : %s@%i, errno = %d", __FILE__, __LINE__, errno); jack_error("JackOSSDriver::DisplayDeviceInfo OSS_SYSINFO failed : %s@%i, errno = %d", __FILE__, __LINE__, errno);
@@ -161,17 +161,17 @@ void JackOSSDriver::DisplayDeviceInfo()
jack_info("OSS numaudioengines %d", si.numaudioengines); jack_info("OSS numaudioengines %d", si.numaudioengines);
jack_info("OSS numcards %d", si.numcards); jack_info("OSS numcards %d", si.numcards);
} }
jack_info("Output capabilities - %d channels : ", fPlaybackChannels); jack_info("Output capabilities - %d channels : ", fPlaybackChannels);
jack_info("Output block size = %d", fOutputBufferSize); jack_info("Output block size = %d", fOutputBufferSize);
if (ioctl(fOutFD, SNDCTL_DSP_GETOSPACE, &info) == -1) { if (ioctl(fOutFD, SNDCTL_DSP_GETOSPACE, &info) == -1) {
jack_error("JackOSSDriver::DisplayDeviceInfo SNDCTL_DSP_GETOSPACE failed : %s@%i, errno = %d", __FILE__, __LINE__, errno); jack_error("JackOSSDriver::DisplayDeviceInfo SNDCTL_DSP_GETOSPACE failed : %s@%i, errno = %d", __FILE__, __LINE__, errno);
} else { } else {
jack_info("output space info: fragments = %d, fragstotal = %d, fragsize = %d, bytes = %d",
jack_info("output space info: fragments = %d, fragstotal = %d, fragsize = %d, bytes = %d",
info.fragments, info.fragstotal, info.fragsize, info.bytes); info.fragments, info.fragstotal, info.fragsize, info.bytes);
} }
if (ioctl(fOutFD, SNDCTL_DSP_GETCAPS, &cap) == -1) { if (ioctl(fOutFD, SNDCTL_DSP_GETCAPS, &cap) == -1) {
jack_error("JackOSSDriver::DisplayDeviceInfo SNDCTL_DSP_GETCAPS failed : %s@%i, errno = %d", __FILE__, __LINE__, errno); jack_error("JackOSSDriver::DisplayDeviceInfo SNDCTL_DSP_GETCAPS failed : %s@%i, errno = %d", __FILE__, __LINE__, errno);
} else { } else {
@@ -184,10 +184,10 @@ void JackOSSDriver::DisplayDeviceInfo()
if (cap & DSP_CAP_MULTI) jack_info(" DSP_CAP_MULTI"); if (cap & DSP_CAP_MULTI) jack_info(" DSP_CAP_MULTI");
if (cap & DSP_CAP_BIND) jack_info(" DSP_CAP_BIND"); if (cap & DSP_CAP_BIND) jack_info(" DSP_CAP_BIND");
} }
}
}
if (fRWMode & kRead) { if (fRWMode & kRead) {
oss_sysinfo si; oss_sysinfo si;
if (ioctl(fInFD, OSS_SYSINFO, &si) == -1) { if (ioctl(fInFD, OSS_SYSINFO, &si) == -1) {
jack_error("JackOSSDriver::DisplayDeviceInfo OSS_SYSINFO failed : %s@%i, errno = %d", __FILE__, __LINE__, errno); jack_error("JackOSSDriver::DisplayDeviceInfo OSS_SYSINFO failed : %s@%i, errno = %d", __FILE__, __LINE__, errno);
@@ -199,14 +199,14 @@ void JackOSSDriver::DisplayDeviceInfo()
jack_info("OSS numaudioengines %d", si.numaudioengines); jack_info("OSS numaudioengines %d", si.numaudioengines);
jack_info("OSS numcards %d", si.numcards); jack_info("OSS numcards %d", si.numcards);
} }
jack_info("Input capabilities - %d channels : ", fCaptureChannels); jack_info("Input capabilities - %d channels : ", fCaptureChannels);
jack_info("Input block size = %d", fInputBufferSize); jack_info("Input block size = %d", fInputBufferSize);
if (ioctl(fInFD, SNDCTL_DSP_GETISPACE, &info) == -1) {
if (ioctl(fInFD, SNDCTL_DSP_GETISPACE, &info) == -1) {
jack_error("JackOSSDriver::DisplayDeviceInfo SNDCTL_DSP_GETOSPACE failed : %s@%i, errno = %d", __FILE__, __LINE__, errno); jack_error("JackOSSDriver::DisplayDeviceInfo SNDCTL_DSP_GETOSPACE failed : %s@%i, errno = %d", __FILE__, __LINE__, errno);
} else { } else {
jack_info("input space info: fragments = %d, fragstotal = %d, fragsize = %d, bytes = %d",
jack_info("input space info: fragments = %d, fragstotal = %d, fragsize = %d, bytes = %d",
info.fragments, info.fragstotal, info.fragsize, info.bytes); info.fragments, info.fragstotal, info.fragsize, info.bytes);
} }


@@ -223,7 +223,7 @@ void JackOSSDriver::DisplayDeviceInfo()
if (cap & DSP_CAP_BIND) jack_info(" DSP_CAP_BIND"); if (cap & DSP_CAP_BIND) jack_info(" DSP_CAP_BIND");
} }
} }
if (ai_in.rate_source != ai_out.rate_source) { if (ai_in.rate_source != ai_out.rate_source) {
jack_info("Warning : input and output are not necessarily driven by the same clock!"); jack_info("Warning : input and output are not necessarily driven by the same clock!");
} }
@@ -238,7 +238,7 @@ int JackOSSDriver::OpenInput()
jack_nframes_t cur_sample_rate; jack_nframes_t cur_sample_rate;


if (fCaptureChannels == 0) fCaptureChannels = 2; if (fCaptureChannels == 0) fCaptureChannels = 2;
if ((fInFD = open(fCaptureDriverName, O_RDONLY | ((fExcl) ? O_EXCL : 0))) < 0) { if ((fInFD = open(fCaptureDriverName, O_RDONLY | ((fExcl) ? O_EXCL : 0))) < 0) {
jack_error("JackOSSDriver::OpenInput failed to open device : %s@%i, errno = %d", __FILE__, __LINE__, errno); jack_error("JackOSSDriver::OpenInput failed to open device : %s@%i, errno = %d", __FILE__, __LINE__, errno);
return -1; return -1;
@@ -253,7 +253,7 @@ int JackOSSDriver::OpenInput()
} }
} }


gFragFormat = (2 << 16) + int2pow2(fEngineControl->fBufferSize * fSampleSize * fCaptureChannels);
gFragFormat = (2 << 16) + int2pow2(fEngineControl->fBufferSize * fSampleSize * fCaptureChannels);
if (ioctl(fInFD, SNDCTL_DSP_SETFRAGMENT, &gFragFormat) == -1) { if (ioctl(fInFD, SNDCTL_DSP_SETFRAGMENT, &gFragFormat) == -1) {
jack_error("JackOSSDriver::OpenInput failed to set fragments : %s@%i, errno = %d", __FILE__, __LINE__, errno); jack_error("JackOSSDriver::OpenInput failed to set fragments : %s@%i, errno = %d", __FILE__, __LINE__, errno);
goto error; goto error;
@@ -267,7 +267,7 @@ int JackOSSDriver::OpenInput()
if (cur_sample_format != fSampleFormat) { if (cur_sample_format != fSampleFormat) {
jack_info("JackOSSDriver::OpenInput driver forced the sample format %ld", fSampleFormat); jack_info("JackOSSDriver::OpenInput driver forced the sample format %ld", fSampleFormat);
} }
cur_capture_channels = fCaptureChannels; cur_capture_channels = fCaptureChannels;
if (ioctl(fInFD, SNDCTL_DSP_CHANNELS, &fCaptureChannels) == -1) { if (ioctl(fInFD, SNDCTL_DSP_CHANNELS, &fCaptureChannels) == -1) {
jack_error("JackOSSDriver::OpenInput failed to set channels : %s@%i, errno = %d", __FILE__, __LINE__, errno); jack_error("JackOSSDriver::OpenInput failed to set channels : %s@%i, errno = %d", __FILE__, __LINE__, errno);
@@ -276,7 +276,7 @@ int JackOSSDriver::OpenInput()
if (cur_capture_channels != fCaptureChannels) { if (cur_capture_channels != fCaptureChannels) {
jack_info("JackOSSDriver::OpenInput driver forced the number of capture channels %ld", fCaptureChannels); jack_info("JackOSSDriver::OpenInput driver forced the number of capture channels %ld", fCaptureChannels);
} }
cur_sample_rate = fEngineControl->fSampleRate; cur_sample_rate = fEngineControl->fSampleRate;
if (ioctl(fInFD, SNDCTL_DSP_SPEED, &fEngineControl->fSampleRate) == -1) { if (ioctl(fInFD, SNDCTL_DSP_SPEED, &fEngineControl->fSampleRate) == -1) {
jack_error("JackOSSDriver::OpenInput failed to set sample rate : %s@%i, errno = %d", __FILE__, __LINE__, errno); jack_error("JackOSSDriver::OpenInput failed to set sample rate : %s@%i, errno = %d", __FILE__, __LINE__, errno);
@@ -291,7 +291,7 @@ int JackOSSDriver::OpenInput()
jack_error("JackOSSDriver::OpenInput failed to get fragments : %s@%i, errno = %d", __FILE__, __LINE__, errno); jack_error("JackOSSDriver::OpenInput failed to get fragments : %s@%i, errno = %d", __FILE__, __LINE__, errno);
goto error; goto error;
} }
if (fInputBufferSize != fEngineControl->fBufferSize * fSampleSize * fCaptureChannels) { if (fInputBufferSize != fEngineControl->fBufferSize * fSampleSize * fCaptureChannels) {
if (fIgnoreHW) { if (fIgnoreHW) {
int new_buffer_size = fInputBufferSize / (fSampleSize * fCaptureChannels); int new_buffer_size = fInputBufferSize / (fSampleSize * fCaptureChannels);
@@ -306,7 +306,7 @@ int JackOSSDriver::OpenInput()
fInputBuffer = (void*)calloc(fInputBufferSize, 1); fInputBuffer = (void*)calloc(fInputBufferSize, 1);
assert(fInputBuffer); assert(fInputBuffer);
return 0; return 0;
error: error:
::close(fInFD); ::close(fInFD);
return -1; return -1;
@@ -321,27 +321,27 @@ int JackOSSDriver::OpenOutput()
jack_nframes_t cur_sample_rate; jack_nframes_t cur_sample_rate;


if (fPlaybackChannels == 0) fPlaybackChannels = 2; if (fPlaybackChannels == 0) fPlaybackChannels = 2;
if ((fOutFD = open(fPlaybackDriverName, O_WRONLY | ((fExcl) ? O_EXCL : 0))) < 0) { if ((fOutFD = open(fPlaybackDriverName, O_WRONLY | ((fExcl) ? O_EXCL : 0))) < 0) {
jack_error("JackOSSDriver::OpenOutput failed to open device : %s@%i, errno = %d", __FILE__, __LINE__, errno); jack_error("JackOSSDriver::OpenOutput failed to open device : %s@%i, errno = %d", __FILE__, __LINE__, errno);
return -1; return -1;
} }


jack_log("JackOSSDriver::OpenOutput output fOutFD = %d", fOutFD); jack_log("JackOSSDriver::OpenOutput output fOutFD = %d", fOutFD);
if (fExcl) { if (fExcl) {
if (ioctl(fOutFD, SNDCTL_DSP_COOKEDMODE, &flags) == -1) { if (ioctl(fOutFD, SNDCTL_DSP_COOKEDMODE, &flags) == -1) {
jack_error("JackOSSDriver::OpenOutput failed to set cooked mode : %s@%i, errno = %d", __FILE__, __LINE__, errno); jack_error("JackOSSDriver::OpenOutput failed to set cooked mode : %s@%i, errno = %d", __FILE__, __LINE__, errno);
goto error; goto error;
}
}
}
}


gFragFormat = (2 << 16) + int2pow2(fEngineControl->fBufferSize * fSampleSize * fPlaybackChannels);
gFragFormat = (2 << 16) + int2pow2(fEngineControl->fBufferSize * fSampleSize * fPlaybackChannels);
if (ioctl(fOutFD, SNDCTL_DSP_SETFRAGMENT, &gFragFormat) == -1) { if (ioctl(fOutFD, SNDCTL_DSP_SETFRAGMENT, &gFragFormat) == -1) {
jack_error("JackOSSDriver::OpenOutput failed to set fragments : %s@%i, errno = %d", __FILE__, __LINE__, errno); jack_error("JackOSSDriver::OpenOutput failed to set fragments : %s@%i, errno = %d", __FILE__, __LINE__, errno);
goto error; goto error;
} }
cur_sample_format = fSampleFormat; cur_sample_format = fSampleFormat;
if (ioctl(fOutFD, SNDCTL_DSP_SETFMT, &fSampleFormat) == -1) { if (ioctl(fOutFD, SNDCTL_DSP_SETFMT, &fSampleFormat) == -1) {
jack_error("JackOSSDriver::OpenOutput failed to set format : %s@%i, errno = %d", __FILE__, __LINE__, errno); jack_error("JackOSSDriver::OpenOutput failed to set format : %s@%i, errno = %d", __FILE__, __LINE__, errno);
@@ -350,7 +350,7 @@ int JackOSSDriver::OpenOutput()
if (cur_sample_format != fSampleFormat) { if (cur_sample_format != fSampleFormat) {
jack_info("JackOSSDriver::OpenOutput driver forced the sample format %ld", fSampleFormat); jack_info("JackOSSDriver::OpenOutput driver forced the sample format %ld", fSampleFormat);
} }
cur_playback_channels = fPlaybackChannels; cur_playback_channels = fPlaybackChannels;
if (ioctl(fOutFD, SNDCTL_DSP_CHANNELS, &fPlaybackChannels) == -1) { if (ioctl(fOutFD, SNDCTL_DSP_CHANNELS, &fPlaybackChannels) == -1) {
jack_error("JackOSSDriver::OpenOutput failed to set channels : %s@%i, errno = %d", __FILE__, __LINE__, errno); jack_error("JackOSSDriver::OpenOutput failed to set channels : %s@%i, errno = %d", __FILE__, __LINE__, errno);
@@ -374,7 +374,7 @@ int JackOSSDriver::OpenOutput()
jack_error("JackOSSDriver::OpenOutput failed to get fragments : %s@%i, errno = %d", __FILE__, __LINE__, errno); jack_error("JackOSSDriver::OpenOutput failed to get fragments : %s@%i, errno = %d", __FILE__, __LINE__, errno);
goto error; goto error;
} }
if (fOutputBufferSize != fEngineControl->fBufferSize * fSampleSize * fPlaybackChannels) { if (fOutputBufferSize != fEngineControl->fBufferSize * fSampleSize * fPlaybackChannels) {
if (fIgnoreHW) { if (fIgnoreHW) {
int new_buffer_size = fOutputBufferSize / (fSampleSize * fPlaybackChannels); int new_buffer_size = fOutputBufferSize / (fSampleSize * fPlaybackChannels);
@@ -385,19 +385,19 @@ int JackOSSDriver::OpenOutput()
goto error; goto error;
} }
} }
fOutputBuffer = (void*)calloc(fOutputBufferSize, 1); fOutputBuffer = (void*)calloc(fOutputBufferSize, 1);
fFirstCycle = true; fFirstCycle = true;
assert(fOutputBuffer); assert(fOutputBuffer);
return 0; return 0;
error: error:
::close(fOutFD); ::close(fOutFD);
return -1; return -1;
} }


int JackOSSDriver::Open(jack_nframes_t nframes, int JackOSSDriver::Open(jack_nframes_t nframes,
int user_nperiods,
int user_nperiods,
jack_nframes_t samplerate, jack_nframes_t samplerate,
bool capturing, bool capturing,
bool playing, bool playing,
@@ -413,7 +413,7 @@ int JackOSSDriver::Open(jack_nframes_t nframes,
bool ignorehwbuf) bool ignorehwbuf)
{ {
// Generic JackAudioDriver Open // Generic JackAudioDriver Open
if (JackAudioDriver::Open(nframes, samplerate, capturing, playing, inchannels, outchannels, monitor,
if (JackAudioDriver::Open(nframes, samplerate, capturing, playing, inchannels, outchannels, monitor,
capture_driver_uid, playback_driver_uid, capture_latency, playback_latency) != 0) { capture_driver_uid, playback_driver_uid, capture_latency, playback_latency) != 0) {
return -1; return -1;
} else { } else {
@@ -422,7 +422,7 @@ int JackOSSDriver::Open(jack_nframes_t nframes,
jack_error("Cannot run in asynchronous mode, use the -S parameter for jackd"); jack_error("Cannot run in asynchronous mode, use the -S parameter for jackd");
return -1; return -1;
} }
fRWMode |= ((capturing) ? kRead : 0); fRWMode |= ((capturing) ? kRead : 0);
fRWMode |= ((playing) ? kWrite : 0); fRWMode |= ((playing) ? kWrite : 0);
fBits = bits; fBits = bits;
@@ -434,7 +434,7 @@ int JackOSSDriver::Open(jack_nframes_t nframes,
// Force memory page in // Force memory page in
memset(&gCycleTable, 0, sizeof(gCycleTable)); memset(&gCycleTable, 0, sizeof(gCycleTable));
#endif #endif
if (OpenAux() < 0) { if (OpenAux() < 0) {
Close(); Close();
return -1; return -1;
@@ -448,14 +448,14 @@ int JackOSSDriver::Close()
{ {
#ifdef JACK_MONITOR #ifdef JACK_MONITOR
FILE* file = fopen("OSSProfiling.log", "w"); FILE* file = fopen("OSSProfiling.log", "w");
if (file) { if (file) {
jack_info("Writing OSS driver timing data...."); jack_info("Writing OSS driver timing data....");
for (int i = 1; i < gCycleCount; i++) { for (int i = 1; i < gCycleCount; i++) {
int d1 = gCycleTable.fTable[i].fAfterRead - gCycleTable.fTable[i].fBeforeRead; int d1 = gCycleTable.fTable[i].fAfterRead - gCycleTable.fTable[i].fBeforeRead;
int d2 = gCycleTable.fTable[i].fAfterReadConvert - gCycleTable.fTable[i].fAfterRead; int d2 = gCycleTable.fTable[i].fAfterReadConvert - gCycleTable.fTable[i].fAfterRead;
int d3 = gCycleTable.fTable[i].fAfterWrite - gCycleTable.fTable[i].fBeforeWrite; int d3 = gCycleTable.fTable[i].fAfterWrite - gCycleTable.fTable[i].fBeforeWrite;
int d4 = gCycleTable.fTable[i].fBeforeWrite - gCycleTable.fTable[i].fBeforeWriteConvert;
int d4 = gCycleTable.fTable[i].fBeforeWrite - gCycleTable.fTable[i].fBeforeWriteConvert;
fprintf(file, "%d \t %d \t %d \t %d \t \n", d1, d2, d3, d4); fprintf(file, "%d \t %d \t %d \t %d \t \n", d1, d2, d3, d4);
} }
fclose(file); fclose(file);
@@ -468,7 +468,7 @@ int JackOSSDriver::Close()
if (file == NULL) { if (file == NULL) {
jack_error("JackOSSDriver::Close cannot open TimingOSS.plot file"); jack_error("JackOSSDriver::Close cannot open TimingOSS.plot file");
} else { } else {
fprintf(file, "set grid\n"); fprintf(file, "set grid\n");
fprintf(file, "set title \"OSS audio driver timing\"\n"); fprintf(file, "set title \"OSS audio driver timing\"\n");
fprintf(file, "set xlabel \"audio cycles\"\n"); fprintf(file, "set xlabel \"audio cycles\"\n");
@@ -477,10 +477,10 @@ int JackOSSDriver::Close()
\"OSSProfiling.log\" using 2 title \"Driver read convert duration\" with lines, \ \"OSSProfiling.log\" using 2 title \"Driver read convert duration\" with lines, \
\"OSSProfiling.log\" using 3 title \"Driver write wait\" with lines, \ \"OSSProfiling.log\" using 3 title \"Driver write wait\" with lines, \
\"OSSProfiling.log\" using 4 title \"Driver write convert duration\" with lines\n"); \"OSSProfiling.log\" using 4 title \"Driver write convert duration\" with lines\n");
fprintf(file, "set output 'TimingOSS.pdf\n"); fprintf(file, "set output 'TimingOSS.pdf\n");
fprintf(file, "set terminal pdf\n"); fprintf(file, "set terminal pdf\n");
fprintf(file, "set grid\n"); fprintf(file, "set grid\n");
fprintf(file, "set title \"OSS audio driver timing\"\n"); fprintf(file, "set title \"OSS audio driver timing\"\n");
fprintf(file, "set xlabel \"audio cycles\"\n"); fprintf(file, "set xlabel \"audio cycles\"\n");
@@ -489,12 +489,12 @@ int JackOSSDriver::Close()
\"OSSProfiling.log\" using 2 title \"Driver read convert duration\" with lines, \ \"OSSProfiling.log\" using 2 title \"Driver read convert duration\" with lines, \
\"OSSProfiling.log\" using 3 title \"Driver write wait\" with lines, \ \"OSSProfiling.log\" using 3 title \"Driver write wait\" with lines, \
\"OSSProfiling.log\" using 4 title \"Driver write convert duration\" with lines\n"); \"OSSProfiling.log\" using 4 title \"Driver write convert duration\" with lines\n");
fclose(file); fclose(file);
} }
#endif #endif
int res = JackAudioDriver::Close(); int res = JackAudioDriver::Close();
CloseAux();
CloseAux();
return res; return res;
} }


@@ -506,8 +506,8 @@ int JackOSSDriver::OpenAux()
if ((fRWMode & kRead) && (OpenInput() < 0)) { if ((fRWMode & kRead) && (OpenInput() < 0)) {
return -1; return -1;
} }
if ((fRWMode & kWrite) && (OpenOutput() < 0)) {
if ((fRWMode & kWrite) && (OpenOutput() < 0)) {
return -1; return -1;
} }


@@ -522,7 +522,7 @@ int JackOSSDriver::OpenAux()
} }
*/ */


DisplayDeviceInfo();
DisplayDeviceInfo();
return 0; return 0;
} }


@@ -532,16 +532,16 @@ void JackOSSDriver::CloseAux()
close(fInFD); close(fInFD);
fInFD = -1; fInFD = -1;
} }
if (fRWMode & kWrite && fOutFD > 0) { if (fRWMode & kWrite && fOutFD > 0) {
close(fOutFD); close(fOutFD);
fOutFD = -1; fOutFD = -1;
} }
if (fInputBuffer) if (fInputBuffer)
free(fInputBuffer); free(fInputBuffer);
fInputBuffer = NULL; fInputBuffer = NULL;
if (fOutputBuffer) if (fOutputBuffer)
free(fOutputBuffer); free(fOutputBuffer);
fOutputBuffer = NULL; fOutputBuffer = NULL;
@@ -554,7 +554,7 @@ int JackOSSDriver::Read()
JackDriver::CycleTakeBeginTime(); JackDriver::CycleTakeBeginTime();
return 0; return 0;
} }
ssize_t count; ssize_t count;


#ifdef JACK_MONITOR #ifdef JACK_MONITOR
@@ -562,28 +562,28 @@ int JackOSSDriver::Read()
#endif #endif


audio_errinfo ei_in; audio_errinfo ei_in;
count = ::read(fInFD, fInputBuffer, fInputBufferSize);
count = ::read(fInFD, fInputBuffer, fInputBufferSize);
#ifdef JACK_MONITOR #ifdef JACK_MONITOR
if (count > 0 && count != (int)fInputBufferSize) if (count > 0 && count != (int)fInputBufferSize)
jack_log("JackOSSDriver::Read count = %ld", count / (fSampleSize * fCaptureChannels)); jack_log("JackOSSDriver::Read count = %ld", count / (fSampleSize * fCaptureChannels));
gCycleTable.fTable[gCycleCount].fAfterRead = GetMicroSeconds(); gCycleTable.fTable[gCycleCount].fAfterRead = GetMicroSeconds();
#endif #endif
// XRun detection // XRun detection
if (ioctl(fInFD, SNDCTL_DSP_GETERROR, &ei_in) == 0) { if (ioctl(fInFD, SNDCTL_DSP_GETERROR, &ei_in) == 0) {


if (ei_in.rec_overruns > 0 ) { if (ei_in.rec_overruns > 0 ) {
jack_error("JackOSSDriver::Read overruns"); jack_error("JackOSSDriver::Read overruns");
jack_time_t cur_time = GetMicroSeconds(); jack_time_t cur_time = GetMicroSeconds();
NotifyXRun(cur_time, float(cur_time - fBeginDateUst)); // Better this value than nothing...
NotifyXRun(cur_time, float(cur_time - fBeginDateUst)); // Better this value than nothing...
} }


if (ei_in.rec_errorcount > 0 && ei_in.rec_lasterror != 0) { if (ei_in.rec_errorcount > 0 && ei_in.rec_lasterror != 0) {
jack_error("%d OSS rec event(s), last=%05d:%d", ei_in.rec_errorcount, ei_in.rec_lasterror, ei_in.rec_errorparm); jack_error("%d OSS rec event(s), last=%05d:%d", ei_in.rec_errorcount, ei_in.rec_lasterror, ei_in.rec_errorparm);
} }
}
}
if (count < 0) { if (count < 0) {
jack_log("JackOSSDriver::Read error = %s", strerror(errno)); jack_log("JackOSSDriver::Read error = %s", strerror(errno));
return -1; return -1;
@@ -603,7 +603,7 @@ int JackOSSDriver::Read()
#ifdef JACK_MONITOR #ifdef JACK_MONITOR
gCycleTable.fTable[gCycleCount].fAfterReadConvert = GetMicroSeconds(); gCycleTable.fTable[gCycleCount].fAfterReadConvert = GetMicroSeconds();
#endif #endif
return 0; return 0;
} }
} }
@@ -618,10 +618,10 @@ int JackOSSDriver::Write()


ssize_t count; ssize_t count;
audio_errinfo ei_out; audio_errinfo ei_out;
// Maybe necessary to write an empty output buffer first time : see http://manuals.opensound.com/developer/fulldup.c.html
// Maybe necessary to write an empty output buffer first time : see http://manuals.opensound.com/developer/fulldup.c.html
if (fFirstCycle) { if (fFirstCycle) {
fFirstCycle = false; fFirstCycle = false;
memset(fOutputBuffer, 0, fOutputBufferSize); memset(fOutputBuffer, 0, fOutputBufferSize);


@@ -633,17 +633,17 @@ int JackOSSDriver::Write()
return -1; return -1;
} }
} }
int delay; int delay;
if (ioctl(fOutFD, SNDCTL_DSP_GETODELAY, &delay) == -1) { if (ioctl(fOutFD, SNDCTL_DSP_GETODELAY, &delay) == -1) {
jack_error("JackOSSDriver::Write error get out delay : %s@%i, errno = %d", __FILE__, __LINE__, errno); jack_error("JackOSSDriver::Write error get out delay : %s@%i, errno = %d", __FILE__, __LINE__, errno);
return -1; return -1;
} }
delay /= fSampleSize * fPlaybackChannels; delay /= fSampleSize * fPlaybackChannels;
jack_info("JackOSSDriver::Write output latency frames = %ld", delay); jack_info("JackOSSDriver::Write output latency frames = %ld", delay);
} }
#ifdef JACK_MONITOR #ifdef JACK_MONITOR
gCycleTable.fTable[gCycleCount].fBeforeWriteConvert = GetMicroSeconds(); gCycleTable.fTable[gCycleCount].fBeforeWriteConvert = GetMicroSeconds();
#endif #endif
@@ -657,7 +657,7 @@ int JackOSSDriver::Write()


#ifdef JACK_MONITOR #ifdef JACK_MONITOR
gCycleTable.fTable[gCycleCount].fBeforeWrite = GetMicroSeconds(); gCycleTable.fTable[gCycleCount].fBeforeWrite = GetMicroSeconds();
#endif
#endif


// Keep end cycle time // Keep end cycle time
JackDriver::CycleTakeEndTime(); JackDriver::CycleTakeEndTime();
@@ -676,14 +676,14 @@ int JackOSSDriver::Write()
if (ei_out.play_underruns > 0) { if (ei_out.play_underruns > 0) {
jack_error("JackOSSDriver::Write underruns"); jack_error("JackOSSDriver::Write underruns");
jack_time_t cur_time = GetMicroSeconds(); jack_time_t cur_time = GetMicroSeconds();
NotifyXRun(cur_time, float(cur_time - fBeginDateUst)); // Better this value than nothing...
NotifyXRun(cur_time, float(cur_time - fBeginDateUst)); // Better this value than nothing...
} }


if (ei_out.play_errorcount > 0 && ei_out.play_lasterror != 0) { if (ei_out.play_errorcount > 0 && ei_out.play_lasterror != 0) {
jack_error("%d OSS play event(s), last=%05d:%d",ei_out.play_errorcount, ei_out.play_lasterror, ei_out.play_errorparm); jack_error("%d OSS play event(s), last=%05d:%d",ei_out.play_errorcount, ei_out.play_lasterror, ei_out.play_errorparm);
} }
} }
if (count < 0) { if (count < 0) {
jack_log("JackOSSDriver::Write error = %s", strerror(errno)); jack_log("JackOSSDriver::Write error = %s", strerror(errno));
return -1; return -1;
@@ -697,15 +697,15 @@ int JackOSSDriver::Write()


int JackOSSDriver::SetBufferSize(jack_nframes_t buffer_size) int JackOSSDriver::SetBufferSize(jack_nframes_t buffer_size)
{ {
CloseAux();
JackAudioDriver::SetBufferSize(buffer_size); // never fails
CloseAux();
JackAudioDriver::SetBufferSize(buffer_size); // Generic change, never fails
return OpenAux(); return OpenAux();
} }


int JackOSSDriver::ProcessSync() int JackOSSDriver::ProcessSync()
{ {
// Read input buffers for the current cycle // Read input buffers for the current cycle
if (Read() < 0) {
if (Read() < 0) {
jack_error("ProcessSync: read error, skip cycle"); jack_error("ProcessSync: read error, skip cycle");
return 0; // Non fatal error here, skip cycle, but continue processing... return 0; // Non fatal error here, skip cycle, but continue processing...
} }
@@ -715,13 +715,13 @@ int JackOSSDriver::ProcessSync()
} else { } else {
fGraphManager->ResumeRefNum(&fClientControl, fSynchroTable); fGraphManager->ResumeRefNum(&fClientControl, fSynchroTable);
} }
// Write output buffers for the current cycle // Write output buffers for the current cycle
if (Write() < 0) {
if (Write() < 0) {
jack_error("JackAudioDriver::ProcessSync: write error, skip cycle"); jack_error("JackAudioDriver::ProcessSync: write error, skip cycle");
return 0; // Non fatal error here, skip cycle, but continue processing... return 0; // Non fatal error here, skip cycle, but continue processing...
} }
return 0; return 0;
} }


@@ -740,7 +740,7 @@ SERVER_EXPORT jack_driver_desc_t* driver_get_descriptor()


strcpy(desc->name, "oss"); // size MUST be less then JACK_DRIVER_NAME_MAX + 1 strcpy(desc->name, "oss"); // size MUST be less then JACK_DRIVER_NAME_MAX + 1
strcpy(desc->desc, "OSS API based audio backend"); // size MUST be less then JACK_DRIVER_PARAM_DESC + 1 strcpy(desc->desc, "OSS API based audio backend"); // size MUST be less then JACK_DRIVER_PARAM_DESC + 1
desc->nparams = OSS_DRIVER_N_PARAMS; desc->nparams = OSS_DRIVER_N_PARAMS;
desc->params = (jack_driver_param_desc_t*)calloc(desc->nparams, sizeof(jack_driver_param_desc_t)); desc->params = (jack_driver_param_desc_t*)calloc(desc->nparams, sizeof(jack_driver_param_desc_t));


@@ -783,7 +783,7 @@ SERVER_EXPORT jack_driver_desc_t* driver_get_descriptor()
desc->params[i].value.ui = OSS_DRIVER_DEF_INS; desc->params[i].value.ui = OSS_DRIVER_DEF_INS;
strcpy(desc->params[i].short_desc, "Capture channels"); strcpy(desc->params[i].short_desc, "Capture channels");
strcpy(desc->params[i].long_desc, desc->params[i].short_desc); strcpy(desc->params[i].long_desc, desc->params[i].short_desc);
i++; i++;
strcpy(desc->params[i].name, "outchannels"); strcpy(desc->params[i].name, "outchannels");
desc->params[i].character = 'o'; desc->params[i].character = 'o';
@@ -807,7 +807,7 @@ SERVER_EXPORT jack_driver_desc_t* driver_get_descriptor()
strcpy(desc->params[i].value.str, OSS_DRIVER_DEF_DEV); strcpy(desc->params[i].value.str, OSS_DRIVER_DEF_DEV);
strcpy(desc->params[i].short_desc, "Input device"); strcpy(desc->params[i].short_desc, "Input device");
strcpy(desc->params[i].long_desc, desc->params[i].short_desc); strcpy(desc->params[i].long_desc, desc->params[i].short_desc);
i++; i++;
strcpy(desc->params[i].name, "playback"); strcpy(desc->params[i].name, "playback");
desc->params[i].character = 'P'; desc->params[i].character = 'P';
@@ -823,7 +823,7 @@ SERVER_EXPORT jack_driver_desc_t* driver_get_descriptor()
strcpy(desc->params[i].value.str, OSS_DRIVER_DEF_DEV); strcpy(desc->params[i].value.str, OSS_DRIVER_DEF_DEV);
strcpy(desc->params[i].short_desc, "OSS device name"); strcpy(desc->params[i].short_desc, "OSS device name");
strcpy(desc->params[i].long_desc, desc->params[i].short_desc); strcpy(desc->params[i].long_desc, desc->params[i].short_desc);
i++; i++;
strcpy(desc->params[i].name, "ignorehwbuf"); strcpy(desc->params[i].name, "ignorehwbuf");
desc->params[i].character = 'b'; desc->params[i].character = 'b';
@@ -831,7 +831,7 @@ SERVER_EXPORT jack_driver_desc_t* driver_get_descriptor()
desc->params[i].value.i = false; desc->params[i].value.i = false;
strcpy(desc->params[i].short_desc, "Ignore hardware period size"); strcpy(desc->params[i].short_desc, "Ignore hardware period size");
strcpy(desc->params[i].long_desc, desc->params[i].short_desc); strcpy(desc->params[i].long_desc, desc->params[i].short_desc);
i++; i++;
strcpy(desc->params[i].name, "input-latency"); strcpy(desc->params[i].name, "input-latency");
desc->params[i].character = 'I'; desc->params[i].character = 'I';
@@ -870,13 +870,13 @@ EXPORT Jack::JackDriverClientInterface* driver_initialize(Jack::JackLockedEngine
bool ignorehwbuf = false; bool ignorehwbuf = false;
jack_nframes_t systemic_input_latency = 0; jack_nframes_t systemic_input_latency = 0;
jack_nframes_t systemic_output_latency = 0; jack_nframes_t systemic_output_latency = 0;
for (node = params; node; node = jack_slist_next(node)) { for (node = params; node; node = jack_slist_next(node)) {
param = (const jack_driver_param_t *)node->data; param = (const jack_driver_param_t *)node->data;


switch (param->character) { switch (param->character) {
case 'r': case 'r':
srate = param->value.ui; srate = param->value.ui;
break; break;
@@ -900,7 +900,7 @@ EXPORT Jack::JackDriverClientInterface* driver_initialize(Jack::JackLockedEngine
case 'o': case 'o':
chan_out = (int)param->value.ui; chan_out = (int)param->value.ui;
break; break;
case 'C': case 'C':
capture = true; capture = true;
if (strcmp(param->value.str, "none") != 0) { if (strcmp(param->value.str, "none") != 0) {
@@ -919,7 +919,7 @@ EXPORT Jack::JackDriverClientInterface* driver_initialize(Jack::JackLockedEngine
playback_pcm_name = param->value.str; playback_pcm_name = param->value.str;
capture_pcm_name = param->value.str; capture_pcm_name = param->value.str;
break; break;
case 'b': case 'b':
ignorehwbuf = true; ignorehwbuf = true;
break; break;
@@ -927,7 +927,7 @@ EXPORT Jack::JackDriverClientInterface* driver_initialize(Jack::JackLockedEngine
case 'e': case 'e':
excl = true; excl = true;
break; break;
case 'I': case 'I':
systemic_input_latency = param->value.ui; systemic_input_latency = param->value.ui;
break; break;
@@ -946,9 +946,9 @@ EXPORT Jack::JackDriverClientInterface* driver_initialize(Jack::JackLockedEngine


Jack::JackOSSDriver* oss_driver = new Jack::JackOSSDriver("system", "oss", engine, table); Jack::JackOSSDriver* oss_driver = new Jack::JackOSSDriver("system", "oss", engine, table);
Jack::JackDriverClientInterface* threaded_driver = new Jack::JackThreadedDriver(oss_driver); Jack::JackDriverClientInterface* threaded_driver = new Jack::JackThreadedDriver(oss_driver);
// Special open for OSS driver... // Special open for OSS driver...
if (oss_driver->Open(frames_per_interrupt, nperiods, srate, capture, playback, chan_in, chan_out,
if (oss_driver->Open(frames_per_interrupt, nperiods, srate, capture, playback, chan_in, chan_out,
excl, monitor, capture_pcm_name, playback_pcm_name, systemic_input_latency, systemic_output_latency, bits, ignorehwbuf) == 0) { excl, monitor, capture_pcm_name, playback_pcm_name, systemic_input_latency, systemic_output_latency, bits, ignorehwbuf) == 0) {
return threaded_driver; return threaded_driver;
} else { } else {


+ 0
- 2
windows/portaudio/JackPortAudioDriver.cpp View File

@@ -225,8 +225,6 @@ error:
return -1; return -1;
} else { } else {
JackAudioDriver::SetBufferSize(buffer_size); // Generic change, never fails JackAudioDriver::SetBufferSize(buffer_size); // Generic change, never fails
// PortAudio specific
JackAudioDriver::UpdateLatencies();
return 0; return 0;
} }
} }


Loading…
Cancel
Save