11use super :: Builder ;
2+ use crate :: abi:: ConvSpirvType ;
23use crate :: builder_spirv:: { BuilderCursor , SpirvConst , SpirvValue , SpirvValueExt , SpirvValueKind } ;
34use crate :: spirv_type:: SpirvType ;
45use rspirv:: dr:: { InsertPoint , Instruction , Operand } ;
@@ -313,7 +314,7 @@ impl<'a, 'tcx> Builder<'a, 'tcx> {
313314 } else {
314315 for index in 0 ..count {
315316 let const_index = self . constant_u32 ( self . span ( ) , index as u32 ) ;
316- let gep_ptr = self . gep ( ptr, & [ const_index] ) ;
317+ let gep_ptr = self . gep ( pat . ty , ptr, & [ const_index] ) ;
317318 self . store ( pat, gep_ptr, Align :: from_bytes ( 0 ) . unwrap ( ) ) ;
318319 }
319320 }
@@ -339,11 +340,11 @@ impl<'a, 'tcx> Builder<'a, 'tcx> {
339340 self . store ( zero, index, zero_align) ;
340341 self . br ( header. llbb ( ) ) ;
341342
342- let current_index = header. load ( index, zero_align) ;
343+ let current_index = header. load ( count . ty , index, zero_align) ;
343344 let cond = header. icmp ( IntPredicate :: IntULT , current_index, count) ;
344345 header. cond_br ( cond, body. llbb ( ) , exit. llbb ( ) ) ;
345346
346- let gep_ptr = body. gep ( ptr, & [ current_index] ) ;
347+ let gep_ptr = body. gep ( pat . ty , ptr, & [ current_index] ) ;
347348 body. store ( pat, gep_ptr, zero_align) ;
348349 let current_index_plus_1 = body. add ( current_index, one) ;
349350 body. store ( current_index_plus_1, index, zero_align) ;
@@ -623,14 +624,15 @@ impl<'a, 'tcx> BuilderMethods<'a, 'tcx> for Builder<'a, 'tcx> {
623624
624625 fn invoke (
625626 & mut self ,
627+ llty : Self :: Type ,
626628 llfn : Self :: Value ,
627629 args : & [ Self :: Value ] ,
628630 then : Self :: BasicBlock ,
629631 _catch : Self :: BasicBlock ,
630632 funclet : Option < & Self :: Funclet > ,
631633 ) -> Self :: Value {
632634 // Exceptions don't exist, jump directly to then block
633- let result = self . call ( llfn, args, funclet) ;
635+ let result = self . call ( llty , llfn, args, funclet) ;
634636 self . emit ( ) . branch ( then) . unwrap ( ) ;
635637 result
636638 }
@@ -842,12 +844,15 @@ impl<'a, 'tcx> BuilderMethods<'a, 'tcx> for Builder<'a, 'tcx> {
842844 self . fatal ( "array alloca not supported yet" )
843845 }
844846
845- fn load ( & mut self , ptr : Self :: Value , _align : Align ) -> Self :: Value {
847+ fn load ( & mut self , ty : Self :: Type , ptr : Self :: Value , _align : Align ) -> Self :: Value {
846848 if let Some ( value) = ptr. const_fold_load ( self ) {
847849 return value;
848850 }
849851 let ty = match self . lookup_type ( ptr. ty ) {
850- SpirvType :: Pointer { pointee } => pointee,
852+ SpirvType :: Pointer { pointee } => {
853+ assert_ty_eq ! ( self , ty, pointee) ;
854+ pointee
855+ }
851856 ty => self . fatal ( & format ! (
852857 "load called on variable that wasn't a pointer: {:?}" ,
853858 ty
@@ -859,16 +864,25 @@ impl<'a, 'tcx> BuilderMethods<'a, 'tcx> for Builder<'a, 'tcx> {
859864 . with_type ( ty)
860865 }
861866
862- fn volatile_load ( & mut self , ptr : Self :: Value ) -> Self :: Value {
867+ fn volatile_load ( & mut self , ty : Self :: Type , ptr : Self :: Value ) -> Self :: Value {
863868 // TODO: Implement this
864- let result = self . load ( ptr, Align :: from_bytes ( 0 ) . unwrap ( ) ) ;
869+ let result = self . load ( ty , ptr, Align :: from_bytes ( 0 ) . unwrap ( ) ) ;
865870 self . zombie ( result. def ( self ) , "volatile load is not supported yet" ) ;
866871 result
867872 }
868873
869- fn atomic_load ( & mut self , ptr : Self :: Value , order : AtomicOrdering , _size : Size ) -> Self :: Value {
874+ fn atomic_load (
875+ & mut self ,
876+ ty : Self :: Type ,
877+ ptr : Self :: Value ,
878+ order : AtomicOrdering ,
879+ _size : Size ,
880+ ) -> Self :: Value {
870881 let ty = match self . lookup_type ( ptr. ty ) {
871- SpirvType :: Pointer { pointee } => pointee,
882+ SpirvType :: Pointer { pointee } => {
883+ assert_ty_eq ! ( self , ty, pointee) ;
884+ pointee
885+ }
872886 ty => self . fatal ( & format ! (
873887 "atomic_load called on variable that wasn't a pointer: {:?}" ,
874888 ty
@@ -903,14 +917,23 @@ impl<'a, 'tcx> BuilderMethods<'a, 'tcx> for Builder<'a, 'tcx> {
903917 let val = if let Some ( llextra) = place. llextra {
904918 OperandValue :: Ref ( place. llval , Some ( llextra) , place. align )
905919 } else if self . cx . is_backend_immediate ( place. layout ) {
906- let llval = self . load ( place. llval , place. align ) ;
920+ let llval = self . load (
921+ place. layout . spirv_type ( self . span ( ) , self ) ,
922+ place. llval ,
923+ place. align ,
924+ ) ;
907925 OperandValue :: Immediate ( self . to_immediate ( llval, place. layout ) )
908926 } else if let Abi :: ScalarPair ( ref a, ref b) = place. layout . abi {
909927 let b_offset = a. value . size ( self ) . align_to ( b. value . align ( self ) . abi ) ;
910928
929+ let pair_ty = place. layout . spirv_type ( self . span ( ) , self ) ;
911930 let mut load = |i, scalar : & Scalar , align| {
912- let llptr = self . struct_gep ( place. llval , i as u64 ) ;
913- let load = self . load ( llptr, align) ;
931+ let llptr = self . struct_gep ( pair_ty, place. llval , i as u64 ) ;
932+ let load = self . load (
933+ self . scalar_pair_element_backend_type ( place. layout , i, false ) ,
934+ llptr,
935+ align,
936+ ) ;
914937 // WARN! This does not go through to_immediate due to only having a Scalar, not a Ty, but it still does
915938 // whatever to_immediate does!
916939 if scalar. is_bool ( ) {
@@ -943,12 +966,12 @@ impl<'a, 'tcx> BuilderMethods<'a, 'tcx> for Builder<'a, 'tcx> {
943966 let zero = self . const_usize ( 0 ) ;
944967 let start = dest. project_index ( & mut self , zero) . llval ;
945968
946- let align = dest
947- . align
948- . restrict_for_offset ( dest. layout . field ( self . cx ( ) , 0 ) . size ) ;
969+ let elem_layout = dest. layout . field ( self . cx ( ) , 0 ) ;
970+ let elem_ty = elem_layout . spirv_type ( self . span ( ) , & self ) ;
971+ let align = dest. align . restrict_for_offset ( elem_layout . size ) ;
949972
950973 for i in 0 ..count {
951- let current = self . inbounds_gep ( start, & [ self . const_usize ( i) ] ) ;
974+ let current = self . inbounds_gep ( elem_ty , start, & [ self . const_usize ( i) ] ) ;
952975 cg_elem. val . store (
953976 & mut self ,
954977 PlaceRef :: new_sized_aligned ( current, cg_elem. layout , align) ,
@@ -1026,17 +1049,25 @@ impl<'a, 'tcx> BuilderMethods<'a, 'tcx> for Builder<'a, 'tcx> {
10261049 . unwrap ( ) ;
10271050 }
10281051
1029- fn gep ( & mut self , ptr : Self :: Value , indices : & [ Self :: Value ] ) -> Self :: Value {
1030- self . gep_help ( ptr, indices, false )
1052+ fn gep ( & mut self , ty : Self :: Type , ptr : Self :: Value , indices : & [ Self :: Value ] ) -> Self :: Value {
1053+ self . gep_help ( ty , ptr, indices, false )
10311054 }
10321055
1033- fn inbounds_gep ( & mut self , ptr : Self :: Value , indices : & [ Self :: Value ] ) -> Self :: Value {
1034- self . gep_help ( ptr, indices, true )
1056+ fn inbounds_gep (
1057+ & mut self ,
1058+ ty : Self :: Type ,
1059+ ptr : Self :: Value ,
1060+ indices : & [ Self :: Value ] ,
1061+ ) -> Self :: Value {
1062+ self . gep_help ( ty, ptr, indices, true )
10351063 }
10361064
1037- fn struct_gep ( & mut self , ptr : Self :: Value , idx : u64 ) -> Self :: Value {
1065+ fn struct_gep ( & mut self , ty : Self :: Type , ptr : Self :: Value , idx : u64 ) -> Self :: Value {
10381066 let pointee = match self . lookup_type ( ptr. ty ) {
1039- SpirvType :: Pointer { pointee } => pointee,
1067+ SpirvType :: Pointer { pointee } => {
1068+ assert_ty_eq ! ( self , ty, pointee) ;
1069+ pointee
1070+ }
10401071 other => self . fatal ( & format ! (
10411072 "struct_gep not on pointer type: {:?}, index {}" ,
10421073 other, idx
@@ -2087,6 +2118,7 @@ impl<'a, 'tcx> BuilderMethods<'a, 'tcx> for Builder<'a, 'tcx> {
20872118
20882119 fn call (
20892120 & mut self ,
2121+ callee_ty : Self :: Type ,
20902122 callee : Self :: Value ,
20912123 args : & [ Self :: Value ] ,
20922124 funclet : Option < & Self :: Funclet > ,
@@ -2104,15 +2136,21 @@ impl<'a, 'tcx> BuilderMethods<'a, 'tcx> for Builder<'a, 'tcx> {
21042136 SpirvType :: Function {
21052137 return_type,
21062138 arguments,
2107- } => ( callee. def ( self ) , return_type, arguments) ,
2139+ } => {
2140+ assert_ty_eq ! ( self , callee_ty, callee. ty) ;
2141+ ( callee. def ( self ) , return_type, arguments)
2142+ }
21082143
21092144 SpirvType :: Pointer { pointee } => match self . lookup_type ( pointee) {
21102145 SpirvType :: Function {
21112146 return_type,
21122147 arguments,
21132148 } => (
21142149 match callee. kind {
2115- SpirvValueKind :: FnAddr { function } => function,
2150+ SpirvValueKind :: FnAddr { function } => {
2151+ assert_ty_eq ! ( self , callee_ty, pointee) ;
2152+ function
2153+ }
21162154
21172155 // Truly indirect call.
21182156 _ => {
0 commit comments