root/trunk/libffado/src/libutil/ringbuffer.h

Revision 445, 7.5 kB (checked in by pieterpalmers, 14 years ago)

* name change from FreeBoB to FFADO
* replaced tabs by 4 spaces
* got rid of end-of-line spaces
* made all license and copyrights conform

library becomes LGPL, apps become GPL
explicitly state LGPL v2.1 and GPL v2 (don't like v3 draft)

copyrights are 2005-2007 Daniel & Pieter
except for the MotU stuff (C) Jonathan, Pieter

Line 
1 /*
2   Copied from the jackd sources
3   function names changed in order to avoid naming problems when using this in
4   a jackd backend.
5
6   Modifications for FFADO by Pieter Palmers
7
8     Copyright (C) 2000 Paul Davis
9     Copyright (C) 2003 Rohan Drape
10
11     This program is free software; you can redistribute it and/or modify
12     it under the terms of the GNU Lesser General Public License as published by
13     the Free Software Foundation; either version 2.1 of the License, or
14     (at your option) any later version.
15
16     This program is distributed in the hope that it will be useful,
17     but WITHOUT ANY WARRANTY; without even the implied warranty of
18     MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
19     GNU Lesser General Public License for more details.
20
21     You should have received a copy of the GNU Lesser General Public License
22     along with this program; if not, write to the Free Software
23     Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
24
25 */
26
27 #ifndef _FFADO_RINGBUFFER_H
28 #define _FFADO_RINGBUFFER_H
29
30 #ifdef __cplusplus
31 extern "C" {
32 #endif
33
34 #include <sys/types.h>
35
36 /** @file ringbuffer.h
37  *
38  *
39  * The key attribute of a ringbuffer is that it can be safely accessed
40  * by two threads simultaneously -- one reading from the buffer and
41  * the other writing to it -- without using any synchronization or
42  * mutual exclusion primitives.  For this to work correctly, there can
43  * only be a single reader and a single writer thread.  Their
44  * identities cannot be interchanged.
45  */
46
47 typedef struct
48 {
49   char  *buf;
50   size_t len;
51 }
52 ffado_ringbuffer_data_t ;
53
54 typedef struct
55 {
56   char         *buf;
57   volatile size_t write_ptr;
58   volatile size_t read_ptr;
59   size_t      size;
60   size_t      size_mask;
61   int          mlocked;
62 }
63 ffado_ringbuffer_t ;
64
65 /**
66  * Allocates a ringbuffer data structure of a specified size. The
67  * caller must arrange for a call to ffado_ringbuffer_free() to release
68  * the memory associated with the ringbuffer.
69  *
70  * @param sz the ringbuffer size in bytes.
71  *
72  * @return a pointer to a new ffado_ringbuffer_t, if successful; NULL
73  * otherwise.
74  */
75 ffado_ringbuffer_t *ffado_ringbuffer_create(size_t sz);
76
77 /**
78  * Frees the ringbuffer data structure allocated by an earlier call to
79  * ffado_ringbuffer_create().
80  *
81  * @param rb a pointer to the ringbuffer structure.
82  */
83 void ffado_ringbuffer_free(ffado_ringbuffer_t *rb);
84
85 /**
86  * Fill a data structure with a description of the current readable
87  * data held in the ringbuffer.  This description is returned in a two
88  * element array of ffado_ringbuffer_data_t.  Two elements are needed
89  * because the data to be read may be split across the end of the
90  * ringbuffer.
91  *
92  * The first element will always contain a valid @a len field, which
93  * may be zero or greater.  If the @a len field is non-zero, then data
94  * can be read in a contiguous fashion using the address given in the
95  * corresponding @a buf field.
96  *
97  * If the second element has a non-zero @a len field, then a second
98  * contiguous stretch of data can be read from the address given in
99  * its corresponding @a buf field.
100  *
101  * @param rb a pointer to the ringbuffer structure.
102  * @param vec a pointer to a 2 element array of ffado_ringbuffer_data_t.
103  *
104  */
105 void ffado_ringbuffer_get_read_vector(const ffado_ringbuffer_t *rb,
106                      ffado_ringbuffer_data_t *vec);
107
108 /**
109  * Fill a data structure with a description of the current writable
110  * space in the ringbuffer.  The description is returned in a two
111  * element array of ffado_ringbuffer_data_t.  Two elements are needed
112  * because the space available for writing may be split across the end
113  * of the ringbuffer.
114  *
115  * The first element will always contain a valid @a len field, which
116  * may be zero or greater.  If the @a len field is non-zero, then data
117  * can be written in a contiguous fashion using the address given in
118  * the corresponding @a buf field.
119  *
120  * If the second element has a non-zero @a len field, then a second
121  * contiguous stretch of data can be written to the address given in
122  * the corresponding @a buf field.
123  *
124  * @param rb a pointer to the ringbuffer structure.
125  * @param vec a pointer to a 2 element array of ffado_ringbuffer_data_t.
126  */
127 void ffado_ringbuffer_get_write_vector(const ffado_ringbuffer_t *rb,
128                       ffado_ringbuffer_data_t *vec);
129
130 /**
131  * Read data from the ringbuffer.
132  *
133  * @param rb a pointer to the ringbuffer structure.
134  * @param dest a pointer to a buffer where data read from the
135  * ringbuffer will go.
136  * @param cnt the number of bytes to read.
137  *
138  * @return the number of bytes read, which may range from 0 to cnt.
139  */
140 size_t ffado_ringbuffer_read(ffado_ringbuffer_t *rb, char *dest, size_t cnt);
141
142 /**
143  * Read data from the ringbuffer. Opposed to ffado_ringbuffer_read()
144  * this function does not move the read pointer. Thus it's
145  * a convenient way to inspect data in the ringbuffer in a
146  * continous fashion. The price is that the data is copied
147  * into a user provided buffer. For "raw" non-copy inspection
148  * of the data in the ringbuffer use ffado_ringbuffer_get_read_vector().
149  *
150  * @param rb a pointer to the ringbuffer structure.
151  * @param dest a pointer to a buffer where data read from the
152  * ringbuffer will go.
153  * @param cnt the number of bytes to read.
154  *
155  * @return the number of bytes read, which may range from 0 to cnt.
156  */
157 size_t ffado_ringbuffer_peek(ffado_ringbuffer_t *rb, char *dest, size_t cnt);
158
159 /**
160  * Advance the read pointer.
161  *
162  * After data have been read from the ringbuffer using the pointers
163  * returned by ffado_ringbuffer_get_read_vector(), use this function to
164  * advance the buffer pointers, making that space available for future
165  * write operations.
166  *
167  * @param rb a pointer to the ringbuffer structure.
168  * @param cnt the number of bytes read.
169  */
170 void ffado_ringbuffer_read_advance(ffado_ringbuffer_t *rb, size_t cnt);
171
172 /**
173  * Return the number of bytes available for reading.
174  *
175  * @param rb a pointer to the ringbuffer structure.
176  *
177  * @return the number of bytes available to read.
178  */
179 size_t ffado_ringbuffer_read_space(const ffado_ringbuffer_t *rb);
180
181 /**
182  * Lock a ringbuffer data block into memory.
183  *
184  * Uses the mlock() system call.  This is not a realtime operation.
185  *
186  * @param rb a pointer to the ringbuffer structure.
187  */
188 int ffado_ringbuffer_mlock(ffado_ringbuffer_t *rb);
189
190 /**
191  * Reset the read and write pointers, making an empty buffer.
192  *
193  * This is not thread safe.
194  *
195  * @param rb a pointer to the ringbuffer structure.
196  */
197 void ffado_ringbuffer_reset(ffado_ringbuffer_t *rb);
198
199 /**
200  * Write data into the ringbuffer.
201  *
202  * @param rb a pointer to the ringbuffer structure.
203  * @param src a pointer to the data to be written to the ringbuffer.
204  * @param cnt the number of bytes to write.
205  *
206  * @return the number of bytes write, which may range from 0 to cnt
207  */
208 size_t ffado_ringbuffer_write(ffado_ringbuffer_t *rb, const char *src,
209                  size_t cnt);
210
211 /**
212  * Advance the write pointer.
213  *
214  * After data have been written the ringbuffer using the pointers
215  * returned by ffado_ringbuffer_get_write_vector(), use this function
216  * to advance the buffer pointer, making the data available for future
217  * read operations.
218  *
219  * @param rb a pointer to the ringbuffer structure.
220  * @param cnt the number of bytes written.
221  */
222 void ffado_ringbuffer_write_advance(ffado_ringbuffer_t *rb, size_t cnt);
223
224 /**
225  * Return the number of bytes available for writing.
226  *
227  * @param rb a pointer to the ringbuffer structure.
228  *
229  * @return the amount of free space (in bytes) available for writing.
230  */
231 size_t ffado_ringbuffer_write_space(const ffado_ringbuffer_t *rb);
232
233
234 #ifdef __cplusplus
235 }
236 #endif
237
238 #endif // FFADO_RINGBUFFER
Note: See TracBrowser for help on using the browser.