| 1 | #!/usr/bin/python |
| 2 | # gnerate_wrappers.py: Parse header and output libhybris binding code |
| 3 | # Adapted for libhybris from apkenv-wrapper-generator |
| 4 | # |
| 5 | # apkenv-wrapper-generator version: |
| 6 | # Copyright (C) 2012 Thomas Perl <m@thp.io>; 2012-10-19 |
| 7 | # |
| 8 | # libhybris version: |
| 9 | # Copyright (C) 2013 Jolla Ltd. |
| 10 | # Contact: Thomas Perl <thomas.perl@jollamobile.com> |
| 11 | # |
| 12 | # Redistribution and use in source and binary forms, with or without |
| 13 | # modification, are permitted provided that the following conditions are met: |
| 14 | # |
| 15 | # 1. Redistributions of source code must retain the above copyright notice, this |
| 16 | # list of conditions and the following disclaimer. |
| 17 | # 2. Redistributions in binary form must reproduce the above copyright notice, |
| 18 | # this list of conditions and the following disclaimer in the documentation |
| 19 | # and/or other materials provided with the distribution. |
| 20 | # |
| 21 | # THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND |
| 22 | # ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED |
| 23 | # WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE |
| 24 | # DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR |
| 25 | # ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES |
| 26 | # (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; |
| 27 | # LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND |
| 28 | # ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT |
| 29 | # (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS |
| 30 | # SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. |
| 31 | # |
| 32 | |
| 33 | import re |
| 34 | import os |
| 35 | import sys |
| 36 | |
| 37 | funcs = [] |
| 38 | |
| 39 | # Some special cases to to avoid having to parse the full C grammar |
| 40 | FIXED_MAPPINGS = { |
| 41 | 'GLint *': 'GLint *', |
| 42 | 'GLuint *': 'GLuint *', |
| 43 | 'GLsizei *': 'GLsizei *', |
| 44 | 'GLfloat eqn[4]': 'GLfloat[4]', |
| 45 | 'GLfixed eqn[4]': 'GLfixed[4]', |
| 46 | 'GLfixed mantissa[16]': 'GLfixed[16]', |
| 47 | 'GLint exponent[16]': 'GLint[16]', |
| 48 | 'GLfloat eqn[4]': 'GLfloat[4]', |
| 49 | 'GLvoid **': 'GLvoid **', |
| 50 | 'GLfloat *': 'GLfloat *', |
| 51 | 'GLfixed *': 'GLfixed *', |
| 52 | } |
| 53 | |
| 54 | # Never generate wrappers for these functions |
| 55 | BLACKLISTED_FUNCS = [ |
| 56 | ] |
| 57 | |
| 58 | def clean_arg(arg): |
| 59 | arg = arg.replace('__restrict', '') |
| 60 | arg = arg.replace('__const', '') |
| 61 | arg = arg.replace('const', '') |
| 62 | return arg.strip() |
| 63 | |
| 64 | def mangle(name): |
| 65 | return 'my_' + name |
| 66 | |
| 67 | class Argument: |
| 68 | def __init__(self, type_, name): |
| 69 | self.type_ = type_ |
| 70 | self.name = name |
| 71 | |
| 72 | class Function: |
| 73 | def __init__(self, retval, name, args): |
| 74 | self.retval = retval |
| 75 | self.name = name |
| 76 | self.raw_args = args |
| 77 | self.parsing_error = None |
| 78 | self.args = list(self._parse_args(args)) |
| 79 | |
| 80 | def _parse_args(self, args): |
| 81 | for arg in map(clean_arg, args.split(',')): |
| 82 | arg = clean_arg(arg) |
| 83 | xarg = re.match(r'^(.*?)([A-Za-z0-9_]+)$', arg) |
| 84 | if not xarg: |
| 85 | # Unknown argument |
| 86 | if arg in FIXED_MAPPINGS: |
| 87 | yield Argument(FIXED_MAPPINGS[arg], '__undefined__') |
| 88 | continue |
| 89 | self.parsing_error = 'Could not parse: ' + repr(arg) |
| 90 | print self.parsing_error |
| 91 | continue |
| 92 | type_, name = xarg.groups() |
| 93 | if type_ == '': |
| 94 | type_ = name |
| 95 | name = '__undefined__' |
| 96 | yield Argument(type_, name) |
| 97 | |
| 98 | if len(sys.argv) != 2: |
| 99 | print >>sys.stderr, """ |
| 100 | Usage: %s glesv1_functions.h |
| 101 | """ % (sys.argv[0],) |
| 102 | sys.exit(1) |
| 103 | |
| 104 | filename = sys.argv[1] |
| 105 | |
| 106 | for line in open(filename): |
| 107 | if line.startswith('/*'): |
| 108 | continue |
| 109 | retval, funcname, args = re.match(r'^(.+ [*]?)([A-Za-z0-9_]+)\((.*)\);\s*$', line).groups() |
| 110 | retval, funcname, args = [x.strip() for x in (retval, funcname, args)] |
| 111 | if funcname not in BLACKLISTED_FUNCS: |
| 112 | funcs.append(Function(retval, funcname, args)) |
| 113 | |
| 114 | LIBRARY_NAME = 'glesv1_cm' |
| 115 | |
| 116 | for function in funcs: |
| 117 | args = [a.type_.strip() for a in function.args if a.type_.strip() not in ('', 'void')] |
| 118 | if function.retval == 'void': |
| 119 | print 'HYBRIS_IMPLEMENT_VOID_FUNCTION%d(%s, %s);' % (len(args), LIBRARY_NAME, ', '.join([function.name] + args)) |
| 120 | else: |
| 121 | print 'HYBRIS_IMPLEMENT_FUNCTION%d(%s, %s, %s);' % (len(args), LIBRARY_NAME, function.retval, ', '.join([function.name] + args)) |
| 122 | |