PDA

View Full Version : thread with socket?



triperzonak
24th September 2008, 02:27
i have part of my application that connects through other pc and send data using socket, as i add this to my main project the timeout of socket will block the gui, so my solution is put this part of program to a qthread..

however after i do this


thread = new Mythread();
thread->start();

It will not wait for the socket to connect, the thread immediately exited so i add thread->wait()


thread = new Mythread();
thread->start();
thread->wait();//this solve the problem however..

by doing this it will block the GUI, and it is not the thread i want after all..

how to solve this?

yuriry
24th September 2008, 04:39
Sockets can be used in blocking (synchronous) and non-blocking (asynchronous) fashion. Non-blocking use of sockets does not require threads because it relies on signals and event loops.

There are two samples available:

Blocking sockets

http://doc.trolltech.com/4.4/network-blockingfortuneclient.html


Look at fortunethread.cpp

Non-blocking sockets

http://doc.trolltech.com/4.4/network-fortuneclient.html


Look at client.cpp

This document gives more background on these two usages of sockets: http://doc.trolltech.com/4.4/qtnetwork.html#using-tcp-with-qtcpsocket-and-qtcpserver

And this document provides some information on using event loops within threads: http://doc.trolltech.com/4.4/threads.html#per-thread-event-loop

It is hard to be more specific without knowing what MyThread::run() looks like.

triperzonak
24th September 2008, 15:26
yeah thanks..

the code doesnt use qt socket but linux socket

im trying to intergrate it to my qt app

im not in my programming pc now..


Mytread::run()
{
//connect using socket
//what would be the diffrence if I add
exec(); //here?
}

yuriry
24th September 2008, 17:28
I think exec() will not help you. You would only need to call it if you wanted to use sockets in a non-blocking way on a separate thread. I assume that you are using Linux sockets in a blocking manner (no select() calls). I would then keep a pointer to an instance of Mythread in an object that is created and used in GUI thread. Check BlockingClient.h for an example. When you receive data using Linux sockets, you need to pass the data to that GUI object. You can emit a signal that your GUI object can receive. See emit newFortune(...) in fortunethread.cpp. Also pay attention to different types of connections between objects: http://doc.trolltech.com/4.4/threads.html#signals-and-slots-across-threads Do not use direct connections without using some synchronization mechanism between Mythread and the GUI thread.

triperzonak
25th September 2008, 10:56
You would only need to call it if you wanted to use sockets in a non-blocking way on a separate thread.

yeah thats what i need.. so i will add exec() then?

i will just call it pass some parameter and execute, I dont need the return data i dont even need to test if the socket connects or not I want to let the thread do that and the application do what it should do.. Calling the socket blocks the GUI so i put it in a thread but if i need to put thread->wait() it will block GUI too..

im just avoiding to call it as binary but if it will block the GUI then i will reconsider it..

caduel
25th September 2008, 11:04
Use QSocketNotifier.
No need to create a separate thread. (You still may to so, if you want, though.)

HTH

yuriry
25th September 2008, 16:21
yeah thats what i need.. so i will add exec() then?

exec() is only required if you want to start an event loop on a thread. If you used QTcpSocket in conjunction with readyRead signal then you would need an event loop. But if you use Linux sockets, and I assume you do NOT use select/poll, just read/write, then you use them in a blocking fashion and your code should be similar to this example http://doc.trolltech.com/4.4/network-blockingfortuneclient.html Even if sockets are used there in a blocking way, GUI thread does not block because blocking read/write calls occur on a separate thread.

And as caduel pointed out, there is a way to achieve non-blocking behavior without creating extra threads, but it seems that it is not an option for you because you are just integrating existing code and do not want to do many changes to it.