Skip to content

Commit

Permalink
8343958: Remove security manager impl in java.lang.Process and java.l…
Browse files Browse the repository at this point in the history
…ang.Runtime.exec

Reviewed-by: jpai, mullan, alanb
  • Loading branch information
Roger Riggs committed Nov 13, 2024
1 parent 5ac330b commit 168b18e
Show file tree
Hide file tree
Showing 4 changed files with 58 additions and 172 deletions.
25 changes: 2 additions & 23 deletions src/java.base/share/classes/java/lang/ProcessBuilder.java
Original file line number Diff line number Diff line change
Expand Up @@ -339,11 +339,6 @@ public List<String> command() {
* @see System#getenv()
*/
public Map<String,String> environment() {
@SuppressWarnings("removal")
SecurityManager security = System.getSecurityManager();
if (security != null)
security.checkPermission(new RuntimePermission("getenv.*"));

if (environment == null)
environment = ProcessEnvironment.environment();

Expand Down Expand Up @@ -1069,11 +1064,6 @@ private Process start(Redirect[] redirects) throws IOException {
// Throws IndexOutOfBoundsException if command is empty
String prog = cmdarray[0];

@SuppressWarnings("removal")
SecurityManager security = System.getSecurityManager();
if (security != null)
security.checkExec(prog);

String dir = directory == null ? null : directory.toString();

for (String s : cmdarray) {
Expand Down Expand Up @@ -1112,24 +1102,13 @@ private Process start(Redirect[] redirects) throws IOException {
}
return process;
} catch (IOException | IllegalArgumentException e) {
String exceptionInfo = ": " + e.getMessage();
Throwable cause = e;
if ((e instanceof IOException) && security != null) {
// Can not disclose the fail reason for read-protected files.
try {
security.checkRead(prog);
} catch (SecurityException se) {
exceptionInfo = "";
cause = se;
}
}
// It's much easier for us to create a high-quality error
// message than the low-level C code which found the problem.
throw new IOException(
"Cannot run program \"" + prog + "\""
+ (dir == null ? "" : " (in directory \"" + dir + "\")")
+ exceptionInfo,
cause);
+ ": " + e.getMessage(),
e);
}
}

Expand Down
95 changes: 25 additions & 70 deletions src/java.base/share/classes/java/lang/ProcessHandleImpl.java
Original file line number Diff line number Diff line change
@@ -1,5 +1,5 @@
/*
* Copyright (c) 2014, 2022, Oracle and/or its affiliates. All rights reserved.
* Copyright (c) 2014, 2024, Oracle and/or its affiliates. All rights reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
Expand Down Expand Up @@ -84,28 +84,28 @@ final class ProcessHandleImpl implements ProcessHandle {
/**
* The thread pool of "process reaper" daemon threads.
*/
@SuppressWarnings("removal")
private static final Executor processReaperExecutor =
AccessController.doPrivileged((PrivilegedAction<Executor>) () -> {
// Initialize ThreadLocalRandom now to avoid using the smaller stack
// of the processReaper threads.
ThreadLocalRandom.current();

// For a debug build, the stack shadow zone is larger;
// Increase the total stack size to avoid potential stack overflow.
int debugDelta = "release".equals(System.getProperty("jdk.debug")) ? 0 : (4*4096);
final long stackSize = Boolean.getBoolean("jdk.lang.processReaperUseDefaultStackSize")
? 0 : REAPER_DEFAULT_STACKSIZE + debugDelta;

ThreadFactory threadFactory = grimReaper -> {
Thread t = InnocuousThread.newSystemThread("process reaper", grimReaper,
stackSize, Thread.MAX_PRIORITY);
privilegedThreadSetDaemon(t, true);
return t;
};

return Executors.newCachedThreadPool(threadFactory);
});
private static final Executor processReaperExecutor = initReaper();

private static Executor initReaper() {
// Initialize ThreadLocalRandom now to avoid using the smaller stack
// of the processReaper threads.
ThreadLocalRandom.current();

// For a debug build, the stack shadow zone is larger;
// Increase the total stack size to avoid potential stack overflow.
int debugDelta = "release".equals(System.getProperty("jdk.debug")) ? 0 : (4 * 4096);
final long stackSize = Boolean.getBoolean("jdk.lang.processReaperUseDefaultStackSize")
? 0 : REAPER_DEFAULT_STACKSIZE + debugDelta;

ThreadFactory threadFactory = grimReaper -> {
Thread t = InnocuousThread.newSystemThread("process reaper", grimReaper,
stackSize, Thread.MAX_PRIORITY);
t.setDaemon(true);
return t;
};

return Executors.newCachedThreadPool(threadFactory);
}

private static class ExitCompletion extends CompletableFuture<Integer> {
final boolean isReaping;
Expand All @@ -115,22 +115,6 @@ private static class ExitCompletion extends CompletableFuture<Integer> {
}
}

@SuppressWarnings("removal")
private static void privilegedThreadSetName(Thread thread, String name) {
AccessController.doPrivileged((PrivilegedAction<Void>) () -> {
thread.setName(name);
return null;
});
}

@SuppressWarnings("removal")
private static void privilegedThreadSetDaemon(Thread thread, boolean on) {
AccessController.doPrivileged((PrivilegedAction<Void>) () -> {
thread.setDaemon(on);
return null;
});
}

/**
* Returns a CompletableFuture that completes with process exit status when
* the process completes.
Expand Down Expand Up @@ -158,7 +142,7 @@ static CompletableFuture<Integer> completion(long pid, boolean shouldReap) {
public void run() {
Thread t = Thread.currentThread();
String threadName = t.getName();
privilegedThreadSetName(t, "process reaper (pid " + pid + ")");
t.setName("process reaper (pid " + pid + ")");
try {
int exitValue = waitForProcessExit0(pid, shouldReap);
if (exitValue == NOT_A_CHILD) {
Expand Down Expand Up @@ -189,7 +173,7 @@ public void run() {
completions.remove(pid, newCompletion);
} finally {
// Restore thread name
privilegedThreadSetName(t, threadName);
t.setName(threadName);
}
}
});
Expand Down Expand Up @@ -255,14 +239,8 @@ private ProcessHandleImpl(long pid, long startTime) {
* @param pid the native process identifier
* @return The ProcessHandle for the pid if the process is alive;
* or {@code null} if the process ID does not exist in the native system.
* @throws SecurityException if RuntimePermission("manageProcess") is not granted
*/
static Optional<ProcessHandle> get(long pid) {
@SuppressWarnings("removal")
SecurityManager sm = System.getSecurityManager();
if (sm != null) {
sm.checkPermission(new RuntimePermission("manageProcess"));
}
long start = isAlive0(pid);
return (start >= 0)
? Optional.of(new ProcessHandleImpl(pid, start))
Expand Down Expand Up @@ -296,14 +274,8 @@ public long pid() {
* Returns the ProcessHandle for the current native process.
*
* @return The ProcessHandle for the OS process.
* @throws SecurityException if RuntimePermission("manageProcess") is not granted
*/
public static ProcessHandleImpl current() {
@SuppressWarnings("removal")
SecurityManager sm = System.getSecurityManager();
if (sm != null) {
sm.checkPermission(new RuntimePermission("manageProcess"));
}
return current;
}

Expand All @@ -319,15 +291,8 @@ public static ProcessHandleImpl current() {
*
* @return a ProcessHandle of the parent process; {@code null} is returned
* if the child process does not have a parent
* @throws SecurityException if permission is not granted by the
* security policy
*/
public Optional<ProcessHandle> parent() {
@SuppressWarnings("removal")
SecurityManager sm = System.getSecurityManager();
if (sm != null) {
sm.checkPermission(new RuntimePermission("manageProcess"));
}
long ppid = parent0(pid, startTime);
if (ppid <= 0) {
return Optional.empty();
Expand Down Expand Up @@ -442,11 +407,6 @@ public Stream<ProcessHandle> children() {
* @return a stream of ProcessHandles
*/
static Stream<ProcessHandle> children(long pid) {
@SuppressWarnings("removal")
SecurityManager sm = System.getSecurityManager();
if (sm != null) {
sm.checkPermission(new RuntimePermission("manageProcess"));
}
int size = 100;
long[] childpids = null;
long[] starttimes = null;
Expand All @@ -463,11 +423,6 @@ static Stream<ProcessHandle> children(long pid) {

@Override
public Stream<ProcessHandle> descendants() {
@SuppressWarnings("removal")
SecurityManager sm = System.getSecurityManager();
if (sm != null) {
sm.checkPermission(new RuntimePermission("manageProcess"));
}
int size = 100;
long[] pids = null;
long[] ppids = null;
Expand Down
21 changes: 2 additions & 19 deletions src/java.base/unix/classes/java/lang/ProcessImpl.java
Original file line number Diff line number Diff line change
Expand Up @@ -42,14 +42,10 @@
import java.util.concurrent.TimeUnit;
import java.util.concurrent.locks.Condition;
import java.util.concurrent.locks.ReentrantLock;
import java.security.AccessController;
import java.security.PrivilegedActionException;
import java.security.PrivilegedExceptionAction;
import jdk.internal.access.JavaIOFileDescriptorAccess;
import jdk.internal.access.SharedSecrets;
import jdk.internal.util.OperatingSystem;
import jdk.internal.util.StaticProperty;
import sun.security.action.GetPropertyAction;

/**
* java.lang.Process subclass in the UNIX environment.
Expand Down Expand Up @@ -95,7 +91,7 @@ private static enum LaunchMechanism {
* @throws Error if the requested launch mechanism is not found or valid
*/
private static LaunchMechanism launchMechanism() {
String s = GetPropertyAction.privilegedGetProperty("jdk.lang.Process.launchMechanism");
String s = System.getProperty("jdk.lang.Process.launchMechanism");
if (s == null) {
return LaunchMechanism.POSIX_SPAWN;
}
Expand Down Expand Up @@ -282,7 +278,6 @@ private native int forkAndExec(int mode, byte[] helperpath,
boolean redirectErrorStream)
throws IOException;

@SuppressWarnings("removal")
private ProcessImpl(final byte[] prog,
final byte[] argBlock, final int argc,
final byte[] envBlock, final int envc,
Expand All @@ -302,14 +297,7 @@ private ProcessImpl(final byte[] prog,
redirectErrorStream);
processHandle = ProcessHandleImpl.getInternal(pid);

try {
AccessController.doPrivileged((PrivilegedExceptionAction<Void>) () -> {
initStreams(fds, forceNullOutputStream);
return null;
});
} catch (PrivilegedActionException ex) {
throw (IOException) ex.getCause();
}
initStreams(fds, forceNullOutputStream);
}

static FileDescriptor newFileDescriptor(int fd) {
Expand Down Expand Up @@ -507,11 +495,6 @@ public CompletableFuture<Process> onExit() {

@Override
public ProcessHandle toHandle() {
@SuppressWarnings("removal")
SecurityManager sm = System.getSecurityManager();
if (sm != null) {
sm.checkPermission(new RuntimePermission("manageProcess"));
}
return processHandle;
}

Expand Down
Loading

1 comment on commit 168b18e

@openjdk-notifier
Copy link

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Please sign in to comment.