4 #include "remote-sim.h"
8 #define IMEM_SIZE 18 /* D10V instruction memory size is 18 bits */
9 #define DMEM_SIZE 16 /* Data memory */
11 enum _leftright { LEFT_FIRST, RIGHT_FIRST };
14 host_callback *d10v_callback;
15 long ins_type_counters[ (int)INS_MAX ];
16 long left_nops, right_nops;
20 static struct hash_entry *lookup_hash PARAMS ((uint32 ins, int size));
25 struct hash_entry *next;
31 struct hash_entry hash_table[MAX_HASH+1];
38 if (format & LONG_OPCODE)
39 return ((insn & 0x3F000000) >> 24);
41 return((insn & 0x7E00) >> 9);
44 static struct hash_entry *
45 lookup_hash (ins, size)
52 h = &hash_table[(ins & 0x3F000000) >> 24];
54 h = &hash_table[(ins & 0x7E00) >> 9];
56 while ( (ins & h->mask) != h->opcode)
60 (*d10v_callback->printf_filtered) (d10v_callback, "ERROR looking up hash for %x at PC %x\n",ins, PC);
73 return (a[0]<<24) + (a[1]<<16) + (a[2]<<8) + (a[3]);
81 return ((int64)a[0]<<56) + ((int64)a[1]<<48) + ((int64)a[2]<<40) + ((int64)a[3]<<32) +
82 ((int64)a[4]<< 24) + ((int64)a[5]<<16) + ((int64)a[6]<<8) + (int64)a[7];
90 return ((uint16)a[0]<<8) + a[1];
95 write_word (addr, data)
105 write_longword (addr, data)
109 addr[0] = (data >> 24) & 0xff;
110 addr[1] = (data >> 16) & 0xff;
111 addr[2] = (data >> 8) & 0xff;
112 addr[3] = data & 0xff;
116 write_longlong (addr, data)
122 a[1] = (data >> 48) & 0xff;
123 a[2] = (data >> 40) & 0xff;
124 a[3] = (data >> 32) & 0xff;
125 a[4] = (data >> 24) & 0xff;
126 a[5] = (data >> 16) & 0xff;
127 a[6] = (data >> 8) & 0xff;
132 get_operands (struct simops *s, uint32 ins)
134 int i, shift, bits, flags;
136 for (i=0; i < s->numops; i++)
138 shift = s->operands[3*i];
139 bits = s->operands[3*i+1];
140 flags = s->operands[3*i+2];
141 mask = 0x7FFFFFFF >> (31 - bits);
142 OP[i] = (ins >> shift) & mask;
150 struct hash_entry *h;
152 if ((d10v_debug & DEBUG_INSTRUCTION) != 0)
153 (*d10v_callback->printf_filtered) (d10v_callback, "do_long 0x%x\n", ins);
155 h = lookup_hash (ins, 1);
156 get_operands (h->ops, ins);
157 State.ins_type = INS_LONG;
158 ins_type_counters[ (int)State.ins_type ]++;
163 do_2_short (ins1, ins2, leftright)
165 enum _leftright leftright;
167 struct hash_entry *h;
171 if ((d10v_debug & DEBUG_INSTRUCTION) != 0)
172 (*d10v_callback->printf_filtered) (d10v_callback, "do_2_short 0x%x (%s) -> 0x%x\n",
173 ins1, (leftright) ? "left" : "right", ins2);
175 /* printf ("do_2_short %x -> %x\n",ins1,ins2); */
176 h = lookup_hash (ins1, 0);
177 get_operands (h->ops, ins1);
178 State.ins_type = (leftright == LEFT_FIRST) ? INS_LEFT : INS_RIGHT;
179 ins_type_counters[ (int)State.ins_type ]++;
182 /* If the PC has changed (ie, a jump), don't do the second instruction */
185 h = lookup_hash (ins2, 0);
186 get_operands (h->ops, ins2);
187 State.ins_type = (leftright == LEFT_FIRST) ? INS_RIGHT : INS_LEFT;
188 ins_type_counters[ (int)State.ins_type ]++;
194 do_parallel (ins1, ins2)
197 struct hash_entry *h1, *h2;
199 if ((d10v_debug & DEBUG_INSTRUCTION) != 0)
200 (*d10v_callback->printf_filtered) (d10v_callback, "do_parallel 0x%x || 0x%x\n", ins1, ins2);
202 h1 = lookup_hash (ins1, 0);
203 h2 = lookup_hash (ins2, 0);
205 if (h1->ops->exec_type == PARONLY)
207 get_operands (h1->ops, ins1);
208 State.ins_type = INS_LEFT;
209 ins_type_counters[ (int)State.ins_type ]++;
213 get_operands (h2->ops, ins2);
214 State.ins_type = INS_RIGHT;
218 else if (h2->ops->exec_type == PARONLY)
220 get_operands (h2->ops, ins2);
221 State.ins_type = INS_RIGHT;
222 ins_type_counters[ (int)State.ins_type ]++;
226 get_operands (h1->ops, ins1);
227 State.ins_type = INS_LEFT;
233 get_operands (h1->ops, ins1);
234 State.ins_type = INS_LEFT_PARALLEL;
235 ins_type_counters[ (int)State.ins_type ]++;
237 get_operands (h2->ops, ins2);
238 State.ins_type = INS_RIGHT_PARALLEL;
239 ins_type_counters[ (int)State.ins_type ]++;
256 State.imem = (uint8 *)calloc(1,1<<IMEM_SIZE);
257 State.dmem = (uint8 *)calloc(1,1<<DMEM_SIZE);
258 if (!State.imem || !State.dmem )
260 (*d10v_callback->printf_filtered) (d10v_callback, "Memory allocation failed.\n");
265 if ((d10v_debug & DEBUG_MEMSIZE) != 0)
267 (*d10v_callback->printf_filtered) (d10v_callback, "Allocated %d bytes instruction memory and\n",1<<IMEM_SIZE);
268 (*d10v_callback->printf_filtered) (d10v_callback, " %d bytes data memory.\n", 1<<DMEM_SIZE);
281 sim_write (addr, buffer, size)
283 unsigned char *buffer;
289 /* (*d10v_callback->printf_filtered) (d10v_callback, "sim_write %d bytes to 0x%x\n",size,addr); */
290 for (i = 0; i < size; i++)
292 State.imem[i+addr] = buffer[i];
302 struct hash_entry *h, *prev;
303 static int init_p = 0;
308 if (strcmp (args, "-t") == 0)
312 (*d10v_callback->printf_filtered) (d10v_callback, "ERROR: unsupported option(s): %s\n",args);
315 /* put all the opcodes in the hash table */
318 for (s = Simops; s->func; s++)
320 h = &hash_table[hash(s->opcode,s->format)];
322 /* go to the last entry in the chain */
328 h->next = calloc(1,sizeof(struct hash_entry));
333 h->opcode = s->opcode;
350 (*d10v_callback->printf_filtered) (d10v_callback, "sim_set_profile %d\n",n);
354 sim_set_profile_size (n)
357 (*d10v_callback->printf_filtered) (d10v_callback, "sim_set_profile_size %d\n",n);
361 sim_resume (step, siggnal)
368 /* (*d10v_callback->printf_filtered) (d10v_callback, "sim_resume (%d,%d) PC=0x%x\n",step,siggnal,PC); */
371 State.exception = SIGTRAP;
377 inst = RLW (PC << 2);
379 switch (inst & 0xC0000000)
382 /* long instruction */
383 do_long (inst & 0x3FFFFFFF);
387 do_2_short ( inst & 0x7FFF, (inst & 0x3FFF8000) >> 15, 0);
391 do_2_short ((inst & 0x3FFF8000) >> 15, inst & 0x7FFF, 1);
394 do_parallel ((inst & 0x3FFF8000) >> 15, inst & 0x7FFF);
398 if (State.RP && PC == RPT_E)
411 while (!State.exception);
430 long total = (ins_type_counters[ (int)INS_LONG ]
431 + ins_type_counters[ (int)INS_LEFT ]
432 + ins_type_counters[ (int)INS_LEFT_PARALLEL ]
433 + ins_type_counters[ (int)INS_RIGHT ]
434 + ins_type_counters[ (int)INS_RIGHT_PARALLEL ]);
436 sprintf (buf, "%ld", total);
439 (*d10v_callback->printf_filtered) (d10v_callback,
440 "executed %*ld instructions in the left container, %*ld parallel, %*ld nops\n",
441 size, ins_type_counters[ (int)INS_LEFT ] + ins_type_counters[ (int)INS_LEFT_PARALLEL ],
442 size, ins_type_counters[ (int)INS_LEFT_PARALLEL ],
445 (*d10v_callback->printf_filtered) (d10v_callback,
446 "executed %*ld instructions in the right container, %*ld parallel, %*ld nops\n",
447 size, ins_type_counters[ (int)INS_RIGHT ] + ins_type_counters[ (int)INS_RIGHT_PARALLEL ],
448 size, ins_type_counters[ (int)INS_RIGHT_PARALLEL ],
451 (*d10v_callback->printf_filtered) (d10v_callback,
452 "executed %*ld long instructions\n",
453 size, ins_type_counters[ (int)INS_LONG ]);
455 (*d10v_callback->printf_filtered) (d10v_callback,
456 "executed %*ld total instructions\n",
461 sim_create_inferior (start_address, argv, env)
462 SIM_ADDR start_address;
468 (*d10v_callback->printf_filtered) (d10v_callback, "sim_create_inferior: PC=0x%x\n", start_address);
470 PC = start_address >> 2;
484 /* printf ("sim_set_callbacks\n"); */
489 sim_stop_reason (reason, sigrc)
490 enum sim_stop *reason;
493 /* (*d10v_callback->printf_filtered) (d10v_callback, "sim_stop_reason: PC=0x%x\n",PC<<2); */
495 switch (State.exception)
497 case SIG_D10V_STOP: /* stop instruction */
498 *reason = sim_exited;
502 case SIG_D10V_EXIT: /* exit trap */
503 *reason = sim_exited;
504 *sigrc = State.regs[2];
507 default: /* some signal */
508 *reason = sim_stopped;
509 *sigrc = State.exception;
515 sim_fetch_register (rn, memory)
517 unsigned char *memory;
521 WRITE_64 (memory, State.a[rn-32]);
522 /* (*d10v_callback->printf_filtered) (d10v_callback, "sim_fetch_register %d 0x%llx\n",rn,State.a[rn-32]); */
526 WRITE_16 (memory, State.regs[rn]);
527 /* (*d10v_callback->printf_filtered) (d10v_callback, "sim_fetch_register %d 0x%x\n",rn,State.regs[rn]); */
532 sim_store_register (rn, memory)
534 unsigned char *memory;
538 State.a[rn-32] = READ_64 (memory) & MASK40;
539 /* (*d10v_callback->printf_filtered) (d10v_callback, "store: a%d=0x%llx\n",rn-32,State.a[rn-32]); */
543 State.regs[rn]= READ_16 (memory);
544 /* (*d10v_callback->printf_filtered) (d10v_callback, "store: r%d=0x%x\n",rn,State.regs[rn]); */
548 sim_read (addr, buffer, size)
550 unsigned char *buffer;
554 for (i = 0; i < size; i++)
556 buffer[i] = State.imem[addr + i];
565 (*d10v_callback->printf_filtered) (d10v_callback, "sim_do_command: %s\n",cmd);
569 sim_load (prog, from_tty)
573 /* Return nonzero so GDB will handle it. */