# Copyright (C) 2002-2026 Simon Josefsson
#
# This file is part of GNU SASL.
#
# This program is free software: you can redistribute it and/or modify
# it under the terms of the GNU General Public License as published by
# the Free Software Foundation, either version 3 of the License, or
# (at your option) any later version.
#
# This program is distributed in the hope that it will be useful,
# but WITHOUT ANY WARRANTY; without even the implied warranty of
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
# GNU General Public License for more details.
#
# You should have received a copy of the GNU General Public License
# along with this program.  If not, see <http://www.gnu.org/licenses/>.

variables:
  GIT_DEPTH: 250
  GNULIB_URL: https://gitlab.com/libidn/gnulib-mirror.git

stages:
 - build
 - release-reproduce
 - test
 - deploy

default:
  artifacts:
    expire_in: 2 weeks
    when: always
    paths:
    - "*.tar.gz"
    - ./**/*.log
    - ./*.log
    - ./config.h
    - ./out/$CI_JOB_NAME_SLUG/**

.gnulib-fetch:
  script:
  - GNULIB_REVISION=$(. bootstrap.conf >&2; echo $GNULIB_REVISION)
  - wget -nv https://gitlab.com/libidn/gnulib-mirror/-/archive/$GNULIB_REVISION/gnulib-mirror-$GNULIB_REVISION.tar.gz
  - gzip -cd gnulib-mirror-$GNULIB_REVISION.tar.gz | tar xf -
  - rm -fv gnulib-mirror-$GNULIB_REVISION.tar.gz
  - export GNULIB_SRCDIR=$PWD/gnulib-mirror-$GNULIB_REVISION

.save-artifacts:
  script:
  - (! command -v git > /dev/null) || git status
  - (! command -v git > /dev/null) || git diff --exit-code # nothing should change version controlled files
  - sha256sum *.tar.*
  - mkdir -pv out/$CI_JOB_NAME_SLUG/{src,log}
  - find config.h *.log tests/*.log -exec mv -v {} out/$CI_JOB_NAME_SLUG/log \;
  - mv -v *-src.tar.* out/$CI_JOB_NAME_SLUG/src/ || true
  - mv -v *.tar.* out/$CI_JOB_NAME_SLUG/

B-Guix:
  rules:
  - when: always # this job is used by merge request jobs tagged with 'needs' on this job
  image: registry.gitlab.com/debdistutils/guix/container:extra
  stage: build
  before_script:
  - cp -rL /gnu/store/*profile/etc/* /etc/
  - echo 'root:x:0:0:root:/:/bin/sh' > /etc/passwd
  - echo 'root:x:0:' > /etc/group
  - export HOME=/
  - guix describe
  script:
  - !reference [.gnulib-fetch, script]
  - time ./bootstrap --no-git
  - time ./configure --enable-gcc-warnings=error
  - time make -j$(nproc) syntax-check
  - time make -C doc compare-makefile
  - time make -j$(nproc) check V=1 VERBOSE=t
  - time make V=1 dist
  - !reference [.save-artifacts, script]

B-gcc:
  image: gcc:latest
  stage: build
  before_script:
  - gcc --version
  - time apt-get update -q
  - time apt-get install -y -q eatmydata
  - time eatmydata apt-get install -y -q --no-install-recommends wget ca-certificates make gcc git patch autoconf automake libtool gettext autopoint gperf gengetopt help2man texinfo gtk-doc-tools libidn11-dev libntlm0-dev libgnutls28-dev libkrb5-dev valgrind
  script:
  - !reference [.gnulib-fetch, script]
  - time ./bootstrap --skip-po --no-git
  - time ./configure --enable-gcc-warnings=error CC="gcc -std=gnu2x" --with-gssapi-impl=mit
  - time make -k syntax-check
  - time make V=1 VERBOSE=t -j$(nproc) -k check
  - time make V=1 VERBOSE=t clean
  - time ./configure --enable-gcc-warnings CC="gcc -std=c23" --with-gssapi-impl=mit
  - time make V=1 VERBOSE=t -j$(nproc) -k all check
  - time make V=1 VERBOSE=t -j$(nproc) dist
  - !reference [.save-artifacts, script]

B-clang:
  image: silkeh/clang:latest
  stage: build
  before_script:
  - clang --version
  - time apt-get update -q
  - time apt-get install -y -q eatmydata
  - time eatmydata apt-get install -y -q --no-install-recommends wget ca-certificates make gcc git patch autoconf automake libtool gettext autopoint gperf gengetopt help2man texinfo gtk-doc-tools libidn11-dev libntlm0-dev libgnutls28-dev libkrb5-dev valgrind
  script:
  - !reference [.gnulib-fetch, script]
  - time ./bootstrap --skip-po --no-git
  - time ./configure --enable-gcc-warnings=error CC="clang -std=gnu2x" CFLAGS="-gdwarf-4 -O2" --with-gssapi-impl=mit
  - time make -k syntax-check
  - time make V=1 VERBOSE=t -j$(nproc) -k check
  - time make V=1 VERBOSE=t clean
  - time ./configure --enable-gcc-warnings=error CC="clang -std=c23" CFLAGS="-gdwarf-4 -O2" --with-gssapi-impl=mit
  - time make V=1 VERBOSE=t -j$(nproc) -k all check
  - time make V=1 VERBOSE=t dist
  - !reference [.save-artifacts, script]

.almarocky: &almarocky
  stage: build
  tags: [ saas-linux-medium-amd64 ]
  variables:
    PKGS: wget git make diffutils patch autoconf automake libtool gettext-devel gperf valgrind gengetopt help2man gtk-doc texinfo gnutls-devel file hostname
  before_script:
  - cat /etc/os-release
  - time dnf install -y epel-release
  - time dnf --enablerepo=$(dnf repolist --all | grep crb > /dev/null && echo crb || echo powertools) install -y ${PKGS}
  - cc --version
  script:
  - !reference [.gnulib-fetch, script]
  - time ./bootstrap --skip-po --no-git
  - sed -i -e '/MAKEFLAGS) dvi/d' Makefile.in # AM_DISTCHECK_DVI_TARGET=
  - time ./configure --enable-gcc-warnings=error
  - time make syntax-check
  - time make -j$(nproc) V=1 VERBOSE=t check
  - time make -j$(nproc) V=1 VERBOSE=t distcheck
  - !reference [.save-artifacts, script]

B-AlmaLinux8:
  image: almalinux:8
  extends: .almarocky

B-RockyLinux8:
  image: rockylinux:8
  extends: .almarocky

B-AlmaLinux9:
  image: almalinux:9
  extends: .almarocky

B-RockyLinux9:
  image: rockylinux:9
  extends: .almarocky

.pureosdebian: &pureosdebian
  tags: [ saas-linux-medium-amd64 ]
  stage: build
  variables:
    DEBIAN_FRONTEND: noninteractive
  before_script:
  - cat /etc/os-release
  - time apt-get update -q
  - time apt-get install -y -q eatmydata
  - time eatmydata apt-get install -y -q --no-install-recommends wget ca-certificates make gcc git patch autoconf automake libtool gettext autopoint gperf gengetopt help2man texinfo gtk-doc-tools libidn11-dev libntlm0-dev libgnutls28-dev libkrb5-dev valgrind
  script:
  - !reference [.gnulib-fetch, script]
  - time ./bootstrap --skip-po --no-git
  - time ./configure --enable-gcc-warnings=error --with-gssapi-impl=mit
  - time make syntax-check
  - time make -j$(nproc) V=1 VERBOSE=t check
  - make -C doc compare-makefile
  - time make -j$(nproc) V=1 VERBOSE=t distcheck AM_DISTCHECK_DVI_TARGET=
  - !reference [.save-artifacts, script]

B-PureOS10:
  image: pureos/byzantium:latest
  extends: .pureosdebian

B-Debian11:
  image: debian:11-slim
  extends: .pureosdebian

B-Devuan5:
  image: devuan/devuan:daedalus
  variables:
    WERROR_CFLAGS: "-Wno-error=use-after-free"
  extends: .pureosdebian

B-Debian12:
  image: debian:12-slim
  variables:
    WERROR_CFLAGS: "-Wno-error=use-after-free"
  extends: .pureosdebian

B-Devuan6:
  image: devuan/devuan:excalibur
  extends: .pureosdebian

B-Debian13:
  image: debian:13-slim
  extends: .pureosdebian

.trisquelubuntu: &trisquelubuntu
  tags: [ saas-linux-medium-amd64 ]
  stage: build
  variables:
    DEBIAN_FRONTEND: noninteractive
  before_script:
  - cat /etc/os-release
  - sed -i 's,http://archive.trisquel.info/trisquel,http://ftp.acc.umu.se/mirror/trisquel/packages,' /etc/apt/sources.list
  - time apt-get update -q
  - time apt-get install -y -q eatmydata
  - time eatmydata apt-get install -y -q --no-install-recommends wget ca-certificates make gcc git patch autoconf automake libtool gettext autopoint gperf gengetopt help2man texinfo gtk-doc-tools libidn11-dev libntlm0-dev
  script:
  - !reference [.gnulib-fetch, script]
  - time ./bootstrap --skip-po --no-git
  - time ./configure --enable-gcc-warnings=error --enable-valgrind-tests
  - time make syntax-check
  - time make -j$(nproc) V=1 VERBOSE=t check
  - make -C doc compare-makefile
  - time make -j$(nproc) V=1 VERBOSE=t distcheck AM_DISTCHECK_DVI_TARGET=
  - !reference [.save-artifacts, script]

B-Trisquel11:
  image: kpengboy/trisquel:11.0
  extends: .trisquelubuntu

B-Ubuntu2204:
  image: ubuntu:22.04
  extends: .trisquelubuntu

B-Trisquel12:
  image: kpengboy/trisquel:12.0
  extends: .trisquelubuntu

B-Ubuntu2404:
  image: ubuntu:24.04
  extends: .trisquelubuntu

# https://www.synopsys.com/blogs/software-security/integrating-coverity-scan-with-gitlab-ci/
Coverity:
  rules:
  - if: $CI_PIPELINE_SOURCE == "merge_request_event"
    when: never
  - if: $CI_COMMIT_REF_PROTECTED == "true"
  - when: manual
  image: $CI_REGISTRY/gsasl/build-images:Debian11
  stage: build
  allow_failure: true
  script:
  - test -n "$COVERITY_SCAN_TOKEN" && test -n "$COVERITY_SCAN_PROJECT_NAME"
  - curl -o /tmp/cov-analysis-linux64.tgz https://scan.coverity.com/download/linux64
    --form project=$COVERITY_SCAN_PROJECT_NAME --form token=$COVERITY_SCAN_TOKEN
  - sha1sum /tmp/cov-analysis-linux64.tgz
  - tar xfz /tmp/cov-analysis-linux64.tgz
  - !reference [.gnulib-fetch, script]
  - time ./bootstrap --skip-po --no-git
  - time ./configure --enable-gcc-warnings=error --with-gssapi-impl=mit CFLAGS="-g -Og"
  - cov-analysis-linux64-*/bin/cov-build --dir cov-int make check -j$(nproc)
  - tar cfz cov-int.tar.gz cov-int
  - curl https://scan.coverity.com/builds?project=$COVERITY_SCAN_PROJECT_NAME
    --form token=$COVERITY_SCAN_TOKEN --form email=$GITLAB_USER_EMAIL
    --form file=@cov-int.tar.gz --form version="`git describe --tags`"
    --form description="`git describe --tags` / $CI_COMMIT_TITLE / $CI_COMMIT_REF_NAME:$CI_PIPELINE_ID"
  artifacts:
    expire_in: 1 week
    paths:
      - cov-int/*.txt

# https://docs.gitlab.com/ee/user/application_security/sast/#customizing-the-sast-settings
sast:
  stage: build
include:
- template: Security/SAST.gitlab-ci.yml

# https://clang.llvm.org/docs/AddressSanitizer.html
# https://github.com/google/sanitizers/wiki/AddressSanitizer
# https://clang.llvm.org/docs/UndefinedBehaviorSanitizer.html
# https://clang.llvm.org/docs/LeakSanitizer.html
# https://github.com/google/sanitizers/wiki/AddressSanitizerLeakSanitizer
# https://github.com/google/sanitizers/wiki/AddressSanitizerFlags
F44-clang-ASan-UBSan:
  image: fedora:44
  stage: build
  before_script:
  - dnf -y update
  - dnf -y install git make diffutils file hostname patch autoconf automake libtool gettext-devel texinfo help2man gtk-doc gengetopt gperf wget gnutls-devel
  - dnf -y install make clang diffutils gnutls-devel gnutls-utils iproute dovecot
  - dnf -y install https://github.com/rpmsphere/noarch/raw/master/r/rpmsphere-release-44-1.noarch.rpm
  - dnf -y install mailutils-libs mailutils-imap4d || true
  script:
  - !reference [.gnulib-fetch, script]
  - time ./bootstrap --skip-po --no-git
  - ./configure --with-gssapi-impl=no --enable-gcc-warnings=error CC=clang CFLAGS="-g -O1 -fsanitize=undefined -fsanitize=address -fsanitize-address-use-after-scope -fno-sanitize-recover=undefined -fno-omit-frame-pointer -fno-optimize-sibling-calls"
  - ASAN_OPTIONS=detect_stack_use_after_return=1:check_initialization_order=1:strict_init_order=1 make check VERBOSE=t V=1
  - grep '^PASS gsasl-mailutils-cram' tests/gsasl-mailutils-cram.log
  - grep '^PASS gsasl-mailutils-tls' tests/gsasl-mailutils-tls.log

# https://clang.llvm.org/docs/AddressSanitizer.html
# https://github.com/google/sanitizers/wiki/AddressSanitizer
# https://clang.llvm.org/docs/UndefinedBehaviorSanitizer.html
# https://clang.llvm.org/docs/LeakSanitizer.html
# https://github.com/google/sanitizers/wiki/AddressSanitizerLeakSanitizer
# https://github.com/google/sanitizers/wiki/AddressSanitizerFlags
F39-clang-ASan-UBSan-mit:
  when: manual # known memory leak in gs2krb5-mailutils
  allow_failure: true
  image: fedora:39
  stage: build
  before_script:
  - dnf -y update
  - dnf -y install git make diffutils file hostname patch autoconf automake libtool gettext-devel texinfo help2man gtk-doc gengetopt gperf wget gnutls-devel
  - dnf -y install make clang diffutils krb5-devel gnutls-devel gnutls-utils krb5-server krb5-workstation iproute dovecot
  - dnf -y install https://github.com/rpmsphere/noarch/raw/master/r/rpmsphere-release-40-1.noarch.rpm
  - dnf -y install mailutils-libs mailutils-imap4d
  script:
  - !reference [.gnulib-fetch, script]
  - time ./bootstrap --skip-po --no-git
  - ./configure --with-gssapi-impl=mit --enable-gcc-warnings=error CC=clang CFLAGS="-g -O1 -fsanitize=undefined -fsanitize=address -fsanitize-address-use-after-scope -fno-sanitize-recover=undefined -fno-omit-frame-pointer -fno-optimize-sibling-calls"
  - ASAN_OPTIONS=detect_stack_use_after_return=1:check_initialization_order=1:strict_init_order=1 make check VERBOSE=t V=1
  - grep '^PASS gsasl-dovecot-gssapi' tests/gsasl-dovecot-gssapi.log
  - grep '^PASS gsasl-mailutils-cram' tests/gsasl-mailutils-cram.log
  - grep '^PASS gsasl-mailutils-tls' tests/gsasl-mailutils-tls.log
  - grep '^PASS gsasl-mailutils-gs2krb5-gssapi' tests/gsasl-mailutils-gs2krb5-gssapi.log

D-coverage-cyclo-doxygen:
  image: ubuntu:24.04
  stage: build
  before_script:
  - time apt-get update -q
  - time apt-get install -y -q eatmydata
  - time eatmydata apt-get install -y -q --no-install-recommends wget ca-certificates make gcc git patch autoconf automake libtool gettext autopoint gperf gengetopt help2man texinfo gtk-doc-tools libidn11-dev libntlm0-dev
  - time eatmydata apt-get install -y -q --no-install-recommends libglib2.0-dev
  - time eatmydata apt-get install -y -q --no-install-recommends iproute2 dovecot-imapd dovecot-gssapi krb5-kdc krb5-admin-server libkrb5-dev libgnutls28-dev gnutls-bin mailutils-imap4d
  - time eatmydata apt-get install -y -q valgrind lcov pmccabe doxygen-latex psutils
  - /usr/sbin/imap4d --version
  script:
  - !reference [.gnulib-fetch, script]
  - time ./bootstrap --skip-po --no-git
  - ./configure --with-gssapi-impl=mit --enable-gcc-warnings=error
  - (cd doc/doxygen && doxygen)
  - make -C doc/doxygen/latex pdf
  - make init-coverage
  - make build-coverage VERBOSE=t
  - grep '^PASS gsasl-dovecot-gssapi' tests/gsasl-dovecot-gssapi.log
  - grep '^PASS gsasl-mailutils-cram' tests/gsasl-mailutils-cram.log
  - grep '^PASS gsasl-mailutils-tls' tests/gsasl-mailutils-tls.log
  - grep '^PASS gsasl-mailutils-gs2krb5-gssapi' tests/gsasl-mailutils-gs2krb5-gssapi.log
  - make syntax-check
  - lcov --remove doc/coverage/gsasl.info '/usr/include/*' '*/doc/*' '*/gl/*' -o doc/coverage/gsasl-filtered.info
  - make gen-coverage PACKAGE=gsasl-filtered
  - cp -rv doc/coverage .
  - make -C doc/cyclo/ cyclo-gsasl.html
  - mkdir cyclo
  - cp -v doc/cyclo/cyclo-gsasl.html cyclo/index.html
  - cp -rv doc/doxygen/html doxygen
  - cp -v doc/doxygen/latex/refman.pdf doxygen/gsasl.pdf
  - git diff --exit-code # nothing should change version controlled files
  artifacts:
    when: on_success
    paths:
      - coverage
      - cyclo
      - doxygen

Fedora-clanganalyzer:
  image: fedora:latest
  stage: build
  before_script:
  - dnf update -y
  - dnf install -y git make diffutils file hostname patch autoconf automake libtool gettext-devel texinfo texinfo-tex texlive texlive-supertabular texlive-framed texlive-morefloats texlive-quotchap texlive-epstopdf help2man gtk-doc gengetopt gperf wget dblatex gnutls-devel
  - dnf install -y clang clang-analyzer
  script:
  - !reference [.gnulib-fetch, script]
  - time ./bootstrap --skip-po --no-git
  - time scan-build ./configure --enable-gcc-warning --disable-silent-rules --enable-gtk-doc --enable-gtk-doc-pdf
  - time scan-build -o clang-analyzer make V=1
  - time make web-manual
  - time make distcheck VERBOSE=t
  - git diff --exit-code # nothing should change version controlled files
  artifacts:
    when: on_success
    paths:
    - "*.tar.gz"
    - ./*.log
    - ./config.h
    - ./**/*.log
    - clang-analyzer
    - doc/reference
    - doc/manual

