* procfs.c (procfs_wait): handle syscall events first.
* procfs.c (GDB_GREGSET_TYPE, GDB_FPREGSET_TYPE): new macros. * config/sparc/xm-sun4sol2.h: use them. * core-sol2.c: don't #undef gregset_t and fpregset_t. * sol-thread.c: ditto. * sparc-tdep.c: ditto.
This commit is contained in:
parent
afcad54a90
commit
15af627cc0
7 changed files with 1466 additions and 67 deletions
|
@ -1,3 +1,13 @@
|
|||
1998-11-24 Felix Lee <flee@cygnus.com>
|
||||
|
||||
* procfs.c (procfs_wait): handle syscall events first.
|
||||
|
||||
* procfs.c (GDB_GREGSET_TYPE, GDB_FPREGSET_TYPE): new macros.
|
||||
* config/sparc/xm-sun4sol2.h: use them.
|
||||
* core-sol2.c: don't #undef gregset_t and fpregset_t.
|
||||
* sol-thread.c: ditto.
|
||||
* sparc-tdep.c: ditto.
|
||||
|
||||
Tue Nov 24 14:13:10 1998 Andrew Cagney <cagney@chook>
|
||||
|
||||
* breakpoint.c (memory_breakpoint_size): Delete global.
|
||||
|
|
|
@ -25,11 +25,12 @@ Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. */
|
|||
|
||||
#include "xm-sysv4.h"
|
||||
|
||||
/* SVR4's can't seem to agree on what to call the type that contains the
|
||||
general registers. Kludge around it with a #define. */
|
||||
/* gdb wants to use the prgregset_t interface rather than
|
||||
the gregset_t interface, partly because that's what's
|
||||
used in core-sol2.c */
|
||||
|
||||
#define gregset_t prgregset_t
|
||||
#define fpregset_t prfpregset_t
|
||||
#define GDB_GREGSET_TYPE prgregset_t
|
||||
#define GDB_FPREGSET_TYPE prfpregset_t
|
||||
|
||||
/* These are not currently used in SVR4 (but should be, FIXME!). */
|
||||
#undef DO_DEFERRED_STORES
|
||||
|
|
|
@ -26,9 +26,6 @@ Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. */
|
|||
and sparc-nat.c to be able to read both flavours. */
|
||||
|
||||
#include "defs.h"
|
||||
#undef gregset_t
|
||||
#undef fpregset_t
|
||||
|
||||
#include <time.h>
|
||||
#include <sys/types.h>
|
||||
#include <sys/regset.h>
|
||||
|
|
114
gdb/merge-syscalls.sh
Executable file
114
gdb/merge-syscalls.sh
Executable file
|
@ -0,0 +1,114 @@
|
|||
#!/bin/sh
|
||||
|
||||
# Copyright 1998 Free Software Foundation, Inc.
|
||||
#
|
||||
# This file is part of GDB.
|
||||
#
|
||||
# This program is free software; you can redistribute it and/or modify
|
||||
# it under the terms of the GNU General Public License as published by
|
||||
# the Free Software Foundation; either version 2 of the License, or
|
||||
# (at your option) any later version.
|
||||
#
|
||||
# This program is distributed in the hope that it will be useful,
|
||||
# but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
# GNU General Public License for more details.
|
||||
#
|
||||
# You should have received a copy of the GNU General Public License
|
||||
# along with this program; if not, write to the Free Software
|
||||
# Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
|
||||
|
||||
################
|
||||
# Usage: merge-syscalls syscall.tab [HEADER-FILE ...]
|
||||
#
|
||||
# This will scan every HEADER-FILE
|
||||
# (default is /usr/include/sys/syscall.h)
|
||||
# for #define SYS_xxx directives,
|
||||
# recursively scanning #included files.
|
||||
#
|
||||
# Then it updates "syscall.tab", which is a file that has a
|
||||
# C fragment to initialize a table of known syscall names.
|
||||
# Any syscalls already in "syscall.tab" will be kept.
|
||||
#
|
||||
# In principle, you don't need to run this unless you're
|
||||
# porting gdb to a new host that uses procfs.c.
|
||||
#
|
||||
# FIXME: perhaps use gcc -E -dM instead.
|
||||
# FIXME: perhaps track which hosts have which syscalls.
|
||||
|
||||
DEST=$1; shift
|
||||
|
||||
WS=`printf "[\t ]*" 2>/dev/null || echo '[ ]*'`
|
||||
|
||||
|
||||
scan_all () {
|
||||
for file
|
||||
do
|
||||
scan_one $file
|
||||
done
|
||||
}
|
||||
|
||||
scan_one () {
|
||||
echo >&2 "scanning $1..."
|
||||
<$1 sed -n -e "
|
||||
/^#${WS}define${WS}SYS_[_a-zA-Z0-9]${WS}/ {
|
||||
s/^${WS}#${WS}define${WS}\(SYS_[_a-zA-Z0-9]*\)${WS}.*/\1/
|
||||
p
|
||||
}
|
||||
/${WS}syscall_table${WS}\[SYS_[_a-zA-Z0-9]*\]/ {
|
||||
s/^.*${WS}syscall_table${WS}\[\(SYS_[_a-zA-Z0-9]*\)\].*/\1/
|
||||
p
|
||||
}
|
||||
" $1 &&
|
||||
|
||||
includes=`
|
||||
<$1 sed -n -e "
|
||||
/^${WS}#${WS}include${WS}</{
|
||||
s/^${WS}#${WS}include${WS}<\([^>]*\)>.*/\1/
|
||||
p
|
||||
}
|
||||
" |
|
||||
while read inc; do
|
||||
for dir in /usr/include; do
|
||||
if [ -f "$dir/$inc" ]; then
|
||||
echo $dir/$inc
|
||||
fi
|
||||
done
|
||||
done
|
||||
` &&
|
||||
|
||||
scan_all $includes
|
||||
}
|
||||
|
||||
case $# in
|
||||
0)
|
||||
set -- /usr/include/sys/syscall.h
|
||||
;;
|
||||
esac
|
||||
|
||||
scan_all $DEST "$@" |
|
||||
sort -u |
|
||||
(
|
||||
echo "/* This file is semi-automatically updated by `basename $0` */"
|
||||
while read sys; do
|
||||
tail=`echo "$sys" | sed 's/^SYS_//'`
|
||||
echo "#if defined ($sys)"
|
||||
echo " syscall_table[$sys] = "\""$tail"\"";"
|
||||
echo "#endif"
|
||||
done
|
||||
) > tmp$$ || exit 1
|
||||
|
||||
if cmp -s $DEST tmp$$; then
|
||||
echo "$DEST unchanged"
|
||||
rm -f tmp$$
|
||||
|
||||
else
|
||||
echo "creating new $DEST..."
|
||||
if [ -f $DEST ]; then
|
||||
mv $DEST $DEST.orig || exit 1
|
||||
echo " (original moved to $DEST.orig)"
|
||||
fi
|
||||
mv tmp$$ $DEST
|
||||
fi
|
||||
|
||||
|
137
gdb/procfs.c
137
gdb/procfs.c
|
@ -116,6 +116,25 @@ regardless of whether or not the actual target has floating point hardware.
|
|||
# endif
|
||||
#endif /* HAVE_MULTIPLE_PROC_FDS */
|
||||
|
||||
|
||||
/* These #ifdefs are for sol2.x in particular. sol2.x has
|
||||
both a "gregset_t" and a "prgregset_t", which have
|
||||
similar uses but different layouts. sol2.x gdb tries to
|
||||
use prgregset_t (and prfpregset_t) everywhere. */
|
||||
|
||||
#ifdef GDB_GREGSET_TYPE
|
||||
typedef GDB_GREGSET_TYPE gdb_gregset_t;
|
||||
#else
|
||||
typedef gregset_t gdb_gregset_t;
|
||||
#endif
|
||||
|
||||
#ifdef GDB_FPREGSET_TYPE
|
||||
typedef GDB_FPREGSET_TYPE gdb_fpregset_t;
|
||||
#else
|
||||
typedef fpregset_t gdb_fpregset_t;
|
||||
#endif
|
||||
|
||||
|
||||
#define MAX_PROC_NAME_SIZE sizeof("/proc/1234567890/status")
|
||||
|
||||
extern struct target_ops procfs_ops; /* Forward declaration */
|
||||
|
@ -149,13 +168,13 @@ struct proc_ctl {
|
|||
/* set general registers */
|
||||
struct greg_ctl {
|
||||
int cmd;
|
||||
gregset_t gregset;
|
||||
gdb_gregset_t gregset;
|
||||
};
|
||||
|
||||
/* set fp registers */
|
||||
struct fpreg_ctl {
|
||||
int cmd;
|
||||
fpregset_t fpregset;
|
||||
gdb_fpregset_t fpregset;
|
||||
};
|
||||
|
||||
/* set signals to be traced */
|
||||
|
@ -221,6 +240,8 @@ struct procinfo {
|
|||
currently installed */
|
||||
/* Pointer to list of syscall trap handlers */
|
||||
struct procfs_syscall_handler *syscall_handlers;
|
||||
int saved_rtnval; /* return value and status for wait(), */
|
||||
int saved_statval; /* as supplied by a syscall handler. */
|
||||
int new_child; /* Non-zero if it's a new thread */
|
||||
};
|
||||
|
||||
|
@ -635,14 +656,14 @@ static void procfs_resume PARAMS ((int pid, int step,
|
|||
/* External function prototypes that can't be easily included in any
|
||||
header file because the args are typedefs in system include files. */
|
||||
|
||||
extern void supply_gregset PARAMS ((gregset_t *));
|
||||
extern void supply_gregset PARAMS ((gdb_gregset_t *));
|
||||
|
||||
extern void fill_gregset PARAMS ((gregset_t *, int));
|
||||
extern void fill_gregset PARAMS ((gdb_gregset_t *, int));
|
||||
|
||||
#ifdef FP0_REGNUM
|
||||
extern void supply_fpregset PARAMS ((fpregset_t *));
|
||||
extern void supply_fpregset PARAMS ((gdb_fpregset_t *));
|
||||
|
||||
extern void fill_fpregset PARAMS ((fpregset_t *, int));
|
||||
extern void fill_fpregset PARAMS ((gdb_fpregset_t *, int));
|
||||
#endif
|
||||
|
||||
/*
|
||||
|
@ -1997,7 +2018,7 @@ procfs_store_registers (regno)
|
|||
procfs_read_status (pi);
|
||||
memcpy ((char *) &greg.gregset,
|
||||
(char *) &pi->prstatus.pr_lwp.pr_context.uc_mcontext.gregs,
|
||||
sizeof (gregset_t));
|
||||
sizeof (gdb_gregset_t));
|
||||
}
|
||||
fill_gregset (&greg.gregset, regno);
|
||||
greg.cmd = PCSREG;
|
||||
|
@ -2023,7 +2044,7 @@ procfs_store_registers (regno)
|
|||
procfs_read_status (pi);
|
||||
memcpy ((char *) &fpreg.fpregset,
|
||||
(char *) &pi->prstatus.pr_lwp.pr_context.uc_mcontext.fpregs,
|
||||
sizeof (fpregset_t));
|
||||
sizeof (gdb_fpregset_t));
|
||||
}
|
||||
fill_fpregset (&fpreg.fpregset, regno);
|
||||
fpreg.cmd = PCSFPREG;
|
||||
|
@ -3359,31 +3380,68 @@ procfs_wait (pid, ourstatus)
|
|||
struct procinfo *pi;
|
||||
struct proc_ctl pctl;
|
||||
|
||||
if (pid != -1) /* Non-specific process? */
|
||||
pi = NULL;
|
||||
else
|
||||
for (pi = procinfo_list; pi; pi = pi->next)
|
||||
if (pi->had_event)
|
||||
break;
|
||||
scan_again:
|
||||
|
||||
/* handle all syscall events first, otherwise we might not
|
||||
notice a thread was created until too late. */
|
||||
|
||||
for (pi = procinfo_list; pi; pi = pi->next)
|
||||
{
|
||||
if (!pi->had_event)
|
||||
continue;
|
||||
|
||||
#ifdef UNIXWARE
|
||||
if (! (pi->prstatus.pr_lwp.pr_flags & (PR_STOPPED | PR_ISTOP)) )
|
||||
continue;
|
||||
|
||||
why = pi->prstatus.pr_lwp.pr_why;
|
||||
what = pi->prstatus.pr_lwp.pr_what;
|
||||
#else
|
||||
if (! (pi->prstatus.pr_flags & (PR_STOPPED | PR_ISTOP)) )
|
||||
continue;
|
||||
|
||||
why = pi->prstatus.pr_why;
|
||||
what = pi->prstatus.pr_what;
|
||||
#endif
|
||||
if (why == PR_SYSENTRY || why == PR_SYSEXIT)
|
||||
{
|
||||
int i;
|
||||
int found_handler = 0;
|
||||
|
||||
for (i = 0; i < pi->num_syscall_handlers; i++)
|
||||
if (pi->syscall_handlers[i].syscall_num == what)
|
||||
{
|
||||
found_handler = 1;
|
||||
pi->saved_rtnval = pi->pid;
|
||||
pi->saved_statval = 0;
|
||||
if (!pi->syscall_handlers[i].func
|
||||
(pi, what, why, &pi->saved_rtnval, &pi->saved_statval))
|
||||
pi->had_event = 0;
|
||||
break;
|
||||
}
|
||||
|
||||
if (!found_handler)
|
||||
{
|
||||
if (why == PR_SYSENTRY)
|
||||
error ("PR_SYSENTRY, unhandled system call %d", what);
|
||||
else
|
||||
error ("PR_SYSEXIT, unhandled system call %d", what);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/* find a relevant process with an event */
|
||||
|
||||
for (pi = procinfo_list; pi; pi = pi->next)
|
||||
if (pi->had_event && (pid == -1 || pi->pid == pid))
|
||||
break;
|
||||
|
||||
if (!pi)
|
||||
{
|
||||
wait_again:
|
||||
|
||||
if (pi)
|
||||
pi->had_event = 0;
|
||||
|
||||
pi = wait_fd ();
|
||||
wait_fd ();
|
||||
goto scan_again;
|
||||
}
|
||||
|
||||
if (pid != -1)
|
||||
for (pi = procinfo_list; pi; pi = pi->next)
|
||||
if (pi->pid == pid && pi->had_event)
|
||||
break;
|
||||
|
||||
if (!pi && !checkerr)
|
||||
goto wait_again;
|
||||
|
||||
#ifdef UNIXWARE
|
||||
if (!checkerr && !(pi->prstatus.pr_lwp.pr_flags & (PR_STOPPED | PR_ISTOP)))
|
||||
#else
|
||||
|
@ -3438,27 +3496,8 @@ procfs_wait (pid, ourstatus)
|
|||
break;
|
||||
case PR_SYSENTRY:
|
||||
case PR_SYSEXIT:
|
||||
{
|
||||
int i;
|
||||
int found_handler = 0;
|
||||
|
||||
for (i = 0; i < pi->num_syscall_handlers; i++)
|
||||
if (pi->syscall_handlers[i].syscall_num == what)
|
||||
{
|
||||
found_handler = 1;
|
||||
if (!pi->syscall_handlers[i].func (pi, what, why,
|
||||
&rtnval, &statval))
|
||||
goto wait_again;
|
||||
|
||||
break;
|
||||
}
|
||||
|
||||
if (!found_handler)
|
||||
if (why == PR_SYSENTRY)
|
||||
error ("PR_SYSENTRY, unhandled system call %d", what);
|
||||
else
|
||||
error ("PR_SYSEXIT, unhandled system call %d", what);
|
||||
}
|
||||
rtnval = pi->saved_rtnval;
|
||||
statval = pi->saved_statval;
|
||||
break;
|
||||
case PR_REQUESTED:
|
||||
statval = (SIGSTOP << 8) | 0177;
|
||||
|
|
|
@ -46,17 +46,6 @@ Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. */
|
|||
procfs.c. */
|
||||
|
||||
#include "defs.h"
|
||||
|
||||
/* Undefine gregset_t and fpregset_t to avoid conflict with defs in xm file. */
|
||||
|
||||
#ifdef gregset_t
|
||||
#undef gregset_t
|
||||
#endif
|
||||
|
||||
#ifdef fpregset_t
|
||||
#undef fpregset_t
|
||||
#endif
|
||||
|
||||
#include <thread.h>
|
||||
#include <proc_service.h>
|
||||
#include <thread_db.h>
|
||||
|
|
1249
gdb/syscall.tab
Normal file
1249
gdb/syscall.tab
Normal file
File diff suppressed because it is too large
Load diff
Loading…
Reference in a new issue