aboutsummaryrefslogtreecommitdiff
path: root/src/regex/test_regex_iterate_api.c
diff options
context:
space:
mode:
Diffstat (limited to 'src/regex/test_regex_iterate_api.c')
-rw-r--r--src/regex/test_regex_iterate_api.c270
1 files changed, 137 insertions, 133 deletions
diff --git a/src/regex/test_regex_iterate_api.c b/src/regex/test_regex_iterate_api.c
index 7711a1154..e7ef72b58 100644
--- a/src/regex/test_regex_iterate_api.c
+++ b/src/regex/test_regex_iterate_api.c
@@ -41,7 +41,8 @@
41 41
42static unsigned int transition_counter; 42static unsigned int transition_counter;
43 43
44struct IteratorContext { 44struct IteratorContext
45{
45 int error; 46 int error;
46 int should_save_graph; 47 int should_save_graph;
47 FILE *graph_filep; 48 FILE *graph_filep;
@@ -50,7 +51,8 @@ struct IteratorContext {
50 unsigned int match_count; 51 unsigned int match_count;
51}; 52};
52 53
53struct RegexStringPair { 54struct RegexStringPair
55{
54 char *regex; 56 char *regex;
55 unsigned int string_count; 57 unsigned int string_count;
56 char *strings[20]; 58 char *strings[20];
@@ -58,63 +60,63 @@ struct RegexStringPair {
58 60
59 61
60static void 62static void
61key_iterator(void *cls, const struct GNUNET_HashCode *key, 63key_iterator (void *cls, const struct GNUNET_HashCode *key,
62 const char *proof, 64 const char *proof,
63 int accepting, unsigned int num_edges, 65 int accepting, unsigned int num_edges,
64 const struct REGEX_BLOCK_Edge *edges) 66 const struct REGEX_BLOCK_Edge *edges)
65{ 67{
66 unsigned int i; 68 unsigned int i;
67 struct IteratorContext *ctx = cls; 69 struct IteratorContext *ctx = cls;
68 char *out_str; 70 char *out_str;
69 char *state_id = GNUNET_strdup(GNUNET_h2s(key)); 71 char *state_id = GNUNET_strdup (GNUNET_h2s (key));
70 72
71 GNUNET_assert(NULL != proof); 73 GNUNET_assert (NULL != proof);
72 if (GNUNET_YES == ctx->should_save_graph) 74 if (GNUNET_YES == ctx->should_save_graph)
75 {
76 if (GNUNET_YES == accepting)
77 GNUNET_asprintf (&out_str, "\"%s\" [shape=doublecircle]\n", state_id);
78 else
79 GNUNET_asprintf (&out_str, "\"%s\" [shape=circle]\n", state_id);
80 fwrite (out_str, strlen (out_str), 1, ctx->graph_filep);
81 GNUNET_free (out_str);
82
83 for (i = 0; i < num_edges; i++)
73 { 84 {
74 if (GNUNET_YES == accepting) 85 transition_counter++;
75 GNUNET_asprintf(&out_str, "\"%s\" [shape=doublecircle]\n", state_id); 86 GNUNET_asprintf (&out_str, "\"%s\" -> \"%s\" [label = \"%s (%s)\"]\n",
76 else 87 state_id, GNUNET_h2s (&edges[i].destination),
77 GNUNET_asprintf(&out_str, "\"%s\" [shape=circle]\n", state_id); 88 edges[i].label, proof);
78 fwrite(out_str, strlen(out_str), 1, ctx->graph_filep); 89 fwrite (out_str, strlen (out_str), 1, ctx->graph_filep);
79 GNUNET_free(out_str); 90
80 91 GNUNET_free (out_str);
81 for (i = 0; i < num_edges; i++)
82 {
83 transition_counter++;
84 GNUNET_asprintf(&out_str, "\"%s\" -> \"%s\" [label = \"%s (%s)\"]\n",
85 state_id, GNUNET_h2s(&edges[i].destination),
86 edges[i].label, proof);
87 fwrite(out_str, strlen(out_str), 1, ctx->graph_filep);
88
89 GNUNET_free(out_str);
90 }
91 } 92 }
93 }
92 else 94 else
93 { 95 {
94 for (i = 0; i < num_edges; i++) 96 for (i = 0; i < num_edges; i++)
95 transition_counter++; 97 transition_counter++;
96 } 98 }
97 99
98 for (i = 0; i < ctx->string_count; i++) 100 for (i = 0; i < ctx->string_count; i++)
99 { 101 {
100 if (0 == strcmp(proof, ctx->strings[i])) 102 if (0 == strcmp (proof, ctx->strings[i]))
101 ctx->match_count++; 103 ctx->match_count++;
102 } 104 }
103 105
104 if (GNUNET_OK != REGEX_BLOCK_check_proof(proof, strlen(proof), key)) 106 if (GNUNET_OK != REGEX_BLOCK_check_proof (proof, strlen (proof), key))
105 { 107 {
106 ctx->error++; 108 ctx->error++;
107 GNUNET_log(GNUNET_ERROR_TYPE_ERROR, 109 GNUNET_log (GNUNET_ERROR_TYPE_ERROR,
108 "Proof check failed: proof: %s key: %s\n", proof, state_id); 110 "Proof check failed: proof: %s key: %s\n", proof, state_id);
109 } 111 }
110 GNUNET_free(state_id); 112 GNUNET_free (state_id);
111} 113}
112 114
113 115
114int 116int
115main(int argc, char *argv[]) 117main (int argc, char *argv[])
116{ 118{
117 GNUNET_log_setup("test-regex", "WARNING", NULL); 119 GNUNET_log_setup ("test-regex", "WARNING", NULL);
118 120
119 int error; 121 int error;
120 struct REGEX_INTERNAL_Automaton *dfa; 122 struct REGEX_INTERNAL_Automaton *dfa;
@@ -143,115 +145,117 @@ main(int argc, char *argv[])
143 2, { INITIAL_PADDING "abcd:000", INITIAL_PADDING "abcd:101" } }, 145 2, { INITIAL_PADDING "abcd:000", INITIAL_PADDING "abcd:101" } },
144 { INITIAL_PADDING "(x*|(0|1|2)(a|b|c|d)+)", 2, 146 { INITIAL_PADDING "(x*|(0|1|2)(a|b|c|d)+)", 2,
145 { INITIAL_PADDING "xxxxxxxx", INITIAL_PADDING "0abcdbad" } }, 147 { INITIAL_PADDING "xxxxxxxx", INITIAL_PADDING "0abcdbad" } },
146 { INITIAL_PADDING "(0|1)(0|1)23456789ABC", 1, { INITIAL_PADDING "11234567" } }, 148 { INITIAL_PADDING "(0|1)(0|1)23456789ABC", 1,
149 { INITIAL_PADDING "11234567" } },
147 { INITIAL_PADDING "0*123456789ABC*", 3, 150 { INITIAL_PADDING "0*123456789ABC*", 3,
148 { INITIAL_PADDING "00123456", INITIAL_PADDING "00000000", 151 { INITIAL_PADDING "00123456", INITIAL_PADDING "00000000",
149 INITIAL_PADDING "12345678" } }, 152 INITIAL_PADDING "12345678" } },
150 { INITIAL_PADDING "0123456789A*BC", 1, { INITIAL_PADDING "01234567" } }, 153 { INITIAL_PADDING "0123456789A*BC", 1, { INITIAL_PADDING "01234567" } },
151 { "GNUNETVPN000100000IPEX6-fc5a:4e1:c2ba::1", 1, { "GNUNETVPN000100000IPEX6-" } } 154 { "GNUNETVPN000100000IPEX6-fc5a:4e1:c2ba::1", 1,
155 { "GNUNETVPN000100000IPEX6-" } }
152 }; 156 };
153 157
154 const char *graph_start_str = "digraph G {\nrankdir=LR\n"; 158 const char *graph_start_str = "digraph G {\nrankdir=LR\n";
155 const char *graph_end_str = "\n}\n"; 159 const char *graph_end_str = "\n}\n";
156 160
157 for (i = 0; i < 13; i++) 161 for (i = 0; i < 13; i++)
162 {
163 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Iterating DFA for regex %s\n",
164 rxstr[i].regex);
165
166
167 /* Create graph */
168 if (GNUNET_YES == REGEX_INTERNAL_ITERATE_SAVE_DEBUG_GRAPH)
158 { 169 {
159 GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, "Iterating DFA for regex %s\n", 170 GNUNET_asprintf (&filename, "iteration_graph_%u.dot", i);
160 rxstr[i].regex); 171 ctx.graph_filep = fopen (filename, "w");
161 172 if (NULL == ctx.graph_filep)
162 173 {
163 /* Create graph */ 174 GNUNET_log (GNUNET_ERROR_TYPE_WARNING,
164 if (GNUNET_YES == REGEX_INTERNAL_ITERATE_SAVE_DEBUG_GRAPH) 175 "Could not open file %s for saving iteration graph.\n",
165 { 176 filename);
166 GNUNET_asprintf(&filename, "iteration_graph_%u.dot", i); 177 ctx.should_save_graph = GNUNET_NO;
167 ctx.graph_filep = fopen(filename, "w"); 178 }
168 if (NULL == ctx.graph_filep)
169 {
170 GNUNET_log(GNUNET_ERROR_TYPE_WARNING,
171 "Could not open file %s for saving iteration graph.\n",
172 filename);
173 ctx.should_save_graph = GNUNET_NO;
174 }
175 else
176 {
177 ctx.should_save_graph = GNUNET_YES;
178 fwrite(graph_start_str, strlen(graph_start_str), 1, ctx.graph_filep);
179 }
180 GNUNET_free(filename);
181 }
182 else 179 else
183 { 180 {
184 ctx.should_save_graph = GNUNET_NO; 181 ctx.should_save_graph = GNUNET_YES;
185 ctx.graph_filep = NULL; 182 fwrite (graph_start_str, strlen (graph_start_str), 1, ctx.graph_filep);
186 } 183 }
187 184 GNUNET_free (filename);
188 /* Iterate over DFA edges */ 185 }
189 transition_counter = 0; 186 else
190 ctx.string_count = rxstr[i].string_count; 187 {
191 ctx.strings = rxstr[i].strings; 188 ctx.should_save_graph = GNUNET_NO;
192 ctx.match_count = 0; 189 ctx.graph_filep = NULL;
193 dfa =
194 REGEX_INTERNAL_construct_dfa(rxstr[i].regex, strlen(rxstr[i].regex), 0);
195 REGEX_INTERNAL_iterate_all_edges(dfa, key_iterator, &ctx);
196 num_transitions =
197 REGEX_INTERNAL_get_transition_count(dfa) - dfa->start->transition_count;
198
199 if (transition_counter < num_transitions)
200 {
201 GNUNET_log(GNUNET_ERROR_TYPE_ERROR,
202 "Automaton has %d transitions, iterated over %d transitions\n",
203 num_transitions, transition_counter);
204 error += 1;
205 }
206
207 if (ctx.match_count < ctx.string_count)
208 {
209 GNUNET_log(GNUNET_ERROR_TYPE_ERROR,
210 "Missing initial states for regex %s\n", rxstr[i].regex);
211 error += (ctx.string_count - ctx.match_count);
212 }
213 else if (ctx.match_count > ctx.string_count)
214 {
215 GNUNET_log(GNUNET_ERROR_TYPE_ERROR,
216 "Duplicate initial transitions for regex %s\n",
217 rxstr[i].regex);
218 error += (ctx.string_count - ctx.match_count);
219 }
220
221 REGEX_INTERNAL_automaton_destroy(dfa);
222
223 /* Finish graph */
224 if (GNUNET_YES == ctx.should_save_graph)
225 {
226 fwrite(graph_end_str, strlen(graph_end_str), 1, ctx.graph_filep);
227 fclose(ctx.graph_filep);
228 ctx.graph_filep = NULL;
229 ctx.should_save_graph = GNUNET_NO;
230 }
231 } 190 }
232 191
192 /* Iterate over DFA edges */
193 transition_counter = 0;
194 ctx.string_count = rxstr[i].string_count;
195 ctx.strings = rxstr[i].strings;
196 ctx.match_count = 0;
197 dfa =
198 REGEX_INTERNAL_construct_dfa (rxstr[i].regex, strlen (rxstr[i].regex), 0);
199 REGEX_INTERNAL_iterate_all_edges (dfa, key_iterator, &ctx);
200 num_transitions =
201 REGEX_INTERNAL_get_transition_count (dfa) - dfa->start->transition_count;
202
203 if (transition_counter < num_transitions)
204 {
205 GNUNET_log (GNUNET_ERROR_TYPE_ERROR,
206 "Automaton has %d transitions, iterated over %d transitions\n",
207 num_transitions, transition_counter);
208 error += 1;
209 }
210
211 if (ctx.match_count < ctx.string_count)
212 {
213 GNUNET_log (GNUNET_ERROR_TYPE_ERROR,
214 "Missing initial states for regex %s\n", rxstr[i].regex);
215 error += (ctx.string_count - ctx.match_count);
216 }
217 else if (ctx.match_count > ctx.string_count)
218 {
219 GNUNET_log (GNUNET_ERROR_TYPE_ERROR,
220 "Duplicate initial transitions for regex %s\n",
221 rxstr[i].regex);
222 error += (ctx.string_count - ctx.match_count);
223 }
224
225 REGEX_INTERNAL_automaton_destroy (dfa);
226
227 /* Finish graph */
228 if (GNUNET_YES == ctx.should_save_graph)
229 {
230 fwrite (graph_end_str, strlen (graph_end_str), 1, ctx.graph_filep);
231 fclose (ctx.graph_filep);
232 ctx.graph_filep = NULL;
233 ctx.should_save_graph = GNUNET_NO;
234 }
235 }
236
233 237
234 for (i = 0; i < 13; i++) 238 for (i = 0; i < 13; i++)
239 {
240 ctx.string_count = rxstr[i].string_count;
241 ctx.strings = rxstr[i].strings;
242 ctx.match_count = 0;
243
244 dfa =
245 REGEX_INTERNAL_construct_dfa (rxstr[i].regex, strlen (rxstr[i].regex), 0);
246 REGEX_INTERNAL_dfa_add_multi_strides (NULL, dfa, 2);
247 REGEX_INTERNAL_iterate_all_edges (dfa, key_iterator, &ctx);
248
249 if (ctx.match_count < ctx.string_count)
235 { 250 {
236 ctx.string_count = rxstr[i].string_count; 251 GNUNET_log (GNUNET_ERROR_TYPE_ERROR,
237 ctx.strings = rxstr[i].strings; 252 "Missing initial states for regex %s\n", rxstr[i].regex);
238 ctx.match_count = 0; 253 error += (ctx.string_count - ctx.match_count);
239
240 dfa =
241 REGEX_INTERNAL_construct_dfa(rxstr[i].regex, strlen(rxstr[i].regex), 0);
242 REGEX_INTERNAL_dfa_add_multi_strides(NULL, dfa, 2);
243 REGEX_INTERNAL_iterate_all_edges(dfa, key_iterator, &ctx);
244
245 if (ctx.match_count < ctx.string_count)
246 {
247 GNUNET_log(GNUNET_ERROR_TYPE_ERROR,
248 "Missing initial states for regex %s\n", rxstr[i].regex);
249 error += (ctx.string_count - ctx.match_count);
250 }
251
252 REGEX_INTERNAL_automaton_destroy(dfa);
253 } 254 }
254 255
256 REGEX_INTERNAL_automaton_destroy (dfa);
257 }
258
255 error += ctx.error; 259 error += ctx.error;
256 260
257 return error; 261 return error;