B-Mingw64-wine:
  image: debian:12-slim
  tags: [ saas-linux-medium-amd64 ]
  stage: build
  before_script:
  - time apt-get update -q
  - time apt-get install -y -q eatmydata
  - time eatmydata apt-get install -y -q --no-install-recommends wget ca-certificates make gcc git patch autoconf automake libtool gettext autopoint gperf gengetopt help2man texinfo gtk-doc-tools libidn11-dev libntlm0-dev libgnutls28-dev libkrb5-dev valgrind
  - time eatmydata apt-get install -y -q make mingw-w64 wine wine64 binfmt-support wine-binfmt
  - update-binfmts --enable wine
  variables:
    WERROR_CFLAGS: "-Wno-error=unused-value -Wno-error=suggest-attribute=format -Wno-error=use-after-free"
  script:
  - !reference [.gnulib-fetch, script]
  - time ./bootstrap --skip-po --no-git
  - ./configure --host=x86_64-w64-mingw32 --enable-gcc-warnings=error
  - make -k -j$(nproc) check V=1 VERBOSE=t

B-Mingw64-cross:
  image: debian:12-slim
  tags: [ saas-linux-medium-amd64 ]
  stage: build
  before_script:
  - time apt-get update -q
  - time apt-get install -y -q eatmydata
  - time eatmydata apt-get install -y -q --no-install-recommends wget ca-certificates make gcc git patch autoconf automake libtool gettext autopoint gperf gengetopt help2man texinfo
  - time eatmydata apt-get install -y -q mingw-w64
  variables:
    WERROR_CFLAGS: "-Wno-error=unused-value -Wno-error=suggest-attribute=format -Wno-error=use-after-free"
  script:
  - !reference [.gnulib-fetch, script]
  - time ./bootstrap --skip-po --no-git
  - mkdir first-cross-should-fail
  - cd first-cross-should-fail
  - ../configure --host=x86_64-w64-mingw32 --enable-gcc-warnings=error
  - (! make -j$(nproc) V=1 VERBOSE=t)
  - cd ../
  - ./configure --enable-gcc-warnings=error
  - make -j$(nproc) V=1 VERBOSE=t
  - make clean
  - ./configure --host=x86_64-w64-mingw32 --enable-gcc-warnings=error
  - make -j$(nproc) V=1 VERBOSE=t
  - (! make -j$(nproc) check V=1 VERBOSE=t)
  - time eatmydata apt-get install -y -q wine wine64 binfmt-support wine-binfmt
  - update-binfmts --enable wine
  - make -k -j$(nproc) check V=1 VERBOSE=t

B-Alpine-mold-arm64:
  image: alpine:latest
  tags: [ saas-linux-small-arm64 ]
  stage: build
  before_script:
  - cat /etc/os-release
  - apk update
  - apk add gcc make libc-dev git wget autoconf automake libtool gettext-dev gperf gengetopt patch coreutils mold help2man texinfo
  script:
  - !reference [.gnulib-fetch, script]
  - time ./bootstrap --skip-po --no-git
  - time ./configure --enable-gcc-warnings=error CC='cc -fuse-ld=mold'
  - time make -j$(nproc) syntax-check
  - time make -j$(nproc) V=1
  - time make -j$(nproc) check V=1 VERBOSE=t 2>&1 | tee build.log
  - git diff --exit-code # nothing should change version controlled files
  - (! grep -E 'mold. warning' build.log)
  - grep 'mold ' lib/src/.libs/libgsasl.so

OpenBSD:
  rules:
  - if: $CI_COMMIT_BRANCH == $CI_DEFAULT_BRANCH
  - when: manual
  tags: [ openbsd ]
  needs: [B-Guix]
  stage: test
  before_script:
  - uname -a
  - sysctl hw
  script:
  - gzip -cd out/b-guix/*-*.tar.gz | tar xf -
  - cd $(gzip -cd out/b-guix/*-*.tar.gz | tar tf - | head -n1)
  - time ./configure --enable-gcc-warnings
  - time make check V=1 VERBOSE=t

# https://docs.gitlab.com/ee/ci/runners/saas/windows_saas_runner.html
B-Windows-UCRT64:
  tags: [ saas-windows-medium-amd64 ]
  stage: build
  variables:
    WERROR_CFLAGS: "-Wno-error=unused-value -Wno-error=suggest-attribute=format -Wno-error=use-after-free"
  script: # https://www.msys2.org/docs/ci/#other-systems
  - wget.exe -nv -O msys2.exe https://github.com/msys2/msys2-installer/releases/download/nightly-x86_64/msys2-base-x86_64-latest.sfx.exe
  - ./msys2.exe -y -oC:\
  - Remove-Item msys2.exe
  - $env:CHERE_INVOKING = 'yes'
  - $env:MSYSTEM = 'UCRT64' # https://www.msys2.org/docs/environments/
  - C:\msys64\usr\bin\bash -lc ' '
  - C:\msys64\usr\bin\bash -lc 'pacman --noconfirm -Syuu'
  - C:\msys64\usr\bin\bash -lc 'pacman --noconfirm -Syuu'
  - |
    C:\msys64\usr\bin\bash -lcx '
    time pacman --noconfirm -Syu git autoconf automake libtool make mingw-w64-ucrt-x86_64-gcc python help2man gengetopt gperf patch gettext-devel texinfo
    # https://docs.github.com/en/get-started/getting-started-with-git/configuring-git-to-handle-line-endings
    file configure.ac
    git config --global core.autocrlf false
    git config --global core.eol lf
    git rm -rf --cached . | tail
    git reset --hard HEAD
    git status
    git describe
    file configure.ac
    GNULIB_REVISION=$(. bootstrap.conf >&2; echo $GNULIB_REVISION)
    wget -nv https://gitlab.com/libidn/gnulib-mirror/-/archive/$GNULIB_REVISION/gnulib-mirror-$GNULIB_REVISION.tar.gz
    tar xfa gnulib-mirror-$GNULIB_REVISION.tar.gz
    rm -fv gnulib-mirror-$GNULIB_REVISION.tar.gz
    export GNULIB_SRCDIR=gnulib-mirror-$GNULIB_REVISION
    time ./bootstrap --skip-po --no-git
    time ./configure --enable-gcc-warnings=error
    time make -j$(nproc) V=1 -k check VERBOSE=t'
  - C:\msys64\usr\bin\bash -lc 'grep ^PASS tests/version.log'

Windows-MSYS:
  tags: [ saas-windows-medium-amd64 ]
  stage: test
  needs: [B-Guix]
  variables:
    WERROR_CFLAGS: "-Wno-error=unused-value -Wno-error=suggest-attribute=format -Wno-error=use-after-free -Wno-error=attributes"
  script: # https://www.msys2.org/docs/ci/#other-systems
  - wget.exe -nv -O msys2.exe https://github.com/msys2/msys2-installer/releases/download/nightly-x86_64/msys2-base-x86_64-latest.sfx.exe
  - ./msys2.exe -y -oC:\
  - Remove-Item msys2.exe
  - $env:CHERE_INVOKING = 'yes'
  - $env:MSYSTEM = 'MSYS' # https://www.msys2.org/docs/environments/
  - C:\msys64\usr\bin\bash -lc ' '
  - C:\msys64\usr\bin\bash -lc 'pacman --noconfirm -Syuu'
  - C:\msys64\usr\bin\bash -lc 'pacman --noconfirm -Syuu'
  - |
    C:\msys64\usr\bin\bash -lcx '
    time pacman --noconfirm -Syu make gcc
    tar xfa out/b-guix/*-*.tar.gz
    cd $(tar tfa out/b-guix/*-*.tar.gz | head -n1)
    time ./configure --enable-gcc-warnings=error
    time make -j$(nproc) V=1 -k check VERBOSE=t'
  - C:\msys64\usr\bin\bash -lc 'grep ^PASS */tests/version.log'

Windows-MINGW64:
  tags: [ saas-windows-medium-amd64 ]
  needs: [B-Guix]
  variables:
     WERROR_CFLAGS: "-Wno-error=unused-value -Wno-error=suggest-attribute=format -Wno-error=use-after-free"
  script: # https://www.msys2.org/docs/ci/#other-systems
  - wget.exe -nv -O msys2.exe https://github.com/msys2/msys2-installer/releases/download/nightly-x86_64/msys2-base-x86_64-latest.sfx.exe
  - ./msys2.exe -y -oC:\
  - Remove-Item msys2.exe
  - $env:CHERE_INVOKING = 'yes'
  - $env:MSYSTEM = 'MINGW64' # https://www.msys2.org/docs/environments/
  - C:\msys64\usr\bin\bash -lc ' '
  - C:\msys64\usr\bin\bash -lc 'pacman --noconfirm -Syuu'
  - C:\msys64\usr\bin\bash -lc 'pacman --noconfirm -Syuu'
  - |
    C:\msys64\usr\bin\bash -lcx '
    time pacman --noconfirm -Syu make mingw-w64-x86_64-gcc
    tar xfa out/b-guix/*-*.tar.gz
    cd $(tar tfa out/b-guix/*-*.tar.gz | head -n1)
    time ./configure --enable-gcc-warnings=error
    time make -j$(nproc) V=1 -k check VERBOSE=t'
  - C:\msys64\usr\bin\bash -lc 'grep ^PASS */tests/version.log'

