8194734 : Handle to jimage file inherited into child processes (win)
Alexander Miloslavskiy
alexandr.miloslavskiy at gmail.com
Mon Apr 2 21:50:28 UTC 2018
The problem in this bug is that jimage file is mistakenly opened with
"inherit by child processes" flag. In our case, the child process is
started with Runtime.exec() and serves as updater that can also replace
embedded JRE. However, due to jimage ("lib/modules") file handle being
inherited, embedded JRE can not be replaced.
The bug was introduced in commits "8087181: Move native jimage code to
its own library (maybe libjimage)"
Before this commit, os::open() was used in libjimage code and it handles
file inheritance correctly, see:
/hotspot/src/share/vm/classfile/imageFile.cpp
* ImageFileReader::open() uses os::open(_name, 0, O_RDONLY)
/hotspot/src/os/windows/vm/os_windows.cpp
* os::open() calls to ::open(pathbuf, oflag | O_BINARY | O_NOINHERIT, mode);
/hotspot/src/os/linux/vm/os_linux.cpp
* os::open() uses both O_CLOEXEC and FD_CLOEXEC
After this commit, a new osSupport::openReadOnly() is implemented and it
does not handle file inheritance properly.
Please find patch attached.
As far as I understand from OpenJDK's "How to contribute" page, I need a
"sponsor" who will get this patch applied.
Windows - compiled and tested:
Bug fixed.
Ubuntu - compiled and tested:
Bug did not occur before my patch due to another bug in childProcess()
function (src/java.base/unix/native/libjava/childproc.c) According to my
debugging, FD_CLOEXEC is applied to jimage file there because
childProcess() thinks that it's a error pipe (FAIL_FILENO). Should the
bug in childProcess() be fixed, it can unearth currently fixed bug.
-------------- next part --------------
# HG changeset patch
# User Alexander Miloslavskiy <alexandr.miloslavskiy at gmail.com>
# Date 1522703926 -10800
# Tue Apr 03 00:18:46 2018 +0300
# Node ID 87954e967cc67cab4b480a4ec7ff54a334e0f4ce
# Parent de0fd2c8a401a564f06d42fac15559154c42358a
8194734: jimage file descriptor was inherited into processes started with Runtime.exec()
Summary: Prevented inheritance with FD_CLOEXEC on unix, O_NOINHERIT on windows.
Refactoring: added O_RDONLY (equals 0)
Refactoring: added O_BINARY on windows (currently ignored by osSupport::read and osSupport::map_memory)
diff -r de0fd2c8a401 -r 87954e967cc6 src/java.base/unix/native/libjimage/osSupport_unix.cpp
--- a/src/java.base/unix/native/libjimage/osSupport_unix.cpp Fri Mar 30 14:36:18 2018 -0700
+++ b/src/java.base/unix/native/libjimage/osSupport_unix.cpp Tue Apr 03 00:18:46 2018 +0300
@@ -38,7 +38,16 @@
* Return the file descriptor.
*/
jint osSupport::openReadOnly(const char *path) {
- return ::open(path, 0);
+ int fd = ::open(path, O_RDONLY);
+
+ // jimage file descriptors must not be inherited by child processes.
+ // This is especially true for child processes started with Runtime.exec (see 8194734)
+ #ifdef FD_CLOEXEC
+ int flags = ::fcntl(fd, F_GETFD);
+ ::fcntl(fd, F_SETFD, flags | FD_CLOEXEC);
+ #endif
+
+ return fd;
}
/**
diff -r de0fd2c8a401 -r 87954e967cc6 src/java.base/windows/native/libjimage/osSupport_windows.cpp
--- a/src/java.base/windows/native/libjimage/osSupport_windows.cpp Fri Mar 30 14:36:18 2018 -0700
+++ b/src/java.base/windows/native/libjimage/osSupport_windows.cpp Tue Apr 03 00:18:46 2018 +0300
@@ -38,7 +38,9 @@
* Return the file descriptor.
*/
jint osSupport::openReadOnly(const char *path) {
- return ::open(path, 0, 0);
+ // jimage file descriptors must not be inherited by child processes.
+ // This is especially true for child processes started with Runtime.exec (see 8194734)
+ return ::open(path, O_BINARY | O_NOINHERIT, O_RDONLY);
}
/**
More information about the core-libs-dev
mailing list