LCOV - code coverage report
Current view: top level - js/src - jshashutil.h (source / functions) Hit Total Coverage
Test: output.info Lines: 20 27 74.1 %
Date: 2017-07-14 16:53:18 Functions: 36 65 55.4 %
Legend: Lines: hit not hit

          Line data    Source code
       1             : /* -*- Mode: C++; tab-width: 8; indent-tabs-mode: nil; c-basic-offset: 4 -*-
       2             :  * vim: set ts=8 sts=4 et sw=4 tw=99:
       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             : #ifndef jshashutil_h
       8             : #define jshashutil_h
       9             : 
      10             : #include "jscntxt.h"
      11             : 
      12             : #include "gc/Zone.h"
      13             : 
      14             : namespace js {
      15             : 
      16             : /*
      17             :  * Used to add entries to a js::HashMap or HashSet where the key depends on a GC
      18             :  * thing that may be moved by generational or compacting GC between the call to
      19             :  * lookupForAdd() and relookupOrAdd().
      20             :  */
      21             : template <class T>
      22             : struct DependentAddPtr
      23             : {
      24             :     typedef typename T::AddPtr AddPtr;
      25             :     typedef typename T::Entry Entry;
      26             : 
      27             :     template <class Lookup>
      28      178331 :     DependentAddPtr(const JSContext* cx, const T& table, const Lookup& lookup)
      29             :       : addPtr(table.lookupForAdd(lookup))
      30      178331 :       , originalGcNumber(cx->zone()->gcNumber())
      31      178329 :     {}
      32             : 
      33        5963 :     DependentAddPtr(DependentAddPtr&& other)
      34             :       : addPtr(other.addPtr)
      35        5963 :       , originalGcNumber(other.originalGcNumber)
      36        5963 :     {}
      37             : 
      38             :     template <class KeyInput, class ValueInput>
      39       15376 :     bool add(JSContext* cx, T& table, const KeyInput& key, const ValueInput& value) {
      40       15376 :         refreshAddPtr(cx, table, key);
      41       15376 :         if (!table.relookupOrAdd(addPtr, key, value)) {
      42           0 :             ReportOutOfMemory(cx);
      43           0 :             return false;
      44             :         }
      45       15376 :         return true;
      46             :     }
      47             : 
      48             :     template <class KeyInput>
      49           0 :     void remove(JSContext* cx, T& table, const KeyInput& key) {
      50           0 :         refreshAddPtr(cx, table, key);
      51           0 :         table.remove(addPtr);
      52           0 :     }
      53             : 
      54      178329 :     bool found() const                 { return addPtr.found(); }
      55      178329 :     explicit operator bool() const     { return found(); }
      56       37183 :     const Entry& operator*() const     { return *addPtr; }
      57      137806 :     const Entry* operator->() const    { return &*addPtr; }
      58             : 
      59             :   private:
      60             :     AddPtr addPtr ;
      61             :     const uint64_t originalGcNumber;
      62             : 
      63             :     template <class KeyInput>
      64       15376 :     void refreshAddPtr(JSContext* cx, T& table, const KeyInput& key) {
      65       15376 :         bool gcHappened = originalGcNumber != cx->zone()->gcNumber();
      66       15376 :         if (gcHappened)
      67           0 :             addPtr = table.lookupForAdd(key);
      68       15376 :     }
      69             : 
      70             :     DependentAddPtr() = delete;
      71             :     DependentAddPtr(const DependentAddPtr&) = delete;
      72             :     DependentAddPtr& operator=(const DependentAddPtr&) = delete;
      73             : };
      74             : 
      75             : template <typename T, typename Lookup>
      76             : inline auto
      77      163327 : MakeDependentAddPtr(const JSContext* cx, T& table, const Lookup& lookup)
      78             :   -> DependentAddPtr<typename mozilla::RemoveReference<decltype(table)>::Type>
      79             : {
      80             :     using Ptr = DependentAddPtr<typename mozilla::RemoveReference<decltype(table)>::Type>;
      81      163327 :     return Ptr(cx, table, lookup);
      82             : }
      83             : 
      84             : } // namespace js
      85             : 
      86             : #endif

Generated by: LCOV version 1.13