1 /* SPDX-License-Identifier: BSD-3-Clause
2 * Copyright (C) 2023 SUSE LLC.
3 * All rights reserved.
4 */
5
6 #include "thread/thread_internal.h"
7 #include "spdk/blob.h"
8
9
10 #define EXT_DEV_BUFFER_SIZE (4 * 1024 * 1024)
11 uint8_t g_ext_dev_buffer[EXT_DEV_BUFFER_SIZE];
12 struct spdk_io_channel g_ext_io_channel;
13
14 static struct spdk_io_channel *
ext_dev_create_channel(struct spdk_bs_dev * dev)15 ext_dev_create_channel(struct spdk_bs_dev *dev)
16 {
17 return &g_ext_io_channel;
18 }
19
20 static void
ext_dev_destroy_channel(struct spdk_bs_dev * dev,struct spdk_io_channel * channel)21 ext_dev_destroy_channel(struct spdk_bs_dev *dev, struct spdk_io_channel *channel)
22 {
23 }
24
25 static void
ext_dev_destroy(struct spdk_bs_dev * dev)26 ext_dev_destroy(struct spdk_bs_dev *dev)
27 {
28 free(dev);
29 }
30
31 static void
ext_dev_read(struct spdk_bs_dev * dev,struct spdk_io_channel * channel,void * payload,uint64_t lba,uint32_t lba_count,struct spdk_bs_dev_cb_args * cb_args)32 ext_dev_read(struct spdk_bs_dev *dev, struct spdk_io_channel *channel, void *payload,
33 uint64_t lba, uint32_t lba_count,
34 struct spdk_bs_dev_cb_args *cb_args)
35 {
36 uint64_t offset, length;
37
38 offset = lba * dev->blocklen;
39 length = lba_count * dev->blocklen;
40 SPDK_CU_ASSERT_FATAL(offset + length <= EXT_DEV_BUFFER_SIZE);
41
42 if (length > 0) {
43 memcpy(payload, &g_ext_dev_buffer[offset], length);
44 }
45
46 cb_args->cb_fn(cb_args->channel, cb_args->cb_arg, 0);
47 }
48
49 static void
ext_dev_write(struct spdk_bs_dev * dev,struct spdk_io_channel * channel,void * payload,uint64_t lba,uint32_t lba_count,struct spdk_bs_dev_cb_args * cb_args)50 ext_dev_write(struct spdk_bs_dev *dev, struct spdk_io_channel *channel, void *payload,
51 uint64_t lba, uint32_t lba_count,
52 struct spdk_bs_dev_cb_args *cb_args)
53 {
54 uint64_t offset, length;
55
56 offset = lba * dev->blocklen;
57 length = lba_count * dev->blocklen;
58 SPDK_CU_ASSERT_FATAL(offset + length <= EXT_DEV_BUFFER_SIZE);
59
60 memcpy(&g_ext_dev_buffer[offset], payload, length);
61
62 cb_args->cb_fn(cb_args->channel, cb_args->cb_arg, 0);
63 }
64
65 static struct spdk_bs_dev *
init_ext_dev(uint64_t blockcnt,uint32_t blocklen)66 init_ext_dev(uint64_t blockcnt, uint32_t blocklen)
67 {
68 struct spdk_bs_dev *dev = calloc(1, sizeof(*dev));
69
70 SPDK_CU_ASSERT_FATAL(dev != NULL);
71
72 dev->create_channel = ext_dev_create_channel;
73 dev->destroy_channel = ext_dev_destroy_channel;
74 dev->destroy = ext_dev_destroy;
75 dev->read = ext_dev_read;
76 dev->write = ext_dev_write;
77 dev->blockcnt = blockcnt;
78 dev->blocklen = blocklen;
79
80 return dev;
81 }
82