From 8d1277b777045f45ffae210edea608c27587d7a2 Mon Sep 17 00:00:00 2001 From: CoolStar Date: Thu, 20 Dec 2018 15:11:31 -0800 Subject: APT 1.7.0-sileo --- cmdline/CMakeLists.txt | 7 +- cmdline/sileo-solver.cc | 214 ++++++++++++++++++++++++++++++++++++++++++++++++ 2 files changed, 220 insertions(+), 1 deletion(-) create mode 100644 cmdline/sileo-solver.cc (limited to 'cmdline') diff --git a/cmdline/CMakeLists.txt b/cmdline/CMakeLists.txt index 8977b45d1..dd66b843c 100644 --- a/cmdline/CMakeLists.txt +++ b/cmdline/CMakeLists.txt @@ -9,6 +9,7 @@ add_executable(apt-helper apt-helper.cc) add_executable(apt-sortpkgs apt-sortpkgs.cc) add_executable(apt-extracttemplates apt-extracttemplates.cc) add_executable(apt-internal-solver apt-internal-solver.cc) +add_executable(sileo-solver sileo-solver.cc) add_executable(apt-dump-solver apt-dump-solver.cc) add_executable(apt-internal-planner apt-internal-planner.cc) add_vendor_file(OUTPUT apt-key @@ -31,6 +32,7 @@ target_link_libraries(apt-mark apt-pkg apt-private) target_link_libraries(apt-sortpkgs apt-pkg apt-private) target_link_libraries(apt-extracttemplates apt-pkg apt-inst apt-private) target_link_libraries(apt-internal-solver apt-pkg apt-inst apt-private) +target_link_libraries(sileo-solver apt-pkg apt-inst apt-private) target_link_libraries(apt-dump-solver apt-pkg apt-inst apt-private) target_link_libraries(apt-internal-planner apt-pkg apt-inst apt-private) @@ -40,6 +42,9 @@ set_target_properties(apt-dump-solver set_target_properties(apt-internal-solver PROPERTIES RUNTIME_OUTPUT_DIRECTORY solvers RUNTIME_OUTPUT_NAME apt) +set_target_properties(sileo-solver + PROPERTIES RUNTIME_OUTPUT_DIRECTORY solvers + RUNTIME_OUTPUT_NAME sileo) set_target_properties(apt-internal-planner PROPERTIES RUNTIME_OUTPUT_DIRECTORY planners RUNTIME_OUTPUT_NAME apt) @@ -50,7 +55,7 @@ install(TARGETS apt apt-cache apt-get apt-config apt-cdrom apt-mark apt-sortpkgs RUNTIME DESTINATION ${CMAKE_INSTALL_BINDIR}) install(TARGETS apt-helper RUNTIME DESTINATION ${CMAKE_INSTALL_LIBEXECDIR}/apt/) -install(TARGETS apt-dump-solver apt-internal-solver RUNTIME DESTINATION ${CMAKE_INSTALL_LIBEXECDIR}/apt/solvers) +install(TARGETS apt-dump-solver apt-internal-solver sileo-solver RUNTIME DESTINATION ${CMAKE_INSTALL_LIBEXECDIR}/apt/solvers) install(TARGETS apt-internal-planner RUNTIME DESTINATION ${CMAKE_INSTALL_LIBEXECDIR}/apt/planners) add_slaves(${CMAKE_INSTALL_LIBEXECDIR}/apt/planners ../solvers/dump planners/dump) diff --git a/cmdline/sileo-solver.cc b/cmdline/sileo-solver.cc new file mode 100644 index 000000000..0bc516c41 --- /dev/null +++ b/cmdline/sileo-solver.cc @@ -0,0 +1,214 @@ +// -*- mode: cpp; mode: fold -*- +// Description /*{{{*/ +/* ##################################################################### + + cover around the internal solver to be able to run it like an external + + ##################################################################### */ + /*}}}*/ +// Include Files /*{{{*/ +#include + +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include + +#include +#include +#include + +#include +#include +#include +#include +#include +#include +#include +#include + +#include + /*}}}*/ + +static bool ShowHelp(CommandLine &) /*{{{*/ +{ + std::cout << + _("Usage: sileo-solver\n" + "\n" + "sileo-solver is an interface to use the internal\n" + "resolver for the APT family for Sileo.\n"); + return true; +} + /*}}}*/ +APT_NORETURN static void DIE(std::string const &message) { /*{{{*/ + std::cerr << "ERROR: " << message << std::endl; + _error->DumpErrors(std::cerr); + exit(EXIT_FAILURE); +} + /*}}}*/ +static std::vector GetCommands() /*{{{*/ +{ + return {}; +} + /*}}}*/ +static bool WriteSolution(pkgDepCache &Cache, FileFd &output) /*{{{*/ +{ + bool Okay = output.Failed() == false; + for (pkgCache::PkgIterator Pkg = Cache.PkgBegin(); Pkg.end() == false && likely(Okay); ++Pkg) + { + std::string action; + if (Cache[Pkg].Delete() == true) + Okay &= EDSP::WriteSolutionStanza(output, "Remove", Pkg.CurrentVer()); + else if (Cache[Pkg].NewInstall() == true || Cache[Pkg].Upgrade() == true) + Okay &= EDSP::WriteSolutionStanza(output, "Install", Cache.GetCandidateVersion(Pkg)); + else if (Cache[Pkg].Garbage == true) + Okay &= EDSP::WriteSolutionStanza(output, "Autoremove", Pkg.CurrentVer()); + } + return Okay; +} + /*}}}*/ +int main(int argc,const char *argv[]) /*{{{*/ +{ + // we really don't need anything + DropPrivileges(); + + CommandLine CmdL; + ParseCommandLine(CmdL, APT_CMD::APT_INTERNAL_SOLVER, &_config, NULL, argc, argv, &ShowHelp, &GetCommands); + + _config->Set("APT::Format::for-sileo",true); + + if (CmdL.FileList[0] != 0 && strcmp(CmdL.FileList[0], "scenario") == 0) + { + if (pkgInitSystem(*_config,_system) == false) { + std::cerr << "System could not be initialized!" << std::endl; + return 1; + } + pkgCacheFile CacheFile; + CacheFile.Open(NULL, false); + APT::PackageSet pkgset = APT::PackageSet::FromCommandLine(CacheFile, CmdL.FileList + 1); + FileFd output; + if (output.OpenDescriptor(STDOUT_FILENO, FileFd::WriteOnly | FileFd::BufferedWrite, true) == false) + return 2; + if (pkgset.empty() == true) + EDSP::WriteScenario(CacheFile, output); + else + { + std::vector pkgvec(CacheFile->Head().PackageCount, false); + for (auto const &p: pkgset) + pkgvec[p->ID] = true; + EDSP::WriteLimitedScenario(CacheFile, output, pkgvec); + } + output.Close(); + _error->DumpErrors(std::cerr); + return 0; + } + + // Deal with stdout not being a tty + if (!isatty(STDOUT_FILENO) && _config->FindI("quiet", -1) == -1) + _config->Set("quiet","1"); + + if (_config->FindI("quiet", 0) < 1) + _config->Set("Debug::EDSP::WriteSolution", true); + + _config->Set("APT::System", "Debian APT solver interface"); + _config->Set("APT::Solver", "internal"); + _config->Set("edsp::scenario", "/nonexistent/stdin"); + _config->Clear("Dir::Log"); + FileFd output; + if (output.OpenDescriptor(STDOUT_FILENO, FileFd::WriteOnly | FileFd::BufferedWrite, true) == false) + DIE("stdout couldn't be opened"); + int const input = STDIN_FILENO; + SetNonBlock(input, false); + + EDSP::WriteProgress(0, "Start up solver…", output); + + if (pkgInitSystem(*_config,_system) == false) + DIE("System could not be initialized!"); + + EDSP::WriteProgress(1, "Read request…", output); + + if (WaitFd(input, false, 5) == false) + DIE("WAIT timed out in the resolver"); + + std::list install, remove; + unsigned int flags; + if (EDSP::ReadRequest(input, install, remove, flags) == false) + DIE("Parsing the request failed!"); + + EDSP::WriteProgress(5, "Read scenario…", output); + + pkgCacheFile CacheFile; + if (CacheFile.Open(NULL, false) == false) + DIE("Failed to open CacheFile!"); + + EDSP::WriteProgress(50, "Apply request on scenario…", output); + + if (EDSP::ApplyRequest(install, remove, CacheFile) == false) + DIE("Failed to apply request to depcache!"); + + pkgProblemResolver Fix(CacheFile); + for (std::list::const_iterator i = remove.begin(); + i != remove.end(); ++i) { + pkgCache::PkgIterator P = CacheFile->FindPkg(*i); + Fix.Clear(P); + Fix.Protect(P); + Fix.Remove(P); + } + + for (std::list::const_iterator i = install.begin(); + i != install.end(); ++i) { + pkgCache::PkgIterator P = CacheFile->FindPkg(*i); + Fix.Clear(P); + Fix.Protect(P); + } + + for (std::list::const_iterator i = install.begin(); + i != install.end(); ++i) + CacheFile->MarkInstall(CacheFile->FindPkg(*i), true); + + EDSP::WriteProgress(60, "Call problemresolver on current scenario…", output); + + std::string failure; + if (flags & EDSP::Request::UPGRADE_ALL) { + int upgrade_flags = APT::Upgrade::ALLOW_EVERYTHING; + if (flags & EDSP::Request::FORBID_NEW_INSTALL) + upgrade_flags |= APT::Upgrade::FORBID_INSTALL_NEW_PACKAGES; + if (flags & EDSP::Request::FORBID_REMOVE) + upgrade_flags |= APT::Upgrade::FORBID_REMOVE_PACKAGES; + + if (APT::Upgrade::Upgrade(CacheFile, upgrade_flags)) + ; + else if (upgrade_flags == APT::Upgrade::ALLOW_EVERYTHING) + failure = "ERR_UNSOLVABLE_FULL_UPGRADE"; + else + failure = "ERR_UNSOLVABLE_UPGRADE"; + } else if (Fix.Resolve() == false) + failure = "ERR_UNSOLVABLE"; + + if (failure.empty() == false) { + std::ostringstream broken; + ShowBroken(broken, CacheFile, false); + EDSP::WriteError(failure.c_str(), broken.str(), output); + return 0; + } + + EDSP::WriteProgress(95, "Write solution…", output); + + if (WriteSolution(CacheFile, output) == false) + DIE("Failed to output the solution!"); + + EDSP::WriteProgress(100, "Done", output); + + return DispatchCommandLine(CmdL, {}); +} + /*}}}*/ -- cgit v1.2.3