]>
git.saurik.com Git - apple/libc.git/blob - regex/FreeBSD/regexec.c
   2  * Copyright (c) 1992, 1993, 1994 Henry Spencer. 
   3  * Copyright (c) 1992, 1993, 1994 
   4  *      The Regents of the University of California.  All rights reserved. 
   6  * This code is derived from software contributed to Berkeley by 
   9  * Redistribution and use in source and binary forms, with or without 
  10  * modification, are permitted provided that the following conditions 
  12  * 1. Redistributions of source code must retain the above copyright 
  13  *    notice, this list of conditions and the following disclaimer. 
  14  * 2. Redistributions in binary form must reproduce the above copyright 
  15  *    notice, this list of conditions and the following disclaimer in the 
  16  *    documentation and/or other materials provided with the distribution. 
  17  * 3. All advertising materials mentioning features or use of this software 
  18  *    must display the following acknowledgement: 
  19  *      This product includes software developed by the University of 
  20  *      California, Berkeley and its contributors. 
  21  * 4. Neither the name of the University nor the names of its contributors 
  22  *    may be used to endorse or promote products derived from this software 
  23  *    without specific prior written permission. 
  25  * THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND 
  26  * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE 
  27  * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE 
  28  * ARE DISCLAIMED.  IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE 
  29  * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL 
  30  * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS 
  31  * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) 
  32  * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT 
  33  * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY 
  34  * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF 
  37  *      @(#)regexec.c   8.3 (Berkeley) 3/20/94 
  40 #if defined(LIBC_SCCS) && !defined(lint) 
  41 static char sccsid
[] = "@(#)regexec.c   8.3 (Berkeley) 3/20/94"; 
  42 #endif /* LIBC_SCCS and not lint */ 
  43 #include <sys/cdefs.h> 
  44 __FBSDID("$FreeBSD: src/lib/libc/regex/regexec.c,v 1.6 2004/07/12 07:35:59 tjr Exp $"); 
  47  * the outer shell of regexec() 
  49  * This file includes engine.c three times, after muchos fiddling with the 
  50  * macros that code uses.  This lets the same code operate on two different 
  51  * representations for state sets and characters. 
  53 #include <sys/types.h> 
  66 static int nope __unused 
= 0;   /* for use in asserts; shuts lint up */ 
  68 static __inline 
size_t 
  69 xmbrtowc(wi
, s
, n
, mbs
, dummy
) 
  79         nr 
= mbrtowc(&wc
, s
, n
, mbs
); 
  84         else if (nr 
== (size_t)-1 || nr 
== (size_t)-2) { 
  85                 memset(mbs
, 0, sizeof(*mbs
)); 
  93 static __inline 
size_t 
  94 xmbrtowc_dummy(wi
, s
, n
, mbs
, dummy
) 
  98 mbstate_t *mbs __unused
; 
  99 wint_t dummy __unused
; 
 103                 *wi 
= (unsigned char)*s
; 
 107 /* macros for manipulating states, small version */ 
 109 #define states1 states          /* for later use in regexec() decision */ 
 110 #define CLEAR(v)        ((v) = 0) 
 111 #define SET0(v, n)      ((v) &= ~((unsigned long)1 << (n))) 
 112 #define SET1(v, n)      ((v) |= (unsigned long)1 << (n)) 
 113 #define ISSET(v, n)     (((v) & ((unsigned long)1 << (n))) != 0) 
 114 #define ASSIGN(d, s)    ((d) = (s)) 
 115 #define EQ(a, b)        ((a) == (b)) 
 116 #define STATEVARS       long dummy      /* dummy version */ 
 117 #define STATESETUP(m, n)        /* nothing */ 
 118 #define STATETEARDOWN(m)        /* nothing */ 
 119 #define SETUP(v)        ((v) = 0) 
 120 #define onestate        long 
 121 #define INIT(o, n)      ((o) = (unsigned long)1 << (n)) 
 122 #define INC(o)  ((o) <<= 1) 
 123 #define ISSTATEIN(v, o) (((v) & (o)) != 0) 
 124 /* some abbreviations; note that some of these know variable names! */ 
 125 /* do "if I'm here, I can also be there" etc without branches */ 
 126 #define FWD(dst, src, n)        ((dst) |= ((unsigned long)(src)&(here)) << (n)) 
 127 #define BACK(dst, src, n)       ((dst) |= ((unsigned long)(src)&(here)) >> (n)) 
 128 #define ISSETBACK(v, n) (((v) & ((unsigned long)here >> (n))) != 0) 
 129 /* no multibyte support */ 
 130 #define XMBRTOWC        xmbrtowc_dummy 
 131 #define ZAPSTATE(mbs)   ((void)(mbs)) 
 133 #define SNAMES                  /* engine.c looks after details */ 
 137 /* now undo things */ 
 160 /* macros for manipulating states, large version */ 
 161 #define states  char * 
 162 #define CLEAR(v)        memset(v, 0, m->g->nstates) 
 163 #define SET0(v, n)      ((v)[n] = 0) 
 164 #define SET1(v, n)      ((v)[n] = 1) 
 165 #define ISSET(v, n)     ((v)[n]) 
 166 #define ASSIGN(d, s)    memcpy(d, s, m->g->nstates) 
 167 #define EQ(a, b)        (memcmp(a, b, m->g->nstates) == 0) 
 168 #define STATEVARS       long vn; char *space 
 169 #define STATESETUP(m, nv)       { (m)->space = malloc((nv)*(m)->g->nstates); \ 
 170                                 if ((m)->space == NULL) return(REG_ESPACE); \ 
 172 #define STATETEARDOWN(m)        { free((m)->space); } 
 173 #define SETUP(v)        ((v) = &m->space[m->vn++ * m->g->nstates]) 
 174 #define onestate        long 
 175 #define INIT(o, n)      ((o) = (n)) 
 176 #define INC(o)  ((o)++) 
 177 #define ISSTATEIN(v, o) ((v)[o]) 
 178 /* some abbreviations; note that some of these know variable names! */ 
 179 /* do "if I'm here, I can also be there" etc without branches */ 
 180 #define FWD(dst, src, n)        ((dst)[here+(n)] |= (src)[here]) 
 181 #define BACK(dst, src, n)       ((dst)[here-(n)] |= (src)[here]) 
 182 #define ISSETBACK(v, n) ((v)[here - (n)]) 
 183 /* no multibyte support */ 
 184 #define XMBRTOWC        xmbrtowc_dummy 
 185 #define ZAPSTATE(mbs)   ((void)(mbs)) 
 187 #define LNAMES                  /* flag */ 
 191 /* multibyte character & large states version */ 
 195 #define XMBRTOWC        xmbrtowc 
 196 #define ZAPSTATE(mbs)   memset((mbs), 0, sizeof(*(mbs))) 
 202  - regexec - interface for matching 
 203  = extern int regexec(const regex_t *, const char *, size_t, \ 
 204  =                                      regmatch_t [], int); 
 205  = #define      REG_NOTBOL      00001 
 206  = #define      REG_NOTEOL      00002 
 207  = #define      REG_STARTEND    00004 
 208  = #define      REG_TRACE       00400   // tracing of execution 
 209  = #define      REG_LARGE       01000   // force large representation 
 210  = #define      REG_BACKR       02000   // force use of backref code 
 212  * We put this here so we can exploit knowledge of the state representation 
 213  * when choosing which matcher to call.  Also, by this point the matchers 
 214  * have been prototyped. 
 216 int                             /* 0 success, REG_NOMATCH failure */ 
 217 regexec(preg
, string
, nmatch
, pmatch
, eflags
) 
 218 const regex_t 
* __restrict preg
; 
 219 const char * __restrict string
; 
 221 regmatch_t pmatch
[__restrict
]; 
 224         struct re_guts 
*g 
= preg
->re_g
; 
 226 #       define  GOODFLAGS(f)    (f) 
 228 #       define  GOODFLAGS(f)    ((f)&(REG_NOTBOL|REG_NOTEOL|REG_STARTEND)) 
 231         if (preg
->re_magic 
!= MAGIC1 
|| g
->magic 
!= MAGIC2
) 
 233         assert(!(g
->iflags
&BAD
)); 
 234         if (g
->iflags
&BAD
)              /* backstop for no-debug case */ 
 236         eflags 
= GOODFLAGS(eflags
); 
 239                 return(mmatcher(g
, (char *)string
, nmatch
, pmatch
, eflags
)); 
 240         else if (g
->nstates 
<= CHAR_BIT
*sizeof(states1
) && !(eflags
®_LARGE
)) 
 241                 return(smatcher(g
, (char *)string
, nmatch
, pmatch
, eflags
)); 
 243                 return(lmatcher(g
, (char *)string
, nmatch
, pmatch
, eflags
));