ref: d304dc8119a737c65eca8717e1f436a1e0edf880
parent: ca4f815cfc673d00834b48535b9903aae3ac3961
author: cinap_lenrek <[email protected]>
date: Thu Aug 7 16:22:00 EDT 2014
5a, 5l: add LDREX/STREX/CLREX instructions
--- a/sys/src/cmd/5a/lex.c
+++ b/sys/src/cmd/5a/lex.c
@@ -380,6 +380,7 @@
"RET", LTYPEA, ARET,
"RFE", LTYPEA, ARFE,
+ "CLREX", LTYPEA, ACLREX,
"TEXT", LTYPEB, ATEXT,
"GLOBL", LTYPEB, AGLOBL,
--- a/sys/src/cmd/5c/5.out.h
+++ b/sys/src/cmd/5c/5.out.h
@@ -156,6 +156,8 @@
ALDREXD,
ASTREXD,
+ ACLREX,
+
ALAST,
};
--- a/sys/src/cmd/5c/enam.c
+++ /dev/null
@@ -1,104 +1,0 @@
-char* anames[] =
-{
- "XXX",
- "AND",
- "EOR",
- "SUB",
- "RSB",
- "ADD",
- "ADC",
- "SBC",
- "RSC",
- "TST",
- "TEQ",
- "CMP",
- "CMN",
- "ORR",
- "BIC",
- "MVN",
- "B",
- "BL",
- "BEQ",
- "BNE",
- "BCS",
- "BHS",
- "BCC",
- "BLO",
- "BMI",
- "BPL",
- "BVS",
- "BVC",
- "BHI",
- "BLS",
- "BGE",
- "BLT",
- "BGT",
- "BLE",
- "MOVWD",
- "MOVWF",
- "MOVDW",
- "MOVFW",
- "MOVFD",
- "MOVDF",
- "MOVF",
- "MOVD",
- "CMPF",
- "CMPD",
- "ADDF",
- "ADDD",
- "SUBF",
- "SUBD",
- "MULF",
- "MULD",
- "DIVF",
- "DIVD",
- "SRL",
- "SRA",
- "SLL",
- "MULU",
- "DIVU",
- "MUL",
- "DIV",
- "MOD",
- "MODU",
- "MOVB",
- "MOVBU",
- "MOVH",
- "MOVHU",
- "MOVW",
- "MOVM",
- "SWPBU",
- "SWPW",
- "NOP",
- "RFE",
- "SWI",
- "MULA",
- "DATA",
- "GLOBL",
- "GOK",
- "HISTORY",
- "NAME",
- "RET",
- "TEXT",
- "WORD",
- "DYNT",
- "INIT",
- "BCASE",
- "CASE",
- "END",
- "MULL",
- "MULAL",
- "MULLU",
- "MULALU",
- "BX",
- "BXRET",
- "DWORD",
- "SIGNAME",
- "SQRTF",
- "SQRTD",
- "LDREX",
- "STREX",
- "LDREXD",
- "STREXD",
- "LAST",
-};
--- a/sys/src/cmd/5l/asm.c
+++ b/sys/src/cmd/5l/asm.c
@@ -1094,12 +1094,19 @@
break;
case 40: /* swp oreg,reg,reg */
- aclass(&p->from);
- if(instoffset != 0)
- diag("offset must be zero in SWP");
+ if(p->as != ASTREX){
+ aclass(&p->from);
+ if(instoffset != 0)
+ diag("offset must be zero in SWP");
+ }
o1 = (0x2<<23) | (0x9<<4);
- if(p->as != ASWPW)
- o1 |= 1 << 22;
+ if(p->as == ASWPBU)
+ o1 |= (1 << 22);
+ else if(p->as == ALDREX || p->as == ASTREX){
+ o1 |= (1 << 23) | 0xf00;
+ if(p->as == ALDREX)
+ o1 |= (1 << 20) | 0xf;
+ }
o1 |= p->from.reg << 16;
o1 |= p->reg << 0;
o1 |= p->to.reg << 12;
@@ -1108,6 +1115,10 @@
case 41: /* rfe -> movm.s.w.u 0(r13),[r15] */
o1 = 0xe8fd8000;
+ break;
+
+ case 42: /* clrex */
+ o1 = 0xf57ff01f;
break;
case 50: /* floating point store */
--- a/sys/src/cmd/5l/optab.c
+++ b/sys/src/cmd/5l/optab.c
@@ -161,8 +161,11 @@
{ AMOVM, C_SOREG,C_NONE, C_LCON, 39, 4, 0 },
{ ASWPW, C_SOREG,C_REG, C_REG, 40, 4, 0 },
+ { ALDREX, C_SOREG,C_NONE, C_REG, 40, 4, 0 },
+ { ASTREX, C_SOREG,C_REG, C_REG, 40, 4, 0 },
{ ARFE, C_NONE, C_NONE, C_NONE, 41, 4, 0 },
+ { ACLREX, C_NONE, C_NONE, C_NONE, 42, 4, 0 },
{ AMOVF, C_FREG, C_NONE, C_FEXT, 50, 4, REGSB },
{ AMOVF, C_FREG, C_NONE, C_FAUTO, 50, 4, REGSP },
--- a/sys/src/cmd/5l/span.c
+++ b/sys/src/cmd/5l/span.c
@@ -743,7 +743,11 @@
break;
case ASWPW:
oprange[ASWPBU] = oprange[r];
+ oprange[ALDREX] = oprange[r];
+ oprange[ASTREX] = oprange[r];
break;
+ case ALDREX:
+ case ASTREX:
case AB:
case ABL:
case ABX:
@@ -752,6 +756,7 @@
case AWORD:
case AMOVM:
case ARFE:
+ case ACLREX:
case ATEXT:
case ACASE:
case ABCASE: