vulkan/overlay: fix min/max computations
[mesa.git] / src / vulkan / overlay-layer / vk_layer_table.cpp
1 /* Copyright (c) 2015-2016 The Khronos Group Inc.
2 * Copyright (c) 2015-2016 Valve Corporation
3 * Copyright (c) 2015-2016 LunarG, Inc.
4 * Copyright (c) 2015-2016 Google, Inc.
5 *
6 * Licensed under the Apache License, Version 2.0 (the "License");
7 * you may not use this file except in compliance with the License.
8 * You may obtain a copy of the License at
9 *
10 * http://www.apache.org/licenses/LICENSE-2.0
11 *
12 * Unless required by applicable law or agreed to in writing, software
13 * distributed under the License is distributed on an "AS IS" BASIS,
14 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
15 * See the License for the specific language governing permissions and
16 * limitations under the License.
17 *
18 * Author: Tobin Ehlis <tobin@lunarg.com>
19 */
20 #include <assert.h>
21 #include <unordered_map>
22 #include <vulkan/vk_dispatch_table_helper.h>
23 #include <vulkan/vk_layer.h>
24 #include "vk_layer_table.h"
25 static device_table_map tableMap;
26 static instance_table_map tableInstanceMap;
27
28 // Map lookup must be thread safe
29 VkLayerDispatchTable *device_dispatch_table(void *object) {
30 dispatch_key key = get_dispatch_key(object);
31 device_table_map::const_iterator it = tableMap.find((void *)key);
32 assert(it != tableMap.end() && "Not able to find device dispatch entry");
33 return it->second;
34 }
35
36 VkLayerInstanceDispatchTable *instance_dispatch_table(void *object) {
37 dispatch_key key = get_dispatch_key(object);
38 instance_table_map::const_iterator it = tableInstanceMap.find((void *)key);
39 assert(it != tableInstanceMap.end() && "Not able to find instance dispatch entry");
40 return it->second;
41 }
42
43 void destroy_dispatch_table(device_table_map &map, dispatch_key key) {
44 device_table_map::const_iterator it = map.find((void *)key);
45 if (it != map.end()) {
46 delete it->second;
47 map.erase(it);
48 }
49 }
50
51 void destroy_dispatch_table(instance_table_map &map, dispatch_key key) {
52 instance_table_map::const_iterator it = map.find((void *)key);
53 if (it != map.end()) {
54 delete it->second;
55 map.erase(it);
56 }
57 }
58
59 void destroy_device_dispatch_table(dispatch_key key) { destroy_dispatch_table(tableMap, key); }
60
61 void destroy_instance_dispatch_table(dispatch_key key) { destroy_dispatch_table(tableInstanceMap, key); }
62
63 VkLayerDispatchTable *get_dispatch_table(device_table_map &map, void *object) {
64 dispatch_key key = get_dispatch_key(object);
65 device_table_map::const_iterator it = map.find((void *)key);
66 assert(it != map.end() && "Not able to find device dispatch entry");
67 return it->second;
68 }
69
70 VkLayerInstanceDispatchTable *get_dispatch_table(instance_table_map &map, void *object) {
71 dispatch_key key = get_dispatch_key(object);
72 instance_table_map::const_iterator it = map.find((void *)key);
73 assert(it != map.end() && "Not able to find instance dispatch entry");
74 return it->second;
75 }
76
77 VkLayerInstanceCreateInfo *get_chain_info(const VkInstanceCreateInfo *pCreateInfo, VkLayerFunction func) {
78 VkLayerInstanceCreateInfo *chain_info = (VkLayerInstanceCreateInfo *)pCreateInfo->pNext;
79 while (chain_info && !(chain_info->sType == VK_STRUCTURE_TYPE_LOADER_INSTANCE_CREATE_INFO && chain_info->function == func)) {
80 chain_info = (VkLayerInstanceCreateInfo *)chain_info->pNext;
81 }
82 assert(chain_info != NULL);
83 return chain_info;
84 }
85
86 VkLayerDeviceCreateInfo *get_chain_info(const VkDeviceCreateInfo *pCreateInfo, VkLayerFunction func) {
87 VkLayerDeviceCreateInfo *chain_info = (VkLayerDeviceCreateInfo *)pCreateInfo->pNext;
88 while (chain_info && !(chain_info->sType == VK_STRUCTURE_TYPE_LOADER_DEVICE_CREATE_INFO && chain_info->function == func)) {
89 chain_info = (VkLayerDeviceCreateInfo *)chain_info->pNext;
90 }
91 assert(chain_info != NULL);
92 return chain_info;
93 }
94
95 /* Various dispatchable objects will use the same underlying dispatch table if they
96 * are created from that "parent" object. Thus use pointer to dispatch table
97 * as the key to these table maps.
98 * Instance -> PhysicalDevice
99 * Device -> CommandBuffer or Queue
100 * If use the object themselves as key to map then implies Create entrypoints have to be intercepted
101 * and a new key inserted into map */
102 VkLayerInstanceDispatchTable *initInstanceTable(VkInstance instance, const PFN_vkGetInstanceProcAddr gpa, instance_table_map &map) {
103 VkLayerInstanceDispatchTable *pTable;
104 dispatch_key key = get_dispatch_key(instance);
105 instance_table_map::const_iterator it = map.find((void *)key);
106
107 if (it == map.end()) {
108 pTable = new VkLayerInstanceDispatchTable;
109 map[(void *)key] = pTable;
110 } else {
111 return it->second;
112 }
113
114 layer_init_instance_dispatch_table(instance, pTable, gpa);
115
116 // Setup func pointers that are required but not externally exposed. These won't be added to the instance dispatch table by
117 // default.
118 pTable->GetPhysicalDeviceProcAddr = (PFN_GetPhysicalDeviceProcAddr)gpa(instance, "vk_layerGetPhysicalDeviceProcAddr");
119
120 return pTable;
121 }
122
123 VkLayerInstanceDispatchTable *initInstanceTable(VkInstance instance, const PFN_vkGetInstanceProcAddr gpa) {
124 return initInstanceTable(instance, gpa, tableInstanceMap);
125 }
126
127 VkLayerDispatchTable *initDeviceTable(VkDevice device, const PFN_vkGetDeviceProcAddr gpa, device_table_map &map) {
128 VkLayerDispatchTable *pTable;
129 dispatch_key key = get_dispatch_key(device);
130 device_table_map::const_iterator it = map.find((void *)key);
131
132 if (it == map.end()) {
133 pTable = new VkLayerDispatchTable;
134 map[(void *)key] = pTable;
135 } else {
136 return it->second;
137 }
138
139 layer_init_device_dispatch_table(device, pTable, gpa);
140
141 return pTable;
142 }
143
144 VkLayerDispatchTable *initDeviceTable(VkDevice device, const PFN_vkGetDeviceProcAddr gpa) {
145 return initDeviceTable(device, gpa, tableMap);
146 }