#include "classifiers.h"
#include "cfg_file.h"
#include "stat_internal.h"
+#include "lua/lua_common.h"
+
+struct rspamd_lua_classifier_ctx {
+ gchar *name;
+ gint classify_ref;
+ gint learn_ref;
+};
+
+static GHashTable *lua_classifiers = NULL;
+
+#define msg_err_luacl(...) rspamd_default_log_function (G_LOG_LEVEL_CRITICAL, \
+ "luacl", task->task_pool->tag.uid, \
+ G_STRFUNC, \
+ __VA_ARGS__)
+#define msg_warn_luacl(...) rspamd_default_log_function (G_LOG_LEVEL_WARNING, \
+ "luacl", task->task_pool->tag.uid, \
+ G_STRFUNC, \
+ __VA_ARGS__)
+#define msg_info_luacl(...) rspamd_default_log_function (G_LOG_LEVEL_INFO, \
+ "luacl", task->task_pool->tag.uid, \
+ G_STRFUNC, \
+ __VA_ARGS__)
+#define msg_debug_luacl(...) rspamd_default_log_function (G_LOG_LEVEL_DEBUG, \
+ "luacl", task->task_pool->tag.uid, \
+ G_STRFUNC, \
+ __VA_ARGS__)
gboolean
lua_classifier_init (rspamd_mempool_t *pool,
struct rspamd_classifier *cl)
{
+ struct rspamd_lua_classifier_ctx *ctx;
+ lua_State *L = cl->ctx->cfg->lua_state;
+ gint cb_classify = -1, cb_learn = -1;
+
+ if (lua_classifiers == NULL) {
+ lua_classifiers = g_hash_table_new_full (rspamd_strcase_hash,
+ rspamd_strcase_equal, g_free, g_free);
+ }
+
+ ctx = g_hash_table_lookup (lua_classifiers, cl->subrs->name);
+
+ if (ctx != NULL) {
+ msg_err_pool ("duplicate lua classifier definition: %s",
+ cl->subrs->name);
+
+ return FALSE;
+ }
+
+ lua_getglobal (L, "rspamd_classifiers");
+ if (lua_type (L, -1) != LUA_TTABLE) {
+ msg_err_pool ("cannot register classifier %s: no rspamd_classifier global",
+ cl->subrs->name);
+ lua_pop (L, 1);
+
+ return FALSE;
+ }
+
+ lua_pushstring (L, cl->subrs->name);
+ lua_gettable (L, -2);
+
+ if (lua_type (L, -1) != LUA_TTABLE) {
+ msg_err_pool ("cannot register classifier %s: bad lua type: %s",
+ cl->subrs->name, lua_typename (L, lua_type (L, -1)));
+ lua_pop (L, 2);
+
+ return FALSE;
+ }
+
+ lua_pushstring (L, "classify");
+ lua_gettable (L, -2);
+
+ if (lua_type (L, -1) != LUA_TFUNCTION) {
+ msg_err_pool ("cannot register classifier %s: bad lua type for classify: %s",
+ cl->subrs->name, lua_typename (L, lua_type (L, -1)));
+ lua_pop (L, 3);
+
+ return FALSE;
+ }
+
+ cb_classify = luaL_ref (L, LUA_REGISTRYINDEX);
+
+ lua_pushstring (L, "learn");
+ lua_gettable (L, -2);
+
+ if (lua_type (L, -1) != LUA_TFUNCTION) {
+ msg_err_pool ("cannot register classifier %s: bad lua type for learn: %s",
+ cl->subrs->name, lua_typename (L, lua_type (L, -1)));
+ lua_pop (L, 3);
+
+ return FALSE;
+ }
+
+ cb_learn = luaL_ref (L, LUA_REGISTRYINDEX);
+ lua_pop (L, 2); /* Table + global */
+
+ ctx = g_malloc0 (sizeof (*ctx));
+ ctx->name = g_strdup (cl->subrs->name);
+ ctx->classify_ref = cb_classify;
+ ctx->learn_ref = cb_learn;
cl->cfg->flags |= RSPAMD_FLAG_CLASSIFIER_NO_BACKEND;
+ g_hash_table_insert (lua_classifiers, ctx->name, ctx);
return TRUE;
}