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