• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*
2  * Mesa 3-D graphics library
3  *
4  * Copyright (C) 2009 Chia-I Wu <olv@0xlab.org>
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  * the rights to use, copy, modify, merge, publish, distribute, sublicense,
10  * and/or sell copies of the Software, and to permit persons to whom the
11  * Software is furnished to do so, subject to the following conditions:
12  *
13  * The above copyright notice and this permission notice shall be included
14  * in all copies or substantial portions of the Software.
15  *
16  * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
17  * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
18  * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.  IN NO EVENT SHALL
19  * THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
20  * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
21  * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
22  * DEALINGS IN THE SOFTWARE.
23  */
24 
25 
26 /**
27  * \file remap.c
28  * Remap table management.
29  *
30  * Entries in the dispatch table are either static or dynamic.  The
31  * dispatch table is shared by mesa core and glapi.  When they are
32  * built separately, it is possible that a static entry in mesa core
33  * is dynamic, or assigned a different static offset, in glapi.  The
34  * remap table is in charge of mapping a static entry in mesa core to
35  * a dynamic entry, or the corresponding static entry, in glapi.
36  */
37 
38 #include <stdbool.h>
39 #include "remap.h"
40 #include "imports.h"
41 #include "glapi/glapi.h"
42 
43 #define MAX_ENTRY_POINTS 16
44 
45 #define need_MESA_remap_table
46 #include "main/remap_helper.h"
47 
48 
49 /* this is global for quick access */
50 int driDispatchRemapTable[driDispatchRemapTable_size];
51 
52 
53 /**
54  * Map a function by its spec.  The function will be added to glapi,
55  * and the dispatch offset will be returned.
56  *
57  * \param spec a '\0'-separated string array specifying a function.
58  *        It begins with the parameter signature of the function,
59  *        followed by the names of the entry points.  An empty entry
60  *        point name terminates the array.
61  *
62  * \return the offset of the (re-)mapped function in the dispatch
63  *         table, or -1.
64  */
65 static int
map_function_spec(const char * spec)66 map_function_spec(const char *spec)
67 {
68    const char *signature;
69    const char *names[MAX_ENTRY_POINTS + 1];
70    int num_names = 0;
71 
72    if (!spec)
73       return -1;
74 
75    signature = spec;
76    spec += strlen(spec) + 1;
77 
78    /* spec is terminated by an empty string */
79    while (*spec) {
80       names[num_names] = spec;
81       num_names++;
82       if (num_names >= MAX_ENTRY_POINTS)
83          break;
84       spec += strlen(spec) + 1;
85    }
86    if (!num_names)
87       return -1;
88 
89    names[num_names] = NULL;
90 
91    /* add the entry points to the dispatch table */
92    return _glapi_add_dispatch(names, signature);
93 }
94 
95 
96 /**
97  * Initialize the remap table.  This is called in one_time_init().
98  * The remap table needs to be initialized before calling the
99  * CALL/GET/SET macros defined in main/dispatch.h.
100  */
101 void
_mesa_init_remap_table(void)102 _mesa_init_remap_table(void)
103 {
104    static bool initialized = false;
105    GLint i;
106 
107    if (initialized)
108       return;
109    initialized = true;
110 
111    /* initialize the MESA_remap_table_functions table */
112    for (i = 0; i < driDispatchRemapTable_size; i++) {
113       int offset;
114       const char *spec;
115 
116       /* sanity check */
117       assert(i == MESA_remap_table_functions[i].remap_index);
118       spec = _mesa_function_pool + MESA_remap_table_functions[i].pool_index;
119 
120       offset = map_function_spec(spec);
121       /* store the dispatch offset in the MESA_remap_table_functions table */
122       driDispatchRemapTable[i] = offset;
123       if (offset < 0) {
124          const char *name = spec + strlen(spec) + 1;
125          _mesa_warning(NULL, "failed to remap %s", name);
126       }
127    }
128 }
129