]> git.alsa-project.org Git - alsa-python.git/commitdiff
added alsacontrol module (not finished)
authorJaroslav Kysela <perex@perex.cz>
Wed, 11 Jul 2007 08:09:31 +0000 (10:09 +0200)
committerJaroslav Kysela <perex@perex.cz>
Wed, 11 Jul 2007 08:09:31 +0000 (10:09 +0200)
- added more attributes for alsa-lib's simple mixer layer

pyalsa/alsacontrol.c [new file with mode: 0644]
pyalsa/alsahcontrol.c
setup.py

diff --git a/pyalsa/alsacontrol.c b/pyalsa/alsacontrol.c
new file mode 100644 (file)
index 0000000..9bbde53
--- /dev/null
@@ -0,0 +1,250 @@
+/*
+ *  Python binding for the ALSA library - Universal Control Layer
+ *  Copyright (c) 2007 by Jaroslav Kysela <perex@suse.cz>
+ *
+ *
+ *   This library is free software; you can redistribute it and/or modify
+ *   it under the terms of the GNU Lesser General Public License as
+ *   published by the Free Software Foundation; either version 2.1 of
+ *   the License, or (at your option) any later version.
+ *
+ *   This program is distributed in the hope that it will be useful,
+ *   but WITHOUT ANY WARRANTY; without even the implied warranty of
+ *   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ *   GNU Lesser General Public License for more details.
+ *
+ *   You should have received a copy of the GNU Lesser General Public
+ *   License along with this library; if not, write to the Free Software
+ *   Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307 USA
+ *
+ */
+
+#include "Python.h"
+#include "structmember.h"
+#include "frameobject.h"
+#ifndef PY_LONG_LONG
+  #define PY_LONG_LONG LONG_LONG
+#endif
+#include "stdlib.h"
+#include "alsa/asoundlib.h"
+
+#ifndef Py_RETURN_NONE
+#define Py_RETURN_NONE return Py_INCREF(Py_None), Py_None
+#endif
+#ifndef Py_RETURN_TRUE
+#define Py_RETURN_TRUE return Py_INCREF(Py_True), Py_True
+#endif
+#ifndef Py_RETURN_FALSE
+#define Py_RETURN_FALSE return Py_INCREF(Py_False), Py_False
+#endif
+
+static PyObject *module;
+#if 0
+static PyObject *buildin;
+#endif
+
+/*
+ *
+ */
+
+#define PYCTL(v) (((v) == Py_None) ? NULL : \
+       ((struct pyalsacontrol *)(v)))
+
+struct pyalsacontrol {
+       PyObject_HEAD
+       snd_ctl_t *handle;
+};
+
+static inline PyObject *get_bool(int val)
+{
+       if (val) {
+               Py_INCREF(Py_True);
+               return Py_True;
+       } else {
+               Py_INCREF(Py_False);
+               return Py_False;
+       }
+}
+
+PyDoc_STRVAR(cardinfo__doc__,
+"cardInfo() -- Return a dictionary with card specific information.");
+
+static PyObject *
+pyalsacontrol_cardinfo(struct pyalsacontrol *self, PyObject *args)
+{
+       snd_ctl_card_info_t *info;
+       PyObject *d;
+
+       snd_ctl_card_info_alloca(&info);
+       int err = snd_ctl_card_info(self->handle, info);
+       if (err < 0) {
+               PyErr_Format(PyExc_IOError,
+                    "Control card info error: %s", strerror(-err));
+               Py_RETURN_NONE;
+       } else {
+               
+       }
+       d = PyDict_New();
+       if (d) {
+               PyDict_SetItem(d, PyString_FromString("card"), PyInt_FromLong(snd_ctl_card_info_get_card(info)));
+               PyDict_SetItem(d, PyString_FromString("id"), PyString_FromString(snd_ctl_card_info_get_id(info)));
+               PyDict_SetItem(d, PyString_FromString("driver"), PyString_FromString(snd_ctl_card_info_get_driver(info)));
+               PyDict_SetItem(d, PyString_FromString("name"), PyString_FromString(snd_ctl_card_info_get_driver(info)));
+               PyDict_SetItem(d, PyString_FromString("longname"), PyString_FromString(snd_ctl_card_info_get_longname(info)));
+               PyDict_SetItem(d, PyString_FromString("mixername"), PyString_FromString(snd_ctl_card_info_get_mixername(info)));
+               PyDict_SetItem(d, PyString_FromString("components"), PyString_FromString(snd_ctl_card_info_get_components(info)));
+       }
+       return d;
+}
+
+PyDoc_STRVAR(alsacontrolinit__doc__,
+"Control([name='default'],[mode=0])\n"
+"  -- Open an ALSA Control device.\n");
+
+static int
+pyalsacontrol_init(struct pyalsacontrol *pyctl, PyObject *args, PyObject *kwds)
+{
+       char *name = "default";
+       int mode = 0, err;
+
+       static char * kwlist[] = { "name", "mode", NULL };
+
+       pyctl->handle = NULL;
+
+       if (!PyArg_ParseTupleAndKeywords(args, kwds, "|si", kwlist, &name, &mode))
+               return -1;
+
+       err = snd_ctl_open(&pyctl->handle, name, mode);
+       if (err < 0) {
+               PyErr_Format(PyExc_IOError,
+                            "Control open error: %s", strerror(-err));
+               return -1;
+       }
+
+       return 0;
+}
+
+static void
+pyalsacontrol_dealloc(struct pyalsacontrol *self)
+{
+       if (self->handle != NULL)
+               snd_ctl_close(self->handle);
+
+       self->ob_type->tp_free(self);
+}
+
+static PyGetSetDef pyalsacontrol_getseters[] = {
+
+       {NULL}
+};
+
+static PyMethodDef pyalsacontrol_methods[] = {
+
+       {"cardInfo",    (PyCFunction)pyalsacontrol_cardinfo,    METH_NOARGS,    cardinfo__doc__},
+       {NULL}
+};
+
+static PyTypeObject pyalsacontrol_type = {
+       PyObject_HEAD_INIT(0)
+       tp_name:        "alsacontrol.Control",
+       tp_basicsize:   sizeof(struct pyalsacontrol),
+       tp_dealloc:     (destructor)pyalsacontrol_dealloc,
+       tp_flags:       Py_TPFLAGS_DEFAULT | Py_TPFLAGS_BASETYPE,
+       tp_doc:         alsacontrolinit__doc__,
+       tp_getset:      pyalsacontrol_getseters,
+       tp_init:        (initproc)pyalsacontrol_init,
+       tp_alloc:       PyType_GenericAlloc,
+       tp_new:         PyType_GenericNew,
+       tp_free:        PyObject_Del,
+       tp_methods:     pyalsacontrol_methods,
+};
+
+/*
+ *
+ */
+
+static PyMethodDef pyalsacontrolparse_methods[] = {
+       {NULL}
+};
+
+PyMODINIT_FUNC
+initalsacontrol(void)
+{
+       PyObject *d, *d1, *l1, *o;
+       int i;
+
+       if (PyType_Ready(&pyalsacontrol_type) < 0)
+               return;
+
+       module = Py_InitModule3("alsacontrol", pyalsacontrolparse_methods, "libasound control wrapper");
+       if (module == NULL)
+               return;
+
+#if 0
+       buildin = PyImport_AddModule("__buildin__");
+       if (buildin == NULL)
+               return;
+       if (PyObject_SetAttrString(module, "__buildins__", buildin) < 0)
+               return;
+#endif
+
+       Py_INCREF(&pyalsacontrol_type);
+       PyModule_AddObject(module, "Control", (PyObject *)&pyalsacontrol_type);
+
+       d = PyModule_GetDict(module);
+
+       /* ---- */
+
+       d1 = PyDict_New();
+
+#define add_space1(pname, name) { \
+       o = PyInt_FromLong(SND_CTL_ELEM_IFACE_##name); \
+       PyDict_SetItemString(d1, pname, o); \
+       Py_DECREF(o); }
+       
+       add_space1("Card", CARD);
+       add_space1("HwDep", HWDEP);
+       add_space1("Mixer", MIXER);
+       add_space1("PCM", PCM);
+       add_space1("RawMidi", RAWMIDI);
+       add_space1("Timer", TIMER);
+       add_space1("Sequencer", SEQUENCER);
+       add_space1("Last", LAST);
+
+       PyDict_SetItemString(d, "InterfaceId", d1);
+       Py_DECREF(d1);
+
+       /* ---- */
+
+       l1 = PyList_New(0);
+
+       for (i = 0; i <= SND_CTL_ELEM_IFACE_LAST; i++) {
+               o = PyString_FromString(snd_ctl_elem_iface_name(i));
+               PyList_Append(l1, o);
+               Py_DECREF(o);
+       }
+
+       PyDict_SetItemString(d, "InterfaceName", l1);
+       Py_DECREF(l1);
+
+       /* ---- */
+
+       d1 = PyDict_New();
+       
+#define add_space5(pname, name) { \
+       o = PyInt_FromLong(SND_CTL_##name); \
+       PyDict_SetItemString(d1, pname, o); \
+       Py_DECREF(o); }
+       
+       add_space5("NonBlock", NONBLOCK);
+       add_space5("Async", ASYNC);
+       add_space5("ReadOnly", READONLY);
+
+       PyDict_SetItemString(d, "OpenMode", d1);
+       Py_DECREF(d1);
+
+       /* ---- */
+
+       if (PyErr_Occurred())
+               Py_FatalError("Cannot initialize module alsacontrol");
+}
index beb22bd6710fdca21f2335d71e0b730fa8195516..c7387e7a35f47ee9ec359de46d081aac7c3cf353 100644 (file)
@@ -136,6 +136,12 @@ pyalsahcontrol_getcount(struct pyalsahcontrol *self, void *priv)
        return PyLong_FromLong(snd_hctl_get_count(self->handle));
 }
 
