return str;
}
+static char *
+svp64_decode_all (char *str, struct svp64_ctx *svp64)
+{
+ str += (sizeof ("all") - 1);
+ if ( ! ISSPACE (*str) && *str != SVP64_SEP && *str != '\0')
+ return NULL;
+
+ svp64_insn_set_prefix_rm_branch_ALL (&svp64->insn, 1);
+
+ *str++ = '\0';
+
+ return str;
+}
+
+static char *
+svp64_decode_snz (char *str, struct svp64_ctx *svp64)
+{
+ str += (sizeof ("snz") - 1);
+ if ( ! ISSPACE (*str) && *str != SVP64_SEP && *str != '\0')
+ return NULL;
+
+ svp64_insn_set_prefix_rm_branch_SNZ (&svp64->insn, 1);
+
+ *str++ = '\0';
+
+ return str;
+}
+
+static char *
+svp64_decode_sl (char *str, struct svp64_ctx *svp64)
+{
+ str += (sizeof ("sl") - 1);
+ if ( ! ISSPACE (*str) && *str != SVP64_SEP && *str != '\0')
+ return NULL;
+
+ svp64_insn_set_prefix_rm_branch_SL (&svp64->insn, 1);
+
+ *str++ = '\0';
+
+ return str;
+}
+
+static char *
+svp64_decode_slu (char *str, struct svp64_ctx *svp64)
+{
+ str += (sizeof ("slu") - 1);
+ if ( ! ISSPACE (*str) && *str != SVP64_SEP && *str != '\0')
+ return NULL;
+
+ svp64_insn_set_prefix_rm_branch_SLu (&svp64->insn, 1);
+
+ *str++ = '\0';
+
+ return str;
+}
+
+static char *
+svp64_decode_lru (char *str, struct svp64_ctx *svp64)
+{
+ str += (sizeof ("lru") - 1);
+ if ( ! ISSPACE (*str) && *str != SVP64_SEP && *str != '\0')
+ return NULL;
+
+ svp64_insn_set_prefix_rm_branch_LRu (&svp64->insn, 1);
+
+ *str++ = '\0';
+
+ return str;
+}
+
+static char *
+svp64_decode_vs (char *str, struct svp64_ctx *svp64)
+{
+ str += (sizeof ("vs") - 1);
+ if ( ! ISSPACE (*str) && *str != SVP64_SEP && *str != '\0')
+ return NULL;
+
+ svp64_insn_set_prefix_rm_branch_vls_VSb (&svp64->insn, 0);
+ svp64_insn_set_prefix_rm_branch_vls_VLi (&svp64->insn, 0);
+
+ *str++ = '\0';
+
+ return str;
+}
+
+static char *
+svp64_decode_vsi (char *str, struct svp64_ctx *svp64)
+{
+ str += (sizeof ("vsi") - 1);
+ if ( ! ISSPACE (*str) && *str != SVP64_SEP && *str != '\0')
+ return NULL;
+
+ svp64_insn_set_prefix_rm_branch_vls_VSb (&svp64->insn, 0);
+ svp64_insn_set_prefix_rm_branch_vls_VLi (&svp64->insn, 1);
+
+ *str++ = '\0';
+
+ return str;
+}
+
+static char *
+svp64_decode_vsb (char *str, struct svp64_ctx *svp64)
+{
+ str += (sizeof ("vsb") - 1);
+ if ( ! ISSPACE (*str) && *str != SVP64_SEP && *str != '\0')
+ return NULL;
+
+ svp64_insn_set_prefix_rm_branch_vls_VSb (&svp64->insn, 1);
+ svp64_insn_set_prefix_rm_branch_vls_VLi (&svp64->insn, 0);
+
+ *str++ = '\0';
+
+ return str;
+}
+
+static char *
+svp64_decode_vsbi (char *str, struct svp64_ctx *svp64)
+{
+ str += (sizeof ("vsbi") - 1);
+ if ( ! ISSPACE (*str) && *str != SVP64_SEP && *str != '\0')
+ return NULL;
+
+ svp64_insn_set_prefix_rm_branch_vls_VSb (&svp64->insn, 1);
+ svp64_insn_set_prefix_rm_branch_vls_VLi (&svp64->insn, 1);
+
+ *str++ = '\0';
+
+ return str;
+}
+
+static char *
+svp64_decode_vli (char *str, struct svp64_ctx *svp64)
+{
+ str += (sizeof ("vli") - 1);
+ if ( ! ISSPACE (*str) && *str != SVP64_SEP && *str != '\0')
+ return NULL;
+
+ svp64_insn_set_prefix_rm_branch_vls_VLi (&svp64->insn, 1);
+
+ *str++ = '\0';
+
+ return str;
+}
+
+static char *
+svp64_decode_ctr (char *str, struct svp64_ctx *svp64)
+{
+ str += (sizeof ("ctr") - 1);
+ if ( ! ISSPACE (*str) && *str != SVP64_SEP && *str != '\0')
+ return NULL;
+
+ svp64_insn_set_prefix_rm_branch_ctr_CTR (&svp64->insn, 1);
+
+ *str++ = '\0';
+
+ return str;
+}
+
+static char *
+svp64_decode_cti (char *str, struct svp64_ctx *svp64)
+{
+ str += (sizeof ("cti") - 1);
+ if ( ! ISSPACE (*str) && *str != SVP64_SEP && *str != '\0')
+ return NULL;
+
+ svp64_insn_set_prefix_rm_branch_ctr_CTR (&svp64->insn, 1);
+ svp64_insn_set_prefix_rm_branch_ctr_CTi (&svp64->insn, 1);
+
+ *str++ = '\0';
+
+ return str;
+}
+
+static char *
+svp64_decode_pi (char *str, struct svp64_ctx *svp64)
+{
+ str += (sizeof ("pi") - 1);
+ if ( ! ISSPACE (*str) && *str != SVP64_SEP && *str != '\0')
+ return NULL;
+
+ svp64_insn_set_prefix_rm_ldst_imm_post_mode (&svp64->insn, 0x4);
+ svp64_insn_set_prefix_rm_ldst_imm_post_pi (&svp64->insn, 1);
+
+ *str++ = '\0';
+
+ return str;
+}
+
+static char *
+svp64_decode_lf (char *str, struct svp64_ctx *svp64)
+{
+ uint64_t mode = svp64_insn_get_prefix_rm_ldst_imm_post_mode (&svp64->insn);
+
+ str += (sizeof ("lf") - 1);
+ if ( ! ISSPACE (*str) && *str != SVP64_SEP && *str != '\0')
+ return NULL;
+
+ svp64_insn_set_prefix_rm_ldst_imm_post_mode (&svp64->insn, (mode | 0x4));
+ svp64_insn_set_prefix_rm_ldst_imm_post_lf (&svp64->insn, 1);
+
+ *str++ = '\0';
+
+ return str;
+}
+
static char *
svp64_decode_mode (char *str, struct svp64_ctx *svp64)
{
SVP64_DECODER ("mrr" , svp64_decode_mrr),
SVP64_DECODER ("mr" , svp64_decode_mr),
SVP64_DECODER ("crm" , svp64_decode_crm),
+ SVP64_DECODER ("all" , svp64_decode_all),
+ SVP64_DECODER ("snz" , svp64_decode_snz),
+ SVP64_DECODER ("sl" , svp64_decode_sl),
+ SVP64_DECODER ("slu" , svp64_decode_slu),
+ SVP64_DECODER ("lru" , svp64_decode_lru),
+ SVP64_DECODER ("vs" , svp64_decode_vs),
+ SVP64_DECODER ("vsi" , svp64_decode_vsi),
+ SVP64_DECODER ("vsb" , svp64_decode_vsb),
+ SVP64_DECODER ("vsbi", svp64_decode_vsbi),
+ SVP64_DECODER ("vli" , svp64_decode_vli),
+ SVP64_DECODER ("ctr" , svp64_decode_ctr),
+ SVP64_DECODER ("cti" , svp64_decode_cti),
+ SVP64_DECODER ("pi" , svp64_decode_pi),
+ SVP64_DECODER ("lf" , svp64_decode_lf),
};
for (i = 0; i < sizeof (table) / sizeof (table[0]); ++i)
* Create mode and (overridden) src/dst widths.
* TODO: sanity-check BC modes.
*/
- svp64->sv_mode = ((svp64->bc_svstep << SVP64_MODE_MOD2_MSB) |
- (svp64->bc_vlset << SVP64_MODE_MOD2_LSB) |
- (svp64->bc_snz << SVP64_MODE_BC_SNZ));
- svp64->srcwid = ((svp64->bc_vsb << 1) | svp64->bc_lru);
- svp64->destwid = ((svp64->bc_lru << 1) | svp64->bc_all);
+ (void)svp64;
}
static void
}
static size_t
-svp64_spec_ldst_imm_rsvd (const struct svp64_ctx *svp64,
+svp64_spec_ldst_imm_post (const struct svp64_ctx *svp64,
struct disassemble_info *info)
{
- (void)svp64;
- (void)info;
+ size_t len = 0;
+ uint64_t pi = svp64_insn_get_prefix_rm_ldst_imm_post_pi (&svp64->insn);
+ uint64_t lf = svp64_insn_get_prefix_rm_ldst_imm_post_lf (&svp64->insn);
+
+ if (pi)
+ len += svp64_spec_printf (info, "pi");
+ if (lf)
+ len += svp64_spec_printf (info, "lf");
return 0;
}
}
static size_t
-svp64_spec_ldst_idx_sat (const struct svp64_ctx *svp64,
+svp64_spec_ldst_idx_ffrc1 (const struct svp64_ctx *svp64,
+ struct disassemble_info *info)
+{
+ size_t len = 0;
+ uint64_t N = svp64_insn_get_prefix_rm_ldst_idx_sat_N (&svp64->insn);
+ uint64_t dz = svp64_insn_get_prefix_rm_ldst_idx_sat_dz (&svp64->insn);
+ uint64_t sz = svp64_insn_get_prefix_rm_ldst_idx_sat_sz (&svp64->insn);
+
+ len += svp64_spec_sat (info, N);
+ len += svp64_spec_dz_sz_zz (info, dz, sz);
+ len += svp64_spec_ldst_idx (svp64, info);
+
+ return len;
+}
+
+static size_t
+svp64_spec_ldst_idx_ffrc0 (const struct svp64_ctx *svp64,
struct disassemble_info *info)
{
size_t len = 0;
size_t idx;
uint64_t match;
static const struct svp64_spec_subtable normal[] = {
- {0x00, 0x38, svp64_spec_normal_simple}, /* simple (no Rc) */
- {0x08, 0x38, svp64_spec_normal_mr}, /* mapreduce (no Rc) */
- {0x11, 0x31, svp64_spec_normal_ffrc1}, /* ffirst, Rc=1 */
- {0x10, 0x31, svp64_spec_normal_ffrc0}, /* ffirst, Rc=0 */
- {0x20, 0x30, svp64_spec_normal_sat}, /* saturation (no Rc) */
+ {0x00, 0x38, svp64_spec_normal_simple}, /* simple (no Rc) */
+ {0x08, 0x38, svp64_spec_normal_mr}, /* mapreduce (no Rc) */
+ {0x11, 0x31, svp64_spec_normal_ffrc1}, /* ffirst, Rc=1 */
+ {0x10, 0x31, svp64_spec_normal_ffrc0}, /* ffirst, Rc=0 */
+ {0x20, 0x30, svp64_spec_normal_sat}, /* saturation (no Rc) */
};
static const struct svp64_spec_subtable ldst_imm[] = {
- {0x00, 0x38, svp64_spec_ldst_imm_simple}, /* simple (no Rc) */
- {0x08, 0x38, svp64_spec_ldst_imm_rsvd}, /* rsvd (no Rc) */
- {0x11, 0x31, svp64_spec_ldst_imm_ffrc1}, /* ffirst, Rc=1 */
- {0x10, 0x31, svp64_spec_ldst_imm_ffrc0}, /* ffirst, Rc=0 */
- {0x20, 0x30, svp64_spec_ldst_imm_sat}, /* saturation (no Rc) */
+ {0x00, 0x38, svp64_spec_ldst_imm_simple}, /* simple (no Rc) */
+ {0x08, 0x38, svp64_spec_ldst_imm_post}, /* post (no Rc) */
+ {0x11, 0x11, svp64_spec_ldst_imm_ffrc1}, /* ffirst, Rc=1 */
+ {0x10, 0x11, svp64_spec_ldst_imm_ffrc0}, /* ffirst, Rc=0 */
+ {0x20, 0x30, svp64_spec_ldst_imm_sat}, /* saturation (no Rc) */
};
static const struct svp64_spec_subtable ldst_idx[] = {
- {0x00, 0x30, svp64_spec_ldst_idx_simple}, /* simple (no Rc) */
- {0x20, 0x30, svp64_spec_ldst_idx_sat}, /* saturation (no Rc) */
+ {0x00, 0x10, svp64_spec_ldst_idx_simple}, /* simple (no Rc) */
+ {0x11, 0x11, svp64_spec_ldst_idx_ffrc1}, /* ffirst, Rc=1 */
+ {0x10, 0x11, svp64_spec_ldst_idx_ffrc0}, /* ffirst, Rc=0 */
};
static const struct svp64_spec_subtable crop[] = {
- {0x00, 0x38, svp64_spec_crop_simple}, /* simple */
- {0x08, 0x38, svp64_spec_crop_mr}, /* mapreduce */
- {0x21, 0x21, svp64_spec_crop_ff3}, /* failfirst, 3-bit CR */
- {0x20, 0x20, svp64_spec_crop_ff5}, /* failfirst, 5-bit CR */
+ {0x00, 0x38, svp64_spec_crop_simple}, /* simple */
+ {0x08, 0x38, svp64_spec_crop_mr}, /* mapreduce */
+ {0x21, 0x21, svp64_spec_crop_ff3}, /* ffirst, 3-bit CR */
+ {0x20, 0x20, svp64_spec_crop_ff5}, /* ffirst, 5-bit CR */
};
static const struct svp64_spec_subtable branch[] = {
- {0x00, 0x03, svp64_spec_branch_simple}, /* simple */
- {0x01, 0x03, svp64_spec_branch_vls}, /* VLset */
- {0x02, 0x03, svp64_spec_branch_ctr}, /* CTR mode */
- {0x03, 0x03, svp64_spec_branch_ctrvls}, /* CTR+VLset mode */
+ {0x00, 0x03, svp64_spec_branch_simple}, /* simple */
+ {0x01, 0x03, svp64_spec_branch_vls}, /* VLset */
+ {0x02, 0x03, svp64_spec_branch_ctr}, /* CTR mode */
+ {0x03, 0x03, svp64_spec_branch_ctrvls}, /* CTR+VLset mode */
};
static const struct svp64_spec_table tables[] = {
[SVP64_MODE_NORMAL] = {normal, ARRAY_SIZE (normal)},