diff --git a/src/Pipeline/BUILD.gn b/src/Pipeline/BUILD.gn
index 39283ed..eb03453 100644
--- a/src/Pipeline/BUILD.gn
+++ b/src/Pipeline/BUILD.gn
@@ -42,6 +42,7 @@
     "SpirvShader.cpp",
     "SpirvShaderControlFlow.cpp",
     "SpirvShaderGLSLstd450.cpp",
+    "SpirvShaderMemory.cpp",
     "SpirvShaderSampling.cpp",
     "VertexProgram.cpp",
     "VertexRoutine.cpp",
diff --git a/src/Pipeline/SpirvShader.cpp b/src/Pipeline/SpirvShader.cpp
index 115e57b..8f59ec4 100644
--- a/src/Pipeline/SpirvShader.cpp
+++ b/src/Pipeline/SpirvShader.cpp
@@ -936,59 +936,7 @@
 		}
 	}
 
-	bool SpirvShader::StoresInHelperInvocation(spv::StorageClass storageClass)
-	{
-		switch (storageClass)
-		{
-		case spv::StorageClassUniform:
-		case spv::StorageClassStorageBuffer:
-		case spv::StorageClassImage:
-			return false;
-		default:
-			return true;
-		}
-	}
-
-	bool SpirvShader::IsExplicitLayout(spv::StorageClass storageClass)
-	{
-		switch (storageClass)
-		{
-		case spv::StorageClassUniform:
-		case spv::StorageClassStorageBuffer:
-		case spv::StorageClassPushConstant:
-			return true;
-		default:
-			return false;
-		}
-	}
-
-	sw::SIMD::Pointer SpirvShader::InterleaveByLane(sw::SIMD::Pointer p)
-	{
-		p *= sw::SIMD::Width;
-		p.staticOffsets[0] += 0 * sizeof(float);
-		p.staticOffsets[1] += 1 * sizeof(float);
-		p.staticOffsets[2] += 2 * sizeof(float);
-		p.staticOffsets[3] += 3 * sizeof(float);
-		return p;
-	}
-
-	bool SpirvShader::IsStorageInterleavedByLane(spv::StorageClass storageClass)
-	{
-		switch (storageClass)
-		{
-		case spv::StorageClassUniform:
-		case spv::StorageClassStorageBuffer:
-		case spv::StorageClassPushConstant:
-		case spv::StorageClassWorkgroup:
-		case spv::StorageClassImage:
-			return false;
-		default:
-			return true;
-		}
-	}
-
-	template<typename F>
-	int SpirvShader::VisitInterfaceInner(Type::ID id, Decorations d, F f) const
+	int SpirvShader::VisitInterfaceInner(Type::ID id, Decorations d, const InterfaceVisitor &f) const
 	{
 		// Recursively walks variable definition and its type tree, taking into account
 		// any explicit Location or Component decorations encountered; where explicit
@@ -1008,19 +956,19 @@
 		switch(obj.opcode())
 		{
 		case spv::OpTypePointer:
-			return VisitInterfaceInner<F>(obj.definition.word(3), d, f);
+			return VisitInterfaceInner(obj.definition.word(3), d, f);
 		case spv::OpTypeMatrix:
 			for (auto i = 0u; i < obj.definition.word(3); i++, d.Location++)
 			{
 				// consumes same components of N consecutive locations
-				VisitInterfaceInner<F>(obj.definition.word(2), d, f);
+				VisitInterfaceInner(obj.definition.word(2), d, f);
 			}
 			return d.Location;
 		case spv::OpTypeVector:
 			for (auto i = 0u; i < obj.definition.word(3); i++, d.Component++)
 			{
 				// consumes N consecutive components in the same location
-				VisitInterfaceInner<F>(obj.definition.word(2), d, f);
+				VisitInterfaceInner(obj.definition.word(2), d, f);
 			}
 			return d.Location + 1;
 		case spv::OpTypeFloat:
@@ -1038,7 +986,7 @@
 			for (auto i = 0u; i < obj.definition.wordCount() - 2; i++)
 			{
 				ApplyDecorationsForIdMember(&d, id, i);
-				d.Location = VisitInterfaceInner<F>(obj.definition.word(i + 2), d, f);
+				d.Location = VisitInterfaceInner(obj.definition.word(i + 2), d, f);
 				d.Component = 0;    // Implicit locations always have component=0
 			}
 			return d.Location;
@@ -1048,7 +996,7 @@
 			auto arraySize = GetConstScalarInt(obj.definition.word(3));
 			for (auto i = 0u; i < arraySize; i++)
 			{
-				d.Location = VisitInterfaceInner<F>(obj.definition.word(2), d, f);
+				d.Location = VisitInterfaceInner(obj.definition.word(2), d, f);
 			}
 			return d.Location;
 		}
@@ -1058,8 +1006,7 @@
 		}
 	}
 
