Asio::Async_read_some - bytes_transferred=0!
Hi, I am using async_read_some() to read data from a tcp connection. In the "async_read_some" handler, sometimes the "bytes_transferred" is zero, and also sometimes causes an error in the read handler called "The I/O operation has been aborted because of either a thread exit or an application request" What could be the reason? Is this an expected behavior? Thanks, Lloyd ______________________________________ Scanned and protected by Email scanner
I am using async_read_some() to read data from a tcp connection. In the "async_read_some" handler, sometimes the "bytes_transferred" is zero, and also sometimes causes an error in the read handler called "The I/O operation has been aborted because of either a thread exit or an application request"
What could be the reason? Is this an expected behavior?
This error usually means that you called socket.close()
This error usually means that you called socket.close()
What surprises me here is - *) The socket is not closed *) The accept handler of initial async_read_some gets the error ("The I/O operation has been aborted because of either a thread exit or an application request") *) After that I am able to wait on same socket and read the data from socket. (The async_read_some is again called form the handler of the "initial async_read_some 's accept handler in a recursive manner) Could there be any other reason for this? This is a multi-threaded application and each socket is created in a new thread, and thread would not exit without completing its execution... Thanks a lot for your hint, Lloyd ______________________________________ Scanned and protected by Email scanner
What surprises me here is -
*) The socket is not closed *) The accept handler of initial async_read_some gets the error ("The I/O operation has been aborted because of either a thread exit or an application request")
*) After that I am able to wait on same socket and read the data from socket. (The async_read_some is again called form the handler of the "initial async_read_some 's accept handler in a recursive manner)
Could there be any other reason for this? This is a multi-threaded application and each socket is created in a new thread, and thread would not exit without completing its execution...
Maybe the thread that calls async_read exits before the relevant completion handler is invoked? By the way, using threads in the way you described in asio-based program is usually a bad idea. The whole point of using async i/o is to avoid such an "explicit" multithreading -- usually one spawns multiple threads to scale for multiple CPUs only. http://www.boost.org/doc/libs/1_43_0/doc/html/boost_asio/examples.html#boost... http://www.boost.org/doc/libs/1_43_0/doc/html/boost_asio/examples.html#boost...
Maybe the thread that calls async_read exits before the relevant completion handler is invoked?
By the way, using threads in the way you described in asio-based program is usually a bad idea. The whole point of using async i/o is to avoid such an "explicit" multithreading -- usually one spawns multiple threads to scale for multiple CPUs only. http://www.boost.org/doc/libs/1_43_0/doc/html/boost_asio/examples.html#boost... http://www.boost.org/doc/libs/1_43_0/doc/html/boost_asio/examples.html#boost...
Yes, you are right, the thread is exiting before the async_read_some. I would like to let you know why I am using threads. This is a server application. The client can give any command, and the server will execute it. Some commands may take much longer time. In this kind of situations, the client may want to STOP the execution of that long job. With the help of threading I am able to do this with the help "Interruption points and interrupts". The server will receive a "STOP command with the thread ID" from the client, So the server can interrupt the thread and stop the job. Is there a better way to implement this? I would be very happy to know that, than using this dirty way I am using now... Thanks a lot, Lloyd ______________________________________ Scanned and protected by Email scanner
Yes, you are right, the thread is exiting before the async_read_some.
You mean "before async_read_some completion"? At least on Windows, this would cause the following behavior: "Note All I/O initiated by a given thread is canceled when that thread exits. For overlapped sockets, pending asynchronous operations can fail if the thread is closed before the operations complete. " http://msdn.microsoft.com/en-us/library/ms741688(VS.85).aspx
I would like to let you know why I am using threads. This is a server application. The client can give any command, and the server will execute it. Some commands may take much longer time. In this kind of situations, the client may want to STOP the execution of that long job. With the help of threading I am able to do this with the help "Interruption points and interrupts". The server will receive a "STOP command with the thread ID" from the client, So the server can interrupt the thread and stop the job.
Is there a better way to implement this? I would be very happy to know that, than using this dirty way I am using now...
Well, you can launch threads for your tasks -- still processing all the i/o in one thread (where you call io_service::run()): // pseudo code // gotCommand is always being called from within a single thread, where io_service::run() is running void gotCommand(Command cmd) { Task task = makeTask(cmd); launchThread(task); }
----- Original Message -----
From: "Igor R"
Yes, you are right, the thread is exiting before the async_read_some. You mean "before async_read_some completion"? At least on Windows,this would cause the following behavior:"Note All I/O initiated by a given thread is canceled when thatthread exits. For overlapped sockets, pending asynchronous operationscan fail if the thread is closed before the operations complete. "http://msdn.microsoft.com/en-us/library/ms741688(VS.85).aspx
I would like to let you know why I am using threads. This is a server> application. The client can give any command, and the server will execute> it. Some commands may take much longer time. In this kind of situations, the> client may want to STOP the execution of that long job. With the help of> threading I am able to do this with the help "Interruption points and> interrupts". The server will receive a "STOP command with the thread ID"> from the client, So the server can interrupt the thread and stop the job.>> Is there a better way to implement this? I would be very happy to know> that, than using this dirty way I am using now... Well, you can launch threads for your tasks -- still processing allthe i/o in one thread (where you call io_service::run()): // pseudo code// gotCommand is always being called from within a single thread,where io_service::run() is runningvoid gotCommand(Command cmd){ Task task = makeTask(cmd); launchThread(task);}_______________________________________________Boost-users mailing listBoost-users@lists.boost.orghttp://lists.boost.org/mailman/listinfo.cgi/boost-users
I think I am doing it in a very similar manner as you have mentioned. The socket is created in the main thread, where the io_service::run() is called.
From the initil data received on the socket, the command is recognised, then a new thread is created and the socket and io_service is passed to it as a reference. Then, inside the thread, the job is performed in an asynchronous manner. As the thread exists before async_read_some is called (I think so), I think at first I get the error in the async_read_some handler, later it works fine... I think a code snippet would be far better than the written words...
main() { ... try { boost::asio::io_service IOService; TCPServer Server(IOService); IOService.run(); } catch(std::exception& e) { } } TCPServer:: TCPServer () { StartAccept(); } TCPServer:: StartAccept() { ... ... //here createa new TCPConnection object , shared_from_this //Then inside TCPConnection object, it waits for new connection using async_accept } "All the code is copied from asio sample", and the async_read Handler does the following AsyncReadhandler() { ... boost::thread *th=new boost::thread(boost::bind(&TCPConnection::ExecutionRoutine,....)) } //This is a thread int TCPConnection::ExecutionRoutine(string Command) { ... ... if(Command = = "BIG_OPERATION") { boost::shared_ptr<BigOp> bo(new BigOp(Socket,IOService)); bo->Operation(); } //Thread exits here, but the "Operation" continues on socket and io_service.... } BigOp::Operation() { Socket.async_read_some(....); } What is your opinion about "signals and slots" in this kind of situation? Thanks a lot, Lloyd ______________________________________ Scanned and protected by Email scanner
participants (2)
-
Igor R
-
Lloyd