@@ -288,19 +288,17 @@ bool CoreChecks::ValidateSetMemBinding(const vvl::DeviceMemory &memory_state, co
288288
289289 const bool bind_2 = (loc.function != Func::vkBindBufferMemory) && (loc.function != Func::vkBindImageMemory);
290290 auto typed_handle = mem_binding.Handle ();
291+ const bool is_buffer = typed_handle.type == kVulkanObjectTypeBuffer ;
291292
292293 if (mem_binding.sparse ) {
293- const char *vuid = nullptr ;
294- const char *handle_type = nullptr ;
295- if (typed_handle.type == kVulkanObjectTypeBuffer ) {
296- handle_type = " BUFFER" ;
294+ const char *vuid = kVUIDUndefined ;
295+ const char *handle_type = is_buffer ? " BUFFER" : " IMAGE" ;
296+ if (is_buffer) {
297297 vuid = bind_2 ? " VUID-VkBindBufferMemoryInfo-buffer-01030" : " VUID-vkBindBufferMemory-buffer-01030" ;
298- } else if (typed_handle.type == kVulkanObjectTypeImage ) {
299- handle_type = " IMAGE" ;
300- vuid = bind_2 ? " VUID-VkBindImageMemoryInfo-image-01045" : " VUID-vkBindImageMemory-image-01045" ;
301298 } else {
302- assert ( false ); // Unsupported object type
299+ vuid = bind_2 ? " VUID-VkBindImageMemoryInfo-image-01045 " : " VUID-vkBindImageMemory-image-01045 " ;
303300 }
301+
304302 const LogObjectList objlist (memory_state.Handle (), typed_handle);
305303 skip |= LogError (vuid, objlist, loc,
306304 " attempting to bind %s to %s which was created with sparse memory flags "
@@ -309,19 +307,30 @@ bool CoreChecks::ValidateSetMemBinding(const vvl::DeviceMemory &memory_state, co
309307 }
310308
311309 const auto *prev_binding = mem_binding.MemState ();
312- if (prev_binding) {
313- const char *vuid = nullptr ;
314- if (typed_handle. type == kVulkanObjectTypeBuffer ) {
310+ if (prev_binding || mem_binding. partial_bound ) {
311+ const char *vuid = kVUIDUndefined ;
312+ if (is_buffer ) {
315313 vuid = bind_2 ? " VUID-VkBindBufferMemoryInfo-buffer-07459" : " VUID-vkBindBufferMemory-buffer-07459" ;
316- } else if (typed_handle. type == kVulkanObjectTypeImage ) {
314+ } else {
317315 vuid = bind_2 ? " VUID-VkBindImageMemoryInfo-image-07460" : " VUID-vkBindImageMemory-image-07460" ;
316+ }
317+
318+ if (mem_binding.partial_bound ) {
319+ Func bind_call = is_buffer ? Func::vkBindBufferMemory2 : Func::vkBindImageMemory2;
320+ const char *handle_type = is_buffer ? " buffer" : " image" ;
321+ const LogObjectList objlist (memory_state.Handle (), typed_handle);
322+ skip |= LogError (
323+ vuid, objlist, loc,
324+ " attempting to bind %s to %s which is in an indeterminate (possibly bound) state. A previous call to %s failed and "
325+ " we have to assume the %s was bound (but best advise is to handle the case and recreate the %s)." ,
326+ FormatHandle (memory_state.Handle ()).c_str (), FormatHandle (typed_handle).c_str (), String (bind_call), handle_type,
327+ handle_type);
318328 } else {
319- assert (false ); // Unsupported object type
329+ const LogObjectList objlist (memory_state.Handle (), typed_handle, prev_binding->Handle ());
330+ skip |= LogError (vuid, objlist, loc, " attempting to bind %s to %s which has already been bound to %s." ,
331+ FormatHandle (memory_state.Handle ()).c_str (), FormatHandle (typed_handle).c_str (),
332+ FormatHandle (prev_binding->Handle ()).c_str ());
320333 }
321- const LogObjectList objlist (memory_state.Handle (), typed_handle, prev_binding->Handle ());
322- skip |= LogError (vuid, objlist, loc, " attempting to bind %s to %s which has already been bound to %s." ,
323- FormatHandle (memory_state.Handle ()).c_str (), FormatHandle (typed_handle).c_str (),
324- FormatHandle (prev_binding->Handle ()).c_str ());
325334 }
326335 return skip;
327336}
@@ -1063,7 +1072,6 @@ bool CoreChecks::PreCallValidateBindBufferMemory(VkDevice device, VkBuffer buffe
10631072bool CoreChecks::PreCallValidateBindBufferMemory2 (VkDevice device, uint32_t bindInfoCount, const VkBindBufferMemoryInfo *pBindInfos,
10641073 const ErrorObject &error_obj) const {
10651074 bool skip = false ;
1066-
10671075 for (uint32_t i = 0 ; i < bindInfoCount; i++) {
10681076 const Location loc = error_obj.location .dot (Field::pBindInfos, i);
10691077 skip |= ValidateBindBufferMemory (pBindInfos[i].buffer , pBindInfos[i].memory , pBindInfos[i].memoryOffset ,
@@ -2061,7 +2069,16 @@ bool CoreChecks::PreCallValidateBindImageMemory2(VkDevice device, uint32_t bindI
20612069
20622070void CoreChecks::PostCallRecordBindImageMemory2 (VkDevice device, uint32_t bindInfoCount, const VkBindImageMemoryInfo *pBindInfos,
20632071 const RecordObject &record_obj) {
2064- if (VK_SUCCESS != record_obj.result ) return ;
2072+ if (VK_SUCCESS != record_obj.result ) {
2073+ if (bindInfoCount > 1 ) {
2074+ for (uint32_t i = 0 ; i < bindInfoCount; i++) {
2075+ if (auto image_state = Get<vvl::Image>(pBindInfos[i].image )) {
2076+ image_state->partial_bound = true ;
2077+ }
2078+ }
2079+ }
2080+ return ;
2081+ }
20652082 StateTracker::PostCallRecordBindImageMemory2 (device, bindInfoCount, pBindInfos, record_obj);
20662083
20672084 for (uint32_t i = 0 ; i < bindInfoCount; i++) {
0 commit comments