@@ -4472,6 +4472,96 @@ fn lower_insn_to_regs<C: LowerCtx<I = Inst>>(
44724472 }
44734473 }
44744474 }
4475+ Opcode :: ExtendedPairwiseAddSigned | Opcode :: ExtendedPairwiseAddUnsigned => {
4476+
4477+ let input_ty = ctx. input_ty ( insn, 0 ) ;
4478+ let output_ty = ctx. output_ty ( insn, 0 ) ;
4479+ let src = put_input_in_reg ( ctx, inputs[ 0 ] ) ;
4480+ let dst = get_output_reg ( ctx, outputs[ 0 ] ) . only_reg ( ) . unwrap ( ) ;
4481+
4482+ match op {
4483+ Opcode :: ExtendedPairwiseAddSigned => match ( input_ty, output_ty) {
4484+ ( types:: I8X16 , types:: I16X8 ) => {
4485+ static MUL_CONST : [ u8 ; 16 ] = [ 0x01 ; 16 ] ;
4486+ let mul_const = ctx. use_constant ( VCodeConstantData :: WellKnown ( & MUL_CONST ) ) ;
4487+ let mul_const_reg = ctx. alloc_tmp ( types:: I8X16 ) . only_reg ( ) . unwrap ( ) ;
4488+ ctx. emit ( Inst :: xmm_load_const ( mul_const, mul_const_reg, types:: I8X16 ) ) ;
4489+ ctx. emit ( Inst :: xmm_mov (
4490+ SseOpcode :: Movdqa ,
4491+ RegMem :: reg ( mul_const_reg. to_reg ( ) ) ,
4492+ dst,
4493+ ) ) ;
4494+ ctx. emit ( Inst :: xmm_rm_r ( SseOpcode :: Pmaddubsw , RegMem :: reg ( src) , dst) ) ;
4495+ eprintln ! ( "Match A!! {:?} {:?} {:?}" , op, input_ty, output_ty) ;
4496+ } ,
4497+ ( types:: I16X8 , types:: I32X4 ) => {
4498+ static MUL_CONST : [ u8 ; 16 ] = [ 0x01 , 0x00 , 0x01 , 0x00 , 0x01 , 0x00 , 0x01 , 0x00 , 0x01 , 0x00 , 0x01 , 0x00 , 0x01 , 0x00 , 0x01 , 0x00 ] ;
4499+ let mul_const = ctx. use_constant ( VCodeConstantData :: WellKnown ( & MUL_CONST ) ) ;
4500+ let mul_const_reg = ctx. alloc_tmp ( types:: I16X8 ) . only_reg ( ) . unwrap ( ) ;
4501+ ctx. emit ( Inst :: xmm_load_const ( mul_const, mul_const_reg, types:: I16X8 ) ) ;
4502+ ctx. emit ( Inst :: xmm_mov (
4503+ SseOpcode :: Movdqa ,
4504+ RegMem :: reg ( src) ,
4505+ dst,
4506+ ) ) ;
4507+ ctx. emit ( Inst :: xmm_rm_r ( SseOpcode :: Pmaddwd , RegMem :: reg ( mul_const_reg. to_reg ( ) ) , dst) ) ;
4508+ eprintln ! ( "Match B!! {:?} {:?} {:?}" , op, input_ty, output_ty) ;
4509+
4510+ } ,
4511+ _ => unreachable ! ( "Type pattern should not be possible." ) ,
4512+ } ,
4513+ Opcode :: ExtendedPairwiseAddUnsigned => match ( input_ty, output_ty) {
4514+ ( types:: I8X16 , types:: I16X8 ) => {
4515+ static MUL_CONST : [ u8 ; 16 ] = [ 0x01 ; 16 ] ;
4516+ let mul_const = ctx. use_constant ( VCodeConstantData :: WellKnown ( & MUL_CONST ) ) ;
4517+ let mul_const_reg = ctx. alloc_tmp ( types:: I8X16 ) . only_reg ( ) . unwrap ( ) ;
4518+ ctx. emit ( Inst :: xmm_load_const ( mul_const, mul_const_reg, types:: I8X16 ) ) ;
4519+ ctx. emit ( Inst :: xmm_mov (
4520+ SseOpcode :: Movdqa ,
4521+ RegMem :: reg ( src) ,
4522+ dst,
4523+ ) ) ;
4524+ ctx. emit ( Inst :: xmm_rm_r ( SseOpcode :: Pmaddubsw , RegMem :: reg ( mul_const_reg. to_reg ( ) ) , dst) ) ;
4525+ println ! ( "Match C!! {:?} {:?} {:?}" , op, input_ty, output_ty) ;
4526+ } ,
4527+ ( types:: I16X8 , types:: I32X4 ) => {
4528+ //static PXOR_CONST: [u8; 16] = [0x80, 0x00, 0x80, 0x00, 0x80, 0x00, 0x80, 0x00, 0x80, 0x00, 0x80, 0x00, 0x80, 0x00, 0x80, 0x00];
4529+ static PXOR_CONST : [ u8 ; 16 ] = [ 0x00 , 0x80 , 0x00 , 0x80 , 0x00 , 0x80 , 0x00 , 0x80 , 0x00 , 0x80 , 0x00 , 0x80 , 0x00 , 0x80 , 0x00 , 0x80 ] ;
4530+ let pxor_const = ctx. use_constant ( VCodeConstantData :: WellKnown ( & PXOR_CONST ) ) ;
4531+ let pxor_const_reg = ctx. alloc_tmp ( types:: I16X8 ) . only_reg ( ) . unwrap ( ) ;
4532+ ctx. emit ( Inst :: xmm_load_const ( pxor_const, pxor_const_reg, types:: I16X8 ) ) ;
4533+ ctx. emit ( Inst :: xmm_mov (
4534+ SseOpcode :: Movdqa ,
4535+ RegMem :: reg ( src) ,
4536+ dst,
4537+ ) ) ;
4538+ ctx. emit ( Inst :: xmm_rm_r ( SseOpcode :: Pxor , RegMem :: reg ( pxor_const_reg. to_reg ( ) ) , dst) ) ;
4539+
4540+
4541+ //static MADD_CONST: [u8; 16] = [0x01; 16];
4542+ static MADD_CONST : [ u8 ; 16 ] = [ 0x01 , 0x00 , 0x01 , 0x00 , 0x01 , 0x00 , 0x01 , 0x00 , 0x01 , 0x00 , 0x01 , 0x00 , 0x01 , 0x00 , 0x01 , 0x00 ] ;
4543+ let madd_const = ctx. use_constant ( VCodeConstantData :: WellKnown ( & MADD_CONST ) ) ;
4544+ let madd_const_reg = ctx. alloc_tmp ( types:: I8X16 ) . only_reg ( ) . unwrap ( ) ;
4545+ ctx. emit ( Inst :: xmm_load_const ( madd_const, madd_const_reg, types:: I16X8 ) ) ;
4546+ ctx. emit ( Inst :: xmm_rm_r ( SseOpcode :: Pmaddwd , RegMem :: reg ( madd_const_reg. to_reg ( ) ) , dst) ) ;
4547+
4548+
4549+ //static ADDD_CONST2: [u8; 16] = [0x00, 0x01, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00];
4550+ static ADDD_CONST2 : [ u8 ; 16 ] = [ 0x00 , 0x00 , 0x01 , 0x00 , 0x00 , 0x00 , 0x01 , 0x00 , 0x00 , 0x00 , 0x01 , 0x00 , 0x00 , 0x00 , 0x01 , 0x00 ] ;
4551+ let addd_const2 = ctx. use_constant ( VCodeConstantData :: WellKnown ( & ADDD_CONST2 ) ) ;
4552+ let addd_const2_reg = ctx. alloc_tmp ( types:: I8X16 ) . only_reg ( ) . unwrap ( ) ;
4553+ ctx. emit ( Inst :: xmm_load_const ( addd_const2, addd_const2_reg, types:: I16X8 ) ) ;
4554+ ctx. emit ( Inst :: xmm_rm_r ( SseOpcode :: Paddd , RegMem :: reg ( addd_const2_reg. to_reg ( ) ) , dst) ) ;
4555+
4556+
4557+ eprintln ! ( "Match D!! {:?} {:?} {:?}" , op, input_ty, output_ty) ;
4558+
4559+ } ,
4560+ _ => unreachable ! ( "Type pattern should not be possible." ) ,
4561+ } ,
4562+ _ => unreachable ! ( "Opcode should not be possible." ) ,
4563+ }
4564+ }
44754565 Opcode :: UwidenHigh | Opcode :: UwidenLow | Opcode :: SwidenHigh | Opcode :: SwidenLow => {
44764566 let input_ty = ctx. input_ty ( insn, 0 ) ;
44774567 let output_ty = ctx. output_ty ( insn, 0 ) ;
0 commit comments