@@ -1144,6 +1144,52 @@ void emitter::emitInsSanityCheck(instrDesc* id)
1144
1144
assert(isValidUimm4From1(emitGetInsSC(id)));
1145
1145
break;
1146
1146
1147
+ case IF_SVE_CE_2A: // ................ ......nnnnn.DDDD -- SVE move predicate from vector
1148
+ assert(isPredicateRegister(id->idReg1())); // DDDD
1149
+ assert(isVectorRegister(id->idReg2())); // nnnnn
1150
+ break;
1151
+
1152
+ case IF_SVE_CE_2B: // .........i...ii. ......nnnnn.DDDD -- SVE move predicate from vector
1153
+ assert(isPredicateRegister(id->idReg1())); // DDDD
1154
+ assert(isVectorRegister(id->idReg2())); // nnnnn
1155
+ assert(isValidUimm<3>(emitGetInsSC(id)));
1156
+ break;
1157
+
1158
+ case IF_SVE_CE_2C: // ..............i. ......nnnnn.DDDD -- SVE move predicate from vector
1159
+ assert(isPredicateRegister(id->idReg1())); // DDDD
1160
+ assert(isVectorRegister(id->idReg2())); // nnnnn
1161
+ assert(isValidUimm<1>(emitGetInsSC(id))); // i
1162
+ break;
1163
+
1164
+ case IF_SVE_CE_2D: // .............ii. ......nnnnn.DDDD -- SVE move predicate from vector
1165
+ assert(isPredicateRegister(id->idReg1())); // DDDD
1166
+ assert(isVectorRegister(id->idReg2())); // nnnnn
1167
+ assert(isValidUimm<3>(emitGetInsSC(id))); // ii
1168
+ break;
1169
+
1170
+ case IF_SVE_CF_2A: // ................ .......NNNNddddd -- SVE move predicate into vector
1171
+ assert(isVectorRegister(id->idReg1())); // ddddd
1172
+ assert(isPredicateRegister(id->idReg2())); // NNNN
1173
+ break;
1174
+
1175
+ case IF_SVE_CF_2B: // .........i...ii. .......NNNNddddd -- SVE move predicate into vector
1176
+ assert(isVectorRegister(id->idReg1())); // ddddd
1177
+ assert(isPredicateRegister(id->idReg2())); // NNNN
1178
+ assert(isValidUimm<3>(emitGetInsSC(id)));
1179
+ break;
1180
+
1181
+ case IF_SVE_CF_2C: // ..............i. .......NNNNddddd -- SVE move predicate into vector
1182
+ assert(isVectorRegister(id->idReg1())); // ddddd
1183
+ assert(isPredicateRegister(id->idReg2())); // NNNN
1184
+ assert(isValidUimm<1>(emitGetInsSC(id))); // i
1185
+ break;
1186
+
1187
+ case IF_SVE_CF_2D: // .............ii. .......NNNNddddd -- SVE move predicate into vector
1188
+ assert(isVectorRegister(id->idReg1())); // ddddd
1189
+ assert(isPredicateRegister(id->idReg2())); // NNNN
1190
+ assert(isValidUimm<2>(emitGetInsSC(id))); // ii
1191
+ break;
1192
+
1147
1193
case IF_SVE_CI_3A: // ........xx..MMMM .......NNNN.DDDD -- SVE permute predicate elements
1148
1194
elemsize = id->idOpSize();
1149
1195
assert(insOptsScalableStandard(id->idInsOpt()));
@@ -8775,6 +8821,30 @@ void emitter::emitIns_R_R(instruction ins,
8775
8821
}
8776
8822
break;
8777
8823
8824
+ case INS_sve_pmov:
8825
+ if (opt != INS_OPTS_SCALABLE_B)
8826
+ {
8827
+ assert(insOptsScalableStandard(opt));
8828
+ return emitIns_R_R_I(INS_sve_pmov, attr, reg1, reg2, 0, opt, sopt);
8829
+ }
8830
+ if (sopt == INS_SCALABLE_OPTS_TO_PREDICATE)
8831
+ {
8832
+ assert(isPredicateRegister(reg1));
8833
+ assert(isVectorRegister(reg2));
8834
+ fmt = IF_SVE_CE_2A;
8835
+ }
8836
+ else if (sopt == INS_SCALABLE_OPTS_TO_VECTOR)
8837
+ {
8838
+ assert(isVectorRegister(reg1));
8839
+ assert(isPredicateRegister(reg2));
8840
+ fmt = IF_SVE_CF_2A;
8841
+ }
8842
+ else
8843
+ {
8844
+ assert(!"invalid instruction");
8845
+ }
8846
+ break;
8847
+
8778
8848
case INS_sve_movs:
8779
8849
{
8780
8850
assert(opt == INS_OPTS_SCALABLE_B);
@@ -9817,6 +9887,57 @@ void emitter::emitIns_R_R_I(instruction ins,
9817
9887
fmt = IF_SVE_BB_2A;
9818
9888
break;
9819
9889
9890
+ case INS_sve_pmov:
9891
+ if (sopt == INS_SCALABLE_OPTS_TO_PREDICATE)
9892
+ {
9893
+ assert(isPredicateRegister(reg1));
9894
+ assert(isVectorRegister(reg2));
9895
+ switch (opt)
9896
+ {
9897
+ case INS_OPTS_SCALABLE_D:
9898
+ assert(isValidUimm<3>(imm));
9899
+ fmt = IF_SVE_CE_2B;
9900
+ break;
9901
+ case INS_OPTS_SCALABLE_S:
9902
+ assert(isValidUimm<2>(imm));
9903
+ fmt = IF_SVE_CE_2D;
9904
+ break;
9905
+ case INS_OPTS_SCALABLE_H:
9906
+ assert(isValidUimm<1>(imm));
9907
+ fmt = IF_SVE_CE_2C;
9908
+ break;
9909
+ default:
9910
+ unreached();
9911
+ }
9912
+ }
9913
+ else if (sopt == INS_SCALABLE_OPTS_TO_VECTOR)
9914
+ {
9915
+ assert(isVectorRegister(reg1));
9916
+ assert(isPredicateRegister(reg2));
9917
+ switch (opt)
9918
+ {
9919
+ case INS_OPTS_SCALABLE_D:
9920
+ assert(isValidUimm<3>(imm));
9921
+ fmt = IF_SVE_CF_2B;
9922
+ break;
9923
+ case INS_OPTS_SCALABLE_S:
9924
+ assert(isValidUimm<2>(imm));
9925
+ fmt = IF_SVE_CF_2D;
9926
+ break;
9927
+ case INS_OPTS_SCALABLE_H:
9928
+ assert(isValidUimm<1>(imm));
9929
+ fmt = IF_SVE_CF_2C;
9930
+ break;
9931
+ default:
9932
+ unreached();
9933
+ }
9934
+ }
9935
+ else
9936
+ {
9937
+ unreached();
9938
+ }
9939
+ break;
9940
+
9820
9941
case INS_sve_sqrshrn:
9821
9942
case INS_sve_sqrshrun:
9822
9943
case INS_sve_uqrshrn:
@@ -19596,6 +19717,10 @@ void emitter::emitIns_Call(EmitCallType callType,
19596
19717
19597
19718
case IF_SVE_CZ_4A_A:
19598
19719
case IF_SVE_CZ_4A_L:
19720
+ case IF_SVE_CE_2A:
19721
+ case IF_SVE_CE_2B:
19722
+ case IF_SVE_CE_2C:
19723
+ case IF_SVE_CE_2D:
19599
19724
case IF_SVE_CF_2A:
19600
19725
case IF_SVE_CF_2B:
19601
19726
case IF_SVE_CF_2C:
@@ -23841,6 +23966,68 @@ BYTE* emitter::emitOutput_InstrSve(BYTE* dst, instrDesc* id)
23841
23966
dst += emitOutput_Instr(dst, code);
23842
23967
break;
23843
23968
23969
+ case IF_SVE_CE_2A: // ................ ......nnnnn.DDDD -- SVE move predicate from vector
23970
+ code = emitInsCodeSve(ins, fmt);
23971
+ code |= insEncodeReg_P_3_to_0(id->idReg1()); // DDDD
23972
+ code |= insEncodeReg_V_9_to_5(id->idReg2()); // nnnnn
23973
+ dst += emitOutput_Instr(dst, code);
23974
+ break;
23975
+
23976
+ case IF_SVE_CE_2B: // .........i...ii. ......nnnnn.DDDD -- SVE move predicate from vector
23977
+ code = emitInsCodeSve(ins, fmt);
23978
+ code |= insEncodeReg_P_3_to_0(id->idReg1()); // DDDD
23979
+ code |= insEncodeReg_V_9_to_5(id->idReg2()); // nnnnn
23980
+ code |= insEncodeSplitUimm<22, 22, 18, 17>(emitGetInsSC(id)); // i...ii
23981
+ dst += emitOutput_Instr(dst, code);
23982
+ break;
23983
+
23984
+ case IF_SVE_CE_2C: // ..............i. ......nnnnn.DDDD -- SVE move predicate from vector
23985
+ code = emitInsCodeSve(ins, fmt);
23986
+ code |= insEncodeReg_P_3_to_0(id->idReg1()); // DDDD
23987
+ code |= insEncodeReg_V_9_to_5(id->idReg2()); // nnnnn
23988
+ code |= insEncodeUimm<17, 17>(emitGetInsSC(id)); // i
23989
+ dst += emitOutput_Instr(dst, code);
23990
+ break;
23991
+
23992
+ case IF_SVE_CE_2D: // .............ii. ......nnnnn.DDDD -- SVE move predicate from vector
23993
+ code = emitInsCodeSve(ins, fmt);
23994
+ code |= insEncodeReg_P_3_to_0(id->idReg1()); // DDDD
23995
+ code |= insEncodeReg_V_9_to_5(id->idReg2()); // nnnnn
23996
+ code |= insEncodeUimm<18, 17>(emitGetInsSC(id)); // ii
23997
+ dst += emitOutput_Instr(dst, code);
23998
+ break;
23999
+
24000
+ case IF_SVE_CF_2A: // ................ .......NNNNddddd -- SVE move predicate into vector
24001
+ code = emitInsCodeSve(ins, fmt);
24002
+ code |= insEncodeReg_V_4_to_0(id->idReg1()); // ddddd
24003
+ code |= insEncodeReg_P_8_to_5(id->idReg2()); // NNNN
24004
+ dst += emitOutput_Instr(dst, code);
24005
+ break;
24006
+
24007
+ case IF_SVE_CF_2B: // .........i...ii. .......NNNNddddd -- SVE move predicate into vector
24008
+ code = emitInsCodeSve(ins, fmt);
24009
+ code |= insEncodeReg_V_4_to_0(id->idReg1()); // ddddd
24010
+ code |= insEncodeReg_P_8_to_5(id->idReg2()); // NNNN
24011
+ code |= insEncodeSplitUimm<22, 22, 18, 17>(emitGetInsSC(id)); // i...ii
24012
+ dst += emitOutput_Instr(dst, code);
24013
+ break;
24014
+
24015
+ case IF_SVE_CF_2C: // ..............i. .......NNNNddddd -- SVE move predicate into vector
24016
+ code = emitInsCodeSve(ins, fmt);
24017
+ code |= insEncodeReg_V_4_to_0(id->idReg1()); // ddddd
24018
+ code |= insEncodeReg_P_8_to_5(id->idReg2()); // NNNN
24019
+ code |= insEncodeUimm<17, 17>(emitGetInsSC(id)); // i
24020
+ dst += emitOutput_Instr(dst, code);
24021
+ break;
24022
+
24023
+ case IF_SVE_CF_2D: // .............ii. .......NNNNddddd -- SVE move predicate into vector
24024
+ code = emitInsCodeSve(ins, fmt);
24025
+ code |= insEncodeReg_V_4_to_0(id->idReg1()); // ddddd
24026
+ code |= insEncodeReg_P_8_to_5(id->idReg2()); // NNNN
24027
+ code |= insEncodeUimm<18, 17>(emitGetInsSC(id)); // ii
24028
+ dst += emitOutput_Instr(dst, code);
24029
+ break;
24030
+
23844
24031
case IF_SVE_CI_3A: // ........xx..MMMM .......NNNN.DDDD -- SVE permute predicate elements
23845
24032
code = emitInsCodeSve(ins, fmt);
23846
24033
code |= insEncodeReg_P_3_to_0(id->idReg1()); // DDDD
@@ -25733,6 +25920,18 @@ void emitter::emitDispReg(regNumber reg, emitAttr attr, bool addComma)
25733
25920
emitDispComma();
25734
25921
}
25735
25922
25923
+ //------------------------------------------------------------------------
25924
+ // emitDispSveReg: Display a scalable vector register name
25925
+ //
25926
+ void emitter::emitDispSveReg(regNumber reg, bool addComma)
25927
+ {
25928
+ assert(isVectorRegister(reg));
25929
+ printf(emitSveRegName(reg));
25930
+
25931
+ if (addComma)
25932
+ emitDispComma();
25933
+ }
25934
+
25736
25935
//------------------------------------------------------------------------
25737
25936
// emitDispSveReg: Display a scalable vector register name with an arrangement suffix
25738
25937
//
@@ -25751,6 +25950,16 @@ void emitter::emitDispSveReg(regNumber reg, insOpts opt, bool addComma)
25751
25950
emitDispComma();
25752
25951
}
25753
25952
25953
+ //------------------------------------------------------------------------
25954
+ // emitDispSveRegIndex: Display a scalable vector register with indexed element
25955
+ //
25956
+ void emitter::emitDispSveRegIndex(regNumber reg, ssize_t index, bool addComma)
25957
+ {
25958
+ assert(isVectorRegister(reg));
25959
+ printf(emitSveRegName(reg));
25960
+ emitDispElementIndex(index, addComma);
25961
+ }
25962
+
25754
25963
//------------------------------------------------------------------------
25755
25964
// emitDispVectorReg: Display a SIMD vector register name with an arrangement suffix
25756
25965
//
@@ -27947,6 +28156,39 @@ void emitter::emitDispInsHelp(
27947
28156
emitDispSveReg(id->idReg3(), id->idInsOpt(), false); // mmmmm
27948
28157
break;
27949
28158
28159
+ case IF_SVE_CE_2A: // ................ ......nnnnn.DDDD -- SVE move predicate from vector
28160
+ emitDispPredicateReg(id->idReg1(), insGetPredicateType(fmt), INS_OPTS_SCALABLE_B, true); // DDDD
28161
+ emitDispSveReg(id->idReg2(), false); // nnnnn
28162
+ break;
28163
+ case IF_SVE_CE_2B: // .........i...ii. ......nnnnn.DDDD -- SVE move predicate from vector
28164
+ emitDispPredicateReg(id->idReg1(), insGetPredicateType(fmt), INS_OPTS_SCALABLE_D, true); // DDDD
28165
+ emitDispSveRegIndex(id->idReg2(), emitGetInsSC(id), false); // nnnnn
28166
+ break;
28167
+ case IF_SVE_CE_2C: // ..............i. ......nnnnn.DDDD -- SVE move predicate from vector
28168
+ emitDispPredicateReg(id->idReg1(), insGetPredicateType(fmt), INS_OPTS_SCALABLE_H, true); // DDDD
28169
+ emitDispSveRegIndex(id->idReg2(), emitGetInsSC(id), false); // nnnnn
28170
+ break;
28171
+ case IF_SVE_CE_2D: // .............ii. ......nnnnn.DDDD -- SVE move predicate from vector
28172
+ emitDispPredicateReg(id->idReg1(), insGetPredicateType(fmt), INS_OPTS_SCALABLE_S, true); // DDDD
28173
+ emitDispSveRegIndex(id->idReg2(), emitGetInsSC(id), false); // nnnnn
28174
+ break;
28175
+ case IF_SVE_CF_2A: // ................ .......NNNNddddd -- SVE move predicate into vector
28176
+ emitDispSveReg(id->idReg1(), true); // ddddd
28177
+ emitDispPredicateReg(id->idReg2(), insGetPredicateType(fmt), INS_OPTS_SCALABLE_B, false); // NNNN
28178
+ break;
28179
+ case IF_SVE_CF_2B: // .........i...ii. .......NNNNddddd -- SVE move predicate into vector
28180
+ emitDispSveRegIndex(id->idReg1(), emitGetInsSC(id), true); // ddddd
28181
+ emitDispPredicateReg(id->idReg2(), insGetPredicateType(fmt), INS_OPTS_SCALABLE_D, false); // NNNN
28182
+ break;
28183
+ case IF_SVE_CF_2C: // ..............i. .......NNNNddddd -- SVE move predicate into vector
28184
+ emitDispSveRegIndex(id->idReg1(), emitGetInsSC(id), true); // ddddd
28185
+ emitDispPredicateReg(id->idReg2(), insGetPredicateType(fmt), INS_OPTS_SCALABLE_H, false); // NNNN
28186
+ break;
28187
+ case IF_SVE_CF_2D: // .............ii. .......NNNNddddd -- SVE move predicate into vector
28188
+ emitDispSveRegIndex(id->idReg1(), emitGetInsSC(id), true); // ddddd
28189
+ emitDispPredicateReg(id->idReg2(), insGetPredicateType(fmt), INS_OPTS_SCALABLE_S, false); // NNNN
28190
+ break;
28191
+
27950
28192
// <Pd>.<T>, <Pn>.<T>, <Pm>.<T>
27951
28193
case IF_SVE_CI_3A: // ........xx..MMMM .......NNNN.DDDD -- SVE permute predicate elements
27952
28194
emitDispPredicateReg(id->idReg1(), insGetPredicateType(fmt, 1), id->idInsOpt(), true); // DDDD
@@ -31763,6 +32005,18 @@ emitter::insExecutionCharacteristics emitter::getInsExecutionCharacteristics(ins
31763
32005
result.insLatency = PERFSCORE_LATENCY_2C;
31764
32006
break;
31765
32007
32008
+ case IF_SVE_CE_2A: // ................ ......nnnnn.DDDD -- SVE move predicate from vector
32009
+ case IF_SVE_CE_2B: // .........i...ii. ......nnnnn.DDDD -- SVE move predicate from vector
32010
+ case IF_SVE_CE_2C: // ..............i. ......nnnnn.DDDD -- SVE move predicate from vector
32011
+ case IF_SVE_CE_2D: // .............ii. ......nnnnn.DDDD -- SVE move predicate from vector
32012
+ case IF_SVE_CF_2A: // ................ .......NNNNddddd -- SVE move predicate into vector
32013
+ case IF_SVE_CF_2B: // .........i...ii. .......NNNNddddd -- SVE move predicate into vector
32014
+ case IF_SVE_CF_2C: // ..............i. .......NNNNddddd -- SVE move predicate into vector
32015
+ case IF_SVE_CF_2D: // .............ii. .......NNNNddddd -- SVE move predicate into vector
32016
+ result.insThroughput = PERFSCORE_THROUGHPUT_140C; // @ToDo currently undocumented
32017
+ result.insLatency = PERFSCORE_LATENCY_140C;
32018
+ break;
32019
+
31766
32020
case IF_SVE_CI_3A: // ........xx..MMMM .......NNNN.DDDD -- SVE permute predicate elements
31767
32021
case IF_SVE_CJ_2A: // ........xx...... .......NNNN.DDDD -- SVE reverse predicate elements
31768
32022
case IF_SVE_CK_2A: // ................ .......NNNN.DDDD -- SVE unpack predicate elements
0 commit comments