From 86f136c733912eaa3b6e79bae3ceb99e7821edf9 Mon Sep 17 00:00:00 2001 From: Damjan Adamic Date: Fri, 21 Mar 2014 20:58:41 +0100 Subject: [PATCH] * USB Joystick implemented * USB Mass storage mode removed from openTX (this is now supported by Bootloader) --- radio/src/Makefile | 8 +- radio/src/opentx.cpp | 82 ++- .../Core/src/usbd_core.c | 8 +- .../STM32_USB_OTG_Driver/inc/usb_bsp.h | 2 + .../STM32_USB_OTG_Driver/src/usb_dcd_int.c | 30 ++ radio/src/targets/taranis/board_taranis.h | 16 +- radio/src/targets/taranis/usb_bsp.c | 28 +- radio/src/targets/taranis/usb_conf.h | 5 - radio/src/targets/taranis/usb_driver.c | 31 +- radio/src/targets/taranis/usbd_conf.h | 6 + radio/src/targets/taranis/usbd_desc.c | 28 +- radio/src/targets/taranis/usbd_hid_joystick.c | 479 ++++++++++++++++++ radio/src/targets/taranis/usbd_usr.cpp | 3 - 13 files changed, 667 insertions(+), 59 deletions(-) create mode 100644 radio/src/targets/taranis/usbd_hid_joystick.c diff --git a/radio/src/Makefile b/radio/src/Makefile index b7ecaef64..781d88838 100644 --- a/radio/src/Makefile +++ b/radio/src/Makefile @@ -655,18 +655,14 @@ ifeq ($(PCB), TARANIS) SRC += targets/taranis/STM32F2xx_StdPeriph_Lib_V1.1.0/Libraries/STM32F2xx_StdPeriph_Driver/src/stm32f2xx_pwr.c SRC += targets/taranis/STM32F2xx_StdPeriph_Lib_V1.1.0/Libraries/STM32F2xx_StdPeriph_Driver/src/stm32f2xx_usart.c SRC += targets/taranis/STM32F2xx_StdPeriph_Lib_V1.1.0/Libraries/CMSIS/Device/ST/STM32F2xx/Source/Templates/gcc_ride7/startup_stm32f2xx.s - SRC += targets/taranis/usb_bsp.c targets/taranis/usbd_desc.c + SRC += targets/taranis/usb_bsp.c targets/taranis/usbd_desc.c targets/taranis/usbd_hid_joystick.c SRC += targets/taranis/STM32_USB-Host-Device_Lib_V2.1.0/Libraries/STM32_USB_OTG_Driver/src/usb_core.c SRC += targets/taranis/STM32_USB-Host-Device_Lib_V2.1.0/Libraries/STM32_USB_OTG_Driver/src/usb_dcd.c SRC += targets/taranis/STM32_USB-Host-Device_Lib_V2.1.0/Libraries/STM32_USB_OTG_Driver/src/usb_dcd_int.c SRC += targets/taranis/STM32_USB-Host-Device_Lib_V2.1.0/Libraries/STM32_USB_Device_Library/Core/src/usbd_core.c SRC += targets/taranis/STM32_USB-Host-Device_Lib_V2.1.0/Libraries/STM32_USB_Device_Library/Core/src/usbd_ioreq.c SRC += targets/taranis/STM32_USB-Host-Device_Lib_V2.1.0/Libraries/STM32_USB_Device_Library/Core/src/usbd_req.c - SRC += targets/taranis/STM32_USB-Host-Device_Lib_V2.1.0/Libraries/STM32_USB_Device_Library/Class/msc/src/usbd_msc_data.c - SRC += targets/taranis/STM32_USB-Host-Device_Lib_V2.1.0/Libraries/STM32_USB_Device_Library/Class/msc/src/usbd_msc_scsi.c - SRC += targets/taranis/STM32_USB-Host-Device_Lib_V2.1.0/Libraries/STM32_USB_Device_Library/Class/msc/src/usbd_msc_bot.c - SRC += targets/taranis/STM32_USB-Host-Device_Lib_V2.1.0/Libraries/STM32_USB_Device_Library/Class/msc/src/usbd_msc_core.c - EXTRABOARDSRC += targets/taranis/usbd_usr.cpp targets/taranis/usbd_storage_msd.cpp + EXTRABOARDSRC += targets/taranis/usbd_usr.cpp SRC += targets/sky9x/syscalls.c ifneq ($(LUA), NO) diff --git a/radio/src/opentx.cpp b/radio/src/opentx.cpp index 7f27376c5..7d507bd90 100644 --- a/radio/src/opentx.cpp +++ b/radio/src/opentx.cpp @@ -588,7 +588,7 @@ void modelDefault(uint8_t id) #if defined(MAVLINK) g_model.mavlink.rc_rssi_scale = 15; - g_model.mavlink.pc_rssi_en = 1; + g_model.mavlink.pc_rssi_en = 1; #endif } @@ -4581,6 +4581,44 @@ void opentxClose() } #endif + +#if defined(PCBTARANIS) && !defined(SIMU) +extern USB_OTG_CORE_HANDLE USB_OTG_dev; + +/* + Prepare and send new USB data packet + + The format of HID_Buffer is defined by + USB endpoint description can be found in + file usb_hid_joystick.c, variable HID_JOYSTICK_ReportDesc +*/ +void usb_joystick_update(void) +{ + static uint8_t HID_Buffer[HID_IN_PACKET]; + + //buttons + HID_Buffer[0] = 0; //buttons + for (int i = 0; i < 8; ++i) { + if ( channelOutputs[i+8] > 0 ) { + HID_Buffer[0] |= (1 << i); + } + } + + //analog values + //uint8_t * p = HID_Buffer + 1; + for (int i = 0; i < 8; ++i) { + int16_t value = channelOutputs[i] / 8; + if ( value > 127 ) value = 127; + else if ( value < -127 ) value = -127; + HID_Buffer[i+1] = static_cast(value); + } + + USBD_HID_SendReport (&USB_OTG_dev, HID_Buffer, HID_IN_PACKET ); +} + +#endif //#if defined(PCBTARANIS) && !defined(SIMU) + + void perMain() { #if defined(SIMU) @@ -4732,14 +4770,24 @@ void perMain() } #endif -#if defined(PCBTARANIS) +#if defined(PCBTARANIS) && !defined(SIMU) static bool usbStarted = false; if (!usbStarted && usbPlugged()) { - opentxClose(); usbStart(); usbStarted = true; } -#endif + + if (usbStarted) { + if (!usbPlugged()) { + //disable USB + usbStop(); + usbStarted = false; + } + else { + usb_joystick_update(); + } + } +#endif //#if defined(PCBTARANIS) && !defined(SIMU) #if defined(NAVIGATION_STICKS) if (StickScrollAllowed) { @@ -4808,28 +4856,22 @@ void perMain() const char *warn = s_warning; uint8_t menu = s_menu_count; - if (usbPlugged()) { + if (!LCD_LOCKED()) { lcd_clear(); - menuMainView(0); - } - else { - if (!LCD_LOCKED()) { - lcd_clear(); - g_menuStack[g_menuStackPtr]((warn || menu) ? 0 : evt); - if (warn) DISPLAY_WARNING(evt); + g_menuStack[g_menuStackPtr]((warn || menu) ? 0 : evt); + if (warn) DISPLAY_WARNING(evt); #if defined(NAVIGATION_MENUS) - if (menu) { - const char * result = displayMenu(evt); - if (result) { - menuHandler(result); - putEvent(EVT_MENU_UP); - } + if (menu) { + const char * result = displayMenu(evt); + if (result) { + menuHandler(result); + putEvent(EVT_MENU_UP); } + } #endif #if defined(LUA) - evt = 0; + evt = 0; #endif - } } #if defined(LUA) diff --git a/radio/src/targets/taranis/STM32_USB-Host-Device_Lib_V2.1.0/Libraries/STM32_USB_Device_Library/Core/src/usbd_core.c b/radio/src/targets/taranis/STM32_USB-Host-Device_Lib_V2.1.0/Libraries/STM32_USB_Device_Library/Core/src/usbd_core.c index fa647eb0f..ec68fc1e4 100644 --- a/radio/src/targets/taranis/STM32_USB-Host-Device_Lib_V2.1.0/Libraries/STM32_USB_Device_Library/Core/src/usbd_core.c +++ b/radio/src/targets/taranis/STM32_USB-Host-Device_Lib_V2.1.0/Libraries/STM32_USB_Device_Library/Core/src/usbd_core.c @@ -159,14 +159,16 @@ void USBD_Init(USB_OTG_CORE_HANDLE *pdev, /** * @brief USBD_DeInit -* Re-Initialize th device library +* Deinitialize USB device library * @param pdev: device instance * @retval status: status */ USBD_Status USBD_DeInit(USB_OTG_CORE_HANDLE *pdev) { - /* Software Init */ - + /*Disable Interrupts*/ + USB_OTG_BSP_DisableInterrupt(pdev); + USB_OTG_DisableGlobalInt(pdev); + USB_OTG_BSP_Deinit(pdev); return USBD_OK; } diff --git a/radio/src/targets/taranis/STM32_USB-Host-Device_Lib_V2.1.0/Libraries/STM32_USB_OTG_Driver/inc/usb_bsp.h b/radio/src/targets/taranis/STM32_USB-Host-Device_Lib_V2.1.0/Libraries/STM32_USB_OTG_Driver/inc/usb_bsp.h index 6f1ebdb78..944683a35 100644 --- a/radio/src/targets/taranis/STM32_USB-Host-Device_Lib_V2.1.0/Libraries/STM32_USB_OTG_Driver/inc/usb_bsp.h +++ b/radio/src/targets/taranis/STM32_USB-Host-Device_Lib_V2.1.0/Libraries/STM32_USB_OTG_Driver/inc/usb_bsp.h @@ -78,9 +78,11 @@ void BSP_Init(void); void USB_OTG_BSP_Init (USB_OTG_CORE_HANDLE *pdev); +void USB_OTG_BSP_Deinit(USB_OTG_CORE_HANDLE *pdev); void USB_OTG_BSP_uDelay (const uint32_t usec); void USB_OTG_BSP_mDelay (const uint32_t msec); void USB_OTG_BSP_EnableInterrupt (USB_OTG_CORE_HANDLE *pdev); +void USB_OTG_BSP_DisableInterrupt (USB_OTG_CORE_HANDLE *pdev); #ifdef USE_HOST_MODE void USB_OTG_BSP_ConfigVBUS(USB_OTG_CORE_HANDLE *pdev); void USB_OTG_BSP_DriveVBUS(USB_OTG_CORE_HANDLE *pdev,uint8_t state); diff --git a/radio/src/targets/taranis/STM32_USB-Host-Device_Lib_V2.1.0/Libraries/STM32_USB_OTG_Driver/src/usb_dcd_int.c b/radio/src/targets/taranis/STM32_USB-Host-Device_Lib_V2.1.0/Libraries/STM32_USB_OTG_Driver/src/usb_dcd_int.c index 32984e610..10840e764 100644 --- a/radio/src/targets/taranis/STM32_USB-Host-Device_Lib_V2.1.0/Libraries/STM32_USB_OTG_Driver/src/usb_dcd_int.c +++ b/radio/src/targets/taranis/STM32_USB-Host-Device_Lib_V2.1.0/Libraries/STM32_USB_OTG_Driver/src/usb_dcd_int.c @@ -470,6 +470,36 @@ static uint32_t DCD_HandleInEP_ISR(USB_OTG_CORE_HANDLE *pdev) } if (diepint.b.emptyintr) { + /*===============ADDED SECTION ==============================*/ + /* + This only applies to INTERRUPT transfer mode. + + diepint.b.emptyintr interrupt can't be reset by writing 1 to + DIEPINT register. According to reference manual, this bit + is read-only. + + The CLEAR_IN_EP_INTR(epnum, emptyintr) does not work! + + The only way to stop this interrupt is to disable it using + mask register DIEPEMPMSK. + + Original code gets here, is unsuccessful at interrupt flag reset + and when interrupt handler returns, another one is fired again, + robbing CPU time, which is then spent only in interrupt handlers + (this one and all other that have higher priority) + + This only happens in HID mode (when interrupt in endpoint is + used) and when host is not actively polling device (us) for + update. This is situation on Linux when no program is using + joystick. The kernel/joystick driver stops polling device. + + */ + if ( pdev->dev.in_ep[epnum].type == USB_OTG_EP_INT ) { + + fifoemptymsk = 0x1 << epnum; + USB_OTG_MODIFY_REG32(&pdev->regs.DREGS->DIEPEMPMSK, fifoemptymsk, 0); + } + /*===============END OF ADDED SECTION ==============================*/ DCD_WriteEmptyTxFifo(pdev , epnum); diff --git a/radio/src/targets/taranis/board_taranis.h b/radio/src/targets/taranis/board_taranis.h index 1f9d38d83..41ad1f1e3 100644 --- a/radio/src/targets/taranis/board_taranis.h +++ b/radio/src/targets/taranis/board_taranis.h @@ -51,11 +51,14 @@ extern "C" { #include "STM32F2xx_StdPeriph_Lib_V1.1.0/Libraries/STM32F2xx_StdPeriph_Driver/inc/stm32f2xx_dma.h" #include "STM32F2xx_StdPeriph_Lib_V1.1.0/Libraries/STM32F2xx_StdPeriph_Driver/inc/stm32f2xx_usart.h" #include "STM32F2xx_StdPeriph_Lib_V1.1.0/Libraries/CMSIS/Device/ST/STM32F2xx/Include/stm32f2xx.h" -#include "STM32_USB-Host-Device_Lib_V2.1.0/Libraries/STM32_USB_Device_Library/Class/msc/inc/usbd_msc_core.h" -#include "STM32_USB-Host-Device_Lib_V2.1.0/Libraries/STM32_USB_Device_Library/Core/inc/usbd_usr.h" -#include "usbd_desc.h" -#include "usb_conf.h" -#include "usbd_conf.h" +#if !defined(SIMU) + #include "STM32_USB-Host-Device_Lib_V2.1.0/Libraries/STM32_USB_Device_Library/Class/msc/inc/usbd_msc_core.h" + #include "STM32_USB-Host-Device_Lib_V2.1.0/Libraries/STM32_USB_Device_Library/Class/hid/inc/usbd_hid_core.h" + #include "STM32_USB-Host-Device_Lib_V2.1.0/Libraries/STM32_USB_Device_Library/Core/inc/usbd_usr.h" + #include "usbd_desc.h" + #include "usb_conf.h" + #include "usbd_conf.h" +#endif #include "hal.h" #include "aspi.h" @@ -199,11 +202,12 @@ void pwrOff(void); #define IS_BACKLIGHT_ON() (TIM10->CCR1 != 0) // USB driver -int usbPlugged(void); #define BOOTLOADER_REQUEST() (0) #define usbBootloader() +uint8_t usbPlugged(void); void usbInit(void); void usbStart(void); +void usbStop(void); #ifdef __cplusplus } diff --git a/radio/src/targets/taranis/usb_bsp.c b/radio/src/targets/taranis/usb_bsp.c index 76fceaf79..f5aa51cac 100644 --- a/radio/src/targets/taranis/usb_bsp.c +++ b/radio/src/targets/taranis/usb_bsp.c @@ -82,9 +82,15 @@ void USB_OTG_BSP_Init(USB_OTG_CORE_HANDLE *pdev) RCC_APB2PeriphClockCmd(RCC_APB2Periph_SYSCFG, ENABLE); RCC_AHB2PeriphClockCmd(RCC_AHB2Periph_OTG_FS, ENABLE) ; } + +void USB_OTG_BSP_Deinit(USB_OTG_CORE_HANDLE *pdev) +{ + //nothing to do +} + /** * @brief USB_OTG_BSP_EnableInterrupt -* Enabele USB Global interrupt +* Enable USB Global interrupt * @param None * @retval None */ @@ -99,6 +105,26 @@ void USB_OTG_BSP_EnableInterrupt(USB_OTG_CORE_HANDLE *pdev) NVIC_InitStructure.NVIC_IRQChannelCmd = ENABLE; NVIC_Init(&NVIC_InitStructure); } + +/** +* @brief USB_OTG_BSP_DisableInterrupt +* Disable USB Global interrupt +* @param None +* @retval None +*/ +void USB_OTG_BSP_DisableInterrupt(USB_OTG_CORE_HANDLE *pdev) +{ + NVIC_InitTypeDef NVIC_InitStructure; + + NVIC_PriorityGroupConfig(NVIC_PriorityGroup_1); + NVIC_InitStructure.NVIC_IRQChannel = OTG_FS_IRQn; + NVIC_InitStructure.NVIC_IRQChannelPreemptionPriority = 1; + NVIC_InitStructure.NVIC_IRQChannelSubPriority = 3; + NVIC_InitStructure.NVIC_IRQChannelCmd = DISABLE; + NVIC_Init(&NVIC_InitStructure); +} + + /** * @brief USB_OTG_BSP_uDelay * This function provides delay time in micro sec diff --git a/radio/src/targets/taranis/usb_conf.h b/radio/src/targets/taranis/usb_conf.h index 6ac79fbad..587461e32 100644 --- a/radio/src/targets/taranis/usb_conf.h +++ b/radio/src/targets/taranis/usb_conf.h @@ -31,11 +31,6 @@ #include "STM32F2xx_StdPeriph_Lib_V1.1.0/Libraries/CMSIS/Device/ST/STM32F2xx/Include/stm32f2xx.h" -#define HID_IN_EP 0x81 -#define HID_OUT_EP 0x01 - -#define HID_IN_PACKET 4 -#define HID_OUT_PACKET 4 /* USB Core and PHY interface configuration. Tip: To avoid modifying these defines each time you need to change the USB diff --git a/radio/src/targets/taranis/usb_driver.c b/radio/src/targets/taranis/usb_driver.c index ea9ca3bde..4cd66d11a 100755 --- a/radio/src/targets/taranis/usb_driver.c +++ b/radio/src/targets/taranis/usb_driver.c @@ -38,9 +38,20 @@ #include "STM32_USB-Host-Device_Lib_V2.1.0/Libraries/STM32_USB_OTG_Driver/inc/usb_dcd_int.h" #include "STM32_USB-Host-Device_Lib_V2.1.0/Libraries/STM32_USB_OTG_Driver/inc/usb_bsp.h" -int usbPlugged(void) +uint8_t usbPlugged(void) { - return GPIO_ReadInputDataBit(GPIOA, PIN_FS_VBUS); + //debounce + static uint8_t debounced_state = 0; + static uint8_t last_state = 0; + if ( GPIO_ReadInputDataBit(GPIOA, PIN_FS_VBUS) ) { + if (last_state) debounced_state = 1; + last_state = 1; + } + else { + if (!last_state) debounced_state = 0; + last_state = 0; + } + return debounced_state; } USB_OTG_CORE_HANDLE USB_OTG_dev; @@ -50,12 +61,24 @@ void OTG_FS_IRQHandler(void) USBD_OTG_ISR_Handler (&USB_OTG_dev); } -void usbInit() +void usbInit(void) { USB_OTG_BSP_Init(&USB_OTG_dev); } -void usbStart() +void usbStart(void) { +#if !defined(BOOT) + //intialize USB as HID device + USBD_Init(&USB_OTG_dev, USB_OTG_FS_CORE_ID, &USR_desc, &USBD_HID_cb, &USR_cb); +#else + //intialize USB as MSC device USBD_Init(&USB_OTG_dev, USB_OTG_FS_CORE_ID, &USR_desc, &USBD_MSC_cb, &USR_cb); +#endif //!defined(BOOT) +} + + +void usbStop(void) +{ + USBD_DeInit(&USB_OTG_dev); } diff --git a/radio/src/targets/taranis/usbd_conf.h b/radio/src/targets/taranis/usbd_conf.h index 753544841..7308a64c8 100644 --- a/radio/src/targets/taranis/usbd_conf.h +++ b/radio/src/targets/taranis/usbd_conf.h @@ -46,6 +46,12 @@ #define MSC_MEDIA_PACKET 4096 +#define HID_IN_EP 0x81 +#define HID_OUT_EP 0x01 + +#define HID_IN_PACKET 9 +#define HID_OUT_PACKET 9 + #endif //__USBD_CONF__H__ diff --git a/radio/src/targets/taranis/usbd_desc.c b/radio/src/targets/taranis/usbd_desc.c index 4abd342ee..32fe20de5 100644 --- a/radio/src/targets/taranis/usbd_desc.c +++ b/radio/src/targets/taranis/usbd_desc.c @@ -31,6 +31,7 @@ #include "usbd_req.h" #include "usbd_conf.h" #include "usb_regs.h" +#include "board_taranis.h" /** @addtogroup STM32_USB_OTG_DEVICE_LIBRARY * @{ @@ -54,16 +55,24 @@ * @{ */ -#define USBD_VID 0x0483 -#define USBD_PID 0x5720 +#define USBD_VID 0x0483 -#define USBD_LANGID_STRING 0x409 -#define USBD_MANUFACTURER_STRING "FrSky" +#define USBD_LANGID_STRING 0x409 +#define USBD_MANUFACTURER_STRING "FrSky" +#define USBD_SERIALNUMBER_FS_STRING "00000000001B" -#define USBD_PRODUCT_FS_STRING "FrSky Taranis Mass Storage" -#define USBD_SERIALNUMBER_FS_STRING "00000000001B" -#define USBD_CONFIGURATION_FS_STRING "MSC Config" -#define USBD_INTERFACE_FS_STRING "MSC Interface" + +#if defined(BOOT) + #define USBD_PID 0x5720 + #define USBD_PRODUCT_FS_STRING "FrSky Taranis Bootloader" + #define USBD_CONFIGURATION_FS_STRING "MSC Config" + #define USBD_INTERFACE_FS_STRING "MSC Interface" +#else + #define USBD_PID 0x5710 + #define USBD_PRODUCT_FS_STRING "FrSky Taranis Joystick" + #define USBD_CONFIGURATION_FS_STRING "HID Config" + #define USBD_INTERFACE_FS_STRING "HID Interface" +#endif USBD_DEVICE USR_desc = { @@ -159,9 +168,7 @@ uint8_t * USBD_USR_LangIDStrDescriptor( uint8_t speed , uint16_t *length) */ uint8_t * USBD_USR_ProductStrDescriptor( uint8_t speed , uint16_t *length) { - USBD_GetString ((uint8_t*)USBD_PRODUCT_FS_STRING, USBD_StrDesc, length); - return USBD_StrDesc; } @@ -188,7 +195,6 @@ uint8_t * USBD_USR_ManufacturerStrDescriptor( uint8_t speed , uint16_t *length) uint8_t * USBD_USR_SerialStrDescriptor( uint8_t speed , uint16_t *length) { USBD_GetString ((uint8_t*)USBD_SERIALNUMBER_FS_STRING, USBD_StrDesc, length); - return USBD_StrDesc; } diff --git a/radio/src/targets/taranis/usbd_hid_joystick.c b/radio/src/targets/taranis/usbd_hid_joystick.c new file mode 100644 index 000000000..29870a824 --- /dev/null +++ b/radio/src/targets/taranis/usbd_hid_joystick.c @@ -0,0 +1,479 @@ +/** + ****************************************************************************** + * @file usbd_hid_core.c + * @author MCD Application Team + * @version V1.1.0 + * @date 19-March-2012 + * @brief This file provides the HID core functions. + * + * @verbatim + * + * =================================================================== + * HID Class Description + * =================================================================== + * This module manages the HID class V1.11 following the "Device Class Definition + * for Human Interface Devices (HID) Version 1.11 Jun 27, 2001". + * This driver implements the following aspects of the specification: + * - The Boot Interface Subclass + * - The Mouse protocol + * - Usage Page : Generic Desktop + * - Usage : Joystick) + * - Collection : Application + * + * @note In HS mode and when the DMA is used, all variables and data structures + * dealing with the DMA during the transaction process should be 32-bit aligned. + * + * + * @endverbatim + * + ****************************************************************************** + * @attention + * + *

