1 // SPDX-License-Identifier: GPL-2.0-or-later 2 /* 3 * Firmware-Assisted Dump support on POWERVM platform. 4 * 5 * Copyright 2011, Mahesh Salgaonkar, IBM Corporation. 6 * Copyright 2019, Hari Bathini, IBM Corporation. 7 */ 8 9 #define pr_fmt(fmt) "rtas fadump: " fmt 10 11 #include <linux/string.h> 12 #include <linux/memblock.h> 13 #include <linux/delay.h> 14 #include <linux/seq_file.h> 15 #include <linux/crash_dump.h> 16 17 #include <asm/page.h> 18 #include <asm/prom.h> 19 #include <asm/rtas.h> 20 #include <asm/fadump.h> 21 #include <asm/fadump-internal.h> 22 23 #include "rtas-fadump.h" 24 25 static struct rtas_fadump_mem_struct fdm; 26 static const struct rtas_fadump_mem_struct *fdm_active; 27 28 static void rtas_fadump_update_config(struct fw_dump *fadump_conf, 29 const struct rtas_fadump_mem_struct *fdm) 30 { 31 fadump_conf->boot_mem_dest_addr = 32 be64_to_cpu(fdm->rmr_region.destination_address); 33 34 fadump_conf->fadumphdr_addr = (fadump_conf->boot_mem_dest_addr + 35 fadump_conf->boot_memory_size); 36 } 37 38 /* 39 * This function is called in the capture kernel to get configuration details 40 * setup in the first kernel and passed to the f/w. 41 */ 42 static void rtas_fadump_get_config(struct fw_dump *fadump_conf, 43 const struct rtas_fadump_mem_struct *fdm) 44 { 45 fadump_conf->boot_mem_addr[0] = 46 be64_to_cpu(fdm->rmr_region.source_address); 47 fadump_conf->boot_mem_sz[0] = be64_to_cpu(fdm->rmr_region.source_len); 48 fadump_conf->boot_memory_size = fadump_conf->boot_mem_sz[0]; 49 50 fadump_conf->boot_mem_top = fadump_conf->boot_memory_size; 51 fadump_conf->boot_mem_regs_cnt = 1; 52 53 /* 54 * Start address of reserve dump area (permanent reservation) for 55 * re-registering FADump after dump capture. 56 */ 57 fadump_conf->reserve_dump_area_start = 58 be64_to_cpu(fdm->cpu_state_data.destination_address); 59 60 rtas_fadump_update_config(fadump_conf, fdm); 61 } 62 63 static u64 rtas_fadump_init_mem_struct(struct fw_dump *fadump_conf) 64 { 65 u64 addr = fadump_conf->reserve_dump_area_start; 66 67 memset(&fdm, 0, sizeof(struct rtas_fadump_mem_struct)); 68 addr = addr & PAGE_MASK; 69 70 fdm.header.dump_format_version = cpu_to_be32(0x00000001); 71 fdm.header.dump_num_sections = cpu_to_be16(3); 72 fdm.header.dump_status_flag = 0; 73 fdm.header.offset_first_dump_section = 74 cpu_to_be32((u32)offsetof(struct rtas_fadump_mem_struct, 75 cpu_state_data)); 76 77 /* 78 * Fields for disk dump option. 79 * We are not using disk dump option, hence set these fields to 0. 80 */ 81 fdm.header.dd_block_size = 0; 82 fdm.header.dd_block_offset = 0; 83 fdm.header.dd_num_blocks = 0; 84 fdm.header.dd_offset_disk_path = 0; 85 86 /* set 0 to disable an automatic dump-reboot. */ 87 fdm.header.max_time_auto = 0; 88 89 /* Kernel dump sections */ 90 /* cpu state data section. */ 91 fdm.cpu_state_data.request_flag = 92 cpu_to_be32(RTAS_FADUMP_REQUEST_FLAG); 93 fdm.cpu_state_data.source_data_type = 94 cpu_to_be16(RTAS_FADUMP_CPU_STATE_DATA); 95 fdm.cpu_state_data.source_address = 0; 96 fdm.cpu_state_data.source_len = 97 cpu_to_be64(fadump_conf->cpu_state_data_size); 98 fdm.cpu_state_data.destination_address = cpu_to_be64(addr); 99 addr += fadump_conf->cpu_state_data_size; 100 101 /* hpte region section */ 102 fdm.hpte_region.request_flag = cpu_to_be32(RTAS_FADUMP_REQUEST_FLAG); 103 fdm.hpte_region.source_data_type = 104 cpu_to_be16(RTAS_FADUMP_HPTE_REGION); 105 fdm.hpte_region.source_address = 0; 106 fdm.hpte_region.source_len = 107 cpu_to_be64(fadump_conf->hpte_region_size); 108 fdm.hpte_region.destination_address = cpu_to_be64(addr); 109 addr += fadump_conf->hpte_region_size; 110 111 /* RMA region section */ 112 fdm.rmr_region.request_flag = cpu_to_be32(RTAS_FADUMP_REQUEST_FLAG); 113 fdm.rmr_region.source_data_type = 114 cpu_to_be16(RTAS_FADUMP_REAL_MODE_REGION); 115 fdm.rmr_region.source_address = cpu_to_be64(0); 116 fdm.rmr_region.source_len = cpu_to_be64(fadump_conf->boot_memory_size); 117 fdm.rmr_region.destination_address = cpu_to_be64(addr); 118 addr += fadump_conf->boot_memory_size; 119 120 rtas_fadump_update_config(fadump_conf, &fdm); 121 122 return addr; 123 } 124 125 static u64 rtas_fadump_get_bootmem_min(void) 126 { 127 return RTAS_FADUMP_MIN_BOOT_MEM; 128 } 129 130 static int rtas_fadump_register(struct fw_dump *fadump_conf) 131 { 132 unsigned int wait_time; 133 int rc, err = -EIO; 134 135 /* TODO: Add upper time limit for the delay */ 136 do { 137 rc = rtas_call(fadump_conf->ibm_configure_kernel_dump, 3, 1, 138 NULL, FADUMP_REGISTER, &fdm, 139 sizeof(struct rtas_fadump_mem_struct)); 140 141 wait_time = rtas_busy_delay_time(rc); 142 if (wait_time) 143 mdelay(wait_time); 144 145 } while (wait_time); 146 147 switch (rc) { 148 case 0: 149 pr_info("Registration is successful!\n"); 150 fadump_conf->dump_registered = 1; 151 err = 0; 152 break; 153 case -1: 154 pr_err("Failed to register. Hardware Error(%d).\n", rc); 155 break; 156 case -3: 157 if (!is_fadump_boot_mem_contiguous()) 158 pr_err("Can't have holes in boot memory area.\n"); 159 else if (!is_fadump_reserved_mem_contiguous()) 160 pr_err("Can't have holes in reserved memory area.\n"); 161 162 pr_err("Failed to register. Parameter Error(%d).\n", rc); 163 err = -EINVAL; 164 break; 165 case -9: 166 pr_err("Already registered!\n"); 167 fadump_conf->dump_registered = 1; 168 err = -EEXIST; 169 break; 170 default: 171 pr_err("Failed to register. Unknown Error(%d).\n", rc); 172 break; 173 } 174 175 return err; 176 } 177 178 static int rtas_fadump_unregister(struct fw_dump *fadump_conf) 179 { 180 unsigned int wait_time; 181 int rc; 182 183 /* TODO: Add upper time limit for the delay */ 184 do { 185 rc = rtas_call(fadump_conf->ibm_configure_kernel_dump, 3, 1, 186 NULL, FADUMP_UNREGISTER, &fdm, 187 sizeof(struct rtas_fadump_mem_struct)); 188 189 wait_time = rtas_busy_delay_time(rc); 190 if (wait_time) 191 mdelay(wait_time); 192 } while (wait_time); 193 194 if (rc) { 195 pr_err("Failed to un-register - unexpected error(%d).\n", rc); 196 return -EIO; 197 } 198 199 fadump_conf->dump_registered = 0; 200 return 0; 201 } 202 203 static int rtas_fadump_invalidate(struct fw_dump *fadump_conf) 204 { 205 unsigned int wait_time; 206 int rc; 207 208 /* TODO: Add upper time limit for the delay */ 209 do { 210 rc = rtas_call(fadump_conf->ibm_configure_kernel_dump, 3, 1, 211 NULL, FADUMP_INVALIDATE, fdm_active, 212 sizeof(struct rtas_fadump_mem_struct)); 213 214 wait_time = rtas_busy_delay_time(rc); 215 if (wait_time) 216 mdelay(wait_time); 217 } while (wait_time); 218 219 if (rc) { 220 pr_err("Failed to invalidate - unexpected error (%d).\n", rc); 221 return -EIO; 222 } 223 224 fadump_conf->dump_active = 0; 225 fdm_active = NULL; 226 return 0; 227 } 228 229 #define RTAS_FADUMP_GPR_MASK 0xffffff0000000000 230 static inline int rtas_fadump_gpr_index(u64 id) 231 { 232 char str[3]; 233 int i = -1; 234 235 if ((id & RTAS_FADUMP_GPR_MASK) == fadump_str_to_u64("GPR")) { 236 /* get the digits at the end */ 237 id &= ~RTAS_FADUMP_GPR_MASK; 238 id >>= 24; 239 str[2] = '\0'; 240 str[1] = id & 0xff; 241 str[0] = (id >> 8) & 0xff; 242 if (kstrtoint(str, 10, &i)) 243 i = -EINVAL; 244 if (i > 31) 245 i = -1; 246 } 247 return i; 248 } 249 250 void rtas_fadump_set_regval(struct pt_regs *regs, u64 reg_id, u64 reg_val) 251 { 252 int i; 253 254 i = rtas_fadump_gpr_index(reg_id); 255 if (i >= 0) 256 regs->gpr[i] = (unsigned long)reg_val; 257 else if (reg_id == fadump_str_to_u64("NIA")) 258 regs->nip = (unsigned long)reg_val; 259 else if (reg_id == fadump_str_to_u64("MSR")) 260 regs->msr = (unsigned long)reg_val; 261 else if (reg_id == fadump_str_to_u64("CTR")) 262 regs->ctr = (unsigned long)reg_val; 263 else if (reg_id == fadump_str_to_u64("LR")) 264 regs->link = (unsigned long)reg_val; 265 else if (reg_id == fadump_str_to_u64("XER")) 266 regs->xer = (unsigned long)reg_val; 267 else if (reg_id == fadump_str_to_u64("CR")) 268 regs->ccr = (unsigned long)reg_val; 269 else if (reg_id == fadump_str_to_u64("DAR")) 270 regs->dar = (unsigned long)reg_val; 271 else if (reg_id == fadump_str_to_u64("DSISR")) 272 regs->dsisr = (unsigned long)reg_val; 273 } 274 275 static struct rtas_fadump_reg_entry* 276 rtas_fadump_read_regs(struct rtas_fadump_reg_entry *reg_entry, 277 struct pt_regs *regs) 278 { 279 memset(regs, 0, sizeof(struct pt_regs)); 280 281 while (be64_to_cpu(reg_entry->reg_id) != fadump_str_to_u64("CPUEND")) { 282 rtas_fadump_set_regval(regs, be64_to_cpu(reg_entry->reg_id), 283 be64_to_cpu(reg_entry->reg_value)); 284 reg_entry++; 285 } 286 reg_entry++; 287 return reg_entry; 288 } 289 290 /* 291 * Read CPU state dump data and convert it into ELF notes. 292 * The CPU dump starts with magic number "REGSAVE". NumCpusOffset should be 293 * used to access the data to allow for additional fields to be added without 294 * affecting compatibility. Each list of registers for a CPU starts with 295 * "CPUSTRT" and ends with "CPUEND". Each register entry is of 16 bytes, 296 * 8 Byte ASCII identifier and 8 Byte register value. The register entry 297 * with identifier "CPUSTRT" and "CPUEND" contains 4 byte cpu id as part 298 * of register value. For more details refer to PAPR document. 299 * 300 * Only for the crashing cpu we ignore the CPU dump data and get exact 301 * state from fadump crash info structure populated by first kernel at the 302 * time of crash. 303 */ 304 static int __init rtas_fadump_build_cpu_notes(struct fw_dump *fadump_conf) 305 { 306 struct rtas_fadump_reg_save_area_header *reg_header; 307 struct fadump_crash_info_header *fdh = NULL; 308 struct rtas_fadump_reg_entry *reg_entry; 309 u32 num_cpus, *note_buf; 310 int i, rc = 0, cpu = 0; 311 struct pt_regs regs; 312 unsigned long addr; 313 void *vaddr; 314 315 addr = be64_to_cpu(fdm_active->cpu_state_data.destination_address); 316 vaddr = __va(addr); 317 318 reg_header = vaddr; 319 if (be64_to_cpu(reg_header->magic_number) != 320 fadump_str_to_u64("REGSAVE")) { 321 pr_err("Unable to read register save area.\n"); 322 return -ENOENT; 323 } 324 325 pr_debug("--------CPU State Data------------\n"); 326 pr_debug("Magic Number: %llx\n", be64_to_cpu(reg_header->magic_number)); 327 pr_debug("NumCpuOffset: %x\n", be32_to_cpu(reg_header->num_cpu_offset)); 328 329 vaddr += be32_to_cpu(reg_header->num_cpu_offset); 330 num_cpus = be32_to_cpu(*((__be32 *)(vaddr))); 331 pr_debug("NumCpus : %u\n", num_cpus); 332 vaddr += sizeof(u32); 333 reg_entry = (struct rtas_fadump_reg_entry *)vaddr; 334 335 rc = fadump_setup_cpu_notes_buf(num_cpus); 336 if (rc != 0) 337 return rc; 338 339 note_buf = (u32 *)fadump_conf->cpu_notes_buf_vaddr; 340 341 if (fadump_conf->fadumphdr_addr) 342 fdh = __va(fadump_conf->fadumphdr_addr); 343 344 for (i = 0; i < num_cpus; i++) { 345 if (be64_to_cpu(reg_entry->reg_id) != 346 fadump_str_to_u64("CPUSTRT")) { 347 pr_err("Unable to read CPU state data\n"); 348 rc = -ENOENT; 349 goto error_out; 350 } 351 /* Lower 4 bytes of reg_value contains logical cpu id */ 352 cpu = (be64_to_cpu(reg_entry->reg_value) & 353 RTAS_FADUMP_CPU_ID_MASK); 354 if (fdh && !cpumask_test_cpu(cpu, &fdh->online_mask)) { 355 RTAS_FADUMP_SKIP_TO_NEXT_CPU(reg_entry); 356 continue; 357 } 358 pr_debug("Reading register data for cpu %d...\n", cpu); 359 if (fdh && fdh->crashing_cpu == cpu) { 360 regs = fdh->regs; 361 note_buf = fadump_regs_to_elf_notes(note_buf, ®s); 362 RTAS_FADUMP_SKIP_TO_NEXT_CPU(reg_entry); 363 } else { 364 reg_entry++; 365 reg_entry = rtas_fadump_read_regs(reg_entry, ®s); 366 note_buf = fadump_regs_to_elf_notes(note_buf, ®s); 367 } 368 } 369 final_note(note_buf); 370 371 if (fdh) { 372 pr_debug("Updating elfcore header (%llx) with cpu notes\n", 373 fdh->elfcorehdr_addr); 374 fadump_update_elfcore_header(__va(fdh->elfcorehdr_addr)); 375 } 376 return 0; 377 378 error_out: 379 fadump_free_cpu_notes_buf(); 380 return rc; 381 382 } 383 384 /* 385 * Validate and process the dump data stored by firmware before exporting 386 * it through '/proc/vmcore'. 387 */ 388 static int __init rtas_fadump_process(struct fw_dump *fadump_conf) 389 { 390 struct fadump_crash_info_header *fdh; 391 int rc = 0; 392 393 if (!fdm_active || !fadump_conf->fadumphdr_addr) 394 return -EINVAL; 395 396 /* Check if the dump data is valid. */ 397 if ((be16_to_cpu(fdm_active->header.dump_status_flag) == 398 RTAS_FADUMP_ERROR_FLAG) || 399 (fdm_active->cpu_state_data.error_flags != 0) || 400 (fdm_active->rmr_region.error_flags != 0)) { 401 pr_err("Dump taken by platform is not valid\n"); 402 return -EINVAL; 403 } 404 if ((fdm_active->rmr_region.bytes_dumped != 405 fdm_active->rmr_region.source_len) || 406 !fdm_active->cpu_state_data.bytes_dumped) { 407 pr_err("Dump taken by platform is incomplete\n"); 408 return -EINVAL; 409 } 410 411 /* Validate the fadump crash info header */ 412 fdh = __va(fadump_conf->fadumphdr_addr); 413 if (fdh->magic_number != FADUMP_CRASH_INFO_MAGIC) { 414 pr_err("Crash info header is not valid.\n"); 415 return -EINVAL; 416 } 417 418 rc = rtas_fadump_build_cpu_notes(fadump_conf); 419 if (rc) 420 return rc; 421 422 /* 423 * We are done validating dump info and elfcore header is now ready 424 * to be exported. set elfcorehdr_addr so that vmcore module will 425 * export the elfcore header through '/proc/vmcore'. 426 */ 427 elfcorehdr_addr = fdh->elfcorehdr_addr; 428 429 return 0; 430 } 431 432 static void rtas_fadump_region_show(struct fw_dump *fadump_conf, 433 struct seq_file *m) 434 { 435 const struct rtas_fadump_section *cpu_data_section; 436 const struct rtas_fadump_mem_struct *fdm_ptr; 437 438 if (fdm_active) 439 fdm_ptr = fdm_active; 440 else 441 fdm_ptr = &fdm; 442 443 cpu_data_section = &(fdm_ptr->cpu_state_data); 444 seq_printf(m, "CPU :[%#016llx-%#016llx] %#llx bytes, Dumped: %#llx\n", 445 be64_to_cpu(cpu_data_section->destination_address), 446 be64_to_cpu(cpu_data_section->destination_address) + 447 be64_to_cpu(cpu_data_section->source_len) - 1, 448 be64_to_cpu(cpu_data_section->source_len), 449 be64_to_cpu(cpu_data_section->bytes_dumped)); 450 451 seq_printf(m, "HPTE:[%#016llx-%#016llx] %#llx bytes, Dumped: %#llx\n", 452 be64_to_cpu(fdm_ptr->hpte_region.destination_address), 453 be64_to_cpu(fdm_ptr->hpte_region.destination_address) + 454 be64_to_cpu(fdm_ptr->hpte_region.source_len) - 1, 455 be64_to_cpu(fdm_ptr->hpte_region.source_len), 456 be64_to_cpu(fdm_ptr->hpte_region.bytes_dumped)); 457 458 seq_printf(m, "DUMP: Src: %#016llx, Dest: %#016llx, ", 459 be64_to_cpu(fdm_ptr->rmr_region.source_address), 460 be64_to_cpu(fdm_ptr->rmr_region.destination_address)); 461 seq_printf(m, "Size: %#llx, Dumped: %#llx bytes\n", 462 be64_to_cpu(fdm_ptr->rmr_region.source_len), 463 be64_to_cpu(fdm_ptr->rmr_region.bytes_dumped)); 464 465 /* Dump is active. Show reserved area start address. */ 466 if (fdm_active) { 467 seq_printf(m, "\nMemory above %#016lx is reserved for saving crash dump\n", 468 fadump_conf->reserve_dump_area_start); 469 } 470 } 471 472 static void rtas_fadump_trigger(struct fadump_crash_info_header *fdh, 473 const char *msg) 474 { 475 /* Call ibm,os-term rtas call to trigger firmware assisted dump */ 476 rtas_os_term((char *)msg); 477 } 478 479 static struct fadump_ops rtas_fadump_ops = { 480 .fadump_init_mem_struct = rtas_fadump_init_mem_struct, 481 .fadump_get_bootmem_min = rtas_fadump_get_bootmem_min, 482 .fadump_register = rtas_fadump_register, 483 .fadump_unregister = rtas_fadump_unregister, 484 .fadump_invalidate = rtas_fadump_invalidate, 485 .fadump_process = rtas_fadump_process, 486 .fadump_region_show = rtas_fadump_region_show, 487 .fadump_trigger = rtas_fadump_trigger, 488 }; 489 490 void __init rtas_fadump_dt_scan(struct fw_dump *fadump_conf, u64 node) 491 { 492 int i, size, num_sections; 493 const __be32 *sections; 494 const __be32 *token; 495 496 /* 497 * Check if Firmware Assisted dump is supported. if yes, check 498 * if dump has been initiated on last reboot. 499 */ 500 token = of_get_flat_dt_prop(node, "ibm,configure-kernel-dump", NULL); 501 if (!token) 502 return; 503 504 fadump_conf->ibm_configure_kernel_dump = be32_to_cpu(*token); 505 fadump_conf->ops = &rtas_fadump_ops; 506 fadump_conf->fadump_supported = 1; 507 508 /* Firmware supports 64-bit value for size, align it to pagesize. */ 509 fadump_conf->max_copy_size = _ALIGN_DOWN(U64_MAX, PAGE_SIZE); 510 511 /* 512 * The 'ibm,kernel-dump' rtas node is present only if there is 513 * dump data waiting for us. 514 */ 515 fdm_active = of_get_flat_dt_prop(node, "ibm,kernel-dump", NULL); 516 if (fdm_active) { 517 pr_info("Firmware-assisted dump is active.\n"); 518 fadump_conf->dump_active = 1; 519 rtas_fadump_get_config(fadump_conf, (void *)__pa(fdm_active)); 520 } 521 522 /* Get the sizes required to store dump data for the firmware provided 523 * dump sections. 524 * For each dump section type supported, a 32bit cell which defines 525 * the ID of a supported section followed by two 32 bit cells which 526 * gives the size of the section in bytes. 527 */ 528 sections = of_get_flat_dt_prop(node, "ibm,configure-kernel-dump-sizes", 529 &size); 530 531 if (!sections) 532 return; 533 534 num_sections = size / (3 * sizeof(u32)); 535 536 for (i = 0; i < num_sections; i++, sections += 3) { 537 u32 type = (u32)of_read_number(sections, 1); 538 539 switch (type) { 540 case RTAS_FADUMP_CPU_STATE_DATA: 541 fadump_conf->cpu_state_data_size = 542 of_read_ulong(§ions[1], 2); 543 break; 544 case RTAS_FADUMP_HPTE_REGION: 545 fadump_conf->hpte_region_size = 546 of_read_ulong(§ions[1], 2); 547 break; 548 } 549 } 550 } 551