Skip to content

Instantly share code, notes, and snippets.

@corrigat
Last active May 17, 2023 22:48
Show Gist options
  • Save corrigat/d3c7c93a96917368f5be407073c05453 to your computer and use it in GitHub Desktop.
Save corrigat/d3c7c93a96917368f5be407073c05453 to your computer and use it in GitHub Desktop.
Building OpenJDK OpenJDK9 OpenJDK10 OpenJDK11 on Centos5 x86 and/or x86_64

Building OpenJDK9 OpenJDK10 OpenJDK11 on centos5

Why?

So you have to build software on this platform still, for SOME reason. Probably money, right? Yeah, I like money. Anyway... Either you, or someone you know has updated your Jenkins installation and now everything requires Java 11. MAYBE you got to plan this out and identified you'll have to get the agent to run on centos5. I didn't have that luxury. It was a weekend slack notification asking if Jenkins was dead. It's been a long week...

How?

Get your Centos 5.11 VM deployed. Clone it. Don't mess with the original machine. Get your yum.repos.d configs pointed to an http, not https, centos-vault mirror.

Install your dependencies from yum:

yum install -y \
	libXtst-devel libXt-devel libXrender-devel libXi-devel \
	cups-devel \
        freetype-devel \
	alsa-lib-devel \
    jdk1.8.0_131

sudo yum install -y "Development Libraries"
sudo yum groupinstall -y "Development Libraries"
sudo yum groupinstall -y "Java Development"

You need updated binutils and GCC 5+ to build openjdk. I used GCC-5.2.0. Get these onto your VM. If your version of curl works (upgraded openssl and curl using updated ssl) you can just use this script to build gcc 5.2.0

APP_NAME="gcc"
VERSION="5.2.0"
APP_STRING="$APP_NAME-$VERSION"
GCC_INSTALL_PATH="/opt/$APP_STRING"

#Binutils.
if [ ! -f "$GCC_INSTALL_PATH/ld" ] ; then
    BINUTILS_APP_NAME="binutils"
    BINUTILS_VERSION="2.30"
    BINUTILS_APP_STRING="$BINUTILS_APP_NAME-$VERSION"
    BINUTILS_ARCHIVE_NAME="$BINUTILS_APP_STRING.tar.bz2"

    DOWNLOAD_PATH="https://ftp.gnu.org/gnu/binutils/$BINUTILS_ARCHIVE_NAME"

    curl -LO $DOWNLOAD_PATH
    tar -xf "$BINUTILS_ARCHIVE_NAME" -C /tmp/

    echo "installing $APP_STRING.."

    pushd /tmp
    pushd $APP_STRING

    ./configure --prefix=$GCC_INSTALL_PATH

    make
    sudo make install
    popd

    rm -rf $APP_NAME*
    popd
fi

#GCC
curl -LO "https://ftp.gnu.org/gnu/gcc/gcc-5.2.0/gcc-5.2.0.tar.bz2"
tar -xf gcc-5.2.0.tar.bz2
pushd gcc-5.2.0
curl -LO "https://gcc.gnu.org/pub/gcc/infrastructure/mpfr-3.1.4.tar.bz2"
curl -LO "https://gcc.gnu.org/pub/gcc/infrastructure/mpc-1.0.3.tar.gz"
curl -LO "https://gcc.gnu.org/pub/gcc/infrastructure/gmp-6.1.0.tar.bz2"
tar -xf mpfr-3.1.4.tar.bz2 && ln -s mpfr-3.1.4 mpfr
tar -xf mpc-1.0.3.tar.gz && ln -s mpc-1.0.3 mpc
tar -xf gmp-6.1.0.tar.bz2 && ln -s gmp-6.1.0 gmp

Configure gcc
./configure --enable-languages=c,c++ \
            --disable-multilib       \
            --enable-threads=posix   \
            --enable-shared          \
            --disable-bootstrap      \
            --enable-__cxa_atexit    \
            --disable-nls            \
            --prefix=/opt/gcc-5.2.0

J_FACTOR=`cat /proc/cpuinfo | grep processor | wc -l`

make -j$J_FACTOR
make install

popd
rm -rf $APP_NAME*
popd

