2 Copyright (C) 2013 Matt Flax <flatmax@flatmax.org>
4 This program is free software; you can redistribute it and/or modify
5 it under the terms of the GNU General Public License as published by
6 the Free Software Foundation; either version 2 of the License, or
7 (at your option) any later version.
9 This program is distributed in the hope that it will be useful,
10 but WITHOUT ANY WARRANTY; without even the implied warranty of
11 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
12 GNU General Public License for more details.
14 You should have received a copy of the GNU General Public License
15 along with this program; if not, write to the Free Software
16 Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
20 #include "JackIIODriver.h"
21 #include "driver_interface.h"
22 #include "JackEngineControl.h"
23 #include "JackGraphManager.h"
27 #define IIO_DEFAULT_CHIP "AD7476A" ///< The default IIO recording chip to look for.
28 #define IIO_DEFAULT_READ_FS 1.e6 ///< The default IIO sample rate for the default chip.
29 #define IIO_DEFAULT_PERIOD_SIZE 2048 ///< The default period size is in the ms range
30 #define IIO_DEFAULT_PERIOD_COUNT 2 ///< The default number of periods
31 #define IIO_DEFAULT_CAPUTURE_PORT_COUNT MAXINT ///< The default number of capture ports is exceedingly big, trimmed down to a realistic size in driver_initialize
32 //#define IIO_SAFETY_FACTOR 2./3. ///< The default safety factor, allow consumption of this fraction of the available DMA buffer before we don't allow the driver to continue.
33 #define IIO_SAFETY_FACTOR 1. ///< The default safety factor, allow consumption of this fraction of the available DMA buffer before we don't allow the driver to continue.
37 int JackIIODriver::Open(jack_nframes_t buffer_size
, jack_nframes_t samplerate
, bool capturing
, bool playing
, int inchannels
, int outchannels
, bool monitor
, const char* capture_driver_name
, const char* playback_driver_name
, jack_nframes_t capture_latency
, jack_nframes_t playback_latency
) {
38 //cout<<"JackIIODriver::Open\n";
40 int ret
=JackAudioDriver::Open(buffer_size
, samplerate
, capturing
, playing
, inchannels
, outchannels
, monitor
, capture_driver_name
, playback_driver_name
, capture_latency
, playback_latency
);
41 if (ret
!=NO_ERROR
) // check whether the JackAudioDriver opened OK
43 ret
=iio
.enable(true); // start the DMA
47 int JackIIODriver::Close() {
48 //cout<<"JackIIODriver::Close\n";
49 iio
.enable(false); // stop the DMA
50 return JackAudioDriver::Close();
53 int JackIIODriver::Read() {
54 //cout<<"JackIIODriver::Read\n";
56 if (iio
.getDeviceCnt()<1) {
57 jack_error("JackIIODriver:: No IIO devices are present ");
60 uint devChCnt
=iio
[0].getChCnt(); // the number of channels per device
62 jack_nframes_t nframes
=data
.rows()/devChCnt
;
64 // This is left here for future debugging.
65 // if (nframes != fEngineControl->fBufferSize)
66 // jack_error("JackIIODriver::Read warning : Jack period size = %ld IIO period size = %ld", fEngineControl->fBufferSize, nframes);
67 // cout<<"processing buffer size : "<<fEngineControl->fBufferSize<<endl;
68 // cout<<"processing channel count : "<<fCaptureChannels<<endl;
70 int ret
=iio
.read(nframes
, data
); // read the data from the IIO subsystem
75 // Keep begin cycle time
76 JackDriver::CycleTakeBeginTime(); // is this necessary ?
78 jack_default_audio_sample_t scaleFactor
=1./32768.;
80 // This is left in for future debugging.
81 //int maxAvailChCnt=data.cols()*devChCnt;
82 // if (fCaptureChannels>maxAvailChCnt)
83 // jack_error("JackIIODriver::Read warning : Jack capture ch. cnt = %ld IIO capture ch. cnt = %ld", fCaptureChannels, maxAvailChCnt);
85 for (int i
= 0; i
< fCaptureChannels
; i
++) {
86 int col
=i
/devChCnt
; // find the column and offset to read from
87 int rowOffset
=i
%devChCnt
;
88 if (fGraphManager
->GetConnectionsNum(fCapturePortList
[i
]) > 0) {
89 jack_default_audio_sample_t
*dest
=GetInputBuffer(i
);
91 for (jack_nframes_t j
=0; j
<nframes
; j
++)
92 dest
[j
]=(jack_default_audio_sample_t
)(data(j
*devChCnt
+rowOffset
, col
))*scaleFactor
;
99 int JackIIODriver::Write() {
100 // cout<<"JackIIODriver::Write\n";
101 JackDriver::CycleTakeEndTime(); // is this necessary ?
105 } // end namespace Jack
113 SERVER_EXPORT
const jack_driver_desc_t
*
114 driver_get_descriptor () {
115 jack_driver_desc_t
* desc
;
116 jack_driver_desc_filler_t filler
;
117 jack_driver_param_value_t value
;
119 desc
= jack_driver_descriptor_construct("iio", JackDriverMaster
, "Linux Industrial IO backend", &filler
);
121 strcpy(value
.str
, IIO_DEFAULT_CHIP
);
122 jack_driver_descriptor_add_parameter(desc
, &filler
, "chip", 'C', JackDriverParamString
, &value
, NULL
, "The name of the chip to search for in the IIO devices", NULL
);
124 value
.ui
= IIO_DEFAULT_CAPUTURE_PORT_COUNT
;
125 jack_driver_descriptor_add_parameter(desc
, &filler
, "capture", 'i', JackDriverParamUInt
, &value
, NULL
, "Provide capture count (block size).", NULL
);
127 value
.ui
= IIO_DEFAULT_PERIOD_SIZE
;
128 jack_driver_descriptor_add_parameter(desc
, &filler
, "period", 'p', JackDriverParamUInt
, &value
, NULL
, "Frames (samples per channel) per period", NULL
);
130 value
.ui
= IIO_DEFAULT_PERIOD_COUNT
;
131 jack_driver_descriptor_add_parameter(desc
, &filler
, "nperiods", 'n', JackDriverParamUInt
, &value
, NULL
, "Number of available periods (block count)", NULL
);
136 SERVER_EXPORT
Jack::JackDriverClientInterface
* driver_initialize(Jack::JackLockedEngine
* engine
, Jack::JackSynchro
* table
, const JSList
* params
) {
138 // As of this implementation the IIO driver is only capture... to be expanded.
140 Jack::JackDriverClientInterface
* threaded_driver
=NULL
;
142 string
chipName(IIO_DEFAULT_CHIP
); // the default chip name to search for in the IIO devices.
143 float fs
= IIO_DEFAULT_READ_FS
; // IIO sample rate is fixed.
144 jack_nframes_t periodSize
= IIO_DEFAULT_PERIOD_SIZE
; // default block size
145 jack_nframes_t periodCount
= IIO_DEFAULT_PERIOD_COUNT
; // default block count
146 uint inChCnt
= IIO_DEFAULT_CAPUTURE_PORT_COUNT
; // The default number of physical input channels - a very large number, to be reduced.
148 for (const JSList
*node
= params
; node
; node
= jack_slist_next (node
)) {
149 jack_driver_param_t
*param
= (jack_driver_param_t
*) node
->data
;
151 switch (param
->character
) {
152 case 'C': // we are specifying a new chip name
153 chipName
= param
->value
.str
;
155 case 'i': // we are specifying the number of capture channels
156 inChCnt
= param
->value
.ui
;
159 periodSize
= param
->value
.ui
;
162 periodCount
= param
->value
.ui
;
167 // create the driver which contains the IIO class
168 Jack::JackIIODriver
* iio_driver
= new Jack::JackIIODriver("system", "iio_pcm", engine
, table
);
170 jack_error("\nHave you run out of memory ? I tried to create the IIO driver in memory but failed!\n");
174 // interrogate the available iio devices searching for the chip name
175 if (iio_driver
->iio
.findDevicesByChipName(chipName
)!=NO_ERROR
) { // find all devices with a particular chip which are present.
176 jack_error("\nThe iio driver found no devices by the name %s\n", chipName
.c_str());
180 if (iio_driver
->iio
.getDeviceCnt()<1) { // If there are no devices found by that chip name, then indicate.
181 jack_error("\nThe iio driver found no devices by the name %s\n", chipName
.c_str());
185 iio_driver
->iio
.printInfo(); // print out detail about the devices which were found ...
187 // if the available number of ports is less then the requested number, then restrict to the number of physical ports.
188 if (iio_driver
->iio
.getChCnt()<inChCnt
)
189 inChCnt
=iio_driver
->iio
.getChCnt();
191 // resize the data buffer column count to match the device count
192 colCnt
=(int)ceil((float)inChCnt
/(float)iio_driver
->iio
[0].getChCnt()); // check whether we require less then the available number of channels
193 ret
=iio_driver
->iio
.getReadArray(periodSize
, iio_driver
->data
); // resize the array to be able to read enough memory
195 jack_error("iio::getReadArray couldn't create the data buffer, indicating the problem.");
198 if (iio_driver
->data
.cols()>colCnt
) // resize the data columns to match the specified number of columns (channels / channels per device)
199 iio_driver
->data
.resize(iio_driver
->data
.rows(), colCnt
);
201 ret
=iio_driver
->iio
.open(periodCount
, periodSize
); // try to open all IIO devices
205 threaded_driver
= new Jack::JackThreadedDriver(iio_driver
);
206 if (threaded_driver
) {
207 bool capture
=true, playback
=false, monitor
=false;
209 jack_nframes_t inputLatency
= periodSize
*periodCount
, outputLatency
=0;
210 // Special open for OSS driver...
211 if (iio_driver
->Open(periodSize
, (jack_nframes_t
)fs
, capture
, playback
, inChCnt
, outChCnt
, monitor
, "iio:device", "iio:device", inputLatency
, outputLatency
)!=0) {
212 delete threaded_driver
;
217 jack_error("\nHave you run out of memory ? I tried to create Jack's standard threaded driver in memory but failed! The good news is that you had enough memory to create the IIO driver.\n");
219 return threaded_driver
;
221 initError
: // error during initialisation, delete and return NULL