jack1 codebase
You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

1334 lines
31KB

  1. /*
  2. OSS driver for Jack
  3. Copyright (C) 2003-2007 Jussi Laako <jussi@sonarnerd.net>
  4. This program is free software; you can redistribute it and/or modify
  5. it under the terms of the GNU General Public License as published by
  6. the Free Software Foundation; either version 2 of the License, or
  7. (at your option) any later version.
  8. This program is distributed in the hope that it will be useful,
  9. but WITHOUT ANY WARRANTY; without even the implied warranty of
  10. MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
  11. GNU General Public License for more details.
  12. You should have received a copy of the GNU General Public License
  13. along with this program; if not, write to the Free Software
  14. Foundation, Inc., 59 Temple Place, Suite 330, Boston,
  15. MA 02111-1307 USA
  16. */
  17. #include <config.h>
  18. #ifdef USE_BARRIER
  19. /*
  20. * POSIX conformance level should be globally defined somewhere, possibly
  21. * in config.h? Otherwise it's pre 1993/09 level, which leaves out significant
  22. * parts of threading and realtime stuff. Note: most of the parts are still
  23. * defined as optional by the standard, so OS conformance to this level
  24. * doesn't necessarily mean everything exists.
  25. */
  26. #define _XOPEN_SOURCE 600
  27. #endif
  28. #ifndef _REENTRANT
  29. #define _REENTRANT
  30. #endif
  31. #ifndef _THREAD_SAFE
  32. #define _THREAD_SAFE
  33. #endif
  34. #include <unistd.h>
  35. #include <pthread.h>
  36. #include <stdlib.h>
  37. #include <string.h>
  38. #include <stdio.h>
  39. #include <fcntl.h>
  40. #include <errno.h>
  41. #include <math.h>
  42. #include <float.h>
  43. #include <stdarg.h>
  44. #include <getopt.h>
  45. #include <semaphore.h>
  46. #include <sys/types.h>
  47. #include <sys/stat.h>
  48. #include <sys/ioctl.h>
  49. #include <sys/soundcard.h>
  50. #include <jack/types.h>
  51. #include <jack/thread.h>
  52. #include "internal.h"
  53. #include "engine.h"
  54. #include <sysdeps/time.h>
  55. #include "oss_driver.h"
  56. #ifndef SNDCTL_DSP_COOKEDMODE
  57. #ifdef _SIOWR
  58. #define SNDCTL_DSP_COOKEDMODE _SIOWR('P', 30, int)
  59. #else /* _SIOWR */
  60. #warning "Unable to define cooked mode!"
  61. #define OSS_NO_COOKED_MODE
  62. #endif /* _SIOWR */
  63. #endif /* SNDCTL_DSP_COOKEDMODE */
  64. #define OSS_DRIVER_N_PARAMS 11
  65. const static jack_driver_param_desc_t oss_params[OSS_DRIVER_N_PARAMS] = {
  66. { "rate",
  67. 'r',
  68. JackDriverParamUInt,
  69. { .ui = OSS_DRIVER_DEF_FS },
  70. NULL,
  71. "sample rate",
  72. "sample rate"
  73. },
  74. { "period",
  75. 'p',
  76. JackDriverParamUInt,
  77. { .ui = OSS_DRIVER_DEF_BLKSIZE },
  78. NULL,
  79. "period size",
  80. "period size"
  81. },
  82. { "nperiods",
  83. 'n',
  84. JackDriverParamUInt,
  85. { .ui = OSS_DRIVER_DEF_NPERIODS },
  86. NULL,
  87. "number of periods in buffer",
  88. "number of periods in buffer"
  89. },
  90. { "wordlength",
  91. 'w',
  92. JackDriverParamInt,
  93. { .i = OSS_DRIVER_DEF_BITS },
  94. NULL,
  95. "word length",
  96. "word length"
  97. },
  98. { "inchannels",
  99. 'i',
  100. JackDriverParamUInt,
  101. { .ui = OSS_DRIVER_DEF_INS },
  102. NULL,
  103. "capture channels",
  104. "capture channels"
  105. },
  106. { "outchannels",
  107. 'o',
  108. JackDriverParamUInt,
  109. { .ui = OSS_DRIVER_DEF_OUTS },
  110. NULL,
  111. "playback channels",
  112. "playback channels"
  113. },
  114. { "capture",
  115. 'C',
  116. JackDriverParamString,
  117. { .str = OSS_DRIVER_DEF_DEV },
  118. NULL,
  119. "input device",
  120. "input device"
  121. },
  122. { "playback",
  123. 'P',
  124. JackDriverParamString,
  125. { .str = OSS_DRIVER_DEF_DEV },
  126. NULL,
  127. "output device",
  128. "output device"
  129. },
  130. { "ignorehwbuf",
  131. 'b',
  132. JackDriverParamBool,
  133. { },
  134. NULL,
  135. "ignore hardware period size",
  136. "ignore hardware period size"
  137. },
  138. { "input latency",
  139. 'I',
  140. JackDriverParamUInt,
  141. { .ui = 0 },
  142. NULL,
  143. "system input latency",
  144. "system input latency"
  145. },
  146. { "output latency",
  147. 'O',
  148. JackDriverParamUInt,
  149. { .ui = 0 },
  150. NULL,
  151. "system output latency",
  152. "system output latency"
  153. }
  154. };
  155. /* internal functions */
  156. static void set_period_size (oss_driver_t *driver,
  157. jack_nframes_t new_period_size)
  158. {
  159. driver->period_size = new_period_size;
  160. driver->period_usecs =
  161. ((double) driver->period_size /
  162. (double) driver->sample_rate) * 1e6;
  163. driver->last_wait_ust = 0;
  164. driver->last_periodtime = driver->engine->get_microseconds();
  165. driver->next_periodtime = 0;
  166. driver->iodelay = 0.0F;
  167. }
  168. static inline void update_times (oss_driver_t *driver)
  169. {
  170. driver->last_periodtime = driver->engine->get_microseconds();
  171. if (driver->next_periodtime > 0)
  172. {
  173. driver->iodelay = (float)
  174. ((long double) driver->last_periodtime -
  175. (long double) driver->next_periodtime);
  176. }
  177. else driver->iodelay = 0.0F;
  178. driver->next_periodtime =
  179. driver->last_periodtime +
  180. driver->period_usecs;
  181. }
  182. static inline void driver_cycle (oss_driver_t *driver)
  183. {
  184. update_times(driver);
  185. driver->engine->transport_cycle_start(driver->engine,
  186. driver->last_periodtime);
  187. driver->last_wait_ust = driver->last_periodtime;
  188. driver->engine->run_cycle(driver->engine,
  189. driver->period_size, driver->iodelay);
  190. }
  191. static void copy_and_convert_in (jack_sample_t *dst, void *src,
  192. size_t nframes, int channel, int chcount, int bits)
  193. {
  194. int srcidx;
  195. int dstidx;
  196. signed short *s16src = (signed short *) src;
  197. signed int *s32src = (signed int *) src;
  198. double *f64src = (double *) src;
  199. jack_sample_t scale;
  200. srcidx = channel;
  201. switch (bits)
  202. {
  203. case 16:
  204. scale = 1.0f / 0x7fff;
  205. for (dstidx = 0; dstidx < nframes; dstidx++)
  206. {
  207. dst[dstidx] = (jack_sample_t)
  208. s16src[srcidx] * scale;
  209. srcidx += chcount;
  210. }
  211. break;
  212. case 24:
  213. scale = 1.0f / 0x7fffff;
  214. for (dstidx = 0; dstidx < nframes; dstidx++)
  215. {
  216. dst[dstidx] = (jack_sample_t)
  217. s32src[srcidx] * scale;
  218. srcidx += chcount;
  219. }
  220. break;
  221. case 32:
  222. scale = 1.0f / 0x7fffffff;
  223. for (dstidx = 0; dstidx < nframes; dstidx++)
  224. {
  225. dst[dstidx] = (jack_sample_t)
  226. s32src[srcidx] * scale;
  227. srcidx += chcount;
  228. }
  229. break;
  230. case 64:
  231. for (dstidx = 0; dstidx < nframes; dstidx++)
  232. {
  233. dst[dstidx] = (jack_sample_t) f64src[srcidx];
  234. srcidx += chcount;
  235. }
  236. break;
  237. }
  238. }
  239. static void copy_and_convert_out (void *dst, jack_sample_t *src,
  240. size_t nframes, int channel, int chcount, int bits)
  241. {
  242. int srcidx;
  243. int dstidx;
  244. signed short *s16dst = (signed short *) dst;
  245. signed int *s32dst = (signed int *) dst;
  246. double *f64dst = (double *) dst;
  247. jack_sample_t scale;
  248. dstidx = channel;
  249. switch (bits)
  250. {
  251. case 16:
  252. scale = 0x7fff;
  253. for (srcidx = 0; srcidx < nframes; srcidx++)
  254. {
  255. s16dst[dstidx] = (signed short)
  256. (src[srcidx] >= 0.0f) ?
  257. (src[srcidx] * scale + 0.5f) :
  258. (src[srcidx] * scale - 0.5f);
  259. dstidx += chcount;
  260. }
  261. break;
  262. case 24:
  263. scale = 0x7fffff;
  264. for (srcidx = 0; srcidx < nframes; srcidx++)
  265. {
  266. s32dst[dstidx] = (signed int)
  267. (src[srcidx] >= 0.0f) ?
  268. (src[srcidx] * scale + 0.5f) :
  269. (src[srcidx] * scale - 0.5f);
  270. dstidx += chcount;
  271. }
  272. break;
  273. case 32:
  274. scale = 0x7fffffff;
  275. for (srcidx = 0; srcidx < nframes; srcidx++)
  276. {
  277. s32dst[dstidx] = (signed int)
  278. (src[srcidx] >= 0.0f) ?
  279. (src[srcidx] * scale + 0.5f) :
  280. (src[srcidx] * scale - 0.5f);
  281. dstidx += chcount;
  282. }
  283. break;
  284. case 64:
  285. for (srcidx = 0; srcidx < nframes; srcidx++)
  286. {
  287. f64dst[dstidx] = (double) src[srcidx];
  288. dstidx += chcount;
  289. }
  290. break;
  291. }
  292. }
  293. static void set_fragment (int fd, size_t fragsize, unsigned int fragcount)
  294. {
  295. int fragsize_2p;
  296. int fragments;
  297. fragsize_2p = (int) (log(fragsize) / log(2.0) + 0.5);
  298. fragments = ((fragcount << 16) | (fragsize_2p & 0xffff));
  299. if (ioctl(fd, SNDCTL_DSP_SETFRAGMENT, &fragments) < 0)
  300. {
  301. jack_error("OSS: failed to set fragment size: %s@%i, errno=%d",
  302. __FILE__, __LINE__, errno);
  303. }
  304. }
  305. static int get_fragment (int fd)
  306. {
  307. int fragsize;
  308. if (ioctl(fd, SNDCTL_DSP_GETBLKSIZE, &fragsize) < 0)
  309. {
  310. jack_error("OSS: failed to get fragment size: %s@%i, errno=%d",
  311. __FILE__, __LINE__, errno);
  312. return 0;
  313. }
  314. return fragsize;
  315. }
  316. static void *io_thread (void *);
  317. /* jack driver interface */
  318. static int oss_driver_attach (oss_driver_t *driver, jack_engine_t *engine)
  319. {
  320. int port_flags;
  321. unsigned int channel;
  322. char channel_name[64];
  323. jack_port_t *port;
  324. jack_latency_range_t range;
  325. driver->engine = engine;
  326. set_period_size(driver, driver->period_size);
  327. if (engine->set_buffer_size(engine, driver->period_size)) {
  328. jack_error ("OSS: cannot set engine buffer size to %d (check MIDI)", driver->period_size);
  329. return -1;
  330. }
  331. engine->set_sample_rate(engine, driver->sample_rate);
  332. port_flags = JackPortIsOutput|JackPortIsPhysical|JackPortIsTerminal;
  333. for (channel = 0; channel < driver->capture_channels; channel++)
  334. {
  335. snprintf(channel_name, sizeof(channel_name),
  336. "capture_%u", channel + 1);
  337. port = jack_port_register(driver->client, channel_name,
  338. JACK_DEFAULT_AUDIO_TYPE, port_flags, 0);
  339. if (port == NULL)
  340. {
  341. jack_error("OSS: cannot register port for %s: %s@%i",
  342. channel_name, __FILE__, __LINE__);
  343. break;
  344. }
  345. range.min = range.max = driver->period_size + driver->sys_in_latency;
  346. jack_port_set_latency_range(port, JackCaptureLatency, &range);
  347. driver->capture_ports =
  348. jack_slist_append(driver->capture_ports, port);
  349. }
  350. port_flags = JackPortIsInput|JackPortIsPhysical|JackPortIsTerminal;
  351. for (channel = 0; channel < driver->playback_channels; channel++)
  352. {
  353. snprintf(channel_name, sizeof(channel_name),
  354. "playback_%u", channel + 1);
  355. port = jack_port_register(driver->client, channel_name,
  356. JACK_DEFAULT_AUDIO_TYPE, port_flags, 0);
  357. if (port == NULL)
  358. {
  359. jack_error("OSS: cannot register port for %s: %s@%i",
  360. channel_name, __FILE__, __LINE__);
  361. break;
  362. }
  363. range.min = range.max = driver->period_size + driver->sys_out_latency;
  364. jack_port_set_latency_range(port, JackPlaybackLatency, &range);
  365. driver->playback_ports =
  366. jack_slist_append(driver->playback_ports, port);
  367. }
  368. jack_activate(driver->client);
  369. return 0;
  370. }
  371. static int oss_driver_detach (oss_driver_t *driver, jack_engine_t *engine)
  372. {
  373. JSList *node;
  374. if (driver->engine == NULL)
  375. return -1;
  376. /*jack_deactivate(driver->client);*/ /* ? */
  377. node = driver->capture_ports;
  378. while (node != NULL)
  379. {
  380. jack_port_unregister(driver->client,
  381. ((jack_port_t *) node->data));
  382. node = jack_slist_next(node);
  383. }
  384. jack_slist_free(driver->capture_ports);
  385. driver->capture_ports = NULL;
  386. node = driver->playback_ports;
  387. while (node != NULL)
  388. {
  389. jack_port_unregister(driver->client,
  390. ((jack_port_t *) node->data));
  391. node = jack_slist_next(node);
  392. }
  393. jack_slist_free(driver->playback_ports);
  394. driver->playback_ports = NULL;
  395. driver->engine = NULL;
  396. return 0;
  397. }
  398. static int oss_driver_start (oss_driver_t *driver)
  399. {
  400. int flags = 0;
  401. int format;
  402. int channels;
  403. int samplerate;
  404. int infd = driver->infd;
  405. int outfd = driver->outfd;
  406. unsigned int period_size;
  407. size_t samplesize;
  408. size_t fragsize;
  409. const char *indev = driver->indev;
  410. const char *outdev = driver->outdev;
  411. switch (driver->bits)
  412. {
  413. case 24:
  414. case 32:
  415. samplesize = sizeof(int);
  416. break;
  417. case 64:
  418. samplesize = sizeof(double);
  419. break;
  420. case 16:
  421. default:
  422. samplesize = sizeof(short);
  423. break;
  424. }
  425. driver->trigger = 0;
  426. if (strcmp(indev, outdev) != 0)
  427. {
  428. if (driver->capture_channels > 0)
  429. {
  430. infd = open(indev, O_RDONLY|O_EXCL);
  431. if (infd < 0)
  432. {
  433. jack_error(
  434. "OSS: failed to open input device %s: %s@%i, errno=%d",
  435. indev, __FILE__, __LINE__, errno);
  436. }
  437. #ifndef OSS_NO_COOKED_MODE
  438. ioctl(infd, SNDCTL_DSP_COOKEDMODE, &flags);
  439. #endif
  440. fragsize = driver->period_size *
  441. driver->capture_channels * samplesize;
  442. set_fragment(infd, fragsize, driver->nperiods);
  443. }
  444. else infd = -1;
  445. if (driver->playback_channels > 0)
  446. {
  447. outfd = open(outdev, O_WRONLY|O_EXCL);
  448. if (outfd < 0)
  449. {
  450. jack_error(
  451. "OSS: failed to open output device %s: %s@%i, errno=%d",
  452. outdev, __FILE__, __LINE__, errno);
  453. }
  454. #ifndef OSS_NO_COOKED_MODE
  455. ioctl(outfd, SNDCTL_DSP_COOKEDMODE, &flags);
  456. #endif
  457. fragsize = driver->period_size *
  458. driver->playback_channels * samplesize;
  459. set_fragment(outfd, fragsize, driver->nperiods);
  460. }
  461. else outfd = -1;
  462. }
  463. else
  464. {
  465. if (driver->capture_channels != 0 &&
  466. driver->playback_channels == 0)
  467. {
  468. infd = open(indev, O_RDWR|O_EXCL);
  469. outfd = -1;
  470. if (infd < 0)
  471. {
  472. jack_error(
  473. "OSS: failed to open device %s: %s@%i, errno=%d",
  474. indev, __FILE__, __LINE__, errno);
  475. return -1;
  476. }
  477. #ifndef OSS_NO_COOKED_MODE
  478. ioctl(infd, SNDCTL_DSP_COOKEDMODE, &flags);
  479. #endif
  480. }
  481. else if (driver->capture_channels == 0 &&
  482. driver->playback_channels != 0)
  483. {
  484. infd = -1;
  485. outfd = open(outdev, O_RDWR|O_EXCL);
  486. if (outfd < 0)
  487. {
  488. jack_error(
  489. "OSS: failed to open device %s: %s@%i, errno=%d",
  490. outdev, __FILE__, __LINE__, errno);
  491. return -1;
  492. }
  493. #ifndef OSS_NO_COOKED_MODE
  494. ioctl(outfd, SNDCTL_DSP_COOKEDMODE, &flags);
  495. #endif
  496. }
  497. else
  498. {
  499. infd = outfd = open(indev, O_RDWR|O_EXCL);
  500. if (infd < 0)
  501. {
  502. jack_error(
  503. "OSS: failed to open device %s: %s@%i, errno=%d",
  504. indev, __FILE__, __LINE__, errno);
  505. return -1;
  506. }
  507. #ifndef OSS_NO_COOKED_MODE
  508. ioctl(infd, SNDCTL_DSP_COOKEDMODE, &flags);
  509. #endif
  510. }
  511. if (infd >= 0 && outfd >= 0)
  512. {
  513. ioctl(outfd, SNDCTL_DSP_SETTRIGGER, &driver->trigger);
  514. driver->trigger = (PCM_ENABLE_INPUT|PCM_ENABLE_OUTPUT);
  515. if (ioctl(infd, SNDCTL_DSP_SETDUPLEX, 0) < 0)
  516. {
  517. if (errno != EINVAL) /* Dont care */
  518. jack_error(
  519. "OSS: failed to enable full duplex for %s: %s@%i, errno=%d",
  520. indev, __FILE__, __LINE__,
  521. errno);
  522. }
  523. }
  524. if (infd >= 0)
  525. {
  526. fragsize = driver->period_size *
  527. driver->capture_channels * samplesize;
  528. set_fragment(infd, fragsize, driver->nperiods);
  529. }
  530. if (outfd >= 0 && infd < 0)
  531. {
  532. fragsize = driver->period_size *
  533. driver->playback_channels * samplesize;
  534. set_fragment(outfd, fragsize, driver->nperiods);
  535. }
  536. }
  537. driver->infd = infd;
  538. driver->outfd = outfd;
  539. if (infd >= 0)
  540. {
  541. format = driver->format;
  542. if (ioctl(infd, SNDCTL_DSP_SETFMT, &format) < 0)
  543. jack_error(
  544. "OSS: failed to set format for %s: %s@%i, errno=%d",
  545. indev, __FILE__, __LINE__, errno);
  546. channels = driver->capture_channels;
  547. if (ioctl(infd, SNDCTL_DSP_CHANNELS, &channels) < 0)
  548. jack_error(
  549. "OSS: failed to set channels for %s: %s@%i, errno=%d",
  550. indev, __FILE__, __LINE__, errno);
  551. samplerate = driver->sample_rate;
  552. if (ioctl(infd, SNDCTL_DSP_SPEED, &samplerate) < 0)
  553. jack_error(
  554. "OSS: failed to set samplerate for %s: %s@%i, errno=%d",
  555. indev, __FILE__, __LINE__, errno);
  556. jack_info("oss_driver: %s : 0x%x/%i/%i (%i)", indev,
  557. format, channels, samplerate, get_fragment(infd));
  558. period_size = get_fragment(infd) / samplesize / channels;
  559. if (period_size != driver->period_size &&
  560. !driver->ignorehwbuf)
  561. {
  562. jack_info("oss_driver: period size update: %u",
  563. period_size);
  564. driver->period_size = period_size;
  565. driver->period_usecs =
  566. ((double) driver->period_size /
  567. (double) driver->sample_rate) * 1e6;
  568. if (driver->engine->set_buffer_size(driver->engine,
  569. driver->period_size)) {
  570. jack_error ("OSS: cannot set engine buffer size to %d (check MIDI)", driver->period_size);
  571. return -1;
  572. }
  573. }
  574. }
  575. if (outfd >= 0 && infd != outfd)
  576. {
  577. format = driver->format;
  578. if (ioctl(outfd, SNDCTL_DSP_SETFMT, &format) < 0)
  579. jack_error(
  580. "OSS: failed to set format for %s: %s@%i, errno=%d",
  581. outdev, __FILE__, __LINE__, errno);
  582. channels = driver->playback_channels;
  583. if (ioctl(outfd, SNDCTL_DSP_CHANNELS, &channels) < 0)
  584. jack_error(
  585. "OSS: failed to set channels for %s: %s@%i, errno=%d",
  586. outdev, __FILE__, __LINE__, errno);
  587. samplerate = driver->sample_rate;
  588. if (ioctl(outfd, SNDCTL_DSP_SPEED, &samplerate) < 0)
  589. jack_error(
  590. "OSS: failed to set samplerate for %s: %s@%i, errno=%d",
  591. outdev, __FILE__, __LINE__, errno);
  592. jack_info("oss_driver: %s : 0x%x/%i/%i (%i)", outdev,
  593. format, channels, samplerate,
  594. get_fragment(outfd));
  595. period_size = get_fragment(outfd) / samplesize / channels;
  596. if (period_size != driver->period_size &&
  597. !driver->ignorehwbuf)
  598. {
  599. jack_info("oss_driver: period size update: %u",
  600. period_size);
  601. driver->period_size = period_size;
  602. driver->period_usecs =
  603. ((double) driver->period_size /
  604. (double) driver->sample_rate) * 1e6;
  605. if (driver->engine->set_buffer_size(driver->engine,
  606. driver->period_size)) {
  607. jack_error ("OSS: cannot set engine buffer size to %d (check MIDI)", driver->period_size);
  608. return -1;
  609. }
  610. }
  611. }
  612. if (driver->capture_channels > 0)
  613. {
  614. driver->indevbufsize = driver->period_size *
  615. driver->capture_channels * samplesize;
  616. driver->indevbuf = malloc(driver->indevbufsize);
  617. if (driver->indevbuf == NULL)
  618. {
  619. jack_error( "OSS: malloc() failed: %s@%i",
  620. __FILE__, __LINE__);
  621. return -1;
  622. }
  623. memset(driver->indevbuf, 0x00, driver->indevbufsize);
  624. }
  625. else
  626. {
  627. driver->indevbufsize = 0;
  628. driver->indevbuf = NULL;
  629. }
  630. if (driver->playback_channels > 0)
  631. {
  632. driver->outdevbufsize = driver->period_size *
  633. driver->playback_channels * samplesize;
  634. driver->outdevbuf = malloc(driver->outdevbufsize);
  635. if (driver->outdevbuf == NULL)
  636. {
  637. jack_error("OSS: malloc() failed: %s@%i",
  638. __FILE__, __LINE__);
  639. return -1;
  640. }
  641. memset(driver->outdevbuf, 0x00, driver->outdevbufsize);
  642. }
  643. else
  644. {
  645. driver->outdevbufsize = 0;
  646. driver->outdevbuf = NULL;
  647. }
  648. jack_info("oss_driver: indevbuf %zd B, outdevbuf %zd B",
  649. driver->indevbufsize, driver->outdevbufsize);
  650. pthread_mutex_init(&driver->mutex_in, NULL);
  651. pthread_mutex_init(&driver->mutex_out, NULL);
  652. # ifdef USE_BARRIER
  653. puts("oss_driver: using barrier mode, (dual thread)");
  654. pthread_barrier_init(&driver->barrier, NULL, 2);
  655. # else
  656. puts("oss_driver: not using barrier mode, (single thread)");
  657. # endif
  658. sem_init(&driver->sem_start, 0, 0);
  659. driver->run = 1;
  660. driver->threads = 0;
  661. if (infd >= 0)
  662. {
  663. if (jack_client_create_thread(NULL, &driver->thread_in,
  664. driver->engine->rtpriority,
  665. driver->engine->control->real_time,
  666. io_thread, driver) < 0)
  667. {
  668. jack_error("OSS: jack_client_create_thread() failed: %s@%i",
  669. __FILE__, __LINE__);
  670. return -1;
  671. }
  672. driver->threads |= 1;
  673. }
  674. # ifdef USE_BARRIER
  675. if (outfd >= 0)
  676. {
  677. if (jack_client_create_thread(NULL, &driver->thread_out,
  678. driver->engine->rtpriority,
  679. driver->engine->control->real_time,
  680. io_thread, driver) < 0)
  681. {
  682. jack_error("OSS: jack_client_create_thread() failed: %s@%i",
  683. __FILE__, __LINE__);
  684. return -1;
  685. }
  686. driver->threads |= 2;
  687. }
  688. # endif
  689. if (driver->threads & 1) sem_post(&driver->sem_start);
  690. if (driver->threads & 2) sem_post(&driver->sem_start);
  691. driver->last_periodtime = driver->engine->get_microseconds();
  692. driver->next_periodtime = 0;
  693. driver->iodelay = 0.0F;
  694. return 0;
  695. }
  696. static int oss_driver_stop (oss_driver_t *driver)
  697. {
  698. void *retval;
  699. driver->run = 0;
  700. if (driver->threads & 1)
  701. {
  702. if (pthread_join(driver->thread_in, &retval) < 0)
  703. {
  704. jack_error("OSS: pthread_join() failed: %s@%i",
  705. __FILE__, __LINE__);
  706. return -1;
  707. }
  708. }
  709. if (driver->threads & 2)
  710. {
  711. if (pthread_join(driver->thread_out, &retval) < 0)
  712. {
  713. jack_error("OSS: pthread_join() failed: %s@%i",
  714. __FILE__, __LINE__);
  715. return -1;
  716. }
  717. }
  718. sem_destroy(&driver->sem_start);
  719. # ifdef USE_BARRIER
  720. pthread_barrier_destroy(&driver->barrier);
  721. # endif
  722. pthread_mutex_destroy(&driver->mutex_in);
  723. pthread_mutex_destroy(&driver->mutex_out);
  724. if (driver->outfd >= 0 && driver->outfd != driver->infd)
  725. {
  726. close(driver->outfd);
  727. driver->outfd = -1;
  728. }
  729. if (driver->infd >= 0)
  730. {
  731. close(driver->infd);
  732. driver->infd = -1;
  733. }
  734. if (driver->indevbuf != NULL)
  735. {
  736. free(driver->indevbuf);
  737. driver->indevbuf = NULL;
  738. }
  739. if (driver->outdevbuf != NULL)
  740. {
  741. free(driver->outdevbuf);
  742. driver->outdevbuf = NULL;
  743. }
  744. return 0;
  745. }
  746. static int oss_driver_read (oss_driver_t *driver, jack_nframes_t nframes)
  747. {
  748. int channel;
  749. jack_sample_t *portbuf;
  750. JSList *node;
  751. jack_port_t *port;
  752. if (!driver->run) return 0;
  753. if (nframes != driver->period_size)
  754. {
  755. jack_error(
  756. "OSS: read failed nframes != period_size (%u/%u): %s@%i",
  757. nframes, driver->period_size, __FILE__, __LINE__);
  758. return -1;
  759. }
  760. pthread_mutex_lock(&driver->mutex_in);
  761. node = driver->capture_ports;
  762. channel = 0;
  763. while (node != NULL)
  764. {
  765. port = (jack_port_t *) node->data;
  766. if (jack_port_connected(port))
  767. {
  768. portbuf = jack_port_get_buffer(port, nframes);
  769. copy_and_convert_in(portbuf, driver->indevbuf,
  770. nframes, channel,
  771. driver->capture_channels,
  772. driver->bits);
  773. }
  774. node = jack_slist_next(node);
  775. channel++;
  776. }
  777. pthread_mutex_unlock(&driver->mutex_in);
  778. return 0;
  779. }
  780. static int oss_driver_write (oss_driver_t *driver, jack_nframes_t nframes)
  781. {
  782. int channel;
  783. jack_sample_t *portbuf;
  784. JSList *node;
  785. jack_port_t *port;
  786. if (!driver->run) return 0;
  787. if (nframes != driver->period_size)
  788. {
  789. jack_error(
  790. "OSS: write failed nframes != period_size (%u/%u): %s@%i",
  791. nframes, driver->period_size, __FILE__, __LINE__);
  792. return -1;
  793. }
  794. pthread_mutex_lock(&driver->mutex_out);
  795. node = driver->playback_ports;
  796. channel = 0;
  797. while (node != NULL)
  798. {
  799. port = (jack_port_t *) node->data;
  800. if (jack_port_connected(port))
  801. {
  802. portbuf = jack_port_get_buffer(port, nframes);
  803. copy_and_convert_out(driver->outdevbuf, portbuf,
  804. nframes, channel,
  805. driver->playback_channels,
  806. driver->bits);
  807. }
  808. node = jack_slist_next(node);
  809. channel++;
  810. }
  811. pthread_mutex_unlock(&driver->mutex_out);
  812. return 0;
  813. }
  814. static int oss_driver_null_cycle (oss_driver_t *driver, jack_nframes_t nframes)
  815. {
  816. pthread_mutex_lock(&driver->mutex_in);
  817. memset(driver->indevbuf, 0x00, driver->indevbufsize);
  818. pthread_mutex_unlock(&driver->mutex_in);
  819. pthread_mutex_lock(&driver->mutex_out);
  820. memset(driver->outdevbuf, 0x00, driver->outdevbufsize);
  821. pthread_mutex_unlock(&driver->mutex_out);
  822. return 0;
  823. }
  824. static int oss_driver_bufsize (oss_driver_t *driver, jack_nframes_t nframes)
  825. {
  826. oss_driver_stop(driver);
  827. set_period_size(driver, nframes);
  828. if (driver->engine->set_buffer_size(driver->engine, driver->period_size)) {
  829. jack_error ("OSS: cannot set engine buffer size to %d (check MIDI)", driver->period_size);
  830. return -1;
  831. }
  832. jack_info("oss_driver: period size update: %u", nframes);
  833. oss_driver_start(driver);
  834. return 0;
  835. }
  836. /* internal driver thread */
  837. #ifdef USE_BARRIER
  838. static inline void synchronize (oss_driver_t *driver)
  839. {
  840. if (driver->threads == 3)
  841. {
  842. if (pthread_barrier_wait(&driver->barrier) ==
  843. PTHREAD_BARRIER_SERIAL_THREAD)
  844. {
  845. driver_cycle(driver);
  846. }
  847. }
  848. else
  849. {
  850. driver_cycle(driver);
  851. }
  852. }
  853. #endif
  854. static void *io_thread (void *param)
  855. {
  856. size_t localsize;
  857. ssize_t io_res;
  858. void *localbuf;
  859. oss_driver_t *driver = (oss_driver_t *) param;
  860. sem_wait(&driver->sem_start);
  861. # ifdef USE_BARRIER
  862. if (pthread_self() == driver->thread_in)
  863. {
  864. localsize = driver->indevbufsize;
  865. localbuf = malloc(localsize);
  866. if (localbuf == NULL)
  867. {
  868. jack_error("OSS: malloc() failed: %s@%i",
  869. __FILE__, __LINE__);
  870. return NULL;
  871. }
  872. while (driver->run)
  873. {
  874. io_res = read(driver->infd, localbuf, localsize);
  875. if (io_res < (ssize_t) localsize)
  876. {
  877. jack_error(
  878. "OSS: read() failed: %s@%i, count=%d/%d, errno=%d",
  879. __FILE__, __LINE__, io_res, localsize,
  880. errno);
  881. break;
  882. }
  883. pthread_mutex_lock(&driver->mutex_in);
  884. memcpy(driver->indevbuf, localbuf, localsize);
  885. pthread_mutex_unlock(&driver->mutex_in);
  886. synchronize(driver);
  887. }
  888. free(localbuf);
  889. }
  890. else if (pthread_self() == driver->thread_out)
  891. {
  892. localsize = driver->outdevbufsize;
  893. localbuf = malloc(localsize);
  894. if (localbuf == NULL)
  895. {
  896. jack_error("OSS: malloc() failed: %s@%i",
  897. __FILE__, __LINE__);
  898. return NULL;
  899. }
  900. if (driver->trigger)
  901. {
  902. /* don't care too much if this fails */
  903. memset(localbuf, 0x00, localsize);
  904. write(driver->outfd, localbuf, localsize);
  905. ioctl(driver->outfd, SNDCTL_DSP_SETTRIGGER, &driver->trigger);
  906. }
  907. while (driver->run)
  908. {
  909. pthread_mutex_lock(&driver->mutex_out);
  910. memcpy(localbuf, driver->outdevbuf, localsize);
  911. pthread_mutex_unlock(&driver->mutex_out);
  912. io_res = write(driver->outfd, localbuf, localsize);
  913. if (io_res < (ssize_t) localsize)
  914. {
  915. jack_error(
  916. "OSS: write() failed: %s@%i, count=%d/%d, errno=%d",
  917. __FILE__, __LINE__, io_res, localsize,
  918. errno);
  919. break;
  920. }
  921. synchronize(driver);
  922. }
  923. free(localbuf);
  924. }
  925. # else
  926. localsize = (driver->indevbufsize >= driver->outdevbufsize) ?
  927. driver->indevbufsize : driver->outdevbufsize;
  928. localbuf = malloc(localsize);
  929. if (localbuf == NULL)
  930. {
  931. jack_error("OSS: malloc() failed: %s@%i", __FILE__, __LINE__);
  932. return NULL;
  933. }
  934. if (driver->trigger)
  935. {
  936. /* don't care too much if this fails */
  937. memset(localbuf, 0x00, localsize);
  938. write(driver->outfd, localbuf, driver->outdevbufsize);
  939. ioctl(driver->outfd, SNDCTL_DSP_SETTRIGGER, &driver->trigger);
  940. }
  941. while (driver->run)
  942. {
  943. if (driver->playback_channels > 0)
  944. {
  945. pthread_mutex_lock(&driver->mutex_out);
  946. memcpy(localbuf, driver->outdevbuf,
  947. driver->outdevbufsize);
  948. pthread_mutex_unlock(&driver->mutex_out);
  949. io_res = write(driver->outfd, localbuf,
  950. driver->outdevbufsize);
  951. if (io_res < (ssize_t) driver->outdevbufsize)
  952. {
  953. jack_error(
  954. "OSS: write() failed: %s@%i, count=%d/%d, errno=%d",
  955. __FILE__, __LINE__, io_res,
  956. driver->outdevbufsize, errno);
  957. break;
  958. }
  959. }
  960. if (driver->capture_channels > 0)
  961. {
  962. io_res = read(driver->infd, localbuf,
  963. driver->indevbufsize);
  964. if (io_res < (ssize_t) driver->indevbufsize)
  965. {
  966. jack_error(
  967. "OSS: read() failed: %s@%i, count=%d/%d, errno=%d",
  968. __FILE__, __LINE__, io_res,
  969. driver->indevbufsize, errno);
  970. break;
  971. }
  972. pthread_mutex_lock(&driver->mutex_in);
  973. memcpy(driver->indevbuf, localbuf,
  974. driver->indevbufsize);
  975. pthread_mutex_unlock(&driver->mutex_in);
  976. }
  977. driver_cycle(driver);
  978. }
  979. free(localbuf);
  980. # endif
  981. return NULL;
  982. }
  983. /* jack driver published interface */
  984. const char driver_client_name[] = "oss";
  985. void driver_finish (jack_driver_t *);
  986. jack_driver_desc_t * driver_get_descriptor ()
  987. {
  988. jack_driver_desc_t *desc;
  989. jack_driver_param_desc_t *params;
  990. desc = (jack_driver_desc_t *) calloc(1, sizeof(jack_driver_desc_t));
  991. if (desc == NULL)
  992. {
  993. jack_error("oss_driver: calloc() failed: %s@%i, errno=%d",
  994. __FILE__, __LINE__, errno);
  995. return NULL;
  996. }
  997. strcpy(desc->name, driver_client_name);
  998. desc->nparams = OSS_DRIVER_N_PARAMS;
  999. params = calloc(desc->nparams, sizeof(jack_driver_param_desc_t));
  1000. if (params == NULL)
  1001. {
  1002. jack_error("oss_driver: calloc() failed: %s@%i, errno=%d",
  1003. __FILE__, __LINE__, errno);
  1004. return NULL;
  1005. }
  1006. memcpy(params, oss_params,
  1007. desc->nparams * sizeof(jack_driver_param_desc_t));
  1008. desc->params = params;
  1009. return desc;
  1010. }
  1011. jack_driver_t * driver_initialize (jack_client_t *client,
  1012. JSList * params)
  1013. {
  1014. int bits = OSS_DRIVER_DEF_BITS;
  1015. jack_nframes_t sample_rate = OSS_DRIVER_DEF_FS;
  1016. jack_nframes_t period_size = OSS_DRIVER_DEF_BLKSIZE;
  1017. jack_nframes_t in_latency = 0;
  1018. jack_nframes_t out_latency = 0;
  1019. unsigned int nperiods = OSS_DRIVER_DEF_NPERIODS;
  1020. unsigned int capture_channels = OSS_DRIVER_DEF_INS;
  1021. unsigned int playback_channels = OSS_DRIVER_DEF_OUTS;
  1022. const JSList *pnode;
  1023. const jack_driver_param_t *param;
  1024. oss_driver_t *driver;
  1025. driver = (oss_driver_t *) malloc(sizeof(oss_driver_t));
  1026. if (driver == NULL)
  1027. {
  1028. jack_error("OSS: malloc() failed: %s@%i, errno=%d",
  1029. __FILE__, __LINE__, errno);
  1030. return NULL;
  1031. }
  1032. memset(driver, 0x00, sizeof(oss_driver_t));
  1033. jack_driver_init((jack_driver_t *) driver);
  1034. driver->attach = (JackDriverAttachFunction) oss_driver_attach;
  1035. driver->detach = (JackDriverDetachFunction) oss_driver_detach;
  1036. driver->start = (JackDriverStartFunction) oss_driver_start;
  1037. driver->stop = (JackDriverStopFunction) oss_driver_stop;
  1038. driver->read = (JackDriverReadFunction) oss_driver_read;
  1039. driver->write = (JackDriverWriteFunction) oss_driver_write;
  1040. driver->null_cycle = (JackDriverNullCycleFunction)
  1041. oss_driver_null_cycle;
  1042. driver->bufsize = (JackDriverBufSizeFunction) oss_driver_bufsize;
  1043. driver->indev = NULL;
  1044. driver->outdev = NULL;
  1045. driver->ignorehwbuf = 0;
  1046. driver->trigger = 0;
  1047. pnode = params;
  1048. while (pnode != NULL)
  1049. {
  1050. param = (const jack_driver_param_t *) pnode->data;
  1051. switch (param->character)
  1052. {
  1053. case 'r':
  1054. sample_rate = param->value.ui;
  1055. break;
  1056. case 'p':
  1057. period_size = param->value.ui;
  1058. break;
  1059. case 'n':
  1060. nperiods = param->value.ui;
  1061. break;
  1062. case 'w':
  1063. bits = param->value.i;
  1064. break;
  1065. case 'i':
  1066. capture_channels = param->value.ui;
  1067. break;
  1068. case 'o':
  1069. playback_channels = param->value.ui;
  1070. break;
  1071. case 'C':
  1072. driver->indev = strdup(param->value.str);
  1073. break;
  1074. case 'P':
  1075. driver->outdev = strdup(param->value.str);
  1076. break;
  1077. case 'b':
  1078. driver->ignorehwbuf = 1;
  1079. break;
  1080. case 'I':
  1081. in_latency = param->value.ui;
  1082. break;
  1083. case 'O':
  1084. out_latency = param->value.ui;
  1085. break;
  1086. }
  1087. pnode = jack_slist_next(pnode);
  1088. }
  1089. driver->sample_rate = sample_rate;
  1090. driver->period_size = period_size;
  1091. driver->nperiods = nperiods;
  1092. driver->bits = bits;
  1093. driver->capture_channels = capture_channels;
  1094. driver->playback_channels = playback_channels;
  1095. driver->sys_in_latency = in_latency;
  1096. driver->sys_out_latency = out_latency;
  1097. /* setting driver->period_usecs & co is delayed until attach */
  1098. driver->finish = driver_finish;
  1099. if (driver->indev == NULL)
  1100. driver->indev = strdup(OSS_DRIVER_DEF_DEV);
  1101. if (driver->outdev == NULL)
  1102. driver->outdev = strdup(OSS_DRIVER_DEF_DEV);
  1103. driver->infd = -1;
  1104. driver->outfd = -1;
  1105. switch (driver->bits)
  1106. {
  1107. # ifndef OSS_ENDIAN
  1108. # ifdef __GNUC__
  1109. # if (defined(__i386__) || defined(__alpha__) || defined(__arm__) || defined(__x86_64__) || (defined(__sh__) && !defined(__LITTLE_ENDIAN__)))
  1110. # define OSS_LITTLE_ENDIAN 1234
  1111. # define OSS_ENDIAN OSS_LITTLE_ENDIAN
  1112. # else
  1113. # define OSS_BIG_ENDIAN 4321
  1114. # define OSS_ENDIAN OSS_BIG_ENDIAN
  1115. # endif
  1116. # else /* __GNUC__ */
  1117. # if (defined(_AIX) || defined(AIX) || defined(sparc) || defined(__hppa) || defined(PPC) || defined(__powerpc__) && !defined(i386) && !defined(__i386) && !defined(__i386__))
  1118. # define OSS_BIG_ENDIAN 4321
  1119. # define OSS_ENDIAN OSS_BIG_ENDIAN
  1120. # else
  1121. # define OSS_LITTLE_ENDIAN 1234
  1122. # define OSS_ENDIAN OSS_LITTLE_ENDIAN
  1123. # endif
  1124. # endif /* __GNUC__ */
  1125. # endif /* OSS_ENDIAN */
  1126. # if (OSS_ENDIAN == 1234)
  1127. /* little-endian architectures */
  1128. case 24: /* little-endian LSB aligned 24-bits in 32-bits integer */
  1129. driver->format = 0x00008000;
  1130. break;
  1131. case 32: /* little-endian 32-bit integer */
  1132. driver->format = 0x00001000;
  1133. break;
  1134. case 64: /* native-endian 64-bit float */
  1135. driver->format = 0x00004000;
  1136. break;
  1137. case 16: /* little-endian 16-bit integer */
  1138. default:
  1139. driver->format = 0x00000010;
  1140. break;
  1141. /* big-endian architectures */
  1142. # else
  1143. case 24: /* big-endian LSB aligned 24-bits in 32-bits integer */
  1144. break;
  1145. driver->format = 0x00010000;
  1146. case 32: /* big-endian 32-bit integer */
  1147. driver->format = 0x00002000;
  1148. break;
  1149. case 64: /* native-endian 64-bit float */
  1150. driver->format = 0x00004000;
  1151. break;
  1152. case 16: /* big-endian 16-bit integer */
  1153. default:
  1154. driver->format = 0x00000020;
  1155. # endif
  1156. }
  1157. driver->indevbuf = driver->outdevbuf = NULL;
  1158. driver->capture_ports = NULL;
  1159. driver->playback_ports = NULL;
  1160. driver->engine = NULL;
  1161. driver->client = client;
  1162. return ((jack_driver_t *) driver);
  1163. }
  1164. void driver_finish (jack_driver_t *driver)
  1165. {
  1166. oss_driver_t *oss_driver = (oss_driver_t *) driver;
  1167. oss_driver = (oss_driver_t *) driver;
  1168. if (oss_driver->indev != NULL)
  1169. free(oss_driver->indev);
  1170. if (oss_driver->outdev != NULL)
  1171. free(oss_driver->outdev);
  1172. free(driver);
  1173. }