diff --git a/repos/os/src/monitor/gdb_stub.h b/repos/os/src/monitor/gdb_stub.h index d0c2461fe1..4d3fbcfebd 100644 --- a/repos/os/src/monitor/gdb_stub.h +++ b/repos/os/src/monitor/gdb_stub.h @@ -77,10 +77,10 @@ struct Monitor::Gdb::State : Noncopyable linker_area_region.writeable ? "ram" : "rom"); xml.attribute("start", - Value(Hex(region.addr + - linker_area_region.addr))); + Value(Hex(region.range.addr + + linker_area_region.range.addr))); xml.attribute("length", - Value(Hex(linker_area_region.size))); + Value(Hex(linker_area_region.range.size))); }); }); @@ -97,10 +97,10 @@ struct Monitor::Gdb::State : Noncopyable stack_area_region.writeable ? "ram" : "rom"); xml.attribute("start", - Value(Hex(region.addr + - stack_area_region.addr))); + Value(Hex(region.range.addr + + stack_area_region.range.addr))); xml.attribute("length", - Value(Hex(stack_area_region.size))); + Value(Hex(stack_area_region.range.size))); }); }); @@ -109,8 +109,8 @@ struct Monitor::Gdb::State : Noncopyable xml.node("memory", [&] { xml.attribute("type", region.writeable ? "ram" : "rom"); - xml.attribute("start", Value(Hex(region.addr))); - xml.attribute("length", Value(Hex(region.size))); + xml.attribute("start", Value(Hex(region.range.addr))); + xml.attribute("length", Value(Hex(region.range.size))); }); }); }); diff --git a/repos/os/src/monitor/monitored_region_map.h b/repos/os/src/monitor/monitored_region_map.h index 116b8bf3e1..bca46d396b 100644 --- a/repos/os/src/monitor/monitored_region_map.h +++ b/repos/os/src/monitor/monitored_region_map.h @@ -87,32 +87,46 @@ struct Monitor::Monitored_region_map : Monitored_rpc_object Constructible _writeable_text_segments { }; - void writeable_text_segments(Allocator &alloc, - Ram_allocator &ram, - Region_map &local_rm) + void writeable_text_segments(Allocator &alloc, + Ram_allocator &ram, + Region_map &local_rm) { if (!_writeable_text_segments.constructed()) _writeable_text_segments.construct(alloc, ram, local_rm); } - struct Region : List::Element + struct Region : Registry::Element { + struct Range + { + addr_t addr; + size_t size; + + bool intersects(Range const &other) const + { + addr_t end = addr + size - 1; + addr_t other_end = other.addr + other.size - 1; + return ((other.addr <= end) && (other_end >= addr)); + } + }; + Dataspace_capability cap; - addr_t addr; - size_t size; + Range range; bool writeable; - Region(Dataspace_capability cap, addr_t addr, size_t size, - bool writeable) - : cap(cap), addr(addr), size(size), writeable(writeable) { } + Region(Registry ®istry, Dataspace_capability cap, + addr_t addr, size_t size, bool writeable) + : Registry::Element(registry, *this), + cap(cap), range(addr, size), writeable(writeable) { } }; - List _regions { }; + Registry _regions { }; void for_each_region(auto const &fn) const { - for (Region const *region = _regions.first(); region; region = region->next()) - fn(*region); + _regions.for_each([&] (Region const ®ion) { + fn(region); + }); } Allocator &_alloc; @@ -124,10 +138,9 @@ struct Monitor::Monitored_region_map : Monitored_rpc_object ~Monitored_region_map() { - while (Region *region = _regions.first()) { - _regions.remove(region); - destroy(_alloc, region); - } + _regions.for_each([&] (Region ®ion) { + destroy(_alloc, ®ion); + }); } /************************** @@ -160,30 +173,20 @@ struct Monitor::Monitored_region_map : Monitored_rpc_object * It can happen that previous attachments got implicitly * removed by destruction of the dataspace without knowledge * of the monitor. The newly obtained region could then - * overlap with outdated region list entries which must + * overlap with outdated region registry entries which must * be removed before inserting the new region. */ - addr_t start_addr = (addr_t)attached_addr; - addr_t end_addr = start_addr + region_size - 1; + Region::Range range { attached_addr, region_size }; - for (Region *region = _regions.first(); region; ) { + _regions.for_each([&] (Region ®ion) { + if (region.range.intersects(range)) + destroy(_alloc, ®ion); + }); - if ((region->addr <= end_addr) && - ((region->addr + region->size - 1) >= start_addr)) { + new (_alloc) Region(_regions, ds, (addr_t)attached_addr, + region_size, writeable); - Region *next_region = region->next(); - _regions.remove(region); - destroy(_alloc, region); - region = next_region; - continue; - } - - region = region->next(); - } - - _regions.insert(new (_alloc) Region(ds, (addr_t)attached_addr, - region_size, writeable)); return attached_addr; } @@ -191,16 +194,10 @@ struct Monitor::Monitored_region_map : Monitored_rpc_object { _real.call(local_addr); - addr_t addr = (addr_t)local_addr; - - for (Region *region = _regions.first(); region; region = region->next()) { - if ((addr >= region->addr) && - (addr <= (region->addr + region->size - 1))) { - _regions.remove(region); - destroy(_alloc, region); - break; - } - } + _regions.for_each([&] (Region ®ion) { + if (region.range.intersects(Region::Range { local_addr, 1 })) + destroy(_alloc, ®ion); + }); } void fault_handler(Signal_context_capability) override