Repository: lucy Updated Branches: refs/heads/master d7feb9970 -> 5535d25f8
Fix previous merge of 'improve-locking' branch I accidentally merged the first version of the 'improve-locking' branch. Add changes to the 'v2' branch as separate commit. Project: http://git-wip-us.apache.org/repos/asf/lucy/repo Commit: http://git-wip-us.apache.org/repos/asf/lucy/commit/5535d25f Tree: http://git-wip-us.apache.org/repos/asf/lucy/tree/5535d25f Diff: http://git-wip-us.apache.org/repos/asf/lucy/diff/5535d25f Branch: refs/heads/master Commit: 5535d25f8a5b1ad86e2d5540589c6e46654e350e Parents: d7feb99 Author: Nick Wellnhofer <wellnho...@aevum.de> Authored: Sun Apr 16 12:43:57 2017 +0200 Committer: Nick Wellnhofer <wellnho...@aevum.de> Committed: Sun Apr 16 12:43:57 2017 +0200 ---------------------------------------------------------------------- core/Lucy/Index/FilePurger.c | 5 ++- core/Lucy/Index/PolyReader.c | 75 ++++++++++++++++++++--------------- core/Lucy/Store/Lock.c | 4 -- core/Lucy/Store/Lock.cfh | 1 - core/Lucy/Store/LockFileLock.c | 2 + core/Lucy/Store/LockFileLock.cfh | 1 + 6 files changed, 49 insertions(+), 39 deletions(-) ---------------------------------------------------------------------- http://git-wip-us.apache.org/repos/asf/lucy/blob/5535d25f/core/Lucy/Index/FilePurger.c ---------------------------------------------------------------------- diff --git a/core/Lucy/Index/FilePurger.c b/core/Lucy/Index/FilePurger.c index 211f0ea..6daa805 100644 --- a/core/Lucy/Index/FilePurger.c +++ b/core/Lucy/Index/FilePurger.c @@ -234,7 +234,10 @@ S_delete_entry(Folder *folder, String *folder_entry) { Folder *inner = Folder_Local_Find_Folder(folder, folder_entry); if (inner == NULL) { return false; } if (Folder_is_a(inner, COMPOUNDFILEREADER)) { - inner = CFReader_Get_Real_Folder((CompoundFileReader*)inner); + CompoundFileReader *cf_reader = (CompoundFileReader*)inner; + inner = CFReader_Get_Real_Folder(cf_reader); + // Close cf.dat to allow speedy deletion on Windows. + CFReader_Close(cf_reader); } Vector *entries = Folder_List(inner, NULL); http://git-wip-us.apache.org/repos/asf/lucy/blob/5535d25f/core/Lucy/Index/PolyReader.c ---------------------------------------------------------------------- diff --git a/core/Lucy/Index/PolyReader.c b/core/Lucy/Index/PolyReader.c index 572cc2b..f554193 100644 --- a/core/Lucy/Index/PolyReader.c +++ b/core/Lucy/Index/PolyReader.c @@ -330,47 +330,51 @@ PolyReader* PolyReader_do_open(PolyReader *self, Obj *index, Snapshot *snapshot, IndexManager *manager) { PolyReaderIVARS *const ivars = PolyReader_IVARS(self); - Folder *folder = S_derive_folder(index); - Err *last_error = NULL; - uint64_t last_gen = 0; + Folder *folder = S_derive_folder(index); + Err *last_error = NULL; + String *last_snapfile = NULL; + String *target_snapfile = NULL; PolyReader_init(self, NULL, folder, snapshot, manager, NULL); DECREF(folder); - while (1) { - String *target_snap_file; - - // If a Snapshot was supplied, use its file. - if (snapshot) { - target_snap_file = Snapshot_Get_Path(snapshot); - if (!target_snap_file) { - THROW(ERR, "Supplied snapshot objects must not be empty"); - } - else { - target_snap_file = (String*)INCREF(target_snap_file); - } + // If a Snapshot was supplied, use its file. + if (snapshot) { + target_snapfile = (String*)INCREF(Snapshot_Get_Path(snapshot)); + if (!target_snapfile) { + THROW(ERR, "Supplied snapshot objects must not be empty"); } - else { - // Otherwise, pick the most recent snap file. - target_snap_file = IxFileNames_latest_snapshot(folder); + } - // No snap file? Looks like the index is empty. We can stop now - // and return NULL. - if (!target_snap_file) { break; } + while (1) { + if (!snapshot) { + // If no Snapshot was supplied, pick the most recent snap file. + DECREF(target_snapfile); + target_snapfile = IxFileNames_latest_snapshot(folder); + + // No snap file? Looks like the index is empty. We can stop now. + if (!target_snapfile) { + DECREF(last_error); + last_error = NULL; + break; + } } - // Derive "generation" of this snapshot file from its name. - uint64_t gen = IxFileNames_extract_gen(target_snap_file); - - if (gen <= last_gen) { + if (last_snapfile + && Str_Equals(target_snapfile, (Obj*)last_snapfile)) { + // The target snapfile hasn't changed since the last iteration. // If a snapshot was supplied, we couldn't read it. Otherwise, // no new snapshot was found which should never happen. Throw // error from previous attempt to read the snapshot. - DECREF(self); - RETHROW(last_error); + break; } - last_gen = gen; + // This is either the first iteration, or we found a newer snapshot. + // Clear error and keep track of snapfile. + DECREF(last_error); + last_error = NULL; + DECREF(last_snapfile); + last_snapfile = (String*)INCREF(target_snapfile); // Get a read lock on the most recent snapshot file if indicated. // There's no need to retry. In the unlikely case that we fail to @@ -378,7 +382,7 @@ PolyReader_do_open(PolyReader *self, Obj *index, Snapshot *snapshot, // FilePurger deleting the snapshot, which means that a newer // snapshot just became available. if (manager) { - if (!S_request_snapshot_lock(self, target_snap_file)) { + if (!S_request_snapshot_lock(self, target_snapfile)) { // Index updated, so try again. last_error = (Err*)INCREF(Err_get_error()); continue; @@ -402,12 +406,11 @@ PolyReader_do_open(PolyReader *self, Obj *index, Snapshot *snapshot, struct try_read_snapshot_context context; context.snapshot = ivars->snapshot; context.folder = folder; - context.path = target_snap_file; + context.path = target_snapfile; last_error = Err_trap(S_try_read_snapshot, &context); if (last_error) { S_release_snapshot_lock(self); - DECREF(target_snap_file); // Index updated, so try again. continue; } @@ -425,18 +428,24 @@ PolyReader_do_open(PolyReader *self, Obj *index, Snapshot *snapshot, last_error = Err_trap(S_try_open_elements, &context); if (last_error) { S_release_snapshot_lock(self); - DECREF(target_snap_file); // Index updated, so try again. continue; } else { // Succeeded. S_init_sub_readers(self, (Vector*)context.seg_readers); DECREF(context.seg_readers); - DECREF(target_snap_file); break; } } + DECREF(target_snapfile); + DECREF(last_snapfile); + + if (last_error) { + DECREF(self); + RETHROW(last_error); + } + return self; } http://git-wip-us.apache.org/repos/asf/lucy/blob/5535d25f/core/Lucy/Store/Lock.c ---------------------------------------------------------------------- diff --git a/core/Lucy/Store/Lock.c b/core/Lucy/Store/Lock.c index 7a4a060..a49925d 100644 --- a/core/Lucy/Store/Lock.c +++ b/core/Lucy/Store/Lock.c @@ -54,9 +54,6 @@ Lock_init(Lock *self, Folder *folder, String *name, int32_t timeout, ivars->name = Str_Clone(name); ivars->interval = interval; - // Derive. - ivars->lock_path = Str_newf("locks/%o.lock", name); - return self; } @@ -65,7 +62,6 @@ Lock_Destroy_IMP(Lock *self) { LockIVARS *const ivars = Lock_IVARS(self); DECREF(ivars->folder); DECREF(ivars->name); - DECREF(ivars->lock_path); SUPER_DESTROY(self, LOCK); } http://git-wip-us.apache.org/repos/asf/lucy/blob/5535d25f/core/Lucy/Store/Lock.cfh ---------------------------------------------------------------------- diff --git a/core/Lucy/Store/Lock.cfh b/core/Lucy/Store/Lock.cfh index 09c2c54..c33ff13 100644 --- a/core/Lucy/Store/Lock.cfh +++ b/core/Lucy/Store/Lock.cfh @@ -31,7 +31,6 @@ abstract class Lucy::Store::Lock inherits Clownfish::Obj { Folder *folder; String *name; - String *lock_path; int32_t timeout; int32_t interval; http://git-wip-us.apache.org/repos/asf/lucy/blob/5535d25f/core/Lucy/Store/LockFileLock.c ---------------------------------------------------------------------- diff --git a/core/Lucy/Store/LockFileLock.c b/core/Lucy/Store/LockFileLock.c index 19d624e..48f1557 100644 --- a/core/Lucy/Store/LockFileLock.c +++ b/core/Lucy/Store/LockFileLock.c @@ -59,6 +59,7 @@ LFLock_init(LockFileLock *self, Folder *folder, String *name, String *host, Lock_init((Lock*)self, folder, name, timeout, interval); LockFileLockIVARS *const ivars = LFLock_IVARS(self); ivars->host = (String*)INCREF(host); + ivars->lock_path = Str_newf("locks/%o.lock", name); ivars->link_path = Str_newf("%o.%o.%i64", ivars->lock_path, host, (int64_t)pid); ivars->exclusive_only = exclusive_only; @@ -357,6 +358,7 @@ LFLock_Destroy_IMP(LockFileLock *self) { LockFileLockIVARS *const ivars = LFLock_IVARS(self); if (ivars->state != LFLOCK_STATE_UNLOCKED) { LFLock_Release(self); } DECREF(ivars->host); + DECREF(ivars->lock_path); DECREF(ivars->link_path); SUPER_DESTROY(self, LOCKFILELOCK); } http://git-wip-us.apache.org/repos/asf/lucy/blob/5535d25f/core/Lucy/Store/LockFileLock.cfh ---------------------------------------------------------------------- diff --git a/core/Lucy/Store/LockFileLock.cfh b/core/Lucy/Store/LockFileLock.cfh index 30fc23a..1a8271b 100644 --- a/core/Lucy/Store/LockFileLock.cfh +++ b/core/Lucy/Store/LockFileLock.cfh @@ -20,6 +20,7 @@ class Lucy::Store::LockFileLock nickname LFLock inherits Lucy::Store::Lock { String *host; + String *lock_path; String *shared_lock_path; String *link_path; int state;