netwerk/base/src/nsDownloader.cpp

Wed, 31 Dec 2014 06:09:35 +0100

author
Michael Schloh von Bennewitz <michael@schloh.com>
date
Wed, 31 Dec 2014 06:09:35 +0100
changeset 0
6474c204b198
permissions
-rw-r--r--

Cloned upstream origin tor-browser at tor-browser-31.3.0esr-4.5-1-build1
revision ID fc1c9ff7c1b2defdbc039f12214767608f46423f for hacking purpose.

     1 /* This Source Code Form is subject to the terms of the Mozilla Public
     2  * License, v. 2.0. If a copy of the MPL was not distributed with this
     3  * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
     5 #include "nsDownloader.h"
     6 #include "nsIInputStream.h"
     7 #include "nsDirectoryServiceUtils.h"
     8 #include "nsDirectoryServiceDefs.h"
     9 #include "nsNetUtil.h"
    10 #include "nsCRTGlue.h"
    12 nsDownloader::~nsDownloader()
    13 {
    14     if (mLocation && mLocationIsTemp) {
    15         // release the sink first since it may still hold an open file
    16         // descriptor to mLocation.  this needs to happen before the
    17         // file can be removed otherwise the Remove call will fail.
    18         if (mSink) {
    19             mSink->Close();
    20             mSink = nullptr;
    21         }
    23         nsresult rv = mLocation->Remove(false);
    24         if (NS_FAILED(rv))
    25             NS_ERROR("unable to remove temp file");
    26     }
    27 }
    29 NS_IMPL_ISUPPORTS(nsDownloader,
    30                   nsIDownloader,
    31                   nsIStreamListener,
    32                   nsIRequestObserver)
    34 NS_IMETHODIMP
    35 nsDownloader::Init(nsIDownloadObserver *observer, nsIFile *location)
    36 {
    37     mObserver = observer;
    38     mLocation = location;
    39     return NS_OK;
    40 }
    42 NS_IMETHODIMP 
    43 nsDownloader::OnStartRequest(nsIRequest *request, nsISupports *ctxt)
    44 {
    45     nsresult rv;
    46     if (!mLocation) {
    47         nsCOMPtr<nsIFile> location;
    48         rv = NS_GetSpecialDirectory(NS_OS_TEMP_DIR, getter_AddRefs(location));
    49         if (NS_FAILED(rv)) return rv;
    51         char buf[13];
    52         NS_MakeRandomString(buf, 8);
    53         memcpy(buf+8, ".tmp", 5);
    54         rv = location->AppendNative(nsDependentCString(buf, 12));
    55         if (NS_FAILED(rv)) return rv;
    57         rv = location->CreateUnique(nsIFile::NORMAL_FILE_TYPE, 0600);
    58         if (NS_FAILED(rv)) return rv;
    60         location.swap(mLocation);
    61         mLocationIsTemp = true;
    62     }
    64     rv = NS_NewLocalFileOutputStream(getter_AddRefs(mSink), mLocation);
    65     if (NS_FAILED(rv)) return rv;
    67     // we could wrap this output stream with a buffered output stream,
    68     // but it shouldn't be necessary since we will be writing large
    69     // chunks given to us via OnDataAvailable.
    71     return NS_OK;
    72 }
    74 NS_IMETHODIMP 
    75 nsDownloader::OnStopRequest(nsIRequest  *request,
    76                             nsISupports *ctxt,
    77                             nsresult     status)
    78 {
    79     if (mSink) {
    80         mSink->Close();
    81         mSink = nullptr;
    82     }
    84     mObserver->OnDownloadComplete(this, request, ctxt, status, mLocation);
    85     mObserver = nullptr;
    87     return NS_OK;
    88 }
    90 NS_METHOD
    91 nsDownloader::ConsumeData(nsIInputStream* in,
    92                           void* closure,
    93                           const char* fromRawSegment,
    94                           uint32_t toOffset,
    95                           uint32_t count,
    96                           uint32_t *writeCount)
    97 {
    98     nsDownloader *self = (nsDownloader *) closure;
    99     if (self->mSink)
   100         return self->mSink->Write(fromRawSegment, count, writeCount);
   102     *writeCount = count;
   103     return NS_OK;
   104 }
   106 NS_IMETHODIMP 
   107 nsDownloader::OnDataAvailable(nsIRequest *request, nsISupports *ctxt, 
   108                               nsIInputStream *inStr, 
   109                               uint64_t sourceOffset, uint32_t count)
   110 {
   111     uint32_t n;  
   112     return inStr->ReadSegments(ConsumeData, this, count, &n);
   113 }

mercurial