From 2edc933ce0e547b616a599d6d18b8235f4ac6058 Mon Sep 17 00:00:00 2001 From: schneider Date: Sat, 10 Dec 2011 21:39:32 +0100 Subject: [PATCH] speed up for cdc --- firmware/usbcdc/Makefile | 1 - firmware/usbcdc/cdc_buf.c | 161 -------------------------------------- firmware/usbcdc/cdc_buf.h | 29 ------- firmware/usbcdc/cdcuser.c | 108 ++++++++++++++++++------- firmware/usbcdc/cdcuser.h | 2 +- firmware/usbcdc/util.c | 31 ++------ 6 files changed, 86 insertions(+), 246 deletions(-) delete mode 100644 firmware/usbcdc/cdc_buf.c delete mode 100644 firmware/usbcdc/cdc_buf.h diff --git a/firmware/usbcdc/Makefile b/firmware/usbcdc/Makefile index 3a9ea98..3019ad4 100644 --- a/firmware/usbcdc/Makefile +++ b/firmware/usbcdc/Makefile @@ -4,7 +4,6 @@ OBJS = OBJS += cdcuser.o -OBJS += cdc_buf.o OBJS += usbcore.o OBJS += usbdesc.o OBJS += usbhw.o diff --git a/firmware/usbcdc/cdc_buf.c b/firmware/usbcdc/cdc_buf.c deleted file mode 100644 index 2a7c1d5..0000000 --- a/firmware/usbcdc/cdc_buf.c +++ /dev/null @@ -1,161 +0,0 @@ -/******************************************************************* - Copyright (C) 2009 FreakLabs - All rights reserved. - - Redistribution and use in source and binary forms, with or without - modification, are permitted provided that the following conditions - are met: - - 1. Redistributions of source code must retain the above copyright - notice, this list of conditions and the following disclaimer. - 2. Redistributions in binary form must reproduce the above copyright - notice, this list of conditions and the following disclaimer in the - documentation and/or other materials provided with the distribution. - 3. Neither the name of the the copyright holder nor the names of its contributors - may be used to endorse or promote products derived from this software - without specific prior written permission. - - THIS SOFTWARE IS PROVIDED BY THE THE COPYRIGHT HOLDERS AND CONTRIBUTORS ``AS IS'' AND - ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE - IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE - ARE DISCLAIMED. IN NO EVENT SHALL THE INSTITUTE OR CONTRIBUTORS BE LIABLE - FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL - DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS - OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) - HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT - LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY - OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF - SUCH DAMAGE. - - Originally written by Christopher Wang aka Akiba. - Please post support questions to the FreakLabs forum. -*******************************************************************/ - -/**************************************************************************/ -/*! - @file cdc_buf.c - @author Christopher Wang (Freaklabs) - Modified by: K. Townsend (microBuilder.eu) - @date 19 May 2010 - - Original code taken from the FreakUSB Open Source USB Device Stack - http://freaklabs.org/index.php/FreakUSB-Open-Source-USB-Device-Stack.html - - If it works well, you can thank Akiba at Freaklabs. If it fails - miserably, you can blame me (since parts of it it were rather - ungraciously modified). :-) - -*/ -/**************************************************************************/ - -#include "cdc_buf.h" - -static cdc_buffer_t cdcfifo; - -/**************************************************************************/ -/*! - Gets a pointer to the fifo buffer -*/ -/**************************************************************************/ -cdc_buffer_t *cdcGetBuffer() -{ - return &cdcfifo; -} - -/**************************************************************************/ -/*! - Initialises the RX FIFO buffer -*/ -/**************************************************************************/ -void cdcBufferInit() -{ - cdcfifo.len = 0; -} - -/**************************************************************************/ -/*! - Read one byte out of the RX buffer. This function will return the byte - located at the array index of the read pointer, and then increment the - read pointer index. If the read pointer exceeds the maximum buffer - size, it will roll over to zero. -*/ -/**************************************************************************/ -uint8_t cdcBufferRead() -{ - uint8_t data; - - data = cdcfifo.buf[cdcfifo.rd_ptr]; - cdcfifo.rd_ptr = (cdcfifo.rd_ptr + 1) % CFG_USBCDC_BUFFERSIZE; - cdcfifo.len--; - return data; -} - -/**************************************************************************/ -/*! - Reads x bytes from cdc buffer - */ -/**************************************************************************/ -uint32_t cdcBufferReadLen(uint8_t* buf, uint32_t len) -{ - uint32_t counter, actual; - counter = actual = 0; - - while(counter != len) - { - // Make sure we don't exceed buffer limits - if (cdcfifo.len > 0) - { - buf[counter] = cdcBufferRead(); - actual++; - counter++; - } - else - { - return actual; - } - } - - return actual; -} - -/**************************************************************************/ -/*! - Write one byte into the RX buffer. This function will write one - byte into the array index specified by the write pointer and increment - the write index. If the write index exceeds the max buffer size, then it - will roll over to zero. -*/ -/**************************************************************************/ -void cdcBufferWrite(uint8_t data) -{ - cdcfifo.buf[cdcfifo.wr_ptr] = data; - cdcfifo.wr_ptr = (cdcfifo.wr_ptr + 1) % CFG_USBCDC_BUFFERSIZE; - cdcfifo.len++; -} - -/**************************************************************************/ -/*! - Clear the fifo read and write pointers and set the length to zero. -*/ -/**************************************************************************/ -void cdcBufferClearFIFO() -{ - cdcfifo.rd_ptr = 0; - cdcfifo.wr_ptr = 0; - cdcfifo.len = 0; -} - -/**************************************************************************/ -/*! - Check whether there is any data pending on the RX buffer. -*/ -/**************************************************************************/ -uint8_t cdcBufferDataPending() -{ - if (cdcfifo.len != 0) - { - return 1; - } - - return 0; -} diff --git a/firmware/usbcdc/cdc_buf.h b/firmware/usbcdc/cdc_buf.h deleted file mode 100644 index c5cdfad..0000000 --- a/firmware/usbcdc/cdc_buf.h +++ /dev/null @@ -1,29 +0,0 @@ -/*---------------------------------------------------------------------------- - * Name: cdc_buf.h - * Purpose: usb cdc buffer handling - * Version: V1.00 - *---------------------------------------------------------------------------*/ - -#ifndef __CDC_BUF_H__ -#define __CDC_BUF_H__ - -#include "projectconfig.h" - -// Buffer used for circular fifo -typedef struct _cdc_buffer_t -{ - volatile uint8_t len; - volatile uint8_t wr_ptr; - volatile uint8_t rd_ptr; - uint8_t buf[CFG_USBCDC_BUFFERSIZE]; -} cdc_buffer_t; - -cdc_buffer_t * cdcGetBuffer(); -void cdcBufferInit(); -uint8_t cdcBufferRead(); -uint32_t cdcBufferReadLen(uint8_t* buf, uint32_t len); -void cdcBufferWrite(uint8_t data); -void cdcBufferClearFIFO(); -uint8_t cdcBufferDataPending(); - -#endif diff --git a/firmware/usbcdc/cdcuser.c b/firmware/usbcdc/cdcuser.c index d553f47..222dae2 100644 --- a/firmware/usbcdc/cdcuser.c +++ b/firmware/usbcdc/cdcuser.c @@ -1,4 +1,4 @@ -/*---------------------------------------------------------------------------- +/*----------/BulkBufOut------------------------------------------------------------------ * U S B - K e r n e l *---------------------------------------------------------------------------- * Name: cdcuser.c @@ -17,6 +17,7 @@ *---------------------------------------------------------------------------*/ #include "projectconfig.h" +#include "basic/basic.h" #include "usb.h" #include "usbhw.h" @@ -24,15 +25,14 @@ #include "usbcore.h" #include "cdc.h" #include "cdcuser.h" -#include "cdc_buf.h" -// unsigned char BulkBufIn [64]; // Buffer to store USB IN packet +unsigned char BulkBufIn [64]; // Buffer to store USB IN packet unsigned char BulkBufOut [64]; // Buffer to store USB OUT packet unsigned char NotificationBuf [10]; CDC_LINE_CODING CDC_LineCoding = {CFG_USBCDC_BAUDRATE, 0, 0, 8}; unsigned short CDC_SerialState = 0x0000; -unsigned short CDC_DepInEmpty = 1; // Data IN EP is empty +volatile unsigned char CDC_DepInEmpty = 1; // Data IN EP is empty /*---------------------------------------------------------------------------- We need a buffer for incoming data on USB port because USB receives @@ -61,6 +61,7 @@ typedef struct __CDC_BUF_T } CDC_BUF_T; CDC_BUF_T CDC_OutBuf; // buffer for all CDC Out data +CDC_BUF_T CDC_InBuf; // buffer for all CDC Out data /*---------------------------------------------------------------------------- read data from CDC_OutBuf @@ -116,6 +117,67 @@ int CDC_OutBufAvailChar (int *availChar) } /* end Buffer handling */ +/*---------------------------------------------------------------------------- + read data from CDC_InBuf + *---------------------------------------------------------------------------*/ +int CDC_RdInBuf (char *buffer, const int *length) +{ + int bytesToRead, bytesRead; + + /* Read *length bytes, block if *bytes are not avaialable */ + bytesToRead = *length; + //bytesToRead = (bytesToRead < (*length)) ? bytesToRead : (*length); + bytesRead = bytesToRead; + + + // ... add code to check for underrun + + while (bytesToRead--) { + *buffer++ = CDC_BUF_RD(CDC_InBuf); + } + return (bytesRead); +} + +/*---------------------------------------------------------------------------- + write data to CDC_InBuf + *---------------------------------------------------------------------------*/ +int CDC_WrInBuf (const char *buffer, int *length) +{ + int bytesToWrite, bytesWritten; + + // Write *length bytes + bytesToWrite = *length; + bytesWritten = bytesToWrite; + + //Just block if we can't write all at once + while( CDC_BUF_SIZE - CDC_BUF_COUNT(CDC_InBuf) < bytesToWrite ); + + //uint8_t flush = CDC_DepInEmpty; + while (bytesToWrite--) { + CDC_BUF_WR(CDC_InBuf, *buffer++); // Copy Data to buffer + } + //if( flush == 1 ){ + if( CDC_DepInEmpty && CDC_BUF_COUNT(CDC_InBuf) ){ + CDC_DepInEmpty = 0; + gpioSetValue (RB_LED2, 0); + CDC_BulkIn(); + } + + return (bytesWritten); +} + +/*---------------------------------------------------------------------------- + check if character(s) are available at CDC_OutBuf + *---------------------------------------------------------------------------*/ +int CDC_InBufAvailChar (int *availChar) +{ + *availChar = CDC_BUF_COUNT(CDC_InBuf); + + return (0); +} +/* end Buffer handling */ + + /*---------------------------------------------------------------------------- CDC Initialisation @@ -129,12 +191,8 @@ void CDC_Init (void) CDC_SerialState = CDC_GetSerialState(); CDC_BUF_RESET(CDC_OutBuf); + CDC_BUF_RESET(CDC_InBuf); - // Initialise the CDC buffer. This is required to buffer outgoing - // data (MCU to PC) since data can only be sent 64 bytes per frame - // with at least 1ms between frames. To see how the buffer is used, - // see 'puts' in systeminit.c - cdcBufferInit(); } @@ -277,25 +335,19 @@ uint32_t CDC_SendBreak (unsigned short wDurationOfBreak) { *---------------------------------------------------------------------------*/ void CDC_BulkIn(void) { -// int numBytesRead, numBytesAvail; -// -// // ToDo: Modify BulkIn to send incoming data to USB -// -// ser_AvailChar (&numBytesAvail); -// -// // ... add code to check for overwrite -// -// numBytesRead = ser_Read ((char *)&BulkBufIn[0], &numBytesAvail); -// -// // send over USB -// if (numBytesRead > 0) { -// USB_WriteEP (CDC_DEP_IN, &BulkBufIn[0], numBytesRead); -// } -// else { -// CDC_DepInEmpty = 1; -// } -// -// + int numBytesRead, numBytesAvail; + CDC_InBufAvailChar(&numBytesAvail); + numBytesRead = CDC_RdInBuf(&BulkBufIn[0], &numBytesAvail); + // send over USB + if (numBytesRead > 0) { + //gpioSetValue (RB_LED0, 1); + USB_WriteEP (CDC_DEP_IN, &BulkBufIn[0], numBytesRead); + //gpioSetValue (RB_LED0, 0); + } else { + //USB_WriteEP (CDC_DEP_IN, "test\r\n", 6); + CDC_DepInEmpty = 1; + //gpioSetValue (RB_LED2, 1); + } } diff --git a/firmware/usbcdc/cdcuser.h b/firmware/usbcdc/cdcuser.h index 55cd910..4a2a82b 100644 --- a/firmware/usbcdc/cdcuser.h +++ b/firmware/usbcdc/cdcuser.h @@ -57,7 +57,7 @@ extern void CDC_Init (void); extern unsigned short CDC_GetSerialState (void); /* flow control */ -extern unsigned short CDC_DepInEmpty; // DataEndPoint IN empty +extern volatile unsigned char CDC_DepInEmpty; // DataEndPoint IN empty #endif /* __CDCUSER_H__ */ diff --git a/firmware/usbcdc/util.c b/firmware/usbcdc/util.c index fd3b041..5f3a69a 100644 --- a/firmware/usbcdc/util.c +++ b/firmware/usbcdc/util.c @@ -16,30 +16,9 @@ volatile unsigned int lastTick; int puts(const char * str){ if(!USB_Configuration) return -1; - - while(*str) - cdcBufferWrite(*str++); - - //XXX: This assumes systick is 1ms, which it isn't for us. - // this makes usbserial unnecessary slow. Ah well.... - - // Check if we can flush the buffer now or if we need to wait - unsigned int currentTick = systickGetTicks(); - if (currentTick != lastTick){ - uint8_t frame[64]; - uint32_t bytesRead = 0; - char repeat=0; - while (cdcBufferDataPending()){ - // Read up to 64 bytes as long as possible - bytesRead = cdcBufferReadLen(frame, 64); - USB_WriteEP (CDC_DEP_IN, frame, bytesRead); - if(repeat) - systickDelay(1); - else - repeat=1; - } - lastTick = currentTick; - } + + int len = strlen(str); + CDC_WrInBuf(str, &len); return 0; } @@ -47,8 +26,8 @@ int puts_plus(const char * str){ if(!USB_Configuration) return -1; - while(*str) - cdcBufferWrite(*str++); + int len = strlen(str); + CDC_WrInBuf(str, &len); return 0; }