ringbuffer.h (4090B)
1/** 2 * FreeRDP: A Remote Desktop Protocol Implementation 3 * 4 * Copyright 2014 Thincast Technologies GmbH 5 * Copyright 2014 Hardening <contact@hardening-consulting.com> 6 * 7 * Licensed under the Apache License, Version 2.0 (the "License"); 8 * you may not use this file except in compliance with the License. 9 * You may obtain a copy of the License at 10 * 11 * http://www.apache.org/licenses/LICENSE-2.0 12 * 13 * Unless required by applicable law or agreed to in writing, software 14 * distributed under the License is distributed on an "AS IS" BASIS, 15 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 16 * See the License for the specific language governing permissions and 17 * limitations under the License. 18 */ 19 20#ifndef FREERDP_UTILS_RINGBUFFER_H 21#define FREERDP_UTILS_RINGBUFFER_H 22 23#include <winpr/wtypes.h> 24#include <freerdp/api.h> 25 26/** @brief ring buffer meta data */ 27struct _RingBuffer 28{ 29 size_t initialSize; 30 size_t freeSize; 31 size_t size; 32 size_t readPtr; 33 size_t writePtr; 34 BYTE* buffer; 35}; 36typedef struct _RingBuffer RingBuffer; 37 38/** @brief a piece of data in the ring buffer, exactly like a glibc iovec */ 39struct _DataChunk 40{ 41 size_t size; 42 const BYTE* data; 43}; 44typedef struct _DataChunk DataChunk; 45 46#ifdef __cplusplus 47extern "C" 48{ 49#endif 50 51 /** initialise a ringbuffer 52 * @param initialSize the initial capacity of the ringBuffer 53 * @return if the initialisation was successful 54 */ 55 FREERDP_API BOOL ringbuffer_init(RingBuffer* rb, size_t initialSize); 56 57 /** destroys internal data used by this ringbuffer 58 * @param ringbuffer 59 */ 60 FREERDP_API void ringbuffer_destroy(RingBuffer* ringbuffer); 61 62 /** computes the space used in this ringbuffer 63 * @param ringbuffer 64 * @return the number of bytes stored in that ringbuffer 65 */ 66 FREERDP_API size_t ringbuffer_used(const RingBuffer* ringbuffer); 67 68 /** returns the capacity of the ring buffer 69 * @param ringbuffer 70 * @return the capacity of this ring buffer 71 */ 72 FREERDP_API size_t ringbuffer_capacity(const RingBuffer* ringbuffer); 73 74 /** writes some bytes in the ringbuffer, if the data doesn't fit, the ringbuffer 75 * is resized automatically 76 * 77 * @param rb the ringbuffer 78 * @param ptr a pointer on the data to add 79 * @param sz the size of the data to add 80 * @return if the operation was successful, it could fail in case of OOM during realloc() 81 */ 82 FREERDP_API BOOL ringbuffer_write(RingBuffer* rb, const BYTE* ptr, size_t sz); 83 84 /** ensures that we have sz bytes available at the write head, and return a pointer 85 * on the write head 86 * 87 * @param rb the ring buffer 88 * @param sz the size to ensure 89 * @return a pointer on the write head, or NULL in case of OOM 90 */ 91 FREERDP_API BYTE* ringbuffer_ensure_linear_write(RingBuffer* rb, size_t sz); 92 93 /** move ahead the write head in case some byte were written directly by using 94 * a pointer retrieved via ringbuffer_ensure_linear_write(). This function is 95 * used to commit the written bytes. The provided size should not exceed the 96 * size ensured by ringbuffer_ensure_linear_write() 97 * 98 * @param rb the ring buffer 99 * @param sz the number of bytes that have been written 100 * @return if the operation was successful, FALSE is sz is too big 101 */ 102 FREERDP_API BOOL ringbuffer_commit_written_bytes(RingBuffer* rb, size_t sz); 103 104 /** peeks the buffer chunks for sz bytes and returns how many chunks are filled. 105 * Note that the sum of the resulting chunks may be smaller than sz. 106 * 107 * @param rb the ringbuffer 108 * @param chunks an array of data chunks that will contain data / size of chunks 109 * @param sz the requested size 110 * @return the number of chunks used for reading sz bytes 111 */ 112 FREERDP_API int ringbuffer_peek(const RingBuffer* rb, DataChunk chunks[2], size_t sz); 113 114 /** move ahead the read head in case some byte were read using ringbuffer_peek() 115 * This function is used to commit the bytes that were effectively consumed. 116 * 117 * @param rb the ring buffer 118 * @param sz the 119 */ 120 FREERDP_API void ringbuffer_commit_read_bytes(RingBuffer* rb, size_t sz); 121 122#ifdef __cplusplus 123} 124#endif 125 126#endif /* FREERDP_UTILS_RINGBUFFER_H */