blob: cc8ed3ba03cb909aa96b9201c3649476ea85d74e [file] [log] [blame]
// Copyright 2019 The Dawn Authors
//
// Licensed under the Apache License, Version 2.0 (the "License");
// you may not use this file except in compliance with the License.
// You may obtain a copy of the License at
//
// http://www.apache.org/licenses/LICENSE-2.0
//
// Unless required by applicable law or agreed to in writing, software
// distributed under the License is distributed on an "AS IS" BASIS,
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
// See the License for the specific language governing permissions and
// limitations under the License.
// A mock GLFW implementation that supports Fuchsia, but only implements
// the functions called from Dawn.
// NOTE: This must be included before GLFW/glfw3.h because the latter will
// include <vulkan/vulkan.h> and "common/vulkan_platform.h" wants to be
// the first header to do so for sanity reasons (e.g. undefining weird
// macros on Windows and Linux).
// clang-format off
#include "common/vulkan_platform.h"
#include "common/Assert.h"
#include <GLFW/glfw3.h>
// clang-format on
#include <dlfcn.h>
int glfwInit(void) {
return GLFW_TRUE;
}
void glfwDefaultWindowHints(void) {
}
void glfwWindowHint(int hint, int value) {
DAWN_UNUSED(hint);
DAWN_UNUSED(value);
}
struct GLFWwindow {
PFN_vkGetInstanceProcAddr GetInstanceProcAddress = nullptr;
void* vulkan_loader = nullptr;
GLFWwindow() {
vulkan_loader = ::dlopen("libvulkan.so", RTLD_NOW);
ASSERT(vulkan_loader != nullptr);
GetInstanceProcAddress = reinterpret_cast<PFN_vkGetInstanceProcAddr>(
dlsym(vulkan_loader, "vkGetInstanceProcAddr"));
ASSERT(GetInstanceProcAddress != nullptr);
}
~GLFWwindow() {
if (vulkan_loader) {
::dlclose(vulkan_loader);
}
vulkan_loader = nullptr;
}
};
GLFWwindow* glfwCreateWindow(int width,
int height,
const char* title,
GLFWmonitor* monitor,
GLFWwindow* share) {
ASSERT(monitor == nullptr);
ASSERT(share == nullptr);
DAWN_UNUSED(width);
DAWN_UNUSED(height);
DAWN_UNUSED(title);
return new GLFWwindow();
}
VkResult glfwCreateWindowSurface(VkInstance instance,
GLFWwindow* window,
const VkAllocationCallbacks* allocator,
VkSurfaceKHR* surface) {
// IMPORTANT: This assumes that the VkInstance was created with a Fuchsia
// swapchain layer enabled, as well as the corresponding extension that
// is queried here to perform the surface creation. Dawn should do all
// required steps in VulkanInfo.cpp, VulkanFunctions.cpp and BackendVk.cpp.
auto vkCreateImagePipeSurfaceFUCHSIA = reinterpret_cast<PFN_vkCreateImagePipeSurfaceFUCHSIA>(
window->GetInstanceProcAddress(instance, "vkCreateImagePipeSurfaceFUCHSIA"));
ASSERT(vkCreateImagePipeSurfaceFUCHSIA != nullptr);
if (!vkCreateImagePipeSurfaceFUCHSIA) {
*surface = VK_NULL_HANDLE;
return VK_ERROR_FEATURE_NOT_PRESENT;
}
const struct VkImagePipeSurfaceCreateInfoFUCHSIA create_info = {
VK_STRUCTURE_TYPE_IMAGEPIPE_SURFACE_CREATE_INFO_FUCHSIA,
nullptr, // pNext
0, // flags, ignored for now
ZX_HANDLE_INVALID, // imagePipeHandle, a null handle matches the framebuffer.
};
return vkCreateImagePipeSurfaceFUCHSIA(instance, &create_info, nullptr, surface);
}