-	template<typename F>
-	void SpirvShader::VisitInterface(Object::ID id, F f) const
+	void SpirvShader::VisitInterface(Object::ID id, const InterfaceVisitor &f) const
 	{
 		// Walk a variable definition and call f for each component in it.
 		Decorations d{};
@@ -1067,146 +1014,7 @@
 
 		auto def = getObject(id).definition;
 		ASSERT(def.opcode() == spv::OpVariable);
-		VisitInterfaceInner<F>(def.word(1), d, f);
-	}
-
-	template<typename F>
-	void SpirvShader::VisitMemoryObjectInner(sw::SpirvShader::Type::ID id, sw::SpirvShader::Decorations d, uint32_t& index, uint32_t offset, F f) const
-	{
-		// Walk a type tree in an explicitly laid out storage class, calling
-		// a functor for each scalar element within the object.
-
-		// The functor's first parameter is the index of the scalar element;
-		// the second parameter is the offset (in bytes) from the base of the
-		// object.
-
-		ApplyDecorationsForId(&d, id);
-		auto const &type = getType(id);
-
-		if (d.HasOffset)
-		{
-			offset += d.Offset;
-			d.HasOffset = false;
-		}
-
-		switch (type.opcode())
-		{
-		case spv::OpTypePointer:
-			VisitMemoryObjectInner<F>(type.definition.word(3), d, index, offset, f);
-			break;
-		case spv::OpTypeInt:
-		case spv::OpTypeFloat:
-			f(index++, offset);
-			break;
-		case spv::OpTypeVector:
-		{
-			auto elemStride = (d.InsideMatrix && d.HasRowMajor && d.RowMajor) ? d.MatrixStride : static_cast<int32_t>(sizeof(float));
-			for (auto i = 0u; i < type.definition.word(3); i++)
-			{
-				VisitMemoryObjectInner(type.definition.word(2), d, index, offset + elemStride * i, f);
-			}
-			break;
-		}
-		case spv::OpTypeMatrix:
-		{
-			auto columnStride = (d.HasRowMajor && d.RowMajor) ? static_cast<int32_t>(sizeof(float)) : d.MatrixStride;
-			d.InsideMatrix = true;
-			for (auto i = 0u; i < type.definition.word(3); i++)
-			{
-				ASSERT(d.HasMatrixStride);
-				VisitMemoryObjectInner(type.definition.word(2), d, index, offset + columnStride * i, f);
-			}
-			break;
-		}
-		case spv::OpTypeStruct:
-			for (auto i = 0u; i < type.definition.wordCount() - 2; i++)
-			{
-				ApplyDecorationsForIdMember(&d, id, i);
-				VisitMemoryObjectInner<F>(type.definition.word(i + 2), d, index, offset, f);
-			}
-			break;
-		case spv::OpTypeArray:
-		{
-			auto arraySize = GetConstScalarInt(type.definition.word(3));
-			for (auto i = 0u; i < arraySize; i++)
-			{
-				ASSERT(d.HasArrayStride);
-				VisitMemoryObjectInner<F>(type.definition.word(2), d, index, offset + i * d.ArrayStride, f);
-			}
-			break;
-		}
-		default:
-			UNREACHABLE("%s", OpcodeName(type.opcode()).c_str());
-		}
-	}
-
-	template<typename F>
-	void SpirvShader::VisitMemoryObject(sw::SpirvShader::Object::ID id, F f) const
-	{
-		auto typeId = getObject(id).type;
-		auto const & type = getType(typeId);
-		if (IsExplicitLayout(type.storageClass))
-		{
-			Decorations d{};
-			ApplyDecorationsForId(&d, id);
-			uint32_t index = 0;
-			VisitMemoryObjectInner<F>(typeId, d, index, 0, f);
-		}
-		else
-		{
-			// Objects without explicit layout are tightly packed.
-			for (auto i = 0u; i < getType(type.element).sizeInComponents; i++)
-			{
-				f(i, i * sizeof(float));
-			}
-		}
-	}
-
-	SIMD::Pointer SpirvShader::GetPointerToData(Object::ID id, int arrayIndex, EmitState const *state) const
-	{
-		auto routine = state->routine;
-		auto &object = getObject(id);
-		switch (object.kind)
-		{
-			case Object::Kind::Pointer:
-			case Object::Kind::InterfaceVariable:
-				return state->getPointer(id);
-
-			case Object::Kind::DescriptorSet:
-			{
-				const auto &d = descriptorDecorations.at(id);
-				ASSERT(d.DescriptorSet >= 0 && d.DescriptorSet < vk::MAX_BOUND_DESCRIPTOR_SETS);
-				ASSERT(d.Binding >= 0);
-
-				auto set = state->getPointer(id);
-
-				auto setLayout = routine->pipelineLayout->getDescriptorSetLayout(d.DescriptorSet);
-				ASSERT_MSG(setLayout->hasBinding(d.Binding), "Descriptor set %d does not contain binding %d", int(d.DescriptorSet), int(d.Binding));
-				int bindingOffset = static_cast<int>(setLayout->getBindingOffset(d.Binding, arrayIndex));
-
-				Pointer<Byte> descriptor = set.base + bindingOffset; // BufferDescriptor*
-				Pointer<Byte> data = *Pointer<Pointer<Byte>>(descriptor + OFFSET(vk::BufferDescriptor, ptr)); // void*
-				Int size = *Pointer<Int>(descriptor + OFFSET(vk::BufferDescriptor, sizeInBytes));
-				if (setLayout->isBindingDynamic(d.Binding))
-				{
-					uint32_t dynamicBindingIndex =
-						routine->pipelineLayout->getDynamicOffsetBase(d.DescriptorSet) +
-						setLayout->getDynamicDescriptorOffset(d.Binding) +
-						arrayIndex;
-					Int offset = routine->descriptorDynamicOffsets[dynamicBindingIndex];
-					Int robustnessSize = *Pointer<Int>(descriptor + OFFSET(vk::BufferDescriptor, robustnessSize));
-					return SIMD::Pointer(data + offset, Min(size, robustnessSize - offset));
-				}
-				else
-				{
-					return SIMD::Pointer(data, size);
-				}
-			}
-
-			default:
-				UNREACHABLE("Invalid pointer kind %d", int(object.kind));
-				return SIMD::Pointer(Pointer<Byte>(), 0);
-		}
+		VisitInterfaceInner(def.word(1), d, f);
 	}
 
 	void SpirvShader::ApplyDecorationsForAccessChain(Decorations *d, DescriptorDecorations *dd, Object::ID baseId, uint32_t numIndexes, uint32_t const *indexIds) const
@@ -2119,240 +1927,6 @@
 		return EmitResult::Continue;
 	}
 
