private unsafe void CreateAssets()
        {
            ID3D12Device *d3dDevice = _deviceResources.D3DDevice;

            Guid iid;

            {
                iid = D3D12.IID_ID3D12GraphicsCommandList;
                ID3D12GraphicsCommandList *commandList;
                ThrowIfFailed(d3dDevice->CreateCommandList(
                                  0,
                                  D3D12_COMMAND_LIST_TYPE.D3D12_COMMAND_LIST_TYPE_DIRECT,
                                  _deviceResources.CommandAllocator,
                                  _pipelineState.Ptr,
                                  &iid,
                                  (void **)&commandList));

                _commandList = commandList;
                DX.NameD3D12Object(_commandList.Ptr, nameof(_commandList));
            }

            // Cube vertices. Each vertex has a position and a color.
            const uint           vertexPositionColorCount = 8;
            VertexPositionColor *cubeVertices             = stackalloc VertexPositionColor[(int)vertexPositionColorCount]
            {
                new VertexPositionColor {
                    pos = new Vector3(-0.5f, -0.5f, -0.5f), color = new Vector3(0.0f, 0.0f, 0.0f)
                },
                new VertexPositionColor {
                    pos = new Vector3(-0.5f, -0.5f, 0.5f), color = new Vector3(0.0f, 0.0f, 1.0f)
                },
                new VertexPositionColor {
                    pos = new Vector3(-0.5f, 0.5f, -0.5f), color = new Vector3(0.0f, 1.0f, 0.0f)
                },
                new VertexPositionColor {
                    pos = new Vector3(-0.5f, 0.5f, 0.5f), color = new Vector3(0.0f, 1.0f, 1.0f)
                },
                new VertexPositionColor {
                    pos = new Vector3(0.5f, -0.5f, -0.5f), color = new Vector3(1.0f, 0.0f, 0.0f)
                },
                new VertexPositionColor {
                    pos = new Vector3(0.5f, -0.5f, 0.5f), color = new Vector3(1.0f, 0.0f, 1.0f)
                },
                new VertexPositionColor {
                    pos = new Vector3(0.5f, 0.5f, -0.5f), color = new Vector3(1.0f, 1.0f, 0.0f)
                },
                new VertexPositionColor {
                    pos = new Vector3(0.5f, 0.5f, 0.5f), color = new Vector3(1.0f, 1.0f, 1.0f)
                }
            };

            Debug.Assert(sizeof(VertexPositionColor) == Marshal.SizeOf <VertexPositionColor>());
            uint vertexBufferSize = (uint)sizeof(VertexPositionColor) * vertexPositionColorCount;

            using ComPtr <ID3D12Resource> vertexBufferUpload = default;

            D3D12_HEAP_PROPERTIES defaultHeapProperties =
                CD3DX12_HEAP_PROPERTIES.Create(D3D12_HEAP_TYPE.D3D12_HEAP_TYPE_DEFAULT);

            D3D12_RESOURCE_DESC vertexBufferDesc = CD3DX12_RESOURCE_DESC.Buffer(vertexBufferSize);

            {
                iid = D3D12.IID_ID3D12Resource;
                ID3D12Resource *vertexBuffer;
                ThrowIfFailed(d3dDevice->CreateCommittedResource(
                                  &defaultHeapProperties,
                                  D3D12_HEAP_FLAGS.D3D12_HEAP_FLAG_NONE,
                                  &vertexBufferDesc,
                                  D3D12_RESOURCE_STATES.D3D12_RESOURCE_STATE_COPY_DEST,
                                  null,
                                  &iid,
                                  (void **)&vertexBuffer));

                _vertexBuffer = vertexBuffer;
            }

            iid = D3D12.IID_ID3D12Resource;
            D3D12_HEAP_PROPERTIES uploadHeapProperties =
                CD3DX12_HEAP_PROPERTIES.Create(D3D12_HEAP_TYPE.D3D12_HEAP_TYPE_UPLOAD);

            ThrowIfFailed(d3dDevice->CreateCommittedResource(
                              &uploadHeapProperties,
                              D3D12_HEAP_FLAGS.D3D12_HEAP_FLAG_NONE,
                              &vertexBufferDesc,
                              D3D12_RESOURCE_STATES.D3D12_RESOURCE_STATE_GENERIC_READ,
                              null,
                              &iid,
                              (void **)vertexBufferUpload.GetAddressOf()));

            DX.NameD3D12Object(_vertexBuffer.Ptr, nameof(_vertexBuffer));

            {
                D3D12_SUBRESOURCE_DATA vertexData;
                vertexData.pData      = (byte *)cubeVertices;
                vertexData.RowPitch   = (IntPtr)vertexBufferSize;
                vertexData.SlicePitch = vertexData.RowPitch;

                Functions.UpdateSubresources(
                    _commandList.Ptr,
                    _vertexBuffer.Ptr,
                    vertexBufferUpload.Ptr,
                    0, 0, 1,
                    &vertexData);

                D3D12_RESOURCE_BARRIER vertexBufferResourceBarrier =
                    CD3DX12_RESOURCE_BARRIER.Transition(_vertexBuffer.Ptr,
                                                        D3D12_RESOURCE_STATES.D3D12_RESOURCE_STATE_COPY_DEST,
                                                        D3D12_RESOURCE_STATES.D3D12_RESOURCE_STATE_VERTEX_AND_CONSTANT_BUFFER);

                _commandList.Ptr->ResourceBarrier(1, &vertexBufferResourceBarrier);
            }

            const int cubeIndicesCount = 36;
            ushort *  cubeIndices      = stackalloc ushort[cubeIndicesCount]
            {
                0,
                2,
                1, // -x
                1,
                2,
                3,

                4,
                5,
                6, // +x
                5,
                7,
                6,

                0,
                1,
                5, // -y
                0,
                5,
                4,

                2,
                6,
                7, // +y
                2,
                7,
                3,

                0,
                4,
                6, // -z
                0,
                6,
                2,

                1,
                3,
                7, // +z
                1,
                7,
                5,
            };
            const uint indexBufferSize = sizeof(ushort) * cubeIndicesCount;

            using var indexBufferUpload = new ComPtr <ID3D12Resource>();

            D3D12_RESOURCE_DESC indexBufferDesc = CD3DX12_RESOURCE_DESC.Buffer(indexBufferSize);

            {
                iid = D3D12.IID_ID3D12Resource;
                ID3D12Resource *indexBuffer;
                ThrowIfFailed(d3dDevice->CreateCommittedResource(
                                  &defaultHeapProperties,
                                  D3D12_HEAP_FLAGS.D3D12_HEAP_FLAG_NONE,
                                  &indexBufferDesc,
                                  D3D12_RESOURCE_STATES.D3D12_RESOURCE_STATE_COPY_DEST,
                                  null,
                                  &iid,
                                  (void **)&indexBuffer));
                _indexBuffer = indexBuffer;
            }

            iid = D3D12.IID_ID3D12Resource;
            ThrowIfFailed(d3dDevice->CreateCommittedResource(
                              &uploadHeapProperties,
                              D3D12_HEAP_FLAGS.D3D12_HEAP_FLAG_NONE,
                              &indexBufferDesc,
                              D3D12_RESOURCE_STATES.D3D12_RESOURCE_STATE_GENERIC_READ,
                              null,
                              &iid,
                              (void **)indexBufferUpload.GetAddressOf()));

            DX.NameD3D12Object(_indexBuffer.Ptr, nameof(_indexBuffer));

            {
                D3D12_SUBRESOURCE_DATA indexData;
                indexData.pData      = (byte *)cubeIndices;
                indexData.RowPitch   = (IntPtr)indexBufferSize;
                indexData.SlicePitch = indexData.RowPitch;

                Functions.UpdateSubresources(
                    _commandList.Ptr,
                    _indexBuffer.Ptr,
                    indexBufferUpload.Ptr,
                    0, 0, 1,
                    &indexData);

                D3D12_RESOURCE_BARRIER indexBufferResourceBarrier =
                    CD3DX12_RESOURCE_BARRIER.Transition(_indexBuffer.Ptr,
                                                        D3D12_RESOURCE_STATES.D3D12_RESOURCE_STATE_COPY_DEST,
                                                        D3D12_RESOURCE_STATES.D3D12_RESOURCE_STATE_INDEX_BUFFER);

                _commandList.Ptr->ResourceBarrier(1, &indexBufferResourceBarrier);
            }

            {
                D3D12_DESCRIPTOR_HEAP_DESC heapDesc;
                heapDesc.NumDescriptors = DeviceResources.FrameCount;
                heapDesc.Type           = D3D12_DESCRIPTOR_HEAP_TYPE.D3D12_DESCRIPTOR_HEAP_TYPE_CBV_SRV_UAV;
                heapDesc.Flags          = D3D12_DESCRIPTOR_HEAP_FLAGS.D3D12_DESCRIPTOR_HEAP_FLAG_SHADER_VISIBLE;

                {
                    ID3D12DescriptorHeap *cbvHeap;
                    iid = D3D12.IID_ID3D12DescriptorHeap;
                    ThrowIfFailed(d3dDevice->CreateDescriptorHeap(&heapDesc, &iid, (void **)&cbvHeap));
                    _cbvHeap = cbvHeap;
                    DX.NameD3D12Object(_cbvHeap.Ptr, nameof(_cbvHeap));
                }
            }

            D3D12_RESOURCE_DESC constantBufferDesc = CD3DX12_RESOURCE_DESC.Buffer(
                DeviceResources.FrameCount * AlignedConstantBufferSize);

            {
                iid = D3D12.IID_ID3D12Resource;
                ID3D12Resource *constantBuffer;
                ThrowIfFailed(d3dDevice->CreateCommittedResource(
                                  &uploadHeapProperties,
                                  D3D12_HEAP_FLAGS.D3D12_HEAP_FLAG_NONE,
                                  &constantBufferDesc,
                                  D3D12_RESOURCE_STATES.D3D12_RESOURCE_STATE_GENERIC_READ,
                                  null,
                                  &iid,
                                  (void **)&constantBuffer));
                _constantBuffer = constantBuffer;

                DX.NameD3D12Object(_constantBuffer.Ptr, nameof(_constantBuffer));
            }

            D3D12_GPU_VIRTUAL_ADDRESS   cbvGpuAddress = _constantBuffer.Ptr->GetGPUVirtualAddress();
            D3D12_CPU_DESCRIPTOR_HANDLE cbvCpuHandle  = _cbvHeap.Ptr->GetCPUDescriptorHandleForHeapStart();

            _cbvDescriptorSize =
                d3dDevice->GetDescriptorHandleIncrementSize(
                    D3D12_DESCRIPTOR_HEAP_TYPE.D3D12_DESCRIPTOR_HEAP_TYPE_CBV_SRV_UAV);

            for (var i = 0; i < DeviceResources.FrameCount; i++)
            {
                D3D12_CONSTANT_BUFFER_VIEW_DESC desc;
                desc.BufferLocation = cbvGpuAddress;
                desc.SizeInBytes    = AlignedConstantBufferSize;
                d3dDevice->CreateConstantBufferView(&desc, cbvCpuHandle);
                cbvGpuAddress += desc.SizeInBytes;
                cbvCpuHandle.Offset((int)_cbvDescriptorSize);
            }

            D3D12_RANGE readRange = CD3DX12_RANGE.Create((UIntPtr)0, (UIntPtr)0);

            fixed(byte **p = &_mappedConstantBuffer)
            {
                ThrowIfFailed(_constantBuffer.Ptr->Map(0, &readRange, (void **)p));
                Unsafe.InitBlockUnaligned(_mappedConstantBuffer, 0, DeviceResources.FrameCount * AlignedConstantBufferSize);
            }

            ThrowIfFailed(_commandList.Ptr->Close());
            const int           ppCommandListCount = 1;
            ID3D12CommandList **ppCommandLists     = stackalloc ID3D12CommandList *[ppCommandListCount]
            {
                (ID3D12CommandList *)_commandList.Ptr
            };

            _deviceResources.CommandQueue->ExecuteCommandLists(ppCommandListCount, ppCommandLists);

            _vertexBufferView.BufferLocation = _vertexBuffer.Ptr->GetGPUVirtualAddress();
            _vertexBufferView.StrideInBytes  = (uint)sizeof(VertexPositionColor);
            _vertexBufferView.SizeInBytes    = vertexBufferSize;

            _indexBufferView.BufferLocation = _indexBuffer.Ptr->GetGPUVirtualAddress();
            _indexBufferView.SizeInBytes    = indexBufferSize;
            _indexBufferView.Format         = DXGI_FORMAT.DXGI_FORMAT_R16_UINT;

            _deviceResources.WaitForGpu();
        }

        #endregion
    }
}