1.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000 1.2 +++ b/netwerk/protocol/data/nsDataChannel.cpp Wed Dec 31 06:09:35 2014 +0100 1.3 @@ -0,0 +1,89 @@ 1.4 +/* -*- Mode: C++; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 4 -*- */ 1.5 +/* This Source Code Form is subject to the terms of the Mozilla Public 1.6 + * License, v. 2.0. If a copy of the MPL was not distributed with this 1.7 + * file, You can obtain one at http://mozilla.org/MPL/2.0/. */ 1.8 + 1.9 +// data implementation 1.10 + 1.11 +#include "nsDataChannel.h" 1.12 + 1.13 +#include "mozilla/Base64.h" 1.14 +#include "nsIOService.h" 1.15 +#include "nsDataHandler.h" 1.16 +#include "nsIPipe.h" 1.17 +#include "nsIInputStream.h" 1.18 +#include "nsIOutputStream.h" 1.19 +#include "nsEscape.h" 1.20 + 1.21 +using namespace mozilla; 1.22 + 1.23 +nsresult 1.24 +nsDataChannel::OpenContentStream(bool async, nsIInputStream **result, 1.25 + nsIChannel** channel) 1.26 +{ 1.27 + NS_ENSURE_TRUE(URI(), NS_ERROR_NOT_INITIALIZED); 1.28 + 1.29 + nsresult rv; 1.30 + 1.31 + nsAutoCString spec; 1.32 + rv = URI()->GetAsciiSpec(spec); 1.33 + if (NS_FAILED(rv)) return rv; 1.34 + 1.35 + nsCString contentType, contentCharset, dataBuffer, hashRef; 1.36 + bool lBase64; 1.37 + rv = nsDataHandler::ParseURI(spec, contentType, contentCharset, 1.38 + lBase64, dataBuffer, hashRef); 1.39 + 1.40 + NS_UnescapeURL(dataBuffer); 1.41 + 1.42 + if (lBase64) { 1.43 + // Don't allow spaces in base64-encoded content. This is only 1.44 + // relevant for escaped spaces; other spaces are stripped in 1.45 + // NewURI. 1.46 + dataBuffer.StripWhitespace(); 1.47 + } 1.48 + 1.49 + nsCOMPtr<nsIInputStream> bufInStream; 1.50 + nsCOMPtr<nsIOutputStream> bufOutStream; 1.51 + 1.52 + // create an unbounded pipe. 1.53 + rv = NS_NewPipe(getter_AddRefs(bufInStream), 1.54 + getter_AddRefs(bufOutStream), 1.55 + nsIOService::gDefaultSegmentSize, 1.56 + UINT32_MAX, 1.57 + async, true); 1.58 + if (NS_FAILED(rv)) 1.59 + return rv; 1.60 + 1.61 + uint32_t contentLen; 1.62 + if (lBase64) { 1.63 + const uint32_t dataLen = dataBuffer.Length(); 1.64 + int32_t resultLen = 0; 1.65 + if (dataLen >= 1 && dataBuffer[dataLen-1] == '=') { 1.66 + if (dataLen >= 2 && dataBuffer[dataLen-2] == '=') 1.67 + resultLen = dataLen-2; 1.68 + else 1.69 + resultLen = dataLen-1; 1.70 + } else { 1.71 + resultLen = dataLen; 1.72 + } 1.73 + resultLen = ((resultLen * 3) / 4); 1.74 + 1.75 + nsAutoCString decodedData; 1.76 + rv = Base64Decode(dataBuffer, decodedData); 1.77 + NS_ENSURE_SUCCESS(rv, rv); 1.78 + rv = bufOutStream->Write(decodedData.get(), resultLen, &contentLen); 1.79 + } else { 1.80 + rv = bufOutStream->Write(dataBuffer.get(), dataBuffer.Length(), &contentLen); 1.81 + } 1.82 + if (NS_FAILED(rv)) 1.83 + return rv; 1.84 + 1.85 + SetContentType(contentType); 1.86 + SetContentCharset(contentCharset); 1.87 + mContentLength = contentLen; 1.88 + 1.89 + NS_ADDREF(*result = bufInStream); 1.90 + 1.91 + return NS_OK; 1.92 +}