-	SpirvShader::EmitResult SpirvShader::EmitVariable(InsnIterator insn, EmitState *state) const
-	{
-		auto routine = state->routine;
-		Object::ID resultId = insn.word(2);
-		auto &object = getObject(resultId);
-		auto &objectTy = getType(object.type);
-
-		switch (objectTy.storageClass)
-		{
-		case spv::StorageClassOutput:
-		case spv::StorageClassPrivate:
-		case spv::StorageClassFunction:
-		{
-			ASSERT(objectTy.opcode() == spv::OpTypePointer);
-			auto base = &routine->getVariable(resultId)[0];
-			auto elementTy = getType(objectTy.element);
-			auto size = elementTy.sizeInComponents * static_cast<uint32_t>(sizeof(float)) * SIMD::Width;
-			state->createPointer(resultId, SIMD::Pointer(base, size));
-			break;
-		}
-		case spv::StorageClassWorkgroup:
-		{
-			ASSERT(objectTy.opcode() == spv::OpTypePointer);
-			auto base = &routine->workgroupMemory[0];
-			auto size = workgroupMemory.size();
-			state->createPointer(resultId, SIMD::Pointer(base, size, workgroupMemory.offsetOf(resultId)));
-			break;
-		}
-		case spv::StorageClassInput:
-		{
-			if (object.kind == Object::Kind::InterfaceVariable)
-			{
-				auto &dst = routine->getVariable(resultId);
-				int offset = 0;
-				VisitInterface(resultId,
-								[&](Decorations const &d, AttribType type) {
-									auto scalarSlot = d.Location << 2 | d.Component;
-									dst[offset++] = routine->inputs[scalarSlot];
-								});
-			}
-			ASSERT(objectTy.opcode() == spv::OpTypePointer);
-			auto base = &routine->getVariable(resultId)[0];
-			auto elementTy = getType(objectTy.element);
-			auto size = elementTy.sizeInComponents * static_cast<uint32_t>(sizeof(float)) * SIMD::Width;
-			state->createPointer(resultId, SIMD::Pointer(base, size));
-			break;
-		}
-		case spv::StorageClassUniformConstant:
-		{
-			const auto &d = descriptorDecorations.at(resultId);
-			ASSERT(d.DescriptorSet >= 0);
-			ASSERT(d.Binding >= 0);
-
-			uint32_t arrayIndex = 0;  // TODO(b/129523279)
-			auto setLayout = routine->pipelineLayout->getDescriptorSetLayout(d.DescriptorSet);
-			if (setLayout->hasBinding(d.Binding))
-			{
-				uint32_t bindingOffset = static_cast<uint32_t>(setLayout->getBindingOffset(d.Binding, arrayIndex));
-				Pointer<Byte> set = routine->descriptorSets[d.DescriptorSet];  // DescriptorSet*
-				Pointer<Byte> binding = Pointer<Byte>(set + bindingOffset);    // vk::SampledImageDescriptor*
-				auto size = 0; // Not required as this pointer is not directly used by SIMD::Read or SIMD::Write.
-				state->createPointer(resultId, SIMD::Pointer(binding, size));
-			}
-			else
-			{
-				// TODO: Error if the variable with the non-existant binding is
-				// used? Or perhaps strip these unused variable declarations as
-				// a preprocess on the SPIR-V?
-			}
-			break;
-		}
-		case spv::StorageClassUniform:
-		case spv::StorageClassStorageBuffer:
-		{
-			const auto &d = descriptorDecorations.at(resultId);
-			ASSERT(d.DescriptorSet >= 0);
-			auto size = 0; // Not required as this pointer is not directly used by SIMD::Read or SIMD::Write.
-			// Note: the module may contain descriptor set references that are not suitable for this implementation -- using a set index higher than the number
-			// of descriptor set binding points we support. As long as the selected entrypoint doesn't actually touch the out of range binding points, this
-			// is valid. In this case make the value nullptr to make it easier to diagnose an attempt to dereference it.
-			if (d.DescriptorSet < vk::MAX_BOUND_DESCRIPTOR_SETS)
-			{
-				state->createPointer(resultId, SIMD::Pointer(routine->descriptorSets[d.DescriptorSet], size));
-			}
-			else
-			{
-				state->createPointer(resultId, SIMD::Pointer(nullptr, 0));
-			}
-			break;
-		}
-		case spv::StorageClassPushConstant:
-		{
-			state->createPointer(resultId, SIMD::Pointer(routine->pushConstants, vk::MAX_PUSH_CONSTANT_SIZE));
-			break;
-		}
-		default:
-			UNREACHABLE("Storage class %d", objectTy.storageClass);
-			break;
-		}
-
-		if (insn.wordCount() > 4)
-		{
-			Object::ID initializerId = insn.word(4);
-			if (getObject(initializerId).kind != Object::Kind::Constant)
-			{
-				UNIMPLEMENTED("Non-constant initializers not yet implemented");
-			}
-			switch (objectTy.storageClass)
-			{
-			case spv::StorageClassOutput:
-			case spv::StorageClassPrivate:
-			case spv::StorageClassFunction:
-			{
-				bool interleavedByLane = IsStorageInterleavedByLane(objectTy.storageClass);
-				auto ptr = GetPointerToData(resultId, 0, state);
-				GenericValue initialValue(this, state, initializerId);
-				VisitMemoryObject(resultId, [&](uint32_t i, uint32_t offset)
-				{
-					auto p = ptr + offset;
-					if (interleavedByLane) { p = InterleaveByLane(p); }
-					auto robustness = OutOfBoundsBehavior::UndefinedBehavior;  // Local variables are always within bounds.
-					p.Store(initialValue.Float(i), robustness, state->activeLaneMask());
-				});
-				break;
-			}
-			default:
-				ASSERT_MSG(initializerId == 0, "Vulkan does not permit variables of storage class %d to have initializers", int(objectTy.storageClass));
-			}
-		}
-
-		return EmitResult::Continue;
-	}
-
-	SpirvShader::EmitResult SpirvShader::EmitLoad(InsnIterator insn, EmitState *state) const
-	{
-		bool atomic = (insn.opcode() == spv::OpAtomicLoad);
-		Object::ID resultId = insn.word(2);
-		Object::ID pointerId = insn.word(3);
-		auto &result = getObject(resultId);
-		auto &resultTy = getType(result.type);
-		auto &pointer = getObject(pointerId);
-		auto &pointerTy = getType(pointer.type);
-		std::memory_order memoryOrder = std::memory_order_relaxed;
-
-		ASSERT(getType(pointer.type).element == result.type);
-		ASSERT(Type::ID(insn.word(1)) == result.type);
-		ASSERT(!atomic || getType(getType(pointer.type).element).opcode() == spv::OpTypeInt);  // Vulkan 1.1: "Atomic instructions must declare a scalar 32-bit integer type, for the value pointed to by Pointer."
-
-		if(pointerTy.storageClass == spv::StorageClassUniformConstant)
-		{
-			// Just propagate the pointer.
-			auto &ptr = state->getPointer(pointerId);
-			state->createPointer(resultId, ptr);
-			return EmitResult::Continue;
-		}
-
-		if(atomic)
-		{
-			Object::ID semanticsId = insn.word(5);
-			auto memorySemantics = static_cast<spv::MemorySemanticsMask>(getObject(semanticsId).constantValue[0]);
-			memoryOrder = MemoryOrder(memorySemantics);
-		}
-
-		auto ptr = GetPointerToData(pointerId, 0, state);
-		bool interleavedByLane = IsStorageInterleavedByLane(pointerTy.storageClass);
-		auto &dst = state->createIntermediate(resultId, resultTy.sizeInComponents);
-		auto robustness = state->getOutOfBoundsBehavior(pointerTy.storageClass);
-
-		VisitMemoryObject(pointerId, [&](uint32_t i, uint32_t offset)
-		{
-			auto p = ptr + offset;
-			if (interleavedByLane) { p = InterleaveByLane(p); }  // TODO: Interleave once, then add offset?
-			dst.move(i, p.Load<SIMD::Float>(robustness, state->activeLaneMask(), atomic, memoryOrder));
-		});
-
-		return EmitResult::Continue;
-	}
-
-	SpirvShader::EmitResult SpirvShader::EmitStore(InsnIterator insn, EmitState *state) const
-	{
-		bool atomic = (insn.opcode() == spv::OpAtomicStore);
-		Object::ID pointerId = insn.word(1);
-		Object::ID objectId = insn.word(atomic ? 4 : 2);
-		auto &object = getObject(objectId);
-		auto &pointer = getObject(pointerId);
-		auto &pointerTy = getType(pointer.type);
-		auto &elementTy = getType(pointerTy.element);
-		std::memory_order memoryOrder = std::memory_order_relaxed;
-
-		if(atomic)
-		{
-			Object::ID semanticsId = insn.word(3);
-			auto memorySemantics = static_cast<spv::MemorySemanticsMask>(getObject(semanticsId).constantValue[0]);
-			memoryOrder = MemoryOrder(memorySemantics);
-		}
-
-		ASSERT(!atomic || elementTy.opcode() == spv::OpTypeInt);  // Vulkan 1.1: "Atomic instructions must declare a scalar 32-bit integer type, for the value pointed to by Pointer."
-
-		auto ptr = GetPointerToData(pointerId, 0, state);
-		bool interleavedByLane = IsStorageInterleavedByLane(pointerTy.storageClass);
-		auto robustness = state->getOutOfBoundsBehavior(pointerTy.storageClass);
-
-		SIMD::Int mask = state->activeLaneMask();
-		if (!StoresInHelperInvocation(pointerTy.storageClass))
-		{
-			mask = mask & state->storesAndAtomicsMask();
-		}
-
-		if (object.kind == Object::Kind::Constant)
-		{
-			// Constant source data.
-			const uint32_t *src = object.constantValue.get();
-			VisitMemoryObject(pointerId, [&](uint32_t i, uint32_t offset)
-			{
-				auto p = ptr + offset;
-				if (interleavedByLane) { p = InterleaveByLane(p); }
-				p.Store(SIMD::Int(src[i]), robustness, mask, atomic, memoryOrder);
-			});
-		}
-		else
-		{
-			// Intermediate source data.
-			auto &src = state->getIntermediate(objectId);
-			VisitMemoryObject(pointerId, [&](uint32_t i, uint32_t offset)
-			{
-				auto p = ptr + offset;
-				if (interleavedByLane) { p = InterleaveByLane(p); }
-				p.Store(src.Float(i), robustness, mask, atomic, memoryOrder);
-			});
-		}
-
-		return EmitResult::Continue;
-	}
-
 	SpirvShader::EmitResult SpirvShader::EmitAccessChain(InsnIterator insn, EmitState *state) const
 	{
 		Type::ID typeId = insn.word(1);
@@ -3051,29 +2625,6 @@
 		return EmitResult::Continue;
 	}
 
