diff --git a/r/redis-cluster-bv/Dockerfiles/8.4.1_ubi_9.7/Dockerfile b/r/redis-cluster-bv/Dockerfiles/8.4.1_ubi_9.7/Dockerfile new file mode 100644 index 0000000000..fc4c0b048f --- /dev/null +++ b/r/redis-cluster-bv/Dockerfiles/8.4.1_ubi_9.7/Dockerfile @@ -0,0 +1,269 @@ +# Copyright Broadcom, Inc. All Rights Reserved. +# SPDX-License-Identifier: APACHE-2.0 + +# Stage 1: Build utilities from source using secure Go version (resolves stdlib CVEs) +FROM registry.access.redhat.com/ubi9/ubi:9.7 AS builder +USER root +# Install build dependencies and a secure Go version (1.26.1) for ppc64le +ENV GO_VERSION="1.26.1" +RUN dnf update -y && dnf install -y git wget tar gcc && \ + wget -q https://golang.org/dl/go${GO_VERSION}.linux-ppc64le.tar.gz && \ + tar -C /usr/local -xzf go${GO_VERSION}.linux-ppc64le.tar.gz && \ + rm go${GO_VERSION}.linux-ppc64le.tar.gz + +ENV PATH="/usr/local/go/bin:$PATH" + +# Build wait-for-port utility from source +RUN mkdir -p /root/build && cd /root/build && \ + git clone https://github.com/bitnami/wait-for-port && \ + cd wait-for-port/ && \ + git checkout v1.0.10 && \ + go build -o wait-for-port . + +# Build gosu utility from source (to resolve stdlib CVEs in the pre-compiled binary) +RUN cd /root/build && \ + git clone https://github.com/tianon/gosu && \ + cd gosu && \ + git checkout 1.19 && \ + CGO_ENABLED=0 go build -o gosu . + +# Stage 2: Build Redis-cluster (aligned with Broadcom/Bitnami 8.4.1 specification) +FROM registry.access.redhat.com/ubi9/ubi:9.7 AS redisbuilder + +# Environmental variables for build consistency +ENV PACKAGE_VERSION="8.4.1" \ + BITNAMI_COMMIT_ID="8fe1092de5cf5664de9f8afc7764b51d69d4da86" \ + REDIS_URL="https://github.com/redis/redis" \ + BITNAMI_URL="https://github.com/bitnami/containers" + +# Install build dependencies +RUN dnf update -y && \ + dnf install -y git wget tar make which procps hostname gcc gcc-c++ openssl openssl-devel ncurses ncurses-devel libstdc++ libstdc++-devel \ + python3 jq tcl diffutils patch autoconf automake libtool cmake python3-devel rust cargo clang-devel llvm-devel && \ + # Explicitly update vulnerable builder packages + dnf update -y python3 openssh && \ + dnf clean all + +WORKDIR /root + +# Clone Bitnami repository for scripts and rootfs +RUN git clone ${BITNAMI_URL} redis-cluster && \ + cd redis-cluster && \ + git checkout ${BITNAMI_COMMIT_ID} + +# Clone and Patch Redis source code with P10 optimization +COPY redis-8.4.1-ppc64le-fixed.patch /tmp/ +RUN git clone ${REDIS_URL} redis && \ + cd redis && \ + git checkout ${PACKAGE_VERSION} && \ + git apply /tmp/redis-8.4.1-ppc64le-fixed.patch + + +# Fix modules/Makefile - Add ppc64le Rust support +RUN cd /root/redis && python3 << 'EOF' +content = open('modules/Makefile').read() +old = "\t\t\tfi ;; \\\n\t\t*) echo" +new = "\t\t\tfi ;; \\\n\t\t'ppc64le') \\\n\t\t\tRUST_INSTALLER=\"rust-$${RUST_VERSION}-powerpc64le-unknown-linux-gnu\"; \\\n\t\t\tRUST_SHA256=\"\"; \\\n\t\t\t;; \\\n\t\t*) echo" +assert old in content, "NO MATCH - modules/Makefile" +open('modules/Makefile', 'w').write(content.replace(old, new)) +print("OK") +EOF + +# Fix modules/common.mk - Add ppc64le arch map +RUN cd /root/redis && python3 << 'EOF' +content = open('modules/common.mk').read() +old = "ARCH_MAP_aarch64 := arm64v8\nARCH_MAP_arm64 := arm64v8" +new = "ARCH_MAP_aarch64 := arm64v8\nARCH_MAP_arm64 := arm64v8\nARCH_MAP_ppc64le := ppc64le" +assert old in content, "NO MATCH - common.mk" +open('modules/common.mk', 'w').write(content.replace(old, new)) +print("OK") +EOF + +# Ensure python3 is available in PATH for module builds (RedisJSON and RedisTimeSeries need it) +# Create symlinks and set up environment +RUN which python3 && python3 --version && \ + mkdir -p /usr/local/bin && \ + ln -sf /usr/bin/python3 /usr/local/bin/python3 && \ + ln -sf /usr/bin/python3 /usr/local/bin/python && \ + ln -sf /usr/bin/python3 /usr/bin/python && \ + which python3 && which python && \ + python3 --version && python --version + +# Final build with all fixes applied +RUN cd /root/redis && \ + EXTRA_CFLAGS="" && \ + if [[ $(uname -m) == "ppc64le" ]]; then \ + if grep -iq "POWER10" /proc/cpuinfo || lscpu | grep -iq "POWER10"; then \ + echo ">>> Power 10 CPU detected. Applying P10 optimization flags..." && \ + EXTRA_CFLAGS="-mcpu=power10 -mtune=power10"; \ + fi \ + fi && \ + export BUILD_WITH_MODULES=yes && \ + export DISABLE_WERRORS=yes && \ + export PATH="/usr/bin:/usr/local/bin:$PATH" && \ + export PYTHON3=/usr/bin/python3 && \ + export PYTHON=/usr/bin/python3 && \ + unset INSTALL_RUST_TOOLCHAIN && \ + which python3 && python3 --version && \ + python3 -c "import sys; print(sys.executable)" && \ + make MALLOC=libc -j "$(nproc)" all IGNORE_MISSING_DEPS=1 || true + +# Fix redisearch - Remove duplicate RS_FIELDMASK_ALL +RUN cd /root/redis && python3 << 'EOF' +path = 'modules/redisearch/src/src/redisearch_rs/ffi/src/lib.rs' +content = open(path).read() +old = "pub const RS_FIELDMASK_ALL: FieldMask = u128::MAX;\n" +assert old in content, "NO MATCH - ffi/src/lib.rs" +open(path, 'w').write(content.replace(old, "")) +print("OK") +EOF + +# Fix redisearch - FieldMask type in fields_only.rs +RUN cd /root/redis && python3 << 'EOF' +path = 'modules/redisearch/src/src/redisearch_rs/inverted_index/src/fields_only.rs' +content = open(path).read() +old = "let field_mask = u128::read_as_varint(cursor)?;" +new = "let field_mask = u64::read_as_varint(cursor)?;" +assert old in content, "NO MATCH - fields_only.rs" +open(path, 'w').write(content.replace(old, new)) +print("OK") +EOF + +# Fix redisearch - RS_FIELDMASK_ALL cast in index_result.rs +RUN cd /root/redis && python3 << 'EOF' +path = 'modules/redisearch/src/src/redisearch_rs/inverted_index/src/index_result.rs' +content = open(path).read() +count = content.count("field_mask: RS_FIELDMASK_ALL,") +assert count > 0, "NO MATCH - index_result.rs" +open(path, 'w').write(content.replace("field_mask: RS_FIELDMASK_ALL,", "field_mask: RS_FIELDMASK_ALL as t_fieldMask,")) +print(f"OK - Replaced {count} occurrences") +EOF + +# Fix VectorSimilarity - Add ppc64le CPU features support +RUN cd /root/redis && python3 << 'EOF' +path = 'modules/redisearch/src/deps/VectorSimilarity/src/VecSim/spaces/spaces.h' +content = open(path).read() +old = """#if defined(CPU_FEATURES_ARCH_AARCH64) + using FeaturesType = cpu_features::Aarch64Features; + constexpr auto getFeatures = cpu_features::GetAarch64Info; +#else + using FeaturesType = cpu_features::X86Features; // Fallback + constexpr auto getFeatures = cpu_features::GetX86Info; +#endif + return arch_opt ? *static_cast(arch_opt) : getFeatures().features;""" +new = """#if defined(CPU_FEATURES_ARCH_AARCH64) + using FeaturesType = cpu_features::Aarch64Features; + constexpr auto getFeatures = cpu_features::GetAarch64Info; + return arch_opt ? *static_cast(arch_opt) : getFeatures().features; +#elif defined(__powerpc64__) + struct EmptyFeatures {}; + return EmptyFeatures{}; +#else + using FeaturesType = cpu_features::X86Features; // Fallback + constexpr auto getFeatures = cpu_features::GetX86Info; + return arch_opt ? *static_cast(arch_opt) : getFeatures().features; +#endif""" +assert old in content, "NO MATCH - spaces.h" +open(path, 'w').write(content.replace(old, new)) +print("OK") +EOF + +# Final build with all fixes applied +RUN cd /root/redis && \ + EXTRA_CFLAGS="" && \ + if [[ $(uname -m) == "ppc64le" ]]; then \ + if grep -iq "POWER10" /proc/cpuinfo || lscpu | grep -iq "POWER10"; then \ + echo ">>> Power 10 CPU detected. Applying P10 optimization flags..." && \ + EXTRA_CFLAGS="-mcpu=power10 -mtune=power10"; \ + fi \ + fi && \ + export BUILD_WITH_MODULES=yes && \ + export DISABLE_WERRORS=yes && \ + export PATH="/usr/bin:/usr/local/bin:$PATH" && \ + export PYTHON3=/usr/bin/python3 && \ + export PYTHON=/usr/bin/python3 && \ + unset INSTALL_RUST_TOOLCHAIN && \ + which python3 && python3 --version && \ + python3 -c "import sys; print(sys.executable)" && \ + make MALLOC=libc -j "$(nproc)" all IGNORE_MISSING_DEPS=1 + +# Collect ONLY the compiled .so module files (not source/deps/build artifacts) +RUN mkdir -p /root/modules-output && \ + cp /root/redis/modules/redisbloom/redisbloom.so /root/modules-output/ && \ + cp /root/redis/modules/redisearch/redisearch.so /root/modules-output/ && \ + cp /root/redis/modules/redisjson/rejson.so /root/modules-output/ && \ + cp /root/redis/modules/redistimeseries/redistimeseries.so /root/modules-output/ && \ + ls -lh /root/modules-output/ + +# Prepare artifacts directory structure - copy only necessary runtime files +RUN mkdir -p /root/output/opt/bitnami/redis/bin /root/output/opt/bitnami/redis/etc /root/output/opt/bitnami/common/bin && \ + cp /root/redis/src/redis-server /root/output/opt/bitnami/redis/bin/ && \ + cp /root/redis/src/redis-cli /root/output/opt/bitnami/redis/bin/ && \ + cp /root/redis/src/redis-benchmark /root/output/opt/bitnami/redis/bin/ && \ + cp /root/redis/src/redis-check-aof /root/output/opt/bitnami/redis/bin/ && \ + cp /root/redis/src/redis-check-rdb /root/output/opt/bitnami/redis/bin/ && \ + cp /root/redis/redis.conf /root/output/opt/bitnami/redis/etc/redis-default.conf && \ + cp -r /root/redis-cluster/bitnami/redis-cluster/8.4/debian-12/rootfs/* /root/output/ && \ + cp -r /root/redis-cluster/bitnami/redis-cluster/8.4/debian-12/prebuildfs/* /root/output/ + +# Stage 3: Final Production Image (UBI 9.7) +FROM registry.access.redhat.com/ubi9/ubi:9.7 + +LABEL org.opencontainers.image.base.name="registry.access.redhat.com/ubi9/ubi:9.7" \ + org.opencontainers.image.created="2026-04-10T12:00:00Z" \ + org.opencontainers.image.description="Redis Cluster optimized for Power10 with Bitnami scripts" \ + org.opencontainers.image.documentation="https://github.com/bitnami/containers/tree/main/bitnami/redis-cluster/README.md" \ + org.opencontainers.image.source="https://github.com/bitnami/containers/tree/main/bitnami/redis-cluster" \ + org.opencontainers.image.title="redis-cluster-ppc64le" \ + org.opencontainers.image.vendor="Broadcom, Inc." \ + org.opencontainers.image.version="8.4.1" + +ENV HOME="/" \ + OS_ARCH="ppc64le" \ + OS_FLAVOUR="rhel-9" \ + OS_NAME="linux" \ + APP_VERSION="8.4.1" \ + BITNAMI_APP_NAME="redis-cluster" \ + IMAGE_REVISION="0" + +# Runtime dependencies for RHEL 9 +RUN dnf update -y && \ + dnf install -y --allowerasing ca-certificates curl wget gzip glibc openssl procps tar libgcc libgomp libstdc++ acl && \ + # Update all packages to resolve reported CVEs + dnf upgrade -y --allowerasing && \ + dnf clean all && \ + rm -rf /var/cache/dnf /var/tmp/* + +# Copy assembled Bitnami structure from builder +COPY --from=redisbuilder /root/output / + +# Copy utilities built from source in Stage 1 +COPY --from=builder /root/build/wait-for-port/wait-for-port /opt/bitnami/common/bin/wait-for-port +COPY --from=builder /root/build/gosu/gosu /opt/bitnami/common/bin/gosu + +# Copy ONLY the compiled .so module files (not entire modules directory with source/deps) +COPY --from=redisbuilder /root/modules-output/*.so /opt/bitnami/redis/modules/ + +# Configure Redis to automatically load modules in default config +RUN echo "" >> /opt/bitnami/redis/etc/redis-default.conf && \ + echo "# Load Redis modules automatically" >> /opt/bitnami/redis/etc/redis-default.conf && \ + echo "loadmodule /opt/bitnami/redis/modules/redisbloom.so" >> /opt/bitnami/redis/etc/redis-default.conf && \ + echo "loadmodule /opt/bitnami/redis/modules/redisearch.so" >> /opt/bitnami/redis/etc/redis-default.conf && \ + echo "loadmodule /opt/bitnami/redis/modules/rejson.so" >> /opt/bitnami/redis/etc/redis-default.conf && \ + echo "loadmodule /opt/bitnami/redis/modules/redistimeseries.so" >> /opt/bitnami/redis/etc/redis-default.conf + +# Permission and PATH configuration +RUN chmod +x /opt/bitnami/common/bin/gosu /opt/bitnami/common/bin/wait-for-port && \ + chmod g+rwX /opt/bitnami +ENV PATH="/opt/bitnami/common/bin:/opt/bitnami/redis/bin:$PATH" + +# Initialization scripts +RUN /opt/bitnami/scripts/redis-cluster/postunpack.sh && \ + ln -sf /opt/bitnami/scripts/redis-cluster/entrypoint.sh /entrypoint.sh && \ + ln -sf /opt/bitnami/scripts/redis-cluster/run.sh /run.sh + +EXPOSE 6379 + +USER 1001 +ENTRYPOINT [ "/opt/bitnami/scripts/redis-cluster/entrypoint.sh" ] +CMD [ "/opt/bitnami/scripts/redis-cluster/run.sh" ] diff --git a/r/redis-cluster-bv/Dockerfiles/8.4.1_ubi_9.7/README.md b/r/redis-cluster-bv/Dockerfiles/8.4.1_ubi_9.7/README.md new file mode 100644 index 0000000000..5dcf9e2398 --- /dev/null +++ b/r/redis-cluster-bv/Dockerfiles/8.4.1_ubi_9.7/README.md @@ -0,0 +1,262 @@ +### Build Command +```bash +docker build -t redis-cluster-ppc64le:8.4.1 -f Dockerfile.txt . +``` + +**Build Time:** Approximately 15-20 minutes (depending on system resources) + +### Verify Build +```bash +docker images | grep redis-cluster-ppc64le +``` + +**Expected Output:** +``` +REPOSITORY TAG IMAGE ID CREATED SIZE +redis-cluster-ppc64le 8.4.1 X minutes ago 445 MB +``` + +--- + + +#### Basic Run +```bash +docker run -d --name redis-standalone \ + -p 6379:6379 \ + -e ALLOW_EMPTY_PASSWORD=yes \ + redis-cluster-ppc64le:8.4.1 \ + redis-server --protected-mode no \ + --loadmodule /opt/bitnami/redis/modules/redisbloom.so \ + --loadmodule /opt/bitnami/redis/modules/redisearch.so \ + --loadmodule /opt/bitnami/redis/modules/rejson.so \ + --loadmodule /opt/bitnami/redis/modules/redistimeseries.so +``` + +#### With Password +```bash +docker run -d --name redis-standalone \ + -p 6379:6379 \ + -e REDIS_PASSWORD=mypassword \ + redis-cluster-ppc64le:8.4.1 \ + redis-server --protected-mode no --requirepass mypassword \ + --loadmodule /opt/bitnami/redis/modules/redisbloom.so \ + --loadmodule /opt/bitnami/redis/modules/redisearch.so \ + --loadmodule /opt/bitnami/redis/modules/rejson.so \ + --loadmodule /opt/bitnami/redis/modules/redistimeseries.so +``` + +## Interactive Shell Access + +```bash +docker exec -it redis-standalone bash +``` + +### 3. Stop and Remove Container + +```bash +docker stop redis-standalone +docker rm redis-standalone +``` + +--- + +## Verification + +### 1. Check Container Status +```bash +docker ps | grep redis-standalone +``` + +### 2. Check Redis Binaries +```bash +docker exec -it redis-standalone ls -lh /opt/bitnami/redis/bin/ +``` + +### 3. Verify Modules Present +```bash +docker exec -it redis-standalone ls -lh /opt/bitnami/redis/modules/ +``` + +**Expected Output:** +``` +total 26M +-rwxrwxr-x. 1 root root 646K redisbloom.so +-rwxrwxr-x. 1 root root 17M redisearch.so +-rwxrwxr-x. 1 root root 2.4M redistimeseries.so +-rwxrwxr-x. 1 root root 5.6M rejson.so +``` + +### 4. Test Redis Connection +```bash +docker exec -it redis-standalone redis-cli ping +``` + +**Expected Output:** +``` +PONG +``` + +### 5. Check Loaded Modules +```bash +docker exec -it redis-standalone redis-cli MODULE LIST +``` + +**Expected Output:** +``` +1) 1) "name" + 2) "bf" + 3) "ver" + 4) (integer) 80402 + ... +2) 1) "name" + 2) "search" + 3) "ver" + 4) (integer) 80405 + ... +3) 1) "name" + 2) "ReJSON" + 3) "ver" + 4) (integer) 80402 + ... +4) 1) "name" + 2) "timeseries" + 3) "ver" + 4) (integer) 80407 + ... +``` + +--- + +## Module Testing + +### RedisJSON Module + +#### Set JSON Data +```bash +docker exec -it redis-standalone redis-cli JSON.SET user:1 . '{"name":"John","age":30,"city":"New York"}' +``` + +**Expected Output:** `OK` + +#### Get JSON Data +```bash +docker exec -it redis-standalone redis-cli JSON.GET user:1 +``` + +**Expected Output:** `"{\"name\":\"John\",\"age\":30,\"city\":\"New York\"}"` + +#### Query JSON Field +```bash +docker exec -it redis-standalone redis-cli JSON.GET user:1 .name +``` + +**Expected Output:** `"\"John\""` + +--- + +### RedisBloom Module + +#### Create Bloom Filter +```bash +docker exec -it redis-standalone redis-cli BF.ADD emails user1@example.com +``` + +**Expected Output:** `(integer) 1` + +#### Check Item Exists +```bash +docker exec -it redis-standalone redis-cli BF.EXISTS emails user1@example.com +``` + +**Expected Output:** `(integer) 1` + +#### Check Non-existent Item +```bash +docker exec -it redis-standalone redis-cli BF.EXISTS emails user2@example.com +``` + +**Expected Output:** `(integer) 0` + +--- + +### RedisTimeSeries Module + +#### Create Time Series +```bash +docker exec -it redis-standalone redis-cli TS.CREATE temperature RETENTION 86400000 LABELS sensor_id 1 location room1 +``` + +**Expected Output:** `OK` + +#### Add Data Points +```bash +docker exec -it redis-standalone redis-cli TS.ADD temperature '*' 22.5 +docker exec -it redis-standalone redis-cli TS.ADD temperature '*' 23.0 +docker exec -it redis-standalone redis-cli TS.ADD temperature '*' 22.8 +``` + +**Expected Output:** `(integer) ` + +#### Query Time Series +```bash +docker exec -it redis-standalone redis-cli TS.RANGE temperature - + +``` + +**Expected Output:** +``` +1) 1) (integer) + 2) "22.5" +2) 1) (integer) + 2) "23" +3) 1) (integer) + 2) "22.8" +``` + +--- + +### RedisSearch Module + +#### Create Index +```bash +docker exec -it redis-standalone redis-cli FT.CREATE products ON HASH PREFIX 1 product: SCHEMA name TEXT SORTABLE price NUMERIC SORTABLE category TAG +``` + +**Expected Output:** `OK` + +#### Add Products +```bash +docker exec -it redis-standalone redis-cli HSET product:1 name "Laptop" price 999 category "Electronics" +docker exec -it redis-standalone redis-cli HSET product:2 name "Mouse" price 25 category "Electronics" +docker exec -it redis-standalone redis-cli HSET product:3 name "Desk" price 299 category "Furniture" +``` + +**Expected Output:** `(integer) 3` + +#### Search Products +```bash +docker exec -it redis-standalone redis-cli FT.SEARCH products "Electronics" RETURN 2 name price +``` + +**Expected Output:** +``` +1) (integer) 2 +2) "product:1" +3) 1) "name" + 2) "Laptop" + 3) "price" + 4) "999" +4) "product:2" +5) 1) "name" + 2) "Mouse" + 3) "price" + 4) "25" +``` + +#### Search with Filter +```bash +docker exec -it redis-standalone redis-cli FT.SEARCH products "@category:{Electronics} @price:[0 100]" +``` + +**Expected Output:** Returns products in Electronics category with price ≤ 100 + +--- diff --git a/r/redis-cluster-bv/LICENSE b/r/redis-cluster-bv/LICENSE new file mode 100644 index 0000000000..8dada3edaf --- /dev/null +++ b/r/redis-cluster-bv/LICENSE @@ -0,0 +1,201 @@ + Apache License + Version 2.0, January 2004 + http://www.apache.org/licenses/ + + TERMS AND CONDITIONS FOR USE, REPRODUCTION, AND DISTRIBUTION + + 1. Definitions. + + "License" shall mean the terms and conditions for use, reproduction, + and distribution as defined by Sections 1 through 9 of this document. + + "Licensor" shall mean the copyright owner or entity authorized by + the copyright owner that is granting the License. + + "Legal Entity" shall mean the union of the acting entity and all + other entities that control, are controlled by, or are under common + control with that entity. For the purposes of this definition, + "control" means (i) the power, direct or indirect, to cause the + direction or management of such entity, whether by contract or + otherwise, or (ii) ownership of fifty percent (50%) or more of the + outstanding shares, or (iii) beneficial ownership of such entity. + + "You" (or "Your") shall mean an individual or Legal Entity + exercising permissions granted by this License. + + "Source" form shall mean the preferred form for making modifications, + including but not limited to software source code, documentation + source, and configuration files. + + "Object" form shall mean any form resulting from mechanical + transformation or translation of a Source form, including but + not limited to compiled object code, generated documentation, + and conversions to other media types. + + "Work" shall mean the work of authorship, whether in Source or + Object form, made available under the License, as indicated by a + copyright notice that is included in or attached to the work + (an example is provided in the Appendix below). + + "Derivative Works" shall mean any work, whether in Source or Object + form, that is based on (or derived from) the Work and for which the + editorial revisions, annotations, elaborations, or other modifications + represent, as a whole, an original work of authorship. For the purposes + of this License, Derivative Works shall not include works that remain + separable from, or merely link (or bind by name) to the interfaces of, + the Work and Derivative Works thereof. + + "Contribution" shall mean any work of authorship, including + the original version of the Work and any modifications or additions + to that Work or Derivative Works thereof, that is intentionally + submitted to Licensor for inclusion in the Work by the copyright owner + or by an individual or Legal Entity authorized to submit on behalf of + the copyright owner. For the purposes of this definition, "submitted" + means any form of electronic, verbal, or written communication sent + to the Licensor or its representatives, including but not limited to + communication on electronic mailing lists, source code control systems, + and issue tracking systems that are managed by, or on behalf of, the + Licensor for the purpose of discussing and improving the Work, but + excluding communication that is conspicuously marked or otherwise + designated in writing by the copyright owner as "Not a Contribution." + + "Contributor" shall mean Licensor and any individual or Legal Entity + on behalf of whom a Contribution has been received by Licensor and + subsequently incorporated within the Work. + + 2. Grant of Copyright License. Subject to the terms and conditions of + this License, each Contributor hereby grants to You a perpetual, + worldwide, non-exclusive, no-charge, royalty-free, irrevocable + copyright license to reproduce, prepare Derivative Works of, + publicly display, publicly perform, sublicense, and distribute the + Work and such Derivative Works in Source or Object form. + + 3. Grant of Patent License. Subject to the terms and conditions of + this License, each Contributor hereby grants to You a perpetual, + worldwide, non-exclusive, no-charge, royalty-free, irrevocable + (except as stated in this section) patent license to make, have made, + use, offer to sell, sell, import, and otherwise transfer the Work, + where such license applies only to those patent claims licensable + by such Contributor that are necessarily infringed by their + Contribution(s) alone or by combination of their Contribution(s) + with the Work to which such Contribution(s) was submitted. If You + institute patent litigation against any entity (including a + cross-claim or counterclaim in a lawsuit) alleging that the Work + or a Contribution incorporated within the Work constitutes direct + or contributory patent infringement, then any patent licenses + granted to You under this License for that Work shall terminate + as of the date such litigation is filed. + + 4. Redistribution. You may reproduce and distribute copies of the + Work or Derivative Works thereof in any medium, with or without + modifications, and in Source or Object form, provided that You + meet the following conditions: + + (a) You must give any other recipients of the Work or + Derivative Works a copy of this License; and + + (b) You must cause any modified files to carry prominent notices + stating that You changed the files; and + + (c) You must retain, in the Source form of any Derivative Works + that You distribute, all copyright, patent, trademark, and + attribution notices from the Source form of the Work, + excluding those notices that do not pertain to any part of + the Derivative Works; and + + (d) If the Work includes a "NOTICE" text file as part of its + distribution, then any Derivative Works that You distribute must + include a readable copy of the attribution notices contained + within such NOTICE file, excluding those notices that do not + pertain to any part of the Derivative Works, in at least one + of the following places: within a NOTICE text file distributed + as part of the Derivative Works; within the Source form or + documentation, if provided along with the Derivative Works; or, + within a display generated by the Derivative Works, if and + wherever such third-party notices normally appear. The contents + of the NOTICE file are for informational purposes only and + do not modify the License. You may add Your own attribution + notices within Derivative Works that You distribute, alongside + or as an addendum to the NOTICE text from the Work, provided + that such additional attribution notices cannot be construed + as modifying the License. + + You may add Your own copyright statement to Your modifications and + may provide additional or different license terms and conditions + for use, reproduction, or distribution of Your modifications, or + for any such Derivative Works as a whole, provided Your use, + reproduction, and distribution of the Work otherwise complies with + the conditions stated in this License. + + 5. Submission of Contributions. Unless You explicitly state otherwise, + any Contribution intentionally submitted for inclusion in the Work + by You to the Licensor shall be under the terms and conditions of + this License, without any additional terms or conditions. + Notwithstanding the above, nothing herein shall supersede or modify + the terms of any separate license agreement you may have executed + with Licensor regarding such Contributions. + + 6. Trademarks. This License does not grant permission to use the trade + names, trademarks, service marks, or product names of the Licensor, + except as required for reasonable and customary use in describing the + origin of the Work and reproducing the content of the NOTICE file. + + 7. Disclaimer of Warranty. Unless required by applicable law or + agreed to in writing, Licensor provides the Work (and each + Contributor provides its Contributions) on an "AS IS" BASIS, + WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or + implied, including, without limitation, any warranties or conditions + of TITLE, NON-INFRINGEMENT, MERCHANTABILITY, or FITNESS FOR A + PARTICULAR PURPOSE. You are solely responsible for determining the + appropriateness of using or redistributing the Work and assume any + risks associated with Your exercise of permissions under this License. + + 8. Limitation of Liability. In no event and under no legal theory, + whether in tort (including negligence), contract, or otherwise, + unless required by applicable law (such as deliberate and grossly + negligent acts) or agreed to in writing, shall any Contributor be + liable to You for damages, including any direct, indirect, special, + incidental, or consequential damages of any character arising as a + result of this License or out of the use or inability to use the + Work (including but not limited to damages for loss of goodwill, + work stoppage, computer failure or malfunction, or any and all + other commercial damages or losses), even if such Contributor + has been advised of the possibility of such damages. + + 9. Accepting Warranty or Additional Liability. While redistributing + the Work or Derivative Works thereof, You may choose to offer, + and charge a fee for, acceptance of support, warranty, indemnity, + or other liability obligations and/or rights consistent with this + License. However, in accepting such obligations, You may act only + on Your own behalf and on Your sole responsibility, not on behalf + of any other Contributor, and only if You agree to indemnify, + defend, and hold each Contributor harmless for any liability + incurred by, or claims asserted against, such Contributor by reason + of your accepting any such warranty or additional liability. + + END OF TERMS AND CONDITIONS + + APPENDIX: How to apply the Apache License to your work. + + To apply the Apache License to your work, attach the following + boilerplate notice, with the fields enclosed by brackets "{}" + replaced with your own identifying information. (Don't include + the brackets!) The text should be enclosed in the appropriate + comment syntax for the file format. We also recommend that a + file or class name and description of purpose be included on the + same "printed page" as the copyright notice for easier + identification within third-party archives. + + Copyright {yyyy} {name of copyright owner} + + Licensed under the Apache License, Version 2.0 (the "License"); + you may not use this file except in compliance with the License. + You may obtain a copy of the License at + + http://www.apache.org/licenses/LICENSE-2.0 + + Unless required by applicable law or agreed to in writing, software + distributed under the License is distributed on an "AS IS" BASIS, + WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + See the License for the specific language governing permissions and + limitations under the License. diff --git a/r/redis-cluster-bv/redis-8.4.1-ppc64le-debug.patch b/r/redis-cluster-bv/redis-8.4.1-ppc64le-debug.patch new file mode 100644 index 0000000000..6ecc16b5d4 --- /dev/null +++ b/r/redis-cluster-bv/redis-8.4.1-ppc64le-debug.patch @@ -0,0 +1,64 @@ +diff --git a/src/debug.c b/src/debug.c +index c1f9ea186..d7b6143a2 100644 +--- a/src/debug.c ++++ b/src/debug.c +@@ -1720,6 +1720,59 @@ void logRegisters(ucontext_t *uc) { + (unsigned long) uc->uc_mcontext.fault_address + ); + logStackContent((void**)uc->uc_mcontext.arm_sp); ++ #elif defined(__powerpc64__) /* Linux ppc64le */ ++ serverLog(LL_WARNING, ++ "\n" ++ "NIP :%016lx MSR :%016lx CTR :%016lx\n" ++ "LR :%016lx XER :%016lx CCR :%016lx\n" ++ "R0 :%016lx R1 :%016lx R2 :%016lx R3 :%016lx\n" ++ "R4 :%016lx R5 :%016lx R6 :%016lx R7 :%016lx\n" ++ "R8 :%016lx R9 :%016lx R10 :%016lx R11 :%016lx\n" ++ "R12 :%016lx R13 :%016lx R14 :%016lx R15 :%016lx\n" ++ "R16 :%016lx R17 :%016lx R18 :%016lx R19 :%016lx\n" ++ "R20 :%016lx R21 :%016lx R22 :%016lx R23 :%016lx\n" ++ "R24 :%016lx R25 :%016lx R26 :%016lx R27 :%016lx\n" ++ "R28 :%016lx R29 :%016lx R30 :%016lx R31 :%016lx\n", ++ (unsigned long) uc->uc_mcontext.gp_regs[32], /* NIP */ ++ (unsigned long) uc->uc_mcontext.gp_regs[33], /* MSR */ ++ (unsigned long) uc->uc_mcontext.gp_regs[35], /* CTR */ ++ (unsigned long) uc->uc_mcontext.gp_regs[36], /* LR */ ++ (unsigned long) uc->uc_mcontext.gp_regs[37], /* XER */ ++ (unsigned long) uc->uc_mcontext.gp_regs[38], /* CCR */ ++ (unsigned long) uc->uc_mcontext.gp_regs[0], ++ (unsigned long) uc->uc_mcontext.gp_regs[1], ++ (unsigned long) uc->uc_mcontext.gp_regs[2], ++ (unsigned long) uc->uc_mcontext.gp_regs[3], ++ (unsigned long) uc->uc_mcontext.gp_regs[4], ++ (unsigned long) uc->uc_mcontext.gp_regs[5], ++ (unsigned long) uc->uc_mcontext.gp_regs[6], ++ (unsigned long) uc->uc_mcontext.gp_regs[7], ++ (unsigned long) uc->uc_mcontext.gp_regs[8], ++ (unsigned long) uc->uc_mcontext.gp_regs[9], ++ (unsigned long) uc->uc_mcontext.gp_regs[10], ++ (unsigned long) uc->uc_mcontext.gp_regs[11], ++ (unsigned long) uc->uc_mcontext.gp_regs[12], ++ (unsigned long) uc->uc_mcontext.gp_regs[13], ++ (unsigned long) uc->uc_mcontext.gp_regs[14], ++ (unsigned long) uc->uc_mcontext.gp_regs[15], ++ (unsigned long) uc->uc_mcontext.gp_regs[16], ++ (unsigned long) uc->uc_mcontext.gp_regs[17], ++ (unsigned long) uc->uc_mcontext.gp_regs[18], ++ (unsigned long) uc->uc_mcontext.gp_regs[19], ++ (unsigned long) uc->uc_mcontext.gp_regs[20], ++ (unsigned long) uc->uc_mcontext.gp_regs[21], ++ (unsigned long) uc->uc_mcontext.gp_regs[22], ++ (unsigned long) uc->uc_mcontext.gp_regs[23], ++ (unsigned long) uc->uc_mcontext.gp_regs[24], ++ (unsigned long) uc->uc_mcontext.gp_regs[25], ++ (unsigned long) uc->uc_mcontext.gp_regs[26], ++ (unsigned long) uc->uc_mcontext.gp_regs[27], ++ (unsigned long) uc->uc_mcontext.gp_regs[28], ++ (unsigned long) uc->uc_mcontext.gp_regs[29], ++ (unsigned long) uc->uc_mcontext.gp_regs[30], ++ (unsigned long) uc->uc_mcontext.gp_regs[31] ++ ); ++ logStackContent((void **)uc->uc_mcontext.gp_regs[1]); /* R1 = stack pointer */ + #else + NOT_SUPPORTED(); + #endif diff --git a/r/redis-cluster-bv/redis-8.4.1-ppc64le-util.patch b/r/redis-cluster-bv/redis-8.4.1-ppc64le-util.patch new file mode 100644 index 0000000000..9398ea03bb --- /dev/null +++ b/r/redis-cluster-bv/redis-8.4.1-ppc64le-util.patch @@ -0,0 +1,15 @@ +diff --git a/tests/support/util.tcl b/tests/support/util.tcl +index 9a27139a7..e6b16139f 100644 +--- a/tests/support/util.tcl ++++ b/tests/support/util.tcl +@@ -1234,6 +1234,10 @@ proc system_backtrace_supported {} { + } elseif {$system_name ne {linux}} { + return 0 + } ++ # ppc64le backtrace() does not reliably capture full stack traces ++ if {[exec uname -m] eq {ppc64le}} { ++ return 0 ++ } + + # libmusl does not support backtrace. Also return 0 on + # static binaries (ldd exit code 1) where we can't detect libmusl diff --git a/r/redis-cluster-bv/redis-cluster_v8.4.1_ubi_9.7.sh b/r/redis-cluster-bv/redis-cluster_v8.4.1_ubi_9.7.sh new file mode 100644 index 0000000000..24e2c049d5 --- /dev/null +++ b/r/redis-cluster-bv/redis-cluster_v8.4.1_ubi_9.7.sh @@ -0,0 +1,121 @@ +#!/bin/bash -e + +# ----------------------------------------------------------------------------- +# Package : redis-cluster +# Version : 8.4.1 +# Source repo : https://github.com/bitnami/containers +# Tested on : UBI:9.7 +# Ci-Check : True +# Language : C +# Script License: Apache License, Version 2 or later +# Maintainer : Amit Kumar +# +# Disclaimer : This script has been tested in root mode on given +# ========== platform using the mentioned version of the package. +# It may not work as expected with newer versions of the +# package and/or distribution. In such case, please +# contact "Maintainer" of this script. +# ----------------------------------------------------------------------------- + +PACKAGE_NAME=redis-cluster +PACKAGE_VERSION=${1:-8.4.1} +PACKAGE_URL=https://github.com/bitnami/containers +COMMIT_ID=8fe1092de5cf5664de9f8afc7764b51d69d4da86 +SCRIPT_PACKAGE_VERSION=$PACKAGE_VERSION +SCRIPT_PATH=$(dirname $(realpath $0)) + +# 1. Install OS Dependencies +dnf update -y +dnf install -y git wget tar make which procps hostname gcc gcc-c++ openssl openssl-devel ncurses ncurses-devel libstdc++ libstdc++-devel \ +python3 jq tcl diffutils patch + +# 2. Clone repository +if [ -d "$PACKAGE_NAME" ]; then +echo ">>> Removing existing directory $PACKAGE_NAME..." +rm -rf "$PACKAGE_NAME" +fi + +git clone $PACKAGE_URL $PACKAGE_NAME +cd $PACKAGE_NAME +git checkout $COMMIT_ID + +BITNAMI_DIR=$(pwd)/bitnami/redis-cluster/8.4/debian-12 + +# 3. Build Redis from source +echo ">>> Building Redis from source..." +cd $SCRIPT_PATH +REDIS_PACKAGE_NAME=redis +REDIS_PACKAGE_URL=https://github.com/redis/redis +PATCH_FILE_DEBUG=redis-8.4.1-ppc64le-debug.patch +PATCH_FILE_UTIL=redis-8.4.1-ppc64le-util.patch + +# Clone repository +if [ -d "$REDIS_PACKAGE_NAME" ]; then + rm -rf "$REDIS_PACKAGE_NAME" +fi + +if ! git clone $REDIS_PACKAGE_URL $REDIS_PACKAGE_NAME; then + echo ">>> ERROR: Failed to clone Redis repository." + exit 1 +fi + +cd $REDIS_PACKAGE_NAME + +# Checkout specific version +git checkout $PACKAGE_VERSION + +# Apply architecture-specific patches +echo ">>> Applying ppc64le patches..." + +if [ -f "$SCRIPT_PATH/$PATCH_FILE_DEBUG" ]; then + echo ">>> Applying debug.c patch: $PATCH_FILE_DEBUG" + if ! patch -p1 --fuzz=3 --ignore-whitespace < "$SCRIPT_PATH/$PATCH_FILE_DEBUG"; then + echo ">>> ERROR: Failed to apply debug.c patch." + exit 1 + fi +else + echo ">>> ERROR: Patch file $PATCH_FILE_DEBUG not found in $SCRIPT_PATH." + exit 1 +fi + +if [ -f "$SCRIPT_PATH/$PATCH_FILE_UTIL" ]; then + echo ">>> Applying util.tcl patch: $PATCH_FILE_UTIL" + if ! patch -p1 --fuzz=3 --ignore-whitespace < "$SCRIPT_PATH/$PATCH_FILE_UTIL"; then + echo ">>> ERROR: Failed to apply util.tcl patch." + exit 1 + fi +else + echo ">>> ERROR: Patch file $PATCH_FILE_UTIL not found in $SCRIPT_PATH." + exit 1 +fi + +echo ">>> All patches applied successfully." + +# Detect Power 10 and apply optimization flags +EXTRA_CFLAGS="" +if [[ $(uname -m) == "ppc64le" ]]; then + if grep -iq "POWER10" /proc/cpuinfo || lscpu | grep -iq "POWER10"; then + echo ">>> Power 10 CPU detected. Applying P10 optimization flags..." + EXTRA_CFLAGS="-mcpu=power10 -mtune=power10" + fi +fi + +# Build Redis +if ! make MALLOC=libc EXTRA_CFLAGS="$EXTRA_CFLAGS" -j$(nproc); then + echo ">>> ERROR: Redis build failed." + exit 1 +fi + +make install + +# 4. Run Redis Test Suite +echo ">>> Running Redis test suite..." +if ! make test MALLOC=libc EXTRA_CFLAGS="$EXTRA_CFLAGS"; then + echo ">>> FAIL: Redis tests failed ..." + exit 2 +fi + +echo "========================================================================" +echo " SUCCESS: $PACKAGE_NAME version $PACKAGE_VERSION built and tested successfully." +echo "========================================================================" +exit 0