Print this page
usr/src/cmd/dlmgmtd/dlmgmt_door.c
| Split |
Close |
| Expand all |
| Collapse all |
--- old/usr/src/lib/libdladm/common/libdlmgmt.c
+++ new/usr/src/lib/libdladm/common/libdlmgmt.c
1 1 /*
2 2 * CDDL HEADER START
3 3 *
4 4 * The contents of this file are subject to the terms of the
5 5 * Common Development and Distribution License (the "License").
6 6 * You may not use this file except in compliance with the License.
7 7 *
8 8 * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE
9 9 * or http://www.opensolaris.org/os/licensing.
10 10 * See the License for the specific language governing permissions
11 11 * and limitations under the License.
12 12 *
13 13 * When distributing Covered Code, include this CDDL HEADER in each
|
↓ open down ↓ |
13 lines elided |
↑ open up ↑ |
14 14 * file and include the License file at usr/src/OPENSOLARIS.LICENSE.
15 15 * If applicable, add the following below this CDDL HEADER, with the
16 16 * fields enclosed by brackets "[]" replaced with your own identifying
17 17 * information: Portions Copyright [yyyy] [name of copyright owner]
18 18 *
19 19 * CDDL HEADER END
20 20 */
21 21 /*
22 22 * Copyright (c) 2005, 2010, Oracle and/or its affiliates. All rights reserved.
23 23 * Copyright 2016 Joyent, Inc.
24 + * Copyright 2023 Oxide Computer Company
24 25 */
25 26
26 27 #include <door.h>
27 28 #include <errno.h>
28 29 #include <assert.h>
29 30 #include <stdio.h>
30 31 #include <stdlib.h>
31 32 #include <unistd.h>
32 33 #include <string.h>
33 34 #include <strings.h>
34 35 #include <zone.h>
35 36 #include <sys/types.h>
36 37 #include <sys/stat.h>
37 38 #include <sys/aggr.h>
38 39 #include <sys/mman.h>
39 40 #include <fcntl.h>
40 41 #include <libdladm.h>
41 42 #include <libdladm_impl.h>
42 43 #include <libdllink.h>
43 44 #include <libdlmgmt.h>
44 45
45 46 /*
46 47 * Table of data type sizes indexed by dladm_datatype_t.
47 48 */
48 49 static size_t dladm_datatype_size[] = {
49 50 0, /* DLADM_TYPE_STR, use strnlen() */
50 51 sizeof (boolean_t), /* DLADM_TYPE_BOOLEAN */
51 52 sizeof (uint64_t) /* DLADM_TYPE_UINT64 */
52 53 };
53 54
54 55 static dladm_status_t
55 56 dladm_door_call(dladm_handle_t handle, void *arg, size_t asize, void *rbuf,
56 57 size_t *rsizep)
57 58 {
58 59 door_arg_t darg;
59 60 int door_fd;
60 61 dladm_status_t status;
61 62 boolean_t reopen = B_FALSE;
62 63
63 64 darg.data_ptr = arg;
64 65 darg.data_size = asize;
65 66 darg.desc_ptr = NULL;
66 67 darg.desc_num = 0;
67 68 darg.rbuf = rbuf;
68 69 darg.rsize = *rsizep;
69 70
70 71 reopen:
71 72 /* The door descriptor is opened if it isn't already */
72 73 if ((status = dladm_door_fd(handle, &door_fd)) != DLADM_STATUS_OK)
73 74 return (status);
74 75 if (door_call(door_fd, &darg) == -1) {
75 76 /*
76 77 * Stale door descriptor is possible if dlmgmtd was re-started
77 78 * since last door_fd open so try re-opening door file.
78 79 */
79 80 if (!reopen && errno == EBADF) {
80 81 (void) close(handle->door_fd);
81 82 handle->door_fd = -1;
82 83 reopen = B_TRUE;
83 84 goto reopen;
84 85 }
85 86 status = dladm_errno2status(errno);
86 87 }
87 88 if (status != DLADM_STATUS_OK)
88 89 return (status);
89 90
90 91 if (darg.rbuf != rbuf) {
91 92 /*
92 93 * The size of the input rbuf is not big enough so that
93 94 * the door allocate the rbuf itself. In this case, return
94 95 * the required size to the caller.
95 96 */
96 97 (void) munmap(darg.rbuf, darg.rsize);
97 98 *rsizep = darg.rsize;
98 99 return (DLADM_STATUS_TOOSMALL);
99 100 } else if (darg.rsize != *rsizep) {
100 101 return (DLADM_STATUS_FAILED);
101 102 }
102 103
103 104 return (dladm_errno2status(((dlmgmt_retval_t *)rbuf)->lr_err));
104 105 }
105 106
106 107 /*
107 108 * Allocate a new linkid with the given name. Return the new linkid.
108 109 */
109 110 dladm_status_t
110 111 dladm_create_datalink_id(dladm_handle_t handle, const char *link,
111 112 datalink_class_t class, uint32_t media, uint32_t flags,
112 113 datalink_id_t *linkidp)
113 114 {
114 115 dlmgmt_door_createid_t createid;
115 116 dlmgmt_createid_retval_t retval;
|
↓ open down ↓ |
82 lines elided |
↑ open up ↑ |
116 117 uint32_t dlmgmt_flags;
117 118 dladm_status_t status;
118 119 size_t sz = sizeof (retval);
119 120
120 121 if (link == NULL || class == DATALINK_CLASS_ALL ||
121 122 !(flags & (DLADM_OPT_ACTIVE | DLADM_OPT_PERSIST)) ||
122 123 linkidp == NULL) {
123 124 return (DLADM_STATUS_BADARG);
124 125 }
125 126
127 + if (getzoneid() != GLOBAL_ZONEID) {
128 + /*
129 + * If we're creating this link in a non-global zone, then do
130 + * not allow it to be persistent, and flag it as transient so
131 + * that it will be automatically cleaned up on zone shutdown,
132 + * rather than being moved to the GZ.
133 + */
134 + if (flags & DLADM_OPT_PERSIST)
135 + return (DLADM_STATUS_TEMPONLY);
136 + flags |= DLADM_OPT_TRANSIENT;
137 + }
138 +
126 139 dlmgmt_flags = (flags & DLADM_OPT_ACTIVE) ? DLMGMT_ACTIVE : 0;
127 140 dlmgmt_flags |= (flags & DLADM_OPT_PERSIST) ? DLMGMT_PERSIST : 0;
128 141 dlmgmt_flags |= (flags & DLADM_OPT_TRANSIENT) ? DLMGMT_TRANSIENT : 0;
129 142
130 143 (void) strlcpy(createid.ld_link, link, MAXLINKNAMELEN);
131 144 createid.ld_class = class;
132 145 createid.ld_media = media;
133 146 createid.ld_flags = dlmgmt_flags;
134 147 createid.ld_cmd = DLMGMT_CMD_CREATE_LINKID;
135 148 createid.ld_prefix = (flags & DLADM_OPT_PREFIX);
136 149
137 150 if ((status = dladm_door_call(handle, &createid, sizeof (createid),
138 151 &retval, &sz)) == DLADM_STATUS_OK) {
139 152 *linkidp = retval.lr_linkid;
140 153 }
141 154 return (status);
142 155 }
143 156
144 157 /*
145 158 * Destroy the given link ID.
146 159 */
147 160 dladm_status_t
148 161 dladm_destroy_datalink_id(dladm_handle_t handle, datalink_id_t linkid,
149 162 uint32_t flags)
150 163 {
151 164 dlmgmt_door_destroyid_t destroyid;
152 165 dlmgmt_destroyid_retval_t retval;
153 166 uint32_t dlmgmt_flags;
154 167 size_t sz = sizeof (retval);
155 168
156 169 dlmgmt_flags = (flags & DLADM_OPT_ACTIVE) ? DLMGMT_ACTIVE : 0;
157 170 dlmgmt_flags |= ((flags & DLADM_OPT_PERSIST) ? DLMGMT_PERSIST : 0);
158 171
159 172 destroyid.ld_cmd = DLMGMT_CMD_DESTROY_LINKID;
160 173 destroyid.ld_linkid = linkid;
161 174 destroyid.ld_flags = dlmgmt_flags;
162 175
163 176 return (dladm_door_call(handle, &destroyid, sizeof (destroyid),
164 177 &retval, &sz));
165 178 }
166 179
167 180 /*
168 181 * Remap a given link ID to a new name.
169 182 */
170 183 dladm_status_t
171 184 dladm_remap_datalink_id(dladm_handle_t handle, datalink_id_t linkid,
172 185 const char *link)
173 186 {
174 187 dlmgmt_door_remapid_t remapid;
175 188 dlmgmt_remapid_retval_t retval;
176 189 size_t sz = sizeof (retval);
177 190
178 191 remapid.ld_cmd = DLMGMT_CMD_REMAP_LINKID;
179 192 remapid.ld_linkid = linkid;
180 193 (void) strlcpy(remapid.ld_link, link, MAXLINKNAMELEN);
181 194
182 195 return (dladm_door_call(handle, &remapid, sizeof (remapid),
183 196 &retval, &sz));
184 197 }
185 198
186 199 /*
187 200 * Make a given link ID active.
188 201 */
189 202 dladm_status_t
190 203 dladm_up_datalink_id(dladm_handle_t handle, datalink_id_t linkid)
191 204 {
192 205 dlmgmt_door_upid_t upid;
193 206 dlmgmt_upid_retval_t retval;
194 207 size_t sz = sizeof (retval);
195 208
196 209 upid.ld_cmd = DLMGMT_CMD_UP_LINKID;
197 210 upid.ld_linkid = linkid;
198 211
199 212 return (dladm_door_call(handle, &upid, sizeof (upid), &retval, &sz));
200 213 }
201 214
202 215 /*
203 216 * Create a new link with the given name. Return the new link's handle
204 217 */
205 218 dladm_status_t
206 219 dladm_create_conf(dladm_handle_t handle, const char *link, datalink_id_t linkid,
207 220 datalink_class_t class, uint32_t media, dladm_conf_t *confp)
208 221 {
209 222 dlmgmt_door_createconf_t createconf;
210 223 dlmgmt_createconf_retval_t retval;
211 224 dladm_status_t status;
212 225 size_t sz = sizeof (retval);
213 226
214 227 if (link == NULL || confp == NULL)
215 228 return (DLADM_STATUS_BADARG);
216 229
217 230 (void) strlcpy(createconf.ld_link, link, MAXLINKNAMELEN);
218 231 createconf.ld_class = class;
219 232 createconf.ld_media = media;
220 233 createconf.ld_linkid = linkid;
221 234 createconf.ld_cmd = DLMGMT_CMD_CREATECONF;
222 235 confp->ds_confid = DLADM_INVALID_CONF;
223 236
224 237 if ((status = dladm_door_call(handle, &createconf, sizeof (createconf),
225 238 &retval, &sz)) == DLADM_STATUS_OK) {
226 239 confp->ds_readonly = B_FALSE;
227 240 confp->ds_confid = retval.lr_confid;
228 241 }
229 242 return (status);
230 243 }
231 244
232 245 /*
233 246 * An active physical link reported by the dlmgmtd daemon might not be active
234 247 * anymore as this link might be removed during system shutdown. Check its
235 248 * real status by calling dladm_phys_info().
236 249 */
237 250 dladm_status_t
238 251 i_dladm_phys_status(dladm_handle_t handle, datalink_id_t linkid,
239 252 uint32_t *flagsp)
240 253 {
241 254 dladm_phys_attr_t dpa;
242 255 dladm_status_t status;
243 256
244 257 assert((*flagsp) & DLMGMT_ACTIVE);
245 258
246 259 status = dladm_phys_info(handle, linkid, &dpa, DLADM_OPT_ACTIVE);
247 260 if (status == DLADM_STATUS_NOTFOUND) {
248 261 /*
249 262 * No active status, this link was removed. Update its status
250 263 * in the daemon and delete all active linkprops.
251 264 *
252 265 * Note that the operation could fail. If it does, return
253 266 * failure now since otherwise dladm_set_linkprop() might
254 267 * call back to i_dladm_phys_status() recursively.
255 268 */
256 269 if ((status = dladm_destroy_datalink_id(handle, linkid,
257 270 DLADM_OPT_ACTIVE)) != DLADM_STATUS_OK)
258 271 return (status);
259 272
260 273 (void) dladm_set_linkprop(handle, linkid, NULL, NULL, 0,
261 274 DLADM_OPT_ACTIVE);
262 275
263 276 (*flagsp) &= ~DLMGMT_ACTIVE;
264 277 status = DLADM_STATUS_OK;
265 278 }
266 279 return (status);
267 280 }
268 281
269 282 /*
270 283 * Walk each entry in the data link configuration repository and
271 284 * call fn on the linkid and arg.
272 285 */
273 286 dladm_status_t
274 287 dladm_walk_datalink_id(int (*fn)(dladm_handle_t, datalink_id_t, void *),
275 288 dladm_handle_t handle, void *argp, datalink_class_t class,
276 289 datalink_media_t dmedia, uint32_t flags)
277 290 {
278 291 dlmgmt_door_getnext_t getnext;
279 292 dlmgmt_getnext_retval_t retval;
280 293 uint32_t dlmgmt_flags;
281 294 datalink_id_t linkid = DATALINK_INVALID_LINKID;
282 295 dladm_status_t status = DLADM_STATUS_OK;
283 296 size_t sz = sizeof (retval);
284 297
285 298 if (fn == NULL)
286 299 return (DLADM_STATUS_BADARG);
287 300
288 301 dlmgmt_flags = (flags & DLADM_OPT_ACTIVE) ? DLMGMT_ACTIVE : 0;
289 302 dlmgmt_flags |= ((flags & DLADM_OPT_PERSIST) ? DLMGMT_PERSIST : 0);
290 303 dlmgmt_flags |= ((flags & DLADM_OPT_TRANSIENT) ? DLMGMT_TRANSIENT : 0);
291 304
292 305 getnext.ld_cmd = DLMGMT_CMD_GETNEXT;
293 306 getnext.ld_class = class;
294 307 getnext.ld_dmedia = dmedia;
295 308 getnext.ld_flags = dlmgmt_flags;
296 309
297 310 do {
298 311 getnext.ld_linkid = linkid;
299 312 if ((status = dladm_door_call(handle, &getnext,
300 313 sizeof (getnext), &retval, &sz)) != DLADM_STATUS_OK) {
301 314 /*
302 315 * Done with walking. If no next datalink is found,
303 316 * return success.
304 317 */
305 318 if (status == DLADM_STATUS_NOTFOUND)
306 319 status = DLADM_STATUS_OK;
307 320 break;
308 321 }
309 322
310 323 linkid = retval.lr_linkid;
311 324 if ((retval.lr_class == DATALINK_CLASS_PHYS) &&
312 325 (retval.lr_flags & DLMGMT_ACTIVE)) {
313 326 /*
314 327 * An active physical link reported by the dlmgmtd
315 328 * daemon might not be active anymore. Check its
316 329 * real status.
317 330 */
318 331 if (i_dladm_phys_status(handle, linkid,
319 332 &retval.lr_flags) != DLADM_STATUS_OK) {
320 333 continue;
321 334 }
322 335
323 336 if (!(dlmgmt_flags & retval.lr_flags))
324 337 continue;
325 338 }
326 339
327 340 if (fn(handle, linkid, argp) == DLADM_WALK_TERMINATE)
328 341 break;
329 342 } while (linkid != DATALINK_INVALID_LINKID);
330 343
331 344 return (status);
332 345 }
333 346
334 347 /*
335 348 * Get a handle of a copy of the link configuration (kept in the daemon)
336 349 * for the given link so it can be updated later by dladm_write_conf().
337 350 */
338 351 dladm_status_t
339 352 dladm_open_conf(dladm_handle_t handle, datalink_id_t linkid,
340 353 dladm_conf_t *confp)
341 354 {
342 355 dlmgmt_door_openconf_t openconf;
343 356 dlmgmt_openconf_retval_t retval;
344 357 dladm_status_t status;
345 358 size_t sz;
346 359
347 360 if (linkid == DATALINK_INVALID_LINKID || confp == NULL)
348 361 return (DLADM_STATUS_BADARG);
349 362
350 363 sz = sizeof (retval);
351 364 openconf.ld_linkid = linkid;
352 365 openconf.ld_cmd = DLMGMT_CMD_OPENCONF;
353 366 confp->ds_confid = DLADM_INVALID_CONF;
354 367 if ((status = dladm_door_call(handle, &openconf,
355 368 sizeof (openconf), &retval, &sz)) == DLADM_STATUS_OK) {
356 369 confp->ds_readonly = B_FALSE;
357 370 confp->ds_confid = retval.lr_confid;
358 371 }
359 372
360 373 return (status);
361 374 }
362 375
363 376 /*
364 377 * Get the handle of a local snapshot of the link configuration. Note that
365 378 * any operations with this handle are read-only, i.e., one can not update
366 379 * the configuration with this handle.
367 380 */
368 381 dladm_status_t
369 382 dladm_getsnap_conf(dladm_handle_t handle, datalink_id_t linkid,
370 383 dladm_conf_t *confp)
371 384 {
372 385 dlmgmt_door_getconfsnapshot_t snapshot;
373 386 dlmgmt_getconfsnapshot_retval_t *retvalp;
374 387 char *nvlbuf;
375 388 dladm_status_t status;
376 389 int err;
377 390 size_t sz;
378 391
379 392 if (linkid == DATALINK_INVALID_LINKID || confp == NULL)
380 393 return (DLADM_STATUS_BADARG);
381 394
382 395 sz = sizeof (dlmgmt_getconfsnapshot_retval_t);
383 396 snapshot.ld_linkid = linkid;
384 397 snapshot.ld_cmd = DLMGMT_CMD_GETCONFSNAPSHOT;
385 398 again:
386 399 if ((retvalp = malloc(sz)) == NULL)
387 400 return (DLADM_STATUS_NOMEM);
388 401
389 402 if ((status = dladm_door_call(handle, &snapshot, sizeof (snapshot),
390 403 retvalp, &sz)) == DLADM_STATUS_TOOSMALL) {
391 404 free(retvalp);
392 405 goto again;
393 406 }
394 407
395 408 if (status != DLADM_STATUS_OK) {
396 409 free(retvalp);
397 410 return (status);
398 411 }
399 412
400 413 confp->ds_readonly = B_TRUE;
401 414 nvlbuf = (char *)retvalp + sizeof (dlmgmt_getconfsnapshot_retval_t);
402 415 if ((err = nvlist_unpack(nvlbuf, retvalp->lr_nvlsz,
403 416 &(confp->ds_nvl), 0)) != 0) {
404 417 status = dladm_errno2status(err);
405 418 }
406 419 free(retvalp);
407 420 return (status);
408 421 }
409 422
410 423 /*
411 424 * Commit the given link to the data link configuration repository so
412 425 * that it will persist across reboots.
413 426 */
414 427 dladm_status_t
415 428 dladm_write_conf(dladm_handle_t handle, dladm_conf_t conf)
416 429 {
417 430 dlmgmt_door_writeconf_t writeconf;
418 431 dlmgmt_writeconf_retval_t retval;
419 432 size_t sz = sizeof (retval);
420 433
421 434 if (conf.ds_confid == DLADM_INVALID_CONF)
422 435 return (DLADM_STATUS_BADARG);
423 436
424 437 if (conf.ds_readonly)
425 438 return (DLADM_STATUS_DENIED);
426 439
427 440 writeconf.ld_cmd = DLMGMT_CMD_WRITECONF;
428 441 writeconf.ld_confid = conf.ds_confid;
429 442
430 443 return (dladm_door_call(handle, &writeconf, sizeof (writeconf),
431 444 &retval, &sz));
432 445 }
433 446
434 447 /*
435 448 * Given a dladm_conf_t, get the specific configuration field
436 449 *
437 450 * If the specified dladm_conf_t is a read-only snapshot of the configuration,
438 451 * get a specific link propertie from that snapshot (nvl), otherwise, get
439 452 * the link protperty from the dlmgmtd daemon using the given confid.
440 453 */
441 454 dladm_status_t
442 455 dladm_get_conf_field(dladm_handle_t handle, dladm_conf_t conf, const char *attr,
443 456 void *attrval, size_t attrsz)
444 457 {
445 458 dladm_status_t status = DLADM_STATUS_OK;
446 459
447 460 if (attrval == NULL || attrsz == 0 || attr == NULL)
448 461 return (DLADM_STATUS_BADARG);
449 462
450 463 if (conf.ds_readonly) {
451 464 uchar_t *oattrval;
452 465 uint32_t oattrsz;
453 466 int err;
454 467
455 468 if ((err = nvlist_lookup_byte_array(conf.ds_nvl, (char *)attr,
456 469 &oattrval, &oattrsz)) != 0) {
457 470 return (dladm_errno2status(err));
458 471 }
459 472 if (oattrsz > attrsz)
460 473 return (DLADM_STATUS_TOOSMALL);
461 474
462 475 bcopy(oattrval, attrval, oattrsz);
463 476 } else {
464 477 dlmgmt_door_getattr_t getattr;
465 478 dlmgmt_getattr_retval_t retval;
466 479 size_t sz = sizeof (retval);
467 480
468 481 if (conf.ds_confid == DLADM_INVALID_CONF)
469 482 return (DLADM_STATUS_BADARG);
470 483
471 484 getattr.ld_cmd = DLMGMT_CMD_GETATTR;
472 485 getattr.ld_confid = conf.ds_confid;
473 486 (void) strlcpy(getattr.ld_attr, attr, MAXLINKATTRLEN);
474 487
475 488 if ((status = dladm_door_call(handle, &getattr,
476 489 sizeof (getattr), &retval, &sz)) != DLADM_STATUS_OK) {
477 490 return (status);
478 491 }
479 492
480 493 if (retval.lr_attrsz > attrsz)
481 494 return (DLADM_STATUS_TOOSMALL);
482 495
483 496 bcopy(retval.lr_attrval, attrval, retval.lr_attrsz);
484 497 }
485 498 return (status);
486 499 }
487 500
488 501 /*
489 502 * Get next property attribute from data link configuration repository.
490 503 * If last_attr is "", return the first property.
491 504 */
492 505 dladm_status_t
493 506 dladm_getnext_conf_linkprop(dladm_handle_t handle __unused, dladm_conf_t conf,
494 507 const char *last_attr, char *attr, void *attrval, size_t attrsz,
495 508 size_t *attrszp)
496 509 {
497 510 nvlist_t *nvl = conf.ds_nvl;
498 511 nvpair_t *last = NULL, *nvp;
499 512 uchar_t *oattrval;
500 513 uint32_t oattrsz;
501 514 int err;
502 515
503 516 if (nvl == NULL || attrval == NULL || attrsz == 0 || attr == NULL ||
504 517 !conf.ds_readonly)
505 518 return (DLADM_STATUS_BADARG);
506 519
507 520 while ((nvp = nvlist_next_nvpair(nvl, last)) != NULL) {
508 521 if (last_attr[0] == '\0')
509 522 break;
510 523 if (last != NULL && strcmp(last_attr, nvpair_name(last)) == 0)
511 524 break;
512 525 last = nvp;
513 526 }
514 527
515 528 if (nvp == NULL)
516 529 return (DLADM_STATUS_NOTFOUND);
517 530
518 531 if ((err = nvpair_value_byte_array(nvp, (uchar_t **)&oattrval,
519 532 &oattrsz)) != 0) {
520 533 return (dladm_errno2status(err));
521 534 }
522 535
523 536 *attrszp = oattrsz;
524 537 if (oattrsz > attrsz)
525 538 return (DLADM_STATUS_TOOSMALL);
526 539
527 540 (void) strlcpy(attr, nvpair_name(nvp), MAXLINKATTRLEN);
528 541 bcopy(oattrval, attrval, oattrsz);
529 542 return (DLADM_STATUS_OK);
530 543 }
531 544
532 545 /*
533 546 * Get the link ID that is associated with the given name in the current zone.
534 547 */
535 548 dladm_status_t
536 549 dladm_name2info(dladm_handle_t handle, const char *link, datalink_id_t *linkidp,
537 550 uint32_t *flagp, datalink_class_t *classp, uint32_t *mediap)
538 551 {
539 552 return (dladm_zname2info(handle, NULL, link, linkidp, flagp, classp,
540 553 mediap));
541 554 }
542 555
543 556 /*
544 557 * Get the link ID that is associated with the given zone/name pair.
545 558 */
546 559 dladm_status_t
547 560 dladm_zname2info(dladm_handle_t handle, const char *zonename, const char *link,
548 561 datalink_id_t *linkidp, uint32_t *flagp, datalink_class_t *classp,
549 562 uint32_t *mediap)
550 563 {
551 564 dlmgmt_door_getlinkid_t getlinkid;
552 565 dlmgmt_getlinkid_retval_t retval;
553 566 datalink_id_t linkid;
554 567 dladm_status_t status;
555 568 size_t sz = sizeof (retval);
556 569
557 570 getlinkid.ld_cmd = DLMGMT_CMD_GETLINKID;
558 571 (void) strlcpy(getlinkid.ld_link, link, MAXLINKNAMELEN);
559 572 if (zonename != NULL)
560 573 getlinkid.ld_zoneid = getzoneidbyname(zonename);
561 574 else
562 575 getlinkid.ld_zoneid = -1;
563 576
564 577 if ((status = dladm_door_call(handle, &getlinkid, sizeof (getlinkid),
565 578 &retval, &sz)) != DLADM_STATUS_OK) {
566 579 return (status);
567 580 }
568 581
569 582 linkid = retval.lr_linkid;
570 583 if (retval.lr_class == DATALINK_CLASS_PHYS &&
571 584 retval.lr_flags & DLMGMT_ACTIVE) {
572 585 /*
573 586 * An active physical link reported by the dlmgmtd daemon
|
↓ open down ↓ |
438 lines elided |
↑ open up ↑ |
574 587 * might not be active anymore. Check and set its real status.
575 588 */
576 589 status = i_dladm_phys_status(handle, linkid, &retval.lr_flags);
577 590 if (status != DLADM_STATUS_OK)
578 591 return (status);
579 592 }
580 593
581 594 if (linkidp != NULL)
582 595 *linkidp = linkid;
583 596 if (flagp != NULL) {
584 - *flagp = retval.lr_flags & DLMGMT_ACTIVE ? DLADM_OPT_ACTIVE : 0;
597 + *flagp = (retval.lr_flags & DLMGMT_ACTIVE) ?
598 + DLADM_OPT_ACTIVE : 0;
585 599 *flagp |= (retval.lr_flags & DLMGMT_PERSIST) ?
586 600 DLADM_OPT_PERSIST : 0;
601 + *flagp |= (retval.lr_flags & DLMGMT_TRANSIENT) ?
602 + DLADM_OPT_TRANSIENT : 0;
587 603 }
588 604 if (classp != NULL)
589 605 *classp = retval.lr_class;
590 606 if (mediap != NULL)
591 607 *mediap = retval.lr_media;
592 608
593 609 return (DLADM_STATUS_OK);
594 610 }
595 611
596 612 /*
597 613 * Get the link name that is associated with the given id.
598 614 */
599 615 dladm_status_t
600 616 dladm_datalink_id2info(dladm_handle_t handle, datalink_id_t linkid,
601 617 uint32_t *flagp, datalink_class_t *classp, uint32_t *mediap, char *link,
602 618 size_t len)
603 619 {
604 620 dlmgmt_door_getname_t getname;
605 621 dlmgmt_getname_retval_t retval;
606 622 dladm_status_t status;
607 623 size_t sz = sizeof (retval);
608 624
609 625 if ((linkid == DATALINK_INVALID_LINKID) || (link != NULL && len == 0) ||
610 626 (link == NULL && len != 0)) {
611 627 return (DLADM_STATUS_BADARG);
612 628 }
613 629
614 630 getname.ld_cmd = DLMGMT_CMD_GETNAME;
615 631 getname.ld_linkid = linkid;
616 632 if ((status = dladm_door_call(handle, &getname, sizeof (getname),
617 633 &retval, &sz)) != DLADM_STATUS_OK) {
618 634 return (status);
619 635 }
620 636
621 637 if (len != 0 && (strlen(retval.lr_link) + 1 > len))
622 638 return (DLADM_STATUS_TOOSMALL);
623 639
624 640 if (retval.lr_class == DATALINK_CLASS_PHYS &&
625 641 retval.lr_flags & DLMGMT_ACTIVE) {
626 642 /*
627 643 * An active physical link reported by the dlmgmtd daemon
628 644 * might not be active anymore. Check and set its real status.
629 645 */
630 646 status = i_dladm_phys_status(handle, linkid, &retval.lr_flags);
631 647 if (status != DLADM_STATUS_OK)
632 648 return (status);
633 649 }
634 650
635 651 if (link != NULL)
636 652 (void) strlcpy(link, retval.lr_link, len);
637 653 if (classp != NULL)
638 654 *classp = retval.lr_class;
639 655 if (mediap != NULL)
640 656 *mediap = retval.lr_media;
641 657 if (flagp != NULL) {
642 658 *flagp = (retval.lr_flags & DLMGMT_ACTIVE) ?
643 659 DLADM_OPT_ACTIVE : 0;
644 660 *flagp |= (retval.lr_flags & DLMGMT_PERSIST) ?
645 661 DLADM_OPT_PERSIST : 0;
646 662 *flagp |= (retval.lr_flags & DLMGMT_TRANSIENT) ?
647 663 DLADM_OPT_TRANSIENT : 0;
648 664 }
649 665 return (DLADM_STATUS_OK);
650 666 }
651 667
652 668 /*
653 669 * Set the given attr with the given attrval for the given link.
654 670 */
655 671 dladm_status_t
656 672 dladm_set_conf_field(dladm_handle_t handle, dladm_conf_t conf, const char *attr,
657 673 dladm_datatype_t type, const void *attrval)
658 674 {
659 675 dlmgmt_door_setattr_t setattr;
660 676 dlmgmt_setattr_retval_t retval;
661 677 size_t attrsz;
662 678 size_t sz = sizeof (retval);
663 679
664 680 if (attr == NULL || attrval == NULL)
665 681 return (DLADM_STATUS_BADARG);
666 682
667 683 if (conf.ds_readonly)
668 684 return (DLADM_STATUS_DENIED);
669 685
670 686 if (type == DLADM_TYPE_STR)
671 687 attrsz = strlen(attrval) + 1;
672 688 else
673 689 attrsz = dladm_datatype_size[type];
674 690
675 691 if (attrsz > MAXLINKATTRVALLEN)
676 692 return (DLADM_STATUS_TOOSMALL);
677 693
678 694 setattr.ld_cmd = DLMGMT_CMD_SETATTR;
679 695 setattr.ld_confid = conf.ds_confid;
680 696 (void) strlcpy(setattr.ld_attr, attr, MAXLINKATTRLEN);
681 697 setattr.ld_attrsz = (uint32_t)attrsz;
682 698 setattr.ld_type = type;
683 699 bcopy(attrval, &setattr.ld_attrval, attrsz);
684 700
685 701 return (dladm_door_call(handle, &setattr, sizeof (setattr),
686 702 &retval, &sz));
687 703 }
688 704
689 705 /*
690 706 * Unset the given attr the given link.
691 707 */
692 708 dladm_status_t
693 709 dladm_unset_conf_field(dladm_handle_t handle, dladm_conf_t conf,
694 710 const char *attr)
695 711 {
696 712 dlmgmt_door_unsetattr_t unsetattr;
697 713 dlmgmt_unsetattr_retval_t retval;
698 714 size_t sz = sizeof (retval);
699 715
700 716 if (attr == NULL)
701 717 return (DLADM_STATUS_BADARG);
702 718
703 719 if (conf.ds_readonly)
704 720 return (DLADM_STATUS_DENIED);
705 721
706 722 unsetattr.ld_cmd = DLMGMT_CMD_UNSETATTR;
707 723 unsetattr.ld_confid = conf.ds_confid;
708 724 (void) strlcpy(unsetattr.ld_attr, attr, MAXLINKATTRLEN);
709 725
710 726 return (dladm_door_call(handle, &unsetattr, sizeof (unsetattr),
711 727 &retval, &sz));
712 728 }
713 729
714 730 /*
715 731 * Remove the given link ID and its entry from the data link configuration
716 732 * repository.
717 733 */
718 734 dladm_status_t
719 735 dladm_remove_conf(dladm_handle_t handle, datalink_id_t linkid)
720 736 {
721 737 dlmgmt_door_removeconf_t removeconf;
722 738 dlmgmt_removeconf_retval_t retval;
723 739 size_t sz = sizeof (retval);
724 740
725 741 removeconf.ld_cmd = DLMGMT_CMD_REMOVECONF;
726 742 removeconf.ld_linkid = linkid;
727 743
728 744 return (dladm_door_call(handle, &removeconf, sizeof (removeconf),
729 745 &retval, &sz));
730 746 }
731 747
732 748 /*
733 749 * Free the contents of the link structure.
734 750 */
735 751 void
736 752 dladm_destroy_conf(dladm_handle_t handle, dladm_conf_t conf)
737 753 {
738 754 dlmgmt_door_destroyconf_t dconf;
739 755 dlmgmt_destroyconf_retval_t retval;
740 756 size_t sz = sizeof (retval);
741 757
742 758 if (conf.ds_readonly) {
743 759 nvlist_free(conf.ds_nvl);
744 760 } else {
745 761 if (conf.ds_confid == DLADM_INVALID_CONF)
746 762 return;
747 763
748 764 dconf.ld_cmd = DLMGMT_CMD_DESTROYCONF;
749 765 dconf.ld_confid = conf.ds_confid;
750 766
751 767 (void) dladm_door_call(handle, &dconf, sizeof (dconf),
752 768 &retval, &sz);
753 769 }
754 770 }
755 771
756 772 dladm_status_t
757 773 dladm_zone_boot(dladm_handle_t handle, zoneid_t zoneid)
758 774 {
759 775 dlmgmt_door_zoneboot_t zoneboot;
760 776 dlmgmt_zoneboot_retval_t retval;
761 777 size_t sz = sizeof (retval);
762 778
763 779 zoneboot.ld_cmd = DLMGMT_CMD_ZONEBOOT;
764 780 zoneboot.ld_zoneid = zoneid;
765 781 return (dladm_door_call(handle, &zoneboot, sizeof (zoneboot),
766 782 &retval, &sz));
767 783 }
768 784
769 785 dladm_status_t
770 786 dladm_zone_halt(dladm_handle_t handle, zoneid_t zoneid)
771 787 {
772 788 dlmgmt_door_zonehalt_t zonehalt;
773 789 dlmgmt_zonehalt_retval_t retval;
774 790 size_t sz = sizeof (retval);
775 791
776 792 zonehalt.ld_cmd = DLMGMT_CMD_ZONEHALT;
777 793 zonehalt.ld_zoneid = zoneid;
778 794 return (dladm_door_call(handle, &zonehalt, sizeof (zonehalt),
779 795 &retval, &sz));
780 796 }
|
↓ open down ↓ |
184 lines elided |
↑ open up ↑ |
XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX