neubert
neubert

Reputation: 16792

compiling outdated PHP yields core dump with OpenSSL functions. OpenSSL version mismatch?

I compiled OpenSSL 0.9.8x with these ./config options:

./config --prefix=/usr/local/openssl-0.9.8 --openssldir=/usr/local/openssl-0.9.8

I'm compiling my PHP version with these ./configure options (among others):

   --with-openssl=/usr/local/openssl-0.9.8
   --with-openssl-dir=/usr/local/openssl-0.9.8

The problem is that when I run a PHP script with openssl_public_encrypt I'm getting a segmentation fault.

Here's what gdb says:

Program terminated with signal 11, Segmentation fault.
#0  0x00007fd3381c5a48 in RSA_public_encrypt () from /usr/lib/x86_64-linux-gnu/libcrypto.so.1.0.0

In /usr/local/openssl-0.9.8/lib/ there's libcrypto.so.0.9.8 so why isn't it using that?

Here's my OpenSSL Makefile:

https://pastebin.com/0QSqLCr8

Here's my PHP Makefile:

https://pastebin.com/dGmu0SYZ

Here's a Dockefile that reproduces the issue:

https://pastebin.com/ziZzvTh8

Any ideas? Thanks!

Upvotes: 2

Views: 471

Answers (2)

Gasol
Gasol

Reputation: 2519

Use LD_LIBRARY_PATH will fix the problem in general, but not for yours in this case.

I have rewritten the Dockerfile based on yours in order to fix the segfault.

  1. Remove both --disable-rpath and --libdir arguments on configure phase of PHP.

    We use rpath to locate shared objects at runtime for custom build openssl on /usr/local/openssl-0.9.8x.

    See option -rpath=dir from https://linux.die.net/man/1/ld

    Add a directory to the runtime library search path. This is used when linking an ELF executable with shared objects. All -rpath arguments are concatenated and passed to the runtime linker, which uses them to locate shared objects at runtime. The -rpath option is also used when locating shared objects which are needed by shared objects explicitly included in the link

  2. Add shared option to config script of OpenSSL

    To build share libraries (libcrypto.so.0.9.8 and libssl.so.0.9.8)

  3. Link kerberos libraries only in /usr/kerberos/lib

    Instead of linking all libraries from /usr/lib/x86_64-linux-gnu to /usr/kerberos/lib, The ordering of runtime search path is /usr/kerberos/lib:/usr/local/openssl-0.9.8/lib

Here is the changes

# https://pastebin.com/ziZzvTh8
--- ziZzvTh8.txt    2019-10-08 10:31:33.229217226 +0800
+++ Dockerfile   2019-10-08 12:07:03.271948150 +0800
@@ -8,7 +8,7 @@
     && wget --no-check-certificate http://www.openssl.org/source/openssl-0.9.8x.tar.gz \
     && tar xvfz openssl-0.9.8x.tar.gz \
     && cd openssl-0.9.8x \
-    && ./config --prefix=/usr/local/openssl-0.9.8 \
+    && ./config shared --prefix=/usr/local/openssl-0.9.8 \
     && make \
     && make install

@@ -23,7 +23,8 @@
     && ln -s /usr/lib/x86_64-linux-gnu/libexpat.so /usr/lib/ \
     && ln -s /usr/lib/x86_64-linux-gnu/libmysqlclient.so /usr/lib/libmysqlclient.so \
     && mkdir /usr/kerberos \
-    && ln -s /usr/lib/x86_64-linux-gnu /usr/kerberos/lib
+    && ln -s /usr/lib/x86_64-linux-gnu/mit-krb5 /usr/kerberos/lib
+

 RUN apt-get build-dep -y php5

@@ -43,7 +44,6 @@
        --with-zlib \
        --with-gd \
        --with-pgsql \
-       --disable-rpath \
        --enable-inline-optimization \
        --with-bz2 \
        --with-zlib \
@@ -62,7 +62,6 @@
        --enable-gd-native-ttf \
        --with-openssl=/usr/local/openssl-0.9.8 \
        --with-openssl-dir=/usr/local/openssl-0.9.8 \
