blob: 89a59b7f4c6534a8c007142910fac8f9e62c7fbf [file] [log] [blame]
Guido van Rossum9c52e0f1992-06-03 17:06:14 +00001/***********************************************************
Guido van Rossumfd71b9e2000-06-30 23:50:40 +00002Copyright (c) 2000, BeOpen.com.
3Copyright (c) 1995-2000, Corporation for National Research Initiatives.
4Copyright (c) 1990-1995, Stichting Mathematisch Centrum.
5All rights reserved.
Guido van Rossum9c52e0f1992-06-03 17:06:14 +00006
Guido van Rossumfd71b9e2000-06-30 23:50:40 +00007See the file "Misc/COPYRIGHT" for information on usage and
8redistribution of this file, and for a DISCLAIMER OF ALL WARRANTIES.
Guido van Rossum9c52e0f1992-06-03 17:06:14 +00009******************************************************************/
10
11/* Sad objects */
12
Barry Warsaw8496d391996-12-13 00:11:04 +000013#include "Python.h"
Guido van Rossum9c52e0f1992-06-03 17:06:14 +000014#include "structmember.h"
15
Guido van Rossumb6775db1994-08-01 11:34:53 +000016#ifdef HAVE_SYS_AUDIOIO_H
17#define SOLARIS
18#endif
19
Guido van Rossume29ed8f1996-12-10 15:21:30 +000020#ifdef HAVE_UNISTD_H
21#include <unistd.h>
22#endif
23
24#ifdef HAVE_FCNTL_H
25#include <fcntl.h>
26#endif
27
Guido van Rossum234f9421993-06-17 12:35:49 +000028#include <stropts.h>
Guido van Rossum9c52e0f1992-06-03 17:06:14 +000029#include <sys/ioctl.h>
Sjoerd Mullender66bca321993-12-03 16:54:45 +000030#ifdef SOLARIS
Guido van Rossumb6775db1994-08-01 11:34:53 +000031#include <sys/audioio.h>
Sjoerd Mullender66bca321993-12-03 16:54:45 +000032#else
Guido van Rossum9c52e0f1992-06-03 17:06:14 +000033#include <sun/audioio.h>
Sjoerd Mullender66bca321993-12-03 16:54:45 +000034#endif
Guido van Rossum9c52e0f1992-06-03 17:06:14 +000035
36/* #define offsetof(str,mem) ((int)(((str *)0)->mem)) */
37
38typedef struct {
Barry Warsaw8496d391996-12-13 00:11:04 +000039 PyObject_HEAD
Guido van Rossum9c52e0f1992-06-03 17:06:14 +000040 int x_fd; /* The open file */
41 int x_icount; /* # samples read */
42 int x_ocount; /* # samples written */
43 int x_isctl; /* True if control device */
44
45} sadobject;
46
47typedef struct {
Barry Warsaw8496d391996-12-13 00:11:04 +000048 PyObject_HEAD
Guido van Rossum9c52e0f1992-06-03 17:06:14 +000049 audio_info_t ai;
50} sadstatusobject;
51
Barry Warsaw8496d391996-12-13 00:11:04 +000052staticforward PyTypeObject Sadtype;
53staticforward PyTypeObject Sadstatustype;
Sjoerd Mullender66bca321993-12-03 16:54:45 +000054static sadstatusobject *sads_alloc(); /* Forward */
Guido van Rossum9c52e0f1992-06-03 17:06:14 +000055
Barry Warsaw8496d391996-12-13 00:11:04 +000056static PyObject *SunAudioError;
Guido van Rossum9c52e0f1992-06-03 17:06:14 +000057
Guido van Rossum9c52e0f1992-06-03 17:06:14 +000058#define is_sadobject(v) ((v)->ob_type == &Sadtype)
59#define is_sadstatusobject(v) ((v)->ob_type == &Sadstatustype)
60
Barry Warsawb0d1b061998-10-31 22:52:54 +000061
Guido van Rossum9c52e0f1992-06-03 17:06:14 +000062static sadobject *
63newsadobject(arg)
Barry Warsaw8496d391996-12-13 00:11:04 +000064 PyObject *arg;
Guido van Rossum9c52e0f1992-06-03 17:06:14 +000065{
66 sadobject *xp;
67 int fd;
68 char *mode;
69 int imode;
Barry Warsawb0d1b061998-10-31 22:52:54 +000070 char* basedev;
71 char* ctldev;
72 char* opendev;
Guido van Rossum9c52e0f1992-06-03 17:06:14 +000073
74 /* Check arg for r/w/rw */
Barry Warsaw8496d391996-12-13 00:11:04 +000075 if (!PyArg_Parse(arg, "s", &mode))
76 return NULL;
77 if (strcmp(mode, "r") == 0)
78 imode = 0;
79 else if (strcmp(mode, "w") == 0)
80 imode = 1;
81 else if (strcmp(mode, "rw") == 0)
82 imode = 2;
83 else if (strcmp(mode, "control") == 0)
84 imode = -1;
Guido van Rossum9c52e0f1992-06-03 17:06:14 +000085 else {
Barry Warsaw8496d391996-12-13 00:11:04 +000086 PyErr_SetString(SunAudioError,
87 "Mode should be one of 'r', 'w', 'rw' or 'control'");
88 return NULL;
Guido van Rossum9c52e0f1992-06-03 17:06:14 +000089 }
90
Barry Warsawb0d1b061998-10-31 22:52:54 +000091 /* Open the correct device. The base device name comes from the
92 * AUDIODEV environment variable first, then /dev/audio. The
93 * control device tacks "ctl" onto the base device name.
94 */
95 basedev = getenv("AUDIODEV");
96 if (!basedev)
97 basedev = "/dev/audio";
98 ctldev = PyMem_NEW(char, strlen(basedev) + 4);
99 if (!ctldev) {
100 PyErr_NoMemory();
Barry Warsaw8496d391996-12-13 00:11:04 +0000101 return NULL;
Guido van Rossum9c52e0f1992-06-03 17:06:14 +0000102 }
Barry Warsawb0d1b061998-10-31 22:52:54 +0000103 strcpy(ctldev, basedev);
104 strcat(ctldev, "ctl");
105
106 if (imode < 0) {
107 opendev = ctldev;
108 fd = open(ctldev, 2);
109 }
110 else {
111 opendev = basedev;
112 fd = open(basedev, imode);
113 }
114 if (fd < 0) {
115 PyErr_SetFromErrnoWithFilename(SunAudioError, opendev);
116 return NULL;
117 }
118 PyMem_DEL(ctldev);
Guido van Rossum9c52e0f1992-06-03 17:06:14 +0000119
120 /* Create and initialize the object */
Guido van Rossumb18618d2000-05-03 23:44:39 +0000121 xp = PyObject_New(sadobject, &Sadtype);
Barry Warsaw42185a21997-01-09 22:29:57 +0000122 if (xp == NULL) {
123 close(fd);
Guido van Rossum9c52e0f1992-06-03 17:06:14 +0000124 return NULL;
Barry Warsaw42185a21997-01-09 22:29:57 +0000125 }
Guido van Rossum9c52e0f1992-06-03 17:06:14 +0000126 xp->x_fd = fd;
127 xp->x_icount = xp->x_ocount = 0;
128 xp->x_isctl = (imode < 0);
129
130 return xp;
131}
132
133/* Sad methods */
134
135static void
136sad_dealloc(xp)
137 sadobject *xp;
138{
139 close(xp->x_fd);
Guido van Rossumb18618d2000-05-03 23:44:39 +0000140 PyObject_Del(xp);
Guido van Rossum9c52e0f1992-06-03 17:06:14 +0000141}
142
Barry Warsaw8496d391996-12-13 00:11:04 +0000143static PyObject *
Guido van Rossum9c52e0f1992-06-03 17:06:14 +0000144sad_read(self, args)
145 sadobject *self;
Barry Warsaw8496d391996-12-13 00:11:04 +0000146 PyObject *args;
Guido van Rossum9c52e0f1992-06-03 17:06:14 +0000147{
148 int size, count;
149 char *cp;
Barry Warsaw8496d391996-12-13 00:11:04 +0000150 PyObject *rv;
Guido van Rossum9c52e0f1992-06-03 17:06:14 +0000151
Barry Warsaw8496d391996-12-13 00:11:04 +0000152 if (!PyArg_Parse(args, "i", &size))
153 return NULL;
154 rv = PyString_FromStringAndSize(NULL, size);
155 if (rv == NULL)
156 return NULL;
Guido van Rossum9c52e0f1992-06-03 17:06:14 +0000157
Barry Warsaw8496d391996-12-13 00:11:04 +0000158 if (!(cp = PyString_AsString(rv)))
159 goto finally;
Guido van Rossum9c52e0f1992-06-03 17:06:14 +0000160
161 count = read(self->x_fd, cp, size);
Barry Warsaw8496d391996-12-13 00:11:04 +0000162 if (count < 0) {
163 PyErr_SetFromErrno(SunAudioError);
164 goto finally;
Guido van Rossum9c52e0f1992-06-03 17:06:14 +0000165 }
Barry Warsaw8496d391996-12-13 00:11:04 +0000166#if 0
167 /* TBD: why print this message if you can handle the condition?
Barry Warsaw42185a21997-01-09 22:29:57 +0000168 * assume it's debugging info which we can just as well get rid
169 * of. in any case this message should *not* be using printf!
170 */
Barry Warsaw8496d391996-12-13 00:11:04 +0000171 if (count != size)
172 printf("sunaudio: funny read rv %d wtd %d\n", count, size);
173#endif
Guido van Rossum9c52e0f1992-06-03 17:06:14 +0000174 self->x_icount += count;
175 return rv;
Barry Warsaw8496d391996-12-13 00:11:04 +0000176
177 finally:
178 Py_DECREF(rv);
179 return NULL;
Guido van Rossum9c52e0f1992-06-03 17:06:14 +0000180}
181
Barry Warsaw8496d391996-12-13 00:11:04 +0000182static PyObject *
Guido van Rossum9c52e0f1992-06-03 17:06:14 +0000183sad_write(self, args)
184 sadobject *self;
Barry Warsaw8496d391996-12-13 00:11:04 +0000185 PyObject *args;
Guido van Rossum9c52e0f1992-06-03 17:06:14 +0000186{
187 char *cp;
188 int count, size;
189
Barry Warsaw8496d391996-12-13 00:11:04 +0000190 if (!PyArg_Parse(args, "s#", &cp, &size))
191 return NULL;
Guido van Rossum9c52e0f1992-06-03 17:06:14 +0000192
193 count = write(self->x_fd, cp, size);
Barry Warsaw8496d391996-12-13 00:11:04 +0000194 if (count < 0) {
195 PyErr_SetFromErrno(SunAudioError);
196 return NULL;
Guido van Rossum9c52e0f1992-06-03 17:06:14 +0000197 }
Barry Warsaw8496d391996-12-13 00:11:04 +0000198#if 0
199 if (count != size)
200 printf("sunaudio: funny write rv %d wanted %d\n", count, size);
201#endif
Guido van Rossum9c52e0f1992-06-03 17:06:14 +0000202 self->x_ocount += count;
203
Barry Warsaw8496d391996-12-13 00:11:04 +0000204 Py_INCREF(Py_None);
205 return Py_None;
Guido van Rossum9c52e0f1992-06-03 17:06:14 +0000206}
207
Barry Warsaw8496d391996-12-13 00:11:04 +0000208static PyObject *
Guido van Rossum9c52e0f1992-06-03 17:06:14 +0000209sad_getinfo(self, args)
Barry Warsaw8496d391996-12-13 00:11:04 +0000210 sadobject *self;
211 PyObject *args;
Guido van Rossum9c52e0f1992-06-03 17:06:14 +0000212{
213 sadstatusobject *rv;
214
Barry Warsaw8496d391996-12-13 00:11:04 +0000215 if (!PyArg_Parse(args, ""))
216 return NULL;
Barry Warsaw42185a21997-01-09 22:29:57 +0000217 if (!(rv = sads_alloc()))
218 return NULL;
219
Barry Warsaw8496d391996-12-13 00:11:04 +0000220 if (ioctl(self->x_fd, AUDIO_GETINFO, &rv->ai) < 0) {
221 PyErr_SetFromErrno(SunAudioError);
222 Py_DECREF(rv);
Guido van Rossum9c52e0f1992-06-03 17:06:14 +0000223 return NULL;
224 }
Barry Warsaw8496d391996-12-13 00:11:04 +0000225 return (PyObject *)rv;
Guido van Rossum9c52e0f1992-06-03 17:06:14 +0000226}
227
Barry Warsaw8496d391996-12-13 00:11:04 +0000228static PyObject *
Guido van Rossum9c52e0f1992-06-03 17:06:14 +0000229sad_setinfo(self, arg)
Barry Warsaw8496d391996-12-13 00:11:04 +0000230 sadobject *self;
231 sadstatusobject *arg;
Guido van Rossum9c52e0f1992-06-03 17:06:14 +0000232{
Barry Warsaw8496d391996-12-13 00:11:04 +0000233 if (!is_sadstatusobject(arg)) {
234 PyErr_SetString(PyExc_TypeError,
235 "Must be sun audio status object");
Guido van Rossum9c52e0f1992-06-03 17:06:14 +0000236 return NULL;
237 }
Barry Warsaw8496d391996-12-13 00:11:04 +0000238 if (ioctl(self->x_fd, AUDIO_SETINFO, &arg->ai) < 0) {
239 PyErr_SetFromErrno(SunAudioError);
Guido van Rossum9c52e0f1992-06-03 17:06:14 +0000240 return NULL;
241 }
Barry Warsaw8496d391996-12-13 00:11:04 +0000242 Py_INCREF(Py_None);
243 return Py_None;
Guido van Rossum9c52e0f1992-06-03 17:06:14 +0000244}
245
Barry Warsaw8496d391996-12-13 00:11:04 +0000246static PyObject *
Guido van Rossum9c52e0f1992-06-03 17:06:14 +0000247sad_ibufcount(self, args)
Barry Warsaw8496d391996-12-13 00:11:04 +0000248 sadobject *self;
249 PyObject *args;
Guido van Rossum9c52e0f1992-06-03 17:06:14 +0000250{
Barry Warsaw8496d391996-12-13 00:11:04 +0000251 audio_info_t ai;
Guido van Rossum9c52e0f1992-06-03 17:06:14 +0000252
Barry Warsaw8496d391996-12-13 00:11:04 +0000253 if (!PyArg_Parse(args, ""))
254 return NULL;
255 if (ioctl(self->x_fd, AUDIO_GETINFO, &ai) < 0) {
256 PyErr_SetFromErrno(SunAudioError);
257 return NULL;
258 }
259 return PyInt_FromLong(ai.record.samples - self->x_icount);
Guido van Rossum9c52e0f1992-06-03 17:06:14 +0000260}
261
Barry Warsaw8496d391996-12-13 00:11:04 +0000262static PyObject *
Guido van Rossum9c52e0f1992-06-03 17:06:14 +0000263sad_obufcount(self, args)
Barry Warsaw8496d391996-12-13 00:11:04 +0000264 sadobject *self;
265 PyObject *args;
Guido van Rossum9c52e0f1992-06-03 17:06:14 +0000266{
Barry Warsaw8496d391996-12-13 00:11:04 +0000267 audio_info_t ai;
Guido van Rossum9c52e0f1992-06-03 17:06:14 +0000268
Barry Warsaw8496d391996-12-13 00:11:04 +0000269 if (!PyArg_Parse(args, ""))
270 return NULL;
271 if (ioctl(self->x_fd, AUDIO_GETINFO, &ai) < 0) {
272 PyErr_SetFromErrno(SunAudioError);
273 return NULL;
274 }
Guido van Rossum1e0b19e1997-04-11 15:23:52 +0000275 /* x_ocount is in bytes, wheras play.samples is in frames */
276 /* we want frames */
277 return PyInt_FromLong(self->x_ocount / (ai.play.channels *
278 ai.play.precision / 8) -
279 ai.play.samples);
Guido van Rossum9c52e0f1992-06-03 17:06:14 +0000280}
281
Barry Warsaw8496d391996-12-13 00:11:04 +0000282static PyObject *
Guido van Rossum9c52e0f1992-06-03 17:06:14 +0000283sad_drain(self, args)
Barry Warsaw8496d391996-12-13 00:11:04 +0000284 sadobject *self;
285 PyObject *args;
Guido van Rossum9c52e0f1992-06-03 17:06:14 +0000286{
287
Barry Warsaw8496d391996-12-13 00:11:04 +0000288 if (!PyArg_Parse(args, ""))
289 return NULL;
290 if (ioctl(self->x_fd, AUDIO_DRAIN, 0) < 0) {
291 PyErr_SetFromErrno(SunAudioError);
292 return NULL;
293 }
294 Py_INCREF(Py_None);
295 return Py_None;
Guido van Rossum9c52e0f1992-06-03 17:06:14 +0000296}
297
Sjoerd Mullender66bca321993-12-03 16:54:45 +0000298#ifdef SOLARIS
Barry Warsaw8496d391996-12-13 00:11:04 +0000299static PyObject *
Sjoerd Mullender66bca321993-12-03 16:54:45 +0000300sad_getdev(self, args)
Barry Warsaw8496d391996-12-13 00:11:04 +0000301 sadobject *self;
302 PyObject *args;
Sjoerd Mullender66bca321993-12-03 16:54:45 +0000303{
Barry Warsaw8496d391996-12-13 00:11:04 +0000304 struct audio_device ad;
Sjoerd Mullender66bca321993-12-03 16:54:45 +0000305
Barry Warsaw8496d391996-12-13 00:11:04 +0000306 if (!PyArg_Parse(args, ""))
307 return NULL;
308 if (ioctl(self->x_fd, AUDIO_GETDEV, &ad) < 0) {
309 PyErr_SetFromErrno(SunAudioError);
310 return NULL;
311 }
312 return Py_BuildValue("(sss)", ad.name, ad.version, ad.config);
Sjoerd Mullender66bca321993-12-03 16:54:45 +0000313}
314#endif
315
Barry Warsaw8496d391996-12-13 00:11:04 +0000316static PyObject *
Guido van Rossum234f9421993-06-17 12:35:49 +0000317sad_flush(self, args)
Barry Warsaw8496d391996-12-13 00:11:04 +0000318 sadobject *self;
319 PyObject *args;
Guido van Rossum234f9421993-06-17 12:35:49 +0000320{
321
Barry Warsaw8496d391996-12-13 00:11:04 +0000322 if (!PyArg_Parse(args, ""))
323 return NULL;
324 if (ioctl(self->x_fd, I_FLUSH, FLUSHW) < 0) {
325 PyErr_SetFromErrno(SunAudioError);
326 return NULL;
327 }
328 Py_INCREF(Py_None);
329 return Py_None;
Guido van Rossum234f9421993-06-17 12:35:49 +0000330}
331
Barry Warsaw8496d391996-12-13 00:11:04 +0000332static PyObject *
Guido van Rossum234f9421993-06-17 12:35:49 +0000333sad_close(self, args)
Barry Warsaw8496d391996-12-13 00:11:04 +0000334 sadobject *self;
335 PyObject *args;
Guido van Rossum234f9421993-06-17 12:35:49 +0000336{
337
Barry Warsaw8496d391996-12-13 00:11:04 +0000338 if (!PyArg_Parse(args, ""))
339 return NULL;
340 if (self->x_fd >= 0) {
341 close(self->x_fd);
342 self->x_fd = -1;
343 }
344 Py_INCREF(Py_None);
345 return Py_None;
Guido van Rossum234f9421993-06-17 12:35:49 +0000346}
347
Barry Warsawb0d1b061998-10-31 22:52:54 +0000348static PyObject *
349sad_fileno(self, args)
350 sadobject *self;
351 PyObject *args;
352{
353 if (!PyArg_Parse(args, ""))
354 return NULL;
355
356 return PyInt_FromLong(self->x_fd);
357}
358
359
Barry Warsaw8496d391996-12-13 00:11:04 +0000360static PyMethodDef sad_methods[] = {
361 { "read", (PyCFunction)sad_read },
362 { "write", (PyCFunction)sad_write },
363 { "ibufcount", (PyCFunction)sad_ibufcount },
364 { "obufcount", (PyCFunction)sad_obufcount },
Guido van Rossum9c52e0f1992-06-03 17:06:14 +0000365#define CTL_METHODS 4
Barry Warsaw8496d391996-12-13 00:11:04 +0000366 { "getinfo", (PyCFunction)sad_getinfo },
367 { "setinfo", (PyCFunction)sad_setinfo },
368 { "drain", (PyCFunction)sad_drain },
369 { "flush", (PyCFunction)sad_flush },
Sjoerd Mullender66bca321993-12-03 16:54:45 +0000370#ifdef SOLARIS
Barry Warsaw8496d391996-12-13 00:11:04 +0000371 { "getdev", (PyCFunction)sad_getdev },
Sjoerd Mullender66bca321993-12-03 16:54:45 +0000372#endif
Barry Warsaw8496d391996-12-13 00:11:04 +0000373 { "close", (PyCFunction)sad_close },
Barry Warsawb0d1b061998-10-31 22:52:54 +0000374 { "fileno", (PyCFunction)sad_fileno },
Guido van Rossum9c52e0f1992-06-03 17:06:14 +0000375 {NULL, NULL} /* sentinel */
376};
377
Barry Warsaw8496d391996-12-13 00:11:04 +0000378static PyObject *
Guido van Rossum9c52e0f1992-06-03 17:06:14 +0000379sad_getattr(xp, name)
380 sadobject *xp;
381 char *name;
382{
Barry Warsaw8496d391996-12-13 00:11:04 +0000383 if (xp->x_isctl)
384 return Py_FindMethod(sad_methods+CTL_METHODS,
385 (PyObject *)xp, name);
Guido van Rossum9c52e0f1992-06-03 17:06:14 +0000386 else
Barry Warsaw8496d391996-12-13 00:11:04 +0000387 return Py_FindMethod(sad_methods, (PyObject *)xp, name);
Guido van Rossum9c52e0f1992-06-03 17:06:14 +0000388}
389
390/* ----------------------------------------------------------------- */
391
392static sadstatusobject *
393sads_alloc() {
Guido van Rossumb18618d2000-05-03 23:44:39 +0000394 return PyObject_New(sadstatusobject, &Sadstatustype);
Guido van Rossum9c52e0f1992-06-03 17:06:14 +0000395}
396
397static void
398sads_dealloc(xp)
Barry Warsaw8496d391996-12-13 00:11:04 +0000399 sadstatusobject *xp;
Guido van Rossum9c52e0f1992-06-03 17:06:14 +0000400{
Barry Warsaw8496d391996-12-13 00:11:04 +0000401 PyMem_DEL(xp);
Guido van Rossum9c52e0f1992-06-03 17:06:14 +0000402}
403
404#define OFF(x) offsetof(audio_info_t,x)
405static struct memberlist sads_ml[] = {
406 { "i_sample_rate", T_UINT, OFF(record.sample_rate) },
407 { "i_channels", T_UINT, OFF(record.channels) },
408 { "i_precision", T_UINT, OFF(record.precision) },
409 { "i_encoding", T_UINT, OFF(record.encoding) },
410 { "i_gain", T_UINT, OFF(record.gain) },
411 { "i_port", T_UINT, OFF(record.port) },
412 { "i_samples", T_UINT, OFF(record.samples) },
413 { "i_eof", T_UINT, OFF(record.eof) },
414 { "i_pause", T_UBYTE, OFF(record.pause) },
415 { "i_error", T_UBYTE, OFF(record.error) },
416 { "i_waiting", T_UBYTE, OFF(record.waiting) },
417 { "i_open", T_UBYTE, OFF(record.open) , RO},
418 { "i_active", T_UBYTE, OFF(record.active) , RO},
Sjoerd Mullender66bca321993-12-03 16:54:45 +0000419#ifdef SOLARIS
420 { "i_buffer_size", T_UINT, OFF(record.buffer_size) },
421 { "i_balance", T_UBYTE, OFF(record.balance) },
422 { "i_avail_ports", T_UINT, OFF(record.avail_ports) },
423#endif
Guido van Rossum9c52e0f1992-06-03 17:06:14 +0000424
425 { "o_sample_rate", T_UINT, OFF(play.sample_rate) },
426 { "o_channels", T_UINT, OFF(play.channels) },
427 { "o_precision", T_UINT, OFF(play.precision) },
428 { "o_encoding", T_UINT, OFF(play.encoding) },
429 { "o_gain", T_UINT, OFF(play.gain) },
430 { "o_port", T_UINT, OFF(play.port) },
431 { "o_samples", T_UINT, OFF(play.samples) },
432 { "o_eof", T_UINT, OFF(play.eof) },
433 { "o_pause", T_UBYTE, OFF(play.pause) },
434 { "o_error", T_UBYTE, OFF(play.error) },
435 { "o_waiting", T_UBYTE, OFF(play.waiting) },
436 { "o_open", T_UBYTE, OFF(play.open) , RO},
437 { "o_active", T_UBYTE, OFF(play.active) , RO},
Sjoerd Mullender66bca321993-12-03 16:54:45 +0000438#ifdef SOLARIS
439 { "o_buffer_size", T_UINT, OFF(play.buffer_size) },
440 { "o_balance", T_UBYTE, OFF(play.balance) },
441 { "o_avail_ports", T_UINT, OFF(play.avail_ports) },
442#endif
Guido van Rossum9c52e0f1992-06-03 17:06:14 +0000443
444 { "monitor_gain", T_UINT, OFF(monitor_gain) },
445 { NULL, 0, 0},
446};
447
Barry Warsaw8496d391996-12-13 00:11:04 +0000448static PyObject *
Guido van Rossum9c52e0f1992-06-03 17:06:14 +0000449sads_getattr(xp, name)
Barry Warsaw8496d391996-12-13 00:11:04 +0000450 sadstatusobject *xp;
451 char *name;
Guido van Rossum9c52e0f1992-06-03 17:06:14 +0000452{
Barry Warsaw8496d391996-12-13 00:11:04 +0000453 return PyMember_Get((char *)&xp->ai, sads_ml, name);
Guido van Rossum9c52e0f1992-06-03 17:06:14 +0000454}
455
456static int
457sads_setattr(xp, name, v)
Barry Warsaw8496d391996-12-13 00:11:04 +0000458 sadstatusobject *xp;
459 char *name;
460 PyObject *v;
Guido van Rossum9c52e0f1992-06-03 17:06:14 +0000461{
Guido van Rossum94472a01992-09-04 09:45:18 +0000462
463 if (v == NULL) {
Barry Warsaw8496d391996-12-13 00:11:04 +0000464 PyErr_SetString(PyExc_TypeError,
465 "can't delete sun audio status attributes");
Guido van Rossumf156f501996-09-11 23:31:23 +0000466 return -1;
Guido van Rossum94472a01992-09-04 09:45:18 +0000467 }
Barry Warsaw8496d391996-12-13 00:11:04 +0000468 return PyMember_Set((char *)&xp->ai, sads_ml, name, v);
Guido van Rossum9c52e0f1992-06-03 17:06:14 +0000469}
470
471/* ------------------------------------------------------------------- */
472
473
Barry Warsaw8496d391996-12-13 00:11:04 +0000474static PyTypeObject Sadtype = {
475 PyObject_HEAD_INIT(&PyType_Type)
Guido van Rossumb6775db1994-08-01 11:34:53 +0000476 0, /*ob_size*/
477 "sun_audio_device", /*tp_name*/
478 sizeof(sadobject), /*tp_size*/
479 0, /*tp_itemsize*/
Guido van Rossum9c52e0f1992-06-03 17:06:14 +0000480 /* methods */
Guido van Rossumb6775db1994-08-01 11:34:53 +0000481 (destructor)sad_dealloc, /*tp_dealloc*/
482 0, /*tp_print*/
483 (getattrfunc)sad_getattr, /*tp_getattr*/
484 0, /*tp_setattr*/
485 0, /*tp_compare*/
486 0, /*tp_repr*/
Guido van Rossum9c52e0f1992-06-03 17:06:14 +0000487};
488
Barry Warsaw8496d391996-12-13 00:11:04 +0000489static PyTypeObject Sadstatustype = {
490 PyObject_HEAD_INIT(&PyType_Type)
Guido van Rossum9c52e0f1992-06-03 17:06:14 +0000491 0, /*ob_size*/
492 "sun_audio_device_status", /*tp_name*/
493 sizeof(sadstatusobject), /*tp_size*/
494 0, /*tp_itemsize*/
495 /* methods */
Guido van Rossumb6775db1994-08-01 11:34:53 +0000496 (destructor)sads_dealloc, /*tp_dealloc*/
497 0, /*tp_print*/
498 (getattrfunc)sads_getattr, /*tp_getattr*/
499 (setattrfunc)sads_setattr, /*tp_setattr*/
500 0, /*tp_compare*/
501 0, /*tp_repr*/
Guido van Rossum9c52e0f1992-06-03 17:06:14 +0000502};
503/* ------------------------------------------------------------------- */
504
Barry Warsaw8496d391996-12-13 00:11:04 +0000505static PyObject *
Guido van Rossum9c52e0f1992-06-03 17:06:14 +0000506sadopen(self, args)
Barry Warsaw8496d391996-12-13 00:11:04 +0000507 PyObject *self;
508 PyObject *args;
Guido van Rossum9c52e0f1992-06-03 17:06:14 +0000509{
Barry Warsaw8496d391996-12-13 00:11:04 +0000510 return (PyObject *)newsadobject(args);
Guido van Rossum9c52e0f1992-06-03 17:06:14 +0000511}
512
Barry Warsaw8496d391996-12-13 00:11:04 +0000513static PyMethodDef sunaudiodev_methods[] = {
Guido van Rossum9c52e0f1992-06-03 17:06:14 +0000514 { "open", sadopen },
515 { 0, 0 },
516};
517
518void
Barry Warsaw8496d391996-12-13 00:11:04 +0000519initsunaudiodev()
520{
521 PyObject *m, *d;
Guido van Rossum9c52e0f1992-06-03 17:06:14 +0000522
Barry Warsaw8496d391996-12-13 00:11:04 +0000523 m = Py_InitModule("sunaudiodev", sunaudiodev_methods);
524 d = PyModule_GetDict(m);
Guido van Rossum0cb96de1997-10-01 04:29:29 +0000525 SunAudioError = PyErr_NewException("sunaudiodev.error", NULL, NULL);
Barry Warsaw42185a21997-01-09 22:29:57 +0000526 if (SunAudioError)
527 PyDict_SetItemString(d, "error", SunAudioError);
Guido van Rossum9c52e0f1992-06-03 17:06:14 +0000528}