Verify your toolchain:

gcc

PATH=/opt/gcc-5.2.0/bin:$PATH gcc --version #should be 5.2.0

binutils

PATH=/opt/gcc-5.2.0/bin:$PATH ld --version #should be 2.30

Now we can build

We got jdk8 from yum, so go fetch jdk9u from openjdk github

git clone https://github.com/openjdk/jdk9u.git
pushd jdk9u

Configure with our toolchain

bash configure --with-toolchain-path=/opt/gcc-5.2.0/bin

Make

make CFLAGS_WARNINGS_ARE_ERRORS="-Wno-error" images

Make is going to fail with some fallocate64 messages. The excellent examples of amazing human beings in this stack overflow thread https://stackoverflow.com/questions/54432009/build-openjdk-9-in-centos5 suggests that we can just go comment that noise out. So go do that. When the build fails, edit the file it failed on and comment out the line with fallocate64. You will need to set result to 0 under that so the next code section block doesn't fail with undefined reference. so like vi jdk/src/java.base/unix/native/libjava/io_util_md.c +228 (where the number is the line from the build error). Relevant example:

        //RESTARTABLE(fallocate64(fd, 0, 0, length), result);
        // Return on success or if errno is neither EOPNOTSUPP nor ENOSYS
        int result = 0;

Run the make line again, repeat until the build fails. I think it's 2 or 3 files. If this fails, try prepending the make line with PATH=/opt/gcc-5.2.0/bin:$PATH to make sure binutils is found.

Nice.

Let's get the distributables into place.

I don't care about the alternatives system, and java installs aren't hard. head over the build output

cd build/linux-*-normal-server-release/

Make a place for openjdk9 to live

sudo mkdir /usr/java/openjdk9

Copy your distributables into place

sudo cp -r jdk /usr/java/openjdk9
sudo cp -r support /usr/java/openjdk9

Do some linking to make it easy to switch java versions

pushd /usr/java
sudo rm default
sudo ln openjdk9/jdk default

Now repoint the links in /usr/bin

pushd /usr/bin
for i in $(ls | grep ^java);do sudo \rm $i; sudo ln -s /usr/java/default/bin/$i $i;done
popd
popd
java --version # this should be openjdk9

Now go build openjdk10 using the same steps and get it into place so we can build openjdk11. When you copy the jdk and support dirs into /usr/java/openjdk10, remake the /usr/java/default link so it points to /usr/java/openjdk10/jdk.

Now the active java should be version 10

java --version

Nice.

Build and install autoconf - like version 2.69 or whatever. Just extract, configure, make, sudo make install. Download it from a mirror https://ftpmirror.gnu.org/gnu/autoconf/

Fetch the jdk11u from the openjdk github account and exctract it. Now configure for headless only because there's a lot of modern features in jdk11 and we can't build for it

bash configure --enable-headless-only --with-toolchain-path=/opt/gcc-5.2.0/bin

AAAAnd it failed. Roll your eyes at the lazy shell script checks, then edit the generated-configure.sh script

vi build/.configure-support/generated-configure.sh

search for 'Cannot compare'. There are 4 sections like this. Comment them all out. they don't matter.

  #if  [[ "$REFERENCE_VERSION" =~ (.*\.){4} ]] ; then
  #  as_fn_error $? "Internal error: Cannot compare to $TOOLCHAIN_MINIMUM_VERSION, only four parts (W.X.Y.Z) is supported" "$LINENO" 5
  #fi

Now run the same configure line again.

Now make

make CFLAGS_WARNINGS_ARE_ERRORS="-Wno-error" LOG_LEVEL=debug images

This is going to error out on FT_ something, I think it's in the path java.desktop somewhere, and it might be like it wants a filename. You're done. It's incomplete, but the pieces you probably need are done. go get the jdk and support folders out of the build output and set them up just like before.

You can now distribute jdk11 by itself to the original or new copy of your original node.

tar -czf ~/openjdk11-centos5-$(uname -i).tgz /usr/java/openjdk11

You can extract this to any machine and set up the linking like on the build machine, and most importantly, hook your centos5 nodes back up to your jenkins instance.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment