@@ -6,6 +6,7 @@ use std::{
6
6
thread,
7
7
} ;
8
8
9
+ use arrayvec:: ArrayVec ;
9
10
use ash:: {
10
11
extensions:: { ext, khr} ,
11
12
vk,
@@ -653,26 +654,27 @@ impl crate::Instance<super::Api> for super::Instance {
653
654
let validation_layer_name =
654
655
CStr :: from_bytes_with_nul ( b"VK_LAYER_KHRONOS_validation\0 " ) . unwrap ( ) ;
655
656
let validation_layer_properties = find_layer ( & instance_layers, validation_layer_name) ;
656
- let validation_features_are_enabled = || {
657
- validation_layer_properties. is_some ( ) . then ( || {
658
- let exts = Self :: enumerate_instance_extension_properties (
659
- & entry,
660
- Some ( validation_layer_name) ,
661
- ) ?;
662
- let mut ext_names = exts
663
- . iter ( )
664
- . filter_map ( |ext| cstr_from_bytes_until_nul ( & ext. extension_name ) ) ;
665
- let found =
666
- ext_names. any ( |ext_name| ext_name == vk:: ExtValidationFeaturesFn :: name ( ) ) ;
667
- Ok ( found)
668
- } )
657
+
658
+ // Determine if VK_EXT_validation_features is available, so we can enable
659
+ // GPU assisted validation and synchronization validation.
660
+ let validation_features_are_enabled = if validation_layer_properties. is_some ( ) {
661
+ // Get the all the instance extension properties.
662
+ let exts =
663
+ Self :: enumerate_instance_extension_properties ( & entry, Some ( validation_layer_name) ) ?;
664
+ // Convert all the names of the extensions into an iterator of CStrs.
665
+ let mut ext_names = exts
666
+ . iter ( )
667
+ . filter_map ( |ext| cstr_from_bytes_until_nul ( & ext. extension_name ) ) ;
668
+ // Find the validation features extension.
669
+ ext_names. any ( |ext_name| ext_name == vk:: ExtValidationFeaturesFn :: name ( ) )
670
+ } else {
671
+ false
669
672
} ;
673
+
670
674
let should_enable_gpu_based_validation = desc
671
675
. flags
672
676
. intersects ( wgt:: InstanceFlags :: GPU_BASED_VALIDATION )
673
- && validation_features_are_enabled ( )
674
- . transpose ( ) ?
675
- . unwrap_or ( false ) ;
677
+ && validation_features_are_enabled;
676
678
677
679
let nv_optimus_layer = CStr :: from_bytes_with_nul ( b"VK_LAYER_NV_optimus\0 " ) . unwrap ( ) ;
678
680
let has_nv_optimus = find_layer ( & instance_layers, nv_optimus_layer) . is_some ( ) ;
@@ -787,14 +789,26 @@ impl crate::Instance<super::Api> for super::Instance {
787
789
create_info = create_info. push_next ( vk_create_info) ;
788
790
}
789
791
790
- let mut gpu_assisted_validation = vk:: ValidationFeaturesEXT :: builder ( )
791
- . enabled_validation_features ( & [
792
- vk:: ValidationFeatureEnableEXT :: GPU_ASSISTED ,
793
- vk:: ValidationFeatureEnableEXT :: GPU_ASSISTED_RESERVE_BINDING_SLOT ,
794
- vk:: ValidationFeatureEnableEXT :: SYNCHRONIZATION_VALIDATION ,
795
- ] ) ;
796
- if should_enable_gpu_based_validation {
797
- create_info = create_info. push_next ( & mut gpu_assisted_validation) ;
792
+ // Enable explicit validation features if available
793
+ let mut validation_features;
794
+ let mut validation_feature_list: ArrayVec < _ , 3 > ;
795
+ if validation_features_are_enabled {
796
+ validation_feature_list = ArrayVec :: new ( ) ;
797
+
798
+ // Always enable synchronization validation
799
+ validation_feature_list
800
+ . push ( vk:: ValidationFeatureEnableEXT :: SYNCHRONIZATION_VALIDATION ) ;
801
+
802
+ // Only enable GPU assisted validation if requested.
803
+ if should_enable_gpu_based_validation {
804
+ validation_feature_list. push ( vk:: ValidationFeatureEnableEXT :: GPU_ASSISTED ) ;
805
+ validation_feature_list
806
+ . push ( vk:: ValidationFeatureEnableEXT :: GPU_ASSISTED_RESERVE_BINDING_SLOT ) ;
807
+ }
808
+
809
+ validation_features = vk:: ValidationFeaturesEXT :: builder ( )
810
+ . enabled_validation_features ( & validation_feature_list) ;
811
+ create_info = create_info. push_next ( & mut validation_features) ;
798
812
}
799
813
800
814
unsafe {
0 commit comments