+static PyObject *
+pyalsahcontrol_getChctl(struct pyalsahcontrol *self, void *priv)
+{
+       return PyInt_FromLong((long)self->handle);
+}
+
 PyDoc_STRVAR(handlevents__doc__,
 "handleEvents() -- Process waiting hcontrol events (and call appropriate callbacks).");
 
@@ -349,13 +355,13 @@ static int
 pyalsahcontrol_init(struct pyalsahcontrol *pyhctl, PyObject *args, PyObject *kwds)
 {
        char *name = "default";
-       int mode = 0, err;
+       int mode = 0, load = 1, err;
 
-       static char * kwlist[] = { "name", "mode", NULL };
+       static char * kwlist[] = { "name", "mode", "load", NULL };
 
        pyhctl->handle = NULL;
 
-       if (!PyArg_ParseTupleAndKeywords(args, kwds, "|si", kwlist, &name, &mode))
+       if (!PyArg_ParseTupleAndKeywords(args, kwds, "|sii", kwlist, &name, &mode, &load))
                return -1;
 
        err = snd_hctl_open(&pyhctl->handle, name, mode);
@@ -365,13 +371,15 @@ pyalsahcontrol_init(struct pyalsahcontrol *pyhctl, PyObject *args, PyObject *kwd
                return -1;
        }
 
-       err = snd_hctl_load(pyhctl->handle);
-       if (err < 0) {
-               snd_hctl_close(pyhctl->handle);
-               pyhctl->handle = NULL;
-               PyErr_Format(PyExc_IOError,
-                            "HControl load error: %s", strerror(-err));
-               return -1;
+       if (load) {
+               err = snd_hctl_load(pyhctl->handle);
+               if (err < 0) {
+                       snd_hctl_close(pyhctl->handle);
+                       pyhctl->handle = NULL;
+                       PyErr_Format(PyExc_IOError,
+                                    "HControl load error: %s", strerror(-err));
+                       return -1;
+               }
        }
 
        return 0;
@@ -389,6 +397,7 @@ pyalsahcontrol_dealloc(struct pyalsahcontrol *self)
 static PyGetSetDef pyalsahcontrol_getseters[] = {
 
        {"count",       (getter)pyalsahcontrol_getcount,        NULL,   "hcontrol element count",               NULL},
+       {"get_C_hctl",  (getter)pyalsahcontrol_getChctl,        NULL,   "hcontrol C pointer (internal)",        NULL},
 
        {NULL}
 };
@@ -449,6 +458,12 @@ pyalsahcontrolelement_uint(struct pyalsahcontrolelement *pyhelem, void *fcn)
        return PyInt_FromLong(((fcn1)fcn)(pyhelem->elem));
 }
 
+static PyObject *
+pyalsahcontrolelement_getChelem(struct pyalsahcontrolelement *self, void *priv)
+{
+       return PyInt_FromLong((long)self->elem);
+}
+
 PyDoc_STRVAR(elock__doc__,
 "lock() -- Lock this element.\n");
 
@@ -521,6 +536,8 @@ pyalsahcontrolelement_init(struct pyalsahcontrolelement *pyhelem, PyObject *args
        int numid = 0, iface = 0, device = 0, subdevice = 0, index = 0;
        snd_ctl_elem_id_t *id;
        static char *kwlist1[] = { "hctl", "interface", "device", "subdevice", "name", "index" };
+       long helem = 0;
+       float f = 0;
 
        snd_ctl_elem_id_alloca(&id);
        pyhelem->pyhandle = NULL;
@@ -532,7 +549,10 @@ pyalsahcontrolelement_init(struct pyalsahcontrolelement *pyhelem, PyObject *args
                return -1;
        }
        first = PyTuple_GetItem(args, 1);
-       if (PyInt_Check(first)) {
+       if (PyFloat_Check(first)) {
+               if (!PyArg_ParseTuple(args, "Ofi", &hctl, &f, &helem))
+                       return -1;
+       } else if (PyInt_Check(first)) {
                if (!PyArg_ParseTuple(args, "Oi", &hctl, &numid))
                        return -1;
                snd_ctl_elem_id_set_numid(id, numid);
@@ -562,7 +582,8 @@ pyalsahcontrolelement_init(struct pyalsahcontrolelement *pyhelem, PyObject *args
        Py_INCREF(hctl);
        pyhelem->handle = PYHCTL(hctl)->handle;
 
-       pyhelem->elem = snd_hctl_find_elem(pyhelem->handle, id);
+       pyhelem->elem = helem > 0 ? (snd_hctl_elem_t *)helem :
+                               snd_hctl_find_elem(pyhelem->handle, id);
        if (pyhelem->elem == NULL) {
                if (numid == 0)
                        PyErr_Format(PyExc_IOError, "cannot find hcontrol element %i,%i,%i,'%s',%i", iface, device, subdevice, name, index);
@@ -596,6 +617,7 @@ static PyGetSetDef pyalsahcontrolelement_getseters[] = {
        {"subdevice",   (getter)pyalsahcontrolelement_uint,     NULL,   "hcontrol element subdevice",   snd_hctl_elem_get_subdevice},
        {"name",        (getter)pyalsahcontrolelement_getname,  NULL,   "hcontrol element name",        NULL},
        {"index",       (getter)pyalsahcontrolelement_uint,     NULL,   "hcontrol element index",       snd_hctl_elem_get_index},
+       {"get_C_helem", (getter)pyalsahcontrolelement_getChelem, NULL,  "hcontrol element C pointer (internal)", NULL },
        
        {NULL}
 };
index e1f51aa17f9c59a32b099e7712c8207494f0affa..afc5a01c62ce91c7364bddd96d6920451a109dbe 100755 (executable)
--- a/setup.py
+++ b/setup.py
@@ -30,6 +30,11 @@ setup(
                     include_dirs=[],
                     library_dirs=[],
                     libraries=['asound']),
+          Extension('pyalsa.alsacontrol',
+                   ['pyalsa/alsacontrol.c'],
+                    include_dirs=[],
+                    library_dirs=[],
+                    libraries=['asound']),
           Extension('pyalsa.alsahcontrol',
                    ['pyalsa/alsahcontrol.c'],
                     include_dirs=[],