xref: /linux/drivers/block/drbd/drbd_nl_gen.c (revision a50eba1e778ad4da5b6f9ddbbf57dabbea59bc05)
1 // SPDX-License-Identifier: ((GPL-2.0 WITH Linux-syscall-note) OR BSD-3-Clause)
2 
3 #include <net/netlink.h>
4 #include <net/genetlink.h>
5 
6 #include <linux/kernel.h>
7 #include <linux/slab.h>
8 #include "drbd_nl_gen.h"
9 
10 #include <uapi/linux/drbd_genl.h>
11 #include <linux/drbd.h>
12 #include <linux/drbd_limits.h>
13 
14 /* Common nested types */
15 const struct nla_policy drbd_connection_info_nl_policy[DRBD_A_CONNECTION_INFO_CONN_ROLE + 1] = {
16 	[DRBD_A_CONNECTION_INFO_CONN_CONNECTION_STATE] = { .type = NLA_U32, },
17 	[DRBD_A_CONNECTION_INFO_CONN_ROLE] = { .type = NLA_U32, },
18 };
19 
20 const struct nla_policy drbd_connection_statistics_nl_policy[DRBD_A_CONNECTION_STATISTICS_CONN_CONGESTED + 1] = {
21 	[DRBD_A_CONNECTION_STATISTICS_CONN_CONGESTED] = { .type = NLA_U8, },
22 };
23 
24 const struct nla_policy drbd_detach_parms_nl_policy[DRBD_A_DETACH_PARMS_FORCE_DETACH + 1] = {
25 	[DRBD_A_DETACH_PARMS_FORCE_DETACH] = { .type = NLA_U8, },
26 };
27 
28 const struct nla_policy drbd_device_info_nl_policy[DRBD_A_DEVICE_INFO_DEV_DISK_STATE + 1] = {
29 	[DRBD_A_DEVICE_INFO_DEV_DISK_STATE] = { .type = NLA_U32, },
30 };
31 
32 const struct nla_policy drbd_device_statistics_nl_policy[DRBD_A_DEVICE_STATISTICS_HISTORY_UUIDS + 1] = {
33 	[DRBD_A_DEVICE_STATISTICS_DEV_SIZE] = { .type = NLA_U64, },
34 	[DRBD_A_DEVICE_STATISTICS_DEV_READ] = { .type = NLA_U64, },
35 	[DRBD_A_DEVICE_STATISTICS_DEV_WRITE] = { .type = NLA_U64, },
36 	[DRBD_A_DEVICE_STATISTICS_DEV_AL_WRITES] = { .type = NLA_U64, },
37 	[DRBD_A_DEVICE_STATISTICS_DEV_BM_WRITES] = { .type = NLA_U64, },
38 	[DRBD_A_DEVICE_STATISTICS_DEV_UPPER_PENDING] = { .type = NLA_U32, },
39 	[DRBD_A_DEVICE_STATISTICS_DEV_LOWER_PENDING] = { .type = NLA_U32, },
40 	[DRBD_A_DEVICE_STATISTICS_DEV_UPPER_BLOCKED] = { .type = NLA_U8, },
41 	[DRBD_A_DEVICE_STATISTICS_DEV_LOWER_BLOCKED] = { .type = NLA_U8, },
42 	[DRBD_A_DEVICE_STATISTICS_DEV_AL_SUSPENDED] = { .type = NLA_U8, },
43 	[DRBD_A_DEVICE_STATISTICS_DEV_EXPOSED_DATA_UUID] = { .type = NLA_U64, },
44 	[DRBD_A_DEVICE_STATISTICS_DEV_CURRENT_UUID] = { .type = NLA_U64, },
45 	[DRBD_A_DEVICE_STATISTICS_DEV_DISK_FLAGS] = { .type = NLA_U32, },
46 	[DRBD_A_DEVICE_STATISTICS_HISTORY_UUIDS] = NLA_POLICY_MAX_LEN(DRBD_NL_HISTORY_UUIDS_SIZE),
47 };
48 
49 const struct nla_policy drbd_disconnect_parms_nl_policy[DRBD_A_DISCONNECT_PARMS_FORCE_DISCONNECT + 1] = {
50 	[DRBD_A_DISCONNECT_PARMS_FORCE_DISCONNECT] = { .type = NLA_U8, },
51 };
52 
53 const struct nla_policy drbd_disk_conf_nl_policy[DRBD_A_DISK_CONF_DISABLE_WRITE_SAME + 1] = {
54 	[DRBD_A_DISK_CONF_BACKING_DEV] = { .type = NLA_NUL_STRING, .len = 128, },
55 	[DRBD_A_DISK_CONF_META_DEV] = { .type = NLA_NUL_STRING, .len = 128, },
56 	[DRBD_A_DISK_CONF_META_DEV_IDX] = { .type = NLA_U32, },
57 	[DRBD_A_DISK_CONF_DISK_SIZE] = { .type = NLA_U64, },
58 	[DRBD_A_DISK_CONF_MAX_BIO_BVECS] = { .type = NLA_U32, },
59 	[DRBD_A_DISK_CONF_ON_IO_ERROR] = { .type = NLA_U32, },
60 	[DRBD_A_DISK_CONF_FENCING] = { .type = NLA_U32, },
61 	[DRBD_A_DISK_CONF_RESYNC_RATE] = { .type = NLA_U32, },
62 	[DRBD_A_DISK_CONF_RESYNC_AFTER] = { .type = NLA_U32, },
63 	[DRBD_A_DISK_CONF_AL_EXTENTS] = { .type = NLA_U32, },
64 	[DRBD_A_DISK_CONF_C_PLAN_AHEAD] = { .type = NLA_U32, },
65 	[DRBD_A_DISK_CONF_C_DELAY_TARGET] = { .type = NLA_U32, },
66 	[DRBD_A_DISK_CONF_C_FILL_TARGET] = { .type = NLA_U32, },
67 	[DRBD_A_DISK_CONF_C_MAX_RATE] = { .type = NLA_U32, },
68 	[DRBD_A_DISK_CONF_C_MIN_RATE] = { .type = NLA_U32, },
69 	[DRBD_A_DISK_CONF_DISK_BARRIER] = { .type = NLA_U8, },
70 	[DRBD_A_DISK_CONF_DISK_FLUSHES] = { .type = NLA_U8, },
71 	[DRBD_A_DISK_CONF_DISK_DRAIN] = { .type = NLA_U8, },
72 	[DRBD_A_DISK_CONF_MD_FLUSHES] = { .type = NLA_U8, },
73 	[DRBD_A_DISK_CONF_DISK_TIMEOUT] = { .type = NLA_U32, },
74 	[DRBD_A_DISK_CONF_READ_BALANCING] = { .type = NLA_U32, },
75 	[DRBD_A_DISK_CONF_AL_UPDATES] = { .type = NLA_U8, },
76 	[DRBD_A_DISK_CONF_DISCARD_ZEROES_IF_ALIGNED] = { .type = NLA_U8, },
77 	[DRBD_A_DISK_CONF_RS_DISCARD_GRANULARITY] = { .type = NLA_U32, },
78 	[DRBD_A_DISK_CONF_DISABLE_WRITE_SAME] = { .type = NLA_U8, },
79 };
80 
81 const struct nla_policy drbd_drbd_cfg_context_nl_policy[DRBD_A_DRBD_CFG_CONTEXT_CTX_PEER_ADDR + 1] = {
82 	[DRBD_A_DRBD_CFG_CONTEXT_CTX_VOLUME] = { .type = NLA_U32, },
83 	[DRBD_A_DRBD_CFG_CONTEXT_CTX_RESOURCE_NAME] = { .type = NLA_NUL_STRING, .len = 128, },
84 	[DRBD_A_DRBD_CFG_CONTEXT_CTX_MY_ADDR] = NLA_POLICY_MAX_LEN(128),
85 	[DRBD_A_DRBD_CFG_CONTEXT_CTX_PEER_ADDR] = NLA_POLICY_MAX_LEN(128),
86 };
87 
88 const struct nla_policy drbd_net_conf_nl_policy[DRBD_A_NET_CONF_SOCK_CHECK_TIMEO + 1] = {
89 	[DRBD_A_NET_CONF_SHARED_SECRET] = { .type = NLA_NUL_STRING, .len = SHARED_SECRET_MAX, },
90 	[DRBD_A_NET_CONF_CRAM_HMAC_ALG] = { .type = NLA_NUL_STRING, .len = SHARED_SECRET_MAX, },
91 	[DRBD_A_NET_CONF_INTEGRITY_ALG] = { .type = NLA_NUL_STRING, .len = SHARED_SECRET_MAX, },
92 	[DRBD_A_NET_CONF_VERIFY_ALG] = { .type = NLA_NUL_STRING, .len = SHARED_SECRET_MAX, },
93 	[DRBD_A_NET_CONF_CSUMS_ALG] = { .type = NLA_NUL_STRING, .len = SHARED_SECRET_MAX, },
94 	[DRBD_A_NET_CONF_WIRE_PROTOCOL] = { .type = NLA_U32, },
95 	[DRBD_A_NET_CONF_CONNECT_INT] = { .type = NLA_U32, },
96 	[DRBD_A_NET_CONF_TIMEOUT] = { .type = NLA_U32, },
97 	[DRBD_A_NET_CONF_PING_INT] = { .type = NLA_U32, },
98 	[DRBD_A_NET_CONF_PING_TIMEO] = { .type = NLA_U32, },
99 	[DRBD_A_NET_CONF_SNDBUF_SIZE] = { .type = NLA_U32, },
100 	[DRBD_A_NET_CONF_RCVBUF_SIZE] = { .type = NLA_U32, },
101 	[DRBD_A_NET_CONF_KO_COUNT] = { .type = NLA_U32, },
102 	[DRBD_A_NET_CONF_MAX_BUFFERS] = { .type = NLA_U32, },
103 	[DRBD_A_NET_CONF_MAX_EPOCH_SIZE] = { .type = NLA_U32, },
104 	[DRBD_A_NET_CONF_UNPLUG_WATERMARK] = { .type = NLA_U32, },
105 	[DRBD_A_NET_CONF_AFTER_SB_0P] = { .type = NLA_U32, },
106 	[DRBD_A_NET_CONF_AFTER_SB_1P] = { .type = NLA_U32, },
107 	[DRBD_A_NET_CONF_AFTER_SB_2P] = { .type = NLA_U32, },
108 	[DRBD_A_NET_CONF_RR_CONFLICT] = { .type = NLA_U32, },
109 	[DRBD_A_NET_CONF_ON_CONGESTION] = { .type = NLA_U32, },
110 	[DRBD_A_NET_CONF_CONG_FILL] = { .type = NLA_U32, },
111 	[DRBD_A_NET_CONF_CONG_EXTENTS] = { .type = NLA_U32, },
112 	[DRBD_A_NET_CONF_TWO_PRIMARIES] = { .type = NLA_U8, },
113 	[DRBD_A_NET_CONF_DISCARD_MY_DATA] = { .type = NLA_U8, },
114 	[DRBD_A_NET_CONF_TCP_CORK] = { .type = NLA_U8, },
115 	[DRBD_A_NET_CONF_ALWAYS_ASBP] = { .type = NLA_U8, },
116 	[DRBD_A_NET_CONF_TENTATIVE] = { .type = NLA_U8, },
117 	[DRBD_A_NET_CONF_USE_RLE] = { .type = NLA_U8, },
118 	[DRBD_A_NET_CONF_CSUMS_AFTER_CRASH_ONLY] = { .type = NLA_U8, },
119 	[DRBD_A_NET_CONF_SOCK_CHECK_TIMEO] = { .type = NLA_U32, },
120 };
121 
122 const struct nla_policy drbd_new_c_uuid_parms_nl_policy[DRBD_A_NEW_C_UUID_PARMS_CLEAR_BM + 1] = {
123 	[DRBD_A_NEW_C_UUID_PARMS_CLEAR_BM] = { .type = NLA_U8, },
124 };
125 
126 const struct nla_policy drbd_peer_device_info_nl_policy[DRBD_A_PEER_DEVICE_INFO_PEER_RESYNC_SUSP_DEPENDENCY + 1] = {
127 	[DRBD_A_PEER_DEVICE_INFO_PEER_REPL_STATE] = { .type = NLA_U32, },
128 	[DRBD_A_PEER_DEVICE_INFO_PEER_DISK_STATE] = { .type = NLA_U32, },
129 	[DRBD_A_PEER_DEVICE_INFO_PEER_RESYNC_SUSP_USER] = { .type = NLA_U32, },
130 	[DRBD_A_PEER_DEVICE_INFO_PEER_RESYNC_SUSP_PEER] = { .type = NLA_U32, },
131 	[DRBD_A_PEER_DEVICE_INFO_PEER_RESYNC_SUSP_DEPENDENCY] = { .type = NLA_U32, },
132 };
133 
134 const struct nla_policy drbd_peer_device_statistics_nl_policy[DRBD_A_PEER_DEVICE_STATISTICS_PEER_DEV_FLAGS + 1] = {
135 	[DRBD_A_PEER_DEVICE_STATISTICS_PEER_DEV_RECEIVED] = { .type = NLA_U64, },
136 	[DRBD_A_PEER_DEVICE_STATISTICS_PEER_DEV_SENT] = { .type = NLA_U64, },
137 	[DRBD_A_PEER_DEVICE_STATISTICS_PEER_DEV_PENDING] = { .type = NLA_U32, },
138 	[DRBD_A_PEER_DEVICE_STATISTICS_PEER_DEV_UNACKED] = { .type = NLA_U32, },
139 	[DRBD_A_PEER_DEVICE_STATISTICS_PEER_DEV_OUT_OF_SYNC] = { .type = NLA_U64, },
140 	[DRBD_A_PEER_DEVICE_STATISTICS_PEER_DEV_RESYNC_FAILED] = { .type = NLA_U64, },
141 	[DRBD_A_PEER_DEVICE_STATISTICS_PEER_DEV_BITMAP_UUID] = { .type = NLA_U64, },
142 	[DRBD_A_PEER_DEVICE_STATISTICS_PEER_DEV_FLAGS] = { .type = NLA_U32, },
143 };
144 
145 const struct nla_policy drbd_res_opts_nl_policy[DRBD_A_RES_OPTS_ON_NO_DATA + 1] = {
146 	[DRBD_A_RES_OPTS_CPU_MASK] = { .type = NLA_NUL_STRING, .len = DRBD_CPU_MASK_SIZE, },
147 	[DRBD_A_RES_OPTS_ON_NO_DATA] = { .type = NLA_U32, },
148 };
149 
150 const struct nla_policy drbd_resize_parms_nl_policy[DRBD_A_RESIZE_PARMS_AL_STRIPE_SIZE + 1] = {
151 	[DRBD_A_RESIZE_PARMS_RESIZE_SIZE] = { .type = NLA_U64, },
152 	[DRBD_A_RESIZE_PARMS_RESIZE_FORCE] = { .type = NLA_U8, },
153 	[DRBD_A_RESIZE_PARMS_NO_RESYNC] = { .type = NLA_U8, },
154 	[DRBD_A_RESIZE_PARMS_AL_STRIPES] = { .type = NLA_U32, },
155 	[DRBD_A_RESIZE_PARMS_AL_STRIPE_SIZE] = { .type = NLA_U32, },
156 };
157 
158 const struct nla_policy drbd_resource_info_nl_policy[DRBD_A_RESOURCE_INFO_RES_SUSP_FEN + 1] = {
159 	[DRBD_A_RESOURCE_INFO_RES_ROLE] = { .type = NLA_U32, },
160 	[DRBD_A_RESOURCE_INFO_RES_SUSP] = { .type = NLA_U8, },
161 	[DRBD_A_RESOURCE_INFO_RES_SUSP_NOD] = { .type = NLA_U8, },
162 	[DRBD_A_RESOURCE_INFO_RES_SUSP_FEN] = { .type = NLA_U8, },
163 };
164 
165 const struct nla_policy drbd_resource_statistics_nl_policy[DRBD_A_RESOURCE_STATISTICS_RES_STAT_WRITE_ORDERING + 1] = {
166 	[DRBD_A_RESOURCE_STATISTICS_RES_STAT_WRITE_ORDERING] = { .type = NLA_U32, },
167 };
168 
169 const struct nla_policy drbd_set_role_parms_nl_policy[DRBD_A_SET_ROLE_PARMS_ASSUME_UPTODATE + 1] = {
170 	[DRBD_A_SET_ROLE_PARMS_ASSUME_UPTODATE] = { .type = NLA_U8, },
171 };
172 
173 const struct nla_policy drbd_start_ov_parms_nl_policy[DRBD_A_START_OV_PARMS_OV_STOP_SECTOR + 1] = {
174 	[DRBD_A_START_OV_PARMS_OV_START_SECTOR] = { .type = NLA_U64, },
175 	[DRBD_A_START_OV_PARMS_OV_STOP_SECTOR] = { .type = NLA_U64, },
176 };
177 
178 /* DRBD_ADM_GET_STATUS - do */
179 static const struct nla_policy drbd_get_status_do_nl_policy[DRBD_NLA_CFG_CONTEXT + 1] = {
180 	[DRBD_NLA_CFG_CONTEXT] = NLA_POLICY_NESTED(drbd_drbd_cfg_context_nl_policy),
181 };
182 
183 /* DRBD_ADM_GET_STATUS - dump */
184 static const struct nla_policy drbd_get_status_dump_nl_policy[DRBD_NLA_CFG_CONTEXT + 1] = {
185 	[DRBD_NLA_CFG_CONTEXT] = NLA_POLICY_NESTED(drbd_drbd_cfg_context_nl_policy),
186 };
187 
188 /* DRBD_ADM_NEW_MINOR - do */
189 static const struct nla_policy drbd_new_minor_nl_policy[DRBD_NLA_CFG_CONTEXT + 1] = {
190 	[DRBD_NLA_CFG_CONTEXT] = NLA_POLICY_NESTED(drbd_drbd_cfg_context_nl_policy),
191 };
192 
193 /* DRBD_ADM_DEL_MINOR - do */
194 static const struct nla_policy drbd_del_minor_nl_policy[DRBD_NLA_CFG_CONTEXT + 1] = {
195 	[DRBD_NLA_CFG_CONTEXT] = NLA_POLICY_NESTED(drbd_drbd_cfg_context_nl_policy),
196 };
197 
198 /* DRBD_ADM_NEW_RESOURCE - do */
199 static const struct nla_policy drbd_new_resource_nl_policy[DRBD_NLA_RESOURCE_OPTS + 1] = {
200 	[DRBD_NLA_CFG_CONTEXT] = NLA_POLICY_NESTED(drbd_drbd_cfg_context_nl_policy),
201 	[DRBD_NLA_RESOURCE_OPTS] = NLA_POLICY_NESTED(drbd_res_opts_nl_policy),
202 };
203 
204 /* DRBD_ADM_DEL_RESOURCE - do */
205 static const struct nla_policy drbd_del_resource_nl_policy[DRBD_NLA_CFG_CONTEXT + 1] = {
206 	[DRBD_NLA_CFG_CONTEXT] = NLA_POLICY_NESTED(drbd_drbd_cfg_context_nl_policy),
207 };
208 
209 /* DRBD_ADM_RESOURCE_OPTS - do */
210 static const struct nla_policy drbd_resource_opts_nl_policy[DRBD_NLA_RESOURCE_OPTS + 1] = {
211 	[DRBD_NLA_CFG_CONTEXT] = NLA_POLICY_NESTED(drbd_drbd_cfg_context_nl_policy),
212 	[DRBD_NLA_RESOURCE_OPTS] = NLA_POLICY_NESTED(drbd_res_opts_nl_policy),
213 };
214 
215 /* DRBD_ADM_CONNECT - do */
216 static const struct nla_policy drbd_connect_nl_policy[DRBD_NLA_NET_CONF + 1] = {
217 	[DRBD_NLA_CFG_CONTEXT] = NLA_POLICY_NESTED(drbd_drbd_cfg_context_nl_policy),
218 	[DRBD_NLA_NET_CONF] = NLA_POLICY_NESTED(drbd_net_conf_nl_policy),
219 };
220 
221 /* DRBD_ADM_DISCONNECT - do */
222 static const struct nla_policy drbd_disconnect_nl_policy[DRBD_NLA_DISCONNECT_PARMS + 1] = {
223 	[DRBD_NLA_CFG_CONTEXT] = NLA_POLICY_NESTED(drbd_drbd_cfg_context_nl_policy),
224 	[DRBD_NLA_DISCONNECT_PARMS] = NLA_POLICY_NESTED(drbd_disconnect_parms_nl_policy),
225 };
226 
227 /* DRBD_ADM_ATTACH - do */
228 static const struct nla_policy drbd_attach_nl_policy[DRBD_NLA_DISK_CONF + 1] = {
229 	[DRBD_NLA_CFG_CONTEXT] = NLA_POLICY_NESTED(drbd_drbd_cfg_context_nl_policy),
230 	[DRBD_NLA_DISK_CONF] = NLA_POLICY_NESTED(drbd_disk_conf_nl_policy),
231 };
232 
233 /* DRBD_ADM_RESIZE - do */
234 static const struct nla_policy drbd_resize_nl_policy[DRBD_NLA_RESIZE_PARMS + 1] = {
235 	[DRBD_NLA_CFG_CONTEXT] = NLA_POLICY_NESTED(drbd_drbd_cfg_context_nl_policy),
236 	[DRBD_NLA_RESIZE_PARMS] = NLA_POLICY_NESTED(drbd_resize_parms_nl_policy),
237 };
238 
239 /* DRBD_ADM_PRIMARY - do */
240 static const struct nla_policy drbd_primary_nl_policy[DRBD_NLA_SET_ROLE_PARMS + 1] = {
241 	[DRBD_NLA_CFG_CONTEXT] = NLA_POLICY_NESTED(drbd_drbd_cfg_context_nl_policy),
242 	[DRBD_NLA_SET_ROLE_PARMS] = NLA_POLICY_NESTED(drbd_set_role_parms_nl_policy),
243 };
244 
245 /* DRBD_ADM_SECONDARY - do */
246 static const struct nla_policy drbd_secondary_nl_policy[DRBD_NLA_SET_ROLE_PARMS + 1] = {
247 	[DRBD_NLA_CFG_CONTEXT] = NLA_POLICY_NESTED(drbd_drbd_cfg_context_nl_policy),
248 	[DRBD_NLA_SET_ROLE_PARMS] = NLA_POLICY_NESTED(drbd_set_role_parms_nl_policy),
249 };
250 
251 /* DRBD_ADM_NEW_C_UUID - do */
252 static const struct nla_policy drbd_new_c_uuid_nl_policy[DRBD_NLA_NEW_C_UUID_PARMS + 1] = {
253 	[DRBD_NLA_CFG_CONTEXT] = NLA_POLICY_NESTED(drbd_drbd_cfg_context_nl_policy),
254 	[DRBD_NLA_NEW_C_UUID_PARMS] = NLA_POLICY_NESTED(drbd_new_c_uuid_parms_nl_policy),
255 };
256 
257 /* DRBD_ADM_START_OV - do */
258 static const struct nla_policy drbd_start_ov_nl_policy[DRBD_NLA_START_OV_PARMS + 1] = {
259 	[DRBD_NLA_START_OV_PARMS] = NLA_POLICY_NESTED(drbd_start_ov_parms_nl_policy),
260 };
261 
262 /* DRBD_ADM_DETACH - do */
263 static const struct nla_policy drbd_detach_nl_policy[DRBD_NLA_DETACH_PARMS + 1] = {
264 	[DRBD_NLA_CFG_CONTEXT] = NLA_POLICY_NESTED(drbd_drbd_cfg_context_nl_policy),
265 	[DRBD_NLA_DETACH_PARMS] = NLA_POLICY_NESTED(drbd_detach_parms_nl_policy),
266 };
267 
268 /* DRBD_ADM_INVALIDATE - do */
269 static const struct nla_policy drbd_invalidate_nl_policy[DRBD_NLA_CFG_CONTEXT + 1] = {
270 	[DRBD_NLA_CFG_CONTEXT] = NLA_POLICY_NESTED(drbd_drbd_cfg_context_nl_policy),
271 };
272 
273 /* DRBD_ADM_INVAL_PEER - do */
274 static const struct nla_policy drbd_inval_peer_nl_policy[DRBD_NLA_CFG_CONTEXT + 1] = {
275 	[DRBD_NLA_CFG_CONTEXT] = NLA_POLICY_NESTED(drbd_drbd_cfg_context_nl_policy),
276 };
277 
278 /* DRBD_ADM_PAUSE_SYNC - do */
279 static const struct nla_policy drbd_pause_sync_nl_policy[DRBD_NLA_CFG_CONTEXT + 1] = {
280 	[DRBD_NLA_CFG_CONTEXT] = NLA_POLICY_NESTED(drbd_drbd_cfg_context_nl_policy),
281 };
282 
283 /* DRBD_ADM_RESUME_SYNC - do */
284 static const struct nla_policy drbd_resume_sync_nl_policy[DRBD_NLA_CFG_CONTEXT + 1] = {
285 	[DRBD_NLA_CFG_CONTEXT] = NLA_POLICY_NESTED(drbd_drbd_cfg_context_nl_policy),
286 };
287 
288 /* DRBD_ADM_SUSPEND_IO - do */
289 static const struct nla_policy drbd_suspend_io_nl_policy[DRBD_NLA_CFG_CONTEXT + 1] = {
290 	[DRBD_NLA_CFG_CONTEXT] = NLA_POLICY_NESTED(drbd_drbd_cfg_context_nl_policy),
291 };
292 
293 /* DRBD_ADM_RESUME_IO - do */
294 static const struct nla_policy drbd_resume_io_nl_policy[DRBD_NLA_CFG_CONTEXT + 1] = {
295 	[DRBD_NLA_CFG_CONTEXT] = NLA_POLICY_NESTED(drbd_drbd_cfg_context_nl_policy),
296 };
297 
298 /* DRBD_ADM_OUTDATE - do */
299 static const struct nla_policy drbd_outdate_nl_policy[DRBD_NLA_CFG_CONTEXT + 1] = {
300 	[DRBD_NLA_CFG_CONTEXT] = NLA_POLICY_NESTED(drbd_drbd_cfg_context_nl_policy),
301 };
302 
303 /* DRBD_ADM_GET_TIMEOUT_TYPE - do */
304 static const struct nla_policy drbd_get_timeout_type_nl_policy[DRBD_NLA_CFG_CONTEXT + 1] = {
305 	[DRBD_NLA_CFG_CONTEXT] = NLA_POLICY_NESTED(drbd_drbd_cfg_context_nl_policy),
306 };
307 
308 /* DRBD_ADM_DOWN - do */
309 static const struct nla_policy drbd_down_nl_policy[DRBD_NLA_CFG_CONTEXT + 1] = {
310 	[DRBD_NLA_CFG_CONTEXT] = NLA_POLICY_NESTED(drbd_drbd_cfg_context_nl_policy),
311 };
312 
313 /* DRBD_ADM_CHG_DISK_OPTS - do */
314 static const struct nla_policy drbd_chg_disk_opts_nl_policy[DRBD_NLA_DISK_CONF + 1] = {
315 	[DRBD_NLA_CFG_CONTEXT] = NLA_POLICY_NESTED(drbd_drbd_cfg_context_nl_policy),
316 	[DRBD_NLA_DISK_CONF] = NLA_POLICY_NESTED(drbd_disk_conf_nl_policy),
317 };
318 
319 /* DRBD_ADM_CHG_NET_OPTS - do */
320 static const struct nla_policy drbd_chg_net_opts_nl_policy[DRBD_NLA_NET_CONF + 1] = {
321 	[DRBD_NLA_CFG_CONTEXT] = NLA_POLICY_NESTED(drbd_drbd_cfg_context_nl_policy),
322 	[DRBD_NLA_NET_CONF] = NLA_POLICY_NESTED(drbd_net_conf_nl_policy),
323 };
324 
325 /* DRBD_ADM_GET_RESOURCES - dump */
326 static const struct nla_policy drbd_get_resources_nl_policy[DRBD_NLA_RESOURCE_STATISTICS + 1] = {
327 	[DRBD_NLA_CFG_CONTEXT] = NLA_POLICY_NESTED(drbd_drbd_cfg_context_nl_policy),
328 	[DRBD_NLA_RESOURCE_INFO] = NLA_POLICY_NESTED(drbd_resource_info_nl_policy),
329 	[DRBD_NLA_RESOURCE_STATISTICS] = NLA_POLICY_NESTED(drbd_resource_statistics_nl_policy),
330 };
331 
332 /* DRBD_ADM_GET_DEVICES - dump */
333 static const struct nla_policy drbd_get_devices_nl_policy[DRBD_NLA_DEVICE_STATISTICS + 1] = {
334 	[DRBD_NLA_CFG_CONTEXT] = NLA_POLICY_NESTED(drbd_drbd_cfg_context_nl_policy),
335 	[DRBD_NLA_DEVICE_INFO] = NLA_POLICY_NESTED(drbd_device_info_nl_policy),
336 	[DRBD_NLA_DEVICE_STATISTICS] = NLA_POLICY_NESTED(drbd_device_statistics_nl_policy),
337 };
338 
339 /* DRBD_ADM_GET_CONNECTIONS - dump */
340 static const struct nla_policy drbd_get_connections_nl_policy[DRBD_NLA_CONNECTION_STATISTICS + 1] = {
341 	[DRBD_NLA_CFG_CONTEXT] = NLA_POLICY_NESTED(drbd_drbd_cfg_context_nl_policy),
342 	[DRBD_NLA_CONNECTION_INFO] = NLA_POLICY_NESTED(drbd_connection_info_nl_policy),
343 	[DRBD_NLA_CONNECTION_STATISTICS] = NLA_POLICY_NESTED(drbd_connection_statistics_nl_policy),
344 };
345 
346 /* DRBD_ADM_GET_PEER_DEVICES - dump */
347 static const struct nla_policy drbd_get_peer_devices_nl_policy[DRBD_NLA_PEER_DEVICE_STATISTICS + 1] = {
348 	[DRBD_NLA_CFG_CONTEXT] = NLA_POLICY_NESTED(drbd_drbd_cfg_context_nl_policy),
349 	[DRBD_NLA_PEER_DEVICE_INFO] = NLA_POLICY_NESTED(drbd_peer_device_info_nl_policy),
350 	[DRBD_NLA_PEER_DEVICE_STATISTICS] = NLA_POLICY_NESTED(drbd_peer_device_statistics_nl_policy),
351 };
352 
353 /* DRBD_ADM_GET_INITIAL_STATE - dump */
354 static const struct nla_policy drbd_get_initial_state_nl_policy[DRBD_NLA_CFG_CONTEXT + 1] = {
355 	[DRBD_NLA_CFG_CONTEXT] = NLA_POLICY_NESTED(drbd_drbd_cfg_context_nl_policy),
356 };
357 
358 /* Ops table for drbd */
359 const struct genl_split_ops drbd_nl_ops[32] = {
360 	{
361 		.cmd		= DRBD_ADM_GET_STATUS,
362 		.pre_doit	= drbd_pre_doit,
363 		.doit		= drbd_nl_get_status_doit,
364 		.post_doit	= drbd_post_doit,
365 		.policy		= drbd_get_status_do_nl_policy,
366 		.maxattr	= DRBD_NLA_CFG_CONTEXT,
367 		.flags		= GENL_CMD_CAP_DO,
368 	},
369 	{
370 		.cmd		= DRBD_ADM_GET_STATUS,
371 		.dumpit		= drbd_nl_get_status_dumpit,
372 		.policy		= drbd_get_status_dump_nl_policy,
373 		.maxattr	= DRBD_NLA_CFG_CONTEXT,
374 		.flags		= GENL_CMD_CAP_DUMP,
375 	},
376 	{
377 		.cmd		= DRBD_ADM_NEW_MINOR,
378 		.pre_doit	= drbd_pre_doit,
379 		.doit		= drbd_nl_new_minor_doit,
380 		.post_doit	= drbd_post_doit,
381 		.policy		= drbd_new_minor_nl_policy,
382 		.maxattr	= DRBD_NLA_CFG_CONTEXT,
383 		.flags		= GENL_ADMIN_PERM | GENL_CMD_CAP_DO,
384 	},
385 	{
386 		.cmd		= DRBD_ADM_DEL_MINOR,
387 		.pre_doit	= drbd_pre_doit,
388 		.doit		= drbd_nl_del_minor_doit,
389 		.post_doit	= drbd_post_doit,
390 		.policy		= drbd_del_minor_nl_policy,
391 		.maxattr	= DRBD_NLA_CFG_CONTEXT,
392 		.flags		= GENL_ADMIN_PERM | GENL_CMD_CAP_DO,
393 	},
394 	{
395 		.cmd		= DRBD_ADM_NEW_RESOURCE,
396 		.pre_doit	= drbd_pre_doit,
397 		.doit		= drbd_nl_new_resource_doit,
398 		.post_doit	= drbd_post_doit,
399 		.policy		= drbd_new_resource_nl_policy,
400 		.maxattr	= DRBD_NLA_RESOURCE_OPTS,
401 		.flags		= GENL_ADMIN_PERM | GENL_CMD_CAP_DO,
402 	},
403 	{
404 		.cmd		= DRBD_ADM_DEL_RESOURCE,
405 		.pre_doit	= drbd_pre_doit,
406 		.doit		= drbd_nl_del_resource_doit,
407 		.post_doit	= drbd_post_doit,
408 		.policy		= drbd_del_resource_nl_policy,
409 		.maxattr	= DRBD_NLA_CFG_CONTEXT,
410 		.flags		= GENL_ADMIN_PERM | GENL_CMD_CAP_DO,
411 	},
412 	{
413 		.cmd		= DRBD_ADM_RESOURCE_OPTS,
414 		.pre_doit	= drbd_pre_doit,
415 		.doit		= drbd_nl_resource_opts_doit,
416 		.post_doit	= drbd_post_doit,
417 		.policy		= drbd_resource_opts_nl_policy,
418 		.maxattr	= DRBD_NLA_RESOURCE_OPTS,
419 		.flags		= GENL_ADMIN_PERM | GENL_CMD_CAP_DO,
420 	},
421 	{
422 		.cmd		= DRBD_ADM_CONNECT,
423 		.pre_doit	= drbd_pre_doit,
424 		.doit		= drbd_nl_connect_doit,
425 		.post_doit	= drbd_post_doit,
426 		.policy		= drbd_connect_nl_policy,
427 		.maxattr	= DRBD_NLA_NET_CONF,
428 		.flags		= GENL_ADMIN_PERM | GENL_CMD_CAP_DO,
429 	},
430 	{
431 		.cmd		= DRBD_ADM_DISCONNECT,
432 		.pre_doit	= drbd_pre_doit,
433 		.doit		= drbd_nl_disconnect_doit,
434 		.post_doit	= drbd_post_doit,
435 		.policy		= drbd_disconnect_nl_policy,
436 		.maxattr	= DRBD_NLA_DISCONNECT_PARMS,
437 		.flags		= GENL_ADMIN_PERM | GENL_CMD_CAP_DO,
438 	},
439 	{
440 		.cmd		= DRBD_ADM_ATTACH,
441 		.pre_doit	= drbd_pre_doit,
442 		.doit		= drbd_nl_attach_doit,
443 		.post_doit	= drbd_post_doit,
444 		.policy		= drbd_attach_nl_policy,
445 		.maxattr	= DRBD_NLA_DISK_CONF,
446 		.flags		= GENL_ADMIN_PERM | GENL_CMD_CAP_DO,
447 	},
448 	{
449 		.cmd		= DRBD_ADM_RESIZE,
450 		.pre_doit	= drbd_pre_doit,
451 		.doit		= drbd_nl_resize_doit,
452 		.post_doit	= drbd_post_doit,
453 		.policy		= drbd_resize_nl_policy,
454 		.maxattr	= DRBD_NLA_RESIZE_PARMS,
455 		.flags		= GENL_ADMIN_PERM | GENL_CMD_CAP_DO,
456 	},
457 	{
458 		.cmd		= DRBD_ADM_PRIMARY,
459 		.pre_doit	= drbd_pre_doit,
460 		.doit		= drbd_nl_primary_doit,
461 		.post_doit	= drbd_post_doit,
462 		.policy		= drbd_primary_nl_policy,
463 		.maxattr	= DRBD_NLA_SET_ROLE_PARMS,
464 		.flags		= GENL_ADMIN_PERM | GENL_CMD_CAP_DO,
465 	},
466 	{
467 		.cmd		= DRBD_ADM_SECONDARY,
468 		.pre_doit	= drbd_pre_doit,
469 		.doit		= drbd_nl_secondary_doit,
470 		.post_doit	= drbd_post_doit,
471 		.policy		= drbd_secondary_nl_policy,
472 		.maxattr	= DRBD_NLA_SET_ROLE_PARMS,
473 		.flags		= GENL_ADMIN_PERM | GENL_CMD_CAP_DO,
474 	},
475 	{
476 		.cmd		= DRBD_ADM_NEW_C_UUID,
477 		.pre_doit	= drbd_pre_doit,
478 		.doit		= drbd_nl_new_c_uuid_doit,
479 		.post_doit	= drbd_post_doit,
480 		.policy		= drbd_new_c_uuid_nl_policy,
481 		.maxattr	= DRBD_NLA_NEW_C_UUID_PARMS,
482 		.flags		= GENL_ADMIN_PERM | GENL_CMD_CAP_DO,
483 	},
484 	{
485 		.cmd		= DRBD_ADM_START_OV,
486 		.pre_doit	= drbd_pre_doit,
487 		.doit		= drbd_nl_start_ov_doit,
488 		.post_doit	= drbd_post_doit,
489 		.policy		= drbd_start_ov_nl_policy,
490 		.maxattr	= DRBD_NLA_START_OV_PARMS,
491 		.flags		= GENL_ADMIN_PERM | GENL_CMD_CAP_DO,
492 	},
493 	{
494 		.cmd		= DRBD_ADM_DETACH,
495 		.pre_doit	= drbd_pre_doit,
496 		.doit		= drbd_nl_detach_doit,
497 		.post_doit	= drbd_post_doit,
498 		.policy		= drbd_detach_nl_policy,
499 		.maxattr	= DRBD_NLA_DETACH_PARMS,
500 		.flags		= GENL_ADMIN_PERM | GENL_CMD_CAP_DO,
501 	},
502 	{
503 		.cmd		= DRBD_ADM_INVALIDATE,
504 		.pre_doit	= drbd_pre_doit,
505 		.doit		= drbd_nl_invalidate_doit,
506 		.post_doit	= drbd_post_doit,
507 		.policy		= drbd_invalidate_nl_policy,
508 		.maxattr	= DRBD_NLA_CFG_CONTEXT,
509 		.flags		= GENL_ADMIN_PERM | GENL_CMD_CAP_DO,
510 	},
511 	{
512 		.cmd		= DRBD_ADM_INVAL_PEER,
513 		.pre_doit	= drbd_pre_doit,
514 		.doit		= drbd_nl_inval_peer_doit,
515 		.post_doit	= drbd_post_doit,
516 		.policy		= drbd_inval_peer_nl_policy,
517 		.maxattr	= DRBD_NLA_CFG_CONTEXT,
518 		.flags		= GENL_ADMIN_PERM | GENL_CMD_CAP_DO,
519 	},
520 	{
521 		.cmd		= DRBD_ADM_PAUSE_SYNC,
522 		.pre_doit	= drbd_pre_doit,
523 		.doit		= drbd_nl_pause_sync_doit,
524 		.post_doit	= drbd_post_doit,
525 		.policy		= drbd_pause_sync_nl_policy,
526 		.maxattr	= DRBD_NLA_CFG_CONTEXT,
527 		.flags		= GENL_ADMIN_PERM | GENL_CMD_CAP_DO,
528 	},
529 	{
530 		.cmd		= DRBD_ADM_RESUME_SYNC,
531 		.pre_doit	= drbd_pre_doit,
532 		.doit		= drbd_nl_resume_sync_doit,
533 		.post_doit	= drbd_post_doit,
534 		.policy		= drbd_resume_sync_nl_policy,
535 		.maxattr	= DRBD_NLA_CFG_CONTEXT,
536 		.flags		= GENL_ADMIN_PERM | GENL_CMD_CAP_DO,
537 	},
538 	{
539 		.cmd		= DRBD_ADM_SUSPEND_IO,
540 		.pre_doit	= drbd_pre_doit,
541 		.doit		= drbd_nl_suspend_io_doit,
542 		.post_doit	= drbd_post_doit,
543 		.policy		= drbd_suspend_io_nl_policy,
544 		.maxattr	= DRBD_NLA_CFG_CONTEXT,
545 		.flags		= GENL_ADMIN_PERM | GENL_CMD_CAP_DO,
546 	},
547 	{
548 		.cmd		= DRBD_ADM_RESUME_IO,
549 		.pre_doit	= drbd_pre_doit,
550 		.doit		= drbd_nl_resume_io_doit,
551 		.post_doit	= drbd_post_doit,
552 		.policy		= drbd_resume_io_nl_policy,
553 		.maxattr	= DRBD_NLA_CFG_CONTEXT,
554 		.flags		= GENL_ADMIN_PERM | GENL_CMD_CAP_DO,
555 	},
556 	{
557 		.cmd		= DRBD_ADM_OUTDATE,
558 		.pre_doit	= drbd_pre_doit,
559 		.doit		= drbd_nl_outdate_doit,
560 		.post_doit	= drbd_post_doit,
561 		.policy		= drbd_outdate_nl_policy,
562 		.maxattr	= DRBD_NLA_CFG_CONTEXT,
563 		.flags		= GENL_ADMIN_PERM | GENL_CMD_CAP_DO,
564 	},
565 	{
566 		.cmd		= DRBD_ADM_GET_TIMEOUT_TYPE,
567 		.pre_doit	= drbd_pre_doit,
568 		.doit		= drbd_nl_get_timeout_type_doit,
569 		.post_doit	= drbd_post_doit,
570 		.policy		= drbd_get_timeout_type_nl_policy,
571 		.maxattr	= DRBD_NLA_CFG_CONTEXT,
572 		.flags		= GENL_ADMIN_PERM | GENL_CMD_CAP_DO,
573 	},
574 	{
575 		.cmd		= DRBD_ADM_DOWN,
576 		.pre_doit	= drbd_pre_doit,
577 		.doit		= drbd_nl_down_doit,
578 		.post_doit	= drbd_post_doit,
579 		.policy		= drbd_down_nl_policy,
580 		.maxattr	= DRBD_NLA_CFG_CONTEXT,
581 		.flags		= GENL_ADMIN_PERM | GENL_CMD_CAP_DO,
582 	},
583 	{
584 		.cmd		= DRBD_ADM_CHG_DISK_OPTS,
585 		.pre_doit	= drbd_pre_doit,
586 		.doit		= drbd_nl_chg_disk_opts_doit,
587 		.post_doit	= drbd_post_doit,
588 		.policy		= drbd_chg_disk_opts_nl_policy,
589 		.maxattr	= DRBD_NLA_DISK_CONF,
590 		.flags		= GENL_ADMIN_PERM | GENL_CMD_CAP_DO,
591 	},
592 	{
593 		.cmd		= DRBD_ADM_CHG_NET_OPTS,
594 		.pre_doit	= drbd_pre_doit,
595 		.doit		= drbd_nl_chg_net_opts_doit,
596 		.post_doit	= drbd_post_doit,
597 		.policy		= drbd_chg_net_opts_nl_policy,
598 		.maxattr	= DRBD_NLA_NET_CONF,
599 		.flags		= GENL_ADMIN_PERM | GENL_CMD_CAP_DO,
600 	},
601 	{
602 		.cmd		= DRBD_ADM_GET_RESOURCES,
603 		.dumpit		= drbd_nl_get_resources_dumpit,
604 		.policy		= drbd_get_resources_nl_policy,
605 		.maxattr	= DRBD_NLA_RESOURCE_STATISTICS,
606 		.flags		= GENL_CMD_CAP_DUMP,
607 	},
608 	{
609 		.cmd		= DRBD_ADM_GET_DEVICES,
610 		.dumpit		= drbd_nl_get_devices_dumpit,
611 		.done		= drbd_adm_dump_devices_done,
612 		.policy		= drbd_get_devices_nl_policy,
613 		.maxattr	= DRBD_NLA_DEVICE_STATISTICS,
614 		.flags		= GENL_CMD_CAP_DUMP,
615 	},
616 	{
617 		.cmd		= DRBD_ADM_GET_CONNECTIONS,
618 		.dumpit		= drbd_nl_get_connections_dumpit,
619 		.done		= drbd_adm_dump_connections_done,
620 		.policy		= drbd_get_connections_nl_policy,
621 		.maxattr	= DRBD_NLA_CONNECTION_STATISTICS,
622 		.flags		= GENL_CMD_CAP_DUMP,
623 	},
624 	{
625 		.cmd		= DRBD_ADM_GET_PEER_DEVICES,
626 		.dumpit		= drbd_nl_get_peer_devices_dumpit,
627 		.done		= drbd_adm_dump_peer_devices_done,
628 		.policy		= drbd_get_peer_devices_nl_policy,
629 		.maxattr	= DRBD_NLA_PEER_DEVICE_STATISTICS,
630 		.flags		= GENL_CMD_CAP_DUMP,
631 	},
632 	{
633 		.cmd		= DRBD_ADM_GET_INITIAL_STATE,
634 		.dumpit		= drbd_nl_get_initial_state_dumpit,
635 		.policy		= drbd_get_initial_state_nl_policy,
636 		.maxattr	= DRBD_NLA_CFG_CONTEXT,
637 		.flags		= GENL_CMD_CAP_DUMP,
638 	},
639 };
640 
641 static const struct genl_multicast_group drbd_nl_mcgrps[] = {
642 	[DRBD_NLGRP_EVENTS] = { "events", },
643 };
644 
645 static int __drbd_cfg_context_from_attrs(struct drbd_cfg_context *s,
646 		struct nlattr ***ret_nested_attribute_table,
647 		struct genl_info *info)
648 {
649 	const int maxtype = DRBD_A_DRBD_CFG_CONTEXT_CTX_PEER_ADDR;
650 	struct nlattr *tla = info->attrs[DRBD_NLA_CFG_CONTEXT];
651 	struct nlattr **ntb;
652 	struct nlattr *nla;
653 	int err = 0;
654 
655 	if (ret_nested_attribute_table)
656 		*ret_nested_attribute_table = NULL;
657 	if (!tla)
658 		return -ENOMSG;
659 	ntb = kcalloc(DRBD_A_DRBD_CFG_CONTEXT_CTX_PEER_ADDR + 1, sizeof(*ntb), GFP_KERNEL);
660 	if (!ntb)
661 		return -ENOMEM;
662 	err = nla_parse_nested_deprecated(ntb, maxtype, tla, drbd_drbd_cfg_context_nl_policy, NULL);
663 	if (err)
664 		goto out;
665 
666 	nla = ntb[DRBD_A_DRBD_CFG_CONTEXT_CTX_VOLUME];
667 	if (nla && s)
668 		s->ctx_volume = nla_get_u32(nla);
669 
670 	nla = ntb[DRBD_A_DRBD_CFG_CONTEXT_CTX_RESOURCE_NAME];
671 	if (nla && s)
672 		s->ctx_resource_name_len = nla_strscpy(s->ctx_resource_name, nla, 128);
673 
674 	nla = ntb[DRBD_A_DRBD_CFG_CONTEXT_CTX_MY_ADDR];
675 	if (nla && s)
676 		s->ctx_my_addr_len = nla_memcpy(s->ctx_my_addr, nla, 128);
677 
678 	nla = ntb[DRBD_A_DRBD_CFG_CONTEXT_CTX_PEER_ADDR];
679 	if (nla && s)
680 		s->ctx_peer_addr_len = nla_memcpy(s->ctx_peer_addr, nla, 128);
681 
682 out:
683 	if (ret_nested_attribute_table && (!err || err == -ENOMSG))
684 		*ret_nested_attribute_table = ntb;
685 	else
686 		kfree(ntb);
687 	return err;
688 }
689 
690 int drbd_cfg_context_from_attrs(struct drbd_cfg_context *s,
691 				struct genl_info *info)
692 {
693 	return __drbd_cfg_context_from_attrs(s, NULL, info);
694 }
695 
696 int drbd_cfg_context_ntb_from_attrs(
697 			struct nlattr ***ret_nested_attribute_table,
698 			struct genl_info *info)
699 {
700 	return __drbd_cfg_context_from_attrs(NULL, ret_nested_attribute_table, info);
701 }
702 
703 static int __disk_conf_from_attrs(struct disk_conf *s,
704 		struct nlattr ***ret_nested_attribute_table,
705 		struct genl_info *info)
706 {
707 	const int maxtype = DRBD_A_DISK_CONF_DISABLE_WRITE_SAME;
708 	struct nlattr *tla = info->attrs[DRBD_NLA_DISK_CONF];
709 	struct nlattr **ntb;
710 	struct nlattr *nla;
711 	int err = 0;
712 
713 	if (ret_nested_attribute_table)
714 		*ret_nested_attribute_table = NULL;
715 	if (!tla)
716 		return -ENOMSG;
717 	ntb = kcalloc(DRBD_A_DISK_CONF_DISABLE_WRITE_SAME + 1, sizeof(*ntb), GFP_KERNEL);
718 	if (!ntb)
719 		return -ENOMEM;
720 	err = nla_parse_nested_deprecated(ntb, maxtype, tla, drbd_disk_conf_nl_policy, NULL);
721 	if (err)
722 		goto out;
723 
724 	nla = ntb[DRBD_A_DISK_CONF_BACKING_DEV];
725 	if (nla) {
726 		if (s)
727 			s->backing_dev_len = nla_strscpy(s->backing_dev, nla, 128);
728 	} else {
729 		pr_info("<< missing required attr: backing_dev\n");
730 		err = -ENOMSG;
731 	}
732 
733 	nla = ntb[DRBD_A_DISK_CONF_META_DEV];
734 	if (nla) {
735 		if (s)
736 			s->meta_dev_len = nla_strscpy(s->meta_dev, nla, 128);
737 	} else {
738 		pr_info("<< missing required attr: meta_dev\n");
739 		err = -ENOMSG;
740 	}
741 
742 	nla = ntb[DRBD_A_DISK_CONF_META_DEV_IDX];
743 	if (nla) {
744 		if (s)
745 			s->meta_dev_idx = nla_get_s32(nla);
746 	} else {
747 		pr_info("<< missing required attr: meta_dev_idx\n");
748 		err = -ENOMSG;
749 	}
750 
751 	nla = ntb[DRBD_A_DISK_CONF_DISK_SIZE];
752 	if (nla && s)
753 		s->disk_size = nla_get_u64(nla);
754 
755 	nla = ntb[DRBD_A_DISK_CONF_MAX_BIO_BVECS];
756 	if (nla && s)
757 		s->max_bio_bvecs = nla_get_u32(nla);
758 
759 	nla = ntb[DRBD_A_DISK_CONF_ON_IO_ERROR];
760 	if (nla && s)
761 		s->on_io_error = nla_get_u32(nla);
762 
763 	nla = ntb[DRBD_A_DISK_CONF_FENCING];
764 	if (nla && s)
765 		s->fencing = nla_get_u32(nla);
766 
767 	nla = ntb[DRBD_A_DISK_CONF_RESYNC_RATE];
768 	if (nla && s)
769 		s->resync_rate = nla_get_u32(nla);
770 
771 	nla = ntb[DRBD_A_DISK_CONF_RESYNC_AFTER];
772 	if (nla && s)
773 		s->resync_after = nla_get_s32(nla);
774 
775 	nla = ntb[DRBD_A_DISK_CONF_AL_EXTENTS];
776 	if (nla && s)
777 		s->al_extents = nla_get_u32(nla);
778 
779 	nla = ntb[DRBD_A_DISK_CONF_C_PLAN_AHEAD];
780 	if (nla && s)
781 		s->c_plan_ahead = nla_get_u32(nla);
782 
783 	nla = ntb[DRBD_A_DISK_CONF_C_DELAY_TARGET];
784 	if (nla && s)
785 		s->c_delay_target = nla_get_u32(nla);
786 
787 	nla = ntb[DRBD_A_DISK_CONF_C_FILL_TARGET];
788 	if (nla && s)
789 		s->c_fill_target = nla_get_u32(nla);
790 
791 	nla = ntb[DRBD_A_DISK_CONF_C_MAX_RATE];
792 	if (nla && s)
793 		s->c_max_rate = nla_get_u32(nla);
794 
795 	nla = ntb[DRBD_A_DISK_CONF_C_MIN_RATE];
796 	if (nla && s)
797 		s->c_min_rate = nla_get_u32(nla);
798 
799 	nla = ntb[DRBD_A_DISK_CONF_DISK_BARRIER];
800 	if (nla && s)
801 		s->disk_barrier = nla_get_u8(nla);
802 
803 	nla = ntb[DRBD_A_DISK_CONF_DISK_FLUSHES];
804 	if (nla && s)
805 		s->disk_flushes = nla_get_u8(nla);
806 
807 	nla = ntb[DRBD_A_DISK_CONF_DISK_DRAIN];
808 	if (nla && s)
809 		s->disk_drain = nla_get_u8(nla);
810 
811 	nla = ntb[DRBD_A_DISK_CONF_MD_FLUSHES];
812 	if (nla && s)
813 		s->md_flushes = nla_get_u8(nla);
814 
815 	nla = ntb[DRBD_A_DISK_CONF_DISK_TIMEOUT];
816 	if (nla && s)
817 		s->disk_timeout = nla_get_u32(nla);
818 
819 	nla = ntb[DRBD_A_DISK_CONF_READ_BALANCING];
820 	if (nla && s)
821 		s->read_balancing = nla_get_u32(nla);
822 
823 	nla = ntb[DRBD_A_DISK_CONF_AL_UPDATES];
824 	if (nla && s)
825 		s->al_updates = nla_get_u8(nla);
826 
827 	nla = ntb[DRBD_A_DISK_CONF_DISCARD_ZEROES_IF_ALIGNED];
828 	if (nla && s)
829 		s->discard_zeroes_if_aligned = nla_get_u8(nla);
830 
831 	nla = ntb[DRBD_A_DISK_CONF_RS_DISCARD_GRANULARITY];
832 	if (nla && s)
833 		s->rs_discard_granularity = nla_get_u32(nla);
834 
835 	nla = ntb[DRBD_A_DISK_CONF_DISABLE_WRITE_SAME];
836 	if (nla && s)
837 		s->disable_write_same = nla_get_u8(nla);
838 
839 out:
840 	if (ret_nested_attribute_table && (!err || err == -ENOMSG))
841 		*ret_nested_attribute_table = ntb;
842 	else
843 		kfree(ntb);
844 	return err;
845 }
846 
847 int disk_conf_from_attrs(struct disk_conf *s,
848 				struct genl_info *info)
849 {
850 	return __disk_conf_from_attrs(s, NULL, info);
851 }
852 
853 int disk_conf_ntb_from_attrs(
854 			struct nlattr ***ret_nested_attribute_table,
855 			struct genl_info *info)
856 {
857 	return __disk_conf_from_attrs(NULL, ret_nested_attribute_table, info);
858 }
859 
860 static int __res_opts_from_attrs(struct res_opts *s,
861 		struct nlattr ***ret_nested_attribute_table,
862 		struct genl_info *info)
863 {
864 	const int maxtype = DRBD_A_RES_OPTS_ON_NO_DATA;
865 	struct nlattr *tla = info->attrs[DRBD_NLA_RESOURCE_OPTS];
866 	struct nlattr **ntb;
867 	struct nlattr *nla;
868 	int err = 0;
869 
870 	if (ret_nested_attribute_table)
871 		*ret_nested_attribute_table = NULL;
872 	if (!tla)
873 		return -ENOMSG;
874 	ntb = kcalloc(DRBD_A_RES_OPTS_ON_NO_DATA + 1, sizeof(*ntb), GFP_KERNEL);
875 	if (!ntb)
876 		return -ENOMEM;
877 	err = nla_parse_nested_deprecated(ntb, maxtype, tla, drbd_res_opts_nl_policy, NULL);
878 	if (err)
879 		goto out;
880 
881 	nla = ntb[DRBD_A_RES_OPTS_CPU_MASK];
882 	if (nla && s)
883 		s->cpu_mask_len = nla_strscpy(s->cpu_mask, nla, DRBD_CPU_MASK_SIZE);
884 
885 	nla = ntb[DRBD_A_RES_OPTS_ON_NO_DATA];
886 	if (nla && s)
887 		s->on_no_data = nla_get_u32(nla);
888 
889 out:
890 	if (ret_nested_attribute_table && (!err || err == -ENOMSG))
891 		*ret_nested_attribute_table = ntb;
892 	else
893 		kfree(ntb);
894 	return err;
895 }
896 
897 int res_opts_from_attrs(struct res_opts *s,
898 				struct genl_info *info)
899 {
900 	return __res_opts_from_attrs(s, NULL, info);
901 }
902 
903 int res_opts_ntb_from_attrs(
904 			struct nlattr ***ret_nested_attribute_table,
905 			struct genl_info *info)
906 {
907 	return __res_opts_from_attrs(NULL, ret_nested_attribute_table, info);
908 }
909 
910 static int __net_conf_from_attrs(struct net_conf *s,
911 		struct nlattr ***ret_nested_attribute_table,
912 		struct genl_info *info)
913 {
914 	const int maxtype = DRBD_A_NET_CONF_SOCK_CHECK_TIMEO;
915 	struct nlattr *tla = info->attrs[DRBD_NLA_NET_CONF];
916 	struct nlattr **ntb;
917 	struct nlattr *nla;
918 	int err = 0;
919 
920 	if (ret_nested_attribute_table)
921 		*ret_nested_attribute_table = NULL;
922 	if (!tla)
923 		return -ENOMSG;
924 	ntb = kcalloc(DRBD_A_NET_CONF_SOCK_CHECK_TIMEO + 1, sizeof(*ntb), GFP_KERNEL);
925 	if (!ntb)
926 		return -ENOMEM;
927 	err = nla_parse_nested_deprecated(ntb, maxtype, tla, drbd_net_conf_nl_policy, NULL);
928 	if (err)
929 		goto out;
930 
931 	nla = ntb[DRBD_A_NET_CONF_SHARED_SECRET];
932 	if (nla && s)
933 		s->shared_secret_len = nla_strscpy(s->shared_secret, nla, SHARED_SECRET_MAX);
934 
935 	nla = ntb[DRBD_A_NET_CONF_CRAM_HMAC_ALG];
936 	if (nla && s)
937 		s->cram_hmac_alg_len = nla_strscpy(s->cram_hmac_alg, nla, SHARED_SECRET_MAX);
938 
939 	nla = ntb[DRBD_A_NET_CONF_INTEGRITY_ALG];
940 	if (nla && s)
941 		s->integrity_alg_len = nla_strscpy(s->integrity_alg, nla, SHARED_SECRET_MAX);
942 
943 	nla = ntb[DRBD_A_NET_CONF_VERIFY_ALG];
944 	if (nla && s)
945 		s->verify_alg_len = nla_strscpy(s->verify_alg, nla, SHARED_SECRET_MAX);
946 
947 	nla = ntb[DRBD_A_NET_CONF_CSUMS_ALG];
948 	if (nla && s)
949 		s->csums_alg_len = nla_strscpy(s->csums_alg, nla, SHARED_SECRET_MAX);
950 
951 	nla = ntb[DRBD_A_NET_CONF_WIRE_PROTOCOL];
952 	if (nla && s)
953 		s->wire_protocol = nla_get_u32(nla);
954 
955 	nla = ntb[DRBD_A_NET_CONF_CONNECT_INT];
956 	if (nla && s)
957 		s->connect_int = nla_get_u32(nla);
958 
959 	nla = ntb[DRBD_A_NET_CONF_TIMEOUT];
960 	if (nla && s)
961 		s->timeout = nla_get_u32(nla);
962 
963 	nla = ntb[DRBD_A_NET_CONF_PING_INT];
964 	if (nla && s)
965 		s->ping_int = nla_get_u32(nla);
966 
967 	nla = ntb[DRBD_A_NET_CONF_PING_TIMEO];
968 	if (nla && s)
969 		s->ping_timeo = nla_get_u32(nla);
970 
971 	nla = ntb[DRBD_A_NET_CONF_SNDBUF_SIZE];
972 	if (nla && s)
973 		s->sndbuf_size = nla_get_u32(nla);
974 
975 	nla = ntb[DRBD_A_NET_CONF_RCVBUF_SIZE];
976 	if (nla && s)
977 		s->rcvbuf_size = nla_get_u32(nla);
978 
979 	nla = ntb[DRBD_A_NET_CONF_KO_COUNT];
980 	if (nla && s)
981 		s->ko_count = nla_get_u32(nla);
982 
983 	nla = ntb[DRBD_A_NET_CONF_MAX_BUFFERS];
984 	if (nla && s)
985 		s->max_buffers = nla_get_u32(nla);
986 
987 	nla = ntb[DRBD_A_NET_CONF_MAX_EPOCH_SIZE];
988 	if (nla && s)
989 		s->max_epoch_size = nla_get_u32(nla);
990 
991 	nla = ntb[DRBD_A_NET_CONF_UNPLUG_WATERMARK];
992 	if (nla && s)
993 		s->unplug_watermark = nla_get_u32(nla);
994 
995 	nla = ntb[DRBD_A_NET_CONF_AFTER_SB_0P];
996 	if (nla && s)
997 		s->after_sb_0p = nla_get_u32(nla);
998 
999 	nla = ntb[DRBD_A_NET_CONF_AFTER_SB_1P];
1000 	if (nla && s)
1001 		s->after_sb_1p = nla_get_u32(nla);
1002 
1003 	nla = ntb[DRBD_A_NET_CONF_AFTER_SB_2P];
1004 	if (nla && s)
1005 		s->after_sb_2p = nla_get_u32(nla);
1006 
1007 	nla = ntb[DRBD_A_NET_CONF_RR_CONFLICT];
1008 	if (nla && s)
1009 		s->rr_conflict = nla_get_u32(nla);
1010 
1011 	nla = ntb[DRBD_A_NET_CONF_ON_CONGESTION];
1012 	if (nla && s)
1013 		s->on_congestion = nla_get_u32(nla);
1014 
1015 	nla = ntb[DRBD_A_NET_CONF_CONG_FILL];
1016 	if (nla && s)
1017 		s->cong_fill = nla_get_u32(nla);
1018 
1019 	nla = ntb[DRBD_A_NET_CONF_CONG_EXTENTS];
1020 	if (nla && s)
1021 		s->cong_extents = nla_get_u32(nla);
1022 
1023 	nla = ntb[DRBD_A_NET_CONF_TWO_PRIMARIES];
1024 	if (nla && s)
1025 		s->two_primaries = nla_get_u8(nla);
1026 
1027 	nla = ntb[DRBD_A_NET_CONF_DISCARD_MY_DATA];
1028 	if (nla && s)
1029 		s->discard_my_data = nla_get_u8(nla);
1030 
1031 	nla = ntb[DRBD_A_NET_CONF_TCP_CORK];
1032 	if (nla && s)
1033 		s->tcp_cork = nla_get_u8(nla);
1034 
1035 	nla = ntb[DRBD_A_NET_CONF_ALWAYS_ASBP];
1036 	if (nla && s)
1037 		s->always_asbp = nla_get_u8(nla);
1038 
1039 	nla = ntb[DRBD_A_NET_CONF_TENTATIVE];
1040 	if (nla && s)
1041 		s->tentative = nla_get_u8(nla);
1042 
1043 	nla = ntb[DRBD_A_NET_CONF_USE_RLE];
1044 	if (nla && s)
1045 		s->use_rle = nla_get_u8(nla);
1046 
1047 	nla = ntb[DRBD_A_NET_CONF_CSUMS_AFTER_CRASH_ONLY];
1048 	if (nla && s)
1049 		s->csums_after_crash_only = nla_get_u8(nla);
1050 
1051 	nla = ntb[DRBD_A_NET_CONF_SOCK_CHECK_TIMEO];
1052 	if (nla && s)
1053 		s->sock_check_timeo = nla_get_u32(nla);
1054 
1055 out:
1056 	if (ret_nested_attribute_table && (!err || err == -ENOMSG))
1057 		*ret_nested_attribute_table = ntb;
1058 	else
1059 		kfree(ntb);
1060 	return err;
1061 }
1062 
1063 int net_conf_from_attrs(struct net_conf *s,
1064 				struct genl_info *info)
1065 {
1066 	return __net_conf_from_attrs(s, NULL, info);
1067 }
1068 
1069 int net_conf_ntb_from_attrs(
1070 			struct nlattr ***ret_nested_attribute_table,
1071 			struct genl_info *info)
1072 {
1073 	return __net_conf_from_attrs(NULL, ret_nested_attribute_table, info);
1074 }
1075 
1076 static int __set_role_parms_from_attrs(struct set_role_parms *s,
1077 		struct nlattr ***ret_nested_attribute_table,
1078 		struct genl_info *info)
1079 {
1080 	const int maxtype = DRBD_A_SET_ROLE_PARMS_ASSUME_UPTODATE;
1081 	struct nlattr *tla = info->attrs[DRBD_NLA_SET_ROLE_PARMS];
1082 	struct nlattr **ntb;
1083 	struct nlattr *nla;
1084 	int err = 0;
1085 
1086 	if (ret_nested_attribute_table)
1087 		*ret_nested_attribute_table = NULL;
1088 	if (!tla)
1089 		return -ENOMSG;
1090 	ntb = kcalloc(DRBD_A_SET_ROLE_PARMS_ASSUME_UPTODATE + 1, sizeof(*ntb), GFP_KERNEL);
1091 	if (!ntb)
1092 		return -ENOMEM;
1093 	err = nla_parse_nested_deprecated(ntb, maxtype, tla, drbd_set_role_parms_nl_policy, NULL);
1094 	if (err)
1095 		goto out;
1096 
1097 	nla = ntb[DRBD_A_SET_ROLE_PARMS_ASSUME_UPTODATE];
1098 	if (nla && s)
1099 		s->assume_uptodate = nla_get_u8(nla);
1100 
1101 out:
1102 	if (ret_nested_attribute_table && (!err || err == -ENOMSG))
1103 		*ret_nested_attribute_table = ntb;
1104 	else
1105 		kfree(ntb);
1106 	return err;
1107 }
1108 
1109 int set_role_parms_from_attrs(struct set_role_parms *s,
1110 				struct genl_info *info)
1111 {
1112 	return __set_role_parms_from_attrs(s, NULL, info);
1113 }
1114 
1115 int set_role_parms_ntb_from_attrs(
1116 			struct nlattr ***ret_nested_attribute_table,
1117 			struct genl_info *info)
1118 {
1119 	return __set_role_parms_from_attrs(NULL, ret_nested_attribute_table, info);
1120 }
1121 
1122 static int __resize_parms_from_attrs(struct resize_parms *s,
1123 		struct nlattr ***ret_nested_attribute_table,
1124 		struct genl_info *info)
1125 {
1126 	const int maxtype = DRBD_A_RESIZE_PARMS_AL_STRIPE_SIZE;
1127 	struct nlattr *tla = info->attrs[DRBD_NLA_RESIZE_PARMS];
1128 	struct nlattr **ntb;
1129 	struct nlattr *nla;
1130 	int err = 0;
1131 
1132 	if (ret_nested_attribute_table)
1133 		*ret_nested_attribute_table = NULL;
1134 	if (!tla)
1135 		return -ENOMSG;
1136 	ntb = kcalloc(DRBD_A_RESIZE_PARMS_AL_STRIPE_SIZE + 1, sizeof(*ntb), GFP_KERNEL);
1137 	if (!ntb)
1138 		return -ENOMEM;
1139 	err = nla_parse_nested_deprecated(ntb, maxtype, tla, drbd_resize_parms_nl_policy, NULL);
1140 	if (err)
1141 		goto out;
1142 
1143 	nla = ntb[DRBD_A_RESIZE_PARMS_RESIZE_SIZE];
1144 	if (nla && s)
1145 		s->resize_size = nla_get_u64(nla);
1146 
1147 	nla = ntb[DRBD_A_RESIZE_PARMS_RESIZE_FORCE];
1148 	if (nla && s)
1149 		s->resize_force = nla_get_u8(nla);
1150 
1151 	nla = ntb[DRBD_A_RESIZE_PARMS_NO_RESYNC];
1152 	if (nla && s)
1153 		s->no_resync = nla_get_u8(nla);
1154 
1155 	nla = ntb[DRBD_A_RESIZE_PARMS_AL_STRIPES];
1156 	if (nla && s)
1157 		s->al_stripes = nla_get_u32(nla);
1158 
1159 	nla = ntb[DRBD_A_RESIZE_PARMS_AL_STRIPE_SIZE];
1160 	if (nla && s)
1161 		s->al_stripe_size = nla_get_u32(nla);
1162 
1163 out:
1164 	if (ret_nested_attribute_table && (!err || err == -ENOMSG))
1165 		*ret_nested_attribute_table = ntb;
1166 	else
1167 		kfree(ntb);
1168 	return err;
1169 }
1170 
1171 int resize_parms_from_attrs(struct resize_parms *s,
1172 				struct genl_info *info)
1173 {
1174 	return __resize_parms_from_attrs(s, NULL, info);
1175 }
1176 
1177 int resize_parms_ntb_from_attrs(
1178 			struct nlattr ***ret_nested_attribute_table,
1179 			struct genl_info *info)
1180 {
1181 	return __resize_parms_from_attrs(NULL, ret_nested_attribute_table, info);
1182 }
1183 
1184 static int __start_ov_parms_from_attrs(struct start_ov_parms *s,
1185 		struct nlattr ***ret_nested_attribute_table,
1186 		struct genl_info *info)
1187 {
1188 	const int maxtype = DRBD_A_START_OV_PARMS_OV_STOP_SECTOR;
1189 	struct nlattr *tla = info->attrs[DRBD_NLA_START_OV_PARMS];
1190 	struct nlattr **ntb;
1191 	struct nlattr *nla;
1192 	int err = 0;
1193 
1194 	if (ret_nested_attribute_table)
1195 		*ret_nested_attribute_table = NULL;
1196 	if (!tla)
1197 		return -ENOMSG;
1198 	ntb = kcalloc(DRBD_A_START_OV_PARMS_OV_STOP_SECTOR + 1, sizeof(*ntb), GFP_KERNEL);
1199 	if (!ntb)
1200 		return -ENOMEM;
1201 	err = nla_parse_nested_deprecated(ntb, maxtype, tla, drbd_start_ov_parms_nl_policy, NULL);
1202 	if (err)
1203 		goto out;
1204 
1205 	nla = ntb[DRBD_A_START_OV_PARMS_OV_START_SECTOR];
1206 	if (nla && s)
1207 		s->ov_start_sector = nla_get_u64(nla);
1208 
1209 	nla = ntb[DRBD_A_START_OV_PARMS_OV_STOP_SECTOR];
1210 	if (nla && s)
1211 		s->ov_stop_sector = nla_get_u64(nla);
1212 
1213 out:
1214 	if (ret_nested_attribute_table && (!err || err == -ENOMSG))
1215 		*ret_nested_attribute_table = ntb;
1216 	else
1217 		kfree(ntb);
1218 	return err;
1219 }
1220 
1221 int start_ov_parms_from_attrs(struct start_ov_parms *s,
1222 				struct genl_info *info)
1223 {
1224 	return __start_ov_parms_from_attrs(s, NULL, info);
1225 }
1226 
1227 int start_ov_parms_ntb_from_attrs(
1228 			struct nlattr ***ret_nested_attribute_table,
1229 			struct genl_info *info)
1230 {
1231 	return __start_ov_parms_from_attrs(NULL, ret_nested_attribute_table, info);
1232 }
1233 
1234 static int __new_c_uuid_parms_from_attrs(struct new_c_uuid_parms *s,
1235 		struct nlattr ***ret_nested_attribute_table,
1236 		struct genl_info *info)
1237 {
1238 	const int maxtype = DRBD_A_NEW_C_UUID_PARMS_CLEAR_BM;
1239 	struct nlattr *tla = info->attrs[DRBD_NLA_NEW_C_UUID_PARMS];
1240 	struct nlattr **ntb;
1241 	struct nlattr *nla;
1242 	int err = 0;
1243 
1244 	if (ret_nested_attribute_table)
1245 		*ret_nested_attribute_table = NULL;
1246 	if (!tla)
1247 		return -ENOMSG;
1248 	ntb = kcalloc(DRBD_A_NEW_C_UUID_PARMS_CLEAR_BM + 1, sizeof(*ntb), GFP_KERNEL);
1249 	if (!ntb)
1250 		return -ENOMEM;
1251 	err = nla_parse_nested_deprecated(ntb, maxtype, tla, drbd_new_c_uuid_parms_nl_policy, NULL);
1252 	if (err)
1253 		goto out;
1254 
1255 	nla = ntb[DRBD_A_NEW_C_UUID_PARMS_CLEAR_BM];
1256 	if (nla && s)
1257 		s->clear_bm = nla_get_u8(nla);
1258 
1259 out:
1260 	if (ret_nested_attribute_table && (!err || err == -ENOMSG))
1261 		*ret_nested_attribute_table = ntb;
1262 	else
1263 		kfree(ntb);
1264 	return err;
1265 }
1266 
1267 int new_c_uuid_parms_from_attrs(struct new_c_uuid_parms *s,
1268 				struct genl_info *info)
1269 {
1270 	return __new_c_uuid_parms_from_attrs(s, NULL, info);
1271 }
1272 
1273 int new_c_uuid_parms_ntb_from_attrs(
1274 			struct nlattr ***ret_nested_attribute_table,
1275 			struct genl_info *info)
1276 {
1277 	return __new_c_uuid_parms_from_attrs(NULL, ret_nested_attribute_table, info);
1278 }
1279 
1280 static int __disconnect_parms_from_attrs(struct disconnect_parms *s,
1281 		struct nlattr ***ret_nested_attribute_table,
1282 		struct genl_info *info)
1283 {
1284 	const int maxtype = DRBD_A_DISCONNECT_PARMS_FORCE_DISCONNECT;
1285 	struct nlattr *tla = info->attrs[DRBD_NLA_DISCONNECT_PARMS];
1286 	struct nlattr **ntb;
1287 	struct nlattr *nla;
1288 	int err = 0;
1289 
1290 	if (ret_nested_attribute_table)
1291 		*ret_nested_attribute_table = NULL;
1292 	if (!tla)
1293 		return -ENOMSG;
1294 	ntb = kcalloc(DRBD_A_DISCONNECT_PARMS_FORCE_DISCONNECT + 1, sizeof(*ntb), GFP_KERNEL);
1295 	if (!ntb)
1296 		return -ENOMEM;
1297 	err = nla_parse_nested_deprecated(ntb, maxtype, tla, drbd_disconnect_parms_nl_policy, NULL);
1298 	if (err)
1299 		goto out;
1300 
1301 	nla = ntb[DRBD_A_DISCONNECT_PARMS_FORCE_DISCONNECT];
1302 	if (nla && s)
1303 		s->force_disconnect = nla_get_u8(nla);
1304 
1305 out:
1306 	if (ret_nested_attribute_table && (!err || err == -ENOMSG))
1307 		*ret_nested_attribute_table = ntb;
1308 	else
1309 		kfree(ntb);
1310 	return err;
1311 }
1312 
1313 int disconnect_parms_from_attrs(struct disconnect_parms *s,
1314 				struct genl_info *info)
1315 {
1316 	return __disconnect_parms_from_attrs(s, NULL, info);
1317 }
1318 
1319 int disconnect_parms_ntb_from_attrs(
1320 			struct nlattr ***ret_nested_attribute_table,
1321 			struct genl_info *info)
1322 {
1323 	return __disconnect_parms_from_attrs(NULL, ret_nested_attribute_table, info);
1324 }
1325 
1326 static int __detach_parms_from_attrs(struct detach_parms *s,
1327 		struct nlattr ***ret_nested_attribute_table,
1328 		struct genl_info *info)
1329 {
1330 	const int maxtype = DRBD_A_DETACH_PARMS_FORCE_DETACH;
1331 	struct nlattr *tla = info->attrs[DRBD_NLA_DETACH_PARMS];
1332 	struct nlattr **ntb;
1333 	struct nlattr *nla;
1334 	int err = 0;
1335 
1336 	if (ret_nested_attribute_table)
1337 		*ret_nested_attribute_table = NULL;
1338 	if (!tla)
1339 		return -ENOMSG;
1340 	ntb = kcalloc(DRBD_A_DETACH_PARMS_FORCE_DETACH + 1, sizeof(*ntb), GFP_KERNEL);
1341 	if (!ntb)
1342 		return -ENOMEM;
1343 	err = nla_parse_nested_deprecated(ntb, maxtype, tla, drbd_detach_parms_nl_policy, NULL);
1344 	if (err)
1345 		goto out;
1346 
1347 	nla = ntb[DRBD_A_DETACH_PARMS_FORCE_DETACH];
1348 	if (nla && s)
1349 		s->force_detach = nla_get_u8(nla);
1350 
1351 out:
1352 	if (ret_nested_attribute_table && (!err || err == -ENOMSG))
1353 		*ret_nested_attribute_table = ntb;
1354 	else
1355 		kfree(ntb);
1356 	return err;
1357 }
1358 
1359 int detach_parms_from_attrs(struct detach_parms *s,
1360 				struct genl_info *info)
1361 {
1362 	return __detach_parms_from_attrs(s, NULL, info);
1363 }
1364 
1365 int detach_parms_ntb_from_attrs(
1366 			struct nlattr ***ret_nested_attribute_table,
1367 			struct genl_info *info)
1368 {
1369 	return __detach_parms_from_attrs(NULL, ret_nested_attribute_table, info);
1370 }
1371 
1372 static int __resource_info_from_attrs(struct resource_info *s,
1373 		struct nlattr ***ret_nested_attribute_table,
1374 		struct genl_info *info)
1375 {
1376 	const int maxtype = DRBD_A_RESOURCE_INFO_RES_SUSP_FEN;
1377 	struct nlattr *tla = info->attrs[DRBD_NLA_RESOURCE_INFO];
1378 	struct nlattr **ntb;
1379 	struct nlattr *nla;
1380 	int err = 0;
1381 
1382 	if (ret_nested_attribute_table)
1383 		*ret_nested_attribute_table = NULL;
1384 	if (!tla)
1385 		return -ENOMSG;
1386 	ntb = kcalloc(DRBD_A_RESOURCE_INFO_RES_SUSP_FEN + 1, sizeof(*ntb), GFP_KERNEL);
1387 	if (!ntb)
1388 		return -ENOMEM;
1389 	err = nla_parse_nested_deprecated(ntb, maxtype, tla, drbd_resource_info_nl_policy, NULL);
1390 	if (err)
1391 		goto out;
1392 
1393 	nla = ntb[DRBD_A_RESOURCE_INFO_RES_ROLE];
1394 	if (nla && s)
1395 		s->res_role = nla_get_u32(nla);
1396 
1397 	nla = ntb[DRBD_A_RESOURCE_INFO_RES_SUSP];
1398 	if (nla && s)
1399 		s->res_susp = nla_get_u8(nla);
1400 
1401 	nla = ntb[DRBD_A_RESOURCE_INFO_RES_SUSP_NOD];
1402 	if (nla && s)
1403 		s->res_susp_nod = nla_get_u8(nla);
1404 
1405 	nla = ntb[DRBD_A_RESOURCE_INFO_RES_SUSP_FEN];
1406 	if (nla && s)
1407 		s->res_susp_fen = nla_get_u8(nla);
1408 
1409 out:
1410 	if (ret_nested_attribute_table && (!err || err == -ENOMSG))
1411 		*ret_nested_attribute_table = ntb;
1412 	else
1413 		kfree(ntb);
1414 	return err;
1415 }
1416 
1417 int resource_info_from_attrs(struct resource_info *s,
1418 				struct genl_info *info)
1419 {
1420 	return __resource_info_from_attrs(s, NULL, info);
1421 }
1422 
1423 int resource_info_ntb_from_attrs(
1424 			struct nlattr ***ret_nested_attribute_table,
1425 			struct genl_info *info)
1426 {
1427 	return __resource_info_from_attrs(NULL, ret_nested_attribute_table, info);
1428 }
1429 
1430 static int __device_info_from_attrs(struct device_info *s,
1431 		struct nlattr ***ret_nested_attribute_table,
1432 		struct genl_info *info)
1433 {
1434 	const int maxtype = DRBD_A_DEVICE_INFO_DEV_DISK_STATE;
1435 	struct nlattr *tla = info->attrs[DRBD_NLA_DEVICE_INFO];
1436 	struct nlattr **ntb;
1437 	struct nlattr *nla;
1438 	int err = 0;
1439 
1440 	if (ret_nested_attribute_table)
1441 		*ret_nested_attribute_table = NULL;
1442 	if (!tla)
1443 		return -ENOMSG;
1444 	ntb = kcalloc(DRBD_A_DEVICE_INFO_DEV_DISK_STATE + 1, sizeof(*ntb), GFP_KERNEL);
1445 	if (!ntb)
1446 		return -ENOMEM;
1447 	err = nla_parse_nested_deprecated(ntb, maxtype, tla, drbd_device_info_nl_policy, NULL);
1448 	if (err)
1449 		goto out;
1450 
1451 	nla = ntb[DRBD_A_DEVICE_INFO_DEV_DISK_STATE];
1452 	if (nla && s)
1453 		s->dev_disk_state = nla_get_u32(nla);
1454 
1455 out:
1456 	if (ret_nested_attribute_table && (!err || err == -ENOMSG))
1457 		*ret_nested_attribute_table = ntb;
1458 	else
1459 		kfree(ntb);
1460 	return err;
1461 }
1462 
1463 int device_info_from_attrs(struct device_info *s,
1464 				struct genl_info *info)
1465 {
1466 	return __device_info_from_attrs(s, NULL, info);
1467 }
1468 
1469 int device_info_ntb_from_attrs(
1470 			struct nlattr ***ret_nested_attribute_table,
1471 			struct genl_info *info)
1472 {
1473 	return __device_info_from_attrs(NULL, ret_nested_attribute_table, info);
1474 }
1475 
1476 static int __connection_info_from_attrs(struct connection_info *s,
1477 		struct nlattr ***ret_nested_attribute_table,
1478 		struct genl_info *info)
1479 {
1480 	const int maxtype = DRBD_A_CONNECTION_INFO_CONN_ROLE;
1481 	struct nlattr *tla = info->attrs[DRBD_NLA_CONNECTION_INFO];
1482 	struct nlattr **ntb;
1483 	struct nlattr *nla;
1484 	int err = 0;
1485 
1486 	if (ret_nested_attribute_table)
1487 		*ret_nested_attribute_table = NULL;
1488 	if (!tla)
1489 		return -ENOMSG;
1490 	ntb = kcalloc(DRBD_A_CONNECTION_INFO_CONN_ROLE + 1, sizeof(*ntb), GFP_KERNEL);
1491 	if (!ntb)
1492 		return -ENOMEM;
1493 	err = nla_parse_nested_deprecated(ntb, maxtype, tla, drbd_connection_info_nl_policy, NULL);
1494 	if (err)
1495 		goto out;
1496 
1497 	nla = ntb[DRBD_A_CONNECTION_INFO_CONN_CONNECTION_STATE];
1498 	if (nla && s)
1499 		s->conn_connection_state = nla_get_u32(nla);
1500 
1501 	nla = ntb[DRBD_A_CONNECTION_INFO_CONN_ROLE];
1502 	if (nla && s)
1503 		s->conn_role = nla_get_u32(nla);
1504 
1505 out:
1506 	if (ret_nested_attribute_table && (!err || err == -ENOMSG))
1507 		*ret_nested_attribute_table = ntb;
1508 	else
1509 		kfree(ntb);
1510 	return err;
1511 }
1512 
1513 int connection_info_from_attrs(struct connection_info *s,
1514 				struct genl_info *info)
1515 {
1516 	return __connection_info_from_attrs(s, NULL, info);
1517 }
1518 
1519 int connection_info_ntb_from_attrs(
1520 			struct nlattr ***ret_nested_attribute_table,
1521 			struct genl_info *info)
1522 {
1523 	return __connection_info_from_attrs(NULL, ret_nested_attribute_table, info);
1524 }
1525 
1526 static int __peer_device_info_from_attrs(struct peer_device_info *s,
1527 		struct nlattr ***ret_nested_attribute_table,
1528 		struct genl_info *info)
1529 {
1530 	const int maxtype = DRBD_A_PEER_DEVICE_INFO_PEER_RESYNC_SUSP_DEPENDENCY;
1531 	struct nlattr *tla = info->attrs[DRBD_NLA_PEER_DEVICE_INFO];
1532 	struct nlattr **ntb;
1533 	struct nlattr *nla;
1534 	int err = 0;
1535 
1536 	if (ret_nested_attribute_table)
1537 		*ret_nested_attribute_table = NULL;
1538 	if (!tla)
1539 		return -ENOMSG;
1540 	ntb = kcalloc(DRBD_A_PEER_DEVICE_INFO_PEER_RESYNC_SUSP_DEPENDENCY + 1, sizeof(*ntb), GFP_KERNEL);
1541 	if (!ntb)
1542 		return -ENOMEM;
1543 	err = nla_parse_nested_deprecated(ntb, maxtype, tla, drbd_peer_device_info_nl_policy, NULL);
1544 	if (err)
1545 		goto out;
1546 
1547 	nla = ntb[DRBD_A_PEER_DEVICE_INFO_PEER_REPL_STATE];
1548 	if (nla && s)
1549 		s->peer_repl_state = nla_get_u32(nla);
1550 
1551 	nla = ntb[DRBD_A_PEER_DEVICE_INFO_PEER_DISK_STATE];
1552 	if (nla && s)
1553 		s->peer_disk_state = nla_get_u32(nla);
1554 
1555 	nla = ntb[DRBD_A_PEER_DEVICE_INFO_PEER_RESYNC_SUSP_USER];
1556 	if (nla && s)
1557 		s->peer_resync_susp_user = nla_get_u32(nla);
1558 
1559 	nla = ntb[DRBD_A_PEER_DEVICE_INFO_PEER_RESYNC_SUSP_PEER];
1560 	if (nla && s)
1561 		s->peer_resync_susp_peer = nla_get_u32(nla);
1562 
1563 	nla = ntb[DRBD_A_PEER_DEVICE_INFO_PEER_RESYNC_SUSP_DEPENDENCY];
1564 	if (nla && s)
1565 		s->peer_resync_susp_dependency = nla_get_u32(nla);
1566 
1567 out:
1568 	if (ret_nested_attribute_table && (!err || err == -ENOMSG))
1569 		*ret_nested_attribute_table = ntb;
1570 	else
1571 		kfree(ntb);
1572 	return err;
1573 }
1574 
1575 int peer_device_info_from_attrs(struct peer_device_info *s,
1576 				struct genl_info *info)
1577 {
1578 	return __peer_device_info_from_attrs(s, NULL, info);
1579 }
1580 
1581 int peer_device_info_ntb_from_attrs(
1582 			struct nlattr ***ret_nested_attribute_table,
1583 			struct genl_info *info)
1584 {
1585 	return __peer_device_info_from_attrs(NULL, ret_nested_attribute_table, info);
1586 }
1587 
1588 static int __resource_statistics_from_attrs(struct resource_statistics *s,
1589 		struct nlattr ***ret_nested_attribute_table,
1590 		struct genl_info *info)
1591 {
1592 	const int maxtype = DRBD_A_RESOURCE_STATISTICS_RES_STAT_WRITE_ORDERING;
1593 	struct nlattr *tla = info->attrs[DRBD_NLA_RESOURCE_STATISTICS];
1594 	struct nlattr **ntb;
1595 	struct nlattr *nla;
1596 	int err = 0;
1597 
1598 	if (ret_nested_attribute_table)
1599 		*ret_nested_attribute_table = NULL;
1600 	if (!tla)
1601 		return -ENOMSG;
1602 	ntb = kcalloc(DRBD_A_RESOURCE_STATISTICS_RES_STAT_WRITE_ORDERING + 1, sizeof(*ntb), GFP_KERNEL);
1603 	if (!ntb)
1604 		return -ENOMEM;
1605 	err = nla_parse_nested_deprecated(ntb, maxtype, tla, drbd_resource_statistics_nl_policy, NULL);
1606 	if (err)
1607 		goto out;
1608 
1609 	nla = ntb[DRBD_A_RESOURCE_STATISTICS_RES_STAT_WRITE_ORDERING];
1610 	if (nla && s)
1611 		s->res_stat_write_ordering = nla_get_u32(nla);
1612 
1613 out:
1614 	if (ret_nested_attribute_table && (!err || err == -ENOMSG))
1615 		*ret_nested_attribute_table = ntb;
1616 	else
1617 		kfree(ntb);
1618 	return err;
1619 }
1620 
1621 int resource_statistics_from_attrs(struct resource_statistics *s,
1622 				struct genl_info *info)
1623 {
1624 	return __resource_statistics_from_attrs(s, NULL, info);
1625 }
1626 
1627 int resource_statistics_ntb_from_attrs(
1628 			struct nlattr ***ret_nested_attribute_table,
1629 			struct genl_info *info)
1630 {
1631 	return __resource_statistics_from_attrs(NULL, ret_nested_attribute_table, info);
1632 }
1633 
1634 static int __device_statistics_from_attrs(struct device_statistics *s,
1635 		struct nlattr ***ret_nested_attribute_table,
1636 		struct genl_info *info)
1637 {
1638 	const int maxtype = DRBD_A_DEVICE_STATISTICS_HISTORY_UUIDS;
1639 	struct nlattr *tla = info->attrs[DRBD_NLA_DEVICE_STATISTICS];
1640 	struct nlattr **ntb;
1641 	struct nlattr *nla;
1642 	int err = 0;
1643 
1644 	if (ret_nested_attribute_table)
1645 		*ret_nested_attribute_table = NULL;
1646 	if (!tla)
1647 		return -ENOMSG;
1648 	ntb = kcalloc(DRBD_A_DEVICE_STATISTICS_HISTORY_UUIDS + 1, sizeof(*ntb), GFP_KERNEL);
1649 	if (!ntb)
1650 		return -ENOMEM;
1651 	err = nla_parse_nested_deprecated(ntb, maxtype, tla, drbd_device_statistics_nl_policy, NULL);
1652 	if (err)
1653 		goto out;
1654 
1655 	nla = ntb[DRBD_A_DEVICE_STATISTICS_DEV_SIZE];
1656 	if (nla && s)
1657 		s->dev_size = nla_get_u64(nla);
1658 
1659 	nla = ntb[DRBD_A_DEVICE_STATISTICS_DEV_READ];
1660 	if (nla && s)
1661 		s->dev_read = nla_get_u64(nla);
1662 
1663 	nla = ntb[DRBD_A_DEVICE_STATISTICS_DEV_WRITE];
1664 	if (nla && s)
1665 		s->dev_write = nla_get_u64(nla);
1666 
1667 	nla = ntb[DRBD_A_DEVICE_STATISTICS_DEV_AL_WRITES];
1668 	if (nla && s)
1669 		s->dev_al_writes = nla_get_u64(nla);
1670 
1671 	nla = ntb[DRBD_A_DEVICE_STATISTICS_DEV_BM_WRITES];
1672 	if (nla && s)
1673 		s->dev_bm_writes = nla_get_u64(nla);
1674 
1675 	nla = ntb[DRBD_A_DEVICE_STATISTICS_DEV_UPPER_PENDING];
1676 	if (nla && s)
1677 		s->dev_upper_pending = nla_get_u32(nla);
1678 
1679 	nla = ntb[DRBD_A_DEVICE_STATISTICS_DEV_LOWER_PENDING];
1680 	if (nla && s)
1681 		s->dev_lower_pending = nla_get_u32(nla);
1682 
1683 	nla = ntb[DRBD_A_DEVICE_STATISTICS_DEV_UPPER_BLOCKED];
1684 	if (nla && s)
1685 		s->dev_upper_blocked = nla_get_u8(nla);
1686 
1687 	nla = ntb[DRBD_A_DEVICE_STATISTICS_DEV_LOWER_BLOCKED];
1688 	if (nla && s)
1689 		s->dev_lower_blocked = nla_get_u8(nla);
1690 
1691 	nla = ntb[DRBD_A_DEVICE_STATISTICS_DEV_AL_SUSPENDED];
1692 	if (nla && s)
1693 		s->dev_al_suspended = nla_get_u8(nla);
1694 
1695 	nla = ntb[DRBD_A_DEVICE_STATISTICS_DEV_EXPOSED_DATA_UUID];
1696 	if (nla && s)
1697 		s->dev_exposed_data_uuid = nla_get_u64(nla);
1698 
1699 	nla = ntb[DRBD_A_DEVICE_STATISTICS_DEV_CURRENT_UUID];
1700 	if (nla && s)
1701 		s->dev_current_uuid = nla_get_u64(nla);
1702 
1703 	nla = ntb[DRBD_A_DEVICE_STATISTICS_DEV_DISK_FLAGS];
1704 	if (nla && s)
1705 		s->dev_disk_flags = nla_get_u32(nla);
1706 
1707 	nla = ntb[DRBD_A_DEVICE_STATISTICS_HISTORY_UUIDS];
1708 	if (nla && s)
1709 		s->history_uuids_len = nla_memcpy(s->history_uuids, nla, DRBD_NL_HISTORY_UUIDS_SIZE);
1710 
1711 out:
1712 	if (ret_nested_attribute_table && (!err || err == -ENOMSG))
1713 		*ret_nested_attribute_table = ntb;
1714 	else
1715 		kfree(ntb);
1716 	return err;
1717 }
1718 
1719 int device_statistics_from_attrs(struct device_statistics *s,
1720 				struct genl_info *info)
1721 {
1722 	return __device_statistics_from_attrs(s, NULL, info);
1723 }
1724 
1725 int device_statistics_ntb_from_attrs(
1726 			struct nlattr ***ret_nested_attribute_table,
1727 			struct genl_info *info)
1728 {
1729 	return __device_statistics_from_attrs(NULL, ret_nested_attribute_table, info);
1730 }
1731 
1732 static int __connection_statistics_from_attrs(struct connection_statistics *s,
1733 		struct nlattr ***ret_nested_attribute_table,
1734 		struct genl_info *info)
1735 {
1736 	const int maxtype = DRBD_A_CONNECTION_STATISTICS_CONN_CONGESTED;
1737 	struct nlattr *tla = info->attrs[DRBD_NLA_CONNECTION_STATISTICS];
1738 	struct nlattr **ntb;
1739 	struct nlattr *nla;
1740 	int err = 0;
1741 
1742 	if (ret_nested_attribute_table)
1743 		*ret_nested_attribute_table = NULL;
1744 	if (!tla)
1745 		return -ENOMSG;
1746 	ntb = kcalloc(DRBD_A_CONNECTION_STATISTICS_CONN_CONGESTED + 1, sizeof(*ntb), GFP_KERNEL);
1747 	if (!ntb)
1748 		return -ENOMEM;
1749 	err = nla_parse_nested_deprecated(ntb, maxtype, tla, drbd_connection_statistics_nl_policy, NULL);
1750 	if (err)
1751 		goto out;
1752 
1753 	nla = ntb[DRBD_A_CONNECTION_STATISTICS_CONN_CONGESTED];
1754 	if (nla && s)
1755 		s->conn_congested = nla_get_u8(nla);
1756 
1757 out:
1758 	if (ret_nested_attribute_table && (!err || err == -ENOMSG))
1759 		*ret_nested_attribute_table = ntb;
1760 	else
1761 		kfree(ntb);
1762 	return err;
1763 }
1764 
1765 int connection_statistics_from_attrs(struct connection_statistics *s,
1766 				struct genl_info *info)
1767 {
1768 	return __connection_statistics_from_attrs(s, NULL, info);
1769 }
1770 
1771 int connection_statistics_ntb_from_attrs(
1772 			struct nlattr ***ret_nested_attribute_table,
1773 			struct genl_info *info)
1774 {
1775 	return __connection_statistics_from_attrs(NULL, ret_nested_attribute_table, info);
1776 }
1777 
1778 static int __peer_device_statistics_from_attrs(struct peer_device_statistics *s,
1779 		struct nlattr ***ret_nested_attribute_table,
1780 		struct genl_info *info)
1781 {
1782 	const int maxtype = DRBD_A_PEER_DEVICE_STATISTICS_PEER_DEV_FLAGS;
1783 	struct nlattr *tla = info->attrs[DRBD_NLA_PEER_DEVICE_STATISTICS];
1784 	struct nlattr **ntb;
1785 	struct nlattr *nla;
1786 	int err = 0;
1787 
1788 	if (ret_nested_attribute_table)
1789 		*ret_nested_attribute_table = NULL;
1790 	if (!tla)
1791 		return -ENOMSG;
1792 	ntb = kcalloc(DRBD_A_PEER_DEVICE_STATISTICS_PEER_DEV_FLAGS + 1, sizeof(*ntb), GFP_KERNEL);
1793 	if (!ntb)
1794 		return -ENOMEM;
1795 	err = nla_parse_nested_deprecated(ntb, maxtype, tla, drbd_peer_device_statistics_nl_policy, NULL);
1796 	if (err)
1797 		goto out;
1798 
1799 	nla = ntb[DRBD_A_PEER_DEVICE_STATISTICS_PEER_DEV_RECEIVED];
1800 	if (nla && s)
1801 		s->peer_dev_received = nla_get_u64(nla);
1802 
1803 	nla = ntb[DRBD_A_PEER_DEVICE_STATISTICS_PEER_DEV_SENT];
1804 	if (nla && s)
1805 		s->peer_dev_sent = nla_get_u64(nla);
1806 
1807 	nla = ntb[DRBD_A_PEER_DEVICE_STATISTICS_PEER_DEV_PENDING];
1808 	if (nla && s)
1809 		s->peer_dev_pending = nla_get_u32(nla);
1810 
1811 	nla = ntb[DRBD_A_PEER_DEVICE_STATISTICS_PEER_DEV_UNACKED];
1812 	if (nla && s)
1813 		s->peer_dev_unacked = nla_get_u32(nla);
1814 
1815 	nla = ntb[DRBD_A_PEER_DEVICE_STATISTICS_PEER_DEV_OUT_OF_SYNC];
1816 	if (nla && s)
1817 		s->peer_dev_out_of_sync = nla_get_u64(nla);
1818 
1819 	nla = ntb[DRBD_A_PEER_DEVICE_STATISTICS_PEER_DEV_RESYNC_FAILED];
1820 	if (nla && s)
1821 		s->peer_dev_resync_failed = nla_get_u64(nla);
1822 
1823 	nla = ntb[DRBD_A_PEER_DEVICE_STATISTICS_PEER_DEV_BITMAP_UUID];
1824 	if (nla && s)
1825 		s->peer_dev_bitmap_uuid = nla_get_u64(nla);
1826 
1827 	nla = ntb[DRBD_A_PEER_DEVICE_STATISTICS_PEER_DEV_FLAGS];
1828 	if (nla && s)
1829 		s->peer_dev_flags = nla_get_u32(nla);
1830 
1831 out:
1832 	if (ret_nested_attribute_table && (!err || err == -ENOMSG))
1833 		*ret_nested_attribute_table = ntb;
1834 	else
1835 		kfree(ntb);
1836 	return err;
1837 }
1838 
1839 int peer_device_statistics_from_attrs(struct peer_device_statistics *s,
1840 				struct genl_info *info)
1841 {
1842 	return __peer_device_statistics_from_attrs(s, NULL, info);
1843 }
1844 
1845 int peer_device_statistics_ntb_from_attrs(
1846 			struct nlattr ***ret_nested_attribute_table,
1847 			struct genl_info *info)
1848 {
1849 	return __peer_device_statistics_from_attrs(NULL, ret_nested_attribute_table, info);
1850 }
1851 
1852 int drbd_cfg_reply_to_skb(struct sk_buff *skb, struct drbd_cfg_reply *s)
1853 {
1854 	struct nlattr *tla = nla_nest_start(skb, DRBD_NLA_CFG_REPLY);
1855 
1856 	if (!tla)
1857 		goto nla_put_failure;
1858 
1859 	if (nla_put(skb, DRBD_A_DRBD_CFG_REPLY_INFO_TEXT, min_t(int, 0,
1860 			s->info_text_len + (s->info_text_len < 0)), s->info_text))
1861 		goto nla_put_failure;
1862 
1863 	nla_nest_end(skb, tla);
1864 	return 0;
1865 
1866 nla_put_failure:
1867 	if (tla)
1868 		nla_nest_cancel(skb, tla);
1869 	return -EMSGSIZE;
1870 }
1871 
1872 int drbd_cfg_context_to_skb(struct sk_buff *skb, struct drbd_cfg_context *s)
1873 {
1874 	struct nlattr *tla = nla_nest_start(skb, DRBD_NLA_CFG_CONTEXT);
1875 
1876 	if (!tla)
1877 		goto nla_put_failure;
1878 
1879 	if (nla_put_u32(skb, DRBD_A_DRBD_CFG_CONTEXT_CTX_VOLUME, s->ctx_volume))
1880 		goto nla_put_failure;
1881 	if (nla_put(skb, DRBD_A_DRBD_CFG_CONTEXT_CTX_RESOURCE_NAME, min_t(int, 128,
1882 			s->ctx_resource_name_len + (s->ctx_resource_name_len < 128)), s->ctx_resource_name))
1883 		goto nla_put_failure;
1884 	if (nla_put(skb, DRBD_A_DRBD_CFG_CONTEXT_CTX_MY_ADDR, min_t(int, 128,
1885 			s->ctx_my_addr_len), s->ctx_my_addr))
1886 		goto nla_put_failure;
1887 	if (nla_put(skb, DRBD_A_DRBD_CFG_CONTEXT_CTX_PEER_ADDR, min_t(int, 128,
1888 			s->ctx_peer_addr_len), s->ctx_peer_addr))
1889 		goto nla_put_failure;
1890 
1891 	nla_nest_end(skb, tla);
1892 	return 0;
1893 
1894 nla_put_failure:
1895 	if (tla)
1896 		nla_nest_cancel(skb, tla);
1897 	return -EMSGSIZE;
1898 }
1899 
1900 int disk_conf_to_skb(struct sk_buff *skb, struct disk_conf *s)
1901 {
1902 	struct nlattr *tla = nla_nest_start(skb, DRBD_NLA_DISK_CONF);
1903 
1904 	if (!tla)
1905 		goto nla_put_failure;
1906 
1907 	if (nla_put(skb, DRBD_A_DISK_CONF_BACKING_DEV, min_t(int, 128,
1908 			s->backing_dev_len + (s->backing_dev_len < 128)), s->backing_dev))
1909 		goto nla_put_failure;
1910 	if (nla_put(skb, DRBD_A_DISK_CONF_META_DEV, min_t(int, 128,
1911 			s->meta_dev_len + (s->meta_dev_len < 128)), s->meta_dev))
1912 		goto nla_put_failure;
1913 	if (nla_put_s32(skb, DRBD_A_DISK_CONF_META_DEV_IDX, s->meta_dev_idx))
1914 		goto nla_put_failure;
1915 	if (nla_put_u64_64bit(skb, DRBD_A_DISK_CONF_DISK_SIZE, s->disk_size, 0))
1916 		goto nla_put_failure;
1917 	if (nla_put_u32(skb, DRBD_A_DISK_CONF_MAX_BIO_BVECS, s->max_bio_bvecs))
1918 		goto nla_put_failure;
1919 	if (nla_put_u32(skb, DRBD_A_DISK_CONF_ON_IO_ERROR, s->on_io_error))
1920 		goto nla_put_failure;
1921 	if (nla_put_u32(skb, DRBD_A_DISK_CONF_FENCING, s->fencing))
1922 		goto nla_put_failure;
1923 	if (nla_put_u32(skb, DRBD_A_DISK_CONF_RESYNC_RATE, s->resync_rate))
1924 		goto nla_put_failure;
1925 	if (nla_put_s32(skb, DRBD_A_DISK_CONF_RESYNC_AFTER, s->resync_after))
1926 		goto nla_put_failure;
1927 	if (nla_put_u32(skb, DRBD_A_DISK_CONF_AL_EXTENTS, s->al_extents))
1928 		goto nla_put_failure;
1929 	if (nla_put_u32(skb, DRBD_A_DISK_CONF_C_PLAN_AHEAD, s->c_plan_ahead))
1930 		goto nla_put_failure;
1931 	if (nla_put_u32(skb, DRBD_A_DISK_CONF_C_DELAY_TARGET, s->c_delay_target))
1932 		goto nla_put_failure;
1933 	if (nla_put_u32(skb, DRBD_A_DISK_CONF_C_FILL_TARGET, s->c_fill_target))
1934 		goto nla_put_failure;
1935 	if (nla_put_u32(skb, DRBD_A_DISK_CONF_C_MAX_RATE, s->c_max_rate))
1936 		goto nla_put_failure;
1937 	if (nla_put_u32(skb, DRBD_A_DISK_CONF_C_MIN_RATE, s->c_min_rate))
1938 		goto nla_put_failure;
1939 	if (nla_put_u8(skb, DRBD_A_DISK_CONF_DISK_BARRIER, s->disk_barrier))
1940 		goto nla_put_failure;
1941 	if (nla_put_u8(skb, DRBD_A_DISK_CONF_DISK_FLUSHES, s->disk_flushes))
1942 		goto nla_put_failure;
1943 	if (nla_put_u8(skb, DRBD_A_DISK_CONF_DISK_DRAIN, s->disk_drain))
1944 		goto nla_put_failure;
1945 	if (nla_put_u8(skb, DRBD_A_DISK_CONF_MD_FLUSHES, s->md_flushes))
1946 		goto nla_put_failure;
1947 	if (nla_put_u32(skb, DRBD_A_DISK_CONF_DISK_TIMEOUT, s->disk_timeout))
1948 		goto nla_put_failure;
1949 	if (nla_put_u32(skb, DRBD_A_DISK_CONF_READ_BALANCING, s->read_balancing))
1950 		goto nla_put_failure;
1951 	if (nla_put_u8(skb, DRBD_A_DISK_CONF_AL_UPDATES, s->al_updates))
1952 		goto nla_put_failure;
1953 	if (nla_put_u8(skb, DRBD_A_DISK_CONF_DISCARD_ZEROES_IF_ALIGNED, s->discard_zeroes_if_aligned))
1954 		goto nla_put_failure;
1955 	if (nla_put_u32(skb, DRBD_A_DISK_CONF_RS_DISCARD_GRANULARITY, s->rs_discard_granularity))
1956 		goto nla_put_failure;
1957 	if (nla_put_u8(skb, DRBD_A_DISK_CONF_DISABLE_WRITE_SAME, s->disable_write_same))
1958 		goto nla_put_failure;
1959 
1960 	nla_nest_end(skb, tla);
1961 	return 0;
1962 
1963 nla_put_failure:
1964 	if (tla)
1965 		nla_nest_cancel(skb, tla);
1966 	return -EMSGSIZE;
1967 }
1968 
1969 int res_opts_to_skb(struct sk_buff *skb, struct res_opts *s)
1970 {
1971 	struct nlattr *tla = nla_nest_start(skb, DRBD_NLA_RESOURCE_OPTS);
1972 
1973 	if (!tla)
1974 		goto nla_put_failure;
1975 
1976 	if (nla_put(skb, DRBD_A_RES_OPTS_CPU_MASK, min_t(int, DRBD_CPU_MASK_SIZE,
1977 			s->cpu_mask_len + (s->cpu_mask_len < DRBD_CPU_MASK_SIZE)), s->cpu_mask))
1978 		goto nla_put_failure;
1979 	if (nla_put_u32(skb, DRBD_A_RES_OPTS_ON_NO_DATA, s->on_no_data))
1980 		goto nla_put_failure;
1981 
1982 	nla_nest_end(skb, tla);
1983 	return 0;
1984 
1985 nla_put_failure:
1986 	if (tla)
1987 		nla_nest_cancel(skb, tla);
1988 	return -EMSGSIZE;
1989 }
1990 
1991 int net_conf_to_skb(struct sk_buff *skb, struct net_conf *s)
1992 {
1993 	struct nlattr *tla = nla_nest_start(skb, DRBD_NLA_NET_CONF);
1994 
1995 	if (!tla)
1996 		goto nla_put_failure;
1997 
1998 	if (nla_put(skb, DRBD_A_NET_CONF_SHARED_SECRET, min_t(int, SHARED_SECRET_MAX,
1999 			s->shared_secret_len + (s->shared_secret_len < SHARED_SECRET_MAX)), s->shared_secret))
2000 		goto nla_put_failure;
2001 	if (nla_put(skb, DRBD_A_NET_CONF_CRAM_HMAC_ALG, min_t(int, SHARED_SECRET_MAX,
2002 			s->cram_hmac_alg_len + (s->cram_hmac_alg_len < SHARED_SECRET_MAX)), s->cram_hmac_alg))
2003 		goto nla_put_failure;
2004 	if (nla_put(skb, DRBD_A_NET_CONF_INTEGRITY_ALG, min_t(int, SHARED_SECRET_MAX,
2005 			s->integrity_alg_len + (s->integrity_alg_len < SHARED_SECRET_MAX)), s->integrity_alg))
2006 		goto nla_put_failure;
2007 	if (nla_put(skb, DRBD_A_NET_CONF_VERIFY_ALG, min_t(int, SHARED_SECRET_MAX,
2008 			s->verify_alg_len + (s->verify_alg_len < SHARED_SECRET_MAX)), s->verify_alg))
2009 		goto nla_put_failure;
2010 	if (nla_put(skb, DRBD_A_NET_CONF_CSUMS_ALG, min_t(int, SHARED_SECRET_MAX,
2011 			s->csums_alg_len + (s->csums_alg_len < SHARED_SECRET_MAX)), s->csums_alg))
2012 		goto nla_put_failure;
2013 	if (nla_put_u32(skb, DRBD_A_NET_CONF_WIRE_PROTOCOL, s->wire_protocol))
2014 		goto nla_put_failure;
2015 	if (nla_put_u32(skb, DRBD_A_NET_CONF_CONNECT_INT, s->connect_int))
2016 		goto nla_put_failure;
2017 	if (nla_put_u32(skb, DRBD_A_NET_CONF_TIMEOUT, s->timeout))
2018 		goto nla_put_failure;
2019 	if (nla_put_u32(skb, DRBD_A_NET_CONF_PING_INT, s->ping_int))
2020 		goto nla_put_failure;
2021 	if (nla_put_u32(skb, DRBD_A_NET_CONF_PING_TIMEO, s->ping_timeo))
2022 		goto nla_put_failure;
2023 	if (nla_put_u32(skb, DRBD_A_NET_CONF_SNDBUF_SIZE, s->sndbuf_size))
2024 		goto nla_put_failure;
2025 	if (nla_put_u32(skb, DRBD_A_NET_CONF_RCVBUF_SIZE, s->rcvbuf_size))
2026 		goto nla_put_failure;
2027 	if (nla_put_u32(skb, DRBD_A_NET_CONF_KO_COUNT, s->ko_count))
2028 		goto nla_put_failure;
2029 	if (nla_put_u32(skb, DRBD_A_NET_CONF_MAX_BUFFERS, s->max_buffers))
2030 		goto nla_put_failure;
2031 	if (nla_put_u32(skb, DRBD_A_NET_CONF_MAX_EPOCH_SIZE, s->max_epoch_size))
2032 		goto nla_put_failure;
2033 	if (nla_put_u32(skb, DRBD_A_NET_CONF_UNPLUG_WATERMARK, s->unplug_watermark))
2034 		goto nla_put_failure;
2035 	if (nla_put_u32(skb, DRBD_A_NET_CONF_AFTER_SB_0P, s->after_sb_0p))
2036 		goto nla_put_failure;
2037 	if (nla_put_u32(skb, DRBD_A_NET_CONF_AFTER_SB_1P, s->after_sb_1p))
2038 		goto nla_put_failure;
2039 	if (nla_put_u32(skb, DRBD_A_NET_CONF_AFTER_SB_2P, s->after_sb_2p))
2040 		goto nla_put_failure;
2041 	if (nla_put_u32(skb, DRBD_A_NET_CONF_RR_CONFLICT, s->rr_conflict))
2042 		goto nla_put_failure;
2043 	if (nla_put_u32(skb, DRBD_A_NET_CONF_ON_CONGESTION, s->on_congestion))
2044 		goto nla_put_failure;
2045 	if (nla_put_u32(skb, DRBD_A_NET_CONF_CONG_FILL, s->cong_fill))
2046 		goto nla_put_failure;
2047 	if (nla_put_u32(skb, DRBD_A_NET_CONF_CONG_EXTENTS, s->cong_extents))
2048 		goto nla_put_failure;
2049 	if (nla_put_u8(skb, DRBD_A_NET_CONF_TWO_PRIMARIES, s->two_primaries))
2050 		goto nla_put_failure;
2051 	if (nla_put_u8(skb, DRBD_A_NET_CONF_DISCARD_MY_DATA, s->discard_my_data))
2052 		goto nla_put_failure;
2053 	if (nla_put_u8(skb, DRBD_A_NET_CONF_TCP_CORK, s->tcp_cork))
2054 		goto nla_put_failure;
2055 	if (nla_put_u8(skb, DRBD_A_NET_CONF_ALWAYS_ASBP, s->always_asbp))
2056 		goto nla_put_failure;
2057 	if (nla_put_u8(skb, DRBD_A_NET_CONF_TENTATIVE, s->tentative))
2058 		goto nla_put_failure;
2059 	if (nla_put_u8(skb, DRBD_A_NET_CONF_USE_RLE, s->use_rle))
2060 		goto nla_put_failure;
2061 	if (nla_put_u8(skb, DRBD_A_NET_CONF_CSUMS_AFTER_CRASH_ONLY, s->csums_after_crash_only))
2062 		goto nla_put_failure;
2063 	if (nla_put_u32(skb, DRBD_A_NET_CONF_SOCK_CHECK_TIMEO, s->sock_check_timeo))
2064 		goto nla_put_failure;
2065 
2066 	nla_nest_end(skb, tla);
2067 	return 0;
2068 
2069 nla_put_failure:
2070 	if (tla)
2071 		nla_nest_cancel(skb, tla);
2072 	return -EMSGSIZE;
2073 }
2074 
2075 int set_role_parms_to_skb(struct sk_buff *skb, struct set_role_parms *s)
2076 {
2077 	struct nlattr *tla = nla_nest_start(skb, DRBD_NLA_SET_ROLE_PARMS);
2078 
2079 	if (!tla)
2080 		goto nla_put_failure;
2081 
2082 	if (nla_put_u8(skb, DRBD_A_SET_ROLE_PARMS_ASSUME_UPTODATE, s->assume_uptodate))
2083 		goto nla_put_failure;
2084 
2085 	nla_nest_end(skb, tla);
2086 	return 0;
2087 
2088 nla_put_failure:
2089 	if (tla)
2090 		nla_nest_cancel(skb, tla);
2091 	return -EMSGSIZE;
2092 }
2093 
2094 int resize_parms_to_skb(struct sk_buff *skb, struct resize_parms *s)
2095 {
2096 	struct nlattr *tla = nla_nest_start(skb, DRBD_NLA_RESIZE_PARMS);
2097 
2098 	if (!tla)
2099 		goto nla_put_failure;
2100 
2101 	if (nla_put_u64_64bit(skb, DRBD_A_RESIZE_PARMS_RESIZE_SIZE, s->resize_size, 0))
2102 		goto nla_put_failure;
2103 	if (nla_put_u8(skb, DRBD_A_RESIZE_PARMS_RESIZE_FORCE, s->resize_force))
2104 		goto nla_put_failure;
2105 	if (nla_put_u8(skb, DRBD_A_RESIZE_PARMS_NO_RESYNC, s->no_resync))
2106 		goto nla_put_failure;
2107 	if (nla_put_u32(skb, DRBD_A_RESIZE_PARMS_AL_STRIPES, s->al_stripes))
2108 		goto nla_put_failure;
2109 	if (nla_put_u32(skb, DRBD_A_RESIZE_PARMS_AL_STRIPE_SIZE, s->al_stripe_size))
2110 		goto nla_put_failure;
2111 
2112 	nla_nest_end(skb, tla);
2113 	return 0;
2114 
2115 nla_put_failure:
2116 	if (tla)
2117 		nla_nest_cancel(skb, tla);
2118 	return -EMSGSIZE;
2119 }
2120 
2121 int state_info_to_skb(struct sk_buff *skb, struct state_info *s)
2122 {
2123 	struct nlattr *tla = nla_nest_start(skb, DRBD_NLA_STATE_INFO);
2124 
2125 	if (!tla)
2126 		goto nla_put_failure;
2127 
2128 	if (nla_put_u32(skb, DRBD_A_STATE_INFO_SIB_REASON, s->sib_reason))
2129 		goto nla_put_failure;
2130 	if (nla_put_u32(skb, DRBD_A_STATE_INFO_CURRENT_STATE, s->current_state))
2131 		goto nla_put_failure;
2132 	if (nla_put_u64_64bit(skb, DRBD_A_STATE_INFO_CAPACITY, s->capacity, 0))
2133 		goto nla_put_failure;
2134 	if (nla_put_u64_64bit(skb, DRBD_A_STATE_INFO_ED_UUID, s->ed_uuid, 0))
2135 		goto nla_put_failure;
2136 	if (nla_put_u32(skb, DRBD_A_STATE_INFO_PREV_STATE, s->prev_state))
2137 		goto nla_put_failure;
2138 	if (nla_put_u32(skb, DRBD_A_STATE_INFO_NEW_STATE, s->new_state))
2139 		goto nla_put_failure;
2140 	if (nla_put(skb, DRBD_A_STATE_INFO_UUIDS, min_t(int, DRBD_NL_UUIDS_SIZE,
2141 			s->uuids_len), s->uuids))
2142 		goto nla_put_failure;
2143 	if (nla_put_u32(skb, DRBD_A_STATE_INFO_DISK_FLAGS, s->disk_flags))
2144 		goto nla_put_failure;
2145 	if (nla_put_u64_64bit(skb, DRBD_A_STATE_INFO_BITS_TOTAL, s->bits_total, 0))
2146 		goto nla_put_failure;
2147 	if (nla_put_u64_64bit(skb, DRBD_A_STATE_INFO_BITS_OOS, s->bits_oos, 0))
2148 		goto nla_put_failure;
2149 	if (nla_put_u64_64bit(skb, DRBD_A_STATE_INFO_BITS_RS_TOTAL, s->bits_rs_total, 0))
2150 		goto nla_put_failure;
2151 	if (nla_put_u64_64bit(skb, DRBD_A_STATE_INFO_BITS_RS_FAILED, s->bits_rs_failed, 0))
2152 		goto nla_put_failure;
2153 	if (nla_put(skb, DRBD_A_STATE_INFO_HELPER, min_t(int, 32,
2154 			s->helper_len + (s->helper_len < 32)), s->helper))
2155 		goto nla_put_failure;
2156 	if (nla_put_u32(skb, DRBD_A_STATE_INFO_HELPER_EXIT_CODE, s->helper_exit_code))
2157 		goto nla_put_failure;
2158 	if (nla_put_u64_64bit(skb, DRBD_A_STATE_INFO_SEND_CNT, s->send_cnt, 0))
2159 		goto nla_put_failure;
2160 	if (nla_put_u64_64bit(skb, DRBD_A_STATE_INFO_RECV_CNT, s->recv_cnt, 0))
2161 		goto nla_put_failure;
2162 	if (nla_put_u64_64bit(skb, DRBD_A_STATE_INFO_READ_CNT, s->read_cnt, 0))
2163 		goto nla_put_failure;
2164 	if (nla_put_u64_64bit(skb, DRBD_A_STATE_INFO_WRIT_CNT, s->writ_cnt, 0))
2165 		goto nla_put_failure;
2166 	if (nla_put_u64_64bit(skb, DRBD_A_STATE_INFO_AL_WRIT_CNT, s->al_writ_cnt, 0))
2167 		goto nla_put_failure;
2168 	if (nla_put_u64_64bit(skb, DRBD_A_STATE_INFO_BM_WRIT_CNT, s->bm_writ_cnt, 0))
2169 		goto nla_put_failure;
2170 	if (nla_put_u32(skb, DRBD_A_STATE_INFO_AP_BIO_CNT, s->ap_bio_cnt))
2171 		goto nla_put_failure;
2172 	if (nla_put_u32(skb, DRBD_A_STATE_INFO_AP_PENDING_CNT, s->ap_pending_cnt))
2173 		goto nla_put_failure;
2174 	if (nla_put_u32(skb, DRBD_A_STATE_INFO_RS_PENDING_CNT, s->rs_pending_cnt))
2175 		goto nla_put_failure;
2176 
2177 	nla_nest_end(skb, tla);
2178 	return 0;
2179 
2180 nla_put_failure:
2181 	if (tla)
2182 		nla_nest_cancel(skb, tla);
2183 	return -EMSGSIZE;
2184 }
2185 
2186 int start_ov_parms_to_skb(struct sk_buff *skb, struct start_ov_parms *s)
2187 {
2188 	struct nlattr *tla = nla_nest_start(skb, DRBD_NLA_START_OV_PARMS);
2189 
2190 	if (!tla)
2191 		goto nla_put_failure;
2192 
2193 	if (nla_put_u64_64bit(skb, DRBD_A_START_OV_PARMS_OV_START_SECTOR, s->ov_start_sector, 0))
2194 		goto nla_put_failure;
2195 	if (nla_put_u64_64bit(skb, DRBD_A_START_OV_PARMS_OV_STOP_SECTOR, s->ov_stop_sector, 0))
2196 		goto nla_put_failure;
2197 
2198 	nla_nest_end(skb, tla);
2199 	return 0;
2200 
2201 nla_put_failure:
2202 	if (tla)
2203 		nla_nest_cancel(skb, tla);
2204 	return -EMSGSIZE;
2205 }
2206 
2207 int new_c_uuid_parms_to_skb(struct sk_buff *skb, struct new_c_uuid_parms *s)
2208 {
2209 	struct nlattr *tla = nla_nest_start(skb, DRBD_NLA_NEW_C_UUID_PARMS);
2210 
2211 	if (!tla)
2212 		goto nla_put_failure;
2213 
2214 	if (nla_put_u8(skb, DRBD_A_NEW_C_UUID_PARMS_CLEAR_BM, s->clear_bm))
2215 		goto nla_put_failure;
2216 
2217 	nla_nest_end(skb, tla);
2218 	return 0;
2219 
2220 nla_put_failure:
2221 	if (tla)
2222 		nla_nest_cancel(skb, tla);
2223 	return -EMSGSIZE;
2224 }
2225 
2226 int timeout_parms_to_skb(struct sk_buff *skb, struct timeout_parms *s)
2227 {
2228 	struct nlattr *tla = nla_nest_start(skb, DRBD_NLA_TIMEOUT_PARMS);
2229 
2230 	if (!tla)
2231 		goto nla_put_failure;
2232 
2233 	if (nla_put_u32(skb, DRBD_A_TIMEOUT_PARMS_TIMEOUT_TYPE, s->timeout_type))
2234 		goto nla_put_failure;
2235 
2236 	nla_nest_end(skb, tla);
2237 	return 0;
2238 
2239 nla_put_failure:
2240 	if (tla)
2241 		nla_nest_cancel(skb, tla);
2242 	return -EMSGSIZE;
2243 }
2244 
2245 int disconnect_parms_to_skb(struct sk_buff *skb, struct disconnect_parms *s)
2246 {
2247 	struct nlattr *tla = nla_nest_start(skb, DRBD_NLA_DISCONNECT_PARMS);
2248 
2249 	if (!tla)
2250 		goto nla_put_failure;
2251 
2252 	if (nla_put_u8(skb, DRBD_A_DISCONNECT_PARMS_FORCE_DISCONNECT, s->force_disconnect))
2253 		goto nla_put_failure;
2254 
2255 	nla_nest_end(skb, tla);
2256 	return 0;
2257 
2258 nla_put_failure:
2259 	if (tla)
2260 		nla_nest_cancel(skb, tla);
2261 	return -EMSGSIZE;
2262 }
2263 
2264 int detach_parms_to_skb(struct sk_buff *skb, struct detach_parms *s)
2265 {
2266 	struct nlattr *tla = nla_nest_start(skb, DRBD_NLA_DETACH_PARMS);
2267 
2268 	if (!tla)
2269 		goto nla_put_failure;
2270 
2271 	if (nla_put_u8(skb, DRBD_A_DETACH_PARMS_FORCE_DETACH, s->force_detach))
2272 		goto nla_put_failure;
2273 
2274 	nla_nest_end(skb, tla);
2275 	return 0;
2276 
2277 nla_put_failure:
2278 	if (tla)
2279 		nla_nest_cancel(skb, tla);
2280 	return -EMSGSIZE;
2281 }
2282 
2283 int resource_info_to_skb(struct sk_buff *skb, struct resource_info *s)
2284 {
2285 	struct nlattr *tla = nla_nest_start(skb, DRBD_NLA_RESOURCE_INFO);
2286 
2287 	if (!tla)
2288 		goto nla_put_failure;
2289 
2290 	if (nla_put_u32(skb, DRBD_A_RESOURCE_INFO_RES_ROLE, s->res_role))
2291 		goto nla_put_failure;
2292 	if (nla_put_u8(skb, DRBD_A_RESOURCE_INFO_RES_SUSP, s->res_susp))
2293 		goto nla_put_failure;
2294 	if (nla_put_u8(skb, DRBD_A_RESOURCE_INFO_RES_SUSP_NOD, s->res_susp_nod))
2295 		goto nla_put_failure;
2296 	if (nla_put_u8(skb, DRBD_A_RESOURCE_INFO_RES_SUSP_FEN, s->res_susp_fen))
2297 		goto nla_put_failure;
2298 
2299 	nla_nest_end(skb, tla);
2300 	return 0;
2301 
2302 nla_put_failure:
2303 	if (tla)
2304 		nla_nest_cancel(skb, tla);
2305 	return -EMSGSIZE;
2306 }
2307 
2308 int device_info_to_skb(struct sk_buff *skb, struct device_info *s)
2309 {
2310 	struct nlattr *tla = nla_nest_start(skb, DRBD_NLA_DEVICE_INFO);
2311 
2312 	if (!tla)
2313 		goto nla_put_failure;
2314 
2315 	if (nla_put_u32(skb, DRBD_A_DEVICE_INFO_DEV_DISK_STATE, s->dev_disk_state))
2316 		goto nla_put_failure;
2317 
2318 	nla_nest_end(skb, tla);
2319 	return 0;
2320 
2321 nla_put_failure:
2322 	if (tla)
2323 		nla_nest_cancel(skb, tla);
2324 	return -EMSGSIZE;
2325 }
2326 
2327 int connection_info_to_skb(struct sk_buff *skb, struct connection_info *s)
2328 {
2329 	struct nlattr *tla = nla_nest_start(skb, DRBD_NLA_CONNECTION_INFO);
2330 
2331 	if (!tla)
2332 		goto nla_put_failure;
2333 
2334 	if (nla_put_u32(skb, DRBD_A_CONNECTION_INFO_CONN_CONNECTION_STATE, s->conn_connection_state))
2335 		goto nla_put_failure;
2336 	if (nla_put_u32(skb, DRBD_A_CONNECTION_INFO_CONN_ROLE, s->conn_role))
2337 		goto nla_put_failure;
2338 
2339 	nla_nest_end(skb, tla);
2340 	return 0;
2341 
2342 nla_put_failure:
2343 	if (tla)
2344 		nla_nest_cancel(skb, tla);
2345 	return -EMSGSIZE;
2346 }
2347 
2348 int peer_device_info_to_skb(struct sk_buff *skb, struct peer_device_info *s)
2349 {
2350 	struct nlattr *tla = nla_nest_start(skb, DRBD_NLA_PEER_DEVICE_INFO);
2351 
2352 	if (!tla)
2353 		goto nla_put_failure;
2354 
2355 	if (nla_put_u32(skb, DRBD_A_PEER_DEVICE_INFO_PEER_REPL_STATE, s->peer_repl_state))
2356 		goto nla_put_failure;
2357 	if (nla_put_u32(skb, DRBD_A_PEER_DEVICE_INFO_PEER_DISK_STATE, s->peer_disk_state))
2358 		goto nla_put_failure;
2359 	if (nla_put_u32(skb, DRBD_A_PEER_DEVICE_INFO_PEER_RESYNC_SUSP_USER, s->peer_resync_susp_user))
2360 		goto nla_put_failure;
2361 	if (nla_put_u32(skb, DRBD_A_PEER_DEVICE_INFO_PEER_RESYNC_SUSP_PEER, s->peer_resync_susp_peer))
2362 		goto nla_put_failure;
2363 	if (nla_put_u32(skb, DRBD_A_PEER_DEVICE_INFO_PEER_RESYNC_SUSP_DEPENDENCY, s->peer_resync_susp_dependency))
2364 		goto nla_put_failure;
2365 
2366 	nla_nest_end(skb, tla);
2367 	return 0;
2368 
2369 nla_put_failure:
2370 	if (tla)
2371 		nla_nest_cancel(skb, tla);
2372 	return -EMSGSIZE;
2373 }
2374 
2375 int resource_statistics_to_skb(struct sk_buff *skb, struct resource_statistics *s)
2376 {
2377 	struct nlattr *tla = nla_nest_start(skb, DRBD_NLA_RESOURCE_STATISTICS);
2378 
2379 	if (!tla)
2380 		goto nla_put_failure;
2381 
2382 	if (nla_put_u32(skb, DRBD_A_RESOURCE_STATISTICS_RES_STAT_WRITE_ORDERING, s->res_stat_write_ordering))
2383 		goto nla_put_failure;
2384 
2385 	nla_nest_end(skb, tla);
2386 	return 0;
2387 
2388 nla_put_failure:
2389 	if (tla)
2390 		nla_nest_cancel(skb, tla);
2391 	return -EMSGSIZE;
2392 }
2393 
2394 int device_statistics_to_skb(struct sk_buff *skb, struct device_statistics *s)
2395 {
2396 	struct nlattr *tla = nla_nest_start(skb, DRBD_NLA_DEVICE_STATISTICS);
2397 
2398 	if (!tla)
2399 		goto nla_put_failure;
2400 
2401 	if (nla_put_u64_64bit(skb, DRBD_A_DEVICE_STATISTICS_DEV_SIZE, s->dev_size, 0))
2402 		goto nla_put_failure;
2403 	if (nla_put_u64_64bit(skb, DRBD_A_DEVICE_STATISTICS_DEV_READ, s->dev_read, 0))
2404 		goto nla_put_failure;
2405 	if (nla_put_u64_64bit(skb, DRBD_A_DEVICE_STATISTICS_DEV_WRITE, s->dev_write, 0))
2406 		goto nla_put_failure;
2407 	if (nla_put_u64_64bit(skb, DRBD_A_DEVICE_STATISTICS_DEV_AL_WRITES, s->dev_al_writes, 0))
2408 		goto nla_put_failure;
2409 	if (nla_put_u64_64bit(skb, DRBD_A_DEVICE_STATISTICS_DEV_BM_WRITES, s->dev_bm_writes, 0))
2410 		goto nla_put_failure;
2411 	if (nla_put_u32(skb, DRBD_A_DEVICE_STATISTICS_DEV_UPPER_PENDING, s->dev_upper_pending))
2412 		goto nla_put_failure;
2413 	if (nla_put_u32(skb, DRBD_A_DEVICE_STATISTICS_DEV_LOWER_PENDING, s->dev_lower_pending))
2414 		goto nla_put_failure;
2415 	if (nla_put_u8(skb, DRBD_A_DEVICE_STATISTICS_DEV_UPPER_BLOCKED, s->dev_upper_blocked))
2416 		goto nla_put_failure;
2417 	if (nla_put_u8(skb, DRBD_A_DEVICE_STATISTICS_DEV_LOWER_BLOCKED, s->dev_lower_blocked))
2418 		goto nla_put_failure;
2419 	if (nla_put_u8(skb, DRBD_A_DEVICE_STATISTICS_DEV_AL_SUSPENDED, s->dev_al_suspended))
2420 		goto nla_put_failure;
2421 	if (nla_put_u64_64bit(skb, DRBD_A_DEVICE_STATISTICS_DEV_EXPOSED_DATA_UUID, s->dev_exposed_data_uuid, 0))
2422 		goto nla_put_failure;
2423 	if (nla_put_u64_64bit(skb, DRBD_A_DEVICE_STATISTICS_DEV_CURRENT_UUID, s->dev_current_uuid, 0))
2424 		goto nla_put_failure;
2425 	if (nla_put_u32(skb, DRBD_A_DEVICE_STATISTICS_DEV_DISK_FLAGS, s->dev_disk_flags))
2426 		goto nla_put_failure;
2427 	if (nla_put(skb, DRBD_A_DEVICE_STATISTICS_HISTORY_UUIDS, min_t(int, DRBD_NL_HISTORY_UUIDS_SIZE,
2428 			s->history_uuids_len), s->history_uuids))
2429 		goto nla_put_failure;
2430 
2431 	nla_nest_end(skb, tla);
2432 	return 0;
2433 
2434 nla_put_failure:
2435 	if (tla)
2436 		nla_nest_cancel(skb, tla);
2437 	return -EMSGSIZE;
2438 }
2439 
2440 int connection_statistics_to_skb(struct sk_buff *skb, struct connection_statistics *s)
2441 {
2442 	struct nlattr *tla = nla_nest_start(skb, DRBD_NLA_CONNECTION_STATISTICS);
2443 
2444 	if (!tla)
2445 		goto nla_put_failure;
2446 
2447 	if (nla_put_u8(skb, DRBD_A_CONNECTION_STATISTICS_CONN_CONGESTED, s->conn_congested))
2448 		goto nla_put_failure;
2449 
2450 	nla_nest_end(skb, tla);
2451 	return 0;
2452 
2453 nla_put_failure:
2454 	if (tla)
2455 		nla_nest_cancel(skb, tla);
2456 	return -EMSGSIZE;
2457 }
2458 
2459 int peer_device_statistics_to_skb(struct sk_buff *skb, struct peer_device_statistics *s)
2460 {
2461 	struct nlattr *tla = nla_nest_start(skb, DRBD_NLA_PEER_DEVICE_STATISTICS);
2462 
2463 	if (!tla)
2464 		goto nla_put_failure;
2465 
2466 	if (nla_put_u64_64bit(skb, DRBD_A_PEER_DEVICE_STATISTICS_PEER_DEV_RECEIVED, s->peer_dev_received, 0))
2467 		goto nla_put_failure;
2468 	if (nla_put_u64_64bit(skb, DRBD_A_PEER_DEVICE_STATISTICS_PEER_DEV_SENT, s->peer_dev_sent, 0))
2469 		goto nla_put_failure;
2470 	if (nla_put_u32(skb, DRBD_A_PEER_DEVICE_STATISTICS_PEER_DEV_PENDING, s->peer_dev_pending))
2471 		goto nla_put_failure;
2472 	if (nla_put_u32(skb, DRBD_A_PEER_DEVICE_STATISTICS_PEER_DEV_UNACKED, s->peer_dev_unacked))
2473 		goto nla_put_failure;
2474 	if (nla_put_u64_64bit(skb, DRBD_A_PEER_DEVICE_STATISTICS_PEER_DEV_OUT_OF_SYNC, s->peer_dev_out_of_sync, 0))
2475 		goto nla_put_failure;
2476 	if (nla_put_u64_64bit(skb, DRBD_A_PEER_DEVICE_STATISTICS_PEER_DEV_RESYNC_FAILED, s->peer_dev_resync_failed, 0))
2477 		goto nla_put_failure;
2478 	if (nla_put_u64_64bit(skb, DRBD_A_PEER_DEVICE_STATISTICS_PEER_DEV_BITMAP_UUID, s->peer_dev_bitmap_uuid, 0))
2479 		goto nla_put_failure;
2480 	if (nla_put_u32(skb, DRBD_A_PEER_DEVICE_STATISTICS_PEER_DEV_FLAGS, s->peer_dev_flags))
2481 		goto nla_put_failure;
2482 
2483 	nla_nest_end(skb, tla);
2484 	return 0;
2485 
2486 nla_put_failure:
2487 	if (tla)
2488 		nla_nest_cancel(skb, tla);
2489 	return -EMSGSIZE;
2490 }
2491 
2492 int drbd_notification_header_to_skb(struct sk_buff *skb, struct drbd_notification_header *s)
2493 {
2494 	struct nlattr *tla = nla_nest_start(skb, DRBD_NLA_NOTIFICATION_HEADER);
2495 
2496 	if (!tla)
2497 		goto nla_put_failure;
2498 
2499 	if (nla_put_u32(skb, DRBD_A_DRBD_NOTIFICATION_HEADER_NH_TYPE, s->nh_type))
2500 		goto nla_put_failure;
2501 
2502 	nla_nest_end(skb, tla);
2503 	return 0;
2504 
2505 nla_put_failure:
2506 	if (tla)
2507 		nla_nest_cancel(skb, tla);
2508 	return -EMSGSIZE;
2509 }
2510 
2511 int drbd_helper_info_to_skb(struct sk_buff *skb, struct drbd_helper_info *s)
2512 {
2513 	struct nlattr *tla = nla_nest_start(skb, DRBD_NLA_HELPER);
2514 
2515 	if (!tla)
2516 		goto nla_put_failure;
2517 
2518 	if (nla_put(skb, DRBD_A_DRBD_HELPER_INFO_HELPER_NAME, min_t(int, 32,
2519 			s->helper_name_len + (s->helper_name_len < 32)), s->helper_name))
2520 		goto nla_put_failure;
2521 	if (nla_put_u32(skb, DRBD_A_DRBD_HELPER_INFO_HELPER_STATUS, s->helper_status))
2522 		goto nla_put_failure;
2523 
2524 	nla_nest_end(skb, tla);
2525 	return 0;
2526 
2527 nla_put_failure:
2528 	if (tla)
2529 		nla_nest_cancel(skb, tla);
2530 	return -EMSGSIZE;
2531 }
2532 
2533 void set_disk_conf_defaults(struct disk_conf *x)
2534 {
2535 	x->on_io_error = DRBD_ON_IO_ERROR_DEF;
2536 	x->fencing = DRBD_FENCING_DEF;
2537 	x->resync_rate = DRBD_RESYNC_RATE_DEF;
2538 	x->resync_after = DRBD_MINOR_NUMBER_DEF;
2539 	x->al_extents = DRBD_AL_EXTENTS_DEF;
2540 	x->c_plan_ahead = DRBD_C_PLAN_AHEAD_DEF;
2541 	x->c_delay_target = DRBD_C_DELAY_TARGET_DEF;
2542 	x->c_fill_target = DRBD_C_FILL_TARGET_DEF;
2543 	x->c_max_rate = DRBD_C_MAX_RATE_DEF;
2544 	x->c_min_rate = DRBD_C_MIN_RATE_DEF;
2545 	x->disk_barrier = DRBD_DISK_BARRIER_DEF;
2546 	x->disk_flushes = DRBD_DISK_FLUSHES_DEF;
2547 	x->disk_drain = DRBD_DISK_DRAIN_DEF;
2548 	x->md_flushes = DRBD_MD_FLUSHES_DEF;
2549 	x->disk_timeout = DRBD_DISK_TIMEOUT_DEF;
2550 	x->read_balancing = DRBD_READ_BALANCING_DEF;
2551 	x->al_updates = DRBD_AL_UPDATES_DEF;
2552 	x->discard_zeroes_if_aligned = DRBD_DISCARD_ZEROES_IF_ALIGNED_DEF;
2553 	x->rs_discard_granularity = DRBD_RS_DISCARD_GRANULARITY_DEF;
2554 	x->disable_write_same = DRBD_DISABLE_WRITE_SAME_DEF;
2555 }
2556 
2557 void set_res_opts_defaults(struct res_opts *x)
2558 {
2559 	memset(x->cpu_mask, 0, sizeof(x->cpu_mask));
2560 	x->cpu_mask_len = 0;
2561 	x->on_no_data = DRBD_ON_NO_DATA_DEF;
2562 }
2563 
2564 void set_net_conf_defaults(struct net_conf *x)
2565 {
2566 	memset(x->shared_secret, 0, sizeof(x->shared_secret));
2567 	x->shared_secret_len = 0;
2568 	memset(x->cram_hmac_alg, 0, sizeof(x->cram_hmac_alg));
2569 	x->cram_hmac_alg_len = 0;
2570 	memset(x->integrity_alg, 0, sizeof(x->integrity_alg));
2571 	x->integrity_alg_len = 0;
2572 	memset(x->verify_alg, 0, sizeof(x->verify_alg));
2573 	x->verify_alg_len = 0;
2574 	memset(x->csums_alg, 0, sizeof(x->csums_alg));
2575 	x->csums_alg_len = 0;
2576 	x->wire_protocol = DRBD_PROTOCOL_DEF;
2577 	x->connect_int = DRBD_CONNECT_INT_DEF;
2578 	x->timeout = DRBD_TIMEOUT_DEF;
2579 	x->ping_int = DRBD_PING_INT_DEF;
2580 	x->ping_timeo = DRBD_PING_TIMEO_DEF;
2581 	x->sndbuf_size = DRBD_SNDBUF_SIZE_DEF;
2582 	x->rcvbuf_size = DRBD_RCVBUF_SIZE_DEF;
2583 	x->ko_count = DRBD_KO_COUNT_DEF;
2584 	x->max_buffers = DRBD_MAX_BUFFERS_DEF;
2585 	x->max_epoch_size = DRBD_MAX_EPOCH_SIZE_DEF;
2586 	x->unplug_watermark = DRBD_UNPLUG_WATERMARK_DEF;
2587 	x->after_sb_0p = DRBD_AFTER_SB_0P_DEF;
2588 	x->after_sb_1p = DRBD_AFTER_SB_1P_DEF;
2589 	x->after_sb_2p = DRBD_AFTER_SB_2P_DEF;
2590 	x->rr_conflict = DRBD_RR_CONFLICT_DEF;
2591 	x->on_congestion = DRBD_ON_CONGESTION_DEF;
2592 	x->cong_fill = DRBD_CONG_FILL_DEF;
2593 	x->cong_extents = DRBD_CONG_EXTENTS_DEF;
2594 	x->two_primaries = DRBD_ALLOW_TWO_PRIMARIES_DEF;
2595 	x->tcp_cork = DRBD_TCP_CORK_DEF;
2596 	x->always_asbp = DRBD_ALWAYS_ASBP_DEF;
2597 	x->use_rle = DRBD_USE_RLE_DEF;
2598 	x->csums_after_crash_only = DRBD_CSUMS_AFTER_CRASH_ONLY_DEF;
2599 	x->sock_check_timeo = DRBD_SOCKET_CHECK_TIMEO_DEF;
2600 }
2601 
2602 void set_resize_parms_defaults(struct resize_parms *x)
2603 {
2604 	x->al_stripes = DRBD_AL_STRIPES_DEF;
2605 	x->al_stripe_size = DRBD_AL_STRIPE_SIZE_DEF;
2606 }
2607