Now it is in separate driver. https://jira.sw.ru/browse/PSBM-129842
Signed-off-by: Kirill Tkhai <[email protected]> --- drivers/md/dm-ploop-cmd.c | 314 ------------------------------------------ drivers/md/dm-ploop-map.c | 107 -------------- drivers/md/dm-ploop-target.c | 11 - drivers/md/dm-ploop.h | 32 ---- 4 files changed, 3 insertions(+), 461 deletions(-) diff --git a/drivers/md/dm-ploop-cmd.c b/drivers/md/dm-ploop-cmd.c index e38d38a2351f..c50749d7d522 100644 --- a/drivers/md/dm-ploop-cmd.c +++ b/drivers/md/dm-ploop-cmd.c @@ -1204,287 +1204,6 @@ static int ploop_flip_upper_deltas(struct ploop *ploop) return cmd.retval; } -static void process_set_push_backup(struct ploop *ploop, struct ploop_cmd *cmd) -{ - struct push_backup *pb = cmd->set_push_backup.pb; - - if (!pb) - cleanup_backup(ploop); - - spin_lock_irq(&ploop->pb_lock); - /* Take bat_rwlock to make pb visible in ploop_map() */ - write_lock(&ploop->bat_rwlock); - swap(ploop->pb, pb); - write_unlock(&ploop->bat_rwlock); - spin_unlock_irq(&ploop->pb_lock); - cmd->retval = 0; - complete(&cmd->comp); /* Last touch of cmd memory */ - - if (pb) - ploop_free_pb(pb); -} - -static void ploop_pb_timer(struct timer_list *timer) -{ - struct push_backup *pb = from_timer(pb, timer, deadline_timer); - u64 deadline, now = get_jiffies_64(); - struct ploop *ploop = pb->ploop; - unsigned long flags; - - spin_lock_irqsave(&ploop->pb_lock, flags); - deadline = pb->deadline_jiffies; - spin_unlock_irqrestore(&ploop->pb_lock, flags); - - if (unlikely(time_before64(now, deadline))) - mod_timer(timer, deadline - now + 1); - else - queue_work(ploop->wq, &ploop->worker); -} - -static struct push_backup *ploop_alloc_pb(struct ploop *ploop, - char *uuid, int timeout) -{ - struct push_backup *pb; - unsigned int size; - void *map; - - pb = kzalloc(sizeof(*pb), GFP_KERNEL); - if (!pb) - return NULL; - snprintf(pb->uuid, sizeof(pb->uuid), "%s", uuid); - pb->ploop = ploop; - init_waitqueue_head(&pb->wq); - INIT_LIST_HEAD(&pb->pending); - pb->rb_root = RB_ROOT; - - pb->deadline_jiffies = S64_MAX; - pb->timeout_in_jiffies = timeout * HZ; - timer_setup(&pb->deadline_timer, ploop_pb_timer, 0); - - size = DIV_ROUND_UP(ploop->nr_bat_entries, 8); - size = round_up(size, sizeof(unsigned long)); - map = kvzalloc(size, GFP_KERNEL); - if (!map) - goto out_pb; - pb->ppb_map = map; - pb->alive = true; - return pb; -out_pb: - kfree(pb); - return NULL; -} - -void ploop_free_pb(struct push_backup *pb) -{ - WARN_ON(!RB_EMPTY_ROOT(&pb->rb_root)); - kvfree(pb->ppb_map); - kfree(pb); -} - -static int ploop_setup_pb_map(struct push_backup *pb, void __user *mask) -{ - unsigned int i, size, nr_bat_entries; - struct ploop *ploop = pb->ploop; - - nr_bat_entries = ploop->nr_bat_entries; - - if (!mask) { - /* Full backup */ - memset(pb->ppb_map, 0xff, nr_bat_entries / 8); - for (i = round_down(nr_bat_entries, 8); i < nr_bat_entries; i++) - set_bit(i, pb->ppb_map); - } else { - /* Partial backup */ - size = DIV_ROUND_UP(nr_bat_entries, 8); - if (copy_from_user(pb->ppb_map, mask, size)) - return -EFAULT; - } - - return 0; -} - -static int ploop_push_backup_start(struct ploop *ploop, char *uuid, - void __user *mask, int timeout) -{ - struct ploop_cmd cmd = { {0} }; - struct push_backup *pb; - char *p = uuid; - int ret; - - cmd.type = PLOOP_CMD_SET_PUSH_BACKUP; - cmd.ploop = ploop; - - if (ploop->pb) - return -EEXIST; - if (timeout <= 0) - return -EINVAL; - /* - * There is no a problem in case of not suspended for the device. - * But this means userspace collects wrong backup. Warn it here. - * Since the device is suspended, we do not care about inflight bios. - */ - if (!dm_suspended(ploop->ti) || ploop->maintaince) - return -EBUSY; - /* Check UUID */ - while (*p) { - if (!isxdigit(*p)) - return -EINVAL; - p++; - } - if (p != uuid + sizeof(pb->uuid) - 1) - return -EINVAL; - pb = ploop_alloc_pb(ploop, uuid, timeout); - if (!pb) - return -ENOMEM; - ret = ploop_setup_pb_map(pb, mask); - if (ret) - goto err_free; - - /* Assign pb in work, to make it visible w/o locks (in work) */ - cmd.set_push_backup.pb = pb; - init_completion(&cmd.comp); - ploop_queue_deferred_cmd(ploop, &cmd); - wait_for_completion(&cmd.comp); - ploop->maintaince = true; - return 0; -err_free: - ploop_free_pb(pb); - return ret; -} - -static int ploop_push_backup_stop(struct ploop *ploop, char *uuid, - int uretval, char *result, unsigned int maxlen) -{ - struct ploop_cmd cmd = { {0} }; - unsigned int sz = 0; - - cmd.type = PLOOP_CMD_SET_PUSH_BACKUP; - cmd.ploop = ploop; - - if (!ploop->pb) - return -EBADF; - if (strcmp(ploop->pb->uuid, uuid)) - return -EINVAL; - - WARN_ON(!ploop->maintaince); - - /* Assign pb in work, to make it visible w/o locks (in work) */ - init_completion(&cmd.comp); - ploop_queue_deferred_cmd(ploop, &cmd); - wait_for_completion(&cmd.comp); - ploop->maintaince = false; - DMEMIT("0"); - return 1; -} - -static int ploop_push_backup_get_uuid(struct ploop *ploop, char *result, - unsigned int maxlen) -{ - struct push_backup *pb = ploop->pb; - unsigned int sz = 0; - - if (pb) - DMEMIT("%s", pb->uuid); - else - result[0] = '\0'; - return 1; -} - -static int ploop_push_backup_read(struct ploop *ploop, char *uuid, - char *result, unsigned int maxlen) -{ - struct push_backup *pb = ploop->pb; - unsigned int left, right, sz = 0; - struct pio *h, *orig_h; - struct rb_node *node; - int ret = 1; - - if (!pb) - return -EBADF; - if (strcmp(uuid, pb->uuid)) - return -EINVAL; - if (!pb->alive) - return -ESTALE; -again: - if (wait_event_interruptible(pb->wq, !list_empty_careful(&pb->pending))) - return -EINTR; - - spin_lock_irq(&ploop->pb_lock); - h = orig_h = list_first_entry_or_null(&pb->pending, typeof(*h), list); - if (unlikely(!h)) { - spin_unlock_irq(&ploop->pb_lock); - goto again; - } - list_del_init(&h->list); - - left = right = h->cluster; - while ((node = rb_prev(&h->node)) != NULL) { - h = rb_entry(node, struct pio, node); - if (h->cluster + 1 != left || list_empty(&h->list)) - break; - list_del_init(&h->list); - left = h->cluster; - } - - h = orig_h; - while ((node = rb_next(&h->node)) != NULL) { - h = rb_entry(node, struct pio, node); - if (h->cluster - 1 != right || list_empty(&h->list)) - break; - list_del_init(&h->list); - right = h->cluster; - } - - DMEMIT("%u:%u", left, right - left + 1); - spin_unlock_irq(&ploop->pb_lock); - return ret; -} - -static int ploop_push_backup_write(struct ploop *ploop, char *uuid, - unsigned int cluster, unsigned int nr) -{ - unsigned int i, nr_bat_entries = ploop->nr_bat_entries; - struct push_backup *pb = ploop->pb; - LIST_HEAD(pio_list); - struct pio *h; - bool has_more = false; - - if (!pb) - return -EBADF; - if (strcmp(uuid, pb->uuid) || !nr) - return -EINVAL; - if (cluster >= nr_bat_entries || nr > nr_bat_entries - cluster) - return -E2BIG; - if (!pb->alive) - return -ESTALE; - - spin_lock_irq(&ploop->pb_lock); - for (i = cluster; i < cluster + nr; i++) - clear_bit(i, pb->ppb_map); - for (i = 0; i < nr; i++) { - h = find_endio_hook_range(ploop, &pb->rb_root, cluster, - cluster + nr - 1); - if (!h) - break; - unlink_postponed_backup_endio(ploop, &pio_list, h); - } - - has_more = !RB_EMPTY_ROOT(&pb->rb_root); - if (has_more) - pb->deadline_jiffies = get_jiffies_64() + pb->timeout_in_jiffies; - else - pb->deadline_jiffies = S64_MAX; - spin_unlock_irq(&ploop->pb_lock); - - if (!list_empty(&pio_list)) { - defer_pios(ploop, NULL, &pio_list); - if (has_more) - mod_timer(&pb->deadline_timer, pb->timeout_in_jiffies + 1); - } - - return 0; -} - /* Handle user commands requested via "message" interface */ void process_deferred_cmd(struct ploop *ploop, struct ploop_index_wb *piwb) __releases(&ploop->deferred_lock) @@ -1513,8 +1232,6 @@ void process_deferred_cmd(struct ploop *ploop, struct ploop_index_wb *piwb) process_tracking_start(ploop, cmd); } else if (cmd->type == PLOOP_CMD_FLIP_UPPER_DELTAS) { process_flip_upper_deltas(ploop, cmd); - } else if (cmd->type == PLOOP_CMD_SET_PUSH_BACKUP) { - process_set_push_backup(ploop, cmd); } else { cmd->retval = -EINVAL; complete(&cmd->comp); @@ -1526,10 +1243,7 @@ static bool msg_wants_down_read(const char *cmd) { /* TODO: kill get_delta_name */ if (!strcmp(cmd, "get_delta_name") || - !strcmp(cmd, "get_img_name") || - !strcmp(cmd, "push_backup_get_uuid") || - !strcmp(cmd, "push_backup_read") || - !strcmp(cmd, "push_backup_write")) + !strcmp(cmd, "get_img_name")) return true; return false; @@ -1540,8 +1254,8 @@ int ploop_message(struct dm_target *ti, unsigned int argc, char **argv, { struct ploop *ploop = ti->private; bool read, forward = true; - int ival, ret = -EPERM; - u64 val, val2; + int ret = -EPERM; + u64 val; if (!capable(CAP_SYS_ADMIN)) goto out; @@ -1592,28 +1306,6 @@ int ploop_message(struct dm_target *ti, unsigned int argc, char **argv, if (argc != 1) goto unlock; ret = ploop_flip_upper_deltas(ploop); - } else if (!strcmp(argv[0], "push_backup_start")) { - if (argc != 4 || kstrtou64(argv[2], 10, &val) < 0 || - kstrtos32(argv[3], 10, &ival) < 0) - goto unlock; - ret = ploop_push_backup_start(ploop, argv[1], (void *)val, ival); - } else if (!strcmp(argv[0], "push_backup_stop")) { - if (argc != 3 || kstrtos32(argv[2], 10, &ival) < 0) - goto unlock; - ret = ploop_push_backup_stop(ploop, argv[1], ival, - result, maxlen); - } else if (!strcmp(argv[0], "push_backup_get_uuid")) { - if (argc != 1) - goto unlock; - ret = ploop_push_backup_get_uuid(ploop, result, maxlen); - } else if (!strcmp(argv[0], "push_backup_read")) { - if (argc != 2) - goto unlock; - ret = ploop_push_backup_read(ploop, argv[1], result, maxlen); - } else if (!strcmp(argv[0], "push_backup_write")) { - if (argc != 3 || sscanf(argv[2], "%llu:%llu", &val, &val2) != 2) - goto unlock; - ret = ploop_push_backup_write(ploop, argv[1], val, val2); } else { ret = -ENOTSUPP; } diff --git a/drivers/md/dm-ploop-map.c b/drivers/md/dm-ploop-map.c index ebcdfb875b10..f8c72d3dedf1 100644 --- a/drivers/md/dm-ploop-map.c +++ b/drivers/md/dm-ploop-map.c @@ -1194,51 +1194,6 @@ static bool postpone_if_cluster_locked(struct ploop *ploop, struct pio *pio, return e_h != NULL; } -static bool postpone_if_required_for_backup(struct ploop *ploop, - struct pio *pio, unsigned int cluster) -{ - struct push_backup *pb = ploop->pb; - bool first, queue_timer = false; - struct pio *h; - - if (likely(!pb || !pb->alive)) - return false; - if (!op_is_write(pio->bi_op)) - return false; - if (!test_bit(cluster, pb->ppb_map)) - return false; - spin_lock_irq(&ploop->pb_lock); - if (!test_bit(cluster, pb->ppb_map)) { - spin_unlock_irq(&ploop->pb_lock); - return false; - } - - h = find_endio_hook(ploop, &pb->rb_root, cluster); - if (h) { - add_endio_pio(h, pio); - spin_unlock_irq(&ploop->pb_lock); - return true; - } - - if (RB_EMPTY_ROOT(&pb->rb_root)) { - pb->deadline_jiffies = get_jiffies_64() + pb->timeout_in_jiffies; - queue_timer = true; - } - - link_endio_hook(ploop, pio, &pb->rb_root, cluster, true); - first = list_empty(&pb->pending); - list_add_tail(&pio->list, &pb->pending); - spin_unlock_irq(&ploop->pb_lock); - - if (first) - wake_up_interruptible(&pb->wq); - - if (queue_timer) - mod_timer(&pb->deadline_timer, pb->timeout_in_jiffies + 1); - - return true; -} - int submit_cluster_cow(struct ploop *ploop, unsigned int level, unsigned int cluster, unsigned int dst_cluster, void (*end_fn)(struct ploop *, int, void *), void *data) @@ -1490,8 +1445,6 @@ static int process_one_deferred_bio(struct ploop *ploop, struct pio *pio, if (postpone_if_cluster_locked(ploop, pio, cluster)) goto out; - if (postpone_if_required_for_backup(ploop, pio, cluster)) - goto out; if (op_is_discard(pio->bi_op)) { handle_discard_pio(ploop, pio, cluster, dst_cluster); @@ -1645,69 +1598,9 @@ static void process_discard_pios(struct ploop *ploop, struct list_head *pios, process_one_discard_pio(ploop, pio, piwb); } -/* Remove from tree bio and endio bio chain */ -void unlink_postponed_backup_endio(struct ploop *ploop, - struct list_head *pio_list, struct pio *h) -{ - struct push_backup *pb = ploop->pb; - - /* Remove from tree and queue attached pios */ - unlink_endio_hook(ploop, &pb->rb_root, h, pio_list); - - /* Unlink from pb->pending */ - list_del_init(&h->list); - - /* Queue relared bio itself */ - list_add_tail(&h->list, pio_list); -} - -void cleanup_backup(struct ploop *ploop) -{ - struct push_backup *pb = ploop->pb; - struct pio *h; - struct rb_node *node; - LIST_HEAD(pio_list); - - spin_lock_irq(&ploop->pb_lock); - /* Take bat_rwlock for visability in kwork */ - write_lock(&ploop->bat_rwlock); - pb->alive = false; - write_unlock(&ploop->bat_rwlock); - - while ((node = pb->rb_root.rb_node) != NULL) { - h = rb_entry(node, struct pio, node); - unlink_postponed_backup_endio(ploop, &pio_list, h); - } - spin_unlock_irq(&ploop->pb_lock); - - if (!list_empty(&pio_list)) - defer_pios(ploop, NULL, &pio_list); - - del_timer_sync(&pb->deadline_timer); -} - -static void check_backup_deadline(struct ploop *ploop) -{ - u64 deadline, now = get_jiffies_64(); - struct push_backup *pb = ploop->pb; - - if (likely(!pb || !pb->alive)) - return; - - spin_lock_irq(&ploop->pb_lock); - deadline = READ_ONCE(pb->deadline_jiffies); - spin_unlock_irq(&ploop->pb_lock); - - if (time_before64(now, deadline)) - return; - - cleanup_backup(ploop); -} - static void check_services_timeout(struct ploop *ploop) { do_discard_cleanup(ploop); - check_backup_deadline(ploop); } void do_ploop_work(struct work_struct *ws) diff --git a/drivers/md/dm-ploop-target.c b/drivers/md/dm-ploop-target.c index d18ff1fa5050..962cab73b390 100644 --- a/drivers/md/dm-ploop-target.c +++ b/drivers/md/dm-ploop-target.c @@ -140,10 +140,6 @@ static void ploop_destroy(struct ploop *ploop) { int i; - if (ploop->pb) { - cleanup_backup(ploop); - ploop_free_pb(ploop->pb); - } if (ploop->wq) { flush_workqueue(ploop->wq); destroy_workqueue(ploop->wq); @@ -296,7 +292,6 @@ static int ploop_ctr(struct dm_target *ti, unsigned int argc, char **argv) rwlock_init(&ploop->bat_rwlock); init_rwsem(&ploop->ctl_rwsem); spin_lock_init(&ploop->deferred_lock); - spin_lock_init(&ploop->pb_lock); INIT_LIST_HEAD(&ploop->deferred_pios); INIT_LIST_HEAD(&ploop->flush_pios); @@ -388,12 +383,6 @@ static void ploop_status(struct dm_target *ti, status_type_t type, p += sprintf(p, "t"); if (READ_ONCE(ploop->noresume)) p += sprintf(p, "n"); - if (ploop->pb) { - if (ploop->pb->alive) - p += sprintf(p, "b"); - else - p += sprintf(p, "B"); - } if (p == stat) p += sprintf(p, "o"); BUG_ON(p - stat >= sizeof(stat)); diff --git a/drivers/md/dm-ploop.h b/drivers/md/dm-ploop.h index a9ef7d71f446..0e2d2dc56fec 100644 --- a/drivers/md/dm-ploop.h +++ b/drivers/md/dm-ploop.h @@ -47,7 +47,6 @@ struct ploop_cmd { #define PLOOP_CMD_UPDATE_DELTA_INDEX 6 #define PLOOP_CMD_TRACKING_START 7 #define PLOOP_CMD_FLIP_UPPER_DELTAS 8 -#define PLOOP_CMD_SET_PUSH_BACKUP 9 struct completion comp; struct ploop *ploop; unsigned int type; @@ -87,9 +86,6 @@ struct ploop_cmd { void *tracking_bitmap; unsigned int tb_nr; } tracking_start; - struct { - struct push_backup *pb; - } set_push_backup; }; }; @@ -129,25 +125,6 @@ struct ploop_index_wb { unsigned int page_nr; }; -struct push_backup { - struct ploop *ploop; - /* Store uuid as string and avoid convertation on every read/write */ - u8 uuid[33]; - bool alive; - - void *ppb_map; - - u64 timeout_in_jiffies; - u64 deadline_jiffies; - struct timer_list deadline_timer; - - /* This tree is for looking for delayed bio by cluster */ - struct rb_root rb_root; - - struct wait_queue_head wq; - struct list_head pending; -}; - /* Metadata page */ struct md_page { struct rb_node node; @@ -229,10 +206,6 @@ struct ploop { /* Maintaince in process */ bool maintaince; - - /* Push Backup */ - struct push_backup *pb; - spinlock_t pb_lock; }; struct ploop_rq { @@ -544,9 +517,6 @@ extern int ploop_clone_and_map(struct dm_target *ti, struct request *rq, union map_info *map_context, struct request **clone); extern int ploop_inflight_bios_ref_switch(struct ploop *ploop, bool killable); extern struct pio *find_lk_of_cluster(struct ploop *ploop, u32 cluster); -extern void unlink_postponed_backup_endio(struct ploop *ploop, - struct list_head *pio_list, - struct pio *h); extern void init_pio(struct ploop *ploop, unsigned int bi_op, struct pio *pio); extern int ploop_rw_page_sync(unsigned rw, struct file *file, u64 index, struct page *page); @@ -565,8 +535,6 @@ extern int submit_cluster_cow(struct ploop *ploop, unsigned int level, extern struct pio * alloc_pio_with_pages(struct ploop *ploop); extern void free_pio_with_pages(struct ploop *ploop, struct pio *pio); extern void pio_prepare_offsets(struct ploop *, struct pio *, unsigned int); -extern void ploop_free_pb(struct push_backup *pb); -extern void cleanup_backup(struct ploop *ploop); extern int ploop_setup_metadata(struct ploop *ploop, struct page *page); extern int ploop_read_delta_metadata(struct ploop *ploop, struct file *file, _______________________________________________ Devel mailing list [email protected] https://lists.openvz.org/mailman/listinfo/devel
