version 0.5.2
[fw/sdcc] / sim / ucsim / s51.src / jmp.cc
index 89aa6d120fb8f7161861656a4b021d0d0ab91d76..ed6f1147ef8f9ea002b61f25bbb89166d99a54ef 100644 (file)
@@ -37,6 +37,8 @@ Software Foundation, 59 Temple Place - Suite 330, Boston, MA
 // local
 #include "uc51cl.h"
 #include "regs51.h"
+#include "types51.h"
+#include "interruptcl.h"
 
 
 /*
@@ -46,7 +48,7 @@ Software Foundation, 59 Temple Place - Suite 330, Boston, MA
  */
 
 int
-t_uc51::inst_ajmp_addr(uchar code)
+cl_51core::inst_ajmp_addr(uchar code)
 {
   uchar h, l;
 
@@ -65,18 +67,21 @@ t_uc51::inst_ajmp_addr(uchar code)
  */
 
 int
-t_uc51::inst_jbc_bit_addr(uchar code)
+cl_51core::inst_jbc_bit_addr(uchar code)
 {
-  uchar bitaddr, *addr, jaddr;
+  uchar bitaddr, jaddr;
 
   bitaddr= fetch();
   jaddr  = fetch();
-  addr   = get_bit(bitaddr, &event_at.ri, &event_at.rs);
-  if (*addr & BIT_MASK(bitaddr))
-    {
-      (*addr)&= ~BIT_MASK(bitaddr);
-      PC= (PC + (signed char)jaddr) & (EROM_SIZE - 1);
-    }
+  t_addr a;
+  t_mem m;
+  class cl_address_space *mem;
+  if ((mem= bit2mem(bitaddr, &a, &m)) == 0)
+    return(resBITADDR);
+  t_mem d= mem->read(a, HW_PORT);
+  mem->write(a, d & ~m);
+  if (d & m)
+    PC= rom->validate_address(PC + (signed char)jaddr);
   tick(1);
   return(resGO);
 }
@@ -89,7 +94,7 @@ t_uc51::inst_jbc_bit_addr(uchar code)
  */
 
 int
-t_uc51::inst_ljmp(uchar code)
+cl_51core::inst_ljmp(uchar code)
 {
   PC= fetch()*256 + fetch();
   tick(1);
@@ -104,32 +109,31 @@ t_uc51::inst_ljmp(uchar code)
  */
 
 int
-t_uc51::inst_acall_addr(uchar code)
+cl_51core::inst_acall_addr(uchar code)
 {
-  uchar h, l, *sp, *aof_SP;
-  int res;
+  uchar h, l;
+  class cl_memory_cell *stck;
+  t_mem sp, sp_before/*, sp_after*/;
 
   h= (code >> 5) & 0x07;
   l= fetch();
-  aof_SP= &((sfr->umem8)[SP]);
-  //MEM(MEM_SFR)[SP]++;
-  (*aof_SP)++;
-  proc_write_sp(*aof_SP);
-  sp= get_indirect(*aof_SP/*sfr->get(SP)*/, &res);
-  if (res != resGO)
-    res= resSTACK_OV;
-  (*sp)= PC & 0xff; // push low byte
+  sp_before= sfr->get(SP);
+  sp= sfr->wadd(SP, 1);
+  //proc_write_sp(sp);
+  stck= iram->get_cell(sp);
+  stck->write(PC & 0xff); // push low byte
   tick(1);
 
-  //MEM(MEM_SFR)[SP]++;
-  (*aof_SP)++;
-  proc_write_sp(*aof_SP);
-  sp= get_indirect(*aof_SP/*sfr->get(SP)*/, &res);
-  if (res != resGO)
-    res= resSTACK_OV;
-  (*sp)= (PC >> 8) & 0xff; // push high byte
+  sp= /*sp_after*= */sfr->wadd(SP, 1);
+  //proc_write_sp(sp);
+  stck= iram->get_cell(sp);
+  stck->write((PC >> 8) & 0xff); // push high byte
+  t_mem pushed= PC;
   PC= (PC & 0xf800) | (h*256 + l);
-  return(res);
+  class cl_stack_op *so= new cl_stack_call(instPC, PC, pushed, sp_before, sp);
+  so->init();
+  stack_write(so);
+  return(resGO);
 }
 
 
@@ -140,39 +144,42 @@ t_uc51::inst_acall_addr(uchar code)
  */
 
 int
-t_uc51::inst_lcall(uchar code, uint addr)
+cl_51core::inst_lcall(uchar code, uint addr, bool intr)
 {
-  uchar h= 0, l= 0, *sp, *aof_SP;
-  int res;
+  uchar h= 0, l= 0;
+  t_mem sp, sp_before/*, sp_after*/;
+  class cl_memory_cell *stck;
 
   if (!addr)
     {
       h= fetch();
       l= fetch();
     }
-  aof_SP= &((sfr->umem8)[SP]);
-  //MEM(MEM_SFR)[SP]++;
-  (*aof_SP)++;
-  proc_write_sp(*aof_SP);
-  sp= get_indirect(*aof_SP/*sfr->get(SP)*/, &res);
-  if (res != resGO)
-    res= resSTACK_OV;
-  (*sp)= PC & 0xff; // push low byte
+  sp_before= sfr->get(SP);
+  sp= sfr->wadd(SP, 1);
+  //proc_write_sp(sp);
+  stck= iram->get_cell(sp);
+  stck->write(PC & 0xff); // push low byte
   if (!addr)
     tick(1);
 
-  //MEM(MEM_SFR)[SP]++;
-  (*aof_SP)++;
-  proc_write_sp(*aof_SP);
-  sp= get_indirect(*aof_SP/*sfr->get(SP)*/, &res);
-  if (res != resGO)
-    res= resSTACK_OV;
-  (*sp)= (PC >> 8) & 0xff; // push high byte
+  sp= sfr->wadd(SP, 1);
+  //proc_write_sp(sp);
+  stck= iram->get_cell(sp);
+  stck->write((PC >> 8) & 0xff); // push high byte
+  t_mem pushed= PC;
   if (addr)
     PC= addr;
   else
     PC= h*256 + l;
-  return(res);
+  class cl_stack_op *so;
+  if (intr)
+    so= new cl_stack_intr(instPC, PC, pushed, sp_before, sp/*_after*/);
+  else
+    so= new cl_stack_call(instPC, PC, pushed, sp_before, sp/*_after*/);
+  so->init();
+  stack_write(so);
+  return(resGO);
 }
 
 
@@ -183,15 +190,19 @@ t_uc51::inst_lcall(uchar code, uint addr)
  */
 
 int
-t_uc51::inst_jb_bit_addr(uchar code)
+cl_51core::inst_jb_bit_addr(uchar code)
 {
-  uchar *addr, bitaddr, jaddr;
+  uchar bitaddr, jaddr;
+  t_addr a;
+  t_mem m;
 
-  addr= get_bit(bitaddr= fetch(), &event_at.ri, &event_at.rs);
+  class cl_address_space *mem;
+  if ((mem= bit2mem(bitaddr= fetch(), &a, &m)) == 0)
+    return(resBITADDR);
   tick(1);
   jaddr= fetch();
-  if (read(addr) & BIT_MASK(bitaddr))
-    PC= (PC + (signed char)jaddr) & (EROM_SIZE-1);
+  if (mem->read(a) & m)
+    PC= rom->validate_address(PC + (signed char)jaddr);
   return(resGO);
 }
 
@@ -203,30 +214,26 @@ t_uc51::inst_jb_bit_addr(uchar code)
  */
 
 int
-t_uc51::inst_ret(uchar code)
+cl_51core::inst_ret(uchar code)
 {
-  uchar h, l, *sp, *aof_SP;
-  int res;
-
-  aof_SP= &((sfr->umem8)[SP]);
-  sp= get_indirect(*aof_SP/*sfr->get(SP)*/, &res);
-  if (res != resGO)
-    res= resSTACK_OV;
-  h= *sp;
-  //MEM(MEM_SFR)[SP]--;
-  (*aof_SP)--;
-  proc_write_sp(*aof_SP);
+  uchar h= 0, l= 0;
+  t_mem sp, sp_before/*, sp_after*/;
+  class cl_memory_cell *stck;
+
+  sp= sp_before= sfr->read(SP);
+  stck= iram->get_cell(sp);
+  h= stck->read();
+  sp= sfr->wadd(SP, -1);
   tick(1);
 
-  sp= get_indirect(*aof_SP/*sfr->get(SP)*/, &res);
-  if (res != resGO)
-    res= resSTACK_OV;
-  l= *sp;
-  //MEM(MEM_SFR)[SP]--;
-  (*aof_SP)--;
-  proc_write_sp(*aof_SP);
+  stck= iram->get_cell(sp);
+  l= stck->read();
+  sp= sfr->wadd(SP, -1);
   PC= h*256 + l;
-  return(res);
+  class cl_stack_op *so= new cl_stack_ret(instPC, PC, sp_before, sp/*_after*/);
+  so->init();
+  stack_read(so);
+  return(resGO);
 }
 
 
@@ -237,15 +244,19 @@ t_uc51::inst_ret(uchar code)
  */
 
 int
-t_uc51::inst_jnb_bit_addr(uchar code)
+cl_51core::inst_jnb_bit_addr(uchar code)
 {
-  uchar *addr, bitaddr, jaddr;
+  uchar bitaddr, jaddr;
+  t_mem m;
+  t_addr a;
+  class cl_address_space *mem;
 
-  addr= get_bit(bitaddr= fetch(), &event_at.ri, &event_at.rs);
+  if ((mem= bit2mem(bitaddr= fetch(), &a, &m)) == 0)
+    return(resBITADDR);
   tick(1);
   jaddr= fetch();
-  if (!(read(addr) & BIT_MASK(bitaddr)))
-    PC= (PC + (signed char)jaddr) & (get_mem_size(MEM_ROM)-1);
+  if (!(mem->read(a) & m))
+    PC= rom->validate_address(PC + (signed char)jaddr);
   return(resGO);
 }
 
@@ -257,31 +268,24 @@ t_uc51::inst_jnb_bit_addr(uchar code)
  */
 
 int
-t_uc51::inst_reti(uchar code)
+cl_51core::inst_reti(uchar code)
 {
-  uchar h, l, *sp, *aof_SP;
-  int res;
-
-  aof_SP= &((sfr->umem8)[SP]);
-  sp= get_indirect(*aof_SP/*sfr->get(SP)*/, &res);
-  if (res != resGO)
-    res= resSTACK_OV;
-  h= *sp;
-  //MEM(MEM_SFR)[SP]--;
-  (*aof_SP)--;
-  proc_write_sp(*aof_SP);
+  uchar h= 0, l= 0;
+  t_mem sp, sp_before, sp_after;
+  class cl_memory_cell *stck;
+
+  sp= sp_before= sfr->read(SP);
+  stck= iram->get_cell(sp);
+  h= stck->read();
+  sp= sfr->wadd(SP, -1);
   tick(1);
 
-  sp= get_indirect(*aof_SP/*sfr->get(SP)*/, &res);
-  if (res != resGO)
-    res= resSTACK_OV;
-  l= *sp;
-  //MEM(MEM_SFR)[SP]--;
-  (*aof_SP)--;
-  proc_write_sp(*aof_SP);
+  stck= iram->get_cell(sp);
+  l= stck->read();
+  sp= sp_after= sfr->wadd(SP, -1);
   PC= h*256 + l;
 
-  was_reti= DD_TRUE;
+  interrupt->was_reti= DD_TRUE;
   class it_level *il= (class it_level *)(it_levels->top());
   if (il &&
       il->level >= 0)
@@ -289,7 +293,11 @@ t_uc51::inst_reti(uchar code)
       il= (class it_level *)(it_levels->pop());
       delete il;
     }
-  return(res);
+  class cl_stack_op *so=
+    new cl_stack_iret(instPC, PC, sp_before, sp_after);
+  so->init();
+  stack_read(so);
+  return(resGO);
 }
 
 
@@ -300,15 +308,14 @@ t_uc51::inst_reti(uchar code)
  */
 
 int
-t_uc51::inst_jc_addr(uchar code)
+cl_51core::inst_jc_addr(uchar code)
 {
   uchar jaddr;
 
   jaddr= fetch();
   tick(1);
-  if (GET_C)
-    PC= (PC + (signed char)jaddr) & (EROM_SIZE-1);
-  event_at.rs= PSW;
+  if (SFR_GET_C)
+    PC= rom->validate_address(PC + (signed char)jaddr);
   return(resGO);
 }
 
@@ -320,15 +327,14 @@ t_uc51::inst_jc_addr(uchar code)
  */
 
 int
-t_uc51::inst_jnc_addr(uchar code)
+cl_51core::inst_jnc_addr(uchar code)
 {
   uchar jaddr;
 
   jaddr= fetch();
   tick(1);
-  if (!GET_C)
-    PC= (PC + (signed char)jaddr) & (EROM_SIZE-1);
-  event_at.rs= ACC;
+  if (!SFR_GET_C)
+    PC= rom->validate_address(PC + (signed char)jaddr);
   return(resGO);
 }
 
@@ -340,14 +346,14 @@ t_uc51::inst_jnc_addr(uchar code)
  */
 
 int
-t_uc51::inst_jz_addr(uchar code)
+cl_51core::inst_jz_addr(uchar code)
 {
   uchar jaddr;
 
   jaddr= fetch();
   tick(1);
-  if (!sfr->get(ACC))
-    PC= (PC + (signed char)jaddr) & (EROM_SIZE-1);
+  if (!acc->read())
+    PC= rom->validate_address(PC + (signed char)jaddr);
   return(resGO);
 }
 
@@ -359,14 +365,14 @@ t_uc51::inst_jz_addr(uchar code)
  */
 
 int
-t_uc51::inst_jnz_addr(uchar code)
+cl_51core::inst_jnz_addr(uchar code)
 {
   uchar jaddr;
 
   jaddr= fetch();
   tick(1);
-  if (sfr->get(ACC))
-    PC= (PC + (signed char)jaddr) & (EROM_SIZE-1);
+  if (acc->read())
+    PC= rom->validate_address(PC + (signed char)jaddr);
   return(resGO);
 }
 
@@ -378,11 +384,9 @@ t_uc51::inst_jnz_addr(uchar code)
  */
 
 int
-t_uc51::inst_jmp_$a_dptr(uchar code)
+cl_51core::inst_jmp_Sa_dptr(uchar code)
 {
-  PC= (sfr->get(DPH)*256 + sfr->get(DPL) +
-       read_mem(MEM_SFR, ACC)) &
-    (EROM_SIZE - 1);
+  PC= rom->validate_address(sfr->read(DPH)*256 + sfr->read(DPL) + acc->read());
   tick(1);
   return(resGO);
 }
@@ -395,10 +399,11 @@ t_uc51::inst_jmp_$a_dptr(uchar code)
  */
 
 int
-t_uc51::inst_sjmp(uchar code)
+cl_51core::inst_sjmp(uchar code)
 {
   signed char target= fetch();
-  PC= (PC + target) & (EROM_SIZE -1);
+
+  PC= rom->validate_address(PC + target);
   tick(1);
   return(resGO);
 }
@@ -411,16 +416,16 @@ t_uc51::inst_sjmp(uchar code)
  */
 
 int
-t_uc51::inst_cjne_a_$data_addr(uchar code)
+cl_51core::inst_cjne_a_Sdata_addr(uchar code)
 {
-  uchar data, jaddr;
+  uchar data, jaddr, ac;
 
   data = fetch();
   jaddr= fetch();
   tick(1);
-  SET_C(sfr->get(ACC) < data);
-  if (read_mem(MEM_SFR, event_at.rs= ACC) != data)
-    PC= (PC + (signed char)jaddr) & (EROM_SIZE - 1);
+  SFR_SET_C((ac= acc->read()) < data);
+  if (ac != data)
+    PC= rom->validate_address(PC + (signed char)jaddr);
   return(resGO);
 }
 
@@ -432,17 +437,19 @@ t_uc51::inst_cjne_a_$data_addr(uchar code)
  */
 
 int
-t_uc51::inst_cjne_a_addr_addr(uchar code)
+cl_51core::inst_cjne_a_addr_addr(uchar code)
 {
-  uchar data, *addr, jaddr;
+  uchar data, jaddr;
+  t_addr a;
+  class cl_memory_cell *cell;
 
-  addr = get_direct(fetch(), &event_at.ri, &event_at.rs);
+  cell= get_direct(a= fetch());
   jaddr= fetch();
   tick(1);
-  data= read(addr);
-  SET_C(sfr->get(ACC) < data);
-  if (sfr->get(event_at.rs= ACC) != data)
-    PC= (PC + (signed char)jaddr) & (EROM_SIZE - 1);
+  data= cell->read();
+  SFR_SET_C(acc->get() < data);
+  if (acc->read() != data)
+    PC= rom->validate_address(PC + (signed char)jaddr);
   return(resGO);
 }
 
@@ -454,19 +461,20 @@ t_uc51::inst_cjne_a_addr_addr(uchar code)
  */
 
 int
-t_uc51::inst_cjne_$ri_$data_addr(uchar code)
+cl_51core::inst_cjne_Sri_Sdata_addr(uchar code)
 {
-  uchar *addr, data, jaddr;
-  int res;
+  uchar data, jaddr;
+  class cl_memory_cell *cell;
 
-  addr = get_indirect(event_at.ri= *(get_reg(code & 0x01)), &res);
+  cell= iram->get_cell(get_reg(code & 0x01)->read());
   data = fetch();
   jaddr= fetch();
   tick(1);
-  SET_C(*addr < data);
-  if (*addr != data)
-    PC= (PC + (signed char)jaddr) & (EROM_SIZE - 1);
-  return(res);
+  t_mem d;
+  SFR_SET_C((d= cell->read()) < data);
+  if (d != data)
+    PC= rom->validate_address(PC + (signed char)jaddr);
+  return(resGO);
 }
 
 
@@ -477,17 +485,19 @@ t_uc51::inst_cjne_$ri_$data_addr(uchar code)
  */
 
 int
-t_uc51::inst_cjne_rn_$data_addr(uchar code)
+cl_51core::inst_cjne_rn_Sdata_addr(uchar code)
 {
-  uchar *reg, data, jaddr;
+  uchar data, jaddr;
+  class cl_memory_cell *reg;
 
-  reg  = get_reg(code & 0x07, &event_at.ri);
+  reg  = get_reg(code & 0x07);
   data = fetch();
   jaddr= fetch();
   tick(1);
-  SET_C(*reg < data);
-  if (*reg != data)
-    PC= (PC + (signed char)jaddr) & (EROM_SIZE - 1);
+  t_mem r;
+  SFR_SET_C((r= reg->read()) < data);
+  if (r != data)
+    PC= rom->validate_address(PC + (signed char)jaddr);
   return(resGO);
 }
 
@@ -499,15 +509,18 @@ t_uc51::inst_cjne_rn_$data_addr(uchar code)
  */
 
 int
-t_uc51::inst_djnz_addr_addr(uchar code)
+cl_51core::inst_djnz_addr_addr(uchar code)
 {
-  uchar *addr, jaddr;
-  
-  addr = get_direct(fetch(), &event_at.wi, &event_at.ws);
+  uchar jaddr;
+  class cl_memory_cell *cell;
+
+  cell = get_direct(fetch());
   jaddr= fetch();
   tick(1);
-  if (--(*addr))
-    PC= (PC + (signed char)jaddr) & (EROM_SIZE-1);
+  t_mem d= cell->read(HW_PORT);//cell->wadd(-1);
+  d= cell->write(d-1);
+  if (d)
+    PC= rom->validate_address(PC + (signed char)jaddr);
   return(resGO);
 }
 
@@ -519,15 +532,17 @@ t_uc51::inst_djnz_addr_addr(uchar code)
  */
 
 int
-t_uc51::inst_djnz_rn_addr(uchar code)
+cl_51core::inst_djnz_rn_addr(uchar code)
 {
-  uchar *reg, jaddr;
-  
-  reg  = get_reg(code & 0x07, &event_at.wi);
+  uchar jaddr;
+  class cl_memory_cell *reg;
+
+  reg  = get_reg(code & 0x07);
   jaddr= fetch();
   tick(1);
-  if (--(*reg))
-    PC= (PC + (signed char)jaddr) & (EROM_SIZE-1);
+  t_mem r= reg->wadd(-1);
+  if (r)
+    PC= rom->validate_address(PC + (signed char)jaddr);
   return(resGO);
 }