Subversion Repository Public Repository

litesoft

Diff Revisions 182 vs 287 for /trunk/Java/ScarPlus/src/com/esotericsoftware/scar/Utils.java

Diff revisions: vs.
  @@ -1,10 +1,13 @@
1 1 package com.esotericsoftware.scar;
2 2
3 3 import java.io.*;
4 + import java.net.*;
4 5 import java.nio.channels.*;
5 6 import java.util.*;
6 7 import java.util.regex.*;
7 8
9 + import javax.tools.*;
10 +
8 11 import static com.esotericsoftware.minlog.Log.*;
9 12
10 13 public class Utils
  @@ -14,60 +17,93 @@
14 17 * "scar.home" System property can be defined.
15 18 */
16 19 static public final String SCAR_HOME;
17 - static {
18 - if (System.getProperty("scar.home") != null)
19 - SCAR_HOME = System.getProperty("scar.home");
20 +
21 + static
22 + {
23 + if ( System.getProperty( "scar.home" ) != null )
24 + {
25 + SCAR_HOME = System.getProperty( "scar.home" );
26 + }
20 27 else
21 - SCAR_HOME = System.getenv("SCAR_HOME");
28 + {
29 + SCAR_HOME = System.getenv( "SCAR_HOME" );
30 + }
22 31 }
23 32
24 33 /**
25 34 * The Java installation directory.
26 35 */
27 - static public final String JAVA_HOME = System.getProperty("java.home");
36 + static public final String JAVA_HOME = System.getProperty( "java.home" );
28 37
29 38 /**
30 39 * True if running on a Mac OS.
31 40 */
32 - static public final boolean isMac = System.getProperty("os.name").toLowerCase().contains("mac os x");
41 + static public final boolean isMac = System.getProperty( "os.name" ).toLowerCase().contains( "mac os x" );
33 42
34 43 /**
35 44 * True if running on a Windows OS.
36 45 */
37 - static public final boolean isWindows = System.getProperty("os.name").toLowerCase().contains("windows");
46 + static public final boolean isWindows = System.getProperty( "os.name" ).toLowerCase().contains( "windows" );
38 47
39 48 /**
40 49 * Returns the full path for the specified file name in the current working directory, the {@link #SCAR_HOME}, and the bin
41 50 * directory of {@link #JAVA_HOME}.
42 51 */
43 - static public String resolvePath (String fileName) {
44 - if (fileName == null) return null;
52 + static public String resolvePath( String fileName )
53 + {
54 + if ( fileName == null )
55 + {
56 + return null;
57 + }
45 58
46 59 String foundFile = lowLevelResolve( fileName );
47 - if (TRACE) trace("scar", "Path \"" + fileName + "\" resolved to: " + foundFile);
60 + if ( TRACE )
61 + {
62 + trace( "scar", "Path \"" + fileName + "\" resolved to: " + foundFile );
63 + }
48 64 return foundFile;
49 65 }
50 66
51 - private static String lowLevelResolve( String fileName ){
67 + private static String lowLevelResolve( String fileName )
68 + {
52 69 String foundFile;
53 - if (fileExists(foundFile = canonical(fileName))) return foundFile;
54 - if (fileExists(foundFile = new File(SCAR_HOME, fileName).getPath())) return foundFile;
55 - if (fileExists(foundFile = new File(JAVA_HOME, "bin/" + fileName).getPath())) return foundFile;
56 - return fileName;
70 + if ( fileExists( foundFile = canonical( fileName ) ) )
71 + {
72 + return foundFile;
73 + }
74 + if ( fileExists( foundFile = new File( SCAR_HOME, fileName ).getPath() ) )
75 + {
76 + return foundFile;
77 + }
78 + if ( fileExists( foundFile = new File( JAVA_HOME, "bin/" + fileName ).getPath() ) )
79 + {
80 + return foundFile;
81 + }
82 + return fileName;
57 83 }
58 84
59 85 /**
60 86 * Returns the canonical path for the specified path. Eg, if "." is passed, this will resolve the actual path and return it.
61 87 */
62 - static public String canonical (String path) {
63 - if (path == null) throw new IllegalArgumentException("path cannot be null.");
88 + static public String canonical( String path )
89 + {
90 + if ( path == null )
91 + {
92 + throw new IllegalArgumentException( "path cannot be null." );
93 + }
64 94
65 - File file = new File(path);
66 - try {
95 + File file = new File( path );
96 + try
97 + {
67 98 return file.getCanonicalPath();
68 - } catch (IOException ex) {
99 + }
100 + catch ( IOException ex )
101 + {
69 102 file = file.getAbsoluteFile();
70 - if (file.getName().equals(".")) file = file.getParentFile();
103 + if ( file.getName().equals( "." ) )
104 + {
105 + file = file.getParentFile();
106 + }
71 107 return file.getPath();
72 108 }
73 109 }
  @@ -75,66 +111,107 @@
75 111 /**
76 112 * Deletes a file or directory and all files and subdirecties under it.
77 113 */
78 - static public boolean delete (String fileName) {
79 - if (fileName == null) throw new IllegalArgumentException("fileName cannot be null.");
114 + static public boolean delete( String fileName )
115 + {
116 + if ( fileName == null )
117 + {
118 + throw new IllegalArgumentException( "fileName cannot be null." );
119 + }
80 120
81 - File file = new File(fileName);
121 + File file = new File( fileName );
82 122 return !file.exists() || delete( file );
83 123 }
84 124
85 - private static boolean delete(File file) {
86 - if (file.isDirectory()) {
125 + private static boolean delete( File file )
126 + {
127 + if ( file.isDirectory() )
128 + {
87 129 File[] files = file.listFiles();
88 130 for ( File aFile : files )
89 131 {
90 132 delete( aFile );
91 133 }
92 134 }
93 - if (TRACE) trace("scar", "Deleting file: " + file);
135 + if ( TRACE )
136 + {
137 + trace( "scar", "Deleting file: " + file );
138 + }
94 139 return file.delete();
95 140 }
96 141
97 142 /**
98 143 * Creates the directories in the specified path.
99 144 */
100 - static public String mkdir (String path) {
101 - if (path == null) throw new IllegalArgumentException("path cannot be null.");
145 + static public String mkdir( String path )
146 + {
147 + if ( path == null )
148 + {
149 + throw new IllegalArgumentException( "path cannot be null." );
150 + }
102 151
103 - if (new File(path).mkdirs() && TRACE) trace("scar", "Created directory: " + path);
152 + if ( new File( path ).mkdirs() && TRACE )
153 + {
154 + trace( "scar", "Created directory: " + path );
155 + }
104 156 return path;
105 157 }
106 158
107 159 /**
108 160 * Returns true if the file exists.
109 161 */
110 - static public boolean fileExists (String path) {
111 - if (path == null) throw new IllegalArgumentException("path cannot be null.");
162 + static public boolean fileExists( String path )
163 + {
164 + if ( path == null )
165 + {
166 + throw new IllegalArgumentException( "path cannot be null." );
167 + }
112 168
113 - return new File(path).exists();
169 + return new File( path ).exists();
114 170 }
115 171
116 172 /**
117 173 * Reads to the end of the input stream and writes the bytes to the output stream.
118 174 */
119 - static public void copyStream (InputStream input, OutputStream output) throws IOException {
120 - if (input == null) throw new IllegalArgumentException("input cannot be null.");
121 - if (output == null) throw new IllegalArgumentException("output cannot be null.");
175 + static public void copyStream( InputStream input, OutputStream output )
176 + throws IOException
177 + {
178 + if ( input == null )
179 + {
180 + throw new IllegalArgumentException( "input cannot be null." );
181 + }
182 + if ( output == null )
183 + {
184 + throw new IllegalArgumentException( "output cannot be null." );
185 + }
122 186
123 - try {
187 + try
188 + {
124 189 byte[] buffer = new byte[4096];
125 - while (true) {
126 - int length = input.read(buffer);
127 - if (length == -1) break;
128 - output.write(buffer, 0, length);
190 + while ( true )
191 + {
192 + int length = input.read( buffer );
193 + if ( length == -1 )
194 + {
195 + break;
196 + }
197 + output.write( buffer, 0, length );
129 198 }
130 - } finally {
131 - try {
199 + }
200 + finally
201 + {
202 + try
203 + {
132 204 output.close();
133 - } catch (Exception ignored) {
134 205 }
135 - try {
206 + catch ( Exception ignored )
207 + {
208 + }
209 + try
210 + {
136 211 input.close();
137 - } catch (Exception ignored) {
212 + }
213 + catch ( Exception ignored )
214 + {
138 215 }
139 216 }
140 217 }
  @@ -142,26 +219,52 @@
142 219 /**
143 220 * Copies a file, overwriting any existing file at the destination.
144 221 */
145 - static public String copyFile (String in, String out) throws IOException {
146 - if (in == null) throw new IllegalArgumentException("in cannot be null.");
147 - if (out == null) throw new IllegalArgumentException("out cannot be null.");
222 + static public String copyFile( String in, String out )
223 + throws IOException
224 + {
225 + if ( in == null )
226 + {
227 + throw new IllegalArgumentException( "in cannot be null." );
228 + }
229 + if ( out == null )
230 + {
231 + throw new IllegalArgumentException( "out cannot be null." );
232 + }
148 233
149 - if (TRACE) trace("scar", "Copying file: " + in + " -> " + out);
234 + if ( TRACE )
235 + {
236 + trace( "scar", "Copying file: " + in + " -> " + out );
237 + }
150 238
151 239 FileChannel sourceChannel = null;
152 240 FileChannel destinationChannel = null;
153 - try {
154 - sourceChannel = new FileInputStream(in).getChannel();
155 - destinationChannel = new FileOutputStream(out).getChannel();
156 - sourceChannel.transferTo(0, sourceChannel.size(), destinationChannel);
157 - } finally {
158 - try {
159 - if (sourceChannel != null) sourceChannel.close();
160 - } catch (Exception ignored) {
161 - }
162 - try {
163 - if (destinationChannel != null) destinationChannel.close();
164 - } catch (Exception ignored) {
241 + try
242 + {
243 + sourceChannel = new FileInputStream( in ).getChannel();
244 + destinationChannel = new FileOutputStream( out ).getChannel();
245 + sourceChannel.transferTo( 0, sourceChannel.size(), destinationChannel );
246 + }
247 + finally
248 + {
249 + try
250 + {
251 + if ( sourceChannel != null )
252 + {
253 + sourceChannel.close();
254 + }
255 + }
256 + catch ( Exception ignored )
257 + {
258 + }
259 + try
260 + {
261 + if ( destinationChannel != null )
262 + {
263 + destinationChannel.close();
264 + }
265 + }
266 + catch ( Exception ignored )
267 + {
165 268 }
166 269 }
167 270 return out;
  @@ -170,32 +273,52 @@
170 273 /**
171 274 * Moves a file, overwriting any existing file at the destination.
172 275 */
173 - static public String moveFile (String in, String out) throws IOException {
174 - if (in == null) throw new IllegalArgumentException("in cannot be null.");
175 - if (out == null) throw new IllegalArgumentException("out cannot be null.");
276 + static public String moveFile( String in, String out )
277 + throws IOException
278 + {
279 + if ( in == null )
280 + {
281 + throw new IllegalArgumentException( "in cannot be null." );
282 + }
283 + if ( out == null )
284 + {
285 + throw new IllegalArgumentException( "out cannot be null." );
286 + }
176 287
177 - copyFile(in, out);
178 - delete(in);
288 + copyFile( in, out );
289 + delete( in );
179 290 return out;
180 291 }
181 292
182 293 /**
183 294 * Returns the textual contents of the specified file.
184 295 */
185 - static public String fileContents (String path) throws IOException {
186 - StringBuilder stringBuffer = new StringBuilder(4096);
187 - FileReader reader = new FileReader(path);
188 - try {
296 + static public String fileContents( String path )
297 + throws IOException
298 + {
299 + StringBuilder stringBuffer = new StringBuilder( 4096 );
300 + FileReader reader = new FileReader( path );
301 + try
302 + {
189 303 char[] buffer = new char[2048];
190 - while (true) {
191 - int length = reader.read(buffer);
192 - if (length == -1) break;
193 - stringBuffer.append(buffer, 0, length);
304 + while ( true )
305 + {
306 + int length = reader.read( buffer );
307 + if ( length == -1 )
308 + {
309 + break;
310 + }
311 + stringBuffer.append( buffer, 0, length );
194 312 }
195 - } finally {
196 - try {
313 + }
314 + finally
315 + {
316 + try
317 + {
197 318 reader.close();
198 - } catch (Exception ignored) {
319 + }
320 + catch ( Exception ignored )
321 + {
199 322 }
200 323 }
201 324 return stringBuffer.toString();
  @@ -204,167 +327,350 @@
204 327 /**
205 328 * Returns only the filename portion of the specified path.
206 329 */
207 - static public String fileName (String path) {
208 - return new File(canonical(path)).getName();
330 + static public String fileName( String path )
331 + {
332 + return new File( canonical( path ) ).getName();
209 333 }
210 334
211 335 /**
212 336 * Returns the parent directory of the specified path.
213 337 */
214 - static public String parent (String path) {
215 - return new File(canonical(path)).getParent();
338 + static public String parent( String path )
339 + {
340 + return new File( canonical( path ) ).getParent();
216 341 }
217 342
218 343 /**
219 344 * Returns only the extension portion of the specified path, or an empty string if there is no extension.
220 345 */
221 - static public String fileExtension (String file) {
222 - if (file == null) throw new IllegalArgumentException("fileName cannot be null.");
346 + static public String fileExtension( String file )
347 + {
348 + if ( file == null )
349 + {
350 + throw new IllegalArgumentException( "fileName cannot be null." );
351 + }
223 352
224 353 int commaIndex = file.indexOf( '.' );
225 - if (commaIndex == -1) return "";
226 - return file.substring(commaIndex + 1);
354 + if ( commaIndex == -1 )
355 + {
356 + return "";
357 + }
358 + return file.substring( commaIndex + 1 );
227 359 }
228 360
229 361 /**
230 362 * Returns only the filename portion of the specified path, without the extension, if any.
231 363 */
232 - static public String fileWithoutExtension (String file) {
233 - if (file == null) throw new IllegalArgumentException("fileName cannot be null.");
364 + static public String fileWithoutExtension( String file )
365 + {
366 + if ( file == null )
367 + {
368 + throw new IllegalArgumentException( "fileName cannot be null." );
369 + }
234 370
235 - int commaIndex = file.indexOf('.');
236 - if (commaIndex == -1) commaIndex = file.length();
237 - int slashIndex = file.replace('\\', '/').lastIndexOf('/');
238 - if (slashIndex == -1)
371 + int commaIndex = file.indexOf( '.' );
372 + if ( commaIndex == -1 )
373 + {
374 + commaIndex = file.length();
375 + }
376 + int slashIndex = file.replace( '\\', '/' ).lastIndexOf( '/' );
377 + if ( slashIndex == -1 )
378 + {
239 379 slashIndex = 0;
380 + }
240 381 else
382 + {
241 383 slashIndex++;
242 - return file.substring(slashIndex, commaIndex);
384 + }
385 + return file.substring( slashIndex, commaIndex );
243 386 }
244 387
245 388 /**
246 389 * Returns a substring of the specified text.
390 + *
247 391 * @param end The end index of the substring. If negative, the index used will be "text.length() + end".
248 392 */
249 - static public String substring (String text, int start, int end) {
250 - if (text == null) throw new IllegalArgumentException("text cannot be null.");
393 + static public String substring( String text, int start, int end )
394 + {
395 + if ( text == null )
396 + {
397 + throw new IllegalArgumentException( "text cannot be null." );
398 + }
251 399
252 - if (end >= 0) return text.substring(start, end);
253 - return text.substring(start, text.length() + end);
400 + if ( end >= 0 )
401 + {
402 + return text.substring( start, end );
403 + }
404 + return text.substring( start, text.length() + end );
254 405 }
255 406
256 407 /**
257 408 * Splits the specified command at spaces that are not surrounded by quotes and passes the result to {@link #shell(String...)}.
258 409 */
259 - static public void shell (String command) throws IOException {
410 + static public void shell( String command )
411 + throws IOException
412 + {
260 413 List<String> matchList = new ArrayList<String>();
261 - Pattern regex = Pattern.compile("[^\\s\"']+|\"([^\"]*)\"|'([^']*)'");
262 - Matcher regexMatcher = regex.matcher(command);
263 - while (regexMatcher.find()) {
264 - if (regexMatcher.group(1) != null)
265 - matchList.add(regexMatcher.group(1));
266 - else if (regexMatcher.group(2) != null)
267 - matchList.add(regexMatcher.group(2));
414 + Pattern regex = Pattern.compile( "[^\\s\"']+|\"([^\"]*)\"|'([^']*)'" );
415 + Matcher regexMatcher = regex.matcher( command );
416 + while ( regexMatcher.find() )
417 + {
418 + if ( regexMatcher.group( 1 ) != null )
419 + {
420 + matchList.add( regexMatcher.group( 1 ) );
421 + }
422 + else if ( regexMatcher.group( 2 ) != null )
423 + {
424 + matchList.add( regexMatcher.group( 2 ) );
425 + }
268 426 else
269 - matchList.add(regexMatcher.group());
427 + {
428 + matchList.add( regexMatcher.group() );
429 + }
270 430 }
271 - shell(matchList.toArray(new String[matchList.size()]));
431 + shell( matchList.toArray( new String[matchList.size()] ) );
272 432 }
273 433
274 434 /**
275 435 * Executes the specified shell command. {@link #resolvePath(String)} is used to locate the file to execute. If not found, on
276 436 * Windows the same filename with an "exe" extension is also tried.
277 437 */
278 - static public void shell (String... command) throws IOException {
279 - if (command == null) throw new IllegalArgumentException("command cannot be null.");
280 - if (command.length == 0) throw new IllegalArgumentException("command cannot be empty.");
438 + static public void shell( String... command )
439 + throws IOException
440 + {
441 + if ( command == null )
442 + {
443 + throw new IllegalArgumentException( "command cannot be null." );
444 + }
445 + if ( command.length == 0 )
446 + {
447 + throw new IllegalArgumentException( "command cannot be empty." );
448 + }
281 449
282 450 String originalCommand = command[0];
283 - command[0] = resolvePath(command[0]);
284 - if (!fileExists(command[0]) && isWindows) {
285 - command[0] = resolvePath(command[0] + ".exe");
286 - if (!fileExists(command[0])) command[0] = originalCommand;
451 + command[0] = resolvePath( command[0] );
452 + if ( !fileExists( command[0] ) && isWindows )
453 + {
454 + command[0] = resolvePath( command[0] + ".exe" );
455 + if ( !fileExists( command[0] ) )
456 + {
457 + command[0] = originalCommand;
458 + }
287 459 }
288 460
289 - if (TRACE) {
290 - StringBuilder buffer = new StringBuilder(256);
291 - for (String text : command) {
292 - buffer.append(text);
293 - buffer.append(' ');
461 + if ( TRACE )
462 + {
463 + StringBuilder buffer = new StringBuilder( 256 );
464 + for ( String text : command )
465 + {
466 + buffer.append( text );
467 + buffer.append( ' ' );
294 468 }
295 - trace("scar", "Executing command: " + buffer);
469 + trace( "scar", "Executing command: " + buffer );
296 470 }
297 471
298 - Process process = new ProcessBuilder(command).start();
472 + Process process = new ProcessBuilder( command ).start();
299 473 // try {
300 474 // process.waitFor();
301 475 // } catch (InterruptedException ignored) {
302 476 // }
303 - BufferedReader reader = new BufferedReader(new InputStreamReader(process.getInputStream()));
304 - while (true) {
477 + BufferedReader reader = new BufferedReader( new InputStreamReader( process.getInputStream() ) );
478 + while ( true )
479 + {
305 480 String line = reader.readLine();
306 - if (line == null) break;
307 - System.out.println(line);
481 + if ( line == null )
482 + {
483 + break;
484 + }
485 + System.out.println( line );
308 486 }
309 487 reader.close();
310 - reader = new BufferedReader(new InputStreamReader(process.getErrorStream()));
311 - while (true) {
488 + reader = new BufferedReader( new InputStreamReader( process.getErrorStream() ) );
489 + while ( true )
490 + {
312 491 String line = reader.readLine();
313 - if (line == null) break;
314 - System.out.println(line);
492 + if ( line == null )
493 + {
494 + break;
495 + }
496 + System.out.println( line );
315 497 }
316 - if (process.exitValue() != 0) {
317 - StringBuilder buffer = new StringBuilder(256);
318 - for (String text : command) {
319 - buffer.append(text);
320 - buffer.append(' ');
498 + if ( process.exitValue() != 0 )
499 + {
500 + StringBuilder buffer = new StringBuilder( 256 );
501 + for ( String text : command )
502 + {
503 + buffer.append( text );
504 + buffer.append( ' ' );
321 505 }
322 - throw new RuntimeException("Error executing command: " + buffer);
506 + throw new RuntimeException( "Error executing command: " + buffer );
323 507 }
324 508 }
325 509
326 510 /**
327 511 * Creates a new keystore for signing JARs. If the keystore file already exists, no action will be taken.
512 + *
328 513 * @return The path to the keystore file.
329 514 */
330 - static public String keystore (String keystoreFile, String alias, String password, String company, String title)
331 - throws IOException {
332 - if (keystoreFile == null) throw new IllegalArgumentException("keystoreFile cannot be null.");
333 - if (fileExists(keystoreFile)) return keystoreFile;
334 - if (alias == null) throw new IllegalArgumentException("alias cannot be null.");
335 - if (password == null) throw new IllegalArgumentException("password cannot be null.");
336 - if (password.length() < 6) throw new IllegalArgumentException("password must be 6 or more characters.");
337 - if (company == null) throw new IllegalArgumentException("company cannot be null.");
338 - if (title == null) throw new IllegalArgumentException("title cannot be null.");
515 + static public String keystore( String keystoreFile, String alias, String password, String company, String title )
516 + throws IOException
517 + {
518 + if ( keystoreFile == null )
519 + {
520 + throw new IllegalArgumentException( "keystoreFile cannot be null." );
521 + }
522 + if ( fileExists( keystoreFile ) )
523 + {
524 + return keystoreFile;
525 + }
526 + if ( alias == null )
527 + {
528 + throw new IllegalArgumentException( "alias cannot be null." );
529 + }
530 + if ( password == null )
531 + {
532 + throw new IllegalArgumentException( "password cannot be null." );
533 + }
534 + if ( password.length() < 6 )
535 + {
536 + throw new IllegalArgumentException( "password must be 6 or more characters." );
537 + }
538 + if ( company == null )
539 + {
540 + throw new IllegalArgumentException( "company cannot be null." );
541 + }
542 + if ( title == null )
543 + {
544 + throw new IllegalArgumentException( "title cannot be null." );
545 + }
339 546
340 - if (DEBUG)
341 - debug("scar", "Creating keystore (" + alias + ":" + password + ", " + company + ", " + title + "): " + keystoreFile);
547 + if ( DEBUG )
548 + {
549 + debug( "scar", "Creating keystore (" + alias + ":" + password + ", " + company + ", " + title + "): " + keystoreFile );
550 + }
342 551
343 - File file = new File(keystoreFile);
552 + File file = new File( keystoreFile );
344 553 file.delete();
345 - Process process = Runtime.getRuntime().exec(
346 - new String[] {resolvePath("keytool"), "-genkey", "-keystore", keystoreFile, "-alias", alias});
347 - OutputStreamWriter writer = new OutputStreamWriter(process.getOutputStream());
348 - writer.write(password + "\n"); // Enter keystore password:
349 - writer.write(password + "\n"); // Re-enter new password:
350 - writer.write(company + "\n"); // What is your first and last name?
351 - writer.write(title + "\n"); // What is the name of your organizational unit?
352 - writer.write(title + "\n"); // What is the name of your organization?
353 - writer.write("\n"); // What is the name of your City or Locality? [Unknown]
354 - writer.write("\n"); // What is the name of your State or Province? [Unknown]
355 - writer.write("\n"); // What is the two-letter country code for this unit? [Unknown]
356 - writer.write("yes\n"); // Correct?
357 - writer.write("\n"); // Return if same alias key password as keystore.
554 + Process process = Runtime.getRuntime().exec( new String[]{resolvePath( "keytool" ), "-genkey", "-keystore", keystoreFile, "-alias", alias} );
555 + OutputStreamWriter writer = new OutputStreamWriter( process.getOutputStream() );
556 + writer.write( password + "\n" ); // Enter keystore password:
557 + writer.write( password + "\n" ); // Re-enter new password:
558 + writer.write( company + "\n" ); // What is your first and last name?
559 + writer.write( title + "\n" ); // What is the name of your organizational unit?
560 + writer.write( title + "\n" ); // What is the name of your organization?
561 + writer.write( "\n" ); // What is the name of your City or Locality? [Unknown]
562 + writer.write( "\n" ); // What is the name of your State or Province? [Unknown]
563 + writer.write( "\n" ); // What is the two-letter country code for this unit? [Unknown]
564 + writer.write( "yes\n" ); // Correct?
565 + writer.write( "\n" ); // Return if same alias key password as keystore.
358 566 writer.flush();
359 567 process.getOutputStream().close();
360 568 process.getInputStream().close();
361 569 process.getErrorStream().close();
362 - try {
570 + try
571 + {
363 572 process.waitFor();
364 - } catch (InterruptedException ignored) {
365 573 }
366 - if (!file.exists()) throw new RuntimeException("Error creating keystore.");
574 + catch ( InterruptedException ignored )
575 + {
576 + }
577 + if ( !file.exists() )
578 + {
579 + throw new RuntimeException( "Error creating keystore." );
580 + }
367 581 return keystoreFile;
368 582 }
369 583
584 + public static Class compileDynamicCodeToClass( int pOverheadStartLines, final String pCode, final URL... pClasspathURLs )
585 + throws ClassNotFoundException
586 + {
587 + JavaCompiler compiler = ToolProvider.getSystemJavaCompiler();
588 + if ( compiler == null )
589 + {
590 + throw new RuntimeException( "No compiler available. Ensure you are running from a 1.6+ JDK, and not a JRE." );
591 + }
592 +
593 + final ByteArrayOutputStream output = new ByteArrayOutputStream( 32 * 1024 );
594 + final SimpleJavaFileObject javaObject = new SimpleJavaFileObject( URI.create( "Generated.java" ), JavaFileObject.Kind.SOURCE )
595 + {
596 + @Override
597 + public OutputStream openOutputStream()
598 + {
599 + return output;
600 + }
601 +
602 + @Override
603 + public CharSequence getCharContent( boolean ignoreEncodingErrors )
604 + {
605 + return pCode;
606 + }
607 + };
608 + DiagnosticCollector<JavaFileObject> diagnostics = new DiagnosticCollector<JavaFileObject>();
609 + //noinspection unchecked
610 + compiler.getTask( null, new ForwardingJavaFileManager( compiler.getStandardFileManager( null, null, null ) )
611 + {
612 + @Override
613 + public JavaFileObject getJavaFileForOutput( Location location, String className, JavaFileObject.Kind kind, FileObject sibling )
614 + {
615 + return javaObject;
616 + }
617 + }, diagnostics, null, null, Arrays.asList( javaObject ) ).call();
618 +
619 + if ( !diagnostics.getDiagnostics().isEmpty() )
620 + {
621 + StringBuilder buffer = new StringBuilder( 1024 );
622 + for ( Diagnostic diagnostic : diagnostics.getDiagnostics() )
623 + {
624 + if ( buffer.length() > 0 )
625 + {
626 + buffer.append( "\n" );
627 + }
628 + buffer.append( "Line " );
629 + buffer.append( diagnostic.getLineNumber() - pOverheadStartLines );
630 + buffer.append( ": " );
631 + buffer.append( diagnostic.getMessage( null ).replaceAll( "^Generated.java:\\d+:\\d* ", "" ) );
632 + }
633 + throw new RuntimeException( "Compilation errors:\n" + buffer );
634 + }
635 +
636 + // Load class.
637 + return new URLClassLoader( pClasspathURLs, Scar.class.getClassLoader() )
638 + {
639 + @Override
640 + protected synchronized Class<?> loadClass( String name, boolean resolve )
641 + throws ClassNotFoundException
642 + {
643 + // Look in this classloader before the parent.
644 + Class c = findLoadedClass( name );
645 + if ( c == null )
646 + {
647 + try
648 + {
649 + c = findClass( name );
650 + }
651 + catch ( ClassNotFoundException e )
652 + {
653 + return super.loadClass( name, resolve );
654 + }
655 + }
656 + if ( resolve )
657 + {
658 + resolveClass( c );
659 + }
660 + return c;
661 + }
662 +
663 + @Override
664 + protected Class<?> findClass( String name )
665 + throws ClassNotFoundException
666 + {
667 + if ( name.equals( "Generated" ) )
668 + {
669 + byte[] bytes = output.toByteArray();
670 + return defineClass( name, bytes, 0, bytes.length );
671 + }
672 + return super.findClass( name );
673 + }
674 + }.loadClass( "Generated" );
675 + }
370 676 }