X-Git-Url: http://nsz.repo.hu/git/?a=blobdiff_plain;f=lexer.c;h=8e0567e3c636820e65ba7a147d232776c0a4839d;hb=26aba71a371f0bbcc8afd213b4398d4e4e52a6f2;hp=c3f86b3845fbe80c5eda9e5c0563d9af19089af0;hpb=2beaa4f65961fe297663e1cec9e5632b7f3e1cba;p=cparser diff --git a/lexer.c b/lexer.c index c3f86b3..8e0567e 100644 --- a/lexer.c +++ b/lexer.c @@ -87,7 +87,9 @@ static size_t read_block(unsigned char *const read_buf, size_t const n) { size_t const s = fread(read_buf, 1, n, input); if (s == 0) { - if (ferror(input)) + /* on OS/X ferror appears to return true on eof as well when running + * the application in gdb... */ + if (!feof(input) && ferror(input)) parse_error("read from input failed"); buf[MAX_PUTBACK] = EOF; bufpos = buf + MAX_PUTBACK; @@ -333,10 +335,20 @@ static named_decoder_t const decoders[] = { { NULL, NULL } }; +/** strcasecmp is not part of C99 so we need our own implementation here */ +static int my_strcasecmp(const char *s1, const char *s2) +{ + for ( ; *s1 != 0; ++s1, ++s2) { + if (tolower(*s1) != tolower(*s2)) + break; + } + return (unsigned char)*s1 - (unsigned char)*s2; +} + void select_input_encoding(char const* const encoding) { for (named_decoder_t const *i = decoders; i->name != NULL; ++i) { - if (strcasecmp(encoding, i->name) != 0) + if (my_strcasecmp(encoding, i->name) != 0) continue; decoder = i->decoder; return; @@ -649,8 +661,9 @@ static void parse_number_hex(void) errorf(&lexer_token.source_position, "hexadecimal floatingpoint constant requires an exponent"); } + obstack_1grow(&symbol_obstack, '\0'); - size_t size = obstack_object_size(&symbol_obstack); + size_t size = obstack_object_size(&symbol_obstack) - 1; char *string = obstack_finish(&symbol_obstack); lexer_token.literal = identify_string(string, size); @@ -743,7 +756,8 @@ static void parse_number(void) } } - size_t size = obstack_object_size(&symbol_obstack); + obstack_1grow(&symbol_obstack, '\0'); + size_t size = obstack_object_size(&symbol_obstack) - 1; char *string = obstack_finish(&symbol_obstack); lexer_token.literal = identify_string(string, size); @@ -756,7 +770,7 @@ static void parse_number(void) /* check for invalid octal digits */ for (size_t i= 0; i < size; ++i) { char t = string[i]; - if (t == '8' || t == '9') + if (t >= '8') errorf(&lexer_token.source_position, "invalid digit '%c' in octal number", t); } @@ -1032,7 +1046,8 @@ static void parse_wide_character_constant(void) } end_of_wide_char_constant:; - size_t size = (size_t) obstack_object_size(&symbol_obstack); + obstack_1grow(&symbol_obstack, '\0'); + size_t size = (size_t) obstack_object_size(&symbol_obstack) - 1; char *string = obstack_finish(&symbol_obstack); lexer_token.type = T_WIDE_CHARACTER_CONSTANT; @@ -1097,7 +1112,8 @@ static void parse_character_constant(void) } end_of_char_constant:; - const size_t size = (size_t)obstack_object_size(&symbol_obstack); + obstack_1grow(&symbol_obstack, '\0'); + const size_t size = (size_t)obstack_object_size(&symbol_obstack)-1; char *const string = obstack_finish(&symbol_obstack); lexer_token.type = T_CHARACTER_CONSTANT; @@ -1238,7 +1254,8 @@ static void parse_line_directive(void) if (pp_token.type != T_INTEGER) { parse_error("expected integer"); } else { - lexer_token.source_position.linenr = atoi(pp_token.literal.begin); + /* use offset -1 as this is about the next line */ + lexer_token.source_position.linenr = atoi(pp_token.literal.begin) - 1; next_pp_token(); } if (pp_token.type == T_STRING_LITERAL) { @@ -1652,15 +1669,15 @@ void lexer_open_buffer(const char *buffer, size_t len, const char *input_name) #if 0 // TODO bufpos = buffer; bufend = buffer + len; + + /* place a virtual \n at the beginning so the lexer knows that we're + * at the beginning of a line */ + c = '\n'; #else (void)buffer; (void)len; panic("builtin lexing not done yet"); #endif - - /* place a virtual \n at the beginning so the lexer knows that we're - * at the beginning of a line */ - c = '\n'; } void exit_lexer(void)