JDK-8156584 : Initialization race in sun.security.x509.AlgorithmId.get
  • Type: Bug
  • Component: security-libs
  • Sub-Component: java.security
  • Affected Version: 8u92
  • Priority: P2
  • Status: Closed
  • Resolution: Fixed
  • Submitted: 2016-05-09
  • Updated: 2022-05-28
  • Resolved: 2016-05-14
The Version table provides details related to the release that this issue/RFE will be addressed.

Unresolved : Release in which this issue/RFE will be addressed.
Resolved: Release in which this issue/RFE has been resolved.
Fixed : Release in which this issue/RFE has been fixed. The release containing this fix may be available for download as an Early Access Release or a General Availability Release.

To download the current JDK release, click here.
JDK 8 JDK 9 Other
8u311Fixed 9 b119Fixed openjdk8u302Fixed
Related Reports
Relates :  
Description
There is an obvious lack of concurrency control with AlgorithmId.oidTable, which can get initialized by two different threads, with rare failures.

Here's a repro that fails for us about 1% of the time:

import java.util.*;
import java.util.concurrent.*;
import sun.security.x509.AlgorithmId;

public class AlgorithmIdBug {
    public static void main(String[] args) throws Throwable {
        final String[] algorithmNames = {
            "PBKDF2WITHHMACSHA1",
            "PBEWITHMD5ANDDES",
            "DSA",
            "SHA384WITHRSA",
            "RSA",
            "SHA1WITHDSA",
            "SHA512WITHRSA",
            "MD2WITHRSA",
            "PBEWITHSHA1ANDDESEDE",
            "SHA1WITHRSA",
            "DIFFIEHELLMAN",
            "MD5WITHRSA",
            "PBEWITHSHA1ANDRC2_40",
            "SHA256WITHRSA",
        };

        final int THREADS = 2;
        final ExecutorService pool = Executors.newFixedThreadPool(THREADS);
        final CountDownLatch startingGate = new CountDownLatch(THREADS);
        final Runnable r = new Runnable() { public void run() {
            startingGate.countDown();
            do {} while (startingGate.getCount() > 0);
            try {
                for (String algorithmName : algorithmNames)
                    AlgorithmId.get(algorithmName);
            } catch (Throwable fail) {
                throw new AssertionError(fail);
            }
        }};
        final ArrayList<Future<?>> futures = new ArrayList<>();
        for (int i = 0; i < THREADS; i++)
            futures.add(pool.submit(r));
        pool.shutdown();
        for (Future<?> future : futures) future.get();
    }
}

giving intermittent

Caused by: java.security.NoSuchAlgorithmException: unrecognized algorithm name: SHA512WITHRSA
	at sun.security.x509.AlgorithmId.get(AlgorithmId.java:407)
	at AlgorithmIdBug$1.run(AlgorithmIdBug.java:32)

Comments
Yes, I will push the backport to jdk 8u soon.
28-05-2021

[~alexsch] Are you planning on pushing this to OpenJDK 8u?
27-05-2021

Fix request (8u): https://mail.openjdk.java.net/pipermail/jdk8u-dev/2021-April/013784.html
30-04-2021

I fixed up URLs pointing to my old webrevs. Amusingly, the official mercurial jdk9 URLs are also broken now. (We should all strive to make URLs eternally useful) I only barely remember this bug, but backport to jdk8 is probably still a good idea.
29-04-2021

Proposed fix for jdk8: http://cr.openjdk.java.net/~martin/webrevs/jdk8/AlgorithmId-get-race/ that also has some other minor improvements to the init code. Brad, I'm inviting you to take over from here if you like. (I understand it's traditional to do jdk9 first)
29-04-2021

For jdk8, we agreed on: http://cr.openjdk.java.net/~martin/webrevs/jdk8/AlgorithmId-get-race/ Here's the obvious port to jdk9: http://cr.openjdk.java.net/~martin/webrevs/jdk9/AlgorithmId-get-race/ although the lazy init should perhaps use jdk9 atomics.
29-04-2021

URL: http://hg.openjdk.java.net/jdk9/jdk9/jdk/rev/d7e0283a937c User: lana Date: 2016-05-18 20:42:24 +0000
18-05-2016

URL: http://hg.openjdk.java.net/jdk9/dev/jdk/rev/d7e0283a937c User: martin Date: 2016-05-14 02:15:10 +0000
14-05-2016

I don't have the cycles right now, I triaged it because it looked to be a valid bug/priority. I would suggest starting a review on security-dev@o.j.n.
10-05-2016

Reported by different teams at Google.
10-05-2016

Added Stuart and Paul because this bug may be a poster child for a fix (in jdk9) involving both VarHandles and immutable collections, since it features an init-once HashMap. But it also needs a more mundane fix for jdk8.
09-05-2016