Motr  M0
stobio.c
Go to the documentation of this file.
1 /*
2  * Copyright (c) 2011-2020 Seagate Technology LLC and/or its Affiliates
3  *
4  * Licensed under the Apache License, Version 2.0 (the "License");
5  * you may not use this file except in compliance with the License.
6  * You may obtain a copy of the License at
7  *
8  * http://www.apache.org/licenses/LICENSE-2.0
9  *
10  * Unless required by applicable law or agreed to in writing, software
11  * distributed under the License is distributed on an "AS IS" BASIS,
12  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13  * See the License for the specific language governing permissions and
14  * limitations under the License.
15  *
16  * For any questions about this software or licensing,
17  * please email opensource@seagate.com or cortx-questions@seagate.com.
18  *
19  */
20 
21 
22 #include <stdlib.h> /* system */
23 
24 #include "lib/arith.h" /* max_check */
25 #include "lib/memory.h"
26 #include "lib/misc.h" /* ARRAY_SIZE */
27 #include "lib/mutex.h"
28 #include "lib/string.h" /* m0_strdup */
29 #include "ut/stob.h"
30 #include "ut/ut.h"
31 
32 #include "stob/domain.h"
33 #include "stob/io.h"
34 #include "stob/stob.h"
35 
36 #define WITH_LOCK(lock, action, args...) ({ \
37  struct m0_mutex *lk = lock; \
38  m0_mutex_lock(lk); \
39  action(args); \
40  m0_mutex_unlock(lk); \
41  })
42 
43 enum {
44  RW_BUFF_NR = 10,
45  MIN_BUFF_SIZE = 4096,
47  TEST_NR = 10
48 };
49 
50 enum {
51  M0_STOB_UT_DOM_KEY = 0xec0de,
53 };
54 
55 struct stobio_test {
56  /* ctrl part */
57  struct m0_stob *st_obj;
58  uint64_t st_stob_key;
59  /* Real block device, if any */
60  char *st_dev_path;
61 
63  struct m0_stob_io st_io;
64 
65  /* this flag controls whether to use direct IO */
67 
70  uint32_t st_block_shift;
71  size_t st_block_size;
72 
73  /* read/write buffers */
78 
79  /* read/write vectors */
82 };
83 
84 /* Test block device */
85 static const char test_blkdev[] = "/dev/loop0";
86 
87 static const char *test_location;
88 static const char *test_location_dio;
89 static const char linux_location[] = "linuxstob:./__s";
90 static const char linux_location_dio[] = "linuxstob:./__s_dio";
91 static const char perf_location[] = "perfstob:./__s";
92 static const char perf_location_dio[] = "perfstob:./__s_dio";
93 static struct m0_stob_domain *test_dom;
95 
96 /* sync object for init/fini */
97 static struct m0_mutex lock;
98 static struct m0_thread thread[TEST_NR];
99 
100 #define ST_ID(id) .st_stob_key = id
101 static struct stobio_test tests[TEST_NR] = {
102  /* buffered IO tests */
103  [0] = { ST_ID(0x01), .st_directio = false },
104  [1] = { ST_ID(0x02), .st_directio = false },
105  [2] = { ST_ID(0x03), .st_directio = false },
106  [3] = { ST_ID(0x04), .st_directio = false },
107  [4] = { ST_ID(0x05), .st_directio = false },
108 
109  /* direct IO tests */
110  [5] = { ST_ID(0x06), .st_directio = true },
111  [6] = { ST_ID(0x07), .st_directio = true },
112  [7] = { ST_ID(0x08), .st_directio = true },
113  [8] = { ST_ID(0x09), .st_directio = true },
114  [9] = { ST_ID(0x0a), .st_directio = true, .st_dev_path="/dev/loop0" },
115 };
116 
117 #undef ST_ID
118 
119 static char *stob_backingfile_get(const struct stobio_test *test)
120 {
121  char backingfile[PATH_MAX];
122  int rc;
123  struct m0_fid fid;
124 
125  m0_fid_set(&fid, 0, test->st_stob_key);
126  rc = sprintf(backingfile, "%s/%" PRIx64 ":%" PRIx64 "",
127  test->st_dom->sd_location_data,
129  M0_UT_ASSERT(rc < sizeof(backingfile));
130  M0_UT_ASSERT(backingfile[0] != '/');
131  return m0_strdup(backingfile);
132 }
133 
134 /*
135  * Assumes that we are dealing with loop-back device /dev/loop0
136  * We don't deal with real device in UT.
137  */
138 static void stob_dev_init(const struct stobio_test *test)
139 {
140  int result;
141  m0_bcount_t dev_sz;
142  char sysbuf[PATH_MAX];
143  char *backingfile;
144 
145  if (!m0_streq(test->st_dev_path, test_blkdev))
146  return;
147 
148  /* Device size in KB */
150  TEST_NR * TEST_NR;
151 
152  /* Device size in MB */
153  dev_sz = dev_sz/1024 + 1;
154 
155  backingfile = stob_backingfile_get(test);
156  sprintf(sysbuf, "dd if=/dev/zero of=%s bs=1M count=%lu >/dev/null 2>&1",
157  backingfile, (unsigned long)dev_sz);
158  result = system(sysbuf);
159  M0_UT_ASSERT(result == 0);
160 
161  sprintf(sysbuf, "losetup -d %s >/dev/null 2>&1", test->st_dev_path);
162  result = system(sysbuf);
163  (void)result;
164  sprintf(sysbuf, "losetup %s %s", test->st_dev_path, backingfile);
165  result = system(sysbuf);
166  M0_UT_ASSERT(result == 0);
167 
168  m0_free(backingfile);
169 }
170 
171 static void stob_dev_fini(const struct stobio_test *test)
172 {
173  int result;
174  char sysbuf[PATH_MAX];
175  char *backingfile;
176 
177  if (test->st_dev_path == NULL ||
178  !m0_streq(test->st_dev_path, test_blkdev))
179  return;
180 
181  sprintf(sysbuf, "losetup -d %s", test->st_dev_path);
182  result = system(sysbuf);
183  M0_UT_ASSERT(result == 0);
184  backingfile = stob_backingfile_get(test);
185  result = sprintf(sysbuf, "rm -f %s", backingfile);
186  M0_UT_ASSERT(result < sizeof(sysbuf));
187  result = system(sysbuf);
188  M0_UT_ASSERT(result == 0);
189  m0_free(backingfile);
190 }
191 
192 static void stobio_io_prepare(struct stobio_test *test,
193  struct m0_stob_io *io)
194 {
195  io->si_flags = 0;
197  io->si_user.ov_vec.v_count = test->st_wrvec;
198 
200  io->si_stob.iv_vec.v_count = test->st_wrvec;
201  io->si_stob.iv_index = test->st_rdvec;
202 }
203 
205  struct m0_stob_io *io)
206 {
208  io->si_user.ov_buf = (void **) test->st_wrbuf_packed;
210 }
211 
213  struct m0_stob_io *io)
214 {
215  io->si_opcode = SIO_READ;
216  io->si_user.ov_buf = (void **) test->st_rdbuf_packed;
218 }
219 
220 static void stobio_write(struct stobio_test *test)
221 {
222  struct m0_stob_io io;
223  struct m0_clink clink;
224  int result;
225 
227 
229 
232 
233  result = m0_stob_io_prepare_and_launch(&io, test->st_obj, NULL, NULL);
234  M0_UT_ASSERT(result == 0);
235 
237 
238  M0_UT_ASSERT(io.si_rc == 0);
240  test->st_rw_buf_size_in_blocks * RW_BUFF_NR);
241 
244 
246 }
247 
248 static void stobio_read(struct stobio_test *test)
249 {
250  struct m0_stob_io io;
251  struct m0_clink clink;
252  int result;
253 
255 
257 
260 
261  result = m0_stob_io_prepare_and_launch(&io, test->st_obj, NULL, NULL);
262  M0_UT_ASSERT(result == 0);
263 
265 
266  M0_UT_ASSERT(io.si_rc == 0);
267  M0_UT_ASSERT(io.si_count == test->st_rw_buf_size_in_blocks * RW_BUFF_NR);
268 
271 
273 }
274 
276 {
277  int i;
278 
279  for (i = 0; i < ARRAY_SIZE(test->st_rdbuf); ++i) {
280  test->st_rdbuf[i] = m0_alloc_aligned(test->st_rw_buf_size,
281  test->st_block_shift);
282  test->st_rdbuf_packed[i] = m0_stob_addr_pack(test->st_rdbuf[i]
283  , test->st_block_shift);
284  M0_UT_ASSERT(test->st_rdbuf[i] != NULL);
285  }
286 
287  for (i = 0; i < ARRAY_SIZE(test->st_wrbuf); ++i) {
288  test->st_wrbuf[i] = m0_alloc_aligned(test->st_rw_buf_size,
289  test->st_block_shift);
290  test->st_wrbuf_packed[i] = m0_stob_addr_pack(test->st_wrbuf[i],
291  test->st_block_shift);
292  M0_UT_ASSERT(test->st_wrbuf[i] != NULL);
293  }
294 }
295 
297 {
298  int i;
299 
300  for (i = 0; i < ARRAY_SIZE(test->st_rdbuf); ++i) {
301  m0_free(test->st_rdbuf[i]);
302  test->st_rdbuf_packed[i] = 0;
303  }
304 
305  for (i = 0; i < ARRAY_SIZE(test->st_wrbuf); ++i) {
306  m0_free(test->st_wrbuf[i]);
307  test->st_wrbuf_packed[i] = 0;
308  }
309 }
310 
311 static int stobio_storage_init(void)
312 {
313  int result;
314 
316 
318  NULL, &test_dom);
319  M0_UT_ASSERT(result == 0);
321 
323  "directio=true", M0_STOB_UT_DOM_DIO_KEY,
324  NULL, &test_dom_dio);
325  M0_UT_ASSERT(result == 0);
327 
328  return result;
329 }
330 
331 static void stobio_storage_fini(void)
332 {
333  int result;
334 
336  M0_UT_ASSERT(result == 0);
338  M0_UT_ASSERT(result == 0);
339 }
340 
341 static int stobio_init(struct stobio_test *test)
342 {
343  int result;
344  struct m0_stob_id stob_id;
345 
346  test->st_dom = test->st_directio ? test_dom_dio : test_dom;
347  m0_stob_id_make(0, test->st_stob_key,
348  m0_stob_domain_id_get(test->st_dom), &stob_id);
349  result = m0_stob_find(&stob_id, &test->st_obj);
350  M0_UT_ASSERT(result == 0);
351 
352  if (test->st_dev_path != NULL)
354 
355  result = m0_stob_locate(test->st_obj);
356  M0_UT_ASSERT(result == 0);
357  result = m0_ut_stob_create(test->st_obj, test->st_dev_path, NULL);
358  M0_UT_ASSERT(result == 0);
359 
360  test->st_block_shift = m0_stob_block_shift(test->st_obj);
361  test->st_block_size = 1 << test->st_block_shift;
362  /* buf_size is chosen so it would be at least MIN_BUFF_SIZE in bytes
363  * or it would consist of at least MIN_BUFF_SIZE_IN_BLOCKS blocks */
364  test->st_rw_buf_size = max_check(MIN_BUFF_SIZE,
365  (1 << test->st_block_shift) * MIN_BUFF_SIZE_IN_BLOCKS);
366  test->st_rw_buf_size_in_blocks = test->st_rw_buf_size / test->st_block_size;
367 
369 
370  return 0;
371 }
372 
373 static void stobio_fini(struct stobio_test *test)
374 {
375  int rc;
376 
377  rc = m0_stob_destroy(test->st_obj, NULL);
378  M0_UT_ASSERT(rc == 0);
381 }
382 
383 static void stobio_rwsegs_prepare(struct stobio_test *test, int starts_from)
384 {
385  int i;
386  for (i = 0; i < RW_BUFF_NR; ++i) {
387  test->st_wrvec[i] = test->st_rw_buf_size_in_blocks;
388  test->st_rdvec[i] = test->st_rw_buf_size_in_blocks
389  * (2 * i + 1 + starts_from);
390  memset(test->st_wrbuf[i], ('a' + i) | 1, test->st_rw_buf_size);
391  }
392 }
393 
395  int starts_from)
396 {
397  int i;
398  for (i = 0; i < RW_BUFF_NR; ++i) {
399  test->st_wrvec[i] = test->st_rw_buf_size_in_blocks;
400  test->st_rdvec[i] = test->st_rw_buf_size_in_blocks
401  * (i + 1 + starts_from);
402  memset(test->st_wrbuf[i], ('A' + i) | 1, test->st_rw_buf_size);
403  }
404 }
405 
406 static void overlapped_rw_test(struct stobio_test *test, int starts_from)
407 {
408  int i;
409  int j;
410 
412 
413  /* Write overlapped segments */
414  stobio_rwsegs_prepare(test, starts_from);
416 
419 
420  /* read WR data */
421  stobio_rwsegs_prepare(test, starts_from);
422  stobio_read(test);
423 
424  /* check WR data */
425  for (i = 0; i < RW_BUFF_NR/2; ++i) {
426  for (j = 0; j < test->st_rw_buf_size; ++j)
427  M0_UT_ASSERT(test->st_rdbuf[i][j] == (('A' + 2 * i) | 1));
428  }
429 
430  for (; i < RW_BUFF_NR; ++i) {
431  for (j = 0; j < test->st_rw_buf_size; ++j)
432  M0_UT_ASSERT(test->st_rdbuf[i][j] == (('a' + i) | 1));
433  }
434 
436 }
437 
438 static void test_stobio(void)
439 {
440  int i;
441  int result;
442 
444 
445  result = stobio_storage_init();
446  M0_UT_ASSERT(result == 0);
447 
448  for (i = 0; i < TEST_NR; ++i) {
449  result = M0_THREAD_INIT
450  (&thread[i], int, NULL,
451  LAMBDA(void, (int x)
452  { overlapped_rw_test(&tests[x], x*100); } ), i,
453  "overlap_test%d", i);
454  M0_UT_ASSERT(result == 0);
455  }
456 
457  for (i = 0; i < TEST_NR; ++i) {
460  }
461 
463 
465 }
466 
467 static void test_short_read(void)
468 {
469  int i;
470  int j;
471  int result;
472  struct stobio_test *test = &tests[0];
473 
475 
476  result = stobio_storage_init();
477  M0_UT_ASSERT(result == 0);
478 
480 
483 
485  for (i = 0; i < RW_BUFF_NR; ++i)
486  test->st_rdvec[i]++;
487  stobio_read(test);
488 
489  for (i = 0; i < RW_BUFF_NR; ++i) {
490  char expected = ('a' + i) | 1;
491  for (j = 0; j < test->st_rw_buf_size - test->st_block_size; ++j)
492  M0_UT_ASSERT(test->st_rdbuf[i][j] == expected);
493  for (; j < test->st_rw_buf_size; ++j)
494  M0_UT_ASSERT(test->st_rdbuf[i][j] == 0);
495  }
496 
500 }
501 
502 /*
503  * In stob_io, indexvec can have different number of elements
504  * than bufvec. Stob implementation will do all the splitting and merging
505  * internally, as necessary.
506  * This test tries to write 1M at offset 1M with a single indexvec. Data
507  * is available in 256 4K buffers.
508  */
509 static void test_single_ivec()
510 {
511  int i;
512  int result;
513  struct m0_stob_io io;
514  struct m0_clink clink;
515  enum {
516  SHIFT = 0,
517  VEC_NR = 256,
518  BLOCK_SIZE = 4096,
519  OFFSET_OR_SIZE = 1048576,
520  };
521  /* read/write buffers */
522  char *st_rdbuf[VEC_NR];
523  char *st_rdbuf_packed[VEC_NR];
524  char *st_wrbuf[VEC_NR];
525  char *st_wrbuf_packed[VEC_NR];
526  /* read/write vectors */
527  m0_bcount_t index[1] = {OFFSET_OR_SIZE >> SHIFT};
528  m0_bcount_t stob_size[1] = {OFFSET_OR_SIZE >> SHIFT};
529  m0_bcount_t size[VEC_NR];
530 
531  struct stobio_test *test = &tests[0];
532 
534  result = stobio_storage_init();
535  M0_UT_ASSERT(result == 0);
537 
538  M0_UT_ASSERT(test->st_block_shift == SHIFT);
539 
540  for (i = 0; i < VEC_NR; ++i) {
544  size[i] = BLOCK_SIZE >> SHIFT;
545 
549  if (SHIFT)
550  memset(st_wrbuf[i], ('a' + i) | 1, SHIFT);
551  }
552 
553  /* Write */
556  io.si_flags = 0;
557  io.si_user.ov_vec.v_nr = VEC_NR;
559  io.si_user.ov_buf = (void **) st_wrbuf_packed;
560  io.si_stob.iv_vec.v_nr = 1;
563 
566  result = m0_stob_io_prepare_and_launch(&io, test->st_obj, NULL, NULL);
567  M0_UT_ASSERT(result == 0);
568 
570  M0_UT_ASSERT(io.si_rc == 0);
571 
575 
576  /* Read */
579  io.si_flags = 0;
580  io.si_user.ov_vec.v_nr = VEC_NR;
582  io.si_user.ov_buf = (void **) st_rdbuf_packed;
583  io.si_stob.iv_vec.v_nr = 1;
586 
589  result = m0_stob_io_prepare_and_launch(&io, test->st_obj, NULL, NULL);
590  M0_UT_ASSERT(result == 0);
591 
593  M0_ASSERT(io.si_rc == 0);
594 
598 
599  for (i = 0; i < VEC_NR; ++i)
600  M0_ASSERT(memcmp(st_wrbuf[i], st_rdbuf[i], BLOCK_SIZE) == 0);
601 
605 
606  for (i = 0; i < VEC_NR; ++i) {
607  m0_free(st_wrbuf[i]);
608  m0_free(st_rdbuf[i]);
609  }
610 }
611 
613 {
616 
617  test_stobio();
618  test_short_read();
620 
622 }
623 
625 {
628 
629  test_stobio();
630  test_short_read();
632 
634 }
635 
636 /*
637  * Local variables:
638  * c-indentation-style: "K&R"
639  * c-basic-offset: 8
640  * tab-width: 8
641  * fill-column: 80
642  * scroll-step: 1
643  * End:
644  */
M0_INTERNAL void m0_chan_wait(struct m0_clink *link)
Definition: chan.c:336
static void stobio_rwsegs_overlapped_prepare(struct stobio_test *test, int starts_from)
Definition: stobio.c:394
#define M0_PRE(cond)
enum m0_stob_io_flags si_flags
Definition: io.h:290
char * st_rdbuf_packed[RW_BUFF_NR]
Definition: stobio.c:75
#define m0_strdup(s)
Definition: string.h:43
M0_INTERNAL void m0_stob_io_fini(struct m0_stob_io *io)
Definition: io.c:122
#define NULL
Definition: misc.h:38
struct m0_stob_domain * st_dom
Definition: stobio.c:62
M0_INTERNAL void m0_clink_init(struct m0_clink *link, m0_chan_cb_t cb)
Definition: chan.c:201
size_t st_block_size
Definition: stobio.c:71
Definition: io.h:230
M0_INTERNAL int m0_stob_locate(struct m0_stob *stob)
Definition: stob.c:128
M0_INTERNAL void m0_clink_del_lock(struct m0_clink *link)
Definition: chan.c:293
int m0_thread_join(struct m0_thread *q)
Definition: kthread.c:169
static bool x
Definition: sm.c:168
static void stobio_read(struct stobio_test *test)
Definition: stobio.c:248
static void stobio_rw_buffs_init(struct stobio_test *test)
Definition: stobio.c:275
static const char perf_location_dio[]
Definition: stobio.c:92
M0_INTERNAL const struct m0_fid * m0_stob_domain_id_get(const struct m0_stob_domain *dom)
Definition: domain.c:300
M0_INTERNAL int m0_stob_domain_destroy(struct m0_stob_domain *dom)
Definition: domain.c:227
static m0_bcount_t stob_size
Definition: storage.c:169
struct m0_vec ov_vec
Definition: vec.h:147
#define max_check(a, b)
Definition: arith.h:95
static struct m0_mutex lock
Definition: stobio.c:97
static void stob_dev_init(const struct stobio_test *test)
Definition: stobio.c:138
static void test_single_ivec()
Definition: stobio.c:509
struct m0_chan si_wait
Definition: io.h:318
uint64_t m0_bcount_t
Definition: types.h:77
#define M0_THREAD_INIT(thread, TYPE, init, func, arg, namefmt,...)
Definition: thread.h:139
static void stobio_io_prepare(struct stobio_test *test, struct m0_stob_io *io)
Definition: stobio.c:192
static void stobio_rw_buffs_fini(struct stobio_test *test)
Definition: stobio.c:296
static const char * test_location
Definition: stobio.c:87
bool st_directio
Definition: stobio.c:66
void ** ov_buf
Definition: vec.h:149
#define PRIx64
Definition: types.h:61
static int stobio_storage_init(void)
Definition: stobio.c:311
struct m0_fid fid
Definition: di.c:46
struct m0_vec iv_vec
Definition: vec.h:139
M0_INTERNAL uint32_t m0_stob_block_shift(struct m0_stob *stob)
Definition: stob.c:270
struct m0_bufvec si_user
Definition: io.h:300
#define WITH_LOCK(lock, action, args...)
Definition: stobio.c:36
static int expected
Definition: locality.c:102
m0_bindex_t * iv_index
Definition: vec.h:141
char * st_wrbuf[RW_BUFF_NR]
Definition: stobio.c:76
int i
Definition: dir.c:1033
M0_INTERNAL int m0_stob_domain_create(const char *location, const char *str_cfg_init, uint64_t dom_key, const char *str_cfg_create, struct m0_stob_domain **out)
Definition: domain.c:217
uint64_t st_stob_key
Definition: stobio.c:58
M0_INTERNAL void m0_fid_set(struct m0_fid *fid, uint64_t container, uint64_t key)
Definition: fid.c:116
#define LAMBDA(T,...)
Definition: thread.h:153
static struct stobio_test tests[TEST_NR]
Definition: stobio.c:101
static void stobio_storage_fini(void)
Definition: stobio.c:331
static int stobio_init(struct stobio_test *test)
Definition: stobio.c:341
static void stobio_rwsegs_prepare(struct stobio_test *test, int starts_from)
Definition: stobio.c:383
M0_INTERNAL int m0_stob_io_prepare_and_launch(struct m0_stob_io *io, struct m0_stob *obj, struct m0_dtx *tx, struct m0_io_scope *scope)
Definition: io.c:219
Definition: stob.h:163
struct m0_indexvec si_stob
Definition: io.h:311
int32_t si_rc
Definition: io.h:334
static const char * test_location_dio
Definition: stobio.c:88
static void stobio_write(struct stobio_test *test)
Definition: stobio.c:220
#define M0_ASSERT(cond)
#define ST_ID(id)
Definition: stobio.c:100
char * st_rdbuf[RW_BUFF_NR]
Definition: stobio.c:74
Definition: tx.c:251
#define m0_streq(a, b)
Definition: string.h:34
void m0_thread_fini(struct m0_thread *q)
Definition: thread.c:92
static void stobio_fini(struct stobio_test *test)
Definition: stobio.c:373
M0_INTERNAL void m0_stob_id_make(uint64_t container, uint64_t key, const struct m0_fid *dom_id, struct m0_stob_id *stob_id)
Definition: stob.c:343
M0_INTERNAL void * m0_stob_addr_pack(const void *buf, uint32_t shift)
Definition: io.c:293
static void test_stobio(void)
Definition: stobio.c:438
M0_INTERNAL void m0_mutex_init(struct m0_mutex *mutex)
Definition: mutex.c:35
static char * stob_backingfile_get(const struct stobio_test *test)
Definition: stobio.c:119
uint64_t f_container
Definition: fid.h:39
static struct m0_stob_domain * test_dom
Definition: stobio.c:93
uint32_t v_nr
Definition: vec.h:51
static struct m0_thread thread[TEST_NR]
Definition: stobio.c:98
Definition: io.h:285
m0_bcount_t * v_count
Definition: vec.h:53
static struct m0_clink clink[RDWR_REQUEST_MAX]
static struct m0_stob_io io
Definition: ad.c:59
m0_bcount_t si_count
Definition: io.h:340
void m0_clink_add_lock(struct m0_chan *chan, struct m0_clink *link)
Definition: chan.c:255
char * st_dev_path
Definition: stobio.c:60
M0_INTERNAL int m0_stob_destroy(struct m0_stob *stob, struct m0_dtx *dtx)
Definition: stob.c:200
char * st_wrbuf_packed[RW_BUFF_NR]
Definition: stobio.c:77
uint32_t st_block_shift
Definition: stobio.c:70
Definition: fid.h:38
uint64_t f_key
Definition: fid.h:40
static void stobio_write_prepare(struct stobio_test *test, struct m0_stob_io *io)
Definition: stobio.c:204
Definition: list.c:42
static const char test_blkdev[]
Definition: stobio.c:85
m0_bcount_t size
Definition: di.c:39
M0_INTERNAL void m0_mutex_fini(struct m0_mutex *mutex)
Definition: mutex.c:42
M0_INTERNAL void m0_clink_fini(struct m0_clink *link)
Definition: chan.c:208
void m0_stob_ut_stobio_linux(void)
Definition: stobio.c:612
size_t st_rw_buf_size_in_blocks
Definition: stobio.c:69
M0_INTERNAL void m0_stob_io_init(struct m0_stob_io *io)
Definition: io.c:111
M0_INTERNAL int m0_stob_find(const struct m0_stob_id *id, struct m0_stob **out)
Definition: stob.c:92
static void test_short_read(void)
Definition: stobio.c:467
static const char linux_location[]
Definition: stobio.c:89
m0_bcount_t st_wrvec[RW_BUFF_NR]
Definition: stobio.c:81
static void stob_dev_fini(const struct stobio_test *test)
Definition: stobio.c:171
static const char perf_location[]
Definition: stobio.c:91
size_t st_rw_buf_size
Definition: stobio.c:68
M0_INTERNAL int m0_ut_stob_create(struct m0_stob *stob, const char *str_cfg, struct m0_be_domain *be_dom)
Definition: stob.c:202
static void stobio_read_prepare(struct stobio_test *test, struct m0_stob_io *io)
Definition: stobio.c:212
static void overlapped_rw_test(struct stobio_test *test, int starts_from)
Definition: stobio.c:406
M0_INTERNAL void * m0_alloc_aligned(size_t size, unsigned shift)
Definition: memory.c:168
Definition: io.h:229
void m0_stob_ut_stobio_perf(void)
Definition: stobio.c:624
Definition: stobio.c:47
struct m0_stob * st_obj
Definition: stobio.c:57
static struct m0_stob_domain * test_dom_dio
Definition: stobio.c:94
void m0_free(void *data)
Definition: memory.c:146
Definition: mutex.h:47
int32_t rc
Definition: trigger_fop.h:47
#define ARRAY_SIZE(a)
Definition: misc.h:45
#define M0_UT_ASSERT(a)
Definition: ut.h:46
struct m0_stob_io st_io
Definition: stobio.c:63
static const char linux_location_dio[]
Definition: stobio.c:90
enum m0_stob_io_opcode si_opcode
Definition: io.h:286
m0_bcount_t st_rdvec[RW_BUFF_NR]
Definition: stobio.c:80