From a00289c115d624fe863c5b6db8dc6414e9aee0b7 Mon Sep 17 00:00:00 2001 From: Emil Lerch Date: Sat, 22 Apr 2023 16:17:55 -0700 Subject: [PATCH] add files that matter (and some that do not) --- CMakeLists.txt | 12 +++ LICENSE | 21 +++++ Makefile | 13 +++ README.md | 37 +++++++++ cdc_acm_template.c | 194 +++++++++++++++++++++++++++++++++++++++++++++ flash_prog_cfg.ini | 11 +++ main.c | 35 ++++++++ proj.conf | 7 ++ usb_config.h | 132 ++++++++++++++++++++++++++++++ 9 files changed, 462 insertions(+) create mode 100644 CMakeLists.txt create mode 100644 LICENSE create mode 100644 Makefile create mode 100644 README.md create mode 100644 cdc_acm_template.c create mode 100644 flash_prog_cfg.ini create mode 100644 main.c create mode 100644 proj.conf create mode 100644 usb_config.h diff --git a/CMakeLists.txt b/CMakeLists.txt new file mode 100644 index 0000000..cba68f9 --- /dev/null +++ b/CMakeLists.txt @@ -0,0 +1,12 @@ +cmake_minimum_required(VERSION 3.15) + +include(proj.conf) + +find_package(bouffalo_sdk REQUIRED HINTS $ENV{BL_SDK_BASE}) + +sdk_add_include_directories(.) + +target_sources(app PRIVATE cdc_acm_template.c) +sdk_set_main_file(main.c) + +project(usbd_cdc_acm) diff --git a/LICENSE b/LICENSE new file mode 100644 index 0000000..a339f72 --- /dev/null +++ b/LICENSE @@ -0,0 +1,21 @@ +MIT License + +Copyright (c) 2023 Emil Lerch + +Permission is hereby granted, free of charge, to any person obtaining a copy +of this software and associated documentation files (the "Software"), to deal +in the Software without restriction, including without limitation the rights +to use, copy, modify, merge, publish, distribute, sublicense, and/or sell +copies of the Software, and to permit persons to whom the Software is +furnished to do so, subject to the following conditions: + +The above copyright notice and this permission notice shall be included in all +copies or substantial portions of the Software. + +THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE +AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE +SOFTWARE. diff --git a/Makefile b/Makefile new file mode 100644 index 0000000..44367c0 --- /dev/null +++ b/Makefile @@ -0,0 +1,13 @@ +SDK_DEMO_PATH ?= . +BL_SDK_BASE ?= $(SDK_DEMO_PATH)/../../../.. + +export BL_SDK_BASE + +CHIP ?= bl616 +BOARD ?= bl616dk +CROSS_COMPILE ?= riscv64-unknown-elf- + +# add custom cmake definition +#cmake_definition+=-Dxxx=sss + +include $(BL_SDK_BASE)/project.build diff --git a/README.md b/README.md new file mode 100644 index 0000000..3bf5dd8 --- /dev/null +++ b/README.md @@ -0,0 +1,37 @@ +# usbd_cdc_acm + + +## Support CHIP + +| CHIP | Remark | +|:----------------:|:------:| +|BL702/BL704/BL706 | | +|BL616/BL618 | | +|BL808 | D0 has no irq | + +## Compile + +- BL702/BL704/BL706 + +``` +make CHIP=bl702 BOARD=bl702dk +``` + +- BL616/BL618 + +``` +make CHIP=bl616 BOARD=bl616dk +``` + +- BL808 + +``` +make CHIP=bl808 BOARD=bl808dk CPU_ID=m0 +make CHIP=bl808 BOARD=bl808dk CPU_ID=d0 +``` + +## Flash + +``` +make flash CHIP=chip_name COMX=xxx # xxx is your com name +``` \ No newline at end of file diff --git a/cdc_acm_template.c b/cdc_acm_template.c new file mode 100644 index 0000000..d50f745 --- /dev/null +++ b/cdc_acm_template.c @@ -0,0 +1,194 @@ +#include "usbd_core.h" +#include "usbd_cdc.h" + +/*!< endpoint address */ +#define CDC_IN_EP 0x81 +#define CDC_OUT_EP 0x02 +#define CDC_INT_EP 0x83 + +#define USBD_VID 0xFFFF +#define USBD_PID 0xFFFF +#define USBD_MAX_POWER 100 +#define USBD_LANGID_STRING 1033 + +/*!< config descriptor size */ +#define USB_CONFIG_SIZE (9 + CDC_ACM_DESCRIPTOR_LEN) + +/*!< global descriptor */ +static const uint8_t cdc_descriptor[] = { + USB_DEVICE_DESCRIPTOR_INIT(USB_2_0, 0xEF, 0x02, 0x01, USBD_VID, USBD_PID, 0x0100, 0x01), + USB_CONFIG_DESCRIPTOR_INIT(USB_CONFIG_SIZE, 0x02, 0x01, USB_CONFIG_BUS_POWERED, USBD_MAX_POWER), + CDC_ACM_DESCRIPTOR_INIT(0x00, CDC_INT_EP, CDC_OUT_EP, CDC_IN_EP, 0x02), + /////////////////////////////////////// + /// string0 descriptor + /////////////////////////////////////// + USB_LANGID_INIT(USBD_LANGID_STRING), + /////////////////////////////////////// + /// string1 descriptor + /////////////////////////////////////// + 0x16, /* bLength */ + USB_DESCRIPTOR_TYPE_STRING, /* bDescriptorType */ + 'E', 0x00, /* wcChar0 */ + 'm', 0x00, /* wcChar1 */ + 'i', 0x00, /* wcChar2 */ + 'l', 0x00, /* wcChar3 */ + ' ', 0x00, /* wcChar4 */ + 'L', 0x00, /* wcChar5 */ + 'e', 0x00, /* wcChar6 */ + 'r', 0x00, /* wcChar7 */ + 'c', 0x00, /* wcChar8 */ + 'h', 0x00, /* wcChar9 */ + /////////////////////////////////////// + /// string2 descriptor + /////////////////////////////////////// + 0x22, /* bLength */ + USB_DESCRIPTOR_TYPE_STRING, /* bDescriptorType */ + 'B', 0x00, /* wcChar0 */ + 'L', 0x00, /* wcChar1 */ + '6', 0x00, /* wcChar2 */ + '1', 0x00, /* wcChar3 */ + '6', 0x00, /* wcChar4 */ + ' ', 0x00, /* wcChar5 */ + 'B', 0x00, /* wcChar6 */ + 'a', 0x00, /* wcChar7 */ + 'r', 0x00, /* wcChar8 */ + 'e', 0x00, /* wcChar9 */ + ' ', 0x00, /* wcChar10 */ + 'M', 0x00, /* wcChar11 */ + 'e', 0x00, /* wcChar12 */ + 't', 0x00, /* wcChar13 */ + 'a', 0x00, /* wcChar14 */ + 'l', 0x00, /* wcChar15 */ + /////////////////////////////////////// + /// string3 descriptor + /////////////////////////////////////// + 0x16, /* bLength */ + USB_DESCRIPTOR_TYPE_STRING, /* bDescriptorType */ + '2', 0x00, /* wcChar0 */ + '0', 0x00, /* wcChar1 */ + '2', 0x00, /* wcChar2 */ + '3', 0x00, /* wcChar3 */ + '-', 0x00, /* wcChar4 */ + '0', 0x00, /* wcChar5 */ + '4', 0x00, /* wcChar6 */ + '-', 0x00, /* wcChar7 */ + '1', 0x00, /* wcChar8 */ + '9', 0x00, /* wcChar9 */ +#ifdef CONFIG_USB_HS + /////////////////////////////////////// + /// device qualifier descriptor + /////////////////////////////////////// + 0x0a, + USB_DESCRIPTOR_TYPE_DEVICE_QUALIFIER, + 0x00, + 0x02, + 0x02, + 0x02, + 0x01, + 0x40, + 0x01, + 0x00, +#endif + 0x00 +}; + +USB_NOCACHE_RAM_SECTION USB_MEM_ALIGNX uint8_t read_buffer[2048]; +USB_NOCACHE_RAM_SECTION USB_MEM_ALIGNX uint8_t write_buffer[2048]; + +volatile bool ep_tx_busy_flag = false; + +#ifdef CONFIG_USB_HS +#define CDC_MAX_MPS 512 +#else +#define CDC_MAX_MPS 64 +#endif + +void usbd_configure_done_callback(void) +{ + /* setup first out ep read transfer */ + usbd_ep_start_read(CDC_OUT_EP, read_buffer, 2048); +} + +void usbd_cdc_acm_bulk_out(uint8_t ep, uint32_t nbytes) +{ + USB_LOG_RAW("actual out len:%d\r\n", nbytes); + // for (int i = 0; i < 100; i++) { + // printf("%02x ", read_buffer[i]); + // } + // printf("\r\n"); + /* setup next out ep read transfer */ + usbd_ep_start_read(CDC_OUT_EP, read_buffer, 2048); +} + +void usbd_cdc_acm_bulk_in(uint8_t ep, uint32_t nbytes) +{ + USB_LOG_RAW("actual in len:%d\r\n", nbytes); + + if ((nbytes % CDC_MAX_MPS) == 0 && nbytes) { + /* send zlp */ + usbd_ep_start_write(CDC_IN_EP, NULL, 0); + } else { + ep_tx_busy_flag = false; + } +} + +/*!< endpoint call back */ +struct usbd_endpoint cdc_out_ep = { + .ep_addr = CDC_OUT_EP, + .ep_cb = usbd_cdc_acm_bulk_out +}; + +struct usbd_endpoint cdc_in_ep = { + .ep_addr = CDC_IN_EP, + .ep_cb = usbd_cdc_acm_bulk_in +}; + +struct usbd_interface intf0; +struct usbd_interface intf1; + +/* function ------------------------------------------------------------------*/ +void cdc_acm_init(void) +{ + const uint8_t data[10] = { 0x31, 0x32, 0x33, 0x34, 0x35, 0x36, 0x37, 0x38, 0x39, 0x30 }; + + memcpy(&write_buffer[0], data, 10); + memset(&write_buffer[10], 'a', 2038); + + usbd_desc_register(cdc_descriptor); + usbd_add_interface(usbd_cdc_acm_init_intf(&intf0)); + usbd_add_interface(usbd_cdc_acm_init_intf(&intf1)); + usbd_add_endpoint(&cdc_out_ep); + usbd_add_endpoint(&cdc_in_ep); + usbd_initialize(); +} + +volatile uint8_t dtr_enable = 0; + +void usbd_cdc_acm_set_dtr(uint8_t intf, bool dtr) +{ + if (dtr) { + dtr_enable = 1; + } else { + dtr_enable = 0; + } +} + +void cdc_acm_data_send_with_dtr(const uint8_t *data, uint32_t data_len ) +{ + if (dtr_enable) { + ep_tx_busy_flag = true; + usbd_ep_start_write(CDC_IN_EP, data, data_len); + while (ep_tx_busy_flag) { + } + } +} + +void cdc_acm_data_send_with_dtr_test(void) +{ + if (dtr_enable) { + ep_tx_busy_flag = true; + usbd_ep_start_write(CDC_IN_EP, write_buffer, 2048); + while (ep_tx_busy_flag) { + } + } +} diff --git a/flash_prog_cfg.ini b/flash_prog_cfg.ini new file mode 100644 index 0000000..5bde55b --- /dev/null +++ b/flash_prog_cfg.ini @@ -0,0 +1,11 @@ +[cfg] +# 0: no erase, 1:programmed section erase, 2: chip erase +erase = 1 +# skip mode set first para is skip addr, second para is skip len, multi-segment region with ; separated +skip_mode = 0x0, 0x0 +# 0: not use isp mode, #1: isp mode +boot2_isp_mode = 0 + +[FW] +filedir = ./build/build_out/usbd*_$(CHIPNAME).bin +address = 0x000000 \ No newline at end of file diff --git a/main.c b/main.c new file mode 100644 index 0000000..b8223c6 --- /dev/null +++ b/main.c @@ -0,0 +1,35 @@ +#include "usbh_core.h" +#include "bflb_mtimer.h" +#include "board.h" + +#include "usbd_core.h" +#include "usbd_cdc.h" + +extern void cdc_acm_init(void); +extern void cdc_acm_data_send_with_dtr(const uint8_t *, uint32_t); + +uint32_t buffer_init(char *); + +USB_NOCACHE_RAM_SECTION USB_MEM_ALIGNX uint8_t write_buffer_main[2048]; + +int main(void) +{ + board_init(); + uint32_t data_len = buffer_init("Hello world!\r\n"); + + cdc_acm_init(); + while (1) { + cdc_acm_data_send_with_dtr(write_buffer_main, data_len); + bflb_mtimer_delay_ms(2000); + } +} + +uint32_t buffer_init(char *data) { + + uint32_t data_len = 0; + for (ssize_t inx = 0; data[inx]; inx++) { + write_buffer_main[inx] = data[inx]; + if (data[inx]) data_len++; + } + return data_len; +} diff --git a/proj.conf b/proj.conf new file mode 100644 index 0000000..4b32eea --- /dev/null +++ b/proj.conf @@ -0,0 +1,7 @@ +set(CONFIG_CHERRYUSB 1) +set(CONFIG_CHERRYUSB_DEVICE 1) +set(CONFIG_CHERRYUSB_DEVICE_CDC 1) +set(CONFIG_CHERRYUSB_DEVICE_HID 1) +set(CONFIG_CHERRYUSB_DEVICE_MSC 1) +set(CONFIG_CHERRYUSB_DEVICE_AUDIO 1) +set(CONFIG_CHERRYUSB_DEVICE_VIDEO 1) \ No newline at end of file diff --git a/usb_config.h b/usb_config.h new file mode 100644 index 0000000..90aaf5d --- /dev/null +++ b/usb_config.h @@ -0,0 +1,132 @@ +/* + * Copyright (c) 2022, sakumisu + * + * SPDX-License-Identifier: Apache-2.0 + */ +#ifndef CHERRYUSB_CONFIG_H +#define CHERRYUSB_CONFIG_H + +/* ================ USB common Configuration ================ */ + +#define CONFIG_USB_PRINTF(...) printf(__VA_ARGS__) + +#define usb_malloc(size) malloc(size) +#define usb_free(ptr) free(ptr) + +#ifndef CONFIG_USB_DBG_LEVEL +#define CONFIG_USB_DBG_LEVEL USB_DBG_INFO +#endif + +/* Enable print with color */ +#define CONFIG_USB_PRINTF_COLOR_ENABLE + +/* data align size when use dma */ +#ifndef CONFIG_USB_ALIGN_SIZE +#define CONFIG_USB_ALIGN_SIZE 4 +#endif + +/* attribute data into no cache ram */ +#define USB_NOCACHE_RAM_SECTION __attribute__((section(".noncacheable"))) + +/* ================= USB Device Stack Configuration ================ */ + +/* Ep0 max transfer buffer, specially for receiving data from ep0 out */ +#define CONFIG_USBDEV_REQUEST_BUFFER_LEN 256 + +/* Setup packet log for debug */ +// #define CONFIG_USBDEV_SETUP_LOG_PRINT + +/* Check if the input descriptor is correct */ +// #define CONFIG_USBDEV_DESC_CHECK + +/* Enable test mode */ +// #define CONFIG_USBDEV_TEST_MODE + +#ifndef CONFIG_USBDEV_MSC_BLOCK_SIZE +#define CONFIG_USBDEV_MSC_BLOCK_SIZE 512 +#endif + +#ifndef CONFIG_USBDEV_MSC_MANUFACTURER_STRING +#define CONFIG_USBDEV_MSC_MANUFACTURER_STRING "" +#endif + +#ifndef CONFIG_USBDEV_MSC_PRODUCT_STRING +#define CONFIG_USBDEV_MSC_PRODUCT_STRING "" +#endif + +#ifndef CONFIG_USBDEV_MSC_VERSION_STRING +#define CONFIG_USBDEV_MSC_VERSION_STRING "0.01" +#endif + +// #define CONFIG_USBDEV_MSC_THREAD + +#ifdef CONFIG_USBDEV_MSC_THREAD +#ifndef CONFIG_USBDEV_MSC_STACKSIZE +#define CONFIG_USBDEV_MSC_STACKSIZE 2048 +#endif + +#ifndef CONFIG_USBDEV_MSC_PRIO +#define CONFIG_USBDEV_MSC_PRIO 4 +#endif +#endif + +#ifndef CONFIG_USBDEV_AUDIO_VERSION +#define CONFIG_USBDEV_AUDIO_VERSION 0x0100 +#endif + +#ifndef CONFIG_USBDEV_AUDIO_MAX_CHANNEL +#define CONFIG_USBDEV_AUDIO_MAX_CHANNEL 8 +#endif + +/* ================ USB HOST Stack Configuration ================== */ + +#define CONFIG_USBHOST_MAX_RHPORTS 1 +#define CONFIG_USBHOST_MAX_EXTHUBS 1 +#define CONFIG_USBHOST_MAX_EHPORTS 4 +#define CONFIG_USBHOST_MAX_INTERFACES 6 +#define CONFIG_USBHOST_MAX_INTF_ALTSETTINGS 8 +#define CONFIG_USBHOST_MAX_ENDPOINTS 4 + +#define CONFIG_USBHOST_DEV_NAMELEN 16 + +#ifndef CONFIG_USBHOST_PSC_PRIO +#define CONFIG_USBHOST_PSC_PRIO 4 +#endif +#ifndef CONFIG_USBHOST_PSC_STACKSIZE +#define CONFIG_USBHOST_PSC_STACKSIZE 2048 +#endif + +//#define CONFIG_USBHOST_GET_STRING_DESC + +/* Ep0 max transfer buffer */ +#define CONFIG_USBHOST_REQUEST_BUFFER_LEN 512 + +#ifndef CONFIG_USBHOST_CONTROL_TRANSFER_TIMEOUT +#define CONFIG_USBHOST_CONTROL_TRANSFER_TIMEOUT 500 +#endif + +#ifndef CONFIG_USBHOST_MSC_TIMEOUT +#define CONFIG_USBHOST_MSC_TIMEOUT 5000 +#endif + +/* ================ USB Device Port Configuration ================*/ + +//#define USBD_IRQHandler USBD_IRQHandler +//#define USB_BASE (0x40080000UL) +//#define USB_NUM_BIDIR_ENDPOINTS 4 + +/* ================ USB Host Port Configuration ==================*/ + +#define CONFIG_USBHOST_PIPE_NUM 10 + +/* ================ EHCI Configuration ================ */ + +#define CONFIG_USB_EHCI_HCCR_BASE (0x20072000) +#define CONFIG_USB_EHCI_HCOR_BASE (0x20072000 + 0x10) +#define CONFIG_USB_EHCI_FRAME_LIST_SIZE 1024 +// #define CONFIG_USB_EHCI_INFO_ENABLE +#define CONFIG_USB_ECHI_HCOR_RESERVED_DISABLE +// #define CONFIG_USB_EHCI_CONFIGFLAG +// #define CONFIG_USB_EHCI_PORT_POWER + +#endif