Subversion Repositories Kolibri OS

Rev

Details | Last modification | View Log | RSS feed

Rev Author Line No. Line
5563 serge 1
#!/usr/bin/env python
2
 
3
# (C) Copyright IBM Corporation 2004, 2005
4
# All Rights Reserved.
5
#
6
# Permission is hereby granted, free of charge, to any person obtaining a
7
# copy of this software and associated documentation files (the "Software"),
8
# to deal in the Software without restriction, including without limitation
9
# on the rights to use, copy, modify, merge, publish, distribute, sub
10
# license, and/or sell copies of the Software, and to permit persons to whom
11
# the Software is furnished to do so, subject to the following conditions:
12
#
13
# The above copyright notice and this permission notice (including the next
14
# paragraph) shall be included in all copies or substantial portions of the
15
# Software.
16
#
17
# THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
18
# IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
19
# FITNESS FOR A PARTICULAR PURPOSE AND NON-INFRINGEMENT.  IN NO EVENT SHALL
20
# IBM AND/OR ITS SUPPLIERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
21
# LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
22
# FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS
23
# IN THE SOFTWARE.
24
#
25
# Authors:
26
#    Ian Romanick 
27
 
28
import gl_XML, glX_XML
29
import license
30
import sys, getopt
31
 
32
class PrintGlOffsets(gl_XML.gl_print_base):
33
    def __init__(self, es=False):
34
        gl_XML.gl_print_base.__init__(self)
35
 
36
        self.name = "gl_apitemp.py (from Mesa)"
37
        self.license = license.bsd_license_template % ( \
38
"""Copyright (C) 1999-2001  Brian Paul   All Rights Reserved.
39
(C) Copyright IBM Corporation 2004""", "BRIAN PAUL, IBM")
40
 
41
        self.es = es
42
 
43
        self.undef_list.append( "KEYWORD1" )
44
        self.undef_list.append( "KEYWORD1_ALT" )
45
        self.undef_list.append( "KEYWORD2" )
46
        self.undef_list.append( "NAME" )
47
        self.undef_list.append( "DISPATCH" )
48
        self.undef_list.append( "RETURN_DISPATCH" )
49
        self.undef_list.append( "DISPATCH_TABLE_NAME" )
50
        self.undef_list.append( "UNUSED_TABLE_NAME" )
51
        self.undef_list.append( "TABLE_ENTRY" )
52
 
53
 
54
    def printFunction(self, f, name):
55
        p_string = ""
56
        o_string = ""
57
        t_string = ""
58
        comma = ""
59
 
60
        if f.is_static_entry_point(name):
61
            keyword = "KEYWORD1"
62
        else:
63
            keyword = "KEYWORD1_ALT"
64
 
65
        n = f.static_name(name)
66
 
67
        silence = ''
68
        space = ''
69
        for p in f.parameterIterator(name):
70
            if p.is_padding:
71
                continue
72
 
73
            if p.is_pointer():
74
                cast = "(const void *) "
75
            else:
76
                cast = ""
77
 
78
            t_string = t_string + comma + p.format_string()
79
            p_string = p_string + comma + p.name
80
            o_string = o_string + comma + cast + p.name
81
            comma = ", "
82
 
83
            silence += "%s(void) %s;" % (space, p.name);
84
            space = ' '
85
 
86
 
87
        if f.return_type != 'void':
88
            dispatch = "RETURN_DISPATCH"
89
        else:
90
            dispatch = "DISPATCH"
91
 
92
        need_proto = False
93
        if not f.is_static_entry_point(name):
94
            need_proto = True
95
        elif self.es:
96
            cat, num = api.get_category_for_name(name)
97
            if (cat.startswith("es") or cat.startswith("GL_OES")):
98
                need_proto = True
99
        if need_proto:
100
            print '%s %s KEYWORD2 NAME(%s)(%s);' % (keyword, f.return_type, n, f.get_parameter_string(name))
101
            print ''
102
 
103
        print '%s %s KEYWORD2 NAME(%s)(%s)' % (keyword, f.return_type, n, f.get_parameter_string(name))
104
        print '{'
105
        if silence:
106
            print '    %s' % (silence)
