17c478bd9Sstevel@tonic-gate /* 27c478bd9Sstevel@tonic-gate * CDDL HEADER START 37c478bd9Sstevel@tonic-gate * 47c478bd9Sstevel@tonic-gate * The contents of this file are subject to the terms of the 5186f7fbfSEdward Pilatowicz * Common Development and Distribution License (the "License"). 6186f7fbfSEdward Pilatowicz * You may not use this file except in compliance with the License. 77c478bd9Sstevel@tonic-gate * 87c478bd9Sstevel@tonic-gate * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE 97c478bd9Sstevel@tonic-gate * or http://www.opensolaris.org/os/licensing. 107c478bd9Sstevel@tonic-gate * See the License for the specific language governing permissions 117c478bd9Sstevel@tonic-gate * and limitations under the License. 127c478bd9Sstevel@tonic-gate * 137c478bd9Sstevel@tonic-gate * When distributing Covered Code, include this CDDL HEADER in each 147c478bd9Sstevel@tonic-gate * file and include the License file at usr/src/OPENSOLARIS.LICENSE. 157c478bd9Sstevel@tonic-gate * If applicable, add the following below this CDDL HEADER, with the 167c478bd9Sstevel@tonic-gate * fields enclosed by brackets "[]" replaced with your own identifying 177c478bd9Sstevel@tonic-gate * information: Portions Copyright [yyyy] [name of copyright owner] 187c478bd9Sstevel@tonic-gate * 197c478bd9Sstevel@tonic-gate * CDDL HEADER END 207c478bd9Sstevel@tonic-gate */ 217c478bd9Sstevel@tonic-gate /* 22186f7fbfSEdward Pilatowicz * Copyright 2008 Sun Microsystems, Inc. All rights reserved. 237c478bd9Sstevel@tonic-gate * Use is subject to license terms. 247c478bd9Sstevel@tonic-gate */ 257c478bd9Sstevel@tonic-gate 267c478bd9Sstevel@tonic-gate /* 27*f76ff24cSBryan Cantrill * Copyright 2017 Joyent, Inc. 28*f76ff24cSBryan Cantrill */ 29*f76ff24cSBryan Cantrill 30*f76ff24cSBryan Cantrill /* 317c478bd9Sstevel@tonic-gate * Support for ::set dcmd. The +/-o option processing code is provided in a 327c478bd9Sstevel@tonic-gate * stand-alone function so it can be used by the command-line option processing 337c478bd9Sstevel@tonic-gate * code in mdb_main.c. This facility provides an easy way for us to add more 347c478bd9Sstevel@tonic-gate * configurable options without having to add a new dcmd each time. 357c478bd9Sstevel@tonic-gate */ 367c478bd9Sstevel@tonic-gate 377c478bd9Sstevel@tonic-gate #include <mdb/mdb_target.h> 387c478bd9Sstevel@tonic-gate #include <mdb/mdb_modapi.h> 397c478bd9Sstevel@tonic-gate #include <mdb/mdb_string.h> 407c478bd9Sstevel@tonic-gate #include <mdb/mdb_debug.h> 417c478bd9Sstevel@tonic-gate #include <mdb/mdb.h> 427c478bd9Sstevel@tonic-gate 437c478bd9Sstevel@tonic-gate /*ARGSUSED*/ 447c478bd9Sstevel@tonic-gate static int 457c478bd9Sstevel@tonic-gate opt_set_mflags(int enable, uint_t bits, const char *arg) 467c478bd9Sstevel@tonic-gate { 477c478bd9Sstevel@tonic-gate mdb.m_flags = (mdb.m_flags & ~bits) | (bits & -enable); 487c478bd9Sstevel@tonic-gate return (1); 497c478bd9Sstevel@tonic-gate } 507c478bd9Sstevel@tonic-gate 517c478bd9Sstevel@tonic-gate /*ARGSUSED*/ 527c478bd9Sstevel@tonic-gate static int 537c478bd9Sstevel@tonic-gate opt_set_tflags(int enable, uint_t bits, const char *arg) 547c478bd9Sstevel@tonic-gate { 557c478bd9Sstevel@tonic-gate mdb.m_tgtflags = (mdb.m_tgtflags & ~bits) | (bits & -enable); 567c478bd9Sstevel@tonic-gate return (1); 577c478bd9Sstevel@tonic-gate } 587c478bd9Sstevel@tonic-gate 597c478bd9Sstevel@tonic-gate static int 607c478bd9Sstevel@tonic-gate opt_pager(int enable, uint_t bits, const char *arg) 617c478bd9Sstevel@tonic-gate { 627c478bd9Sstevel@tonic-gate if (enable) 637c478bd9Sstevel@tonic-gate mdb_iob_setflags(mdb.m_out, MDB_IOB_PGENABLE); 647c478bd9Sstevel@tonic-gate else 657c478bd9Sstevel@tonic-gate mdb_iob_clrflags(mdb.m_out, MDB_IOB_PGENABLE); 667c478bd9Sstevel@tonic-gate 677c478bd9Sstevel@tonic-gate return (opt_set_mflags(enable, bits, arg)); 687c478bd9Sstevel@tonic-gate } 697c478bd9Sstevel@tonic-gate 707c478bd9Sstevel@tonic-gate static int 717c478bd9Sstevel@tonic-gate opt_adb(int enable, uint_t bits, const char *arg) 727c478bd9Sstevel@tonic-gate { 737c478bd9Sstevel@tonic-gate if (enable) 747c478bd9Sstevel@tonic-gate (void) mdb_set_prompt(""); 757c478bd9Sstevel@tonic-gate else if (mdb.m_promptlen == 0) 767c478bd9Sstevel@tonic-gate (void) mdb_set_prompt("> "); 777c478bd9Sstevel@tonic-gate 787c478bd9Sstevel@tonic-gate (void) opt_pager(1 - enable, MDB_FL_PAGER, arg); 797c478bd9Sstevel@tonic-gate return (opt_set_mflags(enable, bits, arg)); 807c478bd9Sstevel@tonic-gate } 817c478bd9Sstevel@tonic-gate 827c478bd9Sstevel@tonic-gate /*ARGSUSED*/ 837c478bd9Sstevel@tonic-gate static int 847c478bd9Sstevel@tonic-gate opt_armemlim(int enable, uint_t bits, const char *arg) 857c478bd9Sstevel@tonic-gate { 867c478bd9Sstevel@tonic-gate if (strisnum(arg)) { 877c478bd9Sstevel@tonic-gate mdb.m_armemlim = strtoi(arg); 887c478bd9Sstevel@tonic-gate return (1); 897c478bd9Sstevel@tonic-gate } 907c478bd9Sstevel@tonic-gate if (strcmp(arg, "none") == 0) { 917c478bd9Sstevel@tonic-gate mdb.m_armemlim = MDB_ARR_NOLIMIT; 927c478bd9Sstevel@tonic-gate return (1); 937c478bd9Sstevel@tonic-gate } 947c478bd9Sstevel@tonic-gate return (0); 957c478bd9Sstevel@tonic-gate } 967c478bd9Sstevel@tonic-gate 977c478bd9Sstevel@tonic-gate /*ARGSUSED*/ 987c478bd9Sstevel@tonic-gate static int 997c478bd9Sstevel@tonic-gate opt_arstrlim(int enable, uint_t bits, const char *arg) 1007c478bd9Sstevel@tonic-gate { 1017c478bd9Sstevel@tonic-gate if (strisnum(arg)) { 1027c478bd9Sstevel@tonic-gate mdb.m_arstrlim = strtoi(arg); 1037c478bd9Sstevel@tonic-gate return (1); 1047c478bd9Sstevel@tonic-gate } 1057c478bd9Sstevel@tonic-gate if (strcmp(arg, "none") == 0) { 1067c478bd9Sstevel@tonic-gate mdb.m_arstrlim = MDB_ARR_NOLIMIT; 1077c478bd9Sstevel@tonic-gate return (1); 1087c478bd9Sstevel@tonic-gate } 1097c478bd9Sstevel@tonic-gate return (0); 1107c478bd9Sstevel@tonic-gate } 1117c478bd9Sstevel@tonic-gate 1127c478bd9Sstevel@tonic-gate /*ARGSUSED*/ 1137c478bd9Sstevel@tonic-gate static int 1147c478bd9Sstevel@tonic-gate opt_exec_mode(int enable, uint_t bits, const char *arg) 1157c478bd9Sstevel@tonic-gate { 1167c478bd9Sstevel@tonic-gate if (strcmp(arg, "ask") == 0) { 1177c478bd9Sstevel@tonic-gate mdb.m_execmode = MDB_EM_ASK; 1187c478bd9Sstevel@tonic-gate return (1); 1197c478bd9Sstevel@tonic-gate } else if (strcmp(arg, "stop") == 0) { 1207c478bd9Sstevel@tonic-gate mdb.m_execmode = MDB_EM_STOP; 1217c478bd9Sstevel@tonic-gate return (1); 1227c478bd9Sstevel@tonic-gate } else if (strcmp(arg, "follow") == 0) { 1237c478bd9Sstevel@tonic-gate mdb.m_execmode = MDB_EM_FOLLOW; 1247c478bd9Sstevel@tonic-gate return (1); 1257c478bd9Sstevel@tonic-gate } 1267c478bd9Sstevel@tonic-gate return (0); 1277c478bd9Sstevel@tonic-gate } 1287c478bd9Sstevel@tonic-gate 1297c478bd9Sstevel@tonic-gate /*ARGSUSED*/ 1307c478bd9Sstevel@tonic-gate static int 1317c478bd9Sstevel@tonic-gate opt_fork_mode(int enable, uint_t bits, const char *arg) 1327c478bd9Sstevel@tonic-gate { 1337c478bd9Sstevel@tonic-gate if (strcmp(arg, "ask") == 0) { 1347c478bd9Sstevel@tonic-gate mdb.m_forkmode = MDB_FM_ASK; 1357c478bd9Sstevel@tonic-gate return (1); 1367c478bd9Sstevel@tonic-gate } else if (strcmp(arg, "parent") == 0) { 1377c478bd9Sstevel@tonic-gate mdb.m_forkmode = MDB_FM_PARENT; 1387c478bd9Sstevel@tonic-gate return (1); 1397c478bd9Sstevel@tonic-gate } else if (strcmp(arg, "child") == 0) { 1407c478bd9Sstevel@tonic-gate mdb.m_forkmode = MDB_FM_CHILD; 1417c478bd9Sstevel@tonic-gate return (1); 1427c478bd9Sstevel@tonic-gate } 1437c478bd9Sstevel@tonic-gate return (0); 1447c478bd9Sstevel@tonic-gate } 1457c478bd9Sstevel@tonic-gate 1467c478bd9Sstevel@tonic-gate /*ARGSUSED*/ 1477c478bd9Sstevel@tonic-gate static int 1487c478bd9Sstevel@tonic-gate opt_set_term(int enable, uint_t bits, const char *arg) 1497c478bd9Sstevel@tonic-gate { 1507c478bd9Sstevel@tonic-gate mdb.m_termtype = strdup(arg); 1517c478bd9Sstevel@tonic-gate mdb.m_flags &= ~MDB_FL_TERMGUESS; 1527c478bd9Sstevel@tonic-gate 1537c478bd9Sstevel@tonic-gate return (1); 1547c478bd9Sstevel@tonic-gate } 1557c478bd9Sstevel@tonic-gate 1567c478bd9Sstevel@tonic-gate int 1577c478bd9Sstevel@tonic-gate mdb_set_options(const char *s, int enable) 1587c478bd9Sstevel@tonic-gate { 1597c478bd9Sstevel@tonic-gate static const struct opdesc { 1607c478bd9Sstevel@tonic-gate const char *opt_name; 1617c478bd9Sstevel@tonic-gate int (*opt_func)(int, uint_t, const char *); 1627c478bd9Sstevel@tonic-gate uint_t opt_bits; 1637c478bd9Sstevel@tonic-gate } opdtab[] = { 1647c478bd9Sstevel@tonic-gate { "adb", opt_adb, MDB_FL_REPLAST | MDB_FL_NOMODS | MDB_FL_ADB }, 1657c478bd9Sstevel@tonic-gate { "array_mem_limit", opt_armemlim, 0 }, 1667c478bd9Sstevel@tonic-gate { "array_str_limit", opt_arstrlim, 0 }, 1677c478bd9Sstevel@tonic-gate { "follow_exec_mode", opt_exec_mode, 0 }, 1687c478bd9Sstevel@tonic-gate { "follow_fork_mode", opt_fork_mode, 0 }, 1697c478bd9Sstevel@tonic-gate { "pager", opt_pager, MDB_FL_PAGER }, 1707c478bd9Sstevel@tonic-gate { "term", opt_set_term, 0 }, 1717c478bd9Sstevel@tonic-gate 172*f76ff24cSBryan Cantrill { "autowrap", opt_set_mflags, MDB_FL_AUTOWRAP }, 1737c478bd9Sstevel@tonic-gate { "ignoreeof", opt_set_mflags, MDB_FL_IGNEOF }, 1747c478bd9Sstevel@tonic-gate { "repeatlast", opt_set_mflags, MDB_FL_REPLAST }, 1757c478bd9Sstevel@tonic-gate { "latest", opt_set_mflags, MDB_FL_LATEST }, 1767c478bd9Sstevel@tonic-gate { "noctf", opt_set_mflags, MDB_FL_NOCTF }, 1777c478bd9Sstevel@tonic-gate { "nomods", opt_set_mflags, MDB_FL_NOMODS }, 1787c478bd9Sstevel@tonic-gate { "showlmid", opt_set_mflags, MDB_FL_SHOWLMID }, 179186f7fbfSEdward Pilatowicz { "lmraw", opt_set_mflags, MDB_FL_LMRAW }, 1807c478bd9Sstevel@tonic-gate { "stop_on_bpt_nosym", opt_set_mflags, MDB_FL_BPTNOSYMSTOP }, 1817c478bd9Sstevel@tonic-gate { "write_readback", opt_set_mflags, MDB_FL_READBACK }, 1827c478bd9Sstevel@tonic-gate 1837c478bd9Sstevel@tonic-gate { "allow_io_access", opt_set_tflags, MDB_TGT_F_ALLOWIO }, 1847c478bd9Sstevel@tonic-gate { "nostop", opt_set_tflags, MDB_TGT_F_NOSTOP }, 1857c478bd9Sstevel@tonic-gate { NULL, NULL, 0 } 1867c478bd9Sstevel@tonic-gate }; 1877c478bd9Sstevel@tonic-gate 1887c478bd9Sstevel@tonic-gate const struct opdesc *opp; 1897c478bd9Sstevel@tonic-gate char *buf = strdup(s); 1907c478bd9Sstevel@tonic-gate char *opt, *arg; 1917c478bd9Sstevel@tonic-gate int status = 1; 1927c478bd9Sstevel@tonic-gate 1937c478bd9Sstevel@tonic-gate for (opt = strtok(buf, ","); opt != NULL; opt = strtok(NULL, ",")) { 1947c478bd9Sstevel@tonic-gate if ((arg = strchr(opt, '=')) != NULL) 1957c478bd9Sstevel@tonic-gate *arg++ = '\0'; 1967c478bd9Sstevel@tonic-gate 1977c478bd9Sstevel@tonic-gate for (opp = opdtab; opp->opt_name != NULL; opp++) { 1987c478bd9Sstevel@tonic-gate if (strcmp(opt, opp->opt_name) == 0) { 1997c478bd9Sstevel@tonic-gate if (opp->opt_bits != 0 && arg != NULL) { 2007c478bd9Sstevel@tonic-gate mdb_warn("option does not accept an " 2017c478bd9Sstevel@tonic-gate "argument -- %s\n", opt); 2027c478bd9Sstevel@tonic-gate status = 0; 2037c478bd9Sstevel@tonic-gate } else if (opp->opt_bits == 0 && arg == NULL) { 2047c478bd9Sstevel@tonic-gate mdb_warn("option requires an argument " 2057c478bd9Sstevel@tonic-gate "-- %s\n", opt); 2067c478bd9Sstevel@tonic-gate status = 0; 2077c478bd9Sstevel@tonic-gate } else if (opp->opt_func(enable != 0, 2087c478bd9Sstevel@tonic-gate opp->opt_bits, arg) == 0) { 2097c478bd9Sstevel@tonic-gate mdb_warn("invalid argument for option " 2107c478bd9Sstevel@tonic-gate "%s -- %s\n", opt, arg); 2117c478bd9Sstevel@tonic-gate status = 0; 2127c478bd9Sstevel@tonic-gate } 2137c478bd9Sstevel@tonic-gate break; 2147c478bd9Sstevel@tonic-gate } 2157c478bd9Sstevel@tonic-gate } 2167c478bd9Sstevel@tonic-gate 2177c478bd9Sstevel@tonic-gate if (opp->opt_name == NULL) { 2187c478bd9Sstevel@tonic-gate mdb_warn("invalid debugger option -- %s\n", opt); 2197c478bd9Sstevel@tonic-gate status = 0; 2207c478bd9Sstevel@tonic-gate } 2217c478bd9Sstevel@tonic-gate } 2227c478bd9Sstevel@tonic-gate 2237c478bd9Sstevel@tonic-gate mdb_free(buf, strlen(s) + 1); 2247c478bd9Sstevel@tonic-gate return (status); 2257c478bd9Sstevel@tonic-gate } 2267c478bd9Sstevel@tonic-gate 2277c478bd9Sstevel@tonic-gate static void 2287c478bd9Sstevel@tonic-gate print_path(const char **path, int indent) 2297c478bd9Sstevel@tonic-gate { 2307c478bd9Sstevel@tonic-gate if (path != NULL && *path != NULL) { 2317c478bd9Sstevel@tonic-gate for (mdb_printf("%s\n", *path++); *path != NULL; path++) 2327c478bd9Sstevel@tonic-gate mdb_printf("%*s%s\n", indent, " ", *path); 2337c478bd9Sstevel@tonic-gate } 2347c478bd9Sstevel@tonic-gate mdb_printf("\n"); 2357c478bd9Sstevel@tonic-gate } 2367c478bd9Sstevel@tonic-gate 2377c478bd9Sstevel@tonic-gate #define LABEL_INDENT 26 2387c478bd9Sstevel@tonic-gate 2397c478bd9Sstevel@tonic-gate static void 2407c478bd9Sstevel@tonic-gate print_properties(void) 2417c478bd9Sstevel@tonic-gate { 2427c478bd9Sstevel@tonic-gate int tflags = mdb_tgt_getflags(mdb.m_target); 2437c478bd9Sstevel@tonic-gate uint_t oflags = mdb_iob_getflags(mdb.m_out) & MDB_IOB_AUTOWRAP; 2447c478bd9Sstevel@tonic-gate 2457c478bd9Sstevel@tonic-gate mdb_iob_clrflags(mdb.m_out, MDB_IOB_AUTOWRAP); 2467c478bd9Sstevel@tonic-gate mdb_printf("\n macro path: "); 2477c478bd9Sstevel@tonic-gate print_path(mdb.m_ipath, 14); 2487c478bd9Sstevel@tonic-gate mdb_printf(" module path: "); 2497c478bd9Sstevel@tonic-gate print_path(mdb.m_lpath, 14); 2507c478bd9Sstevel@tonic-gate mdb_iob_setflags(mdb.m_out, oflags); 2517c478bd9Sstevel@tonic-gate 2527c478bd9Sstevel@tonic-gate mdb_printf("%*s %lr (%s)\n", LABEL_INDENT, "symbol matching distance:", 2537c478bd9Sstevel@tonic-gate mdb.m_symdist, mdb.m_symdist ? "absolute mode" : "smart mode"); 2547c478bd9Sstevel@tonic-gate 2557c478bd9Sstevel@tonic-gate mdb_printf("%*s ", LABEL_INDENT, "array member print limit:"); 2567c478bd9Sstevel@tonic-gate if (mdb.m_armemlim != MDB_ARR_NOLIMIT) 2577c478bd9Sstevel@tonic-gate mdb_printf("%u\n", mdb.m_armemlim); 2587c478bd9Sstevel@tonic-gate else 2597c478bd9Sstevel@tonic-gate mdb_printf("none\n"); 2607c478bd9Sstevel@tonic-gate 2617c478bd9Sstevel@tonic-gate mdb_printf(" array string print limit: "); 2627c478bd9Sstevel@tonic-gate if (mdb.m_arstrlim != MDB_ARR_NOLIMIT) 2637c478bd9Sstevel@tonic-gate mdb_printf("%u\n", mdb.m_arstrlim); 2647c478bd9Sstevel@tonic-gate else 2657c478bd9Sstevel@tonic-gate mdb_printf("none\n"); 2667c478bd9Sstevel@tonic-gate 2677c478bd9Sstevel@tonic-gate mdb_printf("%*s \"%s\"\n", LABEL_INDENT, "command prompt:", 2687c478bd9Sstevel@tonic-gate mdb.m_prompt); 2697c478bd9Sstevel@tonic-gate 2707c478bd9Sstevel@tonic-gate mdb_printf("%*s ", LABEL_INDENT, "debugger options:"); 2717c478bd9Sstevel@tonic-gate (void) mdb_inc_indent(LABEL_INDENT + 1); 2727c478bd9Sstevel@tonic-gate 273*f76ff24cSBryan Cantrill /* 274*f76ff24cSBryan Cantrill * The ::set output implicitly relies on "autowrap" being enabled, so 275*f76ff24cSBryan Cantrill * we enable it for the duration of the command. 276*f76ff24cSBryan Cantrill */ 277*f76ff24cSBryan Cantrill oflags = mdb.m_flags; 278*f76ff24cSBryan Cantrill mdb.m_flags |= MDB_FL_AUTOWRAP; 279*f76ff24cSBryan Cantrill 2807c478bd9Sstevel@tonic-gate mdb_printf("follow_exec_mode="); 2817c478bd9Sstevel@tonic-gate switch (mdb.m_execmode) { 2827c478bd9Sstevel@tonic-gate case MDB_EM_ASK: 2837c478bd9Sstevel@tonic-gate mdb_printf("ask"); 2847c478bd9Sstevel@tonic-gate break; 2857c478bd9Sstevel@tonic-gate case MDB_EM_STOP: 2867c478bd9Sstevel@tonic-gate mdb_printf("stop"); 2877c478bd9Sstevel@tonic-gate break; 2887c478bd9Sstevel@tonic-gate case MDB_EM_FOLLOW: 2897c478bd9Sstevel@tonic-gate mdb_printf("follow"); 2907c478bd9Sstevel@tonic-gate break; 2917c478bd9Sstevel@tonic-gate } 2927c478bd9Sstevel@tonic-gate 2937c478bd9Sstevel@tonic-gate #define COMMAFLAG(name) { mdb_printf(", "); mdb_printf(name); } 2947c478bd9Sstevel@tonic-gate 2957c478bd9Sstevel@tonic-gate COMMAFLAG("follow_fork_mode"); 2967c478bd9Sstevel@tonic-gate switch (mdb.m_forkmode) { 2977c478bd9Sstevel@tonic-gate case MDB_FM_ASK: 2987c478bd9Sstevel@tonic-gate mdb_printf("ask"); 2997c478bd9Sstevel@tonic-gate break; 3007c478bd9Sstevel@tonic-gate case MDB_FM_PARENT: 3017c478bd9Sstevel@tonic-gate mdb_printf("parent"); 3027c478bd9Sstevel@tonic-gate break; 3037c478bd9Sstevel@tonic-gate case MDB_FM_CHILD: 3047c478bd9Sstevel@tonic-gate mdb_printf("child"); 3057c478bd9Sstevel@tonic-gate break; 3067c478bd9Sstevel@tonic-gate } 3077c478bd9Sstevel@tonic-gate 3087c478bd9Sstevel@tonic-gate if (mdb.m_flags & MDB_FL_ADB) 3097c478bd9Sstevel@tonic-gate COMMAFLAG("adb"); 310*f76ff24cSBryan Cantrill if (oflags & MDB_FL_AUTOWRAP) 311*f76ff24cSBryan Cantrill COMMAFLAG("autowrap"); 3127c478bd9Sstevel@tonic-gate if (mdb.m_flags & MDB_FL_IGNEOF) 3137c478bd9Sstevel@tonic-gate COMMAFLAG("ignoreeof"); 314186f7fbfSEdward Pilatowicz if (mdb.m_flags & MDB_FL_LMRAW) 315186f7fbfSEdward Pilatowicz COMMAFLAG("lmraw"); 3167c478bd9Sstevel@tonic-gate if (mdb.m_flags & MDB_FL_PAGER) 3177c478bd9Sstevel@tonic-gate COMMAFLAG("pager"); 3187c478bd9Sstevel@tonic-gate if (mdb.m_flags & MDB_FL_REPLAST) 3197c478bd9Sstevel@tonic-gate COMMAFLAG("repeatlast"); 3207c478bd9Sstevel@tonic-gate if (mdb.m_flags & MDB_FL_SHOWLMID) 3217c478bd9Sstevel@tonic-gate COMMAFLAG("showlmid"); 3227c478bd9Sstevel@tonic-gate if (mdb.m_flags & MDB_FL_BPTNOSYMSTOP) 3237c478bd9Sstevel@tonic-gate COMMAFLAG("stop_on_bpt_nosym"); 3247c478bd9Sstevel@tonic-gate if (mdb.m_flags & MDB_FL_READBACK) 3257c478bd9Sstevel@tonic-gate COMMAFLAG("write_readback"); 3267c478bd9Sstevel@tonic-gate mdb_printf("\n"); 3277c478bd9Sstevel@tonic-gate (void) mdb_dec_indent(LABEL_INDENT + 1); 3287c478bd9Sstevel@tonic-gate 3297c478bd9Sstevel@tonic-gate mdb_printf("%*s ", LABEL_INDENT, "target options:"); 3307c478bd9Sstevel@tonic-gate (void) mdb_inc_indent(LABEL_INDENT + 1); 3317c478bd9Sstevel@tonic-gate 3327c478bd9Sstevel@tonic-gate if (tflags & MDB_TGT_F_RDWR) 3337c478bd9Sstevel@tonic-gate mdb_printf("read-write"); 3347c478bd9Sstevel@tonic-gate else 3357c478bd9Sstevel@tonic-gate mdb_printf("read-only"); 3367c478bd9Sstevel@tonic-gate if (tflags & MDB_TGT_F_ALLOWIO) 3377c478bd9Sstevel@tonic-gate COMMAFLAG("allow-io-access"); 3387c478bd9Sstevel@tonic-gate if (tflags & MDB_TGT_F_FORCE) 3397c478bd9Sstevel@tonic-gate COMMAFLAG("force-attach"); 3407c478bd9Sstevel@tonic-gate if (tflags & MDB_TGT_F_PRELOAD) 3417c478bd9Sstevel@tonic-gate COMMAFLAG("preload-syms"); 3427c478bd9Sstevel@tonic-gate if (tflags & MDB_TGT_F_NOLOAD) 3437c478bd9Sstevel@tonic-gate COMMAFLAG("no-load-objs"); 3447c478bd9Sstevel@tonic-gate if (tflags & MDB_TGT_F_NOSTOP) 3457c478bd9Sstevel@tonic-gate COMMAFLAG("no-stop"); 3467c478bd9Sstevel@tonic-gate mdb_printf("\n"); 3477c478bd9Sstevel@tonic-gate (void) mdb_dec_indent(LABEL_INDENT + 1); 348*f76ff24cSBryan Cantrill 349*f76ff24cSBryan Cantrill mdb.m_flags = oflags; 3507c478bd9Sstevel@tonic-gate } 3517c478bd9Sstevel@tonic-gate 3527c478bd9Sstevel@tonic-gate /*ARGSUSED*/ 3537c478bd9Sstevel@tonic-gate int 3547c478bd9Sstevel@tonic-gate cmd_set(uintptr_t addr, uint_t flags, int argc, const mdb_arg_t *argv) 3557c478bd9Sstevel@tonic-gate { 3567c478bd9Sstevel@tonic-gate const char *opt_I = NULL, *opt_L = NULL, *opt_P = NULL, *opt_o = NULL; 3577c478bd9Sstevel@tonic-gate const char *opt_plus_o = NULL, *opt_D = NULL; 3587c478bd9Sstevel@tonic-gate uint_t opt_w = FALSE, opt_plus_w = FALSE, opt_W = FALSE; 3597c478bd9Sstevel@tonic-gate uint_t opt_plus_W = FALSE, opt_F = FALSE; 3607c478bd9Sstevel@tonic-gate uintptr_t opt_s = (uintptr_t)(long)-1; 3617c478bd9Sstevel@tonic-gate 3627c478bd9Sstevel@tonic-gate int tflags = 0; 3637c478bd9Sstevel@tonic-gate int i; 3647c478bd9Sstevel@tonic-gate 3657c478bd9Sstevel@tonic-gate if (flags & DCMD_ADDRSPEC) 3667c478bd9Sstevel@tonic-gate return (DCMD_USAGE); 3677c478bd9Sstevel@tonic-gate 3687c478bd9Sstevel@tonic-gate /* 3697c478bd9Sstevel@tonic-gate * If no options are specified, print out the current set of target 3707c478bd9Sstevel@tonic-gate * and debugger properties that can be modified with ::set. 3717c478bd9Sstevel@tonic-gate */ 3727c478bd9Sstevel@tonic-gate if (argc == 0) { 3737c478bd9Sstevel@tonic-gate print_properties(); 3747c478bd9Sstevel@tonic-gate return (DCMD_OK); 3757c478bd9Sstevel@tonic-gate } 3767c478bd9Sstevel@tonic-gate 3777c478bd9Sstevel@tonic-gate while ((i = mdb_getopts(argc, argv, 3787c478bd9Sstevel@tonic-gate 'F', MDB_OPT_SETBITS, TRUE, &opt_F, 3797c478bd9Sstevel@tonic-gate 'I', MDB_OPT_STR, &opt_I, 3807c478bd9Sstevel@tonic-gate 'L', MDB_OPT_STR, &opt_L, 3817c478bd9Sstevel@tonic-gate 'P', MDB_OPT_STR, &opt_P, 3827c478bd9Sstevel@tonic-gate 'o', MDB_OPT_STR, &opt_o, 3837c478bd9Sstevel@tonic-gate 's', MDB_OPT_UINTPTR, &opt_s, 3847c478bd9Sstevel@tonic-gate 'w', MDB_OPT_SETBITS, TRUE, &opt_w, 3857c478bd9Sstevel@tonic-gate 'W', MDB_OPT_SETBITS, TRUE, &opt_W, 3867c478bd9Sstevel@tonic-gate 'D', MDB_OPT_STR, &opt_D, NULL)) != argc) { 3877c478bd9Sstevel@tonic-gate uint_t n = 1; 3887c478bd9Sstevel@tonic-gate 3897c478bd9Sstevel@tonic-gate argv += i; /* skip past args we processed */ 3907c478bd9Sstevel@tonic-gate argc -= i; /* adjust argc */ 3917c478bd9Sstevel@tonic-gate 3927c478bd9Sstevel@tonic-gate if (argv[0].a_type != MDB_TYPE_STRING) 3937c478bd9Sstevel@tonic-gate return (DCMD_USAGE); 3947c478bd9Sstevel@tonic-gate 3957c478bd9Sstevel@tonic-gate if (strcmp(argv->a_un.a_str, "+W") == 0) 3967c478bd9Sstevel@tonic-gate opt_plus_W = TRUE; 3977c478bd9Sstevel@tonic-gate else if (strcmp(argv->a_un.a_str, "+w") == 0) 3987c478bd9Sstevel@tonic-gate opt_plus_w = TRUE; 3997c478bd9Sstevel@tonic-gate else if (strcmp(argv->a_un.a_str, "+o") == 0 && 4007c478bd9Sstevel@tonic-gate argc >= 2 && argv[1].a_type == MDB_TYPE_STRING) { 4017c478bd9Sstevel@tonic-gate opt_plus_o = argv[1].a_un.a_str; 4027c478bd9Sstevel@tonic-gate n = 2; 4037c478bd9Sstevel@tonic-gate } else 4047c478bd9Sstevel@tonic-gate return (DCMD_USAGE); 4057c478bd9Sstevel@tonic-gate 4067c478bd9Sstevel@tonic-gate /* remove the flag and possible argument */ 4077c478bd9Sstevel@tonic-gate argv += n; 4087c478bd9Sstevel@tonic-gate argc -= n; 4097c478bd9Sstevel@tonic-gate } 4107c478bd9Sstevel@tonic-gate 4117c478bd9Sstevel@tonic-gate if ((opt_w && opt_plus_w) || (opt_W && opt_plus_W)) 4127c478bd9Sstevel@tonic-gate return (DCMD_USAGE); 4137c478bd9Sstevel@tonic-gate 4147c478bd9Sstevel@tonic-gate /* 4157c478bd9Sstevel@tonic-gate * Handle -w, -/+W and -F first: as these options modify the target, 4167c478bd9Sstevel@tonic-gate * they are the only ::set changes that can potentially fail. We'll 4177c478bd9Sstevel@tonic-gate * use these flags to modify a copy of the target's t_flags, which we'll 4187c478bd9Sstevel@tonic-gate * then pass to the target's setflags op. This allows the target to 4197c478bd9Sstevel@tonic-gate * detect newly-set and newly-cleared flags by comparing the passed 4207c478bd9Sstevel@tonic-gate * value to the current t_flags. 4217c478bd9Sstevel@tonic-gate */ 4227c478bd9Sstevel@tonic-gate tflags = mdb_tgt_getflags(mdb.m_target); 4237c478bd9Sstevel@tonic-gate 4247c478bd9Sstevel@tonic-gate if (opt_w) 4257c478bd9Sstevel@tonic-gate tflags |= MDB_TGT_F_RDWR; 4267c478bd9Sstevel@tonic-gate if (opt_plus_w) 4277c478bd9Sstevel@tonic-gate tflags &= ~MDB_TGT_F_RDWR; 4287c478bd9Sstevel@tonic-gate if (opt_W) 4297c478bd9Sstevel@tonic-gate tflags |= MDB_TGT_F_ALLOWIO; 4307c478bd9Sstevel@tonic-gate if (opt_plus_W) 4317c478bd9Sstevel@tonic-gate tflags &= ~MDB_TGT_F_ALLOWIO; 4327c478bd9Sstevel@tonic-gate if (opt_F) 4337c478bd9Sstevel@tonic-gate tflags |= MDB_TGT_F_FORCE; 4347c478bd9Sstevel@tonic-gate 4357c478bd9Sstevel@tonic-gate if (tflags != mdb_tgt_getflags(mdb.m_target) && 4367c478bd9Sstevel@tonic-gate mdb_tgt_setflags(mdb.m_target, tflags) == -1) 4377c478bd9Sstevel@tonic-gate return (DCMD_ERR); 4387c478bd9Sstevel@tonic-gate 4397c478bd9Sstevel@tonic-gate /* 4407c478bd9Sstevel@tonic-gate * Now handle everything that either can't fail or we don't care if 4417c478bd9Sstevel@tonic-gate * it does. Note that we handle +/-o first in case another option 4427c478bd9Sstevel@tonic-gate * overrides a change made implicity by a +/-o argument (e.g. -P). 4437c478bd9Sstevel@tonic-gate */ 4447c478bd9Sstevel@tonic-gate if (opt_o != NULL) 4457c478bd9Sstevel@tonic-gate (void) mdb_set_options(opt_o, TRUE); 4467c478bd9Sstevel@tonic-gate if (opt_plus_o != NULL) 4477c478bd9Sstevel@tonic-gate (void) mdb_set_options(opt_plus_o, FALSE); 4487c478bd9Sstevel@tonic-gate if (opt_I != NULL) { 4497c478bd9Sstevel@tonic-gate #ifdef _KMDB 4507c478bd9Sstevel@tonic-gate mdb_warn("macro path cannot be set under kmdb\n"); 4517c478bd9Sstevel@tonic-gate #else 4527c478bd9Sstevel@tonic-gate mdb_set_ipath(opt_I); 4537c478bd9Sstevel@tonic-gate #endif 4547c478bd9Sstevel@tonic-gate } 4557c478bd9Sstevel@tonic-gate if (opt_L != NULL) 4567c478bd9Sstevel@tonic-gate mdb_set_lpath(opt_L); 4577c478bd9Sstevel@tonic-gate if (opt_P != NULL) 4587c478bd9Sstevel@tonic-gate (void) mdb_set_prompt(opt_P); 4597c478bd9Sstevel@tonic-gate if (opt_s != (uintptr_t)-1) 4607c478bd9Sstevel@tonic-gate mdb.m_symdist = (size_t)opt_s; 4617c478bd9Sstevel@tonic-gate if (opt_D != NULL && (i = mdb_dstr2mode(opt_D)) != MDB_DBG_HELP) 4627c478bd9Sstevel@tonic-gate mdb_dmode((uint_t)i); 4637c478bd9Sstevel@tonic-gate 4647c478bd9Sstevel@tonic-gate return (DCMD_OK); 4657c478bd9Sstevel@tonic-gate } 466