summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--grammar/rainerscript.c83
-rw-r--r--grammar/rainerscript.h1
-rw-r--r--runtime/rsconf.c1
-rw-r--r--runtime/ruleset.c34
-rw-r--r--runtime/ruleset.h4
5 files changed, 123 insertions, 0 deletions
diff --git a/grammar/rainerscript.c b/grammar/rainerscript.c
index 558ec78f..d0a97f06 100644
--- a/grammar/rainerscript.c
+++ b/grammar/rainerscript.c
@@ -1862,6 +1862,89 @@ cnfstmtNewLegaAct(char *actline)
done: return cnfstmt;
}
+
+/* (recursively) optimize an expression */
+void
+cnfexprOptimize(struct cnfexpr *expr)
+{
+ struct var r, l; /* memory for subexpression results */
+ es_str_t *estr_r, *estr_l;
+ int convok_r, convok_l;
+ int bMustFree, bMustFree2;
+ long long n_r, n_l;
+
+ dbgprintf("optimize expr %p, type '%c'(%u)\n", expr, expr->nodetype, expr->nodetype);
+ switch(expr->nodetype) {
+ case '&':
+ break;
+ case '+':
+ break;
+ case '-':
+ break;
+ case '*':
+ break;
+ case '/':
+ break;
+ case '%':
+ break;
+ default:DBGPRINTF("expr optimizer error: unknown nodetype %u['%c']\n",
+ (unsigned) expr->nodetype, (char) expr->nodetype);
+ break;
+ }
+
+}
+
+/* (recursively) optimize a statement */
+void
+cnfstmtOptimize(struct cnfstmt *root)
+{
+ struct cnfstmt *stmt, *prevstmt;
+
+ prevstmt = NULL;
+ for(stmt = root ; stmt != NULL ; stmt = stmt->next) {
+dbgprintf("RRRR: stmtOptimize: stmt %p, nodetype %u\n", stmt, stmt->nodetype);
+ switch(stmt->nodetype) {
+ case S_NOP:
+ /* unchain NOPs, first NOP remains (TODO?) */
+ if(prevstmt != NULL) {
+ DBGPRINTF("removing NOP\n");
+ prevstmt->next = stmt->next;
+#warning remove memleak, destruct
+ }
+ break;
+ case S_IF:
+ cnfexprOptimize(stmt->d.s_if.expr);
+ if(stmt->d.s_if.t_then != NULL) {
+ cnfstmtOptimize(stmt->d.s_if.t_then);
+ }
+ if(stmt->d.s_if.t_else != NULL) {
+ cnfstmtOptimize(stmt->d.s_if.t_else);
+ }
+ break;
+ case S_PRIFILT:
+ cnfstmtOptimize(stmt->d.s_prifilt.t_then);
+ break;
+ case S_PROPFILT:
+ cnfstmtOptimize(stmt->d.s_propfilt.t_then);
+ break;
+ case S_SET:
+ cnfexprOptimize(stmt->d.s_set.expr);
+ break;
+ case S_STOP:
+ case S_UNSET:
+ case S_ACT:
+ /* nothing to do */
+ break;
+ default:
+ dbgprintf("error: unknown stmt type %u during optimizer run\n",
+ (unsigned) stmt->nodetype);
+ break;
+ }
+ prevstmt = stmt;
+ }
+}
+
+
struct cnffparamlst *
cnffparamlstNew(struct cnfexpr *expr, struct cnffparamlst *next)
{
diff --git a/grammar/rainerscript.h b/grammar/rainerscript.h
index 1b94ba21..bd29ff85 100644
--- a/grammar/rainerscript.h
+++ b/grammar/rainerscript.h
@@ -307,6 +307,7 @@ struct cnfstmt * cnfstmtNewLegaAct(char *actline);
struct cnfstmt * cnfstmtNewSet(char *var, struct cnfexpr *expr);
struct cnfstmt * cnfstmtNewUnset(char *var);
void cnfstmtDestruct(struct cnfstmt *root);
+void cnfstmtOptimize(struct cnfstmt *root);
char* getFIOPName(unsigned iFIOP);
rsRetVal initRainerscript(void);
void unescapeStr(uchar *s, int len);
diff --git a/runtime/rsconf.c b/runtime/rsconf.c
index 7fe573f6..96118538 100644
--- a/runtime/rsconf.c
+++ b/runtime/rsconf.c
@@ -1234,6 +1234,7 @@ ourConf = loadConf; // TODO: remove, once ourConf is gone!
ABORT_FINALIZE(RS_RET_NO_ACTIONS);
}
tellLexEndParsing();
+ rulesetOptimizeAll(loadConf);
tellCoreConfigLoadDone();
tellModulesConfigLoadDone();
diff --git a/runtime/ruleset.c b/runtime/ruleset.c
index bcccb79d..ea8849e2 100644
--- a/runtime/ruleset.c
+++ b/runtime/ruleset.c
@@ -756,6 +756,40 @@ debugPrintAll(rsconf_t *conf)
RETiRet;
}
+static inline void
+rulesetOptimize(ruleset_t *pRuleset)
+{
+ if(Debug) {
+ dbgprintf("ruleset '%s' before optimization:\n",
+ pRuleset->pszName);
+ rulesetDebugPrint((ruleset_t*) pRuleset);
+ }
+ cnfstmtOptimize(pRuleset->root);
+ if(Debug) {
+ dbgprintf("ruleset '%s' after optimization:\n",
+ pRuleset->pszName);
+ rulesetDebugPrint((ruleset_t*) pRuleset);
+ }
+}
+
+/* helper for rulsetOptimizeAll(), optimizes a single ruleset */
+DEFFUNC_llExecFunc(doRulesetOptimizeAll)
+{
+ rulesetOptimize((ruleset_t*) pData);
+ return RS_RET_OK;
+}
+/* optimize all rulesets
+ */
+rsRetVal
+rulesetOptimizeAll(rsconf_t *conf)
+{
+ DEFiRet;
+ dbgprintf("begin ruleset optimization phase\n");
+ llExecFunc(&(conf->rulesets.llRulesets), doRulesetOptimizeAll, NULL);
+ dbgprintf("ruleset optimization phase finished.\n");
+ RETiRet;
+}
+
/* Create a ruleset-specific "main" queue for this ruleset. If one is already
* defined, an error message is emitted but nothing else is done.
diff --git a/runtime/ruleset.h b/runtime/ruleset.h
index 50c8071e..1f8f948f 100644
--- a/runtime/ruleset.h
+++ b/runtime/ruleset.h
@@ -90,5 +90,9 @@ rulesetGetName(ruleset_t *pRuleset)
}
+/* we will most probably convert this module back to traditional C
+ * calling sequence, so here we go...
+ */
rsRetVal rulesetGetRuleset(rsconf_t *conf, ruleset_t **ppRuleset, uchar *pszName);
+rsRetVal rulesetOptimizeAll(rsconf_t *conf);
#endif /* #ifndef INCLUDED_RULESET_H */