Packets just quit sending a file over TCP [file i/o debuggin included]

Started by
5 comments, last by codingsolo 17 years, 7 months ago
I have successfully been able to send a bitmap of 651 bytes over the network. For larger files it seems to just quit after a certain amount sent. These two output files are from the same send. File [#] - 1 is beginning to send, 2 is continue to send, 3 is ending send. The rightmost numbers are just GetTickCount() for a cheap timestamp. NOTE: Ignore the sprintf() error on line 48 (the first line 48 since I didn't increment the packet counter for the end, whoops), the size written is incorrect as the sprintf() accidentally had the # of bytes read total in that place. whoops, but no solution to what I'm experiencing. The server sending out the packets:

1 File [1], Size left is 11894, wrote 256 bytes at 81642781
2 File [2], Size left is 11638, wrote 256 bytes at 81642781
3 File [2], Size left is 11382, wrote 256 bytes at 81642781
4 File [2], Size left is 11126, wrote 256 bytes at 81642781
5 File [2], Size left is 10870, wrote 256 bytes at 81642781
6 File [2], Size left is 10614, wrote 256 bytes at 81642781
7 File [2], Size left is 10358, wrote 256 bytes at 81642781
8 File [2], Size left is 10102, wrote 256 bytes at 81642781
9 File [2], Size left is 9846, wrote 256 bytes at 81642781
10 File [2], Size left is 9590, wrote 256 bytes at 81642781
11 File [2], Size left is 9334, wrote 256 bytes at 81642781
12 File [2], Size left is 9078, wrote 256 bytes at 81642781
13 File [2], Size left is 8822, wrote 256 bytes at 81642781
14 File [2], Size left is 8566, wrote 256 bytes at 81642781
15 File [2], Size left is 8310, wrote 256 bytes at 81642781
16 File [2], Size left is 8054, wrote 256 bytes at 81642781
17 File [2], Size left is 7798, wrote 256 bytes at 81642781
18 File [2], Size left is 7542, wrote 256 bytes at 81642781
19 File [2], Size left is 7286, wrote 256 bytes at 81642781
20 File [2], Size left is 7030, wrote 256 bytes at 81642781
21 File [2], Size left is 6774, wrote 256 bytes at 81642781
22 File [2], Size left is 6518, wrote 256 bytes at 81642781
23 File [2], Size left is 6262, wrote 256 bytes at 81642781
24 File [2], Size left is 6006, wrote 256 bytes at 81642781
25 File [2], Size left is 5750, wrote 256 bytes at 81642781
26 File [2], Size left is 5494, wrote 256 bytes at 81642781
27 File [2], Size left is 5238, wrote 256 bytes at 81642781
28 File [2], Size left is 4982, wrote 256 bytes at 81642781
29 File [2], Size left is 4726, wrote 256 bytes at 81642781
30 File [2], Size left is 4470, wrote 256 bytes at 81642781
31 File [2], Size left is 4214, wrote 256 bytes at 81642781
32 File [2], Size left is 3958, wrote 256 bytes at 81642781
33 File [2], Size left is 3702, wrote 256 bytes at 81642781
34 File [2], Size left is 3446, wrote 256 bytes at 81642781
35 File [2], Size left is 3190, wrote 256 bytes at 81642781
36 File [2], Size left is 2934, wrote 256 bytes at 81642781
37 File [2], Size left is 2678, wrote 256 bytes at 81642781
38 File [2], Size left is 2422, wrote 256 bytes at 81642781
39 File [2], Size left is 2166, wrote 256 bytes at 81642781
40 File [2], Size left is 1910, wrote 256 bytes at 81642781
41 File [2], Size left is 1654, wrote 256 bytes at 81642781
42 File [2], Size left is 1398, wrote 256 bytes at 81642781
43 File [2], Size left is 1142, wrote 256 bytes at 81642781
44 File [2], Size left is 886, wrote 256 bytes at 81642781
45 File [2], Size left is 630, wrote 256 bytes at 81642781
46 File [2], Size left is 374, wrote 256 bytes at 81642781
47 File [2], Size left is 118, wrote 256 bytes at 81642781
48 File [2], Size left is 0, wrote 12032 bytes at 81642781
48 File [3], Size left is 0, wrote 0 bytes at 81642781


the client receiving the packets:

1 File [4], state 1: Size left is 11894, wrote 256 bytes at 81642781
2 File [4], state 2: Size left is 11638, wrote 256 bytes at 81642796
3 File [4], state 2: Size left is 11382, wrote 256 bytes at 81642796
4 File [4], state 2: Size left is 11126, wrote 256 bytes at 81642796
5 File [4], state 2: Size left is 10870, wrote 256 bytes at 81642812
6 File [4], state 2: Size left is 10614, wrote 256 bytes at 81642812
7 File [4], state 2: Size left is 10358, wrote 256 bytes at 81642812
8 File [4], state 2: Size left is 10102, wrote 256 bytes at 81642812
9 File [4], state 2: Size left is 9846, wrote 256 bytes at 81642828
10 File [4], state 2: Size left is 9590, wrote 256 bytes at 81642828
11 File [4], state 2: Size left is 9334, wrote 256 bytes at 81642828
12 File [4], state 2: Size left is 9078, wrote 256 bytes at 81642828
13 File [4], state 2: Size left is 8822, wrote 256 bytes at 81642843
14 File [4], state 2: Size left is 8566, wrote 256 bytes at 81642843
15 File [4], state 2: Size left is 8310, wrote 256 bytes at 81642843
16 File [4], state 2: Size left is 8054, wrote 256 bytes at 81642843
17 File [4], state 2: Size left is 7798, wrote 256 bytes at 81642859
18 File [4], state 2: Size left is 7542, wrote 256 bytes at 81642859
19 File [4], state 2: Size left is 7286, wrote 256 bytes at 81642859
20 File [4], state 2: Size left is 7030, wrote 256 bytes at 81642875
21 File [4], state 2: Size left is 6774, wrote 256 bytes at 81642875
22 File [4], state 2: Size left is 6518, wrote 256 bytes at 81642875
23 File [4], state 2: Size left is 6262, wrote 256 bytes at 81642875
24 File [4], state 2: Size left is 6006, wrote 256 bytes at 81642890
25 File [4], state 2: Size left is 5750, wrote 256 bytes at 81642890
26 File [4], state 2: Size left is 5494, wrote 256 bytes at 81642890
27 File [4], state 2: Size left is 5238, wrote 256 bytes at 81642890
28 File [4], state 2: Size left is 4982, wrote 256 bytes at 81642906
29 File [4], state 2: Size left is 4726, wrote 256 bytes at 81642906
30 File [4], state 2: Size left is 4470, wrote 256 bytes at 81642906


As you can see, the client quits at 30 and there are still 18 packets left to go!! I'm perplexed. Any leads in the right direction will be deeply appreciated. Brandon
Advertisement
Seeing the actual code would help.
Yeah I guess some code would help. I think a clue may have been in my server timestamps. I'm pushing all the packets at once. After some further debugging I went to my SendPacket() function I wrote and this is the output:

Bytes sent 1044 on send of 1024 bytes of 11126 left.Bytes sent 1044 on send of 1024 bytes of 10102 left.Bytes sent 1044 on send of 1024 bytes of 9078 left.Bytes sent 1044 on send of 1024 bytes of 8054 left.Bytes sent 1044 on send of 1024 bytes of 7030 left.Bytes sent 1044 on send of 1024 bytes of 6006 left.Bytes sent 1044 on send of 1024 bytes of 4982 left.Bytes sent 1044 on send of 1024 bytes of 3958 left.Bytes sent -1 on send of 1024 bytes of 2934 left.Last error was 183 !Bytes sent -1 on send of 1024 bytes of 1910 left.Last error was 183 !Bytes sent -1 on send of 1024 bytes of 886 left.Last error was 183 !Bytes sent -1 on send of 886 bytes of 0 left.Last error was 183 !Bytes sent -1 on send of 0 bytes of 0 left.Last error was 183 !


So it is actually failing to send the rest of the packets. Stupid server! The WSAGetLastError() is returning 183. After some searching on here it seems that I'm overflowing the TCP buffer and it is failing maybe???

Here's the code:

void CServer::SendFileToUser(CUser * cUser, sFileInfo* theFile){	sFileTransfer theTransfer;	int fun = 0;	sFileInfo helpFile;	helpFile.file.open("debuggin.txt",ios_base::out|ios_base::trunc);	// If we are starting the file.	if (!theFile->nCurrOffset)	{		theFile->nFileID = rand() % 9000000;		theFile->nFileSize = FileSize(theFile->file);		theTransfer.nFileState = FT_START;	}	 int bytesWrote = 0;		while (bytesWrote <= theFile->nFileSize)	{	// case 1:  If bytesLeft > FT_DATAPACKET		if ((theFile->nFileSize- bytesWrote)  > FT_DATAPACKET)	{		theTransfer.nFileID = theFile->nFileID;		if (theFile->nCurrOffset)			theTransfer.nFileState = FT_CONTINUE;					theFile->file.read(theTransfer.pData,FT_DATAPACKET);		theTransfer.nDataBytes = FT_DATAPACKET;		theFile->nCurrOffset += FT_DATAPACKET;		bytesWrote += FT_DATAPACKET;		theTransfer.nSizeLeft = (theFile->nFileSize- bytesWrote);			cUser->sockUser.SendPacket((void*)&theTransfer);		fun++;		char buff[256];		sprintf(buff, "%d File [%d], Size left is %d, wrote %d bytes at %d\n", fun, theTransfer.nFileState, theTransfer.nSizeLeft, FT_DATAPACKET, GetTickCount());		helpFile.file << buff;	}	// case 2:  bytesLeft < FT_DATAPACKET && bytesLeft > 4	else if ((theFile->nFileSize- bytesWrote) < FT_DATAPACKET && (theFile->nFileSize- bytesWrote) > 0)// && bytesLeft > 4)	{		theTransfer.nFileID = theFile->nFileID;		if (theFile->nCurrOffset)			theTransfer.nFileState = FT_CONTINUE;		theFile->file.read(theTransfer.pData,(theFile->nFileSize- bytesWrote) );//>>2);		theTransfer.nDataBytes = (theFile->nFileSize- bytesWrote) ;//>>2;			theFile->nCurrOffset += (theFile->nFileSize- bytesWrote) ;//>>2;		int ds = (theFile->nFileSize- bytesWrote);		bytesWrote += (theFile->nFileSize- bytesWrote);		theTransfer.nSizeLeft = (theFile->nFileSize- bytesWrote);			cUser->sockUser.SendPacket((void*)&theTransfer);		 fun++;		 	char buff[256];		sprintf(buff, "%d File [%d], Size left is %d, wrote %d bytes at %d\n", fun, theTransfer.nFileState, theTransfer.nSizeLeft, ds, GetTickCount());		helpFile.file << buff;	}		//// case 3:  bytesLeft > 0 && bytesLeft < 4	//else if ( bytesLeft > 0 && bytesLeft < 4)	//{	//	theTransfer.nFileID = theFile->nFileID;	//	if (theFile->nCurrOffset)	//		theTransfer.nFileState = FT_CONTINUE;	//	theFile->file.read((char*)&theTransfer.pData,bytesLeft);	//	theTransfer.nDataBytes = bytesLeft;	//	//	theFile->nCurrOffset += bytesLeft;	//	 bytesLeft = theFile->nFileSize -  theFile->nCurrOffset;	//}	// case 4:  bytesLeft == 0		else if ( (theFile->nFileSize- bytesWrote)  == 0)	{		theTransfer.nFileID = theFile->nFileID;		if (theFile->nCurrOffset)			theTransfer.nFileState = FT_END;		fun = fun;		theTransfer.nSizeLeft = 0;		theTransfer.nDataBytes = 0;				 	char buff[256];		sprintf(buff, "%d File [%d], Size left is %d, wrote %d bytes at %d\n", fun, theTransfer.nFileState, theTransfer.nSizeLeft, 0, GetTickCount());		helpFile.file << buff;		helpFile.file.close();		theFile->file.close();			cUser->sockUser.SendPacket((void*)&theTransfer);		break;    // escaping the while loop!			}		}} /// here is my SendPacket() function too.  Not very inline anymore with the debugging info hehehe.	inline void SendPacket(void* vpPacket)	{ 		int nSize = GetSizeFromID(((sBaseData*)vpPacket)->nID);		int x = send(sock, (char*)vpPacket, nSize + sizeof(int), 0); 				if (((sBaseData*)vpPacket)->nID == PID_FILETRANSFER)		{		fstream f;			f.open("debugs.txt",ios_base::app|ios_base::out);		if (!f.is_open())				f.open("debugs.txt",ios_base::app|ios_base::out);		char buffer[256];		sprintf(buffer, "Code %d on send of %d bytes of %d left.\n",x,((sFileTransfer*)vpPacket)->nDataBytes, ((sFileTransfer*)vpPacket)->nSizeLeft);		f << buffer;		if (x == SOCKET_ERROR)		{			sprintf(buffer, "Last error was %d !",WSAGetLastError());			f << buffer;		}		f.close();		}	}




Thanks for the interests in helping me resolve this problem!

Brandon

Problem slightly resolved!

I now shove all the file transfer packets into a Queue. Each main loop I distribute one packet to each user that has packets waiting in their queue.

This works good for a few hundred kilobytes, then it takes its toll on the protocol.

Am I correct in my assumption that with TCP I can just spit off a ton of packets at one time to a client and he'll get them all properly? I know that TCP guarantees packet delivery, error-free but I seem to be kicking its butt by overflowing its buffer.

If anyone can pseudo-code me a 'proper' method to send a file from the server to the client, I'll be much appreciative.

Brandon
Quote:Original post by codingsolo
Am I correct in my assumption that with TCP I can just spit off a ton of packets at one time to a client and he'll get them all properly? I know that TCP guarantees packet delivery, error-free but I seem to be kicking its butt by overflowing its buffer.


Correction; TCP guarantees data delivery, error-free. It does not deal in packets. When you write something to a TCP socket, you need to check how much was actually written, and if any of it didn't get written, you need to send that part again.
Similarly, when you receive something, you have to check how much you received -- TCP does not guarantee one receive call per send call. Check the Forum FAQ for more information.
enum Bool { True, False, FileNotFound };
Just a followup for any future referencer that may similar problems,

MY SOLUTION:


Just like the guidance here says, capture the return of send().

I utilize this by storing the packets waiting to go out in a STL-queue. I call my function SendPacket() that has a loop that keeps calling send(), escaping only when the BytesSent == BytesToBeSent, or (not logical OR, as I'm looking for the -1 from the send() and not BytesSent == -1 !!!!) I get a -1 (SOCK_ERROR failure!) on send(). My function SendPacket() returns an int of how many bytes were sent, but will return -1 on an error. If it returns something other than -1, I pop() the queue, otherwise I just return from my SendPacket() function and it tries to resend next iteration of the program's main loop where it distributes waiting packets to Users with packets in queue.


Brandon

This topic is closed to new replies.

Advertisement