# https://docs.gitlab.com/ci/runners/hosted_runners/macos/
B-macOS14Xcode15-mit:
  rules:
  - if: $CI_COMMIT_BRANCH == $CI_DEFAULT_BRANCH
  - when: manual
  stage: build
  image: macos-14-xcode-15
  tags: [ saas-macos-medium-m1 ]
  variables:
    HOMEBREW_NO_AUTO_UPDATE: 1
    HOMEBREW_NO_INSTALL_UPGRADE: 1
    HOMEBREW_NO_INSTALL_CLEANUP: 1
    HOMEBREW_NO_INSTALLED_DEPENDENTS_CHECK: 1
  before_script:
  - brew install autoconf automake wget libtool gengetopt help2man texinfo
  script:
  - !reference [.gnulib-fetch, script]
  - time ./bootstrap --no-git --skip-po
  - time ./configure --enable-gcc-warnings=error --with-gssapi-impl=mit WERROR_CFLAGS=-Wno-error=deprecated-declarations
  - make syntax-check
  - time make -j$(nproc) check -k V=1 VERBOSE=t
  - time make V=1 dist
  - !reference [.save-artifacts, script]

B-macOS15Xcode16-heimdal:
  rules:
  - if: $CI_COMMIT_BRANCH == $CI_DEFAULT_BRANCH
  - when: manual
  stage: build
  image: macos-15-xcode-16
  tags: [ saas-macos-large-m2pro ]
  variables:
    HOMEBREW_NO_AUTO_UPDATE: 1
    HOMEBREW_NO_INSTALL_UPGRADE: 1
    HOMEBREW_NO_INSTALL_CLEANUP: 1
    HOMEBREW_NO_INSTALLED_DEPENDENTS_CHECK: 1
  before_script:
  - brew install autoconf automake wget libtool gengetopt help2man texinfo
  script:
  - !reference [.gnulib-fetch, script]
  - time ./bootstrap --no-git --skip-po
  - time ./configure --enable-gcc-warnings=error --with-gssapi-impl=heimdal WERROR_CFLAGS=-Wno-error=deprecated-declarations
  - make syntax-check
  - time make -j$(nproc) check -k V=1 VERBOSE=t
  - time make V=1 dist
  - !reference [.save-artifacts, script]

