1 %option yylineno
2 
3 %{
4 #include "pscan.h"
5 static void skip_strings(char literal);
6 %}
7 
8 %x comment
9 %x strings
10 
11 reserved    "default"|"struct"|"void"|"for"|"if"|"else"|"while"|"do"|"return"|"case"|"switch"|"break"|"auto"|"continue"|"goto"|"sizeof"|"static"|"typedef"|"union"|"volatile"
12 
13 vartype "char"|"double"|"enum"|"extern"|"float"|"int"|"long"|"register"|"short"|"signed"|"unsigned"|"const"
14 
15 cprep "include"|"define"|"if"|"else"|"endif"|"ifdef"|"ifndef"
16 
17 %%
18 {reserved}                            state->last_token = NOT_PROBLEMATIC;
19 
20 {vartype}                             state->last_token = NOT_PROBLEMATIC;
21 
22 
23 "#"{cprep}                            state->last_token = NOT_PROBLEMATIC;
24 
25 NULL				      { if ((state->last_token == PROBLEMATIC) &&
26                                           (state->constant_string < 0)) {
27                                          state->constant_string = state->args;
28                                          }
29                                        }
30 
31 \"                                    {
32                                           if (state->last_token == PROBLEMATIC) {
33                                           if (state->constant_string < 0) {
34                                           state->constant_string = state->args;
35                                           }
36 }
37                                           skip_strings('"');
38                                       }
39 
40 \'                                    skip_strings('\'');
41 
42 \/\/.*$                               /* skip C++ style comments */
43 
44 [a-zA-Z_][_a-zA-Z0-9]*                state = setup_checks(yytext, state);
45 
46 [ \t]+                                /* eat up whitespace */
47 
48 \(                                    {
49                                         if (state->args < 0) state->args = 0;
50                                         state->braces++;
51                                         if (state->braces > 1) {
52                                           state = push_stack(state);
53                                           state->last_token = NOT_PROBLEMATIC;
54                                           state->braces = 1;
55                                           state->args = -1;
56                                         }
57                                       }
58 
59 \,                                    if (state->last_token == PROBLEMATIC) {
60                                         if (state->braces != 0) {
61                                           state->args++;
62                                         } else {
63                                           state->last_token = NOT_PROBLEMATIC;
64                                         }
65                                       }
66 
67 \)                                    if (state->last_token == PROBLEMATIC) {
68                                         check_function(state);
69                                         state->last_token = NOT_PROBLEMATIC;
70                                       } else if (state->braces != 0) {
71                                         state->braces--;
72                                         if (state->braces == 0) {
73                                           state = pop_stack();
74                                         }
75                                       }
76 
77 .                                     {
78                                         if ((state->last_token == PROBLEMATIC) &&
79                                              (state->braces == 0)) {
80                                           state->last_token = NOT_PROBLEMATIC;
81                                         }
82                                       }
83 
84 
85 "\n"|"\r"          		      /* ignore LF's and CR's */
86 
87 
88 "/*"    BEGIN(comment);
89 
90 <comment>[^*\n]*        /* eat anything that's not a '*' */
91 <comment>"*"+[^*/\n]*   /* eat up '*'s not followed by '/'s */
92 <comment>\n             /* do nothing */
93 <comment>"*"+"/"        BEGIN(INITIAL);
94 
95 %%
96 /**********************************************************************
97  * pscan: http://www.striker.ottawa.on.ca/~aland/pscan/
98  *
99  * Copyright (C) 2000 Alan DeKok <aland@ox.org>
100  *
101  * This program is free software; you can redistribute it and/or modify
102  * it under the terms of the GNU General Public License as published by
103  * the Free Software Foundation; either version 2 of the License, or
104  * (at your option) any later version.
105  *
106  * This program is distributed in the hope that it will be useful,
107  * but WITHOUT ANY WARRANTY; without even the implied warranty of
108  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
109  * GNU General Public License for more details.
110  *
111  * You should have received a copy of the GNU General Public License
112  * along with this program; if not, write to the Free Software
113  * Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA
114  *
115  **********************************************************************/
116 static const char rcsid[] = "$Id: scanner.l,v 1.4 2000/07/17 18:51:45 aland Exp $";
117 
118 /* static */
119 void skip_strings(char literal)
120 {
121        int c;
122 
123        while ((c = input()) != literal)
124            {
125            switch (c) {
126 
127            case '\\':
128                       c = input();
129                       if (c == '\\') continue;
130                       if (c == EOF) return;
131                       if (c != literal)
132                         unput(c);
133                       break;
134            case EOF:
135                 return;
136 
137            default:
138                       break;
139             }
140           }
141 }
142