From e781f233038ba39d93e47bc5239b39145a43c7b5 Mon Sep 17 00:00:00 2001 From: "ruslan%netscape.com" Date: Wed, 17 May 2000 00:11:12 +0000 Subject: [PATCH] Fix 18886 - handle http 305 response correctly to close the potential security hole --- netwerk/protocol/http/src/nsHTTPChannel.cpp | 66 +++++++++++++++------ netwerk/protocol/http/src/nsHTTPChannel.h | 4 +- 2 files changed, 51 insertions(+), 19 deletions(-) diff --git a/netwerk/protocol/http/src/nsHTTPChannel.cpp b/netwerk/protocol/http/src/nsHTTPChannel.cpp index a9c7524ca32..1158e25946f 100644 --- a/netwerk/protocol/http/src/nsHTTPChannel.cpp +++ b/netwerk/protocol/http/src/nsHTTPChannel.cpp @@ -1431,13 +1431,16 @@ nsresult nsHTTPChannel::ReportProgress(PRUint32 aProgress, nsresult nsHTTPChannel::Redirect(const char *aNewLocation, - nsIChannel **aResult) + nsIChannel **aResult, PRInt32 aStatusCode) { nsresult rv; nsCOMPtr newURI; nsCOMPtr channel; PRBool checkSecurity = PR_TRUE; + nsXPIDLCString proxyHost; + PRInt32 proxyPort; + *aResult = nsnull; // @@ -1446,22 +1449,42 @@ nsresult nsHTTPChannel::Redirect(const char *aNewLocation, // NS_WITH_SERVICE(nsIIOService, serv, kIOServiceCID, &rv); if (NS_FAILED(rv)) return rv; - - rv = serv->NewURI(aNewLocation, mURI, getter_AddRefs(newURI)); - if (NS_FAILED(rv)) return rv; - - PRBool eq = PR_FALSE; - rv = mURI->Equals(newURI, &eq); - - if (eq) + + if (aStatusCode == 305) // Use-Proxy { - // loop detected - // ruslan/24884 - rv = serv->NewURI(LOOPING_REDIRECT_ERROR_URI, mURI, getter_AddRefs(newURI)); - if (NS_FAILED(rv)) return rv; - - checkSecurity = PR_FALSE; + newURI = mURI; + + nsCOMPtr tmpURI; + rv = serv->NewURI(aNewLocation, mURI, getter_AddRefs(tmpURI)); + + if (NS_FAILED(rv)) + return rv; + + tmpURI -> GetHost (getter_Copies (proxyHost)); + tmpURI -> GetPort (&proxyPort); + + if (proxyPort == -1) + proxyPort = 80; } + else + { + rv = serv->NewURI(aNewLocation, mURI, getter_AddRefs(newURI)); + if (NS_FAILED(rv)) return rv; + + PRBool eq = PR_FALSE; + rv = mURI->Equals(newURI, &eq); + + if (eq) + { + // loop detected + // ruslan/24884 + rv = serv->NewURI(LOOPING_REDIRECT_ERROR_URI, mURI, getter_AddRefs(newURI)); + if (NS_FAILED(rv)) return rv; + + checkSecurity = PR_FALSE; + } + } + // // Move the Reference of the old location to the new one @@ -1525,6 +1548,7 @@ nsresult nsHTTPChannel::Redirect(const char *aNewLocation, // Convey the referrer if one was used for this channel to the next one- nsXPIDLCString referrer; GetRequestHeader(nsHTTPAtoms::Referer, getter_Copies(referrer)); + if (referrer && *referrer) { nsCOMPtr httpChannel = do_QueryInterface(channel); @@ -1532,6 +1556,14 @@ nsresult nsHTTPChannel::Redirect(const char *aNewLocation, httpChannel->SetRequestHeader(nsHTTPAtoms::Referer, referrer); } + if (aStatusCode == 305) // Use Proxy + { + nsCOMPtr httpProxy = do_QueryInterface(channel); + + httpProxy -> SetProxyHost (proxyHost); + httpProxy -> SetProxyPort (proxyPort); + } + // Start the redirect... nsIStreamListener *sl = mResponseDataListener; nsHTTPFinalListener *fl = NS_STATIC_CAST (nsHTTPFinalListener*, sl); @@ -2125,11 +2157,11 @@ nsHTTPChannel::ProcessRedirection(PRInt32 aStatusCode) mResponse->GetHeader(nsHTTPAtoms::Location, getter_Copies(location)); - if (((301 == aStatusCode) || (302 == aStatusCode)) && (location)) + if (((301 == aStatusCode) || (302 == aStatusCode) || (aStatusCode == 305)) && (location)) { nsCOMPtr channel; - rv = Redirect(location, getter_AddRefs(channel)); + rv = Redirect(location, getter_AddRefs(channel), aStatusCode); if (NS_FAILED(rv)) return rv; // Abort the current response... This will disconnect the consumer from diff --git a/netwerk/protocol/http/src/nsHTTPChannel.h b/netwerk/protocol/http/src/nsHTTPChannel.h index 8bb6c6d84f1..7a9b7b88c13 100644 --- a/netwerk/protocol/http/src/nsHTTPChannel.h +++ b/netwerk/protocol/http/src/nsHTTPChannel.h @@ -47,7 +47,7 @@ class nsHTTPRequest; class nsHTTPResponse; class nsICachedNetData; -#define LOOPING_REDIRECT_ERROR_URI "chrome://necko/content/redirect_loop.xul" +#define LOOPING_REDIRECT_ERROR_URI "chrome://packages/core/necko/content/redirect_loop.xul" // Utility functions- TODO share from nsURLHelpers... nsresult @@ -90,7 +90,7 @@ public: nsresult Init(); nsresult Open(PRBool bIgnoreCache=PR_FALSE); nsresult Redirect(const char *aURL, - nsIChannel **aResult); + nsIChannel **aResult, PRInt32 aStatusCode); nsresult ResponseCompleted(nsIStreamListener *aListener, nsresult aStatus,