ublk-cpp v0.0
Loading...
Searching...
No Matches
control.hpp
Go to the documentation of this file.
1
5
6#pragma once
7
10#include "ublk/raw.hpp"
11#include <condy.hpp>
12
13namespace ublk {
14namespace detail {
15
16namespace ex = condy::detail::ex;
17
18struct control_get_dev_info_t {
19 template <typename Sched, typename Alloc>
20 ex::task<void, TaskEnv<Sched, Alloc>> invoke(int fd, uint32_t dev_id,
21 ublksrv_ctrl_dev_info *info) {
22 DevPathBuf<ublksrv_ctrl_dev_info> buf(dev_id);
23 auto s =
24 raw::get_dev_info2(fd, dev_id, &buf, sizeof(buf), DEV_PATH_LEN) |
25 ex::then([&](int32_t r) noexcept {
26 *info = buf.payload;
27 return r;
28 }) |
29 ex::let_error([&](std::error_code ec) {
30 if (ec.value() != EOPNOTSUPP) {
31 throw std::system_error(ec, "get_dev_info2");
32 }
33 return raw::get_dev_info(fd, dev_id, info);
34 });
35 co_await std::move(s);
36 }
37};
38
39template <typename Sched, typename Alloc>
40inline ex::task<void, TaskEnv<Sched, Alloc>>
41cached_get_dev_info(int fd, uint32_t dev_id, ublksrv_ctrl_dev_info *info) {
42 const auto *dev_info = co_await ex::read_env(fetch_dev_info);
43 if (dev_info && dev_info->dev_id == dev_id) {
44 *info = *dev_info;
45 co_return;
46 }
47 co_await control_get_dev_info_t{}.invoke<Sched, Alloc>(fd, dev_id, info);
48}
49
50struct control_get_queue_affinity_t {
51 template <typename Sched, typename Alloc>
52 ex::task<void, TaskEnv<Sched, Alloc>>
53 invoke(int control_fd, uint32_t dev_id, uint16_t q_id, cpu_set_t *cpuset) {
54 ublksrv_ctrl_dev_info info;
55 co_await cached_get_dev_info<Sched, Alloc>(control_fd, dev_id, &info);
56 if (info.flags & UBLK_F_UNPRIVILEGED_DEV) {
57 DevPathBuf<cpu_set_t> buf(dev_id);
58 co_await raw::get_queue_affinity(control_fd, dev_id, q_id, &buf,
59 sizeof(buf), DEV_PATH_LEN);
60 *cpuset = buf.payload;
61 } else {
62 co_await raw::get_queue_affinity(control_fd, dev_id, q_id, cpuset);
63 }
64 }
65};
66
67template <typename Sched, typename Alloc, typename Fn>
68inline ex::task<void, TaskEnv<Sched, Alloc>>
69with_dev_path(int control_fd, uint32_t dev_id, Fn fn) {
70 ublksrv_ctrl_dev_info info;
71 char path[DEV_PATH_LEN];
72 fill_dev_path(path, sizeof(path), dev_id);
73 auto s = cached_get_dev_info<Sched, Alloc>(control_fd, dev_id, &info) |
74 ex::let_value([&, fn = std::move(fn)]() noexcept(
75 noexcept(std::move(fn)(path, DEV_PATH_LEN))) {
76 if (info.flags & UBLK_F_UNPRIVILEGED_DEV) {
77 return std::move(fn)(path, DEV_PATH_LEN);
78 } else {
79 return std::move(fn)(nullptr, 0);
80 }
81 });
82 co_await std::move(s);
83}
84
85struct control_del_dev_t {
86 template <typename Sched, typename Alloc>
87 auto invoke(int control_fd, uint32_t dev_id) {
88 return with_dev_path<Sched, Alloc>(
89 control_fd, dev_id, [=](char *path, uint16_t len) noexcept {
90 return raw::del_dev(control_fd, dev_id, path, len);
91 });
92 }
93};
94
95struct control_start_dev_t {
96 template <typename Sched, typename Alloc>
97 auto invoke(int control_fd, uint32_t dev_id, int32_t daemon_pid) {
98 return with_dev_path<Sched, Alloc>(
99 control_fd, dev_id, [=](char *path, uint16_t len) noexcept {
100 return raw::start_dev(control_fd, dev_id, daemon_pid, path,
101 len);
102 });
103 }
104};
105
106struct control_stop_dev_t {
107 template <typename Sched, typename Alloc>
108 auto invoke(int control_fd, uint32_t dev_id) {
109 return with_dev_path<Sched, Alloc>(
110 control_fd, dev_id, [=](char *path, uint16_t len) noexcept {
111 return raw::stop_dev(control_fd, dev_id, path, len);
112 });
113 }
114};
115
116struct control_set_params_t {
117 template <typename Sched, typename Alloc>
118 ex::task<void, TaskEnv<Sched, Alloc>>
119 invoke(int control_fd, uint32_t dev_id, const ublk_params *params) {
120 ublksrv_ctrl_dev_info info;
121 co_await cached_get_dev_info<Sched, Alloc>(control_fd, dev_id, &info);
122 ublk_params full = *params;
123 full.len = sizeof(full);
124 if (info.flags & UBLK_F_UNPRIVILEGED_DEV) {
125 DevPathBuf<ublk_params> buf(dev_id);
126 buf.payload = full;
127 co_await raw::set_params(control_fd, dev_id, &buf, sizeof(buf),
128 DEV_PATH_LEN);
129 } else {
130 co_await raw::set_params(control_fd, dev_id, &full);
131 }
132 }
133};
134
135struct control_get_params_t {
136 template <typename Sched, typename Alloc>
137 ex::task<void, TaskEnv<Sched, Alloc>>
138 invoke(int control_fd, uint32_t dev_id, ublk_params *params) {
139 ublksrv_ctrl_dev_info info;
140 co_await cached_get_dev_info<Sched, Alloc>(control_fd, dev_id, &info);
141 params->len = sizeof(*params);
142 if (info.flags & UBLK_F_UNPRIVILEGED_DEV) {
143 DevPathBuf<ublk_params> buf(dev_id);
144 buf.payload.len = sizeof(buf.payload);
145 co_await raw::get_params(control_fd, dev_id, &buf, sizeof(buf),
146 DEV_PATH_LEN);
147 *params = buf.payload;
148 } else {
149 co_await raw::get_params(control_fd, dev_id, params);
150 }
151 }
152};
153
154struct control_start_user_recovery_t {
155 template <typename Sched, typename Alloc>
156 auto invoke(int control_fd, uint32_t dev_id) {
157 return with_dev_path<Sched, Alloc>(
158 control_fd, dev_id, [=](char *path, uint16_t len) noexcept {
159 return raw::start_user_recovery(control_fd, dev_id, path, len);
160 });
161 }
162};
163
164struct control_end_user_recovery_t {
165 template <typename Sched, typename Alloc>
166 auto invoke(int control_fd, uint32_t dev_id, int32_t daemon_pid) {
167 return with_dev_path<Sched, Alloc>(
168 control_fd, dev_id, [=](char *path, uint16_t len) noexcept {
169 return raw::end_user_recovery(control_fd, dev_id, daemon_pid,
170 path, len);
171 });
172 }
173};
174
175struct control_del_dev_async_t {
176 template <typename Sched, typename Alloc>
177 auto invoke(int control_fd, uint32_t dev_id) {
178 return with_dev_path<Sched, Alloc>(
179 control_fd, dev_id, [=](char *path, uint16_t len) noexcept {
180 return raw::del_dev_async(control_fd, dev_id, path, len);
181 });
182 }
183};
184
185struct control_update_size_t {
186 template <typename Sched, typename Alloc>
187 auto invoke(int control_fd, uint32_t dev_id, uint64_t sectors) {
188 return with_dev_path<Sched, Alloc>(
189 control_fd, dev_id, [=](char *path, uint16_t len) noexcept {
190 return raw::update_size(control_fd, dev_id, sectors, path, len);
191 });
192 }
193};
194
195struct control_quiesce_dev_t {
196 template <typename Sched, typename Alloc>
197 auto invoke(int control_fd, uint32_t dev_id, uint64_t timeout_ms) {
198 return with_dev_path<Sched, Alloc>(
199 control_fd, dev_id, [=](char *path, uint16_t len) noexcept {
200 return raw::quiesce_dev(control_fd, dev_id, timeout_ms, path,
201 len);
202 });
203 }
204};
205
206struct control_try_stop_dev_t {
207 template <typename Sched, typename Alloc>
208 auto invoke(int control_fd, uint32_t dev_id) {
209 return with_dev_path<Sched, Alloc>(
210 control_fd, dev_id, [=](char *path, uint16_t len) noexcept {
211 return raw::try_stop_dev(control_fd, dev_id, path, len);
212 });
213 }
214};
215
216struct control_register_shm_buf_t {
217 template <typename Sched, typename Alloc>
218 ex::task<int32_t, TaskEnv<Sched, Alloc>>
219 invoke(int control_fd, uint32_t dev_id, const ublk_shmem_buf_reg *reg) {
220 ublksrv_ctrl_dev_info info;
221 co_await cached_get_dev_info<Sched, Alloc>(control_fd, dev_id, &info);
222 if (info.flags & UBLK_F_UNPRIVILEGED_DEV) {
223 DevPathBuf<ublk_shmem_buf_reg> buf(dev_id);
224 buf.payload = *reg;
225 co_return co_await raw::register_shm_buf(control_fd, dev_id, &buf,
226 sizeof(buf), DEV_PATH_LEN);
227 } else {
228 co_return co_await raw::register_shm_buf(control_fd, dev_id, reg);
229 }
230 }
231};
232
233struct control_unregister_shm_buf_t {
234 template <typename Sched, typename Alloc>
235 auto invoke(int control_fd, uint32_t dev_id, uint64_t buf_index) {
236 return with_dev_path<Sched, Alloc>(
237 control_fd, dev_id, [=](char *path, uint16_t len) noexcept {
238 return raw::unregister_shm_buf(control_fd, dev_id, buf_index,
239 path, len);
240 });
241 }
242};
243
244} // namespace detail
245} // namespace ublk
auto start_user_recovery(Fd fd, uint32_t dev_id, const char *dev_path, uint16_t dev_path_len) noexcept
Unprivileged version of start_user_recovery().
Definition raw.hpp:203
auto update_size(Fd fd, uint32_t dev_id, uint64_t sectors, const char *dev_path, uint16_t dev_path_len) noexcept
Unprivileged version of update_size().
Definition raw.hpp:299
auto end_user_recovery(Fd fd, uint32_t dev_id, int32_t daemon_pid, const char *dev_path, uint16_t dev_path_len) noexcept
Unprivileged version of end_user_recovery().
Definition raw.hpp:225
auto set_params(Fd fd, uint32_t dev_id, const void *data, uint16_t size, uint16_t dev_path_len) noexcept
Unprivileged version of set_params().
Definition raw.hpp:156
auto quiesce_dev(Fd fd, uint32_t dev_id, uint64_t timeout_ms, const char *dev_path, uint16_t dev_path_len) noexcept
Unprivileged version of quiesce_dev().
Definition raw.hpp:322
auto start_dev(Fd fd, uint32_t dev_id, int32_t daemon_pid, const char *dev_path, uint16_t dev_path_len) noexcept
Unprivileged version of start_dev().
Definition raw.hpp:111
auto register_shm_buf(Fd fd, uint32_t dev_id, const void *data, uint16_t size, uint16_t dev_path_len) noexcept
Unprivileged version of register_shm_buf().
Definition raw.hpp:368
auto try_stop_dev(Fd fd, uint32_t dev_id, const char *dev_path, uint16_t dev_path_len) noexcept
Unprivileged version of try_stop_dev().
Definition raw.hpp:346
auto del_dev_async(Fd fd, uint32_t dev_id, const char *dev_path, uint16_t dev_path_len) noexcept
Unprivileged version of del_dev_async().
Definition raw.hpp:277
auto unregister_shm_buf(Fd fd, uint32_t dev_id, uint64_t buf_index, const char *dev_path, uint16_t dev_path_len) noexcept
Unprivileged version of unregister_shm_buf().
Definition raw.hpp:395
auto get_dev_info(Fd fd, uint32_t dev_id, void *data, uint16_t size, uint16_t dev_path_len) noexcept
Unprivileged version of get_dev_info().
Definition raw.hpp:52
auto stop_dev(Fd fd, uint32_t dev_id, const char *dev_path, uint16_t dev_path_len) noexcept
Unprivileged version of stop_dev().
Definition raw.hpp:135
auto get_dev_info2(Fd fd, uint32_t dev_id, void *data, uint16_t size, uint16_t dev_path_len) noexcept
Get the device information of a ublk device, works both for privileged and unprivileged modes.
Definition raw.hpp:253
auto del_dev(Fd fd, uint32_t dev_id, const char *dev_path, uint16_t dev_path_len) noexcept
Unprivileged version of del_dev().
Definition raw.hpp:90
auto get_params(Fd fd, uint32_t dev_id, void *data, uint16_t size, uint16_t dev_path_len) noexcept
Unprivileged version of get_params().
Definition raw.hpp:180
auto get_queue_affinity(Fd fd, uint32_t dev_id, uint16_t q_id, void *data, uint16_t size, uint16_t dev_path_len) noexcept
Unprivileged version of get_queue_affinity().
Definition raw.hpp:26
The main namespace of the ublk-cpp library.
Definition ublk.hpp:21
constexpr fetch_dev_info_t fetch_dev_info
Query object instance of fetch_dev_info_t.
Definition query.hpp:48
Path related helpers.
Low-level io_uring command senders for ublk control and I/O commands.
Task environment utils.