Skip to content

Commit 096bf57

Browse files
committed
Fix some wrong line numbers
1 parent f0e1577 commit 096bf57

File tree

4 files changed

+127
-104
lines changed

4 files changed

+127
-104
lines changed

lex.c

Lines changed: 29 additions & 28 deletions
Original file line numberDiff line numberDiff line change
@@ -69,7 +69,7 @@ static inline int is_str(int c)
6969
return isalnum(c) || c == '_';
7070
}
7171

72-
static TOKEN syntax_error(Lexer* S, char* fmt, ...)
72+
static Token syntax_error(Lexer* S, char* fmt, ...)
7373
{
7474
va_list ap;
7575
char msgbuf[256];
@@ -119,14 +119,14 @@ static char* fetch_str(Lexer* S, int (*proceed_condition)(int))
119119
}
120120

121121

122-
static int lex_ident(Lexer* S)
122+
static Token lex_ident(Lexer* S)
123123
{
124124
char* str = fetch_str(S, is_str);
125125
if (!str) {
126126
return syntax_error(S, "Fetching str failed.");
127127
}
128128

129-
TOKEN ret;
129+
TOKENTYPE ret;
130130
if (strcmp(str, "echo") == 0) {
131131
ret = TK_ECHO;
132132
} else if (strcmp(str, "function") == 0) {
@@ -155,20 +155,20 @@ static int lex_ident(Lexer* S)
155155
}
156156

157157
free(str);
158-
return ret;
158+
return create_token(ret, S->lineno);
159159
}
160160

161-
static TOKEN lex_var(Lexer* S)
161+
static Token lex_var(Lexer* S)
162162
{
163163
assert(is_var_start(S->lexchar));
164164
get_next_char(S); // Skip $
165165
char* str = fetch_str(S, is_str);
166166
state_set_string(S, str);
167167

168-
return TK_VAR;
168+
return create_token(TK_VAR, S->lineno);
169169
}
170170

171-
static TOKEN lex_str(Lexer* S)
171+
static Token lex_str(Lexer* S)
172172
{
173173
assert(S->lexchar == '"');
174174
int escape = false;
@@ -212,7 +212,7 @@ static TOKEN lex_str(Lexer* S)
212212
sprintf(errormsg, "Expected \", got %c", S->lexchar);
213213
}
214214
free(str);
215-
TOKEN ret = syntax_error(S, errormsg);
215+
Token ret = syntax_error(S, errormsg);
216216
free(errormsg);
217217
return ret;
218218
}
@@ -221,32 +221,32 @@ static TOKEN lex_str(Lexer* S)
221221

222222
get_next_char(S); // Skip "
223223

224-
return TK_STRING;
224+
return create_token(TK_STRING, S->lineno);
225225
}
226226

227-
int lex_num(Lexer* S)
227+
Token lex_num(Lexer* S)
228228
{
229229
char* numstr = fetch_str(S, isdigit);
230230
int64_t n = (int64_t) strtoll(numstr, NULL, 10);
231231
free(numstr);
232232
state_set_long(S, n);
233233

234-
return TK_LONG;
234+
return create_token(TK_LONG, S->lineno);
235235
}
236236

237-
#define LEX_TWICE(current, expected, TOKEN) \
237+
#define LEX_TWICE(current, expected, TOKENTYPE) \
238238
if ((current) == (expected)) { \
239239
if ((expected) == get_next_char(S)) { \
240240
get_next_char(S); \
241-
return TOKEN; \
241+
return create_token(TOKENTYPE, S->lineno); \
242242
} else \
243-
return (expected); \
243+
return create_token((expected), S->lineno); \
244244
}
245245

246-
int get_token(Lexer* S)
246+
Token get_token(Lexer* S)
247247
{
248248
if (S->lexchar == EOF) {
249-
return TK_END;
249+
return create_token(TK_END, S->lineno);
250250
}
251251

252252
if (S->mode == NONPHP) {
@@ -270,17 +270,17 @@ int get_token(Lexer* S)
270270
return get_token(S);
271271
}
272272
S->u.string = html;
273-
return TK_HTML;
273+
return create_token(TK_HTML, S->lineno);
274274
} else if (S->mode == EMITOPENTAG) {
275275
S->mode = PHP;
276-
return TK_OPENTAG;
276+
return create_token(TK_OPENTAG, S->lineno);
277277
}
278278

