F diff --git a/src/backend/targets/C/ast_to_c.c b/src/backend/targets/C/ast_to_c.c --- a/src/backend/targets/C/ast_to_c.c +++ b/src/backend/targets/C/ast_to_c.cif(vector->number_of_transitions>0){- fprintf(out,"\n\t%smachine_states_lock=1;\n",context_arrow);+ fprintf(out,"\n\t%smachine_states_lock=1;\n\n",context_arrow);+ ast_statement_to_c(out,1,vector->state->on_exit_statement,options);+ fprintf(out,"\n");fprintf(out,"\tswitch(event)\n\t{\n");for(i=0;i<vector->number_of_transitions;++i){//ast_pipeline_to_c(out,3,vector->transitions[i]->pipeline);ast_statement_to_c(out,indentation,vector->transitions[i]->statement,options);+ ast_statement_to_c(out,indentation,vector->transitions[i]->to->on_entry_statement,options);ast_to_c_print_tabs(out,indentation);fprintf(out,"%smachine_states[",context_arrow);ast_token_to_c(out,machine->id);F diff --git a/src/backend/targets/print/print.c b/src/backend/targets/print/print.c --- a/src/backend/targets/print/print.c +++ b/src/backend/targets/print/print.ccase KW_GRANTED:printf("KW_GRANTED");break;+ case KW_ENTERING:+ printf("KW_ENTERING");+ break;+ case KW_EXITING:+ printf("KW_EXITING");+ break;default:printf("LEXERROR");}F diff --git a/src/frontend/lexer.c b/src/frontend/lexer.c --- a/src/frontend/lexer.c +++ b/src/frontend/lexer.creturn get_token(src->src+src->where_in_src-sizeof("else")+1,sizeof("else")-1,KW_ELSE,src->current_row,src->current_column);if(check_and_move_if_on_word("granted",sizeof("granted")-1,src,1))return get_token(src->src+src->where_in_src-sizeof("granted")+1,sizeof("granted")-1,KW_GRANTED,src->current_row,src->current_column);+ if(check_and_move_if_on_word("entering",sizeof("entering")-1,src,1))+ return get_token(src->src+src->where_in_src-sizeof("entering")+1,sizeof("entering")-1,KW_ENTERING,src->current_row,src->current_column);+ if(check_and_move_if_on_word("exiting",sizeof("exiting")-1,src,1))+ return get_token(src->src+src->where_in_src-sizeof("exiting")+1,sizeof("exiting")-1,KW_EXITING,src->current_row,src->current_column);F diff --git a/src/frontend/lexer.h b/src/frontend/lexer.h --- a/src/frontend/lexer.h +++ b/src/frontend/lexer.hKW_IF,KW_ELSE,KW_GRANTED,+ KW_ENTERING,+ KW_EXITING,};struct token{F diff --git a/src/frontend/parser.c b/src/frontend/parser.c --- a/src/frontend/parser.c +++ b/src/frontend/parser.c}}/*- * state : id+ * state : id [ '[' ( 'on' 'entering' statement | 'on 'exiting' statement )* ']' ]**/struct AST_State* parse_state(struct Translation_Data *translation_data){+ struct token *hold_id;+ struct AST *hold_entry=NULL;+ struct AST *hold_exit=NULL;+ int i;+if(get_kw(translation_data)==KW_ID)- return get_ast_state(Queue_Pop(translation_data->tokens));- else+ {+ hold_id=Queue_Pop(translation_data->tokens);++ if(get_and_check(translation_data,KW_OPEN_SQUARE))+ {+ for(i=0;i<2;++i)+ if(get_and_check(translation_data,KW_ON))+ {+ if(get_and_check(translation_data,KW_ENTERING))+ hold_entry=parse_statement(translation_data);+ else if(get_and_check(translation_data,KW_EXITING))+ hold_exit=parse_statement(translation_data);+ else+ break;+ }+ if(get_and_check(translation_data,KW_CLOSE_SQUARE))+ {+ }else+ {+ if(hold_entry)+ delete_ast(hold_entry);+ if(hold_exit)+ delete_ast(hold_exit);+ delete_token(hold_id);+ push_parsing_error("missing closing ']' in state definition",translation_data);+ return NULL;+ }++ }+ return get_ast_state(hold_id,hold_entry,hold_exit);+ }else+ {return NULL;+ }}/** events-inner: id (, id)*{hold_granted=parse_transition_granted(translation_data,states,events);- if(!get_and_check(translation_data,KW_SEMI_COLUMN) && (hold_statement=parse_statement(translation_data,states,events))==NULL)+ if(!get_and_check(translation_data,KW_SEMI_COLUMN) && (hold_statement=parse_statement(translation_data))==NULL){ push_parsing_error("in statement of transition",translation_data); return NULL; }/*GOAL!!!!!*//** statement : 'execute' pipeline ; | 'if' expression statement [ else statement ]*/- struct AST* parse_statement(struct Translation_Data *translation_data,struct AST_States *states,struct AST_Events *events)+ struct AST* parse_statement(struct Translation_Data *translation_data){struct AST *hold_expression;struct AST *hold_body;}else if(get_and_check(translation_data,KW_IF)){hold_expression=parse_expression(translation_data);- hold_body=parse_statement(translation_data,states,events);+ hold_body=parse_statement(translation_data);if(hold_body){if(get_and_check(translation_data,KW_ELSE)){- hold_else=parse_statement(translation_data,states,events);+ hold_else=parse_statement(translation_data);if(hold_else==NULL){push_parsing_error("expected a statement after else",translation_data);}else { push_parsing_error("expected an identifier for starting state",translation_data); return NULL; }}else { push_parsing_error("expected 'on'",translation_data); return NULL; }}- struct AST_State* get_ast_state(struct token *id)+ struct AST_State* get_ast_state(struct token *id,struct AST *entry,struct AST *exit){struct AST_State *ret;+ assert(entry==NULL || entry->type==AST_TYPE_COMMAND || entry->type==AST_TYPE_PIPELINE || entry->type==AST_TYPE_IF);+ assert(exit==NULL || exit->type==AST_TYPE_COMMAND || exit->type==AST_TYPE_PIPELINE || exit->type==AST_TYPE_IF);ret=malloc(sizeof(struct AST_State));ret->type=AST_TYPE_STATE;ret->name=id;+ ret->on_entry_statement=entry;+ ret->on_exit_statement=exit;/*number is assigned in get_ast_states*//*parent machine is determined in anotation stage*/F diff --git a/src/frontend/parser.h b/src/frontend/parser.h --- a/src/frontend/parser.h +++ b/src/frontend/parser.hstruct token *name;struct AST_Machine *parent;size_t number;+ struct AST *on_entry_statement;+ struct AST *on_exit_statement;};struct AST_Event{struct AST* parse_transition_granted(struct Translation_Data *translation_data,struct AST_States *states,struct AST_Events *events);- struct AST* parse_statement(struct Translation_Data *translation_data,struct AST_States *states,struct AST_Events *events);+ struct AST* parse_statement(struct Translation_Data *translation_data);struct AST_Pipeline* parse_pipeline(struct Translation_Data *translation_data);struct AST_Command* parse_command(struct Translation_Data *translation_data);struct AST* parse_not_expression(struct Translation_Data *translation_data);struct AST* parse_primary_expression(struct Translation_Data *translation_data);- struct AST_State* get_ast_state(struct token *id);+ struct AST_State* get_ast_state(struct token *id,struct AST *entry,struct AST *exit);struct AST_Event* get_ast_event(struct token *id);struct AST_States* get_ast_states(struct Queue *states,struct Translation_Data *translation_data);struct AST_Events* get_ast_events(struct Queue *events);