diff options
-rw-r--r-- | src/problems.c | 15 | ||||
-rw-r--r-- | src/rules.c | 42 | ||||
-rw-r--r-- | src/solver.c | 8 |
3 files changed, 56 insertions, 9 deletions
diff --git a/src/problems.c b/src/problems.c index 5cf42a3..afb6639 100644 --- a/src/problems.c +++ b/src/problems.c @@ -441,9 +441,6 @@ convertsolution(Solver *solv, Id why, Queue *solutionq) return; /* false alarm */ p = solv->installed->start + (why - solv->updaterules); - rr = solv->rules + solv->featurerules + (why - solv->updaterules); - if (!rr->p) - rr = solv->rules + why; if (solv->dupmap_all && solv->rules[why].p != p && solv->decisionmap[p] > 0) { /* distupgrade case, allow to keep old package */ @@ -453,6 +450,9 @@ convertsolution(Solver *solv, Id why, Queue *solutionq) } if (solv->decisionmap[p] > 0) return; /* false alarm, turned out we can keep the package */ + rr = solv->rules + solv->featurerules + (why - solv->updaterules); + if (!rr->p) + rr = solv->rules + why; if (rr->w2) { int mvrp = 0; /* multi-version replacement */ @@ -496,12 +496,19 @@ convertsolution(Solver *solv, Id why, Queue *solutionq) queue_push(solutionq, solv->ruletojob.elements[-p - solv->jobrules] + 1); return; } + if (solv->decisionmap[p] > 0) + { + /* disable best rule by keeping the old package */ + queue_push(solutionq, SOLVER_SOLUTION_BEST); + queue_push(solutionq, p); + return; + } rr = solv->rules + solv->featurerules + (p - solv->installed->start); if (!rr->p) rr = solv->rules + solv->updaterules + (p - solv->installed->start); mvrp = 0; /* multi-version replacement */ FOR_RULELITERALS(rp, dp, rr) - if (rp > 0 && solv->decisionmap[rp] > 0) + if (rp > 0 && solv->decisionmap[rp] > 0 && pool->solvables[rp].repo != solv->installed) { mvrp = rp; if (!(solv->noobsoletes.size && MAPTST(&solv->noobsoletes, rp))) diff --git a/src/rules.c b/src/rules.c index 277f771..4b50c57 100644 --- a/src/rules.c +++ b/src/rules.c @@ -1385,6 +1385,8 @@ solver_addduprules(Solver *solv, Map *addedmap) } if (!ip) solver_addrule(solv, -p, 0); /* no match, sorry */ + else + MAPSET(&solv->dupmap, p); /* for best rules processing */ } } else if (!MAPTST(&solv->dupmap, p)) @@ -2432,6 +2434,37 @@ solver_disablechoicerules(Solver *solv, Rule *r) } } +static void +prune_to_update_targets(Solver *solv, Id *cp, Queue *q) +{ + int i, j; + Id p, *cp2; + for (i = j = 0; i < q->count; i++) + { + p = q->elements[i]; + for (cp2 = cp; *cp2; cp2++) + if (*cp2 == p) + { + q->elements[j++] = p; + break; + } + } + queue_truncate(q, j); +} + +static void +prune_to_dup_packages(Solver *solv, Id p, Queue *q) +{ + int i, j; + for (i = j = 0; i < q->count; i++) + { + Id p = q->elements[i]; + if (MAPTST(&solv->dupmap, p)) + q->elements[j++] = p; + } + queue_truncate(q, j); +} + void solver_addbestrules(Solver *solv, int havebestinstalljobs) { @@ -2518,8 +2551,11 @@ solver_addbestrules(Solver *solv, int havebestinstalljobs) if (p2 > 0) queue_push(&q, p2); } + if (solv->update_targets && solv->update_targets->elements[p - installed->start]) + prune_to_update_targets(solv, solv->update_targets->elements + solv->update_targets->elements[p - installed->start], &q); + if (solv->dupinvolvedmap.size && MAPTST(&solv->dupinvolvedmap, p)) + prune_to_dup_packages(solv, p, &q); /* select best packages, just look at prio and version */ - oldcnt = q.count; policy_filter_unwanted(solv, &q, POLICY_MODE_RECOMMEND); if (!q.count) continue; /* orphaned */ @@ -2534,6 +2570,10 @@ solver_addbestrules(Solver *solv, int havebestinstalljobs) FOR_RULELITERALS(p2, pp2, r) if (p2 > 0) queue_push(&q2, p2); + if (solv->update_targets && solv->update_targets->elements[p - installed->start]) + prune_to_update_targets(solv, solv->update_targets->elements + solv->update_targets->elements[p - installed->start], &q2); + if (solv->dupinvolvedmap.size && MAPTST(&solv->dupinvolvedmap, p)) + prune_to_dup_packages(solv, p, &q); policy_filter_unwanted(solv, &q2, POLICY_MODE_RECOMMEND); for (j = 0; j < q2.count; j++) queue_pushunique(&q, q2.elements[j]); diff --git a/src/solver.c b/src/solver.c index 6e2acba..9880442 100644 --- a/src/solver.c +++ b/src/solver.c @@ -3237,10 +3237,7 @@ solver_solve(Solver *solv, Queue *job) solv->infarchrules = solv->infarchrules_end = solv->nrules; if (hasdupjob) - { - solver_addduprules(solv, &addedmap); - solver_freedupmaps(solv); /* no longer needed */ - } + solver_addduprules(solv, &addedmap); else solv->duprules = solv->duprules_end = solv->nrules; @@ -3249,6 +3246,9 @@ solver_solve(Solver *solv, Queue *job) else solv->bestrules = solv->bestrules_end = solv->nrules; + if (hasdupjob) + solver_freedupmaps(solv); /* no longer needed */ + if (1) solver_addchoicerules(solv); else |