/[pcre]/code/trunk/pcre_printint.c
ViewVC logotype

Contents of /code/trunk/pcre_printint.c

Parent Directory Parent Directory | Revision Log Revision Log


Revision 1045 - (show annotations)
Sun Sep 23 16:50:00 2012 UTC (7 years ago) by ph10
File MIME type: text/plain
File size: 19870 byte(s)
Error occurred while calculating annotation data.
Update character class handling to use new character case information; rework 
\h, \H, \v, and \V to use the same apparatus with centrally defined lists.
1 /*************************************************
2 * Perl-Compatible Regular Expressions *
3 *************************************************/
4
5 /* PCRE is a library of functions to support regular expressions whose syntax
6 and semantics are as close as possible to those of the Perl 5 language.
7
8 Written by Philip Hazel
9 Copyright (c) 1997-2012 University of Cambridge
10
11 -----------------------------------------------------------------------------
12 Redistribution and use in source and binary forms, with or without
13 modification, are permitted provided that the following conditions are met:
14
15 * Redistributions of source code must retain the above copyright notice,
16 this list of conditions and the following disclaimer.
17
18 * Redistributions in binary form must reproduce the above copyright
19 notice, this list of conditions and the following disclaimer in the
20 documentation and/or other materials provided with the distribution.
21
22 * Neither the name of the University of Cambridge nor the names of its
23 contributors may be used to endorse or promote products derived from
24 this software without specific prior written permission.
25
26 THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
27 AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
28 IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
29 ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
30 LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
31 CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
32 SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
33 INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
34 CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
35 ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
36 POSSIBILITY OF SUCH DAMAGE.
37 -----------------------------------------------------------------------------
38 */
39
40
41 /* This module contains a PCRE private debugging function for printing out the
42 internal form of a compiled regular expression, along with some supporting
43 local functions. This source file is used in two places:
44
45 (1) It is #included by pcre_compile.c when it is compiled in debugging mode
46 (PCRE_DEBUG defined in pcre_internal.h). It is not included in production
47 compiles. In this case PCRE_INCLUDED is defined.
48
49 (2) It is also compiled separately and linked with pcretest.c, which can be
50 asked to print out a compiled regex for debugging purposes. */
51
52 #ifndef PCRE_INCLUDED
53
54 #ifdef HAVE_CONFIG_H
55 #include "config.h"
56 #endif
57
58 /* For pcretest program. */
59 #define PRIV(name) name
60
61 /* We have to include pcre_internal.h because we need the internal info for
62 displaying the results of pcre_study() and we also need to know about the
63 internal macros, structures, and other internal data values; pcretest has
64 "inside information" compared to a program that strictly follows the PCRE API.
65
66 Although pcre_internal.h does itself include pcre.h, we explicitly include it
67 here before pcre_internal.h so that the PCRE_EXP_xxx macros get set
68 appropriately for an application, not for building PCRE. */
69
70 #include "pcre.h"
71 #include "pcre_internal.h"
72
73 /* These are the funtions that are contained within. It doesn't seem worth
74 having a separate .h file just for this. */
75
76 #endif /* PCRE_INCLUDED */
77
78 #ifdef PCRE_INCLUDED
79 static /* Keep the following function as private. */
80 #endif
81 #ifdef COMPILE_PCRE8
82 void pcre_printint(pcre *external_re, FILE *f, BOOL print_lengths);
83 #else
84 void pcre16_printint(pcre *external_re, FILE *f, BOOL print_lengths);
85 #endif
86
87 /* Macro that decides whether a character should be output as a literal or in
88 hexadecimal. We don't use isprint() because that can vary from system to system
89 (even without the use of locales) and we want the output always to be the same,
90 for testing purposes. */
91
92 #ifdef EBCDIC
93 #define PRINTABLE(c) ((c) >= 64 && (c) < 255)
94 #else
95 #define PRINTABLE(c) ((c) >= 32 && (c) < 127)
96 #endif
97
98 /* The table of operator names. */
99
100 static const char *priv_OP_names[] = { OP_NAME_LIST };
101
102 /* This table of operator lengths is not actually used by the working code,
103 but its size is needed for a check that ensures it is the correct size for the
104 number of opcodes (thus catching update omissions). */
105
106 static const pcre_uint8 priv_OP_lengths[] = { OP_LENGTHS };
107
108
109
110 /*************************************************
111 * Print single- or multi-byte character *
112 *************************************************/
113
114 static int
115 print_char(FILE *f, pcre_uchar *ptr, BOOL utf)
116 {
117 int c = *ptr;
118
119 #ifndef SUPPORT_UTF
120
121 (void)utf; /* Avoid compiler warning */
122 if (PRINTABLE(c)) fprintf(f, "%c", c);
123 else if (c <= 0xff) fprintf(f, "\\x%02x", c);
124 else fprintf(f, "\\x{%x}", c);
125 return 0;
126
127 #else
128
129 #ifdef COMPILE_PCRE8
130
131 if (!utf || (c & 0xc0) != 0xc0)
132 {
133 if (PRINTABLE(c)) fprintf(f, "%c", c);
134 else if (c < 0x80) fprintf(f, "\\x%02x", c);
135 else fprintf(f, "\\x{%02x}", c);
136 return 0;
137 }
138 else
139 {
140 int i;
141 int a = PRIV(utf8_table4)[c & 0x3f]; /* Number of additional bytes */
142 int s = 6*a;
143 c = (c & PRIV(utf8_table3)[a]) << s;
144 for (i = 1; i <= a; i++)
145 {
146 /* This is a check for malformed UTF-8; it should only occur if the sanity
147 check has been turned off. Rather than swallow random bytes, just stop if
148 we hit a bad one. Print it with \X instead of \x as an indication. */
149
150 if ((ptr[i] & 0xc0) != 0x80)
151 {
152 fprintf(f, "\\X{%x}", c);
153 return i - 1;
154 }
155
156 /* The byte is OK */
157
158 s -= 6;
159 c |= (ptr[i] & 0x3f) << s;
160 }
161 fprintf(f, "\\x{%x}", c);
162 return a;
163 }
164
165 #else
166
167 #ifdef COMPILE_PCRE16
168
169 if (!utf || (c & 0xfc00) != 0xd800)
170 {
171 if (PRINTABLE(c)) fprintf(f, "%c", c);
172 else if (c <= 0x80) fprintf(f, "\\x%02x", c);
173 else fprintf(f, "\\x{%02x}", c);
174 return 0;
175 }
176 else
177 {
178 /* This is a check for malformed UTF-16; it should only occur if the sanity
179 check has been turned off. Rather than swallow a low surrogate, just stop if
180 we hit a bad one. Print it with \X instead of \x as an indication. */
181
182 if ((ptr[1] & 0xfc00) != 0xdc00)
183 {
184 fprintf(f, "\\X{%x}", c);
185 return 0;
186 }
187
188 c = (((c & 0x3ff) << 10) | (ptr[1] & 0x3ff)) + 0x10000;
189 fprintf(f, "\\x{%x}", c);
190 return 1;
191 }
192
193 #endif /* COMPILE_PCRE16 */
194
195 #endif /* COMPILE_PCRE8 */
196
197 #endif /* SUPPORT_UTF */
198 }
199
200 /*************************************************
201 * Print uchar string (regardless of utf) *
202 *************************************************/
203
204 static void
205 print_puchar(FILE *f, PCRE_PUCHAR ptr)
206 {
207 while (*ptr != '\0')
208 {
209 register int c = *ptr++;
210 if (PRINTABLE(c)) fprintf(f, "%c", c); else fprintf(f, "\\x{%x}", c);
211 }
212 }
213
214 /*************************************************
215 * Find Unicode property name *
216 *************************************************/
217
218 static const char *
219 get_ucpname(int ptype, int pvalue)
220 {
221 #ifdef SUPPORT_UCP
222 int i;
223 for (i = PRIV(utt_size) - 1; i >= 0; i--)
224 {
225 if (ptype == PRIV(utt)[i].type && pvalue == PRIV(utt)[i].value) break;
226 }
227 return (i >= 0)? PRIV(utt_names) + PRIV(utt)[i].name_offset : "??";
228 #else
229 /* It gets harder and harder to shut off unwanted compiler warnings. */
230 ptype = ptype * pvalue;
231 return (ptype == pvalue)? "??" : "??";
232 #endif
233 }
234
235
236
237 /*************************************************
238 * Print compiled regex *
239 *************************************************/
240
241 /* Make this function work for a regex with integers either byte order.
242 However, we assume that what we are passed is a compiled regex. The
243 print_lengths flag controls whether offsets and lengths of items are printed.
244 They can be turned off from pcretest so that automatic tests on bytecode can be
245 written that do not depend on the value of LINK_SIZE. */
246
247 #ifdef PCRE_INCLUDED
248 static /* Keep the following function as private. */
249 #endif
250 #ifdef COMPILE_PCRE8
251 void
252 pcre_printint(pcre *external_re, FILE *f, BOOL print_lengths)
253 #else
254 void
255 pcre16_printint(pcre *external_re, FILE *f, BOOL print_lengths)
256 #endif
257 {
258 REAL_PCRE *re = (REAL_PCRE *)external_re;
259 pcre_uchar *codestart, *code;
260 BOOL utf;
261
262 unsigned int options = re->options;
263 int offset = re->name_table_offset;
264 int count = re->name_count;
265 int size = re->name_entry_size;
266
267 if (re->magic_number != MAGIC_NUMBER)
268 {
269 offset = ((offset << 8) & 0xff00) | ((offset >> 8) & 0xff);
270 count = ((count << 8) & 0xff00) | ((count >> 8) & 0xff);
271 size = ((size << 8) & 0xff00) | ((size >> 8) & 0xff);
272 options = ((options << 24) & 0xff000000) |
273 ((options << 8) & 0x00ff0000) |
274 ((options >> 8) & 0x0000ff00) |
275 ((options >> 24) & 0x000000ff);
276 }
277
278 code = codestart = (pcre_uchar *)re + offset + count * size;
279 /* PCRE_UTF16 has the same value as PCRE_UTF8. */
280 utf = (options & PCRE_UTF8) != 0;
281
282 for(;;)
283 {
284 pcre_uchar *ccode;
285 const char *flag = " ";
286 int c;
287 int extra = 0;
288
289 if (print_lengths)
290 fprintf(f, "%3d ", (int)(code - codestart));
291 else
292 fprintf(f, " ");
293
294 switch(*code)
295 {
296 /* ========================================================================== */
297 /* These cases are never obeyed. This is a fudge that causes a compile-
298 time error if the vectors OP_names or OP_lengths, which are indexed
299 by opcode, are not the correct length. It seems to be the only way to do
300 such a check at compile time, as the sizeof() operator does not work in
301 the C preprocessor. */
302
303 case OP_TABLE_LENGTH:
304 case OP_TABLE_LENGTH +
305 ((sizeof(priv_OP_names)/sizeof(const char *) == OP_TABLE_LENGTH) &&
306 (sizeof(priv_OP_lengths) == OP_TABLE_LENGTH)):
307 break;
308 /* ========================================================================== */
309
310 case OP_END:
311 fprintf(f, " %s\n", priv_OP_names[*code]);
312 fprintf(f, "------------------------------------------------------------------\n");
313 return;
314
315 case OP_CHAR:
316 fprintf(f, " ");
317 do
318 {
319 code++;
320 code += 1 + print_char(f, code, utf);
321 }
322 while (*code == OP_CHAR);
323 fprintf(f, "\n");
324 continue;
325
326 case OP_CHARI:
327 fprintf(f, " /i ");
328 do
329 {
330 code++;
331 code += 1 + print_char(f, code, utf);
332 }
333 while (*code == OP_CHARI);
334 fprintf(f, "\n");
335 continue;
336
337 case OP_CBRA:
338 case OP_CBRAPOS:
339 case OP_SCBRA:
340 case OP_SCBRAPOS:
341 if (print_lengths) fprintf(f, "%3d ", GET(code, 1));
342 else fprintf(f, " ");
343 fprintf(f, "%s %d", priv_OP_names[*code], GET2(code, 1+LINK_SIZE));
344 break;
345
346 case OP_BRA:
347 case OP_BRAPOS:
348 case OP_SBRA:
349 case OP_SBRAPOS:
350 case OP_KETRMAX:
351 case OP_KETRMIN:
352 case OP_KETRPOS:
353 case OP_ALT:
354 case OP_KET:
355 case OP_ASSERT:
356 case OP_ASSERT_NOT:
357 case OP_ASSERTBACK:
358 case OP_ASSERTBACK_NOT:
359 case OP_ONCE:
360 case OP_ONCE_NC:
361 case OP_COND:
362 case OP_SCOND:
363 case OP_REVERSE:
364 if (print_lengths) fprintf(f, "%3d ", GET(code, 1));
365 else fprintf(f, " ");
366 fprintf(f, "%s", priv_OP_names[*code]);
367 break;
368
369 case OP_CLOSE:
370 fprintf(f, " %s %d", priv_OP_names[*code], GET2(code, 1));
371 break;
372
373 case OP_CREF:
374 case OP_NCREF:
375 fprintf(f, "%3d %s", GET2(code,1), priv_OP_names[*code]);
376 break;
377
378 case OP_RREF:
379 c = GET2(code, 1);
380 if (c == RREF_ANY)
381 fprintf(f, " Cond recurse any");
382 else
383 fprintf(f, " Cond recurse %d", c);
384 break;
385
386 case OP_NRREF:
387 c = GET2(code, 1);
388 if (c == RREF_ANY)
389 fprintf(f, " Cond nrecurse any");
390 else
391 fprintf(f, " Cond nrecurse %d", c);
392 break;
393
394 case OP_DEF:
395 fprintf(f, " Cond def");
396 break;
397
398 case OP_STARI:
399 case OP_MINSTARI:
400 case OP_POSSTARI:
401 case OP_PLUSI:
402 case OP_MINPLUSI:
403 case OP_POSPLUSI:
404 case OP_QUERYI:
405 case OP_MINQUERYI:
406 case OP_POSQUERYI:
407 flag = "/i";
408 /* Fall through */
409 case OP_STAR:
410 case OP_MINSTAR:
411 case OP_POSSTAR:
412 case OP_PLUS:
413 case OP_MINPLUS:
414 case OP_POSPLUS:
415 case OP_QUERY:
416 case OP_MINQUERY:
417 case OP_POSQUERY:
418 case OP_TYPESTAR:
419 case OP_TYPEMINSTAR:
420 case OP_TYPEPOSSTAR:
421 case OP_TYPEPLUS:
422 case OP_TYPEMINPLUS:
423 case OP_TYPEPOSPLUS:
424 case OP_TYPEQUERY:
425 case OP_TYPEMINQUERY:
426 case OP_TYPEPOSQUERY:
427 fprintf(f, " %s ", flag);
428 if (*code >= OP_TYPESTAR)
429 {
430 fprintf(f, "%s", priv_OP_names[code[1]]);
431 if (code[1] == OP_PROP || code[1] == OP_NOTPROP)
432 {
433 fprintf(f, " %s ", get_ucpname(code[2], code[3]));
434 extra = 2;
435 }
436 }
437 else extra = print_char(f, code+1, utf);
438 fprintf(f, "%s", priv_OP_names[*code]);
439 break;
440
441 case OP_EXACTI:
442 case OP_UPTOI:
443 case OP_MINUPTOI:
444 case OP_POSUPTOI:
445 flag = "/i";
446 /* Fall through */
447 case OP_EXACT:
448 case OP_UPTO:
449 case OP_MINUPTO:
450 case OP_POSUPTO:
451 fprintf(f, " %s ", flag);
452 extra = print_char(f, code + 1 + IMM2_SIZE, utf);
453 fprintf(f, "{");
454 if (*code != OP_EXACT && *code != OP_EXACTI) fprintf(f, "0,");
455 fprintf(f, "%d}", GET2(code,1));
456 if (*code == OP_MINUPTO || *code == OP_MINUPTOI) fprintf(f, "?");
457 else if (*code == OP_POSUPTO || *code == OP_POSUPTOI) fprintf(f, "+");
458 break;
459
460 case OP_TYPEEXACT:
461 case OP_TYPEUPTO:
462 case OP_TYPEMINUPTO:
463 case OP_TYPEPOSUPTO:
464 fprintf(f, " %s", priv_OP_names[code[1 + IMM2_SIZE]]);
465 if (code[1 + IMM2_SIZE] == OP_PROP || code[1 + IMM2_SIZE] == OP_NOTPROP)
466 {
467 fprintf(f, " %s ", get_ucpname(code[1 + IMM2_SIZE + 1],
468 code[1 + IMM2_SIZE + 2]));
469 extra = 2;
470 }
471 fprintf(f, "{");
472 if (*code != OP_TYPEEXACT) fprintf(f, "0,");
473 fprintf(f, "%d}", GET2(code,1));
474 if (*code == OP_TYPEMINUPTO) fprintf(f, "?");
475 else if (*code == OP_TYPEPOSUPTO) fprintf(f, "+");
476 break;
477
478 case OP_NOTI:
479 flag = "/i";
480 /* Fall through */
481 case OP_NOT:
482 fprintf(f, " %s [^", flag);
483 extra = print_char(f, code + 1, utf);
484 fprintf(f, "]");
485 break;
486
487 case OP_NOTSTARI:
488 case OP_NOTMINSTARI:
489 case OP_NOTPOSSTARI:
490 case OP_NOTPLUSI:
491 case OP_NOTMINPLUSI:
492 case OP_NOTPOSPLUSI:
493 case OP_NOTQUERYI:
494 case OP_NOTMINQUERYI:
495 case OP_NOTPOSQUERYI:
496 flag = "/i";
497 /* Fall through */
498
499 case OP_NOTSTAR:
500 case OP_NOTMINSTAR:
501 case OP_NOTPOSSTAR:
502 case OP_NOTPLUS:
503 case OP_NOTMINPLUS:
504 case OP_NOTPOSPLUS:
505 case OP_NOTQUERY:
506 case OP_NOTMINQUERY:
507 case OP_NOTPOSQUERY:
508 fprintf(f, " %s [^", flag);
509 extra = print_char(f, code + 1, utf);
510 fprintf(f, "]%s", priv_OP_names[*code]);
511 break;
512
513 case OP_NOTEXACTI:
514 case OP_NOTUPTOI:
515 case OP_NOTMINUPTOI:
516 case OP_NOTPOSUPTOI:
517 flag = "/i";
518 /* Fall through */
519
520 case OP_NOTEXACT:
521 case OP_NOTUPTO:
522 case OP_NOTMINUPTO:
523 case OP_NOTPOSUPTO:
524 fprintf(f, " %s [^", flag);
525 extra = print_char(f, code + 1 + IMM2_SIZE, utf);
526 fprintf(f, "]{");
527 if (*code != OP_NOTEXACT && *code != OP_NOTEXACTI) fprintf(f, "0,");
528 fprintf(f, "%d}", GET2(code,1));
529 if (*code == OP_NOTMINUPTO || *code == OP_NOTMINUPTOI) fprintf(f, "?");
530 else
531 if (*code == OP_NOTPOSUPTO || *code == OP_NOTPOSUPTOI) fprintf(f, "+");
532 break;
533
534 case OP_RECURSE:
535 if (print_lengths) fprintf(f, "%3d ", GET(code, 1));
536 else fprintf(f, " ");
537 fprintf(f, "%s", priv_OP_names[*code]);
538 break;
539
540 case OP_REFI:
541 flag = "/i";
542 /* Fall through */
543 case OP_REF:
544 fprintf(f, " %s \\%d", flag, GET2(code,1));
545 ccode = code + priv_OP_lengths[*code];
546 goto CLASS_REF_REPEAT;
547
548 case OP_CALLOUT:
549 fprintf(f, " %s %d %d %d", priv_OP_names[*code], code[1], GET(code,2),
550 GET(code, 2 + LINK_SIZE));
551 break;
552
553 case OP_PROP:
554 case OP_NOTPROP:
555 fprintf(f, " %s %s", priv_OP_names[*code], get_ucpname(code[1], code[2]));
556 break;
557
558 /* OP_XCLASS can only occur in UTF or PCRE16 modes. However, there's no
559 harm in having this code always here, and it makes it less messy without
560 all those #ifdefs. */
561
562 case OP_CLASS:
563 case OP_NCLASS:
564 case OP_XCLASS:
565 {
566 int i, min, max;
567 BOOL printmap;
568 pcre_uint8 *map;
569
570 fprintf(f, " [");
571
572 if (*code == OP_XCLASS)
573 {
574 extra = GET(code, 1);
575 ccode = code + LINK_SIZE + 1;
576 printmap = (*ccode & XCL_MAP) != 0;
577 if ((*ccode++ & XCL_NOT) != 0) fprintf(f, "^");
578 }
579 else
580 {
581 printmap = TRUE;
582 ccode = code + 1;
583 }
584
585 /* Print a bit map */
586
587 if (printmap)
588 {
589 map = (pcre_uint8 *)ccode;
590 for (i = 0; i < 256; i++)
591 {
592 if ((map[i/8] & (1 << (i&7))) != 0)
593 {
594 int j;
595 for (j = i+1; j < 256; j++)
596 if ((map[j/8] & (1 << (j&7))) == 0) break;
597 if (i == '-' || i == ']') fprintf(f, "\\");
598 if (PRINTABLE(i)) fprintf(f, "%c", i);
599 else fprintf(f, "\\x%02x", i);
600 if (--j > i)
601 {
602 if (j != i + 1) fprintf(f, "-");
603 if (j == '-' || j == ']') fprintf(f, "\\");
604 if (PRINTABLE(j)) fprintf(f, "%c", j);
605 else fprintf(f, "\\x%02x", j);
606 }
607 i = j;
608 }
609 }
610 ccode += 32 / sizeof(pcre_uchar);
611 }
612
613 /* For an XCLASS there is always some additional data */
614
615 if (*code == OP_XCLASS)
616 {
617 int ch;
618 while ((ch = *ccode++) != XCL_END)
619 {
620 if (ch == XCL_PROP)
621 {
622 int ptype = *ccode++;
623 int pvalue = *ccode++;
624 fprintf(f, "\\p{%s}", get_ucpname(ptype, pvalue));
625 }
626 else if (ch == XCL_NOTPROP)
627 {
628 int ptype = *ccode++;
629 int pvalue = *ccode++;
630 fprintf(f, "\\P{%s}", get_ucpname(ptype, pvalue));
631 }
632 else
633 {
634 ccode += 1 + print_char(f, ccode, utf);
635 if (ch == XCL_RANGE)
636 {
637 fprintf(f, "-");
638 ccode += 1 + print_char(f, ccode, utf);
639 }
640 }
641 }
642 }
643
644 /* Indicate a non-UTF class which was created by negation */
645
646 fprintf(f, "]%s", (*code == OP_NCLASS)? " (neg)" : "");
647
648 /* Handle repeats after a class or a back reference */
649
650 CLASS_REF_REPEAT:
651 switch(*ccode)
652 {
653 case OP_CRSTAR:
654 case OP_CRMINSTAR:
655 case OP_CRPLUS:
656 case OP_CRMINPLUS:
657 case OP_CRQUERY:
658 case OP_CRMINQUERY:
659 fprintf(f, "%s", priv_OP_names[*ccode]);
660 extra += priv_OP_lengths[*ccode];
661 break;
662
663 case OP_CRRANGE:
664 case OP_CRMINRANGE:
665 min = GET2(ccode,1);
666 max = GET2(ccode,1 + IMM2_SIZE);
667 if (max == 0) fprintf(f, "{%d,}", min);
668 else fprintf(f, "{%d,%d}", min, max);
669 if (*ccode == OP_CRMINRANGE) fprintf(f, "?");
670 extra += priv_OP_lengths[*ccode];
671 break;
672
673 /* Do nothing if it's not a repeat; this code stops picky compilers
674 warning about the lack of a default code path. */
675
676 default:
677 break;
678 }
679 }
680 break;
681
682 case OP_MARK:
683 case OP_PRUNE_ARG:
684 case OP_SKIP_ARG:
685 case OP_THEN_ARG:
686 fprintf(f, " %s ", priv_OP_names[*code]);
687 print_puchar(f, code + 2);
688 extra += code[1];
689 break;
690
691 case OP_THEN:
692 fprintf(f, " %s", priv_OP_names[*code]);
693 break;
694
695 case OP_CIRCM:
696 case OP_DOLLM:
697 flag = "/m";
698 /* Fall through */
699
700 /* Anything else is just an item with no data, but possibly a flag. */
701
702 default:
703 fprintf(f, " %s %s", flag, priv_OP_names[*code]);
704 break;
705 }
706
707 code += priv_OP_lengths[*code] + extra;
708 fprintf(f, "\n");
709 }
710 }
711
712 /* End of pcre_printint.src */

  ViewVC Help
Powered by ViewVC 1.1.5