/**
* @class KinoSearch::Util::ByteBuf ByteBuf.r
* @brief Growable buffer holding arbitrary bytes.
*
* The ByteBuf is a C struct that's essentially a growable string of char.
* It's like a stripped down Perl scalar that can only deal with strings. It
* knows its own size and capacity, so it can contain arbitrary binary data.
*/
#ifndef H_KINO_BYTEBUF
#define H_KINO_BYTEBUF 1
#include <stddef.h>
#include "KinoSearch/Util/Obj.r"
typedef struct kino_ByteBuf kino_ByteBuf;
typedef struct KINO_BYTEBUF_VTABLE KINO_BYTEBUF_VTABLE;
struct kino_ViewByteBuf;
KINO_CLASS("KinoSearch::Util::ByteBuf", "BB", "KinoSearch::Util::Obj");
struct kino_ByteBuf {
KINO_BYTEBUF_VTABLE *_;
KINO_OBJ_MEMBER_VARS;
char *ptr;
size_t len; /* number of valid chars */
size_t cap; /* allocated bytes, including any null termination */
};
/* Return a pointer to a new ByteBuf with a capacity of [future_size] + 1
* bytes. Size is initialized to 0. The first byte is set to NULL, so the
* ByteBuf has an initial value of "". None of the remaining allocated memory
* is initialized.
*/
kino_ByteBuf*
kino_BB_new(size_t future_size);
/* Return a pointer to a new ByteBuf which holds a copy of the passed-in
* string.
*/
kino_ByteBuf*
kino_BB_new_str(const char *ptr, size_t size);
/* Return a pointer to a new ByteBuf which assumes ownership of the passed-in
* string.
*/
kino_ByteBuf*
kino_BB_new_steal(char *ptr, size_t len, size_t cap);
/* Return a pointer to a new ByteBuf which contains a stringified version of
* [num].
*/
kino_ByteBuf*
kino_BB_new_i64(chy_i64_t num);
/* Lexical comparison of two ByteBufs, with level of indirection set to please
* qsort and friends.
*/
int
kino_BB_compare(const void *va, const void *vb);
/* Version of less_than to pass to PriorityQueue.
*/
chy_bool_t
kino_BB_less_than(const void *va, const void *vb);
/* Deserialize a serialized ByteBuf. Consume characters in the ViewByteBuf.
*/
kino_ByteBuf*
kino_BB_deserialize(struct kino_ViewByteBuf *serialized);
/* Copy the passed-in string into the ByteBuf. Allocate more memory if
* necessary.
*/
void
kino_BB_copy_str(kino_ByteBuf *self, char* ptr, size_t size);
KINO_METHOD("Kino_BB_Copy_Str");
/* Copy the contents of the passed-in string into the original ByteBuf.
* Allocate more memory if necessary.
*/
void
kino_BB_copy_bb(kino_ByteBuf *self, const kino_ByteBuf *other);
KINO_METHOD("Kino_BB_Copy_BB");
/* Concatenate the passed-in string onto the end of the ByteBuf. Allocate more
* memory as needed.
*/
void
kino_BB_cat_str(kino_ByteBuf *self, char* ptr, size_t size);
KINO_METHOD("Kino_BB_Cat_Str");
/* Concatenate the contents of the passed-in ByteBuf onto the end of the
* original ByteBuf. Allocate more memory as needed.
*/
void
kino_BB_cat_bb(kino_ByteBuf *self, const kino_ByteBuf *other);
KINO_METHOD("Kino_BB_Cat_BB");
/* Concatenate the stringified form of [num] onto the end of the ByteBuf.
*/
void
kino_BB_cat_i64(kino_ByteBuf *self, chy_i64_t num);
KINO_METHOD("Kino_BB_Cat_I64");
/* Extract an integer from the stringified version held in the ByteBuf.
*/
chy_i64_t
kino_BB_to_i64(kino_ByteBuf *self);
KINO_METHOD("Kino_BB_To_I64");
/* Assign more memory to the ByteBuf, if it doesn't already have enough room
* to hold a string of [size] bytes. Cannot shrink the allocation.
*/
void
kino_BB_grow(kino_ByteBuf *self, size_t new_size);
KINO_METHOD("Kino_BB_Grow");
/* Test whether the ByteBuf starts with the content of another.
*/
chy_bool_t
kino_BB_starts_with(kino_ByteBuf *self, const kino_ByteBuf *prefix);
KINO_METHOD("Kino_BB_Starts_With");
/* Test whether the ByteBuf ends with the content of another.
*/
chy_bool_t
kino_BB_ends_with_str(kino_ByteBuf *self, const char *postfix,
size_t postfix_len);
KINO_METHOD("Kino_BB_Ends_With_Str");
kino_ByteBuf*
kino_BB_clone(kino_ByteBuf *self);
KINO_METHOD("Kino_BB_Clone");
void
kino_BB_destroy(kino_ByteBuf *self);
KINO_METHOD("Kino_BB_Destroy");
chy_bool_t
kino_BB_equals(kino_ByteBuf *self, kino_ByteBuf *other);
KINO_METHOD("Kino_BB_Equals");
chy_i32_t
kino_BB_hash_code(kino_ByteBuf *self);
KINO_METHOD("Kino_BB_Hash_Code");
kino_ByteBuf*
kino_BB_to_string(kino_ByteBuf *self);
KINO_METHOD("Kino_BB_To_String");
void
kino_BB_serialize(kino_ByteBuf *self, kino_ByteBuf *target);
KINO_METHOD("Kino_BB_Serialize");
KINO_END_CLASS
#define KINO_BB_GROW(self, new_len) \
do { \
if (new_len >= self->cap) \
BB_grow(self, new_len); \
} while (0)
#define KINO_BYTEBUF_BLANK { &KINO_BYTEBUF, 0, "", 0, 0 }
#define KINO_BBEND(self) ((self)->ptr + (self)->len)
#define KINO_BB_CLONE(self) ((kino_ByteBuf*)Kino_Obj_Clone(self))
#define KINO_BB_LITERAL(string) \
{ &KINO_BYTEBUF, 0, string "", sizeof(string) -1, sizeof(string) }
#ifdef KINO_USE_SHORT_NAMES
#define BB_GROW(self, len) KINO_BB_GROW(self, len)
#define BYTEBUF_BLANK KINO_BYTEBUF_BLANK
#define BBEND(self) KINO_BBEND(self)
#define BB_CLONE(self) KINO_BB_CLONE(self)
#define BB_LITERAL(string) KINO_BB_LITERAL(string)
#endif
#endif /* H_KINO_BYTEBUF */
/* Copyright 2006-2007 Marvin Humphrey
*
* This program is free software; you can redistribute it and/or modify
* under the same terms as Perl itself.
*/