static int read_line (lua_State *L, struct membuf *mb) { const char *nl, *s = mb->data; size_t l, n = mb->offset; if (n && (nl = memchr(s, '\n', n))) { char *p = mb->data; /* avoid warning */ l = nl - p; lua_pushlstring(L, p, l); n -= l + 1; mb->offset = n; if (n) memmove(p, nl + 1, n); return 1; } if (!(mb->flags & MEM_ISTREAM)) { n = 1; goto end; } for (; ; ) { stream_read(L, MEM_BUFLINE, 0); s = lua_tolstring(L, -1, &n); if (!n) { n = 1; break; } if (*s == '\n') break; nl = memchr(s + 1, '\n', n - 1); l = !nl ? n : (size_t) (nl - s); if (!membuf_addlstring(L, mb, s, l)) return 0; /* tail */ if (nl) { n -= l; s = nl; break; } lua_pop(L, 1); } end: l = mb->offset; if (l != 0) lua_pushlstring(L, mb->data, l); else lua_pushnil(L); mb->offset = 0; return (!--n) ? 1 : membuf_addlstring(L, mb, s + 1, n); }
int sys_buffer_write_next (lua_State *L, struct sys_buffer *sb, char *buf, const size_t buflen) { struct membuf *mb = sb->mb; if (mb) { if (!buflen) mb->offset = mb->len; if (!membuf_addlstring(L, mb, NULL, buflen)) return 0; sb->ptr.w = mb->data + mb->offset; sb->size = mb->len - mb->offset; } else { struct sys_buffer *osb = (void *) buf; size_t size; char *p; if (sb->ptr.w == buf) { size = sb->size; p = malloc(2 * size); if (!p) return 0; memcpy(p, buf, size); } else { size = 2 * osb->size; p = realloc(osb->ptr.w, 2 * size); if (!p) return 0; sb->size = size; } sb->ptr.w = p + size; osb->ptr.w = p; osb->size = size; } return 1; }
/* * Arguments: membuf_udata, num_bytes (number) * Returns: [membuf_udata] */ static int mem_reserve (lua_State *L) { struct membuf *mb = checkudata(L, 1, MEM_TYPENAME); const int len = luaL_checkinteger(L, 2); if (membuf_addlstring(L, mb, NULL, len)) { lua_settop(L, 1); return 1; } return 0; }
/* * Arguments: membuf_udata, string ... * Returns: [boolean] */ static int membuf_write (lua_State *L) { struct membuf *mb = checkudata(L, 1, MEM_TYPENAME); int narg, i; narg = lua_gettop(L); for (i = 2; i <= narg; ++i) { size_t len = lua_rawlen(L, i); if (len && !membuf_addlstring(L, mb, lua_tostring(L, i), len)) return 0; } lua_pushboolean(L, 1); return 1; }