eolian: disallow pure virtual on non-abstract/mixin classes
authorDaniel Kolesa <d.kolesa@samsung.com>
Thu, 17 Jan 2019 16:13:55 +0000 (17:13 +0100)
committerJunsuChoi <jsuya.choi@samsung.com>
Thu, 24 Jan 2019 05:20:18 +0000 (14:20 +0900)
src/lib/eolian/database_validate.c
src/lib/eolian/eo_parser.c
src/tests/eolian/data/base.eo
src/tests/eolian/data/nmsp1_nmsp11_class2.eo
src/tests/eolian/data/object_impl.eo
src/tests/eolian/data/override.eo
src/tests/eolian/data/override_ref.c

index 69e71ae..61fa18e 100644 (file)
@@ -13,7 +13,6 @@ typedef struct _Validate_State
    Eina_Bool warned;
    Eina_Bool event_redef;
    Eina_Bool unimplemented;
-   Eina_Bool pure_virtual;
 } Validate_State;
 
 static Eina_Bool
@@ -408,48 +407,6 @@ _validate_function(Validate_State *vals, Eolian_Function *func, Eina_Hash *nhash
    if (!_validate_doc(func->set_return_doc))
      return EINA_FALSE;
 
-   if (!vals->pure_virtual)
-     goto final;
-
-   Eolian_Implement *impl = func->impl;
-
-   /* pure virtual methods are ok for abstracts/mixins as well as ifaces
-    * in ifaces they are implicit, in regulars and abstracts explicit
-    */
-   if (!impl || (impl->klass->type != EOLIAN_CLASS_REGULAR))
-     goto final;
-
-   if (func->type == EOLIAN_METHOD && impl->get_pure_virtual)
-     {
-        _eo_parser_log(&func->base,
-          "pure virtual function '%s' in a non-abstract class '%s'",
-          func->base.name, impl->implklass->base.name);
-        return EINA_FALSE;
-     }
-   else if (func->type == EOLIAN_PROPERTY &&
-            impl->get_pure_virtual && impl->set_pure_virtual)
-     {
-        _eo_parser_log(&func->base,
-          "pure virtual property '%s' in a non-abstract class '%s'",
-          func->base.name, impl->implklass->base.name);
-        return EINA_FALSE;
-     }
-   else if (impl->get_pure_virtual)
-     {
-        _eo_parser_log(&func->base,
-          "pure virtual getter '%s' in a non-abstract class '%s'",
-          func->base.name, impl->implklass->base.name);
-        return EINA_FALSE;
-     }
-   else if (impl->set_pure_virtual)
-     {
-        _eo_parser_log(&func->set_base,
-          "pure virtual setter '%s' in a non-abstract class '%s'",
-          func->base.name, impl->implklass->base.name);
-        return EINA_FALSE;
-     }
-
-final:
    /* just for now, when dups become errors there will be no need to check */
    if (!oobj && nhash)
      eina_hash_add(nhash, &func->base.name, &func->base);
@@ -1262,8 +1219,7 @@ database_validate(const Eolian_Unit *src)
    Validate_State vals = {
       EINA_FALSE,
       !!getenv("EOLIAN_EVENT_REDEF_WARN"),
-      !!getenv("EOLIAN_CLASS_UNIMPLEMENTED_WARN"),
-      !!getenv("EOLIAN_PURE_VIRTUAL_WARN")
+      !!getenv("EOLIAN_CLASS_UNIMPLEMENTED_WARN")
    };
 
    /* do an initial pass to refill inherits */
index 172df12..0ea2944 100644 (file)
@@ -1017,6 +1017,13 @@ parse_params(Eo_Lexer *ls, Eina_List **params, Eina_Bool allow_inout,
 }
 
 static void
+check_abstract_pure_virtual(Eo_Lexer *ls)
+{
+   if ((ls->klass->type != EOLIAN_CLASS_ABSTRACT) && (ls->klass->type != EOLIAN_CLASS_MIXIN))
+     eo_lexer_syntax_error(ls, "@pure_virtual only allowed in abstract classes or mixins");
+}
+
+static void
 parse_accessor(Eo_Lexer *ls, Eolian_Function *prop)
 {
    int line, col;
@@ -1047,8 +1054,7 @@ parse_accessor(Eo_Lexer *ls, Eolian_Function *prop)
    for (;;) switch (ls->t.kw)
      {
       case KW_at_pure_virtual:
-        if (ls->klass->type == EOLIAN_CLASS_INTERFACE)
-          eo_lexer_syntax_error(ls, "@pure_virtual is implicit in interfaces");
+        check_abstract_pure_virtual(ls);
         CASE_LOCK(ls, virtp, "pure_virtual qualifier");
         if (is_get) prop->impl->get_pure_virtual = EINA_TRUE;
         else prop->impl->set_pure_virtual = EINA_TRUE;
@@ -1222,8 +1228,7 @@ parse_property(Eo_Lexer *ls)
         eo_lexer_get(ls);
         break;
       case KW_at_pure_virtual:
-        if (ls->klass->type == EOLIAN_CLASS_INTERFACE)
-          eo_lexer_syntax_error(ls, "@pure_virtual is implicit in interfaces");
+        check_abstract_pure_virtual(ls);
         CASE_LOCK(ls, virtp, "pure_virtual qualifier");
         eo_lexer_get(ls);
         break;
@@ -1393,8 +1398,7 @@ parse_method(Eo_Lexer *ls)
         eo_lexer_get(ls);
         break;
       case KW_at_pure_virtual:
-        if (ls->klass->type == EOLIAN_CLASS_INTERFACE)
-          eo_lexer_syntax_error(ls, "@pure_virtual is implicit in interfaces");
+        check_abstract_pure_virtual(ls);
         CASE_LOCK(ls, virtp, "pure_virtual qualifier");
         eo_lexer_get(ls);
         break;
index 1576573..4f1b93d 100644 (file)
@@ -1,4 +1,4 @@
-class Base {
+abstract Base {
    methods {
       @property z {
            values {
index 13750e5..40c7b85 100644 (file)
@@ -1,4 +1,4 @@
-class nmsp1.nmsp11.class2
+abstract nmsp1.nmsp11.class2
 {
    methods {
       @property a {
index e646a70..9cbaed4 100644 (file)
@@ -1,4 +1,4 @@
-class Object_Impl extends Base {
+abstract Object_Impl extends Base {
    methods {
       @property a {
          set {
index 440dc21..221e12f 100644 (file)
@@ -1,4 +1,4 @@
-class Override extends Base {
+abstract Override extends Base {
    methods {
       @property a {
          set @pure_virtual {
index a4b0c90..c177272 100644 (file)
@@ -92,7 +92,7 @@ _override_class_initializer(Efl_Class *klass)
 static const Efl_Class_Description _override_class_desc = {
    EO_VERSION,
    "Override",
-   EFL_CLASS_TYPE_REGULAR,
+   EFL_CLASS_TYPE_REGULAR_NO_INSTANT,
    sizeof(Override_Data),
    _override_class_initializer,
    NULL,