1 /*
   2  * Copyright (c) 2015, 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.
   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 #include "precompiled.hpp"
  26 #include "gc/g1/heapRegionBounds.inline.hpp"
  27 #include "gc/g1/jvmFlagConstraintsG1.hpp"
  28 #include "runtime/globals.hpp"
  29 #include "utilities/globalDefinitions.hpp"
  30 
  31 JVMFlag::Error G1RSetRegionEntriesConstraintFunc(intx value, bool verbose) {
  32   if (!UseG1GC) return JVMFlag::SUCCESS;
  33 
  34   // Default value of G1RSetRegionEntries=0 means will be set ergonomically.
  35   // Minimum value is 1.
  36   if (FLAG_IS_CMDLINE(G1RSetRegionEntries) && (value < 1)) {
  37     JVMFlag::printError(verbose,
  38                         "G1RSetRegionEntries (" INTX_FORMAT ") must be "
  39                         "greater than or equal to 1\n",
  40                         value);
  41     return JVMFlag::VIOLATES_CONSTRAINT;
  42   } else {
  43     return JVMFlag::SUCCESS;
  44   }
  45 }
  46 
  47 JVMFlag::Error G1RSetSparseRegionEntriesConstraintFunc(intx value, bool verbose) {
  48   if (!UseG1GC) return JVMFlag::SUCCESS;
  49 
  50   // Default value of G1RSetSparseRegionEntries=0 means will be set ergonomically.
  51   // Minimum value is 1.
  52   if (FLAG_IS_CMDLINE(G1RSetSparseRegionEntries) && (value < 1)) {
  53     JVMFlag::printError(verbose,
  54                         "G1RSetSparseRegionEntries (" INTX_FORMAT ") must be "
  55                         "greater than or equal to 1\n",
  56                         value);
  57     return JVMFlag::VIOLATES_CONSTRAINT;
  58   } else {
  59     return JVMFlag::SUCCESS;
  60   }
  61 }
  62 
  63 JVMFlag::Error G1HeapRegionSizeConstraintFunc(size_t value, bool verbose) {
  64   if (!UseG1GC) return JVMFlag::SUCCESS;
  65 
  66   // Default value of G1HeapRegionSize=0 means will be set ergonomically.
  67   if (FLAG_IS_CMDLINE(G1HeapRegionSize) && (value < HeapRegionBounds::min_size())) {
  68     JVMFlag::printError(verbose,
  69                         "G1HeapRegionSize (" SIZE_FORMAT ") must be "
  70                         "greater than or equal to ergonomic heap region minimum size\n",
  71                         value);
  72     return JVMFlag::VIOLATES_CONSTRAINT;
  73   } else {
  74     return JVMFlag::SUCCESS;
  75   }
  76 }
  77 
  78 JVMFlag::Error G1NewSizePercentConstraintFunc(uintx value, bool verbose) {
  79   if (!UseG1GC) return JVMFlag::SUCCESS;
  80 
  81   if (value > G1MaxNewSizePercent) {
  82     JVMFlag::printError(verbose,
  83                         "G1NewSizePercent (" UINTX_FORMAT ") must be "
  84                         "less than or equal to G1MaxNewSizePercent (" UINTX_FORMAT ")\n",
  85                         value, G1MaxNewSizePercent);
  86     return JVMFlag::VIOLATES_CONSTRAINT;
  87   } else {
  88     return JVMFlag::SUCCESS;
  89   }
  90 }
  91 
  92 JVMFlag::Error G1MaxNewSizePercentConstraintFunc(uintx value, bool verbose) {
  93   if (!UseG1GC) return JVMFlag::SUCCESS;
  94 
  95   if (value < G1NewSizePercent) {
  96     JVMFlag::printError(verbose,
  97                         "G1MaxNewSizePercent (" UINTX_FORMAT ") must be "
  98                         "greater than or equal to G1NewSizePercent (" UINTX_FORMAT ")\n",
  99                         value, G1NewSizePercent);
 100     return JVMFlag::VIOLATES_CONSTRAINT;
 101   } else {
 102     return JVMFlag::SUCCESS;
 103   }
 104 }
 105 
 106 JVMFlag::Error MaxGCPauseMillisConstraintFuncG1(uintx value, bool verbose) {
 107   if (UseG1GC && FLAG_IS_CMDLINE(MaxGCPauseMillis) && (value >= GCPauseIntervalMillis)) {
 108     JVMFlag::printError(verbose,
 109                         "MaxGCPauseMillis (" UINTX_FORMAT ") must be "
 110                         "less than GCPauseIntervalMillis (" UINTX_FORMAT ")\n",
 111                         value, GCPauseIntervalMillis);
 112     return JVMFlag::VIOLATES_CONSTRAINT;
 113   }
 114 
 115   return JVMFlag::SUCCESS;
 116 }
 117 
 118 JVMFlag::Error GCPauseIntervalMillisConstraintFuncG1(uintx value, bool verbose) {
 119   if (UseG1GC) {
 120     if (FLAG_IS_CMDLINE(GCPauseIntervalMillis)) {
 121       if (value < 1) {
 122         JVMFlag::printError(verbose,
 123                             "GCPauseIntervalMillis (" UINTX_FORMAT ") must be "
 124                             "greater than or equal to 1\n",
 125                             value);
 126         return JVMFlag::VIOLATES_CONSTRAINT;
 127       }
 128 
 129       if (FLAG_IS_DEFAULT(MaxGCPauseMillis)) {
 130         JVMFlag::printError(verbose,
 131                             "GCPauseIntervalMillis cannot be set "
 132                             "without setting MaxGCPauseMillis\n");
 133         return JVMFlag::VIOLATES_CONSTRAINT;
 134       }
 135 
 136       if (value <= MaxGCPauseMillis) {
 137         JVMFlag::printError(verbose,
 138                             "GCPauseIntervalMillis (" UINTX_FORMAT ") must be "
 139                             "greater than MaxGCPauseMillis (" UINTX_FORMAT ")\n",
 140                             value, MaxGCPauseMillis);
 141         return JVMFlag::VIOLATES_CONSTRAINT;
 142       }
 143     }
 144   }
 145 
 146   return JVMFlag::SUCCESS;
 147 }
 148 
 149 JVMFlag::Error NewSizeConstraintFuncG1(size_t value, bool verbose) {
 150 #ifdef _LP64
 151   // Overflow would happen for uint type variable of YoungGenSizer::_min_desired_young_length
 152   // when the value to be assigned exceeds uint range.
 153   // i.e. result of '(uint)(NewSize / region size(1~32MB))'
 154   // So maximum of NewSize should be 'max_juint * 1M'
 155   if (UseG1GC && (value > (max_juint * 1 * M))) {
 156     JVMFlag::printError(verbose,
 157                         "NewSize (" SIZE_FORMAT ") must be less than ergonomic maximum value\n",
 158                         value);
 159     return JVMFlag::VIOLATES_CONSTRAINT;
 160   }
 161 #endif // _LP64
 162   return JVMFlag::SUCCESS;
 163 }
 164 
 165 size_t MaxSizeForHeapAlignmentG1() {
 166   return HeapRegionBounds::max_size();
 167 }