aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorAvatar Ciaran McCreesh <ciaran.mccreesh@googlemail.com> 2010-08-08 13:36:12 +0100
committerAvatar Ciaran McCreesh <ciaran.mccreesh@googlemail.com> 2010-08-08 13:36:12 +0100
commit391a11571d99f0b9ccb030381c32dd9a36721f37 (patch)
treec28d61924211d4319fc38c46eabd3b4ed3db9fcb
parent6f0d1e67b6042352af6662342bc3e98840d7892a (diff)
downloadpaludis-391a11571d99f0b9ccb030381c32dd9a36721f37.tar.gz
paludis-391a11571d99f0b9ccb030381c32dd9a36721f37.tar.xz
GetUseExistingNothingHelper
-rw-r--r--paludis/resolver/Makefile.am2
-rw-r--r--paludis/resolver/destination_utils-fwd.hh1
-rw-r--r--paludis/resolver/destination_utils.cc8
-rw-r--r--paludis/resolver/get_use_existing_nothing_helper-fwd.hh31
-rw-r--r--paludis/resolver/get_use_existing_nothing_helper.cc231
-rw-r--r--paludis/resolver/get_use_existing_nothing_helper.hh62
-rw-r--r--paludis/resolver/resolver_TEST_any.cc1
-rw-r--r--paludis/resolver/resolver_TEST_blockers.cc1
-rw-r--r--paludis/resolver/resolver_TEST_continue_on_failure.cc18
-rw-r--r--paludis/resolver/resolver_TEST_cycles.cc34
-rw-r--r--paludis/resolver/resolver_TEST_purges.cc29
-rw-r--r--paludis/resolver/resolver_test.cc12
-rw-r--r--paludis/resolver/resolver_test.hh7
-rw-r--r--src/clients/cave/resolve_common.cc200
14 files changed, 392 insertions, 245 deletions
diff --git a/paludis/resolver/Makefile.am b/paludis/resolver/Makefile.am
index 6e9453a..b49ff50 100644
--- a/paludis/resolver/Makefile.am
+++ b/paludis/resolver/Makefile.am
@@ -49,6 +49,7 @@ noinst_HEADERS = \
get_constraints_for_purge_helper.hh get_constraints_for_dependent_helper-fwd.hh \
get_constraints_for_via_binary_helper.hh get_constraints_for_via_binary_helper-fwd.hh \
get_destination_types_for_error_helper.hh get_destination_types_for_error_helper-fwd.hh \
+ get_use_existing_nothing_helper.hh get_use_existing_nothing_helper-fwd.hh \
interest_in_spec_helper.hh interest_in_spec_helper-fwd.hh \
job.hh job-fwd.hh \
job_list.hh job_list-fwd.hh \
@@ -105,6 +106,7 @@ libpaludisresolver_a_SOURCES = \
get_constraints_for_purge_helper.cc \
get_constraints_for_via_binary_helper.cc \
get_destination_types_for_error_helper.cc \
+ get_use_existing_nothing_helper.cc \
interest_in_spec_helper.cc \
job.cc \
job_list.cc \
diff --git a/paludis/resolver/destination_utils-fwd.hh b/paludis/resolver/destination_utils-fwd.hh
index 459d80f5..95108f0 100644
--- a/paludis/resolver/destination_utils-fwd.hh
+++ b/paludis/resolver/destination_utils-fwd.hh
@@ -28,6 +28,7 @@ namespace paludis
namespace resolver
{
bool can_make_binary_for(const std::shared_ptr<const PackageID> & id) PALUDIS_ATTRIBUTE((warn_unused_result)) PALUDIS_VISIBLE;
+ bool can_chroot(const std::shared_ptr<const PackageID> & id) PALUDIS_ATTRIBUTE((warn_unused_result)) PALUDIS_VISIBLE;
}
}
diff --git a/paludis/resolver/destination_utils.cc b/paludis/resolver/destination_utils.cc
index 5067062..b58804a 100644
--- a/paludis/resolver/destination_utils.cc
+++ b/paludis/resolver/destination_utils.cc
@@ -32,3 +32,11 @@ paludis::resolver::can_make_binary_for(const std::shared_ptr<const PackageID> &
return id->behaviours_key()->value()->end() == id->behaviours_key()->value()->find("unbinaryable");
}
+bool
+paludis::resolver::can_chroot(const std::shared_ptr<const PackageID> & id)
+{
+ if (! id->behaviours_key())
+ return true;
+ return id->behaviours_key()->value()->end() == id->behaviours_key()->value()->find("unchrootable");
+}
+
diff --git a/paludis/resolver/get_use_existing_nothing_helper-fwd.hh b/paludis/resolver/get_use_existing_nothing_helper-fwd.hh
new file mode 100644
index 0000000..8d07e49
--- /dev/null
+++ b/paludis/resolver/get_use_existing_nothing_helper-fwd.hh
@@ -0,0 +1,31 @@
+/* vim: set sw=4 sts=4 et foldmethod=syntax : */
+
+/*
+ * Copyright (c) 2010 Ciaran McCreesh
+ *
+ * This file is part of the Paludis package manager. Paludis is free software;
+ * you can redistribute it and/or modify it under the terms of the GNU General
+ * Public License version 2, as published by the Free Software Foundation.
+ *
+ * Paludis is distributed in the hope that it will be useful, but WITHOUT ANY
+ * WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS
+ * FOR A PARTICULAR PURPOSE. See the GNU General Public License for more
+ * details.
+ *
+ * You should have received a copy of the GNU General Public License along with
+ * this program; if not, write to the Free Software Foundation, Inc., 59 Temple
+ * Place, Suite 330, Boston, MA 02111-1307 USA
+ */
+
+#ifndef PALUDIS_GUARD_PALUDIS_RESOLVER_GET_USE_EXISTING_NOTHING_HELPER_FWD_HH
+#define PALUDIS_GUARD_PALUDIS_RESOLVER_GET_USE_EXISTING_NOTHING_HELPER_FWD_HH 1
+
+namespace paludis
+{
+ namespace resolver
+ {
+ struct GetUseExistingNothingHelper;
+ }
+}
+
+#endif
diff --git a/paludis/resolver/get_use_existing_nothing_helper.cc b/paludis/resolver/get_use_existing_nothing_helper.cc
new file mode 100644
index 0000000..4862805
--- /dev/null
+++ b/paludis/resolver/get_use_existing_nothing_helper.cc
@@ -0,0 +1,231 @@
+/* vim: set sw=4 sts=4 et foldmethod=syntax : */
+
+/*
+ * Copyright (c) 2010 Ciaran McCreesh
+ *
+ * This file is part of the Paludis package manager. Paludis is free software;
+ * you can redistribute it and/or modify it under the terms of the GNU General
+ * Public License version 2, as published by the Free Software Foundation.
+ *
+ * Paludis is distributed in the hope that it will be useful, but WITHOUT ANY
+ * WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS
+ * FOR A PARTICULAR PURPOSE. See the GNU General Public License for more
+ * details.
+ *
+ * You should have received a copy of the GNU General Public License along with
+ * this program; if not, write to the Free Software Foundation, Inc., 59 Temple
+ * Place, Suite 330, Boston, MA 02111-1307 USA
+ */
+
+#include <paludis/resolver/get_use_existing_nothing_helper.hh>
+#include <paludis/resolver/reason.hh>
+#include <paludis/resolver/constraint.hh>
+#include <paludis/resolver/resolvent.hh>
+#include <paludis/resolver/resolution.hh>
+#include <paludis/resolver/decision.hh>
+#include <paludis/resolver/labels_classifier.hh>
+#include <paludis/resolver/match_qpns.hh>
+#include <paludis/resolver/destination_utils.hh>
+#include <paludis/util/pimp-impl.hh>
+#include <paludis/util/stringify.hh>
+#include <paludis/dep_spec.hh>
+#include <paludis/selection.hh>
+#include <paludis/generator.hh>
+#include <paludis/filter.hh>
+#include <paludis/filtered_generator.hh>
+#include <paludis/environment.hh>
+#include <list>
+
+using namespace paludis;
+using namespace paludis::resolver;
+
+namespace paludis
+{
+ template <>
+ struct Imp<GetUseExistingNothingHelper>
+ {
+ const Environment * const env;
+ std::list<PackageDepSpec> with_specs;
+ std::list<PackageDepSpec> without_specs;
+ UseExisting use_existing_for_dependencies;
+ UseExisting use_existing_for_targets;
+ UseExisting use_existing_for_set_targets;
+
+ Imp(const Environment * const e) :
+ env(e),
+ use_existing_for_dependencies(ue_if_possible),
+ use_existing_for_targets(ue_never),
+ use_existing_for_set_targets(ue_if_same)
+ {
+ }
+ };
+}
+
+GetUseExistingNothingHelper::GetUseExistingNothingHelper(const Environment * const e) :
+ Pimp<GetUseExistingNothingHelper>(e)
+{
+}
+
+GetUseExistingNothingHelper::~GetUseExistingNothingHelper() = default;
+
+void
+GetUseExistingNothingHelper::add_with_spec(const PackageDepSpec & spec)
+{
+ _imp->with_specs.push_back(spec);
+}
+
+void
+GetUseExistingNothingHelper::add_without_spec(const PackageDepSpec & spec)
+{
+ _imp->without_specs.push_back(spec);
+}
+
+void
+GetUseExistingNothingHelper::set_use_existing_for_dependencies(const UseExisting v)
+{
+ _imp->use_existing_for_dependencies = v;
+}
+
+void
+GetUseExistingNothingHelper::set_use_existing_for_targets(const UseExisting v)
+{
+ _imp->use_existing_for_targets = v;
+}
+
+void
+GetUseExistingNothingHelper::set_use_existing_for_set_targets(const UseExisting v)
+{
+ _imp->use_existing_for_set_targets = v;
+}
+
+namespace
+{
+ bool use_existing_from_withish(
+ const Environment * const env,
+ const QualifiedPackageName & name,
+ const std::list<PackageDepSpec> & list)
+ {
+ for (auto l(list.begin()), l_end(list.end()) ;
+ l != l_end ; ++l)
+ if (match_qpns(*env, *l, name))
+ return true;
+ return false;
+ }
+
+ struct UseExistingVisitor
+ {
+ const Environment * const env;
+ const bool from_set;
+ const Resolvent resolvent;
+ const UseExisting use_existing_for_dependencies;
+ const UseExisting use_existing_for_targets;
+ const UseExisting use_existing_for_set_targets;
+
+ bool creating_and_no_appropriate_ids() const
+ {
+ bool (* can)(const std::shared_ptr<const PackageID> &)(0);
+ switch (resolvent.destination_type())
+ {
+ case dt_install_to_slash:
+ return false;
+
+ case dt_create_binary:
+ can = &can_make_binary_for;
+ break;
+
+ case dt_install_to_chroot:
+ can = &can_chroot;
+ break;
+
+ case last_dt:
+ break;
+ }
+
+ if (! can)
+ throw InternalError(PALUDIS_HERE, "unhandled dt");
+
+ auto origin_ids((*env)[selection::AllVersionsSorted(
+ generator::Package(resolvent.package()) |
+ make_slot_filter(resolvent) |
+ filter::SupportsAction<InstallAction>() |
+ filter::NotMasked()
+ )]);
+ if (origin_ids->empty())
+ return false;
+ else
+ {
+ for (auto i(origin_ids->begin()), i_end(origin_ids->end()) ;
+ i != i_end ; ++i)
+ if ((*can)(*i))
+ return false;
+
+ return true;
+ }
+ }
+
+ std::pair<UseExisting, bool> visit(const DependencyReason &) const
+ {
+ return std::make_pair(use_existing_for_dependencies, creating_and_no_appropriate_ids());
+ }
+
+ std::pair<UseExisting, bool> visit(const TargetReason &) const
+ {
+ return std::make_pair(from_set ? use_existing_for_set_targets : use_existing_for_targets,
+ creating_and_no_appropriate_ids());
+ }
+
+ std::pair<UseExisting, bool> visit(const DependentReason &) const
+ {
+ return std::make_pair(ue_if_possible, false);
+ }
+
+ std::pair<UseExisting, bool> visit(const WasUsedByReason &) const
+ {
+ return std::make_pair(ue_if_possible, false);
+ }
+
+ std::pair<UseExisting, bool> visit(const PresetReason &) const
+ {
+ return std::make_pair(ue_if_possible, false);
+ }
+
+ std::pair<UseExisting, bool> visit(const ViaBinaryReason &) const
+ {
+ return std::make_pair(ue_if_possible, false);
+ }
+
+ std::pair<UseExisting, bool> visit(const SetReason & r) const
+ {
+ UseExistingVisitor v{env, true, resolvent, use_existing_for_dependencies, use_existing_for_targets, use_existing_for_set_targets};
+ return r.reason_for_set()->accept_returning<std::pair<UseExisting, bool> >(v);
+ }
+
+ std::pair<UseExisting, bool> visit(const LikeOtherDestinationTypeReason & r) const
+ {
+ UseExistingVisitor v{env, from_set, resolvent, use_existing_for_dependencies, use_existing_for_targets, use_existing_for_set_targets};
+ return r.reason_for_other()->accept_returning<std::pair<UseExisting, bool> >(v);
+ }
+ };
+}
+
+std::pair<UseExisting, bool>
+GetUseExistingNothingHelper::operator() (
+ const std::shared_ptr<const Resolution> & resolution,
+ const PackageDepSpec & spec,
+ const std::shared_ptr<const Reason> & reason) const
+{
+ if (spec.package_ptr())
+ {
+ if (use_existing_from_withish(_imp->env, *spec.package_ptr(), _imp->without_specs))
+ return std::make_pair(ue_if_possible, true);
+ if (use_existing_from_withish(_imp->env, *spec.package_ptr(), _imp->with_specs))
+ return std::make_pair(ue_never, false);
+ }
+
+ UseExistingVisitor v{_imp->env, false, resolution->resolvent(), _imp->use_existing_for_dependencies, _imp->use_existing_for_targets,
+ _imp->use_existing_for_set_targets};
+ return reason->accept_returning<std::pair<UseExisting, bool> >(v);
+}
+
+template class Pimp<GetUseExistingNothingHelper>;
+
diff --git a/paludis/resolver/get_use_existing_nothing_helper.hh b/paludis/resolver/get_use_existing_nothing_helper.hh
new file mode 100644
index 0000000..cf709b3
--- /dev/null
+++ b/paludis/resolver/get_use_existing_nothing_helper.hh
@@ -0,0 +1,62 @@
+/* vim: set sw=4 sts=4 et foldmethod=syntax : */
+
+/*
+ * Copyright (c) 2010 Ciaran McCreesh
+ *
+ * This file is part of the Paludis package manager. Paludis is free software;
+ * you can redistribute it and/or modify it under the terms of the GNU General
+ * Public License version 2, as published by the Free Software Foundation.
+ *
+ * Paludis is distributed in the hope that it will be useful, but WITHOUT ANY
+ * WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS
+ * FOR A PARTICULAR PURPOSE. See the GNU General Public License for more
+ * details.
+ *
+ * You should have received a copy of the GNU General Public License along with
+ * this program; if not, write to the Free Software Foundation, Inc., 59 Temple
+ * Place, Suite 330, Boston, MA 02111-1307 USA
+ */
+
+#ifndef PALUDIS_GUARD_PALUDIS_RESOLVER_GET_USE_EXISTING_NOTHING_HELPER_HH
+#define PALUDIS_GUARD_PALUDIS_RESOLVER_GET_USE_EXISTING_NOTHING_HELPER_HH 1
+
+#include <paludis/resolver/get_use_existing_nothing_helper-fwd.hh>
+#include <paludis/resolver/resolution-fwd.hh>
+#include <paludis/resolver/use_existing-fwd.hh>
+#include <paludis/resolver/reason-fwd.hh>
+#include <paludis/util/pimp.hh>
+#include <paludis/util/attributes.hh>
+#include <paludis/package_id-fwd.hh>
+#include <paludis/dep_spec-fwd.hh>
+#include <paludis/environment-fwd.hh>
+#include <memory>
+
+namespace paludis
+{
+ namespace resolver
+ {
+ class PALUDIS_VISIBLE GetUseExistingNothingHelper :
+ private Pimp<GetUseExistingNothingHelper>
+ {
+ public:
+ explicit GetUseExistingNothingHelper(const Environment * const);
+ ~GetUseExistingNothingHelper();
+
+ void add_with_spec(const PackageDepSpec &);
+ void add_without_spec(const PackageDepSpec &);
+
+ void set_use_existing_for_dependencies(const UseExisting);
+ void set_use_existing_for_targets(const UseExisting);
+ void set_use_existing_for_set_targets(const UseExisting);
+
+ std::pair<UseExisting, bool> operator() (
+ const std::shared_ptr<const Resolution> &,
+ const PackageDepSpec &,
+ const std::shared_ptr<const Reason> &) const;
+ };
+ }
+
+ extern template class Pimp<resolver::GetUseExistingNothingHelper>;
+}
+
+#endif
diff --git a/paludis/resolver/resolver_TEST_any.cc b/paludis/resolver/resolver_TEST_any.cc
index 8e17997..60ba1d1 100644
--- a/paludis/resolver/resolver_TEST_any.cc
+++ b/paludis/resolver/resolver_TEST_any.cc
@@ -60,6 +60,7 @@ namespace
ResolverAnyTestCase(const std::string & s) :
ResolverTestCase("any", s, "exheres-0", "exheres")
{
+ get_use_existing_nothing_helper.set_use_existing_for_dependencies(ue_never);
}
};
}
diff --git a/paludis/resolver/resolver_TEST_blockers.cc b/paludis/resolver/resolver_TEST_blockers.cc
index 322b03e..d6ea458 100644
--- a/paludis/resolver/resolver_TEST_blockers.cc
+++ b/paludis/resolver/resolver_TEST_blockers.cc
@@ -58,6 +58,7 @@ namespace
ResolverBlockersTestCase(const std::string & s, const std::string & e = "exheres-0") :
ResolverTestCase("blockers", s, e, "exheres")
{
+ get_use_existing_nothing_helper.set_use_existing_for_dependencies(ue_never);
}
};
}
diff --git a/paludis/resolver/resolver_TEST_continue_on_failure.cc b/paludis/resolver/resolver_TEST_continue_on_failure.cc
index 10a9119..ab9e63f 100644
--- a/paludis/resolver/resolver_TEST_continue_on_failure.cc
+++ b/paludis/resolver/resolver_TEST_continue_on_failure.cc
@@ -67,15 +67,6 @@ namespace
}
};
- std::pair<UseExisting, bool>
- use_existing_if_same(
- const std::shared_ptr<const Resolution> &,
- const PackageDepSpec &,
- const std::shared_ptr<const Reason> &)
- {
- return std::make_pair(ue_if_same, false);
- }
-
std::string
stringify_req(const JobRequirement & r)
{
@@ -104,14 +95,9 @@ namespace test_cases
if (d)
install("continue-on-failure", "direct-dep", "0");
install("continue-on-failure", "unchanged-dep", "1")->build_dependencies_key()->set_from_string("continue-on-failure/indirect-dep");
- }
- virtual ResolverFunctions get_resolver_functions(InitialConstraints & initial_constraints)
- {
- ResolverFunctions result(ResolverContinueOnFailureTestCase::get_resolver_functions(initial_constraints));
- result.get_use_existing_nothing_fn() = std::bind(&use_existing_if_same, std::placeholders::_1,
- std::placeholders::_2, std::placeholders::_3);
- return result;
+ get_use_existing_nothing_helper.set_use_existing_for_dependencies(ue_if_same);
+ get_use_existing_nothing_helper.set_use_existing_for_targets(ue_if_same);
}
void run()
diff --git a/paludis/resolver/resolver_TEST_cycles.cc b/paludis/resolver/resolver_TEST_cycles.cc
index 8744040..75e55d9 100644
--- a/paludis/resolver/resolver_TEST_cycles.cc
+++ b/paludis/resolver/resolver_TEST_cycles.cc
@@ -58,17 +58,9 @@ namespace
ResolverCyclesTestCase(const std::string & s) :
ResolverTestCase("cycles", s, "exheres-0", "exheres")
{
+ get_use_existing_nothing_helper.set_use_existing_for_dependencies(ue_never);
}
};
-
- std::pair<UseExisting, bool>
- use_existing_if_same(
- const std::shared_ptr<const Resolution> &,
- const PackageDepSpec &,
- const std::shared_ptr<const Reason> &)
- {
- return std::make_pair(ue_if_same, false);
- }
}
namespace test_cases
@@ -80,14 +72,8 @@ namespace test_cases
{
install("no-changes", "dep-a", "1")->build_dependencies_key()->set_from_string("no-changes/dep-b");
install("no-changes", "dep-b", "1")->build_dependencies_key()->set_from_string("no-changes/dep-a");
- }
- virtual ResolverFunctions get_resolver_functions(InitialConstraints & initial_constraints)
- {
- ResolverFunctions result(ResolverCyclesTestCase::get_resolver_functions(initial_constraints));
- result.get_use_existing_nothing_fn() = std::bind(&use_existing_if_same, std::placeholders::_1,
- std::placeholders::_2, std::placeholders::_3);
- return result;
+ get_use_existing_nothing_helper.set_use_existing_for_dependencies(ue_if_same);
}
void run()
@@ -285,14 +271,8 @@ namespace test_cases
{
if (-1 != installed_version)
install(cat, "dep", stringify(installed_version));
- }
- virtual ResolverFunctions get_resolver_functions(InitialConstraints & initial_constraints)
- {
- ResolverFunctions result(ResolverCyclesTestCase::get_resolver_functions(initial_constraints));
- result.get_use_existing_nothing_fn() = std::bind(&use_existing_if_same, std::placeholders::_1,
- std::placeholders::_2, std::placeholders::_3);
- return result;
+ get_use_existing_nothing_helper.set_use_existing_for_dependencies(ue_if_same);
}
void run()
@@ -354,14 +334,8 @@ namespace test_cases
ResolverCyclesTestCase("cycle deps")
{
install("cycle-deps", "dep-g", "1")->build_dependencies_key()->set_from_string("cycle-deps/dep-c");
- }
- virtual ResolverFunctions get_resolver_functions(InitialConstraints & initial_constraints)
- {
- ResolverFunctions result(ResolverCyclesTestCase::get_resolver_functions(initial_constraints));
- result.get_use_existing_nothing_fn() = std::bind(&use_existing_if_same, std::placeholders::_1,
- std::placeholders::_2, std::placeholders::_3);
- return result;
+ get_use_existing_nothing_helper.set_use_existing_for_dependencies(ue_if_same);
}
void run()
diff --git a/paludis/resolver/resolver_TEST_purges.cc b/paludis/resolver/resolver_TEST_purges.cc
index 1ca4b93..be4a6fa 100644
--- a/paludis/resolver/resolver_TEST_purges.cc
+++ b/paludis/resolver/resolver_TEST_purges.cc
@@ -61,18 +61,6 @@ namespace
{
}
};
-
- std::pair<UseExisting, bool>
- use_existing_if_possible_except_target(
- const std::shared_ptr<const Resolution> &,
- const PackageDepSpec & s,
- const std::shared_ptr<const Reason> &)
- {
- if (s.package_ptr() && s.package_ptr()->package() == PackageNamePart("target"))
- return std::make_pair(ue_never, false);
- else
- return std::make_pair(ue_if_possible, false);
- }
}
namespace test_cases
@@ -91,14 +79,8 @@ namespace test_cases
install("purges", "unrelated", "0")->build_dependencies_key()->set_from_string("purges/unrelated-dep");
get_constraints_for_purge_helper.add_purge_spec(parse_user_package_dep_spec("purges/old-dep", &env, { }));
- }
- virtual ResolverFunctions get_resolver_functions(InitialConstraints & initial_constraints)
- {
- ResolverFunctions result(ResolverPurgesTestCase::get_resolver_functions(initial_constraints));
- result.get_use_existing_nothing_fn() = std::bind(&use_existing_if_possible_except_target, std::placeholders::_1,
- std::placeholders::_2, std::placeholders::_3);
- return result;
+ get_use_existing_nothing_helper.set_use_existing_for_dependencies(ue_if_possible);
}
void run()
@@ -135,15 +117,8 @@ namespace test_cases
install("star-slot-purges", "uses", "1")->build_dependencies_key()->set_from_string("star-slot-purges/target:*");
get_constraints_for_purge_helper.add_purge_spec(parse_user_package_dep_spec("star-slot-purges/target", &env, { }));
- }
- virtual ResolverFunctions get_resolver_functions(InitialConstraints & initial_constraints)
- {
- ResolverFunctions result(ResolverPurgesTestCase::get_resolver_functions(initial_constraints));
- result.get_use_existing_nothing_fn() = std::bind(&use_existing_if_possible_except_target, std::placeholders::_1,
- std::placeholders::_2, std::placeholders::_3);
- result.confirm_fn() = std::bind(return_literal_function(false));
- return result;
+ get_use_existing_nothing_helper.set_use_existing_for_dependencies(ue_if_possible);
}
void run()
diff --git a/paludis/resolver/resolver_test.cc b/paludis/resolver/resolver_test.cc
index baed130..9dbbca9 100644
--- a/paludis/resolver/resolver_test.cc
+++ b/paludis/resolver/resolver_test.cc
@@ -133,15 +133,6 @@ namespace
#endif
}
-std::pair<UseExisting, bool>
-paludis::resolver::resolver_test::get_use_existing_nothing_fn(
- const std::shared_ptr<const Resolution> &,
- const PackageDepSpec &,
- const std::shared_ptr<const Reason> &)
-{
- return std::make_pair(ue_never, false);
-}
-
ResolverTestCase::ResolverTestCase(const std::string & t, const std::string & s, const std::string & e,
const std::string & l) :
TestCase(s),
@@ -155,6 +146,7 @@ ResolverTestCase::ResolverTestCase(const std::string & t, const std::string & s,
get_constraints_for_purge_helper(&env),
get_constraints_for_via_binary_helper(&env),
get_destination_types_for_error_helper(&env),
+ get_use_existing_nothing_helper(&env),
interest_in_spec_helper(&env),
make_destination_filtered_generator_helper(&env),
make_origin_filtered_generator_helper(&env),
@@ -227,7 +219,7 @@ ResolverTestCase::get_resolver_functions(InitialConstraints & initial_constraint
std::placeholders::_1),
n::get_resolvents_for_fn() = std::bind(&get_resolvents_for_fn, &env, std::placeholders::_1,
std::placeholders::_2, std::placeholders::_3),
- n::get_use_existing_nothing_fn() = &get_use_existing_nothing_fn,
+ n::get_use_existing_nothing_fn() = std::cref(get_use_existing_nothing_helper),
n::interest_in_spec_fn() = std::cref(interest_in_spec_helper),
n::make_destination_filtered_generator_fn() = std::cref(make_destination_filtered_generator_helper),
n::make_origin_filtered_generator_fn() = std::cref(make_origin_filtered_generator_helper),
diff --git a/paludis/resolver/resolver_test.hh b/paludis/resolver/resolver_test.hh
index 70d4d8a..2932bd3 100644
--- a/paludis/resolver/resolver_test.hh
+++ b/paludis/resolver/resolver_test.hh
@@ -45,6 +45,7 @@
#include <paludis/resolver/get_constraints_for_purge_helper.hh>
#include <paludis/resolver/get_constraints_for_via_binary_helper.hh>
#include <paludis/resolver/get_destination_types_for_error_helper.hh>
+#include <paludis/resolver/get_use_existing_nothing_helper.hh>
#include <paludis/resolver/interest_in_spec_helper.hh>
#include <paludis/resolver/make_destination_filtered_generator_helper.hh>
#include <paludis/resolver/make_origin_filtered_generator_helper.hh>
@@ -92,11 +93,6 @@ namespace paludis
const std::shared_ptr<const SlotName> &,
const std::shared_ptr<const Reason> &);
- std::pair<UseExisting, bool> get_use_existing_nothing_fn(
- const std::shared_ptr<const Resolution> &,
- const PackageDepSpec &,
- const std::shared_ptr<const Reason> &);
-
struct ResolverTestCase : test::TestCase
{
TestEnvironment env;
@@ -113,6 +109,7 @@ namespace paludis
GetConstraintsForPurgeHelper get_constraints_for_purge_helper;
GetConstraintsForViaBinaryHelper get_constraints_for_via_binary_helper;
GetDestinationTypesForErrorHelper get_destination_types_for_error_helper;
+ GetUseExistingNothingHelper get_use_existing_nothing_helper;
InterestInSpecHelper interest_in_spec_helper;
MakeDestinationFilteredGeneratorHelper make_destination_filtered_generator_helper;
MakeOriginFilteredGeneratorHelper make_origin_filtered_generator_helper;
diff --git a/src/clients/cave/resolve_common.cc b/src/clients/cave/resolve_common.cc
index bf1edde..d3cd69d 100644
--- a/src/clients/cave/resolve_common.cc
+++ b/src/clients/cave/resolve_common.cc
@@ -50,6 +50,7 @@
#include <paludis/resolver/resolver.hh>
#include <paludis/resolver/resolution.hh>
#include <paludis/resolver/decision.hh>
+#include <paludis/resolver/destination_utils.hh>
#include <paludis/resolver/resolver_functions.hh>
#include <paludis/resolver/reason.hh>
#include <paludis/resolver/suggest_restart.hh>
@@ -74,6 +75,7 @@
#include <paludis/resolver/get_constraints_for_purge_helper.hh>
#include <paludis/resolver/get_constraints_for_via_binary_helper.hh>
#include <paludis/resolver/get_destination_types_for_error_helper.hh>
+#include <paludis/resolver/get_use_existing_nothing_helper.hh>
#include <paludis/resolver/interest_in_spec_helper.hh>
#include <paludis/resolver/make_destination_filtered_generator_helper.hh>
#include <paludis/resolver/make_origin_filtered_generator_helper.hh>
@@ -129,13 +131,6 @@ namespace
return id->behaviours_key()->value()->end() == id->behaviours_key()->value()->find("unbinaryable");
}
- bool can_chroot(const std::shared_ptr<const PackageID> & id)
- {
- if (! id->behaviours_key())
- return true;
- return id->behaviours_key()->value()->end() == id->behaviours_key()->value()->find("unchrootable");
- }
-
struct DestinationTypesFinder
{
const Environment * const env;
@@ -334,126 +329,6 @@ namespace
return result;
}
- UseExisting use_existing_from_cmdline(const args::EnumArg & a, const bool is_set)
- {
- if (a.argument() == "auto")
- return is_set ? ue_if_same : ue_never;
- else if (a.argument() == "never")
- return ue_never;
- else if (a.argument() == "if-transient")
- return ue_only_if_transient;
- else if (a.argument() == "if-same")
- return ue_if_same;
- else if (a.argument() == "if-same-version")
- return ue_if_same_version;
- else if (a.argument() == "if-possible")
- return ue_if_possible;
- else
- throw args::DoHelp("Don't understand argument '" + a.argument() + "' to '--" + a.long_name() + "'");
- }
-
- struct UseExistingVisitor
- {
- const Environment * const env;
- const ResolveCommandLineResolutionOptions & resolution_options;
- const bool from_set;
- const Resolvent resolvent;
-
- UseExistingVisitor(const Environment * const e, const ResolveCommandLineResolutionOptions & c, const bool f, const Resolvent & r) :
- env(e),
- resolution_options(c),
- from_set(f),
- resolvent(r)
- {
- }
-
- bool creating_and_no_appropriate_ids() const
- {
- bool (* can)(const std::shared_ptr<const PackageID> &)(0);
- switch (resolvent.destination_type())
- {
- case dt_install_to_slash:
- return false;
-
- case dt_create_binary:
- can = &can_make_binary_for;
- break;
-
- case dt_install_to_chroot:
- can = &can_chroot;
- break;
-
- case last_dt:
- break;
- }
-
- if (! can)
- throw InternalError(PALUDIS_HERE, "unhandled dt");
-
- auto origin_ids((*env)[selection::AllVersionsSorted(
- generator::Package(resolvent.package()) |
- make_slot_filter(resolvent) |
- filter::SupportsAction<InstallAction>() |
- filter::NotMasked()
- )]);
- if (origin_ids->empty())
- return false;
- else
- {
- for (auto i(origin_ids->begin()), i_end(origin_ids->end()) ;
- i != i_end ; ++i)
- if ((*can)(*i))
- return false;
-
- return true;
- }
- }
-
- std::pair<UseExisting, bool> visit(const DependencyReason &) const
- {
- return std::make_pair(use_existing_from_cmdline(resolution_options.a_keep, false),
- creating_and_no_appropriate_ids());
- }
-
- std::pair<UseExisting, bool> visit(const TargetReason &) const
- {
- return std::make_pair(use_existing_from_cmdline(resolution_options.a_keep_targets, from_set),
- creating_and_no_appropriate_ids());
- }
-
- std::pair<UseExisting, bool> visit(const DependentReason &) const
- {
- return std::make_pair(ue_if_possible, false);
- }
-
- std::pair<UseExisting, bool> visit(const WasUsedByReason &) const
- {
- return std::make_pair(ue_if_possible, false);
- }
-
- std::pair<UseExisting, bool> visit(const PresetReason &) const
- {
- return std::make_pair(ue_if_possible, false);
- }
-
- std::pair<UseExisting, bool> visit(const ViaBinaryReason &) const
- {
- return std::make_pair(ue_if_possible, false);
- }
-
- std::pair<UseExisting, bool> visit(const SetReason & r) const
- {
- UseExistingVisitor v(env, resolution_options, true, resolvent);
- return r.reason_for_set()->accept_returning<std::pair<UseExisting, bool> >(v);
- }
-
- std::pair<UseExisting, bool> visit(const LikeOtherDestinationTypeReason & r) const
- {
- UseExistingVisitor v(env, resolution_options, true, resolvent);
- return r.reason_for_other()->accept_returning<std::pair<UseExisting, bool> >(v);
- }
- };
-
bool use_existing_from_withish(
const Environment * const,
const QualifiedPackageName & name,
@@ -485,27 +360,6 @@ namespace
return false;
}
- std::pair<UseExisting, bool> use_existing_nothing_fn(
- const Environment * const env,
- const ResolveCommandLineResolutionOptions & resolution_options,
- const PackageDepSpecList & without,
- const PackageDepSpecList & with,
- const std::shared_ptr<const Resolution> & resolution,
- const PackageDepSpec & spec,
- const std::shared_ptr<const Reason> & reason)
- {
- if (spec.package_ptr())
- {
- if (use_existing_from_withish(env, *spec.package_ptr(), without))
- return std::make_pair(ue_if_possible, true);
- if (use_existing_from_withish(env, *spec.package_ptr(), with))
- return std::make_pair(ue_never, false);
- }
-
- UseExistingVisitor v(env, resolution_options, false, resolution->resolvent());
- return reason->accept_returning<std::pair<UseExisting, bool> >(v);
- }
-
int reinstall_scm_days(const ResolveCommandLineResolutionOptions & resolution_options)
{
if (resolution_options.a_reinstall_scm.argument() == "always")
@@ -1117,6 +971,30 @@ namespace
std::cout << std::endl;
}
+
+ UseExisting use_existing_from_arg(const args::EnumArg & arg, const bool is_set)
+ {
+ if (arg.argument() == "auto")
+ {
+ if (is_set)
+ return ue_if_same;
+ else
+ return ue_never;
+ }
+ else if (arg.argument() == "never")
+ return ue_never;
+ else if (arg.argument() == "if-transient")
+ return ue_only_if_transient;
+ else if (arg.argument() == "if-same")
+ return ue_if_same;
+ else if (arg.argument() == "if-same-version")
+ return ue_if_same_version;
+ else if (arg.argument() == "if-possible")
+ return ue_if_possible;
+ else
+ throw args::DoHelp("Don't understand argument '" + arg.argument() + "' to '--"
+ + arg.long_name() + "'");
+ }
}
int
@@ -1134,7 +1012,7 @@ paludis::cave::resolve_common(
int retcode(0);
InitialConstraints initial_constraints;
- PackageDepSpecList with, without;
+ PackageDepSpecList without;
for (args::StringSetArg::ConstIterator i(resolution_options.a_without.begin_args()),
i_end(resolution_options.a_without.end_args()) ;
@@ -1142,12 +1020,6 @@ paludis::cave::resolve_common(
without.push_back(parse_user_package_dep_spec(*i, env.get(),
{ updso_allow_wildcards }));
- for (args::StringSetArg::ConstIterator i(resolution_options.a_with.begin_args()),
- i_end(resolution_options.a_with.end_args()) ;
- i != i_end ; ++i)
- with.push_back(parse_user_package_dep_spec(*i, env.get(),
- { updso_allow_wildcards }));
-
std::shared_ptr<Generator> binary_destinations;
for (PackageDatabase::RepositoryConstIterator r(env->package_database()->begin_repositories()),
r_end(env->package_database()->end_repositories()) ;
@@ -1273,6 +1145,21 @@ paludis::cave::resolve_common(
throw args::DoHelp("Don't understand argument '" + resolution_options.a_make.argument() + "' to '--"
+ resolution_options.a_make.long_name() + "'");
+ GetUseExistingNothingHelper get_use_existing_nothing_helper(env.get());
+ for (args::StringSetArg::ConstIterator i(resolution_options.a_without.begin_args()),
+ i_end(resolution_options.a_without.end_args()) ;
+ i != i_end ; ++i)
+ get_use_existing_nothing_helper.add_without_spec(parse_user_package_dep_spec(*i, env.get(), { updso_allow_wildcards }));
+
+ for (args::StringSetArg::ConstIterator i(resolution_options.a_with.begin_args()),
+ i_end(resolution_options.a_with.end_args()) ;
+ i != i_end ; ++i)
+ get_use_existing_nothing_helper.add_with_spec(parse_user_package_dep_spec(*i, env.get(), { updso_allow_wildcards }));
+
+ get_use_existing_nothing_helper.set_use_existing_for_dependencies(use_existing_from_arg(resolution_options.a_keep, false));
+ get_use_existing_nothing_helper.set_use_existing_for_targets(use_existing_from_arg(resolution_options.a_keep_targets, false));
+ get_use_existing_nothing_helper.set_use_existing_for_set_targets(use_existing_from_arg(resolution_options.a_keep_targets, true));
+
MakeDestinationFilteredGeneratorHelper make_destination_filtered_generator_helper(env.get());
MakeOriginFilteredGeneratorHelper make_origin_filtered_generator_helper(env.get());
@@ -1378,8 +1265,7 @@ paludis::cave::resolve_common(
std::cref(initial_constraints), binary_destinations, _1),
n::get_resolvents_for_fn() = std::bind(&get_resolvents_for_fn,
env.get(), std::cref(resolution_options), _1, _2, _3, DestinationTypes()),
- n::get_use_existing_nothing_fn() = std::bind(&use_existing_nothing_fn,
- env.get(), std::cref(resolution_options), std::cref(without), std::cref(with), _1, _2, _3),
+ n::get_use_existing_nothing_fn() = std::cref(get_use_existing_nothing_helper),
n::interest_in_spec_fn() = std::cref(interest_in_spec_helper),
n::make_destination_filtered_generator_fn() = std::cref(make_destination_filtered_generator_helper),
n::make_origin_filtered_generator_fn() = std::cref(make_origin_filtered_generator_helper),