aRts audio server
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.

232 lines
4.4KB

  1. /*
  2. Copyright (C) 2001 Jochen Hoenicke
  3. jochen@gnu.org
  4. Copyright (C) 2003 Ian Chiew
  5. ian@snork.net
  6. This library is free software; you can redistribute it and/or
  7. modify it under the terms of the GNU Library General Public
  8. License as published by the Free Software Foundation; either
  9. version 2 of the License, or (at your option) any later version.
  10. This library is distributed in the hope that it will be useful,
  11. but WITHOUT ANY WARRANTY; without even the implied warranty of
  12. MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
  13. Library General Public License for more details.
  14. You should have received a copy of the GNU Library General Public License
  15. along with this library; see the file COPYING.LIB. If not, write to
  16. the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor,
  17. Boston, MA 02110-1301, USA.
  18. */
  19. #ifdef HAVE_CONFIG_H
  20. #include <config.h>
  21. #endif
  22. /**
  23. * only compile esound AudioIO class if libesd was detected during
  24. * configure
  25. */
  26. #ifdef HAVE_LIBESD
  27. #include <sys/types.h>
  28. #include <sys/ioctl.h>
  29. #include <sys/time.h>
  30. #include <sys/stat.h>
  31. #include <assert.h>
  32. #include <errno.h>
  33. #include <fcntl.h>
  34. #include <stdio.h>
  35. #include <stdlib.h>
  36. #include <unistd.h>
  37. #include <iostream>
  38. #include "audioio.h"
  39. #include "audiosubsys.h"
  40. #include "iomanager.h"
  41. #include "dispatcher.h"
  42. #include <esd.h>
  43. #ifdef __BIG_ENDIAN__
  44. #define _format_bits 17
  45. #else
  46. #define _format_bits 16
  47. #endif
  48. namespace Arts {
  49. class AudioIOESD : public AudioIO, public IONotify {
  50. protected:
  51. int server_fd, read_fd, write_fd;
  52. public:
  53. AudioIOESD();
  54. void setParam(AudioParam param, int& value);
  55. int getParam(AudioParam param);
  56. void notifyIO(int fd, int type);
  57. bool open();
  58. void close();
  59. void run();
  60. int read(void *buffer, int size);
  61. int write(void *buffer, int size);
  62. };
  63. REGISTER_AUDIO_IO(AudioIOESD,"esd","Enlightened Sound Daemon");
  64. }
  65. using namespace std;
  66. using namespace Arts;
  67. AudioIOESD::AudioIOESD()
  68. {
  69. /*
  70. * default parameters
  71. */
  72. param(samplingRate) = 44100;
  73. paramStr(deviceName) = "null";
  74. param(fragmentSize) = 1024;
  75. param(fragmentCount) = 7;
  76. param(format) = _format_bits;
  77. param(channels) = 2;
  78. param(direction) = 2;
  79. server_fd = -1;
  80. read_fd = -1;
  81. write_fd = -1;
  82. }
  83. bool AudioIOESD::open()
  84. {
  85. int& _channels = param(channels);
  86. int& _direction = param(direction);
  87. int& _samplingRate = param(samplingRate);
  88. int& _format = param(format);
  89. string& _error = paramStr(lastError);
  90. if ((server_fd = esd_open_sound(NULL)) == -1)
  91. {
  92. _error = "Couldn't connect to server";
  93. return false;
  94. }
  95. esd_server_info_t *server_info = esd_get_server_info(server_fd);
  96. if (server_info == NULL)
  97. {
  98. _error = "Unable to query EsounD server";
  99. return false;
  100. }
  101. esd_format_t server_format = server_info->format;
  102. _samplingRate = server_info->rate;
  103. _channels = (server_format & ESD_STEREO) ? 2 : 1;
  104. _format = (server_format & ESD_BITS16) ? _format_bits : 8;
  105. esd_free_server_info(server_info);
  106. if (_direction & directionRead)
  107. {
  108. read_fd = esd_record_stream(server_format, _samplingRate,
  109. NULL, "aRts");
  110. if (read_fd == -1)
  111. {
  112. _error = "Couldn't create read uflow";
  113. return false;
  114. }
  115. }
  116. if (_direction & directionWrite)
  117. {
  118. write_fd = esd_play_stream(server_format, _samplingRate,
  119. NULL, "aRts");
  120. if (write_fd == -1)
  121. {
  122. _error = "Couldn't create write flow";
  123. return false;
  124. }
  125. }
  126. return true;
  127. }
  128. void AudioIOESD::notifyIO(int, int)
  129. {
  130. }
  131. void AudioIOESD::close()
  132. {
  133. if (write_fd != -1)
  134. esd_close(write_fd);
  135. if (read_fd != -1)
  136. esd_close(read_fd);
  137. if (server_fd != -1)
  138. esd_close(server_fd);
  139. }
  140. void AudioIOESD::setParam(AudioParam p, int& value)
  141. {
  142. switch(p)
  143. {
  144. case channels:
  145. case format:
  146. case direction:
  147. case samplingRate:
  148. param(p) = value;
  149. close();
  150. open();
  151. return;
  152. default:
  153. param(p) = value;
  154. return;
  155. }
  156. }
  157. int AudioIOESD::getParam(AudioParam p)
  158. {
  159. switch(p)
  160. {
  161. case selectReadFD:
  162. return read_fd;
  163. case selectWriteFD:
  164. return write_fd;
  165. case canRead:
  166. return ESD_BUF_SIZE;
  167. case canWrite:
  168. return ESD_BUF_SIZE;
  169. // ESD handles are actually socket descriptors, and I know not
  170. // of any portable way to peek at the socket's send or receive
  171. // buffers.
  172. default:
  173. return param(p);
  174. }
  175. }
  176. int AudioIOESD::read(void *buffer, int size)
  177. {
  178. return ::read(read_fd, buffer, size);
  179. }
  180. int AudioIOESD::write(void *buffer, int size)
  181. {
  182. return ::write(write_fd, buffer, size);
  183. }
  184. #endif