diff --git a/.github/actions/shared-steps/action.yml b/.github/actions/shared-steps/action.yml index e1748765..43f8abb2 100644 --- a/.github/actions/shared-steps/action.yml +++ b/.github/actions/shared-steps/action.yml @@ -41,6 +41,11 @@ inputs: runs: using: "composite" steps: + - uses: runs-on/action@v2 + # only when in runs-on environment + if: env.RUNS_ON_VERSION != '' + with: + metrics: cpu,network,memory,disk,io - name: Runner OS, install extra packages shell: bash @@ -73,14 +78,15 @@ runs: echo "version_major=${version_major}" >> $GITHUB_ENV echo "alma_arch=${alma_arch}" >> $GITHUB_ENV - - name: Prepare staff + - name: Prepare stuff shell: bash run: | - # Prepare staff + # Prepare stuff + packer_opts= case ${{ env.runner_os }} in ubuntu) # Packer options - packer_opts="-var ovmf_code=/usr/share/OVMF/OVMF_CODE_4M.fd -var ovmf_vars=/usr/share/OVMF/OVMF_VARS_4M.fd" + packer_opts="-var qemu_binary=/usr/bin/qemu-system-${{ inputs.arch }} -var ovmf_code=/usr/share/OVMF/OVMF_CODE_4M.fd -var ovmf_vars=/usr/share/OVMF/OVMF_VARS_4M.fd" ;; rhel) # Packer options @@ -114,6 +120,10 @@ runs: # AWS S3 path to store images aws_s3_path=images/${{ env.version_major }}/${release}/${{ inputs.type }}/${{ env.TIME_STAMP }} + # tell packer we can use more cpu/ram if we're using runs-on + # which means we're using runs-on with metal instances + [[ ${{ env.RUNS_ON_VERSION }} != '' ]] && packer_opts="${packer_opts} -var cpus=$(($(nproc)-4)) -var memory_${{ env.alma_arch }}=32768" + # Overriding packer source, image mask and S3 path where necessary case "${{ inputs.type }}${{ env.version_major }}" in azure8|azure9) @@ -228,6 +238,17 @@ runs: output_mask=output-${packer_source}/AlmaLinux-*.${{ env.alma_arch }}*.qcow2 packer_source=qemu.${packer_source} ;; + gcp8|gcp9) + output_mask=output-${packer_source}/AlmaLinux-*${version_major}*.${{ env.alma_arch }}.tar.gz + packer_source=qemu.${packer_source} + ;; + gcp10) + packer_source=almalinux_${{ env.version_major }}_${{ inputs.type }}_${{ env.alma_arch }} + [[ ${{ env.version_major }} == *"v2"* ]] && packer_source="${packer_source}_v2" + [[ ${{ inputs.variant }} == *"64k"* ]] && packer_source="almalinux_${{ env.version_major }}_${{ inputs.type }}_64k_${{ env.alma_arch }}" + output_mask=output-${packer_source}/AlmaLinux-*${version_major}*.${{ env.alma_arch }}.tar.gz + packer_source=qemu.${packer_source} + ;; *) output_mask=output-${output_mask} packer_source=qemu.${packer_source} @@ -260,8 +281,24 @@ runs: ;; esac + - name: Remove KVM + if: inputs.type == 'vagrant_virtualbox' || inputs.type == 'vagrant_vmware' + shell: bash + run: | + # Remove KVM + case ${{ env.runner_os }} in + ubuntu) + sudo apt-get -y remove qemu-kvm + ;; + rhel) + sudo dnf -y -q remove qemu-kvm + ;; + esac + sudo rmmod kvm_amd || sudo rmmod kvm_intel || true + sudo rmmod kvm || true + - name: Check nested virtualization support - if: inputs.arch == 'x86_64' && inputs.type != 'vagrant_virtualbox' && inputs.type != 'vagrant_vmware' && inputs.runner != 'aws-ec2' + if: inputs.arch == 'x86_64' && env.RUNS_ON_VERSION == '' && inputs.type != 'vagrant_virtualbox' && inputs.type != 'vagrant_vmware' shell: bash run: | # Check nested virtualization support @@ -356,6 +393,25 @@ runs: # Install ansible sudo ${{ env.runner_os == 'ubuntu' && 'apt-get' || 'dnf -q' }} -y install ansible + - name: Clone SBOM tools + shell: bash + run: | + rm -rf sbom-tools + git clone --depth=1 https://github.com/AlmaLinux/cloud-images-sbom-tools.git sbom-tools + + - name: Set up Python and install generator deps + uses: actions/setup-python@v5 + with: + python-version: '3.11' + cache: 'pip' + cache-dependency-path: sbom-tools/requirements.txt + + - name: Create venv and install + shell: bash + run: | + python -m venv .venv-sbom + .venv-sbom/bin/pip install -r sbom-tools/requirements.txt + - name: Initialize packer shell: bash run: sudo /usr/bin/packer init -upgrade . @@ -365,12 +421,13 @@ runs: run: | # Build ${{ inputs.type }} image # PACKER_LOG=1 + sudo systemctl start libvirtd sudo sh -c "/usr/bin/packer build ${{ env.PACKER_OPTS }} -only=${{ env.packer_source }} ." - name: Locate image file, generate checksum shell: bash run: | - # Locate image file, generate checksum + # Locate image file, generate checksum, rename repo metadata file ls -la $(dirname '${{ env.output_mask }}') image_file=$(ls -1 ${{ env.output_mask }} | head -n 1) [ "x${image_file}" = "x" ] && false @@ -380,8 +437,85 @@ runs: echo "IMAGE_FILE=${image_file}" >> $GITHUB_ENV echo "IMAGE_NAME=$(basename ${image_file})" >> $GITHUB_ENV - # - name: Setup tmate session - # uses: mxschmitt/action-tmate@v3 + # don't fail if this doesn't exist, we may not always generate it + sudo mv sbom-data-*.json $(basename ${image_file}).sbom-data.json || true + + - id: 'google-auth-dev-images' + if: env.IMAGE_TYPE == 'gcp' + uses: 'google-github-actions/auth@v2' + with: + workload_identity_provider: 'projects/443728870479/locations/global/workloadIdentityPools/github-actions/providers/github' + service_account: 'github-actions-cloud-images@almalinux-dev-images-469421.iam.gserviceaccount.com' + + - name: 'Set up Google Cloud SDK' + if: env.IMAGE_TYPE == 'gcp' + uses: 'google-github-actions/setup-gcloud@v3.0.0' + + - name: 'Upload output to GCP storage bucket' + if: env.IMAGE_TYPE == 'gcp' + shell: bash + run: gcloud storage cp ${{ env.IMAGE_FILE }} gs://almalinux-images-dev/almalinux-${version_major}${{ inputs.arch == 'aarch64' && '-arm64' || '' }}-v$(date +'%Y%m%d')/root.tar.gz + + - name: Clone gce_image_publish repo + if: env.IMAGE_TYPE == 'gcp' + uses: actions/checkout@v5 + with: + path: compute-image-tools + repository: GoogleCloudPlatform/compute-image-tools + ref: "20250916.00" + + - name: Build gce_image_publish tool + if: env.IMAGE_TYPE == 'gcp' + shell: bash + run: | + # we need golang + case ${{ env.runner_os }} in + ubuntu) + sudo apt update + sudo apt-get -y install golang-go + ;; + rhel) + sudo dnf -y -q install golang + ;; + esac + # print golang version for reference + go version + # Build gce_image_publish tool + cd compute-image-tools/cli_tools/gce_image_publish + go mod tidy + go install + + - name: Create test image on GCP + if: env.IMAGE_TYPE == 'gcp' + shell: bash + run: | + /home/$USER/go/bin/gce_image_publish \ + -var:environment=test \ + -skip_confirmation \ + -rollout_rate=0 \ + -publish_project="almalinux-dev-images-469421" \ + -work_project="almalinux-dev-images-469421" \ + -replace \ + -source_gcs_path="gs://almalinux-images-dev/" \ + vm-scripts/gcp/almalinux_${version_major}${{ inputs.arch == 'aarch64' && '_arm64' || '' }}.publish.json + + # - name: 'Run Google cloud-image-testing tests (basic suite)' + # if: env.IMAGE_TYPE == 'gcp' && inputs.run_test == 'true' + # shell: bash + # run: | + # cd cloud-image-tests + # ./bin/manager \ + # -local_path bin \ + # -project almalinux-image-testing-469421 \ + # -filter '^(cvm|livemigrate|suspendresume|loadbalancer|guestagent|hostnamevalidation|imageboot|licensevalidation|network|security|hotattach|lssd|disk|packagevalidation|ssh|metadata|vmspec)$' \ + # -images 'projects/almalinux-dev-images-469421/global/images/family/almalinux-${{ env.version_major }}${{ inputs.arch == 'aarch64' && '-arm64' || '' }}' \ + # -parallel_stagger 10s -parallel_count 20 + + - name: Generate SBOM + shell: bash + run: | + echo "Generating SBOM document of ${{ env.IMAGE_FILE }}" + sudo .venv-sbom/bin/python3 sbom-tools/sbom_generator.py "${{ env.IMAGE_NAME }}" "${{ env.IMAGE_FILE }}.sbom-data.json" "${{ env.IMAGE_FILE }}.sbom.spdx.json" - name: Test ${{ inputs.type }} ${{ inputs.variant }} image # Skip testing for vagrant_virtualbox on GH runner because 'vugrant up' fails to connect to the newly created VM via ssh: @@ -474,6 +608,24 @@ runs: name: ${{ env.IMAGE_NAME }} path: ${{ env.IMAGE_FILE }} + - uses: actions/upload-artifact@v4 + name: Store collected sbom data as artifact + id: sbom-data-artifact + if: inputs.store_as_artifact == 'true' + with: + compression-level: 9 + name: ${{ env.IMAGE_NAME }}.sbom-data.json + path: ${{ env.IMAGE_FILE }}.sbom-data.json + + - uses: actions/upload-artifact@v4 + name: Store SBOM as artifact + id: sbom-artifact + if: inputs.store_as_artifact == 'true' + with: + compression-level: 9 + name: ${{ env.IMAGE_NAME }}.sbom.spdx.json + path: ${{ env.IMAGE_FILE }}.sbom.spdx.json + - uses: actions/upload-artifact@v4 name: Store checksum as artifact id: checksum-artifact @@ -488,7 +640,7 @@ runs: id: pkglist-artifact if: inputs.store_as_artifact == 'true' && env.got_pkgs_list == 'true' with: - compression-level: 1 + compression-level: 9 name: ${{ env.IMAGE_NAME }}.txt path: ${{ env.IMAGE_FILE }}.txt diff --git a/.github/workflows/build.yml b/.github/workflows/build.yml index 59601b5f..9e1d53cc 100644 --- a/.github/workflows/build.yml +++ b/.github/workflows/build.yml @@ -30,6 +30,7 @@ on: - ALL - azure # - digitalocean # TODO: require data to work with the cloud, such as: bucket, access key, secret key, etc. + - gcp - gencloud - oci - opennebula @@ -114,6 +115,10 @@ jobs: VARIANTS_GH+=("azure-x86_64") VARIANTS_SH+=("azure-aarch64") fi + if [ "${{ inputs.image_type }}" = "gcp" -o "${{ inputs.image_type }}" = "ALL" ]; then + VARIANTS_GH+=("gcp-x86_64") + VARIANTS_SH+=("gcp-aarch64") + fi if [ "${{ inputs.image_type }}" = "digitalocean" -o "${{ inputs.image_type }}" = "ALL" ]; then if [[ "${{ inputs.version_major }}" != *"kitten"* ]] && [[ "${{ inputs.version_major }}" != *"10" ]]; then VARIANTS_GH+=("digitalocean-x86_64") @@ -145,6 +150,14 @@ jobs: VARIANTS_SH+=("vagrant_vmware-x86_64") # VMware has networking issues on GitHub runners, so we use self-hosted runner fi + # Add SH values to matrix_gh if using runs-on + if [ "${{ github.repository_owner }}" == 'AlmaLinux' ]; then + for sh in "${VARIANTS_SH[@]}"; do + VARIANTS_GH+=("$sh") + done + unset VARIANTS_SH + fi + [ ${#VARIANTS_GH[@]} -ne 0 ] && matrix_gh=$(printf '"%s",' "${VARIANTS_GH[@]}") matrix_gh=${matrix_gh%,} # Remove the trailing comma echo matrix_gh=$(jq -c <<< [${matrix_gh}]) >> $GITHUB_OUTPUT @@ -173,19 +186,25 @@ jobs: build-gh-hosted: name: ${{ matrix.variant }} ${{ matrix.matrix_gh }} image + permissions: + id-token: write + contents: read needs: [init-data] if: ${{ needs.init-data.outputs.matrix_gh != '[]' }} - runs-on: ubuntu-24.04 + # use runs-on runners if within the almalinux org, otherwise GH runners" + runs-on: "${{ github.repository_owner == 'AlmaLinux' && format('runs-on={0}/family=c7i.metal-24xl+c7a.metal-48xl+*8gd.metal*/image=ubuntu24-full-{2}', github.run_id, matrix.variant, contains(matrix.matrix_gh, 'aarch64') && 'arm64' || 'x64') || 'ubuntu-24.04' }}" strategy: fail-fast: false matrix: - variant: ${{ fromJSON(format('["{0}"]', ( inputs.version_major == '10-kitten' || inputs.version_major == '10' ) && format('{0}", "{0}-v2', inputs.version_major) || inputs.version_major )) }} + variant: ${{ fromJSON(format('["{0}"]', ( (inputs.version_major == '10-kitten' || inputs.version_major == '10') && !(contains(needs.init-data.outputs.matrix_gh, 'aarch64') ) ) && format('{0}", "{0}-v2', inputs.version_major) || inputs.version_major )) }} matrix_gh: ${{ fromJSON(needs.init-data.outputs.matrix_gh) }} exclude: - matrix_gh: 'azure-x86_64' variant: '10-kitten-v2' - matrix_gh: 'oci-x86_64' variant: '10-kitten-v2' + - matrix_gh: 'gcp-x86_64' + variant: '10-kitten-v2' # Kitten x86_64_v2 Vagrant for VirtualBox stuck on "Waiting for SSH to become available" - matrix_gh: 'vagrant_virtualbox-x86_64' variant: '10-kitten-v2' @@ -193,6 +212,8 @@ jobs: variant: '10-kitten-v2' - matrix_gh: 'azure-x86_64' variant: '10-v2' + - matrix_gh: 'gcp-x86_64' + variant: '10-v2' - matrix_gh: 'oci-x86_64' variant: '10-v2' - matrix_gh: 'digitalocean-x86_64' @@ -211,7 +232,7 @@ jobs: echo "ARCH=$arch" >> $GITHUB_ENV - name: Checkout ${{ github.action_repository }} - uses: actions/checkout@v4 + uses: actions/checkout@v5 - uses: ./.github/actions/shared-steps name: ${{ matrix.variant }} ${{ matrix.matrix_gh }} image @@ -232,15 +253,25 @@ jobs: store_as_artifact: ${{ inputs.store_as_artifact }} upload_to_s3: ${{ inputs.upload_to_s3 }} notify_mattermost: ${{ inputs.notify_mattermost }} - run_test: true # Do image simple testing and generate installed packages list (vagrant_* only) + run_test: true # Do image simple testing and generate installed packages list (vagrant_* and GCP only) # runner: ${{ github.repository_owner == 'AlmaLinux' && 'aws-ec2' || 'gh_hosted' }} runner: gh_hosted env: PACKER_GITHUB_API_TOKEN: ${{ secrets.GIT_HUB_TOKEN }} + + + + + + + +### Everything below is for self-hosted runners only ### + start-self-hosted-runner: name: ${{ matrix.variant }} ${{ matrix.matrix_sh }} runner - if: ${{ inputs.self-hosted && needs.init-data.outputs.matrix_sh != '[]' }} + # If we're in the almalinux org we use runs-on for self-hosted + if: ${{ github.repository_owner != 'AlmaLinux' && inputs.self-hosted && needs.init-data.outputs.matrix_sh != '[]' }} runs-on: ubuntu-24.04 needs: [init-data] strategy: @@ -316,6 +347,8 @@ jobs: exclude: - matrix_sh: 'oci-aarch64' variant: '10-kitten' + - matrix_sh: 'oci-aarch64' + variant: '10' - matrix_sh: 'oci-aarch64' variant: '9-64k' - matrix_sh: 'oci-aarch64' diff --git a/.github/workflows/test-gcp.yml b/.github/workflows/test-gcp.yml new file mode 100644 index 00000000..6794e2d6 --- /dev/null +++ b/.github/workflows/test-gcp.yml @@ -0,0 +1,269 @@ +name: GCP cloud-image-tests + +on: + workflow_dispatch: + inputs: + version_major: + description: 'AlmaLinux major version' + required: true + default: '10' + type: choice + options: + - 10-kitten + - 10 + - 9 + - 8 + arch: + description: 'Architecture to test' + required: true + default: 'ALL' + type: choice + options: + - ALL + - x86_64 + - aarch64 + image_override: + description: 'Image to test, overrides version_major to test a direct image instead. Architecture must be set properly for the image being passed. This must be a full path to a GCP image, for example, projects/almalinux-dev-images-469421/global/images/almalinux-9-v20230920' + required: false + default: '' + # notify_mattermost: + # description: "Send notification to Mattermost" + # required: true + # type: boolean + # default: false + +jobs: + init-data: + runs-on: ubuntu-latest + outputs: + image_path: ${{ steps.determine_image.outputs.image_path }} + steps: + - name: Determine image to test + id: determine_image + run: | + if [ -n "${{ inputs.image_override }}" ]; then + echo "Using image override: ${{ inputs.image_override }}" + image_path="${{ inputs.image_override }}" + elif [ "${{ inputs.arch == 'ALL' }}" ]; then + echo "Using version major: ${{ inputs.version_major }}" + echo "Using all architectures" + image_path="projects/almalinux-dev-images-469421/global/images/family/almalinux-${{ inputs.version_major }}" + else + echo "Using version major: ${{ inputs.version_major }}" + echo "Using arch: ${{ inputs.arch }}" + image_path="projects/almalinux-dev-images-469421/global/images/family/almalinux-${{ inputs.version_major }}" + fi + echo "Determined image path: ${image_path}" + echo "image_path=${image_path}" >> $GITHUB_OUTPUT + +# # this initial test does the generic suite of tests not assigned to any specific shape - letting the test system +# # choose its own shapes and sizes. This is run first to catch any major issues before running the per-shape tests +# # which take a long time and use a lot of resources. Think of this as a smoke test to catch major issues early. +# test-gcp-initialtest: +# name: AlmaLinux ${{ inputs.image_override || format('{0} {1}', inputs.version_major, matrix.arch) }} Generic Full Run +# needs: init-data +# permissions: +# id-token: write +# contents: read +# runs-on: ubuntu-24.04 +# strategy: +# fail-fast: false +# matrix: +# # this sets the arch matrix based on the input +# # if input is ALL, then set to both x86_64 and aarch64 +# # otherwise set to the selected arch +# arch: ${{ fromJSON(inputs.arch == 'ALL' && '["x86_64","aarch64"]' || format('["{0}"]', inputs.arch)) }} +# steps: +# # we don't need the checked out files, but this is required for the google auth action to work +# - uses: 'actions/checkout@v5' + +# - id: 'google-auth-image-testing' +# uses: 'google-github-actions/auth@v2' +# with: +# workload_identity_provider: 'projects/527193872801/locations/global/workloadIdentityPools/github-actions/providers/github' +# service_account: 'github-actions-image-testing@almalinux-image-testing-469421.iam.gserviceaccount.com' + +# - name: 'Set up Google Cloud SDK' +# uses: 'google-github-actions/setup-gcloud@v3.0.0' + +# - name: 'Run Google cloud-image-testing tests which are hard-coded to specific shapes' +# shell: bash +# run: | +# docker run \ +# -v ${{ env.GOOGLE_GHA_CREDS_PATH }}:/creds/auth.json \ +# -e GOOGLE_APPLICATION_CREDENTIALS=/creds/auth.json \ +# gcr.io/compute-image-tools/cloud-image-tests:latest \ +# -project almalinux-image-testing-469421 \ +# -parallel_stagger 10s \ +# -parallel_count 20 \ +# -filter '^(cvm|livemigrate|suspendresume|loadbalancer|guestagent|hostnamevalidation|imageboot|licensevalidation|network|security|hotattach|packagevalidation|ssh|metadata|disk|lssd|vmspec)$' \ +# -images '${{ needs.init-data.outputs.image_path }}${{ inputs.image_override == '' && matrix.arch == 'aarch64' && '-arm64' || ''}}' + + test-gcp-pershape-x86_64: + name: ${{ inputs.image_override || format('{0}', inputs.version_major) }} x86_64 ${{ matrix.shape }} + #needs: [init-data, test-gcp-initialtest] + needs: init-data + permissions: + id-token: write + contents: read + runs-on: "${{ github.repository_owner == 'AlmaLinux' && format('runs-on={0}/runner=2cpu-linux-x64/spot=false/image=almalinux-10-x86_64', github.run_id) || 'ubuntu-24.04' }}" + if: inputs.arch == 'ALL' || inputs.arch == 'x86_64' + strategy: + fail-fast: false + matrix: + shape: + - n4-standard-2 + - n4-standard-80 + - n2-standard-2 + - n2-standard-128 + - n2d-standard-2 + - n2d-standard-224 + - n1-standard-1 + - n1-standard-96 + - c4-standard-2 + # can never get capacity for 288 so using 192 + - c4-standard-192 + # all lssd shapes fail + # https://github.com/GoogleCloudPlatform/cloud-image-tests/issues/345 + # - c4-standard-4-lssd + # - c4-standard-288-lssd + # never has capacity anywhere + # - c4-standard-288-metal + - c4d-standard-2 + # can never get capacity for 384 so using 192 + - c4d-standard-192 + # - c4d-standard-8-lssd + # - c4d-standard-384-lssd + - c3-standard-4 + - c3-standard-176 + # never any metal capacity available + # - c3-standard-192-metal + # - c3-standard-4-lssd + # - c3-standard-176-lssd + - c3d-standard-4 + - c3d-standard-360 + # - c3d-standard-8-lssd + # - c3d-standard-360-lssd + - e2-standard-2 + - e2-standard-32 + - e2-medium + - t2d-standard-1 + - t2d-standard-60 + # h4d tests fail + # https://github.com/GoogleCloudPlatform/cloud-image-tests/issues/346 + # - h4d-standard-192 + # - h4d-highmem-192-lssd + # can never get capacity for this shape + # - h3-standard-88 + - c2-standard-4 + - c2-standard-60 + - c2d-standard-2 + - c2d-standard-112 + # m4, x4, m3, m2 disabled due to no quotas + # - m4-megamem-28 + # - m4-megamem-224 + # - x4-megamem-960-metal + # - x4-megamem-1920-metal + # - m3-megamem-64 + # - m2-megamem-416 + # m1 quota too low + # - m1-megamem-96 + # z3 tests fail + # https://github.com/GoogleCloudPlatform/cloud-image-tests/issues/346 + # z3 tests not needed, basically c3 with lots of lssd, so covered by c3-lssd tests + # - z3-highmem-14-standardlssd + # things with special zone requirements or other special needs + # include: + # only available in us-central1-b + # disabled, never any capacity available + # - shape: c4d-standard-384-metal + # zone: us-central1-b + + steps: + # we don't need the checked out files, but this is required for the google auth action to work + - uses: 'actions/checkout@v5' + + - id: 'google-auth-image-testing' + uses: 'google-github-actions/auth@v2' + with: + workload_identity_provider: 'projects/527193872801/locations/global/workloadIdentityPools/github-actions/providers/github' + service_account: 'github-actions-image-testing@almalinux-image-testing-469421.iam.gserviceaccount.com' + + - name: 'Set up Google Cloud SDK' + uses: 'google-github-actions/setup-gcloud@v3.0.0' + + - name: Runner OS specific configuration + shell: bash + run: | + # Runner OS specific configuration + if [ -e /etc/redhat-release ]; then + sudo setenforce 0 + sudo dnf -y install podman + runner_user=$USER + sudo loginctl enable-linger $runner_user + docker_cmd=podman + elif lsb_release -cs > /dev/null 2>&1; then + docker_cmd=docker + else + echo "[Debug] Unknown OS" + exit 1 + fi + echo "docker_cmd=${docker_cmd}" >> $GITHUB_ENV + + - name: 'Run Google cloud-image-testing tests on ${{ matrix.shape }}' + shell: bash + run: | + ${{ env.docker_cmd }} run \ + -v ${{ env.GOOGLE_GHA_CREDS_PATH }}:/creds/auth.json \ + -e GOOGLE_APPLICATION_CREDENTIALS=/creds/auth.json \ + gcr.io/compute-image-tools/cloud-image-tests:latest \ + -project almalinux-image-testing-469421 \ + -x86_shape ${{ matrix.shape }} \ + -parallel_count ${{ github.run_attempt > 1 && '5' || '1' }} \ + ${{ matrix.zone && format('-zone {0}', matrix.zone) || '' }} \ + -filter '^(cvm|livemigrate|suspendresume|loadbalancer|guestagent|hostnamevalidation|imageboot|licensevalidation|network|security|hotattach|packagevalidation|ssh|metadata)$' \ + -images '${{ needs.init-data.outputs.image_path || inputs.image_override }}${{ inputs.image_override == '' && matrix.arch == 'aarch64' && '-arm64' || ''}}' + + test-gcp-pershape-aarch64: + name: ${{ inputs.image_override || format('{0}', inputs.version_major) }} aarch64 ${{ matrix.shape }} + #needs: [init-data, test-gcp-initialtest] + needs: init-data + permissions: + id-token: write + contents: read + runs-on: ubuntu-24.04 + if: inputs.arch == 'ALL' || inputs.arch == 'aarch64' + strategy: + fail-fast: false + matrix: + shape: + - c4a-standard-1 + - c4a-standard-72 + - c4a-standard-4-lssd + - c4a-standard-72-lssd + - t2a-standard-1 + - t2a-standard-48 + steps: + # we don't need the checked out files, but this is required for the google auth action to work + - uses: 'actions/checkout@v5' + + - id: 'google-auth-image-testing' + uses: 'google-github-actions/auth@v2' + with: + workload_identity_provider: 'projects/527193872801/locations/global/workloadIdentityPools/github-actions/providers/github' + service_account: 'github-actions-image-testing@almalinux-image-testing-469421.iam.gserviceaccount.com' + + - name: 'Set up Google Cloud SDK' + uses: 'google-github-actions/setup-gcloud@v3.0.0' + + - name: 'Run Google cloud-image-testing tests on ${{ matrix.shape }}' + shell: bash + run: | + docker run \ + -v ${{ env.GOOGLE_GHA_CREDS_PATH }}:/creds/auth.json \ + -e GOOGLE_APPLICATION_CREDENTIALS=/creds/auth.json \ + gcr.io/compute-image-tools/cloud-image-tests:latest \ + -project almalinux-image-testing-469421 \ + -arm64_shape ${{ matrix.shape }} \ + -filter '^(cvm|livemigrate|suspendresume|loadbalancer|guestagent|hostnamevalidation|imageboot|licensevalidation|network|security|hotattach|packagevalidation|ssh|metadata)$' \ + -images '${{ needs.init-data.outputs.image_path || inputs.image_override }}${{ inputs.image_override == '' && matrix.arch == 'aarch64' && '-arm64' || ''}}' diff --git a/almalinux-8-gcp.pkr.hcl b/almalinux-8-gcp.pkr.hcl new file mode 100644 index 00000000..a42abdb0 --- /dev/null +++ b/almalinux-8-gcp.pkr.hcl @@ -0,0 +1,128 @@ +# AlmaLinux OS 8 Packer template for GCP VM images + +source "qemu" "almalinux-8-gcp-x86_64" { + iso_url = local.iso_url_8_x86_64 + iso_checksum = local.iso_checksum_8_x86_64 + http_directory = var.http_directory + shutdown_command = var.root_shutdown_command + ssh_username = var.gencloud_ssh_username + ssh_password = var.gencloud_ssh_password + ssh_timeout = var.ssh_timeout + boot_command = local.gcp_boot_command_8_x86_64 + boot_wait = var.boot_wait + accelerator = "kvm" + disk_interface = "virtio-scsi" + disk_size = var.gcp_disk_size + disk_cache = "unsafe" + disk_discard = "unmap" + disk_detect_zeroes = "unmap" + format = "raw" + headless = var.headless + machine_type = "q35" + memory = var.memory_x86_64 + net_device = "virtio-net" + qemu_binary = var.qemu_binary + vm_name = "AlmaLinux-8-GCP-${var.os_ver_8}-${formatdate("YYYYMMDD", timestamp())}.${var.build_number}.x86_64.raw" + cpu_model = "host" + cpus = var.cpus + efi_boot = true + efi_firmware_code = var.ovmf_code + efi_firmware_vars = var.ovmf_vars + efi_drop_efivars = true +} + +source "qemu" "almalinux-8-gcp-aarch64" { + iso_url = local.iso_url_8_aarch64 + iso_checksum = local.iso_checksum_8_aarch64 + http_directory = var.http_directory + shutdown_command = var.root_shutdown_command + ssh_username = var.gencloud_ssh_username + ssh_password = var.gencloud_ssh_password + ssh_timeout = var.ssh_timeout + boot_command = local.gcp_boot_command_8_aarch64 + boot_wait = var.boot_wait + accelerator = "kvm" + firmware = var.aavmf_code + use_pflash = false + disk_interface = "virtio-scsi" + disk_size = var.gcp_disk_size + disk_cache = "unsafe" + disk_discard = "unmap" + disk_detect_zeroes = "unmap" + format = "raw" + headless = var.headless + machine_type = "virt,gic-version=max" + memory = var.memory_aarch64 + net_device = "virtio-net" + qemu_binary = var.qemu_binary + vm_name = "AlmaLinux-8-GCP-${var.os_ver_8}-${formatdate("YYYYMMDD", timestamp())}.${var.build_number}.aarch64.raw" + cpu_model = "host" + cpus = var.cpus + qemuargs = [ + ["-boot", "strict=on"], + ["-monitor", "none"] + ] +} + +build { + sources = [ + "source.qemu.almalinux-8-gcp-x86_64", + "source.qemu.almalinux-8-gcp-aarch64", + ] + + provisioner "ansible" { + #command = "/home/jonathan/ansible-2.16/bin/ansible-playbook" + #galaxy_command = "/home/jonathan/ansible-2.16/bin/ansible-galaxy" + galaxy_file = "./ansible/requirements.yml" + galaxy_force_install = true + collections_path = "./ansible/collections" + roles_path = "./ansible/roles" + playbook_file = "./ansible/gcp.yml" + ansible_env_vars = [ + "ANSIBLE_PIPELINING=True", + "ANSIBLE_REMOTE_TEMP=/tmp", + "ANSIBLE_SCP_EXTRA_ARGS=-O", + ] + only = ["qemu.almalinux-8-gcp-x86_64"] + } + + provisioner "ansible" { + galaxy_file = "./ansible/requirements.yml" + galaxy_force_install = true + collections_path = "./ansible/collections" + roles_path = "./ansible/roles" + playbook_file = "./ansible/gcp.yml" + ansible_env_vars = [ + "ANSIBLE_PIPELINING=True", + "ANSIBLE_REMOTE_TEMP=/tmp", + "ANSIBLE_SCP_EXTRA_ARGS=-O" + ] + only = ["qemu.almalinux-8-gcp-aarch64"] + } + + # copy SBOM metadata file into output + post-processor "shell-local" { + inline = [ + "cp /tmp/sbom-data-$PACKER_BUILD_NAME.json output-$PACKER_BUILD_NAME/" + ] + } + + post-processor "shell-local" { + inline = [ + "cd output-$PACKER_BUILD_NAME", + "mv AlmaLinux-8-GCP-${var.os_ver_8}-${formatdate("YYYYMMDD", timestamp())}.${var.build_number}.x86_64.raw disk.raw", + "tar -cf - disk.raw | pigz -c > AlmaLinux-8-GCP-${var.os_ver_8}-${formatdate("YYYYMMDD", timestamp())}.${var.build_number}.x86_64.tar.gz" + ] + only = ["qemu.almalinux-8-gcp-x86_64"] + } + + post-processor "shell-local" { + inline = [ + "cd output-$PACKER_BUILD_NAME", + "mv AlmaLinux-8-GCP-${var.os_ver_8}-${formatdate("YYYYMMDD", timestamp())}.${var.build_number}.aarch64.raw disk.raw", + "tar -cf - disk.raw | pigz -c > AlmaLinux-8-GCP-${var.os_ver_8}-${formatdate("YYYYMMDD", timestamp())}.${var.build_number}.aarch64.tar.gz" + ] + only = ["qemu.almalinux-8-gcp-aarch64"] + } + +} diff --git a/almalinux-9-gcp.pkr.hcl b/almalinux-9-gcp.pkr.hcl new file mode 100644 index 00000000..616f8b26 --- /dev/null +++ b/almalinux-9-gcp.pkr.hcl @@ -0,0 +1,128 @@ +# AlmaLinux OS 9 Packer template for GCP VM images + +source "qemu" "almalinux-9-gcp-x86_64" { + iso_url = local.iso_url_9_x86_64 + iso_checksum = local.iso_checksum_9_x86_64 + http_directory = var.http_directory + shutdown_command = var.root_shutdown_command + ssh_username = var.gencloud_ssh_username + ssh_password = var.gencloud_ssh_password + ssh_timeout = var.ssh_timeout + boot_command = var.gcp_boot_command_9_x86_64 + boot_wait = var.boot_wait + accelerator = "kvm" + disk_interface = "virtio-scsi" + disk_size = var.gcp_disk_size + disk_cache = "unsafe" + disk_discard = "unmap" + disk_detect_zeroes = "unmap" + format = "raw" + headless = var.headless + machine_type = "q35" + memory = var.memory_x86_64 + net_device = "virtio-net" + qemu_binary = var.qemu_binary + vm_name = "AlmaLinux-9-GCP-${var.os_ver_9}-${formatdate("YYYYMMDD", timestamp())}.${var.build_number}.x86_64.raw" + cpu_model = "host" + cpus = var.cpus + efi_boot = true + efi_firmware_code = var.ovmf_code + efi_firmware_vars = var.ovmf_vars + efi_drop_efivars = true +} + +source "qemu" "almalinux-9-gcp-aarch64" { + iso_url = local.iso_url_9_aarch64 + iso_checksum = local.iso_checksum_9_aarch64 + http_directory = var.http_directory + shutdown_command = var.root_shutdown_command + ssh_username = var.gencloud_ssh_username + ssh_password = var.gencloud_ssh_password + ssh_timeout = var.ssh_timeout + boot_command = var.gcp_boot_command_9_aarch64 + boot_wait = var.boot_wait + accelerator = "kvm" + firmware = var.aavmf_code + use_pflash = false + disk_interface = "virtio-scsi" + disk_size = var.gcp_disk_size + disk_cache = "unsafe" + disk_discard = "unmap" + disk_detect_zeroes = "unmap" + format = "raw" + headless = var.headless + machine_type = "virt,gic-version=max" + memory = var.memory_aarch64 + net_device = "virtio-net" + qemu_binary = var.qemu_binary + vm_name = "AlmaLinux-9-GCP-${var.os_ver_9}-${formatdate("YYYYMMDD", timestamp())}.${var.build_number}.aarch64.raw" + cpu_model = "host" + cpus = var.cpus + qemuargs = [ + ["-boot", "strict=on"], + ["-monitor", "none"] + ] +} + +build { + sources = [ + "source.qemu.almalinux-9-gcp-x86_64", + "source.qemu.almalinux-9-gcp-aarch64", + ] + + provisioner "ansible" { + #command = "/home/jonathan/ansible-2.16/bin/ansible-playbook" + #galaxy_command = "/home/jonathan/ansible-2.16/bin/ansible-galaxy" + galaxy_file = "./ansible/requirements.yml" + galaxy_force_install = true + collections_path = "./ansible/collections" + roles_path = "./ansible/roles" + playbook_file = "./ansible/gcp.yml" + ansible_env_vars = [ + "ANSIBLE_PIPELINING=True", + "ANSIBLE_REMOTE_TEMP=/tmp", + "ANSIBLE_SCP_EXTRA_ARGS=-O", + ] + only = ["qemu.almalinux-9-gcp-x86_64"] + } + + provisioner "ansible" { + galaxy_file = "./ansible/requirements.yml" + galaxy_force_install = true + collections_path = "./ansible/collections" + roles_path = "./ansible/roles" + playbook_file = "./ansible/gcp.yml" + ansible_env_vars = [ + "ANSIBLE_PIPELINING=True", + "ANSIBLE_REMOTE_TEMP=/tmp", + "ANSIBLE_SCP_EXTRA_ARGS=-O" + ] + only = ["qemu.almalinux-9-gcp-aarch64"] + } + + # copy SBOM metadata file into output + post-processor "shell-local" { + inline = [ + "cp /tmp/sbom-data-$PACKER_BUILD_NAME.json output-$PACKER_BUILD_NAME/" + ] + } + + post-processor "shell-local" { + inline = [ + "cd output-$PACKER_BUILD_NAME", + "mv AlmaLinux-9-GCP-${var.os_ver_9}-${formatdate("YYYYMMDD", timestamp())}.${var.build_number}.x86_64.raw disk.raw", + "tar -cf - disk.raw | pigz -c > AlmaLinux-9-GCP-${var.os_ver_9}-${formatdate("YYYYMMDD", timestamp())}.${var.build_number}.x86_64.tar.gz" + ] + only = ["qemu.almalinux-9-gcp-x86_64"] + } + + post-processor "shell-local" { + inline = [ + "cd output-$PACKER_BUILD_NAME", + "mv AlmaLinux-9-GCP-${var.os_ver_9}-${formatdate("YYYYMMDD", timestamp())}.${var.build_number}.aarch64.raw disk.raw", + "tar -cf - disk.raw | pigz -c > AlmaLinux-9-GCP-${var.os_ver_9}-${formatdate("YYYYMMDD", timestamp())}.${var.build_number}.aarch64.tar.gz" + ] + only = ["qemu.almalinux-9-gcp-aarch64"] + } + +} diff --git a/almalinux_10_gcp.pkr.hcl b/almalinux_10_gcp.pkr.hcl new file mode 100644 index 00000000..aed3da92 --- /dev/null +++ b/almalinux_10_gcp.pkr.hcl @@ -0,0 +1,145 @@ +# AlmaLinux OS 10 Packer template for GCP VM images + +source "qemu" "almalinux_10_gcp_x86_64" { + iso_url = local.iso_url_10_x86_64 + iso_checksum = local.iso_checksum_10_x86_64 + http_directory = var.http_directory + shutdown_command = var.root_shutdown_command + ssh_username = var.gencloud_ssh_username + ssh_password = var.gencloud_ssh_password + ssh_timeout = var.ssh_timeout + boot_command = var.gcp_boot_command_10_x86_64 + boot_wait = var.boot_wait + accelerator = "kvm" + disk_interface = "virtio-scsi" + disk_size = var.gcp_disk_size + disk_cache = "unsafe" + disk_discard = "unmap" + disk_detect_zeroes = "unmap" + format = "raw" + headless = var.headless + machine_type = "q35" + memory = var.memory_x86_64 + net_device = "virtio-net" + qemu_binary = var.qemu_binary + vm_name = "AlmaLinux-10-GCP-${var.os_ver_10}-${formatdate("YYYYMMDD", timestamp())}.${var.build_number}.x86_64.raw" + cpu_model = "host" + cpus = var.cpus + efi_boot = true + efi_firmware_code = var.ovmf_code + efi_firmware_vars = var.ovmf_vars + efi_drop_efivars = true +} + +source "qemu" "almalinux_10_gcp_aarch64" { + iso_url = local.iso_url_10_aarch64 + iso_checksum = local.iso_checksum_10_aarch64 + http_directory = var.http_directory + shutdown_command = var.root_shutdown_command + ssh_username = var.gencloud_ssh_username + ssh_password = var.gencloud_ssh_password + ssh_timeout = var.ssh_timeout + boot_command = var.gcp_boot_command_10_aarch64 + boot_wait = var.boot_wait + accelerator = "kvm" + firmware = var.aavmf_code + use_pflash = false + disk_interface = "virtio-scsi" + disk_size = var.gcp_disk_size + disk_cache = "unsafe" + disk_discard = "unmap" + disk_detect_zeroes = "unmap" + format = "raw" + headless = var.headless + machine_type = "virt,gic-version=max" + memory = var.memory_aarch64 + net_device = "virtio-net" + qemu_binary = var.qemu_binary + vm_name = "AlmaLinux-10-GCP-${var.os_ver_10}-${formatdate("YYYYMMDD", timestamp())}.${var.build_number}.aarch64.raw" + cpu_model = "host" + cpus = var.cpus + qemuargs = [ + ["-boot", "strict=on"], + ["-monitor", "none"] + ] +} + +source "qemu" "almalinux_10_gcp_64k_aarch64" { + iso_url = local.iso_url_10_aarch64 + iso_checksum = local.iso_checksum_10_aarch64 + http_directory = var.http_directory + shutdown_command = var.root_shutdown_command + ssh_username = var.gencloud_ssh_username + ssh_password = var.gencloud_ssh_password + ssh_timeout = var.ssh_timeout + boot_command = var.gcp_boot_command_10_64k_aarch64 + boot_wait = var.boot_wait + accelerator = "kvm" + firmware = var.aavmf_code + use_pflash = false + disk_interface = "virtio-scsi" + disk_size = var.gcp_disk_size + disk_cache = "unsafe" + disk_discard = "unmap" + disk_detect_zeroes = "unmap" + format = "raw" + headless = var.headless + machine_type = "virt,gic-version=max" + memory = var.memory_aarch64 + net_device = "virtio-net" + qemu_binary = var.qemu_binary + vm_name = "AlmaLinux-10-GCP-${var.os_ver_10}-${formatdate("YYYYMMDD", timestamp())}.${var.build_number}-64k.aarch64.raw" + cpu_model = "host" + cpus = var.cpus + qemuargs = [ + ["-boot", "strict=on"], + ["-monitor", "none"] + ] +} + +build { + sources = [ + "source.qemu.almalinux_10_gcp_x86_64", + "source.qemu.almalinux_10_gcp_aarch64", + "source.qemu.almalinux_10_gcp_64k_aarch64", + ] + + provisioner "ansible" { + galaxy_file = "./ansible/requirements.yml" + galaxy_force_install = true + collections_path = "./ansible/collections" + roles_path = "./ansible/roles" + playbook_file = "./ansible/gcp.yml" + ansible_env_vars = [ + "ANSIBLE_PIPELINING=True", + "ANSIBLE_REMOTE_TEMP=/tmp", + "ANSIBLE_SCP_EXTRA_ARGS=-O", + ] + } + + # copy SBOM metadata file into output + post-processor "shell-local" { + inline = [ + "cp /tmp/sbom-data-$PACKER_BUILD_NAME.json output-$PACKER_BUILD_NAME/" + ] + } + + post-processor "shell-local" { + inline = [ + "cd output-$PACKER_BUILD_NAME", + "mv AlmaLinux-10-GCP-${var.os_ver_10}-${formatdate("YYYYMMDD", timestamp())}.${var.build_number}.x86_64.raw disk.raw", + "tar -cf - disk.raw | pigz -c > AlmaLinux-10-GCP-${var.os_ver_10}-${formatdate("YYYYMMDD", timestamp())}.${var.build_number}.x86_64.tar.gz" + ] + only = ["qemu.almalinux_10_gcp_x86_64"] + } + + post-processor "shell-local" { + inline = [ + "cd output-$PACKER_BUILD_NAME", + "mv AlmaLinux-10-GCP-${var.os_ver_10}-${formatdate("YYYYMMDD", timestamp())}.${var.build_number}.aarch64.raw disk.raw", + "tar -cf - disk.raw | pigz -c > AlmaLinux-10-GCP-${var.os_ver_10}-${formatdate("YYYYMMDD", timestamp())}.${var.build_number}.aarch64.tar.gz" + ] + only = ["qemu.almalinux_10_gcp_aarch64"] + } + +} diff --git a/ansible/gcp.yml b/ansible/gcp.yml new file mode 100644 index 00000000..0d2cff6f --- /dev/null +++ b/ansible/gcp.yml @@ -0,0 +1,9 @@ +# An Ansible playbook that configures an AlmaLinux OS GCP image +--- +- name: AlmaLinux GCP + hosts: default + become: true + + roles: + - gcp_guest + - cleanup_vm diff --git a/ansible/roles/cleanup_vm/defaults/main.yml b/ansible/roles/cleanup_vm/defaults/main.yml index 4a0ea179..c2a099fa 100644 --- a/ansible/roles/cleanup_vm/defaults/main.yml +++ b/ansible/roles/cleanup_vm/defaults/main.yml @@ -1,2 +1,3 @@ --- cleanup_ssh_host_keys: true +collect_sbom_data: true diff --git a/ansible/roles/cleanup_vm/tasks/main.yml b/ansible/roles/cleanup_vm/tasks/main.yml index 353042d2..9893a1e5 100644 --- a/ansible/roles/cleanup_vm/tasks/main.yml +++ b/ansible/roles/cleanup_vm/tasks/main.yml @@ -5,6 +5,11 @@ changed_when: removeoldoutput.rc == 0 ignore_errors: yes +- name: Include sbom_data role for SBOM data collection + include_role: + name: sbom_data + when: collect_sbom_data | bool + - name: Find persistent net rules ansible.builtin.find: paths: /etc/udev/rules.d diff --git a/ansible/roles/gcp_guest/meta/main.yml b/ansible/roles/gcp_guest/meta/main.yml new file mode 100644 index 00000000..7f867d73 --- /dev/null +++ b/ansible/roles/gcp_guest/meta/main.yml @@ -0,0 +1,2 @@ +--- +dependencies: diff --git a/ansible/roles/gcp_guest/tasks/main.yml b/ansible/roles/gcp_guest/tasks/main.yml new file mode 100644 index 00000000..7f41f22d --- /dev/null +++ b/ansible/roles/gcp_guest/tasks/main.yml @@ -0,0 +1,28 @@ +--- +- name: Install GCP guest packages + dnf: + name: + - google-compute-engine + - google-osconfig-agent + - gce-disk-expand + state: present + +- name: Install google-cloud-cli + dnf: + name: google-cloud-cli + state: present + when: ansible_distribution_major_version | int >= 10 + +- name: Disable root login via SSH + lineinfile: + path: /etc/ssh/sshd_config + regexp: '^PermitRootLogin' + line: 'PermitRootLogin no' + state: present + +- name: Disable password authentication via SSH + lineinfile: + path: /etc/ssh/sshd_config + regexp: '^PasswordAuthentication' + line: 'PasswordAuthentication no' + state: present diff --git a/ansible/roles/sbom_data/tasks/main.yml b/ansible/roles/sbom_data/tasks/main.yml new file mode 100644 index 00000000..54842569 --- /dev/null +++ b/ansible/roles/sbom_data/tasks/main.yml @@ -0,0 +1,18 @@ +--- +- name: Copy SBOM data collector into the system + ansible.builtin.copy: + src: "{{ playbook_dir }}/../sbom-tools/sbom_data_collector.py" + dest: /dev/shm/sbom_data_collector.py + +- name: Collect SBOM data from the system + ansible.builtin.shell: python3 /dev/shm/sbom_data_collector.py -o /dev/shm/sbom-data.json -v + register: sbom_data_collector + failed_when: false + +- name: Write SBOM data to artifact file + ansible.builtin.fetch: + src: /dev/shm/sbom-data.json + dest: /tmp/sbom-data-{{ packer_build_name }}.json + flat: true + become: false + when: sbom_data_collector.changed diff --git a/http/almalinux-10.gcp-aarch64.ks b/http/almalinux-10.gcp-aarch64.ks new file mode 100644 index 00000000..99e60f59 --- /dev/null +++ b/http/almalinux-10.gcp-aarch64.ks @@ -0,0 +1,84 @@ +# AlmaLinux OS 10 kickstart file for GCP VM images on x86_64 + +url --url https://repo.almalinux.org/almalinux/10/BaseOS/aarch64/os +text +lang en_US.UTF-8 +keyboard us +timezone UTC --utc +selinux --enforcing +firewall --disabled +services --enabled=sshd + +bootloader --timeout=0 --append="biosdevname=0" + +zerombr +clearpart --all --initlabel +part /boot/efi --fstype=efi --size=200 +part / --fstype=xfs --label=root --grow + +rootpw --plaintext almalinux +reboot --eject + +%packages --exclude-weakdeps --inst-langs=en +dracut-config-generic +tar +dnf-automatic +-*firmware +-dracut-config-rescue +-firewalld +-qemu-guest-agent +%end + +# disable kdump service +%addon com_redhat_kdump --disable +%end + +%post +tee -a /etc/yum.repos.d/google-cloud.repo << EOM +[google-compute-engine] +name=Google Compute Engine +baseurl=https://packages.cloud.google.com/yum/repos/google-compute-engine-el10-aarch64-stable +enabled=1 +gpgcheck=1 +repo_gpgcheck=0 +gpgkey=https://packages.cloud.google.com/yum/doc/rpm-package-key-v10.gpg +EOM +tee -a /etc/yum.repos.d/google-cloud.repo << EOM +[google-cloud-sdk] +name=Google Cloud SDK +baseurl=https://packages.cloud.google.com/yum/repos/cloud-sdk-el10-aarch64 +enabled=1 +gpgcheck=1 +repo_gpgcheck=0 +gpgkey=https://packages.cloud.google.com/yum/doc/rpm-package-key-v10.gpg +EOM +%end + +%post --erroronfail + +# permit root login via SSH with password authetication +echo "PermitRootLogin yes" > /etc/ssh/sshd_config.d/01-permitrootlogin.conf + +# Import all RPM GPG keys. +curl -o /etc/pki/rpm-gpg/rpm-package-key-v10.gpg https://packages.cloud.google.com/yum/doc/rpm-package-key-v10.gpg +rpm --import /etc/pki/rpm-gpg/rpm-package-key-v10.gpg + +# Set google-compute-engine config for EL10. +cat >>/etc/default/instance_configs.cfg.distro << EOL +# Disable boto plugin setup. +[InstanceSetup] +set_boto_config = false +EOL + +# Make changes to dnf automatic.conf +# Apply updates for security (RHEL) by default. NOTE this will not work in CentOS. +sed -i'' 's/upgrade_type =.*/upgrade_type = security/' /etc/dnf/automatic.conf +sed -i'' 's/apply_updates =.*/apply_updates = yes/' /etc/dnf/automatic.conf +# Enable the DNF automatic timer service. +systemctl enable dnf-automatic.timer + +# Blacklist the floppy module. +echo "blacklist floppy" > /etc/modprobe.d/blacklist-floppy.conf +restorecon /etc/modprobe.d/blacklist-floppy.conf + +%end diff --git a/http/almalinux-10.gcp-x86_64.ks b/http/almalinux-10.gcp-x86_64.ks new file mode 100644 index 00000000..bd587e98 --- /dev/null +++ b/http/almalinux-10.gcp-x86_64.ks @@ -0,0 +1,85 @@ +# AlmaLinux OS 10 kickstart file for GCP VM images on x86_64 + +url --url https://repo.almalinux.org/almalinux/10/BaseOS/x86_64/os +text +lang en_US.UTF-8 +keyboard us +timezone UTC --utc +selinux --enforcing +firewall --disabled +services --enabled=sshd + +bootloader --timeout=0 --append="scsi_mod.use_blk_mq=Y console=ttyS0,115200" + +zerombr +clearpart --all --initlabel +part /boot/efi --fstype=efi --size=200 +part / --fstype=xfs --label=root --grow + +rootpw --plaintext almalinux +reboot --eject + +%packages --exclude-weakdeps --inst-langs=en +dracut-config-generic +grub2-pc +tar +dnf-automatic +-*firmware +-dracut-config-rescue +-firewalld +-qemu-guest-agent +%end + +# disable kdump service +%addon com_redhat_kdump --disable +%end + +%post +tee -a /etc/yum.repos.d/google-cloud.repo << EOM +[google-compute-engine] +name=Google Compute Engine +baseurl=https://packages.cloud.google.com/yum/repos/google-compute-engine-el10-x86-64-stable +enabled=1 +gpgcheck=1 +repo_gpgcheck=0 +gpgkey=https://packages.cloud.google.com/yum/doc/rpm-package-key-v10.gpg +EOM +tee -a /etc/yum.repos.d/google-cloud.repo << EOM +[google-cloud-sdk] +name=Google Cloud SDK +baseurl=https://packages.cloud.google.com/yum/repos/cloud-sdk-el10-x86_64 +enabled=1 +gpgcheck=1 +repo_gpgcheck=0 +gpgkey=https://packages.cloud.google.com/yum/doc/rpm-package-key-v10.gpg +EOM +%end + +%post --erroronfail + +# permit root login via SSH with password authetication +echo "PermitRootLogin yes" > /etc/ssh/sshd_config.d/01-permitrootlogin.conf + +# Import all RPM GPG keys. +curl -o /etc/pki/rpm-gpg/rpm-package-key-v10.gpg https://packages.cloud.google.com/yum/doc/rpm-package-key-v10.gpg +rpm --import /etc/pki/rpm-gpg/rpm-package-key-v10.gpg + +# Set google-compute-engine config for EL10. +cat >>/etc/default/instance_configs.cfg.distro << EOL +# Disable boto plugin setup. +[InstanceSetup] +set_boto_config = false +EOL + +# Make changes to dnf automatic.conf +# Apply updates for security (RHEL) by default. NOTE this will not work in CentOS. +sed -i'' 's/upgrade_type =.*/upgrade_type = security/' /etc/dnf/automatic.conf +sed -i'' 's/apply_updates =.*/apply_updates = yes/' /etc/dnf/automatic.conf +# Enable the DNF automatic timer service. +systemctl enable dnf-automatic.timer + +# Blacklist the floppy module. +echo "blacklist floppy" > /etc/modprobe.d/blacklist-floppy.conf +restorecon /etc/modprobe.d/blacklist-floppy.conf + +%end diff --git a/http/almalinux-8.gcp-aarch64.ks b/http/almalinux-8.gcp-aarch64.ks new file mode 100644 index 00000000..67f60c6f --- /dev/null +++ b/http/almalinux-8.gcp-aarch64.ks @@ -0,0 +1,186 @@ +# AlmaLinux OS 8 kickstart file for GCP VM images on aarch64 +text --non-interactive +url --url https://repo.almalinux.org/almalinux/8/BaseOS/aarch64/kickstart/ +repo --name=BaseOS --baseurl=https://repo.almalinux.org/almalinux/8/BaseOS/aarch64/os/ +repo --name=AppStream --baseurl=https://repo.almalinux.org/almalinux/8/AppStream/aarch64/os/ + +# From https://github.com/GoogleCloudPlatform/compute-image-tools/blob/master/daisy_workflows/image_build/enterprise_linux/kickstart/almalinux_8.cfg +# We need the images to match what we took over +firewall --enabled +services --disabled="kdump,sshd-keygen@" --enabled="chronyd,rsyslog,sshd" +skipx +timezone --utc UTC --ntpservers=metadata.google.internal +# we clean this up with ansible +rootpw --plaintext almalinux +firstboot --disabled +selinux --enforcing + +# Network configuration +network --bootproto=dhcp --device=link + +bootloader --timeout=0 --location=mbr --append="net.ifnames=0 biosdevname=0 crashkernel=auto" + +zerombr +clearpart --all --initlabel +part /boot/efi --fstype=efi --size=200 +part / --fstype=xfs --label=root --grow + +rootpw --plaintext almalinux +reboot --eject + +# From https://github.com/GoogleCloudPlatform/compute-image-tools/blob/master/daisy_workflows/image_build/enterprise_linux/kickstart/almalinux_8.cfg +# We need the images to match what we took over +# packages.cfg +# Contains a list of packages to be installed, or not, on all flavors. +# The %package command begins the package selection section of kickstart. +# Packages can be specified by group, or package name. @Base and @Core are +# always selected by default so they do not need to be specified. +%packages +acpid +dhcp-client +dnf-automatic +net-tools +openssh-server +python3 +rng-tools +tar +vim +-subscription-manager +-alsa-utils +-b43-fwcutter +-dmraid +-eject +-gpm +-irqbalance +-microcode_ctl +-smartmontools +-aic94xx-firmware +-atmel-firmware +-b43-openfwwf +-bfa-firmware +-ipw2100-firmware +-ipw2200-firmware +-ivtv-firmware +-iwl*-firmware +-kernel-firmware +-libertas-usb8388-firmware +-ql2100-firmware +-ql2200-firmware +-ql23xx-firmware +-ql2400-firmware +-ql2500-firmware +-rt61pci-firmware +-rt73usb-firmware +-xorg-x11-drv-ati-firmware +-zd1211-firmware +%end + +# disable kdump service +%addon com_redhat_kdump --disable +%end + +%post +tee -a /etc/yum.repos.d/google-cloud.repo << EOM +[google-compute-engine] +name=Google Compute Engine +baseurl=https://packages.cloud.google.com/yum/repos/google-compute-engine-el8-aarch64-stable +enabled=1 +gpgcheck=1 +repo_gpgcheck=0 +gpgkey=https://packages.cloud.google.com/yum/doc/yum-key.gpg + https://packages.cloud.google.com/yum/doc/rpm-package-key.gpg +EOM +tee -a /etc/yum.repos.d/google-cloud.repo << EOM +[google-cloud-sdk] +name=Google Cloud SDK +baseurl=https://packages.cloud.google.com/yum/repos/cloud-sdk-el8-aarch64 +enabled=1 +gpgcheck=1 +repo_gpgcheck=0 +gpgkey=https://packages.cloud.google.com/yum/doc/yum-key.gpg + https://packages.cloud.google.com/yum/doc/rpm-package-key.gpg +EOM +%end + +%onerror +echo "Build Failed!" > /dev/ttyAMA0 +shutdown -h now +%end + +%post --erroronfail +set -x +exec &> /dev/ttyAMA0 + +# Import all RPM GPG keys. +curl -o /etc/pki/rpm-gpg/google-rpm-package-key.gpg https://packages.cloud.google.com/yum/doc/rpm-package-key.gpg +curl -o /etc/pki/rpm-gpg/google-key.gpg https://packages.cloud.google.com/yum/doc/yum-key.gpg +rpm --import /etc/pki/rpm-gpg/* + +# Configure the network for GCE. +# Given that GCE users typically control the firewall at the network API level, +# we want to leave the standard Linux firewall setup enabled but all-open. +firewall-offline-cmd --set-default-zone=trusted + +cat >>/etc/dhcp/dhclient.conf <>/etc/default/instance_configs.cfg.distro << EOL +# Disable boto plugin setup. +[InstanceSetup] +set_boto_config = false +EOL + +# Install the Cloud SDK package. +dnf install -y google-cloud-cli + +# Remove files which shouldn't make it into the image. Its possible these files +# will not exist. +rm -f /etc/boto.cfg /etc/udev/rules.d/70-persistent-net.rules + +# Remove eth0 config from installer. +rm -f /etc/sysconfig/network-scripts/ifcfg-eth0 + +# Set ServerAliveInterval and ClientAliveInterval to prevent SSH +# disconnections. The pattern match is tuned to each source config file. +# The $'...' quoting syntax tells the shell to expand escape characters. +sed -i -e $'/^\tServerAliveInterval/d' /etc/ssh/ssh_config +sed -i -e $'/^Host \\*$/a \\\tServerAliveInterval 420' /etc/ssh/ssh_config +sed -i -e '/ClientAliveInterval/s/^.*/ClientAliveInterval 420/' /etc/ssh/sshd_config + +# Make changes to dnf automatic.conf +# Apply updates for security (RHEL) by default. NOTE this will not work in CentOS. +sed -i 's/upgrade_type =.*/upgrade_type = security/' /etc/dnf/automatic.conf +sed -i 's/apply_updates =.*/apply_updates = yes/' /etc/dnf/automatic.conf +# Enable the DNF automatic timer service. +systemctl enable dnf-automatic.timer + +# Cleanup this repo- we don't want to continue updating with it. +# Depending which repos are used in build, one or more of these files will not +# exist. +rm -f /etc/yum.repos.d/google-cloud-unstable.repo \ + /etc/yum.repos.d/google-cloud-staging.repo + +# Blacklist unnecessary modules +cat < /etc/modprobe.d/blacklist.conf +blacklist floppy +blacklist nouveau +blacklist lbm-nouveau +EOF +restorecon /etc/modprobe.d/blacklist.conf + +# Generate initramfs from latest kernel instead of the running kernel. +kver="$(ls -t /lib/modules | head -n1)" +dracut -f --kver="${kver}" + +# Fix selinux contexts on /etc/resolv.conf. +restorecon /etc/resolv.conf +%end + +# Cleanup. +%post --nochroot --log=/dev/ttyAMA0 +set -x +rm -Rf /mnt/sysimage/tmp/* +%end diff --git a/http/almalinux-8.gcp-x86_64.ks b/http/almalinux-8.gcp-x86_64.ks new file mode 100644 index 00000000..95a53bee --- /dev/null +++ b/http/almalinux-8.gcp-x86_64.ks @@ -0,0 +1,187 @@ +# AlmaLinux OS 8 kickstart file for GCP VM images on x86_64 +text --non-interactive +url --url https://repo.almalinux.org/almalinux/8/BaseOS/x86_64/kickstart/ +repo --name=BaseOS --baseurl=https://repo.almalinux.org/almalinux/8/BaseOS/x86_64/os/ +repo --name=AppStream --baseurl=https://repo.almalinux.org/almalinux/8/AppStream/x86_64/os/ + +# From https://github.com/GoogleCloudPlatform/compute-image-tools/blob/master/daisy_workflows/image_build/enterprise_linux/kickstart/almalinux_8.cfg +# We need the images to match what we took over +firewall --enabled +services --disabled="kdump,sshd-keygen@" --enabled="chronyd,rsyslog,sshd" +skipx +timezone --utc UTC --ntpservers=metadata.google.internal +# we clean this up with ansible +rootpw --plaintext almalinux +firstboot --disabled +selinux --enforcing + +# Network configuration +network --bootproto=dhcp --device=link + +bootloader --timeout=0 --location=mbr --append="net.ifnames=0 biosdevname=0 scsi_mod.use_blk_mq=Y crashkernel=auto console=ttyS0,115200" + +zerombr +clearpart --all --initlabel +part /boot/efi --fstype=efi --size=200 +part / --fstype=xfs --label=root --grow + +rootpw --plaintext almalinux +reboot --eject + +# From https://github.com/GoogleCloudPlatform/compute-image-tools/blob/master/daisy_workflows/image_build/enterprise_linux/kickstart/almalinux_8.cfg +# We need the images to match what we took over +# packages.cfg +# Contains a list of packages to be installed, or not, on all flavors. +# The %package command begins the package selection section of kickstart. +# Packages can be specified by group, or package name. @Base and @Core are +# always selected by default so they do not need to be specified. +%packages +acpid +dhcp-client +dnf-automatic +grub2-tools-efi +net-tools +openssh-server +python3 +rng-tools +tar +vim +-subscription-manager +-alsa-utils +-b43-fwcutter +-dmraid +-eject +-gpm +-irqbalance +-microcode_ctl +-smartmontools +-aic94xx-firmware +-atmel-firmware +-b43-openfwwf +-bfa-firmware +-ipw2100-firmware +-ipw2200-firmware +-ivtv-firmware +-iwl*-firmware +-kernel-firmware +-libertas-usb8388-firmware +-ql2100-firmware +-ql2200-firmware +-ql23xx-firmware +-ql2400-firmware +-ql2500-firmware +-rt61pci-firmware +-rt73usb-firmware +-xorg-x11-drv-ati-firmware +-zd1211-firmware +%end + +# disable kdump service +%addon com_redhat_kdump --disable +%end + +%post +tee -a /etc/yum.repos.d/google-cloud.repo << EOM +[google-compute-engine] +name=Google Compute Engine +baseurl=https://packages.cloud.google.com/yum/repos/google-compute-engine-el8-x86_64-stable +enabled=1 +gpgcheck=1 +repo_gpgcheck=0 +gpgkey=https://packages.cloud.google.com/yum/doc/yum-key.gpg + https://packages.cloud.google.com/yum/doc/rpm-package-key.gpg +EOM +tee -a /etc/yum.repos.d/google-cloud.repo << EOM +[google-cloud-sdk] +name=Google Cloud SDK +baseurl=https://packages.cloud.google.com/yum/repos/cloud-sdk-el8-x86_64 +enabled=1 +gpgcheck=1 +repo_gpgcheck=0 +gpgkey=https://packages.cloud.google.com/yum/doc/yum-key.gpg + https://packages.cloud.google.com/yum/doc/rpm-package-key.gpg +EOM +%end + +%onerror +echo "Build Failed!" > /dev/ttyS0 +shutdown -h now +%end + +%post --erroronfail +set -x +exec &> /dev/ttyS0 + +# Import all RPM GPG keys. +curl -o /etc/pki/rpm-gpg/google-rpm-package-key.gpg https://packages.cloud.google.com/yum/doc/rpm-package-key.gpg +curl -o /etc/pki/rpm-gpg/google-key.gpg https://packages.cloud.google.com/yum/doc/yum-key.gpg +rpm --import /etc/pki/rpm-gpg/* + +# Configure the network for GCE. +# Given that GCE users typically control the firewall at the network API level, +# we want to leave the standard Linux firewall setup enabled but all-open. +firewall-offline-cmd --set-default-zone=trusted + +cat >>/etc/dhcp/dhclient.conf <>/etc/default/instance_configs.cfg.distro << EOL +# Disable boto plugin setup. +[InstanceSetup] +set_boto_config = false +EOL + +# Install the Cloud SDK package. +dnf install -y google-cloud-cli + +# Remove files which shouldn't make it into the image. Its possible these files +# will not exist. +rm -f /etc/boto.cfg /etc/udev/rules.d/70-persistent-net.rules + +# Remove eth0 config from installer. +rm -f /etc/sysconfig/network-scripts/ifcfg-eth0 + +# Set ServerAliveInterval and ClientAliveInterval to prevent SSH +# disconnections. The pattern match is tuned to each source config file. +# The $'...' quoting syntax tells the shell to expand escape characters. +sed -i -e $'/^\tServerAliveInterval/d' /etc/ssh/ssh_config +sed -i -e $'/^Host \\*$/a \\\tServerAliveInterval 420' /etc/ssh/ssh_config +sed -i -e '/ClientAliveInterval/s/^.*/ClientAliveInterval 420/' /etc/ssh/sshd_config + +# Make changes to dnf automatic.conf +# Apply updates for security (RHEL) by default. NOTE this will not work in CentOS. +sed -i 's/upgrade_type =.*/upgrade_type = security/' /etc/dnf/automatic.conf +sed -i 's/apply_updates =.*/apply_updates = yes/' /etc/dnf/automatic.conf +# Enable the DNF automatic timer service. +systemctl enable dnf-automatic.timer + +# Cleanup this repo- we don't want to continue updating with it. +# Depending which repos are used in build, one or more of these files will not +# exist. +rm -f /etc/yum.repos.d/google-cloud-unstable.repo \ + /etc/yum.repos.d/google-cloud-staging.repo + +# Blacklist unnecessary modules +cat < /etc/modprobe.d/blacklist.conf +blacklist floppy +blacklist nouveau +blacklist lbm-nouveau +EOF +restorecon /etc/modprobe.d/blacklist.conf + +# Generate initramfs from latest kernel instead of the running kernel. +kver="$(ls -t /lib/modules | head -n1)" +dracut -f --kver="${kver}" + +# Fix selinux contexts on /etc/resolv.conf. +restorecon /etc/resolv.conf +%end + +# Cleanup. +%post --nochroot --log=/dev/ttyS0 +set -x +rm -Rf /mnt/sysimage/tmp/* +%end diff --git a/http/almalinux-9.gcp-aarch64.ks b/http/almalinux-9.gcp-aarch64.ks new file mode 100644 index 00000000..6425cea8 --- /dev/null +++ b/http/almalinux-9.gcp-aarch64.ks @@ -0,0 +1,189 @@ +# AlmaLinux OS 9 kickstart file for GCP VM images on aarch64 +text --non-interactive +url --url https://repo.almalinux.org/almalinux/9/BaseOS/aarch64/kickstart/ +repo --name=BaseOS --baseurl=https://repo.almalinux.org/almalinux/9/BaseOS/aarch64/os/ +repo --name=AppStream --baseurl=https://repo.almalinux.org/almalinux/9/AppStream/aarch64/os/ + +# From https://github.com/GoogleCloudPlatform/compute-image-tools/blob/master/daisy_workflows/image_build/enterprise_linux/kickstart/almalinux_9.cfg +# We need the images to match what we took over +firewall --enabled +services --disabled="kdump,sshd-keygen@" --enabled="chronyd,rsyslog,sshd" +skipx +timezone --utc UTC --ntpservers=metadata.google.internal +# we clean this up with ansible +rootpw --plaintext almalinux +firstboot --disabled +selinux --enforcing + +# Network configuration +network --bootproto=dhcp --device=link + +bootloader --timeout=0 --location=mbr --append="net.ifnames=0 biosdevname=0 crashkernel=auto" + +zerombr +clearpart --all --initlabel +part /boot/efi --fstype=efi --size=200 +part / --fstype=xfs --label=root --grow + +rootpw --plaintext almalinux +reboot --eject + +# From https://github.com/GoogleCloudPlatform/compute-image-tools/blob/master/daisy_workflows/image_build/enterprise_linux/kickstart/almalinux_9.cfg +# We need the images to match what we took over +# packages.cfg +# Contains a list of packages to be installed, or not, on all flavors. +# The %package command begins the package selection section of kickstart. +# Packages can be specified by group, or package name. @Base and @Core are +# always selected by default so they do not need to be specified. +%packages +acpid +dhcp-client +dnf-automatic +net-tools +openssh-server +python3 +rng-tools +tar +vim +-subscription-manager +-alsa-utils +-b43-fwcutter +-dmraid +-eject +-gpm +-irqbalance +-microcode_ctl +-smartmontools +-aic94xx-firmware +-atmel-firmware +-b43-openfwwf +-bfa-firmware +-ipw2100-firmware +-ipw2200-firmware +-ivtv-firmware +-iwl*-firmware +-kernel-firmware +-libertas-usb8388-firmware +-ql2100-firmware +-ql2200-firmware +-ql23xx-firmware +-ql2400-firmware +-ql2500-firmware +-rt61pci-firmware +-rt73usb-firmware +-xorg-x11-drv-ati-firmware +-zd1211-firmware +%end + +# disable kdump service +%addon com_redhat_kdump --disable +%end + +%post +tee -a /etc/yum.repos.d/google-cloud.repo << EOM +[google-compute-engine] +name=Google Compute Engine +baseurl=https://packages.cloud.google.com/yum/repos/google-compute-engine-el9-aarch64-stable +enabled=1 +gpgcheck=1 +repo_gpgcheck=0 +gpgkey=https://packages.cloud.google.com/yum/doc/yum-key.gpg + https://packages.cloud.google.com/yum/doc/rpm-package-key.gpg +EOM +tee -a /etc/yum.repos.d/google-cloud.repo << EOM +[google-cloud-sdk] +name=Google Cloud SDK +baseurl=https://packages.cloud.google.com/yum/repos/cloud-sdk-el9-aarch64 +enabled=1 +gpgcheck=1 +repo_gpgcheck=0 +gpgkey=https://packages.cloud.google.com/yum/doc/yum-key.gpg + https://packages.cloud.google.com/yum/doc/rpm-package-key.gpg +EOM +%end + +%onerror +echo "Build Failed!" > /dev/ttyAMA0 +shutdown -h now +%end + +%post --erroronfail +set -x +exec &> /dev/ttyAMA0 + +# permit root login via SSH with password authetication (disabled later via ansible) +echo "PermitRootLogin yes" > /etc/ssh/sshd_config.d/01-permitrootlogin.conf + +# Import all RPM GPG keys. +curl -o /etc/pki/rpm-gpg/google-rpm-package-key.gpg https://packages.cloud.google.com/yum/doc/rpm-package-key.gpg +curl -o /etc/pki/rpm-gpg/google-key.gpg https://packages.cloud.google.com/yum/doc/yum-key.gpg +rpm --import /etc/pki/rpm-gpg/* + +# Configure the network for GCE. +# Given that GCE users typically control the firewall at the network API level, +# we want to leave the standard Linux firewall setup enabled but all-open. +firewall-offline-cmd --set-default-zone=trusted + +cat >>/etc/dhcp/dhclient.conf <>/etc/default/instance_configs.cfg.distro << EOL +# Disable boto plugin setup. +[InstanceSetup] +set_boto_config = false +EOL + +# Install the Cloud SDK package. +dnf install -y google-cloud-cli + +# Remove files which shouldn't make it into the image. Its possible these files +# will not exist. +rm -f /etc/boto.cfg /etc/udev/rules.d/70-persistent-net.rules + +# Remove eth0 config from installer. +rm -f /etc/sysconfig/network-scripts/ifcfg-eth0 + +# Set ServerAliveInterval and ClientAliveInterval to prevent SSH +# disconnections. The pattern match is tuned to each source config file. +# The $'...' quoting syntax tells the shell to expand escape characters. +sed -i -e $'/^\tServerAliveInterval/d' /etc/ssh/ssh_config +sed -i -e $'/^Host \\*$/a \\\tServerAliveInterval 420' /etc/ssh/ssh_config +sed -i -e '/ClientAliveInterval/s/^.*/ClientAliveInterval 420/' /etc/ssh/sshd_config + +# Make changes to dnf automatic.conf +# Apply updates for security (RHEL) by default. NOTE this will not work in CentOS. +sed -i 's/upgrade_type =.*/upgrade_type = security/' /etc/dnf/automatic.conf +sed -i 's/apply_updates =.*/apply_updates = yes/' /etc/dnf/automatic.conf +# Enable the DNF automatic timer service. +systemctl enable dnf-automatic.timer + +# Cleanup this repo- we don't want to continue updating with it. +# Depending which repos are used in build, one or more of these files will not +# exist. +rm -f /etc/yum.repos.d/google-cloud-unstable.repo \ + /etc/yum.repos.d/google-cloud-staging.repo + +# Blacklist unnecessary modules +cat < /etc/modprobe.d/blacklist.conf +blacklist floppy +blacklist nouveau +blacklist lbm-nouveau +EOF +restorecon /etc/modprobe.d/blacklist.conf + +# Generate initramfs from latest kernel instead of the running kernel. +kver="$(ls -t /lib/modules | head -n1)" +dracut -f --kver="${kver}" + +# Fix selinux contexts on /etc/resolv.conf. +restorecon /etc/resolv.conf +%end + +# Cleanup. +%post --nochroot --log=/dev/ttyAMA0 +set -x +rm -Rf /mnt/sysimage/tmp/* +%end diff --git a/http/almalinux-9.gcp-x86_64.ks b/http/almalinux-9.gcp-x86_64.ks new file mode 100644 index 00000000..8de00ec0 --- /dev/null +++ b/http/almalinux-9.gcp-x86_64.ks @@ -0,0 +1,190 @@ +# AlmaLinux OS 9 kickstart file for GCP VM images on x86_64 +text --non-interactive +url --url https://repo.almalinux.org/almalinux/9/BaseOS/x86_64/kickstart/ +repo --name=BaseOS --baseurl=https://repo.almalinux.org/almalinux/9/BaseOS/x86_64/os/ +repo --name=AppStream --baseurl=https://repo.almalinux.org/almalinux/9/AppStream/x86_64/os/ + +# From https://github.com/GoogleCloudPlatform/compute-image-tools/blob/master/daisy_workflows/image_build/enterprise_linux/kickstart/almalinux_9.cfg +# We need the images to match what we took over +firewall --enabled +services --disabled="kdump,sshd-keygen@" --enabled="chronyd,rsyslog,sshd" +skipx +timezone --utc UTC --ntpservers=metadata.google.internal +# we clean this up with ansible +rootpw --plaintext almalinux +firstboot --disabled +selinux --enforcing + +# Network configuration +network --bootproto=dhcp --device=link + +bootloader --timeout=0 --location=mbr --append="net.ifnames=0 biosdevname=0 scsi_mod.use_blk_mq=Y crashkernel=auto console=ttyS0,115200" + +zerombr +clearpart --all --initlabel +part /boot/efi --fstype=efi --size=200 +part / --fstype=xfs --label=root --grow + +rootpw --plaintext almalinux +reboot --eject + +# From https://github.com/GoogleCloudPlatform/compute-image-tools/blob/master/daisy_workflows/image_build/enterprise_linux/kickstart/almalinux_9.cfg +# We need the images to match what we took over +# packages.cfg +# Contains a list of packages to be installed, or not, on all flavors. +# The %package command begins the package selection section of kickstart. +# Packages can be specified by group, or package name. @Base and @Core are +# always selected by default so they do not need to be specified. +%packages +acpid +dhcp-client +dnf-automatic +grub2-tools-efi +net-tools +openssh-server +python3 +rng-tools +tar +vim +-subscription-manager +-alsa-utils +-b43-fwcutter +-dmraid +-eject +-gpm +-irqbalance +-microcode_ctl +-smartmontools +-aic94xx-firmware +-atmel-firmware +-b43-openfwwf +-bfa-firmware +-ipw2100-firmware +-ipw2200-firmware +-ivtv-firmware +-iwl*-firmware +-kernel-firmware +-libertas-usb8388-firmware +-ql2100-firmware +-ql2200-firmware +-ql23xx-firmware +-ql2400-firmware +-ql2500-firmware +-rt61pci-firmware +-rt73usb-firmware +-xorg-x11-drv-ati-firmware +-zd1211-firmware +%end + +# disable kdump service +%addon com_redhat_kdump --disable +%end + +%post +tee -a /etc/yum.repos.d/google-cloud.repo << EOM +[google-compute-engine] +name=Google Compute Engine +baseurl=https://packages.cloud.google.com/yum/repos/google-compute-engine-el9-x86_64-stable +enabled=1 +gpgcheck=1 +repo_gpgcheck=0 +gpgkey=https://packages.cloud.google.com/yum/doc/yum-key.gpg + https://packages.cloud.google.com/yum/doc/rpm-package-key.gpg +EOM +tee -a /etc/yum.repos.d/google-cloud.repo << EOM +[google-cloud-sdk] +name=Google Cloud SDK +baseurl=https://packages.cloud.google.com/yum/repos/cloud-sdk-el9-x86_64 +enabled=1 +gpgcheck=1 +repo_gpgcheck=0 +gpgkey=https://packages.cloud.google.com/yum/doc/yum-key.gpg + https://packages.cloud.google.com/yum/doc/rpm-package-key.gpg +EOM +%end + +%onerror +echo "Build Failed!" > /dev/ttyS0 +shutdown -h now +%end + +%post --erroronfail +set -x +exec &> /dev/ttyS0 + +# permit root login via SSH with password authetication (disabled later via ansible) +echo "PermitRootLogin yes" > /etc/ssh/sshd_config.d/01-permitrootlogin.conf + +# Import all RPM GPG keys. +curl -o /etc/pki/rpm-gpg/google-rpm-package-key.gpg https://packages.cloud.google.com/yum/doc/rpm-package-key.gpg +curl -o /etc/pki/rpm-gpg/google-key.gpg https://packages.cloud.google.com/yum/doc/yum-key.gpg +rpm --import /etc/pki/rpm-gpg/* + +# Configure the network for GCE. +# Given that GCE users typically control the firewall at the network API level, +# we want to leave the standard Linux firewall setup enabled but all-open. +firewall-offline-cmd --set-default-zone=trusted + +cat >>/etc/dhcp/dhclient.conf <>/etc/default/instance_configs.cfg.distro << EOL +# Disable boto plugin setup. +[InstanceSetup] +set_boto_config = false +EOL + +# Install the Cloud SDK package. +dnf install -y google-cloud-cli + +# Remove files which shouldn't make it into the image. Its possible these files +# will not exist. +rm -f /etc/boto.cfg /etc/udev/rules.d/70-persistent-net.rules + +# Remove eth0 config from installer. +rm -f /etc/sysconfig/network-scripts/ifcfg-eth0 + +# Set ServerAliveInterval and ClientAliveInterval to prevent SSH +# disconnections. The pattern match is tuned to each source config file. +# The $'...' quoting syntax tells the shell to expand escape characters. +sed -i -e $'/^\tServerAliveInterval/d' /etc/ssh/ssh_config +sed -i -e $'/^Host \\*$/a \\\tServerAliveInterval 420' /etc/ssh/ssh_config +sed -i -e '/ClientAliveInterval/s/^.*/ClientAliveInterval 420/' /etc/ssh/sshd_config + +# Make changes to dnf automatic.conf +# Apply updates for security (RHEL) by default. NOTE this will not work in CentOS. +sed -i 's/upgrade_type =.*/upgrade_type = security/' /etc/dnf/automatic.conf +sed -i 's/apply_updates =.*/apply_updates = yes/' /etc/dnf/automatic.conf +# Enable the DNF automatic timer service. +systemctl enable dnf-automatic.timer + +# Cleanup this repo- we don't want to continue updating with it. +# Depending which repos are used in build, one or more of these files will not +# exist. +rm -f /etc/yum.repos.d/google-cloud-unstable.repo \ + /etc/yum.repos.d/google-cloud-staging.repo + +# Blacklist unnecessary modules +cat < /etc/modprobe.d/blacklist.conf +blacklist floppy +blacklist nouveau +blacklist lbm-nouveau +EOF +restorecon /etc/modprobe.d/blacklist.conf + +# Generate initramfs from latest kernel instead of the running kernel. +kver="$(ls -t /lib/modules | head -n1)" +dracut -f --kver="${kver}" + +# Fix selinux contexts on /etc/resolv.conf. +restorecon /etc/resolv.conf +%end + +# Cleanup. +%post --nochroot --log=/dev/ttyS0 +set -x +rm -Rf /mnt/sysimage/tmp/* +%end diff --git a/variables.pkr.hcl b/variables.pkr.hcl index 82afa258..96944734 100644 --- a/variables.pkr.hcl +++ b/variables.pkr.hcl @@ -144,7 +144,7 @@ variable "cpus" { description = "The number of virtual cpus" type = number - default = 2 + default = 4 } variable "memory_x86_64" { @@ -538,6 +538,127 @@ variable "azure_disk_size" { default = "32212254720b" } +variable "gcp_disk_size" { + description = "The size in GB of hard disk of VM" + + type = string + default = "20G" +} + +local "gcp_boot_command_8_x86_64" { + expression = [ + "c", + "linuxefi /images/pxeboot/vmlinuz", + " inst.stage2=hd:LABEL=AlmaLinux-8-${local.os_ver_minor_8}-x86_64-dvd ro", + " inst.text biosdevname=0 net.ifnames=0", + " inst.ks=http://{{ .HTTPIP }}:{{ .HTTPPort }}/almalinux-8.gcp-x86_64.ks", + " console=ttyS0", + "", + "initrdefi /images/pxeboot/initrd.img", + "", + "boot", + ] +} + +local "gcp_boot_command_8_aarch64" { + expression = [ + "c", + "linux /images/pxeboot/vmlinuz", + " inst.stage2=hd:LABEL=AlmaLinux-8-${local.os_ver_minor_8}-aarch64-dvd ro", + " inst.text biosdevname=0 net.ifnames=0", + " inst.ks=http://{{ .HTTPIP }}:{{ .HTTPPort }}/almalinux-8.gcp-aarch64.ks", + "", + "initrd /images/pxeboot/initrd.img", + "", + "boot" + ] +} + +variable "gcp_boot_command_9_x86_64" { + description = "Boot command for AlmaLinux OS 9 GCP x86_64" + + type = list(string) + + default = [ + "e", + "", + "e", + "", + "biosdevname=0", + "", + "net.ifnames=0", + "", + "inst.text", + "", + "inst.ks=http://{{ .HTTPIP }}:{{ .HTTPPort }}/almalinux-9.gcp-x86_64.ks", + " console=ttyS0", + "x", + ] +} + +variable "gcp_boot_command_9_aarch64" { + description = "Boot command for AlmaLinux OS 9 GCP AArch64" + + type = list(string) + + default = [ + "e", + "", + "e", + "", + "biosdevname=0", + "", + "net.ifnames=0", + "", + "inst.text", + "", + "inst.ks=http://{{ .HTTPIP }}:{{ .HTTPPort }}/almalinux-9.gcp-aarch64.ks", + "x", + ] +} + +variable "gcp_boot_command_10_x86_64" { + description = "Boot command for AlmaLinux OS 10 GCP x86_64" + + type = list(string) + + default = [ + "e", + "", + "e", + "", + "biosdevname=0", + "", + "net.ifnames=0", + "", + "inst.text", + "", + "inst.ks=http://{{ .HTTPIP }}:{{ .HTTPPort }}/almalinux-10.gcp-x86_64.ks", + "x", + ] +} + +variable "gcp_boot_command_10_aarch64" { + description = "Boot command for AlmaLinux OS 10 GCP AArch64" + + type = list(string) + + default = [ + "e", + "", + "e", + "", + "biosdevname=0", + "", + "net.ifnames=0", + "", + "inst.text", + "", + "inst.ks=http://{{ .HTTPIP }}:{{ .HTTPPort }}/almalinux-10.gcp-aarch64.ks", + "x", + ] +} + local "azure_boot_command_8_x86_64" { expression = [ "c", diff --git a/vm-scripts/gcp/almalinux_10.publish.json b/vm-scripts/gcp/almalinux_10.publish.json new file mode 100644 index 00000000..7c6683e3 --- /dev/null +++ b/vm-scripts/gcp/almalinux_10.publish.json @@ -0,0 +1,45 @@ +{{/* + Template to publish UEFI-enabled AlmaLinux images. + By default this template is setup to publish to the 'gce-image-builder' + project, the 'environment' variable can be used to publish to 'test', 'prod' + DeleteAfter is set to 180 days for all environments other than prod where no + time period is set. +*/}} +{ + "Name": "almalinux-10", + {{$work_project := printf "%q" "gce-image-builder" -}} + {{$endpoint := `"https://www.googleapis.com/compute/alpha/projects/"` -}} + {{$delete_after := `"24h*30*2"` -}} + {{if eq .environment "test" -}} + "WorkProject": {{$work_project}}, + "PublishProject": "almalinux-dev-images-469421", + "ComputeEndpoint": {{$endpoint}}, + "DeleteAfter": {{$delete_after}}, + {{- else if eq .environment "prod" -}} + "WorkProject": {{$work_project}}, + "PublishProject": "almalinux-cloud", + "ComputeEndpoint": {{$endpoint}}, + {{- else -}} + "WorkProject": {{$work_project}}, + "PublishProject": {{$work_project}}, + "ComputeEndpoint": {{$endpoint}}, + "DeleteAfter": {{$delete_after}}, + {{- end}} + {{$guest_features := `["UEFI_COMPATIBLE", "VIRTIO_SCSI_MULTIQUEUE", "SEV_CAPABLE", "SEV_SNP_CAPABLE", "SEV_LIVE_MIGRATABLE", "SEV_LIVE_MIGRATABLE_V2", "GVNIC", "IDPF", "TDX_CAPABLE"]` -}} + {{$time := trimPrefix .publish_version "v"}} + "Images": [ + { + "Family": "almalinux-10", + "Prefix": "almalinux-10", + "Description": "AlmaLinux, AlmaLinux, 10, x86_64 built on {{$time}}", + "Architecture": "X86_64", + "Licenses": [ + "projects/almalinux-cloud/global/licenses/almalinux-10" + ], + "Labels": { + "public-image": "true" + }, + "GuestOsFeatures": {{$guest_features}} + } + ] +} diff --git a/vm-scripts/gcp/almalinux_10_arm64.publish.json b/vm-scripts/gcp/almalinux_10_arm64.publish.json new file mode 100644 index 00000000..db3365fb --- /dev/null +++ b/vm-scripts/gcp/almalinux_10_arm64.publish.json @@ -0,0 +1,45 @@ +{{/* + Template to publish UEFI-enabled AlmaLinux images. + By default this template is setup to publish to the 'gce-image-builder' + project, the 'environment' variable can be used to publish to 'test', 'prod' + DeleteAfter is set to 180 days for all environments other than prod where no + time period is set. +*/}} +{ + "Name": "almalinux-10-arm64", + {{$work_project := printf "%q" "gce-image-builder" -}} + {{$endpoint := `"https://www.googleapis.com/compute/alpha/projects/"` -}} + {{$delete_after := `"24h*30*2"` -}} + {{if eq .environment "test" -}} + "WorkProject": {{$work_project}}, + "PublishProject": "almalinux-dev-images-469421", + "ComputeEndpoint": {{$endpoint}}, + "DeleteAfter": {{$delete_after}}, + {{- else if eq .environment "prod" -}} + "WorkProject": {{$work_project}}, + "PublishProject": "almalinux-cloud", + "ComputeEndpoint": {{$endpoint}}, + {{- else -}} + "WorkProject": {{$work_project}}, + "PublishProject": {{$work_project}}, + "ComputeEndpoint": {{$endpoint}}, + "DeleteAfter": {{$delete_after}}, + {{- end}} + {{$guest_features := `["UEFI_COMPATIBLE", "GVNIC", "IDPF"]` -}} + {{$time := trimPrefix .publish_version "v"}} + "Images": [ + { + "Family": "almalinux-10-arm64", + "Prefix": "almalinux-10-arm64", + "Description": "AlmaLinux, AlmaLinux, 10, aarch64 built on {{$time}}", + "Architecture": "ARM64", + "Licenses": [ + "projects/almalinux-cloud/global/licenses/almalinux-10" + ], + "Labels": { + "public-image": "true" + }, + "GuestOsFeatures": {{$guest_features}} + } + ] +} diff --git a/vm-scripts/gcp/almalinux_8.publish.json b/vm-scripts/gcp/almalinux_8.publish.json new file mode 100644 index 00000000..9e939981 --- /dev/null +++ b/vm-scripts/gcp/almalinux_8.publish.json @@ -0,0 +1,45 @@ +{{/* + Template to publish UEFI-enabled AlmaLinux images. + By default this template is setup to publish to the 'gce-image-builder' + project, the 'environment' variable can be used to publish to 'test', 'prod' + DeleteAfter is set to 180 days for all environments other than prod where no + time period is set. +*/}} +{ + "Name": "almalinux-8", + {{$work_project := printf "%q" "gce-image-builder" -}} + {{$endpoint := `"https://www.googleapis.com/compute/alpha/projects/"` -}} + {{$delete_after := `"24h*30*2"` -}} + {{if eq .environment "test" -}} + "WorkProject": {{$work_project}}, + "PublishProject": "almalinux-dev-images-469421", + "ComputeEndpoint": {{$endpoint}}, + "DeleteAfter": {{$delete_after}}, + {{- else if eq .environment "prod" -}} + "WorkProject": {{$work_project}}, + "PublishProject": "almalinux-cloud", + "ComputeEndpoint": {{$endpoint}}, + {{- else -}} + "WorkProject": {{$work_project}}, + "PublishProject": {{$work_project}}, + "ComputeEndpoint": {{$endpoint}}, + "DeleteAfter": {{$delete_after}}, + {{- end}} + {{$guest_features := `["UEFI_COMPATIBLE", "VIRTIO_SCSI_MULTIQUEUE", "SEV_CAPABLE", "SEV_LIVE_MIGRATABLE", "GVNIC", "IDPF"]` -}} + {{$time := trimPrefix .publish_version "v"}} + "Images": [ + { + "Family": "almalinux-8", + "Prefix": "almalinux-8", + "Description": "AlmaLinux, AlmaLinux, 8, x86_64 built on {{$time}}", + "Architecture": "X86_64", + "Licenses": [ + "projects/almalinux-cloud/global/licenses/almalinux-8" + ], + "Labels": { + "public-image": "true" + }, + "GuestOsFeatures": {{$guest_features}} + } + ] +} diff --git a/vm-scripts/gcp/almalinux_8_arm64.publish.json b/vm-scripts/gcp/almalinux_8_arm64.publish.json new file mode 100644 index 00000000..6b58565a --- /dev/null +++ b/vm-scripts/gcp/almalinux_8_arm64.publish.json @@ -0,0 +1,45 @@ +{{/* + Template to publish UEFI-enabled AlmaLinux images. + By default this template is setup to publish to the 'gce-image-builder' + project, the 'environment' variable can be used to publish to 'test', 'prod' + DeleteAfter is set to 180 days for all environments other than prod where no + time period is set. +*/}} +{ + "Name": "almalinux-8-arm64", + {{$work_project := printf "%q" "gce-image-builder" -}} + {{$endpoint := `"https://www.googleapis.com/compute/alpha/projects/"` -}} + {{$delete_after := `"24h*30*2"` -}} + {{if eq .environment "test" -}} + "WorkProject": {{$work_project}}, + "PublishProject": "almalinux-dev-images-469421", + "ComputeEndpoint": {{$endpoint}}, + "DeleteAfter": {{$delete_after}}, + {{- else if eq .environment "prod" -}} + "WorkProject": {{$work_project}}, + "PublishProject": "almalinux-cloud", + "ComputeEndpoint": {{$endpoint}}, + {{- else -}} + "WorkProject": {{$work_project}}, + "PublishProject": {{$work_project}}, + "ComputeEndpoint": {{$endpoint}}, + "DeleteAfter": {{$delete_after}}, + {{- end}} + {{$guest_features := `["UEFI_COMPATIBLE", "GVNIC", "IDPF"]` -}} + {{$time := trimPrefix .publish_version "v"}} + "Images": [ + { + "Family": "almalinux-8-arm64", + "Prefix": "almalinux-8-arm64", + "Description": "AlmaLinux, AlmaLinux, 8, aarch64 built on {{$time}}", + "Architecture": "ARM64", + "Licenses": [ + "projects/almalinux-cloud/global/licenses/almalinux-8" + ], + "Labels": { + "public-image": "true" + }, + "GuestOsFeatures": {{$guest_features}} + } + ] +} diff --git a/vm-scripts/gcp/almalinux_9.publish.json b/vm-scripts/gcp/almalinux_9.publish.json new file mode 100644 index 00000000..c34b53a0 --- /dev/null +++ b/vm-scripts/gcp/almalinux_9.publish.json @@ -0,0 +1,45 @@ +{{/* + Template to publish UEFI-enabled AlmaLinux images. + By default this template is setup to publish to the 'gce-image-builder' + project, the 'environment' variable can be used to publish to 'test', 'prod' + DeleteAfter is set to 180 days for all environments other than prod where no + time period is set. +*/}} +{ + "Name": "almalinux-9", + {{$work_project := printf "%q" "gce-image-builder" -}} + {{$endpoint := `"https://www.googleapis.com/compute/alpha/projects/"` -}} + {{$delete_after := `"24h*30*2"` -}} + {{if eq .environment "test" -}} + "WorkProject": {{$work_project}}, + "PublishProject": "almalinux-dev-images-469421", + "ComputeEndpoint": {{$endpoint}}, + "DeleteAfter": {{$delete_after}}, + {{- else if eq .environment "prod" -}} + "WorkProject": {{$work_project}}, + "PublishProject": "almalinux-cloud", + "ComputeEndpoint": {{$endpoint}}, + {{- else -}} + "WorkProject": {{$work_project}}, + "PublishProject": {{$work_project}}, + "ComputeEndpoint": {{$endpoint}}, + "DeleteAfter": {{$delete_after}}, + {{- end}} + {{$guest_features := `["UEFI_COMPATIBLE", "VIRTIO_SCSI_MULTIQUEUE", "SEV_CAPABLE", "SEV_SNP_CAPABLE", "SEV_LIVE_MIGRATABLE", "GVNIC", "IDPF", "TDX_CAPABLE"]` -}} + {{$time := trimPrefix .publish_version "v"}} + "Images": [ + { + "Family": "almalinux-9", + "Prefix": "almalinux-9", + "Description": "AlmaLinux, AlmaLinux, 9, x86_64 built on {{$time}}", + "Architecture": "X86_64", + "Licenses": [ + "projects/almalinux-cloud/global/licenses/almalinux-9" + ], + "Labels": { + "public-image": "true" + }, + "GuestOsFeatures": {{$guest_features}} + } + ] +} diff --git a/vm-scripts/gcp/almalinux_9_arm64.publish.json b/vm-scripts/gcp/almalinux_9_arm64.publish.json new file mode 100644 index 00000000..77558fe7 --- /dev/null +++ b/vm-scripts/gcp/almalinux_9_arm64.publish.json @@ -0,0 +1,45 @@ +{{/* + Template to publish UEFI-enabled AlmaLinux images. + By default this template is setup to publish to the 'gce-image-builder' + project, the 'environment' variable can be used to publish to 'test', 'prod' + DeleteAfter is set to 180 days for all environments other than prod where no + time period is set. +*/}} +{ + "Name": "almalinux-9-arm64", + {{$work_project := printf "%q" "gce-image-builder" -}} + {{$endpoint := `"https://www.googleapis.com/compute/alpha/projects/"` -}} + {{$delete_after := `"24h*30*2"` -}} + {{if eq .environment "test" -}} + "WorkProject": {{$work_project}}, + "PublishProject": "almalinux-dev-images-469421", + "ComputeEndpoint": {{$endpoint}}, + "DeleteAfter": {{$delete_after}}, + {{- else if eq .environment "prod" -}} + "WorkProject": {{$work_project}}, + "PublishProject": "almalinux-cloud", + "ComputeEndpoint": {{$endpoint}}, + {{- else -}} + "WorkProject": {{$work_project}}, + "PublishProject": {{$work_project}}, + "ComputeEndpoint": {{$endpoint}}, + "DeleteAfter": {{$delete_after}}, + {{- end}} + {{$guest_features := `["UEFI_COMPATIBLE", "GVNIC", "IDPF"]` -}} + {{$time := trimPrefix .publish_version "v"}} + "Images": [ + { + "Family": "almalinux-9-arm64", + "Prefix": "almalinux-9-arm64", + "Description": "AlmaLinux, AlmaLinux, 9, aarch64 built on {{$time}}", + "Architecture": "ARM64", + "Licenses": [ + "projects/almalinux-cloud/global/licenses/almalinux-9" + ], + "Labels": { + "public-image": "true" + }, + "GuestOsFeatures": {{$guest_features}} + } + ] +}