107
        if p_string == "":
108
            print '   %s(%s, (), (F, "gl%s();\\n"));' \
109
                    % (dispatch, f.name, name)
110
        else:
111
            print '   %s(%s, (%s), (F, "gl%s(%s);\\n", %s));' \
112
                    % (dispatch, f.name, p_string, name, t_string, o_string)
113
        print '}'
114
        print ''
115
        return
116
 
117
    def printRealHeader(self):
118
        print ''
119
        self.printVisibility( "HIDDEN", "hidden" )
120
        print """
121
/*
122
 * This file is a template which generates the OpenGL API entry point
123
 * functions.  It should be included by a .c file which first defines
124
 * the following macros:
125
 *   KEYWORD1 - usually nothing, but might be __declspec(dllexport) on Win32
126
 *   KEYWORD2 - usually nothing, but might be __stdcall on Win32
127
 *   NAME(n)  - builds the final function name (usually add "gl" prefix)
128
 *   DISPATCH(func, args, msg) - code to do dispatch of named function.
129
 *                               msg is a printf-style debug message.
130
 *   RETURN_DISPATCH(func, args, msg) - code to do dispatch with a return value
131
 *
132
 * Here is an example which generates the usual OpenGL functions:
133
 *   #define KEYWORD1
134
 *   #define KEYWORD2
135
 *   #define NAME(func)  gl##func
136
 *   #define DISPATCH(func, args, msg)                           \\
137
 *          struct _glapi_table *dispatch = CurrentDispatch;     \\
138
 *          (*dispatch->func) args
139
 *   #define RETURN DISPATCH(func, args, msg)                    \\
140
 *          struct _glapi_table *dispatch = CurrentDispatch;     \\
141
 *          return (*dispatch->func) args
142
 *
143
 */
144
 
145
 
146
#if defined( NAME )
147
#ifndef KEYWORD1
148
#define KEYWORD1
149
#endif
150
 
151
#ifndef KEYWORD1_ALT
152
#define KEYWORD1_ALT HIDDEN
153
#endif
154
 
155
#ifndef KEYWORD2
156
#define KEYWORD2
157
#endif
158
 
159
#ifndef DISPATCH
160
#error DISPATCH must be defined
161
#endif
162
 
163
#ifndef RETURN_DISPATCH
164
#error RETURN_DISPATCH must be defined
165
#endif
166
 
167
"""
168
        return
169
 
170
 
171
 
172
    def printInitDispatch(self, api):
173
        print """
174
#endif /* defined( NAME ) */
175
 
176
/*
177
 * This is how a dispatch table can be initialized with all the functions
178
 * we generated above.
179
 */
180
#ifdef DISPATCH_TABLE_NAME
181
 
182
#ifndef TABLE_ENTRY
183
#error TABLE_ENTRY must be defined
184
#endif
185
 
186
#ifdef _GLAPI_SKIP_NORMAL_ENTRY_POINTS
187
#error _GLAPI_SKIP_NORMAL_ENTRY_POINTS must not be defined
188
#endif
189
 
190
_glapi_proc DISPATCH_TABLE_NAME[] = {"""
191
        for f in api.functionIterateByOffset():
192
            print '   TABLE_ENTRY(%s),' % (f.dispatch_name())
193
 
194
        print '   /* A whole bunch of no-op functions.  These might be called'
195
        print '    * when someone tries to call a dynamically-registered'
196
        print '    * extension function without a current rendering context.'
197
        print '    */'
198
        for i in range(1, 100):
199
            print '   TABLE_ENTRY(Unused),'
200
 
201
        print '};'
202
        print '#endif /* DISPATCH_TABLE_NAME */'
203
        print ''
204
        return
205
 
206
 
207
    def printAliasedTable(self, api):
208
        print """
209
/*
210
 * This is just used to silence compiler warnings.
211
 * We list the functions which are not otherwise used.
212
 */
213
#ifdef UNUSED_TABLE_NAME
214
_glapi_proc UNUSED_TABLE_NAME[] = {"""
215
 
216
        normal_entries = []
217
        proto_entries = []
218
        for f in api.functionIterateByOffset():
