I use global mutex in multi-process in windows, however, the mutex won't be released when the owner process crashes, and then another process calls WaitForSingleObject, it returns WAIT_ABANDONED, how should I do to let this mutex relase, or do some other actions when returns WAIT_ABANDONED?
Related
We develop a user-space process running on Linux 3.4.11 in an embedded MIPS system. The process creates multiple (>10) threads using pthreads. The process has a SIGSEGV signal handler which, among other things, generates a log message which goes to our log file. As part of this flow, it acquires a semaphore (bad, I know...).
During our testing the process appeared to hang. We're currently unable to build gdb for the target platform, so I wrote a CLI tool that uses ptrace to extract the register values and USER data using PTRACE_PEEKUSR.
What surprised me to see is that all of our threads were inside our crash handler, trying to acquire the semaphore. This (obviously?) indicates a deadlock on the semaphore, which means that a thread died while holding it. When I dug up the stack, it seemed that almost all of the threads (except one) were in a blocking call (recv, poll, sleep) when the signal handler started running. Manual stack reconstruction on MIPS is a pain so we have not fully done it yet. One thread appeared to be in the middle of a malloc call, which to me indicates that it crashed due to a heap corruption.
A couple of things are still unclear:
1) Assuming one thread crashed in malloc, why would all other threads be running the SIGSEGV handler? As I understand it, a SIGSEGV signal is delivered to the faulting thread, no? Does it mean that each and every one of our threads crashed?
2) Looking at the sigcontext struct for MIPS, it seems it does not contain the memory address which was accessed (badaddr). Is there another place that has it? I couldn't find it anywhere, but it seemed odd to me that it would not be available.
And of course, if anyone can suggest ways to continue the analysis, it would be appreciated!
Yes, it is likely that all of your threads crashed in turn, assuming that you have captured the thread state correctly.
siginfo_t has a si_addr member, which should give you the address of the fault. Whether your kernel fills that in is a different matter.
In-process crash handlers will always be unreliable. You should use an out-of-process handler, and set kernel.core_pattern to invoke it. In current kernels, it is not necessary to write the core file to disk; you can either read the core file from standard input, or just map the process memory of the zombie process (which is still available when the kernel invokes the crash handler).
Suppose that a Linux driver code acquires a spinlock, inside the critical section a function call force the process running on top of the driver to sleep. Knowing that to hold spinlock disables preemption on the relevant processor, is it possible for the process to wake up, and consequently to permit the driver code to release the spinlock ?
No, it is not allowed to sleep while holding a spinlock. Code that does this is buggy.
The only way the process could be woken is if code running on another core did something to wake it up (which means that yes, it will certainly deadlock if there is only one core).
while spinlock other process can't do anything to wake it up, you could try to use semaphores for this type of switching
I plan to use the WinApi CreateMutex function to only allow one running instance of my application. But I wonder what happens if the apps crashs. Is the created Mutex automatically released by the OS if the main process dies? I can't find an answer to this in the MS knowledgebase.
TIA!
A mutex is a kernel object whose lifetime is controlled by its references. When a process terminates, however it terminates, all the references to kernel objects held by that process are removed. If this leaves a kernel object having no remaining references to it, that kernel object is destroyed.
I have a thread that runs in a dll that I dynamic link with in my main app. Is there a way to wait for all threads in an .exe (including it's loaded dll's) without knowing the thread handle? Windows 7 x64, vc++
The thread is a function that does some processing on a certain file, it is not expected to return anything, it works upon a global class that is modified in certain stages of the thread completion. The thread function calls upon other functions .
I want to wait until the last line of the function is executed.
I never did this myself, but you could probably
create a snapshot using CreateToolhelp32Snapshot
then enumerate the threads using Thread32First and Thread32Next
for each thread ID, use OpenThread to aquire a handle. Make sure that you open the thread with the SYNCHRONIZE privilege so that you can, at last
pass all thread handles to WaitForMultipleObjects to wait for all of them to terminate.
Another solution, assuming that all you want is to stop the main() function from running but not exit the process until any other threads are complete, is to call
ExitThread(GetCurrentThread());
from within main(). If you don't call ExitProcess, either explicitly or by returning from main(), Windows will not exit until the last thread exits.
Note that there is a major problem with doing this, no matter how you approach it: if one of the Windows APIs you use has launched a thread that isn't going to exit, your application won't exit either.
The proper solution is for the DLL itself to contain a shutdown function that waits for its own threads to exit if necessary.
I'm trying to understand in a bit more detail how a OS loaderlock is used in relation to the loading and unloading of DLL's in Windows.
I understand that every loaded DLL get notified when a new thread is created/destroyed and or a new DLL is loaded/unloaded.
So does that mean that the DllMain function is run inside a lock and no other thread can access it while it is running, and if you were to create another thread in that function, you could hang the process or even the OS?
Is my understanding correct?
Is there some article somewhere that explain this?
A deadlock can happen when two threads try to acquire two locks in different sequence.
Thread A gets lock A and then tries to get lock B
Meanwhile thread B gets lock B and then tries to get lock A
A thread that's running DllMain has already acquired an implicit O/S lock: therefore they (Microsoft) reckon that it may be unsafe for that thread to try to acquire any other, second lock (e.g. because a different thread might already own that lock and be currently blocked on the implicit O/S lock).
that is correct.
Any such execution is illegal because
it can lead to deadlocks and to use of
DLLs before they have been initialized
by the operating system's loader.
More information can be found here: LoaderLock MDA (MSDN Website)