diff --git a/cpu/sam0_common/include/periph_cpu_common.h b/cpu/sam0_common/include/periph_cpu_common.h index eb10d8c63b..6138e18002 100644 --- a/cpu/sam0_common/include/periph_cpu_common.h +++ b/cpu/sam0_common/include/periph_cpu_common.h @@ -813,6 +813,16 @@ typedef struct { } sam0_common_gmac_config_t; #endif +/** + * @brief USBDEV buffers must be word aligned because of DMA restrictions + */ +#define USBDEV_CPU_DMA_ALIGNMENT (4) + +/** + * @brief USBDEV buffer instantiation requirement + */ +#define USBDEV_CPU_DMA_REQUIREMENTS __attribute__((aligned(USBDEV_CPU_DMA_ALIGNMENT))) + /** * @brief USB peripheral parameters */ diff --git a/cpu/sam0_common/include/sam_usb.h b/cpu/sam0_common/include/sam_usb.h index 9b6800b349..f11d9f9075 100644 --- a/cpu/sam0_common/include/sam_usb.h +++ b/cpu/sam0_common/include/sam_usb.h @@ -31,11 +31,6 @@ extern "C" { #endif -/** - * USB endpoint buffer space - */ -#define SAM_USB_BUF_SPACE USBDEV_EP_BUF_SPACE - /** * Number of USB IN and OUT endpoints */ @@ -49,11 +44,6 @@ typedef struct { const sam0_common_usb_config_t *config; /**< USB peripheral config */ UsbDeviceDescBank banks[2 * SAM_USB_NUM_EP]; /**< Device descriptor banks */ usbdev_ep_t endpoints[2 * SAM_USB_NUM_EP]; /**< Endpoints */ - size_t used; /**< Number of bytes from the - buffer that are used */ - __attribute__ ((aligned(4))) - uint8_t buffer[SAM_USB_BUF_SPACE]; /**< Buffer space, must be - 32-bit aligned */ bool suspended; /**< Suspend active */ } sam0_common_usb_t; diff --git a/cpu/sam0_common/periph/usbdev.c b/cpu/sam0_common/periph/usbdev.c index f392640e4d..4a54511846 100644 --- a/cpu/sam0_common/periph/usbdev.c +++ b/cpu/sam0_common/periph/usbdev.c @@ -22,6 +22,7 @@ #include #include #include +#include "architecture.h" #include "cpu.h" #include "cpu_conf.h" #include "periph/gpio.h" @@ -46,12 +47,11 @@ static sam0_common_usb_t _usbdevs[USB_INST_NUM]; const usbdev_driver_t driver; static void _usbdev_ep_init(usbdev_ep_t *ep); -static int _usbdev_ep_ready(usbdev_ep_t *ep, size_t len); +static int _usbdev_ep_xmit(usbdev_ep_t *ep, uint8_t *buf, size_t len); static usbdev_ep_t *_usbdev_new_ep(usbdev_t *dev, usb_ep_type_t type, - usb_ep_dir_t dir, size_t buf_len); + usb_ep_dir_t dir, size_t len); static int _bank_set_size(usbdev_ep_t *ep); -static int _ep_unready(usbdev_ep_t *ep); static inline unsigned _ep_num(unsigned num, usb_ep_dir_t dir) { @@ -144,13 +144,6 @@ static void _disable_ep_irq_in(UsbDeviceEndpoint *ep_reg) USB_DEVICE_EPINTENCLR_STALL1; } -static void _bank_set_address(usbdev_ep_t *ep) -{ - UsbDeviceDescBank *bank = _bank_from_ep(ep); - - bank->ADDR.reg = (uint32_t)ep->buf; -} - static int _bank_set_size(usbdev_ep_t *ep) { UsbDeviceDescBank *bank = _bank_from_ep(ep); @@ -255,7 +248,7 @@ static inline void _poweron(sam0_common_usb_t *dev) } static usbdev_ep_t *_usbdev_new_ep(usbdev_t *dev, usb_ep_type_t type, - usb_ep_dir_t dir, size_t buf_len) + usb_ep_dir_t dir, size_t size) { sam0_common_usb_t *usbdev = (sam0_common_usb_t *)dev; /* The IP supports all types for all endpoints */ @@ -279,17 +272,9 @@ static usbdev_ep_t *_usbdev_new_ep(usbdev_t *dev, usb_ep_type_t type, if (res) { res->dev = dev; res->dir = dir; - if (usbdev->used + buf_len < SAM_USB_BUF_SPACE) { - res->buf = usbdev->buffer + usbdev->used; - res->len = buf_len; - if (_bank_set_size(res) < 0) { - return NULL; - } - usbdev->used += buf_len; - _bank_set_address(res); - res->type = type; - res->dev = dev; - } + res->type = type; + res->len = size; + _bank_set_size(res); } return res; } @@ -334,7 +319,6 @@ static void _usbdev_init(usbdev_t *dev) /* Only one usb device on this board */ sam0_common_usb_t *usbdev = (sam0_common_usb_t *)dev; - usbdev->used = 0; /* Set GPIO */ gpio_init(usbdev->config->dp, GPIO_IN); gpio_init(usbdev->config->dm, GPIO_IN); @@ -688,16 +672,6 @@ static int _usbdev_ep_set(usbdev_ep_t *ep, usbopt_ep_t opt, _ep_set_stall(ep, *(usbopt_enable_t *)value); res = sizeof(usbopt_enable_t); break; - case USBOPT_EP_READY: - assert(value_len == sizeof(usbopt_enable_t)); - if (*((usbopt_enable_t *)value)) { - _ep_unready(ep); - } - else { - _usbdev_ep_ready(ep, 0); - } - res = sizeof(usbopt_enable_t); - break; default: DEBUG("sam_usb: Unhandled set call: 0x%x\n", opt); break; @@ -705,23 +679,13 @@ static int _usbdev_ep_set(usbdev_ep_t *ep, usbopt_ep_t opt, return res; } -static int _ep_unready(usbdev_ep_t *ep) -{ - UsbDeviceEndpoint *ep_reg = _ep_reg_from_ep(ep); - - if (ep->dir == USB_EP_DIR_IN) { - ep_reg->EPSTATUSCLR.reg = USB_DEVICE_EPSTATUSCLR_BK1RDY; - } - else { - ep_reg->EPSTATUSSET.reg = USB_DEVICE_EPSTATUSSET_BK0RDY; - } - return 0; -} - -static int _usbdev_ep_ready(usbdev_ep_t *ep, size_t len) +static int _usbdev_ep_xmit(usbdev_ep_t *ep, uint8_t *buf, size_t len) { UsbDeviceEndpoint *ep_reg = _ep_reg_from_ep(ep); + /* Assert the alignment required for the buffers */ + assert(HAS_ALIGNMENT_OF(buf, USBDEV_CPU_DMA_ALIGNMENT)); + _bank_from_ep(ep)->ADDR.reg = (uint32_t)(intptr_t)buf; if (ep->dir == USB_EP_DIR_IN) { _disable_ep_stall_in(ep_reg); _bank_from_ep(ep)->PCKSIZE.bit.BYTE_COUNT = len; @@ -803,5 +767,5 @@ const usbdev_driver_t driver = { .ep_get = _usbdev_ep_get, .ep_set = _usbdev_ep_set, .ep_esr = _usbdev_ep_esr, - .ready = _usbdev_ep_ready, + .xmit = _usbdev_ep_xmit, };