@@ -8,7 +8,7 @@ namespace audio_tools {
8
8
9
9
/* *
10
10
* @brief Basic I2S API - for the STM32
11
- * Depends on https://github.com/pschatzmann/STM32F411 -i2s-prototype
11
+ * Depends on https://github.com/pschatzmann/stm32f411 -i2s
12
12
* We just add a write and read buffer and pass some parameters to the STM32 API!
13
13
* @author Phil Schatzmann
14
14
* @copyright GPLv3
@@ -27,11 +27,14 @@ class I2SBase {
27
27
28
28
// / starts the DAC with the default config in TX Mode
29
29
bool begin (RxTxMode mode = TX_MODE) {
30
+ TRACED ();
30
31
return begin (defaultConfig (mode));
31
32
}
32
33
33
34
// / starts the DAC
34
35
bool begin (I2SConfig cfg) {
36
+ TRACED ();
37
+ bool result = false ;
35
38
deleteBuffers ();
36
39
37
40
if (cfg.bits_per_sample !=16 ){
@@ -48,27 +51,28 @@ class I2SBase {
48
51
switch (cfg.rx_tx_mode ){
49
52
case RX_MODE:
50
53
p_rx_buffer = new NBuffer<uint8_t >(cfg.buffer_size , cfg.buffer_count );
51
- startI2SReceive (&i2s_stm32, writeFromReceive, cfg.buffer_size );
54
+ result = startI2SReceive (&i2s_stm32, writeFromReceive, cfg.buffer_size );
52
55
break ;
53
56
case TX_MODE:
54
57
p_tx_buffer = new NBuffer<uint8_t >(cfg.buffer_size , cfg.buffer_count );
55
- startI2STransmit (&i2s_stm32, readToTransmit, cfg.buffer_size );
58
+ result = startI2STransmit (&i2s_stm32, readToTransmit, cfg.buffer_size );
56
59
break ;
57
60
case RXTX_MODE:
58
61
p_tx_buffer = new NBuffer<uint8_t >(cfg.buffer_size , cfg.buffer_count );
59
- startI2STransmitReceive (&i2s_stm32, readToTransmit, writeFromReceive, cfg.buffer_size );
62
+ result = startI2STransmitReceive (&i2s_stm32, readToTransmit, writeFromReceive, cfg.buffer_size );
60
63
break ;
61
64
default :
62
65
LOGE (" Unsupported mode" );
63
66
return false ;
64
67
65
68
}
66
69
67
- return true ;
70
+ return result ;
68
71
}
69
72
70
73
// / stops the I2C and unistalls the driver
71
74
void end (){
75
+ TRACED ();
72
76
stopI2S ();
73
77
deleteBuffers ();
74
78
}
@@ -80,42 +84,33 @@ class I2SBase {
80
84
81
85
// / We limit the write size to the buffer size
82
86
int availableForWrite () {
83
- return I2S_BUFFER_COUNT* I2S_BUFFER_SIZE;
87
+ return I2S_BUFFER_SIZE;
84
88
}
85
89
86
90
// / provides the actual configuration
87
91
I2SConfig config () {
88
92
return cfg;
89
93
}
90
94
91
- // / writes the data to the I2S interface
95
+ // / blocking writes for the data to the I2S interface
92
96
size_t writeBytes (const void *src, size_t size_bytes){
97
+ TRACED ();
93
98
size_t result = 0 ;
94
- if (cfg.channels == 2 ){
95
- result = p_tx_buffer->writeArray ((uint8_t *)src, size_bytes);
96
- } else {
97
- // write each sample 2 times
98
- int samples = size_bytes / 2 ;
99
- int16_t *src_16 = (int16_t *)src;
100
- int16_t tmp[2 ];
101
- int result = 0 ;
102
- for (int j=0 ;j<samples;j++){
103
- tmp[0 ]=src_16[j];
104
- tmp[1 ]=src_16[j];
105
- if (p_tx_buffer->availableForWrite ()>=4 ){
106
- p_tx_buffer->writeArray ((uint8_t *)tmp, 4 );
107
- result = j*2 ;
108
- } else {
109
- // abort if the buffer is full
110
- break ;
111
- }
112
- }
99
+ int open = size_bytes;
100
+ while (open>0 ){
101
+ int actual_written = writeBytesExt (src, size_bytes);
102
+ result+= actual_written;
103
+ open -= actual_written;
104
+ if (open>0 ){
105
+ delay (10 );
106
+ }
113
107
}
114
108
return result;
115
109
}
116
110
117
111
size_t readBytes (void *dest, size_t size_bytes){
118
- if (cfg.channels == 2 ){
112
+ TRACED ();
113
+ if (cfg.channels == 2 ){
119
114
return p_rx_buffer->readArray ((uint8_t *)dest, size_bytes);
120
115
} else {
121
116
// combine two channels to 1: so request double the amout
@@ -134,10 +129,12 @@ class I2SBase {
134
129
}
135
130
}
136
131
132
+ // / @brief Callback function used by https://github.com/pschatzmann/stm32f411-i2s
137
133
static void writeFromReceive (uint8_t *buffer, uint16_t byteCount){
138
134
p_rx_buffer->writeArray (buffer, byteCount);
139
135
}
140
136
137
+ // / @brief Callback function used by https://github.com/pschatzmann/stm32f411-i2s
141
138
static void readToTransmit (uint8_t *buffer, uint16_t byteCount) {
142
139
memset (buffer,0 ,byteCount);
143
140
p_tx_buffer->readArray (buffer, byteCount);
@@ -227,7 +224,31 @@ class I2SBase {
227
224
}
228
225
}
229
226
230
-
227
+ size_t writeBytesExt (const void *src, size_t size_bytes){
228
+ size_t result = 0 ;
229
+ if (cfg.channels == 2 ){
230
+ result = p_tx_buffer->writeArray ((uint8_t *)src, size_bytes);
231
+ } else {
232
+ // write each sample 2 times
233
+ int samples = size_bytes / 2 ;
234
+ int16_t *src_16 = (int16_t *)src;
235
+ int16_t tmp[2 ];
236
+ int result = 0 ;
237
+ for (int j=0 ;j<samples;j++){
238
+ tmp[0 ]=src_16[j];
239
+ tmp[1 ]=src_16[j];
240
+ if (p_tx_buffer->availableForWrite ()>=4 ){
241
+ p_tx_buffer->writeArray ((uint8_t *)tmp, 4 );
242
+ result = j*2 ;
243
+ } else {
244
+ // abort if the buffer is full
245
+ break ;
246
+ }
247
+ }
248
+ }
249
+ LOGD (" writeBytesExt: %u" , result)
250
+ return result;
251
+ }
231
252
};
232
253
233
254
}
0 commit comments