9fans - fans of the OS Plan 9 from Bell Labs
 help / color / mirror / Atom feed
* [9fans] a pair nec bugs
@ 2011-05-20  1:30 erik quanstrom
  2011-05-20  5:05 ` [9fans] a pair nsec bugs erik quanstrom
  2011-05-20 10:43 ` [9fans] a pair nec bugs ron minnich
  0 siblings, 2 replies; 19+ messages in thread
From: erik quanstrom @ 2011-05-20  1:30 UTC (permalink / raw)
  To: 9fans

i've been having trouble with nsec.  i've been dealing with an application
that has ~128 processes.  it does not use the thread library, but these
processes all share memory.  unfortunately, this results in wild thrashing
of nsec(2) because there are more shared-memory processes than slots
in the fds[] table in /sys/src/libc/nsec.c.  a call to nsec can cause delays
of up to 1s.

unfortunately, this isn't the real motivation.  the real motivation is that
recently a few processes were added that need to have their own fd tables.
and unfortunately this causes nsec() to enter an infinite loop.

in looking at the code, there seemed to be a number of ways to fix one
particular problem, but the given algorithm seems resistant to a generally
correct solution.

it seemed to me that the _privates (see exec(2)) array was the way to go.
process-private memory will never by falsely shared between processes
that don't share fd tables.  i kept the global fd to keep from opening
nsec() too many times.

in the case of this application, instead of opening nsec() afresh on
nearly every call, it is now opened just 3 times.

one note is that while i'm aware of privalloc(2), i didn't use it.  the
implementation doesn't appear correct for shared-memory procs.
i think there are two issues
- locking is unnecessary.  the only preemptable unit of execution is
a process and each process is guarenteed to have its own instance
of _privates and _nprivates.
- for shared-memory procs, we will run out of privates because
the static privinit will be falsely shared.  privinit should be replaced
by using a private entry.

i've attached my proposed solution.

- erik

----

#include <u.h>
#include <libc.h>

extern	void	**_privates;
extern	int	_nprivates;

	int	fd	= -1;

/*
 * BUG: this is chosen by fiat and without coordination.
 * privalloc(2) does not appear safe in a shared-memory
 * environment.
 */
#define	Fd	((int*)_privates[0])

static uvlong order = 0x0001020304050607ULL;

static void
be2vlong(vlong *to, uchar *f)
{
	uchar *t, *o;
	int i;

	t = (uchar*)to;
	o = (uchar*)&order;
	for(i = 0; i < sizeof order; i++)
		t[o[i]] = f[i];
}

static int*
getfd(void)
{
	if(Fd != nil)
		return Fd;
	return &fd;
}

static void
reopen(int *fd)
{
	*fd = open("/dev/bintime", OREAD|OCEXEC);
}

vlong
nsec(void)
{
	int *p;
	uchar b[8];
	vlong t;

	p = getfd();
	if(*p == -1)
		reopen(p);
	if(pread(*p, b, sizeof b, 0) != sizeof b){
		if(p != Fd){
			p = malloc(sizeof *p);
			if(p == nil)
				return 0;
			_privates[0] = p;
		}
		reopen(p);
		if(pread(*p, b, sizeof b, 0) != sizeof b)
			return 0;
	}
	be2vlong(&t, b);
	return t;
}



^ permalink raw reply	[flat|nested] 19+ messages in thread
* Re: [9fans] a pair nec bugs
@ 2011-06-03 13:13 erik quanstrom
  0 siblings, 0 replies; 19+ messages in thread
From: erik quanstrom @ 2011-06-03 13:13 UTC (permalink / raw)
  To: 9fans

> unfortunately, that one still fails:

i was willing to accept the fact that closing random file descriptors
could result in lossage at this point to solve the infinite loop problem.
(and any library function that opens a fd is potentially racing with
any other thread closing random fds.)

it's worse than that, unfortunately.  since there's no close-on-exit
flag, a program that makes a habit of forking with a shared fd table
quickly hits the 5000 fd limit.  kfs is a quick casuality.

i do like your rsec(int fd), but for some reason i'd rather not admit
there's a fd in there.  one is tempted to paw through /proc/pid/fd.  :-)

- erik



^ permalink raw reply	[flat|nested] 19+ messages in thread

end of thread, other threads:[~2011-06-04 18:12 UTC | newest]

Thread overview: 19+ messages (download: mbox.gz / follow: Atom feed)
-- links below jump to the message on this page --
2011-05-20  1:30 [9fans] a pair nec bugs erik quanstrom
2011-05-20  5:05 ` [9fans] a pair nsec bugs erik quanstrom
2011-05-20 10:43 ` [9fans] a pair nec bugs ron minnich
2011-05-20 10:52   ` roger peppe
2011-05-20 10:57     ` ron minnich
2011-05-20 12:47   ` erik quanstrom
2011-05-20 19:03     ` ron minnich
2011-05-20 19:16       ` erik quanstrom
2011-05-21  3:27       ` erik quanstrom
2011-05-21  9:59         ` Charles Forsyth
2011-05-21 12:16           ` erik quanstrom
2011-05-21 21:50           ` erik quanstrom
2011-05-21 22:14             ` Charles Forsyth
2011-05-22  3:06               ` erik quanstrom
2011-05-22 13:30                 ` Charles Forsyth
2011-06-02 19:16                   ` erik quanstrom
2011-06-03  9:52                     ` Charles Forsyth
2011-06-04 18:12                       ` adriano
2011-06-03 13:13 erik quanstrom

This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for NNTP newsgroup(s).