diff --git a/data/shaders/glsl/oit/geometry.frag b/data/shaders/glsl/oit/geometry.frag
index 7aef80ba5d9b037af87c851f35c6dd66df8922ab..17c143fc22b255762535c6bde136c81f146e76c9 100644
--- a/data/shaders/glsl/oit/geometry.frag
+++ b/data/shaders/glsl/oit/geometry.frag
@@ -15,7 +15,7 @@ layout (set = 0, binding = 1) buffer GeometrySBO
     uint maxNodeCount;
 };
 
-layout (set = 0, binding = 2, r32ui) uniform uimage2D headIndexImage;
+layout (set = 0, binding = 2, r32ui) uniform coherent uimage2D headIndexImage;
 
 layout (set = 0, binding = 3) buffer LinkedListSBO
 {
diff --git a/data/shaders/glsl/oit/geometry.frag.spv b/data/shaders/glsl/oit/geometry.frag.spv
index f7563e991303a37f219b7c4afb295357b9fc1ba4..7e861318bc539afe8c57e4ee090dd8f314ed9baa 100644
Binary files a/data/shaders/glsl/oit/geometry.frag.spv and b/data/shaders/glsl/oit/geometry.frag.spv differ
diff --git a/examples/oit/oit.cpp b/examples/oit/oit.cpp
index 4458c3d490091405d9777ce87950bf775dc61374..2da04e10776d54417f15f5f77c28e050eb6b197e 100644
--- a/examples/oit/oit.cpp
+++ b/examples/oit/oit.cpp
@@ -192,20 +192,35 @@ private:
 		VK_CHECK_RESULT(vkCreateFramebuffer(device, &fbufCreateInfo, nullptr, &geometryPass.framebuffer));
 
 		// Create a buffer for GeometrySBO
-		// Using the device memory will be best but I will use the host visible buffer to make this example simple.
+		vks::Buffer stagingBuffer;
+	
 		VK_CHECK_RESULT(vulkanDevice->createBuffer(
-			VK_BUFFER_USAGE_STORAGE_BUFFER_BIT,
+			VK_BUFFER_USAGE_TRANSFER_SRC_BIT,
 			VK_MEMORY_PROPERTY_HOST_VISIBLE_BIT | VK_MEMORY_PROPERTY_HOST_COHERENT_BIT,
-			&geometryPass.geometry,
+			&stagingBuffer,
 			sizeof(geometrySBO)));
+		VK_CHECK_RESULT(stagingBuffer.map());
 
-		VK_CHECK_RESULT(geometryPass.geometry.map());
+		VK_CHECK_RESULT(vulkanDevice->createBuffer(
+			VK_BUFFER_USAGE_STORAGE_BUFFER_BIT | VK_BUFFER_USAGE_TRANSFER_DST_BIT,
+			VK_MEMORY_PROPERTY_DEVICE_LOCAL_BIT,
+			&geometryPass.geometry,
+			sizeof(geometrySBO)));
 
 		// Set up GeometrySBO data.
 		geometrySBO.count = 0;
 		geometrySBO.maxNodeCount = NODE_COUNT * width * height;
-		memcpy(geometryPass.geometry.mapped, &geometrySBO, sizeof(geometrySBO));
+		memcpy(stagingBuffer.mapped, &geometrySBO, sizeof(geometrySBO));
+
+		// Copy data to device
+		VkCommandBuffer copyCmd = vulkanDevice->createCommandBuffer(VK_COMMAND_BUFFER_LEVEL_PRIMARY, true);
+		VkBufferCopy copyRegion = {};
+		copyRegion.size = sizeof(geometrySBO);
+		vkCmdCopyBuffer(copyCmd, stagingBuffer.buffer, geometryPass.geometry.buffer, 1, &copyRegion);
+		vulkanDevice->flushCommandBuffer(copyCmd, queue, true);
 
+		stagingBuffer.destroy();
+		
 		// Create a texture for HeadIndex.
 		// This image will track the head index of each fragment.
 		geometryPass.headIndex.device = vulkanDevice;
@@ -260,12 +275,10 @@ private:
 		// Create a buffer for LinkedListSBO
 		VK_CHECK_RESULT(vulkanDevice->createBuffer(
 			VK_BUFFER_USAGE_STORAGE_BUFFER_BIT,
-			VK_MEMORY_PROPERTY_HOST_VISIBLE_BIT | VK_MEMORY_PROPERTY_HOST_COHERENT_BIT,
+			VK_MEMORY_PROPERTY_DEVICE_LOCAL_BIT,
 			&geometryPass.linkedList,
 			sizeof(Node) * geometrySBO.maxNodeCount));
 
-		VK_CHECK_RESULT(geometryPass.linkedList.map());
-
 		// Change HeadIndex image's layout from UNDEFINED to GENERAL
 		VkCommandBufferAllocateInfo cmdBufAllocInfo = vks::initializers::commandBufferAllocateInfo(cmdPool, VK_COMMAND_BUFFER_LEVEL_PRIMARY, 1);
 
@@ -376,7 +389,7 @@ private:
 		pipelineCI.pViewportState = &viewportState;
 		pipelineCI.pDepthStencilState = &depthStencilState;
 		pipelineCI.pDynamicState = &dynamicState;
-		pipelineCI.stageCount = shaderStages.size();
+		pipelineCI.stageCount = static_cast<uint32_t>(shaderStages.size());
 		pipelineCI.pStages = shaderStages.data();
 		pipelineCI.pVertexInputState = vkglTF::Vertex::getPipelineVertexInputState({ vkglTF::VertexComponent::Position });
 
@@ -400,7 +413,7 @@ private:
 		pipelineCI.pViewportState = &viewportState;
 		pipelineCI.pDepthStencilState = &depthStencilState;
 		pipelineCI.pDynamicState = &dynamicState;
-		pipelineCI.stageCount = shaderStages.size();
+		pipelineCI.stageCount = static_cast<uint32_t>(shaderStages.size());
 		pipelineCI.pStages = shaderStages.data();
 		pipelineCI.pVertexInputState = &vertexInputInfo;
 
@@ -422,10 +435,7 @@ private:
 		};
 
 		VkDescriptorPoolCreateInfo descriptorPoolInfo =
