Skip to content

Commit fba4f15

Browse files
committed
rtio: Add a context pool
Adds a context pool that can be used when a number of threads may be dynamically created to use with RTIO. While the pool has a small cost to it, the cost of verifying a statically declared kobject likely makes it worth avoiding dynamically allocating these with the typical kobject_alloc method. Instead this arena style pool of objects can be used where the kobject validation uses the gperf hash created at build time. Signed-off-by: Tom Burdick <thomas.burdick@intel.com>
1 parent 6aa46f4 commit fba4f15

File tree

1 file changed

+125
-0
lines changed

1 file changed

+125
-0
lines changed

include/zephyr/rtio/pool.h

Lines changed: 125 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,125 @@
1+
/*
2+
* Copyright (c) 2025 Intel Corporation
3+
*
4+
* SPDX-License-Identifier: Apache-2.0
5+
*/
6+
7+
/**
8+
* @file
9+
* @brief Real-Time IO pool API for maintaining a pool for RTIO contexts
10+
*/
11+
12+
#ifndef ZEPHYR_INCLUDE_RTIO_POOL_H_
13+
#define ZEPHYR_INCLUDE_RTIO_POOL_H_
14+
15+
#include <zephyr/rtio.h>
16+
17+
#ifdef __cplusplus
18+
extern "C" {
19+
#endif
20+
21+
/**
22+
* @brief RTIO Pool
23+
* @defgroup rtio_pool RTIO Pool API
24+
* @ingroup rtio
25+
* @{
26+
*/
27+
28+
/* clang-format off */
29+
30+
/** @cond ignore */
31+
32+
#define Z_RTIO_POOL_NAME_N(n, name) \
33+
name##_##n
34+
35+
#define Z_RTIO_POOL_DEFINE_N(n, name, sq_sz, cq_sz) \
36+
RTIO_DEFINE(Z_RTIO_POOL_NAME_N(n, name), sq_sz, cq_sz)
37+
38+
#define Z_RTIO_POOL_REF_N(n, name) \
39+
&Z_RTIO_POOL_NAME_N(n, name)
40+
41+
/** @endcond */
42+
43+
/* clang-format on */
44+
45+
/**
46+
* @brief Pool of RTIO contexts to use with dynamically created threads
47+
*/
48+
struct rtio_pool {
49+
/** Size of the pool */
50+
size_t pool_size;
51+
52+
/** Array containing contexts of the pool */
53+
struct rtio **contexts;
54+
55+
/** Atomic bitmap to signal a member is used/unused */
56+
atomic_t *used;
57+
};
58+
59+
/* clang-format off */
60+
61+
/**
62+
* @brief Statically define and initialize a pool of RTIO contexts
63+
*
64+
* @param name Name of the RTIO pool
65+
* @param pool_sz Number of RTIO contexts to allocate in the pool
66+
* @param sq_sz Size of the submission queue entry pool per context
67+
* @param cq_sz Size of the completion queue entry pool per context
68+
*/
69+
#define RTIO_POOL_DEFINE(name, pool_sz, sq_sz, cq_sz) \
70+
LISTIFY(pool_sz, RTIO_DEFINE_N, (;), name, sq_sz, cq_sz) \
71+
struct rtio *name_##contexts[] = { \
72+
LISTIFY(pool_sz, Z_RTIO_POOL_REF_N, (,), name) \
73+
}; \
74+
ATOMIC_DEFINE(name_##used, pool_sz); \
75+
STRUCT_SECTION_ITERABLE(rtio_pool, name) = { \
76+
.pool_size = pool_sz, \
77+
.contexts = name_##contexts, \
78+
.used = name_##used, \
79+
}
80+
81+
/* clang-format on */
82+
83+
/**
84+
* @brief Obtain an RTIO context from a pool
85+
*/
86+
__syscall struct rtio *rtio_pool_acquire(struct rtio_pool *pool);
87+
88+
static inline struct rtio *z_impl_rtio_pool_acquire(struct rtio_pool *pool)
89+
{
90+
struct rtio *r = NULL;
91+
92+
for (size_t i = 0; i < pool->pool_size; i++) {
93+
if (atomic_test_and_set_bit(pool->used, i) == 0) {
94+
r = pool->contexts[i];
95+
break;
96+
}
97+
}
98+
99+
return r;
100+
}
101+
102+
/**
103+
* @brief Return an RTIO context to a pool
104+
*/
105+
__syscall void rtio_pool_release(struct rtio_pool *pool, struct rtio *r);
106+
107+
static inline void z_impl_rtio_pool_release(struct rtio_pool *pool, struct rtio *r)
108+
{
109+
for (size_t i = 0; i < pool->pool_size; i++) {
110+
if (pool->contexts[i] == r) {
111+
atomic_clear_bit(pool->used, i);
112+
break;
113+
}
114+
}
115+
}
116+
117+
/**
118+
* @}
119+
*/
120+
121+
#ifdef __cplusplus
122+
}
123+
#endif
124+
125+
#endif /* ZEPHYR_INCLUDE_RTIO_POOL_H_ */

0 commit comments

Comments
 (0)