]> git.ipfire.org Git - thirdparty/rspamd.git/commitdiff
Support metaoptions in lua configuration.
authorVsevolod Stakhov <vsevolod@highsecure.ru>
Fri, 14 Jun 2013 14:49:37 +0000 (15:49 +0100)
committerVsevolod Stakhov <vsevolod@highsecure.ru>
Fri, 14 Jun 2013 14:49:37 +0000 (15:49 +0100)
src/cfg_xml.c
src/cfg_xml.h
src/lua/lua_cfg_file.c
src/lua/lua_common.c
src/lua/lua_common.h
src/plugins/surbl.c

index cabd4f2430dc0ae5446bc974818565fc0263794c..8307e22a99da4180603d575b53a45d34d62af36f 100644 (file)
@@ -2470,6 +2470,9 @@ check_module_option (const gchar *mname, const gchar *optname, const gchar *data
                        return FALSE;
                }
                break;
+       case MODULE_OPT_TYPE_META:
+               msg_warn ("option %s should be meta option for module %s not an ordinary one", optname, mname);
+               return FALSE;
        }
 
        return TRUE;
index 48eac018da5e5349b9f9fba763f98d3898ee3b91..c4d992c14fc64d0cb679ca277433ce4529be8069 100644 (file)
@@ -43,6 +43,7 @@ enum module_opt_type {
        MODULE_OPT_TYPE_MAP,
        MODULE_OPT_TYPE_SIZE,
        MODULE_OPT_TYPE_FLAG,
+       MODULE_OPT_TYPE_META,
        MODULE_OPT_TYPE_ANY
 };
 
index 433e70fc78cd4ac8c90525b47913fa31db7a559b..be16b42809ca756c30adf30af1cc1856192566d1 100644 (file)
@@ -81,13 +81,13 @@ lua_process_module (lua_State *L, const gchar *param, struct config_file *cfg)
                new_module = TRUE;
        }
 
-       /* Now iterate throught module table */
+       /* Now iterate through module table */
        for (lua_pushnil(L); lua_next(L, -2); lua_pop(L, 1)) {
                /* key - -2, value - -1 */
                name = luaL_checkstring (L, -2);
                if (name != NULL) {
                        lua_check_element (cfg->cfg_pool, name, &cur_opt, &cur);
-                       lua_process_element (cfg, name, cur, -1);
+                       lua_process_element (cfg, name, param, cur, -1, TRUE);
                        g_hash_table_insert (cfg->modules_opts, (gpointer)param, cur_opt);
                }
        }
@@ -184,12 +184,17 @@ lua_process_metric (lua_State *L, const gchar *name, struct config_file *cfg)
 
 /* Process single element */
 void
