From 35eaa9f85f89be1fe0edf4dd3036d14f4848eed4 Mon Sep 17 00:00:00 2001 From: Jo-Philipp Wich Date: Thu, 4 Sep 2014 11:35:09 +0000 Subject: [PATCH] libs/web: add support for string templates to the template parser Signed-off-by: Matthias Schiffer --- modules/base/src/template_lualib.c | 24 +++++++++++++++++---- modules/base/src/template_parser.c | 43 +++++++++++++++++++++++++++++++++----- modules/base/src/template_parser.h | 1 + 3 files changed, 59 insertions(+), 9 deletions(-) diff --git a/modules/base/src/template_lualib.c b/modules/base/src/template_lualib.c index 0d4364104..103561188 100644 --- a/modules/base/src/template_lualib.c +++ b/modules/base/src/template_lualib.c @@ -18,10 +18,8 @@ #include "template_lualib.h" -int template_L_parse(lua_State *L) +static int template_L_do_parse(lua_State *L, struct template_parser *parser, const char *chunkname) { - const char *file = luaL_checkstring(L, 1); - struct template_parser *parser = template_open(file); int lua_status, rv; if (!parser) @@ -32,7 +30,7 @@ int template_L_parse(lua_State *L) return 3; } - lua_status = lua_load(L, template_reader, parser, file); + lua_status = lua_load(L, template_reader, parser, chunkname); if (lua_status == 0) rv = 1; @@ -44,6 +42,23 @@ int template_L_parse(lua_State *L) return rv; } +int template_L_parse(lua_State *L) +{ + const char *file = luaL_checkstring(L, 1); + struct template_parser *parser = template_open(file); + + return template_L_do_parse(L, parser, file); +} + +int template_L_parse_string(lua_State *L) +{ + size_t len; + const char *str = luaL_checklstring(L, 1, &len); + struct template_parser *parser = template_string(str, len); + + return template_L_do_parse(L, parser, "[string]"); +} + int template_L_utf8(lua_State *L) { size_t len = 0; @@ -146,6 +161,7 @@ static int template_L_hash(lua_State *L) { /* module table */ static const luaL_reg R[] = { { "parse", template_L_parse }, + { "parse_string", template_L_parse_string }, { "utf8", template_L_utf8 }, { "pcdata", template_L_pcdata }, { "striptags", template_L_striptags }, diff --git a/modules/base/src/template_parser.c b/modules/base/src/template_parser.c index 1aa5131ff..c263fbf9f 100644 --- a/modules/base/src/template_parser.c +++ b/modules/base/src/template_parser.c @@ -100,6 +100,36 @@ err: return NULL; } +struct template_parser * template_string(const char *str, uint32_t len) +{ + struct template_parser *parser; + + if (!str) { + errno = EINVAL; + goto err; + } + + if (!(parser = malloc(sizeof(*parser)))) + goto err; + + memset(parser, 0, sizeof(*parser)); + parser->fd = -1; + + parser->size = len; + parser->data = (char*)str; + + parser->off = parser->data; + parser->cur_chunk.type = T_TYPE_INIT; + parser->cur_chunk.s = parser->data; + parser->cur_chunk.e = parser->data; + + return parser; + +err: + template_close(parser); + return NULL; +} + void template_close(struct template_parser *parser) { if (!parser) @@ -108,11 +138,14 @@ void template_close(struct template_parser *parser) if (parser->gc != NULL) free(parser->gc); - if ((parser->data != NULL) && (parser->data != MAP_FAILED)) - munmap(parser->data, parser->size); + /* if file is not set, we were parsing a string */ + if (parser->file) { + if ((parser->data != NULL) && (parser->data != MAP_FAILED)) + munmap(parser->data, parser->size); - if (parser->fd >= 0) - close(parser->fd); + if (parser->fd >= 0) + close(parser->fd); + } free(parser); } @@ -376,7 +409,7 @@ int template_error(lua_State *L, struct template_parser *parser) line++; snprintf(msg, sizeof(msg), "Syntax error in %s:%d: %s", - parser->file, line + chunkline, err ? err : "(unknown error)"); + parser->file ? parser->file : "[string]", line + chunkline, err ? err : "(unknown error)"); lua_pushnil(L); lua_pushinteger(L, line + chunkline); diff --git a/modules/base/src/template_parser.h b/modules/base/src/template_parser.h index ad03cbcfb..a3200a2df 100644 --- a/modules/base/src/template_parser.h +++ b/modules/base/src/template_parser.h @@ -71,6 +71,7 @@ struct template_parser { }; struct template_parser * template_open(const char *file); +struct template_parser * template_string(const char *str, uint32_t len); void template_close(struct template_parser *parser); const char *template_reader(lua_State *L, void *ud, size_t *sz); -- 2.11.0