How does /usr/bin/java work on Mac?
Solution 1:
I can't fully answer your question but I have a few practical clues I can share.
TL:DR;
I think that /usr/bin/java
is a proxy application, part of MacOS, that calls the java
command in the current java installation as defined by JAVA_HOME
env var.
And this is the same for all the java related commands in /usr/bin
More details
I have installed (manually, by unzipping the openjdks into /Library/Java/JavaVirtualMachines/
) many versions of Java, and just by setting a different JAVA_HOME, the version switches:
$ JAVA_HOME=/Library/Java/JavaVirtualMachines/jdk1.8.0_112.jdk/Contents/Home && java -version
java version "1.8.0_112"
Java(TM) SE Runtime Environment (build 1.8.0_112-b16)
Java HotSpot(TM) 64-Bit Server VM (build 25.112-b16, mixed mode)
$ JAVA_HOME=/Library/Java/JavaVirtualMachines/amazon-corretto-11.jdk/Contents/Home/ && java -version
openjdk version "11.0.11" 2021-04-20 LTS
OpenJDK Runtime Environment Corretto-11.0.11.9.1 (build 11.0.11+9-LTS)
OpenJDK 64-Bit Server VM Corretto-11.0.11.9.1 (build 11.0.11+9-LTS, mixed mode)
$ JAVA_HOME=/Library/Java/JavaVirtualMachines/jdk-16.0.1.jdk/Contents/Home/ && java -version
openjdk version "16.0.1" 2021-04-20
OpenJDK Runtime Environment (build 16.0.1+9-24)
OpenJDK 64-Bit Server VM (build 16.0.1+9-24, mixed mode, sharing)
All the Java commands in /usr/bin
have the same size (136Kb in my case):
$ ll -h /usr/bin/ja*
-rwxr-xr-x 1 root wheel 136K Jan 1 2020 /usr/bin/jar
-rwxr-xr-x 1 root wheel 136K Jan 1 2020 /usr/bin/jarsigner
-rwxr-xr-x 1 root wheel 136K Jan 1 2020 /usr/bin/java
-rwxr-xr-x 1 root wheel 136K Jan 1 2020 /usr/bin/javac
-rwxr-xr-x 1 root wheel 136K Jan 1 2020 /usr/bin/javadoc
-rwxr-xr-x 1 root wheel 136K Jan 1 2020 /usr/bin/javah
-rwxr-xr-x 1 root wheel 136K Jan 1 2020 /usr/bin/javap
-rwxr-xr-x 1 root wheel 136K Jan 1 2020 /usr/bin/javapackager
-rwxr-xr-x 1 root wheel 136K Jan 1 2020 /usr/bin/javaws
Actually, many files in /usr/bin
are the same:
$ find /usr/bin | sort | xargs md5 | grep d50afbfa4f5d05e8db7ad88c30390888
MD5 (/usr/bin/appletviewer) = d50afbfa4f5d05e8db7ad88c30390888
MD5 (/usr/bin/apt) = d50afbfa4f5d05e8db7ad88c30390888
MD5 (/usr/bin/extcheck) = d50afbfa4f5d05e8db7ad88c30390888
MD5 (/usr/bin/idlj) = d50afbfa4f5d05e8db7ad88c30390888
MD5 (/usr/bin/jar) = d50afbfa4f5d05e8db7ad88c30390888
MD5 (/usr/bin/jarsigner) = d50afbfa4f5d05e8db7ad88c30390888
MD5 (/usr/bin/java) = d50afbfa4f5d05e8db7ad88c30390888
MD5 (/usr/bin/javac) = d50afbfa4f5d05e8db7ad88c30390888
MD5 (/usr/bin/javadoc) = d50afbfa4f5d05e8db7ad88c30390888
MD5 (/usr/bin/javah) = d50afbfa4f5d05e8db7ad88c30390888
.
.
.
In "System Information.app > Software > Installation" I don't find any specific installation occurred around Jan 1 2020
, from the same I see I installed Catalina on 2019-10-12 and Big Sur on 2020-12-04 (all files in /usr/bin
have date Jan 1 2020
).
Also pkgutil
doesn't tell me to which package installation the /usr/bin/java
commands belongs:
$ pkgutil --file-info /usr/bin/java
volume: /
path: /usr/bin/java
I believe it's part of MacOS and was installed (or updated) by Big Sur.
Let me know if I missed anything or have more info for a clearer picture :-)
Solution 2:
The most complete answer I've found is this Stack Overflow answer:
https://stackoverflow.com/questions/21964709/how-to-set-or-change-the-default-java-jdk-version-on-macos/44169445#44169445
In summary, /usr/bin/java
finds all of the JVMs under /Library/Java/JavaVirtualMachines
and ~/Library/Java/JavaVirtualMachines
and points to the latest JVM that has Contents/Info.plist
. If you rename that file in a JVM to, say, Contents/Info.plist.disabled
, then /usr/bin/java
will not pick it.