eolian: var parsing (global and constant)

This makes the API effectively functional. Also, I added new API
eolian_variable_is_extern to match structs and typedefs.
This commit is contained in:
Daniel Kolesa 2014-08-08 15:57:39 +01:00
parent cc1988fddd
commit 65332eb3ca
8 changed files with 128 additions and 26 deletions

View File

@ -1255,6 +1255,16 @@ EAPI Eina_Stringshare *eolian_variable_full_name_get(const Eolian_Variable *var)
*/
EAPI Eina_Iterator *eolian_variable_namespaces_get(const Eolian_Variable *var);
/*
* @brief Check if a variable is extern.
*
* @param[in] var the variable.
* @return EINA_TRUE if it's extern, EINA_FALSE otherwise.
*
* @ingroup Eolian
*/
EAPI Eina_Bool eolian_variable_is_extern(const Eolian_Variable *var);
#endif
#ifdef __cplusplus

View File

@ -18,7 +18,7 @@ database_var_del(Eolian_Variable *var)
free(var);
}
Eina_Bool
static Eina_Bool
database_var_global_add(Eolian_Variable *var)
{
if (!_globals) return EINA_FALSE;
@ -28,7 +28,7 @@ database_var_global_add(Eolian_Variable *var)
return EINA_TRUE;
}
Eina_Bool
static Eina_Bool
database_var_constant_add(Eolian_Variable *var)
{
if (!_constants) return EINA_FALSE;
@ -37,3 +37,11 @@ database_var_constant_add(Eolian_Variable *var)
((Eina_List*)eina_hash_find(_constantsf, var->base.file), var));
return EINA_TRUE;
}
Eina_Bool
database_var_add(Eolian_Variable *var)
{
if (var->type == EOLIAN_VAR_GLOBAL)
return database_var_global_add(var);
return database_var_constant_add(var);
}

View File

@ -93,3 +93,10 @@ eolian_variable_namespaces_get(const Eolian_Variable *var)
if (!var->namespaces) return NULL;
return eina_list_iterator_new(var->namespaces);
}
EAPI Eina_Bool
eolian_variable_is_extern(const Eolian_Variable *var)
{
EINA_SAFETY_ON_NULL_RETURN_VAL(var, EINA_FALSE);
return var->is_extern;
}

View File

@ -149,6 +149,7 @@ eo_definitions_temps_free(Eo_Lexer_Temps *tmp)
Eina_Strbuf *buf;
Eo_Param_Def *par;
Eolian_Type *tp;
Eolian_Variable *var;
const char *s;
EINA_LIST_FREE(tmp->str_bufs, buf)
@ -169,6 +170,9 @@ eo_definitions_temps_free(Eo_Lexer_Temps *tmp)
EINA_LIST_FREE(tmp->type_defs, tp)
database_type_del(tp);
EINA_LIST_FREE(tmp->var_defs, var)
database_var_del(var);
if (tmp->prop)
eo_definitions_property_def_free(tmp->prop);

View File

@ -110,6 +110,7 @@ typedef struct _Eo_Lexer_Temps
Eo_Class_Def *kls;
Eo_Ret_Def *ret_def;
Eina_List *type_defs;
Eina_List *var_defs;
Eo_Property_Def *prop;
Eo_Method_Def *meth;
Eo_Param_Def *param;

View File

@ -27,9 +27,9 @@ enum Tokens
KW(destructor), KW(eo_prefix), KW(events), KW(func), KW(get), \
KW(implements), KW(interface), KW(keys), KW(legacy), KW(legacy_prefix), \
KW(methods), KW(mixin), KW(own), KW(params), KW(properties), KW(set), \
KW(type), KW(values), KWAT(class), KWAT(const), KWAT(constructor), \
KWAT(extern), KWAT(in), KWAT(inout), KWAT(nonull), KWAT(out), \
KWAT(private), KWAT(protected), KWAT(warn_unused), \
KW(type), KW(values), KW(var), KWAT(class), KWAT(const), \
KWAT(constructor), KWAT(extern), KWAT(in), KWAT(inout), KWAT(nonull), \
KWAT(out), KWAT(private), KWAT(protected), KWAT(warn_unused), \
\
KW(byte), KW(ubyte), KW(char), KW(short), KW(ushort), KW(int), KW(uint), \
KW(long), KW(ulong), KW(llong), KW(ullong), \

View File

