├── 8.0 └── alpine3.8 │ └── cli │ ├── Dockerfile │ ├── docker-php-entrypoint │ ├── docker-php-ext-configure │ ├── docker-php-ext-enable │ ├── docker-php-ext-install │ └── docker-php-source └── README.md /8.0/alpine3.8/cli/Dockerfile: -------------------------------------------------------------------------------- 1 | # 2 | # NOTE: THIS DOCKERFILE IS GENERATED VIA "update.sh" 3 | # 4 | # PLEASE DO NOT EDIT IT DIRECTLY. 5 | # 6 | 7 | FROM alpine:3.8 8 | 9 | # dependencies required for running "phpize" 10 | # these get automatically installed and removed by "docker-php-ext-*" (unless they're already installed) 11 | ENV PHPIZE_DEPS \ 12 | autoconf \ 13 | dpkg-dev dpkg \ 14 | file \ 15 | g++ \ 16 | gcc \ 17 | libc-dev \ 18 | make \ 19 | pkgconf \ 20 | re2c 21 | 22 | # persistent / runtime deps 23 | RUN apk add --no-cache \ 24 | ca-certificates \ 25 | curl \ 26 | tar \ 27 | xz \ 28 | # https://github.com/docker-library/php/issues/494 29 | libressl 30 | 31 | # ensure www-data user exists 32 | RUN set -x \ 33 | && addgroup -g 82 -S www-data \ 34 | && adduser -u 82 -D -S -G www-data www-data 35 | # 82 is the standard uid/gid for "www-data" in Alpine 36 | # https://git.alpinelinux.org/aports/tree/main/apache2/apache2.pre-install?h=3.9-stable 37 | # https://git.alpinelinux.org/aports/tree/main/lighttpd/lighttpd.pre-install?h=3.9-stable 38 | # https://git.alpinelinux.org/aports/tree/main/nginx/nginx.pre-install?h=3.9-stable 39 | 40 | ENV PHP_INI_DIR /usr/local/etc/php 41 | RUN set -eux; \ 42 | mkdir -p "$PHP_INI_DIR/conf.d"; \ 43 | # allow running as an arbitrary user (https://github.com/docker-library/php/issues/743) 44 | [ ! -d /var/www/html ]; \ 45 | mkdir -p /var/www/html; \ 46 | chown www-data:www-data /var/www/html; \ 47 | chmod 777 /var/www/html 48 | 49 | #### 50 | #### 51 | 52 | # Apply stack smash protection to functions using local buffers and alloca() 53 | # Make PHP's main executable position-independent (improves ASLR security mechanism, and has no performance impact on x86_64) 54 | # Enable optimization (-O2) 55 | # Enable linker optimization (this sorts the hash buckets to improve cache locality, and is non-default) 56 | # Adds GNU HASH segments to generated executables (this is used if present, and is much faster than sysv hash; in this configuration, sysv hash is also generated) 57 | # https://github.com/docker-library/php/issues/272 58 | ENV PHP_CFLAGS="-fstack-protector-strong -fpic -fpie -O2" 59 | ENV PHP_CPPFLAGS="$PHP_CFLAGS" 60 | ENV PHP_LDFLAGS="-Wl,-O1 -Wl,--hash-style=both -pie" 61 | 62 | ENV PHP_VERSION 8.0.0 63 | ENV PHP_URL="https://github.com/php/php-src/archive/master.zip" 64 | 65 | RUN set -xe; \ 66 | \ 67 | apk add --no-cache --virtual .fetch-deps \ 68 | gnupg \ 69 | wget \ 70 | ; \ 71 | \ 72 | mkdir -p /usr/src; \ 73 | cd /usr/src; \ 74 | \ 75 | wget -O php.zip "$PHP_URL"; \ 76 | \ 77 | apk del --no-network .fetch-deps 78 | 79 | COPY docker-php-source /usr/local/bin/ 80 | 81 | RUN set -xe \ 82 | && apk add --no-cache --virtual .build-deps \ 83 | $PHPIZE_DEPS \ 84 | argon2-dev \ 85 | coreutils \ 86 | curl-dev \ 87 | libedit-dev \ 88 | libsodium-dev \ 89 | libxml2-dev \ 90 | libressl-dev \ 91 | sqlite-dev \ 92 | bison \ 93 | \ 94 | && export CFLAGS="$PHP_CFLAGS" \ 95 | CPPFLAGS="$PHP_CPPFLAGS" \ 96 | LDFLAGS="$PHP_LDFLAGS" \ 97 | && docker-php-source extract \ 98 | && cd /usr/src/php/php-src-master \ 99 | && gnuArch="$(dpkg-architecture --query DEB_BUILD_GNU_TYPE)" \ 100 | && ./buildconf \ 101 | && ./configure \ 102 | --build="$gnuArch" \ 103 | --with-config-file-path="$PHP_INI_DIR" \ 104 | --with-config-file-scan-dir="$PHP_INI_DIR/conf.d" \ 105 | \ 106 | # make sure invalid --configure-flags are fatal errors intead of just warnings 107 | --enable-option-checking=fatal \ 108 | \ 109 | # https://github.com/docker-library/php/issues/439 110 | --with-mhash \ 111 | \ 112 | # --enable-ftp is included here because ftp_ssl_connect() needs ftp to be compiled statically (see https://github.com/docker-library/php/issues/236) 113 | --enable-ftp \ 114 | # --enable-mysqlnd is included here because it's harder to compile after the fact than extensions are (since it's a plugin for several extensions, not an extension in itself) 115 | --enable-mysqlnd \ 116 | # https://wiki.php.net/rfc/argon2_password_hash (7.2+) 117 | --with-password-argon2 \ 118 | # https://wiki.php.net/rfc/libsodium 119 | --with-sodium=shared \ 120 | \ 121 | --with-curl \ 122 | --with-libedit \ 123 | --with-openssl \ 124 | --with-zlib \ 125 | --enable-pcntl \ 126 | --enable-opcache \ 127 | \ 128 | # bundled pcre does not support JIT on s390x 129 | # https://manpages.debian.org/stretch/libpcre3-dev/pcrejit.3.en.html#AVAILABILITY_OF_JIT_SUPPORT 130 | $(test "$gnuArch" = 's390x-linux-gnu' && echo '--without-pcre-jit') \ 131 | \ 132 | $PHP_EXTRA_CONFIGURE_ARGS \ 133 | && make -j "$(nproc)" \ 134 | && find -type f -name '*.a' -delete \ 135 | && make install \ 136 | && { find /usr/local/bin /usr/local/sbin -type f -perm +0111 -exec strip --strip-all '{}' + || true; } \ 137 | && make clean \ 138 | \ 139 | # https://github.com/docker-library/php/issues/692 (copy default example "php.ini" files somewhere easily discoverable) 140 | && cp -v php.ini-* "$PHP_INI_DIR/" \ 141 | \ 142 | && cd / \ 143 | && docker-php-source delete \ 144 | \ 145 | && runDeps="$( \ 146 | scanelf --needed --nobanner --format '%n#p' --recursive /usr/local \ 147 | | tr ',' '\n' \ 148 | | sort -u \ 149 | | awk 'system("[ -e /usr/local/lib/" $1 " ]") == 0 { next } { print "so:" $1 }' \ 150 | )" \ 151 | && apk add --no-cache $runDeps \ 152 | \ 153 | && apk del --no-network .build-deps \ 154 | \ 155 | && rm -rf /tmp/pear ~/.pearrc 156 | 157 | COPY docker-php-ext-* docker-php-entrypoint /usr/local/bin/ 158 | 159 | # sodium was built as a shared module (so that it can be replaced later if so desired), so let's enable it too (https://github.com/docker-library/php/issues/598) 160 | RUN docker-php-ext-enable sodium 161 | 162 | ENTRYPOINT ["docker-php-entrypoint"] 163 | #### 164 | CMD ["php", "-a"] 165 | #### 166 | -------------------------------------------------------------------------------- /8.0/alpine3.8/cli/docker-php-entrypoint: -------------------------------------------------------------------------------- 1 | #!/bin/sh 2 | set -e 3 | 4 | # first arg is `-f` or `--some-option` 5 | if [ "${1#-}" != "$1" ]; then 6 | set -- php "$@" 7 | fi 8 | 9 | exec "$@" 10 | -------------------------------------------------------------------------------- /8.0/alpine3.8/cli/docker-php-ext-configure: -------------------------------------------------------------------------------- 1 | #!/bin/sh 2 | set -e 3 | 4 | # prefer user supplied CFLAGS, but default to our PHP_CFLAGS 5 | : ${CFLAGS:=$PHP_CFLAGS} 6 | : ${CPPFLAGS:=$PHP_CPPFLAGS} 7 | : ${LDFLAGS:=$PHP_LDFLAGS} 8 | export CFLAGS CPPFLAGS LDFLAGS 9 | 10 | srcExists= 11 | if [ -d /usr/src/php ]; then 12 | srcExists=1 13 | fi 14 | docker-php-source extract 15 | if [ -z "$srcExists" ]; then 16 | touch /usr/src/php/.docker-delete-me 17 | fi 18 | 19 | cd /usr/src/php/ext 20 | 21 | usage() { 22 | echo "usage: $0 ext-name [configure flags]" 23 | echo " ie: $0 gd --with-jpeg-dir=/usr/local/something" 24 | echo 25 | echo 'Possible values for ext-name:' 26 | find . \ 27 | -mindepth 2 \ 28 | -maxdepth 2 \ 29 | -type f \ 30 | -name 'config.m4' \ 31 | | xargs -n1 dirname \ 32 | | xargs -n1 basename \ 33 | | sort \ 34 | | xargs 35 | echo 36 | echo 'Some of the above modules are already compiled into PHP; please check' 37 | echo 'the output of "php -i" to see which modules are already loaded.' 38 | } 39 | 40 | ext="$1" 41 | if [ -z "$ext" ] || [ ! -d "$ext" ]; then 42 | usage >&2 43 | exit 1 44 | fi 45 | shift 46 | 47 | pm='unknown' 48 | if [ -e /lib/apk/db/installed ]; then 49 | pm='apk' 50 | fi 51 | 52 | if [ "$pm" = 'apk' ]; then 53 | if \ 54 | [ -n "$PHPIZE_DEPS" ] \ 55 | && ! apk info --installed .phpize-deps > /dev/null \ 56 | && ! apk info --installed .phpize-deps-configure > /dev/null \ 57 | ; then 58 | apk add --no-cache --virtual .phpize-deps-configure $PHPIZE_DEPS 59 | fi 60 | fi 61 | 62 | if command -v dpkg-architecture > /dev/null; then 63 | gnuArch="$(dpkg-architecture --query DEB_BUILD_GNU_TYPE)" 64 | set -- --build="$gnuArch" "$@" 65 | fi 66 | 67 | cd "$ext" 68 | phpize 69 | ./configure "$@" 70 | -------------------------------------------------------------------------------- /8.0/alpine3.8/cli/docker-php-ext-enable: -------------------------------------------------------------------------------- 1 | #!/bin/sh 2 | set -e 3 | 4 | extDir="$(php -r 'echo ini_get("extension_dir");')" 5 | cd "$extDir" 6 | 7 | usage() { 8 | echo "usage: $0 [options] module-name [module-name ...]" 9 | echo " ie: $0 gd mysqli" 10 | echo " $0 pdo pdo_mysql" 11 | echo " $0 --ini-name 0-apc.ini apcu apc" 12 | echo 13 | echo 'Possible values for module-name:' 14 | find -maxdepth 1 \ 15 | -type f \ 16 | -name '*.so' \ 17 | -exec basename '{}' ';' \ 18 | | sort \ 19 | | xargs 20 | echo 21 | echo 'Some of the above modules are already compiled into PHP; please check' 22 | echo 'the output of "php -i" to see which modules are already loaded.' 23 | } 24 | 25 | opts="$(getopt -o 'h?' --long 'help,ini-name:' -- "$@" || { usage >&2 && false; })" 26 | eval set -- "$opts" 27 | 28 | iniName= 29 | while true; do 30 | flag="$1" 31 | shift 32 | case "$flag" in 33 | --help|-h|'-?') usage && exit 0 ;; 34 | --ini-name) iniName="$1" && shift ;; 35 | --) break ;; 36 | *) 37 | { 38 | echo "error: unknown flag: $flag" 39 | usage 40 | } >&2 41 | exit 1 42 | ;; 43 | esac 44 | done 45 | 46 | modules= 47 | for module; do 48 | if [ -z "$module" ]; then 49 | continue 50 | fi 51 | if [ -f "$module.so" ] && ! [ -f "$module" ]; then 52 | # allow ".so" to be optional 53 | module="$module.so" 54 | fi 55 | if ! [ -f "$module" ]; then 56 | echo >&2 "error: '$module' does not exist" 57 | echo >&2 58 | usage >&2 59 | exit 1 60 | fi 61 | modules="$modules $module" 62 | done 63 | 64 | if [ -z "$modules" ]; then 65 | usage >&2 66 | exit 1 67 | fi 68 | 69 | pm='unknown' 70 | if [ -e /lib/apk/db/installed ]; then 71 | pm='apk' 72 | fi 73 | 74 | apkDel= 75 | if [ "$pm" = 'apk' ]; then 76 | if \ 77 | [ -n "$PHPIZE_DEPS" ] \ 78 | && ! apk info --installed .phpize-deps > /dev/null \ 79 | && ! apk info --installed .phpize-deps-configure > /dev/null \ 80 | ; then 81 | apk add --no-cache --virtual '.docker-php-ext-enable-deps' binutils 82 | apkDel='.docker-php-ext-enable-deps' 83 | fi 84 | fi 85 | 86 | for module in $modules; do 87 | if readelf --wide --syms "$module" | grep -q ' zend_extension_entry$'; then 88 | # https://wiki.php.net/internals/extensions#loading_zend_extensions 89 | absModule="$(readlink -f "$module")" 90 | line="zend_extension=$absModule" 91 | else 92 | line="extension=$module" 93 | fi 94 | 95 | ext="$(basename "$module")" 96 | ext="${ext%.*}" 97 | if php -r 'exit(extension_loaded("'"$ext"'") ? 0 : 1);'; then 98 | # this isn't perfect, but it's better than nothing 99 | # (for example, 'opcache.so' presents inside PHP as 'Zend OPcache', not 'opcache') 100 | echo >&2 101 | echo >&2 "warning: $ext ($module) is already loaded!" 102 | echo >&2 103 | continue 104 | fi 105 | 106 | ini="$PHP_INI_DIR/conf.d/${iniName:-"docker-php-ext-$ext.ini"}" 107 | if ! grep -q "$line" "$ini" 2>/dev/null; then 108 | echo "$line" >> "$ini" 109 | fi 110 | done 111 | 112 | if [ "$pm" = 'apk' ] && [ -n "$apkDel" ]; then 113 | apk del --no-network $apkDel 114 | fi 115 | -------------------------------------------------------------------------------- /8.0/alpine3.8/cli/docker-php-ext-install: -------------------------------------------------------------------------------- 1 | #!/bin/sh 2 | set -e 3 | 4 | # prefer user supplied CFLAGS, but default to our PHP_CFLAGS 5 | : ${CFLAGS:=$PHP_CFLAGS} 6 | : ${CPPFLAGS:=$PHP_CPPFLAGS} 7 | : ${LDFLAGS:=$PHP_LDFLAGS} 8 | export CFLAGS CPPFLAGS LDFLAGS 9 | 10 | srcExists= 11 | if [ -d /usr/src/php ]; then 12 | srcExists=1 13 | fi 14 | docker-php-source extract 15 | if [ -z "$srcExists" ]; then 16 | touch /usr/src/php/.docker-delete-me 17 | fi 18 | 19 | cd /usr/src/php/ext 20 | 21 | usage() { 22 | echo "usage: $0 [-jN] ext-name [ext-name ...]" 23 | echo " ie: $0 gd mysqli" 24 | echo " $0 pdo pdo_mysql" 25 | echo " $0 -j5 gd mbstring mysqli pdo pdo_mysql shmop" 26 | echo 27 | echo 'if custom ./configure arguments are necessary, see docker-php-ext-configure' 28 | echo 29 | echo 'Possible values for ext-name:' 30 | find . \ 31 | -mindepth 2 \ 32 | -maxdepth 2 \ 33 | -type f \ 34 | -name 'config.m4' \ 35 | | xargs -n1 dirname \ 36 | | xargs -n1 basename \ 37 | | sort \ 38 | | xargs 39 | echo 40 | echo 'Some of the above modules are already compiled into PHP; please check' 41 | echo 'the output of "php -i" to see which modules are already loaded.' 42 | } 43 | 44 | opts="$(getopt -o 'h?j:' --long 'help,jobs:' -- "$@" || { usage >&2 && false; })" 45 | eval set -- "$opts" 46 | 47 | j=1 48 | while true; do 49 | flag="$1" 50 | shift 51 | case "$flag" in 52 | --help|-h|'-?') usage && exit 0 ;; 53 | --jobs|-j) j="$1" && shift ;; 54 | --) break ;; 55 | *) 56 | { 57 | echo "error: unknown flag: $flag" 58 | usage 59 | } >&2 60 | exit 1 61 | ;; 62 | esac 63 | done 64 | 65 | exts= 66 | for ext; do 67 | if [ -z "$ext" ]; then 68 | continue 69 | fi 70 | if [ ! -d "$ext" ]; then 71 | echo >&2 "error: $PWD/$ext does not exist" 72 | echo >&2 73 | usage >&2 74 | exit 1 75 | fi 76 | exts="$exts $ext" 77 | done 78 | 79 | if [ -z "$exts" ]; then 80 | usage >&2 81 | exit 1 82 | fi 83 | 84 | pm='unknown' 85 | if [ -e /lib/apk/db/installed ]; then 86 | pm='apk' 87 | fi 88 | 89 | apkDel= 90 | if [ "$pm" = 'apk' ]; then 91 | if [ -n "$PHPIZE_DEPS" ]; then 92 | if apk info --installed .phpize-deps-configure > /dev/null; then 93 | apkDel='.phpize-deps-configure' 94 | elif ! apk info --installed .phpize-deps > /dev/null; then 95 | apk add --no-cache --virtual .phpize-deps $PHPIZE_DEPS 96 | apkDel='.phpize-deps' 97 | fi 98 | fi 99 | fi 100 | 101 | popDir="$PWD" 102 | for ext in $exts; do 103 | cd "$ext" 104 | [ -e Makefile ] || docker-php-ext-configure "$ext" 105 | make -j"$j" 106 | make -j"$j" install 107 | find modules \ 108 | -maxdepth 1 \ 109 | -name '*.so' \ 110 | -exec basename '{}' ';' \ 111 | | xargs -r docker-php-ext-enable 112 | make -j"$j" clean 113 | cd "$popDir" 114 | done 115 | 116 | if [ "$pm" = 'apk' ] && [ -n "$apkDel" ]; then 117 | apk del --no-network $apkDel 118 | fi 119 | 120 | if [ -e /usr/src/php/.docker-delete-me ]; then 121 | docker-php-source delete 122 | fi 123 | -------------------------------------------------------------------------------- /8.0/alpine3.8/cli/docker-php-source: -------------------------------------------------------------------------------- 1 | #!/bin/sh 2 | set -e 3 | 4 | dir=/usr/src/php 5 | 6 | usage() { 7 | echo "usage: $0 COMMAND" 8 | echo 9 | echo "Manage php source tarball lifecycle." 10 | echo 11 | echo "Commands:" 12 | echo " extract extract php source tarball into directory $dir if not already done." 13 | echo " delete delete extracted php source located into $dir if not already done." 14 | echo 15 | } 16 | 17 | case "$1" in 18 | extract) 19 | mkdir -p "$dir" 20 | if [ ! -f "$dir/.docker-extracted" ]; then 21 | unzip /usr/src/php.zip -d "$dir" 22 | touch "$dir/.docker-extracted" 23 | fi 24 | ;; 25 | 26 | delete) 27 | rm -rf "$dir" 28 | ;; 29 | 30 | *) 31 | usage 32 | exit 1 33 | ;; 34 | esac 35 | -------------------------------------------------------------------------------- /README.md: -------------------------------------------------------------------------------- 1 | # PHP 8.0 Docker with JIT 2 | 3 | Docker Unofficial Image packaging for PHP 4 | 5 | Run: 6 | ```bash 7 | docker run -it akondas/php:8.0-cli-alpine 8 | ``` 9 | 10 | Run with enabled JIT: 11 | ```bash 12 | docker run -it akondas/php:8.0-cli-alpine -dzend_extension=opcache.so -dopcache.enable_cli=1 -dopcache.jit_buffer_size=500000000 -dopcache.jit=1235 13 | ``` 14 | --------------------------------------------------------------------------------