1/* 2 * Copyright (c) 2011, 2015, Oracle and/or its affiliates. All rights reserved. 3 * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. 4 * 5 * This code is free software; you can redistribute it and/or modify it 6 * under the terms of the GNU General Public License version 2 only, as 7 * published by the Free Software Foundation. 8 * 9 * This code is distributed in the hope that it will be useful, but WITHOUT 10 * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or 11 * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License 12 * version 2 for more details (a copy is included in the LICENSE file that 13 * accompanied this code). 14 * 15 * You should have received a copy of the GNU General Public License version 16 * 2 along with this work; if not, write to the Free Software Foundation, 17 * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA. 18 * 19 * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA 20 * or visit www.oracle.com if you need additional information or have any 21 * questions. 22 * 23 */ 24 25#ifndef SHARE_VM_SERVICES_DIAGNOSTICCOMMAND_HPP 26#define SHARE_VM_SERVICES_DIAGNOSTICCOMMAND_HPP 27 28#include "classfile/vmSymbols.hpp" 29#include "runtime/arguments.hpp" 30#include "runtime/os.hpp" 31#include "runtime/vmThread.hpp" 32#include "services/diagnosticArgument.hpp" 33#include "services/diagnosticCommand.hpp" 34#include "services/diagnosticCommand_ext.hpp" 35#include "services/diagnosticFramework.hpp" 36#include "utilities/macros.hpp" 37#include "utilities/ostream.hpp" 38#include "oops/method.hpp" 39 40class HelpDCmd : public DCmdWithParser { 41protected: 42 DCmdArgument<bool> _all; 43 DCmdArgument<char*> _cmd; 44public: 45 HelpDCmd(outputStream* output, bool heap); 46 static const char* name() { return "help"; } 47 static const char* description() { 48 return "For more information about a specific command use 'help <command>'. " 49 "With no argument this will show a list of available commands. " 50 "'help all' will show help for all commands."; 51 } 52 static const char* impact() { return "Low"; } 53 static int num_arguments(); 54 virtual void execute(DCmdSource source, TRAPS); 55}; 56 57class VersionDCmd : public DCmd { 58public: 59 VersionDCmd(outputStream* output, bool heap) : DCmd(output,heap) { } 60 static const char* name() { return "VM.version"; } 61 static const char* description() { 62 return "Print JVM version information."; 63 } 64 static const char* impact() { return "Low"; } 65 static const JavaPermission permission() { 66 JavaPermission p = {"java.util.PropertyPermission", 67 "java.vm.version", "read"}; 68 return p; 69 } 70 static int num_arguments() { return 0; } 71 virtual void execute(DCmdSource source, TRAPS); 72}; 73 74class CommandLineDCmd : public DCmd { 75public: 76 CommandLineDCmd(outputStream* output, bool heap) : DCmd(output, heap) { } 77 static const char* name() { return "VM.command_line"; } 78 static const char* description() { 79 return "Print the command line used to start this VM instance."; 80 } 81 static const char* impact() { return "Low"; } 82 static const JavaPermission permission() { 83 JavaPermission p = {"java.lang.management.ManagementPermission", 84 "monitor", NULL}; 85 return p; 86 } 87 static int num_arguments() { return 0; } 88 virtual void execute(DCmdSource source, TRAPS) { 89 Arguments::print_on(_output); 90 } 91}; 92 93// See also: get_system_properties in attachListener.cpp 94class PrintSystemPropertiesDCmd : public DCmd { 95public: 96 PrintSystemPropertiesDCmd(outputStream* output, bool heap) : DCmd(output, heap) { } 97 static const char* name() { return "VM.system_properties"; } 98 static const char* description() { 99 return "Print system properties."; 100 } 101 static const char* impact() { 102 return "Low"; 103 } 104 static const JavaPermission permission() { 105 JavaPermission p = {"java.util.PropertyPermission", 106 "*", "read"}; 107 return p; 108 } 109 static int num_arguments() { return 0; } 110 virtual void execute(DCmdSource source, TRAPS); 111}; 112 113// See also: print_flag in attachListener.cpp 114class PrintVMFlagsDCmd : public DCmdWithParser { 115protected: 116 DCmdArgument<bool> _all; 117public: 118 PrintVMFlagsDCmd(outputStream* output, bool heap); 119 static const char* name() { return "VM.flags"; } 120 static const char* description() { 121 return "Print VM flag options and their current values."; 122 } 123 static const char* impact() { 124 return "Low"; 125 } 126 static const JavaPermission permission() { 127 JavaPermission p = {"java.lang.management.ManagementPermission", 128 "monitor", NULL}; 129 return p; 130 } 131 static int num_arguments(); 132 virtual void execute(DCmdSource source, TRAPS); 133}; 134 135class SetVMFlagDCmd : public DCmdWithParser { 136protected: 137 DCmdArgument<char*> _flag; 138 DCmdArgument<char*> _value; 139 140public: 141 SetVMFlagDCmd(outputStream* output, bool heap); 142 static const char* name() { return "VM.set_flag"; } 143 static const char* description() { 144 return "Sets VM flag option using the provided value."; 145 } 146 static const char* impact() { 147 return "Low"; 148 } 149 static const JavaPermission permission() { 150 JavaPermission p = {"java.lang.management.ManagementPermission", 151 "control", NULL}; 152 return p; 153 } 154 static int num_arguments(); 155 virtual void execute(DCmdSource source, TRAPS); 156}; 157 158class JVMTIDataDumpDCmd : public DCmd { 159public: 160 JVMTIDataDumpDCmd(outputStream* output, bool heap) : DCmd(output, heap) { } 161 static const char* name() { return "JVMTI.data_dump"; } 162 static const char* description() { 163 return "Signal the JVM to do a data-dump request for JVMTI."; 164 } 165 static const char* impact() { 166 return "High"; 167 } 168 static const JavaPermission permission() { 169 JavaPermission p = {"java.lang.management.ManagementPermission", 170 "monitor", NULL}; 171 return p; 172 } 173 static int num_arguments() { return 0; } 174 virtual void execute(DCmdSource source, TRAPS); 175}; 176 177#if INCLUDE_SERVICES 178#if INCLUDE_JVMTI 179class JVMTIAgentLoadDCmd : public DCmdWithParser { 180protected: 181 DCmdArgument<char*> _libpath; 182 DCmdArgument<char*> _option; 183public: 184 JVMTIAgentLoadDCmd(outputStream* output, bool heap); 185 static const char* name() { return "JVMTI.agent_load"; } 186 static const char* description() { 187 return "Load JVMTI native agent."; 188 } 189 static const char* impact() { return "Low"; } 190 static const JavaPermission permission() { 191 JavaPermission p = {"java.lang.management.ManagementPermission", 192 "control", NULL}; 193 return p; 194 } 195 static int num_arguments(); 196 virtual void execute(DCmdSource source, TRAPS); 197}; 198#endif // INCLUDE_JVMTI 199#endif // INCLUDE_SERVICES 200 201class VMDynamicLibrariesDCmd : public DCmd { 202public: 203 VMDynamicLibrariesDCmd(outputStream* output, bool heap); 204 static const char* name() { 205 return "VM.dynlibs"; 206 } 207 static const char* description() { 208 return "Print loaded dynamic libraries."; 209 } 210 static const char* impact() { 211 return "Low"; 212 } 213 static const JavaPermission permission() { 214 JavaPermission p = {"java.lang.management.ManagementPermission", 215 "monitor", NULL}; 216 return p; 217 } 218 static int num_arguments() { 219 return 0; 220 }; 221 virtual void execute(DCmdSource source, TRAPS); 222}; 223 224class VMUptimeDCmd : public DCmdWithParser { 225protected: 226 DCmdArgument<bool> _date; 227public: 228 VMUptimeDCmd(outputStream* output, bool heap); 229 static const char* name() { return "VM.uptime"; } 230 static const char* description() { 231 return "Print VM uptime."; 232 } 233 static const char* impact() { 234 return "Low"; 235 } 236 static int num_arguments(); 237 virtual void execute(DCmdSource source, TRAPS); 238}; 239 240class VMInfoDCmd : public DCmd { 241public: 242 VMInfoDCmd(outputStream* output, bool heap) : DCmd(output, heap) { } 243 static const char* name() { return "VM.info"; } 244 static const char* description() { 245 return "Print information about JVM environment and status."; 246 } 247 static const char* impact() { return "Low"; } 248 static const JavaPermission permission() { 249 JavaPermission p = {"java.lang.management.ManagementPermission", 250 "monitor", NULL}; 251 return p; 252 } 253 static int num_arguments() { return 0; } 254 virtual void execute(DCmdSource source, TRAPS); 255}; 256 257class SystemGCDCmd : public DCmd { 258public: 259 SystemGCDCmd(outputStream* output, bool heap) : DCmd(output, heap) { } 260 static const char* name() { return "GC.run"; } 261 static const char* description() { 262 return "Call java.lang.System.gc()."; 263 } 264 static const char* impact() { 265 return "Medium: Depends on Java heap size and content."; 266 } 267 static int num_arguments() { return 0; } 268 virtual void execute(DCmdSource source, TRAPS); 269}; 270 271class RunFinalizationDCmd : public DCmd { 272public: 273 RunFinalizationDCmd(outputStream* output, bool heap) : DCmd(output, heap) { } 274 static const char* name() { return "GC.run_finalization"; } 275 static const char* description() { 276 return "Call java.lang.System.runFinalization()."; 277 } 278 static const char* impact() { 279 return "Medium: Depends on Java content."; 280 } 281 static int num_arguments() { return 0; } 282 virtual void execute(DCmdSource source, TRAPS); 283}; 284 285class HeapInfoDCmd : public DCmd { 286public: 287 HeapInfoDCmd(outputStream* output, bool heap) : DCmd(output, heap) { } 288 static const char* name() { return "GC.heap_info"; } 289 static const char* description() { 290 return "Provide generic Java heap information."; 291 } 292 static const char* impact() { 293 return "Medium"; 294 } 295 static int num_arguments() { return 0; } 296 static const JavaPermission permission() { 297 JavaPermission p = {"java.lang.management.ManagementPermission", 298 "monitor", NULL}; 299 return p; 300 } 301 302 virtual void execute(DCmdSource source, TRAPS); 303}; 304 305class FinalizerInfoDCmd : public DCmd { 306public: 307 FinalizerInfoDCmd(outputStream* output, bool heap) : DCmd(output, heap) { } 308 static const char* name() { return "GC.finalizer_info"; } 309 static const char* description() { 310 return "Provide information about Java finalization queue."; 311 } 312 static const char* impact() { 313 return "Medium"; 314 } 315 static int num_arguments() { return 0; } 316 static const JavaPermission permission() { 317 JavaPermission p = {"java.lang.management.ManagementPermission", 318 "monitor", NULL}; 319 return p; 320 } 321 322 virtual void execute(DCmdSource source, TRAPS); 323}; 324 325#if INCLUDE_SERVICES // Heap dumping supported 326// See also: dump_heap in attachListener.cpp 327class HeapDumpDCmd : public DCmdWithParser { 328protected: 329 DCmdArgument<char*> _filename; 330 DCmdArgument<bool> _all; 331public: 332 HeapDumpDCmd(outputStream* output, bool heap); 333 static const char* name() { 334 return "GC.heap_dump"; 335 } 336 static const char* description() { 337 return "Generate a HPROF format dump of the Java heap."; 338 } 339 static const char* impact() { 340 return "High: Depends on Java heap size and content. " 341 "Request a full GC unless the '-all' option is specified."; 342 } 343 static const JavaPermission permission() { 344 JavaPermission p = {"java.lang.management.ManagementPermission", 345 "monitor", NULL}; 346 return p; 347 } 348 static int num_arguments(); 349 virtual void execute(DCmdSource source, TRAPS); 350}; 351#endif // INCLUDE_SERVICES 352 353// See also: inspectheap in attachListener.cpp 354class ClassHistogramDCmd : public DCmdWithParser { 355protected: 356 DCmdArgument<bool> _all; 357public: 358 ClassHistogramDCmd(outputStream* output, bool heap); 359 static const char* name() { 360 return "GC.class_histogram"; 361 } 362 static const char* description() { 363 return "Provide statistics about the Java heap usage."; 364 } 365 static const char* impact() { 366 return "High: Depends on Java heap size and content."; 367 } 368 static const JavaPermission permission() { 369 JavaPermission p = {"java.lang.management.ManagementPermission", 370 "monitor", NULL}; 371 return p; 372 } 373 static int num_arguments(); 374 virtual void execute(DCmdSource source, TRAPS); 375}; 376 377class ClassStatsDCmd : public DCmdWithParser { 378protected: 379 DCmdArgument<bool> _all; 380 DCmdArgument<bool> _csv; 381 DCmdArgument<bool> _help; 382 DCmdArgument<char*> _columns; 383public: 384 ClassStatsDCmd(outputStream* output, bool heap); 385 static const char* name() { 386 return "GC.class_stats"; 387 } 388 static const char* description() { 389 return "Provide statistics about Java class meta data."; 390 } 391 static const char* impact() { 392 return "High: Depends on Java heap size and content."; 393 } 394 static int num_arguments(); 395 virtual void execute(DCmdSource source, TRAPS); 396}; 397 398 399class ClassHierarchyDCmd : public DCmdWithParser { 400protected: 401 DCmdArgument<bool> _print_interfaces; // true if inherited interfaces should be printed. 402 DCmdArgument<bool> _print_subclasses; // true if subclasses of the specified classname should be printed. 403 DCmdArgument<char*> _classname; // Optional single class name whose hierarchy should be printed. 404public: 405 ClassHierarchyDCmd(outputStream* output, bool heap); 406 static const char* name() { 407 return "VM.class_hierarchy"; 408 } 409 static const char* description() { 410 return "Print a list of all loaded classes, indented to show the class hiearchy. " 411 "The name of each class is followed by the ClassLoaderData* of its ClassLoader, " 412 "or \"null\" if loaded by the bootstrap class loader."; 413 } 414 static const char* impact() { 415 return "Medium: Depends on number of loaded classes."; 416 } 417 static const JavaPermission permission() { 418 JavaPermission p = {"java.lang.management.ManagementPermission", 419 "monitor", NULL}; 420 return p; 421 } 422 static int num_arguments(); 423 virtual void execute(DCmdSource source, TRAPS); 424}; 425 426class TouchedMethodsDCmd : public DCmdWithParser { 427public: 428 TouchedMethodsDCmd(outputStream* output, bool heap); 429 static const char* name() { 430 return "VM.print_touched_methods"; 431 } 432 static const char* description() { 433 return "Print all methods that have ever been touched during the lifetime of this JVM."; 434 } 435 static const char* impact() { 436 return "Medium: Depends on Java content."; 437 } 438 static int num_arguments(); 439 virtual void execute(DCmdSource source, TRAPS); 440}; 441 442// See also: thread_dump in attachListener.cpp 443class ThreadDumpDCmd : public DCmdWithParser { 444protected: 445 DCmdArgument<bool> _locks; 446public: 447 ThreadDumpDCmd(outputStream* output, bool heap); 448 static const char* name() { return "Thread.print"; } 449 static const char* description() { 450 return "Print all threads with stacktraces."; 451 } 452 static const char* impact() { 453 return "Medium: Depends on the number of threads."; 454 } 455 static const JavaPermission permission() { 456 JavaPermission p = {"java.lang.management.ManagementPermission", 457 "monitor", NULL}; 458 return p; 459 } 460 static int num_arguments(); 461 virtual void execute(DCmdSource source, TRAPS); 462}; 463 464// Enhanced JMX Agent support 465 466class JMXStartRemoteDCmd : public DCmdWithParser { 467 468 // Explicitly list all properties that could be 469 // passed to Agent.startRemoteManagementAgent() 470 // com.sun.management is omitted 471 472 DCmdArgument<char *> _config_file; 473 DCmdArgument<char *> _jmxremote_host; 474 DCmdArgument<char *> _jmxremote_port; 475 DCmdArgument<char *> _jmxremote_rmi_port; 476 DCmdArgument<char *> _jmxremote_ssl; 477 DCmdArgument<char *> _jmxremote_registry_ssl; 478 DCmdArgument<char *> _jmxremote_authenticate; 479 DCmdArgument<char *> _jmxremote_password_file; 480 DCmdArgument<char *> _jmxremote_access_file; 481 DCmdArgument<char *> _jmxremote_login_config; 482 DCmdArgument<char *> _jmxremote_ssl_enabled_cipher_suites; 483 DCmdArgument<char *> _jmxremote_ssl_enabled_protocols; 484 DCmdArgument<char *> _jmxremote_ssl_need_client_auth; 485 DCmdArgument<char *> _jmxremote_ssl_config_file; 486 487 // JDP support 488 // Keep autodiscovery char* not bool to pass true/false 489 // as property value to java level. 490 DCmdArgument<char *> _jmxremote_autodiscovery; 491 DCmdArgument<jlong> _jdp_port; 492 DCmdArgument<char *> _jdp_address; 493 DCmdArgument<char *> _jdp_source_addr; 494 DCmdArgument<jlong> _jdp_ttl; 495 DCmdArgument<jlong> _jdp_pause; 496 DCmdArgument<char *> _jdp_name; 497 498public: 499 JMXStartRemoteDCmd(outputStream *output, bool heap_allocated); 500 501 static const char *name() { 502 return "ManagementAgent.start"; 503 } 504 505 static const char *description() { 506 return "Start remote management agent."; 507 } 508 509 static int num_arguments(); 510 511 virtual void execute(DCmdSource source, TRAPS); 512 513}; 514 515class JMXStartLocalDCmd : public DCmd { 516 517 // Explicitly request start of local agent, 518 // it will not be started by start dcmd 519 520 521public: 522 JMXStartLocalDCmd(outputStream *output, bool heap_allocated); 523 524 static const char *name() { 525 return "ManagementAgent.start_local"; 526 } 527 528 static const char *description() { 529 return "Start local management agent."; 530 } 531 532 virtual void execute(DCmdSource source, TRAPS); 533 534}; 535 536class JMXStopRemoteDCmd : public DCmd { 537public: 538 JMXStopRemoteDCmd(outputStream *output, bool heap_allocated) : 539 DCmd(output, heap_allocated) { 540 // Do Nothing 541 } 542 543 static const char *name() { 544 return "ManagementAgent.stop"; 545 } 546 547 static const char *description() { 548 return "Stop remote management agent."; 549 } 550 551 virtual void execute(DCmdSource source, TRAPS); 552}; 553 554// Print the JMX system status 555class JMXStatusDCmd : public DCmd { 556public: 557 JMXStatusDCmd(outputStream *output, bool heap_allocated); 558 559 static const char *name() { 560 return "ManagementAgent.status"; 561 } 562 563 static const char *description() { 564 return "Print the management agent status."; 565 } 566 567 static const JavaPermission permission() { 568 JavaPermission p = {"java.lang.management.ManagementPermission", 569 "monitor", NULL}; 570 return p; 571 } 572 573 virtual void execute(DCmdSource source, TRAPS); 574 575}; 576 577class CompileQueueDCmd : public DCmd { 578public: 579 CompileQueueDCmd(outputStream* output, bool heap) : DCmd(output, heap) {} 580 static const char* name() { 581 return "Compiler.queue"; 582 } 583 static const char* description() { 584 return "Print methods queued for compilation."; 585 } 586 static const char* impact() { 587 return "Low"; 588 } 589 static const JavaPermission permission() { 590 JavaPermission p = {"java.lang.management.ManagementPermission", 591 "monitor", NULL}; 592 return p; 593 } 594 static int num_arguments() { return 0; } 595 virtual void execute(DCmdSource source, TRAPS); 596}; 597 598class CodeListDCmd : public DCmd { 599public: 600 CodeListDCmd(outputStream* output, bool heap) : DCmd(output, heap) {} 601 static const char* name() { 602 return "Compiler.codelist"; 603 } 604 static const char* description() { 605 return "Print all compiled methods in code cache that are alive"; 606 } 607 static const char* impact() { 608 return "Medium"; 609 } 610 static const JavaPermission permission() { 611 JavaPermission p = {"java.lang.management.ManagementPermission", 612 "monitor", NULL}; 613 return p; 614 } 615 static int num_arguments() { return 0; } 616 virtual void execute(DCmdSource source, TRAPS); 617}; 618 619 620class CodeCacheDCmd : public DCmd { 621public: 622 CodeCacheDCmd(outputStream* output, bool heap) : DCmd(output, heap) {} 623 static const char* name() { 624 return "Compiler.codecache"; 625 } 626 static const char* description() { 627 return "Print code cache layout and bounds."; 628 } 629 static const char* impact() { 630 return "Low"; 631 } 632 static const JavaPermission permission() { 633 JavaPermission p = {"java.lang.management.ManagementPermission", 634 "monitor", NULL}; 635 return p; 636 } 637 static int num_arguments() { return 0; } 638 virtual void execute(DCmdSource source, TRAPS); 639}; 640 641class CompilerDirectivesPrintDCmd : public DCmd { 642public: 643 CompilerDirectivesPrintDCmd(outputStream* output, bool heap) : DCmd(output, heap) {} 644 static const char* name() { 645 return "Compiler.directives_print"; 646 } 647 static const char* description() { 648 return "Print all active compiler directives."; 649 } 650 static const char* impact() { 651 return "Low"; 652 } 653 static const JavaPermission permission() { 654 JavaPermission p = {"java.lang.management.ManagementPermission", 655 "monitor", NULL}; 656 return p; 657 } 658 static int num_arguments() { return 0; } 659 virtual void execute(DCmdSource source, TRAPS); 660}; 661 662class CompilerDirectivesRemoveDCmd : public DCmd { 663public: 664 CompilerDirectivesRemoveDCmd(outputStream* output, bool heap) : DCmd(output, heap) {} 665 static const char* name() { 666 return "Compiler.directives_remove"; 667 } 668 static const char* description() { 669 return "Remove latest added compiler directive."; 670 } 671 static const char* impact() { 672 return "Low"; 673 } 674 static const JavaPermission permission() { 675 JavaPermission p = {"java.lang.management.ManagementPermission", 676 "monitor", NULL}; 677 return p; 678 } 679 static int num_arguments() { return 0; } 680 virtual void execute(DCmdSource source, TRAPS); 681}; 682 683class CompilerDirectivesAddDCmd : public DCmdWithParser { 684protected: 685 DCmdArgument<char*> _filename; 686public: 687 CompilerDirectivesAddDCmd(outputStream* output, bool heap); 688 static const char* name() { 689 return "Compiler.directives_add"; 690 } 691 static const char* description() { 692 return "Add compiler directives from file."; 693 } 694 static const char* impact() { 695 return "Low"; 696 } 697 static const JavaPermission permission() { 698 JavaPermission p = {"java.lang.management.ManagementPermission", 699 "monitor", NULL}; 700 return p; 701 } 702 static int num_arguments(); 703 virtual void execute(DCmdSource source, TRAPS); 704}; 705 706class CompilerDirectivesClearDCmd : public DCmd { 707public: 708 CompilerDirectivesClearDCmd(outputStream* output, bool heap) : DCmd(output, heap) {} 709 static const char* name() { 710 return "Compiler.directives_clear"; 711 } 712 static const char* description() { 713 return "Remove all compiler directives."; 714 } 715 static const char* impact() { 716 return "Low"; 717 } 718 static const JavaPermission permission() { 719 JavaPermission p = {"java.lang.management.ManagementPermission", 720 "monitor", NULL}; 721 return p; 722 } 723 static int num_arguments() { return 0; } 724 virtual void execute(DCmdSource source, TRAPS); 725}; 726 727#endif // SHARE_VM_SERVICES_DIAGNOSTICCOMMAND_HPP 728