system.c
author Hajime Tazaki <tazaki@nict.go.jp>
Wed, 13 Feb 2013 22:37:34 +0900
changeset 651 9d7e2cd9633b
parent 498 e20e1bd4bbf3
permissions -rw-r--r--
add a testcase to reproduce threaded dlclose crash (Bug 1513)
Ignore whitespace changes - Everywhere: Within whitespace: At end of lines:
5
9c494e553ab8 wrapper around syscalls
Mathieu Lacage <mathieu.lacage@sophia.inria.fr>
parents:
diff changeset
     1
#include "system.h"
252
c286e4bf5ad5 introduce machine_system_mmap
Mathieu Lacage <mathieu.lacage@sophia.inria.fr>
parents: 243
diff changeset
     2
#include "machine.h"
5
9c494e553ab8 wrapper around syscalls
Mathieu Lacage <mathieu.lacage@sophia.inria.fr>
parents:
diff changeset
     3
#include <sys/mman.h>
19
81ba45397f67 start file loading.
Mathieu Lacage <mathieu.lacage@sophia.inria.fr>
parents: 11
diff changeset
     4
#include <fcntl.h>
219
dada1f12a458 fix return type of munmap and add getpagesize
Mathieu Lacage <mathieu.lacage@sophia.inria.fr>
parents: 77
diff changeset
     5
#include <sys/param.h> // for EXEC_PAGESIZE
231
41ad566b03d8 lock dlopen/dlclose
Mathieu Lacage <mathieu.lacage@sophia.inria.fr>
parents: 219
diff changeset
     6
#include <linux/futex.h>
5
9c494e553ab8 wrapper around syscalls
Mathieu Lacage <mathieu.lacage@sophia.inria.fr>
parents:
diff changeset
     7
19
81ba45397f67 start file loading.
Mathieu Lacage <mathieu.lacage@sophia.inria.fr>
parents: 11
diff changeset
     8
/* The magic checks below for -256 are probably misterious to non-kernel programmers:
81ba45397f67 start file loading.
Mathieu Lacage <mathieu.lacage@sophia.inria.fr>
parents: 11
diff changeset
     9
 * they come from the fact that we call the raw system calls, not the libc wrappers
81ba45397f67 start file loading.
Mathieu Lacage <mathieu.lacage@sophia.inria.fr>
parents: 11
diff changeset
    10
 * here so, we get the kernel return value which does not give us errno so, the
81ba45397f67 start file loading.
Mathieu Lacage <mathieu.lacage@sophia.inria.fr>
parents: 11
diff changeset
    11
 * error number is multiplexed with the return value of the system call itself.
81ba45397f67 start file loading.
Mathieu Lacage <mathieu.lacage@sophia.inria.fr>
parents: 11
diff changeset
    12
 * In practice, since there are less than 256 errnos defined (on my system, 131), 
81ba45397f67 start file loading.
Mathieu Lacage <mathieu.lacage@sophia.inria.fr>
parents: 11
diff changeset
    13
 * the kernel returns -errno to indicate an error, the expected value otherwise.
81ba45397f67 start file loading.
Mathieu Lacage <mathieu.lacage@sophia.inria.fr>
parents: 11
diff changeset
    14
 */
81ba45397f67 start file loading.
Mathieu Lacage <mathieu.lacage@sophia.inria.fr>
parents: 11
diff changeset
    15
252
c286e4bf5ad5 introduce machine_system_mmap
Mathieu Lacage <mathieu.lacage@sophia.inria.fr>
parents: 243
diff changeset
    16
