diff --git a/src/lib/eolian/eo_lexer.c b/src/lib/eolian/eo_lexer.c index 6b2747a130..aad79d8f71 100644 --- a/src/lib/eolian/eo_lexer.c +++ b/src/lib/eolian/eo_lexer.c @@ -45,6 +45,7 @@ next_char(Eo_Lexer *ls) #define KW(x) #x #define KWAT(x) "@" #x +#define KWH(x) "#" #x static const char * const tokens[] = { @@ -87,6 +88,7 @@ static const char * const ctypes[] = #undef KW #undef KWAT +#undef KWH #define is_newline(c) ((c) == '\n' || (c) == '\r') @@ -989,10 +991,10 @@ lex(Eo_Lexer *ls, Eo_Token *tok) return TOK_NUMBER; } if (ls->current && (isalnum(ls->current) - || ls->current == '@' || ls->current == '_')) + || ls->current == '@' || ls->current == '#' || ls->current == '_')) { int col = ls->column; - Eina_Bool at_kw = (ls->current == '@'); + Eina_Bool pfx_kw = (ls->current == '@') || (ls->current == '#'); const char *str; eina_strbuf_reset(ls->buff); do @@ -1007,7 +1009,7 @@ lex(Eo_Lexer *ls, Eo_Token *tok) str); ls->column = col + 1; tok->value.s = eina_stringshare_add(str); - if (at_kw && tok->kw == 0) + if (pfx_kw && tok->kw == 0) eo_lexer_syntax_error(ls, "invalid keyword"); return TOK_VALUE; } diff --git a/src/lib/eolian/eo_lexer.h b/src/lib/eolian/eo_lexer.h index e9b5e7b0e0..5bc7064151 100644 --- a/src/lib/eolian/eo_lexer.h +++ b/src/lib/eolian/eo_lexer.h @@ -39,6 +39,8 @@ enum Tokens KWAT(private), KWAT(property), KWAT(protected), KWAT(restart), \ KWAT(pure_virtual), \ \ + KWH(version), \ + \ KW(byte), KW(ubyte), KW(char), KW(short), KW(ushort), KW(int), KW(uint), \ KW(long), KW(ulong), KW(llong), KW(ullong), \ \ @@ -71,6 +73,7 @@ enum Tokens /* "regular" keyword and @ prefixed keyword */ #define KW(x) KW_##x #define KWAT(x) KW_at_##x +#define KWH(x) KW_hash_##x enum Keywords { @@ -80,6 +83,7 @@ enum Keywords #undef KW #undef KWAT +#undef KWH enum Numbers { diff --git a/src/lib/eolian/eo_parser.c b/src/lib/eolian/eo_parser.c index 524b31a383..74c76d3a7d 100644 --- a/src/lib/eolian/eo_parser.c +++ b/src/lib/eolian/eo_parser.c @@ -1,4 +1,5 @@ #include +#include #ifdef HAVE_CONFIG_H # include "config.h" @@ -2278,10 +2279,37 @@ found_class: static void parse_chunk(Eo_Lexer *ls, Eina_Bool eot) { + Eina_Bool parsing_header = EINA_TRUE; + Eina_Bool has_version = EINA_FALSE; while (ls->t.token >= 0) - /* set eot to EINA_TRUE so that we only allow parsing of one class */ - if (parse_unit(ls, eot)) - eot = EINA_TRUE; + switch (ls->t.kw) + { + case KW_hash_version: + { + CASE_LOCK(ls, version, "#version specifier"); + if (!parsing_header) + eo_lexer_syntax_error(ls, "header keyword outside of unit header"); + eo_lexer_get(ls); + + check(ls, TOK_NUMBER); + if (ls->t.kw != NUM_INT) + eo_lexer_syntax_error(ls, "invalid #version value"); + if (ls->t.value.u > USHRT_MAX) + eo_lexer_syntax_error(ls, "#version too high"); + else if (ls->t.value.u < 0) + eo_lexer_syntax_error(ls, "#version too low"); + + ls->unit->version = (unsigned short)(ls->t.value.u); + eo_lexer_get(ls); + break; + } + default: + parsing_header = EINA_FALSE; + /* set eot to EINA_TRUE so that we only allow parsing of one class */ + if (parse_unit(ls, eot)) + eot = EINA_TRUE; + break; + } } Eolian_Unit * diff --git a/src/lib/eolian/eolian_database.c b/src/lib/eolian/eolian_database.c index 93e833e9a5..0fb5a134f6 100644 --- a/src/lib/eolian/eolian_database.c +++ b/src/lib/eolian/eolian_database.c @@ -572,6 +572,9 @@ database_unit_init(Eolian_State *state, Eolian_Unit *unit, const char *file) unit->structs = eina_hash_stringshared_new(EINA_FREE_CB(database_typedecl_del)); unit->enums = eina_hash_stringshared_new(EINA_FREE_CB(database_typedecl_del)); unit->objects = eina_hash_stringshared_new(NULL); + + /* baseline version; support for higher featurelevel must be specified explicitly */ + unit->version = 1; } static void diff --git a/src/lib/eolian/eolian_database.h b/src/lib/eolian/eolian_database.h index f74d0fa31a..0dce769370 100644 --- a/src/lib/eolian/eolian_database.h +++ b/src/lib/eolian/eolian_database.h @@ -45,6 +45,7 @@ struct _Eolian_Unit Eina_Hash *structs; Eina_Hash *enums; Eina_Hash *objects; + unsigned short version; }; typedef struct _Eolian_State_Area