2 * testRegexp.c: simple module for testing regular expressions
4 * See Copyright for the status of this software.
6 * Daniel Veillard <veillard@redhat.com>
10 #ifdef LIBXML_AUTOMATA_ENABLED
13 #include <libxml/tree.h>
14 #include <libxml/xmlautomata.h>
16 static int scanNumber(char **ptr
) {
21 while ((*cur
>= '0') && (*cur
<= '9')) {
22 ret
= ret
* 10 + (*cur
- '0');
30 testRegexpFile(const char *filename
) {
37 xmlAutomataStatePtr states
[1000];
38 xmlRegexpPtr regexp
= NULL
;
39 xmlRegExecCtxtPtr exec
= NULL
;
41 for (i
= 0;i
<1000;i
++)
44 input
= fopen(filename
, "r");
46 xmlGenericError(xmlGenericErrorContext
,
47 "Cannot open %s for reading\n", filename
);
51 am
= xmlNewAutomata();
53 xmlGenericError(xmlGenericErrorContext
,
54 "Cannot create automata\n");
58 states
[0] = xmlAutomataGetInitState(am
);
59 if (states
[0] == NULL
) {
60 xmlGenericError(xmlGenericErrorContext
,
61 "Cannot get start state\n");
68 while (fgets(expr
, 4500, input
) != NULL
) {
74 ((expr
[len
] == '\n') || (expr
[len
] == '\t') ||
75 (expr
[len
] == '\r') || (expr
[len
] == ' '))) len
--;
78 if ((am
!= NULL
) && (expr
[0] == 't') && (expr
[1] == ' ')) {
82 from
= scanNumber(&ptr
);
84 xmlGenericError(xmlGenericErrorContext
,
85 "Bad line %s\n", expr
);
88 if (states
[from
] == NULL
)
89 states
[from
] = xmlAutomataNewState(am
);
91 to
= scanNumber(&ptr
);
93 xmlGenericError(xmlGenericErrorContext
,
94 "Bad line %s\n", expr
);
97 if (states
[to
] == NULL
)
98 states
[to
] = xmlAutomataNewState(am
);
100 xmlAutomataNewTransition(am
, states
[from
], states
[to
],
102 } else if ((am
!= NULL
) && (expr
[0] == 'e') && (expr
[1] == ' ')) {
103 char *ptr
= &expr
[2];
106 from
= scanNumber(&ptr
);
108 xmlGenericError(xmlGenericErrorContext
,
109 "Bad line %s\n", expr
);
112 if (states
[from
] == NULL
)
113 states
[from
] = xmlAutomataNewState(am
);
115 to
= scanNumber(&ptr
);
116 if (states
[to
] == NULL
)
117 states
[to
] = xmlAutomataNewState(am
);
118 xmlAutomataNewEpsilon(am
, states
[from
], states
[to
]);
119 } else if ((am
!= NULL
) && (expr
[0] == 'f') && (expr
[1] == ' ')) {
120 char *ptr
= &expr
[2];
123 state
= scanNumber(&ptr
);
124 if (states
[state
] == NULL
) {
125 xmlGenericError(xmlGenericErrorContext
,
126 "Bad state %d : %s\n", state
, expr
);
129 xmlAutomataSetFinalState(am
, states
[state
]);
130 } else if ((am
!= NULL
) && (expr
[0] == 'c') && (expr
[1] == ' ')) {
131 char *ptr
= &expr
[2];
135 from
= scanNumber(&ptr
);
137 xmlGenericError(xmlGenericErrorContext
,
138 "Bad line %s\n", expr
);
141 if (states
[from
] == NULL
)
142 states
[from
] = xmlAutomataNewState(am
);
144 to
= scanNumber(&ptr
);
146 xmlGenericError(xmlGenericErrorContext
,
147 "Bad line %s\n", expr
);
150 if (states
[to
] == NULL
)
151 states
[to
] = xmlAutomataNewState(am
);
153 min
= scanNumber(&ptr
);
155 xmlGenericError(xmlGenericErrorContext
,
156 "Bad line %s\n", expr
);
160 max
= scanNumber(&ptr
);
162 xmlGenericError(xmlGenericErrorContext
,
163 "Bad line %s\n", expr
);
167 xmlAutomataNewCountTrans(am
, states
[from
], states
[to
],
168 BAD_CAST ptr
, min
, max
, NULL
);
169 } else if ((am
!= NULL
) && (expr
[0] == '-') && (expr
[1] == '-')) {
170 /* end of the automata */
171 regexp
= xmlAutomataCompile(am
);
174 if (regexp
== NULL
) {
175 xmlGenericError(xmlGenericErrorContext
,
176 "Failed to compile the automata");
179 } else if ((expr
[0] == '=') && (expr
[1] == '>')) {
180 if (regexp
== NULL
) {
181 printf("=> failed not compiled\n");
184 exec
= xmlRegNewExecCtxt(regexp
, NULL
, NULL
);
186 ret
= xmlRegExecPushString(exec
, NULL
, NULL
);
189 printf("=> Passed\n");
190 else if ((ret
== 0) || (ret
== -1))
191 printf("=> Failed\n");
193 printf("=> Error\n");
194 xmlRegFreeExecCtxt(exec
);
198 } else if (regexp
!= NULL
) {
200 exec
= xmlRegNewExecCtxt(regexp
, NULL
, NULL
);
201 ret
= xmlRegExecPushString(exec
, BAD_CAST expr
, NULL
);
203 xmlGenericError(xmlGenericErrorContext
,
204 "Unexpected line %s\n", expr
);
210 xmlRegFreeRegexp(regexp
);
212 xmlRegFreeExecCtxt(exec
);
217 int main(int argc
, char **argv
) {
224 xmlAutomataStatePtr start
, cur
;
226 xmlRegExecCtxtPtr exec
;
228 am
= xmlNewAutomata();
229 start
= xmlAutomataGetInitState(am
);
231 /* generate a[ba]*a */
232 cur
= xmlAutomataNewTransition(am
, start
, NULL
, BAD_CAST
"a", NULL
);
233 xmlAutomataNewTransition(am
, cur
, cur
, BAD_CAST
"b", NULL
);
234 xmlAutomataNewTransition(am
, cur
, cur
, BAD_CAST
"a", NULL
);
235 cur
= xmlAutomataNewCountTrans(am
, cur
, NULL
, BAD_CAST
"a", 2, 3, NULL
);
236 xmlAutomataSetFinalState(am
, cur
);
238 /* compile it in a regexp and free the automata */
239 regexp
= xmlAutomataCompile(am
);
242 /* test the regexp */
243 xmlRegexpPrint(stdout
, regexp
);
244 exec
= xmlRegNewExecCtxt(regexp
, NULL
, NULL
);
245 ret
= xmlRegExecPushString(exec
, BAD_CAST
"a", NULL
);
250 ret
=xmlRegExecPushString(exec
, BAD_CAST
"a", NULL
);
255 ret
=xmlRegExecPushString(exec
, BAD_CAST
"b", NULL
);
260 ret
=xmlRegExecPushString(exec
, BAD_CAST
"a", NULL
);
265 ret
=xmlRegExecPushString(exec
, BAD_CAST
"a", NULL
);
270 ret
=xmlRegExecPushString(exec
, BAD_CAST
"a", NULL
);
275 ret
=xmlRegExecPushString(exec
, BAD_CAST
"a", NULL
);
281 ret
= xmlRegExecPushString(exec
, NULL
, NULL
);
287 xmlRegFreeExecCtxt(exec
);
289 /* free the regexp */
290 xmlRegFreeRegexp(regexp
);
294 for (i
= 1;i
< argc
;i
++)
295 testRegexpFile(argv
[i
]);
305 int main(int argc ATTRIBUTE_UNUSED
, char **argv ATTRIBUTE_UNUSED
) {
306 printf("%s : Automata support not compiled in\n", argv
[0]);
309 #endif /* LIBXML_AUTOMATA_ENABLED */