diff --git a/AGENTS.md b/AGENTS.md index d6f3885..a05646c 100644 --- a/AGENTS.md +++ b/AGENTS.md @@ -21,7 +21,7 @@ - On Rocky Linux 9, `glibc-devel`, `kernel-headers`, and `libstdc++-devel` may be installed directly or as compiler dependencies because they are foundational C/C++ platform and toolchain components. - On Alpine Linux, `musl-dev` and `linux-headers` may be installed directly or as compiler dependencies because they are foundational C/C++ platform and toolchain components. -- The `rocky9-system` image is the exception to the rules above: it deliberately installs third-party libraries and their `-dev`/`-devel` packages from the Rocky Linux 9, CRB and EPEL repositories instead of building them from source. It uses no `sources/` directory and no pinned versions. Libraries missing from those repositories (for example the Meta libraries) are skipped, not built from source. +- The `rocky9-system` image is the exception to the rules above: it deliberately installs third-party libraries and their `-devel` packages from the Rocky Linux 9, CRB and EPEL repositories instead of building them from source, with Protobuf (`v3.21.12`, installed under `/usr/local`) as the only library built from source. Other libraries use distribution versions and are not pinned. Libraries missing from those repositories (for example `magic_enum`) are skipped, not built from source. ## Meta Libraries diff --git a/README.md b/README.md index 2073435..ecfad98 100644 --- a/README.md +++ b/README.md @@ -27,7 +27,7 @@ PREFIX=/opt/stack ./debian13/build.sh PREFIX=/opt/stack ./rocky9/build.sh ``` -The `rocky9-system` image uses the libraries shipped by Rocky Linux 9 (BaseOS, AppStream, CRB and EPEL) instead of building them from source. Libraries that those repositories do not provide, such as Folly and the other Meta libraries, are simply left out. +The `rocky9-system` image uses the libraries shipped by Rocky Linux 9 (BaseOS, AppStream, CRB and EPEL) instead of building them from source, except Protobuf, which is built from source (`v3.21.12`, under `/usr/local`). Libraries that those repositories do not provide are simply left out. ## Run diff --git a/rocky9-system/Dockerfile b/rocky9-system/Dockerfile index a060d5a..7f53873 100644 --- a/rocky9-system/Dockerfile +++ b/rocky9-system/Dockerfile @@ -41,7 +41,7 @@ RUN git config --global url."https://wangguofang.net/github.com/".insteadOf "htt RUN test "$(cmake --version | sed -n '1s/[^0-9]*//p' | cut -d. -f2)" -ge 29 # Libraries come from the distribution (Rocky Linux 9, CRB and EPEL) instead of being built from -# source. A package that is not available in these repositories is skipped, not an error. +# source, except Protobuf (below). A package that is not available in these repositories is skipped, not an error. RUN dnf install --assumeyes --enablerepo=crb,epel \ --setopt=skip_missing_names_on_install=True \ --skip-broken \ @@ -76,8 +76,6 @@ RUN dnf install --assumeyes --enablerepo=crb,epel \ nettle-devel \ numactl-devel \ openssl-devel \ - protobuf-compiler \ - protobuf-devel \ rapidjson-devel \ librdkafka-devel \ snappy-devel \ @@ -94,4 +92,19 @@ RUN dnf install --assumeyes --enablerepo=crb,epel \ && dnf clean all \ && rm -rf /var/cache/dnf +# Protobuf is the only library built from source; it is installed under /usr/local, which takes +# precedence over the system packages in /usr. +RUN --mount=type=bind,from=sources,source=protobuf-v3.21.12.tar.gz,target=/tmp/protobuf.tar.gz \ + mkdir src \ + && tar --extract --gzip --file=/tmp/protobuf.tar.gz --directory=src --strip-components=1 \ + && cmake -G Ninja -S src -B build -Dprotobuf_BUILD_TESTS=OFF \ + -Dprotobuf_BUILD_SHARED_LIBS=OFF \ + -Dprotobuf_WITH_ZLIB=ON \ + -DCMAKE_BUILD_TYPE=Release \ + -DBUILD_SHARED_LIBS=OFF \ + -DCMAKE_INSTALL_PREFIX=/usr/local \ + -DCMAKE_POSITION_INDEPENDENT_CODE=ON \ + && cmake --build build --parallel "$(nproc)" --target install \ + && rm -rf build src + CMD ["/bin/bash"] diff --git a/rocky9-system/build.sh b/rocky9-system/build.sh index 934400b..0b04f7e 100755 --- a/rocky9-system/build.sh +++ b/rocky9-system/build.sh @@ -4,16 +4,16 @@ set -eu IMAGE_NAME="${IMAGE_NAME:-rocky9-system-stack}" SCRIPT_DIR=$(CDPATH= cd -- "$(dirname -- "$0")" && pwd) +SOURCES_DIR="${SOURCES_DIR:-$SCRIPT_DIR/../sources}" +FETCH_SCRIPT="$SCRIPT_DIR/../fetch-sources.sh" -if command -v podman >/dev/null 2>&1; then - ENGINE=podman -elif command -v docker >/dev/null 2>&1; then - ENGINE=docker -else - echo "Error: Podman or Docker is required." >&2 +if ! command -v podman >/dev/null 2>&1; then + echo "Error: Podman is required." >&2 exit 1 fi -ENGINE="${CONTAINER_ENGINE:-$ENGINE}" -echo "Building image $IMAGE_NAME with $ENGINE ..." -exec "$ENGINE" build --tag "$IMAGE_NAME" "$SCRIPT_DIR" +SOURCES_DIR="$SOURCES_DIR" "$FETCH_SCRIPT" + +echo "Building image $IMAGE_NAME with podman ..." +exec podman build --build-context sources="$SOURCES_DIR" \ + --tag "$IMAGE_NAME" "$SCRIPT_DIR"