aboutsummaryrefslogtreecommitdiff
path: root/target
diff options
context:
space:
mode:
authorDavid Hildenbrand <david@redhat.com>2018-09-27 15:02:58 +0200
committerCornelia Huck <cohuck@redhat.com>2018-10-04 10:32:39 +0200
commit82d179336dd696d04495963ca007fa961496d924 (patch)
tree1b85a9a352ccabfb12eee1312b480bda7ca307ea /target
parent13054739b5838c7ef9d2e6e88a68bbf914d63bfa (diff)
s390x/tcg: support flags for instructions
Storing flags for instructions allows us to efficiently verify certain properties at a central point. Examples might later be handling if AFP is disabled in CR0, we are not in problem state, or if vector instructions are disabled in CR0. Reviewed-by: Richard Henderson <richard.henderson@linaro.org> Reviewed-by: Thomas Huth <thuth@redhat.com> Signed-off-by: David Hildenbrand <david@redhat.com> Message-Id: <20180927130303.12236-5-david@redhat.com> Signed-off-by: Cornelia Huck <cohuck@redhat.com>
Diffstat (limited to 'target')
-rw-r--r--target/s390x/insn-data.def3
-rw-r--r--target/s390x/translate.c22
2 files changed, 19 insertions, 6 deletions
diff --git a/target/s390x/insn-data.def b/target/s390x/insn-data.def
index 9c7b434fca..7ab28b7f2d 100644
--- a/target/s390x/insn-data.def
+++ b/target/s390x/insn-data.def
@@ -3,6 +3,8 @@
*
* C(OPC, NAME, FMT, FAC, I1, I2, P, W, OP, CC)
* D(OPC, NAME, FMT, FAC, I1, I2, P, W, OP, CC, DATA)
+ * E(OPC, NAME, FMT, FAC, I1, I2, P, W, OP, CC, DATA, FLAGS)
+ * F(OPC, NAME, FMT, FAC, I1, I2, P, W, OP, CC, FLAGS)
*
* OPC = (op << 8) | op2 where op is the major, op2 the minor opcode
* NAME = name of the opcode, used internally
@@ -15,6 +17,7 @@
* OP = func op_xx does the bulk of the operation
* CC = func cout_xx defines how cc should get set
* DATA = immediate argument to op_xx function
+ * FLAGS = categorize the type of instruction (e.g. for advanced checks)
*
* The helpers get called in order: I1, I2, P, OP, W, CC
*/
diff --git a/target/s390x/translate.c b/target/s390x/translate.c
index 43b736335f..146a817ce2 100644
--- a/target/s390x/translate.c
+++ b/target/s390x/translate.c
@@ -1121,6 +1121,7 @@ typedef struct {
struct DisasInsn {
unsigned opc:16;
+ unsigned flags:16;
DisasFormat fmt:8;
unsigned fac:8;
unsigned spec:8;
@@ -5835,17 +5836,24 @@ static void in2_insn(DisasContext *s, DisasFields *f, DisasOps *o)
search tree, rather than us having to post-process the table. */
#define C(OPC, NM, FT, FC, I1, I2, P, W, OP, CC) \
- D(OPC, NM, FT, FC, I1, I2, P, W, OP, CC, 0)
+ E(OPC, NM, FT, FC, I1, I2, P, W, OP, CC, 0, 0)
-#define D(OPC, NM, FT, FC, I1, I2, P, W, OP, CC, D) insn_ ## NM,
+#define D(OPC, NM, FT, FC, I1, I2, P, W, OP, CC, D) \
+ E(OPC, NM, FT, FC, I1, I2, P, W, OP, CC, D, 0)
+
+#define F(OPC, NM, FT, FC, I1, I2, P, W, OP, CC, FL) \
+ E(OPC, NM, FT, FC, I1, I2, P, W, OP, CC, 0, FL)
+
+#define E(OPC, NM, FT, FC, I1, I2, P, W, OP, CC, D, FL) insn_ ## NM,
enum DisasInsnEnum {
#include "insn-data.def"
};
-#undef D
-#define D(OPC, NM, FT, FC, I1, I2, P, W, OP, CC, D) { \
+#undef E
+#define E(OPC, NM, FT, FC, I1, I2, P, W, OP, CC, D, FL) { \
.opc = OPC, \
+ .flags = FL, \
.fmt = FMT_##FT, \
.fac = FAC_##FC, \
.spec = SPEC_in1_##I1 | SPEC_in2_##I2 | SPEC_prep_##P | SPEC_wout_##W, \
@@ -5916,8 +5924,8 @@ static const DisasInsn insn_info[] = {
#include "insn-data.def"
};
-#undef D
-#define D(OPC, NM, FT, FC, I1, I2, P, W, OP, CC, D) \
+#undef E
+#define E(OPC, NM, FT, FC, I1, I2, P, W, OP, CC, D, FL) \
case OPC: return &insn_info[insn_ ## NM];
static const DisasInsn *lookup_opc(uint16_t opc)
@@ -5929,6 +5937,8 @@ static const DisasInsn *lookup_opc(uint16_t opc)
}
}
+#undef F
+#undef E
#undef D
#undef C