• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 #ifndef DISPLAY_VK_H
2 #define DISPLAY_VK_H
3 
4 #include <functional>
5 #include <memory>
6 #include <unordered_map>
7 
8 #include "CompositorVk.h"
9 #include "Hwc2.h"
10 #include "RenderContext.h"
11 #include "SwapChainStateVk.h"
12 #include "vulkan/cereal/common/goldfish_vk_dispatch.h"
13 
14 // The DisplayVk class holds the Vulkan and other states required to draw a
15 // frame in a host window.
16 
17 class DisplayVk {
18    public:
19     class DisplayBufferInfo {
20        public:
21         ~DisplayBufferInfo();
22 
23        private:
24         DisplayBufferInfo(const goldfish_vk::VulkanDispatch &, VkDevice,
25                           uint32_t width, uint32_t height, VkFormat, VkImage);
26 
27         const goldfish_vk::VulkanDispatch &m_vk;
28         VkDevice m_vkDevice;
29         uint32_t m_width;
30         uint32_t m_height;
31         VkFormat m_vkFormat;
32 
33         VkImageView m_vkImageView;
34 
35         friend class DisplayVk;
36     };
37     DisplayVk(const goldfish_vk::VulkanDispatch &, VkPhysicalDevice,
38               uint32_t swapChainQueueFamilyIndex,
39               uint32_t compositorQueueFamilyIndex, VkDevice,
40               VkQueue compositorVkQueue, VkQueue swapChainVkQueue);
41     ~DisplayVk();
42     void bindToSurface(VkSurfaceKHR, uint32_t width, uint32_t height);
43     // The caller is responsible to make sure the VkImage lives longer than the
44     // DisplayBufferInfo created here. However, given that DisplayBufferInfo
45     // lives in a shared_ptr, the potential lifetime of DisplayBufferInfo is
46     // aligned to DisplayVk when DisplayVk::m_surfaceState::m_prevDisplayBuffer
47     // is locked and upgraded to a shared_ptr in DisplayVk::post.
48     std::shared_ptr<DisplayBufferInfo> createDisplayBuffer(VkImage, VkFormat,
49                                                            uint32_t width,
50                                                            uint32_t height);
51     void post(const std::shared_ptr<DisplayBufferInfo> &);
52 
53     void compose(
54         uint32_t numLayers, const ComposeLayer layers[],
55         const std::vector<std::shared_ptr<DisplayBufferInfo>> &composeBuffers);
56 
57    private:
58     bool canComposite(VkFormat);
59     // Returns if the composition specified by the parameter is different from
60     // the previous composition. If the composition is different, update the
61     // previous composition stored in m_surfaceState. Must be called after
62     // bindToSurface() is called.
63     bool compareAndSaveComposition(
64         uint32_t renderTargetIndex, uint32_t numLayers,
65         const ComposeLayer layers[],
66         const std::vector<std::shared_ptr<DisplayBufferInfo>> &composeBuffers);
67 
68     const goldfish_vk::VulkanDispatch &m_vk;
69     VkPhysicalDevice m_vkPhysicalDevice;
70     uint32_t m_swapChainQueueFamilyIndex;
71     uint32_t m_compositorQueueFamilyIndex;
72     VkDevice m_vkDevice;
73     VkQueue m_compositorVkQueue;
74     VkQueue m_swapChainVkQueue;
75     VkCommandPool m_vkCommandPool;
76     VkSampler m_compositionVkSampler;
77     VkFence m_frameDrawCompleteFence;
78     VkSemaphore m_imageReadySem;
79     VkSemaphore m_frameDrawCompleteSem;
80 
81     std::unique_ptr<SwapChainStateVk> m_swapChainStateVk;
82     std::unique_ptr<CompositorVk> m_compositorVk;
83     struct SurfaceState {
84         struct Layer {
85             ComposeLayer m_hwc2Layer;
86             std::weak_ptr<DisplayBufferInfo> m_displayBuffer;
87         };
88 
89         uint32_t m_width = 0;
90         uint32_t m_height = 0;
91         std::unordered_map<uint32_t, std::vector<std::unique_ptr<Layer>>>
92             m_prevCompositions;
93     };
94     std::unique_ptr<SurfaceState> m_surfaceState;
95     std::unordered_map<VkFormat, bool> m_canComposite;
96 };
97 
98 #endif
99