linux/include/ras/ras_event.h
<<
>>
Prefs
   1/* SPDX-License-Identifier: GPL-2.0 */
   2#undef TRACE_SYSTEM
   3#define TRACE_SYSTEM ras
   4#define TRACE_INCLUDE_FILE ras_event
   5
   6#if !defined(_TRACE_HW_EVENT_MC_H) || defined(TRACE_HEADER_MULTI_READ)
   7#define _TRACE_HW_EVENT_MC_H
   8
   9#include <linux/tracepoint.h>
  10#include <linux/edac.h>
  11#include <linux/ktime.h>
  12#include <linux/pci.h>
  13#include <linux/aer.h>
  14#include <linux/cper.h>
  15#include <linux/mm.h>
  16
  17/*
  18 * MCE Extended Error Log trace event
  19 *
  20 * These events are generated when hardware detects a corrected or
  21 * uncorrected event.
  22 */
  23
  24/* memory trace event */
  25
  26#if defined(CONFIG_ACPI_EXTLOG) || defined(CONFIG_ACPI_EXTLOG_MODULE)
  27TRACE_EVENT(extlog_mem_event,
  28        TP_PROTO(struct cper_sec_mem_err *mem,
  29                 u32 err_seq,
  30                 const guid_t *fru_id,
  31                 const char *fru_text,
  32                 u8 sev),
  33
  34        TP_ARGS(mem, err_seq, fru_id, fru_text, sev),
  35
  36        TP_STRUCT__entry(
  37                __field(u32, err_seq)
  38                __field(u8, etype)
  39                __field(u8, sev)
  40                __field(u64, pa)
  41                __field(u8, pa_mask_lsb)
  42                __field_struct(guid_t, fru_id)
  43                __string(fru_text, fru_text)
  44                __field_struct(struct cper_mem_err_compact, data)
  45        ),
  46
  47        TP_fast_assign(
  48                __entry->err_seq = err_seq;
  49                if (mem->validation_bits & CPER_MEM_VALID_ERROR_TYPE)
  50                        __entry->etype = mem->error_type;
  51                else
  52                        __entry->etype = ~0;
  53                __entry->sev = sev;
  54                if (mem->validation_bits & CPER_MEM_VALID_PA)
  55                        __entry->pa = mem->physical_addr;
  56                else
  57                        __entry->pa = ~0ull;
  58
  59                if (mem->validation_bits & CPER_MEM_VALID_PA_MASK)
  60                        __entry->pa_mask_lsb = (u8)__ffs64(mem->physical_addr_mask);
  61                else
  62                        __entry->pa_mask_lsb = ~0;
  63                __entry->fru_id = *fru_id;
  64                __assign_str(fru_text, fru_text);
  65                cper_mem_err_pack(mem, &__entry->data);
  66        ),
  67
  68        TP_printk("{%d} %s error: %s physical addr: %016llx (mask lsb: %x) %sFRU: %pUl %.20s",
  69                  __entry->err_seq,
  70                  cper_severity_str(__entry->sev),
  71                  cper_mem_err_type_str(__entry->etype),
  72                  __entry->pa,
  73                  __entry->pa_mask_lsb,
  74                  cper_mem_err_unpack(p, &__entry->data),
  75                  &__entry->fru_id,
  76                  __get_str(fru_text))
  77);
  78#endif
  79
  80/*
  81 * Hardware Events Report
  82 *
  83 * Those events are generated when hardware detected a corrected or
  84 * uncorrected event, and are meant to replace the current API to report
  85 * errors defined on both EDAC and MCE subsystems.
  86 *
  87 * FIXME: Add events for handling memory errors originated from the
  88 *        MCE subsystem.
  89 */
  90
  91/*
  92 * Hardware-independent Memory Controller specific events
  93 */
  94
  95/*
  96 * Default error mechanisms for Memory Controller errors (CE and UE)
  97 */
  98TRACE_EVENT(mc_event,
  99
 100        TP_PROTO(const unsigned int err_type,
 101                 const char *error_msg,
 102                 const char *label,
 103                 const int error_count,
 104                 const u8 mc_index,
 105                 const s8 top_layer,
 106                 const s8 mid_layer,
 107                 const s8 low_layer,
 108                 unsigned long address,
 109                 const u8 grain_bits,
 110                 unsigned long syndrome,
 111                 const char *driver_detail),
 112
 113        TP_ARGS(err_type, error_msg, label, error_count, mc_index,
 114                top_layer, mid_layer, low_layer, address, grain_bits,
 115                syndrome, driver_detail),
 116
 117        TP_STRUCT__entry(
 118                __field(        unsigned int,   error_type              )
 119                __string(       msg,            error_msg               )
 120                __string(       label,          label                   )
 121                __field(        u16,            error_count             )
 122                __field(        u8,             mc_index                )
 123                __field(        s8,             top_layer               )
 124                __field(        s8,             middle_layer            )
 125                __field(        s8,             lower_layer             )
 126                __field(        long,           address                 )
 127                __field(        u8,             grain_bits              )
 128                __field(        long,           syndrome                )
 129                __string(       driver_detail,  driver_detail           )
 130        ),
 131
 132        TP_fast_assign(
 133                __entry->error_type             = err_type;
 134                __assign_str(msg, error_msg);
 135                __assign_str(label, label);
 136                __entry->error_count            = error_count;
 137                __entry->mc_index               = mc_index;
 138                __entry->top_layer              = top_layer;
 139                __entry->middle_layer           = mid_layer;
 140                __entry->lower_layer            = low_layer;
 141                __entry->address                = address;
 142                __entry->grain_bits             = grain_bits;
 143                __entry->syndrome               = syndrome;
 144                __assign_str(driver_detail, driver_detail);
 145        ),
 146
 147        TP_printk("%d %s error%s:%s%s on %s (mc:%d location:%d:%d:%d address:0x%08lx grain:%d syndrome:0x%08lx%s%s)",
 148                  __entry->error_count,
 149                  mc_event_error_type(__entry->error_type),
 150                  __entry->error_count > 1 ? "s" : "",
 151                  __get_str(msg)[0] ? " " : "",
 152                  __get_str(msg),
 153                  __get_str(label),
 154                  __entry->mc_index,
 155                  __entry->top_layer,
 156                  __entry->middle_layer,
 157                  __entry->lower_layer,
 158                  __entry->address,
 159                  1 << __entry->grain_bits,
 160                  __entry->syndrome,
 161                  __get_str(driver_detail)[0] ? " " : "",
 162                  __get_str(driver_detail))
 163);
 164
 165/*
 166 * ARM Processor Events Report
 167 *
 168 * This event is generated when hardware detects an ARM processor error
 169 * has occurred. UEFI 2.6 spec section N.2.4.4.
 170 */
 171TRACE_EVENT(arm_event,
 172
 173        TP_PROTO(const struct cper_sec_proc_arm *proc),
 174
 175        TP_ARGS(proc),
 176
 177        TP_STRUCT__entry(
 178                __field(u64, mpidr)
 179                __field(u64, midr)
 180                __field(u32, running_state)
 181                __field(u32, psci_state)
 182                __field(u8, affinity)
 183        ),
 184
 185        TP_fast_assign(
 186                if (proc->validation_bits & CPER_ARM_VALID_AFFINITY_LEVEL)
 187                        __entry->affinity = proc->affinity_level;
 188                else
 189                        __entry->affinity = ~0;
 190                if (proc->validation_bits & CPER_ARM_VALID_MPIDR)
 191                        __entry->mpidr = proc->mpidr;
 192                else
 193                        __entry->mpidr = 0ULL;
 194                __entry->midr = proc->midr;
 195                if (proc->validation_bits & CPER_ARM_VALID_RUNNING_STATE) {
 196                        __entry->running_state = proc->running_state;
 197                        __entry->psci_state = proc->psci_state;
 198                } else {
 199                        __entry->running_state = ~0;
 200                        __entry->psci_state = ~0;
 201                }
 202        ),
 203
 204        TP_printk("affinity level: %d; MPIDR: %016llx; MIDR: %016llx; "
 205                  "running state: %d; PSCI state: %d",
 206                  __entry->affinity, __entry->mpidr, __entry->midr,
 207                  __entry->running_state, __entry->psci_state)
 208);
 209
 210/*
 211 * Non-Standard Section Report
 212 *
 213 * This event is generated when hardware detected a hardware
 214 * error event, which may be of non-standard section as defined
 215 * in UEFI spec appendix "Common Platform Error Record", or may
 216 * be of sections for which TRACE_EVENT is not defined.
 217 *
 218 */
 219TRACE_EVENT(non_standard_event,
 220
 221        TP_PROTO(const guid_t *sec_type,
 222                 const guid_t *fru_id,
 223                 const char *fru_text,
 224                 const u8 sev,
 225                 const u8 *err,
 226                 const u32 len),
 227
 228        TP_ARGS(sec_type, fru_id, fru_text, sev, err, len),
 229
 230        TP_STRUCT__entry(
 231                __array(char, sec_type, UUID_SIZE)
 232                __array(char, fru_id, UUID_SIZE)
 233                __string(fru_text, fru_text)
 234                __field(u8, sev)
 235                __field(u32, len)
 236                __dynamic_array(u8, buf, len)
 237        ),
 238
 239        TP_fast_assign(
 240                memcpy(__entry->sec_type, sec_type, UUID_SIZE);
 241                memcpy(__entry->fru_id, fru_id, UUID_SIZE);
 242                __assign_str(fru_text, fru_text);
 243                __entry->sev = sev;
 244                __entry->len = len;
 245                memcpy(__get_dynamic_array(buf), err, len);
 246        ),
 247
 248        TP_printk("severity: %d; sec type:%pU; FRU: %pU %s; data len:%d; raw data:%s",
 249                  __entry->sev, __entry->sec_type,
 250                  __entry->fru_id, __get_str(fru_text),
 251                  __entry->len,
 252                  __print_hex(__get_dynamic_array(buf), __entry->len))
 253);
 254
 255/*
 256 * PCIe AER Trace event
 257 *
 258 * These events are generated when hardware detects a corrected or
 259 * uncorrected event on a PCIe device. The event report has
 260 * the following structure:
 261 *
 262 * char * dev_name -    The name of the slot where the device resides
 263 *                      ([domain:]bus:device.function).
 264 * u32 status -         Either the correctable or uncorrectable register
 265 *                      indicating what error or errors have been seen
 266 * u8 severity -        error severity 0:NONFATAL 1:FATAL 2:CORRECTED
 267 */
 268
 269#define aer_correctable_errors                                  \
 270        {PCI_ERR_COR_RCVR,      "Receiver Error"},              \
 271        {PCI_ERR_COR_BAD_TLP,   "Bad TLP"},                     \
 272        {PCI_ERR_COR_BAD_DLLP,  "Bad DLLP"},                    \
 273        {PCI_ERR_COR_REP_ROLL,  "RELAY_NUM Rollover"},          \
 274        {PCI_ERR_COR_REP_TIMER, "Replay Timer Timeout"},        \
 275        {PCI_ERR_COR_ADV_NFAT,  "Advisory Non-Fatal Error"},    \
 276        {PCI_ERR_COR_INTERNAL,  "Corrected Internal Error"},    \
 277        {PCI_ERR_COR_LOG_OVER,  "Header Log Overflow"}
 278
 279#define aer_uncorrectable_errors                                \
 280        {PCI_ERR_UNC_UND,       "Undefined"},                   \
 281        {PCI_ERR_UNC_DLP,       "Data Link Protocol Error"},    \
 282        {PCI_ERR_UNC_SURPDN,    "Surprise Down Error"},         \
 283        {PCI_ERR_UNC_POISON_TLP,"Poisoned TLP"},                \
 284        {PCI_ERR_UNC_FCP,       "Flow Control Protocol Error"}, \
 285        {PCI_ERR_UNC_COMP_TIME, "Completion Timeout"},          \
 286        {PCI_ERR_UNC_COMP_ABORT,"Completer Abort"},             \
 287        {PCI_ERR_UNC_UNX_COMP,  "Unexpected Completion"},       \
 288        {PCI_ERR_UNC_RX_OVER,   "Receiver Overflow"},           \
 289        {PCI_ERR_UNC_MALF_TLP,  "Malformed TLP"},               \
 290        {PCI_ERR_UNC_ECRC,      "ECRC Error"},                  \
 291        {PCI_ERR_UNC_UNSUP,     "Unsupported Request Error"},   \
 292        {PCI_ERR_UNC_ACSV,      "ACS Violation"},               \
 293        {PCI_ERR_UNC_INTN,      "Uncorrectable Internal Error"},\
 294        {PCI_ERR_UNC_MCBTLP,    "MC Blocked TLP"},              \
 295        {PCI_ERR_UNC_ATOMEG,    "AtomicOp Egress Blocked"},     \
 296        {PCI_ERR_UNC_TLPPRE,    "TLP Prefix Blocked Error"}
 297
 298TRACE_EVENT(aer_event,
 299        TP_PROTO(const char *dev_name,
 300                 const u32 status,
 301                 const u8 severity,
 302                 const u8 tlp_header_valid,
 303                 struct aer_header_log_regs *tlp),
 304
 305        TP_ARGS(dev_name, status, severity, tlp_header_valid, tlp),
 306
 307        TP_STRUCT__entry(
 308                __string(       dev_name,       dev_name        )
 309                __field(        u32,            status          )
 310                __field(        u8,             severity        )
 311                __field(        u8,             tlp_header_valid)
 312                __array(        u32,            tlp_header, 4   )
 313        ),
 314
 315        TP_fast_assign(
 316                __assign_str(dev_name, dev_name);
 317                __entry->status         = status;
 318                __entry->severity       = severity;
 319                __entry->tlp_header_valid = tlp_header_valid;
 320                if (tlp_header_valid) {
 321                        __entry->tlp_header[0] = tlp->dw0;
 322                        __entry->tlp_header[1] = tlp->dw1;
 323                        __entry->tlp_header[2] = tlp->dw2;
 324                        __entry->tlp_header[3] = tlp->dw3;
 325                }
 326        ),
 327
 328        TP_printk("%s PCIe Bus Error: severity=%s, %s, TLP Header=%s\n",
 329                __get_str(dev_name),
 330                __entry->severity == AER_CORRECTABLE ? "Corrected" :
 331                        __entry->severity == AER_FATAL ?
 332                        "Fatal" : "Uncorrected, non-fatal",
 333                __entry->severity == AER_CORRECTABLE ?
 334                __print_flags(__entry->status, "|", aer_correctable_errors) :
 335                __print_flags(__entry->status, "|", aer_uncorrectable_errors),
 336                __entry->tlp_header_valid ?
 337                        __print_array(__entry->tlp_header, 4, 4) :
 338                        "Not available")
 339);
 340
 341/*
 342 * memory-failure recovery action result event
 343 *
 344 * unsigned long pfn -  Page Frame Number of the corrupted page
 345 * int type     -       Page types of the corrupted page
 346 * int result   -       Result of recovery action
 347 */
 348
 349#ifdef CONFIG_MEMORY_FAILURE
 350#define MF_ACTION_RESULT        \
 351        EM ( MF_IGNORED, "Ignored" )    \
 352        EM ( MF_FAILED,  "Failed" )     \
 353        EM ( MF_DELAYED, "Delayed" )    \
 354        EMe ( MF_RECOVERED, "Recovered" )
 355
 356#define MF_PAGE_TYPE            \
 357        EM ( MF_MSG_KERNEL, "reserved kernel page" )                    \
 358        EM ( MF_MSG_KERNEL_HIGH_ORDER, "high-order kernel page" )       \
 359        EM ( MF_MSG_SLAB, "kernel slab page" )                          \
 360        EM ( MF_MSG_DIFFERENT_COMPOUND, "different compound page after locking" ) \
 361        EM ( MF_MSG_POISONED_HUGE, "huge page already hardware poisoned" )      \
 362        EM ( MF_MSG_HUGE, "huge page" )                                 \
 363        EM ( MF_MSG_FREE_HUGE, "free huge page" )                       \
 364        EM ( MF_MSG_UNMAP_FAILED, "unmapping failed page" )             \
 365        EM ( MF_MSG_DIRTY_SWAPCACHE, "dirty swapcache page" )           \
 366        EM ( MF_MSG_CLEAN_SWAPCACHE, "clean swapcache page" )           \
 367        EM ( MF_MSG_DIRTY_MLOCKED_LRU, "dirty mlocked LRU page" )       \
 368        EM ( MF_MSG_CLEAN_MLOCKED_LRU, "clean mlocked LRU page" )       \
 369        EM ( MF_MSG_DIRTY_UNEVICTABLE_LRU, "dirty unevictable LRU page" )       \
 370        EM ( MF_MSG_CLEAN_UNEVICTABLE_LRU, "clean unevictable LRU page" )       \
 371        EM ( MF_MSG_DIRTY_LRU, "dirty LRU page" )                       \
 372        EM ( MF_MSG_CLEAN_LRU, "clean LRU page" )                       \
 373        EM ( MF_MSG_TRUNCATED_LRU, "already truncated LRU page" )       \
 374        EM ( MF_MSG_BUDDY, "free buddy page" )                          \
 375        EM ( MF_MSG_BUDDY_2ND, "free buddy page (2nd try)" )            \
 376        EMe ( MF_MSG_UNKNOWN, "unknown page" )
 377
 378/*
 379 * First define the enums in MM_ACTION_RESULT to be exported to userspace
 380 * via TRACE_DEFINE_ENUM().
 381 */
 382#undef EM
 383#undef EMe
 384#define EM(a, b) TRACE_DEFINE_ENUM(a);
 385#define EMe(a, b)       TRACE_DEFINE_ENUM(a);
 386
 387MF_ACTION_RESULT
 388MF_PAGE_TYPE
 389
 390/*
 391 * Now redefine the EM() and EMe() macros to map the enums to the strings
 392 * that will be printed in the output.
 393 */
 394#undef EM
 395#undef EMe
 396#define EM(a, b)                { a, b },
 397#define EMe(a, b)       { a, b }
 398
 399TRACE_EVENT(memory_failure_event,
 400        TP_PROTO(unsigned long pfn,
 401                 int type,
 402                 int result),
 403
 404        TP_ARGS(pfn, type, result),
 405
 406        TP_STRUCT__entry(
 407                __field(unsigned long, pfn)
 408                __field(int, type)
 409                __field(int, result)
 410        ),
 411
 412        TP_fast_assign(
 413                __entry->pfn    = pfn;
 414                __entry->type   = type;
 415                __entry->result = result;
 416        ),
 417
 418        TP_printk("pfn %#lx: recovery action for %s: %s",
 419                __entry->pfn,
 420                __print_symbolic(__entry->type, MF_PAGE_TYPE),
 421                __print_symbolic(__entry->result, MF_ACTION_RESULT)
 422        )
 423);
 424#endif /* CONFIG_MEMORY_FAILURE */
 425#endif /* _TRACE_HW_EVENT_MC_H */
 426
 427/* This part must be outside protection */
 428#include <trace/define_trace.h>
 429