LCOV - code coverage report
Current view: top level - dom/file - MemoryBlobImpl.cpp (source / functions) Hit Total Coverage
Test: output.info Lines: 2 70 2.9 %
Date: 2017-07-14 16:53:18 Functions: 0 17 0.0 %
Legend: Lines: hit not hit

          Line data    Source code
       1             : /* -*- Mode: C++; tab-width: 8; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
       2             : /* vim: set ts=8 sts=2 et sw=2 tw=80: */
       3             : /* This Source Code Form is subject to the terms of the Mozilla Public
       4             :  * License, v. 2.0. If a copy of the MPL was not distributed with this
       5             :  * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
       6             : 
       7             : #include "MemoryBlobImpl.h"
       8             : #include "mozilla/IntegerPrintfMacros.h"
       9             : #include "mozilla/SHA1.h"
      10             : #include "nsPrintfCString.h"
      11             : 
      12             : namespace mozilla {
      13             : namespace dom {
      14             : 
      15           0 : NS_IMPL_ADDREF(MemoryBlobImpl::DataOwnerAdapter)
      16           0 : NS_IMPL_RELEASE(MemoryBlobImpl::DataOwnerAdapter)
      17             : 
      18           0 : NS_INTERFACE_MAP_BEGIN(MemoryBlobImpl::DataOwnerAdapter)
      19           0 :   NS_INTERFACE_MAP_ENTRY(nsIInputStream)
      20           0 :   NS_INTERFACE_MAP_ENTRY(nsISeekableStream)
      21           0 :   NS_INTERFACE_MAP_ENTRY(nsICloneableInputStream)
      22           0 :   NS_INTERFACE_MAP_ENTRY_CONDITIONAL(nsIIPCSerializableInputStream,
      23             :                                      mSerializableInputStream)
      24           0 :   NS_INTERFACE_MAP_ENTRY_AMBIGUOUS(nsISupports, nsIInputStream)
      25           0 : NS_INTERFACE_MAP_END
      26             : 
      27           0 : nsresult MemoryBlobImpl::DataOwnerAdapter::Create(DataOwner* aDataOwner,
      28             :                                                   uint32_t aStart,
      29             :                                                   uint32_t aLength,
      30             :                                                   nsIInputStream** _retval)
      31             : {
      32             :   nsresult rv;
      33           0 :   MOZ_ASSERT(aDataOwner, "Uh ...");
      34             : 
      35           0 :   nsCOMPtr<nsIInputStream> stream;
      36             : 
      37           0 :   rv = NS_NewByteInputStream(getter_AddRefs(stream),
      38           0 :                              static_cast<const char*>(aDataOwner->mData) +
      39             :                              aStart,
      40             :                              (int32_t)aLength,
      41           0 :                              NS_ASSIGNMENT_DEPEND);
      42           0 :   NS_ENSURE_SUCCESS(rv, rv);
      43             : 
      44           0 :   NS_ADDREF(*_retval =
      45           0 :               new MemoryBlobImpl::DataOwnerAdapter(aDataOwner, stream));
      46             : 
      47           0 :   return NS_OK;
      48             : }
      49             : 
      50           0 : NS_IMPL_ISUPPORTS_INHERITED0(MemoryBlobImpl, BlobImpl)
      51             : 
      52             : already_AddRefed<BlobImpl>
      53           0 : MemoryBlobImpl::CreateSlice(uint64_t aStart, uint64_t aLength,
      54             :                             const nsAString& aContentType,
      55             :                             ErrorResult& aRv)
      56             : {
      57             :   RefPtr<BlobImpl> impl =
      58           0 :     new MemoryBlobImpl(this, aStart, aLength, aContentType);
      59           0 :   return impl.forget();
      60             : }
      61             : 
      62             : void
      63           0 : MemoryBlobImpl::GetInternalStream(nsIInputStream** aStream, ErrorResult& aRv)
      64             : {
      65           0 :   if (mLength > INT32_MAX) {
      66           0 :     aRv.Throw(NS_ERROR_FAILURE);
      67           0 :     return;
      68             :   }
      69             : 
      70           0 :   aRv = MemoryBlobImpl::DataOwnerAdapter::Create(mDataOwner, mStart, mLength,
      71           0 :                                                  aStream);
      72             : }
      73             : 
      74             : /* static */ StaticMutex
      75           3 : MemoryBlobImpl::DataOwner::sDataOwnerMutex;
      76             : 
      77             : /* static */ StaticAutoPtr<LinkedList<MemoryBlobImpl::DataOwner>>
      78           3 : MemoryBlobImpl::DataOwner::sDataOwners;
      79             : 
      80             : /* static */ bool
      81             : MemoryBlobImpl::DataOwner::sMemoryReporterRegistered = false;
      82             : 
      83           0 : MOZ_DEFINE_MALLOC_SIZE_OF(MemoryFileDataOwnerMallocSizeOf)
      84             : 
      85           0 : class MemoryBlobImplDataOwnerMemoryReporter final
      86             :   : public nsIMemoryReporter
      87             : {
      88           0 :   ~MemoryBlobImplDataOwnerMemoryReporter() {}
      89             : 
      90             : public:
      91             :   NS_DECL_THREADSAFE_ISUPPORTS
      92             : 
      93           0 :   NS_IMETHOD CollectReports(nsIHandleReportCallback* aHandleReport,
      94             :                             nsISupports* aData, bool aAnonymize) override
      95             :   {
      96             :     typedef MemoryBlobImpl::DataOwner DataOwner;
      97             : 
      98           0 :     StaticMutexAutoLock lock(DataOwner::sDataOwnerMutex);
      99             : 
     100           0 :     if (!DataOwner::sDataOwners) {
     101           0 :       return NS_OK;
     102             :     }
     103             : 
     104           0 :     const size_t LARGE_OBJECT_MIN_SIZE = 8 * 1024;
     105           0 :     size_t smallObjectsTotal = 0;
     106             : 
     107           0 :     for (DataOwner *owner = DataOwner::sDataOwners->getFirst();
     108           0 :          owner; owner = owner->getNext()) {
     109             : 
     110           0 :       size_t size = MemoryFileDataOwnerMallocSizeOf(owner->mData);
     111             : 
     112           0 :       if (size < LARGE_OBJECT_MIN_SIZE) {
     113           0 :         smallObjectsTotal += size;
     114             :       } else {
     115           0 :         SHA1Sum sha1;
     116           0 :         sha1.update(owner->mData, owner->mLength);
     117             :         uint8_t digest[SHA1Sum::kHashSize]; // SHA1 digests are 20 bytes long.
     118           0 :         sha1.finish(digest);
     119             : 
     120           0 :         nsAutoCString digestString;
     121           0 :         for (size_t i = 0; i < sizeof(digest); i++) {
     122           0 :           digestString.AppendPrintf("%02x", digest[i]);
     123             :         }
     124             : 
     125           0 :         aHandleReport->Callback(
     126           0 :           /* process */ NS_LITERAL_CSTRING(""),
     127           0 :           nsPrintfCString(
     128             :             "explicit/dom/memory-file-data/large/file(length=%" PRIu64 ", sha1=%s)",
     129             :             owner->mLength, aAnonymize ? "<anonymized>" : digestString.get()),
     130             :           KIND_HEAP, UNITS_BYTES, size,
     131           0 :           nsPrintfCString(
     132             :             "Memory used to back a memory file of length %" PRIu64 " bytes.  The file "
     133             :             "has a sha1 of %s.\n\n"
     134             :             "Note that the allocator may round up a memory file's length -- "
     135             :             "that is, an N-byte memory file may take up more than N bytes of "
     136             :             "memory.",
     137             :             owner->mLength, digestString.get()),
     138           0 :           aData);
     139             :       }
     140             :     }
     141             : 
     142           0 :     if (smallObjectsTotal > 0) {
     143           0 :       aHandleReport->Callback(
     144           0 :         /* process */ NS_LITERAL_CSTRING(""),
     145           0 :         NS_LITERAL_CSTRING("explicit/dom/memory-file-data/small"),
     146             :         KIND_HEAP, UNITS_BYTES, smallObjectsTotal,
     147           0 :         nsPrintfCString(
     148             :           "Memory used to back small memory files (i.e. those taking up less "
     149             :           "than %zu bytes of memory each).\n\n"
     150             :           "Note that the allocator may round up a memory file's length -- "
     151             :           "that is, an N-byte memory file may take up more than N bytes of "
     152             :           "memory.", LARGE_OBJECT_MIN_SIZE),
     153           0 :         aData);
     154             :     }
     155             : 
     156           0 :     return NS_OK;
     157             :   }
     158             : };
     159             : 
     160           0 : NS_IMPL_ISUPPORTS(MemoryBlobImplDataOwnerMemoryReporter, nsIMemoryReporter)
     161             : 
     162             : /* static */ void
     163           0 : MemoryBlobImpl::DataOwner::EnsureMemoryReporterRegistered()
     164             : {
     165           0 :   sDataOwnerMutex.AssertCurrentThreadOwns();
     166           0 :   if (sMemoryReporterRegistered) {
     167           0 :     return;
     168             :   }
     169             : 
     170           0 :   RegisterStrongMemoryReporter(new MemoryBlobImplDataOwnerMemoryReporter());
     171             : 
     172           0 :   sMemoryReporterRegistered = true;
     173             : }
     174             : 
     175             : } // namespace dom
     176             : } // namespace mozilla

Generated by: LCOV version 1.13