Print this page

        

*** 19,30 **** * CDDL HEADER END */ /* * Copyright (c) 2003, 2010, Oracle and/or its affiliates. All rights reserved. - * Copyright 2016, Joyent Inc. * Copyright (c) 2015 by Delphix. All rights reserved. */ /* * Copyright 2011 Nexenta Systems, Inc. All rights reserved. */ --- 19,30 ---- * CDDL HEADER END */ /* * Copyright (c) 2003, 2010, Oracle and/or its affiliates. All rights reserved. * Copyright (c) 2015 by Delphix. All rights reserved. + * Copyright 2016, Joyent Inc. */ /* * Copyright 2011 Nexenta Systems, Inc. All rights reserved. */
*** 134,146 **** MNTOPT_RO "," MNTOPT_LOFS_NOSUB "," MNTOPT_NODEVICES #define DFSTYPES "/etc/dfs/fstypes" #define MAXTNZLEN 2048 - /* Number of times to retry unmounting if it fails */ - #define UMOUNT_RETRIES 30 - /* a reasonable estimate for the number of lwps per process */ #define LWPS_PER_PROCESS 10 /* for routing socket */ static int rts_seqno = 0; --- 134,143 ----
*** 178,188 **** /* from libsocket, not in any header file */ extern int getnetmaskbyaddr(struct in_addr, struct in_addr *); /* from zoneadmd */ extern char query_hook[]; - extern char post_statechg_hook[]; /* * For each "net" resource configured in zonecfg, we track a zone_addr_list_t * node in a linked list that is sorted by linkid. The list is constructed as * the xml configuration file is parsed, and the information --- 175,184 ----
*** 215,225 **** autofs_cleanup(zoneid_t zoneid) { /* * Ask autofs to unmount all trigger nodes in the given zone. */ ! return (_autofssys(AUTOFS_UNMOUNTALL, (void *)((uintptr_t)zoneid))); } static void free_mnttable(struct mnttab *mnt_array, uint_t nelem) { --- 211,221 ---- autofs_cleanup(zoneid_t zoneid) { /* * Ask autofs to unmount all trigger nodes in the given zone. */ ! return (_autofssys(AUTOFS_UNMOUNTALL, (void *)zoneid)); } static void free_mnttable(struct mnttab *mnt_array, uint_t nelem) {
*** 606,633 **** resolve_lofs(zlogp, zroot, zrootlen); (void) strcpy(strrchr(zroot, '/') + 1, "lu"); } /* - * Perform brand-specific cleanup if we are unable to unmount a FS. - */ - static void - brand_umount_cleanup(zlog_t *zlogp, char *path) - { - char cmdbuf[2 * MAXPATHLEN]; - - if (post_statechg_hook[0] == '\0') - return; - - if (snprintf(cmdbuf, sizeof (cmdbuf), "%s %d %d %s", post_statechg_hook, - ZONE_STATE_DOWN, Z_UNMOUNT, path) > sizeof (cmdbuf)) - return; - - (void) do_subproc(zlogp, cmdbuf, NULL, B_FALSE); - } - - /* * The general strategy for unmounting filesystems is as follows: * * - Remote filesystems may be dead, and attempting to contact them as * part of a regular unmount may hang forever; we want to always try to * forcibly unmount such filesystems and only fall back to regular --- 602,611 ----
*** 656,666 **** */ static int unmount_filesystems(zlog_t *zlogp, zoneid_t zoneid, boolean_t unmount_cmd) { int error = 0; - int fail = 0; FILE *mnttab; struct mnttab *mnts; uint_t nmnt; char zroot[MAXPATHLEN + 1]; size_t zrootlen; --- 634,643 ----
*** 744,788 **** */ if (stuck) { if (umount2(path, MS_FORCE) == 0) { unmounted = B_TRUE; stuck = B_FALSE; - fail = 0; } else { /* ! * We may hit a failure here if there ! * is an app in the GZ with an open ! * pipe into the zone (commonly into ! * the zone's /var/run). This type ! * of app will notice the closed ! * connection and cleanup, but it may ! * take a while and we have no easy ! * way to notice that. To deal with ! * this case, we will wait and retry ! * a few times before we give up. */ - fail++; - if (fail < (UMOUNT_RETRIES - 1)) { - zerror(zlogp, B_FALSE, - "unable to unmount '%s', " - "retrying in 2 seconds", - path); - (void) sleep(2); - } else if (fail > UMOUNT_RETRIES) { error++; zerror(zlogp, B_FALSE, ! "unmount of '%s' failed", ! path); free_mnttable(mnts, nmnt); goto out; - } else { - /* Try the hook 2 times */ - brand_umount_cleanup(zlogp, - path); } } - } /* * Try regular unmounts for everything else. */ if (!unmounted && umount2(path, 0) != 0) newcount++; --- 721,744 ---- */ if (stuck) { if (umount2(path, MS_FORCE) == 0) { unmounted = B_TRUE; stuck = B_FALSE; } else { /* ! * The first failure indicates a ! * mount we won't be able to get ! * rid of automatically, so we ! * bail. */ error++; zerror(zlogp, B_FALSE, ! "unable to unmount '%s'", path); free_mnttable(mnts, nmnt); goto out; } } /* * Try regular unmounts for everything else. */ if (!unmounted && umount2(path, 0) != 0) newcount++;
*** 1114,1127 **** } int vplat_get_iptype(zlog_t *zlogp, zone_iptype_t *iptypep) { ! if (zonecfg_get_iptype(snap_hndl, iptypep) != Z_OK) { zerror(zlogp, B_FALSE, "invalid ip-type configuration"); return (-1); } return (0); } /* * Apply the standard lists of devices/symlinks/mappings and the user-specified --- 1070,1096 ---- } int vplat_get_iptype(zlog_t *zlogp, zone_iptype_t *iptypep) { ! zone_dochandle_t handle; ! ! if ((handle = zonecfg_init_handle()) == NULL) { ! zerror(zlogp, B_TRUE, "getting zone configuration handle"); ! return (-1); ! } ! if (zonecfg_get_snapshot_handle(zone_name, handle) != Z_OK) { ! zerror(zlogp, B_FALSE, "invalid configuration"); ! zonecfg_fini_handle(handle); ! return (-1); ! } ! if (zonecfg_get_iptype(handle, iptypep) != Z_OK) { zerror(zlogp, B_FALSE, "invalid ip-type configuration"); + zonecfg_fini_handle(handle); return (-1); } + zonecfg_fini_handle(handle); return (0); } /* * Apply the standard lists of devices/symlinks/mappings and the user-specified
*** 1130,1146 **** */ static int mount_one_dev(zlog_t *zlogp, char *devpath, zone_mnt_t mount_cmd) { char brand[MAXNAMELEN]; brand_handle_t bh = NULL; struct zone_devtab ztab; di_prof_t prof = NULL; int err; int retval = -1; zone_iptype_t iptype; ! const char *curr_iptype = NULL; if (di_prof_init(devpath, &prof)) { zerror(zlogp, B_TRUE, "failed to initialize profile"); goto cleanup; } --- 1099,1116 ---- */ static int mount_one_dev(zlog_t *zlogp, char *devpath, zone_mnt_t mount_cmd) { char brand[MAXNAMELEN]; + zone_dochandle_t handle = NULL; brand_handle_t bh = NULL; struct zone_devtab ztab; di_prof_t prof = NULL; int err; int retval = -1; zone_iptype_t iptype; ! const char *curr_iptype; if (di_prof_init(devpath, &prof)) { zerror(zlogp, B_TRUE, "failed to initialize profile"); goto cleanup; }
*** 1171,1182 **** break; case ZS_EXCLUSIVE: curr_iptype = "exclusive"; break; } - if (curr_iptype == NULL) - abort(); if (brand_platform_iter_devices(bh, zone_name, mount_one_dev_device_cb, prof, curr_iptype) != 0) { zerror(zlogp, B_TRUE, "failed to add standard device"); goto cleanup; --- 1141,1150 ----
*** 1187,1209 **** zerror(zlogp, B_TRUE, "failed to add standard symlink"); goto cleanup; } /* Add user-specified devices and directories */ ! if ((err = zonecfg_setdevent(snap_hndl)) != 0) { zerror(zlogp, B_FALSE, "%s: %s", zone_name, zonecfg_strerror(err)); goto cleanup; } ! while (zonecfg_getdevent(snap_hndl, &ztab) == Z_OK) { if (di_prof_add_dev(prof, ztab.zone_dev_match)) { zerror(zlogp, B_TRUE, "failed to add " "user-specified device"); goto cleanup; } } ! (void) zonecfg_enddevent(snap_hndl); /* Send profile to kernel */ if (di_prof_commit(prof)) { zerror(zlogp, B_TRUE, "failed to commit profile"); goto cleanup; --- 1155,1186 ---- zerror(zlogp, B_TRUE, "failed to add standard symlink"); goto cleanup; } /* Add user-specified devices and directories */ ! if ((handle = zonecfg_init_handle()) == NULL) { ! zerror(zlogp, B_FALSE, "can't initialize zone handle"); ! goto cleanup; ! } ! if ((err = zonecfg_get_handle(zone_name, handle)) != 0) { ! zerror(zlogp, B_FALSE, "can't get handle for zone " ! "%s: %s", zone_name, zonecfg_strerror(err)); ! goto cleanup; ! } ! if ((err = zonecfg_setdevent(handle)) != 0) { zerror(zlogp, B_FALSE, "%s: %s", zone_name, zonecfg_strerror(err)); goto cleanup; } ! while (zonecfg_getdevent(handle, &ztab) == Z_OK) { if (di_prof_add_dev(prof, ztab.zone_dev_match)) { zerror(zlogp, B_TRUE, "failed to add " "user-specified device"); goto cleanup; } } ! (void) zonecfg_enddevent(handle); /* Send profile to kernel */ if (di_prof_commit(prof)) { zerror(zlogp, B_TRUE, "failed to commit profile"); goto cleanup;
*** 1212,1221 **** --- 1189,1200 ---- retval = 0; cleanup: if (bh != NULL) brand_close(bh); + if (handle != NULL) + zonecfg_fini_handle(handle); if (prof) di_prof_fini(prof); return (retval); }
*** 1705,1714 **** --- 1684,1694 ---- char rootpath[MAXPATHLEN]; char brand[MAXNAMELEN]; char luroot[MAXPATHLEN]; int i, num_fs = 0; struct zone_fstab *fs_ptr = NULL; + zone_dochandle_t handle = NULL; zone_state_t zstate; brand_handle_t bh; plat_gmount_cb_data_t cb; if (zone_get_state(zone_name, &zstate) != Z_OK ||
*** 1723,1733 **** if (zone_get_rootpath(zone_name, rootpath, sizeof (rootpath)) != Z_OK) { zerror(zlogp, B_TRUE, "unable to determine zone root"); goto bad; } ! if (zonecfg_setfsent(snap_hndl) != Z_OK) { zerror(zlogp, B_FALSE, "invalid configuration"); goto bad; } /* --- 1703,1718 ---- if (zone_get_rootpath(zone_name, rootpath, sizeof (rootpath)) != Z_OK) { zerror(zlogp, B_TRUE, "unable to determine zone root"); goto bad; } ! if ((handle = zonecfg_init_handle()) == NULL) { ! zerror(zlogp, B_TRUE, "getting zone configuration handle"); ! goto bad; ! } ! if (zonecfg_get_snapshot_handle(zone_name, handle) != Z_OK || ! zonecfg_setfsent(handle) != Z_OK) { zerror(zlogp, B_FALSE, "invalid configuration"); goto bad; } /*
*** 1741,1750 **** --- 1726,1736 ---- } /* Get a handle to the brand info for this zone */ if ((bh = brand_open(brand)) == NULL) { zerror(zlogp, B_FALSE, "unable to determine zone brand"); + zonecfg_fini_handle(handle); return (-1); } /* * Get the list of global filesystems to mount from the brand
*** 1755,1764 **** --- 1741,1751 ---- cb.pgcd_num_fs = &num_fs; if (brand_platform_iter_gmounts(bh, zone_name, zonepath, plat_gmount_cb, &cb) != 0) { zerror(zlogp, B_FALSE, "unable to mount filesystems"); brand_close(bh); + zonecfg_fini_handle(handle); return (-1); } brand_close(bh); /*
*** 1765,1778 **** * Iterate through the rest of the filesystems. Sort them all, * then mount them in sorted order. This is to make sure the * higher level directories (e.g., /usr) get mounted before * any beneath them (e.g., /usr/local). */ ! if (mount_filesystems_fsent(snap_hndl, zlogp, &fs_ptr, &num_fs, mount_cmd) != 0) goto bad; /* * Normally when we mount a zone all the zone filesystems * get mounted relative to rootpath, which is usually * <zonepath>/root. But when mounting a zone for administration * purposes via the zone "mount" state, build_mounted_pre_var() --- 1752,1768 ---- * Iterate through the rest of the filesystems. Sort them all, * then mount them in sorted order. This is to make sure the * higher level directories (e.g., /usr) get mounted before * any beneath them (e.g., /usr/local). */ ! if (mount_filesystems_fsent(handle, zlogp, &fs_ptr, &num_fs, mount_cmd) != 0) goto bad; + zonecfg_fini_handle(handle); + handle = NULL; + /* * Normally when we mount a zone all the zone filesystems * get mounted relative to rootpath, which is usually * <zonepath>/root. But when mounting a zone for administration * purposes via the zone "mount" state, build_mounted_pre_var()
*** 1864,1873 **** --- 1854,1865 ---- * Everything looks fine. */ return (0); bad: + if (handle != NULL) + zonecfg_fini_handle(handle); free_fs_data(fs_ptr, num_fs); return (-1); } /* caller makes sure neither parameter is NULL */
*** 2219,2229 **** --- 2211,2227 ---- (void) memset(&lifr.lifr_addr, 0, sizeof (lifr.lifr_addr)); if (ioctl(s, SIOCLIFADDIF, (caddr_t)&lifr) < 0) { /* * Here, we know that the interface can't be brought up. + * A similar warning message was already printed out to + * the console by zoneadm(1M) so instead we log the + * message to syslog and continue. */ + zerror(&logsys, B_TRUE, "WARNING: skipping network interface " + "'%s' which may not be present/plumbed in the " + "global zone.", lifr.lifr_name); (void) close(s); return (Z_OK); } /* Preserve literal IPv4 address for later potential printing. */
*** 2432,2462 **** * whatever we set up, and return an error. */ static int configure_shared_network_interfaces(zlog_t *zlogp) { struct zone_nwiftab nwiftab, loopback_iftab; zoneid_t zoneid; if ((zoneid = getzoneidbyname(zone_name)) == ZONE_ID_UNDEFINED) { zerror(zlogp, B_TRUE, "unable to get zoneid"); return (-1); } ! if (zonecfg_setnwifent(snap_hndl) == Z_OK) { for (;;) { ! if (zonecfg_getnwifent(snap_hndl, &nwiftab) != Z_OK) break; - nwifent_free_attrs(&nwiftab); if (configure_one_interface(zlogp, zoneid, &nwiftab) != Z_OK) { ! (void) zonecfg_endnwifent(snap_hndl); return (-1); } } ! (void) zonecfg_endnwifent(snap_hndl); } if (is_system_labeled()) { /* * Labeled zones share the loopback interface * so it is not plumbed for shared stack instances. */ --- 2430,2471 ---- * whatever we set up, and return an error. */ static int configure_shared_network_interfaces(zlog_t *zlogp) { + zone_dochandle_t handle; struct zone_nwiftab nwiftab, loopback_iftab; zoneid_t zoneid; if ((zoneid = getzoneidbyname(zone_name)) == ZONE_ID_UNDEFINED) { zerror(zlogp, B_TRUE, "unable to get zoneid"); return (-1); } ! if ((handle = zonecfg_init_handle()) == NULL) { ! zerror(zlogp, B_TRUE, "getting zone configuration handle"); ! return (-1); ! } ! if (zonecfg_get_snapshot_handle(zone_name, handle) != Z_OK) { ! zerror(zlogp, B_FALSE, "invalid configuration"); ! zonecfg_fini_handle(handle); ! return (-1); ! } ! if (zonecfg_setnwifent(handle) == Z_OK) { for (;;) { ! if (zonecfg_getnwifent(handle, &nwiftab) != Z_OK) break; if (configure_one_interface(zlogp, zoneid, &nwiftab) != Z_OK) { ! (void) zonecfg_endnwifent(handle); ! zonecfg_fini_handle(handle); return (-1); } } ! (void) zonecfg_endnwifent(handle); } + zonecfg_fini_handle(handle); if (is_system_labeled()) { /* * Labeled zones share the loopback interface * so it is not plumbed for shared stack instances. */
*** 2899,2943 **** free(new); } } /* * Add the kernel access control information for the interface names. * If anything goes wrong, we log a general error message, attempt to tear down * whatever we set up, and return an error. */ static int configure_exclusive_network_interfaces(zlog_t *zlogp, zoneid_t zoneid) { struct zone_nwiftab nwiftab; char rootpath[MAXPATHLEN]; char path[MAXPATHLEN]; datalink_id_t linkid; di_prof_t prof = NULL; boolean_t added = B_FALSE; zone_addr_list_t *zalist = NULL, *new; ! if (zonecfg_setnwifent(snap_hndl) != Z_OK) return (0); for (;;) { ! if (zonecfg_getnwifent(snap_hndl, &nwiftab) != Z_OK) break; - nwifent_free_attrs(&nwiftab); if (prof == NULL) { if (zone_get_devroot(zone_name, rootpath, sizeof (rootpath)) != Z_OK) { ! (void) zonecfg_endnwifent(snap_hndl); zerror(zlogp, B_TRUE, "unable to determine dev root"); return (-1); } (void) snprintf(path, sizeof (path), "%s%s", rootpath, ! "/dev"); if (di_prof_init(path, &prof) != 0) { ! (void) zonecfg_endnwifent(snap_hndl); zerror(zlogp, B_TRUE, "failed to initialize profile"); return (-1); } } --- 2908,2985 ---- free(new); } } /* + * For IP networking, we need to use the illumos-native device tree. For most + * zones, this is $ZONEROOT/dev. For LX ones, it's $ZONEROOT/native/dev. + * Return the appropriate post-$ZONEROOT path. + */ + static char * + get_brand_dev(void) + { + static char *lxpath = "/native/dev"; + /* Cheesy hard-coding of strlen("/native") */ + char *default_path = lxpath + 7; + + /* LX zones are the exception... */ + if (strcmp(brand_name, "lx") == 0) + return (lxpath); + + return (default_path); + } + + /* * Add the kernel access control information for the interface names. * If anything goes wrong, we log a general error message, attempt to tear down * whatever we set up, and return an error. */ static int configure_exclusive_network_interfaces(zlog_t *zlogp, zoneid_t zoneid) { + zone_dochandle_t handle; struct zone_nwiftab nwiftab; char rootpath[MAXPATHLEN]; char path[MAXPATHLEN]; datalink_id_t linkid; di_prof_t prof = NULL; boolean_t added = B_FALSE; zone_addr_list_t *zalist = NULL, *new; ! if ((handle = zonecfg_init_handle()) == NULL) { ! zerror(zlogp, B_TRUE, "getting zone configuration handle"); ! return (-1); ! } ! if (zonecfg_get_snapshot_handle(zone_name, handle) != Z_OK) { ! zerror(zlogp, B_FALSE, "invalid configuration"); ! zonecfg_fini_handle(handle); ! return (-1); ! } ! ! if (zonecfg_setnwifent(handle) != Z_OK) { ! zonecfg_fini_handle(handle); return (0); + } for (;;) { ! if (zonecfg_getnwifent(handle, &nwiftab) != Z_OK) break; if (prof == NULL) { if (zone_get_devroot(zone_name, rootpath, sizeof (rootpath)) != Z_OK) { ! (void) zonecfg_endnwifent(handle); ! zonecfg_fini_handle(handle); zerror(zlogp, B_TRUE, "unable to determine dev root"); return (-1); } (void) snprintf(path, sizeof (path), "%s%s", rootpath, ! get_brand_dev()); if (di_prof_init(path, &prof) != 0) { ! (void) zonecfg_endnwifent(handle); ! zonecfg_fini_handle(handle); zerror(zlogp, B_TRUE, "failed to initialize profile"); return (-1); } }
*** 2957,2994 **** &linkid, NULL, NULL, NULL) == DLADM_STATUS_OK && add_datalink(zlogp, zone_name, linkid, nwiftab.zone_nwif_physical) == 0) { added = B_TRUE; } else { ! /* ! * Failed to add network device, but the brand hook ! * might be doing this for us, so keep silent. ! */ ! continue; } /* set up the new IP interface, and add them all later */ new = malloc(sizeof (*new)); if (new == NULL) { zerror(zlogp, B_TRUE, "no memory for %s", nwiftab.zone_nwif_physical); free_ip_interface(zalist); } bzero(new, sizeof (*new)); new->za_nwiftab = nwiftab; new->za_linkid = linkid; zalist = add_ip_interface(zalist, new); } if (zalist != NULL) { if ((errno = add_net(zlogp, zoneid, zalist)) != 0) { ! (void) zonecfg_endnwifent(snap_hndl); zerror(zlogp, B_TRUE, "failed to add address"); free_ip_interface(zalist); return (-1); } free_ip_interface(zalist); } ! (void) zonecfg_endnwifent(snap_hndl); if (prof != NULL && added) { if (di_prof_commit(prof) != 0) { zerror(zlogp, B_TRUE, "failed to commit profile"); return (-1); --- 2999,3038 ---- &linkid, NULL, NULL, NULL) == DLADM_STATUS_OK && add_datalink(zlogp, zone_name, linkid, nwiftab.zone_nwif_physical) == 0) { added = B_TRUE; } else { ! (void) zonecfg_endnwifent(handle); ! zonecfg_fini_handle(handle); ! zerror(zlogp, B_TRUE, "failed to add network device"); ! return (-1); } /* set up the new IP interface, and add them all later */ new = malloc(sizeof (*new)); if (new == NULL) { zerror(zlogp, B_TRUE, "no memory for %s", nwiftab.zone_nwif_physical); + zonecfg_fini_handle(handle); free_ip_interface(zalist); } bzero(new, sizeof (*new)); new->za_nwiftab = nwiftab; new->za_linkid = linkid; zalist = add_ip_interface(zalist, new); } if (zalist != NULL) { if ((errno = add_net(zlogp, zoneid, zalist)) != 0) { ! (void) zonecfg_endnwifent(handle); ! zonecfg_fini_handle(handle); zerror(zlogp, B_TRUE, "failed to add address"); free_ip_interface(zalist); return (-1); } free_ip_interface(zalist); } ! (void) zonecfg_endnwifent(handle); ! zonecfg_fini_handle(handle); if (prof != NULL && added) { if (di_prof_commit(prof) != 0) { zerror(zlogp, B_TRUE, "failed to commit profile"); return (-1);
*** 3120,3146 **** "protection", NULL, 0, DLADM_OPT_ACTIVE); if (dlstatus == DLADM_STATUS_NOTFOUND) { /* datalink does not belong to the GZ */ continue; } ! if (dlstatus != DLADM_STATUS_OK) zerror(zlogp, B_FALSE, - "clear 'protection' link property: %s", dladm_status2str(dlstatus, dlerr)); ! dlstatus = dladm_set_linkprop(dld_handle, *dllink, "allowed-ips", NULL, 0, DLADM_OPT_ACTIVE); ! if (dlstatus != DLADM_STATUS_OK) zerror(zlogp, B_FALSE, - "clear 'allowed-ips' link property: %s", dladm_status2str(dlstatus, dlerr)); } free(dllinks); return (0); } static int tcp_abort_conn(zlog_t *zlogp, zoneid_t zoneid, const struct sockaddr_storage *local, const struct sockaddr_storage *remote) { int fd; struct strioctl ioc; --- 3164,3215 ---- "protection", NULL, 0, DLADM_OPT_ACTIVE); if (dlstatus == DLADM_STATUS_NOTFOUND) { /* datalink does not belong to the GZ */ continue; } ! if (dlstatus != DLADM_STATUS_OK) { zerror(zlogp, B_FALSE, dladm_status2str(dlstatus, dlerr)); ! free(dllinks); ! return (-1); ! } dlstatus = dladm_set_linkprop(dld_handle, *dllink, "allowed-ips", NULL, 0, DLADM_OPT_ACTIVE); ! if (dlstatus != DLADM_STATUS_OK) { zerror(zlogp, B_FALSE, dladm_status2str(dlstatus, dlerr)); + free(dllinks); + return (-1); } + } free(dllinks); return (0); } static int + unconfigure_exclusive_network_interfaces(zlog_t *zlogp, zoneid_t zoneid) + { + int dlnum = 0; + + /* + * The kernel shutdown callback for the dls module should have removed + * all datalinks from this zone. If any remain, then there's a + * problem. + */ + if (zone_list_datalink(zoneid, &dlnum, NULL) != 0) { + zerror(zlogp, B_TRUE, "unable to list network interfaces"); + return (-1); + } + if (dlnum != 0) { + zerror(zlogp, B_FALSE, + "datalinks remain in zone after shutdown"); + return (-1); + } + return (0); + } + + static int tcp_abort_conn(zlog_t *zlogp, zoneid_t zoneid, const struct sockaddr_storage *local, const struct sockaddr_storage *remote) { int fd; struct strioctl ioc;
*** 3218,3235 **** static int get_privset(zlog_t *zlogp, priv_set_t *privs, zone_mnt_t mount_cmd) { int error = -1; char *privname = NULL; if (ALT_MOUNT(mount_cmd)) { zone_iptype_t iptype; ! const char *curr_iptype = NULL; ! if (zonecfg_get_iptype(snap_hndl, &iptype) != Z_OK) { zerror(zlogp, B_TRUE, "unable to determine ip-type"); return (-1); } switch (iptype) { case ZS_SHARED: --- 3287,3316 ---- static int get_privset(zlog_t *zlogp, priv_set_t *privs, zone_mnt_t mount_cmd) { int error = -1; + zone_dochandle_t handle; char *privname = NULL; + if ((handle = zonecfg_init_handle()) == NULL) { + zerror(zlogp, B_TRUE, "getting zone configuration handle"); + return (-1); + } + if (zonecfg_get_snapshot_handle(zone_name, handle) != Z_OK) { + zerror(zlogp, B_FALSE, "invalid configuration"); + zonecfg_fini_handle(handle); + return (-1); + } + if (ALT_MOUNT(mount_cmd)) { zone_iptype_t iptype; ! const char *curr_iptype; ! if (zonecfg_get_iptype(handle, &iptype) != Z_OK) { zerror(zlogp, B_TRUE, "unable to determine ip-type"); + zonecfg_fini_handle(handle); return (-1); } switch (iptype) { case ZS_SHARED:
*** 3238,3256 **** case ZS_EXCLUSIVE: curr_iptype = "exclusive"; break; } ! if (zonecfg_default_privset(privs, curr_iptype) == Z_OK) return (0); ! zerror(zlogp, B_FALSE, "failed to determine the zone's default privilege set"); return (-1); } ! switch (zonecfg_get_privset(snap_hndl, privs, &privname)) { case Z_OK: error = 0; break; case Z_PRIV_PROHIBITED: zerror(zlogp, B_FALSE, "privilege \"%s\" is not permitted " --- 3319,3339 ---- case ZS_EXCLUSIVE: curr_iptype = "exclusive"; break; } ! if (zonecfg_default_privset(privs, curr_iptype) == Z_OK) { ! zonecfg_fini_handle(handle); return (0); ! } zerror(zlogp, B_FALSE, "failed to determine the zone's default privilege set"); + zonecfg_fini_handle(handle); return (-1); } ! switch (zonecfg_get_privset(handle, privs, &privname)) { case Z_OK: error = 0; break; case Z_PRIV_PROHIBITED: zerror(zlogp, B_FALSE, "privilege \"%s\" is not permitted "
*** 3269,3278 **** --- 3352,3362 ---- "privilege set"); break; } free(privname); + zonecfg_fini_handle(handle); return (error); } static char * zone_proj_rctl(const char *name)
*** 3294,3312 **** --- 3378,3407 ---- char *nvl_packed = NULL; size_t nvl_size = 0; nvlist_t **nvlv = NULL; int rctlcount = 0; int error = -1; + zone_dochandle_t handle; struct zone_rctltab rctltab; rctlblk_t *rctlblk = NULL; uint64_t maxlwps; uint64_t maxprocs; int rproc, rlwp; *bufp = NULL; *bufsizep = 0; + if ((handle = zonecfg_init_handle()) == NULL) { + zerror(zlogp, B_TRUE, "getting zone configuration handle"); + return (-1); + } + if (zonecfg_get_snapshot_handle(zone_name, handle) != Z_OK) { + zerror(zlogp, B_FALSE, "invalid configuration"); + zonecfg_fini_handle(handle); + return (-1); + } + rctltab.zone_rctl_valptr = NULL; if (nvlist_alloc(&nvl, NV_UNIQUE_NAME, 0) != 0) { zerror(zlogp, B_TRUE, "%s failed", "nvlist_alloc"); goto out; }
*** 3335,3354 **** "unable to set max-processes alias"); goto out; } } ! if (zonecfg_setrctlent(snap_hndl) != Z_OK) { zerror(zlogp, B_FALSE, "%s failed", "zonecfg_setrctlent"); goto out; } if ((rctlblk = malloc(rctlblk_size())) == NULL) { zerror(zlogp, B_TRUE, "memory allocation failed"); goto out; } ! while (zonecfg_getrctlent(snap_hndl, &rctltab) == Z_OK) { struct zone_rctlvaltab *rctlval; uint_t i, count; const char *name = rctltab.zone_rctl_name; char *proj_nm; --- 3430,3449 ---- "unable to set max-processes alias"); goto out; } } ! if (zonecfg_setrctlent(handle) != Z_OK) { zerror(zlogp, B_FALSE, "%s failed", "zonecfg_setrctlent"); goto out; } if ((rctlblk = malloc(rctlblk_size())) == NULL) { zerror(zlogp, B_TRUE, "memory allocation failed"); goto out; } ! while (zonecfg_getrctlent(handle, &rctltab) == Z_OK) { struct zone_rctlvaltab *rctlval; uint_t i, count; const char *name = rctltab.zone_rctl_name; char *proj_nm;
*** 3447,3457 **** nvlist_free(nvlv[i]); free(nvlv); nvlv = NULL; rctlcount++; } ! (void) zonecfg_endrctlent(snap_hndl); if (rctlcount == 0) { error = 0; goto out; } --- 3542,3552 ---- nvlist_free(nvlv[i]); free(nvlv); nvlv = NULL; rctlcount++; } ! (void) zonecfg_endrctlent(handle); if (rctlcount == 0) { error = 0; goto out; }
*** 3471,3480 **** --- 3566,3577 ---- if (error && nvl_packed != NULL) free(nvl_packed); nvlist_free(nvl); if (nvlv != NULL) free(nvlv); + if (handle != NULL) + zonecfg_fini_handle(handle); return (error); } static int get_implicit_datasets(zlog_t *zlogp, char **retstr)
*** 3486,3504 **** if (snprintf(cmdbuf, sizeof (cmdbuf), "%s datasets", query_hook) > sizeof (cmdbuf)) return (-1); ! if (do_subproc(zlogp, cmdbuf, retstr, B_FALSE) != 0) return (-1); return (0); } static int get_datasets(zlog_t *zlogp, char **bufp, size_t *bufsizep) { struct zone_dstab dstab; size_t total, offset, len; int error = -1; char *str = NULL; char *implicit_datasets = NULL; --- 3583,3602 ---- if (snprintf(cmdbuf, sizeof (cmdbuf), "%s datasets", query_hook) > sizeof (cmdbuf)) return (-1); ! if (do_subproc(zlogp, cmdbuf, retstr) != 0) return (-1); return (0); } static int get_datasets(zlog_t *zlogp, char **bufp, size_t *bufsizep) { + zone_dochandle_t handle; struct zone_dstab dstab; size_t total, offset, len; int error = -1; char *str = NULL; char *implicit_datasets = NULL;
*** 3505,3528 **** int implicit_len = 0; *bufp = NULL; *bufsizep = 0; if (get_implicit_datasets(zlogp, &implicit_datasets) != 0) { zerror(zlogp, B_FALSE, "getting implicit datasets failed"); goto out; } ! if (zonecfg_setdsent(snap_hndl) != Z_OK) { zerror(zlogp, B_FALSE, "%s failed", "zonecfg_setdsent"); goto out; } total = 0; ! while (zonecfg_getdsent(snap_hndl, &dstab) == Z_OK) total += strlen(dstab.zone_dataset_name) + 1; ! (void) zonecfg_enddsent(snap_hndl); if (implicit_datasets != NULL) implicit_len = strlen(implicit_datasets); if (implicit_len > 0) total += implicit_len + 1; --- 3603,3636 ---- int implicit_len = 0; *bufp = NULL; *bufsizep = 0; + if ((handle = zonecfg_init_handle()) == NULL) { + zerror(zlogp, B_TRUE, "getting zone configuration handle"); + return (-1); + } + if (zonecfg_get_snapshot_handle(zone_name, handle) != Z_OK) { + zerror(zlogp, B_FALSE, "invalid configuration"); + zonecfg_fini_handle(handle); + return (-1); + } + if (get_implicit_datasets(zlogp, &implicit_datasets) != 0) { zerror(zlogp, B_FALSE, "getting implicit datasets failed"); goto out; } ! if (zonecfg_setdsent(handle) != Z_OK) { zerror(zlogp, B_FALSE, "%s failed", "zonecfg_setdsent"); goto out; } total = 0; ! while (zonecfg_getdsent(handle, &dstab) == Z_OK) total += strlen(dstab.zone_dataset_name) + 1; ! (void) zonecfg_enddsent(handle); if (implicit_datasets != NULL) implicit_len = strlen(implicit_datasets); if (implicit_len > 0) total += implicit_len + 1;
*** 3535,3558 **** if ((str = malloc(total)) == NULL) { zerror(zlogp, B_TRUE, "memory allocation failed"); goto out; } ! if (zonecfg_setdsent(snap_hndl) != Z_OK) { zerror(zlogp, B_FALSE, "%s failed", "zonecfg_setdsent"); goto out; } offset = 0; ! while (zonecfg_getdsent(snap_hndl, &dstab) == Z_OK) { len = strlen(dstab.zone_dataset_name); (void) strlcpy(str + offset, dstab.zone_dataset_name, total - offset); offset += len; if (offset < total - 1) str[offset++] = ','; } ! (void) zonecfg_enddsent(snap_hndl); if (implicit_len > 0) (void) strlcpy(str + offset, implicit_datasets, total - offset); error = 0; --- 3643,3666 ---- if ((str = malloc(total)) == NULL) { zerror(zlogp, B_TRUE, "memory allocation failed"); goto out; } ! if (zonecfg_setdsent(handle) != Z_OK) { zerror(zlogp, B_FALSE, "%s failed", "zonecfg_setdsent"); goto out; } offset = 0; ! while (zonecfg_getdsent(handle, &dstab) == Z_OK) { len = strlen(dstab.zone_dataset_name); (void) strlcpy(str + offset, dstab.zone_dataset_name, total - offset); offset += len; if (offset < total - 1) str[offset++] = ','; } ! (void) zonecfg_enddsent(handle); if (implicit_len > 0) (void) strlcpy(str + offset, implicit_datasets, total - offset); error = 0;
*** 3560,3598 **** *bufsizep = total; out: if (error != 0 && str != NULL) free(str); if (implicit_datasets != NULL) free(implicit_datasets); return (error); } static int validate_datasets(zlog_t *zlogp) { struct zone_dstab dstab; zfs_handle_t *zhp; libzfs_handle_t *hdl; ! if (zonecfg_setdsent(snap_hndl) != Z_OK) { zerror(zlogp, B_FALSE, "invalid configuration"); return (-1); } if ((hdl = libzfs_init()) == NULL) { zerror(zlogp, B_FALSE, "opening ZFS library"); return (-1); } ! while (zonecfg_getdsent(snap_hndl, &dstab) == Z_OK) { if ((zhp = zfs_open(hdl, dstab.zone_dataset_name, ZFS_TYPE_FILESYSTEM)) == NULL) { zerror(zlogp, B_FALSE, "cannot open ZFS dataset '%s'", dstab.zone_dataset_name); libzfs_fini(hdl); return (-1); } /* --- 3668,3722 ---- *bufsizep = total; out: if (error != 0 && str != NULL) free(str); + if (handle != NULL) + zonecfg_fini_handle(handle); if (implicit_datasets != NULL) free(implicit_datasets); return (error); } static int validate_datasets(zlog_t *zlogp) { + zone_dochandle_t handle; struct zone_dstab dstab; zfs_handle_t *zhp; libzfs_handle_t *hdl; ! if ((handle = zonecfg_init_handle()) == NULL) { ! zerror(zlogp, B_TRUE, "getting zone configuration handle"); ! return (-1); ! } ! if (zonecfg_get_snapshot_handle(zone_name, handle) != Z_OK) { zerror(zlogp, B_FALSE, "invalid configuration"); + zonecfg_fini_handle(handle); return (-1); } + if (zonecfg_setdsent(handle) != Z_OK) { + zerror(zlogp, B_FALSE, "invalid configuration"); + zonecfg_fini_handle(handle); + return (-1); + } + if ((hdl = libzfs_init()) == NULL) { zerror(zlogp, B_FALSE, "opening ZFS library"); + zonecfg_fini_handle(handle); return (-1); } ! while (zonecfg_getdsent(handle, &dstab) == Z_OK) { if ((zhp = zfs_open(hdl, dstab.zone_dataset_name, ZFS_TYPE_FILESYSTEM)) == NULL) { zerror(zlogp, B_FALSE, "cannot open ZFS dataset '%s'", dstab.zone_dataset_name); + zonecfg_fini_handle(handle); libzfs_fini(hdl); return (-1); } /*
*** 3603,3621 **** zfs_prop_set(zhp, zfs_prop_to_name(ZFS_PROP_ZONED), "on") != 0) { zerror(zlogp, B_FALSE, "cannot set 'zoned' " "property for ZFS dataset '%s'\n", dstab.zone_dataset_name); zfs_close(zhp); libzfs_fini(hdl); return (-1); } zfs_close(zhp); } ! (void) zonecfg_enddsent(snap_hndl); libzfs_fini(hdl); return (0); } --- 3727,3747 ---- zfs_prop_set(zhp, zfs_prop_to_name(ZFS_PROP_ZONED), "on") != 0) { zerror(zlogp, B_FALSE, "cannot set 'zoned' " "property for ZFS dataset '%s'\n", dstab.zone_dataset_name); + zonecfg_fini_handle(handle); zfs_close(zhp); libzfs_fini(hdl); return (-1); } zfs_close(zhp); } ! (void) zonecfg_enddsent(handle); + zonecfg_fini_handle(handle); libzfs_fini(hdl); return (0); }
*** 4348,4361 **** setup_zone_rm(zlog_t *zlogp, char *zone_name, zoneid_t zoneid) { int res; uint64_t tmp; char sched[MAXNAMELEN]; char pool_err[128]; /* Get the scheduling class set in the zone configuration. */ ! if (zonecfg_get_sched_class(snap_hndl, sched, sizeof (sched)) == Z_OK && strlen(sched) > 0) { if (zone_setattr(zoneid, ZONE_ATTR_SCHED_CLASS, sched, strlen(sched)) == -1) zerror(zlogp, B_TRUE, "WARNING: unable to set the " "default scheduling class"); --- 4474,4499 ---- setup_zone_rm(zlog_t *zlogp, char *zone_name, zoneid_t zoneid) { int res; uint64_t tmp; char sched[MAXNAMELEN]; + zone_dochandle_t handle = NULL; char pool_err[128]; + if ((handle = zonecfg_init_handle()) == NULL) { + zerror(zlogp, B_TRUE, "getting zone configuration handle"); + return (Z_BAD_HANDLE); + } + + if ((res = zonecfg_get_snapshot_handle(zone_name, handle)) != Z_OK) { + zerror(zlogp, B_FALSE, "invalid configuration"); + zonecfg_fini_handle(handle); + return (res); + } + /* Get the scheduling class set in the zone configuration. */ ! if (zonecfg_get_sched_class(handle, sched, sizeof (sched)) == Z_OK && strlen(sched) > 0) { if (zone_setattr(zoneid, ZONE_ATTR_SCHED_CLASS, sched, strlen(sched)) == -1) zerror(zlogp, B_TRUE, "WARNING: unable to set the " "default scheduling class");
*** 4396,4406 **** * in by default so we can print a warning and modify the class * if we wouldn't be using FSS. */ char class_name[PC_CLNMSZ]; ! if (zonecfg_get_dflt_sched_class(snap_hndl, class_name, sizeof (class_name)) != Z_OK) { zerror(zlogp, B_FALSE, "WARNING: unable to determine " "the zone's scheduling class"); } else if (strcmp("FSS", class_name) != 0) { --- 4534,4544 ---- * in by default so we can print a warning and modify the class * if we wouldn't be using FSS. */ char class_name[PC_CLNMSZ]; ! if (zonecfg_get_dflt_sched_class(handle, class_name, sizeof (class_name)) != Z_OK) { zerror(zlogp, B_FALSE, "WARNING: unable to determine " "the zone's scheduling class"); } else if (strcmp("FSS", class_name) != 0) {
*** 4429,4464 **** * If we are rebooting we want to attempt to reuse any temporary pool * that was previously set up. zonecfg_bind_tmp_pool() will do the * right thing in all cases (reuse or create) based on the current * zonecfg. */ ! if ((res = zonecfg_bind_tmp_pool(snap_hndl, zoneid, pool_err, sizeof (pool_err))) != Z_OK) { if (res == Z_POOL || res == Z_POOL_CREATE || res == Z_POOL_BIND) zerror(zlogp, B_FALSE, "%s: %s\ndedicated-cpu setting " "cannot be instantiated", zonecfg_strerror(res), pool_err); else zerror(zlogp, B_FALSE, "could not bind zone to " "temporary pool: %s", zonecfg_strerror(res)); return (Z_POOL_BIND); } /* * Check if we need to warn about poold not being enabled. */ ! if (zonecfg_warn_poold(snap_hndl)) { zerror(zlogp, B_FALSE, "WARNING: A range of dedicated-cpus has " "been specified\nbut the dynamic pool service is not " "enabled.\nThe system will not dynamically adjust the\n" "processor allocation within the specified range\n" "until svc:/system/pools/dynamic is enabled.\n" "See poold(1M)."); } /* The following is a warning, not an error. */ ! if ((res = zonecfg_bind_pool(snap_hndl, zoneid, pool_err, sizeof (pool_err))) != Z_OK) { if (res == Z_POOL_BIND) zerror(zlogp, B_FALSE, "WARNING: unable to bind to " "pool '%s'; using default pool.", pool_err); else if (res == Z_POOL) --- 4567,4603 ---- * If we are rebooting we want to attempt to reuse any temporary pool * that was previously set up. zonecfg_bind_tmp_pool() will do the * right thing in all cases (reuse or create) based on the current * zonecfg. */ ! if ((res = zonecfg_bind_tmp_pool(handle, zoneid, pool_err, sizeof (pool_err))) != Z_OK) { if (res == Z_POOL || res == Z_POOL_CREATE || res == Z_POOL_BIND) zerror(zlogp, B_FALSE, "%s: %s\ndedicated-cpu setting " "cannot be instantiated", zonecfg_strerror(res), pool_err); else zerror(zlogp, B_FALSE, "could not bind zone to " "temporary pool: %s", zonecfg_strerror(res)); + zonecfg_fini_handle(handle); return (Z_POOL_BIND); } /* * Check if we need to warn about poold not being enabled. */ ! if (zonecfg_warn_poold(handle)) { zerror(zlogp, B_FALSE, "WARNING: A range of dedicated-cpus has " "been specified\nbut the dynamic pool service is not " "enabled.\nThe system will not dynamically adjust the\n" "processor allocation within the specified range\n" "until svc:/system/pools/dynamic is enabled.\n" "See poold(1M)."); } /* The following is a warning, not an error. */ ! if ((res = zonecfg_bind_pool(handle, zoneid, pool_err, sizeof (pool_err))) != Z_OK) { if (res == Z_POOL_BIND) zerror(zlogp, B_FALSE, "WARNING: unable to bind to " "pool '%s'; using default pool.", pool_err); else if (res == Z_POOL)
*** 4468,4480 **** zerror(zlogp, B_FALSE, "WARNING: %s", zonecfg_strerror(res)); } /* Update saved pool name in case it has changed */ ! (void) zonecfg_get_poolname(snap_hndl, zone_name, pool_name, sizeof (pool_name)); return (Z_OK); } static void report_prop_err(zlog_t *zlogp, const char *name, const char *value, int res) --- 4607,4620 ---- zerror(zlogp, B_FALSE, "WARNING: %s", zonecfg_strerror(res)); } /* Update saved pool name in case it has changed */ ! (void) zonecfg_get_poolname(handle, zone_name, pool_name, sizeof (pool_name)); + zonecfg_fini_handle(handle); return (Z_OK); } static void report_prop_err(zlog_t *zlogp, const char *name, const char *value, int res)
*** 4571,4602 **** return (Z_OK); } static int ! setup_zone_attrs(zlog_t *zlogp, zoneid_t zoneid) { int res = Z_OK; ! if ((res = setup_zone_hostid(snap_hndl, zlogp, zoneid)) != Z_OK) goto out; ! if ((res = setup_zone_fs_allowed(snap_hndl, zlogp, zoneid)) != Z_OK) goto out; out: return (res); } - /* - * The zone_did is a persistent debug ID. Each zone should have a unique ID - * in the kernel. This is used for things like DTrace which want to monitor - * zones across reboots. They can't use the zoneid since that changes on - * each boot. - */ zoneid_t ! vplat_create(zlog_t *zlogp, zone_mnt_t mount_cmd, zoneid_t zone_did) { zoneid_t rval = -1; priv_set_t *privs; char rootpath[MAXPATHLEN]; char *rctlbuf = NULL; --- 4711,4747 ---- return (Z_OK); } static int ! setup_zone_attrs(zlog_t *zlogp, char *zone_namep, zoneid_t zoneid) { + zone_dochandle_t handle; int res = Z_OK; ! if ((handle = zonecfg_init_handle()) == NULL) { ! zerror(zlogp, B_TRUE, "getting zone configuration handle"); ! return (Z_BAD_HANDLE); ! } ! if ((res = zonecfg_get_snapshot_handle(zone_namep, handle)) != Z_OK) { ! zerror(zlogp, B_FALSE, "invalid configuration"); goto out; + } ! if ((res = setup_zone_hostid(handle, zlogp, zoneid)) != Z_OK) goto out; + if ((res = setup_zone_fs_allowed(handle, zlogp, zoneid)) != Z_OK) + goto out; + out: + zonecfg_fini_handle(handle); return (res); } zoneid_t ! vplat_create(zlog_t *zlogp, zone_mnt_t mount_cmd) { zoneid_t rval = -1; priv_set_t *privs; char rootpath[MAXPATHLEN]; char *rctlbuf = NULL;
*** 4608,4618 **** char *kzone; FILE *fp = NULL; tsol_zcent_t *zcent = NULL; int match = 0; int doi = 0; ! int flags = -1; zone_iptype_t iptype; if (zone_get_rootpath(zone_name, rootpath, sizeof (rootpath)) != Z_OK) { zerror(zlogp, B_TRUE, "unable to determine zone root"); return (-1); --- 4753,4763 ---- char *kzone; FILE *fp = NULL; tsol_zcent_t *zcent = NULL; int match = 0; int doi = 0; ! int flags; zone_iptype_t iptype; if (zone_get_rootpath(zone_name, rootpath, sizeof (rootpath)) != Z_OK) { zerror(zlogp, B_TRUE, "unable to determine zone root"); return (-1);
*** 4630,4641 **** break; case ZS_EXCLUSIVE: flags = ZCF_NET_EXCL; break; } - if (flags == -1) - abort(); if ((privs = priv_allocset()) == NULL) { zerror(zlogp, B_TRUE, "%s failed", "priv_allocset"); return (-1); } --- 4775,4784 ----
*** 4735,4745 **** } xerr = 0; if ((zoneid = zone_create(kzone, rootpath, privs, rctlbuf, rctlbufsz, zfsbuf, zfsbufsz, &xerr, match, doi, zlabel, ! flags, zone_did)) == -1) { if (xerr == ZE_AREMOUNTS) { if (zonecfg_find_mounts(rootpath, NULL, NULL) < 1) { zerror(zlogp, B_FALSE, "An unknown file-system is mounted on " "a subdirectory of %s", rootpath); --- 4878,4888 ---- } xerr = 0; if ((zoneid = zone_create(kzone, rootpath, privs, rctlbuf, rctlbufsz, zfsbuf, zfsbufsz, &xerr, match, doi, zlabel, ! flags)) == -1) { if (xerr == ZE_AREMOUNTS) { if (zonecfg_find_mounts(rootpath, NULL, NULL) < 1) { zerror(zlogp, B_FALSE, "An unknown file-system is mounted on " "a subdirectory of %s", rootpath);
*** 4781,4791 **** if (mount_cmd == Z_MNT_BOOT) { brand_handle_t bh; struct brand_attr attr; char modname[MAXPATHLEN]; ! if (setup_zone_attrs(zlogp, zoneid) != Z_OK) goto error; if ((bh = brand_open(brand_name)) == NULL) { zerror(zlogp, B_FALSE, "unable to determine brand name"); --- 4924,4934 ---- if (mount_cmd == Z_MNT_BOOT) { brand_handle_t bh; struct brand_attr attr; char modname[MAXPATHLEN]; ! if (setup_zone_attrs(zlogp, zone_name, zoneid) != Z_OK) goto error; if ((bh = brand_open(brand_name)) == NULL) { zerror(zlogp, B_FALSE, "unable to determine brand name");
*** 4839,4850 **** (void) zone_shutdown(zoneid); (void) zone_destroy(zoneid); } if (rctlbuf != NULL) free(rctlbuf); - if (zfsbuf != NULL) - free(zfsbuf); priv_freeset(privs); if (fp != NULL) zonecfg_close_scratch(fp); lofs_discard_mnttab(); if (zcent != NULL) --- 4982,4991 ----
*** 4979,4990 **** 0) { lofs_discard_mnttab(); return (-1); } break; - default: - abort(); } } write_index_file(zoneid); --- 5120,5129 ----
*** 5056,5067 **** return (0); } } int ! vplat_teardown(zlog_t *zlogp, boolean_t unmount_cmd, boolean_t rebooting, ! boolean_t debug) { char *kzone; zoneid_t zoneid; int res; char pool_err[128]; --- 5195,5205 ---- return (0); } } int ! vplat_teardown(zlog_t *zlogp, boolean_t unmount_cmd, boolean_t rebooting) { char *kzone; zoneid_t zoneid; int res; char pool_err[128];
*** 5095,5110 **** if (unmount_cmd) (void) lu_root_teardown(zlogp); goto error; } ! if (remove_datalink_pool(zlogp, zoneid) != 0) zerror(zlogp, B_FALSE, "unable clear datalink pool property"); ! if (remove_datalink_protect(zlogp, zoneid) != 0) zerror(zlogp, B_FALSE, "unable clear datalink protect property"); /* * The datalinks assigned to the zone will be removed from the NGZ as * part of zone_shutdown() so that we need to remove protect/pool etc. * before zone_shutdown(). Even if the shutdown itself fails, the zone --- 5233,5252 ---- if (unmount_cmd) (void) lu_root_teardown(zlogp); goto error; } ! if (remove_datalink_pool(zlogp, zoneid) != 0) { zerror(zlogp, B_FALSE, "unable clear datalink pool property"); + goto error; + } ! if (remove_datalink_protect(zlogp, zoneid) != 0) { zerror(zlogp, B_FALSE, "unable clear datalink protect property"); + goto error; + } /* * The datalinks assigned to the zone will be removed from the NGZ as * part of zone_shutdown() so that we need to remove protect/pool etc. * before zone_shutdown(). Even if the shutdown itself fails, the zone
*** 5134,5144 **** goto error; } brand_close(bh); if ((strlen(cmdbuf) > EXEC_LEN) && ! (do_subproc(zlogp, cmdbuf, NULL, debug) != Z_OK)) { zerror(zlogp, B_FALSE, "%s failed", cmdbuf); goto error; } if (!unmount_cmd) { --- 5276,5286 ---- goto error; } brand_close(bh); if ((strlen(cmdbuf) > EXEC_LEN) && ! (do_subproc(zlogp, cmdbuf, NULL) != Z_OK)) { zerror(zlogp, B_FALSE, "%s failed", cmdbuf); goto error; } if (!unmount_cmd) {
*** 5166,5175 **** --- 5308,5323 ---- "network interfaces in zone"); goto error; } break; case ZS_EXCLUSIVE: + if (unconfigure_exclusive_network_interfaces(zlogp, + zoneid) != 0) { + zerror(zlogp, B_FALSE, "unable to unconfigure " + "network interfaces in zone"); + goto error; + } status = dladm_zone_halt(dld_handle, zoneid); if (status != DLADM_STATUS_OK) { zerror(zlogp, B_FALSE, "unable to notify " "dlmgmtd of zone halt: %s", dladm_status2str(status, errmsg));
*** 5202,5214 **** if (!unmount_cmd) { boolean_t destroy_tmp_pool = B_TRUE; if (rebooting) { struct zone_psettab pset_tab; ! if (zonecfg_lookup_pset(snap_hndl, &pset_tab) == Z_OK) destroy_tmp_pool = B_FALSE; } if (destroy_tmp_pool) { if ((res = zonecfg_destroy_tmp_pool(zone_name, pool_err, sizeof (pool_err))) != Z_OK) { --- 5350,5367 ---- if (!unmount_cmd) { boolean_t destroy_tmp_pool = B_TRUE; if (rebooting) { struct zone_psettab pset_tab; + zone_dochandle_t handle; ! if ((handle = zonecfg_init_handle()) != NULL && ! zonecfg_get_handle(zone_name, handle) == Z_OK && ! zonecfg_lookup_pset(handle, &pset_tab) == Z_OK) destroy_tmp_pool = B_FALSE; + + zonecfg_fini_handle(handle); } if (destroy_tmp_pool) { if ((res = zonecfg_destroy_tmp_pool(zone_name, pool_err, sizeof (pool_err))) != Z_OK) {