Skip to content

Commit

Permalink
Add VK_EXT_external_memory_metal (#2414)
Browse files Browse the repository at this point in the history
* Add VK_EXT_external_memory_metal

* Add missing VUIDs for VK_EXT_external_memory_metal

* Add MTLHeap as a possible handle to export/import

* Reword lifespan segment, merge VUID and fix typos

* VK_EXT_external_memory_metal fix build due to rebase issue

* VK_EXT_external_memory_metal has no features

* VK_EXT_external_memory_metal add missing const to param

* VK_EXT_external_memory_metal fix parameter name

* VK_EXT_external_memory_metal address MTLHeap and VUID feedback

* VK_EXT_external_memory_metal typo fixes and allocationSize VUID

* VK_EXT_external_memory_metal fix "impor" typo
  • Loading branch information
aitor-lunarg authored Jan 24, 2025
1 parent 840c7b8 commit 25ec2b7
Show file tree
Hide file tree
Showing 8 changed files with 402 additions and 18 deletions.
27 changes: 27 additions & 0 deletions appendices/VK_EXT_external_memory_metal.adoc
Original file line number Diff line number Diff line change
@@ -0,0 +1,27 @@
// Copyright 2024 The Khronos Group Inc.
//
// SPDX-License-Identifier: CC-BY-4.0

include::{generated}/meta/{refprefix}VK_EXT_external_memory_metal.adoc[]

=== Other Extension Metadata

*Last Modified Date*::
2024-07-18
*IP Status*::
No known IP claims.
*Contributors*::
- Aitor Camacho Larrondo, LunarG Inc.

=== Description

An application may wish to reference device memory in multiple Vulkan device instances, in multiple processes, and/or in Metal API.
This extension enables an application to export and import Metal handles from Vulkan memory objects such that the underlying
resources can be referenced outside the scope of the Vulkan device instance that created them.

include::{generated}/interfaces/VK_EXT_external_memory_metal.adoc[]

=== Version History

* Revision 1, 2024-07-18 (Aitor Camacho Larrondo)
** Initial revision
153 changes: 153 additions & 0 deletions chapters/VK_EXT_external_memory_metal/device_memory.adoc
Original file line number Diff line number Diff line change
@@ -0,0 +1,153 @@
// Copyright 2024 The Khronos Group Inc.
//
// SPDX-License-Identifier: CC-BY-4.0

=== Metal External Memory

[open,refpage='VkImportMemoryMetalHandleInfoEXT',desc='Import Metal memory created on the same physical device',type='structs']
--
To import memory from a Metal handle, add a
slink:VkImportMemoryMetalHandleInfoEXT structure to the pname:pNext chain of
the slink:VkMemoryAllocateInfo structure.

The sname:VkImportMemoryMetalHandleInfoEXT structure is defined as:

include::{generated}/api/structs/VkImportMemoryMetalHandleInfoEXT.adoc[]

* pname:sType is a elink:VkStructureType value identifying this structure.
* pname:pNext is `NULL` or a pointer to a structure extending this
structure.
* pname:handleType is a elink:VkExternalMemoryHandleTypeFlagBits value
specifying the type of pname:handle or pname:name.
* pname:handle is `NULL` or the external handle to import.

Importing memory object payloads from Metal handles shares the
ownership of the handle to the Vulkan implementation.

Applications can: import the same payload into multiple instances of Vulkan,
into the same instance from which it was exported, and multiple times into a
given Vulkan instance.
In all cases, each import operation must: create a distinct
sname:VkDeviceMemory object.

.Valid Usage
****
* If pname:handleType is not `0`, it must: be supported for import, as
reported by slink:VkExternalImageFormatProperties or
slink:VkExternalBufferProperties
* The memory from which pname:handle was exported must: have been created
on the same underlying physical device as pname:device
* If pname:handleType is not `0`, it must: be
ename:VK_EXTERNAL_MEMORY_HANDLE_TYPE_MTLBUFFER_BIT_EXT,
ename:VK_EXTERNAL_MEMORY_HANDLE_TYPE_MTLTEXTURE_BIT_EXT or
ename:VK_EXTERNAL_MEMORY_HANDLE_TYPE_MTLHEAP_BIT_EXT
* If pname:handleType is not `0` , pname:handle must: be a valid non-NULL
handle of the type specified by pname:handleType
* pname:handle must: obey any requirements listed for pname:handleType in
<<external-memory-handle-types-compatibility,external memory handle
types compatibility>>
****

include::{generated}/validity/structs/VkImportMemoryMetalHandleInfoEXT.adoc[]
--

[open,refpage='vkGetMemoryMetalHandleEXT',desc='Get a Metal handle for a memory object',type='protos']
--
To export a Metal handle representing the payload of a Vulkan device
memory object, call:

include::{generated}/api/protos/vkGetMemoryMetalHandleEXT.adoc[]

* pname:device is the logical device that created the device memory being
exported.
* pname:pGetMetalHandleInfo is a pointer to a
slink:VkMemoryGetMetalHandleInfoEXT structure containing parameters of
the export operation.
* pname:pHandle will return the Metal handle representing the payload of
the device memory object.

Unless the app retains the handle object returned by the call, the lifespan will be the same as
the associated `VkDeviceMemory`.

include::{generated}/validity/protos/vkGetMemoryMetalHandleEXT.adoc[]
--

[open,refpage='VkMemoryGetMetalHandleInfoEXT',desc='Structure describing a Metal handle memory export operation',type='structs']
--
The sname:VkMemoryGetMetalHandleInfoEXT structure is defined as:

include::{generated}/api/structs/VkMemoryGetMetalHandleInfoEXT.adoc[]

* pname:sType is a elink:VkStructureType value identifying this structure.
* pname:pNext is `NULL` or a pointer to a structure extending this
structure.
* pname:memory is the memory object from which the handle will be
exported.
* pname:handleType is a elink:VkExternalMemoryHandleTypeFlagBits value
specifying the type of handle requested.

The properties of the handle returned depend on the value of
pname:handleType.
See elink:VkExternalMemoryHandleTypeFlagBits for a description of the
properties of the defined external memory handle types.

.Valid Usage
****
* pname:memory must: have been created with a valid
slink:VkExportMemoryAllocateInfo
* pname:handleType must: have been included in
slink:VkExportMemoryAllocateInfo::pname:handleTypes when pname:memory
was created
* pname:handleType must: be
ename:VK_EXTERNAL_MEMORY_HANDLE_TYPE_MTLBUFFER_BIT_EXT,
ename:VK_EXTERNAL_MEMORY_HANDLE_TYPE_MTLTEXTURE_BIT_EXT or
ename:VK_EXTERNAL_MEMORY_HANDLE_TYPE_MTLHEAP_BIT_EXT
****

include::{generated}/validity/structs/VkMemoryGetMetalHandleInfoEXT.adoc[]
--

[open,refpage='vkGetMemoryMetalHandlePropertiesEXT',desc='Get Properties of External Memory Metal Handles',type='protos']
--
Metal memory handles compatible with Vulkan may: also be created by
non-Vulkan APIs using methods beyond the scope of this specification.
To determine the correct parameters to use when importing such handles,
call:

include::{generated}/api/protos/vkGetMemoryMetalHandlePropertiesEXT.adoc[]

* pname:device is the logical device that will be importing pname:handle.
* pname:handleType is a elink:VkExternalMemoryHandleTypeFlagBits value
specifying the type of the handle pname:handle.
* pname:handle is the handle which will be imported.
* pname:pMemoryMetalHandleProperties is a pointer to a
slink:VkMemoryMetalHandlePropertiesEXT structure in which properties of
pname:handle are returned.

.Valid Usage
****
* pname:handle must: point to a valid id<MTLBuffer>, id<MTLTexture> or
id<MTLDevice>
* pname:handleType must: be
ename:VK_EXTERNAL_MEMORY_HANDLE_TYPE_MTLBUFFER_BIT_EXT,
ename:VK_EXTERNAL_MEMORY_HANDLE_TYPE_MTLTEXTURE_BIT_EXT or
ename:VK_EXTERNAL_MEMORY_HANDLE_TYPE_MTLHEAP_BIT_EXT
****

include::{generated}/validity/protos/vkGetMemoryMetalHandlePropertiesEXT.adoc[]
--

[open,refpage='VkMemoryMetalHandlePropertiesEXT',desc='Properties of External Memory Metal Handles',type='structs']
--
The sname:VkMemoryMetalHandlePropertiesEXT structure returned is defined as:

include::{generated}/api/structs/VkMemoryMetalHandlePropertiesEXT.adoc[]

* pname:sType is a elink:VkStructureType value identifying this structure.
* pname:pNext is `NULL` or a pointer to a structure extending this
structure.
* pname:memoryTypeBits is a bitmask containing one bit set for every
memory type which the specified Metal handle can: be imported as.

include::{generated}/validity/structs/VkMemoryMetalHandlePropertiesEXT.adoc[]
--
16 changes: 16 additions & 0 deletions chapters/capabilities.adoc
Original file line number Diff line number Diff line change
Expand Up @@ -528,6 +528,14 @@ ifdef::VK_QNX_external_memory_screen_buffer[]
See <<memory-external-qnx-screen-buffer,QNX Screen Buffer>> for more
details of this handle type.
endif::VK_QNX_external_memory_screen_buffer[]
ifdef::VK_EXT_external_memory_metal[]
* ename:VK_EXTERNAL_MEMORY_HANDLE_TYPE_MTLBUFFER_BIT_EXT is a handle to
a `MTLResource` holding a `MTLBuffer`.
* ename:VK_EXTERNAL_MEMORY_HANDLE_TYPE_MTLTEXTURE_BIT_EXT is a handle to
a `MTLResource` holding a `MTLTexture`.
* ename:VK_EXTERNAL_MEMORY_HANDLE_TYPE_MTLHEAP_BIT_EXT is a handle to
a `MTLResource` holding a `MTLHeap`.
endif::VK_EXT_external_memory_metal[]

<<<

Expand Down Expand Up @@ -568,6 +576,11 @@ endif::VK_NV_external_memory_sci_buf[]
ifdef::VK_QNX_external_memory_screen_buffer[]
| ename:VK_EXTERNAL_MEMORY_HANDLE_TYPE_SCREEN_BUFFER_BIT_QNX | No restriction | No restriction
endif::VK_QNX_external_memory_screen_buffer[]
ifdef::VK_EXT_external_memory_metal[]
| ename:VK_EXTERNAL_MEMORY_HANDLE_TYPE_MTLBUFFER_BIT_EXT | No restriction | Must match
| ename:VK_EXTERNAL_MEMORY_HANDLE_TYPE_MTLTEXTURE_BIT_EXT | No restriction | Must match
| ename:VK_EXTERNAL_MEMORY_HANDLE_TYPE_MTLHEAP_BIT_EXT | No restriction | Must match
endif::VK_EXT_external_memory_metal[]
|====

ifdef::VK_EXT_external_memory_host[]
Expand Down Expand Up @@ -707,6 +720,9 @@ ifdef::VK_QNX_external_memory_screen_buffer[]
* ename:VK_EXTERNAL_MEMORY_HANDLE_TYPE_SCREEN_BUFFER_BIT_QNX for images
only
endif::VK_QNX_external_memory_screen_buffer[]
ifdef::VK_EXT_external_memory_metal[]
* ename:VK_EXTERNAL_MEMORY_HANDLE_TYPE_MTLTEXTURE_BIT_EXT
endif::VK_EXT_external_memory_metal[]

ifdef::VK_ANDROID_external_memory_android_hardware_buffer[]
Implementations must: not report
Expand Down
43 changes: 37 additions & 6 deletions chapters/memory.adoc
Original file line number Diff line number Diff line change
Expand Up @@ -1209,7 +1209,7 @@ include::{generated}/api/structs/VkMemoryAllocateInfo.adoc[]
The internal data of an allocated device memory object must: include a
reference to implementation-specific resources, referred to as the memory
object's _payload_.
ifdef::VK_KHR_external_memory_win32,VK_KHR_external_memory_fd,VK_EXT_external_memory_host,VK_ANDROID_external_memory_android_hardware_buffer,VK_FUCHSIA_external_memory,VK_NV_external_memory_sci_buf,VK_QNX_external_memory_screen_buffer[]
ifdef::VK_KHR_external_memory_win32,VK_KHR_external_memory_fd,VK_EXT_external_memory_host,VK_ANDROID_external_memory_android_hardware_buffer,VK_FUCHSIA_external_memory,VK_NV_external_memory_sci_buf,VK_QNX_external_memory_screen_buffer,VK_EXT_external_memory_metal[]
Applications can: also import and export that internal data to and from
device memory objects to share data between Vulkan instances and other
compatible APIs.
Expand Down Expand Up @@ -1245,6 +1245,10 @@ endif::VK_NV_external_memory_sci_buf[]
ifdef::VK_QNX_external_memory_screen_buffer[]
* slink:VkImportScreenBufferInfoQNX with a non-`NULL` pname:buffer value
endif::VK_QNX_external_memory_screen_buffer[]
ifdef::VK_EXT_external_memory_metal[]
* slink:VkImportMemoryMetalHandleInfoEXT with a non-zero pname:handleType
value
endif::VK_EXT_external_memory_metal[]

ifdef::VK_KHR_external_memory_win32[]
If the parameters define an import operation and the external handle type is
Expand All @@ -1263,6 +1267,13 @@ The implementation must: query the size of this allocation from the
stext:NvSciBufAttrList associated with the external stext:NvSciBufObj.
endif::VK_NV_external_memory_sci_buf[]

ifdef::VK_EXT_external_memory_metal[]
If the parameters define an import operation and the external handle type is
ename:VK_EXTERNAL_MEMORY_HANDLE_TYPE_MTLTEXTURE_BIT_EXT,
pname:allocationSize is ignored.
The implementation must: query the size of these allocations from the OS.
endif::VK_EXT_external_memory_metal[]

Whether device memory objects constructed via a memory import operation hold
a reference to their payload depends on the properties of the handle type
used to perform the import, as defined below for each valid handle type.
Expand Down Expand Up @@ -1315,17 +1326,17 @@ This is because for an export operation, there is currently no way for the
application to know the memory type index before allocating.
endif::VK_ANDROID_external_memory_android_hardware_buffer[]

endif::VK_KHR_external_memory_win32,VK_KHR_external_memory_fd,VK_EXT_external_memory_host,VK_ANDROID_external_memory_android_hardware_buffer,VK_FUCHSIA_external_memory,VK_NV_external_memory_sci_buf,VK_QNX_external_memory_screen_buffer[]
endif::VK_KHR_external_memory_win32,VK_KHR_external_memory_fd,VK_EXT_external_memory_host,VK_ANDROID_external_memory_android_hardware_buffer,VK_FUCHSIA_external_memory,VK_NV_external_memory_sci_buf,VK_QNX_external_memory_screen_buffer,VK_EXT_external_memory_metal[]

.Valid Usage
****
* [[VUID-VkMemoryAllocateInfo-allocationSize-07897]]
ifdef::VK_KHR_external_memory_win32,VK_KHR_external_memory_fd,VK_EXT_external_memory_host,VK_ANDROID_external_memory_android_hardware_buffer,VK_FUCHSIA_external_memory,VK_NV_external_memory_sci_buf,VK_QNX_external_memory_screen_buffer[]
ifdef::VK_KHR_external_memory_win32,VK_KHR_external_memory_fd,VK_EXT_external_memory_host,VK_ANDROID_external_memory_android_hardware_buffer,VK_FUCHSIA_external_memory,VK_NV_external_memory_sci_buf,VK_QNX_external_memory_screen_buffer,VK_EXT_external_memory_metal[]
If the parameters do not define an <<memory-import-operation,import or
export operation>>,
endif::VK_KHR_external_memory_win32,VK_KHR_external_memory_fd,VK_EXT_external_memory_host,VK_ANDROID_external_memory_android_hardware_buffer,VK_FUCHSIA_external_memory,VK_NV_external_memory_sci_buf,VK_QNX_external_memory_screen_buffer[]
endif::VK_KHR_external_memory_win32,VK_KHR_external_memory_fd,VK_EXT_external_memory_host,VK_ANDROID_external_memory_android_hardware_buffer,VK_FUCHSIA_external_memory,VK_NV_external_memory_sci_buf,VK_QNX_external_memory_screen_buffer,VK_EXT_external_memory_metal[]
pname:allocationSize must: be greater than `0`
ifdef::VK_KHR_external_memory_win32,VK_KHR_external_memory_fd,VK_EXT_external_memory_host,VK_ANDROID_external_memory_android_hardware_buffer,VK_FUCHSIA_external_memory,VK_NV_external_memory_sci_buf,VK_QNX_external_memory_screen_buffer[]
ifdef::VK_KHR_external_memory_win32,VK_KHR_external_memory_fd,VK_EXT_external_memory_host,VK_ANDROID_external_memory_android_hardware_buffer,VK_FUCHSIA_external_memory,VK_NV_external_memory_sci_buf,VK_QNX_external_memory_screen_buffer,VK_EXT_external_memory_metal[]
* [[VUID-VkMemoryAllocateInfo-None-06657]]
The parameters must: not define more than one
<<memory-import-operation,import operation>>
Expand All @@ -1336,7 +1347,7 @@ ifdef::VK_ANDROID_external_memory_android_hardware_buffer[]
ename:VK_EXTERNAL_MEMORY_HANDLE_TYPE_ANDROID_HARDWARE_BUFFER_BIT_ANDROID
endif::VK_ANDROID_external_memory_android_hardware_buffer[]
, pname:allocationSize must: be greater than `0`
endif::VK_KHR_external_memory_win32,VK_KHR_external_memory_fd,VK_EXT_external_memory_host,VK_ANDROID_external_memory_android_hardware_buffer,VK_FUCHSIA_external_memory,VK_NV_external_memory_sci_buf,VK_QNX_external_memory_screen_buffer[]
endif::VK_KHR_external_memory_win32,VK_KHR_external_memory_fd,VK_EXT_external_memory_host,VK_ANDROID_external_memory_android_hardware_buffer,VK_FUCHSIA_external_memory,VK_NV_external_memory_sci_buf,VK_QNX_external_memory_screen_buffer,VK_EXT_external_memory_metal[]
ifdef::VK_FUCHSIA_buffer_collection[]
* [[VUID-VkMemoryAllocateInfo-buffer-06380]]
If the parameters define an import operation from an
Expand Down Expand Up @@ -1643,6 +1654,22 @@ ifdef::VK_QNX_external_memory_screen_buffer[]
of pname:image and the QNX Screen buffer's code:_screen_buffer must: be
identical
endif::VK_QNX_external_memory_screen_buffer[]
ifdef::VK_EXT_external_memory_metal[]
* If the parameters define an import operation and the external handle is
a ename:VK_EXTERNAL_MEMORY_HANDLE_TYPE_MTLTEXTURE_BIT_EXT, then
pname:pNext must: include a slink:VkMemoryDedicatedAllocateInfo with
pname:image that is not dlink:VK_NULL_HANDLE
* If the parameters define an import operation, the external handle is a
Metal MTLTexture, and the pname:pNext chain includes a
slink:VkMemoryDedicatedAllocateInfo structure with pname:image that is
not dlink:VK_NULL_HANDLE, the width, height, array layer dimensions,
and mipmap levels of pname:image and the Metal MTLTexture's must: be
identical
* If the parameters define an import operation, the external handle is a
Metal MTLTexture, and the pname:pNext chain includes a
slink:VkMemoryDedicatedAllocateInfo structure with pname:image that is
not dlink:VK_NULL_HANDLE, pname:allocationSize must: be `0`
endif::VK_EXT_external_memory_metal[]
ifdef::VK_VERSION_1_2,VK_KHR_buffer_device_address[]
* [[VUID-VkMemoryAllocateInfo-opaqueCaptureAddress-03329]]
If
Expand Down Expand Up @@ -3249,6 +3276,10 @@ ifdef::VK_QNX_external_memory_screen_buffer[]
include::{chapters}/VK_QNX_external_memory_screen_buffer/device_memory.adoc[]
endif::VK_QNX_external_memory_screen_buffer[]

ifdef::VK_EXT_external_memory_metal[]
include::{chapters}/VK_EXT_external_memory_metal/device_memory.adoc[]
endif::VK_EXT_external_memory_metal[]


ifdef::VK_VERSION_1_1,VK_KHR_device_group[]
=== Device Group Memory Allocations
Expand Down
17 changes: 12 additions & 5 deletions chapters/resources.adoc
Original file line number Diff line number Diff line change
Expand Up @@ -8589,13 +8589,20 @@ flink:vkGetBufferMemoryRequirements or flink:vkGetBufferMemoryRequirements2
with slink:VkBuffer before it has been bound to memory.
endif::VK_ANDROID_external_memory_android_hardware_buffer[]

ifdef::VK_KHR_external_memory_win32,VK_EXT_external_memory_metal[]
The value of pname:size has no meaning and should: be ignored
if the resource being queried was created with any of the following
external memory handle types:

ifdef::VK_KHR_external_memory_win32[]
If the resource being queried was created with the
ename:VK_EXTERNAL_MEMORY_HANDLE_TYPE_D3D11_TEXTURE_BIT,
ename:VK_EXTERNAL_MEMORY_HANDLE_TYPE_D3D11_TEXTURE_KMT_BIT, or
ename:VK_EXTERNAL_MEMORY_HANDLE_TYPE_D3D12_RESOURCE_BIT external memory
handle type, the value of pname:size has no meaning and should: be ignored.
* ename:VK_EXTERNAL_MEMORY_HANDLE_TYPE_D3D11_TEXTURE_BIT
* ename:VK_EXTERNAL_MEMORY_HANDLE_TYPE_D3D11_TEXTURE_KMT_BIT
* ename:VK_EXTERNAL_MEMORY_HANDLE_TYPE_D3D12_RESOURCE_BIT
endif::VK_KHR_external_memory_win32[]
ifdef::VK_EXT_external_memory_metal[]
* ename:VK_EXTERNAL_MEMORY_HANDLE_TYPE_MTLTEXTURE_BIT_EXT
endif::VK_EXT_external_memory_metal[]
endif::VK_KHR_external_memory_win32,VK_EXT_external_memory_metal[]

The implementation guarantees certain properties about the memory
requirements returned by
Expand Down
Loading

0 comments on commit 25ec2b7

Please sign in to comment.