Tue, 06 Jan 2015 21:39:09 +0100
Conditionally force memory storage according to privacy.thirdparty.isolate;
This solves Tor bug #9701, complying with disk avoidance documented in
https://www.torproject.org/projects/torbrowser/design/#disk-avoidance.
1 /* -*- Mode: C++; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
2 /* This Source Code Form is subject to the terms of the Mozilla Public
3 * License, v. 2.0. If a copy of the MPL was not distributed with this
4 * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
6 #include "gfxCrashReporterUtils.h"
8 #if defined(MOZ_CRASHREPORTER)
9 #define MOZ_GFXFEATUREREPORTER 1
10 #endif
12 #ifdef MOZ_GFXFEATUREREPORTER
13 #include "gfxCrashReporterUtils.h"
14 #include <string.h> // for strcmp
15 #include "mozilla/Assertions.h" // for MOZ_ASSERT_HELPER2
16 #include "mozilla/Services.h" // for GetObserverService
17 #include "mozilla/mozalloc.h" // for operator new, etc
18 #include "nsAutoPtr.h" // for nsRefPtr
19 #include "nsCOMPtr.h" // for nsCOMPtr
20 #include "nsError.h" // for NS_OK, NS_FAILED, nsresult
21 #include "nsExceptionHandler.h" // for AppendAppNotesToCrashReport
22 #include "nsID.h"
23 #include "nsIEventTarget.h" // for NS_DISPATCH_NORMAL
24 #include "nsIObserver.h" // for nsIObserver, etc
25 #include "nsIObserverService.h" // for nsIObserverService
26 #include "nsIRunnable.h" // for nsIRunnable
27 #include "nsISupports.h"
28 #include "nsString.h" // for nsAutoCString, nsCString, etc
29 #include "nsTArray.h" // for nsTArray
30 #include "nsThreadUtils.h" // for NS_DispatchToMainThread, etc
31 #include "nscore.h" // for NS_IMETHOD, NS_IMETHODIMP, etc
33 namespace mozilla {
35 static nsTArray<nsCString> *gFeaturesAlreadyReported = nullptr;
37 class ObserverToDestroyFeaturesAlreadyReported : public nsIObserver
38 {
40 public:
41 NS_DECL_ISUPPORTS
42 NS_DECL_NSIOBSERVER
44 ObserverToDestroyFeaturesAlreadyReported() {}
45 virtual ~ObserverToDestroyFeaturesAlreadyReported() {}
46 };
48 NS_IMPL_ISUPPORTS(ObserverToDestroyFeaturesAlreadyReported,
49 nsIObserver)
51 NS_IMETHODIMP
52 ObserverToDestroyFeaturesAlreadyReported::Observe(nsISupports* aSubject,
53 const char* aTopic,
54 const char16_t* aData)
55 {
56 if (!strcmp(aTopic, "xpcom-shutdown")) {
57 if (gFeaturesAlreadyReported) {
58 delete gFeaturesAlreadyReported;
59 gFeaturesAlreadyReported = nullptr;
60 }
61 }
62 return NS_OK;
63 }
65 class ScopedGfxFeatureReporter::AppNoteWritingRunnable : public nsRunnable {
66 public:
67 AppNoteWritingRunnable(char aStatusChar, const char *aFeature) :
68 mStatusChar(aStatusChar), mFeature(aFeature) {}
69 NS_IMETHOD Run() {
70 // LeakLog made me do this. Basically, I just wanted gFeaturesAlreadyReported to be a static nsTArray<nsCString>,
71 // and LeakLog was complaining about leaks like this:
72 // leaked 1 instance of nsTArray_base with size 8 bytes
73 // leaked 7 instances of nsStringBuffer with size 8 bytes each (56 bytes total)
74 // So this is a work-around using a pointer, and using a nsIObserver to deallocate on xpcom shutdown.
75 // Yay for fighting bloat.
76 if (!gFeaturesAlreadyReported) {
77 nsCOMPtr<nsIObserverService> observerService = mozilla::services::GetObserverService();
78 if (!observerService)
79 return NS_OK;
80 nsRefPtr<ObserverToDestroyFeaturesAlreadyReported> observer = new ObserverToDestroyFeaturesAlreadyReported;
81 nsresult rv = observerService->AddObserver(observer, "xpcom-shutdown", false);
82 if (NS_FAILED(rv)) {
83 observer = nullptr;
84 return NS_OK;
85 }
86 gFeaturesAlreadyReported = new nsTArray<nsCString>;
87 }
89 nsAutoCString featureString;
90 featureString.AppendPrintf("%s%c ",
91 mFeature,
92 mStatusChar);
94 if (!gFeaturesAlreadyReported->Contains(featureString)) {
95 gFeaturesAlreadyReported->AppendElement(featureString);
96 CrashReporter::AppendAppNotesToCrashReport(featureString);
97 }
98 return NS_OK;
99 }
100 private:
101 char mStatusChar;
102 const char *mFeature;
103 };
105 void
106 ScopedGfxFeatureReporter::WriteAppNote(char statusChar)
107 {
108 nsCOMPtr<nsIRunnable> r = new AppNoteWritingRunnable(statusChar, mFeature);
109 NS_DispatchToMainThread(r.get(), NS_DISPATCH_NORMAL);
110 }
112 } // end namespace mozilla
114 #else
116 namespace mozilla {
117 void ScopedGfxFeatureReporter::WriteAppNote(char) {}
118 }
120 #endif