spinn_common  development
Support code for SpiNNaker applications.
circular_buffer.h
Go to the documentation of this file.
1 /*
2  * Copyright (c) 2013 The University of Manchester
3  *
4  * Licensed under the Apache License, Version 2.0 (the "License");
5  * you may not use this file except in compliance with the License.
6  * You may obtain a copy of the License at
7  *
8  * https://www.apache.org/licenses/LICENSE-2.0
9  *
10  * Unless required by applicable law or agreed to in writing, software
11  * distributed under the License is distributed on an "AS IS" BASIS,
12  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13  * See the License for the specific language governing permissions and
14  * limitations under the License.
15  */
16 
19 #ifndef _CIRCULAR_BUFFER_H_
20 #define _CIRCULAR_BUFFER_H_
21 
22 #include <stdint.h>
23 #include <stdbool.h>
24 
26 typedef struct _circular_buffer {
28  uint32_t buffer_size;
30  uint32_t output;
32  uint32_t input;
35  uint32_t overflows;
37  uint32_t buffer[];
39 
42 
48 static inline uint32_t _circular_buffer_next(
49  circular_buffer buffer, uint32_t current) {
50  return (current + 1) & buffer->buffer_size;
51 }
52 
56 static inline bool _circular_buffer_not_empty(circular_buffer buffer) {
57  return buffer->input != buffer->output;
58 }
59 
64 static inline bool _circular_buffer_not_full(
65  circular_buffer buffer, uint32_t next) {
66  return next != buffer->output;
67 }
68 
74 
79 static inline bool circular_buffer_add(circular_buffer buffer, uint32_t item) {
80  uint32_t next = _circular_buffer_next(buffer, buffer->input);
81  bool success = _circular_buffer_not_full(buffer, next);
82 
83  if (success) {
84  buffer->buffer[buffer->input] = item;
85  buffer->input = next;
86  } else {
87  buffer->overflows++;
88  }
89 
90  return success;
91 }
92 
97 static inline bool circular_buffer_get_next(
98  circular_buffer buffer, uint32_t *item) {
99  bool success = _circular_buffer_not_empty(buffer);
100 
101  if (success) {
102  *item = buffer->buffer[buffer->output];
103  buffer->output = _circular_buffer_next(buffer, buffer->output);
104  }
105 
106  return success;
107 }
108 
114  circular_buffer buffer, uint32_t item) {
115  bool success = _circular_buffer_not_empty(buffer);
116  if (success) {
117  success = (buffer->buffer[buffer->output] == item);
118  if (success) {
119  buffer->output = _circular_buffer_next(buffer, buffer->output);
120  }
121  }
122  return success;
123 }
124 
128 static inline uint32_t circular_buffer_size(circular_buffer buffer) {
129  return buffer->input >= buffer->output
130  ? buffer->input - buffer->output
131  : (buffer->input + buffer->buffer_size + 1) - buffer->output;
132 }
133 
139  circular_buffer buffer) {
140  return buffer->overflows;
141 }
142 
145 static inline void circular_buffer_clear(circular_buffer buffer) {
146  buffer->input = 0;
147  buffer->output = 0;
148 }
149 
154 
155 //---------------------------------------
156 // Synaptic rewiring support functions
157 //---------------------------------------
162 static inline uint32_t circular_buffer_input(circular_buffer buffer) {
163  return buffer->input;
164 }
165 
170 static inline uint32_t circular_buffer_output(circular_buffer buffer) {
171  return buffer->output;
172 }
173 
177 static inline uint32_t circular_buffer_real_size(circular_buffer buffer) {
178  return buffer->buffer_size;
179 }
180 
186 static inline uint32_t circular_buffer_value_at_index(
187  circular_buffer buffer, uint32_t index) {
188  return buffer->buffer[index & buffer->buffer_size];
189 }
190 
191 #endif // _CIRCULAR_BUFFER_H_
static bool circular_buffer_get_next(circular_buffer buffer, uint32_t *item)
Get the next item from an existing buffer.
Definition: circular_buffer.h:97
uint32_t overflows
The number of times an insertion has failed due to the buffer being full.
Definition: circular_buffer.h:35
static uint32_t _circular_buffer_next(circular_buffer buffer, uint32_t current)
Get the index of the next position in the buffer from the given value.
Definition: circular_buffer.h:48
static uint32_t circular_buffer_value_at_index(circular_buffer buffer, uint32_t index)
Get the buffer contents at a particular index.
Definition: circular_buffer.h:186
static uint32_t circular_buffer_input(circular_buffer buffer)
Get the input index.
Definition: circular_buffer.h:162
_circular_buffer * circular_buffer
The public interface type is a pointer to the implementation.
Definition: circular_buffer.h:41
uint32_t buffer_size
The size of the buffer. One less than a power of two.
Definition: circular_buffer.h:28
static uint32_t circular_buffer_get_n_buffer_overflows(circular_buffer buffer)
Get the number of overflows that have occurred when adding to the buffer.
Definition: circular_buffer.h:138
uint32_t input
The index of the next position in the buffer to write to.
Definition: circular_buffer.h:32
static uint32_t circular_buffer_output(circular_buffer buffer)
Get the output index.
Definition: circular_buffer.h:170
static bool circular_buffer_add(circular_buffer buffer, uint32_t item)
Add an item to an existing buffer.
Definition: circular_buffer.h:79
static bool _circular_buffer_not_empty(circular_buffer buffer)
Get whether the buffer is not empty.
Definition: circular_buffer.h:56
uint32_t buffer[]
The buffer itself.
Definition: circular_buffer.h:37
circular_buffer circular_buffer_initialize(uint32_t size)
Create a new FIFO circular buffer of at least the given size. For efficiency, the buffer can be bigge...
Definition: circular_buffer.c:47
static void circular_buffer_clear(circular_buffer buffer)
Clear the circular buffer.
Definition: circular_buffer.h:145
void circular_buffer_print_buffer(circular_buffer buffer)
Print the contents of the buffer.
Definition: circular_buffer.c:68
uint32_t output
The index of the next position in the buffer to read from.
Definition: circular_buffer.h:30
static uint32_t circular_buffer_size(circular_buffer buffer)
Get the size of the buffer.
Definition: circular_buffer.h:128
static bool _circular_buffer_not_full(circular_buffer buffer, uint32_t next)
Get whether the buffer is able to accept more values.
Definition: circular_buffer.h:64
static uint32_t circular_buffer_real_size(circular_buffer buffer)
Get the buffer size.
Definition: circular_buffer.h:177
static bool circular_buffer_advance_if_next_equals(circular_buffer buffer, uint32_t item)
Advance the buffer if the next item is equal to the given value.
Definition: circular_buffer.h:113
Implementation of a circular buffer.
Definition: circular_buffer.h:26