• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 //
2 // Copyright 2019 The ANGLE Project Authors. All rights reserved.
3 // Use of this source code is governed by a BSD-style license that can be
4 // found in the LICENSE file.
5 //
6 // mtl_utils.h:
7 //    Declares utilities functions that create Metal shaders, convert from angle enums
8 //    to Metal enums and so on.
9 //
10 
11 #ifndef LIBANGLE_RENDERER_METAL_MTL_UTILS_H_
12 #define LIBANGLE_RENDERER_METAL_MTL_UTILS_H_
13 
14 #import <Metal/Metal.h>
15 
16 #include "angle_gl.h"
17 #include "common/PackedEnums.h"
18 #include "libANGLE/Context.h"
19 #include "libANGLE/Texture.h"
20 #include "libANGLE/renderer/metal/mtl_format_utils.h"
21 #include "libANGLE/renderer/metal/mtl_resources.h"
22 #include "libANGLE/renderer/metal/mtl_state_cache.h"
23 
24 namespace rx
25 {
26 
27 class ContextMtl;
28 
29 void StartFrameCapture(id<MTLDevice> metalDevice, id<MTLCommandQueue> metalCmdQueue);
30 void StartFrameCapture(ContextMtl *context);
31 void StopFrameCapture();
32 
33 namespace mtl
34 {
35 
36 // Initialize texture content to black.
37 angle::Result InitializeTextureContents(const gl::Context *context,
38                                         const TextureRef &texture,
39                                         const Format &textureObjFormat,
40                                         const ImageNativeIndex &index);
41 // Same as above but using GPU clear operation instead of CPU.
42 // - channelsToInit parameter controls which channels will get their content initialized.
43 angle::Result InitializeTextureContentsGPU(const gl::Context *context,
44                                            const TextureRef &texture,
45                                            const Format &textureObjFormat,
46                                            const ImageNativeIndex &index,
47                                            MTLColorWriteMask channelsToInit);
48 
49 // Same as above but for a depth/stencil texture.
50 angle::Result InitializeDepthStencilTextureContentsGPU(const gl::Context *context,
51                                                        const TextureRef &texture,
52                                                        const Format &textureObjFormat,
53                                                        const ImageNativeIndex &index);
54 
55 // Unified texture's per slice/depth texel reading function
56 angle::Result ReadTexturePerSliceBytes(const gl::Context *context,
57                                        const TextureRef &texture,
58                                        size_t bytesPerRow,
59                                        const gl::Rectangle &fromRegion,
60                                        const MipmapNativeLevel &mipLevel,
61                                        uint32_t sliceOrDepth,
62                                        uint8_t *dataOut);
63 
64 angle::Result ReadTexturePerSliceBytesToBuffer(const gl::Context *context,
65                                                const TextureRef &texture,
66                                                size_t bytesPerRow,
67                                                const gl::Rectangle &fromRegion,
68                                                const MipmapNativeLevel &mipLevel,
69                                                uint32_t sliceOrDepth,
70                                                uint32_t dstOffset,
71                                                const BufferRef &dstBuffer);
72 
73 MTLViewport GetViewport(const gl::Rectangle &rect, double znear = 0, double zfar = 1);
74 MTLViewport GetViewportFlipY(const gl::Rectangle &rect,
75                              NSUInteger screenHeight,
76                              double znear = 0,
77                              double zfar  = 1);
78 MTLViewport GetViewport(const gl::Rectangle &rect,
79                         NSUInteger screenHeight,
80                         bool flipY,
81                         double znear = 0,
82                         double zfar  = 1);
83 MTLScissorRect GetScissorRect(const gl::Rectangle &rect,
84                               NSUInteger screenHeight = 0,
85                               bool flipY              = false);
86 
87 uint32_t GetDeviceVendorId(id<MTLDevice> metalDevice);
88 
89 AutoObjCPtr<id<MTLLibrary>> CreateShaderLibrary(
90     const mtl::ContextDevice &metalDevice,
91     const std::string &source,
92     NSDictionary<NSString *, NSObject *> *substitutionDictionary,
93     bool enableFastMath,
94     AutoObjCPtr<NSError *> *error);
95 
96 AutoObjCPtr<id<MTLLibrary>> CreateShaderLibrary(const mtl::ContextDevice &metalDevice,
97                                                 const std::string &source,
98                                                 AutoObjCPtr<NSError *> *error);
99 
100 AutoObjCPtr<id<MTLLibrary>> CreateShaderLibrary(
101     const mtl::ContextDevice &metalDevice,
102     const char *source,
103     size_t sourceLen,
104     NSDictionary<NSString *, NSObject *> *substitutionDictionary,
105     bool enableFastMath,
106     AutoObjCPtr<NSError *> *error);
107 
108 AutoObjCPtr<id<MTLLibrary>> CreateShaderLibraryFromBinary(
109     id<MTLDevice> metalDevice,
110     const uint8_t *binarySource,
111     size_t binarySourceLen,
112     NSDictionary<NSString *, NSObject *> *substitutionDictionary,
113     AutoObjCPtr<NSError *> *error);
114 
115 bool SupportsAppleGPUFamily(id<MTLDevice> device, uint8_t appleFamily);
116 
117 bool SupportsMacGPUFamily(id<MTLDevice> device, uint8_t macFamily);
118 
119 // Need to define invalid enum value since Metal doesn't define it
120 constexpr MTLTextureType MTLTextureTypeInvalid = static_cast<MTLTextureType>(NSUIntegerMax);
121 static_assert(sizeof(MTLTextureType) == sizeof(NSUInteger),
122               "MTLTextureType is supposed to be based on NSUInteger");
123 
124 constexpr MTLPrimitiveType MTLPrimitiveTypeInvalid = static_cast<MTLPrimitiveType>(NSUIntegerMax);
125 static_assert(sizeof(MTLPrimitiveType) == sizeof(NSUInteger),
126               "MTLPrimitiveType is supposed to be based on NSUInteger");
127 
128 constexpr MTLIndexType MTLIndexTypeInvalid = static_cast<MTLIndexType>(NSUIntegerMax);
129 static_assert(sizeof(MTLIndexType) == sizeof(NSUInteger),
130               "MTLIndexType is supposed to be based on NSUInteger");
131 
132 MTLTextureType GetTextureType(gl::TextureType glType);
133 
134 MTLSamplerMinMagFilter GetFilter(GLenum filter);
135 MTLSamplerMipFilter GetMipmapFilter(GLenum filter);
136 MTLSamplerAddressMode GetSamplerAddressMode(GLenum wrap);
137 
138 MTLBlendFactor GetBlendFactor(GLenum factor);
139 MTLBlendOperation GetBlendOp(GLenum op);
140 
141 MTLCompareFunction GetCompareFunc(GLenum func);
142 MTLStencilOperation GetStencilOp(GLenum op);
143 
144 MTLWinding GetFontfaceWinding(GLenum frontFaceMode, bool invert);
145 
146 PrimitiveTopologyClass GetPrimitiveTopologyClass(gl::PrimitiveMode mode);
147 MTLPrimitiveType GetPrimitiveType(gl::PrimitiveMode mode);
148 MTLIndexType GetIndexType(gl::DrawElementsType type);
149 
150 #if ANGLE_MTL_SWIZZLE_AVAILABLE
151 MTLTextureSwizzle GetTextureSwizzle(GLenum swizzle);
152 #endif
153 
154 // Get color write mask for a specified format. Some formats such as RGB565 doesn't have alpha
155 // channel but is emulated by a RGBA8 format, we need to disable alpha write for this format.
156 // - emulatedChannelsOut: if the format is emulated, this pointer will store a true value.
157 MTLColorWriteMask GetEmulatedColorWriteMask(const mtl::Format &mtlFormat,
158                                             bool *emulatedChannelsOut);
159 MTLColorWriteMask GetEmulatedColorWriteMask(const mtl::Format &mtlFormat);
160 bool IsFormatEmulated(const mtl::Format &mtlFormat);
161 size_t EstimateTextureSizeInBytes(const mtl::Format &mtlFormat,
162                                   size_t width,
163                                   size_t height,
164                                   size_t depth,
165                                   size_t sampleCount,
166                                   size_t numMips);
167 
168 NSUInteger GetMaxRenderTargetSizeForDeviceInBytes(const mtl::ContextDevice &device);
169 NSUInteger GetMaxNumberOfRenderTargetsForDevice(const mtl::ContextDevice &device);
170 bool DeviceHasMaximumRenderTargetSize(id<MTLDevice> device);
171 
172 // Useful to set clear color for texture originally having no alpha in GL, but backend's format
173 // has alpha channel.
174 MTLClearColor EmulatedAlphaClearColor(MTLClearColor color, MTLColorWriteMask colorMask);
175 
176 NSUInteger ComputeTotalSizeUsedForMTLRenderPassDescriptor(const MTLRenderPassDescriptor *descriptor,
177                                                           const Context *context,
178                                                           const mtl::ContextDevice &device);
179 
180 NSUInteger ComputeTotalSizeUsedForMTLRenderPipelineDescriptor(
181     const MTLRenderPipelineDescriptor *descriptor,
182     const Context *context,
183     const mtl::ContextDevice &device);
184 
185 gl::Box MTLRegionToGLBox(const MTLRegion &mtlRegion);
186 
187 MipmapNativeLevel GetNativeMipLevel(GLuint level, GLuint base);
188 GLuint GetGLMipLevel(const MipmapNativeLevel &nativeLevel, GLuint base);
189 
190 angle::Result TriangleFanBoundCheck(ContextMtl *context, size_t numTris);
191 
192 angle::Result GetTriangleFanIndicesCount(ContextMtl *context,
193                                          GLsizei vetexCount,
194                                          uint32_t *numElemsOut);
195 
196 angle::Result CreateMslShader(Context *context,
197                               id<MTLLibrary> shaderLib,
198                               NSString *shaderName,
199                               MTLFunctionConstantValues *funcConstants,
200                               AutoObjCPtr<id<MTLFunction>> *shaderOut);
201 
202 angle::Result CreateMslShader(Context *context,
203                               id<MTLLibrary> shaderLib,
204                               NSString *shaderName,
205                               MTLFunctionConstantValues *funcConstants,
206                               id<MTLFunction> *shaderOut);
207 
208 }  // namespace mtl
209 }  // namespace rx
210 
211 #endif /* LIBANGLE_RENDERER_METAL_MTL_UTILS_H_ */
212