util-src/ringbuffer.c
changeset 10484 94cacf9fd0ae
parent 8738 856a40ec4a0a
child 10902 c6465fb3c839
equal deleted inserted replaced
10483:d362934437eb 10484:94cacf9fd0ae
    13 	size_t alen; /* allocated size */
    13 	size_t alen; /* allocated size */
    14 	size_t blen; /* current content size */
    14 	size_t blen; /* current content size */
    15 	char buffer[];
    15 	char buffer[];
    16 } ringbuffer;
    16 } ringbuffer;
    17 
    17 
    18 char readchar(ringbuffer *b) {
    18 static void writechar(ringbuffer *b, char c) {
    19 	b->blen--;
       
    20 	return b->buffer[(b->rpos++) % b->alen];
       
    21 }
       
    22 
       
    23 void writechar(ringbuffer *b, char c) {
       
    24 	b->blen++;
    19 	b->blen++;
    25 	b->buffer[(b->wpos++) % b->alen] = c;
    20 	b->buffer[(b->wpos++) % b->alen] = c;
    26 }
    21 }
    27 
    22 
    28 /* make sure position counters stay within the allocation */
    23 /* make sure position counters stay within the allocation */
    29 void modpos(ringbuffer *b) {
    24 static void modpos(ringbuffer *b) {
    30 	b->rpos = b->rpos % b->alen;
    25 	b->rpos = b->rpos % b->alen;
    31 	b->wpos = b->wpos % b->alen;
    26 	b->wpos = b->wpos % b->alen;
    32 }
    27 }
    33 
    28 
    34 int find(ringbuffer *b, const char *s, size_t l) {
    29 static int find(ringbuffer *b, const char *s, size_t l) {
    35 	size_t i, j;
    30 	size_t i, j;
    36 	int m;
    31 	int m;
    37 
    32 
    38 	if(b->rpos == b->wpos) { /* empty */
    33 	if(b->rpos == b->wpos) { /* empty */
    39 		return 0;
    34 		return 0;
    62 
    57 
    63 /*
    58 /*
    64  * Find first position of a substring in buffer
    59  * Find first position of a substring in buffer
    65  * (buffer, string) -> number
    60  * (buffer, string) -> number
    66  */
    61  */
    67 int rb_find(lua_State *L) {
    62 static int rb_find(lua_State *L) {
    68 	size_t l, m;
    63 	size_t l, m;
    69 	ringbuffer *b = luaL_checkudata(L, 1, "ringbuffer_mt");
    64 	ringbuffer *b = luaL_checkudata(L, 1, "ringbuffer_mt");
    70 	const char *s = luaL_checklstring(L, 2, &l);
    65 	const char *s = luaL_checklstring(L, 2, &l);
    71 	m = find(b, s, l);
    66 	m = find(b, s, l);
    72 
    67 
    80 
    75 
    81 /*
    76 /*
    82  * Move read position forward without returning the data
    77  * Move read position forward without returning the data
    83  * (buffer, number) -> boolean
    78  * (buffer, number) -> boolean
    84  */
    79  */
    85 int rb_discard(lua_State *L) {
    80 static int rb_discard(lua_State *L) {
    86 	ringbuffer *b = luaL_checkudata(L, 1, "ringbuffer_mt");
    81 	ringbuffer *b = luaL_checkudata(L, 1, "ringbuffer_mt");
    87 	size_t r = luaL_checkinteger(L, 2);
    82 	size_t r = luaL_checkinteger(L, 2);
    88 
    83 
    89 	if(r > b->blen) {
    84 	if(r > b->blen) {
    90 		lua_pushboolean(L, 0);
    85 		lua_pushboolean(L, 0);
   101 
    96 
   102 /*
    97 /*
   103  * Read bytes from buffer
    98  * Read bytes from buffer
   104  * (buffer, number, boolean?) -> string
    99  * (buffer, number, boolean?) -> string
   105  */
   100  */
   106 int rb_read(lua_State *L) {
   101 static int rb_read(lua_State *L) {
   107 	ringbuffer *b = luaL_checkudata(L, 1, "ringbuffer_mt");
   102 	ringbuffer *b = luaL_checkudata(L, 1, "ringbuffer_mt");
   108 	size_t r = luaL_checkinteger(L, 2);
   103 	size_t r = luaL_checkinteger(L, 2);
   109 	int peek = lua_toboolean(L, 3);
   104 	int peek = lua_toboolean(L, 3);
   110 
   105 
   111 	if(r > b->blen) {
   106 	if(r > b->blen) {
   133 
   128 
   134 /*
   129 /*
   135  * Read buffer until first occurrence of a substring
   130  * Read buffer until first occurrence of a substring
   136  * (buffer, string) -> string
   131  * (buffer, string) -> string
   137  */
   132  */
   138 int rb_readuntil(lua_State *L) {
   133 static int rb_readuntil(lua_State *L) {
   139 	size_t l, m;
   134 	size_t l, m;
   140 	ringbuffer *b = luaL_checkudata(L, 1, "ringbuffer_mt");
   135 	ringbuffer *b = luaL_checkudata(L, 1, "ringbuffer_mt");
   141 	const char *s = luaL_checklstring(L, 2, &l);
   136 	const char *s = luaL_checklstring(L, 2, &l);
   142 	m = find(b, s, l);
   137 	m = find(b, s, l);
   143 
   138 
   152 
   147 
   153 /*
   148 /*
   154  * Write bytes into the buffer
   149  * Write bytes into the buffer
   155  * (buffer, string) -> integer
   150  * (buffer, string) -> integer
   156  */
   151  */
   157 int rb_write(lua_State *L) {
   152 static int rb_write(lua_State *L) {
   158 	size_t l, w = 0;
   153 	size_t l, w = 0;
   159 	ringbuffer *b = luaL_checkudata(L, 1, "ringbuffer_mt");
   154 	ringbuffer *b = luaL_checkudata(L, 1, "ringbuffer_mt");
   160 	const char *s = luaL_checklstring(L, 2, &l);
   155 	const char *s = luaL_checklstring(L, 2, &l);
   161 
   156 
   162 	/* Does `l` bytes fit? */
   157 	/* Does `l` bytes fit? */
   175 	lua_pushinteger(L, w);
   170 	lua_pushinteger(L, w);
   176 
   171 
   177 	return 1;
   172 	return 1;
   178 }
   173 }
   179 
   174 
   180 int rb_tostring(lua_State *L) {
   175 static int rb_tostring(lua_State *L) {
   181 	ringbuffer *b = luaL_checkudata(L, 1, "ringbuffer_mt");
   176 	ringbuffer *b = luaL_checkudata(L, 1, "ringbuffer_mt");
   182 	lua_pushfstring(L, "ringbuffer: %p %d/%d", b, b->blen, b->alen);
   177 	lua_pushfstring(L, "ringbuffer: %p %d/%d", b, b->blen, b->alen);
   183 	return 1;
   178 	return 1;
   184 }
   179 }
   185 
   180 
   186 int rb_length(lua_State *L) {
   181 static int rb_length(lua_State *L) {
   187 	ringbuffer *b = luaL_checkudata(L, 1, "ringbuffer_mt");
   182 	ringbuffer *b = luaL_checkudata(L, 1, "ringbuffer_mt");
   188 	lua_pushinteger(L, b->blen);
   183 	lua_pushinteger(L, b->blen);
   189 	return 1;
   184 	return 1;
   190 }
   185 }
   191 
   186 
   192 int rb_size(lua_State *L) {
   187 static int rb_size(lua_State *L) {
   193 	ringbuffer *b = luaL_checkudata(L, 1, "ringbuffer_mt");
   188 	ringbuffer *b = luaL_checkudata(L, 1, "ringbuffer_mt");
   194 	lua_pushinteger(L, b->alen);
   189 	lua_pushinteger(L, b->alen);
   195 	return 1;
   190 	return 1;
   196 }
   191 }
   197 
   192 
   198 int rb_free(lua_State *L) {
   193 static int rb_free(lua_State *L) {
   199 	ringbuffer *b = luaL_checkudata(L, 1, "ringbuffer_mt");
   194 	ringbuffer *b = luaL_checkudata(L, 1, "ringbuffer_mt");
   200 	lua_pushinteger(L, b->alen - b->blen);
   195 	lua_pushinteger(L, b->alen - b->blen);
   201 	return 1;
   196 	return 1;
   202 }
   197 }
   203 
   198 
   204 int rb_new(lua_State *L) {
   199 static int rb_new(lua_State *L) {
   205 	size_t size = luaL_optinteger(L, 1, sysconf(_SC_PAGESIZE));
   200 	size_t size = luaL_optinteger(L, 1, sysconf(_SC_PAGESIZE));
   206 	ringbuffer *b = lua_newuserdata(L, sizeof(ringbuffer) + size);
   201 	ringbuffer *b = lua_newuserdata(L, sizeof(ringbuffer) + size);
   207 
   202 
   208 	b->rpos = 0;
   203 	b->rpos = 0;
   209 	b->wpos = 0;
   204 	b->wpos = 0;