1 /*
2 * Mesa 3-D graphics library
3 *
4 * Copyright (C) 2010 LunarG Inc.
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 * Authors:
25 * Chia-I Wu <[email protected]>
26 */
27
28 #include <stdlib.h>
29 #include <string.h>
30 #include <assert.h>
31 #include "c11/threads.h"
32
33 #include "util/macros.h"
34 #include "util/simple_mtx.h"
35 #include "u_current.h"
36 #include "entry.h"
37 #include "stub.h"
38 #include "table.h"
39
40
41 struct mapi_stub {
42 size_t name_offset;
43 int slot;
44 };
45
46 /* define public_string_pool and public_stubs */
47 #define MAPI_TMP_PUBLIC_STUBS
48 #include "mapi_tmp.h"
49
50 void
stub_init_once(void)51 stub_init_once(void)
52 {
53 static once_flag flag = ONCE_FLAG_INIT;
54 call_once(&flag, entry_patch_public);
55 }
56
57 static int
stub_compare(const void * key,const void * elem)58 stub_compare(const void *key, const void *elem)
59 {
60 const char *name = (const char *) key;
61 const struct mapi_stub *stub = (const struct mapi_stub *) elem;
62 const char *stub_name;
63
64 stub_name = &public_string_pool[stub->name_offset];
65
66 return strcmp(name, stub_name);
67 }
68
69 /**
70 * Return the public stub with the given name.
71 */
72 const struct mapi_stub *
stub_find_public(const char * name)73 stub_find_public(const char *name)
74 {
75 return (const struct mapi_stub *) bsearch(name, public_stubs,
76 ARRAY_SIZE(public_stubs), sizeof(public_stubs[0]), stub_compare);
77 }
78
79
80 static const struct mapi_stub *
search_table_by_slot(const struct mapi_stub * table,size_t num_entries,int slot)81 search_table_by_slot(const struct mapi_stub *table, size_t num_entries,
82 int slot)
83 {
84 size_t i;
85 for (i = 0; i < num_entries; ++i) {
86 if (table[i].slot == slot)
87 return &table[i];
88 }
89 return NULL;
90 }
91
92 const struct mapi_stub *
stub_find_by_slot(int slot)93 stub_find_by_slot(int slot)
94 {
95 const struct mapi_stub *stub =
96 search_table_by_slot(public_stubs, ARRAY_SIZE(public_stubs), slot);
97 return stub;
98 }
99
100 /**
101 * Return the name of a stub.
102 */
103 const char *
stub_get_name(const struct mapi_stub * stub)104 stub_get_name(const struct mapi_stub *stub)
105 {
106 return &public_string_pool[stub->name_offset];
107 }
108
109 /**
110 * Return the slot of a stub.
111 */
112 int
stub_get_slot(const struct mapi_stub * stub)113 stub_get_slot(const struct mapi_stub *stub)
114 {
115 return stub->slot;
116 }
117
118 /**
119 * Return the address of a stub.
120 */
121 mapi_func
stub_get_addr(const struct mapi_stub * stub)122 stub_get_addr(const struct mapi_stub *stub)
123 {
124 return entry_get_public(stub->slot);
125 }
126