-			vks::initializers::descriptorPoolCreateInfo(
-				poolSizes.size(),
-				poolSizes.data(),
-				2);
+			vks::initializers::descriptorPoolCreateInfo(poolSizes, 2);
 
 		VK_CHECK_RESULT(vkCreateDescriptorPool(device, &descriptorPoolInfo, nullptr, &descriptorPool));
 	}
@@ -468,7 +478,7 @@ private:
 				&geometryPass.linkedList.descriptor)
 		};
 
-		vkUpdateDescriptorSets(device, writeDescriptorSets.size(), writeDescriptorSets.data(), 0, NULL);
+		vkUpdateDescriptorSets(device, static_cast<uint32_t>(writeDescriptorSets.size()), writeDescriptorSets.data(), 0, NULL);
 
 		// Update a color descriptor set.
 		allocInfo =
@@ -494,7 +504,7 @@ private:
 				&geometryPass.linkedList.descriptor)
 		};
 
-		vkUpdateDescriptorSets(device, writeDescriptorSets.size(), writeDescriptorSets.data(), 0, NULL);
+		vkUpdateDescriptorSets(device, static_cast<uint32_t>(writeDescriptorSets.size()), writeDescriptorSets.data(), 0, NULL);
 	}
 
 	void buildCommandBuffers()
@@ -538,6 +548,15 @@ private:
 
 			vkCmdClearColorImage(drawCmdBuffers[i], geometryPass.headIndex.image, VK_IMAGE_LAYOUT_GENERAL, &clearColor, 1, &subresRange);
 
+			// Clear previous geometry pass data
+			vkCmdFillBuffer(drawCmdBuffers[i], geometryPass.geometry.buffer, 0, sizeof(uint32_t), 0);
+
+			// We need a barrier to make sure all writes are finished before starting to write again
+			VkMemoryBarrier memoryBarrier = vks::initializers::memoryBarrier();
+			memoryBarrier.srcAccessMask = VK_ACCESS_TRANSFER_WRITE_BIT;
+			memoryBarrier.dstAccessMask = VK_ACCESS_SHADER_READ_BIT | VK_ACCESS_SHADER_WRITE_BIT;
+			vkCmdPipelineBarrier(drawCmdBuffers[i], VK_PIPELINE_STAGE_TRANSFER_BIT, VK_PIPELINE_STAGE_FRAGMENT_SHADER_BIT, 0, 1, &memoryBarrier, 0, nullptr, 0, nullptr);
+
 			// Begin the geometry render pass
 			renderPassBeginInfo.renderPass = geometryPass.renderPass;
 			renderPassBeginInfo.framebuffer = geometryPass.framebuffer;
@@ -569,6 +588,7 @@ private:
 				}
 			}
 
+			models.cube.bindBuffers(drawCmdBuffers[i]);
 			objectData.color = glm::vec4(0.0f, 0.0f, 1.0f, 0.5f);
 			for (uint32_t x = 0; x < 2; x++)
 			{
@@ -611,17 +631,9 @@ private:
 	void draw()
 	{
 		VulkanExampleBase::prepareFrame();
-
-		// Clear previous geometry pass data
-		memset(geometryPass.geometry.mapped, 0, sizeof(uint32_t));
-
-		// Command buffer to be submitted to the queue
 		submitInfo.commandBufferCount = 1;
 		submitInfo.pCommandBuffers = &drawCmdBuffers[currentBuffer];
-
-		// Submit to queue
 		VK_CHECK_RESULT(vkQueueSubmit(queue, 1, &submitInfo, VK_NULL_HANDLE));
-
 		VulkanExampleBase::submitFrame();
 	}