]> git.ipfire.org Git - thirdparty/binutils-gdb.git/blame - sim/m32r/traps-linux.c
Update Copyright year range in all files maintained by GDB.
[thirdparty/binutils-gdb.git] / sim / m32r / traps-linux.c
CommitLineData
6edf0760 1/* m32r exception, interrupt, and trap (EIT) support
ecd75fc8 2 Copyright (C) 1998-2014 Free Software Foundation, Inc.
6edf0760
NC
3 Contributed by Renesas.
4
5 This file is part of GDB, the GNU debugger.
6
7 This program is free software; you can redistribute it and/or modify
8 it under the terms of the GNU General Public License as published by
4744ac1b
JB
9 the Free Software Foundation; either version 3 of the License, or
10 (at your option) any later version.
6edf0760
NC
11
12 This program is distributed in the hope that it will be useful,
13 but WITHOUT ANY WARRANTY; without even the implied warranty of
14 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
15 GNU General Public License for more details.
16
4744ac1b
JB
17 You should have received a copy of the GNU General Public License
18 along with this program. If not, see <http://www.gnu.org/licenses/>. */
6edf0760
NC
19
20#include "sim-main.h"
21#include "syscall.h"
22#include "targ-vals.h"
23#include <dirent.h>
24#include <errno.h>
25#include <fcntl.h>
26#include <time.h>
27#include <unistd.h>
28#include <utime.h>
29#include <sys/mman.h>
30#include <sys/poll.h>
31#include <sys/resource.h>
32#include <sys/sysinfo.h>
33#include <sys/stat.h>
34#include <sys/time.h>
35#include <sys/timeb.h>
36#include <sys/timex.h>
37#include <sys/types.h>
38#include <sys/uio.h>
39#include <sys/utsname.h>
40#include <sys/vfs.h>
6edf0760
NC
41#include <linux/sysctl.h>
42#include <linux/types.h>
43#include <linux/unistd.h>
44
45#define TRAP_ELF_SYSCALL 0
46#define TRAP_LINUX_SYSCALL 2
47#define TRAP_FLUSH_CACHE 12
48
49/* The semantic code invokes this for invalid (unrecognized) instructions. */
50
51SEM_PC
52sim_engine_invalid_insn (SIM_CPU *current_cpu, IADDR cia, SEM_PC vpc)
53{
54 SIM_DESC sd = CPU_STATE (current_cpu);
55
56#if 0
57 if (STATE_ENVIRONMENT (sd) == OPERATING_ENVIRONMENT)
58 {
59 h_bsm_set (current_cpu, h_sm_get (current_cpu));
60 h_bie_set (current_cpu, h_ie_get (current_cpu));
61 h_bcond_set (current_cpu, h_cond_get (current_cpu));
62 /* sm not changed */
63 h_ie_set (current_cpu, 0);
64 h_cond_set (current_cpu, 0);
65
66 h_bpc_set (current_cpu, cia);
67
68 sim_engine_restart (CPU_STATE (current_cpu), current_cpu, NULL,
69 EIT_RSVD_INSN_ADDR);
70 }
71 else
72#endif
73 sim_engine_halt (sd, current_cpu, NULL, cia, sim_stopped, SIM_SIGILL);
74 return vpc;
75}
76
77/* Process an address exception. */
78
79void
80m32r_core_signal (SIM_DESC sd, SIM_CPU *current_cpu, sim_cia cia,
81 unsigned int map, int nr_bytes, address_word addr,
82 transfer_type transfer, sim_core_signals sig)
83{
84 if (STATE_ENVIRONMENT (sd) == OPERATING_ENVIRONMENT)
85 {
86 m32rbf_h_cr_set (current_cpu, H_CR_BBPC,
87 m32rbf_h_cr_get (current_cpu, H_CR_BPC));
88 if (MACH_NUM (CPU_MACH (current_cpu)) == MACH_M32R)
89 {
90 m32rbf_h_bpsw_set (current_cpu, m32rbf_h_psw_get (current_cpu));
91 /* sm not changed */
92 m32rbf_h_psw_set (current_cpu, m32rbf_h_psw_get (current_cpu) & 0x80);
93 }
94 else if (MACH_NUM (CPU_MACH (current_cpu)) == MACH_M32RX)
95 {
96 m32rxf_h_bpsw_set (current_cpu, m32rxf_h_psw_get (current_cpu));
97 /* sm not changed */
98 m32rxf_h_psw_set (current_cpu, m32rxf_h_psw_get (current_cpu) & 0x80);
99 }
100 else
101 {
102 m32r2f_h_bpsw_set (current_cpu, m32r2f_h_psw_get (current_cpu));
103 /* sm not changed */
104 m32r2f_h_psw_set (current_cpu, m32r2f_h_psw_get (current_cpu) & 0x80);
105 }
106 m32rbf_h_cr_set (current_cpu, H_CR_BPC, cia);
107
108 sim_engine_restart (CPU_STATE (current_cpu), current_cpu, NULL,
109 EIT_ADDR_EXCP_ADDR);
110 }
111 else
112 sim_core_signal (sd, current_cpu, cia, map, nr_bytes, addr,
113 transfer, sig);
114}
115\f
116/* Read/write functions for system call interface. */
117
118static int
119syscall_read_mem (host_callback *cb, struct cb_syscall *sc,
120 unsigned long taddr, char *buf, int bytes)
121{
122 SIM_DESC sd = (SIM_DESC) sc->p1;
123 SIM_CPU *cpu = (SIM_CPU *) sc->p2;
124
125 return sim_core_read_buffer (sd, cpu, read_map, buf, taddr, bytes);
126}
127
128static int
129syscall_write_mem (host_callback *cb, struct cb_syscall *sc,
130 unsigned long taddr, const char *buf, int bytes)
131{
132 SIM_DESC sd = (SIM_DESC) sc->p1;
133 SIM_CPU *cpu = (SIM_CPU *) sc->p2;
134
135 return sim_core_write_buffer (sd, cpu, write_map, buf, taddr, bytes);
136}
137
138/* Translate target's address to host's address. */
139
140static void *
141t2h_addr (host_callback *cb, struct cb_syscall *sc,
142 unsigned long taddr)
143{
6edf0760
NC
144 void *addr;
145 SIM_DESC sd = (SIM_DESC) sc->p1;
146 SIM_CPU *cpu = (SIM_CPU *) sc->p2;
147
148 if (taddr == 0)
149 return NULL;
150
151 return sim_core_trans_addr (sd, cpu, read_map, taddr);
152}
153
154static unsigned int
155conv_endian (unsigned int tvalue)
156{
157 unsigned int hvalue;
158 unsigned int t1, t2, t3, t4;
159
160 if (CURRENT_HOST_BYTE_ORDER == LITTLE_ENDIAN)
161 {
162 t1 = tvalue & 0xff000000;
163 t2 = tvalue & 0x00ff0000;
164 t3 = tvalue & 0x0000ff00;
165 t4 = tvalue & 0x000000ff;
166
167 hvalue = t1 >> 24;
168 hvalue += t2 >> 8;
169 hvalue += t3 << 8;
170 hvalue += t4 << 24;
171 }
172 else
173 hvalue = tvalue;
174
175 return hvalue;
176}
177
178static unsigned short
179conv_endian16 (unsigned short tvalue)
180{
181 unsigned short hvalue;
182 unsigned short t1, t2;
183
184 if (CURRENT_HOST_BYTE_ORDER == LITTLE_ENDIAN)
185 {
186 t1 = tvalue & 0xff00;
187 t2 = tvalue & 0x00ff;
188
189 hvalue = t1 >> 8;
190 hvalue += t2 << 8;
191 }
192 else
193 hvalue = tvalue;
194
195 return hvalue;
196}
197
198static void
199translate_endian(void *addr, size_t size)
200{
201 unsigned int *p = (unsigned int *) addr;
202 int i;
203
204 for (i = 0; i <= size - 4; i += 4,p++)
205 *p = conv_endian(*p);
206
207 if (i <= size - 2)
208 *((unsigned short *) p) = conv_endian16(*((unsigned short *) p));
209}
210
211/* Trap support.
212 The result is the pc address to continue at.
213 Preprocessing like saving the various registers has already been done. */
214
215USI
216m32r_trap (SIM_CPU *current_cpu, PCADDR pc, int num)
217{
218 SIM_DESC sd = CPU_STATE (current_cpu);
219 host_callback *cb = STATE_CALLBACK (sd);
220
221#ifdef SIM_HAVE_BREAKPOINTS
222 /* Check for breakpoints "owned" by the simulator first, regardless
223 of --environment. */
224 if (num == TRAP_BREAKPOINT)
225 {
226 /* First try sim-break.c. If it's a breakpoint the simulator "owns"
227 it doesn't return. Otherwise it returns and let's us try. */
228 sim_handle_breakpoint (sd, current_cpu, pc);
229 /* Fall through. */
230 }
231#endif
232
233 switch (num)
234 {
235 case TRAP_ELF_SYSCALL :
236 {
237 CB_SYSCALL s;
238
239 CB_SYSCALL_INIT (&s);
240 s.func = m32rbf_h_gr_get (current_cpu, 0);
241 s.arg1 = m32rbf_h_gr_get (current_cpu, 1);
242 s.arg2 = m32rbf_h_gr_get (current_cpu, 2);
243 s.arg3 = m32rbf_h_gr_get (current_cpu, 3);
244
245 if (s.func == TARGET_SYS_exit)
246 {
247 sim_engine_halt (sd, current_cpu, NULL, pc, sim_exited, s.arg1);
248 }
249
250 s.p1 = (PTR) sd;
251 s.p2 = (PTR) current_cpu;
252 s.read_mem = syscall_read_mem;
253 s.write_mem = syscall_write_mem;
254 cb_syscall (cb, &s);
255 m32rbf_h_gr_set (current_cpu, 2, s.errcode);
256 m32rbf_h_gr_set (current_cpu, 0, s.result);
257 m32rbf_h_gr_set (current_cpu, 1, s.result2);
258 break;
259 }
260
261 case TRAP_LINUX_SYSCALL :
262 {
263 CB_SYSCALL s;
264 unsigned int func, arg1, arg2, arg3, arg4, arg5, arg6, arg7;
265 int result, result2, errcode;
266
267 if (STATE_ENVIRONMENT (sd) == OPERATING_ENVIRONMENT)
268 {
269 /* The new pc is the trap vector entry.
270 We assume there's a branch there to some handler.
271 Use cr5 as EVB (EIT Vector Base) register. */
272 USI new_pc = m32rbf_h_cr_get (current_cpu, 5) + 0x40 + num * 4;
273 return new_pc;
274 }
275
276 func = m32rbf_h_gr_get (current_cpu, 7);
277 arg1 = m32rbf_h_gr_get (current_cpu, 0);
278 arg2 = m32rbf_h_gr_get (current_cpu, 1);
279 arg3 = m32rbf_h_gr_get (current_cpu, 2);
280 arg4 = m32rbf_h_gr_get (current_cpu, 3);
281 arg5 = m32rbf_h_gr_get (current_cpu, 4);
282 arg6 = m32rbf_h_gr_get (current_cpu, 5);
283 arg7 = m32rbf_h_gr_get (current_cpu, 6);
284
285 CB_SYSCALL_INIT (&s);
286 s.func = func;
287 s.arg1 = arg1;
288 s.arg2 = arg2;
289 s.arg3 = arg3;
290
291 s.p1 = (PTR) sd;
292 s.p2 = (PTR) current_cpu;
293 s.read_mem = syscall_read_mem;
294 s.write_mem = syscall_write_mem;
295
296 result = 0;
297 result2 = 0;
298 errcode = 0;
299
300 switch (func)
301 {
302 case __NR_exit:
303 sim_engine_halt (sd, current_cpu, NULL, pc, sim_exited, arg1);
304 break;
305
306 case __NR_read:
307 result = read(arg1, t2h_addr(cb, &s, arg2), arg3);
308 errcode = errno;
309 break;
310
311 case __NR_write:
312 result = write(arg1, t2h_addr(cb, &s, arg2), arg3);
313 errcode = errno;
314 break;
315
316 case __NR_open:
317 result = open((char *) t2h_addr(cb, &s, arg1), arg2, arg3);
318 errcode = errno;
319 break;
320
321 case __NR_close:
322 result = close(arg1);
323 errcode = errno;
324 break;
325
326 case __NR_creat:
327 result = creat((char *) t2h_addr(cb, &s, arg1), arg2);
328 errcode = errno;
329 break;
330
331 case __NR_link:
332 result = link((char *) t2h_addr(cb, &s, arg1),
333 (char *) t2h_addr(cb, &s, arg2));
334 errcode = errno;
335 break;
336
337 case __NR_unlink:
338 result = unlink((char *) t2h_addr(cb, &s, arg1));
339 errcode = errno;
340 break;
341
342 case __NR_chdir:
343 result = chdir((char *) t2h_addr(cb, &s, arg1));
344 errcode = errno;
345 break;
346
347 case __NR_time:
348 {
349 time_t t;
350
351 if (arg1 == 0)
352 {
353 result = (int) time(NULL);
354 errcode = errno;
355 }
356 else
357 {
358 result = (int) time(&t);
359 errcode = errno;
360
361 if (result != 0)
362 break;
363
364 translate_endian((void *) &t, sizeof(t));
365 if ((s.write_mem) (cb, &s, arg1, (char *) &t, sizeof(t)) != sizeof(t))
366 {
367 result = -1;
368 errcode = EINVAL;
369 }
370 }
371 }
372 break;
373
374 case __NR_mknod:
375 result = mknod((char *) t2h_addr(cb, &s, arg1),
376 (mode_t) arg2, (dev_t) arg3);
377 errcode = errno;
378 break;
379
380 case __NR_chmod:
381 result = chmod((char *) t2h_addr(cb, &s, arg1), (mode_t) arg2);
382 errcode = errno;
383 break;
384
19e64aa9 385 case __NR_lchown32:
6edf0760
NC
386 case __NR_lchown:
387 result = lchown((char *) t2h_addr(cb, &s, arg1),
388 (uid_t) arg2, (gid_t) arg3);
389 errcode = errno;
390 break;
391
392 case __NR_lseek:
393 result = (int) lseek(arg1, (off_t) arg2, arg3);
394 errcode = errno;
395 break;
396
397 case __NR_getpid:
398 result = getpid();
399 errcode = errno;
400 break;
401
19e64aa9 402 case __NR_getuid32:
6edf0760
NC
403 case __NR_getuid:
404 result = getuid();
405 errcode = errno;
406 break;
407
408 case __NR_utime:
409 {
410 struct utimbuf buf;
411
412 if (arg2 == 0)
413 {
414 result = utime((char *) t2h_addr(cb, &s, arg1), NULL);
415 errcode = errno;
416 }
417 else
418 {
419 buf = *((struct utimbuf *) t2h_addr(cb, &s, arg2));
420 translate_endian((void *) &buf, sizeof(buf));
421 result = utime((char *) t2h_addr(cb, &s, arg1), &buf);
422 errcode = errno;
423 }
424 }
425 break;
426
427 case __NR_access:
428 result = access((char *) t2h_addr(cb, &s, arg1), arg2);
429 errcode = errno;
430 break;
431
432 case __NR_ftime:
433 {
434 struct timeb t;
435
436 result = ftime(&t);
437 errcode = errno;
438
439 if (result != 0)
440 break;
441
442 t.time = conv_endian(t.time);
443 t.millitm = conv_endian16(t.millitm);
444 t.timezone = conv_endian16(t.timezone);
445 t.dstflag = conv_endian16(t.dstflag);
446 if ((s.write_mem) (cb, &s, arg1, (char *) &t, sizeof(t))
447 != sizeof(t))
448 {
449 result = -1;
450 errcode = EINVAL;
451 }
452 }
453
454 case __NR_sync:
455 sync();
456 result = 0;
457 break;
458
459 case __NR_rename:
460 result = rename((char *) t2h_addr(cb, &s, arg1),
461 (char *) t2h_addr(cb, &s, arg2));
462 errcode = errno;
463 break;
464
465 case __NR_mkdir:
466 result = mkdir((char *) t2h_addr(cb, &s, arg1), arg2);
467 errcode = errno;
468 break;
469
470 case __NR_rmdir:
471 result = rmdir((char *) t2h_addr(cb, &s, arg1));
472 errcode = errno;
473 break;
474
475 case __NR_dup:
476 result = dup(arg1);
477 errcode = errno;
478 break;
479
480 case __NR_brk:
481 result = brk((void *) arg1);
482 errcode = errno;
483 //result = arg1;
484 break;
485
19e64aa9 486 case __NR_getgid32:
6edf0760
NC
487 case __NR_getgid:
488 result = getgid();
489 errcode = errno;
490 break;
491
19e64aa9 492 case __NR_geteuid32:
6edf0760
NC
493 case __NR_geteuid:
494 result = geteuid();
495 errcode = errno;
496 break;
497
19e64aa9 498 case __NR_getegid32:
6edf0760
NC
499 case __NR_getegid:
500 result = getegid();
501 errcode = errno;
502 break;
503
504 case __NR_ioctl:
505 result = ioctl(arg1, arg2, arg3);
506 errcode = errno;
507 break;
508
509 case __NR_fcntl:
510 result = fcntl(arg1, arg2, arg3);
511 errcode = errno;
512 break;
513
6edf0760
NC
514 case __NR_dup2:
515 result = dup2(arg1, arg2);
516 errcode = errno;
517 break;
518
519 case __NR_getppid:
520 result = getppid();
521 errcode = errno;
522 break;
523
524 case __NR_getpgrp:
525 result = getpgrp();
526 errcode = errno;
527 break;
528
529 case __NR_getrlimit:
530 {
531 struct rlimit rlim;
532
533 result = getrlimit(arg1, &rlim);
534 errcode = errno;
535
536 if (result != 0)
537 break;
538
539 translate_endian((void *) &rlim, sizeof(rlim));
540 if ((s.write_mem) (cb, &s, arg2, (char *) &rlim, sizeof(rlim))
541 != sizeof(rlim))
542 {
543 result = -1;
544 errcode = EINVAL;
545 }
546 }
547 break;
548
549 case __NR_getrusage:
550 {
551 struct rusage usage;
552
553 result = getrusage(arg1, &usage);
554 errcode = errno;
555
556 if (result != 0)
557 break;
558
559 translate_endian((void *) &usage, sizeof(usage));
560 if ((s.write_mem) (cb, &s, arg2, (char *) &usage, sizeof(usage))
561 != sizeof(usage))
562 {
563 result = -1;
564 errcode = EINVAL;
565 }
566 }
567 break;
568
569 case __NR_gettimeofday:
570 {
571 struct timeval tv;
572 struct timezone tz;
573
574 result = gettimeofday(&tv, &tz);
575 errcode = errno;
576
577 if (result != 0)
578 break;
579
580 translate_endian((void *) &tv, sizeof(tv));
581 if ((s.write_mem) (cb, &s, arg1, (char *) &tv, sizeof(tv))
582 != sizeof(tv))
583 {
584 result = -1;
585 errcode = EINVAL;
586 }
587
588 translate_endian((void *) &tz, sizeof(tz));
589 if ((s.write_mem) (cb, &s, arg2, (char *) &tz, sizeof(tz))
590 != sizeof(tz))
591 {
592 result = -1;
593 errcode = EINVAL;
594 }
595 }
596 break;
597
19e64aa9 598 case __NR_getgroups32:
6edf0760
NC
599 case __NR_getgroups:
600 {
601 gid_t *list;
602
603 if (arg1 > 0)
604 list = (gid_t *) malloc(arg1 * sizeof(gid_t));
605
606 result = getgroups(arg1, list);
607 errcode = errno;
608
609 if (result != 0)
610 break;
611
612 translate_endian((void *) list, arg1 * sizeof(gid_t));
613 if (arg1 > 0)
614 if ((s.write_mem) (cb, &s, arg2, (char *) list, arg1 * sizeof(gid_t))
615 != arg1 * sizeof(gid_t))
616 {
617 result = -1;
618 errcode = EINVAL;
619 }
620 }
621 break;
622
623 case __NR_select:
624 {
625 int n;
626 fd_set readfds;
627 fd_set *treadfdsp;
628 fd_set *hreadfdsp;
629 fd_set writefds;
630 fd_set *twritefdsp;
631 fd_set *hwritefdsp;
632 fd_set exceptfds;
633 fd_set *texceptfdsp;
634 fd_set *hexceptfdsp;
635 struct timeval *ttimeoutp;
636 struct timeval timeout;
637
638 n = arg1;
639
640 treadfdsp = (fd_set *) arg2;
641 if (treadfdsp != NULL)
642 {
643 readfds = *((fd_set *) t2h_addr(cb, &s, (unsigned int) treadfdsp));
644 translate_endian((void *) &readfds, sizeof(readfds));
645 hreadfdsp = &readfds;
646 }
647 else
648 hreadfdsp = NULL;
649
650 twritefdsp = (fd_set *) arg3;
651 if (twritefdsp != NULL)
652 {
653 writefds = *((fd_set *) t2h_addr(cb, &s, (unsigned int) twritefdsp));
654 translate_endian((void *) &writefds, sizeof(writefds));
655 hwritefdsp = &writefds;
656 }
657 else
658 hwritefdsp = NULL;
659
660 texceptfdsp = (fd_set *) arg4;
661 if (texceptfdsp != NULL)
662 {
663 exceptfds = *((fd_set *) t2h_addr(cb, &s, (unsigned int) texceptfdsp));
664 translate_endian((void *) &exceptfds, sizeof(exceptfds));
665 hexceptfdsp = &exceptfds;
666 }
667 else
668 hexceptfdsp = NULL;
669
670 ttimeoutp = (struct timeval *) arg5;
671 timeout = *((struct timeval *) t2h_addr(cb, &s, (unsigned int) ttimeoutp));
672 translate_endian((void *) &timeout, sizeof(timeout));
673
674 result = select(n, hreadfdsp, hwritefdsp, hexceptfdsp, &timeout);
675 errcode = errno;
676
677 if (result != 0)
678 break;
679
680 if (treadfdsp != NULL)
681 {
682 translate_endian((void *) &readfds, sizeof(readfds));
683 if ((s.write_mem) (cb, &s, (unsigned long) treadfdsp,
684 (char *) &readfds, sizeof(readfds)) != sizeof(readfds))
685 {
686 result = -1;
687 errcode = EINVAL;
688 }
689 }
690
691 if (twritefdsp != NULL)
692 {
693 translate_endian((void *) &writefds, sizeof(writefds));
694 if ((s.write_mem) (cb, &s, (unsigned long) twritefdsp,
695 (char *) &writefds, sizeof(writefds)) != sizeof(writefds))
696 {
697 result = -1;
698 errcode = EINVAL;
699 }
700 }
701
702 if (texceptfdsp != NULL)
703 {
704 translate_endian((void *) &exceptfds, sizeof(exceptfds));
705 if ((s.write_mem) (cb, &s, (unsigned long) texceptfdsp,
706 (char *) &exceptfds, sizeof(exceptfds)) != sizeof(exceptfds))
707 {
708 result = -1;
709 errcode = EINVAL;
710 }
711 }
712
713 translate_endian((void *) &timeout, sizeof(timeout));
714 if ((s.write_mem) (cb, &s, (unsigned long) ttimeoutp,
715 (char *) &timeout, sizeof(timeout)) != sizeof(timeout))
716 {
717 result = -1;
718 errcode = EINVAL;
719 }
720 }
721 break;
722
723 case __NR_symlink:
724 result = symlink((char *) t2h_addr(cb, &s, arg1),
725 (char *) t2h_addr(cb, &s, arg2));
726 errcode = errno;
727 break;
728
729 case __NR_readlink:
730 result = readlink((char *) t2h_addr(cb, &s, arg1),
731 (char *) t2h_addr(cb, &s, arg2),
732 arg3);
733 errcode = errno;
734 break;
735
736 case __NR_readdir:
737 result = (int) readdir((DIR *) t2h_addr(cb, &s, arg1));
738 errcode = errno;
739 break;
740
741#if 0
742 case __NR_mmap:
743 {
744 result = (int) mmap((void *) t2h_addr(cb, &s, arg1),
745 arg2, arg3, arg4, arg5, arg6);
746 errcode = errno;
747
748 if (errno == 0)
749 {
750 sim_core_attach (sd, NULL,
751 0, access_read_write_exec, 0,
752 result, arg2, 0, NULL, NULL);
753 }
754 }
755 break;
756#endif
19e64aa9
KI
757 case __NR_mmap2:
758 {
759 void *addr;
760 size_t len;
761 int prot, flags, fildes;
762 off_t off;
763
764 addr = (void *) t2h_addr(cb, &s, arg1);
765 len = arg2;
766 prot = arg3;
767 flags = arg4;
768 fildes = arg5;
769 off = arg6 << 12;
770
771 result = (int) mmap(addr, len, prot, flags, fildes, off);
772 errcode = errno;
773 if (result != -1)
774 {
775 char c;
776 if (sim_core_read_buffer (sd, NULL, read_map, &c, result, 1) == 0)
777 sim_core_attach (sd, NULL,
778 0, access_read_write_exec, 0,
779 result, len, 0, NULL, NULL);
780 }
781 }
782 break;
783
6edf0760
NC
784 case __NR_mmap:
785 {
786 void *addr;
787 size_t len;
788 int prot, flags, fildes;
789 off_t off;
790
791 addr = *((void **) t2h_addr(cb, &s, arg1));
792 len = *((size_t *) t2h_addr(cb, &s, arg1 + 4));
793 prot = *((int *) t2h_addr(cb, &s, arg1 + 8));
794 flags = *((int *) t2h_addr(cb, &s, arg1 + 12));
795 fildes = *((int *) t2h_addr(cb, &s, arg1 + 16));
796 off = *((off_t *) t2h_addr(cb, &s, arg1 + 20));
797
798 addr = (void *) conv_endian((unsigned int) addr);
799 len = conv_endian(len);
800 prot = conv_endian(prot);
801 flags = conv_endian(flags);
802 fildes = conv_endian(fildes);
803 off = conv_endian(off);
804
805 //addr = (void *) t2h_addr(cb, &s, (unsigned int) addr);
806 result = (int) mmap(addr, len, prot, flags, fildes, off);
807 errcode = errno;
808
809 //if (errno == 0)
810 if (result != -1)
811 {
812 char c;
813 if (sim_core_read_buffer (sd, NULL, read_map, &c, result, 1) == 0)
814 sim_core_attach (sd, NULL,
815 0, access_read_write_exec, 0,
816 result, len, 0, NULL, NULL);
817 }
818 }
819 break;
820
821 case __NR_munmap:
822 {
823 result = munmap((void *)arg1, arg2);
824 errcode = errno;
825 if (result != -1)
826 {
827 sim_core_detach (sd, NULL, 0, arg2, result);
828 }
829 }
830 break;
831
832 case __NR_truncate:
833 result = truncate((char *) t2h_addr(cb, &s, arg1), arg2);
834 errcode = errno;
835 break;
836
837 case __NR_ftruncate:
838 result = ftruncate(arg1, arg2);
839 errcode = errno;
840 break;
841
842 case __NR_fchmod:
843 result = fchmod(arg1, arg2);
844 errcode = errno;
845 break;
846
19e64aa9 847 case __NR_fchown32:
6edf0760
NC
848 case __NR_fchown:
849 result = fchown(arg1, arg2, arg3);
850 errcode = errno;
851 break;
852
853 case __NR_statfs:
854 {
855 struct statfs statbuf;
856
857 result = statfs((char *) t2h_addr(cb, &s, arg1), &statbuf);
858 errcode = errno;
859
860 if (result != 0)
861 break;
862
863 translate_endian((void *) &statbuf, sizeof(statbuf));
864 if ((s.write_mem) (cb, &s, arg2, (char *) &statbuf, sizeof(statbuf))
865 != sizeof(statbuf))
866 {
867 result = -1;
868 errcode = EINVAL;
869 }
870 }
871 break;
872
873 case __NR_fstatfs:
874 {
875 struct statfs statbuf;
876
877 result = fstatfs(arg1, &statbuf);
878 errcode = errno;
879
880 if (result != 0)
881 break;
882
883 translate_endian((void *) &statbuf, sizeof(statbuf));
884 if ((s.write_mem) (cb, &s, arg2, (char *) &statbuf, sizeof(statbuf))
885 != sizeof(statbuf))
886 {
887 result = -1;
888 errcode = EINVAL;
889 }
890 }
891 break;
892
893 case __NR_syslog:
894 result = syslog(arg1, (char *) t2h_addr(cb, &s, arg2));
895 errcode = errno;
896 break;
897
898 case __NR_setitimer:
899 {
900 struct itimerval value, ovalue;
901
902 value = *((struct itimerval *) t2h_addr(cb, &s, arg2));
903 translate_endian((void *) &value, sizeof(value));
904
905 if (arg2 == 0)
906 {
907 result = setitimer(arg1, &value, NULL);
908 errcode = errno;
909 }
910 else
911 {
912 result = setitimer(arg1, &value, &ovalue);
913 errcode = errno;
914
915 if (result != 0)
916 break;
917
918 translate_endian((void *) &ovalue, sizeof(ovalue));
919 if ((s.write_mem) (cb, &s, arg3, (char *) &ovalue, sizeof(ovalue))
920 != sizeof(ovalue))
921 {
922 result = -1;
923 errcode = EINVAL;
924 }
925 }
926 }
927 break;
928
929 case __NR_getitimer:
930 {
931 struct itimerval value;
932
933 result = getitimer(arg1, &value);
934 errcode = errno;
935
936 if (result != 0)
937 break;
938
939 translate_endian((void *) &value, sizeof(value));
940 if ((s.write_mem) (cb, &s, arg2, (char *) &value, sizeof(value))
941 != sizeof(value))
942 {
943 result = -1;
944 errcode = EINVAL;
945 }
946 }
947 break;
948
949 case __NR_stat:
950 {
951 char *buf;
952 int buflen;
953 struct stat statbuf;
954
955 result = stat((char *) t2h_addr(cb, &s, arg1), &statbuf);
956 errcode = errno;
957 if (result < 0)
958 break;
959
960 buflen = cb_host_to_target_stat (cb, NULL, NULL);
961 buf = xmalloc (buflen);
962 if (cb_host_to_target_stat (cb, &statbuf, buf) != buflen)
963 {
964 /* The translation failed. This is due to an internal
965 host program error, not the target's fault. */
966 free (buf);
967 result = -1;
968 errcode = ENOSYS;
969 break;
970 }
971 if ((s.write_mem) (cb, &s, arg2, buf, buflen) != buflen)
972 {
973 free (buf);
974 result = -1;
975 errcode = EINVAL;
976 break;
977 }
978 free (buf);
979 }
980 break;
981
982 case __NR_lstat:
983 {
984 char *buf;
985 int buflen;
986 struct stat statbuf;
987
988 result = lstat((char *) t2h_addr(cb, &s, arg1), &statbuf);
989 errcode = errno;
990 if (result < 0)
991 break;
992
993 buflen = cb_host_to_target_stat (cb, NULL, NULL);
994 buf = xmalloc (buflen);
995 if (cb_host_to_target_stat (cb, &statbuf, buf) != buflen)
996 {
997 /* The translation failed. This is due to an internal
998 host program error, not the target's fault. */
999 free (buf);
1000 result = -1;
1001 errcode = ENOSYS;
1002 break;
1003 }
1004 if ((s.write_mem) (cb, &s, arg2, buf, buflen) != buflen)
1005 {
1006 free (buf);
1007 result = -1;
1008 errcode = EINVAL;
1009 break;
1010 }
1011 free (buf);
1012 }
1013 break;
1014
1015 case __NR_fstat:
1016 {
1017 char *buf;
1018 int buflen;
1019 struct stat statbuf;
1020
1021 result = fstat(arg1, &statbuf);
1022 errcode = errno;
1023 if (result < 0)
1024 break;
1025
1026 buflen = cb_host_to_target_stat (cb, NULL, NULL);
1027 buf = xmalloc (buflen);
1028 if (cb_host_to_target_stat (cb, &statbuf, buf) != buflen)
1029 {
1030 /* The translation failed. This is due to an internal
1031 host program error, not the target's fault. */
1032 free (buf);
1033 result = -1;
1034 errcode = ENOSYS;
1035 break;
1036 }
1037 if ((s.write_mem) (cb, &s, arg2, buf, buflen) != buflen)
1038 {
1039 free (buf);
1040 result = -1;
1041 errcode = EINVAL;
1042 break;
1043 }
1044 free (buf);
1045 }
1046 break;
1047
1048 case __NR_sysinfo:
1049 {
1050 struct sysinfo info;
1051
1052 result = sysinfo(&info);
1053 errcode = errno;
1054
1055 if (result != 0)
1056 break;
1057
1058 info.uptime = conv_endian(info.uptime);
1059 info.loads[0] = conv_endian(info.loads[0]);
1060 info.loads[1] = conv_endian(info.loads[1]);
1061 info.loads[2] = conv_endian(info.loads[2]);
1062 info.totalram = conv_endian(info.totalram);
1063 info.freeram = conv_endian(info.freeram);
1064 info.sharedram = conv_endian(info.sharedram);
1065 info.bufferram = conv_endian(info.bufferram);
1066 info.totalswap = conv_endian(info.totalswap);
1067 info.freeswap = conv_endian(info.freeswap);
1068 info.procs = conv_endian16(info.procs);
1069#if LINUX_VERSION_CODE >= 0x20400
1070 info.totalhigh = conv_endian(info.totalhigh);
1071 info.freehigh = conv_endian(info.freehigh);
1072 info.mem_unit = conv_endian(info.mem_unit);
1073#endif
1074 if ((s.write_mem) (cb, &s, arg1, (char *) &info, sizeof(info))
1075 != sizeof(info))
1076 {
1077 result = -1;
1078 errcode = EINVAL;
1079 }
1080 }
1081 break;
1082
1083#if 0
1084 case __NR_ipc:
1085 {
1086 result = ipc(arg1, arg2, arg3, arg4,
1087 (void *) t2h_addr(cb, &s, arg5), arg6);
1088 errcode = errno;
1089 }
1090 break;
1091#endif
1092
1093 case __NR_fsync:
1094 result = fsync(arg1);
1095 errcode = errno;
1096 break;
1097
1098 case __NR_uname:
1099 /* utsname contains only arrays of char, so it is not necessary
1100 to translate endian. */
1101 result = uname((struct utsname *) t2h_addr(cb, &s, arg1));
1102 errcode = errno;
1103 break;
1104
1105 case __NR_adjtimex:
1106 {
1107 struct timex buf;
1108
1109 result = adjtimex(&buf);
1110 errcode = errno;
1111
1112 if (result != 0)
1113 break;
1114
1115 translate_endian((void *) &buf, sizeof(buf));
1116 if ((s.write_mem) (cb, &s, arg1, (char *) &buf, sizeof(buf))
1117 != sizeof(buf))
1118 {
1119 result = -1;
1120 errcode = EINVAL;
1121 }
1122 }
1123 break;
1124
1125 case __NR_mprotect:
1126 result = mprotect((void *) arg1, arg2, arg3);
1127 errcode = errno;
1128 break;
1129
6edf0760
NC
1130 case __NR_fchdir:
1131 result = fchdir(arg1);
1132 errcode = errno;
1133 break;
1134
19e64aa9 1135 case __NR_setfsuid32:
6edf0760
NC
1136 case __NR_setfsuid:
1137 result = setfsuid(arg1);
1138 errcode = errno;
1139 break;
1140
19e64aa9 1141 case __NR_setfsgid32:
6edf0760
NC
1142 case __NR_setfsgid:
1143 result = setfsgid(arg1);
1144 errcode = errno;
1145 break;
1146
1147#if 0
1148 case __NR__llseek:
1149 {
1150 loff_t buf;
1151
1152 result = _llseek(arg1, arg2, arg3, &buf, arg5);
1153 errcode = errno;
1154
1155 if (result != 0)
1156 break;
1157
1158 translate_endian((void *) &buf, sizeof(buf));
1159 if ((s.write_mem) (cb, &s, t2h_addr(cb, &s, arg4),
1160 (char *) &buf, sizeof(buf)) != sizeof(buf))
1161 {
1162 result = -1;
1163 errcode = EINVAL;
1164 }
1165 }
1166 break;
1167
1168 case __NR_getdents:
1169 {
1170 struct dirent dir;
1171
1172 result = getdents(arg1, &dir, arg3);
1173 errcode = errno;
1174
1175 if (result != 0)
1176 break;
1177
1178 dir.d_ino = conv_endian(dir.d_ino);
1179 dir.d_off = conv_endian(dir.d_off);
1180 dir.d_reclen = conv_endian16(dir.d_reclen);
1181 if ((s.write_mem) (cb, &s, arg2, (char *) &dir, sizeof(dir))
1182 != sizeof(dir))
1183 {
1184 result = -1;
1185 errcode = EINVAL;
1186 }
1187 }
1188 break;
1189#endif
1190
1191 case __NR_flock:
1192 result = flock(arg1, arg2);
1193 errcode = errno;
1194 break;
1195
1196 case __NR_msync:
1197 result = msync((void *) arg1, arg2, arg3);
1198 errcode = errno;
1199 break;
1200
1201 case __NR_readv:
1202 {
1203 struct iovec vector;
1204
1205 vector = *((struct iovec *) t2h_addr(cb, &s, arg2));
1206 translate_endian((void *) &vector, sizeof(vector));
1207
1208 result = readv(arg1, &vector, arg3);
1209 errcode = errno;
1210 }
1211 break;
1212
1213 case __NR_writev:
1214 {
1215 struct iovec vector;
1216
1217 vector = *((struct iovec *) t2h_addr(cb, &s, arg2));
1218 translate_endian((void *) &vector, sizeof(vector));
1219
1220 result = writev(arg1, &vector, arg3);
1221 errcode = errno;
1222 }
1223 break;
1224
1225 case __NR_fdatasync:
1226 result = fdatasync(arg1);
1227 errcode = errno;
1228 break;
1229
1230 case __NR_mlock:
1231 result = mlock((void *) t2h_addr(cb, &s, arg1), arg2);
1232 errcode = errno;
1233 break;
1234
1235 case __NR_munlock:
1236 result = munlock((void *) t2h_addr(cb, &s, arg1), arg2);
1237 errcode = errno;
1238 break;
1239
1240 case __NR_nanosleep:
1241 {
1242 struct timespec req, rem;
1243
1244 req = *((struct timespec *) t2h_addr(cb, &s, arg2));
1245 translate_endian((void *) &req, sizeof(req));
1246
1247 result = nanosleep(&req, &rem);
1248 errcode = errno;
1249
1250 if (result != 0)
1251 break;
1252
1253 translate_endian((void *) &rem, sizeof(rem));
1254 if ((s.write_mem) (cb, &s, arg2, (char *) &rem, sizeof(rem))
1255 != sizeof(rem))
1256 {
1257 result = -1;
1258 errcode = EINVAL;
1259 }
1260 }
1261 break;
1262
1263 case __NR_mremap: /* FIXME */
1264 result = (int) mremap((void *) t2h_addr(cb, &s, arg1), arg2, arg3, arg4);
1265 errcode = errno;
1266 break;
1267
19e64aa9 1268 case __NR_getresuid32:
6edf0760
NC
1269 case __NR_getresuid:
1270 {
1271 uid_t ruid, euid, suid;
1272
1273 result = getresuid(&ruid, &euid, &suid);
1274 errcode = errno;
1275
1276 if (result != 0)
1277 break;
1278
1279 *((uid_t *) t2h_addr(cb, &s, arg1)) = conv_endian(ruid);
1280 *((uid_t *) t2h_addr(cb, &s, arg2)) = conv_endian(euid);
1281 *((uid_t *) t2h_addr(cb, &s, arg3)) = conv_endian(suid);
1282 }
1283 break;
1284
1285 case __NR_poll:
1286 {
1287 struct pollfd ufds;
1288
1289 ufds = *((struct pollfd *) t2h_addr(cb, &s, arg1));
1290 ufds.fd = conv_endian(ufds.fd);
1291 ufds.events = conv_endian16(ufds.events);
1292 ufds.revents = conv_endian16(ufds.revents);
1293
1294 result = poll(&ufds, arg2, arg3);
1295 errcode = errno;
1296 }
1297 break;
1298
19e64aa9 1299 case __NR_getresgid32:
6edf0760
NC
1300 case __NR_getresgid:
1301 {
1302 uid_t rgid, egid, sgid;
1303
1304 result = getresgid(&rgid, &egid, &sgid);
1305 errcode = errno;
1306
1307 if (result != 0)
1308 break;
1309
1310 *((uid_t *) t2h_addr(cb, &s, arg1)) = conv_endian(rgid);
1311 *((uid_t *) t2h_addr(cb, &s, arg2)) = conv_endian(egid);
1312 *((uid_t *) t2h_addr(cb, &s, arg3)) = conv_endian(sgid);
1313 }
1314 break;
1315
1316 case __NR_pread:
1317 result = pread(arg1, (void *) t2h_addr(cb, &s, arg2), arg3, arg4);
1318 errcode = errno;
1319 break;
1320
1321 case __NR_pwrite:
1322 result = pwrite(arg1, (void *) t2h_addr(cb, &s, arg2), arg3, arg4);
1323 errcode = errno;
1324 break;
1325
19e64aa9 1326 case __NR_chown32:
6edf0760
NC
1327 case __NR_chown:
1328 result = chown((char *) t2h_addr(cb, &s, arg1), arg2, arg3);
1329 errcode = errno;
1330 break;
1331
1332 case __NR_getcwd:
1333 result = (int) getcwd((char *) t2h_addr(cb, &s, arg1), arg2);
1334 errcode = errno;
1335 break;
1336
1337 case __NR_sendfile:
1338 {
1339 off_t offset;
1340
1341 offset = *((off_t *) t2h_addr(cb, &s, arg3));
1342 offset = conv_endian(offset);
1343
1344 result = sendfile(arg1, arg2, &offset, arg3);
1345 errcode = errno;
1346
1347 if (result != 0)
1348 break;
1349
1350 *((off_t *) t2h_addr(cb, &s, arg3)) = conv_endian(offset);
1351 }
1352 break;
1353
1354 default:
1355 result = -1;
1356 errcode = ENOSYS;
1357 break;
1358 }
1359
1360 if (result == -1)
1361 m32rbf_h_gr_set (current_cpu, 0, -errcode);
1362 else
1363 m32rbf_h_gr_set (current_cpu, 0, result);
1364 break;
1365 }
1366
1367 case TRAP_BREAKPOINT:
1368 sim_engine_halt (sd, current_cpu, NULL, pc,
1369 sim_stopped, SIM_SIGTRAP);
1370 break;
1371
1372 case TRAP_FLUSH_CACHE:
1373 /* Do nothing. */
1374 break;
1375
1376 default :
1377 {
1378 /* Use cr5 as EVB (EIT Vector Base) register. */
1379 USI new_pc = m32rbf_h_cr_get (current_cpu, 5) + 0x40 + num * 4;
1380 return new_pc;
1381 }
1382 }
1383
1384 /* Fake an "rte" insn. */
1385 /* FIXME: Should duplicate all of rte processing. */
1386 return (pc & -4) + 4;
1387}