x32: add ia32 support
* Makefile.am (EXTRA_DIST): Add linux/x32/errnoent1.h, linux/x32/ioctlent1.h, linux/x32/signalent1.h and linux/x32/syscallent1.h. * configure.ac: Remove AC_GNU_SOURCE, obsoleted by AC_USE_SYSTEM_EXTENSIONS. * defs.h (SUPPORTED_PERSONALITIES): Set to 2 for X32. (PERSONALITY1_WORDSIZE): Set to 4 for X32. * file.c (stat64): New struct for X32. (sys_lseek32): New function for X32. (stat64): Undef. (sys_fstat64): Likewise. (sys_stat64): Likewise. (realprintstat64): New function for X32. (sys_fstat64): Likewise. (sys_stat64): Likewise. * mem.c (sys_old_mmap): New function for X32. * pathtrace.c (pathtrace_match): Also check sys_old_mmap for X32. * syscall.c (update_personality): Add X32 support. (get_scno): Support currpers == 1 for X32. * linux/syscall.h (sys_lseek32): New function prototype for X32. * linux/x32/errnoent1.h: New file. * linux/x32/ioctlent1.h: Likewise. * linux/x32/signalent1.h: Likewise. * linux/x32/syscallent1.h: Likewise.
This commit is contained in:
parent
2bb4581ee5
commit
085e428860
@ -80,6 +80,8 @@ EXTRA_DIST = $(man_MANS) errnoent.sh signalent.sh syscallent.sh ioctlsort.c \
|
||||
linux/tile/ioctlent.h.in linux/tile/syscallent.h \
|
||||
linux/x32/errnoent.h linux/x32/ioctlent.h.in \
|
||||
linux/x32/signalent.h linux/x32/syscallent.h \
|
||||
linux/x32/errnoent1.h linux/x32/ioctlent1.h \
|
||||
linux/x32/signalent1.h linux/x32/syscallent1.h \
|
||||
linux/x86_64/ioctlent.h.in linux/x86_64/syscallent.h \
|
||||
linux/x86_64/gentab.pl \
|
||||
linux/x86_64/errnoent1.h linux/x86_64/ioctlent1.h \
|
||||
|
@ -9,8 +9,6 @@ AM_MAINTAINER_MODE
|
||||
AC_CANONICAL_HOST
|
||||
|
||||
AC_PROG_CC
|
||||
AC_GNU_SOURCE
|
||||
|
||||
AC_USE_SYSTEM_EXTENSIONS
|
||||
|
||||
AC_MSG_CHECKING([for supported architecture])
|
||||
|
7
defs.h
7
defs.h
@ -227,6 +227,13 @@ extern long ptrace(int, int, char *, long);
|
||||
# define PERSONALITY2_WORDSIZE 4
|
||||
#endif
|
||||
|
||||
#ifdef X32
|
||||
# undef SUPPORTED_PERSONALITIES
|
||||
# define SUPPORTED_PERSONALITIES 2
|
||||
# define PERSONALITY0_WORDSIZE 4
|
||||
# define PERSONALITY1_WORDSIZE 4
|
||||
#endif
|
||||
|
||||
#ifdef ARM
|
||||
# undef SUPPORTED_PERSONALITIES
|
||||
# define SUPPORTED_PERSONALITIES 2
|
||||
|
129
file.c
129
file.c
@ -96,6 +96,28 @@ struct stat {
|
||||
unsigned long long st_ctime_nsec;
|
||||
long long __unused[3];
|
||||
};
|
||||
|
||||
struct stat64 {
|
||||
unsigned long long st_dev;
|
||||
unsigned char __pad0[4];
|
||||
unsigned long __st_ino;
|
||||
unsigned int st_mode;
|
||||
unsigned int st_nlink;
|
||||
unsigned long st_uid;
|
||||
unsigned long st_gid;
|
||||
unsigned long long st_rdev;
|
||||
unsigned char __pad3[4];
|
||||
long long st_size;
|
||||
unsigned long st_blksize;
|
||||
unsigned long long st_blocks;
|
||||
unsigned long st_atime;
|
||||
unsigned long st_atime_nsec;
|
||||
unsigned long st_mtime;
|
||||
unsigned int st_mtime_nsec;
|
||||
unsigned long st_ctime;
|
||||
unsigned long st_ctime_nsec;
|
||||
unsigned long long st_ino;
|
||||
};
|
||||
#else
|
||||
# undef dev_t
|
||||
# undef ino_t
|
||||
@ -521,6 +543,28 @@ sys_lseek(struct tcb *tcp)
|
||||
}
|
||||
return RVAL_LUDECIMAL;
|
||||
}
|
||||
|
||||
# if defined(X32)
|
||||
int
|
||||
sys_lseek32(struct tcb *tcp)
|
||||
{
|
||||
long offset;
|
||||
int _whence;
|
||||
|
||||
if (entering(tcp)) {
|
||||
printfd(tcp, tcp->u_arg[0]);
|
||||
tprints(", ");
|
||||
offset = tcp->u_arg[1];
|
||||
_whence = tcp->u_arg[2];
|
||||
if (_whence == SEEK_SET)
|
||||
tprintf("%lu, ", offset);
|
||||
else
|
||||
tprintf("%ld, ", offset);
|
||||
printxval(whence, _whence, "SEEK_???");
|
||||
}
|
||||
return RVAL_UDECIMAL;
|
||||
}
|
||||
# endif
|
||||
#else
|
||||
int
|
||||
sys_lseek(struct tcb *tcp)
|
||||
@ -2722,3 +2766,88 @@ sys_swapon(struct tcb *tcp)
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
|
||||
#ifdef X32
|
||||
# undef stat64
|
||||
# undef sys_fstat64
|
||||
# undef sys_stat64
|
||||
|
||||
static void
|
||||
realprintstat64(struct tcb *tcp, long addr)
|
||||
{
|
||||
struct stat64 statbuf;
|
||||
|
||||
if (!addr) {
|
||||
tprints("NULL");
|
||||
return;
|
||||
}
|
||||
if (syserror(tcp) || !verbose(tcp)) {
|
||||
tprintf("%#lx", addr);
|
||||
return;
|
||||
}
|
||||
|
||||
if (umove(tcp, addr, &statbuf) < 0) {
|
||||
tprints("{...}");
|
||||
return;
|
||||
}
|
||||
|
||||
if (!abbrev(tcp)) {
|
||||
tprintf("{st_dev=makedev(%lu, %lu), st_ino=%llu, st_mode=%s, ",
|
||||
(unsigned long) major(statbuf.st_dev),
|
||||
(unsigned long) minor(statbuf.st_dev),
|
||||
(unsigned long long) statbuf.st_ino,
|
||||
sprintmode(statbuf.st_mode));
|
||||
tprintf("st_nlink=%lu, st_uid=%lu, st_gid=%lu, ",
|
||||
(unsigned long) statbuf.st_nlink,
|
||||
(unsigned long) statbuf.st_uid,
|
||||
(unsigned long) statbuf.st_gid);
|
||||
tprintf("st_blksize=%lu, ",
|
||||
(unsigned long) statbuf.st_blksize);
|
||||
tprintf("st_blocks=%lu, ", (unsigned long) statbuf.st_blocks);
|
||||
}
|
||||
else
|
||||
tprintf("{st_mode=%s, ", sprintmode(statbuf.st_mode));
|
||||
switch (statbuf.st_mode & S_IFMT) {
|
||||
case S_IFCHR: case S_IFBLK:
|
||||
tprintf("st_rdev=makedev(%lu, %lu), ",
|
||||
(unsigned long) major(statbuf.st_rdev),
|
||||
(unsigned long) minor(statbuf.st_rdev));
|
||||
break;
|
||||
default:
|
||||
tprintf("st_size=%llu, ", (unsigned long long) statbuf.st_size);
|
||||
break;
|
||||
}
|
||||
if (!abbrev(tcp)) {
|
||||
tprintf("st_atime=%s, ", sprinttime(statbuf.st_atime));
|
||||
tprintf("st_mtime=%s, ", sprinttime(statbuf.st_mtime));
|
||||
tprintf("st_ctime=%s", sprinttime(statbuf.st_ctime));
|
||||
tprints("}");
|
||||
}
|
||||
else
|
||||
tprints("...}");
|
||||
}
|
||||
|
||||
int
|
||||
sys_fstat64(struct tcb *tcp)
|
||||
{
|
||||
if (entering(tcp)) {
|
||||
printfd(tcp, tcp->u_arg[0]);
|
||||
tprints(", ");
|
||||
} else {
|
||||
realprintstat64(tcp, tcp->u_arg[1]);
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
|
||||
int
|
||||
sys_stat64(struct tcb *tcp)
|
||||
{
|
||||
if (entering(tcp)) {
|
||||
printpath(tcp, tcp->u_arg[0]);
|
||||
tprints(", ");
|
||||
} else {
|
||||
realprintstat64(tcp, tcp->u_arg[1]);
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
#endif
|
||||
|
@ -371,3 +371,7 @@ int sys_shmsys();
|
||||
#define SYS_shmsys_subcall 207
|
||||
#define SYS_shmsys_nsubcalls 4
|
||||
#endif
|
||||
|
||||
#ifdef X32
|
||||
int sys_lseek32();
|
||||
#endif
|
||||
|
2
linux/x32/errnoent1.h
Normal file
2
linux/x32/errnoent1.h
Normal file
@ -0,0 +1,2 @@
|
||||
/* Our second set comes from the i386 files. */
|
||||
#include "../errnoent.h"
|
2
linux/x32/ioctlent1.h
Normal file
2
linux/x32/ioctlent1.h
Normal file
@ -0,0 +1,2 @@
|
||||
/* Our second set comes from the i386 files. */
|
||||
#include "linux/ioctlent.h"
|
2
linux/x32/signalent1.h
Normal file
2
linux/x32/signalent1.h
Normal file
@ -0,0 +1,2 @@
|
||||
/* Our second set comes from the i386 files. */
|
||||
#include "../signalent.h"
|
11
linux/x32/syscallent1.h
Normal file
11
linux/x32/syscallent1.h
Normal file
@ -0,0 +1,11 @@
|
||||
/* Our second set comes from the i386 files.
|
||||
Only a couple of calls we cannot support without the i386 headers. */
|
||||
|
||||
#define sys_oldstat printargs
|
||||
#define sys_oldfstat printargs
|
||||
#define sys_oldlstat printargs
|
||||
#define sys_lseek sys_lseek32
|
||||
#define sys_lstat64 sys_stat64
|
||||
#define sys_truncate64 sys_truncate
|
||||
#define sys_ftruncate64 sys_ftruncate
|
||||
#include "i386/syscallent.h"
|
34
mem.c
34
mem.c
@ -311,6 +311,40 @@ sys_mmap(struct tcb *tcp)
|
||||
#endif /* !HAVE_LONG_LONG_OFF_T */
|
||||
|
||||
#if _LFS64_LARGEFILE || HAVE_LONG_LONG_OFF_T
|
||||
# if defined(X32)
|
||||
int sys_old_mmap(struct tcb *tcp)
|
||||
{
|
||||
long u_arg[6];
|
||||
if (umoven(tcp, tcp->u_arg[0], sizeof(u_arg), (char *) u_arg) == -1)
|
||||
return 0;
|
||||
if (entering(tcp)) {
|
||||
/* addr */
|
||||
if (!u_arg[0])
|
||||
tprints("NULL, ");
|
||||
else
|
||||
tprintf("%#lx, ", u_arg[0]);
|
||||
/* len */
|
||||
tprintf("%lu, ", u_arg[1]);
|
||||
/* prot */
|
||||
printflags(mmap_prot, u_arg[2], "PROT_???");
|
||||
tprints(", ");
|
||||
/* flags */
|
||||
# ifdef MAP_TYPE
|
||||
printxval(mmap_flags, u_arg[3] & MAP_TYPE, "MAP_???");
|
||||
addflags(mmap_flags, u_arg[3] & ~MAP_TYPE);
|
||||
# else
|
||||
printflags(mmap_flags, u_arg[3], "MAP_???");
|
||||
# endif
|
||||
/* fd */
|
||||
tprints(", ");
|
||||
printfd(tcp, u_arg[4]);
|
||||
/* offset */
|
||||
tprintf(", %#lx", u_arg[5]);
|
||||
}
|
||||
return RVAL_HEX;
|
||||
}
|
||||
# endif
|
||||
|
||||
/* TODO: comment which arches use this routine.
|
||||
* For one, does ALPHA on Linux use this??
|
||||
* From code it seems that it might use 7 or 8 registers,
|
||||
|
@ -224,9 +224,7 @@ pathtrace_match(struct tcb *tcp)
|
||||
}
|
||||
|
||||
if (
|
||||
#if !defined X32
|
||||
s->sys_func == sys_old_mmap ||
|
||||
#endif
|
||||
s->sys_func == sys_mmap) {
|
||||
/* x, x, x, x, fd */
|
||||
return fdmatch(tcp, tcp->u_arg[4]);
|
||||
|
30
syscall.c
30
syscall.c
@ -273,6 +273,12 @@ update_personality(struct tcb *tcp, int personality)
|
||||
fprintf(stderr, "[ Process PID=%d runs in %s mode. ]\n",
|
||||
tcp->pid, names[personality]);
|
||||
}
|
||||
# elif defined(X32)
|
||||
if (!qflag) {
|
||||
static const char *const names[] = {"x32", "32 bit"};
|
||||
fprintf(stderr, "[ Process PID=%d runs in %s mode. ]\n",
|
||||
tcp->pid, names[personality]);
|
||||
}
|
||||
# endif
|
||||
}
|
||||
#endif
|
||||
@ -868,15 +874,25 @@ get_scno(struct tcb *tcp)
|
||||
}
|
||||
# endif
|
||||
# ifdef X32
|
||||
if (currpers == 0 || currpers == 1) {
|
||||
fprintf(stderr, "syscall_%lu (...) in unsupported %s "
|
||||
"mode of process PID=%d\n", scno,
|
||||
currpers == 0 ? "64-bit" : "32-bit", tcp->pid);
|
||||
return 0;
|
||||
/* Value of currpers:
|
||||
* 0: 64 bit
|
||||
* 1: 32 bit
|
||||
* 2: X32
|
||||
* Value of current_personality:
|
||||
* 0: X32
|
||||
* 1: 32 bit
|
||||
*/
|
||||
switch (currpers) {
|
||||
case 0:
|
||||
fprintf(stderr, "syscall_%lu (...) in unsupported "
|
||||
"64-bit mode of process PID=%d\n",
|
||||
scno, tcp->pid);
|
||||
return 0;
|
||||
case 2:
|
||||
currpers = 0;
|
||||
}
|
||||
# else
|
||||
update_personality(tcp, currpers);
|
||||
# endif
|
||||
update_personality(tcp, currpers);
|
||||
#elif defined(IA64)
|
||||
# define IA64_PSR_IS ((long)1 << 34)
|
||||
if (upeek(tcp, PT_CR_IPSR, &psr) >= 0)
|
||||
|
Loading…
x
Reference in New Issue
Block a user