[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]
[Tinycc-devel] [PATCH 3/8] arm-asm: Add mcr, mrc
From: |
Danny Milosavljevic |
Subject: |
[Tinycc-devel] [PATCH 3/8] arm-asm: Add mcr, mrc |
Date: |
Thu, 14 Jan 2021 23:22:22 +0100 |
---
arm-asm.c | 50 ++++++++++++++++++++++++++++++++++++++++++--------
arm-tok.h | 2 ++
2 files changed, 44 insertions(+), 8 deletions(-)
diff --git a/arm-asm.c b/arm-asm.c
index 54947e6..ada746b 100644
--- a/arm-asm.c
+++ b/arm-asm.c
@@ -336,6 +336,7 @@ static void asm_coprocessor_opcode(TCCState *s1, int token)
{
uint8_t registers[3];
unsigned int i;
uint8_t high_nibble;
+ uint8_t mrc = 0;
if (tok >= TOK_ASM_p0 && tok <= TOK_ASM_p15) {
coprocessor = tok - TOK_ASM_p0;
@@ -361,12 +362,22 @@ static void asm_coprocessor_opcode(TCCState *s1, int
token) {
next();
else
expect("','");
- if (tok >= TOK_ASM_c0 && tok <= TOK_ASM_c15) {
- registers[i] = tok - TOK_ASM_c0;
- next();
+ if (i == 0 && token != TOK_ASM_cdp2 && (ARM_INSTRUCTION_GROUP(token)
== TOK_ASM_mrceq || ARM_INSTRUCTION_GROUP(token) == TOK_ASM_mcreq)) {
+ if (tok >= TOK_ASM_r0 && tok <= TOK_ASM_r15) {
+ registers[i] = tok - TOK_ASM_r0;
+ next();
+ } else {
+ expect("'r<number>'");
+ return;
+ }
} else {
- expect("'c<number>");
- return;
+ if (tok >= TOK_ASM_c0 && tok <= TOK_ASM_c15) {
+ registers[i] = tok - TOK_ASM_c0;
+ next();
+ } else {
+ expect("'c<number>'");
+ return;
+ }
}
}
if (tok == ',') {
@@ -381,11 +392,32 @@ static void asm_coprocessor_opcode(TCCState *s1, int
token) {
return;
}
- if (token == TOK_ASM_cdp2)
+ if (token == TOK_ASM_cdp2) {
high_nibble = 0xF;
- else
+ asm_emit_coprocessor_opcode(high_nibble, coprocessor, opcode1.e.v,
registers[0], registers[1], registers[2], opcode2.e.v, 0);
+ return;
+ } else
high_nibble = condition_code_of_token(token);
- asm_emit_coprocessor_opcode(high_nibble, coprocessor, opcode1.e.v,
registers[0], registers[1], registers[2], opcode2.e.v, 0);
+
+ switch (ARM_INSTRUCTION_GROUP(token)) {
+ case TOK_ASM_cdpeq:
+ asm_emit_coprocessor_opcode(high_nibble, coprocessor, opcode1.e.v,
registers[0], registers[1], registers[2], opcode2.e.v, 0);
+ break;
+ case TOK_ASM_mrceq:
+ // opcode1 encoding changes! highest and lowest bit gone.
+ mrc = 1;
+ /* fallthrough */
+ case TOK_ASM_mcreq:
+ // opcode1 encoding changes! highest and lowest bit gone.
+ if (opcode1.e.v > 7) {
+ tcc_error("opcode1 of instruction '%s' must be an immediate value
between 0 and 7", get_tok_str(token, NULL));
+ return;
+ }
+ asm_emit_coprocessor_opcode(high_nibble, coprocessor, 0x8 |
(opcode1.e.v << 1) | mrc, registers[0], registers[1], registers[2],
opcode2.e.v, 1);
+ break;
+ default:
+ expect("known instruction");
+ }
}
/* data processing and single data transfer instructions only */
@@ -1553,6 +1585,8 @@ ST_FUNC void asm_opcode(TCCState *s1, int token)
return asm_long_multiplication_opcode(s1, token);
case TOK_ASM_cdpeq:
+ case TOK_ASM_mcreq:
+ case TOK_ASM_mrceq:
return asm_coprocessor_opcode(s1, token);
default:
expect("known instruction");
diff --git a/arm-tok.h b/arm-tok.h
index 269c4a7..7f15b73 100644
--- a/arm-tok.h
+++ b/arm-tok.h
@@ -214,3 +214,5 @@
DEF_ASM_CONDED(rrxs)
DEF_ASM_CONDED(cdp)
+ DEF_ASM_CONDED(mcr)
+ DEF_ASM_CONDED(mrc)
- [Tinycc-devel] [PATCH 0/8] Implement ARM VFP in ARM inline assembler, Danny Milosavljevic, 2021/01/14
- [Tinycc-devel] [PATCH 4/8] arm-asm: Add ldc, ldcl, stc, stcl, Danny Milosavljevic, 2021/01/14
- [Tinycc-devel] [PATCH 1/8] arm-asm: Add cdp, Danny Milosavljevic, 2021/01/14
- [Tinycc-devel] [PATCH 3/8] arm-asm: Add mcr, mrc,
Danny Milosavljevic <=
- [Tinycc-devel] [PATCH 5/8] arm-asm: Add ldc2, ldc2l, stc2, stc2l, Danny Milosavljevic, 2021/01/14
- [Tinycc-devel] [PATCH 8/8] arm-asm: Add vneg, vabs, vsqrt, vcmp, vcmpe, Danny Milosavljevic, 2021/01/14
- [Tinycc-devel] [PATCH 2/8] arm-asm: Add cdp2, Danny Milosavljevic, 2021/01/14
- [Tinycc-devel] [PATCH 7/8] arm-asm: Add vmla, vmls, vnmls, vnmla, vmul, vnmul, vadd, vsub, vdiv, Danny Milosavljevic, 2021/01/14
- [Tinycc-devel] [PATCH 6/8] arm-asm: Add vldr, vstr., Danny Milosavljevic, 2021/01/14