/[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 457 by ph10, Sat Oct 3 16:24:08 2009 UTC revision 472 by ph10, Fri Dec 11 16:42:50 2009 UTC
# Line 343  static const char error_texts[] = Line 343  static const char error_texts[] =
343    "digit expected after (?+\0"    "digit expected after (?+\0"
344    "] is an invalid data character in JavaScript compatibility mode\0"    "] is an invalid data character in JavaScript compatibility mode\0"
345    /* 65 */    /* 65 */
346    "different names for subpatterns of the same number are not allowed";    "different names for subpatterns of the same number are not allowed";
347    
348    
349  /* Table to identify digits and hex digits. This is used when compiling  /* Table to identify digits and hex digits. This is used when compiling
# Line 1102  if (ptr[0] == CHAR_LEFT_PARENTHESIS) Line 1102  if (ptr[0] == CHAR_LEFT_PARENTHESIS)
1102        if (name != NULL && lorn == ptr - thisname &&        if (name != NULL && lorn == ptr - thisname &&
1103            strncmp((const char *)name, (const char *)thisname, lorn) == 0)            strncmp((const char *)name, (const char *)thisname, lorn) == 0)
1104          return *count;          return *count;
1105        term++;        term++;
1106        }        }
1107      }      }
1108    }    }
# Line 1148  for (; *ptr != 0; ptr++) Line 1148  for (; *ptr != 0; ptr++)
1148            break;            break;
1149          }          }
1150        else if (!negate_class && ptr[1] == CHAR_CIRCUMFLEX_ACCENT)        else if (!negate_class && ptr[1] == CHAR_CIRCUMFLEX_ACCENT)
1151          {          {
1152          negate_class = TRUE;          negate_class = TRUE;
1153          ptr++;          ptr++;
1154          }          }
1155        else break;        else break;
1156        }        }
1157    
# Line 1317  for (;;) Line 1317  for (;;)
1317    
1318      case OP_CALLOUT:      case OP_CALLOUT:
1319      case OP_CREF:      case OP_CREF:
1320        case OP_NCREF:
1321      case OP_RREF:      case OP_RREF:
1322        case OP_NRREF:
1323      case OP_DEF:      case OP_DEF:
1324      code += _pcre_OP_lengths[*code];      code += _pcre_OP_lengths[*code];
1325      break;      break;
# Line 1338  for (;;) Line 1340  for (;;)
1340    
1341  /* Scan a branch and compute the fixed length of subject that will match it,  /* Scan a branch and compute the fixed length of subject that will match it,
1342  if the length is fixed. This is needed for dealing with backward assertions.  if the length is fixed. This is needed for dealing with backward assertions.
1343  In UTF8 mode, the result is in characters rather than bytes. The branch is  In UTF8 mode, the result is in characters rather than bytes. The branch is
1344  temporarily terminated with OP_END when this function is called.  temporarily terminated with OP_END when this function is called.
1345    
1346  This function is called when a backward assertion is encountered, so that if it  This function is called when a backward assertion is encountered, so that if it
1347  fails, the error message can point to the correct place in the pattern.  fails, the error message can point to the correct place in the pattern.
1348  However, we cannot do this when the assertion contains subroutine calls,  However, we cannot do this when the assertion contains subroutine calls,
1349  because they can be forward references. We solve this by remembering this case  because they can be forward references. We solve this by remembering this case
1350  and doing the check at the end; a flag specifies which mode we are running in.  and doing the check at the end; a flag specifies which mode we are running in.
1351    
1352  Arguments:  Arguments:
1353    code     points to the start of the pattern (the bracket)    code     points to the start of the pattern (the bracket)
1354    options  the compiling options    options  the compiling options
1355    atend    TRUE if called when the pattern is complete    atend    TRUE if called when the pattern is complete
1356    cd       the "compile data" structure    cd       the "compile data" structure
1357    
1358  Returns:   the fixed length,  Returns:   the fixed length,
1359               or -1 if there is no fixed length,               or -1 if there is no fixed length,
1360               or -2 if \C was encountered               or -2 if \C was encountered
1361               or -3 if an OP_RECURSE item was encountered and atend is FALSE               or -3 if an OP_RECURSE item was encountered and atend is FALSE
# Line 1403  for (;;) Line 1405  for (;;)
1405      cc += 1 + LINK_SIZE;      cc += 1 + LINK_SIZE;
1406      branchlength = 0;      branchlength = 0;
1407      break;      break;
1408    
1409      /* A true recursion implies not fixed length, but a subroutine call may      /* A true recursion implies not fixed length, but a subroutine call may
1410      be OK. If the subroutine is a forward reference, we can't deal with      be OK. If the subroutine is a forward reference, we can't deal with
1411      it until the end of the pattern, so return -3. */      it until the end of the pattern, so return -3. */
1412    
1413      case OP_RECURSE:      case OP_RECURSE:
1414      if (!atend) return -3;      if (!atend) return -3;
1415      cs = ce = (uschar *)cd->start_code + GET(cc, 1);  /* Start subpattern */      cs = ce = (uschar *)cd->start_code + GET(cc, 1);  /* Start subpattern */
1416      do ce += GET(ce, 1); while (*ce == OP_ALT);       /* End subpattern */      do ce += GET(ce, 1); while (*ce == OP_ALT);       /* End subpattern */
1417      if (cc > cs && cc < ce) return -1;                /* Recursion */      if (cc > cs && cc < ce) return -1;                /* Recursion */
1418      d = find_fixedlength(cs + 2, options, atend, cd);      d = find_fixedlength(cs + 2, options, atend, cd);
1419      if (d < 0) return d;      if (d < 0) return d;
1420      branchlength += d;      branchlength += d;
1421      cc += 1 + LINK_SIZE;      cc += 1 + LINK_SIZE;
1422      break;      break;
1423    
1424      /* Skip over assertive subpatterns */      /* Skip over assertive subpatterns */
1425    
# Line 1432  for (;;) Line 1434  for (;;)
1434    
1435      case OP_REVERSE:      case OP_REVERSE:
1436      case OP_CREF:      case OP_CREF:
1437        case OP_NCREF:
1438      case OP_RREF:      case OP_RREF:
1439        case OP_NRREF:
1440      case OP_DEF:      case OP_DEF:
1441      case OP_OPT:      case OP_OPT:
1442      case OP_CALLOUT:      case OP_CALLOUT:
# Line 1455  for (;;) Line 1459  for (;;)
1459      branchlength++;      branchlength++;
1460      cc += 2;      cc += 2;
1461  #ifdef SUPPORT_UTF8  #ifdef SUPPORT_UTF8
1462      if ((options & PCRE_UTF8) != 0 && cc[-1] >= 0xc0)      if ((options & PCRE_UTF8) != 0 && cc[-1] >= 0xc0)
1463        cc += _pcre_utf8_table4[cc[-1] & 0x3f];        cc += _pcre_utf8_table4[cc[-1] & 0x3f];
1464  #endif  #endif
1465      break;      break;
# Line 1467  for (;;) Line 1471  for (;;)
1471      branchlength += GET2(cc,1);      branchlength += GET2(cc,1);
1472      cc += 4;      cc += 4;
1473  #ifdef SUPPORT_UTF8  #ifdef SUPPORT_UTF8
1474      if ((options & PCRE_UTF8) != 0 && cc[-1] >= 0xc0)      if ((options & PCRE_UTF8) != 0 && cc[-1] >= 0xc0)
1475        cc += _pcre_utf8_table4[cc[-1] & 0x3f];        cc += _pcre_utf8_table4[cc[-1] & 0x3f];
1476  #endif  #endif
1477      break;      break;
# Line 1552  for (;;) Line 1556  for (;;)
1556    
1557  /* This little function scans through a compiled pattern until it finds a  /* This little function scans through a compiled pattern until it finds a
1558  capturing bracket with the given number, or, if the number is negative, an  capturing bracket with the given number, or, if the number is negative, an
1559  instance of OP_REVERSE for a lookbehind. The function is global in the C sense  instance of OP_REVERSE for a lookbehind. The function is global in the C sense
1560  so that it can be called from pcre_study() when finding the minimum matching  so that it can be called from pcre_study() when finding the minimum matching
1561  length.  length.
1562    
1563  Arguments:  Arguments:
# Line 1577  for (;;) Line 1581  for (;;)
1581    the table is zero; the actual length is stored in the compiled code. */    the table is zero; the actual length is stored in the compiled code. */
1582    
1583    if (c == OP_XCLASS) code += GET(code, 1);    if (c == OP_XCLASS) code += GET(code, 1);
1584    
1585    /* Handle recursion */    /* Handle recursion */
1586    
1587    else if (c == OP_REVERSE)    else if (c == OP_REVERSE)
1588      {      {
1589      if (number < 0) return (uschar *)code;      if (number < 0) return (uschar *)code;
1590      code += _pcre_OP_lengths[c];      code += _pcre_OP_lengths[c];
1591      }      }
1592    
# Line 1953  for (code = first_significant_code(code Line 1957  for (code = first_significant_code(code
1957      case OP_POSQUERY:      case OP_POSQUERY:
1958      if (utf8 && code[1] >= 0xc0) code += _pcre_utf8_table4[code[1] & 0x3f];      if (utf8 && code[1] >= 0xc0) code += _pcre_utf8_table4[code[1] & 0x3f];
1959      break;      break;
1960    
1961      case OP_UPTO:      case OP_UPTO:
1962      case OP_MINUPTO:      case OP_MINUPTO:
1963      case OP_POSUPTO:      case OP_POSUPTO:
# Line 3911  we set the flag only if there is a liter Line 3915  we set the flag only if there is a liter
3915    
3916        if (repeat_max == 0) goto END_REPEAT;        if (repeat_max == 0) goto END_REPEAT;
3917    
3918        /*--------------------------------------------------------------------*/        /*--------------------------------------------------------------------*/
3919        /* This code is obsolete from release 8.00; the restriction was finally        /* This code is obsolete from release 8.00; the restriction was finally
3920        removed: */        removed: */
3921    
3922        /* All real repeats make it impossible to handle partial matching (maybe        /* All real repeats make it impossible to handle partial matching (maybe
3923        one day we will be able to remove this restriction). */        one day we will be able to remove this restriction). */
3924    
3925        /* if (repeat_max != 1) cd->external_flags |= PCRE_NOPARTIAL; */        /* if (repeat_max != 1) cd->external_flags |= PCRE_NOPARTIAL; */
3926        /*--------------------------------------------------------------------*/        /*--------------------------------------------------------------------*/
3927    
3928        /* Combine the op_type with the repeat_type */        /* Combine the op_type with the repeat_type */
3929    
# Line 4066  we set the flag only if there is a liter Line 4070  we set the flag only if there is a liter
4070          goto END_REPEAT;          goto END_REPEAT;
4071          }          }
4072    
4073        /*--------------------------------------------------------------------*/        /*--------------------------------------------------------------------*/
4074        /* This code is obsolete from release 8.00; the restriction was finally        /* This code is obsolete from release 8.00; the restriction was finally
4075        removed: */        removed: */
4076    
# Line 4074  we set the flag only if there is a liter Line 4078  we set the flag only if there is a liter
4078        one day we will be able to remove this restriction). */        one day we will be able to remove this restriction). */
4079    
4080        /* if (repeat_max != 1) cd->external_flags |= PCRE_NOPARTIAL; */        /* if (repeat_max != 1) cd->external_flags |= PCRE_NOPARTIAL; */
4081        /*--------------------------------------------------------------------*/        /*--------------------------------------------------------------------*/
4082    
4083        if (repeat_min == 0 && repeat_max == -1)        if (repeat_min == 0 && repeat_max == -1)
4084          *code++ = OP_CRSTAR + repeat_type;          *code++ = OP_CRSTAR + repeat_type;
# Line 4389  we set the flag only if there is a liter Line 4393  we set the flag only if there is a liter
4393      if (possessive_quantifier)      if (possessive_quantifier)
4394        {        {
4395        int len;        int len;
4396    
4397        if (*tempcode == OP_TYPEEXACT)        if (*tempcode == OP_TYPEEXACT)
4398          tempcode += _pcre_OP_lengths[*tempcode] +          tempcode += _pcre_OP_lengths[*tempcode] +
4399            ((tempcode[3] == OP_PROP || tempcode[3] == OP_NOTPROP)? 2 : 0);            ((tempcode[3] == OP_PROP || tempcode[3] == OP_NOTPROP)? 2 : 0);
4400    
4401        else if (*tempcode == OP_EXACT || *tempcode == OP_NOTEXACT)        else if (*tempcode == OP_EXACT || *tempcode == OP_NOTEXACT)
4402          {          {
4403          tempcode += _pcre_OP_lengths[*tempcode];          tempcode += _pcre_OP_lengths[*tempcode];
# Line 4401  we set the flag only if there is a liter Line 4405  we set the flag only if there is a liter
4405          if (utf8 && tempcode[-1] >= 0xc0)          if (utf8 && tempcode[-1] >= 0xc0)
4406            tempcode += _pcre_utf8_table4[tempcode[-1] & 0x3f];            tempcode += _pcre_utf8_table4[tempcode[-1] & 0x3f];
4407  #endif  #endif
4408          }          }
4409    
4410        len = code - tempcode;        len = code - tempcode;
4411        if (len > 0) switch (*tempcode)        if (len > 0) switch (*tempcode)
4412          {          {
# Line 4481  we set the flag only if there is a liter Line 4485  we set the flag only if there is a liter
4485              strncmp((char *)name, vn, namelen) == 0)              strncmp((char *)name, vn, namelen) == 0)
4486            {            {
4487            /* Check for open captures before ACCEPT */            /* Check for open captures before ACCEPT */
4488    
4489            if (verbs[i].op == OP_ACCEPT)            if (verbs[i].op == OP_ACCEPT)
4490              {              {
4491              open_capitem *oc;              open_capitem *oc;
4492              cd->had_accept = TRUE;              cd->had_accept = TRUE;
4493              for (oc = cd->open_caps; oc != NULL; oc = oc->next)              for (oc = cd->open_caps; oc != NULL; oc = oc->next)
4494                {                {
4495                *code++ = OP_CLOSE;                *code++ = OP_CLOSE;
4496                PUT2INC(code, 0, oc->number);                PUT2INC(code, 0, oc->number);
4497                }                }
4498              }              }
4499            *code++ = verbs[i].op;            *code++ = verbs[i].op;
4500            break;            break;
4501            }            }
# Line 4654  we set the flag only if there is a liter Line 4658  we set the flag only if there is a liter
4658            }            }
4659    
4660          /* Otherwise (did not start with "+" or "-"), start by looking for the          /* Otherwise (did not start with "+" or "-"), start by looking for the
4661          name. */          name. If we find a name, add one to the opcode to change OP_CREF or
4662            OP_RREF into OP_NCREF or OP_NRREF. These behave exactly the same,
4663            except they record that the reference was originally to a name. The
4664            information is used to check duplicate names. */
4665    
4666          slot = cd->name_table;          slot = cd->name_table;
4667          for (i = 0; i < cd->names_found; i++)          for (i = 0; i < cd->names_found; i++)
# Line 4669  we set the flag only if there is a liter Line 4676  we set the flag only if there is a liter
4676            {            {
4677            recno = GET2(slot, 0);            recno = GET2(slot, 0);
4678            PUT2(code, 2+LINK_SIZE, recno);            PUT2(code, 2+LINK_SIZE, recno);
4679              code[1+LINK_SIZE]++;
4680            }            }
4681    
4682          /* Search the pattern for a forward reference */          /* Search the pattern for a forward reference */
# Line 4677  we set the flag only if there is a liter Line 4685  we set the flag only if there is a liter
4685                          (options & PCRE_EXTENDED) != 0)) > 0)                          (options & PCRE_EXTENDED) != 0)) > 0)
4686            {            {
4687            PUT2(code, 2+LINK_SIZE, i);            PUT2(code, 2+LINK_SIZE, i);
4688              code[1+LINK_SIZE]++;
4689            }            }
4690    
4691          /* If terminator == 0 it means that the name followed directly after          /* If terminator == 0 it means that the name followed directly after
# Line 4878  we set the flag only if there is a liter Line 4887  we set the flag only if there is a liter
4887            is because the number of names, and hence the table size, is computed            is because the number of names, and hence the table size, is computed
4888            in the pre-compile, and it affects various numbers and pointers which            in the pre-compile, and it affects various numbers and pointers which
4889            would all have to be modified, and the compiled code moved down, if            would all have to be modified, and the compiled code moved down, if
4890            duplicates with the same number were omitted from the table. This            duplicates with the same number were omitted from the table. This
4891            doesn't seem worth the hassle. However, *different* names for the            doesn't seem worth the hassle. However, *different* names for the
4892            same number are not permitted. */            same number are not permitted. */
4893    
# Line 4886  we set the flag only if there is a liter Line 4895  we set the flag only if there is a liter
4895              {              {
4896              BOOL dupname = FALSE;              BOOL dupname = FALSE;
4897              slot = cd->name_table;              slot = cd->name_table;
4898    
4899              for (i = 0; i < cd->names_found; i++)              for (i = 0; i < cd->names_found; i++)
4900                {                {
4901                int crc = memcmp(name, slot+2, namelen);                int crc = memcmp(name, slot+2, namelen);
# Line 4900  we set the flag only if there is a liter Line 4909  we set the flag only if there is a liter
4909                      *errorcodeptr = ERR43;                      *errorcodeptr = ERR43;
4910                      goto FAILED;                      goto FAILED;
4911                      }                      }
4912                    else dupname = TRUE;                    else dupname = TRUE;
4913                    }                    }
4914                  else crc = -1;      /* Current name is a substring */                  else crc = -1;      /* Current name is a substring */
4915                  }                  }
4916    
4917                /* Make space in the table and break the loop for an earlier                /* Make space in the table and break the loop for an earlier
4918                name. For a duplicate or later name, carry on. We do this for                name. For a duplicate or later name, carry on. We do this for
4919                duplicates so that in the simple case (when ?(| is not used) they                duplicates so that in the simple case (when ?(| is not used) they
4920                are in order of their numbers. */                are in order of their numbers. */
4921    
4922                if (crc < 0)                if (crc < 0)
4923                  {                  {
4924                  memmove(slot + cd->name_entry_size, slot,                  memmove(slot + cd->name_entry_size, slot,
4925                    (cd->names_found - i) * cd->name_entry_size);                    (cd->names_found - i) * cd->name_entry_size);
4926                  break;                  break;
4927                  }                  }
4928    
4929                /* Continue the loop for a later or duplicate name */                /* Continue the loop for a later or duplicate name */
4930    
4931                slot += cd->name_entry_size;                slot += cd->name_entry_size;
4932                }                }
4933    
4934              /* For non-duplicate names, check for a duplicate number before              /* For non-duplicate names, check for a duplicate number before
4935              adding the new name. */              adding the new name. */
4936    
4937              if (!dupname)              if (!dupname)
4938                {                {
4939                uschar *cslot = cd->name_table;                uschar *cslot = cd->name_table;
# Line 4936  we set the flag only if there is a liter Line 4945  we set the flag only if there is a liter
4945                      {                      {
4946                      *errorcodeptr = ERR65;                      *errorcodeptr = ERR65;
4947                      goto FAILED;                      goto FAILED;
4948                      }                      }
4949                    }                    }
4950                  else i--;                  else i--;
4951                  cslot += cd->name_entry_size;                  cslot += cd->name_entry_size;
4952                  }                  }
4953                }                }
4954    
4955              PUT2(slot, 0, cd->bracount + 1);              PUT2(slot, 0, cd->bracount + 1);
4956              memcpy(slot + 2, name, namelen);              memcpy(slot + 2, name, namelen);
# Line 5122  we set the flag only if there is a liter Line 5131  we set the flag only if there is a liter
5131            if (lengthptr == NULL)            if (lengthptr == NULL)
5132              {              {
5133              *code = OP_END;              *code = OP_END;
5134              if (recno != 0)              if (recno != 0)
5135                called = _pcre_find_bracket(cd->start_code, utf8, recno);                called = _pcre_find_bracket(cd->start_code, utf8, recno);
5136    
5137              /* Forward reference */              /* Forward reference */
# Line 5239  we set the flag only if there is a liter Line 5248  we set the flag only if there is a liter
5248              {              {
5249              cd->external_options = newoptions;              cd->external_options = newoptions;
5250              }              }
5251           else            else
5252              {              {
5253              if ((options & PCRE_IMS) != (newoptions & PCRE_IMS))              if ((options & PCRE_IMS) != (newoptions & PCRE_IMS))
5254                {                {
# Line 5774  int branchfirstbyte, branchreqbyte; Line 5783  int branchfirstbyte, branchreqbyte;
5783  int length;  int length;
5784  int orig_bracount;  int orig_bracount;
5785  int max_bracount;  int max_bracount;
5786    int old_external_options = cd->external_options;
5787  branch_chain bc;  branch_chain bc;
5788    
5789  bc.outer = bcptr;  bc.outer = bcptr;
# Line 5803  if (*code == OP_CBRA) Line 5813  if (*code == OP_CBRA)
5813    capnumber = GET2(code, 1 + LINK_SIZE);    capnumber = GET2(code, 1 + LINK_SIZE);
5814    capitem.number = capnumber;    capitem.number = capnumber;
5815    capitem.next = cd->open_caps;    capitem.next = cd->open_caps;
5816    cd->open_caps = &capitem;    cd->open_caps = &capitem;
5817    }    }
5818    
5819  /* Offset is set zero to mark that this bracket is still open */  /* Offset is set zero to mark that this bracket is still open */
5820    
# Line 5850  for (;;) Line 5860  for (;;)
5860      return FALSE;      return FALSE;
5861      }      }
5862    
5863      /* If the external options have changed during this branch, it means that we
5864      are at the top level, and a leading option setting has been encountered. We
5865      need to re-set the original option values to take account of this so that,
5866      during the pre-compile phase, we know to allow for a re-set at the start of
5867      subsequent branches. */
5868    
5869      if (old_external_options != cd->external_options)
5870        oldims = cd->external_options & PCRE_IMS;
5871    
5872    /* Keep the highest bracket count in case (?| was used and some branch    /* Keep the highest bracket count in case (?| was used and some branch
5873    has fewer than the rest. */    has fewer than the rest. */
5874    
# Line 5900  for (;;) Line 5919  for (;;)
5919    
5920      /* If lookbehind, check that this branch matches a fixed-length string, and      /* If lookbehind, check that this branch matches a fixed-length string, and
5921      put the length into the OP_REVERSE item. Temporarily mark the end of the      put the length into the OP_REVERSE item. Temporarily mark the end of the
5922      branch with OP_END. If the branch contains OP_RECURSE, the result is -3      branch with OP_END. If the branch contains OP_RECURSE, the result is -3
5923      because there may be forward references that we can't check here. Set a      because there may be forward references that we can't check here. Set a
5924      flag to cause another lookbehind check at the end. Why not do it all at the      flag to cause another lookbehind check at the end. Why not do it all at the
5925      end? Because common, erroneous checks are picked up here and the offset of      end? Because common, erroneous checks are picked up here and the offset of
5926      the problem can be shown. */      the problem can be shown. */
5927    
5928      if (lookbehind)      if (lookbehind)
# Line 5914  for (;;) Line 5933  for (;;)
5933        DPRINTF(("fixed length = %d\n", fixed_length));        DPRINTF(("fixed length = %d\n", fixed_length));
5934        if (fixed_length == -3)        if (fixed_length == -3)
5935          {          {
5936          cd->check_lookbehind = TRUE;          cd->check_lookbehind = TRUE;
5937          }          }
5938        else if (fixed_length < 0)        else if (fixed_length < 0)
5939          {          {
5940          *errorcodeptr = (fixed_length == -2)? ERR36 : ERR25;          *errorcodeptr = (fixed_length == -2)? ERR36 : ERR25;
# Line 5949  for (;;) Line 5968  for (;;)
5968          }          }
5969        while (branch_length > 0);        while (branch_length > 0);
5970        }        }
5971    
5972      /* If it was a capturing subpattern, remove it from the chain. */      /* If it was a capturing subpattern, remove it from the chain. */
5973    
5974      if (capnumber > 0) cd->open_caps = cd->open_caps->next;      if (capnumber > 0) cd->open_caps = cd->open_caps->next;
5975    
5976      /* Fill in the ket */      /* Fill in the ket */
# Line 5960  for (;;) Line 5979  for (;;)
5979      PUT(code, 1, code - start_bracket);      PUT(code, 1, code - start_bracket);
5980      code += 1 + LINK_SIZE;      code += 1 + LINK_SIZE;
5981    
5982      /* Resetting option if needed */      /* Reset options if needed. */
5983    
5984      if ((options & PCRE_IMS) != oldims && *ptr == CHAR_RIGHT_PARENTHESIS)      if ((options & PCRE_IMS) != oldims && *ptr == CHAR_RIGHT_PARENTHESIS)
5985        {        {
# Line 6156  do { Line 6175  do {
6175       switch (*scode)       switch (*scode)
6176         {         {
6177         case OP_CREF:         case OP_CREF:
6178           case OP_NCREF:
6179         case OP_RREF:         case OP_RREF:
6180           case OP_NRREF:
6181         case OP_DEF:         case OP_DEF:
6182         return FALSE;         return FALSE;
6183    
# Line 6643  subpattern. */ Line 6664  subpattern. */
6664    
6665  if (errorcode == 0 && re->top_backref > re->top_bracket) errorcode = ERR15;  if (errorcode == 0 && re->top_backref > re->top_bracket) errorcode = ERR15;
6666    
6667  /* If there were any lookbehind assertions that contained OP_RECURSE  /* If there were any lookbehind assertions that contained OP_RECURSE
6668  (recursions or subroutine calls), a flag is set for them to be checked here,  (recursions or subroutine calls), a flag is set for them to be checked here,
6669  because they may contain forward references. Actual recursions can't be fixed  because they may contain forward references. Actual recursions can't be fixed
6670  length, but subroutine calls can. It is done like this so that those without  length, but subroutine calls can. It is done like this so that those without
# Line 6654  length, and set their lengths. */ Line 6675  length, and set their lengths. */
6675  if (cd->check_lookbehind)  if (cd->check_lookbehind)
6676    {    {
6677    uschar *cc = (uschar *)codestart;    uschar *cc = (uschar *)codestart;
6678    
6679    /* Loop, searching for OP_REVERSE items, and process those that do not have    /* Loop, searching for OP_REVERSE items, and process those that do not have
6680    their length set. (Actually, it will also re-process any that have a length    their length set. (Actually, it will also re-process any that have a length
6681    of zero, but that is a pathological case, and it does no harm.) When we find    of zero, but that is a pathological case, and it does no harm.) When we find
6682    one, we temporarily terminate the branch it is in while we scan it. */    one, we temporarily terminate the branch it is in while we scan it. */
6683    
6684    for (cc = (uschar *)_pcre_find_bracket(codestart, utf8, -1);    for (cc = (uschar *)_pcre_find_bracket(codestart, utf8, -1);
6685         cc != NULL;         cc != NULL;
6686         cc = (uschar *)_pcre_find_bracket(cc, utf8, -1))         cc = (uschar *)_pcre_find_bracket(cc, utf8, -1))
6687      {      {
6688      if (GET(cc, 1) == 0)      if (GET(cc, 1) == 0)
6689        {        {
6690        int fixed_length;        int fixed_length;
6691        uschar *be = cc - 1 - LINK_SIZE + GET(cc, -LINK_SIZE);        uschar *be = cc - 1 - LINK_SIZE + GET(cc, -LINK_SIZE);
6692        int end_op = *be;        int end_op = *be;
6693        *be = OP_END;        *be = OP_END;
6694        fixed_length = find_fixedlength(cc, re->options, TRUE, cd);        fixed_length = find_fixedlength(cc, re->options, TRUE, cd);
6695        *be = end_op;        *be = end_op;
# Line 6676  if (cd->check_lookbehind) Line 6697  if (cd->check_lookbehind)
6697        if (fixed_length < 0)        if (fixed_length < 0)
6698          {          {
6699          errorcode = (fixed_length == -2)? ERR36 : ERR25;          errorcode = (fixed_length == -2)? ERR36 : ERR25;
6700          break;          break;
6701          }          }
6702        PUT(cc, 1, fixed_length);        PUT(cc, 1, fixed_length);
6703        }        }
6704      cc += 1 + LINK_SIZE;      cc += 1 + LINK_SIZE;
6705      }      }
6706    }    }
6707    
6708  /* Failed to compile, or error while post-processing */  /* Failed to compile, or error while post-processing */
6709    

Legend:
Removed from v.457  
changed lines
  Added in v.472

  ViewVC Help
Powered by ViewVC 1.1.5