summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--discover/device-handler.c62
-rw-r--r--discover/device-handler.h2
-rw-r--r--discover/parser.c4
3 files changed, 62 insertions, 6 deletions
diff --git a/discover/device-handler.c b/discover/device-handler.c
index c0f6066..a8df295 100644
--- a/discover/device-handler.c
+++ b/discover/device-handler.c
@@ -29,6 +29,8 @@ struct device_handler {
struct discover_device **devices;
unsigned int n_devices;
+
+ struct list unresolved_boot_options;
};
static bool resource_is_resolved(struct resource *res)
@@ -46,6 +48,25 @@ static bool __attribute__((used)) boot_option_is_resolved(
resource_is_resolved(opt->icon);
}
+static bool resource_resolve(struct resource *res, struct parser *parser,
+ struct device_handler *handler)
+{
+ if (resource_is_resolved(res))
+ return true;
+
+ parser->resolve_resource(handler, res);
+
+ return res->resolved;
+}
+
+static bool boot_option_resolve(struct discover_boot_option *opt,
+ struct device_handler *handler)
+{
+ return resource_resolve(opt->boot_image, opt->source, handler) &&
+ resource_resolve(opt->initrd, opt->source, handler) &&
+ resource_resolve(opt->icon, opt->source, handler);
+}
+
static void boot_option_finalise(struct discover_boot_option *opt)
{
assert(boot_option_is_resolved(opt));
@@ -63,6 +84,25 @@ static void boot_option_finalise(struct discover_boot_option *opt)
opt->option->icon_file = opt->icon->url->full;
}
+static void process_boot_option_queue(struct device_handler *handler)
+{
+ struct discover_boot_option *opt, *tmp;
+
+ list_for_each_entry_safe(&handler->unresolved_boot_options,
+ opt, tmp, list) {
+
+ if (!boot_option_resolve(opt, handler))
+ continue;
+
+ list_remove(&opt->list);
+ list_add(&opt->device->boot_options, &opt->list);
+ talloc_steal(opt->device, opt);
+ boot_option_finalise(opt);
+ discover_server_notify_boot_option_add(handler->server,
+ opt->option);
+ }
+}
+
/**
* context_commit - Commit a temporary discovery context to the handler,
* and notify the clients about any new options / devices
@@ -91,23 +131,34 @@ static void context_commit(struct device_handler *handler,
talloc_steal(handler, dev);
discover_server_notify_device_add(handler->server, dev->device);
+
+ /* this new device might be able to resolve existing boot
+ * options */
+ process_boot_option_queue(handler);
}
/* move boot options from the context to the device */
list_for_each_entry_safe(&ctx->boot_options, opt, tmp, list) {
list_remove(&opt->list);
- list_add(&dev->boot_options, &opt->list);
- talloc_steal(dev, opt);
- boot_option_finalise(opt);
- discover_server_notify_boot_option_add(handler->server,
- opt->option);
+
+ if (boot_option_resolve(opt, handler)) {
+ list_add(&dev->boot_options, &opt->list);
+ talloc_steal(dev, opt);
+ boot_option_finalise(opt);
+ discover_server_notify_boot_option_add(handler->server,
+ opt->option);
+ } else {
+ list_add(&handler->unresolved_boot_options, &opt->list);
+ talloc_steal(handler, opt);
+ }
}
}
void discover_context_add_boot_option(struct discover_context *ctx,
struct discover_boot_option *boot_option)
{
+ boot_option->source = ctx->parser;
list_add(&ctx->boot_options, &boot_option->list);
talloc_steal(ctx, boot_option);
}
@@ -437,6 +488,7 @@ struct device_handler *device_handler_init(struct discover_server *server,
handler->n_devices = 0;
handler->server = server;
handler->dry_run = dry_run;
+ list_init(&handler->unresolved_boot_options);
/* set up our mount point base */
pb_mkdir_recursive(mount_base());
diff --git a/discover/device-handler.h b/discover/device-handler.h
index 5dead24..be55f73 100644
--- a/discover/device-handler.h
+++ b/discover/device-handler.h
@@ -27,6 +27,7 @@ struct discover_device {
};
struct discover_boot_option {
+ struct parser *source;
struct discover_device *device;
struct boot_option *option;
struct list_item list;
@@ -38,6 +39,7 @@ struct discover_boot_option {
struct discover_context {
+ struct parser *parser;
struct event *event;
struct discover_device *device;
struct list boot_options;
diff --git a/discover/parser.c b/discover/parser.c
index 462d614..0df8a73 100644
--- a/discover/parser.c
+++ b/discover/parser.c
@@ -18,7 +18,7 @@ struct parser __kboot_parser;
struct parser __native_parser;
struct parser __yaboot_parser;
-static const struct parser *const parsers[] = {
+static struct parser *const parsers[] = {
// &__native_parser,
&__kboot_parser,
&__grub2_parser,
@@ -116,8 +116,10 @@ void iterate_parsers(struct discover_context *ctx)
for (i = 0; parsers[i]; i++) {
pb_log("\ttrying parser '%s'\n", parsers[i]->name);
+ ctx->parser = parsers[i];
iterate_parser_files(ctx, parsers[i]);
}
+ ctx->parser = NULL;
}
void parser_init(void)
OpenPOWER on IntegriCloud