I'm developing with VC2005, and I'm having a problem with a thread.
I have a thread that dequeue data from a queue and send it. But this thread send one petition and have to wait for the answer to send a new petition (I want to put a timeout to prevent a infinite timeout).
I have a thread like this:
while (true){
dequeue()
send()
WaitForSingleObject(ptClass->getMutex(),10000);
}
But this WaitForSingleObject never stops... I've init event like this:
HANDLE ghMutex = CreateEvent(NULL,FALSE, FALSE, "");
The idea is to block the thread to stop sending data, and when the answer comes, unblock this thread to send a new petition... Why never stops???
regards
This thread you have is waiting for the event to be SET to signaled so it can be woken up again. You have to set the event to signalled using SetEvent. Not sure where you'd do it, as I don't know your architecture, but that's what's missing.
The WaitForSingleObject is taking your thread out of CPU context, but it isn't being woken up again.
Your timeout of your Wait should be set to INFINITE if you want it to wait until the event has been set to signaled and you cannot guarantee that it will happen immediately.
You're not using a mutex, you're using a AutoResetEvent, but you have to set it!
Related
I have a thread for a connection UDP.
I want to pause my thread while timeout (or while there isn't new frames in my QStack which stores UDP frames).
run(){
forever{
QTimer *timer_nb = new QTimer();
timer_nb->start(500);
// --- Wait for timeout or new frames in my QStack
//then ....
}
}
I found a function select(), but I don't really understand how it works ...
Is there an alternative with Qt ?
(Sorry for my english)
The Qt mindset is most of the time to work with events, the Qt event loop will do the wait/pause for you. Though select (pselect on linux) does exactly what you want... it is not the Qt way.
A Qt way of doing it could be to connect to both signals of a new frame received and a timeout occured. If your objects are created in your UDP thread, their slots will be executed in the same thread (doc about this).
You can initialize in the run function and create+connect the signals to some custom slot(s), then instead of calling forever you just call exec() (doc). The run function will not return and therefore not terminate your thread, but will be waiting for events until you terminate the thread yourself by calling exit(). You can call it yourself when you have received what you want, or from the main thread to just stop processing the frames at some point.
Then you need a custom slot which process new frames and reset the QTimer to restart the timeout from 0. And eventually another custom slot to handle the timeout, or the same slot depending on what you have to do when it happens.
Now you can see your code is not blocking, so you could probably do all of this directly in the main thread, except if the data processing is long.
Use-case
Single threaded Application
Non-blocking Async-IO using poll
A waitable object ( eg. a mutex ) with a timeout period
Problem at hand
I don;t want to create a specialized thread to wait for a timeout, and thus, I want to use poll to wait for a timeout on the waitable object in an ~Async~ fashion.
Is it possible to get notified for a mutex wait timeout using poll?
Main thread Pseudo code
Existing logic
wait for multiple FDs using poll
for each ~ready~ FD, process the IO
goto #1
Desired Logic
wait for multiple FDs and Mutexes using poll
for each ~ready~ FD, process the IO
For each timedout mutex process timeout ( eg. execute a registered callback )
For each signaled mutex process wait completion
goto #1
Pthread mutexes do not have a file handle.
Implement your own mutex on top of eventfd, then you can wait for it with poll().
I have a windows service where I am receiving http requests and launching a process for it which might run more than an hour . I need to get notified in main service when a process ends .And when service is ended i need to terminate all child processes . I understand that if I do waitforsingleobject it will hang on windows service until the process is completed , and no further http requests will be entertained ? I am doing following for now which works but its not correct approach .
if(CreateProcess( TEXT(EXEPATH),
procArguments,
NULL,
NULL,
FALSE,
0,
NULL,
NULL,
&si,
&pi )
)
{
processHandles[processCount] = pi.hProcess;
processStreams[processCount] = eventId.c_str();
processCount++;
}
On Service stop I am doing this
for(int index=0;index<10;index++){
g_pAppLog->Log("Stop Process for processStreams[%d] %s\n",index,processStreams[index].c_str());
int terminationResult = TerminateProcess(processHandles[index],1);
}
The functions WaitForSingleObjectEx and WaitForMultipleObjectsEx allow you to specify a timeout, so that the function will not hang forever.
You can thus call the function in a loop, checking if the process has really terminated, or it's just a timeout expiration.
Anyway, you should not WaitFor anything, unless you have nothing better to do.
If you have a web server, you should listen to connection and spawn responding processes.
If you just want to check if a process terminated, you can call GetExitCodeProcess.
So, summing up, you might either:
Run a loop that:
accepts a request;
spawns a process;
checks if any of the previously created process terminated (without blocking);
Make a two-thread application, with one thread accepting requests, and the other one calling WaitForMultipleObjectsEx in a loop, and possibly handling children termination.
In your main service, you should create a thread to do that, so the main thread can still be running.. In this thread, you should use WaitforMultipleObjects to wait for all the child process to end, once a process is ended, the corresponding code will be execute.
Please check the MSDN for details
Do the waiting in a different thread than the one that is processing SCM requests. Use CreateEvent() to create a waitable manual-reset event, then have the waiting thread use WaitForMultipleObjects() to wait on both the event and the child process at the same time. WaitForMultipleObjects() will tell you which one is signaled first. When the service is being stopped, signal the event with SetEvent(). When the child process exits, its handle will be signaled. If the event gets signaled first, the waiting thread can call TerminateProcess() on the child process.
I have a pthread running and waiting for messages from a socket. The thread gets blocked to wait a message and doesn't wake up until receiving a new one. Is there a way to send a signal to thread to wake up and for the receive function (recvmsg) to return an error code related to signal?
Yes, by default SIGINT will interrupt all syscalls. From man recv:
EINTR The receive was interrupted by delivery of a signal before any
data were available; see signal(7).
and
MSG_WAITALL (since Linux 2.2)
This flag requests that the operation block until the full request is
satisfied. However, the call may still return less data than requested
if a signal is caught, an error or disconnect occurs, or the next
data to be received is of a different type than that returned.
However, you cannot target a specific thread or specific operation.
If you wish to have this, I suggest using a condition that the receiving thread can explicitely listen for. There is a wellknown trick on linux which allows the receiving thread to use select or poll to listen for the socket and the 'condition' simultaneously[1].
The trick is to open a pipe from the master thread to the client (receiving) thread. The master writes to the pipe upon reaching a certain state (the signal so to speak). The client (receiving) thread can simply poll both the pipe and the socket and only check which of the two awoke it.
[1] normally pthread_cond_wait and poll/select cannot be combined without racing so you'd need to program wait loops with small timeouts. On Win32 by contrast it is as simple as WaitForMultipleObjects and you're done
Simple question, I think.
I have one thread that responds to a callback that is called when a user connects via TCP. That callback wants an answer if I accept or reject the login. Problem is I have to send a login request to a security server via asynchronous message passing and wait for a response.
What is the best way to handle this? Right now I have some code that just loops in the callback testing to see if the security server has sent a reply and when it comes in I read it and return the appropriate boolean. It just seems kind of gross.
TIA
First of all, you need a locking library that contains a monitor class with the ability to:
acquire a lock, guaranteeing mutual exclusion, i.e. that only one thread can hold the lock at any time
sleep on the lock, which means releasing the lock temporarily, and sleeping until the lock can be reacquired
signal on the lock, notifying sleeping threads that they should wake up and reacquire the lock. It is only possible to signal on the lock while holding the lock. This means that the signal will never have the immediate effect of waking up other threads. Typically the signaling thread will signal and then immediately release the lock, allowing the threads that have just been signaled to wake up. Waking up has the effect of a return of the blocking call to sleep, with the lock reacquired.
So with that functionality available from some library, you need to implement a security server proxy that uses the asynchronous security server to implement a synchronous service. When the synchronous authenticate() function is called in some thread (denoted thread 1), this is what should happen:
proxy acquires the lock
proxy sends a request message to the security server
proxy goes to sleep, waiting for the result, thread 1 is now blocked and the lock is available
security server computes a result
security server sends a message with the result to the proxy
the proxy message handler function is called in thread 2, thread 1 is still blocked
the proxy acquires the lock in thread 2
the proxy retrieves the result from the message and stores it in a member variable
the proxy signals on the lock, causing thread 1 blocking on sleep to try to wake up, but it can't, because thread 2 still holds the lock (inside the sleep() function, thread 2 is now blocked on a call to acquire the lock)
the proxy message handler releases its lock
the sleep call in thread 1 reacquires the lock and returns
the synchronous function in thread 1 then immediately releases its lock and returns the result
The last part with thread 1 reacquiring the lock only to immediately release it may seem pointless, but it matters because this ensures that the message handler is done before the synchronous function proceeds.
In pseudocode, it actually looks a lot simpler that you might expect:
class SecutityProxy
{
public:
SecutityProxy( SecurityServer& server ) : m_server(server)
{}
Result authenticate( username, password )
{
m_monitor.lock();
m_server.send_message( username, password );
m_monitor.sleep();
m_monitor.unlock();
return m_result;
}
void message_received( message )
{
m_monitor.lock();
m_result = message;
m_monitor->signal();
m_monitor.unlock();
}
private:
SecurityServer& m_server;
Monitor m_monitor;
Result m_result;
};
Note that this implementation cannot handle more than one request at a time! In order to handle multiple concurrent requests, you need to be able to store multiple results. You also need to store the thread handles of the threads that correspond to each request. In the message handler, you need to figure out which thread is blocking on any given request, and then just wake up the relevant thread in the signal() call, the locking library must support this.
Note also that it is highly recommended to implement a RAII class to handle the lock() and unlock() calls on the monitor.
Presumably, you would block on your asynchronous call to the security server to effectively make it synchronous.
In the function that initiates the login check, after sending the message to request the check block on something. A Windows Event would work, as would a boolean flag and a boost::condition_variable or a boost::unique_future.
In the code that receives the response message from the security server set the event, or future or flag/condition variable. This will then wake up the initial function and allow it to return the appropriate response to the initial caller.