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

Diff of /code/trunk/pcre_compile.c

Parent Directory Parent Directory | Revision Log Revision Log | View Patch Patch

revision 1364 by ph10, Sat Oct 5 15:45:11 2013 UTC revision 1365 by ph10, Sun Oct 6 18:33:56 2013 UTC
# Line 1524  for (;;) Line 1524  for (;;)
1524    
1525      case OP_CALLOUT:      case OP_CALLOUT:
1526      case OP_CREF:      case OP_CREF:
1527      case OP_NCREF:      case OP_DNCREF:
1528      case OP_RREF:      case OP_RREF:
1529      case OP_NRREF:      case OP_DNRREF:
1530      case OP_DEF:      case OP_DEF:
1531      code += PRIV(OP_lengths)[*code];      code += PRIV(OP_lengths)[*code];
1532      break;      break;
# Line 1663  for (;;) Line 1663  for (;;)
1663      case OP_COMMIT:      case OP_COMMIT:
1664      case OP_CREF:      case OP_CREF:
1665      case OP_DEF:      case OP_DEF:
1666        case OP_DNCREF:
1667        case OP_DNRREF:
1668      case OP_DOLL:      case OP_DOLL:
1669      case OP_DOLLM:      case OP_DOLLM:
1670      case OP_EOD:      case OP_EOD:
1671      case OP_EODN:      case OP_EODN:
1672      case OP_FAIL:      case OP_FAIL:
     case OP_NCREF:  
     case OP_NRREF:  
