regexp.c (1ea316270f1f75922ac53976d5d8808a41442f46) | regexp.c (f6b74a7d164b5fada266d00e723155a178a4529f) |
---|---|
1/* 2 * regcomp and regexec -- regsub and regerror are elsewhere 3 * 4 * Copyright (c) 1986 by University of Toronto. 5 * Written by Henry Spencer. Not derived from licensed software. 6 * 7 * Permission is granted to anyone to use this software for any 8 * purpose on any computer system, and to redistribute it freely, --- 193 unchanged lines hidden (view full) --- 202 * thing really will compile successfully, and we never have to move the 203 * code and thus invalidate pointers into it. (Note that it has to be in 204 * one piece because free() must be able to free it all.) 205 * 206 * Beware that the optimization-preparation code in here knows about some 207 * of the structure of the compiled regexp. 208 */ 209regexp * | 1/* 2 * regcomp and regexec -- regsub and regerror are elsewhere 3 * 4 * Copyright (c) 1986 by University of Toronto. 5 * Written by Henry Spencer. Not derived from licensed software. 6 * 7 * Permission is granted to anyone to use this software for any 8 * purpose on any computer system, and to redistribute it freely, --- 193 unchanged lines hidden (view full) --- 202 * thing really will compile successfully, and we never have to move the 203 * code and thus invalidate pointers into it. (Note that it has to be in 204 * one piece because free() must be able to free it all.) 205 * 206 * Beware that the optimization-preparation code in here knows about some 207 * of the structure of the compiled regexp. 208 */ 209regexp * |
210regcomp(char *exp) | 210regcomp(exp) 211char *exp; |
211{ | 212{ |
212 regexp *r; 213 char *scan; 214 char *longest; 215 int len; | 213 register regexp *r; 214 register char *scan; 215 register char *longest; 216 register int len; |
216 int flags; 217 218 if (exp == NULL) 219 FAIL("NULL argument"); 220 221 /* First pass: determine size, legality. */ 222 regparse = exp; 223 regnpar = 1; --- 67 unchanged lines hidden (view full) --- 291 * 292 * Caller must absorb opening parenthesis. 293 * 294 * Combining parenthesis handling with the base level of regular expression 295 * is a trifle forced, but the need to tie the tails of the branches to what 296 * follows makes it hard to avoid. 297 */ 298static char * | 217 int flags; 218 219 if (exp == NULL) 220 FAIL("NULL argument"); 221 222 /* First pass: determine size, legality. */ 223 regparse = exp; 224 regnpar = 1; --- 67 unchanged lines hidden (view full) --- 292 * 293 * Caller must absorb opening parenthesis. 294 * 295 * Combining parenthesis handling with the base level of regular expression 296 * is a trifle forced, but the need to tie the tails of the branches to what 297 * follows makes it hard to avoid. 298 */ 299static char * |
299reg(int paren, int *flagp) | 300reg(paren, flagp) 301int paren; /* Parenthesized? */ 302int *flagp; |
300{ | 303{ |
301 char *ret; 302 char *br; 303 char *ender; 304 int parno = 0; | 304 register char *ret; 305 register char *br; 306 register char *ender; 307 register int parno = 0; |
305 int flags; 306 307 *flagp = HASWIDTH; /* Tentatively. */ 308 309 /* Make an OPEN node, if parenthesized. */ 310 if (paren) { 311 if (regnpar >= NSUBEXP) 312 FAIL("too many ()"); --- 48 unchanged lines hidden (view full) --- 361} 362 363/* 364 - regbranch - one alternative of an | operator 365 * 366 * Implements the concatenation operator. 367 */ 368static char * | 308 int flags; 309 310 *flagp = HASWIDTH; /* Tentatively. */ 311 312 /* Make an OPEN node, if parenthesized. */ 313 if (paren) { 314 if (regnpar >= NSUBEXP) 315 FAIL("too many ()"); --- 48 unchanged lines hidden (view full) --- 364} 365 366/* 367 - regbranch - one alternative of an | operator 368 * 369 * Implements the concatenation operator. 370 */ 371static char * |
369regbranch(int *flagp) | 372regbranch(flagp) 373int *flagp; |
370{ | 374{ |
371 char *ret; 372 char *chain; 373 char *latest; | 375 register char *ret; 376 register char *chain; 377 register char *latest; |
374 int flags; 375 376 *flagp = WORST; /* Tentatively. */ 377 378 ret = regnode(BRANCH); 379 chain = NULL; 380 while (*regparse != '\0' && *regparse != '|' && *regparse != ')') { 381 latest = regpiece(&flags); --- 17 unchanged lines hidden (view full) --- 399 * 400 * Note that the branching code sequences used for ? and the general cases 401 * of * and + are somewhat optimized: they use the same NOTHING node as 402 * both the endmarker for their branch list and the body of the last branch. 403 * It might seem that this node could be dispensed with entirely, but the 404 * endmarker role is not redundant. 405 */ 406static char * | 378 int flags; 379 380 *flagp = WORST; /* Tentatively. */ 381 382 ret = regnode(BRANCH); 383 chain = NULL; 384 while (*regparse != '\0' && *regparse != '|' && *regparse != ')') { 385 latest = regpiece(&flags); --- 17 unchanged lines hidden (view full) --- 403 * 404 * Note that the branching code sequences used for ? and the general cases 405 * of * and + are somewhat optimized: they use the same NOTHING node as 406 * both the endmarker for their branch list and the body of the last branch. 407 * It might seem that this node could be dispensed with entirely, but the 408 * endmarker role is not redundant. 409 */ 410static char * |
407regpiece(int *flagp) | 411regpiece(flagp) 412int *flagp; |
408{ | 413{ |
409 char *ret; 410 char op; 411 char *next; | 414 register char *ret; 415 register char op; 416 register char *next; |
412 int flags; 413 414 ret = regatom(&flags); 415 if (ret == NULL) 416 return(NULL); 417 418 op = *regparse; 419 if (!ISMULT(op)) { --- 42 unchanged lines hidden (view full) --- 462 - regatom - the lowest level 463 * 464 * Optimization: gobbles an entire sequence of ordinary characters so that 465 * it can turn them into a single node, which is smaller to store and 466 * faster to run. Backslashed characters are exceptions, each becoming a 467 * separate node; the code is simpler that way and it's not worth fixing. 468 */ 469static char * | 417 int flags; 418 419 ret = regatom(&flags); 420 if (ret == NULL) 421 return(NULL); 422 423 op = *regparse; 424 if (!ISMULT(op)) { --- 42 unchanged lines hidden (view full) --- 467 - regatom - the lowest level 468 * 469 * Optimization: gobbles an entire sequence of ordinary characters so that 470 * it can turn them into a single node, which is smaller to store and 471 * faster to run. Backslashed characters are exceptions, each becoming a 472 * separate node; the code is simpler that way and it's not worth fixing. 473 */ 474static char * |
470regatom(int *flagp) | 475regatom(flagp) 476int *flagp; |
471{ | 477{ |
472 char *ret; | 478 register char *ret; |
473 int flags; 474 475 *flagp = WORST; /* Tentatively. */ 476 477 switch (*regparse++) { 478 case '^': 479 ret = regnode(BOL); 480 break; 481 case '$': 482 ret = regnode(EOL); 483 break; 484 case '.': 485 ret = regnode(ANY); 486 *flagp |= HASWIDTH|SIMPLE; 487 break; 488 case '[': { | 479 int flags; 480 481 *flagp = WORST; /* Tentatively. */ 482 483 switch (*regparse++) { 484 case '^': 485 ret = regnode(BOL); 486 break; 487 case '$': 488 ret = regnode(EOL); 489 break; 490 case '.': 491 ret = regnode(ANY); 492 *flagp |= HASWIDTH|SIMPLE; 493 break; 494 case '[': { |
489 int clss; 490 int classend; | 495 register int clss; 496 register int classend; |
491 492 if (*regparse == '^') { /* Complement of range. */ 493 ret = regnode(ANYBUT); 494 regparse++; 495 } else 496 ret = regnode(ANYOF); 497 if (*regparse == ']' || *regparse == '-') 498 regc(*regparse++); --- 43 unchanged lines hidden (view full) --- 542 if (*regparse == '\0') 543 FAIL("trailing \\"); 544 ret = regnode(EXACTLY); 545 regc(*regparse++); 546 regc('\0'); 547 *flagp |= HASWIDTH|SIMPLE; 548 break; 549 default: { | 497 498 if (*regparse == '^') { /* Complement of range. */ 499 ret = regnode(ANYBUT); 500 regparse++; 501 } else 502 ret = regnode(ANYOF); 503 if (*regparse == ']' || *regparse == '-') 504 regc(*regparse++); --- 43 unchanged lines hidden (view full) --- 548 if (*regparse == '\0') 549 FAIL("trailing \\"); 550 ret = regnode(EXACTLY); 551 regc(*regparse++); 552 regc('\0'); 553 *flagp |= HASWIDTH|SIMPLE; 554 break; 555 default: { |
550 int len; 551 char ender; | 556 register int len; 557 register char ender; |
552 553 regparse--; 554 len = (int) strcspn(regparse, META); 555 if (len <= 0) 556 FAIL("internal disaster"); 557 ender = *(regparse+len); 558 if (len > 1 && ISMULT(ender)) 559 len--; /* Back off clear of ?+* operand. */ --- 12 unchanged lines hidden (view full) --- 572 573 return(ret); 574} 575 576/* 577 - regnode - emit a node 578 */ 579static char * /* Location. */ | 558 559 regparse--; 560 len = (int) strcspn(regparse, META); 561 if (len <= 0) 562 FAIL("internal disaster"); 563 ender = *(regparse+len); 564 if (len > 1 && ISMULT(ender)) 565 len--; /* Back off clear of ?+* operand. */ --- 12 unchanged lines hidden (view full) --- 578 579 return(ret); 580} 581 582/* 583 - regnode - emit a node 584 */ 585static char * /* Location. */ |
580regnode(char op) | 586regnode(op) 587char op; |
581{ | 588{ |
582 char *ret; 583 char *ptr; | 589 register char *ret; 590 register char *ptr; |
584 585 ret = regcode; 586 if (ret == ®dummy) { 587 regsize += 3; 588 return(ret); 589 } 590 591 ptr = ret; --- 4 unchanged lines hidden (view full) --- 596 597 return(ret); 598} 599 600/* 601 - regc - emit (if appropriate) a byte of code 602 */ 603static void | 591 592 ret = regcode; 593 if (ret == ®dummy) { 594 regsize += 3; 595 return(ret); 596 } 597 598 ptr = ret; --- 4 unchanged lines hidden (view full) --- 603 604 return(ret); 605} 606 607/* 608 - regc - emit (if appropriate) a byte of code 609 */ 610static void |
604regc(char b) | 611regc(b) 612char b; |
605{ 606 if (regcode != ®dummy) 607 *regcode++ = b; 608 else 609 regsize++; 610} 611 612/* 613 - reginsert - insert an operator in front of already-emitted operand 614 * 615 * Means relocating the operand. 616 */ 617static void | 613{ 614 if (regcode != ®dummy) 615 *regcode++ = b; 616 else 617 regsize++; 618} 619 620/* 621 - reginsert - insert an operator in front of already-emitted operand 622 * 623 * Means relocating the operand. 624 */ 625static void |
618reginsert(char op, char *opnd) | 626reginsert(op, opnd) 627char op; 628char *opnd; |
619{ | 629{ |
620 char *src; 621 char *dst; 622 char *place; | 630 register char *src; 631 register char *dst; 632 register char *place; |
623 624 if (regcode == ®dummy) { 625 regsize += 3; 626 return; 627 } 628 629 src = regcode; 630 regcode += 3; --- 6 unchanged lines hidden (view full) --- 637 *place++ = '\0'; 638 *place++ = '\0'; 639} 640 641/* 642 - regtail - set the next-pointer at the end of a node chain 643 */ 644static void | 633 634 if (regcode == ®dummy) { 635 regsize += 3; 636 return; 637 } 638 639 src = regcode; 640 regcode += 3; --- 6 unchanged lines hidden (view full) --- 647 *place++ = '\0'; 648 *place++ = '\0'; 649} 650 651/* 652 - regtail - set the next-pointer at the end of a node chain 653 */ 654static void |
645regtail(char *p, char *val) | 655regtail(p, val) 656char *p; 657char *val; |
646{ | 658{ |
647 char *scan; 648 char *temp; 649 int offset; | 659 register char *scan; 660 register char *temp; 661 register int offset; |
650 651 if (p == ®dummy) 652 return; 653 654 /* Find last node. */ 655 scan = p; 656 for (;;) { 657 temp = regnext(scan); --- 9 unchanged lines hidden (view full) --- 667 *(scan+1) = (offset>>8)&0377; 668 *(scan+2) = offset&0377; 669} 670 671/* 672 - regoptail - regtail on operand of first argument; nop if operandless 673 */ 674static void | 662 663 if (p == ®dummy) 664 return; 665 666 /* Find last node. */ 667 scan = p; 668 for (;;) { 669 temp = regnext(scan); --- 9 unchanged lines hidden (view full) --- 679 *(scan+1) = (offset>>8)&0377; 680 *(scan+2) = offset&0377; 681} 682 683/* 684 - regoptail - regtail on operand of first argument; nop if operandless 685 */ 686static void |
675regoptail(char *p, char *val) | 687regoptail(p, val) 688char *p; 689char *val; |
676{ 677 /* "Operandless" and "op != BRANCH" are synonymous in practice. */ 678 if (p == NULL || p == ®dummy || OP(p) != BRANCH) 679 return; 680 regtail(OPERAND(p), val); 681} 682 683/* --- 20 unchanged lines hidden (view full) --- 704void regdump(); 705STATIC char *regprop(); 706#endif 707 708/* 709 - regexec - match a regexp against a string 710 */ 711int | 690{ 691 /* "Operandless" and "op != BRANCH" are synonymous in practice. */ 692 if (p == NULL || p == ®dummy || OP(p) != BRANCH) 693 return; 694 regtail(OPERAND(p), val); 695} 696 697/* --- 20 unchanged lines hidden (view full) --- 718void regdump(); 719STATIC char *regprop(); 720#endif 721 722/* 723 - regexec - match a regexp against a string 724 */ 725int |
712regexec2(regexp *prog, char *string, int notbol) | 726regexec2(prog, string, notbol) 727register regexp *prog; 728register char *string; 729int notbol; |
713{ | 730{ |
714 char *s; | 731 register char *s; |
715 716 /* Be paranoid... */ 717 if (prog == NULL || string == NULL) { 718 regerror("NULL parameter"); 719 return(0); 720 } 721 722 /* Check validity of program. */ --- 40 unchanged lines hidden (view full) --- 763 return(1); 764 } while (*s++ != '\0'); 765 766 /* Failure. */ 767 return(0); 768} 769 770int | 732 733 /* Be paranoid... */ 734 if (prog == NULL || string == NULL) { 735 regerror("NULL parameter"); 736 return(0); 737 } 738 739 /* Check validity of program. */ --- 40 unchanged lines hidden (view full) --- 780 return(1); 781 } while (*s++ != '\0'); 782 783 /* Failure. */ 784 return(0); 785} 786 787int |
771regexec(regexp *prog, char *string) | 788regexec(prog, string) 789register regexp *prog; 790register char *string; |
772{ 773 return regexec2(prog, string, 0); 774} 775 776/* 777 - regtry - try match at specific point 778 */ 779static int /* 0 failure, 1 success */ | 791{ 792 return regexec2(prog, string, 0); 793} 794 795/* 796 - regtry - try match at specific point 797 */ 798static int /* 0 failure, 1 success */ |
780regtry(regexp *prog, char *string) | 799regtry(prog, string) 800regexp *prog; 801char *string; |
781{ | 802{ |
782 int i; 783 char **sp; 784 char **ep; | 803 register int i; 804 register char **sp; 805 register char **ep; |
785 786 reginput = string; 787 regstartp = prog->startp; 788 regendp = prog->endp; 789 790 sp = prog->startp; 791 ep = prog->endp; 792 for (i = NSUBEXP; i > 0; i--) { --- 14 unchanged lines hidden (view full) --- 807 * Conceptually the strategy is simple: check to see whether the current 808 * node matches, call self recursively to see whether the rest matches, 809 * and then act accordingly. In practice we make some effort to avoid 810 * recursion, in particular by going through "ordinary" nodes (that don't 811 * need to know whether the rest of the match failed) by a loop instead of 812 * by recursion. 813 */ 814static int /* 0 failure, 1 success */ | 806 807 reginput = string; 808 regstartp = prog->startp; 809 regendp = prog->endp; 810 811 sp = prog->startp; 812 ep = prog->endp; 813 for (i = NSUBEXP; i > 0; i--) { --- 14 unchanged lines hidden (view full) --- 828 * Conceptually the strategy is simple: check to see whether the current 829 * node matches, call self recursively to see whether the rest matches, 830 * and then act accordingly. In practice we make some effort to avoid 831 * recursion, in particular by going through "ordinary" nodes (that don't 832 * need to know whether the rest of the match failed) by a loop instead of 833 * by recursion. 834 */ 835static int /* 0 failure, 1 success */ |
815regmatch(char *prog) | 836regmatch(prog) 837char *prog; |
816{ | 838{ |
817 char *scan; /* Current node. */ 818 char *next; /* Next node. */ | 839 register char *scan; /* Current node. */ 840 char *next; /* Next node. */ |
819 820 scan = prog; 821#ifdef DEBUG 822 if (scan != NULL && regnarrate) 823 fprintf(stderr, "%s(\n", regprop(scan)); 824#endif 825 while (scan != NULL) { 826#ifdef DEBUG --- 12 unchanged lines hidden (view full) --- 839 return(0); 840 break; 841 case ANY: 842 if (*reginput == '\0') 843 return(0); 844 reginput++; 845 break; 846 case EXACTLY: { | 841 842 scan = prog; 843#ifdef DEBUG 844 if (scan != NULL && regnarrate) 845 fprintf(stderr, "%s(\n", regprop(scan)); 846#endif 847 while (scan != NULL) { 848#ifdef DEBUG --- 12 unchanged lines hidden (view full) --- 861 return(0); 862 break; 863 case ANY: 864 if (*reginput == '\0') 865 return(0); 866 reginput++; 867 break; 868 case EXACTLY: { |
847 int len; 848 char *opnd; | 869 register int len; 870 register char *opnd; |
849 850 opnd = OPERAND(scan); 851 /* Inline the first character, for speed. */ 852 if (*opnd != *reginput) 853 return(0); 854 len = (int) strlen(opnd); 855 if (len > 1 && strncmp(opnd, reginput, len) != 0) 856 return(0); --- 18 unchanged lines hidden (view full) --- 875 case OPEN+2: 876 case OPEN+3: 877 case OPEN+4: 878 case OPEN+5: 879 case OPEN+6: 880 case OPEN+7: 881 case OPEN+8: 882 case OPEN+9: { | 871 872 opnd = OPERAND(scan); 873 /* Inline the first character, for speed. */ 874 if (*opnd != *reginput) 875 return(0); 876 len = (int) strlen(opnd); 877 if (len > 1 && strncmp(opnd, reginput, len) != 0) 878 return(0); --- 18 unchanged lines hidden (view full) --- 897 case OPEN+2: 898 case OPEN+3: 899 case OPEN+4: 900 case OPEN+5: 901 case OPEN+6: 902 case OPEN+7: 903 case OPEN+8: 904 case OPEN+9: { |
883 int no; 884 char *save; | 905 register int no; 906 register char *save; |
885 886 no = OP(scan) - OPEN; 887 save = reginput; 888 889 if (regmatch(next)) { 890 /* 891 * Don't set startp if some later 892 * invocation of the same parentheses --- 11 unchanged lines hidden (view full) --- 904 case CLOSE+2: 905 case CLOSE+3: 906 case CLOSE+4: 907 case CLOSE+5: 908 case CLOSE+6: 909 case CLOSE+7: 910 case CLOSE+8: 911 case CLOSE+9: { | 907 908 no = OP(scan) - OPEN; 909 save = reginput; 910 911 if (regmatch(next)) { 912 /* 913 * Don't set startp if some later 914 * invocation of the same parentheses --- 11 unchanged lines hidden (view full) --- 926 case CLOSE+2: 927 case CLOSE+3: 928 case CLOSE+4: 929 case CLOSE+5: 930 case CLOSE+6: 931 case CLOSE+7: 932 case CLOSE+8: 933 case CLOSE+9: { |
912 int no; 913 char *save; | 934 register int no; 935 register char *save; |
914 915 no = OP(scan) - CLOSE; 916 save = reginput; 917 918 if (regmatch(next)) { 919 /* 920 * Don't set endp if some later 921 * invocation of the same parentheses 922 * already has. 923 */ 924 if (regendp[no] == NULL) 925 regendp[no] = save; 926 return(1); 927 } else 928 return(0); 929 } 930 /* NOTREACHED */ 931 break; 932 case BRANCH: { | 936 937 no = OP(scan) - CLOSE; 938 save = reginput; 939 940 if (regmatch(next)) { 941 /* 942 * Don't set endp if some later 943 * invocation of the same parentheses 944 * already has. 945 */ 946 if (regendp[no] == NULL) 947 regendp[no] = save; 948 return(1); 949 } else 950 return(0); 951 } 952 /* NOTREACHED */ 953 break; 954 case BRANCH: { |
933 char *save; | 955 register char *save; |
934 935 if (OP(next) != BRANCH) /* No choice. */ 936 next = OPERAND(scan); /* Avoid recursion. */ 937 else { 938 do { 939 save = reginput; 940 if (regmatch(OPERAND(scan))) 941 return(1); 942 reginput = save; 943 scan = regnext(scan); 944 } while (scan != NULL && OP(scan) == BRANCH); 945 return(0); 946 /* NOTREACHED */ 947 } 948 } 949 /* NOTREACHED */ 950 break; 951 case STAR: 952 case PLUS: { | 956 957 if (OP(next) != BRANCH) /* No choice. */ 958 next = OPERAND(scan); /* Avoid recursion. */ 959 else { 960 do { 961 save = reginput; 962 if (regmatch(OPERAND(scan))) 963 return(1); 964 reginput = save; 965 scan = regnext(scan); 966 } while (scan != NULL && OP(scan) == BRANCH); 967 return(0); 968 /* NOTREACHED */ 969 } 970 } 971 /* NOTREACHED */ 972 break; 973 case STAR: 974 case PLUS: { |
953 char nextch; 954 int no; 955 char *save; 956 int min; | 975 register char nextch; 976 register int no; 977 register char *save; 978 register int min; |
957 958 /* 959 * Lookahead to avoid useless match attempts 960 * when we know what character comes next. 961 */ 962 nextch = '\0'; 963 if (OP(next) == EXACTLY) 964 nextch = *OPERAND(next); --- 34 unchanged lines hidden (view full) --- 999 regerror("corrupted pointers"); 1000 return(0); 1001} 1002 1003/* 1004 - regrepeat - repeatedly match something simple, report how many 1005 */ 1006static int | 979 980 /* 981 * Lookahead to avoid useless match attempts 982 * when we know what character comes next. 983 */ 984 nextch = '\0'; 985 if (OP(next) == EXACTLY) 986 nextch = *OPERAND(next); --- 34 unchanged lines hidden (view full) --- 1021 regerror("corrupted pointers"); 1022 return(0); 1023} 1024 1025/* 1026 - regrepeat - repeatedly match something simple, report how many 1027 */ 1028static int |
1007regrepeat(char *p) | 1029regrepeat(p) 1030char *p; |
1008{ | 1031{ |
1009 int count = 0; 1010 char *scan; 1011 char *opnd; | 1032 register int count = 0; 1033 register char *scan; 1034 register char *opnd; |
1012 1013 scan = reginput; 1014 opnd = OPERAND(p); 1015 switch (OP(p)) { 1016 case ANY: 1017 count = (int) strlen(scan); 1018 scan += count; 1019 break; --- 24 unchanged lines hidden (view full) --- 1044 1045 return(count); 1046} 1047 1048/* 1049 - regnext - dig the "next" pointer out of a node 1050 */ 1051static char * | 1035 1036 scan = reginput; 1037 opnd = OPERAND(p); 1038 switch (OP(p)) { 1039 case ANY: 1040 count = (int) strlen(scan); 1041 scan += count; 1042 break; --- 24 unchanged lines hidden (view full) --- 1067 1068 return(count); 1069} 1070 1071/* 1072 - regnext - dig the "next" pointer out of a node 1073 */ 1074static char * |
1052regnext(char *p) | 1075regnext(p) 1076register char *p; |
1053{ | 1077{ |
1054 int offset; | 1078 register int offset; |
1055 1056 if (p == ®dummy) 1057 return(NULL); 1058 1059 offset = NEXT(p); 1060 if (offset == 0) 1061 return(NULL); 1062 --- 6 unchanged lines hidden (view full) --- 1069#ifdef DEBUG 1070 1071STATIC char *regprop(); 1072 1073/* 1074 - regdump - dump a regexp onto stdout in vaguely comprehensible form 1075 */ 1076void | 1079 1080 if (p == ®dummy) 1081 return(NULL); 1082 1083 offset = NEXT(p); 1084 if (offset == 0) 1085 return(NULL); 1086 --- 6 unchanged lines hidden (view full) --- 1093#ifdef DEBUG 1094 1095STATIC char *regprop(); 1096 1097/* 1098 - regdump - dump a regexp onto stdout in vaguely comprehensible form 1099 */ 1100void |
1077regdump(regexp *r) | 1101regdump(r) 1102regexp *r; |
1078{ | 1103{ |
1079 char *s; 1080 char op = EXACTLY; /* Arbitrary non-END op. */ 1081 char *next; | 1104 register char *s; 1105 register char op = EXACTLY; /* Arbitrary non-END op. */ 1106 register char *next; |
1082 1083 1084 s = r->program + 1; 1085 while (op != END) { /* While that wasn't END last time... */ 1086 op = OP(s); 1087 printf("%2d%s", s-r->program, regprop(s)); /* Where, what. */ 1088 next = regnext(s); 1089 if (next == NULL) /* Next ptr. */ --- 21 unchanged lines hidden (view full) --- 1111 printf("must have \"%s\"", r->regmust); 1112 printf("\n"); 1113} 1114 1115/* 1116 - regprop - printable representation of opcode 1117 */ 1118static char * | 1107 1108 1109 s = r->program + 1; 1110 while (op != END) { /* While that wasn't END last time... */ 1111 op = OP(s); 1112 printf("%2d%s", s-r->program, regprop(s)); /* Where, what. */ 1113 next = regnext(s); 1114 if (next == NULL) /* Next ptr. */ --- 21 unchanged lines hidden (view full) --- 1136 printf("must have \"%s\"", r->regmust); 1137 printf("\n"); 1138} 1139 1140/* 1141 - regprop - printable representation of opcode 1142 */ 1143static char * |
1119regprop(char *op) | 1144regprop(op) 1145char *op; |
1120{ | 1146{ |
1121 char *p; | 1147 register char *p; |
1122 static char buf[50]; 1123 1124 (void) strcpy(buf, ":"); 1125 1126 switch (OP(op)) { 1127 case BOL: 1128 p = "BOL"; 1129 break; --- 72 unchanged lines hidden (view full) --- 1202 */ 1203#ifdef STRCSPN 1204/* 1205 * strcspn - find length of initial segment of s1 consisting entirely 1206 * of characters not from s2 1207 */ 1208 1209static int | 1148 static char buf[50]; 1149 1150 (void) strcpy(buf, ":"); 1151 1152 switch (OP(op)) { 1153 case BOL: 1154 p = "BOL"; 1155 break; --- 72 unchanged lines hidden (view full) --- 1228 */ 1229#ifdef STRCSPN 1230/* 1231 * strcspn - find length of initial segment of s1 consisting entirely 1232 * of characters not from s2 1233 */ 1234 1235static int |
1210strcspn(char *s1, char *s2) | 1236strcspn(s1, s2) 1237char *s1; 1238char *s2; |
1211{ | 1239{ |
1212 char *scan1; 1213 char *scan2; 1214 int count; | 1240 register char *scan1; 1241 register char *scan2; 1242 register int count; |
1215 1216 count = 0; 1217 for (scan1 = s1; *scan1 != '\0'; scan1++) { 1218 for (scan2 = s2; *scan2 != '\0';) /* ++ moved down. */ 1219 if (*scan1 == *scan2++) 1220 return(count); 1221 count++; 1222 } 1223 return(count); 1224} 1225#endif | 1243 1244 count = 0; 1245 for (scan1 = s1; *scan1 != '\0'; scan1++) { 1246 for (scan2 = s2; *scan2 != '\0';) /* ++ moved down. */ 1247 if (*scan1 == *scan2++) 1248 return(count); 1249 count++; 1250 } 1251 return(count); 1252} 1253#endif |