platform: remove cache attribute from io_mem call

Instead of allowing the client to set a caching attribute
in the io_mem() call of the device interface, which was
only used to decide in between of the memory  being
write-combined or not, remove it from the API.
Instead use the information delivered by the devices ROM,
whether memory from a PCI BAR is prefetchable or not,
to decide whether it is mapped write-combined or not.

Ref genodelabs/genode#4578
This commit is contained in:
Stefan Kalkowski 2022-09-28 13:59:17 +02:00 committed by Christian Helmuth
parent 7334128a2e
commit 6a7247ab44
11 changed files with 31 additions and 28 deletions

View File

@ -125,15 +125,15 @@ struct Platform::Device_client : Rpc_client<Device_interface>
return call<Rpc_irq>(id);
}
Io_mem_session_capability io_mem(unsigned id, Range &range, Cache cache)
Io_mem_session_capability io_mem(unsigned id, Range &range)
{
return call<Rpc_io_mem>(id, range, cache);
return call<Rpc_io_mem>(id, range);
}
Dataspace_capability io_mem_dataspace(unsigned id = 0)
{
Range range { };
return Io_mem_session_client(io_mem(id, range, UNCACHED)).dataspace();
return Io_mem_session_client(io_mem(id, range)).dataspace();
}
};

View File

@ -116,7 +116,7 @@ void lx_platform_device_init()
Device_interface::Range range { };
Io_mem_session_client io_mem_client {
device_cap.call<Device_interface::Rpc_io_mem>(res_count, range, UNCACHED) };
device_cap.call<Device_interface::Rpc_io_mem>(res_count, range) };
Io_mem & iom = *new (Lx_kit::env().heap())
Io_mem(io_mem_client.dataspace(), range.start, range.size,

View File

@ -49,9 +49,9 @@ class Platform::Device : Interface, Noncopyable
return _cap.call<Device_interface::Rpc_irq>(index);
}
Io_mem_session_capability _io_mem(unsigned index, Range &range, Cache cache)
Io_mem_session_capability _io_mem(unsigned index, Range &range)
{
return _cap.call<Device_interface::Rpc_io_mem>(index, range, cache);
return _cap.call<Device_interface::Rpc_io_mem>(index, range);
}
Io_port_session_capability _io_port_range(unsigned index)
@ -92,7 +92,7 @@ class Platform::Device::Mmio : Range, Attached_dataspace, public Genode::Mmio
Dataspace_capability _ds_cap(Device &device, unsigned id)
{
Io_mem_session_client io_mem(device._io_mem(id, *this, UNCACHED));
Io_mem_session_client io_mem(device._io_mem(id, *this));
return io_mem.dataspace();
}

View File

@ -42,7 +42,7 @@ struct Platform::Device_interface : Interface
GENODE_RPC(Rpc_irq, Irq_session_capability, irq, unsigned);
GENODE_RPC(Rpc_io_mem, Io_mem_session_capability, io_mem,
unsigned, Range &, Cache);
unsigned, Range &);
GENODE_RPC(Rpc_io_port_range, Io_port_session_capability, io_port_range,
unsigned);

View File

@ -44,15 +44,15 @@ struct Platform::Device_client : Rpc_client<Device_interface>
return call<Rpc_irq>(id);
}
Io_mem_session_capability io_mem(unsigned id, Range &range, Cache cache)
Io_mem_session_capability io_mem(unsigned id, Range &range)
{
return call<Rpc_io_mem>(id, range, cache);
return call<Rpc_io_mem>(id, range);
}
Dataspace_capability io_mem_dataspace(unsigned id = 0)
{
Range range { };
return Io_mem_session_client(io_mem(id, range, UNCACHED)).dataspace();
return Io_mem_session_client(io_mem(id, range)).dataspace();
}
};

View File

@ -134,9 +134,7 @@ class Platform::Device_component : public Rpc_object<Device_interface,
return _irq.cap();
}
Io_mem_session_capability io_mem(unsigned idx,
Range & range,
Cache /* ignore caching */)
Io_mem_session_capability io_mem(unsigned idx, Range & range)
{
range.start = 0;

View File

@ -84,9 +84,10 @@ class Driver::Device : private List_model<Device>::Element
Pci_bar bar;
Range range;
bool prefetchable;
Io_mem(Pci_bar bar, Range range)
: bar(bar), range(range) {}
Io_mem(Pci_bar bar, Range range, bool pf)
: bar(bar), range(range), prefetchable(pf) {}
};
struct Irq : List_model<Irq>::Element
@ -228,7 +229,7 @@ class Driver::Device : private List_model<Device>::Element
{
unsigned idx = 0;
_io_mem_list.for_each([&] (Io_mem const & iomem) {
fn(idx++, iomem.range, iomem.bar); });
fn(idx++, iomem.range, iomem.bar, iomem.prefetchable); });
}
template <typename FN> void for_each_io_port_range(FN const & fn) const
@ -420,7 +421,8 @@ struct Driver::Io_mem_update_policy : Genode::List_model<Device::Io_mem>::Update
Bar bar { node.attribute_value<uint8_t>("pci_bar", Bar::INVALID) };
Range range { node.attribute_value<Genode::addr_t>("address", 0),
node.attribute_value<Genode::size_t>("size", 0) };
return *(new (alloc) Element(bar, range));
bool pf { node.attribute_value("prefetchable", false) };
return *(new (alloc) Element(bar, range, pf));
}
void update_element(Element &, Genode::Xml_node) {}

