summaryrefslogtreecommitdiff
path: root/drivers/vulkan/vulkan_context.h
blob: 7a62ef51e207db972dce2d7203f86108740769d6 (plain)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
#ifndef VULKAN_CONTEXT_H
#define VULKAN_CONTEXT_H

#include "core/error_list.h"
#include "core/ustring.h"
#include <vulkan/vulkan.h>

class VulkanContext {

	enum {
		MAX_EXTENSIONS = 128,
		MAX_LAYERS = 64,
		FRAME_LAG = 2
	};

	bool use_validation_layers;

	VkInstance inst;
	VkSurfaceKHR surface;
	VkPhysicalDevice gpu;
	VkPhysicalDeviceProperties gpu_props;
	uint32_t queue_family_count;
	VkQueueFamilyProperties *queue_props;
	VkDevice device;

	//present
	uint32_t graphics_queue_family_index;
	uint32_t present_queue_family_index;
	bool separate_present_queue;
	VkQueue graphics_queue;
	VkQueue present_queue;
	VkColorSpaceKHR color_space;
	VkFormat format;
	VkSemaphore image_acquired_semaphores[FRAME_LAG];
	VkSemaphore draw_complete_semaphores[FRAME_LAG];
	VkSemaphore image_ownership_semaphores[FRAME_LAG];
	int frame_index;
	VkFence fences[FRAME_LAG];
	VkPhysicalDeviceMemoryProperties memory_properties;

	typedef struct {
		VkImage image;
		VkCommandBuffer cmd;
		VkCommandBuffer graphics_to_present_cmd;
		VkImageView view;
		VkBuffer uniform_buffer;
		VkDeviceMemory uniform_memory;
		VkFramebuffer framebuffer;
		VkDescriptorSet descriptor_set;
	} SwapchainImageResources;

	VkSwapchainKHR swapchain;
	SwapchainImageResources *swapchain_image_resources;
	VkPresentModeKHR presentMode;
	uint32_t swapchainImageCount;
	uint64_t refresh_duration;
	bool syncd_with_actual_presents;
	uint64_t refresh_duration_multiplier;
	uint64_t target_IPD; // image present duration (inverse of frame rate)
	uint64_t prev_desired_present_time;
	uint32_t next_present_id;
	uint32_t last_early_id; // 0 if no early images
	uint32_t last_late_id; // 0 if no late images
	bool is_minimized;
	uint32_t current_buffer;

	//commands
	VkRenderPass render_pass;
	VkCommandPool present_cmd_pool; //for separate present queue

	bool prepared;
	int width, height;

	//extensions
	bool VK_KHR_incremental_present_enabled;
	bool VK_GOOGLE_display_timing_enabled;
	const char **instance_validation_layers;
	uint32_t enabled_extension_count;
	uint32_t enabled_layer_count;
	const char *extension_names[MAX_EXTENSIONS];
	const char *enabled_layers[MAX_LAYERS];

	PFN_vkCreateDebugUtilsMessengerEXT CreateDebugUtilsMessengerEXT;
	PFN_vkDestroyDebugUtilsMessengerEXT DestroyDebugUtilsMessengerEXT;
	PFN_vkSubmitDebugUtilsMessageEXT SubmitDebugUtilsMessageEXT;
	PFN_vkCmdBeginDebugUtilsLabelEXT CmdBeginDebugUtilsLabelEXT;
	PFN_vkCmdEndDebugUtilsLabelEXT CmdEndDebugUtilsLabelEXT;
	PFN_vkCmdInsertDebugUtilsLabelEXT CmdInsertDebugUtilsLabelEXT;
	PFN_vkSetDebugUtilsObjectNameEXT SetDebugUtilsObjectNameEXT;
	PFN_vkGetPhysicalDeviceSurfaceSupportKHR fpGetPhysicalDeviceSurfaceSupportKHR;
	PFN_vkGetPhysicalDeviceSurfaceCapabilitiesKHR fpGetPhysicalDeviceSurfaceCapabilitiesKHR;
	PFN_vkGetPhysicalDeviceSurfaceFormatsKHR fpGetPhysicalDeviceSurfaceFormatsKHR;
	PFN_vkGetPhysicalDeviceSurfacePresentModesKHR fpGetPhysicalDeviceSurfacePresentModesKHR;
	PFN_vkCreateSwapchainKHR fpCreateSwapchainKHR;
	PFN_vkDestroySwapchainKHR fpDestroySwapchainKHR;
	PFN_vkGetSwapchainImagesKHR fpGetSwapchainImagesKHR;
	PFN_vkAcquireNextImageKHR fpAcquireNextImageKHR;
	PFN_vkQueuePresentKHR fpQueuePresentKHR;
	PFN_vkGetRefreshCycleDurationGOOGLE fpGetRefreshCycleDurationGOOGLE;
	PFN_vkGetPastPresentationTimingGOOGLE fpGetPastPresentationTimingGOOGLE;

	VkDebugUtilsMessengerEXT dbg_messenger;

	Error _create_validation_layers();
	Error _initialize_extensions();

	VkBool32 _check_layers(uint32_t check_count, const char **check_names, uint32_t layer_count, VkLayerProperties *layers);
	static VKAPI_ATTR VkBool32 VKAPI_CALL _debug_messenger_callback(VkDebugUtilsMessageSeverityFlagBitsEXT messageSeverity,
			VkDebugUtilsMessageTypeFlagsEXT messageType,
			const VkDebugUtilsMessengerCallbackDataEXT *pCallbackData,
			void *pUserData);

	Error _create_physical_device();
	Error _create_device();
	Error _create_swap_chain();
	Error _create_semaphores();

	Error _prepare_buffers();
	Error _prepare_framebuffers();
	Error _create_buffers();

	int screen_width;
	int screen_height;
	bool minimized;

	Vector<VkCommandBuffer> command_buffer_queue;
	int command_buffer_count;

protected:
	virtual const char *_get_platform_surface_extension() const = 0;
	virtual VkResult _create_surface(VkSurfaceKHR *surface, VkInstance p_instance) = 0;

	VkSurfaceKHR &get_surface() { return surface; }

public:
	VkDevice get_device();
	VkPhysicalDevice get_physical_device();
	int get_frame_count() const;
	uint32_t get_graphics_queue() const;

	int get_screen_width(int p_screen = 0);
	int get_screen_height(int p_screen = 0);

	VkFramebuffer get_frame_framebuffer(int p_frame);
	VkRenderPass get_render_pass();
	VkFormat get_screen_format() const;
	VkPhysicalDeviceLimits get_device_limits() const;

	void set_setup_buffer(const VkCommandBuffer &pCommandBuffer);
	void append_command_buffer(const VkCommandBuffer &pCommandBuffer);
	void resize_notify();
	void flush(bool p_flush_setup = false, bool p_flush_pending = false);
	Error swap_buffers();
	Error initialize(int p_width, int p_height, bool p_minimized);
	VulkanContext();
};

#endif // VULKAN_DEVICE_H