void *system_mmap(void *start, size_t length, int prot, int flags, int fd, off_t offset)
c286e4bf5ad5 introduce machine_system_mmap
Mathieu Lacage <mathieu.lacage@sophia.inria.fr>
parents: 243
diff changeset
    17
{
498
e20e1bd4bbf3 move syscall functions to .c file.
Mathieu Lacage <mathieu.lacage@sophia.inria.fr>
parents: 252
diff changeset
    18
  void *retval = machine_system_mmap (start, length, prot, flags, fd, offset);
e20e1bd4bbf3 move syscall functions to .c file.
Mathieu Lacage <mathieu.lacage@sophia.inria.fr>
parents: 252
diff changeset
    19
  return retval;
252
c286e4bf5ad5 introduce machine_system_mmap
Mathieu Lacage <mathieu.lacage@sophia.inria.fr>
parents: 243
diff changeset
    20
}
c286e4bf5ad5 introduce machine_system_mmap
Mathieu Lacage <mathieu.lacage@sophia.inria.fr>
parents: 243
diff changeset
    21
219
dada1f12a458 fix return type of munmap and add getpagesize
Mathieu Lacage <mathieu.lacage@sophia.inria.fr>
parents: 77
diff changeset
    22
int system_munmap (uint8_t *start, size_t size)
5
9c494e553ab8 wrapper around syscalls
Mathieu Lacage <mathieu.lacage@sophia.inria.fr>
parents:
diff changeset
    23
{
498
e20e1bd4bbf3 move syscall functions to .c file.
Mathieu Lacage <mathieu.lacage@sophia.inria.fr>
parents: 252
diff changeset
    24
  int status = MACHINE_SYSCALL2 (munmap, start, size);
219
dada1f12a458 fix return type of munmap and add getpagesize
Mathieu Lacage <mathieu.lacage@sophia.inria.fr>
parents: 77
diff changeset
    25
  if (status < 0 && status > -256)
dada1f12a458 fix return type of munmap and add getpagesize
Mathieu Lacage <mathieu.lacage@sophia.inria.fr>
parents: 77
diff changeset
    26
    {
dada1f12a458 fix return type of munmap and add getpagesize
Mathieu Lacage <mathieu.lacage@sophia.inria.fr>
parents: 77
diff changeset
    27
      return -1;
dada1f12a458 fix return type of munmap and add getpagesize
Mathieu Lacage <mathieu.lacage@sophia.inria.fr>
parents: 77
diff changeset
    28
    }
dada1f12a458 fix return type of munmap and add getpagesize
Mathieu Lacage <mathieu.lacage@sophia.inria.fr>
parents: 77
diff changeset
    29
  return status;
5
9c494e553ab8 wrapper around syscalls
Mathieu Lacage <mathieu.lacage@sophia.inria.fr>
parents:
diff changeset
    30
}
19
81ba45397f67 start file loading.
Mathieu Lacage <mathieu.lacage@sophia.inria.fr>
parents: 11
diff changeset
    31
int system_mprotect (const void *addr, size_t len, int prot)
81ba45397f67 start file loading.
Mathieu Lacage <mathieu.lacage@sophia.inria.fr>
parents: 11
diff changeset
    32
{
498
e20e1bd4bbf3 move syscall functions to .c file.
Mathieu Lacage <mathieu.lacage@sophia.inria.fr>
parents: 252
diff changeset
    33
  int status = MACHINE_SYSCALL3 (mprotect, addr, len, prot);
19
81ba45397f67 start file loading.
Mathieu Lacage <mathieu.lacage@sophia.inria.fr>
parents: 11
diff changeset
    34
  if (status < 0 && status > -256)
81ba45397f67 start file loading.
Mathieu Lacage <mathieu.lacage@sophia.inria.fr>
parents: 11
diff changeset
    35
    {
81ba45397f67 start file loading.
Mathieu Lacage <mathieu.lacage@sophia.inria.fr>
parents: 11
diff changeset
    36
      return -1;
81ba45397f67 start file loading.
Mathieu Lacage <mathieu.lacage@sophia.inria.fr>
parents: 11
diff changeset
    37
    }
81ba45397f67 start file loading.
Mathieu Lacage <mathieu.lacage@sophia.inria.fr>
parents: 11
diff changeset
    38
  return status;
81ba45397f67 start file loading.
Mathieu Lacage <mathieu.lacage@sophia.inria.fr>
parents: 11
diff changeset
    39
}
11
3f8127aba22f add logging framework, initialize it from LD_DEBUG
Mathieu Lacage <mathieu.lacage@sophia.inria.fr>
parents: 5
diff changeset
    40
