summaryrefslogtreecommitdiff
path: root/src/solver.c
diff options
context:
space:
mode:
authorTimo Teräs <timo.teras@iki.fi>2012-04-27 08:47:20 +0300
committerTimo Teräs <timo.teras@iki.fi>2012-04-27 08:47:20 +0300
commit29c7fb359eb058fef81a465271ec6384a15b9a2f (patch)
tree6f1ba6f850ae3197935d456298b6c76f2bf6e32f /src/solver.c
parent06323b3778418f923bd839850c5a10f2463c02b3 (diff)
downloadapk-tools-29c7fb359eb058fef81a465271ec6384a15b9a2f.tar.gz
apk-tools-29c7fb359eb058fef81a465271ec6384a15b9a2f.tar.bz2
apk-tools-29c7fb359eb058fef81a465271ec6384a15b9a2f.tar.xz
apk-tools-29c7fb359eb058fef81a465271ec6384a15b9a2f.zip
solver: fix backtracking with install_if dependencies
Diffstat (limited to 'src/solver.c')
-rw-r--r--src/solver.c37
1 files changed, 20 insertions, 17 deletions
diff --git a/src/solver.c b/src/solver.c
index f89b1e2..0417616 100644
--- a/src/solver.c
+++ b/src/solver.c
@@ -542,7 +542,7 @@ static void foreach_dependency(struct apk_solver_state *ss, struct apk_dependenc
func(ss, &deps->item[i]);
}
-static int install_if_missing(struct apk_solver_state *ss, struct apk_package *pkg)
+static int install_if_missing(struct apk_solver_state *ss, struct apk_package *pkg, struct apk_name *exclude)
{
int i, missing = 0;
@@ -550,7 +550,8 @@ static int install_if_missing(struct apk_solver_state *ss, struct apk_package *p
struct apk_dependency *dep = &pkg->install_if->item[i];
struct apk_name *name = dep->name;
- if (!name->ss.locked || !apk_dep_is_provided(dep, &name->ss.chosen))
+ if (name == exclude ||
+ !name->ss.locked || !apk_dep_is_provided(dep, &name->ss.chosen))
missing++;
}
@@ -674,13 +675,14 @@ static void trigger_install_if(struct apk_solver_state *ss,
{
struct apk_name *name = pkg->name;
- if (install_if_missing(ss, pkg) == 0) {
- dbg_printf("trigger_install_if: " PKG_VER_FMT " triggered\n",
- PKG_VER_PRINTF(pkg));
- name->ss.install_ifs++;
- inherit_package_state(ss->db, pkg, parent_pkg);
- promote_name(ss, name);
- }
+ if (install_if_missing(ss, pkg, NULL) != 0)
+ return;
+
+ dbg_printf("trigger_install_if: " PKG_VER_FMT " triggered\n",
+ PKG_VER_PRINTF(pkg));
+ name->ss.install_ifs++;
+ inherit_package_state(ss->db, pkg, parent_pkg);
+ promote_name(ss, name);
}
static void untrigger_install_if(struct apk_solver_state *ss,
@@ -689,13 +691,14 @@ static void untrigger_install_if(struct apk_solver_state *ss,
{
struct apk_name *name = pkg->name;
- if (install_if_missing(ss, pkg) != 1) {
- dbg_printf("untrigger_install_if: " PKG_VER_FMT " no longer triggered\n",
- PKG_VER_PRINTF(pkg));
- name->ss.install_ifs--;
- uninherit_package_state(ss->db, pkg, parent_pkg);
- demote_name(ss, name);
- }
+ if (install_if_missing(ss, pkg, parent_pkg->name) != 0)
+ return;
+
+ dbg_printf("untrigger_install_if: " PKG_VER_FMT " no longer triggered\n",
+ PKG_VER_PRINTF(pkg));
+ name->ss.install_ifs--;
+ uninherit_package_state(ss->db, pkg, parent_pkg);
+ demote_name(ss, name);
}
static inline void assign_name(
@@ -1254,7 +1257,7 @@ static int expand_branch(struct apk_solver_state *ss)
else
branching_point = BRANCH_YES;
} else if (name->ss.requirers == 0 && name->ss.install_ifs != 0 &&
- install_if_missing(ss, pkg0)) {
+ install_if_missing(ss, pkg0, NULL)) {
/* not directly required, and package specific
* install_if never triggered */
primary_decision = DECISION_EXCLUDE;