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

Diff of /code/trunk/pcre_exec.c

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

revision 742 by zherczeg, Sun Nov 6 08:05:33 2011 UTC revision 915 by zherczeg, Tue Feb 14 13:05:39 2012 UTC
# Line 6  Line 6 
6  and semantics are as close as possible to those of the Perl 5 language.  and semantics are as close as possible to those of the Perl 5 language.
7    
8                         Written by Philip Hazel                         Written by Philip Hazel
9             Copyright (c) 1997-2011 University of Cambridge             Copyright (c) 1997-2012 University of Cambridge
10    
11  -----------------------------------------------------------------------------  -----------------------------------------------------------------------------
12  Redistribution and use in source and binary forms, with or without  Redistribution and use in source and binary forms, with or without
# Line 82  negative to avoid the external error cod Line 82  negative to avoid the external error cod
82  #define MATCH_SKIP_ARG     (-993)  #define MATCH_SKIP_ARG     (-993)
83  #define MATCH_THEN         (-992)  #define MATCH_THEN         (-992)
84    
 /* This is a convenience macro for code that occurs many times. */  
   
 #define MRRETURN(ra) \  
   { \  
   md->mark = markptr; \  
   RRETURN(ra); \  
   }  
   
85  /* Maximum number of ints of offset to save on the stack for recursive calls.  /* Maximum number of ints of offset to save on the stack for recursive calls.
86  If the offset vector is bigger, malloc is used. This should be a multiple of 3,  If the offset vector is bigger, malloc is used. This should be a multiple of 3,
87  because the offset vector is always a multiple of 3 long. */  because the offset vector is always a multiple of 3 long. */
# Line 121  Returns:     nothing Line 113  Returns:     nothing
113  */  */
114    
115  static void  static void
116  pchars(const uschar *p, int length, BOOL is_subject, match_data *md)  pchars(const pcre_uchar *p, int length, BOOL is_subject, match_data *md)
117  {  {
118  unsigned int c;  unsigned int c;
119  if (is_subject && length > md->end_subject - p) length = md->end_subject - p;  if (is_subject && length > md->end_subject - p) length = md->end_subject - p;
# Line 152  Returns:      < 0 if not matched, otherw Line 144  Returns:      < 0 if not matched, otherw
144  */  */
145    
146  static int  static int
147  match_ref(int offset, register USPTR eptr, int length, match_data *md,  match_ref(int offset, register PCRE_PUCHAR eptr, int length, match_data *md,
148    BOOL caseless)    BOOL caseless)
149  {  {
150  USPTR eptr_start = eptr;  int matched_length = length;
151  register USPTR p = md->start_subject + md->offset_vector[offset];  register PCRE_PUCHAR p = md->start_subject + md->offset_vector[offset];
152    
153  #ifdef PCRE_DEBUG  #ifdef PCRE_DEBUG
154  if (eptr >= md->end_subject)  if (eptr >= md->end_subject)
# Line 181  ASCII characters. */ Line 173  ASCII characters. */
173    
174  if (caseless)  if (caseless)
175    {    {
176  #ifdef SUPPORT_UTF8  #ifdef SUPPORT_UTF
177  #ifdef SUPPORT_UCP  #ifdef SUPPORT_UCP
178    if (md->utf8)    if (md->utf)
179      {      {
180      /* Match characters up to the end of the reference. NOTE: the number of      /* Match characters up to the end of the reference. NOTE: the number of
181      bytes matched may differ, because there are some characters whose upper and      bytes matched may differ, because there are some characters whose upper and
# Line 193  if (caseless) Line 185  if (caseless)
185      the latter. It is important, therefore, to check the length along the      the latter. It is important, therefore, to check the length along the
186      reference, not along the subject (earlier code did this wrong). */      reference, not along the subject (earlier code did this wrong). */
187    
188      USPTR endptr = p + length;      PCRE_PUCHAR endptr = p + length;
189        PCRE_PUCHAR eptr_start = eptr;
190      while (p < endptr)      while (p < endptr)
191        {        {
192        int c, d;        int c, d;
193        if (eptr >= md->end_subject) return -1;        if (eptr >= md->end_subject) return -((int)(eptr - eptr_start) + 1);
194        GETCHARINC(c, eptr);        GETCHARINC(c, eptr);
195        GETCHARINC(d, p);        GETCHARINC(d, p);
196        if (c != d && c != UCD_OTHERCASE(d)) return -1;        if (c != d && c != UCD_OTHERCASE(d)) return -1;
197        }        }
198        matched_length = (int)(eptr - eptr_start);
199      }      }
200    else    else
201  #endif  #endif
# Line 210  if (caseless) Line 204  if (caseless)
204    /* The same code works when not in UTF-8 mode and in UTF-8 mode when there    /* The same code works when not in UTF-8 mode and in UTF-8 mode when there
205    is no UCP support. */    is no UCP support. */
206      {      {
207      if (eptr + length > md->end_subject) return -1;      if (eptr + length > md->end_subject)
208          {
209          if (md->partial == 0)
210            return -1;
211          length = (int)(md->end_subject - eptr);
212          matched_length = -(length + 1);
213          }
214      while (length-- > 0)      while (length-- > 0)
215        { if (md->lcc[*p++] != md->lcc[*eptr++]) return -1; }        {
216          if (TABLE_GET(*p, md->lcc, *p) != TABLE_GET(*eptr, md->lcc, *eptr)) return -1;
217          p++;
218          eptr++;
219          }
220      }      }
221    }    }
222    
# Line 221  are in UTF-8 mode. */ Line 225  are in UTF-8 mode. */
225    
226  else  else
227    {    {
228    if (eptr + length > md->end_subject) return -1;    if (eptr + length > md->end_subject)
229        {
230        if (md->partial == 0)
231          return -1;
232        length = (int)(md->end_subject - eptr);
233        matched_length = -(length + 1);
234        }
235    while (length-- > 0) if (*p++ != *eptr++) return -1;    while (length-- > 0) if (*p++ != *eptr++) return -1;
236    }    }
237    
238  return eptr - eptr_start;  return matched_length;
239  }  }
240    
241    
# Line 290  actually used in this definition. */ Line 300  actually used in this definition. */
300  #define RMATCH(ra,rb,rc,rd,re,rw) \  #define RMATCH(ra,rb,rc,rd,re,rw) \
301    { \    { \
302    printf("match() called in line %d\n", __LINE__); \    printf("match() called in line %d\n", __LINE__); \
303    rrc = match(ra,rb,mstart,markptr,rc,rd,re,rdepth+1); \    rrc = match(ra,rb,mstart,rc,rd,re,rdepth+1); \
304    printf("to line %d\n", __LINE__); \    printf("to line %d\n", __LINE__); \
305    }    }
306  #define RRETURN(ra) \  #define RRETURN(ra) \
# Line 300  actually used in this definition. */ Line 310  actually used in this definition. */
310    }    }
311  #else  #else
312  #define RMATCH(ra,rb,rc,rd,re,rw) \  #define RMATCH(ra,rb,rc,rd,re,rw) \
313    rrc = match(ra,rb,mstart,markptr,rc,rd,re,rdepth+1)    rrc = match(ra,rb,mstart,rc,rd,re,rdepth+1)
314  #define RRETURN(ra) return ra  #define RRETURN(ra) return ra
315  #endif  #endif
316    
# Line 315  argument of match(), which never changes Line 325  argument of match(), which never changes
325    
326  #define RMATCH(ra,rb,rc,rd,re,rw)\  #define RMATCH(ra,rb,rc,rd,re,rw)\
327    {\    {\
328    heapframe *newframe = (heapframe *)(pcre_stack_malloc)(sizeof(heapframe));\    heapframe *newframe = (heapframe *)(PUBL(stack_malloc))(sizeof(heapframe));\
329    if (newframe == NULL) RRETURN(PCRE_ERROR_NOMEMORY);\    if (newframe == NULL) RRETURN(PCRE_ERROR_NOMEMORY);\
330    frame->Xwhere = rw; \    frame->Xwhere = rw; \
331    newframe->Xeptr = ra;\    newframe->Xeptr = ra;\
332    newframe->Xecode = rb;\    newframe->Xecode = rb;\
333    newframe->Xmstart = mstart;\    newframe->Xmstart = mstart;\
   newframe->Xmarkptr = markptr;\  
334    newframe->Xoffset_top = rc;\    newframe->Xoffset_top = rc;\
335    newframe->Xeptrb = re;\    newframe->Xeptrb = re;\
336    newframe->Xrdepth = frame->Xrdepth + 1;\    newframe->Xrdepth = frame->Xrdepth + 1;\
# Line 337  argument of match(), which never changes Line 346  argument of match(), which never changes
346    {\    {\
347    heapframe *oldframe = frame;\    heapframe *oldframe = frame;\
348    frame = oldframe->Xprevframe;\    frame = oldframe->Xprevframe;\
349    (pcre_stack_free)(oldframe);\    if (oldframe != &frame_zero) (PUBL(stack_free))(oldframe);\
350    if (frame != NULL)\    if (frame != NULL)\
351      {\      {\
352      rrc = ra;\      rrc = ra;\
# Line 354  typedef struct heapframe { Line 363  typedef struct heapframe {
363    
364    /* Function arguments that may change */    /* Function arguments that may change */
365    
366    USPTR Xeptr;    PCRE_PUCHAR Xeptr;
367    const uschar *Xecode;    const pcre_uchar *Xecode;
368    USPTR Xmstart;    PCRE_PUCHAR Xmstart;
   USPTR Xmarkptr;  
369    int Xoffset_top;    int Xoffset_top;
370    eptrblock *Xeptrb;    eptrblock *Xeptrb;
371    unsigned int Xrdepth;    unsigned int Xrdepth;
372    
373    /* Function local variables */    /* Function local variables */
374    
375    USPTR Xcallpat;    PCRE_PUCHAR Xcallpat;
376  #ifdef SUPPORT_UTF8  #ifdef SUPPORT_UTF
377    USPTR Xcharptr;    PCRE_PUCHAR Xcharptr;
378  #endif  #endif
379    USPTR Xdata;    PCRE_PUCHAR Xdata;
380    USPTR Xnext;    PCRE_PUCHAR Xnext;
381    USPTR Xpp;    PCRE_PUCHAR Xpp;
382    USPTR Xprev;    PCRE_PUCHAR Xprev;
383    USPTR Xsaved_eptr;    PCRE_PUCHAR Xsaved_eptr;
384    
385    recursion_info Xnew_recursive;    recursion_info Xnew_recursive;
386    
# Line 385  typedef struct heapframe { Line 393  typedef struct heapframe {
393    int Xprop_value;    int Xprop_value;
394    int Xprop_fail_result;    int Xprop_fail_result;
395    int Xoclength;    int Xoclength;
396    uschar Xocchars[8];    pcre_uchar Xocchars[6];
397  #endif  #endif
398    
399    int Xcodelink;    int Xcodelink;
# Line 427  returns a negative (error) response, the Line 435  returns a negative (error) response, the
435  same response. */  same response. */
436    
437  /* These macros pack up tests that are used for partial matching, and which  /* These macros pack up tests that are used for partial matching, and which
438  appears several times in the code. We set the "hit end" flag if the pointer is  appear several times in the code. We set the "hit end" flag if the pointer is
439  at the end of the subject and also past the start of the subject (i.e.  at the end of the subject and also past the start of the subject (i.e.
440  something has been matched). For hard partial matching, we then return  something has been matched). For hard partial matching, we then return
441  immediately. The second one is used when we already know we are past the end of  immediately. The second one is used when we already know we are past the end of
# Line 438  the subject. */ Line 446  the subject. */
446        eptr > md->start_used_ptr) \        eptr > md->start_used_ptr) \
447      { \      { \
448      md->hitend = TRUE; \      md->hitend = TRUE; \
449      if (md->partial > 1) MRRETURN(PCRE_ERROR_PARTIAL); \      if (md->partial > 1) RRETURN(PCRE_ERROR_PARTIAL); \
450      }      }
451    
452  #define SCHECK_PARTIAL()\  #define SCHECK_PARTIAL()\
453    if (md->partial != 0 && eptr > md->start_used_ptr) \    if (md->partial != 0 && eptr > md->start_used_ptr) \
454      { \      { \
455      md->hitend = TRUE; \      md->hitend = TRUE; \
456      if (md->partial > 1) MRRETURN(PCRE_ERROR_PARTIAL); \      if (md->partial > 1) RRETURN(PCRE_ERROR_PARTIAL); \
457      }      }
458    
459    
460  /* Performance note: It might be tempting to extract commonly used fields from  /* Performance note: It might be tempting to extract commonly used fields from
461  the md structure (e.g. utf8, end_subject) into individual variables to improve  the md structure (e.g. utf, end_subject) into individual variables to improve
462  performance. Tests using gcc on a SPARC disproved this; in the first case, it  performance. Tests using gcc on a SPARC disproved this; in the first case, it
463  made performance worse.  made performance worse.
464    
# Line 459  Arguments: Line 467  Arguments:
467     ecode       pointer to current position in compiled code     ecode       pointer to current position in compiled code
468     mstart      pointer to the current match start position (can be modified     mstart      pointer to the current match start position (can be modified
469                   by encountering \K)                   by encountering \K)
    markptr     pointer to the most recent MARK name, or NULL  
470     offset_top  current top pointer     offset_top  current top pointer
471     md          pointer to "static" info for the match     md          pointer to "static" info for the match
472     eptrb       pointer to chain of blocks containing eptr at start of     eptrb       pointer to chain of blocks containing eptr at start of
# Line 474  Returns:       MATCH_MATCH if matched Line 481  Returns:       MATCH_MATCH if matched
481  */  */
482    
483  static int  static int
484  match(REGISTER USPTR eptr, REGISTER const uschar *ecode, USPTR mstart,  match(REGISTER PCRE_PUCHAR eptr, REGISTER const pcre_uchar *ecode,
485    const uschar *markptr, int offset_top, match_data *md, eptrblock *eptrb,    PCRE_PUCHAR mstart, int offset_top, match_data *md, eptrblock *eptrb,
486    unsigned int rdepth)    unsigned int rdepth)
487  {  {
488  /* These variables do not need to be preserved over recursion in this function,  /* These variables do not need to be preserved over recursion in this function,
# Line 485  so they can be ordinary variables in all Line 492  so they can be ordinary variables in all
492  register int  rrc;         /* Returns from recursive calls */  register int  rrc;         /* Returns from recursive calls */
493  register int  i;           /* Used for loops not involving calls to RMATCH() */  register int  i;           /* Used for loops not involving calls to RMATCH() */
494  register unsigned int c;   /* Character values not kept over RMATCH() calls */  register unsigned int c;   /* Character values not kept over RMATCH() calls */
495  register BOOL utf8;        /* Local copy of UTF-8 flag for speed */  register BOOL utf;         /* Local copy of UTF flag for speed */
496    
497  BOOL minimize, possessive; /* Quantifier options */  BOOL minimize, possessive; /* Quantifier options */
498  BOOL caseless;  BOOL caseless;
499  int condcode;  int condcode;
500    
501  /* When recursion is not being used, all "local" variables that have to be  /* When recursion is not being used, all "local" variables that have to be
502  preserved over calls to RMATCH() are part of a "frame" which is obtained from  preserved over calls to RMATCH() are part of a "frame". We set up the top-level
503  heap storage. Set up the top-level frame here; others are obtained from the  frame on the stack here; subsequent instantiations are obtained from the heap
504  heap whenever RMATCH() does a "recursion". See the macro definitions above. */  whenever RMATCH() does a "recursion". See the macro definitions above. Putting
505    the top-level on the stack rather than malloc-ing them all gives a performance
506    boost in many cases where there is not much "recursion". */
507    
508  #ifdef NO_RECURSE  #ifdef NO_RECURSE
509  heapframe *frame = (heapframe *)(pcre_stack_malloc)(sizeof(heapframe));  heapframe frame_zero;
510  if (frame == NULL) RRETURN(PCRE_ERROR_NOMEMORY);  heapframe *frame = &frame_zero;
511  frame->Xprevframe = NULL;            /* Marks the top level */  frame->Xprevframe = NULL;            /* Marks the top level */
512    
513  /* Copy in the original argument variables */  /* Copy in the original argument variables */
# Line 506  frame->Xprevframe = NULL;            /* Line 515  frame->Xprevframe = NULL;            /*
515  frame->Xeptr = eptr;  frame->Xeptr = eptr;
516  frame->Xecode = ecode;  frame->Xecode = ecode;
517  frame->Xmstart = mstart;  frame->Xmstart = mstart;
 frame->Xmarkptr = markptr;  
518  frame->Xoffset_top = offset_top;  frame->Xoffset_top = offset_top;
519  frame->Xeptrb = eptrb;  frame->Xeptrb = eptrb;
520  frame->Xrdepth = rdepth;  frame->Xrdepth = rdepth;
# Line 520  HEAP_RECURSE: Line 528  HEAP_RECURSE:
528  #define eptr               frame->Xeptr  #define eptr               frame->Xeptr
529  #define ecode              frame->Xecode  #define ecode              frame->Xecode
530  #define mstart             frame->Xmstart  #define mstart             frame->Xmstart
 #define markptr            frame->Xmarkptr  
531  #define offset_top         frame->Xoffset_top  #define offset_top         frame->Xoffset_top
532  #define eptrb              frame->Xeptrb  #define eptrb              frame->Xeptrb
533  #define rdepth             frame->Xrdepth  #define rdepth             frame->Xrdepth
534    
535  /* Ditto for the local variables */  /* Ditto for the local variables */
536    
537  #ifdef SUPPORT_UTF8  #ifdef SUPPORT_UTF
538  #define charptr            frame->Xcharptr  #define charptr            frame->Xcharptr
539  #endif  #endif
540  #define callpat            frame->Xcallpat  #define callpat            frame->Xcallpat
# Line 585  declarations can be cut out in a block. Line 592  declarations can be cut out in a block.
592  below are for variables that do not have to be preserved over a recursive call  below are for variables that do not have to be preserved over a recursive call
593  to RMATCH(). */  to RMATCH(). */
594    
595  #ifdef SUPPORT_UTF8  #ifdef SUPPORT_UTF
596  const uschar *charptr;  const pcre_uchar *charptr;
597  #endif  #endif
598  const uschar *callpat;  const pcre_uchar *callpat;
599  const uschar *data;  const pcre_uchar *data;
600  const uschar *next;  const pcre_uchar *next;
601  USPTR         pp;  PCRE_PUCHAR       pp;
602  const uschar *prev;  const pcre_uchar *prev;
603  USPTR         saved_eptr;  PCRE_PUCHAR       saved_eptr;
604    
605  recursion_info new_recursive;  recursion_info new_recursive;
606    
# Line 606  int prop_type; Line 613  int prop_type;
613  int prop_value;  int prop_value;
614  int prop_fail_result;  int prop_fail_result;
615  int oclength;  int oclength;
616  uschar occhars[8];  pcre_uchar occhars[6];
617  #endif  #endif
618    
619  int codelink;  int codelink;
# Line 622  int save_offset1, save_offset2, save_off Line 629  int save_offset1, save_offset2, save_off
629  int stacksave[REC_STACK_SAVE_MAX];  int stacksave[REC_STACK_SAVE_MAX];
630    
631  eptrblock newptrb;  eptrblock newptrb;
632    
633    /* There is a special fudge for calling match() in a way that causes it to
634    measure the size of its basic stack frame when the stack is being used for
635    recursion. The second argument (ecode) being NULL triggers this behaviour. It
636    cannot normally ever be NULL. The return is the negated value of the frame
637    size. */
638    
639    if (ecode == NULL)
640      {
641      if (rdepth == 0)
642        return match((PCRE_PUCHAR)&rdepth, NULL, NULL, 0, NULL, NULL, 1);
643      else
644        {
645        int len = (char *)&rdepth - (char *)eptr;
646        return (len > 0)? -len : len;
647        }
648      }
649  #endif     /* NO_RECURSE */  #endif     /* NO_RECURSE */
650    
651  /* To save space on the stack and in the heap frame, I have doubled up on some  /* To save space on the stack and in the heap frame, I have doubled up on some
# Line 634  the alternative names that are used. */ Line 658  the alternative names that are used. */
658  #define code_offset   codelink  #define code_offset   codelink
659  #define condassert    condition  #define condassert    condition
660  #define matched_once  prev_is_word  #define matched_once  prev_is_word
661    #define foc           number
662    #define save_mark     data
663    
664  /* These statements are here to stop the compiler complaining about unitialized  /* These statements are here to stop the compiler complaining about unitialized
665  variables. */  variables. */
# Line 659  defined). However, RMATCH isn't like a f Line 685  defined). However, RMATCH isn't like a f
685  complicated macro. It has to be used in one particular way. This shouldn't,  complicated macro. It has to be used in one particular way. This shouldn't,
686  however, impact performance when true recursion is being used. */  however, impact performance when true recursion is being used. */
687    
688  #ifdef SUPPORT_UTF8  #ifdef SUPPORT_UTF
689  utf8 = md->utf8;       /* Local copy of the flag */  utf = md->utf;       /* Local copy of the flag */
690  #else  #else
691  utf8 = FALSE;  utf = FALSE;
692  #endif  #endif
693    
694  /* First check that we haven't called match() too many times, or that we  /* First check that we haven't called match() too many times, or that we
# Line 701  for (;;) Line 727  for (;;)
727    switch(op)    switch(op)
728      {      {
729      case OP_MARK:      case OP_MARK:
730      markptr = ecode + 2;      md->nomatch_mark = ecode + 2;
731      RMATCH(eptr, ecode + _pcre_OP_lengths[*ecode] + ecode[1], offset_top, md,      md->mark = NULL;    /* In case previously set by assertion */
732        RMATCH(eptr, ecode + PRIV(OP_lengths)[*ecode] + ecode[1], offset_top, md,
733        eptrb, RM55);        eptrb, RM55);
734        if ((rrc == MATCH_MATCH || rrc == MATCH_ACCEPT) &&
735             md->mark == NULL) md->mark = ecode + 2;
736    
737      /* A return of MATCH_SKIP_ARG means that matching failed at SKIP with an      /* A return of MATCH_SKIP_ARG means that matching failed at SKIP with an
738      argument, and we must check whether that argument matches this MARK's      argument, and we must check whether that argument matches this MARK's
# Line 712  for (;;) Line 741  for (;;)
741      position and return MATCH_SKIP. Otherwise, pass back the return code      position and return MATCH_SKIP. Otherwise, pass back the return code
742      unaltered. */      unaltered. */
743    
744      if (rrc == MATCH_SKIP_ARG &&      else if (rrc == MATCH_SKIP_ARG &&
745          strcmp((char *)markptr, (char *)(md->start_match_ptr)) == 0)          STRCMP_UC_UC(ecode + 2, md->start_match_ptr) == 0)
746        {        {
747        md->start_match_ptr = eptr;        md->start_match_ptr = eptr;
748        RRETURN(MATCH_SKIP);        RRETURN(MATCH_SKIP);
749        }        }
   
     if (md->mark == NULL) md->mark = markptr;  
750      RRETURN(rrc);      RRETURN(rrc);
751    
752      case OP_FAIL:      case OP_FAIL:
753      MRRETURN(MATCH_NOMATCH);      RRETURN(MATCH_NOMATCH);
754    
755      /* COMMIT overrides PRUNE, SKIP, and THEN */      /* COMMIT overrides PRUNE, SKIP, and THEN */
756    
757      case OP_COMMIT:      case OP_COMMIT:
758      RMATCH(eptr, ecode + _pcre_OP_lengths[*ecode], offset_top, md,      RMATCH(eptr, ecode + PRIV(OP_lengths)[*ecode], offset_top, md,
759        eptrb, RM52);        eptrb, RM52);
760      if (rrc != MATCH_NOMATCH && rrc != MATCH_PRUNE &&      if (rrc != MATCH_NOMATCH && rrc != MATCH_PRUNE &&
761          rrc != MATCH_SKIP && rrc != MATCH_SKIP_ARG &&          rrc != MATCH_SKIP && rrc != MATCH_SKIP_ARG &&
762          rrc != MATCH_THEN)          rrc != MATCH_THEN)
763        RRETURN(rrc);        RRETURN(rrc);
764      MRRETURN(MATCH_COMMIT);      RRETURN(MATCH_COMMIT);
765    
766      /* PRUNE overrides THEN */      /* PRUNE overrides THEN */
767    
768      case OP_PRUNE:      case OP_PRUNE:
769      RMATCH(eptr, ecode + _pcre_OP_lengths[*ecode], offset_top, md,      RMATCH(eptr, ecode + PRIV(OP_lengths)[*ecode], offset_top, md,
770        eptrb, RM51);        eptrb, RM51);
771      if (rrc != MATCH_NOMATCH && rrc != MATCH_THEN) RRETURN(rrc);      if (rrc != MATCH_NOMATCH && rrc != MATCH_THEN) RRETURN(rrc);
772      MRRETURN(MATCH_PRUNE);      RRETURN(MATCH_PRUNE);
773    
774      case OP_PRUNE_ARG:      case OP_PRUNE_ARG:
775      RMATCH(eptr, ecode + _pcre_OP_lengths[*ecode] + ecode[1], offset_top, md,      md->nomatch_mark = ecode + 2;
776        md->mark = NULL;    /* In case previously set by assertion */
777        RMATCH(eptr, ecode + PRIV(OP_lengths)[*ecode] + ecode[1], offset_top, md,
778        eptrb, RM56);        eptrb, RM56);
779        if ((rrc == MATCH_MATCH || rrc == MATCH_ACCEPT) &&
780             md->mark == NULL) md->mark = ecode + 2;
781      if (rrc != MATCH_NOMATCH && rrc != MATCH_THEN) RRETURN(rrc);      if (rrc != MATCH_NOMATCH && rrc != MATCH_THEN) RRETURN(rrc);
     md->mark = ecode + 2;  
782      RRETURN(MATCH_PRUNE);      RRETURN(MATCH_PRUNE);
783    
784      /* SKIP overrides PRUNE and THEN */      /* SKIP overrides PRUNE and THEN */
785    
786      case OP_SKIP:      case OP_SKIP:
787      RMATCH(eptr, ecode + _pcre_OP_lengths[*ecode], offset_top, md,      RMATCH(eptr, ecode + PRIV(OP_lengths)[*ecode], offset_top, md,
788        eptrb, RM53);        eptrb, RM53);
789      if (rrc != MATCH_NOMATCH && rrc != MATCH_PRUNE && rrc != MATCH_THEN)      if (rrc != MATCH_NOMATCH && rrc != MATCH_PRUNE && rrc != MATCH_THEN)
790        RRETURN(rrc);        RRETURN(rrc);
791      md->start_match_ptr = eptr;   /* Pass back current position */      md->start_match_ptr = eptr;   /* Pass back current position */
792      MRRETURN(MATCH_SKIP);      RRETURN(MATCH_SKIP);
793    
794        /* Note that, for Perl compatibility, SKIP with an argument does NOT set
795        nomatch_mark. There is a flag that disables this opcode when re-matching a
796        pattern that ended with a SKIP for which there was not a matching MARK. */
797    
798      case OP_SKIP_ARG:      case OP_SKIP_ARG:
799      RMATCH(eptr, ecode + _pcre_OP_lengths[*ecode] + ecode[1], offset_top, md,      if (md->ignore_skip_arg)
800          {
801          ecode += PRIV(OP_lengths)[*ecode] + ecode[1];
802          break;
803          }
804        RMATCH(eptr, ecode + PRIV(OP_lengths)[*ecode] + ecode[1], offset_top, md,
805        eptrb, RM57);        eptrb, RM57);
806      if (rrc != MATCH_NOMATCH && rrc != MATCH_PRUNE && rrc != MATCH_THEN)      if (rrc != MATCH_NOMATCH && rrc != MATCH_PRUNE && rrc != MATCH_THEN)
807        RRETURN(rrc);        RRETURN(rrc);
808    
809      /* Pass back the current skip name by overloading md->start_match_ptr and      /* Pass back the current skip name by overloading md->start_match_ptr and
810      returning the special MATCH_SKIP_ARG return code. This will either be      returning the special MATCH_SKIP_ARG return code. This will either be
811      caught by a matching MARK, or get to the top, where it is treated the same      caught by a matching MARK, or get to the top, where it causes a rematch
812      as PRUNE. */      with the md->ignore_skip_arg flag set. */
813    
814      md->start_match_ptr = ecode + 2;      md->start_match_ptr = ecode + 2;
815      RRETURN(MATCH_SKIP_ARG);      RRETURN(MATCH_SKIP_ARG);
# Line 780  for (;;) Line 819  for (;;)
819      match pointer to do this. */      match pointer to do this. */
820    
821      case OP_THEN:      case OP_THEN:
822      RMATCH(eptr, ecode + _pcre_OP_lengths[*ecode], offset_top, md,      RMATCH(eptr, ecode + PRIV(OP_lengths)[*ecode], offset_top, md,
823        eptrb, RM54);        eptrb, RM54);
824      if (rrc != MATCH_NOMATCH) RRETURN(rrc);      if (rrc != MATCH_NOMATCH) RRETURN(rrc);
825      md->start_match_ptr = ecode;      md->start_match_ptr = ecode;
826      MRRETURN(MATCH_THEN);      RRETURN(MATCH_THEN);
827    
828      case OP_THEN_ARG:      case OP_THEN_ARG:
829      RMATCH(eptr, ecode + _pcre_OP_lengths[*ecode] + ecode[1], offset_top,      md->nomatch_mark = ecode + 2;
830        md->mark = NULL;    /* In case previously set by assertion */
831        RMATCH(eptr, ecode + PRIV(OP_lengths)[*ecode] + ecode[1], offset_top,
832        md, eptrb, RM58);        md, eptrb, RM58);
833        if ((rrc == MATCH_MATCH || rrc == MATCH_ACCEPT) &&
834             md->mark == NULL) md->mark = ecode + 2;
835      if (rrc != MATCH_NOMATCH) RRETURN(rrc);      if (rrc != MATCH_NOMATCH) RRETURN(rrc);
836      md->start_match_ptr = ecode;      md->start_match_ptr = ecode;
     md->mark = ecode + 2;  
837      RRETURN(MATCH_THEN);      RRETURN(MATCH_THEN);
838    
839      /* Handle an atomic group that does not contain any capturing parentheses.      /* Handle an atomic group that does not contain any capturing parentheses.
# Line 810  for (;;) Line 852  for (;;)
852      case OP_ONCE_NC:      case OP_ONCE_NC:
853      prev = ecode;      prev = ecode;
854      saved_eptr = eptr;      saved_eptr = eptr;
855        save_mark = md->mark;
856      do      do
857        {        {
858        RMATCH(eptr, ecode + 1 + LINK_SIZE, offset_top, md, eptrb, RM64);        RMATCH(eptr, ecode + 1 + LINK_SIZE, offset_top, md, eptrb, RM64);
# Line 828  for (;;) Line 871  for (;;)
871    
872        if (rrc != MATCH_NOMATCH) RRETURN(rrc);        if (rrc != MATCH_NOMATCH) RRETURN(rrc);
873        ecode += GET(ecode,1);        ecode += GET(ecode,1);
874          md->mark = save_mark;
875        }        }
876      while (*ecode == OP_ALT);      while (*ecode == OP_ALT);
877    
# Line 907  for (;;) Line 951  for (;;)
951        save_offset2 = md->offset_vector[offset+1];        save_offset2 = md->offset_vector[offset+1];
952        save_offset3 = md->offset_vector[md->offset_end - number];        save_offset3 = md->offset_vector[md->offset_end - number];
953        save_capture_last = md->capture_last;        save_capture_last = md->capture_last;
954          save_mark = md->mark;
955    
956        DPRINTF(("saving %d %d %d\n", save_offset1, save_offset2, save_offset3));        DPRINTF(("saving %d %d %d\n", save_offset1, save_offset2, save_offset3));
957        md->offset_vector[md->offset_end - number] =        md->offset_vector[md->offset_end - number] =
# Line 915  for (;;) Line 960  for (;;)
960        for (;;)        for (;;)
961          {          {
962          if (op >= OP_SBRA) md->match_function_type = MATCH_CBEGROUP;          if (op >= OP_SBRA) md->match_function_type = MATCH_CBEGROUP;
963          RMATCH(eptr, ecode + _pcre_OP_lengths[*ecode], offset_top, md,          RMATCH(eptr, ecode + PRIV(OP_lengths)[*ecode], offset_top, md,
964            eptrb, RM1);            eptrb, RM1);
965          if (rrc == MATCH_ONCE) break;  /* Backing up through an atomic group */          if (rrc == MATCH_ONCE) break;  /* Backing up through an atomic group */
966    
# Line 943  for (;;) Line 988  for (;;)
988          if (rrc != MATCH_NOMATCH) RRETURN(rrc);          if (rrc != MATCH_NOMATCH) RRETURN(rrc);
989          md->capture_last = save_capture_last;          md->capture_last = save_capture_last;
990          ecode += GET(ecode, 1);          ecode += GET(ecode, 1);
991            md->mark = save_mark;
992          if (*ecode != OP_ALT) break;          if (*ecode != OP_ALT) break;
993          }          }
994    
# Line 953  for (;;) Line 999  for (;;)
999    
1000        /* At this point, rrc will be one of MATCH_ONCE or MATCH_NOMATCH. */        /* At this point, rrc will be one of MATCH_ONCE or MATCH_NOMATCH. */
1001    
       if (md->mark == NULL) md->mark = markptr;  
1002        RRETURN(rrc);        RRETURN(rrc);
1003        }        }
1004    
# Line 1003  for (;;) Line 1048  for (;;)
1048    
1049        else if (!md->hasthen && ecode[GET(ecode, 1)] != OP_ALT)        else if (!md->hasthen && ecode[GET(ecode, 1)] != OP_ALT)
1050          {          {
1051          ecode += _pcre_OP_lengths[*ecode];          ecode += PRIV(OP_lengths)[*ecode];
1052          goto TAIL_RECURSE;          goto TAIL_RECURSE;
1053          }          }
1054    
1055        /* In all other cases, we have to make another call to match(). */        /* In all other cases, we have to make another call to match(). */
1056    
1057        RMATCH(eptr, ecode + _pcre_OP_lengths[*ecode], offset_top, md, eptrb,        save_mark = md->mark;
1058          RMATCH(eptr, ecode + PRIV(OP_lengths)[*ecode], offset_top, md, eptrb,
1059          RM2);          RM2);
1060    
1061        /* See comment in the code for capturing groups above about handling        /* See comment in the code for capturing groups above about handling
# Line 1027  for (;;) Line 1073  for (;;)
1073          {          {
1074          if (rrc == MATCH_ONCE)          if (rrc == MATCH_ONCE)
1075            {            {
1076            const uschar *scode = ecode;            const pcre_uchar *scode = ecode;
1077            if (*scode != OP_ONCE)           /* If not at start, find it */            if (*scode != OP_ONCE)           /* If not at start, find it */
1078              {              {
1079              while (*scode == OP_ALT) scode += GET(scode, 1);              while (*scode == OP_ALT) scode += GET(scode, 1);
# Line 1038  for (;;) Line 1084  for (;;)
1084          RRETURN(rrc);          RRETURN(rrc);
1085          }          }
1086        ecode += GET(ecode, 1);        ecode += GET(ecode, 1);
1087          md->mark = save_mark;
1088        if (*ecode != OP_ALT) break;        if (*ecode != OP_ALT) break;
1089        }        }
1090    
     if (md->mark == NULL) md->mark = markptr;  