void system_write (int fd, const void *buf, size_t size)
3f8127aba22f add logging framework, initialize it from LD_DEBUG
Mathieu Lacage <mathieu.lacage@sophia.inria.fr>
parents: 5
diff changeset
    41
{
498
e20e1bd4bbf3 move syscall functions to .c file.
Mathieu Lacage <mathieu.lacage@sophia.inria.fr>
parents: 252
diff changeset
    42
  MACHINE_SYSCALL3(write,fd,buf,size);
11
3f8127aba22f add logging framework, initialize it from LD_DEBUG
Mathieu Lacage <mathieu.lacage@sophia.inria.fr>
parents: 5
diff changeset
    43
}
19
81ba45397f67 start file loading.
Mathieu Lacage <mathieu.lacage@sophia.inria.fr>
parents: 11
diff changeset
    44
int system_open_ro (const char *file)
81ba45397f67 start file loading.
Mathieu Lacage <mathieu.lacage@sophia.inria.fr>
parents: 11
diff changeset
    45
{
498
e20e1bd4bbf3 move syscall functions to .c file.
Mathieu Lacage <mathieu.lacage@sophia.inria.fr>
parents: 252
diff changeset
    46
  int status = MACHINE_SYSCALL2 (open,file,O_RDONLY);
19
81ba45397f67 start file loading.
Mathieu Lacage <mathieu.lacage@sophia.inria.fr>
parents: 11
diff changeset
    47
  if (status < 0 && status > -256)
81ba45397f67 start file loading.
Mathieu Lacage <mathieu.lacage@sophia.inria.fr>
parents: 11
diff changeset
    48
    {
81ba45397f67 start file loading.
Mathieu Lacage <mathieu.lacage@sophia.inria.fr>
parents: 11
diff changeset
    49
      return -1;
81ba45397f67 start file loading.
Mathieu Lacage <mathieu.lacage@sophia.inria.fr>
parents: 11
diff changeset
    50
    }
81ba45397f67 start file loading.
Mathieu Lacage <mathieu.lacage@sophia.inria.fr>
parents: 11
diff changeset
    51
  return status;
81ba45397f67 start file loading.
Mathieu Lacage <mathieu.lacage@sophia.inria.fr>
parents: 11
diff changeset
    52
}
81ba45397f67 start file loading.
Mathieu Lacage <mathieu.lacage@sophia.inria.fr>
parents: 11
diff changeset
    53
int system_read (int fd, void *buffer, size_t to_read)
81ba45397f67 start file loading.
Mathieu Lacage <mathieu.lacage@sophia.inria.fr>
parents: 11
diff changeset
    54
{
498
e20e1bd4bbf3 move syscall functions to .c file.
Mathieu Lacage <mathieu.lacage@sophia.inria.fr>
parents: 252
diff changeset
    55
  int status = MACHINE_SYSCALL3 (read, fd, buffer, to_read);
19
81ba45397f67 start file loading.
Mathieu Lacage <mathieu.lacage@sophia.inria.fr>
parents: 11
diff changeset
    56
  if (status < 0 && status > -256)
81ba45397f67 start file loading.
Mathieu Lacage <mathieu.lacage@sophia.inria.fr>
parents: 11
diff changeset
    57
    {
81ba45397f67 start file loading.
Mathieu Lacage <mathieu.lacage@sophia.inria.fr>
parents: 11
diff changeset
    58
      return -1;
81ba45397f67 start file loading.
Mathieu Lacage <mathieu.lacage@sophia.inria.fr>
parents: 11
diff changeset
    59
    }
81ba45397f67 start file loading.
Mathieu Lacage <mathieu.lacage@sophia.inria.fr>
parents: 11
diff changeset
    60
  return status;
81ba45397f67 start file loading.
Mathieu Lacage <mathieu.lacage@sophia.inria.fr>
parents: 11
diff changeset
    61
}
81ba45397f67 start file loading.
Mathieu Lacage <mathieu.lacage@sophia.inria.fr>
parents: 11
diff changeset
    62
