1 /* CRIS exception, interrupt, and trap (EIT) support 2 Copyright (C) 2004-2024 Free Software Foundation, Inc. 3 Contributed by Axis Communications. 4 5 This file is part of the GNU simulators. 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 "portability.h" 24 #include "sim-main.h" 25 #include "sim-syscall.h" 26 #include "sim-options.h" 27 #include "sim-signal.h" 28 #include "sim/callback.h" 29 #include "bfd.h" 30 /* FIXME: get rid of targ-vals.h usage everywhere else. */ 31 32 #include <stdlib.h> 33 #include <stdarg.h> 34 #include <errno.h> 35 #include <unistd.h> 36 #ifdef HAVE_FCNTL_H 37 #include <fcntl.h> 38 #endif 39 #ifdef HAVE_SYS_PARAM_H 40 #include <sys/param.h> 41 #endif 42 #include <sys/stat.h> 43 /* For PATH_MAX, originally. */ 44 #ifdef HAVE_LIMITS_H 45 #include <limits.h> 46 #endif 47 48 /* From ld/sysdep.h. */ 49 #ifdef PATH_MAX 50 # define SIM_PATHMAX PATH_MAX 51 #else 52 # ifdef MAXPATHLEN 53 # define SIM_PATHMAX MAXPATHLEN 54 # else 55 # define SIM_PATHMAX 1024 56 # endif 57 #endif 58 59 /* The verbatim values are from asm-cris/unistd.h. */ 60 61 #define TARGET_SYS_exit 1 62 #define TARGET_SYS_read 3 63 #define TARGET_SYS_write 4 64 #define TARGET_SYS_open 5 65 #define TARGET_SYS_close 6 66 #define TARGET_SYS_unlink 10 67 #define TARGET_SYS_time 13 68 #define TARGET_SYS_lseek 19 69 #define TARGET_SYS_getpid 20 70 #define TARGET_SYS_access 33 71 #define TARGET_SYS_kill 37 72 #define TARGET_SYS_rename 38 73 #define TARGET_SYS_pipe 42 74 #define TARGET_SYS_brk 45 75 #define TARGET_SYS_ioctl 54 76 #define TARGET_SYS_fcntl 55 77 #define TARGET_SYS_getppid 64 78 #define TARGET_SYS_setrlimit 75 79 #define TARGET_SYS_gettimeofday 78 80 #define TARGET_SYS_readlink 85 81 #define TARGET_SYS_munmap 91 82 #define TARGET_SYS_truncate 92 83 #define TARGET_SYS_ftruncate 93 84 #define TARGET_SYS_socketcall 102 85 #define TARGET_SYS_stat 106 86 #define TARGET_SYS_fstat 108 87 #define TARGET_SYS_wait4 114 88 #define TARGET_SYS_sigreturn 119 89 #define TARGET_SYS_clone 120 90 #define TARGET_SYS_uname 122 91 #define TARGET_SYS_mprotect 125 92 #define TARGET_SYS_llseek 140 93 #define TARGET_SYS_writev 146 94 #define TARGET_SYS__sysctl 149 95 #define TARGET_SYS_sched_setparam 154 96 #define TARGET_SYS_sched_getparam 155 97 #define TARGET_SYS_sched_setscheduler 156 98 #define TARGET_SYS_sched_getscheduler 157 99 #define TARGET_SYS_sched_yield 158 100 #define TARGET_SYS_sched_get_priority_max 159 101 #define TARGET_SYS_sched_get_priority_min 160 102 #define TARGET_SYS_mremap 163 103 #define TARGET_SYS_poll 168 104 #define TARGET_SYS_rt_sigaction 174 105 #define TARGET_SYS_rt_sigprocmask 175 106 #define TARGET_SYS_rt_sigsuspend 179 107 #define TARGET_SYS_getcwd 183 108 #define TARGET_SYS_ugetrlimit 191 109 #define TARGET_SYS_mmap2 192 110 #define TARGET_SYS_stat64 195 111 #define TARGET_SYS_lstat64 196 112 #define TARGET_SYS_fstat64 197 113 #define TARGET_SYS_geteuid32 201 114 #define TARGET_SYS_getuid32 199 115 #define TARGET_SYS_getegid32 202 116 #define TARGET_SYS_getgid32 200 117 #define TARGET_SYS_fcntl64 221 118 #define TARGET_SYS_set_thread_area 243 119 #define TARGET_SYS_exit_group 252 120 121 #define TARGET_PROT_READ 0x1 122 #define TARGET_PROT_WRITE 0x2 123 #define TARGET_PROT_EXEC 0x4 124 #define TARGET_PROT_NONE 0x0 125 126 #define TARGET_MAP_SHARED 0x01 127 #define TARGET_MAP_PRIVATE 0x02 128 #define TARGET_MAP_TYPE 0x0f 129 #define TARGET_MAP_FIXED 0x10 130 #define TARGET_MAP_ANONYMOUS 0x20 131 #define TARGET_MAP_DENYWRITE 0x800 132 133 #define TARGET_CTL_KERN 1 134 #define TARGET_CTL_VM 2 135 #define TARGET_CTL_NET 3 136 #define TARGET_CTL_PROC 4 137 #define TARGET_CTL_FS 5 138 #define TARGET_CTL_DEBUG 6 139 #define TARGET_CTL_DEV 7 140 #define TARGET_CTL_BUS 8 141 #define TARGET_CTL_ABI 9 142 143 #define TARGET_CTL_KERN_VERSION 4 144 145 /* linux/mman.h */ 146 #define TARGET_MREMAP_MAYMOVE 1 147 #define TARGET_MREMAP_FIXED 2 148 149 #define TARGET_TCGETS 0x5401 150 151 #define TARGET_UTSNAME "#7 Thu Jan 1 00:00:00 MET 2009" 152 153 /* Seconds since 1970-01-01 to the above date + 10 minutes; 154 'date -d "Thu Jan 1 00:00:10 MET 2009" +%s'. */ 155 #define TARGET_EPOCH 1230764410 156 157 /* Milliseconds since start of run. We use the number of syscalls to 158 avoid introducing noise in the execution time. */ 159 #define TARGET_TIME_MS(cpu) (CRIS_SIM_CPU (cpu)->syscalls) 160 161 /* Seconds as in time(2). */ 162 #define TARGET_TIME(cpu) (TARGET_EPOCH + TARGET_TIME_MS (cpu) / 1000) 163 164 #define TARGET_SCHED_OTHER 0 165 166 #define TARGET_RLIMIT_STACK 3 167 #define TARGET_RLIMIT_NOFILE 7 168 169 #define SIM_TARGET_MAX_THREADS 64 170 #define SIM_MAX_ALLOC_CHUNK (512*1024*1024) 171 172 /* From linux/sched.h. */ 173 #define TARGET_CSIGNAL 0x000000ff 174 #define TARGET_CLONE_VM 0x00000100 175 #define TARGET_CLONE_FS 0x00000200 176 #define TARGET_CLONE_FILES 0x00000400 177 #define TARGET_CLONE_SIGHAND 0x00000800 178 #define TARGET_CLONE_PID 0x00001000 179 #define TARGET_CLONE_PTRACE 0x00002000 180 #define TARGET_CLONE_VFORK 0x00004000 181 #define TARGET_CLONE_PARENT 0x00008000 182 #define TARGET_CLONE_THREAD 0x00010000 183 #define TARGET_CLONE_SIGNAL (TARGET_CLONE_SIGHAND | TARGET_CLONE_THREAD) 184 185 /* From asm-cris/poll.h. */ 186 #define TARGET_POLLIN 1 187 188 /* From asm-cris/signal.h. */ 189 #define TARGET_SIG_BLOCK 0 190 #define TARGET_SIG_UNBLOCK 1 191 #define TARGET_SIG_SETMASK 2 192 193 #define TARGET_SIG_DFL 0 194 #define TARGET_SIG_IGN 1 195 #define TARGET_SIG_ERR ((USI)-1) 196 197 #define TARGET_SIGHUP 1 198 #define TARGET_SIGINT 2 199 #define TARGET_SIGQUIT 3 200 #define TARGET_SIGILL 4 201 #define TARGET_SIGTRAP 5 202 #define TARGET_SIGABRT 6 203 #define TARGET_SIGIOT 6 204 #define TARGET_SIGBUS 7 205 #define TARGET_SIGFPE 8 206 #define TARGET_SIGKILL 9 207 #define TARGET_SIGUSR1 10 208 #define TARGET_SIGSEGV 11 209 #define TARGET_SIGUSR2 12 210 #define TARGET_SIGPIPE 13 211 #define TARGET_SIGALRM 14 212 #define TARGET_SIGTERM 15 213 #define TARGET_SIGSTKFLT 16 214 #define TARGET_SIGCHLD 17 215 #define TARGET_SIGCONT 18 216 #define TARGET_SIGSTOP 19 217 #define TARGET_SIGTSTP 20 218 #define TARGET_SIGTTIN 21 219 #define TARGET_SIGTTOU 22 220 #define TARGET_SIGURG 23 221 #define TARGET_SIGXCPU 24 222 #define TARGET_SIGXFSZ 25 223 #define TARGET_SIGVTALRM 26 224 #define TARGET_SIGPROF 27 225 #define TARGET_SIGWINCH 28 226 #define TARGET_SIGIO 29 227 #define TARGET_SIGPOLL SIGIO 228 /* Actually commented out in the kernel header. */ 229 #define TARGET_SIGLOST 29 230 #define TARGET_SIGPWR 30 231 #define TARGET_SIGSYS 31 232 233 /* From include/asm-cris/signal.h. */ 234 #define TARGET_SA_NOCLDSTOP 0x00000001 235 #define TARGET_SA_NOCLDWAIT 0x00000002 /* not supported yet */ 236 #define TARGET_SA_SIGINFO 0x00000004 237 #define TARGET_SA_ONSTACK 0x08000000 238 #define TARGET_SA_RESTART 0x10000000 239 #define TARGET_SA_NODEFER 0x40000000 240 #define TARGET_SA_RESETHAND 0x80000000 241 #define TARGET_SA_INTERRUPT 0x20000000 /* dummy -- ignored */ 242 #define TARGET_SA_RESTORER 0x04000000 243 244 /* From linux/wait.h. */ 245 #define TARGET_WNOHANG 1 246 #define TARGET_WUNTRACED 2 247 #define TARGET___WNOTHREAD 0x20000000 248 #define TARGET___WALL 0x40000000 249 #define TARGET___WCLONE 0x80000000 250 251 /* From linux/limits.h. */ 252 #define TARGET_PIPE_BUF 4096 253 254 /* From unistd.h. */ 255 #define TARGET_R_OK 4 256 #define TARGET_W_OK 2 257 #define TARGET_X_OK 1 258 #define TARGET_F_OK 0 259 260 static const char stat_map[] = 261 "st_dev,2:space,10:space,4:st_mode,4:st_nlink,4:st_uid,4" 262 ":st_gid,4:st_rdev,2:space,10:st_size,8:st_blksize,4:st_blocks,4" 263 ":space,4:st_atime,4:space,4:st_mtime,4:space,4:st_ctime,4:space,4" 264 ":st_ino,8"; 265 266 static const CB_TARGET_DEFS_MAP syscall_map[] = 267 { 268 { "open", CB_SYS_open, TARGET_SYS_open }, 269 { "close", CB_SYS_close, TARGET_SYS_close }, 270 { "read", CB_SYS_read, TARGET_SYS_read }, 271 { "write", CB_SYS_write, TARGET_SYS_write }, 272 { "lseek", CB_SYS_lseek, TARGET_SYS_lseek }, 273 { "unlink", CB_SYS_unlink, TARGET_SYS_unlink }, 274 { "getpid", CB_SYS_getpid, TARGET_SYS_getpid }, 275 { "fstat", CB_SYS_fstat, TARGET_SYS_fstat64 }, 276 { "lstat", CB_SYS_lstat, TARGET_SYS_lstat64 }, 277 { "stat", CB_SYS_stat, TARGET_SYS_stat64 }, 278 { "pipe", CB_SYS_pipe, TARGET_SYS_pipe }, 279 { "rename", CB_SYS_rename, TARGET_SYS_rename }, 280 { "truncate", CB_SYS_truncate, TARGET_SYS_truncate }, 281 { "ftruncate", CB_SYS_ftruncate, TARGET_SYS_ftruncate }, 282 { 0, -1, -1 } 283 }; 284 285 /* An older, 32-bit-only stat mapping. */ 286 static const char stat32_map[] = 287 "st_dev,2:space,2:st_ino,4:st_mode,2:st_nlink,2:st_uid,2" 288 ":st_gid,2:st_rdev,2:space,2:st_size,4:st_blksize,4:st_blocks,4" 289 ":st_atime,4:space,4:st_mtime,4:space,4:st_ctime,4:space,12"; 290 291 /* Map for calls using the 32-bit struct stat. Primarily used by the 292 newlib Linux mapping. */ 293 static const CB_TARGET_DEFS_MAP syscall_stat32_map[] = 294 { 295 { "fstat", CB_SYS_fstat, TARGET_SYS_fstat }, 296 { "stat", CB_SYS_stat, TARGET_SYS_stat }, 297 { 0, -1, -1 } 298 }; 299 300 /* Giving the true value for the running sim process will lead to 301 non-time-invariant behavior. */ 302 #define TARGET_PID 42 303 304 /* Unfortunately, we don't get this from cris.cpu at the moment, and if 305 we did, we'd still don't get a register number with the "16" offset. */ 306 #define TARGET_SRP_REGNUM (16+11) 307 308 /* Extracted by applying 309 awk '/^#define/ { printf "#ifdef %s\n { %s, %s },\n#endif\n", $2, $2, $3;}' 310 on .../include/asm/errno.h in a GNU/Linux/CRIS installation and 311 adjusting the synonyms. */ 312 313 static const CB_TARGET_DEFS_MAP errno_map[] = 314 { 315 #ifdef EPERM 316 { "EPERM", EPERM, 1 }, 317 #endif 318 #ifdef ENOENT 319 { "ENOENT", ENOENT, 2 }, 320 #endif 321 #ifdef ESRCH 322 { "ESRCH", ESRCH, 3 }, 323 #endif 324 #ifdef EINTR 325 { "EINTR", EINTR, 4 }, 326 #endif 327 #ifdef EIO 328 { "EIO", EIO, 5 }, 329 #endif 330 #ifdef ENXIO 331 { "ENXIO", ENXIO, 6 }, 332 #endif 333 #ifdef E2BIG 334 { "E2BIG", E2BIG, 7 }, 335 #endif 336 #ifdef ENOEXEC 337 { "ENOEXEC", ENOEXEC, 8 }, 338 #endif 339 #ifdef EBADF 340 { "EBADF", EBADF, 9 }, 341 #endif 342 #ifdef ECHILD 343 { "ECHILD", ECHILD, 10 }, 344 #endif 345 #ifdef EAGAIN 346 { "EAGAIN", EAGAIN, 11 }, 347 #endif 348 #ifdef ENOMEM 349 { "ENOMEM", ENOMEM, 12 }, 350 #endif 351 #ifdef EACCES 352 { "EACCES", EACCES, 13 }, 353 #endif 354 #ifdef EFAULT 355 { "EFAULT", EFAULT, 14 }, 356 #endif 357 #ifdef ENOTBLK 358 { "ENOTBLK", ENOTBLK, 15 }, 359 #endif 360 #ifdef EBUSY 361 { "EBUSY", EBUSY, 16 }, 362 #endif 363 #ifdef EEXIST 364 { "EEXIST", EEXIST, 17 }, 365 #endif 366 #ifdef EXDEV 367 { "EXDEV", EXDEV, 18 }, 368 #endif 369 #ifdef ENODEV 370 { "ENODEV", ENODEV, 19 }, 371 #endif 372 #ifdef ENOTDIR 373 { "ENOTDIR", ENOTDIR, 20 }, 374 #endif 375 #ifdef EISDIR 376 { "EISDIR", EISDIR, 21 }, 377 #endif 378 #ifdef EINVAL 379 { "EINVAL", EINVAL, 22 }, 380 #endif 381 #ifdef ENFILE 382 { "ENFILE", ENFILE, 23 }, 383 #endif 384 #ifdef EMFILE 385 { "EMFILE", EMFILE, 24 }, 386 #endif 387 #ifdef ENOTTY 388 { "ENOTTY", ENOTTY, 25 }, 389 #endif 390 #ifdef ETXTBSY 391 { "ETXTBSY", ETXTBSY, 26 }, 392 #endif 393 #ifdef EFBIG 394 { "EFBIG", EFBIG, 27 }, 395 #endif 396 #ifdef ENOSPC 397 { "ENOSPC", ENOSPC, 28 }, 398 #endif 399 #ifdef ESPIPE 400 { "ESPIPE", ESPIPE, 29 }, 401 #endif 402 #ifdef EROFS 403 { "EROFS", EROFS, 30 }, 404 #endif 405 #ifdef EMLINK 406 { "EMLINK", EMLINK, 31 }, 407 #endif 408 #ifdef EPIPE 409 { "EPIPE", EPIPE, 32 }, 410 #endif 411 #ifdef EDOM 412 { "EDOM", EDOM, 33 }, 413 #endif 414 #ifdef ERANGE 415 { "ERANGE", ERANGE, 34 }, 416 #endif 417 #ifdef EDEADLK 418 { "EDEADLK", EDEADLK, 35 }, 419 #endif 420 #ifdef ENAMETOOLONG 421 { "ENAMETOOLONG", ENAMETOOLONG, 36 }, 422 #endif 423 #ifdef ENOLCK 424 { "ENOLCK", ENOLCK, 37 }, 425 #endif 426 #ifdef ENOSYS 427 { "ENOSYS", ENOSYS, 38 }, 428 #endif 429 #ifdef ENOTEMPTY 430 { "ENOTEMPTY", ENOTEMPTY, 39 }, 431 #endif 432 #ifdef ELOOP 433 { "ELOOP", ELOOP, 40 }, 434 #endif 435 #ifdef EWOULDBLOCK 436 { "EWOULDBLOCK", EWOULDBLOCK, 11 }, 437 #endif 438 #ifdef ENOMSG 439 { "ENOMSG", ENOMSG, 42 }, 440 #endif 441 #ifdef EIDRM 442 { "EIDRM", EIDRM, 43 }, 443 #endif 444 #ifdef ECHRNG 445 { "ECHRNG", ECHRNG, 44 }, 446 #endif 447 #ifdef EL2NSYNC 448 { "EL2NSYNC", EL2NSYNC, 45 }, 449 #endif 450 #ifdef EL3HLT 451 { "EL3HLT", EL3HLT, 46 }, 452 #endif 453 #ifdef EL3RST 454 { "EL3RST", EL3RST, 47 }, 455 #endif 456 #ifdef ELNRNG 457 { "ELNRNG", ELNRNG, 48 }, 458 #endif 459 #ifdef EUNATCH 460 { "EUNATCH", EUNATCH, 49 }, 461 #endif 462 #ifdef ENOCSI 463 { "ENOCSI", ENOCSI, 50 }, 464 #endif 465 #ifdef EL2HLT 466 { "EL2HLT", EL2HLT, 51 }, 467 #endif 468 #ifdef EBADE 469 { "EBADE", EBADE, 52 }, 470 #endif 471 #ifdef EBADR 472 { "EBADR", EBADR, 53 }, 473 #endif 474 #ifdef EXFULL 475 { "EXFULL", EXFULL, 54 }, 476 #endif 477 #ifdef ENOANO 478 { "ENOANO", ENOANO, 55 }, 479 #endif 480 #ifdef EBADRQC 481 { "EBADRQC", EBADRQC, 56 }, 482 #endif 483 #ifdef EBADSLT 484 { "EBADSLT", EBADSLT, 57 }, 485 #endif 486 #ifdef EDEADLOCK 487 { "EDEADLOCK", EDEADLOCK, 35 }, 488 #endif 489 #ifdef EBFONT 490 { "EBFONT", EBFONT, 59 }, 491 #endif 492 #ifdef ENOSTR 493 { "ENOSTR", ENOSTR, 60 }, 494 #endif 495 #ifdef ENODATA 496 { "ENODATA", ENODATA, 61 }, 497 #endif 498 #ifdef ETIME 499 { "ETIME", ETIME, 62 }, 500 #endif 501 #ifdef ENOSR 502 { "ENOSR", ENOSR, 63 }, 503 #endif 504 #ifdef ENONET 505 { "ENONET", ENONET, 64 }, 506 #endif 507 #ifdef ENOPKG 508 { "ENOPKG", ENOPKG, 65 }, 509 #endif 510 #ifdef EREMOTE 511 { "EREMOTE", EREMOTE, 66 }, 512 #endif 513 #ifdef ENOLINK 514 { "ENOLINK", ENOLINK, 67 }, 515 #endif 516 #ifdef EADV 517 { "EADV", EADV, 68 }, 518 #endif 519 #ifdef ESRMNT 520 { "ESRMNT", ESRMNT, 69 }, 521 #endif 522 #ifdef ECOMM 523 { "ECOMM", ECOMM, 70 }, 524 #endif 525 #ifdef EPROTO 526 { "EPROTO", EPROTO, 71 }, 527 #endif 528 #ifdef EMULTIHOP 529 { "EMULTIHOP", EMULTIHOP, 72 }, 530 #endif 531 #ifdef EDOTDOT 532 { "EDOTDOT", EDOTDOT, 73 }, 533 #endif 534 #ifdef EBADMSG 535 { "EBADMSG", EBADMSG, 74 }, 536 #endif 537 #ifdef EOVERFLOW 538 { "EOVERFLOW", EOVERFLOW, 75 }, 539 #endif 540 #ifdef ENOTUNIQ 541 { "ENOTUNIQ", ENOTUNIQ, 76 }, 542 #endif 543 #ifdef EBADFD 544 { "EBADFD", EBADFD, 77 }, 545 #endif 546 #ifdef EREMCHG 547 { "EREMCHG", EREMCHG, 78 }, 548 #endif 549 #ifdef ELIBACC 550 { "ELIBACC", ELIBACC, 79 }, 551 #endif 552 #ifdef ELIBBAD 553 { "ELIBBAD", ELIBBAD, 80 }, 554 #endif 555 #ifdef ELIBSCN 556 { "ELIBSCN", ELIBSCN, 81 }, 557 #endif 558 #ifdef ELIBMAX 559 { "ELIBMAX", ELIBMAX, 82 }, 560 #endif 561 #ifdef ELIBEXEC 562 { "ELIBEXEC", ELIBEXEC, 83 }, 563 #endif 564 #ifdef EILSEQ 565 { "EILSEQ", EILSEQ, 84 }, 566 #endif 567 #ifdef ERESTART 568 { "ERESTART", ERESTART, 85 }, 569 #endif 570 #ifdef ESTRPIPE 571 { "ESTRPIPE", ESTRPIPE, 86 }, 572 #endif 573 #ifdef EUSERS 574 { "EUSERS", EUSERS, 87 }, 575 #endif 576 #ifdef ENOTSOCK 577 { "ENOTSOCK", ENOTSOCK, 88 }, 578 #endif 579 #ifdef EDESTADDRREQ 580 { "EDESTADDRREQ", EDESTADDRREQ, 89 }, 581 #endif 582 #ifdef EMSGSIZE 583 { "EMSGSIZE", EMSGSIZE, 90 }, 584 #endif 585 #ifdef EPROTOTYPE 586 { "EPROTOTYPE", EPROTOTYPE, 91 }, 587 #endif 588 #ifdef ENOPROTOOPT 589 { "ENOPROTOOPT", ENOPROTOOPT, 92 }, 590 #endif 591 #ifdef EPROTONOSUPPORT 592 { "EPROTONOSUPPORT", EPROTONOSUPPORT, 93 }, 593 #endif 594 #ifdef ESOCKTNOSUPPORT 595 { "ESOCKTNOSUPPORT", ESOCKTNOSUPPORT, 94 }, 596 #endif 597 #ifdef EOPNOTSUPP 598 { "EOPNOTSUPP", EOPNOTSUPP, 95 }, 599 #endif 600 #ifdef EPFNOSUPPORT 601 { "EPFNOSUPPORT", EPFNOSUPPORT, 96 }, 602 #endif 603 #ifdef EAFNOSUPPORT 604 { "EAFNOSUPPORT", EAFNOSUPPORT, 97 }, 605 #endif 606 #ifdef EADDRINUSE 607 { "EADDRINUSE", EADDRINUSE, 98 }, 608 #endif 609 #ifdef EADDRNOTAVAIL 610 { "EADDRNOTAVAIL", EADDRNOTAVAIL, 99 }, 611 #endif 612 #ifdef ENETDOWN 613 { "ENETDOWN", ENETDOWN, 100 }, 614 #endif 615 #ifdef ENETUNREACH 616 { "ENETUNREACH", ENETUNREACH, 101 }, 617 #endif 618 #ifdef ENETRESET 619 { "ENETRESET", ENETRESET, 102 }, 620 #endif 621 #ifdef ECONNABORTED 622 { "ECONNABORTED", ECONNABORTED, 103 }, 623 #endif 624 #ifdef ECONNRESET 625 { "ECONNRESET", ECONNRESET, 104 }, 626 #endif 627 #ifdef ENOBUFS 628 { "ENOBUFS", ENOBUFS, 105 }, 629 #endif 630 #ifdef EISCONN 631 { "EISCONN", EISCONN, 106 }, 632 #endif 633 #ifdef ENOTCONN 634 { "ENOTCONN", ENOTCONN, 107 }, 635 #endif 636 #ifdef ESHUTDOWN 637 { "ESHUTDOWN", ESHUTDOWN, 108 }, 638 #endif 639 #ifdef ETOOMANYREFS 640 { "ETOOMANYREFS", ETOOMANYREFS, 109 }, 641 #endif 642 #ifdef ETIMEDOUT 643 { "ETIMEDOUT", ETIMEDOUT, 110 }, 644 #endif 645 #ifdef ECONNREFUSED 646 { "ECONNREFUSED", ECONNREFUSED, 111 }, 647 #endif 648 #ifdef EHOSTDOWN 649 { "EHOSTDOWN", EHOSTDOWN, 112 }, 650 #endif 651 #ifdef EHOSTUNREACH 652 { "EHOSTUNREACH", EHOSTUNREACH, 113 }, 653 #endif 654 #ifdef EALREADY 655 { "EALREADY", EALREADY, 114 }, 656 #endif 657 #ifdef EINPROGRESS 658 { "EINPROGRESS", EINPROGRESS, 115 }, 659 #endif 660 #ifdef ESTALE 661 { "ESTALE", ESTALE, 116 }, 662 #endif 663 #ifdef EUCLEAN 664 { "EUCLEAN", EUCLEAN, 117 }, 665 #endif 666 #ifdef ENOTNAM 667 { "ENOTNAM", ENOTNAM, 118 }, 668 #endif 669 #ifdef ENAVAIL 670 { "ENAVAIL", ENAVAIL, 119 }, 671 #endif 672 #ifdef EISNAM 673 { "EISNAM", EISNAM, 120 }, 674 #endif 675 #ifdef EREMOTEIO 676 { "EREMOTEIO", EREMOTEIO, 121 }, 677 #endif 678 #ifdef EDQUOT 679 { "EDQUOT", EDQUOT, 122 }, 680 #endif 681 #ifdef ENOMEDIUM 682 { "ENOMEDIUM", ENOMEDIUM, 123 }, 683 #endif 684 #ifdef EMEDIUMTYPE 685 { "EMEDIUMTYPE", EMEDIUMTYPE, 124 }, 686 #endif 687 { 0, 0, 0 } 688 }; 689 690 /* Extracted by applying 691 perl -ne 'if ($_ =~ /^#define/) { split; 692 printf "#ifdef $_[1]\n { %s, 0x%x },\n#endif\n", 693 $_[1], $_[2] =~ /^0/ ? oct($_[2]) : $_[2];}' 694 on pertinent parts of .../include/asm/fcntl.h in a GNU/Linux/CRIS 695 installation and removing synonyms and unnecessary items. Don't 696 forget the end-marker. */ 697 698 /* These we treat specially, as they're used in the fcntl F_GETFL 699 syscall. For consistency, open_map is also manually edited to use 700 these macros. */ 701 #define TARGET_O_ACCMODE 0x3 702 #define TARGET_O_RDONLY 0x0 703 #define TARGET_O_WRONLY 0x1 704 705 static const CB_TARGET_DEFS_MAP open_map[] = { 706 #ifdef O_ACCMODE 707 { "O_ACCMODE", O_ACCMODE, TARGET_O_ACCMODE }, 708 #endif 709 #ifdef O_RDONLY 710 { "O_RDONLY", O_RDONLY, TARGET_O_RDONLY }, 711 #endif 712 #ifdef O_WRONLY 713 { "O_WRONLY", O_WRONLY, TARGET_O_WRONLY }, 714 #endif 715 #ifdef O_RDWR 716 { "O_RDWR", O_RDWR, 0x2 }, 717 #endif 718 #ifdef O_CREAT 719 { "O_CREAT", O_CREAT, 0x40 }, 720 #endif 721 #ifdef O_EXCL 722 { "O_EXCL", O_EXCL, 0x80 }, 723 #endif 724 #ifdef O_NOCTTY 725 { "O_NOCTTY", O_NOCTTY, 0x100 }, 726 #endif 727 #ifdef O_TRUNC 728 { "O_TRUNC", O_TRUNC, 0x200 }, 729 #endif 730 #ifdef O_APPEND 731 { "O_APPEND", O_APPEND, 0x400 }, 732 #endif 733 #ifdef O_NONBLOCK 734 { "O_NONBLOCK", O_NONBLOCK, 0x800 }, 735 #endif 736 #ifdef O_NDELAY 737 { "O_NDELAY", O_NDELAY, 0x0 }, 738 #endif 739 #ifdef O_SYNC 740 { "O_SYNC", O_SYNC, 0x1000 }, 741 #endif 742 #ifdef FASYNC 743 { "FASYNC", FASYNC, 0x2000 }, 744 #endif 745 #ifdef O_DIRECT 746 { "O_DIRECT", O_DIRECT, 0x4000 }, 747 #endif 748 #ifdef O_LARGEFILE 749 { "O_LARGEFILE", O_LARGEFILE, 0x8000 }, 750 #endif 751 #ifdef O_DIRECTORY 752 { "O_DIRECTORY", O_DIRECTORY, 0x10000 }, 753 #endif 754 #ifdef O_NOFOLLOW 755 { "O_NOFOLLOW", O_NOFOLLOW, 0x20000 }, 756 #endif 757 { 0, -1, -1 } 758 }; 759 760 /* Let's be less drastic and more traceable. FIXME: mark as noreturn. */ 761 #define abort() \ 762 sim_io_error (sd, "simulator unhandled condition at %s:%d", \ 763 __FUNCTION__, __LINE__) 764 765 /* Needed for the cris_pipe_nonempty and cris_pipe_empty syscalls. */ 766 static SIM_CPU *current_cpu_for_cb_callback; 767 768 static USI create_map (SIM_DESC, struct cris_sim_mmapped_page **, 769 USI addr, USI len); 770 static USI unmap_pages (SIM_DESC, struct cris_sim_mmapped_page **, 771 USI addr, USI len); 772 static USI is_mapped (SIM_DESC, struct cris_sim_mmapped_page **, 773 USI addr, USI len); 774 static void dump_statistics (SIM_CPU *current_cpu); 775 static void make_first_thread (SIM_CPU *current_cpu); 776 777 /* When we risk running self-modified code (as in trampolines), this is 778 called from special-case insns. The silicon CRIS CPU:s have enough 779 cache snooping implemented making this a simulator-only issue. Tests: 780 gcc.c-torture/execute/931002-1.c execution, -O3 -g 781 gcc.c-torture/execute/931002-1.c execution, -O3 -fomit-frame-pointer. */ 782 783 void 784 cris_flush_simulator_decode_cache (SIM_CPU *current_cpu, 785 USI pc ATTRIBUTE_UNUSED) 786 { 787 SIM_DESC sd = CPU_STATE (current_cpu); 788 789 #if WITH_SCACHE 790 if (USING_SCACHE_P (sd)) 791 scache_flush_cpu (current_cpu); 792 #endif 793 } 794 795 /* Output statistics at the end of a run. */ 796 static void 797 dump_statistics (SIM_CPU *current_cpu) 798 { 799 SIM_DESC sd = CPU_STATE (current_cpu); 800 CRIS_MISC_PROFILE *profp 801 = CPU_CRIS_MISC_PROFILE (current_cpu); 802 uint64_t total = profp->basic_cycle_count; 803 804 /* Historically, these messages have gone to stderr, so we'll keep it 805 that way. It's also easier to then tell it from normal program 806 output. FIXME: Add redirect option like "run -e file". */ 807 808 /* The --cris-stats={basic|unaligned|schedulable|all} counts affect 809 what's included in the "total" count only. */ 810 switch (CPU_CRIS_MISC_PROFILE (current_cpu)->flags 811 & FLAG_CRIS_MISC_PROFILE_ALL) 812 { 813 case FLAG_CRIS_MISC_PROFILE_SIMPLE: 814 sim_io_eprintf (sd, "Basic clock cycles, total @: %" PRIu64 "\n", total); 815 break; 816 817 case (FLAG_CRIS_MISC_PROFILE_UNALIGNED | FLAG_CRIS_MISC_PROFILE_SIMPLE): 818 total += profp->unaligned_mem_dword_count; 819 sim_io_eprintf (sd, 820 "Clock cycles including stall cycles for unaligned " 821 "accesses @: %" PRIu64 "\n", 822 total); 823 break; 824 825 case (FLAG_CRIS_MISC_PROFILE_SCHEDULABLE | FLAG_CRIS_MISC_PROFILE_SIMPLE): 826 total 827 += (profp->memsrc_stall_count 828 + profp->memraw_stall_count 829 + profp->movemsrc_stall_count 830 + profp->movemdst_stall_count 831 + profp->mulsrc_stall_count 832 + profp->jumpsrc_stall_count 833 + profp->unaligned_mem_dword_count); 834 sim_io_eprintf (sd, "Schedulable clock cycles, total @: %" PRIu64 "\n", 835 total); 836 break; 837 838 case FLAG_CRIS_MISC_PROFILE_ALL: 839 total 840 += (profp->memsrc_stall_count 841 + profp->memraw_stall_count 842 + profp->movemsrc_stall_count 843 + profp->movemdst_stall_count 844 + profp->movemaddr_stall_count 845 + profp->mulsrc_stall_count 846 + profp->jumpsrc_stall_count 847 + profp->branch_stall_count 848 + profp->jumptarget_stall_count 849 + profp->unaligned_mem_dword_count); 850 sim_io_eprintf (sd, "All accounted clock cycles, total @: %" PRIu64 "\n", 851 total); 852 break; 853 854 default: 855 sim_engine_abort (sd, current_cpu, 0, 856 "Internal inconsistency at %s:%d", 857 __FILE__, __LINE__); 858 } 859 860 /* For v32, unaligned_mem_dword_count should always be 0. For 861 v10, memsrc_stall_count should always be 0. */ 862 sim_io_eprintf (sd, "Memory source stall cycles: %" PRIu64 "\n", 863 profp->memsrc_stall_count + profp->unaligned_mem_dword_count); 864 sim_io_eprintf (sd, "Memory read-after-write stall cycles: %" PRIu64 "\n", 865 profp->memraw_stall_count); 866 sim_io_eprintf (sd, "Movem source stall cycles: %" PRIu64 "\n", 867 profp->movemsrc_stall_count); 868 sim_io_eprintf (sd, "Movem destination stall cycles: %" PRIu64 "\n", 869 profp->movemdst_stall_count); 870 sim_io_eprintf (sd, "Movem address stall cycles: %" PRIu64 "\n", 871 profp->movemaddr_stall_count); 872 sim_io_eprintf (sd, "Multiplication source stall cycles: %" PRIu64 "\n", 873 profp->mulsrc_stall_count); 874 sim_io_eprintf (sd, "Jump source stall cycles: %" PRIu64 "\n", 875 profp->jumpsrc_stall_count); 876 sim_io_eprintf (sd, "Branch misprediction stall cycles: %" PRIu64 "\n", 877 profp->branch_stall_count); 878 sim_io_eprintf (sd, "Jump target stall cycles: %" PRIu64 "\n", 879 profp->jumptarget_stall_count); 880 } 881 882 /* Check whether any part of [addr .. addr + len - 1] is already mapped. 883 Return 1 if a overlap detected, 0 otherwise. */ 884 885 static USI 886 is_mapped (SIM_DESC sd ATTRIBUTE_UNUSED, 887 struct cris_sim_mmapped_page **rootp, 888 USI addr, USI len) 889 { 890 struct cris_sim_mmapped_page *mapp; 891 892 if (len == 0 || (len & 8191)) 893 abort (); 894 895 /* Iterate over the reverse-address sorted pages until we find a page in 896 or lower than the checked area. */ 897 for (mapp = *rootp; mapp != NULL && mapp->addr >= addr; mapp = mapp->prev) 898 if (mapp->addr < addr + len && mapp->addr >= addr) 899 return 1; 900 901 return 0; 902 } 903 904 /* Check whether any part of [addr .. addr + len - 1] is *un*mapped. 905 Return 1 if the whole area is mapped, 0 otherwise. */ 906 907 static USI 908 is_mapped_only (SIM_DESC sd ATTRIBUTE_UNUSED, 909 struct cris_sim_mmapped_page **rootp, 910 USI addr, USI len) 911 { 912 struct cris_sim_mmapped_page *mapp; 913 914 if (len == 0 || (len & 8191)) 915 abort (); 916 917 /* Iterate over the reverse-address sorted pages until we find a page 918 lower than the checked area. */ 919 for (mapp = *rootp; mapp != NULL && mapp->addr >= addr; mapp = mapp->prev) 920 if (addr == mapp->addr && len == 8192) 921 return 1; 922 else if (addr + len > mapp->addr) 923 len -= 8192; 924 925 return 0; 926 } 927 928 /* Provide a prototype to silence -Wmissing-prototypes. */ 929 void cris_dump_map (SIM_CPU *current_cpu); 930 931 /* Debug helper; to be run from gdb. */ 932 void 933 cris_dump_map (SIM_CPU *current_cpu) 934 { 935 struct cris_sim_cpu *cris_cpu = CRIS_SIM_CPU (current_cpu); 936 struct cris_sim_mmapped_page *mapp; 937 USI start, end; 938 939 for (mapp = cris_cpu->highest_mmapped_page, 940 start = mapp == NULL ? 0 : mapp->addr + 8192, 941 end = mapp == NULL ? 0 : mapp->addr + 8191; 942 mapp != NULL; 943 mapp = mapp->prev) 944 { 945 if (mapp->addr != start - 8192) 946 { 947 sim_io_eprintf (CPU_STATE (current_cpu), "0x%x..0x%x\n", start, end); 948 end = mapp->addr + 8191; 949 } 950 951 start = mapp->addr; 952 } 953 954 if (cris_cpu->highest_mmapped_page != NULL) 955 sim_io_eprintf (CPU_STATE (current_cpu), "0x%x..0x%x\n", start, end); 956 } 957 958 /* Create mmapped memory. ADDR is -1 if any address will do. Caller 959 must make sure that the address isn't already mapped. */ 960 961 static USI 962 create_map (SIM_DESC sd, struct cris_sim_mmapped_page **rootp, USI addr, 963 USI len) 964 { 965 struct cris_sim_mmapped_page *mapp; 966 struct cris_sim_mmapped_page **higher_prevp = rootp; 967 USI new_addr = 0x40000000; 968 969 if (addr != (USI) -1) 970 new_addr = addr; 971 else if (*rootp && rootp[0]->addr >= new_addr) 972 new_addr = rootp[0]->addr + 8192; 973 974 if (len != 8192) 975 { 976 USI page_addr; 977 978 if (len & 8191) 979 /* Which is better: return an error for this, or just round it up? */ 980 abort (); 981 982 /* Do a recursive call for each page in the request. */ 983 for (page_addr = new_addr; len != 0; page_addr += 8192, len -= 8192) 984 if (create_map (sd, rootp, page_addr, 8192) >= (USI) -8191) 985 abort (); 986 987 return new_addr; 988 } 989 990 for (mapp = *rootp; 991 mapp != NULL && mapp->addr > new_addr; 992 mapp = mapp->prev) 993 higher_prevp = &mapp->prev; 994 995 /* Assert for consistency that we don't create duplicate maps. */ 996 if (is_mapped (sd, rootp, new_addr, len)) 997 abort (); 998 999 /* Allocate the new page, on the next higher page from the last one 1000 allocated, and link in the new descriptor before previous ones. */ 1001 mapp = malloc (sizeof (*mapp)); 1002 1003 if (mapp == NULL) 1004 return (USI) -ENOMEM; 1005 1006 sim_core_attach (sd, NULL, 0, access_read_write_exec, 0, 1007 new_addr, len, 1008 0, NULL, NULL); 1009 1010 mapp->addr = new_addr; 1011 mapp->prev = *higher_prevp; 1012 *higher_prevp = mapp; 1013 1014 return new_addr; 1015 } 1016 1017 /* Unmap one or more pages. */ 1018 1019 static USI 1020 unmap_pages (SIM_DESC sd, struct cris_sim_mmapped_page **rootp, USI addr, 1021 USI len) 1022 { 1023 struct cris_sim_mmapped_page *mapp; 1024 struct cris_sim_mmapped_page **higher_prevp = rootp; 1025 1026 if (len != 8192) 1027 { 1028 USI page_addr; 1029 int ret = 0; 1030 1031 if (len & 8191) 1032 /* Which is better: return an error for this, or just round it up? */ 1033 abort (); 1034 1035 /* Loop backwards to make each call is O(1) over the number of pages 1036 allocated, if we're unmapping from the high end of the pages. */ 1037 for (page_addr = addr + len - 8192; 1038 page_addr > addr; 1039 page_addr -= 8192) 1040 if (unmap_pages (sd, rootp, page_addr, 8192)) 1041 ret = EINVAL; 1042 1043 if (unmap_pages (sd, rootp, addr, 8192)) 1044 ret = EINVAL; 1045 1046 return ret; 1047 } 1048 1049 for (mapp = *rootp; mapp != NULL && mapp->addr > addr; mapp = mapp->prev) 1050 higher_prevp = &mapp->prev; 1051 1052 if (mapp == NULL || mapp->addr != addr) 1053 return EINVAL; 1054 1055 *higher_prevp = mapp->prev; 1056 sim_core_detach (sd, NULL, 0, 0, addr); 1057 free (mapp); 1058 return 0; 1059 } 1060 1061 /* The semantic code invokes this for illegal (unrecognized) instructions. */ 1062 1063 SEM_PC 1064 sim_engine_invalid_insn (SIM_CPU *current_cpu, IADDR cia, SEM_PC vpc) 1065 { 1066 SIM_DESC sd = CPU_STATE (current_cpu); 1067 1068 sim_engine_halt (sd, current_cpu, NULL, cia, sim_stopped, SIM_SIGILL); 1069 return vpc; 1070 } 1071 1072 /* Swap one context for another. */ 1073 1074 static void 1075 schedule (SIM_CPU *current_cpu, int next) 1076 { 1077 struct cris_sim_cpu *cris_cpu = CRIS_SIM_CPU (current_cpu); 1078 1079 /* Need to mark context-switches in the trace output. */ 1080 if ((CPU_CRIS_MISC_PROFILE (current_cpu)->flags 1081 & FLAG_CRIS_MISC_PROFILE_XSIM_TRACE)) 1082 cris_trace_printf (CPU_STATE (current_cpu), current_cpu, 1083 "\t#:%d\n", next); 1084 1085 /* Copy the current context (if there is one) to its slot. */ 1086 if (cris_cpu->thread_data[cris_cpu->threadno].cpu_context) 1087 memcpy (cris_cpu->thread_data[cris_cpu->threadno].cpu_context, 1088 &cris_cpu->cpu_data_placeholder, 1089 cris_cpu->thread_cpu_data_size); 1090 1091 /* Copy the new context from its slot. */ 1092 memcpy (&cris_cpu->cpu_data_placeholder, 1093 cris_cpu->thread_data[next].cpu_context, 1094 cris_cpu->thread_cpu_data_size); 1095 1096 /* Update needed stuff to indicate the new context. */ 1097 cris_cpu->threadno = next; 1098 1099 /* Handle pending signals. */ 1100 if (cris_cpu->thread_data[next].sigpending 1101 /* We don't run nested signal handlers. This means that pause(2) 1102 and sigsuspend(2) do not work in sighandlers, but that 1103 shouldn't be too hard a restriction. It also greatly 1104 simplifies the code. */ 1105 && cris_cpu->thread_data[next].cpu_context_atsignal == NULL) 1106 { 1107 int sig; 1108 1109 /* See if there's really a pending, non-blocked handler. We don't 1110 queue signals, so just use the first one in ascending order. */ 1111 for (sig = 0; sig < 64; sig++) 1112 if (cris_cpu->thread_data[next].sigdata[sig].pending 1113 && !cris_cpu->thread_data[next].sigdata[sig].blocked) 1114 { 1115 bfd_byte regbuf[4]; 1116 USI sp; 1117 int i; 1118 USI blocked; 1119 USI pc = sim_pc_get (current_cpu); 1120 1121 /* It's simpler to save the CPU context inside the simulator 1122 than on the stack. */ 1123 cris_cpu->thread_data[next].cpu_context_atsignal 1124 = (*cris_cpu->make_thread_cpu_data) (current_cpu, 1125 cris_cpu->thread_data[next] 1126 .cpu_context); 1127 1128 (*CPU_REG_FETCH (current_cpu)) (current_cpu, H_GR_SP, regbuf, 4); 1129 sp = bfd_getl32 (regbuf); 1130 1131 /* Make sure we have an aligned stack. */ 1132 sp &= ~3; 1133 1134 /* Make room for the signal frame, aligned. FIXME: Check that 1135 the memory exists, map it in if absent. (BTW, should also 1136 implement on-access automatic stack allocation). */ 1137 sp -= 20; 1138 1139 /* This isn't the same signal frame as the kernel uses, because 1140 we don't want to bother getting all registers on and off the 1141 stack. */ 1142 1143 /* First, we store the currently blocked signals. */ 1144 blocked = 0; 1145 for (i = 0; i < 32; i++) 1146 blocked 1147 |= cris_cpu->thread_data[next].sigdata[i + 1].blocked << i; 1148 sim_core_write_aligned_4 (current_cpu, pc, 0, sp, blocked); 1149 blocked = 0; 1150 for (i = 0; i < 31; i++) 1151 blocked 1152 |= cris_cpu->thread_data[next].sigdata[i + 33].blocked << i; 1153 sim_core_write_aligned_4 (current_cpu, pc, 0, sp + 4, blocked); 1154 1155 /* Then, the actual instructions. This is CPU-specific, but we 1156 use instructions from the common subset for v10 and v32 which 1157 should be safe for the time being but could be parametrized 1158 if need be. */ 1159 /* MOVU.W [PC+],R9. */ 1160 sim_core_write_aligned_2 (current_cpu, pc, 0, sp + 8, 0x9c5f); 1161 /* .WORD TARGET_SYS_sigreturn. */ 1162 sim_core_write_aligned_2 (current_cpu, pc, 0, sp + 10, 1163 TARGET_SYS_sigreturn); 1164 /* BREAK 13. */ 1165 sim_core_write_aligned_2 (current_cpu, pc, 0, sp + 12, 0xe93d); 1166 1167 /* NOP (on v32; it's SETF on v10, but is the correct compatible 1168 instruction. Still, it doesn't matter because v10 has no 1169 delay slot for BREAK so it will not be executed). */ 1170 sim_core_write_aligned_2 (current_cpu, pc, 0, sp + 16, 0x05b0); 1171 1172 /* Modify registers to hold the right values for the sighandler 1173 context: updated stackpointer and return address pointing to 1174 the sigreturn stub. */ 1175 bfd_putl32 (sp, regbuf); 1176 (*CPU_REG_STORE (current_cpu)) (current_cpu, H_GR_SP, regbuf, 4); 1177 bfd_putl32 (sp + 8, regbuf); 1178 (*CPU_REG_STORE (current_cpu)) (current_cpu, TARGET_SRP_REGNUM, 1179 regbuf, 4); 1180 1181 cris_cpu->thread_data[next].sigdata[sig].pending = 0; 1182 1183 /* Block this signal (for the duration of the sighandler). */ 1184 cris_cpu->thread_data[next].sigdata[sig].blocked = 1; 1185 1186 sim_pc_set (current_cpu, cris_cpu->sighandler[sig]); 1187 bfd_putl32 (sig, regbuf); 1188 (*CPU_REG_STORE (current_cpu)) (current_cpu, H_GR_R10, 1189 regbuf, 4); 1190 1191 /* We ignore a SA_SIGINFO flag in the sigaction call; the code I 1192 needed all this for, specifies a SA_SIGINFO call but treats it 1193 like an ordinary sighandler; only the signal number argument is 1194 inspected. To make future need to implement SA_SIGINFO 1195 correctly possible, we set the siginfo argument register to a 1196 magic (hopefully non-address) number. (NB: then, you should 1197 just need to pass the siginfo argument; it seems you probably 1198 don't need to implement the specific rt_sigreturn.) */ 1199 bfd_putl32 (0xbad5161f, regbuf); 1200 (*CPU_REG_STORE (current_cpu)) (current_cpu, H_GR_R11, 1201 regbuf, 4); 1202 1203 /* The third argument is unused and the kernel sets it to 0. */ 1204 bfd_putl32 (0, regbuf); 1205 (*CPU_REG_STORE (current_cpu)) (current_cpu, H_GR_R12, 1206 regbuf, 4); 1207 return; 1208 } 1209 1210 /* No, there actually was no pending signal for this thread. Reset 1211 this flag. */ 1212 cris_cpu->thread_data[next].sigpending = 0; 1213 } 1214 } 1215 1216 /* Reschedule the simplest possible way until something else is absolutely 1217 necessary: 1218 - A. Find the next process (round-robin) that doesn't have at_syscall 1219 set, schedule it. 1220 - B. If there is none, just run the next process, round-robin. 1221 - Clear at_syscall for the current process. */ 1222 1223 static void 1224 reschedule (SIM_CPU *current_cpu) 1225 { 1226 SIM_DESC sd = CPU_STATE (current_cpu); 1227 struct cris_sim_cpu *cris_cpu = CRIS_SIM_CPU (current_cpu); 1228 int i; 1229 1230 /* Iterate over all thread slots, because after a few thread creations 1231 and exits, we don't know where the live ones are. */ 1232 for (i = (cris_cpu->threadno + 1) % SIM_TARGET_MAX_THREADS; 1233 i != cris_cpu->threadno; 1234 i = (i + 1) % SIM_TARGET_MAX_THREADS) 1235 if (cris_cpu->thread_data[i].cpu_context 1236 && cris_cpu->thread_data[i].at_syscall == 0) 1237 { 1238 schedule (current_cpu, i); 1239 return; 1240 } 1241 1242 /* Pick any next live thread. */ 1243 for (i = (cris_cpu->threadno + 1) % SIM_TARGET_MAX_THREADS; 1244 i != cris_cpu->threadno; 1245 i = (i + 1) % SIM_TARGET_MAX_THREADS) 1246 if (cris_cpu->thread_data[i].cpu_context) 1247 { 1248 schedule (current_cpu, i); 1249 return; 1250 } 1251 1252 /* More than one live thread, but we couldn't find the next one? */ 1253 abort (); 1254 } 1255 1256 /* Set up everything to receive (or IGN) an incoming signal to the 1257 current context. */ 1258 1259 static int 1260 deliver_signal (SIM_CPU *current_cpu, int sig, unsigned int pid) 1261 { 1262 struct cris_sim_cpu *cris_cpu = CRIS_SIM_CPU (current_cpu); 1263 int i; 1264 USI pc = sim_pc_get (current_cpu); 1265 1266 /* Find the thread index of the pid. */ 1267 for (i = 0; i < SIM_TARGET_MAX_THREADS; i++) 1268 /* Apparently it's ok to send signals to zombies (so a check for 1269 cris_cpu->thread_data[i].cpu_context != NULL would be wrong). */ 1270 if (cris_cpu->thread_data[i].threadid == pid - TARGET_PID) 1271 { 1272 if (sig < 64) 1273 switch (cris_cpu->sighandler[sig]) 1274 { 1275 case TARGET_SIG_DFL: 1276 switch (sig) 1277 { 1278 /* The following according to the glibc 1279 documentation. (The kernel code has non-obvious 1280 execution paths.) */ 1281 case TARGET_SIGFPE: 1282 case TARGET_SIGILL: 1283 case TARGET_SIGSEGV: 1284 case TARGET_SIGBUS: 1285 case TARGET_SIGABRT: 1286 case TARGET_SIGTRAP: 1287 case TARGET_SIGSYS: 1288 1289 case TARGET_SIGTERM: 1290 case TARGET_SIGINT: 1291 case TARGET_SIGQUIT: 1292 case TARGET_SIGKILL: 1293 case TARGET_SIGHUP: 1294 1295 case TARGET_SIGALRM: 1296 case TARGET_SIGVTALRM: 1297 case TARGET_SIGPROF: 1298 case TARGET_SIGSTOP: 1299 1300 case TARGET_SIGPIPE: 1301 case TARGET_SIGLOST: 1302 case TARGET_SIGXCPU: 1303 case TARGET_SIGXFSZ: 1304 case TARGET_SIGUSR1: 1305 case TARGET_SIGUSR2: 1306 sim_io_eprintf (CPU_STATE (current_cpu), 1307 "Exiting pid %d due to signal %d\n", 1308 pid, sig); 1309 sim_engine_halt (CPU_STATE (current_cpu), current_cpu, 1310 NULL, pc, sim_stopped, 1311 sig == TARGET_SIGABRT 1312 ? SIM_SIGABRT : SIM_SIGILL); 1313 return 0; 1314 1315 /* The default for all other signals is to be ignored. */ 1316 default: 1317 return 0; 1318 } 1319 1320 case TARGET_SIG_IGN: 1321 switch (sig) 1322 { 1323 case TARGET_SIGKILL: 1324 case TARGET_SIGSTOP: 1325 /* Can't ignore these signals. */ 1326 sim_io_eprintf (CPU_STATE (current_cpu), 1327 "Exiting pid %d due to signal %d\n", 1328 pid, sig); 1329 sim_engine_halt (CPU_STATE (current_cpu), current_cpu, 1330 NULL, pc, sim_stopped, SIM_SIGILL); 1331 return 0; 1332 1333 default: 1334 return 0; 1335 } 1336 break; 1337 1338 default: 1339 /* Mark the signal as pending, making schedule () check 1340 closer. The signal will be handled when the thread is 1341 scheduled and the signal is unblocked. */ 1342 cris_cpu->thread_data[i].sigdata[sig].pending = 1; 1343 cris_cpu->thread_data[i].sigpending = 1; 1344 return 0; 1345 } 1346 else 1347 { 1348 sim_io_eprintf (CPU_STATE (current_cpu), 1349 "Unimplemented signal: %d\n", sig); 1350 sim_engine_halt (CPU_STATE (current_cpu), current_cpu, NULL, pc, 1351 sim_stopped, SIM_SIGILL); 1352 } 1353 } 1354 1355 return 1356 -cb_host_to_target_errno (STATE_CALLBACK (CPU_STATE (current_cpu)), 1357 ESRCH); 1358 } 1359 1360 /* Make the vector and the first item, the main thread. */ 1361 1362 static void 1363 make_first_thread (SIM_CPU *current_cpu) 1364 { 1365 SIM_DESC sd = CPU_STATE (current_cpu); 1366 struct cris_sim_cpu *cris_cpu = CRIS_SIM_CPU (current_cpu); 1367 1368 cris_cpu->thread_data 1369 = xcalloc (1, SIM_TARGET_MAX_THREADS * sizeof (cris_cpu->thread_data[0])); 1370 cris_cpu->thread_data[0].cpu_context 1371 = (*cris_cpu->make_thread_cpu_data) (current_cpu, 1372 &cris_cpu->cpu_data_placeholder); 1373 cris_cpu->thread_data[0].parent_threadid = -1; 1374 1375 /* For good measure. */ 1376 if (TARGET_SIG_DFL != 0) 1377 abort (); 1378 } 1379 1380 /* Handle unknown system calls. Returns (if it does) the syscall 1381 return value. */ 1382 1383 static USI ATTRIBUTE_PRINTF (3, 4) 1384 cris_unknown_syscall (SIM_CPU *current_cpu, USI pc, char *s, ...) 1385 { 1386 SIM_DESC sd = CPU_STATE (current_cpu); 1387 host_callback *cb = STATE_CALLBACK (sd); 1388 1389 if (cris_unknown_syscall_action == CRIS_USYSC_MSG_STOP 1390 || cris_unknown_syscall_action == CRIS_USYSC_MSG_ENOSYS) 1391 { 1392 va_list ap; 1393 1394 va_start (ap, s); 1395 sim_io_evprintf (sd, s, ap); 1396 va_end (ap); 1397 1398 if (cris_unknown_syscall_action == CRIS_USYSC_MSG_STOP) 1399 sim_engine_halt (sd, current_cpu, NULL, pc, sim_stopped, SIM_SIGILL); 1400 } 1401 1402 return -cb_host_to_target_errno (cb, ENOSYS); 1403 } 1404 1405 /* Main function: the handler of the "break 13" syscall insn. */ 1406 1407 USI 1408 cris_break_13_handler (SIM_CPU *current_cpu, USI callnum, USI arg1, 1409 USI arg2, USI arg3, USI arg4, USI arg5, USI arg6, 1410 USI pc) 1411 { 1412 CB_SYSCALL s; 1413 SIM_DESC sd = CPU_STATE (current_cpu); 1414 struct cris_sim_cpu *cris_cpu = CRIS_SIM_CPU (current_cpu); 1415 host_callback *cb = STATE_CALLBACK (sd); 1416 int retval; 1417 int threadno = cris_cpu->threadno; 1418 1419 cris_cpu->syscalls++; 1420 1421 CB_SYSCALL_INIT (&s); 1422 s.func = callnum; 1423 s.arg1 = arg1; 1424 s.arg2 = arg2; 1425 s.arg3 = arg3; 1426 1427 /* The type of s.arg2 is long, so for hosts with 64-bit longs, we need 1428 to sign-extend the lseek offset to be passed as a signed number, 1429 else we'll truncate it to something > 2GB on hosts where sizeof 1430 long > sizeof USI. We avoid doing it for all syscalls, as arg2 is 1431 e.g. an address for some syscalls. */ 1432 if (callnum == TARGET_SYS_lseek) 1433 s.arg2 = (SI) arg2; 1434 1435 if (callnum == TARGET_SYS_exit_group 1436 || (callnum == TARGET_SYS_exit && cris_cpu->m1threads == 0)) 1437 { 1438 if (CPU_CRIS_MISC_PROFILE (current_cpu)->flags 1439 & FLAG_CRIS_MISC_PROFILE_ALL) 1440 dump_statistics (current_cpu); 1441 sim_engine_halt (sd, current_cpu, NULL, pc, sim_exited, arg1); 1442 } 1443 1444 s.p1 = sd; 1445 s.p2 = current_cpu; 1446 s.read_mem = sim_syscall_read_mem; 1447 s.write_mem = sim_syscall_write_mem; 1448 1449 current_cpu_for_cb_callback = current_cpu; 1450 1451 if (cb_syscall (cb, &s) != CB_RC_OK) 1452 { 1453 sim_engine_abort (sd, current_cpu, pc, 1454 "Break 13: invalid %d? Returned %ld\n", callnum, 1455 s.result); 1456 } 1457 1458 retval = s.result == -1 ? -s.errcode : s.result; 1459 1460 if (s.errcode != 0 && s.errcode == cb_host_to_target_errno (cb, ENOSYS)) 1461 { 1462 /* If the generic simulator call said ENOSYS, then let's try the 1463 ones we know ourselves. 1464 1465 The convention is to provide *very limited* functionality on an 1466 as-needed basis, only what's covered by the test-suite, tests 1467 added when functionality changes and abort with a descriptive 1468 message for *everything* else. Where there's no test-case, we 1469 just abort. */ 1470 switch (callnum) 1471 { 1472 case 0: 1473 /* It's a pretty safe bet that the "old setup() system call" 1474 number will not be re-used; we can't say the same for higher 1475 numbers. We treat this simulator-generated call as "wait 1476 forever"; we re-run this insn. The wait is ended by a 1477 callback. Sanity check that this is the reason we got 1478 here. */ 1479 if (cris_cpu->thread_data == NULL 1480 || (cris_cpu->thread_data[threadno].pipe_write_fd == 0)) 1481 goto unimplemented_syscall; 1482 1483 sim_pc_set (current_cpu, pc); 1484 retval = arg1; 1485 break; 1486 1487 case TARGET_SYS_fcntl64: 1488 case TARGET_SYS_fcntl: 1489 switch (arg2) 1490 { 1491 case 1: 1492 /* F_GETFD. 1493 Glibc checks stdin, stdout and stderr fd:s for 1494 close-on-exec security sanity. We just need to provide a 1495 OK return value. If we really need to have a 1496 close-on-exec flag true, we could just do a real fcntl 1497 here. */ 1498 retval = 0; 1499 break; 1500 1501 case 2: 1502 /* F_SETFD. Just ignore attempts to set the close-on-exec 1503 flag. */ 1504 retval = 0; 1505 break; 1506 1507 case 3: 1508 /* F_GETFL. Check for the special case for open+fdopen. */ 1509 if (cris_cpu->last_syscall == TARGET_SYS_open 1510 && arg1 == cris_cpu->last_open_fd) 1511 { 1512 retval = cris_cpu->last_open_flags & TARGET_O_ACCMODE; 1513 break; 1514 } 1515 else if (arg1 == 0) 1516 { 1517 /* Because we can't freopen fd:s 0, 1, 2 to mean 1518 something else than stdin, stdout and stderr 1519 (sim/common/syscall.c:cb_syscall special cases fd 1520 0, 1 and 2), we know what flags that we can 1521 sanely return for these fd:s. */ 1522 retval = TARGET_O_RDONLY; 1523 break; 1524 } 1525 else if (arg1 == 1 || arg1 == 2) 1526 { 1527 retval = TARGET_O_WRONLY; 1528 break; 1529 } 1530 ATTRIBUTE_FALLTHROUGH; 1531 default: 1532 /* Nothing else is implemented. */ 1533 retval 1534 = cris_unknown_syscall (current_cpu, pc, 1535 "Unimplemented %s syscall " 1536 "(fd: 0x%lx: cmd: 0x%lx arg: " 1537 "0x%lx)\n", 1538 callnum == TARGET_SYS_fcntl 1539 ? "fcntl" : "fcntl64", 1540 (unsigned long) (USI) arg1, 1541 (unsigned long) (USI) arg2, 1542 (unsigned long) (USI) arg3); 1543 break; 1544 } 1545 break; 1546 1547 case TARGET_SYS_uname: 1548 { 1549 /* Fill in a few constants to appease glibc. */ 1550 static char sim_utsname[6][65] = 1551 { 1552 "Linux", 1553 "sim-target", 1554 "2.6.27", 1555 TARGET_UTSNAME, 1556 "cris", /* Overwritten below. */ 1557 "localdomain" 1558 }; 1559 1560 /* Having the hardware type in Linux equal to the bfd 1561 printable name is deliberate: if you make config.guess 1562 work on your Linux-type system the usual way, it 1563 probably will; either the bfd printable_name or the 1564 ambiguous arch_name. */ 1565 strcpy (sim_utsname[4], STATE_ARCHITECTURE (sd)->printable_name); 1566 1567 if ((s.write_mem) (cb, &s, arg1, (const char *) sim_utsname, 1568 sizeof (sim_utsname)) 1569 != sizeof (sim_utsname)) 1570 retval = -cb_host_to_target_errno (cb, EFAULT); 1571 else 1572 retval = 0; 1573 break; 1574 } 1575 1576 case TARGET_SYS_geteuid32: 1577 /* We tell the truth with these. Maybe we shouldn't, but it 1578 should match the "stat" information. */ 1579 retval = geteuid (); 1580 break; 1581 1582 case TARGET_SYS_getuid32: 1583 retval = getuid (); 1584 break; 1585 1586 case TARGET_SYS_getegid32: 1587 retval = getegid (); 1588 break; 1589 1590 case TARGET_SYS_getgid32: 1591 retval = getgid (); 1592 break; 1593 1594 case TARGET_SYS_brk: 1595 /* Most often, we just return the argument, like the Linux 1596 kernel. */ 1597 retval = arg1; 1598 1599 if (arg1 == 0) 1600 retval = cris_cpu->endbrk; 1601 else if (arg1 <= cris_cpu->endmem) 1602 cris_cpu->endbrk = arg1; 1603 else 1604 { 1605 USI new_end = (arg1 + 8191) & ~8191; 1606 1607 /* If the simulator wants to brk more than a certain very 1608 large amount, something is wrong. FIXME: Return an error 1609 or abort? Have command-line selectable? */ 1610 if (new_end - cris_cpu->endmem > SIM_MAX_ALLOC_CHUNK) 1611 { 1612 cris_cpu->endbrk = cris_cpu->endmem; 1613 retval = cris_cpu->endmem; 1614 break; 1615 } 1616 1617 sim_core_attach (sd, NULL, 0, access_read_write_exec, 0, 1618 cris_cpu->endmem, 1619 new_end - cris_cpu->endmem, 1620 0, NULL, NULL); 1621 cris_cpu->endbrk = arg1; 1622 cris_cpu->endmem = new_end; 1623 } 1624 break; 1625 1626 case TARGET_SYS_getpid: 1627 /* Correct until CLONE_THREAD is implemented. */ 1628 retval = cris_cpu->thread_data == NULL 1629 ? TARGET_PID 1630 : TARGET_PID + cris_cpu->thread_data[threadno].threadid; 1631 break; 1632 1633 case TARGET_SYS_getppid: 1634 /* Correct until CLONE_THREAD is implemented. */ 1635 retval = cris_cpu->thread_data == NULL 1636 ? TARGET_PID - 1 1637 : (TARGET_PID 1638 + cris_cpu->thread_data[threadno].parent_threadid); 1639 break; 1640 1641 case TARGET_SYS_mmap2: 1642 { 1643 USI addr = arg1; 1644 USI len = arg2; 1645 USI prot = arg3; 1646 USI flags = arg4; 1647 USI fd = arg5; 1648 USI pgoff = arg6; 1649 1650 /* At 2.6.27, Linux (many (all?) ports, in the mmap2 syscalls) 1651 still masked away this bit, so let's just ignore 1652 it. */ 1653 flags &= ~TARGET_MAP_DENYWRITE; 1654 1655 /* If the simulator wants to mmap more than the very large 1656 limit, something is wrong. FIXME: Return an error or 1657 abort? Have command-line selectable? */ 1658 if (len > SIM_MAX_ALLOC_CHUNK) 1659 { 1660 retval = -cb_host_to_target_errno (cb, ENOMEM); 1661 break; 1662 } 1663 1664 if ((prot != (TARGET_PROT_READ | TARGET_PROT_WRITE) 1665 && (prot 1666 != (TARGET_PROT_READ 1667 | TARGET_PROT_WRITE 1668 | TARGET_PROT_EXEC)) 1669 && (prot != (TARGET_PROT_READ | TARGET_PROT_EXEC)) 1670 && prot != TARGET_PROT_READ) 1671 || (flags != (TARGET_MAP_ANONYMOUS | TARGET_MAP_PRIVATE) 1672 && flags != TARGET_MAP_PRIVATE 1673 && flags != (TARGET_MAP_ANONYMOUS 1674 | TARGET_MAP_PRIVATE | TARGET_MAP_FIXED) 1675 && flags != (TARGET_MAP_PRIVATE | TARGET_MAP_FIXED) 1676 && flags != TARGET_MAP_SHARED) 1677 || (fd != (USI) -1 1678 && prot != TARGET_PROT_READ 1679 && prot != (TARGET_PROT_READ | TARGET_PROT_EXEC) 1680 && prot != (TARGET_PROT_READ | TARGET_PROT_WRITE)) 1681 || (fd == (USI) -1 && pgoff != 0) 1682 || (fd != (USI) -1 && (flags & TARGET_MAP_ANONYMOUS))) 1683 { 1684 retval 1685 = cris_unknown_syscall (current_cpu, pc, 1686 "Unimplemented mmap2 call " 1687 "(0x%lx, 0x%lx, 0x%lx, " 1688 "0x%lx, 0x%lx, 0x%lx)\n", 1689 (unsigned long) arg1, 1690 (unsigned long) arg2, 1691 (unsigned long) arg3, 1692 (unsigned long) arg4, 1693 (unsigned long) arg5, 1694 (unsigned long) arg6); 1695 break; 1696 } 1697 else if (fd != (USI) -1) 1698 { 1699 /* Map a file. */ 1700 1701 USI newaddr; 1702 USI pos; 1703 1704 /* A non-aligned argument is allowed for files. */ 1705 USI newlen = (len + 8191) & ~8191; 1706 1707 /* We only support read, read|exec, and read|write, 1708 which we should already have checked. Check again 1709 anyway. */ 1710 if (prot != TARGET_PROT_READ 1711 && prot != (TARGET_PROT_READ | TARGET_PROT_EXEC) 1712 && prot != (TARGET_PROT_READ | TARGET_PROT_WRITE)) 1713 abort (); 1714 1715 if (flags & TARGET_MAP_FIXED) 1716 unmap_pages (sd, &cris_cpu->highest_mmapped_page, 1717 addr, newlen); 1718 else if (is_mapped (sd, &cris_cpu->highest_mmapped_page, 1719 addr, newlen)) 1720 addr = 0; 1721 1722 newaddr 1723 = create_map (sd, &cris_cpu->highest_mmapped_page, 1724 addr != 0 || (flags & TARGET_MAP_FIXED) 1725 ? addr : -1, 1726 newlen); 1727 1728 if (newaddr >= (USI) -8191) 1729 { 1730 abort (); 1731 retval = -cb_host_to_target_errno (cb, -(SI) newaddr); 1732 break; 1733 } 1734 1735 /* We were asked for MAP_FIXED, but couldn't. */ 1736 if ((flags & TARGET_MAP_FIXED) && newaddr != addr) 1737 { 1738 abort (); 1739 unmap_pages (sd, &cris_cpu->highest_mmapped_page, 1740 newaddr, newlen); 1741 retval = -cb_host_to_target_errno (cb, EINVAL); 1742 break; 1743 } 1744 1745 /* Find the current position in the file. */ 1746 s.func = TARGET_SYS_lseek; 1747 s.arg1 = fd; 1748 s.arg2 = 0; 1749 s.arg3 = SEEK_CUR; 1750 if (cb_syscall (cb, &s) != CB_RC_OK) 1751 abort (); 1752 pos = s.result; 1753 1754 if (s.result < 0) 1755 abort (); 1756 1757 /* Move to the correct offset in the file. */ 1758 s.func = TARGET_SYS_lseek; 1759 s.arg1 = fd; 1760 s.arg2 = pgoff*8192; 1761 s.arg3 = SEEK_SET; 1762 if (cb_syscall (cb, &s) != CB_RC_OK) 1763 abort (); 1764 1765 if (s.result < 0) 1766 abort (); 1767 1768 /* Use the standard read callback to read in "len" 1769 bytes. */ 1770 s.func = TARGET_SYS_read; 1771 s.arg1 = fd; 1772 s.arg2 = newaddr; 1773 s.arg3 = len; 1774 if (cb_syscall (cb, &s) != CB_RC_OK) 1775 abort (); 1776 1777 /* If the result is a page or more lesser than what 1778 was requested, something went wrong. */ 1779 if (len >= 8192 && (USI) s.result <= len - 8192) 1780 abort (); 1781 1782 /* After reading, we need to go back to the previous 1783 position in the file. */ 1784 s.func = TARGET_SYS_lseek; 1785 s.arg1 = fd; 1786 s.arg2 = pos; 1787 s.arg3 = SEEK_SET; 1788 if (cb_syscall (cb, &s) != CB_RC_OK) 1789 abort (); 1790 if (pos != (USI) s.result) 1791 abort (); 1792 1793 retval = newaddr; 1794 } 1795 else 1796 { 1797 USI newlen = (len + 8191) & ~8191; 1798 USI newaddr; 1799 1800 if (flags & TARGET_MAP_FIXED) 1801 unmap_pages (sd, &cris_cpu->highest_mmapped_page, 1802 addr, newlen); 1803 else if (is_mapped (sd, &cris_cpu->highest_mmapped_page, 1804 addr, newlen)) 1805 addr = 0; 1806 1807 newaddr = create_map (sd, &cris_cpu->highest_mmapped_page, 1808 addr != 0 || (flags & TARGET_MAP_FIXED) 1809 ? addr : -1, 1810 newlen); 1811 1812 if (newaddr >= (USI) -8191) 1813 retval = -cb_host_to_target_errno (cb, -(SI) newaddr); 1814 else 1815 retval = newaddr; 1816 1817 if ((flags & TARGET_MAP_FIXED) && newaddr != addr) 1818 { 1819 abort (); 1820 unmap_pages (sd, &cris_cpu->highest_mmapped_page, 1821 newaddr, newlen); 1822 retval = -cb_host_to_target_errno (cb, EINVAL); 1823 break; 1824 } 1825 } 1826 break; 1827 } 1828 1829 case TARGET_SYS_mprotect: 1830 { 1831 /* We only cover the case of linuxthreads mprotecting out 1832 its stack guard page and of dynamic loading mprotecting 1833 away the data (for some reason the whole library, then 1834 mprotects away the data part and mmap-FIX:es it again. */ 1835 USI addr = arg1; 1836 USI len = arg2; 1837 USI prot = arg3; 1838 1839 if (prot != TARGET_PROT_NONE 1840 || !is_mapped_only (sd, &cris_cpu->highest_mmapped_page, 1841 addr, (len + 8191) & ~8191)) 1842 { 1843 retval 1844 = cris_unknown_syscall (current_cpu, pc, 1845 "Unimplemented mprotect call " 1846 "(0x%lx, 0x%lx, 0x%lx)\n", 1847 (unsigned long) arg1, 1848 (unsigned long) arg2, 1849 (unsigned long) arg3); 1850 break; 1851 } 1852 1853 /* Just ignore this. We could make this equal to munmap, 1854 but then we'd have to make sure no anon mmaps gets this 1855 address before a subsequent MAP_FIXED mmap intended to 1856 override it. */ 1857 retval = 0; 1858 break; 1859 } 1860 1861 case TARGET_SYS_ioctl: 1862 { 1863 /* We support only a very limited functionality: checking 1864 stdout with TCGETS to perform the isatty function. The 1865 TCGETS ioctl isn't actually performed or the result used by 1866 an isatty () caller in a "hello, world" program; only the 1867 return value is then used. Maybe we shouldn't care about 1868 the environment of the simulator regarding isatty, but 1869 that's been working before, in the xsim simulator. */ 1870 if (arg2 == TARGET_TCGETS && arg1 == 1) 1871 retval = isatty (1) ? 0 : cb_host_to_target_errno (cb, EINVAL); 1872 else 1873 retval = -cb_host_to_target_errno (cb, EINVAL); 1874 break; 1875 } 1876 1877 case TARGET_SYS_munmap: 1878 { 1879 USI addr = arg1; 1880 USI len = arg2; 1881 USI result 1882 = unmap_pages (sd, &cris_cpu->highest_mmapped_page, addr, 1883 len); 1884 retval = result != 0 ? -cb_host_to_target_errno (cb, result) : 0; 1885 break; 1886 } 1887 1888 case TARGET_SYS_wait4: 1889 { 1890 int i; 1891 USI pid = arg1; 1892 USI saddr = arg2; 1893 USI options = arg3; 1894 USI rusagep = arg4; 1895 1896 /* FIXME: We're not properly implementing __WCLONE, and we 1897 don't really need the special casing so we might as well 1898 make this general. */ 1899 if ((!(pid == (USI) -1 1900 && options == (TARGET___WCLONE | TARGET_WNOHANG) 1901 && saddr != 0) 1902 && !(pid > 0 1903 && (options == TARGET___WCLONE 1904 || options == TARGET___WALL))) 1905 || rusagep != 0 1906 || cris_cpu->thread_data == NULL) 1907 { 1908 retval 1909 = cris_unknown_syscall (current_cpu, pc, 1910 "Unimplemented wait4 call " 1911 "(0x%lx, 0x%lx, 0x%lx, 0x%lx)\n", 1912 (unsigned long) arg1, 1913 (unsigned long) arg2, 1914 (unsigned long) arg3, 1915 (unsigned long) arg4); 1916 break; 1917 } 1918 1919 if (pid == (USI) -1) 1920 for (i = 1; i < SIM_TARGET_MAX_THREADS; i++) 1921 { 1922 if (cris_cpu->thread_data[threadno].threadid 1923 == cris_cpu->thread_data[i].parent_threadid 1924 && cris_cpu->thread_data[i].threadid != 0 1925 && cris_cpu->thread_data[i].cpu_context == NULL) 1926 { 1927 /* A zombied child. Get the exit value and clear the 1928 zombied entry so it will be reused. */ 1929 sim_core_write_unaligned_4 (current_cpu, pc, 0, saddr, 1930 cris_cpu 1931 ->thread_data[i].exitval); 1932 retval 1933 = cris_cpu->thread_data[i].threadid + TARGET_PID; 1934 memset (&cris_cpu->thread_data[i], 0, 1935 sizeof (cris_cpu->thread_data[i])); 1936 goto outer_break; 1937 } 1938 } 1939 else 1940 { 1941 /* We're waiting for a specific PID. If we don't find 1942 it zombied on this run, rerun the syscall. */ 1943 for (i = 1; i < SIM_TARGET_MAX_THREADS; i++) 1944 if (pid == cris_cpu->thread_data[i].threadid + TARGET_PID 1945 && cris_cpu->thread_data[i].cpu_context == NULL) 1946 { 1947 if (saddr != 0) 1948 /* Get the exit value if the caller wants it. */ 1949 sim_core_write_unaligned_4 (current_cpu, pc, 0, 1950 saddr, 1951 cris_cpu 1952 ->thread_data[i].exitval); 1953 1954 retval 1955 = cris_cpu->thread_data[i].threadid + TARGET_PID; 1956 memset (&cris_cpu->thread_data[i], 0, 1957 sizeof (cris_cpu->thread_data[i])); 1958 1959 goto outer_break; 1960 } 1961 1962 sim_pc_set (current_cpu, pc); 1963 } 1964 1965 retval = -cb_host_to_target_errno (cb, ECHILD); 1966 outer_break: 1967 break; 1968 } 1969 1970 case TARGET_SYS_rt_sigaction: 1971 { 1972 USI signum = arg1; 1973 USI old_sa = arg3; 1974 USI new_sa = arg2; 1975 1976 /* The kernel says: 1977 struct sigaction { 1978 __sighandler_t sa_handler; 1979 unsigned long sa_flags; 1980 void (*sa_restorer)(void); 1981 sigset_t sa_mask; 1982 }; */ 1983 1984 if (old_sa != 0) 1985 { 1986 sim_core_write_unaligned_4 (current_cpu, pc, 0, old_sa + 0, 1987 cris_cpu->sighandler[signum]); 1988 sim_core_write_unaligned_4 (current_cpu, pc, 0, arg3 + 4, 0); 1989 sim_core_write_unaligned_4 (current_cpu, pc, 0, arg3 + 8, 0); 1990 1991 /* We'll assume _NSIG_WORDS is 2 for the kernel. */ 1992 sim_core_write_unaligned_4 (current_cpu, pc, 0, arg3 + 12, 0); 1993 sim_core_write_unaligned_4 (current_cpu, pc, 0, arg3 + 16, 0); 1994 } 1995 if (new_sa != 0) 1996 { 1997 USI target_sa_handler 1998 = sim_core_read_unaligned_4 (current_cpu, pc, 0, new_sa); 1999 USI target_sa_flags 2000 = sim_core_read_unaligned_4 (current_cpu, pc, 0, new_sa + 4); 2001 USI target_sa_restorer 2002 = sim_core_read_unaligned_4 (current_cpu, pc, 0, new_sa + 8); 2003 USI target_sa_mask_low 2004 = sim_core_read_unaligned_4 (current_cpu, pc, 0, new_sa + 12); 2005 USI target_sa_mask_high 2006 = sim_core_read_unaligned_4 (current_cpu, pc, 0, new_sa + 16); 2007 2008 /* We won't interrupt a syscall so we won't restart it, 2009 but a signal(2) call ends up syscalling rt_sigaction 2010 with this flag, so we have to handle it. The 2011 sa_restorer field contains garbage when not 2012 TARGET_SA_RESTORER, so don't look at it. For the 2013 time being, we don't nest sighandlers, so we 2014 ignore the sa_mask, which simplifies things. */ 2015 if ((target_sa_flags != 0 2016 && target_sa_flags != TARGET_SA_RESTART 2017 && target_sa_flags != (TARGET_SA_RESTART|TARGET_SA_SIGINFO)) 2018 || target_sa_handler == 0) 2019 { 2020 retval 2021 = cris_unknown_syscall (current_cpu, pc, 2022 "Unimplemented rt_sigaction " 2023 "syscall " 2024 "(0x%lx, 0x%lx: " 2025 "[0x%x, 0x%x, 0x%x, " 2026 "{0x%x, 0x%x}], 0x%lx)\n", 2027 (unsigned long) arg1, 2028 (unsigned long) arg2, 2029 target_sa_handler, 2030 target_sa_flags, 2031 target_sa_restorer, 2032 target_sa_mask_low, 2033 target_sa_mask_high, 2034 (unsigned long) arg3); 2035 break; 2036 } 2037 2038 cris_cpu->sighandler[signum] = target_sa_handler; 2039 2040 /* Because we may have unblocked signals, one may now be 2041 pending, if there are threads, that is. */ 2042 if (cris_cpu->thread_data) 2043 cris_cpu->thread_data[threadno].sigpending = 1; 2044 } 2045 retval = 0; 2046 break; 2047 } 2048 2049 case TARGET_SYS_mremap: 2050 { 2051 USI addr = arg1; 2052 USI old_len = arg2; 2053 USI new_len = arg3; 2054 USI flags = arg4; 2055 USI new_addr = arg5; 2056 USI mapped_addr; 2057 2058 if (new_len == old_len) 2059 /* The program and/or library is possibly confused but 2060 this is a valid call. Happens with ipps-1.40 on file 2061 svs_all. */ 2062 retval = addr; 2063 else if (new_len < old_len) 2064 { 2065 /* Shrinking is easy. */ 2066 if (unmap_pages (sd, &cris_cpu->highest_mmapped_page, 2067 addr + new_len, old_len - new_len) != 0) 2068 retval = -cb_host_to_target_errno (cb, EINVAL); 2069 else 2070 retval = addr; 2071 } 2072 else if (! is_mapped (sd, &cris_cpu->highest_mmapped_page, 2073 addr + old_len, new_len - old_len)) 2074 { 2075 /* If the extension isn't mapped, we can just add it. */ 2076 mapped_addr 2077 = create_map (sd, &cris_cpu->highest_mmapped_page, 2078 addr + old_len, new_len - old_len); 2079 2080 if (mapped_addr > (USI) -8192) 2081 retval = -cb_host_to_target_errno (cb, -(SI) mapped_addr); 2082 else 2083 retval = addr; 2084 } 2085 else if (flags & TARGET_MREMAP_MAYMOVE) 2086 { 2087 /* Create a whole new map and copy the contents 2088 block-by-block there. We ignore the new_addr argument 2089 for now. */ 2090 char buf[8192]; 2091 USI prev_addr = addr; 2092 USI prev_len = old_len; 2093 2094 mapped_addr 2095 = create_map (sd, &cris_cpu->highest_mmapped_page, 2096 -1, new_len); 2097 2098 if (mapped_addr > (USI) -8192) 2099 { 2100 retval = -cb_host_to_target_errno (cb, -(SI) new_addr); 2101 break; 2102 } 2103 2104 retval = mapped_addr; 2105 2106 for (; old_len > 0; 2107 old_len -= 8192, mapped_addr += 8192, addr += 8192) 2108 { 2109 if (sim_core_read_buffer (sd, current_cpu, read_map, buf, 2110 addr, 8192) != 8192 2111 || sim_core_write_buffer (sd, current_cpu, 0, buf, 2112 mapped_addr, 8192) != 8192) 2113 abort (); 2114 } 2115 2116 if (unmap_pages (sd, &cris_cpu->highest_mmapped_page, 2117 prev_addr, prev_len) != 0) 2118 abort (); 2119 } 2120 else 2121 retval = -cb_host_to_target_errno (cb, -ENOMEM); 2122 break; 2123 } 2124 2125 case TARGET_SYS_poll: 2126 { 2127 int npollfds = arg2; 2128 int timeout = arg3; 2129 SI ufds = arg1; 2130 SI fd = -1; 2131 HI events = -1; 2132 HI revents = 0; 2133 struct stat buf; 2134 int i; 2135 2136 /* The kernel says: 2137 struct pollfd { 2138 int fd; 2139 short events; 2140 short revents; 2141 }; */ 2142 2143 /* Check that this is the expected poll call from 2144 linuxthreads/manager.c; we don't support anything else. 2145 Remember, fd == 0 isn't supported. */ 2146 if (npollfds != 1 2147 || ((fd = sim_core_read_unaligned_4 (current_cpu, pc, 2148 0, ufds)) <= 0) 2149 || ((events = sim_core_read_unaligned_2 (current_cpu, pc, 2150 0, ufds + 4)) 2151 != TARGET_POLLIN) 2152 || ((cb->to_fstat) (cb, fd, &buf) != 0 2153 || (buf.st_mode & S_IFIFO) == 0) 2154 || cris_cpu->thread_data == NULL) 2155 { 2156 retval 2157 = cris_unknown_syscall (current_cpu, pc, 2158 "Unimplemented poll syscall " 2159 "(0x%lx: [0x%x, 0x%x, x], " 2160 "0x%lx, 0x%lx)\n", 2161 (unsigned long) arg1, fd, events, 2162 (unsigned long) arg2, 2163 (unsigned long) arg3); 2164 break; 2165 } 2166 2167 retval = 0; 2168 2169 /* Iterate over threads; find a marker that a writer is 2170 sleeping, waiting for a reader. */ 2171 for (i = 0; i < SIM_TARGET_MAX_THREADS; i++) 2172 if (cris_cpu->thread_data[i].cpu_context != NULL 2173 && cris_cpu->thread_data[i].pipe_read_fd == fd) 2174 { 2175 revents = TARGET_POLLIN; 2176 retval = 1; 2177 break; 2178 } 2179 2180 /* Timeout decreases with whatever time passed between the 2181 last syscall and this. That's not exactly right for the 2182 first call, but it's close enough that it isn't 2183 worthwhile to complicate matters by making that a special 2184 case. */ 2185 timeout 2186 -= (TARGET_TIME_MS (current_cpu) 2187 - (cris_cpu->thread_data[threadno].last_execution)); 2188 2189 /* Arrange to repeat this syscall until timeout or event, 2190 decreasing timeout at each iteration. */ 2191 if (timeout > 0 && revents == 0) 2192 { 2193 bfd_byte timeout_buf[4]; 2194 2195 bfd_putl32 (timeout, timeout_buf); 2196 (*CPU_REG_STORE (current_cpu)) (current_cpu, 2197 H_GR_R12, timeout_buf, 4); 2198 sim_pc_set (current_cpu, pc); 2199 retval = arg1; 2200 break; 2201 } 2202 2203 sim_core_write_unaligned_2 (current_cpu, pc, 0, ufds + 4 + 2, 2204 revents); 2205 break; 2206 } 2207 2208 case TARGET_SYS_time: 2209 { 2210 retval = (int) (*cb->time) (cb); 2211 2212 /* At time of this writing, CB_SYSCALL_time doesn't do the 2213 part of setting *arg1 to the return value. */ 2214 if (arg1) 2215 sim_core_write_unaligned_4 (current_cpu, pc, 0, arg1, retval); 2216 break; 2217 } 2218 2219 case TARGET_SYS_gettimeofday: 2220 if (arg1 != 0) 2221 { 2222 USI ts = TARGET_TIME (current_cpu); 2223 USI tms = TARGET_TIME_MS (current_cpu); 2224 2225 /* First dword is seconds since TARGET_EPOCH. */ 2226 sim_core_write_unaligned_4 (current_cpu, pc, 0, arg1, ts); 2227 2228 /* Second dword is microseconds. */ 2229 sim_core_write_unaligned_4 (current_cpu, pc, 0, arg1 + 4, 2230 (tms % 1000) * 1000); 2231 } 2232 if (arg2 != 0) 2233 { 2234 /* Time-zone info is always cleared. */ 2235 sim_core_write_unaligned_4 (current_cpu, pc, 0, arg2, 0); 2236 sim_core_write_unaligned_4 (current_cpu, pc, 0, arg2 + 4, 0); 2237 } 2238 retval = 0; 2239 break; 2240 2241 case TARGET_SYS_llseek: 2242 { 2243 /* If it fits, tweak parameters to fit the "generic" 32-bit 2244 lseek and use that. */ 2245 SI fd = arg1; 2246 SI offs_hi = arg2; 2247 SI offs_lo = arg3; 2248 SI resultp = arg4; 2249 SI whence = arg5; 2250 retval = 0; 2251 2252 if (!((offs_hi == 0 && offs_lo >= 0) 2253 || (offs_hi == -1 && offs_lo < 0))) 2254 { 2255 retval 2256 = cris_unknown_syscall (current_cpu, pc, 2257 "Unimplemented llseek offset," 2258 " fd %d: 0x%x:0x%x\n", 2259 fd, (unsigned) arg2, 2260 (unsigned) arg3); 2261 break; 2262 } 2263 2264 s.func = TARGET_SYS_lseek; 2265 s.arg2 = offs_lo; 2266 s.arg3 = whence; 2267 if (cb_syscall (cb, &s) != CB_RC_OK) 2268 { 2269 sim_io_eprintf (sd, "Break 13: invalid %d? Returned %ld\n", callnum, 2270 s.result); 2271 sim_engine_halt (sd, current_cpu, NULL, pc, sim_stopped, SIM_SIGILL); 2272 } 2273 if (s.result < 0) 2274 retval = -s.errcode; 2275 else 2276 { 2277 sim_core_write_unaligned_4 (current_cpu, pc, 0, resultp, 2278 s.result); 2279 sim_core_write_unaligned_4 (current_cpu, pc, 0, resultp + 4, 2280 s.result < 0 ? -1 : 0); 2281 } 2282 break; 2283 } 2284 2285 /* ssize_t writev(int fd, const struct iovec *iov, int iovcnt); 2286 where: 2287 struct iovec { 2288 void *iov_base; Starting address 2289 size_t iov_len; Number of bytes to transfer 2290 }; */ 2291 case TARGET_SYS_writev: 2292 { 2293 SI fd = arg1; 2294 SI iov = arg2; 2295 SI iovcnt = arg3; 2296 SI retcnt = 0; 2297 int i; 2298 2299 /* We'll ignore strict error-handling and just do multiple write calls. */ 2300 for (i = 0; i < iovcnt; i++) 2301 { 2302 int sysret; 2303 USI iov_base 2304 = sim_core_read_unaligned_4 (current_cpu, pc, 0, 2305 iov + 8*i); 2306 USI iov_len 2307 = sim_core_read_unaligned_4 (current_cpu, pc, 0, 2308 iov + 8*i + 4); 2309 2310 s.func = TARGET_SYS_write; 2311 s.arg1 = fd; 2312 s.arg2 = iov_base; 2313 s.arg3 = iov_len; 2314 2315 if (cb_syscall (cb, &s) != CB_RC_OK) 2316 abort (); 2317 sysret = s.result == -1 ? -s.errcode : s.result; 2318 2319 if (sysret != iov_len) 2320 { 2321 if (i != 0) 2322 abort (); 2323 retcnt = sysret; 2324 break; 2325 } 2326 2327 retcnt += iov_len; 2328 } 2329 2330 retval = retcnt; 2331 } 2332 break; 2333 2334 /* This one does have a generic callback function, but at the time 2335 of this writing, cb_syscall does not have code for it, and we 2336 need target-specific code for the threads implementation 2337 anyway. */ 2338 case TARGET_SYS_kill: 2339 { 2340 USI pid = arg1; 2341 USI sig = arg2; 2342 2343 retval = 0; 2344 2345 /* At kill(2), glibc sets signal masks such that the thread 2346 machinery is initialized. Still, there is and was only 2347 one thread. */ 2348 if (cris_cpu->max_threadid == 0) 2349 { 2350 if (pid != TARGET_PID) 2351 { 2352 retval = -cb_host_to_target_errno (cb, EPERM); 2353 break; 2354 } 2355 2356 /* FIXME: Signal infrastructure (target-to-sim mapping). */ 2357 if (sig == TARGET_SIGABRT) 2358 /* A call "abort ()", i.e. "kill (getpid(), SIGABRT)" is 2359 the end-point for failing GCC test-cases. */ 2360 sim_engine_halt (sd, current_cpu, NULL, pc, sim_stopped, 2361 SIM_SIGABRT); 2362 else 2363 { 2364 sim_io_eprintf (sd, "Unimplemented signal: %d\n", sig); 2365 sim_engine_halt (sd, current_cpu, NULL, pc, sim_stopped, 2366 SIM_SIGILL); 2367 } 2368 2369 /* This will not be reached. */ 2370 abort (); 2371 } 2372 else 2373 retval = deliver_signal (current_cpu, sig, pid); 2374 break; 2375 } 2376 2377 case TARGET_SYS_rt_sigprocmask: 2378 { 2379 int i; 2380 USI how = arg1; 2381 USI newsetp = arg2; 2382 USI oldsetp = arg3; 2383 2384 if (how != TARGET_SIG_BLOCK 2385 && how != TARGET_SIG_SETMASK 2386 && how != TARGET_SIG_UNBLOCK) 2387 { 2388 retval 2389 = cris_unknown_syscall (current_cpu, pc, 2390 "Unimplemented rt_sigprocmask " 2391 "syscall (0x%x, 0x%x, 0x%x)\n", 2392 arg1, arg2, arg3); 2393 break; 2394 } 2395 2396 if (newsetp) 2397 { 2398 USI set_low 2399 = sim_core_read_unaligned_4 (current_cpu, pc, 0, 2400 newsetp); 2401 USI set_high 2402 = sim_core_read_unaligned_4 (current_cpu, pc, 0, 2403 newsetp + 4); 2404 2405 /* The sigmask is kept in the per-thread data, so we may 2406 need to create the first one. */ 2407 if (cris_cpu->thread_data == NULL) 2408 make_first_thread (current_cpu); 2409 2410 if (how == TARGET_SIG_SETMASK) 2411 for (i = 0; i < 64; i++) 2412 cris_cpu->thread_data[threadno].sigdata[i].blocked = 0; 2413 2414 for (i = 0; i < 32; i++) 2415 if ((set_low & (1 << i))) 2416 cris_cpu->thread_data[threadno].sigdata[i + 1].blocked 2417 = (how != TARGET_SIG_UNBLOCK); 2418 2419 for (i = 0; i < 31; i++) 2420 if ((set_high & (1 << i))) 2421 cris_cpu->thread_data[threadno].sigdata[i + 33].blocked 2422 = (how != TARGET_SIG_UNBLOCK); 2423 2424 /* The mask changed, so a signal may be unblocked for 2425 execution. */ 2426 cris_cpu->thread_data[threadno].sigpending = 1; 2427 } 2428 2429 if (oldsetp != 0) 2430 { 2431 USI set_low = 0; 2432 USI set_high = 0; 2433 2434 for (i = 0; i < 32; i++) 2435 if (cris_cpu->thread_data[threadno] 2436 .sigdata[i + 1].blocked) 2437 set_low |= 1 << i; 2438 for (i = 0; i < 31; i++) 2439 if (cris_cpu->thread_data[threadno] 2440 .sigdata[i + 33].blocked) 2441 set_high |= 1 << i; 2442 2443 sim_core_write_unaligned_4 (current_cpu, pc, 0, oldsetp + 0, set_low); 2444 sim_core_write_unaligned_4 (current_cpu, pc, 0, oldsetp + 4, set_high); 2445 } 2446 2447 retval = 0; 2448 break; 2449 } 2450 2451 case TARGET_SYS_sigreturn: 2452 { 2453 int i; 2454 bfd_byte regbuf[4]; 2455 int was_sigsuspended; 2456 2457 if (cris_cpu->thread_data == NULL 2458 /* The CPU context is saved with the simulator data, not 2459 on the stack as in the real world. */ 2460 || (cris_cpu->thread_data[threadno].cpu_context_atsignal 2461 == NULL)) 2462 { 2463 retval 2464 = cris_unknown_syscall (current_cpu, pc, 2465 "Invalid sigreturn syscall: " 2466 "no signal handler active " 2467 "(0x%lx, 0x%lx, 0x%lx, 0x%lx, " 2468 "0x%lx, 0x%lx)\n", 2469 (unsigned long) arg1, 2470 (unsigned long) arg2, 2471 (unsigned long) arg3, 2472 (unsigned long) arg4, 2473 (unsigned long) arg5, 2474 (unsigned long) arg6); 2475 break; 2476 } 2477 2478 was_sigsuspended 2479 = cris_cpu->thread_data[threadno].sigsuspended; 2480 2481 /* Restore the sigmask, either from the stack copy made when 2482 the sighandler was called, or from the saved state 2483 specifically for sigsuspend(2). */ 2484 if (was_sigsuspended) 2485 { 2486 cris_cpu->thread_data[threadno].sigsuspended = 0; 2487 for (i = 0; i < 64; i++) 2488 cris_cpu->thread_data[threadno].sigdata[i].blocked 2489 = cris_cpu->thread_data[threadno] 2490 .sigdata[i].blocked_suspendsave; 2491 } 2492 else 2493 { 2494 USI sp; 2495 USI set_low; 2496 USI set_high; 2497 2498 (*CPU_REG_FETCH (current_cpu)) (current_cpu, 2499 H_GR_SP, regbuf, 4); 2500 sp = bfd_getl32 (regbuf); 2501 set_low 2502 = sim_core_read_unaligned_4 (current_cpu, pc, 0, sp); 2503 set_high 2504 = sim_core_read_unaligned_4 (current_cpu, pc, 0, sp + 4); 2505 2506 for (i = 0; i < 32; i++) 2507 cris_cpu->thread_data[threadno].sigdata[i + 1].blocked 2508 = (set_low & (1 << i)) != 0; 2509 for (i = 0; i < 31; i++) 2510 cris_cpu->thread_data[threadno].sigdata[i + 33].blocked 2511 = (set_high & (1 << i)) != 0; 2512 } 2513 2514 /* The mask changed, so a signal may be unblocked for 2515 execution. */ 2516 cris_cpu->thread_data[threadno].sigpending = 1; 2517 2518 memcpy (&cris_cpu->cpu_data_placeholder, 2519 cris_cpu->thread_data[threadno].cpu_context_atsignal, 2520 cris_cpu->thread_cpu_data_size); 2521 free (cris_cpu->thread_data[threadno].cpu_context_atsignal); 2522 cris_cpu->thread_data[threadno].cpu_context_atsignal = NULL; 2523 2524 /* The return value must come from the saved R10. */ 2525 (*CPU_REG_FETCH (current_cpu)) (current_cpu, H_GR_R10, regbuf, 4); 2526 retval = bfd_getl32 (regbuf); 2527 2528 /* We must also break the "sigsuspension loop". */ 2529 if (was_sigsuspended) 2530 sim_pc_set (current_cpu, sim_pc_get (current_cpu) + 2); 2531 break; 2532 } 2533 2534 case TARGET_SYS_rt_sigsuspend: 2535 { 2536 USI newsetp = arg1; 2537 USI setsize = arg2; 2538 2539 if (setsize != 8) 2540 { 2541 retval 2542 = cris_unknown_syscall (current_cpu, pc, 2543 "Unimplemented rt_sigsuspend syscall" 2544 " arguments (0x%lx, 0x%lx)\n", 2545 (unsigned long) arg1, 2546 (unsigned long) arg2); 2547 break; 2548 } 2549 2550 /* Don't change the signal mask if we're already in 2551 sigsuspend state (i.e. this syscall is a rerun). */ 2552 else if (!cris_cpu->thread_data[threadno].sigsuspended) 2553 { 2554 USI set_low 2555 = sim_core_read_unaligned_4 (current_cpu, pc, 0, 2556 newsetp); 2557 USI set_high 2558 = sim_core_read_unaligned_4 (current_cpu, pc, 0, 2559 newsetp + 4); 2560 int i; 2561 2562 /* Save the current sigmask and insert the user-supplied 2563 one. */ 2564 for (i = 0; i < 32; i++) 2565 { 2566 cris_cpu->thread_data[threadno] 2567 .sigdata[i + 1].blocked_suspendsave 2568 = cris_cpu->thread_data[threadno] 2569 .sigdata[i + 1].blocked; 2570 2571 cris_cpu->thread_data[threadno] 2572 .sigdata[i + 1].blocked = (set_low & (1 << i)) != 0; 2573 } 2574 for (i = 0; i < 31; i++) 2575 { 2576 cris_cpu->thread_data[threadno] 2577 .sigdata[i + 33].blocked_suspendsave 2578 = cris_cpu->thread_data[threadno] 2579 .sigdata[i + 33].blocked; 2580 cris_cpu->thread_data[threadno] 2581 .sigdata[i + 33].blocked = (set_high & (1 << i)) != 0; 2582 } 2583 2584 cris_cpu->thread_data[threadno].sigsuspended = 1; 2585 2586 /* The mask changed, so a signal may be unblocked for 2587 execution. */ 2588 cris_cpu->thread_data[threadno].sigpending = 1; 2589 } 2590 2591 /* Because we don't use arg1 (newsetp) when this syscall is 2592 rerun, it doesn't matter that we overwrite it with the 2593 (constant) return value. */ 2594 retval = -cb_host_to_target_errno (cb, EINTR); 2595 sim_pc_set (current_cpu, pc); 2596 break; 2597 } 2598 2599 /* Add case labels here for other syscalls using the 32-bit 2600 "struct stat", provided they have a corresponding simulator 2601 function of course. */ 2602 case TARGET_SYS_stat: 2603 case TARGET_SYS_fstat: 2604 { 2605 /* As long as the infrastructure doesn't cache anything 2606 related to the stat mapping, this trick gets us a dual 2607 "struct stat"-type mapping in the least error-prone way. */ 2608 const char *saved_map = cb->stat_map; 2609 CB_TARGET_DEFS_MAP *saved_syscall_map = cb->syscall_map; 2610 2611 cb->syscall_map = (CB_TARGET_DEFS_MAP *) syscall_stat32_map; 2612 cb->stat_map = stat32_map; 2613 2614 if (cb_syscall (cb, &s) != CB_RC_OK) 2615 { 2616 abort (); 2617 sim_engine_halt (sd, current_cpu, NULL, pc, sim_stopped, 2618 SIM_SIGILL); 2619 } 2620 retval = s.result == -1 ? -s.errcode : s.result; 2621 2622 cb->stat_map = saved_map; 2623 cb->syscall_map = saved_syscall_map; 2624 break; 2625 } 2626 2627 case TARGET_SYS_getcwd: 2628 { 2629 USI buf = arg1; 2630 USI size = arg2; 2631 2632 char *cwd = xmalloc (SIM_PATHMAX); 2633 if (cwd != getcwd (cwd, SIM_PATHMAX)) 2634 abort (); 2635 2636 /* FIXME: When and if we support chdir, we need something 2637 a bit more elaborate. */ 2638 if (simulator_sysroot[0] != '\0') 2639 strcpy (cwd, "/"); 2640 2641 retval = -cb_host_to_target_errno (cb, ERANGE); 2642 if (strlen (cwd) + 1 <= size) 2643 { 2644 retval = strlen (cwd) + 1; 2645 if (sim_core_write_buffer (sd, current_cpu, 0, cwd, 2646 buf, retval) 2647 != (unsigned int) retval) 2648 retval = -cb_host_to_target_errno (cb, EFAULT); 2649 } 2650 free (cwd); 2651 break; 2652 } 2653 2654 case TARGET_SYS_access: 2655 { 2656 SI path = arg1; 2657 SI mode = arg2; 2658 char *pbuf = xmalloc (SIM_PATHMAX); 2659 int i; 2660 int o = 0; 2661 int hmode = 0; 2662 2663 if (sim_core_read_unaligned_1 (current_cpu, pc, 0, path) == '/') 2664 { 2665 strcpy (pbuf, simulator_sysroot); 2666 o += strlen (simulator_sysroot); 2667 } 2668 2669 for (i = 0; i + o < SIM_PATHMAX; i++) 2670 { 2671 pbuf[i + o] 2672 = sim_core_read_unaligned_1 (current_cpu, pc, 0, path + i); 2673 if (pbuf[i + o] == 0) 2674 break; 2675 } 2676 2677 if (i + o == SIM_PATHMAX) 2678 { 2679 retval = -cb_host_to_target_errno (cb, ENAMETOOLONG); 2680 break; 2681 } 2682 2683 /* Assert that we don't get calls for files for which we 2684 don't have support. */ 2685 if (strncmp (pbuf + strlen (simulator_sysroot), 2686 "/proc/", 6) == 0) 2687 abort (); 2688 #define X_AFLAG(x) if (mode & TARGET_ ## x) hmode |= x 2689 X_AFLAG (R_OK); 2690 X_AFLAG (W_OK); 2691 X_AFLAG (X_OK); 2692 X_AFLAG (F_OK); 2693 #undef X_AFLAG 2694 2695 if (access (pbuf, hmode) != 0) 2696 retval = -cb_host_to_target_errno (cb, errno); 2697 else 2698 retval = 0; 2699 2700 free (pbuf); 2701 break; 2702 } 2703 2704 case TARGET_SYS_readlink: 2705 { 2706 SI path = arg1; 2707 SI buf = arg2; 2708 SI bufsiz = arg3; 2709 char *pbuf = xmalloc (SIM_PATHMAX); 2710 char *lbuf = xmalloc (SIM_PATHMAX); 2711 char *lbuf_alloc = lbuf; 2712 int nchars = -1; 2713 int i; 2714 int o = 0; 2715 2716 if (sim_core_read_unaligned_1 (current_cpu, pc, 0, path) == '/') 2717 { 2718 strcpy (pbuf, simulator_sysroot); 2719 o += strlen (simulator_sysroot); 2720 } 2721 2722 for (i = 0; i + o < SIM_PATHMAX; i++) 2723 { 2724 pbuf[i + o] 2725 = sim_core_read_unaligned_1 (current_cpu, pc, 0, path + i); 2726 if (pbuf[i + o] == 0) 2727 break; 2728 } 2729 2730 if (i + o == SIM_PATHMAX) 2731 { 2732 retval = -cb_host_to_target_errno (cb, ENAMETOOLONG); 2733 break; 2734 } 2735 2736 /* Intervene calls for certain files expected in the target 2737 proc file system. */ 2738 if (strcmp (pbuf + strlen (simulator_sysroot), 2739 "/proc/" XSTRING (TARGET_PID) "/exe") == 0) 2740 { 2741 char *argv0 2742 = (STATE_PROG_ARGV (sd) != NULL 2743 ? *STATE_PROG_ARGV (sd) : NULL); 2744 2745 if (argv0 == NULL || *argv0 == '.') 2746 { 2747 retval 2748 = cris_unknown_syscall (current_cpu, pc, 2749 "Unimplemented readlink syscall " 2750 "(0x%lx: [\"%s\"], 0x%lx)\n", 2751 (unsigned long) arg1, pbuf, 2752 (unsigned long) arg2); 2753 break; 2754 } 2755 else if (*argv0 == '/') 2756 { 2757 if (strncmp (simulator_sysroot, argv0, 2758 strlen (simulator_sysroot)) == 0) 2759 argv0 += strlen (simulator_sysroot); 2760 2761 strcpy (lbuf, argv0); 2762 nchars = strlen (argv0) + 1; 2763 } 2764 else 2765 { 2766 if (getcwd (lbuf, SIM_PATHMAX) != NULL 2767 && strlen (lbuf) + 2 + strlen (argv0) < SIM_PATHMAX) 2768 { 2769 if (strncmp (simulator_sysroot, lbuf, 2770 strlen (simulator_sysroot)) == 0) 2771 lbuf += strlen (simulator_sysroot); 2772 2773 strcat (lbuf, "/"); 2774 strcat (lbuf, argv0); 2775 nchars = strlen (lbuf) + 1; 2776 } 2777 else 2778 abort (); 2779 } 2780 } 2781 else 2782 nchars = readlink (pbuf, lbuf, SIM_PATHMAX); 2783 2784 /* We trust that the readlink result returns a *relative* 2785 link, or one already adjusted for the file-path-prefix. 2786 (We can't generally tell the difference, so we go with 2787 the easiest decision; no adjustment.) */ 2788 2789 if (nchars == -1) 2790 { 2791 retval = -cb_host_to_target_errno (cb, errno); 2792 break; 2793 } 2794 2795 if (bufsiz < nchars) 2796 nchars = bufsiz; 2797 2798 if (sim_core_write_buffer (sd, current_cpu, write_map, lbuf, 2799 buf, nchars) != (unsigned int) nchars) 2800 retval = -cb_host_to_target_errno (cb, EFAULT); 2801 else 2802 retval = nchars; 2803 2804 free (pbuf); 2805 free (lbuf_alloc); 2806 break; 2807 } 2808 2809 case TARGET_SYS_sched_getscheduler: 2810 { 2811 USI pid = arg1; 2812 2813 /* FIXME: Search (other) existing threads. */ 2814 if (pid != 0 && pid != TARGET_PID) 2815 retval = -cb_host_to_target_errno (cb, ESRCH); 2816 else 2817 retval = TARGET_SCHED_OTHER; 2818 break; 2819 } 2820 2821 case TARGET_SYS_sched_getparam: 2822 { 2823 USI pid = arg1; 2824 USI paramp = arg2; 2825 2826 /* The kernel says: 2827 struct sched_param { 2828 int sched_priority; 2829 }; */ 2830 2831 if (pid != 0 && pid != TARGET_PID) 2832 retval = -cb_host_to_target_errno (cb, ESRCH); 2833 else 2834 { 2835 /* FIXME: Save scheduler setting before threads are 2836 created too. */ 2837 sim_core_write_unaligned_4 (current_cpu, pc, 0, paramp, 2838 cris_cpu->thread_data != NULL 2839 ? (cris_cpu 2840 ->thread_data[threadno] 2841 .priority) 2842 : 0); 2843 retval = 0; 2844 } 2845 break; 2846 } 2847 2848 case TARGET_SYS_sched_setparam: 2849 { 2850 USI pid = arg1; 2851 USI paramp = arg2; 2852 2853 if ((pid != 0 && pid != TARGET_PID) 2854 || sim_core_read_unaligned_4 (current_cpu, pc, 0, 2855 paramp) != 0) 2856 retval = -cb_host_to_target_errno (cb, EINVAL); 2857 else 2858 retval = 0; 2859 break; 2860 } 2861 2862 case TARGET_SYS_sched_setscheduler: 2863 { 2864 USI pid = arg1; 2865 USI policy = arg2; 2866 USI paramp = arg3; 2867 2868 if ((pid != 0 && pid != TARGET_PID) 2869 || policy != TARGET_SCHED_OTHER 2870 || sim_core_read_unaligned_4 (current_cpu, pc, 0, 2871 paramp) != 0) 2872 retval = -cb_host_to_target_errno (cb, EINVAL); 2873 else 2874 /* FIXME: Save scheduler setting to be read in later 2875 sched_getparam calls. */ 2876 retval = 0; 2877 break; 2878 } 2879 2880 case TARGET_SYS_sched_yield: 2881 /* We reschedule to the next thread after a syscall anyway, so 2882 we don't have to do anything here than to set the return 2883 value. */ 2884 retval = 0; 2885 break; 2886 2887 case TARGET_SYS_sched_get_priority_min: 2888 case TARGET_SYS_sched_get_priority_max: 2889 if (arg1 != 0) 2890 retval = -cb_host_to_target_errno (cb, EINVAL); 2891 else 2892 retval = 0; 2893 break; 2894 2895 case TARGET_SYS_ugetrlimit: 2896 { 2897 unsigned int curlim, maxlim; 2898 if (arg1 != TARGET_RLIMIT_STACK && arg1 != TARGET_RLIMIT_NOFILE) 2899 { 2900 retval = -cb_host_to_target_errno (cb, EINVAL); 2901 break; 2902 } 2903 2904 /* The kernel says: 2905 struct rlimit { 2906 unsigned long rlim_cur; 2907 unsigned long rlim_max; 2908 }; */ 2909 if (arg1 == TARGET_RLIMIT_NOFILE) 2910 { 2911 /* Sadly a very low limit. Better not lie, though. */ 2912 maxlim = curlim = MAX_CALLBACK_FDS; 2913 } 2914 else /* arg1 == TARGET_RLIMIT_STACK */ 2915 { 2916 maxlim = 0xffffffff; 2917 curlim = 0x800000; 2918 } 2919 sim_core_write_unaligned_4 (current_cpu, pc, 0, arg2, curlim); 2920 sim_core_write_unaligned_4 (current_cpu, pc, 0, arg2 + 4, maxlim); 2921 retval = 0; 2922 break; 2923 } 2924 2925 case TARGET_SYS_setrlimit: 2926 if (arg1 != TARGET_RLIMIT_STACK) 2927 { 2928 retval = -cb_host_to_target_errno (cb, EINVAL); 2929 break; 2930 } 2931 /* FIXME: Save values for future ugetrlimit calls. */ 2932 retval = 0; 2933 break; 2934 2935 /* Provide a very limited subset of the sysctl functions, and 2936 abort for the rest. */ 2937 case TARGET_SYS__sysctl: 2938 { 2939 /* The kernel says: 2940 struct __sysctl_args { 2941 int *name; 2942 int nlen; 2943 void *oldval; 2944 size_t *oldlenp; 2945 void *newval; 2946 size_t newlen; 2947 unsigned long __unused[4]; 2948 }; */ 2949 SI name = sim_core_read_unaligned_4 (current_cpu, pc, 0, arg1); 2950 SI name0 = name == 0 2951 ? 0 : sim_core_read_unaligned_4 (current_cpu, pc, 0, name); 2952 SI name1 = name == 0 2953 ? 0 : sim_core_read_unaligned_4 (current_cpu, pc, 0, name + 4); 2954 SI nlen 2955 = sim_core_read_unaligned_4 (current_cpu, pc, 0, arg1 + 4); 2956 SI oldval 2957 = sim_core_read_unaligned_4 (current_cpu, pc, 0, arg1 + 8); 2958 SI oldlenp 2959 = sim_core_read_unaligned_4 (current_cpu, pc, 0, arg1 + 12); 2960 SI oldlen = oldlenp == 0 2961 ? 0 : sim_core_read_unaligned_4 (current_cpu, pc, 0, oldlenp); 2962 SI newval 2963 = sim_core_read_unaligned_4 (current_cpu, pc, 0, arg1 + 16); 2964 SI newlen 2965 = sim_core_read_unaligned_4 (current_cpu, pc, 0, arg1 + 20); 2966 2967 if (name0 == TARGET_CTL_KERN && name1 == TARGET_CTL_KERN_VERSION) 2968 { 2969 SI to_write = oldlen < (SI) sizeof (TARGET_UTSNAME) 2970 ? oldlen : (SI) sizeof (TARGET_UTSNAME); 2971 2972 sim_core_write_unaligned_4 (current_cpu, pc, 0, oldlenp, 2973 sizeof (TARGET_UTSNAME)); 2974 2975 if (sim_core_write_buffer (sd, current_cpu, write_map, 2976 TARGET_UTSNAME, oldval, 2977 to_write) 2978 != (unsigned int) to_write) 2979 retval = -cb_host_to_target_errno (cb, EFAULT); 2980 else 2981 retval = 0; 2982 break; 2983 } 2984 2985 retval 2986 = cris_unknown_syscall (current_cpu, pc, 2987 "Unimplemented _sysctl syscall " 2988 "(0x%lx: [0x%lx, 0x%lx]," 2989 " 0x%lx, 0x%lx, 0x%lx, 0x%lx, 0x%lx)\n", 2990 (unsigned long) name, 2991 (unsigned long) name0, 2992 (unsigned long) name1, 2993 (unsigned long) nlen, 2994 (unsigned long) oldval, 2995 (unsigned long) oldlenp, 2996 (unsigned long) newval, 2997 (unsigned long) newlen); 2998 break; 2999 } 3000 3001 case TARGET_SYS_exit: 3002 { 3003 /* Here for all but the last thread. */ 3004 int i; 3005 int pid 3006 = cris_cpu->thread_data[threadno].threadid + TARGET_PID; 3007 int ppid 3008 = (cris_cpu->thread_data[threadno].parent_threadid 3009 + TARGET_PID); 3010 int exitsig = cris_cpu->thread_data[threadno].exitsig; 3011 3012 /* Any children are now all orphans. */ 3013 for (i = 0; i < SIM_TARGET_MAX_THREADS; i++) 3014 if (cris_cpu->thread_data[i].parent_threadid 3015 == cris_cpu->thread_data[threadno].threadid) 3016 /* Make getppid(2) return 1 for them, poor little ones. */ 3017 cris_cpu->thread_data[i].parent_threadid = -TARGET_PID + 1; 3018 3019 /* Free the cpu context data. When the parent has received 3020 the exit status, we'll clear the entry too. */ 3021 free (cris_cpu->thread_data[threadno].cpu_context); 3022 cris_cpu->thread_data[threadno].cpu_context = NULL; 3023 cris_cpu->m1threads--; 3024 if (arg1 != 0) 3025 { 3026 sim_io_eprintf (sd, "Thread %d exited with status %d\n", 3027 pid, arg1); 3028 sim_engine_halt (sd, current_cpu, NULL, pc, sim_stopped, 3029 SIM_SIGILL); 3030 } 3031 3032 /* Still, we may want to support non-zero exit values. */ 3033 cris_cpu->thread_data[threadno].exitval = arg1 << 8; 3034 3035 if (exitsig) 3036 deliver_signal (current_cpu, exitsig, ppid); 3037 break; 3038 } 3039 3040 case TARGET_SYS_clone: 3041 { 3042 int nthreads = cris_cpu->m1threads + 1; 3043 void *thread_cpu_data; 3044 bfd_byte old_sp_buf[4]; 3045 bfd_byte sp_buf[4]; 3046 const bfd_byte zeros[4] = { 0, 0, 0, 0 }; 3047 int i; 3048 3049 /* That's right, the syscall clone arguments are reversed 3050 compared to sys_clone notes in clone(2) and compared to 3051 other Linux ports (i.e. it's the same order as in the 3052 clone(2) libcall). */ 3053 USI flags = arg2; 3054 USI newsp = arg1; 3055 3056 if (nthreads == SIM_TARGET_MAX_THREADS) 3057 { 3058 retval = -cb_host_to_target_errno (cb, EAGAIN); 3059 break; 3060 } 3061 3062 /* FIXME: Implement the low byte. */ 3063 if ((flags & ~TARGET_CSIGNAL) != 3064 (TARGET_CLONE_VM 3065 | TARGET_CLONE_FS 3066 | TARGET_CLONE_FILES 3067 | TARGET_CLONE_SIGHAND) 3068 || newsp == 0) 3069 { 3070 retval 3071 = cris_unknown_syscall (current_cpu, pc, 3072 "Unimplemented clone syscall " 3073 "(0x%lx, 0x%lx)\n", 3074 (unsigned long) arg1, 3075 (unsigned long) arg2); 3076 break; 3077 } 3078 3079 if (cris_cpu->thread_data == NULL) 3080 make_first_thread (current_cpu); 3081 3082 /* The created thread will get the new SP and a cleared R10. 3083 Since it's created out of a copy of the old thread and we 3084 don't have a set-register-function that just take the 3085 cpu_data as a parameter, we set the childs values first, 3086 and write back or overwrite them in the parent after the 3087 copy. */ 3088 (*CPU_REG_FETCH (current_cpu)) (current_cpu, 3089 H_GR_SP, old_sp_buf, 4); 3090 bfd_putl32 (newsp, sp_buf); 3091 (*CPU_REG_STORE (current_cpu)) (current_cpu, 3092 H_GR_SP, sp_buf, 4); 3093 (*CPU_REG_STORE (current_cpu)) (current_cpu, 3094 H_GR_R10, (bfd_byte *) zeros, 4); 3095 thread_cpu_data 3096 = (*cris_cpu 3097 ->make_thread_cpu_data) (current_cpu, 3098 &cris_cpu->cpu_data_placeholder); 3099 (*CPU_REG_STORE (current_cpu)) (current_cpu, 3100 H_GR_SP, old_sp_buf, 4); 3101 3102 retval = ++cris_cpu->max_threadid + TARGET_PID; 3103 3104 /* Find an unused slot. After a few threads have been created 3105 and exited, the array is expected to be a bit fragmented. 3106 We don't reuse the first entry, though, that of the 3107 original thread. */ 3108 for (i = 1; i < SIM_TARGET_MAX_THREADS; i++) 3109 if (cris_cpu->thread_data[i].cpu_context == NULL 3110 /* Don't reuse a zombied entry. */ 3111 && cris_cpu->thread_data[i].threadid == 0) 3112 break; 3113 3114 memcpy (&cris_cpu->thread_data[i], 3115 &cris_cpu->thread_data[threadno], 3116 sizeof (cris_cpu->thread_data[i])); 3117 cris_cpu->thread_data[i].cpu_context = thread_cpu_data; 3118 cris_cpu->thread_data[i].cpu_context_atsignal = NULL; 3119 cris_cpu->thread_data[i].threadid = cris_cpu->max_threadid; 3120 cris_cpu->thread_data[i].parent_threadid 3121 = cris_cpu->thread_data[threadno].threadid; 3122 cris_cpu->thread_data[i].pipe_read_fd = 0; 3123 cris_cpu->thread_data[i].pipe_write_fd = 0; 3124 cris_cpu->thread_data[i].at_syscall = 0; 3125 cris_cpu->thread_data[i].sigpending = 0; 3126 cris_cpu->thread_data[i].sigsuspended = 0; 3127 cris_cpu->thread_data[i].exitsig = flags & TARGET_CSIGNAL; 3128 cris_cpu->m1threads = nthreads; 3129 break; 3130 } 3131 3132 /* Better watch these in case they do something necessary. */ 3133 case TARGET_SYS_socketcall: 3134 retval = -cb_host_to_target_errno (cb, ENOSYS); 3135 break; 3136 3137 case TARGET_SYS_set_thread_area: 3138 /* Do the same error check as Linux. */ 3139 if (arg1 & 255) 3140 { 3141 retval = -cb_host_to_target_errno (cb, EINVAL); 3142 break; 3143 } 3144 (*cris_cpu->set_target_thread_data) (current_cpu, arg1); 3145 retval = 0; 3146 break; 3147 3148 unimplemented_syscall: 3149 default: 3150 retval 3151 = cris_unknown_syscall (current_cpu, pc, 3152 "Unimplemented syscall: %d " 3153 "(0x%x, 0x%x, 0x%x, 0x%x, 0x%x, 0x%x)\n", 3154 callnum, arg1, arg2, arg3, arg4, arg5, 3155 arg6); 3156 } 3157 } 3158 3159 /* Minimal support for fcntl F_GETFL as used in open+fdopen. */ 3160 if (callnum == TARGET_SYS_open) 3161 { 3162 cris_cpu->last_open_fd = retval; 3163 cris_cpu->last_open_flags = arg2; 3164 } 3165 3166 cris_cpu->last_syscall = callnum; 3167 3168 /* A system call is a rescheduling point. For the time being, we don't 3169 reschedule anywhere else. */ 3170 if (cris_cpu->m1threads != 0 3171 /* We need to schedule off from an exiting thread that is the 3172 second-last one. */ 3173 || (cris_cpu->thread_data != NULL 3174 && cris_cpu->thread_data[threadno].cpu_context == NULL)) 3175 { 3176 bfd_byte retval_buf[4]; 3177 3178 cris_cpu->thread_data[threadno].last_execution 3179 = TARGET_TIME_MS (current_cpu); 3180 bfd_putl32 (retval, retval_buf); 3181 (*CPU_REG_STORE (current_cpu)) (current_cpu, H_GR_R10, retval_buf, 4); 3182 3183 cris_cpu->thread_data[threadno].at_syscall = 1; 3184 reschedule (current_cpu); 3185 3186 (*CPU_REG_FETCH (current_cpu)) (current_cpu, H_GR_R10, retval_buf, 4); 3187 retval = bfd_getl32 (retval_buf); 3188 } 3189 3190 return retval; 3191 } 3192 3193 /* Callback from simulator write saying that the pipe at (reader, writer) 3194 is now non-empty (so the writer should wait until the pipe is empty, at 3195 least not write to this or any other pipe). Simplest is to just wait 3196 until the pipe is empty. */ 3197 3198 static void 3199 cris_pipe_nonempty (host_callback *cb ATTRIBUTE_UNUSED, 3200 int reader, int writer) 3201 { 3202 SIM_CPU *cpu = current_cpu_for_cb_callback; 3203 struct cris_sim_cpu *cris_cpu = CRIS_SIM_CPU (cpu); 3204 const bfd_byte zeros[4] = { 0, 0, 0, 0 }; 3205 3206 /* It's the current thread: we just have to re-run the current 3207 syscall instruction (presumably "break 13") and change the syscall 3208 to the special simulator-wait code. Oh, and set a marker that 3209 we're waiting, so we can disambiguate the special call from a 3210 program error. 3211 3212 This function may be called multiple times between cris_pipe_empty, 3213 but we must avoid e.g. decreasing PC every time. Check fd markers 3214 to tell. */ 3215 if (cris_cpu->thread_data == NULL) 3216 { 3217 sim_io_eprintf (CPU_STATE (cpu), 3218 "Terminating simulation due to writing pipe rd:wr %d:%d" 3219 " from one single thread\n", reader, writer); 3220 sim_engine_halt (CPU_STATE (cpu), cpu, 3221 NULL, sim_pc_get (cpu), sim_stopped, SIM_SIGILL); 3222 } 3223 else if (cris_cpu->thread_data[cris_cpu->threadno].pipe_write_fd == 0) 3224 { 3225 cris_cpu->thread_data[cris_cpu->threadno].pipe_write_fd = writer; 3226 cris_cpu->thread_data[cris_cpu->threadno].pipe_read_fd = reader; 3227 /* FIXME: We really shouldn't change registers other than R10 in 3228 syscalls (like R9), here or elsewhere. */ 3229 (*CPU_REG_STORE (cpu)) (cpu, H_GR_R9, (bfd_byte *) zeros, 4); 3230 sim_pc_set (cpu, sim_pc_get (cpu) - 2); 3231 } 3232 } 3233 3234 /* Callback from simulator close or read call saying that the pipe at 3235 (reader, writer) is now empty (so the writer can write again, perhaps 3236 leave a waiting state). If there are bytes remaining, they couldn't be 3237 consumed (perhaps due to the pipe closing). */ 3238 3239 static void 3240 cris_pipe_empty (host_callback *cb, 3241 int reader, 3242 int writer) 3243 { 3244 int i; 3245 SIM_CPU *cpu = current_cpu_for_cb_callback; 3246 struct cris_sim_cpu *cris_cpu = CRIS_SIM_CPU (cpu); 3247 SIM_DESC sd = CPU_STATE (current_cpu_for_cb_callback); 3248 bfd_byte r10_buf[4]; 3249 int remaining 3250 = cb->pipe_buffer[writer].size - cb->pipe_buffer[reader].size; 3251 3252 /* We need to find the thread that waits for this pipe. */ 3253 for (i = 0; i < SIM_TARGET_MAX_THREADS; i++) 3254 if (cris_cpu->thread_data[i].cpu_context 3255 && cris_cpu->thread_data[i].pipe_write_fd == writer) 3256 { 3257 int retval; 3258 3259 /* Temporarily switch to this cpu context, so we can change the 3260 PC by ordinary calls. */ 3261 3262 memcpy (cris_cpu->thread_data[cris_cpu->threadno].cpu_context, 3263 &cris_cpu->cpu_data_placeholder, 3264 cris_cpu->thread_cpu_data_size); 3265 memcpy (&cris_cpu->cpu_data_placeholder, 3266 cris_cpu->thread_data[i].cpu_context, 3267 cris_cpu->thread_cpu_data_size); 3268 3269 /* The return value is supposed to contain the number of 3270 written bytes, which is the number of bytes requested and 3271 returned at the write call. You might think the right 3272 thing is to adjust the return-value to be only the 3273 *consumed* number of bytes, but it isn't. We're only 3274 called if the pipe buffer is fully consumed or it is being 3275 closed, possibly with remaining bytes. For the latter 3276 case, the writer is still supposed to see success for 3277 PIPE_BUF bytes (a constant which we happen to know and is 3278 unlikely to change). The return value may also be a 3279 negative number; an error value. This case is covered 3280 because "remaining" is always >= 0. */ 3281 (*CPU_REG_FETCH (cpu)) (cpu, H_GR_R10, r10_buf, 4); 3282 retval = (int) bfd_getl_signed_32 (r10_buf); 3283 if (retval - remaining > TARGET_PIPE_BUF) 3284 { 3285 bfd_putl32 (retval - remaining, r10_buf); 3286 (*CPU_REG_STORE (cpu)) (cpu, H_GR_R10, r10_buf, 4); 3287 } 3288 sim_pc_set (cpu, sim_pc_get (cpu) + 2); 3289 memcpy (cris_cpu->thread_data[i].cpu_context, 3290 &cris_cpu->cpu_data_placeholder, 3291 cris_cpu->thread_cpu_data_size); 3292 memcpy (&cris_cpu->cpu_data_placeholder, 3293 cris_cpu->thread_data[cris_cpu->threadno].cpu_context, 3294 cris_cpu->thread_cpu_data_size); 3295 cris_cpu->thread_data[i].pipe_read_fd = 0; 3296 cris_cpu->thread_data[i].pipe_write_fd = 0; 3297 return; 3298 } 3299 3300 abort (); 3301 } 3302 3303 /* We have a simulator-specific notion of time. See TARGET_TIME. */ 3304 3305 static int64_t 3306 cris_time (host_callback *cb ATTRIBUTE_UNUSED) 3307 { 3308 return TARGET_TIME (current_cpu_for_cb_callback); 3309 } 3310 3311 static int 3312 cris_getpid (host_callback *cb ATTRIBUTE_UNUSED) 3313 { 3314 return TARGET_PID; 3315 } 3316 3317 /* Set target-specific callback data. */ 3318 3319 void 3320 cris_set_callbacks (host_callback *cb) 3321 { 3322 /* Yeargh, have to cast away constness to avoid warnings. */ 3323 cb->syscall_map = (CB_TARGET_DEFS_MAP *) syscall_map; 3324 cb->errno_map = (CB_TARGET_DEFS_MAP *) errno_map; 3325 3326 cb->getpid = cris_getpid; 3327 3328 /* The kernel stat64 layout. If we see a file > 2G, the "long" 3329 parameter to cb_store_target_endian will make st_size negative. 3330 Similarly for st_ino. FIXME: Find a 64-bit type, and use it 3331 *unsigned*, and/or add syntax for signed-ness. */ 3332 cb->stat_map = stat_map; 3333 cb->open_map = (CB_TARGET_DEFS_MAP *) open_map; 3334 cb->pipe_nonempty = cris_pipe_nonempty; 3335 cb->pipe_empty = cris_pipe_empty; 3336 cb->time = cris_time; 3337 } 3338 3339 /* Process an address exception. */ 3340 3341 void 3342 cris_core_signal (SIM_DESC sd, SIM_CPU *current_cpu, sim_cia cia, 3343 unsigned int map, int nr_bytes, address_word addr, 3344 transfer_type transfer, sim_core_signals sig) 3345 { 3346 sim_core_signal (sd, current_cpu, cia, map, nr_bytes, addr, 3347 transfer, sig); 3348 } 3349