1 /*----------------------------------------------------------------------------
2 ChucK Concurrent, On-the-fly Audio Programming Language
3 Compiler and Virtual Machine
5 Copyright (c) 2004 Ge Wang and Perry R. Cook. All rights reserved.
6 http://chuck.cs.princeton.edu/
7 http://soundlab.cs.princeton.edu/
9 This program is free software; you can redistribute it and/or modify
10 it under the terms of the GNU General Public License as published by
11 the Free Software Foundation; either version 2 of the License, or
12 (at your option) any later version.
14 This program is distributed in the hope that it will be useful,
15 but WITHOUT ANY WARRANTY; without even the implied warranty of
16 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
17 GNU General Public License for more details.
19 You should have received a copy of the GNU General Public License
20 along with this program; if not, write to the Free Software
21 Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307
23 -----------------------------------------------------------------------------*/
25 //-----------------------------------------------------------------------------
26 // name: digiio_rtaudio.h
27 // desc: digitalio over RtAudio (from Gary Scavone)
29 // author: Ge Wang (gewang@cs.princeton.edu)
30 // Perry R. Cook (prc@cs.princeton.edu)
32 //-----------------------------------------------------------------------------
33 #ifndef __DIGITAL_IO_H__
34 #define __DIGITAL_IO_H__
36 #include "chuck_def.h"
41 //-----------------------------------------------------------------------------
42 // define and forward references
43 //-----------------------------------------------------------------------------
44 // #ifndef SAFE_DELETE
45 // #define SAFE_DELETE(p) { if(p) { delete (p); (p)=NULL; } }
46 // #define SAFE_DELETE_ARRAY(p) { if(p) { delete[] (p); (p)=NULL; } }
50 #if defined(__MACOSX_CORE__)
51 #define BUFFER_SIZE_DEFAULT 256
53 #define BUFFER_SIZE_DEFAULT 512
55 #define NUM_BUFFERS_DEFAULT 8
56 #define NUM_CHANNELS_DEFAULT 2 // number of channels
57 #if defined(__LINUX_ALSA__ ) || defined(__LINUX_OSS__) || defined(__LINUX_JACK__)
58 #define SAMPLING_RATE_DEFAULT 48000 // sampling rate
59 #define USE_CB_DEFAULT TRUE // callback
61 #define SAMPLING_RATE_DEFAULT 44100 // sampling rate
62 #define USE_CB_DEFAULT TRUE // callback
64 #define BITS_PER_SAMPLE_DEFAULT 16 // sample size
65 #define DEVICE_NUM_OUT_DEFAULT 0
66 #define DEVICE_NUM_IN_DEFAULT 0
69 // #define SAMPLE_SHORT short
70 // #define SAMPLE_INTERNAL SAMPLE_SHORT
71 // #define SAMPLE float
72 // #define S_MAX 0x7fff // max value for 16 bit
73 // #define S_MIN -0x7fff // min value for 16 bit
75 // external to internal sample conversion
76 // #define SAMPLE_TO_INTERNAL(s) ( (SAMPLE_INTERNAL)((SAMPLE)S_MAX * s) )
77 // #define INTERNAL_TO_SAMPLE(s) ( (SAMPLE)((SAMPLE)s / S_MAX) )
80 #define BOOL__ DWORD__
81 #define DWORD__ unsigned long
83 #define UINT__ DWORD__
84 #define BYTE__ unsigned char
100 //-----------------------------------------------------------------------------
103 //-----------------------------------------------------------------------------
107 static BOOL__
initialize( DWORD__ num_dac_channels
= NUM_CHANNELS_DEFAULT
,
108 DWORD__ num_adc_channels
= NUM_CHANNELS_DEFAULT
,
109 DWORD__ sampling_rate
= SAMPLING_RATE_DEFAULT
,
110 DWORD__ bps
= BITS_PER_SAMPLE_DEFAULT
,
111 DWORD__ buffer_size
= BUFFER_SIZE_DEFAULT
,
112 DWORD__ num_buffers
= NUM_BUFFERS_DEFAULT
,
113 DWORD__ block
= TRUE
,
114 Chuck_VM
* vm_ref
= NULL
,
115 BOOL__ rt_audio
= TRUE
,
116 void * callback
= NULL
, void * data
= NULL
);
117 static BOOL__
watchdog_start();
118 static BOOL__
watchdog_stop();
119 static void shutdown();
123 static DWORD__
sampling_rate( ) { return m_sampling_rate
; }
124 static DWORD__
num_channels_out( ) { return m_num_channels_out
; }
125 static DWORD__
num_channels_in( ) { return m_num_channels_in
; }
126 static DWORD__
bps( ) { return m_bps
; }
127 static DWORD__
buffer_size( ) { return m_buffer_size
; }
128 static DWORD__
num_buffers( ) { return m_num_buffers
; }
129 static RtAudio
* audio( ) { return m_rtaudio
; }
130 static BOOL__
start( );
131 static BOOL__
stop( );
132 static BOOL__
tick( );
133 static void set_extern( SAMPLE
* in
, SAMPLE
* out
)
134 { m_extern_in
= in
; m_extern_out
= out
; }
135 static int cb( char * buffer
, int buffer_size
, void * user_data
);
136 static int cb2( char * buffer
, int buffer_size
, void * user_data
);
139 static BOOL__ m_init
;
140 static DWORD__ m_start
;
141 static DWORD__ m_tick_count
;
142 static DWORD__ m_num_channels_out
;
143 static DWORD__ m_num_channels_in
;
144 static DWORD__ m_sampling_rate
;
145 static DWORD__ m_bps
;
146 static DWORD__ m_buffer_size
;
147 static DWORD__ m_num_buffers
;
148 static RtAudio
* m_rtaudio
;
149 static SAMPLE
* m_buffer_out
;
150 static SAMPLE
* m_buffer_in
;
151 static SAMPLE
** m_write_ptr
;
152 static SAMPLE
** m_read_ptr
;
153 static SAMPLE
* m_extern_in
;
154 static SAMPLE
* m_extern_out
;
155 static BOOL__ m_out_ready
;
156 static BOOL__ m_in_ready
;
157 static BOOL__ m_use_cb
;
159 static DWORD__ m_end
;
160 static DWORD__ m_block
;
161 static DWORD__ m_xrun
;
163 static DWORD__ m_dac_n
;
164 static DWORD__ m_adc_n
;
170 //-----------------------------------------------------------------------------
173 //-----------------------------------------------------------------------------
177 virtual ~TickOut() {}
180 virtual BOOL__
reset() { return true; }
181 virtual BOOL__
tick_out( SAMPLE s
) = 0;
182 virtual BOOL__
tick_out( SAMPLE l
, SAMPLE r
) = 0;
183 virtual BOOL__
tick_out( const SAMPLE
* out
, DWORD__ n
) = 0;
189 //-----------------------------------------------------------------------------
192 //-----------------------------------------------------------------------------
196 virtual ~TickIn() { }
199 virtual BOOL__
reset() { return true; }
201 virtual BOOL__
tick_in( SAMPLE
* in
) = 0;
202 virtual BOOL__
tick_in( SAMPLE
* l
, SAMPLE
* r
) = 0;
203 virtual BOOL__
tick_in( SAMPLE
* in
, DWORD__ n
) = 0;
205 virtual SAMPLE
tick( )
206 { SAMPLE in
; return ( tick_in( &in
) ? in
: (SAMPLE
)0.0f
); }
212 //-----------------------------------------------------------------------------
213 // name: class DigitalOut
215 //-----------------------------------------------------------------------------
216 class DigitalOut
: public TickOut
230 virtual BOOL__
tick_out( SAMPLE s
);
231 virtual BOOL__
tick_out( SAMPLE l
, SAMPLE r
);
232 virtual BOOL__
tick_out( const SAMPLE
* samples
, DWORD__ n
);
238 SAMPLE
* m_data_ptr_out
;
239 SAMPLE
* m_data_max_out
;
241 inline BOOL__
prepare_tick_out();
247 //-----------------------------------------------------------------------------
248 // name: class DigitalIn
250 //-----------------------------------------------------------------------------
251 class DigitalIn
: public TickIn
265 virtual BOOL__
tick_in( SAMPLE
* s
);
266 virtual BOOL__
tick_in( SAMPLE
* l
, SAMPLE
* r
);
267 virtual BOOL__
tick_in( SAMPLE
* samples
, DWORD__ n
);
274 SAMPLE
* m_data_ptr_in
;
275 SAMPLE
* m_data_max_in
;
277 inline BOOL__
prepare_tick_in();
283 //-----------------------------------------------------------------------------
284 // name: AudioBufferX
286 //-----------------------------------------------------------------------------
290 AudioBufferX( DWORD__ size
= 0 );
293 BOOL__
initialize( DWORD__ size
);
309 //-----------------------------------------------------------------------------
310 // name: AudioBufferIn
312 //-----------------------------------------------------------------------------
313 class AudioBufferIn
: public TickIn
, public AudioBufferX
316 AudioBufferIn( DWORD__ size
= 0 );
317 virtual ~AudioBufferIn();
320 virtual BOOL__
reset();
321 virtual BOOL__
tick_in( SAMPLE
* in
);
322 virtual BOOL__
tick_in( SAMPLE
* l
, SAMPLE
* r
);
323 virtual BOOL__
tick_in( SAMPLE
* in
, DWORD__ n
);
329 //-----------------------------------------------------------------------------
330 // name: AudioBufferOut
332 //-----------------------------------------------------------------------------
333 class AudioBufferOut
: public TickOut
, public AudioBufferX
336 AudioBufferOut( DWORD__ size
= 0 );
337 virtual ~AudioBufferOut();
340 virtual BOOL__
reset();
341 virtual BOOL__
tick_out( SAMPLE s
);
342 virtual BOOL__
tick_out( SAMPLE l
, SAMPLE r
);
343 virtual BOOL__
tick_out( const SAMPLE
* out
, DWORD__ n
);