aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorAvatar Ciaran McCreesh <ciaran.mccreesh@googlemail.com> 2006-11-21 08:53:47 +0000
committerAvatar Ciaran McCreesh <ciaran.mccreesh@googlemail.com> 2006-11-21 08:53:47 +0000
commit528a64c6fcf47774757494ed66387d2ba636090b (patch)
tree988eb16daabd694a6e28f2fbc5d33af6bd1fbb6e
parent63791dc326a121bdad255843a80816207b7b3803 (diff)
downloadpaludis-528a64c6fcf47774757494ed66387d2ba636090b.tar.gz
paludis-528a64c6fcf47774757494ed66387d2ba636090b.tar.xz
Add --dl-reinstall-scm support
-rw-r--r--paludis/dep_list.cc32
-rw-r--r--paludis/dep_list.hh13
-rw-r--r--paludis/dep_list.sr1
-rw-r--r--paludis/repositories/vdb/vdb_repository.cc44
-rw-r--r--paludis/repositories/vdb/vdb_repository.hh4
-rw-r--r--paludis/repository.hh22
-rw-r--r--paludis/version_spec.cc20
-rw-r--r--paludis/version_spec.hh5
-rw-r--r--paludis/version_spec_TEST.cc15
-rw-r--r--src/paludis/command_line.cc7
-rw-r--r--src/paludis/command_line.hh1
-rw-r--r--src/paludis/install.cc14
12 files changed, 172 insertions, 6 deletions
diff --git a/paludis/dep_list.cc b/paludis/dep_list.cc
index de145d5..eb7bd50 100644
--- a/paludis/dep_list.cc
+++ b/paludis/dep_list.cc
@@ -67,6 +67,7 @@ CircularDependencyError::CircularDependencyError(const std::string & msg) throw
DepListOptions::DepListOptions() :
reinstall(dl_reinstall_never),
+ reinstall_scm(dl_reinstall_scm_never),
target_type(dl_target_package),
upgrade(dl_upgrade_always),
installed_deps_pre(dl_deps_discard),
@@ -785,6 +786,37 @@ DepList::prefer_installed_over_uninstalled(const PackageDatabaseEntry & installe
if (dl_upgrade_as_needed == _imp->opts.upgrade)
return true;
+ if (dl_reinstall_scm_never != _imp->opts.reinstall_scm)
+ if (installed.version.is_scm() && uninstalled.version == installed.version)
+ {
+ static time_t current_time(time(0)); /* static to avoid weirdness */
+ time_t installed_time(_imp->env->package_database()->fetch_repository(installed.repository
+ )->installed_interface->installed_time(installed.name, installed.version));
+ do
+ {
+ switch (_imp->opts.reinstall_scm)
+ {
+ case dl_reinstall_scm_always:
+ return false;
+
+ case dl_reinstall_scm_daily:
+ if (current_time - installed_time > (24 * 60 * 60))
+ return false;
+ continue;
+
+ case dl_reinstall_scm_weekly:
+ if (current_time - installed_time > (24 * 60 * 60 * 7))
+ return false;
+ continue;
+
+ case dl_reinstall_never:
+ ; /* nothing */
+ }
+
+ throw InternalError(PALUDIS_HERE, "Bad value for opts.reinstall_scm");
+ } while (false);
+ }
+
/* use != rather than > to correctly force a downgrade when packages are
* removed. */
if (uninstalled.version != installed.version)
diff --git a/paludis/dep_list.hh b/paludis/dep_list.hh
index 6d15a54..3e9bbee 100644
--- a/paludis/dep_list.hh
+++ b/paludis/dep_list.hh
@@ -59,6 +59,19 @@ namespace paludis
};
/**
+ * When should we reinstall scm.
+ *
+ * \ingroup grpdepresolver
+ */
+ enum DepListReinstallScmOption
+ {
+ dl_reinstall_scm_never,
+ dl_reinstall_scm_always,
+ dl_reinstall_scm_daily,
+ dl_reinstall_scm_weekly
+ };
+
+ /**
* When should we upgrade.
*
* \ingroup grpdepresolver
diff --git a/paludis/dep_list.sr b/paludis/dep_list.sr
index 74ea6a3..9b0c553 100644
--- a/paludis/dep_list.sr
+++ b/paludis/dep_list.sr
@@ -4,6 +4,7 @@
make_class_DepListOptions()
{
key reinstall DepListReinstallOption
+ key reinstall_scm DepListReinstallScmOption
key target_type DepListTargetType
key upgrade DepListUpgradeOption
diff --git a/paludis/repositories/vdb/vdb_repository.cc b/paludis/repositories/vdb/vdb_repository.cc
index 53e667d..468c150 100644
--- a/paludis/repositories/vdb/vdb_repository.cc
+++ b/paludis/repositories/vdb/vdb_repository.cc
@@ -75,11 +75,15 @@ namespace
/// Our built USE flags.
std::set<UseFlagName> use;
+ /// Our installed date.
+ time_t installed_time;
+
/// Constructor
VDBEntry(const QualifiedPackageName & n, const VersionSpec & v) :
name(n),
version(v),
- metadata(0)
+ metadata(0),
+ installed_time(0)
{
}
@@ -681,6 +685,44 @@ VDBRepository::do_contents(
return result;
}
+time_t
+VDBRepository::do_installed_time(const QualifiedPackageName & q,
+ const VersionSpec & v) const
+{
+ Context context("When finding installed time for '" + stringify(q) +
+ "-" + stringify(v) + "':");
+
+ if (! _imp->entries_valid)
+ _imp->load_entries();
+
+ std::pair<std::vector<VDBEntry>::iterator, std::vector<VDBEntry>::iterator>
+ r(std::equal_range(_imp->entries.begin(), _imp->entries.end(), std::make_pair(
+ q, v), VDBEntry::CompareVersion()));
+
+ if (r.first == r.second)
+ throw NoSuchPackageError(stringify(PackageDatabaseEntry(q, v, name())));
+ else
+ {
+ if (0 == r.first->installed_time)
+ {
+ FSEntry f(_imp->location / stringify(q.category) / (stringify(q.package) + "-"
+ + stringify(v)) / "CONTENTS");
+ try
+ {
+ r.first->installed_time = f.ctime();
+ }
+ catch (const FSError & e)
+ {
+ Log::get_instance()->message(ll_warning, lc_no_context, "Can't get ctime of '"
+ + stringify(f) + "' due to exception '" + e.message() + "' (" + e.what()
+ + ")");
+ r.first->installed_time = 1;
+ }
+ }
+ return r.first->installed_time;
+ }
+}
+
UseFlagState
VDBRepository::do_query_use(const UseFlagName & f,
const PackageDatabaseEntry * const e) const
diff --git a/paludis/repositories/vdb/vdb_repository.hh b/paludis/repositories/vdb/vdb_repository.hh
index 4f2edfd..1745694 100644
--- a/paludis/repositories/vdb/vdb_repository.hh
+++ b/paludis/repositories/vdb/vdb_repository.hh
@@ -78,6 +78,10 @@ namespace paludis
const QualifiedPackageName &,
const VersionSpec &) const;
+ virtual time_t do_installed_time(
+ const QualifiedPackageName &,
+ const VersionSpec &) const;
+
virtual bool do_is_licence(const std::string &) const;
virtual void do_uninstall(const QualifiedPackageName &, const VersionSpec &,
diff --git a/paludis/repository.hh b/paludis/repository.hh
index 0f06bbd..452b288 100644
--- a/paludis/repository.hh
+++ b/paludis/repository.hh
@@ -496,6 +496,16 @@ namespace paludis
const QualifiedPackageName &,
const VersionSpec &) const = 0;
+ /**
+ * Override in descendents: when was a package installed.
+ */
+ virtual time_t do_installed_time(
+ const QualifiedPackageName &,
+ const VersionSpec &) const
+ {
+ return time_t(0);
+ }
+
public:
/**
* Fetch contents.
@@ -507,6 +517,18 @@ namespace paludis
return do_contents(q, v);
}
+ /**
+ * When was a package installed.
+ *
+ * Can return time_t(0) if the installed time is unknown.
+ */
+ time_t installed_time(
+ const QualifiedPackageName & q,
+ const VersionSpec & v) const
+ {
+ return do_installed_time(q, v);
+ }
+
virtual ~RepositoryInstalledInterface() { }
};
diff --git a/paludis/version_spec.cc b/paludis/version_spec.cc
index 7af0415..1971b79 100644
--- a/paludis/version_spec.cc
+++ b/paludis/version_spec.cc
@@ -343,15 +343,16 @@ VersionSpec::hash_value() const
namespace
{
/**
- * Identify Part instances that are revisions.
+ * Identify Part instances that are of a certain kind.
*
* \ingroup grpversions
*/
- struct IsRevisionPart
+ template <PartKind p_>
+ struct IsPart
{
bool operator() (const Part & p) const
{
- return p.kind == revision;
+ return p.kind == p_;
}
};
}
@@ -365,7 +366,7 @@ VersionSpec::remove_revision() const
result._imp->parts.erase(std::remove_if(
result._imp->parts.begin(),
result._imp->parts.end(),
- IsRevisionPart()), result._imp->parts.end());
+ IsPart<revision>()), result._imp->parts.end());
std::string::size_type p;
if (std::string::npos != ((p = result._imp->text.rfind("-r"))))
@@ -379,7 +380,7 @@ std::string
VersionSpec::revision_only() const
{
std::vector<Part>::const_iterator r(std::find_if(_imp->parts.begin(),
- _imp->parts.end(), IsRevisionPart()));
+ _imp->parts.end(), IsPart<revision>()));
if (r != _imp->parts.end())
return "r" + stringify(r->value);
else
@@ -393,3 +394,12 @@ paludis::operator<< (std::ostream & s, const VersionSpec & v)
return s;
}
+bool
+VersionSpec::is_scm() const
+{
+ std::vector<Part>::const_iterator r(std::find_if(_imp->parts.begin(),
+ _imp->parts.end(), IsPart<scm>()));
+
+ return r != _imp->parts.end();
+}
+
diff --git a/paludis/version_spec.hh b/paludis/version_spec.hh
index 74f97a9..5772997 100644
--- a/paludis/version_spec.hh
+++ b/paludis/version_spec.hh
@@ -115,6 +115,11 @@ namespace paludis
*/
std::string revision_only() const;
+ /**
+ * Are we an -scm package?
+ */
+ bool is_scm() const;
+
};
/**
diff --git a/paludis/version_spec_TEST.cc b/paludis/version_spec_TEST.cc
index 204a9f7..789fa9c 100644
--- a/paludis/version_spec_TEST.cc
+++ b/paludis/version_spec_TEST.cc
@@ -185,6 +185,21 @@ namespace test_cases
} test_version_revision_only;
/**
+ * \test VersionSpec is_scm
+ *
+ */
+ struct VersionIsScmTest : TestCase
+ {
+ VersionIsScmTest() : TestCase("version spec is_scm") {}
+
+ void run()
+ {
+ TEST_CHECK(! VersionSpec("1.2").is_scm());
+ TEST_CHECK(VersionSpec("1.2-scm-r99").is_scm());
+ }
+ } test_version_is_scm;
+
+ /**
* \test VersionSpec ordering.
*
*/
diff --git a/src/paludis/command_line.cc b/src/paludis/command_line.cc
index 7605637..1d6a748 100644
--- a/src/paludis/command_line.cc
+++ b/src/paludis/command_line.cc
@@ -96,6 +96,13 @@ CommandLine::CommandLine() :
("always", "Always")
("if-use-changed", "If USE flags have changed"),
"never"),
+ dl_reinstall_scm(&dl_args, "dl-reinstall-scm", '\0', "When to reinstall scm packages",
+ paludis::args::EnumArg::EnumArgOptions
+ ("never", "Never")
+ ("always", "Always")
+ ("daily", "If they are over a day old")
+ ("weekly", "If they are over a week old"),
+ "never"),
dl_upgrade(&dl_args, "dl-upgrade", '\0', "When to upgrade packages",
paludis::args::EnumArg::EnumArgOptions
("always", "Always")
diff --git a/src/paludis/command_line.hh b/src/paludis/command_line.hh
index 6a4acba..8f5a3b1 100644
--- a/src/paludis/command_line.hh
+++ b/src/paludis/command_line.hh
@@ -197,6 +197,7 @@ class CommandLine :
paludis::args::ArgsGroup dl_args;
paludis::args::EnumArg dl_reinstall;
+ paludis::args::EnumArg dl_reinstall_scm;
paludis::args::EnumArg dl_upgrade;
paludis::args::EnumArg dl_installed_deps_pre;
diff --git a/src/paludis/install.cc b/src/paludis/install.cc
index af567a7..dd3ed0c 100644
--- a/src/paludis/install.cc
+++ b/src/paludis/install.cc
@@ -695,6 +695,20 @@ do_install()
throw DoHelp("bad value for --dl-reinstall");
}
+ if (CommandLine::get_instance()->dl_reinstall_scm.specified())
+ {
+ if (CommandLine::get_instance()->dl_reinstall_scm.argument() == "never")
+ options.reinstall_scm = dl_reinstall_scm_never;
+ else if (CommandLine::get_instance()->dl_reinstall_scm.argument() == "always")
+ options.reinstall_scm = dl_reinstall_scm_always;
+ else if (CommandLine::get_instance()->dl_reinstall_scm.argument() == "daily")
+ options.reinstall_scm = dl_reinstall_scm_daily;
+ else if (CommandLine::get_instance()->dl_reinstall_scm.argument() == "weekly")
+ options.reinstall_scm = dl_reinstall_scm_weekly;
+ else
+ throw DoHelp("bad value for --dl-reinstall-scm");
+ }
+
if (CommandLine::get_instance()->dl_upgrade.specified())
{
if (CommandLine::get_instance()->dl_upgrade.argument() == "as-needed")