sculpt: inform user about incomplete pkg install

This commit handles the corner case where a package could be installed
successfully but the package's runtime definition is inconsistent with
the content delivered by the package's dependencies, i.e., the <content>
of the runtime file lists ROM modules that do not exist.

With this patch, the '+' menu shows the message "installed but
incomplete" whenever a package is in such a state.

Issue #3241
This commit is contained in:
Norman Feske 2019-03-21 12:21:05 +01:00
parent d6376f8188
commit 01cff3ce84
3 changed files with 52 additions and 10 deletions

View File

@ -22,6 +22,7 @@ namespace Sculpt {
static inline bool blueprint_missing (Xml_node, Path const &);
static inline bool blueprint_any_missing (Xml_node);
static inline bool blueprint_rom_missing (Xml_node, Path const &);
static inline bool blueprint_any_rom_missing(Xml_node);
}
@ -53,10 +54,21 @@ static inline bool Sculpt::blueprint_any_missing(Xml_node blueprint)
}
static inline bool Sculpt::blueprint_any_rom_missing(Xml_node blueprint)
/**
* Return true if one or more ROMs of the pkg 'path' are missing from the
* blueprint
*
* If 'path' is an invalid string, all pkgs of the blueprint are checked.
*/
static inline bool Sculpt::blueprint_rom_missing(Xml_node blueprint, Path const &path)
{
bool result = false;
blueprint.for_each_sub_node("pkg", [&] (Xml_node pkg) {
/* skip pkgs that we are not interested in */
if (path.valid() && pkg.attribute_value("path", Path()) != path)
return;
pkg.for_each_sub_node("missing_rom", [&] (Xml_node missing_rom) {
/* ld.lib.so is always taken from the base system */
@ -71,4 +83,10 @@ static inline bool Sculpt::blueprint_any_rom_missing(Xml_node blueprint)
return result;
}
static inline bool Sculpt::blueprint_any_rom_missing(Xml_node blueprint)
{
return blueprint_rom_missing(blueprint, Path());
}
#endif /* _DEPOT_QUERY_H_ */

View File

@ -201,11 +201,11 @@ void Popup_dialog::_gen_menu_elements(Xml_generator &xml) const
});
String<100> const text(Pretty(name), " " "(", version, ")",
installing ? " installing... " : "...");
installing ? " installing... " : "... ");
_gen_menu_entry(xml, id, text, selected);
if (selected && _pkg_missing && !installing) {
if (selected && !installing) {
_construction_info.with_construction([&] (Component const &component) {
@ -213,7 +213,25 @@ void Popup_dialog::_gen_menu_elements(Xml_generator &xml) const
gen_named_node(xml, "vbox", "vbox", [&] () {
if (_nic_ready()) {
/*
* Package is installed but content is missing
*
* This can happen when the pkg's runtime is
* inconsistent with the content contained in
* the pkg's archives.
*/
if (!_pkg_missing && _pkg_rom_missing) {
_gen_info_label(xml, "pad2", "");
_gen_info_label(xml, "path", component.path);
_gen_info_label(xml, "pad3", "");
xml.node("label", [&] () {
xml.attribute("text", "installed but incomplete"); });
}
/*
* Package is missing but can be installed
*/
else if (_pkg_missing && _nic_ready()) {
_gen_pkg_info(xml, component);
_gen_info_label(xml, "pad2", "");
@ -226,8 +244,13 @@ void Popup_dialog::_gen_menu_elements(Xml_generator &xml) const
});
});
});
}
} else {
/*
* Package is missing and we cannot do anything
* about it
*/
else if (_pkg_missing) {
_gen_info_label(xml, "pad2", "");
_gen_info_label(xml, "path", component.path);
_gen_info_label(xml, "pad3", "");

View File

@ -126,7 +126,8 @@ struct Sculpt::Popup_dialog
typedef Depot::Archive::User User;
User _selected_user { };
bool _pkg_missing = false;
bool _pkg_missing = false;
bool _pkg_rom_missing = false;
Component::Name _construction_name { };
@ -465,11 +466,11 @@ struct Sculpt::Popup_dialog
if (_state < PKG_REQUESTED)
return;
_pkg_missing = blueprint_missing(blueprint, construction.path)
|| blueprint_any_rom_missing(blueprint);
_pkg_rom_missing = blueprint_rom_missing(blueprint, construction.path);
_pkg_missing = blueprint_missing (blueprint, construction.path);
construction.try_apply_blueprint(blueprint);
if (construction.blueprint_known && !_pkg_missing)
if (construction.blueprint_known && !_pkg_missing && !_pkg_rom_missing)
_state = PKG_SHOWN;
generate();
@ -480,7 +481,7 @@ struct Sculpt::Popup_dialog
if (_state == DEPOT_SELECTION)
return true;
return _state >= PKG_REQUESTED && _pkg_missing;
return _state >= PKG_REQUESTED && (_pkg_missing || _pkg_rom_missing);
}
bool interested_in_file_operations() const