Ed Tanous | 904063f | 2017-03-02 16:48:24 -0800 | [diff] [blame^] | 1 | generators_list = [ |
| 2 | [0x20, "BMC"], |
| 3 | [0x2C, "ME"], |
| 4 | [0x01, 0x1F, 'BIOS'], |
| 5 | [0x21, 0x3F, 'SMI Handler'], |
| 6 | [0x41, 0x5F, 'System Management Software'], |
| 7 | [0x61, 0x7F, 'OEM'], |
| 8 | [0x81, 0x8D, 'Remote Console Software 1-7'], |
| 9 | [0x8f, 0x8f, 'Terminal Mode Remote Console software'], |
| 10 | ]; |
| 11 | |
| 12 | sensor_type_list = |
| 13 | [ |
| 14 | [0x00, "Reserved"], |
| 15 | [0x01, "Temperature"], |
| 16 | [0x02, "Voltage"], |
| 17 | [0x03, "Current"], |
| 18 | [0x04, "Fan"], |
| 19 | [0x05, "Physical Security (Chassis Intrusion)"], |
| 20 | [0x06, "Platform Security Violation Attempt"], |
| 21 | [0x07, "Processor"], |
| 22 | [0x08, "Power Supply"], |
| 23 | [0x09, "Power Unit"], |
| 24 | [0x0A, "Cooling Device"], |
| 25 | [0x0B, "Other Units-based Sensor"], |
| 26 | [0x0C, "Memory"], |
| 27 | [0x0D, "Bay"], |
| 28 | [0x0E, "POST Memory Resize"], |
| 29 | [0x0F, "POST Error"], |
| 30 | [0x10, "Event Logging Disabled"], |
| 31 | [0x11, "Watchdog 1"], |
| 32 | [0x12, "System Event"], |
| 33 | [0x13, "Critical Interrupt"], |
| 34 | [0x14, "Button / Switch"], |
| 35 | [0x15, "Module / Board"], |
| 36 | [0x16, "Microcontroller / Coprocessor"], |
| 37 | [0x17, "Add-in Card"], |
| 38 | [0x18, "Chassis"], |
| 39 | [0x19, "Chip Set"], |
| 40 | [0x1A, "Other FRU"], |
| 41 | [0x1B, "Cable / Interconnect"], |
| 42 | [0x1C, "Terminator"], |
| 43 | [0x1D, "System Boot / Restart Initiated"], |
| 44 | [0x1E, "Boot Error"], |
| 45 | [0x1F, "Base OS Boot / Installation Status"], |
| 46 | [0x20, "OS Stop / Shutdown"], |
| 47 | [0x21, "Slot / Connector"], |
| 48 | [0x22, "System ACPI Power State"], |
| 49 | [0x23, "Watchdog 2"], |
| 50 | [0x24, "Platform Alert"], |
| 51 | [0x25, "Entity Presence"], |
| 52 | [0x26, "Monitor ASIC / IC"], |
| 53 | [0x27, "LAN"], |
| 54 | [0x28, "Management Subsystem Health"], |
| 55 | [0x29, "Battery"], |
| 56 | [0x2A, "Session Audit"], |
| 57 | [0x2B, "Version Change"], |
| 58 | [0x2C, "FRU State"], |
| 59 | [0xC0, 0xFF, "OEM RESERVED"], |
| 60 | [0x2d, 0xBF, "Reserved"] |
| 61 | ]; |
| 62 | |
| 63 | event_reading_type_list = [ |
| 64 | [0x01, "Threshold"], |
| 65 | [0x02, 0x0C, "Generic"], |
| 66 | [0x6F, "Sensor Specific"], |
| 67 | [0x70, 0x7F, "OEM"], |
| 68 | ]; |
| 69 | |
| 70 | memory_ras_mode = { |
| 71 | 0x00: "No Mode", |
| 72 | 0x01: "Mirroring Mode", |
| 73 | 0x02: "Lockstep Mode", |
| 74 | 0x03: "Invalid RAS Mode", |
| 75 | 0x04: "Rank Sparing Mode" |
| 76 | }; |
| 77 | |
| 78 | caterr_error_type = { |
| 79 | 0x00: "Unknown", |
| 80 | 0x01: "CATERR", |
| 81 | 0x02: "CPU Core Error", |
| 82 | 0x03: "CPU Icc max Mismatch", |
| 83 | 0x04: "CATERR due to CPU 3-strike timeout", |
| 84 | }; |
| 85 | |
| 86 | config_error_values = { |
| 87 | 0x00: " - CFG syntax error", |
| 88 | 0x01: " - Chassis auto-detect error", |
| 89 | 0x02: " - SDR/CFG file mismatch", |
| 90 | 0x03: " - SDR or CFG file corrupted", |
| 91 | 0x04: " - SDR syntax error" |
| 92 | }; |
| 93 | |
| 94 | ras_select_string = " Prior RAS: %s Seleted RAS: %s"; |
| 95 | |
| 96 | |
| 97 | function decode_bios_xeon_dimm_slot_event(generator_id, sensor_type, event_data_offset, event_data){ |
| 98 | var return_string = ""; |
| 99 | |
| 100 | var entity_id = 0x20; // TODO find a way to get this. |
| 101 | // This was previously identified by sensor numbers hardcoded. |
| 102 | // 0x20 = Mem Conf Sensor; 0x2B = Rdnc Mod Sensor |
| 103 | |
| 104 | //if bios generated event and sensor_type is memory |
| 105 | if (generator_id == 0x01){ |
| 106 | if ((entity_id == 0x020) || (entity_id == 0x02B)){ |
| 107 | // if sensor is mem conf sensor or rdnc mod sensor |
| 108 | if ((event_data[0] & 0xA0) == 0xA0){ |
| 109 | var offset = event_data[0] & 0xF |
| 110 | var prior; |
| 111 | var selected; |
| 112 | if (offset <= 1){ |
| 113 | if (entity_id == 0x02B){ |
| 114 | offset = sel_data[1] & 0xF; |
| 115 | if (offset in memory_ras_mode){ |
| 116 | prior = memory_ras_mode[offset]; |
| 117 | } |
| 118 | } |
| 119 | |
| 120 | offset = sel_data[2] & 0xF; |
| 121 | if (offset in memory_ras_mode){ |
| 122 | selected = memory_ras_mode[offset]; |
| 123 | } |
| 124 | if (prior == null){ |
| 125 | return_string += selected; |
| 126 | } else { |
| 127 | return_string += ras_select_string.format(prior, selected); |
| 128 | } |
| 129 | } |
| 130 | } |
| 131 | } |
| 132 | } |
| 133 | }; |
| 134 | |
| 135 | |
| 136 | function cpu_caterr_ext_string(generator_id, sensor_type, event_data_offset, event_data){ |
| 137 | var return_string = ""; |
| 138 | if (event_data[0] == 0xA1) |
| 139 | { |
| 140 | |
| 141 | return_string += "- CATERR type: "; |
| 142 | return_string += caterr_error_type[event_data[2]] || "Reserved"; |
| 143 | |
| 144 | return_string += ", CPU bitmap that causes the system CATERR:"; |
| 145 | for (var cpu_number = 1; cpu_number <=4; cpu_number++){ |
| 146 | if ((1 << cpu_number) & event_data[2] > 0){ |
| 147 | return_string += " CPU" + cpu_number; |
| 148 | } |
| 149 | } |
| 150 | } |
| 151 | return return_string; |
| 152 | }; |
| 153 | |
| 154 | function config_error_ext_string(generator_id, sensor_type, event_data_offset, event_data){ |
| 155 | var return_string = ""; |
| 156 | |
| 157 | if (event_data[0] == 0x21) |
| 158 | { |
| 159 | return_string += config_error_values[event_data[1]] || " Reserved"; |
| 160 | } |
| 161 | return return_string; |
| 162 | }; |
| 163 | |
| 164 | function mtm_level_change_ext_string(generator_id, sensor_type, event_data_offset, event_data){ |
| 165 | var return_string = ""; |
| 166 | |
| 167 | if (event_data[0] == 0x81) |
| 168 | { |
| 169 | if (event_data[1] <= 2 && event_data[1] >= 1){ |
| 170 | return_string += "Level " + event_data[1]; |
| 171 | } else { |
| 172 | return_string += "Reserved"; |
| 173 | } |
| 174 | } |
| 175 | return return_string; |
| 176 | }; |
| 177 | |
| 178 | function vrd_hot_ext_string(generator_id, sensor_type, event_data_offset, event_data){ |
| 179 | var return_string = ""; |
| 180 | |
| 181 | if (event_data_offset == 0x01) |
| 182 | { |
| 183 | if (event_data[1] > 0){ |
| 184 | |
| 185 | return_string += " - Processor VRD HOT map:"; |
| 186 | for (var cpu_number = 1; cpu_number <=4; cpu_number++){ |
| 187 | if ((1 << cpu_number) & event_data[1] > 0){ |
| 188 | return_string += " CPU" + cpu_number; |
| 189 | } |
| 190 | } |
| 191 | } |
| 192 | if (event_data[2] > 0){ |
| 193 | return_string += ", Memory VRD HOT map:"; |
| 194 | for (var cpu_dimm_number = 1; cpu_dimm_number <=4; cpu_dimm_number++){ |
| 195 | if ((1 << cpu_dimm_number) & event_data[2] > 0){ |
| 196 | return_string += " CPU" + (cpu_dimm_number-1) >> 1; |
| 197 | |
| 198 | if ((cpu_dimm_number+1) % 2 == 1){ |
| 199 | return_string += ", DIMM Channel 1/2"; |
| 200 | } else { |
| 201 | return_string += ", DIMM Channel 3/4"; |
| 202 | } |
| 203 | } |
| 204 | } |
| 205 | } |
| 206 | } |
| 207 | return return_string; |
| 208 | }; |
| 209 | |
| 210 | function decode_drive_or_dimm_temperature_sel(generator_id, sensor_type, event_data_offset, event_data){ |
| 211 | var return_string = "" |
| 212 | if (generator_id == 0x20){ // if generated from the BMC |
| 213 | if (((event_data[0] & 0xF0) == 0xA0) && (event_data[1] == 0x01)){ |
| 214 | // drive temperature sel |
| 215 | // Sensor Type 0x01 (Temperature) |
| 216 | // Event Type 0x01 (Threshold) |
| 217 | // OEM Data 0 [7:4] == 0b1010 (2 bytes OEM data, extended format) |
| 218 | // OEM Data 1 (SSD Drive format) |
| 219 | |
| 220 | // Get the standard string, since this is technically a standard |
| 221 | // event. Then, add the OEM data. |
| 222 | |
| 223 | for (var drive_number = 0; drive_number < 8; drive_number++) { |
| 224 | if (( 1 << drive_number) & event_data[1]) { |
| 225 | return_string += " :Drive " + drive_number; |
| 226 | } |
| 227 | } |
| 228 | } else if ((event_data[0] & 0xF0) == 0x30) { |
| 229 | // Dimm aggregate thermal margin |
| 230 | //TODO fix this |
| 231 | for (var cpu_number = 0; cpu_number < 8; cpu_number++) { |
| 232 | if ((1 <<cpu_number) & event_data[2]){ |
| 233 | cpu_number += 1; |
| 234 | break; |
| 235 | } |
| 236 | } |
| 237 | |
| 238 | if (event_data[0]){ |
| 239 | for (var dimm_counter = 0; dimm_counter < 8; dimm_counter++) { |
| 240 | if ((1 << dimm_counter) & event_data[0]){ |
| 241 | dimm_number = dimm_counter % 4; |
| 242 | dimm_channel = dimm_counter >> 2; |
| 243 | break; |
| 244 | } |
| 245 | } |
| 246 | } |
| 247 | } |
| 248 | } |
| 249 | } |
| 250 | |
| 251 | /* This dict defines the states for the SEL reader. The first level of keys |
| 252 | is used to map the event type to a section. The rest of the sections are used |
| 253 | to map the individual event data to an entry. |
| 254 | if the key "sensor_type" is present, it will use that entry to map a specific sensor |
| 255 | type to a string and a severity. the lowest level of dictionaries maps the offset |
| 256 | to a user facing string. |
| 257 | |
| 258 | a custom_handler can be added to the dict and invoked at the lowest level to |
| 259 | manage non-standard sel to string implementationations or ones that require code |
| 260 | to determine. |
| 261 | */ |
| 262 | event_reading_type_states = { |
| 263 | 0x00: "Unspecified", |
| 264 | 0x01: { // Threshold |
| 265 | 0x00: ["Lower Non-critical - going low", "Degraded"], |
| 266 | 0x01: ["Lower Non-critical - going high", "Degraded"], |
| 267 | 0x02: ["Lower Critical - going low", "Non-Fatal"], |
| 268 | 0x03: ["Lower Critical - going high", "Non-Fatal"], |
| 269 | 0x04: ["Lower Non-recoverable - going low", "Fatal"], |
| 270 | 0x05: ["Lower Non-recoverable - going high", "Fatal"], |
| 271 | 0x06: ["Upper Non-critical - going low", "Degraded"], |
| 272 | 0x07: ["Upper Non-critical - going high", "Degraded"], |
| 273 | 0x08: ["Upper Critical - going low", "Non-Fatal"], |
| 274 | 0x09: ["Upper Critical - going high", "Non-Fatal"], |
| 275 | 0x0A: ["Upper Non-recoverable - going low", "Fatal"], |
| 276 | 0x0B: ["Upper Non-recoverable - going high", "Fatal"], |
| 277 | "sensor_type": { |
| 278 | 0x01: decode_drive_or_dimm_temperature_sel // hard drive |
| 279 | } |
| 280 | }, |
| 281 | 0x02: { //Discrete |
| 282 | 0x00: "Transition to Idle", |
| 283 | 0x01: "Transition to Active", |
| 284 | 0x02: "Transition to Busy" |
| 285 | }, |
| 286 | 0x03: { |
| 287 | 0x00: "State Deasserted", |
| 288 | 0x01: "State Asserted", |
| 289 | "sensor_type": { |
| 290 | 0x07: cpu_caterr_ext_string, |
| 291 | 0x28: [mtm_level_change_ext_string, config_error_ext_string], |
| 292 | |
| 293 | } |
| 294 | }, |
| 295 | 0x04: { |
| 296 | 0x00: "Predictive Failure deasserted", |
| 297 | 0x01: ["Predictive Failure asserted", "Degraded"] |
| 298 | }, |
| 299 | 0x05: { |
| 300 | 0x00: "Limit Not Exceeded", |
| 301 | 0x01: ["Limit Exceeded", "Degraded"], |
| 302 | "sensor_type": { |
| 303 | 0x01: vrd_hot_ext_string |
| 304 | } |
| 305 | }, |
| 306 | 0x06: { |
| 307 | 0x00: "Performance Met", |
| 308 | 0x01: ["Performance Lags", "Degraded"] |
| 309 | }, |
| 310 | 0x07: { |
| 311 | 0x00: "Transition to OK", |
| 312 | 0x01: ["Transition to Non-Critical from OK", "Degraded"], |
| 313 | 0x02: ["Transition to Critical from less severe", "Non-Fatal"], |
| 314 | 0x03: ["Transition to Non-recoverable from less severe", "Fatal"], |
| 315 | 0x04: ["Transition to Non-Critical from more severe", "Degraded"], |
| 316 | 0x05: ["Transition to Critical from Non-recoverable", "Non-Fatal"], |
| 317 | 0x06: ["Transition to Non-recoverable", "Fatal"], |
| 318 | 0x07: ["Monitor", "Degraded"], |
| 319 | 0x08: "Informational" |
| 320 | }, |
| 321 | 0x08: { |
| 322 | 0x00: "Device Removed / Device Absent", |
| 323 | 0x01: "Device Inserted / Device Present" |
| 324 | }, |
| 325 | 0x09: { |
| 326 | 0x00: "Device Disabled", |
| 327 | 0x01: "Device Enabled", |
| 328 | "sensor_type": { |
| 329 | 0x0C: decode_bios_xeon_dimm_slot_event |
| 330 | } |
| 331 | }, |
| 332 | 0x0A: { |
| 333 | 0x00: "Transition to Running", |
| 334 | 0x01: "Transition to In Test", |
| 335 | 0x02: "Transition to Power Off", |
| 336 | 0x03: "Transition to On Line", |
| 337 | 0x04: "Transition to Off Line", |
| 338 | 0x05: "Transition to Off Duty", |
| 339 | 0x06: "Transition to Degraded", |
| 340 | 0x07: "Transition to Power Save", |
| 341 | 0x08: ["Install Error", "Degraded"] |
| 342 | }, |
| 343 | 0x0B: { |
| 344 | 0x00: "Redundancy Regained", |
| 345 | 0x01: ["Redundancy Lost", "Degraded"], |
| 346 | 0x02: ["Redundancy Degraded", "Degraded"], |
| 347 | 0x03: "Non-redundant:Sufficient Resources from Redundant", |
| 348 | 0x04: "Non-redundant:Sufficient Resources from Insufficient Resources", |
| 349 | 0x05: ["Non-redundant:Insufficient Resources", "Degraded"], |
| 350 | 0x06: ["Redundancy Degraded from Fully Redundant", "Degraded"], |
| 351 | 0x07: ["Redundancy Degraded from Non-redundant", "Degraded"] |
| 352 | }, |
| 353 | 0x0C: { |
| 354 | 0x00: "D0 Power State", |
| 355 | 0x01: "D1 Power State", |
| 356 | 0x02: "D2 Power State", |
| 357 | 0x03: "D3 Power State" |
| 358 | }, |
| 359 | 0x6F: { // OEM |
| 360 | "sensor_type": { |
| 361 | 0x00: "", // reserved |
| 362 | 0x01: "", // Temperature |
| 363 | 0x02: "", // Voltage |
| 364 | 0x03: "", // Current |
| 365 | 0x04: "N/A", //Fan |
| 366 | 0x05: { // General Chassis Intrusion |
| 367 | 0x00: ["General Chassis Intrusion", "Degraded"], |
| 368 | 0x01: ["Drive Bay intrusion", "Degraded"], |
| 369 | 0x02: ["I/O Card area intrusion", "Degraded"], |
| 370 | 0x03: ["Processor area intrusion", "Degraded"], |
| 371 | 0x04: ["LAN Leash Lost", "Degraded"], |
| 372 | 0x05: ["Unauthorized dock", "Degraded"], |
| 373 | 0x06: ["FAN area intrusion", "Degraded"], |
| 374 | }, |
| 375 | 0x06: { // Physical Security - Violation Attempt |
| 376 | 0x00: ["Secure Mode Violation attempt", "Degraded"], |
| 377 | 0x01: ["Pre-boot Password Violation - user password", "Degraded"], |
| 378 | 0x02: ["Pre-boot Password Violation attempt - setup password", "Degraded"], |
| 379 | 0x03: ["Pre-boot Password Violation - network boot password", "Degraded"], |
| 380 | 0x04: ["Other pre-boot Password Violation", "Degraded"], |
| 381 | 0x05: ["Out-of-band Access Password Violation", "Degraded"] |
| 382 | }, |
| 383 | 0x07: { // Processor |
| 384 | 0x00: ["IERR", "Degraded"], |
| 385 | 0x01: ["Thermal Trip", "Degraded"], |
| 386 | 0x02: ["FRB1/BIST failure", "Degraded"], |
| 387 | 0x03: ["FRB2/Hang in POST failure", "Degraded"], |
| 388 | 0x04: ["FRB3/Processor Startup/Initialization failure", "Degraded"], |
| 389 | 0x05: ["Configuration Error", "Degraded"], |
| 390 | 0x06: ["SM BIOS Uncorrectable CPU-complex Error", "Degraded"], |
| 391 | 0x07: ["Processor Presence detected", "Degraded"], |
| 392 | 0x08: ["Processor disabled", "Degraded"], |
| 393 | 0x09: ["Terminator Presence Detected", "Degraded"], |
| 394 | 0x0A: ["Processor Automatically Throttled", "Degraded"], |
| 395 | 0x0B: ["Machine Check Exception (Uncorrectable)", "Fatal"], |
| 396 | 0x0C: ["Correctable Machine Check Error", "Non-Fatal"] |
| 397 | }, |
| 398 | 0x08: { // Power Supply |
| 399 | 0x00: "Presence detected", |
| 400 | 0x01: ["Power Supply Failure detected", "Degraded"], |
| 401 | 0x02: ["Predictive Failure", "Degraded"], |
| 402 | 0x03: ["Power Supply input lost (AC/DC)", "Degraded"], |
| 403 | 0x04: ["Power Supply input lost or out-of-range", "Degraded"], |
| 404 | 0x05: ["Power Supply input out-of-range, but present", "Degraded"], |
| 405 | 0x06: ["Configuration error", "Degraded"], |
| 406 | 0x07: ["Power Supply Inactive (in standby state)", "Degraded"] |
| 407 | }, |
| 408 | 0x09: { // Power unit |
| 409 | 0x00: "Power Off / Power Down", |
| 410 | 0x01: "Power Cycle", |
| 411 | 0x02: "240VA Power Down", |
| 412 | 0x03: "Interlock Power Down", |
| 413 | 0x04: ["AC lost / Power input lost", "Degraded"], |
| 414 | 0x05: ["Soft Power Control Failure", "Degraded"], |
| 415 | 0x06: ["Power Unit Failure detected", "Degraded"], |
| 416 | 0x07: ["Predictive Failure", "Degraded"] |
| 417 | }, |
| 418 | 0x0C: { // Memory |
| 419 | 0x00: ["Correctable ECC / other correctable memory error", "Degraded"], |
| 420 | 0x01: ["Uncorrectable ECC", "Fatal"], |
| 421 | 0x02: "Parity", |
| 422 | 0x03: ["Memory Scrub Failed", "Fatal"], |
| 423 | 0x04: "Memory Device Disabled", |
| 424 | 0x05: ["Correctable ECC / other correctable memory error logging limit reached", "Degraded"], |
| 425 | 0x06: "Presence detected", |
| 426 | 0x07: ["Configuration error", "Fatal"], |
| 427 | 0x08: "Spare", |
| 428 | 0x09: "Memory Automatically Throttled", |
| 429 | 0x0A: ["Critical Overtemperature", "Fatal"] |
| 430 | }, |
| 431 | 0x0D: { // Drive Slot |
| 432 | 0x00: "Drive Presence", |
| 433 | 0x01: ["Drive Fault", "Fatal"], |
| 434 | 0x02: ["Predictive Failure", "Fatal"], |
| 435 | 0x03: "Hot Spare", |
| 436 | 0x04: "Consistency Check / Parity Check in progress", |
| 437 | 0x05: ["In Critical Array", "Degraded"], |
| 438 | 0x06: ["In Failed Array", "Degraded"], |
| 439 | 0x07: ["Rebuild/Remap in progress", "Degraded"], |
| 440 | 0x08: ["Rebuild/Remap Aborted", "Degraded"] |
| 441 | }, |
| 442 | 0x0F: { // POST Error |
| 443 | 0x00: "POST Error", |
| 444 | 0x01: "System Firmware Hang", |
| 445 | 0x02: "System Firmware Progress" |
| 446 | }, |
| 447 | 0x10: { // Event Logging Disabled |
| 448 | 0x00: "Correctable Memory Error Logging Disabled", |
| 449 | 0x01: "Event Type Logging Disabled", |
| 450 | 0x02: "All Event Logging Disabled", |
| 451 | 0x03: "All Event Logging Disabled", |
| 452 | 0x04: ["SEL Full", "Degraded"], |
| 453 | 0x05: ["SEL Almost Full", "Degraded"], |
| 454 | 0x06: "Correctable Machine Check Error Logging Disabled" |
| 455 | }, |
| 456 | 0x11: { // Watchdog 1 |
| 457 | 0x0: ["BIOS Watchdog Reset", "Fatal"], |
| 458 | 0x1: ["OS Watchdog Reset", "Fatal"], |
| 459 | 0x2: ["OS Watchdog Shut Down", "Fatal"], |
| 460 | 0x3: ["OS Watchdog Power Down", "Fatal"], |
| 461 | 0x4: ["OS Watchdog Power Cycle", "Fatal"], |
| 462 | 0x5: ["OS Watchdog NMI / Diagnostic Interrupt", "Fatal"], |
| 463 | 0x6: ["OS Watchdog Expired, status only", "Fatal"], |
| 464 | 0x7: ["OS Watchdog pre-timeout Interrupt, non-NMI", "Fatal"] |
| 465 | }, |
| 466 | 0x12: { // System Event |
| 467 | 0x0: "System Reconfigured", |
| 468 | 0x1: "OEM System Boot Event", |
| 469 | 0x2: ["Undetermined system hardware failure", "Fatal"], |
| 470 | 0x3: ["Entry added to Auxiliary Log", "Degraded"], |
| 471 | 0x4: ["PEF Action", "Degraded"], |
| 472 | 0x5: "Timestamp Clock Synch" |
| 473 | }, |
| 474 | 0x13: { // Critical Interrupt |
| 475 | 0x0: ["Front Panel NMI / Diagnostic Interrupt", "Fatal"], |
| 476 | 0x1: ["Bus Timeout", "Fatal"], |
| 477 | 0x2: ["I/O channel check NMI", "Fatal"], |
| 478 | 0x3: ["Software NMI", "Fatal"], |
| 479 | 0x4: ["PCI PERR", "Fatal"], |
| 480 | 0x5: ["PCI SERRt", "Fatal"], |
| 481 | 0x6: ["EISA Fail Safe Timeout", "Fatal"], |
| 482 | 0x7: ["Bus Correctable Error", "Fatal"], |
| 483 | 0x8: ["Bus Uncorrectable Error", "Fatal"], |
| 484 | 0x9: ["Fatal NMI (port 61h, bit 7)", "Fatal"], |
| 485 | 0xA: ["Bus Fatal Error", "Fatal"], |
| 486 | 0xB: ["Bus Degraded", "Fatal"] |
| 487 | }, |
| 488 | 0x14: { // Button / Switch |
| 489 | 0x0: "Power Button pressed", |
| 490 | 0x1: "Sleep Button pressed", |
| 491 | 0x2: "Reset Button pressed", |
| 492 | 0x3: "FRU latch open", |
| 493 | 0x4: "FRU service request button" |
| 494 | }, |
| 495 | 0x19: { // Chip Set |
| 496 | 0x0: ["Soft Power Control Failure", "Fatal"], |
| 497 | 0x1: ["Thermal Trip", "Fatal"] |
| 498 | }, |
| 499 | 0x1B: { // Cable / Interconnect |
| 500 | 0x0: "Cable/Interconnect is connected", |
| 501 | 0x1: ["Configuration Error - Incorrect cable connected / Incorrect interconnection", "Fatal"], |
| 502 | }, |
| 503 | 0x1D: { // System Boot / Restart Initiated |
| 504 | 0x0: ["Initiated by power up", "Fatal"], |
| 505 | 0x1: ["Initiated by hard reset", "Fatal"], |
| 506 | 0x2: ["Initiated by warm reset", "Fatal"], |
| 507 | 0x3: ["User requested PXE boot", "Fatal"], |
| 508 | 0x4: "Automatic boot to diagnostic", |
| 509 | 0x5: ["OS / run-time software initiated hard reset", "Fatal"], |
| 510 | 0x6: ["OS / run-time software initiated warm reset", "Fatal"], |
| 511 | 0x7: ["System Restart", "Fatal"], |
| 512 | }, |
| 513 | 0x1E: { // Boot Error |
| 514 | 0x0: ["No bootable media", "Degraded"], |
| 515 | 0x1: ["Non-bootable diskette left in drive", "Degraded"], |
| 516 | 0x2: ["PXE Server not found", "Fatal"], |
| 517 | 0x3: ["Invalid boot sector", "Fatal"], |
| 518 | 0x4: ["Timeout waiting for user selection of boot source", "Fatal"], |
| 519 | }, |
| 520 | 0x1F: { // Base OS Boot / Installation Status |
| 521 | 0x0: "A: boot completed", |
| 522 | 0x1: "C: boot completed", |
| 523 | 0x2: "PXE boot completed", |
| 524 | 0x3: "Diagnostic boot completed", |
| 525 | 0x4: "CD-ROM boot completed", |
| 526 | 0x5: "ROM boot completed", |
| 527 | 0x6: "boot completed - boot device not specified", |
| 528 | 0x7: "Base OS/Hypervisor Installation started", |
| 529 | 0x8: "Base OS/Hypervisor Installation completed", |
| 530 | 0x9: ["Base OS/Hypervisor Installation aborted", "Fatal"], |
| 531 | 0xA: ["Base OS/Hypervisor Installation failed", "Fatal"] |
| 532 | }, |
| 533 | 0x20: { // OS Stop / Shutdown |
| 534 | 0x0: ["Critical stop during OS load / initialization", "Fatal"], |
| 535 | 0x1: ["Run-time Critical Stop", "Fatal"], |
| 536 | 0x2: "OS Graceful Stop", |
| 537 | 0x3: "OS Graceful Shutdown", |
| 538 | 0x4: "Soft Shutdown initiated by PEF", |
| 539 | 0x5: ["Agent Not Responding", "Fatal"] |
| 540 | }, |
| 541 | 0x21: { // Slot / Connector |
| 542 | 0x0: ["Fault Status asserted", "Fatal"], |
| 543 | 0x1: "Identify Status asserted", |
| 544 | 0x2: "Slot / Connector Device installed/attached", |
| 545 | 0x3: "Slot / Connector Ready for Device Installation", |
| 546 | 0x4: "Slot/Connector Ready for Device Removal", |
| 547 | 0x5: "Slot Power is Off", |
| 548 | 0x6: "Slot / Connector Device Removal Request", |
| 549 | 0x7: ["Interlock asserted", "Degraded"], |
| 550 | 0x8: "Slot is Disabled", |
| 551 | 0x9: ["Slot holds spare device", "Fatal"] |
| 552 | }, |
| 553 | 0x22: { // System ACPI Power State |
| 554 | 0x0: "S0 / G0 \"working\"", |
| 555 | 0x1: "S1 \"sleeping with system h/w & processor context maintained\"", |
| 556 | 0x2: "S2 \"sleeping, processor context lost\"", |
| 557 | 0x3: "S3 \"sleeping, processor & h/w context lost, memory retained.\"", |
| 558 | 0x4: "S4 \"non-volatile sleep / suspend-to disk\"", |
| 559 | 0x5: "S5 / G2 \"soft-off\"", |
| 560 | 0x6: "S4 / S5 soft-off, particular S4 / S5 state cannot be determined", |
| 561 | 0x7: "G3 / Mechanical Off", |
| 562 | 0x8: "Sleeping in an S1, S2, or S3 states", |
| 563 | 0x9: "G1 sleeping", |
| 564 | 0xA: "S5 entered by override", |
| 565 | 0xB: "Legacy ON state", |
| 566 | 0xC: "Legacy OFF state", |
| 567 | 0xE: ["Unknown", "Fatal"] |
| 568 | }, |
| 569 | 0x23: { // Watchdog 2 |
| 570 | 0x0: ["Timer expired, status only", "Non-Fatal"], |
| 571 | 0x1: ["Hard Reset", "Fatal"], |
| 572 | 0x2: ["Power Down", "Fatal"], |
| 573 | 0x3: ["Power Cycle", "Fatal"], |
| 574 | 0x8: ["Timer interrupt", "Fatal"] |
| 575 | }, |
| 576 | 0x24: { // Platform Alert |
| 577 | 0x0: ["platform generated page", "Non-Fatal"], |
| 578 | 0x1: ["platform generated LAN alert", "Non-Fatal"], |
| 579 | 0x2: ["platform Event Trap generated", "Non-Fatal"], |
| 580 | 0x3: ["platform generated SNMP trap", "Non-Fatal"] |
| 581 | }, |
| 582 | 0x25: { // Entity Presence |
| 583 | 0x0: "Entity Present", |
| 584 | 0x1: "Entity Absent", |
| 585 | 0x2: "Entity Disabled" |
| 586 | }, |
| 587 | 0x27: { // LAN |
| 588 | 0x0: ["LAN Heartbeat Lost", "Fatal"], |
| 589 | 0x1: "LAN Heartbeat" |
| 590 | }, |
| 591 | 0x28: { // Management Subsystem Health |
| 592 | 0x0: ["sensor access degraded or unavailable", "Fatal"], |
| 593 | 0x1: ["controller access degraded or unavailable", "Fatal"], |
| 594 | 0x2: ["management controller off-line", "Fatal"], |
| 595 | 0x3: ["management controller unavailable", "Fatal"], |
| 596 | 0x4: ["Sensor failure", "Fatal"], |
| 597 | 0x5: ["FRU failure", "Fatal"] |
| 598 | }, |
| 599 | 0x29: { // Battery |
| 600 | 0x0: ["battery low (predictive failure)", "Fatal"], |
| 601 | 0x1: ["battery failed", "Fatal"], |
| 602 | 0x2: "battery presence detected" |
| 603 | }, |
| 604 | 0x2A: { // Session Audit |
| 605 | 0x0: "Session Activated", |
| 606 | 0x1: "Session Deactivated", |
| 607 | 0x2: ["Invalid Username or Password", "Non-Fatal"], |
| 608 | 0x3: ["Invalid password disable", "Non-Fatal"], |
| 609 | }, |
| 610 | 0x2B: { // Version Change |
| 611 | 0x0: "Hardware change detected with associated Entity", |
| 612 | 0x1: "Firmware or software change detected with associated Entity", |
| 613 | 0x6: "Hardware Change detected with associated Entity was successful", |
| 614 | 0x7: "Software or F/W Change detected with associated Entity was successful", |
| 615 | 0x2: ["Hardware incompatibility detected with associated Entity", "Fatal"], |
| 616 | 0x3: ["Firmware or software incompatibility detected with associated Entity", "Fatal"], |
| 617 | 0x4: ["Entity is of an invalid or unsupported hardware version", "Fatal"], |
| 618 | 0x5: ["Entity contains an invalid or unsupported firmware or software version", "Fatal"] |
| 619 | }, |
| 620 | 0x2C: { // FRU State |
| 621 | 0x0: ["FRU Not Installed", "Fatal"], |
| 622 | 0x1: "FRU Inactive (in standby or \"hot spare\" state)", |
| 623 | 0x2: "FRU Activation Requested", |
| 624 | 0x3: "FRU Activation In Progress", |
| 625 | 0x4: "FRU Active", |
| 626 | 0x5: "FRU Deactivation Requested", |
| 627 | 0x6: "FRU Deactivation In Progress", |
| 628 | 0x7: ["FRU Communication Lost", "Fatal"] |
| 629 | } |
| 630 | } |
| 631 | } |
| 632 | }; |
| 633 | |
| 634 | |
| 635 | function getSelDescription(sel_data){ |
| 636 | var sel_description_string = ""; |
| 637 | var severity = "Healthy"; |
| 638 | try{ |
| 639 | var event_data = [sel_data[13], sel_data[14], sel_data[15]]; |
| 640 | var sensor_type = sel_data[10]; |
| 641 | |
| 642 | var this_entry; |
| 643 | |
| 644 | var generator_id = sel_data[7]; |
| 645 | var event_reading_type = sel_data[12] & 0x7f; |
| 646 | var event_asserted = (sel_data[12] >> 7) == 0; |
| 647 | var event_reading_type_string = getStringFromIdList(event_reading_type_list, event_reading_type); |
| 648 | |
| 649 | if (event_reading_type in event_reading_type_states){ |
| 650 | this_entry = event_reading_type_states[event_reading_type]; |
| 651 | |
| 652 | if ("sensor_type" in this_entry){ |
| 653 | if (sensor_type in this_entry["sensor_type"]){ |
| 654 | this_entry = this_entry["sensor_type"][sensor_type] |
| 655 | } |
| 656 | } |
| 657 | |
| 658 | if (typeof this_entry == "string"){ |
| 659 | sel_description_string += this_entry; |
| 660 | } else if (typeof this_entry == "object") { |
| 661 | var event_data_offset = event_data[0] & 0xf; |
| 662 | |
| 663 | if (event_data_offset in this_entry){ |
| 664 | var sensor_entity = this_entry[event_data_offset]; |
| 665 | if (typeof sensor_entity == "object"){ |
| 666 | // only apply the severity string if event was asserted |
| 667 | // all deassertion events are considered "healthy" |
| 668 | if (event_asserted) { |
| 669 | severity = sensor_entity[1]; |
| 670 | } |
| 671 | sel_description_string += sensor_entity[0]; |
| 672 | } else if (typeof sensor_entity == "string"){ |
| 673 | sel_description_string += sensor_entity; |
| 674 | } else if (typeof sensor_entity == "function"){ |
| 675 | sel_description_string += this_handler(generator_id, sensor_type, event_data_offset, event_data) |
| 676 | } |
| 677 | } |
| 678 | } |
| 679 | } |
| 680 | |
| 681 | if (event_asserted){ |
| 682 | sel_description_string += " - Asserted"; |
| 683 | } else { |
| 684 | sel_description_string += " - Deasserted"; |
| 685 | } |
| 686 | } catch(err) { |
| 687 | console.log("SEL decode died with error " + err) |
| 688 | } |
| 689 | return [sel_description_string, severity]; |
| 690 | } |
| 691 | |
| 692 | function parseHexString(str) { |
| 693 | var result = []; |
| 694 | while (str.length >= 2) { |
| 695 | result.push(parseInt(str.substring(0, 2), 16)); |
| 696 | str = str.substring(2, str.length); |
| 697 | } |
| 698 | return result; |
| 699 | }; |
| 700 | |
| 701 | function getStringFromIdList(generator_id, generators_list){ |
| 702 | var generator_string = null; |
| 703 | for (var generator_index = 0; generator_index < generators_list.length; generator_index++){ |
| 704 | this_generator_entry = generators_list[generator_index]; |
| 705 | var generator_id = generator_id & 0xFF; |
| 706 | // range based match |
| 707 | if (this_generator_entry.length === 3){ |
| 708 | if (generator_id >= this_generator_entry[0] && |
| 709 | generator_id <= this_generator_entry[1]){ |
| 710 | generator_string = this_generator_entry[2]; |
| 711 | break; |
| 712 | } |
| 713 | } else { |
| 714 | // exact match |
| 715 | if (generator_id == this_generator_entry[0]){ |
| 716 | generator_string = this_generator_entry[1]; |
| 717 | break |
| 718 | } |
| 719 | } |
| 720 | } |
| 721 | |
| 722 | if (generator_string == null){ |
| 723 | generator_string = "(0X" |
| 724 | generator_string += ("00" + this_entry.generator_id.toString(16)).substr(-2).toUpperCase(); |
| 725 | generator_string += ")" |
| 726 | } |
| 727 | return generator_string; |
| 728 | }; |
| 729 | |
| 730 | function get_sensor_names_from_sdr(sdr_list){ |
| 731 | var sdr_names = {}; |
| 732 | |
| 733 | for (var sdr_index = 0; sdr_index < sdr_list.length; sdr_index++) { |
| 734 | var this_sdr = parseHexString(sdr_list[sdr_index].raw_data); |
| 735 | |
| 736 | var sdr_type = this_sdr[3]; |
| 737 | var owner = this_sdr[5]; |
| 738 | var string_offset = null; |
| 739 | if (sdr_type == 0x01){ |
| 740 | string_offset = 47; |
| 741 | } else if (sdr_type == 0x02){ |
| 742 | string_offset = 31; |
| 743 | } else if (sdr_type == 0x02){ |
| 744 | string_offset = 16; |
| 745 | } |
| 746 | if (string_offset !== null){ |
| 747 | var type_length_code = this_sdr[string_offset]; |
| 748 | var type_code = type_length_code >> 6; |
| 749 | var length = type_length_code & 0x3F; |
| 750 | var string_name = ""; |
| 751 | var sensor_number = 0; |
| 752 | if (type_code == 0x03){ |
| 753 | sensor_number = this_sdr[7]; |
| 754 | for (var string_index = 0; string_index < length; string_index++){ |
| 755 | var this_character = this_sdr[string_offset + 1 + string_index]; |
| 756 | var character = String.fromCharCode(this_character); |
| 757 | string_name += character; |
| 758 | } |
| 759 | } |
| 760 | sdr_names[(owner << 8) + sensor_number] = string_name; |
| 761 | } |
| 762 | |
| 763 | } |
| 764 | return sdr_names; |
| 765 | } |
| 766 | |
| 767 | |
| 768 | angular.module('bmcApp').controller('selController', function($scope, Restangular) { |
| 769 | |
| 770 | var sdr_promise = Restangular.all('sdrentries').getList(); |
| 771 | var sel_promise = Restangular.all('selentries').getList(); |
| 772 | |
| 773 | //wait for all the requests to finish |
| 774 | Promise.all([sdr_promise, sel_promise]) |
| 775 | .then(function(values) { |
| 776 | |
| 777 | |
| 778 | sdr_entries_incoming = values[0]; |
| 779 | sel_entries_incoming = values[1]; |
| 780 | |
| 781 | var sensor_names = get_sensor_names_from_sdr(sdr_entries_incoming); |
| 782 | |
| 783 | $scope.sel_entries.length = 0; |
| 784 | // TODO don't generate so many extra entries |
| 785 | for (var i = 0; i < 20; i++){ |
| 786 | for (var entry_index = 0; entry_index < sel_entries_incoming.length; entry_index++) { |
| 787 | this_entry = new Object(); |
| 788 | raw_sel = parseHexString(sel_entries_incoming[entry_index]["raw_data"]) |
| 789 | |
| 790 | this_entry.id = (raw_sel[1] << 8) + raw_sel[0]; |
| 791 | this_entry.generator_id = raw_sel[7]; |
| 792 | this_entry.channel_number = raw_sel[8] >> 4; |
| 793 | this_entry.sensor_number = raw_sel[11]; |
| 794 | this_entry.lun = raw_sel[8] & 0x03; |
| 795 | this_entry.timestamp = (raw_sel[6] << 24) + (raw_sel[5] << 16) + (raw_sel[4] << 8) + raw_sel[3]; |
| 796 | this_entry.sensor_type_id = raw_sel[10]; |
| 797 | |
| 798 | this_entry.generator_name = getStringFromIdList(this_entry.generator_id, generators_list); |
| 799 | this_entry.sensor_type_string = getStringFromIdList(this_entry.sensor_type_id, sensor_type_list); |
| 800 | sel_description = getSelDescription(raw_sel); |
| 801 | this_entry.description_string = sel_description[0]; |
| 802 | this_entry.event_severity = sel_description[1]; |
| 803 | |
| 804 | var sensor_uid = (this_entry.generator_id << 8) + this_entry.sensor_number; |
| 805 | if (sensor_uid in sensor_names){ |
| 806 | this_entry.sensor_name = sensor_names[sensor_uid]; |
| 807 | } else { |
| 808 | this_entry.sensor_name = "Unknown"; |
| 809 | } |
| 810 | |
| 811 | $scope.sel_entries.push(this_entry); |
| 812 | } |
| 813 | } |
| 814 | |
| 815 | var unique_controllers = {}; |
| 816 | for( var sel_index in $scope.sel_entries ){ |
| 817 | unique_controllers[$scope.sel_entries[sel_index].generator_name] = 0; |
| 818 | } |
| 819 | var unique_controller_names = []; |
| 820 | for(var key in unique_controllers){ |
| 821 | unique_controller_names.push(key); |
| 822 | } |
| 823 | |
| 824 | $scope.unique_columns["controller"] = unique_controller_names; |
| 825 | }); |
| 826 | |
| 827 | |
| 828 | $scope.filtered_sel = []; |
| 829 | $scope.filtered_and_sliced_sel = []; |
| 830 | $scope.sel_entries = []; |
| 831 | $scope.current_page = 1; |
| 832 | $scope.items_per_page = 10; |
| 833 | $scope.max_size = 5; |
| 834 | $scope.unique_columns = {"controller": []}; |
| 835 | $scope.selectedColumns = {"controller": []}; |
| 836 | |
| 837 | onPageChange = function() { |
| 838 | var begin = (($scope.current_page - 1) * $scope.items_per_page) |
| 839 | , end = begin + $scope.items_per_page; |
| 840 | $scope.filtered_and_sliced_sel = $scope.filtered_sel.slice(begin, end) |
| 841 | }; |
| 842 | |
| 843 | onFilterChange = function() { |
| 844 | var filtered_sel = []; |
| 845 | var sel_entries = $scope.sel_entries; |
| 846 | if ($scope.selectedColumns["controller"].length == 0){ |
| 847 | filtered_sel = $scope.sel_entries; |
| 848 | } else { |
| 849 | for(var sel_entry_index = 0; sel_entry_index < sel_entries.length; sel_entry_index++){ |
| 850 | entry = sel_entries[sel_entry_index]; |
| 851 | for (var controller_index = 0; controller_index < $scope.selectedColumns["controller"].length; controller_index++){ |
| 852 | controller = $scope.selectedColumns["controller"][controller_index]; |
| 853 | if (angular.equals(entry.generator_name, controller)) { |
| 854 | filtered_sel.push(entry); |
| 855 | break; |
| 856 | } |
| 857 | } |
| 858 | } |
| 859 | } |
| 860 | |
| 861 | $scope.filtered_sel = filtered_sel; |
| 862 | onPageChange(); |
| 863 | }; |
| 864 | |
| 865 | $scope.$watch('current_page + items_per_page ', onPageChange); |
| 866 | $scope.$watch('selectedColumns', onFilterChange, true /*deep*/); |
| 867 | $scope.$watchCollection('sel_entries', onFilterChange); |
| 868 | |
| 869 | $scope.setSelectedController = function () { |
| 870 | var id = this.company; |
| 871 | if (_.contains($scope.selectedColumns["controller"], id)) { |
| 872 | $scope.selectedColumns["controller"] = _.without($scope.selectedColumns["controller"], id); |
| 873 | } else { |
| 874 | $scope.selectedColumns["controller"].push(id); |
| 875 | } |
| 876 | return false; |
| 877 | }; |
| 878 | |
| 879 | $scope.isChecked = function (id) { |
| 880 | if (_.contains($scope.selectedColumns["controller"], id)) { |
| 881 | return 'fa fa-check pull-right'; |
| 882 | } |
| 883 | return false; |
| 884 | }; |
| 885 | |
| 886 | $scope.checkAll = function () { |
| 887 | $scope.selectedColumns["controller"] = $scope.unique_columns["controller"]; |
| 888 | }; |
| 889 | |
| 890 | $scope.uncheckAll = function () { |
| 891 | $scope.selectedColumns["controller"] = []; |
| 892 | }; |
| 893 | }); |