LCOV - code coverage report
Current view: top level - src/heap - slot-set.cc (source / functions) Hit Total Coverage
Test: app.info Lines: 54 54 100.0 %
Date: 2019-04-18 Functions: 11 11 100.0 %

          Line data    Source code
       1             : // Copyright 2018 the V8 project authors. All rights reserved.
       2             : // Use of this source code is governed by a BSD-style license that can be
       3             : // found in the LICENSE file.
       4             : 
       5             : #include "src/heap/slot-set.h"
       6             : 
       7             : namespace v8 {
       8             : namespace internal {
       9             : 
      10       20667 : TypedSlots::~TypedSlots() {
      11       10097 :   Chunk* chunk = head_;
      12       31339 :   while (chunk != nullptr) {
      13       10621 :     Chunk* next = chunk->next;
      14       10621 :     delete[] chunk->buffer;
      15       10621 :     delete chunk;
      16             :     chunk = next;
      17             :   }
      18       10097 :   head_ = nullptr;
      19       10097 :   tail_ = nullptr;
      20       10570 : }
      21             : 
      22      490649 : void TypedSlots::Insert(SlotType type, uint32_t offset) {
      23      490649 :   TypedSlot slot = {TypeField::encode(type) | OffsetField::encode(offset)};
      24      490649 :   Chunk* chunk = EnsureChunk();
      25             :   DCHECK_LT(chunk->count, chunk->capacity);
      26      490644 :   chunk->buffer[chunk->count] = slot;
      27      490644 :   ++chunk->count;
      28      490644 : }
      29             : 
      30         472 : void TypedSlots::Merge(TypedSlots* other) {
      31         472 :   if (other->head_ == nullptr) {
      32             :     return;
      33             :   }
      34         472 :   if (head_ == nullptr) {
      35         354 :     head_ = other->head_;
      36         354 :     tail_ = other->tail_;
      37             :   } else {
      38         118 :     tail_->next = other->head_;
      39         118 :     tail_ = other->tail_;
      40             :   }
      41         472 :   other->head_ = nullptr;
      42         472 :   other->tail_ = nullptr;
      43             : }
      44             : 
      45      490653 : TypedSlots::Chunk* TypedSlots::EnsureChunk() {
      46      490653 :   if (!head_) {
      47        9743 :     head_ = tail_ = NewChunk(nullptr, kInitialBufferSize);
      48             :   }
      49      490653 :   if (head_->count == head_->capacity) {
      50         878 :     head_ = NewChunk(head_, NextCapacity(head_->capacity));
      51             :   }
      52      490653 :   return head_;
      53             : }
      54             : 
      55       10621 : TypedSlots::Chunk* TypedSlots::NewChunk(Chunk* next, int capacity) {
      56       10621 :   Chunk* chunk = new Chunk;
      57       10621 :   chunk->next = next;
      58       10621 :   chunk->buffer = new TypedSlot[capacity];
      59       10621 :   chunk->capacity = capacity;
      60       10621 :   chunk->count = 0;
      61       10621 :   return chunk;
      62             : }
      63             : 
      64       28868 : TypedSlotSet::~TypedSlotSet() { FreeToBeFreedChunks(); }
      65             : 
      66       10484 : void TypedSlotSet::FreeToBeFreedChunks() {
      67       10484 :   base::MutexGuard guard(&to_be_freed_chunks_mutex_);
      68       10484 :   std::stack<std::unique_ptr<Chunk>> empty;
      69             :   to_be_freed_chunks_.swap(empty);
      70       10484 : }
      71             : 
      72         922 : void TypedSlotSet::ClearInvalidSlots(
      73             :     const std::map<uint32_t, uint32_t>& invalid_ranges) {
      74             :   Chunk* chunk = LoadHead();
      75        2856 :   while (chunk != nullptr) {
      76         967 :     TypedSlot* buffer = chunk->buffer;
      77         967 :     int count = chunk->count;
      78       38969 :     for (int i = 0; i < count; i++) {
      79       19001 :       TypedSlot slot = LoadTypedSlot(buffer + i);
      80             :       SlotType type = TypeField::decode(slot.type_and_offset);
      81       19001 :       if (type == CLEARED_SLOT) continue;
      82        9840 :       uint32_t offset = OffsetField::decode(slot.type_and_offset);
      83             :       std::map<uint32_t, uint32_t>::const_iterator upper_bound =
      84             :           invalid_ranges.upper_bound(offset);
      85        9840 :       if (upper_bound == invalid_ranges.begin()) continue;
      86             :       // upper_bounds points to the invalid range after the given slot. Hence,
      87             :       // we have to go to the previous element.
      88             :       upper_bound--;
      89             :       DCHECK_LE(upper_bound->first, offset);
      90        9360 :       if (upper_bound->second > offset) {
      91             :         ClearTypedSlot(buffer + i);
      92             :       }
      93             :     }
      94             :     chunk = LoadNext(chunk);
      95             :   }
      96         922 : }
      97             : 
      98             : }  // namespace internal
      99      122036 : }  // namespace v8

Generated by: LCOV version 1.10