src/event_buffer.c

changeset 27
0d82e4f49a56
parent 26
a117895e867c
child 28
f7b864b661f4
equal deleted inserted replaced
26:a117895e867c 27:0d82e4f49a56
9 #define BUFFER_ADD_CHECK_INPUT_FIRST 1 9 #define BUFFER_ADD_CHECK_INPUT_FIRST 1
10 10
11 static le_buffer* event_buffer_get(lua_State* L, int idx) { 11 static le_buffer* event_buffer_get(lua_State* L, int idx) {
12 return (le_buffer*)luaL_checkudata(L, idx, EVENT_BUFFER_MT); 12 return (le_buffer*)luaL_checkudata(L, idx, EVENT_BUFFER_MT);
13 } 13 }
14 static void event_buffer_check(lua_State* L, int idx) {
15 le_buffer* buf = (le_buffer*)luaL_checkudata(L, idx, EVENT_BUFFER_MT);
16 if(!buf->buffer)
17 luaL_argerror(L, idx, "Attempt to use closed event_buffer object");
18 return buf;
19 }
14 static int is_event_buffer(lua_State* L, int idx) { 20 static int is_event_buffer(lua_State* L, int idx) {
15 int ret; 21 int ret;
16 lua_getmetatable(L, idx); 22 lua_getmetatable(L, idx);
17 luaL_getmetatable(L, EVENT_BUFFER_MT); 23 luaL_getmetatable(L, EVENT_BUFFER_MT);
18 ret = lua_rawequal(L, -2, -1); 24 ret = lua_rawequal(L, -2, -1);
19 lua_pop(L, 2); 25 lua_pop(L, 2);
20 return ret; 26 return ret;
21 } 27 }
22 28
29 /* TODO: Use lightuserdata mapping to locate hanging object instances */
30 static int event_buffer_push(lua_State* L, struct evbuffer* buffer) {
31 le_buffer *buf = (le_buffer*)lua_newuserdata(L, sizeof(le_buffer));
32 buf->buffer = buffer;
33 luaL_getmetatable(L, EVENT_BUFFER_MT);
34 lua_setmetatable(L, -2);
35 return 1;
36 }
37
38 static int event_buffer_push_new(lua_State* L) {
39 return event_buffer_push(L, evbuffer_new());
40 }
41
42 static int event_buffer_gc(lua_State* L) {
43 le_buffer* buf = event_buffer_get(L, 1);
44 if(buf->buffer) {
45 evbuffer_free(buf->buffer);
46 buf->buffer = NULL;
47 }
48 return 0;
49 }
50
23 /* LUA: buffer:add(...) 51 /* LUA: buffer:add(...)
24 progressively adds items to the buffer 52 progressively adds items to the buffer
25 if arg[*] is string, treat as a string:format call 53 if arg[*] is string, treat as a string:format call
26 if arg[*] is a buffer, perform event_add_buffer 54 if arg[*] is a buffer, perform event_add_buffer
27 returns number of bytes added 55 returns number of bytes added
28 */ 56 */
29 int event_buffer_add(lua_State* L) { 57 static int event_buffer_add(lua_State* L) {
30 le_buffer* buf = event_buffer_get(L, 1); 58 le_buffer* buf = event_buffer_check(L, 1);
31 struct evbuffer* buffer = buf->buffer; 59 struct evbuffer* buffer = buf->buffer;
32 int oldLength = EVBUFFER_LENGTH(buffer); 60 int oldLength = EVBUFFER_LENGTH(buffer);
33 int last = lua_top(L); 61 int last = lua_top(L);
34 int i; 62 int i;
35 for(i = 2; i <= last; i++) { 63 for(i = 2; i <= last; i++) {
44 size_t len; 72 size_t len;
45 const char* data = lua_tolstring(L, i, &len); 73 const char* data = lua_tolstring(L, i, &len);
46 if(0 != evbuffer_add(buffer, data, len)) 74 if(0 != evbuffer_add(buffer, data, len))
47 luaL_error(L, "Failed to add data to the buffer"); 75 luaL_error(L, "Failed to add data to the buffer");
48 } else { 76 } else {
49 le_buffer* buf2 = event_buffer_get(L, i); 77 le_buffer* buf2 = event_buffer_check(L, i);
50 if(0 != evbuffer_add_buffer(buffer, buf2->buffer)) 78 if(0 != evbuffer_add_buffer(buffer, buf2->buffer))
51 luaL_error(L, "Failed to move buffer-data to the buffer"); 79 luaL_error(L, "Failed to move buffer-data to the buffer");
52 } 80 }
53 } 81 }
54 lua_pushinteger(L, EVBUFFER_LENGTH(buffer) - oldLength); 82 lua_pushinteger(L, EVBUFFER_LENGTH(buffer) - oldLength);
55 return 1; 83 return 1;
56 } 84 }
57 85
86 static int event_buffer_get_length(lua_State* L) {
87 le_buffer* buf = event_buffer_check(L, 1);
88 lua_pushinteger(L, EVBUFFER_LENGTH(buf->buffer));
89 return 1;
90 }
91
92 /* MAYBE: Could add caching */
93 static int event_buffer_get_data(lua_State* L) {
94 le_buffer* buf = event_buffer_check(L, 1);
95 lua_pushlstring(L, EVBUFFER_DATA(buf->buffer), EVBUFFER_LENGTH(buf->buffer));
96 return 1;
97 }
98
99 static int event_buffer_drain(lua_State* L) {
100 le_buffer* buf = event_buffer_check(L, 1);
101 size_t len = luaL_checkinteger(L, 2);
102 evbuffer_drain(buf->buffer, len);
103 return 0;
104 }
105
58 static luaL_Reg buffer_funcs[] = { 106 static luaL_Reg buffer_funcs[] = {
59 {"add",event_buffer_add}, 107 {"add",event_buffer_add},
108 {"length",event_buffer_get_length},
109 {"get_data",event_buffer_get_data},
110 {"drain",event_buffer_drain},
111 {"close",event_buffer_gc},
60 {NULL, NULL} 112 {NULL, NULL}
61 }; 113 };
62 static luaL_Ref funcs[] = { 114 static luaL_Ref funcs[] = {
115 {"new",event_buffer_push_new},
63 {NULL, NULL} 116 {NULL, NULL}
64 }; 117 };
65 118
66 int event_buffer_register(lua_State* L) { 119 int event_buffer_register(lua_State* L) {
67 luaL_newmetatable(L, EVENT_BUFFER_MT); 120 luaL_newmetatable(L, EVENT_BUFFER_MT);
121 lua_pushcfunction(L, event_buffer_gc);
122 lua_setfield(L, -2, "__gc");
68 lua_newtable(L); 123 lua_newtable(L);
69 luaL_register(L, NULL, buffer_funcs); 124 luaL_register(L, NULL, buffer_funcs);
70 lua_setfield(L, -2, "__index"); 125 lua_setfield(L, -2, "__index");
71 lua_pop(L, 1); 126 lua_pop(L, 1);
72 127

mercurial