LCOV - differential code coverage report
Current view: top level - src/backend/regex - regc_lex.c (source / functions) Coverage Total Hit UBC CBC
Current: Differential Code Coverage 16@8cea358b128 vs 17@8cea358b128 Lines: 94.9 % 554 526 28 526
Current Date: 2024-04-14 14:21:10 Functions: 100.0 % 9 9 9
Baseline: 16@8cea358b128 Branches: 79.5 % 477 379 98 379
Baseline Date: 2024-04-14 14:21:09 Line coverage date bins:
Legend: Lines: hit not hit | Branches: + taken - not taken # not executed (240..) days: 94.9 % 554 526 28 526
Function coverage date bins:
(240..) days: 100.0 % 9 9 9
Branch coverage date bins:
(240..) days: 79.5 % 477 379 98 379

 Age         Owner                    Branch data    TLA  Line data    Source code
                                  1                 :                : /*
                                  2                 :                :  * lexical analyzer
                                  3                 :                :  * This file is #included by regcomp.c.
                                  4                 :                :  *
                                  5                 :                :  * Copyright (c) 1998, 1999 Henry Spencer.  All rights reserved.
                                  6                 :                :  *
                                  7                 :                :  * Development of this software was funded, in part, by Cray Research Inc.,
                                  8                 :                :  * UUNET Communications Services Inc., Sun Microsystems Inc., and Scriptics
                                  9                 :                :  * Corporation, none of whom are responsible for the results.  The author
                                 10                 :                :  * thanks all of them.
                                 11                 :                :  *
                                 12                 :                :  * Redistribution and use in source and binary forms -- with or without
                                 13                 :                :  * modification -- are permitted for any purpose, provided that
                                 14                 :                :  * redistributions in source form retain this entire copyright notice and
                                 15                 :                :  * indicate the origin and nature of any modifications.
                                 16                 :                :  *
                                 17                 :                :  * I'd appreciate being given credit for this package in the documentation
                                 18                 :                :  * of software which uses it, but that is not a requirement.
                                 19                 :                :  *
                                 20                 :                :  * THIS SOFTWARE IS PROVIDED ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES,
                                 21                 :                :  * INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY
                                 22                 :                :  * AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.  IN NO EVENT SHALL
                                 23                 :                :  * HENRY SPENCER BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
                                 24                 :                :  * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
                                 25                 :                :  * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS;
                                 26                 :                :  * OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY,
                                 27                 :                :  * WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR
                                 28                 :                :  * OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF
                                 29                 :                :  * ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
                                 30                 :                :  *
                                 31                 :                :  * src/backend/regex/regc_lex.c
                                 32                 :                :  *
                                 33                 :                :  */
                                 34                 :                : 
                                 35                 :                : /* scanning macros (know about v) */
                                 36                 :                : #define ATEOS()     (v->now >= v->stop)
                                 37                 :                : #define HAVE(n)     (v->stop - v->now >= (n))
                                 38                 :                : #define NEXT1(c)    (!ATEOS() && *v->now == CHR(c))
                                 39                 :                : #define NEXT2(a,b)  (HAVE(2) && *v->now == CHR(a) && *(v->now+1) == CHR(b))
                                 40                 :                : #define NEXT3(a,b,c)    (HAVE(3) && *v->now == CHR(a) && \
                                 41                 :                :                         *(v->now+1) == CHR(b) && \
                                 42                 :                :                         *(v->now+2) == CHR(c))
                                 43                 :                : #define SET(c)      (v->nexttype = (c))
                                 44                 :                : #define SETV(c, n)  (v->nexttype = (c), v->nextvalue = (n))
                                 45                 :                : #define RET(c)      return (SET(c), 1)
                                 46                 :                : #define RETV(c, n)  return (SETV(c, n), 1)
                                 47                 :                : #define FAILW(e)    return (ERR(e), 0)  /* ERR does SET(EOS) */
                                 48                 :                : #define LASTTYPE(t) (v->lasttype == (t))
                                 49                 :                : 
                                 50                 :                : /* lexical contexts */
                                 51                 :                : #define L_ERE   1               /* mainline ERE/ARE */
                                 52                 :                : #define L_BRE   2               /* mainline BRE */
                                 53                 :                : #define L_Q 3                   /* REG_QUOTE */
                                 54                 :                : #define L_EBND  4               /* ERE/ARE bound */
                                 55                 :                : #define L_BBND  5               /* BRE bound */
                                 56                 :                : #define L_BRACK 6               /* brackets */
                                 57                 :                : #define L_CEL   7               /* collating element */
                                 58                 :                : #define L_ECL   8               /* equivalence class */
                                 59                 :                : #define L_CCL   9               /* character class */
                                 60                 :                : #define INTOCON(c)  (v->lexcon = (c))
                                 61                 :                : #define INCON(con)  (v->lexcon == (con))
                                 62                 :                : 
                                 63                 :                : /* construct pointer past end of chr array */
                                 64                 :                : #define ENDOF(array)    ((array) + sizeof(array)/sizeof(chr))
                                 65                 :                : 
                                 66                 :                : /*
                                 67                 :                :  * lexstart - set up lexical stuff, scan leading options
                                 68                 :                :  */
                                 69                 :                : static void
 2489 tgl@sss.pgh.pa.us          70                 :CBC        3610 : lexstart(struct vars *v)
                                 71                 :                : {
 7559 bruce@momjian.us           72                 :           3610 :     prefixes(v);                /* may turn on new type bits etc. */
 7739 tgl@sss.pgh.pa.us          73         [ +  + ]:           3610 :     NOERR();
                                 74                 :                : 
 7559 bruce@momjian.us           75         [ +  + ]:           3607 :     if (v->cflags & REG_QUOTE)
                                 76                 :                :     {
                                 77         [ -  + ]:             48 :         assert(!(v->cflags & (REG_ADVANCED | REG_EXPANDED | REG_NEWLINE)));
 7739 tgl@sss.pgh.pa.us          78                 :             48 :         INTOCON(L_Q);
                                 79                 :                :     }
 7559 bruce@momjian.us           80         [ +  + ]:           3559 :     else if (v->cflags & REG_EXTENDED)
                                 81                 :                :     {
                                 82         [ -  + ]:           3431 :         assert(!(v->cflags & REG_QUOTE));
 7739 tgl@sss.pgh.pa.us          83                 :           3431 :         INTOCON(L_ERE);
                                 84                 :                :     }
                                 85                 :                :     else
                                 86                 :                :     {
 7559 bruce@momjian.us           87         [ -  + ]:            128 :         assert(!(v->cflags & (REG_QUOTE | REG_ADVF)));
 7739 tgl@sss.pgh.pa.us          88                 :            128 :         INTOCON(L_BRE);
                                 89                 :                :     }
                                 90                 :                : 
                                 91                 :           3607 :     v->nexttype = EMPTY;     /* remember we were at the start */
 7559 bruce@momjian.us           92                 :           3607 :     next(v);                    /* set up the first token */
                                 93                 :                : }
                                 94                 :                : 
                                 95                 :                : /*
                                 96                 :                :  * prefixes - implement various special prefixes
                                 97                 :                :  */
                                 98                 :                : static void
 2489 tgl@sss.pgh.pa.us          99                 :           3610 : prefixes(struct vars *v)
                                100                 :                : {
                                101                 :                :     /* literal string doesn't get any of this stuff */
 7559 bruce@momjian.us          102         [ +  + ]:           3610 :     if (v->cflags & REG_QUOTE)
 7739 tgl@sss.pgh.pa.us         103                 :             41 :         return;
                                104                 :                : 
                                105                 :                :     /* initial "***" gets special things */
                                106   [ +  +  +  -  :           3569 :     if (HAVE(4) && NEXT3('*', '*', '*'))
                                     +  +  +  -  +  
                                                 - ]
 7559 bruce@momjian.us          107   [ +  +  +  - ]:             10 :         switch (*(v->now + 3))
                                108                 :                :         {
                                109                 :              2 :             case CHR('?'):      /* "***?" error, msg shows version */
                                110         [ -  + ]:              2 :                 ERR(REG_BADPAT);
                                111                 :              2 :                 return;         /* proceed no further */
                                112                 :                :                 break;
                                113                 :              2 :             case CHR('='):      /* "***=" shifts to literal string */
                                114                 :              2 :                 NOTE(REG_UNONPOSIX);
                                115                 :              2 :                 v->cflags |= REG_QUOTE;
                                116                 :              2 :                 v->cflags &= ~(REG_ADVANCED | REG_EXPANDED | REG_NEWLINE);
                                117                 :              2 :                 v->now += 4;
                                118                 :              2 :                 return;         /* and there can be no more prefixes */
                                119                 :                :                 break;
                                120                 :              6 :             case CHR(':'):      /* "***:" shifts to AREs */
                                121                 :              6 :                 NOTE(REG_UNONPOSIX);
                                122                 :              6 :                 v->cflags |= REG_ADVANCED;
                                123                 :              6 :                 v->now += 4;
                                124                 :              6 :                 break;
 7559 bruce@momjian.us          125                 :UBC           0 :             default:            /* otherwise *** is just an error */
                                126         [ #  # ]:              0 :                 ERR(REG_BADRPT);
                                127                 :              0 :                 return;
                                128                 :                :                 break;
                                129                 :                :         }
                                130                 :                : 
                                131                 :                :     /* BREs and EREs don't get embedded options */
 7559 bruce@momjian.us          132         [ +  + ]:CBC        3565 :     if ((v->cflags & REG_ADVANCED) != REG_ADVANCED)
 7739 tgl@sss.pgh.pa.us         133                 :            133 :         return;
                                134                 :                : 
                                135                 :                :     /* embedded options (AREs only) */
 7559 bruce@momjian.us          136   [ +  +  +  -  :           3432 :     if (HAVE(3) && NEXT2('(', '?') && iscalpha(*(v->now + 2)))
                                     +  +  +  +  +  
                                                 + ]
                                137                 :                :     {
 7739 tgl@sss.pgh.pa.us         138                 :             28 :         NOTE(REG_UNONPOSIX);
                                139                 :             28 :         v->now += 2;
                                140   [ +  -  +  + ]:             60 :         for (; !ATEOS() && iscalpha(*v->now); v->now++)
 7559 bruce@momjian.us          141   [ +  +  +  +  :             33 :             switch (*v->now)
                                     +  +  +  +  +  
                                           +  +  + ]
                                142                 :                :             {
                                143                 :              3 :                 case CHR('b'):  /* BREs (but why???) */
                                144                 :              3 :                     v->cflags &= ~(REG_ADVANCED | REG_QUOTE);
                                145                 :              3 :                     break;
                                146                 :              3 :                 case CHR('c'):  /* case sensitive */
                                147                 :              3 :                     v->cflags &= ~REG_ICASE;
                                148                 :              3 :                     break;
                                149                 :              2 :                 case CHR('e'):  /* plain EREs */
                                150                 :              2 :                     v->cflags |= REG_EXTENDED;
                                151                 :              2 :                     v->cflags &= ~(REG_ADVF | REG_QUOTE);
                                152                 :              2 :                     break;
                                153                 :              5 :                 case CHR('i'):  /* case insensitive */
                                154                 :              5 :                     v->cflags |= REG_ICASE;
                                155                 :              5 :                     break;
                                156                 :              5 :                 case CHR('m'):  /* Perloid synonym for n */
                                157                 :                :                 case CHR('n'):  /* \n affects ^ $ . [^ */
                                158                 :              5 :                     v->cflags |= REG_NEWLINE;
                                159                 :              5 :                     break;
                                160                 :              2 :                 case CHR('p'):  /* ~Perl, \n affects . [^ */
                                161                 :              2 :                     v->cflags |= REG_NLSTOP;
                                162                 :              2 :                     v->cflags &= ~REG_NLANCH;
                                163                 :              2 :                     break;
                                164                 :              6 :                 case CHR('q'):  /* literal string */
                                165                 :              6 :                     v->cflags |= REG_QUOTE;
                                166                 :              6 :                     v->cflags &= ~REG_ADVANCED;
                                167                 :              6 :                     break;
                                168                 :              1 :                 case CHR('s'):  /* single line, \n ordinary */
                                169                 :              1 :                     v->cflags &= ~REG_NEWLINE;
                                170                 :              1 :                     break;
                                171                 :              1 :                 case CHR('t'):  /* tight syntax */
                                172                 :              1 :                     v->cflags &= ~REG_EXPANDED;
                                173                 :              1 :                     break;
                                174                 :              2 :                 case CHR('w'):  /* weird, \n affects ^ $ only */
                                175                 :              2 :                     v->cflags &= ~REG_NLSTOP;
                                176                 :              2 :                     v->cflags |= REG_NLANCH;
                                177                 :              2 :                     break;
                                178                 :              2 :                 case CHR('x'):  /* expanded syntax */
                                179                 :              2 :                     v->cflags |= REG_EXPANDED;
                                180                 :              2 :                     break;
                                181                 :              1 :                 default:
                                182         [ -  + ]:              1 :                     ERR(REG_BADOPT);
                                183                 :              1 :                     return;
                                184                 :                :             }
                                185   [ +  -  -  + ]:             27 :         if (!NEXT1(')'))
                                186                 :                :         {
 7739 tgl@sss.pgh.pa.us         187         [ #  # ]:UBC           0 :             ERR(REG_BADOPT);
                                188                 :              0 :             return;
                                189                 :                :         }
 7739 tgl@sss.pgh.pa.us         190                 :CBC          27 :         v->now++;
 7559 bruce@momjian.us          191         [ +  + ]:             27 :         if (v->cflags & REG_QUOTE)
                                192                 :              5 :             v->cflags &= ~(REG_EXPANDED | REG_NEWLINE);
                                193                 :                :     }
                                194                 :                : }
                                195                 :                : 
                                196                 :                : /*
                                197                 :                :  * next - get next token
                                198                 :                :  */
                                199                 :                : static int                      /* 1 normal, 0 failure */
 2489 tgl@sss.pgh.pa.us         200                 :          67865 : next(struct vars *v)
                                201                 :                : {
                                202                 :                :     chr         c;
                                203                 :                : 
  599                           204                 :          67866 : next_restart:                   /* loop here after eating a comment */
                                205                 :                : 
                                206                 :                :     /* errors yield an infinite sequence of failures */
 7739                           207         [ +  + ]:          67866 :     if (ISERR())
 7559 bruce@momjian.us          208                 :             68 :         return 0;               /* the error has set nexttype to EOS */
                                209                 :                : 
                                210                 :                :     /* remember flavor of last token */
 7739 tgl@sss.pgh.pa.us         211                 :          67798 :     v->lasttype = v->nexttype;
                                212                 :                : 
                                213                 :                :     /* REG_BOSONLY */
 7559 bruce@momjian.us          214   [ +  +  +  + ]:          67798 :     if (v->nexttype == EMPTY && (v->cflags & REG_BOSONLY))
                                215                 :                :     {
                                216                 :                :         /* at start of a REG_BOSONLY RE */
 7739 tgl@sss.pgh.pa.us         217                 :              2 :         RETV(SBEGIN, 0);        /* same as \A */
                                218                 :                :     }
                                219                 :                : 
                                220                 :                :     /* skip white space etc. if appropriate (not in literal or []) */
 7559 bruce@momjian.us          221         [ +  + ]:          67796 :     if (v->cflags & REG_EXPANDED)
                                222         [ +  + ]:           1233 :         switch (v->lexcon)
                                223                 :                :         {
                                224                 :            813 :             case L_ERE:
                                225                 :                :             case L_BRE:
                                226                 :                :             case L_EBND:
                                227                 :                :             case L_BBND:
                                228                 :            813 :                 skip(v);
                                229                 :            813 :                 break;
                                230                 :                :         }
                                231                 :                : 
                                232                 :                :     /* handle EOS, depending on context */
                                233         [ +  + ]:          67796 :     if (ATEOS())
                                234                 :                :     {
                                235   [ +  +  +  - ]:           3515 :         switch (v->lexcon)
                                236                 :                :         {
                                237                 :           3499 :             case L_ERE:
                                238                 :                :             case L_BRE:
                                239                 :                :             case L_Q:
                                240                 :           3499 :                 RET(EOS);
                                241                 :                :                 break;
                                242                 :              2 :             case L_EBND:
                                243                 :                :             case L_BBND:
                                244         [ -  + ]:              2 :                 FAILW(REG_EBRACE);
                                245                 :                :                 break;
                                246                 :             14 :             case L_BRACK:
                                247                 :                :             case L_CEL:
                                248                 :                :             case L_ECL:
                                249                 :                :             case L_CCL:
                                250         [ -  + ]:             14 :                 FAILW(REG_EBRACK);
                                251                 :                :                 break;
                                252                 :                :         }
 7739 tgl@sss.pgh.pa.us         253                 :UBC           0 :         assert(NOTREACHED);
                                254                 :                :     }
                                255                 :                : 
                                256                 :                :     /* okay, time to actually get a character */
 7739 tgl@sss.pgh.pa.us         257                 :CBC       64281 :     c = *v->now++;
                                258                 :                : 
                                259                 :                :     /* deal with the easy contexts, punt EREs to code below */
 7559 bruce@momjian.us          260   [ +  +  +  +  :          64281 :     switch (v->lexcon)
                                        +  +  +  +  
                                                 - ]
                                261                 :                :     {
                                262                 :            322 :         case L_BRE:             /* punt BREs to separate function */
                                263                 :            322 :             return brenext(v, c);
                                264                 :                :             break;
                                265                 :          60097 :         case L_ERE:             /* see below */
 7739 tgl@sss.pgh.pa.us         266                 :          60097 :             break;
 7559 bruce@momjian.us          267                 :            247 :         case L_Q:               /* literal strings are easy */
                                268                 :            247 :             RETV(PLAIN, c);
                                269                 :                :             break;
                                270                 :            791 :         case L_BBND:            /* bounds are fairly simple */
                                271                 :                :         case L_EBND:
                                272   [ +  +  +  +  :            791 :             switch (c)
                                                 + ]
                                273                 :                :             {
                                274                 :            414 :                 case CHR('0'):
                                275                 :                :                 case CHR('1'):
                                276                 :                :                 case CHR('2'):
                                277                 :                :                 case CHR('3'):
                                278                 :                :                 case CHR('4'):
                                279                 :                :                 case CHR('5'):
                                280                 :                :                 case CHR('6'):
                                281                 :                :                 case CHR('7'):
                                282                 :                :                 case CHR('8'):
                                283                 :                :                 case CHR('9'):
                                284                 :            414 :                     RETV(DIGIT, (chr) DIGITVAL(c));
                                285                 :                :                     break;
                                286                 :            122 :                 case CHR(','):
                                287                 :            122 :                     RET(',');
                                288                 :                :                     break;
                                289                 :            251 :                 case CHR('}'):  /* ERE bound ends with } */
                                290         [ +  - ]:            251 :                     if (INCON(L_EBND))
                                291                 :                :                     {
                                292                 :            251 :                         INTOCON(L_ERE);
                                293   [ +  -  +  +  :            251 :                         if ((v->cflags & REG_ADVF) && NEXT1('?'))
                                              +  + ]
                                294                 :                :                         {
                                295                 :             45 :                             v->now++;
                                296                 :             45 :                             NOTE(REG_UNONPOSIX);
                                297                 :             45 :                             RETV('}', 0);
                                298                 :                :                         }
                                299                 :            206 :                         RETV('}', 1);
                                300                 :                :                     }
                                301                 :                :                     else
 7559 bruce@momjian.us          302         [ #  # ]:UBC           0 :                         FAILW(REG_BADBR);
                                303                 :                :                     break;
 2489 tgl@sss.pgh.pa.us         304                 :CBC           3 :                 case CHR('\\'): /* BRE bound ends with \} */
 7559 bruce@momjian.us          305   [ +  +  +  -  :              3 :                     if (INCON(L_BBND) && NEXT1('}'))
                                              +  - ]
                                306                 :                :                     {
                                307                 :              2 :                         v->now++;
                                308                 :              2 :                         INTOCON(L_BRE);
 1151 tgl@sss.pgh.pa.us         309                 :              2 :                         RETV('}', 1);
                                310                 :                :                     }
                                311                 :                :                     else
 7559 bruce@momjian.us          312         [ -  + ]:              1 :                         FAILW(REG_BADBR);
                                313                 :                :                     break;
                                314                 :              1 :                 default:
                                315         [ -  + ]:              1 :                     FAILW(REG_BADBR);
                                316                 :                :                     break;
                                317                 :                :             }
                                318                 :                :             assert(NOTREACHED);
                                319                 :                :             break;
                                320   [ +  +  +  +  :           2075 :         case L_BRACK:           /* brackets are not too hard */
                                                 + ]
                                321                 :                :             switch (c)
                                322                 :                :             {
                                323                 :            586 :                 case CHR(']'):
                                324         [ +  + ]:            586 :                     if (LASTTYPE('['))
                                325                 :              2 :                         RETV(PLAIN, c);
                                326                 :                :                     else
                                327                 :                :                     {
                                328         [ +  + ]:            584 :                         INTOCON((v->cflags & REG_EXTENDED) ?
                                329                 :                :                                 L_ERE : L_BRE);
                                330                 :            584 :                         RET(']');
                                331                 :                :                     }
                                332                 :                :                     break;
                                333                 :             64 :                 case CHR('\\'):
                                334                 :             64 :                     NOTE(REG_UBBS);
                                335         [ +  + ]:             64 :                     if (!(v->cflags & REG_ADVF))
                                336                 :              7 :                         RETV(PLAIN, c);
                                337                 :             57 :                     NOTE(REG_UNONPOSIX);
                                338         [ -  + ]:             57 :                     if (ATEOS())
 7559 bruce@momjian.us          339         [ #  # ]:UBC           0 :                         FAILW(REG_EESCAPE);
 1144 tgl@sss.pgh.pa.us         340         [ -  + ]:CBC          57 :                     if (!lexescape(v))
 1144 tgl@sss.pgh.pa.us         341                 :UBC           0 :                         return 0;
 7559 bruce@momjian.us          342         [ +  + ]:CBC          57 :                     switch (v->nexttype)
                                343                 :                :                     {           /* not all escapes okay here */
                                344                 :             56 :                         case PLAIN:
                                345                 :                :                         case CCLASSS:
                                346                 :                :                         case CCLASSC:
                                347                 :             56 :                             return 1;
                                348                 :                :                             break;
                                349                 :                :                     }
                                350                 :                :                     /* not one of the acceptable escapes */
                                351         [ -  + ]:              1 :                     FAILW(REG_EESCAPE);
                                352                 :                :                     break;
                                353                 :            296 :                 case CHR('-'):
                                354   [ +  +  +  +  :            296 :                     if (LASTTYPE('[') || NEXT1(']'))
                                              +  + ]
                                355                 :              8 :                         RETV(PLAIN, c);
                                356                 :                :                     else
                                357                 :            288 :                         RETV(RANGE, c);
                                358                 :                :                     break;
                                359                 :            151 :                 case CHR('['):
                                360         [ -  + ]:            151 :                     if (ATEOS())
 7559 bruce@momjian.us          361         [ #  # ]:UBC           0 :                         FAILW(REG_EBRACK);
 7559 bruce@momjian.us          362   [ +  +  +  + ]:CBC         151 :                     switch (*v->now++)
                                363                 :                :                     {
                                364                 :             12 :                         case CHR('.'):
                                365                 :             12 :                             INTOCON(L_CEL);
                                366                 :                :                             /* might or might not be locale-specific */
                                367                 :             12 :                             RET(COLLEL);
                                368                 :                :                             break;
                                369                 :             16 :                         case CHR('='):
                                370                 :             16 :                             INTOCON(L_ECL);
                                371                 :             16 :                             NOTE(REG_ULOCALE);
                                372                 :             16 :                             RET(ECLASS);
                                373                 :                :                             break;
                                374                 :            121 :                         case CHR(':'):
                                375                 :            121 :                             INTOCON(L_CCL);
                                376                 :            121 :                             NOTE(REG_ULOCALE);
                                377                 :            121 :                             RET(CCLASS);
                                378                 :                :                             break;
 2489 tgl@sss.pgh.pa.us         379                 :              2 :                         default:    /* oops */
 7559 bruce@momjian.us          380                 :              2 :                             v->now--;
                                381                 :              2 :                             RETV(PLAIN, c);
                                382                 :                :                             break;
                                383                 :                :                     }
                                384                 :                :                     assert(NOTREACHED);
                                385                 :                :                     break;
 7739 tgl@sss.pgh.pa.us         386                 :            978 :                 default:
 7559 bruce@momjian.us          387                 :            978 :                     RETV(PLAIN, c);
                                388                 :                :                     break;
                                389                 :                :             }
                                390                 :                :             assert(NOTREACHED);
                                391                 :                :             break;
                                392                 :             32 :         case L_CEL:             /* collating elements are easy */
                                393   [ +  +  +  -  :             32 :             if (c == CHR('.') && NEXT1(']'))
                                              +  - ]
                                394                 :                :             {
                                395                 :             10 :                 v->now++;
                                396                 :             10 :                 INTOCON(L_BRACK);
                                397                 :             10 :                 RETV(END, '.');
                                398                 :                :             }
                                399                 :                :             else
                                400                 :             22 :                 RETV(PLAIN, c);
                                401                 :                :             break;
                                402                 :             24 :         case L_ECL:             /* ditto equivalence classes */
                                403   [ +  +  +  -  :             24 :             if (c == CHR('=') && NEXT1(']'))
                                              +  - ]
                                404                 :                :             {
                                405                 :             12 :                 v->now++;
                                406                 :             12 :                 INTOCON(L_BRACK);
                                407                 :             12 :                 RETV(END, '=');
                                408                 :                :             }
                                409                 :                :             else
 7739 tgl@sss.pgh.pa.us         410                 :             12 :                 RETV(PLAIN, c);
                                411                 :                :             break;
 7559 bruce@momjian.us          412                 :            693 :         case L_CCL:             /* ditto character classes */
                                413   [ +  +  +  -  :            693 :             if (c == CHR(':') && NEXT1(']'))
                                              +  - ]
                                414                 :                :             {
                                415                 :            116 :                 v->now++;
                                416                 :            116 :                 INTOCON(L_BRACK);
                                417                 :            116 :                 RETV(END, ':');
                                418                 :                :             }
                                419                 :                :             else
                                420                 :            577 :                 RETV(PLAIN, c);
                                421                 :                :             break;
 7739 tgl@sss.pgh.pa.us         422                 :UBC           0 :         default:
 7559 bruce@momjian.us          423                 :              0 :             assert(NOTREACHED);
                                424                 :                :             break;
                                425                 :                :     }
                                426                 :                : 
                                427                 :                :     /* that got rid of everything except EREs and AREs */
 7739 tgl@sss.pgh.pa.us         428         [ -  + ]:CBC       60097 :     assert(INCON(L_ERE));
                                429                 :                : 
                                430                 :                :     /* deal with EREs and AREs, except for backslashes */
 7559 bruce@momjian.us          431   [ +  +  +  +  :          60097 :     switch (c)
                                     +  +  +  +  +  
                                        +  +  +  + ]
                                432                 :                :     {
                                433                 :            309 :         case CHR('|'):
                                434                 :            309 :             RET('|');
                                435                 :                :             break;
                                436                 :          10561 :         case CHR('*'):
                                437   [ +  -  +  +  :          10561 :             if ((v->cflags & REG_ADVF) && NEXT1('?'))
                                              +  + ]
                                438                 :                :             {
                                439                 :             27 :                 v->now++;
                                440                 :             27 :                 NOTE(REG_UNONPOSIX);
                                441                 :             27 :                 RETV('*', 0);
                                442                 :                :             }
                                443                 :          10534 :             RETV('*', 1);
                                444                 :                :             break;
                                445                 :            442 :         case CHR('+'):
                                446   [ +  +  +  +  :            442 :             if ((v->cflags & REG_ADVF) && NEXT1('?'))
                                              +  + ]
                                447                 :                :             {
                                448                 :             22 :                 v->now++;
                                449                 :             22 :                 NOTE(REG_UNONPOSIX);
                                450                 :             22 :                 RETV('+', 0);
                                451                 :                :             }
                                452                 :            420 :             RETV('+', 1);
                                453                 :                :             break;
                                454                 :             60 :         case CHR('?'):
                                455   [ +  +  +  +  :             60 :             if ((v->cflags & REG_ADVF) && NEXT1('?'))
                                              +  + ]
                                456                 :                :             {
                                457                 :              2 :                 v->now++;
                                458                 :              2 :                 NOTE(REG_UNONPOSIX);
                                459                 :              2 :                 RETV('?', 0);
                                460                 :                :             }
                                461                 :             58 :             RETV('?', 1);
                                462                 :                :             break;
                                463                 :            259 :         case CHR('{'):          /* bounds start or plain character */
                                464         [ +  + ]:            259 :             if (v->cflags & REG_EXPANDED)
                                465                 :             16 :                 skip(v);
                                466   [ +  +  +  + ]:            259 :             if (ATEOS() || !iscdigit(*v->now))
                                467                 :                :             {
                                468                 :              4 :                 NOTE(REG_UBRACES);
                                469                 :              4 :                 NOTE(REG_UUNSPEC);
                                470                 :              4 :                 RETV(PLAIN, c);
                                471                 :                :             }
                                472                 :                :             else
                                473                 :                :             {
                                474                 :            255 :                 NOTE(REG_UBOUNDS);
                                475                 :            255 :                 INTOCON(L_EBND);
                                476                 :            255 :                 RET('{');
                                477                 :                :             }
                                478                 :                :             assert(NOTREACHED);
                                479                 :                :             break;
                                480                 :           2578 :         case CHR('('):          /* parenthesis, or advanced extension */
                                481   [ +  +  +  -  :           2578 :             if ((v->cflags & REG_ADVF) && NEXT1('?'))
                                              +  + ]
                                482                 :                :             {
                                483                 :            242 :                 NOTE(REG_UNONPOSIX);
                                484                 :            242 :                 v->now++;
 3089 tgl@sss.pgh.pa.us         485         [ -  + ]:            242 :                 if (ATEOS())
 3089 tgl@sss.pgh.pa.us         486         [ #  # ]:UBC           0 :                     FAILW(REG_BADRPT);
 7559 bruce@momjian.us          487   [ +  +  +  +  :CBC         242 :                 switch (*v->now++)
                                              +  + ]
                                488                 :                :                 {
 2489 tgl@sss.pgh.pa.us         489                 :            106 :                     case CHR(':'):  /* non-capturing paren */
 7559 bruce@momjian.us          490                 :            106 :                         RETV('(', 0);
                                491                 :                :                         break;
 2489 tgl@sss.pgh.pa.us         492                 :              1 :                     case CHR('#'):  /* comment */
 7559 bruce@momjian.us          493   [ +  -  +  + ]:              8 :                         while (!ATEOS() && *v->now != CHR(')'))
                                494                 :              7 :                             v->now++;
                                495         [ +  - ]:              1 :                         if (!ATEOS())
                                496                 :              1 :                             v->now++;
                                497         [ -  + ]:              1 :                         assert(v->nexttype == v->lasttype);
  599 tgl@sss.pgh.pa.us         498                 :              1 :                         goto next_restart;
 2489                           499                 :             42 :                     case CHR('='):  /* positive lookahead */
 3089                           500                 :             42 :                         NOTE(REG_ULOOKAROUND);
                                501                 :             42 :                         RETV(LACON, LATYPE_AHEAD_POS);
                                502                 :                :                         break;
 2489                           503                 :             39 :                     case CHR('!'):  /* negative lookahead */
 3089                           504                 :             39 :                         NOTE(REG_ULOOKAROUND);
                                505                 :             39 :                         RETV(LACON, LATYPE_AHEAD_NEG);
                                506                 :                :                         break;
                                507                 :             53 :                     case CHR('<'):
                                508         [ -  + ]:             53 :                         if (ATEOS())
 3089 tgl@sss.pgh.pa.us         509         [ #  # ]:UBC           0 :                             FAILW(REG_BADRPT);
 3089 tgl@sss.pgh.pa.us         510      [ +  +  - ]:CBC          53 :                         switch (*v->now++)
                                511                 :                :                         {
 2489                           512                 :             39 :                             case CHR('='):  /* positive lookbehind */
 3089                           513                 :             39 :                                 NOTE(REG_ULOOKAROUND);
                                514                 :             39 :                                 RETV(LACON, LATYPE_BEHIND_POS);
                                515                 :                :                                 break;
 2489                           516                 :             14 :                             case CHR('!'):  /* negative lookbehind */
 3089                           517                 :             14 :                                 NOTE(REG_ULOOKAROUND);
                                518                 :             14 :                                 RETV(LACON, LATYPE_BEHIND_NEG);
                                519                 :                :                                 break;
 3089 tgl@sss.pgh.pa.us         520                 :UBC           0 :                             default:
                                521         [ #  # ]:              0 :                                 FAILW(REG_BADRPT);
                                522                 :                :                                 break;
                                523                 :                :                         }
                                524                 :                :                         assert(NOTREACHED);
                                525                 :                :                         break;
 7559 bruce@momjian.us          526                 :CBC           1 :                     default:
                                527         [ -  + ]:              1 :                         FAILW(REG_BADRPT);
                                528                 :                :                         break;
                                529                 :                :                 }
                                530                 :                :                 assert(NOTREACHED);
                                531                 :                :             }
  979 tgl@sss.pgh.pa.us         532                 :           2336 :             RETV('(', 1);
                                533                 :                :             break;
 7559 bruce@momjian.us          534                 :           2545 :         case CHR(')'):
                                535         [ +  + ]:           2545 :             if (LASTTYPE('('))
                                536                 :             23 :                 NOTE(REG_UUNSPEC);
                                537                 :           2545 :             RETV(')', c);
                                538                 :                :             break;
                                539                 :            553 :         case CHR('['):          /* easy except for [[:<:]] and [[:>:]] */
                                540   [ +  +  +  + ]:            553 :             if (HAVE(6) && *(v->now + 0) == CHR('[') &&
                                541         [ +  + ]:            132 :                 *(v->now + 1) == CHR(':') &&
                                542         [ +  + ]:            122 :                 (*(v->now + 2) == CHR('<') ||
                                543         [ +  + ]:            117 :                  *(v->now + 2) == CHR('>')) &&
                                544         [ +  - ]:             10 :                 *(v->now + 3) == CHR(':') &&
                                545         [ +  - ]:             10 :                 *(v->now + 4) == CHR(']') &&
                                546         [ +  - ]:             10 :                 *(v->now + 5) == CHR(']'))
                                547                 :                :             {
                                548                 :             10 :                 c = *(v->now + 2);
                                549                 :             10 :                 v->now += 6;
                                550                 :             10 :                 NOTE(REG_UNONPOSIX);
                                551         [ +  + ]:             10 :                 RET((c == CHR('<')) ? '<' : '>');
                                552                 :                :             }
                                553                 :            543 :             INTOCON(L_BRACK);
                                554   [ +  +  +  + ]:            543 :             if (NEXT1('^'))
                                555                 :                :             {
                                556                 :            108 :                 v->now++;
                                557                 :            108 :                 RETV('[', 0);
                                558                 :                :             }
                                559                 :            435 :             RETV('[', 1);
                                560                 :                :             break;
                                561                 :           1521 :         case CHR('.'):
                                562                 :           1521 :             RET('.');
                                563                 :                :             break;
                                564                 :           2270 :         case CHR('^'):
                                565                 :           2270 :             RET('^');
                                566                 :                :             break;
                                567                 :           1995 :         case CHR('$'):
                                568                 :           1995 :             RET('$');
                                569                 :                :             break;
 2489 tgl@sss.pgh.pa.us         570                 :           1056 :         case CHR('\\'):         /* mostly punt backslashes to code below */
 7559 bruce@momjian.us          571         [ +  + ]:           1056 :             if (ATEOS())
                                572         [ -  + ]:              1 :                 FAILW(REG_EESCAPE);
                                573                 :           1055 :             break;
                                574                 :          35948 :         default:                /* ordinary character */
                                575                 :          35948 :             RETV(PLAIN, c);
                                576                 :                :             break;
                                577                 :                :     }
                                578                 :                : 
                                579                 :                :     /* ERE/ARE backslash handling; backslash already eaten */
 7739 tgl@sss.pgh.pa.us         580         [ -  + ]:           1055 :     assert(!ATEOS());
 7559 bruce@momjian.us          581         [ +  + ]:           1055 :     if (!(v->cflags & REG_ADVF))
                                582                 :                :     {                           /* only AREs have non-trivial escapes */
                                583         [ +  + ]:              4 :         if (iscalnum(*v->now))
                                584                 :                :         {
 7739 tgl@sss.pgh.pa.us         585                 :              3 :             NOTE(REG_UBSALNUM);
                                586                 :              3 :             NOTE(REG_UUNSPEC);
                                587                 :                :         }
                                588                 :              4 :         RETV(PLAIN, *v->now++);
                                589                 :                :     }
 1144                           590                 :           1051 :     return lexescape(v);
                                591                 :                : }
                                592                 :                : 
                                593                 :                : /*
                                594                 :                :  * lexescape - parse an ARE backslash escape (backslash already eaten)
                                595                 :                :  *
                                596                 :                :  * This is used for ARE backslashes both normally and inside bracket
                                597                 :                :  * expressions.  In the latter case, not all escape types are allowed,
                                598                 :                :  * but the caller must reject unwanted ones after we return.
                                599                 :                :  */
                                600                 :                : static int
 2489                           601                 :           1108 : lexescape(struct vars *v)
                                602                 :                : {
                                603                 :                :     chr         c;
                                604                 :                :     static const chr alert[] = {
                                605                 :                :         CHR('a'), CHR('l'), CHR('e'), CHR('r'), CHR('t')
                                606                 :                :     };
                                607                 :                :     static const chr esc[] = {
                                608                 :                :         CHR('E'), CHR('S'), CHR('C')
                                609                 :                :     };
                                610                 :                :     const chr  *save;
                                611                 :                : 
 7559 bruce@momjian.us          612         [ -  + ]:           1108 :     assert(v->cflags & REG_ADVF);
                                613                 :                : 
 7739 tgl@sss.pgh.pa.us         614         [ -  + ]:           1108 :     assert(!ATEOS());
                                615                 :           1108 :     c = *v->now++;
                                616                 :                : 
                                617                 :                :     /* if it's not alphanumeric ASCII, treat it as a plain character */
  359 jdavis@postgresql.or      618   [ +  +  +  +  :           1108 :     if (!('a' <= c && c <= 'z') &&
                                              +  + ]
                                619   [ +  +  +  + ]:            843 :         !('A' <= c && c <= 'Z') &&
                                620         [ +  + ]:            302 :         !('0' <= c && c <= '9'))
 7739 tgl@sss.pgh.pa.us         621                 :            620 :         RETV(PLAIN, c);
                                622                 :                : 
                                623                 :            488 :     NOTE(REG_UNONPOSIX);
 7559 bruce@momjian.us          624   [ +  +  +  +  :            488 :     switch (c)
                                     +  +  +  +  +  
                                     +  +  +  +  +  
                                     +  +  +  +  +  
                                     +  +  +  +  +  
                                        +  +  +  + ]
                                625                 :                :     {
                                626                 :              1 :         case CHR('a'):
                                627                 :              1 :             RETV(PLAIN, chrnamed(v, alert, ENDOF(alert), CHR('\007')));
                                628                 :                :             break;
                                629                 :             11 :         case CHR('A'):
                                630                 :             11 :             RETV(SBEGIN, 0);
                                631                 :                :             break;
                                632                 :             13 :         case CHR('b'):
                                633                 :             13 :             RETV(PLAIN, CHR('\b'));
                                634                 :                :             break;
                                635                 :              5 :         case CHR('B'):
                                636                 :              5 :             RETV(PLAIN, CHR('\\'));
                                637                 :                :             break;
                                638                 :              2 :         case CHR('c'):
                                639                 :              2 :             NOTE(REG_UUNPORT);
                                640         [ -  + ]:              2 :             if (ATEOS())
 7559 bruce@momjian.us          641         [ #  # ]:UBC           0 :                 FAILW(REG_EESCAPE);
 7559 bruce@momjian.us          642                 :CBC           2 :             RETV(PLAIN, (chr) (*v->now++ & 037));
                                643                 :                :             break;
                                644                 :             94 :         case CHR('d'):
                                645                 :             94 :             NOTE(REG_ULOCALE);
 1144 tgl@sss.pgh.pa.us         646                 :             94 :             RETV(CCLASSS, CC_DIGIT);
                                647                 :                :             break;
 7559 bruce@momjian.us          648                 :             12 :         case CHR('D'):
                                649                 :             12 :             NOTE(REG_ULOCALE);
 1144 tgl@sss.pgh.pa.us         650                 :             12 :             RETV(CCLASSC, CC_DIGIT);
                                651                 :                :             break;
 7559 bruce@momjian.us          652                 :              1 :         case CHR('e'):
                                653                 :              1 :             NOTE(REG_UUNPORT);
                                654                 :              1 :             RETV(PLAIN, chrnamed(v, esc, ENDOF(esc), CHR('\033')));
                                655                 :                :             break;
                                656                 :              1 :         case CHR('f'):
                                657                 :              1 :             RETV(PLAIN, CHR('\f'));
                                658                 :                :             break;
                                659                 :             17 :         case CHR('m'):
                                660                 :             17 :             RET('<');
                                661                 :                :             break;
                                662                 :             14 :         case CHR('M'):
                                663                 :             14 :             RET('>');
                                664                 :                :             break;
                                665                 :              6 :         case CHR('n'):
                                666                 :              6 :             RETV(PLAIN, CHR('\n'));
                                667                 :                :             break;
                                668                 :              5 :         case CHR('r'):
                                669                 :              5 :             RETV(PLAIN, CHR('\r'));
                                670                 :                :             break;
                                671                 :             28 :         case CHR('s'):
                                672                 :             28 :             NOTE(REG_ULOCALE);
 1144 tgl@sss.pgh.pa.us         673                 :             28 :             RETV(CCLASSS, CC_SPACE);
                                674                 :                :             break;
 7559 bruce@momjian.us          675                 :             17 :         case CHR('S'):
                                676                 :             17 :             NOTE(REG_ULOCALE);
 1144 tgl@sss.pgh.pa.us         677                 :             17 :             RETV(CCLASSC, CC_SPACE);
                                678                 :                :             break;
 7559 bruce@momjian.us          679                 :              2 :         case CHR('t'):
                                680                 :              2 :             RETV(PLAIN, CHR('\t'));
                                681                 :                :             break;
                                682                 :             28 :         case CHR('u'):
                                683                 :             28 :             c = lexdigits(v, 16, 4, 4);
 2981 tgl@sss.pgh.pa.us         684   [ +  +  -  + ]:             28 :             if (ISERR() || !CHR_IS_IN_RANGE(c))
 7559 bruce@momjian.us          685         [ +  - ]:              1 :                 FAILW(REG_EESCAPE);
                                686                 :             27 :             RETV(PLAIN, c);
                                687                 :                :             break;
                                688                 :             10 :         case CHR('U'):
                                689                 :             10 :             c = lexdigits(v, 16, 8, 8);
 2981 tgl@sss.pgh.pa.us         690   [ +  +  -  + ]:             10 :             if (ISERR() || !CHR_IS_IN_RANGE(c))
 7559 bruce@momjian.us          691         [ +  - ]:              5 :                 FAILW(REG_EESCAPE);
                                692                 :              5 :             RETV(PLAIN, c);
                                693                 :                :             break;
                                694                 :              1 :         case CHR('v'):
                                695                 :              1 :             RETV(PLAIN, CHR('\v'));
                                696                 :                :             break;
                                697                 :             50 :         case CHR('w'):
                                698                 :             50 :             NOTE(REG_ULOCALE);
 1144 tgl@sss.pgh.pa.us         699                 :             50 :             RETV(CCLASSS, CC_WORD);
                                700                 :                :             break;
 7559 bruce@momjian.us          701                 :              8 :         case CHR('W'):
                                702                 :              8 :             NOTE(REG_ULOCALE);
 1144 tgl@sss.pgh.pa.us         703                 :              8 :             RETV(CCLASSC, CC_WORD);
                                704                 :                :             break;
 7559 bruce@momjian.us          705                 :              6 :         case CHR('x'):
                                706                 :              6 :             NOTE(REG_UUNPORT);
 2489 tgl@sss.pgh.pa.us         707                 :              6 :             c = lexdigits(v, 16, 1, 255);   /* REs >255 long outside spec */
 2981                           708   [ +  +  +  + ]:              6 :             if (ISERR() || !CHR_IS_IN_RANGE(c))
 7559 bruce@momjian.us          709         [ +  + ]:              4 :                 FAILW(REG_EESCAPE);
                                710                 :              2 :             RETV(PLAIN, c);
                                711                 :                :             break;
                                712                 :              9 :         case CHR('y'):
                                713                 :              9 :             NOTE(REG_ULOCALE);
                                714                 :              9 :             RETV(WBDRY, 0);
                                715                 :                :             break;
                                716                 :             19 :         case CHR('Y'):
                                717                 :             19 :             NOTE(REG_ULOCALE);
                                718                 :             19 :             RETV(NWBDRY, 0);
                                719                 :                :             break;
                                720                 :              6 :         case CHR('Z'):
                                721                 :              6 :             RETV(SEND, 0);
                                722                 :                :             break;
                                723                 :            116 :         case CHR('1'):
                                724                 :                :         case CHR('2'):
                                725                 :                :         case CHR('3'):
                                726                 :                :         case CHR('4'):
                                727                 :                :         case CHR('5'):
                                728                 :                :         case CHR('6'):
                                729                 :                :         case CHR('7'):
                                730                 :                :         case CHR('8'):
                                731                 :                :         case CHR('9'):
                                732                 :            116 :             save = v->now;
                                733                 :            116 :             v->now--;            /* put first digit back */
 2489 tgl@sss.pgh.pa.us         734                 :            116 :             c = lexdigits(v, 10, 1, 255);   /* REs >255 long outside spec */
 7559 bruce@momjian.us          735         [ -  + ]:            116 :             if (ISERR())
 7559 bruce@momjian.us          736         [ #  # ]:UBC           0 :                 FAILW(REG_EESCAPE);
                                737                 :                :             /* ugly heuristic (first test is "exactly 1 digit?") */
 4916 tgl@sss.pgh.pa.us         738   [ +  +  +  +  :CBC         116 :             if (v->now == save || ((int) c > 0 && (int) c <= v->nsubexp))
                                              +  + ]
                                739                 :                :             {
 7559 bruce@momjian.us          740                 :            111 :                 NOTE(REG_UBACKREF);
 2795 tgl@sss.pgh.pa.us         741                 :            111 :                 RETV(BACKREF, c);
                                742                 :                :             }
                                743                 :                :             /* oops, doesn't look like it's a backref after all... */
 7559 bruce@momjian.us          744                 :              5 :             v->now = save;
                                745                 :                :             /* and fall through into octal number */
                                746                 :                :             /* FALLTHROUGH */
                                747                 :             10 :         case CHR('0'):
                                748                 :             10 :             NOTE(REG_UUNPORT);
                                749                 :             10 :             v->now--;            /* put first digit back */
                                750                 :             10 :             c = lexdigits(v, 8, 1, 3);
                                751         [ -  + ]:             10 :             if (ISERR())
 7559 bruce@momjian.us          752         [ #  # ]:UBC           0 :                 FAILW(REG_EESCAPE);
 3133 tgl@sss.pgh.pa.us         753         [ +  + ]:CBC          10 :             if (c > 0xff)
                                754                 :                :             {
                                755                 :                :                 /* out of range, so we handled one digit too much */
                                756                 :              1 :                 v->now--;
                                757                 :              1 :                 c >>= 3;
                                758                 :                :             }
 7559 bruce@momjian.us          759                 :             10 :             RETV(PLAIN, c);
                                760                 :                :             break;
                                761                 :              1 :         default:
                                762                 :                : 
                                763                 :                :             /*
                                764                 :                :              * Throw an error for unrecognized ASCII alpha escape sequences,
                                765                 :                :              * which reserves them for future use if needed.
                                766                 :                :              */
  359 jdavis@postgresql.or      767         [ -  + ]:              1 :             FAILW(REG_EESCAPE);
                                768                 :                :             break;
                                769                 :                :     }
                                770                 :                :     assert(NOTREACHED);
                                771                 :                : }
                                772                 :                : 
                                773                 :                : /*
                                774                 :                :  * lexdigits - slurp up digits and return chr value
                                775                 :                :  *
                                776                 :                :  * This does not account for overflow; callers should range-check the result
                                777                 :                :  * if maxlen is large enough to make that possible.
                                778                 :                :  */
                                779                 :                : static chr                      /* chr value; errors signalled via ERR */
 2489 tgl@sss.pgh.pa.us         780                 :            170 : lexdigits(struct vars *v,
                                781                 :                :           int base,
                                782                 :                :           int minlen,
                                783                 :                :           int maxlen)
                                784                 :                : {
                                785                 :                :     uchr        n;              /* unsigned to avoid overflow misbehavior */
                                786                 :                :     int         len;
                                787                 :                :     chr         c;
                                788                 :                :     int         d;
 7559 bruce@momjian.us          789                 :            170 :     const uchr  ub = (uchr) base;
                                790                 :                : 
 7739 tgl@sss.pgh.pa.us         791                 :            170 :     n = 0;
 7559 bruce@momjian.us          792   [ +  +  +  + ]:            543 :     for (len = 0; len < maxlen && !ATEOS(); len++)
                                793                 :                :     {
 7739 tgl@sss.pgh.pa.us         794                 :            460 :         c = *v->now++;
 7559 bruce@momjian.us          795   [ +  -  +  +  :            460 :         switch (c)
                                        -  +  +  + ]
                                796                 :                :         {
                                797                 :            343 :             case CHR('0'):
                                798                 :                :             case CHR('1'):
                                799                 :                :             case CHR('2'):
                                800                 :                :             case CHR('3'):
                                801                 :                :             case CHR('4'):
                                802                 :                :             case CHR('5'):
                                803                 :                :             case CHR('6'):
                                804                 :                :             case CHR('7'):
                                805                 :                :             case CHR('8'):
                                806                 :                :             case CHR('9'):
                                807                 :            343 :                 d = DIGITVAL(c);
                                808                 :            343 :                 break;
 7559 bruce@momjian.us          809                 :UBC           0 :             case CHR('a'):
                                810                 :                :             case CHR('A'):
                                811                 :              0 :                 d = 10;
                                812                 :              0 :                 break;
 7559 bruce@momjian.us          813                 :CBC           8 :             case CHR('b'):
                                814                 :                :             case CHR('B'):
                                815                 :              8 :                 d = 11;
                                816                 :              8 :                 break;
                                817                 :              2 :             case CHR('c'):
                                818                 :                :             case CHR('C'):
                                819                 :              2 :                 d = 12;
                                820                 :              2 :                 break;
 7559 bruce@momjian.us          821                 :UBC           0 :             case CHR('d'):
                                822                 :                :             case CHR('D'):
                                823                 :              0 :                 d = 13;
                                824                 :              0 :                 break;
 7559 bruce@momjian.us          825                 :CBC           2 :             case CHR('e'):
                                826                 :                :             case CHR('E'):
                                827                 :              2 :                 d = 14;
                                828                 :              2 :                 break;
                                829                 :             29 :             case CHR('f'):
                                830                 :                :             case CHR('F'):
                                831                 :             29 :                 d = 15;
                                832                 :             29 :                 break;
                                833                 :             76 :             default:
                                834                 :             76 :                 v->now--;        /* oops, not a digit at all */
                                835                 :             76 :                 d = -1;
                                836                 :             76 :                 break;
                                837                 :                :         }
                                838                 :                : 
                                839         [ +  + ]:            460 :         if (d >= base)
                                840                 :                :         {                       /* not a plausible digit */
 7739 tgl@sss.pgh.pa.us         841                 :             11 :             v->now--;
                                842                 :             11 :             d = -1;
                                843                 :                :         }
                                844         [ +  + ]:            460 :         if (d < 0)
 7559 bruce@momjian.us          845                 :             87 :             break;              /* NOTE BREAK OUT */
                                846                 :            373 :         n = n * ub + (uchr) d;
                                847                 :                :     }
 7739 tgl@sss.pgh.pa.us         848         [ +  + ]:            170 :     if (len < minlen)
                                849         [ -  + ]:              7 :         ERR(REG_EESCAPE);
                                850                 :                : 
 7559 bruce@momjian.us          851                 :            170 :     return (chr) n;
                                852                 :                : }
                                853                 :                : 
                                854                 :                : /*
                                855                 :                :  * brenext - get next BRE token
                                856                 :                :  *
                                857                 :                :  * This is much like EREs except for all the stupid backslashes and the
                                858                 :                :  * context-dependency of some things.
                                859                 :                :  */
                                860                 :                : static int                      /* 1 normal, 0 failure */
 2489 tgl@sss.pgh.pa.us         861                 :            322 : brenext(struct vars *v,
                                862                 :                :         chr c)
                                863                 :                : {
 7559 bruce@momjian.us          864   [ +  +  +  +  :            322 :     switch (c)
                                           +  +  + ]
                                865                 :                :     {
                                866                 :             23 :         case CHR('*'):
                                867   [ +  +  +  +  :             23 :             if (LASTTYPE(EMPTY) || LASTTYPE('(') || LASTTYPE('^'))
                                              +  + ]
                                868                 :              6 :                 RETV(PLAIN, c);
 1192 tgl@sss.pgh.pa.us         869                 :             17 :             RETV('*', 1);
                                870                 :                :             break;
 7559 bruce@momjian.us          871                 :             74 :         case CHR('['):
                                872   [ +  +  +  + ]:             74 :             if (HAVE(6) && *(v->now + 0) == CHR('[') &&
                                873         [ +  + ]:             22 :                 *(v->now + 1) == CHR(':') &&
                                874         [ +  + ]:             12 :                 (*(v->now + 2) == CHR('<') ||
                                875         [ +  + ]:              8 :                  *(v->now + 2) == CHR('>')) &&
                                876         [ +  - ]:              8 :                 *(v->now + 3) == CHR(':') &&
                                877         [ +  - ]:              8 :                 *(v->now + 4) == CHR(']') &&
                                878         [ +  - ]:              8 :                 *(v->now + 5) == CHR(']'))
                                879                 :                :             {
                                880                 :              8 :                 c = *(v->now + 2);
                                881                 :              8 :                 v->now += 6;
                                882                 :              8 :                 NOTE(REG_UNONPOSIX);
                                883         [ +  + ]:              8 :                 RET((c == CHR('<')) ? '<' : '>');
                                884                 :                :             }
                                885                 :             66 :             INTOCON(L_BRACK);
                                886   [ +  +  +  + ]:             66 :             if (NEXT1('^'))
                                887                 :                :             {
                                888                 :              6 :                 v->now++;
                                889                 :              6 :                 RETV('[', 0);
                                890                 :                :             }
                                891                 :             60 :             RETV('[', 1);
                                892                 :                :             break;
                                893                 :              4 :         case CHR('.'):
                                894                 :              4 :             RET('.');
                                895                 :                :             break;
                                896                 :             18 :         case CHR('^'):
                                897         [ +  + ]:             18 :             if (LASTTYPE(EMPTY))
                                898                 :             14 :                 RET('^');
                                899         [ +  + ]:              4 :             if (LASTTYPE('('))
                                900                 :                :             {
                                901                 :              1 :                 NOTE(REG_UUNSPEC);
                                902                 :              1 :                 RET('^');
                                903                 :                :             }
 7739 tgl@sss.pgh.pa.us         904                 :              3 :             RETV(PLAIN, c);
                                905                 :                :             break;
 7559 bruce@momjian.us          906                 :             15 :         case CHR('$'):
                                907         [ -  + ]:             15 :             if (v->cflags & REG_EXPANDED)
 7559 bruce@momjian.us          908                 :UBC           0 :                 skip(v);
 7559 bruce@momjian.us          909         [ +  + ]:CBC          15 :             if (ATEOS())
                                910                 :             11 :                 RET('$');
                                911   [ +  +  +  -  :              4 :             if (NEXT2('\\', ')'))
                                              +  - ]
                                912                 :                :             {
                                913                 :              1 :                 NOTE(REG_UUNSPEC);
                                914                 :              1 :                 RET('$');
                                915                 :                :             }
                                916                 :              3 :             RETV(PLAIN, c);
                                917                 :                :             break;
                                918                 :             26 :         case CHR('\\'):
                                919                 :             26 :             break;              /* see below */
                                920                 :            162 :         default:
                                921                 :            162 :             RETV(PLAIN, c);
                                922                 :                :             break;
                                923                 :                :     }
                                924                 :                : 
 7739 tgl@sss.pgh.pa.us         925         [ -  + ]:             26 :     assert(c == CHR('\\'));
                                926                 :                : 
                                927         [ +  + ]:             26 :     if (ATEOS())
                                928         [ -  + ]:              1 :         FAILW(REG_EESCAPE);
                                929                 :                : 
                                930                 :             25 :     c = *v->now++;
 7559 bruce@momjian.us          931   [ +  +  +  +  :             25 :     switch (c)
                                           +  +  + ]
                                932                 :                :     {
                                933                 :              3 :         case CHR('{'):
                                934                 :              3 :             INTOCON(L_BBND);
                                935                 :              3 :             NOTE(REG_UBOUNDS);
                                936                 :              3 :             RET('{');
                                937                 :                :             break;
                                938                 :              6 :         case CHR('('):
                                939                 :              6 :             RETV('(', 1);
                                940                 :                :             break;
                                941                 :              6 :         case CHR(')'):
                                942                 :              6 :             RETV(')', c);
                                943                 :                :             break;
                                944                 :              3 :         case CHR('<'):
                                945                 :              3 :             NOTE(REG_UNONPOSIX);
                                946                 :              3 :             RET('<');
                                947                 :                :             break;
                                948                 :              3 :         case CHR('>'):
                                949                 :              3 :             NOTE(REG_UNONPOSIX);
                                950                 :              3 :             RET('>');
                                951                 :                :             break;
                                952                 :              2 :         case CHR('1'):
                                953                 :                :         case CHR('2'):
                                954                 :                :         case CHR('3'):
                                955                 :                :         case CHR('4'):
                                956                 :                :         case CHR('5'):
                                957                 :                :         case CHR('6'):
                                958                 :                :         case CHR('7'):
                                959                 :                :         case CHR('8'):
                                960                 :                :         case CHR('9'):
                                961                 :              2 :             NOTE(REG_UBACKREF);
                                962                 :              2 :             RETV(BACKREF, (chr) DIGITVAL(c));
                                963                 :                :             break;
                                964                 :              2 :         default:
                                965         [ +  - ]:              2 :             if (iscalnum(c))
                                966                 :                :             {
                                967                 :              2 :                 NOTE(REG_UBSALNUM);
                                968                 :              2 :                 NOTE(REG_UUNSPEC);
                                969                 :                :             }
                                970                 :              2 :             RETV(PLAIN, c);
                                971                 :                :             break;
                                972                 :                :     }
                                973                 :                : 
                                974                 :                :     assert(NOTREACHED);
                                975                 :                :     return 0;
                                976                 :                : }
                                977                 :                : 
                                978                 :                : /*
                                979                 :                :  * skip - skip white space and comments in expanded form
                                980                 :                :  */
                                981                 :                : static void
 2489 tgl@sss.pgh.pa.us         982                 :            829 : skip(struct vars *v)
                                983                 :                : {
 5904                           984                 :            829 :     const chr  *start = v->now;
                                985                 :                : 
 7559 bruce@momjian.us          986         [ +  - ]:            829 :     assert(v->cflags & REG_EXPANDED);
                                987                 :                : 
                                988                 :                :     for (;;)
                                989                 :                :     {
 7739 tgl@sss.pgh.pa.us         990   [ +  +  +  + ]:           1342 :         while (!ATEOS() && iscspace(*v->now))
                                991                 :            443 :             v->now++;
                                992   [ +  +  +  + ]:            899 :         if (ATEOS() || *v->now != CHR('#'))
                                993                 :                :             break;              /* NOTE BREAK OUT */
                                994   [ +  -  -  + ]:             70 :         assert(NEXT1('#'));
                                995   [ +  -  +  + ]:            704 :         while (!ATEOS() && *v->now != CHR('\n'))
                                996                 :            634 :             v->now++;
                                997                 :                :         /* leave the newline to be picked up by the iscspace loop */
                                998                 :                :     }
                                999                 :                : 
                               1000         [ +  + ]:            829 :     if (v->now != start)
                               1001                 :            103 :         NOTE(REG_UNONPOSIX);
                               1002                 :            829 : }
                               1003                 :                : 
                               1004                 :                : /*
                               1005                 :                :  * newline - return the chr for a newline
                               1006                 :                :  *
                               1007                 :                :  * This helps confine use of CHR to this source file.
                               1008                 :                :  */
                               1009                 :                : static chr
                               1010                 :            272 : newline(void)
                               1011                 :                : {
                               1012                 :            272 :     return CHR('\n');
                               1013                 :                : }
                               1014                 :                : 
                               1015                 :                : /*
                               1016                 :                :  * chrnamed - return the chr known by a given (chr string) name
                               1017                 :                :  *
                               1018                 :                :  * The code is a bit clumsy, but this routine gets only such specialized
                               1019                 :                :  * use that it hardly matters.
                               1020                 :                :  */
                               1021                 :                : static chr
 2489                          1022                 :              2 : chrnamed(struct vars *v,
                               1023                 :                :          const chr *startp,     /* start of name */
                               1024                 :                :          const chr *endp,       /* just past end of name */
                               1025                 :                :          chr lastresort)        /* what to return if name lookup fails */
                               1026                 :                : {
                               1027                 :                :     chr         c;
                               1028                 :                :     int         errsave;
                               1029                 :                :     int         e;
                               1030                 :                :     struct cvec *cv;
                               1031                 :                : 
 7739                          1032                 :              2 :     errsave = v->err;
                               1033                 :              2 :     v->err = 0;
                               1034                 :              2 :     c = element(v, startp, endp);
                               1035                 :              2 :     e = v->err;
                               1036                 :              2 :     v->err = errsave;
                               1037                 :                : 
                               1038         [ -  + ]:              2 :     if (e != 0)
 2795 tgl@sss.pgh.pa.us        1039                 :UBC           0 :         return lastresort;
                               1040                 :                : 
 7739 tgl@sss.pgh.pa.us        1041                 :CBC           2 :     cv = range(v, c, c, 0);
                               1042         [ +  - ]:              2 :     if (cv->nchrs == 0)
 2795                          1043                 :              2 :         return lastresort;
 7739 tgl@sss.pgh.pa.us        1044                 :UBC           0 :     return cv->chrs[0];
                               1045                 :                : }
        

Generated by: LCOV version 2.1-beta2-3-g6141622