F diff --git a/src/environment/error/gcc_error.c b/src/environment/error/gcc_error.c
--- a/src/environment/error/gcc_error.c
+++ b/src/environment/error/gcc_error.c
%D - denoted
%I - identifier
*/
- struct Translation_Message* get_translation_message(const char *message_format,struct Program *program,struct Source_Location *location,va_list args)
+ struct Translation_Message* get_translation_message(const char *message_format,struct Program *program,char *filename,size_t filename_size,size_t line,size_t column,va_list args)
{
size_t i;
struct Translation_Message *ret;
- hold_return_string=get_translation_message_location_prefix(location->src_name->full_name,location->line,location->column);
+ hold_return_string=get_translation_message_location_prefix(filename,line,column);
for(i=0;i<1000 && message_format[i]!='\0';++i)
ret=wonky_malloc(sizeof(struct Translation_Message));
ret->message=hold_return_string;
- ret->line=location->line;
- ret->column=location->column;
- ret->filename=location->src_name->full_name;
+ ret->line=line;
+ ret->column=column;
+ ret->filename=filename;
return ret;
}
{
Queue_Push(program->errors,message);
}
- void push_translation_message_inner(const char *prefix,const char *message_format,struct Program *program,struct Source_Location *location,va_list args)
+ void push_translation_message_inner(const char *prefix,const char *message_format,struct Program *program,char *filename,size_t filename_size,size_t line,size_t column,va_list args)
{
struct Translation_Message *hold_message;
- char *filename=NULL;
- size_t line=0;
- size_t row=0;
-
- hold_message=get_translation_message(message_format,program,location,args);
+ hold_message=get_translation_message(message_format,program,filename,filename_size,line,column,args);
hold_message->message=gstr_append_and_consume(gstr_to_heap(prefix),hold_message->message);
Queue_Push(program->errors,hold_message);
}
{
va_list args;
va_start(args,translation_data);
- push_translation_message_inner("[Error] ",message_format,translation_data->program,translation_data->token_pointer->current_location,args);
+ push_translation_message_inner("[Error] ",
+ message_format,
+ translation_data->program,
+ translation_data->token_pointer->context->filename,
+ translation_data->token_pointer->context->filename_size,
+ translation_data->token_pointer->context->line,
+ translation_data->token_pointer->context->column,
+ args);
va_end(args);
}
void push_translation_note(const char *note_message,struct Translation_Data *translation_data, ...)
{
va_list args;
va_start(args,translation_data);
- push_translation_message_inner("[Note] ",note_message,translation_data->program,translation_data->token_pointer->current_location,args);
+ push_translation_message_inner("[Note] ",
+ note_message,
+ translation_data->program,
+ translation_data->token_pointer->context->filename,
+ translation_data->token_pointer->context->filename_size,
+ translation_data->token_pointer->context->line,
+ translation_data->token_pointer->context->column,
+ args);
va_end(args);
}
void push_lexing_error(char *error_message,struct Lexer_Data *lexer_data)
F diff --git a/src/environment/error/gcc_error.h b/src/environment/error/gcc_error.h
--- a/src/environment/error/gcc_error.h
+++ b/src/environment/error/gcc_error.h
%D denoted - takes pointer to Denoted
%I identifier - takes pointer to an id
*/
- struct Translation_Message* get_translation_message(const char *message_format,struct Program *program,struct Source_Location *location,va_list args);
- struct Translation_Message* get_translation_message_inner(const char *message,struct Program *program,struct Source_Location *location);
+ struct Translation_Message* get_translation_message(const char *message_format,struct Program *program,char *filename,size_t filename_size,size_t line,size_t column,va_list args);
+ struct Translation_Message* get_translation_message_inner(const char *message,struct Program *program,char *filename,size_t filename_size,size_t line,size_t column);
void push_translation_message_into_program_as_error(struct Translation_Message *message,struct Program *program);
- void push_translation_message_inner(const char *prefix,const char *message_format,struct Program *program,struct Source_Location *location,va_list args);
+ void push_translation_message_inner(const char *prefix,const char *message_format,struct Program *program,char *filename,size_t filename_size,size_t line,size_t column,va_list args);
void push_translation_error(const char *message_format,struct Translation_Data *translation_data, ...);
void push_translation_note(const char *note_message,struct Translation_Data *translation_data, ...);
F diff --git a/src/frontend/lex/lex_preprocessing_directive.c b/src/frontend/lex/lex_preprocessing_directive.c
--- a/src/frontend/lex/lex_preprocessing_directive.c
+++ b/src/frontend/lex/lex_preprocessing_directive.c
ret=preprocessing_extract_next_token(lexer_data);
if(ret==NULL)
- return get_error_token("PREPROCESSING EMPTY DIRECTIVE NOT SUPPORTED",where,lexer_data->program);
+ return get_error_token("PREPROCESSING EMPTY DIRECTIVE NOT SUPPORTED",where,lexer_data->previous_token_location,lexer_data->program);
- switch(ret->type)
- {
- case LT_ERROR:
- return ret;
- default:
- return get_error_token("PREPROCESSING DIRECTIVE NOT RECOGNIZED",where,lexer_data->program);
- }
return ret;
}
struct token* preprocessing_lex_defined_unary_operator(struct Lexer_Data *lexer_data,struct Source_Location *where)
{
- return get_error_token("PREPROCESSING DIRECTIVES NOT DONE",where,lexer_data->program);
+ return get_error_token("PREPROCESSING DIRECTIVES NOT DONE",where,lexer_data->previous_token_location,lexer_data->program);
}
struct token* preprocessing_extract_next_token(struct Lexer_Data *lexer_data)
{
lexer_data->where_in_src,
lexer_data->src->src_name
),
+ lexer_data->previous_token_location,
lexer_data->program);
}while(hold_node->keyword==KW_COMMENT);
switch(finishing_node->preprocessing_keyword)
{
case PKW_IF:
- return get_error_token("PREPROCESSING IF NOT DONE",token_location,lexer_data->program);
+ return get_error_token("PREPROCESSING IF NOT DONE",token_location,lexer_data->previous_token_location,lexer_data->program);
case PKW_IFDEF:
- return get_error_token("PREPROCESSING IFDEF NOT DONE",token_location,lexer_data->program);
+ return get_error_token("PREPROCESSING IFDEF NOT DONE",token_location,lexer_data->previous_token_location,lexer_data->program);
case PKW_IFNDEF:
- return get_error_token("PREPROCESSING IFNDEF NOT DONE",token_location,lexer_data->program);
+ return get_error_token("PREPROCESSING IFNDEF NOT DONE",token_location,lexer_data->previous_token_location,lexer_data->program);
case PKW_ELIF:
- return get_error_token("PREPROCESSING ELIF NOT DONE",token_location,lexer_data->program);
+ return get_error_token("PREPROCESSING ELIF NOT DONE",token_location,lexer_data->previous_token_location,lexer_data->program);
case PKW_ELSE:
- return get_error_token("PREPROCESSING ELSE NOT DONE",token_location,lexer_data->program);
+ return get_error_token("PREPROCESSING ELSE NOT DONE",token_location,lexer_data->previous_token_location,lexer_data->program);
case PKW_ENDIF:
- return get_error_token("PREPROCESSING ENDIF NOT DONE",token_location,lexer_data->program);
+ return get_error_token("PREPROCESSING ENDIF NOT DONE",token_location,lexer_data->previous_token_location,lexer_data->program);
case PKW_INCLUDE:
- return get_error_token("PREPROCESSING INCLUDE NOT DONE",token_location,lexer_data->program);
+ return get_error_token("PREPROCESSING INCLUDE NOT DONE",token_location,lexer_data->previous_token_location,lexer_data->program);
case PKW_DEFINE:
- return get_error_token("PREPROCESSING DEFINE NOT DONE",token_location,lexer_data->program);
+ return get_error_token("PREPROCESSING DEFINE NOT DONE",token_location,lexer_data->previous_token_location,lexer_data->program);
case PKW_UNDEF:
- return get_error_token("PREPROCESSING UNDEF NOT DONE",token_location,lexer_data->program);
+ return get_error_token("PREPROCESSING UNDEF NOT DONE",token_location,lexer_data->previous_token_location,lexer_data->program);
case PKW_LINE:
- return get_error_token("PREPROCESSING LINE NOT DONE",token_location,lexer_data->program);
+ return preprocessing_lex_line_directive(lexer_data,token_location);
case PKW_ERROR:
- return get_error_token("PREPROCESSING ERROR NOT DONE",token_location,lexer_data->program);
+ return preprocessing_lex_error_directive(lexer_data,token_location);
case PKW_PRAGMA:
- return get_error_token("PREPROCESSING PRAGMA NOT DONE",token_location,lexer_data->program);
+ return get_error_token("PREPROCESSING PRAGMA NOT DONE",token_location,lexer_data->previous_token_location,lexer_data->program);
case PKW_DEFINED:
- return get_error_token("PREPROCESSING DEFINED NOT DONE",token_location,lexer_data->program);
+ return get_error_token("PREPROCESSING DEFINED NOT DONE",token_location,lexer_data->previous_token_location,lexer_data->program);
default:
return lexer_make_token_finishing_on_node(lexer_data,finishing_node,start_position);
}
wonky_assert(SHOULD_NOT_REACH_HERE);
}
+ struct token* preprocessing_lex_line_directive(struct Lexer_Data *lexer_data,struct Source_Location *where)
+ {
+ struct token_line_directive *ret;
+ struct token_constant *hold_token_constant;
+ struct token_string *hold_token_string;
+
+ ret=wonky_malloc(sizeof(struct token_line_directive));
+ ret->type=PKW_LINE;
+ ret->directive_delta=get_source_location_delta(lexer_data->previous_token_location,where);
+
+ ret->filename=NULL;
+
+ if(!preprocessing_eol(lexer_data))
+ {
+ hold_token_constant=(struct token_constant*)preprocessing_extract_next_token(lexer_data);
+ if(hold_token_constant->type!=KW_CONSTANT || !type_is_a_plain_signed_int(hold_token_constant->constant->type))
+ {
+ push_lexing_error("Expected a digit sequence in the #line directive",lexer_data);
+ ret->line=0;
+ return (struct token*)ret;
+ }else
+ {
+ /*TODO make it not host type specific*/
+ ret->line=*(int*)hold_token_constant->constant->value;
+ wonky_free(hold_token_constant);
+ }
+ }else
+ {
+ push_lexing_error("Expected a digit sequence in the #line directive",lexer_data);
+ ret->line=0;
+ return (struct token*)ret;
+ }
+
+ if(!preprocessing_eol(lexer_data))
+ {
+ hold_token_string=(struct token_string*)preprocessing_extract_next_token(lexer_data);
+ if(hold_token_string->type!=KW_STRING || !type_is_a_normal_string(hold_token_string->constant->type))
+ {
+ push_lexing_error("Expected a digit sequence in the #line directive",lexer_data);
+ ret->line=0;
+ return (struct token*)ret;
+ }else
+ {
+ /*TODO make it not host type specific*/
+ ret->filename=(char*)hold_token_string->constant->value;
+ ret->filename_size=get_type_size(hold_token_string->constant->type);
+ }
+ }
+
+
+ return (struct token*)ret;
+ }
+ /* pp[opt] nl */
+ struct token* preprocessing_lex_error_directive(struct Lexer_Data *lexer_data,struct Source_Location *where)
+ {
+ struct token_error_directive *ret;
+ size_t hold_start_location;
+ size_t hold_error_size;
+
+ hold_start_location=lexer_data->where_in_src;
+ preprocessing_goto_end_of_line(lexer_data);
+
+ ret=wonky_malloc(sizeof(struct token_error_directive));
+ ret->type=PKW_ERROR;
+ ret->delta=get_source_location_delta(lexer_data->previous_token_location,where);
+
+ hold_error_size=lexer_data->where_in_src-hold_start_location;
+ ret->error_message=wonky_malloc(sizeof("#error ")+hold_error_size);
+ ret->error_message[sizeof("#error ")+hold_error_size]='\0';
+
+ gmemmove(ret->error_message,"#error ",sizeof("#error ")-1);
+ gmemmove(ret->error_message+sizeof("#error ")-1,lexer_data->src->src+hold_start_location,hold_error_size);
+
+ return (struct token*)ret;
+ }
+ void preprocessing_goto_end_of_line(struct Lexer_Data *lexer_data)
+ {
+ enum {
+ START,
+ START_OF_POSSIBLE_LINE_SPLICE,
+ END,
+ } state;
+ state=START;
+ do{
+
+ if(lexer_eof(lexer_data))
+ return ;
+
+ switch(state)
+ {
+ case START:
+ if(lexer_data->src->src[lexer_data->where_in_src] == '\\')
+ {
+ state=START_OF_POSSIBLE_LINE_SPLICE;
+ ++lexer_data->where_in_src;
+ ++lexer_data->which_column;
+ }else if(lexer_data->src->src[lexer_data->where_in_src]=='\n')
+ {
+ state=END;
+ }else
+ {
+ state=START;
+ ++lexer_data->where_in_src;
+ ++lexer_data->which_column;
+ }
+ break;
+ case START_OF_POSSIBLE_LINE_SPLICE:
+ if(lexer_data->src->src[lexer_data->where_in_src] == '\n')
+ {
+ state=START;
+ ++lexer_data->where_in_src;
+ lexer_data->which_column=0;
+ ++lexer_data->which_row;
+ }else
+ {
+ state=START;
+ }
+ break;
+ default:
+ wonky_assert(SHOULD_NOT_REACH_HERE);
+ }
+
+ }while(state!=END);
+
+ }
#endif
F diff --git a/src/frontend/lex/lex_preprocessing_directive.h b/src/frontend/lex/lex_preprocessing_directive.h
--- a/src/frontend/lex/lex_preprocessing_directive.h
+++ b/src/frontend/lex/lex_preprocessing_directive.h
struct token* preprocessing_lex_defined_unary_operator(struct Lexer_Data *lexer_data,struct Source_Location *where);
+ void preprocessing_goto_end_of_line(struct Lexer_Data *lexer_data);
struct token* preprocessing_extract_next_token(struct Lexer_Data *lexer_data);
struct Automata_Node* preprocessing_feed_automata_until_error(struct Lexer_Data *lexer_data);
struct Automata_Node *preprocessing_feed_automata_next_char(struct Lexer_Data *lexer_data,struct Automata_Node *node);
F diff --git a/src/frontend/lex/lexer.c b/src/frontend/lex/lexer.c
--- a/src/frontend/lex/lexer.c
+++ b/src/frontend/lex/lexer.c
ret->automata_view=AUTOMATA_VIEW_NORMAL;
ret->src=src;
ret->program=program;
+ ret->previous_token_location=&start_of_file;
return ret;
lexer_data->where_in_src,
lexer_data->src->src_name
),
+ lexer_data->previous_token_location,
lexer_data->program);
}while(hold_node->keyword==KW_COMMENT);
ret=lexer_make_token_finishing_on_node(lexer_data, hold_node, where_does_the_token_start_in_the_source_file);
lexer_data->is_in_the_begining_of_line=0;
+ lexer_data->previous_token_location=ret->delta->location;
return ret;
}
{
if(!lexer_data->is_in_the_begining_of_line)
{
- return get_error_token("# is not in the begining of a logical line",token_location,lexer_data->program);
+ return get_error_token("# is not in the begining of a logical line",token_location,lexer_data->previous_token_location,lexer_data->program);
}else
{
return lex_preprocessing_directive(lexer_data,token_location);
id=get_identifier(lexer_data->src->src+start_position,lexer_data->where_in_src-start_position);
finishing_node->data=id;
}
- return get_id_token(finishing_node->data,token_location);
+ return get_id_token(finishing_node->data,token_location,lexer_data->previous_token_location);
break;
case KW_AUTO:
case KW_DO:
case KW_BOOL:
case KW_COMPLEX:
case KW_IMAGINARY:
- return get_keyword_token(finishing_node->keyword,token_location);
+ return get_keyword_token(finishing_node->keyword,token_location,lexer_data->previous_token_location);
case KW_EXCLAMATION:
case KW_PERCENT:
case KW_OPEN_CURLY:
case KW_DIV_EQ:
case KW_FORWARD_SLASH:
- return get_punctuator_token(finishing_node->keyword,token_location);
+ return get_punctuator_token(finishing_node->keyword,token_location,lexer_data->previous_token_location);
case KW_HEXADECIMAL_CONSTANT:
case KW_DECIMAL_CONSTANT:
case KW_FLOAT_HEXADECIMAL_CONSTANT:
case KW_CHAR_CONSTANT:
case KW_WIDE_CHAR_CONSTANT:
- return get_constant_token(finishing_node->keyword,token_location,lexer_data->src->src+start_position,lexer_data->where_in_src-start_position);
+ return get_constant_token(finishing_node->keyword,token_location,lexer_data->previous_token_location,lexer_data->src->src+start_position,lexer_data->where_in_src-start_position);
case KW_STRING:
case KW_WIDE_STRING:
- return get_string_token(finishing_node->keyword,token_location,lexer_data->src->src+start_position+1,lexer_data->where_in_src-start_position-2);
+ return get_string_token(finishing_node->keyword,token_location,lexer_data->previous_token_location,lexer_data->src->src+start_position+1,lexer_data->where_in_src-start_position-2);
case PKW_FILE_MACRO:
- return get_file_macro_token(token_location);
+ return get_file_macro_token(token_location,lexer_data->previous_token_location);
case PKW_DATE_MACRO:
- return get_date_macro_token(token_location);
+ return get_date_macro_token(token_location,lexer_data->previous_token_location);
case PKW_LINE_MACRO:
- return get_line_macro_token(token_location);
+ return get_line_macro_token(token_location,lexer_data->previous_token_location);
case PKW_STDC_MACRO:
- return get_stdc_macro_token(token_location);
+ return get_stdc_macro_token(token_location,lexer_data->previous_token_location);
case PKW_STDC_HOSTED_MACRO:
- return get_stdc_hosted_macro_token(token_location);
+ return get_stdc_hosted_macro_token(token_location,lexer_data->previous_token_location);
case PKW_STDC_VERSION_MACRO:
- return get_stdc_version_macro_token(token_location);
+ return get_stdc_version_macro_token(token_location,lexer_data->previous_token_location);
case PKW_TIME_MACRO:
- return get_time_macro_token(token_location);
+ return get_time_macro_token(token_location,lexer_data->previous_token_location);
case PKW_IF:
case PKW_IFDEF:
case PKW_IFNDEF:
id=get_identifier(lexer_data->src->src+start_position,lexer_data->where_in_src-start_position);
finishing_node->data=id;
}
- return get_id_token(finishing_node->data,token_location);
+ return get_id_token(finishing_node->data,token_location,lexer_data->previous_token_location);
break;
case PKW_DEFINED:
if(lexer_data->automata_view==AUTOMATA_VIEW_PREPROCESSING_DIRECTIVE)
id=get_identifier(lexer_data->src->src+start_position,lexer_data->where_in_src-start_position);
finishing_node->data=id;
}
- return get_id_token(finishing_node->data,token_location);
+ return get_id_token(finishing_node->data,token_location,lexer_data->previous_token_location);
}
default:
- return get_error_token("Unexpected token",token_location,lexer_data->program);
+ return get_error_token("Unexpected token",token_location,lexer_data->previous_token_location,lexer_data->program);
}
wonky_assert(SHOULD_NOT_REACH_HERE);
F diff --git a/src/frontend/lex/lexer.h b/src/frontend/lex/lexer.h
--- a/src/frontend/lex/lexer.h
+++ b/src/frontend/lex/lexer.h
struct Source_File *src;
struct Program *program;
+ struct Source_Location *previous_token_location;
+
};
F diff --git a/src/frontend/parse/parse_translation_unit.c b/src/frontend/parse/parse_translation_unit.c
--- a/src/frontend/parse/parse_translation_unit.c
+++ b/src/frontend/parse/parse_translation_unit.c
parse_external_definition(translation_data,hold);
if(has_new_errors(translation_data))
{
- chase_next_semicolumn(translation_data);
+ if(translation_data->program->continue_to_parse)
+ chase_next_semicolumn(translation_data);
+ else
+ break;
}
}else
{
F diff --git a/src/semantics/program/program.c b/src/semantics/program/program.c
--- a/src/semantics/program/program.c
+++ b/src/semantics/program/program.c
ret->source_files=wonky_malloc(sizeof(struct Queue));
ret->errors=wonky_malloc(sizeof(struct Queue));
ret->types=wonky_malloc(sizeof(struct Map));
+ ret->continue_to_parse=1;
ret->preprocessing_translation_units=wonky_malloc(sizeof(struct Map));
ret->preprocessing_translation_units_to_be_compiled=wonky_malloc(sizeof(struct Queue));
return program;
}
+ void program_stop_parsing(struct Program *program)
+ {
+ program->continue_to_parse=0;
+ }
_Bool has_new_errors(struct Translation_Data *translation_data)
{
F diff --git a/src/semantics/program/program.h b/src/semantics/program/program.h
--- a/src/semantics/program/program.h
+++ b/src/semantics/program/program.h
struct Queue *source_files;
+ /*errors*/
struct Queue *errors;
size_t number_of_errors_when_last_checked;
+ _Bool continue_to_parse;
/*
the type node structures from
struct Program* parse_program(char **base_source_names);
void entype_program(struct Program *program);
+ void program_stop_parsing(struct Program *program);
_Bool has_new_errors(struct Translation_Data *translation_data);
_Bool has_no_tokens(struct Translation_Data *translation_data);
F diff --git a/src/semantics/program/translation_unit.c b/src/semantics/program/translation_unit.c
--- a/src/semantics/program/translation_unit.c
+++ b/src/semantics/program/translation_unit.c
{
Queue_Push(unit->tokens,token);
}
+ struct token* token_ptr_get_token_under_pointer_in_preprocessing_directive(struct Token_Pointer *token_pointer)
+ {
+
+ }
struct token* token_ptr_get_token_under_pointer(struct Token_Pointer *token_pointer)
{
struct token *hold_token;
{
while( (hold_hold_hold_token=token_ptr_check_next_normal_token(token_pointer))->type==KW_STRING
|| hold_hold_hold_token->type==PKW_FILE_MACRO
- )
+ )
{
hold_hold_token=hold_token;
hold_token=token_ptr_get_token_under_pointer_inner(token_pointer);
if(token_ptr_has_buffered_tokens(token_pointer)) /*A special macro might buffer a token*/
return token_ptr_get_buffered_token(token_pointer);
- hold_token=(struct token*)token_pointer->current_token_node->data;
+ hold_token=(struct token*)token_pointer->context->current_token_node->data;
token_ptr_goto_next_token(token_pointer);
return;
while(1)
{
- if(token_pointer->current_token_node==NULL)
+ if(token_pointer->context->current_token_node==NULL)
return;
- hold_token=(struct token*)token_pointer->current_token_node->data;
+ hold_token=(struct token*)token_pointer->context->current_token_node->data;
if(hold_token==NULL)
return;
token_ptr_execute_pragma_directive(token_pointer,(struct token_pragma_directive*)hold_token);
break;
case PKW_FILE_MACRO:
- token_ptr_execute_file_special_macro(token_pointer);
+ token_ptr_execute_file_special_macro(token_pointer,hold_token);
return;/*NOTICE*/
case PKW_LINE_MACRO:
- token_ptr_execute_line_special_macro(token_pointer);
+ token_ptr_execute_line_special_macro(token_pointer,hold_token);
return;/*NOTICE*/
case PKW_STDC_MACRO:
- token_ptr_execute_stdc_special_macro(token_pointer);
+ token_ptr_execute_stdc_special_macro(token_pointer,hold_token);
return;/*NOTICE*/
case PKW_STDC_HOSTED_MACRO:
- token_ptr_execute_stdc_hosted_special_macro(token_pointer);
+ token_ptr_execute_stdc_hosted_special_macro(token_pointer,hold_token);
return;/*NOTICE*/
case PKW_STDC_VERSION_MACRO:
- token_ptr_execute_stdc_version_special_macro(token_pointer);
+ token_ptr_execute_stdc_version_special_macro(token_pointer,hold_token);
return;/*NOTICE*/
case LT_EOF:
if(token_pointer->call_stack->size>0)
{
- token_pointer->current_token_node=Stack_Pop(token_pointer->call_stack);
+ token_pointer->context=Stack_Pop(token_pointer->call_stack);
}else
{
- token_pointer->current_token_node=NULL;
+ token_pointer->context=NULL;
return;
}
break;
case LT_ERROR:
push_translation_message_into_program_as_error(((struct token_error*)hold_token)->error,token_pointer->program);
- token_pointer->current_token_node=token_pointer->current_token_node->prev;
+ token_pointer->context->current_token_node=token_pointer->context->current_token_node->prev;
break;
default:
return;
if(!token_ptr_has_remaining_tokens(token_pointer))
return get_eof_token();
else
- return (struct token*)token_pointer->current_token_node->data;
+ return (struct token*)token_pointer->context->current_token_node->data;
}
void token_ptr_goto_next_token(struct Token_Pointer *token_pointer)
{
if(token_ptr_has_remaining_tokens(token_pointer) && !token_ptr_has_buffered_tokens(token_pointer))
- token_pointer->current_token_node=token_pointer->current_token_node->prev;
+ token_pointer->context->current_token_node=token_pointer->context->current_token_node->prev;
}
struct Token_Pointer* get_token_ptr(struct Preprocessing_Translation_Unit *unit,struct Program *program)
{
struct Token_Pointer *ret;
+
ret=wonky_malloc(sizeof(struct Token_Pointer));
- ret->current_token_node=unit->tokens->first;
+ ret->context=get_token_ptr_context(unit->tokens->first);
ret->call_stack=wonky_malloc(sizeof(struct Stack));
- ret->ungeted_tokens=wonky_malloc(sizeof(struct Queue));
Stack_Init(ret->call_stack);
- Queue_Init(ret->ungeted_tokens);
- ret->current_location=((struct token*)unit->tokens->first->data)->location;/*todo: make sure translation unit has a token*/
ret->program=program;
return ret;
}
void token_ptr_execute_line_directive(struct Token_Pointer *ptr,struct token_line_directive *line_directive)
{
+ if(line_directive->filename!=NULL)
+ {
+ ptr->context->filename=line_directive->filename;
+ ptr->context->filename_size=line_directive->filename_size;
+ }
+
+ ptr->context->line=line_directive->line-2;
+ ptr->context->column=0;
+
token_ptr_goto_next_token(ptr);
}
void token_ptr_execute_error_directive(struct Token_Pointer *ptr,struct token_error_directive *error_directive)
{
+ struct Translation_Message *hold_error;
+ va_list hack;
+ hold_error=get_translation_message(
+ error_directive->error_message,
+ ptr->program,
+ ptr->context->filename,
+ ptr->context->filename_size,
+ ptr->context->line,
+ ptr->context->column,
+ hack);
+ push_translation_message_into_program_as_error(hold_error,ptr->program);
+ program_stop_parsing(ptr->program);
token_ptr_goto_next_token(ptr);
}
void token_ptr_execute_pragma_directive(struct Token_Pointer *ptr,struct token_pragma_directive *pragma_directive)
{
token_ptr_goto_next_token(ptr);
}
- void token_ptr_execute_file_special_macro(struct Token_Pointer *ptr)
+ void token_ptr_execute_file_special_macro(struct Token_Pointer *ptr,struct token *directive)
{
struct token_string *file;
token_ptr_goto_next_token(ptr);
- file=(struct token_string*)get_string_token(KW_STRING,ptr->current_location,ptr->current_location->src_name->full_name,ptr->current_location->src_name->full_name_size);
- Queue_Push(ptr->ungeted_tokens,file);
+ file=(struct token_string*)get_string_token(
+ KW_STRING,
+ directive->delta->location,
+ directive->delta->location,
+ directive->delta->location->src_name->full_name,
+ directive->delta->location->src_name->full_name_size);
+ Queue_Push(ptr->context->ungeted_tokens,file);
}
- void token_ptr_execute_line_special_macro(struct Token_Pointer *ptr)
+ void token_ptr_execute_line_special_macro(struct Token_Pointer *ptr,struct token *directive)
{
struct token_constant *line;
token_ptr_goto_next_token(ptr);
- line=(struct token_constant*)get_constant_long_long_int_token(ptr->current_location,ptr->current_location->line+1);
- Queue_Push(ptr->ungeted_tokens,line);
+ line=(struct token_constant*)get_constant_long_long_int_token(
+ directive->delta->location,
+ directive->delta->location,
+ ptr->context->line+1);
+ Queue_Push(ptr->context->ungeted_tokens,line);
}
- void token_ptr_execute_stdc_special_macro(struct Token_Pointer *ptr)
+ void token_ptr_execute_stdc_special_macro(struct Token_Pointer *ptr,struct token *directive)
{
struct token_constant *line;
token_ptr_goto_next_token(ptr);
- line=(struct token_constant*)get_constant_token(KW_DECIMAL_CONSTANT,ptr->current_location,"1",1);
- Queue_Push(ptr->ungeted_tokens,line);
+ line=(struct token_constant*)get_constant_token(
+ KW_DECIMAL_CONSTANT,
+ directive->delta->location,
+ directive->delta->location,
+ "1",
+ 1);
+ Queue_Push(ptr->context->ungeted_tokens,line);
}
- void token_ptr_execute_stdc_hosted_special_macro(struct Token_Pointer *ptr)
+ void token_ptr_execute_stdc_hosted_special_macro(struct Token_Pointer *ptr,struct token *directive)
{
struct token_constant *line;
token_ptr_goto_next_token(ptr);
- line=(struct token_constant*)get_constant_token(KW_DECIMAL_CONSTANT,ptr->current_location,"1",1);
- Queue_Push(ptr->ungeted_tokens,line);
+ line=(struct token_constant*)get_constant_token(
+ KW_DECIMAL_CONSTANT,
+ directive->delta->location,
+ directive->delta->location,
+ "1",
+ 1);
+ Queue_Push(ptr->context->ungeted_tokens,line);
}
- void token_ptr_execute_stdc_version_special_macro(struct Token_Pointer *ptr)
+ void token_ptr_execute_stdc_version_special_macro(struct Token_Pointer *ptr,struct token *directive)
{
struct token_constant *line;
token_ptr_goto_next_token(ptr);
- line=(struct token_constant*)get_constant_token(KW_LONG_DECIMAL_CONSTANT,ptr->current_location,"199901",sizeof("199901")-1);
- Queue_Push(ptr->ungeted_tokens,line);
+ line=(struct token_constant*)get_constant_token(
+ KW_LONG_DECIMAL_CONSTANT,
+ directive->delta->location,
+ directive->delta->location,
+ "199901",
+ sizeof("199901")-1);
+ Queue_Push(ptr->context->ungeted_tokens,line);
}
void delete_token_ptr(struct Token_Pointer *ptr)
{
wonky_free(ptr);
}
+ struct Token_Pointer_Context* get_token_ptr_context(struct Queue_Node *start)
+ {
+ struct Token_Pointer_Context *ret;
+ struct Source_Location *hold_location;
+
+ ret=wonky_malloc(sizeof(struct Token_Pointer_Context));
+ ret->current_token_node=start;
+ ret->ungeted_tokens=wonky_malloc(sizeof(struct Queue));
+ hold_location=((struct token*)start->data)->delta->location;
+
+ ret->line=hold_location->line;
+ ret->column=hold_location->column;
+ ret->filename=hold_location->src_name->full_name;
+ ret->filename_size=hold_location->src_name->full_name_size;
+
+ Queue_Init(ret->ungeted_tokens);
+ return ret;
+ }
_Bool token_ptr_has_remaining_tokens(struct Token_Pointer *ptr)
{
if(token_ptr_has_buffered_tokens(ptr))
return 1;
}else
{
- return ptr->current_token_node!=NULL;
+ return ptr->context->current_token_node!=NULL;
}
}
void token_ptr_unget_token(struct Token_Pointer *ptr,struct token *token)
{
- Queue_Push(ptr->ungeted_tokens,token);
+ Queue_Push(ptr->context->ungeted_tokens,token);
}
void token_ptr_assume_location_of_token(struct Token_Pointer *ptr,struct token *token)
{
- ptr->current_location=token->location;
+ ptr->context->line+=token->delta->line_offset;
+ ptr->context->column=token->delta->column;
}
_Bool token_ptr_has_buffered_tokens(struct Token_Pointer *ptr)
{
- return ptr->ungeted_tokens->size!=0;
+ return ptr->context->ungeted_tokens->size!=0;
}
struct token* token_ptr_get_buffered_token(struct Token_Pointer *ptr)
{
if(token_ptr_has_buffered_tokens(ptr))
- return (struct token*)Queue_Pop(ptr->ungeted_tokens);
+ return (struct token*)Queue_Pop(ptr->context->ungeted_tokens);
else
return NULL;
}
struct token* token_ptr_check_buffered_token(struct Token_Pointer *ptr)
{
if(token_ptr_has_buffered_tokens(ptr))
- return (struct token*)ptr->ungeted_tokens->first->data;
+ return (struct token*)ptr->context->ungeted_tokens->first->data;
else
return NULL;
}
+ void token_ptr_jump_to(struct Token_Pointer *ptr,struct Queue_Node *where_to)
+ {
+ struct Token_Pointer_Context *new_context;
+
+ new_context=get_token_ptr_context(where_to);
+ Stack_Push(ptr->call_stack,ptr->context);
+ ptr->context=new_context;
+ }
#endif
F diff --git a/src/semantics/program/translation_unit.h b/src/semantics/program/translation_unit.h
--- a/src/semantics/program/translation_unit.h
+++ b/src/semantics/program/translation_unit.h
{
struct Queue *tokens;
};
- struct Token_Pointer
+ struct Token_Pointer_Context
{
struct Queue_Node *current_token_node;
+ struct Queue *ungeted_tokens;
+ size_t line;
+ size_t column;
+ char *filename;
+ size_t filename_size;
+ };
+ struct Token_Pointer
+ {
struct Stack *call_stack;
- struct Source_Location *current_location;
+ struct Token_Pointer_Context *context;
struct Program *program;
- struct Queue *ungeted_tokens;
};
struct Preprocessing_Translation_Unit* get_preprocessing_translation_unit(struct Source_File *source);
void delete_preprocessing_translation_unit(struct Preprocessing_Translation_Unit *unit);
void push_token_into_preprocessing_translation_unit(struct Preprocessing_Translation_Unit *unit,struct token *token);
+ struct token* token_ptr_get_token_under_pointer_in_preprocessing_directive(struct Token_Pointer *token_pointer);
struct token* token_ptr_get_token_under_pointer(struct Token_Pointer *token_pointer);
struct token* token_ptr_get_token_under_pointer_inner(struct Token_Pointer *token_pointer);
struct token* token_ptr_check_next_normal_token(struct Token_Pointer *token_pointer);
struct Token_Pointer* get_token_ptr(struct Preprocessing_Translation_Unit *unit,struct Program *program);
void delete_token_ptr(struct Token_Pointer *ptr);
+ struct Token_Pointer_Context* get_token_ptr_context(struct Queue_Node *start);
_Bool token_ptr_has_remaining_tokens(struct Token_Pointer *ptr);
void token_ptr_execute_error_directive(struct Token_Pointer *ptr,struct token_error_directive *error_directive);
void token_ptr_execute_pragma_directive(struct Token_Pointer *ptr,struct token_pragma_directive *pragma_directive);
void token_ptr_execute_defined_unary_operator(struct Token_Pointer *ptr,struct token_defined_unary_operator *operator);
- void token_ptr_execute_file_special_macro(struct Token_Pointer *ptr);
- void token_ptr_execute_line_special_macro(struct Token_Pointer *ptr);
- void token_ptr_execute_stdc_special_macro(struct Token_Pointer *ptr);
- void token_ptr_execute_stdc_hosted_special_macro(struct Token_Pointer *ptr);
- void token_ptr_execute_stdc_version_special_macro(struct Token_Pointer *ptr);
+ void token_ptr_execute_file_special_macro(struct Token_Pointer *ptr,struct token *directive);
+ void token_ptr_execute_line_special_macro(struct Token_Pointer *ptr,struct token *directive);
+ void token_ptr_execute_stdc_special_macro(struct Token_Pointer *ptr,struct token *directive);
+ void token_ptr_execute_stdc_hosted_special_macro(struct Token_Pointer *ptr,struct token *directive);
+ void token_ptr_execute_stdc_version_special_macro(struct Token_Pointer *ptr,struct token *directive);
void token_ptr_assume_location_of_token(struct Token_Pointer *ptr,struct token *token);
F diff --git a/src/semantics/value/type.c b/src/semantics/value/type.c
--- a/src/semantics/value/type.c
+++ b/src/semantics/value/type.c
return (type->specifier==TS_CHAR || type->specifier==TS_INT || type->specifier==TS_FLOAT || type->specifier==TS_DOUBLE || type->specifier==TS_POINTER);
}
+ _Bool type_is_a_plain_signed_int(struct Type *type)
+ {
+
+ return type->specifier==TS_INT && ((struct Type_Basic*)type)->constraint==TC_NONE && ((struct Type_Basic*)type)->sign==TSIGN_SIGNED;
+ }
_Bool type_is_of_object(struct Type *type)
{
return !(type->specifier==TS_VOID || type->specifier==TS_FUNC || type->specifier==TS_NONE || type->specifier==TS_ERROR);
{
return (type->specifier==TS_INT || type->specifier==TS_CHAR || type->specifier==TS_DOUBLE || type->specifier==TS_FLOAT || type->specifier==TS_VOID);
}
+ _Bool type_is_character(struct Type *type)
+ {
+ return type->specifier==TS_CHAR;
+ }
_Bool type_is_arithmetic(struct Type *type)
{
return (type->specifier==TS_CHAR || type->specifier==TS_INT || type->specifier==TS_FLOAT || type->specifier==TS_DOUBLE );
{
return (type->specifier==TS_POINTER || type->specifier==TS_ARRAY || type->specifier==TS_FUNC);
}
+ _Bool type_is_a_normal_string(struct Type *type)
+ {
+ return type_is_an_array(type) && type_is_character(((struct Type_Array*)type)->is_array_of);
+ }
_Bool type_is_a_variable_length_array(struct Type *type)
{
return 0;
F diff --git a/src/semantics/value/type.h b/src/semantics/value/type.h
--- a/src/semantics/value/type.h
+++ b/src/semantics/value/type.h
_Bool types_of_bitfields_are_compatible_unqalified(struct Type_Bit_Field *a,struct Type_Bit_Field *b);
_Bool types_of_enum_are_compatible_unqualified(struct Type_Enum *a,struct Type_Enum *b);
+ _Bool type_is_a_plain_signed_int(struct Type *type);
+
_Bool type_is_of_object(struct Type *type);
_Bool type_is_complete(struct Type *type);
_Bool type_is_integer_type(struct Type *type);
_Bool type_is_derivative(struct Type *type);
_Bool type_is_a_variable_length_array(struct Type *type);
_Bool type_is_an_array(struct Type *type);
+ _Bool type_is_a_normal_string(struct Type *type);
/*these return 0 if constant/volatile-ness makes no sense for the type*/
_Bool type_is_constant(struct Type *type);
F diff --git a/src/syntax/source_file.c b/src/syntax/source_file.c
--- a/src/syntax/source_file.c
+++ b/src/syntax/source_file.c
#include <source_file.h>
char *well_known_locations_base[]={"","/usr/include/","/usr/include/x86_64-linux-gnu/",NULL};
+
+ struct Source_Location start_of_file
+ =
+ {
+ .line=0,
+ .column=0,
+ .on_which_byte=0,
+ .src_name=NULL,
+ };
/*TODO this is not giving correct results, but was left as it is because of time constraits*/
struct Source_File* get_source_file_from_string(char *filename,size_t filename_size)
{
return ret;
}
+ struct Source_Location_Delta* get_source_location_delta(struct Source_Location *begining,struct Source_Location *ending)
+ {
+ struct Source_Location_Delta *ret;
+
+ wonky_assert(begining->line <= ending->line);
+ wonky_assert(begining->on_which_byte <= ending->on_which_byte);
+
+ ret=wonky_malloc(sizeof(struct Source_Location_Delta));
+ ret->line_offset=ending->line - begining->line;
+ ret->column=ending->column;
+ ret->location=ending;
+
+ return ret;
+ }
void delete_source_file(struct Source_File *src)
{
wonky_free(src);
F diff --git a/src/syntax/source_file.h b/src/syntax/source_file.h
--- a/src/syntax/source_file.h
+++ b/src/syntax/source_file.h
#include <gcc_error.h>
extern char *well_known_locations_base[];
+ extern struct Source_Location start_of_file;
struct Source_Name
{
char *filename;
size_t on_which_byte;
struct Source_Name *src_name;
};
+ struct Source_Location_Delta
+ {
+ size_t line_offset;
+ size_t column; /*this is a copy from end_location*/
+ struct Source_Location *location;
+ };
struct Source_File
{
enum Source_Text_Type type;
struct Source_Name* get_source_name_from_tokens(struct Token_Pointer *ptr);
struct Source_Location* get_source_location(size_t line,size_t column,size_t on_which_byte,struct Source_Name *src_name);
+
+ struct Source_Location_Delta* get_source_location_delta(struct Source_Location *begining,struct Source_Location *ending);
+
void normalise_source_name(struct Source_Name *name);
void delete_source_file(struct Source_File *src);
void delete_source_name(struct Source_Name *name);
F diff --git a/src/syntax/token/token.c b/src/syntax/token/token.c
--- a/src/syntax/token/token.c
+++ b/src/syntax/token/token.c
*cpy=*src;
return cpy;
}
- struct token* get_id_token(struct identifier *id,struct Source_Location *location)
+ struct token* get_id_token(struct identifier *id,struct Source_Location *current_location,struct Source_Location *previous_location)
{
struct token_identifier *ret;
ret=wonky_malloc(sizeof(struct token_identifier));
ret->type=KW_ID;
- ret->location=location;
+ ret->delta=get_source_location_delta(previous_location,current_location);
ret->id=id;
return (struct token*)ret;
}
- struct token* get_keyword_token(enum LEXER_TYPE type,struct Source_Location *location)
+ struct token* get_keyword_token(enum LEXER_TYPE type,struct Source_Location *current_location,struct Source_Location *previous_location)
{
struct token_keyword *ret;
ret=wonky_malloc(sizeof(struct token_keyword));
ret->type=type;
- ret->location=location;
+ ret->delta=get_source_location_delta(previous_location,current_location);
return (struct token*)ret;
}
- struct token* get_punctuator_token(enum LEXER_TYPE type,struct Source_Location *location)
+ struct token* get_punctuator_token(enum LEXER_TYPE type,struct Source_Location *current_location,struct Source_Location *previous_location)
{
struct token_punctuator *ret;
ret=wonky_malloc(sizeof(struct token_punctuator));
ret->type=type;
- ret->location=location;
+ ret->delta=get_source_location_delta(previous_location,current_location);
ret->punctuator_type=PUNCTUATOR_NORMAL;/*TODO*/
return (struct token*)ret;
}
- struct token* get_constant_token(enum LEXER_TYPE bare_type,struct Source_Location *location,char *data,size_t size)
+ struct token* get_constant_token(enum LEXER_TYPE bare_type,struct Source_Location *current_location,struct Source_Location *previous_location,char *data,size_t size)
{
struct token_constant *ret;
ret=wonky_malloc(sizeof(struct token_constant));
- ret->location=location;
+ ret->delta=get_source_location_delta(previous_location,current_location);
ret->type=KW_CONSTANT;
switch(bare_type)
return (struct token*)ret;
}
- struct token* get_constant_long_long_int_token(struct Source_Location *location,long long int number)
+ struct token* get_constant_long_long_int_token(struct Source_Location *current_location,struct Source_Location *previous_location,long long int number)
{
struct token_constant *ret;
ret=wonky_malloc(sizeof(struct token_constant));
- ret->location=location;
+ ret->delta=get_source_location_delta(previous_location,current_location);
ret->type=KW_CONSTANT;
ret->constant=get_long_long_int_constant(number);
return (struct token*)ret;
}
- struct token* get_string_token(enum LEXER_TYPE bare_type,struct Source_Location *location,char *data,size_t size)
+ struct token* get_string_token(enum LEXER_TYPE bare_type,struct Source_Location *current_location,struct Source_Location *previous_location,char *data,size_t size)
{
struct token_string *ret;
ret=wonky_malloc(sizeof(struct token_string));
ret->type=bare_type;
- ret->location=location;
+ ret->delta=get_source_location_delta(previous_location,current_location);
if(bare_type==KW_STRING)
{
return (struct token*)ret;
}
- struct token* get_include_directive_token(struct Source_Location *location,struct Queue *tokens)
+ struct token* get_include_directive_token(struct Source_Location *current_location,struct Source_Location *previous_location,struct Queue *tokens)
{
struct token_include_directive *ret;
ret=wonky_malloc(sizeof(struct token_string));
- ret->location=location;
+ ret->delta=get_source_location_delta(previous_location,current_location);
ret->tokens=tokens;
return (struct token*)ret;
}
- struct token* get_if_directive_token(struct Source_Location *location,struct Queue *controlling_tokens,struct Queue_Node *if_true,struct Queue_Node *if_false,struct Queue_Node *end_of_if_directive);
-
- struct token* get_ifdef_directive_token(struct Source_Location *location,struct identifier *id,struct Queue_Node *if_true,struct Queue_Node *if_false,struct Queue_Node *end_of_if_directive);
-
- struct token* get_ifdef_directive_token(struct Source_Location *location,struct identifier *id,struct Queue_Node *if_true,struct Queue_Node *if_false,struct Queue_Node *end_of_if_directive);
-
- struct token* get_normal_define_directive_token(struct Source_Location *location,struct identifier *id,struct Queue *replacement_tokens);
-
- struct token* get_functionlike_define_directive_token(struct Source_Location *location,struct identifier *id,struct Queue *argument_id_list_tokens,struct Queue *replacement_tokens);
-
- struct token* get_undef_directive_token(struct Source_Location *location,struct identifier *id);
- struct token* get_line_directive_token(struct Source_Location *location,struct Source_Location *new_location);
- struct token* get_error_directive_token(struct Source_Location *location,struct token_string *error_message);
- struct token* get_pragma_directive(struct Source_Location *location,enum Pragma_Type type);
- struct token* get_defined_unary_operator(struct Source_Location *location,struct identifier *id);
-
- struct token* get_error_token(const char *msg,struct Source_Location *location,struct Program *program,...)
+ struct token* get_error_token(const char *msg,struct Source_Location *current_location,struct Source_Location *previous_location,struct Program *program,...)
{
struct token_error *ret;
va_list args;
ret=wonky_malloc(sizeof(struct token_error));
ret->type=LT_ERROR;
- ret->location=location;
- ret->error=get_translation_message(msg,program,location,args);
+ ret->delta=get_source_location_delta(previous_location,current_location);
+ ret->error=get_translation_message(
+ msg,
+ program,
+ current_location->src_name->full_name,
+ current_location->src_name->full_name_size,
+ current_location->line,
+ current_location->column,
+ args);
return (struct token*)ret;
}
struct token *ret;
ret=wonky_malloc(sizeof(struct token));
ret->type=LT_EOF;
- ret->location=NULL;
+ ret->delta=NULL;
return ret;
}
struct token_string *ret;
ret=wonky_malloc(sizeof(struct token_string));
ret->type=KW_STRING;
- ret->location=first->location;
+ ret->delta=first->delta;
ret->constant=concatenate_string_literals(first->constant,second->constant);
return (struct token*)ret;
}
- struct token* get_file_macro_token(struct Source_Location *token_location)
+ struct token* get_file_macro_token(struct Source_Location *current_location,struct Source_Location *previous_location)
{
struct token *ret;
ret=wonky_malloc(sizeof(struct token));
ret->type=PKW_FILE_MACRO;
- ret->location=token_location;
+ ret->delta=get_source_location_delta(previous_location,current_location);
return ret;
}
1900 + timeptr->tm_year);
return result;
}
- struct token* get_date_macro_token(struct Source_Location *token_location)
+ struct token* get_date_macro_token(struct Source_Location *current_location,struct Source_Location *previous_location)
{
struct tm *tm;
time_t t;
ret=ascdate(tm);
size=gstrnlen(ret,27);
- return (struct token*)get_string_token(KW_STRING,token_location,ret,size);
+ return (struct token*)get_string_token(KW_STRING,current_location,previous_location,ret,size);
error:
- return (struct token*)get_string_token(KW_STRING,token_location,"Time could not be determined",sizeof("Time could not be determined"));
+ return (struct token*)get_string_token(
+ KW_STRING,
+ current_location,
+ current_location,
+ "Time could not be determined",
+ sizeof("Time could not be determined"));
}
- struct token* get_line_macro_token(struct Source_Location *token_location)
+ struct token* get_line_macro_token(struct Source_Location *current_location,struct Source_Location *previous_location)
{
struct token *ret;
ret=wonky_malloc(sizeof(struct token));
ret->type=PKW_LINE_MACRO;
- ret->location=token_location;
+ ret->delta=get_source_location_delta(previous_location,current_location);;
return ret;
}
- struct token* get_stdc_macro_token(struct Source_Location *token_location)
+ struct token* get_stdc_macro_token(struct Source_Location *current_location,struct Source_Location *previous_location)
{
struct token *ret;
ret=wonky_malloc(sizeof(struct token));
ret->type=PKW_STDC_MACRO;
- ret->location=token_location;
+ ret->delta=get_source_location_delta(previous_location,current_location);;
return ret;
}
- struct token* get_stdc_hosted_macro_token(struct Source_Location *token_location)
+ struct token* get_stdc_hosted_macro_token(struct Source_Location *current_location,struct Source_Location *previous_location)
{
struct token *ret;
ret=wonky_malloc(sizeof(struct token));
ret->type=PKW_STDC_HOSTED_MACRO;
- ret->location=token_location;
+ ret->delta=get_source_location_delta(previous_location,current_location);;
return ret;
}
- struct token* get_stdc_version_macro_token(struct Source_Location *token_location)
+ struct token* get_stdc_version_macro_token(struct Source_Location *current_location,struct Source_Location *previous_location)
{
struct token *ret;
ret=wonky_malloc(sizeof(struct token));
ret->type=PKW_STDC_VERSION_MACRO;
- ret->location=token_location;
+ ret->delta=get_source_location_delta(previous_location,current_location);;
return ret;
}
);
return result;
}
- struct token* get_time_macro_token(struct Source_Location *token_location)
+ struct token* get_time_macro_token(struct Source_Location *current_location,struct Source_Location *previous_location)
{
struct tm *tm;
time_t t;
ret=asctime_for_macro(tm);
size=gstrnlen(ret,27);
- return (struct token*)get_string_token(KW_STRING,token_location,ret,size);
+ return (struct token*)get_string_token(
+ KW_STRING,
+ current_location,
+ previous_location,
+ ret,size);
error:
- return (struct token*)get_string_token(KW_STRING,token_location,"Time could not be determined",sizeof("Time could not be determined"));
+ return (struct token*)get_string_token(KW_STRING,current_location,current_location,"Time could not be determined",sizeof("Time could not be determined"));
}
#endif
F diff --git a/src/syntax/token/token.h b/src/syntax/token/token.h
--- a/src/syntax/token/token.h
+++ b/src/syntax/token/token.h
struct token
{
enum LEXER_TYPE type;
- struct Source_Location *location;
+ struct Source_Location_Delta *delta;
};
struct token_identifier
{
enum LEXER_TYPE type;
- struct Source_Location *location;
+ struct Source_Location_Delta *delta;
struct identifier *id;
};
struct token_keyword
{
enum LEXER_TYPE type;
- struct Source_Location *location;
+ struct Source_Location_Delta *delta;
};
struct token_punctuator
{
enum LEXER_TYPE type;
- struct Source_Location *location;
+ struct Source_Location_Delta *delta;
enum Punctuator_Token_Type punctuator_type;
};
struct token_constant
{
enum LEXER_TYPE type;
- struct Source_Location *location;
+ struct Source_Location_Delta *delta;
struct Constant *constant;
};
struct token_string
{
enum LEXER_TYPE type;
- struct Source_Location *location;
+ struct Source_Location_Delta *delta;
struct Constant *constant;
};
struct token_include_directive
{
enum LEXER_TYPE type;
- struct Source_Location *location;
+ struct Source_Location_Delta *delta;
struct Queue *tokens;
};
struct token_if_directive
{
enum LEXER_TYPE type;
- struct Source_Location *location;
+ struct Source_Location_Delta *delta;
struct Queue *controlling_expression;
struct Queue_Node *if_true;
struct Queue_Node *if_false;
struct token_ifdef_directive
{
enum LEXER_TYPE type;
- struct Source_Location *location;
+ struct Source_Location_Delta *delta;
struct identifier *id;
struct Queue_Node *if_defined;
struct Queue_Node *if_undefined;
struct token_ifndef_directive
{
enum LEXER_TYPE type;
- struct Source_Location *location;
+ struct Source_Location_Delta *delta;
struct identifier *id;
struct Queue_Node *if_undefined;
struct Queue_Node *if_defined;
struct token_normal_define_directive
{
enum LEXER_TYPE type;
- struct Source_Location *location;
+ struct Source_Location_Delta *delta;
struct normal_define_directive *define;
};
struct token_functionlike_define_directive
{
enum LEXER_TYPE type;
- struct Source_Location *location;
+ struct Source_Location_Delta *delta;
struct functionlike_define_directive_argument *define;
};
struct token_undef_directive
{
enum LEXER_TYPE type;
- struct Source_Location *location;
+ struct Source_Location_Delta *delta;
struct identifier *id;
};
struct token_line_directive
{
enum LEXER_TYPE type;
- struct Source_Location *directive_location;
- struct Source_Location *real_location;
- struct Source_Location *new_location;
+ struct Source_Location_Delta *directive_delta;
+
+ size_t line;
+ char *filename;
+ size_t filename_size;
};
struct token_error_directive
{
enum LEXER_TYPE type;
- struct Source_Location *location;
- struct token_string *error_message;
+ struct Source_Location_Delta *delta;
+ char *error_message;
};
struct token_pragma_directive
{
enum LEXER_TYPE type;
- struct Source_Location *location;
+ struct Source_Location_Delta *delta;
enum Pragma_Type pragma_type;
};
struct token_defined_unary_operator
{
enum LEXER_TYPE type;
- struct Source_Location *location;
+ struct Source_Location_Delta *delta;
struct identifier *id;
};
struct token_hashtag_unary_operator
{
enum LEXER_TYPE type;
- struct Source_Location *location;
+ struct Source_Location_Delta *delta;
struct token_functionlike_define_directive *operand;
};
struct token_hashtag_hastag_unary_operator
{
enum LEXER_TYPE type;
- struct Source_Location *location;
+ struct Source_Location_Delta *delta;
struct Queue *operands;
};
struct token_error
{
enum LEXER_TYPE type;
- struct Source_Location *location;
+ struct Source_Location_Delta *delta;
struct Translation_Message *error;
};
void handle_splicing(struct token *word);
char compare_tokens(struct token *a,struct token *b);
- struct token* get_id_token(struct identifier *id,struct Source_Location *location);
- struct token* get_keyword_token(enum LEXER_TYPE type,struct Source_Location *location);
- struct token* get_punctuator_token(enum LEXER_TYPE type,struct Source_Location *location);
- struct token* get_constant_token(enum LEXER_TYPE bare_type,struct Source_Location *location,char *data,size_t size);
- struct token* get_constant_long_long_int_token(struct Source_Location *location,long long int number);
- struct token* get_string_token(enum LEXER_TYPE bare_type,struct Source_Location *location,char *data,size_t size);
- struct token* get_include_directive_token(struct Source_Location *location,struct Queue *tokens);
- struct token* get_if_directive_token(struct Source_Location *location,struct Queue *controlling_tokens,struct Queue_Node *if_true,struct Queue_Node *if_false,struct Queue_Node *end_of_if_directive);
+ struct token* get_id_token(struct identifier *id,struct Source_Location *current_location,struct Source_Location *previous_location);
+ struct token* get_keyword_token(enum LEXER_TYPE type,struct Source_Location *current_location,struct Source_Location *previous_location);
+ struct token* get_punctuator_token(enum LEXER_TYPE type,struct Source_Location *current_location,struct Source_Location *previous_location);
+ struct token* get_constant_token(enum LEXER_TYPE bare_type,struct Source_Location *current_location,struct Source_Location *previous_location,char *data,size_t size);
+ struct token* get_constant_long_long_int_token(struct Source_Location *current_location,struct Source_Location *previous_location,long long int number);
+ struct token* get_string_token(enum LEXER_TYPE bare_type,struct Source_Location *current_location,struct Source_Location *previous_location,char *data,size_t size);
+ struct token* get_include_directive_token(struct Source_Location *current_location,struct Source_Location *previous_location,struct Queue *tokens);
+ struct token* get_if_directive_token(struct Source_Location *current_location,struct Source_Location *previous_location,struct Queue *controlling_tokens,struct Queue_Node *if_true,struct Queue_Node *if_false,struct Queue_Node *end_of_if_directive);
- struct token* get_ifdef_directive_token(struct Source_Location *location,struct identifier *id,struct Queue_Node *if_true,struct Queue_Node *if_false,struct Queue_Node *end_of_if_directive);
+ struct token* get_ifdef_directive_token(struct Source_Location *current_location,struct Source_Location *previous_location,struct identifier *id,struct Queue_Node *if_true,struct Queue_Node *if_false,struct Queue_Node *end_of_if_directive);
- struct token* get_ifdef_directive_token(struct Source_Location *location,struct identifier *id,struct Queue_Node *if_true,struct Queue_Node *if_false,struct Queue_Node *end_of_if_directive);
+ struct token* get_ifdef_directive_token(struct Source_Location *current_location,struct Source_Location *previous_location,struct identifier *id,struct Queue_Node *if_true,struct Queue_Node *if_false,struct Queue_Node *end_of_if_directive);
- struct token* get_normal_define_directive_token(struct Source_Location *location,struct identifier *id,struct Queue *replacement_tokens);
+ struct token* get_normal_define_directive_token(struct Source_Location *current_location,struct Source_Location *previous_location,struct identifier *id,struct Queue *replacement_tokens);
- struct token* get_functionlike_define_directive_token(struct Source_Location *location,struct identifier *id,struct Queue *argument_id_list_tokens,struct Queue *replacement_tokens);
+ struct token* get_functionlike_define_directive_token(struct Source_Location *current_location,struct Source_Location *previous_location,struct identifier *id,struct Queue *argument_id_list_tokens,struct Queue *replacement_tokens);
- struct token* get_undef_directive_token(struct Source_Location *location,struct identifier *id);
- struct token* get_line_directive_token(struct Source_Location *location,struct Source_Location *new_location);
- struct token* get_error_directive_token(struct Source_Location *location,struct token_string *error_message);
- struct token* get_pragma_directive(struct Source_Location *location,enum Pragma_Type type);
- struct token* get_defined_unary_operator(struct Source_Location *location,struct identifier *id);
- struct token* get_hashtag_unary_operator(struct Source_Location *location,struct token_functionlike_define_directive *operand);
- struct token* get_hashtag_hashtag_unary_operator(struct Source_Location *location,struct Queue *operands);
- struct token* get_error_token(const char *msg,struct Source_Location *location,struct Program *program,...);
+ struct token* get_undef_directive_token(struct Source_Location *current_location,struct Source_Location *previous_location,struct identifier *id);
+ struct token* get_line_directive_token(struct Source_Location *current_location,struct Source_Location *new_location,struct Source_Location *previous_location);
+ struct token* get_error_directive_token(struct Source_Location *current_location,struct Source_Location *previous_location,struct token_string *error_message);
+ struct token* get_pragma_directive(struct Source_Location *current_location,struct Source_Location *previous_location,enum Pragma_Type type);
+ struct token* get_defined_unary_operator(struct Source_Location *current_location,struct Source_Location *previous_location,struct identifier *id);
+ struct token* get_hashtag_unary_operator(struct Source_Location *current_location,struct Source_Location *previous_location,struct token_functionlike_define_directive *operand);
+ struct token* get_hashtag_hashtag_unary_operator(struct Source_Location *current_location,struct Source_Location *previous_location,struct Queue *operands);
+ struct token* get_error_token(const char *msg,struct Source_Location *current_location,struct Source_Location *previous_location,struct Program *program,...);
struct token* get_eof_token();
struct token* get_token_from_two_adjacent_strings(struct token_string *first,struct token_string *second);
- struct token* get_file_macro_token(struct Source_Location *token_location);
- struct token* get_date_macro_token(struct Source_Location *token_location);
- struct token* get_line_macro_token(struct Source_Location *token_location);
- struct token* get_stdc_macro_token(struct Source_Location *token_location);
- struct token* get_stdc_hosted_macro_token(struct Source_Location *token_location);
- struct token* get_stdc_version_macro_token(struct Source_Location *token_location);
- struct token* get_time_macro_token(struct Source_Location *token_location);
+ struct token* get_file_macro_token(struct Source_Location *current_location,struct Source_Location *previous_location);
+ struct token* get_date_macro_token(struct Source_Location *current_location,struct Source_Location *previous_location);
+ struct token* get_line_macro_token(struct Source_Location *current_location,struct Source_Location *previous_location);
+ struct token* get_stdc_macro_token(struct Source_Location *current_location,struct Source_Location *previous_location);
+ struct token* get_stdc_hosted_macro_token(struct Source_Location *current_location,struct Source_Location *previous_location);
+ struct token* get_stdc_version_macro_token(struct Source_Location *current_location,struct Source_Location *previous_location);
+ struct token* get_time_macro_token(struct Source_Location *current_location,struct Source_Location *previous_location);
#endif