-lua_process_element (struct config_file *cfg, const gchar *name, struct module_opt *opt, gint idx) 
+lua_process_element (struct config_file *cfg, const gchar *name,
+               const gchar *module_name, struct module_opt *opt, gint idx, gboolean allow_meta)
 {
        lua_State                            *L = cfg->lua_state;
-       gint                            t;
-       double                               *num;
+       gint                                  t;
+       double                              *num;
        gboolean                             *flag;
+       GList                                *module_metas, *cur_meta;
+       struct module_meta_opt              *meta_opt, *new = NULL;
+       const gchar                         *meta_name;
+       struct module_opt                   *new_opt;
        
        t = lua_type (L, idx);
        /* Handle type */
@@ -214,8 +219,47 @@ lua_process_element (struct config_file *cfg, const gchar *name, struct module_o
                        opt->actual_data = memory_pool_strdup (cfg->cfg_pool, name);
                        opt->lua_type = LUA_VAR_FUNCTION;
                        break;
+               case LUA_TTABLE:
+                       /* Handle meta option if possible */
+                       if (!allow_meta) {
+                               msg_warn ("meta options cannot be nested");
+                               return;
+                       }
+                       meta_name = lua_get_table_index_str (L, "name");
+                       /* Meta option should not be handled by a normal option */
+                       opt->lua_type = LUA_VAR_UNKNOWN;
+                       if (meta_name == NULL) {
+                               msg_warn ("table parameters must have 'name' attribute to be defined");
+                       }
+                       else {
+                               module_metas = g_hash_table_lookup (cfg->modules_metas, module_name);
+                               cur_meta = module_metas;
+                               while (cur_meta) {
+                                       meta_opt = cur_meta->data;
+                                       if (g_ascii_strcasecmp (meta_opt->name, module_name) == 0) {
+                                               new = meta_opt;
+                                               break;
+                                       }
+                                       cur_meta = g_list_next (cur_meta);
+                               }
+                               if (new == NULL) {
+                                       new = memory_pool_alloc0 (cfg->cfg_pool, sizeof (struct module_meta_opt));
+                                       module_metas = g_list_prepend (module_metas, new);
+                                       g_hash_table_insert (cfg->modules_metas, (gpointer)module_name, module_metas);
+                               }
+                               /* Now iterate through the table */
+                               for (lua_pushnil(L); lua_next(L, -2); lua_pop(L, 1)) {
+                                       /* 'key' is at index -2 and 'value' is at index -1 */
+                                       /* Key must be a string and value must be a table */
+                                       name = luaL_checkstring (L, -2);
+                                       if (name != NULL) {
+                                               lua_check_element (cfg->cfg_pool, name, &new->options, &new_opt);
+                                               lua_process_element (cfg, name, module_name, new_opt, -1, FALSE);
+                                       }
+                               }
+                       }
+                       break;
                case LUA_TNIL:
-               case LUA_TTABLE: 
                case LUA_TUSERDATA:
                case LUA_TTHREAD:
                case LUA_TLIGHTUSERDATA:
@@ -252,7 +296,7 @@ lua_module_callback (gpointer key, gpointer value, gpointer ud)
                                /* Try to get global variable */
                                lua_getglobal (L, opt->param);
                        }
-                       lua_process_element (cfg, opt->param, opt, -1);
+                       lua_process_element (cfg, opt->param, key, opt, -1, TRUE);
                }
                cur = g_list_next (cur);
        }
index d7922909f685b9fbfb9e1a35986637a4e682cac1..960b73f91706c4540aa7d4a42df469b7503ba93d 100644 (file)
@@ -282,6 +282,21 @@ lua_set_table_index (lua_State * L, const gchar *index, const gchar *value)
        lua_settable (L, -3);
 }
 
+const gchar *
+lua_get_table_index_str (lua_State *L, const gchar *index)
+{
+       const gchar *result;
+
+       lua_pushstring (L, index);
+       lua_gettable (L, -2);
+       if (!lua_isstring (L, -1)) {
+               return NULL;
+       }
+       result = lua_tostring (L, -1);
+       lua_pop (L, 1);
+       return result;
+}
+
 static void
 lua_common_log (GLogLevelFlags level, lua_State *L, const gchar *msg)
 {
index d7a8d18f14ca8cfcfee4364e04282fab6c67e643..d03fba0ce80c3edd46422ae79c3d6229876bf165 100644 (file)
@@ -67,6 +67,11 @@ void lua_setclass (lua_State *L, const gchar *classname, gint objidx);
  */
 void lua_set_table_index (lua_State *L, const gchar *index, const gchar *value);
 
+/**
+ * Get string value of index in a table (return t['index'])
+ */
+const gchar * lua_get_table_index_str (lua_State *L, const gchar *index);
+
 /**
  * Convert classname to string
  */
@@ -140,7 +145,8 @@ double lua_normalizer_func (struct config_file *cfg, long double score, void *pa
 
 /* Config file functions */
 void lua_post_load_config (struct config_file *cfg);
-void lua_process_element (struct config_file *cfg, const gchar *name, struct module_opt *opt, gint idx);
+void lua_process_element (struct config_file *cfg, const gchar *name,
+               const gchar *module_name, struct module_opt *opt, gint idx, gboolean allow_meta);
 gboolean lua_handle_param (struct worker_task *task, gchar *mname, gchar *optname, 
                                                        enum lua_var_type expected_type, gpointer *res);
 gboolean lua_check_condition (struct config_file *cfg, const gchar *condition);
index 1491b1b62fca4f04fcef236dd0598118dec80767..051bf10faf63cdb981ea6af76b579b8e5821db8d 100644 (file)
@@ -92,7 +92,7 @@ exception_insert (gpointer st, gconstpointer key, gpointer value)
 {
        GHashTable                    **t = st;
        gint                            level = 0;
-       const gchar                     *p = key;
+       const gchar                   *p = key;
        f_str_t                        *val;