paul@65 | 1 | #include "pipe_paging.h" |
paul@65 | 2 | |
paul@66 | 3 | PipePaging::PipePaging(offset_t size) |
paul@66 | 4 | : _size(size) |
paul@65 | 5 | { |
paul@65 | 6 | } |
paul@65 | 7 | |
paul@67 | 8 | /* Detach one endpoint. */ |
paul@67 | 9 | |
paul@67 | 10 | void PipePaging::detach() |
paul@67 | 11 | { |
paul@67 | 12 | if (!_endpoints) |
paul@67 | 13 | return; |
paul@67 | 14 | else |
paul@67 | 15 | _endpoints--; |
paul@67 | 16 | |
paul@69 | 17 | /* Return if the other endpoint is attached. */ |
paul@69 | 18 | |
paul@67 | 19 | if (_endpoints) |
paul@67 | 20 | return; |
paul@67 | 21 | |
paul@67 | 22 | /* Discard all regions from the pipe. */ |
paul@67 | 23 | |
paul@67 | 24 | while (!_regions.empty()) |
paul@67 | 25 | { |
paul@67 | 26 | PageMapper *mapper = _regions.front(); |
paul@67 | 27 | |
paul@67 | 28 | _regions.pop_front(); |
paul@67 | 29 | mapper->detach(); |
paul@67 | 30 | delete mapper; |
paul@67 | 31 | } |
paul@67 | 32 | } |
paul@67 | 33 | |
paul@65 | 34 | /* Add a region to the sequence. */ |
paul@65 | 35 | |
paul@65 | 36 | void PipePaging::add_region(PageMapper *mapper) |
paul@65 | 37 | { |
paul@65 | 38 | _regions.push_back(mapper); |
paul@65 | 39 | } |
paul@65 | 40 | |
paul@65 | 41 | /* Return the first region in the sequence. */ |
paul@65 | 42 | |
paul@65 | 43 | PageMapper *PipePaging::first_region() |
paul@65 | 44 | { |
paul@65 | 45 | return _regions.front(); |
paul@65 | 46 | } |
paul@65 | 47 | |
paul@65 | 48 | /* Return the next region for the reader. If only a single region remains, with |
paul@65 | 49 | the reader wishing to move to the next, return NULL. */ |
paul@65 | 50 | |
paul@65 | 51 | PageMapper *PipePaging::next_region() |
paul@65 | 52 | { |
paul@65 | 53 | if (_regions.size() > 1) |
paul@65 | 54 | { |
paul@66 | 55 | /* Discard the accessor from the current region. */ |
paul@66 | 56 | |
paul@66 | 57 | if (_accessors.size() > _regions.size()) |
paul@66 | 58 | _accessors.pop_front(); |
paul@66 | 59 | |
paul@67 | 60 | /* Detach and discard the current page mapper. */ |
paul@67 | 61 | |
paul@67 | 62 | PageMapper *mapper = _regions.front(); |
paul@67 | 63 | |
paul@65 | 64 | _regions.pop_front(); |
paul@67 | 65 | mapper->detach(); |
paul@67 | 66 | delete mapper; |
paul@67 | 67 | |
paul@67 | 68 | /* Return the next region. */ |
paul@67 | 69 | |
paul@65 | 70 | return _regions.front(); |
paul@65 | 71 | } |
paul@65 | 72 | else |
paul@65 | 73 | return NULL; |
paul@65 | 74 | } |
paul@65 | 75 | |
paul@66 | 76 | /* Initialise an accessor for a region. */ |
paul@66 | 77 | |
paul@66 | 78 | PipeAccessor *PipePaging::accessor() |
paul@66 | 79 | { |
paul@66 | 80 | PipeAccessor accessor; |
paul@66 | 81 | |
paul@66 | 82 | _accessors.push_back(accessor); |
paul@66 | 83 | return &_accessors.back(); |
paul@66 | 84 | } |
paul@66 | 85 | |
paul@65 | 86 | // vim: tabstop=4 expandtab shiftwidth=4 |