View File

@ -47,7 +47,7 @@ Driver::Session_component & Device_component::session() { return _session; }
Genode::Io_mem_session_capability
Device_component::io_mem(unsigned idx, Range &range, Cache cache)
Device_component::io_mem(unsigned idx, Range &range)
{
Io_mem_session_capability cap;
@ -60,7 +60,7 @@ Device_component::io_mem(unsigned idx, Range &range, Cache cache)
iomem.io_mem.construct(_env,
iomem.range.start,
iomem.range.size,
cache == WRITE_COMBINED);
iomem.prefetchable);
range = iomem.range;
range.start &= 0xfff;
@ -159,13 +159,14 @@ Device_component::Device_component(Registry<Device_component> & registry,
new (session.heap()) Irq(_irq_registry, idx, nr, type, polarity, mode);
});
device.for_each_io_mem([&] (unsigned idx, Range range, Device::Pci_bar)
device.for_each_io_mem([&] (unsigned idx, Range range,
Device::Pci_bar, bool pf)
{
session.ram_quota_guard().withdraw(Ram_quota{Io_mem_session::RAM_QUOTA});
_ram_quota += Io_mem_session::RAM_QUOTA;
session.cap_quota_guard().withdraw(Cap_quota{Io_mem_session::CAP_QUOTA});
_cap_quota += Io_mem_session::CAP_QUOTA;
new (session.heap()) Io_mem(_io_mem_registry, idx, range);
new (session.heap()) Io_mem(_io_mem_registry, idx, range, pf);
});
device.for_each_io_port_range([&] (unsigned idx, Io_port_range::Range range)
@ -193,7 +194,7 @@ Device_component::Device_component(Registry<Device_component> & registry,
session.cap_quota_guard().withdraw(Cap_quota{Io_mem_session::CAP_QUOTA});
_cap_quota += Io_mem_session::CAP_QUOTA;
Io_mem & iomem = *(new (session.heap())
Io_mem(_reserved_mem_registry, idx, range));
Io_mem(_reserved_mem_registry, idx, range, false));
iomem.io_mem.construct(_env, iomem.range.start,
iomem.range.size, false);
session.device_pd().attach_dma_mem(iomem.io_mem->dataspace(),

View File

@ -61,14 +61,16 @@ class Driver::Device_component : public Rpc_object<Platform::Device_interface,
{
unsigned idx;
Range range;
bool prefetchable;
Constructible<Io_mem_connection> io_mem {};
Io_mem(Registry<Io_mem> & registry,
unsigned idx,
Range range)
Range range,
bool pf)
:
Registry<Io_mem>::Element(registry, *this),
idx(idx), range(range) {}
idx(idx), range(range), prefetchable(pf) {}
};
struct Io_port_range : Registry<Io_port_range>::Element
@ -109,7 +111,7 @@ class Driver::Device_component : public Rpc_object<Platform::Device_interface,
************************************/
Irq_session_capability irq(unsigned);
Io_mem_session_capability io_mem(unsigned, Range &, Cache);
Io_mem_session_capability io_mem(unsigned, Range &);
Io_port_session_capability io_port_range(unsigned);
private:

View File

@ -53,7 +53,7 @@ struct Config_helper
/* enable memory space when I/O mem is defined */
_dev.for_each_io_mem([&] (unsigned, Driver::Device::Io_mem::Range,
Driver::Device::Pci_bar) {
Driver::Device::Pci_bar, bool) {
Config::Command::Memory_space_enable::set(cmd, 1); });
/* enable i/o space when I/O ports are defined */

View File

@ -80,7 +80,7 @@ void Driver::pci_virtio_info(Device const & dev,
unsigned idx = ~0U;
dev.for_each_io_mem([&] (unsigned i,
Driver::Device::Io_mem::Range,
Driver::Device::Pci_bar bar) {
Driver::Device::Pci_bar bar, bool) {
if (bar.number == cap.read<Capability::Bar>()) idx = i; });
xml.node("virtio_range", [&] () {