From mboxrd@z Thu Jan 1 00:00:00 1970 Return-Path: Received: from lists.gentoo.org (pigeon.gentoo.org [208.92.234.80]) (using TLSv1.3 with cipher TLS_AES_256_GCM_SHA384 (256/256 bits) key-exchange X25519 server-signature RSA-PSS (2048 bits)) (No client certificate requested) by finch.gentoo.org (Postfix) with ESMTPS id DC540159C96 for ; Mon, 29 Jul 2024 21:53:17 +0000 (UTC) Received: from pigeon.gentoo.org (localhost [127.0.0.1]) by pigeon.gentoo.org (Postfix) with SMTP id BF8282BC0D4; Mon, 29 Jul 2024 21:52:49 +0000 (UTC) Received: from mail-lf1-x134.google.com (mail-lf1-x134.google.com [IPv6:2a00:1450:4864:20::134]) (using TLSv1.3 with cipher TLS_AES_256_GCM_SHA384 (256/256 bits) key-exchange X25519 server-signature RSA-PSS (4096 bits) server-digest SHA256) (No client certificate requested) by pigeon.gentoo.org (Postfix) with ESMTPS id 53FF42BC0CC for ; Mon, 29 Jul 2024 21:52:49 +0000 (UTC) Received: by mail-lf1-x134.google.com with SMTP id 2adb3069b0e04-52f024f468bso5840753e87.1 for ; Mon, 29 Jul 2024 14:52:49 -0700 (PDT) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=gmail.com; s=20230601; t=1722289968; x=1722894768; darn=lists.gentoo.org; h=content-transfer-encoding:mime-version:references:in-reply-to :message-id:date:subject:cc:to:from:from:to:cc:subject:date :message-id:reply-to; bh=2OkscpVDwkQRvBO1b5uRNtQlu597E0lKV60Ri75XbDo=; b=jjYskOf3ALyphobrTqqUbbap3V6msxdKy8azSO9Wsum++juGeS3sSLswUbJra5k7Q1 skxwxabbHUIqRULiK8p6PNPdYfXY/6ghekhbxofE3EsdcY1Rg/3eeEnzgauKBjkvWAAn qYCpySUqx/rEE2noAdmOX+4xS/RWhlujtIHxToH/PGEINYQ8/mBLwKCsRM6RFQ5KDIyx 9K1cnjXAvAW4U/mDR+baE5OQWpuDvTl/O2dbUwJRFBuRrAVo2pbxrFojrmEPvITyJzYW gGg4/edo+A8eNv1QZMY3IkvvXqpOpUV0RYAWxU+F3TwfHxURSFY6py56yf9rF1oW7rRO j5cw== X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=1e100.net; s=20230601; t=1722289968; x=1722894768; h=content-transfer-encoding:mime-version:references:in-reply-to :message-id:date:subject:cc:to:from:x-gm-message-state:from:to:cc :subject:date:message-id:reply-to; bh=2OkscpVDwkQRvBO1b5uRNtQlu597E0lKV60Ri75XbDo=; b=JcepFbGSjVOq8Xx68D9+1tLHsqcHhXJS/fu2dle8xTNLrDxy9GiE1W3MZx9Tv27/LJ UyYFTe6PQJTksCDmZc1XzVcpNInpaR8CW4weYzwkqsBxvrvtcD7lkdtotzKTrgt58dRd r2DBa7tOgX/XgCvhf1SnlG2h4wNJ2HC01hM9661hHnr2L9rCmCxP3ERF9ko+P6AB26+9 QlwPNeaY+YgD23edPPj/FwVMAD2FEy307TsGGK+cCW61oe7bIXTlox+A0uJ3/bOSMacJ t18rmlCY3XQL6k3e8x3q6cF/kEKa7uRd7+OhEqOYXtBRj2L5CxsQYtypg7jIOew06ZhI d4vA== X-Gm-Message-State: AOJu0YwggFInyNAj3r9d6qcwKk5w8BpYDrn7Deqgz9vjRdkk9E85HR0S vWd9B4xwidcUkeaaMx1t9erRBW8lDDsHXOZp63TjqGthrSYm/1gvzez8mwLX X-Google-Smtp-Source: AGHT+IFUA+c3ccMwMyULMz66VJ2dmdlEe27eCVZCnrfl+Vq04YoGi5VEh8EzigoB8LG2+/zxOXrPWA== X-Received: by 2002:a05:6512:10c2:b0:52c:fd46:bf07 with SMTP id 2adb3069b0e04-5309b2ce6d0mr7080190e87.49.1722289967489; Mon, 29 Jul 2024 14:52:47 -0700 (PDT) Received: from localhost.localdomain ([62.244.50.57]) by smtp.gmail.com with ESMTPSA id a640c23a62f3a-a7acad9046fsm564748266b.147.2024.07.29.14.52.46 (version=TLS1_3 cipher=TLS_AES_256_GCM_SHA384 bits=256/256); Mon, 29 Jul 2024 14:52:47 -0700 (PDT) From: Zurab Kvachadze To: gentoo-dev@lists.gentoo.org Cc: conikost@gentoo.org, Zurab Kvachadze Subject: [gentoo-dev] [RFC PATCH v2 02/20] nginx-module.eclass: Add new eclass for building NGINX external modules Date: Tue, 30 Jul 2024 00:52:18 +0300 Message-ID: <20240729215241.13243-3-zurabid2016@gmail.com> X-Mailer: git-send-email 2.44.2 In-Reply-To: <20240729215241.13243-1-zurabid2016@gmail.com> References: <20240729215241.13243-1-zurabid2016@gmail.com> Precedence: bulk List-Post: List-Help: List-Unsubscribe: List-Subscribe: List-Id: Gentoo Linux mail X-BeenThere: gentoo-dev@lists.gentoo.org Reply-to: gentoo-dev@lists.gentoo.org X-Auto-Response-Suppress: DR, RN, NRN, OOF, AutoReply MIME-Version: 1.0 Content-Transfer-Encoding: 8bit X-Archives-Salt: 3fbf449c-65e1-4fcd-bb23-c7aa99d0acd0 X-Archives-Hash: bd385bdce4be3f22fdbebfa384d93ebd Currently, it is impossible for NGINX external modules to be packaged on their own, separately from the NGINX ebuild. The nginx-module.eclass enables packaging third party NGINX modules as any other software in the Gentoo tree. The eclass builds on the foundation provided by nginx.eclass. NGINX modules are somewhat special in the way they are built. In addition to (obviously) requiring NGINX headers, their build system is the one of NGINX. Actually, they are intended to be built and installed alongside the NGINX server, but, luckily, it is possible to succesfuly build a module, given (1) the headers, (2) the build system and the exact same (3) ./configure flags that have been used to configure NGINX itself are present. The points (1) and (2) are taken for granted here, as nginx.eclass takes care of them: * headers are installed into /usr/include/nginx * build system is installed into /usr/src/nginx As for the (3) point, the configuration flags are recorder into ngx_auto_config.h file as preprocessor #define's. The file is also saved into /usr/include/nginx. The build process undergoes in the ${WORKDIR}/nginx directory, which has 3 symlinks: * src/ -> /usr/include/nginx * configure -> /usr/src/nginx/configure * auto/ -> /usr/src/nginx/auto The build is the exact same as building a module "in-tree": the ./configure script is called with the '--add-dynamic-module' flag. The rest of the eclass is really simple; src_compile() executes 'make modules' and src_install() installs the compiled shared objects into /usr/$(get_libdir)/nginx/modules. Closes: https://bugs.gentoo.org/573710 Signed-off-by: Zurab Kvachadze --- eclass/nginx-module.eclass | 180 +++++++++++++++++++++++++++++++++++++ 1 file changed, 180 insertions(+) create mode 100644 eclass/nginx-module.eclass diff --git a/eclass/nginx-module.eclass b/eclass/nginx-module.eclass new file mode 100644 index 000000000000..4f2a1e6c6ed6 --- /dev/null +++ b/eclass/nginx-module.eclass @@ -0,0 +1,180 @@ +# Copyright 1999-2024 Gentoo Authors +# Distributed under the terms of the GNU General Public License v2 + +# @ECLASS: nginx-module.eclass +# @MAINTAINER: +# Zurab Kvachadze +# @AUTHOR: +# Zurab Kvachadze +# @SUPPORTED_EAPIS: 8 +# @PROVIDES: toolchain-funcs flag-o-matic +# @BLURB: Provides a common set of functions for building NGINX's dynamic modules +# @DESCRIPTION: +# The nginx-module.eclass automates configuring, building and installing NGINX's +# dynamic modules. Using this eclass is as simple as calling 'inherit nginx-module'. +# +# This eclass automatically adds dependency on NGINX. If the part of the +# module's functionality depends on the NGINX configuration (e.g. +# HMAC generation support depending on http_ssl module being enabled), the +# corresponding code should be rewritten so that the functionality in question +# (1) is unconditionally enabled/disabled or (2) could be toggled by a USE flag. +# +# If the module makes use of the ngx_devel_kit (NDK), it must make sure to +# add that to the relevant *DEPEND variables and to call "append-cflags -DNDK", +# since (obviously) the NDK is not built alongside the module. + +case ${EAPI} in + 8) ;; + *) die "${ECLASS}: EAPI ${EAPI:-0} not supported" ;; +esac + +if [[ -z ${_NGINX_MODULE_ECLASS} ]]; then +_NGINX_MODULE_ECLASS=1 + +inherit toolchain-funcs flag-o-matic + +# @FUNCTION: econf_ngx +# @USAGE: [...] +# @DESCRIPTION: +# Call ./configure, passing the supplied arguments. +# The NGINX's build system consists of many helper scripts, which are executed +# relative to the working directory. Therefore, the function only supports +# executing the configure script from the current working directory. This +# function also checks whether the script is executable. If any of the above +# conditions are not satisfied, the function aborts the build process with +# 'die'. It also fails if the script itself exits with a non-zero exit code, +# unless the function is called with 'nonfatal'. +# If running ./configure is required, this is the way it should be done. +econf_ngx() { + debug-print-function "${FUNCNAME[0]}" "$@" + [[ ! -x ./configure ]] && + die "./configure is not present in the current working directory or is not executable" + echo "./configure ${*@Q}" >&2 + ./configure "$@" + # For some reason, NGINX's ./configure returns 1 if it is used with the + # '--help' argument. + if [[ $? -ne 0 && "$1" != --help ]]; then + die -n "./configure ${*@Q} failed" + fi +} + +# As per upstream documentation, modules must be rebuilt with each NGINX +# upgrade. +DEPEND=" + www-servers/nginx:=[modules(-)] +" +BDEPEND="${DEPEND}" +RDEPEND="${DEPEND}" + +# @ECLASS_VARIABLE: NGINX_MOD_S +# @DESCRIPTION: +# Holds the path to the module's build directory, used in the +# nginx-module_src_configure() phase function. Defaults to ${S}. Can be changed +# by the ebuild. +: "${NGINX_MOD_S=${S}}" + +# The ${S} variable is set to the path of the directory where the actual build +# will be performed. In this directory, symbolic links to NGINX's build system +# and NGINX's headers are created by the nginx-module_src_unpack() phase +# function. +S="${WORKDIR}/nginx" + + +# @FUNCTION: nginx-module_src_unpack +# @DESCRIPTION: +# Unpacks the sources and sets up the build directory in S=${WORKDIR}/nginx. +# Creates the following symbolic links (to not copy the files over): +# - '${S}/src' -> '/usr/include/nginx', +# - '${S}/auto' -> '/usr/src/nginx/auto', +# - '${S}/configure' -> '/usr/src/nginx/configure'. +# For additional information, see nginx.eclass source, namely +# nginx_src_install() function. +nginx-module_src_unpack() { + default + mkdir nginx || die "mkdir failed" + ln -s "${BROOT}/usr/src/nginx/configure" nginx/configure || die "ln failed" + ln -s "${BROOT}/usr/src/nginx/auto" nginx/auto || die "ln failed" + ln -s "${ESYSROOT}/usr/include/nginx" nginx/src || die "ln failed" +} + +# @FUNCTION: nginx-module_src_prepare +# @DESCRIPTION: +# Patches module's initialisation code so that any module's preprocessor +# definitions appear in the separate '__ngx_gentoo_mod_config.h' file inside the +# 'build' directory. This function also makes module's "config" script clear +# whatever content build/ngx_auto_config.h may have at the time of invocation. +# Then, default_src_prepare() is called. +nginx-module_src_prepare() { + sed -i -e '1i\' -e ': > build/ngx_auto_config.h' "${NGINX_MOD_S}/config" + echo 'mv build/ngx_auto_config.h build/__ngx_gentoo_mod_config.h' \ + >> "${NGINX_MOD_S}/config" + default_src_prepare +} + +# @FUNCTION: nginx-module_src_configure +# @DESCRIPTION: +# Configures the dynamic module(s) by calling NGINX's ./configure script. +# Custom flags can be supplied via the 'myconf' array, taking precedence over +# eclass's flags. +# This assembles ngx_auto_config.h from the system ngx_auto_config.h and +# __ngx_gentoo_mod_config.h (see nginx-module_src_prepare()), and +# ngx_auto_headers.h from the system ngx_auto_headers.h. +nginx-module_src_configure() { + local ngx_mod_flags + ngx_mod_flags=( + --with-cc="$(tc-getCC)" + --with-cpp="$(tc-getCPP)" + # The '-isystem' flag is used instead of '-I', so as for the installed + # (system) modules' headers to be of lower priority than the headers of + # the currently built module. This only affects the modules that both + # come with and install their own headers, e.g. ngx_devel_kit. + --with-cc-opt="-isystem src/modules" + --with-ld-opt="${LDFLAGS}" + --builddir=build + --add-dynamic-module="${NGINX_MOD_S}" + ) + + # NGINX build system adds directories under src/ to the include path based + # on selected modules. Since nginx.eclass does not save/restore the + # configuration flags, we have to add the directories to the include path + # manually. + # The src/os is added automatically by the auto/unix script and the + # src/modules directory is included by the '--with-cc-opt' configuration + # flag. + append-cflags "$(find -H src -mindepth 1 -type d \! \( \( -path 'src/os' -o \ + -path 'src/modules' \) -prune \) -printf '-I %p ')" + + eval "local -a EXTRA_ECONF=( ${EXTRA_ECONF} )" + + # Setting the required environmental variables to skip the unneeded + # execution of certain scripts (see nginx_src_install() in nginx.eclass). + _NGINX_GENTOO_SKIP_PHASES=1 econf_ngx \ + "${ngx_mod_flags[@]}" \ + "${myconf[@]}" \ + "${EXTRA_ECONF[@]}" + + cat "${ESYSROOT}/usr/include/nginx/ngx_auto_config.h" \ + build/__ngx_gentoo_mod_config.h > build/ngx_auto_config.h || + die "cat failed" + cp "${ESYSROOT}/usr/include/nginx/ngx_auto_headers.h" build || + die "cp failed" +} + +# @FUNCTION: nginx-module_src_compile +# @DESCRIPTION: +# Compiles the module(s) by calling "make modules". +nginx-module_src_compile() { + emake modules +} + +# @FUNCTION: nginx-module_src_install +# @DESCRIPTION: +# Installs the compiled module(s) into /usr/${libdir}/nginx/modules. +nginx-module_src_install() { + insinto "/usr/$(get_libdir)/nginx/modules" + doins build/*.so +} + +fi + +EXPORT_FUNCTIONS src_unpack src_prepare src_configure src_compile src_install -- 2.44.2