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 "code/relocInfo.hpp" 27 #include "compiler/compilerDefinitions.hpp" 28 #include "oops/metadata.hpp" 29 #include "runtime/os.hpp" 30 #include "interpreter/invocationCounter.hpp" 31 #include "runtime/arguments.hpp" 32 #include "runtime/flags/jvmFlag.hpp" 33 #include "runtime/flags/jvmFlagConstraintsCompiler.hpp" 34 #include "runtime/globals.hpp" 35 #include "runtime/globals_extension.hpp" 36 37 JVMFlag::Error AliasLevelConstraintFunc(intx value, bool verbose) { 38 if ((value <= 1) && (Arguments::mode() == Arguments::_comp || Arguments::mode() == Arguments::_mixed)) { 39 JVMFlag::printError(verbose, 40 "AliasLevel (" INTX_FORMAT ") is not " 41 "compatible with -Xcomp or -Xmixed\n", 42 value); 43 return JVMFlag::VIOLATES_CONSTRAINT; 44 } else { 45 return JVMFlag::SUCCESS; 46 } 47 } 48 49 /** 50 * Validate the minimum number of compiler threads needed to run the 51 * JVM. The following configurations are possible. 52 * 53 * 1) The JVM is build using an interpreter only. As a result, the minimum number of 54 * compiler threads is 0. 55 * 2) The JVM is build using the compiler(s) and tiered compilation is disabled. As 56 * a result, either C1 or C2 is used, so the minimum number of compiler threads is 1. 57 * 3) The JVM is build using the compiler(s) and tiered compilation is enabled. However, 58 * the option "TieredStopAtLevel < CompLevel_full_optimization". As a result, only 59 * C1 can be used, so the minimum number of compiler threads is 1. 60 * 4) The JVM is build using the compilers and tiered compilation is enabled. The option 61 * 'TieredStopAtLevel = CompLevel_full_optimization' (the default value). As a result, 62 * the minimum number of compiler threads is 2. 63 */ 64 JVMFlag::Error CICompilerCountConstraintFunc(intx value, bool verbose) { 65 int min_number_of_compiler_threads = 0; 66 #if !defined(COMPILER1) && !defined(COMPILER2) && !INCLUDE_JVMCI 67 // case 1 68 #else 69 if (!TieredCompilation || (TieredStopAtLevel < CompLevel_full_optimization)) { 70 min_number_of_compiler_threads = 1; // case 2 or case 3 71 } else { 72 min_number_of_compiler_threads = 2; // case 4 (tiered) 73 } 74 #endif 75 76 // The default CICompilerCount's value is CI_COMPILER_COUNT. 77 // With a client VM, -XX:+TieredCompilation causes TieredCompilation 78 // to be true here (the option is validated later) and 79 // min_number_of_compiler_threads to exceed CI_COMPILER_COUNT. 80 min_number_of_compiler_threads = MIN2(min_number_of_compiler_threads, CI_COMPILER_COUNT); 81 82 if (value < (intx)min_number_of_compiler_threads) { 83 JVMFlag::printError(verbose, 84 "CICompilerCount (" INTX_FORMAT ") must be " 85 "at least %d \n", 86 value, min_number_of_compiler_threads); 87 return JVMFlag::VIOLATES_CONSTRAINT; 88 } else { 89 return JVMFlag::SUCCESS; 90 } 91 } 92 93 JVMFlag::Error AllocatePrefetchDistanceConstraintFunc(intx value, bool verbose) { 94 if (value < 0 || value > 512) { 95 JVMFlag::printError(verbose, 96 "AllocatePrefetchDistance (" INTX_FORMAT ") must be " 97 "between 0 and %d\n", 98 AllocatePrefetchDistance, 512); 99 return JVMFlag::VIOLATES_CONSTRAINT; 100 } 101 102 return JVMFlag::SUCCESS; 103 } 104 105 JVMFlag::Error AllocatePrefetchStepSizeConstraintFunc(intx value, bool verbose) { 106 if (AllocatePrefetchStyle == 3) { 107 if (value % wordSize != 0) { 108 JVMFlag::printError(verbose, 109 "AllocatePrefetchStepSize (" INTX_FORMAT ") must be multiple of %d\n", 110 value, wordSize); 111 return JVMFlag::VIOLATES_CONSTRAINT; 112 } 113 } 114 return JVMFlag::SUCCESS; 115 } 116 117 JVMFlag::Error AllocatePrefetchInstrConstraintFunc(intx value, bool verbose) { 118 intx max_value = max_intx; 119 #if defined(SPARC) 120 max_value = 1; 121 #elif defined(X86) 122 max_value = 3; 123 #endif 124 if (value < 0 || value > max_value) { 125 JVMFlag::printError(verbose, 126 "AllocatePrefetchInstr (" INTX_FORMAT ") must be " 127 "between 0 and " INTX_FORMAT "\n", value, max_value); 128 return JVMFlag::VIOLATES_CONSTRAINT; 129 } 130 131 return JVMFlag::SUCCESS; 132 } 133 134 JVMFlag::Error CompileThresholdConstraintFunc(intx value, bool verbose) { 135 if (value < 0 || value > INT_MAX >> InvocationCounter::count_shift) { 136 JVMFlag::printError(verbose, 137 "CompileThreshold (" INTX_FORMAT ") " 138 "must be between 0 and %d\n", 139 value, 140 INT_MAX >> InvocationCounter::count_shift); 141 return JVMFlag::VIOLATES_CONSTRAINT; 142 } 143 144 return JVMFlag::SUCCESS; 145 } 146 147 JVMFlag::Error OnStackReplacePercentageConstraintFunc(intx value, bool verbose) { 148 int backward_branch_limit; 149 if (ProfileInterpreter) { 150 if (OnStackReplacePercentage < InterpreterProfilePercentage) { 151 JVMFlag::printError(verbose, 152 "OnStackReplacePercentage (" INTX_FORMAT ") must be " 153 "larger than InterpreterProfilePercentage (" INTX_FORMAT ")\n", 154 OnStackReplacePercentage, InterpreterProfilePercentage); 155 return JVMFlag::VIOLATES_CONSTRAINT; 156 } 157 158 backward_branch_limit = ((CompileThreshold * (OnStackReplacePercentage - InterpreterProfilePercentage)) / 100) 159 << InvocationCounter::count_shift; 160 161 if (backward_branch_limit < 0) { 162 JVMFlag::printError(verbose, 163 "CompileThreshold * (InterpreterProfilePercentage - OnStackReplacePercentage) / 100 = " 164 INTX_FORMAT " " 165 "must be between 0 and %d, try changing " 166 "CompileThreshold, InterpreterProfilePercentage, and/or OnStackReplacePercentage\n", 167 (CompileThreshold * (OnStackReplacePercentage - InterpreterProfilePercentage)) / 100, 168 INT_MAX >> InvocationCounter::count_shift); 169 return JVMFlag::VIOLATES_CONSTRAINT; 170 } 171 } else { 172 if (OnStackReplacePercentage < 0 ) { 173 JVMFlag::printError(verbose, 174 "OnStackReplacePercentage (" INTX_FORMAT ") must be " 175 "non-negative\n", OnStackReplacePercentage); 176 return JVMFlag::VIOLATES_CONSTRAINT; 177 } 178 179 backward_branch_limit = ((CompileThreshold * OnStackReplacePercentage) / 100) 180 << InvocationCounter::count_shift; 181 182 if (backward_branch_limit < 0) { 183 JVMFlag::printError(verbose, 184 "CompileThreshold * OnStackReplacePercentage / 100 = " INTX_FORMAT " " 185 "must be between 0 and %d, try changing " 186 "CompileThreshold and/or OnStackReplacePercentage\n", 187 (CompileThreshold * OnStackReplacePercentage) / 100, 188 INT_MAX >> InvocationCounter::count_shift); 189 return JVMFlag::VIOLATES_CONSTRAINT; 190 } 191 } 192 return JVMFlag::SUCCESS; 193 } 194 195 JVMFlag::Error CodeCacheSegmentSizeConstraintFunc(uintx value, bool verbose) { 196 if (CodeCacheSegmentSize < (uintx)CodeEntryAlignment) { 197 JVMFlag::printError(verbose, 198 "CodeCacheSegmentSize (" UINTX_FORMAT ") must be " 199 "larger than or equal to CodeEntryAlignment (" INTX_FORMAT ") " 200 "to align entry points\n", 201 CodeCacheSegmentSize, CodeEntryAlignment); 202 return JVMFlag::VIOLATES_CONSTRAINT; 203 } 204 205 if (CodeCacheSegmentSize < sizeof(jdouble)) { 206 JVMFlag::printError(verbose, 207 "CodeCacheSegmentSize (" UINTX_FORMAT ") must be " 208 "at least " SIZE_FORMAT " to align constants\n", 209 CodeCacheSegmentSize, sizeof(jdouble)); 210 return JVMFlag::VIOLATES_CONSTRAINT; 211 } 212 213 #ifdef COMPILER2 214 if (CodeCacheSegmentSize < (uintx)OptoLoopAlignment) { 215 JVMFlag::printError(verbose, 216 "CodeCacheSegmentSize (" UINTX_FORMAT ") must be " 217 "larger than or equal to OptoLoopAlignment (" INTX_FORMAT ") " 218 "to align inner loops\n", 219 CodeCacheSegmentSize, OptoLoopAlignment); 220 return JVMFlag::VIOLATES_CONSTRAINT; 221 } 222 #endif 223 224 return JVMFlag::SUCCESS; 225 } 226 227 JVMFlag::Error CompilerThreadPriorityConstraintFunc(intx value, bool verbose) { 228 #ifdef SOLARIS 229 if ((value < MinimumPriority || value > MaximumPriority) && 230 (value != -1) && (value != -FXCriticalPriority)) { 231 JVMFlag::printError(verbose, 232 "CompileThreadPriority (" INTX_FORMAT ") must be " 233 "between %d and %d inclusively or -1 (means no change) " 234 "or %d (special value for critical thread class/priority)\n", 235 value, MinimumPriority, MaximumPriority, -FXCriticalPriority); 236 return JVMFlag::VIOLATES_CONSTRAINT; 237 } 238 #endif 239 240 return JVMFlag::SUCCESS; 241 } 242 243 JVMFlag::Error CodeEntryAlignmentConstraintFunc(intx value, bool verbose) { 244 #ifdef SPARC 245 if (CodeEntryAlignment % relocInfo::addr_unit() != 0) { 246 JVMFlag::printError(verbose, 247 "CodeEntryAlignment (" INTX_FORMAT ") must be " 248 "multiple of NOP size\n", CodeEntryAlignment); 249 return JVMFlag::VIOLATES_CONSTRAINT; 250 } 251 #endif 252 253 if (!is_power_of_2(value)) { 254 JVMFlag::printError(verbose, 255 "CodeEntryAlignment (" INTX_FORMAT ") must be " 256 "a power of two\n", CodeEntryAlignment); 257 return JVMFlag::VIOLATES_CONSTRAINT; 258 } 259 260 if (CodeEntryAlignment < 16) { 261 JVMFlag::printError(verbose, 262 "CodeEntryAlignment (" INTX_FORMAT ") must be " 263 "greater than or equal to %d\n", 264 CodeEntryAlignment, 16); 265 return JVMFlag::VIOLATES_CONSTRAINT; 266 } 267 268 return JVMFlag::SUCCESS; 269 } 270 271 JVMFlag::Error OptoLoopAlignmentConstraintFunc(intx value, bool verbose) { 272 if (!is_power_of_2(value)) { 273 JVMFlag::printError(verbose, 274 "OptoLoopAlignment (" INTX_FORMAT ") " 275 "must be a power of two\n", 276 value); 277 return JVMFlag::VIOLATES_CONSTRAINT; 278 } 279 280 // Relevant on ppc, s390, sparc. Will be optimized where 281 // addr_unit() == 1. 282 if (OptoLoopAlignment % relocInfo::addr_unit() != 0) { 283 JVMFlag::printError(verbose, 284 "OptoLoopAlignment (" INTX_FORMAT ") must be " 285 "multiple of NOP size (%d)\n", 286 value, relocInfo::addr_unit()); 287 return JVMFlag::VIOLATES_CONSTRAINT; 288 } 289 290 return JVMFlag::SUCCESS; 291 } 292 293 JVMFlag::Error ArraycopyDstPrefetchDistanceConstraintFunc(uintx value, bool verbose) { 294 if (value >= 4032) { 295 JVMFlag::printError(verbose, 296 "ArraycopyDstPrefetchDistance (" UINTX_FORMAT ") must be" 297 "between 0 and 4031\n", value); 298 return JVMFlag::VIOLATES_CONSTRAINT; 299 } 300 301 return JVMFlag::SUCCESS; 302 } 303 304 JVMFlag::Error ArraycopySrcPrefetchDistanceConstraintFunc(uintx value, bool verbose) { 305 if (value >= 4032) { 306 JVMFlag::printError(verbose, 307 "ArraycopySrcPrefetchDistance (" UINTX_FORMAT ") must be" 308 "between 0 and 4031\n", value); 309 return JVMFlag::VIOLATES_CONSTRAINT; 310 } 311 312 return JVMFlag::SUCCESS; 313 } 314 315 JVMFlag::Error TypeProfileLevelConstraintFunc(uintx value, bool verbose) { 316 for (int i = 0; i < 3; i++) { 317 if (value % 10 > 2) { 318 JVMFlag::printError(verbose, 319 "Invalid value (" UINTX_FORMAT ") " 320 "in TypeProfileLevel at position %d\n", value, i); 321 return JVMFlag::VIOLATES_CONSTRAINT; 322 } 323 value = value / 10; 324 } 325 326 return JVMFlag::SUCCESS; 327 } 328 329 JVMFlag::Error InitArrayShortSizeConstraintFunc(intx value, bool verbose) { 330 if (value % BytesPerLong != 0) { 331 return JVMFlag::VIOLATES_CONSTRAINT; 332 } else { 333 return JVMFlag::SUCCESS; 334 } 335 } 336 337 #ifdef COMPILER2 338 JVMFlag::Error InteriorEntryAlignmentConstraintFunc(intx value, bool verbose) { 339 if (InteriorEntryAlignment > CodeEntryAlignment) { 340 JVMFlag::printError(verbose, 341 "InteriorEntryAlignment (" INTX_FORMAT ") must be " 342 "less than or equal to CodeEntryAlignment (" INTX_FORMAT ")\n", 343 InteriorEntryAlignment, CodeEntryAlignment); 344 return JVMFlag::VIOLATES_CONSTRAINT; 345 } 346 347 #ifdef SPARC 348 if (InteriorEntryAlignment % relocInfo::addr_unit() != 0) { 349 JVMFlag::printError(verbose, 350 "InteriorEntryAlignment (" INTX_FORMAT ") must be " 351 "multiple of NOP size\n"); 352 return JVMFlag::VIOLATES_CONSTRAINT; 353 } 354 #endif 355 356 if (!is_power_of_2(value)) { 357 JVMFlag::printError(verbose, 358 "InteriorEntryAlignment (" INTX_FORMAT ") must be " 359 "a power of two\n", InteriorEntryAlignment); 360 return JVMFlag::VIOLATES_CONSTRAINT; 361 } 362 363 int minimum_alignment = 16; 364 #if defined(SPARC) || (defined(X86) && !defined(AMD64)) 365 minimum_alignment = 4; 366 #elif defined(S390) 367 minimum_alignment = 2; 368 #endif 369 370 if (InteriorEntryAlignment < minimum_alignment) { 371 JVMFlag::printError(verbose, 372 "InteriorEntryAlignment (" INTX_FORMAT ") must be " 373 "greater than or equal to %d\n", 374 InteriorEntryAlignment, minimum_alignment); 375 return JVMFlag::VIOLATES_CONSTRAINT; 376 } 377 378 return JVMFlag::SUCCESS; 379 } 380 381 JVMFlag::Error NodeLimitFudgeFactorConstraintFunc(intx value, bool verbose) { 382 if (value < MaxNodeLimit * 2 / 100 || value > MaxNodeLimit * 40 / 100) { 383 JVMFlag::printError(verbose, 384 "NodeLimitFudgeFactor must be between 2%% and 40%% " 385 "of MaxNodeLimit (" INTX_FORMAT ")\n", 386 MaxNodeLimit); 387 return JVMFlag::VIOLATES_CONSTRAINT; 388 } 389 390 return JVMFlag::SUCCESS; 391 } 392 #endif // COMPILER2 393 394 JVMFlag::Error RTMTotalCountIncrRateConstraintFunc(int value, bool verbose) { 395 #if INCLUDE_RTM_OPT 396 if (UseRTMLocking && !is_power_of_2(RTMTotalCountIncrRate)) { 397 JVMFlag::printError(verbose, 398 "RTMTotalCountIncrRate (%d) must be " 399 "a power of 2, resetting it to 64\n", 400 RTMTotalCountIncrRate); 401 FLAG_SET_DEFAULT(RTMTotalCountIncrRate, 64); 402 } 403 #endif 404 405 return JVMFlag::SUCCESS; 406 }