macOS15Xcode16-mit:
  rules:
  - if: $CI_COMMIT_BRANCH == $CI_DEFAULT_BRANCH
  - when: manual
  stage: test
  image: macos-15-xcode-16
  tags: [ saas-macos-medium-m1 ]
  needs: [B-Guix]
  script:
  - tar xfz out/b-guix/*-*.tar.gz
  - cd $(tar tfz out/b-guix/*-*.tar.gz | head -n1)
  - ./configure --enable-gcc-warnings=error --with-gssapi-impl=mit WERROR_CFLAGS=-Wno-error=deprecated-declarations
  - make syntax-check
  - time make -j$(nproc) check V=1 VERBOSE=t

macOS15Xcode16-heimdal:
  rules:
  - if: $CI_COMMIT_BRANCH == $CI_DEFAULT_BRANCH
  - when: manual
  stage: test
  image: macos-15-xcode-16
  tags: [ saas-macos-medium-m1 ]
  needs: [B-Guix]
  script:
  - tar xfz out/b-guix/*-*.tar.gz
  - cd $(tar tfz out/b-guix/*-*.tar.gz | head -n1)
  - ./configure --enable-gcc-warnings=error --with-gssapi-impl=heimdal WERROR_CFLAGS=-Wno-error=deprecated-declarations
  - make syntax-check
  - time make -j$(nproc) check V=1 VERBOSE=t

macOS15Xcode16-framework:
  rules:
  - if: $CI_COMMIT_BRANCH == $CI_DEFAULT_BRANCH
  - when: manual
  stage: test
  image: macos-15-xcode-16
  tags: [ saas-macos-medium-m1 ]
  needs: [B-Guix]
  script:
  - tar xfz out/b-guix/*-*.tar.gz
  - cd $(tar tfz out/b-guix/*-*.tar.gz | head -n1)
  - ./configure --enable-gcc-warnings=error --with-gssapi-impl=framework
  - make syntax-check
  - time make -j$(nproc) check V=1 VERBOSE=t

.pages:
  image: alpine:latest
  stage: deploy
  needs: ["D-coverage-cyclo-doxygen", "Fedora-clanganalyzer", "B-Guix"]
  script:
    - mkdir -v public public/source
    - mv coverage/ cyclo/ doxygen/ public/
    - mv clang-analyzer/* public/clang-analyzer
    - mv doc/manual public/manual
    - mv doc/reference/html public/reference
    - mv doc/reference/gsasl.pdf public/reference/
    - mv out/b-guix/*.tar.gz public/source/
    - (cd public/source && ln -s *.tar.gz gsasl-latest.tar.gz)
    - mv out/b-guix/src/*.tar.gz public/source/
    - (cd public/source && ln -s *-src.tar.gz gsasl-latest-src.tar.gz)
  artifacts:
    paths:
    - public
    expire_in: 30 days

pages:
  extends: .pages
  only:
    - master

pages-test:
  extends: .pages
  except:
    - master

0-compare:
  image: alpine:latest
  stage: release-reproduce
  needs: [ B-AlmaLinux8, B-AlmaLinux9, B-RockyLinux8, B-RockyLinux9, B-Trisquel11, B-Trisquel12, B-Ubuntu2204, B-Ubuntu2404, B-PureOS10, B-Debian11, B-Devuan5, B-Devuan6, B-Debian12, B-Debian13, B-gcc, B-clang, B-Guix, R-Guix, R-Debian12, R-Debian13, R-Ubuntu2404, R-Ubuntu2604, S-Trisquel10, S-Ubuntu2004 ]
  script:
  - cd out
  - sha256sum */*.tar.* */*/*.tar.* | sort | grep    -- -src.tar.
  - sha256sum */*.tar.* */*/*.tar.* | sort | grep -v -- -src.tar.
  - sha256sum */*.tar.* */*/*.tar.* | sort | uniq -c -w64 | sort -rn
  - sha256sum */*.tar.* */*/*.tar.* | grep    -- -src.tar. | sort | uniq -c -w64 | grep -v '^      1 '
  - sha256sum */*.tar.* */*/*.tar.* | grep -v -- -src.tar. | sort | uniq -c -w64 | grep -v '^      1 '
# Confirm modern git-archive tarball reproducibility
  - cmp b-almalinux8/src/*.tar.gz b-almalinux9/src/*.tar.gz
  - cmp b-almalinux8/src/*.tar.gz b-debian12/src/*.tar.gz
  - cmp b-almalinux8/src/*.tar.gz b-devuan5/src/*.tar.gz
  - cmp b-almalinux8/src/*.tar.gz b-devuan6/src/*.tar.gz
  - cmp b-almalinux8/src/*.tar.gz b-rockylinux8/src/*.tar.gz
  - cmp b-almalinux8/src/*.tar.gz b-rockylinux9/src/*.tar.gz
  - cmp b-almalinux8/src/*.tar.gz b-trisquel12/src/*v2.*.tar.gz
  - cmp b-almalinux8/src/*.tar.gz r-debian12/src/*.tar.gz
  - cmp b-almalinux8/src/*.tar.gz r-debian13/src/*.tar.gz
  - cmp b-almalinux8/src/*.tar.gz r-guix/src/*.tar.gz
  - cmp b-almalinux8/src/*.tar.gz r-ubuntu2404/src/*v2.*.tar.gz
  - cmp b-almalinux8/src/*.tar.gz r-ubuntu2604/src/*v2.*.tar.gz
# Confirm old git-archive (export-subst but long git describe) tarball reproducibility
  - cmp b-trisquel11/src/*.tar.gz b-ubuntu2204/src/*.tar.gz
# Confirm really old git-archive (no export-subst) tarball reproducibility
  - cmp b-debian11/src/*.tar.gz b-pureos10/src/*.tar.gz
# Confirm 'make dist' generated tarball reproducibility
  - cmp b-almalinux8/*.tar.gz b-rockylinux8/*.tar.gz || true # flaky
  - cmp b-almalinux9/*.tar.gz b-rockylinux9/*.tar.gz
  - cmp b-pureos10/*.tar.gz b-debian11/*.tar.gz
  - cmp b-devuan5/*.tar.gz b-debian12/*.tar.gz
  - cmp b-devuan6/*.tar.gz b-debian13/*.tar.gz
  - cmp b-debian13/*.tar.gz r-debian13/*.tar.gz
  - cmp b-trisquel11/*.tar.gz b-ubuntu2204/*.tar.gz
  - cmp b-trisquel12/*.tar.gz b-ubuntu2404/*.tar.gz
  - cmp b-guix/*.tar.gz r-guix/*.tar.gz
# Confirm 'make dist' from git-archive tarball reproducibility
  - cmp s-trisquel10/*.tar.gz s-ubuntu2004/*.tar.gz
  artifacts:
    expire_in: 2 weeks
    when: always
    paths:
    - ./out/**

R-Guix:
  tags: [ saas-linux-medium-amd64 ]
  image: registry.gitlab.com/debdistutils/guix/container:extra
  stage: release-reproduce
  needs: []
  before_script:
  - cp -rL /gnu/store/*profile/etc/* /etc/
  - echo 'root:x:0:0:root:/:/bin/sh' > /etc/passwd
  - echo 'root:x:0:' > /etc/group
  - export HOME=/
  - guix describe
  script:
  - !reference [.gnulib-fetch, script]
  - time ./bootstrap --no-git
  - time ./configure
  - time make V=1 syntax-check
  - time make -j$(nproc) check V=1 VERBOSE=t
  - time make -j$(nproc) dist V=1 VERBOSE=t
  - git status
  - git diff --exit-code
  - gpg --batch --passphrase '' --quick-gen-key pipeline@example.org
  - git checkout -B cibranch
  - git config user.email "pipeline@example.org"
  - git config user.name "Pipeline Builder"
  - git config user.signingkey pipeline@example.org
  - |
    if test -z "$CI_COMMIT_TAG"; then
      sed -i '3i * Noteworthy changes in release ?.? (????-??-??) [?]\n\n** WARNING This release was prepared automatically with no testing.\n' NEWS
      git commit -m "Warn about automatic release." NEWS
      relver='23.42.17'
      reltyp='alpha'
    else # maintainer ran release-commit
      relver=$(cat NEWS | sed -n -e 's/.*release \([0-9.]\+\) (....-..-..) \[\(.*\)\].*/\1/p' | head -1)
      reltyp=$(cat NEWS | sed -n -e 's/.*release \([0-9.]\+\) (....-..-..) \[\(.*\)\].*/\2/p' | head -1)
    fi
  - test -n "$CI_COMMIT_TAG" || make release-commit RELEASE="$relver $reltyp"
  - make release RELEASE="$relver $reltyp" V=1 VERBOSE=t AM_DISTCHECK_DVI_TARGET=
  - cat -n ~/announce-*
  - git diff --exit-code # nothing should change version controlled files
  - sha256sum *.tar.*
  - mkdir -pv out/$CI_JOB_NAME_SLUG/{src,rel,log}
  - find config.h *.log tests/*.log -exec mv -v {} out/$CI_JOB_NAME_SLUG/log \;
  - test -n "$CI_COMMIT_TAG" || mv -v *23.42.17* out/$CI_JOB_NAME_SLUG/rel/
  - mv -v *-src.tar.* out/$CI_JOB_NAME_SLUG/src/
  - mv -v *.tar.* ~/announce-* out/$CI_JOB_NAME_SLUG/

R-Debian12:
  tags: [ saas-linux-medium-amd64 ]
  image: debian:12-slim
  stage: release-reproduce
  needs: []
  before_script:
  - cat /etc/os-release
  - time apt-get update -q
  - time apt-get install -y -q eatmydata
  - time eatmydata apt-get install -y -q wget make gcc git autoconf automake libtool gettext autopoint gperf gengetopt help2man texinfo gtk-doc-tools libidn11-dev libntlm0-dev libgnutls28-dev libkrb5-dev libgssglue-dev libdigest-sha3-perl # cvs libglib2.0-dev curl
  script:
  - !reference [.gnulib-fetch, script]
  - time ./bootstrap --skip-po --no-git
  - time ./configure --enable-gcc-warnings
  - time make syntax-check
  - time make -j$(nproc) check V=1 VERBOSE=t
  - time make -j$(nproc) dist
  - sha256sum *.tar.*
  - git status
  - git diff --exit-code
  - time apt-get install -y -q --no-install-recommends gpg gpgv2 gpg-agent
  - gpg --batch --passphrase '' --quick-gen-key pipeline@example.org
  - git checkout -B cibranch
  - git config user.email "pipeline@example.org"
  - git config user.name "Pipeline Builder"
  - git config user.signingkey pipeline@example.org
  - |
    if test -z "$CI_COMMIT_TAG"; then
      sed -i '3i * Noteworthy changes in release ?.? (????-??-??) [?]\n\n** WARNING This release was prepared automatically with no testing.\n' NEWS
      git commit -m "Warn about automatic release." NEWS
      relver='23.42.17'
      reltyp='alpha'
    else # maintainer ran release-commit
      relver=$(cat NEWS | sed -n -e 's/.*release \([0-9.]\+\) (....-..-..) \[\(.*\)\].*/\1/p' | head -1)
      reltyp=$(cat NEWS | sed -n -e 's/.*release \([0-9.]\+\) (....-..-..) \[\(.*\)\].*/\2/p' | head -1)
    fi
  - test -n "$CI_COMMIT_TAG" || make release-commit RELEASE="$relver $reltyp"
  - time make release RELEASE="$relver $reltyp" V=1 VERBOSE=t AM_DISTCHECK_DVI_TARGET=
  - cat -n ~/announce-*
  - git diff --exit-code # nothing should change version controlled files
  - sha256sum *.tar.*
  - mkdir -pv out/$CI_JOB_NAME_SLUG/{src,rel,log}
  - find config.h *.log tests/*.log -exec mv -v {} out/$CI_JOB_NAME_SLUG/log \;
  - test -n "$CI_COMMIT_TAG" || mv -v *23.42.17* out/$CI_JOB_NAME_SLUG/rel/
  - mv -v *-src.tar.* out/$CI_JOB_NAME_SLUG/src/
  - mv -v *.tar.* ~/announce-* out/$CI_JOB_NAME_SLUG/

R-Debian13:
  tags: [ saas-linux-medium-amd64 ]
  image: debian:13-slim
  stage: release-reproduce
  needs: []
  before_script:
  - cat /etc/os-release
  - time apt-get update -q
  - time apt-get install -y -q eatmydata
  - time eatmydata apt-get install -y -q wget make gcc git autoconf automake libtool gettext autopoint gperf gengetopt help2man texinfo gtk-doc-tools libidn11-dev libntlm0-dev libgnutls28-dev libkrb5-dev libgssglue-dev libdigest-sha3-perl # cvs libglib2.0-dev curl
  script:
  - !reference [.gnulib-fetch, script]
  - time ./bootstrap --skip-po --no-git
  - time ./configure --enable-gcc-warnings
  - time make syntax-check
  - time make -j$(nproc) check V=1 VERBOSE=t
  - time make -j$(nproc) dist
  - sha256sum *.tar.*
  - git status
  - git diff --exit-code
  - time apt-get install -y -q --no-install-recommends gpg gpgv gpg-agent
  - gpg --batch --passphrase '' --quick-gen-key pipeline@example.org
  - git checkout -B cibranch
  - git config user.email "pipeline@example.org"
  - git config user.name "Pipeline Builder"
  - git config user.signingkey pipeline@example.org
  - |
    if test -z "$CI_COMMIT_TAG"; then
      sed -i '3i * Noteworthy changes in release ?.? (????-??-??) [?]\n\n** WARNING This release was prepared automatically with no testing.\n' NEWS
      git commit -m "Warn about automatic release." NEWS
      relver='23.42.17'
      reltyp='alpha'
    else # maintainer ran release-commit
      relver=$(cat NEWS | sed -n -e 's/.*release \([0-9.]\+\) (....-..-..) \[\(.*\)\].*/\1/p' | head -1)
      reltyp=$(cat NEWS | sed -n -e 's/.*release \([0-9.]\+\) (....-..-..) \[\(.*\)\].*/\2/p' | head -1)
    fi
  - test -n "$CI_COMMIT_TAG" || make release-commit RELEASE="$relver $reltyp"
  - time make release RELEASE="$relver $reltyp" V=1 VERBOSE=t AM_DISTCHECK_DVI_TARGET=
  - cat -n ~/announce-*
  - git diff --exit-code # nothing should change version controlled files
  - sha256sum *.tar.*
  - mkdir -pv out/$CI_JOB_NAME_SLUG/{src,rel,log}
  - find config.h *.log tests/*.log -exec mv -v {} out/$CI_JOB_NAME_SLUG/log \;
  - test -n "$CI_COMMIT_TAG" || mv -v *23.42.17* out/$CI_JOB_NAME_SLUG/rel/
  - mv -v *-src.tar.* out/$CI_JOB_NAME_SLUG/src/
  - mv -v *.tar.* ~/announce-* out/$CI_JOB_NAME_SLUG/

R-Ubuntu2404:
  image: ubuntu:24.04
  tags: [ saas-linux-medium-amd64 ]
  stage: release-reproduce
  needs: []
  before_script:
  - cat /etc/os-release
  - time apt-get update -q
  - time apt-get install -y -q eatmydata
  - time eatmydata apt-get install -y -q --no-install-recommends wget ca-certificates make gcc git patch autoconf automake libtool gettext autopoint gperf gengetopt help2man texinfo gtk-doc-tools libidn11-dev libntlm0-dev libgnutls28-dev libkrb5-dev libgssglue-dev libdigest-sha3-perl
  script:
  - !reference [.gnulib-fetch, script]
  - time ./bootstrap --skip-po --no-git
  - time ./configure --enable-gcc-warnings=error
  - time make -j$(nproc) syntax-check
  - time make -j$(nproc) check V=1 VERBOSE=t
  - time make -j$(nproc) dist
  - sha256sum *.tar.*
  - git status
  - git diff --exit-code # nothing should change version controlled files
  - time apt-get install -y -q --no-install-recommends gpg gpgv gpg-agent
  - gpg --batch --passphrase '' --quick-gen-key pipeline@example.org
  - git checkout $CI_COMMIT_BRANCH
  - git config user.email "pipeline@example.org"
  - git config user.name "Pipeline Builder"
  - git config user.signingkey pipeline@example.org
  - |
    if test -z "$CI_COMMIT_TAG"; then
      sed -i '3i * Noteworthy changes in release ?.? (????-??-??) [?]\n\n** WARNING This release was prepared automatically with no testing.\n' NEWS
      git commit -m "Warn about automatic release." NEWS
      relver='23.42.17'
      reltyp='alpha'
    else # maintainer ran release-commit
      relver=$(cat NEWS | sed -n -e 's/.*release \([0-9.]\+\) (....-..-..) \[\(.*\)\].*/\1/p' | head -1)
      reltyp=$(cat NEWS | sed -n -e 's/.*release \([0-9.]\+\) (....-..-..) \[\(.*\)\].*/\2/p' | head -1)
    fi
  - test -n "$CI_COMMIT_TAG" || make release-commit RELEASE="$relver $reltyp"
  - make release RELEASE="$relver $reltyp" V=1 VERBOSE=t AM_DISTCHECK_DVI_TARGET=
  - cat -n ~/announce-*
  - git diff --exit-code # nothing should change version controlled files
  - sha256sum *.tar.*
  - mkdir -pv out/$CI_JOB_NAME_SLUG/{src,rel,log}
  - find config.h *.log tests/*.log -exec mv -v {} out/$CI_JOB_NAME_SLUG/log \;
  - test -n "$CI_COMMIT_TAG" || mv -v *23.42.17* out/$CI_JOB_NAME_SLUG/rel/
  - mv -v *-src.tar.* out/$CI_JOB_NAME_SLUG/src/
  - mv -v *.tar.* ~/announce-* out/$CI_JOB_NAME_SLUG/

R-Ubuntu2604:
  image: ubuntu:26.04
  tags: [ saas-linux-medium-amd64 ]
  stage: release-reproduce
  needs: []
  before_script:
  - cat /etc/os-release
  - time apt-get update -q
  - time apt-get install -y -q eatmydata
  - time eatmydata apt-get install -y -q --no-install-recommends wget ca-certificates make gcc git patch autoconf automake libtool gettext autopoint gperf gengetopt help2man texinfo gtk-doc-tools libidn11-dev libntlm0-dev libgnutls28-dev libkrb5-dev libgssglue-dev libdigest-sha3-perl
  script:
  - !reference [.gnulib-fetch, script]
  - time ./bootstrap --skip-po --no-git
  - time ./configure --enable-gcc-warnings=error
  - time make -j$(nproc) syntax-check
  - time make -j$(nproc) check V=1 VERBOSE=t
  - time make -j$(nproc) dist
  - sha256sum *.tar.*
  - git status
  - git diff --exit-code # nothing should change version controlled files
  - time apt-get install -y -q --no-install-recommends gpg gpgv gpg-agent
  - gpg --batch --passphrase '' --quick-gen-key pipeline@example.org
  - git checkout $CI_COMMIT_BRANCH
  - git config user.email "pipeline@example.org"
  - git config user.name "Pipeline Builder"
  - git config user.signingkey pipeline@example.org
  - |
    if test -z "$CI_COMMIT_TAG"; then
      sed -i '3i * Noteworthy changes in release ?.? (????-??-??) [?]\n\n** WARNING This release was prepared automatically with no testing.\n' NEWS
      git commit -m "Warn about automatic release." NEWS
      relver='23.42.17'
      reltyp='alpha'
    else # maintainer ran release-commit
      relver=$(cat NEWS | sed -n -e 's/.*release \([0-9.]\+\) (....-..-..) \[\(.*\)\].*/\1/p' | head -1)
      reltyp=$(cat NEWS | sed -n -e 's/.*release \([0-9.]\+\) (....-..-..) \[\(.*\)\].*/\2/p' | head -1)
    fi
  - test -n "$CI_COMMIT_TAG" || make release-commit RELEASE="$relver $reltyp"
  - make release RELEASE="$relver $reltyp" V=1 VERBOSE=t AM_DISTCHECK_DVI_TARGET=
  - cat -n ~/announce-*
  - git diff --exit-code # nothing should change version controlled files
  - sha256sum *.tar.*
  - mkdir -pv out/$CI_JOB_NAME_SLUG/{src,rel,log}
  - find config.h *.log tests/*.log -exec mv -v {} out/$CI_JOB_NAME_SLUG/log \;
  - test -n "$CI_COMMIT_TAG" || mv -v *23.42.17* out/$CI_JOB_NAME_SLUG/rel/
  - mv -v *-src.tar.* out/$CI_JOB_NAME_SLUG/src/
  - mv -v *.tar.* ~/announce-* out/$CI_JOB_NAME_SLUG/

S-Trisquel10:
  tags: [ saas-linux-medium-amd64 ]
  image: docker.io/kpengboy/trisquel:10.0
  stage: release-reproduce
  needs: [B-Guix]
  before_script:
  - cat /etc/os-release
  - sed -i 's,http://archive.trisquel.info/trisquel,http://ftp.acc.umu.se/mirror/trisquel/packages,' /etc/apt/sources.list
  - time apt-get update -q
  - time apt-get install -y -q eatmydata
  - time eatmydata apt-get install -y -q wget make gcc git autoconf automake libtool gettext autopoint gperf gengetopt help2man texinfo gtk-doc-tools libidn11-dev libntlm0-dev libgnutls28-dev libkrb5-dev libgssglue-dev # cvs libglib2.0-dev curl
  script:
  - mkdir -pv ../b
  - cd ../b
  - tar xfz ../*/out/b-guix/src/*-*.tar.gz
  - cd $(tar tfa ../*/out/b-guix/src/*-*.tar.gz | head -n1)
  - !reference [.gnulib-fetch, script]
  - time ./bootstrap --no-git
  - time ./configure
  - grep '^VERSION = ' Makefile | grep -v UNKNOWN
  - time make -j$(nproc) check V=1 VERBOSE=t
  - time make -j$(nproc) dist AM_DISTCHECK_DVI_TARGET=
  - sha256sum *.tar.*
  - mkdir -pv $CI_PROJECT_DIR/out/$CI_JOB_NAME_SLUG/{src,log}
  - find config.h *.log tests/*.log -exec mv -v {} $CI_PROJECT_DIR/out/$CI_JOB_NAME_SLUG/log \;
  - mv -v *.tar.* $CI_PROJECT_DIR/out/$CI_JOB_NAME_SLUG/

S-Ubuntu2004:
  tags: [ saas-linux-medium-amd64 ]
  image: ubuntu:20.04
  stage: release-reproduce
  needs: [B-Guix]
  variables:
    DEBIAN_FRONTEND: noninteractive
  before_script:
  - cat /etc/os-release
  - time apt-get update -q
  - time apt-get install -y -q eatmydata
  - time eatmydata apt-get install -y -q wget make gcc git autoconf automake libtool gettext autopoint gperf gengetopt help2man texinfo gtk-doc-tools libidn11-dev libntlm0-dev libgnutls28-dev libkrb5-dev libgssglue-dev # cvs libglib2.0-dev curl
  script:
  - tar xfz out/b-guix/src/*-*.tar.gz
  - cd $(tar tfa out/b-guix/src/*-*.tar.gz | head -n1)
  - !reference [.gnulib-fetch, script]
  - time ./bootstrap --no-git
  - time ./configure
  - grep '^VERSION = ' Makefile | grep -v UNKNOWN
  - time make -j$(nproc) check V=1 VERBOSE=t
  - time make -j$(nproc) dist AM_DISTCHECK_DVI_TARGET=
  - sha256sum *.tar.*
  - mkdir -pv ../out/$CI_JOB_NAME_SLUG/{src,log}
  - find config.h *.log tests/*.log -exec mv -v {} ../out/$CI_JOB_NAME_SLUG/log \;
  - mv -v *.tar.* ../out/$CI_JOB_NAME_SLUG/

Ubuntu-14.04:
  image: ubuntu:14.04
  stage: test
  needs: [B-Guix]
  before_script:
  - apt-get update -q
  - apt-get install -y -q make gcc valgrind
  script:
  - tar xfa out/b-guix/*-*.tar.gz
  - cd $(tar tfa out/b-guix/*-*.tar.gz | head -n1)
  - ./configure --enable-gcc-warnings=error
  - make -j$(nproc) check V=1 VERBOSE=t

Debian11-heimdal:
  image: debian:11-slim
  stage: test
  needs: [B-Guix]
  before_script:
  - apt-get update -q
  - apt-get install -y -q make gcc heimdal-dev valgrind iproute2 dovecot-imapd dovecot-gssapi krb5-kdc krb5-admin-server gnutls-bin libmailutils7
  - apt-get download mailutils-imap4d
  - dpkg -x mailutils-imap4d* x
  - cp x/usr/sbin/imap4d /usr/sbin/
  - rm -rf x
  - /usr/sbin/imap4d --version
  script:
  - tar xfa out/b-guix/*-*.tar.gz
  - cd $(tar tfa out/b-guix/*-*.tar.gz | head -n1)
  - ./configure  --with-gssapi-impl=heimdal --enable-gcc-warnings=error
  - make check V=1 VERBOSE=t VALGRINDFLAGS=--leak-check=no
  - grep '^PASS gsasl-dovecot-gssapi' tests/gsasl-dovecot-gssapi.log
  - grep '^PASS gsasl-mailutils-cram' tests/gsasl-mailutils-cram.log
  - grep '^PASS gsasl-mailutils-tls' tests/gsasl-mailutils-tls.log
  - grep '^PASS gsasl-mailutils-gs2krb5-gssapi' tests/gsasl-mailutils-gs2krb5-gssapi.log
  - GSASL=src/gsasl tests/gsasl-dovecot-gssapi.sh
  - GSASL="./libtool --mode=execute valgrind --leak-check=full src/gsasl" tests/gsasl-dovecot-gssapi.sh

Ubuntu-20.04-mit:
  image: ubuntu:20.04
  stage: test
  needs: [B-Guix]
  before_script:
  - apt-get update -q
  - apt-get install -y -q make gcc libkrb5-dev valgrind iproute2 dovecot-imapd dovecot-gssapi krb5-kdc krb5-admin-server gnutls-bin libmailutils6
  - apt-get download mailutils-imap4d
  - dpkg -x mailutils-imap4d* x
  - cp x/usr/sbin/imap4d /usr/sbin/
  - rm -rf x
  - /usr/sbin/imap4d --version
  script:
  - tar xfa out/b-guix/*-*.tar.gz
  - cd $(tar tfa out/b-guix/*-*.tar.gz | head -n1)
  - ./configure  --with-gssapi-impl=mit --enable-gcc-warnings=error
  - make check V=1 VERBOSE=t
  - grep '^PASS gsasl-dovecot-gssapi' tests/gsasl-dovecot-gssapi.log
  - grep '^PASS gsasl-mailutils-cram' tests/gsasl-mailutils-cram.log
  - grep '^PASS gsasl-mailutils-tls' tests/gsasl-mailutils-tls.log
  - grep '^PASS gsasl-mailutils-gs2krb5-gssapi' tests/gsasl-mailutils-gs2krb5-gssapi.log
  - GSASL=src/gsasl tests/gsasl-dovecot-gssapi.sh
  - GSASL="./libtool --mode=execute valgrind --error-exitcode=1 --leak-check=full src/gsasl" tests/gsasl-dovecot-gssapi.sh

Debian11-mit:
  image: debian:11-slim
  stage: test
  needs: [B-Guix]
  before_script:
  - apt-get update -q
  - apt-get install -y -q make gcc libkrb5-dev valgrind iproute2 dovecot-imapd dovecot-gssapi krb5-kdc krb5-admin-server libgnutls28-dev gnutls-bin libmailutils7
  - apt-get download mailutils-imap4d
  - dpkg -x mailutils-imap4d* x
  - cp x/usr/sbin/imap4d /usr/sbin/
  - rm -rf x
  - /usr/sbin/imap4d --version
  script:
  - tar xfa out/b-guix/*-*.tar.gz
  - cd $(tar tfa out/b-guix/*-*.tar.gz | head -n1)
  - ./configure --with-gssapi-impl=mit --enable-gcc-warnings=error
  - make check V=1 VERBOSE=t
  - grep '^PASS gsasl-dovecot-gssapi' tests/gsasl-dovecot-gssapi.log
  - grep '^PASS gsasl-mailutils-cram' tests/gsasl-mailutils-cram.log
  - GSASL=src/gsasl tests/gsasl-mailutils-cram.sh
  - GSASL="./libtool --mode=execute valgrind --error-exitcode=1 --leak-check=full --gen-suppressions=all --suppressions=tests/libgsasl.supp src/gsasl" tests/gsasl-mailutils-cram.sh
  - GSASL=src/gsasl IMAP4D="valgrind --error-exitcode=1 env LD_PRELOAD=lib/src/.libs/libgsasl.so /usr/sbin/imap4d" tests/gsasl-mailutils-cram.sh
  - grep '^PASS gsasl-mailutils-tls' tests/gsasl-mailutils-tls.log
  - GSASL=src/gsasl tests/gsasl-mailutils-tls.sh
  - GSASL="./libtool --mode=execute valgrind --error-exitcode=1 --leak-check=full --gen-suppressions=all --suppressions=tests/libgsasl.supp src/gsasl" tests/gsasl-mailutils-tls.sh
  - GSASL=src/gsasl IMAP4D="valgrind --error-exitcode=1 env LD_PRELOAD=lib/src/.libs/libgsasl.so /usr/sbin/imap4d" tests/gsasl-mailutils-tls.sh
  - grep '^PASS gsasl-mailutils-gs2krb5-gssapi' tests/gsasl-mailutils-gs2krb5-gssapi.log
  - GSASL=src/gsasl tests/gsasl-mailutils-gs2krb5-gssapi.sh
  - GSASL="./libtool --mode=execute valgrind --error-exitcode=1 --leak-check=full --gen-suppressions=all --suppressions=tests/libgsasl.supp src/gsasl" tests/gsasl-mailutils-gs2krb5-gssapi.sh
  - GSASL=src/gsasl IMAP4D="valgrind --error-exitcode=1 env LD_PRELOAD=lib/src/.libs/libgsasl.so /usr/sbin/imap4d" tests/gsasl-mailutils-gs2krb5-gssapi.sh

Debian-testing-heimdal:
  image: debian:testing-slim
  stage: test
  needs: [B-Guix]
  before_script:
  - apt-get update -q
  - apt-get install -y -q make gcc heimdal-dev valgrind iproute2 dovecot-imapd dovecot-gssapi krb5-kdc krb5-admin-server libgnutls28-dev gnutls-bin libmailutils9 mailutils-imap4d
  script:
  - tar xfa out/b-guix/*-*.tar.gz
  - cd $(tar tfa out/b-guix/*-*.tar.gz | head -n1)
  - ./configure --with-gssapi-impl=mit --enable-gcc-warnings=error WERROR_CFLAGS="-Wno-error=use-after-free"
  - make check V=1 VERBOSE=t VALGRINDFLAGS=--leak-check=no
  - grep '^PASS gsasl-dovecot-gssapi' tests/gsasl-dovecot-gssapi.log
  - grep '^PASS gsasl-mailutils-cram' tests/gsasl-mailutils-cram.log
  - GSASL=src/gsasl tests/gsasl-mailutils-cram.sh
  - GSASL="./libtool --mode=execute valgrind --error-exitcode=1 src/gsasl" tests/gsasl-mailutils-cram.sh
  - GSASL="./libtool --mode=execute valgrind --leak-check=full src/gsasl" tests/gsasl-mailutils-cram.sh
  - GSASL=src/gsasl IMAP4D="valgrind --error-exitcode=1 env LD_PRELOAD=lib/src/.libs/libgsasl.so /usr/sbin/imap4d" tests/gsasl-mailutils-cram.sh
  - grep '^PASS gsasl-mailutils-tls' tests/gsasl-mailutils-tls.log
  - GSASL=src/gsasl tests/gsasl-mailutils-tls.sh
  - GSASL="./libtool --mode=execute valgrind --error-exitcode=1 src/gsasl" tests/gsasl-mailutils-tls.sh
  - GSASL="./libtool --mode=execute valgrind --leak-check=full src/gsasl" tests/gsasl-mailutils-tls.sh
  - GSASL=src/gsasl IMAP4D="valgrind --error-exitcode=1 env LD_PRELOAD=lib/src/.libs/libgsasl.so /usr/sbin/imap4d" tests/gsasl-mailutils-tls.sh
  - grep '^PASS gsasl-mailutils-gs2krb5-gssapi' tests/gsasl-mailutils-gs2krb5-gssapi.log
  - GSASL=src/gsasl tests/gsasl-mailutils-gs2krb5-gssapi.sh
  - GSASL="./libtool --mode=execute valgrind --error-exitcode=1 src/gsasl" tests/gsasl-mailutils-gs2krb5-gssapi.sh
  - GSASL="./libtool --mode=execute valgrind --leak-check=full src/gsasl" tests/gsasl-mailutils-gs2krb5-gssapi.sh
  - GSASL=src/gsasl IMAP4D="valgrind --error-exitcode=1 env LD_PRELOAD=lib/src/.libs/libgsasl.so /usr/sbin/imap4d" tests/gsasl-mailutils-gs2krb5-gssapi.sh

Ubuntu-20.04-gssglue:
  image: ubuntu:20.04 # FIXME XXX 22.04: gsasl-mailutils-tls: imap4d: process 21651 terminated on signal 11
  stage: test
  needs: [B-Guix]
  before_script:
  - apt-get update -q
  - apt-get install -y -q make gcc libgssglue-dev valgrind iproute2 dovecot-imapd dovecot-gssapi krb5-kdc krb5-admin-server libgnutls28-dev gnutls-bin libmailutils6
  - apt-get download mailutils-imap4d
  - dpkg -x mailutils-imap4d* x
  - cp x/usr/sbin/imap4d /usr/sbin/
  - rm -rf x
  - /usr/sbin/imap4d --version
  script:
  - tar xfa out/b-guix/*-*.tar.gz
  - cd $(tar tfa out/b-guix/*-*.tar.gz | head -n1)
  - ./configure --with-gssapi-impl=gssglue --enable-gcc-warnings=error WERROR_CFLAGS=-Wno-error=discarded-qualifiers
  - make check V=1 VERBOSE=t VALGRINDFLAGS="--error-exitcode=0 --leak-check=no"
  - grep '^PASS gsasl-dovecot-gssapi' tests/gsasl-dovecot-gssapi.log
  - grep '^PASS gsasl-mailutils-cram' tests/gsasl-mailutils-cram.log
  - GSASL=src/gsasl tests/gsasl-mailutils-cram.sh
  - GSASL="./libtool --mode=execute valgrind --error-exitcode=1 --leak-check=full src/gsasl" tests/gsasl-mailutils-cram.sh
  - GSASL=src/gsasl IMAP4D="valgrind --error-exitcode=1 env LD_PRELOAD=lib/src/.libs/libgsasl.so /usr/sbin/imap4d" tests/gsasl-mailutils-cram.sh
  - grep '^PASS gsasl-mailutils-tls' tests/gsasl-mailutils-tls.log
  - GSASL=src/gsasl tests/gsasl-mailutils-tls.sh
  - GSASL="./libtool --mode=execute valgrind src/gsasl" tests/gsasl-mailutils-tls.sh
  - GSASL=src/gsasl IMAP4D="valgrind --error-exitcode=1 env LD_PRELOAD=lib/src/.libs/libgsasl.so /usr/sbin/imap4d" tests/gsasl-mailutils-tls.sh
  - grep '^PASS gsasl-mailutils-gs2krb5-gssapi' tests/gsasl-mailutils-gs2krb5-gssapi.log
  - GSASL=src/gsasl tests/gsasl-mailutils-gs2krb5-gssapi.sh
  - GSASL="./libtool --mode=execute valgrind --leak-check=full src/gsasl" tests/gsasl-mailutils-gs2krb5-gssapi.sh
  - GSASL=src/gsasl IMAP4D="valgrind --error-exitcode=1 env LD_PRELOAD=lib/src/.libs/libgsasl.so /usr/sbin/imap4d" tests/gsasl-mailutils-gs2krb5-gssapi.sh

Ubuntu-22.04-gssglue:
  image: ubuntu:22.04
  stage: test
  needs: [B-Guix]
  before_script:
  - apt-get update -q
  - apt-get install -y -q make gcc libgssglue-dev valgrind iproute2 dovecot-imapd dovecot-gssapi krb5-kdc krb5-admin-server libgnutls28-dev libmailutils8
  - apt-get download mailutils-imap4d
  - dpkg -x mailutils-imap4d* x
  - cp x/usr/sbin/imap4d /usr/sbin/
  - rm -rf x
  - /usr/sbin/imap4d --version
  script:
  - tar xfa out/b-guix/*-*.tar.gz
  - cd $(tar tfa out/b-guix/*-*.tar.gz | head -n1)
  - ./configure --with-gssapi-impl=gssglue --enable-gcc-warnings=error WERROR_CFLAGS=-Wno-error=discarded-qualifiers
  - make check V=1 VERBOSE=t VALGRINDFLAGS=--leak-check=no
  - grep '^PASS gsasl-dovecot-gssapi' tests/gsasl-dovecot-gssapi.log
  - grep '^PASS gsasl-mailutils-cram' tests/gsasl-mailutils-cram.log
  - GSASL=src/gsasl tests/gsasl-mailutils-cram.sh
  - GSASL="./libtool --mode=execute valgrind --error-exitcode=1 --leak-check=full src/gsasl" tests/gsasl-mailutils-cram.sh
  - GSASL=src/gsasl IMAP4D="valgrind --error-exitcode=1 env LD_PRELOAD=lib/src/.libs/libgsasl.so /usr/sbin/imap4d" tests/gsasl-mailutils-cram.sh
  - grep '^PASS gsasl-mailutils-gs2krb5-gssapi' tests/gsasl-mailutils-gs2krb5-gssapi.log
  - GSASL=src/gsasl tests/gsasl-mailutils-gs2krb5-gssapi.sh
  - GSASL="./libtool --mode=execute valgrind --leak-check=full src/gsasl" tests/gsasl-mailutils-gs2krb5-gssapi.sh
  - GSASL=src/gsasl IMAP4D="valgrind --error-exitcode=1 env LD_PRELOAD=lib/src/.libs/libgsasl.so /usr/sbin/imap4d" tests/gsasl-mailutils-gs2krb5-gssapi.sh

Trisquel10-distcheck:
  image: kpengboy/trisquel:10.0
  stage: test
  needs: [B-Guix]
  before_script:
  - apt-get update -q
  - apt-get install -y -q make gcc gtk-doc-tools texinfo valgrind
  script:
  - tar xfa out/b-guix/*-*.tar.gz
  - cd $(tar tfa out/b-guix/*-*.tar.gz | head -n1)
  - ./configure --enable-gcc-warnings=error
  - make distcheck V=1 VERBOSE=t AM_DISTCHECK_DVI_TARGET=

OracleLinux7:
  image: oraclelinux:7
  stage: test
  needs: [B-Guix]
  before_script:
  - yum -y install make gcc diffutils valgrind gnutls-devel
  script:
  - tar xfa out/b-guix/*-*.tar.gz
  - cd $(tar tfz out/b-guix/*-*.tar.gz | head -n1)
  - time ./configure --enable-gcc-warnings=error
  - time make -j$(nproc) -k check V=1 VERBOSE=t

AlmaLinux8-krb5:
  image: almalinux:8
  stage: test
  needs: [B-Guix]
  before_script:
  - yum -y install make gcc diffutils krb5-devel valgrind
  script:
  - tar xfa out/b-guix/*-*.tar.gz
  - cd $(tar tfa out/b-guix/*-*.tar.gz | head -n1)
  - ./configure --enable-gcc-warnings=error --with-gssapi-impl=mit
  - grep 'USE_GS2 1' config.log
  - make check V=1 VERBOSE=t

Alpine:
  image: alpine:latest
  stage: test
  needs: [B-Guix]
  before_script:
  - echo "ipv6" >> /etc/modules
  - apk update
  - apk add build-base gettext gettext-dev valgrind
  script:
  - tar xfa out/b-guix/*-*.tar.gz
  - cd $(tar tfz out/b-guix/*-*.tar.gz | head -n1)
  - ./configure --enable-gcc-warnings=error
  - make check V=1 VERBOSE=t

Alpine-heimdal:
  image: alpine:latest
  stage: test
  needs: [B-Guix]
  before_script:
  - echo "ipv6" >> /etc/modules
  - apk update
  - apk add build-base gettext gettext-dev heimdal-dev valgrind
  script:
  - tar xfa out/b-guix/*-*.tar.gz
  - cd $(tar tfz out/b-guix/*-*.tar.gz | head -n1)
  - ./configure --enable-gcc-warnings=error --with-gssapi-impl=heimdal
  - grep 'USE_GS2 1' config.log
  - make check V=1 VERBOSE=t

ArchLinux:
  image: archlinux:latest
  stage: test
  needs: [B-Guix]
  before_script:
  - pacman -Syu --noconfirm make gcc diffutils file net-tools inetutils
  script:
  - tar xfa out/b-guix/*-*.tar.gz
  - cd $(tar tfz out/b-guix/*-*.tar.gz | head -n1)
  - mkdir b
  - cd b
  - ../configure --enable-gcc-warnings=error
  - make check V=1 VERBOSE=t

Debian9:
  image: debian/eol:stretch-slim
  stage: test
  needs: [B-Guix]
  before_script:
  # https://github.com/debuerreotype/docker-debian-eol-artifacts/issues/10
  - printf "deb http://archive.debian.org/debian/ stretch main\ndeb http://archive.debian.org/debian/ stretch-backports main\ndeb http://archive.debian.org/debian-security/ stretch/updates main\n" > /etc/apt/sources.list
  - apt-get update -q
  - apt-get install -y -q make gcc
  script:
  - tar xfa out/b-guix/*-*.tar.gz
  - cd $(tar tfz out/b-guix/*-*.tar.gz | head -n1)
  - ./configure --enable-gcc-warnings=error
  - make check V=1 VERBOSE=t
  - make syntax-check

Debian10-gss:
  image: debian/eol:buster-slim
  stage: test
  needs: [B-Guix]
  before_script:
  - apt-get update -q
  - apt-get install -y -q make gcc libgss-dev datefudge
  script:
  - tar xfa out/b-guix/*-*.tar.gz
  - cd $(tar tfz out/b-guix/*-*.tar.gz | head -n1)
  - ./configure --with-gssapi-impl=gss --enable-gcc-warnings=error
  - grep 'ac_cv_libgss=yes' config.log
  - grep 'USE_GS2 1' config.log
  - (! make check V=1 VERBOSE=t)
  - datefudge 2022-01-01 make check V=1 VERBOSE=t
  - grep '^PASS gssapi' tests/gssapi.log
  - grep '^PASS gs2-krb5' tests/gs2-krb5.log

Debian9-gssglue:
  image: debian/eol:stretch-slim
  stage: test
  needs: [B-Guix]
  before_script:
  # https://github.com/debuerreotype/docker-debian-eol-artifacts/issues/10
  - printf "deb http://archive.debian.org/debian/ stretch main\ndeb http://archive.debian.org/debian/ stretch-backports main\ndeb http://archive.debian.org/debian-security/ stretch/updates main\n" > /etc/apt/sources.list
  - apt-get update -q
  - apt-get install -y -q make gcc libgssglue-dev libgnutls28-dev
  script:
  - tar xfa out/b-guix/*-*.tar.gz
  - cd $(tar tfz out/b-guix/*-*.tar.gz | head -n1)
  - ./configure --with-gssapi-impl=gssglue --enable-gcc-warnings=error WERROR_CFLAGS=-Wno-error=discarded-qualifiers
  - grep 'ac_cv_libgssglue=yes' config.log
  - grep 'USE_GS2 1' config.log
  - make check V=1 VERBOSE=t

Debian11-armcross:
  image: debian:bullseye-slim
  stage: test
  needs: [B-Guix]
  before_script:
  - apt-get update -qq
  - apt-get install -y -q make gcc-arm-linux-gnueabi qemu-user qemu-user-binfmt file
  - update-binfmts --enable qemu-arm
  script:
  - tar xfa out/b-guix/*-*.tar.gz
  - cd $(tar tfz out/b-guix/*-*.tar.gz | head -n1)
  - mkdir b
  - cd b
  - ../configure --host=arm-linux-gnueabi --enable-gcc-warnings=error CFLAGS="-static --static"
  - make -j$(nproc) V=1
  - arm-linux-gnueabi-readelf -h lib/src/.libs/libgsasl.a
  - arm-linux-gnueabi-readelf -h src/gsasl
  - file src/gsasl
  - LANG=C.UTF-8 qemu-arm src/gsasl --mkpasswd --mechanism SCRAM-SHA-1 -p foo
  - make check VERBOSE=t

Debian-gsasl4win:
  image: debian:bullseye
  stage: test
  needs: [B-Guix]
  before_script:
  - dpkg --add-architecture i386
  - apt-get update -q
  - apt-get install -y -q make mingw-w64 wine wine32 wine64 libwine libwine:i386 binfmt-support wine-binfmt zip
  - update-binfmts --enable wine
  script:
  - mkdir windows/dist
  - cp -v out/b-guix/*-*.tar.gz windows/dist/
  - cd windows/
  - make -f gsasl4win.mk VERSION=`echo dist/gsasl-*.tar.gz | sed -e 's/.*gsasl-//g' -e 's/.tar.gz//g'` gsasl4win32 gsasl4win64
  artifacts:
    expire_in: 2 weeks
    paths:
      - windows/gsasl-*.zip

Mingw32:
  image: debian:latest
  stage: test
  needs: [B-Guix]
  before_script:
  - dpkg --add-architecture i386
  - apt-get update -q
  - apt-get install -y -q make mingw-w64 wine wine32 libwine libwine:i386 binfmt-support wine-binfmt
  - update-binfmts --enable wine
  variables:
     WERROR_CFLAGS: "-Wno-error=unused-value -Wno-error=suggest-attribute=format -Wno-error=use-after-free"
  script:
  - tar xfa out/b-guix/*-*.tar.gz
  - cd $(tar tfz out/b-guix/*-*.tar.gz | head -n1)
  - mkdir b
  - cd b
  - ../configure --host=i686-w64-mingw32 CC='i686-w64-mingw32-gcc -static-libgcc' --enable-gcc-warnings=error
  - make -k -j$(nproc) check V=1 VERBOSE=t

Mingw64:
  image: debian:latest
  stage: test
  needs: [B-Guix]
  before_script:
  - apt-get update -q
  - apt-get install -y -q make mingw-w64 wine wine64 binfmt-support wine-binfmt
  - update-binfmts --enable wine
  variables:
     WERROR_CFLAGS: "-Wno-error=unused-value -Wno-error=suggest-attribute=format -Wno-error=use-after-free"
  script:
  - tar xfa out/b-guix/*-*.tar.gz
  - cd $(tar tfz out/b-guix/*-*.tar.gz | head -n1)
  - mkdir b
  - cd b
  - ../configure --host=x86_64-w64-mingw32 --enable-gcc-warnings=error
  - make -k -j$(nproc) check V=1 VERBOSE=t

Debian12-interop:
  image: debian:12-slim
  stage: test
  needs: [B-Guix]
  before_script:
  - apt-get update -q
  - apt-get install -y -q make gcc file libntlm0-dev
  - apt-get install -y -q msmtp swaks libauthen-sasl-perl libmailutils-dev dovecot-imapd
  script:
  - tar xfa out/b-guix/*-*.tar.gz
  - cd $(tar tfz out/b-guix/*-*.tar.gz | head -n1)
  - mkdir b
  - cd b
  - ../configure --enable-gcc-warnings=error WERROR_CFLAGS="-Wno-error=use-after-free"
  - make -j$(nproc) V=1
  - examples/smtp-server &
  - rm /etc/dovecot/conf.d/10-auth.conf
  - echo amFzOntQTEFJTn1zZXNhbTo6OjoK | base64 -d > /etc/dovecot/users
  - echo bG9nX3BhdGggPSAvdmFyL2xvZy9kb3ZlY290LmxvZwpwcm90b2NvbCBpbWFwIHsKfQpwYXNzZGIgewogIGRyaXZlciA9IHBhc3N3ZC1maWxlCiAgYXJncyA9IC9ldGMvZG92ZWNvdC91c2Vycwp9CnVzZXJkYiB7CiAgZHJpdmVyID0gc3RhdGljCiAgYXJncyA9IHVpZD1ub2JvZHkgZ2lkPW5vZ3JvdXAgaG9tZT0vdG1wL2RvdmVjb3QvJWQvJXUKfQpkaXNhYmxlX3BsYWludGV4dF9hdXRoPW5vCmF1dGhfbWVjaGFuaXNtcyA9IHBsYWluIGxvZ2luIGRpZ2VzdC1tZDUgY3JhbS1tZDUgc2NyYW0tc2hhLTEgc2NyYW0tc2hhLTI1NiBhbm9ueW1vdXMgZXh0ZXJuYWwgeG9hdXRoMgo= | base64 -d > /etc/dovecot/local.conf
  - service dovecot restart
  - src/gsasl localhost 2000 --smtp --mechanism PLAIN --password sesam -d
  - src/gsasl localhost 2000 --smtp --mechanism LOGIN --password sesam -d
  - src/gsasl localhost 2000 --smtp --mechanism CRAM-MD5 --password sesam -d
  - src/gsasl localhost 2000 --smtp --mechanism DIGEST-MD5 --password sesam -d --quality-of-protection="" --realm=""
  - src/gsasl localhost 2000 --smtp --mechanism SCRAM-SHA-1 --password sesam -d
  - src/gsasl localhost 2000 --smtp --mechanism SCRAM-SHA-256 --password sesam -d
  - (src/gsasl localhost 2000 --smtp --mechanism PLAIN --password wrong -d 2>&1 || true) | grep 'server error'
  - (src/gsasl localhost 2000 --smtp --mechanism LOGIN --password wrong -d 2>&1 || true) | grep 'server error'
  - (src/gsasl localhost 2000 --smtp --mechanism CRAM-MD5 --password wrong -d 2>&1 || true) | grep 'server error'
  - (src/gsasl localhost 2000 --smtp --mechanism DIGEST-MD5 --password wrong -d --quality-of-protection="" --realm="" 2>&1 || true) | grep 'server error'
  - (src/gsasl localhost 2000 --smtp --mechanism SCRAM-SHA-1 --password wrong -d 2>&1 || true) | grep 'server error'
  - (src/gsasl localhost 2000 --smtp --mechanism SCRAM-SHA-256 --password wrong -d 2>&1 || true) | grep 'server error'
  - printf "verbose on\nconnect 127.0.0.1 2000\nehlo foo\nset username jas\nset password sesam\nauth PLAIN\nquit\n" |mailutils smtp 2>&1 | grep '235 OK \[authid'
  - printf "verbose on\nconnect 127.0.0.1 2000\nehlo foo\nset username jas\nset password sesam\nauth LOGIN\nquit\n" |mailutils smtp 2>&1 | grep '235 OK \[authid'
  - printf "verbose on\nconnect 127.0.0.1 2000\nehlo foo\nset username jas\nset password sesam\nauth CRAM-MD5\nquit\n" |mailutils smtp 2>&1 | grep '235 OK \[authid'
  - printf "verbose on\nconnect 127.0.0.1 2000\nehlo foo\nset username jas\nset password sesam\nauth DIGEST-MD5\nquit\n" |mailutils smtp 2>&1 | grep '235 OK \[authid'
  - printf "verbose on\nconnect 127.0.0.1 2000\nehlo foo\nset username jas\nset password sesam\nauth SCRAM-SHA-1\nquit\n" |mailutils smtp 2>&1 | grep '235 OK \[authid'
  - printf "verbose on\nconnect 127.0.0.1 2000\nehlo foo\nset username jas\nset password sesam\nauth SCRAM-SHA-256\nquit\n" | LD_PRELOAD=lib/src/.libs/libgsasl.so mailutils smtp 2>&1 | grep '235 OK \[authid'
  - printf "verbose on\nconnect 127.0.0.1 2000\nehlo foo\nset username jas\nset password wrong\nauth PLAIN\nquit\n" |mailutils smtp 2>&1 | grep 'Error authenticating user'
  - printf "verbose on\nconnect 127.0.0.1 2000\nehlo foo\nset username jas\nset password wrong\nauth LOGIN\nquit\n" |mailutils smtp 2>&1 | grep 'Error authenticating user'
  - printf "verbose on\nconnect 127.0.0.1 2000\nehlo foo\nset username jas\nset password wrong\nauth CRAM-MD5\nquit\n" |mailutils smtp 2>&1 | grep 'Error authenticating user'
  - printf "verbose on\nconnect 127.0.0.1 2000\nehlo foo\nset username jas\nset password wrong\nauth DIGEST-MD5\nquit\n" |mailutils smtp 2>&1 | grep 'Error authenticating user'
  - printf "verbose on\nconnect 127.0.0.1 2000\nehlo foo\nset username jas\nset password wrong\nauth SCRAM-SHA-1\nquit\n" |mailutils smtp 2>&1 | grep 'Error authenticating user'
  - printf "verbose on\nconnect 127.0.0.1 2000\nehlo foo\nset username jas\nset password wrong\nauth SCRAM-SHA-256\nquit\n" | LD_PRELOAD=lib/src/.libs/libgsasl.so mailutils smtp 2>&1 | grep 'Error authenticating user'
  - (swaks --to user@example.com --server 127.0.0.1:2000 --auth CRAM-MD5 --auth-user jas --auth-password wrong 2>&1 || true) | grep 'No authentication type succeeded'
  - (swaks --to user@example.com --server 127.0.0.1:2000 --auth DIGEST-MD5 --auth-user jas --auth-password wrong 2>&1 || true) | grep 'No authentication type succeeded'
  - (swaks --to user@example.com --server 127.0.0.1:2000 --auth PLAIN --auth-user jas --auth-password wrong 2>&1 || true) | grep 'No authentication type succeeded'
  - (swaks --to user@example.com --server 127.0.0.1:2000 --auth LOGIN --auth-user jas --auth-password wrong 2>&1 || true) | grep 'No authentication type succeeded'
  - swaks --to user@example.com --server 127.0.0.1:2000 --auth CRAM-MD5 --auth-user jas --auth-password sesam
  - swaks --to user@example.com --server 127.0.0.1:2000 --auth DIGEST-MD5 --auth-user jas --auth-password sesam
  - swaks --to user@example.com --server 127.0.0.1:2000 --auth PLAIN --auth-user jas --auth-password sesam
  - swaks --to user@example.com --server 127.0.0.1:2000 --auth LOGIN --auth-user jas --auth-password sesam
  - echo foo | msmtp --host=localhost --port=2000 --auth=cram-md5 --debug -f user@example.com user@example.com --user=jas  --passwordeval 'echo sesam'
  - echo foo | msmtp --host=localhost --port=2000 --auth=digest-md5 --debug -f user@example.com user@example.com --user=jas  --passwordeval 'echo sesam'
  - echo foo | msmtp --host=localhost --port=2000 --auth=scram-sha-1 --debug -f user@example.com user@example.com --user=jas  --passwordeval 'echo sesam'
  - echo foo | msmtp --host=localhost --port=2000 --auth=plain --debug -f user@example.com user@example.com --user=jas  --passwordeval 'echo sesam'
  - echo foo | msmtp --host=localhost --port=2000 --auth=login --debug -f user@example.com user@example.com --user=jas  --passwordeval 'echo sesam'
  - tail -F /var/log/dovecot.log &
  - src/gsasl localhost --no-starttls --mechanism PLAIN -a jas --password sesam -d
  - src/gsasl localhost --no-starttls --mechanism LOGIN -a jas --password sesam -d
  - src/gsasl localhost --no-starttls --mechanism CRAM-MD5 -a jas --password sesam -d
  - src/gsasl localhost --no-starttls --mechanism DIGEST-MD5 -a jas --password sesam -d --quality-of-protection="" --realm=""
  - src/gsasl localhost --no-starttls --mechanism SCRAM-SHA-1 -a jas --password sesam -d
  - src/gsasl localhost --no-starttls --mechanism SCRAM-SHA-256 -a jas --password sesam -d
  - src/gsasl localhost --no-starttls --mechanism ANONYMOUS -n user -d

Debian11-gss-interop:
  image: debian:11-slim
  stage: test
  needs: [B-Guix]
  variables:
    DEBIAN_FRONTEND: noninteractive
  before_script:
  - apt-get update -qq
  - apt-get install -y -q make gcc file libntlm0-dev datefudge | tail -10
  - apt-get install -y -qq krb5-multidev libgssglue-dev heimdal-multidev libgss-dev valgrind | tail -10
  - apt-get install -y -q shishi msmtp swaks libauthen-sasl-perl libmailutils-dev dovecot-imapd dovecot-gssapi krb5-kdc krb5-admin-server net-tools expect | tail -10
  - rm /etc/dovecot/conf.d/10-auth.conf
  - echo 'jas:{PLAIN}sesam::::' > /etc/dovecot/users
  - printf 'auth_gssapi_hostname = imap.gsasl.example\nauth_krb5_keytab = /etc/dovecot/dovecot.keytab\nlog_path = /var/log/dovecot.log\nprotocol imap {\n}\npassdb {\n  driver = passwd-file\n  args = /etc/dovecot/users\n}\nuserdb {\n  driver = static\n  args = uid=nobody gid=nogroup home=/tmp/dovecot/%d/%u\n}\ndisable_plaintext_auth=no\nauth_mechanisms = plain login digest-md5 cram-md5 scram-sha-1 scram-sha-256 gssapi anonymous external xoauth2\n' > /etc/dovecot/local.conf
  - sed -i 's/default_realm =.*/default_realm = GSASL.EXAMPLE/' /etc/krb5.conf
  - sed -i 's/EXAMPLE.COM = {/GSASL.EXAMPLE = {/' /etc/krb5kdc/kdc.conf
  - printf '[logging]\nkdc = FILE:/tmp/kdc.log\n' >> /etc/krb5kdc/kdc.conf
  - printf '[realms]\nGSASL.EXAMPLE = {\nkdc = kdc.gsasl.example\n}\n' >> /etc/krb5.conf
  - printf '127.0.1.2 kdc.gsasl.example\n127.0.1.3 imap.gsasl.example\n127.0.1.4 smtp.gsasl.example' >> /etc/hosts
  - printf 'default-realm GSASL.EXAMPLE\nrealm-kdc=GSASL.EXAMPLE,kdc.gsasl.example/tcp\n' > /etc/shishi/shishi.conf
  - cat /etc/krb5.conf
  - cat /etc/krb5kdc/kdc.conf
  - kdb5_util -P foo create -s
  - kadmin.local addprinc -randkey smtp/smtp.gsasl.example
  - kadmin.local addprinc -randkey imap/imap.gsasl.example
  - kadmin.local addprinc -pw bar jas
  - kadmin.local ktadd smtp/smtp.gsasl.example
  - kadmin.local ktadd -k /etc/dovecot/dovecot.keytab imap/imap.gsasl.example
  - chgrp dovecot /etc/dovecot/dovecot.keytab
  - chmod g+r /etc/dovecot/dovecot.keytab
  - service dovecot restart
  - service krb5-kdc restart
  - echo bar | kinit jas@GSASL.EXAMPLE
  - tail -F /var/log/dovecot.log /tmp/kdc.log &
  script:
  - tar xfa out/b-guix/*-*.tar.gz
  - cd $(tar tfz out/b-guix/*-*.tar.gz | head -n1)
  - mkdir mit
  - cd mit
  - ../configure --with-gssapi-impl=mit | tail -45
  - make -j$(nproc) | tail -10
  - ./libtool --mode=execute valgrind --error-exitcode=1 --exit-on-first-error=yes examples/smtp-server 2000 &
  - while ! netstat -na|grep 0.0.0.0:2000; do sleep 1; done
  - src/gsasl smtp.gsasl.example 2000 --smtp --mechanism GSSAPI -d | grep '235 OK \[authid. N/A authzid. N/A gssname. jas@GSASL.EXAMPLE\]'
  - src/gsasl smtp.gsasl.example 2000 --smtp --mechanism GS2-KRB5 -d | grep '235 OK \[authid. N/A authzid. N/A gssname. jas@GSASL.EXAMPLE\]'
  - src/gsasl smtp.gsasl.example 2000 --smtp --mechanism GSSAPI -z rms -d | grep '235 OK \[authid. N/A authzid. rms gssname. jas@GSASL.EXAMPLE\]'
  - src/gsasl smtp.gsasl.example 2000 --smtp --mechanism GS2-KRB5 -z rms -d | grep '235 OK \[authid. N/A authzid. rms gssname. jas@GSASL.EXAMPLE\]'
  - printf "verbose on\nconnect 127.0.0.1 2000\nehlo foo\nset username rms\nset service smtp\nset host smtp.gsasl.example\nauth GSSAPI\nquit\n" | mailutils smtp 2>&1 | grep '235 OK \[authid. N/A authzid. rms gssname. jas@GSASL.EXAMPLE\]' # 'authzid:rms -- system libgsasl has GSS-API client authzid bug
  - printf "verbose on\nconnect 127.0.0.1 2000\nehlo foo\nset username rms\nset service smtp\nset host smtp.gsasl.example\nauth GS2-KRB5\nquit\n" | mailutils smtp 2>&1 | grep '235 OK \[authid. N/A authzid. N/A gssname. jas@GSASL.EXAMPLE\]'
  - printf "verbose on\nconnect 127.0.0.1 2000\nehlo foo\nset password unused\nset service smtp\nset host smtp.gsasl.example\nauth GSSAPI\nquit\n" | mailutils smtp 2>&1 | grep '235 OK \[authid. N/A authzid. N/A gssname. jas@GSASL.EXAMPLE\]'
  - printf "verbose on\nconnect 127.0.0.1 2000\nehlo foo\nset password unused jas\nset service smtp\nset host smtp.gsasl.example\nauth GS2-KRB5\nquit\n" | mailutils smtp 2>&1 | grep '235 OK \[authid. N/A authzid. N/A gssname. jas@GSASL.EXAMPLE\]'
  - printf "verbose on\nconnect 127.0.0.1 2000\nehlo foo\nset username rms\nset service smtp\nset host smtp.gsasl.example\nauth GSSAPI\nquit\n" | LD_PRELOAD=lib/src/.libs/libgsasl.so mailutils smtp 2>&1 | grep '235 OK \[authid. N/A authzid. N/A gssname. jas@GSASL.EXAMPLE\]'
  - printf "verbose on\nconnect 127.0.0.1 2000\nehlo foo\nset username rms\nset service smtp\nset host smtp.gsasl.example\nauth GS2-KRB5\nquit\n" | LD_PRELOAD=lib/src/.libs/libgsasl.so mailutils smtp 2>&1 | grep '235 OK \[authid. N/A authzid. N/A gssname. jas@GSASL.EXAMPLE\]'
  - printf "verbose on\nconnect 127.0.0.1 2000\nehlo foo\nset password unused\nset service smtp\nset host smtp.gsasl.example\nauth GSSAPI\nquit\n" | LD_PRELOAD=lib/src/.libs/libgsasl.so mailutils smtp 2>&1 | grep '235 OK \[authid. N/A authzid. N/A gssname. jas@GSASL.EXAMPLE\]'
  - printf "verbose on\nconnect 127.0.0.1 2000\nehlo foo\nset password unused jas\nset service smtp\nset host smtp.gsasl.example\nauth GS2-KRB5\nquit\n" | LD_PRELOAD=lib/src/.libs/libgsasl.so mailutils smtp 2>&1 | grep '235 OK \[authid. N/A authzid. N/A gssname. jas@GSASL.EXAMPLE\]'
  - echo foo | msmtp --host=smtp.gsasl.example --port=2000 --auth=gssapi --debug -f user@example.com user@example.com --user=jas | grep '235 OK \[authid. N/A authzid. jas gssname. jas@GSASL.EXAMPLE\]' # system libgssapi GSSAPI authzid bug
  - echo foo | LD_PRELOAD=lib/src/.libs/libgsasl.so msmtp --host=smtp.gsasl.example --port=2000 --auth=gssapi --debug -f user@example.com user@example.com --user=jas | grep '235 OK \[authid. N/A authzid. jas gssname. jas@GSASL.EXAMPLE\]'
  - src/gsasl imap.gsasl.example --no-starttls --mechanism GSSAPI -a jas -d 2>&1 | tee /dev/stderr | grep 'Client authentication finished (server trusted)...'
  - mkdir ../gssglue
  - cd ../gssglue
  - ../configure --with-gssapi-impl=gssglue CPPFLAGS=-I/usr/include/gssglue | tail -45
  - make -j$(nproc) | tail -10
  - ./libtool --mode=execute valgrind --error-exitcode=1 --exit-on-first-error=yes examples/smtp-server 2001 & # gssglue with default libgssapi-krb5.so once someone connect
  - while ! netstat -na|grep 0.0.0.0:2001; do sleep 1; done
  - src/gsasl smtp.gsasl.example 2000 --smtp --mechanism GSSAPI -z rms -d | grep '235 OK \[authid. N/A authzid. rms gssname. jas@GSASL.EXAMPLE\]'
  - src/gsasl smtp.gsasl.example 2000 --smtp --mechanism GS2-KRB5 -d | grep '235 OK \[authid. N/A authzid. N/A gssname. jas@GSASL.EXAMPLE\]'
  - src/gsasl smtp.gsasl.example 2001 --smtp --mechanism GSSAPI -z rms -d | grep '235 OK \[authid. N/A authzid. rms gssname. jas@GSASL.EXAMPLE\]'
  - src/gsasl smtp.gsasl.example 2001 --smtp --mechanism GS2-KRB5 -d | grep '235 OK \[authid. N/A authzid. N/A gssname. jas@GSASL.EXAMPLE\]'
  - src/gsasl imap.gsasl.example --no-starttls --mechanism GSSAPI -a jas -d 2>&1 | tee /dev/stderr | grep 'Client authentication finished (server trusted)...'
  - (! env LD_PRELOAD=/usr/lib/x86_64-linux-gnu/libgsasl.so.7 src/gsasl imap.gsasl.example --no-starttls --mechanism GSSAPI -d 2>&1) | tee /dev/stderr | grep 'gsasl. server error' # system libgsasl GSS-API client authzid bug - sends 'root' as authzid
  - src/gsasl imap.gsasl.example --no-starttls --mechanism GSSAPI -d 2>&1 | tee /dev/stderr | grep 'Client authentication finished (server trusted)...'
  - mv /etc/gssapi_mech.conf /etc/gssapi_mech.conf-
  - echo 'fnord' > /etc/gssapi_mech.conf
  - (! src/gsasl smtp.gsasl.example 2000 --smtp --mechanism GSSAPI -d 2>&1) | tee /dev/stderr | grep fnord
  - echo 'libgssapi.so.3 mechglue_internal_krb5_init' > /etc/gssapi_mech.conf # heimdal
  - src/gsasl smtp.gsasl.example 2001 --smtp --mechanism GSSAPI -z rms -d | grep '235 OK \[authid. N/A authzid. rms gssname. jas@GSASL.EXAMPLE\]'
  - src/gsasl smtp.gsasl.example 2001 --smtp --mechanism GS2-KRB5 -d | grep '235 OK \[authid. N/A authzid. N/A gssname. jas@GSASL.EXAMPLE\]'
  - src/gsasl imap.gsasl.example --no-starttls --mechanism GSSAPI -a jas -d 2>&1 | tee /dev/stderr | grep 'Client authentication finished (server trusted)...'
  - ./libtool --mode=execute valgrind --error-exitcode=1 --exit-on-first-error=yes examples/smtp-server 2010 & # gssglue with heimdal libgssapi.so once someone connect
  - while ! netstat -na|grep 0.0.0.0:2010; do sleep 1; done
  - src/gsasl smtp.gsasl.example 2010 --smtp --mechanism GSSAPI -z rms -d | grep '235 OK \[authid. N/A authzid. rms gssname. jas@GSASL.EXAMPLE\]'
  - src/gsasl smtp.gsasl.example 2010 --smtp --mechanism GS2-KRB5 -d | grep '235 OK \[authid. N/A authzid. N/A gssname. jas@GSASL.EXAMPLE\]'
  - mv /etc/gssapi_mech.conf- /etc/gssapi_mech.conf
  - mkdir ../heimdal
  - cd ../heimdal
  - ../configure --with-gssapi-impl=heimdal | tail -45
  - make -j$(nproc) | tail -10
  - ./libtool --mode=execute valgrind --error-exitcode=1 --exit-on-first-error=yes examples/smtp-server 2002 &
  - while ! netstat -na|grep 0.0.0.0:2002; do sleep 1; done
  - src/gsasl smtp.gsasl.example 2000 --smtp --mechanism GSSAPI -z rms -d | grep '235 OK \[authid. N/A authzid. rms gssname. jas@GSASL.EXAMPLE\]'
  - src/gsasl smtp.gsasl.example 2000 --smtp --mechanism GS2-KRB5 -d | grep '235 OK \[authid. N/A authzid. N/A gssname. jas@GSASL.EXAMPLE\]'
  - src/gsasl smtp.gsasl.example 2001 --smtp --mechanism GSSAPI -z rms -d | grep '235 OK \[authid. N/A authzid. rms gssname. jas@GSASL.EXAMPLE\]'
  - src/gsasl smtp.gsasl.example 2001 --smtp --mechanism GS2-KRB5 -d | grep '235 OK \[authid. N/A authzid. N/A gssname. jas@GSASL.EXAMPLE\]'
  - src/gsasl smtp.gsasl.example 2002 --smtp --mechanism GSSAPI -z rms -d | grep '235 OK \[authid. N/A authzid. rms gssname. jas@GSASL.EXAMPLE\]'
  - src/gsasl smtp.gsasl.example 2002 --smtp --mechanism GS2-KRB5 -d | grep '235 OK \[authid. N/A authzid. N/A gssname. jas@GSASL.EXAMPLE\]'
  - src/gsasl smtp.gsasl.example 2010 --smtp --mechanism GSSAPI -z rms -d | grep '235 OK \[authid. N/A authzid. rms gssname. jas@GSASL.EXAMPLE\]'
  - src/gsasl smtp.gsasl.example 2010 --smtp --mechanism GS2-KRB5 -d | grep '235 OK \[authid. N/A authzid. N/A gssname. jas@GSASL.EXAMPLE\]'
  - src/gsasl imap.gsasl.example --no-starttls --mechanism GSSAPI -a jas -d 2>&1 | tee /dev/stderr | grep 'Client authentication finished (server trusted)...'
  - src/gsasl imap.gsasl.example --no-starttls --mechanism GSSAPI -d 2>&1 | tee /dev/stderr | grep 'Client authentication finished (server trusted)...'
  - (! env LD_PRELOAD=/usr/lib/x86_64-linux-gnu/libgsasl.so.7 src/gsasl imap.gsasl.example --no-starttls --mechanism GSSAPI -d 2>&1) | tee /dev/stderr | grep 'gsasl. server error'
  - mkdir ../gss
  - cd ../gss
  - ../configure --with-gssapi-impl=gss | tail -45
  - (! make check LOG_VALGRIND= VALGRIND= | tail -10)
  - datefudge 2022-01-01 make check LOG_VALGRIND= VALGRIND= | tail -10 # tests/gssapi.c actually does something only with libgss
  - ./libtool --mode=execute valgrind --error-exitcode=1 --exit-on-first-error=yes examples/smtp-server 2003 &
  - while ! netstat -na|grep 0.0.0.0:2003; do sleep 1; done
  - expect -c 'spawn shishi jas; expect "*assword" ;send -- "bar\r"; expect ticket; exit'
  - shishi -l  # FIXME XXX use of SHISHI_USER=jas below is a Shishi bug or at least misfeature
  - tail -v -n +0 ~/.shishi/tickets
  - (! env SHISHI_USER=jas src/gsasl imap.gsasl.example --no-starttls --mechanism GSSAPI -a jas -d 2>&1) | tee /dev/stderr | grep 'gss_unwrap' # FIXME XXX no support for AES gss_wrap in GNU GSS
  - (! env SHISHI_USER=jas src/gsasl smtp.gsasl.example 2000 --smtp --mechanism GSSAPI -a jas -d 2>&1) | grep 'gss_unwrap'
  - env SHISHI_USER=jas src/gsasl smtp.gsasl.example 2000 --smtp --mechanism GS2-KRB5 -d | grep '235 OK \[authid. N/A authzid. N/A gssname. jas@GSASL.EXAMPLE\]' # GS2 doesn't use gss_wrap
  - env SHISHI_USER=jas src/gsasl smtp.gsasl.example 2000 --smtp --mechanism GS2-KRB5 -z rms -d | grep '235 OK \[authid. N/A authzid. rms gssname. jas@GSASL.EXAMPLE\]'
  - echo 'client-kdc-etypes=des3-cbc-sha1-kd' > ~/.shishi/shishi.conf # Try 3DES that GNU GSS support
  - shishi -l
  - (! env SHISHI_USER=jas src/gsasl imap.gsasl.example --no-starttls --mechanism GSSAPI -a jas -d 2>&1) | tee /dev/stderr | grep 'BAD_ENCRYPTION_TYPE' # no 3DES key on KDC
  - (! env SHISHI_USER=jas src/gsasl smtp.gsasl.example 2000 --smtp --mechanism GSSAPI -a jas -d 2>&1) | grep 'gss_unwrap' # uses cached AES key for service
  - shishi -d --server-name smtp/smtp.gsasl.example -v # remove AES key for smtp.gsasl.example
  - (! env SHISHI_USER=jas src/gsasl smtp.gsasl.example 2000 --smtp --mechanism GSSAPI -a jas -d 2>&1) | grep 'gss_init_sec_context' # attempts to get 3des key but it doesn't exist
  - kadmin.local ktadd -e des3-cbc-sha1 smtp/smtp.gsasl.example
  - kadmin.local ktadd -e des3-cbc-sha1 -k /etc/dovecot/dovecot.keytab imap/imap.gsasl.example
  - env SHISHI_USER=jas src/gsasl imap.gsasl.example --no-starttls --mechanism GSSAPI -a jas -d 2>&1 | tee /dev/stderr | grep 'Client authentication finished (server trusted)...'
  - env SHISHI_USER=jas src/gsasl smtp.gsasl.example 2000 --smtp --mechanism GSSAPI -d | grep '235 OK \[authid. N/A authzid. N/A gssname. jas@GSASL.EXAMPLE\]'
  - env SHISHI_USER=jas src/gsasl smtp.gsasl.example 2000 --smtp --mechanism GSSAPI -z rms -d | grep '235 OK \[authid. N/A authzid. rms gssname. jas@GSASL.EXAMPLE\]'
  - env SHISHI_USER=jas src/gsasl smtp.gsasl.example 2000 --smtp --mechanism GS2-KRB5 -d | grep '235 OK \[authid. N/A authzid. N/A gssname. jas@GSASL.EXAMPLE\]'
  - env SHISHI_USER=jas src/gsasl smtp.gsasl.example 2001 --smtp --mechanism GSSAPI -d | grep '235 OK \[authid. N/A authzid. N/A gssname. jas@GSASL.EXAMPLE\]'
  - env SHISHI_USER=jas src/gsasl smtp.gsasl.example 2001 --smtp --mechanism GS2-KRB5 -d | grep '235 OK \[authid. N/A authzid. N/A gssname. jas@GSASL.EXAMPLE\]'
  - env SHISHI_USER=jas src/gsasl smtp.gsasl.example 2002 --smtp --mechanism GSSAPI -d | grep '235 OK \[authid. N/A authzid. N/A gssname. jas@GSASL.EXAMPLE\]'
  - env SHISHI_USER=jas src/gsasl smtp.gsasl.example 2002 --smtp --mechanism GS2-KRB5 -d | grep '235 OK \[authid. N/A authzid. N/A gssname. jas@GSASL.EXAMPLE\]'
  - env SHISHI_USER=jas src/gsasl smtp.gsasl.example 2010 --smtp --mechanism GSSAPI -d | grep '235 OK \[authid. N/A authzid. N/A gssname. jas@GSASL.EXAMPLE\]'
  - env SHISHI_USER=jas src/gsasl smtp.gsasl.example 2010 --smtp --mechanism GS2-KRB5 -d | grep '235 OK \[authid. N/A authzid. N/A gssname. jas@GSASL.EXAMPLE\]'
  - (! env SHISHI_USER=jas src/gsasl smtp.gsasl.example 2003 --smtp --mechanism GSSAPI -d 2>&1) | grep 'gss_acquire_cred' # no system keys for shishi-based server
  - (! env SHISHI_USER=jas src/gsasl smtp.gsasl.example 2003 --smtp --mechanism GS2-KRB5 -d 2>&1) | grep 'gss_acquire_cred'
  - rm /etc/krb5.keytab
  - kadmin.local ktadd -e des3-cbc-sha1 smtp/smtp.gsasl.example
  - keytab2shishi --verbose
  - shishi -d --server-name smtp/smtp.gsasl.example -v # remove old 3DES key for smtp.gsasl.example
  - env SHISHI_USER=jas src/gsasl smtp.gsasl.example 2003 --smtp --mechanism GSSAPI -d | grep '235 OK \[authid. N/A authzid. N/A gssname. jas\]' # GSS bug wrt displayname?
  - env SHISHI_USER=jas src/gsasl smtp.gsasl.example 2003 --smtp --mechanism GS2-KRB5 -d | grep '235 OK \[authid. N/A authzid. N/A gssname. jas\]'
  - env SHISHI_USER=jas src/gsasl smtp.gsasl.example 2003 --smtp --mechanism GSSAPI -z rms -d | grep '235 OK \[authid. N/A authzid. rms gssname. jas\]' # GSS bug wrt displayname?
  - env SHISHI_USER=jas src/gsasl smtp.gsasl.example 2003 --smtp --mechanism GS2-KRB5 -z rms -d | grep '235 OK \[authid. N/A authzid. rms gssname. jas\]'
  - mv /etc/gssapi_mech.conf /etc/gssapi_mech.conf-
  - echo 'libgss.so.3 mechglue_internal_krb5_init' > /etc/gssapi_mech.conf # gnu gss
  - env SHISHI_USER=jas ../gssglue/src/gsasl smtp.gsasl.example 2001 --smtp --mechanism GSSAPI -z rms -d | grep '235 OK \[authid. N/A authzid. rms gssname. jas@GSASL.EXAMPLE\]'
  - env SHISHI_USER=jas ../gssglue/src/gsasl smtp.gsasl.example 2001 --smtp --mechanism GS2-KRB5 -d | grep '235 OK \[authid. N/A authzid. N/A gssname. jas@GSASL.EXAMPLE\]'
  - env SHISHI_USER=jas ../gssglue/src/gsasl smtp.gsasl.example 2001 --smtp --mechanism GSSAPI -d | grep '235 OK \[authid. N/A authzid. N/A gssname. jas@GSASL.EXAMPLE\]'
  - mv ~/.shishi/tickets ~/.shishi/tickets-
  - (! env SHISHI_USER=jas ../gssglue/src/gsasl smtp.gsasl.example 2001 --smtp --mechanism GSSAPI -d 2>&1) | grep 'gss_init_sec_context'
  - mv ~/.shishi/tickets- ~/.shishi/tickets
  - ../gssglue/libtool --mode=execute valgrind --error-exitcode=1 --exit-on-first-error=yes ../gssglue/examples/smtp-server 2011 & # gssglue with gnu gss once someone connect
  - while ! netstat -na|grep 0.0.0.0:2011; do sleep 1; done
  - env SHISHI_USER=jas src/gsasl smtp.gsasl.example 2011 --smtp --mechanism GSSAPI -z rms -d | grep '235 OK \[authid. N/A authzid. rms gssname. jas\]'
  - env SHISHI_USER=jas src/gsasl smtp.gsasl.example 2011 --smtp --mechanism GS2-KRB5 -d | grep '235 OK \[authid. N/A authzid. N/A gssname. jas\]'
  - mv /etc/shishi/shishi.keys /etc/shishi/shishi.keys-
  - (! env SHISHI_USER=jas src/gsasl smtp.gsasl.example 2011 --smtp --mechanism GSSAPI -a jas -d 2>&1) | grep 'gss_acquire'
  - mv /etc/shishi/shishi.keys- /etc/shishi/shishi.keys
  - shishi -d
  - (! env SHISHI_USER=jas src/gsasl smtp.gsasl.example 2011 --smtp --mechanism GSSAPI -a jas -d 2>&1) | grep 'gss_init_sec'
  - mv /etc/gssapi_mech.conf- /etc/gssapi_mech.conf
  - sleep 10 # allow log outputs to catch up