219
            normal_ents, proto_ents = self.classifyEntryPoints(f)
220
 
221
            # exclude f.name
222
            if f.name in normal_ents:
223
                normal_ents.remove(f.name)
224
            elif f.name in proto_ents:
225
                proto_ents.remove(f.name)
226
 
227
            normal_ents = [f.static_name(ent) for ent in normal_ents]
228
            proto_ents = [f.static_name(ent) for ent in proto_ents]
229
 
230
            normal_entries.extend(normal_ents)
231
            proto_entries.extend(proto_ents)
232
 
233
        print '#ifndef _GLAPI_SKIP_NORMAL_ENTRY_POINTS'
234
        for ent in normal_entries:
235
            print '   TABLE_ENTRY(%s),' % (ent)
236
        print '#endif /* _GLAPI_SKIP_NORMAL_ENTRY_POINTS */'
237
        print '#ifndef _GLAPI_SKIP_PROTO_ENTRY_POINTS'
238
        for ent in proto_entries:
239
            print '   TABLE_ENTRY(%s),' % (ent)
240
        print '#endif /* _GLAPI_SKIP_PROTO_ENTRY_POINTS */'
241
 
242
        print '};'
243
        print '#endif /*UNUSED_TABLE_NAME*/'
244
        print ''
245
        return
246
 
247
 
248
    def classifyEntryPoints(self, func):
249
        normal_names = []
250
        normal_stubs = []
251
        proto_names = []
252
        proto_stubs = []
253
        # classify the entry points
254
        for name in func.entry_points:
255
            if func.has_different_protocol(name):
256
                if func.is_static_entry_point(name):
257
                    proto_names.append(name)
258
                else:
259
                    proto_stubs.append(name)
260
            else:
261
                if func.is_static_entry_point(name):
262
                    normal_names.append(name)
263
                else:
264
                    normal_stubs.append(name)
265
        # there can be at most one stub for a function
266
        if normal_stubs:
267
            normal_names.append(normal_stubs[0])
268
        elif proto_stubs:
269
            proto_names.append(proto_stubs[0])
270
 
271
        return (normal_names, proto_names)
272
 
273
    def printBody(self, api):
274
        normal_entry_points = []
275
        proto_entry_points = []
276
        for func in api.functionIterateByOffset():
277
            normal_ents, proto_ents = self.classifyEntryPoints(func)
278
            normal_entry_points.append((func, normal_ents))
279
            proto_entry_points.append((func, proto_ents))
280
 
281
        print '#ifndef _GLAPI_SKIP_NORMAL_ENTRY_POINTS'
282
        print ''
283
        for func, ents in normal_entry_points:
284
            for ent in ents:
285
                self.printFunction(func, ent)
286
        print ''
287
        print '#endif /* _GLAPI_SKIP_NORMAL_ENTRY_POINTS */'
288
        print ''
289
        print '/* these entry points might require different protocols */'
290
        print '#ifndef _GLAPI_SKIP_PROTO_ENTRY_POINTS'
291
        print ''
292
        for func, ents in proto_entry_points:
293
            for ent in ents:
294
                self.printFunction(func, ent)
295
        print ''
296
        print '#endif /* _GLAPI_SKIP_PROTO_ENTRY_POINTS */'
297
        print ''
298
 
299
        self.printInitDispatch(api)
300
        self.printAliasedTable(api)
301
        return
302
 
303
 
304
def show_usage():
305
    print "Usage: %s [-f input_file_name] [-c]" % sys.argv[0]
306
    print "-c          Enable compatibility with OpenGL ES."
307
    sys.exit(1)
308
 
309
if __name__ == '__main__':
310
    file_name = "gl_API.xml"
311
 
312
    try:
313
        (args, trail) = getopt.getopt(sys.argv[1:], "f:c")
314
    except Exception,e:
315
        show_usage()
316
 
317
    es = False
318
    for (arg,val) in args:
319
        if arg == "-f":
320
            file_name = val
321
        elif arg == "-c":
322
            es = True
323
 
324
    api = gl_XML.parse_GL_API(file_name, glX_XML.glx_item_factory())
325
 
326
    printer = PrintGlOffsets(es)
327
    printer.Print(api)