summaryrefslogtreecommitdiff
path: root/audio_hpux.c
diff options
context:
space:
mode:
Diffstat (limited to 'audio_hpux.c')
-rw-r--r--audio_hpux.c160
1 files changed, 160 insertions, 0 deletions
diff --git a/audio_hpux.c b/audio_hpux.c
new file mode 100644
index 0000000..8d666da
--- /dev/null
+++ b/audio_hpux.c
@@ -0,0 +1,160 @@
+/*
+ * Taken mainly from xmp, Cc( 1996-98 Claudio Matsuoka and Hipolito Carraro Jr
+ *
+ * Who knows if it works, not I, not I...
+ * -- Isaac
+ */
+
+#include <sys/audio.h>
+
+#define ARCH_esd_audio_open
+int esd_audio_open()
+{
+ const char *device = "/dev/audio";
+
+ int afd = -1;
+ int mode = O_WRONLY;
+ int gain = AUDIO_MAX_GAIN;
+ int bsize;
+ int port = AUDIO_OUT_SPEAKER;
+ int flags, test;
+ struct audio_gain again;
+ struct audio_describe adescribe;
+ struct audio_limits alimit;
+
+ if ((esd_audio_format & ESD_MASK_FUNC) == ESD_RECORD) {
+ fprintf(stderr, "No idea how to record audio on hp-ux boxen, FIXME\n");
+ esd_audio_fd = -1;
+ return -1;
+ }
+
+ if ((afd = open(device, mode)) == -1) {
+ perror(device);
+ esd_audio_fd = -1;
+ return -1;
+ }
+
+ flags = fcntl(afd, F_GETFL, 0);
+ if (flags < 0) {
+ perror("F_GETFL");
+ esd_audio_fd = -1;
+ return -1;
+ }
+ flags |= O_NDELAY;
+ fcntl(afd, F_SETFL, flags);
+ if (flags < 0) {
+ perror("F_SETFL");
+ esd_audio_fd = -1;
+ return -1;
+ }
+
+ if ((esd_audio_format & ESD_MASK_BITS) == ESD_BITS16)
+ flags = AUDIO_FORMAT_LINEAR16BIT;
+ else
+ flags = AUDIO_FORMAT_ULAW; /* FIXME: is this right? */
+ /* TODO: probably need a linear2ulaw before sending the mix to the audio device */
+ if (ioctl(afd, AUDIO_SET_DATA_FORMAT, flags) == -1) {
+ perror("AUDIO_SET_DATA_FORMAT");
+ close(afd);
+ esd_audio_fd = -1;
+ return -1;
+ }
+
+ if ((esd_audio_format & ESD_MASK_CHAN) == ESD_STEREO)
+ flags = 2;
+ else
+ flags = 1;
+ if (ioctl(afd, AUDIO_SET_CHANNELS, flags) == -1) {
+ perror("AUDIO_SET_CHANNELS");
+ close(afd);
+ esd_audio_fd = -1;
+ return -1;
+ }
+
+ if (ioctl(afd, AUDIO_SET_OUTPUT, port) == -1) {
+ perror("AUDIO_SET_PORT");
+ close(afd);
+ esd_audio_fd = -1;
+ return -1;
+ }
+
+ test = esd_audio_rate;
+ if (ioctl(afd, AUDIO_SET_SAMPLE_RATE, test) == -1) {
+ perror("AUDIO_SET_SAMPLE_RATE");
+ close(afd);
+ esd_audio_fd = -1;
+ return -1;
+ }
+ if (fabs(test - esd_audio_rate) > esd_audio_rate * 0.05) {
+ fprintf(stderr,"unsupported playback rate: %d\n", esd_audio_rate);
+ close(afd);
+ esd_audio_fd = -1;
+ return -1;
+ }
+
+ if (ioctl(afd, AUDIO_DESCRIBE, &adescribe) == -1) {
+ perror("AUDIO_DESCRIBE");
+ close(afd);
+ esd_audio_fd = -1;
+ return -1;
+ }
+
+ if (ioctl(afd, AUDIO_GET_GAINS, &again) == -1) {
+ perror("AUDIO_GET_GAINS");
+ close(afd);
+ esd_audio_fd = -1;
+ return -1;
+ }
+
+ /* Don't modify transmit_gain unless it's out of bounds. */
+ if (again.cgain[0].transmit_gain < adescribe.min_transmit_gain ||
+ again.cgain[1].transmit_gain < adescribe.min_transmit_gain ||
+ again.cgain[0].transmit_gain > adescribe.max_transmit_gain ||
+ again.cgain[1].transmit_gain > adescribe.max_transmit_gain) {
+ fprintf(stderr, "one or more of your gain values was out of range - fixed.\n");
+ if (again.cgain[0].transmit_gain < adescribe.min_transmit_gain)
+ again.cgain[0].transmit_gain = adescribe.min_transmit_gain;
+ if (again.cgain[1].transmit_gain < adescribe.min_transmit_gain)
+ again.cgain[1].transmit_gain = adescribe.min_transmit_gain;
+ if (again.cgain[0].transmit_gain > adescribe.max_transmit_gain)
+ again.cgain[0].transmit_gain = adescribe.max_transmit_gain;
+ if (again.cgain[1].transmit_gain > adescribe.max_transmit_gain)
+ again.cgain[1].transmit_gain = adescribe.max_transmit_gain;
+ }
+
+ if (ioctl(afd, AUDIO_SET_GAINS, &again) == -1) {
+ perror("AUDIO_SET_GAINS");
+ close(afd);
+ esd_audio_fd = -1;
+ return -1;
+ }
+
+ if (!ioctl(afd, AUDIO_GET_LIMITS, &alimit)) {
+ bsize = (0x0100 << 16);
+ } else {
+ bsize = alimit.max_transmit_buffer_size;
+ }
+
+ while (bsize) {
+ if (ioctl(afd, AUDIO_SET_TXBUFSIZE, bsize) != -1) {
+ break;
+ }
+ bsize >>= 1;
+ }
+ if (!bsize) {
+ close(afd);
+ esd_audio_fd = -1;
+ return -1;
+ }
+
+ if (ioctl(afd, AUDIO_SET_TXBUFSIZE, bsize) == -1) {
+ perror("AUDIO_SET_TXBUFSIZE");
+ close(afd);
+ esd_audio_fd = -1;
+ return -1;
+ }
+
+ esd_audio_fd = afd;
+ return afd;
+}
+