@@ -105,7 +105,6 @@ fn emit_aapcs_va_arg(
105105 let mut end = bx. build_sibling_block ( "va_arg.end" ) ;
106106 let zero = bx. const_i32 ( 0 ) ;
107107 let offset_align = Align :: from_bytes ( 4 ) . unwrap ( ) ;
108- assert_eq ! ( bx. tcx( ) . sess. target. endian, Endian :: Little ) ;
109108
110109 let gr_type = target_ty. is_any_ptr ( ) || target_ty. is_integral ( ) ;
111110 let ( reg_off, reg_top_index, slot_size) = if gr_type {
@@ -144,9 +143,14 @@ fn emit_aapcs_va_arg(
144143 let top = in_reg. load ( top, bx. tcx ( ) . data_layout . pointer_align . abi ) ;
145144
146145 // reg_value = *(@top + reg_off_v);
147- let top = in_reg. gep ( top, & [ reg_off_v] ) ;
148- let top = in_reg. bitcast ( top, bx. cx . type_ptr_to ( layout. llvm_type ( bx) ) ) ;
149- let reg_value = in_reg. load ( top, layout. align . abi ) ;
146+ let mut reg_addr = in_reg. gep ( top, & [ reg_off_v] ) ;
147+ if bx. tcx ( ) . sess . target . endian == Endian :: Big && layout. size . bytes ( ) != slot_size {
148+ // On big-endian systems the value is right-aligned in its slot.
149+ let offset = bx. const_i32 ( ( slot_size - layout. size . bytes ( ) ) as i32 ) ;
150+ reg_addr = in_reg. gep ( reg_addr, & [ offset] ) ;
151+ }
152+ let reg_addr = in_reg. bitcast ( reg_addr, bx. cx . type_ptr_to ( layout. llvm_type ( bx) ) ) ;
153+ let reg_value = in_reg. load ( reg_addr, layout. align . abi ) ;
150154 in_reg. br ( & end. llbb ( ) ) ;
151155
152156 // On Stack block
0 commit comments