Important changes to repositories hosted on mbed.com
Mbed hosted mercurial repositories are deprecated and are due to be permanently deleted in July 2026.
To keep a copy of this software download the repository Zip archive or clone locally using Mercurial.
It is also possible to export all your personal repositories from the account settings page.
Revision 2:6013f6d867e5, committed 2014-04-04
- Comitter:
- jeroen3
- Date:
- Fri Apr 04 21:36:55 2014 +0000
- Parent:
- 1:5f59aa9b86ed
- Commit message:
- major revision, now supports multiple C formats and Templates C++
Changed in this revision
--- a/xIFO.c Mon Oct 28 19:20:00 2013 +0000
+++ /dev/null Thu Jan 01 00:00:00 1970 +0000
@@ -1,287 +0,0 @@
-
- /**
- * @file xifo.c
- * @brief xifo circular buffer
- * @details xifo supplies object oriented circular buffer with 32 bit size elements. \n
- * To use either as FIFO (First In First Out) or as FILO (First In Last Out)
- *
- * @Author Jeroen Lodder
- * @Date April 2013
- * @version 2
- *
- * @{
- */
-#include "xIFO.h"
-
-/**
- * @brief Initialise buffer object structure.
- *
- * @note Does not clear memory pool.
- *
- * @param[in] c Pointer to @p xifo_t object used for configuration.
- * @param[in] s Number of elements buffer can hold (size).
- * @param[in] sp Start of pre-allocated memory pool.
- */
-void xifo_init(xifo_t *c, uint32_t s, uint32_t *sp){
- c->startpool = sp;
- c->endpool = &sp[s-1];
- c->size = s;
- c->full = 0;
- c->elementcount = 0;
- c->read = sp;
- c->write = sp;
-}
-
-/**
- * @brief Clear buffer contents
- *
- * @note Must be used on initialised buffer object.
- *
- * @param[in] c Pointer to @p xifo_t object.
- */
-void xifo_clear(xifo_t *c){
- c->ptemp = c->startpool;
- while(c->ptemp <= c->endpool){
- *c->ptemp++ = 0;
- }
-}
-
-/**
- * @brief Read from buffer (lr) Least Recent oriented (fifo)
- *
- * @note Buffer state will be preserved
- *
- * @warning Consider this opertaion as atomic!
- *
- * @details Read n elements from the oldest element to the most recent.
- * As for index[0] the least recently added element is returned.
- * And for index[elementcount] the most recent element is returned.
- * This makes it possible to peek in fifo.
- *
- * @param[in] c Pointer to @p xifo_t used for configuration.
- * @param[in] index Index relative from least recent
- *
- * @return Contents of element or 0 if failed (element can hold 0)
- */
-uint32_t xifo_read_lr(xifo_t *c, uint32_t index){
- /* Verify there is valid data to read */
- if(index+1 > c->elementcount){
- return 0; /* Nothing to read there */
- }
- /* Calculate index of oldest element */
- index = (c->elementcount-1) - index;
- /* Set pointer */
- c->ptemp = (c->read) - index;
- if(c->ptemp < c->startpool){
- /* We exceeded pool boundaries */
- /* Calculate overshoot (startpool - indexptr) and subtract from end */
- /* Since one element of overshoot results in end - 1 you would miss the last value */
- c->ptemp = (c->endpool+1) - (c->startpool - c->ptemp);
- }
- /* Read most recent */
- return *c->ptemp;
-}
-
-/**
- * @brief Read from buffer (mr) Most Recent oriented (filo)
- *
- * @note Buffer state will be preserved
- *
- * @warning Consider this opertaion as atomic!
- *
- * @details Read n elements back in time.
- * As for index[0] the most recently added element is returned.
- * And for index[elementcount] the oldest element is returned.
- * This makes it possible to keep history. For DSP application.
- *
- * @param[in] c Pointer to @p xifo_t used for configuration.
- * @param[in] index Index relative from most recent
- *
- * @return Contents of element or 0 if failed (element can hold 0)
- */
-uint32_t xifo_read_mr(xifo_t *c, uint32_t index){
- /* Verify there is valid data to read */
- if(index+1 > c->elementcount){
- return 0; /* Nothing to read there */
- }
- /* Set pointer */
- c->ptemp = (c->read) - index;
- /* Validate pointer */
- if(c->ptemp < c->startpool){
- /* We exceeded pool boundaries */
- /* Calculate overshoot (startpool - indexptr) and subtract from end */
- /* Since one element of overshoot results in end - 1 you would miss the last value */
- c->ptemp = (c->endpool+1) - (c->startpool - c->ptemp);
- }
- /* Read most recent */
- return *c->ptemp;
-}
-
-/**
- * @brief Pop (mr) most recent from buffer (filo)
- *
- * @note Buffer state will be altered
- *
- * @warning Consider this opertaion as atomic!
- *
- * @details Read and remove the most recently added from the buffer.
- * Using this results in a stack type of buffer.
- *
- * @param[in] c Pointer to @p xifo_t used for configuration.
- *
- * @return Contents of element or 0 if failed (element can hold 0)
- */
-uint32_t xifo_pop_mr(xifo_t *c){
- /* Verify there is valid data read */
- if(c->elementcount == 0){
- return 0; /* Nothing to read there */
- }
- /* Read */
- c->temp = *c->read;
- /* Empty */
- *c->read = 0;
- /* Most recent element read, return write pointer */
- c->write = c->read;
- /* Decrement read pointer */
- c->read--;
- /* Validate pointer */
- if( c->read < c->startpool ){
- /* We exceeded pool boundaries */
- c->read = c->endpool;
- }
- /* Reduce elementcount */
- c->elementcount--;
- if(c->elementcount < c->size)
- c->full = 0;
- return c->temp;
-}
-
-/**
- * @brief Pop (lr) least recent from buffer (fifo)
- *
- * @note Buffer state will be altered
- *
- * @warning Consider this opertaion as atomic!
- *
- * @details Read and remove the least recently added from the buffer.
- * Using this results in a fifo type of buffer.
- *
- * @param[in] c Pointer to @p xifo_t used for configuration.
- *
- * @return Contents of element or 0 if failed (element can hold 0)
- */
-uint32_t xifo_pop_lr(xifo_t *c){
- /* Verify there is valid data read */
- if(c->elementcount == 0){
- return 0; /* Nothing to read there */
- }
- /* Derive least recent buffer element */
- c->ptemp = c->read+1 - c->elementcount;
- /* Validate pointer */
- if(c->ptemp < c->startpool){
- /* We exceeded pool boundaries */
- /* Calculate overshoot (startpool - indexptr) and subtract from end */
- /* Since one element of overshoot results in end - 1 you would miss the last value */
- c->ptemp = (c->endpool+1) - (c->startpool - c->ptemp);
- }
- /* Read oldest buffer element */
- { /* block with temporary variable to prevent stack use */
- register uint32_t element;
- /* Read to temp register */
- element = *c->ptemp;
- /* Empty */
- *c->ptemp = 0;
- /* Clear temp register */
- c->temp = element;
- }
- /* Reduce elementcount */
- c->elementcount--;
- /* Check full flag */
- if(c->elementcount < c->size)
- c->full = 0;
- return c->temp;
-}
-
-/**
- * @brief Write to buffer
- *
- * @note Readpointer is automatically set to the last added element.
- *
- * @warning Consider this opertaion as atomic!
- *
- * @details Adds a value to the buffer.
- * Automatically overwrites oldest elements when full.
- *
- * @param[in] c Pointer to @p xifo_t used for configuration.
- * @param[in] data Data to add to buffer
- *
- * @return Number of free buffer elements
- */
-uint32_t xifo_write(xifo_t *c, uint32_t data){
- /* Write data */
- *c->write = data;
- /* Update read pointer to most recent element */
- c->read = c->write;
- /* Write pointer increment */
- c->write += 1;
- /* Validate pointer */
- if( c->write > c->endpool){
- /* We exceeded pool boundaries */
- c->write = c->startpool;
- }
- /* Update elementcount */
- c->elementcount++;
- /* Verify full */
- if( c->elementcount >= c->size ){
- c->full = 1;
- c->elementcount = c->size;
- }
- /* return free elements count */
- return c->size - c->elementcount;
-}
-
-/**
- * @brief Get buffer size
- *
- * @param[in] c Pointer to @p xifo_t used for configuration.
- *
- * @return Size of memory pool in elements
- */
-uint32_t xifo_get_size(xifo_t *c){
- return c->size;
-}
-
-/**
- * @brief Get number of used elements
- *
- * @param[in] c Pointer to @p xifo_t used for configuration.
- *
- * @return Number of used buffer elements
- */
-uint32_t xifo_get_used(xifo_t *c){
- return c->elementcount;
-}
-
-/**
-* @brief Get number of free elements
-*
-* @param[in] c Pointer to @p xifo_t used for configuration.
-*
-* @return Number of free elements
-*/
-uint32_t xifo_get_free(xifo_t *c){
- return c->size - c->elementcount;
-}
-
-/**
- * @brief Get full flag
- *
- * @param[in] c Pointer to @p xifo_t used for configuration.
- *
- * @return 1 if full
- */
-uint32_t xifo_get_full(xifo_t *c){
- return c->full;
-}
-
-/** @} */
--- /dev/null Thu Jan 01 00:00:00 1970 +0000
+++ b/xIFO.cpp Fri Apr 04 21:36:55 2014 +0000
@@ -0,0 +1,1142 @@
+/**
+ * @file xifo.c
+ * @brief xifo circular buffer with <t>/8/16/32/64 bit elements
+ * @details xifo supplies object oriented circular buffer with 8 bit size elements. \n
+ * To use either as FIFO (First In First Out) or as FILO (First In Last Out)
+ * You might want to rename this file is you are using a C compiler.
+ *
+ * @Author Jeroen Lodder
+ * @Date March 2014
+ * @version 3
+ *
+ * Copyright (c) 2014 Jeroen Lodder
+ *
+ * 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.
+ *
+ * @{
+ */
+#include "xIFO.h"
+
+#if xIFO_USE_64BIT == TRUE
+/**
+ * @brief Initialize buffer object structure.
+ *
+ * @note Does not clear memory pool.
+ *
+ * @param[in] c Pointer to @p xifo64_t object used for configuration.
+ * @param[in] s Number of elements buffer can hold (size).
+ * @param[in] sp Start of pre-allocated memory pool.
+ */
+void xifo64_init(xifo64_t *c, uint32_t s, uint64_t *sp){
+ c->startpool = sp;
+ c->size = s;
+ c->endpool = &sp[--s];
+ c->full = 0;
+ c->count = 0;
+ c->read = sp;
+ c->write = sp;
+}
+
+/**
+ * @brief Clear buffer memory pool
+ *
+ * @note Must be used on initialised buffer object.
+ *
+ * @param[in] c Pointer to @p xifo64_t object.
+ */
+void xifo64_clear(xifo64_t *c){
+ register uint64_t *ptemp = c->startpool;
+ register uint32_t i = c->size;
+ while(i--){
+
+ *ptemp++ = 0;
+ }
+}
+
+/**
+ * @brief Read from buffer (lr) Least Recent oriented (fifo)
+ *
+ * @note Buffer state will be preserved
+ *
+ * @warning Consider this opertaion as atomic!
+ *
+ * @details Read n elements from the oldest element to the most recent.
+ * As for index[0] the least recently added element is returned.
+ * And for index[count] the most recent element is returned.
+ * This makes it possible to peek in fifo.
+ *
+ * @param[in] c Pointer to @p xifo64_t used for configuration.
+ * @param[in] index Index relative from least recent
+ *
+ * @return Contents of element or 0 if failed (element can hold 0)
+ */
+uint64_t xifo64_read_lr(xifo64_t *c, uint32_t index){
+ register uint64_t *ptemp;
+ /* Verify there is valid data to read */
+ if(index >= c->count){
+ return 0; /* Nothing to read there */
+ }
+ /* Calculate index of oldest element */
+ index = (c->count-1) - index;
+ /* Set pointer */
+ ptemp = (c->read) - index;
+ if(ptemp < c->startpool){
+ /* Exceeded pool boundaries */
+ /* Calculate overshoot (startpool - indexptr) and subtract from end */
+ /* Since one element of overshoot results in end - 1 you would miss the last value */
+ ptemp = (c->endpool+1) - (c->startpool - ptemp);
+ }
+ /* Read most recent */
+ return *ptemp;
+}
+
+/**
+ * @brief Read from buffer (mr) Most Recent oriented (filo)
+ *
+ * @note Buffer state will be preserved
+ *
+ * @warning Consider this opertaion as atomic!
+ *
+ * @details Read n elements back in time.
+ * As for index[0] the most recently added element is returned.
+ * And for index[count] the oldest element is returned.
+ * This makes it possible to keep history. For DSP application.
+ *
+ * @param[in] c Pointer to @p xifo64_t used for configuration.
+ * @param[in] index Index relative from most recent
+ *
+ * @return Contents of element or 0 if failed (element can hold 0)
+ */
+uint64_t xifo64_read_mr(xifo64_t *c, uint32_t index){
+ register uint64_t *ptemp;
+ /* Verify there is valid data to read */
+ if(index >= c->count){
+ return 0; /* Nothing to read there */
+ }
+ /* Set pointer */
+ ptemp = (c->read) - index;
+ /* Validate pointer */
+ if(ptemp < c->startpool){
+ /* Exceeded pool boundaries */
+ /* Calculate overshoot (startpool - indexptr) and subtract from end */
+ /* Since one element of overshoot results in end - 1 you would miss the last value */
+ ptemp = (c->endpool+1) - (c->startpool - ptemp);
+ }
+ /* Read most recent */
+ return *ptemp;
+}
+
+/**
+ * @brief Pop (mr) most recent from buffer (filo)
+ *
+ * @note Buffer state will be altered
+ *
+ * @warning Consider this opertaion as atomic!
+ *
+ * @details Read and remove the most recently added from the buffer.
+ * Using this results in a stack type of buffer.
+ *
+ * @param[in] c Pointer to @p xifo64_t used for configuration.
+ *
+ * @return Contents of element or 0 if failed (element can hold 0)
+ */
+uint64_t xifo64_pop_mr(xifo64_t *c){
+ register uint64_t temp;
+ /* Verify there is valid data read */
+ if(c->count == 0){
+ return 0; /* Nothing to read there */
+ }
+ /* Read */
+ temp = *c->read;
+ /* Empty */
+ *c->read = 0;
+ /* Most recent element read, return write pointer */
+ c->write = c->read;
+ /* Decrement read pointer */
+ c->read--;
+ /* Validate pointer */
+ if( c->read < c->startpool ){
+ /* Exceeded pool boundaries */
+ c->read = c->endpool;
+ }
+ /* Reduce count */
+ c->count--;
+ if(c->count < c->size)
+ c->full = 0;
+ return temp;
+}
+
+/**
+ * @brief Pop (lr) least recent from buffer (fifo)
+ *
+ * @note Buffer state will be altered
+ *
+ * @warning Consider this opertaion as atomic!
+ *
+ * @details Read and remove the least recently added from the buffer.
+ * Using this results in a fifo type of buffer.
+ *
+ * @param[in] c Pointer to @p xifo64_t used for configuration.
+ *
+ * @return Contents of element or 0 if failed (element can hold 0)
+ */
+uint64_t xifo64_pop_lr(xifo64_t *c){
+ register uint64_t *ptemp;
+ register uint64_t temp;
+ /* Verify there is valid data read */
+ if(c->count == 0){
+ return 0; /* Nothing to read there */
+ }
+ /* Derive least recent buffer element */
+ ptemp = (c->read+1) - c->count;
+ /* Validate pointer */
+ if(ptemp < c->startpool){
+ /* Exceeded pool boundaries */
+ /* Calculate overshoot (startpool - indexptr) and subtract from end */
+ /* Since one element of overshoot results in end - 1 you would miss the last value */
+ ptemp = (c->endpool+1) - (c->startpool - ptemp);
+ }
+ /* Read oldest buffer element */
+ /* Read to temp register */
+ temp = *ptemp;
+ /* Empty buffer element */
+ *ptemp = 0;
+ /* Reduce count */
+ c->count--;
+ /* Check full flag */
+ if(c->count < c->size)
+ c->full = 0;
+ return temp;
+}
+
+/**
+ * @brief Write to buffer
+ *
+ * @note Readpointer is automatically set to the last added element.
+ *
+ * @warning Consider this opertaion as atomic!
+ *
+ * @details Adds a value to the buffer.
+ * Automatically overwrites oldest elements when full.
+ *
+ * @param[in] c Pointer to @p xifo64_t used for configuration.
+ * @param[in] data Data to add to buffer
+ *
+ * @return Number of free buffer elements
+ */
+uint32_t xifo64_write(xifo64_t *c, uint64_t data){
+ /* Write data */
+ *c->write = data;
+ /* Update read pointer to most recent element */
+ c->read = c->write;
+ /* Write pointer increment */
+ c->write++;
+ /* Validate pointer */
+ if( c->write > c->endpool){
+ /* We exceeded pool boundaries */
+ c->write = c->startpool;
+ }
+ /* Update count */
+ c->count++;
+ /* Verify full */
+ if( c->count >= c->size ){
+ c->full = 1;
+ c->count = c->size;
+ }
+ /* return free elements count */
+ return c->size - c->count;
+}
+
+/**
+ * @brief Get buffer size
+ *
+ * @param[in] c Pointer to @p xifo64_t used for configuration.
+ *
+ * @return Size of memory pool in elements
+ */
+uint32_t xifo64_get_size(xifo64_t *c){
+ return c->size;
+}
+
+/**
+ * @brief Get number of used elements
+ *
+ * @param[in] c Pointer to @p xifo64_t used for configuration.
+ *
+ * @return Number of used buffer elements
+ */
+uint32_t xifo64_get_used(xifo64_t *c){
+ return c->count;
+}
+
+/**
+* @brief Get number of free elements
+*
+* @param[in] c Pointer to @p xifo64_t used for configuration.
+*
+* @return Number of free elements
+*/
+uint32_t xifo64_get_free(xifo64_t *c){
+ return c->size - c->count;
+}
+
+/**
+ * @brief Get full flag
+ *
+ * @param[in] c Pointer to @p xifo64_t used for configuration.
+ *
+ * @return 1 if full
+ */
+uint32_t xifo64_get_full(xifo64_t *c){
+ return c->full;
+}
+
+/** @} */
+#endif
+
+#if xIFO_USE_32BIT == TRUE
+/**
+ * @brief Initialize buffer object structure.
+ *
+ * @note Does not clear memory pool.
+ *
+ * @param[in] c Pointer to @p xifo32_t object used for configuration.
+ * @param[in] s Number of elements buffer can hold (size).
+ * @param[in] sp Start of pre-allocated memory pool.
+ */
+void xifo32_init(xifo32_t *c, uint32_t s, uint32_t *sp){
+ c->startpool = sp;
+ c->size = s;
+ c->endpool = &sp[--s];
+ c->full = 0;
+ c->count = 0;
+ c->read = sp;
+ c->write = sp;
+}
+
+/**
+ * @brief Clear buffer memory pool
+ *
+ * @note Must be used on initialised buffer object.
+ *
+ * @param[in] c Pointer to @p xifo32_t object.
+ */
+void xifo32_clear(xifo32_t *c){
+ register uint32_t *ptemp = c->startpool;
+ register uint32_t i = c->size;
+ while(i--){
+ *ptemp++ = 0;
+ }
+}
+
+/**
+ * @brief Read from buffer (lr) Least Recent oriented (fifo)
+ *
+ * @note Buffer state will be preserved
+ *
+ * @warning Consider this opertaion as atomic!
+ *
+ * @details Read n elements from the oldest element to the most recent.
+ * As for index[0] the least recently added element is returned.
+ * And for index[count] the most recent element is returned.
+ * This makes it possible to peek in fifo.
+ *
+ * @param[in] c Pointer to @p xifo32_t used for configuration.
+ * @param[in] index Index relative from least recent
+ *
+ * @return Contents of element or 0 if failed (element can hold 0)
+ */
+uint32_t xifo32_read_lr(xifo32_t *c, uint32_t index){
+ register uint32_t *ptemp;
+ /* Verify there is valid data to read */
+ if(index >= c->count){
+ return 0; /* Nothing to read there */
+ }
+ /* Calculate index of oldest element */
+ index = (c->count-1) - index;
+ /* Set pointer */
+ ptemp = (c->read) - index;
+ if(ptemp < c->startpool){
+ /* Exceeded pool boundaries */
+ /* Calculate overshoot (startpool - indexptr) and subtract from end */
+ /* Since one element of overshoot results in end - 1 you would miss the last value */
+ ptemp = (c->endpool+1) - (c->startpool - ptemp);
+ }
+ /* Read most recent */
+ return *ptemp;
+}
+
+/**
+ * @brief Read from buffer (mr) Most Recent oriented (filo)
+ *
+ * @note Buffer state will be preserved
+ *
+ * @warning Consider this opertaion as atomic!
+ *
+ * @details Read n elements back in time.
+ * As for index[0] the most recently added element is returned.
+ * And for index[count] the oldest element is returned.
+ * This makes it possible to keep history. For DSP application.
+ *
+ * @param[in] c Pointer to @p xifo32_t used for configuration.
+ * @param[in] index Index relative from most recent
+ *
+ * @return Contents of element or 0 if failed (element can hold 0)
+ */
+uint32_t xifo32_read_mr(xifo32_t *c, uint32_t index){
+ register uint32_t *ptemp;
+ /* Verify there is valid data to read */
+ if(index >= c->count){
+ return 0; /* Nothing to read there */
+ }
+ /* Set pointer */
+ ptemp = (c->read) - index;
+ /* Validate pointer */
+ if(ptemp < c->startpool){
+ /* Exceeded pool boundaries */
+ /* Calculate overshoot (startpool - indexptr) and subtract from end */
+ /* Since one element of overshoot results in end - 1 you would miss the last value */
+ ptemp = (c->endpool+1) - (c->startpool - ptemp);
+ }
+ /* Read most recent */
+ return *ptemp;
+}
+
+/**
+ * @brief Pop (mr) most recent from buffer (filo)
+ *
+ * @note Buffer state will be altered
+ *
+ * @warning Consider this opertaion as atomic!
+ *
+ * @details Read and remove the most recently added from the buffer.
+ * Using this results in a stack type of buffer.
+ *
+ * @param[in] c Pointer to @p xifo32_t used for configuration.
+ *
+ * @return Contents of element or 0 if failed (element can hold 0)
+ */
+uint32_t xifo32_pop_mr(xifo32_t *c){
+ register uint32_t temp;
+ /* Verify there is valid data read */
+ if(c->count == 0){
+ return 0; /* Nothing to read there */
+ }
+ /* Read */
+ temp = *c->read;
+ /* Empty */
+ *c->read = 0;
+ /* Most recent element read, return write pointer */
+ c->write = c->read;
+ /* Decrement read pointer */
+ c->read--;
+ /* Validate pointer */
+ if( c->read < c->startpool ){
+ /* Exceeded pool boundaries */
+ c->read = c->endpool;
+ }
+ /* Reduce count */
+ c->count--;
+ if(c->count < c->size)
+ c->full = 0;
+ return temp;
+}
+
+/**
+ * @brief Pop (lr) least recent from buffer (fifo)
+ *
+ * @note Buffer state will be altered
+ *
+ * @warning Consider this opertaion as atomic!
+ *
+ * @details Read and remove the least recently added from the buffer.
+ * Using this results in a fifo type of buffer.
+ *
+ * @param[in] c Pointer to @p xifo32_t used for configuration.
+ *
+ * @return Contents of element or 0 if failed (element can hold 0)
+ */
+uint32_t xifo32_pop_lr(xifo32_t *c){
+ register uint32_t *ptemp;
+ register uint32_t temp;
+ /* Verify there is valid data read */
+ if(c->count == 0){
+ return 0; /* Nothing to read there */
+ }
+ /* Derive least recent buffer element */
+ ptemp = (c->read+1) - c->count;
+ /* Validate pointer */
+ if(ptemp < c->startpool){
+ /* Exceeded pool boundaries */
+ /* Calculate overshoot (startpool - indexptr) and subtract from end */
+ /* Since one element of overshoot results in end - 1 you would miss the last value */
+ ptemp = (c->endpool+1) - (c->startpool - ptemp);
+ }
+ /* Read oldest buffer element */
+ /* Read to temp register */
+ temp = *ptemp;
+ /* Empty buffer element */
+ *ptemp = 0;
+ /* Reduce count */
+ c->count--;
+ /* Check full flag */
+ if(c->count < c->size)
+ c->full = 0;
+ return temp;
+}
+
+/**
+ * @brief Write to buffer
+ *
+ * @note Readpointer is automatically set to the last added element.
+ *
+ * @warning Consider this opertaion as atomic!
+ *
+ * @details Adds a value to the buffer.
+ * Automatically overwrites oldest elements when full.
+ *
+ * @param[in] c Pointer to @p xifo32_t used for configuration.
+ * @param[in] data Data to add to buffer
+ *
+ * @return Number of free buffer elements
+ */
+uint32_t xifo32_write(xifo32_t *c, uint32_t data){
+ /* Write data */
+ *c->write = data;
+ /* Update read pointer to most recent element */
+ c->read = c->write;
+ /* Write pointer increment */
+ c->write++;
+ /* Validate pointer */
+ if( c->write > c->endpool){
+ /* We exceeded pool boundaries */
+ c->write = c->startpool;
+ }
+ /* Update count */
+ c->count++;
+ /* Verify full */
+ if( c->count >= c->size ){
+ c->full = 1;
+ c->count = c->size;
+ }
+ /* return free elements count */
+ return c->size - c->count;
+}
+
+/**
+ * @brief Get buffer size
+ *
+ * @param[in] c Pointer to @p xifo32_t used for configuration.
+ *
+ * @return Size of memory pool in elements
+ */
+uint32_t xifo32_get_size(xifo32_t *c){
+ return c->size;
+}
+
+/**
+ * @brief Get number of used elements
+ *
+ * @param[in] c Pointer to @p xifo32_t used for configuration.
+ *
+ * @return Number of used buffer elements
+ */
+uint32_t xifo32_get_used(xifo32_t *c){
+ return c->count;
+}
+
+/**
+* @brief Get number of free elements
+*
+* @param[in] c Pointer to @p xifo32_t used for configuration.
+*
+* @return Number of free elements
+*/
+uint32_t xifo32_get_free(xifo32_t *c){
+ return c->size - c->count;
+}
+
+/**
+ * @brief Get full flag
+ *
+ * @param[in] c Pointer to @p xifo32_t used for configuration.
+ *
+ * @return 1 if full
+ */
+uint32_t xifo32_get_full(xifo32_t *c){
+ return c->full;
+}
+
+/** @} */
+#endif
+
+#if xIFO_USE_16BIT == TRUE
+/**
+ * @brief Initialize buffer object structure.
+ *
+ * @note Does not clear memory pool.
+ *
+ * @param[in] c Pointer to @p xifo16_t object used for configuration.
+ * @param[in] s Number of elements buffer can hold (size).
+ * @param[in] sp Start of pre-allocated memory pool.
+ */
+void xifo16_init(xifo16_t *c, uint32_t s, uint16_t *sp){
+ c->startpool = sp;
+ c->size = s;
+ c->endpool = &sp[--s];
+ c->full = 0;
+ c->count = 0;
+ c->read = sp;
+ c->write = sp;
+}
+
+/**
+ * @brief Clear buffer memory pool
+ *
+ * @note Must be used on initialised buffer object.
+ *
+ * @param[in] c Pointer to @p xifo16_t object.
+ */
+void xifo16_clear(xifo16_t *c){
+ register uint16_t *ptemp = c->startpool;
+ register uint32_t i = c->size;
+ while(i--){
+ *ptemp++ = 0;
+ }
+}
+
+/**
+ * @brief Read from buffer (lr) Least Recent oriented (fifo)
+ *
+ * @note Buffer state will be preserved
+ *
+ * @warning Consider this opertaion as atomic!
+ *
+ * @details Read n elements from the oldest element to the most recent.
+ * As for index[0] the least recently added element is returned.
+ * And for index[count] the most recent element is returned.
+ * This makes it possible to peek in fifo.
+ *
+ * @param[in] c Pointer to @p xifo16_t used for configuration.
+ * @param[in] index Index relative from least recent
+ *
+ * @return Contents of element or 0 if failed (element can hold 0)
+ */
+uint16_t xifo16_read_lr(xifo16_t *c, uint32_t index){
+ register uint16_t *ptemp;
+ /* Verify there is valid data to read */
+ if(index >= c->count){
+ return 0; /* Nothing to read there */
+ }
+ /* Calculate index of oldest element */
+ index = (c->count-1) - index;
+ /* Set pointer */
+ ptemp = (c->read) - index;
+ if(ptemp < c->startpool){
+ /* Exceeded pool boundaries */
+ /* Calculate overshoot (startpool - indexptr) and subtract from end */
+ /* Since one element of overshoot results in end - 1 you would miss the last value */
+ ptemp = (c->endpool+1) - (c->startpool - ptemp);
+ }
+ /* Read most recent */
+ return *ptemp;
+}
+
+/**
+ * @brief Read from buffer (mr) Most Recent oriented (filo)
+ *
+ * @note Buffer state will be preserved
+ *
+ * @warning Consider this opertaion as atomic!
+ *
+ * @details Read n elements back in time.
+ * As for index[0] the most recently added element is returned.
+ * And for index[count] the oldest element is returned.
+ * This makes it possible to keep history. For DSP application.
+ *
+ * @param[in] c Pointer to @p xifo16_t used for configuration.
+ * @param[in] index Index relative from most recent
+ *
+ * @return Contents of element or 0 if failed (element can hold 0)
+ */
+uint16_t xifo16_read_mr(xifo16_t *c, uint32_t index){
+ register uint16_t *ptemp;
+ /* Verify there is valid data to read */
+ if(index >= c->count){
+ return 0; /* Nothing to read there */
+ }
+ /* Set pointer */
+ ptemp = (c->read) - index;
+ /* Validate pointer */
+ if(ptemp < c->startpool){
+ /* Exceeded pool boundaries */
+ /* Calculate overshoot (startpool - indexptr) and subtract from end */
+ /* Since one element of overshoot results in end - 1 you would miss the last value */
+ ptemp = (c->endpool+1) - (c->startpool - ptemp);
+ }
+ /* Read most recent */
+ return *ptemp;
+}
+
+/**
+ * @brief Pop (mr) most recent from buffer (filo)
+ *
+ * @note Buffer state will be altered
+ *
+ * @warning Consider this opertaion as atomic!
+ *
+ * @details Read and remove the most recently added from the buffer.
+ * Using this results in a stack type of buffer.
+ *
+ * @param[in] c Pointer to @p xifo16_t used for configuration.
+ *
+ * @return Contents of element or 0 if failed (element can hold 0)
+ */
+uint16_t xifo16_pop_mr(xifo16_t *c){
+ register uint16_t temp;
+ /* Verify there is valid data read */
+ if(c->count == 0){
+ return 0; /* Nothing to read there */
+ }
+ /* Read */
+ temp = *c->read;
+ /* Empty */
+ *c->read = 0;
+ /* Most recent element read, return write pointer */
+ c->write = c->read;
+ /* Decrement read pointer */
+ c->read--;
+ /* Validate pointer */
+ if( c->read < c->startpool ){
+ /* Exceeded pool boundaries */
+ c->read = c->endpool;
+ }
+ /* Reduce count */
+ c->count--;
+ if(c->count < c->size)
+ c->full = 0;
+ return temp;
+}
+
+/**
+ * @brief Pop (lr) least recent from buffer (fifo)
+ *
+ * @note Buffer state will be altered
+ *
+ * @warning Consider this opertaion as atomic!
+ *
+ * @details Read and remove the least recently added from the buffer.
+ * Using this results in a fifo type of buffer.
+ *
+ * @param[in] c Pointer to @p xifo16_t used for configuration.
+ *
+ * @return Contents of element or 0 if failed (element can hold 0)
+ */
+uint16_t xifo16_pop_lr(xifo16_t *c){
+ register uint16_t *ptemp;
+ register uint16_t temp;
+ /* Verify there is valid data read */
+ if(c->count == 0){
+ return 0; /* Nothing to read there */
+ }
+ /* Derive least recent buffer element */
+ ptemp = (c->read+1) - c->count;
+ /* Validate pointer */
+ if(ptemp < c->startpool){
+ /* Exceeded pool boundaries */
+ /* Calculate overshoot (startpool - indexptr) and subtract from end */
+ /* Since one element of overshoot results in end - 1 you would miss the last value */
+ ptemp = (c->endpool+1) - (c->startpool - ptemp);
+ }
+ /* Read oldest buffer element */
+ /* Read to temp register */
+ temp = *ptemp;
+ /* Empty buffer element */
+ *ptemp = 0;
+ /* Reduce count */
+ c->count--;
+ /* Check full flag */
+ if(c->count < c->size)
+ c->full = 0;
+ return temp;
+}
+
+/**
+ * @brief Write to buffer
+ *
+ * @note Readpointer is automatically set to the last added element.
+ *
+ * @warning Consider this opertaion as atomic!
+ *
+ * @details Adds a value to the buffer.
+ * Automatically overwrites oldest elements when full.
+ *
+ * @param[in] c Pointer to @p xifo16_t used for configuration.
+ * @param[in] data Data to add to buffer
+ *
+ * @return Number of free buffer elements
+ */
+uint32_t xifo16_write(xifo16_t *c, uint16_t data){
+ /* Write data */
+ *c->write = data;
+ /* Update read pointer to most recent element */
+ c->read = c->write;
+ /* Write pointer increment */
+ c->write++;
+ /* Validate pointer */
+ if( c->write > c->endpool){
+ /* We exceeded pool boundaries */
+ c->write = c->startpool;
+ }
+ /* Update count */
+ c->count++;
+ /* Verify full */
+ if( c->count >= c->size ){
+ c->full = 1;
+ c->count = c->size;
+ }
+ /* return free elements count */
+ return c->size - c->count;
+}
+
+/**
+ * @brief Get buffer size
+ *
+ * @param[in] c Pointer to @p xifo16_t used for configuration.
+ *
+ * @return Size of memory pool in elements
+ */
+uint32_t xifo16_get_size(xifo16_t *c){
+ return c->size;
+}
+
+/**
+ * @brief Get number of used elements
+ *
+ * @param[in] c Pointer to @p xifo16_t used for configuration.
+ *
+ * @return Number of used buffer elements
+ */
+uint32_t xifo16_get_used(xifo16_t *c){
+ return c->count;
+}
+
+/**
+* @brief Get number of free elements
+*
+* @param[in] c Pointer to @p xifo16_t used for configuration.
+*
+* @return Number of free elements
+*/
+uint32_t xifo16_get_free(xifo16_t *c){
+ return c->size - c->count;
+}
+
+/**
+ * @brief Get full flag
+ *
+ * @param[in] c Pointer to @p xifo16_t used for configuration.
+ *
+ * @return 1 if full
+ */
+uint32_t xifo16_get_full(xifo16_t *c){
+ return c->full;
+}
+
+/** @} */
+
+#endif
+
+#if xIFO_USE_8BIT == TRUE
+/**
+ * @brief Initialize buffer object structure.
+ *
+ * @note Does not clear memory pool.
+ *
+ * @param[in] c Pointer to @p xifo8_t object used for configuration.
+ * @param[in] s Number of elements buffer can hold (size).
+ * @param[in] sp Start of pre-allocated memory pool.
+ */
+void xifo8_init(xifo8_t *c, uint32_t s, uint8_t *sp){
+ c->startpool = sp;
+ c->size = s;
+ c->endpool = &sp[--s];
+ c->full = 0;
+ c->count = 0;
+ c->read = sp;
+ c->write = sp;
+}
+
+/**
+ * @brief Clear buffer memory pool
+ *
+ * @note Must be used on initialised buffer object.
+ *
+ * @param[in] c Pointer to @p xifo8_t object.
+ */
+void xifo8_clear(xifo8_t *c){
+ register uint8_t *ptemp = c->startpool;
+ register uint32_t i = c->size;
+ while(i--){
+ *ptemp++ = 0;
+ }
+}
+
+/**
+ * @brief Read from buffer (lr) Least Recent oriented (fifo)
+ *
+ * @note Buffer state will be preserved
+ *
+ * @warning Consider this opertaion as atomic!
+ *
+ * @details Read n elements from the oldest element to the most recent.
+ * As for index[0] the least recently added element is returned.
+ * And for index[count] the most recent element is returned.
+ * This makes it possible to peek in fifo.
+ *
+ * @param[in] c Pointer to @p xifo8_t used for configuration.
+ * @param[in] index Index relative from least recent
+ *
+ * @return Contents of element or 0 if failed (element can hold 0)
+ */
+uint8_t xifo8_read_lr(xifo8_t *c, uint32_t index){
+ register uint8_t *ptemp;
+ /* Verify there is valid data to read */
+ if(index >= c->count){
+ return 0; /* Nothing to read there */
+ }
+ /* Calculate index of oldest element */
+ index = (c->count-1) - index;
+ /* Set pointer */
+ ptemp = (c->read) - index;
+ if(ptemp < c->startpool){
+ /* Exceeded pool boundaries */
+ /* Calculate overshoot (startpool - indexptr) and subtract from end */
+ /* Since one element of overshoot results in end - 1 you would miss the last value */
+ ptemp = (c->endpool+1) - (c->startpool - ptemp);
+ }
+ /* Read most recent */
+ return *ptemp;
+}
+
+/**
+ * @brief Read from buffer (mr) Most Recent oriented (filo)
+ *
+ * @note Buffer state will be preserved
+ *
+ * @warning Consider this opertaion as atomic!
+ *
+ * @details Read n elements back in time.
+ * As for index[0] the most recently added element is returned.
+ * And for index[count] the oldest element is returned.
+ * This makes it possible to keep history. For DSP application.
+ *
+ * @param[in] c Pointer to @p xifo8_t used for configuration.
+ * @param[in] index Index relative from most recent
+ *
+ * @return Contents of element or 0 if failed (element can hold 0)
+ */
+uint8_t xifo8_read_mr(xifo8_t *c, uint32_t index){
+ register uint8_t *ptemp;
+ /* Verify there is valid data to read */
+ if(index >= c->count){
+ return 0; /* Nothing to read there */
+ }
+ /* Set pointer */
+ ptemp = (c->read) - index;
+ /* Validate pointer */
+ if(ptemp < c->startpool){
+ /* Exceeded pool boundaries */
+ /* Calculate overshoot (startpool - indexptr) and subtract from end */
+ /* Since one element of overshoot results in end - 1 you would miss the last value */
+ ptemp = (c->endpool+1) - (c->startpool - ptemp);
+ }
+ /* Read most recent */
+ return *ptemp;
+}
+
+/**
+ * @brief Pop (mr) most recent from buffer (filo)
+ *
+ * @note Buffer state will be altered
+ *
+ * @warning Consider this opertaion as atomic!
+ *
+ * @details Read and remove the most recently added from the buffer.
+ * Using this results in a stack type of buffer.
+ *
+ * @param[in] c Pointer to @p xifo8_t used for configuration.
+ *
+ * @return Contents of element or 0 if failed (element can hold 0)
+ */
+uint8_t xifo8_pop_mr(xifo8_t *c){
+ register uint8_t temp;
+ /* Verify there is valid data read */
+ if(c->count == 0){
+ return 0; /* Nothing to read there */
+ }
+ /* Read */
+ temp = *c->read;
+ /* Empty */
+ *c->read = 0;
+ /* Most recent element read, return write pointer */
+ c->write = c->read;
+ /* Decrement read pointer */
+ c->read--;
+ /* Validate pointer */
+ if( c->read < c->startpool ){
+ /* Exceeded pool boundaries */
+ c->read = c->endpool;
+ }
+ /* Reduce count */
+ c->count--;
+ if(c->count < c->size)
+ c->full = 0;
+ return temp;
+}
+
+/**
+ * @brief Pop (lr) least recent from buffer (fifo)
+ *
+ * @note Buffer state will be altered
+ *
+ * @warning Consider this opertaion as atomic!
+ *
+ * @details Read and remove the least recently added from the buffer.
+ * Using this results in a fifo type of buffer.
+ *
+ * @param[in] c Pointer to @p xifo8_t used for configuration.
+ *
+ * @return Contents of element or 0 if failed (element can hold 0)
+ */
+uint8_t xifo8_pop_lr(xifo8_t *c){
+ register uint8_t *ptemp;
+ register uint8_t temp;
+ /* Verify there is valid data read */
+ if(c->count == 0){
+ return 0; /* Nothing to read there */
+ }
+ /* Derive least recent buffer element */
+ ptemp = (c->read+1) - c->count;
+ /* Validate pointer */
+ if(ptemp < c->startpool){
+ /* Exceeded pool boundaries */
+ /* Calculate overshoot (startpool - indexptr) and subtract from end */
+ /* Since one element of overshoot results in end - 1 you would miss the last value */
+ ptemp = (c->endpool+1) - (c->startpool - ptemp);
+ }
+ /* Read oldest buffer element */
+ /* Read to temp register */
+ temp = *ptemp;
+ /* Empty buffer element */
+ *ptemp = 0;
+ /* Reduce count */
+ c->count--;
+ /* Check full flag */
+ if(c->count < c->size)
+ c->full = 0;
+ return temp;
+}
+
+/**
+ * @brief Write to buffer
+ *
+ * @note Readpointer is automatically set to the last added element.
+ *
+ * @warning Consider this opertaion as atomic!
+ *
+ * @details Adds a value to the buffer.
+ * Automatically overwrites oldest elements when full.
+ *
+ * @param[in] c Pointer to @p xifo8_t used for configuration.
+ * @param[in] data Data to add to buffer
+ *
+ * @return Number of free buffer elements
+ */
+uint32_t xifo8_write(xifo8_t *c, uint8_t data){
+ /* Write data */
+ *c->write = data;
+ /* Update read pointer to most recent element */
+ c->read = c->write;
+ /* Write pointer increment */
+ c->write++;
+ /* Validate pointer */
+ if( c->write > c->endpool){
+ /* We exceeded pool boundaries */
+ c->write = c->startpool;
+ }
+ /* Update count */
+ c->count++;
+ /* Verify full */
+ if( c->count >= c->size ){
+ c->full = 1;
+ c->count = c->size;
+ }
+ /* return free elements count */
+ return c->size - c->count;
+}
+
+/**
+ * @brief Get buffer size
+ *
+ * @param[in] c Pointer to @p xifo8_t used for configuration.
+ *
+ * @return Size of memory pool in elements
+ */
+uint32_t xifo8_get_size(xifo8_t *c){
+ return c->size;
+}
+
+/**
+ * @brief Get number of used elements
+ *
+ * @param[in] c Pointer to @p xifo8_t used for configuration.
+ *
+ * @return Number of used buffer elements
+ */
+uint32_t xifo8_get_used(xifo8_t *c){
+ return c->count;
+}
+
+/**
+* @brief Get number of free elements
+*
+* @param[in] c Pointer to @p xifo8_t used for configuration.
+*
+* @return Number of free elements
+*/
+uint32_t xifo8_get_free(xifo8_t *c){
+ return c->size - c->count;
+}
+
+/**
+ * @brief Get full flag
+ *
+ * @param[in] c Pointer to @p xifo8_t used for configuration.
+ *
+ * @return 1 if full
+ */
+uint32_t xifo8_get_full(xifo8_t *c){
+ return c->full;
+}
+
+/** @} */
+#endif
+
+/** @} */
--- a/xIFO.h Mon Oct 28 19:20:00 2013 +0000
+++ b/xIFO.h Fri Apr 04 21:36:55 2014 +0000
@@ -1,92 +1,545 @@
-
- /**
+/**
* @file xifo.h
- * @brief xifo circular buffer
- * @details xifo supplies object oriented circular buffer with 32 bit size elements. \n
- * To use either as FIFO (First In First Out) or as FILO (First In Last Out)
+ * @brief xifo circular buffer for all elements
+ * @details xifo supplies object oriented circular buffer with x bit size elements. \n
+ * To use either as FIFO (First In First Out) or as FILO (First In Last Out)
+ * Below are defines to disable or enable any xIFO type you like.
*
- * @author Jeroen Lodder
- * @date April 2013
- * @version 2
+ * @author Jeroen Lodder
+ * @date March 2014
+ * @version 3
+ *
+ * Copyright (c) 2014 Jeroen Lodder
+ *
+ * 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.
*
* @{
*/
-
- /**
- * Code has been tested on Cortex M0 (LPC1114)
- * Performance table, number of core clocks
- * Measured with a timer before and after
- * r1 = timer->TC
- * test_function
- * r2 = timer->TC
- *
- * Function Speed Worst Case
- *
- * write 69 71
- * read_mr 59 59
- * read_lr 63 70
- * pop_mr 76 78
- * pop_lr 45 45
- *
- */
-
#ifndef _xifo_H_
#define _xifo_H_
-
+
#include <inttypes.h>
-#if defined(__arm__) || defined(__DOXYGEN__)
-#pragma anon_unions /**< Allow unnamed unions */
+#if !defined(TRUE) || defined(__DOXYGEN__)
+#define TRUE (1)
+#endif
+#if !defined(FALSE) || defined(__DOXYGEN__)
+#define FALSE !(TRUE)
+#endif
+
+#ifdef __cplusplus
+#if !defined(xIFO_USE_CPP) || defined(__DOXYGEN__)
+#define xIFO_USE_CPP TRUE
+#endif
+#endif
+
+#if !defined(xIFO_USE_64BIT) || defined(__DOXYGEN__)
+#define xIFO_USE_64BIT TRUE
+#endif
+
+#if !defined(xIFO_USE_32BIT) || defined(__DOXYGEN__)
+#define xIFO_USE_32BIT TRUE
+#endif
+
+#if !defined(xIFO_USE_16BIT) || defined(__DOXYGEN__)
+#define xIFO_USE_16BIT TRUE
+#endif
+
+#if !defined(xIFO_USE_8BIT) || defined(__DOXYGEN__)
+#define xIFO_USE_8BIT TRUE
#endif
+
+#if xIFO_USE_CPP == TRUE
+/**
+ * @brief Circular Buffer object.
+ * @details This class holds the object of a circular buffer
+ */
+template <class xifo_dtype>
+class Xifo
+{
+public:
+ /**
+ * @brief Initialise xifo.
+ * @note Does not clear memory pool.
+ * @param[in] Number of elements buffer can hold (size).
+ */
+ Xifo(uint32_t size)
+ {
+ startpool = new xifo_dtype[size];
+ endpool = &startpool[size-1];
+ isize = size;
+ ifull = 0;
+ icount = 0;
+ read = startpool;
+ pwrite = startpool;
+ }
+
+ /**
+ * @brief Initialise xifo.
+ * @note Does not clear memory pool.
+ * @param[in] Number of elements buffer can hold (size).
+ * @param[in] Start of pre-allocated memory pool.
+ */
+ Xifo(uint32_t size, xifo_dtype *sp)
+ {
+ startpool = sp;
+ endpool = &sp[size-1];
+ isize = size;
+ ifull = 0;
+ icount = 0;
+ read = sp;
+ pwrite = sp;
+ }
+
+ /**
+ * @brief Deinitialise (and deallocate) buffer xifo.
+ * @note Does not clear memory pool.
+ */
+ ~Xifo(void)
+ {
+ if(dynamic){
+ delete startpool;
+ }
+ }
+
+ /**
+ * @brief Clear buffer memory pool
+ * @note Must be used on initialised buffer object.
+ * @param[in] c Pointer to @p xifo_SIZETYPE_t object.
+ */
+ void clear(void)
+ {
+ register xifo_dtype *ptemp = startpool;
+ while(ptemp <= endpool){
+ *ptemp++ = 0;
+ }
+ }
+
+ /**
+ * @brief Reset buffer
+ * @note Must be used on initialised buffer object.
+ * @param[in] c Pointer to @p xifo_SIZETYPE_t object.
+ */
+ void reset(void)
+ {
+ register xifo_dtype *ptemp = startpool;
+ while(ptemp <= endpool){
+ *ptemp++ = 0;
+ }
+ ifull = 0;
+ icount = 0;
+ read = startpool;
+ pwrite = startpool;
+ }
+
+ /**
+ * @brief Write to buffer
+ *
+ * @note Readpointer is automatically set to the last added element.
+ *
+ * @warning Consider this opertaion as atomic!
+ *
+ * @details Adds a value to the buffer.
+ * Automatically overwrites oldest elements when full.
+ *
+ * @param[in] c Pointer to @p xifo_SIZETYPE_t used for configuration.
+ * @param[in] data Data to add to buffer
+ *
+ * @return Number of free buffer elements
+ */
+ uint32_t write(xifo_dtype data)
+ {
+ /* Write data */
+ *pwrite = data;
+ /* Update read pointer to most recent element */
+ read = pwrite;
+ /* Write pointer increment */
+ pwrite += 1;
+ /* Validate pointer */
+ if( pwrite > endpool){
+ /* Exceeded pool boundaries */
+ pwrite = startpool;
+ }
+ /* Update count */
+ icount++;
+ /* Verify full */
+ if( icount >= isize ){
+ ifull = 1;
+ icount = isize;
+ }
+ /* return free elements count */
+ return isize - icount;
+ }
+
+ /**
+ * @brief Read from buffer (lr) Least Recent oriented (fifo)
+ *
+ * @note Buffer state will be preserved
+ *
+ * @warning Consider this opertaion as atomic!
+ *
+ * @details Read n elements from the oldest element to the most recent.
+ * As for index[0] the least recently added element is returned.
+ * And for index[count] the most recent element is returned.
+ * This makes it possible to peek in fifo.
+ *
+ * @param[in] c Pointer to @p xifo_SIZETYPE_t used for configuration.
+ * @param[in] index Index relative from least recent
+ *
+ * @return Contents of element or 0 if failed (element can hold 0)
+ */
+ xifo_dtype read_lr(uint32_t index)
+ {
+ register xifo_dtype *ptemp;
+ /* Verify there is valid data to read */
+ if(index+1 > icount){
+ return 0;
+ }
+ /* Calculate index of oldest element */
+ index = (icount-1) - index;
+ /* Set pointer */
+ ptemp = (read) - index;
+ if(ptemp < startpool){
+ /* Exceeded pool boundaries */
+ /* Calculate overshoot (startpool - indexptr) and subtract from end */
+ /* Since one element of overshoot results in end - 1 you would miss the last value */
+ ptemp = (endpool+1) - (startpool - ptemp);
+ }
+ /* Read most recent */
+ return *ptemp;
+ }
+
+ /**
+ * @brief Pop (lr) least recent from buffer (fifo)
+ *
+ * @note Buffer state will be altered
+ *
+ * @warning Consider this opertaion as atomic!
+ *
+ * @details Read and remove the least recently added from the buffer.
+ * Using this results in a fifo type of buffer.
+ *
+ * @param[in] c Pointer to @p xifo_SIZETYPE_t used for configuration.
+ *
+ * @return Contents of element or 0 if failed (element can hold 0)
+ */
+ xifo_dtype pop_lr()
+ {
+ register xifo_dtype *ptemp;
+ xifo_dtype temp;
+ /* Verify there is valid data read */
+ if(icount == 0){
+ return 0;
+ }
+ /* Derive least recent buffer element */
+ ptemp = read+1 - icount;
+ /* Validate pointer */
+ if(ptemp < startpool){
+ /* Exceeded pool boundaries */
+ /* Calculate overshoot (startpool - indexptr) and subtract from end */
+ /* Since one element of overshoot results in end - 1 you would miss the last value */
+ ptemp = (endpool+1) - (startpool - ptemp);
+ }
+ /* Read oldest buffer element */
+ /* Read to temp register */
+ temp = *ptemp;
+ /* Empty buffer element */
+ *ptemp = 0;
+ /* Reduce count */
+ icount--;
+ /* Check full flag */
+ if(icount < isize)
+ ifull = 0;
+ return temp;
+ }
+
+ /**
+ * @brief Read from buffer (mr) Most Recent oriented (filo)
+ *
+ * @note Buffer state will be preserved
+ *
+ * @warning Consider this opertaion as atomic!
+ *
+ * @details Read n elements back in time.
+ * As for index[0] the most recently added element is returned.
+ * And for index[count] the oldest element is returned.
+ * This makes it possible to keep history. For DSP application.
+ *
+ * @param[in] c Pointer to @p xifo_SIZETYPE_t used for configuration.
+ * @param[in] index Index relative from most recent
+ *
+ * @return Contents of element or 0 if failed (element can hold 0)
+ */
+ xifo_dtype read_mr(uint32_t index)
+ {
+ register xifo_dtype *ptemp;
+ /* Verify there is valid data to read */
+ if(index+1 > icount){
+ return 0;
+ }
+ /* Set pointer */
+ ptemp = read - index;
+ /* Validate pointer */
+ if(ptemp < startpool){
+ /* Exceeded pool boundaries */
+ /* Calculate overshoot (startpool - indexptr) and subtract from end */
+ /* Since one element of overshoot results in end - 1 you would miss the last value */
+ ptemp = (endpool+1) - (startpool - ptemp);
+ }
+ /* Read most recent */
+ return *ptemp;
+ }
+
+ /**
+ * @brief Pop (mr) most recent from buffer (filo)
+ *
+ * @note Buffer state will be altered
+ *
+ * @warning Consider this opertaion as atomic!
+ *
+ * @details Read and remove the most recently added from the buffer.
+ * Using this results in a stack type of buffer.
+ *
+ * @param[in] c Pointer to @p xifo_SIZETYPE_t used for configuration.
+ *
+ * @return Contents of element or 0 if failed (element can hold 0)
+ */
+ xifo_dtype pop_mr()
+ {
+ register xifo_dtype temp;
+ /* Verify there is valid data read */
+ if(icount == 0){
+ return 0;
+ }
+ /* Read */
+ temp = *read;
+ /* Empty */
+ *read = 0;
+ /* Most recent element read, return write pointer */
+ pwrite = read;
+ /* Decrement read pointer */
+ read--;
+ /* Validate pointer */
+ if( read < startpool ){
+ /* Exceeded pool boundaries */
+ read = endpool;
+ }
+ /* Reduce count */
+ icount--;
+ if(icount < isize)
+ ifull = 0;
+ return temp;
+ }
+
+ /* Extractors */
+ uint32_t size(){ return isize; } /**< @brief Get buffer size */
+ uint32_t used(){ return icount; } /**< @brief Get number of used elements */
+ uint32_t full(){ return ifull; } /**< @brief Get full flag */
+ uint32_t free(){ return isize-icount; } /**< @brief Get number of free elements */
+private:
+ bool dynamic;
+ xifo_dtype *startpool; /**< @brief First element in pool */
+ xifo_dtype *endpool; /**< @brief Last element in pool */
+ xifo_dtype *read; /**< @brief Read pointer */
+ xifo_dtype *pwrite; /**< @brief Write pointer */
+ /* Variables: */
+ uint32_t ifull; /**< @brief Flag indicating buffer is full */
+ uint32_t icount; /**< @brief Number of elements used */
+ uint32_t isize; /**< @brief Size of buffer */
+};
+#endif
+
+#if xIFO_USE_64BIT == TRUE
/**
* @brief Circular Buffer object.
* @details This struct holds the object of a circular buffer
*/
typedef struct {
-/* Pointers: */
- uint32_t *startpool; /**< @brief First element in pool */
- uint32_t *endpool; /**< @brief Last element in pool */
- uint32_t *read; /**< @brief Read pointer */
- uint32_t *write; /**< @brief Write pointer */
-/* Variables: */
- uint32_t full; /**< @brief Flag indicating buffer is full */
- uint32_t elementcount;/**< @brief Number of elements used */
- uint32_t size; /**< @brief Size of buffer */
-/* Locally used in functions to prevent stack use: */
- /**< @brief union to prevent lvalue typecasting */
- union {
- uint32_t temp; /**< @brief temp variable and padding for even sized block */
- uint32_t *ptemp; /**< @brief temp variable and padding for even sized block */
- };
-}xifo_t;
+ /* Pointers: */
+ uint64_t *startpool; /**< @brief First element in pool */
+ uint64_t *endpool; /**< @brief Last element in pool */
+ uint64_t *read; /**< @brief Read pointer */
+ uint64_t *write; /**< @brief Write pointer */
+ /* Variables: */
+ uint32_t full; /**< @brief Flag indicating buffer is full */
+ uint32_t count; /**< @brief Number of elements used */
+ uint32_t size; /**< @brief Size of buffer */
+}xifo64_t;
+
+/**< @brief Circular Buffer memory pool type. */
+typedef uint64_t xifo64_pool_t;
+#ifdef __cplusplus
+extern "C" {
+#endif
+/* xifo Common */
+void xifo64_init( xifo64_t *c, uint32_t size, uint64_t *startpool );
+void xifo64_clear( xifo64_t *c );
+uint32_t xifo64_write( xifo64_t *c, uint64_t data );
+/* FIFO use */
+uint64_t xifo64_read_lr( xifo64_t *c, uint32_t index );
+uint64_t xifo64_pop_lr( xifo64_t *c );
+/* LIFO use */
+uint64_t xifo64_read_mr( xifo64_t *c, uint32_t index );
+uint64_t xifo64_pop_mr( xifo64_t *c );
+/* Extractors */
+uint32_t xifo64_get_size( xifo64_t *c );
+uint32_t xifo64_get_used( xifo64_t *c );
+uint32_t xifo64_get_full( xifo64_t *c );
+uint32_t xifo64_get_free( xifo64_t *c );
+#ifdef __cplusplus
+}
+#endif
+#endif
+
+#if xIFO_USE_32BIT == TRUE
/**
- * @brief Circular Buffer memory pool type.
+ * @brief Circular Buffer object.
+ * @details This struct holds the object of a circular buffer
*/
-typedef unsigned int xifo_pool_t;
+typedef struct {
+ /* Pointers: */
+ uint32_t *startpool; /**< @brief First element in pool */
+ uint32_t *endpool; /**< @brief Last element in pool */
+ uint32_t *read; /**< @brief Read pointer */
+ uint32_t *write; /**< @brief Write pointer */
+ /* Variables: */
+ uint32_t full; /**< @brief Flag indicating buffer is full */
+ uint32_t count; /**< @brief Number of elements used */
+ uint32_t size; /**< @brief Size of buffer */
+}xifo32_t;
+
+/**< @brief Circular Buffer memory pool type. */
+typedef uint32_t xifo32_pool_t;
#ifdef __cplusplus
extern "C" {
#endif
/* xifo Common */
-void xifo_init(xifo_t *c, uint32_t size, uint32_t *startpool);
-void xifo_clear(xifo_t *c);
-uint32_t xifo_write(xifo_t *c, uint32_t data);
+void xifo32_init( xifo32_t *c, uint32_t size, uint32_t *startpool );
+void xifo32_clear( xifo32_t *c );
+uint32_t xifo32_write( xifo32_t *c, uint32_t data );
/* FIFO use */
-uint32_t xifo_read_lr(xifo_t *c, uint32_t index);
-uint32_t xifo_pop_lr(xifo_t *c);
+uint32_t xifo32_read_lr( xifo32_t *c, uint32_t index );
+uint32_t xifo32_pop_lr( xifo32_t *c );
/* LIFO use */
-uint32_t xifo_read_mr(xifo_t *c, uint32_t index);
-uint32_t xifo_pop_mr(xifo_t *c);
+uint32_t xifo32_read_mr( xifo32_t *c, uint32_t index );
+uint32_t xifo32_pop_mr( xifo32_t *c );
/* Extractors */
-uint32_t xifo_get_size(xifo_t *c);
-uint32_t xifo_get_used(xifo_t *c);
-uint32_t xifo_get_full(xifo_t *c);
-uint32_t xifo_get_free(xifo_t *c);
+uint32_t xifo32_get_size( xifo32_t *c );
+uint32_t xifo32_get_used( xifo32_t *c );
+uint32_t xifo32_get_full( xifo32_t *c );
+uint32_t xifo32_get_free( xifo32_t *c );
#ifdef __cplusplus
}
#endif
+#endif
+
+#if xIFO_USE_16BIT == TRUE
+/**
+ * @brief Circular Buffer object.
+ * @details This struct holds the object of a circular buffer
+ */
+typedef struct {
+ /* Pointers: */
+ uint16_t *startpool; /**< @brief First element in pool */
+ uint16_t *endpool; /**< @brief Last element in pool */
+ uint16_t *read; /**< @brief Read pointer */
+ uint16_t *write; /**< @brief Write pointer */
+ /* Variables: */
+ uint32_t full; /**< @brief Flag indicating buffer is full */
+ uint32_t count; /**< @brief Number of elements used */
+ uint32_t size; /**< @brief Size of buffer */
+}xifo16_t;
+
+/**
+ * @brief Circular Buffer memory pool type.
+ */
+typedef uint16_t xifo16_pool_t;
+
+#ifdef __cplusplus
+extern "C" {
+#endif
+/* xifo Common */
+void xifo16_init( xifo16_t *c, uint32_t size, uint16_t *startpool);
+void xifo16_clear( xifo16_t *c);
+uint32_t xifo16_write( xifo16_t *c, uint16_t data);
+/* FIFO use */
+uint16_t xifo16_read_lr( xifo16_t *c, uint32_t index);
+uint16_t xifo16_pop_lr( xifo16_t *c);
+/* LIFO use */
+uint16_t xifo16_read_mr( xifo16_t *c, uint32_t index);
+uint16_t xifo16_pop_mr( xifo16_t *c);
+/* Extractors */
+uint32_t xifo16_get_size( xifo16_t *c);
+uint32_t xifo16_get_used( xifo16_t *c);
+uint32_t xifo16_get_full( xifo16_t *c);
+uint32_t xifo16_get_free( xifo16_t *c);
+#ifdef __cplusplus
+}
+#endif
+#endif
+
+#if xIFO_USE_8BIT == TRUE
+/**
+ * @brief Circular Buffer object.
+ * @details This struct holds the object of a circular buffer
+ */
+typedef struct {
+ /* Pointers: */
+ uint8_t *startpool; /**< @brief First element in pool */
+ uint8_t *endpool; /**< @brief Last element in pool */
+ uint8_t *read; /**< @brief Read pointer */
+ uint8_t *write; /**< @brief Write pointer */
+ /* Variables: */
+ uint32_t full; /**< @brief Flag indicating buffer is full */
+ uint32_t count; /**< @brief Number of elements used */
+ uint32_t size; /**< @brief Size of buffer */
+}xifo8_t;
+
+/**< @brief Circular Buffer memory pool type. */
+typedef uint8_t xifo8_pool_t;
+
+#ifdef __cplusplus
+extern "C" {
+#endif
+/* xifo Common */
+void xifo8_init(xifo8_t *c, uint32_t size, uint8_t *startpool );
+void xifo8_clear( xifo8_t *c );
+uint32_t xifo8_write( xifo8_t *c, uint8_t data );
+/* FIFO use */
+uint8_t xifo8_read_lr( xifo8_t *c, uint32_t index );
+uint8_t xifo8_pop_lr( xifo8_t *c );
+/* LIFO use */
+uint8_t xifo8_read_mr( xifo8_t *c, uint32_t index );
+uint8_t xifo8_pop_mr( xifo8_t *c );
+/* Extractors */
+uint32_t xifo8_get_size( xifo8_t *c );
+uint32_t xifo8_get_used( xifo8_t *c );
+uint32_t xifo8_get_full( xifo8_t *c );
+uint32_t xifo8_get_free( xifo8_t *c );
+#ifdef __cplusplus
+}
+#endif
+#endif
+
#endif //_xifo_H_
/** @} */