1// Copyright 2016 The Fuchsia Authors 2// 3// Use of this source code is governed by a MIT-style 4// license that can be found in the LICENSE file or at 5// https://opensource.org/licenses/MIT 6#pragma once 7 8#include <fbl/intrusive_double_list.h> 9#include <fbl/macros.h> 10 11#include <trace.h> 12#include <vm/pmm.h> 13#include <zircon/types.h> 14 15class PmmNode; 16 17class PmmArena : public fbl::DoublyLinkedListable<PmmArena*> { 18public: 19 constexpr PmmArena() = default; 20 ~PmmArena() = default; 21 22 DISALLOW_COPY_ASSIGN_AND_MOVE(PmmArena); 23 24 // initialize the arena and allocate memory for internal data structures 25 zx_status_t Init(const pmm_arena_info_t* info, PmmNode* node); 26 27 // accessors 28 const pmm_arena_info_t& info() const { return info_; } 29 const char* name() const { return info_.name; } 30 paddr_t base() const { return info_.base; } 31 size_t size() const { return info_.size; } 32 unsigned int flags() const { return info_.flags; } 33 unsigned int priority() const { return info_.priority; } 34 35 // Counts the number of pages in every state. For each page in the arena, 36 // increments the corresponding VM_PAGE_STATE_*-indexed entry of 37 // |state_count|. Does not zero out the entries first. 38 void CountStates(size_t state_count[VM_PAGE_STATE_COUNT_]) const; 39 40 vm_page_t* get_page(size_t index) { return &page_array_[index]; } 41 42 // find a free run of contiguous pages 43 vm_page_t* FindFreeContiguous(size_t count, uint8_t alignment_log2); 44 45 // return a pointer to a specific page 46 vm_page_t* FindSpecific(paddr_t pa); 47 48 // helpers 49 bool page_belongs_to_arena(const vm_page* page) const { 50 return (page->paddr() >= base() && page->paddr() < (base() + size())); 51 } 52 53 bool address_in_arena(paddr_t address) const { 54 return (address >= info_.base && address <= info_.base + info_.size - 1); 55 } 56 57 void Dump(bool dump_pages, bool dump_free_ranges) const; 58 59private: 60 pmm_arena_info_t info_ = {}; 61 vm_page_t* page_array_ = nullptr; 62}; 63