Motr  M0
buffer_pool_ut.c
Go to the documentation of this file.
1 /* -*- C -*- */
2 /*
3  * Copyright (c) 2012-2020 Seagate Technology LLC and/or its Affiliates
4  *
5  * Licensed under the Apache License, Version 2.0 (the "License");
6  * you may not use this file except in compliance with the License.
7  * You may obtain a copy of the License at
8  *
9  * http://www.apache.org/licenses/LICENSE-2.0
10  *
11  * Unless required by applicable law or agreed to in writing, software
12  * distributed under the License is distributed on an "AS IS" BASIS,
13  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
14  * See the License for the specific language governing permissions and
15  * limitations under the License.
16  *
17  * For any questions about this software or licensing,
18  * please email opensource@seagate.com or cortx-questions@seagate.com.
19  *
20  */
21 
22 
23 #include "ut/ut.h"
24 #include "lib/arith.h" /* min64 */
25 #include "lib/memory.h"/* M0_ALLOC_PTR */
26 #include "lib/misc.h" /* M0_SET0 */
27 #include "lib/thread.h"/* M0_THREAD_INIT */
28 #include "lib/time.h" /* m0_nanosleep */
29 #include "net/lnet/lnet.h"
30 #include "net/buffer_pool.h"
31 #include "net/net_internal.h"
32 
33 static void notempty(struct m0_net_buffer_pool *bp);
34 static void low(struct m0_net_buffer_pool *bp);
35 static void buffers_get_put(int rc);
36 
37 static struct m0_net_buffer_pool bp;
38 static struct m0_chan buf_chan;
39 
40 static const struct m0_net_buffer_pool_ops b_ops = {
42  .nbpo_below_threshold = low,
43 };
44 
48 static void test_init(void)
49 {
50  int rc;
51  uint32_t seg_nr = 64;
52  m0_bcount_t seg_size = 4096;
53  uint32_t colours = 10;
54  unsigned shift = 12;
55  uint32_t buf_nr = 10;
56 
60  M0_ASSERT(rc == 0);
62  bp.nbp_ndom),
63  seg_nr);
64  bp.nbp_ops = &b_ops;
67  seg_size, colours, shift, false);
68  M0_UT_ASSERT(rc == 0);
73  M0_UT_ASSERT(rc == buf_nr);
74 }
75 
76 static void test_get_put(void)
77 {
78  struct m0_net_buffer *nb;
79  uint32_t free = bp.nbp_free;
82  M0_UT_ASSERT(nb != NULL);
83  M0_UT_ASSERT(--free == bp.nbp_free);
86  M0_UT_ASSERT(++free == bp.nbp_free);
89 }
90 
91 static void test_get_put_colour(void)
92 {
93  struct m0_net_buffer *nb;
94  uint32_t free = bp.nbp_free;
95  enum {
96  COLOUR = 1,
97  };
100  M0_UT_ASSERT(nb != NULL);
101  M0_UT_ASSERT(--free == bp.nbp_free);
102  m0_net_buffer_pool_put(&bp, nb, COLOUR);
103  M0_UT_ASSERT(++free == bp.nbp_free);
105  nb = m0_net_buffer_pool_get(&bp, COLOUR);
106  M0_UT_ASSERT(nb != NULL);
107  M0_UT_ASSERT(--free == bp.nbp_free);
110  M0_UT_ASSERT(++free == bp.nbp_free);
112 }
113 
114 static void test_grow(void)
115 {
116  uint32_t buf_nr = bp.nbp_buf_nr;
118  /* Buffer pool grow by one */
120  M0_UT_ASSERT(++buf_nr == bp.nbp_buf_nr);
123 }
124 
125 static void test_prune(void)
126 {
127  uint32_t buf_nr = bp.nbp_buf_nr;
130  M0_UT_ASSERT(--buf_nr == bp.nbp_buf_nr);
133 }
134 
135 static void test_get_put_multiple(void)
136 {
137  int i;
138  int rc;
139  const int nr_client_threads = 10;
140  struct m0_thread *client_thread;
141 
144  for (i = 0; i < nr_client_threads; i++) {
146  rc = M0_THREAD_INIT(&client_thread[i], int,
148  M0_BUFFER_ANY_COLOUR, "client_%d", i);
149  M0_ASSERT(rc == 0);
150  M0_SET0(&client_thread[++i]);
151  /* value of integer 'i' is used to put or get the
152  buffer in coloured list */
153  rc = M0_THREAD_INIT(&client_thread[i], int,
155  i, "client_%d", i);
156  M0_ASSERT(rc == 0);
157  }
158  for (i = 0; i < nr_client_threads; i++) {
160  }
165 }
166 
167 static void test_fini(void)
168 {
176 }
177 
178 static void buffers_get_put(int rc)
179 {
180  struct m0_net_buffer *nb;
181  struct m0_clink buf_link;
182 
183  m0_clink_init(&buf_link, NULL);
184  m0_clink_add_lock(&buf_chan, &buf_link);
185  do {
187  nb = m0_net_buffer_pool_get(&bp, rc);
189  if (nb == NULL)
190  m0_chan_wait(&buf_link);
191  } while (nb == NULL);
192  m0_nanosleep(m0_time(0, 100), NULL);
194  if (nb != NULL)
197  m0_clink_del_lock(&buf_link);
198  m0_clink_fini(&buf_link);
199 }
200 
201 static void notempty(struct m0_net_buffer_pool *bp)
202 {
204 }
205 
206 static void low(struct m0_net_buffer_pool *bp)
207 {
208  /* Buffer pool is LOW */
209 }
210 
212  .ts_name = "buffer_pool_ut",
213  .ts_init = NULL,
214  .ts_fini = NULL,
215  .ts_tests = {
216  { "buffer_pool_init", test_init },
217  { "buffer_pool_get_put", test_get_put },
218  { "buffer_pool_get_put_colour", test_get_put_colour },
219  { "buffer_pool_grow", test_grow },
220  { "buffer_pool_prune", test_prune },
221  { "buffer_pool_get_put_multiple", test_get_put_multiple },
222  { "buffer_pool_fini", test_fini },
223  { NULL, NULL }
224  }
225 };
226 M0_EXPORTED(buffer_pool_ut);
227 
228 /*
229  * Local variables:
230  * c-indentation-style: "K&R"
231  * c-basic-offset: 8
232  * tab-width: 8
233  * fill-column: 80
234  * scroll-step: 1
235  * End:
236  */
static m0_bcount_t seg_size
Definition: net.c:118
M0_INTERNAL void m0_net_buffer_pool_fini(struct m0_net_buffer_pool *pool)
Definition: buffer_pool.c:154
static void test_fini(void)
M0_INTERNAL void m0_chan_wait(struct m0_clink *link)
Definition: chan.c:336
#define M0_ALLOC_ARR(arr, nr)
Definition: memory.h:84
void m0_net_domain_fini(struct m0_net_domain *dom)
Definition: domain.c:71
static uint32_t seg_nr
Definition: net.c:119
#define NULL
Definition: misc.h:38
M0_INTERNAL void m0_clink_init(struct m0_clink *link, m0_chan_cb_t cb)
Definition: chan.c:201
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 void low(struct m0_net_buffer_pool *bp)
M0_INTERNAL struct m0_net_buffer * m0_net_buffer_pool_get(struct m0_net_buffer_pool *pool, uint32_t colour)
Definition: buffer_pool.c:215
M0_INTERNAL void m0_net_buffer_pool_unlock(struct m0_net_buffer_pool *pool)
Definition: buffer_pool.c:203
static void test_get_put_multiple(void)
const struct m0_net_buffer_pool_ops * nbp_ops
Definition: buffer_pool.h:263
uint64_t m0_bcount_t
Definition: types.h:77
#define M0_THREAD_INIT(thread, TYPE, init, func, arg, namefmt,...)
Definition: thread.h:139
#define M0_SET0(obj)
Definition: misc.h:64
Definition: ut.h:77
m0_time_t m0_time(uint64_t secs, long ns)
Definition: time.c:41
struct m0_ut_suite buffer_pool_ut
M0_INTERNAL void m0_chan_signal(struct m0_chan *chan)
Definition: chan.c:159
int i
Definition: dir.c:1033
static void buffers_get_put(int rc)
M0_INTERNAL bool m0_net_buffer_pool_invariant(const struct m0_net_buffer_pool *pool)
Definition: buffer_pool.c:50
M0_INTERNAL void m0_chan_init(struct m0_chan *chan, struct m0_mutex *ch_guard)
Definition: chan.c:96
static void test_init(void)
#define M0_ASSERT(cond)
M0_INTERNAL bool m0_net_buffer_pool_prune(struct m0_net_buffer_pool *pool)
Definition: buffer_pool.c:310
static struct m0_chan buf_chan
static void test_get_put_colour(void)
void(* nbpo_not_empty)(struct m0_net_buffer_pool *)
Definition: buffer_pool.h:150
M0_INTERNAL void m0_net_buffer_pool_lock(struct m0_net_buffer_pool *pool)
Definition: buffer_pool.c:186
struct m0_net_xprt * m0_net_xprt_default_get(void)
Definition: net.c:151
Definition: chan.h:229
static void test_prune(void)
static void notempty(struct m0_net_buffer_pool *bp)
struct m0_net_domain * nbp_ndom
Definition: buffer_pool.h:261
void m0_clink_add_lock(struct m0_chan *chan, struct m0_clink *link)
Definition: chan.c:255
const char * ts_name
Definition: ut.h:99
static struct m0_net_buffer_pool bp
static uint32_t min32u(uint32_t a, uint32_t b)
Definition: arith.h:56
int m0_net_domain_init(struct m0_net_domain *dom, const struct m0_net_xprt *xprt)
Definition: domain.c:36
struct m0_mutex nbp_mutex
Definition: buffer_pool.h:259
static void test_grow(void)
#define M0_ALLOC_PTR(ptr)
Definition: memory.h:86
M0_INTERNAL int m0_net_buffer_pool_provision(struct m0_net_buffer_pool *pool, uint32_t buf_nr)
Definition: buffer_pool.c:125
M0_INTERNAL void m0_clink_fini(struct m0_clink *link)
Definition: chan.c:208
static struct m0_thread * client_thread
M0_INTERNAL int32_t m0_net_domain_get_max_buffer_segments(struct m0_net_domain *dom)
static const struct m0_net_buffer_pool_ops b_ops
M0_INTERNAL void m0_net_buffer_pool_put(struct m0_net_buffer_pool *pool, struct m0_net_buffer *buf, uint32_t colour)
Definition: buffer_pool.c:243
M0_INTERNAL void m0_chan_fini_lock(struct m0_chan *chan)
Definition: chan.c:112
void m0_free(void *data)
Definition: memory.c:146
M0_INTERNAL int m0_net_buffer_pool_init(struct m0_net_buffer_pool *pool, struct m0_net_domain *ndom, uint32_t threshold, uint32_t seg_nr, m0_bcount_t seg_size, uint32_t colours, unsigned shift, bool dont_dump)
Definition: buffer_pool.c:82
int32_t rc
Definition: trigger_fop.h:47
#define M0_UT_ASSERT(a)
Definition: ut.h:46
static void test_get_put(void)
static int nr_client_threads
Definition: rpc_ping.c:86
int m0_nanosleep(const m0_time_t req, m0_time_t *rem)
Definition: ktime.c:73