Support enum-type detection for binding generator
authorHamdi Sahloul <hamdisahloul@hotmail.com>
Mon, 20 Aug 2018 14:35:41 +0000 (23:35 +0900)
committerHamdi Sahloul <hamdisahloul@hotmail.com>
Fri, 24 Aug 2018 16:58:42 +0000 (01:58 +0900)
modules/java/generator/gen_java.py
modules/python/src2/gen2.py
modules/python/src2/hdr_parser.py

index d3a4664..5de9b5d 100755 (executable)
@@ -341,6 +341,7 @@ class JavaWrapperGenerator(object):
         self.classes = { "Mat" : ClassInfo([ 'class Mat', '', [], [] ], self.namespaces) }
         self.module = ""
         self.Module = ""
+        self.enum_types = []
         self.ported_func_list = []
         self.skipped_func_list = []
         self.def_args_hist = {} # { def_args_cnt : funcs_cnt }
@@ -421,6 +422,10 @@ class JavaWrapperGenerator(object):
                 ci.addConst(constinfo)
                 logging.info('ok: %s', constinfo)
 
+    def add_enum(self, decl): # [ "enum cname", "", [], [] ]
+        enumname = decl[0].replace("enum ", "").strip()
+        self.enum_types.append(enumname)
+
     def add_func(self, decl):
         fi = FuncInfo(decl, namespaces=self.namespaces)
         classname = fi.classname or self.Module
@@ -479,6 +484,9 @@ class JavaWrapperGenerator(object):
                     self.add_class(decl)
                 elif name.startswith("const"):
                     self.add_const(decl)
+                elif name.startswith("enum"):
+                    # enum
+                    self.add_enum(decl)
                 else: # function
                     self.add_func(decl)
 
index 24ffafa..5aef0b5 100755 (executable)
@@ -664,6 +664,9 @@ class FuncInfo(object):
                     if tp.endswith("*"):
                         defval0 = "0"
                         tp1 = tp.replace("*", "_ptr")
+                tp_candidates = [a.tp, normalize_class_name(self.namespace + "." + a.tp)]
+                if any(tp in codegen.enum_types for tp in tp_candidates):
+                    defval0 = "static_cast<%s>(%d)" % (a.tp, 0)
 
                 amapping = simple_argtype_mapping.get(tp, (tp, "O", defval0))
                 parse_name = a.name
@@ -835,6 +838,7 @@ class PythonWrapperGenerator(object):
         self.classes = {}
         self.namespaces = {}
         self.consts = {}
+        self.enum_types = []
         self.code_include = StringIO()
         self.code_types = StringIO()
         self.code_funcs = StringIO()
@@ -892,6 +896,10 @@ class PythonWrapperGenerator(object):
         py_signatures.append(dict(name=py_name, value=value))
         #print(cname + ' => ' + str(py_name) + ' (value=' + value + ')')
 
+    def add_enum(self, name, decl):
+        enumname = normalize_class_name(name)
+        self.enum_types.append(enumname)
+
     def add_func(self, decl):
         namespace, classes, barename = self.split_decl_name(decl[0])
         cname = "::".join(namespace+classes+[barename])
@@ -996,6 +1004,9 @@ class PythonWrapperGenerator(object):
                 elif name.startswith("const"):
                     # constant
                     self.add_const(name.replace("const ", "").strip(), decl)
+                elif name.startswith("enum"):
+                    # enum
+                    self.add_enum(name.replace("enum ", "").strip(), decl)
                 else:
                     # function
                     self.add_func(decl)
index c5cc3c0..254f3d5 100755 (executable)
@@ -705,20 +705,19 @@ class CppHeaderParser(object):
                             decl[1] = ": " + ", ".join([self.get_dotted_name(b).replace(".","::") for b in bases])
                     return stmt_type, classname, True, decl
 
-            if stmt.startswith("enum"):
-                return "enum", "", True, None
-
-            if stmt.startswith("namespace"):
+            if stmt.startswith("enum") or stmt.startswith("namespace"):
                 stmt_list = stmt.split()
                 if len(stmt_list) < 2:
                     stmt_list.append("<unnamed>")
                 return stmt_list[0], stmt_list[1], True, None
+
             if stmt.startswith("extern") and "\"C\"" in stmt:
                 return "namespace", "", True, None
 
         if end_token == "}" and context == "enum":
             decl = self.parse_enum(stmt)
-            return "enum", "", False, decl
+            name = stack_top[self.BLOCK_NAME]
+            return "enum", name, False, decl
 
         if end_token == ";" and stmt.startswith("typedef"):
             # TODO: handle typedef's more intelligently
@@ -896,8 +895,9 @@ class CppHeaderParser(object):
                     stmt_type, name, parse_flag, decl = self.parse_stmt(stmt, token, docstring=docstring)
                     if decl:
                         if stmt_type == "enum":
-                            for d in decl:
-                                decls.append(d)
+                            if name != "<unnamed>":
+                                decls.append(["enum " + self.get_dotted_name(name), "", [], [], None, ""])
+                            decls.extend(decl)
                         else:
                             decls.append(decl)