From 081fbea14d12f79c8d91ce4fe1f1004c7bc08656 Mon Sep 17 00:00:00 2001 From: David Kalnischkies Date: Wed, 12 Apr 2017 17:39:06 +0200 Subject: error in update on Release information changes The value of Origin, Label, Codename and co can be used in user configuration from apts own pinning to unattended upgrades. A repository changing this values can therefore have serious effects on the behaviour of apt and other tools using these values. In a first step we will generate error messages for these changes now explaining the need for explicit confirmation and provide config options and commandline flags to accept them. --- apt-pkg/acquire-item.cc | 60 ++++++++++++++++++++++++++++++++++++++++++++----- 1 file changed, 55 insertions(+), 5 deletions(-) (limited to 'apt-pkg/acquire-item.cc') diff --git a/apt-pkg/acquire-item.cc b/apt-pkg/acquire-item.cc index 574ef4939..f5ff8288b 100644 --- a/apt-pkg/acquire-item.cc +++ b/apt-pkg/acquire-item.cc @@ -1605,13 +1605,63 @@ bool pkgAcqMetaBase::VerifyVendor(string const &) /*{{{*/ if (TransactionManager->MetaIndexParser->CheckDist(ExpectedDist) == false) _error->Warning(_("Conflicting distribution: %s (expected %s but got %s)"), Desc.Description.c_str(), ExpectedDist.c_str(), NowCodename.c_str()); - // might be okay, might be not + + // changed info potentially breaks user config like pinning if (TransactionManager->LastMetaIndexParser != nullptr) { - auto const LastCodename = TransactionManager->LastMetaIndexParser->GetCodename(); - if (LastCodename.empty() == false && NowCodename.empty() == false && LastCodename != NowCodename) - _error->Warning(_("Conflicting distribution: %s (expected %s but got %s)"), - Desc.Description.c_str(), LastCodename.c_str(), NowCodename.c_str()); + auto const AllowInfoChange = _config->FindB("Acquire::AllowReleaseInfoChange", false); + auto const quietInfoChange = _config->FindB("quiet::ReleaseInfoChange", false); + struct { + char const * const Type; + bool const Allowed; + decltype(&metaIndex::GetOrigin) const Getter; + } checkers[] = { + { "Origin", AllowInfoChange, &metaIndex::GetOrigin }, + { "Label", AllowInfoChange, &metaIndex::GetLabel }, + { "Version", true, &metaIndex::GetVersion }, // numbers change all the time, that is okay + { "Suite", AllowInfoChange, &metaIndex::GetSuite }, + { "Codename", AllowInfoChange, &metaIndex::GetCodename }, + { nullptr, false, nullptr } + }; + auto const CheckReleaseInfo = [&](char const * const Type, bool const AllowChange, decltype(checkers[0].Getter) const Getter) { + std::string const Last = (TransactionManager->LastMetaIndexParser->*Getter)(); + std::string const Now = (TransactionManager->MetaIndexParser->*Getter)(); + if (Last == Now) + return true; + auto const Allow = _config->FindB(std::string("Acquire::AllowReleaseInfoChange::").append(Type), AllowChange); + auto const msg = _("Repository '%s' changed its '%s' value from '%s' to '%s'"); + if (Allow == false) + _error->Error(msg, Desc.Description.c_str(), Type, Last.c_str(), Now.c_str()); + else if (_config->FindB(std::string("quiet::ReleaseInfoChange::").append(Type), quietInfoChange) == false) + _error->Notice(msg, Desc.Description.c_str(), Type, Last.c_str(), Now.c_str()); + return Allow; + }; + bool CRI = true; + for (short i = 0; checkers[i].Type != nullptr; ++i) + if (CheckReleaseInfo(checkers[i].Type, checkers[i].Allowed, checkers[i].Getter) == false) + CRI = false; + + { + auto const Last = TransactionManager->LastMetaIndexParser->GetDefaultPin(); + auto const Now = TransactionManager->MetaIndexParser->GetDefaultPin(); + if (Last != Now) + { + auto const Allow = _config->FindB("Acquire::AllowReleaseInfoChange::DefaultPin", AllowInfoChange); + auto const msg = _("Repository '%s' changed its default priority for %s from %hi to %hi."); + if (Allow == false) + _error->Error(msg, Desc.Description.c_str(), "apt_preferences(5)", Last, Now); + else if (_config->FindB("quiet::ReleaseInfoChange::DefaultPin", quietInfoChange) == false) + _error->Notice(msg, Desc.Description.c_str(), "apt_preferences(5)", Last, Now); + CRI &= Allow; + } + } + if (CRI == false) + { + // TRANSLATOR: %s is the name of the manpage in question, e.g. apt-secure(8) + _error->Notice(_("This must be accepted explicitly before updates for " + "this repository can be applied. See %s manpage for details."), "apt-secure(8)"); + return false; + } } return true; } -- cgit v1.2.3