Skip site navigation (1)Skip section navigation (2)
Date:      Wed, 10 Apr 2002 13:18:14 +1000 (EST)
From:      callum.gibson@db.com
To:        tlambert2@mindspring.com
Cc:        hackers@FreeBSD.ORG
Subject:   Re: ipcrm/shmctl failure
Message-ID:  <20020410031814.21717.qmail@merton.aus.deuba.com>
In-Reply-To: <3CB37B90.521B33A5@mindspring.com> from "tlambert2@mindspring.com" at Apr 09, 2002 04:38:56 PM

next in thread | previous in thread | raw e-mail | index | archive | help
I have a theory (and a patch) if you're willing to hear it.

tlambert2@mindspring.com writes:
}> I'd like to take a step further and say it's in SYSVSHM design. All a
}> program has to do is forget to do a shm_detach() and you're f#$%ed.
}Heh.  I could make the same argument about "open"...

Except that the kernel seems to keep track of file handles ok.

}> You could say that X11 shouldn't use SHMs the way it does now yeah. =)
}The real problem is that over the UNIX domain socket, it doesn't
}get client disconnect notificiations necessary for resource tracking,
}AND browser use of these resources is practically the degenerate case.

I think you're right about the linux stuff. It looks that you _will_ get
an EINVAL on a valid shmid if it has already been marked for deletion
(but presumably still exists due to references). Using the -o to ipcs
I see there are existing references (why didn't anyone suggest that
before) - but these are by non existent processes.

I'm now pretty sure this is caused by the linux implementation of
threads which uses multiple processes instead of a single proces. Now
vm_fork() (vm/vm_glue.c) calls shmfork which increments the shm ref count
for the forked process but this _shouldn't_ get called when rfork is
called with RFMEM (which is what linux_clone() does). So, turning to
the exit side of things, sys_exit() calls exit1() which only calls
shmexit to decrement the count if vm_refcnt == 1. Ok, rfork(RFMEM)
increments vm_refcnt in vm_fork(), and it may be decremented in
vmspace_unshare() or vmspace_free(). However as best I can see, nothing
in exit1() calls any vm stuff unless vm_refcnt is already 1. So unless
someone can point out where I've missed the call, I think the fix is
something like:

--- kern_exit.c.orig    Fri Dec 14 14:33:50 2001
+++ kern_exit.c Wed Apr 10 13:16:01 2002
@@ -218,6 +218,8 @@
                    VM_MAXUSER_ADDRESS);
                (void) vm_map_remove(&vm->vm_map, VM_MIN_ADDRESS,
                    VM_MAXUSER_ADDRESS);
+       } else {
+       	vmspace_free(vm);
        }
 
        if (SESS_LEADER(p)) {

This will decrement the vm_refcnt for exiting rfork'd processes and allow
the final exit to do all the appropriate cleanup, including the shmexit.

linux-mozilla would be a pretty heavy thread user. If only linux threads
was posix compliant, eh (I know Terry has commented on this before).

Callum Gibson                               callum.gibson@db.com
Global Markets IT, Deutsche Bank, Australia       61 2 9258 1620
### The opinions in this message are mine and not Deutsche's ###

To Unsubscribe: send mail to majordomo@FreeBSD.org
with "unsubscribe freebsd-hackers" in the body of the message




Want to link to this message? Use this URL: <https://mail-archive.FreeBSD.org/cgi/mid.cgi?20020410031814.21717.qmail>