From d30dfd8631dcafcf27f595d6fc515f823ec57f43 Mon Sep 17 00:00:00 2001 From: Stephen Heumann Date: Tue, 14 Aug 2018 18:35:11 -0500 Subject: [PATCH] Before sending a request, check if the remote side has closed the connection. This avoids sending out requests that can't work, and also gives an opportunity to process packets from the old connection while it's still logged in, which may avoid some strange behavior. --- http.c | 42 ++++++++++++++++++++++++++++-------------- tcpconnection.c | 4 +--- 2 files changed, 29 insertions(+), 17 deletions(-) diff --git a/http.c b/http.c index 1cbaea3..ef5228f 100644 --- a/http.c +++ b/http.c @@ -93,7 +93,10 @@ Boolean BuildHTTPRequest(Session *sess, char *resourceStr) { enum NetDiskError DoHTTPRequest(Session *sess, unsigned long start, unsigned long end) { top:; - rlrBuff rlrBuff = {0}; + union { + srBuff srBuff; + rlrBuff rlrBuff; + } u; Word tcpError; Boolean wantRedirect = FALSE, gotRedirect = FALSE; enum NetDiskError result; @@ -105,6 +108,17 @@ top:; /* Send out request */ result = NETWORK_ERROR; unsigned int netErrors = 0; + + TCPIPPoll(); + if (sess->tcpLoggedIn) { + tcpError = TCPIPStatusTCP(sess->ipid, &u.srBuff); + if (tcpError || toolerror() || u.srBuff.srState != TCPSESTABLISHED) { + EndTCPConnection(sess); + } + } + + u.rlrBuff.rlrBuffHandle = NULL; + netRetry: if (!sess->tcpLoggedIn || netErrors) { if (StartTCPConnection(sess) != 0) @@ -128,7 +142,7 @@ netRetry: tcpError = TCPIPReadLineTCP(sess->ipid, (void*)((LongWord)"\p\r\n\r\n" | 0x80000000), buffTypeNewHandle, (Ref)NULL, - 0xFFFFFF, &rlrBuff); + 0xFFFFFF, &u.rlrBuff); if (tcpError || toolerror()) { if (netErrors == 0) { netErrors++; @@ -137,25 +151,25 @@ netRetry: goto errorReturn; } } - } while (rlrBuff.rlrBuffCount == 0 + } while (u.rlrBuff.rlrBuffCount == 0 && GetTick() - startTime < HTTP_RESPONSE_TIMEOUT * 60); result = NO_RESPONSE; - if (!rlrBuff.rlrIsDataFlag) + if (!u.rlrBuff.rlrIsDataFlag) goto errorReturn; result = INVALID_RESPONSE; /* Response must be at least long enough for a status line & final CRLF */ - if (rlrBuff.rlrBuffCount < 8+1+3+1+2+2) + if (u.rlrBuff.rlrBuffCount < 8+1+3+1+2+2) goto errorReturn; - HLock(rlrBuff.rlrBuffHandle); + HLock(u.rlrBuff.rlrBuffHandle); - char *response = *rlrBuff.rlrBuffHandle; - char *responseEnd = response + rlrBuff.rlrBuffCount; + char *response = *u.rlrBuff.rlrBuffHandle; + char *responseEnd = response + u.rlrBuff.rlrBuffCount; /* Make response a C-string. Specifically, it will end "CR LF NUL NUL". */ - response[rlrBuff.rlrBuffCount - 2] = '\0'; - response[rlrBuff.rlrBuffCount - 1] = '\0'; + response[u.rlrBuff.rlrBuffCount - 2] = '\0'; + response[u.rlrBuff.rlrBuffCount - 1] = '\0'; /* Parse status line of HTTP response */ char *endPtr; @@ -335,7 +349,7 @@ netRetry: /* Wanted redirect: Retry with new location if we got it. */ if (wantRedirect) { if (gotRedirect) { - DisposeHandle(rlrBuff.rlrBuffHandle); + DisposeHandle(u.rlrBuff.rlrBuffHandle); goto top; } else { result = UNSUPPORTED_RESPONSE; @@ -359,12 +373,12 @@ netRetry: goto errorReturn; result = OPERATION_SUCCESSFUL; - DisposeHandle(rlrBuff.rlrBuffHandle); + DisposeHandle(u.rlrBuff.rlrBuffHandle); return result; errorReturn: - if (rlrBuff.rlrBuffHandle != NULL) { - DisposeHandle(rlrBuff.rlrBuffHandle); + if (u.rlrBuff.rlrBuffHandle != NULL) { + DisposeHandle(u.rlrBuff.rlrBuffHandle); } /* Error condition on this TCP connection means it can't be reused. */ diff --git a/tcpconnection.c b/tcpconnection.c index 32ea2b8..33f7b85 100644 --- a/tcpconnection.c +++ b/tcpconnection.c @@ -1,8 +1,5 @@ #pragma noroot -#define NETWORK_ERR 1 -#define NO_RESP_ERR 2 - #include #include #include @@ -57,6 +54,7 @@ void EndTCPConnection(Session *sess) { TCPIPPoll(); TCPIPAbortTCP(sess->ipid); TCPIPLogout(sess->ipid); + sess->ipid = 0; sess->tcpLoggedIn = FALSE; } }