diff options
| author | bunnei <bunneidev@gmail.com> | 2015-01-06 12:42:10 -0500 | 
|---|---|---|
| committer | bunnei <bunneidev@gmail.com> | 2015-01-06 12:42:10 -0500 | 
| commit | 89bb0ecbd534527898a836e8565702364906cdb9 (patch) | |
| tree | 47dd582f543e140b356be9df4813f644f4f29740 | |
| parent | 9c8b867d86612a04bc0e563831d1d0feee9ffe89 (diff) | |
| parent | 8132c01830c9e71e75e6bc1e365326cf07c5b00f (diff) | |
Merge pull request #417 from kevinhartman/exclusive-tag-fix
Added exclusive reservation granule from ARMv7 spec to dyncom...
| -rw-r--r-- | src/core/arm/dyncom/arm_dyncom_interpreter.cpp | 12 | ||||
| -rw-r--r-- | src/core/arm/skyeye_common/armdefs.h | 22 | 
2 files changed, 18 insertions, 16 deletions
| diff --git a/src/core/arm/dyncom/arm_dyncom_interpreter.cpp b/src/core/arm/dyncom/arm_dyncom_interpreter.cpp index 593e0eabd..9b291862c 100644 --- a/src/core/arm/dyncom/arm_dyncom_interpreter.cpp +++ b/src/core/arm/dyncom/arm_dyncom_interpreter.cpp @@ -63,16 +63,21 @@ extern void switch_mode(arm_core_t *core, uint32_t mode);  typedef arm_core_t arm_processor;  typedef unsigned int (*shtop_fp_t)(arm_processor *cpu, unsigned int sht_oper); +// Defines a reservation granule of 2 words, which protects the first 2 words starting at the tag. +// This is the smallest granule allowed by the v7 spec, and is coincidentally just large enough to +// support LDR/STREXD. +static const ARMword RESERVATION_GRANULE_MASK = 0xFFFFFFF8; +  // Exclusive memory access  static int exclusive_detect(ARMul_State* state, ARMword addr){ -    if(state->exclusive_tag == addr) +    if(state->exclusive_tag == (addr & RESERVATION_GRANULE_MASK))          return 0;      else          return -1;  }  static void add_exclusive_addr(ARMul_State* state, ARMword addr){ -    state->exclusive_tag = addr; +    state->exclusive_tag = addr & RESERVATION_GRANULE_MASK;      return;  } @@ -80,7 +85,6 @@ static void remove_exclusive(ARMul_State* state, ARMword addr){      state->exclusive_tag = 0xFFFFFFFF;  } -  unsigned int DPO(Immediate)(arm_processor *cpu, unsigned int sht_oper) {      unsigned int immed_8 = BITS(sht_oper, 0, 7);      unsigned int rotate_imm = BITS(sht_oper, 8, 11); @@ -4613,7 +4617,6 @@ unsigned InterpreterMainLoop(ARMul_State* state) {              add_exclusive_addr(cpu, read_addr);              cpu->exclusive_state = 1; -            // TODO(bunnei): Do we need to also make [read_addr + 4] exclusive?              RD = Memory::Read32(read_addr);              RD2 = Memory::Read32(read_addr + 4); @@ -6133,7 +6136,6 @@ unsigned InterpreterMainLoop(ARMul_State* state) {              if ((exclusive_detect(cpu, write_addr) == 0) && (cpu->exclusive_state == 1)) {                  remove_exclusive(cpu, write_addr);                  cpu->exclusive_state = 0; -                // TODO(bunnei): Remove exclusive from [write_addr + 4] if we implement this in LDREXD                  Memory::Write32(write_addr, cpu->Reg[inst_cream->Rm]);                  Memory::Write32(write_addr + 4, cpu->Reg[inst_cream->Rm + 1]); diff --git a/src/core/arm/skyeye_common/armdefs.h b/src/core/arm/skyeye_common/armdefs.h index 3100d7adc..1b2cef451 100644 --- a/src/core/arm/skyeye_common/armdefs.h +++ b/src/core/arm/skyeye_common/armdefs.h @@ -165,20 +165,20 @@ struct ARMul_State      unsigned ErrorCode;    /* type of illegal instruction */      /* Order of the following register should not be modified */ -    ARMword Reg[16];      /* the current register file */ -    ARMword Cpsr;         /* the current psr */ +    ARMword Reg[16];            /* the current register file */ +    ARMword Cpsr;               /* the current psr */      ARMword Spsr_copy;      ARMword phys_pc;      ARMword Reg_usr[2]; -    ARMword Reg_svc[2];   /* R13_SVC R14_SVC */ -    ARMword Reg_abort[2]; /* R13_ABORT R14_ABORT */ -    ARMword Reg_undef[2]; /* R13 UNDEF R14 UNDEF */ -    ARMword Reg_irq[2];   /* R13_IRQ R14_IRQ */ -    ARMword Reg_firq[7];  /* R8---R14 FIRQ */ -    ARMword Spsr[7];      /* the exception psr's */ -    ARMword Mode;         /* the current mode */ -    ARMword Bank;         /* the current register bank */ -    ARMword exclusive_tag; +    ARMword Reg_svc[2];         /* R13_SVC R14_SVC */ +    ARMword Reg_abort[2];       /* R13_ABORT R14_ABORT */ +    ARMword Reg_undef[2];       /* R13 UNDEF R14 UNDEF */ +    ARMword Reg_irq[2];         /* R13_IRQ R14_IRQ */ +    ARMword Reg_firq[7];        /* R8---R14 FIRQ */ +    ARMword Spsr[7];            /* the exception psr's */ +    ARMword Mode;               /* the current mode */ +    ARMword Bank;               /* the current register bank */ +    ARMword exclusive_tag;      /* the address for which the local monitor is in exclusive access mode */      ARMword exclusive_state;      ARMword exclusive_result;      ARMword CP15[VFP_BASE - CP15_BASE]; | 