1091      RRETURN(MATCH_NOMATCH);      RRETURN(MATCH_NOMATCH);
1092    
1093      /* Handle possessive capturing brackets with an unlimited repeat. We come      /* Handle possessive capturing brackets with an unlimited repeat. We come
# Line 1070  for (;;) Line 1116  for (;;)
1116      if (offset < md->offset_max)      if (offset < md->offset_max)
1117        {        {
1118        matched_once = FALSE;        matched_once = FALSE;
1119        code_offset = ecode - md->start_code;        code_offset = (int)(ecode - md->start_code);
1120    
1121        save_offset1 = md->offset_vector[offset];        save_offset1 = md->offset_vector[offset];
1122        save_offset2 = md->offset_vector[offset+1];        save_offset2 = md->offset_vector[offset+1];
# Line 1093  for (;;) Line 1139  for (;;)
1139          md->offset_vector[md->offset_end - number] =          md->offset_vector[md->offset_end - number] =
1140            (int)(eptr - md->start_subject);            (int)(eptr - md->start_subject);
1141          if (op >= OP_SBRA) md->match_function_type = MATCH_CBEGROUP;          if (op >= OP_SBRA) md->match_function_type = MATCH_CBEGROUP;
1142          RMATCH(eptr, ecode + _pcre_OP_lengths[*ecode], offset_top, md,          RMATCH(eptr, ecode + PRIV(OP_lengths)[*ecode], offset_top, md,
1143            eptrb, RM63);            eptrb, RM63);
1144          if (rrc == MATCH_KETRPOS)          if (rrc == MATCH_KETRPOS)
1145            {            {
# Line 1129  for (;;) Line 1175  for (;;)
1175          md->offset_vector[md->offset_end - number] = save_offset3;          md->offset_vector[md->offset_end - number] = save_offset3;
1176          }          }
1177    
       if (md->mark == NULL) md->mark = markptr;  
1178        if (allow_zero || matched_once)        if (allow_zero || matched_once)
1179          {          {
1180          ecode += 1 + LINK_SIZE;          ecode += 1 + LINK_SIZE;
# Line 1161  for (;;) Line 1206  for (;;)
1206    
1207      POSSESSIVE_NON_CAPTURE:      POSSESSIVE_NON_CAPTURE:
1208      matched_once = FALSE;      matched_once = FALSE;
1209      code_offset = ecode - md->start_code;      code_offset = (int)(ecode - md->start_code);
1210    
1211      for (;;)      for (;;)
1212        {        {
1213        if (op >= OP_SBRA) md->match_function_type = MATCH_CBEGROUP;        if (op >= OP_SBRA) md->match_function_type = MATCH_CBEGROUP;
1214        RMATCH(eptr, ecode + _pcre_OP_lengths[*ecode], offset_top, md,        RMATCH(eptr, ecode + PRIV(OP_lengths)[*ecode], offset_top, md,
1215          eptrb, RM48);          eptrb, RM48);
1216        if (rrc == MATCH_KETRPOS)        if (rrc == MATCH_KETRPOS)
1217          {          {
# Line 1216  for (;;) Line 1261  for (;;)
1261    
1262      if (ecode[LINK_SIZE+1] == OP_CALLOUT)      if (ecode[LINK_SIZE+1] == OP_CALLOUT)
1263        {        {
1264        if (pcre_callout != NULL)        if (PUBL(callout) != NULL)
1265          {          {
1266          pcre_callout_block cb;          PUBL(callout_block) cb;
1267          cb.version          = 2;   /* Version 1 of the callout block */          cb.version          = 2;   /* Version 1 of the callout block */
1268          cb.callout_number   = ecode[LINK_SIZE+2];          cb.callout_number   = ecode[LINK_SIZE+2];
1269          cb.offset_vector    = md->offset_vector;          cb.offset_vector    = md->offset_vector;
1270    #ifdef COMPILE_PCRE8
1271          cb.subject          = (PCRE_SPTR)md->start_subject;          cb.subject          = (PCRE_SPTR)md->start_subject;
1272    #else
1273            cb.subject          = (PCRE_SPTR16)md->start_subject;
1274    #endif
1275          cb.subject_length   = (int)(md->end_subject - md->start_subject);          cb.subject_length   = (int)(md->end_subject - md->start_subject);
1276          cb.start_match      = (int)(mstart - md->start_subject);          cb.start_match      = (int)(mstart - md->start_subject);
1277          cb.current_position = (int)(eptr - md->start_subject);          cb.current_position = (int)(eptr - md->start_subject);
# Line 1231  for (;;) Line 1280  for (;;)
1280          cb.capture_top      = offset_top/2;          cb.capture_top      = offset_top/2;
1281          cb.capture_last     = md->capture_last;          cb.capture_last     = md->capture_last;
1282          cb.callout_data     = md->callout_data;          cb.callout_data     = md->callout_data;
1283          cb.mark             = markptr;          cb.mark             = md->nomatch_mark;
1284          if ((rrc = (*pcre_callout)(&cb)) > 0) MRRETURN(MATCH_NOMATCH);          if ((rrc = (*PUBL(callout))(&cb)) > 0) RRETURN(MATCH_NOMATCH);
1285          if (rrc < 0) RRETURN(rrc);          if (rrc < 0) RRETURN(rrc);
1286          }          }
1287        ecode += _pcre_OP_lengths[OP_CALLOUT];        ecode += PRIV(OP_lengths)[OP_CALLOUT];
1288        }        }
1289    
1290      condcode = ecode[LINK_SIZE+1];      condcode = ecode[LINK_SIZE+1];
# Line 1252  for (;;) Line 1301  for (;;)
1301        else        else
1302          {          {
1303          int recno = GET2(ecode, LINK_SIZE + 2);   /* Recursion group number*/          int recno = GET2(ecode, LINK_SIZE + 2);   /* Recursion group number*/
1304          condition =  (recno == RREF_ANY || recno == md->recursive->group_num);          condition = (recno == RREF_ANY || recno == md->recursive->group_num);
1305    
1306          /* If the test is for recursion into a specific subpattern, and it is          /* If the test is for recursion into a specific subpattern, and it is
1307          false, but the test was set up by name, scan the table to see if the          false, but the test was set up by name, scan the table to see if the
1308          name refers to any other numbers, and test them. The condition is true          name refers to any other numbers, and test them. The condition is true
1309          if any one is set. */          if any one is set. */
1310    
1311          if (!condition && condcode == OP_NRREF && recno != RREF_ANY)          if (!condition && condcode == OP_NRREF)
1312            {            {
1313            uschar *slotA = md->name_table;            pcre_uchar *slotA = md->name_table;
1314            for (i = 0; i < md->name_count; i++)            for (i = 0; i < md->name_count; i++)
1315              {              {
1316              if (GET2(slotA, 0) == recno) break;              if (GET2(slotA, 0) == recno) break;
# Line 1274  for (;;) Line 1323  for (;;)
1323    
1324            if (i < md->name_count)            if (i < md->name_count)
1325              {              {
1326              uschar *slotB = slotA;              pcre_uchar *slotB = slotA;
1327              while (slotB > md->name_table)              while (slotB > md->name_table)
1328                {                {
1329                slotB -= md->name_entry_size;                slotB -= md->name_entry_size;
1330                if (strcmp((char *)slotA + 2, (char *)slotB + 2) == 0)                if (STRCMP_UC_UC(slotA + IMM2_SIZE, slotB + IMM2_SIZE) == 0)
1331                  {                  {
1332                  condition = GET2(slotB, 0) == md->recursive->group_num;                  condition = GET2(slotB, 0) == md->recursive->group_num;
1333                  if (condition) break;                  if (condition) break;
# Line 1294  for (;;) Line 1343  for (;;)
1343                for (i++; i < md->name_count; i++)                for (i++; i < md->name_count; i++)
1344                  {                  {
1345                  slotB += md->name_entry_size;                  slotB += md->name_entry_size;
1346                  if (strcmp((char *)slotA + 2, (char *)slotB + 2) == 0)                  if (STRCMP_UC_UC(slotA + IMM2_SIZE, slotB + IMM2_SIZE) == 0)
1347                    {                    {
1348                    condition = GET2(slotB, 0) == md->recursive->group_num;                    condition = GET2(slotB, 0) == md->recursive->group_num;
1349                    if (condition) break;                    if (condition) break;
# Line 1307  for (;;) Line 1356  for (;;)
1356    
1357          /* Chose branch according to the condition */          /* Chose branch according to the condition */
1358    
1359          ecode += condition? 3 : GET(ecode, 1);          ecode += condition? 1 + IMM2_SIZE : GET(ecode, 1);
1360          }          }
1361        }        }
1362    
# Line 1324  for (;;) Line 1373  for (;;)
1373        if (!condition && condcode == OP_NCREF)        if (!condition && condcode == OP_NCREF)
1374          {          {
1375          int refno = offset >> 1;          int refno = offset >> 1;
1376          uschar *slotA = md->name_table;          pcre_uchar *slotA = md->name_table;
1377    
1378          for (i = 0; i < md->name_count; i++)          for (i = 0; i < md->name_count; i++)
1379            {            {
# Line 1338  for (;;) Line 1387  for (;;)
1387    
1388          if (i < md->name_count)          if (i < md->name_count)
1389            {            {
1390            uschar *slotB = slotA;            pcre_uchar *slotB = slotA;
1391            while (slotB > md->name_table)            while (slotB > md->name_table)
1392              {              {
1393              slotB -= md->name_entry_size;              slotB -= md->name_entry_size;
1394              if (strcmp((char *)slotA + 2, (char *)slotB + 2) == 0)              if (STRCMP_UC_UC(slotA + IMM2_SIZE, slotB + IMM2_SIZE) == 0)
1395                {                {
1396                offset = GET2(slotB, 0) << 1;                offset = GET2(slotB, 0) << 1;
1397                condition = offset < offset_top &&                condition = offset < offset_top &&
# Line 1360  for (;;) Line 1409  for (;;)
1409              for (i++; i < md->name_count; i++)              for (i++; i < md->name_count; i++)
1410                {                {
1411                slotB += md->name_entry_size;                slotB += md->name_entry_size;
1412                if (strcmp((char *)slotA + 2, (char *)slotB + 2) == 0)                if (STRCMP_UC_UC(slotA + IMM2_SIZE, slotB + IMM2_SIZE) == 0)
1413                  {                  {
1414                  offset = GET2(slotB, 0) << 1;                  offset = GET2(slotB, 0) << 1;
1415                  condition = offset < offset_top &&                  condition = offset < offset_top &&
# Line 1375  for (;;) Line 1424  for (;;)
1424    
1425        /* Chose branch according to the condition */        /* Chose branch according to the condition */
1426    
1427        ecode += condition? 3 : GET(ecode, 1);        ecode += condition? 1 + IMM2_SIZE : GET(ecode, 1);
1428        }        }
1429    
1430      else if (condcode == OP_DEF)     /* DEFINE - always false */      else if (condcode == OP_DEF)     /* DEFINE - always false */
# Line 1467  for (;;) Line 1516  for (;;)
1516        md->offset_vector[offset+1] = (int)(eptr - md->start_subject);        md->offset_vector[offset+1] = (int)(eptr - md->start_subject);
1517        if (offset_top <= offset) offset_top = offset + 2;        if (offset_top <= offset) offset_top = offset + 2;
1518        }        }
1519      ecode += 3;      ecode += 1 + IMM2_SIZE;
1520      break;      break;
1521    
1522    
# Line 1487  for (;;) Line 1536  for (;;)
1536           (md->notempty ||           (md->notempty ||
1537             (md->notempty_atstart &&             (md->notempty_atstart &&
1538               mstart == md->start_subject + md->start_offset)))               mstart == md->start_subject + md->start_offset)))
1539        MRRETURN(MATCH_NOMATCH);        RRETURN(MATCH_NOMATCH);
1540    
1541      /* Otherwise, we have a match. */      /* Otherwise, we have a match. */
1542    
# Line 1496  for (;;) Line 1545  for (;;)
1545      md->start_match_ptr = mstart;       /* and the start (\K can modify) */      md->start_match_ptr = mstart;       /* and the start (\K can modify) */
1546    
1547      /* For some reason, the macros don't work properly if an expression is      /* For some reason, the macros don't work properly if an expression is
1548      given as the argument to MRRETURN when the heap is in use. */      given as the argument to RRETURN when the heap is in use. */
1549    
1550      rrc = (op == OP_END)? MATCH_MATCH : MATCH_ACCEPT;      rrc = (op == OP_END)? MATCH_MATCH : MATCH_ACCEPT;
1551      MRRETURN(rrc);      RRETURN(rrc);
1552    
1553      /* Assertion brackets. Check the alternative branches in turn - the      /* Assertion brackets. Check the alternative branches in turn - the
1554      matching won't pass the KET for an assertion. If any one branch matches,      matching won't pass the KET for an assertion. If any one branch matches,
# Line 1514  for (;;) Line 1563  for (;;)
1563    
1564      case OP_ASSERT:      case OP_ASSERT:
1565      case OP_ASSERTBACK:      case OP_ASSERTBACK:
1566        save_mark = md->mark;
1567      if (md->match_function_type == MATCH_CONDASSERT)      if (md->match_function_type == MATCH_CONDASSERT)
1568        {        {
1569        condassert = TRUE;        condassert = TRUE;
# Line 1527  for (;;) Line 1577  for (;;)
1577        if (rrc == MATCH_MATCH || rrc == MATCH_ACCEPT)        if (rrc == MATCH_MATCH || rrc == MATCH_ACCEPT)
1578          {          {
1579          mstart = md->start_match_ptr;   /* In case \K reset it */          mstart = md->start_match_ptr;   /* In case \K reset it */
         markptr = md->mark;  
1580          break;          break;
1581          }          }
1582    
# Line 1536  for (;;) Line 1585  for (;;)
1585    
1586        if (rrc != MATCH_NOMATCH && rrc != MATCH_THEN) RRETURN(rrc);        if (rrc != MATCH_NOMATCH && rrc != MATCH_THEN) RRETURN(rrc);
1587        ecode += GET(ecode, 1);        ecode += GET(ecode, 1);
1588          md->mark = save_mark;
1589        }        }
1590      while (*ecode == OP_ALT);      while (*ecode == OP_ALT);
1591    
1592      if (*ecode == OP_KET) MRRETURN(MATCH_NOMATCH);      if (*ecode == OP_KET) RRETURN(MATCH_NOMATCH);
1593    
1594      /* If checking an assertion for a condition, return MATCH_MATCH. */      /* If checking an assertion for a condition, return MATCH_MATCH. */
1595    
# Line 1559  for (;;) Line 1609  for (;;)
1609    
1610      case OP_ASSERT_NOT:      case OP_ASSERT_NOT:
1611      case OP_ASSERTBACK_NOT:      case OP_ASSERTBACK_NOT:
1612        save_mark = md->mark;
1613      if (md->match_function_type == MATCH_CONDASSERT)      if (md->match_function_type == MATCH_CONDASSERT)
1614        {        {
1615        condassert = TRUE;        condassert = TRUE;
# Line 1569  for (;;) Line 1620  for (;;)
1620      do      do
1621        {        {
1622        RMATCH(eptr, ecode + 1 + LINK_SIZE, offset_top, md, NULL, RM5);        RMATCH(eptr, ecode + 1 + LINK_SIZE, offset_top, md, NULL, RM5);
1623        if (rrc == MATCH_MATCH || rrc == MATCH_ACCEPT) MRRETURN(MATCH_NOMATCH);        md->mark = save_mark;
1624          if (rrc == MATCH_MATCH || rrc == MATCH_ACCEPT) RRETURN(MATCH_NOMATCH);
1625        if (rrc == MATCH_SKIP || rrc == MATCH_PRUNE || rrc == MATCH_COMMIT)        if (rrc == MATCH_SKIP || rrc == MATCH_PRUNE || rrc == MATCH_COMMIT)
1626          {          {
1627          do ecode += GET(ecode,1); while (*ecode == OP_ALT);          do ecode += GET(ecode,1); while (*ecode == OP_ALT);
# Line 1595  for (;;) Line 1647  for (;;)
1647      back a number of characters, not bytes. */      back a number of characters, not bytes. */
1648    
1649      case OP_REVERSE:      case OP_REVERSE:
1650  #ifdef SUPPORT_UTF8  #ifdef SUPPORT_UTF
1651      if (utf8)      if (utf)
1652        {        {
1653        i = GET(ecode, 1);        i = GET(ecode, 1);
1654        while (i-- > 0)        while (i-- > 0)
1655          {          {
1656          eptr--;          eptr--;
1657          if (eptr < md->start_subject) MRRETURN(MATCH_NOMATCH);          if (eptr < md->start_subject) RRETURN(MATCH_NOMATCH);
1658          BACKCHAR(eptr);          BACKCHAR(eptr);
1659          }          }
1660        }        }
# Line 1613  for (;;) Line 1665  for (;;)
1665    
1666        {        {
1667        eptr -= GET(ecode, 1);        eptr -= GET(ecode, 1);
1668        if (eptr < md->start_subject) MRRETURN(MATCH_NOMATCH);        if (eptr < md->start_subject) RRETURN(MATCH_NOMATCH);
1669        }        }
1670    
1671      /* Save the earliest consulted character, then skip to next op code */      /* Save the earliest consulted character, then skip to next op code */
# Line 1627  for (;;) Line 1679  for (;;)
1679      function is able to force a failure. */      function is able to force a failure. */
1680    
1681      case OP_CALLOUT:      case OP_CALLOUT:
1682      if (pcre_callout != NULL)      if (PUBL(callout) != NULL)
1683        {        {
1684        pcre_callout_block cb;        PUBL(callout_block) cb;
1685        cb.version          = 2;   /* Version 1 of the callout block */        cb.version          = 2;   /* Version 1 of the callout block */
1686        cb.callout_number   = ecode[1];        cb.callout_number   = ecode[1];
1687        cb.offset_vector    = md->offset_vector;        cb.offset_vector    = md->offset_vector;
1688    #ifdef COMPILE_PCRE8
1689        cb.subject          = (PCRE_SPTR)md->start_subject;        cb.subject          = (PCRE_SPTR)md->start_subject;
1690    #else
1691          cb.subject          = (PCRE_SPTR16)md->start_subject;
1692    #endif
1693        cb.subject_length   = (int)(md->end_subject - md->start_subject);        cb.subject_length   = (int)(md->end_subject - md->start_subject);
1694        cb.start_match      = (int)(mstart - md->start_subject);        cb.start_match      = (int)(mstart - md->start_subject);
1695        cb.current_position = (int)(eptr - md->start_subject);        cb.current_position = (int)(eptr - md->start_subject);
# Line 1642  for (;;) Line 1698  for (;;)
1698        cb.capture_top      = offset_top/2;        cb.capture_top      = offset_top/2;
1699        cb.capture_last     = md->capture_last;        cb.capture_last     = md->capture_last;
1700        cb.callout_data     = md->callout_data;        cb.callout_data     = md->callout_data;
1701        cb.mark             = markptr;        cb.mark             = md->nomatch_mark;
1702        if ((rrc = (*pcre_callout)(&cb)) > 0) MRRETURN(MATCH_NOMATCH);        if ((rrc = (*PUBL(callout))(&cb)) > 0) RRETURN(MATCH_NOMATCH);
1703        if (rrc < 0) RRETURN(rrc);        if (rrc < 0) RRETURN(rrc);
1704        }        }
1705      ecode += 2 + 2*LINK_SIZE;      ecode += 2 + 2*LINK_SIZE;
# Line 1702  for (;;) Line 1758  for (;;)
1758        else        else
1759          {          {
1760          new_recursive.offset_save =          new_recursive.offset_save =
1761            (int *)(pcre_malloc)(new_recursive.saved_max * sizeof(int));            (int *)(PUBL(malloc))(new_recursive.saved_max * sizeof(int));
1762          if (new_recursive.offset_save == NULL) RRETURN(PCRE_ERROR_NOMEMORY);          if (new_recursive.offset_save == NULL) RRETURN(PCRE_ERROR_NOMEMORY);
1763          }          }
1764        memcpy(new_recursive.offset_save, md->offset_vector,        memcpy(new_recursive.offset_save, md->offset_vector,
# Line 1717  for (;;) Line 1773  for (;;)
1773        do        do
1774          {          {
1775          if (cbegroup) md->match_function_type = MATCH_CBEGROUP;          if (cbegroup) md->match_function_type = MATCH_CBEGROUP;
1776          RMATCH(eptr, callpat + _pcre_OP_lengths[*callpat], offset_top,          RMATCH(eptr, callpat + PRIV(OP_lengths)[*callpat], offset_top,
1777            md, eptrb, RM6);            md, eptrb, RM6);
1778          memcpy(md->offset_vector, new_recursive.offset_save,          memcpy(md->offset_vector, new_recursive.offset_save,
1779              new_recursive.saved_max * sizeof(int));              new_recursive.saved_max * sizeof(int));
# Line 1726  for (;;) Line 1782  for (;;)
1782            {            {
1783            DPRINTF(("Recursion matched\n"));            DPRINTF(("Recursion matched\n"));
1784            if (new_recursive.offset_save != stacksave)            if (new_recursive.offset_save != stacksave)
1785              (pcre_free)(new_recursive.offset_save);              (PUBL(free))(new_recursive.offset_save);
1786    
1787            /* Set where we got to in the subject, and reset the start in case            /* Set where we got to in the subject, and reset the start in case
1788            it was changed by \K. This *is* propagated back out of a recursion,            it was changed by \K. This *is* propagated back out of a recursion,
# Line 1744  for (;;) Line 1800  for (;;)
1800            {            {
1801            DPRINTF(("Recursion gave error %d\n", rrc));            DPRINTF(("Recursion gave error %d\n", rrc));
1802            if (new_recursive.offset_save != stacksave)            if (new_recursive.offset_save != stacksave)
1803              (pcre_free)(new_recursive.offset_save);              (PUBL(free))(new_recursive.offset_save);
1804            RRETURN(rrc);            RRETURN(rrc);
1805            }            }
1806    
# Line 1756  for (;;) Line 1812  for (;;)
1812        DPRINTF(("Recursion didn't match\n"));        DPRINTF(("Recursion didn't match\n"));
1813        md->recursive = new_recursive.prevrec;        md->recursive = new_recursive.prevrec;
1814        if (new_recursive.offset_save != stacksave)        if (new_recursive.offset_save != stacksave)
1815          (pcre_free)(new_recursive.offset_save);          (PUBL(free))(new_recursive.offset_save);
1816        MRRETURN(MATCH_NOMATCH);        RRETURN(MATCH_NOMATCH);
1817        }        }
1818    
1819      RECURSION_MATCHED:      RECURSION_MATCHED:
# Line 1837  for (;;) Line 1893  for (;;)
1893        md->end_match_ptr = eptr;      /* For ONCE_NC */        md->end_match_ptr = eptr;      /* For ONCE_NC */
1894        md->end_offset_top = offset_top;        md->end_offset_top = offset_top;
1895        md->start_match_ptr = mstart;        md->start_match_ptr = mstart;
1896        MRRETURN(MATCH_MATCH);         /* Sets md->mark */        RRETURN(MATCH_MATCH);         /* Sets md->mark */
1897        }        }
1898    
1899      /* For capturing groups we have to check the group number back at the start      /* For capturing groups we have to check the group number back at the start
# Line 1979  for (;;) Line 2035  for (;;)
2035      /* Not multiline mode: start of subject assertion, unless notbol. */      /* Not multiline mode: start of subject assertion, unless notbol. */
2036    
2037      case OP_CIRC:      case OP_CIRC:
2038      if (md->notbol && eptr == md->start_subject) MRRETURN(MATCH_NOMATCH);      if (md->notbol && eptr == md->start_subject) RRETURN(MATCH_NOMATCH);
2039    
2040      /* Start of subject assertion */      /* Start of subject assertion */
2041    
2042      case OP_SOD:      case OP_SOD:
2043      if (eptr != md->start_subject) MRRETURN(MATCH_NOMATCH);      if (eptr != md->start_subject) RRETURN(MATCH_NOMATCH);
2044      ecode++;      ecode++;
2045      break;      break;
2046    
2047      /* Multiline mode: start of subject unless notbol, or after any newline. */      /* Multiline mode: start of subject unless notbol, or after any newline. */
2048    
2049      case OP_CIRCM:      case OP_CIRCM:
2050      if (md->notbol && eptr == md->start_subject) MRRETURN(MATCH_NOMATCH);      if (md->notbol && eptr == md->start_subject) RRETURN(MATCH_NOMATCH);
2051      if (eptr != md->start_subject &&      if (eptr != md->start_subject &&
2052          (eptr == md->end_subject || !WAS_NEWLINE(eptr)))          (eptr == md->end_subject || !WAS_NEWLINE(eptr)))
2053        MRRETURN(MATCH_NOMATCH);        RRETURN(MATCH_NOMATCH);
2054      ecode++;      ecode++;
2055      break;      break;
2056    
2057      /* Start of match assertion */      /* Start of match assertion */
2058    
2059      case OP_SOM:      case OP_SOM:
2060      if (eptr != md->start_subject + md->start_offset) MRRETURN(MATCH_NOMATCH);      if (eptr != md->start_subject + md->start_offset) RRETURN(MATCH_NOMATCH);
2061      ecode++;      ecode++;
2062      break;      break;
2063    
# Line 2017  for (;;) Line 2073  for (;;)
2073    
2074      case OP_DOLLM:      case OP_DOLLM:
2075      if (eptr < md->end_subject)      if (eptr < md->end_subject)
2076        { if (!IS_NEWLINE(eptr)) MRRETURN(MATCH_NOMATCH); }        { if (!IS_NEWLINE(eptr)) RRETURN(MATCH_NOMATCH); }
2077      else      else
2078        {        {
2079        if (md->noteol) MRRETURN(MATCH_NOMATCH);        if (md->noteol) RRETURN(MATCH_NOMATCH);
2080        SCHECK_PARTIAL();        SCHECK_PARTIAL();
2081        }        }
2082      ecode++;      ecode++;
# Line 2030  for (;;) Line 2086  for (;;)
2086      subject unless noteol is set. */      subject unless noteol is set. */
2087    
2088      case OP_DOLL:      case OP_DOLL:
2089      if (md->noteol) MRRETURN(MATCH_NOMATCH);      if (md->noteol) RRETURN(MATCH_NOMATCH);
2090      if (!md->endonly) goto ASSERT_NL_OR_EOS;      if (!md->endonly) goto ASSERT_NL_OR_EOS;
2091    
2092      /* ... else fall through for endonly */      /* ... else fall through for endonly */
# Line 2038  for (;;) Line 2094  for (;;)
2094      /* End of subject assertion (\z) */      /* End of subject assertion (\z) */
2095    
2096      case OP_EOD:      case OP_EOD:
2097      if (eptr < md->end_subject) MRRETURN(MATCH_NOMATCH);      if (eptr < md->end_subject) RRETURN(MATCH_NOMATCH);
2098      SCHECK_PARTIAL();      SCHECK_PARTIAL();
2099      ecode++;      ecode++;
2100      break;      break;
# Line 2049  for (;;) Line 2105  for (;;)
2105      ASSERT_NL_OR_EOS:      ASSERT_NL_OR_EOS:
2106      if (eptr < md->end_subject &&      if (eptr < md->end_subject &&
2107          (!IS_NEWLINE(eptr) || eptr != md->end_subject - md->nllen))          (!IS_NEWLINE(eptr) || eptr != md->end_subject - md->nllen))
2108        MRRETURN(MATCH_NOMATCH);        RRETURN(MATCH_NOMATCH);
2109    
2110      /* Either at end of string or \n before end. */      /* Either at end of string or \n before end. */
2111    
# Line 2068  for (;;) Line 2124  for (;;)
2124        be "non-word" characters. Remember the earliest consulted character for        be "non-word" characters. Remember the earliest consulted character for
2125        partial matching. */        partial matching. */
2126    
2127  #ifdef SUPPORT_UTF8  #ifdef SUPPORT_UTF
2128        if (utf8)        if (utf)
2129          {          {
2130          /* Get status of previous character */          /* Get status of previous character */
2131    
2132          if (eptr == md->start_subject) prev_is_word = FALSE; else          if (eptr == md->start_subject) prev_is_word = FALSE; else
2133            {            {
2134            USPTR lastptr = eptr - 1;            PCRE_PUCHAR lastptr = eptr - 1;
2135            while((*lastptr & 0xc0) == 0x80) lastptr--;            BACKCHAR(lastptr);
2136            if (lastptr < md->start_used_ptr) md->start_used_ptr = lastptr;            if (lastptr < md->start_used_ptr) md->start_used_ptr = lastptr;
2137            GETCHAR(c, lastptr);            GETCHAR(c, lastptr);
2138  #ifdef SUPPORT_UCP  #ifdef SUPPORT_UCP
# Line 2141  for (;;) Line 2197  for (;;)
2197              }              }
2198            else            else
2199  #endif  #endif
2200            prev_is_word = ((md->ctypes[eptr[-1]] & ctype_word) != 0);            prev_is_word = MAX_255(eptr[-1])
2201                && ((md->ctypes[eptr[-1]] & ctype_word) != 0);
2202            }            }
2203    
2204          /* Get status of next character */          /* Get status of next character */
# Line 2164  for (;;) Line 2221  for (;;)
2221            }            }
2222          else          else
2223  #endif  #endif
2224          cur_is_word = ((md->ctypes[*eptr] & ctype_word) != 0);          cur_is_word = MAX_255(*eptr)
2225              && ((md->ctypes[*eptr] & ctype_word) != 0);
2226          }          }
2227    
2228        /* Now see if the situation is what we want */        /* Now see if the situation is what we want */
2229    
2230        if ((*ecode++ == OP_WORD_BOUNDARY)?        if ((*ecode++ == OP_WORD_BOUNDARY)?
2231             cur_is_word == prev_is_word : cur_is_word != prev_is_word)             cur_is_word == prev_is_word : cur_is_word != prev_is_word)
2232          MRRETURN(MATCH_NOMATCH);          RRETURN(MATCH_NOMATCH);
2233        }        }
2234      break;      break;
2235    
2236      /* Match a single character type; inline for speed */      /* Match a single character type; inline for speed */
2237    
2238      case OP_ANY:      case OP_ANY:
2239      if (IS_NEWLINE(eptr)) MRRETURN(MATCH_NOMATCH);      if (IS_NEWLINE(eptr)) RRETURN(MATCH_NOMATCH);
2240      /* Fall through */      /* Fall through */
2241    
2242      case OP_ALLANY:      case OP_ALLANY:
2243      if (eptr >= md->end_subject)   /* DO NOT merge the eptr++ here; it must */      if (eptr >= md->end_subject)   /* DO NOT merge the eptr++ here; it must */
2244        {                            /* not be updated before SCHECK_PARTIAL. */        {                            /* not be updated before SCHECK_PARTIAL. */
2245        SCHECK_PARTIAL();        SCHECK_PARTIAL();
2246        MRRETURN(MATCH_NOMATCH);        RRETURN(MATCH_NOMATCH);
2247        }        }
2248      eptr++;      eptr++;
2249      if (utf8) while (eptr < md->end_subject && (*eptr & 0xc0) == 0x80) eptr++;  #ifdef SUPPORT_UTF
2250        if (utf) ACROSSCHAR(eptr < md->end_subject, *eptr, eptr++);
2251    #endif
2252      ecode++;      ecode++;
2253      break;      break;
2254    
# Line 2199  for (;;) Line 2259  for (;;)
2259      if (eptr >= md->end_subject)   /* DO NOT merge the eptr++ here; it must */      if (eptr >= md->end_subject)   /* DO NOT merge the eptr++ here; it must */
2260        {                            /* not be updated before SCHECK_PARTIAL. */        {                            /* not be updated before SCHECK_PARTIAL. */
2261        SCHECK_PARTIAL();        SCHECK_PARTIAL();
2262        MRRETURN(MATCH_NOMATCH);        RRETURN(MATCH_NOMATCH);
2263        }        }
2264      eptr++;      eptr++;
2265      ecode++;      ecode++;
# Line 2209  for (;;) Line 2269  for (;;)
2269      if (eptr >= md->end_subject)      if (eptr >= md->end_subject)
2270        {        {
2271        SCHECK_PARTIAL();        SCHECK_PARTIAL();
2272        MRRETURN(MATCH_NOMATCH);        RRETURN(MATCH_NOMATCH);
2273        }        }
2274      GETCHARINCTEST(c, eptr);      GETCHARINCTEST(c, eptr);
2275      if (      if (
2276  #ifdef SUPPORT_UTF8  #if defined SUPPORT_UTF || !(defined COMPILE_PCRE8)
2277         c < 256 &&         c < 256 &&
2278  #endif  #endif
2279         (md->ctypes[c] & ctype_digit) != 0         (md->ctypes[c] & ctype_digit) != 0
2280         )         )
2281        MRRETURN(MATCH_NOMATCH);        RRETURN(MATCH_NOMATCH);
2282      ecode++;      ecode++;
2283      break;      break;
2284    
# Line 2226  for (;;) Line 2286  for (;;)
2286      if (eptr >= md->end_subject)      if (eptr >= md->end_subject)
2287        {        {
2288        SCHECK_PARTIAL();        SCHECK_PARTIAL();
2289        MRRETURN(MATCH_NOMATCH);        RRETURN(MATCH_NOMATCH);
2290        }        }
2291      GETCHARINCTEST(c, eptr);      GETCHARINCTEST(c, eptr);
2292      if (      if (
2293  #ifdef SUPPORT_UTF8  #if defined SUPPORT_UTF || !(defined COMPILE_PCRE8)
2294         c >= 256 ||         c > 255 ||
2295  #endif  #endif
2296         (md->ctypes[c] & ctype_digit) == 0         (md->ctypes[c] & ctype_digit) == 0
2297         )         )
2298        MRRETURN(MATCH_NOMATCH);        RRETURN(MATCH_NOMATCH);
2299      ecode++;      ecode++;
2300      break;      break;
2301    
# Line 2243  for (;;) Line 2303  for (;;)
2303      if (eptr >= md->end_subject)      if (eptr >= md->end_subject)
2304        {        {
2305        SCHECK_PARTIAL();        SCHECK_PARTIAL();
2306        MRRETURN(MATCH_NOMATCH);        RRETURN(MATCH_NOMATCH);
2307        }        }
2308      GETCHARINCTEST(c, eptr);      GETCHARINCTEST(c, eptr);
2309      if (      if (
2310  #ifdef SUPPORT_UTF8  #if defined SUPPORT_UTF || !(defined COMPILE_PCRE8)
2311         c < 256 &&         c < 256 &&
2312  #endif  #endif
2313         (md->ctypes[c] & ctype_space) != 0         (md->ctypes[c] & ctype_space) != 0
2314         )         )
2315        MRRETURN(MATCH_NOMATCH);        RRETURN(MATCH_NOMATCH);
2316      ecode++;      ecode++;
2317      break;      break;
2318    
# Line 2260  for (;;) Line 2320  for (;;)
2320      if (eptr >= md->end_subject)      if (eptr >= md->end_subject)
2321        {        {
2322        SCHECK_PARTIAL();        SCHECK_PARTIAL();
2323        MRRETURN(MATCH_NOMATCH);        RRETURN(MATCH_NOMATCH);
2324        }        }
2325      GETCHARINCTEST(c, eptr);      GETCHARINCTEST(c, eptr);
2326      if (      if (
2327  #ifdef SUPPORT_UTF8  #if defined SUPPORT_UTF || !(defined COMPILE_PCRE8)
2328         c >= 256 ||         c > 255 ||
2329  #endif  #endif
2330         (md->ctypes[c] & ctype_space) == 0         (md->ctypes[c] & ctype_space) == 0
2331         )         )
2332        MRRETURN(MATCH_NOMATCH);        RRETURN(MATCH_NOMATCH);
2333      ecode++;      ecode++;
2334      break;      break;
2335    
# Line 2277  for (;;) Line 2337  for (;;)
2337      if (eptr >= md->end_subject)      if (eptr >= md->end_subject)
2338        {        {
2339        SCHECK_PARTIAL();        SCHECK_PARTIAL();
2340        MRRETURN(MATCH_NOMATCH);        RRETURN(MATCH_NOMATCH);
2341        }        }
2342      GETCHARINCTEST(c, eptr);      GETCHARINCTEST(c, eptr);
2343      if (      if (
2344  #ifdef SUPPORT_UTF8  #if defined SUPPORT_UTF || !(defined COMPILE_PCRE8)
2345         c < 256 &&         c < 256 &&
2346  #endif  #endif
2347         (md->ctypes[c] & ctype_word) != 0         (md->ctypes[c] & ctype_word) != 0
2348         )         )
2349        MRRETURN(MATCH_NOMATCH);        RRETURN(MATCH_NOMATCH);
2350      ecode++;      ecode++;
2351      break;      break;
2352    
# Line 2294  for (;;) Line 2354  for (;;)
2354      if (eptr >= md->end_subject)      if (eptr >= md->end_subject)
2355        {        {
2356        SCHECK_PARTIAL();        SCHECK_PARTIAL();
2357        MRRETURN(MATCH_NOMATCH);        RRETURN(MATCH_NOMATCH);
2358        }        }
2359      GETCHARINCTEST(c, eptr);      GETCHARINCTEST(c, eptr);
2360      if (      if (
2361  #ifdef SUPPORT_UTF8  #if defined SUPPORT_UTF || !(defined COMPILE_PCRE8)
2362         c >= 256 ||         c > 255 ||
2363  #endif  #endif
2364         (md->ctypes[c] & ctype_word) == 0         (md->ctypes[c] & ctype_word) == 0
2365         )         )
2366        MRRETURN(MATCH_NOMATCH);        RRETURN(MATCH_NOMATCH);
2367      ecode++;      ecode++;
2368      break;      break;
2369    
# Line 2311  for (;;) Line 2371  for (;;)
2371      if (eptr >= md->end_subject)      if (eptr >= md->end_subject)
2372        {        {
2373        SCHECK_PARTIAL();        SCHECK_PARTIAL();
2374        MRRETURN(MATCH_NOMATCH);        RRETURN(MATCH_NOMATCH);
2375        }        }
2376      GETCHARINCTEST(c, eptr);      GETCHARINCTEST(c, eptr);
2377      switch(c)      switch(c)
2378        {        {
2379        default: MRRETURN(MATCH_NOMATCH);        default: RRETURN(MATCH_NOMATCH);
2380    
2381        case 0x000d:        case 0x000d:
2382        if (eptr < md->end_subject && *eptr == 0x0a) eptr++;        if (eptr < md->end_subject && *eptr == 0x0a) eptr++;
# Line 2330  for (;;) Line 2390  for (;;)
2390        case 0x0085:        case 0x0085:
2391        case 0x2028:        case 0x2028:
2392        case 0x2029:        case 0x2029:
2393        if (md->bsr_anycrlf) MRRETURN(MATCH_NOMATCH);        if (md->bsr_anycrlf) RRETURN(MATCH_NOMATCH);
2394        break;        break;
2395        }        }
2396      ecode++;      ecode++;
# Line 2340  for (;;) Line 2400  for (;;)
2400      if (eptr >= md->end_subject)      if (eptr >= md->end_subject)
2401        {        {
2402        SCHECK_PARTIAL();        SCHECK_PARTIAL();
2403        MRRETURN(MATCH_NOMATCH);        RRETURN(MATCH_NOMATCH);
2404        }        }
2405      GETCHARINCTEST(c, eptr);      GETCHARINCTEST(c, eptr);
2406      switch(c)      switch(c)
# Line 2365  for (;;) Line 2425  for (;;)
2425        case 0x202f:    /* NARROW NO-BREAK SPACE */        case 0x202f:    /* NARROW NO-BREAK SPACE */
2426        case 0x205f:    /* MEDIUM MATHEMATICAL SPACE */        case 0x205f:    /* MEDIUM MATHEMATICAL SPACE */
2427        case 0x3000:    /* IDEOGRAPHIC SPACE */        case 0x3000:    /* IDEOGRAPHIC SPACE */
2428        MRRETURN(MATCH_NOMATCH);        RRETURN(MATCH_NOMATCH);
2429        }        }
2430      ecode++;      ecode++;
2431      break;      break;
# Line 2374  for (;;) Line 2434  for (;;)
2434      if (eptr >= md->end_subject)      if (eptr >= md->end_subject)
2435        {        {
2436        SCHECK_PARTIAL();        SCHECK_PARTIAL();
2437        MRRETURN(MATCH_NOMATCH);        RRETURN(MATCH_NOMATCH);
2438        }        }
2439      GETCHARINCTEST(c, eptr);      GETCHARINCTEST(c, eptr);
2440      switch(c)      switch(c)
2441        {        {
2442        default: MRRETURN(MATCH_NOMATCH);        default: RRETURN(MATCH_NOMATCH);
2443        case 0x09:      /* HT */        case 0x09:      /* HT */
2444        case 0x20:      /* SPACE */        case 0x20:      /* SPACE */
2445        case 0xa0:      /* NBSP */        case 0xa0:      /* NBSP */
# Line 2408  for (;;) Line 2468  for (;;)
2468      if (eptr >= md->end_subject)      if (eptr >= md->end_subject)
2469        {        {
2470        SCHECK_PARTIAL();        SCHECK_PARTIAL();
2471        MRRETURN(MATCH_NOMATCH);        RRETURN(MATCH_NOMATCH);
2472        }        }
2473      GETCHARINCTEST(c, eptr);      GETCHARINCTEST(c, eptr);
2474      switch(c)      switch(c)
# Line 2421  for (;;) Line 2481  for (;;)
2481        case 0x85:      /* NEL */        case 0x85:      /* NEL */
2482        case 0x2028:    /* LINE SEPARATOR */        case 0x2028:    /* LINE SEPARATOR */
2483        case 0x2029:    /* PARAGRAPH SEPARATOR */        case 0x2029:    /* PARAGRAPH SEPARATOR */
2484        MRRETURN(MATCH_NOMATCH);        RRETURN(MATCH_NOMATCH);
2485        }        }
2486      ecode++;      ecode++;
2487      break;      break;
# Line 2430  for (;;) Line 2490  for (;;)
2490      if (eptr >= md->end_subject)      if (eptr >= md->end_subject)
2491        {        {
2492        SCHECK_PARTIAL();        SCHECK_PARTIAL();
2493        MRRETURN(MATCH_NOMATCH);        RRETURN(MATCH_NOMATCH);
2494        }        }
2495      GETCHARINCTEST(c, eptr);      GETCHARINCTEST(c, eptr);
2496      switch(c)      switch(c)
2497        {        {
2498        default: MRRETURN(MATCH_NOMATCH);        default: RRETURN(MATCH_NOMATCH);
2499        case 0x0a:      /* LF */        case 0x0a:      /* LF */
2500        case 0x0b:      /* VT */        case 0x0b:      /* VT */
2501        case 0x0c:      /* FF */        case 0x0c:      /* FF */
# Line 2457  for (;;) Line 2517  for (;;)
2517      if (eptr >= md->end_subject)      if (eptr >= md->end_subject)
2518        {        {
2519        SCHECK_PARTIAL();        SCHECK_PARTIAL();
2520        MRRETURN(MATCH_NOMATCH);        RRETURN(MATCH_NOMATCH);
2521        }        }
2522      GETCHARINCTEST(c, eptr);      GETCHARINCTEST(c, eptr);
2523        {        {
# Line 2466  for (;;) Line 2526  for (;;)
2526        switch(ecode[1])        switch(ecode[1])
2527          {          {
2528          case PT_ANY:          case PT_ANY:
2529          if (op == OP_NOTPROP) MRRETURN(MATCH_NOMATCH);          if (op == OP_NOTPROP) RRETURN(MATCH_NOMATCH);
2530          break;          break;
2531    
2532          case PT_LAMP:          case PT_LAMP:
2533          if ((prop->chartype == ucp_Lu ||          if ((prop->chartype == ucp_Lu ||
2534               prop->chartype == ucp_Ll ||               prop->chartype == ucp_Ll ||
2535               prop->chartype == ucp_Lt) == (op == OP_NOTPROP))               prop->chartype == ucp_Lt) == (op == OP_NOTPROP))
2536            MRRETURN(MATCH_NOMATCH);            RRETURN(MATCH_NOMATCH);
2537          break;          break;
2538    
2539          case PT_GC:          case PT_GC:
2540          if ((ecode[2] != _pcre_ucp_gentype[prop->chartype]) == (op == OP_PROP))          if ((ecode[2] != PRIV(ucp_gentype)[prop->chartype]) == (op == OP_PROP))
2541            MRRETURN(MATCH_NOMATCH);            RRETURN(MATCH_NOMATCH);
2542          break;          break;
2543    
2544          case PT_PC:          case PT_PC:
2545          if ((ecode[2] != prop->chartype) == (op == OP_PROP))          if ((ecode[2] != prop->chartype) == (op == OP_PROP))
2546            MRRETURN(MATCH_NOMATCH);            RRETURN(MATCH_NOMATCH);
2547          break;          break;
2548    
2549          case PT_SC:          case PT_SC:
2550          if ((ecode[2] != prop->script) == (op == OP_PROP))          if ((ecode[2] != prop->script) == (op == OP_PROP))
2551            MRRETURN(MATCH_NOMATCH);            RRETURN(MATCH_NOMATCH);
2552          break;          break;
2553    
2554          /* These are specials */          /* These are specials */
2555    
2556          case PT_ALNUM:          case PT_ALNUM:
2557          if ((_pcre_ucp_gentype[prop->chartype] == ucp_L ||          if ((PRIV(ucp_gentype)[prop->chartype] == ucp_L ||
2558               _pcre_ucp_gentype[prop->chartype] == ucp_N) == (op == OP_NOTPROP))               PRIV(ucp_gentype)[prop->chartype] == ucp_N) == (op == OP_NOTPROP))
2559            MRRETURN(MATCH_NOMATCH);            RRETURN(MATCH_NOMATCH);
2560          break;          break;
2561    
2562          case PT_SPACE:    /* Perl space */          case PT_SPACE:    /* Perl space */
2563          if ((_pcre_ucp_gentype[prop->chartype] == ucp_Z ||          if ((PRIV(ucp_gentype)[prop->chartype] == ucp_Z ||
2564               c == CHAR_HT || c == CHAR_NL || c == CHAR_FF || c == CHAR_CR)               c == CHAR_HT || c == CHAR_NL || c == CHAR_FF || c == CHAR_CR)
2565                 == (op == OP_NOTPROP))                 == (op == OP_NOTPROP))
2566            MRRETURN(MATCH_NOMATCH);            RRETURN(MATCH_NOMATCH);
2567          break;          break;
2568    
2569          case PT_PXSPACE:  /* POSIX space */          case PT_PXSPACE:  /* POSIX space */
2570          if ((_pcre_ucp_gentype[prop->chartype] == ucp_Z ||          if ((PRIV(ucp_gentype)[prop->chartype] == ucp_Z ||
2571               c == CHAR_HT || c == CHAR_NL || c == CHAR_VT ||               c == CHAR_HT || c == CHAR_NL || c == CHAR_VT ||
2572               c == CHAR_FF || c == CHAR_CR)               c == CHAR_FF || c == CHAR_CR)
2573                 == (op == OP_NOTPROP))                 == (op == OP_NOTPROP))
2574            MRRETURN(MATCH_NOMATCH);            RRETURN(MATCH_NOMATCH);
2575          break;          break;
2576    
2577          case PT_WORD:          case PT_WORD:
2578          if ((_pcre_ucp_gentype[prop->chartype] == ucp_L ||          if ((PRIV(ucp_gentype)[prop->chartype] == ucp_L ||
2579               _pcre_ucp_gentype[prop->chartype] == ucp_N ||               PRIV(ucp_gentype)[prop->chartype] == ucp_N ||
2580               c == CHAR_UNDERSCORE) == (op == OP_NOTPROP))               c == CHAR_UNDERSCORE) == (op == OP_NOTPROP))
2581            MRRETURN(MATCH_NOMATCH);            RRETURN(MATCH_NOMATCH);
2582          break;          break;
2583    
2584          /* This should never occur */          /* This should never occur */
# Line 2538  for (;;) Line 2598  for (;;)
2598      if (eptr >= md->end_subject)      if (eptr >= md->end_subject)
2599        {        {
2600        SCHECK_PARTIAL();        SCHECK_PARTIAL();
2601        MRRETURN(MATCH_NOMATCH);        RRETURN(MATCH_NOMATCH);
2602        }        }
2603      GETCHARINCTEST(c, eptr);      GETCHARINCTEST(c, eptr);
2604      if (UCD_CATEGORY(c) == ucp_M) MRRETURN(MATCH_NOMATCH);      if (UCD_CATEGORY(c) == ucp_M) RRETURN(MATCH_NOMATCH);
2605      while (eptr < md->end_subject)      while (eptr < md->end_subject)
2606        {        {
2607        int len = 1;        int len = 1;
2608        if (!utf8) c = *eptr; else { GETCHARLEN(c, eptr, len); }        if (!utf) c = *eptr; else { GETCHARLEN(c, eptr, len); }
2609        if (UCD_CATEGORY(c) != ucp_M) break;        if (UCD_CATEGORY(c) != ucp_M) break;
2610        eptr += len;        eptr += len;
2611        }        }
2612        if (md->partial != 0 && eptr >= md->end_subject)
2613          {
2614          SCHECK_PARTIAL();
2615          }
2616      ecode++;      ecode++;
2617      break;      break;
2618  #endif  #endif
# Line 2566  for (;;) Line 2630  for (;;)
2630      case OP_REFI:      case OP_REFI:
2631      caseless = op == OP_REFI;      caseless = op == OP_REFI;
2632      offset = GET2(ecode, 1) << 1;               /* Doubled ref number */      offset = GET2(ecode, 1) << 1;               /* Doubled ref number */
2633      ecode += 3;      ecode += 1 + IMM2_SIZE;
2634    
2635      /* If the reference is unset, there are two possibilities:      /* If the reference is unset, there are two possibilities:
2636    
# Line 2606  for (;;) Line 2670  for (;;)
2670        case OP_CRMINRANGE:        case OP_CRMINRANGE:
2671        minimize = (*ecode == OP_CRMINRANGE);        minimize = (*ecode == OP_CRMINRANGE);
2672        min = GET2(ecode, 1);        min = GET2(ecode, 1);
2673        max = GET2(ecode, 3);        max = GET2(ecode, 1 + IMM2_SIZE);
2674        if (max == 0) max = INT_MAX;        if (max == 0) max = INT_MAX;
2675        ecode += 5;        ecode += 1 + 2 * IMM2_SIZE;
2676        break;        break;
2677    
2678        default:               /* No repeat follows */        default:               /* No repeat follows */
2679        if ((length = match_ref(offset, eptr, length, md, caseless)) < 0)        if ((length = match_ref(offset, eptr, length, md, caseless)) < 0)
2680          {          {
2681            eptr += -(length + 1);
2682          CHECK_PARTIAL();          CHECK_PARTIAL();
2683          MRRETURN(MATCH_NOMATCH);          RRETURN(MATCH_NOMATCH);
2684          }          }
2685        eptr += length;        eptr += length;
2686        continue;              /* With the main loop */        continue;              /* With the main loop */
2687        }        }
2688    
2689      /* Handle repeated back references. If the length of the reference is      /* Handle repeated back references. If the length of the reference is
2690      zero, just continue with the main loop. */      zero, just continue with the main loop. If the length is negative, it
2691        means the reference is unset in non-Java-compatible mode. If the minimum is
2692        zero, we can continue at the same level without recursion. For any other
2693        minimum, carrying on will result in NOMATCH. */
2694    
2695      if (length == 0) continue;      if (length == 0) continue;
2696        if (length < 0 && min == 0) continue;
2697    
2698      /* First, ensure the minimum number of matches are present. We get back      /* First, ensure the minimum number of matches are present. We get back
2699      the length of the reference string explicitly rather than passing the      the length of the reference string explicitly rather than passing the
# Line 2635  for (;;) Line 2704  for (;;)
2704        int slength;        int slength;
2705        if ((slength = match_ref(offset, eptr, length, md, caseless)) < 0)        if ((slength = match_ref(offset, eptr, length, md, caseless)) < 0)
2706          {          {
2707            eptr += -(slength + 1);
2708          CHECK_PARTIAL();          CHECK_PARTIAL();
2709          MRRETURN(MATCH_NOMATCH);          RRETURN(MATCH_NOMATCH);
2710          }          }
2711        eptr += slength;        eptr += slength;
2712        }        }
# Line 2655  for (;;) Line 2725  for (;;)
2725          int slength;          int slength;
2726          RMATCH(eptr, ecode, offset_top, md, eptrb, RM14);          RMATCH(eptr, ecode, offset_top, md, eptrb, RM14);
2727          if (rrc != MATCH_NOMATCH) RRETURN(rrc);          if (rrc != MATCH_NOMATCH) RRETURN(rrc);
2728          if (fi >= max) MRRETURN(MATCH_NOMATCH);          if (fi >= max) RRETURN(MATCH_NOMATCH);
2729          if ((slength = match_ref(offset, eptr, length, md, caseless)) < 0)          if ((slength = match_ref(offset, eptr, length, md, caseless)) < 0)
2730            {            {
2731              eptr += -(slength + 1);
2732            CHECK_PARTIAL();            CHECK_PARTIAL();
2733            MRRETURN(MATCH_NOMATCH);            RRETURN(MATCH_NOMATCH);
2734            }            }
2735          eptr += slength;          eptr += slength;
2736          }          }
# Line 2676  for (;;) Line 2747  for (;;)
2747          int slength;          int slength;
2748          if ((slength = match_ref(offset, eptr, length, md, caseless)) < 0)          if ((slength = match_ref(offset, eptr, length, md, caseless)) < 0)
2749            {            {
2750              /* Restore the eptr after the check. */
2751              eptr += -(slength + 1);
2752            CHECK_PARTIAL();            CHECK_PARTIAL();
2753              eptr -= -(slength + 1);
2754            break;            break;
2755            }            }
2756          eptr += slength;          eptr += slength;
# Line 2687  for (;;) Line 2761  for (;;)
2761          if (rrc != MATCH_NOMATCH) RRETURN(rrc);          if (rrc != MATCH_NOMATCH) RRETURN(rrc);
2762          eptr -= length;          eptr -= length;
2763          }          }
2764        MRRETURN(MATCH_NOMATCH);        RRETURN(MATCH_NOMATCH);
2765        }        }
2766      /* Control never gets here */      /* Control never gets here */
2767    
# Line 2705  for (;;) Line 2779  for (;;)
2779      case OP_NCLASS:      case OP_NCLASS:
2780      case OP_CLASS:      case OP_CLASS:
2781        {        {
2782          /* The data variable is saved across frames, so the byte map needs to
2783          be stored there. */
2784    #define BYTE_MAP ((pcre_uint8 *)data)
2785        data = ecode + 1;                /* Save for matching */        data = ecode + 1;                /* Save for matching */
2786        ecode += 33;                     /* Advance past the item */        ecode += 1 + (32 / sizeof(pcre_uchar)); /* Advance past the item */
2787    
2788        switch (*ecode)        switch (*ecode)
2789          {          {
# Line 2727  for (;;) Line 2804  for (;;)
2804          case OP_CRMINRANGE:          case OP_CRMINRANGE:
2805          minimize = (*ecode == OP_CRMINRANGE);          minimize = (*ecode == OP_CRMINRANGE);
2806          min = GET2(ecode, 1);          min = GET2(ecode, 1);
2807          max = GET2(ecode, 3);          max = GET2(ecode, 1 + IMM2_SIZE);
2808          if (max == 0) max = INT_MAX;          if (max == 0) max = INT_MAX;
2809          ecode += 5;          ecode += 1 + 2 * IMM2_SIZE;
2810          break;          break;
2811    
2812          default:               /* No repeat follows */          default:               /* No repeat follows */
# Line 2739  for (;;) Line 2816  for (;;)
2816    
2817        /* First, ensure the minimum number of matches are present. */        /* First, ensure the minimum number of matches are present. */
2818    
2819  #ifdef SUPPORT_UTF8  #ifdef SUPPORT_UTF
2820        /* UTF-8 mode */        if (utf)
       if (utf8)  
2821          {          {
2822          for (i = 1; i <= min; i++)          for (i = 1; i <= min; i++)
2823            {            {
2824            if (eptr >= md->end_subject)            if (eptr >= md->end_subject)
2825              {              {
2826              SCHECK_PARTIAL();              SCHECK_PARTIAL();
2827              MRRETURN(MATCH_NOMATCH);              RRETURN(MATCH_NOMATCH);
2828              }              }
2829            GETCHARINC(c, eptr);            GETCHARINC(c, eptr);
2830            if (c > 255)            if (c > 255)
2831              {              {
2832              if (op == OP_CLASS) MRRETURN(MATCH_NOMATCH);              if (op == OP_CLASS) RRETURN(MATCH_NOMATCH);
2833              }              }
2834            else            else
2835              {              if ((BYTE_MAP[c/8] & (1 << (c&7))) == 0) RRETURN(MATCH_NOMATCH);
             if ((data[c/8] & (1 << (c&7))) == 0) MRRETURN(MATCH_NOMATCH);  
             }  
2836            }            }
2837          }          }
2838        else        else
2839  #endif  #endif
2840        /* Not UTF-8 mode */        /* Not UTF mode */
2841          {          {
2842          for (i = 1; i <= min; i++)          for (i = 1; i <= min; i++)
2843            {            {
2844            if (eptr >= md->end_subject)            if (eptr >= md->end_subject)
2845              {              {
2846              SCHECK_PARTIAL();              SCHECK_PARTIAL();
2847              MRRETURN(MATCH_NOMATCH);              RRETURN(MATCH_NOMATCH);
2848              }              }
2849            c = *eptr++;            c = *eptr++;
2850            if ((data[c/8] & (1 << (c&7))) == 0) MRRETURN(MATCH_NOMATCH);  #ifndef COMPILE_PCRE8
2851              if (c > 255)
2852                {
2853                if (op == OP_CLASS) RRETURN(MATCH_NOMATCH);
2854                }
2855              else
2856    #endif
2857                if ((BYTE_MAP[c/8] & (1 << (c&7))) == 0) RRETURN(MATCH_NOMATCH);
2858            }            }
2859          }          }
2860    
# Line 2787  for (;;) Line 2868  for (;;)
2868    
2869        if (minimize)        if (minimize)
2870          {          {
2871  #ifdef SUPPORT_UTF8  #ifdef SUPPORT_UTF
2872          /* UTF-8 mode */          if (utf)
         if (utf8)  
2873            {            {
2874            for (fi = min;; fi++)            for (fi = min;; fi++)
2875              {              {
2876              RMATCH(eptr, ecode, offset_top, md, eptrb, RM16);              RMATCH(eptr, ecode, offset_top, md, eptrb, RM16);
2877              if (rrc != MATCH_NOMATCH) RRETURN(rrc);              if (rrc != MATCH_NOMATCH) RRETURN(rrc);
2878              if (fi >= max) MRRETURN(MATCH_NOMATCH);              if (fi >= max) RRETURN(MATCH_NOMATCH);
2879              if (eptr >= md->end_subject)              if (eptr >= md->end_subject)
2880                {                {
2881                SCHECK_PARTIAL();                SCHECK_PARTIAL();
2882                MRRETURN(MATCH_NOMATCH);                RRETURN(MATCH_NOMATCH);
2883                }                }
2884              GETCHARINC(c, eptr);              GETCHARINC(c, eptr);
2885              if (c > 255)              if (c > 255)
2886                {                {
2887                if (op == OP_CLASS) MRRETURN(MATCH_NOMATCH);                if (op == OP_CLASS) RRETURN(MATCH_NOMATCH);
2888                }                }
2889              else              else
2890                {                if ((BYTE_MAP[c/8] & (1 << (c&7))) == 0) RRETURN(MATCH_NOMATCH);
               if ((data[c/8] & (1 << (c&7))) == 0) MRRETURN(MATCH_NOMATCH);  
               }  
2891              }              }
2892            }            }
2893          else          else
2894  #endif  #endif
2895          /* Not UTF-8 mode */          /* Not UTF mode */
2896            {            {
2897            for (fi = min;; fi++)            for (fi = min;; fi++)
2898              {              {
2899              RMATCH(eptr, ecode, offset_top, md, eptrb, RM17);              RMATCH(eptr, ecode, offset_top, md, eptrb, RM17);
2900              if (rrc != MATCH_NOMATCH) RRETURN(rrc);              if (rrc != MATCH_NOMATCH) RRETURN(rrc);
2901              if (fi >= max) MRRETURN(MATCH_NOMATCH);              if (fi >= max) RRETURN(MATCH_NOMATCH);
2902              if (eptr >= md->end_subject)              if (eptr >= md->end_subject)
2903                {                {
2904                SCHECK_PARTIAL();                SCHECK_PARTIAL();
2905                MRRETURN(MATCH_NOMATCH);                RRETURN(MATCH_NOMATCH);
2906                }                }
2907              c = *eptr++;              c = *eptr++;
2908              if ((data[c/8] & (1 << (c&7))) == 0) MRRETURN(MATCH_NOMATCH);  #ifndef COMPILE_PCRE8
2909                if (c > 255)
2910                  {
2911                  if (op == OP_CLASS) RRETURN(MATCH_NOMATCH);
2912                  }
2913                else
2914    #endif
2915                  if ((BYTE_MAP[c/8] & (1 << (c&7))) == 0) RRETURN(MATCH_NOMATCH);
2916              }              }
2917            }            }
2918          /* Control never gets here */          /* Control never gets here */
# Line 2839  for (;;) Line 2924  for (;;)
2924          {          {
2925          pp = eptr;          pp = eptr;
2926    
2927  #ifdef SUPPORT_UTF8  #ifdef SUPPORT_UTF
2928          /* UTF-8 mode */          if (utf)
         if (utf8)  
2929            {            {
2930            for (i = min; i < max; i++)            for (i = min; i < max; i++)
2931              {              {
# Line 2857  for (;;) Line 2941  for (;;)
2941                if (op == OP_CLASS) break;                if (op == OP_CLASS) break;
2942                }                }
2943              else              else
2944                {                if ((BYTE_MAP[c/8] & (1 << (c&7))) == 0) break;
               if ((data[c/8] & (1 << (c&7))) == 0) break;  
               }  
2945              eptr += len;              eptr += len;
2946              }              }
2947            for (;;)            for (;;)
# Line 2872  for (;;) Line 2954  for (;;)
2954            }            }
2955          else          else
2956  #endif  #endif
2957            /* Not UTF-8 mode */            /* Not UTF mode */
2958            {            {
2959            for (i = min; i < max; i++)            for (i = min; i < max; i++)
2960              {              {
# Line 2882  for (;;) Line 2964  for (;;)
2964                break;                break;
2965                }                }
2966              c = *eptr;              c = *eptr;
2967              if ((data[c/8] & (1 << (c&7))) == 0) break;  #ifndef COMPILE_PCRE8
2968                if (c > 255)
2969                  {
2970                  if (op == OP_CLASS) break;
2971                  }
2972                else
2973    #endif
2974                  if ((BYTE_MAP[c/8] & (1 << (c&7))) == 0) break;
2975              eptr++;              eptr++;
2976              }              }
2977            while (eptr >= pp)            while (eptr >= pp)
# Line 2893  for (;;) Line 2982  for (;;)
2982              }              }
2983            }            }
2984    
2985          MRRETURN(MATCH_NOMATCH);          RRETURN(MATCH_NOMATCH);
2986          }          }
2987    #undef BYTE_MAP
2988        }        }
2989      /* Control never gets here */      /* Control never gets here */
2990    
# Line 2903  for (;;) Line 2993  for (;;)
2993      when UTF-8 mode mode is supported. Nevertheless, we may not be in UTF-8      when UTF-8 mode mode is supported. Nevertheless, we may not be in UTF-8
2994      mode, because Unicode properties are supported in non-UTF-8 mode. */      mode, because Unicode properties are supported in non-UTF-8 mode. */
2995    
2996  #ifdef SUPPORT_UTF8  #if defined SUPPORT_UTF || !defined COMPILE_PCRE8
2997      case OP_XCLASS:      case OP_XCLASS:
2998        {        {
2999        data = ecode + 1 + LINK_SIZE;                /* Save for matching */        data = ecode + 1 + LINK_SIZE;                /* Save for matching */
# Line 2928  for (;;) Line 3018  for (;;)
3018          case OP_CRMINRANGE:          case OP_CRMINRANGE:
3019          minimize = (*ecode == OP_CRMINRANGE);          minimize = (*ecode == OP_CRMINRANGE);
3020          min = GET2(ecode, 1);          min = GET2(ecode, 1);
3021          max = GET2(ecode, 3);          max = GET2(ecode, 1 + IMM2_SIZE);
3022          if (max == 0) max = INT_MAX;          if (max == 0) max = INT_MAX;
3023          ecode += 5;          ecode += 1 + 2 * IMM2_SIZE;
3024          break;          break;
3025    
3026          default:               /* No repeat follows */          default:               /* No repeat follows */
# Line 2945  for (;;) Line 3035  for (;;)
3035          if (eptr >= md->end_subject)          if (eptr >= md->end_subject)
3036            {            {
3037            SCHECK_PARTIAL();            SCHECK_PARTIAL();
3038            MRRETURN(MATCH_NOMATCH);            RRETURN(MATCH_NOMATCH);
3039            }            }
3040          GETCHARINCTEST(c, eptr);          GETCHARINCTEST(c, eptr);
3041          if (!_pcre_xclass(c, data)) MRRETURN(MATCH_NOMATCH);          if (!PRIV(xclass)(c, data, utf)) RRETURN(MATCH_NOMATCH);
3042          }          }
3043    
3044        /* If max == min we can continue with the main loop without the        /* If max == min we can continue with the main loop without the
# Line 2965  for (;;) Line 3055  for (;;)
3055            {            {
3056            RMATCH(eptr, ecode, offset_top, md, eptrb, RM20);            RMATCH(eptr, ecode, offset_top, md, eptrb, RM20);
3057            if (rrc != MATCH_NOMATCH) RRETURN(rrc);            if (rrc != MATCH_NOMATCH) RRETURN(rrc);
3058            if (fi >= max) MRRETURN(MATCH_NOMATCH);            if (fi >= max) RRETURN(MATCH_NOMATCH);
3059            if (eptr >= md->end_subject)            if (eptr >= md->end_subject)
3060              {              {
3061              SCHECK_PARTIAL();              SCHECK_PARTIAL();
3062              MRRETURN(MATCH_NOMATCH);              RRETURN(MATCH_NOMATCH);
3063              }              }
3064            GETCHARINCTEST(c, eptr);            GETCHARINCTEST(c, eptr);
3065            if (!_pcre_xclass(c, data)) MRRETURN(MATCH_NOMATCH);            if (!PRIV(xclass)(c, data, utf)) RRETURN(MATCH_NOMATCH);
3066            }            }
3067          /* Control never gets here */          /* Control never gets here */
3068          }          }
# Line 2990  for (;;) Line 3080  for (;;)
3080              SCHECK_PARTIAL();              SCHECK_PARTIAL();
3081              break;              break;
3082              }              }
3083    #ifdef SUPPORT_UTF
3084            GETCHARLENTEST(c, eptr, len);            GETCHARLENTEST(c, eptr, len);
3085            if (!_pcre_xclass(c, data)) break;  #else
3086              c = *eptr;
3087    #endif
3088              if (!PRIV(xclass)(c, data, utf)) break;
3089            eptr += len;            eptr += len;
3090            }            }
3091          for(;;)          for(;;)
# Line 2999  for (;;) Line 3093  for (;;)
3093            RMATCH(eptr, ecode, offset_top, md, eptrb, RM21);            RMATCH(eptr, ecode, offset_top, md, eptrb, RM21);
3094            if (rrc != MATCH_NOMATCH) RRETURN(rrc);            if (rrc != MATCH_NOMATCH) RRETURN(rrc);
3095            if (eptr-- == pp) break;        /* Stop if tried at original pos */            if (eptr-- == pp) break;        /* Stop if tried at original pos */
3096            if (utf8) BACKCHAR(eptr);  #ifdef SUPPORT_UTF
3097              if (utf) BACKCHAR(eptr);
3098    #endif
3099            }            }
3100          MRRETURN(MATCH_NOMATCH);          RRETURN(MATCH_NOMATCH);
3101          }          }
3102    
3103        /* Control never gets here */        /* Control never gets here */
# Line 3011  for (;;) Line 3107  for (;;)
3107      /* Match a single character, casefully */      /* Match a single character, casefully */
3108    
3109      case OP_CHAR:      case OP_CHAR:
3110  #ifdef SUPPORT_UTF8  #ifdef SUPPORT_UTF
3111      if (utf8)      if (utf)
3112        {        {
3113        length = 1;        length = 1;
3114        ecode++;        ecode++;
# Line 3020  for (;;) Line 3116  for (;;)
3116        if (length > md->end_subject - eptr)        if (length > md->end_subject - eptr)
3117          {          {
3118          CHECK_PARTIAL();             /* Not SCHECK_PARTIAL() */          CHECK_PARTIAL();             /* Not SCHECK_PARTIAL() */
3119          MRRETURN(MATCH_NOMATCH);          RRETURN(MATCH_NOMATCH);
3120          }          }
3121        while (length-- > 0) if (*ecode++ != *eptr++) MRRETURN(MATCH_NOMATCH);        while (length-- > 0) if (*ecode++ != *eptr++) RRETURN(MATCH_NOMATCH);
3122        }        }
3123      else      else
3124  #endif  #endif
3125        /* Not UTF mode */
     /* Non-UTF-8 mode */  
3126        {        {
3127        if (md->end_subject - eptr < 1)        if (md->end_subject - eptr < 1)
3128          {          {
3129          SCHECK_PARTIAL();            /* This one can use SCHECK_PARTIAL() */          SCHECK_PARTIAL();            /* This one can use SCHECK_PARTIAL() */
3130          MRRETURN(MATCH_NOMATCH);          RRETURN(MATCH_NOMATCH);
3131          }          }
3132        if (ecode[1] != *eptr++) MRRETURN(MATCH_NOMATCH);        if (ecode[1] != *eptr++) RRETURN(MATCH_NOMATCH);
3133        ecode += 2;        ecode += 2;
3134        }        }
3135      break;      break;
3136    
3137      /* Match a single character, caselessly */      /* Match a single character, caselessly. If we are at the end of the
3138        subject, give up immediately. */
3139    
3140      case OP_CHARI:      case OP_CHARI:
3141  #ifdef SUPPORT_UTF8      if (eptr >= md->end_subject)
3142      if (utf8)        {
3143          SCHECK_PARTIAL();
3144          RRETURN(MATCH_NOMATCH);
3145          }
3146    
3147    #ifdef SUPPORT_UTF
3148        if (utf)
3149        {        {
3150        length = 1;        length = 1;
3151        ecode++;        ecode++;
3152        GETCHARLEN(fc, ecode, length);        GETCHARLEN(fc, ecode, length);
3153    
       if (length > md->end_subject - eptr)  
         {  
         CHECK_PARTIAL();             /* Not SCHECK_PARTIAL() */  
         MRRETURN(MATCH_NOMATCH);  
         }  
   
3154        /* If the pattern character's value is < 128, we have only one byte, and        /* If the pattern character's value is < 128, we have only one byte, and
3155        can use the fast lookup table. */        we know that its other case must also be one byte long, so we can use the
3156          fast lookup table. We know that there is at least one byte left in the
3157          subject. */
3158    
3159        if (fc < 128)        if (fc < 128)
3160          {          {
3161          if (md->lcc[*ecode++] != md->lcc[*eptr++]) MRRETURN(MATCH_NOMATCH);          if (md->lcc[fc]
3162                != TABLE_GET(*eptr, md->lcc, *eptr)) RRETURN(MATCH_NOMATCH);
3163            ecode++;
3164            eptr++;
3165          }          }
3166    
3167        /* Otherwise we must pick up the subject character */        /* Otherwise we must pick up the subject character. Note that we cannot
3168          use the value of "length" to check for sufficient bytes left, because the
3169          other case of the character may have more or fewer bytes.  */
3170    
3171        else        else
3172          {          {
# Line 3079  for (;;) Line 3182  for (;;)
3182  #ifdef SUPPORT_UCP  #ifdef SUPPORT_UCP
3183            if (dc != UCD_OTHERCASE(fc))            if (dc != UCD_OTHERCASE(fc))
3184  #endif  #endif
3185              MRRETURN(MATCH_NOMATCH);              RRETURN(MATCH_NOMATCH);
3186            }            }
3187          }          }
3188        }        }
3189      else      else
3190  #endif   /* SUPPORT_UTF8 */  #endif   /* SUPPORT_UTF */
3191    
3192      /* Non-UTF-8 mode */      /* Not UTF mode */
3193        {        {
3194        if (md->end_subject - eptr < 1)        if (TABLE_GET(ecode[1], md->lcc, ecode[1])
3195          {            != TABLE_GET(*eptr, md->lcc, *eptr)) RRETURN(MATCH_NOMATCH);
3196          SCHECK_PARTIAL();            /* This one can use SCHECK_PARTIAL() */        eptr++;
         MRRETURN(MATCH_NOMATCH);  
         }  
       if (md->lcc[ecode[1]] != md->lcc[*eptr++]) MRRETURN(MATCH_NOMATCH);  
3197        ecode += 2;        ecode += 2;
3198        }        }
3199      break;      break;
# Line 3103  for (;;) Line 3203  for (;;)
3203      case OP_EXACT:      case OP_EXACT:
3204      case OP_EXACTI:      case OP_EXACTI:
3205      min = max = GET2(ecode, 1);      min = max = GET2(ecode, 1);
3206      ecode += 3;      ecode += 1 + IMM2_SIZE;
3207      goto REPEATCHAR;      goto REPEATCHAR;
3208    
3209      case OP_POSUPTO:      case OP_POSUPTO:
# Line 3118  for (;;) Line 3218  for (;;)
3218      min = 0;      min = 0;
3219      max = GET2(ecode, 1);      max = GET2(ecode, 1);
3220      minimize = *ecode == OP_MINUPTO || *ecode == OP_MINUPTOI;      minimize = *ecode == OP_MINUPTO || *ecode == OP_MINUPTOI;
3221      ecode += 3;      ecode += 1 + IMM2_SIZE;
3222      goto REPEATCHAR;      goto REPEATCHAR;
3223    
3224      case OP_POSSTAR:      case OP_POSSTAR:
# Line 3166  for (;;) Line 3266  for (;;)
3266      /* Common code for all repeated single-character matches. */      /* Common code for all repeated single-character matches. */
3267    
3268      REPEATCHAR:      REPEATCHAR:
3269  #ifdef SUPPORT_UTF8  #ifdef SUPPORT_UTF
3270      if (utf8)      if (utf)
3271        {        {
3272        length = 1;        length = 1;
3273        charptr = ecode;        charptr = ecode;
# Line 3183  for (;;) Line 3283  for (;;)
3283          unsigned int othercase;          unsigned int othercase;
3284          if (op >= OP_STARI &&     /* Caseless */          if (op >= OP_STARI &&     /* Caseless */
3285              (othercase = UCD_OTHERCASE(fc)) != fc)              (othercase = UCD_OTHERCASE(fc)) != fc)
3286            oclength = _pcre_ord2utf8(othercase, occhars);            oclength = PRIV(ord2utf)(othercase, occhars);
3287          else oclength = 0;          else oclength = 0;
3288  #endif  /* SUPPORT_UCP */  #endif  /* SUPPORT_UCP */
3289    
3290          for (i = 1; i <= min; i++)          for (i = 1; i <= min; i++)
3291            {            {
3292            if (eptr <= md->end_subject - length &&            if (eptr <= md->end_subject - length &&
3293              memcmp(eptr, charptr, length) == 0) eptr += length;              memcmp(eptr, charptr, IN_UCHARS(length)) == 0) eptr += length;
3294  #ifdef SUPPORT_UCP  #ifdef SUPPORT_UCP
3295            else if (oclength > 0 &&            else if (oclength > 0 &&
3296                     eptr <= md->end_subject - oclength &&                     eptr <= md->end_subject - oclength &&
3297                     memcmp(eptr, occhars, oclength) == 0) eptr += oclength;                     memcmp(eptr, occhars, IN_UCHARS(oclength)) == 0) eptr += oclength;
3298  #endif  /* SUPPORT_UCP */  #endif  /* SUPPORT_UCP */
3299            else            else
3300              {              {
3301              CHECK_PARTIAL();              CHECK_PARTIAL();
3302              MRRETURN(MATCH_NOMATCH);              RRETURN(MATCH_NOMATCH);
3303              }              }
3304            }            }
3305    
# Line 3211  for (;;) Line 3311  for (;;)
3311              {              {
3312              RMATCH(eptr, ecode, offset_top, md, eptrb, RM22);              RMATCH(eptr, ecode, offset_top, md, eptrb, RM22);
3313              if (rrc != MATCH_NOMATCH) RRETURN(rrc);              if (rrc != MATCH_NOMATCH) RRETURN(rrc);
3314              if (fi >= max) MRRETURN(MATCH_NOMATCH);              if (fi >= max) RRETURN(MATCH_NOMATCH);
3315              if (eptr <= md->end_subject - length &&              if (eptr <= md->end_subject - length &&
3316                memcmp(eptr, charptr, length) == 0) eptr += length;                memcmp(eptr, charptr, IN_UCHARS(length)) == 0) eptr += length;
3317  #ifdef SUPPORT_UCP  #ifdef SUPPORT_UCP
3318              else if (oclength > 0 &&              else if (oclength > 0 &&
3319                       eptr <= md->end_subject - oclength &&                       eptr <= md->end_subject - oclength &&
3320                       memcmp(eptr, occhars, oclength) == 0) eptr += oclength;                       memcmp(eptr, occhars, IN_UCHARS(oclength)) == 0) eptr += oclength;
3321  #endif  /* SUPPORT_UCP */  #endif  /* SUPPORT_UCP */
3322              else              else
3323                {                {
3324                CHECK_PARTIAL();                CHECK_PARTIAL();
3325                MRRETURN(MATCH_NOMATCH);                RRETURN(MATCH_NOMATCH);
3326                }                }
3327              }              }
3328            /* Control never gets here */            /* Control never gets here */
# Line 3234  for (;;) Line 3334  for (;;)
3334            for (i = min; i < max; i++)            for (i = min; i < max; i++)
3335              {              {
3336              if (eptr <= md->end_subject - length &&              if (eptr <= md->end_subject - length &&
3337                  memcmp(eptr, charptr, length) == 0) eptr += length;                  memcmp(eptr, charptr, IN_UCHARS(length)) == 0) eptr += length;
3338  #ifdef SUPPORT_UCP  #ifdef SUPPORT_UCP
3339              else if (oclength > 0 &&              else if (oclength > 0 &&
3340                       eptr <= md->end_subject - oclength &&                       eptr <= md->end_subject - oclength &&
3341                       memcmp(eptr, occhars, oclength) == 0) eptr += oclength;                       memcmp(eptr, occhars, IN_UCHARS(oclength)) == 0) eptr += oclength;
3342  #endif  /* SUPPORT_UCP */  #endif  /* SUPPORT_UCP */
3343              else              else
3344                {                {
# Line 3253  for (;;) Line 3353  for (;;)
3353              {              {
3354              RMATCH(eptr, ecode, offset_top, md, eptrb, RM23);              RMATCH(eptr, ecode, offset_top, md, eptrb, RM23);
3355              if (rrc != MATCH_NOMATCH) RRETURN(rrc);              if (rrc != MATCH_NOMATCH) RRETURN(rrc);
3356              if (eptr == pp) { MRRETURN(MATCH_NOMATCH); }              if (eptr == pp) { RRETURN(MATCH_NOMATCH); }
3357  #ifdef SUPPORT_UCP  #ifdef SUPPORT_UCP
3358              eptr--;              eptr--;
3359              BACKCHAR(eptr);              BACKCHAR(eptr);
# Line 3270  for (;;) Line 3370  for (;;)
3370        value of fc will always be < 128. */        value of fc will always be < 128. */
3371        }        }
3372      else      else
3373  #endif  /* SUPPORT_UTF8 */  #endif  /* SUPPORT_UTF */
3374          /* When not in UTF-8 mode, load a single-byte character. */
3375      /* When not in UTF-8 mode, load a single-byte character. */        fc = *ecode++;
3376    
3377      fc = *ecode++;      /* The value of fc at this point is always one character, though we may
3378        or may not be in UTF mode. The code is duplicated for the caseless and
     /* The value of fc at this point is always less than 256, though we may or  
     may not be in UTF-8 mode. The code is duplicated for the caseless and  
3379      caseful cases, for speed, since matching characters is likely to be quite      caseful cases, for speed, since matching characters is likely to be quite
3380      common. First, ensure the minimum number of matches are present. If min =      common. First, ensure the minimum number of matches are present. If min =
3381      max, continue at the same level without recursing. Otherwise, if      max, continue at the same level without recursing. Otherwise, if
# Line 3290  for (;;) Line 3388  for (;;)
3388    
3389      if (op >= OP_STARI)  /* Caseless */      if (op >= OP_STARI)  /* Caseless */
3390        {        {
3391        fc = md->lcc[fc];  #ifdef COMPILE_PCRE8
3392          /* fc must be < 128 if UTF is enabled. */
3393          foc = md->fcc[fc];
3394    #else
3395    #ifdef SUPPORT_UTF
3396    #ifdef SUPPORT_UCP
3397          if (utf && fc > 127)
3398            foc = UCD_OTHERCASE(fc);
3399    #else
3400          if (utf && fc > 127)
3401            foc = fc;
3402    #endif /* SUPPORT_UCP */
3403          else
3404    #endif /* SUPPORT_UTF */
3405            foc = TABLE_GET(fc, md->fcc, fc);
3406    #endif /* COMPILE_PCRE8 */
3407    
3408        for (i = 1; i <= min; i++)        for (i = 1; i <= min; i++)
3409          {          {
3410          if (eptr >= md->end_subject)          if (eptr >= md->end_subject)
3411            {            {
3412            SCHECK_PARTIAL();            SCHECK_PARTIAL();
3413            MRRETURN(MATCH_NOMATCH);            RRETURN(MATCH_NOMATCH);
3414            }            }
3415          if (fc != md->lcc[*eptr++]) MRRETURN(MATCH_NOMATCH);          if (fc != *eptr && foc != *eptr) RRETURN(MATCH_NOMATCH);
3416            eptr++;
3417          }          }
3418        if (min == max) continue;        if (min == max) continue;
3419        if (minimize)        if (minimize)
# Line 3307  for (;;) Line 3422  for (;;)
3422            {            {
3423            RMATCH(eptr, ecode, offset_top, md, eptrb, RM24);            RMATCH(eptr, ecode, offset_top, md, eptrb, RM24);
3424            if (rrc != MATCH_NOMATCH) RRETURN(rrc);            if (rrc != MATCH_NOMATCH) RRETURN(rrc);
3425            if (fi >= max) MRRETURN(MATCH_NOMATCH);            if (fi >= max) RRETURN(MATCH_NOMATCH);
3426            if (eptr >= md->end_subject)            if (eptr >= md->end_subject)
3427              {              {
3428              SCHECK_PARTIAL();              SCHECK_PARTIAL();
3429              MRRETURN(MATCH_NOMATCH);              RRETURN(MATCH_NOMATCH);
3430              }              }
3431            if (fc != md->lcc[*eptr++]) MRRETURN(MATCH_NOMATCH);            if (fc != *eptr && foc != *eptr) RRETURN(MATCH_NOMATCH);
3432              eptr++;
3433            }            }
3434          /* Control never gets here */          /* Control never gets here */
3435          }          }
# Line 3327  for (;;) Line 3443  for (;;)
3443              SCHECK_PARTIAL();              SCHECK_PARTIAL();
3444              break;              break;
3445              }              }
3446            if (fc != md->lcc[*eptr]) break;            if (fc != *eptr && foc != *eptr) break;
3447            eptr++;            eptr++;
3448            }            }
3449    
# Line 3339  for (;;) Line 3455  for (;;)
3455            eptr--;            eptr--;
3456            if (rrc != MATCH_NOMATCH) RRETURN(rrc);            if (rrc != MATCH_NOMATCH) RRETURN(rrc);
3457            }            }
3458          MRRETURN(MATCH_NOMATCH);          RRETURN(MATCH_NOMATCH);
3459          }          }
3460        /* Control never gets here */        /* Control never gets here */
3461        }        }
# Line 3353  for (;;) Line 3469  for (;;)
3469          if (eptr >= md->end_subject)          if (eptr >= md->end_subject)
3470            {            {
3471            SCHECK_PARTIAL();            SCHECK_PARTIAL();
3472            MRRETURN(MATCH_NOMATCH);            RRETURN(MATCH_NOMATCH);
3473            }            }
3474          if (fc != *eptr++) MRRETURN(MATCH_NOMATCH);          if (fc != *eptr++) RRETURN(MATCH_NOMATCH);
3475          }          }
3476    
3477        if (min == max) continue;        if (min == max) continue;
# Line 3366  for (;;) Line 3482  for (;;)
3482            {            {
3483            RMATCH(eptr, ecode, offset_top, md, eptrb, RM26);            RMATCH(eptr, ecode, offset_top, md, eptrb, RM26);
3484            if (rrc != MATCH_NOMATCH) RRETURN(rrc);            if (rrc != MATCH_NOMATCH) RRETURN(rrc);
3485            if (fi >= max) MRRETURN(MATCH_NOMATCH);            if (fi >= max) RRETURN(MATCH_NOMATCH);
3486            if (eptr >= md->end_subject)            if (eptr >= md->end_subject)
3487              {              {
3488              SCHECK_PARTIAL();              SCHECK_PARTIAL();
3489              MRRETURN(MATCH_NOMATCH);              RRETURN(MATCH_NOMATCH);
3490              }              }
3491            if (fc != *eptr++) MRRETURN(MATCH_NOMATCH);            if (fc != *eptr++) RRETURN(MATCH_NOMATCH);
3492            }            }
3493          /* Control never gets here */          /* Control never gets here */
3494          }          }
# Line 3397  for (;;) Line 3513  for (;;)
3513            eptr--;            eptr--;
3514            if (rrc != MATCH_NOMATCH) RRETURN(rrc);            if (rrc != MATCH_NOMATCH) RRETURN(rrc);
3515            }            }
3516          MRRETURN(MATCH_NOMATCH);          RRETURN(MATCH_NOMATCH);
3517          }          }
3518        }        }
3519      /* Control never gets here */      /* Control never gets here */
# Line 3410  for (;;) Line 3526  for (;;)
3526      if (eptr >= md->end_subject)      if (eptr >= md->end_subject)
3527        {        {
3528        SCHECK_PARTIAL();        SCHECK_PARTIAL();
3529        MRRETURN(MATCH_NOMATCH);        RRETURN(MATCH_NOMATCH);
3530        }        }
3531      ecode++;      ecode++;
3532      GETCHARINCTEST(c, eptr);      GETCHARINCTEST(c, eptr);
3533      if (op == OP_NOTI)         /* The caseless case */      if (op == OP_NOTI)         /* The caseless case */
3534        {        {
3535  #ifdef SUPPORT_UTF8        register unsigned int ch, och;
3536        if (c < 256)        ch = *ecode++;
3537  #endif  #ifdef COMPILE_PCRE8
3538        c = md->lcc[c];        /* ch must be < 128 if UTF is enabled. */
3539        if (md->lcc[*ecode++] == c) MRRETURN(MATCH_NOMATCH);        och = md->fcc[ch];
3540    #else
3541    #ifdef SUPPORT_UTF
3542    #ifdef SUPPORT_UCP
3543          if (utf && ch > 127)
3544            och = UCD_OTHERCASE(ch);
3545    #else
3546          if (utf && ch > 127)
3547            och = ch;
3548    #endif /* SUPPORT_UCP */
3549          else
3550    #endif /* SUPPORT_UTF */
3551            och = TABLE_GET(ch, md->fcc, ch);
3552    #endif /* COMPILE_PCRE8 */
3553          if (ch == c || och == c) RRETURN(MATCH_NOMATCH);
3554        }        }
3555      else    /* Caseful */      else    /* Caseful */
3556        {        {
3557        if (*ecode++ == c) MRRETURN(MATCH_NOMATCH);        if (*ecode++ == c) RRETURN(MATCH_NOMATCH);
3558        }        }
3559      break;      break;
3560    
# Line 3438  for (;;) Line 3568  for (;;)
3568      case OP_NOTEXACT:      case OP_NOTEXACT:
3569      case OP_NOTEXACTI:      case OP_NOTEXACTI:
3570      min = max = GET2(ecode, 1);      min = max = GET2(ecode, 1);
3571      ecode += 3;      ecode += 1 + IMM2_SIZE;
3572      goto REPEATNOTCHAR;      goto REPEATNOTCHAR;
3573    
3574      case OP_NOTUPTO:      case OP_NOTUPTO:
# Line 3448  for (;;) Line 3578  for (;;)
3578      min = 0;      min = 0;
3579      max = GET2(ecode, 1);      max = GET2(ecode, 1);
3580      minimize = *ecode == OP_NOTMINUPTO || *ecode == OP_NOTMINUPTOI;      minimize = *ecode == OP_NOTMINUPTO || *ecode == OP_NOTMINUPTOI;
3581      ecode += 3;      ecode += 1 + IMM2_SIZE;
3582      goto REPEATNOTCHAR;      goto REPEATNOTCHAR;
3583    
3584      case OP_NOTPOSSTAR:      case OP_NOTPOSSTAR:
# Line 3480  for (;;) Line 3610  for (;;)
3610      possessive = TRUE;      possessive = TRUE;
3611      min = 0;      min = 0;
3612      max = GET2(ecode, 1);      max = GET2(ecode, 1);
3613      ecode += 3;      ecode += 1 + IMM2_SIZE;
3614      goto REPEATNOTCHAR;      goto REPEATNOTCHAR;
3615    
3616      case OP_NOTSTAR:      case OP_NOTSTAR:
# Line 3519  for (;;) Line 3649  for (;;)
3649    
3650      if (op >= OP_NOTSTARI)     /* Caseless */      if (op >= OP_NOTSTARI)     /* Caseless */
3651        {        {
3652        fc = md->lcc[fc];  #ifdef COMPILE_PCRE8
3653          /* fc must be < 128 if UTF is enabled. */
3654          foc = md->fcc[fc];
3655    #else
3656    #ifdef SUPPORT_UTF
3657    #ifdef SUPPORT_UCP
3658          if (utf && fc > 127)
3659            foc = UCD_OTHERCASE(fc);
3660    #else
3661          if (utf && fc > 127)
3662            foc = fc;
3663    #endif /* SUPPORT_UCP */
3664          else
3665    #endif /* SUPPORT_UTF */
3666            foc = TABLE_GET(fc, md->fcc, fc);
3667    #endif /* COMPILE_PCRE8 */
3668    
3669  #ifdef SUPPORT_UTF8  #ifdef SUPPORT_UTF
3670        /* UTF-8 mode */        if (utf)
       if (utf8)  
3671          {          {
3672          register unsigned int d;          register unsigned int d;
3673          for (i = 1; i <= min; i++)          for (i = 1; i <= min; i++)
# Line 3531  for (;;) Line 3675  for (;;)
3675            if (eptr >= md->end_subject)            if (eptr >= md->end_subject)
3676              {              {
3677              SCHECK_PARTIAL();              SCHECK_PARTIAL();
3678              MRRETURN(MATCH_NOMATCH);              RRETURN(MATCH_NOMATCH);
3679              }              }
3680            GETCHARINC(d, eptr);            GETCHARINC(d, eptr);
3681            if (d < 256) d = md->lcc[d];            if (fc == d || (unsigned int) foc == d) RRETURN(MATCH_NOMATCH);
           if (fc == d) MRRETURN(MATCH_NOMATCH);  
3682            }            }
3683          }          }
3684        else        else
3685  #endif  #endif
3686          /* Not UTF mode */
       /* Not UTF-8 mode */  
3687          {          {
3688          for (i = 1; i <= min; i++)          for (i = 1; i <= min; i++)
3689            {            {
3690            if (eptr >= md->end_subject)            if (eptr >= md->end_subject)
3691              {              {
3692              SCHECK_PARTIAL();              SCHECK_PARTIAL();
3693              MRRETURN(MATCH_NOMATCH);              RRETURN(MATCH_NOMATCH);
3694              }              }
3695            if (fc == md->lcc[*eptr++]) MRRETURN(MATCH_NOMATCH);            if (fc == *eptr || foc == *eptr) RRETURN(MATCH_NOMATCH);
3696              eptr++;
3697            }            }
3698          }          }
3699    
# Line 3558  for (;;) Line 3701  for (;;)
3701    
3702        if (minimize)        if (minimize)
3703          {          {
3704  #ifdef SUPPORT_UTF8  #ifdef SUPPORT_UTF
3705          /* UTF-8 mode */          if (utf)
         if (utf8)  
3706            {            {
3707            register unsigned int d;            register unsigned int d;
3708            for (fi = min;; fi++)            for (fi = min;; fi++)
3709              {              {
3710              RMATCH(eptr, ecode, offset_top, md, eptrb, RM28);              RMATCH(eptr, ecode, offset_top, md, eptrb, RM28);
3711              if (rrc != MATCH_NOMATCH) RRETURN(rrc);              if (rrc != MATCH_NOMATCH) RRETURN(rrc);
3712              if (fi >= max) MRRETURN(MATCH_NOMATCH);              if (fi >= max) RRETURN(MATCH_NOMATCH);
3713              if (eptr >= md->end_subject)              if (eptr >= md->end_subject)
3714                {                {
3715                SCHECK_PARTIAL();                SCHECK_PARTIAL();
3716                MRRETURN(MATCH_NOMATCH);                RRETURN(MATCH_NOMATCH);
3717                }                }
3718              GETCHARINC(d, eptr);              GETCHARINC(d, eptr);
3719              if (d < 256) d = md->lcc[d];              if (fc == d || (unsigned int)foc == d) RRETURN(MATCH_NOMATCH);
             if (fc == d) MRRETURN(MATCH_NOMATCH);  
3720              }              }
3721            }            }
3722          else          else
3723  #endif  #endif
3724          /* Not UTF-8 mode */          /* Not UTF mode */
3725            {            {
3726            for (fi = min;; fi++)            for (fi = min;; fi++)
3727              {              {
3728              RMATCH(eptr, ecode, offset_top, md, eptrb, RM29);              RMATCH(eptr, ecode, offset_top, md, eptrb, RM29);
3729              if (rrc != MATCH_NOMATCH) RRETURN(rrc);              if (rrc != MATCH_NOMATCH) RRETURN(rrc);
3730              if (fi >= max) MRRETURN(MATCH_NOMATCH);              if (fi >= max) RRETURN(MATCH_NOMATCH);
3731              if (eptr >= md->end_subject)              if (eptr >= md->end_subject)
3732                {                {
3733                SCHECK_PARTIAL();                SCHECK_PARTIAL();
3734                MRRETURN(MATCH_NOMATCH);                RRETURN(MATCH_NOMATCH);
3735                }                }
3736              if (fc == md->lcc[*eptr++]) MRRETURN(MATCH_NOMATCH);              if (fc == *eptr || foc == *eptr) RRETURN(MATCH_NOMATCH);
3737                eptr++;
3738              }              }
3739            }            }
3740          /* Control never gets here */          /* Control never gets here */
# Line 3604  for (;;) Line 3746  for (;;)
3746          {          {
3747          pp = eptr;          pp = eptr;
3748    
3749  #ifdef SUPPORT_UTF8  #ifdef SUPPORT_UTF
3750          /* UTF-8 mode */          if (utf)
         if (utf8)  
3751            {            {
3752            register unsigned int d;            register unsigned int d;
3753            for (i = min; i < max; i++)            for (i = min; i < max; i++)
# Line 3618  for (;;) Line 3759  for (;;)
3759                break;                break;
3760                }                }
3761              GETCHARLEN(d, eptr, len);              GETCHARLEN(d, eptr, len);
3762              if (d < 256) d = md->lcc[d];              if (fc == d || (unsigned int)foc == d) break;
             if (fc == d) break;  
3763              eptr += len;              eptr += len;
3764              }              }
3765          if (possessive) continue;            if (possessive) continue;
3766          for(;;)            for(;;)
3767              {              {
3768              RMATCH(eptr, ecode, offset_top, md, eptrb, RM30);              RMATCH(eptr, ecode, offset_top, md, eptrb, RM30);
3769              if (rrc != MATCH_NOMATCH) RRETURN(rrc);              if (rrc != MATCH_NOMATCH) RRETURN(rrc);
# Line 3633  for (;;) Line 3773  for (;;)
3773            }            }
3774          else          else
3775  #endif  #endif
3776          /* Not UTF-8 mode */          /* Not UTF mode */
3777            {            {
3778            for (i = min; i < max; i++)            for (i = min; i < max; i++)
3779              {              {
# Line 3642  for (;;) Line 3782  for (;;)
3782                SCHECK_PARTIAL();                SCHECK_PARTIAL();
3783                break;                break;
3784                }                }
3785              if (fc == md->lcc[*eptr]) break;              if (fc == *eptr || foc == *eptr) break;
3786              eptr++;              eptr++;
3787              }              }
3788            if (possessive) continue;            if (possessive) continue;
# Line 3654  for (;;) Line 3794  for (;;)
3794              }              }
3795            }            }
3796    
3797          MRRETURN(MATCH_NOMATCH);          RRETURN(MATCH_NOMATCH);
3798          }          }
3799        /* Control never gets here */        /* Control never gets here */
3800        }        }
# Line 3663  for (;;) Line 3803  for (;;)
3803    
3804      else      else
3805        {        {
3806  #ifdef SUPPORT_UTF8  #ifdef SUPPORT_UTF
3807        /* UTF-8 mode */        if (utf)
       if (utf8)  
3808          {          {
3809          register unsigned int d;          register unsigned int d;
3810          for (i = 1; i <= min; i++)          for (i = 1; i <= min; i++)
# Line 3673  for (;;) Line 3812  for (;;)
3812            if (eptr >= md->end_subject)            if (eptr >= md->end_subject)
3813              {              {
3814              SCHECK_PARTIAL();              SCHECK_PARTIAL();
3815              MRRETURN(MATCH_NOMATCH);              RRETURN(MATCH_NOMATCH);
3816              }              }
3817            GETCHARINC(d, eptr);            GETCHARINC(d, eptr);
3818            if (fc == d) MRRETURN(MATCH_NOMATCH);            if (fc == d) RRETURN(MATCH_NOMATCH);
3819            }            }
3820          }          }
3821        else        else
3822  #endif  #endif
3823        /* Not UTF-8 mode */        /* Not UTF mode */
3824          {          {
3825          for (i = 1; i <= min; i++)          for (i = 1; i <= min; i++)
3826            {            {
3827            if (eptr >= md->end_subject)            if (eptr >= md->end_subject)
3828              {              {
3829              SCHECK_PARTIAL();              SCHECK_PARTIAL();
3830              MRRETURN(MATCH_NOMATCH);              RRETURN(MATCH_NOMATCH);
3831              }              }
3832            if (fc == *eptr++) MRRETURN(MATCH_NOMATCH);            if (fc == *eptr++) RRETURN(MATCH_NOMATCH);
3833            }            }
3834          }          }
3835    
# Line 3698  for (;;) Line 3837  for (;;)
3837    
3838        if (minimize)        if (minimize)
3839          {          {
3840  #ifdef SUPPORT_UTF8  #ifdef SUPPORT_UTF
3841          /* UTF-8 mode */          if (utf)
         if (utf8)  
3842            {            {
3843            register unsigned int d;            register unsigned int d;
3844            for (fi = min;; fi++)            for (fi = min;; fi++)
3845              {              {
3846              RMATCH(eptr, ecode, offset_top, md, eptrb, RM32);              RMATCH(eptr, ecode, offset_top, md, eptrb, RM32);
3847              if (rrc != MATCH_NOMATCH) RRETURN(rrc);              if (rrc != MATCH_NOMATCH) RRETURN(rrc);
3848              if (fi >= max) MRRETURN(MATCH_NOMATCH);              if (fi >= max) RRETURN(MATCH_NOMATCH);
3849              if (eptr >= md->end_subject)              if (eptr >= md->end_subject)
3850                {                {
3851                SCHECK_PARTIAL();                SCHECK_PARTIAL();
3852                MRRETURN(MATCH_NOMATCH);                RRETURN(MATCH_NOMATCH);
3853                }                }
3854              GETCHARINC(d, eptr);              GETCHARINC(d, eptr);
3855              if (fc == d) MRRETURN(MATCH_NOMATCH);              if (fc == d) RRETURN(MATCH_NOMATCH);
3856              }              }
3857            }            }
3858          else          else
3859  #endif  #endif
3860          /* Not UTF-8 mode */          /* Not UTF mode */
3861            {            {
3862            for (fi = min;; fi++)            for (fi = min;; fi++)
3863              {              {
3864              RMATCH(eptr, ecode, offset_top, md, eptrb, RM33);              RMATCH(eptr, ecode, offset_top, md, eptrb, RM33);
3865              if (rrc != MATCH_NOMATCH) RRETURN(rrc);              if (rrc != MATCH_NOMATCH) RRETURN(rrc);
3866              if (fi >= max) MRRETURN(MATCH_NOMATCH);              if (fi >= max) RRETURN(MATCH_NOMATCH);
3867              if (eptr >= md->end_subject)              if (eptr >= md->end_subject)
3868                {                {
3869                SCHECK_PARTIAL();                SCHECK_PARTIAL();
3870                MRRETURN(MATCH_NOMATCH);                RRETURN(MATCH_NOMATCH);
3871                }                }
3872              if (fc == *eptr++) MRRETURN(MATCH_NOMATCH);              if (fc == *eptr++) RRETURN(MATCH_NOMATCH);
3873              }              }
3874            }            }
3875          /* Control never gets here */          /* Control never gets here */
# Line 3743  for (;;) Line 3881  for (;;)
3881          {          {
3882          pp = eptr;          pp = eptr;
3883    
3884  #ifdef SUPPORT_UTF8  #ifdef SUPPORT_UTF
3885          /* UTF-8 mode */          if (utf)
         if (utf8)  
3886            {            {
3887            register unsigned int d;            register unsigned int d;
3888            for (i = min; i < max; i++)            for (i = min; i < max; i++)
# Line 3771  for (;;) Line 3908  for (;;)
3908            }            }
3909          else          else
3910  #endif  #endif
3911          /* Not UTF-8 mode */          /* Not UTF mode */
3912            {            {
3913            for (i = min; i < max; i++)            for (i = min; i < max; i++)
3914              {              {
# Line 3792  for (;;) Line 3929  for (;;)
3929              }              }
3930            }            }
3931    
3932          MRRETURN(MATCH_NOMATCH);          RRETURN(MATCH_NOMATCH);
3933          }          }
3934        }        }
3935      /* Control never gets here */      /* Control never gets here */
# Line 3804  for (;;) Line 3941  for (;;)
3941      case OP_TYPEEXACT:      case OP_TYPEEXACT:
3942      min = max = GET2(ecode, 1);      min = max = GET2(ecode, 1);
3943      minimize = TRUE;      minimize = TRUE;
3944      ecode += 3;      ecode += 1 + IMM2_SIZE;
3945      goto REPEATTYPE;      goto REPEATTYPE;
3946    
3947      case OP_TYPEUPTO:      case OP_TYPEUPTO:
# Line 3812  for (;;) Line 3949  for (;;)
3949      min = 0;      min = 0;
3950      max = GET2(ecode, 1);      max = GET2(ecode, 1);
3951      minimize = *ecode == OP_TYPEMINUPTO;      minimize = *ecode == OP_TYPEMINUPTO;
3952      ecode += 3;      ecode += 1 + IMM2_SIZE;
3953      goto REPEATTYPE;      goto REPEATTYPE;
3954    
3955      case OP_TYPEPOSSTAR:      case OP_TYPEPOSSTAR:
# Line 3840  for (;;) Line 3977  for (;;)
3977      possessive = TRUE;      possessive = TRUE;
3978      min = 0;      min = 0;
3979      max = GET2(ecode, 1);      max = GET2(ecode, 1);
3980      ecode += 3;      ecode += 1 + IMM2_SIZE;
3981      goto REPEATTYPE;      goto REPEATTYPE;
3982    
3983      case OP_TYPESTAR:      case OP_TYPESTAR:
# Line 3886  for (;;) Line 4023  for (;;)
4023          switch(prop_type)          switch(prop_type)
4024            {            {
4025            case PT_ANY:            case PT_ANY:
4026            if (prop_fail_result) MRRETURN(MATCH_NOMATCH);            if (prop_fail_result) RRETURN(MATCH_NOMATCH);
4027            for (i = 1; i <= min; i++)            for (i = 1; i <= min; i++)
4028              {              {
4029              if (eptr >= md->end_subject)              if (eptr >= md->end_subject)
4030                {                {
4031                SCHECK_PARTIAL();                SCHECK_PARTIAL();
4032                MRRETURN(MATCH_NOMATCH);                RRETURN(MATCH_NOMATCH);
4033                }                }
4034              GETCHARINCTEST(c, eptr);              GETCHARINCTEST(c, eptr);
4035              }              }
# Line 3905  for (;;) Line 4042  for (;;)
4042              if (eptr >= md->end_subject)              if (eptr >= md->end_subject)
4043                {                {
4044                SCHECK_PARTIAL();                SCHECK_PARTIAL();
4045                MRRETURN(MATCH_NOMATCH);                RRETURN(MATCH_NOMATCH);
4046                }                }
4047              GETCHARINCTEST(c, eptr);              GETCHARINCTEST(c, eptr);
4048              chartype = UCD_CHARTYPE(c);              chartype = UCD_CHARTYPE(c);
4049              if ((chartype == ucp_Lu ||              if ((chartype == ucp_Lu ||
4050                   chartype == ucp_Ll ||                   chartype == ucp_Ll ||
4051                   chartype == ucp_Lt) == prop_fail_result)                   chartype == ucp_Lt) == prop_fail_result)
4052                MRRETURN(MATCH_NOMATCH);                RRETURN(MATCH_NOMATCH);
4053              }              }
4054            break;            break;
4055    
# Line 3922  for (;;) Line 4059  for (;;)
4059              if (eptr >= md->end_subject)              if (eptr >= md->end_subject)
4060                {                {
4061                SCHECK_PARTIAL();                SCHECK_PARTIAL();
4062                MRRETURN(MATCH_NOMATCH);                RRETURN(MATCH_NOMATCH);
4063                }                }
4064              GETCHARINCTEST(c, eptr);              GETCHARINCTEST(c, eptr);
4065              if ((UCD_CATEGORY(c) == prop_value) == prop_fail_result)              if ((UCD_CATEGORY(c) == prop_value) == prop_fail_result)
4066                MRRETURN(MATCH_NOMATCH);                RRETURN(MATCH_NOMATCH);
4067              }              }
4068            break;            break;
4069    
# Line 3936  for (;;) Line 4073  for (;;)
4073              if (eptr >= md->end_subject)              if (eptr >= md->end_subject)
4074                {                {
4075                SCHECK_PARTIAL();                SCHECK_PARTIAL();
4076                MRRETURN(MATCH_NOMATCH);                RRETURN(MATCH_NOMATCH);
4077                }                }
4078              GETCHARINCTEST(c, eptr);              GETCHARINCTEST(c, eptr);
4079              if ((UCD_CHARTYPE(c) == prop_value) == prop_fail_result)              if ((UCD_CHARTYPE(c) == prop_value) == prop_fail_result)
4080                MRRETURN(MATCH_NOMATCH);                RRETURN(MATCH_NOMATCH);
4081              }              }
4082            break;            break;
4083    
# Line 3950  for (;;) Line 4087  for (;;)
4087              if (eptr >= md->end_subject)              if (eptr >= md->end_subject)
4088                {                {
4089                SCHECK_PARTIAL();                SCHECK_PARTIAL();
4090                MRRETURN(MATCH_NOMATCH);                RRETURN(MATCH_NOMATCH);
4091                }                }
4092              GETCHARINCTEST(c, eptr);              GETCHARINCTEST(c, eptr);
4093              if ((UCD_SCRIPT(c) == prop_value) == prop_fail_result)              if ((UCD_SCRIPT(c) == prop_value) == prop_fail_result)
4094                MRRETURN(MATCH_NOMATCH);                RRETURN(MATCH_NOMATCH);
4095              }              }
4096            break;            break;
4097    
# Line 3965  for (;;) Line 4102  for (;;)
4102              if (eptr >= md->end_subject)              if (eptr >= md->end_subject)
4103                {                {
4104                SCHECK_PARTIAL();                SCHECK_PARTIAL();
4105                MRRETURN(MATCH_NOMATCH);                RRETURN(MATCH_NOMATCH);
4106                }                }
4107              GETCHARINCTEST(c, eptr);              GETCHARINCTEST(c, eptr);
4108              category = UCD_CATEGORY(c);              category = UCD_CATEGORY(c);
4109              if ((category == ucp_L || category == ucp_N) == prop_fail_result)              if ((category == ucp_L || category == ucp_N) == prop_fail_result)
4110                MRRETURN(MATCH_NOMATCH);                RRETURN(MATCH_NOMATCH);
4111              }              }
4112            break;            break;
4113    
# Line 3980  for (;;) Line 4117  for (;;)
4117              if (eptr >= md->end_subject)              if (eptr >= md->end_subject)
4118                {                {
4119                SCHECK_PARTIAL();                SCHECK_PARTIAL();
4120                MRRETURN(MATCH_NOMATCH);                RRETURN(MATCH_NOMATCH);
4121                }                }
4122              GETCHARINCTEST(c, eptr);              GETCHARINCTEST(c, eptr);
4123              if ((UCD_CATEGORY(c) == ucp_Z || c == CHAR_HT || c == CHAR_NL ||              if ((UCD_CATEGORY(c) == ucp_Z || c == CHAR_HT || c == CHAR_NL ||
4124                   c == CHAR_FF || c == CHAR_CR)                   c == CHAR_FF || c == CHAR_CR)
4125                     == prop_fail_result)                     == prop_fail_result)
4126                MRRETURN(MATCH_NOMATCH);                RRETURN(MATCH_NOMATCH);
4127              }              }
4128            break;            break;
4129    
# Line 3996  for (;;) Line 4133  for (;;)
4133              if (eptr >= md->end_subject)              if (eptr >= md->end_subject)
4134                {                {
4135                SCHECK_PARTIAL();                SCHECK_PARTIAL();
4136                MRRETURN(MATCH_NOMATCH);                RRETURN(MATCH_NOMATCH);
4137                }                }
4138              GETCHARINCTEST(c, eptr);              GETCHARINCTEST(c, eptr);
4139              if ((UCD_CATEGORY(c) == ucp_Z || c == CHAR_HT || c == CHAR_NL ||              if ((UCD_CATEGORY(c) == ucp_Z || c == CHAR_HT || c == CHAR_NL ||
4140                   c == CHAR_VT || c == CHAR_FF || c == CHAR_CR)                   c == CHAR_VT || c == CHAR_FF || c == CHAR_CR)
4141                     == prop_fail_result)                     == prop_fail_result)
4142                MRRETURN(MATCH_NOMATCH);                RRETURN(MATCH_NOMATCH);
4143              }              }
4144            break;            break;
4145    
# Line 4013  for (;;) Line 4150  for (;;)
4150              if (eptr >= md->end_subject)              if (eptr >= md->end_subject)
4151                {                {
4152                SCHECK_PARTIAL();                SCHECK_PARTIAL();
4153                MRRETURN(MATCH_NOMATCH);                RRETURN(MATCH_NOMATCH);
4154                }                }
4155              GETCHARINCTEST(c, eptr);              GETCHARINCTEST(c, eptr);
4156              category = UCD_CATEGORY(c);              category = UCD_CATEGORY(c);
4157              if ((category == ucp_L || category == ucp_N || c == CHAR_UNDERSCORE)              if ((category == ucp_L || category == ucp_N || c == CHAR_UNDERSCORE)
4158                     == prop_fail_result)                     == prop_fail_result)
4159                MRRETURN(MATCH_NOMATCH);                RRETURN(MATCH_NOMATCH);
4160              }              }
4161            break;            break;
4162    
# Line 4040  for (;;) Line 4177  for (;;)
4177            if (eptr >= md->end_subject)            if (eptr >= md->end_subject)
4178              {              {
4179              SCHECK_PARTIAL();              SCHECK_PARTIAL();
4180              MRRETURN(MATCH_NOMATCH);              RRETURN(MATCH_NOMATCH);
4181              }              }
4182            GETCHARINCTEST(c, eptr);            GETCHARINCTEST(c, eptr);
4183            if (UCD_CATEGORY(c) == ucp_M) MRRETURN(MATCH_NOMATCH);            if (UCD_CATEGORY(c) == ucp_M) RRETURN(MATCH_NOMATCH);
4184            while (eptr < md->end_subject)            while (eptr < md->end_subject)
4185              {              {
4186              int len = 1;              int len = 1;
4187              if (!utf8) c = *eptr; else { GETCHARLEN(c, eptr, len); }              if (!utf) c = *eptr; else { GETCHARLEN(c, eptr, len); }
4188              if (UCD_CATEGORY(c) != ucp_M) break;              if (UCD_CATEGORY(c) != ucp_M) break;
4189              eptr += len;              eptr += len;
4190              }              }
4191            }            }
4192            if (md->partial != 0 && eptr >= md->end_subject)
4193              {
4194              SCHECK_PARTIAL();
4195              }
4196          }          }
4197    
4198        else        else
# Line 4059  for (;;) Line 4200  for (;;)
4200    
4201  /* Handle all other cases when the coding is UTF-8 */  /* Handle all other cases when the coding is UTF-8 */
4202    
4203  #ifdef SUPPORT_UTF8  #ifdef SUPPORT_UTF
4204        if (utf8) switch(ctype)        if (utf) switch(ctype)
4205          {          {
4206          case OP_ANY:          case OP_ANY:
4207          for (i = 1; i <= min; i++)          for (i = 1; i <= min; i++)
# Line 4068  for (;;) Line 4209  for (;;)
4209            if (eptr >= md->end_subject)            if (eptr >= md->end_subject)
4210              {              {
4211              SCHECK_PARTIAL();              SCHECK_PARTIAL();
4212              MRRETURN(MATCH_NOMATCH);              RRETURN(MATCH_NOMATCH);
4213              }              }
4214            if (IS_NEWLINE(eptr)) MRRETURN(MATCH_NOMATCH);            if (IS_NEWLINE(eptr)) RRETURN(MATCH_NOMATCH);
4215            eptr++;            eptr++;
4216            while (eptr < md->end_subject && (*eptr & 0xc0) == 0x80) eptr++;            ACROSSCHAR(eptr < md->end_subject, *eptr, eptr++);
4217            }            }
4218          break;          break;
4219    
# Line 4082  for (;;) Line 4223  for (;;)
4223            if (eptr >= md->end_subject)            if (eptr >= md->end_subject)
4224              {              {
4225              SCHECK_PARTIAL();              SCHECK_PARTIAL();
4226              MRRETURN(MATCH_NOMATCH);              RRETURN(MATCH_NOMATCH);
4227              }              }
4228            eptr++;            eptr++;
4229            while (eptr < md->end_subject && (*eptr & 0xc0) == 0x80) eptr++;            ACROSSCHAR(eptr < md->end_subject, *eptr, eptr++);
4230            }            }
4231          break;          break;
4232    
4233          case OP_ANYBYTE:          case OP_ANYBYTE:
4234          if (eptr > md->end_subject - min) MRRETURN(MATCH_NOMATCH);          if (eptr > md->end_subject - min) RRETURN(MATCH_NOMATCH);
4235          eptr += min;          eptr += min;
4236          break;          break;
4237    
# Line 4100  for (;;) Line 4241  for (;;)
4241            if (eptr >= md->end_subject)            if (eptr >= md->end_subject)
4242              {              {
4243              SCHECK_PARTIAL();              SCHECK_PARTIAL();
4244              MRRETURN(MATCH_NOMATCH);              RRETURN(MATCH_NOMATCH);
4245              }              }
4246            GETCHARINC(c, eptr);            GETCHARINC(c, eptr);
4247            switch(c)            switch(c)
4248              {              {
4249              default: MRRETURN(MATCH_NOMATCH);              default: RRETURN(MATCH_NOMATCH);
4250    
4251              case 0x000d:              case 0x000d:
4252              if (eptr < md->end_subject && *eptr == 0x0a) eptr++;              if (eptr < md->end_subject && *eptr == 0x0a) eptr++;
# Line 4119  for (;;) Line 4260  for (;;)
4260              case 0x0085:              case 0x0085:
4261              case 0x2028:              case 0x2028:
4262              case 0x2029:              case 0x2029:
4263              if (md->bsr_anycrlf) MRRETURN(MATCH_NOMATCH);              if (md->bsr_anycrlf) RRETURN(MATCH_NOMATCH);
4264              break;              break;
4265              }              }
4266            }            }
# Line 4131  for (;;) Line 4272  for (;;)
4272            if (eptr >= md->end_subject)            if (eptr >= md->end_subject)
4273              {              {
4274              SCHECK_PARTIAL();              SCHECK_PARTIAL();
4275              MRRETURN(MATCH_NOMATCH);              RRETURN(MATCH_NOMATCH);
4276              }              }
4277            GETCHARINC(c, eptr);            GETCHARINC(c, eptr);
4278            switch(c)            switch(c)
# Line 4156  for (;;) Line 4297  for (;;)
4297              case 0x202f:    /* NARROW NO-BREAK SPACE */              case 0x202f:    /* NARROW NO-BREAK SPACE */
4298              case 0x205f:    /* MEDIUM MATHEMATICAL SPACE */              case 0x205f:    /* MEDIUM MATHEMATICAL SPACE */
4299              case 0x3000:    /* IDEOGRAPHIC SPACE */              case 0x3000:    /* IDEOGRAPHIC SPACE */
4300              MRRETURN(MATCH_NOMATCH);              RRETURN(MATCH_NOMATCH);
4301              }              }
4302            }            }
4303          break;          break;
# Line 4167  for (;;) Line 4308  for (;;)
4308            if (eptr >= md->end_subject)            if (eptr >= md->end_subject)
4309              {              {
4310              SCHECK_PARTIAL();              SCHECK_PARTIAL();
4311              MRRETURN(MATCH_NOMATCH);              RRETURN(MATCH_NOMATCH);
4312              }              }
4313            GETCHARINC(c, eptr);            GETCHARINC(c, eptr);
4314            switch(c)            switch(c)
4315              {              {
4316              default: MRRETURN(MATCH_NOMATCH);              default: RRETURN(MATCH_NOMATCH);
4317              case 0x09:      /* HT */              case 0x09:      /* HT */
4318              case 0x20:      /* SPACE */              case 0x20:      /* SPACE */
4319              case 0xa0:      /* NBSP */              case 0xa0:      /* NBSP */
# Line 4203  for (;;) Line 4344  for (;;)
4344            if (eptr >= md->end_subject)            if (eptr >= md->end_subject)
4345              {              {
4346              SCHECK_PARTIAL();              SCHECK_PARTIAL();
4347              MRRETURN(MATCH_NOMATCH);              RRETURN(MATCH_NOMATCH);
4348              }              }
4349            GETCHARINC(c, eptr);            GETCHARINC(c, eptr);
4350            switch(c)            switch(c)
# Line 4216  for (;;) Line 4357  for (;;)
4357              case 0x85:      /* NEL */              case 0x85:      /* NEL */
4358              case 0x2028:    /* LINE SEPARATOR */              case 0x2028:    /* LINE SEPARATOR */
4359              case 0x2029:    /* PARAGRAPH SEPARATOR */              case 0x2029:    /* PARAGRAPH SEPARATOR */
4360              MRRETURN(MATCH_NOMATCH);              RRETURN(MATCH_NOMATCH);
4361              }              }
4362            }            }
4363          break;          break;
# Line 4227  for (;;) Line 4368  for (;;)
4368            if (eptr >= md->end_subject)            if (eptr >= md->end_subject)
4369              {              {
4370              SCHECK_PARTIAL();              SCHECK_PARTIAL();
4371              MRRETURN(MATCH_NOMATCH);              RRETURN(MATCH_NOMATCH);
4372              }              }
4373            GETCHARINC(c, eptr);            GETCHARINC(c, eptr);
4374            switch(c)            switch(c)
4375              {              {
4376              default: MRRETURN(MATCH_NOMATCH);              default: RRETURN(MATCH_NOMATCH);
4377              case 0x0a:      /* LF */              case 0x0a:      /* LF */
4378              case 0x0b:      /* VT */              case 0x0b:      /* VT */
4379              case 0x0c:      /* FF */              case 0x0c:      /* FF */
# Line 4251  for (;;) Line 4392  for (;;)
4392            if (eptr >= md->end_subject)            if (eptr >= md->end_subject)
4393              {              {
4394              SCHECK_PARTIAL();              SCHECK_PARTIAL();
4395              MRRETURN(MATCH_NOMATCH);              RRETURN(MATCH_NOMATCH);
4396              }              }
4397            GETCHARINC(c, eptr);            GETCHARINC(c, eptr);
4398            if (c < 128 && (md->ctypes[c] & ctype_digit) != 0)            if (c < 128 && (md->ctypes[c] & ctype_digit) != 0)
4399              MRRETURN(MATCH_NOMATCH);              RRETURN(MATCH_NOMATCH);
4400            }            }
4401          break;          break;
4402    
# Line 4265  for (;;) Line 4406  for (;;)
4406            if (eptr >= md->end_subject)            if (eptr >= md->end_subject)
4407              {              {
4408              SCHECK_PARTIAL();              SCHECK_PARTIAL();
4409              MRRETURN(MATCH_NOMATCH);              RRETURN(MATCH_NOMATCH);
4410              }              }
4411            if (*eptr >= 128 || (md->ctypes[*eptr++] & ctype_digit) == 0)            if (*eptr >= 128 || (md->ctypes[*eptr] & ctype_digit) == 0)
4412              MRRETURN(MATCH_NOMATCH);              RRETURN(MATCH_NOMATCH);
4413              eptr++;
4414            /* No need to skip more bytes - we know it's a 1-byte character */            /* No need to skip more bytes - we know it's a 1-byte character */
4415            }            }
4416          break;          break;
# Line 4279  for (;;) Line 4421  for (;;)
4421            if (eptr >= md->end_subject)            if (eptr >= md->end_subject)
4422              {              {
4423              SCHECK_PARTIAL();              SCHECK_PARTIAL();
4424              MRRETURN(MATCH_NOMATCH);              RRETURN(MATCH_NOMATCH);
4425              }              }
4426            if (*eptr < 128 && (md->ctypes[*eptr] & ctype_space) != 0)            if (*eptr < 128 && (md->ctypes[*eptr] & ctype_space) != 0)
4427              MRRETURN(MATCH_NOMATCH);              RRETURN(MATCH_NOMATCH);
4428            while (++eptr < md->end_subject && (*eptr & 0xc0) == 0x80);            eptr++;
4429              ACROSSCHAR(eptr < md->end_subject, *eptr, eptr++);
4430            }            }
4431          break;          break;
4432    
# Line 4293  for (;;) Line 4436  for (;;)
4436            if (eptr >= md->end_subject)            if (eptr >= md->end_subject)
4437              {              {
4438              SCHECK_PARTIAL();              SCHECK_PARTIAL();
4439              MRRETURN(MATCH_NOMATCH);              RRETURN(MATCH_NOMATCH);
4440              }              }
4441            if (*eptr >= 128 || (md->ctypes[*eptr++] & ctype_space) == 0)            if (*eptr >= 128 || (md->ctypes[*eptr] & ctype_space) == 0)
4442              MRRETURN(MATCH_NOMATCH);              RRETURN(MATCH_NOMATCH);
4443              eptr++;
4444            /* No need to skip more bytes - we know it's a 1-byte character */            /* No need to skip more bytes - we know it's a 1-byte character */
4445            }            }
4446          break;          break;
# Line 4307  for (;;) Line 4451  for (;;)
4451            if (eptr >= md->end_subject)            if (eptr >= md->end_subject)
4452              {              {
4453              SCHECK_PARTIAL();              SCHECK_PARTIAL();
4454              MRRETURN(MATCH_NOMATCH);              RRETURN(MATCH_NOMATCH);
4455              }              }
4456            if (*eptr < 128 && (md->ctypes[*eptr] & ctype_word) != 0)            if (*eptr < 128 && (md->ctypes[*eptr] & ctype_word) != 0)
4457              MRRETURN(MATCH_NOMATCH);              RRETURN(MATCH_NOMATCH);
4458            while (++eptr < md->end_subject && (*eptr & 0xc0) == 0x80);            eptr++;
4459              ACROSSCHAR(eptr < md->end_subject, *eptr, eptr++);
4460            }            }
4461          break;          break;
4462    
# Line 4321  for (;;) Line 4466  for (;;)
4466            if (eptr >= md->end_subject)            if (eptr >= md->end_subject)
4467              {              {
4468              SCHECK_PARTIAL();              SCHECK_PARTIAL();
4469              MRRETURN(MATCH_NOMATCH);              RRETURN(MATCH_NOMATCH);
4470              }              }
4471            if (*eptr >= 128 || (md->ctypes[*eptr++] & ctype_word) == 0)            if (*eptr >= 128 || (md->ctypes[*eptr] & ctype_word) == 0)
4472              MRRETURN(MATCH_NOMATCH);              RRETURN(MATCH_NOMATCH);
4473              eptr++;
4474            /* No need to skip more bytes - we know it's a 1-byte character */            /* No need to skip more bytes - we know it's a 1-byte character */
4475            }            }
4476          break;          break;
# Line 4334  for (;;) Line 4480  for (;;)
4480          }  /* End switch(ctype) */          }  /* End switch(ctype) */
4481    
4482        else        else
4483  #endif     /* SUPPORT_UTF8 */  #endif     /* SUPPORT_UTF */
4484    
4485        /* Code for the non-UTF-8 case for minimum matching of operators other        /* Code for the non-UTF-8 case for minimum matching of operators other
4486        than OP_PROP and OP_NOTPROP. */        than OP_PROP and OP_NOTPROP. */
# Line 4347  for (;;) Line 4493  for (;;)
4493            if (eptr >= md->end_subject)            if (eptr >= md->end_subject)
4494              {              {
4495              SCHECK_PARTIAL();              SCHECK_PARTIAL();
4496              MRRETURN(MATCH_NOMATCH);              RRETURN(MATCH_NOMATCH);
4497              }              }
4498            if (IS_NEWLINE(eptr)) MRRETURN(MATCH_NOMATCH);            if (IS_NEWLINE(eptr)) RRETURN(MATCH_NOMATCH);
4499            eptr++;            eptr++;
4500            }            }
4501          break;          break;
# Line 4358  for (;;) Line 4504  for (;;)
4504          if (eptr > md->end_subject - min)          if (eptr > md->end_subject - min)
4505            {            {
4506            SCHECK_PARTIAL();            SCHECK_PARTIAL();
4507            MRRETURN(MATCH_NOMATCH);            RRETURN(MATCH_NOMATCH);
4508            }            }
4509          eptr += min;          eptr += min;
4510          break;          break;
# Line 4367  for (;;) Line 4513  for (;;)
4513          if (eptr > md->end_subject - min)          if (eptr > md->end_subject - min)
4514            {            {
4515            SCHECK_PARTIAL();            SCHECK_PARTIAL();
4516            MRRETURN(MATCH_NOMATCH);            RRETURN(MATCH_NOMATCH);
4517            }            }
4518          eptr += min;          eptr += min;
4519          break;          break;
# Line 4378  for (;;) Line 4524  for (;;)
4524            if (eptr >= md->end_subject)            if (eptr >= md->end_subject)
4525              {              {
4526              SCHECK_PARTIAL();              SCHECK_PARTIAL();
4527              MRRETURN(MATCH_NOMATCH);              RRETURN(MATCH_NOMATCH);
4528              }              }
4529            switch(*eptr++)            switch(*eptr++)
4530              {              {
4531              default: MRRETURN(MATCH_NOMATCH);              default: RRETURN(MATCH_NOMATCH);
4532    
4533              case 0x000d:              case 0x000d:
4534              if (eptr < md->end_subject && *eptr == 0x0a) eptr++;              if (eptr < md->end_subject && *eptr == 0x0a) eptr++;
# Line 4394  for (;;) Line 4540  for (;;)
4540              case 0x000b:              case 0x000b:
4541              case 0x000c:              case 0x000c:
4542              case 0x0085:              case 0x0085:
4543              if (md->bsr_anycrlf) MRRETURN(MATCH_NOMATCH);  #ifdef COMPILE_PCRE16
4544                case 0x2028:
4545                case 0x2029:
4546    #endif
4547                if (md->bsr_anycrlf) RRETURN(MATCH_NOMATCH);
4548              break;              break;
4549              }              }
4550            }            }
# Line 4406  for (;;) Line 4556  for (;;)
4556            if (eptr >= md->end_subject)            if (eptr >= md->end_subject)
4557              {              {
4558              SCHECK_PARTIAL();              SCHECK_PARTIAL();
4559              MRRETURN(MATCH_NOMATCH);              RRETURN(MATCH_NOMATCH);
4560              }              }
4561            switch(*eptr++)            switch(*eptr++)
4562              {              {
# Line 4414  for (;;) Line 4564  for (;;)
4564              case 0x09:      /* HT */              case 0x09:      /* HT */
4565              case 0x20:      /* SPACE */              case 0x20:      /* SPACE */
4566              case 0xa0:      /* NBSP */              case 0xa0:      /* NBSP */
4567              MRRETURN(MATCH_NOMATCH);  #ifdef COMPILE_PCRE16
4568                case 0x1680:    /* OGHAM SPACE MARK */
4569                case 0x180e:    /* MONGOLIAN VOWEL SEPARATOR */
4570                case 0x2000:    /* EN QUAD */
4571                case 0x2001:    /* EM QUAD */
4572                case 0x2002:    /* EN SPACE */
4573                case 0x2003:    /* EM SPACE */
4574                case 0x2004:    /* THREE-PER-EM SPACE */
4575                case 0x2005:    /* FOUR-PER-EM SPACE */
4576                case 0x2006:    /* SIX-PER-EM SPACE */
4577                case 0x2007:    /* FIGURE SPACE */
4578                case 0x2008:    /* PUNCTUATION SPACE */
4579                case 0x2009:    /* THIN SPACE */
4580                case 0x200A:    /* HAIR SPACE */
4581                case 0x202f:    /* NARROW NO-BREAK SPACE */
4582                case 0x205f:    /* MEDIUM MATHEMATICAL SPACE */
4583                case 0x3000:    /* IDEOGRAPHIC SPACE */
4584    #endif
4585                RRETURN(MATCH_NOMATCH);
4586              }              }
4587            }            }
4588          break;          break;
# Line 4425  for (;;) Line 4593  for (;;)
4593            if (eptr >= md->end_subject)            if (eptr >= md->end_subject)
4594              {              {
4595              SCHECK_PARTIAL();              SCHECK_PARTIAL();
4596              MRRETURN(MATCH_NOMATCH);              RRETURN(MATCH_NOMATCH);
4597              }              }
4598            switch(*eptr++)            switch(*eptr++)
4599              {              {
4600              default: MRRETURN(MATCH_NOMATCH);              default: RRETURN(MATCH_NOMATCH);
4601              case 0x09:      /* HT */              case 0x09:      /* HT */
4602              case 0x20:      /* SPACE */              case 0x20:      /* SPACE */
4603              case 0xa0:      /* NBSP */              case 0xa0:      /* NBSP */
4604    #ifdef COMPILE_PCRE16
4605                case 0x1680:    /* OGHAM SPACE MARK */
4606                case 0x180e:    /* MONGOLIAN VOWEL SEPARATOR */
4607                case 0x2000:    /* EN QUAD */
4608                case 0x2001:    /* EM QUAD */
4609                case 0x2002:    /* EN SPACE */
4610                case 0x2003:    /* EM SPACE */
4611                case 0x2004:    /* THREE-PER-EM SPACE */
4612                case 0x2005:    /* FOUR-PER-EM SPACE */
4613                case 0x2006:    /* SIX-PER-EM SPACE */
4614                case 0x2007:    /* FIGURE SPACE */
4615                case 0x2008:    /* PUNCTUATION SPACE */
4616                case 0x2009:    /* THIN SPACE */
4617                case 0x200A:    /* HAIR SPACE */
4618                case 0x202f:    /* NARROW NO-BREAK SPACE */
4619                case 0x205f:    /* MEDIUM MATHEMATICAL SPACE */
4620                case 0x3000:    /* IDEOGRAPHIC SPACE */
4621    #endif
4622              break;              break;
4623              }              }
4624            }            }
# Line 4444  for (;;) Line 4630  for (;;)
4630            if (eptr >= md->end_subject)            if (eptr >= md->end_subject)
4631              {              {
4632              SCHECK_PARTIAL();              SCHECK_PARTIAL();
4633              MRRETURN(MATCH_NOMATCH);              RRETURN(MATCH_NOMATCH);
4634              }              }
4635            switch(*eptr++)            switch(*eptr++)
4636              {              {
# Line 4454  for (;;) Line 4640  for (;;)
4640              case 0x0c:      /* FF */              case 0x0c:      /* FF */
4641              case 0x0d:      /* CR */              case 0x0d:      /* CR */
4642              case 0x85:      /* NEL */              case 0x85:      /* NEL */
4643              MRRETURN(MATCH_NOMATCH);  #ifdef COMPILE_PCRE16
4644                case 0x2028:    /* LINE SEPARATOR */
4645                case 0x2029:    /* PARAGRAPH SEPARATOR */
4646    #endif
4647                RRETURN(MATCH_NOMATCH);
4648              }              }
4649            }            }
4650          break;          break;
# Line 4465  for (;;) Line 4655  for (;;)
4655            if (eptr >= md->end_subject)            if (eptr >= md->end_subject)
4656              {              {
4657              SCHECK_PARTIAL();              SCHECK_PARTIAL();
4658              MRRETURN(MATCH_NOMATCH);              RRETURN(MATCH_NOMATCH);
4659              }              }
4660            switch(*eptr++)            switch(*eptr++)
4661              {              {
4662              default: MRRETURN(MATCH_NOMATCH);              default: RRETURN(MATCH_NOMATCH);
4663              case 0x0a:      /* LF */              case 0x0a:      /* LF */
4664              case 0x0b:      /* VT */              case 0x0b:      /* VT */
4665              case 0x0c:      /* FF */              case 0x0c:      /* FF */
4666              case 0x0d:      /* CR */              case 0x0d:      /* CR */
4667              case 0x85:      /* NEL */              case 0x85:      /* NEL */
4668    #ifdef COMPILE_PCRE16
4669                case 0x2028:    /* LINE SEPARATOR */
4670                case 0x2029:    /* PARAGRAPH SEPARATOR */
4671    #endif
4672              break;              break;
4673              }              }
4674            }            }
# Line 4486  for (;;) Line 4680  for (;;)
4680            if (eptr >= md->end_subject)            if (eptr >= md->end_subject)
4681              {              {
4682              SCHECK_PARTIAL();              SCHECK_PARTIAL();
4683              MRRETURN(MATCH_NOMATCH);              RRETURN(MATCH_NOMATCH);
4684              }              }
4685            if ((md->ctypes[*eptr++] & ctype_digit) != 0) MRRETURN(MATCH_NOMATCH);            if (MAX_255(*eptr) && (md->ctypes[*eptr] & ctype_digit) != 0)
4686                RRETURN(MATCH_NOMATCH);
4687              eptr++;
4688            }            }
4689          break;          break;
4690    
# Line 4498  for (;;) Line 4694  for (;;)
4694            if (eptr >= md->end_subject)            if (eptr >= md->end_subject)
4695              {              {
4696              SCHECK_PARTIAL();              SCHECK_PARTIAL();
4697              MRRETURN(MATCH_NOMATCH);              RRETURN(MATCH_NOMATCH);
4698              }              }
4699            if ((md->ctypes[*eptr++] & ctype_digit) == 0) MRRETURN(MATCH_NOMATCH);            if (!MAX_255(*eptr) || (md->ctypes[*eptr] & ctype_digit) == 0)
4700                RRETURN(MATCH_NOMATCH);
4701              eptr++;
4702            }            }
4703          break;          break;
4704    
# Line 4510  for (;;) Line 4708  for (;;)
4708            if (eptr >= md->end_subject)            if (eptr >= md->end_subject)
4709              {              {
4710              SCHECK_PARTIAL();              SCHECK_PARTIAL();
4711              MRRETURN(MATCH_NOMATCH);              RRETURN(MATCH_NOMATCH);
4712              }              }
4713            if ((md->ctypes[*eptr++] & ctype_space) != 0) MRRETURN(MATCH_NOMATCH);            if (MAX_255(*eptr) && (md->ctypes[*eptr] & ctype_space) != 0)
4714                RRETURN(MATCH_NOMATCH);
4715              eptr++;
4716            }            }
4717          break;          break;
4718    
# Line 4522  for (;;) Line 4722  for (;;)
4722            if (eptr >= md->end_subject)            if (eptr >= md->end_subject)
4723              {              {
4724              SCHECK_PARTIAL();              SCHECK_PARTIAL();
4725              MRRETURN(MATCH_NOMATCH);              RRETURN(MATCH_NOMATCH);
4726              }              }
4727            if ((md->ctypes[*eptr++] & ctype_space) == 0) MRRETURN(MATCH_NOMATCH);            if (!MAX_255(*eptr) || (md->ctypes[*eptr] & ctype_space) == 0)
4728                RRETURN(MATCH_NOMATCH);
4729              eptr++;
4730            }            }
4731          break;          break;
4732    
# Line 4534  for (;;) Line 4736  for (;;)
4736            if (eptr >= md->end_subject)            if (eptr >= md->end_subject)
4737              {              {
4738              SCHECK_PARTIAL();              SCHECK_PARTIAL();
4739              MRRETURN(MATCH_NOMATCH);              RRETURN(MATCH_NOMATCH);
4740              }              }
4741            if ((md->ctypes[*eptr++] & ctype_word) != 0)            if (MAX_255(*eptr) && (md->ctypes[*eptr] & ctype_word) != 0)
4742              MRRETURN(MATCH_NOMATCH);              RRETURN(MATCH_NOMATCH);
4743              eptr++;
4744            }            }
4745          break;          break;
4746    
# Line 4547  for (;;) Line 4750  for (;;)
4750            if (eptr >= md->end_subject)            if (eptr >= md->end_subject)
4751              {              {
4752              SCHECK_PARTIAL();              SCHECK_PARTIAL();
4753              MRRETURN(MATCH_NOMATCH);              RRETURN(MATCH_NOMATCH);
4754              }              }
4755            if ((md->ctypes[*eptr++] & ctype_word) == 0)            if (!MAX_255(*eptr) || (md->ctypes[*eptr] & ctype_word) == 0)
4756              MRRETURN(MATCH_NOMATCH);              RRETURN(MATCH_NOMATCH);
4757              eptr++;
4758            }            }
4759          break;          break;
4760    
# Line 4579  for (;;) Line 4783  for (;;)
4783              {              {
4784              RMATCH(eptr, ecode, offset_top, md, eptrb, RM36);              RMATCH(eptr, ecode, offset_top, md, eptrb, RM36);
4785              if (rrc != MATCH_NOMATCH) RRETURN(rrc);              if (rrc != MATCH_NOMATCH) RRETURN(rrc);
4786              if (fi >= max) MRRETURN(MATCH_NOMATCH);              if (fi >= max) RRETURN(MATCH_NOMATCH);
4787              if (eptr >= md->end_subject)              if (eptr >= md->end_subject)
4788                {                {
4789                SCHECK_PARTIAL();                SCHECK_PARTIAL();
4790                MRRETURN(MATCH_NOMATCH);                RRETURN(MATCH_NOMATCH);
4791                }                }
4792              GETCHARINCTEST(c, eptr);              GETCHARINCTEST(c, eptr);
4793              if (prop_fail_result) MRRETURN(MATCH_NOMATCH);              if (prop_fail_result) RRETURN(MATCH_NOMATCH);
4794              }              }
4795            /* Control never gets here */            /* Control never gets here */
4796    
# Line 4596  for (;;) Line 4800  for (;;)
4800              int chartype;              int chartype;
4801              RMATCH(eptr, ecode, offset_top, md, eptrb, RM37);              RMATCH(eptr, ecode, offset_top, md, eptrb, RM37);
4802              if (rrc != MATCH_NOMATCH) RRETURN(rrc);              if (rrc != MATCH_NOMATCH) RRETURN(rrc);
4803              if (fi >= max) MRRETURN(MATCH_NOMATCH);              if (fi >= max) RRETURN(MATCH_NOMATCH);
4804              if (eptr >= md->end_subject)              if (eptr >= md->end_subject)
4805                {                {
4806                SCHECK_PARTIAL();                SCHECK_PARTIAL();
4807                MRRETURN(MATCH_NOMATCH);                RRETURN(MATCH_NOMATCH);
4808                }                }
4809              GETCHARINCTEST(c, eptr);              GETCHARINCTEST(c, eptr);
4810              chartype = UCD_CHARTYPE(c);              chartype = UCD_CHARTYPE(c);
4811              if ((chartype == ucp_Lu ||              if ((chartype == ucp_Lu ||
4812                   chartype == ucp_Ll ||                   chartype == ucp_Ll ||
4813                   chartype == ucp_Lt) == prop_fail_result)                   chartype == ucp_Lt) == prop_fail_result)
4814                MRRETURN(MATCH_NOMATCH);                RRETURN(MATCH_NOMATCH);
4815              }              }
4816            /* Control never gets here */            /* Control never gets here */
4817    
# Line 4616  for (;;) Line 4820  for (;;)
4820              {              {
4821              RMATCH(eptr, ecode, offset_top, md, eptrb, RM38);              RMATCH(eptr, ecode, offset_top, md, eptrb, RM38);
4822              if (rrc != MATCH_NOMATCH) RRETURN(rrc);              if (rrc != MATCH_NOMATCH) RRETURN(rrc);
4823              if (fi >= max) MRRETURN(MATCH_NOMATCH);              if (fi >= max) RRETURN(MATCH_NOMATCH);
4824              if (eptr >= md->end_subject)              if (eptr >= md->end_subject)
4825                {                {
4826                SCHECK_PARTIAL();                SCHECK_PARTIAL();
4827                MRRETURN(MATCH_NOMATCH);                RRETURN(MATCH_NOMATCH);
4828                }                }
4829              GETCHARINCTEST(c, eptr);              GETCHARINCTEST(c, eptr);
4830              if ((UCD_CATEGORY(c) == prop_value) == prop_fail_result)              if ((UCD_CATEGORY(c) == prop_value) == prop_fail_result)
4831                MRRETURN(MATCH_NOMATCH);                RRETURN(MATCH_NOMATCH);
4832              }              }
4833            /* Control never gets here */            /* Control never gets here */
4834    
# Line 4633  for (;;) Line 4837  for (;;)
4837              {              {
4838              RMATCH(eptr, ecode, offset_top, md, eptrb, RM39);              RMATCH(eptr, ecode, offset_top, md, eptrb, RM39);
4839              if (rrc != MATCH_NOMATCH) RRETURN(rrc);              if (rrc != MATCH_NOMATCH) RRETURN(rrc);
4840              if (fi >= max) MRRETURN(MATCH_NOMATCH);              if (fi >= max) RRETURN(MATCH_NOMATCH);
4841              if (eptr >= md->end_subject)              if (eptr >= md->end_subject)
4842                {                {
4843                SCHECK_PARTIAL();                SCHECK_PARTIAL();
4844                MRRETURN(MATCH_NOMATCH);                RRETURN(MATCH_NOMATCH);
4845                }                }
4846              GETCHARINCTEST(c, eptr);              GETCHARINCTEST(c, eptr);
4847              if ((UCD_CHARTYPE(c) == prop_value) == prop_fail_result)              if ((UCD_CHARTYPE(c) == prop_value) == prop_fail_result)
4848                MRRETURN(MATCH_NOMATCH);                RRETURN(MATCH_NOMATCH);
4849              }              }
4850            /* Control never gets here */            /* Control never gets here */
4851    
# Line 4650  for (;;) Line 4854  for (;;)
4854              {              {
4855              RMATCH(eptr, ecode, offset_top, md, eptrb, RM40);              RMATCH(eptr, ecode, offset_top, md, eptrb, RM40);
4856              if (rrc != MATCH_NOMATCH) RRETURN(rrc);              if (rrc != MATCH_NOMATCH) RRETURN(rrc);
4857              if (fi >= max) MRRETURN(MATCH_NOMATCH);              if (fi >= max) RRETURN(MATCH_NOMATCH);
4858              if (eptr >= md->end_subject)              if (eptr >= md->end_subject)
4859                {                {
4860                SCHECK_PARTIAL();                SCHECK_PARTIAL();
4861                MRRETURN(MATCH_NOMATCH);                RRETURN(MATCH_NOMATCH);
4862                }                }
4863              GETCHARINCTEST(c, eptr);              GETCHARINCTEST(c, eptr);
4864              if ((UCD_SCRIPT(c) == prop_value) == prop_fail_result)              if ((UCD_SCRIPT(c) == prop_value) == prop_fail_result)
4865                MRRETURN(MATCH_NOMATCH);                RRETURN(MATCH_NOMATCH);
4866              }              }
4867            /* Control never gets here */            /* Control never gets here */
4868    
# Line 4668  for (;;) Line 4872  for (;;)
4872              int category;              int category;
4873              RMATCH(eptr, ecode, offset_top, md, eptrb, RM59);              RMATCH(eptr, ecode, offset_top, md, eptrb, RM59);
4874              if (rrc != MATCH_NOMATCH) RRETURN(rrc);              if (rrc != MATCH_NOMATCH) RRETURN(rrc);
4875              if (fi >= max) MRRETURN(MATCH_NOMATCH);              if (fi >= max) RRETURN(MATCH_NOMATCH);
4876              if (eptr >= md->end_subject)              if (eptr >= md->end_subject)
4877                {                {
4878                SCHECK_PARTIAL();                SCHECK_PARTIAL();
4879                MRRETURN(MATCH_NOMATCH);                RRETURN(MATCH_NOMATCH);
4880                }                }
4881              GETCHARINCTEST(c, eptr);              GETCHARINCTEST(c, eptr);
4882              category = UCD_CATEGORY(c);              category = UCD_CATEGORY(c);
4883              if ((category == ucp_L || category == ucp_N) == prop_fail_result)              if ((category == ucp_L || category == ucp_N) == prop_fail_result)
4884                MRRETURN(MATCH_NOMATCH);                RRETURN(MATCH_NOMATCH);
4885              }              }
4886            /* Control never gets here */            /* Control never gets here */
4887    
# Line 4686  for (;;) Line 4890  for (;;)
4890              {              {
4891              RMATCH(eptr, ecode, offset_top, md, eptrb, RM60);              RMATCH(eptr, ecode, offset_top, md, eptrb, RM60);
4892              if (rrc != MATCH_NOMATCH) RRETURN(rrc);              if (rrc != MATCH_NOMATCH) RRETURN(rrc);
4893              if (fi >= max) MRRETURN(MATCH_NOMATCH);              if (fi >= max) RRETURN(MATCH_NOMATCH);
4894              if (eptr >= md->end_subject)              if (eptr >= md->end_subject)
4895                {                {
4896                SCHECK_PARTIAL();                SCHECK_PARTIAL();
4897                MRRETURN(MATCH_NOMATCH);                RRETURN(MATCH_NOMATCH);
4898                }                }
4899              GETCHARINCTEST(c, eptr);              GETCHARINCTEST(c, eptr);
4900              if ((UCD_CATEGORY(c) == ucp_Z || c == CHAR_HT || c == CHAR_NL ||              if ((UCD_CATEGORY(c) == ucp_Z || c == CHAR_HT || c == CHAR_NL ||
4901                   c == CHAR_FF || c == CHAR_CR)                   c == CHAR_FF || c == CHAR_CR)
4902                     == prop_fail_result)                     == prop_fail_result)
4903                MRRETURN(MATCH_NOMATCH);                RRETURN(MATCH_NOMATCH);
4904              }              }
4905            /* Control never gets here */            /* Control never gets here */
4906    
# Line 4705  for (;;) Line 4909  for (;;)
4909              {              {
4910              RMATCH(eptr, ecode, offset_top, md, eptrb, RM61);              RMATCH(eptr, ecode, offset_top, md, eptrb, RM61);
4911              if (rrc != MATCH_NOMATCH) RRETURN(rrc);              if (rrc != MATCH_NOMATCH) RRETURN(rrc);
4912              if (fi >= max) MRRETURN(MATCH_NOMATCH);              if (fi >= max) RRETURN(MATCH_NOMATCH);
4913              if (eptr >= md->end_subject)              if (eptr >= md->end_subject)
4914                {                {
4915                SCHECK_PARTIAL();                SCHECK_PARTIAL();
4916                MRRETURN(MATCH_NOMATCH);                RRETURN(MATCH_NOMATCH);
4917                }                }
4918              GETCHARINCTEST(c, eptr);              GETCHARINCTEST(c, eptr);
4919              if ((UCD_CATEGORY(c) == ucp_Z || c == CHAR_HT || c == CHAR_NL ||              if ((UCD_CATEGORY(c) == ucp_Z || c == CHAR_HT || c == CHAR_NL ||
4920                   c == CHAR_VT || c == CHAR_FF || c == CHAR_CR)                   c == CHAR_VT || c == CHAR_FF || c == CHAR_CR)
4921                     == prop_fail_result)                     == prop_fail_result)
4922                MRRETURN(MATCH_NOMATCH);                RRETURN(MATCH_NOMATCH);
4923              }              }
4924            /* Control never gets here */            /* Control never gets here */
4925    
# Line 4725  for (;;) Line 4929  for (;;)
4929              int category;              int category;
4930              RMATCH(eptr, ecode, offset_top, md, eptrb, RM62);              RMATCH(eptr, ecode, offset_top, md, eptrb, RM62);
4931              if (rrc != MATCH_NOMATCH) RRETURN(rrc);              if (rrc != MATCH_NOMATCH) RRETURN(rrc);
4932              if (fi >= max) MRRETURN(MATCH_NOMATCH);              if (fi >= max) RRETURN(MATCH_NOMATCH);
4933              if (eptr >= md->end_subject)              if (eptr >= md->end_subject)
4934                {                {
4935                SCHECK_PARTIAL();                SCHECK_PARTIAL();
4936                MRRETURN(MATCH_NOMATCH);                RRETURN(MATCH_NOMATCH);
4937                }                }
4938              GETCHARINCTEST(c, eptr);              GETCHARINCTEST(c, eptr);
4939              category = UCD_CATEGORY(c);              category = UCD_CATEGORY(c);
# Line 4737  for (;;) Line 4941  for (;;)
4941                   category == ucp_N ||                   category == ucp_N ||
4942                   c == CHAR_UNDERSCORE)                   c == CHAR_UNDERSCORE)
4943                     == prop_fail_result)                     == prop_fail_result)
4944                MRRETURN(MATCH_NOMATCH);                RRETURN(MATCH_NOMATCH);
4945              }              }
4946            /* Control never gets here */            /* Control never gets here */
4947    
# Line 4757  for (;;) Line 4961  for (;;)
4961            {            {
4962            RMATCH(eptr, ecode, offset_top, md, eptrb, RM41);            RMATCH(eptr, ecode, offset_top, md, eptrb, RM41);
4963            if (rrc != MATCH_NOMATCH) RRETURN(rrc);            if (rrc != MATCH_NOMATCH) RRETURN(rrc);
4964            if (fi >= max) MRRETURN(MATCH_NOMATCH);            if (fi >= max) RRETURN(MATCH_NOMATCH);
4965            if (eptr >= md->end_subject)            if (eptr >= md->end_subject)
4966              {              {
4967              SCHECK_PARTIAL();              SCHECK_PARTIAL();
4968              MRRETURN(MATCH_NOMATCH);              RRETURN(MATCH_NOMATCH);
4969              }              }
4970            GETCHARINCTEST(c, eptr);            GETCHARINCTEST(c, eptr);
4971            if (UCD_CATEGORY(c) == ucp_M) MRRETURN(MATCH_NOMATCH);            if (UCD_CATEGORY(c) == ucp_M) RRETURN(MATCH_NOMATCH);
4972            while (eptr < md->end_subject)            while (eptr < md->end_subject)
4973              {              {
4974              int len = 1;              int len = 1;
4975              if (!utf8) c = *eptr; else { GETCHARLEN(c, eptr, len); }              if (!utf) c = *eptr; else { GETCHARLEN(c, eptr, len); }
4976              if (UCD_CATEGORY(c) != ucp_M) break;              if (UCD_CATEGORY(c) != ucp_M) break;
4977              eptr += len;              eptr += len;
4978              }              }
4979              if (md->partial != 0 && eptr >= md->end_subject)
4980                {
4981                SCHECK_PARTIAL();
4982                }
4983            }            }
4984          }          }
4985        else        else
4986  #endif     /* SUPPORT_UCP */  #endif     /* SUPPORT_UCP */
4987    
4988  #ifdef SUPPORT_UTF8  #ifdef SUPPORT_UTF
4989        /* UTF-8 mode */        if (utf)
       if (utf8)  
