summaryrefslogtreecommitdiff
path: root/kern/cbuf.h
diff options
context:
space:
mode:
Diffstat (limited to 'kern/cbuf.h')
-rw-r--r--kern/cbuf.h50
1 files changed, 37 insertions, 13 deletions
diff --git a/kern/cbuf.h b/kern/cbuf.h
index 3ea38418..4d69334d 100644
--- a/kern/cbuf.h
+++ b/kern/cbuf.h
@@ -1,5 +1,5 @@
/*
- * Copyright (c) 2015 Richard Braun.
+ * Copyright (c) 2015-2017 Richard Braun.
*
* This program is free software: you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
@@ -21,6 +21,9 @@
#ifndef _KERN_CBUF_H
#define _KERN_CBUF_H
+#include <stdbool.h>
+#include <stddef.h>
+
/*
* Circular buffer descriptor.
*
@@ -29,30 +32,30 @@
*/
struct cbuf {
char *buf;
- unsigned long capacity;
- unsigned long start;
- unsigned long end;
+ size_t capacity;
+ size_t start;
+ size_t end;
};
-static inline unsigned long
+static inline size_t
cbuf_capacity(const struct cbuf *cbuf)
{
return cbuf->capacity;
}
-static inline unsigned long
+static inline size_t
cbuf_start(const struct cbuf *cbuf)
{
return cbuf->start;
}
-static inline unsigned long
+static inline size_t
cbuf_end(const struct cbuf *cbuf)
{
return cbuf->end;
}
-static inline unsigned long
+static inline size_t
cbuf_size(const struct cbuf *cbuf)
{
return cbuf->end - cbuf->start;
@@ -64,13 +67,21 @@ cbuf_clear(struct cbuf *cbuf)
cbuf->start = cbuf->end;
}
+static inline bool
+cbuf_range_valid(const struct cbuf *cbuf, size_t start, size_t end)
+{
+ return (((end - start) <= cbuf_size(cbuf))
+ && ((start - cbuf->start) <= cbuf_size(cbuf))
+ && ((cbuf->end - end) <= cbuf_size(cbuf)));
+}
+
/*
* Initialize a circular buffer.
*
* The descriptor is set to use the given buffer for storage. Capacity
* must be a power-of-two.
*/
-void cbuf_init(struct cbuf *cbuf, char *buf, unsigned long capacity);
+void cbuf_init(struct cbuf *cbuf, char *buf, size_t capacity);
/*
* Append a byte to a circular buffer.
@@ -90,12 +101,25 @@ void cbuf_push(struct cbuf *cbuf, char byte);
int cbuf_pop(struct cbuf *cbuf, char *bytep);
/*
- * Read a byte at a specific location.
+ * Write into a circular buffer at a specific location.
+ *
+ * If the given index is outside buffer boundaries, ERROR_INVAL is returned.
+ * Otherwise size bytes are copied into the circular buffer. If the range
+ * in the circular buffer goes beyond its end, the end index is updated as
+ * appropriate. If the buffer is full when extending its end, the oldest
+ * bytes are overwritten and the start index is updated accordingly.
+ */
+int cbuf_write(struct cbuf *cbuf, size_t index, const void *buf, size_t size);
+
+/*
+ * Read from a circular buffer at a specific location.
*
* If the given index is outside buffer boundaries, ERROR_INVAL is returned.
- * Otherwise the byte is stored at the bytep address and 0 is returned.
- * The buffer isn't changed by this operation.
+ * Otherwise at most *sizep bytes are copied into the given byte buffer,
+ * and *sizep is updated to the number of bytes actually copied.
+ *
+ * The circular buffer isn't changed by this operation.
*/
-int cbuf_read(const struct cbuf *cbuf, unsigned long index, char *bytep);
+int cbuf_read(const struct cbuf *cbuf, size_t index, void *buf, size_t *sizep);
#endif /* _KERN_CBUF_H */