-	std::memory_order SpirvShader::MemoryOrder(spv::MemorySemanticsMask memorySemantics)
-	{
-		auto control = static_cast<uint32_t>(memorySemantics) & static_cast<uint32_t>(
-			spv::MemorySemanticsAcquireMask |
-			spv::MemorySemanticsReleaseMask |
-			spv::MemorySemanticsAcquireReleaseMask |
-			spv::MemorySemanticsSequentiallyConsistentMask
-		);
-		switch (control)
-		{
-		case spv::MemorySemanticsMaskNone:                   return std::memory_order_relaxed;
-		case spv::MemorySemanticsAcquireMask:                return std::memory_order_acquire;
-		case spv::MemorySemanticsReleaseMask:                return std::memory_order_release;
-		case spv::MemorySemanticsAcquireReleaseMask:         return std::memory_order_acq_rel;
-		case spv::MemorySemanticsSequentiallyConsistentMask: return std::memory_order_acq_rel;  // Vulkan 1.1: "SequentiallyConsistent is treated as AcquireRelease"
-		default:
-			// "it is invalid for more than one of these four bits to be set:
-			// Acquire, Release, AcquireRelease, or SequentiallyConsistent."
-			UNREACHABLE("MemorySemanticsMask: %x", int(control));
-			return std::memory_order_acq_rel;
-		}
-	}
-
 	SIMD::Float SpirvShader::Dot(unsigned numComponents, GenericValue const & x, GenericValue const & y) const
 	{
 		SIMD::Float d = x.Float(0) * y.Float(0);
@@ -4217,52 +3768,6 @@
 		return EmitResult::Continue;
 	}
 
