| 543 | } |
| 544 | |
| 545 | bool MemTracker::GcMemory(int64_t max_consumption) { |
| 546 | if (max_consumption < 0) return true; |
| 547 | lock_guard<mutex> l(gc_lock_); |
| 548 | if (consumption_metric_ != NULL) RefreshConsumptionFromMetric(); |
| 549 | int64_t pre_gc_consumption = consumption(); |
| 550 | // Check if someone gc'd before us |
| 551 | if (pre_gc_consumption < max_consumption) return false; |
| 552 | if (num_gcs_metric_ != NULL) num_gcs_metric_->Increment(1); |
| 553 | |
| 554 | int64_t curr_consumption = pre_gc_consumption; |
| 555 | // Try to free up some memory |
| 556 | for (int i = 0; i < gc_functions_.size(); ++i) { |
| 557 | // Try to free up the amount we are over plus some extra so that we don't have to |
| 558 | // immediately GC again. Don't free all the memory since that can be unnecessarily |
| 559 | // expensive. |
| 560 | const int64_t EXTRA_BYTES_TO_FREE = 512L * 1024L * 1024L; |
| 561 | int64_t bytes_to_free = curr_consumption - max_consumption + EXTRA_BYTES_TO_FREE; |
| 562 | gc_functions_[i](bytes_to_free); |
| 563 | if (consumption_metric_ != NULL) RefreshConsumptionFromMetric(); |
| 564 | curr_consumption = consumption(); |
| 565 | if (max_consumption - curr_consumption <= EXTRA_BYTES_TO_FREE) break; |
| 566 | } |
| 567 | |
| 568 | if (bytes_freed_by_last_gc_metric_ != NULL) { |
| 569 | bytes_freed_by_last_gc_metric_->SetValue(pre_gc_consumption - curr_consumption); |
| 570 | } |
| 571 | return curr_consumption > max_consumption; |
| 572 | } |
| 573 | |
| 574 | Status ScopedMemTracker::TryConsume(int64_t size) { |
| 575 | DCHECK(tracker_ != nullptr); |
no test coverage detected