Fr0zT Posted April 13, 2010 Share Posted April 13, 2010 (edited) Hi All, I'm hoping someone can help me with TCPRecv. I am using it quite successfully in my program for all but one HTTP POST call. All of the message does not arrive, it gets cut off. I have used wireshark to confirm that the entire message came in, but doesn't show up in $recv. I should have received 2960 bytes but I actually got about 1060 (after HTTP header.) It's also strange becuase normally when I POST with TCPSend, the [Next sequence number] of TCP properties end up being the [ACK] number when it comes back with "HTTP/1.1 200 OK", but with this one post, the [Next sequence number] was 696 and the [ACK] that came back was 697. Also right before the [ACK] was a [RST,ACK] which I assume has something to do with it being out of order (I don't see these resets anywhere else.) I have tried this from 2 different locations so I know it's not a firewall issue, besides I can see all of the data in wireshark, it just doesn't get to autoit TCPRecv. Also I know the problem is limited to Autoit because it works fine natively in a custom browser app. Here is a basic snip of my code: AutoItSetOption("TCPTimeout", "1000") ;I have tried higher values here too and with/without quotes.... TCPStartup() Local $dst="some IP address", $recv = "", $ConnectedSocket = TCPConnect($dst, 80), $postPacket="Some HTTP request here" TCPSend($ConnectedSocket, $postPacket) If @error Then _checkSocketErrors() ;just checks if socket <> -1 otherwise closes it While $recv = "" $recv = TCPRecv($ConnectedSocket, 131072) ;I have tried many values from 2048 and up.. ;I've also tried the BinaryToString with binary option for TCPRecv ;I have a GUIGetMsg() deal here for easing up on the tight loop. but I've tried it without WEnd consolewrite($recv & @CRLF) that's pretty much it. It works great on smaller bits of data, but over the 1024 area and I start missing stuff. Thanks in advance for any help! Edited April 13, 2010 by Fr0zT [size="1"][font="Lucida Console"]My ScriptsTrue multi-threaded ping[/font][/size] Link to comment Share on other sites More sharing options...
BrettF Posted April 14, 2010 Share Posted April 14, 2010 Maybe try editing your receiving loop? ;Reset $recv $recv = "" ;Start a loop While 1 ;Recieve data $recv &= TCPRecv($ConnectedSocket, 1024) ;If error then we have recieved all data or something has gone wrong ;Exit the loop If @error Then ExitLoop WEnd ;Display recieved data. MsgBox (0, "", $recv) Cheers, Brett Vist my blog!UDFs: Opens The Default Mail Client | _LoginBox | Convert Reg to AU3 | BASS.au3 (BASS.dll) (Includes various BASS Libraries) | MultiLang.au3 (Multi-Language GUIs!)Example Scripts: Computer Info Telnet Server | "Secure" HTTP Server (Based on Manadar's Server)Software: AAMP- Advanced AutoIt Media Player | WorldCam | AYTU - Youtube Uploader Tutorials: Learning to Script with AutoIt V3Projects (Hardware + AutoIt): ArduinoUseful Links: AutoIt 1-2-3 | The AutoIt Downloads Section: | SciTE4AutoIt3 Full Version! Link to comment Share on other sites More sharing options...
Fr0zT Posted April 14, 2010 Author Share Posted April 14, 2010 While 1 ;Recieve data $recv &= TCPRecv($ConnectedSocket, 1024) ;If error then we have recieved all data or something has gone wrong ;Exit the loop If @error Then ExitLoop WEnd I have been trying it that way as well with no luck (actually more like this is what I think you meant) While 1 ;Recieve data $recv &= TCPRecv($ConnectedSocket, 1024) ;If error then we have recieved all data or something has gone wrong ;Exit the loop If @error = 0 Then ExitLoop WEnd [size="1"][font="Lucida Console"]My ScriptsTrue multi-threaded ping[/font][/size] Link to comment Share on other sites More sharing options...
Fr0zT Posted April 16, 2010 Author Share Posted April 16, 2010 (edited) Alright I've figured it out. Turns out it was a timing thing all along. I just needed to wait a little longer for the data to come in. But probing @error for a 0 or -1 just doesn't work well enough so I decided instead that since this is HTTP, I could parse out the Content-Length and just wait until I got it all(or time-out) Local $bytes = 0, $timer_start = TimerInit() While 1 _checkMessages() ;My nMsg routine $recv &= TCPRecv($ConnectedSocket, 4096) If @error = -1 Then ExitLoop ;Just to be thorough $parse_start = StringInStr($recv, "Content-Length") + 15 If $parse_start > 15 Then $bytes = Int(StringStripWS(StringStripCR(StringMid($recv, $parse_start, StringInStr($recv,@CRLF,0,1,$parse_start) - $parse_start)),8)) ;This is what really makes the difference. Were waiting for all the data to come in If $bytes > 0 And StringLen($recv) >= $bytes Then ExitLoop If TimerDiff($timer_start) > 1000 + ($seconds * 1000) Then $seconds += 1 GUICtrlSetData($g_go, $seconds) If $seconds = 5 Then ExitLoop ;Last resort EndIf WEnd That did the trick, now the TCPRecv routine waits until it has received all the data before exiting. Edited April 16, 2010 by Fr0zT [size="1"][font="Lucida Console"]My ScriptsTrue multi-threaded ping[/font][/size] Link to comment Share on other sites More sharing options...
Recommended Posts
Create an account or sign in to comment
You need to be a member in order to leave a comment
Create an account
Sign up for a new account in our community. It's easy!
Register a new accountSign in
Already have an account? Sign in here.
Sign In Now