2004-06-03 Roland McGrath <roland@redhat.com>

* strace.c (main) [LINUX]: Expand TCBTAB as necessary for threads
	attached.  Attach threads only under -f.  Set TCB_FOLLOWFORK in them.
	(expand_tcbtab): New function, broken out of ...
	* process.c (fork_tcb): ... here, call that.
	* defs.h: Declare expand_tcbtab.
This commit is contained in:
Roland McGrath 2004-06-04 01:50:45 +00:00
parent 25e8259c36
commit 7b54a7ae61
3 changed files with 36 additions and 21 deletions

1
defs.h
View File

@ -413,6 +413,7 @@ extern char *xlookup P((struct xlat *, int));
extern struct tcb *alloctcb P((int));
extern struct tcb *pid2tcb P((int));
extern void droptcb P((struct tcb *));
extern int expand_tcbtab P((void));
extern void set_sortby P((char *));
extern void set_overhead P((int));

View File

@ -402,27 +402,10 @@ static int
fork_tcb(struct tcb *tcp)
{
if (nprocs == tcbtabsize) {
/* Allocate some more TCBs and expand the table.
We don't want to relocate the TCBs because our
callers have pointers and it would be a pain.
So tcbtab is a table of pointers. Since we never
free the TCBs, we allocate a single chunk of many. */
struct tcb **newtab = (struct tcb **)
realloc(tcbtab, 2 * tcbtabsize * sizeof tcbtab[0]);
struct tcb *newtcbs = (struct tcb *) calloc(tcbtabsize,
sizeof *newtcbs);
int i;
if (newtab == NULL || newtcbs == NULL) {
if (newtab != NULL)
free(newtab);
if (expand_tcbtab()) {
tcp->flags &= ~TCB_FOLLOWFORK;
fprintf(stderr, "sys_fork: tcb table full\n");
return 1;
}
for (i = tcbtabsize; i < 2 * tcbtabsize; ++i)
newtab[i] = &newtcbs[i - tcbtabsize];
tcbtabsize *= 2;
tcbtab = newtab;
}
tcp->flags |= TCB_FOLLOWFORK;

View File

@ -403,7 +403,7 @@ char *argv[];
# ifdef LINUX
if (tcp->flags & TCB_CLONE_THREAD)
continue;
{
if (followfork) {
char procdir[MAXPATHLEN];
DIR *dir;
sprintf(procdir, "/proc/%d/task", tcp->pid);
@ -424,13 +424,17 @@ char *argv[];
(char *) 1, 0) < 0)
++nerr;
else if (tid != tcbtab[c]->pid) {
tcp = alloctcb(tid);
if (nprocs == tcbtabsize &&
expand_tcbtab())
tcp = NULL;
else
tcp = alloctcb(tid);
if (tcp == NULL) {
fprintf(stderr, "%s: out of memory\n",
progname);
exit(1);
}
tcp->flags |= TCB_ATTACHED|TCB_CLONE_THREAD|TCB_CLONE_DETACHED;
tcp->flags |= TCB_ATTACHED|TCB_CLONE_THREAD|TCB_CLONE_DETACHED|TCB_FOLLOWFORK;
tcbtab[c]->nchildren++;
tcbtab[c]->nclone_threads++;
tcbtab[c]->nclone_detached++;
@ -688,6 +692,33 @@ struct tcb *tcp;
return;
}
int
expand_tcbtab()
{
/* Allocate some more TCBs and expand the table.
We don't want to relocate the TCBs because our
callers have pointers and it would be a pain.
So tcbtab is a table of pointers. Since we never
free the TCBs, we allocate a single chunk of many. */
struct tcb **newtab = (struct tcb **)
realloc(tcbtab, 2 * tcbtabsize * sizeof tcbtab[0]);
struct tcb *newtcbs = (struct tcb *) calloc(tcbtabsize,
sizeof *newtcbs);
int i;
if (newtab == NULL || newtcbs == NULL) {
if (newtab != NULL)
free(newtab);
return 1;
}
for (i = tcbtabsize; i < 2 * tcbtabsize; ++i)
newtab[i] = &newtcbs[i - tcbtabsize];
tcbtabsize *= 2;
tcbtab = newtab;
return 0;
}
struct tcb *
alloctcb(pid)
int pid;