tor-browser

The Tor Browser
git clone https://git.dasho.dev/tor-browser.git
Log | Files | Refs | README | LICENSE

CacheFileUtils.h (6914B)


      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/. */
      4 
      5 #ifndef CacheFileUtils__h__
      6 #define CacheFileUtils__h__
      7 
      8 #include "nsError.h"
      9 #include "nsCOMPtr.h"
     10 #include "nsString.h"
     11 #include "nsTArray.h"
     12 #include "mozilla/Mutex.h"
     13 #include "mozilla/StaticMutex.h"
     14 #include "mozilla/TimeStamp.h"
     15 
     16 class nsILoadContextInfo;
     17 
     18 namespace mozilla {
     19 namespace net {
     20 namespace CacheFileUtils {
     21 
     22 extern const char* kAltDataKey;
     23 
     24 already_AddRefed<nsILoadContextInfo> ParseKey(const nsACString& aKey,
     25                                              nsACString* aIdEnhance = nullptr,
     26                                              nsACString* aURISpec = nullptr);
     27 
     28 void AppendKeyPrefix(nsILoadContextInfo* aInfo, nsACString& _retval);
     29 
     30 void AppendTagWithValue(nsACString& aTarget, char const aTag,
     31                        const nsACString& aValue);
     32 
     33 nsresult KeyMatchesLoadContextInfo(const nsACString& aKey,
     34                                   nsILoadContextInfo* aInfo, bool* _retval);
     35 
     36 class ValidityPair {
     37 public:
     38  ValidityPair(uint32_t aOffset, uint32_t aLen);
     39 
     40  ValidityPair& operator=(const ValidityPair& aOther) = default;
     41 
     42  // Returns true when two pairs can be merged, i.e. they do overlap or the one
     43  // ends exactly where the other begins.
     44  bool CanBeMerged(const ValidityPair& aOther) const;
     45 
     46  // Returns true when aOffset is placed anywhere in the validity interval or
     47  // exactly after its end.
     48  bool IsInOrFollows(uint32_t aOffset) const;
     49 
     50  // Returns true when this pair has lower offset than the other pair. In case
     51  // both pairs have the same offset it returns true when this pair has a
     52  // shorter length.
     53  bool LessThan(const ValidityPair& aOther) const;
     54 
     55  // Merges two pair into one.
     56  void Merge(const ValidityPair& aOther);
     57 
     58  uint32_t Offset() const { return mOffset; }
     59  uint32_t Len() const { return mLen; }
     60 
     61 private:
     62  uint32_t mOffset;
     63  uint32_t mLen;
     64 };
     65 
     66 class ValidityMap {
     67 public:
     68  // Prints pairs in the map into log.
     69  void Log() const;
     70 
     71  // Returns number of pairs in the map.
     72  uint32_t Length() const;
     73 
     74  // Adds a new pair to the map. It keeps the pairs ordered and merges pairs
     75  // when possible.
     76  void AddPair(uint32_t aOffset, uint32_t aLen);
     77 
     78  // Removes all pairs from the map.
     79  void Clear();
     80 
     81  size_t SizeOfExcludingThis(mozilla::MallocSizeOf mallocSizeOf) const;
     82 
     83  ValidityPair& operator[](uint32_t aIdx);
     84 
     85 private:
     86  nsTArray<ValidityPair> mMap;
     87 };
     88 
     89 class DetailedCacheHitTelemetry {
     90 public:
     91  enum ERecType { HIT = 0, MISS = 1 };
     92 
     93  static void AddRecord(ERecType aType, TimeStamp aLoadStart);
     94 
     95 private:
     96  class HitRate {
     97   public:
     98    HitRate();
     99 
    100    void AddRecord(ERecType aType);
    101    uint32_t GetHitRateBucket() const;
    102    uint32_t Count();
    103    void Reset();
    104 
    105   private:
    106    uint32_t mHitCnt = 0;
    107    uint32_t mMissCnt = 0;
    108  };
    109 
    110  // Group the hits and misses statistics by cache files count ranges (0-5000,
    111  // 5001-10000, ... , 95001- )
    112  static const uint32_t kRangeSize = 5000;
    113  static const uint32_t kNumOfRanges = 20;
    114  static const uint32_t kPercentageRange = 5;
    115  static const uint32_t kMaxPercentage = 100;
    116 
    117  // Use the same ranges to report an average hit rate. Report the hit rates
    118  // (and reset the counters) every kTotalSamplesReportLimit samples.
    119  static const uint32_t kTotalSamplesReportLimit = 1000;
    120 
    121  // Report hit rate for a given cache size range only if it contains
    122  // kHitRateSamplesReportLimit or more samples. This limit should avoid
    123  // reporting a biased statistics.
    124  static const uint32_t kHitRateSamplesReportLimit = 500;
    125 
    126  // All hit rates are accumulated in a single telemetry probe, so to use
    127  // a sane number of enumerated values the hit rate is divided into buckets
    128  // instead of using a percent value. This constant defines number of buckets
    129  // that we divide the hit rates into. I.e. we'll report ranges 0%-5%, 5%-10%,
    130  // 10-%15%, ...
    131  static const uint32_t kHitRateBuckets = 20;
    132 
    133  // Protects sRecordCnt, sHRStats and Telemetry::Accumulated() calls.
    134  static StaticMutex sLock;
    135 
    136  // Counter of samples that is compared against kTotalSamplesReportLimit.
    137  static uint32_t sRecordCnt MOZ_GUARDED_BY(sLock);
    138 
    139  // Hit rate statistics for every cache size range.
    140  static HitRate sHRStats[kNumOfRanges] MOZ_GUARDED_BY(sLock);
    141 };
    142 
    143 class CachePerfStats {
    144 public:
    145  // perfStatTypes in displayRcwnStats() in toolkit/content/aboutNetworking.js
    146  // must match EDataType
    147  enum EDataType {
    148    IO_OPEN = 0,
    149    IO_READ = 1,
    150    IO_WRITE = 2,
    151    ENTRY_OPEN = 3,
    152    LAST = 4
    153  };
    154 
    155  static void AddValue(EDataType aType, uint32_t aValue, bool aShortOnly);
    156  static uint32_t GetAverage(EDataType aType, bool aFiltered);
    157  static uint32_t GetStdDev(EDataType aType, bool aFiltered);
    158  static bool IsCacheSlow();
    159  static void GetSlowStats(uint32_t* aSlow, uint32_t* aNotSlow);
    160 
    161 private:
    162  // This class computes average and standard deviation, it returns an
    163  // arithmetic avg and stddev until total number of values reaches mWeight.
    164  // Then it returns modified moving average computed as follows:
    165  //
    166  //   avg = (1-a)*avg + a*value
    167  //   avgsq = (1-a)*avgsq + a*value^2
    168  //   stddev = sqrt(avgsq - avg^2)
    169  //
    170  //   where
    171  //       avgsq is an average of the square of the values
    172  //       a = 1 / weight
    173  class MMA {
    174   public:
    175    MMA(uint32_t aTotalWeight, bool aFilter);
    176 
    177    void AddValue(uint32_t aValue);
    178    uint32_t GetAverage();
    179    uint32_t GetStdDev();
    180 
    181   private:
    182    uint64_t mSum;
    183    uint64_t mSumSq;
    184    uint32_t mCnt;
    185    uint32_t mWeight;
    186    bool mFilter;
    187  };
    188 
    189  class PerfData {
    190   public:
    191    PerfData();
    192 
    193    void AddValue(uint32_t aValue, bool aShortOnly);
    194    uint32_t GetAverage(bool aFiltered);
    195    uint32_t GetStdDev(bool aFiltered);
    196 
    197   private:
    198    // Contains filtered data (i.e. times when we think the cache and disk was
    199    // not busy) for a longer time.
    200    MMA mFilteredAvg;
    201 
    202    // Contains unfiltered average of few recent values.
    203    MMA mShortAvg;
    204  };
    205 
    206  static StaticMutex sLock;
    207 
    208  static PerfData sData[LAST] MOZ_GUARDED_BY(sLock);
    209  static uint32_t sCacheSlowCnt MOZ_GUARDED_BY(sLock);
    210  static uint32_t sCacheNotSlowCnt MOZ_GUARDED_BY(sLock);
    211 };
    212 
    213 void FreeBuffer(void* aBuf);
    214 
    215 nsresult ParseAlternativeDataInfo(const char* aInfo, int64_t* _offset,
    216                                  nsACString* _type);
    217 
    218 void BuildAlternativeDataInfo(const char* aInfo, int64_t aOffset,
    219                              nsACString& _retval);
    220 
    221 class CacheFileLock final {
    222 public:
    223  NS_INLINE_DECL_THREADSAFE_REFCOUNTING(CacheFileLock)
    224  CacheFileLock() = default;
    225 
    226  mozilla::Mutex& Lock() MOZ_RETURN_CAPABILITY(mLock) { return mLock; }
    227 
    228 private:
    229  ~CacheFileLock() = default;
    230 
    231  mozilla::Mutex mLock{"CacheFile.mLock"};
    232 };
    233 
    234 }  // namespace CacheFileUtils
    235 }  // namespace net
    236 }  // namespace mozilla
    237 
    238 #endif