1d62bc4baSyz147064 /* 2d62bc4baSyz147064 * CDDL HEADER START 3d62bc4baSyz147064 * 4d62bc4baSyz147064 * The contents of this file are subject to the terms of the 5d62bc4baSyz147064 * Common Development and Distribution License (the "License"). 6d62bc4baSyz147064 * You may not use this file except in compliance with the License. 7d62bc4baSyz147064 * 8d62bc4baSyz147064 * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE 9d62bc4baSyz147064 * or http://www.opensolaris.org/os/licensing. 10d62bc4baSyz147064 * See the License for the specific language governing permissions 11d62bc4baSyz147064 * and limitations under the License. 12d62bc4baSyz147064 * 13d62bc4baSyz147064 * When distributing Covered Code, include this CDDL HEADER in each 14d62bc4baSyz147064 * file and include the License file at usr/src/OPENSOLARIS.LICENSE. 15d62bc4baSyz147064 * If applicable, add the following below this CDDL HEADER, with the 16d62bc4baSyz147064 * fields enclosed by brackets "[]" replaced with your own identifying 17d62bc4baSyz147064 * information: Portions Copyright [yyyy] [name of copyright owner] 18d62bc4baSyz147064 * 19d62bc4baSyz147064 * CDDL HEADER END 20d62bc4baSyz147064 */ 21d62bc4baSyz147064 /* 2282a2fc47SJames Carlson * Copyright 2009 Sun Microsystems, Inc. All rights reserved. 23d62bc4baSyz147064 * Use is subject to license terms. 24d62bc4baSyz147064 */ 25d62bc4baSyz147064 26d62bc4baSyz147064 #include <door.h> 27d62bc4baSyz147064 #include <errno.h> 28d62bc4baSyz147064 #include <assert.h> 29d62bc4baSyz147064 #include <stdio.h> 30d62bc4baSyz147064 #include <stdlib.h> 31d62bc4baSyz147064 #include <unistd.h> 32d62bc4baSyz147064 #include <string.h> 33d62bc4baSyz147064 #include <strings.h> 342b24ab6bSSebastien Roy #include <zone.h> 35d62bc4baSyz147064 #include <sys/types.h> 36d62bc4baSyz147064 #include <sys/stat.h> 37d62bc4baSyz147064 #include <sys/aggr.h> 3882a2fc47SJames Carlson #include <sys/mman.h> 39d62bc4baSyz147064 #include <fcntl.h> 40d62bc4baSyz147064 #include <libdladm.h> 41d62bc4baSyz147064 #include <libdladm_impl.h> 42d62bc4baSyz147064 #include <libdllink.h> 43d62bc4baSyz147064 #include <libdlmgmt.h> 44d62bc4baSyz147064 45d62bc4baSyz147064 /* 46d62bc4baSyz147064 * Table of data type sizes indexed by dladm_datatype_t. 47d62bc4baSyz147064 */ 48d62bc4baSyz147064 static size_t dladm_datatype_size[] = { 49d62bc4baSyz147064 0, /* DLADM_TYPE_STR, use strnlen() */ 50d62bc4baSyz147064 sizeof (boolean_t), /* DLADM_TYPE_BOOLEAN */ 51d62bc4baSyz147064 sizeof (uint64_t) /* DLADM_TYPE_UINT64 */ 52d62bc4baSyz147064 }; 53d62bc4baSyz147064 54d62bc4baSyz147064 static dladm_status_t 554ac67f02SAnurag S. Maskey dladm_door_call(dladm_handle_t handle, void *arg, size_t asize, void *rbuf, 564ac67f02SAnurag S. Maskey size_t rsize) 57d62bc4baSyz147064 { 58d62bc4baSyz147064 door_arg_t darg; 594ac67f02SAnurag S. Maskey int door_fd; 60d62bc4baSyz147064 dladm_status_t status = DLADM_STATUS_OK; 61d62bc4baSyz147064 62d62bc4baSyz147064 darg.data_ptr = arg; 63d62bc4baSyz147064 darg.data_size = asize; 64d62bc4baSyz147064 darg.desc_ptr = NULL; 65d62bc4baSyz147064 darg.desc_num = 0; 66d62bc4baSyz147064 darg.rbuf = rbuf; 67024b0a25Sseb darg.rsize = rsize; 68d62bc4baSyz147064 694ac67f02SAnurag S. Maskey /* The door descriptor is opened if it isn't already */ 704ac67f02SAnurag S. Maskey if ((status = dladm_door_fd(handle, &door_fd)) != DLADM_STATUS_OK) 714ac67f02SAnurag S. Maskey return (status); 724ac67f02SAnurag S. Maskey if (door_call(door_fd, &darg) == -1) 73d62bc4baSyz147064 status = dladm_errno2status(errno); 74d62bc4baSyz147064 if (status != DLADM_STATUS_OK) 75d62bc4baSyz147064 return (status); 76d62bc4baSyz147064 77d62bc4baSyz147064 if (darg.rbuf != rbuf) { 78d62bc4baSyz147064 /* 79d62bc4baSyz147064 * The size of the input rbuf is not big enough so that 80d62bc4baSyz147064 * the door allocate the rbuf itself. In this case, simply 81d62bc4baSyz147064 * think something wrong with the door call. 82d62bc4baSyz147064 */ 83d62bc4baSyz147064 (void) munmap(darg.rbuf, darg.rsize); 84d62bc4baSyz147064 return (DLADM_STATUS_TOOSMALL); 85d62bc4baSyz147064 } 86024b0a25Sseb if (darg.rsize != rsize) 87d62bc4baSyz147064 return (DLADM_STATUS_FAILED); 88d62bc4baSyz147064 89024b0a25Sseb return (dladm_errno2status(((dlmgmt_retval_t *)rbuf)->lr_err)); 90d62bc4baSyz147064 } 91d62bc4baSyz147064 92d62bc4baSyz147064 /* 93d62bc4baSyz147064 * Allocate a new linkid with the given name. Return the new linkid. 94d62bc4baSyz147064 */ 95d62bc4baSyz147064 dladm_status_t 964ac67f02SAnurag S. Maskey dladm_create_datalink_id(dladm_handle_t handle, const char *link, 974ac67f02SAnurag S. Maskey datalink_class_t class, uint32_t media, uint32_t flags, 984ac67f02SAnurag S. Maskey datalink_id_t *linkidp) 99d62bc4baSyz147064 { 100d62bc4baSyz147064 dlmgmt_door_createid_t createid; 101d62bc4baSyz147064 dlmgmt_createid_retval_t retval; 102d62bc4baSyz147064 uint32_t dlmgmt_flags; 103d62bc4baSyz147064 dladm_status_t status; 104d62bc4baSyz147064 105024b0a25Sseb if (link == NULL || class == DATALINK_CLASS_ALL || 106d62bc4baSyz147064 !(flags & (DLADM_OPT_ACTIVE | DLADM_OPT_PERSIST)) || 107d62bc4baSyz147064 linkidp == NULL) { 108d62bc4baSyz147064 return (DLADM_STATUS_BADARG); 109d62bc4baSyz147064 } 110d62bc4baSyz147064 111d62bc4baSyz147064 dlmgmt_flags = (flags & DLADM_OPT_ACTIVE) ? DLMGMT_ACTIVE : 0; 112d62bc4baSyz147064 dlmgmt_flags |= (flags & DLADM_OPT_PERSIST) ? DLMGMT_PERSIST : 0; 113d62bc4baSyz147064 114d62bc4baSyz147064 (void) strlcpy(createid.ld_link, link, MAXLINKNAMELEN); 115d62bc4baSyz147064 createid.ld_class = class; 116d62bc4baSyz147064 createid.ld_media = media; 117d62bc4baSyz147064 createid.ld_flags = dlmgmt_flags; 118d62bc4baSyz147064 createid.ld_cmd = DLMGMT_CMD_CREATE_LINKID; 119d62bc4baSyz147064 createid.ld_prefix = (flags & DLADM_OPT_PREFIX); 120d62bc4baSyz147064 1214ac67f02SAnurag S. Maskey if ((status = dladm_door_call(handle, &createid, sizeof (createid), 1224ac67f02SAnurag S. Maskey &retval, sizeof (retval))) == DLADM_STATUS_OK) { 123d62bc4baSyz147064 *linkidp = retval.lr_linkid; 124024b0a25Sseb } 125024b0a25Sseb return (status); 126d62bc4baSyz147064 } 127d62bc4baSyz147064 128d62bc4baSyz147064 /* 129d62bc4baSyz147064 * Destroy the given link ID. 130d62bc4baSyz147064 */ 131d62bc4baSyz147064 dladm_status_t 1324ac67f02SAnurag S. Maskey dladm_destroy_datalink_id(dladm_handle_t handle, datalink_id_t linkid, 1334ac67f02SAnurag S. Maskey uint32_t flags) 134d62bc4baSyz147064 { 135d62bc4baSyz147064 dlmgmt_door_destroyid_t destroyid; 136d62bc4baSyz147064 dlmgmt_destroyid_retval_t retval; 137d62bc4baSyz147064 uint32_t dlmgmt_flags; 138d62bc4baSyz147064 139d62bc4baSyz147064 dlmgmt_flags = (flags & DLADM_OPT_ACTIVE) ? DLMGMT_ACTIVE : 0; 140d62bc4baSyz147064 dlmgmt_flags |= ((flags & DLADM_OPT_PERSIST) ? DLMGMT_PERSIST : 0); 141d62bc4baSyz147064 142d62bc4baSyz147064 destroyid.ld_cmd = DLMGMT_CMD_DESTROY_LINKID; 143d62bc4baSyz147064 destroyid.ld_linkid = linkid; 144d62bc4baSyz147064 destroyid.ld_flags = dlmgmt_flags; 145d62bc4baSyz147064 1464ac67f02SAnurag S. Maskey return (dladm_door_call(handle, &destroyid, sizeof (destroyid), &retval, 1474ac67f02SAnurag S. Maskey sizeof (retval))); 148d62bc4baSyz147064 } 149d62bc4baSyz147064 150d62bc4baSyz147064 /* 151d62bc4baSyz147064 * Remap a given link ID to a new name. 152d62bc4baSyz147064 */ 153d62bc4baSyz147064 dladm_status_t 1544ac67f02SAnurag S. Maskey dladm_remap_datalink_id(dladm_handle_t handle, datalink_id_t linkid, 1554ac67f02SAnurag S. Maskey const char *link) 156d62bc4baSyz147064 { 157d62bc4baSyz147064 dlmgmt_door_remapid_t remapid; 158d62bc4baSyz147064 dlmgmt_remapid_retval_t retval; 159d62bc4baSyz147064 160d62bc4baSyz147064 remapid.ld_cmd = DLMGMT_CMD_REMAP_LINKID; 161d62bc4baSyz147064 remapid.ld_linkid = linkid; 162d62bc4baSyz147064 (void) strlcpy(remapid.ld_link, link, MAXLINKNAMELEN); 163d62bc4baSyz147064 1644ac67f02SAnurag S. Maskey return (dladm_door_call(handle, &remapid, sizeof (remapid), &retval, 1654ac67f02SAnurag S. Maskey sizeof (retval))); 166d62bc4baSyz147064 } 167d62bc4baSyz147064 168d62bc4baSyz147064 /* 169d62bc4baSyz147064 * Make a given link ID active. 170d62bc4baSyz147064 */ 171d62bc4baSyz147064 dladm_status_t 1724ac67f02SAnurag S. Maskey dladm_up_datalink_id(dladm_handle_t handle, datalink_id_t linkid) 173d62bc4baSyz147064 { 174d62bc4baSyz147064 dlmgmt_door_upid_t upid; 175d62bc4baSyz147064 dlmgmt_upid_retval_t retval; 176d62bc4baSyz147064 177d62bc4baSyz147064 upid.ld_cmd = DLMGMT_CMD_UP_LINKID; 178d62bc4baSyz147064 upid.ld_linkid = linkid; 179d62bc4baSyz147064 1804ac67f02SAnurag S. Maskey return (dladm_door_call(handle, &upid, sizeof (upid), &retval, 1814ac67f02SAnurag S. Maskey sizeof (retval))); 182d62bc4baSyz147064 } 183d62bc4baSyz147064 184d62bc4baSyz147064 /* 185d62bc4baSyz147064 * Create a new link with the given name. Return the new link's handle 186d62bc4baSyz147064 */ 187d62bc4baSyz147064 dladm_status_t 1884ac67f02SAnurag S. Maskey dladm_create_conf(dladm_handle_t handle, const char *link, datalink_id_t linkid, 189d62bc4baSyz147064 datalink_class_t class, uint32_t media, dladm_conf_t *confp) 190d62bc4baSyz147064 { 191d62bc4baSyz147064 dlmgmt_door_createconf_t createconf; 192d62bc4baSyz147064 dlmgmt_createconf_retval_t retval; 193d62bc4baSyz147064 dladm_status_t status; 194d62bc4baSyz147064 195024b0a25Sseb if (link == NULL || confp == NULL) 196d62bc4baSyz147064 return (DLADM_STATUS_BADARG); 197d62bc4baSyz147064 198d62bc4baSyz147064 (void) strlcpy(createconf.ld_link, link, MAXLINKNAMELEN); 199d62bc4baSyz147064 createconf.ld_class = class; 200d62bc4baSyz147064 createconf.ld_media = media; 201d62bc4baSyz147064 createconf.ld_linkid = linkid; 202d62bc4baSyz147064 createconf.ld_cmd = DLMGMT_CMD_CREATECONF; 203d62bc4baSyz147064 2044ac67f02SAnurag S. Maskey if ((status = dladm_door_call(handle, &createconf, sizeof (createconf), 205024b0a25Sseb &retval, sizeof (retval))) == DLADM_STATUS_OK) { 206d62bc4baSyz147064 *confp = retval.lr_conf; 207024b0a25Sseb } 208024b0a25Sseb return (status); 209d62bc4baSyz147064 } 210d62bc4baSyz147064 211d62bc4baSyz147064 /* 212d62bc4baSyz147064 * An active physical link reported by the dlmgmtd daemon might not be active 213d62bc4baSyz147064 * anymore as this link might be removed during system shutdown. Check its 214d62bc4baSyz147064 * real status by calling dladm_phys_info(). 215d62bc4baSyz147064 */ 216d62bc4baSyz147064 dladm_status_t 2174ac67f02SAnurag S. Maskey i_dladm_phys_status(dladm_handle_t handle, datalink_id_t linkid, 2184ac67f02SAnurag S. Maskey uint32_t *flagsp) 219d62bc4baSyz147064 { 220d62bc4baSyz147064 dladm_phys_attr_t dpa; 221d62bc4baSyz147064 dladm_status_t status; 222d62bc4baSyz147064 223d62bc4baSyz147064 assert((*flagsp) & DLMGMT_ACTIVE); 224d62bc4baSyz147064 2254ac67f02SAnurag S. Maskey status = dladm_phys_info(handle, linkid, &dpa, DLADM_OPT_ACTIVE); 226d62bc4baSyz147064 if (status == DLADM_STATUS_NOTFOUND) { 227d62bc4baSyz147064 /* 228d62bc4baSyz147064 * No active status, this link was removed. Update its status 229d62bc4baSyz147064 * in the daemon and delete all active linkprops. 2302d4eecfaSCathy Zhou * 2312d4eecfaSCathy Zhou * Note that the operation could fail. If it does, return 2322d4eecfaSCathy Zhou * failure now since otherwise dladm_set_linkprop() might 2332d4eecfaSCathy Zhou * call back to i_dladm_phys_status() recursively. 234d62bc4baSyz147064 */ 2354ac67f02SAnurag S. Maskey if ((status = dladm_destroy_datalink_id(handle, linkid, 2364ac67f02SAnurag S. Maskey DLADM_OPT_ACTIVE)) != DLADM_STATUS_OK) 2372d4eecfaSCathy Zhou return (status); 2382d4eecfaSCathy Zhou 2394ac67f02SAnurag S. Maskey (void) dladm_set_linkprop(handle, linkid, NULL, NULL, 0, 240d62bc4baSyz147064 DLADM_OPT_ACTIVE); 241d62bc4baSyz147064 242d62bc4baSyz147064 (*flagsp) &= ~DLMGMT_ACTIVE; 243d62bc4baSyz147064 status = DLADM_STATUS_OK; 244d62bc4baSyz147064 } 245d62bc4baSyz147064 return (status); 246d62bc4baSyz147064 } 247d62bc4baSyz147064 248d62bc4baSyz147064 /* 249d62bc4baSyz147064 * Walk each entry in the data link configuration repository and 250d62bc4baSyz147064 * call fn on the linkid and arg. 251d62bc4baSyz147064 */ 252d62bc4baSyz147064 dladm_status_t 2534ac67f02SAnurag S. Maskey dladm_walk_datalink_id(int (*fn)(dladm_handle_t, datalink_id_t, void *), 2544ac67f02SAnurag S. Maskey dladm_handle_t handle, void *argp, datalink_class_t class, 2554ac67f02SAnurag S. Maskey datalink_media_t dmedia, uint32_t flags) 256d62bc4baSyz147064 { 257d62bc4baSyz147064 dlmgmt_door_getnext_t getnext; 258d62bc4baSyz147064 dlmgmt_getnext_retval_t retval; 259d62bc4baSyz147064 uint32_t dlmgmt_flags; 260d62bc4baSyz147064 datalink_id_t linkid = DATALINK_INVALID_LINKID; 261d62bc4baSyz147064 dladm_status_t status = DLADM_STATUS_OK; 262d62bc4baSyz147064 263d62bc4baSyz147064 if (fn == NULL) 264d62bc4baSyz147064 return (DLADM_STATUS_BADARG); 265d62bc4baSyz147064 266d62bc4baSyz147064 dlmgmt_flags = (flags & DLADM_OPT_ACTIVE) ? DLMGMT_ACTIVE : 0; 267d62bc4baSyz147064 dlmgmt_flags |= ((flags & DLADM_OPT_PERSIST) ? DLMGMT_PERSIST : 0); 268d62bc4baSyz147064 269d62bc4baSyz147064 getnext.ld_cmd = DLMGMT_CMD_GETNEXT; 270d62bc4baSyz147064 getnext.ld_class = class; 271d62bc4baSyz147064 getnext.ld_dmedia = dmedia; 272d62bc4baSyz147064 getnext.ld_flags = dlmgmt_flags; 273d62bc4baSyz147064 274d62bc4baSyz147064 do { 275d62bc4baSyz147064 getnext.ld_linkid = linkid; 2764ac67f02SAnurag S. Maskey if ((status = dladm_door_call(handle, &getnext, 2774ac67f02SAnurag S. Maskey sizeof (getnext), &retval, sizeof (retval))) != 2784ac67f02SAnurag S. Maskey DLADM_STATUS_OK) { 279d62bc4baSyz147064 /* 280*7363c184SCathy Zhou * Done with walking. If no next datalink is found, 281*7363c184SCathy Zhou * return success. 282d62bc4baSyz147064 */ 283*7363c184SCathy Zhou if (status == DLADM_STATUS_NOTFOUND) 284*7363c184SCathy Zhou status = DLADM_STATUS_OK; 285d62bc4baSyz147064 break; 286d62bc4baSyz147064 } 287d62bc4baSyz147064 288d62bc4baSyz147064 linkid = retval.lr_linkid; 289d62bc4baSyz147064 if ((retval.lr_class == DATALINK_CLASS_PHYS) && 290d62bc4baSyz147064 (retval.lr_flags & DLMGMT_ACTIVE)) { 291d62bc4baSyz147064 /* 292d62bc4baSyz147064 * An active physical link reported by the dlmgmtd 293d62bc4baSyz147064 * daemon might not be active anymore. Check its 294d62bc4baSyz147064 * real status. 295d62bc4baSyz147064 */ 2964ac67f02SAnurag S. Maskey if (i_dladm_phys_status(handle, linkid, 2974ac67f02SAnurag S. Maskey &retval.lr_flags) != DLADM_STATUS_OK) { 298d62bc4baSyz147064 continue; 299d62bc4baSyz147064 } 300d62bc4baSyz147064 301d62bc4baSyz147064 if (!(dlmgmt_flags & retval.lr_flags)) 302d62bc4baSyz147064 continue; 303d62bc4baSyz147064 } 304d62bc4baSyz147064 3054ac67f02SAnurag S. Maskey if (fn(handle, linkid, argp) == DLADM_WALK_TERMINATE) 306d62bc4baSyz147064 break; 307d62bc4baSyz147064 } while (linkid != DATALINK_INVALID_LINKID); 308d62bc4baSyz147064 309d62bc4baSyz147064 return (status); 310d62bc4baSyz147064 } 311d62bc4baSyz147064 312d62bc4baSyz147064 /* 313d62bc4baSyz147064 * Get the link properties structure for the given link. 314d62bc4baSyz147064 */ 315d62bc4baSyz147064 dladm_status_t 3164ac67f02SAnurag S. Maskey dladm_read_conf(dladm_handle_t handle, datalink_id_t linkid, 3174ac67f02SAnurag S. Maskey dladm_conf_t *confp) 318d62bc4baSyz147064 { 319d62bc4baSyz147064 dlmgmt_door_readconf_t readconf; 320d62bc4baSyz147064 dlmgmt_readconf_retval_t retval; 321d62bc4baSyz147064 dladm_status_t status; 322d62bc4baSyz147064 323d62bc4baSyz147064 if (linkid == DATALINK_INVALID_LINKID || confp == NULL) 324d62bc4baSyz147064 return (DLADM_STATUS_BADARG); 325d62bc4baSyz147064 326d62bc4baSyz147064 readconf.ld_linkid = linkid; 327d62bc4baSyz147064 readconf.ld_cmd = DLMGMT_CMD_READCONF; 328d62bc4baSyz147064 3294ac67f02SAnurag S. Maskey if ((status = dladm_door_call(handle, &readconf, sizeof (readconf), 330024b0a25Sseb &retval, sizeof (retval))) == DLADM_STATUS_OK) { 331d62bc4baSyz147064 *confp = retval.lr_conf; 332024b0a25Sseb } 333024b0a25Sseb return (status); 334d62bc4baSyz147064 } 335d62bc4baSyz147064 336d62bc4baSyz147064 /* 337d62bc4baSyz147064 * Commit the given link to the data link configuration repository so 338d62bc4baSyz147064 * that it will persist across reboots. 339d62bc4baSyz147064 */ 340d62bc4baSyz147064 dladm_status_t 3414ac67f02SAnurag S. Maskey dladm_write_conf(dladm_handle_t handle, dladm_conf_t conf) 342d62bc4baSyz147064 { 343d62bc4baSyz147064 dlmgmt_door_writeconf_t writeconf; 344d62bc4baSyz147064 dlmgmt_writeconf_retval_t retval; 345d62bc4baSyz147064 346d62bc4baSyz147064 if (conf == DLADM_INVALID_CONF) 347d62bc4baSyz147064 return (DLADM_STATUS_BADARG); 348d62bc4baSyz147064 349d62bc4baSyz147064 writeconf.ld_cmd = DLMGMT_CMD_WRITECONF; 350d62bc4baSyz147064 writeconf.ld_conf = conf; 351d62bc4baSyz147064 3524ac67f02SAnurag S. Maskey return (dladm_door_call(handle, &writeconf, sizeof (writeconf), &retval, 3534ac67f02SAnurag S. Maskey sizeof (retval))); 354d62bc4baSyz147064 } 355d62bc4baSyz147064 356d62bc4baSyz147064 /* 357d62bc4baSyz147064 * Given a link ID and a key, get the matching information from 358d62bc4baSyz147064 * data link configuration repository. 359d62bc4baSyz147064 */ 360d62bc4baSyz147064 dladm_status_t 3614ac67f02SAnurag S. Maskey dladm_get_conf_field(dladm_handle_t handle, dladm_conf_t conf, const char *attr, 3624ac67f02SAnurag S. Maskey void *attrval, size_t attrsz) 363d62bc4baSyz147064 { 364d62bc4baSyz147064 dlmgmt_door_getattr_t getattr; 365024b0a25Sseb dlmgmt_getattr_retval_t retval; 366024b0a25Sseb dladm_status_t status; 367d62bc4baSyz147064 368d62bc4baSyz147064 if (conf == DLADM_INVALID_CONF || attrval == NULL || 369024b0a25Sseb attrsz == 0 || attr == NULL) { 370d62bc4baSyz147064 return (DLADM_STATUS_BADARG); 371d62bc4baSyz147064 } 372d62bc4baSyz147064 373d62bc4baSyz147064 getattr.ld_cmd = DLMGMT_CMD_GETATTR; 374d62bc4baSyz147064 getattr.ld_conf = conf; 375d62bc4baSyz147064 (void) strlcpy(getattr.ld_attr, attr, MAXLINKATTRLEN); 376d62bc4baSyz147064 3774ac67f02SAnurag S. Maskey if ((status = dladm_door_call(handle, &getattr, sizeof (getattr), 3784ac67f02SAnurag S. Maskey &retval, sizeof (retval))) != DLADM_STATUS_OK) { 379d62bc4baSyz147064 return (status); 380d62bc4baSyz147064 } 381d62bc4baSyz147064 382024b0a25Sseb if (retval.lr_attrsz > attrsz) 383024b0a25Sseb return (DLADM_STATUS_TOOSMALL); 384024b0a25Sseb 385024b0a25Sseb bcopy(retval.lr_attrval, attrval, retval.lr_attrsz); 386024b0a25Sseb return (DLADM_STATUS_OK); 387024b0a25Sseb } 388024b0a25Sseb 389d62bc4baSyz147064 /* 39062ee1d25SArtem Kachitchkine * Get next property attribute from data link configuration repository. 39162ee1d25SArtem Kachitchkine */ 39262ee1d25SArtem Kachitchkine dladm_status_t 39362ee1d25SArtem Kachitchkine dladm_getnext_conf_linkprop(dladm_handle_t handle, dladm_conf_t conf, 39462ee1d25SArtem Kachitchkine const char *last_attr, char *attr, void *attrval, size_t attrsz, 39562ee1d25SArtem Kachitchkine size_t *attrszp) 39662ee1d25SArtem Kachitchkine { 39762ee1d25SArtem Kachitchkine dlmgmt_door_linkprop_getnext_t getnext; 39862ee1d25SArtem Kachitchkine dlmgmt_linkprop_getnext_retval_t retval; 39962ee1d25SArtem Kachitchkine dladm_status_t status; 40062ee1d25SArtem Kachitchkine 40162ee1d25SArtem Kachitchkine if (conf == DLADM_INVALID_CONF || attrval == NULL || 40262ee1d25SArtem Kachitchkine attrsz == 0 || attr == NULL) { 40362ee1d25SArtem Kachitchkine return (DLADM_STATUS_BADARG); 40462ee1d25SArtem Kachitchkine } 40562ee1d25SArtem Kachitchkine 40662ee1d25SArtem Kachitchkine getnext.ld_cmd = DLMGMT_CMD_LINKPROP_GETNEXT; 40762ee1d25SArtem Kachitchkine getnext.ld_conf = conf; 40862ee1d25SArtem Kachitchkine (void) strlcpy(getnext.ld_last_attr, last_attr, MAXLINKATTRLEN); 40962ee1d25SArtem Kachitchkine 41062ee1d25SArtem Kachitchkine if ((status = dladm_door_call(handle, &getnext, sizeof (getnext), 41162ee1d25SArtem Kachitchkine &retval, sizeof (retval))) != DLADM_STATUS_OK) { 41262ee1d25SArtem Kachitchkine return (status); 41362ee1d25SArtem Kachitchkine } 41462ee1d25SArtem Kachitchkine 41562ee1d25SArtem Kachitchkine *attrszp = retval.lr_attrsz; 41662ee1d25SArtem Kachitchkine if (retval.lr_attrsz > attrsz) { 41762ee1d25SArtem Kachitchkine return (DLADM_STATUS_TOOSMALL); 41862ee1d25SArtem Kachitchkine } 41962ee1d25SArtem Kachitchkine 42062ee1d25SArtem Kachitchkine (void) strlcpy(attr, retval.lr_attr, MAXLINKATTRLEN); 42162ee1d25SArtem Kachitchkine bcopy(retval.lr_attrval, attrval, retval.lr_attrsz); 42262ee1d25SArtem Kachitchkine return (DLADM_STATUS_OK); 42362ee1d25SArtem Kachitchkine } 42462ee1d25SArtem Kachitchkine 42562ee1d25SArtem Kachitchkine /* 426d62bc4baSyz147064 * Get the link ID that is associated with the given name. 427d62bc4baSyz147064 */ 428d62bc4baSyz147064 dladm_status_t 4294ac67f02SAnurag S. Maskey dladm_name2info(dladm_handle_t handle, const char *link, datalink_id_t *linkidp, 4304ac67f02SAnurag S. Maskey uint32_t *flagp, datalink_class_t *classp, uint32_t *mediap) 431d62bc4baSyz147064 { 432d62bc4baSyz147064 dlmgmt_door_getlinkid_t getlinkid; 433d62bc4baSyz147064 dlmgmt_getlinkid_retval_t retval; 434d62bc4baSyz147064 datalink_id_t linkid; 435d62bc4baSyz147064 dladm_status_t status; 436d62bc4baSyz147064 437d62bc4baSyz147064 getlinkid.ld_cmd = DLMGMT_CMD_GETLINKID; 438d62bc4baSyz147064 (void) strlcpy(getlinkid.ld_link, link, MAXLINKNAMELEN); 439d62bc4baSyz147064 4404ac67f02SAnurag S. Maskey if ((status = dladm_door_call(handle, &getlinkid, sizeof (getlinkid), 441024b0a25Sseb &retval, sizeof (retval))) != DLADM_STATUS_OK) { 442d62bc4baSyz147064 return (status); 443024b0a25Sseb } 444d62bc4baSyz147064 445d62bc4baSyz147064 linkid = retval.lr_linkid; 446d62bc4baSyz147064 if (retval.lr_class == DATALINK_CLASS_PHYS && 447d62bc4baSyz147064 retval.lr_flags & DLMGMT_ACTIVE) { 448d62bc4baSyz147064 /* 449d62bc4baSyz147064 * An active physical link reported by the dlmgmtd daemon 450d62bc4baSyz147064 * might not be active anymore. Check and set its real status. 451d62bc4baSyz147064 */ 4524ac67f02SAnurag S. Maskey status = i_dladm_phys_status(handle, linkid, &retval.lr_flags); 453d62bc4baSyz147064 if (status != DLADM_STATUS_OK) 454d62bc4baSyz147064 return (status); 455d62bc4baSyz147064 } 456d62bc4baSyz147064 457d62bc4baSyz147064 if (linkidp != NULL) 458d62bc4baSyz147064 *linkidp = linkid; 459d62bc4baSyz147064 if (flagp != NULL) { 460d62bc4baSyz147064 *flagp = retval.lr_flags & DLMGMT_ACTIVE ? DLADM_OPT_ACTIVE : 0; 461d62bc4baSyz147064 *flagp |= (retval.lr_flags & DLMGMT_PERSIST) ? 462d62bc4baSyz147064 DLADM_OPT_PERSIST : 0; 463d62bc4baSyz147064 } 464d62bc4baSyz147064 if (classp != NULL) 465d62bc4baSyz147064 *classp = retval.lr_class; 466d62bc4baSyz147064 if (mediap != NULL) 467d62bc4baSyz147064 *mediap = retval.lr_media; 468d62bc4baSyz147064 469d62bc4baSyz147064 return (DLADM_STATUS_OK); 470d62bc4baSyz147064 } 471d62bc4baSyz147064 472d62bc4baSyz147064 /* 473d62bc4baSyz147064 * Get the link name that is associated with the given id. 474d62bc4baSyz147064 */ 475d62bc4baSyz147064 dladm_status_t 4764ac67f02SAnurag S. Maskey dladm_datalink_id2info(dladm_handle_t handle, datalink_id_t linkid, 4774ac67f02SAnurag S. Maskey uint32_t *flagp, datalink_class_t *classp, uint32_t *mediap, char *link, 4784ac67f02SAnurag S. Maskey size_t len) 479d62bc4baSyz147064 { 480d62bc4baSyz147064 dlmgmt_door_getname_t getname; 481d62bc4baSyz147064 dlmgmt_getname_retval_t retval; 482d62bc4baSyz147064 dladm_status_t status; 483d62bc4baSyz147064 484d62bc4baSyz147064 if ((linkid == DATALINK_INVALID_LINKID) || (link != NULL && len == 0) || 485d62bc4baSyz147064 (link == NULL && len != 0)) { 486d62bc4baSyz147064 return (DLADM_STATUS_BADARG); 487d62bc4baSyz147064 } 488d62bc4baSyz147064 489d62bc4baSyz147064 getname.ld_cmd = DLMGMT_CMD_GETNAME; 490d62bc4baSyz147064 getname.ld_linkid = linkid; 4914ac67f02SAnurag S. Maskey if ((status = dladm_door_call(handle, &getname, sizeof (getname), 4924ac67f02SAnurag S. Maskey &retval, sizeof (retval))) != DLADM_STATUS_OK) { 493d62bc4baSyz147064 return (status); 494d62bc4baSyz147064 } 495d62bc4baSyz147064 496024b0a25Sseb if (len != 0 && (strlen(retval.lr_link) + 1 > len)) 497024b0a25Sseb return (DLADM_STATUS_TOOSMALL); 498024b0a25Sseb 499d62bc4baSyz147064 if (retval.lr_class == DATALINK_CLASS_PHYS && 500d62bc4baSyz147064 retval.lr_flags & DLMGMT_ACTIVE) { 501d62bc4baSyz147064 /* 502d62bc4baSyz147064 * An active physical link reported by the dlmgmtd daemon 503d62bc4baSyz147064 * might not be active anymore. Check and set its real status. 504d62bc4baSyz147064 */ 5054ac67f02SAnurag S. Maskey status = i_dladm_phys_status(handle, linkid, &retval.lr_flags); 506d62bc4baSyz147064 if (status != DLADM_STATUS_OK) 507d62bc4baSyz147064 return (status); 508d62bc4baSyz147064 } 509d62bc4baSyz147064 510d62bc4baSyz147064 if (link != NULL) 511d62bc4baSyz147064 (void) strlcpy(link, retval.lr_link, len); 512d62bc4baSyz147064 if (classp != NULL) 513d62bc4baSyz147064 *classp = retval.lr_class; 514d62bc4baSyz147064 if (mediap != NULL) 515d62bc4baSyz147064 *mediap = retval.lr_media; 516d62bc4baSyz147064 if (flagp != NULL) { 517d62bc4baSyz147064 *flagp = retval.lr_flags & DLMGMT_ACTIVE ? 518d62bc4baSyz147064 DLADM_OPT_ACTIVE : 0; 519d62bc4baSyz147064 *flagp |= (retval.lr_flags & DLMGMT_PERSIST) ? 520d62bc4baSyz147064 DLADM_OPT_PERSIST : 0; 521d62bc4baSyz147064 } 522d62bc4baSyz147064 return (DLADM_STATUS_OK); 523d62bc4baSyz147064 } 524d62bc4baSyz147064 525d62bc4baSyz147064 /* 526d62bc4baSyz147064 * Set the given attr with the given attrval for the given link. 527d62bc4baSyz147064 */ 528d62bc4baSyz147064 dladm_status_t 5294ac67f02SAnurag S. Maskey dladm_set_conf_field(dladm_handle_t handle, dladm_conf_t conf, const char *attr, 530d62bc4baSyz147064 dladm_datatype_t type, const void *attrval) 531d62bc4baSyz147064 { 532024b0a25Sseb dlmgmt_door_setattr_t setattr; 533d62bc4baSyz147064 dlmgmt_setattr_retval_t retval; 534024b0a25Sseb size_t attrsz; 535d62bc4baSyz147064 536024b0a25Sseb if (attr == NULL || attrval == NULL) 537d62bc4baSyz147064 return (DLADM_STATUS_BADARG); 538d62bc4baSyz147064 539d62bc4baSyz147064 if (type == DLADM_TYPE_STR) 540d62bc4baSyz147064 attrsz = strlen(attrval) + 1; 541d62bc4baSyz147064 else 542d62bc4baSyz147064 attrsz = dladm_datatype_size[type]; 543d62bc4baSyz147064 544024b0a25Sseb if (attrsz > MAXLINKATTRVALLEN) 545024b0a25Sseb return (DLADM_STATUS_TOOSMALL); 546d62bc4baSyz147064 547024b0a25Sseb setattr.ld_cmd = DLMGMT_CMD_SETATTR; 548024b0a25Sseb setattr.ld_conf = conf; 549024b0a25Sseb (void) strlcpy(setattr.ld_attr, attr, MAXLINKATTRLEN); 550024b0a25Sseb setattr.ld_attrsz = attrsz; 551024b0a25Sseb setattr.ld_type = type; 552024b0a25Sseb bcopy(attrval, &setattr.ld_attrval, attrsz); 553d62bc4baSyz147064 5544ac67f02SAnurag S. Maskey return (dladm_door_call(handle, &setattr, sizeof (setattr), &retval, 5554ac67f02SAnurag S. Maskey sizeof (retval))); 556d62bc4baSyz147064 } 557d62bc4baSyz147064 558d62bc4baSyz147064 /* 559d62bc4baSyz147064 * Unset the given attr the given link. 560d62bc4baSyz147064 */ 561d62bc4baSyz147064 dladm_status_t 5624ac67f02SAnurag S. Maskey dladm_unset_conf_field(dladm_handle_t handle, dladm_conf_t conf, 5634ac67f02SAnurag S. Maskey const char *attr) 564d62bc4baSyz147064 { 565d62bc4baSyz147064 dlmgmt_door_unsetattr_t unsetattr; 566d62bc4baSyz147064 dlmgmt_unsetattr_retval_t retval; 567d62bc4baSyz147064 568024b0a25Sseb if (attr == NULL) 569d62bc4baSyz147064 return (DLADM_STATUS_BADARG); 570d62bc4baSyz147064 571d62bc4baSyz147064 unsetattr.ld_cmd = DLMGMT_CMD_UNSETATTR; 572d62bc4baSyz147064 unsetattr.ld_conf = conf; 573d62bc4baSyz147064 (void) strlcpy(unsetattr.ld_attr, attr, MAXLINKATTRLEN); 574d62bc4baSyz147064 5754ac67f02SAnurag S. Maskey return (dladm_door_call(handle, &unsetattr, sizeof (unsetattr), &retval, 5764ac67f02SAnurag S. Maskey sizeof (retval))); 577d62bc4baSyz147064 } 578d62bc4baSyz147064 579d62bc4baSyz147064 /* 580d62bc4baSyz147064 * Remove the given link ID and its entry from the data link configuration 581d62bc4baSyz147064 * repository. 582d62bc4baSyz147064 */ 583d62bc4baSyz147064 dladm_status_t 5844ac67f02SAnurag S. Maskey dladm_remove_conf(dladm_handle_t handle, datalink_id_t linkid) 585d62bc4baSyz147064 { 586d62bc4baSyz147064 dlmgmt_door_removeconf_t removeconf; 587d62bc4baSyz147064 dlmgmt_removeconf_retval_t retval; 588d62bc4baSyz147064 589d62bc4baSyz147064 removeconf.ld_cmd = DLMGMT_CMD_REMOVECONF; 590d62bc4baSyz147064 removeconf.ld_linkid = linkid; 591d62bc4baSyz147064 5924ac67f02SAnurag S. Maskey return (dladm_door_call(handle, &removeconf, sizeof (removeconf), 593024b0a25Sseb &retval, sizeof (retval))); 594d62bc4baSyz147064 } 595d62bc4baSyz147064 596d62bc4baSyz147064 /* 597d62bc4baSyz147064 * Free the contents of the link structure. 598d62bc4baSyz147064 */ 599d62bc4baSyz147064 void 6004ac67f02SAnurag S. Maskey dladm_destroy_conf(dladm_handle_t handle, dladm_conf_t conf) 601d62bc4baSyz147064 { 602d62bc4baSyz147064 dlmgmt_door_destroyconf_t destroyconf; 603d62bc4baSyz147064 dlmgmt_destroyconf_retval_t retval; 604d62bc4baSyz147064 605d62bc4baSyz147064 if (conf == DLADM_INVALID_CONF) 606d62bc4baSyz147064 return; 607d62bc4baSyz147064 608d62bc4baSyz147064 destroyconf.ld_cmd = DLMGMT_CMD_DESTROYCONF; 609d62bc4baSyz147064 destroyconf.ld_conf = conf; 610d62bc4baSyz147064 6114ac67f02SAnurag S. Maskey (void) dladm_door_call(handle, &destroyconf, sizeof (destroyconf), 612024b0a25Sseb &retval, sizeof (retval)); 613d62bc4baSyz147064 } 6142b24ab6bSSebastien Roy 6152b24ab6bSSebastien Roy dladm_status_t 6162b24ab6bSSebastien Roy dladm_zone_boot(dladm_handle_t handle, zoneid_t zoneid) 6172b24ab6bSSebastien Roy { 6182b24ab6bSSebastien Roy dlmgmt_door_zoneboot_t zoneboot; 6192b24ab6bSSebastien Roy dlmgmt_zoneboot_retval_t retval; 6202b24ab6bSSebastien Roy 6212b24ab6bSSebastien Roy zoneboot.ld_cmd = DLMGMT_CMD_ZONEBOOT; 6222b24ab6bSSebastien Roy zoneboot.ld_zoneid = zoneid; 6232b24ab6bSSebastien Roy return (dladm_door_call(handle, &zoneboot, sizeof (zoneboot), &retval, 6242b24ab6bSSebastien Roy sizeof (retval))); 6252b24ab6bSSebastien Roy } 6262b24ab6bSSebastien Roy 6272b24ab6bSSebastien Roy dladm_status_t 6282b24ab6bSSebastien Roy dladm_zone_halt(dladm_handle_t handle, zoneid_t zoneid) 6292b24ab6bSSebastien Roy { 6302b24ab6bSSebastien Roy dlmgmt_door_zonehalt_t zonehalt; 6312b24ab6bSSebastien Roy dlmgmt_zonehalt_retval_t retval; 6322b24ab6bSSebastien Roy 6332b24ab6bSSebastien Roy zonehalt.ld_cmd = DLMGMT_CMD_ZONEHALT; 6342b24ab6bSSebastien Roy zonehalt.ld_zoneid = zoneid; 6352b24ab6bSSebastien Roy return (dladm_door_call(handle, &zonehalt, sizeof (zonehalt), &retval, 6362b24ab6bSSebastien Roy sizeof (retval))); 6372b24ab6bSSebastien Roy } 638