From 35c5e892695ad4e2169003c0dd2a00db8c1679a4 Mon Sep 17 00:00:00 2001 From: Daniel Kolesa Date: Mon, 16 Jan 2017 15:51:11 +0100 Subject: [PATCH] eolian: remove/add APIs and clean up implements system As there is no need to have separate is_auto, is_empty and is_pure_virtual for functions and implements (each function has its own base implement by default) I removed the function ones. Instead, I added a way to retrieve a function's base implement so that you can instead do the checks on the implement even when you only have the function. I also moved base implement build directly into the parser instead of the database filler. That allows for significant cleanup. I also removed distinction of implement pointers in Eolian_Function for get and set as implements now always contain an entire thing so the pointer was always the same anyway. Things should still behave more or less the same, but ordering of generated functions has changed because ordering of implements has changed. --- src/bin/eolian/sources.c | 18 +-- src/bindings/luajit/eolian.lua | 18 +-- src/lib/eolian/Eolian.h | 35 +----- src/lib/eolian/database_fill.c | 124 ++------------------ src/lib/eolian/database_function_api.c | 76 +----------- src/lib/eolian/eo_parser.c | 71 ++++++++--- src/lib/eolian/eolian_database.h | 9 +- src/scripts/elua/apps/docgen/doctree.lua | 6 +- src/tests/eolian/data/docs_ref.h | 30 ++--- src/tests/eolian/data/docs_ref_legacy.h | 30 ++--- src/tests/eolian/data/object_impl_add_ref.c | 26 ++-- src/tests/eolian/data/object_impl_ref.c | 26 ++-- src/tests/eolian/data/override_ref.c | 66 ++++++----- src/tests/eolian/eolian_parsing.c | 51 +++----- 14 files changed, 194 insertions(+), 392 deletions(-) diff --git a/src/bin/eolian/sources.c b/src/bin/eolian/sources.c index aff1f4b432..f264f531a2 100644 --- a/src/bin/eolian/sources.c +++ b/src/bin/eolian/sources.c @@ -272,7 +272,7 @@ _gen_func(const Eolian_Class *cl, const Eolian_Function *fid, Eina_Bool impl_same_class = (eolian_implement_class_get(impl) == cl); Eina_Bool impl_need = EINA_TRUE; - if (impl_same_class && eolian_function_is_pure_virtual(fid, ftype)) + if (impl_same_class && eolian_implement_is_pure_virtual(impl, ftype)) impl_need = EINA_FALSE; Eina_Stringshare *rtpn = rtp ? eolian_type_c_type_get(rtp) @@ -495,14 +495,14 @@ _gen_func(const Eolian_Class *cl, const Eolian_Function *fid, static void _gen_opfunc(const Eolian_Function *fid, Eolian_Function_Type ftype, - Eina_Strbuf *buf, Eina_Bool pinit, + Eina_Strbuf *buf, const Eolian_Implement *impl, Eina_Bool pinit, const char *cnamel, const char *ocnamel) { Eina_Stringshare *fnm = eolian_function_full_c_name_get(fid, ftype, EINA_FALSE); eina_strbuf_append(buf, " EFL_OBJECT_OP_FUNC("); eina_strbuf_append(buf, fnm); eina_strbuf_append(buf, ", "); - if (!ocnamel && eolian_function_is_pure_virtual(fid, ftype)) + if (!ocnamel && eolian_implement_is_pure_virtual(impl, ftype)) eina_strbuf_append(buf, "NULL),\n"); else { @@ -566,17 +566,17 @@ _gen_initializer(const Eolian_Class *cl, Eina_Strbuf *buf) switch (ftype) { case EOLIAN_PROP_GET: - _gen_opfunc(fid, EOLIAN_PROP_GET, obuf, found_get, cnamel, ocnamel); + _gen_opfunc(fid, EOLIAN_PROP_GET, obuf, imp, found_get, cnamel, ocnamel); break; case EOLIAN_PROP_SET: - _gen_opfunc(fid, EOLIAN_PROP_SET, obuf, found_set, cnamel, ocnamel); + _gen_opfunc(fid, EOLIAN_PROP_SET, obuf, imp, found_set, cnamel, ocnamel); break; case EOLIAN_PROPERTY: - _gen_opfunc(fid, EOLIAN_PROP_SET, obuf, found_set, cnamel, ocnamel); - _gen_opfunc(fid, EOLIAN_PROP_GET, obuf, found_get, cnamel, ocnamel); + _gen_opfunc(fid, EOLIAN_PROP_SET, obuf, imp, found_set, cnamel, ocnamel); + _gen_opfunc(fid, EOLIAN_PROP_GET, obuf, imp, found_get, cnamel, ocnamel); break; default: - _gen_opfunc(fid, EOLIAN_METHOD, obuf, found_get, cnamel, ocnamel); + _gen_opfunc(fid, EOLIAN_METHOD, obuf, imp, found_get, cnamel, ocnamel); break; } @@ -840,7 +840,7 @@ _gen_proto(const Eolian_Class *cl, const Eolian_Function *fid, const char *cnamel) { Eina_Bool impl_same_class = (eolian_implement_class_get(impl) == cl); - if (impl_same_class && eolian_function_is_pure_virtual(fid, ftype)) + if (impl_same_class && eolian_implement_is_pure_virtual(impl, ftype)) return; char *ocnamel = NULL; diff --git a/src/bindings/luajit/eolian.lua b/src/bindings/luajit/eolian.lua index fb8be5720a..d96b7e690a 100644 --- a/src/bindings/luajit/eolian.lua +++ b/src/bindings/luajit/eolian.lua @@ -250,9 +250,7 @@ ffi.cdef [[ const Eolian_Function *eolian_class_function_get_by_name(const Eolian_Class *klass, const char *func_name, Eolian_Function_Type f_type); const char *eolian_function_legacy_get(const Eolian_Function *function_id, Eolian_Function_Type f_type); const Eolian_Documentation *eolian_function_documentation_get(const Eolian_Function *function_id, Eolian_Function_Type f_type); - Eina_Bool eolian_function_is_pure_virtual(const Eolian_Function *function_id, Eolian_Function_Type f_type); - Eina_Bool eolian_function_is_auto(const Eolian_Function *function_id, Eolian_Function_Type f_type); - Eina_Bool eolian_function_is_empty(const Eolian_Function *function_id, Eolian_Function_Type f_type); + const Eolian_Implement *eolian_function_implement_get(const Eolian_Function *function_id); Eina_Bool eolian_function_is_legacy_only(const Eolian_Function *function_id, Eolian_Function_Type ftype); Eina_Bool eolian_function_is_class(const Eolian_Function *function_id); Eina_Bool eolian_function_is_c_only(const Eolian_Function *function_id); @@ -783,16 +781,10 @@ M.Function = ffi.metatype("Eolian_Function", { return v end, - is_pure_virtual = function(self, ftype) - return eolian.eolian_function_is_pure_virtual(self, ftype) ~= 0 - end, - - is_auto = function(self, ftype) - return eolian.eolian_function_is_auto(self, ftype) ~= 0 - end, - - is_empty = function(self, ftype) - return eolian.eolian_function_is_empty(self, ftype) ~= 0 + implement_get = function(self) + local v = eolian.eolian_function_implement_get(self) + if v == nil then return nil end + return v end, is_legacy_only = function(self, ftype) diff --git a/src/lib/eolian/Eolian.h b/src/lib/eolian/Eolian.h index b06efeee06..97b28cf177 100644 --- a/src/lib/eolian/Eolian.h +++ b/src/lib/eolian/Eolian.h @@ -761,43 +761,14 @@ EAPI Eina_Stringshare *eolian_function_legacy_get(const Eolian_Function *functio EAPI const Eolian_Documentation *eolian_function_documentation_get(const Eolian_Function *function_id, Eolian_Function_Type f_type); /* - * @brief Indicates if a function is pure virtual. + * @brief Returns the implement for a function. * * @param[in] function_id Id of the function - * @param[in] f_type The function type, for property get/set distinction. - * @return EINA_TRUE if pure virtual, EINA_FALSE othrewise. - * - * Acceptable input types are METHOD, PROP_GET and PROP_SET. + * @return the implement or NULL. * * @ingroup Eolian */ -EAPI Eina_Bool eolian_function_is_pure_virtual(const Eolian_Function *function_id, Eolian_Function_Type f_type); - -/* - * @brief Indicates if a function is auto. - * - * @param[in] function_id Id of the function - * @param[in] f_type The function type, for property get/set distinction. - * @return EINA_TRUE if auto, EINA_FALSE othrewise. - * - * Acceptable input types are METHOD, PROP_GET and PROP_SET. - * - * @ingroup Eolian - */ -EAPI Eina_Bool eolian_function_is_auto(const Eolian_Function *function_id, Eolian_Function_Type f_type); - -/* - * @brief Indicates if a function is empty. - * - * @param[in] function_id Id of the function - * @param[in] f_type The function type, for property get/set distinction. - * @return EINA_TRUE if empty, EINA_FALSE othrewise. - * - * Acceptable input types are METHOD, PROP_GET and PROP_SET. - * - * @ingroup Eolian - */ -EAPI Eina_Bool eolian_function_is_empty(const Eolian_Function *function_id, Eolian_Function_Type f_type); +EAPI const Eolian_Implement *eolian_function_implement_get(const Eolian_Function *function_id); /* * @brief Indicates if a function is legacy only. diff --git a/src/lib/eolian/database_fill.c b/src/lib/eolian/database_fill.c index 11d083e1f7..fb4d1bc0db 100644 --- a/src/lib/eolian/database_fill.c +++ b/src/lib/eolian/database_fill.c @@ -30,8 +30,7 @@ _print_linecol(const Eolian_Object *base) } static Eina_Bool -_get_impl_func(Eolian_Class *cl, Eolian_Implement *impl, - Eolian_Function_Type ftype, Eolian_Function **foo_id) +_get_impl_func(Eolian_Class *cl, Eolian_Implement *impl, Eolian_Function_Type ftype) { size_t imlen = strlen(impl->full_name); char *clbuf = alloca(imlen + 1); @@ -118,7 +117,6 @@ _get_impl_func(Eolian_Class *cl, Eolian_Implement *impl, return EINA_FALSE; } - *foo_id = (Eolian_Function *)fid; impl->foo_id = fid; return EINA_TRUE; @@ -128,7 +126,6 @@ _get_impl_func(Eolian_Class *cl, Eolian_Implement *impl, static Eina_Bool _db_fill_implement(Eolian_Class *cl, Eolian_Implement *impl) { - Eolian_Function *foo_id; Eolian_Function_Type ftype = EOLIAN_METHOD; if (impl->is_prop_get && impl->is_prop_set) @@ -138,135 +135,32 @@ _db_fill_implement(Eolian_Class *cl, Eolian_Implement *impl) else if (impl->is_prop_set) ftype = EOLIAN_PROP_SET; - if (!_get_impl_func(cl, impl, ftype, &foo_id)) - return EINA_FALSE; - - foo_id->get_auto = impl->get_auto; - foo_id->set_auto = impl->set_auto; - foo_id->get_empty = impl->get_empty; - foo_id->set_empty = impl->set_empty; - if (foo_id->get_auto || foo_id->get_empty) - { - if (ftype == EOLIAN_METHOD) - foo_id->set_impl = impl; - foo_id->get_impl = impl; - } - if (foo_id->set_auto || foo_id->set_empty) - foo_id->set_impl = impl; - - return EINA_TRUE; -} - -static void -_db_build_implement(Eolian_Class *cl, Eolian_Function *foo_id) -{ - if (foo_id->type == EOLIAN_PROP_SET) - { - if (foo_id->set_impl) return; - } - else if (foo_id->type == EOLIAN_PROP_GET) - { - if (foo_id->get_impl) return; - } - else if (foo_id->get_impl && foo_id->set_impl) return; - - Eolian_Implement *impl = calloc(1, sizeof(Eolian_Implement)); - - if (foo_id->type == EOLIAN_PROP_SET) - impl->base = foo_id->set_base; - else - impl->base = foo_id->base; - eina_stringshare_ref(impl->base.file); - - impl->klass = cl; - impl->foo_id = foo_id; - impl->full_name = eina_stringshare_printf("%s.%s", cl->full_name, - foo_id->name); - - if (foo_id->type == EOLIAN_PROPERTY) - { - if (foo_id->get_pure_virtual && !foo_id->get_impl) - { - impl->get_pure_virtual = EINA_TRUE; - impl->is_prop_get = EINA_TRUE; - foo_id->get_impl = impl; - cl->implements = eina_list_append(cl->implements, impl); - /* repeat for set */ - _db_build_implement(cl, foo_id); - return; - } - else if (foo_id->set_pure_virtual && !foo_id->set_impl) - { - impl->set_pure_virtual = EINA_TRUE; - impl->is_prop_set = EINA_TRUE; - foo_id->set_impl = impl; - cl->implements = eina_list_append(cl->implements, impl); - /* repeat for get */ - _db_build_implement(cl, foo_id); - return; - } - if (foo_id->get_impl) - { - impl->is_prop_set = EINA_TRUE; - impl->set_pure_virtual = foo_id->set_pure_virtual; - foo_id->set_impl = impl; - } - else if (foo_id->set_impl) - { - impl->is_prop_get = EINA_TRUE; - foo_id->get_impl = impl; - } - else - foo_id->get_impl = foo_id->set_impl = impl; - } - else if (foo_id->type == EOLIAN_PROP_SET) - { - impl->is_prop_set = EINA_TRUE; - impl->get_pure_virtual = foo_id->get_pure_virtual; - foo_id->set_impl = impl; - } - else if (foo_id->type == EOLIAN_PROP_GET) - { - impl->is_prop_get = EINA_TRUE; - impl->get_pure_virtual = foo_id->set_pure_virtual; - foo_id->get_impl = impl; - } - else - { - impl->get_pure_virtual = foo_id->get_pure_virtual; - foo_id->get_impl = foo_id->set_impl = impl; - } - - cl->implements = eina_list_append(cl->implements, impl); + return _get_impl_func(cl, impl, ftype); } static Eina_Bool _db_fill_implements(Eolian_Class *cl) { Eolian_Implement *impl; - Eolian_Function *foo_id; Eina_List *l; - Eina_Hash *th = eina_hash_string_small_new(NULL); + Eina_Hash *th = eina_hash_string_small_new(NULL), + *pth = eina_hash_string_small_new(NULL); EINA_LIST_FOREACH(cl->implements, l, impl) { - if (eina_hash_find(th, impl->full_name)) + Eina_Bool prop = (impl->is_prop_get || impl->is_prop_set); + if (eina_hash_find(prop ? pth : th, impl->full_name)) { _print_linecol(&impl->base); fprintf(stderr, "duplicate implement '%s'\n", impl->full_name); return EINA_FALSE; } - if (!_db_fill_implement(cl, impl)) + if ((impl->klass != cl) && !_db_fill_implement(cl, impl)) return EINA_FALSE; - eina_hash_add(th, impl->full_name, impl->full_name); + eina_hash_add(prop ? pth : th, impl->full_name, impl->full_name); } eina_hash_free(th); - - EINA_LIST_FOREACH(cl->properties, l, foo_id) - _db_build_implement(cl, foo_id); - - EINA_LIST_FOREACH(cl->methods, l, foo_id) - _db_build_implement(cl, foo_id); + eina_hash_free(pth); return EINA_TRUE; } diff --git a/src/lib/eolian/database_function_api.c b/src/lib/eolian/database_function_api.c index 479141af35..1ad2a3ab91 100644 --- a/src/lib/eolian/database_function_api.c +++ b/src/lib/eolian/database_function_api.c @@ -196,79 +196,11 @@ eolian_function_documentation_get(const Eolian_Function *fid, Eolian_Function_Ty } } -EAPI Eina_Bool -eolian_function_is_pure_virtual(const Eolian_Function *fid, Eolian_Function_Type ftype) +EAPI const Eolian_Implement * +eolian_function_implement_get(const Eolian_Function *fid) { - EINA_SAFETY_ON_NULL_RETURN_VAL(fid, EINA_FALSE); - EINA_SAFETY_ON_FALSE_RETURN_VAL(ftype != EOLIAN_UNRESOLVED, EINA_FALSE); - EINA_SAFETY_ON_FALSE_RETURN_VAL(ftype != EOLIAN_PROPERTY, EINA_FALSE); - switch (ftype) - { - case EOLIAN_METHOD: - if (fid->type != EOLIAN_METHOD) - return EINA_FALSE; - return fid->get_pure_virtual; - case EOLIAN_PROP_GET: - if ((fid->type != EOLIAN_PROP_GET) && (fid->type != EOLIAN_PROPERTY)) - return EINA_FALSE; - return fid->get_pure_virtual; - case EOLIAN_PROP_SET: - if ((fid->type != EOLIAN_PROP_SET) && (fid->type != EOLIAN_PROPERTY)) - return EINA_FALSE; - return fid->set_pure_virtual; - default: - return EINA_FALSE; - } -} - -EAPI Eina_Bool -eolian_function_is_auto(const Eolian_Function *fid, Eolian_Function_Type ftype) -{ - EINA_SAFETY_ON_NULL_RETURN_VAL(fid, EINA_FALSE); - EINA_SAFETY_ON_FALSE_RETURN_VAL(ftype != EOLIAN_UNRESOLVED, EINA_FALSE); - EINA_SAFETY_ON_FALSE_RETURN_VAL(ftype != EOLIAN_PROPERTY, EINA_FALSE); - switch (ftype) - { - case EOLIAN_METHOD: - if (fid->type != EOLIAN_METHOD) - return EINA_FALSE; - return fid->get_auto; - case EOLIAN_PROP_GET: - if ((fid->type != EOLIAN_PROP_GET) && (fid->type != EOLIAN_PROPERTY)) - return EINA_FALSE; - return fid->get_auto; - case EOLIAN_PROP_SET: - if ((fid->type != EOLIAN_PROP_SET) && (fid->type != EOLIAN_PROPERTY)) - return EINA_FALSE; - return fid->set_auto; - default: - return EINA_FALSE; - } -} - -EAPI Eina_Bool -eolian_function_is_empty(const Eolian_Function *fid, Eolian_Function_Type ftype) -{ - EINA_SAFETY_ON_NULL_RETURN_VAL(fid, EINA_FALSE); - EINA_SAFETY_ON_FALSE_RETURN_VAL(ftype != EOLIAN_UNRESOLVED, EINA_FALSE); - EINA_SAFETY_ON_FALSE_RETURN_VAL(ftype != EOLIAN_PROPERTY, EINA_FALSE); - switch (ftype) - { - case EOLIAN_METHOD: - if (fid->type != EOLIAN_METHOD) - return EINA_FALSE; - return fid->get_empty; - case EOLIAN_PROP_GET: - if ((fid->type != EOLIAN_PROP_GET) && (fid->type != EOLIAN_PROPERTY)) - return EINA_FALSE; - return fid->get_empty; - case EOLIAN_PROP_SET: - if ((fid->type != EOLIAN_PROP_SET) && (fid->type != EOLIAN_PROPERTY)) - return EINA_FALSE; - return fid->set_empty; - default: - return EINA_FALSE; - } + EINA_SAFETY_ON_NULL_RETURN_VAL(fid, NULL); + return fid->impl; } EAPI Eina_Bool diff --git a/src/lib/eolian/eo_parser.c b/src/lib/eolian/eo_parser.c index eaa28b7359..5dd8376cc8 100644 --- a/src/lib/eolian/eo_parser.c +++ b/src/lib/eolian/eo_parser.c @@ -1191,8 +1191,8 @@ parse_accessor(Eo_Lexer *ls, Eolian_Function *prop) { case KW_at_pure_virtual: CASE_LOCK(ls, virtp, "pure_virtual qualifier"); - if (is_get) prop->get_pure_virtual = EINA_TRUE; - else prop->set_pure_virtual = EINA_TRUE; + if (is_get) prop->impl->get_pure_virtual = EINA_TRUE; + else prop->impl->set_pure_virtual = EINA_TRUE; eo_lexer_get(ls); break; case KW_at_protected: @@ -1297,11 +1297,11 @@ _func_pure_virtual_set(Eo_Lexer *ls, Eolian_Function *foo_id, Eina_Bool virt) return; if (foo_id->type == EOLIAN_PROP_GET || foo_id->type == EOLIAN_METHOD) - foo_id->get_pure_virtual = EINA_TRUE; + foo_id->impl->get_pure_virtual = EINA_TRUE; else if (foo_id->type == EOLIAN_PROP_SET) - foo_id->set_pure_virtual = EINA_TRUE; + foo_id->impl->set_pure_virtual = EINA_TRUE; else if (foo_id->type == EOLIAN_PROPERTY) - foo_id->get_pure_virtual = foo_id->set_pure_virtual = EINA_TRUE; + foo_id->impl->get_pure_virtual = foo_id->impl->set_pure_virtual = EINA_TRUE; } static void @@ -1309,6 +1309,7 @@ parse_property(Eo_Lexer *ls) { int line, col; Eolian_Function *prop = NULL; + Eolian_Implement *impl = NULL; Eina_Bool has_get = EINA_FALSE, has_set = EINA_FALSE, has_keys = EINA_FALSE, has_values = EINA_FALSE, has_protected = EINA_FALSE, has_class = EINA_FALSE, @@ -1319,7 +1320,13 @@ parse_property(Eo_Lexer *ls) prop->type = EOLIAN_UNRESOLVED; prop->get_scope = prop->set_scope = EOLIAN_SCOPE_PUBLIC; FILL_BASE(prop->base, ls, ls->line_number, ls->column); + impl = calloc(1, sizeof(Eolian_Implement)); + impl->klass = ls->tmp.kls; + impl->foo_id = prop; + FILL_BASE(impl->base, ls, ls->line_number, ls->column); + prop->impl = impl; ls->tmp.kls->properties = eina_list_append(ls->tmp.kls->properties, prop); + ls->tmp.kls->implements = eina_list_append(ls->tmp.kls->implements, impl); check(ls, TOK_VALUE); if (ls->t.kw == KW_get || ls->t.kw == KW_set) { @@ -1327,6 +1334,7 @@ parse_property(Eo_Lexer *ls) return; } prop->name = eina_stringshare_ref(ls->t.value.s); + impl->full_name = eina_stringshare_printf("%s.%s", ls->tmp.kls->full_name, prop->name); eo_lexer_get(ls); for (;;) switch (ls->t.kw) { @@ -1366,10 +1374,12 @@ body: { case KW_get: CASE_LOCK(ls, get, "get definition") + impl->is_prop_get = EINA_TRUE; parse_accessor(ls, prop); break; case KW_set: CASE_LOCK(ls, set, "set definition") + impl->is_prop_set = EINA_TRUE; parse_accessor(ls, prop); break; case KW_keys: @@ -1386,7 +1396,10 @@ body: end: check_match(ls, '}', '{', line, col); if (!has_get && !has_set) - prop->type = EOLIAN_PROPERTY; + { + prop->type = EOLIAN_PROPERTY; + impl->is_prop_get = impl->is_prop_set = EINA_TRUE; + } _func_pure_virtual_set(ls, prop, has_virtp); } @@ -1395,6 +1408,7 @@ parse_method(Eo_Lexer *ls) { int line, col; Eolian_Function *meth = NULL; + Eolian_Implement *impl = NULL; Eina_Bool has_const = EINA_FALSE, has_params = EINA_FALSE, has_return = EINA_FALSE, has_legacy = EINA_FALSE, has_protected = EINA_FALSE, has_class = EINA_FALSE, @@ -1405,7 +1419,13 @@ parse_method(Eo_Lexer *ls) meth->type = EOLIAN_METHOD; meth->get_scope = meth->set_scope = EOLIAN_SCOPE_PUBLIC; FILL_BASE(meth->base, ls, ls->line_number, ls->column); + impl = calloc(1, sizeof(Eolian_Implement)); + impl->klass = ls->tmp.kls; + impl->foo_id = meth; + FILL_BASE(impl->base, ls, ls->line_number, ls->column); + meth->impl = impl; ls->tmp.kls->methods = eina_list_append(ls->tmp.kls->methods, meth); + ls->tmp.kls->implements = eina_list_append(ls->tmp.kls->implements, impl); check(ls, TOK_VALUE); if (ls->t.kw == KW_get || ls->t.kw == KW_set) { @@ -1413,6 +1433,7 @@ parse_method(Eo_Lexer *ls) return; } meth->name = eina_stringshare_ref(ls->t.value.s); + impl->full_name = eina_stringshare_printf("%s.%s", ls->tmp.kls->full_name, meth->name); eo_lexer_get(ls); for (;;) switch (ls->t.kw) { @@ -1515,9 +1536,6 @@ parse_implement(Eo_Lexer *ls, Eina_Bool iface) check_next(ls, ';'); return; } - impl = calloc(1, sizeof(Eolian_Implement)); - FILL_BASE(impl->base, ls, iline, icol); - ls->tmp.kls->implements = eina_list_append(ls->tmp.kls->implements, impl); Eina_Bool glob_auto = EINA_FALSE, glob_empty = EINA_FALSE; switch (ls->t.kw) { @@ -1537,12 +1555,29 @@ parse_implement(Eo_Lexer *ls, Eina_Bool iface) eo_lexer_get(ls); if (ls->t.token != TOK_VALUE) eo_lexer_syntax_error(ls, "name expected"); - impl->full_name = eina_stringshare_printf("%s.%s", - ls->tmp.kls->full_name, - ls->t.value.s); + Eina_Stringshare *iname = eina_stringshare_printf("%s.%s", + ls->tmp.kls->full_name, + ls->t.value.s); + Eina_List *l; + Eolian_Implement *fimp; + EINA_LIST_FOREACH(ls->tmp.kls->implements, l, fimp) + if (iname == fimp->full_name) + { + impl = fimp; + break; + } + eina_stringshare_del(iname); + if (!impl) + eo_lexer_syntax_error(ls, "implement of non-existent function"); eo_lexer_get(ls); goto propbeg; } + else + { + impl = calloc(1, sizeof(Eolian_Implement)); + FILL_BASE(impl->base, ls, iline, icol); + ls->tmp.kls->implements = eina_list_append(ls->tmp.kls->implements, impl); + } if (ls->t.token != TOK_VALUE) eo_lexer_syntax_error(ls, "class name expected"); buf = push_strbuf(ls); @@ -1620,13 +1655,11 @@ propend: check_next(ls, '}'); } else - { - if (glob_auto) - impl->get_auto = impl->set_auto = EINA_TRUE; - if (glob_empty) - impl->get_empty = impl->set_empty = EINA_TRUE; - check_next(ls, ';'); - } + check_next(ls, ';'); + if (glob_auto) + impl->get_auto = impl->set_auto = EINA_TRUE; + if (glob_empty) + impl->get_empty = impl->set_empty = EINA_TRUE; end: if (buf) { diff --git a/src/lib/eolian/eolian_database.h b/src/lib/eolian/eolian_database.h index eeace389d6..9040262113 100644 --- a/src/lib/eolian/eolian_database.h +++ b/src/lib/eolian/eolian_database.h @@ -123,8 +123,7 @@ struct _Eolian_Function Eolian_Type *set_ret_type; Eolian_Expression *get_ret_val; Eolian_Expression *set_ret_val; - Eolian_Implement *get_impl; - Eolian_Implement *set_impl; + Eolian_Implement *impl; Eina_Stringshare *get_legacy; Eina_Stringshare *set_legacy; Eolian_Documentation *common_doc; @@ -133,12 +132,6 @@ struct _Eolian_Function Eolian_Documentation *get_return_doc; Eolian_Documentation *set_return_doc; Eina_Bool obj_is_const :1; /* True if the object has to be const. Useful for a few methods. */ - Eina_Bool get_pure_virtual :1; - Eina_Bool set_pure_virtual :1; - Eina_Bool get_auto :1; - Eina_Bool set_auto :1; - Eina_Bool get_empty :1; - Eina_Bool set_empty :1; Eina_Bool get_return_warn_unused :1; /* also used for methods */ Eina_Bool set_return_warn_unused :1; Eina_Bool get_only_legacy: 1; diff --git a/src/scripts/elua/apps/docgen/doctree.lua b/src/scripts/elua/apps/docgen/doctree.lua index 0bb9c75a06..b5d81ee579 100644 --- a/src/scripts/elua/apps/docgen/doctree.lua +++ b/src/scripts/elua/apps/docgen/doctree.lua @@ -322,15 +322,15 @@ M.Function = Node:clone { end, is_pure_virtual = function(self, ft) - return self.func:is_pure_virtual(ft) + return self.func:implement_get():is_pure_virtual(ft) end, is_auto = function(self, ft) - return self.func:is_auto(ft) + return self.func:implement_get():is_auto(ft) end, is_empty = function(self, ft) - return self.func:is_empty(ft) + return self.func:implement_get():is_empty(ft) end, is_legacy_only = function(self, ft) diff --git a/src/tests/eolian/data/docs_ref.h b/src/tests/eolian/data/docs_ref.h index 8f25fd72ed..bd9224efbd 100644 --- a/src/tests/eolian/data/docs_ref.h +++ b/src/tests/eolian/data/docs_ref.h @@ -85,6 +85,21 @@ typedef struct _Opaque Opaque; EWAPI const Efl_Class *docs_class_get(void); +/** + * @brief Method documentation. + * + * @param[in] a Param documentation. + * @param[out] b + * @param[out] c Another param documentation. + * + * @return Return documentation. + * + * @since 1.18 + * + * @ingroup Docs + */ +EOAPI int docs_meth(Eo *obj, int a, float *b, long *c); + /** * @brief Property common documentation. * @@ -111,21 +126,6 @@ EOAPI void docs_prop_set(Eo *obj, int val); */ EOAPI int docs_prop_get(const Eo *obj); -/** - * @brief Method documentation. - * - * @param[in] a Param documentation. - * @param[out] b - * @param[out] c Another param documentation. - * - * @return Return documentation. - * - * @since 1.18 - * - * @ingroup Docs - */ -EOAPI int docs_meth(Eo *obj, int a, float *b, long *c); - EWAPI extern const Efl_Event_Description _DOCS_EVENT_CLICKED; /** Event docs. diff --git a/src/tests/eolian/data/docs_ref_legacy.h b/src/tests/eolian/data/docs_ref_legacy.h index 529326c5d7..5d3849ac36 100644 --- a/src/tests/eolian/data/docs_ref_legacy.h +++ b/src/tests/eolian/data/docs_ref_legacy.h @@ -71,6 +71,21 @@ typedef struct _Opaque Opaque; #endif +/** + * @brief Method documentation. + * + * @param[in] a Param documentation. + * @param[out] b + * @param[out] c Another param documentation. + * + * @return Return documentation. + * + * @since 1.18 + * + * @ingroup Docs + */ +EAPI int docs_meth(Docs *obj, int a, float *b, long *c); + /** * @brief Property common documentation. * @@ -97,19 +112,4 @@ EAPI void docs_prop_set(Docs *obj, int val); */ EAPI int docs_prop_get(const Docs *obj); -/** - * @brief Method documentation. - * - * @param[in] a Param documentation. - * @param[out] b - * @param[out] c Another param documentation. - * - * @return Return documentation. - * - * @since 1.18 - * - * @ingroup Docs - */ -EAPI int docs_meth(Docs *obj, int a, float *b, long *c); - #endif diff --git a/src/tests/eolian/data/object_impl_add_ref.c b/src/tests/eolian/data/object_impl_add_ref.c index 1e2aa21431..f97248aa27 100644 --- a/src/tests/eolian/data/object_impl_add_ref.c +++ b/src/tests/eolian/data/object_impl_add_ref.c @@ -7,19 +7,6 @@ typedef struct } Object_Impl_Data; -EOLIAN static void -_object_impl_base_constructor(Eo *obj, Object_Impl_Data *pd) -{ - -} - -EOLIAN static void -_object_impl_base_destructor(Eo *obj, Object_Impl_Data *pd) -{ - base_destructor(efl_super(obj, OBJECT_IMPL_CLASS)); - -} - EOLIAN static Eina_Bool _object_impl_a_set(Eo *obj, Object_Impl_Data *pd, const char *part, const Eina_List *value) { @@ -62,6 +49,19 @@ _object_impl_foo2(const Eo *obj, Object_Impl_Data *pd, int a, const char *b) } +EOLIAN static void +_object_impl_base_constructor(Eo *obj, Object_Impl_Data *pd) +{ + +} + +EOLIAN static void +_object_impl_base_destructor(Eo *obj, Object_Impl_Data *pd) +{ + base_destructor(efl_super(obj, OBJECT_IMPL_CLASS)); + +} + EOLIAN static void _object_impl_class_constructor(Efl_Class *klass) { diff --git a/src/tests/eolian/data/object_impl_ref.c b/src/tests/eolian/data/object_impl_ref.c index 454903c6ab..335613af01 100644 --- a/src/tests/eolian/data/object_impl_ref.c +++ b/src/tests/eolian/data/object_impl_ref.c @@ -7,19 +7,6 @@ typedef struct } Object_Impl_Data; -EOLIAN static void -_object_impl_base_constructor(Eo *obj, Object_Impl_Data *pd) -{ - -} - -EOLIAN static void -_object_impl_base_destructor(Eo *obj, Object_Impl_Data *pd) -{ - base_destructor(efl_super(obj, OBJECT_IMPL_CLASS)); - -} - EOLIAN static Eina_Bool _object_impl_a_set(Eo *obj, Object_Impl_Data *pd, const char *part, const Eina_List *value) { @@ -62,6 +49,19 @@ _object_impl_foo2(const Eo *obj, Object_Impl_Data *pd, int a, const char *b) } +EOLIAN static void +_object_impl_base_constructor(Eo *obj, Object_Impl_Data *pd) +{ + +} + +EOLIAN static void +_object_impl_base_destructor(Eo *obj, Object_Impl_Data *pd) +{ + base_destructor(efl_super(obj, OBJECT_IMPL_CLASS)); + +} + EOLIAN static void _object_impl_class_constructor(Efl_Class *klass) { diff --git a/src/tests/eolian/data/override_ref.c b/src/tests/eolian/data/override_ref.c index 9d6fd8cade..76b9f4095c 100644 --- a/src/tests/eolian/data/override_ref.c +++ b/src/tests/eolian/data/override_ref.c @@ -1,6 +1,8 @@ +EOAPI EFL_VOID_FUNC_BODY(override_a_set); -void _override_base_constructor(Eo *obj, Override_Data *pd); +void _override_a_get(Eo *obj, Override_Data *pd); +EOAPI EFL_VOID_FUNC_BODY_CONST(override_a_get); static void __eolian_override_b_set(Eo *obj EINA_UNUSED, Override_Data *pd, int idx EINA_UNUSED, float a, char b, int c) { @@ -11,6 +13,30 @@ static void __eolian_override_b_set(Eo *obj EINA_UNUSED, Override_Data *pd, int EOAPI EFL_VOID_FUNC_BODYV(override_b_set, EFL_FUNC_CALL(idx, a, b, c), int idx, float a, char b, int c); +static void __eolian_override_b_get(Eo *obj EINA_UNUSED, Override_Data *pd, int idx EINA_UNUSED, float *a, char *b, int *c) +{ + if (a) *a = pd->a; + if (b) *b = pd->b; + if (c) *c = pd->c; +} + +EOAPI EFL_VOID_FUNC_BODYV_CONST(override_b_get, EFL_FUNC_CALL(idx, a, b, c), int idx, float *a, char *b, int *c); + +static void __eolian_override_c_set(Eo *obj EINA_UNUSED, Override_Data *pd, int idx EINA_UNUSED, int c) +{ + c = pd->c; +} + +EOAPI EFL_VOID_FUNC_BODYV(override_c_set, EFL_FUNC_CALL(idx, c), int idx, int c); + +static int __eolian_override_c_get(Eo *obj EINA_UNUSED, Override_Data *pd EINA_UNUSED, int idx EINA_UNUSED) +{ + return 50; +} + +EOAPI EFL_FUNC_BODYV_CONST(override_c_get, int, 50, EFL_FUNC_CALL(idx), int idx); +EOAPI EFL_VOID_FUNC_BODY(override_foo); + static void __eolian_override_bar(Eo *obj EINA_UNUSED, Override_Data *pd EINA_UNUSED, int idx EINA_UNUSED, int *a, char **str) { if (a) *a = 250; @@ -19,12 +45,8 @@ static void __eolian_override_bar(Eo *obj EINA_UNUSED, Override_Data *pd EINA_UN EOAPI EFL_VOID_FUNC_BODYV(override_bar, EFL_FUNC_CALL(idx, a, str), int idx, int *a, char **str); -static int __eolian_override_c_get(Eo *obj EINA_UNUSED, Override_Data *pd EINA_UNUSED, int idx EINA_UNUSED) -{ - return 50; -} +void _override_base_constructor(Eo *obj, Override_Data *pd); -EOAPI EFL_FUNC_BODYV_CONST(override_c_get, int, 50, EFL_FUNC_CALL(idx), int idx); static void __eolian_override_base_z_set(Eo *obj EINA_UNUSED, Override_Data *pd, int a, char b, float c) { @@ -41,36 +63,22 @@ static void __eolian_override_base_z_get(Eo *obj EINA_UNUSED, Override_Data *pd, if (c) *c = pd->c; } -EOAPI EFL_VOID_FUNC_BODY(override_a_set); - -void _override_a_get(Eo *obj, Override_Data *pd); - -EOAPI EFL_VOID_FUNC_BODY_CONST(override_a_get); - -void _override_b_get(Eo *obj, Override_Data *pd, int idx, float *a, char *b, int *c); - -EOAPI EFL_VOID_FUNC_BODYV_CONST(override_b_get, EFL_FUNC_CALL(idx, a, b, c), int idx, float *a, char *b, int *c); - -void _override_c_set(Eo *obj, Override_Data *pd, int idx, int c); - -EOAPI EFL_VOID_FUNC_BODYV(override_c_set, EFL_FUNC_CALL(idx, c), int idx, int c); -EOAPI EFL_VOID_FUNC_BODY(override_foo); static Eina_Bool _override_class_initializer(Efl_Class *klass) { EFL_OPS_DEFINE(ops, - EFL_OBJECT_OP_FUNC(base_constructor, _override_base_constructor), - EFL_OBJECT_OP_FUNC(override_b_set, __eolian_override_b_set), - EFL_OBJECT_OP_FUNC(override_bar, __eolian_override_bar), - EFL_OBJECT_OP_FUNC(override_c_get, __eolian_override_c_get), - EFL_OBJECT_OP_FUNC(base_z_set, __eolian_override_base_z_set), - EFL_OBJECT_OP_FUNC(base_z_get, __eolian_override_base_z_get), EFL_OBJECT_OP_FUNC(override_a_set, NULL), EFL_OBJECT_OP_FUNC(override_a_get, _override_a_get), - EFL_OBJECT_OP_FUNC(override_b_get, _override_b_get), - EFL_OBJECT_OP_FUNC(override_c_set, _override_c_set), - EFL_OBJECT_OP_FUNC(override_foo, NULL) + EFL_OBJECT_OP_FUNC(override_b_set, __eolian_override_b_set), + EFL_OBJECT_OP_FUNC(override_b_get, __eolian_override_b_get), + EFL_OBJECT_OP_FUNC(override_c_set, __eolian_override_c_set), + EFL_OBJECT_OP_FUNC(override_c_get, __eolian_override_c_get), + EFL_OBJECT_OP_FUNC(override_foo, NULL), + EFL_OBJECT_OP_FUNC(override_bar, __eolian_override_bar), + EFL_OBJECT_OP_FUNC(base_constructor, _override_base_constructor), + EFL_OBJECT_OP_FUNC(base_z_set, __eolian_override_base_z_set), + EFL_OBJECT_OP_FUNC(base_z_get, __eolian_override_base_z_get) ); return efl_class_functions_set(klass, &ops, NULL); } diff --git a/src/tests/eolian/eolian_parsing.c b/src/tests/eolian/eolian_parsing.c index 889d5c9f52..15b032ad49 100644 --- a/src/tests/eolian/eolian_parsing.c +++ b/src/tests/eolian/eolian_parsing.c @@ -87,10 +87,6 @@ START_TEST(eolian_namespaces) fail_if(eina_iterator_next(iter, &dummy)); eina_iterator_free(iter); - /* Virtual regression */ - fail_if(!(fid = eolian_class_function_get_by_name(class112, "a", EOLIAN_UNRESOLVED))); - fail_if(!eolian_function_is_pure_virtual(fid, EOLIAN_PROP_SET)); - eolian_shutdown(); } END_TEST @@ -170,7 +166,6 @@ END_TEST START_TEST(eolian_override) { Eina_Iterator *iter; - const Eolian_Function *fid = NULL; const Eolian_Class *impl_class = NULL; const Eolian_Function *impl_func = NULL; const Eolian_Class *class, *base; @@ -185,30 +180,9 @@ START_TEST(eolian_override) fail_if(!(class = eolian_class_get_by_name("Override"))); fail_if(!(base = eolian_class_get_by_name("Base"))); - /* Base ctor */ - fail_if(!(fid = eolian_class_function_get_by_name(base, "constructor", EOLIAN_METHOD))); - fail_if(!eolian_function_is_pure_virtual(fid, EOLIAN_METHOD)); - - /* Property */ - fail_if(!(fid = eolian_class_function_get_by_name(class, "a", EOLIAN_PROPERTY))); - fail_if(!eolian_function_is_pure_virtual(fid, EOLIAN_PROP_SET)); - fail_if(eolian_function_is_pure_virtual(fid, EOLIAN_PROP_GET)); - - /* Method */ - fail_if(!(fid = eolian_class_function_get_by_name(class, "foo", EOLIAN_METHOD))); - fail_if(!eolian_function_is_pure_virtual(fid, EOLIAN_METHOD)); - /* Implements */ fail_if(!(iter = eolian_class_implements_get(class))); - - fail_if(!(eina_iterator_next(iter, (void**)&impl))); - fail_if(eolian_implement_is_auto(impl, EOLIAN_METHOD)); - fail_if(eolian_implement_is_empty(impl, EOLIAN_METHOD)); - fail_if(eolian_implement_is_pure_virtual(impl, EOLIAN_METHOD)); - fail_if(!(impl_class = eolian_implement_class_get(impl))); - fail_if(!(impl_func = eolian_implement_function_get(impl, NULL))); - fail_if(impl_class != base); - fail_if(strcmp(eolian_function_name_get(impl_func), "constructor")); + fail_if(!(eina_iterator_next(iter, (void**)&impl))); /* skip a */ fail_if(!(eina_iterator_next(iter, (void**)&impl))); fail_if(!eolian_implement_is_auto(impl, EOLIAN_PROP_SET)); @@ -218,12 +192,9 @@ START_TEST(eolian_override) fail_if(!(impl_func = eolian_implement_function_get(impl, NULL))); fail_if(impl_class != class); fail_if(strcmp(eolian_function_name_get(impl_func), "b")); - fail_if(!eolian_function_is_auto(impl_func, EOLIAN_PROP_SET)); - fail_if(eolian_function_is_auto(impl_func, EOLIAN_PROP_GET)); - fail_if(eolian_function_is_empty(impl_func, EOLIAN_PROP_SET)); - fail_if(eolian_function_is_empty(impl_func, EOLIAN_PROP_GET)); - fail_if(eolian_function_is_pure_virtual(impl_func, EOLIAN_PROP_SET)); - fail_if(eolian_function_is_pure_virtual(impl_func, EOLIAN_PROP_GET)); + + fail_if(!(eina_iterator_next(iter, (void**)&impl))); /* skip c */ + fail_if(!(eina_iterator_next(iter, (void**)&impl))); /* skip foo */ fail_if(!(eina_iterator_next(iter, (void**)&impl))); fail_if(eolian_implement_is_auto(impl, EOLIAN_METHOD)); @@ -233,9 +204,15 @@ START_TEST(eolian_override) fail_if(!(impl_func = eolian_implement_function_get(impl, NULL))); fail_if(impl_class != class); fail_if(strcmp(eolian_function_name_get(impl_func), "bar")); - fail_if(eolian_function_is_auto(impl_func, EOLIAN_METHOD)); - fail_if(!eolian_function_is_empty(impl_func, EOLIAN_METHOD)); - fail_if(eolian_function_is_pure_virtual(impl_func, EOLIAN_METHOD)); + + fail_if(!(eina_iterator_next(iter, (void**)&impl))); + fail_if(eolian_implement_is_auto(impl, EOLIAN_METHOD)); + fail_if(eolian_implement_is_empty(impl, EOLIAN_METHOD)); + fail_if(eolian_implement_is_pure_virtual(impl, EOLIAN_METHOD)); + fail_if(!(impl_class = eolian_implement_class_get(impl))); + fail_if(!(impl_func = eolian_implement_function_get(impl, NULL))); + fail_if(impl_class != base); + fail_if(strcmp(eolian_function_name_get(impl_func), "constructor")); eina_iterator_free(iter); @@ -285,6 +262,8 @@ START_TEST(eolian_ctor_dtor) /* Base ctor/dtor */ fail_if(!(iter = eolian_class_implements_get(class))); fail_if(!(eina_iterator_next(iter, (void**)&impl))); + fail_if(!(eina_iterator_next(iter, (void**)&impl))); + fail_if(!(eina_iterator_next(iter, (void**)&impl))); fail_if(!(impl_class = eolian_implement_class_get(impl))); fail_if(!(impl_func = eolian_implement_function_get(impl, NULL))); fail_if(impl_class != base);