diff --git a/src/box/vinyl.c b/src/box/vinyl.c index 477d2d92542ad3632280587057db17adfb3010e0..fc68f592dbff78422cf21be7d9e27eb6116ee41f 100644 --- a/src/box/vinyl.c +++ b/src/box/vinyl.c @@ -5796,7 +5796,7 @@ vy_join(struct vy_env *env, struct vclock *vclock, struct xstream *stream) recovery = vy_recovery_new(vclock_sum(vclock), true); if (recovery == NULL) goto out_join_cord; - rc = vy_recovery_iterate(recovery, false, vy_join_cb, ctx); + rc = vy_recovery_iterate(recovery, vy_join_cb, ctx); vy_recovery_delete(recovery); /* Send the last range. */ if (rc == 0) @@ -5923,7 +5923,7 @@ vy_gc(struct vy_env *env, struct vy_recovery *recovery, .gc_mask = gc_mask, .gc_lsn = gc_lsn, }; - vy_recovery_iterate(recovery, true, vy_gc_cb, &arg); + vy_recovery_iterate(recovery, vy_gc_cb, &arg); } void @@ -5977,7 +5977,7 @@ vy_backup_cb(const struct vy_log_record *record, void *cb_arg) arg->index_id = record->index_id; } - if (record->type != VY_LOG_CREATE_RUN) + if (record->type != VY_LOG_CREATE_RUN || record->is_dropped) goto out; char path[PATH_MAX]; @@ -6015,7 +6015,7 @@ vy_backup(struct vy_env *env, struct vclock *vclock, .cb = cb, .cb_arg = cb_arg, }; - int rc = vy_recovery_iterate(recovery, false, vy_backup_cb, &arg); + int rc = vy_recovery_iterate(recovery, vy_backup_cb, &arg); vy_recovery_delete(recovery); return rc; } diff --git a/src/box/vy_index.c b/src/box/vy_index.c index 403f546010a62d6de9e1e88a0d2d987218901b36..89e458dbf82df369044aebec86e829114b66e3cf 100644 --- a/src/box/vy_index.c +++ b/src/box/vy_index.c @@ -416,7 +416,11 @@ vy_index_recovery_cb(const struct vy_log_record *record, void *cb_arg) assert(record->index_lsn == index->opts.lsn); index->is_dropped = true; break; + case VY_LOG_PREPARE_RUN: + break; case VY_LOG_CREATE_RUN: + if (record->is_dropped) + break; assert(record->index_lsn == index->opts.lsn); run = vy_run_new(record->run_id); if (run == NULL) @@ -436,6 +440,8 @@ vy_index_recovery_cb(const struct vy_log_record *record, void *cb_arg) goto out; } break; + case VY_LOG_DROP_RUN: + break; case VY_LOG_INSERT_RANGE: assert(record->index_lsn == index->opts.lsn); range = vy_range_new(record->range_id, begin, end, @@ -531,6 +537,14 @@ vy_index_recover(struct vy_index *index, struct vy_recovery *recovery, return vy_index_init_range_tree(index); } + if (index->is_dropped) { + /* + * Initial range is not stored in the metadata log + * for dropped indexes, but we need it for recovery. + */ + return vy_index_init_range_tree(index); + } + /* * Account ranges to the index and check that the range tree * does not have holes or overlaps. diff --git a/src/box/vy_log.c b/src/box/vy_log.c index 965a83a192e80d34d21f1661511506a4b4e371f4..2c7aa84c7b9f76bed1c09c117650359eb507c164 100644 --- a/src/box/vy_log.c +++ b/src/box/vy_log.c @@ -975,8 +975,7 @@ vy_log_create(const struct vclock *vclock, struct vy_recovery *recovery) .dir = &vy_log.dir, .vclock = vclock, }; - if (vy_recovery_iterate(recovery, true, - vy_log_rotate_cb_func, &arg) < 0) + if (vy_recovery_iterate(recovery, vy_log_rotate_cb_func, &arg) < 0) goto err_write_xlog; if (!xlog_is_open(&xlog)) @@ -2009,7 +2008,7 @@ vy_recovery_cb_call(vy_recovery_cb cb, void *cb_arg, static int vy_recovery_iterate_index(struct vy_index_recovery_info *index, - bool include_deleted, vy_recovery_cb cb, void *cb_arg) + vy_recovery_cb cb, void *cb_arg) { struct vy_range_recovery_info *range; struct vy_slice_recovery_info *slice; @@ -2034,29 +2033,6 @@ vy_recovery_iterate_index(struct vy_index_recovery_info *index, return -1; } - if (!include_deleted && index->is_dropped) { - /* - * Do not load the index as it is going to be - * dropped on WAL recovery anyway. Just create - * an initial range to make vy_get() happy. - */ - vy_log_record_init(&record); - record.type = VY_LOG_INSERT_RANGE; - record.index_lsn = index->index_lsn; - record.range_id = INT64_MAX; /* fake id */ - record.begin = record.end = NULL; - if (vy_recovery_cb_call(cb, cb_arg, &record) != 0) - return -1; - - vy_log_record_init(&record); - record.type = VY_LOG_DROP_INDEX; - record.index_lsn = index->index_lsn; - if (vy_recovery_cb_call(cb, cb_arg, &record) != 0) - return -1; - - return 0; - } - if (index->dump_lsn >= 0) { vy_log_record_init(&record); record.type = VY_LOG_DUMP_INDEX; @@ -2067,10 +2043,6 @@ vy_recovery_iterate_index(struct vy_index_recovery_info *index, } rlist_foreach_entry(run, &index->runs, in_index) { - if (!include_deleted && - (run->is_dropped || run->is_incomplete)) - continue; - vy_log_record_init(&record); if (run->is_incomplete) { record.type = VY_LOG_PREPARE_RUN; @@ -2080,6 +2052,7 @@ vy_recovery_iterate_index(struct vy_index_recovery_info *index, } record.index_lsn = index->index_lsn; record.run_id = run->id; + record.is_dropped = run->is_dropped; if (vy_recovery_cb_call(cb, cb_arg, &record) != 0) return -1; @@ -2132,7 +2105,7 @@ vy_recovery_iterate_index(struct vy_index_recovery_info *index, } int -vy_recovery_iterate(struct vy_recovery *recovery, bool include_deleted, +vy_recovery_iterate(struct vy_recovery *recovery, vy_recovery_cb cb, void *cb_arg) { mh_int_t i; @@ -2146,8 +2119,7 @@ vy_recovery_iterate(struct vy_recovery *recovery, bool include_deleted, */ if (index->is_dropped && rlist_empty(&index->runs)) continue; - if (vy_recovery_iterate_index(index, include_deleted, - cb, cb_arg) < 0) + if (vy_recovery_iterate_index(index, cb, cb_arg) < 0) return -1; } return 0; @@ -2161,5 +2133,5 @@ vy_recovery_load_index(struct vy_recovery *recovery, int64_t index_lsn, index = vy_recovery_lookup_index(recovery, index_lsn); if (index == NULL) return 0; - return vy_recovery_iterate_index(index, false, cb, cb_arg); + return vy_recovery_iterate_index(index, cb, cb_arg); } diff --git a/src/box/vy_log.h b/src/box/vy_log.h index 06881fcb1aec6ded59ffbba88b9a140fe59558ec..953dd2938fac5043cc04c673964c9ce6a4bbc9f1 100644 --- a/src/box/vy_log.h +++ b/src/box/vy_log.h @@ -176,6 +176,12 @@ struct vy_log_record { int64_t run_id; /** Unique ID of the run slice. */ int64_t slice_id; + /** + * For VY_LOG_CREATE_RUN record: hint that the run + * is dropped, i.e. there is a VY_LOG_DROP_RUN record + * following this one. + */ + bool is_dropped; /** * Msgpack key for start of the range/slice. * NULL if the range/slice starts from -inf. @@ -369,13 +375,9 @@ typedef int * slices of a range always go right after the range, in the * chronological order, while an index's runs go after the index * and before its ranges. - * - * If @include_deleted is set, this function will also iterate over - * deleted objects, issuing the corresponding "delete" record for each - * of them. */ int -vy_recovery_iterate(struct vy_recovery *recovery, bool include_deleted, +vy_recovery_iterate(struct vy_recovery *recovery, vy_recovery_cb cb, void *cb_arg); /**