[PATCH 10/11] target/hexagon: fix iassign{r,w} to cover all threads

Brian Cain <[email protected]>
Newsgroups gmane.comp.emulators.qemu
Message-ID <[email protected]>
iassignw/iassignr were filtering CPU_FOREACH by MODECTL_E, the
thread-enabled mask. That mask reflects whether a thread has been
started, not whether it exists, so IMASK writes/reads never reached
threads that hadn't been started yet, leaving their IMASK stale or
unreadable. Drop the MODECTL_E filtering and operate on every thread.

Signed-off-by: Brian Cain <[email protected]>
---
 target/hexagon/op_helper.c | 42 +++++++++-----------------------------
 1 file changed, 10 insertions(+), 32 deletions(-)

diff --git a/target/hexagon/op_helper.c b/target/hexagon/op_helper.c
index df31ed2488a..e19c3c91085 100644
--- a/target/hexagon/op_helper.c
+++ b/target/hexagon/op_helper.c
@@ -1637,61 +1637,39 @@ void HELPER(cswi)(CPUHexagonState *env, uint32_t mask)
 
 void HELPER(iassignw)(CPUHexagonState *env, uint32_t src)
 {
-    uint32_t modectl;
-    uint32_t thread_enabled_mask;
     CPUState *cpu;
-    HexagonCPU *hex_cpu;
 
     BQL_LOCK_GUARD();
-    hex_cpu = env_archcpu(env);
-    modectl = hex_cpu->globalregs ?
-        hexagon_globalreg_read(hex_cpu->globalregs, HEX_SREG_MODECTL,
-                               env->threadId) : 0;
-    thread_enabled_mask = GET_FIELD(MODECTL_E, modectl);
 
     CPU_FOREACH(cpu) {
         CPUHexagonState *thread_env = &(HEXAGON_CPU(cpu)->env);
-        uint32_t thread_id_mask = 0x1 << thread_env->threadId;
-        if (thread_enabled_mask & thread_id_mask) {
-            uint32_t imask = thread_env->t_sreg[HEX_SREG_IMASK];
-            uint32_t intbitpos = (src >> 16) & 0xF;
-            uint32_t val = (src >> thread_env->threadId) & 0x1;
-            imask = deposit32(imask, intbitpos, 1, val);
-            thread_env->t_sreg[HEX_SREG_IMASK] = imask;
+        uint32_t imask = thread_env->t_sreg[HEX_SREG_IMASK];
+        uint32_t intbitpos = (src >> 16) & 0xF;
+        uint32_t val = (src >> thread_env->threadId) & 0x1;
+        imask = deposit32(imask, intbitpos, 1, val);
+        thread_env->t_sreg[HEX_SREG_IMASK] = imask;
 
-            qemu_log_mask(CPU_LOG_INT, "%s: thread " TARGET_FMT_ld
-               ", new imask 0x%" PRIx32 "\n", __func__,
-               thread_env->threadId, imask);
-        }
+        qemu_log_mask(CPU_LOG_INT, "%s: thread " TARGET_FMT_ld
+           ", new imask 0x%" PRIx32 "\n", __func__,
+           thread_env->threadId, imask);
     }
     hex_interrupt_update(env);
 }
 
 uint32_t HELPER(iassignr)(CPUHexagonState *env, uint32_t src)
 {
-    uint32_t modectl;
-    uint32_t thread_enabled_mask;
     uint32_t intbitpos;
     uint32_t dest_reg;
     CPUState *cpu;
-    HexagonCPU *hex_cpu;
 
     BQL_LOCK_GUARD();
-    hex_cpu = env_archcpu(env);
-    modectl = hex_cpu->globalregs ?
-        hexagon_globalreg_read(hex_cpu->globalregs, HEX_SREG_MODECTL,
-                               env->threadId) : 0;
-    thread_enabled_mask = GET_FIELD(MODECTL_E, modectl);
     /* src fields are in same position as modectl, but mean different things */
     intbitpos = GET_FIELD(MODECTL_W, src);
     dest_reg = 0;
     CPU_FOREACH(cpu) {
         CPUHexagonState *thread_env = &(HEXAGON_CPU(cpu)->env);
-        uint32_t thread_id_mask = 0x1 << thread_env->threadId;
-        if (thread_enabled_mask & thread_id_mask) {
-            uint32_t imask = thread_env->t_sreg[HEX_SREG_IMASK];
-            dest_reg |= ((imask >> intbitpos) & 0x1) << thread_env->threadId;
-        }
+        uint32_t imask = thread_env->t_sreg[HEX_SREG_IMASK];
+        dest_reg |= ((imask >> intbitpos) & 0x1) << thread_env->threadId;
     }
 
     return dest_reg;
-- 
2.34.1
lmpx.com only provides a reader for public news (NNTP) servers. It is not affiliated with the servers or forums shown here and is not responsible for the content of articles, which is written by their respective authors.