blob: 4705b0ceb5d1d5a20713c3cbc4753ece376d81d5 [file] [log] [blame]
Jon Ashburn8d8dad02014-12-01 14:22:40 -07001/*
Courtney Goeltzenleuchter9cc421e2015-04-08 15:36:08 -06002 * Vulkan
Jon Ashburn8d8dad02014-12-01 14:22:40 -07003 *
4 * Copyright (C) 2014 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 */
25
26#include <string.h>
27#include <stdlib.h>
28#include <assert.h>
29#include <unordered_map>
Ian Elliott81ac44c2015-01-13 17:52:38 -070030#include "loader_platform.h"
Courtney Goeltzenleuchter9cc421e2015-04-08 15:36:08 -060031#include "vk_dispatch_table_helper.h"
Tobin Ehlis2d1d9702015-07-03 09:42:57 -060032#include "vk_layer.h"
Ian Elliott20f06872015-02-12 17:08:34 -070033// The following is #included again to catch certain OS-specific functions
34// being used:
35#include "loader_platform.h"
Jon Ashburn8d8dad02014-12-01 14:22:40 -070036
Jon Ashburn1245cec2015-05-18 13:20:15 -060037static void initLayerTable(const VkBaseLayerObject *devw, VkLayerDispatchTable *pTable, const unsigned int layerNum);
Jon Ashburnd9564002015-05-07 10:27:37 -060038static void initLayerInstanceTable(const VkBaseLayerObject *instw, VkLayerInstanceDispatchTable *pTable, const unsigned int layerNum);
Jon Ashburnd25a78e2015-05-15 16:40:25 -060039/* Various dispatchable objects will use the same underlying dispatch table if they
40 * are created from that "parent" object. Thus use pointer to dispatch table
41 * as the key to table maps (tableMap1, tableInstanceMap1, tableMap2, tableInstanceMap2.
42 * Instance -> PhysicalDevice
43 * Device -> CmdBuffer or Queue
44 * If use the object themselves as key to map then implies Create entrypoints have to be intercepted
45 * and a new key inserted into map */
Jon Ashburn8d8dad02014-12-01 14:22:40 -070046/******************************** Layer multi1 functions **************************/
Jon Ashburn301c5f02015-04-06 10:58:22 -060047static std::unordered_map<void *, VkLayerDispatchTable *> tableMap1;
Jon Ashburnd9564002015-05-07 10:27:37 -060048static std::unordered_map<void *, VkLayerInstanceDispatchTable *> tableInstanceMap1;
Jon Ashburn8d8dad02014-12-01 14:22:40 -070049static bool layer1_first_activated = false;
50
Jon Ashburn5a10d212015-06-01 10:02:09 -060051// Map lookup must be thread safe
52static inline VkLayerDispatchTable *device_dispatch_table1(VkObject object)
53{
54 VkLayerDispatchTable *pDisp = *(VkLayerDispatchTable **) object;
55 std::unordered_map<void *, VkLayerDispatchTable *>::const_iterator it = tableMap1.find((void *) pDisp);
56 assert(it != tableMap1.end() && "Not able to find device dispatch entry");
57 return it->second;
58}
59
60static inline VkLayerInstanceDispatchTable *instance_dispatch_table1(VkObject object)
61{
62 VkLayerInstanceDispatchTable *pDisp = *(VkLayerInstanceDispatchTable **) object;
63 std::unordered_map<void *, VkLayerInstanceDispatchTable *>::const_iterator it = tableInstanceMap1.find((void *) pDisp);
64 assert(it != tableInstanceMap1.end() && "Not able to find instance dispatch entry");
65 return it->second;
66}
67
Jon Ashburnd25a78e2015-05-15 16:40:25 -060068static VkLayerDispatchTable *getLayer1Table(const VkBaseLayerObject *devw)
Jon Ashburn8d8dad02014-12-01 14:22:40 -070069{
Jon Ashburn301c5f02015-04-06 10:58:22 -060070 VkLayerDispatchTable *pTable;
Jon Ashburnd25a78e2015-05-15 16:40:25 -060071 assert(devw);
72 VkLayerDispatchTable **ppDisp = (VkLayerDispatchTable **) devw->baseObject;
Jon Ashburn8d8dad02014-12-01 14:22:40 -070073
Jon Ashburnd25a78e2015-05-15 16:40:25 -060074 std::unordered_map<void *, VkLayerDispatchTable *>::const_iterator it = tableMap1.find((void *) *ppDisp);
Jon Ashburn8d8dad02014-12-01 14:22:40 -070075 if (it == tableMap1.end())
76 {
Jon Ashburn301c5f02015-04-06 10:58:22 -060077 pTable = new VkLayerDispatchTable;
Jon Ashburnd25a78e2015-05-15 16:40:25 -060078 tableMap1[(void *) *ppDisp] = pTable;
79 initLayerTable(devw, pTable, 1);
Jon Ashburn8d8dad02014-12-01 14:22:40 -070080 return pTable;
81 } else
82 {
83 return it->second;
84 }
85}
Jon Ashburnd25a78e2015-05-15 16:40:25 -060086static VkLayerInstanceDispatchTable *getLayer1InstanceTable(const VkBaseLayerObject *instw)
Jon Ashburnd9564002015-05-07 10:27:37 -060087{
88 VkLayerInstanceDispatchTable *pTable;
Jon Ashburnd9564002015-05-07 10:27:37 -060089 assert(instw);
Jon Ashburnd25a78e2015-05-15 16:40:25 -060090 VkLayerInstanceDispatchTable **ppDisp = (VkLayerInstanceDispatchTable **) instw->baseObject;
91
92 std::unordered_map<void *, VkLayerInstanceDispatchTable *>::const_iterator it = tableInstanceMap1.find((void *) *ppDisp);
Jon Ashburnd9564002015-05-07 10:27:37 -060093 if (it == tableInstanceMap1.end())
94 {
95 pTable = new VkLayerInstanceDispatchTable;
Jon Ashburnd25a78e2015-05-15 16:40:25 -060096 tableInstanceMap1[(void *) *ppDisp] = pTable;
Jon Ashburnd9564002015-05-07 10:27:37 -060097 initLayerInstanceTable(instw, pTable, 1);
98 return pTable;
99 } else
100 {
101 return it->second;
102 }
103}
Jon Ashburn8d8dad02014-12-01 14:22:40 -0700104#ifdef __cplusplus
105extern "C" {
106#endif
107
Jon Ashburn17f37372015-05-19 16:34:53 -0600108/* hook DextroyDevice to remove tableMap entry */
109VK_LAYER_EXPORT VkResult VKAPI multi1DestroyDevice(VkDevice device)
110{
111 VkLayerDispatchTable *pDisp = *(VkLayerDispatchTable **) device;
Jon Ashburn5a10d212015-06-01 10:02:09 -0600112 VkResult res = device_dispatch_table1(device)->DestroyDevice(device);
Jon Ashburn17f37372015-05-19 16:34:53 -0600113 tableMap1.erase(pDisp);
114 return res;
115}
116
117/* hook DestroyInstance to remove tableInstanceMap entry */
118VK_LAYER_EXPORT VkResult VKAPI multi1DestroyInstance(VkInstance instance)
119{
120 VkLayerInstanceDispatchTable *pDisp = *(VkLayerInstanceDispatchTable **) instance;
Jon Ashburn5a10d212015-06-01 10:02:09 -0600121 VkResult res = instance_dispatch_table1(instance)->DestroyInstance(instance);
Jon Ashburn17f37372015-05-19 16:34:53 -0600122 tableInstanceMap1.erase(pDisp);
123 return res;
124}
125
Jon Ashburn2666e2f2015-05-15 15:09:35 -0600126VK_LAYER_EXPORT VkResult VKAPI multi1CreateSampler(VkDevice device, const VkSamplerCreateInfo* pCreateInfo, VkSampler* pSampler)
Jon Ashburn8d8dad02014-12-01 14:22:40 -0700127{
Jon Ashburnd25a78e2015-05-15 16:40:25 -0600128 VkLayerDispatchTable **ppDisp = (VkLayerDispatchTable **) device;
Jon Ashburn2666e2f2015-05-15 15:09:35 -0600129
130 printf("At start of multi1 layer vkCreateSampler()\n");
Jon Ashburn5a10d212015-06-01 10:02:09 -0600131 VkResult result = device_dispatch_table1(device)->CreateSampler(device, pCreateInfo, pSampler);
Jon Ashburn2666e2f2015-05-15 15:09:35 -0600132 printf("Completed multi1 layer vkCreateSampler()\n");
Jon Ashburn8d8dad02014-12-01 14:22:40 -0700133 return result;
134}
135
Courtney Goeltzenleuchter382489d2015-04-10 08:34:15 -0600136VK_LAYER_EXPORT VkResult VKAPI multi1CreateGraphicsPipeline(VkDevice device, const VkGraphicsPipelineCreateInfo* pCreateInfo,
137 VkPipeline* pPipeline)
Jon Ashburn8d8dad02014-12-01 14:22:40 -0700138{
Jon Ashburnd25a78e2015-05-15 16:40:25 -0600139 VkLayerDispatchTable **ppDisp = (VkLayerDispatchTable **) device;
Jon Ashburn8d8dad02014-12-01 14:22:40 -0700140
Courtney Goeltzenleuchter9cc421e2015-04-08 15:36:08 -0600141 printf("At start of multi1 layer vkCreateGraphicsPipeline()\n");
Jon Ashburn5a10d212015-06-01 10:02:09 -0600142 VkResult result = device_dispatch_table1(device)->CreateGraphicsPipeline(device, pCreateInfo, pPipeline);
Courtney Goeltzenleuchter9cc421e2015-04-08 15:36:08 -0600143 printf("Completed multi1 layer vkCreateGraphicsPipeline()\n");
Jon Ashburn8d8dad02014-12-01 14:22:40 -0700144 return result;
145}
146
Mike Stroyan230e6252015-04-17 12:36:38 -0600147VK_LAYER_EXPORT VkResult VKAPI multi1StorePipeline(VkDevice device, VkPipeline pipeline, size_t* pDataSize, void* pData)
Jon Ashburn8d8dad02014-12-01 14:22:40 -0700148{
Jon Ashburnd25a78e2015-05-15 16:40:25 -0600149 VkLayerDispatchTable **ppDisp = (VkLayerDispatchTable **) device;
Jon Ashburn8d8dad02014-12-01 14:22:40 -0700150
Courtney Goeltzenleuchter9cc421e2015-04-08 15:36:08 -0600151 printf("At start of multi1 layer vkStorePipeline()\n");
Jon Ashburn5a10d212015-06-01 10:02:09 -0600152 VkResult result = device_dispatch_table1(device)->StorePipeline(device, pipeline, pDataSize, pData);
Courtney Goeltzenleuchter9cc421e2015-04-08 15:36:08 -0600153 printf("Completed multi1 layer vkStorePipeline()\n");
Jon Ashburn8d8dad02014-12-01 14:22:40 -0700154 return result;
155}
156
Jon Ashburn1245cec2015-05-18 13:20:15 -0600157VK_LAYER_EXPORT void * VKAPI multi1GetDeviceProcAddr(VkDevice device, const char* pName)
Jon Ashburn8d8dad02014-12-01 14:22:40 -0700158{
Jon Ashburn1245cec2015-05-18 13:20:15 -0600159 VkBaseLayerObject* devw = (VkBaseLayerObject *) device;
Chia-I Wue9ae3882015-01-05 09:41:27 +0800160
Jon Ashburn1245cec2015-05-18 13:20:15 -0600161 if (device == NULL)
Jon Ashburn8d8dad02014-12-01 14:22:40 -0700162 return NULL;
Chia-I Wue9ae3882015-01-05 09:41:27 +0800163
Chia-I Wue9ae3882015-01-05 09:41:27 +0800164
Jon Ashburn4f2575f2015-05-28 16:25:02 -0600165
166 if (!strcmp("vkGetDeviceProcAddr", pName)) {
167 getLayer1Table(devw);
Jon Ashburn7cb4e0e2015-05-19 10:05:54 -0600168 return (void *) multi1GetDeviceProcAddr;
Jon Ashburn4f2575f2015-05-28 16:25:02 -0600169 }
Jon Ashburn17f37372015-05-19 16:34:53 -0600170 if (!strcmp("vkDestroyDevice", pName))
171 return (void *) multi1DestroyDevice;
Jon Ashburn2666e2f2015-05-15 15:09:35 -0600172 if (!strcmp("vkCreateSampler", pName))
173 return (void *) multi1CreateSampler;
Jon Ashburn4f2575f2015-05-28 16:25:02 -0600174 if (!strcmp("vkCreateGraphicsPipeline", pName))
Mark Lobodzinskie2d07a52015-01-29 08:55:56 -0600175 return (void *) multi1CreateGraphicsPipeline;
Jon Ashburn4f2575f2015-05-28 16:25:02 -0600176 if (!strcmp("vkStorePipeline", pName))
Mark Lobodzinskie2d07a52015-01-29 08:55:56 -0600177 return (void *) multi1StorePipeline;
Jon Ashburn8d8dad02014-12-01 14:22:40 -0700178 else {
Jon Ashburn4f2575f2015-05-28 16:25:02 -0600179 VkLayerDispatchTable **ppDisp = (VkLayerDispatchTable **) device;
Jon Ashburn5a10d212015-06-01 10:02:09 -0600180 VkLayerDispatchTable* pTable = device_dispatch_table1(device);
Jon Ashburn4f2575f2015-05-28 16:25:02 -0600181 if (pTable->GetDeviceProcAddr == NULL)
Jon Ashburn8d8dad02014-12-01 14:22:40 -0700182 return NULL;
Jon Ashburn4f2575f2015-05-28 16:25:02 -0600183 return pTable->GetDeviceProcAddr(device, pName);
Jon Ashburn79b78ac2015-05-05 14:22:52 -0600184 }
185}
186
Jon Ashburnd9564002015-05-07 10:27:37 -0600187VK_LAYER_EXPORT void * VKAPI multi1GetInstanceProcAddr(VkInstance inst, const char* pName)
Jon Ashburn79b78ac2015-05-05 14:22:52 -0600188{
189 VkBaseLayerObject* instw = (VkBaseLayerObject *) inst;
190
191 if (inst == NULL)
192 return NULL;
193
Jon Ashburn79b78ac2015-05-05 14:22:52 -0600194
Jon Ashburn4f2575f2015-05-28 16:25:02 -0600195
196 if (!strcmp("vkGetInstanceProcAddr", pName)) {
197 getLayer1InstanceTable(instw);
Jon Ashburn7cb4e0e2015-05-19 10:05:54 -0600198 return (void *) multi1GetInstanceProcAddr;
Jon Ashburn4f2575f2015-05-28 16:25:02 -0600199 }
Jon Ashburn17f37372015-05-19 16:34:53 -0600200 if (!strcmp("vkDestroyInstance", pName))
201 return (void *) multi1DestroyInstance;
Tony Barbour426b9052015-06-24 16:06:58 -0600202 if (!strcmp("GetGlobalExtensionProperties", pName))
203 return (void*) vkGetGlobalExtensionProperties;
204 if (!strcmp("GetGlobalExtensionCount", pName))
205 return (void*) vkGetGlobalExtensionCount;
Jon Ashburn79b78ac2015-05-05 14:22:52 -0600206 else {
Jon Ashburn4f2575f2015-05-28 16:25:02 -0600207 VkLayerInstanceDispatchTable **ppDisp = (VkLayerInstanceDispatchTable **) inst;
Jon Ashburn5a10d212015-06-01 10:02:09 -0600208 VkLayerInstanceDispatchTable* pTable = instance_dispatch_table1(inst);
Jon Ashburn4f2575f2015-05-28 16:25:02 -0600209 if (pTable->GetInstanceProcAddr == NULL)
Jon Ashburn79b78ac2015-05-05 14:22:52 -0600210 return NULL;
Jon Ashburn4f2575f2015-05-28 16:25:02 -0600211 return pTable->GetInstanceProcAddr(inst, pName);
Jon Ashburn8d8dad02014-12-01 14:22:40 -0700212 }
Jon Ashburn8d8dad02014-12-01 14:22:40 -0700213}
214
215/******************************** Layer multi2 functions **************************/
Jon Ashburn301c5f02015-04-06 10:58:22 -0600216static std::unordered_map<void *, VkLayerDispatchTable *> tableMap2;
Jon Ashburnd9564002015-05-07 10:27:37 -0600217static std::unordered_map<void *, VkLayerInstanceDispatchTable *> tableInstanceMap2;
Jon Ashburn8d8dad02014-12-01 14:22:40 -0700218static bool layer2_first_activated = false;
219
Jon Ashburn5a10d212015-06-01 10:02:09 -0600220// Map lookup must be thread safe
221static inline VkLayerDispatchTable *device_dispatch_table2(VkObject object)
222{
223 VkLayerDispatchTable *pDisp = *(VkLayerDispatchTable **) object;
224 std::unordered_map<void *, VkLayerDispatchTable *>::const_iterator it = tableMap2.find((void *) pDisp);
225 assert(it != tableMap2.end() && "Not able to find device dispatch entry");
226 return it->second;
227}
228
229static inline VkLayerInstanceDispatchTable *instance_dispatch_table2(VkObject object)
230{
231 VkLayerInstanceDispatchTable *pDisp = *(VkLayerInstanceDispatchTable **) object;
232 std::unordered_map<void *, VkLayerInstanceDispatchTable *>::const_iterator it = tableInstanceMap2.find((void *) pDisp);
233 assert(it != tableInstanceMap2.end() && "Not able to find instance dispatch entry");
234 return it->second;
235}
236
Jon Ashburnd25a78e2015-05-15 16:40:25 -0600237static VkLayerInstanceDispatchTable *getLayer2InstanceTable(const VkBaseLayerObject *instw)
Jon Ashburnd9564002015-05-07 10:27:37 -0600238{
239 VkLayerInstanceDispatchTable *pTable;
Jon Ashburnd9564002015-05-07 10:27:37 -0600240 assert(instw);
Jon Ashburnd25a78e2015-05-15 16:40:25 -0600241 VkLayerInstanceDispatchTable **ppDisp = (VkLayerInstanceDispatchTable **) instw->baseObject;
242
243 std::unordered_map<void *, VkLayerInstanceDispatchTable *>::const_iterator it = tableInstanceMap2.find((void *) *ppDisp);
Jon Ashburnd9564002015-05-07 10:27:37 -0600244 if (it == tableInstanceMap2.end())
245 {
246 pTable = new VkLayerInstanceDispatchTable;
Jon Ashburnd25a78e2015-05-15 16:40:25 -0600247 tableInstanceMap2[(void *) *ppDisp] = pTable;
Jon Ashburnd9564002015-05-07 10:27:37 -0600248 initLayerInstanceTable(instw, pTable, 2);
249 return pTable;
250 } else
251 {
252 return it->second;
253 }
254}
255
Jon Ashburnd25a78e2015-05-15 16:40:25 -0600256static VkLayerDispatchTable *getLayer2Table(const VkBaseLayerObject *devw)
Jon Ashburn8d8dad02014-12-01 14:22:40 -0700257{
Jon Ashburn301c5f02015-04-06 10:58:22 -0600258 VkLayerDispatchTable *pTable;
Jon Ashburnd25a78e2015-05-15 16:40:25 -0600259 assert(devw);
260 VkLayerDispatchTable **ppDisp = (VkLayerDispatchTable **) devw->baseObject;
Jon Ashburn8d8dad02014-12-01 14:22:40 -0700261
Jon Ashburnd25a78e2015-05-15 16:40:25 -0600262 std::unordered_map<void *, VkLayerDispatchTable *>::const_iterator it = tableMap2.find((void *) *ppDisp);
Jon Ashburn8d8dad02014-12-01 14:22:40 -0700263 if (it == tableMap2.end())
264 {
Jon Ashburn301c5f02015-04-06 10:58:22 -0600265 pTable = new VkLayerDispatchTable;
Jon Ashburnd25a78e2015-05-15 16:40:25 -0600266 tableMap2[(void *) *ppDisp] = pTable;
267 initLayerTable(devw, pTable, 2);
Jon Ashburn8d8dad02014-12-01 14:22:40 -0700268 return pTable;
269 } else
270 {
271 return it->second;
272 }
273}
274
Jon Ashburn2666e2f2015-05-15 15:09:35 -0600275VK_LAYER_EXPORT VkResult VKAPI multi2EnumeratePhysicalDevices(
276 VkInstance instance,
277 uint32_t* pPhysicalDeviceCount,
278 VkPhysicalDevice* pPhysicalDevices)
279{
Jon Ashburnd25a78e2015-05-15 16:40:25 -0600280 VkLayerInstanceDispatchTable **ppDisp = (VkLayerInstanceDispatchTable **) instance;
Jon Ashburnd25a78e2015-05-15 16:40:25 -0600281
Jon Ashburn2666e2f2015-05-15 15:09:35 -0600282 printf("At start of wrapped multi2 vkEnumeratePhysicalDevices()\n");
Jon Ashburn5a10d212015-06-01 10:02:09 -0600283 VkResult result = instance_dispatch_table2(instance)->EnumeratePhysicalDevices(instance, pPhysicalDeviceCount, pPhysicalDevices);
Jon Ashburn2666e2f2015-05-15 15:09:35 -0600284 printf("Completed multi2 layer vkEnumeratePhysicalDevices()\n");
285 return result;
286}
287
Jon Ashburn17f37372015-05-19 16:34:53 -0600288/* hook DextroyDevice to remove tableMap entry */
289VK_LAYER_EXPORT VkResult VKAPI multi2DestroyDevice(VkDevice device)
290{
291 VkLayerDispatchTable *pDisp = *(VkLayerDispatchTable **) device;
Jon Ashburn5a10d212015-06-01 10:02:09 -0600292 VkResult res = device_dispatch_table2(device)->DestroyDevice(device);
Jon Ashburn17f37372015-05-19 16:34:53 -0600293 tableMap2.erase(pDisp);
294 return res;
295}
296
297/* hook DestroyInstance to remove tableInstanceMap entry */
298VK_LAYER_EXPORT VkResult VKAPI multi2DestroyInstance(VkInstance instance)
299{
300 VkLayerInstanceDispatchTable *pDisp = *(VkLayerInstanceDispatchTable **) instance;
Jon Ashburn5a10d212015-06-01 10:02:09 -0600301 VkResult res = instance_dispatch_table2(instance)->DestroyInstance(instance);
Jon Ashburn17f37372015-05-19 16:34:53 -0600302 tableInstanceMap2.erase(pDisp);
303 return res;
304}
305
Tony Barbour8205d902015-04-16 15:59:00 -0600306VK_LAYER_EXPORT VkResult VKAPI multi2CreateDevice(VkPhysicalDevice gpu, const VkDeviceCreateInfo* pCreateInfo,
Courtney Goeltzenleuchter382489d2015-04-10 08:34:15 -0600307 VkDevice* pDevice)
Jon Ashburn8d8dad02014-12-01 14:22:40 -0700308{
Courtney Goeltzenleuchter9cc421e2015-04-08 15:36:08 -0600309 printf("At start of multi2 vkCreateDevice()\n");
Courtney Goeltzenleuchterbe637992015-06-25 18:01:43 -0600310 VkResult result = device_dispatch_table2(*pDevice)->CreateDevice(gpu, pCreateInfo, pDevice);
Courtney Goeltzenleuchter9cc421e2015-04-08 15:36:08 -0600311 printf("Completed multi2 layer vkCreateDevice()\n");
Jon Ashburn8d8dad02014-12-01 14:22:40 -0700312 return result;
313}
314
Courtney Goeltzenleuchter382489d2015-04-10 08:34:15 -0600315VK_LAYER_EXPORT VkResult VKAPI multi2CreateCommandBuffer(VkDevice device, const VkCmdBufferCreateInfo* pCreateInfo,
316 VkCmdBuffer* pCmdBuffer)
Jon Ashburn8d8dad02014-12-01 14:22:40 -0700317{
Jon Ashburnd25a78e2015-05-15 16:40:25 -0600318 VkLayerDispatchTable **ppDisp = (VkLayerDispatchTable **) device;
Jon Ashburn8d8dad02014-12-01 14:22:40 -0700319
Courtney Goeltzenleuchter9cc421e2015-04-08 15:36:08 -0600320 printf("At start of multi2 layer vkCreateCommandBuffer()\n");
Jon Ashburn5a10d212015-06-01 10:02:09 -0600321 VkResult result = device_dispatch_table2(device)->CreateCommandBuffer(device, pCreateInfo, pCmdBuffer);
Courtney Goeltzenleuchter9cc421e2015-04-08 15:36:08 -0600322 printf("Completed multi2 layer vkCreateCommandBuffer()\n");
Jon Ashburn8d8dad02014-12-01 14:22:40 -0700323 return result;
324}
325
Courtney Goeltzenleuchter382489d2015-04-10 08:34:15 -0600326VK_LAYER_EXPORT VkResult VKAPI multi2BeginCommandBuffer(VkCmdBuffer cmdBuffer, const VkCmdBufferBeginInfo* pBeginInfo)
Jon Ashburn8d8dad02014-12-01 14:22:40 -0700327{
Jon Ashburnd25a78e2015-05-15 16:40:25 -0600328 VkLayerDispatchTable **ppDisp = (VkLayerDispatchTable **) cmdBuffer;
Jon Ashburn8d8dad02014-12-01 14:22:40 -0700329
Courtney Goeltzenleuchter9cc421e2015-04-08 15:36:08 -0600330 printf("At start of multi2 layer vkBeginCommandBuffer()\n");
Jon Ashburn5a10d212015-06-01 10:02:09 -0600331 VkResult result = device_dispatch_table2(cmdBuffer)->BeginCommandBuffer(cmdBuffer, pBeginInfo);
Courtney Goeltzenleuchter9cc421e2015-04-08 15:36:08 -0600332 printf("Completed multi2 layer vkBeginCommandBuffer()\n");
Jon Ashburn8d8dad02014-12-01 14:22:40 -0700333 return result;
334
335}
336
Jon Ashburn1245cec2015-05-18 13:20:15 -0600337VK_LAYER_EXPORT void * VKAPI multi2GetDeviceProcAddr(VkDevice device, const char* pName)
Jon Ashburn8d8dad02014-12-01 14:22:40 -0700338{
Jon Ashburn1245cec2015-05-18 13:20:15 -0600339 VkBaseLayerObject* devw = (VkBaseLayerObject *) device;
Chia-I Wue9ae3882015-01-05 09:41:27 +0800340
Jon Ashburn1245cec2015-05-18 13:20:15 -0600341 if (device == NULL)
Jon Ashburn8d8dad02014-12-01 14:22:40 -0700342 return NULL;
Chia-I Wue9ae3882015-01-05 09:41:27 +0800343
Jon Ashburn4f2575f2015-05-28 16:25:02 -0600344 if (!strcmp("vkGetDeviceProcAddr", pName)) {
345 getLayer2Table(devw);
Jon Ashburn7cb4e0e2015-05-19 10:05:54 -0600346 return (void *) multi2GetDeviceProcAddr;
Jon Ashburn4f2575f2015-05-28 16:25:02 -0600347 }
Courtney Goeltzenleuchterbe637992015-06-25 18:01:43 -0600348 if (!strcmp("vkCreateDevice", pName))
349 return (void *) multi2CreateDevice;
Jon Ashburn17f37372015-05-19 16:34:53 -0600350 if (!strcmp("vkDestroyDevice", pName))
351 return (void *) multi2DestroyDevice;
Jon Ashburn1245cec2015-05-18 13:20:15 -0600352 if (!strcmp("vkCreateCommandBuffer", pName))
Mark Lobodzinskie2d07a52015-01-29 08:55:56 -0600353 return (void *) multi2CreateCommandBuffer;
Jon Ashburn79b78ac2015-05-05 14:22:52 -0600354 else if (!strcmp("vkBeginCommandBuffer", pName))
Mark Lobodzinskie2d07a52015-01-29 08:55:56 -0600355 return (void *) multi2BeginCommandBuffer;
Jon Ashburn8d8dad02014-12-01 14:22:40 -0700356 else {
Jon Ashburn4f2575f2015-05-28 16:25:02 -0600357 VkLayerDispatchTable **ppDisp = (VkLayerDispatchTable **) device;
Jon Ashburn5a10d212015-06-01 10:02:09 -0600358 VkLayerDispatchTable* pTable = device_dispatch_table2(device);
Jon Ashburn4f2575f2015-05-28 16:25:02 -0600359 if (pTable->GetDeviceProcAddr == NULL)
Jon Ashburn8d8dad02014-12-01 14:22:40 -0700360 return NULL;
Jon Ashburn4f2575f2015-05-28 16:25:02 -0600361 return pTable->GetDeviceProcAddr(device, pName);
Jon Ashburn79b78ac2015-05-05 14:22:52 -0600362 }
363}
364
Jon Ashburnd9564002015-05-07 10:27:37 -0600365VK_LAYER_EXPORT void * VKAPI multi2GetInstanceProcAddr(VkInstance inst, const char* pName)
Jon Ashburn79b78ac2015-05-05 14:22:52 -0600366{
367 VkBaseLayerObject* instw = (VkBaseLayerObject *) inst;
368
369 if (inst == NULL)
370 return NULL;
371
Jon Ashburn4f2575f2015-05-28 16:25:02 -0600372 if (!strcmp("vkGetInstanceProcAddr", pName)) {
373 getLayer2InstanceTable(instw);
Jon Ashburn7cb4e0e2015-05-19 10:05:54 -0600374 return (void *) multi2GetInstanceProcAddr;
Jon Ashburn4f2575f2015-05-28 16:25:02 -0600375 }
Jon Ashburn2666e2f2015-05-15 15:09:35 -0600376 if (!strcmp("vkEnumeratePhysicalDevices", pName))
377 return (void *) multi2EnumeratePhysicalDevices;
Jon Ashburn17f37372015-05-19 16:34:53 -0600378 if (!strcmp("vkDestroyInstance", pName))
379 return (void *) multi2DestroyInstance;
Tony Barbour426b9052015-06-24 16:06:58 -0600380 else if (!strcmp("GetGlobalExtensionProperties", pName))
381 return (void*) vkGetGlobalExtensionProperties;
382 else if (!strcmp("GetGlobalExtensionCount", pName))
383 return (void*) vkGetGlobalExtensionCount;
Jon Ashburn79b78ac2015-05-05 14:22:52 -0600384 else {
Jon Ashburn4f2575f2015-05-28 16:25:02 -0600385 VkLayerInstanceDispatchTable **ppDisp = (VkLayerInstanceDispatchTable **) inst;
Jon Ashburn5a10d212015-06-01 10:02:09 -0600386 VkLayerInstanceDispatchTable* pTable = instance_dispatch_table2(inst);
Jon Ashburn4f2575f2015-05-28 16:25:02 -0600387 if (pTable->GetInstanceProcAddr == NULL)
Jon Ashburn79b78ac2015-05-05 14:22:52 -0600388 return NULL;
Jon Ashburn4f2575f2015-05-28 16:25:02 -0600389 return pTable->GetInstanceProcAddr(inst, pName);
Jon Ashburn8d8dad02014-12-01 14:22:40 -0700390 }
Jon Ashburn8d8dad02014-12-01 14:22:40 -0700391}
392
393/********************************* Common functions ********************************/
Jon Ashburn8d8dad02014-12-01 14:22:40 -0700394
Jon Ashburneb2728b2015-04-10 14:33:07 -0600395struct extProps {
396 uint32_t version;
397 const char * const name;
398};
399
400#define MULTI_LAYER_EXT_ARRAY_SIZE 2
Courtney Goeltzenleuchter1c7c65d2015-06-10 17:39:03 -0600401static const VkExtensionProperties multiExts[MULTI_LAYER_EXT_ARRAY_SIZE] = {
402 {
403 VK_STRUCTURE_TYPE_EXTENSION_PROPERTIES,
404 "multi1",
405 0x10,
406 "Sample layer: multi",
407// 0,
408// NULL,
409 },
410 {
411 VK_STRUCTURE_TYPE_EXTENSION_PROPERTIES,
412 "multi2",
413 0x10,
414 "Sample layer: multi",
415// 0,
416// NULL,
417 }
Jon Ashburneb2728b2015-04-10 14:33:07 -0600418};
419
Tony Barbour426b9052015-06-24 16:06:58 -0600420VK_LAYER_EXPORT VkResult VKAPI vkGetGlobalExtensionCount(
421 uint32_t* pCount)
422{
423 *pCount = MULTI_LAYER_EXT_ARRAY_SIZE;
424 return VK_SUCCESS;
425}
426
427VK_LAYER_EXPORT VkResult VKAPI vkGetGlobalExtensionProperties(
Courtney Goeltzenleuchter1c7c65d2015-06-10 17:39:03 -0600428 uint32_t extensionIndex,
Tony Barbour426b9052015-06-24 16:06:58 -0600429 VkExtensionProperties* pProperties)
Jon Ashburneb2728b2015-04-10 14:33:07 -0600430{
Jon Ashburneb2728b2015-04-10 14:33:07 -0600431 /* This entrypoint is NOT going to init it's own dispatch table since loader calls here early */
Tony Barbour426b9052015-06-24 16:06:58 -0600432 if (extensionIndex >= MULTI_LAYER_EXT_ARRAY_SIZE)
433 return VK_ERROR_INVALID_VALUE;
Jon Ashburneb2728b2015-04-10 14:33:07 -0600434
Tony Barbour426b9052015-06-24 16:06:58 -0600435 memcpy(pProperties, &multiExts[extensionIndex], sizeof(VkExtensionProperties));
Jon Ashburneb2728b2015-04-10 14:33:07 -0600436
437 return VK_SUCCESS;
438}
439
Jon Ashburn1245cec2015-05-18 13:20:15 -0600440VK_LAYER_EXPORT void * VKAPI vkGetDeviceProcAddr(VkDevice device, const char* pName)
Jon Ashburn8d8dad02014-12-01 14:22:40 -0700441{
Jon Ashburn1245cec2015-05-18 13:20:15 -0600442 // to find each layers GPA routine Loader will search via "<layerName>GetDeviceProcAddr"
443 if (!strcmp("multi1GetDeviceProcAddr", pName))
444 return (void *) multi1GetDeviceProcAddr;
445 else if (!strcmp("multi2GetDeviceProcAddr", pName))
446 return (void *) multi2GetDeviceProcAddr;
447 else if (!strcmp("vkGetDeviceProcAddr", pName))
448 return (void *) vkGetDeviceProcAddr;
Jon Ashburn8d8dad02014-12-01 14:22:40 -0700449
450 // use first layer activated as GPA dispatch table activation happens in order
451 else if (layer1_first_activated)
Jon Ashburn1245cec2015-05-18 13:20:15 -0600452 return multi1GetDeviceProcAddr(device, pName);
Jon Ashburn8d8dad02014-12-01 14:22:40 -0700453 else if (layer2_first_activated)
Jon Ashburn1245cec2015-05-18 13:20:15 -0600454 return multi2GetDeviceProcAddr(device, pName);
Jon Ashburn8d8dad02014-12-01 14:22:40 -0700455 else
456 return NULL;
457
458}
459
Jon Ashburn79b78ac2015-05-05 14:22:52 -0600460VK_LAYER_EXPORT void * VKAPI vkGetInstanceProcAddr(VkInstance inst, const char* pName)
461{
Jon Ashburn1245cec2015-05-18 13:20:15 -0600462 // to find each layers GPA routine Loader will search via "<layerName>GetInstanceProcAddr"
463 if (!strcmp("multi1GetInstanceProcAddr", pName))
Jon Ashburnd9564002015-05-07 10:27:37 -0600464 return (void *) multi1GetInstanceProcAddr;
Jon Ashburn79b78ac2015-05-05 14:22:52 -0600465 else if (!strcmp("multi2GetInstanceProcAddr", pName))
Jon Ashburnd9564002015-05-07 10:27:37 -0600466 return (void *) multi2GetInstanceProcAddr;
Jon Ashburn79b78ac2015-05-05 14:22:52 -0600467 else if (!strcmp("vkGetInstanceProcAddr", pName))
Jon Ashburn1245cec2015-05-18 13:20:15 -0600468 return (void *) vkGetInstanceProcAddr;
Jon Ashburn79b78ac2015-05-05 14:22:52 -0600469
470 // use first layer activated as GPA dispatch table activation happens in order
471 else if (layer1_first_activated)
Jon Ashburnd9564002015-05-07 10:27:37 -0600472 return multi1GetInstanceProcAddr(inst, pName);
Jon Ashburn79b78ac2015-05-05 14:22:52 -0600473 else if (layer2_first_activated)
Jon Ashburnd9564002015-05-07 10:27:37 -0600474 return multi2GetInstanceProcAddr(inst, pName);
Jon Ashburn79b78ac2015-05-05 14:22:52 -0600475 else
476 return NULL;
477
478}
Jon Ashburn8d8dad02014-12-01 14:22:40 -0700479#ifdef __cplusplus
480} //extern "C"
481#endif
482
Jon Ashburn1245cec2015-05-18 13:20:15 -0600483static void initLayerTable(const VkBaseLayerObject *devw, VkLayerDispatchTable *pTable, const unsigned int layerNum)
Jon Ashburn8d8dad02014-12-01 14:22:40 -0700484{
Jon Ashburn8d8dad02014-12-01 14:22:40 -0700485 if (layerNum == 2 && layer1_first_activated == false)
486 layer2_first_activated = true;
487 if (layerNum == 1 && layer2_first_activated == false)
488 layer1_first_activated = true;
489
Jon Ashburn4f2575f2015-05-28 16:25:02 -0600490 layer_initialize_dispatch_table(pTable, devw);
Jon Ashburn8d8dad02014-12-01 14:22:40 -0700491}
Jon Ashburnd9564002015-05-07 10:27:37 -0600492
493static void initLayerInstanceTable(const VkBaseLayerObject *instw, VkLayerInstanceDispatchTable *pTable, const unsigned int layerNum)
494{
495 if (layerNum == 2 && layer1_first_activated == false)
496 layer2_first_activated = true;
497 if (layerNum == 1 && layer2_first_activated == false)
498 layer1_first_activated = true;
499
Jon Ashburn4f2575f2015-05-28 16:25:02 -0600500 layer_init_instance_dispatch_table(pTable, instw);
Jon Ashburnd9564002015-05-07 10:27:37 -0600501}