Skip to content

[Issue-3456] Apply systemPropertyVariables before the fork initializes networking - #3467

Merged
olamy merged 1 commit into
apache:masterfrom
joseluisll:fix-3456-prefer-ipv4-stack
Sep 10, 2026
Merged

olamy merged 1 commit into
apache:masterfrom
joseluisll:fix-3456-prefer-ipv4-stack

Conversation

@joseluisll

Copy link
Copy Markdown
Contributor

Fixes #3456.

What

systemPropertyVariables were applied too late in the forked JVM, so java.net.preferIPv4Stack (and java.net.preferIPv6Addresses) were silently ignored and the fork kept running on the IPv6 stack. Reported against 3.6.0, hit by Hadoop in HADOOP-19964.

Why

ForkedBooter#setupBooter read the booter properties file before applying the effective system properties:

BooterDeserializer booterDeserializer =
        new BooterDeserializer(createSurefirePropertiesIfFileExists(tmpDir, surefirePropsFileName));
setSystemProperties(new File(tmpDir, effectiveSystemPropertiesFileName));

That was harmless while the file was read with FileInputStream. In 3.6.0, commit 0c24343 (#3179) changed createSurefirePropertiesIfFileExists to java.nio.file.Files.newInputStream, and that call chain is:

Files.newInputStream β†’ FileChannel β†’ sun.nio.ch.UnixFileDispatcherImpl (WindowsFileDispatcherImpl) β†’ static { IOUtil.load(); } β†’ BootLoader.loadLibrary("net")

libnet's JNI_OnLoad calls Boolean.getBoolean("java.net.preferIPv4Stack") once and caches the answer in ipv6_available. So by the time setSystemProperties ran, the networking stack was already fixed, and the property had no effect β€” silently, and only on machines that actually have IPv6.

Ordinary java.nio.file calls are not enough to trigger this on Unix β€” sun.nio.fs.UnixNativeDispatcher loads only "nio" β€” which is why the file-reading path specifically is what regressed.

How

  • setSystemProperties(...) is now the first statement of setupBooter, before anything else in the fork runs.
  • createSurefirePropertiesIfFileExists uses FileInputStream again, so the guarantee does not silently depend on which java.io/java.nio API a future change happens to pick. Both spots carry a comment explaining why.

Platform caveat

Windows cannot be fixed this way and never worked, including before 3.6.0. sun.nio.fs.WindowsNativeDispatcher loads the native library itself:

static {
    // nio.dll has dependency on net.dll
    jdk.internal.loader.BootLoader.loadLibrary("net");
    jdk.internal.loader.BootLoader.loadLibrary("nio");
    initIDs();
}

Opening any jar on the class path reaches that (ZipFile$Source stats the file through java.nio.file), so java.net.preferIPv4Stack is already frozen before main runs. Users who need it on Windows have to pass -Djava.net.preferIPv4Stack=true via argLine. The new integration test is skipped on Windows for this reason.

Tests

  • ForkedBooterMockTest.shouldReadSurefirePropertiesWithoutInitializingNio β€” pins the booter properties file to a non-NIO stream. Fails on the 3.6.0 code, passes with this change.
  • Surefire3456PreferIPv4StackIT β€” runs a project configured with <java.net.preferIPv4Stack>true</java.net.preferIPv4Stack> in systemPropertyVariables and asserts the fork really is on the IPv4 stack (no Inet6Address reported by NetworkInterface). Skipped on Windows per the caveat above.

Verified locally: mvn clean install is green, and ForkedBooterMockTest fails as expected when the Files.newInputStream call is put back. The new IT was exercised on Windows only, where it fails without the fix on the property-propagation path and is skipped by the OS assumption in its final form β€” I have no Linux box here, so the IT's positive path needs CI to confirm.

Checklist

  • Each commit in the pull request should have a meaningful subject line and body.

  • Write a pull request description that is detailed enough to understand what the pull request does, how, and why.

  • Run mvn clean install to make sure basic checks pass. A more thorough check will be performed on your pull request automatically.

  • You have run the integration tests successfully (mvn -Prun-its clean install). β€” only the new IT was run locally; the full suite was not.

  • I hereby declare this contribution to be licenced under the Apache License Version 2.0, January 2004

πŸ€– Generated with Claude Code

…s networking

ForkedBooter#setupBooter read the booter properties file through
java.nio.file.Files before it applied the effective system properties.
On every platform that path initializes sun.nio.ch.IOUtil, whose static
initializer loads the native "net" library; libnet's JNI_OnLoad reads
java.net.preferIPv4Stack once and caches the result in ipv6_available.
Any value coming from systemPropertyVariables therefore arrived too late
and was silently ignored, and the fork kept running on the IPv6 stack.

The nio call was introduced in 3.6.0 (0c24343, apache#3179), which replaced
FileInputStream with Files.newInputStream; before that no java.nio
channel was touched during boot and the property took effect.

Apply the effective system properties as the very first statement of
setupBooter and read the booter properties file with FileInputStream
again, so the ordering guarantee does not depend on which java.io/java.nio
API a later change happens to pick.

Note that Windows cannot be fixed this way: sun.nio.fs.WindowsNativeDispatcher
loads "net" itself ("nio.dll has dependency on net.dll") and any jar on the
class path triggers it during JVM start-up, before main. The new integration
test is skipped there.

Co-Authored-By: Claude Opus 5 <noreply@anthropic.com>
@olamy olamy added the bug Something isn't working label Sep 10, 2026
@olamy olamy added this to the 3.6.1 milestone Sep 10, 2026
}

/**
* Deliberately uses {@link FileInputStream} instead of {@link java.nio.file.Files#newInputStream}: the latter

Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

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

LOL back in the 90's πŸ™„ 🀣

@olamy
olamy merged commit 4c9e16f into apache:master Sep 10, 2026
14 checks passed
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

bug Something isn't working

Projects

None yet

Development

Successfully merging this pull request may close these issues.

[Regression] java.net.preferIPv4Stack set via systemPropertyVariables is ignored since 3.6.0

2 participants