1673      case OP_NOT_WORD_BOUNDARY:      case OP_NOT_WORD_BOUNDARY:
1674      case OP_PRUNE:      case OP_PRUNE:
1675      case OP_REVERSE:      case OP_REVERSE:
# Line 6030  for (;; ptr++) Line 6030  for (;; ptr++)
6030                 tempptr[2] == CHAR_LESS_THAN_SIGN))                 tempptr[2] == CHAR_LESS_THAN_SIGN))
6031            break;            break;
6032    
6033          /* Most other conditions use OP_CREF (a couple change to OP_RREF          /* Other conditions use OP_CREF/OP_DNCREF/OP_RREF/OP_DNRREF, and all
6034          below), and all need to skip 1+IMM2_SIZE bytes at the start of the group. */          need to skip at least 1+IMM2_SIZE bytes at the start of the group. */
6035    
6036          code[1+LINK_SIZE] = OP_CREF;          code[1+LINK_SIZE] = OP_CREF;
6037          skipbytes = 1+IMM2_SIZE;          skipbytes = 1+IMM2_SIZE;
# Line 6047  for (;; ptr++) Line 6047  for (;; ptr++)
6047            }            }
6048    
6049          /* Check for a test for a named group's having been set, using the Perl          /* Check for a test for a named group's having been set, using the Perl
6050          syntax (?(<name>) or (?('name') */          syntax (?(<name>) or (?('name'), and also allow for the original PCRE
6051            syntax of (?(name) or for (?(+n), (?(-n), and just (?(n). As names may
6052            consist entirely of digits, there is scope for ambiguity. */
6053    
6054          else if (ptr[1] == CHAR_LESS_THAN_SIGN)          else if (ptr[1] == CHAR_LESS_THAN_SIGN)
6055            {            {
# Line 6064  for (;; ptr++) Line 6066  for (;; ptr++)
6066            terminator = CHAR_NULL;            terminator = CHAR_NULL;
6067            if (ptr[1] == CHAR_MINUS || ptr[1] == CHAR_PLUS) refsign = *(++ptr);            if (ptr[1] == CHAR_MINUS || ptr[1] == CHAR_PLUS) refsign = *(++ptr);
6068            }            }
6069    
6070            /* When a name is one of a number of duplicates, a different opcode is
6071            used and it needs more memory. Unfortunately we cannot tell whether a
6072            name is a duplicate in the first pass, so we have to allow for more
6073            memory except when we know it is a relative numerical reference. */
6074    
6075            if (refsign < 0 && lengthptr != NULL) *lengthptr += IMM2_SIZE;
6076    
6077          /* We now expect to read a name; any thing else is an error */          /* We now expect to read a name (possibly all digits); any thing else
6078            is an error. In the case of all digits, also get it as a number. */
6079    
6080          if (!MAX_255(ptr[1]) || (cd->ctypes[ptr[1]] & ctype_word) == 0)          if (!MAX_255(ptr[1]) || (cd->ctypes[ptr[1]] & ctype_word) == 0)
6081            {            {
# Line 6074  for (;; ptr++) Line 6084  for (;; ptr++)
6084            goto FAILED;            goto FAILED;
6085            }            }
6086    
         /* Read the name, but also get it as a number if it's all digits */  
   
6087          recno = 0;          recno = 0;
6088          name = ++ptr;          name = ++ptr;
6089          while (MAX_255(*ptr) && (cd->ctypes[*ptr] & ctype_word) != 0)          while (MAX_255(*ptr) && (cd->ctypes[*ptr] & ctype_word) != 0)
# Line 6086  for (;; ptr++) Line 6094  for (;; ptr++)
6094            }            }
6095          namelen = (int)(ptr - name);          namelen = (int)(ptr - name);
6096    
6097            /* Check the terminator */
6098    
6099          if ((terminator > 0 && *ptr++ != (pcre_uchar)terminator) ||          if ((terminator > 0 && *ptr++ != (pcre_uchar)terminator) ||
6100              *ptr++ != CHAR_RIGHT_PARENTHESIS)              *ptr++ != CHAR_RIGHT_PARENTHESIS)
6101            {            {
# Line 6121  for (;; ptr++) Line 6131  for (;; ptr++)
6131            }            }
6132    
6133          /* Otherwise (did not start with "+" or "-"), start by looking for the          /* Otherwise (did not start with "+" or "-"), start by looking for the
6134          name. If we find a name, add one to the opcode to change OP_CREF or          name. */
6135          OP_RREF into OP_NCREF or OP_NRREF. These behave exactly the same,  
         except they record that the reference was originally to a name. The  
         information is used to check duplicate names. */  
   
6136          slot = cd->name_table;          slot = cd->name_table;
6137          for (i = 0; i < cd->names_found; i++)          for (i = 0; i < cd->names_found; i++)
6138            {            {
# Line 6133  for (;; ptr++) Line 6140  for (;; ptr++)
6140            slot += cd->name_entry_size;            slot += cd->name_entry_size;
6141            }            }
6142    
6143          /* Found the named subpattern */          /* Found the named subpattern. If the name is duplicated, add one to
6144            the opcode to change CREF/RREF into DNCREF/DNRREF and insert
6145            appropriate data values. Otherwise, just insert the unique subpattern
6146            number. */
6147    
6148          if (i < cd->names_found)          if (i < cd->names_found)
6149            {            {
6150            recno = GET2(slot, 0);            int offset = i++;
6151            PUT2(code, 2+LINK_SIZE, recno);            int count = 1;
6152            code[1+LINK_SIZE]++;            recno = GET2(slot, 0);   /* Number from first found */
6153              for (; i < cd->names_found; i++)
6154                {
6155                slot += cd->name_entry_size;
6156                if (STRNCMP_UC_UC(name, slot+IMM2_SIZE, namelen) != 0) break;
6157                count++;
6158                }
6159              if (count > 1)
6160                {
6161                PUT2(code, 2+LINK_SIZE, offset);
6162                PUT2(code, 2+LINK_SIZE+IMM2_SIZE, count);
6163                skipbytes += IMM2_SIZE;
6164                code[1+LINK_SIZE]++;
6165                }
6166              else  /* Not a duplicated name */
6167                {
6168                PUT2(code, 2+LINK_SIZE, recno);
6169                }
6170            }            }
6171    
6172          /* If terminator == CHAR_NULL it means that the name followed directly          /* If terminator == CHAR_NULL it means that the name followed directly
# Line 7829  do { Line 7856  do {
7856       switch (*scode)       switch (*scode)
7857         {         {
7858         case OP_CREF:         case OP_CREF:
7859         case OP_NCREF:         case OP_DNCREF:
7860         case OP_RREF:         case OP_RREF:
7861         case OP_NRREF:         case OP_DNRREF:
7862         case OP_DEF:         case OP_DEF:
7863         return FALSE;         return FALSE;
7864    

Legend:
Removed from v.1364  
changed lines
  Added in v.1365

  ViewVC Help
Powered by ViewVC 1.1.5