© COPYRIGHT 2012 STMicroelectronics

+ * + * Licensed under MCD-ST Liberty SW License Agreement V2, (the "License"); + * You may not use this file except in compliance with the License. + * You may obtain a copy of the License at: + * + * http://www.st.com/software_license_agreement_liberty_v2 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + * + ****************************************************************************** + */ + +/* Includes ------------------------------------------------------------------*/ +#include "usbd_hid_core.h" +#include "usbd_req.h" +#include "usbd_desc.h" + +/** @addtogroup STM32_USB_OTG_DEVICE_LIBRARY + * @{ + */ + + +/** @defgroup USBD_HID + * @brief usbd core module + * @{ + */ + +/** @defgroup USBD_HID_Private_TypesDefinitions + * @{ + */ +/** + * @} + */ + + +/** @defgroup USBD_HID_Private_Defines + * @{ + */ + +/** + * @} + */ + + +/** @defgroup USBD_HID_Private_Macros + * @{ + */ +/** + * @} + */ + + + + +/** @defgroup USBD_HID_Private_FunctionPrototypes + * @{ + */ + + +static uint8_t USBD_HID_Init (void *pdev, + uint8_t cfgidx); + +static uint8_t USBD_HID_DeInit (void *pdev, + uint8_t cfgidx); + +static uint8_t USBD_HID_Setup (void *pdev, + USB_SETUP_REQ *req); + +static uint8_t *USBD_HID_GetCfgDesc (uint8_t speed, uint16_t *length); + +static uint8_t USBD_HID_DataIn (void *pdev, uint8_t epnum); +/** + * @} + */ + + + +#ifdef USB_OTG_HS_INTERNAL_DMA_ENABLED + #if defined ( __ICCARM__ ) /*!< IAR Compiler */ + #pragma data_alignment=4 + #endif +#endif /* USB_OTG_HS_INTERNAL_DMA_ENABLED */ +/* + This USB HID endpoint report description defines a device with: + * 8 digital buttons + * 8 analog axes with 8bit resolution + + Repot packet described as C struct is: + + struct { + uint8_t buttons; //bit 0 - button 1, bit 1 - button 2, ..., mapped to channels 9-16, on if channel > 0 + uint8_t X; //analog value, mapped to channel 1 + uint8_t Y; //analog value, mapped to channel 2 + uint8_t Z; //analog value, mapped to channel 3 + uint8_t Rx; //analog value, mapped to channel 4 + uint8_t Ry //analog value, mapped to channel 5 + uint8_t Rz; //analog value, mapped to channel 6 + uint8_t S1; //analog value, mapped to channel 7 + uint8_t S2; //analog value, mapped to channel 8 + } +*/ +__ALIGN_BEGIN static uint8_t HID_JOYSTICK_ReportDesc[] __ALIGN_END = +{ + 0x05, 0x01, // USAGE_PAGE (Generic Desktop) + 0x09, 0x05, // USAGE (Game Pad) + 0xa1, 0x01, // COLLECTION (Application) + 0xa1, 0x00, // COLLECTION (Physical) + 0x05, 0x09, // USAGE_PAGE (Button) + 0x19, 0x01, // USAGE_MINIMUM (Button 1) + 0x29, 0x08, // USAGE_MAXIMUM (Button 8) + 0x15, 0x00, // LOGICAL_MINIMUM (0) + 0x25, 0x01, // LOGICAL_MAXIMUM (1) + 0x95, 0x08, // REPORT_COUNT (8) + 0x75, 0x01, // REPORT_SIZE (1) + 0x81, 0x02, // INPUT (Data,Var,Abs) + 0x05, 0x01, // USAGE_PAGE (Generic Desktop) + 0x09, 0x30, // USAGE (X) + 0x09, 0x31, // USAGE (Y) + 0x09, 0x32, // USAGE (Z) + 0x09, 0x33, // USAGE (Rx) + 0x09, 0x34, // USAGE (Ry) + 0x09, 0x35, // USAGE (Rz) + 0x09, 0x36, // USAGE (Slider) + 0x09, 0x36, // USAGE (Slider) + 0x15, 0x81, // LOGICAL_MINIMUM (-127) + 0x25, 0x7f, // LOGICAL_MAXIMUM (127) + 0x75, 0x08, // REPORT_SIZE (8) + 0x95, 0x08, // REPORT_COUNT (8) + 0x81, 0x02, // INPUT (Data,Var,Abs) + 0xc0, // END_COLLECTION + 0xc0 // END_COLLECTION +}; + + +/** @defgroup USBD_HID_Private_Variables + * @{ + */ + +USBD_Class_cb_TypeDef USBD_HID_cb = +{ + USBD_HID_Init, + USBD_HID_DeInit, + USBD_HID_Setup, + NULL, /*EP0_TxSent*/ + NULL, /*EP0_RxReady*/ + USBD_HID_DataIn, /*DataIn*/ + NULL, /*DataOut*/ + NULL, /*SOF */ + NULL, + NULL, + USBD_HID_GetCfgDesc, +#ifdef USB_OTG_HS_CORE + USBD_HID_GetCfgDesc, /* use same config as per FS */ +#endif +}; + +#ifdef USB_OTG_HS_INTERNAL_DMA_ENABLED + #if defined ( __ICCARM__ ) /*!< IAR Compiler */ + #pragma data_alignment=4 + #endif +#endif /* USB_OTG_HS_INTERNAL_DMA_ENABLED */ +__ALIGN_BEGIN static uint32_t USBD_HID_AltSet __ALIGN_END = 0; + +#ifdef USB_OTG_HS_INTERNAL_DMA_ENABLED + #if defined ( __ICCARM__ ) /*!< IAR Compiler */ + #pragma data_alignment=4 + #endif +#endif /* USB_OTG_HS_INTERNAL_DMA_ENABLED */ +__ALIGN_BEGIN static uint32_t USBD_HID_Protocol __ALIGN_END = 0; + +#ifdef USB_OTG_HS_INTERNAL_DMA_ENABLED + #if defined ( __ICCARM__ ) /*!< IAR Compiler */ + #pragma data_alignment=4 + #endif +#endif /* USB_OTG_HS_INTERNAL_DMA_ENABLED */ +__ALIGN_BEGIN static uint32_t USBD_HID_IdleState __ALIGN_END = 0; + +#ifdef USB_OTG_HS_INTERNAL_DMA_ENABLED + #if defined ( __ICCARM__ ) /*!< IAR Compiler */ + #pragma data_alignment=4 + #endif +#endif /* USB_OTG_HS_INTERNAL_DMA_ENABLED */ +/* USB HID device Configuration Descriptor */ +__ALIGN_BEGIN static uint8_t USBD_HID_CfgDesc[USB_HID_CONFIG_DESC_SIZ] __ALIGN_END = +{ + 0x09, /* bLength: Configuration Descriptor size */ + USB_CONFIGURATION_DESCRIPTOR_TYPE, /* bDescriptorType: Configuration */ + USB_HID_CONFIG_DESC_SIZ, + /* wTotalLength: Bytes returned */ + 0x00, + 0x01, /*bNumInterfaces: 1 interface*/ + 0x01, /*bConfigurationValue: Configuration value*/ + 0x00, /*iConfiguration: Index of string descriptor describing + the configuration*/ + 0xE0, /*bmAttributes: bus powered and Support Remote Wake-up */ + 0x32, /*MaxPower 100 mA: this current is used for detecting Vbus*/ + + /************** Descriptor of Joystick Mouse interface ****************/ + /* 09 */ + 0x09, /*bLength: Interface Descriptor size*/ + USB_INTERFACE_DESCRIPTOR_TYPE,/*bDescriptorType: Interface descriptor type*/ + 0x00, /*bInterfaceNumber: Number of Interface*/ + 0x00, /*bAlternateSetting: Alternate setting*/ + 0x01, /*bNumEndpoints*/ + 0x03, /*bInterfaceClass: HID*/ + 0x00 /*0x01*/, /*bInterfaceSubClass : 1=BOOT, 0=no boot*/ + 0x00 /*0x02*/, /*nInterfaceProtocol : 0=none, 1=keyboard, 2=mouse*/ + 0, /*iInterface: Index of string descriptor*/ + /******************** Descriptor of Joystick Mouse HID ********************/ + /* 18 */ + 0x09, /*bLength: HID Descriptor size*/ + HID_DESCRIPTOR_TYPE, /*bDescriptorType: HID*/ + 0x11, /*bcdHID: HID Class Spec release number*/ + 0x01, + 0x00, /*bCountryCode: Hardware target country*/ + 0x01, /*bNumDescriptors: Number of HID class descriptors to follow*/ + 0x22, /*bDescriptorType*/ + sizeof(HID_JOYSTICK_ReportDesc),/*wItemLength: Total length of Report descriptor*/ + 0x00, + /******************** Descriptor of Mouse endpoint ********************/ + /* 27 */ + 0x07, /*bLength: Endpoint Descriptor size*/ + USB_ENDPOINT_DESCRIPTOR_TYPE, /*bDescriptorType:*/ + + HID_IN_EP, /*bEndpointAddress: Endpoint Address (IN)*/ + 0x03, /*bmAttributes: Interrupt endpoint*/ + HID_IN_PACKET, /*wMaxPacketSize: 4 Byte max */ + 0x00, + 0x0A, /*bInterval: Polling Interval (10 ms)*/ + /* 34 */ +} ; + + + +static uint8_t ReportSent; + +/** + * @} + */ + +/** @defgroup USBD_HID_Private_Functions + * @{ + */ + +/** + * @brief USBD_HID_Init + * Initialize the HID interface + * @param pdev: device instance + * @param cfgidx: Configuration index + * @retval status + */ +static uint8_t USBD_HID_Init (void *pdev, + uint8_t cfgidx) +{ + + /* Open EP IN */ + DCD_EP_Open(pdev, + HID_IN_EP, + HID_IN_PACKET, + USB_OTG_EP_INT); + + /* Open EP OUT */ + DCD_EP_Open(pdev, + HID_OUT_EP, + HID_OUT_PACKET, + USB_OTG_EP_INT); + + ReportSent = 1; + return USBD_OK; +} + +/** + * @brief USBD_HID_Init + * DeInitialize the HID layer + * @param pdev: device instance + * @param cfgidx: Configuration index + * @retval status + */ +static uint8_t USBD_HID_DeInit (void *pdev, + uint8_t cfgidx) +{ + /* Close HID EPs */ + DCD_EP_Close (pdev , HID_IN_EP); + DCD_EP_Close (pdev , HID_OUT_EP); + + ReportSent = 1; + return USBD_OK; +} + +/** + * @brief USBD_HID_Setup + * Handle the HID specific requests + * @param pdev: instance + * @param req: usb requests + * @retval status + */ +static uint8_t USBD_HID_Setup (void *pdev, + USB_SETUP_REQ *req) +{ + uint16_t len = 0; + uint8_t *pbuf = NULL; + + switch (req->bmRequest & USB_REQ_TYPE_MASK) + { + case USB_REQ_TYPE_CLASS : + switch (req->bRequest) + { + + + case HID_REQ_SET_PROTOCOL: + USBD_HID_Protocol = (uint8_t)(req->wValue); + break; + + case HID_REQ_GET_PROTOCOL: + USBD_CtlSendData (pdev, + (uint8_t *)&USBD_HID_Protocol, + 1); + break; + + case HID_REQ_SET_IDLE: + USBD_HID_IdleState = (uint8_t)(req->wValue >> 8); + break; + + case HID_REQ_GET_IDLE: + USBD_CtlSendData (pdev, + (uint8_t *)&USBD_HID_IdleState, + 1); + break; + + default: + USBD_CtlError (pdev, req); + return USBD_FAIL; + } + break; + + case USB_REQ_TYPE_STANDARD: + switch (req->bRequest) + { + case USB_REQ_GET_DESCRIPTOR: + if( req->wValue >> 8 == HID_REPORT_DESC) + { + len = MIN(sizeof(HID_JOYSTICK_ReportDesc) , req->wLength); + pbuf = HID_JOYSTICK_ReportDesc; // wiiccReportDescriptor; // + } + else if( req->wValue >> 8 == HID_DESCRIPTOR_TYPE) + { + +#ifdef USB_OTG_HS_INTERNAL_DMA_ENABLED + pbuf = USBD_HID_Desc; +#else + pbuf = USBD_HID_CfgDesc + 0x12; +#endif + len = MIN(USB_HID_DESC_SIZ , req->wLength); + } + + USBD_CtlSendData (pdev, + pbuf, + len); + + break; + + case USB_REQ_GET_INTERFACE : + USBD_CtlSendData (pdev, + (uint8_t *)&USBD_HID_AltSet, + 1); + break; + + case USB_REQ_SET_INTERFACE : + USBD_HID_AltSet = (uint8_t)(req->wValue); + break; + } + } + return USBD_OK; +} + + +/** + * @brief USBD_HID_SendReport + * Send HID Report + * @param pdev: device instance + * @param buff: pointer to report + * @retval status + */ +uint8_t USBD_HID_SendReport (USB_OTG_CORE_HANDLE *pdev, + uint8_t *report, + uint16_t len) +{ + if (pdev->dev.device_status == USB_OTG_CONFIGURED ) + { + if ( ReportSent ) + { + ReportSent = 0; + DCD_EP_Tx (pdev, HID_IN_EP, report, len); + } + } + return USBD_OK; +} + +/** + * @brief USBD_HID_GetCfgDesc + * return configuration descriptor + * @param speed : current device speed + * @param length : pointer data length + * @retval pointer to descriptor buffer + */ +static uint8_t *USBD_HID_GetCfgDesc (uint8_t speed, uint16_t *length) +{ + *length = sizeof (USBD_HID_CfgDesc); + return USBD_HID_CfgDesc; +} + +/** + * @brief USBD_HID_DataIn + * handle data IN Stage + * @param pdev: device instance + * @param epnum: endpoint index + * @retval status + */ +static uint8_t USBD_HID_DataIn (void *pdev, + uint8_t epnum) +{ + ReportSent = 1; + /* Ensure that the FIFO is empty before a new transfer, this condition could + be caused by a new transfer before the end of the previous transfer */ + DCD_EP_Flush(pdev, HID_IN_EP); + return USBD_OK; +} + +/** + * @} + */ + + +/** + * @} + */ + + +/** + * @} + */ + +/************************ (C) COPYRIGHT STMicroelectronics *****END OF FILE****/ diff --git a/radio/src/targets/taranis/usbd_usr.cpp b/radio/src/targets/taranis/usbd_usr.cpp index 26187ef41..5c443baf6 100644 --- a/radio/src/targets/taranis/usbd_usr.cpp +++ b/radio/src/targets/taranis/usbd_usr.cpp @@ -119,9 +119,6 @@ void USBD_USR_DeviceConnected (void) */ void USBD_USR_DeviceDisconnected (void) { -#if !defined(BOOT) - NVIC_SystemReset(); -#endif }