Book a Demo!
CoCalc Logo Icon
StoreFeaturesDocsShareSupportNewsAboutPoliciesSign UpSign In
PojavLauncherTeam
GitHub Repository: PojavLauncherTeam/mobile
Path: blob/master/test/hotspot/jtreg/vmTestbase/nsk/share/gc/ArgumentHandler.java
41161 views
1
/*
2
* Copyright (c) 2003, 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
package nsk.share.gc;
25
26
import nsk.share.*;
27
28
/**
29
* Parser for GC tests' arguments.
30
* <p>
31
* <code>ArgumentHandler</code> handles specific command line arguments
32
* related to way of execution of a test in addition to general arguments
33
* recognized by {@link ArgumentParser <code>ArgumentParser</code>}.
34
* <p>
35
* Following is the list of specific options for <code>ArgumentHandler</code>:
36
* <ul>
37
* <li><code>-iterations="<i>value</i>"</code>, where <i>value</i> must either
38
* be "infinity", or an integer number, greater than 0. This parameter
39
* specifies the number of iterations to run the testcase. If the value is
40
* "infinity", then the test will be run for at least <code>gcTimeout</code>
41
* minutes. Otherwise, the testcase will be repeated for
42
* <code>iterations</code> times.
43
* <li><code>-gcTimeout="<i>value</i>"</code>, where <i>value</i> must be an
44
* integer number, greater than 0. If <i>infinity</i> is set to
45
* <code>iterations</code>, then the test consider <code>gcTimeout</code>
46
* argument to run the test for at least specified number of minutes.
47
* <li><code>-threads="<i>value</i>"</code>, where <i>value</i> must be an
48
* integer number, greater than 0. A user may specify the number of threads
49
* to start in the test with that paramenter. However, a test may ignore
50
* this value, if it does know the number of threads to start. It
51
* depends on a test: read its README file.
52
* <li><code>-memoryEater="<i>value</i>"</code>, where <i>value</i> must be
53
* either "single", or "multi" string. This argument specifies if a single
54
* thread should be used to eat the whole heap or not. If "multi" string is
55
* assigned to <code>-memoryEater</code>, then a number of threads will be
56
* started to eat the heap. The number is equal to number of available
57
* processors plus 1.
58
* <li><code>-largeClassesPath="<i>value</i>"</code>, where <i>value</i> is a
59
* directory to load large classes from.
60
* <li><code>-fieldsLimitation="<i>value</i>"</code>, where <i>value</i> must
61
* be either "over", or "under" string. This argument specifies what classes
62
* should be loaded from <code>largeClassesPath</code> directory. If
63
* <i>over</i> is set, then the classes that have number of fileds over
64
* JVM limitation should be loaded, otherwise -- classes that have number
65
* of fileds under limitation.
66
* </ul>
67
* @see ArgumentParser
68
*/
69
public class ArgumentHandler extends ArgumentParser {
70
71
// Define all possible arguments
72
private final static String ITERATIONS = "iterations";
73
private final static String AGGREGATION_DEPTH = "aggregationDepth";
74
private final static String GC_TIMEOUT = "gcTimeout";
75
private final static String THREADS = "threads";
76
private final static String MEM_EATER = "memoryEater";
77
private final static String LARGE_CLASSES_PATH = "largeClassesPath";
78
private final static String FIELDS_LIMITATION = "fieldsLimitation";
79
80
// An acceptible value for ITERATIONS
81
private final static String INFINITY = "infinity";
82
83
// Acceptible values for MEM_EATER
84
private final static String ME_SINGLE = "single";
85
private final static String ME_MULTI = "multi";
86
87
// Acceptible values for FIELDS_LIMITATION
88
private final static String FL_OVER = "over";
89
private final static String FL_UNDER = "under";
90
91
/**
92
* Keep a copy of raw command-line arguments and parse them;
93
* but throw an exception on parsing error.
94
*
95
* @param args Array of the raw command-line arguments.
96
*
97
* @throws BadOption If unknown option or illegal option value found
98
*
99
* @see ArgumentParser
100
*/
101
public ArgumentHandler(String args[]) {
102
super(args);
103
}
104
105
/**
106
* Returns number of iterations.
107
* <p>
108
* If <code>-iterations="<i>infinity</i>"</code>, the method returns -1.
109
* If the argument is not set, the method returns 1. Otherwise, the
110
* specified number is returned.
111
*
112
* @return number of iterations.
113
*
114
*/
115
public int getIterations() {
116
String value = options.getProperty(ITERATIONS, "1");
117
118
if (INFINITY.equals(value))
119
return -1;
120
121
try {
122
return Integer.parseInt(value);
123
} catch (NumberFormatException e) {
124
throw new TestBug("Not an integer value of \"" + ITERATIONS
125
+ "\" argument: " + value);
126
}
127
}
128
129
130
/**
131
* Returns the depth of object aggregation.
132
* <p>
133
* If the argument is not set, the method returns 0. Otherwise, the
134
* specified number is returned.
135
*
136
* @return number of aggregation depth.
137
*
138
*/
139
public int getAggregationDepth() {
140
String value = options.getProperty(AGGREGATION_DEPTH, "0");
141
142
try {
143
return Integer.parseInt(value);
144
} catch (NumberFormatException e) {
145
throw new TestBug("Not an integer value of \"" + AGGREGATION_DEPTH
146
+ "\" argument: " + value);
147
}
148
}
149
150
151
/**
152
* Returns number of minutes to run the test.
153
* <p>
154
* @return number of minutes to run the test.
155
*
156
*/
157
public int getGCTimeout() {
158
String value = options.getProperty(GC_TIMEOUT);
159
160
try {
161
return Integer.parseInt(value);
162
} catch (NumberFormatException e) {
163
throw new TestBug("\"" + GC_TIMEOUT + "\" argument is not defined "
164
+ "or is not integer: " + value);
165
}
166
}
167
168
/**
169
* Returns a directory to load large classes from.
170
* <p>
171
* @return a directory to load large classes from.
172
*
173
*/
174
public String getLargeClassesPath() {
175
return options.getProperty(LARGE_CLASSES_PATH);
176
}
177
178
/**
179
* Returns number of threads to start in a test. If <code>threads</code>
180
* is not set, the method returns specified number of threads.
181
* <p>
182
* @param defaultValue default value, if <code>threads</code> is not set.
183
* @return number of threads to start in a test.
184
*
185
*/
186
public int getThreads(int defaultValue) {
187
String value = options.getProperty(THREADS);
188
189
if (value == null)
190
return defaultValue;
191
192
try {
193
return Integer.parseInt(value);
194
} catch (NumberFormatException e) {
195
throw new TestBug("Not an integer value of \"" + THREADS
196
+ "\" argument: " + value);
197
}
198
}
199
200
/**
201
* Returns true if single thread should be used to eat the whole heap,
202
* false otherwise.
203
*
204
* @return true if single thread should be used to eat the whole heap,
205
* false otherwise.
206
*
207
*/
208
public boolean isSingleMemoryEater() {
209
String value = options.getProperty(MEM_EATER);
210
211
if (value == null)
212
return true;
213
else if (value.equals(ME_SINGLE))
214
return true;
215
else if (value.equals(ME_MULTI))
216
return false;
217
else
218
throw new TestBug("Value for \"" + MEM_EATER + "\" must be either "
219
+ ME_SINGLE + ", or " + ME_MULTI);
220
}
221
222
/**
223
* Returns true if classes with number of fileds over limitation should be
224
* loaded, false otherwise.
225
*
226
* @return true if classes with number of fileds over limitation should be
227
* loaded, false otherwise.
228
*
229
*/
230
public boolean isOverFieldsLimitation() {
231
String value = options.getProperty(FIELDS_LIMITATION);
232
233
if (value == null)
234
return false;
235
else if (value.equals(FL_OVER))
236
return true;
237
else if (value.equals(FL_UNDER))
238
return false;
239
else
240
throw new TestBug("Value for \"" + FIELDS_LIMITATION + "\" must be "
241
+ "either " + FL_OVER + ", or " + FL_UNDER);
242
}
243
244
/**
245
* Checks if an option is allowed and has proper value.
246
* This method is invoked by <code>parseArguments()</code>
247
*
248
* @param option option name
249
* @param value string representation of value
250
* (could be an empty string too)
251
* null if this option has no value
252
* @return <i>true</i> if option is allowed and has proper value,
253
* <i>false</i> if option is not admissible
254
*
255
* @throws <i>BadOption</i> if option has an illegal value
256
*
257
* @see #parseArguments()
258
*/
259
protected boolean checkOption(String option, String value) {
260
261
// Define iterations
262
if (option.equals(ITERATIONS)) {
263
if (INFINITY.equals(value))
264
return true;
265
266
try {
267
int number = Integer.parseInt(value);
268
269
if (number < 1)
270
throw new BadOption(option + ": value must be greater than "
271
+ "zero.");
272
} catch (NumberFormatException e) {
273
throw new BadOption("Value for option \"" + option + "\" must "
274
+ "be integer or \"" + INFINITY + "\": "
275
+ value);
276
}
277
return true;
278
}
279
280
// Define timeout
281
if (option.equals(GC_TIMEOUT)) {
282
try {
283
int number = Integer.parseInt(value);
284
285
if (number < 0)
286
throw new BadOption(option + ": value must be a positive "
287
+ "integer");
288
} catch (NumberFormatException e) {
289
throw new BadOption("Value for option \"" + option + "\" must "
290
+ "be integer: " + value);
291
}
292
return true;
293
}
294
295
// Define threads
296
if (option.equals(THREADS)) {
297
try {
298
int number = Integer.parseInt(value);
299
300
if (number < 0)
301
throw new BadOption(option + ": value must be a positive "
302
+ "integer");
303
} catch (NumberFormatException e) {
304
throw new BadOption("Value for option \"" + option + "\" must "
305
+ "be integer: " + value);
306
}
307
return true;
308
}
309
310
// Define path to large classes
311
if (option.equals(LARGE_CLASSES_PATH))
312
return true;
313
314
// Define memory eater
315
if (option.equals(MEM_EATER)) {
316
if ( (ME_SINGLE.equals(value)) || (ME_MULTI.equals(value)) )
317
return true;
318
else
319
throw new BadOption("Value for option \"" + option + "\" must "
320
+ "be either " + ME_SINGLE + ", or "
321
+ ME_MULTI + ": " + value);
322
}
323
324
// Define fields limitation
325
if (option.equals(FIELDS_LIMITATION)) {
326
if ( (FL_OVER.equals(value)) || (FL_UNDER.equals(value)) )
327
return true;
328
else
329
throw new BadOption("Value for option \"" + option + "\" must "
330
+ "be either " + FL_OVER + ", or "
331
+ FL_UNDER + ": " + value);
332
}
333
334
// Define aggregationDepth
335
if (option.equals(AGGREGATION_DEPTH)) {
336
try {
337
int number = Integer.parseInt(value);
338
339
if (number < 0)
340
throw new BadOption(option + ": value must be a positive "
341
+ "integer");
342
} catch (NumberFormatException e) {
343
throw new BadOption("Value for option \"" + option + "\" must "
344
+ "be integer: " + value);
345
}
346
return true;
347
}
348
349
return super.checkOption(option, value);
350
}
351
352
/**
353
* Checks if the values of all options are consistent.
354
* This method is invoked by <code>parseArguments()</code>
355
*
356
* @throws <i>BadOption</i> if options have inconsistent values
357
*
358
* @see ArgumentParser#parseArguments()
359
*/
360
protected void checkOptions() {
361
super.checkOptions();
362
}
363
} // ArgumentHandler
364
365