-	SpirvShader::EmitResult SpirvShader::EmitCopyMemory(InsnIterator insn, EmitState *state) const
-	{
-		Object::ID dstPtrId = insn.word(1);
-		Object::ID srcPtrId = insn.word(2);
-		auto &dstPtrTy = getType(getObject(dstPtrId).type);
-		auto &srcPtrTy = getType(getObject(srcPtrId).type);
-		ASSERT(dstPtrTy.element == srcPtrTy.element);
-
-		bool dstInterleavedByLane = IsStorageInterleavedByLane(dstPtrTy.storageClass);
-		bool srcInterleavedByLane = IsStorageInterleavedByLane(srcPtrTy.storageClass);
-		auto dstPtr = GetPointerToData(dstPtrId, 0, state);
-		auto srcPtr = GetPointerToData(srcPtrId, 0, state);
-
-		std::unordered_map<uint32_t, uint32_t> srcOffsets;
-
-		VisitMemoryObject(srcPtrId, [&](uint32_t i, uint32_t srcOffset) { srcOffsets[i] = srcOffset; });
-
-		VisitMemoryObject(dstPtrId, [&](uint32_t i, uint32_t dstOffset)
-		{
-			auto it = srcOffsets.find(i);
-			ASSERT(it != srcOffsets.end());
-			auto srcOffset = it->second;
-
-			auto dst = dstPtr + dstOffset;
-			auto src = srcPtr + srcOffset;
-			if (dstInterleavedByLane) { dst = InterleaveByLane(dst); }
-			if (srcInterleavedByLane) { src = InterleaveByLane(src); }
-
-			// TODO(b/131224163): Optimize based on src/dst storage classes.
-			auto robustness = OutOfBoundsBehavior::RobustBufferAccess;
-
-			auto value = src.Load<SIMD::Float>(robustness, state->activeLaneMask());
-			dst.Store(value, robustness, state->activeLaneMask());
-		});
-		return EmitResult::Continue;
-	}
-
-	SpirvShader::EmitResult SpirvShader::EmitMemoryBarrier(InsnIterator insn, EmitState *state) const
-	{
-		auto semantics = spv::MemorySemanticsMask(GetConstScalarInt(insn.word(2)));
-		// TODO: We probably want to consider the memory scope here. For now,
-		// just always emit the full fence.
-		Fence(semantics);
-		return EmitResult::Continue;
-	}
-
 	SpirvShader::EmitResult SpirvShader::EmitGroupNonUniform(InsnIterator insn, EmitState *state) const
 	{
 		static_assert(SIMD::Width == 4, "EmitGroupNonUniform makes many assumptions that the SIMD vector width is 4");
diff --git a/src/Pipeline/SpirvShader.hpp b/src/Pipeline/SpirvShader.hpp
index 4889c57..20b96cc 100644
--- a/src/Pipeline/SpirvShader.hpp
+++ b/src/Pipeline/SpirvShader.hpp
@@ -731,17 +731,17 @@
 		// Output storage buffers and images should not be affected by helper invocations
 		static bool StoresInHelperInvocation(spv::StorageClass storageClass);
 
-		template<typename F>
-		int VisitInterfaceInner(Type::ID id, Decorations d, F f) const;
+		using InterfaceVisitor = std::function<void(Decorations const, AttribType)>;
 
-		template<typename F>
-		void VisitInterface(Object::ID id, F f) const;
+		void VisitInterface(Object::ID id, const InterfaceVisitor& v) const;
 
-		template<typename F>
-		void VisitMemoryObject(Object::ID id, F f) const;
+		int VisitInterfaceInner(Type::ID id, Decorations d, const InterfaceVisitor& v) const;
 
-		template<typename F>
-		void VisitMemoryObjectInner(Type::ID id, Decorations d, uint32_t &index, uint32_t offset, F f) const;
+		using MemoryVisitor = std::function<void(uint32_t index, uint32_t offset)>;
+
+		void VisitMemoryObject(Object::ID id, const MemoryVisitor& v) const;
+
+		void VisitMemoryObjectInner(Type::ID id, Decorations d, uint32_t &index, uint32_t offset, const MemoryVisitor& v) const;
 
 		Object& CreateConstant(InsnIterator it);
 
diff --git a/src/Pipeline/SpirvShaderMemory.cpp b/src/Pipeline/SpirvShaderMemory.cpp
new file mode 100644
index 0000000..afecbfe
--- /dev/null
+++ b/src/Pipeline/SpirvShaderMemory.cpp
@@ -0,0 +1,517 @@
+// Copyright 2019 The SwiftShader Authors. All Rights Reserved.
+//
+// Licensed under the Apache License, Version 2.0 (the "License");
+// you may not use this file except in compliance with the License.
+// You may obtain a copy of the License at
+//
+//    http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS,
+// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+// See the License for the specific language governing permissions and
+// limitations under the License.
+
+#include "SpirvShader.hpp"
+
+#include "ShaderCore.hpp"
+
+#include "Vulkan/VkPipelineLayout.hpp"
+
+#include <spirv/unified1/spirv.hpp>
+#include <spirv/unified1/GLSL.std.450.h>
+
+namespace sw {
+
+SpirvShader::EmitResult SpirvShader::EmitLoad(InsnIterator insn, EmitState *state) const
+{
+	bool atomic = (insn.opcode() == spv::OpAtomicLoad);
+	Object::ID resultId = insn.word(2);
+	Object::ID pointerId = insn.word(3);
+	auto &result = getObject(resultId);
+	auto &resultTy = getType(result.type);
+	auto &pointer = getObject(pointerId);
+	auto &pointerTy = getType(pointer.type);
+	std::memory_order memoryOrder = std::memory_order_relaxed;
+
+	ASSERT(getType(pointer.type).element == result.type);
+	ASSERT(Type::ID(insn.word(1)) == result.type);
+	ASSERT(!atomic || getType(getType(pointer.type).element).opcode() == spv::OpTypeInt);  // Vulkan 1.1: "Atomic instructions must declare a scalar 32-bit integer type, for the value pointed to by Pointer."
+
+	if(pointerTy.storageClass == spv::StorageClassUniformConstant)
+	{
+		// Just propagate the pointer.
+		auto &ptr = state->getPointer(pointerId);
+		state->createPointer(resultId, ptr);
+		return EmitResult::Continue;
+	}
+
+	if(atomic)
+	{
+		Object::ID semanticsId = insn.word(5);
+		auto memorySemantics = static_cast<spv::MemorySemanticsMask>(getObject(semanticsId).constantValue[0]);
+		memoryOrder = MemoryOrder(memorySemantics);
+	}
+
+	auto ptr = GetPointerToData(pointerId, 0, state);
+	bool interleavedByLane = IsStorageInterleavedByLane(pointerTy.storageClass);
+	auto &dst = state->createIntermediate(resultId, resultTy.sizeInComponents);
+	auto robustness = state->getOutOfBoundsBehavior(pointerTy.storageClass);
+
+	VisitMemoryObject(pointerId, [&](uint32_t i, uint32_t offset)
+	{
+		auto p = ptr + offset;
+		if (interleavedByLane) { p = InterleaveByLane(p); }  // TODO: Interleave once, then add offset?
+		dst.move(i, p.Load<SIMD::Float>(robustness, state->activeLaneMask(), atomic, memoryOrder));
+	});
+
+	return EmitResult::Continue;
+}
+
+SpirvShader::EmitResult SpirvShader::EmitStore(InsnIterator insn, EmitState *state) const
+{
+	bool atomic = (insn.opcode() == spv::OpAtomicStore);
+	Object::ID pointerId = insn.word(1);
+	Object::ID objectId = insn.word(atomic ? 4 : 2);
+	auto &object = getObject(objectId);
+	auto &pointer = getObject(pointerId);
+	auto &pointerTy = getType(pointer.type);
+	auto &elementTy = getType(pointerTy.element);
+	std::memory_order memoryOrder = std::memory_order_relaxed;
+
+	if(atomic)
+	{
+		Object::ID semanticsId = insn.word(3);
+		auto memorySemantics = static_cast<spv::MemorySemanticsMask>(getObject(semanticsId).constantValue[0]);
+		memoryOrder = MemoryOrder(memorySemantics);
+	}
+
+	ASSERT(!atomic || elementTy.opcode() == spv::OpTypeInt);  // Vulkan 1.1: "Atomic instructions must declare a scalar 32-bit integer type, for the value pointed to by Pointer."
+
+	auto ptr = GetPointerToData(pointerId, 0, state);
+	bool interleavedByLane = IsStorageInterleavedByLane(pointerTy.storageClass);
+	auto robustness = state->getOutOfBoundsBehavior(pointerTy.storageClass);
+
+	SIMD::Int mask = state->activeLaneMask();
+	if (!StoresInHelperInvocation(pointerTy.storageClass))
+	{
+		mask = mask & state->storesAndAtomicsMask();
+	}
+
+	if (object.kind == Object::Kind::Constant)
+	{
+		// Constant source data.
+		const uint32_t *src = object.constantValue.get();
+		VisitMemoryObject(pointerId, [&](uint32_t i, uint32_t offset)
+		{
+			auto p = ptr + offset;
+			if (interleavedByLane) { p = InterleaveByLane(p); }
+			p.Store(SIMD::Int(src[i]), robustness, mask, atomic, memoryOrder);
+		});
+	}
+	else
+	{
+		// Intermediate source data.
+		auto &src = state->getIntermediate(objectId);
+		VisitMemoryObject(pointerId, [&](uint32_t i, uint32_t offset)
+		{
+			auto p = ptr + offset;
+			if (interleavedByLane) { p = InterleaveByLane(p); }
+			p.Store(src.Float(i), robustness, mask, atomic, memoryOrder);
+		});
+	}
+
+	return EmitResult::Continue;
+}
+
+SpirvShader::EmitResult SpirvShader::EmitVariable(InsnIterator insn, EmitState *state) const
+{
+	auto routine = state->routine;
+	Object::ID resultId = insn.word(2);
+	auto &object = getObject(resultId);
+	auto &objectTy = getType(object.type);
+
+	switch (objectTy.storageClass)
+	{
+	case spv::StorageClassOutput:
+	case spv::StorageClassPrivate:
+	case spv::StorageClassFunction:
+	{
+		ASSERT(objectTy.opcode() == spv::OpTypePointer);
+		auto base = &routine->getVariable(resultId)[0];
+		auto elementTy = getType(objectTy.element);
+		auto size = elementTy.sizeInComponents * static_cast<uint32_t>(sizeof(float)) * SIMD::Width;
+		state->createPointer(resultId, SIMD::Pointer(base, size));
+		break;
+	}
+	case spv::StorageClassWorkgroup:
+	{
+		ASSERT(objectTy.opcode() == spv::OpTypePointer);
+		auto base = &routine->workgroupMemory[0];
+		auto size = workgroupMemory.size();
+		state->createPointer(resultId, SIMD::Pointer(base, size, workgroupMemory.offsetOf(resultId)));
+		break;
+	}
+	case spv::StorageClassInput:
+	{
+		if (object.kind == Object::Kind::InterfaceVariable)
+		{
+			auto &dst = routine->getVariable(resultId);
+			int offset = 0;
+			VisitInterface(resultId,
+							[&](Decorations const &d, AttribType type) {
+								auto scalarSlot = d.Location << 2 | d.Component;
+								dst[offset++] = routine->inputs[scalarSlot];
+							});
+		}
+		ASSERT(objectTy.opcode() == spv::OpTypePointer);
+		auto base = &routine->getVariable(resultId)[0];
+		auto elementTy = getType(objectTy.element);
+		auto size = elementTy.sizeInComponents * static_cast<uint32_t>(sizeof(float)) * SIMD::Width;
+		state->createPointer(resultId, SIMD::Pointer(base, size));
+		break;
+	}
+	case spv::StorageClassUniformConstant:
+	{
+		const auto &d = descriptorDecorations.at(resultId);
+		ASSERT(d.DescriptorSet >= 0);
+		ASSERT(d.Binding >= 0);
+
+		uint32_t arrayIndex = 0;  // TODO(b/129523279)
+		auto setLayout = routine->pipelineLayout->getDescriptorSetLayout(d.DescriptorSet);
+		if (setLayout->hasBinding(d.Binding))
+		{
+			uint32_t bindingOffset = static_cast<uint32_t>(setLayout->getBindingOffset(d.Binding, arrayIndex));
+			Pointer<Byte> set = routine->descriptorSets[d.DescriptorSet];  // DescriptorSet*
+			Pointer<Byte> binding = Pointer<Byte>(set + bindingOffset);    // vk::SampledImageDescriptor*
+			auto size = 0; // Not required as this pointer is not directly used by SIMD::Read or SIMD::Write.
+			state->createPointer(resultId, SIMD::Pointer(binding, size));
+		}
+		else
+		{
+			// TODO: Error if the variable with the non-existant binding is
+			// used? Or perhaps strip these unused variable declarations as
+			// a preprocess on the SPIR-V?
+		}
+		break;
+	}
+	case spv::StorageClassUniform:
+	case spv::StorageClassStorageBuffer:
+	{
+		const auto &d = descriptorDecorations.at(resultId);
+		ASSERT(d.DescriptorSet >= 0);
+		auto size = 0; // Not required as this pointer is not directly used by SIMD::Read or SIMD::Write.
+		// Note: the module may contain descriptor set references that are not suitable for this implementation -- using a set index higher than the number
+		// of descriptor set binding points we support. As long as the selected entrypoint doesn't actually touch the out of range binding points, this
+		// is valid. In this case make the value nullptr to make it easier to diagnose an attempt to dereference it.
+		if (d.DescriptorSet < vk::MAX_BOUND_DESCRIPTOR_SETS)
+		{
+			state->createPointer(resultId, SIMD::Pointer(routine->descriptorSets[d.DescriptorSet], size));
+		}
+		else
+		{
+			state->createPointer(resultId, SIMD::Pointer(nullptr, 0));
+		}
+		break;
+	}
+	case spv::StorageClassPushConstant:
+	{
+		state->createPointer(resultId, SIMD::Pointer(routine->pushConstants, vk::MAX_PUSH_CONSTANT_SIZE));
+		break;
+	}
+	default:
+		UNREACHABLE("Storage class %d", objectTy.storageClass);
+		break;
+	}
+
+	if (insn.wordCount() > 4)
+	{
+		Object::ID initializerId = insn.word(4);
+		if (getObject(initializerId).kind != Object::Kind::Constant)
+		{
+			UNIMPLEMENTED("Non-constant initializers not yet implemented");
+		}
+		switch (objectTy.storageClass)
+		{
+		case spv::StorageClassOutput:
+		case spv::StorageClassPrivate:
+		case spv::StorageClassFunction:
+		{
+			bool interleavedByLane = IsStorageInterleavedByLane(objectTy.storageClass);
+			auto ptr = GetPointerToData(resultId, 0, state);
+			GenericValue initialValue(this, state, initializerId);
+			VisitMemoryObject(resultId, [&](uint32_t i, uint32_t offset)
+			{
+				auto p = ptr + offset;
+				if (interleavedByLane) { p = InterleaveByLane(p); }
+				auto robustness = OutOfBoundsBehavior::UndefinedBehavior;  // Local variables are always within bounds.
+				p.Store(initialValue.Float(i), robustness, state->activeLaneMask());
+			});
+			break;
+		}
+		default:
+			ASSERT_MSG(initializerId == 0, "Vulkan does not permit variables of storage class %d to have initializers", int(objectTy.storageClass));
+		}
+	}
+
+	return EmitResult::Continue;
+}
+
+SpirvShader::EmitResult SpirvShader::EmitCopyMemory(InsnIterator insn, EmitState *state) const
+{
+	Object::ID dstPtrId = insn.word(1);
+	Object::ID srcPtrId = insn.word(2);
+	auto &dstPtrTy = getType(getObject(dstPtrId).type);
+	auto &srcPtrTy = getType(getObject(srcPtrId).type);
+	ASSERT(dstPtrTy.element == srcPtrTy.element);
+
+	bool dstInterleavedByLane = IsStorageInterleavedByLane(dstPtrTy.storageClass);
+	bool srcInterleavedByLane = IsStorageInterleavedByLane(srcPtrTy.storageClass);
+	auto dstPtr = GetPointerToData(dstPtrId, 0, state);
+	auto srcPtr = GetPointerToData(srcPtrId, 0, state);
+
+	std::unordered_map<uint32_t, uint32_t> srcOffsets;
+
+	VisitMemoryObject(srcPtrId, [&](uint32_t i, uint32_t srcOffset) { srcOffsets[i] = srcOffset; });
+
+	VisitMemoryObject(dstPtrId, [&](uint32_t i, uint32_t dstOffset)
+	{
+		auto it = srcOffsets.find(i);
+		ASSERT(it != srcOffsets.end());
+		auto srcOffset = it->second;
+
+		auto dst = dstPtr + dstOffset;
+		auto src = srcPtr + srcOffset;
+		if (dstInterleavedByLane) { dst = InterleaveByLane(dst); }
+		if (srcInterleavedByLane) { src = InterleaveByLane(src); }
+
+		// TODO(b/131224163): Optimize based on src/dst storage classes.
+		auto robustness = OutOfBoundsBehavior::RobustBufferAccess;
+
+		auto value = src.Load<SIMD::Float>(robustness, state->activeLaneMask());
+		dst.Store(value, robustness, state->activeLaneMask());
+	});
+	return EmitResult::Continue;
+}
+
+SpirvShader::EmitResult SpirvShader::EmitMemoryBarrier(InsnIterator insn, EmitState *state) const
+{
+	auto semantics = spv::MemorySemanticsMask(GetConstScalarInt(insn.word(2)));
+	// TODO: We probably want to consider the memory scope here. For now,
+	// just always emit the full fence.
+	Fence(semantics);
+	return EmitResult::Continue;
+}
+
+void SpirvShader::VisitMemoryObjectInner(sw::SpirvShader::Type::ID id, sw::SpirvShader::Decorations d, uint32_t& index, uint32_t offset, const MemoryVisitor &f) const
+{
+	// Walk a type tree in an explicitly laid out storage class, calling
+	// a functor for each scalar element within the object.
+
+	// The functor's first parameter is the index of the scalar element;
+	// the second parameter is the offset (in bytes) from the base of the
+	// object.
+
+	ApplyDecorationsForId(&d, id);
+	auto const &type = getType(id);
+
+	if (d.HasOffset)
+	{
+		offset += d.Offset;
+		d.HasOffset = false;
+	}
+
+	switch (type.opcode())
+	{
+	case spv::OpTypePointer:
+		VisitMemoryObjectInner(type.definition.word(3), d, index, offset, f);
+		break;
+	case spv::OpTypeInt:
+	case spv::OpTypeFloat:
+		f(index++, offset);
+		break;
+	case spv::OpTypeVector:
+	{
+		auto elemStride = (d.InsideMatrix && d.HasRowMajor && d.RowMajor) ? d.MatrixStride : static_cast<int32_t>(sizeof(float));
+		for (auto i = 0u; i < type.definition.word(3); i++)
+		{
+			VisitMemoryObjectInner(type.definition.word(2), d, index, offset + elemStride * i, f);
+		}
+		break;
+	}
+	case spv::OpTypeMatrix:
+	{
+		auto columnStride = (d.HasRowMajor && d.RowMajor) ? static_cast<int32_t>(sizeof(float)) : d.MatrixStride;
+		d.InsideMatrix = true;
+		for (auto i = 0u; i < type.definition.word(3); i++)
+		{
+			ASSERT(d.HasMatrixStride);
+			VisitMemoryObjectInner(type.definition.word(2), d, index, offset + columnStride * i, f);
+		}
+		break;
+	}
+	case spv::OpTypeStruct:
+		for (auto i = 0u; i < type.definition.wordCount() - 2; i++)
+		{
+			ApplyDecorationsForIdMember(&d, id, i);
+			VisitMemoryObjectInner(type.definition.word(i + 2), d, index, offset, f);
+		}
+		break;
+	case spv::OpTypeArray:
+	{
+		auto arraySize = GetConstScalarInt(type.definition.word(3));
+		for (auto i = 0u; i < arraySize; i++)
+		{
+			ASSERT(d.HasArrayStride);
+			VisitMemoryObjectInner(type.definition.word(2), d, index, offset + i * d.ArrayStride, f);
+		}
+		break;
+	}
+	default:
+		UNREACHABLE("%s", OpcodeName(type.opcode()).c_str());
+	}
+}
+
+void SpirvShader::VisitMemoryObject(sw::SpirvShader::Object::ID id, const MemoryVisitor &f) const
+{
+	auto typeId = getObject(id).type;
+	auto const & type = getType(typeId);
+	if (IsExplicitLayout(type.storageClass))
+	{
+		Decorations d{};
+		ApplyDecorationsForId(&d, id);
+		uint32_t index = 0;
+		VisitMemoryObjectInner(typeId, d, index, 0, f);
+	}
+	else
+	{
+		// Objects without explicit layout are tightly packed.
+		for (auto i = 0u; i < getType(type.element).sizeInComponents; i++)
+		{
+			f(i, i * sizeof(float));
+		}
+	}
+}
+
+SIMD::Pointer SpirvShader::GetPointerToData(Object::ID id, int arrayIndex, EmitState const *state) const
+{
+	auto routine = state->routine;
+	auto &object = getObject(id);
+	switch (object.kind)
+	{
+		case Object::Kind::Pointer:
+		case Object::Kind::InterfaceVariable:
+			return state->getPointer(id);
+
+		case Object::Kind::DescriptorSet:
+		{
+			const auto &d = descriptorDecorations.at(id);
+			ASSERT(d.DescriptorSet >= 0 && d.DescriptorSet < vk::MAX_BOUND_DESCRIPTOR_SETS);
+			ASSERT(d.Binding >= 0);
+
+			auto set = state->getPointer(id);
+
+			auto setLayout = routine->pipelineLayout->getDescriptorSetLayout(d.DescriptorSet);
+			ASSERT_MSG(setLayout->hasBinding(d.Binding), "Descriptor set %d does not contain binding %d", int(d.DescriptorSet), int(d.Binding));
+			int bindingOffset = static_cast<int>(setLayout->getBindingOffset(d.Binding, arrayIndex));
+
+			Pointer<Byte> descriptor = set.base + bindingOffset; // BufferDescriptor*
+			Pointer<Byte> data = *Pointer<Pointer<Byte>>(descriptor + OFFSET(vk::BufferDescriptor, ptr)); // void*
+			Int size = *Pointer<Int>(descriptor + OFFSET(vk::BufferDescriptor, sizeInBytes));
+			if (setLayout->isBindingDynamic(d.Binding))
+			{
+				uint32_t dynamicBindingIndex =
+					routine->pipelineLayout->getDynamicOffsetBase(d.DescriptorSet) +
+					setLayout->getDynamicDescriptorOffset(d.Binding) +
+					arrayIndex;
+				Int offset = routine->descriptorDynamicOffsets[dynamicBindingIndex];
+				Int robustnessSize = *Pointer<Int>(descriptor + OFFSET(vk::BufferDescriptor, robustnessSize));
+				return SIMD::Pointer(data + offset, Min(size, robustnessSize - offset));
+			}
+			else
+			{
+				return SIMD::Pointer(data, size);
+			}
+		}
+
+		default:
+			UNREACHABLE("Invalid pointer kind %d", int(object.kind));
+			return SIMD::Pointer(Pointer<Byte>(), 0);
+	}
+}
+
+std::memory_order SpirvShader::MemoryOrder(spv::MemorySemanticsMask memorySemantics)
+{
+	auto control = static_cast<uint32_t>(memorySemantics) & static_cast<uint32_t>(
+		spv::MemorySemanticsAcquireMask |
+		spv::MemorySemanticsReleaseMask |
+		spv::MemorySemanticsAcquireReleaseMask |
+		spv::MemorySemanticsSequentiallyConsistentMask
+	);
+	switch (control)
+	{
+	case spv::MemorySemanticsMaskNone:                   return std::memory_order_relaxed;
+	case spv::MemorySemanticsAcquireMask:                return std::memory_order_acquire;
+	case spv::MemorySemanticsReleaseMask:                return std::memory_order_release;
+	case spv::MemorySemanticsAcquireReleaseMask:         return std::memory_order_acq_rel;
+	case spv::MemorySemanticsSequentiallyConsistentMask: return std::memory_order_acq_rel;  // Vulkan 1.1: "SequentiallyConsistent is treated as AcquireRelease"
+	default:
+		// "it is invalid for more than one of these four bits to be set:
+		// Acquire, Release, AcquireRelease, or SequentiallyConsistent."
+		UNREACHABLE("MemorySemanticsMask: %x", int(control));
+		return std::memory_order_acq_rel;
+	}
+}
+
+bool SpirvShader::StoresInHelperInvocation(spv::StorageClass storageClass)
+{
+	switch (storageClass)
+	{
+	case spv::StorageClassUniform:
+	case spv::StorageClassStorageBuffer:
+	case spv::StorageClassImage:
+		return false;
+	default:
+		return true;
+	}
+}
+
+bool SpirvShader::IsExplicitLayout(spv::StorageClass storageClass)
+{
+	switch (storageClass)
+	{
+	case spv::StorageClassUniform:
+	case spv::StorageClassStorageBuffer:
+	case spv::StorageClassPushConstant:
+		return true;
+	default:
+		return false;
+	}
+}
+
+sw::SIMD::Pointer SpirvShader::InterleaveByLane(sw::SIMD::Pointer p)
+{
+	p *= sw::SIMD::Width;
+	p.staticOffsets[0] += 0 * sizeof(float);
+	p.staticOffsets[1] += 1 * sizeof(float);
+	p.staticOffsets[2] += 2 * sizeof(float);
+	p.staticOffsets[3] += 3 * sizeof(float);
+	return p;
+}
+
+bool SpirvShader::IsStorageInterleavedByLane(spv::StorageClass storageClass)
+{
+	switch (storageClass)
+	{
+	case spv::StorageClassUniform:
+	case spv::StorageClassStorageBuffer:
+	case spv::StorageClassPushConstant:
+	case spv::StorageClassWorkgroup:
+	case spv::StorageClassImage:
+		return false;
+	default:
+		return true;
+	}
+}
+
+}  // namespace sw
\ No newline at end of file
diff --git a/src/Vulkan/vulkan.vcxproj b/src/Vulkan/vulkan.vcxproj
index e77b208..8f0c931 100644
--- a/src/Vulkan/vulkan.vcxproj
+++ b/src/Vulkan/vulkan.vcxproj
@@ -167,6 +167,7 @@
     <ClCompile Include="..\Pipeline\SpirvShader.cpp" />
     <ClCompile Include="..\Pipeline\SpirvShaderControlFlow.cpp" />
     <ClCompile Include="..\Pipeline\SpirvShaderGLSLstd450.cpp" />
+    <ClCompile Include="..\Pipeline\SpirvShaderMemory.cpp" />
     <ClCompile Include="..\Pipeline\SpirvShaderSampling.cpp" />
     <ClCompile Include="..\Pipeline\SpirvShader_dbg.cpp" />
     <ClCompile Include="..\Pipeline\VertexProgram.cpp" />
diff --git a/src/Vulkan/vulkan.vcxproj.filters b/src/Vulkan/vulkan.vcxproj.filters
index e8e3c09..514b33a 100644
--- a/src/Vulkan/vulkan.vcxproj.filters
+++ b/src/Vulkan/vulkan.vcxproj.filters
@@ -252,6 +252,9 @@
     <ClCompile Include="..\Pipeline\SpirvShaderGLSLstd450.cpp">
       <Filter>Source Files\Pipeline</Filter>
     </ClCompile>
+    <ClCompile Include="..\Pipeline\SpirvShaderMemory.cpp">
+      <Filter>Source Files\Pipeline</Filter>
+    </ClCompile>
     <ClCompile Include="..\Pipeline\SpirvShaderSampling.cpp">
       <Filter>Source Files\Pipeline</Filter>
     </ClCompile>