279279
int c = S->lexchar;
280280
while (is_whitespace(c)) {
281281
c = get_next_char(S); // Consume whitespace
282282
if (c == EOF) {
283-
return TK_END;
283+
return create_token(TK_END, S->lineno);
284284
}
285285
}
286286

@@ -310,26 +310,26 @@ int get_token(Lexer* S)
310310
c = get_next_char(S);
311311
if (c == '=') {
312312
get_next_char(S);
313-
return TK_LTEQ;
313+
return create_token(TK_LTEQ, S->lineno);
314314
} else if (c == '<') {
315315
get_next_char(S);
316-
return TK_SHL;
316+
return create_token(TK_SHL, S->lineno);
317317
}
318318

319-
return '<';
319+
return create_token('<', S->lineno);
320320
}
321321

322322
if (c == '>') {
323323
c = get_next_char(S);
324324
if (c == '=') {
325325
get_next_char(S);
326-
return TK_GTEQ;
326+
return create_token(TK_GTEQ, S->lineno);
327327
} else if (c == '>') {
328328
get_next_char(S);
329-
return TK_SHR;
329+
return create_token(TK_SHR, S->lineno);
330330
}
331331

332-
return '>';
332+
return create_token('>', S->lineno);
333333
}
334334

335335
if (c == '/') {
@@ -339,12 +339,12 @@ int get_token(Lexer* S)
339339
S->lineno++;
340340
return get_token(S);
341341
} else {
342-
return '/';
342+
return create_token('/', S->lineno);
343343
}
344344
}
345345

346346
get_next_char(S);
347-
return c;
347+
return create_token(c, S->lineno);
348348
}
349349

350350
Lexer* create_lexer(FILE *file)
@@ -358,6 +358,7 @@ Lexer* create_lexer(FILE *file)
358358
ret->lineno = 1;
359359
ret->mode = NONPHP;
360360
ret->file = file;
361+
ret->token = create_token(0, 1);
361362
get_next_char(ret);
362363
return ret;
363364
}
@@ -421,7 +422,7 @@ char* get_token_name(int tok)
421422
void print_tokenstream(Lexer* S)
422423
{
423424
int tok;
424-
while ((tok = get_token(S)) != TK_END) {
425+
while ((tok = get_token(S).type) != TK_END) {
425426
char* name = get_token_name(tok);
426427
if (name) {
427428
puts(name);

lex.h

Lines changed: 16 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -6,7 +6,7 @@
66
#include <stdlib.h>
77
#include <stdint.h>
88

9-
typedef enum TOKEN {
9+
typedef enum TOKENTYPE {
1010
TK_OPENTAG = 256, // Make them outside ascii range
1111
TK_IDENTIFIER,
1212
TK_ECHO,
@@ -37,11 +37,23 @@ typedef enum TOKEN {
3737

3838
TK_HTML,
3939
TK_END
40-
} TOKEN;
40+
} TOKENTYPE;
4141
enum MODE {
4242
PHP, NONPHP, EMITOPENTAG
4343
};
4444

45+
typedef uint32_t lineno_t;
46+
47+
typedef struct Token {
48+
TOKENTYPE type;
49+
lineno_t lineno;
50+
} Token;
51+
52+
static inline Token create_token(TOKENTYPE type, lineno_t lineno) {
53+
Token ret = { .type = type, .lineno = lineno };
54+
return ret;
55+
}
56+
4557
typedef enum VALTYPE {
4658
NONE,
4759
MALLOCSTR,
@@ -50,13 +62,12 @@ typedef enum VALTYPE {
5062
ERROR
5163
} VALTYPE;
5264

53-
typedef uint32_t lineno_t;
5465

5566
typedef struct Lexer {
5667
enum MODE mode;
5768
lineno_t lineno;
5869
FILE* file;
59-
int token;
70+
Token token;
6071
int lexchar;
6172
VALTYPE val;
6273
union {
@@ -69,7 +80,7 @@ typedef struct Lexer {
6980
Lexer* create_lexer(FILE *);
7081
void destroy_lexer(Lexer *);
7182

72-
int get_token(Lexer*);
83+
Token get_token(Lexer*);
7384
char* get_token_name(int);
7485
void print_tokenstream(Lexer*);
7586

0 commit comments

Comments
 (0)