arduino-audio-tools
Loading...
Searching...
No Matches
USBAudioDeviceESP32.h
Go to the documentation of this file.
1#pragma once
2#include <Arduino.h>
3
4#ifdef ESP32
5
6#if ARDUINO_USB_CDC_ON_BOOT
7#error USB Audio is only available in OTG mode, not CDC-on-boot mode
8#else
9
10#include <USB.h>
11
12#include <cstring>
13
17#include "esp32-hal-tinyusb.h"
18
19namespace audio_tools {
20
21class Emulated_TinyUSB;
22
56 friend class Emulated_TinyUSB;
57
58 public:
61
62 // ── ESP32 descriptor callback
63 // ───────────────────────────────────────────────
64 // Called by the arduino-esp32 framework when it builds the configuration
65 // descriptor. The callback reads the current descriptor at call time, so any
66 // format change callback reads the current descriptor at call time, so any
67 // format change made via setConfig() before re-enumeration is picked up
68 // automatically without re-registering the interface.
69
70 static uint16_t descriptorCallback(uint8_t* dst, uint8_t* itf) {
71 auto& dev = getActualInstance();
72 // *itf carries the running interface index: set our base from it so that
73 // composite configurations (e.g. CDC + Audio) get non-overlapping
74 // numbers.
75 if (itf) dev.config_.itf_num_ac = *itf;
76 uint16_t len = dev.getDescriptor(dst);
77 if (itf) *itf += dev.numInterfaces();
78 return len;
79 }
80
85
86 bool setupUSB() {
87 if (setup_called) return true;
88 setup_called = true;
89 USB.VID(config_.vid);
90 USB.PID(config_.pid);
91 USB.productName(config_.product);
92 USB.manufacturerName(config_.manufacturer);
93 USB.serialNumber(config_.serial);
94 USB.usbClass(TUSB_CLASS_MISC);
95 USB.usbSubClass(MISC_SUBCLASS_COMMON);
96 USB.usbProtocol(MISC_PROTOCOL_IAD);
97 USB.usbAttributes(
98 (uint8_t)(0x80u | (config_.self_powered ? 0x40u : 0x00u)));
99 USB.usbPower(config_.max_power_ma);
101 static uint8_t desc[USB_DESCR_MAX_LEN];
102 uint16_t audio_len = getDescriptor(desc);
103 assert(audio_len <= USB_DESCR_MAX_LEN);
104 tinyusb_enable_interface(USB_INTERFACE_AUDIO, audio_len,
106 return true;
107 }
108
111
114
116 int getActualCore() const override { return xPortGetCoreID();}
117
121 void serviceUSB() override {}
122
123
124 protected:
126 USBAudioBackend& backend() override { return backend_impl_; }
127
142 if (config_.enable_ep_in) {
144 } else if (isFeedbackEpEnabled()) {
146 }
149 }
152 }
153 }
154
155 static int16_t allocInEndpoint() {
156 uint8_t n = tinyusb_get_free_in_endpoint();
157 if (n == 0) {
158 LOGE("No free USB IN endpoint available");
159 return -1;
160 }
161 return (int16_t)(0x80u | n);
162 }
163
164 static int16_t allocOutEndpoint() {
165 uint8_t n = tinyusb_get_free_out_endpoint();
166 if (n == 0) {
167 LOGE("No free USB OUT endpoint available");
168 return -1;
169 }
170 return (int16_t)n;
171 }
172
173
176 void resizeBuffers() override {
177 uint16_t block_sz = packetSize();
178 uint8_t block_cnt = config_.fifo_packets;
179 if (isEpInEnabled()) buffer_tx_.resize(block_sz * block_cnt);
180 if (isEpOutEnabled()) buffer_rx_.resize(block_sz * block_cnt);
181 }
182
190 bool beginUSB() override {
191 if (begin_called) return true;
192 setupUSB();
193 bool rc = true;
194 if (config_.begin_usb) {
195 begin_called = true;
196 rc = USB.begin();
197 }
198 return rc;
199 }
200
201 bool begin_called = false;
202 bool setup_called = false;
203 // Block-pool buffers with FreeRTOS queues for cross-core safety.
204 // TX: writeMaxWait=5ms (copier blocks briefly for free block),
205 // readMaxWait=0 (xfer_cb never blocks).
206 // RX: writeMaxWait=0 (xfer_cb never blocks),
207 // readMaxWait=0 (sketch polls via copier, never blocks).
208 // SynchronizedNBufferRTOS buffer_tx_{0, 0, 5, 0};
209 // SynchronizedNBufferRTOS buffer_rx_{0, 0, 0, 0};
210
211 // size_t streamBufferSize, size_t xTriggerLevel = 1 TickType_t writeMaxWait
212 // = portMAX_DELAY, TickType_t readMaxWait = portMAX_DELAY,
215};
216
224 public:
225 bool isInitialized() { return tud_inited(); }
226 bool begin(int) { return true; }
227 bool mounted(void) {
228 if (!device().begin_called) return true;
229 return tud_mounted();
230 }
231 bool suspended(void) { return tud_suspended(); }
232 bool ready(void) { return tud_ready(); }
233 bool remoteWakeup(void) { return tud_remote_wakeup(); }
234 bool detach(void) {
235 if (!device().begin_called) return true;
236 return tud_disconnect();
237 }
238 bool attach(void) {
239 if (!device().begin_called) {
240 device().beginUSB();
241 return USB.begin();
242 }
243
244 return tud_connect();
245 }
246 // bool beginUSB() { return device().beginUSB(); }
251};
252
254
263
264} // namespace audio_tools
265
266#endif // ARDUINO_USB_CDC_ON_BOOT
267#endif // ESP32
If you want to use the framework w/o Arduino you need to provide the implementation of a couple of cl...
#define LOGE(...)
Definition AudioLoggerIDF.h:30
#define USB_DESCR_MAX_LEN
Definition USBAudioDeviceBase.h:47
#define assert(T)
Definition avr.h:10
Shared functionality of all buffers.
Definition Buffers.h:23
Buffer implementation which is using a FreeRTOS StreamBuffer. The default allocator uses psram is ava...
Definition BufferRTOS.h:33
bool resize(size_t size)
Re-Allocats the memory and the queue.
Definition BufferRTOS.h:54
Minimal wrapper around the ESP32 TinyUSB API. We emulate the basic functionality so that we can use t...
Definition USBAudioDeviceESP32.h:223
bool isInitialized()
Definition USBAudioDeviceESP32.h:225
bool attach(void)
Definition USBAudioDeviceESP32.h:238
USBAudioDeviceESP32 & device()
Definition USBAudioDeviceESP32.h:247
bool suspended(void)
Definition USBAudioDeviceESP32.h:231
bool remoteWakeup(void)
Definition USBAudioDeviceESP32.h:233
bool ready(void)
Definition USBAudioDeviceESP32.h:232
bool mounted(void)
Definition USBAudioDeviceESP32.h:227
bool detach(void)
Definition USBAudioDeviceESP32.h:234
bool begin(int)
Definition USBAudioDeviceESP32.h:226
Abstract seam for every raw USB-stack call the UAC2 driver (USBAudioDeviceBase) needs....
Definition USBAudioBackend.h:160
USBAudioBackend implementation wrapping the real TinyUSB device stack. Injected by the ESP32,...
Definition USBAudioBackendTinyUSB.h:48
USB Audio Device class for audio streaming over USB.
Definition USBAudioDeviceBase.h:109
bool isEpInEnabled() const
Returns true if the IN endpoint is enabled.
Definition USBAudioDeviceBase.h:391
USBAudioConfig config_
Definition USBAudioDeviceBase.h:856
uint16_t getDescriptor(uint8_t *desc)
Returns the audio-function descriptor block for use in tud_descriptor_configuration_cb().
Definition USBAudioDeviceBase.h:776
static USBAudioDeviceBase & activeInstance()
Returns the most-recently-constructed instance (base or subclass).
Definition USBAudioDeviceBase.h:388
uint16_t packetSize() const
Definition USBAudioDeviceBase.h:1101
bool isFeedbackEpEnabled() const
Returns true if the feedback endpoint is enabled. Only meaningful in pure RX (OUT-only) mode: with an...
Definition USBAudioDeviceBase.h:399
bool isEpOutEnabled() const
Returns true if the OUT endpoint is enabled.
Definition USBAudioDeviceBase.h:394
USBAudioDeviceBase subclass for ESP32-S2/S3 using the arduino-esp32 stack.
Definition USBAudioDeviceESP32.h:55
bool setupUSB()
Definition USBAudioDeviceESP32.h:86
static USBAudioDeviceESP32 & getActualInstance()
Definition USBAudioDeviceESP32.h:81
static int16_t allocOutEndpoint()
Definition USBAudioDeviceESP32.h:164
BufferRTOS< uint8_t > buffer_rx_
Definition USBAudioDeviceESP32.h:214
void resolveEndpoints()
Resolve any endpoint left at -1 ("allocate dynamically") to a free endpoint number via arduino-esp32'...
Definition USBAudioDeviceESP32.h:141
BaseBuffer< uint8_t > & bufferTx() override
Returns cross-core safe TX buffer (FreeRTOS queue of blocks).
Definition USBAudioDeviceESP32.h:110
void serviceUSB() override
No-op: the arduino-esp32 framework already runs a dedicated FreeRTOS task that calls tud_task() conti...
Definition USBAudioDeviceESP32.h:121
USBAudioDeviceESP32(USBAudioConfig cfg)
Definition USBAudioDeviceESP32.h:60
bool beginUSB() override
Configure and start the ESP32 USB stack.
Definition USBAudioDeviceESP32.h:190
static uint16_t descriptorCallback(uint8_t *dst, uint8_t *itf)
Definition USBAudioDeviceESP32.h:70
void resizeBuffers() override
Resize buffers as block pools: block size = one USB frame at the current sample rate,...
Definition USBAudioDeviceESP32.h:176
static int16_t allocInEndpoint()
Definition USBAudioDeviceESP32.h:155
USBAudioBackend & backend() override
Returns the backend used for all raw USB-stack calls (TinyUSB today, or a future native-HAL backend)....
Definition USBAudioDeviceESP32.h:126
bool begin_called
Definition USBAudioDeviceESP32.h:201
BaseBuffer< uint8_t > & bufferRx() override
Returns cross-core safe RX buffer (FreeRTOS queue of blocks).
Definition USBAudioDeviceESP32.h:113
USBAudioBackendTinyUSB backend_impl_
Definition USBAudioDeviceESP32.h:125
BufferRTOS< uint8_t > buffer_tx_
Definition USBAudioDeviceESP32.h:213
int getActualCore() const override
Returns the actual core on which the call is running (for RP2040)
Definition USBAudioDeviceESP32.h:116
bool setup_called
Definition USBAudioDeviceESP32.h:202
Generic Implementation of sound input and output for desktop environments using portaudio.
Definition LMSEchoCancellationStream.h:6
static Emulated_TinyUSB TinyUSBDevice
Definition USBAudioDeviceESP32.h:253
Configuration for USB Audio (inherits sample_rate / channels / bits_per_sample from AudioInfo).
Definition USBAudioConfig.h:117
bool enable_interrupt_ep
Definition USBAudioConfig.h:197
int16_t ep_fb
ISO IN (explicit feedback, RX-only mode)
Definition USBAudioConfig.h:134
bool self_powered
Definition USBAudioConfig.h:163
const char * serial
Definition USBAudioConfig.h:162
int16_t ep_in
ISO IN (device → host, capture/microphone)
Definition USBAudioConfig.h:132
const char * product
Definition USBAudioConfig.h:161
int16_t ep_int
INT IN (AC status/change notifications)
Definition USBAudioConfig.h:135
uint8_t max_power_ma
Definition USBAudioConfig.h:164
const char * manufacturer
Definition USBAudioConfig.h:160
uint16_t pid
Definition USBAudioConfig.h:159
uint16_t vid
Definition USBAudioConfig.h:158
int16_t ep_out
ISO OUT (host → device, playback/speaker)
Definition USBAudioConfig.h:133
bool enable_ep_in
device → host (capture / microphone)
Definition USBAudioConfig.h:120
uint8_t fifo_packets
Definition USBAudioConfig.h:148
bool enable_ep_out
host → device (playback / speaker)
Definition USBAudioConfig.h:121
bool begin_usb
Definition USBAudioConfig.h:236