This is a live mirror of the Perl 5 development currently hosted at https://github.com/perl/perl5
perl 5.002gamma: hints/sco.sh
[perl5.git] / regcomp.c
index 250813c..d120eb7 100644 (file)
--- a/regcomp.c
+++ b/regcomp.c
  * blame Henry for some of the lack of readability.
  */
 
+/* The names of the functions have been changed from regcomp and
+ * regexec to  pregcomp and pregexec in order to avoid conflicts
+ * with the POSIX routines of the same names.
+*/
+
 /*SUPPRESS 112*/
 /*
- * regcomp and regexec -- regsub and regerror are not used in perl
+ * pregcomp and pregexec -- regsub and regerror are not used in perl
  *
  *     Copyright (c) 1986 by University of Toronto.
  *     Written by Henry Spencer.  Not derived from licensed software.
@@ -88,7 +93,7 @@
 #define TRYAGAIN       0x8     /* Weeded out a declaration. */
 
 /*
- * Forward declarations for regcomp()'s friends.
+ * Forward declarations for pregcomp()'s friends.
  */
 
 static char *reg _((I32, I32 *));
@@ -107,7 +112,7 @@ static void regtail _((char *, char *));
 static char* nextchar _((void));
 
 /*
- - regcomp - compile a regular expression into internal code
+ - pregcomp - compile a regular expression into internal code
  *
  * We can't allocate space until we know how big the compiled form will be,
  * but we can't compile it (and thus know how big it is) until we've got a
@@ -122,7 +127,7 @@ static char* nextchar _((void));
  * of the structure of the compiled regexp.  [I'll say.]
  */
 regexp *
-regcomp(exp,xend,pm)
+pregcomp(exp,xend,pm)
 char* exp;
 char* xend;
 PMOP* pm;
@@ -268,10 +273,12 @@ PMOP* pm;
                }
                else    /* single branch is ok */
                    scan = NEXTOPER(scan);
+               continue;
            }
            if (OP(scan) == UNLESSM) {
                curback = -30000;
                scan = regnext(scan);
+               continue;
            }
            if (OP(scan) == EXACTLY) {
                char *t;
@@ -399,7 +406,7 @@ I32 *flagp;
     if (paren) {
        if (*regparse == '?') {
            regparse++;
-           paren = *nextchar();
+           paren = *regparse++;
            ret = NULL;
            switch (paren) {
            case ':':
@@ -414,7 +421,7 @@ I32 *flagp;
                while (*regparse && *regparse != ')')
                    regparse++;
                if (*regparse != ')')
-                   croak("Sequence (?#... not terminated", *regparse);
+                   croak("Sequence (?#... not terminated");
                nextchar();
                *flagp = TRYAGAIN;
                return NULL;
@@ -492,7 +499,7 @@ I32 *flagp;
     }
 
     /* Check for proper termination. */
-    if (paren && *nextchar() != ')') {
+    if (paren && (regparse >= regxend || *nextchar() != ')')) {
        FAIL("unmatched () in regexp");
     } else if (!paren && regparse < regxend) {
        if (*regparse == ')') {
@@ -861,6 +868,15 @@ tryagain:
            goto defchar;
        }
        break;
+
+    case '#':
+       if (regflags & PMf_EXTENDED) {
+           while (regparse < regxend && *regparse != '\n') regparse++;
+           if (regparse < regxend)
+               goto tryagain;
+       }
+       /* FALL THROUGH */
+
     default: {
            register I32 len;
            register char ender;
@@ -958,6 +974,11 @@ tryagain:
                        break;
                    }
                    break;
+               case '#':
+                   if (regflags & PMf_EXTENDED) {
+                       while (p < regxend && *p != '\n') p++;
+                   }
+                   /* FALL THROUGH */
                case ' ': case '\t': case '\n': case '\r': case '\f': case '\v':
                    if (regflags & PMf_EXTENDED) {
                        p++;
@@ -1152,11 +1173,28 @@ nextchar()
 {
     char* retval = regparse++;
 
-    if (regflags & PMf_EXTENDED) {
-       while (isSPACE(*regparse))
+    for (;;) {
+       if (*regparse == '(' && regparse[1] == '?' &&
+               regparse[2] == '#') {
+           while (*regparse && *regparse != ')')
+               regparse++;
            regparse++;
+           continue;
+       }
+       if (regflags & PMf_EXTENDED) {
+           if (isSPACE(*regparse)) {
+               regparse++;
+               continue;
+           }
+           else if (*regparse == '#') {
+               while (*regparse && *regparse != '\n')
+                   regparse++;
+               regparse++;
+               continue;
+           }
+       }
+       return retval;
     }
-    return retval;
 }
 
 /*
@@ -1588,7 +1626,7 @@ char *op;
 #endif /* DEBUGGING */
 
 void
-regfree(r)
+pregfree(r)
 struct regexp *r;
 {
     if (!r)