From ffcff14819bff42b05c7689057fc8e883fb88089 Mon Sep 17 00:00:00 2001 From: Vsevolod Stakhov Date: Sat, 29 Mar 2014 16:13:45 -0700 Subject: [PATCH] Handle invalid IP addresses. --- src/lua/lua_common.h | 1 + src/lua/lua_ip.c | 56 ++++++++++++++++++++++++++++++-------------- 2 files changed, 39 insertions(+), 18 deletions(-) diff --git a/src/lua/lua_common.h b/src/lua/lua_common.h index ec5215edf..0dd5349ea 100644 --- a/src/lua/lua_common.h +++ b/src/lua/lua_common.h @@ -137,6 +137,7 @@ struct rspamd_lua_ip { struct in_addr ip4; } data; int af; + gboolean is_valid; }; /** diff --git a/src/lua/lua_ip.c b/src/lua/lua_ip.c index daf5a03ce..4706af9ee 100644 --- a/src/lua/lua_ip.c +++ b/src/lua/lua_ip.c @@ -32,6 +32,7 @@ LUA_FUNCTION_DEF (ip, inversed_str_octets); LUA_FUNCTION_DEF (ip, from_string); LUA_FUNCTION_DEF (ip, destroy); LUA_FUNCTION_DEF (ip, get_version); +LUA_FUNCTION_DEF (ip, is_valid); static const struct luaL_reg iplib_m[] = { LUA_INTERFACE_DEF (ip, to_string), @@ -40,6 +41,7 @@ static const struct luaL_reg iplib_m[] = { LUA_INTERFACE_DEF (ip, str_octets), LUA_INTERFACE_DEF (ip, inversed_str_octets), LUA_INTERFACE_DEF (ip, get_version), + LUA_INTERFACE_DEF (ip, is_valid), {"__tostring", lua_ip_to_string}, {"__gc", lua_ip_destroy}, {NULL, NULL} @@ -67,7 +69,7 @@ lua_ip_to_table (lua_State *L) int max, i; guint8 *ptr; - if (ip != NULL) { + if (ip != NULL && ip->is_valid) { lua_newtable (L); if (ip->af == AF_INET) { max = 32 / 8; @@ -96,7 +98,7 @@ lua_ip_str_octets (lua_State *L) guint8 *ptr; char numbuf[8]; - if (ip != NULL) { + if (ip != NULL && ip->is_valid) { lua_newtable (L); if (ip->af == AF_INET) { max = 32 / 8; @@ -136,7 +138,7 @@ lua_ip_inversed_str_octets (lua_State *L) guint8 *ptr; char numbuf[4]; - if (ip != NULL) { + if (ip != NULL && ip->is_valid) { lua_newtable (L); if (ip->af == AF_INET) { max = 32 / 8; @@ -175,7 +177,7 @@ lua_ip_to_string (lua_State *L) struct rspamd_lua_ip *ip = lua_check_ip (L, 1); gchar dst[INET6_ADDRSTRLEN + 1]; - if (ip != NULL) { + if (ip != NULL && ip->is_valid) { lua_pushstring (L, inet_ntop (ip->af, &ip->data, dst, sizeof (dst))); } else { @@ -196,14 +198,14 @@ lua_ip_from_string (lua_State *L) ip = g_slice_alloc (sizeof (struct rspamd_lua_ip)); if (inet_pton (AF_INET, ip_str, &ip->data.ip4) == 1) { ip->af = AF_INET; + ip->is_valid = TRUE; } else if (inet_pton (AF_INET6, ip_str, &ip->data.ip6) == 1) { ip->af = AF_INET6; + ip->is_valid = TRUE; } else { - g_slice_free1 (sizeof (struct rspamd_lua_ip), ip); - lua_pushnil (L); - return 1; + ip->is_valid = FALSE; } pip = lua_newuserdata (L, sizeof (struct rspamd_lua_ip *)); lua_setclass (L, "rspamd{ip}", -1); @@ -222,7 +224,7 @@ lua_ip_to_number (lua_State *L) struct rspamd_lua_ip *ip = lua_check_ip (L, 1); guint32 dst[4], i; - if (ip != NULL) { + if (ip != NULL && ip->is_valid) { if (ip->af == AF_INET) { /* One integer in host byte order */ lua_pushinteger (L, ntohl (ip->data.ip4.s_addr)); @@ -255,6 +257,7 @@ lua_ip_from_number (lua_State *L) ip = g_slice_alloc (sizeof (struct rspamd_lua_ip)); src[0] = lua_tointeger (L, 1); ip->af = AF_INET; + ip->is_valid = TRUE; ip->data.ip4.s_addr = htonl (src[0]); pip = lua_newuserdata (L, sizeof (struct rspamd_lua_ip *)); lua_setclass (L, "rspamd{ip}", -1); @@ -268,6 +271,7 @@ lua_ip_from_number (lua_State *L) G_STATIC_ASSERT (sizeof (ip->data) >= sizeof (src)); ip = g_slice_alloc (sizeof (struct rspamd_lua_ip)); ip->af = AF_INET6; + ip->is_valid = TRUE; memcpy (&ip->data, src, sizeof (src)); pip = lua_newuserdata (L, sizeof (struct rspamd_lua_ip *)); lua_setclass (L, "rspamd{ip}", -1); @@ -297,7 +301,7 @@ lua_ip_get_version (lua_State *L) { struct rspamd_lua_ip *ip = lua_check_ip (L, 1); - if (ip) { + if (ip && ip->is_valid) { lua_pushnumber (L, ip->af == AF_INET6 ? 6 : 4); } else { @@ -307,17 +311,33 @@ lua_ip_get_version (lua_State *L) return 1; } +static gint +lua_ip_is_valid (lua_State *L) +{ + struct rspamd_lua_ip *ip = lua_check_ip (L, 1); + + if (ip) { + lua_pushboolean (L, ip->is_valid); + } + else { + lua_pushnil (L); + } + + return 1; +} + void lua_ip_push (lua_State *L, int af, gpointer data) { struct rspamd_lua_ip *ip, **pip; + ip = g_slice_alloc (sizeof (struct rspamd_lua_ip)); + if (!rspamd_ip_is_valid (data, af)) { - lua_pushnil (L); + ip->is_valid = FALSE; } else { - ip = g_slice_alloc (sizeof (struct rspamd_lua_ip)); - + ip->is_valid = TRUE; ip->af = af; if (af == AF_INET6) { memcpy (&ip->data, data, sizeof (struct in6_addr)); @@ -325,10 +345,11 @@ lua_ip_push (lua_State *L, int af, gpointer data) else { memcpy (&ip->data, data, sizeof (struct in_addr)); } - pip = lua_newuserdata (L, sizeof (struct rspamd_lua_ip *)); - lua_setclass (L, "rspamd{ip}", -1); - *pip = ip; + } + pip = lua_newuserdata (L, sizeof (struct rspamd_lua_ip *)); + lua_setclass (L, "rspamd{ip}", -1); + *pip = ip; } void @@ -341,6 +362,7 @@ lua_ip_push_fromstring (lua_State *L, const gchar *ip_str) } else { ip = g_slice_alloc (sizeof (struct rspamd_lua_ip)); + ip->is_valid = TRUE; if (inet_pton (AF_INET, ip_str, &ip->data.ip4) == 1) { ip->af = AF_INET; } @@ -348,9 +370,7 @@ lua_ip_push_fromstring (lua_State *L, const gchar *ip_str) ip->af = AF_INET6; } else { - g_slice_free1 (sizeof (struct rspamd_lua_ip), ip); - lua_pushnil (L); - return; + ip->is_valid = FALSE; } pip = lua_newuserdata (L, sizeof (struct rspamd_lua_ip *)); -- 2.39.5