Important changes to repositories hosted on mbed.com
Mbed hosted mercurial repositories are deprecated and are due to be permanently deleted in July 2026.
To keep a copy of this software download the repository Zip archive or clone locally using Mercurial.
It is also possible to export all your personal repositories from the account settings page.
Dependents: TYBLE16_simple_data_logger TYBLE16_MP3_Air
USBAudio.cpp
00001 /* 00002 * Copyright (c) 2018-2019, Arm Limited and affiliates. 00003 * SPDX-License-Identifier: Apache-2.0 00004 * 00005 * Licensed under the Apache License, Version 2.0 (the "License"); 00006 * you may not use this file except in compliance with the License. 00007 * You may obtain a copy of the License at 00008 * 00009 * http://www.apache.org/licenses/LICENSE-2.0 00010 * 00011 * Unless required by applicable law or agreed to in writing, software 00012 * distributed under the License is distributed on an "AS IS" BASIS, 00013 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 00014 * See the License for the specific language governing permissions and 00015 * limitations under the License. 00016 */ 00017 00018 #include "stdint.h" 00019 #include "USBAudio.h" 00020 #include "USBAudio_Types.h" 00021 #include "EndpointResolver.h" 00022 #include "usb_phy_api.h" 00023 00024 #define SAMPLE_SIZE 2 00025 #define XFER_FREQUENCY_HZ 1000 00026 #define WRITE_READY_UNBLOCK (1 << 0) 00027 #define READ_READY_UNBLOCK (1 << 1) 00028 00029 class USBAudio::AsyncWrite: public AsyncOp { 00030 public: 00031 AsyncWrite(USBAudio *audio, uint8_t *buf, uint32_t size): 00032 audio(audio), tx_buf(buf), tx_size(size), result(false) 00033 { 00034 00035 } 00036 00037 virtual ~AsyncWrite() 00038 { 00039 00040 } 00041 00042 virtual bool process() 00043 { 00044 if (audio->_tx_state != Opened) { 00045 result = false; 00046 return true; 00047 } 00048 00049 uint32_t actual_size = 0; 00050 audio->write_nb(tx_buf, tx_size, &actual_size); 00051 tx_size -= actual_size; 00052 tx_buf += actual_size; 00053 if (tx_size == 0) { 00054 result = true; 00055 return true; 00056 } 00057 00058 return false; 00059 } 00060 00061 USBAudio *audio; 00062 uint8_t *tx_buf; 00063 uint32_t tx_size; 00064 bool result; 00065 }; 00066 00067 class USBAudio::AsyncRead: public AsyncOp { 00068 public: 00069 AsyncRead(USBAudio *audio, uint8_t *buf, uint32_t size, uint32_t *size_read, bool read_all) 00070 : audio(audio), rx_buf(buf), rx_size(size), rx_actual(size_read), all(read_all), result(false) 00071 { 00072 00073 } 00074 00075 virtual ~AsyncRead() 00076 { 00077 00078 } 00079 00080 virtual bool process() 00081 { 00082 if (audio->_rx_state != Opened) { 00083 result = false; 00084 return true; 00085 } 00086 00087 uint32_t actual_size = 0; 00088 audio->read_nb(rx_buf, rx_size, &actual_size); 00089 rx_buf += actual_size; 00090 *rx_actual += actual_size; 00091 rx_size -= actual_size; 00092 if ((!all && *rx_actual > 0) || (rx_size == 0)) { 00093 // Wake thread if request is done 00094 result = true; 00095 return true; 00096 } 00097 00098 return false; 00099 } 00100 00101 USBAudio *audio; 00102 uint8_t *rx_buf; 00103 uint32_t rx_size; 00104 uint32_t *rx_actual; 00105 bool all; 00106 bool result; 00107 }; 00108 00109 static void stub_volume() 00110 { 00111 00112 } 00113 00114 static void stub_handler(USBAudio::AudioEvent event) 00115 { 00116 (void)event; 00117 } 00118 00119 USBAudio::USBAudio(bool connect, uint32_t frequency_rx, uint8_t channel_count_rx, uint32_t frequency_tx, uint8_t channel_count_tx, uint32_t buffer_ms, uint16_t vendor_id, uint16_t product_id, uint16_t product_release): 00120 USBDevice(get_usb_phy(), vendor_id, product_id, product_release) 00121 { 00122 _init(frequency_rx, channel_count_rx, frequency_tx, channel_count_tx, buffer_ms); 00123 00124 // connect or init device 00125 if (connect) { 00126 USBDevice::connect(); 00127 } else { 00128 USBDevice::init(); 00129 } 00130 } 00131 00132 USBAudio::USBAudio(USBPhy *phy, uint32_t frequency_rx, uint8_t channel_count_rx, uint32_t frequency_tx, uint8_t channel_count_tx, uint32_t buffer_ms, uint16_t vendor_id, uint16_t product_id, uint16_t product_release): 00133 USBDevice(phy, vendor_id, product_id, product_release) 00134 { 00135 _init(frequency_rx, channel_count_rx, frequency_tx, channel_count_tx, buffer_ms); 00136 } 00137 00138 void USBAudio::_init(uint32_t frequency_rx, uint8_t channel_count_rx, uint32_t frequency_tx, uint8_t channel_count_tx, uint32_t buffer_ms) 00139 { 00140 _connected = false; 00141 00142 _volume = 0; 00143 _mute = 0; 00144 _vol_cur = 0x0080; 00145 _vol_min = 0x0000; 00146 _vol_max = 0x0100; 00147 _vol_res = 0x0004; 00148 00149 _update_vol = mbed::callback(stub_volume); 00150 _tx_done = mbed::callback(stub_handler); 00151 _rx_done = mbed::callback(stub_handler); 00152 00153 _rx_overflow = 0; 00154 _tx_underflow = 0; 00155 00156 _tx_freq = frequency_tx; 00157 _rx_freq = frequency_rx; 00158 00159 _tx_channel_count = channel_count_tx; 00160 _rx_channel_count = channel_count_rx; 00161 00162 _tx_idle = true; 00163 _tx_frame_fract = 0; 00164 _tx_whole_frames_per_xfer = _tx_freq / XFER_FREQUENCY_HZ; 00165 _tx_fract_frames_per_xfer = _tx_freq % XFER_FREQUENCY_HZ; 00166 00167 uint32_t max_frames = _tx_whole_frames_per_xfer + (_tx_fract_frames_per_xfer ? 1 : 0); 00168 _tx_packet_size_max = max_frames * SAMPLE_SIZE * _tx_channel_count; 00169 _rx_packet_size_max = (_rx_freq + 1000 - 1) / 1000 * _rx_channel_count * 2; 00170 00171 _tx_packet_buf = new uint8_t[_tx_packet_size_max](); 00172 _rx_packet_buf = new uint8_t[_rx_packet_size_max](); 00173 00174 _tx_queue.resize(buffer_ms * _tx_channel_count * SAMPLE_SIZE * _tx_freq / XFER_FREQUENCY_HZ); 00175 _rx_queue.resize(buffer_ms * _rx_channel_count * SAMPLE_SIZE * _rx_freq / XFER_FREQUENCY_HZ); 00176 00177 _tx_state = Closed; 00178 _rx_state = Closed; 00179 00180 EndpointResolver resolver(endpoint_table()); 00181 resolver.endpoint_ctrl(64); 00182 _episo_out = resolver.endpoint_out(USB_EP_TYPE_ISO, _tx_packet_size_max); 00183 _episo_in = resolver.endpoint_in(USB_EP_TYPE_ISO, _rx_packet_size_max); 00184 MBED_ASSERT(resolver.valid()); 00185 00186 _channel_config_rx = (_rx_channel_count == 1) ? CHANNEL_M : CHANNEL_L + CHANNEL_R; 00187 _channel_config_tx = (_tx_channel_count == 1) ? CHANNEL_M : CHANNEL_L + CHANNEL_R; 00188 00189 _build_configuration_desc(); 00190 } 00191 00192 USBAudio::~USBAudio() 00193 { 00194 disconnect(); 00195 deinit(); 00196 00197 delete[] _tx_packet_buf; 00198 delete[] _rx_packet_buf; 00199 } 00200 00201 void USBAudio::connect() 00202 { 00203 lock(); 00204 00205 if (!_connected) { 00206 USBDevice::connect(); 00207 _connected = true; 00208 _receive_change(Closed); 00209 _send_change(Closed); 00210 } 00211 00212 unlock(); 00213 } 00214 00215 void USBAudio::disconnect() 00216 { 00217 lock(); 00218 00219 if (_connected) { 00220 _connected = false; 00221 USBDevice::disconnect(); 00222 _receive_change(Powerdown); 00223 _send_change(Powerdown); 00224 } 00225 00226 unlock(); 00227 } 00228 00229 bool USBAudio::read(uint8_t *buf, uint32_t size) 00230 { 00231 lock(); 00232 00233 uint32_t actual; 00234 AsyncRead read(this, buf, size, &actual, true); 00235 _read_list.add(&read); 00236 00237 unlock(); 00238 00239 read.wait(NULL); 00240 return read.result; 00241 } 00242 00243 void USBAudio::read_nb(uint8_t *buf, uint32_t size, uint32_t *actual) 00244 { 00245 00246 lock(); 00247 00248 uint32_t available = _rx_queue.size(); 00249 uint32_t copy_size = available > size ? size : available; 00250 _rx_queue.read(buf, copy_size); 00251 *actual = copy_size; 00252 00253 unlock(); 00254 } 00255 00256 uint32_t USBAudio::read_overflows(bool clear) 00257 { 00258 lock(); 00259 00260 uint32_t overflows = _rx_overflow; 00261 if (clear) { 00262 _rx_overflow = 0; 00263 } 00264 00265 unlock(); 00266 return overflows; 00267 } 00268 00269 00270 bool USBAudio::read_ready() 00271 { 00272 lock(); 00273 00274 bool ready = _rx_state == Opened; 00275 00276 unlock(); 00277 00278 return ready; 00279 } 00280 00281 void USBAudio::read_wait_ready() 00282 { 00283 _flags.wait_any(READ_READY_UNBLOCK, osWaitForever, false); 00284 } 00285 00286 bool USBAudio::write(uint8_t *buf, uint32_t size) 00287 { 00288 lock(); 00289 00290 AsyncWrite write(this, buf, size); 00291 _write_list.add(&write); 00292 00293 unlock(); 00294 00295 write.wait(NULL); 00296 return write.result; 00297 } 00298 00299 void USBAudio::write_nb(uint8_t *buf, uint32_t size, uint32_t *actual) 00300 { 00301 lock(); 00302 00303 uint32_t available = _tx_queue.free(); 00304 uint32_t copy_size = available > size ? size : available; 00305 _tx_queue.write(buf, copy_size); 00306 *actual = copy_size; 00307 _send_isr_start(); 00308 00309 unlock(); 00310 } 00311 00312 uint32_t USBAudio::write_underflows(bool clear) 00313 { 00314 lock(); 00315 00316 uint32_t underflows = _tx_underflow; 00317 if (clear) { 00318 _tx_underflow = 0; 00319 } 00320 00321 unlock(); 00322 return underflows; 00323 } 00324 00325 bool USBAudio::write_ready() 00326 { 00327 lock(); 00328 00329 bool ready = _tx_state == Opened; 00330 00331 unlock(); 00332 00333 return ready; 00334 } 00335 00336 void USBAudio::write_wait_ready() 00337 { 00338 _flags.wait_any(WRITE_READY_UNBLOCK, osWaitForever, false); 00339 } 00340 00341 00342 float USBAudio::get_volume() 00343 { 00344 lock(); 00345 00346 float ret = _mute ? 0.0f : _volume; 00347 00348 unlock(); 00349 return ret; 00350 } 00351 00352 void USBAudio::attach(mbed::Callback<void()> &cb) 00353 { 00354 lock(); 00355 00356 _update_vol = cb; 00357 if (!_update_vol) { 00358 _update_vol = stub_volume; 00359 } 00360 00361 unlock(); 00362 } 00363 00364 void USBAudio::attach_tx(mbed::Callback<void(AudioEvent)> &cb) 00365 { 00366 lock(); 00367 00368 _tx_done = cb; 00369 if (!_tx_done) { 00370 _tx_done = mbed::callback(stub_handler); 00371 } 00372 00373 unlock(); 00374 } 00375 00376 void USBAudio::attach_rx(mbed::Callback<void(AudioEvent)> &cb) 00377 { 00378 lock(); 00379 00380 _rx_done = cb; 00381 if (!_rx_done) { 00382 _rx_done = mbed::callback(stub_handler); 00383 } 00384 00385 unlock(); 00386 } 00387 00388 void USBAudio::callback_state_change(DeviceState new_state) 00389 { 00390 assert_locked(); 00391 00392 if (_connected && (new_state != Configured)) { 00393 _receive_change(Closed); 00394 _send_change(Closed); 00395 } 00396 } 00397 00398 void USBAudio::callback_request(const setup_packet_t *setup) 00399 { 00400 assert_locked(); 00401 00402 RequestResult result = PassThrough; 00403 uint8_t *data = NULL; 00404 uint32_t size = 0; 00405 00406 // Process class-specific requests 00407 if (setup->bmRequestType.Type == CLASS_TYPE) { 00408 00409 // Feature Unit: Interface = 0, ID = 2 00410 if (setup->wIndex == 0x0200) { 00411 00412 // Master Channel 00413 if ((setup->wValue & 0xff) == 0) { 00414 00415 switch (setup->wValue >> 8) { 00416 case MUTE_CONTROL: 00417 switch (setup->bRequest) { 00418 case REQUEST_GET_CUR: 00419 size = 1; 00420 data = &_mute; 00421 result = Send; 00422 break; 00423 00424 case REQUEST_SET_CUR: 00425 size = 1; 00426 data = _control_receive; 00427 result = Receive; 00428 break; 00429 default: 00430 break; 00431 } 00432 break; 00433 case VOLUME_CONTROL: 00434 switch (setup->bRequest) { 00435 case REQUEST_GET_CUR: 00436 size = 2; 00437 data = (uint8_t *)&_vol_cur; 00438 result = Send; 00439 break; 00440 case REQUEST_GET_MIN: 00441 size = 2; 00442 data = (uint8_t *)&_vol_min; 00443 result = Send; 00444 break; 00445 case REQUEST_GET_MAX: 00446 size = 2; 00447 data = (uint8_t *)&_vol_max; 00448 result = Send; 00449 break; 00450 case REQUEST_GET_RES: 00451 size = 2; 00452 data = (uint8_t *)&_vol_res; 00453 result = Send; 00454 break; 00455 00456 case REQUEST_SET_CUR: 00457 size = 2; 00458 data = _control_receive; 00459 result = Receive; 00460 break; 00461 case REQUEST_SET_MIN: 00462 size = 2; 00463 data = _control_receive; 00464 result = Receive; 00465 break; 00466 case REQUEST_SET_MAX: 00467 size = 2; 00468 data = _control_receive; 00469 result = Receive; 00470 break; 00471 case REQUEST_SET_RES: 00472 size = 2; 00473 data = _control_receive; 00474 result = Receive; 00475 break; 00476 } 00477 break; 00478 default: 00479 break; 00480 } 00481 } 00482 } 00483 } 00484 complete_request(result, data, size); 00485 } 00486 00487 void USBAudio::callback_request_xfer_done(const setup_packet_t *setup, bool aborted) 00488 { 00489 assert_locked(); 00490 00491 if (aborted) { 00492 complete_request_xfer_done(false); 00493 return; 00494 } 00495 00496 if (setup->bmRequestType.dataTransferDirection == DEVICE_TO_HOST) { 00497 complete_request_xfer_done(true); 00498 return; 00499 } 00500 00501 if ((setup->wLength == 1) || (setup->wLength == 2)) { 00502 uint16_t data = (_control_receive[0] << 0) | (_control_receive[1] << 8); 00503 data &= ((setup->wLength == 1) ? 0xFF : 0xFFFF); 00504 switch (setup->wValue >> 8) { 00505 case MUTE_CONTROL: 00506 switch (setup->bRequest) { 00507 case REQUEST_SET_CUR: 00508 _mute = data & 0xff; 00509 _update_vol.call(); 00510 break; 00511 default: 00512 break; 00513 } 00514 break; 00515 case VOLUME_CONTROL: 00516 switch (setup->bRequest) { 00517 case REQUEST_SET_CUR: 00518 _vol_cur = data; 00519 _volume = (float)_vol_cur / (float)_vol_max; 00520 _update_vol.call(); 00521 break; 00522 default: 00523 break; 00524 } 00525 break; 00526 default: 00527 break; 00528 } 00529 complete_request_xfer_done(true); 00530 return; 00531 } 00532 00533 complete_request_xfer_done(false); 00534 } 00535 00536 void USBAudio::callback_set_configuration(uint8_t configuration) 00537 { 00538 assert_locked(); 00539 00540 bool ret = false; 00541 if (configuration == DEFAULT_CONFIGURATION) { 00542 endpoint_remove_all(); 00543 00544 // Configure isochronous endpoint 00545 endpoint_add(_episo_out, _rx_packet_size_max, USB_EP_TYPE_ISO, static_cast<ep_cb_t>(&USBAudio::_receive_isr)); 00546 endpoint_add(_episo_in, _tx_packet_size_max, USB_EP_TYPE_ISO, static_cast<ep_cb_t>(&USBAudio::_send_isr)); 00547 00548 // activate readings on this endpoint 00549 read_start(_episo_out, _rx_packet_buf, _rx_packet_size_max); 00550 ret = true; 00551 } 00552 complete_set_configuration(ret); 00553 } 00554 00555 void USBAudio::callback_set_interface(uint16_t interface, uint8_t alternate) 00556 { 00557 assert_locked(); 00558 00559 bool ret = false; 00560 if (interface == 0 && alternate == 0) { 00561 ret = true; 00562 } 00563 if (interface == 1 && (alternate == 0 || alternate == 1)) { 00564 _receive_change(alternate == 1 ? Opened : Closed); 00565 ret = true; 00566 } 00567 if (interface == 2 && (alternate == 0 || alternate == 1)) { 00568 _send_change(alternate == 1 ? Opened : Closed); 00569 ret = true; 00570 } 00571 complete_set_interface(ret); 00572 } 00573 00574 const uint8_t *USBAudio::configuration_desc(uint8_t index) 00575 { 00576 if (index != 0) { 00577 return NULL; 00578 } 00579 return _config_descriptor; 00580 } 00581 00582 const uint8_t *USBAudio::string_iinterface_desc() 00583 { 00584 static const uint8_t stringIinterfaceDescriptor[] = { 00585 0x0c, //bLength 00586 STRING_DESCRIPTOR, //bDescriptorType 0x03 00587 'A', 0, 'u', 0, 'd', 0, 'i', 0, 'o', 0 //bString iInterface - Audio 00588 }; 00589 return stringIinterfaceDescriptor; 00590 } 00591 00592 const uint8_t *USBAudio::string_iproduct_desc() 00593 { 00594 static const uint8_t stringIproductDescriptor[] = { 00595 0x16, //bLength 00596 STRING_DESCRIPTOR, //bDescriptorType 0x03 00597 'M', 0, 'b', 0, 'e', 0, 'd', 0, ' ', 0, 'A', 0, 'u', 0, 'd', 0, 'i', 0, 'o', 0 //bString iProduct - Mbed Audio 00598 }; 00599 return stringIproductDescriptor; 00600 } 00601 00602 #define TOTAL_DESCRIPTOR_LENGTH ((1 * CONFIGURATION_DESCRIPTOR_LENGTH) \ 00603 + (5 * INTERFACE_DESCRIPTOR_LENGTH) \ 00604 + (1 * CONTROL_INTERFACE_DESCRIPTOR_LENGTH + 1) \ 00605 + (2 * INPUT_TERMINAL_DESCRIPTOR_LENGTH) \ 00606 + (1 * FEATURE_UNIT_DESCRIPTOR_LENGTH) \ 00607 + (2 * OUTPUT_TERMINAL_DESCRIPTOR_LENGTH) \ 00608 + (2 * STREAMING_INTERFACE_DESCRIPTOR_LENGTH) \ 00609 + (2 * FORMAT_TYPE_I_DESCRIPTOR_LENGTH) \ 00610 + (2 * (ENDPOINT_DESCRIPTOR_LENGTH + 2)) \ 00611 + (2 * STREAMING_ENDPOINT_DESCRIPTOR_LENGTH) ) 00612 00613 #define TOTAL_CONTROL_INTF_LENGTH (CONTROL_INTERFACE_DESCRIPTOR_LENGTH + 1 + \ 00614 2*INPUT_TERMINAL_DESCRIPTOR_LENGTH + \ 00615 FEATURE_UNIT_DESCRIPTOR_LENGTH + \ 00616 2*OUTPUT_TERMINAL_DESCRIPTOR_LENGTH) 00617 00618 void USBAudio::_build_configuration_desc() 00619 { 00620 uint8_t config_descriptor_temp[] = { 00621 // Configuration 1 00622 CONFIGURATION_DESCRIPTOR_LENGTH, // bLength 00623 CONFIGURATION_DESCRIPTOR, // bDescriptorType 00624 LSB(TOTAL_DESCRIPTOR_LENGTH), // wTotalLength (LSB) 00625 MSB(TOTAL_DESCRIPTOR_LENGTH), // wTotalLength (MSB) 00626 0x03, // bNumInterfaces 00627 DEFAULT_CONFIGURATION, // bConfigurationValue 00628 0x00, // iConfiguration 00629 0x80, // bmAttributes 00630 50, // bMaxPower 00631 00632 // Interface 0, Alternate Setting 0, Audio Control 00633 INTERFACE_DESCRIPTOR_LENGTH, // bLength 00634 INTERFACE_DESCRIPTOR, // bDescriptorType 00635 0x00, // bInterfaceNumber 00636 0x00, // bAlternateSetting 00637 0x00, // bNumEndpoints 00638 AUDIO_CLASS, // bInterfaceClass 00639 SUBCLASS_AUDIOCONTROL, // bInterfaceSubClass 00640 0x00, // bInterfaceProtocol 00641 0x00, // iInterface 00642 00643 00644 // Audio Control Interface 00645 CONTROL_INTERFACE_DESCRIPTOR_LENGTH + 1,// bLength 00646 INTERFACE_DESCRIPTOR_TYPE, // bDescriptorType 00647 CONTROL_HEADER, // bDescriptorSubtype 00648 LSB(0x0100), // bcdADC (LSB) 00649 MSB(0x0100), // bcdADC (MSB) 00650 LSB(TOTAL_CONTROL_INTF_LENGTH), // wTotalLength 00651 MSB(TOTAL_CONTROL_INTF_LENGTH), // wTotalLength 00652 0x02, // bInCollection 00653 0x01, // baInterfaceNr 00654 0x02, // baInterfaceNr 00655 00656 // Audio Input Terminal (Speaker) 00657 INPUT_TERMINAL_DESCRIPTOR_LENGTH, // bLength 00658 INTERFACE_DESCRIPTOR_TYPE, // bDescriptorType 00659 CONTROL_INPUT_TERMINAL, // bDescriptorSubtype 00660 0x01, // bTerminalID 00661 LSB(TERMINAL_USB_STREAMING), // wTerminalType 00662 MSB(TERMINAL_USB_STREAMING), // wTerminalType 00663 0x00, // bAssocTerminal 00664 _rx_channel_count, // bNrChannels 00665 (uint8_t)(LSB(_channel_config_rx)), // wChannelConfig 00666 (uint8_t)(MSB(_channel_config_rx)), // wChannelConfig 00667 0x00, // iChannelNames 00668 0x00, // iTerminal 00669 00670 // Audio Feature Unit (Speaker) 00671 FEATURE_UNIT_DESCRIPTOR_LENGTH, // bLength 00672 INTERFACE_DESCRIPTOR_TYPE, // bDescriptorType 00673 CONTROL_FEATURE_UNIT, // bDescriptorSubtype 00674 0x02, // bUnitID 00675 0x01, // bSourceID 00676 0x01, // bControlSize 00677 CONTROL_MUTE | 00678 CONTROL_VOLUME, // bmaControls(0) 00679 0x00, // bmaControls(1) 00680 0x00, // iTerminal 00681 00682 // Audio Output Terminal (Speaker) 00683 OUTPUT_TERMINAL_DESCRIPTOR_LENGTH, // bLength 00684 INTERFACE_DESCRIPTOR_TYPE, // bDescriptorType 00685 CONTROL_OUTPUT_TERMINAL, // bDescriptorSubtype 00686 0x03, // bTerminalID 00687 LSB(TERMINAL_SPEAKER), // wTerminalType 00688 MSB(TERMINAL_SPEAKER), // wTerminalType 00689 0x00, // bAssocTerminal 00690 0x02, // bSourceID 00691 0x00, // iTerminal 00692 00693 00694 // Audio Input Terminal (Microphone) 00695 INPUT_TERMINAL_DESCRIPTOR_LENGTH, // bLength 00696 INTERFACE_DESCRIPTOR_TYPE, // bDescriptorType 00697 CONTROL_INPUT_TERMINAL, // bDescriptorSubtype 00698 0x04, // bTerminalID 00699 LSB(TERMINAL_MICROPHONE), // wTerminalType 00700 MSB(TERMINAL_MICROPHONE), // wTerminalType 00701 0x00, // bAssocTerminal 00702 _tx_channel_count, // bNrChannels 00703 (uint8_t)(LSB(_channel_config_tx)), // wChannelConfig 00704 (uint8_t)(MSB(_channel_config_tx)), // wChannelConfig 00705 0x00, // iChannelNames 00706 0x00, // iTerminal 00707 00708 // Audio Output Terminal (Microphone) 00709 OUTPUT_TERMINAL_DESCRIPTOR_LENGTH, // bLength 00710 INTERFACE_DESCRIPTOR_TYPE, // bDescriptorType 00711 CONTROL_OUTPUT_TERMINAL, // bDescriptorSubtype 00712 0x05, // bTerminalID 00713 LSB(TERMINAL_USB_STREAMING), // wTerminalType 00714 MSB(TERMINAL_USB_STREAMING), // wTerminalType 00715 0x00, // bAssocTerminal 00716 0x04, // bSourceID 00717 0x00, // iTerminal 00718 00719 00720 00721 00722 00723 00724 // Interface 1, Alternate Setting 0, Audio Streaming - Zero Bandwith 00725 INTERFACE_DESCRIPTOR_LENGTH, // bLength 00726 INTERFACE_DESCRIPTOR, // bDescriptorType 00727 0x01, // bInterfaceNumber 00728 0x00, // bAlternateSetting 00729 0x00, // bNumEndpoints 00730 AUDIO_CLASS, // bInterfaceClass 00731 SUBCLASS_AUDIOSTREAMING, // bInterfaceSubClass 00732 0x00, // bInterfaceProtocol 00733 0x00, // iInterface 00734 00735 // Interface 1, Alternate Setting 1, Audio Streaming - Operational 00736 INTERFACE_DESCRIPTOR_LENGTH, // bLength 00737 INTERFACE_DESCRIPTOR, // bDescriptorType 00738 0x01, // bInterfaceNumber 00739 0x01, // bAlternateSetting 00740 0x01, // bNumEndpoints 00741 AUDIO_CLASS, // bInterfaceClass 00742 SUBCLASS_AUDIOSTREAMING, // bInterfaceSubClass 00743 0x00, // bInterfaceProtocol 00744 0x00, // iInterface 00745 00746 // Audio Streaming Interface 00747 STREAMING_INTERFACE_DESCRIPTOR_LENGTH, // bLength 00748 INTERFACE_DESCRIPTOR_TYPE, // bDescriptorType 00749 STREAMING_GENERAL, // bDescriptorSubtype 00750 0x01, // bTerminalLink 00751 0x00, // bDelay 00752 LSB(FORMAT_PCM), // wFormatTag 00753 MSB(FORMAT_PCM), // wFormatTag 00754 00755 // Audio Type I Format 00756 FORMAT_TYPE_I_DESCRIPTOR_LENGTH, // bLength 00757 INTERFACE_DESCRIPTOR_TYPE, // bDescriptorType 00758 STREAMING_FORMAT_TYPE, // bDescriptorSubtype 00759 FORMAT_TYPE_I, // bFormatType 00760 _rx_channel_count, // bNrChannels 00761 0x02, // bSubFrameSize 00762 16, // bBitResolution 00763 0x01, // bSamFreqType 00764 (uint8_t)(LSB(_rx_freq)), // tSamFreq 00765 (uint8_t)((_rx_freq >> 8) & 0xff), // tSamFreq 00766 (uint8_t)((_rx_freq >> 16) & 0xff), // tSamFreq 00767 00768 // Endpoint - Standard Descriptor 00769 ENDPOINT_DESCRIPTOR_LENGTH + 2, // bLength 00770 ENDPOINT_DESCRIPTOR, // bDescriptorType 00771 _episo_out, // bEndpointAddress 00772 E_ISOCHRONOUS, // bmAttributes 00773 (uint8_t)(LSB(_rx_packet_size_max)), // wMaxPacketSize 00774 (uint8_t)(MSB(_rx_packet_size_max)), // wMaxPacketSize 00775 0x01, // bInterval 00776 0x00, // bRefresh 00777 0x00, // bSynchAddress 00778 00779 // Endpoint - Audio Streaming 00780 STREAMING_ENDPOINT_DESCRIPTOR_LENGTH, // bLength 00781 ENDPOINT_DESCRIPTOR_TYPE, // bDescriptorType 00782 ENDPOINT_GENERAL, // bDescriptor 00783 0x00, // bmAttributes 00784 0x00, // bLockDelayUnits 00785 LSB(0x0000), // wLockDelay 00786 MSB(0x0000), // wLockDelay 00787 00788 00789 // Interface 1, Alternate Setting 0, Audio Streaming - Zero Bandwith 00790 INTERFACE_DESCRIPTOR_LENGTH, // bLength 00791 INTERFACE_DESCRIPTOR, // bDescriptorType 00792 0x02, // bInterfaceNumber 00793 0x00, // bAlternateSetting 00794 0x00, // bNumEndpoints 00795 AUDIO_CLASS, // bInterfaceClass 00796 SUBCLASS_AUDIOSTREAMING, // bInterfaceSubClass 00797 0x00, // bInterfaceProtocol 00798 0x00, // iInterface 00799 00800 // Interface 1, Alternate Setting 1, Audio Streaming - Operational 00801 INTERFACE_DESCRIPTOR_LENGTH, // bLength 00802 INTERFACE_DESCRIPTOR, // bDescriptorType 00803 0x02, // bInterfaceNumber 00804 0x01, // bAlternateSetting 00805 0x01, // bNumEndpoints 00806 AUDIO_CLASS, // bInterfaceClass 00807 SUBCLASS_AUDIOSTREAMING, // bInterfaceSubClass 00808 0x00, // bInterfaceProtocol 00809 0x00, // iInterface 00810 00811 // Audio Streaming Interface 00812 STREAMING_INTERFACE_DESCRIPTOR_LENGTH, // bLength 00813 INTERFACE_DESCRIPTOR_TYPE, // bDescriptorType 00814 SUBCLASS_AUDIOCONTROL, // bDescriptorSubtype 00815 0x05, // bTerminalLink (output terminal microphone) 00816 0x01, // bDelay 00817 0x01, // wFormatTag 00818 0x00, // wFormatTag 00819 00820 // Audio Type I Format 00821 FORMAT_TYPE_I_DESCRIPTOR_LENGTH, // bLength 00822 INTERFACE_DESCRIPTOR_TYPE, // bDescriptorType 00823 SUBCLASS_AUDIOSTREAMING, // bDescriptorSubtype 00824 FORMAT_TYPE_I, // bFormatType 00825 _tx_channel_count, // bNrChannels 00826 0x02, // bSubFrameSize 00827 0x10, // bBitResolution 00828 0x01, // bSamFreqType 00829 (uint8_t)(LSB(_tx_freq)), // tSamFreq 00830 (uint8_t)((_tx_freq >> 8) & 0xff), // tSamFreq 00831 (uint8_t)((_tx_freq >> 16) & 0xff), // tSamFreq 00832 00833 // Endpoint - Standard Descriptor 00834 ENDPOINT_DESCRIPTOR_LENGTH + 2, // bLength 00835 ENDPOINT_DESCRIPTOR, // bDescriptorType 00836 _episo_in, // bEndpointAddress 00837 E_ISOCHRONOUS, // bmAttributes 00838 (uint8_t)(LSB(_tx_packet_size_max)), // wMaxPacketSize 00839 (uint8_t)(MSB(_tx_packet_size_max)), // wMaxPacketSize 00840 0x01, // bInterval 00841 0x00, // bRefresh 00842 0x00, // bSynchAddress 00843 00844 // Endpoint - Audio Streaming 00845 STREAMING_ENDPOINT_DESCRIPTOR_LENGTH, // bLength 00846 ENDPOINT_DESCRIPTOR_TYPE, // bDescriptorType 00847 ENDPOINT_GENERAL, // bDescriptor 00848 0x00, // bmAttributes 00849 0x00, // bLockDelayUnits 00850 LSB(0x0000), // wLockDelay 00851 MSB(0x0000), // wLockDelay 00852 }; 00853 00854 MBED_ASSERT(sizeof(config_descriptor_temp) == sizeof(_config_descriptor)); 00855 memcpy(_config_descriptor, config_descriptor_temp, sizeof(_config_descriptor)); 00856 } 00857 00858 void USBAudio::_receive_change(ChannelState new_state) 00859 { 00860 assert_locked(); 00861 00862 ChannelState prev_state = _rx_state; 00863 _rx_state = new_state; 00864 if (prev_state == new_state) { 00865 // no change 00866 return; 00867 } 00868 00869 if (prev_state == Opened) { 00870 // Leaving the opened state 00871 _read_list.process(); 00872 _rx_done.call(End); 00873 } 00874 if (new_state == Opened) { 00875 // Entering the opened state 00876 _read_list.process(); 00877 _rx_done.call(Start); 00878 } 00879 if (new_state == Closed) { 00880 // Only block if the channel is closed 00881 _flags.clear(READ_READY_UNBLOCK); 00882 } else { 00883 _flags.set(READ_READY_UNBLOCK); 00884 } 00885 } 00886 00887 void USBAudio::_receive_isr() 00888 { 00889 assert_locked(); 00890 00891 uint32_t size = read_finish(_episo_out); 00892 00893 if (size > _rx_queue.free()) { 00894 _rx_overflow++; 00895 } else { 00896 00897 // Copy data over 00898 _rx_queue.write(_rx_packet_buf, size); 00899 00900 // Signal that there is more data available 00901 _read_list.process(); 00902 if (_rx_done) { 00903 _rx_done.call(Transfer); 00904 } 00905 } 00906 00907 read_start(_episo_out, _rx_packet_buf, _rx_packet_size_max); 00908 } 00909 00910 void USBAudio::_send_change(ChannelState new_state) 00911 { 00912 assert_locked(); 00913 00914 ChannelState prev_state = _tx_state; 00915 _tx_state = new_state; 00916 if (prev_state == new_state) { 00917 // no change 00918 return; 00919 } 00920 00921 if (prev_state == Opened) { 00922 // Leaving the opened state 00923 _write_list.process(); 00924 _tx_done.call(End); 00925 } 00926 if (new_state == Opened) { 00927 // Entering the opened state 00928 _write_list.process(); 00929 _tx_done.call(Start); 00930 } 00931 if (new_state == Closed) { 00932 // Only block if the channel is closed 00933 _flags.clear(WRITE_READY_UNBLOCK); 00934 } else { 00935 _flags.set(WRITE_READY_UNBLOCK); 00936 } 00937 } 00938 void USBAudio::_send_isr_start() 00939 { 00940 assert_locked(); 00941 00942 if (!_tx_idle) { 00943 return; 00944 } 00945 00946 _send_isr_next_sync(); 00947 } 00948 00949 void USBAudio::_send_isr_next_sync() 00950 { 00951 // Compute size to send 00952 uint32_t fames = _tx_whole_frames_per_xfer; 00953 if (_tx_frame_fract >= XFER_FREQUENCY_HZ) { 00954 _tx_frame_fract -= XFER_FREQUENCY_HZ; 00955 fames += 1; 00956 } 00957 uint32_t send_size = fames * _tx_channel_count * 2; 00958 00959 // Check if this is the initial TX packet 00960 if (_tx_idle && !_tx_queue.full()) { 00961 // Don't start until the TX buffer is full 00962 return; 00963 } 00964 00965 // Check if this stream was closed 00966 if (_tx_state != Opened) { 00967 _tx_idle = true; 00968 return; 00969 } 00970 00971 // Check for enough data to send 00972 if (_tx_queue.size() < send_size) { 00973 _tx_underflow++; 00974 _tx_idle = true; 00975 return; 00976 } 00977 00978 // Copy data over 00979 _tx_queue.read(_tx_packet_buf, send_size); 00980 00981 // Start the write 00982 write_start(_episo_in, _tx_packet_buf, send_size); 00983 _tx_idle = false; 00984 _tx_frame_fract += _tx_fract_frames_per_xfer; 00985 } 00986 00987 void USBAudio::_send_isr() 00988 { 00989 assert_locked(); 00990 00991 write_finish(_episo_in); 00992 00993 _send_isr_next_sync(); 00994 00995 // Signal that there is space for more data 00996 _write_list.process(); 00997 if (_tx_done) { 00998 _tx_done.call(Transfer); 00999 } 01000 }
Generated on Tue Jul 12 2022 13:55:02 by
