1a6d42e7dSPeter Dunlap /* 2a6d42e7dSPeter Dunlap * CDDL HEADER START 3a6d42e7dSPeter Dunlap * 4a6d42e7dSPeter Dunlap * The contents of this file are subject to the terms of the 5a6d42e7dSPeter Dunlap * Common Development and Distribution License (the "License"). 6a6d42e7dSPeter Dunlap * You may not use this file except in compliance with the License. 7a6d42e7dSPeter Dunlap * 8a6d42e7dSPeter Dunlap * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE 9a6d42e7dSPeter Dunlap * or http://www.opensolaris.org/os/licensing. 10a6d42e7dSPeter Dunlap * See the License for the specific language governing permissions 11a6d42e7dSPeter Dunlap * and limitations under the License. 12a6d42e7dSPeter Dunlap * 13a6d42e7dSPeter Dunlap * When distributing Covered Code, include this CDDL HEADER in each 14a6d42e7dSPeter Dunlap * file and include the License file at usr/src/OPENSOLARIS.LICENSE. 15a6d42e7dSPeter Dunlap * If applicable, add the following below this CDDL HEADER, with the 16a6d42e7dSPeter Dunlap * fields enclosed by brackets "[]" replaced with your own identifying 17a6d42e7dSPeter Dunlap * information: Portions Copyright [yyyy] [name of copyright owner] 18a6d42e7dSPeter Dunlap * 19a6d42e7dSPeter Dunlap * CDDL HEADER END 20a6d42e7dSPeter Dunlap */ 21a6d42e7dSPeter Dunlap /* 2230e7468fSPeter Dunlap * Copyright 2009 Sun Microsystems, Inc. All rights reserved. 23a6d42e7dSPeter Dunlap * Use is subject to license terms. 24a6d42e7dSPeter Dunlap */ 25a6d42e7dSPeter Dunlap 26a6d42e7dSPeter Dunlap #include <sys/mdb_modapi.h> 27a6d42e7dSPeter Dunlap #include <sys/cpuvar.h> 28a6d42e7dSPeter Dunlap #include <sys/conf.h> 29a6d42e7dSPeter Dunlap #include <sys/file.h> 30a6d42e7dSPeter Dunlap #include <sys/types.h> 31a6d42e7dSPeter Dunlap #include <sys/taskq.h> 32a6d42e7dSPeter Dunlap #include <sys/sysmacros.h> 33a6d42e7dSPeter Dunlap #include <sys/socket.h> /* networking stuff */ 34a6d42e7dSPeter Dunlap #include <sys/strsubr.h> /* networking stuff */ 35a6d42e7dSPeter Dunlap #include <sys/nvpair.h> 36a6d42e7dSPeter Dunlap #include <sys/sunldi.h> 37a6d42e7dSPeter Dunlap #include <sys/stmf.h> 38a6d42e7dSPeter Dunlap #include <sys/stmf_ioctl.h> 39a6d42e7dSPeter Dunlap #include <sys/portif.h> 40a6d42e7dSPeter Dunlap 41a6d42e7dSPeter Dunlap #define IDM_CONN_SM_STRINGS 42bf604c64SPeter Dunlap #define IDM_TASK_SM_STRINGS 43a6d42e7dSPeter Dunlap #define ISCSIT_TGT_SM_STRINGS 44a6d42e7dSPeter Dunlap #define ISCSIT_SESS_SM_STRINGS 45a6d42e7dSPeter Dunlap #define ISCSIT_LOGIN_SM_STRINGS 4630e7468fSPeter Dunlap #define ISCSI_SESS_SM_STRINGS 4730e7468fSPeter Dunlap #define ISCSI_CMD_SM_STRINGS 4830e7468fSPeter Dunlap #define ISCSI_ICS_NAMES 4930e7468fSPeter Dunlap #define ISCSI_LOGIN_STATE_NAMES 50a6d42e7dSPeter Dunlap #include <sys/idm/idm.h> 51*aff4bce5Syi zhang - Sun Microsystems - Beijing China #include <iscsi.h> 52a6d42e7dSPeter Dunlap #include <iscsit.h> 53a6d42e7dSPeter Dunlap #include <iscsit_isns.h> 54a6d42e7dSPeter Dunlap 55a6d42e7dSPeter Dunlap /* 56a6d42e7dSPeter Dunlap * We want to be able to print multiple levels of object hierarchy with a 57a6d42e7dSPeter Dunlap * single dcmd information, and preferably also exclude intermediate 58a6d42e7dSPeter Dunlap * levels if desired. For example some of the target objects have the 59a6d42e7dSPeter Dunlap * following relationship: 60a6d42e7dSPeter Dunlap * 61a6d42e7dSPeter Dunlap * target --> session --> connection --> task 62a6d42e7dSPeter Dunlap * 63a6d42e7dSPeter Dunlap * The session dcmd should allow the printing of all associated tasks for the 64a6d42e7dSPeter Dunlap * sessions without printing all the associated connections. To accomplish 65a6d42e7dSPeter Dunlap * this the following structure contains a bit for each object type. Dcmds 66a6d42e7dSPeter Dunlap * should invoked the functions for child objects if any bits are set 67a6d42e7dSPeter Dunlap * in iscsi_dcmd_ctrl_t but the functions for the child object should only 68a6d42e7dSPeter Dunlap * print data if their associated bit is set. 69a6d42e7dSPeter Dunlap * 70a6d42e7dSPeter Dunlap * Each dcmd should provide an external interface with the standard MDB API 71a6d42e7dSPeter Dunlap * and an internal interface that accepts iscsi_dcmd_ctrl_t. To display 72a6d42e7dSPeter Dunlap * child objects the dcmd calls the internal interface for the child object 73a6d42e7dSPeter Dunlap * directly. Dcmds invoked from the command line will, of course, call the 74a6d42e7dSPeter Dunlap * external interface. See iscsi_conn() and iscsi_conn_impl(). 75a6d42e7dSPeter Dunlap */ 76a6d42e7dSPeter Dunlap 77a6d42e7dSPeter Dunlap typedef struct { 78a6d42e7dSPeter Dunlap union { 79a6d42e7dSPeter Dunlap uint32_t idc_children; 80a6d42e7dSPeter Dunlap struct { 81a6d42e7dSPeter Dunlap uint32_t idc_tgt:1, 82a6d42e7dSPeter Dunlap idc_tpgt:1, 83a6d42e7dSPeter Dunlap idc_portal:1, 84a6d42e7dSPeter Dunlap idc_sess:1, 85a6d42e7dSPeter Dunlap idc_conn:1, 86a6d42e7dSPeter Dunlap idc_print_ip:1, 87a6d42e7dSPeter Dunlap idc_task:1, 88a6d42e7dSPeter Dunlap idc_buffer:1, 89a6d42e7dSPeter Dunlap idc_states:1, 90a6d42e7dSPeter Dunlap idc_rc_audit:1, 91a6d42e7dSPeter Dunlap idc_lun:1, 92a6d42e7dSPeter Dunlap idc_hba:1; 93a6d42e7dSPeter Dunlap } child; 94a6d42e7dSPeter Dunlap } u; 95a6d42e7dSPeter Dunlap boolean_t idc_ini; 96a6d42e7dSPeter Dunlap boolean_t idc_tgt; 97a6d42e7dSPeter Dunlap boolean_t idc_verbose; 98a6d42e7dSPeter Dunlap boolean_t idc_header; 99a6d42e7dSPeter Dunlap /* 100a6d42e7dSPeter Dunlap * Our connection dcmd code works off the global connection lists 101a6d42e7dSPeter Dunlap * in IDM since we want to know about connections even when they 102a6d42e7dSPeter Dunlap * have not progressed to the point that they have an associated 103a6d42e7dSPeter Dunlap * session. If we use "::iscsi_sess [-c]" then we only want to 104a6d42e7dSPeter Dunlap * see connections associated with particular session. To avoid 105a6d42e7dSPeter Dunlap * writing a separate set of code to print session-specific connection 106a6d42e7dSPeter Dunlap * the session code should set the sessions kernel address in the 107a6d42e7dSPeter Dunlap * following field. The connection code will then only print 108a6d42e7dSPeter Dunlap * connections that match. 109a6d42e7dSPeter Dunlap */ 110a6d42e7dSPeter Dunlap uintptr_t idc_assoc_session; 111a6d42e7dSPeter Dunlap } iscsi_dcmd_ctrl_t; 112a6d42e7dSPeter Dunlap 113a6d42e7dSPeter Dunlap static int iscsi_walk_all_sess(iscsi_dcmd_ctrl_t *idc); 11430e7468fSPeter Dunlap static int iscsi_walk_ini_sessions(uintptr_t array_addr); 115a6d42e7dSPeter Dunlap static int iscsi_walk_all_conn(iscsi_dcmd_ctrl_t *idc); 116a6d42e7dSPeter Dunlap static int iscsi_tgt_walk_cb(uintptr_t addr, const void *list_walker_data, 117a6d42e7dSPeter Dunlap void *idc_void); 118a6d42e7dSPeter Dunlap static int iscsi_tpgt_walk_cb(uintptr_t addr, const void *list_walker_data, 119a6d42e7dSPeter Dunlap void *idc_void); 120a6d42e7dSPeter Dunlap static int iscsi_tpg_walk_cb(uintptr_t addr, const void *list_walker_data, 121a6d42e7dSPeter Dunlap void *idc_void); 122a6d42e7dSPeter Dunlap static int iscsi_portal_walk_cb(uintptr_t addr, const void *list_walker_data, 123a6d42e7dSPeter Dunlap void *idc_void); 124a6d42e7dSPeter Dunlap static int iscsi_sess_walk_cb(uintptr_t addr, const void *list_walker_data, 125a6d42e7dSPeter Dunlap void *idc_void); 126a6d42e7dSPeter Dunlap static int iscsi_conn_walk_cb(uintptr_t addr, const void *list_walker_data, 127a6d42e7dSPeter Dunlap void *idc_void); 128a6d42e7dSPeter Dunlap static int iscsi_buffer_walk_cb(uintptr_t addr, const void *list_walker_data, 129a6d42e7dSPeter Dunlap void *idc_void); 130a6d42e7dSPeter Dunlap static int iscsi_tgt_impl(uintptr_t addr, iscsi_dcmd_ctrl_t *idc); 131a6d42e7dSPeter Dunlap static int iscsi_tpgt_impl(uintptr_t addr, iscsi_dcmd_ctrl_t *idc); 132a6d42e7dSPeter Dunlap static int iscsi_tpg_impl(uintptr_t addr, iscsi_dcmd_ctrl_t *idc); 133a6d42e7dSPeter Dunlap static int iscsi_portal_impl(uintptr_t addr, iscsi_dcmd_ctrl_t *idc); 134a6d42e7dSPeter Dunlap static int iscsi_sess_impl(uintptr_t addr, iscsi_dcmd_ctrl_t *idc); 135a6d42e7dSPeter Dunlap static int iscsi_conn_impl(uintptr_t addr, iscsi_dcmd_ctrl_t *idc); 136a6d42e7dSPeter Dunlap static void iscsi_print_iscsit_conn_data(idm_conn_t *ict); 137a6d42e7dSPeter Dunlap static void iscsi_print_idm_conn_data(idm_conn_t *ict); 138a6d42e7dSPeter Dunlap static int iscsi_task_impl(uintptr_t addr, iscsi_dcmd_ctrl_t *idc); 139a6d42e7dSPeter Dunlap static void iscsi_print_iscsit_task_data(idm_task_t *idt); 140a6d42e7dSPeter Dunlap static int iscsi_buffer_impl(uintptr_t addr, iscsi_dcmd_ctrl_t *idc); 141a6d42e7dSPeter Dunlap static idm_conn_type_t idm_conn_type(uintptr_t addr); 142a6d42e7dSPeter Dunlap static int iscsi_i_task_impl(idm_task_t *idt, uintptr_t addr, 143a6d42e7dSPeter Dunlap iscsi_dcmd_ctrl_t *idc); 144a6d42e7dSPeter Dunlap static int iscsi_refcnt_impl(uintptr_t addr); 145a6d42e7dSPeter Dunlap static int iscsi_sm_audit_impl(uintptr_t addr); 146a6d42e7dSPeter Dunlap static int iscsi_isns(uintptr_t addr, uint_t flags, int argc, 147a6d42e7dSPeter Dunlap const mdb_arg_t *argv); 148a6d42e7dSPeter Dunlap 14930e7468fSPeter Dunlap static const char *iscsi_idm_conn_event(unsigned int event); 15030e7468fSPeter Dunlap static const char *iscsi_iscsit_tgt_event(unsigned int event); 15130e7468fSPeter Dunlap static const char *iscsi_iscsit_sess_event(unsigned int event); 15230e7468fSPeter Dunlap static const char *iscsi_iscsit_login_event(unsigned int event); 15330e7468fSPeter Dunlap static const char *iscsi_iscsi_cmd_event(unsigned int event); 15430e7468fSPeter Dunlap static const char *iscsi_iscsi_sess_event(unsigned int event); 15530e7468fSPeter Dunlap static const char *iscsi_idm_conn_state(unsigned int state); 15630e7468fSPeter Dunlap static const char *iscsi_idm_task_state(unsigned int state); 15730e7468fSPeter Dunlap static const char *iscsi_iscsit_tgt_state(unsigned int state); 15830e7468fSPeter Dunlap static const char *iscsi_iscsit_sess_state(unsigned int state); 15930e7468fSPeter Dunlap static const char *iscsi_iscsit_login_state(unsigned int state); 16030e7468fSPeter Dunlap static const char *iscsi_iscsi_cmd_state(unsigned int state); 16130e7468fSPeter Dunlap static const char *iscsi_iscsi_sess_state(unsigned int state); 16230e7468fSPeter Dunlap static const char *iscsi_iscsi_conn_state(unsigned int state); 16330e7468fSPeter Dunlap static const char *iscsi_iscsi_login_state(unsigned int state); 164a6d42e7dSPeter Dunlap 165a6d42e7dSPeter Dunlap static void iscsi_format_timestamp(char *ts_str, int strlen, 166a6d42e7dSPeter Dunlap timespec_t *ts); 16730e7468fSPeter Dunlap static char *iscsi_inet_ntop(int af, const void *addr, char *buf, int addrlen); 168a6d42e7dSPeter Dunlap static void convert2ascii(char *, const in6_addr_t *); 169a6d42e7dSPeter Dunlap static int sa_to_str(struct sockaddr_storage *sa, char *addr); 170e42a0851Speter dunlap static int iscsi_isns_esi_cb(uintptr_t addr, const void *walker_data, 171e42a0851Speter dunlap void *data); 172a6d42e7dSPeter Dunlap static int iscsi_isns_portal_cb(uintptr_t addr, const void *walker_data, 173a6d42e7dSPeter Dunlap void *data); 174a6d42e7dSPeter Dunlap 175a6d42e7dSPeter Dunlap #define PORTAL_STR_LEN (INET6_ADDRSTRLEN + 7) 176a6d42e7dSPeter Dunlap 177a6d42e7dSPeter Dunlap /* 178a6d42e7dSPeter Dunlap * ::iscsi_tgt [-scatgpbSRv] 179a6d42e7dSPeter Dunlap * 180a6d42e7dSPeter Dunlap * iscsi_tgt - Print out information associated with an iscsit target instance 181a6d42e7dSPeter Dunlap * 182a6d42e7dSPeter Dunlap * s Print associated session information 183a6d42e7dSPeter Dunlap * c Print associated connection information 184a6d42e7dSPeter Dunlap * a Print IP addresses with connection information 185a6d42e7dSPeter Dunlap * t Print associated task information 186a6d42e7dSPeter Dunlap * g Print associated TPG information 187a6d42e7dSPeter Dunlap * p Print portals with TPG information 188a6d42e7dSPeter Dunlap * b Print associated buffer information 189a6d42e7dSPeter Dunlap * S Print recent state events and transitions 190a6d42e7dSPeter Dunlap * R Print reference count audit data 191a6d42e7dSPeter Dunlap * v Verbose output about the connection 192a6d42e7dSPeter Dunlap */ 193a6d42e7dSPeter Dunlap /*ARGSUSED*/ 194a6d42e7dSPeter Dunlap static int 195a6d42e7dSPeter Dunlap iscsi_tgt(uintptr_t addr, uint_t flags, int argc, const mdb_arg_t *argv) 196a6d42e7dSPeter Dunlap { 197a6d42e7dSPeter Dunlap iscsi_dcmd_ctrl_t idc; 198a6d42e7dSPeter Dunlap int buffer = 0, task = 0, print_ip = 0; 199a6d42e7dSPeter Dunlap int tpgt = 0, conn = 0, sess = 0, portal = 0; 200a6d42e7dSPeter Dunlap int states = 0, rc_audit = 0; 201a6d42e7dSPeter Dunlap uintptr_t iscsit_global_addr, avl_addr, list_addr; 202a6d42e7dSPeter Dunlap GElf_Sym sym; 203a6d42e7dSPeter Dunlap 204a6d42e7dSPeter Dunlap bzero(&idc, sizeof (idc)); 205a6d42e7dSPeter Dunlap if (mdb_getopts(argc, argv, 206a6d42e7dSPeter Dunlap 'a', MDB_OPT_SETBITS, TRUE, &print_ip, 207a6d42e7dSPeter Dunlap 'g', MDB_OPT_SETBITS, TRUE, &tpgt, 208a6d42e7dSPeter Dunlap 's', MDB_OPT_SETBITS, TRUE, &sess, 209a6d42e7dSPeter Dunlap 'c', MDB_OPT_SETBITS, TRUE, &conn, 210a6d42e7dSPeter Dunlap 't', MDB_OPT_SETBITS, TRUE, &task, 211a6d42e7dSPeter Dunlap 'b', MDB_OPT_SETBITS, TRUE, &buffer, 212a6d42e7dSPeter Dunlap 'p', MDB_OPT_SETBITS, TRUE, &portal, 213a6d42e7dSPeter Dunlap 'S', MDB_OPT_SETBITS, TRUE, &states, 214a6d42e7dSPeter Dunlap 'R', MDB_OPT_SETBITS, TRUE, &rc_audit, 215a6d42e7dSPeter Dunlap 'v', MDB_OPT_SETBITS, TRUE, &idc.idc_verbose, 216a6d42e7dSPeter Dunlap NULL) != argc) 217a6d42e7dSPeter Dunlap return (DCMD_USAGE); 218a6d42e7dSPeter Dunlap 219a6d42e7dSPeter Dunlap idc.u.child.idc_tgt = 1; 220a6d42e7dSPeter Dunlap idc.u.child.idc_print_ip = print_ip; 221a6d42e7dSPeter Dunlap idc.u.child.idc_tpgt = tpgt; 222a6d42e7dSPeter Dunlap idc.u.child.idc_portal = portal; 223a6d42e7dSPeter Dunlap idc.u.child.idc_sess = sess; 224a6d42e7dSPeter Dunlap idc.u.child.idc_conn = conn; 225a6d42e7dSPeter Dunlap idc.u.child.idc_task = task; 226a6d42e7dSPeter Dunlap idc.u.child.idc_buffer = buffer; 227a6d42e7dSPeter Dunlap idc.u.child.idc_states = states; 228a6d42e7dSPeter Dunlap idc.u.child.idc_rc_audit = rc_audit; 229a6d42e7dSPeter Dunlap 230a6d42e7dSPeter Dunlap if (DCMD_HDRSPEC(flags)) 231a6d42e7dSPeter Dunlap idc.idc_header = 1; 232a6d42e7dSPeter Dunlap 233a6d42e7dSPeter Dunlap /* 234a6d42e7dSPeter Dunlap * If no address was specified on the command line, we 235a6d42e7dSPeter Dunlap * print out all tgtions 236a6d42e7dSPeter Dunlap */ 237a6d42e7dSPeter Dunlap if (!(flags & DCMD_ADDRSPEC)) { 238a6d42e7dSPeter Dunlap if (mdb_lookup_by_name("iscsit_global", &sym) == -1) { 239a6d42e7dSPeter Dunlap mdb_warn("failed to find symbol 'iscsit_global'"); 240a6d42e7dSPeter Dunlap return (DCMD_ERR); 241a6d42e7dSPeter Dunlap } 242a6d42e7dSPeter Dunlap iscsit_global_addr = (uintptr_t)sym.st_value; 243a6d42e7dSPeter Dunlap avl_addr = iscsit_global_addr + 244a6d42e7dSPeter Dunlap offsetof(iscsit_global_t, global_target_list); 245a6d42e7dSPeter Dunlap if (mdb_pwalk("avl", iscsi_tgt_walk_cb, &idc, avl_addr) == -1) { 246a6d42e7dSPeter Dunlap mdb_warn("avl walk failed for global target tree"); 247a6d42e7dSPeter Dunlap return (DCMD_ERR); 248a6d42e7dSPeter Dunlap } 249a6d42e7dSPeter Dunlap list_addr = iscsit_global_addr + 250a6d42e7dSPeter Dunlap offsetof(iscsit_global_t, global_deleted_target_list); 251a6d42e7dSPeter Dunlap if (mdb_pwalk("list", iscsi_tgt_walk_cb, 252a6d42e7dSPeter Dunlap &idc, list_addr) == -1) { 253a6d42e7dSPeter Dunlap mdb_warn("list walk failed for deleted target list"); 254a6d42e7dSPeter Dunlap return (DCMD_ERR); 255a6d42e7dSPeter Dunlap } 256a6d42e7dSPeter Dunlap return (DCMD_OK); 257a6d42e7dSPeter Dunlap } else { 258a6d42e7dSPeter Dunlap return (iscsi_tgt_impl(addr, &idc)); 259a6d42e7dSPeter Dunlap } 260a6d42e7dSPeter Dunlap /*NOTREACHED*/ 261a6d42e7dSPeter Dunlap } 262a6d42e7dSPeter Dunlap 263a6d42e7dSPeter Dunlap static int 264a6d42e7dSPeter Dunlap iscsi_tpg(uintptr_t addr, uint_t flags, int argc, const mdb_arg_t *argv) 265a6d42e7dSPeter Dunlap { 266a6d42e7dSPeter Dunlap iscsi_dcmd_ctrl_t idc; 267a6d42e7dSPeter Dunlap uintptr_t iscsit_global_addr, avl_addr; 268a6d42e7dSPeter Dunlap GElf_Sym sym; 269a6d42e7dSPeter Dunlap 270a6d42e7dSPeter Dunlap bzero(&idc, sizeof (idc)); 271a6d42e7dSPeter Dunlap if (mdb_getopts(argc, argv, 272a6d42e7dSPeter Dunlap 'v', MDB_OPT_SETBITS, TRUE, &idc.idc_verbose, 273a6d42e7dSPeter Dunlap NULL) != argc) 274a6d42e7dSPeter Dunlap return (DCMD_USAGE); 275a6d42e7dSPeter Dunlap 276a6d42e7dSPeter Dunlap idc.u.child.idc_portal = 1; /* Always print portals */ 277a6d42e7dSPeter Dunlap if (DCMD_HDRSPEC(flags)) 278a6d42e7dSPeter Dunlap idc.idc_header = 1; 279a6d42e7dSPeter Dunlap 280a6d42e7dSPeter Dunlap /* 281a6d42e7dSPeter Dunlap * If no address was specified on the command line, we 282a6d42e7dSPeter Dunlap * print out all tgtions 283a6d42e7dSPeter Dunlap */ 284a6d42e7dSPeter Dunlap if (!(flags & DCMD_ADDRSPEC)) { 285a6d42e7dSPeter Dunlap if (mdb_lookup_by_name("iscsit_global", &sym) == -1) { 286a6d42e7dSPeter Dunlap mdb_warn("failed to find symbol 'iscsit_global'"); 287a6d42e7dSPeter Dunlap return (DCMD_ERR); 288a6d42e7dSPeter Dunlap } 289a6d42e7dSPeter Dunlap iscsit_global_addr = (uintptr_t)sym.st_value; 290a6d42e7dSPeter Dunlap avl_addr = iscsit_global_addr + 291a6d42e7dSPeter Dunlap offsetof(iscsit_global_t, global_tpg_list); 292a6d42e7dSPeter Dunlap if (mdb_pwalk("avl", iscsi_tpg_walk_cb, &idc, avl_addr) == -1) { 293a6d42e7dSPeter Dunlap mdb_warn("avl walk failed for global target tree"); 294a6d42e7dSPeter Dunlap return (DCMD_ERR); 295a6d42e7dSPeter Dunlap } 296a6d42e7dSPeter Dunlap return (DCMD_OK); 297a6d42e7dSPeter Dunlap } else { 298a6d42e7dSPeter Dunlap return (iscsi_tpg_impl(addr, &idc)); 299a6d42e7dSPeter Dunlap } 300a6d42e7dSPeter Dunlap /*NOTREACHED*/ 301a6d42e7dSPeter Dunlap } 302a6d42e7dSPeter Dunlap 303a6d42e7dSPeter Dunlap /* 304a6d42e7dSPeter Dunlap * ::iscsi_sess [-bctvIT] 305a6d42e7dSPeter Dunlap * 306a6d42e7dSPeter Dunlap * iscsi_sess - Print out information associated with an iSCSI session 307a6d42e7dSPeter Dunlap * 308a6d42e7dSPeter Dunlap * I Print only initiator sessions 309a6d42e7dSPeter Dunlap * T Print only target sessions 310a6d42e7dSPeter Dunlap * c Print associated connection information 311a6d42e7dSPeter Dunlap * a Print IP addresses with connection information 312a6d42e7dSPeter Dunlap * t Print associated task information 313a6d42e7dSPeter Dunlap * b Print associated buffer information 314a6d42e7dSPeter Dunlap * S Print recent state events and transitions 315a6d42e7dSPeter Dunlap * R Print reference count audit data 316a6d42e7dSPeter Dunlap * v Verbose output about the connection 317a6d42e7dSPeter Dunlap */ 318a6d42e7dSPeter Dunlap /*ARGSUSED*/ 319a6d42e7dSPeter Dunlap static int 320a6d42e7dSPeter Dunlap iscsi_sess(uintptr_t addr, uint_t flags, int argc, const mdb_arg_t *argv) 321a6d42e7dSPeter Dunlap { 322a6d42e7dSPeter Dunlap iscsi_dcmd_ctrl_t idc; 323a6d42e7dSPeter Dunlap int buffer = 0, task = 0, conn = 0, print_ip = 0; 324a6d42e7dSPeter Dunlap int states = 0, rc_audit = 0; 325a6d42e7dSPeter Dunlap 326a6d42e7dSPeter Dunlap bzero(&idc, sizeof (idc)); 327a6d42e7dSPeter Dunlap if (mdb_getopts(argc, argv, 328a6d42e7dSPeter Dunlap 'I', MDB_OPT_SETBITS, TRUE, &idc.idc_ini, 329a6d42e7dSPeter Dunlap 'T', MDB_OPT_SETBITS, TRUE, &idc.idc_tgt, 330a6d42e7dSPeter Dunlap 'a', MDB_OPT_SETBITS, TRUE, &print_ip, 331a6d42e7dSPeter Dunlap 'c', MDB_OPT_SETBITS, TRUE, &conn, 332a6d42e7dSPeter Dunlap 't', MDB_OPT_SETBITS, TRUE, &task, 333a6d42e7dSPeter Dunlap 'b', MDB_OPT_SETBITS, TRUE, &buffer, 334a6d42e7dSPeter Dunlap 'S', MDB_OPT_SETBITS, TRUE, &states, 335a6d42e7dSPeter Dunlap 'R', MDB_OPT_SETBITS, TRUE, &rc_audit, 336a6d42e7dSPeter Dunlap 'v', MDB_OPT_SETBITS, TRUE, &idc.idc_verbose, 337a6d42e7dSPeter Dunlap NULL) != argc) 338a6d42e7dSPeter Dunlap return (DCMD_USAGE); 339a6d42e7dSPeter Dunlap 340a6d42e7dSPeter Dunlap idc.u.child.idc_sess = 1; 341a6d42e7dSPeter Dunlap idc.u.child.idc_print_ip = print_ip; 342a6d42e7dSPeter Dunlap idc.u.child.idc_conn = conn; 343a6d42e7dSPeter Dunlap idc.u.child.idc_task = task; 344a6d42e7dSPeter Dunlap idc.u.child.idc_buffer = buffer; 345a6d42e7dSPeter Dunlap idc.u.child.idc_states = states; 346a6d42e7dSPeter Dunlap idc.u.child.idc_rc_audit = rc_audit; 347a6d42e7dSPeter Dunlap if (DCMD_HDRSPEC(flags)) 348a6d42e7dSPeter Dunlap idc.idc_header = 1; 349a6d42e7dSPeter Dunlap 350a6d42e7dSPeter Dunlap /* 351a6d42e7dSPeter Dunlap * If no address was specified on the command line, we 352a6d42e7dSPeter Dunlap * print out all sessions 353a6d42e7dSPeter Dunlap */ 354a6d42e7dSPeter Dunlap if (!(flags & DCMD_ADDRSPEC)) { 355a6d42e7dSPeter Dunlap return (iscsi_walk_all_sess(&idc)); 356a6d42e7dSPeter Dunlap } else { 357a6d42e7dSPeter Dunlap return (iscsi_sess_impl(addr, &idc)); 358a6d42e7dSPeter Dunlap } 359a6d42e7dSPeter Dunlap /*NOTREACHED*/ 360a6d42e7dSPeter Dunlap } 361a6d42e7dSPeter Dunlap 362a6d42e7dSPeter Dunlap 363a6d42e7dSPeter Dunlap 364a6d42e7dSPeter Dunlap /* 365a6d42e7dSPeter Dunlap * ::iscsi_conn [-btvIT] 366a6d42e7dSPeter Dunlap * 367a6d42e7dSPeter Dunlap * iscsi_conn - Print out information associated with an iSCSI connection 368a6d42e7dSPeter Dunlap * 369a6d42e7dSPeter Dunlap * I Print only initiator connections 370a6d42e7dSPeter Dunlap * T Print only target connections 371a6d42e7dSPeter Dunlap * a Print IP addresses with connection information 372a6d42e7dSPeter Dunlap * t Print associated task information 373a6d42e7dSPeter Dunlap * b Print associated buffer information 374a6d42e7dSPeter Dunlap * S Print recent state events and transitions 375a6d42e7dSPeter Dunlap * R Print reference count audit data 376a6d42e7dSPeter Dunlap * v Verbose output about the connection 377a6d42e7dSPeter Dunlap */ 378a6d42e7dSPeter Dunlap /*ARGSUSED*/ 379a6d42e7dSPeter Dunlap static int 380a6d42e7dSPeter Dunlap iscsi_conn(uintptr_t addr, uint_t flags, int argc, const mdb_arg_t *argv) 381a6d42e7dSPeter Dunlap { 382a6d42e7dSPeter Dunlap iscsi_dcmd_ctrl_t idc; 383a6d42e7dSPeter Dunlap int buffer = 0, task = 0, print_ip = 0; 384a6d42e7dSPeter Dunlap int states = 0, rc_audit = 0; 385a6d42e7dSPeter Dunlap 386a6d42e7dSPeter Dunlap bzero(&idc, sizeof (idc)); 387a6d42e7dSPeter Dunlap if (mdb_getopts(argc, argv, 388a6d42e7dSPeter Dunlap 'I', MDB_OPT_SETBITS, TRUE, &idc.idc_ini, 389a6d42e7dSPeter Dunlap 'T', MDB_OPT_SETBITS, TRUE, &idc.idc_tgt, 390a6d42e7dSPeter Dunlap 'a', MDB_OPT_SETBITS, TRUE, &print_ip, 391a6d42e7dSPeter Dunlap 't', MDB_OPT_SETBITS, TRUE, &task, 392a6d42e7dSPeter Dunlap 'b', MDB_OPT_SETBITS, TRUE, &buffer, 393a6d42e7dSPeter Dunlap 'S', MDB_OPT_SETBITS, TRUE, &states, 394a6d42e7dSPeter Dunlap 'R', MDB_OPT_SETBITS, TRUE, &rc_audit, 395a6d42e7dSPeter Dunlap 'v', MDB_OPT_SETBITS, TRUE, &idc.idc_verbose, 396a6d42e7dSPeter Dunlap NULL) != argc) 397a6d42e7dSPeter Dunlap return (DCMD_USAGE); 398a6d42e7dSPeter Dunlap 399a6d42e7dSPeter Dunlap idc.u.child.idc_conn = 1; 400a6d42e7dSPeter Dunlap idc.u.child.idc_print_ip = print_ip; 401a6d42e7dSPeter Dunlap idc.u.child.idc_task = task; 402a6d42e7dSPeter Dunlap idc.u.child.idc_buffer = buffer; 403a6d42e7dSPeter Dunlap idc.u.child.idc_states = states; 404a6d42e7dSPeter Dunlap idc.u.child.idc_rc_audit = rc_audit; 405a6d42e7dSPeter Dunlap if (DCMD_HDRSPEC(flags)) 406a6d42e7dSPeter Dunlap idc.idc_header = 1; 407a6d42e7dSPeter Dunlap 408a6d42e7dSPeter Dunlap /* 409a6d42e7dSPeter Dunlap * If no address was specified on the command line, we 410a6d42e7dSPeter Dunlap * print out all connections 411a6d42e7dSPeter Dunlap */ 412a6d42e7dSPeter Dunlap if (!(flags & DCMD_ADDRSPEC)) { 413a6d42e7dSPeter Dunlap return (iscsi_walk_all_conn(&idc)); 414a6d42e7dSPeter Dunlap } else { 415a6d42e7dSPeter Dunlap return (iscsi_conn_impl(addr, &idc)); 416a6d42e7dSPeter Dunlap } 417a6d42e7dSPeter Dunlap /*NOTREACHED*/ 418a6d42e7dSPeter Dunlap } 419a6d42e7dSPeter Dunlap 420a6d42e7dSPeter Dunlap /* 421a6d42e7dSPeter Dunlap * ::iscsi_task [-bv] 422a6d42e7dSPeter Dunlap * 423a6d42e7dSPeter Dunlap * iscsi_task - Print out information associated with an iSCSI task 424a6d42e7dSPeter Dunlap * 425a6d42e7dSPeter Dunlap * b Print associated buffer information 426a6d42e7dSPeter Dunlap * S Print recent state events and transitions 427a6d42e7dSPeter Dunlap * R Print reference count audit data 428a6d42e7dSPeter Dunlap * v Verbose output about the connection 429a6d42e7dSPeter Dunlap */ 430a6d42e7dSPeter Dunlap /*ARGSUSED*/ 431a6d42e7dSPeter Dunlap static int 432a6d42e7dSPeter Dunlap iscsi_task(uintptr_t addr, uint_t flags, int argc, const mdb_arg_t *argv) 433a6d42e7dSPeter Dunlap { 434a6d42e7dSPeter Dunlap iscsi_dcmd_ctrl_t idc; 435a6d42e7dSPeter Dunlap int buffer = 0; 436a6d42e7dSPeter Dunlap int states = 0, rc_audit = 0; 437a6d42e7dSPeter Dunlap 438a6d42e7dSPeter Dunlap bzero(&idc, sizeof (idc)); 439a6d42e7dSPeter Dunlap if (mdb_getopts(argc, argv, 440a6d42e7dSPeter Dunlap 'b', MDB_OPT_SETBITS, TRUE, &buffer, 441a6d42e7dSPeter Dunlap 'S', MDB_OPT_SETBITS, TRUE, &states, 442a6d42e7dSPeter Dunlap 'R', MDB_OPT_SETBITS, TRUE, &rc_audit, 443a6d42e7dSPeter Dunlap 'v', MDB_OPT_SETBITS, TRUE, &idc.idc_verbose, 444a6d42e7dSPeter Dunlap NULL) != argc) 445a6d42e7dSPeter Dunlap return (DCMD_USAGE); 446a6d42e7dSPeter Dunlap 447a6d42e7dSPeter Dunlap idc.u.child.idc_conn = 0; 448a6d42e7dSPeter Dunlap idc.u.child.idc_task = 1; 449a6d42e7dSPeter Dunlap idc.u.child.idc_buffer = buffer; 450a6d42e7dSPeter Dunlap idc.u.child.idc_states = states; 451a6d42e7dSPeter Dunlap idc.u.child.idc_rc_audit = rc_audit; 452a6d42e7dSPeter Dunlap if (DCMD_HDRSPEC(flags)) 453a6d42e7dSPeter Dunlap idc.idc_header = 1; 454a6d42e7dSPeter Dunlap 455a6d42e7dSPeter Dunlap /* 456a6d42e7dSPeter Dunlap * If no address was specified on the command line, we 457a6d42e7dSPeter Dunlap * print out all connections 458a6d42e7dSPeter Dunlap */ 459a6d42e7dSPeter Dunlap if (!(flags & DCMD_ADDRSPEC)) { 460a6d42e7dSPeter Dunlap return (iscsi_walk_all_conn(&idc)); 461a6d42e7dSPeter Dunlap } else { 462a6d42e7dSPeter Dunlap return (iscsi_task_impl(addr, &idc)); 463a6d42e7dSPeter Dunlap } 464a6d42e7dSPeter Dunlap /*NOTREACHED*/ 465a6d42e7dSPeter Dunlap } 466a6d42e7dSPeter Dunlap 467a6d42e7dSPeter Dunlap /* 468a6d42e7dSPeter Dunlap * ::iscsi_refcnt 469a6d42e7dSPeter Dunlap * 470a6d42e7dSPeter Dunlap * iscsi_refcnt - Dump an idm_refcnt_t structure 471a6d42e7dSPeter Dunlap * 472a6d42e7dSPeter Dunlap */ 473a6d42e7dSPeter Dunlap /*ARGSUSED*/ 474a6d42e7dSPeter Dunlap static int 475a6d42e7dSPeter Dunlap iscsi_refcnt(uintptr_t addr, uint_t flags, int argc, const mdb_arg_t *argv) 476a6d42e7dSPeter Dunlap { 477a6d42e7dSPeter Dunlap if (!(flags & DCMD_ADDRSPEC)) { 478a6d42e7dSPeter Dunlap return (DCMD_ERR); 479a6d42e7dSPeter Dunlap } else { 480a6d42e7dSPeter Dunlap return (iscsi_refcnt_impl(addr)); 481a6d42e7dSPeter Dunlap } 482a6d42e7dSPeter Dunlap /*NOTREACHED*/ 483a6d42e7dSPeter Dunlap } 484a6d42e7dSPeter Dunlap 485a6d42e7dSPeter Dunlap /* 486a6d42e7dSPeter Dunlap * ::iscsi_states 487a6d42e7dSPeter Dunlap * 488a6d42e7dSPeter Dunlap * iscsi_states - Dump events and state transitions recoreded in an 489a6d42e7dSPeter Dunlap * idm_sm_audit_t structure 490a6d42e7dSPeter Dunlap * 491a6d42e7dSPeter Dunlap */ 492a6d42e7dSPeter Dunlap /*ARGSUSED*/ 493a6d42e7dSPeter Dunlap static int 494a6d42e7dSPeter Dunlap iscsi_states(uintptr_t addr, uint_t flags, int argc, const mdb_arg_t *argv) 495a6d42e7dSPeter Dunlap { 496a6d42e7dSPeter Dunlap if (!(flags & DCMD_ADDRSPEC)) { 497a6d42e7dSPeter Dunlap return (DCMD_ERR); 498a6d42e7dSPeter Dunlap } else { 499a6d42e7dSPeter Dunlap return (iscsi_sm_audit_impl(addr)); 500a6d42e7dSPeter Dunlap } 501a6d42e7dSPeter Dunlap /*NOTREACHED*/ 502a6d42e7dSPeter Dunlap } 503a6d42e7dSPeter Dunlap 50430e7468fSPeter Dunlap /* 50530e7468fSPeter Dunlap * Helper function to list all the initiator sessions 50630e7468fSPeter Dunlap */ 50730e7468fSPeter Dunlap static int 50830e7468fSPeter Dunlap iscsi_walk_ini_sessions(uintptr_t array_vaddr) 50930e7468fSPeter Dunlap { 51030e7468fSPeter Dunlap iscsi_hba_t ihp; 51130e7468fSPeter Dunlap int i; 51230e7468fSPeter Dunlap int array_size; 51330e7468fSPeter Dunlap struct i_ddi_soft_state *ss; 51430e7468fSPeter Dunlap iscsi_sess_t *isp; 51530e7468fSPeter Dunlap 51630e7468fSPeter Dunlap ss = (struct i_ddi_soft_state *)mdb_alloc(sizeof (*ss), 51730e7468fSPeter Dunlap UM_SLEEP|UM_GC); 51830e7468fSPeter Dunlap if (mdb_vread(ss, sizeof (*ss), array_vaddr) != sizeof (*ss)) { 51930e7468fSPeter Dunlap mdb_warn("Cannot read softstate struct (Invalid pointer?).\n"); 52030e7468fSPeter Dunlap return (DCMD_ERR); 52130e7468fSPeter Dunlap } 52230e7468fSPeter Dunlap array_size = ss->n_items * (sizeof (void *)); 52330e7468fSPeter Dunlap array_vaddr = (uintptr_t)ss->array; 52430e7468fSPeter Dunlap ss->array = mdb_alloc(array_size, UM_SLEEP|UM_GC); 52530e7468fSPeter Dunlap if (mdb_vread(ss->array, array_size, array_vaddr) != array_size) { 52630e7468fSPeter Dunlap mdb_warn("Corrupted softstate struct.\n"); 52730e7468fSPeter Dunlap return (DCMD_ERR); 52830e7468fSPeter Dunlap } 52930e7468fSPeter Dunlap for (i = 0; i < ss->n_items; i++) { 53030e7468fSPeter Dunlap if (ss->array[i] == 0) 53130e7468fSPeter Dunlap continue; 53230e7468fSPeter Dunlap 53330e7468fSPeter Dunlap if (mdb_vread(&ihp, sizeof (ihp), (uintptr_t)ss->array[i]) 53430e7468fSPeter Dunlap != sizeof (ihp)) { 53530e7468fSPeter Dunlap mdb_warn("Corrupted softstate struct.\n"); 53630e7468fSPeter Dunlap return (DCMD_ERR); 53730e7468fSPeter Dunlap } 53830e7468fSPeter Dunlap mdb_printf("iscsi_hba %p sessions: \n", ihp); 53930e7468fSPeter Dunlap mdb_printf("%<u>%-19s %-4s %-8s%</u>\n", 54030e7468fSPeter Dunlap "Session", "Type", "State"); 54130e7468fSPeter Dunlap for (isp = ihp.hba_sess_list; isp; ) { 54230e7468fSPeter Dunlap iscsi_sess_t sess; 54330e7468fSPeter Dunlap if ((mdb_vread(&sess, sizeof (iscsi_sess_t), 54430e7468fSPeter Dunlap (uintptr_t)isp)) != sizeof (iscsi_sess_t)) { 54530e7468fSPeter Dunlap mdb_warn("Failed to read session\n"); 54630e7468fSPeter Dunlap return (DCMD_ERR); 54730e7468fSPeter Dunlap } 54830e7468fSPeter Dunlap mdb_printf("%-19p %-4d %-8d\n", isp, 54930e7468fSPeter Dunlap sess.sess_type, 55030e7468fSPeter Dunlap sess.sess_state); 55130e7468fSPeter Dunlap isp = sess.sess_next; 55230e7468fSPeter Dunlap } 55330e7468fSPeter Dunlap } 55430e7468fSPeter Dunlap return (DCMD_OK); 55530e7468fSPeter Dunlap } 55630e7468fSPeter Dunlap 557a6d42e7dSPeter Dunlap static int 558a6d42e7dSPeter Dunlap iscsi_walk_all_sess(iscsi_dcmd_ctrl_t *idc) 559a6d42e7dSPeter Dunlap { 560a6d42e7dSPeter Dunlap uintptr_t iscsit_global_addr; 561a6d42e7dSPeter Dunlap uintptr_t avl_addr; 562a6d42e7dSPeter Dunlap uintptr_t list_addr; 563a6d42e7dSPeter Dunlap GElf_Sym sym; 56430e7468fSPeter Dunlap uintptr_t adr; 56530e7468fSPeter Dunlap /* Initiator sessions */ 56630e7468fSPeter Dunlap if (idc->idc_ini) { 56730e7468fSPeter Dunlap if (mdb_readvar(&adr, "iscsi_state") == -1) { 568a6d42e7dSPeter Dunlap 56930e7468fSPeter Dunlap mdb_warn("state variable iscsi_state not found.\n"); 57030e7468fSPeter Dunlap mdb_warn("Is the driver loaded ?\n"); 57130e7468fSPeter Dunlap return (DCMD_ERR); 57230e7468fSPeter Dunlap } 57330e7468fSPeter Dunlap return (iscsi_walk_ini_sessions(adr)); 57430e7468fSPeter Dunlap } 57530e7468fSPeter Dunlap /* Target sessions */ 576a6d42e7dSPeter Dunlap /* Walk discovery sessions */ 577a6d42e7dSPeter Dunlap if (mdb_lookup_by_name("iscsit_global", &sym) == -1) { 578a6d42e7dSPeter Dunlap mdb_warn("failed to find symbol 'iscsit_global'"); 579a6d42e7dSPeter Dunlap return (DCMD_ERR); 580a6d42e7dSPeter Dunlap } 581a6d42e7dSPeter Dunlap iscsit_global_addr = (uintptr_t)sym.st_value; 582a6d42e7dSPeter Dunlap avl_addr = iscsit_global_addr + 583a6d42e7dSPeter Dunlap offsetof(iscsit_global_t, global_discovery_sessions); 584a6d42e7dSPeter Dunlap if (mdb_pwalk("avl", iscsi_sess_walk_cb, idc, avl_addr) == -1) { 585a6d42e7dSPeter Dunlap mdb_warn("avl walk failed for discovery sessions"); 586a6d42e7dSPeter Dunlap return (DCMD_ERR); 587a6d42e7dSPeter Dunlap } 588a6d42e7dSPeter Dunlap 589a6d42e7dSPeter Dunlap /* Walk targets printing all session info */ 590a6d42e7dSPeter Dunlap avl_addr = iscsit_global_addr + 591a6d42e7dSPeter Dunlap offsetof(iscsit_global_t, global_target_list); 592a6d42e7dSPeter Dunlap if (mdb_pwalk("avl", iscsi_tgt_walk_cb, idc, avl_addr) == -1) { 593a6d42e7dSPeter Dunlap mdb_warn("avl walk failed for target/session tree"); 594a6d42e7dSPeter Dunlap return (DCMD_ERR); 595a6d42e7dSPeter Dunlap } 596a6d42e7dSPeter Dunlap 597a6d42e7dSPeter Dunlap /* Walk deleting targets printing all session info */ 598a6d42e7dSPeter Dunlap list_addr = iscsit_global_addr + 599a6d42e7dSPeter Dunlap offsetof(iscsit_global_t, global_deleted_target_list); 600a6d42e7dSPeter Dunlap if (mdb_pwalk("list", iscsi_tgt_walk_cb, idc, list_addr) == -1) { 601a6d42e7dSPeter Dunlap mdb_warn("list walk failed for deleted target list"); 602a6d42e7dSPeter Dunlap return (DCMD_ERR); 603a6d42e7dSPeter Dunlap } 604a6d42e7dSPeter Dunlap 605a6d42e7dSPeter Dunlap return (DCMD_OK); 606a6d42e7dSPeter Dunlap } 607a6d42e7dSPeter Dunlap 608a6d42e7dSPeter Dunlap static int 609a6d42e7dSPeter Dunlap iscsi_walk_all_conn(iscsi_dcmd_ctrl_t *idc) 610a6d42e7dSPeter Dunlap { 611a6d42e7dSPeter Dunlap uintptr_t idm_global_addr; 612a6d42e7dSPeter Dunlap uintptr_t list_addr; 613a6d42e7dSPeter Dunlap GElf_Sym sym; 614a6d42e7dSPeter Dunlap 615a6d42e7dSPeter Dunlap /* Walk initiator connections */ 616a6d42e7dSPeter Dunlap if (mdb_lookup_by_name("idm", &sym) == -1) { 617a6d42e7dSPeter Dunlap mdb_warn("failed to find symbol 'idm'"); 618a6d42e7dSPeter Dunlap return (DCMD_ERR); 619a6d42e7dSPeter Dunlap } 620a6d42e7dSPeter Dunlap idm_global_addr = (uintptr_t)sym.st_value; 621a6d42e7dSPeter Dunlap /* Walk connection list associated with the initiator */ 622a6d42e7dSPeter Dunlap list_addr = idm_global_addr + offsetof(idm_global_t, idm_ini_conn_list); 623a6d42e7dSPeter Dunlap if (mdb_pwalk("list", iscsi_conn_walk_cb, idc, list_addr) == -1) { 624a6d42e7dSPeter Dunlap mdb_warn("list walk failed for initiator connections"); 625a6d42e7dSPeter Dunlap return (DCMD_ERR); 626a6d42e7dSPeter Dunlap } 627a6d42e7dSPeter Dunlap 628a6d42e7dSPeter Dunlap /* Walk connection list associated with the target */ 629a6d42e7dSPeter Dunlap list_addr = idm_global_addr + offsetof(idm_global_t, idm_tgt_conn_list); 630a6d42e7dSPeter Dunlap if (mdb_pwalk("list", iscsi_conn_walk_cb, idc, list_addr) == -1) { 631a6d42e7dSPeter Dunlap mdb_warn("list walk failed for target service instances"); 632a6d42e7dSPeter Dunlap return (DCMD_ERR); 633a6d42e7dSPeter Dunlap } 634a6d42e7dSPeter Dunlap 635a6d42e7dSPeter Dunlap return (DCMD_OK); 636a6d42e7dSPeter Dunlap } 637a6d42e7dSPeter Dunlap 638a6d42e7dSPeter Dunlap /*ARGSUSED*/ 639a6d42e7dSPeter Dunlap static int 640a6d42e7dSPeter Dunlap iscsi_tpg_walk_cb(uintptr_t addr, const void *list_walker_data, 641a6d42e7dSPeter Dunlap void *idc_void) 642a6d42e7dSPeter Dunlap { 643a6d42e7dSPeter Dunlap /* We don't particularly care about the list walker data */ 644a6d42e7dSPeter Dunlap iscsi_dcmd_ctrl_t *idc = idc_void; 645a6d42e7dSPeter Dunlap int rc; 646a6d42e7dSPeter Dunlap 647a6d42e7dSPeter Dunlap rc = iscsi_tpg_impl(addr, idc); 648a6d42e7dSPeter Dunlap 649a6d42e7dSPeter Dunlap return ((rc == DCMD_OK) ? WALK_NEXT : WALK_ERR); 650a6d42e7dSPeter Dunlap } 651a6d42e7dSPeter Dunlap 652a6d42e7dSPeter Dunlap /*ARGSUSED*/ 653a6d42e7dSPeter Dunlap static int 654a6d42e7dSPeter Dunlap iscsi_tgt_walk_cb(uintptr_t addr, const void *list_walker_data, 655a6d42e7dSPeter Dunlap void *idc_void) 656a6d42e7dSPeter Dunlap { 657a6d42e7dSPeter Dunlap /* We don't particularly care about the list walker data */ 658a6d42e7dSPeter Dunlap iscsi_dcmd_ctrl_t *idc = idc_void; 659a6d42e7dSPeter Dunlap int rc; 660a6d42e7dSPeter Dunlap 661a6d42e7dSPeter Dunlap rc = iscsi_tgt_impl(addr, idc); 662a6d42e7dSPeter Dunlap 663a6d42e7dSPeter Dunlap return ((rc == DCMD_OK) ? WALK_NEXT : WALK_ERR); 664a6d42e7dSPeter Dunlap } 665a6d42e7dSPeter Dunlap 666a6d42e7dSPeter Dunlap /*ARGSUSED*/ 667a6d42e7dSPeter Dunlap static int 668a6d42e7dSPeter Dunlap iscsi_tpgt_walk_cb(uintptr_t addr, const void *list_walker_data, 669a6d42e7dSPeter Dunlap void *idc_void) 670a6d42e7dSPeter Dunlap { 671a6d42e7dSPeter Dunlap /* We don't particularly care about the list walker data */ 672a6d42e7dSPeter Dunlap iscsi_dcmd_ctrl_t *idc = idc_void; 673a6d42e7dSPeter Dunlap int rc; 674a6d42e7dSPeter Dunlap 675a6d42e7dSPeter Dunlap rc = iscsi_tpgt_impl(addr, idc); 676a6d42e7dSPeter Dunlap 677a6d42e7dSPeter Dunlap return ((rc == DCMD_OK) ? WALK_NEXT : WALK_ERR); 678a6d42e7dSPeter Dunlap } 679a6d42e7dSPeter Dunlap 680a6d42e7dSPeter Dunlap /*ARGSUSED*/ 681a6d42e7dSPeter Dunlap static int 682a6d42e7dSPeter Dunlap iscsi_portal_walk_cb(uintptr_t addr, const void *list_walker_data, 683a6d42e7dSPeter Dunlap void *idc_void) 684a6d42e7dSPeter Dunlap { 685a6d42e7dSPeter Dunlap /* We don't particularly care about the list walker data */ 686a6d42e7dSPeter Dunlap iscsi_dcmd_ctrl_t *idc = idc_void; 687a6d42e7dSPeter Dunlap int rc; 688a6d42e7dSPeter Dunlap 689a6d42e7dSPeter Dunlap rc = iscsi_portal_impl(addr, idc); 690a6d42e7dSPeter Dunlap 691a6d42e7dSPeter Dunlap return ((rc == DCMD_OK) ? WALK_NEXT : WALK_ERR); 692a6d42e7dSPeter Dunlap } 693a6d42e7dSPeter Dunlap 694a6d42e7dSPeter Dunlap /*ARGSUSED*/ 695a6d42e7dSPeter Dunlap static int 696a6d42e7dSPeter Dunlap iscsi_sess_walk_cb(uintptr_t addr, const void *list_walker_data, 697a6d42e7dSPeter Dunlap void *idc_void) 698a6d42e7dSPeter Dunlap { 699a6d42e7dSPeter Dunlap /* We don't particularly care about the list walker data */ 700a6d42e7dSPeter Dunlap iscsi_dcmd_ctrl_t *idc = idc_void; 701a6d42e7dSPeter Dunlap int rc; 702a6d42e7dSPeter Dunlap 703a6d42e7dSPeter Dunlap rc = iscsi_sess_impl(addr, idc); 704a6d42e7dSPeter Dunlap 705a6d42e7dSPeter Dunlap return ((rc == DCMD_OK) ? WALK_NEXT : WALK_ERR); 706a6d42e7dSPeter Dunlap } 707a6d42e7dSPeter Dunlap 708a6d42e7dSPeter Dunlap /*ARGSUSED*/ 709a6d42e7dSPeter Dunlap static int 710a6d42e7dSPeter Dunlap iscsi_sess_conn_walk_cb(uintptr_t addr, const void *list_walker_data, 711a6d42e7dSPeter Dunlap void *idc_void) 712a6d42e7dSPeter Dunlap { 713a6d42e7dSPeter Dunlap /* We don't particularly care about the list walker data */ 714a6d42e7dSPeter Dunlap iscsi_dcmd_ctrl_t *idc = idc_void; 715a6d42e7dSPeter Dunlap iscsit_conn_t ict; 716a6d42e7dSPeter Dunlap int rc; 717a6d42e7dSPeter Dunlap 718a6d42e7dSPeter Dunlap /* 719a6d42e7dSPeter Dunlap * This function is different from iscsi_conn_walk_cb because 720a6d42e7dSPeter Dunlap * we get an iscsit_conn_t instead of an idm_conn_t 721a6d42e7dSPeter Dunlap * 722a6d42e7dSPeter Dunlap * Read iscsit_conn_t, use to get idm_conn_t pointer 723a6d42e7dSPeter Dunlap */ 724a6d42e7dSPeter Dunlap if (mdb_vread(&ict, sizeof (iscsit_conn_t), addr) != 725a6d42e7dSPeter Dunlap sizeof (iscsit_conn_t)) { 726a6d42e7dSPeter Dunlap return (DCMD_ERR); 727a6d42e7dSPeter Dunlap } 728a6d42e7dSPeter Dunlap rc = iscsi_conn_impl((uintptr_t)ict.ict_ic, idc); 729a6d42e7dSPeter Dunlap 730a6d42e7dSPeter Dunlap return ((rc == DCMD_OK) ? WALK_NEXT : WALK_ERR); 731a6d42e7dSPeter Dunlap } 732a6d42e7dSPeter Dunlap 733a6d42e7dSPeter Dunlap /*ARGSUSED*/ 734a6d42e7dSPeter Dunlap static int 735a6d42e7dSPeter Dunlap iscsi_conn_walk_cb(uintptr_t addr, const void *list_walker_data, 736a6d42e7dSPeter Dunlap void *idc_void) 737a6d42e7dSPeter Dunlap { 738a6d42e7dSPeter Dunlap /* We don't particularly care about the list walker data */ 739a6d42e7dSPeter Dunlap iscsi_dcmd_ctrl_t *idc = idc_void; 740a6d42e7dSPeter Dunlap int rc; 741a6d42e7dSPeter Dunlap 742a6d42e7dSPeter Dunlap rc = iscsi_conn_impl(addr, idc); 743a6d42e7dSPeter Dunlap 744a6d42e7dSPeter Dunlap return ((rc == DCMD_OK) ? WALK_NEXT : WALK_ERR); 745a6d42e7dSPeter Dunlap } 746a6d42e7dSPeter Dunlap 747a6d42e7dSPeter Dunlap /*ARGSUSED*/ 748a6d42e7dSPeter Dunlap static int 749a6d42e7dSPeter Dunlap iscsi_buffer_walk_cb(uintptr_t addr, const void *list_walker_data, 750a6d42e7dSPeter Dunlap void *idc_void) 751a6d42e7dSPeter Dunlap { 752a6d42e7dSPeter Dunlap /* We don't particularly care about the list walker data */ 753a6d42e7dSPeter Dunlap iscsi_dcmd_ctrl_t *idc = idc_void; 754a6d42e7dSPeter Dunlap int rc; 755a6d42e7dSPeter Dunlap 756a6d42e7dSPeter Dunlap rc = iscsi_buffer_impl(addr, idc); 757a6d42e7dSPeter Dunlap 758a6d42e7dSPeter Dunlap return ((rc == DCMD_OK) ? WALK_NEXT : WALK_ERR); 759a6d42e7dSPeter Dunlap } 760a6d42e7dSPeter Dunlap 761a6d42e7dSPeter Dunlap static int 762a6d42e7dSPeter Dunlap iscsi_tgt_impl(uintptr_t addr, iscsi_dcmd_ctrl_t *idc) 763a6d42e7dSPeter Dunlap { 764a6d42e7dSPeter Dunlap iscsit_tgt_t tgt; 765a6d42e7dSPeter Dunlap uintptr_t avl_addr, rc_addr, states_addr; 766a6d42e7dSPeter Dunlap char tgt_name[MAX_ISCSI_NODENAMELEN]; 767a6d42e7dSPeter Dunlap int verbose, states, rc_audit; 768a6d42e7dSPeter Dunlap 769a6d42e7dSPeter Dunlap /* 770a6d42e7dSPeter Dunlap * Read iscsit_tgt_t 771a6d42e7dSPeter Dunlap */ 772a6d42e7dSPeter Dunlap if (mdb_vread(&tgt, sizeof (iscsit_tgt_t), addr) != 773a6d42e7dSPeter Dunlap sizeof (iscsit_tgt_t)) { 774a6d42e7dSPeter Dunlap return (DCMD_ERR); 775a6d42e7dSPeter Dunlap } 776a6d42e7dSPeter Dunlap 777a6d42e7dSPeter Dunlap /* 778a6d42e7dSPeter Dunlap * Read target name if available 779a6d42e7dSPeter Dunlap */ 780a6d42e7dSPeter Dunlap if ((tgt.target_name == NULL) || 781a6d42e7dSPeter Dunlap (mdb_readstr(tgt_name, sizeof (tgt_name), 782a6d42e7dSPeter Dunlap (uintptr_t)tgt.target_name) == -1)) { 783a6d42e7dSPeter Dunlap strcpy(tgt_name, "N/A"); 784a6d42e7dSPeter Dunlap } 785a6d42e7dSPeter Dunlap 786a6d42e7dSPeter Dunlap /* 787a6d42e7dSPeter Dunlap * Brief output 788a6d42e7dSPeter Dunlap * 789a6d42e7dSPeter Dunlap * iscsit_tgt_t pointer 790a6d42e7dSPeter Dunlap * iscsit_tgt_t.target_stmf_state 791a6d42e7dSPeter Dunlap * iscsit_tgt_t.target_sess_list.avl_numnodes (session count) 792a6d42e7dSPeter Dunlap * iscsit_tgt_t.target_name; 793a6d42e7dSPeter Dunlap */ 794a6d42e7dSPeter Dunlap 795a6d42e7dSPeter Dunlap verbose = idc->idc_verbose; 796a6d42e7dSPeter Dunlap states = idc->u.child.idc_states; 797a6d42e7dSPeter Dunlap rc_audit = idc->u.child.idc_rc_audit; 798a6d42e7dSPeter Dunlap 799a6d42e7dSPeter Dunlap /* For now we will ignore the verbose flag */ 800a6d42e7dSPeter Dunlap if (idc->u.child.idc_tgt) { 801a6d42e7dSPeter Dunlap /* Print target data */ 802a6d42e7dSPeter Dunlap if (idc->idc_header) { 803a6d42e7dSPeter Dunlap mdb_printf("%<u>%-19s %-4s %-8s%</u>\n", 804a6d42e7dSPeter Dunlap "iscsit_tgt_t", "Sess", "State"); 805a6d42e7dSPeter Dunlap } 806a6d42e7dSPeter Dunlap mdb_printf("%-19p %-4d %-8d\n", addr, 807a6d42e7dSPeter Dunlap tgt.target_sess_list.avl_numnodes, 808a6d42e7dSPeter Dunlap tgt.target_state); 809a6d42e7dSPeter Dunlap mdb_printf(" %s\n", tgt_name); 810a6d42e7dSPeter Dunlap } 811a6d42e7dSPeter Dunlap 812a6d42e7dSPeter Dunlap idc->idc_header = 0; 813a6d42e7dSPeter Dunlap idc->idc_verbose = 0; 814a6d42e7dSPeter Dunlap 815a6d42e7dSPeter Dunlap /* 816a6d42e7dSPeter Dunlap * Print states if requested 817a6d42e7dSPeter Dunlap */ 818a6d42e7dSPeter Dunlap if (idc->u.child.idc_tgt && states) { 819a6d42e7dSPeter Dunlap states_addr = addr + offsetof(iscsit_tgt_t, target_state_audit); 820a6d42e7dSPeter Dunlap 821a6d42e7dSPeter Dunlap (void) mdb_inc_indent(4); 822a6d42e7dSPeter Dunlap mdb_printf("State History:\n"); 823a6d42e7dSPeter Dunlap if (iscsi_sm_audit_impl(states_addr) != DCMD_OK) 824a6d42e7dSPeter Dunlap return (DCMD_ERR); 825a6d42e7dSPeter Dunlap idc->u.child.idc_states = 0; 826a6d42e7dSPeter Dunlap (void) mdb_dec_indent(4); 827a6d42e7dSPeter Dunlap } 828a6d42e7dSPeter Dunlap 829a6d42e7dSPeter Dunlap /* 830a6d42e7dSPeter Dunlap * Print refcnt audit data if requested 831a6d42e7dSPeter Dunlap */ 832a6d42e7dSPeter Dunlap if (idc->u.child.idc_tgt && rc_audit) { 833a6d42e7dSPeter Dunlap (void) mdb_inc_indent(4); 834a6d42e7dSPeter Dunlap mdb_printf("target_sess_refcnt:\n"); 835a6d42e7dSPeter Dunlap rc_addr = addr + 836a6d42e7dSPeter Dunlap offsetof(iscsit_tgt_t, target_sess_refcnt); 837a6d42e7dSPeter Dunlap if (iscsi_refcnt_impl(rc_addr) != DCMD_OK) 838a6d42e7dSPeter Dunlap return (DCMD_ERR); 839a6d42e7dSPeter Dunlap 840a6d42e7dSPeter Dunlap mdb_printf("target_refcnt:\n"); 841a6d42e7dSPeter Dunlap rc_addr = addr + 842a6d42e7dSPeter Dunlap offsetof(iscsit_tgt_t, target_refcnt); 843a6d42e7dSPeter Dunlap 844a6d42e7dSPeter Dunlap if (iscsi_refcnt_impl(rc_addr) != DCMD_OK) 845a6d42e7dSPeter Dunlap return (DCMD_ERR); 846a6d42e7dSPeter Dunlap idc->u.child.idc_rc_audit = 0; 847a6d42e7dSPeter Dunlap (void) mdb_dec_indent(4); 848a6d42e7dSPeter Dunlap } 849a6d42e7dSPeter Dunlap 850a6d42e7dSPeter Dunlap /* Any child objects to walk? */ 851a6d42e7dSPeter Dunlap if (idc->u.child.idc_tpgt || idc->u.child.idc_sess || 852a6d42e7dSPeter Dunlap idc->u.child.idc_conn || idc->u.child.idc_task || 853a6d42e7dSPeter Dunlap idc->u.child.idc_buffer) { 854a6d42e7dSPeter Dunlap /* Walk TPGT tree */ 855a6d42e7dSPeter Dunlap idc->idc_header = 1; 856a6d42e7dSPeter Dunlap (void) mdb_inc_indent(4); 857a6d42e7dSPeter Dunlap avl_addr = addr + 858a6d42e7dSPeter Dunlap offsetof(iscsit_tgt_t, target_tpgt_list); 859a6d42e7dSPeter Dunlap if (mdb_pwalk("avl", iscsi_tpgt_walk_cb, idc, 860a6d42e7dSPeter Dunlap avl_addr) == -1) { 861a6d42e7dSPeter Dunlap mdb_warn("target tpgt list walk failed"); 862a6d42e7dSPeter Dunlap (void) mdb_dec_indent(4); 863a6d42e7dSPeter Dunlap return (DCMD_ERR); 864a6d42e7dSPeter Dunlap } 865a6d42e7dSPeter Dunlap (void) mdb_dec_indent(4); 866a6d42e7dSPeter Dunlap 867a6d42e7dSPeter Dunlap /* Walk sess tree */ 868a6d42e7dSPeter Dunlap idc->idc_header = 1; 869a6d42e7dSPeter Dunlap (void) mdb_inc_indent(4); 870a6d42e7dSPeter Dunlap avl_addr = addr + offsetof(iscsit_tgt_t, target_sess_list); 871a6d42e7dSPeter Dunlap if (mdb_pwalk("avl", iscsi_sess_walk_cb, idc, 872a6d42e7dSPeter Dunlap avl_addr) == -1) { 873a6d42e7dSPeter Dunlap mdb_warn("target sess list walk failed"); 874a6d42e7dSPeter Dunlap (void) mdb_dec_indent(4); 875a6d42e7dSPeter Dunlap return (DCMD_ERR); 876a6d42e7dSPeter Dunlap } 877a6d42e7dSPeter Dunlap (void) mdb_dec_indent(4); 878a6d42e7dSPeter Dunlap 879a6d42e7dSPeter Dunlap idc->idc_header = 0; 880a6d42e7dSPeter Dunlap } 881a6d42e7dSPeter Dunlap 882a6d42e7dSPeter Dunlap idc->idc_verbose = verbose; 883a6d42e7dSPeter Dunlap idc->u.child.idc_states = states; 884a6d42e7dSPeter Dunlap idc->u.child.idc_rc_audit = rc_audit; 885a6d42e7dSPeter Dunlap return (DCMD_OK); 886a6d42e7dSPeter Dunlap } 887a6d42e7dSPeter Dunlap 888a6d42e7dSPeter Dunlap static int 889a6d42e7dSPeter Dunlap iscsi_tpgt_impl(uintptr_t addr, iscsi_dcmd_ctrl_t *idc) 890a6d42e7dSPeter Dunlap { 891a6d42e7dSPeter Dunlap iscsit_tpgt_t tpgt; 892a6d42e7dSPeter Dunlap iscsit_tpg_t tpg; 893a6d42e7dSPeter Dunlap uintptr_t avl_addr, tpg_addr; 894a6d42e7dSPeter Dunlap 895a6d42e7dSPeter Dunlap /* 896a6d42e7dSPeter Dunlap * Read iscsit_tpgt_t 897a6d42e7dSPeter Dunlap */ 898a6d42e7dSPeter Dunlap if (mdb_vread(&tpgt, sizeof (iscsit_tpgt_t), addr) != 899a6d42e7dSPeter Dunlap sizeof (iscsit_tpgt_t)) { 900a6d42e7dSPeter Dunlap return (DCMD_ERR); 901a6d42e7dSPeter Dunlap } 902a6d42e7dSPeter Dunlap 903a6d42e7dSPeter Dunlap tpg_addr = (uintptr_t)tpgt.tpgt_tpg; 904a6d42e7dSPeter Dunlap 905a6d42e7dSPeter Dunlap /* 906a6d42e7dSPeter Dunlap * Read iscsit_tpg_t 907a6d42e7dSPeter Dunlap */ 908a6d42e7dSPeter Dunlap if (mdb_vread(&tpg, sizeof (iscsit_tpg_t), tpg_addr) != 909a6d42e7dSPeter Dunlap sizeof (iscsit_tpg_t)) { 910a6d42e7dSPeter Dunlap return (DCMD_ERR); 911a6d42e7dSPeter Dunlap } 912a6d42e7dSPeter Dunlap 913a6d42e7dSPeter Dunlap /* 914a6d42e7dSPeter Dunlap * Brief output 915a6d42e7dSPeter Dunlap * 916a6d42e7dSPeter Dunlap * iscsit_tpgt_t pointer 917a6d42e7dSPeter Dunlap * iscsit_tpg_t pointer 918a6d42e7dSPeter Dunlap * iscsit_tpg_t.tpg_name 919a6d42e7dSPeter Dunlap * iscsit_tpgt_t.tpgt_tag; 920a6d42e7dSPeter Dunlap */ 921a6d42e7dSPeter Dunlap 922a6d42e7dSPeter Dunlap /* For now we will ignore the verbose flag */ 923a6d42e7dSPeter Dunlap if (idc->u.child.idc_tpgt) { 924a6d42e7dSPeter Dunlap /* Print target data */ 925a6d42e7dSPeter Dunlap if (idc->idc_header) { 926a6d42e7dSPeter Dunlap mdb_printf("%<u>%-?s %-?s %-18s %-6s%</u>\n", 927a6d42e7dSPeter Dunlap "iscsit_tpgt_t", "iscsit_tpg_t", "Name", "Tag"); 928a6d42e7dSPeter Dunlap } 929a6d42e7dSPeter Dunlap mdb_printf("%?p %?p %-18s 0x%04x\n", addr, tpgt.tpgt_tpg, 930a6d42e7dSPeter Dunlap tpg.tpg_name, tpgt.tpgt_tag); 931a6d42e7dSPeter Dunlap } 932a6d42e7dSPeter Dunlap 933a6d42e7dSPeter Dunlap /* 934a6d42e7dSPeter Dunlap * Assume for now that anyone interested in TPGT wants to see the 935a6d42e7dSPeter Dunlap * portals as well. 936a6d42e7dSPeter Dunlap */ 937a6d42e7dSPeter Dunlap idc->idc_header = 1; 938a6d42e7dSPeter Dunlap (void) mdb_inc_indent(4); 939a6d42e7dSPeter Dunlap avl_addr = tpg_addr + offsetof(iscsit_tpg_t, tpg_portal_list); 940a6d42e7dSPeter Dunlap if (mdb_pwalk("avl", iscsi_portal_walk_cb, idc, avl_addr) == -1) { 941a6d42e7dSPeter Dunlap mdb_warn("portal list walk failed"); 942a6d42e7dSPeter Dunlap (void) mdb_dec_indent(4); 943a6d42e7dSPeter Dunlap return (DCMD_ERR); 944a6d42e7dSPeter Dunlap } 945a6d42e7dSPeter Dunlap (void) mdb_dec_indent(4); 946a6d42e7dSPeter Dunlap idc->idc_header = 0; 947a6d42e7dSPeter Dunlap 948a6d42e7dSPeter Dunlap return (DCMD_OK); 949a6d42e7dSPeter Dunlap } 950a6d42e7dSPeter Dunlap 951a6d42e7dSPeter Dunlap static int 952a6d42e7dSPeter Dunlap iscsi_tpg_impl(uintptr_t addr, iscsi_dcmd_ctrl_t *idc) 953a6d42e7dSPeter Dunlap { 954a6d42e7dSPeter Dunlap iscsit_tpg_t tpg; 955a6d42e7dSPeter Dunlap uintptr_t avl_addr; 956a6d42e7dSPeter Dunlap 957a6d42e7dSPeter Dunlap /* 958a6d42e7dSPeter Dunlap * Read iscsit_tpg_t 959a6d42e7dSPeter Dunlap */ 960a6d42e7dSPeter Dunlap if (mdb_vread(&tpg, sizeof (iscsit_tpg_t), addr) != 961a6d42e7dSPeter Dunlap sizeof (iscsit_tpg_t)) { 962a6d42e7dSPeter Dunlap return (DCMD_ERR); 963a6d42e7dSPeter Dunlap } 964a6d42e7dSPeter Dunlap 965a6d42e7dSPeter Dunlap /* 966a6d42e7dSPeter Dunlap * Brief output 967a6d42e7dSPeter Dunlap * 968a6d42e7dSPeter Dunlap * iscsit_tpgt_t pointer 969a6d42e7dSPeter Dunlap * iscsit_tpg_t pointer 970a6d42e7dSPeter Dunlap * iscsit_tpg_t.tpg_name 971a6d42e7dSPeter Dunlap * iscsit_tpgt_t.tpgt_tag; 972a6d42e7dSPeter Dunlap */ 973a6d42e7dSPeter Dunlap 974a6d42e7dSPeter Dunlap /* For now we will ignore the verbose flag */ 975a6d42e7dSPeter Dunlap 976a6d42e7dSPeter Dunlap /* Print target data */ 977a6d42e7dSPeter Dunlap if (idc->idc_header) { 978a6d42e7dSPeter Dunlap mdb_printf("%<u>%-?s %-18s%</u>\n", 979a6d42e7dSPeter Dunlap "iscsit_tpg_t", "Name"); 980a6d42e7dSPeter Dunlap } 981a6d42e7dSPeter Dunlap mdb_printf("%?p %-18s\n", addr, tpg.tpg_name); 982a6d42e7dSPeter Dunlap 983a6d42e7dSPeter Dunlap 984a6d42e7dSPeter Dunlap /* 985a6d42e7dSPeter Dunlap * Assume for now that anyone interested in TPG wants to see the 986a6d42e7dSPeter Dunlap * portals as well. 987a6d42e7dSPeter Dunlap */ 988a6d42e7dSPeter Dunlap idc->idc_header = 1; 989a6d42e7dSPeter Dunlap (void) mdb_inc_indent(4); 990a6d42e7dSPeter Dunlap avl_addr = addr + offsetof(iscsit_tpg_t, tpg_portal_list); 991a6d42e7dSPeter Dunlap if (mdb_pwalk("avl", iscsi_portal_walk_cb, idc, avl_addr) == -1) { 992a6d42e7dSPeter Dunlap mdb_warn("portal list walk failed"); 993a6d42e7dSPeter Dunlap (void) mdb_dec_indent(4); 994a6d42e7dSPeter Dunlap return (DCMD_ERR); 995a6d42e7dSPeter Dunlap } 996a6d42e7dSPeter Dunlap (void) mdb_dec_indent(4); 997a6d42e7dSPeter Dunlap idc->idc_header = 0; 998a6d42e7dSPeter Dunlap 999a6d42e7dSPeter Dunlap return (DCMD_OK); 1000a6d42e7dSPeter Dunlap } 1001a6d42e7dSPeter Dunlap 1002a6d42e7dSPeter Dunlap static int 1003a6d42e7dSPeter Dunlap iscsi_portal_impl(uintptr_t addr, iscsi_dcmd_ctrl_t *idc) 1004a6d42e7dSPeter Dunlap { 1005a6d42e7dSPeter Dunlap iscsit_portal_t portal; 1006a6d42e7dSPeter Dunlap char portal_addr[PORTAL_STR_LEN]; 1007a6d42e7dSPeter Dunlap if (idc->u.child.idc_portal) { 1008a6d42e7dSPeter Dunlap /* 1009a6d42e7dSPeter Dunlap * Read iscsit_portal_t 1010a6d42e7dSPeter Dunlap */ 1011a6d42e7dSPeter Dunlap if (mdb_vread(&portal, sizeof (iscsit_portal_t), addr) != 1012a6d42e7dSPeter Dunlap sizeof (iscsit_portal_t)) { 1013a6d42e7dSPeter Dunlap return (DCMD_ERR); 1014a6d42e7dSPeter Dunlap } 1015a6d42e7dSPeter Dunlap 1016a6d42e7dSPeter Dunlap /* Print portal data */ 1017a6d42e7dSPeter Dunlap if (idc->idc_header) { 1018a6d42e7dSPeter Dunlap mdb_printf("%<u>%-?s %-?s %-30s%</u>\n", 1019a6d42e7dSPeter Dunlap "iscsit_portal_t", "idm_svc_t", "IP:Port"); 1020a6d42e7dSPeter Dunlap } 1021a6d42e7dSPeter Dunlap sa_to_str(&portal.portal_addr, portal_addr); 1022a6d42e7dSPeter Dunlap mdb_printf("%?p %?p %s\n", addr, portal.portal_svc, 1023a6d42e7dSPeter Dunlap portal_addr); 1024a6d42e7dSPeter Dunlap } 1025a6d42e7dSPeter Dunlap 1026a6d42e7dSPeter Dunlap return (DCMD_OK); 1027a6d42e7dSPeter Dunlap } 1028a6d42e7dSPeter Dunlap 1029a6d42e7dSPeter Dunlap static int 1030a6d42e7dSPeter Dunlap iscsi_sess_impl(uintptr_t addr, iscsi_dcmd_ctrl_t *idc) 1031a6d42e7dSPeter Dunlap { 1032a6d42e7dSPeter Dunlap iscsit_sess_t ist; 1033a6d42e7dSPeter Dunlap uintptr_t list_addr, states_addr, rc_addr; 1034a6d42e7dSPeter Dunlap char ini_name[80]; 1035a6d42e7dSPeter Dunlap char tgt_name[80]; 1036a6d42e7dSPeter Dunlap int verbose, states, rc_audit; 1037a6d42e7dSPeter Dunlap 1038a6d42e7dSPeter Dunlap /* 1039a6d42e7dSPeter Dunlap * Read iscsit_sess_t 1040a6d42e7dSPeter Dunlap */ 1041a6d42e7dSPeter Dunlap if (mdb_vread(&ist, sizeof (iscsit_sess_t), addr) != 1042a6d42e7dSPeter Dunlap sizeof (iscsit_sess_t)) { 1043a6d42e7dSPeter Dunlap return (DCMD_ERR); 1044a6d42e7dSPeter Dunlap } 1045a6d42e7dSPeter Dunlap 1046a6d42e7dSPeter Dunlap /* 1047a6d42e7dSPeter Dunlap * Brief output 1048a6d42e7dSPeter Dunlap * 1049a6d42e7dSPeter Dunlap * iscsit_sess_t pointer 1050a6d42e7dSPeter Dunlap * iscsit_sess_t.ist_state/iscsit_sess_t.ist_ffp_conn_count 1051a6d42e7dSPeter Dunlap * iscsit_sess_t.ist_tsih 1052a6d42e7dSPeter Dunlap * iscsit_sess_t.ist_initiator_name 1053a6d42e7dSPeter Dunlap */ 1054a6d42e7dSPeter Dunlap 1055a6d42e7dSPeter Dunlap verbose = idc->idc_verbose; 1056a6d42e7dSPeter Dunlap states = idc->u.child.idc_states; 1057a6d42e7dSPeter Dunlap rc_audit = idc->u.child.idc_rc_audit; 1058a6d42e7dSPeter Dunlap 1059a6d42e7dSPeter Dunlap if (idc->u.child.idc_sess) { 1060a6d42e7dSPeter Dunlap if (verbose) { 1061a6d42e7dSPeter Dunlap /* 1062a6d42e7dSPeter Dunlap * Read initiator name if available 1063a6d42e7dSPeter Dunlap */ 1064a6d42e7dSPeter Dunlap if ((ist.ist_initiator_name == NULL) || 1065a6d42e7dSPeter Dunlap (mdb_readstr(ini_name, sizeof (ini_name), 1066a6d42e7dSPeter Dunlap (uintptr_t)ist.ist_initiator_name) == -1)) { 1067a6d42e7dSPeter Dunlap strcpy(ini_name, "N/A"); 1068a6d42e7dSPeter Dunlap } 1069a6d42e7dSPeter Dunlap 1070a6d42e7dSPeter Dunlap /* 1071a6d42e7dSPeter Dunlap * Read target name if available 1072a6d42e7dSPeter Dunlap */ 1073a6d42e7dSPeter Dunlap if ((ist.ist_target_name == NULL) || 1074a6d42e7dSPeter Dunlap (mdb_readstr(tgt_name, sizeof (tgt_name), 1075a6d42e7dSPeter Dunlap (uintptr_t)ist.ist_target_name) == -1)) { 1076a6d42e7dSPeter Dunlap strcpy(tgt_name, "N/A"); 1077a6d42e7dSPeter Dunlap } 1078a6d42e7dSPeter Dunlap 1079a6d42e7dSPeter Dunlap mdb_printf("Session %p\n", addr); 1080a6d42e7dSPeter Dunlap mdb_printf("%16s: %d\n", "State", 1081a6d42e7dSPeter Dunlap ist.ist_state); 1082a6d42e7dSPeter Dunlap mdb_printf("%16s: %d\n", "Last State", 1083a6d42e7dSPeter Dunlap ist.ist_last_state); 1084a6d42e7dSPeter Dunlap mdb_printf("%16s: %d\n", "FFP Connections", 1085a6d42e7dSPeter Dunlap ist.ist_ffp_conn_count); 1086a6d42e7dSPeter Dunlap mdb_printf("%16s: %02x%02x%02x%02x%02x%02x\n", "ISID", 1087a6d42e7dSPeter Dunlap ist.ist_isid[0], ist.ist_isid[1], ist.ist_isid[2], 1088a6d42e7dSPeter Dunlap ist.ist_isid[3], ist.ist_isid[4], ist.ist_isid[5]); 1089a6d42e7dSPeter Dunlap mdb_printf("%16s: 0x%04x\n", "TSIH", 1090a6d42e7dSPeter Dunlap ist.ist_tsih); 1091a6d42e7dSPeter Dunlap mdb_printf("%16s: %s\n", "Initiator IQN", 1092a6d42e7dSPeter Dunlap ini_name); 1093a6d42e7dSPeter Dunlap mdb_printf("%16s: %s\n", "Target IQN", 1094a6d42e7dSPeter Dunlap tgt_name); 1095a6d42e7dSPeter Dunlap mdb_printf("%16s: %08x\n", "ExpCmdSN", 1096a6d42e7dSPeter Dunlap ist.ist_expcmdsn); 1097a6d42e7dSPeter Dunlap mdb_printf("%16s: %08x\n", "MaxCmdSN", 1098a6d42e7dSPeter Dunlap ist.ist_maxcmdsn); 1099a6d42e7dSPeter Dunlap } else { 1100a6d42e7dSPeter Dunlap /* Print session data */ 1101a6d42e7dSPeter Dunlap if (idc->idc_header) { 1102a6d42e7dSPeter Dunlap mdb_printf("%<u>%-?s %10s %-12s %-6s%</u>\n", 1103a6d42e7dSPeter Dunlap "iscsit_sess_t", "State/Conn", "ISID", 1104a6d42e7dSPeter Dunlap "TSIH"); 1105a6d42e7dSPeter Dunlap } 1106a6d42e7dSPeter Dunlap mdb_printf("%?p %4d/%-4d %02x%02x%02x%02x%02x%02x " 1107a6d42e7dSPeter Dunlap "0x%04x\n", addr, 1108a6d42e7dSPeter Dunlap ist.ist_state, ist.ist_ffp_conn_count, 1109a6d42e7dSPeter Dunlap ist.ist_isid[0], ist.ist_isid[1], ist.ist_isid[2], 1110a6d42e7dSPeter Dunlap ist.ist_isid[3], ist.ist_isid[4], ist.ist_isid[5], 1111a6d42e7dSPeter Dunlap ist.ist_tsih); 1112a6d42e7dSPeter Dunlap } 1113a6d42e7dSPeter Dunlap idc->idc_header = 0; 1114a6d42e7dSPeter Dunlap } 1115a6d42e7dSPeter Dunlap 1116a6d42e7dSPeter Dunlap idc->idc_verbose = 0; 1117a6d42e7dSPeter Dunlap 1118a6d42e7dSPeter Dunlap /* 1119a6d42e7dSPeter Dunlap * Print states if requested 1120a6d42e7dSPeter Dunlap */ 1121a6d42e7dSPeter Dunlap if (states) { 1122a6d42e7dSPeter Dunlap states_addr = addr + offsetof(iscsit_sess_t, ist_state_audit); 1123a6d42e7dSPeter Dunlap 1124a6d42e7dSPeter Dunlap (void) mdb_inc_indent(4); 1125a6d42e7dSPeter Dunlap mdb_printf("State History:\n"); 1126a6d42e7dSPeter Dunlap if (iscsi_sm_audit_impl(states_addr) != DCMD_OK) 1127a6d42e7dSPeter Dunlap return (DCMD_ERR); 1128a6d42e7dSPeter Dunlap 1129a6d42e7dSPeter Dunlap /* Don't print state history for child objects */ 1130a6d42e7dSPeter Dunlap idc->u.child.idc_states = 0; 1131a6d42e7dSPeter Dunlap (void) mdb_dec_indent(4); 1132a6d42e7dSPeter Dunlap } 1133a6d42e7dSPeter Dunlap 1134a6d42e7dSPeter Dunlap /* 1135a6d42e7dSPeter Dunlap * Print refcnt audit data if requested 1136a6d42e7dSPeter Dunlap */ 1137a6d42e7dSPeter Dunlap if (rc_audit) { 1138a6d42e7dSPeter Dunlap (void) mdb_inc_indent(4); 1139a6d42e7dSPeter Dunlap mdb_printf("Reference History:\n"); 1140a6d42e7dSPeter Dunlap rc_addr = addr + 1141a6d42e7dSPeter Dunlap offsetof(iscsit_sess_t, ist_refcnt); 1142a6d42e7dSPeter Dunlap if (iscsi_refcnt_impl(rc_addr) != DCMD_OK) 1143a6d42e7dSPeter Dunlap return (DCMD_ERR); 1144a6d42e7dSPeter Dunlap 1145a6d42e7dSPeter Dunlap /* Don't print audit data for child objects */ 1146a6d42e7dSPeter Dunlap idc->u.child.idc_rc_audit = 0; 1147a6d42e7dSPeter Dunlap (void) mdb_dec_indent(4); 1148a6d42e7dSPeter Dunlap } 1149a6d42e7dSPeter Dunlap 1150a6d42e7dSPeter Dunlap /* Any child objects to walk? */ 1151a6d42e7dSPeter Dunlap if (idc->u.child.idc_conn || idc->u.child.idc_task || 1152a6d42e7dSPeter Dunlap idc->u.child.idc_buffer) { 1153a6d42e7dSPeter Dunlap /* Walk conn list */ 1154a6d42e7dSPeter Dunlap idc->idc_header = 1; 1155a6d42e7dSPeter Dunlap (void) mdb_inc_indent(4); 1156a6d42e7dSPeter Dunlap list_addr = addr + offsetof(iscsit_sess_t, ist_conn_list); 1157a6d42e7dSPeter Dunlap if (mdb_pwalk("list", iscsi_sess_conn_walk_cb, idc, 1158a6d42e7dSPeter Dunlap list_addr) == -1) { 1159a6d42e7dSPeter Dunlap mdb_warn("session conn list walk failed"); 1160a6d42e7dSPeter Dunlap (void) mdb_dec_indent(4); 1161a6d42e7dSPeter Dunlap return (DCMD_ERR); 1162a6d42e7dSPeter Dunlap } 1163a6d42e7dSPeter Dunlap (void) mdb_dec_indent(4); 1164a6d42e7dSPeter Dunlap idc->idc_header = 0; 1165a6d42e7dSPeter Dunlap } 1166a6d42e7dSPeter Dunlap 1167a6d42e7dSPeter Dunlap idc->idc_verbose = verbose; 1168a6d42e7dSPeter Dunlap idc->u.child.idc_states = states; 1169a6d42e7dSPeter Dunlap idc->u.child.idc_rc_audit = rc_audit; 1170a6d42e7dSPeter Dunlap 1171a6d42e7dSPeter Dunlap return (DCMD_OK); 1172a6d42e7dSPeter Dunlap } 1173a6d42e7dSPeter Dunlap 1174a6d42e7dSPeter Dunlap static int 1175a6d42e7dSPeter Dunlap iscsi_conn_impl(uintptr_t addr, iscsi_dcmd_ctrl_t *idc) 1176a6d42e7dSPeter Dunlap { 1177a6d42e7dSPeter Dunlap uintptr_t idm_global_addr, states_addr, rc_addr; 1178a6d42e7dSPeter Dunlap uintptr_t task_addr, task_ptr; 1179a6d42e7dSPeter Dunlap GElf_Sym sym; 1180a6d42e7dSPeter Dunlap idm_task_t idt; 1181a6d42e7dSPeter Dunlap idm_conn_t ic; 1182a6d42e7dSPeter Dunlap char *conn_type; 1183a6d42e7dSPeter Dunlap int task_idx; 1184a6d42e7dSPeter Dunlap char laddr[PORTAL_STR_LEN]; 1185a6d42e7dSPeter Dunlap char raddr[PORTAL_STR_LEN]; 1186a6d42e7dSPeter Dunlap int verbose, states, rc_audit; 1187a6d42e7dSPeter Dunlap 1188a6d42e7dSPeter Dunlap /* 1189a6d42e7dSPeter Dunlap * Get pointer to task table 1190a6d42e7dSPeter Dunlap */ 1191a6d42e7dSPeter Dunlap 1192a6d42e7dSPeter Dunlap if (mdb_lookup_by_name("idm", &sym) == -1) { 1193a6d42e7dSPeter Dunlap mdb_warn("failed to find symbol 'idm'"); 1194a6d42e7dSPeter Dunlap return (DCMD_ERR); 1195a6d42e7dSPeter Dunlap } 1196a6d42e7dSPeter Dunlap 1197a6d42e7dSPeter Dunlap idm_global_addr = (uintptr_t)sym.st_value; 1198a6d42e7dSPeter Dunlap 1199a6d42e7dSPeter Dunlap if (mdb_vread(&task_ptr, sizeof (uintptr_t), 1200a6d42e7dSPeter Dunlap idm_global_addr + offsetof(idm_global_t, idm_taskid_table)) != 1201a6d42e7dSPeter Dunlap sizeof (uintptr_t)) { 1202a6d42e7dSPeter Dunlap mdb_warn("Failed to read address of task table"); 1203a6d42e7dSPeter Dunlap return (DCMD_ERR); 1204a6d42e7dSPeter Dunlap } 1205a6d42e7dSPeter Dunlap 1206a6d42e7dSPeter Dunlap /* 1207a6d42e7dSPeter Dunlap * Read idm_conn_t 1208a6d42e7dSPeter Dunlap */ 1209a6d42e7dSPeter Dunlap if (mdb_vread(&ic, sizeof (idm_conn_t), addr) != sizeof (idm_conn_t)) { 1210a6d42e7dSPeter Dunlap return (DCMD_ERR); 1211a6d42e7dSPeter Dunlap } 1212a6d42e7dSPeter Dunlap conn_type = (ic.ic_conn_type == CONN_TYPE_INI) ? "Ini" : 1213a6d42e7dSPeter Dunlap (ic.ic_conn_type == CONN_TYPE_TGT) ? "Tgt" : "Unk"; 1214a6d42e7dSPeter Dunlap 1215a6d42e7dSPeter Dunlap /* 1216a6d42e7dSPeter Dunlap * Brief output 1217a6d42e7dSPeter Dunlap * 1218a6d42e7dSPeter Dunlap * idm_conn_t pointer 1219a6d42e7dSPeter Dunlap * idm_conn_t.ic_conn_type 1220a6d42e7dSPeter Dunlap * idm_conn_t.ic_statet+idm_conn_t.ic_ffp 1221a6d42e7dSPeter Dunlap */ 1222a6d42e7dSPeter Dunlap 1223a6d42e7dSPeter Dunlap verbose = idc->idc_verbose; 1224a6d42e7dSPeter Dunlap states = idc->u.child.idc_states; 1225a6d42e7dSPeter Dunlap rc_audit = idc->u.child.idc_rc_audit; 1226a6d42e7dSPeter Dunlap 1227a6d42e7dSPeter Dunlap if (idc->u.child.idc_conn) { 1228a6d42e7dSPeter Dunlap if (idc->idc_verbose) { 1229a6d42e7dSPeter Dunlap mdb_printf("IDM Conn %p\n", addr); 1230a6d42e7dSPeter Dunlap if (ic.ic_conn_type == CONN_TYPE_TGT) { 1231a6d42e7dSPeter Dunlap iscsi_print_iscsit_conn_data(&ic); 1232a6d42e7dSPeter Dunlap } else { 1233a6d42e7dSPeter Dunlap iscsi_print_idm_conn_data(&ic); 1234a6d42e7dSPeter Dunlap } 1235a6d42e7dSPeter Dunlap } else { 1236a6d42e7dSPeter Dunlap /* Print connection data */ 1237a6d42e7dSPeter Dunlap if (idc->idc_header) { 1238a6d42e7dSPeter Dunlap mdb_printf("%<u>%-?s %-6s %-10s %12s%</u>\n", 1239a6d42e7dSPeter Dunlap "idm_conn_t", "Type", "Transport", 1240a6d42e7dSPeter Dunlap "State/FFP"); 1241a6d42e7dSPeter Dunlap } 1242a6d42e7dSPeter Dunlap mdb_printf("%?p %-6s %-10s %6d/%-6d\n", addr, conn_type, 1243a6d42e7dSPeter Dunlap (ic.ic_transport_type == 1244a6d42e7dSPeter Dunlap IDM_TRANSPORT_TYPE_ISER) ? "ISER_IB" : 1245a6d42e7dSPeter Dunlap (ic.ic_transport_type == 1246a6d42e7dSPeter Dunlap IDM_TRANSPORT_TYPE_SOCKETS) ? "SOCKETS" : 1247a6d42e7dSPeter Dunlap "N/A", 1248a6d42e7dSPeter Dunlap ic.ic_state, ic.ic_ffp); 1249a6d42e7dSPeter Dunlap if (idc->u.child.idc_print_ip) { 1250a6d42e7dSPeter Dunlap sa_to_str(&ic.ic_laddr, laddr); 1251a6d42e7dSPeter Dunlap sa_to_str(&ic.ic_raddr, raddr); 1252a6d42e7dSPeter Dunlap mdb_printf(" L%s R%s\n", 1253a6d42e7dSPeter Dunlap laddr, raddr); 1254a6d42e7dSPeter Dunlap } 1255a6d42e7dSPeter Dunlap } 1256a6d42e7dSPeter Dunlap } 1257a6d42e7dSPeter Dunlap idc->idc_header = 0; 1258a6d42e7dSPeter Dunlap 1259a6d42e7dSPeter Dunlap idc->idc_verbose = 0; 1260a6d42e7dSPeter Dunlap 1261a6d42e7dSPeter Dunlap /* 1262a6d42e7dSPeter Dunlap * Print states if requested 1263a6d42e7dSPeter Dunlap */ 1264a6d42e7dSPeter Dunlap if (states) { 1265a6d42e7dSPeter Dunlap states_addr = addr + offsetof(idm_conn_t, ic_state_audit); 1266a6d42e7dSPeter Dunlap 1267a6d42e7dSPeter Dunlap (void) mdb_inc_indent(4); 1268a6d42e7dSPeter Dunlap mdb_printf("State History:\n"); 1269a6d42e7dSPeter Dunlap if (iscsi_sm_audit_impl(states_addr) != DCMD_OK) 1270a6d42e7dSPeter Dunlap return (DCMD_ERR); 1271a6d42e7dSPeter Dunlap 1272a6d42e7dSPeter Dunlap /* Don't print state history for child objects */ 1273a6d42e7dSPeter Dunlap idc->u.child.idc_states = 0; 1274a6d42e7dSPeter Dunlap (void) mdb_dec_indent(4); 1275a6d42e7dSPeter Dunlap } 1276a6d42e7dSPeter Dunlap 1277a6d42e7dSPeter Dunlap /* 1278a6d42e7dSPeter Dunlap * Print refcnt audit data if requested 1279a6d42e7dSPeter Dunlap */ 1280a6d42e7dSPeter Dunlap if (rc_audit) { 1281a6d42e7dSPeter Dunlap (void) mdb_inc_indent(4); 1282a6d42e7dSPeter Dunlap mdb_printf("Reference History:\n"); 1283a6d42e7dSPeter Dunlap rc_addr = addr + offsetof(idm_conn_t, ic_refcnt); 1284a6d42e7dSPeter Dunlap if (iscsi_refcnt_impl(rc_addr) != DCMD_OK) 1285a6d42e7dSPeter Dunlap return (DCMD_ERR); 1286a6d42e7dSPeter Dunlap 1287a6d42e7dSPeter Dunlap /* Don't print audit data for child objects */ 1288a6d42e7dSPeter Dunlap idc->u.child.idc_rc_audit = 0; 1289a6d42e7dSPeter Dunlap (void) mdb_dec_indent(4); 1290a6d42e7dSPeter Dunlap } 1291a6d42e7dSPeter Dunlap 1292a6d42e7dSPeter Dunlap task_idx = 0; 1293a6d42e7dSPeter Dunlap 1294a6d42e7dSPeter Dunlap /* Any child objects to walk? */ 1295a6d42e7dSPeter Dunlap if (idc->u.child.idc_task || idc->u.child.idc_buffer) { 1296a6d42e7dSPeter Dunlap idc->idc_header = 1; 1297a6d42e7dSPeter Dunlap while (task_idx < IDM_TASKIDS_MAX) { 1298a6d42e7dSPeter Dunlap 1299a6d42e7dSPeter Dunlap /* 1300a6d42e7dSPeter Dunlap * Read the next idm_task_t 1301a6d42e7dSPeter Dunlap */ 1302a6d42e7dSPeter Dunlap 1303a6d42e7dSPeter Dunlap if (mdb_vread(&task_addr, sizeof (uintptr_t), 1304a6d42e7dSPeter Dunlap task_ptr) != sizeof (uintptr_t)) { 1305a6d42e7dSPeter Dunlap mdb_warn("Failed to read task pointer"); 1306a6d42e7dSPeter Dunlap return (DCMD_ERR); 1307a6d42e7dSPeter Dunlap } 1308a6d42e7dSPeter Dunlap 1309a6d42e7dSPeter Dunlap if (task_addr == NULL) { 1310a6d42e7dSPeter Dunlap task_ptr += sizeof (uintptr_t); 1311a6d42e7dSPeter Dunlap task_idx++; 1312a6d42e7dSPeter Dunlap continue; 1313a6d42e7dSPeter Dunlap } 1314a6d42e7dSPeter Dunlap 1315a6d42e7dSPeter Dunlap if (mdb_vread(&idt, sizeof (idm_task_t), task_addr) 1316a6d42e7dSPeter Dunlap != sizeof (idm_task_t)) { 1317a6d42e7dSPeter Dunlap mdb_warn("Failed to read task pointer"); 1318a6d42e7dSPeter Dunlap return (DCMD_ERR); 1319a6d42e7dSPeter Dunlap } 1320a6d42e7dSPeter Dunlap 1321a6d42e7dSPeter Dunlap if (((uintptr_t)idt.idt_ic == addr) && 1322a6d42e7dSPeter Dunlap (idt.idt_state != TASK_IDLE)) { 1323a6d42e7dSPeter Dunlap (void) mdb_inc_indent(4); 1324a6d42e7dSPeter Dunlap if (iscsi_i_task_impl(&idt, task_addr, idc) 1325a6d42e7dSPeter Dunlap == -1) { 1326a6d42e7dSPeter Dunlap mdb_warn("Failed to walk connection " 1327a6d42e7dSPeter Dunlap "task tree"); 1328a6d42e7dSPeter Dunlap (void) mdb_dec_indent(4); 1329a6d42e7dSPeter Dunlap return (DCMD_ERR); 1330a6d42e7dSPeter Dunlap } 1331a6d42e7dSPeter Dunlap (void) mdb_dec_indent(4); 1332a6d42e7dSPeter Dunlap } 1333a6d42e7dSPeter Dunlap 1334a6d42e7dSPeter Dunlap task_ptr += sizeof (uintptr_t); 1335a6d42e7dSPeter Dunlap task_idx++; 1336a6d42e7dSPeter Dunlap } 1337a6d42e7dSPeter Dunlap idc->idc_header = 0; 1338a6d42e7dSPeter Dunlap } 1339a6d42e7dSPeter Dunlap 1340a6d42e7dSPeter Dunlap idc->idc_verbose = verbose; 1341a6d42e7dSPeter Dunlap idc->u.child.idc_states = states; 1342a6d42e7dSPeter Dunlap idc->u.child.idc_rc_audit = rc_audit; 1343a6d42e7dSPeter Dunlap 1344a6d42e7dSPeter Dunlap return (DCMD_OK); 1345a6d42e7dSPeter Dunlap } 1346a6d42e7dSPeter Dunlap 1347a6d42e7dSPeter Dunlap static void 1348a6d42e7dSPeter Dunlap iscsi_print_iscsit_conn_data(idm_conn_t *ic) 1349a6d42e7dSPeter Dunlap { 1350a6d42e7dSPeter Dunlap iscsit_conn_t ict; 1351a6d42e7dSPeter Dunlap char *csg; 1352a6d42e7dSPeter Dunlap char *nsg; 1353a6d42e7dSPeter Dunlap 1354a6d42e7dSPeter Dunlap iscsi_print_idm_conn_data(ic); 1355a6d42e7dSPeter Dunlap 1356a6d42e7dSPeter Dunlap if (mdb_vread(&ict, sizeof (iscsit_conn_t), 1357a6d42e7dSPeter Dunlap (uintptr_t)ic->ic_handle) != sizeof (iscsit_conn_t)) { 1358a6d42e7dSPeter Dunlap mdb_printf("**Failed to read conn private data\n"); 1359a6d42e7dSPeter Dunlap return; 1360a6d42e7dSPeter Dunlap } 1361a6d42e7dSPeter Dunlap 1362a6d42e7dSPeter Dunlap if (ict.ict_login_sm.icl_login_state != ILS_LOGIN_DONE) { 1363a6d42e7dSPeter Dunlap switch (ict.ict_login_sm.icl_login_csg) { 1364a6d42e7dSPeter Dunlap case ISCSI_SECURITY_NEGOTIATION_STAGE: 1365a6d42e7dSPeter Dunlap csg = "Security"; 1366a6d42e7dSPeter Dunlap break; 1367a6d42e7dSPeter Dunlap case ISCSI_OP_PARMS_NEGOTIATION_STAGE: 1368a6d42e7dSPeter Dunlap csg = "Operational"; 1369a6d42e7dSPeter Dunlap break; 1370a6d42e7dSPeter Dunlap case ISCSI_FULL_FEATURE_PHASE: 1371a6d42e7dSPeter Dunlap csg = "FFP"; 1372a6d42e7dSPeter Dunlap break; 1373a6d42e7dSPeter Dunlap default: 1374a6d42e7dSPeter Dunlap csg = "Unknown"; 1375a6d42e7dSPeter Dunlap } 1376a6d42e7dSPeter Dunlap switch (ict.ict_login_sm.icl_login_nsg) { 1377a6d42e7dSPeter Dunlap case ISCSI_SECURITY_NEGOTIATION_STAGE: 1378a6d42e7dSPeter Dunlap nsg = "Security"; 1379a6d42e7dSPeter Dunlap break; 1380a6d42e7dSPeter Dunlap case ISCSI_OP_PARMS_NEGOTIATION_STAGE: 1381a6d42e7dSPeter Dunlap nsg = "Operational"; 1382a6d42e7dSPeter Dunlap break; 1383a6d42e7dSPeter Dunlap case ISCSI_FULL_FEATURE_PHASE: 1384a6d42e7dSPeter Dunlap nsg = "FFP"; 1385a6d42e7dSPeter Dunlap break; 1386a6d42e7dSPeter Dunlap default: 1387a6d42e7dSPeter Dunlap nsg = "Unknown"; 1388a6d42e7dSPeter Dunlap } 1389a6d42e7dSPeter Dunlap mdb_printf("%20s: %d\n", "Login State", 1390a6d42e7dSPeter Dunlap ict.ict_login_sm.icl_login_state); 1391a6d42e7dSPeter Dunlap mdb_printf("%20s: %d\n", "Login Last State", 1392a6d42e7dSPeter Dunlap ict.ict_login_sm.icl_login_last_state); 1393a6d42e7dSPeter Dunlap mdb_printf("%20s: %s\n", "CSG", csg); 1394a6d42e7dSPeter Dunlap mdb_printf("%20s: %s\n", "NSG", nsg); 1395a6d42e7dSPeter Dunlap mdb_printf("%20s: %d\n", "Transit", 1396a6d42e7dSPeter Dunlap ict.ict_login_sm.icl_login_transit >> 7); 1397a6d42e7dSPeter Dunlap mdb_printf("%20s: %p\n", "Request nvlist", 1398a6d42e7dSPeter Dunlap ict.ict_login_sm.icl_request_nvlist); 1399a6d42e7dSPeter Dunlap mdb_printf("%20s: %p\n", "Response nvlist", 1400a6d42e7dSPeter Dunlap ict.ict_login_sm.icl_response_nvlist); 1401a6d42e7dSPeter Dunlap mdb_printf("%20s: %p\n", "Negotiated nvlist", 1402a6d42e7dSPeter Dunlap ict.ict_login_sm.icl_negotiated_values); 1403a6d42e7dSPeter Dunlap if (ict.ict_login_sm.icl_login_state == ILS_LOGIN_ERROR) { 1404a6d42e7dSPeter Dunlap mdb_printf("%20s: 0x%02x\n", "Error Class", 1405a6d42e7dSPeter Dunlap ict.ict_login_sm.icl_login_resp_err_class); 1406a6d42e7dSPeter Dunlap mdb_printf("%20s: 0x%02x\n", "Error Detail", 1407a6d42e7dSPeter Dunlap ict.ict_login_sm.icl_login_resp_err_detail); 1408a6d42e7dSPeter Dunlap } 1409a6d42e7dSPeter Dunlap } 1410a6d42e7dSPeter Dunlap mdb_printf("%20s: 0x%04x\n", "CID", ict.ict_cid); 1411a6d42e7dSPeter Dunlap mdb_printf("%20s: 0x%08x\n", "StatSN", ict.ict_statsn); 1412a6d42e7dSPeter Dunlap } 1413a6d42e7dSPeter Dunlap 1414a6d42e7dSPeter Dunlap static void 1415a6d42e7dSPeter Dunlap iscsi_print_idm_conn_data(idm_conn_t *ic) 1416a6d42e7dSPeter Dunlap { 1417a6d42e7dSPeter Dunlap char laddr[PORTAL_STR_LEN]; 1418a6d42e7dSPeter Dunlap char raddr[PORTAL_STR_LEN]; 1419a6d42e7dSPeter Dunlap 1420a6d42e7dSPeter Dunlap sa_to_str(&ic->ic_laddr, laddr); 1421a6d42e7dSPeter Dunlap sa_to_str(&ic->ic_raddr, raddr); 1422a6d42e7dSPeter Dunlap 1423a6d42e7dSPeter Dunlap mdb_printf("%20s: %s\n", "Conn Type", 1424a6d42e7dSPeter Dunlap ((ic->ic_conn_type == CONN_TYPE_TGT) ? "Target" : 1425a6d42e7dSPeter Dunlap ((ic->ic_conn_type == CONN_TYPE_INI) ? "Initiator" : 1426a6d42e7dSPeter Dunlap "Unknown"))); 1427a6d42e7dSPeter Dunlap if (ic->ic_conn_type == CONN_TYPE_TGT) { 1428a6d42e7dSPeter Dunlap mdb_printf("%20s: %p\n", "Svc. Binding", 1429a6d42e7dSPeter Dunlap ic->ic_svc_binding); 1430a6d42e7dSPeter Dunlap } 1431a6d42e7dSPeter Dunlap mdb_printf("%20s: %s\n", "Transport", 1432a6d42e7dSPeter Dunlap (ic->ic_transport_type == IDM_TRANSPORT_TYPE_ISER) ? "ISER_IB" : 1433a6d42e7dSPeter Dunlap (ic->ic_transport_type == IDM_TRANSPORT_TYPE_SOCKETS) ? "SOCKETS" : 1434a6d42e7dSPeter Dunlap "N/A"); 1435a6d42e7dSPeter Dunlap 1436a6d42e7dSPeter Dunlap mdb_printf("%20s: %s\n", "Local IP", laddr); 1437a6d42e7dSPeter Dunlap mdb_printf("%20s: %s\n", "Remote IP", raddr); 1438a6d42e7dSPeter Dunlap mdb_printf("%20s: %d\n", "State", 1439a6d42e7dSPeter Dunlap ic->ic_state); 1440a6d42e7dSPeter Dunlap mdb_printf("%20s: %d\n", "Last State", 1441a6d42e7dSPeter Dunlap ic->ic_last_state); 1442a6d42e7dSPeter Dunlap mdb_printf("%20s: %d %s\n", "Refcount", 1443a6d42e7dSPeter Dunlap ic->ic_refcnt.ir_refcnt, 1444a6d42e7dSPeter Dunlap (ic->ic_refcnt.ir_waiting == REF_NOWAIT) ? "" : 1445a6d42e7dSPeter Dunlap ((ic->ic_refcnt.ir_waiting == REF_WAIT_SYNC) ? "REF_WAIT_SYNC" : 1446a6d42e7dSPeter Dunlap ((ic->ic_refcnt.ir_waiting == REF_WAIT_ASYNC) ? "REF_WAIT_ASYNC" : 1447a6d42e7dSPeter Dunlap "UNKNOWN"))); 1448a6d42e7dSPeter Dunlap } 1449a6d42e7dSPeter Dunlap 1450a6d42e7dSPeter Dunlap static int 1451a6d42e7dSPeter Dunlap iscsi_i_task_impl(idm_task_t *idt, uintptr_t addr, iscsi_dcmd_ctrl_t *idc) 1452a6d42e7dSPeter Dunlap { 1453a6d42e7dSPeter Dunlap uintptr_t list_addr, rc_addr; 1454a6d42e7dSPeter Dunlap idm_conn_type_t conn_type; 1455a6d42e7dSPeter Dunlap int verbose, states, rc_audit; 1456a6d42e7dSPeter Dunlap 1457a6d42e7dSPeter Dunlap conn_type = idm_conn_type((uintptr_t)idt->idt_ic); 1458a6d42e7dSPeter Dunlap 1459a6d42e7dSPeter Dunlap verbose = idc->idc_verbose; 1460a6d42e7dSPeter Dunlap states = idc->u.child.idc_states; 1461a6d42e7dSPeter Dunlap rc_audit = idc->u.child.idc_rc_audit; 1462a6d42e7dSPeter Dunlap 1463a6d42e7dSPeter Dunlap if (idc->u.child.idc_task) { 1464a6d42e7dSPeter Dunlap if (verbose) { 1465a6d42e7dSPeter Dunlap mdb_printf("Task %p\n", addr); 1466a6d42e7dSPeter Dunlap (void) mdb_inc_indent(2); 1467a6d42e7dSPeter Dunlap if (conn_type == CONN_TYPE_TGT) { 1468a6d42e7dSPeter Dunlap iscsi_print_iscsit_task_data(idt); 1469a6d42e7dSPeter Dunlap } 1470a6d42e7dSPeter Dunlap (void) mdb_dec_indent(2); 1471a6d42e7dSPeter Dunlap } else { 1472a6d42e7dSPeter Dunlap /* Print task data */ 1473a6d42e7dSPeter Dunlap if (idc->idc_header) { 1474a6d42e7dSPeter Dunlap mdb_printf( 1475bf604c64SPeter Dunlap "%<u>%-?s %-16s %-4s %-8s %-8s%</u>\n", 1476bf604c64SPeter Dunlap "Tasks:", "State", "Ref", 1477a6d42e7dSPeter Dunlap (conn_type == CONN_TYPE_TGT ? "TTT" : 1478a6d42e7dSPeter Dunlap (conn_type == CONN_TYPE_INI ? "ITT" : 1479a6d42e7dSPeter Dunlap "TT")), "Handle"); 1480a6d42e7dSPeter Dunlap } 1481bf604c64SPeter Dunlap mdb_printf("%?p %-16s %04x %08x %08x\n", addr, 1482bf604c64SPeter Dunlap idm_ts_name[idt->idt_state], 1483bf604c64SPeter Dunlap idt->idt_refcnt.ir_refcnt, 1484bf604c64SPeter Dunlap idt->idt_tt, idt->idt_client_handle); 1485a6d42e7dSPeter Dunlap } 1486a6d42e7dSPeter Dunlap } 1487a6d42e7dSPeter Dunlap idc->idc_header = 0; 1488a6d42e7dSPeter Dunlap idc->idc_verbose = 0; 1489a6d42e7dSPeter Dunlap 1490a6d42e7dSPeter Dunlap /* 1491a6d42e7dSPeter Dunlap * Print states if requested 1492a6d42e7dSPeter Dunlap */ 1493a6d42e7dSPeter Dunlap #if 0 1494a6d42e7dSPeter Dunlap if (states) { 1495a6d42e7dSPeter Dunlap states_addr = addr + offsetof(idm_task_t, idt_state_audit); 1496a6d42e7dSPeter Dunlap 1497a6d42e7dSPeter Dunlap (void) mdb_inc_indent(4); 1498a6d42e7dSPeter Dunlap mdb_printf("State History:\n"); 1499a6d42e7dSPeter Dunlap if (iscsi_sm_audit_impl(states_addr) != DCMD_OK) 1500a6d42e7dSPeter Dunlap return (DCMD_ERR); 1501a6d42e7dSPeter Dunlap 1502a6d42e7dSPeter Dunlap /* Don't print state history for child objects */ 1503a6d42e7dSPeter Dunlap idc->u.child.idc_states = 0; 1504a6d42e7dSPeter Dunlap (void) mdb_dec_indent(4); 1505a6d42e7dSPeter Dunlap } 1506a6d42e7dSPeter Dunlap #endif 1507a6d42e7dSPeter Dunlap 1508a6d42e7dSPeter Dunlap /* 1509a6d42e7dSPeter Dunlap * Print refcnt audit data if requested 1510a6d42e7dSPeter Dunlap */ 1511a6d42e7dSPeter Dunlap if (rc_audit) { 1512a6d42e7dSPeter Dunlap (void) mdb_inc_indent(4); 1513a6d42e7dSPeter Dunlap mdb_printf("Reference History:\n"); 1514a6d42e7dSPeter Dunlap rc_addr = addr + 1515a6d42e7dSPeter Dunlap offsetof(idm_task_t, idt_refcnt); 1516a6d42e7dSPeter Dunlap if (iscsi_refcnt_impl(rc_addr) != DCMD_OK) 1517a6d42e7dSPeter Dunlap return (DCMD_ERR); 1518a6d42e7dSPeter Dunlap 1519a6d42e7dSPeter Dunlap /* Don't print audit data for child objects */ 1520a6d42e7dSPeter Dunlap idc->u.child.idc_rc_audit = 0; 1521a6d42e7dSPeter Dunlap (void) mdb_dec_indent(4); 1522a6d42e7dSPeter Dunlap } 1523a6d42e7dSPeter Dunlap 1524a6d42e7dSPeter Dunlap 1525a6d42e7dSPeter Dunlap /* Buffers are leaf objects */ 1526a6d42e7dSPeter Dunlap if (idc->u.child.idc_buffer) { 1527a6d42e7dSPeter Dunlap /* Walk in buffer list */ 1528a6d42e7dSPeter Dunlap (void) mdb_inc_indent(2); 1529a6d42e7dSPeter Dunlap mdb_printf("In buffers:\n"); 1530a6d42e7dSPeter Dunlap idc->idc_header = 1; 1531a6d42e7dSPeter Dunlap (void) mdb_inc_indent(2); 1532a6d42e7dSPeter Dunlap list_addr = addr + offsetof(idm_task_t, idt_inbufv); 1533a6d42e7dSPeter Dunlap if (mdb_pwalk("list", iscsi_buffer_walk_cb, idc, list_addr) == 1534a6d42e7dSPeter Dunlap -1) { 1535a6d42e7dSPeter Dunlap mdb_warn("list walk failed for task in buffers"); 1536a6d42e7dSPeter Dunlap (void) mdb_dec_indent(4); 1537a6d42e7dSPeter Dunlap return (DCMD_ERR); 1538a6d42e7dSPeter Dunlap } 1539a6d42e7dSPeter Dunlap (void) mdb_dec_indent(2); 1540a6d42e7dSPeter Dunlap /* Walk out buffer list */ 1541a6d42e7dSPeter Dunlap mdb_printf("Out buffers:\n"); 1542a6d42e7dSPeter Dunlap idc->idc_header = 1; 1543a6d42e7dSPeter Dunlap (void) mdb_inc_indent(2); 1544a6d42e7dSPeter Dunlap list_addr = addr + offsetof(idm_task_t, idt_outbufv); 1545a6d42e7dSPeter Dunlap if (mdb_pwalk("list", iscsi_buffer_walk_cb, idc, list_addr) == 1546a6d42e7dSPeter Dunlap -1) { 1547a6d42e7dSPeter Dunlap mdb_warn("list walk failed for task out buffers\n"); 1548a6d42e7dSPeter Dunlap (void) mdb_dec_indent(2); 1549a6d42e7dSPeter Dunlap return (DCMD_ERR); 1550a6d42e7dSPeter Dunlap } 1551a6d42e7dSPeter Dunlap (void) mdb_dec_indent(4); 1552a6d42e7dSPeter Dunlap } 1553a6d42e7dSPeter Dunlap 1554a6d42e7dSPeter Dunlap idc->idc_verbose = verbose; 1555a6d42e7dSPeter Dunlap idc->u.child.idc_states = states; 1556a6d42e7dSPeter Dunlap idc->u.child.idc_rc_audit = rc_audit; 1557a6d42e7dSPeter Dunlap 1558a6d42e7dSPeter Dunlap return (DCMD_OK); 1559a6d42e7dSPeter Dunlap } 1560a6d42e7dSPeter Dunlap 1561a6d42e7dSPeter Dunlap static int 1562a6d42e7dSPeter Dunlap iscsi_task_impl(uintptr_t addr, iscsi_dcmd_ctrl_t *idc) 1563a6d42e7dSPeter Dunlap { 1564a6d42e7dSPeter Dunlap idm_task_t idt; 1565a6d42e7dSPeter Dunlap 1566a6d42e7dSPeter Dunlap /* 1567a6d42e7dSPeter Dunlap * Read idm_conn_t 1568a6d42e7dSPeter Dunlap */ 1569a6d42e7dSPeter Dunlap if (mdb_vread(&idt, sizeof (idm_task_t), addr) != sizeof (idm_task_t)) { 1570a6d42e7dSPeter Dunlap return (DCMD_ERR); 1571a6d42e7dSPeter Dunlap } 1572a6d42e7dSPeter Dunlap 1573a6d42e7dSPeter Dunlap return (iscsi_i_task_impl(&idt, addr, idc)); 1574a6d42e7dSPeter Dunlap } 1575a6d42e7dSPeter Dunlap 1576a6d42e7dSPeter Dunlap #define ISCSI_CDB_INDENT 16 1577a6d42e7dSPeter Dunlap 1578a6d42e7dSPeter Dunlap static void 1579a6d42e7dSPeter Dunlap iscsi_print_iscsit_task_data(idm_task_t *idt) 1580a6d42e7dSPeter Dunlap { 1581a6d42e7dSPeter Dunlap iscsit_task_t itask; 1582a6d42e7dSPeter Dunlap boolean_t good_scsi_task = B_TRUE; 1583a6d42e7dSPeter Dunlap scsi_task_t scsi_task; 1584a6d42e7dSPeter Dunlap 1585a6d42e7dSPeter Dunlap if (mdb_vread(&itask, sizeof (iscsit_task_t), 1586a6d42e7dSPeter Dunlap (uintptr_t)idt->idt_private) != sizeof (iscsit_task_t)) { 1587a6d42e7dSPeter Dunlap mdb_printf("**Failed to read idt_private data\n"); 1588a6d42e7dSPeter Dunlap return; 1589a6d42e7dSPeter Dunlap } 1590a6d42e7dSPeter Dunlap 1591a6d42e7dSPeter Dunlap if (mdb_vread(&scsi_task, sizeof (scsi_task_t), 1592a6d42e7dSPeter Dunlap (uintptr_t)itask.it_stmf_task) != sizeof (scsi_task_t)) { 1593a6d42e7dSPeter Dunlap good_scsi_task = B_FALSE; 1594a6d42e7dSPeter Dunlap } 1595a6d42e7dSPeter Dunlap 1596bf604c64SPeter Dunlap mdb_printf("%20s: %s(%d)\n", "State", 1597bf604c64SPeter Dunlap idt->idt_state > TASK_MAX_STATE ? 1598bf604c64SPeter Dunlap "UNKNOWN" : idm_ts_name[idt->idt_state], 1599bf604c64SPeter Dunlap idt->idt_state); 1600bf604c64SPeter Dunlap mdb_printf("%20s: %d/%d\n", "STMF abort/IDM aborted", 1601bf604c64SPeter Dunlap itask.it_stmf_abort, itask.it_aborted); 1602a6d42e7dSPeter Dunlap mdb_printf("%20s: %p/%p/%p%s\n", 1603a6d42e7dSPeter Dunlap "iscsit/STMF/LU", idt->idt_private, 1604a6d42e7dSPeter Dunlap itask.it_stmf_task, good_scsi_task ? scsi_task.task_lu_private : 0, 1605a6d42e7dSPeter Dunlap good_scsi_task ? "" : "**"); 1606a6d42e7dSPeter Dunlap if (good_scsi_task) { 1607a6d42e7dSPeter Dunlap mdb_printf("%20s: %08x/%08x\n", "ITT/TTT", 1608a6d42e7dSPeter Dunlap itask.it_itt, itask.it_ttt); 1609a6d42e7dSPeter Dunlap mdb_printf("%20s: %08x\n", "CmdSN", 1610a6d42e7dSPeter Dunlap itask.it_cmdsn); 1611a6d42e7dSPeter Dunlap mdb_printf("%20s: %02x %02x %02x %02x %02x %02x %02x %02x\n", 1612a6d42e7dSPeter Dunlap "LU number", 1613a6d42e7dSPeter Dunlap scsi_task.task_lun_no[0], scsi_task.task_lun_no[1], 1614a6d42e7dSPeter Dunlap scsi_task.task_lun_no[2], scsi_task.task_lun_no[3], 1615a6d42e7dSPeter Dunlap scsi_task.task_lun_no[4], scsi_task.task_lun_no[5], 1616a6d42e7dSPeter Dunlap scsi_task.task_lun_no[6], scsi_task.task_lun_no[7]); 1617bf604c64SPeter Dunlap mdb_printf(" CDB (%d bytes):\n", 1618a6d42e7dSPeter Dunlap scsi_task.task_cdb_length); 1619a6d42e7dSPeter Dunlap (void) mdb_inc_indent(ISCSI_CDB_INDENT); 1620a6d42e7dSPeter Dunlap if (mdb_dumpptr((uintptr_t)scsi_task.task_cdb, 1621a6d42e7dSPeter Dunlap scsi_task.task_cdb_length, 1622a6d42e7dSPeter Dunlap MDB_DUMP_RELATIVE | MDB_DUMP_TRIM | 1623a6d42e7dSPeter Dunlap MDB_DUMP_GROUP(1), 1624a6d42e7dSPeter Dunlap (mdb_dumpptr_cb_t)mdb_vread, NULL)) { 1625a6d42e7dSPeter Dunlap mdb_printf("** Invalid CDB addr (%p)\n", 1626a6d42e7dSPeter Dunlap scsi_task.task_cdb); 1627a6d42e7dSPeter Dunlap } 1628a6d42e7dSPeter Dunlap (void) mdb_dec_indent(ISCSI_CDB_INDENT); 1629a6d42e7dSPeter Dunlap mdb_printf("%20s: %d/%d\n", "STMF cur/max bufs", 1630a6d42e7dSPeter Dunlap scsi_task.task_cur_nbufs, 1631a6d42e7dSPeter Dunlap scsi_task.task_max_nbufs); 1632a6d42e7dSPeter Dunlap mdb_printf("%20s: 0x%08x/0x%08x/0x%08x\n", "Bytes Exp/Cmd/Done", 1633a6d42e7dSPeter Dunlap scsi_task.task_expected_xfer_length, 1634a6d42e7dSPeter Dunlap scsi_task.task_cmd_xfer_length, 1635a6d42e7dSPeter Dunlap scsi_task.task_nbytes_transferred); 1636a6d42e7dSPeter Dunlap mdb_printf("%20s: 0x%x/0x%x\n", "TX-ini start/done", 1637a6d42e7dSPeter Dunlap idt->idt_tx_to_ini_start, 1638a6d42e7dSPeter Dunlap idt->idt_tx_to_ini_done); 1639a6d42e7dSPeter Dunlap mdb_printf("%20s: 0x%x/0x%x\n", "RX-ini start/done", 1640a6d42e7dSPeter Dunlap idt->idt_rx_from_ini_start, 1641a6d42e7dSPeter Dunlap idt->idt_rx_from_ini_done); 1642a6d42e7dSPeter Dunlap } 1643a6d42e7dSPeter Dunlap } 1644a6d42e7dSPeter Dunlap 1645a6d42e7dSPeter Dunlap static int 1646a6d42e7dSPeter Dunlap iscsi_buffer_impl(uintptr_t addr, iscsi_dcmd_ctrl_t *idc) 1647a6d42e7dSPeter Dunlap { 1648a6d42e7dSPeter Dunlap idm_buf_t idb; 1649a6d42e7dSPeter Dunlap 1650a6d42e7dSPeter Dunlap /* 1651a6d42e7dSPeter Dunlap * Read idm_buf_t 1652a6d42e7dSPeter Dunlap */ 1653a6d42e7dSPeter Dunlap if (mdb_vread(&idb, sizeof (idm_buf_t), addr) != sizeof (idm_buf_t)) { 1654a6d42e7dSPeter Dunlap return (DCMD_ERR); 1655a6d42e7dSPeter Dunlap } 1656a6d42e7dSPeter Dunlap 1657a6d42e7dSPeter Dunlap 1658a6d42e7dSPeter Dunlap if (idc->idc_header) { 1659a6d42e7dSPeter Dunlap mdb_printf("%<u>%-?s %?s/%-8s %8s %8s %8s%</u>\n", 1660a6d42e7dSPeter Dunlap "idm_buf_t", "Mem Rgn", "Length", 1661a6d42e7dSPeter Dunlap "Rel Off", "Xfer Len", "Exp. Off"); 1662a6d42e7dSPeter Dunlap } 1663a6d42e7dSPeter Dunlap idc->idc_header = 0; 1664a6d42e7dSPeter Dunlap 1665a6d42e7dSPeter Dunlap /* Print buffer data */ 1666a6d42e7dSPeter Dunlap mdb_printf("%?p %?p/%08x %8x %8x %08x\n", addr, 1667a6d42e7dSPeter Dunlap idb.idb_buf, idb.idb_buflen, 1668a6d42e7dSPeter Dunlap idb.idb_bufoffset, idb.idb_xfer_len, 1669a6d42e7dSPeter Dunlap idb.idb_exp_offset); 1670a6d42e7dSPeter Dunlap 1671a6d42e7dSPeter Dunlap 1672a6d42e7dSPeter Dunlap /* Buffers are leaf objects */ 1673a6d42e7dSPeter Dunlap 1674a6d42e7dSPeter Dunlap return (DCMD_OK); 1675a6d42e7dSPeter Dunlap } 1676a6d42e7dSPeter Dunlap 1677a6d42e7dSPeter Dunlap static int 1678a6d42e7dSPeter Dunlap iscsi_refcnt_impl(uintptr_t addr) 1679a6d42e7dSPeter Dunlap { 1680a6d42e7dSPeter Dunlap idm_refcnt_t refcnt; 1681a6d42e7dSPeter Dunlap refcnt_audit_buf_t *anb; 1682a6d42e7dSPeter Dunlap int ctr; 1683a6d42e7dSPeter Dunlap 1684a6d42e7dSPeter Dunlap /* 1685a6d42e7dSPeter Dunlap * Print refcnt info 1686a6d42e7dSPeter Dunlap */ 1687a6d42e7dSPeter Dunlap if (mdb_vread(&refcnt, sizeof (idm_refcnt_t), addr) != 1688a6d42e7dSPeter Dunlap sizeof (idm_refcnt_t)) { 1689a6d42e7dSPeter Dunlap return (DCMD_ERR); 1690a6d42e7dSPeter Dunlap } 1691a6d42e7dSPeter Dunlap 1692a6d42e7dSPeter Dunlap anb = &refcnt.ir_audit_buf; 1693a6d42e7dSPeter Dunlap 1694a6d42e7dSPeter Dunlap ctr = anb->anb_max_index + 1; 1695a6d42e7dSPeter Dunlap anb->anb_index--; 1696a6d42e7dSPeter Dunlap anb->anb_index &= anb->anb_max_index; 1697a6d42e7dSPeter Dunlap 1698a6d42e7dSPeter Dunlap while (ctr) { 1699a6d42e7dSPeter Dunlap refcnt_audit_record_t *anr; 1700a6d42e7dSPeter Dunlap 1701a6d42e7dSPeter Dunlap anr = anb->anb_records + anb->anb_index; 1702a6d42e7dSPeter Dunlap 1703a6d42e7dSPeter Dunlap if (anr->anr_depth) { 1704a6d42e7dSPeter Dunlap char c[MDB_SYM_NAMLEN]; 1705a6d42e7dSPeter Dunlap GElf_Sym sym; 1706a6d42e7dSPeter Dunlap int i; 1707a6d42e7dSPeter Dunlap 1708a6d42e7dSPeter Dunlap mdb_printf("\nRefCnt: %u\t", anr->anr_refcnt); 1709a6d42e7dSPeter Dunlap 1710a6d42e7dSPeter Dunlap for (i = 0; i < anr->anr_depth; i++) { 1711a6d42e7dSPeter Dunlap if (mdb_lookup_by_addr(anr->anr_stack[i], 1712a6d42e7dSPeter Dunlap MDB_SYM_FUZZY, c, sizeof (c), 1713a6d42e7dSPeter Dunlap &sym) == -1) { 1714a6d42e7dSPeter Dunlap continue; 1715a6d42e7dSPeter Dunlap } 1716a6d42e7dSPeter Dunlap mdb_printf("%s+0x%1x", c, 1717a6d42e7dSPeter Dunlap anr->anr_stack[i] - 1718a6d42e7dSPeter Dunlap (uintptr_t)sym.st_value); 1719a6d42e7dSPeter Dunlap ++i; 1720a6d42e7dSPeter Dunlap break; 1721a6d42e7dSPeter Dunlap } 1722a6d42e7dSPeter Dunlap 1723a6d42e7dSPeter Dunlap while (i < anr->anr_depth) { 1724a6d42e7dSPeter Dunlap if (mdb_lookup_by_addr(anr->anr_stack[i], 1725a6d42e7dSPeter Dunlap MDB_SYM_FUZZY, c, sizeof (c), 1726a6d42e7dSPeter Dunlap &sym) == -1) { 1727a6d42e7dSPeter Dunlap ++i; 1728a6d42e7dSPeter Dunlap continue; 1729a6d42e7dSPeter Dunlap } 1730a6d42e7dSPeter Dunlap mdb_printf("\n\t\t%s+0x%1x", c, 1731a6d42e7dSPeter Dunlap anr->anr_stack[i] - 1732a6d42e7dSPeter Dunlap (uintptr_t)sym.st_value); 1733a6d42e7dSPeter Dunlap ++i; 1734a6d42e7dSPeter Dunlap } 1735a6d42e7dSPeter Dunlap mdb_printf("\n"); 1736a6d42e7dSPeter Dunlap } 1737a6d42e7dSPeter Dunlap anb->anb_index--; 1738a6d42e7dSPeter Dunlap anb->anb_index &= anb->anb_max_index; 1739a6d42e7dSPeter Dunlap ctr--; 1740a6d42e7dSPeter Dunlap } 1741a6d42e7dSPeter Dunlap 1742a6d42e7dSPeter Dunlap return (DCMD_OK); 1743a6d42e7dSPeter Dunlap } 1744a6d42e7dSPeter Dunlap 1745a6d42e7dSPeter Dunlap static int 1746a6d42e7dSPeter Dunlap iscsi_sm_audit_impl(uintptr_t addr) 1747a6d42e7dSPeter Dunlap { 1748a6d42e7dSPeter Dunlap sm_audit_buf_t audit_buf; 1749a6d42e7dSPeter Dunlap int ctr; 1750a6d42e7dSPeter Dunlap const char *event_name; 1751a6d42e7dSPeter Dunlap const char *state_name; 1752a6d42e7dSPeter Dunlap const char *new_state_name; 1753a6d42e7dSPeter Dunlap char ts_string[40]; 1754a6d42e7dSPeter Dunlap /* 1755a6d42e7dSPeter Dunlap * Print refcnt info 1756a6d42e7dSPeter Dunlap */ 1757a6d42e7dSPeter Dunlap if (mdb_vread(&audit_buf, sizeof (sm_audit_buf_t), addr) != 1758a6d42e7dSPeter Dunlap sizeof (sm_audit_buf_t)) { 1759a6d42e7dSPeter Dunlap return (DCMD_ERR); 1760a6d42e7dSPeter Dunlap } 1761a6d42e7dSPeter Dunlap 1762a6d42e7dSPeter Dunlap ctr = audit_buf.sab_max_index + 1; 1763a6d42e7dSPeter Dunlap audit_buf.sab_index++; 1764a6d42e7dSPeter Dunlap audit_buf.sab_index &= audit_buf.sab_max_index; 1765a6d42e7dSPeter Dunlap 1766a6d42e7dSPeter Dunlap while (ctr) { 1767a6d42e7dSPeter Dunlap sm_audit_record_t *sar; 1768a6d42e7dSPeter Dunlap 1769a6d42e7dSPeter Dunlap sar = audit_buf.sab_records + audit_buf.sab_index; 1770a6d42e7dSPeter Dunlap 1771a6d42e7dSPeter Dunlap iscsi_format_timestamp(ts_string, 40, &sar->sar_timestamp); 1772a6d42e7dSPeter Dunlap 1773a6d42e7dSPeter Dunlap switch (sar->sar_type) { 1774a6d42e7dSPeter Dunlap case SAR_STATE_EVENT: 1775a6d42e7dSPeter Dunlap switch (sar->sar_sm_type) { 1776a6d42e7dSPeter Dunlap case SAS_IDM_CONN: 1777a6d42e7dSPeter Dunlap state_name = 1778a6d42e7dSPeter Dunlap iscsi_idm_conn_state(sar->sar_state); 1779a6d42e7dSPeter Dunlap event_name = 1780a6d42e7dSPeter Dunlap iscsi_idm_conn_event(sar->sar_event); 1781a6d42e7dSPeter Dunlap break; 1782a6d42e7dSPeter Dunlap case SAS_ISCSIT_TGT: 1783a6d42e7dSPeter Dunlap state_name = 1784a6d42e7dSPeter Dunlap iscsi_iscsit_tgt_state(sar->sar_state); 1785a6d42e7dSPeter Dunlap event_name = 1786a6d42e7dSPeter Dunlap iscsi_iscsit_tgt_event(sar->sar_event); 1787a6d42e7dSPeter Dunlap break; 1788a6d42e7dSPeter Dunlap case SAS_ISCSIT_SESS: 1789a6d42e7dSPeter Dunlap state_name = 1790a6d42e7dSPeter Dunlap iscsi_iscsit_sess_state(sar->sar_state); 1791a6d42e7dSPeter Dunlap event_name = 1792a6d42e7dSPeter Dunlap iscsi_iscsit_sess_event(sar->sar_event); 1793a6d42e7dSPeter Dunlap break; 1794a6d42e7dSPeter Dunlap case SAS_ISCSIT_LOGIN: 1795a6d42e7dSPeter Dunlap state_name = 1796a6d42e7dSPeter Dunlap iscsi_iscsit_login_state(sar->sar_state); 1797a6d42e7dSPeter Dunlap event_name = 1798a6d42e7dSPeter Dunlap iscsi_iscsit_login_event(sar->sar_event); 1799a6d42e7dSPeter Dunlap break; 180030e7468fSPeter Dunlap case SAS_ISCSI_CMD: 180130e7468fSPeter Dunlap state_name = 180230e7468fSPeter Dunlap iscsi_iscsi_cmd_state(sar->sar_state); 180330e7468fSPeter Dunlap event_name= 180430e7468fSPeter Dunlap iscsi_iscsi_cmd_event(sar->sar_event); 180530e7468fSPeter Dunlap break; 180630e7468fSPeter Dunlap case SAS_ISCSI_SESS: 180730e7468fSPeter Dunlap state_name = 180830e7468fSPeter Dunlap iscsi_iscsi_sess_state(sar->sar_state); 180930e7468fSPeter Dunlap event_name= 181030e7468fSPeter Dunlap iscsi_iscsi_sess_event(sar->sar_event); 181130e7468fSPeter Dunlap break; 1812a6d42e7dSPeter Dunlap default: 1813a6d42e7dSPeter Dunlap state_name = event_name = "N/A"; 1814a6d42e7dSPeter Dunlap break; 1815a6d42e7dSPeter Dunlap } 1816a6d42e7dSPeter Dunlap mdb_printf("%s|%s (%d)\n\t%9s %s (%d) %p\n", 1817a6d42e7dSPeter Dunlap ts_string, state_name, sar->sar_state, 1818a6d42e7dSPeter Dunlap "Event", event_name, 1819a6d42e7dSPeter Dunlap sar->sar_event, sar->sar_event_info); 1820a6d42e7dSPeter Dunlap 1821a6d42e7dSPeter Dunlap break; 1822a6d42e7dSPeter Dunlap case SAR_STATE_CHANGE: 1823a6d42e7dSPeter Dunlap switch (sar->sar_sm_type) { 1824a6d42e7dSPeter Dunlap case SAS_IDM_CONN: 1825a6d42e7dSPeter Dunlap state_name = 1826a6d42e7dSPeter Dunlap iscsi_idm_conn_state(sar->sar_state); 1827a6d42e7dSPeter Dunlap new_state_name = 1828a6d42e7dSPeter Dunlap iscsi_idm_conn_state(sar->sar_new_state); 1829a6d42e7dSPeter Dunlap break; 1830a6d42e7dSPeter Dunlap case SAS_IDM_TASK: 1831a6d42e7dSPeter Dunlap state_name = 1832a6d42e7dSPeter Dunlap iscsi_idm_task_state(sar->sar_state); 1833a6d42e7dSPeter Dunlap new_state_name = 1834a6d42e7dSPeter Dunlap iscsi_idm_task_state(sar->sar_new_state); 1835a6d42e7dSPeter Dunlap break; 1836a6d42e7dSPeter Dunlap case SAS_ISCSIT_TGT: 1837a6d42e7dSPeter Dunlap state_name = 1838a6d42e7dSPeter Dunlap iscsi_iscsit_tgt_state(sar->sar_state); 1839a6d42e7dSPeter Dunlap new_state_name = 1840a6d42e7dSPeter Dunlap iscsi_iscsit_tgt_state(sar->sar_new_state); 1841a6d42e7dSPeter Dunlap break; 1842a6d42e7dSPeter Dunlap case SAS_ISCSIT_SESS: 1843a6d42e7dSPeter Dunlap state_name = 1844a6d42e7dSPeter Dunlap iscsi_iscsit_sess_state(sar->sar_state); 1845a6d42e7dSPeter Dunlap new_state_name = 1846a6d42e7dSPeter Dunlap iscsi_iscsit_sess_state(sar->sar_new_state); 1847a6d42e7dSPeter Dunlap break; 1848a6d42e7dSPeter Dunlap case SAS_ISCSIT_LOGIN: 1849a6d42e7dSPeter Dunlap state_name = 1850a6d42e7dSPeter Dunlap iscsi_iscsit_login_state(sar->sar_state); 1851a6d42e7dSPeter Dunlap new_state_name = 1852a6d42e7dSPeter Dunlap iscsi_iscsit_login_state( 1853a6d42e7dSPeter Dunlap sar->sar_new_state); 1854a6d42e7dSPeter Dunlap break; 185530e7468fSPeter Dunlap case SAS_ISCSI_CMD: 185630e7468fSPeter Dunlap state_name = 185730e7468fSPeter Dunlap iscsi_iscsi_cmd_state(sar->sar_state); 185830e7468fSPeter Dunlap new_state_name= 185930e7468fSPeter Dunlap iscsi_iscsi_cmd_state(sar->sar_new_state); 186030e7468fSPeter Dunlap break; 186130e7468fSPeter Dunlap case SAS_ISCSI_SESS: 186230e7468fSPeter Dunlap state_name = 186330e7468fSPeter Dunlap iscsi_iscsi_sess_state(sar->sar_state); 186430e7468fSPeter Dunlap new_state_name= 186530e7468fSPeter Dunlap iscsi_iscsi_sess_state(sar->sar_new_state); 186630e7468fSPeter Dunlap break; 186730e7468fSPeter Dunlap case SAS_ISCSI_CONN: 186830e7468fSPeter Dunlap state_name = 186930e7468fSPeter Dunlap iscsi_iscsi_conn_state(sar->sar_state); 187030e7468fSPeter Dunlap new_state_name= 187130e7468fSPeter Dunlap iscsi_iscsi_conn_state(sar->sar_new_state); 187230e7468fSPeter Dunlap break; 187330e7468fSPeter Dunlap case SAS_ISCSI_LOGIN: 187430e7468fSPeter Dunlap state_name = 187530e7468fSPeter Dunlap iscsi_iscsi_login_state(sar->sar_state); 187630e7468fSPeter Dunlap new_state_name= 187730e7468fSPeter Dunlap iscsi_iscsi_login_state(sar->sar_new_state); 187830e7468fSPeter Dunlap break; 1879a6d42e7dSPeter Dunlap default: 1880a6d42e7dSPeter Dunlap break; 1881a6d42e7dSPeter Dunlap } 1882a6d42e7dSPeter Dunlap mdb_printf("%s|%s (%d)\n\t%9s %s (%d)\n", 1883a6d42e7dSPeter Dunlap ts_string, state_name, sar->sar_state, 1884a6d42e7dSPeter Dunlap "New State", new_state_name, sar->sar_new_state); 1885a6d42e7dSPeter Dunlap default: 1886a6d42e7dSPeter Dunlap state_name = new_state_name = "N/A"; 1887a6d42e7dSPeter Dunlap break; 1888a6d42e7dSPeter Dunlap } 1889a6d42e7dSPeter Dunlap 1890a6d42e7dSPeter Dunlap audit_buf.sab_index++; 1891a6d42e7dSPeter Dunlap audit_buf.sab_index &= audit_buf.sab_max_index; 1892a6d42e7dSPeter Dunlap ctr--; 1893a6d42e7dSPeter Dunlap } 1894a6d42e7dSPeter Dunlap 1895a6d42e7dSPeter Dunlap return (DCMD_OK); 1896a6d42e7dSPeter Dunlap } 1897a6d42e7dSPeter Dunlap 1898a6d42e7dSPeter Dunlap static const char * 189930e7468fSPeter Dunlap iscsi_idm_conn_event(unsigned int event) 1900a6d42e7dSPeter Dunlap { 190130e7468fSPeter Dunlap return ((event < CE_MAX_EVENT) ? idm_ce_name[event] : "N/A"); 1902a6d42e7dSPeter Dunlap } 1903a6d42e7dSPeter Dunlap 1904a6d42e7dSPeter Dunlap static const char * 190530e7468fSPeter Dunlap iscsi_iscsit_tgt_event(unsigned int event) 1906a6d42e7dSPeter Dunlap { 190730e7468fSPeter Dunlap return ((event < TE_MAX_EVENT) ? iscsit_te_name[event] : "N/A"); 1908a6d42e7dSPeter Dunlap } 1909a6d42e7dSPeter Dunlap 1910a6d42e7dSPeter Dunlap static const char * 191130e7468fSPeter Dunlap iscsi_iscsit_sess_event(unsigned int event) 1912a6d42e7dSPeter Dunlap { 191330e7468fSPeter Dunlap return ((event < SE_MAX_EVENT) ? iscsit_se_name[event] : "N/A"); 1914a6d42e7dSPeter Dunlap } 1915a6d42e7dSPeter Dunlap 1916a6d42e7dSPeter Dunlap static const char * 191730e7468fSPeter Dunlap iscsi_iscsit_login_event(unsigned int event) 1918a6d42e7dSPeter Dunlap { 191930e7468fSPeter Dunlap return ((event < ILE_MAX_EVENT) ? iscsit_ile_name[event] : "N/A"); 192030e7468fSPeter Dunlap } 1921a6d42e7dSPeter Dunlap 192230e7468fSPeter Dunlap static const char * 192330e7468fSPeter Dunlap iscsi_iscsi_cmd_event(unsigned int event) 192430e7468fSPeter Dunlap { 192530e7468fSPeter Dunlap return ((event < ISCSI_CMD_EVENT_MAX) ? 192630e7468fSPeter Dunlap iscsi_cmd_event_names[event] : "N/A"); 1927a6d42e7dSPeter Dunlap } 1928a6d42e7dSPeter Dunlap 1929a6d42e7dSPeter Dunlap static const char * 193030e7468fSPeter Dunlap iscsi_iscsi_sess_event(unsigned int event) 1931a6d42e7dSPeter Dunlap { 1932a6d42e7dSPeter Dunlap 193330e7468fSPeter Dunlap return ((event < ISCSI_SESS_EVENT_MAX) ? 193430e7468fSPeter Dunlap iscsi_sess_event_names[event] : "N/A"); 193530e7468fSPeter Dunlap } 1936a6d42e7dSPeter Dunlap 193730e7468fSPeter Dunlap static const char * 193830e7468fSPeter Dunlap iscsi_idm_conn_state(unsigned int state) 193930e7468fSPeter Dunlap { 194030e7468fSPeter Dunlap return ((state < CS_MAX_STATE) ? idm_cs_name[state] : "N/A"); 1941a6d42e7dSPeter Dunlap } 1942a6d42e7dSPeter Dunlap 1943a6d42e7dSPeter Dunlap /*ARGSUSED*/ 1944a6d42e7dSPeter Dunlap static const char * 194530e7468fSPeter Dunlap iscsi_idm_task_state(unsigned int state) 1946a6d42e7dSPeter Dunlap { 194730e7468fSPeter Dunlap return ("N/A"); 1948a6d42e7dSPeter Dunlap } 1949a6d42e7dSPeter Dunlap 1950a6d42e7dSPeter Dunlap static const char * 195130e7468fSPeter Dunlap iscsi_iscsit_tgt_state(unsigned int state) 1952a6d42e7dSPeter Dunlap { 195330e7468fSPeter Dunlap return ((state < TS_MAX_STATE) ? iscsit_ts_name[state] : "N/A"); 1954a6d42e7dSPeter Dunlap } 1955a6d42e7dSPeter Dunlap 1956a6d42e7dSPeter Dunlap static const char * 195730e7468fSPeter Dunlap iscsi_iscsit_sess_state(unsigned int state) 1958a6d42e7dSPeter Dunlap { 195930e7468fSPeter Dunlap return ((state < SS_MAX_STATE) ? iscsit_ss_name[state] : "N/A"); 196030e7468fSPeter Dunlap } 1961a6d42e7dSPeter Dunlap 196230e7468fSPeter Dunlap static const char * 196330e7468fSPeter Dunlap iscsi_iscsit_login_state(unsigned int state) 196430e7468fSPeter Dunlap { 196530e7468fSPeter Dunlap return ((state < ILS_MAX_STATE) ? iscsit_ils_name[state] : "N/A"); 1966a6d42e7dSPeter Dunlap } 1967a6d42e7dSPeter Dunlap 1968a6d42e7dSPeter Dunlap static const char * 196930e7468fSPeter Dunlap iscsi_iscsi_cmd_state(unsigned int state) 1970a6d42e7dSPeter Dunlap { 197130e7468fSPeter Dunlap return ((state < ISCSI_CMD_STATE_MAX) ? 197230e7468fSPeter Dunlap iscsi_cmd_state_names[state] : "N/A"); 197330e7468fSPeter Dunlap } 1974a6d42e7dSPeter Dunlap 197530e7468fSPeter Dunlap static const char * 197630e7468fSPeter Dunlap iscsi_iscsi_sess_state(unsigned int state) 197730e7468fSPeter Dunlap { 197830e7468fSPeter Dunlap return ((state < ISCSI_SESS_STATE_MAX) ? 197930e7468fSPeter Dunlap iscsi_sess_state_names[state] : "N/A"); 198030e7468fSPeter Dunlap } 1981a6d42e7dSPeter Dunlap 198230e7468fSPeter Dunlap static const char * 198330e7468fSPeter Dunlap iscsi_iscsi_conn_state(unsigned int state) 198430e7468fSPeter Dunlap { 198530e7468fSPeter Dunlap return ((state < ISCSI_CONN_STATE_MAX) ? iscsi_ics_name[state] : "N/A"); 1986a6d42e7dSPeter Dunlap } 1987a6d42e7dSPeter Dunlap 198830e7468fSPeter Dunlap static const char * 198930e7468fSPeter Dunlap iscsi_iscsi_login_state(unsigned int state) 199030e7468fSPeter Dunlap { 199130e7468fSPeter Dunlap return ((state < LOGIN_MAX) ? iscsi_login_state_names[state] : "N/A"); 199230e7468fSPeter Dunlap } 1993a6d42e7dSPeter Dunlap 1994a6d42e7dSPeter Dunlap 1995a6d42e7dSPeter Dunlap /* 1996a6d42e7dSPeter Dunlap * Retrieve connection type given a kernel address 1997a6d42e7dSPeter Dunlap */ 1998a6d42e7dSPeter Dunlap static idm_conn_type_t 1999a6d42e7dSPeter Dunlap idm_conn_type(uintptr_t addr) 2000a6d42e7dSPeter Dunlap { 2001a6d42e7dSPeter Dunlap idm_conn_type_t result = 0; /* Unknown */ 2002a6d42e7dSPeter Dunlap uintptr_t idm_conn_type_addr; 2003a6d42e7dSPeter Dunlap 2004a6d42e7dSPeter Dunlap idm_conn_type_addr = addr + offsetof(idm_conn_t, ic_conn_type); 2005a6d42e7dSPeter Dunlap (void) mdb_vread(&result, sizeof (result), idm_conn_type_addr); 2006a6d42e7dSPeter Dunlap 2007a6d42e7dSPeter Dunlap return (result); 2008a6d42e7dSPeter Dunlap } 2009a6d42e7dSPeter Dunlap 2010a6d42e7dSPeter Dunlap /* 2011a6d42e7dSPeter Dunlap * Convert a sockaddr to the string representation, suitable for 2012a6d42e7dSPeter Dunlap * storing in an nvlist or printing out in a list. 2013a6d42e7dSPeter Dunlap */ 2014a6d42e7dSPeter Dunlap static int 2015a6d42e7dSPeter Dunlap sa_to_str(struct sockaddr_storage *sa, char *buf) 2016a6d42e7dSPeter Dunlap { 2017a6d42e7dSPeter Dunlap char pbuf[7]; 2018a6d42e7dSPeter Dunlap const char *bufp; 2019a6d42e7dSPeter Dunlap struct sockaddr_in *sin; 2020a6d42e7dSPeter Dunlap struct sockaddr_in6 *sin6; 2021a6d42e7dSPeter Dunlap uint16_t port; 2022a6d42e7dSPeter Dunlap 2023a6d42e7dSPeter Dunlap if (!sa || !buf) { 2024a6d42e7dSPeter Dunlap return (EINVAL); 2025a6d42e7dSPeter Dunlap } 2026a6d42e7dSPeter Dunlap 2027a6d42e7dSPeter Dunlap buf[0] = '\0'; 2028a6d42e7dSPeter Dunlap 2029a6d42e7dSPeter Dunlap if (sa->ss_family == AF_INET) { 2030a6d42e7dSPeter Dunlap sin = (struct sockaddr_in *)sa; 203130e7468fSPeter Dunlap bufp = iscsi_inet_ntop(AF_INET, 2032a6d42e7dSPeter Dunlap (const void *)&(sin->sin_addr.s_addr), 2033a6d42e7dSPeter Dunlap buf, PORTAL_STR_LEN); 2034a6d42e7dSPeter Dunlap if (bufp == NULL) { 2035a6d42e7dSPeter Dunlap return (-1); 2036a6d42e7dSPeter Dunlap } 2037a6d42e7dSPeter Dunlap mdb_nhconvert(&port, &sin->sin_port, sizeof (uint16_t)); 2038a6d42e7dSPeter Dunlap } else if (sa->ss_family == AF_INET6) { 2039a6d42e7dSPeter Dunlap strlcat(buf, "[", sizeof (buf)); 2040a6d42e7dSPeter Dunlap sin6 = (struct sockaddr_in6 *)sa; 204130e7468fSPeter Dunlap bufp = iscsi_inet_ntop(AF_INET6, 2042a6d42e7dSPeter Dunlap (const void *)&sin6->sin6_addr.s6_addr, 2043a6d42e7dSPeter Dunlap &buf[1], PORTAL_STR_LEN - 1); 2044a6d42e7dSPeter Dunlap if (bufp == NULL) { 2045a6d42e7dSPeter Dunlap return (-1); 2046a6d42e7dSPeter Dunlap } 2047a6d42e7dSPeter Dunlap strlcat(buf, "]", PORTAL_STR_LEN); 2048a6d42e7dSPeter Dunlap mdb_nhconvert(&port, &sin->sin_port, sizeof (uint16_t)); 2049a6d42e7dSPeter Dunlap } else { 2050a6d42e7dSPeter Dunlap return (EINVAL); 2051a6d42e7dSPeter Dunlap } 2052a6d42e7dSPeter Dunlap 2053a6d42e7dSPeter Dunlap 2054a6d42e7dSPeter Dunlap mdb_snprintf(pbuf, sizeof (pbuf), ":%u", port); 2055a6d42e7dSPeter Dunlap strlcat(buf, pbuf, PORTAL_STR_LEN); 2056a6d42e7dSPeter Dunlap 2057a6d42e7dSPeter Dunlap return (0); 2058a6d42e7dSPeter Dunlap } 2059a6d42e7dSPeter Dunlap 2060a6d42e7dSPeter Dunlap 2061a6d42e7dSPeter Dunlap static void 2062a6d42e7dSPeter Dunlap iscsi_format_timestamp(char *ts_str, int strlen, timespec_t *ts) 2063a6d42e7dSPeter Dunlap { 2064a6d42e7dSPeter Dunlap mdb_snprintf(ts_str, strlen, "%Y:%03d:%03d:%03d", ts->tv_sec, 2065a6d42e7dSPeter Dunlap (ts->tv_nsec / 1000000) % 1000, (ts->tv_nsec / 1000) % 1000, 2066a6d42e7dSPeter Dunlap ts->tv_nsec % 1000); 2067a6d42e7dSPeter Dunlap } 2068a6d42e7dSPeter Dunlap 2069a6d42e7dSPeter Dunlap /* 2070a6d42e7dSPeter Dunlap * Help information for the iscsi_isns dcmd 2071a6d42e7dSPeter Dunlap */ 2072a6d42e7dSPeter Dunlap static void 2073a6d42e7dSPeter Dunlap iscsi_isns_help(void) 2074a6d42e7dSPeter Dunlap { 2075a6d42e7dSPeter Dunlap mdb_printf("iscsi_isns:\n"); 2076a6d42e7dSPeter Dunlap mdb_inc_indent(4); 2077a6d42e7dSPeter Dunlap mdb_printf("-e: Print ESI information\n"); 2078a6d42e7dSPeter Dunlap mdb_printf("-p: Print portal information\n"); 2079a6d42e7dSPeter Dunlap mdb_printf("-s: Print iSNS server information\n"); 2080a6d42e7dSPeter Dunlap mdb_printf("-t: Print target information\n"); 2081a6d42e7dSPeter Dunlap mdb_printf("-v: Add verbosity to the other options' output\n"); 2082a6d42e7dSPeter Dunlap mdb_dec_indent(4); 2083a6d42e7dSPeter Dunlap } 2084a6d42e7dSPeter Dunlap 2085a6d42e7dSPeter Dunlap /* ARGSUSED */ 2086a6d42e7dSPeter Dunlap static int 2087a6d42e7dSPeter Dunlap iscsi_isns_esi_cb(uintptr_t addr, const void *walker_data, void *data) 2088a6d42e7dSPeter Dunlap { 2089a6d42e7dSPeter Dunlap isns_esi_tinfo_t tinfo; 2090a6d42e7dSPeter Dunlap 2091a6d42e7dSPeter Dunlap if (mdb_vread(&tinfo, sizeof (isns_esi_tinfo_t), addr) != 2092a6d42e7dSPeter Dunlap sizeof (isns_esi_tinfo_t)) { 2093a6d42e7dSPeter Dunlap return (WALK_ERR); 2094a6d42e7dSPeter Dunlap } 2095a6d42e7dSPeter Dunlap 2096a6d42e7dSPeter Dunlap mdb_printf("ESI thread/thr did : 0x%p / %d\n", tinfo.esi_thread, 2097a6d42e7dSPeter Dunlap tinfo.esi_thread_did); 2098a6d42e7dSPeter Dunlap mdb_printf("ESI sonode : 0x%p\n", tinfo.esi_so); 2099a6d42e7dSPeter Dunlap mdb_printf("ESI port : %d\n", tinfo.esi_port); 2100a6d42e7dSPeter Dunlap mdb_printf("ESI thread running : %s\n", 2101a6d42e7dSPeter Dunlap (tinfo.esi_thread_running) ? "Yes" : "No"); 2102a6d42e7dSPeter Dunlap 2103a6d42e7dSPeter Dunlap return (WALK_NEXT); 2104a6d42e7dSPeter Dunlap } 2105a6d42e7dSPeter Dunlap 2106a6d42e7dSPeter Dunlap static int 2107a6d42e7dSPeter Dunlap iscsi_isns_esi(iscsi_dcmd_ctrl_t *idc) 2108a6d42e7dSPeter Dunlap { 2109e42a0851Speter dunlap GElf_Sym sym; 2110e42a0851Speter dunlap uintptr_t addr; 2111a6d42e7dSPeter Dunlap 2112e42a0851Speter dunlap if (mdb_lookup_by_name("esi", &sym) == -1) { 2113a6d42e7dSPeter Dunlap mdb_warn("failed to find symbol 'esi_list'"); 2114a6d42e7dSPeter Dunlap return (DCMD_ERR); 2115a6d42e7dSPeter Dunlap } 2116e42a0851Speter dunlap addr = (uintptr_t)sym.st_value; 2117a6d42e7dSPeter Dunlap 2118a6d42e7dSPeter Dunlap idc->idc_header = 1; 2119e42a0851Speter dunlap (void) iscsi_isns_esi_cb(addr, NULL, idc); 2120a6d42e7dSPeter Dunlap 2121a6d42e7dSPeter Dunlap return (0); 2122a6d42e7dSPeter Dunlap } 2123a6d42e7dSPeter Dunlap 2124a6d42e7dSPeter Dunlap /* ARGSUSED */ 2125a6d42e7dSPeter Dunlap static int 2126a6d42e7dSPeter Dunlap iscsi_isns_portal_cb(uintptr_t addr, const void *walker_data, void *data) 2127a6d42e7dSPeter Dunlap { 2128a6d42e7dSPeter Dunlap iscsi_dcmd_ctrl_t *idc = (iscsi_dcmd_ctrl_t *)data; 2129a6d42e7dSPeter Dunlap isns_portal_list_t portal; 2130a6d42e7dSPeter Dunlap char portal_addr[PORTAL_STR_LEN]; 2131a6d42e7dSPeter Dunlap struct sockaddr_storage *ss; 2132e42a0851Speter dunlap char ts_string[40]; 2133a6d42e7dSPeter Dunlap 2134a6d42e7dSPeter Dunlap if (mdb_vread(&portal, sizeof (isns_portal_list_t), addr) != 2135a6d42e7dSPeter Dunlap sizeof (isns_portal_list_t)) { 2136a6d42e7dSPeter Dunlap return (WALK_ERR); 2137a6d42e7dSPeter Dunlap } 2138a6d42e7dSPeter Dunlap 2139a6d42e7dSPeter Dunlap ss = &portal.portal_addr; 2140a6d42e7dSPeter Dunlap sa_to_str(ss, portal_addr); 2141a6d42e7dSPeter Dunlap mdb_printf("Portal IP address "); 2142a6d42e7dSPeter Dunlap 2143a6d42e7dSPeter Dunlap if (ss->ss_family == AF_INET) { 2144a6d42e7dSPeter Dunlap mdb_printf("(v4): %s", portal_addr); 2145a6d42e7dSPeter Dunlap } else { 2146a6d42e7dSPeter Dunlap mdb_printf("(v6): %s", portal_addr); 2147a6d42e7dSPeter Dunlap } 2148a6d42e7dSPeter Dunlap 2149a6d42e7dSPeter Dunlap if (portal.portal_iscsit == NULL) { 2150a6d42e7dSPeter Dunlap mdb_printf(" (Default portal)\n"); 2151a6d42e7dSPeter Dunlap } else { 2152a6d42e7dSPeter Dunlap mdb_printf("\n"); 2153a6d42e7dSPeter Dunlap } 2154a6d42e7dSPeter Dunlap 2155a6d42e7dSPeter Dunlap if ((portal.portal_iscsit != NULL) && (idc->idc_verbose)) { 2156a6d42e7dSPeter Dunlap iscsi_portal_impl((uintptr_t)portal.portal_iscsit, idc); 2157a6d42e7dSPeter Dunlap } 2158a6d42e7dSPeter Dunlap 2159e42a0851Speter dunlap iscsi_format_timestamp(ts_string, 40, &portal.portal_esi_timestamp); 2160e42a0851Speter dunlap mdb_printf("Portal ESI timestamp: 0x%p\n\n", ts_string); 2161a6d42e7dSPeter Dunlap 2162a6d42e7dSPeter Dunlap return (WALK_NEXT); 2163a6d42e7dSPeter Dunlap } 2164a6d42e7dSPeter Dunlap 2165a6d42e7dSPeter Dunlap static int 2166a6d42e7dSPeter Dunlap iscsi_isns_portals(iscsi_dcmd_ctrl_t *idc) 2167a6d42e7dSPeter Dunlap { 2168a6d42e7dSPeter Dunlap GElf_Sym sym; 2169a6d42e7dSPeter Dunlap uintptr_t portal_list; 2170a6d42e7dSPeter Dunlap 2171a6d42e7dSPeter Dunlap if (mdb_lookup_by_name("portal_list", &sym) == -1) { 2172a6d42e7dSPeter Dunlap mdb_warn("failed to find symbol 'portal_list'"); 2173a6d42e7dSPeter Dunlap return (DCMD_ERR); 2174a6d42e7dSPeter Dunlap } 2175a6d42e7dSPeter Dunlap 2176a6d42e7dSPeter Dunlap portal_list = (uintptr_t)sym.st_value; 2177a6d42e7dSPeter Dunlap idc->idc_header = 1; 2178a6d42e7dSPeter Dunlap 2179a6d42e7dSPeter Dunlap if (mdb_pwalk("list", iscsi_isns_portal_cb, idc, portal_list) == -1) { 2180a6d42e7dSPeter Dunlap mdb_warn("avl walk failed for portal_list"); 2181a6d42e7dSPeter Dunlap return (DCMD_ERR); 2182a6d42e7dSPeter Dunlap } 2183a6d42e7dSPeter Dunlap 2184a6d42e7dSPeter Dunlap return (0); 2185a6d42e7dSPeter Dunlap } 2186a6d42e7dSPeter Dunlap 2187a6d42e7dSPeter Dunlap /* ARGSUSED */ 2188a6d42e7dSPeter Dunlap static int 2189a6d42e7dSPeter Dunlap iscsi_isns_targets_cb(uintptr_t addr, const void *walker_data, void *data) 2190a6d42e7dSPeter Dunlap { 2191a6d42e7dSPeter Dunlap iscsi_dcmd_ctrl_t *idc = (iscsi_dcmd_ctrl_t *)data; 2192a6d42e7dSPeter Dunlap isns_target_t itarget; 2193a6d42e7dSPeter Dunlap int rc = 0; 2194a6d42e7dSPeter Dunlap 2195a6d42e7dSPeter Dunlap if (mdb_vread(&itarget, sizeof (isns_target_t), addr) != 2196a6d42e7dSPeter Dunlap sizeof (isns_target_t)) { 2197a6d42e7dSPeter Dunlap return (WALK_ERR); 2198a6d42e7dSPeter Dunlap } 2199a6d42e7dSPeter Dunlap 2200a6d42e7dSPeter Dunlap idc->idc_header = 1; 2201a6d42e7dSPeter Dunlap 2202a6d42e7dSPeter Dunlap mdb_printf("Target: %p\n", itarget.target); 2203a6d42e7dSPeter Dunlap mdb_inc_indent(4); 2204a6d42e7dSPeter Dunlap mdb_printf("Registered: %s\n", 2205a6d42e7dSPeter Dunlap (itarget.target_registered) ? "Yes" : "No"); 2206a6d42e7dSPeter Dunlap 2207a6d42e7dSPeter Dunlap rc = iscsi_tgt_impl((uintptr_t)itarget.target, idc); 2208a6d42e7dSPeter Dunlap 2209a6d42e7dSPeter Dunlap mdb_dec_indent(4); 2210a6d42e7dSPeter Dunlap 2211a6d42e7dSPeter Dunlap if (rc == DCMD_OK) { 2212a6d42e7dSPeter Dunlap return (WALK_NEXT); 2213a6d42e7dSPeter Dunlap } 2214a6d42e7dSPeter Dunlap 2215a6d42e7dSPeter Dunlap return (WALK_ERR); 2216a6d42e7dSPeter Dunlap } 2217a6d42e7dSPeter Dunlap 2218a6d42e7dSPeter Dunlap static int 2219a6d42e7dSPeter Dunlap iscsi_isns_targets(iscsi_dcmd_ctrl_t *idc) 2220a6d42e7dSPeter Dunlap { 2221a6d42e7dSPeter Dunlap GElf_Sym sym; 2222a6d42e7dSPeter Dunlap uintptr_t isns_target_list; 2223a6d42e7dSPeter Dunlap 2224a6d42e7dSPeter Dunlap if (mdb_lookup_by_name("isns_target_list", &sym) == -1) { 2225a6d42e7dSPeter Dunlap mdb_warn("failed to find symbol 'isns_target_list'"); 2226a6d42e7dSPeter Dunlap return (DCMD_ERR); 2227a6d42e7dSPeter Dunlap } 2228a6d42e7dSPeter Dunlap 2229a6d42e7dSPeter Dunlap isns_target_list = (uintptr_t)sym.st_value; 2230a6d42e7dSPeter Dunlap idc->idc_header = 1; 2231a6d42e7dSPeter Dunlap idc->u.child.idc_tgt = 1; 2232a6d42e7dSPeter Dunlap 2233a6d42e7dSPeter Dunlap if (mdb_pwalk("avl", iscsi_isns_targets_cb, idc, 2234a6d42e7dSPeter Dunlap isns_target_list) == -1) { 2235a6d42e7dSPeter Dunlap mdb_warn("avl walk failed for isns_target_list"); 2236a6d42e7dSPeter Dunlap return (DCMD_ERR); 2237a6d42e7dSPeter Dunlap } 2238a6d42e7dSPeter Dunlap 2239a6d42e7dSPeter Dunlap return (0); 2240a6d42e7dSPeter Dunlap } 2241a6d42e7dSPeter Dunlap 2242a6d42e7dSPeter Dunlap /* ARGSUSED */ 2243a6d42e7dSPeter Dunlap static int 2244a6d42e7dSPeter Dunlap iscsi_isns_servers_cb(uintptr_t addr, const void *walker_data, void *data) 2245a6d42e7dSPeter Dunlap { 2246a6d42e7dSPeter Dunlap GElf_Sym sym; 2247a6d42e7dSPeter Dunlap iscsit_isns_svr_t server; 2248a6d42e7dSPeter Dunlap char server_addr[PORTAL_STR_LEN]; 2249a6d42e7dSPeter Dunlap struct sockaddr_storage *ss; 2250a6d42e7dSPeter Dunlap clock_t lbolt; 2251a6d42e7dSPeter Dunlap 2252a6d42e7dSPeter Dunlap if (mdb_vread(&server, sizeof (iscsit_isns_svr_t), addr) != 2253a6d42e7dSPeter Dunlap sizeof (iscsit_isns_svr_t)) { 2254a6d42e7dSPeter Dunlap return (WALK_ERR); 2255a6d42e7dSPeter Dunlap } 2256a6d42e7dSPeter Dunlap 2257a6d42e7dSPeter Dunlap if (mdb_lookup_by_name("lbolt", &sym) == -1) { 2258a6d42e7dSPeter Dunlap mdb_warn("failed to find symbol 'lbolt'"); 2259a6d42e7dSPeter Dunlap return (DCMD_ERR); 2260a6d42e7dSPeter Dunlap } 2261a6d42e7dSPeter Dunlap 2262a6d42e7dSPeter Dunlap if (mdb_vread(&lbolt, sizeof (clock_t), sym.st_value) != 2263a6d42e7dSPeter Dunlap sizeof (clock_t)) { 2264a6d42e7dSPeter Dunlap return (WALK_ERR); 2265a6d42e7dSPeter Dunlap } 2266a6d42e7dSPeter Dunlap 2267a6d42e7dSPeter Dunlap mdb_printf("iSNS server %p:\n", addr); 2268a6d42e7dSPeter Dunlap mdb_inc_indent(4); 2269a6d42e7dSPeter Dunlap ss = &server.svr_sa; 2270a6d42e7dSPeter Dunlap sa_to_str(ss, server_addr); 2271a6d42e7dSPeter Dunlap 2272a6d42e7dSPeter Dunlap mdb_printf("IP address "); 2273a6d42e7dSPeter Dunlap if (ss->ss_family == AF_INET) { 2274a6d42e7dSPeter Dunlap mdb_printf("(v4): %s\n", server_addr); 2275a6d42e7dSPeter Dunlap } else { 2276a6d42e7dSPeter Dunlap mdb_printf("(v6): %s\n", server_addr); 2277a6d42e7dSPeter Dunlap } 2278a6d42e7dSPeter Dunlap 2279a6d42e7dSPeter Dunlap mdb_printf("Last ESI message : %d seconds ago\n", 2280a6d42e7dSPeter Dunlap ((lbolt - server.svr_last_msg) / 100)); 2281a6d42e7dSPeter Dunlap mdb_printf("Client registered: %s\n", 2282a6d42e7dSPeter Dunlap (server.svr_registered) ? "Yes" : "No"); 2283a6d42e7dSPeter Dunlap mdb_dec_indent(4); 2284a6d42e7dSPeter Dunlap 2285a6d42e7dSPeter Dunlap return (WALK_ERR); 2286a6d42e7dSPeter Dunlap } 2287a6d42e7dSPeter Dunlap 2288a6d42e7dSPeter Dunlap static int 2289a6d42e7dSPeter Dunlap iscsi_isns_servers(iscsi_dcmd_ctrl_t *idc) 2290a6d42e7dSPeter Dunlap { 2291a6d42e7dSPeter Dunlap uintptr_t iscsit_global_addr; 2292a6d42e7dSPeter Dunlap uintptr_t list_addr; 2293a6d42e7dSPeter Dunlap GElf_Sym sym; 2294a6d42e7dSPeter Dunlap 2295a6d42e7dSPeter Dunlap if (mdb_lookup_by_name("iscsit_global", &sym) == -1) { 2296a6d42e7dSPeter Dunlap mdb_warn("failed to find symbol 'iscsit_global'"); 2297a6d42e7dSPeter Dunlap return (DCMD_ERR); 2298a6d42e7dSPeter Dunlap } 2299a6d42e7dSPeter Dunlap 2300a6d42e7dSPeter Dunlap iscsit_global_addr = (uintptr_t)sym.st_value; 2301a6d42e7dSPeter Dunlap idc->idc_header = 1; 2302a6d42e7dSPeter Dunlap list_addr = iscsit_global_addr + 2303a6d42e7dSPeter Dunlap offsetof(iscsit_global_t, global_isns_cfg.isns_svrs); 2304a6d42e7dSPeter Dunlap 2305a6d42e7dSPeter Dunlap if (mdb_pwalk("list", iscsi_isns_servers_cb, idc, list_addr) == -1) { 2306a6d42e7dSPeter Dunlap mdb_warn("list walk failed for iSNS servers"); 2307a6d42e7dSPeter Dunlap return (DCMD_ERR); 2308a6d42e7dSPeter Dunlap } 2309a6d42e7dSPeter Dunlap 2310a6d42e7dSPeter Dunlap return (0); 2311a6d42e7dSPeter Dunlap } 2312a6d42e7dSPeter Dunlap 2313a6d42e7dSPeter Dunlap /* ARGSUSED */ 2314a6d42e7dSPeter Dunlap static int 2315a6d42e7dSPeter Dunlap iscsi_isns(uintptr_t addr, uint_t flags, int argc, const mdb_arg_t *argv) 2316a6d42e7dSPeter Dunlap { 2317a6d42e7dSPeter Dunlap iscsi_dcmd_ctrl_t idc; 2318a6d42e7dSPeter Dunlap int portals = 0, esi = 0, targets = 0, verbose = 0, servers = 0; 2319a6d42e7dSPeter Dunlap 2320a6d42e7dSPeter Dunlap if (flags & DCMD_ADDRSPEC) { 2321a6d42e7dSPeter Dunlap mdb_warn("iscsi_isns is only a global dcmd."); 2322a6d42e7dSPeter Dunlap return (DCMD_ERR); 2323a6d42e7dSPeter Dunlap } 2324a6d42e7dSPeter Dunlap 2325a6d42e7dSPeter Dunlap bzero(&idc, sizeof (idc)); 2326a6d42e7dSPeter Dunlap if (mdb_getopts(argc, argv, 2327a6d42e7dSPeter Dunlap 'e', MDB_OPT_SETBITS, TRUE, &esi, 2328a6d42e7dSPeter Dunlap 'p', MDB_OPT_SETBITS, TRUE, &portals, 2329a6d42e7dSPeter Dunlap 's', MDB_OPT_SETBITS, TRUE, &servers, 2330a6d42e7dSPeter Dunlap 't', MDB_OPT_SETBITS, TRUE, &targets, 2331a6d42e7dSPeter Dunlap 'v', MDB_OPT_SETBITS, TRUE, &verbose, 2332a6d42e7dSPeter Dunlap NULL) != argc) 2333a6d42e7dSPeter Dunlap return (DCMD_USAGE); 2334a6d42e7dSPeter Dunlap 2335a6d42e7dSPeter Dunlap if ((esi + portals + targets + servers) > 1) { 2336a6d42e7dSPeter Dunlap mdb_printf("Only one of e, p, s, and t must be provided"); 2337a6d42e7dSPeter Dunlap return (DCMD_ERR); 2338a6d42e7dSPeter Dunlap } 2339a6d42e7dSPeter Dunlap 2340a6d42e7dSPeter Dunlap if ((esi | portals | targets | servers) == 0) { 2341a6d42e7dSPeter Dunlap mdb_printf("Exactly one of e, p, s, or t must be provided"); 2342a6d42e7dSPeter Dunlap return (DCMD_ERR); 2343a6d42e7dSPeter Dunlap } 2344a6d42e7dSPeter Dunlap 2345a6d42e7dSPeter Dunlap idc.idc_verbose = verbose; 2346a6d42e7dSPeter Dunlap 2347a6d42e7dSPeter Dunlap if (esi) { 2348a6d42e7dSPeter Dunlap return (iscsi_isns_esi(&idc)); 2349a6d42e7dSPeter Dunlap } 2350a6d42e7dSPeter Dunlap 2351a6d42e7dSPeter Dunlap if (portals) { 2352a6d42e7dSPeter Dunlap return (iscsi_isns_portals(&idc)); 2353a6d42e7dSPeter Dunlap } 2354a6d42e7dSPeter Dunlap 2355a6d42e7dSPeter Dunlap if (servers) { 2356a6d42e7dSPeter Dunlap return (iscsi_isns_servers(&idc)); 2357a6d42e7dSPeter Dunlap } 2358a6d42e7dSPeter Dunlap 2359a6d42e7dSPeter Dunlap return (iscsi_isns_targets(&idc)); 2360a6d42e7dSPeter Dunlap } 2361a6d42e7dSPeter Dunlap 2362a6d42e7dSPeter Dunlap /* 236330e7468fSPeter Dunlap * iscsi_inet_ntop -- Convert an IPv4 or IPv6 address in binary form into 2364a6d42e7dSPeter Dunlap * printable form, and return a pointer to that string. Caller should 2365a6d42e7dSPeter Dunlap * provide a buffer of correct length to store string into. 2366a6d42e7dSPeter Dunlap * Note: this routine is kernel version of inet_ntop. It has similar 236730e7468fSPeter Dunlap * format as iscsi_inet_ntop() defined in rfc2553. But it does not do 2368a6d42e7dSPeter Dunlap * error handling operations exactly as rfc2553 defines. This function 2369a6d42e7dSPeter Dunlap * is used by kernel inet directory routines only for debugging. 237030e7468fSPeter Dunlap * This iscsi_inet_ntop() function, does not return NULL if third argument 2371a6d42e7dSPeter Dunlap * is NULL. The reason is simple that we don't want kernel to panic 2372a6d42e7dSPeter Dunlap * as the output of this function is directly fed to ip<n>dbg macro. 2373a6d42e7dSPeter Dunlap * Instead it uses a local buffer for destination address for 2374a6d42e7dSPeter Dunlap * those calls which purposely pass NULL ptr for the destination 2375a6d42e7dSPeter Dunlap * buffer. This function is thread-safe when the caller passes a non- 2376a6d42e7dSPeter Dunlap * null buffer with the third argument. 2377a6d42e7dSPeter Dunlap */ 2378a6d42e7dSPeter Dunlap /* ARGSUSED */ 2379a6d42e7dSPeter Dunlap 2380a6d42e7dSPeter Dunlap #define OK_16PTR(p) (!((uintptr_t)(p) & 0x1)) 2381a6d42e7dSPeter Dunlap #if defined(__x86) 2382a6d42e7dSPeter Dunlap #define OK_32PTR(p) OK_16PTR(p) 2383a6d42e7dSPeter Dunlap #else 2384a6d42e7dSPeter Dunlap #define OK_32PTR(p) (!((uintptr_t)(p) & 0x3)) 2385a6d42e7dSPeter Dunlap #endif 2386a6d42e7dSPeter Dunlap 2387a6d42e7dSPeter Dunlap char * 238830e7468fSPeter Dunlap iscsi_inet_ntop(int af, const void *addr, char *buf, int addrlen) 2389a6d42e7dSPeter Dunlap { 2390a6d42e7dSPeter Dunlap static char local_buf[PORTAL_STR_LEN]; 2391a6d42e7dSPeter Dunlap static char *err_buf1 = "<badaddr>"; 2392a6d42e7dSPeter Dunlap static char *err_buf2 = "<badfamily>"; 2393a6d42e7dSPeter Dunlap in6_addr_t *v6addr; 2394a6d42e7dSPeter Dunlap uchar_t *v4addr; 2395a6d42e7dSPeter Dunlap char *caddr; 2396a6d42e7dSPeter Dunlap 2397a6d42e7dSPeter Dunlap /* 239830e7468fSPeter Dunlap * We don't allow thread unsafe iscsi_inet_ntop calls, they 2399a6d42e7dSPeter Dunlap * must pass a non-null buffer pointer. For DEBUG mode 2400a6d42e7dSPeter Dunlap * we use the ASSERT() and for non-debug kernel it will 2401a6d42e7dSPeter Dunlap * silently allow it for now. Someday we should remove 2402a6d42e7dSPeter Dunlap * the static buffer from this function. 2403a6d42e7dSPeter Dunlap */ 2404a6d42e7dSPeter Dunlap 2405a6d42e7dSPeter Dunlap ASSERT(buf != NULL); 2406a6d42e7dSPeter Dunlap if (buf == NULL) 2407a6d42e7dSPeter Dunlap buf = local_buf; 2408a6d42e7dSPeter Dunlap buf[0] = '\0'; 2409a6d42e7dSPeter Dunlap 2410a6d42e7dSPeter Dunlap /* Let user know politely not to send NULL or unaligned addr */ 2411a6d42e7dSPeter Dunlap if (addr == NULL || !(OK_32PTR(addr))) { 2412a6d42e7dSPeter Dunlap return (err_buf1); 2413a6d42e7dSPeter Dunlap } 2414a6d42e7dSPeter Dunlap 2415a6d42e7dSPeter Dunlap 2416a6d42e7dSPeter Dunlap #define UC(b) (((int)b) & 0xff) 2417a6d42e7dSPeter Dunlap switch (af) { 2418a6d42e7dSPeter Dunlap case AF_INET: 2419a6d42e7dSPeter Dunlap ASSERT(addrlen >= INET_ADDRSTRLEN); 2420a6d42e7dSPeter Dunlap v4addr = (uchar_t *)addr; 2421a6d42e7dSPeter Dunlap (void) mdb_snprintf(buf, INET6_ADDRSTRLEN, 2422a6d42e7dSPeter Dunlap "%03d.%03d.%03d.%03d", 2423a6d42e7dSPeter Dunlap UC(v4addr[0]), UC(v4addr[1]), UC(v4addr[2]), UC(v4addr[3])); 2424a6d42e7dSPeter Dunlap return (buf); 2425a6d42e7dSPeter Dunlap 2426a6d42e7dSPeter Dunlap case AF_INET6: 2427a6d42e7dSPeter Dunlap ASSERT(addrlen >= INET6_ADDRSTRLEN); 2428a6d42e7dSPeter Dunlap v6addr = (in6_addr_t *)addr; 2429a6d42e7dSPeter Dunlap if (IN6_IS_ADDR_V4MAPPED(v6addr)) { 2430a6d42e7dSPeter Dunlap caddr = (char *)addr; 2431a6d42e7dSPeter Dunlap (void) mdb_snprintf(buf, INET6_ADDRSTRLEN, 2432a6d42e7dSPeter Dunlap "::ffff:%d.%d.%d.%d", 2433a6d42e7dSPeter Dunlap UC(caddr[12]), UC(caddr[13]), 2434a6d42e7dSPeter Dunlap UC(caddr[14]), UC(caddr[15])); 2435a6d42e7dSPeter Dunlap } else if (IN6_IS_ADDR_V4COMPAT(v6addr)) { 2436a6d42e7dSPeter Dunlap caddr = (char *)addr; 2437a6d42e7dSPeter Dunlap (void) mdb_snprintf(buf, INET6_ADDRSTRLEN, 2438a6d42e7dSPeter Dunlap "::%d.%d.%d.%d", 2439a6d42e7dSPeter Dunlap UC(caddr[12]), UC(caddr[13]), UC(caddr[14]), 2440a6d42e7dSPeter Dunlap UC(caddr[15])); 2441a6d42e7dSPeter Dunlap } else if (IN6_IS_ADDR_UNSPECIFIED(v6addr)) { 2442a6d42e7dSPeter Dunlap (void) mdb_snprintf(buf, INET6_ADDRSTRLEN, "::"); 2443a6d42e7dSPeter Dunlap } else { 2444a6d42e7dSPeter Dunlap convert2ascii(buf, v6addr); 2445a6d42e7dSPeter Dunlap } 2446a6d42e7dSPeter Dunlap return (buf); 2447a6d42e7dSPeter Dunlap 2448a6d42e7dSPeter Dunlap default: 2449a6d42e7dSPeter Dunlap return (err_buf2); 2450a6d42e7dSPeter Dunlap } 2451a6d42e7dSPeter Dunlap #undef UC 2452a6d42e7dSPeter Dunlap } 2453a6d42e7dSPeter Dunlap 2454a6d42e7dSPeter Dunlap /* 2455a6d42e7dSPeter Dunlap * 2456a6d42e7dSPeter Dunlap * v6 formats supported 2457a6d42e7dSPeter Dunlap * General format xxxx:xxxx:xxxx:xxxx:xxxx:xxxx:xxxx:xxxx 2458a6d42e7dSPeter Dunlap * The short hand notation :: is used for COMPAT addr 2459a6d42e7dSPeter Dunlap * Other forms : fe80::xxxx:xxxx:xxxx:xxxx 2460a6d42e7dSPeter Dunlap */ 2461a6d42e7dSPeter Dunlap static void 2462a6d42e7dSPeter Dunlap convert2ascii(char *buf, const in6_addr_t *addr) 2463a6d42e7dSPeter Dunlap { 2464a6d42e7dSPeter Dunlap int hexdigits; 2465a6d42e7dSPeter Dunlap int head_zero = 0; 2466a6d42e7dSPeter Dunlap int tail_zero = 0; 2467a6d42e7dSPeter Dunlap /* tempbuf must be big enough to hold ffff:\0 */ 2468a6d42e7dSPeter Dunlap char tempbuf[6]; 2469a6d42e7dSPeter Dunlap char *ptr; 2470a6d42e7dSPeter Dunlap uint16_t out_addr_component; 2471a6d42e7dSPeter Dunlap uint16_t *addr_component; 2472a6d42e7dSPeter Dunlap size_t len; 2473a6d42e7dSPeter Dunlap boolean_t first = B_FALSE; 2474a6d42e7dSPeter Dunlap boolean_t med_zero = B_FALSE; 2475a6d42e7dSPeter Dunlap boolean_t end_zero = B_FALSE; 2476a6d42e7dSPeter Dunlap 2477a6d42e7dSPeter Dunlap addr_component = (uint16_t *)addr; 2478a6d42e7dSPeter Dunlap ptr = buf; 2479a6d42e7dSPeter Dunlap 2480a6d42e7dSPeter Dunlap /* First count if trailing zeroes higher in number */ 2481a6d42e7dSPeter Dunlap for (hexdigits = 0; hexdigits < 8; hexdigits++) { 2482a6d42e7dSPeter Dunlap if (*addr_component == 0) { 2483a6d42e7dSPeter Dunlap if (hexdigits < 4) 2484a6d42e7dSPeter Dunlap head_zero++; 2485a6d42e7dSPeter Dunlap else 2486a6d42e7dSPeter Dunlap tail_zero++; 2487a6d42e7dSPeter Dunlap } 2488a6d42e7dSPeter Dunlap addr_component++; 2489a6d42e7dSPeter Dunlap } 2490a6d42e7dSPeter Dunlap addr_component = (uint16_t *)addr; 2491a6d42e7dSPeter Dunlap if (tail_zero > head_zero && (head_zero + tail_zero) != 7) 2492a6d42e7dSPeter Dunlap end_zero = B_TRUE; 2493a6d42e7dSPeter Dunlap 2494a6d42e7dSPeter Dunlap for (hexdigits = 0; hexdigits < 8; hexdigits++) { 2495a6d42e7dSPeter Dunlap 2496a6d42e7dSPeter Dunlap /* if entry is a 0 */ 2497a6d42e7dSPeter Dunlap 2498a6d42e7dSPeter Dunlap if (*addr_component == 0) { 2499a6d42e7dSPeter Dunlap if (!first && *(addr_component + 1) == 0) { 2500a6d42e7dSPeter Dunlap if (end_zero && (hexdigits < 4)) { 2501a6d42e7dSPeter Dunlap *ptr++ = '0'; 2502a6d42e7dSPeter Dunlap *ptr++ = ':'; 2503a6d42e7dSPeter Dunlap } else { 2504a6d42e7dSPeter Dunlap /* 2505a6d42e7dSPeter Dunlap * address starts with 0s .. 2506a6d42e7dSPeter Dunlap * stick in leading ':' of pair 2507a6d42e7dSPeter Dunlap */ 2508a6d42e7dSPeter Dunlap if (hexdigits == 0) 2509a6d42e7dSPeter Dunlap *ptr++ = ':'; 2510a6d42e7dSPeter Dunlap /* add another */ 2511a6d42e7dSPeter Dunlap *ptr++ = ':'; 2512a6d42e7dSPeter Dunlap first = B_TRUE; 2513a6d42e7dSPeter Dunlap med_zero = B_TRUE; 2514a6d42e7dSPeter Dunlap } 2515a6d42e7dSPeter Dunlap } else if (first && med_zero) { 2516a6d42e7dSPeter Dunlap if (hexdigits == 7) 2517a6d42e7dSPeter Dunlap *ptr++ = ':'; 2518a6d42e7dSPeter Dunlap addr_component++; 2519a6d42e7dSPeter Dunlap continue; 2520a6d42e7dSPeter Dunlap } else { 2521a6d42e7dSPeter Dunlap *ptr++ = '0'; 2522a6d42e7dSPeter Dunlap *ptr++ = ':'; 2523a6d42e7dSPeter Dunlap } 2524a6d42e7dSPeter Dunlap addr_component++; 2525a6d42e7dSPeter Dunlap continue; 2526a6d42e7dSPeter Dunlap } 2527a6d42e7dSPeter Dunlap if (med_zero) 2528a6d42e7dSPeter Dunlap med_zero = B_FALSE; 2529a6d42e7dSPeter Dunlap 2530a6d42e7dSPeter Dunlap tempbuf[0] = '\0'; 2531a6d42e7dSPeter Dunlap mdb_nhconvert(&out_addr_component, addr_component, 2532a6d42e7dSPeter Dunlap sizeof (uint16_t)); 2533a6d42e7dSPeter Dunlap (void) mdb_snprintf(tempbuf, 6, "%x:", out_addr_component); 2534a6d42e7dSPeter Dunlap len = strlen(tempbuf); 2535a6d42e7dSPeter Dunlap bcopy(tempbuf, ptr, len); 2536a6d42e7dSPeter Dunlap ptr = ptr + len; 2537a6d42e7dSPeter Dunlap addr_component++; 2538a6d42e7dSPeter Dunlap } 2539a6d42e7dSPeter Dunlap *--ptr = '\0'; 2540a6d42e7dSPeter Dunlap } 2541a6d42e7dSPeter Dunlap 2542a6d42e7dSPeter Dunlap 2543a6d42e7dSPeter Dunlap /* 2544a6d42e7dSPeter Dunlap * MDB module linkage information: 2545a6d42e7dSPeter Dunlap * 2546a6d42e7dSPeter Dunlap * We declare a list of structures describing our dcmds, a list of structures 2547a6d42e7dSPeter Dunlap * describing our walkers and a function named _mdb_init to return a pointer 2548a6d42e7dSPeter Dunlap * to our module information. 2549a6d42e7dSPeter Dunlap */ 2550a6d42e7dSPeter Dunlap static const mdb_dcmd_t dcmds[] = { 2551a6d42e7dSPeter Dunlap { "iscsi_tgt", "[-agsctbSRv]", 2552a6d42e7dSPeter Dunlap "iSCSI target information", iscsi_tgt }, 2553a6d42e7dSPeter Dunlap { "iscsi_tpg", "[-v]", 2554a6d42e7dSPeter Dunlap "iSCSI target portal group information", iscsi_tpg }, 2555a6d42e7dSPeter Dunlap { "iscsi_sess", "[-abtvcSRIT]", 2556a6d42e7dSPeter Dunlap "iSCSI session information", iscsi_sess }, 2557a6d42e7dSPeter Dunlap { "iscsi_conn", "[-abtvSRIT]", 2558a6d42e7dSPeter Dunlap "iSCSI connection information", iscsi_conn }, 2559a6d42e7dSPeter Dunlap { "iscsi_task", "[-bSRv]", 2560a6d42e7dSPeter Dunlap "iSCSI task information", iscsi_task }, 2561a6d42e7dSPeter Dunlap { "iscsi_refcnt", "", 2562a6d42e7dSPeter Dunlap "Print audit informtion for idm_refcnt_t", iscsi_refcnt }, 2563a6d42e7dSPeter Dunlap { "iscsi_states", "", 2564a6d42e7dSPeter Dunlap "Dump events and state transitions recorded in an\t" 2565a6d42e7dSPeter Dunlap "\t\tidm_sm_audit_t structure", iscsi_states }, 2566a6d42e7dSPeter Dunlap { "iscsi_isns", "[-epstv]", 2567a6d42e7dSPeter Dunlap "Print iscsit iSNS information", iscsi_isns, iscsi_isns_help }, 2568a6d42e7dSPeter Dunlap { NULL } 2569a6d42e7dSPeter Dunlap }; 2570a6d42e7dSPeter Dunlap 2571a6d42e7dSPeter Dunlap /* 2572a6d42e7dSPeter Dunlap * No walkers for now. Initiator might need some since it doesn't use list_t 2573a6d42e7dSPeter Dunlap */ 2574a6d42e7dSPeter Dunlap 2575a6d42e7dSPeter Dunlap static const mdb_modinfo_t modinfo = { 2576a6d42e7dSPeter Dunlap MDB_API_VERSION, dcmds, NULL 2577a6d42e7dSPeter Dunlap }; 2578a6d42e7dSPeter Dunlap 2579a6d42e7dSPeter Dunlap const mdb_modinfo_t * 2580a6d42e7dSPeter Dunlap _mdb_init(void) 2581a6d42e7dSPeter Dunlap { 2582a6d42e7dSPeter Dunlap return (&modinfo); 2583a6d42e7dSPeter Dunlap } 2584