kopia lustrzana https://github.com/skuep/AIOC
rodzic
ae24f73803
commit
6e77ea22ae
|
@ -97,6 +97,7 @@
|
|||
//------------- CLASS -------------//
|
||||
#define CFG_TUD_AUDIO 1
|
||||
#define CFG_TUD_CDC 1
|
||||
#define CFG_TUD_HID 1
|
||||
|
||||
// CDC FIFO size of TX and RX
|
||||
#define CFG_TUD_CDC_RX_BUFSIZE 128
|
||||
|
@ -105,6 +106,9 @@
|
|||
// CDC Endpoint transfer buffer size, more is faster
|
||||
#define CFG_TUD_CDC_EP_BUFSIZE 64
|
||||
|
||||
// HID buffer size
|
||||
#define CFG_TUD_HID_EP_BUFSIZE 8
|
||||
|
||||
//--------------------------------------------------------------------
|
||||
// AUDIO CLASS DRIVER CONFIGURATION
|
||||
//--------------------------------------------------------------------
|
||||
|
@ -115,7 +119,7 @@
|
|||
#define CFG_TUD_AUDIO_ENABLE_EP_OUT 1
|
||||
#define CFG_TUD_AUDIO_ENABLE_FEEDBACK_EP 1
|
||||
|
||||
#define CFG_TUD_AUDIO_FUNC_1_DESC_LEN TUD_AUDIO_IO_DESC_LEN
|
||||
#define CFG_TUD_AUDIO_FUNC_1_DESC_LEN AIOC_AUDIO_DESC_LEN
|
||||
#define CFG_TUD_AUDIO_FUNC_1_N_AS_INT 1
|
||||
#define CFG_TUD_AUDIO_FUNC_1_CTRL_BUF_SZ 64
|
||||
#define CFG_TUD_AUDIO_FUNC_1_N_BYTES_PER_SAMPLE 2
|
||||
|
|
|
@ -1,6 +1,7 @@
|
|||
#include "stm32f3xx_hal.h"
|
||||
#include "aioc.h"
|
||||
#include "led.h"
|
||||
#include "ptt.h"
|
||||
#include "usb.h"
|
||||
#include <assert.h>
|
||||
#include <stdio.h>
|
||||
|
@ -91,6 +92,8 @@ int main(void)
|
|||
LED_MODE(0, LED_MODE_SLOWPULSE2X);
|
||||
LED_MODE(1, LED_MODE_SLOWPULSE2X);
|
||||
|
||||
PTT_Init();
|
||||
|
||||
USB_Init();
|
||||
|
||||
uint32_t i = 0;
|
||||
|
|
|
@ -4,6 +4,7 @@
|
|||
#include "tusb.h"
|
||||
#include "usb_serial.h"
|
||||
#include "usb_audio.h"
|
||||
#include "usb_hid.h"
|
||||
|
||||
// We have ISOCHRONOUS endpoints defined that share the same endpoint number, but have opposing directions.
|
||||
// However with STM32 hardware, ISOCHRONOUS endpoints use both RX and TX structures of the same endpoint register in hardware
|
||||
|
@ -26,13 +27,17 @@ uint8_t tu_stm32_edpt_number_cb(uint8_t addr)
|
|||
case EPNUM_AUDIO_FB:
|
||||
return 0x03;
|
||||
|
||||
case EPNUM_CDC_0_OUT:
|
||||
case EPNUM_CDC_0_IN:
|
||||
case EPNUM_HID_IN:
|
||||
case EPNUM_HID_OUT:
|
||||
return 0x04;
|
||||
|
||||
case EPNUM_CDC_0_NOTIF:
|
||||
case EPNUM_CDC_0_OUT:
|
||||
case EPNUM_CDC_0_IN:
|
||||
return 0x05;
|
||||
|
||||
case EPNUM_CDC_0_NOTIF:
|
||||
return 0x06;
|
||||
|
||||
default:
|
||||
TU_BREAKPOINT();
|
||||
return 0x00;
|
||||
|
@ -127,6 +132,7 @@ void USB_Init(void)
|
|||
// Init classes
|
||||
USB_SerialInit();
|
||||
USB_AudioInit();
|
||||
USB_HIDInit();
|
||||
|
||||
// Start USB Stack
|
||||
tud_init(BOARD_TUD_RHPORT);
|
||||
|
|
|
@ -52,10 +52,50 @@ uint8_t const* tud_descriptor_device_cb(void) {
|
|||
return (uint8_t const*) &desc_device;
|
||||
}
|
||||
|
||||
//--------------------------------------------------------------------+
|
||||
// HID Report Descriptor
|
||||
//--------------------------------------------------------------------+
|
||||
|
||||
uint8_t const desc_hid_report[] = {
|
||||
/* CM108 emulation */
|
||||
HID_USAGE_PAGE ( HID_USAGE_PAGE_CONSUMER ),
|
||||
HID_USAGE ( HID_USAGE_CONSUMER_CONTROL ),
|
||||
HID_COLLECTION ( HID_COLLECTION_APPLICATION ),
|
||||
/* Input */
|
||||
HID_USAGE ( 0x00 ),
|
||||
HID_LOGICAL_MIN ( 0x00 ),
|
||||
HID_LOGICAL_MAX_N ( 0xff, 2 ),
|
||||
HID_REPORT_SIZE ( 8 ),
|
||||
HID_REPORT_COUNT( 4 ),
|
||||
HID_INPUT ( HID_DATA | HID_VARIABLE | HID_ABSOLUTE ),
|
||||
/* Output */
|
||||
HID_USAGE ( 0x00 ),
|
||||
HID_LOGICAL_MIN ( 0x00 ),
|
||||
HID_LOGICAL_MAX_N ( 0xff, 2 ),
|
||||
HID_REPORT_SIZE ( 8 ),
|
||||
HID_REPORT_COUNT( 4 ),
|
||||
HID_OUTPUT ( HID_DATA | HID_VARIABLE | HID_ABSOLUTE ),
|
||||
HID_COLLECTION_END
|
||||
};
|
||||
|
||||
// Invoked when received GET HID REPORT DESCRIPTOR
|
||||
// Application return pointer to descriptor
|
||||
// Descriptor contents must exist long enough for transfer to complete
|
||||
uint8_t const * tud_hid_descriptor_report_cb(uint8_t itf)
|
||||
{
|
||||
(void) itf;
|
||||
return desc_hid_report;
|
||||
}
|
||||
|
||||
//--------------------------------------------------------------------+
|
||||
// Configuration Descriptor
|
||||
//--------------------------------------------------------------------+
|
||||
#define CONFIG_TOTAL_LEN (TUD_CONFIG_DESC_LEN + CFG_TUD_CDC * TUD_CDC_DESC_LEN + CFG_TUD_AUDIO * TUD_AUDIO_IO_DESC_LEN)
|
||||
#define CONFIG_TOTAL_LEN ( \
|
||||
TUD_CONFIG_DESC_LEN + \
|
||||
AIOC_AUDIO_DESC_LEN + \
|
||||
AIOC_HID_DESC_LEN + \
|
||||
AIOC_CDC_DESC_LEN \
|
||||
)
|
||||
|
||||
uint8_t const desc_fs_configuration[] = {
|
||||
// Config number, interface count, string index, total length, attribute, power in mA
|
||||
|
@ -68,7 +108,28 @@ uint8_t const desc_fs_configuration[] = {
|
|||
/* _power_ma */ 100
|
||||
),
|
||||
|
||||
TUD_CDC_DESCRIPTOR(
|
||||
AIOC_AUDIO_DESCRIPTOR(
|
||||
/* _itfnum */ ITF_NUM_AUDIO_CONTROL,
|
||||
/* _stridx */ STR_IDX_AUDIOITF,
|
||||
/* _nBytesPerSample */ CFG_TUD_AUDIO_FUNC_1_N_BYTES_PER_SAMPLE,
|
||||
/* _nBitsUsedPerSample */ CFG_TUD_AUDIO_FUNC_1_N_BYTES_PER_SAMPLE*8,
|
||||
/* _epin */ EPNUM_AUDIO_IN,
|
||||
/* _epinsize */ CFG_TUD_AUDIO_FUNC_1_EP_IN_SZ_MAX,
|
||||
/* _epout */ EPNUM_AUDIO_OUT,
|
||||
/* _epoutsize */ CFG_TUD_AUDIO_FUNC_1_EP_OUT_SZ_MAX,
|
||||
/* _epfb */ EPNUM_AUDIO_FB
|
||||
),
|
||||
AIOC_HID_DESCRIPTOR(
|
||||
/* _itfnum */ ITF_NUM_HID,
|
||||
/* _stridx */ STR_IDX_HIDITF,
|
||||
/* _boot_protocol */HID_ITF_PROTOCOL_NONE,
|
||||
/*_report_desc_len*/sizeof(desc_hid_report),
|
||||
/* _epin */ EPNUM_HID_IN,
|
||||
/* _epsize */ CFG_TUD_HID_EP_BUFSIZE,
|
||||
/* _ep_interval */ 0x20
|
||||
),
|
||||
|
||||
AIOC_CDC_DESCRIPTOR(
|
||||
/* _itfnum */ ITF_NUM_CDC_0,
|
||||
/* _stridx */ STR_IDX_CDCITF,
|
||||
/* _ep_notif */ EPNUM_CDC_0_NOTIF,
|
||||
|
@ -76,18 +137,6 @@ uint8_t const desc_fs_configuration[] = {
|
|||
/* _epout */ EPNUM_CDC_0_OUT,
|
||||
/* _epin */ EPNUM_CDC_0_IN,
|
||||
/* _epsize */ CFG_TUD_CDC_EP_BUFSIZE
|
||||
),
|
||||
|
||||
TUD_AUDIO_IO_DESCRIPTOR(
|
||||
/*_itfnum*/ ITF_NUM_AUDIO_CONTROL,
|
||||
/*_stridx*/ STR_IDX_AUDIOITF,
|
||||
/*_nBytesPerSample*/ CFG_TUD_AUDIO_FUNC_1_N_BYTES_PER_SAMPLE,
|
||||
/*_nBitsUsedPerSample*/ CFG_TUD_AUDIO_FUNC_1_N_BYTES_PER_SAMPLE*8,
|
||||
/*_epin*/ EPNUM_AUDIO_IN,
|
||||
/*_epinsize*/ CFG_TUD_AUDIO_FUNC_1_EP_IN_SZ_MAX,
|
||||
/*_epout*/ EPNUM_AUDIO_OUT,
|
||||
/*_epoutsize*/ CFG_TUD_AUDIO_FUNC_1_EP_OUT_SZ_MAX,
|
||||
/*_epfb*/ EPNUM_AUDIO_FB
|
||||
)
|
||||
};
|
||||
|
||||
|
@ -209,6 +258,10 @@ const uint16_t * tud_descriptor_string_cb(uint8_t index, uint16_t langid) {
|
|||
len = ascii_to_utf16(ptr, len, USB_STRING_AUDIOOUTCHAN);
|
||||
break;
|
||||
|
||||
case STR_IDX_HIDITF:
|
||||
len = ascii_to_utf16(ptr, len, USB_STRING_HIDITF);
|
||||
break;
|
||||
|
||||
default:
|
||||
TU_ASSERT(0, NULL);
|
||||
break;
|
||||
|
|
|
@ -3,11 +3,12 @@
|
|||
|
||||
/* Interfaces */
|
||||
enum USB_DESCRIPTORS_ITF {
|
||||
ITF_NUM_CDC_0 = 0,
|
||||
ITF_NUM_CDC_0_DATA,
|
||||
ITF_NUM_AUDIO_CONTROL,
|
||||
ITF_NUM_AUDIO_CONTROL = 0,
|
||||
ITF_NUM_AUDIO_STREAMING_OUT,
|
||||
ITF_NUM_AUDIO_STREAMING_IN,
|
||||
ITF_NUM_HID, /* For CM108 compatibility make this interface #3 */
|
||||
ITF_NUM_CDC_0,
|
||||
ITF_NUM_CDC_0_DATA,
|
||||
ITF_NUM_TOTAL
|
||||
};
|
||||
|
||||
|
@ -17,7 +18,6 @@ enum USB_STRING_IDX {
|
|||
STR_IDX_MANUFACTURER,
|
||||
STR_IDX_PRODUCT,
|
||||
STR_IDX_SERIAL,
|
||||
STR_IDX_CDCITF,
|
||||
STR_IDX_AUDIOITF,
|
||||
STR_IDX_AUDIOIN,
|
||||
STR_IDX_AUDIOOUT,
|
||||
|
@ -25,6 +25,8 @@ enum USB_STRING_IDX {
|
|||
STR_IDX_AUDIOOUTVOL,
|
||||
STR_IDX_AUDIOINCHAN,
|
||||
STR_IDX_AUDIOOUTCHAN,
|
||||
STR_IDX_HIDITF,
|
||||
STR_IDX_CDCITF
|
||||
};
|
||||
|
||||
#define USB_VID 0x1209
|
||||
|
@ -33,7 +35,6 @@ enum USB_STRING_IDX {
|
|||
|
||||
#define USB_STRING_MANUFACTURER "AIOC"
|
||||
#define USB_STRING_PRODUCT "All-In-One-Cable"
|
||||
#define USB_STRING_CDCITF "AIOC CDC"
|
||||
#define USB_STRING_AUDIOITF "AIOC Audio"
|
||||
#define USB_STRING_AUDIOIN "AIOC Audio In"
|
||||
#define USB_STRING_AUDIOOUT "AIOC Audio Out"
|
||||
|
@ -41,14 +42,19 @@ enum USB_STRING_IDX {
|
|||
#define USB_STRING_AUDIOOUTVOL "AIOC Audio Out Volume"
|
||||
#define USB_STRING_AUDIOINCHAN "AIOC Audio In Channel"
|
||||
#define USB_STRING_AUDIOOUTCHAN "AIOC Audio Out Channel"
|
||||
#define USB_STRING_CDCITF "AIOC CDC"
|
||||
#define USB_STRING_HIDITF "AIOC HID"
|
||||
|
||||
/* Endpoints */
|
||||
#define EPNUM_AUDIO_IN 0x81
|
||||
#define EPNUM_AUDIO_OUT 0x02
|
||||
#define EPNUM_AUDIO_FB 0x82
|
||||
#define EPNUM_CDC_0_OUT 0x03
|
||||
#define EPNUM_CDC_0_IN 0x83
|
||||
#define EPNUM_CDC_0_NOTIF 0x84
|
||||
#define EPNUM_HID_IN 0x83
|
||||
#define EPNUM_HID_OUT 0x03
|
||||
#define EPNUM_CDC_0_OUT 0x04
|
||||
#define EPNUM_CDC_0_IN 0x84
|
||||
#define EPNUM_CDC_0_NOTIF 0x85
|
||||
|
||||
|
||||
/* Custom Audio Descriptor.
|
||||
* Courtesy of https://github.com/hathach/tinyusb/issues/1249#issuecomment-1148727765 */
|
||||
|
@ -65,7 +71,7 @@ enum USB_STRING_IDX {
|
|||
#define AUDIO_NUM_INCHANNELS 0x01
|
||||
#define AUDIO_NUM_OUTCHANNELS 0x01
|
||||
|
||||
#define TUD_AUDIO_CTRL_TOTAL_LEN ( \
|
||||
#define AIOC_AUDIO_CTRL_TOTAL_LEN ( \
|
||||
TUD_AUDIO_DESC_CLK_SRC_LEN + \
|
||||
TUD_AUDIO_DESC_INPUT_TERM_LEN + \
|
||||
TUD_AUDIO_DESC_FEATURE_UNIT_ONE_CHANNEL_LEN + \
|
||||
|
@ -75,11 +81,11 @@ enum USB_STRING_IDX {
|
|||
TUD_AUDIO_DESC_OUTPUT_TERM_LEN + \
|
||||
TUD_AUDIO_DESC_FEATURE_UNIT_ONE_CHANNEL_LEN)
|
||||
|
||||
#define TUD_AUDIO_IO_DESC_LEN ( \
|
||||
#define AIOC_AUDIO_DESC_LEN ( \
|
||||
TUD_AUDIO_DESC_IAD_LEN + \
|
||||
TUD_AUDIO_DESC_STD_AC_LEN + \
|
||||
TUD_AUDIO_DESC_CS_AC_LEN + \
|
||||
TUD_AUDIO_CTRL_TOTAL_LEN + \
|
||||
AIOC_AUDIO_CTRL_TOTAL_LEN + \
|
||||
/* Speaker Interface */ \
|
||||
TUD_AUDIO_DESC_STD_AS_INT_LEN + \
|
||||
TUD_AUDIO_DESC_STD_AS_INT_LEN + \
|
||||
|
@ -96,14 +102,14 @@ enum USB_STRING_IDX {
|
|||
TUD_AUDIO_DESC_STD_AS_ISO_EP_LEN + \
|
||||
TUD_AUDIO_DESC_CS_AS_ISO_EP_LEN)
|
||||
|
||||
#define TUD_AUDIO_IO_DESCRIPTOR(_itfnum, _stridx, _nBytesPerSample, _nBitsUsedPerSample, _epin, _epinsize, _epout, _epoutsize, _epfb) \
|
||||
#define AIOC_AUDIO_DESCRIPTOR(_itfnum, _stridx, _nBytesPerSample, _nBitsUsedPerSample, _epin, _epinsize, _epout, _epoutsize, _epfb) \
|
||||
/* Standard Interface Association Descriptor (IAD) */ \
|
||||
TUD_AUDIO_DESC_IAD(_itfnum, AUDIO_NUM_INTERFACES, /*_stridx*/ 0x00), \
|
||||
/* Audio Control Interface */ \
|
||||
/* Standard AC Interface Descriptor(4.7.1) */ \
|
||||
TUD_AUDIO_DESC_STD_AC(/*_itfnum*/ _itfnum, /*_nEPs*/ 0x00, /*_stridx*/ _stridx), \
|
||||
/* Class-Specific AC Interface Header Descriptor(4.7.2) */ \
|
||||
TUD_AUDIO_DESC_CS_AC(/*_bcdADC*/ 0x0200, AUDIO_FUNC_CONVERTER, TUD_AUDIO_CTRL_TOTAL_LEN, /*_ctrl*/ AUDIO_CS_AS_INTERFACE_CTRL_LATENCY_POS), \
|
||||
TUD_AUDIO_DESC_CS_AC(/*_bcdADC*/ 0x0200, AUDIO_FUNC_CONVERTER, AIOC_AUDIO_CTRL_TOTAL_LEN, /*_ctrl*/ AUDIO_CS_AS_INTERFACE_CTRL_LATENCY_POS), \
|
||||
/* Clock Source Descriptor(4.7.2.1) */ \
|
||||
TUD_AUDIO_DESC_CLK_SRC(AUDIO_CTRL_ID_SPK_CLOCK, AUDIO_CLOCK_SOURCE_ATT_INT_PRO_CLK, (AUDIO_CTRL_RW << AUDIO_CLOCK_SOURCE_CTRL_CLK_FRQ_POS), /*_assocTerm*/ AUDIO_CTRL_ID_SPK_INPUT_STREAM, /*_stridx*/ 0x00), \
|
||||
/* Speaker Terminals */ \
|
||||
|
@ -147,4 +153,19 @@ enum USB_STRING_IDX {
|
|||
/* Class-Specific AS Isochronous Audio Data Endpoint Descriptor(4.10.1.2) */ \
|
||||
TUD_AUDIO_DESC_CS_AS_ISO_EP(AUDIO_CS_AS_ISO_DATA_EP_ATT_NON_MAX_PACKETS_OK, AUDIO_CTRL_NONE, AUDIO_CS_AS_ISO_DATA_EP_LOCK_DELAY_UNIT_UNDEFINED, 0x0000)
|
||||
|
||||
|
||||
#define AIOC_HID_DESC_LEN (9 + 9 + 7)
|
||||
|
||||
#define AIOC_HID_DESCRIPTOR(_itfnum, _stridx, _boot_protocol, _report_desc_len, _epin, _epsize, _ep_interval) \
|
||||
/* Interface */\
|
||||
9, TUSB_DESC_INTERFACE, _itfnum, 0, 1, TUSB_CLASS_HID, (uint8_t)((_boot_protocol) ? (uint8_t)HID_SUBCLASS_BOOT : 0), _boot_protocol, _stridx,\
|
||||
/* HID descriptor */\
|
||||
9, HID_DESC_TYPE_HID, U16_TO_U8S_LE(0x0100), 0, 1, HID_DESC_TYPE_REPORT, U16_TO_U8S_LE(_report_desc_len),\
|
||||
/* Endpoint In */\
|
||||
7, TUSB_DESC_ENDPOINT, _epin, TUSB_XFER_INTERRUPT, U16_TO_U8S_LE(_epsize), _ep_interval
|
||||
|
||||
#define AIOC_CDC_DESC_LEN TUD_CDC_DESC_LEN
|
||||
|
||||
#define AIOC_CDC_DESCRIPTOR TUD_CDC_DESCRIPTOR
|
||||
|
||||
#endif /* USB_DESCRIPTORS_H_ */
|
||||
|
|
|
@ -0,0 +1,70 @@
|
|||
#include "usb_hid.h"
|
||||
#include "tusb.h"
|
||||
#include "ptt.h"
|
||||
#include "usb_descriptors.h"
|
||||
|
||||
#define USB_HID_INOUT_REPORT_LEN 4
|
||||
|
||||
static uint8_t gpioState = 0x00;
|
||||
|
||||
static void ControlPTT(uint8_t gpio)
|
||||
{
|
||||
/* PTT1 on GPIO 3, PTT2 on GPIO4 */
|
||||
uint8_t pttMask = (gpio & 0x04 ? PTT_MASK_PTT1 : 0) |
|
||||
(gpio & 0x08 ? PTT_MASK_PTT2 : 0);
|
||||
|
||||
PTT_Control(pttMask);
|
||||
}
|
||||
|
||||
// Invoked when received GET_REPORT control request
|
||||
// Application must fill buffer report's content and return its length.
|
||||
// Return zero will cause the stack to STALL request
|
||||
uint16_t tud_hid_get_report_cb(uint8_t itf, uint8_t report_id, hid_report_type_t report_type, uint8_t* buffer, uint16_t reqlen)
|
||||
{
|
||||
(void) itf;
|
||||
(void) report_id;
|
||||
(void) report_type;
|
||||
(void) buffer;
|
||||
(void) reqlen;
|
||||
|
||||
buffer[0] = 0x00;
|
||||
buffer[1] = gpioState;
|
||||
buffer[2] = 0x00;
|
||||
buffer[3] = 0x00;
|
||||
|
||||
return USB_HID_INOUT_REPORT_LEN;
|
||||
}
|
||||
|
||||
// Invoked when received SET_REPORT control request
|
||||
void tud_hid_set_report_cb(uint8_t itf, uint8_t report_id, hid_report_type_t report_type, uint8_t const* buffer, uint16_t bufsize)
|
||||
{
|
||||
(void) itf;
|
||||
(void) report_id;
|
||||
|
||||
switch (report_type) {
|
||||
case HID_REPORT_TYPE_OUTPUT:
|
||||
TU_ASSERT(bufsize == USB_HID_INOUT_REPORT_LEN, /* */);
|
||||
|
||||
/* Output report, emulate CM108 behaviour */
|
||||
if ((buffer[0] & 0xC0) == 0) {
|
||||
gpioState = buffer[1];
|
||||
ControlPTT(gpioState);
|
||||
}
|
||||
break;
|
||||
|
||||
case HID_REPORT_TYPE_FEATURE:
|
||||
/* Custom extension for configuring the AIOC */
|
||||
break;
|
||||
|
||||
default:
|
||||
TU_BREAKPOINT();
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
void USB_HIDInit(void)
|
||||
{
|
||||
|
||||
|
||||
}
|
|
@ -0,0 +1,6 @@
|
|||
#ifndef USB_HID_H_
|
||||
#define USB_HID_H_
|
||||
|
||||
void USB_HIDInit(void);
|
||||
|
||||
#endif /* USB_HID_H_ */
|
Ładowanie…
Reference in New Issue