int system_lseek (int fd, off_t offset, int whence)
81ba45397f67 start file loading.
Mathieu Lacage <mathieu.lacage@sophia.inria.fr>
parents: 11
diff changeset
    63
{
498
e20e1bd4bbf3 move syscall functions to .c file.
Mathieu Lacage <mathieu.lacage@sophia.inria.fr>
parents: 252
diff changeset
    64
  int status = MACHINE_SYSCALL3 (lseek, fd, offset, whence);
19
81ba45397f67 start file loading.
Mathieu Lacage <mathieu.lacage@sophia.inria.fr>
parents: 11
diff changeset
    65
  if (status < 0 && status > -256)
81ba45397f67 start file loading.
Mathieu Lacage <mathieu.lacage@sophia.inria.fr>
parents: 11
diff changeset
    66
    {
81ba45397f67 start file loading.
Mathieu Lacage <mathieu.lacage@sophia.inria.fr>
parents: 11
diff changeset
    67
      return -1;
81ba45397f67 start file loading.
Mathieu Lacage <mathieu.lacage@sophia.inria.fr>
parents: 11
diff changeset
    68
    }
81ba45397f67 start file loading.
Mathieu Lacage <mathieu.lacage@sophia.inria.fr>
parents: 11
diff changeset
    69
  return status;
81ba45397f67 start file loading.
Mathieu Lacage <mathieu.lacage@sophia.inria.fr>
parents: 11
diff changeset
    70
}
81ba45397f67 start file loading.
Mathieu Lacage <mathieu.lacage@sophia.inria.fr>
parents: 11
diff changeset
    71
int system_fstat (const char *file, struct stat *buf)
81ba45397f67 start file loading.
Mathieu Lacage <mathieu.lacage@sophia.inria.fr>
parents: 11
diff changeset
    72
{
498
e20e1bd4bbf3 move syscall functions to .c file.
Mathieu Lacage <mathieu.lacage@sophia.inria.fr>
parents: 252
diff changeset
    73
  int status = MACHINE_SYSCALL2 (stat,file,buf);
19
81ba45397f67 start file loading.
Mathieu Lacage <mathieu.lacage@sophia.inria.fr>
parents: 11
diff changeset
    74
  if (status < 0 && status > -256)
81ba45397f67 start file loading.
Mathieu Lacage <mathieu.lacage@sophia.inria.fr>
parents: 11
diff changeset
    75
    {
81ba45397f67 start file loading.
Mathieu Lacage <mathieu.lacage@sophia.inria.fr>
parents: 11
diff changeset
    76
      return -1;
81ba45397f67 start file loading.
Mathieu Lacage <mathieu.lacage@sophia.inria.fr>
parents: 11
diff changeset
    77
    }
81ba45397f67 start file loading.
Mathieu Lacage <mathieu.lacage@sophia.inria.fr>
parents: 11
diff changeset
    78
  return status;
81ba45397f67 start file loading.
Mathieu Lacage <mathieu.lacage@sophia.inria.fr>
parents: 11
diff changeset
    79
}
81ba45397f67 start file loading.
Mathieu Lacage <mathieu.lacage@sophia.inria.fr>
parents: 11
diff changeset
    80
void system_close (int fd)
81ba45397f67 start file loading.
Mathieu Lacage <mathieu.lacage@sophia.inria.fr>
parents: 11
diff changeset
    81
{
498
e20e1bd4bbf3 move syscall functions to .c file.
Mathieu Lacage <mathieu.lacage@sophia.inria.fr>
parents: 252
diff changeset
    82
  MACHINE_SYSCALL1 (close,fd);
19
81ba45397f67 start file loading.
Mathieu Lacage <mathieu.lacage@sophia.inria.fr>
parents: 11
diff changeset
    83
}
81ba45397f67 start file loading.
Mathieu Lacage <mathieu.lacage@sophia.inria.fr>
parents: 11
diff changeset
    84
