mapi: Fix hidden entries.
authorChia-I Wu <olv@lunarg.com>
Fri, 10 Dec 2010 16:26:32 +0000 (00:26 +0800)
committerChia-I Wu <olv@lunarg.com>
Fri, 24 Dec 2010 09:28:52 +0000 (17:28 +0800)
Hidden entries are just like normal entries except that they are not
exported.  Since it is not always possible to hide them, and two hidden
aliases can share the same entry, the name of hidden aliases are mangled
to '_dispatch_stub_<slot>'.

src/mapi/mapi/mapi_abi.py

index 0059171e6ab8d5967c93f529145e26b089392624..fb91f6165a03cfe3db227eb217e5478ed69b5d33 100644 (file)
@@ -236,15 +236,32 @@ class ABIPrinter(object):
         self.api_entry = 'KHRONOS_APIENTRY'
         self.api_attrs = 'KHRONOS_APIATTRIBUTES'
 
-    def c_header(self):
+    def c_notice(self):
         return '/* This file is automatically generated by mapi_abi.py.  Do not modify. */'
 
-    def c_includes(self):
+    def c_public_includes(self):
         """Return includes of the client API headers."""
         defines = ['#define ' + d for d in self.api_defines]
         includes = ['#include ' + h for h in self.api_headers]
         return "\n".join(defines + includes)
 
+    def need_entry_point(self, ent):
+        """Return True if an entry point is needed for the entry."""
+        # non-handcode hidden aliases may share the entry they alias
+        use_alias = (ent.hidden and ent.alias and not ent.handcode)
+        return not use_alias
+
+    def c_public_declarations(self, prefix):
+        """Return the declarations of public entry points."""
+        decls = []
+        for ent in self.entries:
+            if not self.need_entry_point(ent):
+                continue
+            export = self.api_call if not ent.hidden else ''
+            decls.append(self._c_decl(ent, prefix, True, export) + ';')
+
+        return "\n".join(decls)
+
     def c_mapi_table(self):
         """Return defines of the dispatch table size."""
         num_static_entries = 0
@@ -278,16 +295,31 @@ class ABIPrinter(object):
 
         return self.indent + self.indent.join(specv1)
 
-    def _c_function(self, ent, prefix, stringify=False):
+    def _c_function(self, ent, prefix, mangle=False, stringify=False):
         """Return the function name of an entry."""
         formats = { True: '"%s%s"', False: '%s%s' }
         fmt = formats[stringify]
-        return fmt % (prefix, ent.name)
+        name = ent.name
+        if mangle and ent.hidden:
+            name = '_dispatch_stub_' + str(ent.slot)
+        return fmt % (prefix, name)
+
+    def _c_function_call(self, ent, prefix):
+        """Return the function name used for calling."""
+        if ent.handcode:
+            # _c_function does not handle this case
+            fmt = '%s%s'
+            name = fmt % (prefix, ent.handcode)
+        elif self.need_entry_point(ent):
+            name = self._c_function(ent, prefix, True)
+        else:
+            name = self._c_function(ent.alias, prefix, True)
+        return name
 
-    def _c_decl(self, ent, prefix, export=''):
+    def _c_decl(self, ent, prefix, mangle=False, export=''):
         """Return the C declaration for the entry."""
         decl = '%s %s %s(%s)' % (ent.c_return(), self.api_entry,
-                self._c_function(ent, prefix), ent.c_params())
+                self._c_function(ent, prefix, mangle), ent.c_params())
         if export:
             decl = export + ' ' + decl
         if self.api_attrs:
@@ -313,10 +345,12 @@ class ABIPrinter(object):
         """Return the public dispatch functions."""
         dispatches = []
         for ent in self.entries:
-            if ent.hidden:
+            if not self.need_entry_point(ent):
                 continue
 
-            proto = self._c_decl(ent, prefix, self.api_call)
+            export = self.api_call if not ent.hidden else ''
+
+            proto = self._c_decl(ent, prefix, True, export)
             cast = self._c_cast(ent)
 
             ret = ''
@@ -362,7 +396,7 @@ class ABIPrinter(object):
         stubs = []
         for ent in self.entries_sorted_by_names:
             stubs.append('%s{ (mapi_func) %s, %d, (void *) %d }' % (
-                self.indent, self._c_function(ent, prefix),
+                self.indent, self._c_function_call(ent, prefix),
                 ent.slot, pool_offsets[ent]))
 
         return ',\n'.join(stubs)
@@ -374,10 +408,10 @@ class ABIPrinter(object):
             if ent.alias:
                 continue
 
-            proto = self._c_decl(ent, prefix, 'static')
+            proto = self._c_decl(ent, prefix, False, 'static')
 
             stmt1 = self.indent + '%s(%s);' % (self.noop_warn,
-                    self._c_function(ent, warn_prefix, True))
+                    self._c_function(ent, warn_prefix, False, True))
 
             if ent.ret:
                 stmt2 = self.indent + 'return (%s) 0;' % (ent.ret)
@@ -406,7 +440,10 @@ class ABIPrinter(object):
 
         asm.append('__asm__(')
         for ent in self.entries:
-            name = self._c_function(ent, prefix, True)
+            if not self.need_entry_point(ent):
+                continue
+
+            name = self._c_function(ent, prefix, True, True)
 
             if ent.handcode:
                 asm.append('#if 0')
@@ -417,7 +454,7 @@ class ABIPrinter(object):
             if ent.alias:
                 asm.append('".globl "%s"\\n"' % (name))
                 asm.append('".set "%s", "%s"\\n"' % (name,
-                    self._c_function(ent.alias, prefix, True)))
+                    self._c_function(ent.alias, prefix, True, True)))
             else:
                 asm.append('STUB_ASM_ENTRY(%s)"\\n"' % (name))
                 asm.append('"\\t"STUB_ASM_CODE("%d")"\\n"' % (ent.slot))
@@ -430,10 +467,12 @@ class ABIPrinter(object):
         return "\n".join(asm)
 
     def output_for_lib(self):
-        print self.c_header()
+        print self.c_notice()
         print
         print '#ifdef MAPI_TMP_DEFINES'
-        print self.c_includes()
+        print self.c_public_includes()
+        print
+        print self.c_public_declarations(self.prefix_lib)
         print '#undef MAPI_TMP_DEFINES'
         print '#endif /* MAPI_TMP_DEFINES */'
         print
@@ -486,7 +525,7 @@ class ABIPrinter(object):
         print '#endif /* MAPI_TMP_STUB_ASM_GCC */'
 
     def output_for_app(self):
-        print self.c_header()
+        print self.c_notice()
         print
         print self.c_private_declarations(self.prefix_app)
         print