mirror of
https://github.com/hathach/tinyusb.git
synced 2025-03-23 04:20:47 +00:00
- wrap up hcd max3421, work well with nrf52840
- also add usbh_defer_func()
This commit is contained in:
parent
1b9108ea0d
commit
21ab40bab2
@ -109,10 +109,12 @@ void max3421e_int_handler(nrfx_gpiote_pin_t pin, nrf_gpiote_polarity_t action) {
|
|||||||
void tuh_max3421e_int_api(uint8_t rhport, bool enabled) {
|
void tuh_max3421e_int_api(uint8_t rhport, bool enabled) {
|
||||||
(void) rhport;
|
(void) rhport;
|
||||||
|
|
||||||
|
// use NVIC_Enable/Disable instead since nrfx_gpiote_trigger_enable/disable clear pending and can miss interrupt
|
||||||
|
// when disabled
|
||||||
if (enabled) {
|
if (enabled) {
|
||||||
nrfx_gpiote_trigger_enable(MAX3241E_INTR_PIN, true);
|
NVIC_EnableIRQ(GPIOTE_IRQn);
|
||||||
} else {
|
} else {
|
||||||
nrfx_gpiote_trigger_disable(MAX3241E_INTR_PIN);
|
NVIC_DisableIRQ(GPIOTE_IRQn);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -266,6 +268,7 @@ void board_init(void) {
|
|||||||
in_config.pull = NRF_GPIO_PIN_PULLUP;
|
in_config.pull = NRF_GPIO_PIN_PULLUP;
|
||||||
|
|
||||||
nrfx_gpiote_in_init(MAX3241E_INTR_PIN, &in_config, max3421e_int_handler);
|
nrfx_gpiote_in_init(MAX3241E_INTR_PIN, &in_config, max3421e_int_handler);
|
||||||
|
nrfx_gpiote_trigger_enable(MAX3241E_INTR_PIN, true);
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
}
|
}
|
||||||
|
@ -753,29 +753,33 @@ bool tuh_edpt_abort_xfer(uint8_t daddr, uint8_t ep_addr) {
|
|||||||
// USBH API For Class Driver
|
// USBH API For Class Driver
|
||||||
//--------------------------------------------------------------------+
|
//--------------------------------------------------------------------+
|
||||||
|
|
||||||
uint8_t usbh_get_rhport(uint8_t dev_addr)
|
uint8_t usbh_get_rhport(uint8_t dev_addr) {
|
||||||
{
|
usbh_device_t *dev = get_device(dev_addr);
|
||||||
usbh_device_t* dev = get_device(dev_addr);
|
|
||||||
return dev ? dev->rhport : _dev0.rhport;
|
return dev ? dev->rhport : _dev0.rhport;
|
||||||
}
|
}
|
||||||
|
|
||||||
uint8_t* usbh_get_enum_buf(void)
|
uint8_t *usbh_get_enum_buf(void) {
|
||||||
{
|
|
||||||
return _usbh_ctrl_buf;
|
return _usbh_ctrl_buf;
|
||||||
}
|
}
|
||||||
|
|
||||||
void usbh_int_set(bool enabled)
|
void usbh_int_set(bool enabled) {
|
||||||
{
|
|
||||||
// TODO all host controller if multiple are used since they shared the same event queue
|
// TODO all host controller if multiple are used since they shared the same event queue
|
||||||
if (enabled)
|
if (enabled) {
|
||||||
{
|
|
||||||
hcd_int_enable(_usbh_controller);
|
hcd_int_enable(_usbh_controller);
|
||||||
}else
|
} else {
|
||||||
{
|
|
||||||
hcd_int_disable(_usbh_controller);
|
hcd_int_disable(_usbh_controller);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void usbh_defer_func(osal_task_func_t func, void *param, bool in_isr) {
|
||||||
|
hcd_event_t event = { 0 };
|
||||||
|
event.event_id = USBH_EVENT_FUNC_CALL;
|
||||||
|
event.func_call.func = func;
|
||||||
|
event.func_call.param = param;
|
||||||
|
|
||||||
|
osal_queue_send(_usbh_q, &event, in_isr);
|
||||||
|
}
|
||||||
|
|
||||||
//--------------------------------------------------------------------+
|
//--------------------------------------------------------------------+
|
||||||
// Endpoint API
|
// Endpoint API
|
||||||
//--------------------------------------------------------------------+
|
//--------------------------------------------------------------------+
|
||||||
|
@ -24,8 +24,8 @@
|
|||||||
* This file is part of the TinyUSB stack.
|
* This file is part of the TinyUSB stack.
|
||||||
*/
|
*/
|
||||||
|
|
||||||
#ifndef _TUSB_USBH_CLASSDRIVER_H_
|
#ifndef _TUSB_USBH_PVT_H_
|
||||||
#define _TUSB_USBH_CLASSDRIVER_H_
|
#define _TUSB_USBH_PVT_H_
|
||||||
|
|
||||||
#include "osal/osal.h"
|
#include "osal/osal.h"
|
||||||
#include "common/tusb_fifo.h"
|
#include "common/tusb_fifo.h"
|
||||||
@ -76,6 +76,8 @@ uint8_t* usbh_get_enum_buf(void);
|
|||||||
|
|
||||||
void usbh_int_set(bool enabled);
|
void usbh_int_set(bool enabled);
|
||||||
|
|
||||||
|
void usbh_defer_func(osal_task_func_t func, void *param, bool in_isr);
|
||||||
|
|
||||||
//--------------------------------------------------------------------+
|
//--------------------------------------------------------------------+
|
||||||
// USBH Endpoint API
|
// USBH Endpoint API
|
||||||
//--------------------------------------------------------------------+
|
//--------------------------------------------------------------------+
|
||||||
@ -85,12 +87,10 @@ bool usbh_edpt_xfer_with_callback(uint8_t dev_addr, uint8_t ep_addr, uint8_t * b
|
|||||||
tuh_xfer_cb_t complete_cb, uintptr_t user_data);
|
tuh_xfer_cb_t complete_cb, uintptr_t user_data);
|
||||||
|
|
||||||
TU_ATTR_ALWAYS_INLINE
|
TU_ATTR_ALWAYS_INLINE
|
||||||
static inline bool usbh_edpt_xfer(uint8_t dev_addr, uint8_t ep_addr, uint8_t * buffer, uint16_t total_bytes)
|
static inline bool usbh_edpt_xfer(uint8_t dev_addr, uint8_t ep_addr, uint8_t * buffer, uint16_t total_bytes) {
|
||||||
{
|
|
||||||
return usbh_edpt_xfer_with_callback(dev_addr, ep_addr, buffer, total_bytes, NULL, 0);
|
return usbh_edpt_xfer_with_callback(dev_addr, ep_addr, buffer, total_bytes, NULL, 0);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
// Claim an endpoint before submitting a transfer.
|
// Claim an endpoint before submitting a transfer.
|
||||||
// If caller does not make any transfer, it must release endpoint for others.
|
// If caller does not make any transfer, it must release endpoint for others.
|
||||||
bool usbh_edpt_claim(uint8_t dev_addr, uint8_t ep_addr);
|
bool usbh_edpt_claim(uint8_t dev_addr, uint8_t ep_addr);
|
||||||
|
@ -194,7 +194,6 @@ typedef struct {
|
|||||||
uint8_t hxfr;
|
uint8_t hxfr;
|
||||||
|
|
||||||
atomic_flag busy; // busy transferring
|
atomic_flag busy; // busy transferring
|
||||||
volatile uint8_t intr_disable_count;
|
|
||||||
volatile uint16_t frame_count;
|
volatile uint16_t frame_count;
|
||||||
|
|
||||||
max3421_ep_t ep[CFG_TUH_MAX3421_ENDPOINT_TOTAL]; // [0] is reserved for addr0
|
max3421_ep_t ep[CFG_TUH_MAX3421_ENDPOINT_TOTAL]; // [0] is reserved for addr0
|
||||||
@ -241,14 +240,6 @@ static void max3421_spi_unlock(uint8_t rhport, bool in_isr) {
|
|||||||
if (!in_isr) {
|
if (!in_isr) {
|
||||||
tuh_max3421e_int_api(rhport, true);
|
tuh_max3421e_int_api(rhport, true);
|
||||||
(void) osal_mutex_unlock(_hcd_data.spi_mutex);
|
(void) osal_mutex_unlock(_hcd_data.spi_mutex);
|
||||||
|
|
||||||
// when re-enable interrupt, we may miss INTR edge (usually via GPIO detection interrupt).
|
|
||||||
// It would be ok if we are operating since SOF will re-trigger interrupt.
|
|
||||||
// However, for CONDET_IRQ i.e host not operating therefore we need to manually handle it here.
|
|
||||||
if (_hcd_data.hirq & HIRQ_CONDET_IRQ) {
|
|
||||||
handle_connect_irq(rhport, false);
|
|
||||||
hirq_write(rhport, HIRQ_CONDET_IRQ, false);
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -470,28 +461,13 @@ bool hcd_init(uint8_t rhport) {
|
|||||||
// Enable USB interrupt
|
// Enable USB interrupt
|
||||||
// Not actually enable GPIO interrupt, just set variable to prevent handler to process
|
// Not actually enable GPIO interrupt, just set variable to prevent handler to process
|
||||||
void hcd_int_enable (uint8_t rhport) {
|
void hcd_int_enable (uint8_t rhport) {
|
||||||
// tuh_max3421e_int_api(rhport, true);
|
tuh_max3421e_int_api(rhport, true);
|
||||||
|
|
||||||
(void) rhport;
|
|
||||||
if (_hcd_data.intr_disable_count) {
|
|
||||||
_hcd_data.intr_disable_count--;
|
|
||||||
}
|
|
||||||
|
|
||||||
// when re-enable interrupt, we may miss INTR edge (usually via GPIO detection interrupt).
|
|
||||||
// It would be ok if we are operating since SOF will re-trigger interrupt.
|
|
||||||
// However, for CONDET_IRQ i.e host not operating therefore we need to manually handle it here.
|
|
||||||
// if (_hcd_data.hirq & HIRQ_CONDET_IRQ) {
|
|
||||||
// handle_connect_irq(rhport, false);
|
|
||||||
// hirq_write(rhport, HIRQ_CONDET_IRQ, false);
|
|
||||||
// }
|
|
||||||
}
|
}
|
||||||
|
|
||||||
// Disable USB interrupt
|
// Disable USB interrupt
|
||||||
// Not actually disable GPIO interrupt, just set variable to prevent handler to process
|
// Not actually disable GPIO interrupt, just set variable to prevent handler to process
|
||||||
void hcd_int_disable(uint8_t rhport) {
|
void hcd_int_disable(uint8_t rhport) {
|
||||||
//tuh_max3421e_int_api(rhport, false);
|
tuh_max3421e_int_api(rhport, false);
|
||||||
(void) rhport;
|
|
||||||
_hcd_data.intr_disable_count++;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
// Get frame number (1ms)
|
// Get frame number (1ms)
|
||||||
@ -896,14 +872,6 @@ void hcd_int_handler(uint8_t rhport) {
|
|||||||
_hcd_data.frame_count++;
|
_hcd_data.frame_count++;
|
||||||
}
|
}
|
||||||
|
|
||||||
// interrupt is disabled by usbh task: only ack FRAME IRQ and skip the rest
|
|
||||||
if (_hcd_data.intr_disable_count) {
|
|
||||||
if (hirq & HIRQ_FRAME_IRQ) {
|
|
||||||
hirq_write(rhport, HIRQ_FRAME_IRQ, true);
|
|
||||||
}
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (hirq & HIRQ_CONDET_IRQ) {
|
if (hirq & HIRQ_CONDET_IRQ) {
|
||||||
handle_connect_irq(rhport, true);
|
handle_connect_irq(rhport, true);
|
||||||
}
|
}
|
||||||
|
Loading…
x
Reference in New Issue
Block a user