074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier/*
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier * CDDL HEADER START
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier *
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier * The contents of this file are subject to the terms of the
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier * Common Development and Distribution License (the "License").
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier * You may not use this file except in compliance with the License.
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier *
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier * or http://www.opensolaris.org/os/licensing.
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier * See the License for the specific language governing permissions
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier * and limitations under the License.
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier *
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier * When distributing Covered Code, include this CDDL HEADER in each
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier * file and include the License file at usr/src/OPENSOLARIS.LICENSE.
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier * If applicable, add the following below this CDDL HEADER, with the
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier * fields enclosed by brackets "[]" replaced with your own identifying
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier * information: Portions Copyright [yyyy] [name of copyright owner]
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier *
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier * CDDL HEADER END
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier */
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier/*
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier * Copyright 2009 Sun Microsystems, Inc. All rights reserved.
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier * Use is subject to license terms.
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier */
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier/*
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier * Create a generic topology node.
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier */
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier#include <sys/types.h>
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier#include <strings.h>
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier#include <sys/fm/protocol.h>
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier#include <fm/topo_mod.h>
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier#include <fm/topo_hc.h>
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier#include <x86pi_impl.h>
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier#define _ENUM_NAME "enum_generic"
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier#define _FAC_PROV "fac_prov_ipmi"
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier/*
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier * Create a generic topo node based on the hcfmri strcuture passed in.
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier */
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothierint
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothierx86pi_enum_generic(topo_mod_t *mod, x86pi_hcfmri_t *hcfmri,
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier tnode_t *t_bindparent, tnode_t *t_fmriparent, tnode_t **t_node, int flag)
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier{
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier int rv;
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier int err;
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier nvlist_t *out;
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier nvlist_t *fmri;
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier nvlist_t *auth;
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier topo_mod_dprintf(mod, "%s adding entry for type (%s)\n",
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier _ENUM_NAME, hcfmri->hc_name);
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier if (t_bindparent == NULL) {
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier topo_mod_dprintf(mod,
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier "%s called with NULL parent for type %s\n",
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier _ENUM_NAME, hcfmri->hc_name);
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier return (-1);
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier }
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier /* Create the FMRI for this node */
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier auth = topo_mod_auth(mod, t_bindparent);
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier fmri = topo_mod_hcfmri(mod, t_fmriparent, FM_HC_SCHEME_VERSION,
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier hcfmri->hc_name, hcfmri->instance, NULL, auth,
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier hcfmri->part_number, hcfmri->version, hcfmri->serial_number);
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier nvlist_free(auth);
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier if (fmri == NULL) {
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier topo_mod_dprintf(mod,
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier "%s failed to create %s fmri : %s\n", _ENUM_NAME,
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier hcfmri->hc_name, topo_strerror(topo_mod_errno(mod)));
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier return (-1);
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier }
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier rv = topo_node_range_create(mod, t_bindparent, hcfmri->hc_name, 0, 4);
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier if (rv != 0 && topo_mod_errno(mod) != EMOD_NODE_DUP) {
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier topo_mod_dprintf(mod, "%s range create failed for node %s\n",
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier _ENUM_NAME, hcfmri->hc_name);
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier }
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier /* Bind this node to the parent */
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier *t_node = x86pi_node_bind(mod, t_bindparent, hcfmri, fmri, flag);
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier nvlist_free(fmri);
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier if (*t_node == NULL) {
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier topo_mod_dprintf(mod,
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier "%s failed to bind %s node instance %d: %s\n",
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier _ENUM_NAME, hcfmri->hc_name, hcfmri->instance,
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier topo_strerror(topo_mod_errno(mod)));
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier return (-1);
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier }
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier /* call IPMI facility provider to register fac methods */
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier if (topo_mod_load(mod, _FAC_PROV, TOPO_VERSION) == NULL) {
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier topo_mod_dprintf(mod,
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier "%s: Failed to load %s module: %s\n", _ENUM_NAME, _FAC_PROV,
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier topo_mod_errmsg(mod));
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier return (-1);
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier }
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier rv = topo_mod_enumerate(mod, *t_node, _FAC_PROV, _FAC_PROV, 0, 0, NULL);
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier if (rv != 0) {
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier topo_mod_dprintf(mod,
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier "%s: %s failed: %s\n", _ENUM_NAME, _FAC_PROV,
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier topo_mod_errmsg(mod));
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier return (-1);
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier }
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier /* invoke fac_prov_ipmi_enum method */
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier if (topo_method_supported(*t_node, TOPO_METH_FAC_ENUM, 0)) {
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier if (topo_method_invoke(*t_node, TOPO_METH_FAC_ENUM, 0, NULL,
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier &out, &err) != 0) {
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier /* log the error and drive on */
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier topo_mod_dprintf(mod,
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier "%s: TOPO_METH_FAC_ENUM failed\n", _ENUM_NAME);
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier } else {
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier fac_done = 1;
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier }
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier }
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier topo_mod_dprintf(mod, "%s added (%s) node\n", _ENUM_NAME,
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier topo_node_name(*t_node));
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier return (0);
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier}
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothiertnode_t *
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothierx86pi_node_bind(topo_mod_t *mod, tnode_t *t_parent, x86pi_hcfmri_t *hcfmri,
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier nvlist_t *fmri, int flag)
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier{
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier int result;
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier tnode_t *t_node;
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier char *f = "x86pi_node_bind";
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier if (t_parent == NULL) {
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier topo_mod_dprintf(mod,
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier "%s: NULL parent for %s node instance %d\n",
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier f, hcfmri->hc_name, hcfmri->instance);
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier return (NULL);
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier }
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier /* Bind this node to the parent */
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier t_node = topo_node_bind(mod, t_parent, hcfmri->hc_name,
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier hcfmri->instance, fmri);
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier if (t_node == NULL) {
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier topo_mod_dprintf(mod,
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier "%s: failed to bind %s node instance %d: %s\n",
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier f, hcfmri->hc_name, (uint32_t)hcfmri->instance,
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier topo_strerror(topo_mod_errno(mod)));
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier return (NULL);
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier }
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier topo_mod_dprintf(mod, "%s: bound %s node instance %d type %s\n",
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier f, hcfmri->hc_name, hcfmri->instance, hcfmri->hc_name);
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier /*
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier * We have bound the node. Now decorate it with an appropriate
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier * FRU and label (which may be inherited from the parent).
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier */
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier result = x86pi_set_frufmri(mod, hcfmri, t_parent, t_node, flag);
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier if (result != 0) {
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier /*
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier * Though we have failed to set the FRU FMRI we still continue.
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier * The module errno is set by the called routine, so we report
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier * the problem and move on.
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier */
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier topo_mod_dprintf(mod,
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier "%s: failed to set FRU FMRI for %s node\n",
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier f, hcfmri->hc_name);
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier }
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier result = x86pi_set_label(mod, hcfmri->location, hcfmri->hc_name,
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier t_node);
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier if (result != 0) {
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier /*
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier * Though we have failed to set the label, we still continue.
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier * The module errno is set by the called routine, so we report
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier * the problem and move on.
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier */
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier topo_mod_dprintf(mod, "%s: no label for %s node\n",
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier f, hcfmri->hc_name);
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier }
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier result = x86pi_set_auth(mod, hcfmri, t_parent, t_node);
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier if (result != 0) {
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier /*
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier * Though we have failed to set the authority, we still
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier * continue. The module errno is set by the called routine, so
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier * we report the problem and move on.
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier */
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier topo_mod_dprintf(mod,
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier "%s: no authority information for %s node\n",
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier f, hcfmri->hc_name);
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier }
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier result = x86pi_set_system(mod, t_node);
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier if (result != 0) {
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier /*
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier * Though we have failed to set the system group, we still
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier * continue. The module errno is set by the called routine, so
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier * we report the problem and move on.
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier */
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier topo_mod_dprintf(mod,
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier "%s: no system information for %s node\n",
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier f, hcfmri->hc_name);
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier }
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier return (t_node);
074bb90d80fdbeb2d04a8450a55ecbc96de28785Tom Pothier}