diff --git a/repos/base-hw/include/spec/x86_64/muen/sinfo.h b/repos/base-hw/include/spec/x86_64/muen/sinfo.h
index b83705adc..64fe5f70f 100644
--- a/repos/base-hw/include/spec/x86_64/muen/sinfo.h
+++ b/repos/base-hw/include/spec/x86_64/muen/sinfo.h
@@ -19,8 +19,8 @@
#include
-struct subject_info_type;
-struct scheduling_info_type;
+struct Subject_info_type;
+struct Scheduling_info_type;
namespace Genode
{
@@ -35,14 +35,27 @@ class Genode::Sinfo
public:
enum Config {
- PHYSICAL_BASE_ADDR = 0xe00000000,
- SIZE = 0x9000,
- MAX_NAME_LENGTH = 63,
- HASH_LENGTH = 32,
+ MUEN_SUBJECT_INFO_MAGIC = 0x02006f666e69756dULL,
+ MAX_RESOURCE_COUNT = 255,
+ MAX_NAME_LENGTH = 63,
+ PHYSICAL_BASE_ADDR = 0xe00000000,
+ SIZE = 0x8000,
+ HASH_LENGTH = 32,
+ MEM_WRITABLE_FLAG = (1 << 0),
+ MEM_EXECUTABLE_FLAG = (1 << 1),
+ MEM_CHANNEL_FLAG = (1 << 2),
+ DEV_MSI_FLAG = (1 << 0),
};
Sinfo(const addr_t base_addr);
+ /* Resource name */
+ struct Name_type {
+ uint8_t length;
+ char data[MAX_NAME_LENGTH];
+ uint8_t null_term;
+ } __attribute__((packed));
+
enum Content {
CONTENT_UNINITIALIZED,
CONTENT_FILL,
@@ -50,42 +63,67 @@ class Genode::Sinfo
};
/* Structure holding information about a memory region */
- struct Memregion_info {
+ struct Memregion_type {
enum Content content;
- char name[MAX_NAME_LENGTH + 1];
uint64_t address;
uint64_t size;
- bool writable;
- bool executable;
uint8_t hash[HASH_LENGTH];
+ uint8_t flags;
uint16_t pattern;
- };
+ char padding[1];
+ } __attribute__((packed));
- /* Structure holding information about a Muen channel */
- struct Channel_info {
- char name[MAX_NAME_LENGTH + 1];
- uint64_t address;
- uint64_t size;
- uint8_t event_number;
- uint8_t vector;
- bool writable;
- bool has_event;
- bool has_vector;
- };
-
- /* Structure holding information about PCI devices */
- struct Dev_info {
+ /*
+ * Structure holding information about a PCI device,
+ * explicitly padded to the size of the largest resource variant
+ */
+ struct Device_type {
uint16_t sid;
uint16_t irte_start;
uint8_t irq_start;
uint8_t ir_count;
- bool msi_capable;
+ uint8_t flags;
+ char padding[sizeof(struct Memregion_type) - 7];
+ } __attribute__((packed));
+
+ /* Currently known resource types */
+ enum Resource_kind {
+ RES_NONE,
+ RES_MEMORY,
+ RES_EVENT,
+ RES_VECTOR,
+ RES_DEVICE
};
+ /* Resource data depending on the kind of resource */
+ union Resource_data {
+ struct Memregion_type mem;
+ struct Device_type dev;
+ uint8_t number;
+ };
+
+ /* Exported resource with associated name */
+ struct Resource_type {
+ enum Resource_kind kind;
+ struct Name_type name;
+ char padding[3];
+ union Resource_data data;
+ } __attribute__((packed));
+
+ /* Muen subject information (sinfo) structure */
+ struct Subject_info_type {
+ uint64_t magic;
+ uint32_t tsc_khz;
+ struct Name_type name;
+ uint16_t resource_count;
+ char padding[1];
+ struct Resource_type resources[MAX_RESOURCE_COUNT];
+ } __attribute__((packed));
+
/*
* Check Muen sinfo Magic.
*/
- bool check_magic(void);
+ bool check_magic(void) const;
/*
* Return subject name.
@@ -95,83 +133,55 @@ class Genode::Sinfo
const char * get_subject_name(void);
/*
- * Return information for a channel given by name.
+ * Return resource with given name and kind.
*
- * If no channel with given name exists, False is returned. The
- * event_number and vector parameters are only valid if indicated by
- * the has_[event|vector] struct members.
+ * If no resource with given name exists, null is returned.
*/
- bool get_channel_info(const char * const name,
- struct Channel_info *channel);
-
- /*
- * Return information for a memory region given by name.
- *
- * If no memory region with given name exists, False is returned.
- */
- bool get_memregion_info(const char * const name,
- struct Memregion_info *memregion);
+ const struct Resource_type *
+ get_resource(const char *const name, enum Resource_kind kind) const;
/*
* Return information for PCI device with given SID.
*
- * The function returns false if no device information for the
- * specified device exists.
+ * The function returns null if no device information for the specified device
+ * exists.
*/
- bool get_dev_info(const uint16_t sid, struct Dev_info *dev);
+ const struct Device_type * get_device(const uint16_t sid) const;
/*
- * Channel callback.
+ * Resource callback.
*
- * Used in the muen_for_each_channel function. The optional void data pointer
- * can be used to pass additional data.
+ * Used in the for_each_resource function. The optional void data
+ * pointer can be used to pass additional data.
*/
- typedef bool (*Channel_cb)(const struct Channel_info * const channel,
+ typedef bool (*resource_cb)(const struct Resource_type *const res,
void *data);
/*
- * Invoke given callback function for each available channel.
+ * Invoke given callback function for each available resource.
*
- * Channel information and the optional data argument are passed to each
+ * Resource information and the optional data argument are passed to each
* invocation of the callback. If a callback invocation returns false,
* processing is aborted and false is returned to the caller.
*/
- bool for_each_channel(Channel_cb func, void *data);
-
- /*
- * Memory region callback.
- *
- * Used in the muen_for_each_memregion function. The optional void data pointer
- * can be used to pass additional data.
- */
- typedef bool (*Memregion_cb)(const struct Memregion_info * const memregion,
- void *data);
-
- /*
- * Invoke given callback function for each available memory region.
- *
- * Memory region information and the optional data argument are passed to each
- * invocation of the callback. If a callback invocation returns false,
- * processing is aborted and false is returned to the caller.
- */
- bool for_each_memregion(Memregion_cb func, void *data);
+ bool for_each_resource(resource_cb func, void *data) const;
/*
* Return TSC tick rate in kHz.
*
* The function returns 0 if the TSC tick rate cannot be retrieved.
*/
- uint64_t get_tsc_khz(void);
+ uint64_t get_tsc_khz(void) const;
/*
* Return start time of current minor frame in TSC ticks.
*/
- uint64_t get_sched_start(void);
+ uint64_t get_sched_start(void) const;
/*
* Return end time of current minor frame in TSC ticks.
*/
- uint64_t get_sched_end(void);
+ uint64_t get_sched_end(void) const;
/*
* Log sinfo status.
@@ -180,25 +190,22 @@ class Genode::Sinfo
private:
- subject_info_type * sinfo = nullptr;
- scheduling_info_type * sched_info = nullptr;
+ Subject_info_type * sinfo = nullptr;
+ Scheduling_info_type * sched_info = nullptr;
char subject_name[MAX_NAME_LENGTH + 1];
bool subject_name_set = false;
/*
- * Fill memregion struct with memory region info from resource given by
- * index.
+ * Iterate over all resources beginning at given start resource. If the res
+ * member of the iterator is nil, the function (re)starts the iteration at the first
+ * resource.
*/
- void fill_memregion_data(uint8_t idx, struct Memregion_info *region);
+ struct iterator {
+ const struct Resource_type *res;
+ unsigned int idx;
+ };
- /*
- * Fill channel struct with channel information from resource given by
- * index.
- */
- void fill_channel_data(uint8_t idx, struct Channel_info *channel);
-
- /* Fill dev struct with data from PCI device info given by index. */
- void fill_dev_data(uint8_t idx, struct Dev_info *dev);
+ bool iterate_resources(struct iterator *const iter) const;
};
#endif /* _INCLUDE__SPEC__X86_64__MUEN__SINFO_H_ */
diff --git a/repos/base-hw/src/bootstrap/spec/x86_64/platform_muen.cc b/repos/base-hw/src/bootstrap/spec/x86_64/platform_muen.cc
index 28d17ac4f..4a2a3dbaf 100644
--- a/repos/base-hw/src/bootstrap/spec/x86_64/platform_muen.cc
+++ b/repos/base-hw/src/bootstrap/spec/x86_64/platform_muen.cc
@@ -32,13 +32,15 @@ Bootstrap::Platform::Board::Board()
Memory_region { TIMER_BASE_ADDR, TIMER_SIZE },
Memory_region { TIMER_PREEMPT_BASE_ADDR, TIMER_PREEMPT_SIZE })
{
- struct Sinfo::Memregion_info region;
-
Sinfo sinfo(Sinfo::PHYSICAL_BASE_ADDR);
- if (!sinfo.get_memregion_info("ram", ®ion))
+ const struct Sinfo::Resource_type *
+ region = sinfo.get_resource("ram", Sinfo::RES_MEMORY);
+
+ if (!region)
Genode::error("Unable to retrieve base-hw ram region");
else
- early_ram_regions.add(Memory_region { region.address, region.size });
+ early_ram_regions.add(Memory_region
+ { region->data.mem.address, region->data.mem.size });
}
diff --git a/repos/base-hw/src/core/spec/x86_64/muen/platform_support.cc b/repos/base-hw/src/core/spec/x86_64/muen/platform_support.cc
index f34b05a3e..20503ac8b 100644
--- a/repos/base-hw/src/core/spec/x86_64/muen/platform_support.cc
+++ b/repos/base-hw/src/core/spec/x86_64/muen/platform_support.cc
@@ -66,27 +66,27 @@ bool Platform::get_msi_params(const addr_t mmconf, addr_t &address,
addr_t &data, unsigned &irq_number)
{
const unsigned sid = Mmconf_address::to_sid(mmconf);
+ const struct Sinfo::Device_type *dev = sinfo()->get_device(sid);
- struct Sinfo::Dev_info dev_info;
- if (!sinfo()->get_dev_info(sid, &dev_info)) {
+ if (!dev) {
error("error retrieving Muen info for device with SID ", Hex(sid));
return false;
}
- if (!dev_info.ir_count) {
+ if (!dev->ir_count) {
error("device ", Hex(sid), " has no IRQ assigned");
return false;
}
- if (!dev_info.msi_capable) {
+ if (!(dev->flags & Sinfo::DEV_MSI_FLAG)) {
error("device ", Hex(sid), " not configured for MSI");
return false;
}
data = 0;
- address = Msi_address::to_msi_addr(dev_info.irte_start);
- irq_number = dev_info.irq_start;
+ address = Msi_address::to_msi_addr(dev->irte_start);
+ irq_number = dev->irq_start;
log("enabling MSI for device with SID ", Hex(sid), ": "
- "IRTE ", dev_info.irte_start, ", IRQ ", irq_number);
+ "IRTE ", dev->irte_start, ", IRQ ", irq_number);
return true;
}
diff --git a/repos/base-hw/src/core/spec/x86_64/muen/timer.cc b/repos/base-hw/src/core/spec/x86_64/muen/timer.cc
index cfc8b098b..7bccaac1d 100644
--- a/repos/base-hw/src/core/spec/x86_64/muen/timer.cc
+++ b/repos/base-hw/src/core/spec/x86_64/muen/timer.cc
@@ -30,22 +30,26 @@ Timer_driver::Timer_driver(unsigned) : ticks_per_ms(sinfo()->get_tsc_khz())
/* first sinfo instance, output status */
sinfo()->log_status();
- struct Sinfo::Memregion_info region;
- if (!sinfo()->get_memregion_info("timed_event", ®ion)) {
+ const struct Sinfo::Resource_type *
+ region = sinfo()->get_resource("timed_event", Sinfo::RES_MEMORY);
+ if (!region) {
error("muen-timer: Unable to retrieve timed event region");
throw Invalid_region();
}
- event_page = (Subject_timed_event *)Platform::mmio_to_virt(region.address);
+ event_page = (Subject_timed_event *)
+ Platform::mmio_to_virt(region->data.mem.address);
event_page->event_nr = Board::TIMER_EVENT_KERNEL;
- log("muen-timer: Page @", Hex(region.address), ", "
+ log("muen-timer: Page @", Hex(region->data.mem.address), ", "
"frequency ", ticks_per_ms, " kHz, "
"event ", (unsigned)event_page->event_nr);
- if (sinfo()->get_memregion_info("monitor_timed_event", ®ion)) {
- log("muen-timer: Found guest timed event page @", Hex(region.address),
+ region = sinfo()->get_resource("monitor_timed_event", Sinfo::RES_MEMORY);
+ if (region) {
+ log("muen-timer: Found guest timed event page @", Hex(region->data.mem.address),
" -> enabling preemption");
- guest_event_page = (Subject_timed_event *)Platform::mmio_to_virt(region.address);
+ guest_event_page = (Subject_timed_event *)
+ Platform::mmio_to_virt(region->data.mem.address);
guest_event_page->event_nr = Board::TIMER_EVENT_PREEMPT;
}
}
diff --git a/repos/base-hw/src/lib/muen/muschedinfo.h b/repos/base-hw/src/lib/muen/muschedinfo.h
index b368dd3fb..503c67bab 100644
--- a/repos/base-hw/src/lib/muen/muschedinfo.h
+++ b/repos/base-hw/src/lib/muen/muschedinfo.h
@@ -16,9 +16,9 @@
#include
-struct scheduling_info_type {
- uint64_t tsc_schedule_start;
- uint64_t tsc_schedule_end;
+struct Scheduling_info_type {
+ Genode::uint64_t tsc_schedule_start;
+ Genode::uint64_t tsc_schedule_end;
} __attribute__((packed, aligned (8)));
#endif /* _BASE__MUEN_MUSCHEDINFO_H_ */
diff --git a/repos/base-hw/src/lib/muen/musinfo.h b/repos/base-hw/src/lib/muen/musinfo.h
deleted file mode 100644
index 558a7b3de..000000000
--- a/repos/base-hw/src/lib/muen/musinfo.h
+++ /dev/null
@@ -1,88 +0,0 @@
-/*
- * \brief Muen subject info
- * \author Reto Buerki
- * \date 2015-04-21
- */
-
-/*
- * Copyright (C) 2015-2017 Genode Labs GmbH
- *
- * This file is part of the Genode OS framework, which is distributed
- * under the terms of the GNU Affero General Public License version 3.
- */
-
-#ifndef _LIB__MUEN__MUSINFO_H_
-#define _LIB__MUEN__MUSINFO_H_
-
-#include
-#include
-
-#define MUEN_SUBJECT_INFO_MAGIC 0x01006f666e69756dULL
-
-#define MAX_RESOURCE_COUNT 255
-#define NO_RESOURCE 0
-
-using namespace Genode;
-
-struct name_type {
- uint8_t length;
- char data[Sinfo::MAX_NAME_LENGTH];
-} __attribute__((packed));
-
-#define MEM_WRITABLE_FLAG (1 << 0)
-#define MEM_EXECUTABLE_FLAG (1 << 1)
-
-struct memregion_type {
- enum Sinfo::Content content;
- uint64_t address;
- uint64_t size;
- uint8_t hash[Sinfo::HASH_LENGTH];
- uint8_t flags;
- uint16_t pattern;
- char padding[1];
-} __attribute__((packed, aligned (8)));
-
-#define CHAN_EVENT_FLAG (1 << 0)
-#define CHAN_VECTOR_FLAG (1 << 1)
-
-struct channel_info_type {
- uint8_t flags;
- uint8_t event;
- uint8_t vector;
- char padding[5];
-} __attribute__((packed, aligned (8)));
-
-struct resource_type {
- struct name_type name;
- uint8_t memregion_idx;
- uint8_t channel_info_idx;
- char padding[6];
-} __attribute__((packed, aligned (8)));
-
-struct dev_info_type {
- uint16_t sid;
- uint16_t irte_start;
- uint8_t irq_start;
- uint8_t ir_count;
- uint8_t flags;
- char padding[1];
-} __attribute__((packed, aligned (8)));
-
-#define DEV_MSI_FLAG (1 << 0)
-
-struct subject_info_type {
- uint64_t magic;
- struct name_type name;
- uint8_t resource_count;
- uint8_t memregion_count;
- uint8_t channel_info_count;
- uint8_t dev_info_count;
- char padding[4];
- uint64_t tsc_khz;
- struct resource_type resources[MAX_RESOURCE_COUNT];
- struct memregion_type memregions[MAX_RESOURCE_COUNT];
- struct channel_info_type channels_info[MAX_RESOURCE_COUNT];
- struct dev_info_type dev_info[MAX_RESOURCE_COUNT];
-} __attribute__((packed, aligned (8)));
-
-#endif /* _LIB__MUEN__MUSINFO_H_ */
diff --git a/repos/base-hw/src/lib/muen/sinfo.cc b/repos/base-hw/src/lib/muen/sinfo.cc
index 58b40fe24..c50c84ab3 100644
--- a/repos/base-hw/src/lib/muen/sinfo.cc
+++ b/repos/base-hw/src/lib/muen/sinfo.cc
@@ -17,7 +17,6 @@
#include
-#include "musinfo.h"
#include "muschedinfo.h"
#define roundup(x, y) ( \
@@ -26,28 +25,11 @@
(((x) + (__y - 1)) / __y) * __y; \
})
-static_assert(sizeof(subject_info_type) <= Sinfo::SIZE,
+using namespace Genode;
+
+static_assert(sizeof(Sinfo::Subject_info_type) <= Sinfo::SIZE,
"Size of subject info type larger than Sinfo::SIZE.");
-/* Log channel information */
-static bool log_channel(Genode::Sinfo::Channel_info const * const channel, void *)
-{
- if (channel->has_event || channel->has_vector) {
- Genode::log("muen-sinfo: [",
- channel->writable ? "writer" : "reader", " with ",
- channel->has_event ? "event " : "vector", " ",
- channel->has_event ? channel->event_number : channel->vector,
- "] ", Genode::Cstring(channel->name));
- } else {
- Genode::log("muen-sinfo: [",
- channel->writable ? "writer" : "reader", " with no ",
- channel->writable ? "event " : "vector", " ",
- "] ", Genode::Cstring(channel->name));
- }
-
- return true;
-}
-
static const char * const content_names[] = {
"uninitialized", "fill", "file",
@@ -62,6 +44,13 @@ static bool hash_available(const uint8_t * const first)
}
+static bool names_equal(const struct Sinfo::Name_type *const n1,
+ const char *const n2)
+{
+ return n1->length == strlen(n2) && strcmp(n1->data, n2) == 0;
+}
+
+
/* Convert given hash to hex string */
static char *hash_to_hex(char *buffer, const unsigned char *first)
{
@@ -72,48 +61,60 @@ static char *hash_to_hex(char *buffer, const unsigned char *first)
}
-/* Log memory region information */
-static bool log_memregion(Genode::Sinfo::Memregion_info const * const region, void *)
+static bool log_resource(const struct Sinfo::Resource_type *const res, void *)
{
char hash_str[65];
- Genode::log("muen-sinfo: [", content_names[region->content],
- ", addr ", Genode::Hex(region->address),
- " size ", Genode::Hex(region->size), " ",
- region->writable ? "rw" : "ro",
- region->executable ? "x" : "-",
- "] ", Genode::Cstring(region->name));
+ switch (res->kind) {
+ case Sinfo::RES_MEMORY:
+ Genode::log("muen-sinfo: memory [",
+ content_names[res->data.mem.content],
+ ", addr ", Genode::Hex(res->data.mem.address),
+ " size ", Genode::Hex(res->data.mem.size), " ",
+ res->data.mem.flags & Sinfo::MEM_WRITABLE_FLAG ? "rw" : "ro",
+ res->data.mem.flags & Sinfo::MEM_EXECUTABLE_FLAG ? "x" : "-",
+ res->data.mem.flags & Sinfo::MEM_CHANNEL_FLAG ? "c" : "-",
+ "] ", res->name.data);
- if (region->content == Sinfo::CONTENT_FILL)
- Genode::log("muen-sinfo: [pattern ", region->pattern, "]");
- if (hash_available(region->hash))
- Genode::log("muen-sinfo: [hash 0x",
- Genode::Cstring(hash_to_hex(hash_str, region->hash)), "]");
+ if (res->data.mem.content == Sinfo::CONTENT_FILL)
+ Genode::log("muen-sinfo: [pattern ", res->data.mem.pattern, "]");
+
+ if (hash_available(res->data.mem.hash))
+ Genode::log("muen-sinfo: [hash 0x",
+ Genode::Cstring(hash_to_hex(hash_str, res->data.mem.hash)),
+ "]");
+ break;
+ case Sinfo::RES_DEVICE:
+ Genode::log("muen-sinfo: device [sid ", Genode::Hex(res->data.dev.sid),
+ " IRTE/IRQ start ", res->data.dev.irte_start,
+ "/", res->data.dev.irq_start,
+ " IR count ", res->data.dev.ir_count,
+ " flags ", res->data.dev.flags, "] ", res->name.data);
+ break;
+ case Sinfo::RES_EVENT:
+ Genode::log("muen-sinfo: event [number ", res->data.number, "] ", res->name.data);
+ break;
+ case Sinfo::RES_VECTOR:
+ Genode::log("muen-sinfo: vector [number ", res->data.number, "] ", res->name.data);
+ break;
+ case Sinfo::RES_NONE:
+ break;
+ default:
+ Genode::log("muen-sinfo: UNKNOWN resource at address %p\n",
+ res);
+ break;
+ }
return true;
}
-/* Returns true if the given resource is a memory region */
-static bool is_memregion(const struct resource_type * const resource)
-{
- return resource->memregion_idx != NO_RESOURCE;
-}
-
-
-/* Returns true if the given resource is a channel */
-static bool is_channel(const struct resource_type * const resource)
-{
- return is_memregion(resource) && resource->channel_info_idx != NO_RESOURCE;
-}
-
-
Sinfo::Sinfo(const addr_t base_addr)
:
- sinfo((subject_info_type *)base_addr)
+ sinfo((Subject_info_type *)base_addr)
{
- const uint64_t sinfo_page_size = roundup(sizeof(subject_info_type), 0x1000);
- sched_info = ((scheduling_info_type *)(base_addr + sinfo_page_size));
+ const uint64_t sinfo_page_size = roundup(sizeof(Subject_info_type), 0x1000);
+ sched_info = ((Scheduling_info_type *)(base_addr + sinfo_page_size));
if (!check_magic()) {
Genode::error("muen-sinfo: Subject information MAGIC mismatch");
@@ -122,7 +123,7 @@ Sinfo::Sinfo(const addr_t base_addr)
}
-bool Sinfo::check_magic(void)
+bool Sinfo::check_magic(void) const
{
return sinfo != 0 && sinfo->magic == MUEN_SUBJECT_INFO_MAGIC;
}
@@ -144,100 +145,58 @@ const char * Sinfo::get_subject_name(void)
}
-bool Sinfo::get_channel_info(const char * const name,
- struct Channel_info *channel)
+bool Sinfo::iterate_resources(struct iterator *const iter) const
{
- int i;
-
- if (!check_magic())
- return false;
-
- for (i = 0; i < sinfo->resource_count; i++) {
- if (is_channel(&sinfo->resources[i]) &&
- strcmp(sinfo->resources[i].name.data, name) == 0) {
- fill_channel_data(i, channel);
- return true;
- }
+ if (!iter->res) {
+ iter->res = &sinfo->resources[0];
+ iter->idx = 0;
+ } else {
+ iter->res++;
+ iter->idx++;
}
- return false;
+ return iter->idx < sinfo->resource_count
+ && iter->res->kind != RES_NONE;
}
-bool Sinfo::get_memregion_info(const char * const name,
- struct Memregion_info *memregion)
+const struct Sinfo::Resource_type *
+Sinfo::get_resource(const char *const name, enum Resource_kind kind) const
{
- int i;
+ struct iterator i = { nullptr, 0 };
- if (!check_magic())
- return false;
+ while (iterate_resources(&i))
+ if (i.res->kind == kind && names_equal(&i.res->name, name))
+ return i.res;
- for (i = 0; i < sinfo->resource_count; i++) {
- if (is_memregion(&sinfo->resources[i]) &&
- strcmp(sinfo->resources[i].name.data, name) == 0) {
- fill_memregion_data(i, memregion);
- return true;
- }
- }
- return false;
+ return nullptr;
}
-bool Sinfo::get_dev_info(const uint16_t sid, struct Dev_info *dev)
+const struct Sinfo::Device_type * Sinfo::get_device(const uint16_t sid) const
{
- int i;
+ struct iterator i = { nullptr, 0 };
- if (!check_magic())
- return false;
+ while (iterate_resources(&i))
+ if (i.res->kind == RES_DEVICE && i.res->data.dev.sid == sid)
+ return &i.res->data.dev;
- for (i = 0; i < sinfo->dev_info_count; i++) {
- if (sinfo->dev_info[i].sid == sid) {
- fill_dev_data(i, dev);
- return true;
- }
- }
- return false;
+ return nullptr;
}
-bool Sinfo::for_each_channel(Channel_cb func, void *data)
+bool Sinfo::for_each_resource(resource_cb func, void *data) const
{
- int i;
- struct Channel_info current_channel;
+ struct iterator i = { nullptr, 0 };
- if (!check_magic())
- return false;
+ while (iterate_resources(&i))
+ if (!func(i.res, data))
+ return 0;
- for (i = 0; i < sinfo->resource_count; i++) {
- if (is_channel(&sinfo->resources[i])) {
- fill_channel_data(i, ¤t_channel);
- if (!func(¤t_channel, data))
- return false;
- }
- }
- return true;
+ return 1;
}
-bool Sinfo::for_each_memregion(Memregion_cb func, void *data)
-{
- int i;
- struct Memregion_info current_region;
-
- if (!check_magic())
- return false;
-
- for (i = 0; i < sinfo->resource_count; i++) {
- if (is_memregion(&sinfo->resources[i])) {
- fill_memregion_data(i, ¤t_region);
- if (!func(¤t_region, data))
- return false;
- }
- }
- return true;
-}
-
-
-uint64_t Sinfo::get_tsc_khz(void)
+uint64_t Sinfo::get_tsc_khz(void) const
{
if (!check_magic())
return 0;
@@ -246,7 +205,7 @@ uint64_t Sinfo::get_tsc_khz(void)
}
-uint64_t Sinfo::get_sched_start(void)
+uint64_t Sinfo::get_sched_start(void) const
{
if (!check_magic())
return 0;
@@ -255,7 +214,7 @@ uint64_t Sinfo::get_sched_start(void)
}
-uint64_t Sinfo::get_sched_end(void)
+uint64_t Sinfo::get_sched_end(void) const
{
if (!check_magic())
return 0;
@@ -275,66 +234,10 @@ void Sinfo::log_status()
return;
}
+ const uint16_t count = sinfo->resource_count;
+
Genode::log("muen-sinfo: Subject name is '",
Sinfo::get_subject_name(), "'");
- Genode::log("muen-sinfo: Subject information exports ",
- sinfo->memregion_count, " memory region(s)");
- for_each_memregion(log_memregion, nullptr);
- Genode::log("muen-sinfo: Subject information exports ",
- sinfo->channel_info_count, " channel(s)");
- for_each_channel(log_channel, 0);
-}
-
-
-void Sinfo::fill_memregion_data(uint8_t idx, struct Memregion_info *region)
-{
- const struct resource_type resource = sinfo->resources[idx];
- const struct memregion_type memregion =
- sinfo->memregions[resource.memregion_idx - 1];
-
- memset(®ion->name, 0, MAX_NAME_LENGTH + 1);
- memcpy(®ion->name, resource.name.data, resource.name.length);
-
- memcpy(®ion->hash, memregion.hash, HASH_LENGTH);
-
- region->content = memregion.content;
- region->address = memregion.address;
- region->size = memregion.size;
- region->pattern = memregion.pattern;
- region->writable = memregion.flags & MEM_WRITABLE_FLAG;
- region->executable = memregion.flags & MEM_EXECUTABLE_FLAG;
-}
-
-
-void Sinfo::fill_channel_data(uint8_t idx, struct Channel_info *channel)
-{
- const struct resource_type resource = sinfo->resources[idx];
- const struct memregion_type memregion =
- sinfo->memregions[resource.memregion_idx - 1];
- const struct channel_info_type channel_info =
- sinfo->channels_info[resource.channel_info_idx - 1];
-
- memset(&channel->name, 0, MAX_NAME_LENGTH + 1);
- memcpy(&channel->name, resource.name.data, resource.name.length);
-
- channel->address = memregion.address;
- channel->size = memregion.size;
- channel->writable = memregion.flags & MEM_WRITABLE_FLAG;
-
- channel->has_event = channel_info.flags & CHAN_EVENT_FLAG;
- channel->event_number = channel_info.event;
- channel->has_vector = channel_info.flags & CHAN_VECTOR_FLAG;
- channel->vector = channel_info.vector;
-}
-
-
-void Sinfo::fill_dev_data(uint8_t idx, struct Dev_info *dev)
-{
- const struct dev_info_type dev_info = sinfo->dev_info[idx];
-
- dev->sid = dev_info.sid;
- dev->irte_start = dev_info.irte_start;
- dev->irq_start = dev_info.irq_start;
- dev->ir_count = dev_info.ir_count;
- dev->msi_capable = dev_info.flags & DEV_MSI_FLAG;
+ Genode::log("muen-sinfo: Subject exports ", count, " resources");
+ for_each_resource(log_resource, nullptr);
}
diff --git a/repos/ports/src/virtualbox/spec/muen/mem_region.h b/repos/ports/src/virtualbox/spec/muen/mem_region.h
index 6279d848a..f5dfda193 100644
--- a/repos/ports/src/virtualbox/spec/muen/mem_region.h
+++ b/repos/ports/src/virtualbox/spec/muen/mem_region.h
@@ -79,18 +79,23 @@ struct Mem_region : Genode::List::Element,
Genode::Rom_connection sinfo_rom(env, "subject_info_page");
Genode::Sinfo sinfo ((addr_t)env.rm().attach (sinfo_rom.dataspace()));
- struct Genode::Sinfo::Memregion_info region1, region4;
- if (!sinfo.get_memregion_info("vm_ram_1", ®ion1)) {
+ const struct Genode::Sinfo::Resource_type *region1
+ = sinfo.get_resource("vm_ram_1", Genode::Sinfo::RES_MEMORY);
+ const struct Genode::Sinfo::Resource_type *region4
+ = sinfo.get_resource("vm_ram_4", Genode::Sinfo::RES_MEMORY);
+
+ if (!region1) {
Genode::error("unable to retrieve vm_ram_1 region");
return 0;
}
- if (!sinfo.get_memregion_info("vm_ram_4", ®ion4)) {
+ if (!region4) {
Genode::error("unable to retrieve vm_ram_4 region");
return 0;
}
- cur_region.base = region1.address;
- cur_region.size = region4.address + region4.size - region1.address;
+ cur_region.base = region1->data.mem.address;
+ cur_region.size = region4->data.mem.address + region4->data.mem.size
+ - region1->data.mem.address;
counter++;
_clear = false;
diff --git a/repos/ports/src/virtualbox/spec/muen/sup.cc b/repos/ports/src/virtualbox/spec/muen/sup.cc
index 08cab05b7..39b43f3c3 100644
--- a/repos/ports/src/virtualbox/spec/muen/sup.cc
+++ b/repos/ports/src/virtualbox/spec/muen/sup.cc
@@ -113,17 +113,17 @@ bool setup_subject_state()
if (cur_state)
return true;
- struct Sinfo::Memregion_info region;
+ const struct Sinfo::Resource_type *region
+ = sinfo()->get_resource("monitor_state", Sinfo::RES_MEMORY);
- if (!sinfo()->get_memregion_info("monitor_state", ®ion)) {
+ if (!region) {
error("unable to retrieve monitor state region");
return false;
}
try {
- static Attached_io_mem_dataspace subject_ds(genode_env(),
- region.address,
- region.size);
+ static Attached_io_mem_dataspace subject_ds
+ (genode_env(), region->data.mem.address, region->data.mem.size);
cur_state = subject_ds.local_addr();
return true;
} catch (...) {
@@ -143,17 +143,17 @@ bool setup_subject_interrupts()
if (guest_interrupts)
return true;
- struct Sinfo::Memregion_info region;
+ const struct Sinfo::Resource_type *region
+ = sinfo()->get_resource("monitor_interrupts", Sinfo::RES_MEMORY);
- if (!sinfo()->get_memregion_info("monitor_interrupts", ®ion)) {
+ if (!region) {
error("unable to retrieve monitor interrupts region");
return false;
}
try {
- static Attached_io_mem_dataspace subject_intrs(genode_env(),
- region.address,
- region.size);
+ static Attached_io_mem_dataspace subject_intrs
+ (genode_env(), region->data.mem.address, region->data.mem.size);
static Guest_interrupts g((addr_t)subject_intrs.local_addr());
guest_interrupts = &g;
return true;