From patchwork Fri Jun 9 11:58:56 2023 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Sergei Shtepa X-Patchwork-Id: 105638 Return-Path: Delivered-To: ouuuleilei@gmail.com Received: by 2002:a59:994d:0:b0:3d9:f83d:47d9 with SMTP id k13csp957429vqr; Fri, 9 Jun 2023 06:43:58 -0700 (PDT) X-Google-Smtp-Source: ACHHUZ75MwRi9rpihY9rErRuFSQ6qZBmi+97naeEU36nxuFNwLgqi4sirPZuDEDK7Lcpm+v+jiuI X-Received: by 2002:a17:902:b702:b0:1b0:26f0:4c8e with SMTP id d2-20020a170902b70200b001b026f04c8emr869140pls.69.1686318238643; Fri, 09 Jun 2023 06:43:58 -0700 (PDT) ARC-Seal: i=1; a=rsa-sha256; t=1686318238; cv=none; d=google.com; s=arc-20160816; b=VEwTf/I434KreaeYPQUXXKTeQ5uk+XnvtTAoxElPWLM9aMDPgkAp1b7wC3fvOpTCVw K2ZVHEOJvZ6XrKYr2C1OtPVUSMnwqe4jImsbzfG0s3B/lZsXHE3q36ZTiFBADX9GTlYL fLjwLaMTPJcc+5e0/hGtLygT8iBW5S9p9uMfaGQhC2aqOg0ep4b+EUav8GlXtRuKdSmu 1Cojf4qUzRVPaMUO4zdmIsPZvo/4k2GqPTi4Y5U5ePdT85v04suEYV0FCX8jA4uRDnPg 5XPrVbE1K0QJq6QrmWFk6DsW9Xb/45ia0MMZdvfbhRvuTqzV1Qyag5IQXHqiGWiWBBYK zxZw== ARC-Message-Signature: i=1; a=rsa-sha256; c=relaxed/relaxed; d=google.com; s=arc-20160816; h=list-id:precedence:content-transfer-encoding:mime-version :references:in-reply-to:message-id:date:subject:cc:to:from :dkim-signature; bh=SLOWvZa9vJo565OIEup8WCzwZ50SqCqIg3IOsqiIpd8=; b=ifwiXNlHOtXgeq2Ym5HZDJCzVV4p2GZZEyHQ/7CrrM7Go6iEBiLRp7pku70Ilu9UxL rv2qgHeTgS9+WHC0P0tXaQWQHUAJMlWaoPui1b+sz91+ZQTyZC4YwMg3ODAkeAt/ZMKl YZ4RIGdVIj287tsKaQvtFoIrLbfbYBfIoTErNIZ4w8MSEmG091lPkkQLs3dTM8rCiuBA frxLbZONT0Fsbn44h5z6s5J3AO/WxnfZEBp43lHh9gTtGOrN0EifyOUeO3HRvd3krCNk iKkzUa7qfl5Ru/YTDlCoOdr3UU1ew9prSP5fbrINGDc2VBuOFoVOyTUux8u9aWT0GCWG xjTQ== ARC-Authentication-Results: i=1; mx.google.com; dkim=pass header.i=@veeam.com header.s=mx4-2022 header.b=GHGB+24O; spf=pass (google.com: domain of linux-kernel-owner@vger.kernel.org designates 2620:137:e000::1:20 as permitted sender) smtp.mailfrom=linux-kernel-owner@vger.kernel.org; dmarc=pass (p=REJECT sp=REJECT dis=NONE) header.from=veeam.com Received: from out1.vger.email (out1.vger.email. [2620:137:e000::1:20]) by mx.google.com with ESMTP id d11-20020a170902cecb00b001a6e1b073cdsi2721963plg.639.2023.06.09.06.43.43; Fri, 09 Jun 2023 06:43:58 -0700 (PDT) Received-SPF: pass (google.com: domain of linux-kernel-owner@vger.kernel.org designates 2620:137:e000::1:20 as permitted sender) client-ip=2620:137:e000::1:20; Authentication-Results: mx.google.com; dkim=pass header.i=@veeam.com header.s=mx4-2022 header.b=GHGB+24O; spf=pass (google.com: domain of linux-kernel-owner@vger.kernel.org designates 2620:137:e000::1:20 as permitted sender) smtp.mailfrom=linux-kernel-owner@vger.kernel.org; dmarc=pass (p=REJECT sp=REJECT dis=NONE) header.from=veeam.com Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S230400AbjFINWb (ORCPT + 99 others); Fri, 9 Jun 2023 09:22:31 -0400 Received: from lindbergh.monkeyblade.net ([23.128.96.19]:45626 "EHLO lindbergh.monkeyblade.net" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S231396AbjFINW3 (ORCPT ); Fri, 9 Jun 2023 09:22:29 -0400 X-Greylist: delayed 119 seconds by postgrey-1.37 at lindbergh.monkeyblade.net; Fri, 09 Jun 2023 06:22:28 PDT Received: from mx4.veeam.com (mx4.veeam.com [104.41.138.86]) by lindbergh.monkeyblade.net (Postfix) with ESMTPS id 108B7180; Fri, 9 Jun 2023 06:22:28 -0700 (PDT) Received: from mail.veeam.com (prgmbx01.amust.local [172.24.128.102]) (using TLSv1.2 with cipher ECDHE-RSA-AES256-GCM-SHA384 (256/256 bits)) (No client certificate requested) by mx4.veeam.com (Postfix) with ESMTPS id 9E5A52B42E; Fri, 9 Jun 2023 15:07:05 +0300 (MSK) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=veeam.com; s=mx4-2022; t=1686312425; bh=SLOWvZa9vJo565OIEup8WCzwZ50SqCqIg3IOsqiIpd8=; h=From:To:CC:Subject:Date:In-Reply-To:References:From; b=GHGB+24O9PSDaRBLKgrbNR6Hr9z102CSwo5YhbnrnUx+K1Vk1VqoT9PCPV3cl9qo+ /OqDhsS/t4aZSnMv0vuOV+GC7PaYvvk3SoTfRIES1mK5Uj5w1CqLBckK4rgH3BBBu9 luh9137icizk3A8R0bJKFRMsRjUNqpii9g5jFb5WPCZ9PoI2V7r5hWtWQpKAYhqK6H z3KPHuAFYFI1OS40a+AaTVy0/cQKpEYbVSnYVw12fq57dsgI/TVK2HpjL9QW1VCPDg MT/Jqoqj8XrH+8LaleHjsL4qCQ2HHcC9gHuvMXGxcODjCQwovoy+bDwNOLQMso/fmY qw3R/2PPzBfqQ== Received: from ssh-deb10-ssd-vb.amust.local (172.24.10.107) by prgmbx01.amust.local (172.24.128.102) with Microsoft SMTP Server (version=TLS1_2, cipher=TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384) id 15.2.1118.26; Fri, 9 Jun 2023 14:07:04 +0200 From: Sergei Shtepa To: , , , CC: , , , , , , , , , , , , Subject: [PATCH v4 09/11] blksnap: event queue from the difference storage Date: Fri, 9 Jun 2023 13:58:56 +0200 Message-ID: <20230609115858.4737-9-sergei.shtepa@veeam.com> X-Mailer: git-send-email 2.20.1 In-Reply-To: <20230609115858.4737-1-sergei.shtepa@veeam.com> References: <20230609115858.4737-1-sergei.shtepa@veeam.com> MIME-Version: 1.0 X-Originating-IP: [172.24.10.107] X-ClientProxiedBy: prgmbx02.amust.local (172.24.128.103) To prgmbx01.amust.local (172.24.128.102) X-EsetResult: clean, is OK X-EsetId: 37303A2924031554627C6B X-Veeam-MMEX: True X-Spam-Status: No, score=-2.1 required=5.0 tests=BAYES_00,DKIMWL_WL_HIGH, DKIM_SIGNED,DKIM_VALID,DKIM_VALID_AU,DKIM_VALID_EF,RCVD_IN_DNSWL_NONE, RCVD_IN_MSPIKE_H2,SPF_HELO_NONE,SPF_PASS,T_SCC_BODY_TEXT_LINE, URIBL_BLOCKED autolearn=ham autolearn_force=no version=3.4.6 X-Spam-Checker-Version: SpamAssassin 3.4.6 (2021-04-09) on lindbergh.monkeyblade.net Precedence: bulk List-ID: X-Mailing-List: linux-kernel@vger.kernel.org X-getmail-retrieved-from-mailbox: =?utf-8?q?INBOX?= X-GMAIL-THRID: =?utf-8?q?1768232833397471063?= X-GMAIL-MSGID: =?utf-8?q?1768232833397471063?= Provides transmission of events from the difference storage to the user process. Only two events are currently defined. The first is that there are few free regions in the difference storage. The second is that the request for a free region for storing differences failed with an error, since there are no more free regions left in the difference storage (the snapshot overflow state). Co-developed-by: Christoph Hellwig Signed-off-by: Christoph Hellwig Signed-off-by: Sergei Shtepa --- drivers/block/blksnap/event_queue.c | 87 +++++++++++++++++++++++++++++ drivers/block/blksnap/event_queue.h | 65 +++++++++++++++++++++ 2 files changed, 152 insertions(+) create mode 100644 drivers/block/blksnap/event_queue.c create mode 100644 drivers/block/blksnap/event_queue.h -- 2.20.1 diff --git a/drivers/block/blksnap/event_queue.c b/drivers/block/blksnap/event_queue.c new file mode 100644 index 000000000000..5d3bedd63c10 --- /dev/null +++ b/drivers/block/blksnap/event_queue.c @@ -0,0 +1,87 @@ +// SPDX-License-Identifier: GPL-2.0 +/* Copyright (C) 2023 Veeam Software Group GmbH */ +#define pr_fmt(fmt) KBUILD_MODNAME "-event_queue: " fmt + +#include +#include +#include "event_queue.h" + +void event_queue_init(struct event_queue *event_queue) +{ + INIT_LIST_HEAD(&event_queue->list); + spin_lock_init(&event_queue->lock); + init_waitqueue_head(&event_queue->wq_head); +} + +void event_queue_done(struct event_queue *event_queue) +{ + struct event *event; + + spin_lock(&event_queue->lock); + while (!list_empty(&event_queue->list)) { + event = list_first_entry(&event_queue->list, struct event, + link); + list_del(&event->link); + event_free(event); + } + spin_unlock(&event_queue->lock); +} + +int event_gen(struct event_queue *event_queue, gfp_t flags, int code, + const void *data, int data_size) +{ + struct event *event; + + event = kzalloc(sizeof(struct event) + data_size + 1, flags); + if (!event) + return -ENOMEM; + + event->time = ktime_get(); + event->code = code; + event->data_size = data_size; + memcpy(event->data, data, data_size); + + pr_debug("Generate event: time=%lld code=%d data_size=%d\n", + event->time, event->code, event->data_size); + + spin_lock(&event_queue->lock); + list_add_tail(&event->link, &event_queue->list); + spin_unlock(&event_queue->lock); + + wake_up(&event_queue->wq_head); + return 0; +} + +struct event *event_wait(struct event_queue *event_queue, + unsigned long timeout_ms) +{ + int ret; + + ret = wait_event_interruptible_timeout(event_queue->wq_head, + !list_empty(&event_queue->list), timeout_ms); + if (ret >= 0) { + struct event *event = ERR_PTR(-ENOENT); + + spin_lock(&event_queue->lock); + if (!list_empty(&event_queue->list)) { + event = list_first_entry(&event_queue->list, + struct event, link); + list_del(&event->link); + } + spin_unlock(&event_queue->lock); + + if (IS_ERR(event)) + pr_debug("Queue list is empty, timeout_ms=%lu\n", timeout_ms); + else + pr_debug("Event received: time=%lld code=%d\n", + event->time, event->code); + return event; + } + if (ret == -ERESTARTSYS) { + pr_debug("event waiting interrupted\n"); + return ERR_PTR(-EINTR); + } + + pr_err("Failed to wait event. errno=%d\n", abs(ret)); + return ERR_PTR(ret); +} diff --git a/drivers/block/blksnap/event_queue.h b/drivers/block/blksnap/event_queue.h new file mode 100644 index 000000000000..7f1209bbfc98 --- /dev/null +++ b/drivers/block/blksnap/event_queue.h @@ -0,0 +1,65 @@ +/* SPDX-License-Identifier: GPL-2.0 */ +/* Copyright (C) 2023 Veeam Software Group GmbH */ +#ifndef __BLKSNAP_EVENT_QUEUE_H +#define __BLKSNAP_EVENT_QUEUE_H + +#include +#include +#include +#include +#include + +/** + * struct event - An event to be passed to the user space. + * @link: + * The list header allows to combine events from the queue. + * @time: + * A timestamp indicates when an event occurred. + * @code: + * Event code. + * @data_size: + * The number of bytes in the event data array. + * @data: + * An array of event data. The allowed size of the array is limited + * so that the size of the entire structure does not exceed PAGE_SIZE. + * + * Events can be different, so they contain different data. The size of the + * data array is not defined exactly, but it has limitations. The size of + * the event structure may exceed the PAGE_SIZE. + */ +struct event { + struct list_head link; + ktime_t time; + int code; + int data_size; + char data[]; +}; + +/** + * struct event_queue - A queue of &struct event. + * @list: + * Linked list for storing events. + * @lock: + * Spinlock allows to guarantee safety of the linked list. + * @wq_head: + * A wait queue allows to put a user thread in a waiting state until + * an event appears in the linked list. + */ +struct event_queue { + struct list_head list; + spinlock_t lock; + struct wait_queue_head wq_head; +}; + +void event_queue_init(struct event_queue *event_queue); +void event_queue_done(struct event_queue *event_queue); + +int event_gen(struct event_queue *event_queue, gfp_t flags, int code, + const void *data, int data_size); +struct event *event_wait(struct event_queue *event_queue, + unsigned long timeout_ms); +static inline void event_free(struct event *event) +{ + kfree(event); +}; +#endif /* __BLKSNAP_EVENT_QUEUE_H */