275c9da86e89f8abf71135cf63d9fc23671b2e60eschrock * CDDL HEADER START
275c9da86e89f8abf71135cf63d9fc23671b2e60eschrock * The contents of this file are subject to the terms of the
275c9da86e89f8abf71135cf63d9fc23671b2e60eschrock * Common Development and Distribution License (the "License").
275c9da86e89f8abf71135cf63d9fc23671b2e60eschrock * You may not use this file except in compliance with the License.
275c9da86e89f8abf71135cf63d9fc23671b2e60eschrock * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE
275c9da86e89f8abf71135cf63d9fc23671b2e60eschrock * See the License for the specific language governing permissions
275c9da86e89f8abf71135cf63d9fc23671b2e60eschrock * and limitations under the License.
275c9da86e89f8abf71135cf63d9fc23671b2e60eschrock * When distributing Covered Code, include this CDDL HEADER in each
275c9da86e89f8abf71135cf63d9fc23671b2e60eschrock * file and include the License file at usr/src/OPENSOLARIS.LICENSE.
275c9da86e89f8abf71135cf63d9fc23671b2e60eschrock * If applicable, add the following below this CDDL HEADER, with the
275c9da86e89f8abf71135cf63d9fc23671b2e60eschrock * fields enclosed by brackets "[]" replaced with your own identifying
275c9da86e89f8abf71135cf63d9fc23671b2e60eschrock * information: Portions Copyright [yyyy] [name of copyright owner]
275c9da86e89f8abf71135cf63d9fc23671b2e60eschrock * CDDL HEADER END
ac88567a7a5bb7f01cf22cf366bc9d6203e24d7aHyon Kim * Copyright (c) 2008, 2010, Oracle and/or its affiliates. All rights reserved.
275c9da86e89f8abf71135cf63d9fc23671b2e60eschrock ((eip)->st_hdr.sehi_ed_len + sizeof (ses2_ed_hdr_impl_t))))
c4800545504378963d9f2eeb253f06899664f9f6jmcp * ses_snap_primary_enclosure() finds the primary enclosure for
c4800545504378963d9f2eeb253f06899664f9f6jmcp * the supplied ses_snap_t.
275c9da86e89f8abf71135cf63d9fc23671b2e60eschrock if (nvlist_alloc(&np->sn_props, NV_UNIQUE_NAME, 0) != 0)
275c9da86e89f8abf71135cf63d9fc23671b2e60eschrock * Parse element type descriptor.
275c9da86e89f8abf71135cf63d9fc23671b2e60eschrockelem_parse_td(ses2_td_hdr_impl_t *tip, const char *tp, nvlist_t *nvl)
275c9da86e89f8abf71135cf63d9fc23671b2e60eschrock SES_NV_ADD(fixed_string, nverr, nvl, SES_PROP_CLASS_DESCRIPTION,
275c9da86e89f8abf71135cf63d9fc23671b2e60eschrock return (0);
275c9da86e89f8abf71135cf63d9fc23671b2e60eschrock * Build a skeleton tree of nodes in the given snapshot. This is the heart of
275c9da86e89f8abf71135cf63d9fc23671b2e60eschrock * libses, and is responsible for parsing the config page into a tree and
275c9da86e89f8abf71135cf63d9fc23671b2e60eschrock * populating nodes with data from the config page.
275c9da86e89f8abf71135cf63d9fc23671b2e60eschrock pp = ses_snap_find_page(sp, SES2_DIAGPAGE_CONFIG, B_FALSE);
275c9da86e89f8abf71135cf63d9fc23671b2e60eschrock return (ses_error(ESES_BAD_RESPONSE, "target does not support "
275c9da86e89f8abf71135cf63d9fc23671b2e60eschrock "configuration diagnostic page"));
275c9da86e89f8abf71135cf63d9fc23671b2e60eschrock if (pp->ssp_len < offsetof(ses2_config_page_impl_t, scpi_data))
275c9da86e89f8abf71135cf63d9fc23671b2e60eschrock return (ses_error(ESES_BAD_RESPONSE, "no enclosure "
275c9da86e89f8abf71135cf63d9fc23671b2e60eschrock "descriptors found"));
275c9da86e89f8abf71135cf63d9fc23671b2e60eschrock * Start with the root of the tree, which is a target node, containing
275c9da86e89f8abf71135cf63d9fc23671b2e60eschrock * just the SCSI inquiry properties.
275c9da86e89f8abf71135cf63d9fc23671b2e60eschrock if ((root = ses_node_alloc(sp, sp->ss_root)) == NULL)
275c9da86e89f8abf71135cf63d9fc23671b2e60eschrock return (-1);
275c9da86e89f8abf71135cf63d9fc23671b2e60eschrock SES_NV_ADD(string, err, root->sn_props, SCSI_PROP_VENDOR,
275c9da86e89f8abf71135cf63d9fc23671b2e60eschrock SES_NV_ADD(string, err, root->sn_props, SCSI_PROP_PRODUCT,
275c9da86e89f8abf71135cf63d9fc23671b2e60eschrock SES_NV_ADD(string, err, root->sn_props, SCSI_PROP_REVISION,
275c9da86e89f8abf71135cf63d9fc23671b2e60eschrock for (eip = (ses2_ed_impl_t *)pip->scpi_data, i = 0;
275c9da86e89f8abf71135cf63d9fc23671b2e60eschrock if (!SES_WITHIN_PAGE_STRUCT(eip, pp->ssp_page, pp->ssp_len))
275c9da86e89f8abf71135cf63d9fc23671b2e60eschrock * There should really be only one Enclosure element possible for a
275c9da86e89f8abf71135cf63d9fc23671b2e60eschrock * give subenclosure ID. The standard never comes out and says this,
275c9da86e89f8abf71135cf63d9fc23671b2e60eschrock * but it does describe this element as "managing the enclosure itself"
275c9da86e89f8abf71135cf63d9fc23671b2e60eschrock * which implies rather strongly that the subenclosure ID field is that
275c9da86e89f8abf71135cf63d9fc23671b2e60eschrock * of, well, the enclosure itself. Since an enclosure can't contain
275c9da86e89f8abf71135cf63d9fc23671b2e60eschrock * itself, it follows logically that each subenclosure has at most one
275c9da86e89f8abf71135cf63d9fc23671b2e60eschrock * Enclosure type descriptor elements matching its ID. Of course, some
275c9da86e89f8abf71135cf63d9fc23671b2e60eschrock * enclosure firmware is buggy, so this may not always work out; in
275c9da86e89f8abf71135cf63d9fc23671b2e60eschrock * this case we just ignore all but the first Enclosure-type element
275c9da86e89f8abf71135cf63d9fc23671b2e60eschrock * with our subenclosure ID.
275c9da86e89f8abf71135cf63d9fc23671b2e60eschrock for (eip = (ses2_ed_impl_t *)pip->scpi_data, i = 0;
275c9da86e89f8abf71135cf63d9fc23671b2e60eschrock if (!SES_WITHIN_PAGE_STRUCT(eip, pp->ssp_page, pp->ssp_len))
275c9da86e89f8abf71135cf63d9fc23671b2e60eschrock return (-1);
275c9da86e89f8abf71135cf63d9fc23671b2e60eschrock if (!SES_WITHIN_PAGE(eip, eip->st_hdr.sehi_ed_len +
275c9da86e89f8abf71135cf63d9fc23671b2e60eschrock return (-1);
275c9da86e89f8abf71135cf63d9fc23671b2e60eschrock return (ses_error(ESES_BAD_RESPONSE, "no enclosure "
275c9da86e89f8abf71135cf63d9fc23671b2e60eschrock "descriptors found"));
ac88567a7a5bb7f01cf22cf366bc9d6203e24d7aHyon Kim for (i = 0, toff = 0, idx = eidx = 0; i < n_etds; i++) {
275c9da86e89f8abf71135cf63d9fc23671b2e60eschrock if (!SES_WITHIN_PAGE_STRUCT(tip, pp->ssp_page, pp->ssp_len))
275c9da86e89f8abf71135cf63d9fc23671b2e60eschrock return (-1);
275c9da86e89f8abf71135cf63d9fc23671b2e60eschrock return (-1);
275c9da86e89f8abf71135cf63d9fc23671b2e60eschrock return (-1);
275c9da86e89f8abf71135cf63d9fc23671b2e60eschrock return (-1);
275c9da86e89f8abf71135cf63d9fc23671b2e60eschrock return (0);
275c9da86e89f8abf71135cf63d9fc23671b2e60eschrock return (0);
275c9da86e89f8abf71135cf63d9fc23671b2e60eschrock return (-1);
275c9da86e89f8abf71135cf63d9fc23671b2e60eschrock return (-1);
275c9da86e89f8abf71135cf63d9fc23671b2e60eschrock return (0);
275c9da86e89f8abf71135cf63d9fc23671b2e60eschrock return (-1);
275c9da86e89f8abf71135cf63d9fc23671b2e60eschrock return (-1);
275c9da86e89f8abf71135cf63d9fc23671b2e60eschrock return (0);
275c9da86e89f8abf71135cf63d9fc23671b2e60eschrock * A node identifier is a (generation, index) tuple that can be used to lookup a
275c9da86e89f8abf71135cf63d9fc23671b2e60eschrock * node within this target at a later point. This will be valid across
275c9da86e89f8abf71135cf63d9fc23671b2e60eschrock * snapshots, though it will return failure if the generation count has changed.
275c9da86e89f8abf71135cf63d9fc23671b2e60eschrock return (((uint64_t)np->sn_snapshot->ss_generation << 32) |