- #include <stdint.h> 
- #include <stdio.h> 
- #include <stdlib.h> 
- #include <string.h> 
-   
- #include "ififo.h" 
-   
- // "infinite" fifo for uint32_t values 
- // NOT thread-safe! (i.e. can't put and get from different threads) 
-   
- static volatile uint32_t head; 
- static volatile uint32_t tail; 
- static volatile uint32_t mask; 
- static volatile uint32_t size; 
-   
- static volatile uint32_t * volatile fifo = NULL; 
-   
- #define IFIFO_INITIAL_SIZE (4096) // must be 2^n 
-   
-   
- void ififo_init(void) 
- { 
-         head = tail = 0; 
-   
-         mask = (size = IFIFO_INITIAL_SIZE) - 1; 
-   
-         fifo  = malloc(- size *sizeof(uint32_t));
-         if( !fifo ) 
-         { 
-                 fprintf(- stderr ,"%s: can't allocate initial memory chunk!\n",- __PRETTY_FUNCTION__ );
 
-         } 
- } 
-   
- void ififo_free(void) 
- { 
-         if(fifo) 
-         { 
-                 fifo=NULL; 
-         } 
- } 
-   
-   
-   
- void ififo_put(uint32_t value) 
- { 
-         if( ((head+1)&mask)==(tail&mask) ) 
-         { // fifo is to be overflown, add more memory to it 
- printf("ififo overflow: old head=%x, old tail=%x, old mask=%x, old size=%x, old ptr=%p\n",- head ,- tail ,- mask ,- size ,- fifo );
 
-                 uint32_t old_size = size; 
-                 uint32_t old_mask = mask; 
-   
-                 size <<= 1; 
-                 if( (size>>1)!=old_size ) 
-                 { 
-                         fprintf(- stderr ,"%s: fifo have to become too large!\n",- __PRETTY_FUNCTION__ );
 
-                 } 
-   
-                 mask = (size-1); 
- printf("ififo overflow: new mask=%x, new size=%x\n",- mask ,- size );
 
-                 fifo  = realloc((void *)- fifo ,- size *sizeof(uint32_t));
- printf("ififo overflow: new ptr=%p\n",- fifo );
 
-                 if( !fifo ) 
-                 { 
-                         fprintf(- stderr ,"%s: can't allocate more memory for fifo!\n",- __PRETTY_FUNCTION__ );
 
-                 } 
-   
-                 // realign and copy contents, if needed 
-                 if( (head&old_mask)<(tail&old_mask) ) 
-                 { 
-                         if( (head&old_mask)>0 ) 
-                         { 
-                                 memcpy( (void *)(- fifo +- old_size ), (void *)- fifo , (- head &- old_mask )*sizeof(uint32_t) );
 
-                         } 
-   
-                         head += old_size; 
-                         head &= mask; 
-                 } 
- printf("ififo overflow: new head=%x\n",- head );
 
-         } 
-   
-         fifo[head&mask] = value; 
-         head++; 
-         head &= mask; 
- } 
-   
- uint32_t ififo_get(void) 
- { 
-         if( (head&mask)!=(tail&mask) ) 
-         { 
-                 uint32_t value = fifo[tail&mask]; 
-                 tail++; 
-                 tail &= mask; 
-   
-                 return value; 
-         } 
-         else 
-         { 
-                 fprintf(- stderr ,"%s: attempted to get from empty ififo!\n",- __PRETTY_FUNCTION__ );
 
-         } 
- } 
-   
- size_t ififo_used(void) 
- { // return how many words are used in fifo (how many times it may supply 'get' without any 'put') 
-   
-         return mask & (head-tail); 
- } 
-   
-