diff --git a/lib/usb_cdcacm.c b/lib/usb_cdcacm.c index b5b46f3..b866f42 100644 --- a/lib/usb_cdcacm.c +++ b/lib/usb_cdcacm.c @@ -39,6 +39,8 @@ /** maximum packet size for USB data transfer */ #define USB_DATA_TRANSFER_SIZE 64 +volatile bool usb_cdcacm_connecting = false; + static uint8_t usbd_control_buffer[128] = {0}; /**< buffer to be used for control requests */ static usbd_device *usb_device = NULL; /**< structure holding all the info related to the USB device */ @@ -47,7 +49,6 @@ static uint8_t tx_buffer[512] = {0}; /**< ring buffer for data to transmit */ static volatile uint16_t tx_i = 0; /**< current position if transmitted data */ static volatile uint16_t tx_used = 0; /**< how much data needs to be transmitted */ static volatile bool tx_lock = false; /**< if the transmit buffer is currently being written */ -static bool connected = false; /**< is the USB device is connected to a host */ /** USB CDC ACM device descriptor * @note as defined in USB CDC specification section 5 @@ -200,6 +201,7 @@ static const struct usb_interface_descriptor usb_dfu_interface = { .bInterfaceSubClass = 1, /**< DFU interface subclass (not defined in libopencm3 dfu lib) */ .bInterfaceProtocol = 1, /**< runtime protocol (not defined in libopencm3 dfu lib) */ .iInterface = 3, /**< the index of the string in the string table that represents interface description */ + .extra = &usb_dfu_functional, /**< point to functional descriptor */ .extralen = sizeof(usb_dfu_functional), /**< size of functional descriptor */ }; @@ -324,7 +326,7 @@ static int usb_cdcacm_control_request(usbd_device *usbd_dev, struct usb_setup_da } else { switch (req->bRequest) { case USB_CDC_REQ_SET_CONTROL_LINE_STATE: - connected = req->wValue ? true : false; // check if terminal is open + usb_cdcacm_connecting = req->wValue ? true : false; // check if terminal is open //bool dtr = (req->wValue & (1 << 0)) ? true : false; //bool rts = (req->wValue & (1 << 1)) ? true : false; /* this Linux cdc_acm driver requires this to be implemented @@ -360,6 +362,9 @@ static int usb_cdcacm_control_request(usbd_device *usbd_dev, struct usb_setup_da default: return 0; } + if (tx_used>0) { // if buffer is not empty + usbd_ep_write_packet(usb_device, 0x82, NULL, 0); // trigger tx callback + } } return 1; } @@ -378,7 +383,7 @@ static void usb_cdcacm_data_rx_cb(usbd_device *usbd_dev, uint8_t ep) /* receive data */ usb_length = usbd_ep_read_packet(usbd_dev, 0x02, usb_data, sizeof(usb_data)); if (usb_length) { // copy received data - for (uint16_t i=0; i0) { // to buffer is not empty anymore + if (tx_used>0) { // if buffer is not empty anymore usbd_ep_write_packet(usb_device, 0x82, NULL, 0); // trigger tx callback } } diff --git a/lib/usb_cdcacm.h b/lib/usb_cdcacm.h index d56f489..df1c534 100644 --- a/lib/usb_cdcacm.h +++ b/lib/usb_cdcacm.h @@ -19,6 +19,9 @@ */ #pragma once +/** flag set to true when user is connected to USB CDC ACM port (e.g. when a terminal is opened) */ +extern volatile bool usb_cdcacm_connecting; + /** setup USB CDC ACM peripheral */ void usb_cdcacm_setup(void); /** send character over USB (non-blocking)