Skip site navigation (1)Skip section navigation (2)
Date:      Wed, 17 Apr 2002 13:08:44 +1000 (EST)
From:      callum.gibson@db.com
To:        tlambert2@mindspring.com
Cc:        hackers@FreeBSD.ORG
Subject:   Re: ipcrm/shmctl failure (fix NOT found)
Message-ID:  <20020417030844.14060.qmail@merton.aus.deuba.com>
In-Reply-To: <3CBCD715.9E9B6971@mindspring.com> from "tlambert2@mindspring.com" at Apr 16, 2002 06:59:49 PM

next in thread | previous in thread | raw e-mail | index | archive | help
tlambert2@mindspring.com writes:
}] You'd actually think that not incrementing in the RFMEM case, but
}] then decrementing if the RFMEM reference goes from 1->0 would be
}] the correct thing to do.

I didn't know if you were talking about "not incrementing" when the
process exits or when it rforked. If you rfork(RFMEM), you'd want to
increment the vm_refcnt I'm pretty sure (and it does). The whole bug is
the point that vm_refcnt is never decremented and the shm_nattch is
therefore only decremented if you explicitly detach from memory (which
will call shm_delete_mapping). So if an rfork'd program uses shared mem
and crashes, the vm_refcnt stays > 1, the shared mem is never freed
because shmexit -> shm_delete_mapping is never called.  Hopefully this
only affects shared mem, as there is more stuff inside the if statement
you include below other than the shmexit.

}This should actually be a pretty trivial to fix.  If you look in
}/sys/kern/kern_exec.c in exec_new_vmspace(), you'll see the proper
}way of exiting on the shm instance:
}
}        if (vmspace->vm_refcnt == 1) {
}                if (vmspace->vm_shm)
}                        shmexit(imgp->proc);
}
}...in other words, the resource track exit does not occur until
}the reference count is about to go from 1->0.  Note that there
}is an implicit race here, actually, between the reference and
}the detach, in which another instance could conceivably be
}created.  8-(.

Don't know about the race, although one is mentioned in the cvs logs on
the current branch. I presume you're talking SMP only though?
As a side note, in current this reads:
	if (--vmspace->vm_refcnt == 0) {

However, I can't find the spot where the ref count _actually_ goes to zero
in 4.5 - I suspect it does, but the only decrement of vm_refcnt in the
code is in vmspace_free and I traced all calls to that. I suspect it
just frees all the memory associated with the process on exit
without doing the final decrement to zero. There is a comment just above
cpu_exit which says:

         * The address space is released by "vmspace_free(p->p_vmspace)";

but I don't know who calls that unless it somehow happens from cpu_exit.

}At this point, I think it would be wise to instrument rfork, fork,
}vm_fork, shmfork, and shmexit to see what's going on with your
}particular program.
}
}It may be that your program is reattaching an already attached
}shared memory segment, and expecting the behaviour to be sane.
}
}Really, the place to look for that would be in the Linux kernel
}sources, to see how it handled shares memory segments with Linux
}threads... it may be that it doesn't expect them to be attached,
}and that each thread is expected to do the attach.  The above
}instrumentation points should tell you this.

This is not limited to linux threads, it should affect anything which
increments vm_refcnt and allocates shared mem. It's obvious what should
happen, just not obvious how to implement it without causing a side effect.
Not sure that seeing how linux does it would help in this regard.

Anyway, all you volunteers step right up...

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?20020417030844.14060.qmail>