Open FFBoard
Open source force feedback firmware
dcd.h
Go to the documentation of this file.
1/*
2 * The MIT License (MIT)
3 *
4 * Copyright (c) 2019 Ha Thach (tinyusb.org)
5 *
6 * Permission is hereby granted, free of charge, to any person obtaining a copy
7 * of this software and associated documentation files (the "Software"), to deal
8 * in the Software without restriction, including without limitation the rights
9 * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
10 * copies of the Software, and to permit persons to whom the Software is
11 * furnished to do so, subject to the following conditions:
12 *
13 * The above copyright notice and this permission notice shall be included in
14 * all copies or substantial portions of the Software.
15 *
16 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
17 * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
18 * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
19 * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
20 * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
21 * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
22 * THE SOFTWARE.
23 *
24 * This file is part of the TinyUSB stack.
25 */
26
27#ifndef TUSB_DCD_H_
28#define TUSB_DCD_H_
29
30#include "common/tusb_common.h"
31#include "osal/osal.h"
32#include "common/tusb_fifo.h"
33
34#ifdef __cplusplus
35 extern "C" {
36#endif
37
38//--------------------------------------------------------------------+
39// MACRO CONSTANT TYPEDEF PROTYPES
40//--------------------------------------------------------------------+
41
42typedef enum {
43 DCD_EVENT_INVALID = 0, // 0
44 DCD_EVENT_BUS_RESET, // 1
45 DCD_EVENT_UNPLUGGED, // 2
46 DCD_EVENT_SOF, // 3
47 DCD_EVENT_SUSPEND, // 4 TODO LPM Sleep L1 support
48 DCD_EVENT_RESUME, // 5
49 DCD_EVENT_SETUP_RECEIVED, // 6
50 DCD_EVENT_XFER_COMPLETE, // 7
51 USBD_EVENT_FUNC_CALL, // 8 Not an DCD event, just a convenient way to defer ISR function
52 DCD_EVENT_COUNT
53} dcd_eventid_t;
54
55typedef struct TU_ATTR_ALIGNED(4) {
56 uint8_t rhport;
57 uint8_t event_id;
58
59 union {
60 // BUS RESET
61 struct {
62 tusb_speed_t speed;
63 } bus_reset;
64
65 // SOF
66 struct {
67 uint32_t frame_count;
68 }sof;
69
70 // SETUP_RECEIVED
71 tusb_control_request_t setup_received;
72
73 // XFER_COMPLETE
74 struct {
75 uint8_t ep_addr;
76 uint8_t result;
77 uint32_t len;
79
80 // FUNC_CALL
81 struct {
82 void (*func) (void*);
83 void* param;
84 }func_call;
85 };
87
88//TU_VERIFY_STATIC(sizeof(dcd_event_t) <= 12, "size is not correct");
89
90//--------------------------------------------------------------------+
91// Memory API
92//--------------------------------------------------------------------+
93
94// clean/flush data cache: write cache -> memory.
95// Required before an DMA TX transfer to make sure data is in memory
96void dcd_dcache_clean(void const* addr, uint32_t data_size) TU_ATTR_WEAK;
97
98// invalidate data cache: mark cache as invalid, next read will read from memory
99// Required BOTH before and after an DMA RX transfer
100void dcd_dcache_invalidate(void const* addr, uint32_t data_size) TU_ATTR_WEAK;
101
102// clean and invalidate data cache
103// Required before an DMA transfer where memory is both read/write by DMA
104void dcd_dcache_clean_invalidate(void const* addr, uint32_t data_size) TU_ATTR_WEAK;
105
106//--------------------------------------------------------------------+
107// Controller API
108//--------------------------------------------------------------------+
109
110// Initialize controller to device mode
111bool dcd_init(uint8_t rhport, const tusb_rhport_init_t* rh_init);
112
113// Deinitialize controller, unset device mode.
114bool dcd_deinit(uint8_t rhport);
115
116// Interrupt Handler
117void dcd_int_handler(uint8_t rhport);
118
119// Enable device interrupt
120void dcd_int_enable (uint8_t rhport);
121
122// Disable device interrupt
123void dcd_int_disable(uint8_t rhport);
124
125// Receive Set Address request, mcu port must also include status IN response
126void dcd_set_address(uint8_t rhport, uint8_t dev_addr);
127
128// Wake up host
129void dcd_remote_wakeup(uint8_t rhport);
130
131// Connect by enabling internal pull-up resistor on D+/D-
132void dcd_connect(uint8_t rhport);
133
134// Disconnect by disabling internal pull-up resistor on D+/D-
135void dcd_disconnect(uint8_t rhport);
136
137// Enable/Disable Start-of-frame interrupt. Default is disabled
138void dcd_sof_enable(uint8_t rhport, bool en);
139
140#if CFG_TUD_TEST_MODE
141// Put device into a test mode (needs power cycle to quit)
142void dcd_enter_test_mode(uint8_t rhport, tusb_feature_test_mode_t test_selector);
143#endif
144//--------------------------------------------------------------------+
145// Endpoint API
146//--------------------------------------------------------------------+
147
148// Invoked when a control transfer's status stage is complete.
149// May help DCD to prepare for next control transfer, this API is optional.
150void dcd_edpt0_status_complete(uint8_t rhport, tusb_control_request_t const * request);
151
152// Configure endpoint's registers according to descriptor
153bool dcd_edpt_open (uint8_t rhport, tusb_desc_endpoint_t const * desc_ep);
154
155// Close all non-control endpoints, cancel all pending transfers if any.
156// Invoked when switching from a non-zero Configuration by SET_CONFIGURE therefore
157// required for multiple configuration support.
158void dcd_edpt_close_all (uint8_t rhport);
159
160// Submit a transfer, When complete dcd_event_xfer_complete() is invoked to notify the stack
161bool dcd_edpt_xfer (uint8_t rhport, uint8_t ep_addr, uint8_t * buffer, uint16_t total_bytes);
162
163// Submit an transfer using fifo, When complete dcd_event_xfer_complete() is invoked to notify the stack
164// This API is optional, may be useful for register-based for transferring data.
165bool dcd_edpt_xfer_fifo (uint8_t rhport, uint8_t ep_addr, tu_fifo_t * ff, uint16_t total_bytes) TU_ATTR_WEAK;
166
167// Stall endpoint, any queuing transfer should be removed from endpoint
168void dcd_edpt_stall (uint8_t rhport, uint8_t ep_addr);
169
170// clear stall, data toggle is also reset to DATA0
171// This API never calls with control endpoints, since it is auto cleared when receiving setup packet
172void dcd_edpt_clear_stall (uint8_t rhport, uint8_t ep_addr);
173
174#ifdef TUP_DCD_EDPT_ISO_ALLOC
175// Allocate packet buffer used by ISO endpoints
176// Some MCU need manual packet buffer allocation, we allocate the largest size to avoid clustering
177bool dcd_edpt_iso_alloc(uint8_t rhport, uint8_t ep_addr, uint16_t largest_packet_size);
178
179// Configure and enable an ISO endpoint according to descriptor
180bool dcd_edpt_iso_activate(uint8_t rhport, tusb_desc_endpoint_t const * desc_ep);
181
182#else
183// Close an endpoint.
184void dcd_edpt_close(uint8_t rhport, uint8_t ep_addr);
185
186#endif
187
188//--------------------------------------------------------------------+
189// Event API (implemented by stack)
190//--------------------------------------------------------------------+
191
192// Called by DCD to notify device stack
193extern void dcd_event_handler(dcd_event_t const * event, bool in_isr);
194
195// helper to send bus signal event
196TU_ATTR_ALWAYS_INLINE static inline void dcd_event_bus_signal (uint8_t rhport, dcd_eventid_t eid, bool in_isr) {
197 dcd_event_t event;
198 event.rhport = rhport;
199 event.event_id = eid;
200 dcd_event_handler(&event, in_isr);
201}
202
203// helper to send bus reset event
204TU_ATTR_ALWAYS_INLINE static inline void dcd_event_bus_reset (uint8_t rhport, tusb_speed_t speed, bool in_isr) {
205 dcd_event_t event;
206 event.rhport = rhport;
207 event.event_id = DCD_EVENT_BUS_RESET;
208 event.bus_reset.speed = speed;
209 dcd_event_handler(&event, in_isr);
210}
211
212// helper to send setup received
213TU_ATTR_ALWAYS_INLINE static inline void dcd_event_setup_received(uint8_t rhport, uint8_t const * setup, bool in_isr) {
214 dcd_event_t event;
215 event.rhport = rhport;
216 event.event_id = DCD_EVENT_SETUP_RECEIVED;
217 memcpy(&event.setup_received, setup, sizeof(tusb_control_request_t));
218 dcd_event_handler(&event, in_isr);
219}
220
221// helper to send transfer complete event
222TU_ATTR_ALWAYS_INLINE static inline void dcd_event_xfer_complete (uint8_t rhport, uint8_t ep_addr, uint32_t xferred_bytes, uint8_t result, bool in_isr) {
223 dcd_event_t event;
224 event.rhport = rhport;
225 event.event_id = DCD_EVENT_XFER_COMPLETE;
226 event.xfer_complete.ep_addr = ep_addr;
227 event.xfer_complete.len = xferred_bytes;
228 event.xfer_complete.result = result;
229 dcd_event_handler(&event, in_isr);
230}
231
232TU_ATTR_ALWAYS_INLINE static inline void dcd_event_sof(uint8_t rhport, uint32_t frame_count, bool in_isr) {
233 dcd_event_t event;
234 event.rhport = rhport;
235 event.event_id = DCD_EVENT_SOF;
236 event.sof.frame_count = frame_count;
237 dcd_event_handler(&event, in_isr);
238}
239
240#ifdef __cplusplus
241 }
242#endif
243
244#endif
bool dcd_edpt_iso_activate(uint8_t rhport, tusb_desc_endpoint_t const *desc_ep)
Definition: dcd_musb.c:707
static TU_ATTR_ALWAYS_INLINE void dcd_event_bus_signal(uint8_t rhport, dcd_eventid_t eid, bool in_isr)
Definition: dcd.h:196
static TU_ATTR_ALWAYS_INLINE void dcd_event_xfer_complete(uint8_t rhport, uint8_t ep_addr, uint32_t xferred_bytes, uint8_t result, bool in_isr)
Definition: dcd.h:222
bool dcd_edpt_xfer_fifo(uint8_t rhport, uint8_t ep_addr, tu_fifo_t *ff, uint16_t total_bytes) TU_ATTR_WEAK
Definition: dcd_ft9xx.c:894
void dcd_edpt_stall(uint8_t rhport, uint8_t ep_addr)
Definition: dcd_ft9xx.c:905
static TU_ATTR_ALWAYS_INLINE void dcd_event_sof(uint8_t rhport, uint32_t frame_count, bool in_isr)
Definition: dcd.h:232
void dcd_edpt_close(uint8_t rhport, uint8_t ep_addr)
Definition: dcd_ci_fs.c:402
void dcd_enter_test_mode(uint8_t rhport, tusb_feature_test_mode_t test_selector)
Definition: dcd_dwc2.c:1008
void dcd_int_handler(uint8_t rhport)
Definition: dcd_ft9xx.c:954
void dcd_dcache_invalidate(void const *addr, uint32_t data_size) TU_ATTR_WEAK
Definition: dcd_ci_hs.c:65
void dcd_disconnect(uint8_t rhport)
Definition: fsdev_stm32.h:344
void dcd_dcache_clean_invalidate(void const *addr, uint32_t data_size) TU_ATTR_WEAK
Definition: dcd_ci_hs.c:69
void dcd_dcache_clean(void const *addr, uint32_t data_size) TU_ATTR_WEAK
Definition: dcd_ci_hs.c:61
void dcd_edpt_close_all(uint8_t rhport)
Definition: dcd_ft9xx.c:802
static TU_ATTR_ALWAYS_INLINE void dcd_event_setup_received(uint8_t rhport, uint8_t const *setup, bool in_isr)
Definition: dcd.h:213
void dcd_int_disable(uint8_t rhport)
Definition: dcd_samd.c:138
void dcd_edpt_clear_stall(uint8_t rhport, uint8_t ep_addr)
Definition: dcd_ft9xx.c:927
void dcd_connect(uint8_t rhport)
Definition: fsdev_stm32.h:349
bool dcd_deinit(uint8_t rhport)
Definition: usbd.c:91
bool dcd_edpt_xfer(uint8_t rhport, uint8_t ep_addr, uint8_t *buffer, uint16_t total_bytes)
Definition: dcd_ft9xx.c:810
dcd_event_t
Definition: dcd.h:86
void dcd_edpt0_status_complete(uint8_t rhport, tusb_control_request_t const *request)
Definition: usbd_control.c:38
void dcd_event_handler(dcd_event_t const *event, bool in_isr)
Definition: usbd.c:1153
void dcd_set_address(uint8_t rhport, uint8_t dev_addr)
Definition: dcd_ft9xx.c:553
static TU_ATTR_ALWAYS_INLINE void dcd_event_bus_reset(uint8_t rhport, tusb_speed_t speed, bool in_isr)
Definition: dcd.h:204
bool dcd_init(uint8_t rhport, const tusb_rhport_init_t *rh_init)
Definition: dcd_ft9xx.c:520
bool dcd_edpt_iso_alloc(uint8_t rhport, uint8_t ep_addr, uint16_t largest_packet_size)
Definition: dcd_musb.c:697
struct TU_ATTR_ALIGNED(4)
Definition: dcd.h:55
void dcd_int_enable(uint8_t rhport)
Definition: dcd_samd.c:132
void dcd_remote_wakeup(uint8_t rhport)
Definition: dcd_ft9xx.c:593
void dcd_sof_enable(uint8_t rhport, bool en)
Definition: dcd_ft9xx.c:661
bool dcd_edpt_open(uint8_t rhport, tusb_desc_endpoint_t const *desc_ep)
Definition: dcd_ft9xx.c:674
static bool in_isr
void bus_reset(void)
Definition: dcd_nrf5x.c:533
uint16_t total_bytes
Definition: dcd_nuc505.c:113
uint8_t dev_addr
Definition: dcd_pic32mz.c:81
static void xfer_complete(xfer_ctl_t *xfer, uint8_t result, bool in_isr)
Definition: dcd_pic32mz.c:296
uint8_t const * buffer
Definition: midi_device.h:100
static void * memcpy(void *dst, const void *src, size_t n)
Definition: ringbuffer.c:8
AUDIO Channel Cluster Descriptor (4.1)
Definition: audio.h:647
tusb_speed_t
defined base on EHCI specs value for Endpoint Speed
Definition: tusb_types.h:49
tusb_feature_test_mode_t
Definition: tusb_types.h:225
CFG_TUH_MEM_ALIGN tusb_control_request_t request
Definition: usbh.c:259