aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--src/libstore/local-store.cc88
1 files changed, 42 insertions, 46 deletions
diff --git a/src/libstore/local-store.cc b/src/libstore/local-store.cc
index f88af10f7..15200e842 100644
--- a/src/libstore/local-store.cc
+++ b/src/libstore/local-store.cc
@@ -75,6 +75,11 @@ static void throwSQLiteError(sqlite3 * db, const format & f)
}
+/* Convenience macros for retrying a SQLite transaction. */
+#define retry_sqlite while (1) { try {
+#define end_retry_sqlite break; } catch (SQLiteBusy & e) { } }
+
+
SQLite::~SQLite()
{
try {
@@ -1219,39 +1224,33 @@ void LocalStore::registerValidPaths(const ValidPathInfos & infos)
* expense of some speed of the path registering operation. */
if (settings.syncBeforeRegistering) sync();
- while (1) {
- try {
- SQLiteTxn txn(db);
- PathSet paths;
+ retry_sqlite {
+ SQLiteTxn txn(db);
+ PathSet paths;
+
+ foreach (ValidPathInfos::const_iterator, i, infos) {
+ assert(i->hash.type == htSHA256);
+ if (isValidPath(i->path))
+ updatePathInfo(*i);
+ else
+ addValidPath(*i);
+ paths.insert(i->path);
+ }
- foreach (ValidPathInfos::const_iterator, i, infos) {
- assert(i->hash.type == htSHA256);
- if (isValidPath(i->path))
- updatePathInfo(*i);
- else
- addValidPath(*i);
- paths.insert(i->path);
- }
+ foreach (ValidPathInfos::const_iterator, i, infos) {
+ unsigned long long referrer = queryValidPathId(i->path);
+ foreach (PathSet::iterator, j, i->references)
+ addReference(referrer, queryValidPathId(*j));
+ }
- foreach (ValidPathInfos::const_iterator, i, infos) {
- unsigned long long referrer = queryValidPathId(i->path);
- foreach (PathSet::iterator, j, i->references)
- addReference(referrer, queryValidPathId(*j));
- }
+ /* Do a topological sort of the paths. This will throw an
+ error if a cycle is detected and roll back the
+ transaction. Cycles can only occur when a derivation
+ has multiple outputs. */
+ topoSortPaths(*this, paths);
- /* Do a topological sort of the paths. This will throw an
- error if a cycle is detected and roll back the
- transaction. Cycles can only occur when a derivation
- has multiple outputs. */
- topoSortPaths(*this, paths);
-
- txn.commit();
- break;
- } catch (SQLiteBusy & e) {
- /* Retry; the `txn' destructor will roll back the current
- transaction. */
- }
- }
+ txn.commit();
+ } end_retry_sqlite;
}
@@ -1642,23 +1641,20 @@ void LocalStore::invalidatePathChecked(const Path & path)
{
assertStorePath(path);
- while (1) {
- try {
- SQLiteTxn txn(db);
-
- if (isValidPath(path)) {
- PathSet referrers; queryReferrers(path, referrers);
- referrers.erase(path); /* ignore self-references */
- if (!referrers.empty())
- throw PathInUse(format("cannot delete path `%1%' because it is in use by %2%")
- % path % showPaths(referrers));
- invalidatePath(path);
- }
+ retry_sqlite {
+ SQLiteTxn txn(db);
- txn.commit();
- break;
- } catch (SQLiteBusy & e) { };
- }
+ if (isValidPath(path)) {
+ PathSet referrers; queryReferrers(path, referrers);
+ referrers.erase(path); /* ignore self-references */
+ if (!referrers.empty())
+ throw PathInUse(format("cannot delete path `%1%' because it is in use by %2%")
+ % path % showPaths(referrers));
+ invalidatePath(path);
+ }
+
+ txn.commit();
+ } end_retry_sqlite;
}