-       --with-libdir=/lib/x86_64-linux-gnu \
        --enable-ftp \
        --with-imap \
        --with-imap-ssl \
@@ -72,4 +71,6 @@
      && make \
      && make install-cli

+ADD test.php /root/test.php
+
 CMD ["bash"]

test.php

<?php

$key = <<<EOF
-----BEGIN PUBLIC KEY-----
MIIBIjANBgkqhkiG9w0BAQEFAAOCAQ8AMIIBCgKCAQEAmHzD76i8DA25nC+Qsswi
OM0lW+gViiQD4tEm7suxBc2BGibtdlrsprVIId92hSjQKx4x8+XVWU6k89T5vy8Y
txpXN759OWdGkDi8uvZuYclMjW9Rao+oqSvbXH37R7oSY287I+6uOHclGhniQN3q
RyoXBkbhDk0/FTI/i549q/gGk1UZYv449KLrDOqmtohRcIyAYVnvvWtD1kIzourq
hMtEIrPqwoBqTaUA9kOIXw1jMovao2TN52j48KgOg9KjqtdwUwD9e6n7hJd/subF
6woc8L7zjJFOHH5gacUC7vtiMpBpnSyLQpjFLepYYwftjsRmg4xLdh+Zvgw3xqi4
lwIDAQAB
-----END PUBLIC KEY-----
EOF;

var_dump(openssl_public_encrypt($data, $crypted, $key));
var_dump($crypted);

Result

root@7c5df089bcb0:/# php -v
PHP 4.4.9 (cli) (built: Oct  8 2019 04:09:29)
Copyright (c) 1997-2008 The PHP Group
Zend Engine v1.3.0, Copyright (c) 1998-2004 Zend Technologies

root@7c5df089bcb0:/# php -i | grep OpenSSL
CURL Information => libcurl/7.26.0 OpenSSL/0.9.8x zlib/1.2.7 libidn/1.25 libssh2/1.4.2 librtmp/2.3
OpenSSL support => enabled
OpenSSL Version => OpenSSL 0.9.8x 10 May 2012

root@7c5df089bcb0:/# php /root/test.php
bool(true)
string(256) "W`r�b��e��',뱌Zł^�$�֗��S����w�j�د<������� �)<��j��JL(f@�A���5_S�X=g-?0M�(�d�����+���     �nD*gzË��ڞc'�\'͗�'vnmo�G�Bv�
#~�y D!��lb�t^���| )[za��5���y�G{�\�"

root@7c5df089bcb0:/# ldd `which php` | egrep 'libssl|libcrypto'
        libssl.so.0.9.8 => /usr/local/openssl-0.9.8/lib/libssl.so.0.9.8 (0x00007efe86da1000)
        libcrypto.so.0.9.8 => /usr/local/openssl-0.9.8/lib/libcrypto.so.0.9.8 (0x00007efe86a0b000)
        libssl.so.1.0.0 => /usr/lib/x86_64-linux-gnu/libssl.so.1.0.0 (0x00007efe8401b000)
        libcrypto.so.1.0.0 => /usr/lib/x86_64-linux-gnu/libcrypto.so.1.0.0 (0x00007efe83c21000)

root@7c5df089bcb0:/# objdump -p `which php` | grep RPATH
  RPATH                /usr/lib/x86_64-linux-gnu:/usr/kerberos/lib:/usr/local/openssl-0.9.8/lib

Upvotes: 1

raffis
raffis

Reputation: 556

The problem is that ld-linux resolves the link at runtime to the wrong library.

Try to execute it by setting LD_LIBRARY_PATH: LD_LIBRARY_PATH=/usr/local/openssl-0.9.8/lib php very_old_php_44_script_which_shall_not_be_used.php

If it works you might want to execute it using: LD_DEBUG=all php ... to check where and why the dynamic linker does not use the 0.9.8 openssl version.

Upvotes: 2

Related Questions