blob: 175ce567f98ad425acc719c8f0c271470cd41567 [file] [log] [blame]
Jayanth Othayothb1eda6a2021-06-28 00:26:30 -05001extern "C"
2{
Ben Tyner792f32f2020-06-02 08:50:47 -05003#include <libpdbg.h>
Jayanth Othayothb1eda6a2021-06-28 00:26:30 -05004#include <libpdbg_sbe.h>
5}
Ben Tyner792f32f2020-06-02 08:50:47 -05006
Zane Shelleya06dcf82021-11-03 10:23:21 -05007#include <config.h>
8
Ben Tynerb9715172021-09-29 08:46:19 -05009#ifdef CONFIG_PHAL_API
10#include <libphal.H>
11#endif
12
Ben Tyner0205f3b2020-02-24 10:24:47 -060013#include <analyzer/analyzer_main.hpp>
Ben Tynerb797b3e2020-06-29 10:12:05 -050014#include <attn/attention.hpp>
Ben Tynerbcf65a82020-12-01 08:46:36 -060015#include <attn/attn_common.hpp>
Ben Tynerb797b3e2020-06-29 10:12:05 -050016#include <attn/attn_config.hpp>
Ben Tyner4bbcb382021-02-22 09:29:00 -060017#include <attn/attn_dbus.hpp>
Ben Tynerb797b3e2020-06-29 10:12:05 -050018#include <attn/attn_handler.hpp>
19#include <attn/attn_logging.hpp>
20#include <attn/bp_handler.hpp>
21#include <attn/ti_handler.hpp>
Ben Tynerbcf65a82020-12-01 08:46:36 -060022#include <attn/vital_handler.hpp>
Ben Tynerfe2c50d2021-07-23 13:38:53 -050023#include <util/dbus.hpp>
Ben Tyner76e52f62022-02-01 10:46:44 -060024#include <util/ffdc_file.hpp>
25#include <util/trace.hpp>
Ben Tyneref320152020-01-09 10:31:23 -060026
Ben Tynerb481d902020-03-05 10:24:23 -060027#include <algorithm>
Ben Tyneref320152020-01-09 10:31:23 -060028#include <iomanip>
Ben Tynerb1ebfcb2020-05-08 18:52:48 -050029#include <map>
Ben Tyner9ae5ca42020-02-28 13:13:50 -060030#include <sstream>
Ben Tynerb481d902020-03-05 10:24:23 -060031#include <vector>
Ben Tyneref320152020-01-09 10:31:23 -060032
33namespace attn
34{
35
36/**
Ben Tyneref320152020-01-09 10:31:23 -060037 * @brief Handle checkstop attention
38 *
Ben Tynerb481d902020-03-05 10:24:23 -060039 * @param i_attention Attention object
Ben Tyner3fb52e52020-03-31 10:10:07 -050040 * @return 0 indicates that the checkstop attention was successfully handled
41 * 1 indicates that the checkstop attention was NOT successfully
42 * handled.
Ben Tyneref320152020-01-09 10:31:23 -060043 */
Ben Tynerb481d902020-03-05 10:24:23 -060044int handleCheckstop(Attention* i_attention);
Ben Tyneref320152020-01-09 10:31:23 -060045
46/**
47 * @brief Handle special attention
48 *
Ben Tynerb481d902020-03-05 10:24:23 -060049 * @param i_attention Attention object
Ben Tyner3fb52e52020-03-31 10:10:07 -050050 * @return 0 indicates that the special attention was successfully handled
51 * 1 indicates that the special attention was NOT successfully handled
Ben Tyneref320152020-01-09 10:31:23 -060052 */
Ben Tynerb481d902020-03-05 10:24:23 -060053int handleSpecial(Attention* i_attention);
Ben Tyneref320152020-01-09 10:31:23 -060054
Ben Tynerfb190542020-11-06 09:27:56 -060055/** @brief Determine if attention is active and not masked */
Ben Tyner1965e502020-11-20 10:32:24 -060056bool activeAttn(uint32_t i_val, uint32_t i_mask, uint32_t i_attn);
Ben Tynerfb190542020-11-06 09:27:56 -060057
Ben Tynerb9715172021-09-29 08:46:19 -050058#ifdef CONFIG_PHAL_API
59/** @brief Handle phal sbe exception */
60void phalSbeExceptionHandler(openpower::phal::exception::SbeError& e,
Ben Tyner76e52f62022-02-01 10:46:44 -060061 uint32_t chipPosition, uint32_t command);
Ben Tynerb9715172021-09-29 08:46:19 -050062#endif
63
64/** @brief Get static TI info data based on host state */
65void getStaticTiInfo(uint8_t*& tiInfoPtr);
66
67/** @brief Check if TI info data is valid */
68bool tiInfoValid(uint8_t* tiInfo);
69
Ben Tyneref320152020-01-09 10:31:23 -060070/**
Ben Tyneref320152020-01-09 10:31:23 -060071 * @brief The main attention handler logic
Ben Tyner970fd4f2020-02-19 13:46:42 -060072 *
73 * @param i_breakpoints true = breakpoint special attn handling enabled
Ben Tyneref320152020-01-09 10:31:23 -060074 */
Ben Tyner3fb52e52020-03-31 10:10:07 -050075void attnHandler(Config* i_config)
Ben Tyneref320152020-01-09 10:31:23 -060076{
Ben Tynerb481d902020-03-05 10:24:23 -060077 // Vector of active attentions to be handled
78 std::vector<Attention> active_attentions;
79
Ben Tyneref320152020-01-09 10:31:23 -060080 uint32_t isr_val, isr_mask;
Ben Tyneref320152020-01-09 10:31:23 -060081
82 // loop through processors looking for active attentions
austinfcuibfa831a2022-01-26 15:37:07 -060083 trace::inf("Attention handler started");
Ben Tyner117af992020-05-22 13:32:11 -050084
Ben Tyneref320152020-01-09 10:31:23 -060085 pdbg_target* target;
Ben Tyner5e622d82020-09-11 10:10:24 -050086 pdbg_for_each_class_target("proc", target)
Ben Tyneref320152020-01-09 10:31:23 -060087 {
88 if (PDBG_TARGET_ENABLED == pdbg_target_probe(target))
89 {
Zane Shelleya79f6c82021-01-12 16:38:49 -060090 auto proc = pdbg_target_index(target); // get processor number
Ben Tyneref320152020-01-09 10:31:23 -060091
Ben Tynerb83c8522020-11-20 10:45:26 -060092 // Use PIB target to determine if a processor is enabled
Ben Tyner5e622d82020-09-11 10:10:24 -050093 char path[16];
Ben Tynerb83c8522020-11-20 10:45:26 -060094 sprintf(path, "/proc%d/pib", proc);
Ben Tyner8882c322021-02-05 12:13:21 -060095 pdbg_target* pibTarget = pdbg_target_from_path(nullptr, path);
Ben Tynerb1ebfcb2020-05-08 18:52:48 -050096
Ben Tynerb83c8522020-11-20 10:45:26 -060097 // sanity check
Ben Tyner8882c322021-02-05 12:13:21 -060098 if (nullptr == pibTarget)
Ben Tynerb83c8522020-11-20 10:45:26 -060099 {
austinfcuibfa831a2022-01-26 15:37:07 -0600100 trace::inf("pib path or target not found");
Ben Tynerb83c8522020-11-20 10:45:26 -0600101 continue;
102 }
103
Ben Tyner8882c322021-02-05 12:13:21 -0600104 // check if pib target is enabled
105 if (PDBG_TARGET_ENABLED == pdbg_target_probe(pibTarget))
Ben Tyneref320152020-01-09 10:31:23 -0600106 {
Ben Tynerb83c8522020-11-20 10:45:26 -0600107 // The processor FSI target is required for CFAM read
108 sprintf(path, "/proc%d/fsi", proc);
Ben Tyner8882c322021-02-05 12:13:21 -0600109 pdbg_target* fsiTarget = pdbg_target_from_path(nullptr, path);
Ben Tynerb83c8522020-11-20 10:45:26 -0600110
111 // sanity check
Ben Tyner8882c322021-02-05 12:13:21 -0600112 if (nullptr == fsiTarget)
Ben Tynerb83c8522020-11-20 10:45:26 -0600113 {
austinfcuibfa831a2022-01-26 15:37:07 -0600114 trace::inf("fsi path or target not found");
Ben Tynerb83c8522020-11-20 10:45:26 -0600115 continue;
116 }
117
Ben Tyner8882c322021-02-05 12:13:21 -0600118 // trace the proc number
austinfcuibfa831a2022-01-26 15:37:07 -0600119 trace::inf("proc: %u", proc);
Ben Tyner1965e502020-11-20 10:32:24 -0600120
Ben Tyner5adc96e2020-11-20 10:54:12 -0600121 isr_val = 0xffffffff; // invalid isr value
122
Ben Tyner5e622d82020-09-11 10:10:24 -0500123 // get active attentions on processor
Ben Tyner8882c322021-02-05 12:13:21 -0600124 if (RC_SUCCESS != fsi_read(fsiTarget, 0x1007, &isr_val))
Ben Tyneref320152020-01-09 10:31:23 -0600125 {
Ben Tynerfb190542020-11-06 09:27:56 -0600126 // log cfam read error
austinfcuibfa831a2022-01-26 15:37:07 -0600127 trace::err("cfam read 0x1007 FAILED");
Ben Tyner7a0dd542021-02-12 09:33:44 -0600128 eventAttentionFail((int)AttnSection::attnHandler |
129 ATTN_PDBG_CFAM);
Ben Tyneref320152020-01-09 10:31:23 -0600130 }
Ben Tyner5adc96e2020-11-20 10:54:12 -0600131 else if (0xffffffff == isr_val)
132 {
austinfcuibfa831a2022-01-26 15:37:07 -0600133 trace::err("cfam read 0x1007 INVALID");
Ben Tyner5adc96e2020-11-20 10:54:12 -0600134 continue;
135 }
Ben Tyneref320152020-01-09 10:31:23 -0600136 else
137 {
Ben Tyner8882c322021-02-05 12:13:21 -0600138 // trace isr value
austinfcuibfa831a2022-01-26 15:37:07 -0600139 trace::inf("cfam 0x1007 = 0x%08x", isr_val);
Ben Tyner1965e502020-11-20 10:32:24 -0600140
Ben Tyner5adc96e2020-11-20 10:54:12 -0600141 isr_mask = 0xffffffff; // invalid isr mask
142
Ben Tyner5e622d82020-09-11 10:10:24 -0500143 // get interrupt enabled special attentions mask
Ben Tyner8882c322021-02-05 12:13:21 -0600144 if (RC_SUCCESS != fsi_read(fsiTarget, 0x100d, &isr_mask))
Ben Tyneref320152020-01-09 10:31:23 -0600145 {
Ben Tynerfb190542020-11-06 09:27:56 -0600146 // log cfam read error
austinfcuibfa831a2022-01-26 15:37:07 -0600147 trace::err("cfam read 0x100d FAILED");
Ben Tyner7a0dd542021-02-12 09:33:44 -0600148 eventAttentionFail((int)AttnSection::attnHandler |
149 ATTN_PDBG_CFAM);
Ben Tyneref320152020-01-09 10:31:23 -0600150 }
Ben Tyner5adc96e2020-11-20 10:54:12 -0600151 else if (0xffffffff == isr_mask)
152 {
austinfcuibfa831a2022-01-26 15:37:07 -0600153 trace::err("cfam read 0x100d INVALID");
Ben Tyner5adc96e2020-11-20 10:54:12 -0600154 continue;
155 }
Ben Tyner5e622d82020-09-11 10:10:24 -0500156 else
157 {
Ben Tyner8882c322021-02-05 12:13:21 -0600158 // trace true mask
austinfcuibfa831a2022-01-26 15:37:07 -0600159 trace::inf("cfam 0x100d = 0x%08x", isr_mask);
Ben Tyner1965e502020-11-20 10:32:24 -0600160
Ben Tynerfb190542020-11-06 09:27:56 -0600161 // SBE vital attention active and not masked?
Ben Tyner1965e502020-11-20 10:32:24 -0600162 if (true == activeAttn(isr_val, isr_mask, SBE_ATTN))
Ben Tyner5e622d82020-09-11 10:10:24 -0500163 {
164 active_attentions.emplace_back(Attention::Vital,
165 handleVital, target,
166 i_config);
167 }
168
Ben Tynerfb190542020-11-06 09:27:56 -0600169 // Checkstop attention active and not masked?
170 if (true ==
Ben Tyner1965e502020-11-20 10:32:24 -0600171 activeAttn(isr_val, isr_mask, CHECKSTOP_ATTN))
Ben Tyner5e622d82020-09-11 10:10:24 -0500172 {
173 active_attentions.emplace_back(Attention::Checkstop,
174 handleCheckstop,
175 target, i_config);
176 }
177
Ben Tynerfb190542020-11-06 09:27:56 -0600178 // Special attention active and not masked?
Ben Tyner1965e502020-11-20 10:32:24 -0600179 if (true == activeAttn(isr_val, isr_mask, SPECIAL_ATTN))
Ben Tyner5e622d82020-09-11 10:10:24 -0500180 {
181 active_attentions.emplace_back(Attention::Special,
182 handleSpecial,
183 target, i_config);
184 }
185 } // cfam 0x100d valid
186 } // cfam 0x1007 valid
Ben Tyner8882c322021-02-05 12:13:21 -0600187 } // fsi target enabled
188 } // pib target enabled
Ben Tyner5e622d82020-09-11 10:10:24 -0500189 } // next processor
Ben Tyneref320152020-01-09 10:31:23 -0600190
Ben Tynerb481d902020-03-05 10:24:23 -0600191 // convert to heap, highest priority is at front
192 if (!std::is_heap(active_attentions.begin(), active_attentions.end()))
193 {
194 std::make_heap(active_attentions.begin(), active_attentions.end());
195 }
196
197 // call the attention handler until one is handled or all were attempted
198 while (false == active_attentions.empty())
199 {
200 // handle highest priority attention, done if successful
201 if (RC_SUCCESS == active_attentions.front().handle())
202 {
Ben Tynerb1ebfcb2020-05-08 18:52:48 -0500203 // an attention was handled so we are done
Ben Tynerb481d902020-03-05 10:24:23 -0600204 break;
205 }
206
207 // move attention to back of vector
208 std::pop_heap(active_attentions.begin(), active_attentions.end());
209
210 // remove attention from vector
211 active_attentions.pop_back();
212 }
Ben Tyneref320152020-01-09 10:31:23 -0600213}
214
215/**
Ben Tyneref320152020-01-09 10:31:23 -0600216 * @brief Handle checkstop attention
Ben Tyner3fb52e52020-03-31 10:10:07 -0500217 *
218 * @param i_attention Attention object
219 * @return 0 indicates that the checkstop attention was successfully handled
220 * 1 indicates that the checkstop attention was NOT successfully
221 * handled.
Ben Tyneref320152020-01-09 10:31:23 -0600222 */
Ben Tynerb481d902020-03-05 10:24:23 -0600223int handleCheckstop(Attention* i_attention)
Ben Tyneref320152020-01-09 10:31:23 -0600224{
Ben Tyner3fb52e52020-03-31 10:10:07 -0500225 int rc = RC_SUCCESS; // assume checkstop handled
Ben Tyneref320152020-01-09 10:31:23 -0600226
austinfcuibfa831a2022-01-26 15:37:07 -0600227 trace::inf("checkstop handler started");
Ben Tynerb1ebfcb2020-05-08 18:52:48 -0500228
Ben Tynerb8335562021-07-16 12:43:52 -0500229 // capture some additional data for logs/traces
230 addHbStatusRegs();
231
Ben Tyner3fb52e52020-03-31 10:10:07 -0500232 // if checkstop handling enabled, handle checkstop attention
233 if (false == (i_attention->getConfig()->getFlag(enCheckstop)))
234 {
austinfcuibfa831a2022-01-26 15:37:07 -0600235 trace::inf("Checkstop handling disabled");
Ben Tyner3fb52e52020-03-31 10:10:07 -0500236 }
237 else
238 {
Ben Tyner07ebb9b2021-12-01 12:16:24 -0600239 // wait for power fault handling before starting analyses
240 sleepSeconds(POWER_FAULT_WAIT);
241
Zane Shelley9fb73932020-09-15 13:34:57 -0500242 // Look for any attentions found in hardware. This will generate and
Zane Shelley7ae9c8c2020-12-02 20:10:31 -0600243 // commit a PEL if any errors are found.
Ben Tyner7029e522021-08-09 19:18:24 -0500244 DumpParameters dumpParameters;
Zane Shelleyebff0d32021-11-21 10:52:07 -0600245 auto logid = analyzer::analyzeHardware(
246 analyzer::AnalysisType::SYSTEM_CHECKSTOP, dumpParameters);
Zane Shelley611b3442021-11-19 16:02:01 -0600247 if (0 == logid)
Ben Tynerb1ebfcb2020-05-08 18:52:48 -0500248 {
Zane Shelley611b3442021-11-19 16:02:01 -0600249 // A PEL should exist for a checkstop attention.
Ben Tynerb1ebfcb2020-05-08 18:52:48 -0500250 rc = RC_ANALYZER_ERROR;
251 }
Ben Tyner7029e522021-08-09 19:18:24 -0500252 else
253 {
Zane Shelley611b3442021-11-19 16:02:01 -0600254 requestDump(logid, dumpParameters);
Ben Tyner7029e522021-08-09 19:18:24 -0500255 util::dbus::transitionHost(util::dbus::HostState::Quiesce);
256 }
Ben Tyner3fb52e52020-03-31 10:10:07 -0500257 }
Ben Tyneref320152020-01-09 10:31:23 -0600258
Ben Tyneref320152020-01-09 10:31:23 -0600259 return rc;
260}
261
262/**
263 * @brief Handle special attention
Ben Tyner3fb52e52020-03-31 10:10:07 -0500264 *
265 * @param i_attention Attention object
266 * @return 0 indicates that the special attention was successfully handled
267 * 1 indicates that the special attention was NOT successfully handled
Ben Tyneref320152020-01-09 10:31:23 -0600268 */
Ben Tynerb481d902020-03-05 10:24:23 -0600269int handleSpecial(Attention* i_attention)
Ben Tyneref320152020-01-09 10:31:23 -0600270{
Ben Tynerb1ebfcb2020-05-08 18:52:48 -0500271 int rc = RC_SUCCESS; // assume special attention handled
Ben Tyneref320152020-01-09 10:31:23 -0600272
Ben Tynerfb190542020-11-06 09:27:56 -0600273 // The TI info chipop will give us a pointer to the TI info data
Ben Tyner98430b32020-08-19 19:14:02 -0500274 uint8_t* tiInfo = nullptr; // ptr to TI info data
275 uint32_t tiInfoLen = 0; // length of TI info data
276 pdbg_target* attnProc = i_attention->getTarget(); // proc with attention
Ben Tynerb1ebfcb2020-05-08 18:52:48 -0500277
Ben Tyner29651ef2021-02-08 10:51:03 -0600278 bool tiInfoStatic = false; // assume TI info was provided (not created)
279
Ben Tynerb9715172021-09-29 08:46:19 -0500280 // need proc target to get dynamic TI info
281 if (nullptr != attnProc)
Ben Tyner89c0a7a2020-08-07 12:07:35 -0500282 {
Ben Tynerb9715172021-09-29 08:46:19 -0500283#ifdef CONFIG_PHAL_API
austinfcuibfa831a2022-01-26 15:37:07 -0600284 trace::inf("using libphal to get TI info");
Ben Tynerb9715172021-09-29 08:46:19 -0500285
286 // phal library uses proc target for get ti info
287 if (PDBG_TARGET_ENABLED == pdbg_target_probe(attnProc))
288 {
289 try
290 {
291 // get dynamic TI info
292 openpower::phal::sbe::getTiInfo(attnProc, &tiInfo, &tiInfoLen);
293 }
Ben Tyner76e52f62022-02-01 10:46:44 -0600294 catch (openpower::phal::exception::SbeError& sbeError)
Ben Tynerb9715172021-09-29 08:46:19 -0500295 {
296 // library threw an exception
Ben Tyner76e52f62022-02-01 10:46:44 -0600297 // note: phal::sbe::getTiInfo = command class | command ==
298 // 0xa900 | 0x04 = 0xa904. The sbe fifo command class and
299 // commands are defined in the sbefifo library source code but
300 // do not seem to be exported/installed for consumption
301 // externally.
Ben Tynerb9715172021-09-29 08:46:19 -0500302 uint32_t procNum = pdbg_target_index(attnProc);
Ben Tyner76e52f62022-02-01 10:46:44 -0600303 phalSbeExceptionHandler(sbeError, procNum, 0xa904);
Ben Tynerb9715172021-09-29 08:46:19 -0500304 }
305 }
306#else
austinfcuibfa831a2022-01-26 15:37:07 -0600307 trace::inf("using libpdbg to get TI info");
Ben Tynerb9715172021-09-29 08:46:19 -0500308
309 // pdbg library uses pib target for get ti info
Ben Tyner98430b32020-08-19 19:14:02 -0500310 char path[16];
311 sprintf(path, "/proc%d/pib", pdbg_target_index(attnProc));
312 pdbg_target* tiInfoTarget = pdbg_target_from_path(nullptr, path);
313
314 if (nullptr != tiInfoTarget)
Ben Tyner89c0a7a2020-08-07 12:07:35 -0500315 {
Ben Tyner98430b32020-08-19 19:14:02 -0500316 if (PDBG_TARGET_ENABLED == pdbg_target_probe(tiInfoTarget))
317 {
Ben Tyner98430b32020-08-19 19:14:02 -0500318 sbe_mpipl_get_ti_info(tiInfoTarget, &tiInfo, &tiInfoLen);
Ben Tyner98430b32020-08-19 19:14:02 -0500319 }
Ben Tyner89c0a7a2020-08-07 12:07:35 -0500320 }
Ben Tynerb9715172021-09-29 08:46:19 -0500321#endif
Ben Tyner89c0a7a2020-08-07 12:07:35 -0500322 }
Ben Tyneref320152020-01-09 10:31:23 -0600323
Ben Tynerb9715172021-09-29 08:46:19 -0500324 // dynamic TI info is not available
325 if (nullptr == tiInfo)
Ben Tyner970fd4f2020-02-19 13:46:42 -0600326 {
austinfcuibfa831a2022-01-26 15:37:07 -0600327 trace::inf("TI info data ptr is invalid");
Ben Tynerb9715172021-09-29 08:46:19 -0500328 getStaticTiInfo(tiInfo);
329 tiInfoStatic = true;
Ben Tyner3fb52e52020-03-31 10:10:07 -0500330 }
Ben Tyner0fe5df42020-12-03 08:57:17 -0600331
Ben Tynerb9715172021-09-29 08:46:19 -0500332 // check TI info for validity and handle
333 if (true == tiInfoValid(tiInfo))
334 {
335 // TI info is valid handle TI if support enabled
336 if (true == (i_attention->getConfig()->getFlag(enTerminate)))
337 {
338 // Call TI special attention handler
339 rc = tiHandler((TiDataArea*)tiInfo);
340 }
341 }
342 else
Ben Tyner3fb52e52020-03-31 10:10:07 -0500343 {
austinfcuibfa831a2022-01-26 15:37:07 -0600344 trace::inf("TI info NOT valid");
Ben Tyner98430b32020-08-19 19:14:02 -0500345
Ben Tynere4f5dbe2020-10-19 07:19:33 -0500346 // if configured to handle TI as default special attention
Ben Tynerfe156492021-04-08 07:28:13 -0500347 if (i_attention->getConfig()->getFlag(dfltTi))
Ben Tynere4f5dbe2020-10-19 07:19:33 -0500348 {
Ben Tynerfe156492021-04-08 07:28:13 -0500349 // TI handling may be disabled
Ben Tynere4f5dbe2020-10-19 07:19:33 -0500350 if (true == (i_attention->getConfig()->getFlag(enTerminate)))
351 {
Ben Tynere4f5dbe2020-10-19 07:19:33 -0500352 // Call TI special attention handler
Ben Tynerb9715172021-09-29 08:46:19 -0500353 rc = tiHandler((TiDataArea*)tiInfo);
Ben Tynere4f5dbe2020-10-19 07:19:33 -0500354 }
Ben Tyner3fb52e52020-03-31 10:10:07 -0500355 }
Ben Tynerb9715172021-09-29 08:46:19 -0500356 // configured to handle breakpoint as default special attention
Ben Tynerfe156492021-04-08 07:28:13 -0500357 else
358 {
359 // breakpoint handling may be disabled
360 if (true == (i_attention->getConfig()->getFlag(enBreakpoints)))
361 {
362 // Call the breakpoint special attention handler
363 rc = bpHandler();
364 }
365 }
Ben Tyner970fd4f2020-02-19 13:46:42 -0600366 }
Ben Tyneref320152020-01-09 10:31:23 -0600367
Ben Tynerb9715172021-09-29 08:46:19 -0500368 // release TI data buffer if not ours
369 if (false == tiInfoStatic)
Ben Tyner792f32f2020-06-02 08:50:47 -0500370 {
Ben Tynerb9715172021-09-29 08:46:19 -0500371 // sanity check
372 if (nullptr != tiInfo)
373 {
374 free(tiInfo);
375 }
Ben Tyner792f32f2020-06-02 08:50:47 -0500376 }
377
Ben Tynerb9715172021-09-29 08:46:19 -0500378 // trace non-successful exit condition
Ben Tyner3fb52e52020-03-31 10:10:07 -0500379 if (RC_SUCCESS != rc)
380 {
austinfcuibfa831a2022-01-26 15:37:07 -0600381 trace::inf("Special attn not handled");
Ben Tyner3fb52e52020-03-31 10:10:07 -0500382 }
Ben Tyneref320152020-01-09 10:31:23 -0600383
384 return rc;
385}
386
Ben Tynerfb190542020-11-06 09:27:56 -0600387/**
388 * @brief Determine if attention is active and not masked
389 *
390 * Determine whether an attention needs to be handled and trace details of
391 * attention type and whether it is masked or not.
392 *
393 * @param i_val attention status register
394 * @param i_mask attention true mask register
395 * @param i_attn attention type
396 * @param i_proc processor associated with registers
397 *
398 * @return true if attention is active and not masked, otherwise false
399 */
Ben Tyner1965e502020-11-20 10:32:24 -0600400bool activeAttn(uint32_t i_val, uint32_t i_mask, uint32_t i_attn)
Ben Tynerfb190542020-11-06 09:27:56 -0600401{
Zane Shelley9fb657f2021-01-12 15:30:58 -0600402 bool rc = false; // assume attn masked and/or inactive
Ben Tynerfb190542020-11-06 09:27:56 -0600403
404 // if attention active
405 if (0 != (i_val & i_attn))
406 {
austinfcuibfa831a2022-01-26 15:37:07 -0600407 std::string msg;
Ben Tynerfb190542020-11-06 09:27:56 -0600408
Zane Shelley9fb657f2021-01-12 15:30:58 -0600409 bool validAttn = true; // known attention type
410
Ben Tynerfb190542020-11-06 09:27:56 -0600411 switch (i_attn)
412 {
413 case SBE_ATTN:
austinfcuibfa831a2022-01-26 15:37:07 -0600414 msg = "SBE attn";
Ben Tynerfb190542020-11-06 09:27:56 -0600415 break;
416 case CHECKSTOP_ATTN:
austinfcuibfa831a2022-01-26 15:37:07 -0600417 msg = "Checkstop attn";
Ben Tynerfb190542020-11-06 09:27:56 -0600418 break;
419 case SPECIAL_ATTN:
austinfcuibfa831a2022-01-26 15:37:07 -0600420 msg = "Special attn";
Ben Tynerfb190542020-11-06 09:27:56 -0600421 break;
422 default:
austinfcuibfa831a2022-01-26 15:37:07 -0600423 msg = "Unknown attn";
Ben Tynerfb190542020-11-06 09:27:56 -0600424 validAttn = false;
425 }
426
427 // see if attention is masked
428 if (true == validAttn)
429 {
430 if (0 != (i_mask & i_attn))
431 {
432 rc = true; // attention active and not masked
433 }
434 else
435 {
austinfcuibfa831a2022-01-26 15:37:07 -0600436 msg += " masked";
Ben Tynerfb190542020-11-06 09:27:56 -0600437 }
438 }
439
austinfcuibfa831a2022-01-26 15:37:07 -0600440 trace::inf(msg.c_str()); // commit trace stream
Ben Tynerfb190542020-11-06 09:27:56 -0600441 }
442
443 return rc;
444}
Ben Tynerb9715172021-09-29 08:46:19 -0500445
446#ifdef CONFIG_PHAL_API
Ben Tyner76e52f62022-02-01 10:46:44 -0600447
Ben Tynerb9715172021-09-29 08:46:19 -0500448/**
449 * @brief Handle phal sbe exception
450 *
451 * @param[in] e - exception object
452 * @param[in] procNum - processor number associated with sbe exception
453 */
Ben Tyner76e52f62022-02-01 10:46:44 -0600454void phalSbeExceptionHandler(openpower::phal::exception::SbeError& sbeError,
455 uint32_t chipPosition, uint32_t command)
Ben Tynerb9715172021-09-29 08:46:19 -0500456{
Ben Tyner76e52f62022-02-01 10:46:44 -0600457 trace::err("Attention handler phal exception handler");
Ben Tynerb9715172021-09-29 08:46:19 -0500458
Ben Tyner76e52f62022-02-01 10:46:44 -0600459 // Trace exception details
460 trace::err(sbeError.what());
461
462 // Create event log entry with SBE FFDC data if provided
463 auto fd = sbeError.getFd();
464 if (fd > 0)
Ben Tynerb9715172021-09-29 08:46:19 -0500465 {
Ben Tyner76e52f62022-02-01 10:46:44 -0600466 trace::err("SBE FFDC data is available");
467
468 // FFDC parser expects chip position and command (command class |
469 // command) to be in the additional data.
470 std::map<std::string, std::string> additionalData = {
471 {"SRC6", std::to_string((chipPosition << 16) | command)}};
472
473 // See phosphor-logging/extensions/openpower-pels/README.md, "Self Boot
474 // Engine(SBE) First Failure Data Capture(FFDC)" - SBE FFDC file type
475 // is 0xCB, version is 0x01.
476 std::vector<util::FFDCTuple> ffdc{util::FFDCTuple{
477 util::FFDCFormat::Custom, static_cast<uint8_t>(0xCB),
478 static_cast<uint8_t>(0x01), fd}};
479
480 // Create event log entry with FFDC data
Ben Tyner13159682022-02-16 14:55:38 -0600481 util::dbus::createPel("org.open_power.Processor.Error.SbeChipOpFailure",
482 levelPelError, additionalData, ffdc);
Ben Tynerb9715172021-09-29 08:46:19 -0500483 }
484}
485#endif
486
487/**
488 * @brief Get static TI info data based on host state
489 *
490 * @param[out] tiInfo - pointer to static TI info data
491 */
492void getStaticTiInfo(uint8_t*& tiInfo)
493{
494 util::dbus::HostRunningState runningState = util::dbus::hostRunningState();
495
496 // assume host state is unknown
497 std::string stateString = "host state unknown";
498
499 if ((util::dbus::HostRunningState::Started == runningState) ||
500 (util::dbus::HostRunningState::Unknown == runningState))
501 {
502 if (util::dbus::HostRunningState::Started == runningState)
503 {
504 stateString = "host started";
505 }
506 tiInfo = (uint8_t*)defaultPhypTiInfo;
507 }
508 else
509 {
510 stateString = "host not started";
511 tiInfo = (uint8_t*)defaultHbTiInfo;
512 }
513
514 // trace host state
austinfcuibfa831a2022-01-26 15:37:07 -0600515 trace::inf(stateString.c_str());
Ben Tynerb9715172021-09-29 08:46:19 -0500516}
517
518/**
519 * @brief Check if TI info data is valid
520 *
521 * @param[in] tiInfo - pointer to TI info data
522 * @return true if TI info data is valid, else false
523 */
524bool tiInfoValid(uint8_t* tiInfo)
525{
526 bool tiInfoValid = false; // assume TI info invalid
527
528 // TI info data[0] non-zero indicates TI info valid (usually)
529 if ((nullptr != tiInfo) && (0 != tiInfo[0]))
530 {
531 TiDataArea* tiDataArea = (TiDataArea*)tiInfo;
532
Ben Tynerb9715172021-09-29 08:46:19 -0500533 // trace a few known TI data area values
austinfcuibfa831a2022-01-26 15:37:07 -0600534 trace::inf("TI data command = 0x02x", tiDataArea->command);
Ben Tynerb9715172021-09-29 08:46:19 -0500535
536 // Another check for valid TI Info since it has been seen that
537 // tiInfo[0] != 0 but TI info is not valid
538 if (0xa1 == tiDataArea->command)
539 {
540 tiInfoValid = true;
541
542 // trace some more data since TI info appears valid
austinfcuibfa831a2022-01-26 15:37:07 -0600543 trace::inf("TI data term-type = 0x02x",
544 tiDataArea->hbTerminateType);
Ben Tynerb9715172021-09-29 08:46:19 -0500545
austinfcuibfa831a2022-01-26 15:37:07 -0600546 trace::inf("TI data SRC format = 0x02x", tiDataArea->srcFormat);
Ben Tynerb9715172021-09-29 08:46:19 -0500547
austinfcuibfa831a2022-01-26 15:37:07 -0600548 trace::inf("TI data source = 0x02x", tiDataArea->source);
Ben Tynerb9715172021-09-29 08:46:19 -0500549 }
550 }
551
552 return tiInfoValid;
553}
554
Ben Tyneref320152020-01-09 10:31:23 -0600555} // namespace attn