Open pitman75 opened 1 year ago
Dump USB data transfer for STM32 HID Keyboard standalone and for composite HID Keyboard + UAC MIC
Looks like for composite device host doesn't read some config data and device for host is in wrong state. Data goes but rejected.
RAW dump data usb_composite-1-2022-07-20.zip usb_keyboard-2-2022-07-20.zip
After some changes my composite device works well. Thanks a lot of your huge work!
That is nice!! Do you mind sharing your changes? If so, please send a pull request.
I can explain my changes and test it on STM32L475. Now I have hardware USB protocol analyzer and can debug USB communications on low-level.
General:
if(!STM32F1_DEVICE) else if (hpcd->Init.speed == PCD_SPEED_HIGH) { speed = USBD_SPEED_HIGH; }
I'll resume later. Your plugin is very helpfull I can help you to do it better.
Also for HID keyboard I replaced report descriptor
In the file usbd_hid_keyboard.h change size of report descriptor
In the file usbd_hid_keyboard.c replace report descriptor
/ HID keyboard report descriptor / ALIGN_BEGIN static uint8_t HID_KEYBOARD_ReportDesc[HID_KEYBOARD_REPORT_DESC_SIZE] ALIGN_END = { 0x05, 0x01, // USAGE_PAGE (Generic Desktop) 0x09, 0x06, // USAGE (Keyboard) 0xa1, 0x01, // COLLECTION (Application) 0x05, 0x07, // USAGE_PAGE (Keyboard) 0x19, 0xe0, // USAGE_MINIMUM (Keyboard LeftControl) 0x29, 0xe7, // USAGE_MAXIMUM (Keyboard Right GUI) 0x15, 0x00, // LOGICAL_MINIMUM (0) 0x25, 0x01, // LOGICAL_MAXIMUM (1) 0x75, 0x01, // REPORT_SIZE (1) 0x95, 0x08, // REPORT_COUNT (8) 0x81, 0x02, // INPUT (Data,Var,Abs) 0x95, 0x01, // REPORT_COUNT (1) 0x75, 0x08, // REPORT_SIZE (8) 0x81, 0x03, // INPUT (Cnst,Var,Abs) 0x95, 0x05, // REPORT_COUNT (5) 0x75, 0x01, // REPORT_SIZE (1) 0x05, 0x08, // USAGE_PAGE (LEDs) 0x19, 0x01, // USAGE_MINIMUM (Num Lock) 0x29, 0x05, // USAGE_MAXIMUM (Kana) 0x91, 0x02, // OUTPUT (Data,Var,Abs) 0x95, 0x01, // REPORT_COUNT (1) 0x75, 0x03, // REPORT_SIZE (3) 0x91, 0x03, // OUTPUT (Cnst,Var,Abs) 0x95, 0x06, // REPORT_COUNT (6) 0x75, 0x08, // REPORT_SIZE (8) 0x15, 0x00, // LOGICAL_MINIMUM (0) 0x25, 0x65, // LOGICAL_MAXIMUM (101) 0x05, 0x07, // USAGE_PAGE (Keyboard) 0x19, 0x00, // USAGE_MINIMUM (Reserved (no event indicated)) 0x29, 0x65, // USAGE_MAXIMUM (Keyboard Application) 0x81, 0x00, // INPUT (Data,Ary,Abs) 0xc0 // END_COLLECTION };
After this changes for keyboard it works well.
Generic changes for usb microphone:
In the file usbd_audio_mic.c fix incorrect size of section:
/* USB Microphone Audio Feature Unit Descriptor */
0x07 + AUDIO_MIC_CHANNELS + 1, /* bLength */
In the file usbd_audio_mic.h change value for MIN, MAX, RES of audio control
After this changes Windows 10 read its without any problem.
Dirty solution for send audio data
case USB_REQ_SET_INTERFACE: if (pdev->dev_state == USBD_STATE_CONFIGURED) { if ((uint8_t)(req->wValue) <= USBD_MAX_NUM_INTERFACES) { haudio->alt_setting = (uint8_t)(req->wValue); //printf("Set interface USB command: %lu for EP 0x%02X\r\n", haudio->alt_setting, AUDIO_MIC_EP); if (haudio->alt_setting) { printf("%lu start\r\n", HAL_GetTick()); audio_play_start(); } else { printf("%lu stop\r\n", HAL_GetTick()); audio_play_stop(); }
USBD_LL_FlushEP(pdev, AUDIO_MIC_EP);
}
else
{
printf("wVal wrong 0x%02X\r\n", req->wValue);
/* Call the error management function (command will be NAKed */
USBD_CtlError(pdev, req);
ret = USBD_FAIL;
}
}
else
{
printf("USB_REQ_GET_INTERFACE wrong 0x%02X\r\n", pdev->dev_state);
USBD_CtlError(pdev, req);
ret = USBD_FAIL;
}
break;
Add flush MIC IN to static uint8_t USBD_AUDIO_MIC_IsoINIncomplete(USBD_HandleTypeDef *pdev, uint8_t epnum) { UNUSED(pdev); UNUSED(epnum); USBD_LL_FlushEP (pdev, AUDIO_MIC_EP); return (uint8_t)USBD_OK; }
When capture audio started -> enable 1ms timer with interrupt to fill audio data to TX buffer.
Very important that when capture started to fill any data to output buffer. Without data after few rejected IN requests in Windows and 5000 IN requests in Linux -> the MIC IN pipe will be stopped without notification on application side. I added play silent white noise before and after played prerecorded audio all time while capture exist.
Need do working USB composite device USB keyboard and USB microphone. I did it for CubeMX standalone devices, it works well.
The MCU is STM32L476 STM32CubeMX 1.9.0
Software Pack Componet Selector marked:
Software Packs Parameter Settings marked:
Also configured FreeRTOS, MX_USB_DEVICE_Init() called at once when default task started.
Build process break on:
`#if(!STM32F1_DEVICE) else if (hpcd->Init.speed == PCD_SPEED_HIGH) { speed = USBD_SPEED_HIGH; }
endif`
PCD_SPEED_HIGH undeclared.
After remove this #if....#endif build process is success. PC Windows/Linux found composite USB device keyboard + microphone. But when I send key like keyboard via function USBD_HID_Keyboard_SendReport keys not typed on console. I used wireshark in Linux and see that MCU send ISO IN packet like in worked standalone solution. But no any key on console.
Also I see error in USB description by Thesicon USB Descriptor Dumper
`AC Interface Header Descriptor:
0x09 bLength 0x24 bDescriptorType 0x01 bDescriptorSubtype 0x0100 bcdADC 0x0026 wTotalLength (38 bytes)
usb_composite_not_wrk.txt
What is wrong?