diff options
43 files changed, 1339 insertions, 0 deletions
diff --git a/src/scripts/pyolian/pyratemp.py b/src/scripts/pyolian/pyratemp.py index c28e260b4b..1ddfb773fc 100644 --- a/src/scripts/pyolian/pyratemp.py +++ b/src/scripts/pyolian/pyratemp.py @@ -846,6 +846,8 @@ class EvalPseudoSandbox: "complex" : builtins.complex, "dict" : builtins.dict, "enumerate" : builtins.enumerate, + "filter" : builtins.filter, + "next" : builtins.next, "float" : builtins.float, "int" : builtins.int, "list" : builtins.list, diff --git a/src/scripts/testgen/README.md b/src/scripts/testgen/README.md new file mode 100644 index 0000000000..4531f636db --- /dev/null +++ b/src/scripts/testgen/README.md @@ -0,0 +1,146 @@ + +Testgen: Template-based Eolian tests generator +=============================================================================== + +Testgen is a Python Script using the Pyolian to generate tests rendering +templates with custom files, this can be a easy way to expand the +API test coveraged. + +Testgen can generate tests C and to other bingings languages only +adding new language specialized templates. + +Installation +============ + +There is nothing to install to use the generator, everything is included in +the efl source tree and it is intended to work directly inside the tree, +usually at efl tests compilation time (make check). + +The only requirement is that **the source tree must be already built** (not +installed) because pyolian search the eolian .so/.dll inside the source tree. + +If you built the efl tree in a custom location (fe, you build out-of-tree) you +can tell pyolian where to find the built eolian .so files using the +`EOLIAN_SO_DIR` environment variable. + + +Command line usage +================== + +The simplest way to use the generator is from the command line, using the +`src/scripts/testgen/testgen.py` command, the `--help` option state: + +``` +usage: testgen.py [-h] testname suitename filename [eofiles [eofiles ...]] + +Eolian Test Generator. + +positional arguments: + testname The Test Name used to find custom and template files. (REQUIRED) + suitename The Suite Name used to find custom files. (REQUIRED) + filename Generated test file destination. (REQUIRED) + eofiles The Eolian Files to use. + +optional arguments: + -h, --help show this help message and exit +``` +Use .c extension in <filename> to generate C tests or .cs to CSharp + +To test this generator in `src/scripts/testgen` you can run: +``` +./testgen.py automated efl efl_automated_test.c efl_loop.eo +``` +This will rendere the automated tests using files in `src/tests/automated` with +suite name `efl_automated` and with Efl.Loop Class as Test Case +`efl_automated_efl_loop_test` + +or run: +``` +./testgen.py automated eio eio_automated_test.c eio_sentry.eo eio_model.eo +``` +This will rendere with suite name `eio_automated` and with Eio.Sentry and +Eio.Model Class as Test Cases `eio_automated_eio_sentry_test` and +`eio_automated_eio_model_test` + + +How customise a Generated Test +============================== + +Testgen use the filesystem to find custom files if you need customise a test, +add/write follow files in src/tests: + + Suite custom files + * `src/test/<testname>/` + |-> <suitename>_custom.c #add include files, functions or structs + |-> <suitename>_init.c #add code in SUITE_INIT + |-> <suitename>_shutdown.c #add code in SUITE_SHUTDOWN + + Class Test case custom files + * `src/test/<testname>/<class_name>/` #use lowercase and `_` separator + |-> custom.c #add include files, functions or structs + |-> init.c #add default way to create the object of this class + |-> shutdown.c #add default way to free the object + +Funtions Tests +- Tests methodes custom files + * `src/test/<testname>/<class_name>/<method_name>` + |-> arg_init.c #initialize method arguments (arg_<argument_name>) + |-> init.c #add how to create the object (replace default) + |-> arg_shutdown.c #free arguments + |-> shutdown.c #add how to free the object (replace default) + +- Tests properties custom files + * `src/test/<testname>/<class_name>/<property_name>` + | -- Property Get -- + |-> arg_get_init.c #initialize property get arguments (arg_<argument_name>) + |-> get_init.c #how to create the object (replace default) + |-> arg_get_shutdown.c #free arguments + |-> get_shutdown.c #how to free the object (replace default) + | -- Property Set -- + |-> arg_set_init.c #initialize propety set arguments (arg_<argument_name>) + |-> set_init.c #how to create the object (replace default) + |-> arg_set_shutdown.c #free arguments + |-> set_shutdown.c #how to free the object (replace default) + +Event Tests +- Tests Events custom files + * `src/test/<testname>/<class_name>/<event_name>/` + |-> init.cs #add how to initialize the objects + |-> custom.cs #add customizations in callback + |-> shutdown.cs #add shutdown or any method to call the event + +to make some custom files you only need a code using: + `parent` -> default name of parent object defined as `Eo *` + `obj` -> default name of current object + `arg_<name>` -> replace <name> with functions arguments name + +you can use custom.c (suite or class) to add specilized code, structs and callbacks + +-- Use `*.cs` to Emono/CSharp generated code -- + +Some class or function test don't need a test in some Suite, you can disable test generated +of it with a blank file as following: + +use lowercase and `_` as separator +`src/test/<testname>/<class_name>` #don't generate test for <class_name> +`src/test/<testname>/<class_name>/method_name` #don't generate test for <method_name> +`src/test/<testname>/<class_name>/<property_name>` #don't generate test for this property +`src/test/<testname>/<class_name>/<property_name>_get` #don't generate test for this property get +`src/test/<testname>/<class_name>/<property_name>_set` #don't generate test for this property set + + +Where to find more info +======================= + + * read the Pyolian README file in EFL scripts + * read the eolian.py file (it declare the full eolian API) + * read the generator.py file (it's super simple) + * read the original [pyratemp docs](https://www.simple-is-better.org/template/pyratemp.html) + + +Note +==== + +This markdown file is mirrored in efl src tree (src/scripts/pyolian) and in +phab wiki (phab.enlightenment.org/w/pyolian). Don't forget to update the other +if you change one! diff --git a/src/scripts/testgen/__init__.py b/src/scripts/testgen/__init__.py new file mode 100644 index 0000000000..e69de29bb2 --- /dev/null +++ b/src/scripts/testgen/__init__.py diff --git a/src/scripts/testgen/ekeys.py b/src/scripts/testgen/ekeys.py new file mode 100644 index 0000000000..42d9889f8d --- /dev/null +++ b/src/scripts/testgen/ekeys.py @@ -0,0 +1,272 @@ +#!/usr/bin/env python3 +# encoding: utf-8 +from enum import IntEnum, IntFlag + +from testgen import name_helpers + + +class Function_List_Type(IntFlag): + OWN = 1 + IMPLEMENTS = 2 # Overrides + EXTENSIONS = 4 # Interfaces/Mixins + INHERITED = 8 # Inherited but not overriden methods and classes + INHERITS_FULL = 4 & 8 + + +class EKeys: + def __init__(self, ext): + self.ext = ext + self.dicttypes = {} + self.keywords = [] + self.verbs = [] + self.blacklist = ["efl_constructor"] + self.keyloads = ["init", "shutdown", "custom"] + self.implementsbl = ["construtor", "destructor", "finalize"] + self.funclist = Function_List_Type.OWN | Function_List_Type.IMPLEMENTS + + def type_convert(self, eotype): + return eotype.name + + def event_convert(self, event): + return event.c_macro + + def print_arg(self, eoarg): + return "arg_{}".format(eoarg.name) + + def format_name(self, func): + return self.name + + +class EMonoKeys(EKeys): + def __init__(self, ext): + super().__init__(ext) + self.funclist = ( + Function_List_Type.OWN + | Function_List_Type.IMPLEMENTS + | Function_List_Type.EXTENSIONS + ) + self.dicttypes = { + "byte": "sbyte", + "llong": "long", + "int8": "sbyte", + "int16": "short", + "int32": "int", + "int64": "long", + "ssize": "long", + "ubyte": "byte", + "ullong": "ulong", + "uint8": "byte", + "uint16": "ushort", + "uint32": "uint", + "uint64": "ulong", + "size": "ulong", + "ptrdiff": "long", + "intptr": "System.IntPtr", + "uintptr": "System.IntPtr", + "void_ptr": "System.IntPtr", + "void": "System.IntPtr", # only if is out/inout + "Error": "Eina.Error", + "string": "System.String", + "mstring": "System.String", + "stringshare": "System.String", + "any_value": "Eina.Value", + "any_value_ptr": "Eina.Value" + # complex Types + , + "list": "Eina.List", + "inlist": "Eina.Inlist", + "array": "Eina.Array", + "inarray": "Eina.Inarray", + "hash": "Eina.Hash", + "promise": "int", + "future": "int", + "iterator": "Eina.Iterator", + "accessor": "Eina.Accessor", + "strbuf": "Eina.Strbuf", + "Efl.Class": "System.Type", + "rw_slice": "Eina.RwSlice", + "slice": "Eina.Slice", + } + + self.keywords = [ + "delete", + "do", + "lock", + "event", + "in", + "object", + "interface", + "string", + "internal", + "fixed", + "base", + ] + + self.verbs = [ + "add", + "get", + "is", + "del", + "thaw", + "freeze", + "save", + "wait", + "eject", + "raise", + "lower", + "load", + "dup", + "reset", + "unload", + "close", + "set", + "interpolate", + "has", + "grab", + "check", + "find", + "ungrab", + "unset", + "clear", + "pop", + "new", + "peek", + "push", + "update", + "show", + "move", + "hide", + "calculate", + "resize", + "attach", + "pack", + "unpack", + "emit", + "call", + "append", + ] + + self.blacklist = [ + "efl_event_callback_array_priority_add", + "efl_event_callback_forwarder_priority_add", + "efl_player_position_get", + "efl_text_font_source", + "efl_ui_focus_manager_focus_get", + "efl_ui_widget_focus", + "efl_ui_text_password", + "elm_interface_scrollable_repeat_events", + "elm_wdg_item_del", + "elm_wdg_item_focus", + "elm_interface_scrollable_mirrored_set", + "evas_obj_table_mirrored", + "edje_obj_load_error_get", + "efl_ui_focus_user_parent_get", + "efl_canvas_object_scale", # duplicated signature + "efl_access_parent_get", + "efl_access_name", + "efl_access_root_get", + "efl_access_type_get", + "efl_access_role_get", + "efl_access_action_description", + "efl_access_image_description", + "efl_access_component_layer_get", # duplicated signature + "efl_access_component_alpha_get", + "efl_access_component_size_get", + "efl_ui_spin_button_loop_get", + "efl_ui_list_model_size_get", + "efl_ui_list_relayout_layout_do", + "efl_constructor", + ] + + self.struct_blacklist = [ + "Efl.Event_Description", + "Eina.Binbuf", + "Eina.Strbuf", + "Eina.Slice", + "Eina.Rw_Slice", + "Eina.Promise", + "Eina.Value", + "Eina.Value_Type", + "Eina.Future", + ] + + def escape_keyword(self, key): + key = "kw_{}".format(key) if key in self.keywords else key + return "{}Add".format(key) if key == "Finalize" else key + + def direction_get(self, param): + direction = param.direction + + if direction == direction.INOUT: + return "ref" + elif direction != direction.IN: + if param.type.name in ("slice", "rw_slice"): + return "ref" + else: + return "out" + elif (direction == direction.IN) and param.type.is_ptr: + if param.type.typedecl and ( + param.type.typedecl.type == param.type.typedecl.type.STRUCT + ): + return "ref" if param.type.name not in self.struct_blacklist else None + + return None + + def klass_name(self, eotype): + *namespaces, name = eotype.name.split(".") + namespaces = [self.escape_keyword(x.lower()) for x in namespaces] + is_interface = eotype.type == eotype.type.CLASS + k_name = ("I" if is_interface else "") + name + return ".".join(namespaces + [k_name]) + + def type_convert(self, eotype): + if eotype.type == eotype.type.VOID: + return "System.IntPtr" + + new_type = self.dicttypes.get( + eotype.name, name_helpers.type_managed_name(eotype) + ) + if new_type not in ("Eina.RwSlice", "Eina.Slice") and eotype.base_type: + # Stringshare is a special case where its C# type differs if inside or outside + # a container: + # - Non-contained stringshares are directly converted to strings. + # - Contained stringshares are kept as the container parameter as a tag to + # marshal the value correctly whem adding/removing items from the container. + if eotype.base_type.name == "stringshare": + base_type = "Eina.Stringshare" + else: + base_type = self.dicttypes.get( + eotype.base_type.name, + name_helpers.type_managed_name(eotype.base_type), + ) + new_type = "{}<{}>".format(new_type, base_type) + + return new_type + + def event_convert(self, event): + return "{}Evt".format("".join([i.capitalize() for i in event.name.split(",")])) + + def print_arg(self, eoarg): + r = super().print_arg(eoarg) + prefix = self.direction_get(eoarg) or None + + return " ".join([prefix, r]) if prefix else r + + def format_name(self, func): + names = func.comp.name.split("_") + + if func.type == func.type.METHOD and names[-1] in self.verbs: + names.insert(0, names.pop()) + + fname = "".join([name.capitalize() for name in names]) + + if func.type == func.type.METHOD: + fname = self.escape_keyword(fname) + + return fname + + +def GetKey(ext): + if ext == ".cs": + return EMonoKeys(ext) + return EKeys(ext) diff --git a/src/scripts/testgen/name_helpers.py b/src/scripts/testgen/name_helpers.py new file mode 100644 index 0000000000..e03ad23a41 --- /dev/null +++ b/src/scripts/testgen/name_helpers.py @@ -0,0 +1,92 @@ +#!/usr/bin/env python3 +# encoding: utf-8 + +"""Helper module with naming rules for the C# binding.""" + +import os +import sys + +# Hackish way of detecting pyolian... +script_path = os.path.dirname(os.path.realpath(__file__)) + +if "EFL_DIR" in os.environ: + root_path = os.environ["EFL_DIR"] +else: + root_path = os.path.abspath(os.path.join(script_path, "..", "..", "..")) + +sys.path.insert(0, os.path.join(root_path, "src", "scripts")) + +from pyolian import eolian + + +def remove_underlines(name): + """Removes underlines from name""" + return name.replace("_", "") + + +def managed_name(name): + """Replaces underlines and capitalize first letter of each word""" + + words = name.split("_") + return "".join(word[0].upper() + word[1:] for word in words) + + +def managed_namespaces(namespaces): + """Converts an eolian list of namespaces into the managed namespace""" + return ".".join(remove_underlines(nsp) for nsp in namespaces) + + +def class_managed_name(cls): + """Gets the full managed name of the given eolian class""" + ret = managed_namespaces(cls.namespaces) + + if ret: + ret += "." + + if cls.type in (eolian.Eolian_Class_Type.INTERFACE, eolian.Eolian_Class_Type.MIXIN): + ret += "I" + + ret += remove_underlines(cls.short_name) + + if ret == "Efl.Class": + return "System.Type" + + return ret + + +def type_managed_name(type): + """Gets the full managed name of a given type.""" + if type.type == eolian.Eolian_Type_Type.CLASS: + return class_managed_name(type.class_) + + ret = managed_namespaces(type.namespaces) + + if ret: + ret += "." + + ret += remove_underlines(type.short_name) + + return ret + + +# Need to pass the class as it is not accessible from Event in Pyolian +def event_args_managed_name(event, cls): + """Gets the full managed name of the event arguments struct""" + if event.type is None: + return "System.EventArgs" + + ret = class_managed_name(cls) + + return ret + managed_name(event.myname) + "Evt_Args" + + +def event_managed_short_name(event): + """Gets the managed short name of an event""" + + return managed_name(event.name.replace(",", "_")) + "Evt" + + +def enum_field_managed_name(field): + """Gets the managed name of an Enum field""" + + return managed_name(field.name) diff --git a/src/scripts/testgen/suitegen.py b/src/scripts/testgen/suitegen.py new file mode 100644 index 0000000000..5551eabf8e --- /dev/null +++ b/src/scripts/testgen/suitegen.py @@ -0,0 +1,291 @@ +import itertools +import os +from pyolian.eolian import Eolian_Function_Type, Eolian_Class_Type, Eolian_Object_Scope +from .ekeys import GetKey, Function_List_Type +from pyolian import eolian + +from testgen import name_helpers + + +class BaseItem: + def __init__(self, path, keys, prefix=""): + self.path = path + self.keys = keys + self.prefix = prefix + + def __getattr__(self, attr): + if not attr.split("_")[-1] in self.keys.keyloads: + raise AttributeError("Error getting {}".format(attr)) + + filename = os.path.join(self.path, self.prefix + attr) + self.keys.ext + if os.path.isfile(filename): + with open(filename, "r") as f: + return f.read() + return None + + +class ComItem(BaseItem): + def __init__(self, comp, path, keys): + super().__init__(path, keys) + self.comp = comp + + def __getattr__(self, attr): + if hasattr(self.comp, attr): + return getattr(self.comp, attr) + return super().__getattr__(attr) + + +class FuncItem(ComItem): + def __init__(self, comp, path, keys): + super().__init__(comp, os.path.join(path, comp.name), keys) + + self.has_getter = ( + comp.type in (Eolian_Function_Type.PROP_GET, Eolian_Function_Type.PROPERTY) + and comp.full_c_getter_name not in keys.blacklist + and comp.getter_scope == Eolian_Object_Scope.PUBLIC + and not os.path.isfile("{}_get".format(os.path.join(path, comp.name))) + ) + self.has_setter = ( + comp.type in (Eolian_Function_Type.PROP_SET, Eolian_Function_Type.PROPERTY) + and comp.full_c_setter_name not in keys.blacklist + and comp.setter_scope == Eolian_Object_Scope.PUBLIC + and not os.path.isfile("{}_set".format(os.path.join(path, comp.name))) + ) + + self.is_enum = ( + lambda arg: arg.type + and arg.type.typedecl + and arg.type.typedecl.type == arg.type.typedecl.type.ENUM + ) + self.is_number = lambda arg: arg.type and arg.type.builtin_type in ( + arg.type.builtin_type.INT, + arg.type.builtin_type.UINT, + arg.type.builtin_type.LONG, + arg.type.builtin_type.ULONG, + arg.type.builtin_type.LLONG, + arg.type.builtin_type.ULLONG, + arg.type.builtin_type.INT8, + arg.type.builtin_type.UINT8, + arg.type.builtin_type.INT16, + arg.type.builtin_type.UINT16, + arg.type.builtin_type.INT32, + arg.type.builtin_type.UINT32, + arg.type.builtin_type.INT64, + arg.type.builtin_type.UINT64, + arg.type.builtin_type.INT128, + arg.type.builtin_type.UINT128, + ) + + @property + def getter_args(self): + return itertools.chain(self.getter_values, self.getter_keys) + + @property + def setter_args(self): + return itertools.chain(self.setter_values, self.setter_keys) + + @property + def format_name(self): + return self.keys.format_name(self) + + +class EventItem(ComItem): + def __init__(self, comp, path, keys): + self.myname = comp.name.replace(",", "_") + super().__init__(comp, os.path.join(path, self.myname), keys) + self.format_name = self.keys.event_convert(self) + + +class ClassItem(ComItem): + def __init__(self, comp, path, keys): + self.myname = os.path.splitext(comp.file)[0] + super().__init__(comp, os.path.join(path, self.myname), keys) + + def mfilter(f): + if f.full_c_method_name in self.keys.blacklist: + return False + + if os.path.isfile(os.path.join(self.path, f.name)): + return False + + if f.type == Eolian_Function_Type.PROPERTY: + if f.getter_scope != Eolian_Object_Scope.PUBLIC: + scope = f.setter_scope + else: + scope = f.getter_scope + else: + scope = f.scope_get(f.type) + + if scope != Eolian_Object_Scope.PUBLIC: + return False + + return True + + if self.keys.funclist & Function_List_Type.OWN: + self._methods = { + m.name: FuncItem(m, self.path, keys) + for m in self.comp.methods + if mfilter(m) + } + self._properties = { + p.name: FuncItem(p, self.path, keys) + for p in self.comp.properties + if mfilter(p) + } + self._events = { + e.name: EventItem(e, self.path, keys) for e in self.comp.events + } + else: + self._methods = {} + self._properties = {} + self._events = {} + + if self.keys.funclist & Function_List_Type.IMPLEMENTS: + for imp in comp.implements: + + if ( + imp.namespace == self.name + or imp.short_name.lower() in self.keys.implementsbl + ): + continue + + f = imp.function + + if not mfilter(f): + continue + + if f.type == Eolian_Function_Type.METHOD: + if f.name in self._methods: + continue + self._methods[f.name] = FuncItem(f, self.path, keys) + elif f.type in ( + Eolian_Function_Type.PROPERTY, + Eolian_Function_Type.PROP_GET, + Eolian_Function_Type.PROP_SET, + ): + if f.name in self._properties: + continue + self._properties[f.name] = FuncItem(f, self.path, keys) + + parents = [] + + if self.keys.funclist & Function_List_Type.INHERITS_FULL: + # Use inherits full to get inherited interfaces too + parents = self.comp.inherits_full + else: + if self.keys.funclist & Function_List_Type.EXTENSIONS: + parents = self.comp.extensions_hierarchy + + if self.keys.funclist & Function_List_Type.INHERITED: + if parents: + parents = itertools.chain(self.comp.hierarchy, parents) + else: + parents = self.comp.hierarchy + + for eoclass in parents: + for f in filter(mfilter, eoclass.methods): + if f.name in self._methods: + continue + self._methods[f.name] = FuncItem(f, self.path, keys) + for f in filter(mfilter, eoclass.properties): + if f.name in self._properties: + continue + self._properties[f.name] = FuncItem(f, self.path, keys) + + @property + def properties(self): + return filter(lambda p: p.has_setter or p.has_getter, self._properties.values()) + + @property + def properties_get(self): + return filter(lambda p: p.has_getter, self._properties.values()) + + @property + def properties_set(self): + return filter(lambda p: p.has_setter, self._properties.values()) + + @property + def methods(self): + return self._methods.values() + + @property + def events(self): + return self._events.values() + + def __iter__(self): + return itertools.chain(self.methods, self.properties) + + +class SuiteGen(BaseItem): + def __init__(self, name, testname, filename, path, template=None): + keys = GetKey(os.path.splitext(filename)[1]) + super().__init__(path, keys, name + "_") + self.name = name + self.testname = testname + self.fullname = "_".join([name, testname]) if testname else name + self.filename = filename + self.template = template + self.clslist = [] + + if not self.template: + script_path = os.path.dirname(os.path.realpath(__file__)) + self.template = os.path.join( + script_path, "testgenerator{}.template".format(self.keys.ext) + ) + + def __iter__(self): + return iter(self.clslist) + + def type_convert(self, eotype): + if eotype.type == eolian.Eolian_Type_Type.CLASS: + return name_helpers.class_managed_name(eotype.class_) + + if eotype.typedecl: + return name_helpers.type_managed_name(eotype) + + return self.keys.type_convert(eotype) + + def constructor_params(self, cls): + ret = [] + + constructors = itertools.chain( + cls.constructors, *[base.constructors for base in cls.inherits_full] + ) + + for constructor in constructors: + # Skip optional constructors for now + if constructor.is_optional: + continue + func = constructor.function + + if func.type == eolian.Eolian_Function_Type.PROPERTY: + first_param = list(func.setter_values)[0] + else: + first_param = list(func.parameters)[0] + param_type = first_param.type + + ret.append("default({})".format(name_helpers.type_managed_name(param_type))) + + return (", " if ret else "") + ", ".join(ret) + + def print_arg(self, eoarg): + return self.keys.print_arg(eoarg) + + def intersect(self, a, b): + return list(set(a) & set(b)) + + def loadFiles(self, eolian_db, eofiles): + self.clslist.clear() + for eofile in eofiles: + eocls = eolian_db.class_by_file_get(os.path.basename(eofile)) + if not eocls or eocls.type != Eolian_Class_Type.REGULAR: + continue + self.loadObj(eocls) + + def loadObj(self, eocls): + cls = ClassItem(eocls, self.path, self.keys) + if not os.path.isfile(cls.path): + cls.myfullname = "{}_{}".format(self.fullname, cls.myname) + self.clslist.append(cls) + else: + print("removing {} Class from generated list".format(cls.name)) diff --git a/src/scripts/testgen/testgen.py b/src/scripts/testgen/testgen.py new file mode 100755 index 0000000000..24ec00195e --- /dev/null +++ b/src/scripts/testgen/testgen.py @@ -0,0 +1,125 @@ +#!/usr/bin/env python3 +# encoding: utf-8 + +import os +import sys +import datetime + + +script_path = os.path.dirname(os.path.realpath(__file__)) + +if "EFL_DIR" in os.environ: + root_path = os.environ["EFL_DIR"] +else: + root_path = os.path.abspath(os.path.join(script_path, "..", "..", "..")) + +sys.path.insert(0, os.path.join(root_path, "src", "scripts")) + +from pyolian import eolian +from pyolian import pyratemp +from testgen.suitegen import SuiteGen +from testgen import name_helpers + +# Use .eo files from the source tree (not the installed ones) +SCAN_FOLDER = os.path.join(root_path, "src", "lib") + +# create main eolian state +eolian_db = eolian.Eolian_State() +if not isinstance(eolian_db, eolian.Eolian_State): + raise (RuntimeError("Eolian, failed to create Eolian state")) + +# eolian source tree scan +if not eolian_db.directory_add(SCAN_FOLDER): + raise (RuntimeError("Eolian, failed to scan source directory")) + +# Parse all known eo files +if not eolian_db.all_eot_files_parse(): + raise (RuntimeError("Eolian, failed to parse all EOT files")) + +if not eolian_db.all_eo_files_parse(): + raise (RuntimeError("Eolian, failed to parse all EO files")) + +# cleanup the database on exit +import atexit + + +def cleanup_db(): + global eolian_db + del eolian_db + + +atexit.register(cleanup_db) + + +class Template(pyratemp.Template): + def __init__( + self, + filename, + encoding="utf-8", + loader_class=pyratemp.LoaderFile, + parser_class=pyratemp.Parser, + renderer_class=pyratemp.Renderer, + eval_class=pyratemp.EvalPseudoSandbox, + ): + + global_ctx = {} + global_ctx.update( + { + # Template info + "date": datetime.datetime.now(), + "template_file": os.path.basename(filename), + } + ) + + self.template_filename = filename + pyratemp.Template.__init__( + self, + filename=filename, + encoding=encoding, + data=global_ctx, + loader_class=loader_class, + parser_class=parser_class, + renderer_class=renderer_class, + eval_class=eval_class, + ) + + def render(self, suite, verbose=True): + # Build the context for the template + ctx = {} + ctx["suite"] = suite + ctx["name_helpers"] = name_helpers + # render with the augmented context + output = self(**ctx) + + if suite.filename is not None: + # write to file + with open(suite.filename, "w") as f: + f.write(output) + + +if __name__ == "__main__": + import argparse + + parser = argparse.ArgumentParser(description="Eolian Test Generator.") + parser.add_argument( + "testname", + help="The Test Name used to find custom and template files. (REQUIRED)", + ) + parser.add_argument( + "suitename", help="The Suite Name used to find custom files. (REQUIRED)" + ) + parser.add_argument("filename", help="Generated test file destination. (REQUIRED)") + parser.add_argument("eofiles", nargs="*", help="The Eolian Files to use.") + + args = parser.parse_args() + + testdir = os.path.join(root_path, "src", "tests", args.testname) + + suite = SuiteGen(args.suitename, args.testname, args.filename, testdir) + suite.loadFiles(eolian_db, args.eofiles) + + t = Template(suite.template) + # try: + t.render(suite) +# except: +# print("ERROR RENDERING - Cannot create file: {}".format(suite.filename)) diff --git a/src/scripts/testgen/testgenerator.c.template b/src/scripts/testgen/testgenerator.c.template new file mode 100644 index 0000000000..99fc76d596 --- /dev/null +++ b/src/scripts/testgen/testgenerator.c.template @@ -0,0 +1,187 @@ +<!--(macro m_show)--> + <!--(if mshow)--> +${mshow}$#! + <!--(end)--> +<!--(end)--> +<!--(macro init)--> + Eo *parent = NULL; + Eo *obj = NULL; + + <!--(if exists("mfunc") and mfunc!= None)--> +${mfunc}$ + <!--(elif exists("mcls") and mcls!= None)--> +${mcls}$ + <!--(else)--> + obj = efl_add_ref(${cls.c_macro}$, parent); + fail_if(!obj, "ERROR: Cannot init ${cls.name}$!\n"); + <!--(end)--> +<!--(end)--> +<!--(macro shutdown)--> + /** shutdown **/ + <!--(if exists("mfunc") and mfunc != None)--> +${mfunc}$ + <!--(elif exists("mcls") and mcls != None)--> +${mcls}$ + <!--(end)--> + efl_unref(obj); +<!--(end)--> +<!--(macro arg_default)--> + <!--(if arg.type.name == "__builtin_free_cb" or arg.type.is_ptr or arg.type.type == arg.type.type.CLASS or arg.type.builtin_type == arg.type.builtin_type.STRING)-->NULL<!--(elif arg.type.builtin_type == arg.type.builtin_type.ANY_VALUE)-->EINA_VALUE_EMPTY<!--(elif arg.type.typedecl and arg.type.typedecl.type == arg.type.typedecl.type.STRUCT )-->{}<!--(else)-->0<!--(end)-->; +<!--(end)--> +<!--(macro args_declaration)--> + <!--(for arg in args)--> + <!--(if arg.type.typedecl and arg.type.typedecl.type == arg.type.typedecl.type.FUNCTION_POINTER)--> + void * arg_${arg.name}$_data = NULL; + ${arg.type.c_type_param}$ arg_${arg.name}$ = NULL; + Eina_Free_Cb arg_${arg.name}$_free_cb = NULL; + <!--(else)--> + ${arg.type.c_type_param}$ arg_${arg.name}$ = ${arg_default(arg=arg)}$ + <!--(end)--> + <!--(end)--> +<!--(end)--> +<!--(macro print_arg)--> + <!--(if arg.type.typedecl and arg.type.typedecl.type == arg.type.typedecl.type.FUNCTION_POINTER)--> +arg_${arg.name}$_data, arg_${arg.name}$, arg_${arg.name}$_free_cb + <!--(else)--> + <!--(if arg.direction in (arg.direction.OUT, arg.direction.INOUT))-->&<!--(end)-->arg_${arg.name}$ + <!--(end)--> +<!--(end)--> +<!--(macro arg_self)--> + <!--(if not func.is_class)--> + obj + <!--(end)--> +<!--(end)--> +<!--(macro print_comma)--> + <!--(if i > 0 or not is_class)--> + , + <!--(end)--> +<!--(end)--> + +#ifdef HAVE_CONFIG_H +# include <config.h> +#endif + +#include <check.h> +#include "efl_check.h" +${m_show(mshow=suite.custom)}$#! +#include <Elementary.h> + +<!--(for cls in suite)--> +void ${cls.myfullname}$_test(TCase *tc); +<!--(end)--> + +static const Efl_Test_Case etc[] = { +<!--(for cls in suite)--> + { "${suite.name.capitalize()}$ ${suite.testname.capitalize()}$ ${cls.myname.capitalize()}$", ${cls.myfullname}$_test }, +<!--(end)--> + { NULL, NULL } +}; + +<!--(for cls in suite)--> + +/**************** TEST CASE ${cls.c_macro}$ ****************/ +${m_show(mshow=cls.custom)}$#! + +START_TEST(${cls.myfullname}$_smoke) +{ +${init(mcls=cls.init)}$ +${shutdown(mcls=cls.shutdown)}$ +} +END_TEST + + <!--(for func in cls.methods)--> +START_TEST(${cls.myfullname}$_${func.full_c_method_name}$) +{ +${args_declaration(args=func.parameters)}$${init(mcls=cls.init,mfunc=func.init)}$ +${m_show(mshow=func.arg_init)}$#! + <!--(if func.method_return_type)-->${func.method_return_type.c_type_return}$ r = <!--(end)-->${func.full_c_method_name}$(${arg_self(func=func)}$<!--(for i, arg in enumerate(func.parameters))-->${print_comma(i=i, is_class=func.is_class)}$${print_arg(arg=arg)}$<!--(end)-->); + <!--(if func.method_return_type)-->(void)r;<!--(end)--> +${m_show(mshow=func.arg_shutdown)}$#! +${shutdown(mcls=cls.shutdown,mfunc=func.shutdown)}$ +} +END_TEST + + <!--(end)--> + + <!--(for func in cls.properties)--> + <!--(if func.has_getter)--> +START_TEST(${cls.myfullname}$_${func.full_c_getter_name}$) +{ + <!--(if len(list(func.getter_values)) > 1)--> +${args_declaration(args=func.getter_values)}$ + <!--(end)--> +${args_declaration(args=func.getter_keys)}$${init(mcls=cls.init,mfunc=func.get_init)}$ +${m_show(mshow=func.arg_get_init)}$#! + <!--(if len(list(func.getter_values)) == 1)--> + ${list(func.getter_values)[0].type.c_type_return}$ r = ${func.full_c_getter_name}$(obj<!--(for arg in func.getter_keys)-->, arg_${arg.name}$<!--(end)-->); + (void)r; + <!--(else)--> + ${func.full_c_getter_name}$(obj<!--(for arg in func.getter_keys)-->, arg_${arg.name}$<!--(end)--><!--(for arg in func.getter_values)-->, &arg_${arg.name}$<!--(end)-->); + <!--(end)--> +${m_show(mshow=func.arg_get_shutdown)}$#! +${shutdown(mcls=cls.shutdown,mfunc=func.get_shutdown)}$ +} +END_TEST + + <!--(end)--> + <!--(if func.has_setter)--> +START_TEST(${cls.myfullname}$_${func.full_c_setter_name}$) +{ +${args_declaration(args=func.setter_keys)}$${args_declaration(args=func.setter_values)}$${init(mcls=cls.init,mfunc=func.set_init)}$ +${m_show(mshow=func.arg_set_init)}$#! + ${func.full_c_setter_name}$(obj<!--(for arg in func.setter_keys)-->, arg_${arg.name}$<!--(end)--><!--(for arg in func.setter_values)-->, arg_${arg.name}$<!--(end)-->); +${m_show(mshow=func.arg_set_shutdown)}$#! +${shutdown(mcls=cls.shutdown,mfunc=func.set_shutdown)}$ +} +END_TEST + + <!--(end)--> + <!--(end)--> +void ${cls.myfullname}$_test(TCase *tc) +{ + tcase_add_test(tc, ${cls.myfullname}$_smoke); + <!--(for func in cls.methods)--> + tcase_add_test(tc, ${cls.myfullname}$_${func.full_c_method_name}$); + <!--(end)--> + <!--(for func in cls.properties_get)--> + tcase_add_test(tc, ${cls.myfullname}$_${func.full_c_getter_name}$); + <!--(end)--> + <!--(for func in cls.properties_set)--> + tcase_add_test(tc, ${cls.myfullname}$_${func.full_c_setter_name}$); + <!--(end)--> +} +<!--(end)--> + +SUITE_INIT(${suite.name}$) +{ + fail_if(!eina_init(), "ERROR: Cannot init Eina!\n"); + fail_if(!ecore_init(), "ERROR: Cannot init Ecore!\n"); + fail_if(!efl_object_init(), "ERROR: Cannot init EO!\n"); +${m_show(mshow=suite.init)}$#! +} + +SUITE_SHUTDOWN(${suite.name}$) +{ +${m_show(mshow=suite.shutdown)}$#! + ecore_shutdown(); + eina_shutdown(); +} + +int +main(int argc, char **argv) +{ + int failed_count; + + if (!_efl_test_option_disp(argc, argv, etc)) + return 0; + +#ifdef NEED_RUN_IN_TREE + putenv("EFL_RUN_IN_TREE=1"); +#endif + + failed_count = _efl_suite_build_and_run(argc - 1, (const char **)argv + 1, + "${suite.fullname}$", etc, SUITE_INIT_FN(${suite.name}$), SUITE_SHUTDOWN_FN(${suite.name}$)); + + return (failed_count == 0) ? 0 : 255; +} + diff --git a/src/scripts/testgen/testgenerator.cs.template b/src/scripts/testgen/testgenerator.cs.template new file mode 100644 index 0000000000..c2085e838d --- /dev/null +++ b/src/scripts/testgen/testgenerator.cs.template @@ -0,0 +1,113 @@ +<!--(macro m_show)--> + <!--(if mshow)--> +${mshow}$#! + <!--(end)--> +<!--(end)--> +<!--(macro def_obj)-->${name_helpers.class_managed_name(param.type.class_)}$ arg_${param.name}$ = null;<!--(end)--> +<!--(macro def_param)--> + <!--(if param.type.type == param.type.type.CLASS)-->${def_obj(param=param)}$<!--(else)-->${suite.type_convert(param.type)}$ arg_${param.name}$ = default(${suite.type_convert(param.type)}$);<!--(end)--> +<!--(end)--> +<!--(macro def_params)--> + <!--(for p in parameters)--> + ${def_param(param=p)}$ + <!--(end)--> +<!--(end)--> +<!--(macro meth_target)--> + <!--(if func.is_class)-->${name_helpers.class_managed_name(cls)}$<!--(else)-->obj<!--(end)--> +<!--(end)--> +using System; + +namespace TestSuite +{ +<!--(if suite.custom)-->${suite.custom}$<!--(end)--> +<!--(for cls in suite)--> +/**************** TEST CASE ${cls.c_macro}$ ****************/ +class Test${cls.name.replace('.','')}$ +{ + + ${name_helpers.class_managed_name(cls)}$ obj; +${m_show(mshow=cls.custom)}$#! + + public void SetUp() + { +${m_show(mshow=suite.init)}$#! + <!--(if cls.init)--> +${cls.init}$ + <!--(else)--> + obj = new ${name_helpers.class_managed_name(cls)}$(null${suite.constructor_params(cls)}$); + <!--(end)--> + } + + public void TearDown() + { +${m_show(mshow=suite.shutdown)}$#! + <!--(if cls.shutdown)--> +${cls.shutdown}$ + <!--(else)--> + obj.Dispose(); + obj = null; + <!--(end)--> + } + + public void smoke() + { + } + +#! METHODS + <!--(for func in cls.methods)--> + public void ${func.name}$() + { + <!--(if len(list(func.parameters)) > 0)--> +${def_params(parameters=func.parameters)}$ + <!--(end)--> +${m_show(mshow=func.arg_init)}$#! +${m_show(mshow=func.init)}$#! + <!--(if func.method_return_type)-->var r = <!--(end)-->${meth_target(func=func, cls=cls)}$.${func.format_name}$(${', '.join([ suite.print_arg(p) for p in func.parameters])}$); +${m_show(mshow=func.arg_shutdown)}$#! +${m_show(mshow=func.shutdown)}$#! + } + + <!--(end)--> +#! PROPERTIES FUNCTION GET + <!--(for func in cls.properties)--> + <!--(if func.has_getter)--> + public void ${func.name}$_pget() + { + <!--(if func.getter_return_type or len(list(func.getter_values)) > 1)--> +${def_params(parameters=func.getter_values)}$ + <!--(end)--> + <!--(if len(list(func.getter_keys)) > 0)--> +${def_params(parameters=func.getter_keys)}$ + <!--(end)--> +${m_show(mshow=func.arg_get_init)}$#! +${m_show(mshow=func.get_init)}$#! + <!--(if not func.getter_return_type and len(list(func.getter_values)) == 1)--> + var arg_${list(func.getter_values)[0].name}$ = ${meth_target(func=func, cls=cls)}$.Get${func.format_name}$(${', '.join(['arg_{}'.format(param.name) for param in func.getter_keys])}$); + <!--(else)--> + <!--(if func.getter_return_type)-->var r = <!--(end)-->${meth_target(func=func, cls=cls)}$.Get${func.format_name}$(${', '.join([suite.print_arg(p) for p in func.getter_keys] + ['out arg_{}'.format(p.name) for p in func.getter_values])}$); + <!--(end)--> +${m_show(mshow=func.arg_get_shutdown)}$#! +${m_show(mshow=func.get_shutdown)}$#! + } + + <!--(end)--> +#! PROPERTIES FUNCTION SET + <!--(if func.has_setter)--> + public void ${func.name}$_pset() + { +${def_params(parameters=func.setter_values)}$ + <!--(if len(list(func.setter_keys)) > 0)--> +${def_params(parameters=func.setter_keys)}$ + <!--(end)--> +${m_show(mshow=func.arg_set_init)}$#! +${m_show(mshow=func.set_init)}$#! + ${meth_target(func=func, cls=cls)}$.Set${func.format_name}$(${', '.join([suite.print_arg(p) for p in list(func.setter_keys) + list(func.setter_values)])}$); +${m_show(mshow=func.arg_set_shutdown)}$#! +${m_show(mshow=func.set_shutdown)}$#! + } + + <!--(end)--> + <!--(end)--> +} +<!--(end)--> +} diff --git a/src/tests/automated/ecore_audio_custom.c b/src/tests/automated/ecore_audio_custom.c new file mode 100644 index 0000000000..538ed42109 --- /dev/null +++ b/src/tests/automated/ecore_audio_custom.c @@ -0,0 +1,3 @@ +#include <Ecore.h> +#include <Ecore_Audio.h> +#include <Ecore_File.h> diff --git a/src/tests/automated/ecore_audio_init.c b/src/tests/automated/ecore_audio_init.c new file mode 100644 index 0000000000..3dd8aecd65 --- /dev/null +++ b/src/tests/automated/ecore_audio_init.c @@ -0,0 +1,2 @@ + int _rinit = ecore_audio_init(); + ck_assert_int_eq(_rinit, 1); diff --git a/src/tests/automated/ecore_audio_out/input_attach/arg_init.c b/src/tests/automated/ecore_audio_out/input_attach/arg_init.c new file mode 100644 index 0000000000..fcebbe029b --- /dev/null +++ b/src/tests/automated/ecore_audio_out/input_attach/arg_init.c @@ -0,0 +1 @@ + arg_input = efl_add(ECORE_AUDIO_IN_CLASS, NULL); diff --git a/src/tests/automated/ecore_audio_out/input_detach/arg_init.c b/src/tests/automated/ecore_audio_out/input_detach/arg_init.c new file mode 100644 index 0000000000..fcebbe029b --- /dev/null +++ b/src/tests/automated/ecore_audio_out/input_detach/arg_init.c @@ -0,0 +1 @@ + arg_input = efl_add(ECORE_AUDIO_IN_CLASS, NULL); diff --git a/src/tests/automated/ecore_audio_out_wasapi/init.c b/src/tests/automated/ecore_audio_out_wasapi/init.c new file mode 100644 index 0000000000..da9426da1e --- /dev/null +++ b/src/tests/automated/ecore_audio_out_wasapi/init.c @@ -0,0 +1,3 @@ +#ifdef _WIN32 + obj = efl_add_ref(ECORE_AUDIO_OUT_WASAPI_CLASS, parent); + fail_if(!obj, "ERROR: Cannot init Ecore.Audio.Out.Wasapi!\n") diff --git a/src/tests/automated/ecore_audio_out_wasapi/shutdown.c b/src/tests/automated/ecore_audio_out_wasapi/shutdown.c new file mode 100644 index 0000000000..23fe0f1229 --- /dev/null +++ b/src/tests/automated/ecore_audio_out_wasapi/shutdown.c @@ -0,0 +1,3 @@ +#else +(void)parent; +#endif diff --git a/src/tests/automated/ector_custom.c b/src/tests/automated/ector_custom.c new file mode 100644 index 0000000000..0ff115b738 --- /dev/null +++ b/src/tests/automated/ector_custom.c @@ -0,0 +1,3 @@ +#include <cairo/Ector_Cairo.h> +#include <software/Ector_Software.h> +#include <gl/Ector_GL.h> diff --git a/src/tests/automated/ector_init.c b/src/tests/automated/ector_init.c new file mode 100644 index 0000000000..b0006b6a1f --- /dev/null +++ b/src/tests/automated/ector_init.c @@ -0,0 +1 @@ + fail_if(!ector_init(), "ERROR: Cannot init Ector!\n"); diff --git a/src/tests/automated/ector_renderer_cairo_shape/init.c b/src/tests/automated/ector_renderer_cairo_shape/init.c new file mode 100644 index 0000000000..e0d899fa57 --- /dev/null +++ b/src/tests/automated/ector_renderer_cairo_shape/init.c @@ -0,0 +1,2 @@ +Ector_Surface *surface = efl_add(ECTOR_CAIRO_SOFTWARE_SURFACE_CLASS, NULL); +obj = efl_add_ref(ECTOR_RENDERER_CAIRO_SHAPE_CLASS, parent, ector_renderer_surface_set(efl_added, surface)); diff --git a/src/tests/automated/ector_shutdown.c b/src/tests/automated/ector_shutdown.c new file mode 100644 index 0000000000..2428e6ec56 --- /dev/null +++ b/src/tests/automated/ector_shutdown.c @@ -0,0 +1 @@ + ector_shutdown(); diff --git a/src/tests/automated/edje_custom.c b/src/tests/automated/edje_custom.c new file mode 100644 index 0000000000..edbf1b78f2 --- /dev/null +++ b/src/tests/automated/edje_custom.c @@ -0,0 +1 @@ +#define EFL_CANVAS_LAYOUT_BETA diff --git a/src/tests/automated/edje_init.c b/src/tests/automated/edje_init.c new file mode 100644 index 0000000000..4e81da1772 --- /dev/null +++ b/src/tests/automated/edje_init.c @@ -0,0 +1,2 @@ + fail_if(!ecore_evas_init(), "ERROR: Cannot init Ecore Evas!\n"); + fail_if(!edje_init(), "ERROR: Cannot init Edje!\n"); diff --git a/src/tests/automated/edje_shutdown.c b/src/tests/automated/edje_shutdown.c new file mode 100644 index 0000000000..450dda7d2b --- /dev/null +++ b/src/tests/automated/edje_shutdown.c @@ -0,0 +1,2 @@ + edje_shutdown(); + ecore_evas_shutdown(); diff --git a/src/tests/automated/efl_canvas_layout_part/init.c b/src/tests/automated/efl_canvas_layout_part/init.c new file mode 100644 index 0000000000..7d4a56a17b --- /dev/null +++ b/src/tests/automated/efl_canvas_layout_part/init.c @@ -0,0 +1,9 @@ + parent = evas_new(); + evas_output_method_set(parent, evas_render_method_lookup("buffer")); + Evas_Engine_Info *einfo = evas_engine_info_get(parent); + evas_engine_info_set(parent, einfo); + + evas_output_size_set(parent, 500, 500); + evas_output_viewport_set(parent, 0, 0, 500, 500); + + (void)obj; diff --git a/src/tests/automated/efl_canvas_layout_part_box/init.c b/src/tests/automated/efl_canvas_layout_part_box/init.c new file mode 100644 index 0000000000..7d4a56a17b --- /dev/null +++ b/src/tests/automated/efl_canvas_layout_part_box/init.c @@ -0,0 +1,9 @@ + parent = evas_new(); + evas_output_method_set(parent, evas_render_method_lookup("buffer")); + Evas_Engine_Info *einfo = evas_engine_info_get(parent); + evas_engine_info_set(parent, einfo); + + evas_output_size_set(parent, 500, 500); + evas_output_viewport_set(parent, 0, 0, 500, 500); + + (void)obj; diff --git a/src/tests/automated/efl_canvas_layout_part_external/init.c b/src/tests/automated/efl_canvas_layout_part_external/init.c new file mode 100644 index 0000000000..b42f732b75 --- /dev/null +++ b/src/tests/automated/efl_canvas_layout_part_external/init.c @@ -0,0 +1,8 @@ + parent = evas_new(); + evas_output_method_set(parent, evas_render_method_lookup("buffer")); + Evas_Engine_Info *einfo = evas_engine_info_get(parent); + evas_engine_info_set(parent, einfo); + + evas_output_size_set(parent, 500, 500); + evas_output_viewport_set(parent, 0, 0, 500, 500); + (void)obj; diff --git a/src/tests/automated/efl_canvas_layout_part_swallow/init.c b/src/tests/automated/efl_canvas_layout_part_swallow/init.c new file mode 100644 index 0000000000..b42f732b75 --- /dev/null +++ b/src/tests/automated/efl_canvas_layout_part_swallow/init.c @@ -0,0 +1,8 @@ + parent = evas_new(); + evas_output_method_set(parent, evas_render_method_lookup("buffer")); + Evas_Engine_Info *einfo = evas_engine_info_get(parent); + evas_engine_info_set(parent, einfo); + + evas_output_size_set(parent, 500, 500); + evas_output_viewport_set(parent, 0, 0, 500, 500); + (void)obj; diff --git a/src/tests/automated/efl_canvas_layout_part_table/init.c b/src/tests/automated/efl_canvas_layout_part_table/init.c new file mode 100644 index 0000000000..b42f732b75 --- /dev/null +++ b/src/tests/automated/efl_canvas_layout_part_table/init.c @@ -0,0 +1,8 @@ + parent = evas_new(); + evas_output_method_set(parent, evas_render_method_lookup("buffer")); + Evas_Engine_Info *einfo = evas_engine_info_get(parent); + evas_engine_info_set(parent, einfo); + + evas_output_size_set(parent, 500, 500); + evas_output_viewport_set(parent, 0, 0, 500, 500); + (void)obj; diff --git a/src/tests/automated/efl_canvas_layout_part_text/init.c b/src/tests/automated/efl_canvas_layout_part_text/init.c new file mode 100644 index 0000000000..b42f732b75 --- /dev/null +++ b/src/tests/automated/efl_canvas_layout_part_text/init.c @@ -0,0 +1,8 @@ + parent = evas_new(); + evas_output_method_set(parent, evas_render_method_lookup("buffer")); + Evas_Engine_Info *einfo = evas_engine_info_get(parent); + evas_engine_info_set(parent, einfo); + + evas_output_size_set(parent, 500, 500); + evas_output_viewport_set(parent, 0, 0, 500, 500); + (void)obj; diff --git a/src/tests/automated/efl_canvas_video/init.c b/src/tests/automated/efl_canvas_video/init.c new file mode 100644 index 0000000000..f75bda251f --- /dev/null +++ b/src/tests/automated/efl_canvas_video/init.c @@ -0,0 +1,2 @@ + obj = efl_add(EFL_CANVAS_VIDEO_CLASS, parent, efl_canvas_object_legacy_ctor(efl_added)); + fail_if(!obj, "Error: Canot get obj!\n"); diff --git a/src/tests/automated/efl_loop/begin/init.c b/src/tests/automated/efl_loop/begin/init.c new file mode 100644 index 0000000000..78fbba3fca --- /dev/null +++ b/src/tests/automated/efl_loop/begin/init.c @@ -0,0 +1,9 @@ +int argc = 2; +char *argv[] = { "efl_ui_suite", "test" }; +(void)parent; + +_EFL_APP_VERSION_SET(); +obj = efl_app_get(); +efl_event_callback_add(obj, EFL_LOOP_EVENT_ARGUMENTS, efl_main, NULL); +fail_if(!ecore_init_ex(argc, argv)); +__EFL_MAIN_CONSTRUCTOR; diff --git a/src/tests/automated/efl_loop/begin/shutdown.c b/src/tests/automated/efl_loop/begin/shutdown.c new file mode 100644 index 0000000000..1f578789d4 --- /dev/null +++ b/src/tests/automated/efl_loop/begin/shutdown.c @@ -0,0 +1,3 @@ +efl_loop_exit_code_process(r); +__EFL_MAIN_DESTRUCTOR; +ecore_shutdown_ex(); diff --git a/src/tests/automated/efl_loop/custom.c b/src/tests/automated/efl_loop/custom.c new file mode 100644 index 0000000000..f7df130584 --- /dev/null +++ b/src/tests/automated/efl_loop/custom.c @@ -0,0 +1,5 @@ +EAPI_MAIN void +efl_main(void *data EINA_UNUSED, const Efl_Event *ev) +{ + efl_loop_quit(ev->object, EINA_VALUE_EMPTY); +} diff --git a/src/tests/automated/efl_loop/timeout/arg_init.c b/src/tests/automated/efl_loop/timeout/arg_init.c new file mode 100644 index 0000000000..e2e28fb725 --- /dev/null +++ b/src/tests/automated/efl_loop/timeout/arg_init.c @@ -0,0 +1 @@ + arg_time = 0.5; diff --git a/src/tests/automated/efl_text_markup_util/init.c b/src/tests/automated/efl_text_markup_util/init.c new file mode 100644 index 0000000000..4d5230d0b1 --- /dev/null +++ b/src/tests/automated/efl_text_markup_util/init.c @@ -0,0 +1 @@ +(void)parent; diff --git a/src/tests/automated/eio_custom.c b/src/tests/automated/eio_custom.c new file mode 100644 index 0000000000..7f57ce11c4 --- /dev/null +++ b/src/tests/automated/eio_custom.c @@ -0,0 +1 @@ +#include <Eio.h> diff --git a/src/tests/automated/eio_init.c b/src/tests/automated/eio_init.c new file mode 100644 index 0000000000..2787098b73 --- /dev/null +++ b/src/tests/automated/eio_init.c @@ -0,0 +1 @@ + fail_if(!eio_init(), "ERROR: Cannot init Eio!\n"); diff --git a/src/tests/automated/eio_shutdown.c b/src/tests/automated/eio_shutdown.c new file mode 100644 index 0000000000..fad342e9ce --- /dev/null +++ b/src/tests/automated/eio_shutdown.c @@ -0,0 +1 @@ + eio_shutdown(); diff --git a/src/tests/automated/eldbus_init.c b/src/tests/automated/eldbus_init.c new file mode 100644 index 0000000000..dcfbbec39e --- /dev/null +++ b/src/tests/automated/eldbus_init.c @@ -0,0 +1 @@ +fail_if(eldbus_init() < 0, "ERROR: Cannot init Eldbus!\n"); diff --git a/src/tests/automated/eldbus_shutdown.c b/src/tests/automated/eldbus_shutdown.c new file mode 100644 index 0000000000..f3077072c5 --- /dev/null +++ b/src/tests/automated/eldbus_shutdown.c @@ -0,0 +1 @@ +eldbus_shutdown(); diff --git a/src/tests/automated/emotion_custom.c b/src/tests/automated/emotion_custom.c new file mode 100644 index 0000000000..811c9944a8 --- /dev/null +++ b/src/tests/automated/emotion_custom.c @@ -0,0 +1,2 @@ +#include "Emotion.h" +#include "Evas_Internal.h" diff --git a/src/tests/automated/emotion_init.c b/src/tests/automated/emotion_init.c new file mode 100644 index 0000000000..f6d1d030a8 --- /dev/null +++ b/src/tests/automated/emotion_init.c @@ -0,0 +1,3 @@ + fail_if(!ecore_evas_init(), "ERROR: Cannot init ECore Evas!\n"); + fail_if(!emotion_init(), "ERROR: Cannot init Emotion!\n"); + diff --git a/src/tests/automated/emotion_shutdown.c b/src/tests/automated/emotion_shutdown.c new file mode 100644 index 0000000000..e82aef7387 --- /dev/null +++ b/src/tests/automated/emotion_shutdown.c @@ -0,0 +1,4 @@ +// efl_unref(parent); +// ecore_evas_free(ee); + emotion_shutdown(); +// ecore_evas_shutdown(); diff --git a/src/tests/automated/evas_custom.c b/src/tests/automated/evas_custom.c new file mode 100644 index 0000000000..6cd14a5113 --- /dev/null +++ b/src/tests/automated/evas_custom.c @@ -0,0 +1 @@ +#include "efl_canvas_surface.h" |