4990          {          {
4991          for (fi = min;; fi++)          for (fi = min;; fi++)
4992            {            {
4993            RMATCH(eptr, ecode, offset_top, md, eptrb, RM42);            RMATCH(eptr, ecode, offset_top, md, eptrb, RM42);
4994            if (rrc != MATCH_NOMATCH) RRETURN(rrc);            if (rrc != MATCH_NOMATCH) RRETURN(rrc);
4995            if (fi >= max) MRRETURN(MATCH_NOMATCH);            if (fi >= max) RRETURN(MATCH_NOMATCH);
4996            if (eptr >= md->end_subject)            if (eptr >= md->end_subject)
4997              {              {
4998              SCHECK_PARTIAL();              SCHECK_PARTIAL();
4999              MRRETURN(MATCH_NOMATCH);              RRETURN(MATCH_NOMATCH);
5000              }              }
5001            if (ctype == OP_ANY && IS_NEWLINE(eptr))            if (ctype == OP_ANY && IS_NEWLINE(eptr))
5002              MRRETURN(MATCH_NOMATCH);              RRETURN(MATCH_NOMATCH);
5003            GETCHARINC(c, eptr);            GETCHARINC(c, eptr);
5004            switch(ctype)            switch(ctype)
5005              {              {
# Line 4804  for (;;) Line 5011  for (;;)
5011              case OP_ANYNL:              case OP_ANYNL:
5012              switch(c)              switch(c)
5013                {                {
5014                default: MRRETURN(MATCH_NOMATCH);                default: RRETURN(MATCH_NOMATCH);
5015                case 0x000d:                case 0x000d:
5016                if (eptr < md->end_subject && *eptr == 0x0a) eptr++;                if (eptr < md->end_subject && *eptr == 0x0a) eptr++;
5017                break;                break;
# Line 4816  for (;;) Line 5023  for (;;)
5023                case 0x0085:                case 0x0085:
5024                case 0x2028:                case 0x2028:
5025                case 0x2029:                case 0x2029:
5026                if (md->bsr_anycrlf) MRRETURN(MATCH_NOMATCH);                if (md->bsr_anycrlf) RRETURN(MATCH_NOMATCH);
5027                break;                break;
5028                }                }
5029              break;              break;
# Line 4844  for (;;) Line 5051  for (;;)
5051                case 0x202f:    /* NARROW NO-BREAK SPACE */                case 0x202f:    /* NARROW NO-BREAK SPACE */
5052                case 0x205f:    /* MEDIUM MATHEMATICAL SPACE */                case 0x205f:    /* MEDIUM MATHEMATICAL SPACE */
5053                case 0x3000:    /* IDEOGRAPHIC SPACE */                case 0x3000:    /* IDEOGRAPHIC SPACE */
5054                MRRETURN(MATCH_NOMATCH);                RRETURN(MATCH_NOMATCH);
5055                }                }
5056              break;              break;
5057    
5058              case OP_HSPACE:              case OP_HSPACE:
5059              switch(c)              switch(c)
5060                {                {
5061                default: MRRETURN(MATCH_NOMATCH);                default: RRETURN(MATCH_NOMATCH);
5062                case 0x09:      /* HT */                case 0x09:      /* HT */
5063                case 0x20:      /* SPACE */                case 0x20:      /* SPACE */
5064                case 0xa0:      /* NBSP */                case 0xa0:      /* NBSP */
# Line 4886  for (;;) Line 5093  for (;;)
5093                case 0x85:      /* NEL */                case 0x85:      /* NEL */
5094                case 0x2028:    /* LINE SEPARATOR */                case 0x2028:    /* LINE SEPARATOR */
5095                case 0x2029:    /* PARAGRAPH SEPARATOR */                case 0x2029:    /* PARAGRAPH SEPARATOR */
5096                MRRETURN(MATCH_NOMATCH);                RRETURN(MATCH_NOMATCH);
5097                }                }
5098              break;              break;
5099    
5100              case OP_VSPACE:              case OP_VSPACE:
5101              switch(c)              switch(c)
5102                {                {
5103                default: MRRETURN(MATCH_NOMATCH);                default: RRETURN(MATCH_NOMATCH);
5104                case 0x0a:      /* LF */                case 0x0a:      /* LF */
5105                case 0x0b:      /* VT */                case 0x0b:      /* VT */
5106                case 0x0c:      /* FF */                case 0x0c:      /* FF */
# Line 4907  for (;;) Line 5114  for (;;)
5114    
5115              case OP_NOT_DIGIT:              case OP_NOT_DIGIT:
5116              if (c < 256 && (md->ctypes[c] & ctype_digit) != 0)              if (c < 256 && (md->ctypes[c] & ctype_digit) != 0)
5117                MRRETURN(MATCH_NOMATCH);                RRETURN(MATCH_NOMATCH);
5118              break;              break;
5119    
5120              case OP_DIGIT:              case OP_DIGIT:
5121              if (c >= 256 || (md->ctypes[c] & ctype_digit) == 0)              if (c >= 256 || (md->ctypes[c] & ctype_digit) == 0)
5122                MRRETURN(MATCH_NOMATCH);                RRETURN(MATCH_NOMATCH);
5123              break;              break;
5124    
5125              case OP_NOT_WHITESPACE:              case OP_NOT_WHITESPACE:
5126              if (c < 256 && (md->ctypes[c] & ctype_space) != 0)              if (c < 256 && (md->ctypes[c] & ctype_space) != 0)
5127                MRRETURN(MATCH_NOMATCH);                RRETURN(MATCH_NOMATCH);
5128              break;              break;
5129    
5130              case OP_WHITESPACE:              case OP_WHITESPACE:
5131              if  (c >= 256 || (md->ctypes[c] & ctype_space) == 0)              if (c >= 256 || (md->ctypes[c] & ctype_space) == 0)
5132                MRRETURN(MATCH_NOMATCH);                RRETURN(MATCH_NOMATCH);
5133              break;              break;
5134    
5135              case OP_NOT_WORDCHAR:              case OP_NOT_WORDCHAR:
5136              if (c < 256 && (md->ctypes[c] & ctype_word) != 0)              if (c < 256 && (md->ctypes[c] & ctype_word) != 0)
5137                MRRETURN(MATCH_NOMATCH);                RRETURN(MATCH_NOMATCH);
5138              break;              break;
5139    
5140              case OP_WORDCHAR:              case OP_WORDCHAR:
5141              if (c >= 256 || (md->ctypes[c] & ctype_word) == 0)              if (c >= 256 || (md->ctypes[c] & ctype_word) == 0)
5142                MRRETURN(MATCH_NOMATCH);                RRETURN(MATCH_NOMATCH);
5143              break;              break;
5144    
5145              default:              default:
# Line 4942  for (;;) Line 5149  for (;;)
5149          }          }
5150        else        else
5151  #endif  #endif
5152        /* Not UTF-8 mode */        /* Not UTF mode */
5153          {          {
5154          for (fi = min;; fi++)          for (fi = min;; fi++)
5155            {            {
5156            RMATCH(eptr, ecode, offset_top, md, eptrb, RM43);            RMATCH(eptr, ecode, offset_top, md, eptrb, RM43);
5157            if (rrc != MATCH_NOMATCH) RRETURN(rrc);            if (rrc != MATCH_NOMATCH) RRETURN(rrc);
5158            if (fi >= max) MRRETURN(MATCH_NOMATCH);            if (fi >= max) RRETURN(MATCH_NOMATCH);
5159            if (eptr >= md->end_subject)            if (eptr >= md->end_subject)
5160              {              {
5161              SCHECK_PARTIAL();              SCHECK_PARTIAL();
5162              MRRETURN(MATCH_NOMATCH);              RRETURN(MATCH_NOMATCH);
5163              }              }
5164            if (ctype == OP_ANY && IS_NEWLINE(eptr))            if (ctype == OP_ANY && IS_NEWLINE(eptr))
5165              MRRETURN(MATCH_NOMATCH);              RRETURN(MATCH_NOMATCH);
5166            c = *eptr++;            c = *eptr++;
5167            switch(ctype)            switch(ctype)
5168              {              {
# Line 4967  for (;;) Line 5174  for (;;)
5174              case OP_ANYNL:              case OP_ANYNL:
5175              switch(c)              switch(c)
5176                {                {
5177                default: MRRETURN(MATCH_NOMATCH);                default: RRETURN(MATCH_NOMATCH);
5178                case 0x000d:                case 0x000d:
5179                if (eptr < md->end_subject && *eptr == 0x0a) eptr++;                if (eptr < md->end_subject && *eptr == 0x0a) eptr++;
5180                break;                break;
# Line 4978  for (;;) Line 5185  for (;;)
5185                case 0x000b:                case 0x000b:
5186                case 0x000c:                case 0x000c:
5187                case 0x0085:                case 0x0085:
5188                if (md->bsr_anycrlf) MRRETURN(MATCH_NOMATCH);  #ifdef COMPILE_PCRE16
5189                  case 0x2028:
5190                  case 0x2029:
5191    #endif
5192                  if (md->bsr_anycrlf) RRETURN(MATCH_NOMATCH);
5193                break;                break;
5194                }                }
5195              break;              break;
# Line 4990  for (;;) Line 5201  for (;;)
5201                case 0x09:      /* HT */                case 0x09:      /* HT */
5202                case 0x20:      /* SPACE */                case 0x20:      /* SPACE */
5203                case 0xa0:      /* NBSP */                case 0xa0:      /* NBSP */
5204                MRRETURN(MATCH_NOMATCH);  #ifdef COMPILE_PCRE16
5205                  case 0x1680:    /* OGHAM SPACE MARK */
5206                  case 0x180e:    /* MONGOLIAN VOWEL SEPARATOR */
5207                  case 0x2000:    /* EN QUAD */
5208                  case 0x2001:    /* EM QUAD */
5209                  case 0x2002:    /* EN SPACE */
5210                  case 0x2003:    /* EM SPACE */
5211                  case 0x2004:    /* THREE-PER-EM SPACE */
5212                  case 0x2005:    /* FOUR-PER-EM SPACE */
5213                  case 0x2006:    /* SIX-PER-EM SPACE */
5214                  case 0x2007:    /* FIGURE SPACE */
5215                  case 0x2008:    /* PUNCTUATION SPACE */
5216                  case 0x2009:    /* THIN SPACE */
5217                  case 0x200A:    /* HAIR SPACE */
5218                  case 0x202f:    /* NARROW NO-BREAK SPACE */
5219                  case 0x205f:    /* MEDIUM MATHEMATICAL SPACE */
5220                  case 0x3000:    /* IDEOGRAPHIC SPACE */
5221    #endif
5222                  RRETURN(MATCH_NOMATCH);
5223                }                }
5224              break;              break;
5225    
5226              case OP_HSPACE:              case OP_HSPACE:
5227              switch(c)              switch(c)
5228                {                {
5229                default: MRRETURN(MATCH_NOMATCH);                default: RRETURN(MATCH_NOMATCH);
5230                case 0x09:      /* HT */                case 0x09:      /* HT */
5231                case 0x20:      /* SPACE */                case 0x20:      /* SPACE */
5232                case 0xa0:      /* NBSP */                case 0xa0:      /* NBSP */
5233    #ifdef COMPILE_PCRE16
5234                  case 0x1680:    /* OGHAM SPACE MARK */
5235                  case 0x180e:    /* MONGOLIAN VOWEL SEPARATOR */
5236                  case 0x2000:    /* EN QUAD */
5237                  case 0x2001:    /* EM QUAD */
5238                  case 0x2002:    /* EN SPACE */
5239                  case 0x2003:    /* EM SPACE */
5240                  case 0x2004:    /* THREE-PER-EM SPACE */
5241                  case 0x2005:    /* FOUR-PER-EM SPACE */
5242                  case 0x2006:    /* SIX-PER-EM SPACE */
5243                  case 0x2007:    /* FIGURE SPACE */
5244                  case 0x2008:    /* PUNCTUATION SPACE */
5245                  case 0x2009:    /* THIN SPACE */
5246                  case 0x200A:    /* HAIR SPACE */
5247                  case 0x202f:    /* NARROW NO-BREAK SPACE */
5248                  case 0x205f:    /* MEDIUM MATHEMATICAL SPACE */
5249                  case 0x3000:    /* IDEOGRAPHIC SPACE */
5250    #endif
5251                break;                break;
5252                }                }
5253              break;              break;
# Line 5014  for (;;) Line 5261  for (;;)
5261                case 0x0c:      /* FF */                case 0x0c:      /* FF */
5262                case 0x0d:      /* CR */                case 0x0d:      /* CR */
5263                case 0x85:      /* NEL */                case 0x85:      /* NEL */
5264                MRRETURN(MATCH_NOMATCH);  #ifdef COMPILE_PCRE16
5265                  case 0x2028:    /* LINE SEPARATOR */
5266                  case 0x2029:    /* PARAGRAPH SEPARATOR */
5267    #endif
5268                  RRETURN(MATCH_NOMATCH);
5269                }                }
5270              break;              break;
5271    
5272              case OP_VSPACE:              case OP_VSPACE:
5273              switch(c)              switch(c)
5274                {                {
5275                default: MRRETURN(MATCH_NOMATCH);                default: RRETURN(MATCH_NOMATCH);
5276                case 0x0a:      /* LF */                case 0x0a:      /* LF */
5277                case 0x0b:      /* VT */                case 0x0b:      /* VT */
5278                case 0x0c:      /* FF */                case 0x0c:      /* FF */
5279                case 0x0d:      /* CR */                case 0x0d:      /* CR */
5280                case 0x85:      /* NEL */                case 0x85:      /* NEL */
5281    #ifdef COMPILE_PCRE16
5282                  case 0x2028:    /* LINE SEPARATOR */
5283                  case 0x2029:    /* PARAGRAPH SEPARATOR */
5284    #endif
5285                break;                break;
5286                }                }
5287              break;              break;
5288    
5289              case OP_NOT_DIGIT:              case OP_NOT_DIGIT:
5290              if ((md->ctypes[c] & ctype_digit) != 0) MRRETURN(MATCH_NOMATCH);              if (MAX_255(c) && (md->ctypes[c] & ctype_digit) != 0) RRETURN(MATCH_NOMATCH);
5291              break;              break;
5292    
5293              case OP_DIGIT:              case OP_DIGIT: