static int kt_stack_common(uintptr_t addr, uint_t flags, int argc, const mdb_arg_t *argv, mdb_tgt_stack_f *func) { kt_data_t *kt = mdb.m_target->t_data; void *arg = (void *)(uintptr_t)mdb.m_nargs; mdb_tgt_gregset_t gregs, *grp; if (flags & DCMD_ADDRSPEC) { bzero(&gregs, sizeof (gregs)); gregs.kregs[KREG_RBP] = addr; grp = &gregs; } else grp = kt->k_regs; if (argc != 0) { if (argv->a_type == MDB_TYPE_CHAR || argc > 1) return (DCMD_USAGE); if (argv->a_type == MDB_TYPE_STRING) arg = (void *)mdb_strtoull(argv->a_un.a_str); else arg = (void *)argv->a_un.a_val; } (void) mdb_amd64_kvm_stack_iter(mdb.m_target, grp, func, arg); return (DCMD_OK); }
/*ARGSUSED*/ static int scalehrtime_cmd(uintptr_t addr, uint_t flags, int argc, const mdb_arg_t *argv) { uint32_t nsec_scale; hrtime_t tsc = addr, hrt; unsigned int *tscp = (unsigned int *)&tsc; uintptr_t scalehrtimef; uint64_t scale; GElf_Sym sym; if (!(flags & DCMD_ADDRSPEC)) { if (argc != 1) return (DCMD_USAGE); switch (argv[0].a_type) { case MDB_TYPE_STRING: tsc = mdb_strtoull(argv[0].a_un.a_str); break; case MDB_TYPE_IMMEDIATE: tsc = argv[0].a_un.a_val; break; default: return (DCMD_USAGE); } } if (mdb_readsym(&scalehrtimef, sizeof (scalehrtimef), "scalehrtimef") == -1) { mdb_warn("couldn't read 'scalehrtimef'"); return (DCMD_ERR); } if (mdb_lookup_by_name("tsc_scalehrtime", &sym) == -1) { mdb_warn("couldn't find 'tsc_scalehrtime'"); return (DCMD_ERR); } if (sym.st_value != scalehrtimef) { mdb_warn("::scalehrtime requires that scalehrtimef " "be set to tsc_scalehrtime\n"); return (DCMD_ERR); } if (mdb_readsym(&nsec_scale, sizeof (nsec_scale), "nsec_scale") == -1) { mdb_warn("couldn't read 'nsec_scale'"); return (DCMD_ERR); } scale = (uint64_t)nsec_scale; hrt = ((uint64_t)tscp[1] * scale) << NSEC_SHIFT; hrt += ((uint64_t)tscp[0] * scale) >> (32 - NSEC_SHIFT); mdb_printf("0x%llx\n", hrt); return (DCMD_OK); }
/*ARGSUSED*/ int pte_dcmd(uintptr_t addr, uint_t flags, int argc, const mdb_arg_t *argv) { int level = 0; uint64_t pte = 0; char *level_str = NULL; char *pte_str = NULL; init_mmu(); if (mmu.num_level == 0) return (DCMD_ERR); if (mdb_getopts(argc, argv, 'p', MDB_OPT_STR, &pte_str, 'l', MDB_OPT_STR, &level_str) != argc) return (DCMD_USAGE); /* * parse the PTE to decode, if it's 0, we don't do anything */ if (pte_str != NULL) { pte = mdb_strtoull(pte_str); } else { if ((flags & DCMD_ADDRSPEC) == 0) return (DCMD_USAGE); pte = addr; } if (pte == 0) return (DCMD_OK); /* * parse the level if supplied */ if (level_str != NULL) { level = mdb_strtoull(level_str); if (level < 0 || level > mmu.max_level) return (DCMD_ERR); } return (do_pte_dcmd(level, pte)); }
int va2pfn_dcmd(uintptr_t addr, uint_t flags, int argc, const mdb_arg_t *argv) { uintptr_t addrspace; char *addrspace_str = NULL; int piped = flags & DCMD_PIPE_OUT; pfn_t pfn; pfn_t mfn; int rc; init_mmu(); if (mmu.num_level == 0) return (DCMD_ERR); if (mdb_getopts(argc, argv, 'a', MDB_OPT_STR, &addrspace_str) != argc) return (DCMD_USAGE); if ((flags & DCMD_ADDRSPEC) == 0) return (DCMD_USAGE); /* * parse the address space */ if (addrspace_str != NULL) addrspace = mdb_strtoull(addrspace_str); else addrspace = 0; rc = do_va2pa(addr, (struct as *)addrspace, !piped, NULL, &mfn); if (rc != DCMD_OK) return (rc); if ((pfn = mdb_mfn_to_pfn(mfn)) == -(pfn_t)1) { mdb_warn("Invalid mfn %lr\n", mfn); return (DCMD_ERR); } if (piped) { mdb_printf("0x%lr\n", pfn); return (DCMD_OK); } mdb_printf("Virtual address 0x%p maps pfn 0x%lr", addr, pfn); if (is_xpv) mdb_printf(" (mfn 0x%lr)", mfn); mdb_printf("\n"); return (DCMD_OK); }
static int xhci_mdb_find_trb(uintptr_t addr, uint_t flags, int argc, const mdb_arg_t *argv) { xhci_ring_t xr; uint64_t base, max, target; if (!(flags & DCMD_ADDRSPEC)) { mdb_warn("missing required xhci_ring_t\n"); return (DCMD_USAGE); } if (argc == 0) { mdb_warn("missing required PA of ring\n"); return (DCMD_USAGE); } if (argc > 1) { mdb_warn("too many arguments\n"); return (DCMD_USAGE); } if (mdb_vread(&xr, sizeof (xr), addr) != sizeof (xr)) { mdb_warn("failed to read xhci_ring_t at %p", addr); return (DCMD_USAGE); } if (argv[0].a_type == MDB_TYPE_IMMEDIATE) { target = argv[0].a_un.a_val; } else if (argv[0].a_type == MDB_TYPE_STRING) { target = mdb_strtoull(argv[0].a_un.a_str); } else { mdb_warn("argument is an unknown supported type: %d\n", argv[0].a_type); return (DCMD_USAGE); } target = roundup(target, sizeof (xhci_trb_t)); base = xr.xr_dma.xdb_cookies[0].dmac_laddress; max = base + xr.xr_ntrb * sizeof (xhci_trb_t); if (target < base || target > max) { mdb_warn("target address %p is outside the range of PAs for " "TRBs in the ring [%p, %p)", target, base, max); return (DCMD_ERR); } target -= base; mdb_printf("0x%" PRIx64 "\n", target + (uintptr_t)xr.xr_trb); return (DCMD_OK); }
int rctl(uintptr_t addr, uint_t flags, int argc, const mdb_arg_t *argv) { rctl_t rctl; rctl_dict_entry_t dict; char name[256]; rctl_hndl_t hndl; if (!(flags & DCMD_ADDRSPEC)) return (DCMD_USAGE); if (mdb_vread(&rctl, sizeof (rctl_t), addr) == -1) { mdb_warn("failed to read rctl_t structure at %p", addr); return (DCMD_ERR); } if (argc != 0) { const mdb_arg_t *argp = &argv[0]; if (argp->a_type == MDB_TYPE_IMMEDIATE) hndl = (rctl_hndl_t)argp->a_un.a_val; else hndl = (rctl_hndl_t)mdb_strtoull(argp->a_un.a_str); if (rctl.rc_id != hndl) return (DCMD_OK); } if (mdb_vread(&dict, sizeof (rctl_dict_entry_t), (uintptr_t)rctl.rc_dict_entry) == -1) { mdb_warn("failed to read dict entry for rctl_t %p at %p", addr, rctl.rc_dict_entry); return (DCMD_ERR); } if (mdb_readstr(name, 256, (uintptr_t)(dict.rcd_name)) == -1) { mdb_warn("failed to read name for rctl_t %p", addr); return (DCMD_ERR); } mdb_printf("%0?p\t%3d : %s\n", addr, rctl.rc_id, name); if (mdb_pwalk("rctl_val", (mdb_walk_cb_t)print_val, &(rctl.rc_cursor), addr) == -1) { mdb_warn("failed to walk all values for rctl_t %p", addr); return (DCMD_ERR); } return (DCMD_OK); }
int sonode(uintptr_t addr, uint_t flags, int argc, const mdb_arg_t *argv) { const char *optf = NULL; const char *optt = NULL; const char *optp = NULL; int family, type, proto; int filter = 0; struct sonode so; if (!(flags & DCMD_ADDRSPEC)) { if (mdb_walk_dcmd("genunix`sonode", "genunix`sonode", argc, argv) == -1) { mdb_warn("failed to walk sonode"); return (DCMD_ERR); } return (DCMD_OK); } if (mdb_getopts(argc, argv, 'f', MDB_OPT_STR, &optf, 't', MDB_OPT_STR, &optt, 'p', MDB_OPT_STR, &optp, NULL) != argc) return (DCMD_USAGE); if (optf != NULL) { if (strcmp("inet", optf) == 0) family = AF_INET; else if (strcmp("inet6", optf) == 0) family = AF_INET6; else if (strcmp("unix", optf) == 0) family = AF_UNIX; else family = mdb_strtoull(optf); filter = 1; } if (optt != NULL) { if (strcmp("stream", optt) == 0) type = SOCK_STREAM; else if (strcmp("dgram", optt) == 0) type = SOCK_DGRAM; else if (strcmp("raw", optt) == 0) type = SOCK_RAW; else type = mdb_strtoull(optt); filter = 1; } if (optp != NULL) { proto = mdb_strtoull(optp); filter = 1; } if (DCMD_HDRSPEC(flags) && !filter) { mdb_printf("%<u>%-?s Family Type Proto State Mode Flag " "AccessVP%</u>\n", "Sonode:"); } if (mdb_vread(&so, sizeof (so), addr) == -1) { mdb_warn("failed to read sonode at %p", addr); return (DCMD_ERR); } if ((optf != NULL) && (so.so_family != family)) return (DCMD_OK); if ((optt != NULL) && (so.so_type != type)) return (DCMD_OK); if ((optp != NULL) && (so.so_protocol != proto)) return (DCMD_OK); if (filter) { mdb_printf("%0?p\n", addr); return (DCMD_OK); } mdb_printf("%0?p ", addr); switch (so.so_family) { case AF_UNIX: mdb_printf("unix "); break; case AF_INET: mdb_printf("inet "); break; case AF_INET6: mdb_printf("inet6 "); break; default: mdb_printf("%6hi", so.so_family); } switch (so.so_type) { case SOCK_STREAM: mdb_printf(" strm"); break; case SOCK_DGRAM: mdb_printf(" dgrm"); break; case SOCK_RAW: mdb_printf(" raw "); break; default: mdb_printf(" %4hi", so.so_type); } mdb_printf(" %5hi %05x %04x %04hx\n", so.so_protocol, so.so_state, so.so_mode, so.so_flag); return (DCMD_OK); }
int zsd(uintptr_t addr, uint_t flags, int argc, const mdb_arg_t *argv) { zone_t zone; const mdb_arg_t *argp; int argcindex; struct zsd_cb_data cbd; char name[ZONE_NAMELEN]; int len; /* * Walk all zones if necessary. */ if (argc > 2) return (DCMD_USAGE); if ((flags & DCMD_ADDRSPEC) == 0) { if (mdb_walk_dcmd("zone", "zsd", argc, argv) == -1) { mdb_warn("failed to walk zone\n"); return (DCMD_ERR); } return (DCMD_OK); } /* * Make sure a zone_t can be read from the specified address. */ if (mdb_vread(&zone, sizeof (zone), addr) == -1) { mdb_warn("couldn't read zone_t at %p", (void *)addr); return (DCMD_ERR); } /* * Get the optional arguments (key or -v or both). Note that * mdb_getopts() will not parse a key argument because it is not * preceded by an option letter. We'll get around this by requiring * that all options precede the optional key argument. */ cbd.keygiven = FALSE; cbd.voptgiven = FALSE; if (argc > 0 && (argcindex = mdb_getopts(argc, argv, 'v', MDB_OPT_SETBITS, TRUE, &cbd.voptgiven, NULL)) != argc) { /* * No options may appear after the key. */ if (argcindex != argc - 1) return (DCMD_USAGE); /* * The missed argument should be a key. */ argp = &argv[argcindex]; if (argp->a_type == MDB_TYPE_IMMEDIATE) cbd.key = argp->a_un.a_val; else cbd.key = mdb_strtoull(argp->a_un.a_str); cbd.keygiven = TRUE; cbd.found = FALSE; } /* * Prepare to output the specified zone's ZSD information. */ if (DCMD_HDRSPEC(flags)) mdb_printf("%<u>%-20s %?s %?s %8s%</u>\n", "ZONE", "KEY", "VALUE", "FLAGS"); len = mdb_readstr(name, ZONE_NAMELEN, (uintptr_t)zone.zone_name); if (len > 0) { if (len == ZONE_NAMELEN) (void) strcpy(&name[len - 4], "..."); } else { (void) strcpy(name, "??"); } mdb_printf("%-20s ", name); /* * Display the requested ZSD entries. */ mdb_inc_indent(21); if (mdb_pwalk("zsd", zsd_print, &cbd, addr) != 0) { mdb_warn("failed to walk zsd\n"); mdb_dec_indent(21); return (DCMD_ERR); } if (cbd.keygiven == TRUE && cbd.found == FALSE) { mdb_printf("no corresponding ZSD entry found\n"); mdb_dec_indent(21); return (DCMD_ERR); } mdb_dec_indent(21); return (DCMD_OK); }
/*ARGSUSED*/ int emlxs_msgbuf(uintptr_t base_addr, uint_t flags, int argc, const mdb_arg_t *argv) { uintptr_t addr; emlxs_device_t device; uint32_t brd_no; emlxs_msg_log_t log; uint32_t count; uint32_t first; uint32_t last; uint32_t idx; uint32_t i; char *level; emlxs_msg_t msg; char merge[1024]; emlxs_msg_entry_t entry; char buffer[256]; char buffer2[256]; int32_t instance[MAX_FC_BRDS]; char driver[32]; int32_t instance_count; uint32_t ddiinst; if (argc != 1) { mdb_printf("Usage: ::%s_msgbuf <instance(hex)>\n", DRIVER_NAME); mdb_printf("mdb: try \"::help %s_msgbuf\" for more information", DRIVER_NAME); return (DCMD_ERR); } /* Get the device address */ mdb_snprintf(buffer, sizeof (buffer), "%s_device", DRIVER_NAME); if (mdb_readvar(&device, buffer) == -1) { mdb_snprintf(buffer2, sizeof (buffer2), "%s not found.\n", buffer); mdb_warn(buffer2); mdb_snprintf(buffer2, sizeof (buffer2), "Is the %s driver loaded ?\n", DRIVER_NAME); mdb_warn(buffer2); return (DCMD_ERR); } /* Get the device instance table */ mdb_snprintf(buffer, sizeof (buffer), "%s_instance", DRIVER_NAME); if (mdb_readvar(&instance, buffer) == -1) { mdb_snprintf(buffer2, sizeof (buffer2), "%s not found.\n", buffer); mdb_warn(buffer2); mdb_snprintf(buffer2, sizeof (buffer2), "Is the %s driver loaded ?\n", DRIVER_NAME); mdb_warn(buffer2); return (DCMD_ERR); } /* Get the device instance count */ mdb_snprintf(buffer, sizeof (buffer), "%s_instance_count", DRIVER_NAME); if (mdb_readvar(&instance_count, buffer) == -1) { mdb_snprintf(buffer2, sizeof (buffer2), "%s not found.\n", buffer); mdb_warn(buffer2); mdb_snprintf(buffer2, sizeof (buffer2), "Is the %s driver loaded ?\n", DRIVER_NAME); mdb_warn(buffer2); return (DCMD_ERR); } ddiinst = (uint32_t)mdb_strtoull(argv[0].a_un.a_str); for (brd_no = 0; brd_no < instance_count; brd_no++) { if (instance[brd_no] == ddiinst) { break; } } if (brd_no == instance_count) { mdb_warn("Device instance not found. ddinst=%d\n", ddiinst); return (DCMD_ERR); } /* Check if buffer is null */ addr = (uintptr_t)device.log[brd_no]; if (addr == 0) { mdb_warn("Device instance not found. ddinst=%d\n", ddiinst); return (0); } if (mdb_vread(&log, sizeof (emlxs_msg_log_t), addr) != sizeof (emlxs_msg_log_t)) { mdb_warn("\nUnable to read %d bytes @ %llx.\n", sizeof (emlxs_msg_log_t), addr); return (0); } /* Check if buffer is empty */ if (log.count == 0) { mdb_warn("Log buffer empty.\n"); return (0); } /* Get last entry id saved */ last = log.count - 1; /* Check if buffer has already been filled once */ if (log.count >= log.size) { first = log.count - log.size; idx = log.next; } else { /* Buffer not yet filled */ first = 0; idx = 0; } /* Get the total number of messages available for return */ count = last - first + 1; mdb_printf("\n"); /* Print the messages */ for (i = 0; i < count; i++) { if (mdb_vread(&entry, sizeof (emlxs_msg_entry_t), (uintptr_t)&log.entry[idx]) != sizeof (emlxs_msg_entry_t)) { mdb_warn("Cannot read log entry. index=%d count=%d\n", idx, count); return (DCMD_ERR); } if (mdb_vread(&msg, sizeof (emlxs_msg_t), (uintptr_t)entry.msg) != sizeof (emlxs_msg_t)) { mdb_warn("Cannot read msg. index=%d count=%d\n", idx, count); return (DCMD_ERR); } switch (msg.level) { case EMLXS_DEBUG: level = " DEBUG"; break; case EMLXS_NOTICE: level = " NOTICE"; break; case EMLXS_WARNING: level = "WARNING"; break; case EMLXS_ERROR: level = " ERROR"; break; case EMLXS_PANIC: level = " PANIC"; break; default: level = "UNKNOWN"; break; } if (entry.vpi == 0) { mdb_snprintf(driver, sizeof (driver), "%s%d", DRIVER_NAME, entry.instance); } else { mdb_snprintf(driver, sizeof (driver), "%s%d.%d", DRIVER_NAME, entry.instance, entry.vpi); } /* Generate the message string */ if (msg.buffer[0] != 0) { if (entry.buffer[0] != 0) { mdb_snprintf(merge, sizeof (merge), "[%Y:%03d:%03d:%03d] " "%6d:[%1X.%04X]%s:%7s:%4d: %s\n(%s)\n", entry.id_time.tv_sec, (int)entry.id_time.tv_nsec/1000000, (int)(entry.id_time.tv_nsec/1000)%1000, (int)entry.id_time.tv_nsec%1000, entry.id, entry.fileno, entry.line, driver, level, msg.id, msg.buffer, entry.buffer); } else { mdb_snprintf(merge, sizeof (merge), "[%Y:%03d:%03d:%03d] " "%6d:[%1X.%04X]%s:%7s:%4d: %s\n", entry.id_time.tv_sec, (int)entry.id_time.tv_nsec/1000000, (int)(entry.id_time.tv_nsec/1000)%1000, (int)entry.id_time.tv_nsec%1000, entry.id, entry.fileno, entry.line, driver, level, msg.id, msg.buffer); } } else { if (entry.buffer[0] != 0) { mdb_snprintf(merge, sizeof (merge), "[%Y:%03d:%03d:%03d] " "%6d:[%1X.%04X]%s:%7s:%4d:\n(%s)\n", entry.id_time.tv_sec, (int)entry.id_time.tv_nsec/1000000, (int)(entry.id_time.tv_nsec/1000)%1000, (int)entry.id_time.tv_nsec%1000, entry.id, entry.fileno, entry.line, driver, level, msg.id, entry.buffer); } else { mdb_snprintf(merge, sizeof (merge), "[%Y:%03d:%03d:%03d] " "%6d:[%1X.%04X]%s:%7s:%4d: %s\n", entry.id_time.tv_sec, (int)entry.id_time.tv_nsec/1000000, (int)(entry.id_time.tv_nsec/1000)%1000, (int)entry.id_time.tv_nsec%1000, entry.id, entry.fileno, entry.line, driver, level, msg.id, msg.buffer); } } mdb_printf("%s", merge); /* Increment index */ if (++idx >= log.size) { idx = 0; } } mdb_printf("\n"); return (0); } /* emlxs_msgbuf() */
/*ARGSUSED*/ int emlxs_dump(uintptr_t base_addr, uint_t flags, int argc, const mdb_arg_t *argv) { uintptr_t addr; emlxs_device_t device; uint32_t brd_no; uint32_t i; char buffer[256]; char buffer2[256]; int32_t instance[MAX_FC_BRDS]; int32_t instance_count; uint32_t ddiinst; uint8_t *bptr; char *cptr; emlxs_file_t dump_txtfile; emlxs_file_t dump_dmpfile; emlxs_file_t dump_ceefile; uint32_t size; uint32_t file; if (argc != 2) { goto usage; } if ((strcmp(argv[0].a_un.a_str, "all") == 0) || (strcmp(argv[0].a_un.a_str, "ALL") == 0) || (strcmp(argv[0].a_un.a_str, "All") == 0)) { file = 0; } else if ((strcmp(argv[0].a_un.a_str, "txt") == 0) || (strcmp(argv[0].a_un.a_str, "TXT") == 0) || (strcmp(argv[0].a_un.a_str, "Txt") == 0)) { file = 1; } else if ((strcmp(argv[0].a_un.a_str, "dmp") == 0) || (strcmp(argv[0].a_un.a_str, "DMP") == 0) || (strcmp(argv[0].a_un.a_str, "Dmp") == 0)) { file = 2; } else if ((strcmp(argv[0].a_un.a_str, "cee") == 0) || (strcmp(argv[0].a_un.a_str, "CEE") == 0) || (strcmp(argv[0].a_un.a_str, "Cee") == 0)) { file = 3; } else { goto usage; } /* Get the device address */ mdb_snprintf(buffer, sizeof (buffer), "%s_device", DRIVER_NAME); if (mdb_readvar(&device, buffer) == -1) { mdb_snprintf(buffer2, sizeof (buffer2), "%s not found.\n", buffer); mdb_warn(buffer2); mdb_snprintf(buffer2, sizeof (buffer2), "Is the %s driver loaded ?\n", DRIVER_NAME); mdb_warn(buffer2); return (DCMD_ERR); } /* Get the device instance table */ mdb_snprintf(buffer, sizeof (buffer), "%s_instance", DRIVER_NAME); if (mdb_readvar(&instance, buffer) == -1) { mdb_snprintf(buffer2, sizeof (buffer2), "%s not found.\n", buffer); mdb_warn(buffer2); mdb_snprintf(buffer2, sizeof (buffer2), "Is the %s driver loaded ?\n", DRIVER_NAME); mdb_warn(buffer2); return (DCMD_ERR); } /* Get the device instance count */ mdb_snprintf(buffer, sizeof (buffer), "%s_instance_count", DRIVER_NAME); if (mdb_readvar(&instance_count, buffer) == -1) { mdb_snprintf(buffer2, sizeof (buffer2), "%s not found.\n", buffer); mdb_warn(buffer2); mdb_snprintf(buffer2, sizeof (buffer2), "Is the %s driver loaded ?\n", DRIVER_NAME); mdb_warn(buffer2); return (DCMD_ERR); } ddiinst = (uint32_t)mdb_strtoull(argv[1].a_un.a_str); for (brd_no = 0; brd_no < instance_count; brd_no++) { if (instance[brd_no] == ddiinst) { break; } } if (brd_no == instance_count) { mdb_warn("Device instance not found. ddinst=%d\n", ddiinst); return (DCMD_ERR); } if (file == 0 || file == 1) { addr = (uintptr_t)device.dump_txtfile[brd_no]; if (addr == 0) { mdb_warn("TXT file: Device instance not found. " \ "ddinst=%d\n", ddiinst); goto dmp_file; } if (mdb_vread(&dump_txtfile, sizeof (dump_txtfile), addr) != sizeof (dump_txtfile)) { mdb_warn("TXT file: Unable to read %d bytes @ %llx.\n", sizeof (dump_txtfile), addr); goto dmp_file; } size = (uintptr_t)dump_txtfile.ptr - (uintptr_t)dump_txtfile.buffer; if (size == 0) { mdb_printf("TXT file: Not available.\n"); goto dmp_file; } bptr = (uint8_t *)mdb_zalloc(size, UM_SLEEP|UM_GC); if (bptr == 0) { mdb_warn("TXT file: Unable to allocate file buffer. " \ "ddinst=%d size=%d\n", ddiinst, size); goto dmp_file; } if (mdb_vread(bptr, size, (uintptr_t)dump_txtfile.buffer) != size) { mdb_warn("TXT file: Unable to read %d bytes @ %llx.\n", size, dump_txtfile.buffer); goto dmp_file; } mdb_printf("<TXT File Start>\n"); mdb_printf("\n"); mdb_printf("%s", bptr); mdb_printf("\n"); mdb_printf("<TXT File End>\n"); } dmp_file: if (file == 0 || file == 2) { addr = (uintptr_t)device.dump_dmpfile[brd_no]; if (addr == 0) { mdb_warn("DMP file: Device instance not found. " \ "ddinst=%d\n", ddiinst); goto cee_file; } if (mdb_vread(&dump_dmpfile, sizeof (dump_dmpfile), addr) != sizeof (dump_dmpfile)) { mdb_warn("DMP file: Unable to read %d bytes @ %llx.\n", sizeof (dump_dmpfile), addr); goto cee_file; } size = (uintptr_t)dump_dmpfile.ptr - (uintptr_t)dump_dmpfile.buffer; if (size == 0) { mdb_printf("DMP file: Not available.\n"); goto cee_file; } bptr = (uint8_t *)mdb_zalloc(size, UM_SLEEP|UM_GC); if (bptr == 0) { mdb_warn("DMP file: Unable to allocate file buffer. " \ "ddinst=%d size=%d\n", ddiinst, size); goto cee_file; } if (mdb_vread(bptr, size, (uintptr_t)dump_dmpfile.buffer) != size) { mdb_warn("DMP file: Unable to read %d bytes @ %llx.\n", size, dump_dmpfile.buffer); goto cee_file; } mdb_printf("<DMP File Start>\n"); mdb_printf("\n"); bzero(buffer2, sizeof (buffer2)); cptr = buffer2; for (i = 0; i < size; i++) { if (i && !(i % 16)) { mdb_printf(" %s\n", buffer2); bzero(buffer2, sizeof (buffer2)); cptr = buffer2; } if (!(i % 16)) { mdb_printf("%08X: ", i); } if (!(i % 4)) { mdb_printf(" "); } if ((*bptr >= 32) && (*bptr <= 126)) { *cptr++ = *bptr; } else { *cptr++ = '.'; } mdb_printf("%02X ", *bptr++); } size = 16 - (i % 16); for (i = 0; size < 16 && i < size; i++) { if (!(i % 4)) { mdb_printf(" "); } mdb_printf(" "); } mdb_printf(" %s\n", buffer2); mdb_printf("\n"); mdb_printf("<DMP File End>\n"); } cee_file: if (file == 0 || file == 3) { addr = (uintptr_t)device.dump_ceefile[brd_no]; if (addr == 0) { mdb_warn("CEE file: Device instance not found. " \ "ddinst=%d\n", ddiinst); goto done; } if (mdb_vread(&dump_ceefile, sizeof (dump_ceefile), addr) != sizeof (dump_ceefile)) { mdb_warn("CEE file: Unable to read %d bytes @ %llx.\n", sizeof (dump_ceefile), addr); goto done; } size = (uintptr_t)dump_ceefile.ptr - (uintptr_t)dump_ceefile.buffer; if (size == 0) { mdb_printf("CEE file: Not available.\n"); goto done; } bptr = (uint8_t *)mdb_zalloc(size, UM_SLEEP|UM_GC); if (bptr == 0) { mdb_warn("CEE file: Unable to allocate file buffer. " \ "ddinst=%d size=%d\n", ddiinst, size); goto done; } if (mdb_vread(bptr, size, (uintptr_t)dump_ceefile.buffer) != size) { mdb_warn("CEE file: Unable to read %d bytes @ %llx.\n", size, dump_ceefile.buffer); goto done; } mdb_printf("<CEE File Start>\n"); mdb_printf("\n"); bzero(buffer2, sizeof (buffer2)); cptr = buffer2; for (i = 0; i < size; i++) { if (i && !(i % 16)) { mdb_printf(" %s\n", buffer2); bzero(buffer2, sizeof (buffer2)); cptr = buffer2; } if (!(i % 16)) { mdb_printf("%08X: ", i); } if (!(i % 4)) { mdb_printf(" "); } if ((*bptr >= 32) && (*bptr <= 126)) { *cptr++ = *bptr; } else { *cptr++ = '.'; } mdb_printf("%02X ", *bptr++); } size = 16 - (i % 16); for (i = 0; size < 16 && i < size; i++) { if (!(i % 4)) { mdb_printf(" "); } mdb_printf(" "); } mdb_printf(" %s\n", buffer2); mdb_printf("\n"); mdb_printf("<CEE File End>\n"); } done: mdb_printf("\n"); return (0); usage: mdb_printf("Usage: ::%s_dump <file> <instance (hex)>\n", DRIVER_NAME); mdb_printf("mdb: try \"::help %s_dump\" for more information", DRIVER_NAME); return (DCMD_ERR); } /* emlxs_dump() */
/* * Print out all project, task, and process rctls for a given process. * If a handle is specified, print only the rctl matching that handle * for the process. */ int rctl_list(uintptr_t addr, uint_t flags, int argc, const mdb_arg_t *argv) { proc_t proc; uintptr_t set; task_t task; kproject_t proj; zone_t zone; dict_data_t rdict; int i; rdict.dict_addr = NULL; if (!(flags & DCMD_ADDRSPEC)) return (DCMD_USAGE); if (argc == 0) rdict.hndl = 0; else if (argc == 1) { /* * User specified a handle. Go find the rctl_dict_entity_t * structure so we know what type of rctl to look for. */ const mdb_arg_t *argp = &argv[0]; if (argp->a_type == MDB_TYPE_IMMEDIATE) rdict.hndl = (rctl_hndl_t)argp->a_un.a_val; else rdict.hndl = (rctl_hndl_t)mdb_strtoull(argp->a_un.a_str); if (mdb_walk("rctl_dict_list", (mdb_walk_cb_t)hndl2dict, &rdict) == -1) { mdb_warn("failed to walk rctl_dict_list"); return (DCMD_ERR); } /* Couldn't find a rctl_dict_entry_t for this handle */ if (rdict.dict_addr == NULL) return (DCMD_ERR); } else return (DCMD_USAGE); if (mdb_vread(&proc, sizeof (proc_t), addr) == -1) { mdb_warn("failed to read proc at %p", addr); return (DCMD_ERR); } if (mdb_vread(&zone, sizeof (zone_t), (uintptr_t)proc.p_zone) == -1) { mdb_warn("failed to read zone at %p", proc.p_zone); return (DCMD_ERR); } if (mdb_vread(&task, sizeof (task_t), (uintptr_t)proc.p_task) == -1) { mdb_warn("failed to read task at %p", proc.p_task); return (DCMD_ERR); } if (mdb_vread(&proj, sizeof (kproject_t), (uintptr_t)task.tk_proj) == -1) { mdb_warn("failed to read proj at %p", task.tk_proj); return (DCMD_ERR); } for (i = 0; i <= RC_MAX_ENTITY; i++) { /* * If user didn't specify a handle, print rctls for all * types. Otherwise, we can walk the rctl_set for only the * entity specified by the handle. */ if (rdict.hndl != 0 && rdict.type != i) continue; switch (i) { case (RCENTITY_PROCESS): set = (uintptr_t)proc.p_rctls; break; case (RCENTITY_TASK): set = (uintptr_t)task.tk_rctls; break; case (RCENTITY_PROJECT): set = (uintptr_t)proj.kpj_rctls; break; case (RCENTITY_ZONE): set = (uintptr_t)zone.zone_rctls; break; default: mdb_warn("Unknown rctl type %d", i); return (DCMD_ERR); } if (mdb_pwalk_dcmd("rctl_set", "rctl", argc, argv, set) == -1) { mdb_warn("failed to walk rctls in set %p", set); return (DCMD_ERR); } } return (DCMD_OK); }