blob: c83b019eb00808b1280aa6832320aa7dd2d95b92 [file] [log] [blame]
From d8c341b72aad30bff1417f1a2cec82af9cc14786 Mon Sep 17 00:00:00 2001
From: Richard J. Knight <rjknight@us.ibm.com>
Date: Thu, 19 Feb 2015 23:47:03 -0600
Subject: [PATCH 2/5] Update dev tree with additional sensor information
-Add sensor type, reading type and specific offsets.
-Add IPMI entity ID and instance information for sensors
-Include IPMI Enity instance in targets which have ipmi sensors
attribute
Change-Id: I02b0a5046c67e2e00af30a0c78cbcc182ae4c0cd
RTC:123186
(cherry picked from commit ff8c81ac1ab76d9835165a8dae4a0e3b1e5a0055)
---
src/include/usr/ipmi/ipmisensor.H | 96 ++++++++++++++++++++
src/usr/devtree/bld_devtree.C | 89 ++++++++++++++-----
src/usr/ipmi/ipmisensor.C | 76 ++++++++++++++++
src/usr/targeting/common/Targets.pm | 2 +-
.../common/xmltohb/attribute_types_hb.xml | 73 +++++++++++++++
.../targeting/common/xmltohb/target_types_hb.xml | 12 ++-
6 files changed, 322 insertions(+), 26 deletions(-)
diff --git a/src/include/usr/ipmi/ipmisensor.H b/src/include/usr/ipmi/ipmisensor.H
index 7b4e3fa..ef00bfa 100644
--- a/src/include/usr/ipmi/ipmisensor.H
+++ b/src/include/usr/ipmi/ipmisensor.H
@@ -48,6 +48,20 @@ namespace SENSOR
const uint8_t INVALID_TYPE = 0xFF;
/**
+ * @enum sensorReadingTypes
+ * Sensor specific completion codes, defined in IPMI Spec.
+ *
+ */
+ enum sensorReadingType
+ {
+ THRESHOLD = 0x01,
+ DIGITAL_ASSERT_DEASSERT = 0x03,
+ DIGITAL_ENABLE_DISABLE = 0x09,
+ SENSOR_SPECIFIC = 0x6f,
+ };
+
+
+ /**
* @enum procStatusSensorOffsets
* Sensor specific completion codes, defined in IPMI Spec.
*
@@ -90,6 +104,74 @@ namespace SENSOR
CRITICAL_OVER_TEMP = 0x0A,
};
+ /**
+ * @enum firmwareBootProgressSensorOffsets
+ * Boot progress specific offsets defined in IPMI Spec.
+ *
+ */
+ enum firmwareProgressSensorOffsets
+ {
+ // offset 02h
+ SYSTEM_FIRMWARE_PROGRESS = 0x02,
+ };
+
+ /**
+ * @enum discrete09_Offsets
+ *
+ * Offsets specific to IPMI sensor reading type 09
+ * digital discrete senosrs. These offsets result in
+ * Device Enabled or Device Disabled events in the
+ * BMC event log.
+ *
+ */
+ enum discrete09_Offsets
+ {
+ // offset 00h
+ DEVICE_DISABLED = 0x0,
+
+ //offset 01h
+ DEVICE_ENABLED = 0x1,
+ };
+
+ /**
+ * @enum discrete03_Offsets
+ *
+ * Offsets specific to IPMI sensor reading type 03
+ * digital discrete senosrs. These offsets result in generic
+ * State Asserted or State Deasserted events in the
+ * BMC event log.
+ *
+ */
+ enum discrete03_Offsets
+ {
+ // offset 00h
+ DEASSERTED = 0x00,
+
+ //offset 01h
+ ASSERTED = 0x01,
+ };
+
+ /**
+ * @enum acpiPowerState_Offsets
+ *
+ * Offsets specific to IPMI ACPI Power state
+ * senosrs. These offsets result in power
+ * state messages in the BMC event log.
+ *
+ */
+ enum acpiPowerState_Offsets
+ {
+ // offset 0h
+ S0_G0_WORKING = 0x00,
+
+ // offset 05h
+ G5_SOFT_OFF = 0x05,
+
+ //offset 0Bh
+ LEGACY_ON = 0x0B,
+
+ };
+
//** Bit definition for set sensor reading cmd operation field
// [7:6] 10b - write given values to event data bytes let BMC handle
// offset in event data 1 when an external event is
@@ -827,6 +909,20 @@ namespace SENSOR
errlHndl_t getAPSSChannelSensorNumbers(
const uint16_t (* &o_sensor_numbers)[16]);
+ /**
+ * Helper function to return a mask of the supported masks for the
+ * sensor passed in.
+ *
+ * @param[i] - sensor name to determine the offset for.
+ * @param[o] - sensor reading type, defined in IPMI spec for the
+ * passed in sensor number.
+ *
+ *
+ * @return sensor offsets
+ */
+ uint16_t getSensorOffsets(TARGETING::SENSOR_NAME i_name,
+ sensorReadingType &o_readType );
+
}; // end namespace
diff --git a/src/usr/devtree/bld_devtree.C b/src/usr/devtree/bld_devtree.C
index dd81392..f4647a3 100644
--- a/src/usr/devtree/bld_devtree.C
+++ b/src/usr/devtree/bld_devtree.C
@@ -1299,17 +1299,40 @@ errlHndl_t bld_fdt_mem(devTree * i_dt, bool i_smallTree)
return errhdl;
}
+
+#ifdef CONFIG_BMC_IPMI
+enum
+{
+ ENTITY_ID_MASK = 0x00FF,
+ SENSOR_TYPE_MASK = 0xFF00,
+};
+
/* create a node for each IPMI sensor in the system, the sensor unit number
corresponds to the BMC assigned sensor number */
uint32_t bld_sensor_node(devTree * i_dt, const dtOffset_t & i_parentNode,
- const uint16_t sensorData[] )
+ const uint16_t sensorData[],
+ uint32_t instance, uint32_t chipId )
{
- const uint32_t sensorNumber = sensorData[
+ SENSOR::sensorReadingType readType;
+
+ // pass in the sensor name to get back the supported offsets and the event
+ // reading type for this sensor.
+ uint32_t offsets = SENSOR::getSensorOffsets(
+ static_cast<TARGETING::SENSOR_NAME>(
+ sensorData[TARGETING::IPMI_SENSOR_ARRAY_NAME_OFFSET]),
+ readType);
+
+ const uint16_t sensorNumber = sensorData[
TARGETING::IPMI_SENSOR_ARRAY_NUMBER_OFFSET];
- const uint32_t sensorName =
- sensorData[TARGETING::IPMI_SENSOR_ARRAY_NAME_OFFSET];
+ // the sensor name is a combination of the sensor type + entity ID
+ const uint16_t sensorType = (
+ sensorData[TARGETING::IPMI_SENSOR_ARRAY_NAME_OFFSET]
+ & SENSOR_TYPE_MASK) >> 8;
+
+ const uint16_t entityId =
+ sensorData[TARGETING::IPMI_SENSOR_ARRAY_NAME_OFFSET] & ENTITY_ID_MASK;
/* Build sensor node based on sensor number */
dtOffset_t sensorNode = i_dt->addNode(i_parentNode, "sensor", sensorNumber);
@@ -1317,22 +1340,35 @@ uint32_t bld_sensor_node(devTree * i_dt, const dtOffset_t & i_parentNode,
i_dt->addPropertyCell32(sensorNode, "reg", sensorNumber);
// add sensor type
- i_dt->addPropertyCell32(sensorNode, "ipmi-sensor-type", sensorName);
-
- // @TODO RTC:113902
- // get more info from Ben H. regarding what info he needs
- // add the name of the sensor
- //i_dt->addPropertyString(sensorNode, "name", sensorToString( sensorName ));
- // i_dt->addPropertyCell32(sensorNode, "ipmi-entity-type",
- // sensorData[ENTITY_TYPE_OFFSET]);
- // i_dt->addPropertyCell32(sensorNode, "ipmi-reading-type",
- // sensorData[READING_TYPE_OFFSET]);
-
- /* return the phandle for this sensor, might need to add it to the
- cpus node per Ben H. proposal */
+ i_dt->addPropertyCell32(sensorNode, "ipmi-sensor-type", sensorType);
+ i_dt->addPropertyCell32(sensorNode, "ipmi-entity-id", entityId);
+ i_dt->addPropertyCell32(sensorNode, "ipmi-entity-instance", instance);
+ i_dt->addPropertyCell32(sensorNode, "ipmi-sensor-offsets", offsets);
+ i_dt->addPropertyCell32(sensorNode, "ipmi-sensor-reading-type", readType);
+
+ // currently we only add the chip ID to the OCC sensor
+ if(chipId != 0xFF )
+ {
+ i_dt->addPropertyCell32(sensorNode, "ibm,chip-id", chipId);
+ }
+
+ /* return the phandle for this sensor */
return i_dt->getPhandle(sensorNode);
}
+// return the IPMI entity instance from the SDR for this
+// target.
+uint32_t getInstanceNumber( TARGETING::Target * i_pTarget )
+{
+ AttributeTraits<ATTR_IPMI_INSTANCE>::Type l_instance;
+
+ l_instance = i_pTarget->getAttr<TARGETING::ATTR_IPMI_INSTANCE>();
+
+ return l_instance;
+
+}
+
+// build the sensor node for a given target
uint32_t bld_sensor_node(devTree * i_dt, const dtOffset_t & i_sensorNode,
TARGETING::Target * i_pTarget )
{
@@ -1344,6 +1380,17 @@ uint32_t bld_sensor_node(devTree * i_dt, const dtOffset_t & i_sensorNode,
* for each sensor */
if ( i_pTarget->tryGetAttr<ATTR_IPMI_SENSORS>(l_sensors) )
{
+ uint32_t chipId = 0xFF;
+
+ // add the chip id to the OCC sensor since OPAL needs it to figure out
+ // which OCC it is.
+ if( TARGETING::TYPE_OCC == i_pTarget->getAttr<TARGETING::ATTR_TYPE>())
+ {
+ ConstTargetHandle_t proc = getParentChip(i_pTarget);
+
+ chipId = getProcChipId( proc );
+ }
+
for(uint16_t i=0; i< array_rows; i++)
{
/* if the sensor number is 0xFF move on */
@@ -1351,7 +1398,8 @@ uint32_t bld_sensor_node(devTree * i_dt, const dtOffset_t & i_sensorNode,
{
/* use this row to create the next sensor node - ignoring
* return value for now */
- bld_sensor_node(i_dt, i_sensorNode, l_sensors[i] );
+ bld_sensor_node(i_dt, i_sensorNode, l_sensors[i],
+ getInstanceNumber(i_pTarget) , chipId );
}
else
{
@@ -1394,10 +1442,6 @@ errlHndl_t bld_fdt_sensors(devTree * i_dt, const dtOffset_t & i_parentNode,
i_dt->addPropertyCell32(sensorNode, "#address-cells", 1);
i_dt->addPropertyCell32(sensorNode, "#size-cells", 0);
- // pass ALL IPMI_SENSORS to opal
- // @TODO RTC:113902 - add remaining sensor info and limit sensors
- // and adjust the sensors passed to opal to match their requirements
-
/* loop through all the targets and get the IPMI sensor data if it
exists */
for (TargetIterator itr = TARGETING::targetService().begin();
@@ -1454,6 +1498,7 @@ errlHndl_t bld_fdt_bmc(devTree * i_dt, bool i_smallTree)
return errhdl;
}
+#endif
errlHndl_t bld_fdt_vpd(devTree * i_dt, bool i_smallTree)
{
diff --git a/src/usr/ipmi/ipmisensor.C b/src/usr/ipmi/ipmisensor.C
index 3e15e91..fc7284b 100644
--- a/src/usr/ipmi/ipmisensor.C
+++ b/src/usr/ipmi/ipmisensor.C
@@ -1121,4 +1121,80 @@ namespace SENSOR
return NULL;
}
+ uint16_t getSensorOffsets( TARGETING::SENSOR_NAME i_name,
+ sensorReadingType &o_readType )
+ {
+
+ uint16_t offsets = 0;
+
+ // most of our sensors use generic sensor specific reading types
+ // so use that as the default value
+ o_readType = SENSOR_SPECIFIC;
+
+ // sensor type is lower byte of sensor name, if we dont match
+ // based on name, then try the sensor type
+ uint16_t t = ( i_name >> 8 ) & 0x00FF;
+
+ switch( i_name )
+ {
+ case TARGETING::SENSOR_NAME_FW_BOOT_PROGRESS:
+ {
+ offsets = ( 1 << SYSTEM_FIRMWARE_PROGRESS );
+ break;
+ }
+ case TARGETING::SENSOR_NAME_OCC_ACTIVE:
+ {
+ offsets = ( 1 << DEVICE_DISABLED ) |
+ ( 1 << DEVICE_ENABLED );
+ o_readType = DIGITAL_ENABLE_DISABLE;
+ break;
+ }
+ case TARGETING::SENSOR_NAME_HOST_STATUS:
+ {
+ offsets = ( 1 << S0_G0_WORKING ) |
+ ( 1 << G5_SOFT_OFF ) |
+ ( 1 << LEGACY_ON );
+ break;
+ }
+ case TARGETING::SENSOR_NAME_PCI_ACTIVE:
+ case TARGETING::SENSOR_NAME_OS_BOOT:
+ {
+ // default all offsets enabled
+ offsets = 0x7FFF;
+ break;
+ }
+
+ default:
+ {
+ // try sensor type
+ switch (t)
+ {
+ case TARGETING::SENSOR_TYPE_FAULT:
+ offsets = ( 1 << ASSERTED );
+ o_readType = DIGITAL_ASSERT_DEASSERT;
+ break;
+
+ case TARGETING::SENSOR_TYPE_PROCESSOR:
+ offsets = ( 1 << PROC_PRESENCE_DETECTED ) |
+ ( 1 << PROC_DISABLED ) |
+ ( 1 << IERR );
+ break;
+
+ case TARGETING::SENSOR_TYPE_MEMORY:
+ offsets = ( 1 << MEMORY_DEVICE_DISABLED ) |
+ ( 1 << MEM_DEVICE_PRESENCE_DETECTED );
+ break;
+ default:
+ offsets = 0;
+ o_readType = THRESHOLD;
+ break;
+ }
+
+ }
+ }
+
+ return offsets;
+ }
+
+
}; // end name space
diff --git a/src/usr/targeting/common/Targets.pm b/src/usr/targeting/common/Targets.pm
index eb1ea1f..29f6bcb 100644
--- a/src/usr/targeting/common/Targets.pm
+++ b/src/usr/targeting/common/Targets.pm
@@ -195,7 +195,7 @@ sub printAttribute
$filter{ENTITY_ID_LOOKUP} = 1;
$filter{ENTITY_INSTANCE} = 1;
$filter{MBA_NUM} = 1;
- $filter{IPMI_INSTANCE} = 1;
+ $filter{IPMI_INSTANCE} = 0;
$filter{IPMI_NAME} = 1;
$filter{INSTANCE_ID} = 1;
#$filter{ADC_CHANNEL_SENSOR_NUMBERS} = 1;
diff --git a/src/usr/targeting/common/xmltohb/attribute_types_hb.xml b/src/usr/targeting/common/xmltohb/attribute_types_hb.xml
index 3bb57e6..74fb492 100644
--- a/src/usr/targeting/common/xmltohb/attribute_types_hb.xml
+++ b/src/usr/targeting/common/xmltohb/attribute_types_hb.xml
@@ -822,6 +822,16 @@
<writeable/>
<hbOnly/>
</attribute>
+<attribute>
+ <id>IPMI_INSTANCE</id>
+ <description>Holds the IPMI instance number for this entity.</description>
+ <simpleType>
+ <uint32_t>
+ </uint32_t>
+ </simpleType>
+ <persistency>non-volatile</persistency>
+ <readable/>
+</attribute>
<enumerationType>
<id>ENTITY_ID</id>
<description>Enumeration indicating the IPMI entity ID, these values are
@@ -1003,6 +1013,69 @@
</enumerator>
</enumerationType>
+<enumerationType>
+ <id>SENSOR_TYPE</id>
+ <description>Enumeration indicating the IPMI sensor type, these values
+ are defined in the IPMI specification. These values will be used when
+ sending sensor reading events to the BMC.</description>
+ <enumerator>
+ <name>NA</name>
+ <value>0</value>
+ </enumerator>
+ <enumerator>
+ <name>TEMPERATURE</name>
+ <value>0x01</value>
+ </enumerator>
+ <enumerator>
+ <name>PROCESSOR</name>
+ <value>0x07</value>
+ </enumerator>
+ <enumerator>
+ <name>MEMORY</name>
+ <value>0x0c</value>
+ </enumerator>
+ <enumerator>
+ <name>SYS_FW_PROGRESS</name>
+ <value>0x0F</value>
+ </enumerator>
+ <enumerator>
+ <name>SYS_EVENT</name>
+ <value>0x12</value>
+ </enumerator>
+ <enumerator>
+ <name>OS_BOOT</name>
+ <value>0x1F</value>
+ </enumerator>
+ <enumerator>
+ <name>APCI_POWER_STATE</name>
+ <value>0x22</value>
+ </enumerator>
+ <enumerator>
+ <name>FREQ</name>
+ <value>0xC1</value>
+ </enumerator>
+ <enumerator>
+ <name>POWER</name>
+ <value>0xC2</value>
+ </enumerator>
+ <enumerator>
+ <name>BOOT_COUNT</name>
+ <value>0xC3</value>
+ </enumerator>
+ <enumerator>
+ <name>PCI_LINK_PRES</name>
+ <value>0xC4</value>
+ </enumerator>
+ <enumerator>
+ <name>PWR_LIMIT_ACTIVE</name>
+ <value>0xC4</value>
+ </enumerator>
+ <enumerator>
+ <name>FAULT</name>
+ <value>0xC7</value>
+ </enumerator>
+</enumerationType>
+
<!-- IPMI Sensor numbers are defined in the IPMI spec as 8 bit values. However
in the hostboot code they will be defined as a uint16_t to allow us to add
additonal information. An example relates to error logs returned by the OCC,
diff --git a/src/usr/targeting/common/xmltohb/target_types_hb.xml b/src/usr/targeting/common/xmltohb/target_types_hb.xml
index 8255b70..bd00b87 100644
--- a/src/usr/targeting/common/xmltohb/target_types_hb.xml
+++ b/src/usr/targeting/common/xmltohb/target_types_hb.xml
@@ -33,6 +33,14 @@
================================================================= -->
<targetTypeExtension>
+ <id>base</id>
+ <attribute>
+ <id>IPMI_INSTANCE</id>
+ <default>0</default>
+ </attribute>
+</targetTypeExtension>
+
+<targetTypeExtension>
<id>sys-sys-power8</id>
<attribute><id>IS_MPIPL_HB</id></attribute>
<attribute><id>IBSCOM_ENABLE_OVERRIDE</id></attribute>
@@ -182,9 +190,7 @@
<attribute>
<id>PSTATE_TABLE</id>
</attribute>
- <attribute>
- <id>IPMI_SENSORS</id>
- </attribute>
+ <attribute><id>IPMI_SENSORS</id></attribute>
</targetTypeExtension>
<targetTypeExtension>
--
1.7.4.1