void system_exit (int status)
81ba45397f67 start file loading.
Mathieu Lacage <mathieu.lacage@sophia.inria.fr>
parents: 11
diff changeset
    85
{
498
e20e1bd4bbf3 move syscall functions to .c file.
Mathieu Lacage <mathieu.lacage@sophia.inria.fr>
parents: 252
diff changeset
    86
  MACHINE_SYSCALL1 (exit, status);
19
81ba45397f67 start file loading.
Mathieu Lacage <mathieu.lacage@sophia.inria.fr>
parents: 11
diff changeset
    87
}
219
dada1f12a458 fix return type of munmap and add getpagesize
Mathieu Lacage <mathieu.lacage@sophia.inria.fr>
parents: 77
diff changeset
    88
dada1f12a458 fix return type of munmap and add getpagesize
Mathieu Lacage <mathieu.lacage@sophia.inria.fr>
parents: 77
diff changeset
    89
int system_getpagesize (void)
dada1f12a458 fix return type of munmap and add getpagesize
Mathieu Lacage <mathieu.lacage@sophia.inria.fr>
parents: 77
diff changeset
    90
{
dada1f12a458 fix return type of munmap and add getpagesize
Mathieu Lacage <mathieu.lacage@sophia.inria.fr>
parents: 77
diff changeset
    91
  // Theoretically, this should be a dynamically-calculated value but, really, I don't
dada1f12a458 fix return type of munmap and add getpagesize
Mathieu Lacage <mathieu.lacage@sophia.inria.fr>
parents: 77
diff changeset
    92
  // know how to query the kernel for this so, instead, we use the kernel headers.
dada1f12a458 fix return type of munmap and add getpagesize
Mathieu Lacage <mathieu.lacage@sophia.inria.fr>
parents: 77
diff changeset
    93
  return EXEC_PAGESIZE;
dada1f12a458 fix return type of munmap and add getpagesize
Mathieu Lacage <mathieu.lacage@sophia.inria.fr>
parents: 77
diff changeset
    94
}
231
41ad566b03d8 lock dlopen/dlclose
Mathieu Lacage <mathieu.lacage@sophia.inria.fr>
parents: 219
diff changeset
    95
void system_futex_wake (uint32_t *uaddr, uint32_t val)
41ad566b03d8 lock dlopen/dlclose
Mathieu Lacage <mathieu.lacage@sophia.inria.fr>
parents: 219
diff changeset
    96
{
498
e20e1bd4bbf3 move syscall functions to .c file.
Mathieu Lacage <mathieu.lacage@sophia.inria.fr>
parents: 252
diff changeset
    97
  MACHINE_SYSCALL6 (futex, uaddr, FUTEX_WAKE, val, 0, 0, 0);
231
41ad566b03d8 lock dlopen/dlclose
Mathieu Lacage <mathieu.lacage@sophia.inria.fr>
parents: 219
diff changeset
    98
}
41ad566b03d8 lock dlopen/dlclose
Mathieu Lacage <mathieu.lacage@sophia.inria.fr>
parents: 219
diff changeset
    99
void system_futex_wait (uint32_t *uaddr, uint32_t val)
41ad566b03d8 lock dlopen/dlclose
Mathieu Lacage <mathieu.lacage@sophia.inria.fr>
parents: 219
diff changeset
   100
{
498
e20e1bd4bbf3 move syscall functions to .c file.
Mathieu Lacage <mathieu.lacage@sophia.inria.fr>
parents: 252
diff changeset
   101
  MACHINE_SYSCALL6 (futex, uaddr, FUTEX_WAIT, val, 0, 0, 0);
231
41ad566b03d8 lock dlopen/dlclose
Mathieu Lacage <mathieu.lacage@sophia.inria.fr>
parents: 219
diff changeset
   102
}