RSocket::Send() question

Login to reply to this topic.
Mon, 2006-12-11 11:46
Joined: 2006-12-11
Forum posts: 7
Hi Symbian geeks,
I have a question for you:
when the asynchronous method RSocket::Send() completes for a TCP/IP socket, where do the data to be sent reside with guarantee?
Does the completion of the Send() method mean that a) ALL of the data were succesfully pushed to the local TCP/IP stack or b) that ALL of the data were succesfully received by the remote TCP/IP stack?
I believe that the second is true but I need an answer from some expert to be 100% sure. If the first is true it means that to make sure that the data have been succesfully received by the remote, some kind of acknowledgment mechanism is needed on the application layer.

Thanks in advance,
George

Mon, 2006-12-11 17:53
Joined: 2005-02-18
Forum posts: 100
Re: RSocket::Send() question
The correct answer is (a).

Which means, the when you close the TCP socket, it will still stay around and try to transfer the unsent data (if any left). Application writer has be aware that

- with simple "Open - send data - Close" application cannot be 100% certain that all data was eventually transmitted. For that, you always need some application level protocol that acknowledges the receipt of file.

- some information can be got by doing Shutdown (ENormal or EStopOutput) before the Close. The OK completion at least signals that all data has been received by remote TCP protocol engine.

- if your protocol is like HTTP: send request and wait for reply, and the reply does not come. In such case, ALWAYS USE Shutdown EImmediate before closing. Otherwise the TCP machinery will potentially attempt deliver the request and orderly shutdown for several minutes!
Tue, 2006-12-12 13:31
Joined: 2006-10-07
Forum posts: 131
Re: RSocket::Send() question
As far as I can understand, you can use an overload of Send() to know how much data was sent (last argument).
Code:
IMPORT_C void Send(const TDesC8 &aDesc, TUint someFlags, TRequestStatus &aStatus, TSockXfrLength &aLen);
Tue, 2006-12-12 19:09
Joined: 2005-02-18
Forum posts: 100
Re: RSocket::Send() question
After digging deeper into this, I must revise my previous answer: unfortunately you cannot use Shutdown ENormal/EStopOutput to wait until all data has been sent. Both complete the request without waiting for the send buffers to become empty.

There is actually obscure ioctl that is supposed to do exactly that:
Code:
socket.Ioctl(KIoctlTcpNotifyDataSent, iStatus, NULL, KSolInetTcp);
When issued, it should complete when TCP send buffers become empty (of course this may not happen, if you keep filling the buffers with Send/Write at same time).

My advise for using Shutdown EImmediate for any stuck sockets still stands.

TSockXfrLength just tells how much data from your send was actually accepted into the protocol buffers (at this point I don't know exactly the situation when XfrLenth would be different from the length of aDesC8).
Wed, 2006-12-13 02:57
Joined: 2006-10-07
Forum posts: 131
Re: RSocket::Send() question
Quote from: msa2
TSockXfrLength just tells how much data from your send was actually accepted into the protocol buffers (at this point I don't know exactly the situation when XfrLenth would be different from the length of aDesC8).

Are you sure? Would that mean that documentation is not correct?


Quote from: RSocket Documentation
The TSockXfrLength argument will return the amount of data actually sent.
Fri, 2006-12-15 15:29
Joined: 2006-12-11
Forum posts: 7
Re: RSocket::Send() question
What I'm actually doing is to call the asynchronous RSocket::Write() to send some data to the remote host and I want to know if every single TCP packet, i.e. the complete data have been received by the remote TCP/IP stack.
So if Write() completes when the last packet is received & acknowledged by the remote TCP/IP stack then it makes me happy.
Else if there is no such guarantee I have to implement some kind of acknowledgment mechanism in the application layer to avoid cases where Write() may have complete with KErrNone but not all of the packets have been yet received by the remote host (e.g. connection breaks right after).
Also, my protocol is message-exchange based and not a request-reply. So, after a host sends a message to another it doesn't wait for a reply, it just wants to know if it eventually received the whole message. So I cannot use the Shutdown() method.
I know that TCP/IP is a reliable protocol but is this reliability transfered to the application level?

Thanks a lot,
George
Thu, 2008-05-08 04:48
Joined: 2008-01-31
Forum posts: 1
Re: RSocket::Send() question

what's the method to overcome this problem?
How to garantee that the pckg is received by the remote host?

  • Login to reply to this topic.