@ -114,6 +114,20 @@ pop_type(Eo_Lexer *ls)
ls->tmp.type_defs = eina_list_remove_list(ls->tmp.type_defs, ls->tmp.type_defs);
}
static Eolian_Variable *
push_var(Eo_Lexer *ls)
{
Eolian_Variable *def = calloc(1, sizeof(Eolian_Variable));
ls->tmp.var_defs = eina_list_prepend(ls->tmp.var_defs, def);
return def;
}
static void
pop_var(Eo_Lexer *ls)
{
ls->tmp.var_defs = eina_list_remove_list(ls->tmp.var_defs, ls->tmp.var_defs);
}
static void
append_node(Eo_Lexer *ls, int type, void *def)
{
@ -188,29 +202,40 @@ parse_name_list(Eo_Lexer *ls)
return ls->tmp.str_items;
}
#define NAMESPACE_PARSE(def, dname) \
char *full_name = strdup(dname); \
char *name = full_name, *dot = full_name; \
def->full_name = dname; \
do \
{ \
dot = strchr(dot, '.'); \
if (dot) \
{ \
*dot = '\0'; \
def->namespaces = eina_list_append(def->namespaces, \
eina_stringshare_add(name)); \
++dot; \
name = dot; \
} \
} \
while (dot); \
def->name = eina_stringshare_add(name); \
free(full_name);
static void
_fill_type_name(Eolian_Type *tp, const char *type_name)
{
char *full_name = strdup(type_name);
char *name = full_name, *dot = full_name;
tp->full_name = type_name;
do
{
dot = strchr(dot, '.');
if (dot)
{
*dot = '\0';
tp->namespaces = eina_list_append(tp->namespaces,
eina_stringshare_add(name));
++dot;
name = dot;
}
}
while (dot);
tp->name = eina_stringshare_add(name);
free(full_name);
NAMESPACE_PARSE(tp, type_name)
}
static void
_fill_variable_name(Eolian_Variable *var, const char *var_name)
{
NAMESPACE_PARSE(var, var_name)
}
#undef NAMESPACE_PARSE
static Eolian_Expression *
push_expr(Eo_Lexer *ls)
{
@ -795,7 +820,7 @@ parse_typedef(Eo_Lexer *ls)
redef_error(ls, EOLIAN_TYPE_ALIAS, tp);
}
eo_lexer_context_pop(ls);
(void)!!test_next(ls, ':');
check_next(ls, ':');
def->base_type = parse_type_struct(ls, EINA_TRUE);
pop_type(ls);
check_next(ls, ';');
@ -807,6 +832,46 @@ parse_typedef(Eo_Lexer *ls)
return def;
}
static Eolian_Variable *
parse_variable(Eo_Lexer *ls, Eina_Bool global)
{
Eolian_Variable *def = push_var(ls);
Eina_Bool is_extern = EINA_FALSE;
Eina_Strbuf *buf;
eo_lexer_get(ls);
if (ls->t.kw == KW_at_extern)
{
is_extern = EINA_TRUE;
eo_lexer_get(ls);
}
def->type = global ? EOLIAN_VAR_GLOBAL : EOLIAN_VAR_CONSTANT;
def->is_extern = is_extern;
buf = push_strbuf(ls);
eo_lexer_context_push(ls);
def->base.file = eina_stringshare_ref(ls->filename);
def->base.line = ls->line_number;
def->base.column = ls->column;
parse_name(ls, buf);
_fill_variable_name(def, eina_stringshare_add(eina_strbuf_string_get(buf)));
check_next(ls, ':');
def->base_type = parse_type(ls);
pop_type(ls);
if (ls->t.token == '=')
{
ls->expr_mode = EINA_TRUE;
eo_lexer_get(ls);
def->value = parse_expr(ls);
ls->expr_mode = EINA_FALSE;
}
check_next(ls, ';');
if (ls->t.token == TOK_COMMENT)
{
def->comment = eina_stringshare_ref(ls->t.value.s);
eo_lexer_get(ls);
}
return def;
}
static void
parse_return(Eo_Lexer *ls, Eina_Bool allow_void)
{
@ -1534,6 +1599,13 @@ parse_unit(Eo_Lexer *ls, Eina_Bool eot)
pop_type(ls);
break;
}
case KW_const:
case KW_var:
{
database_var_add(parse_variable(ls, ls->t.kw == KW_var));
pop_var(ls);
break;
}
case KW_struct:
{
const char *name;

View File

@ -242,6 +242,7 @@ struct _Eolian_Variable
Eolian_Type *base_type;
Eolian_Expression *value;
Eina_Stringshare *comment;
Eina_Bool is_extern :1;
};
int database_init();
@ -265,8 +266,7 @@ void database_expr_del(Eolian_Expression *expr);
/* variables */
void database_var_del(Eolian_Variable *var);
Eina_Bool database_var_global_add(Eolian_Variable *var);
Eina_Bool database_var_constant_add(Eolian_Variable *var);
Eina_Bool database_var_add(Eolian_Variable *var);
/* classes */