17aec1d6eScindi /* 27aec1d6eScindi * CDDL HEADER START 37aec1d6eScindi * 47aec1d6eScindi * The contents of this file are subject to the terms of the 57aec1d6eScindi * Common Development and Distribution License (the "License"). 67aec1d6eScindi * You may not use this file except in compliance with the License. 77aec1d6eScindi * 87aec1d6eScindi * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE 97aec1d6eScindi * or http://www.opensolaris.org/os/licensing. 107aec1d6eScindi * See the License for the specific language governing permissions 117aec1d6eScindi * and limitations under the License. 127aec1d6eScindi * 137aec1d6eScindi * When distributing Covered Code, include this CDDL HEADER in each 147aec1d6eScindi * file and include the License file at usr/src/OPENSOLARIS.LICENSE. 157aec1d6eScindi * If applicable, add the following below this CDDL HEADER, with the 167aec1d6eScindi * fields enclosed by brackets "[]" replaced with your own identifying 177aec1d6eScindi * information: Portions Copyright [yyyy] [name of copyright owner] 187aec1d6eScindi * 197aec1d6eScindi * CDDL HEADER END 207aec1d6eScindi */ 217aec1d6eScindi 227aec1d6eScindi /* 23c93c462eSCheng Sean Ye * Copyright 2009 Sun Microsystems, Inc. All rights reserved. 247aec1d6eScindi * Use is subject to license terms. 25*f2dbfd32SRobert Mustacchi * Copyright 2019, Joyent, Inc. 267aec1d6eScindi */ 277aec1d6eScindi 287aec1d6eScindi #include <unistd.h> 29e4b86885SCheng Sean Ye #include <fcntl.h> 307aec1d6eScindi #include <stdio.h> 317aec1d6eScindi #include <stdlib.h> 328a40a695Sgavinm #include <stdarg.h> 337aec1d6eScindi #include <string.h> 347aec1d6eScindi #include <strings.h> 357aec1d6eScindi #include <limits.h> 367aec1d6eScindi #include <alloca.h> 377aec1d6eScindi #include <kstat.h> 387aec1d6eScindi #include <errno.h> 397aec1d6eScindi #include <libnvpair.h> 407aec1d6eScindi #include <sys/types.h> 417aec1d6eScindi #include <sys/bitmap.h> 427aec1d6eScindi #include <sys/processor.h> 437aec1d6eScindi #include <sys/param.h> 447aec1d6eScindi #include <sys/fm/protocol.h> 457aec1d6eScindi #include <sys/systeminfo.h> 467aec1d6eScindi #include <sys/mc.h> 478a40a695Sgavinm #include <sys/mc_amd.h> 4820c794b3Sgavinm #include <sys/mc_intel.h> 49e4b86885SCheng Sean Ye #include <sys/devfm.h> 50e4b86885SCheng Sean Ye #include <fm/fmd_agent.h> 517aec1d6eScindi #include <fm/topo_mod.h> 527aec1d6eScindi 537aec1d6eScindi #include "chip.h" 547aec1d6eScindi 55bac58072Sgavinm #define MAX_DIMMNUM 7 56bac58072Sgavinm #define MAX_CSNUM 7 57bac58072Sgavinm 587aec1d6eScindi /* 597aec1d6eScindi * Enumerates the processing chips, or sockets, (as distinct from cores) in a 607aec1d6eScindi * system. For each chip found, the necessary nodes (one or more cores, and 617aec1d6eScindi * possibly a memory controller) are constructed underneath. 627aec1d6eScindi */ 637aec1d6eScindi 6420c794b3Sgavinm static int chip_enum(topo_mod_t *, tnode_t *, const char *, 6520c794b3Sgavinm topo_instance_t, topo_instance_t, void *, void *); 668a40a695Sgavinm 670eb822a1Scindi static const topo_modops_t chip_ops = 680eb822a1Scindi { chip_enum, NULL}; 690eb822a1Scindi static const topo_modinfo_t chip_info = 709dd0f810Scindi { CHIP_NODE_NAME, FM_FMRI_SCHEME_HC, CHIP_VERSION, &chip_ops }; 710eb822a1Scindi 720eb822a1Scindi static const topo_pgroup_info_t chip_pgroup = 739dd0f810Scindi { PGNAME(CHIP), TOPO_STABILITY_PRIVATE, TOPO_STABILITY_PRIVATE, 1 }; 74e4b86885SCheng Sean Ye 75e4b86885SCheng Sean Ye static const topo_pgroup_info_t core_pgroup = 76e4b86885SCheng Sean Ye { PGNAME(CORE), TOPO_STABILITY_PRIVATE, TOPO_STABILITY_PRIVATE, 1 }; 77e4b86885SCheng Sean Ye 78e4b86885SCheng Sean Ye static const topo_pgroup_info_t strand_pgroup = 79e4b86885SCheng Sean Ye { PGNAME(STRAND), TOPO_STABILITY_PRIVATE, TOPO_STABILITY_PRIVATE, 1 }; 808a40a695Sgavinm 8120c794b3Sgavinm static const topo_method_t chip_methods[] = { 824557a2a1Srobj { SIMPLE_CHIP_LBL, "Property method", 0, 834557a2a1Srobj TOPO_STABILITY_INTERNAL, simple_chip_label}, 844557a2a1Srobj { G4_CHIP_LBL, "Property method", 0, 854557a2a1Srobj TOPO_STABILITY_INTERNAL, g4_chip_label}, 862cb5535aSrobj { A4FPLUS_CHIP_LBL, "Property method", 0, 872cb5535aSrobj TOPO_STABILITY_INTERNAL, a4fplus_chip_label}, 8864d1d4abSAdrian Frost { FSB2_CHIP_LBL, "Property method", 0, 8964d1d4abSAdrian Frost TOPO_STABILITY_INTERNAL, fsb2_chip_label}, 902a613b59SRobert Mustacchi { TOPO_METH_REPLACED, TOPO_METH_REPLACED_DESC, 912a613b59SRobert Mustacchi TOPO_METH_REPLACED_VERSION, TOPO_STABILITY_INTERNAL, 922a613b59SRobert Mustacchi chip_fmri_replaced }, 934557a2a1Srobj { NULL } 944557a2a1Srobj }; 954557a2a1Srobj 96e4b86885SCheng Sean Ye static const topo_method_t strands_retire_methods[] = { 97e4b86885SCheng Sean Ye { TOPO_METH_RETIRE, TOPO_METH_RETIRE_DESC, 98e4b86885SCheng Sean Ye TOPO_METH_RETIRE_VERSION, TOPO_STABILITY_INTERNAL, 99e4b86885SCheng Sean Ye retire_strands }, 100e4b86885SCheng Sean Ye { TOPO_METH_UNRETIRE, TOPO_METH_UNRETIRE_DESC, 101e4b86885SCheng Sean Ye TOPO_METH_UNRETIRE_VERSION, TOPO_STABILITY_INTERNAL, 102e4b86885SCheng Sean Ye unretire_strands }, 103e4b86885SCheng Sean Ye { TOPO_METH_SERVICE_STATE, TOPO_METH_SERVICE_STATE_DESC, 104e4b86885SCheng Sean Ye TOPO_METH_SERVICE_STATE_VERSION, TOPO_STABILITY_INTERNAL, 105e4b86885SCheng Sean Ye service_state_strands }, 106e4b86885SCheng Sean Ye { TOPO_METH_UNUSABLE, TOPO_METH_UNUSABLE_DESC, 107e4b86885SCheng Sean Ye TOPO_METH_UNUSABLE_VERSION, TOPO_STABILITY_INTERNAL, 108e4b86885SCheng Sean Ye unusable_strands }, 109e4b86885SCheng Sean Ye { NULL } 110e4b86885SCheng Sean Ye }; 111e4b86885SCheng Sean Ye 1127aec1d6eScindi int 1137aec1d6eScindi _topo_init(topo_mod_t *mod) 1147aec1d6eScindi { 1150eb822a1Scindi if (getenv("TOPOCHIPDBG")) 1160eb822a1Scindi topo_mod_setdebug(mod); 1177aec1d6eScindi topo_mod_dprintf(mod, "initializing chip enumerator\n"); 1187aec1d6eScindi 1190eb822a1Scindi if (topo_mod_register(mod, &chip_info, TOPO_VERSION) != 0) { 1208a40a695Sgavinm whinge(mod, NULL, "failed to register hc: " 1217aec1d6eScindi "%s\n", topo_mod_errmsg(mod)); 1227aec1d6eScindi return (-1); /* mod errno set */ 1237aec1d6eScindi } 1247aec1d6eScindi 1257aec1d6eScindi return (0); 1267aec1d6eScindi } 1277aec1d6eScindi 1287aec1d6eScindi void 1297aec1d6eScindi _topo_fini(topo_mod_t *mod) 1307aec1d6eScindi { 1317aec1d6eScindi topo_mod_unregister(mod); 1327aec1d6eScindi } 1337aec1d6eScindi 134e4b86885SCheng Sean Ye boolean_t 135e4b86885SCheng Sean Ye is_xpv(void) 136e3d60c9bSAdrian Frost { 137e4b86885SCheng Sean Ye static int r = -1; 138e4b86885SCheng Sean Ye char platform[MAXNAMELEN]; 139e3d60c9bSAdrian Frost 140e4b86885SCheng Sean Ye if (r != -1) 141e4b86885SCheng Sean Ye return (r == 0); 142e3d60c9bSAdrian Frost 143e4b86885SCheng Sean Ye (void) sysinfo(SI_PLATFORM, platform, sizeof (platform)); 144e4b86885SCheng Sean Ye r = strcmp(platform, "i86xpv"); 145e4b86885SCheng Sean Ye return (r == 0); 146e4b86885SCheng Sean Ye } 147e3d60c9bSAdrian Frost 148e4b86885SCheng Sean Ye static tnode_t * 149e4b86885SCheng Sean Ye create_node(topo_mod_t *mod, tnode_t *pnode, nvlist_t *auth, char *name, 1502a613b59SRobert Mustacchi topo_instance_t inst, nvlist_t *cpu, uint16_t smbios_id) 151e4b86885SCheng Sean Ye { 152e4b86885SCheng Sean Ye nvlist_t *fmri; 153e4b86885SCheng Sean Ye tnode_t *cnode; 154e3d60c9bSAdrian Frost 155e4b86885SCheng Sean Ye if (mkrsrc(mod, pnode, name, inst, auth, &fmri) != 0) { 156e4b86885SCheng Sean Ye whinge(mod, NULL, "create_node: mkrsrc failed\n"); 157e4b86885SCheng Sean Ye return (NULL); 158e3d60c9bSAdrian Frost } 159074bb90dSTom Pothier 160074bb90dSTom Pothier if (FM_AWARE_SMBIOS(mod)) { 161074bb90dSTom Pothier id_t phys_cpu_smbid; 162074bb90dSTom Pothier int perr = 0; 163074bb90dSTom Pothier const char *serial = NULL; 164074bb90dSTom Pothier const char *part = NULL; 165074bb90dSTom Pothier const char *rev = NULL; 166074bb90dSTom Pothier 167074bb90dSTom Pothier phys_cpu_smbid = smbios_id; 168074bb90dSTom Pothier serial = chip_serial_smbios_get(mod, phys_cpu_smbid); 169074bb90dSTom Pothier part = chip_part_smbios_get(mod, phys_cpu_smbid); 170074bb90dSTom Pothier rev = chip_rev_smbios_get(mod, phys_cpu_smbid); 171074bb90dSTom Pothier 172074bb90dSTom Pothier perr += nvlist_add_string(fmri, FM_FMRI_HC_SERIAL_ID, 173074bb90dSTom Pothier serial); 174074bb90dSTom Pothier perr += nvlist_add_string(fmri, FM_FMRI_HC_PART, 175074bb90dSTom Pothier part); 176074bb90dSTom Pothier perr += nvlist_add_string(fmri, FM_FMRI_HC_REVISION, 177074bb90dSTom Pothier rev); 178074bb90dSTom Pothier 179074bb90dSTom Pothier if (perr != 0) 180074bb90dSTom Pothier whinge(mod, NULL, 181074bb90dSTom Pothier "create_node: nvlist_add_string failed\n"); 182074bb90dSTom Pothier 183074bb90dSTom Pothier topo_mod_strfree(mod, (char *)serial); 184074bb90dSTom Pothier topo_mod_strfree(mod, (char *)part); 185074bb90dSTom Pothier topo_mod_strfree(mod, (char *)rev); 1862a613b59SRobert Mustacchi } else { 1872a613b59SRobert Mustacchi char *serial = NULL; 1882a613b59SRobert Mustacchi 1892a613b59SRobert Mustacchi if (nvlist_lookup_string(cpu, FM_PHYSCPU_INFO_CHIP_IDENTSTR, 1902a613b59SRobert Mustacchi &serial) == 0) { 1912a613b59SRobert Mustacchi if (nvlist_add_string(fmri, FM_FMRI_HC_SERIAL_ID, 1922a613b59SRobert Mustacchi serial) != 0) { 1932a613b59SRobert Mustacchi whinge(mod, NULL, 1942a613b59SRobert Mustacchi "create_node: nvlist_add_string failed\n"); 1952a613b59SRobert Mustacchi } 1962a613b59SRobert Mustacchi } 197074bb90dSTom Pothier } 198074bb90dSTom Pothier 199e4b86885SCheng Sean Ye cnode = topo_node_bind(mod, pnode, name, inst, fmri); 200074bb90dSTom Pothier 201e4b86885SCheng Sean Ye nvlist_free(fmri); 202074bb90dSTom Pothier if (cnode == NULL) { 203074bb90dSTom Pothier whinge(mod, NULL, "create_node: node bind failed" 204074bb90dSTom Pothier " for %s %d\n", name, (int)inst); 205074bb90dSTom Pothier } 206e3d60c9bSAdrian Frost 207e4b86885SCheng Sean Ye return (cnode); 208e3d60c9bSAdrian Frost } 209e3d60c9bSAdrian Frost 210e3d60c9bSAdrian Frost static int 211074bb90dSTom Pothier create_strand(topo_mod_t *mod, tnode_t *pnode, nvlist_t *cpu, 212074bb90dSTom Pothier nvlist_t *auth, uint16_t chip_smbiosid) 213e3d60c9bSAdrian Frost { 214e4b86885SCheng Sean Ye tnode_t *strand; 215e4b86885SCheng Sean Ye int32_t strandid, cpuid; 216074bb90dSTom Pothier int err, perr, nerr = 0; 217e4b86885SCheng Sean Ye nvlist_t *fmri; 218074bb90dSTom Pothier char *serial = NULL; 219074bb90dSTom Pothier char *part = NULL; 220074bb90dSTom Pothier char *rev = NULL; 221e3d60c9bSAdrian Frost 222e4b86885SCheng Sean Ye if ((err = nvlist_lookup_int32(cpu, FM_PHYSCPU_INFO_STRAND_ID, 223e4b86885SCheng Sean Ye &strandid)) != 0) { 224e4b86885SCheng Sean Ye whinge(mod, NULL, "create_strand: lookup strand_id failed: " 225e4b86885SCheng Sean Ye "%s\n", strerror(err)); 226e3d60c9bSAdrian Frost return (-1); 227e4b86885SCheng Sean Ye } 228e3d60c9bSAdrian Frost 229e4b86885SCheng Sean Ye if ((strand = topo_node_lookup(pnode, STRAND_NODE_NAME, strandid)) 230e4b86885SCheng Sean Ye != NULL) { 231e4b86885SCheng Sean Ye whinge(mod, NULL, "create_strand: duplicate tuple found\n"); 232e4b86885SCheng Sean Ye return (-1); 233e4b86885SCheng Sean Ye } 234e3d60c9bSAdrian Frost 235e4b86885SCheng Sean Ye if ((strand = create_node(mod, pnode, auth, STRAND_NODE_NAME, 2362a613b59SRobert Mustacchi strandid, cpu, chip_smbiosid)) == NULL) 237e4b86885SCheng Sean Ye return (-1); 238e3d60c9bSAdrian Frost 239e4b86885SCheng Sean Ye /* 240e4b86885SCheng Sean Ye * Inherit FRU from core node, in native use cpu scheme ASRU, 241e4b86885SCheng Sean Ye * in xpv, use hc scheme ASRU. 242e4b86885SCheng Sean Ye */ 243074bb90dSTom Pothier (void) topo_node_fru_set(strand, NULL, 0, &perr); 244074bb90dSTom Pothier /* 245074bb90dSTom Pothier * From the inherited FRU, extract the Serial 246074bb90dSTom Pothier * number(if SMBIOS donates) and set it in the ASRU 247074bb90dSTom Pothier */ 248074bb90dSTom Pothier if (FM_AWARE_SMBIOS(mod)) { 249074bb90dSTom Pothier char *val = NULL; 250074bb90dSTom Pothier 251074bb90dSTom Pothier if (topo_prop_get_fmri(strand, TOPO_PGROUP_PROTOCOL, 252074bb90dSTom Pothier TOPO_PROP_RESOURCE, &fmri, &err) != 0) 253074bb90dSTom Pothier whinge(mod, NULL, 254074bb90dSTom Pothier "create_strand: topo_prop_get_fmri failed\n"); 255074bb90dSTom Pothier if (nvlist_lookup_string(fmri, FM_FMRI_HC_SERIAL_ID, &val) != 0) 256074bb90dSTom Pothier whinge(mod, NULL, 257074bb90dSTom Pothier "create_strand: nvlist_lookup_string failed: \n"); 258074bb90dSTom Pothier else 259074bb90dSTom Pothier serial = topo_mod_strdup(mod, val); 260074bb90dSTom Pothier nvlist_free(fmri); 261074bb90dSTom Pothier } 262e4b86885SCheng Sean Ye if (is_xpv()) { 263e4b86885SCheng Sean Ye if (topo_node_resource(strand, &fmri, &err) == -1) { 264e4b86885SCheng Sean Ye whinge(mod, &nerr, "create_strand: " 265e4b86885SCheng Sean Ye "topo_node_resource failed\n"); 266e4b86885SCheng Sean Ye } else { 267074bb90dSTom Pothier if (FM_AWARE_SMBIOS(mod)) 268074bb90dSTom Pothier (void) nvlist_add_string(fmri, 269074bb90dSTom Pothier FM_FMRI_HC_SERIAL_ID, serial); 270e4b86885SCheng Sean Ye (void) topo_node_asru_set(strand, fmri, 0, &err); 271e3d60c9bSAdrian Frost nvlist_free(fmri); 272e3d60c9bSAdrian Frost } 273e4b86885SCheng Sean Ye } else { 274e4b86885SCheng Sean Ye if (nvlist_lookup_int32(cpu, STRAND_CPU_ID, &cpuid) != 0) { 275e4b86885SCheng Sean Ye whinge(mod, &nerr, "create_strand: lookup cpuid " 276e4b86885SCheng Sean Ye "failed\n"); 277e4b86885SCheng Sean Ye } else { 278074bb90dSTom Pothier if ((fmri = cpu_fmri_create(mod, cpuid, serial, 0)) 279e4b86885SCheng Sean Ye != NULL) { 280e4b86885SCheng Sean Ye (void) topo_node_asru_set(strand, fmri, 281e4b86885SCheng Sean Ye 0, &err); 282e4b86885SCheng Sean Ye nvlist_free(fmri); 283e4b86885SCheng Sean Ye } else { 284e4b86885SCheng Sean Ye whinge(mod, &nerr, "create_strand: " 285e4b86885SCheng Sean Ye "cpu_fmri_create() failed\n"); 286e4b86885SCheng Sean Ye } 287e4b86885SCheng Sean Ye } 288e4b86885SCheng Sean Ye } 289e3d60c9bSAdrian Frost 290e4b86885SCheng Sean Ye if (topo_method_register(mod, strand, strands_retire_methods) < 0) 291e4b86885SCheng Sean Ye whinge(mod, &nerr, "create_strand: " 292e4b86885SCheng Sean Ye "topo_method_register failed\n"); 293e3d60c9bSAdrian Frost 294e4b86885SCheng Sean Ye (void) topo_pgroup_create(strand, &strand_pgroup, &err); 295e4b86885SCheng Sean Ye nerr -= add_nvlist_longprops(mod, strand, cpu, PGNAME(STRAND), NULL, 2968031591dSSrihari Venkatesan STRAND_CHIP_ID, STRAND_PROCNODE_ID, STRAND_CORE_ID, STRAND_CPU_ID, 2978031591dSSrihari Venkatesan NULL); 298e3d60c9bSAdrian Frost 299074bb90dSTom Pothier if (FM_AWARE_SMBIOS(mod)) { 300074bb90dSTom Pothier (void) topo_node_label_set(strand, NULL, &perr); 301074bb90dSTom Pothier 302074bb90dSTom Pothier if (topo_node_resource(strand, &fmri, &perr) != 0) { 303074bb90dSTom Pothier whinge(mod, &nerr, "create_strand: " 304074bb90dSTom Pothier "topo_node_resource failed\n"); 305074bb90dSTom Pothier perr = 0; 306074bb90dSTom Pothier } 307074bb90dSTom Pothier 308074bb90dSTom Pothier perr += nvlist_lookup_string(fmri, 309074bb90dSTom Pothier FM_FMRI_HC_PART, &part); 310074bb90dSTom Pothier perr += nvlist_lookup_string(fmri, 311074bb90dSTom Pothier FM_FMRI_HC_REVISION, &rev); 312074bb90dSTom Pothier 313074bb90dSTom Pothier if (perr != 0) { 314074bb90dSTom Pothier whinge(mod, NULL, 315074bb90dSTom Pothier "create_strand: nvlist_lookup_string failed\n"); 316074bb90dSTom Pothier perr = 0; 317074bb90dSTom Pothier } 318074bb90dSTom Pothier 319074bb90dSTom Pothier perr += topo_prop_set_string(strand, PGNAME(STRAND), 320074bb90dSTom Pothier FM_FMRI_HC_SERIAL_ID, TOPO_PROP_IMMUTABLE, serial, &perr); 321074bb90dSTom Pothier perr += topo_prop_set_string(strand, PGNAME(STRAND), 322074bb90dSTom Pothier FM_FMRI_HC_PART, TOPO_PROP_IMMUTABLE, part, &perr); 323074bb90dSTom Pothier perr += topo_prop_set_string(strand, PGNAME(STRAND), 324074bb90dSTom Pothier FM_FMRI_HC_REVISION, TOPO_PROP_IMMUTABLE, rev, &perr); 325074bb90dSTom Pothier 326074bb90dSTom Pothier if (perr != 0) 327074bb90dSTom Pothier whinge(mod, NULL, "create_strand: topo_prop_set_string" 328074bb90dSTom Pothier "failed\n"); 329074bb90dSTom Pothier 330074bb90dSTom Pothier nvlist_free(fmri); 331074bb90dSTom Pothier topo_mod_strfree(mod, serial); 332074bb90dSTom Pothier } 333074bb90dSTom Pothier 334e4b86885SCheng Sean Ye return (err == 0 && nerr == 0 ? 0 : -1); 335e3d60c9bSAdrian Frost } 336e3d60c9bSAdrian Frost 3377aec1d6eScindi static int 338074bb90dSTom Pothier create_core(topo_mod_t *mod, tnode_t *pnode, nvlist_t *cpu, 339074bb90dSTom Pothier nvlist_t *auth, uint16_t chip_smbiosid) 3407aec1d6eScindi { 341e4b86885SCheng Sean Ye tnode_t *core; 342e4b86885SCheng Sean Ye int32_t coreid, cpuid; 343074bb90dSTom Pothier int err, perr, nerr = 0; 344e4b86885SCheng Sean Ye nvlist_t *fmri; 345074bb90dSTom Pothier char *serial = NULL; 346074bb90dSTom Pothier char *part = NULL; 347074bb90dSTom Pothier char *rev = NULL; 3487aec1d6eScindi 349e4b86885SCheng Sean Ye if ((err = nvlist_lookup_int32(cpu, FM_PHYSCPU_INFO_CORE_ID, &coreid)) 350e4b86885SCheng Sean Ye != 0) { 351e4b86885SCheng Sean Ye whinge(mod, NULL, "create_core: lookup core_id failed: %s\n", 352e4b86885SCheng Sean Ye strerror(err)); 3537aec1d6eScindi return (-1); 354e4b86885SCheng Sean Ye } 355e4b86885SCheng Sean Ye if ((core = topo_node_lookup(pnode, CORE_NODE_NAME, coreid)) == NULL) { 356e4b86885SCheng Sean Ye if ((core = create_node(mod, pnode, auth, CORE_NODE_NAME, 3572a613b59SRobert Mustacchi coreid, cpu, chip_smbiosid)) == NULL) 358e4b86885SCheng Sean Ye return (-1); 3597aec1d6eScindi 3608a40a695Sgavinm /* 361e4b86885SCheng Sean Ye * Inherit FRU from the chip node, for native, we use hc 362e4b86885SCheng Sean Ye * scheme ASRU for the core node. 3638a40a695Sgavinm */ 364074bb90dSTom Pothier (void) topo_node_fru_set(core, NULL, 0, &perr); 365074bb90dSTom Pothier /* 366074bb90dSTom Pothier * From the inherited FRU, extract the Serial 367074bb90dSTom Pothier * number if SMBIOS donates and set it in the ASRU 368074bb90dSTom Pothier */ 369074bb90dSTom Pothier if (FM_AWARE_SMBIOS(mod)) { 370074bb90dSTom Pothier char *val = NULL; 371074bb90dSTom Pothier 372074bb90dSTom Pothier if (topo_node_resource(core, &fmri, &err) != 0) 373074bb90dSTom Pothier whinge(mod, NULL, 374074bb90dSTom Pothier "create_core: topo_prop_get_fmri failed\n"); 375074bb90dSTom Pothier if (nvlist_lookup_string(fmri, FM_FMRI_HC_SERIAL_ID, 376074bb90dSTom Pothier &val) != 0) 377074bb90dSTom Pothier whinge(mod, NULL, "create_core:" 378074bb90dSTom Pothier "nvlist_lookup_string failed\n"); 379074bb90dSTom Pothier else 380074bb90dSTom Pothier serial = topo_mod_strdup(mod, val); 381074bb90dSTom Pothier nvlist_free(fmri); 382074bb90dSTom Pothier } 383e4b86885SCheng Sean Ye if (is_xpv()) { 384e4b86885SCheng Sean Ye if (topo_node_resource(core, &fmri, &err) == -1) { 385e4b86885SCheng Sean Ye whinge(mod, &nerr, "create_core: " 386e4b86885SCheng Sean Ye "topo_node_resource failed\n"); 387e4b86885SCheng Sean Ye } else { 388074bb90dSTom Pothier if (FM_AWARE_SMBIOS(mod)) 389074bb90dSTom Pothier (void) nvlist_add_string(fmri, 390074bb90dSTom Pothier FM_FMRI_HC_SERIAL_ID, serial); 391e4b86885SCheng Sean Ye (void) topo_node_asru_set(core, fmri, 0, &err); 392e4b86885SCheng Sean Ye nvlist_free(fmri); 393e4b86885SCheng Sean Ye } 3947aec1d6eScindi } 395e4b86885SCheng Sean Ye if (topo_method_register(mod, core, strands_retire_methods) < 0) 396e4b86885SCheng Sean Ye whinge(mod, &nerr, "create_core: " 397e4b86885SCheng Sean Ye "topo_method_register failed\n"); 398e4b86885SCheng Sean Ye 399e4b86885SCheng Sean Ye (void) topo_pgroup_create(core, &core_pgroup, &err); 4008031591dSSrihari Venkatesan nerr -= add_nvlist_longprops(mod, core, cpu, PGNAME(CORE), NULL, 4018031591dSSrihari Venkatesan CORE_CHIP_ID, CORE_PROCNODE_ID, NULL); 4027aec1d6eScindi 403e4b86885SCheng Sean Ye if (topo_node_range_create(mod, core, STRAND_NODE_NAME, 404e4b86885SCheng Sean Ye 0, 255) != 0) 405e4b86885SCheng Sean Ye return (-1); 406*f2dbfd32SRobert Mustacchi 407*f2dbfd32SRobert Mustacchi /* 408*f2dbfd32SRobert Mustacchi * Creating a temperature sensor may fail because the sensor 409*f2dbfd32SRobert Mustacchi * doesn't exist or due to internal reasons. At the moment, we 410*f2dbfd32SRobert Mustacchi * swallow any such errors that occur. 411*f2dbfd32SRobert Mustacchi */ 412*f2dbfd32SRobert Mustacchi (void) chip_create_core_temp_sensor(mod, core); 413e4b86885SCheng Sean Ye } 4148a40a695Sgavinm 415074bb90dSTom Pothier if (!is_xpv()) { 4168a40a695Sgavinm /* 417e4b86885SCheng Sean Ye * In native mode, we're in favor of cpu scheme ASRU for 418e4b86885SCheng Sean Ye * printing reason. More work needs to be done to support 419e4b86885SCheng Sean Ye * multi-strand cpu: the ASRU will be a list of cpuid then. 4208a40a695Sgavinm */ 421e4b86885SCheng Sean Ye if (nvlist_lookup_int32(cpu, STRAND_CPU_ID, &cpuid) != 0) { 422e4b86885SCheng Sean Ye whinge(mod, &nerr, "create_core: lookup cpuid " 4238a40a695Sgavinm "failed\n"); 424e4b86885SCheng Sean Ye } else { 425074bb90dSTom Pothier if ((fmri = cpu_fmri_create(mod, cpuid, serial, 0)) 426e4b86885SCheng Sean Ye != NULL) { 427e4b86885SCheng Sean Ye (void) topo_node_asru_set(core, fmri, 0, &err); 428e4b86885SCheng Sean Ye nvlist_free(fmri); 429e4b86885SCheng Sean Ye } else { 430e4b86885SCheng Sean Ye whinge(mod, &nerr, "create_core: " 431e4b86885SCheng Sean Ye "cpu_fmri_create() failed\n"); 432e4b86885SCheng Sean Ye } 4337aec1d6eScindi } 4347aec1d6eScindi } 4357aec1d6eScindi 436074bb90dSTom Pothier if (FM_AWARE_SMBIOS(mod)) { 437074bb90dSTom Pothier (void) topo_node_label_set(core, NULL, &perr); 438074bb90dSTom Pothier 439074bb90dSTom Pothier if (topo_node_resource(core, &fmri, &perr) != 0) { 440074bb90dSTom Pothier whinge(mod, &nerr, "create_core: " 441074bb90dSTom Pothier "topo_node_resource failed\n"); 442074bb90dSTom Pothier perr = 0; 443074bb90dSTom Pothier } 444074bb90dSTom Pothier 445074bb90dSTom Pothier perr += nvlist_lookup_string(fmri, 446074bb90dSTom Pothier FM_FMRI_HC_PART, &part); 447074bb90dSTom Pothier perr += nvlist_lookup_string(fmri, 448074bb90dSTom Pothier FM_FMRI_HC_REVISION, &rev); 449074bb90dSTom Pothier 450074bb90dSTom Pothier if (perr != 0) { 451074bb90dSTom Pothier whinge(mod, NULL, 452074bb90dSTom Pothier "create_core: nvlist_lookup_string failed\n"); 453074bb90dSTom Pothier perr = 0; 454074bb90dSTom Pothier } 455074bb90dSTom Pothier 456074bb90dSTom Pothier perr += topo_prop_set_string(core, PGNAME(CORE), 457074bb90dSTom Pothier FM_FMRI_HC_SERIAL_ID, TOPO_PROP_IMMUTABLE, serial, &perr); 458074bb90dSTom Pothier perr += topo_prop_set_string(core, PGNAME(CORE), 459074bb90dSTom Pothier FM_FMRI_HC_PART, TOPO_PROP_IMMUTABLE, part, &perr); 460074bb90dSTom Pothier perr += topo_prop_set_string(core, PGNAME(CORE), 461074bb90dSTom Pothier FM_FMRI_HC_REVISION, TOPO_PROP_IMMUTABLE, rev, &perr); 462074bb90dSTom Pothier 463074bb90dSTom Pothier if (perr != 0) 464074bb90dSTom Pothier whinge(mod, NULL, "create_core: topo_prop_set_string" 465074bb90dSTom Pothier "failed\n"); 466074bb90dSTom Pothier 467074bb90dSTom Pothier nvlist_free(fmri); 468074bb90dSTom Pothier topo_mod_strfree(mod, serial); 469074bb90dSTom Pothier } 470074bb90dSTom Pothier 471074bb90dSTom Pothier err = create_strand(mod, core, cpu, auth, chip_smbiosid); 472e4b86885SCheng Sean Ye 473e4b86885SCheng Sean Ye return (err == 0 && nerr == 0 ? 0 : -1); 4747aec1d6eScindi } 4757aec1d6eScindi 4767aec1d6eScindi static int 477e4b86885SCheng Sean Ye create_chip(topo_mod_t *mod, tnode_t *pnode, topo_instance_t min, 478e4b86885SCheng Sean Ye topo_instance_t max, nvlist_t *cpu, nvlist_t *auth, 479c26bf377SRob Johnston int mc_offchip, kstat_ctl_t *kc) 4807aec1d6eScindi { 481e4b86885SCheng Sean Ye tnode_t *chip; 482e4b86885SCheng Sean Ye nvlist_t *fmri = NULL; 483074bb90dSTom Pothier int err, perr, nerr = 0; 4848031591dSSrihari Venkatesan int32_t chipid, procnodeid, procnodes_per_pkg; 485c26bf377SRob Johnston const char *vendor, *brand; 4868031591dSSrihari Venkatesan int32_t family, model; 487c93c462eSCheng Sean Ye boolean_t create_mc = B_FALSE; 488074bb90dSTom Pothier uint16_t smbios_id; 4897aec1d6eScindi 490074bb90dSTom Pothier /* 491074bb90dSTom Pothier * /dev/fm will export the chipid based on SMBIOS' ordering 492074bb90dSTom Pothier * of Type-4 structures, if SMBIOS meets FMA needs 493074bb90dSTom Pothier */ 4948031591dSSrihari Venkatesan err = nvlist_lookup_pairs(cpu, 0, 4958031591dSSrihari Venkatesan FM_PHYSCPU_INFO_CHIP_ID, DATA_TYPE_INT32, &chipid, 4968031591dSSrihari Venkatesan FM_PHYSCPU_INFO_NPROCNODES, DATA_TYPE_INT32, &procnodes_per_pkg, 4978031591dSSrihari Venkatesan FM_PHYSCPU_INFO_PROCNODE_ID, DATA_TYPE_INT32, &procnodeid, 4988031591dSSrihari Venkatesan FM_PHYSCPU_INFO_VENDOR_ID, DATA_TYPE_STRING, &vendor, 4998031591dSSrihari Venkatesan FM_PHYSCPU_INFO_FAMILY, DATA_TYPE_INT32, &family, 5008031591dSSrihari Venkatesan FM_PHYSCPU_INFO_MODEL, DATA_TYPE_INT32, &model, 5018031591dSSrihari Venkatesan NULL); 5028031591dSSrihari Venkatesan 5038031591dSSrihari Venkatesan if (err) { 5048031591dSSrihari Venkatesan whinge(mod, NULL, "create_chip: lookup failed: %s\n", 505e4b86885SCheng Sean Ye strerror(err)); 506e4b86885SCheng Sean Ye return (-1); 5077aec1d6eScindi } 5087aec1d6eScindi 509e4b86885SCheng Sean Ye if (chipid < min || chipid > max) 510e4b86885SCheng Sean Ye return (-1); 5117aec1d6eScindi 512074bb90dSTom Pothier if (FM_AWARE_SMBIOS(mod)) { 513074bb90dSTom Pothier if ((err = nvlist_lookup_uint16(cpu, 514074bb90dSTom Pothier FM_PHYSCPU_INFO_SMBIOS_ID, &smbios_id)) != 0) { 515074bb90dSTom Pothier whinge(mod, NULL, 516074bb90dSTom Pothier "create_chip: lookup smbios_id failed" 517074bb90dSTom Pothier ": enumerating x86pi & chip topology, but" 518074bb90dSTom Pothier " no Chip properties from SMBIOS" 519074bb90dSTom Pothier " - err msg : %s\n", strerror(err)); 520074bb90dSTom Pothier /* 521074bb90dSTom Pothier * Lets reset the module specific 522074bb90dSTom Pothier * data to NULL, overriding any 523074bb90dSTom Pothier * SMBIOS capability encoded earlier. 524074bb90dSTom Pothier * This will fail all subsequent 525074bb90dSTom Pothier * FM_AWARE_SMBIOS checks. 526074bb90dSTom Pothier */ 527074bb90dSTom Pothier topo_mod_setspecific(mod, NULL); 528074bb90dSTom Pothier } 529074bb90dSTom Pothier } 530074bb90dSTom Pothier 531e4b86885SCheng Sean Ye if ((chip = topo_node_lookup(pnode, CHIP_NODE_NAME, chipid)) == NULL) { 532e4b86885SCheng Sean Ye if ((chip = create_node(mod, pnode, auth, CHIP_NODE_NAME, 5332a613b59SRobert Mustacchi chipid, cpu, smbios_id)) == NULL) 534e4b86885SCheng Sean Ye return (-1); 535074bb90dSTom Pothier /* 536074bb90dSTom Pothier * Do not register XML map methods if SMBIOS can provide 537074bb90dSTom Pothier * serial, part, revision & label 538074bb90dSTom Pothier */ 539074bb90dSTom Pothier if (!FM_AWARE_SMBIOS(mod)) { 540074bb90dSTom Pothier if (topo_method_register(mod, chip, chip_methods) < 0) 541074bb90dSTom Pothier whinge(mod, &nerr, "create_chip: " 542074bb90dSTom Pothier "topo_method_register failed\n"); 5437aec1d6eScindi } 5447aec1d6eScindi 545e4b86885SCheng Sean Ye (void) topo_pgroup_create(chip, &chip_pgroup, &err); 546e4b86885SCheng Sean Ye nerr -= add_nvlist_strprop(mod, chip, cpu, PGNAME(CHIP), 5478031591dSSrihari Venkatesan CHIP_VENDOR_ID, NULL); 548e4b86885SCheng Sean Ye nerr -= add_nvlist_longprops(mod, chip, cpu, PGNAME(CHIP), 5498031591dSSrihari Venkatesan NULL, CHIP_FAMILY, CHIP_MODEL, CHIP_STEPPING, NULL); 5504557a2a1Srobj 551c26bf377SRob Johnston /* 552c26bf377SRob Johnston * Attempt to lookup the processor brand string in kstats. 553c26bf377SRob Johnston * and add it as a prop, if found. 554c26bf377SRob Johnston */ 555c26bf377SRob Johnston brand = get_chip_brand(mod, kc, chipid); 556c26bf377SRob Johnston if (brand != NULL && topo_prop_set_string(chip, PGNAME(CHIP), 557c26bf377SRob Johnston CHIP_BRAND, TOPO_PROP_IMMUTABLE, brand, &perr) != 0) { 558c26bf377SRob Johnston whinge(mod, &nerr, "failed to set prop %s/%s", 559c26bf377SRob Johnston PGNAME(CHIP), CHIP_BRAND); 560c26bf377SRob Johnston } 561c26bf377SRob Johnston topo_mod_strfree(mod, (char *)brand); 562c26bf377SRob Johnston 563074bb90dSTom Pothier if (FM_AWARE_SMBIOS(mod)) { 564074bb90dSTom Pothier int fru = 0; 565074bb90dSTom Pothier char *serial = NULL; 566074bb90dSTom Pothier char *part = NULL; 567074bb90dSTom Pothier char *rev = NULL; 568074bb90dSTom Pothier char *label; 569074bb90dSTom Pothier 570074bb90dSTom Pothier fru = chip_fru_smbios_get(mod, smbios_id); 571074bb90dSTom Pothier /* 572074bb90dSTom Pothier * Chip is not a FRU, set the FRU fmri of parent node 573074bb90dSTom Pothier */ 574074bb90dSTom Pothier if (topo_node_resource(chip, &fmri, &perr) != 0) 575074bb90dSTom Pothier whinge(mod, &nerr, "create_chip: " 576074bb90dSTom Pothier "topo_node_resource failed\n"); 577074bb90dSTom Pothier if (!fru) { 578074bb90dSTom Pothier (void) topo_node_fru_set(chip, NULL, 0, &perr); 579074bb90dSTom Pothier label = NULL; 580074bb90dSTom Pothier } else { 581074bb90dSTom Pothier label = (char *)chip_label_smbios_get(mod, 582074bb90dSTom Pothier pnode, smbios_id, NULL); 583074bb90dSTom Pothier 584074bb90dSTom Pothier if (topo_node_fru_set(chip, fmri, 0, &perr) 585074bb90dSTom Pothier != 0) { 586074bb90dSTom Pothier whinge(mod, NULL, "create_chip: " 587074bb90dSTom Pothier "topo_node_fru_set failed\n"); 588074bb90dSTom Pothier perr = 0; 589074bb90dSTom Pothier } 590074bb90dSTom Pothier } 591074bb90dSTom Pothier 592074bb90dSTom Pothier perr += nvlist_lookup_string(fmri, 593074bb90dSTom Pothier FM_FMRI_HC_SERIAL_ID, &serial); 594074bb90dSTom Pothier perr += nvlist_lookup_string(fmri, 595074bb90dSTom Pothier FM_FMRI_HC_PART, &part); 596074bb90dSTom Pothier perr += nvlist_lookup_string(fmri, 597074bb90dSTom Pothier FM_FMRI_HC_REVISION, &rev); 598074bb90dSTom Pothier 599074bb90dSTom Pothier if (perr != 0) { 600074bb90dSTom Pothier whinge(mod, NULL, 601074bb90dSTom Pothier "create_chip: nvlist_lookup_string" 602074bb90dSTom Pothier "failed\n"); 603074bb90dSTom Pothier perr = 0; 604074bb90dSTom Pothier } 605074bb90dSTom Pothier 606074bb90dSTom Pothier perr += topo_prop_set_string(chip, PGNAME(CHIP), 607074bb90dSTom Pothier FM_FMRI_HC_SERIAL_ID, TOPO_PROP_IMMUTABLE, 608074bb90dSTom Pothier serial, &perr); 609074bb90dSTom Pothier perr += topo_prop_set_string(chip, PGNAME(CHIP), 610074bb90dSTom Pothier FM_FMRI_HC_PART, TOPO_PROP_IMMUTABLE, 611074bb90dSTom Pothier part, &perr); 612074bb90dSTom Pothier perr += topo_prop_set_string(chip, PGNAME(CHIP), 613074bb90dSTom Pothier FM_FMRI_HC_REVISION, TOPO_PROP_IMMUTABLE, 614074bb90dSTom Pothier rev, &perr); 615074bb90dSTom Pothier 616074bb90dSTom Pothier if (perr != 0) 617074bb90dSTom Pothier whinge(mod, NULL, 618074bb90dSTom Pothier "create_chip: topo_prop_set_string" 619074bb90dSTom Pothier "failed\n"); 620074bb90dSTom Pothier 621074bb90dSTom Pothier nvlist_free(fmri); 622074bb90dSTom Pothier 623074bb90dSTom Pothier if (topo_node_label_set(chip, label, &perr) 624074bb90dSTom Pothier == -1) { 625074bb90dSTom Pothier whinge(mod, NULL, "create_chip: " 626074bb90dSTom Pothier "topo_node_label_set failed\n"); 627074bb90dSTom Pothier } 628074bb90dSTom Pothier topo_mod_strfree(mod, label); 629074bb90dSTom Pothier 630074bb90dSTom Pothier } else { 631074bb90dSTom Pothier if (topo_node_resource(chip, &fmri, &err) == -1) { 632074bb90dSTom Pothier whinge(mod, &nerr, "create_chip: " 633074bb90dSTom Pothier "topo_node_resource failed\n"); 634074bb90dSTom Pothier } else { 635074bb90dSTom Pothier (void) topo_node_fru_set(chip, fmri, 0, &perr); 636074bb90dSTom Pothier nvlist_free(fmri); 637074bb90dSTom Pothier } 638074bb90dSTom Pothier } 639074bb90dSTom Pothier 640e4b86885SCheng Sean Ye if (topo_method_register(mod, chip, strands_retire_methods) < 0) 641e4b86885SCheng Sean Ye whinge(mod, &nerr, "create_chip: " 642e4b86885SCheng Sean Ye "topo_method_register failed\n"); 6437aec1d6eScindi 6448031591dSSrihari Venkatesan if (topo_node_range_create(mod, chip, CORE_NODE_NAME, 0, 255)) 645e4b86885SCheng Sean Ye return (-1); 646c93c462eSCheng Sean Ye 6478031591dSSrihari Venkatesan if (strcmp(vendor, "AuthenticAMD") == 0) { 6488031591dSSrihari Venkatesan if (topo_node_range_create(mod, chip, MCT_NODE_NAME, 6498031591dSSrihari Venkatesan 0, 255)) 6508031591dSSrihari Venkatesan return (-1); 6518031591dSSrihari Venkatesan } 6528031591dSSrihari Venkatesan 653c93c462eSCheng Sean Ye create_mc = B_TRUE; 654*f2dbfd32SRobert Mustacchi 655*f2dbfd32SRobert Mustacchi /* 656*f2dbfd32SRobert Mustacchi * Creating a temperature sensor may fail because the sensor 657*f2dbfd32SRobert Mustacchi * doesn't exist or due to internal reasons. At the moment, we 658*f2dbfd32SRobert Mustacchi * swallow any such errors that occur. 659*f2dbfd32SRobert Mustacchi */ 660*f2dbfd32SRobert Mustacchi (void) chip_create_chip_temp_sensor(mod, chip); 661e4b86885SCheng Sean Ye } 6627aec1d6eScindi 663074bb90dSTom Pothier if (FM_AWARE_SMBIOS(mod)) { 664074bb90dSTom Pothier int status = 0; 665074bb90dSTom Pothier /* 666074bb90dSTom Pothier * STATUS 667074bb90dSTom Pothier * CPU Socket Populated 668074bb90dSTom Pothier * CPU Socket Unpopulated 669074bb90dSTom Pothier * Populated : Enabled 670074bb90dSTom Pothier * Populated : Disabled by BIOS (Setup) 671074bb90dSTom Pothier * Populated : Disabled by BIOS (Error) 672074bb90dSTom Pothier * Populated : Idle 673074bb90dSTom Pothier * 674074bb90dSTom Pothier * Enumerate core & strand only for Populated : Enabled 675074bb90dSTom Pothier * Enumerate Off-Chip Memory Controller only for 676074bb90dSTom Pothier * Populated : Enabled 677074bb90dSTom Pothier */ 678074bb90dSTom Pothier 679074bb90dSTom Pothier status = chip_status_smbios_get(mod, (id_t)smbios_id); 680074bb90dSTom Pothier if (!status) { 681074bb90dSTom Pothier whinge(mod, NULL, "create_chip: " 682074bb90dSTom Pothier "CPU Socket is not populated or is disabled\n"); 683074bb90dSTom Pothier return (0); 684074bb90dSTom Pothier } 685074bb90dSTom Pothier } 686074bb90dSTom Pothier 687074bb90dSTom Pothier err = create_core(mod, chip, cpu, auth, smbios_id); 6889dd0f810Scindi 689e4b86885SCheng Sean Ye /* 690e4b86885SCheng Sean Ye * Create memory-controller node under a chip for architectures 691e4b86885SCheng Sean Ye * that may have on-chip memory-controller(s). 692074bb90dSTom Pothier * If SMBIOS meets FMA needs, when Multi-Chip-Module is 693074bb90dSTom Pothier * addressed, mc instances should be derived from SMBIOS 694e4b86885SCheng Sean Ye */ 6958031591dSSrihari Venkatesan if (strcmp(vendor, "AuthenticAMD") == 0) { 6968031591dSSrihari Venkatesan amd_mc_create(mod, smbios_id, chip, MCT_NODE_NAME, auth, 6978031591dSSrihari Venkatesan procnodeid, procnodes_per_pkg, family, model, &nerr); 6988031591dSSrihari Venkatesan } else if (create_mc && !mc_offchip) 6998031591dSSrihari Venkatesan onchip_mc_create(mod, smbios_id, chip, MCT_NODE_NAME, auth); 7007aec1d6eScindi 701e4b86885SCheng Sean Ye return (err == 0 && nerr == 0 ? 0 : -1); 702e4b86885SCheng Sean Ye } 703e3d60c9bSAdrian Frost 704e4b86885SCheng Sean Ye /*ARGSUSED*/ 705e4b86885SCheng Sean Ye static int 706e4b86885SCheng Sean Ye create_chips(topo_mod_t *mod, tnode_t *pnode, const char *name, 707e4b86885SCheng Sean Ye topo_instance_t min, topo_instance_t max, void *arg, nvlist_t *auth, 708e4b86885SCheng Sean Ye int mc_offchip) 709e4b86885SCheng Sean Ye { 710e4b86885SCheng Sean Ye fmd_agent_hdl_t *hdl; 711e4b86885SCheng Sean Ye nvlist_t **cpus; 712e4b86885SCheng Sean Ye int nerr = 0; 713e4b86885SCheng Sean Ye uint_t i, ncpu; 714c26bf377SRob Johnston kstat_ctl_t *kc; 71520c794b3Sgavinm 716e4b86885SCheng Sean Ye if (strcmp(name, CHIP_NODE_NAME) != 0) 717e4b86885SCheng Sean Ye return (0); 718e4b86885SCheng Sean Ye 719e4b86885SCheng Sean Ye if ((hdl = fmd_agent_open(FMD_AGENT_VERSION)) == NULL) 720e4b86885SCheng Sean Ye return (-1); 721e4b86885SCheng Sean Ye if (fmd_agent_physcpu_info(hdl, &cpus, &ncpu) != 0) { 722e4b86885SCheng Sean Ye whinge(mod, NULL, "create_chip: fmd_agent_physcpu_info " 723e4b86885SCheng Sean Ye "failed: %s\n", fmd_agent_errmsg(hdl)); 724e4b86885SCheng Sean Ye fmd_agent_close(hdl); 725e4b86885SCheng Sean Ye return (-1); 7267aec1d6eScindi } 727e4b86885SCheng Sean Ye fmd_agent_close(hdl); 7287aec1d6eScindi 729c26bf377SRob Johnston if ((kc = kstat_open()) == NULL) { 730c26bf377SRob Johnston whinge(mod, NULL, "kstat_open() failed"); 731c26bf377SRob Johnston return (topo_mod_seterrno(mod, EMOD_PARTIAL_ENUM)); 732c26bf377SRob Johnston } 733c26bf377SRob Johnston 734e4b86885SCheng Sean Ye for (i = 0; i < ncpu; i++) { 735e4b86885SCheng Sean Ye nerr -= create_chip(mod, pnode, min, max, cpus[i], auth, 736c26bf377SRob Johnston mc_offchip, kc); 737e4b86885SCheng Sean Ye nvlist_free(cpus[i]); 738e4b86885SCheng Sean Ye } 739c26bf377SRob Johnston (void) kstat_close(kc); 740e4b86885SCheng Sean Ye umem_free(cpus, sizeof (nvlist_t *) * ncpu); 7417aec1d6eScindi 7428a40a695Sgavinm if (nerr == 0) { 7438a40a695Sgavinm return (0); 7448a40a695Sgavinm } else { 7457aec1d6eScindi (void) topo_mod_seterrno(mod, EMOD_PARTIAL_ENUM); 7468a40a695Sgavinm return (-1); 7478a40a695Sgavinm } 7487aec1d6eScindi } 7497aec1d6eScindi 7500eb822a1Scindi /*ARGSUSED*/ 7517aec1d6eScindi static int 7527aec1d6eScindi chip_enum(topo_mod_t *mod, tnode_t *pnode, const char *name, 753074bb90dSTom Pothier topo_instance_t min, topo_instance_t max, void *arg, void *smbios_enabled) 7547aec1d6eScindi { 7550eb822a1Scindi int rv = 0; 7560eb822a1Scindi nvlist_t *auth = NULL; 757e3d60c9bSAdrian Frost int offchip_mc; 758e4b86885SCheng Sean Ye char buf[BUFSIZ]; 759e4b86885SCheng Sean Ye const char *dom0 = "control_d"; 760e4b86885SCheng Sean Ye 761e4b86885SCheng Sean Ye /* 762e4b86885SCheng Sean Ye * Create nothing if we're running in domU. 763e4b86885SCheng Sean Ye */ 764e4b86885SCheng Sean Ye if (sysinfo(SI_PLATFORM, buf, sizeof (buf)) == -1) 765e4b86885SCheng Sean Ye return (-1); 766e4b86885SCheng Sean Ye 767e4b86885SCheng Sean Ye if (strncmp(buf, "i86pc", sizeof (buf)) != 0 && 768e4b86885SCheng Sean Ye strncmp(buf, "i86xpv", sizeof (buf)) != 0) 769e4b86885SCheng Sean Ye return (0); 770e4b86885SCheng Sean Ye 771e4b86885SCheng Sean Ye if (strncmp(buf, "i86xpv", sizeof (buf)) == 0) { 772e4b86885SCheng Sean Ye int fd = open("/dev/xen/domcaps", O_RDONLY); 773e4b86885SCheng Sean Ye 774e4b86885SCheng Sean Ye if (fd != -1) { 775e4b86885SCheng Sean Ye if (read(fd, buf, sizeof (buf)) <= 0 || 776e4b86885SCheng Sean Ye strncmp(buf, dom0, strlen(dom0)) != 0) { 777e4b86885SCheng Sean Ye (void) close(fd); 778e4b86885SCheng Sean Ye return (0); 779e4b86885SCheng Sean Ye } 780e4b86885SCheng Sean Ye (void) close(fd); 781e4b86885SCheng Sean Ye } 782e4b86885SCheng Sean Ye } 7830eb822a1Scindi 784074bb90dSTom Pothier /* 785074bb90dSTom Pothier * Set Chip Enumerator Module's private data with the value passed by 786074bb90dSTom Pothier * x86pi Enumerator, defining SMBIOS capabilities 787074bb90dSTom Pothier */ 788074bb90dSTom Pothier topo_mod_setspecific(mod, smbios_enabled); 789074bb90dSTom Pothier 790074bb90dSTom Pothier if (FM_AWARE_SMBIOS(mod)) 791074bb90dSTom Pothier if (init_chip_smbios(mod) != 0) { 792074bb90dSTom Pothier whinge(mod, NULL, 793074bb90dSTom Pothier "init_chip_smbios() failed, " 794074bb90dSTom Pothier " enumerating x86pi & chip topology, but no" 795074bb90dSTom Pothier " CPU & Memory properties will be" 796074bb90dSTom Pothier " derived from SMBIOS\n"); 797074bb90dSTom Pothier /* 798074bb90dSTom Pothier * Lets reset the module specific 799074bb90dSTom Pothier * data to NULL, overriding any 800074bb90dSTom Pothier * SMBIOS capability encoded earlier. 801074bb90dSTom Pothier * This will fail all subsequent 802074bb90dSTom Pothier * FM_AWARE_SMBIOS checks. 803074bb90dSTom Pothier */ 804074bb90dSTom Pothier topo_mod_setspecific(mod, NULL); 805074bb90dSTom Pothier } 806074bb90dSTom Pothier 8070eb822a1Scindi auth = topo_mod_auth(mod, pnode); 8087aec1d6eScindi 809e3d60c9bSAdrian Frost offchip_mc = mc_offchip_open(); 8109dd0f810Scindi if (strcmp(name, CHIP_NODE_NAME) == 0) 811e4b86885SCheng Sean Ye rv = create_chips(mod, pnode, name, min, max, NULL, auth, 812e3d60c9bSAdrian Frost offchip_mc); 8137aec1d6eScindi 814e3d60c9bSAdrian Frost if (offchip_mc) 81520c794b3Sgavinm (void) mc_offchip_create(mod, pnode, "memory-controller", auth); 81620c794b3Sgavinm 8170eb822a1Scindi nvlist_free(auth); 8180eb822a1Scindi 8190eb822a1Scindi return (rv); 8207aec1d6eScindi } 821