## 5.1. Command Pools

Command pools are opaque objects that command buffer memory is allocated from, and which allow the implementation to amortize the cost of resource creation across multiple command buffers. Command pools are application-synchronized, meaning that a command pool must not be used concurrently in multiple threads. That includes use via recording commands on any command buffers allocated from the pool, as well as operations that allocate, free, and reset command buffers or the pool itself.

Command pools are represented by `VkCommandPool` handles:

    VK_DEFINE_NON_DISPATCHABLE_HANDLE(VkCommandPool)

To create a command pool, call:

    VkResult vkCreateCommandPool(
        VkDevice                                    device,
        const VkCommandPoolCreateInfo*              pCreateInfo,
        const VkAllocationCallbacks*                pAllocator,
        VkCommandPool*                              pCommandPool);

- `device` is the logical device that creates the command pool.
- `pCreateInfo` contains information used to create the command pool.
- `pAllocator` controls host memory allocation as described in the Memory Allocation chapter.
- `pCommandPool` points to a `VkCommandPool` handle in which the created pool is returned.

The `VkCommandPoolCreateInfo` structure is defined as:

    typedef struct VkCommandPoolCreateInfo {
        VkStructureType             sType;
        const void*                 pNext;
        VkCommandPoolCreateFlags    flags;
        uint32_t                    queueFamilyIndex;
    } VkCommandPoolCreateInfo;

- `sType` is the type of this structure.
- `pNext` is `NULL` or a pointer to an extension-specific structure.

- `flags` is a bitmask indicating usage behavior for the pool and command buffers allocated from it. Bits which can be set include:

      typedef enum VkCommandPoolCreateFlagBits {
          VK_COMMAND_POOL_CREATE_TRANSIENT_BIT = 0x00000001,
          VK_COMMAND_POOL_CREATE_RESET_COMMAND_BUFFER_BIT = 0x00000002,
      } VkCommandPoolCreateFlagBits;

  - `VK_COMMAND_POOL_CREATE_TRANSIENT_BIT` indicates that command buffers allocated from the pool will be short-lived, meaning that they will be reset or freed in a relatively short timeframe. This flag may be used by the implementation to control memory allocation behavior within the pool.
  - `VK_COMMAND_POOL_CREATE_RESET_COMMAND_BUFFER_BIT` controls whether command buffers allocated from the pool can be individually reset. If this flag is set, individual command buffers allocated from the pool can be reset either explicitly, by calling `vkResetCommandBuffer`, or implicitly, by calling `vkBeginCommandBuffer` on an executable command buffer. If this flag is not set, then `vkResetCommandBuffer` and `vkBeginCommandBuffer` (on an executable command buffer) must not be called on the command buffers allocated from the pool, and they can only be reset in bulk by calling `vkResetCommandPool`.
- `queueFamilyIndex` designates a queue family as described in section Queue Family Properties. All command buffers allocated from this command pool must be submitted on queues from the same queue family.

To reset a command pool, call:

    VkResult vkResetCommandPool(
        VkDevice                                    device,
        VkCommandPool                               commandPool,
        VkCommandPoolResetFlags                     flags);

- `device` is the logical device that owns the command pool.
- `commandPool` is the command pool to reset.

- `flags` contains additional flags controlling the behavior of the reset. Bits which can be set include:

      typedef enum VkCommandPoolResetFlagBits {
          VK_COMMAND_POOL_RESET_RELEASE_RESOURCES_BIT = 0x00000001,
      } VkCommandPoolResetFlagBits;

  If `flags` includes `VK_COMMAND_POOL_RESET_RELEASE_RESOURCES_BIT`, resetting a command pool recycles all of the resources from the command pool back to the system.

Resetting a command pool recycles all of the resources from all of the command buffers allocated from the command pool back to the command pool. All command buffers that have been allocated from the command pool are put in the initial state.

To destroy a command pool, call:

    void vkDestroyCommandPool(
        VkDevice                                    device,
        VkCommandPool                               commandPool,
        const VkAllocationCallbacks*                pAllocator);

- `device` is the logical device that destroys the command pool.
- `commandPool` is the handle of the command pool to destroy.
- `pAllocator` controls host memory allocation as described in the Memory Allocation chapter.

When a pool is destroyed, all command buffers allocated from the pool are implicitly freed and become invalid. Command buffers allocated from a given pool do not need to be freed before destroying that command pool.