/*** * function trie.create(patterns) * Creates new trie data structure * @param {table} array of string patterns * @return {trie} new trie object */ static gint lua_trie_create (lua_State *L) { ac_trie_t *trie, **ptrie; ac_trie_pat_t *pat; gint npat = 0; gsize sz; if (!lua_istable (L, 1)) { msg_err ("lua trie expects array of patterns for now"); lua_pushnil (L); } else { lua_pushvalue (L, 1); lua_pushnil (L); while (lua_next (L, -2) != 0) { if (lua_isstring (L, -1)) { npat ++; } lua_pop (L, 1); } pat = g_new (ac_trie_pat_t, npat); lua_pushnil (L); npat = 0; while (lua_next (L, -2) != 0) { if (lua_isstring (L, -1)) { pat[npat].ptr = lua_tolstring (L, -1, &sz); pat[npat].len = sz; npat ++; } lua_pop (L, 1); } lua_pop (L, 1); /* table */ trie = acism_create (pat, npat); ptrie = lua_newuserdata (L, sizeof (ac_trie_t *)); rspamd_lua_setclass (L, "rspamd{trie}", -1); *ptrie = trie; g_free (pat); } return 1; }
int main(int argc, char **argv) { if (argc < 2 || argc > 4) usage("pattern_file target_file [[-]expected]\ne.g. acism_x patts act.txt -5"); MEMBUF patt = chomp(slurp(argv[1])); if (!patt.ptr) die("cannot read %s", argv[1]); int npatts; MEMREF *pattv = refsplit(patt.ptr, '\n', &npatts); double t = tick(); ACISM *psp = acism_create(pattv, npatts); t = tick() - t; plan_tests(argc < 3 ? 1 : 3); ok(psp, "acism_create(pattv[%d]) compiled, in %.3f secs", npatts, t); acism_dump(psp, PS_ALL, stderr, pattv); #ifdef ACISM_STATS { int i; for (i = 1; i < (int)psstat[0].val; ++i) if (psstat[i].val) fprintf(stderr, "%11llu %s\n", psstat[i].val, psstat[i].name); } #endif//ACISM_STATS diag("state machine saved as acism.tmp"); FILE *fp = FOPEN("acism.tmp", "w"); acism_save(fp, psp); fclose(fp); if (argc > 2) { // Negative count => print match details int expected = argc > 3 ? atoi(argv[3]) : 0; int details = expected < 0; if (details) expected = -expected; FILE* textfp = FOPEN(argv[2], "r"); // REUSE PATTERN FILE AS A TARGET if (!fp) die("cannot open %s", argv[2]); static char buf[1024*1024]; MEMREF text = {buf, 0}; int state = 0; double elapsed = 0, start = tick(); while (0 < (text.len = fread(buf, sizeof*buf, sizeof buf, textfp))) { t = tick(); (void)acism_more(psp, text, (ACISM_ACTION*)on_match, pattv, &state); elapsed += tick() - t; putc('.', stderr); } putc('\n', stderr); fclose(textfp); ok(text.len == 0, "text_file scanned in 1M blocks; read(s) took %.3f secs", tick() - start - elapsed); if (!ok(actual == expected || expected == 0, "%d matches found, in %.3f secs", actual, elapsed)) diag("actual: %d\n", actual); } buffree(patt); free(pattv); acism_destroy(psp); return exit_status(); }