1 /*
   2  * Copyright (c) 2016, 2018, 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.  Oracle designates this
   8  * particular file as subject to the "Classpath" exception as provided
   9  * by Oracle in the LICENSE file that accompanied this code.
  10  *
  11  * This code is distributed in the hope that it will be useful, but WITHOUT
  12  * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
  13  * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
  14  * version 2 for more details (a copy is included in the LICENSE file that
  15  * accompanied this code).
  16  *
  17  * You should have received a copy of the GNU General Public License version
  18  * 2 along with this work; if not, write to the Free Software Foundation,
  19  * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
  20  *
  21  * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
  22  * or visit www.oracle.com if you need additional information or have any
  23  * questions.
  24  */
  25 
  26 package jdk.jfr.internal.dcmd;
  27 
  28 
  29 
  30 import jdk.jfr.internal.LogLevel;
  31 import jdk.jfr.internal.LogTag;
  32 import jdk.jfr.internal.Logger;
  33 import jdk.jfr.internal.Options;
  34 import jdk.jfr.internal.Repository;
  35 import jdk.jfr.internal.SecuritySupport.SafePath;
  36 
  37 /**
  38  * JFR.configure - invoked from native
  39  *
  40  */
  41 //Instantiated by native
  42 final class DCmdConfigure extends AbstractDCmd {
  43     /**
  44      * Execute JFR.configure.
  45      *
  46      * @param repositoryPath the path
  47      * @param dumpPath path to dump to on fatal error (oom)
  48      * @param stackDepth depth of stack traces
  49      * @param globalBufferCount number of global buffers
  50      * @param globalBufferSize size of global buffers
  51      * @param threadBufferSize size of thread buffer for events
  52      * @param maxChunkSize threshold at which a new chunk is created in the disk repository
  53      * @param sampleThreads if thread sampling should be enabled
  54      *
  55      * @return result
  56 
  57      * @throws DCmdException
  58      *             if the dump could not be completed
  59      */
  60     public String execute
  61     (
  62             String repositoryPath,
  63             String dumpPath,
  64             Integer stackDepth,
  65             Long globalBufferCount,
  66             Long globalBufferSize,
  67             Long threadBufferSize,
  68             Long memorySize,
  69             Long maxChunkSize,
  70             Boolean sampleThreads
  71 
  72     ) throws DCmdException {
  73         if (Logger.shouldLog(LogTag.JFR_DCMD, LogLevel.DEBUG)) {
  74             Logger.log(LogTag.JFR_DCMD, LogLevel.DEBUG, "Executing DCmdConfigure: repositorypath=" + repositoryPath +
  75                     ", dumppath=" + dumpPath +
  76                     ", stackdepth=" + stackDepth +
  77                     ", globalbuffercount=" + globalBufferCount +
  78                     ", globalbuffersize=" + globalBufferSize +
  79                     ", thread_buffer_size" + threadBufferSize +
  80                     ", memorysize" + memorySize +
  81                     ", maxchunksize=" + maxChunkSize +
  82                     ", samplethreads" + sampleThreads);
  83         }
  84 
  85 
  86         boolean updated = false;
  87         if (repositoryPath != null) {
  88             try {
  89                 SafePath s = new SafePath(repositoryPath);
  90                 Repository.getRepository().setBasePath(s);
  91                 Logger.log(LogTag.JFR, LogLevel.INFO, "Base repository path set to " + repositoryPath);
  92             } catch (Exception e) {
  93                 throw new DCmdException("Could not use " + repositoryPath + " as repository. " + e.getMessage(), e);
  94             }
  95             printRepositoryPath();
  96             updated = true;
  97         }
  98 
  99         if (dumpPath != null)  {
 100             Options.setDumpPath(new SafePath(dumpPath));
 101             Logger.log(LogTag.JFR, LogLevel.INFO, "Emergency dump path set to " + dumpPath);
 102             printDumpPath();
 103             updated = true;
 104         }
 105 
 106         if (stackDepth != null)  {
 107             Options.setStackDepth(stackDepth);
 108             Logger.log(LogTag.JFR, LogLevel.INFO, "Stack depth set to " + stackDepth);
 109             printStackDepth();
 110             updated = true;
 111         }
 112 
 113         if (globalBufferCount != null)  {
 114             Options.setGlobalBufferCount(globalBufferCount);
 115             Logger.log(LogTag.JFR, LogLevel.INFO, "Global buffer count set to " + globalBufferCount);
 116             printGlobalBufferCount();
 117             updated = true;
 118         }
 119 
 120         if (globalBufferSize != null)  {
 121             Options.setGlobalBufferSize(globalBufferSize);
 122             Logger.log(LogTag.JFR, LogLevel.INFO, "Global buffer size set to " + globalBufferSize);
 123             printGlobalBufferSize();
 124             updated = true;
 125         }
 126 
 127         if (threadBufferSize != null)  {
 128             Options.setThreadBufferSize(threadBufferSize);
 129             Logger.log(LogTag.JFR, LogLevel.INFO, "Thread buffer size set to " + threadBufferSize);
 130             printThreadBufferSize();
 131             updated = true;
 132         }
 133 
 134         if (memorySize != null) {
 135             Options.setMemorySize(memorySize);
 136             Logger.log(LogTag.JFR, LogLevel.INFO, "Memory size set to " + memorySize);
 137             printMemorySize();
 138             updated = true;
 139         }
 140 
 141         if (maxChunkSize != null)  {
 142             Options.setMaxChunkSize(maxChunkSize);
 143             Logger.log(LogTag.JFR, LogLevel.INFO, "Max chunk size set to " + maxChunkSize);
 144             printMaxChunkSize();
 145             updated = true;
 146         }
 147 
 148         if (sampleThreads != null)  {
 149             Options.setSampleThreads(sampleThreads);
 150             Logger.log(LogTag.JFR, LogLevel.INFO, "Sample threads set to " + sampleThreads);
 151             printSampleThreads();
 152             updated = true;
 153         }
 154 
 155         if (!updated) {
 156             println("Current configuration:");
 157             println();
 158             printRepositoryPath();
 159             printStackDepth();
 160             printGlobalBufferCount();
 161             printGlobalBufferSize();
 162             printThreadBufferSize();
 163             printMemorySize();
 164             printMaxChunkSize();
 165             printSampleThreads();
 166         }
 167         return getResult();
 168     }
 169 
 170     private void printRepositoryPath() {
 171         print("Repository path: ");
 172         printPath(Repository.getRepository().getRepositoryPath());
 173         println();
 174     }
 175 
 176     private void printDumpPath() {
 177         print("Dump path: ");
 178         printPath(Options.getDumpPath());
 179         println();
 180     }
 181 
 182     private void printSampleThreads() {
 183         println("Sample threads: " + Options.getSampleThreads());
 184     }
 185 
 186     private void printStackDepth() {
 187         println("Stack depth: " +  Options.getStackDepth());
 188     }
 189 
 190     private void printGlobalBufferCount() {
 191         println("Global buffer count: " +  Options.getGlobalBufferCount());
 192     }
 193 
 194     private void printGlobalBufferSize() {
 195         print("Global buffer size: ");
 196         printBytes(Options.getGlobalBufferSize());
 197         println();
 198     }
 199 
 200     private void printThreadBufferSize() {
 201         print("Thread buffer size: ");
 202         printBytes(Options.getThreadBufferSize());
 203         println();
 204     }
 205 
 206     private void printMemorySize() {
 207         print("Memory size: ");
 208         printBytes(Options.getMemorySize());
 209         println();
 210     }
 211 
 212     private void printMaxChunkSize() {
 213         print("Max chunk size: ");
 214         printBytes(Options.getMaxChunkSize());
 215         println();
 216     }
 217 }