#ifndef INCLUDED_C_BYTERINGBUFFER_H #define INCLUDED_C_BYTERINGBUFFER_H #ifndef INCLUDED_C_BASE_H #include #endif /*INCLUDED_C_BASE_H*/ /* ------------------------------------------------------------------------------------------------------------------ */ /* */ typedef struct { uint8_t* buffer; c_size_t capacity; c_size_t head; c_size_t tail; c_bool_t is_full; }c_ByteRingBuffer_t; c_err_t c_ByteRingBuffer_Init(c_ByteRingBuffer_t* self, c_size_t capacity); void c_ByteRingBuffer_Destroy(c_ByteRingBuffer_t* self); c_err_t c_ByteRingBuffer_WriteByte(c_ByteRingBuffer_t* self, uint8_t byte); c_err_t c_ByteRingBuffer_ReadByte(c_ByteRingBuffer_t* self, uint8_t* out_byte); c_size_t c_ByteRingBuffer_WriteBuffer(c_ByteRingBuffer_t* self, const uint8_t* src, c_size_t len); c_size_t c_ByteRingBuffer_ReadBuffer(c_ByteRingBuffer_t* self, uint8_t* dest, c_size_t len); c_size_t c_ByteRingBuffer_GetSize(const c_ByteRingBuffer_t* self); c_bool_t c_ByteRingBuffer_IsEmpty(const c_ByteRingBuffer_t* self); c_bool_t c_ByteRingBuffer_IsFull(const c_ByteRingBuffer_t* self); /* * Writes a single byte, overwriting the oldest byte if the buffer is full. */ void c_ByteRingBuffer_WriteByteOverwrite(c_ByteRingBuffer_t* self, uint8_t byte); /* * Writes a buffer span, overwriting the oldest bytes continuously if capacity is exceeded. */ c_size_t c_ByteRingBuffer_WriteBufferOverwrite(c_ByteRingBuffer_t* self, const uint8_t* src, c_size_t len); /* * Inspects a single byte at the head position without removing it. */ c_err_t c_ByteRingBuffer_PeekByte(const c_ByteRingBuffer_t* self, uint8_t* out_byte); /* * Inspects up to 'len' bytes starting from the head position without removing them. * Returns the actual number of bytes peeked. */ c_size_t c_ByteRingBuffer_PeekBuffer(const c_ByteRingBuffer_t* self, uint8_t* dest, c_size_t len); /* * Advances the head pointer to drop up to 'len' bytes without copying data. * Returns the actual number of bytes dropped. */ c_size_t c_ByteRingBuffer_Discard(c_ByteRingBuffer_t* self, c_size_t len); /* * Returns the direct linear address to read the first available contiguous memory block. * @param out_contiguous_len: Populated with the byte depth length of the straight chunk line. * @return Pointer into the structural array channel, or NULL if buffer is empty. */ const uint8_t* c_ByteRingBuffer_GetReadPtr(const c_ByteRingBuffer_t* self, c_size_t* out_contiguous_len); /* * Returns the direct linear address to write into the first available contiguous free memory block. * @param out_contiguous_len: Populated with the space depth length of the straight chunk line. * @return Pointer into the structural array channel, or NULL if buffer is full. */ uint8_t* c_ByteRingBuffer_GetWritePtr(const c_ByteRingBuffer_t* self, c_size_t* out_contiguous_len); /* * Searches for the first occurrence of a byte sequence (pattern) within the ring buffer. * Returns the relative offset from the current head pointer (0 to size-1), or C_ERR_NOT_FOUND. */ c_index_t c_ByteRingBuffer_IndexOfBuffer(const c_ByteRingBuffer_t* self, const uint8_t* pattern, c_size_t pattern_len); /* * Searches for the first occurrence of a single byte within the ring buffer. * Returns the relative offset from the current head pointer (0 to size-1), or C_ERR_NOT_FOUND. */ c_index_t c_ByteRingBuffer_IndexOfByte(const c_ByteRingBuffer_t* self, uint8_t target); /* * Searches for the last occurrence of a byte sequence within the ring buffer. * Returns the relative offset from the current head pointer (0 to size-1), or C_ERR_NOT_FOUND. */ c_index_t c_ByteRingBuffer_LastIndexOfBuffer(const c_ByteRingBuffer_t* self, const uint8_t* pattern, c_size_t pattern_len); /* * Consumes and extracts data into 'dest' up to and including the specified token sequence. * Returns the total number of bytes read and placed into dest, or 0 if token is not found. */ c_size_t c_ByteRingBuffer_ReadUntilToken(c_ByteRingBuffer_t* self, const uint8_t* token, c_size_t token_len, uint8_t* dest, c_size_t dest_max_len); /* * Retrieves a single byte from the buffer at a relative index position from the head. * @param self: The ring buffer instance. * @param relative_offset: The offset relative to the head pointer (0 = oldest unread byte, size-1 = newest byte). * @param out_byte: Destination pointer for the extracted byte. * @return C_SUCCESS on clean execution, C_ERR_INVALID_PARAM, or C_ERR_OUT_OF_BOUNDS. */ c_err_t c_ByteRingBuffer_GetAtRelative(const c_ByteRingBuffer_t* self, c_size_t relative_offset, uint8_t* out_byte); /* * Checks if the byte at a specific relative offset from the head matches the given value. * @param self: The ring buffer instance. * @param offset: The relative offset from the current head pointer (0 = oldest unread byte). * @param value: The expected byte value to compare against. * @return C_TRUE (1) if it matches perfectly, C_FALSE (0) if it mismatches, is empty, or out of bounds. */ c_bool_t c_ByteRingBuffer_Is(const c_ByteRingBuffer_t* self, c_index_t offset, uint8_t value); /* * Compares the contents of the ring buffer starting at a relative offset with an external flat buffer. * @param self: The ring buffer instance. * @param offset: The relative offset from the current head pointer to start comparing from. * @param buffer: The external memory array to compare against. * @param len: The number of bytes to compare. * @return 0 if the memory blocks match exactly, < 0 if the ring buffer data is lexicographically smaller, * > 0 if it is larger. Returns (C_ERR_INVALID_PARAM) or (C_ERR_OUT_OF_BOUNDS) on range violations. */ int c_ByteRingBuffer_Memcmp(const c_ByteRingBuffer_t* self, c_size_t offset, const uint8_t* buffer, c_size_t len); /* * Parses an unsigned long value from the ring buffer starting at a specific relative offset. * @param self: The ring buffer instance. * @param offset: The relative offset from the current head pointer to start parsing from. * @param base: The number base system to parse (0 for auto-detection, 2-36). * @param out_value: Destination pointer for the parsed unsigned long. * @param out_end_offset: Optional destination pointer for the relative offset immediately following the parsed number. * @return C_SUCCESS on clean execution, C_ERR_INVALID_PARAM, or C_ERR_OUT_OF_BOUNDS. */ c_err_t c_ByteRingBuffer_Strtoul(const c_ByteRingBuffer_t* self, c_size_t offset, int base, unsigned long* out_value, c_size_t* out_end_offset); #endif /*INCLUDED_C_BYTERINGBUFFER_H*/