1 /* 2 * Copyright (C) 2014 The Android Open Source Project 3 * Copyright (c) 1995, 2006, Oracle and/or its affiliates. All rights reserved. 4 * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. 5 * 6 * This code is free software; you can redistribute it and/or modify it 7 * under the terms of the GNU General Public License version 2 only, as 8 * published by the Free Software Foundation. Oracle designates this 9 * particular file as subject to the "Classpath" exception as provided 10 * by Oracle in the LICENSE file that accompanied this code. 11 * 12 * This code is distributed in the hope that it will be useful, but WITHOUT 13 * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or 14 * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License 15 * version 2 for more details (a copy is included in the LICENSE file that 16 * accompanied this code). 17 * 18 * You should have received a copy of the GNU General Public License version 19 * 2 along with this work; if not, write to the Free Software Foundation, 20 * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA. 21 * 22 * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA 23 * or visit www.oracle.com if you need additional information or have any 24 * questions. 25 */ 26 27 package java.lang; 28 29 import java.io.*; 30 import java.util.StringTokenizer; 31 import sun.reflect.CallerSensitive; 32 import java.lang.ref.FinalizerReference; 33 import java.util.ArrayList; 34 import java.util.List; 35 import dalvik.system.BaseDexClassLoader; 36 import dalvik.system.VMDebug; 37 import dalvik.system.VMStack; 38 import dalvik.system.VMRuntime; 39 import libcore.io.IoUtils; 40 import libcore.io.Libcore; 41 import libcore.util.EmptyArray; 42 import static android.system.OsConstants._SC_NPROCESSORS_CONF; 43 44 /** 45 * Every Java application has a single instance of class 46 * <code>Runtime</code> that allows the application to interface with 47 * the environment in which the application is running. The current 48 * runtime can be obtained from the <code>getRuntime</code> method. 49 * <p> 50 * An application cannot create its own instance of this class. 51 * 52 * @author unascribed 53 * @see java.lang.Runtime#getRuntime() 54 * @since JDK1.0 55 */ 56 57 public class Runtime { 58 private static Runtime currentRuntime = new Runtime(); 59 60 /** 61 * Holds the list of threads to run when the VM terminates 62 */ 63 private List<Thread> shutdownHooks = new ArrayList<Thread>(); 64 65 /** 66 * Reflects whether finalization should be run for all objects 67 * when the VM terminates. 68 */ 69 private static boolean finalizeOnExit; 70 71 /** 72 * Reflects whether we are already shutting down the VM. 73 */ 74 private boolean shuttingDown; 75 76 /** 77 * Reflects whether we are tracing method calls. 78 */ 79 private boolean tracingMethods; 80 81 private static native void nativeExit(int code); 82 83 /** 84 * Returns the runtime object associated with the current Java application. 85 * Most of the methods of class <code>Runtime</code> are instance 86 * methods and must be invoked with respect to the current runtime object. 87 * 88 * @return the <code>Runtime</code> object associated with the current 89 * Java application. 90 */ 91 public static Runtime getRuntime() { 92 return currentRuntime; 93 } 94 95 /** Don't let anyone else instantiate this class */ 96 private Runtime() {} 97 98 /** 99 * Terminates the currently running Java virtual machine by initiating its 100 * shutdown sequence. This method never returns normally. The argument 101 * serves as a status code; by convention, a nonzero status code indicates 102 * abnormal termination. 103 * 104 * <p> The virtual machine's shutdown sequence consists of two phases. In 105 * the first phase all registered {@link #addShutdownHook shutdown hooks}, 106 * if any, are started in some unspecified order and allowed to run 107 * concurrently until they finish. In the second phase all uninvoked 108 * finalizers are run if {@link #runFinalizersOnExit finalization-on-exit} 109 * has been enabled. Once this is done the virtual machine {@link #halt 110 * halts}. 111 * 112 * <p> If this method is invoked after the virtual machine has begun its 113 * shutdown sequence then if shutdown hooks are being run this method will 114 * block indefinitely. If shutdown hooks have already been run and on-exit 115 * finalization has been enabled then this method halts the virtual machine 116 * with the given status code if the status is nonzero; otherwise, it 117 * blocks indefinitely. 118 * 119 * <p> The <tt>{@link System#exit(int) System.exit}</tt> method is the 120 * conventional and convenient means of invoking this method. <p> 121 * 122 * @param status 123 * Termination status. By convention, a nonzero status code 124 * indicates abnormal termination. 125 * 126 * @throws SecurityException 127 * If a security manager is present and its <tt>{@link 128 * SecurityManager#checkExit checkExit}</tt> method does not permit 129 * exiting with the specified status 130 * 131 * @see java.lang.SecurityException 132 * @see java.lang.SecurityManager#checkExit(int) 133 * @see #addShutdownHook 134 * @see #removeShutdownHook 135 * @see #runFinalizersOnExit 136 * @see #halt(int) 137 */ 138 public void exit(int status) { 139 // Make sure we don't try this several times 140 synchronized(this) { 141 if (!shuttingDown) { 142 shuttingDown = true; 143 144 Thread[] hooks; 145 synchronized (shutdownHooks) { 146 // create a copy of the hooks 147 hooks = new Thread[shutdownHooks.size()]; 148 shutdownHooks.toArray(hooks); 149 } 150 151 // Start all shutdown hooks concurrently 152 for (Thread hook : hooks) { 153 hook.start(); 154 } 155 156 // Wait for all shutdown hooks to finish 157 for (Thread hook : hooks) { 158 try { 159 hook.join(); 160 } catch (InterruptedException ex) { 161 // Ignore, since we are at VM shutdown. 162 } 163 } 164 165 // Ensure finalization on exit, if requested 166 if (finalizeOnExit) { 167 runFinalization(); 168 } 169 170 // Get out of here finally... 171 nativeExit(status); 172 } 173 } 174 } 175 176 /** 177 * Registers a new virtual-machine shutdown hook. 178 * 179 * <p> The Java virtual machine <i>shuts down</i> in response to two kinds 180 * of events: 181 * 182 * <ul> 183 * 184 * <p> <li> The program <i>exits</i> normally, when the last non-daemon 185 * thread exits or when the <tt>{@link #exit exit}</tt> (equivalently, 186 * <tt>{@link System#exit(int) System.exit}</tt>) method is invoked, or 187 * 188 * <p> <li> The virtual machine is <i>terminated</i> in response to a 189 * user interrupt, such as typing <tt>^C</tt>, or a system-wide event, 190 * such as user logoff or system shutdown. 191 * 192 * </ul> 193 * 194 * <p> A <i>shutdown hook</i> is simply an initialized but unstarted 195 * thread. When the virtual machine begins its shutdown sequence it will 196 * start all registered shutdown hooks in some unspecified order and let 197 * them run concurrently. When all the hooks have finished it will then 198 * run all uninvoked finalizers if finalization-on-exit has been enabled. 199 * Finally, the virtual machine will halt. Note that daemon threads will 200 * continue to run during the shutdown sequence, as will non-daemon threads 201 * if shutdown was initiated by invoking the <tt>{@link #exit exit}</tt> 202 * method. 203 * 204 * <p> Once the shutdown sequence has begun it can be stopped only by 205 * invoking the <tt>{@link #halt halt}</tt> method, which forcibly 206 * terminates the virtual machine. 207 * 208 * <p> Once the shutdown sequence has begun it is impossible to register a 209 * new shutdown hook or de-register a previously-registered hook. 210 * Attempting either of these operations will cause an 211 * <tt>{@link IllegalStateException}</tt> to be thrown. 212 * 213 * <p> Shutdown hooks run at a delicate time in the life cycle of a virtual 214 * machine and should therefore be coded defensively. They should, in 215 * particular, be written to be thread-safe and to avoid deadlocks insofar 216 * as possible. They should also not rely blindly upon services that may 217 * have registered their own shutdown hooks and therefore may themselves in 218 * the process of shutting down. Attempts to use other thread-based 219 * services such as the AWT event-dispatch thread, for example, may lead to 220 * deadlocks. 221 * 222 * <p> Shutdown hooks should also finish their work quickly. When a 223 * program invokes <tt>{@link #exit exit}</tt> the expectation is 224 * that the virtual machine will promptly shut down and exit. When the 225 * virtual machine is terminated due to user logoff or system shutdown the 226 * underlying operating system may only allow a fixed amount of time in 227 * which to shut down and exit. It is therefore inadvisable to attempt any 228 * user interaction or to perform a long-running computation in a shutdown 229 * hook. 230 * 231 * <p> Uncaught exceptions are handled in shutdown hooks just as in any 232 * other thread, by invoking the <tt>{@link ThreadGroup#uncaughtException 233 * uncaughtException}</tt> method of the thread's <tt>{@link 234 * ThreadGroup}</tt> object. The default implementation of this method 235 * prints the exception's stack trace to <tt>{@link System#err}</tt> and 236 * terminates the thread; it does not cause the virtual machine to exit or 237 * halt. 238 * 239 * <p> In rare circumstances the virtual machine may <i>abort</i>, that is, 240 * stop running without shutting down cleanly. This occurs when the 241 * virtual machine is terminated externally, for example with the 242 * <tt>SIGKILL</tt> signal on Unix or the <tt>TerminateProcess</tt> call on 243 * Microsoft Windows. The virtual machine may also abort if a native 244 * method goes awry by, for example, corrupting internal data structures or 245 * attempting to access nonexistent memory. If the virtual machine aborts 246 * then no guarantee can be made about whether or not any shutdown hooks 247 * will be run. <p> 248 * 249 * @param hook 250 * An initialized but unstarted <tt>{@link Thread}</tt> object 251 * 252 * @throws IllegalArgumentException 253 * If the specified hook has already been registered, 254 * or if it can be determined that the hook is already running or 255 * has already been run 256 * 257 * @throws IllegalStateException 258 * If the virtual machine is already in the process 259 * of shutting down 260 * 261 * @throws SecurityException 262 * If a security manager is present and it denies 263 * <tt>{@link RuntimePermission}("shutdownHooks")</tt> 264 * 265 * @see #removeShutdownHook 266 * @see #halt(int) 267 * @see #exit(int) 268 * @since 1.3 269 */ 270 public void addShutdownHook(Thread hook) { 271 // Sanity checks 272 if (hook == null) { 273 throw new NullPointerException("hook == null"); 274 } 275 276 if (shuttingDown) { 277 throw new IllegalStateException("VM already shutting down"); 278 } 279 280 if (hook.started) { 281 throw new IllegalArgumentException("Hook has already been started"); 282 } 283 284 synchronized (shutdownHooks) { 285 if (shutdownHooks.contains(hook)) { 286 throw new IllegalArgumentException("Hook already registered."); 287 } 288 289 shutdownHooks.add(hook); 290 } 291 } 292 293 /** 294 * De-registers a previously-registered virtual-machine shutdown hook. <p> 295 * 296 * @param hook the hook to remove 297 * @return <tt>true</tt> if the specified hook had previously been 298 * registered and was successfully de-registered, <tt>false</tt> 299 * otherwise. 300 * 301 * @throws IllegalStateException 302 * If the virtual machine is already in the process of shutting 303 * down 304 * 305 * @throws SecurityException 306 * If a security manager is present and it denies 307 * <tt>{@link RuntimePermission}("shutdownHooks")</tt> 308 * 309 * @see #addShutdownHook 310 * @see #exit(int) 311 * @since 1.3 312 */ 313 public boolean removeShutdownHook(Thread hook) { 314 // Sanity checks 315 if (hook == null) { 316 throw new NullPointerException("hook == null"); 317 } 318 319 if (shuttingDown) { 320 throw new IllegalStateException("VM already shutting down"); 321 } 322 323 synchronized (shutdownHooks) { 324 return shutdownHooks.remove(hook); 325 } 326 } 327 328 /** 329 * Forcibly terminates the currently running Java virtual machine. This 330 * method never returns normally. 331 * 332 * <p> This method should be used with extreme caution. Unlike the 333 * <tt>{@link #exit exit}</tt> method, this method does not cause shutdown 334 * hooks to be started and does not run uninvoked finalizers if 335 * finalization-on-exit has been enabled. If the shutdown sequence has 336 * already been initiated then this method does not wait for any running 337 * shutdown hooks or finalizers to finish their work. <p> 338 * 339 * @param status 340 * Termination status. By convention, a nonzero status code 341 * indicates abnormal termination. If the <tt>{@link Runtime#exit 342 * exit}</tt> (equivalently, <tt>{@link System#exit(int) 343 * System.exit}</tt>) method has already been invoked then this 344 * status code will override the status code passed to that method. 345 * 346 * @throws SecurityException 347 * If a security manager is present and its <tt>{@link 348 * SecurityManager#checkExit checkExit}</tt> method does not permit 349 * an exit with the specified status 350 * 351 * @see #exit 352 * @see #addShutdownHook 353 * @see #removeShutdownHook 354 * @since 1.3 355 */ 356 public void halt(int status) { 357 nativeExit(status); 358 } 359 360 /** 361 * Enable or disable finalization on exit; doing so specifies that the 362 * finalizers of all objects that have finalizers that have not yet been 363 * automatically invoked are to be run before the Java runtime exits. 364 * By default, finalization on exit is disabled. 365 * 366 * <p>If there is a security manager, 367 * its <code>checkExit</code> method is first called 368 * with 0 as its argument to ensure the exit is allowed. 369 * This could result in a SecurityException. 370 * 371 * @param value true to enable finalization on exit, false to disable 372 * @deprecated This method is inherently unsafe. It may result in 373 * finalizers being called on live objects while other threads are 374 * concurrently manipulating those objects, resulting in erratic 375 * behavior or deadlock. 376 * 377 * @throws SecurityException 378 * if a security manager exists and its <code>checkExit</code> 379 * method doesn't allow the exit. 380 * 381 * @see java.lang.Runtime#exit(int) 382 * @see java.lang.Runtime#gc() 383 * @see java.lang.SecurityManager#checkExit(int) 384 * @since JDK1.1 385 */ 386 @Deprecated 387 public static void runFinalizersOnExit(boolean value) { 388 finalizeOnExit = value; 389 } 390 391 /** 392 * Executes the specified string command in a separate process. 393 * 394 * <p>This is a convenience method. An invocation of the form 395 * <tt>exec(command)</tt> 396 * behaves in exactly the same way as the invocation 397 * <tt>{@link #exec(String, String[], File) exec}(command, null, null)</tt>. 398 * 399 * @param command a specified system command. 400 * 401 * @return A new {@link Process} object for managing the subprocess 402 * 403 * @throws SecurityException 404 * If a security manager exists and its 405 * {@link SecurityManager#checkExec checkExec} 406 * method doesn't allow creation of the subprocess 407 * 408 * @throws IOException 409 * If an I/O error occurs 410 * 411 * @throws NullPointerException 412 * If <code>command</code> is <code>null</code> 413 * 414 * @throws IllegalArgumentException 415 * If <code>command</code> is empty 416 * 417 * @see #exec(String[], String[], File) 418 * @see ProcessBuilder 419 */ 420 public Process exec(String command) throws IOException { 421 return exec(command, null, null); 422 } 423 424 /** 425 * Executes the specified string command in a separate process with the 426 * specified environment. 427 * 428 * <p>This is a convenience method. An invocation of the form 429 * <tt>exec(command, envp)</tt> 430 * behaves in exactly the same way as the invocation 431 * <tt>{@link #exec(String, String[], File) exec}(command, envp, null)</tt>. 432 * 433 * @param command a specified system command. 434 * 435 * @param envp array of strings, each element of which 436 * has environment variable settings in the format 437 * <i>name</i>=<i>value</i>, or 438 * <tt>null</tt> if the subprocess should inherit 439 * the environment of the current process. 440 * 441 * @return A new {@link Process} object for managing the subprocess 442 * 443 * @throws SecurityException 444 * If a security manager exists and its 445 * {@link SecurityManager#checkExec checkExec} 446 * method doesn't allow creation of the subprocess 447 * 448 * @throws IOException 449 * If an I/O error occurs 450 * 451 * @throws NullPointerException 452 * If <code>command</code> is <code>null</code>, 453 * or one of the elements of <code>envp</code> is <code>null</code> 454 * 455 * @throws IllegalArgumentException 456 * If <code>command</code> is empty 457 * 458 * @see #exec(String[], String[], File) 459 * @see ProcessBuilder 460 */ 461 public Process exec(String command, String[] envp) throws IOException { 462 return exec(command, envp, null); 463 } 464 465 /** 466 * Executes the specified string command in a separate process with the 467 * specified environment and working directory. 468 * 469 * <p>This is a convenience method. An invocation of the form 470 * <tt>exec(command, envp, dir)</tt> 471 * behaves in exactly the same way as the invocation 472 * <tt>{@link #exec(String[], String[], File) exec}(cmdarray, envp, dir)</tt>, 473 * where <code>cmdarray</code> is an array of all the tokens in 474 * <code>command</code>. 475 * 476 * <p>More precisely, the <code>command</code> string is broken 477 * into tokens using a {@link StringTokenizer} created by the call 478 * <code>new {@link StringTokenizer}(command)</code> with no 479 * further modification of the character categories. The tokens 480 * produced by the tokenizer are then placed in the new string 481 * array <code>cmdarray</code>, in the same order. 482 * 483 * @param command a specified system command. 484 * 485 * @param envp array of strings, each element of which 486 * has environment variable settings in the format 487 * <i>name</i>=<i>value</i>, or 488 * <tt>null</tt> if the subprocess should inherit 489 * the environment of the current process. 490 * 491 * @param dir the working directory of the subprocess, or 492 * <tt>null</tt> if the subprocess should inherit 493 * the working directory of the current process. 494 * 495 * @return A new {@link Process} object for managing the subprocess 496 * 497 * @throws SecurityException 498 * If a security manager exists and its 499 * {@link SecurityManager#checkExec checkExec} 500 * method doesn't allow creation of the subprocess 501 * 502 * @throws IOException 503 * If an I/O error occurs 504 * 505 * @throws NullPointerException 506 * If <code>command</code> is <code>null</code>, 507 * or one of the elements of <code>envp</code> is <code>null</code> 508 * 509 * @throws IllegalArgumentException 510 * If <code>command</code> is empty 511 * 512 * @see ProcessBuilder 513 * @since 1.3 514 */ 515 public Process exec(String command, String[] envp, File dir) 516 throws IOException { 517 if (command.length() == 0) 518 throw new IllegalArgumentException("Empty command"); 519 520 StringTokenizer st = new StringTokenizer(command); 521 String[] cmdarray = new String[st.countTokens()]; 522 for (int i = 0; st.hasMoreTokens(); i++) 523 cmdarray[i] = st.nextToken(); 524 return exec(cmdarray, envp, dir); 525 } 526 527 /** 528 * Executes the specified command and arguments in a separate process. 529 * 530 * <p>This is a convenience method. An invocation of the form 531 * <tt>exec(cmdarray)</tt> 532 * behaves in exactly the same way as the invocation 533 * <tt>{@link #exec(String[], String[], File) exec}(cmdarray, null, null)</tt>. 534 * 535 * @param cmdarray array containing the command to call and 536 * its arguments. 537 * 538 * @return A new {@link Process} object for managing the subprocess 539 * 540 * @throws SecurityException 541 * If a security manager exists and its 542 * {@link SecurityManager#checkExec checkExec} 543 * method doesn't allow creation of the subprocess 544 * 545 * @throws IOException 546 * If an I/O error occurs 547 * 548 * @throws NullPointerException 549 * If <code>cmdarray</code> is <code>null</code>, 550 * or one of the elements of <code>cmdarray</code> is <code>null</code> 551 * 552 * @throws IndexOutOfBoundsException 553 * If <code>cmdarray</code> is an empty array 554 * (has length <code>0</code>) 555 * 556 * @see ProcessBuilder 557 */ 558 public Process exec(String cmdarray[]) throws IOException { 559 return exec(cmdarray, null, null); 560 } 561 562 /** 563 * Executes the specified command and arguments in a separate process 564 * with the specified environment. 565 * 566 * <p>This is a convenience method. An invocation of the form 567 * <tt>exec(cmdarray, envp)</tt> 568 * behaves in exactly the same way as the invocation 569 * <tt>{@link #exec(String[], String[], File) exec}(cmdarray, envp, null)</tt>. 570 * 571 * @param cmdarray array containing the command to call and 572 * its arguments. 573 * 574 * @param envp array of strings, each element of which 575 * has environment variable settings in the format 576 * <i>name</i>=<i>value</i>, or 577 * <tt>null</tt> if the subprocess should inherit 578 * the environment of the current process. 579 * 580 * @return A new {@link Process} object for managing the subprocess 581 * 582 * @throws SecurityException 583 * If a security manager exists and its 584 * {@link SecurityManager#checkExec checkExec} 585 * method doesn't allow creation of the subprocess 586 * 587 * @throws IOException 588 * If an I/O error occurs 589 * 590 * @throws NullPointerException 591 * If <code>cmdarray</code> is <code>null</code>, 592 * or one of the elements of <code>cmdarray</code> is <code>null</code>, 593 * or one of the elements of <code>envp</code> is <code>null</code> 594 * 595 * @throws IndexOutOfBoundsException 596 * If <code>cmdarray</code> is an empty array 597 * (has length <code>0</code>) 598 * 599 * @see ProcessBuilder 600 */ 601 public Process exec(String[] cmdarray, String[] envp) throws IOException { 602 return exec(cmdarray, envp, null); 603 } 604 605 606 /** 607 * Executes the specified command and arguments in a separate process with 608 * the specified environment and working directory. 609 * 610 * <p>Given an array of strings <code>cmdarray</code>, representing the 611 * tokens of a command line, and an array of strings <code>envp</code>, 612 * representing "environment" variable settings, this method creates 613 * a new process in which to execute the specified command. 614 * 615 * <p>This method checks that <code>cmdarray</code> is a valid operating 616 * system command. Which commands are valid is system-dependent, 617 * but at the very least the command must be a non-empty list of 618 * non-null strings. 619 * 620 * <p>If <tt>envp</tt> is <tt>null</tt>, the subprocess inherits the 621 * environment settings of the current process. 622 * 623 * <p>A minimal set of system dependent environment variables may 624 * be required to start a process on some operating systems. 625 * As a result, the subprocess may inherit additional environment variable 626 * settings beyond those in the specified environment. 627 * 628 * <p>{@link ProcessBuilder#start()} is now the preferred way to 629 * start a process with a modified environment. 630 * 631 * <p>The working directory of the new subprocess is specified by <tt>dir</tt>. 632 * If <tt>dir</tt> is <tt>null</tt>, the subprocess inherits the 633 * current working directory of the current process. 634 * 635 * <p>If a security manager exists, its 636 * {@link SecurityManager#checkExec checkExec} 637 * method is invoked with the first component of the array 638 * <code>cmdarray</code> as its argument. This may result in a 639 * {@link SecurityException} being thrown. 640 * 641 * <p>Starting an operating system process is highly system-dependent. 642 * Among the many things that can go wrong are: 643 * <ul> 644 * <li>The operating system program file was not found. 645 * <li>Access to the program file was denied. 646 * <li>The working directory does not exist. 647 * </ul> 648 * 649 * <p>In such cases an exception will be thrown. The exact nature 650 * of the exception is system-dependent, but it will always be a 651 * subclass of {@link IOException}. 652 * 653 * 654 * @param cmdarray array containing the command to call and 655 * its arguments. 656 * 657 * @param envp array of strings, each element of which 658 * has environment variable settings in the format 659 * <i>name</i>=<i>value</i>, or 660 * <tt>null</tt> if the subprocess should inherit 661 * the environment of the current process. 662 * 663 * @param dir the working directory of the subprocess, or 664 * <tt>null</tt> if the subprocess should inherit 665 * the working directory of the current process. 666 * 667 * @return A new {@link Process} object for managing the subprocess 668 * 669 * @throws SecurityException 670 * If a security manager exists and its 671 * {@link SecurityManager#checkExec checkExec} 672 * method doesn't allow creation of the subprocess 673 * 674 * @throws IOException 675 * If an I/O error occurs 676 * 677 * @throws NullPointerException 678 * If <code>cmdarray</code> is <code>null</code>, 679 * or one of the elements of <code>cmdarray</code> is <code>null</code>, 680 * or one of the elements of <code>envp</code> is <code>null</code> 681 * 682 * @throws IndexOutOfBoundsException 683 * If <code>cmdarray</code> is an empty array 684 * (has length <code>0</code>) 685 * 686 * @see ProcessBuilder 687 * @since 1.3 688 */ 689 public Process exec(String[] cmdarray, String[] envp, File dir) 690 throws IOException { 691 return new ProcessBuilder(cmdarray) 692 .environment(envp) 693 .directory(dir) 694 .start(); 695 } 696 697 /** 698 * Returns the number of processors available to the Java virtual machine. 699 * 700 * <p> This value may change during a particular invocation of the virtual 701 * machine. Applications that are sensitive to the number of available 702 * processors should therefore occasionally poll this property and adjust 703 * their resource usage appropriately. </p> 704 * 705 * @return the maximum number of processors available to the virtual 706 * machine; never smaller than one 707 * @since 1.4 708 */ 709 public int availableProcessors() { 710 return (int) Libcore.os.sysconf(_SC_NPROCESSORS_CONF); 711 } 712 713 /** 714 * Returns the amount of free memory in the Java Virtual Machine. 715 * Calling the 716 * <code>gc</code> method may result in increasing the value returned 717 * by <code>freeMemory.</code> 718 * 719 * @return an approximation to the total amount of memory currently 720 * available for future allocated objects, measured in bytes. 721 */ 722 public native long freeMemory(); 723 724 /** 725 * Returns the total amount of memory in the Java virtual machine. 726 * The value returned by this method may vary over time, depending on 727 * the host environment. 728 * <p> 729 * Note that the amount of memory required to hold an object of any 730 * given type may be implementation-dependent. 731 * 732 * @return the total amount of memory currently available for current 733 * and future objects, measured in bytes. 734 */ 735 public native long totalMemory(); 736 737 /** 738 * Returns the maximum amount of memory that the Java virtual machine will 739 * attempt to use. If there is no inherent limit then the value {@link 740 * java.lang.Long#MAX_VALUE} will be returned. </p> 741 * 742 * @return the maximum amount of memory that the virtual machine will 743 * attempt to use, measured in bytes 744 * @since 1.4 745 */ 746 public native long maxMemory(); 747 748 /** 749 * Runs the garbage collector. 750 * Calling this method suggests that the Java virtual machine expend 751 * effort toward recycling unused objects in order to make the memory 752 * they currently occupy available for quick reuse. When control 753 * returns from the method call, the virtual machine has made 754 * its best effort to recycle all discarded objects. 755 * <p> 756 * The name <code>gc</code> stands for "garbage 757 * collector". The virtual machine performs this recycling 758 * process automatically as needed, in a separate thread, even if the 759 * <code>gc</code> method is not invoked explicitly. 760 * <p> 761 * The method {@link System#gc()} is the conventional and convenient 762 * means of invoking this method. 763 */ 764 public native void gc(); 765 766 /* Wormhole for calling java.lang.ref.Finalizer.runFinalization */ 767 private static native void runFinalization0(); 768 769 /** 770 * Runs the finalization methods of any objects pending finalization. 771 * Calling this method suggests that the Java virtual machine expend 772 * effort toward running the <code>finalize</code> methods of objects 773 * that have been found to be discarded but whose <code>finalize</code> 774 * methods have not yet been run. When control returns from the 775 * method call, the virtual machine has made a best effort to 776 * complete all outstanding finalizations. 777 * <p> 778 * The virtual machine performs the finalization process 779 * automatically as needed, in a separate thread, if the 780 * <code>runFinalization</code> method is not invoked explicitly. 781 * <p> 782 * The method {@link System#runFinalization()} is the conventional 783 * and convenient means of invoking this method. 784 * 785 * @see java.lang.Object#finalize() 786 */ 787 public void runFinalization() { 788 VMRuntime.runFinalization(0); 789 } 790 791 /** 792 * Enables/Disables tracing of instructions. 793 * If the <code>boolean</code> argument is <code>true</code>, this 794 * method suggests that the Java virtual machine emit debugging 795 * information for each instruction in the virtual machine as it 796 * is executed. The format of this information, and the file or other 797 * output stream to which it is emitted, depends on the host environment. 798 * The virtual machine may ignore this request if it does not support 799 * this feature. The destination of the trace output is system 800 * dependent. 801 * <p> 802 * If the <code>boolean</code> argument is <code>false</code>, this 803 * method causes the virtual machine to stop performing the 804 * detailed instruction trace it is performing. 805 * 806 * @param enable <code>true</code> to enable instruction tracing; 807 * <code>false</code> to disable this feature. 808 */ 809 // Android changed - param name s/on/enable 810 public void traceInstructions(boolean enable) { 811 } 812 813 /** 814 * Enables/Disables tracing of method calls. 815 * If the <code>boolean</code> argument is <code>true</code>, this 816 * method suggests that the Java virtual machine emit debugging 817 * information for each method in the virtual machine as it is 818 * called. The format of this information, and the file or other output 819 * stream to which it is emitted, depends on the host environment. The 820 * virtual machine may ignore this request if it does not support 821 * this feature. 822 * <p> 823 * Calling this method with argument false suggests that the 824 * virtual machine cease emitting per-call debugging information. 825 * 826 * @param enable <code>true</code> to enable instruction tracing; 827 * <code>false</code> to disable this feature. 828 */ 829 // Android changed - param name s/on/enable 830 public void traceMethodCalls(boolean enable) { 831 if (enable != tracingMethods) { 832 if (enable) { 833 VMDebug.startMethodTracing(); 834 } else { 835 VMDebug.stopMethodTracing(); 836 } 837 tracingMethods = enable; 838 } 839 } 840 841 /** 842 * Loads the specified filename as a dynamic library. The filename 843 * argument must be a complete path name, 844 * (for example 845 * <code>Runtime.getRuntime().load("/home/avh/lib/libX11.so");</code>). 846 * <p> 847 * First, if there is a security manager, its <code>checkLink</code> 848 * method is called with the <code>filename</code> as its argument. 849 * This may result in a security exception. 850 * <p> 851 * This is similar to the method {@link #loadLibrary(String)}, but it 852 * accepts a general file name as an argument rather than just a library 853 * name, allowing any file of native code to be loaded. 854 * <p> 855 * The method {@link System#load(String)} is the conventional and 856 * convenient means of invoking this method. 857 * 858 * @param filename the file to load. 859 * @exception SecurityException if a security manager exists and its 860 * <code>checkLink</code> method doesn't allow 861 * loading of the specified dynamic library 862 * @exception UnsatisfiedLinkError if the file does not exist. 863 * @exception NullPointerException if <code>filename</code> is 864 * <code>null</code> 865 * @see java.lang.Runtime#getRuntime() 866 * @see java.lang.SecurityException 867 * @see java.lang.SecurityManager#checkLink(java.lang.String) 868 */ 869 @CallerSensitive 870 public void load(String filename) { 871 load0(VMStack.getStackClass1(), filename); 872 } 873 874 /** Check target sdk, if it's higher than N, we throw an UnsupportedOperationException */ 875 private void checkTargetSdkVersionForLoad(String methodName) { 876 final int targetSdkVersion = VMRuntime.getRuntime().getTargetSdkVersion(); 877 if (targetSdkVersion > 24) { 878 throw new UnsupportedOperationException(methodName + " is not supported on SDK " + 879 targetSdkVersion); 880 } 881 } 882 883 // Fixes b/25859957 regression. Depending on private methods is bad, mkay. 884 void load(String absolutePath, ClassLoader loader) { 885 checkTargetSdkVersionForLoad("java.lang.Runtime#load(String, ClassLoader)"); 886 887 java.lang.System.logE("java.lang.Runtime#load(String, ClassLoader)" + 888 " is private and will be removed in a future Android release"); 889 if (absolutePath == null) { 890 throw new NullPointerException("absolutePath == null"); 891 } 892 String error = doLoad(absolutePath, loader); 893 if (error != null) { 894 throw new UnsatisfiedLinkError(error); 895 } 896 } 897 898 synchronized void load0(Class fromClass, String filename) { 899 if (!(new File(filename).isAbsolute())) { 900 throw new UnsatisfiedLinkError( 901 "Expecting an absolute path of the library: " + filename); 902 } 903 if (filename == null) { 904 throw new NullPointerException("filename == null"); 905 } 906 String error = doLoad(filename, fromClass.getClassLoader()); 907 if (error != null) { 908 throw new UnsatisfiedLinkError(error); 909 } 910 } 911 912 /** 913 * Loads the dynamic library with the specified library name. 914 * A file containing native code is loaded from the local file system 915 * from a place where library files are conventionally obtained. The 916 * details of this process are implementation-dependent. The 917 * mapping from a library name to a specific filename is done in a 918 * system-specific manner. 919 * <p> 920 * First, if there is a security manager, its <code>checkLink</code> 921 * method is called with the <code>libname</code> as its argument. 922 * This may result in a security exception. 923 * <p> 924 * The method {@link System#loadLibrary(String)} is the conventional 925 * and convenient means of invoking this method. If native 926 * methods are to be used in the implementation of a class, a standard 927 * strategy is to put the native code in a library file (call it 928 * <code>LibFile</code>) and then to put a static initializer: 929 * <blockquote><pre> 930 * static { System.loadLibrary("LibFile"); } 931 * </pre></blockquote> 932 * within the class declaration. When the class is loaded and 933 * initialized, the necessary native code implementation for the native 934 * methods will then be loaded as well. 935 * <p> 936 * If this method is called more than once with the same library 937 * name, the second and subsequent calls are ignored. 938 * 939 * @param libname the name of the library. 940 * @exception SecurityException if a security manager exists and its 941 * <code>checkLink</code> method doesn't allow 942 * loading of the specified dynamic library 943 * @exception UnsatisfiedLinkError if the library does not exist. 944 * @exception NullPointerException if <code>libname</code> is 945 * <code>null</code> 946 * @see java.lang.SecurityException 947 * @see java.lang.SecurityManager#checkLink(java.lang.String) 948 */ 949 @CallerSensitive 950 public void loadLibrary(String libname) { 951 loadLibrary0(VMStack.getCallingClassLoader(), libname); 952 } 953 954 /** 955 * Temporarily preserved for backward compatibility. Applications call this 956 * method using reflection. 957 * 958 * **** THIS METHOD WILL BE REMOVED IN A FUTURE ANDROID VERSION **** 959 * 960 * http://b/26217329 961 * 962 * @hide 963 */ 964 public void loadLibrary(String libname, ClassLoader classLoader) { 965 checkTargetSdkVersionForLoad("java.lang.Runtime#loadLibrary(String, ClassLoader)"); 966 java.lang.System.logE("java.lang.Runtime#loadLibrary(String, ClassLoader)" + 967 " is private and will be removed in a future Android release"); 968 loadLibrary0(classLoader, libname); 969 } 970 971 synchronized void loadLibrary0(ClassLoader loader, String libname) { 972 if (libname.indexOf((int)File.separatorChar) != -1) { 973 throw new UnsatisfiedLinkError( 974 "Directory separator should not appear in library name: " + libname); 975 } 976 String libraryName = libname; 977 if (loader != null) { 978 String filename = loader.findLibrary(libraryName); 979 if (filename == null) { 980 // It's not necessarily true that the ClassLoader used 981 // System.mapLibraryName, but the default setup does, and it's 982 // misleading to say we didn't find "libMyLibrary.so" when we 983 // actually searched for "liblibMyLibrary.so.so". 984 throw new UnsatisfiedLinkError(loader + " couldn't find \"" + 985 System.mapLibraryName(libraryName) + "\""); 986 } 987 String error = doLoad(filename, loader); 988 if (error != null) { 989 throw new UnsatisfiedLinkError(error); 990 } 991 return; 992 } 993 994 String filename = System.mapLibraryName(libraryName); 995 List<String> candidates = new ArrayList<String>(); 996 String lastError = null; 997 for (String directory : getLibPaths()) { 998 String candidate = directory + filename; 999 candidates.add(candidate); 1000 1001 if (IoUtils.canOpenReadOnly(candidate)) { 1002 String error = doLoad(candidate, loader); 1003 if (error == null) { 1004 return; // We successfully loaded the library. Job done. 1005 } 1006 lastError = error; 1007 } 1008 } 1009 1010 if (lastError != null) { 1011 throw new UnsatisfiedLinkError(lastError); 1012 } 1013 throw new UnsatisfiedLinkError("Library " + libraryName + " not found; tried " + candidates); 1014 } 1015 1016 private volatile String[] mLibPaths = null; 1017 1018 private String[] getLibPaths() { 1019 if (mLibPaths == null) { 1020 synchronized(this) { 1021 if (mLibPaths == null) { 1022 mLibPaths = initLibPaths(); 1023 } 1024 } 1025 } 1026 return mLibPaths; 1027 } 1028 1029 private static String[] initLibPaths() { 1030 String javaLibraryPath = System.getProperty("java.library.path"); 1031 if (javaLibraryPath == null) { 1032 return EmptyArray.STRING; 1033 } 1034 String[] paths = javaLibraryPath.split(":"); 1035 // Add a '/' to the end of each directory so we don't have to do it every time. 1036 for (int i = 0; i < paths.length; ++i) { 1037 if (!paths[i].endsWith("/")) { 1038 paths[i] += "/"; 1039 } 1040 } 1041 return paths; 1042 } 1043 private String doLoad(String name, ClassLoader loader) { 1044 // Android apps are forked from the zygote, so they can't have a custom LD_LIBRARY_PATH, 1045 // which means that by default an app's shared library directory isn't on LD_LIBRARY_PATH. 1046 1047 // The PathClassLoader set up by frameworks/base knows the appropriate path, so we can load 1048 // libraries with no dependencies just fine, but an app that has multiple libraries that 1049 // depend on each other needed to load them in most-dependent-first order. 1050 1051 // We added API to Android's dynamic linker so we can update the library path used for 1052 // the currently-running process. We pull the desired path out of the ClassLoader here 1053 // and pass it to nativeLoad so that it can call the private dynamic linker API. 1054 1055 // We didn't just change frameworks/base to update the LD_LIBRARY_PATH once at the 1056 // beginning because multiple apks can run in the same process and third party code can 1057 // use its own BaseDexClassLoader. 1058 1059 // We didn't just add a dlopen_with_custom_LD_LIBRARY_PATH call because we wanted any 1060 // dlopen(3) calls made from a .so's JNI_OnLoad to work too. 1061 1062 // So, find out what the native library search path is for the ClassLoader in question... 1063 String librarySearchPath = null; 1064 if (loader != null && loader instanceof BaseDexClassLoader) { 1065 BaseDexClassLoader dexClassLoader = (BaseDexClassLoader) loader; 1066 librarySearchPath = dexClassLoader.getLdLibraryPath(); 1067 } 1068 // nativeLoad should be synchronized so there's only one LD_LIBRARY_PATH in use regardless 1069 // of how many ClassLoaders are in the system, but dalvik doesn't support synchronized 1070 // internal natives. 1071 synchronized (this) { 1072 return nativeLoad(name, loader, librarySearchPath); 1073 } 1074 } 1075 1076 // TODO: should be synchronized, but dalvik doesn't support synchronized internal natives. 1077 private static native String nativeLoad(String filename, ClassLoader loader, 1078 String librarySearchPath); 1079 1080 /** 1081 * Creates a localized version of an input stream. This method takes 1082 * an <code>InputStream</code> and returns an <code>InputStream</code> 1083 * equivalent to the argument in all respects except that it is 1084 * localized: as characters in the local character set are read from 1085 * the stream, they are automatically converted from the local 1086 * character set to Unicode. 1087 * <p> 1088 * If the argument is already a localized stream, it may be returned 1089 * as the result. 1090 * 1091 * @param in InputStream to localize 1092 * @return a localized input stream 1093 * @see java.io.InputStream 1094 * @see java.io.BufferedReader#BufferedReader(java.io.Reader) 1095 * @see java.io.InputStreamReader#InputStreamReader(java.io.InputStream) 1096 * @deprecated As of JDK 1.1, the preferred way to translate a byte 1097 * stream in the local encoding into a character stream in Unicode is via 1098 * the <code>InputStreamReader</code> and <code>BufferedReader</code> 1099 * classes. 1100 */ 1101 @Deprecated 1102 public InputStream getLocalizedInputStream(InputStream in) { 1103 return in; 1104 } 1105 1106 /** 1107 * Creates a localized version of an output stream. This method 1108 * takes an <code>OutputStream</code> and returns an 1109 * <code>OutputStream</code> equivalent to the argument in all respects 1110 * except that it is localized: as Unicode characters are written to 1111 * the stream, they are automatically converted to the local 1112 * character set. 1113 * <p> 1114 * If the argument is already a localized stream, it may be returned 1115 * as the result. 1116 * 1117 * @deprecated As of JDK 1.1, the preferred way to translate a 1118 * Unicode character stream into a byte stream in the local encoding is via 1119 * the <code>OutputStreamWriter</code>, <code>BufferedWriter</code>, and 1120 * <code>PrintWriter</code> classes. 1121 * 1122 * @param out OutputStream to localize 1123 * @return a localized output stream 1124 * @see java.io.OutputStream 1125 * @see java.io.BufferedWriter#BufferedWriter(java.io.Writer) 1126 * @see java.io.OutputStreamWriter#OutputStreamWriter(java.io.OutputStream) 1127 * @see java.io.PrintWriter#PrintWriter(java.io.OutputStream) 1128 */ 1129 @Deprecated 1130 public OutputStream getLocalizedOutputStream(OutputStream out) { 1131 return out; 1132 } 1133 1134 } 1135