From: Donald Sharp Date: Wed, 25 Oct 2017 19:06:30 +0000 (-0400) Subject: lua: Initial Lua import X-Git-Tag: frr-7.1-dev~318^2~1 X-Git-Url: https://git.puffer.fish/?a=commitdiff_plain;h=634949aef8ffbd504fe6337a4668de4b9b8b3941;p=mirror%2Ffrr.git lua: Initial Lua import This code sets up the ability to use lua inside of FRR. Signed-off-by: Donald Sharp --- diff --git a/configure.ac b/configure.ac index 32d5756a61..4b848594d9 100755 --- a/configure.ac +++ b/configure.ac @@ -203,7 +203,15 @@ elif test "x${enable_dev_build}" = "xyes"; then AC_C_FLAG([-g3]) AC_C_FLAG([-O0]) fi + if test "x${enable_lua}" = "xyes"; then + AC_CHECK_LIB([lua], [lua_newstate], + [LIBS="$LIBS -llua"]) + AC_DEFINE(HAVE_LUA,,Lua enabled for development) + fi else + if test "x${enable_lua}" = "xyes"; then + AC_MSG_ERROR([Lua is not meant to be built/used outside of development at this time]) + fi if test "z$orig_cflags" = "z"; then AC_C_FLAG([-g]) AC_C_FLAG([-Os], [ @@ -454,6 +462,9 @@ fi AC_ARG_ENABLE([dev_build], AS_HELP_STRING([--enable-dev-build], [build for development])) +AC_ARG_ENABLE([lua], + AS_HELP_STRING([--enable-lua], [Build Lua scripting])) + if test x"${enable_time_check}" != x"no" ; then if test x"${enable_time_check}" = x"yes" -o x"${enable_time_check}" = x ; then AC_DEFINE(CONSUMED_TIME_CHECK,5000000,Consumed Time Check) @@ -1126,6 +1137,7 @@ if test x"$LIBM" = x ; then AC_MSG_WARN([Unable to find working pow function - bgpd may not link]) fi LIBS="$TMPLIBS" + AC_SUBST(LIBM) AC_CHECK_FUNCS([ppoll], [ diff --git a/lib/lua.c b/lib/lua.c new file mode 100644 index 0000000000..3d701a9364 --- /dev/null +++ b/lib/lua.c @@ -0,0 +1,130 @@ +/* + * This file defines the lua interface into + * FRRouting. + * + * Copyright (C) 2016 Cumulus Networks, Inc. + * Donald Sharp + * + * This file is part of FreeRangeRouting (FRR). + * + * FRR is free software; you can redistribute it and/or modify it under the + * terms of the GNU General Public License as published by the Free Software + * Foundation; either version 2, or (at your option) any later version. + * + * FRR is distributed in the hope that it will be useful, but WITHOUT ANY + * WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS + * FOR A PARTICULAR PURPOSE. See the GNU General Public License for more + * details. + * + * You should have received a copy of the GNU General Public License along + * with FRR; see the file COPYING. If not, write to the Free Software + * Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. + */ +#include + +#include + +#if defined(HAVE_LUA) +#include "prefix.h" +#include "lua.h" +#include "log.h" + +static int lua_zlog_debug(lua_State *L) +{ + int debug_lua = 1; + const char *string = lua_tostring(L, 1); + + if (debug_lua) + zlog_debug("%s", string); + + return 0; +} + +const char *get_string(lua_State *L, const char *key) +{ + const char *str; + + lua_pushstring(L, key); + lua_gettable(L, -2); + + str = (const char *)lua_tostring(L, -1); + lua_pop(L, 1); + + return str; +} + +int get_integer(lua_State *L, const char *key) +{ + int result; + + lua_pushstring(L, key); + lua_gettable(L, -2); + + result = lua_tointeger(L, -1); + lua_pop(L, 1); + + return result; +} + +static void *lua_alloc(void *ud, void *ptr, size_t osize, + size_t nsize) +{ + (void)ud; (void)osize; /* not used */ + if (nsize == 0) { + free(ptr); + return NULL; + } else + return realloc(ptr, nsize); +} + +lua_State *lua_initialize(const char *file) +{ + int status; + lua_State *L = lua_newstate(lua_alloc, NULL); + + zlog_debug("Newstate: %p", L); + luaL_openlibs(L); + zlog_debug("Opened lib"); + status = luaL_loadfile(L, file); + if (status) { + zlog_debug("Failure to open %s %d", file, status); + lua_close(L); + return NULL; + } + + lua_pcall(L, 0, LUA_MULTRET, 0); + zlog_debug("Setting global function"); + lua_pushcfunction(L, lua_zlog_debug); + lua_setglobal(L, "zlog_debug"); + + return L; +} + +void lua_setup_prefix_table(lua_State *L, const struct prefix *prefix) +{ + char buffer[100]; + + lua_newtable(L); + lua_pushstring(L, prefix2str(prefix, buffer, 100)); + lua_setfield(L, -2, "route"); + lua_pushinteger(L, prefix->family); + lua_setfield(L, -2, "family"); + lua_setglobal(L, "prefix"); +} + +enum lua_rm_status lua_run_rm_rule(lua_State *L, const char *rule) +{ + int status; + + lua_getglobal(L, rule); + status = lua_pcall(L, 0, 1, 0); + if (status) { + zlog_debug("Executing Failure with function: %s: %d", + rule, status); + return LUA_RM_FAILURE; + } + + status = lua_tonumber(L, -1); + return status; +} +#endif diff --git a/lib/lua.h b/lib/lua.h new file mode 100644 index 0000000000..8020a22711 --- /dev/null +++ b/lib/lua.h @@ -0,0 +1,79 @@ +/* + * This file defines the lua interface into + * FRRouting. + * + * Copyright (C) 2016 Cumulus Networks, Inc. + * Donald Sharp + * + * This file is part of FreeRangeRouting (FRR). + * + * FRR is free software; you can redistribute it and/or modify it under the + * terms of the GNU General Public License as published by the Free Software + * Foundation; either version 2, or (at your option) any later version. + * + * FRR is distributed in the hope that it will be useful, but WITHOUT ANY + * WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS + * FOR A PARTICULAR PURPOSE. See the GNU General Public License for more + * details. + * + * You should have received a copy of the GNU General Public License along + * with FRR; see the file COPYING. If not, write to the Free Software + * Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. + */ +#ifndef __LUA_H__ +#define __LUA_H__ + +#if defined(HAVE_LUA) + +#include +#include +#include + +/* + * These functions are helper functions that + * try to glom some of the lua_XXX functionality + * into what we actually need, instead of having + * to make multiple calls to set up what + * we want + */ +enum lua_rm_status { + /* + * Script function run failure. This will translate into a + * deny + */ + LUA_RM_FAILURE = 0, + /* + * No Match was found for the route map function + */ + LUA_RM_NOMATCH, + /* + * Match was found but no changes were made to the + * incoming data. + */ + LUA_RM_MATCH, + /* + * Match was found and data was modified, so + * figure out what changed + */ + LUA_RM_MATCH_AND_CHANGE, +}; + +/* + * Open up the lua.scr file and parse + * initial global values, if any. + */ +lua_State *lua_initialize(const char *file); + +void lua_setup_prefix_table(lua_State *L, const struct prefix *prefix); + +enum lua_rm_status lua_run_rm_rule(lua_State *L, const char *rule); + +/* + * Get particular string/integer information + * from a table. It is *assumed* that + * the table has already been selected + */ +const char *get_string(lua_State *L, const char *key); +int get_integer(lua_State *L, const char *key); +#endif +#endif diff --git a/lib/subdir.am b/lib/subdir.am index 499bb94920..6dc2fc529e 100644 --- a/lib/subdir.am +++ b/lib/subdir.am @@ -82,6 +82,7 @@ lib_libfrr_la_SOURCES = \ lib/workqueue.c \ lib/zclient.c \ lib/logicalrouter.c \ + lib/lua.c \ # end vtysh_scan += \ @@ -190,6 +191,7 @@ pkginclude_HEADERS += \ lib/zclient.h \ lib/zebra.h \ lib/logicalrouter.h \ + lib/lua.h \ lib/pbr.h \ # end