Mercurial > hg > vampy-host
changeset 8:db72f98403b4 lf-numpy-arrays
Working on the code so that it accepts numpy n-dim arrays directly (output of scikits.audiolab). Not working for stereo.
author | luisf <luis.figueira@eecs.qmul.ac.uk> |
---|---|
date | Thu, 14 Mar 2013 11:37:07 +0000 |
parents | d29c25695f5e |
children | 703f52bf8a2e |
files | Makefile vampyhost.cpp vampyhost_test.py |
diffstat | 3 files changed, 114 insertions(+), 80 deletions(-) [+] |
line wrap: on
line diff
--- a/Makefile Tue Mar 12 18:20:06 2013 +0000 +++ b/Makefile Thu Mar 14 11:37:07 2013 +0000 @@ -1,27 +1,25 @@ PY_INCLUDE_PATH := /usr/include/python2.7 -NUMPY_INCLUDE_PATH := /usr/lib/python2.7/site-packages/numpy/core/include +NUMPY_INCLUDE_PATH := /System/Library/Frameworks/Python.framework/Versions/2.7/Extras/lib/python/numpy/core/include CFLAGS := -O2 -fPIC -Wall -I$(PY_INCLUDE_PATH) -I$(NUMPY_INCLUDE_PATH) -I. -CXXFLAGS := -O2 -fPIC -Wall -I$(PY_INCLUDE_PATH) -I$(NUMPY_INCLUDE_PATH) -I. +CXXFLAGS := -O2 -fPIC -Wall -I$(PY_INCLUDE_PATH) -I$(NUMPY_INCLUDE_PATH) -I. -I../vamp-plugin-sdk -LDFLAGS := -shared -lpython2.7 -lvamp-hostsdk +LDFLAGS := -shared -L../vamp-plugin-sdk -lpython2.7 -lvamp-hostsdk #LDFLAGS := -dynamiclib -lpython2.5 /usr/lib/libvamp-hostsdk.a +all: pyRealTime.so vampyhost.so -all: pyRealTime.so vampyhost.so - -pyRealTime.a: pyRealTime.o +pyRealTime.a: pyRealTime.o ar r $@ pyRealTime.o pyRealTime.so: pyRealTime.o - g++ -shared $^ -o $@ $(LDFLAGS) + g++ -shared $^ -o $@ $(LDFLAGS) vampyhost.so: vampyhost.o pyRealTime.a g++ -o $@ -shared $^ $(LDFLAGS) - -clean: +clean: rm *.o rm *.so - rm *.a + rm *.a
--- a/vampyhost.cpp Tue Mar 12 18:20:06 2013 +0000 +++ b/vampyhost.cpp Thu Mar 14 11:37:07 2013 +0000 @@ -483,12 +483,12 @@ vampyhost_process(PyObject *self, PyObject *args) { PyObject *pyPluginHandle; - PyObject *pyBuffer; + PyArrayObject *pyBuffer; PyObject *pyRealTime; if (!PyArg_ParseTuple(args, "OOO", &pyPluginHandle, // C object holding a pointer to a plugin and its descriptor - &pyBuffer, // Audio data + &pyBuffer, // Audio data (NumPy ndim array) &pyRealTime)) { // TimeStamp PyErr_SetString(PyExc_TypeError, "Required: plugin handle, buffer, timestmap."); @@ -502,48 +502,72 @@ Plugin *plugin; if (!getPluginHandle(pyPluginHandle, &plugin, &key)) { - PyErr_SetString(PyExc_AttributeError, - "Invalid or already deleted plugin handle."); - return NULL; + PyErr_SetString(PyExc_AttributeError, + "Invalid or already deleted plugin handle."); + return NULL; } PyPluginDescriptor *pd = (PyPluginDescriptor*) key; if (!pd->isInitialised) { - PyErr_SetString(PyExc_StandardError, - "Plugin has not been initialised."); - return NULL; } + PyErr_SetString(PyExc_StandardError, + "Plugin has not been initialised."); + return NULL; } size_t channels = pd->channels; size_t blockSize = pd->blockSize; - if (!PyList_Check(pyBuffer)) { - PyErr_SetString(PyExc_TypeError, "List of NumPy Array required for process input."); + if (!PyArray_Check(pyBuffer)) { + PyErr_SetString(PyExc_TypeError, "Argument is not a Numpy array."); return NULL; } - if (PyList_GET_SIZE(pyBuffer) != channels) { - std::cerr << "Wrong number of channels: got " << PyList_GET_SIZE(pyBuffer) << ", expected " << channels << std::endl; + if (pyBuffer->nd != channels) { + cerr << "Wrong number of channels: got " << pyBuffer->nd << ", expected " << channels << endl; PyErr_SetString(PyExc_TypeError, "Wrong number of channels"); return NULL; } + int n = pyBuffer->dimensions[0]; + int m = pyBuffer->dimensions[1]; + + cout << "Kind :" << pyBuffer->descr->kind << endl; + cout << "Strides 0 :" << pyBuffer->strides[0] << endl; + cout << "Strides 1 :" << pyBuffer->strides[1] << endl; + cout << "Flags:" << pyBuffer->flags << endl; + float **inbuf = new float *[channels]; + cout << "Created inbuf with #channels: " << channels << endl; for (int c = 0; c < channels; ++c) { - PyObject *cbuf = PyList_GET_ITEM(pyBuffer, c); - inbuf[c] = pyArrayToFloatArray(cbuf); + + // cout << "[Host] Converting channel #" << c << endl; + // PyObject *cbuf = PyList_GET_ITEM(pyBuffer, c); + // cout << "Ok1..." << endl; + // inbuf[c] = pyArrayToFloatArray(cbuf); + + inbuf[c] = pyArrayToFloatArray((PyObject*) pyBuffer); + + cout << "Ok2..." << endl; + if (!inbuf[c]) { PyErr_SetString(PyExc_TypeError,"NumPy Array required for each channel in process input."); return NULL; } + + cout << "[Host] Converted channel #" << c << endl; + } RealTime timeStamp = *PyRealTime_AsPointer(pyRealTime); + cout << "[Host] Gonna call plugin->process" << endl; + //Call process and store the output pd->output = plugin->process(inbuf, timeStamp); + cout << "[Host] Called plugin->process" << endl; + /* TODO: DO SOMETHONG WITH THE FEATURE SET HERE */ /// convert to appropriate python objects, reuse types and conversion utilities from Vampy ... @@ -553,8 +577,11 @@ } delete[] inbuf; + + + + return NULL; //!!! Need to return actual features! - } /* GET / SET OUTPUT */ @@ -706,6 +733,9 @@ m = Py_InitModule3("vampyhost", vampyhost_methods, module_doc); if (m == NULL) return; + // Numpy array library initialization function + import_array(); + // PyModule_AddObject(m, "realtime", (PyObject *)&RealTime_Type); }
--- a/vampyhost_test.py Tue Mar 12 18:20:06 2013 +0000 +++ b/vampyhost_test.py Thu Mar 14 11:37:07 2013 +0000 @@ -1,57 +1,55 @@ - import sys import os sys.path.append(os.getcwd()) -import scikits.audiolab as al; +import numpy as np +print np.__version__ + +import matplotlib.pyplot as plt +import scikits.audiolab as al + +import vampyhost as vh #from melscale import melscale #from melscale import initialize -from pylab import * # from melscale import * -from numpy import * -from pylab import * -from time import * - -from vampyhost import * -import vampyhost -import vampyhost as vh #import pyRealTime -#from pyRealTime import * #deal with an audio file -wavfile='test.wav' +wavfile = 'test-mono.wav' +# wavfile = '4sample-stereo-ny.wav' -wavdata, samplerate, format = al.wavread(wavfile); +af = al.Sndfile(wavfile) -print "samplerate: ",samplerate -print "number of samples (frames): ",wavdata.size +nchannels = af.channels -audio = wavdata.transpose() +print "Samplerate: ", af.samplerate +print "Number of channels: ", nchannels +print "Number of samples (frames): ", af.nframes -channels = audio.size -print "channels: ",channels - -rt=realtime(4,70) +rt = vh.realtime(4, 70) #test RealTime Object -for i in [0,1,2] : - if (i==0) : rtl=[] - rtl.append(realtime()) - print ">>>>>RealTime's method: ", rtl[i].values() +for i in [0, 1, 2]: + if i == 0: + rtl = [] + rtl.append(vh.realtime()) + print ">>>>>RealTime's method: ", rtl[i].values() class feature_example(): - def __init__(self): - self.hasTimestamp - self.timestamp - self.values - self.label + def __init__(self): + self.hasTimestamp + self.timestamp + self.values + self.label pluginlist = vh.enumeratePlugins() -for i,n in enumerate(pluginlist) : print i,":",n -pluginKey=pluginlist[0]; # try the first plugin listed +for i, n in enumerate(pluginlist): + print i, ":", n + +pluginKey = pluginlist[0] # try the first plugin listed retval = vh.getLibraryPath(pluginKey) print pluginKey @@ -59,40 +57,48 @@ print vh.getPluginCategory(pluginKey) print vh.getOutputList(pluginKey) -handle = vh.loadPlugin(pluginKey,samplerate); -print "\n\nPlugin handle: ",handle +handle = vh.loadPlugin(pluginKey, af.samplerate) -print "Output list of: ",pluginKey,"\n",vh.getOutputList(handle) -print "Have ", len(audio), " channels in audio" -#initialise: pluginhandle, channels, stepSize, blockSize -if vh.initialise(handle,len(audio),1024,1024): - print "Initialise succeeded" +print "\n\nPlugin handle: ", handle +print "Output list of: ", pluginKey, "\n", vh.getOutputList(handle) + +# initialise: pluginhandle, channels, stepSize, blockSize +if vh.initialise(handle, nchannels, 1024, 1024): + print "Initialise succeeded" else: - print "Initialise failed!" - exit(1) + print "Initialise failed!" + exit(1) -#!!! continue with this lark +# should return a realtime object +rt = vh.frame2RealTime(100000, 22050) +print rt -rt=frame2RealTime(100000,22050) -print type(rt) +assert type(rt) == type(vh.realtime()) -out=vh.process(handle,list(audio),rt) ##!!! cast to list should not be necessary -output = vh.getOutput(handle,1); +audio = af.read_frames(af.nframes) +audio = np.transpose(audio) + +print "Gonna send", len(audio) + +out = vh.process(handle, audio, rt) +print "OKEYDOKEY: Processed" + +output = vh.getOutput(handle, 1) print type(output) print output #print output[1].label -print "_______________OUTPUT TYPE_________:",type(out) -in_audio = frombuffer(audio,int16,-1,0) -out_audio = frombuffer(out,float32,-1,0) -subplot(211) -plot(in_audio) -subplot(212) -plot(out_audio) +print "_______________OUTPUT TYPE_________:", type(out) +in_audio = np.frombuffer(audio, np.int16, -1, 0) +out_audio = np.frombuffer(out, np.float32, -1, 0) +plt.subplot(211) +plt.plot(in_audio) +plt.subplot(212) +plt.plot(out_audio) -show() +plt.show() #do some processing here #buffer is a multichannel frame or a numpy array containing samples @@ -102,8 +108,8 @@ #output is a list of list of features -vh.unloadPlugin(handle); -vh.unloadPlugin(handle); # test if it chrashes... +vh.unloadPlugin(handle) +vh.unloadPlugin(handle) # test if it chrashes... print vh.getOutputList(handle)