From a86dd9c96ac249942b3564ddd211ef8bb8ef92e22a8e4efaedf9d3acac08f97e Mon Sep 17 00:00:00 2001 From: Pedro Monreal Gonzalez Date: Mon, 2 Dec 2024 12:11:19 +0000 Subject: [PATCH 1/8] - Remove unrecognized option: --enable-m-guard OBS-URL: https://build.opensuse.org/package/show/devel:libraries:c_c++/libgcrypt?expand=0&rev=182 --- .gitattributes | 23 + .gitignore | 1 + baselibs.conf | 8 + hwf.deny | 34 + libgcrypt-1.10.0-allow_FSM_same_state.patch | 15 + libgcrypt-1.10.3.tar.bz2 | 3 + libgcrypt-1.10.3.tar.bz2.sig | Bin 0 -> 238 bytes libgcrypt-1.11.0.tar.bz2 | 3 + libgcrypt-1.11.0.tar.bz2.sig | Bin 0 -> 119 bytes ...poly1305-Optimized-chacha20-poly1305.patch | 1993 +++++++++++++++++ libgcrypt-FIPS-SLI-hash-mac.patch | 172 ++ libgcrypt-FIPS-SLI-kdf-leylength.patch | 42 + libgcrypt-FIPS-SLI-pk.patch | 177 ++ libgcrypt-FIPS-jitter-errorcodes.patch | 16 + libgcrypt-FIPS-jitter-standalone.patch | 183 ++ libgcrypt-FIPS-jitter-whole-entropy.patch | 41 + libgcrypt-FIPS-rndjent_poll.patch | 114 + libgcrypt-jitterentropy-3.4.0.patch | 618 +++++ libgcrypt-no-deprecated-grep-alias.patch | 35 + libgcrypt-nobetasuffix.patch | 24 + ...e-P10-assembly-with-ENABLE_FORCE_SOF.patch | 76 + libgcrypt.changes | 1857 +++++++++++++++ libgcrypt.keyring | 86 + libgcrypt.spec | 192 ++ random.conf | 9 + 25 files changed, 5722 insertions(+) create mode 100644 .gitattributes create mode 100644 .gitignore create mode 100644 baselibs.conf create mode 100644 hwf.deny create mode 100644 libgcrypt-1.10.0-allow_FSM_same_state.patch create mode 100644 libgcrypt-1.10.3.tar.bz2 create mode 100644 libgcrypt-1.10.3.tar.bz2.sig create mode 100644 libgcrypt-1.11.0.tar.bz2 create mode 100644 libgcrypt-1.11.0.tar.bz2.sig create mode 100644 libgcrypt-Chacha20-poly1305-Optimized-chacha20-poly1305.patch create mode 100644 libgcrypt-FIPS-SLI-hash-mac.patch create mode 100644 libgcrypt-FIPS-SLI-kdf-leylength.patch create mode 100644 libgcrypt-FIPS-SLI-pk.patch create mode 100644 libgcrypt-FIPS-jitter-errorcodes.patch create mode 100644 libgcrypt-FIPS-jitter-standalone.patch create mode 100644 libgcrypt-FIPS-jitter-whole-entropy.patch create mode 100644 libgcrypt-FIPS-rndjent_poll.patch create mode 100644 libgcrypt-jitterentropy-3.4.0.patch create mode 100644 libgcrypt-no-deprecated-grep-alias.patch create mode 100644 libgcrypt-nobetasuffix.patch create mode 100644 libgcrypt-ppc-enable-P10-assembly-with-ENABLE_FORCE_SOF.patch create mode 100644 libgcrypt.changes create mode 100644 libgcrypt.keyring create mode 100644 libgcrypt.spec create mode 100644 random.conf diff --git a/.gitattributes b/.gitattributes new file mode 100644 index 0000000..9b03811 --- /dev/null +++ b/.gitattributes @@ -0,0 +1,23 @@ +## Default LFS +*.7z filter=lfs diff=lfs merge=lfs -text +*.bsp filter=lfs diff=lfs merge=lfs -text +*.bz2 filter=lfs diff=lfs merge=lfs -text +*.gem filter=lfs diff=lfs merge=lfs -text +*.gz filter=lfs diff=lfs merge=lfs -text +*.jar filter=lfs diff=lfs merge=lfs -text +*.lz filter=lfs diff=lfs merge=lfs -text +*.lzma filter=lfs diff=lfs merge=lfs -text +*.obscpio filter=lfs diff=lfs merge=lfs -text +*.oxt filter=lfs diff=lfs merge=lfs -text +*.pdf filter=lfs diff=lfs merge=lfs -text +*.png filter=lfs diff=lfs merge=lfs -text +*.rpm filter=lfs diff=lfs merge=lfs -text +*.tbz filter=lfs diff=lfs merge=lfs -text +*.tbz2 filter=lfs diff=lfs merge=lfs -text +*.tgz filter=lfs diff=lfs merge=lfs -text +*.ttf filter=lfs diff=lfs merge=lfs -text +*.txz filter=lfs diff=lfs merge=lfs -text +*.whl filter=lfs diff=lfs merge=lfs -text +*.xz filter=lfs diff=lfs merge=lfs -text +*.zip filter=lfs diff=lfs merge=lfs -text +*.zst filter=lfs diff=lfs merge=lfs -text diff --git a/.gitignore b/.gitignore new file mode 100644 index 0000000..57affb6 --- /dev/null +++ b/.gitignore @@ -0,0 +1 @@ +.osc diff --git a/baselibs.conf b/baselibs.conf new file mode 100644 index 0000000..a018a0a --- /dev/null +++ b/baselibs.conf @@ -0,0 +1,8 @@ +libgcrypt20 + provides "libgcrypt- = " + obsoletes "libgcrypt- <= " + provides "libgcrypt20-hmac- = -%release" + obsoletes "libgcrypt20-hmac- < -%release" +libgcrypt-devel + requires -libgcrypt- + requires "libgcrypt20- = " diff --git a/hwf.deny b/hwf.deny new file mode 100644 index 0000000..2236468 --- /dev/null +++ b/hwf.deny @@ -0,0 +1,34 @@ +# This file can be used to globally disable the use of hardware +# based optimizations. Supported options are: +# padlock-rng +# padlock-aes +# padlock-sha +# padlock-mmul +# intel-cpu +# intel-fast-shld +# intel-bmi2 +# intel-ssse3 +# intel-sse4.1 +# intel-pclmul +# intel-aesni +# intel-rdrand +# intel-avx +# intel-avx2 +# intel-fast-vpgather +# intel-rdtsc +# intel-shaext +# intel-vaes-vpclmul +# arm-neon +# arm-aes +# arm-sha1 +# arm-sha2 +# arm-pmull +# ppc-vcrypto +# ppc-arch_3_00 +# ppc-arch_2_07 +# ppc-arch_3_10 +# s390x-msa +# s390x-msa-4 +# s390x-msa-8 +# s390x-msa-9 +# s390x-vx diff --git a/libgcrypt-1.10.0-allow_FSM_same_state.patch b/libgcrypt-1.10.0-allow_FSM_same_state.patch new file mode 100644 index 0000000..843cfea --- /dev/null +++ b/libgcrypt-1.10.0-allow_FSM_same_state.patch @@ -0,0 +1,15 @@ +Index: libgcrypt-1.10.0/src/fips.c +=================================================================== +--- libgcrypt-1.10.0.orig/src/fips.c ++++ libgcrypt-1.10.0/src/fips.c +@@ -890,6 +890,10 @@ fips_new_state (enum module_states new_s + + } + ++ /* Allow a transition to the current state */ ++ if (current_state == new_state) ++ ok = 1; ++ + if (ok) + { + current_state = new_state; diff --git a/libgcrypt-1.10.3.tar.bz2 b/libgcrypt-1.10.3.tar.bz2 new file mode 100644 index 0000000..653803f --- /dev/null +++ b/libgcrypt-1.10.3.tar.bz2 @@ -0,0 +1,3 @@ +version https://git-lfs.github.com/spec/v1 +oid sha256:8b0870897ac5ac67ded568dcfadf45969cfa8a6beb0fd60af2a9eadc2a3272aa +size 3783827 diff --git a/libgcrypt-1.10.3.tar.bz2.sig b/libgcrypt-1.10.3.tar.bz2.sig new file mode 100644 index 0000000000000000000000000000000000000000000000000000000000000000..4172518bc29eafb0304aa2c7def555b970a6accea442a7542087b98c44485773 GIT binary patch literal 238 zcmeAuWnmEGV2~A4WXWBXm$E!p!y#PSlPRcU`VKV*t6Qv0sliEW8MrtFU?N}p82-vF z=ITAZ*qv<_(;dOxrp<8yN$DSFdR>!gz3<7nXwGD1Muyiq%7Ht6>~>#&|Ibh5V-ok6 zm#e%* literal 0 HcmV?d00001 diff --git a/libgcrypt-1.11.0.tar.bz2 b/libgcrypt-1.11.0.tar.bz2 new file mode 100644 index 0000000..28d1068 --- /dev/null +++ b/libgcrypt-1.11.0.tar.bz2 @@ -0,0 +1,3 @@ +version https://git-lfs.github.com/spec/v1 +oid sha256:09120c9867ce7f2081d6aaa1775386b98c2f2f246135761aae47d81f58685b9c +size 4180345 diff --git a/libgcrypt-1.11.0.tar.bz2.sig b/libgcrypt-1.11.0.tar.bz2.sig new file mode 100644 index 0000000000000000000000000000000000000000000000000000000000000000..2debe948a9ffbbc9c835efae5cce0c65517df124ea67ba4cc04d1dffdd7b3160 GIT binary patch literal 119 zcmeAuWnmEGV2~A4WXWBXm$E!p!y#PSlPRcU`VKV*t6Qv0X+=xZ7`QkEU?T178UE=O z)|M}6Y-XM7H2JWvsFP0?XX&fr%U>#e4G(K{b;T<%GJNLLSKO|_Z@vBphsk!en!WkH T(k44uvO>;;f4NZp`vWfkiCryG literal 0 HcmV?d00001 diff --git a/libgcrypt-Chacha20-poly1305-Optimized-chacha20-poly1305.patch b/libgcrypt-Chacha20-poly1305-Optimized-chacha20-poly1305.patch new file mode 100644 index 0000000..5877fee --- /dev/null +++ b/libgcrypt-Chacha20-poly1305-Optimized-chacha20-poly1305.patch @@ -0,0 +1,1993 @@ +commit 88fe7ac33eb4cb4dff76a5cc7fca50da5fb0ee3a +Author: Danny Tsen +Date: Sun Jun 12 21:30:19 2022 +0300 + + Chacha20 poly1305 Optimized chacha20 poly1305 for P10 operation + + * configure.ac: Added chacha20 and poly1305 assembly implementations. + * cipher/chacha20-p10le-8x.s: (New) - support 8 blocks (512 bytes) + unrolling. + * cipher/poly1305-p10le.s: (New) - support 4 blocks (128 bytes) + unrolling. + * cipher/Makefile.am: Added new chacha20 and poly1305 files. + * cipher/chacha20.c: Added PPC p10 le support for 8x chacha20. + * cipher/poly1305.c: Added PPC p10 le support for 4x poly1305. + * cipher/poly1305-internal.h: Added PPC p10 le support for poly1305. + --- + + GnuPG-bug-id: 6006 + Signed-off-by: Danny Tsen + [jk: cosmetic changes to C code] + [jk: fix building on ppc64be] + Signed-off-by: Jussi Kivilinna + +Index: libgcrypt-1.10.2/cipher/Makefile.am +=================================================================== +--- libgcrypt-1.10.2.orig/cipher/Makefile.am ++++ libgcrypt-1.10.2/cipher/Makefile.am +@@ -83,6 +83,7 @@ EXTRA_libcipher_la_SOURCES = \ + chacha20.c chacha20-amd64-ssse3.S chacha20-amd64-avx2.S \ + chacha20-armv7-neon.S chacha20-aarch64.S \ + chacha20-ppc.c chacha20-s390x.S \ ++ chacha20-p10le-8x.s \ + cipher-gcm-ppc.c cipher-gcm-intel-pclmul.c cipher-gcm-armv7-neon.S \ + cipher-gcm-armv8-aarch32-ce.S cipher-gcm-armv8-aarch64-ce.S \ + crc.c crc-intel-pclmul.c crc-armv8-ce.c \ +@@ -99,6 +100,7 @@ EXTRA_libcipher_la_SOURCES = \ + md4.c \ + md5.c \ + poly1305-s390x.S \ ++ poly1305-p10le.s \ + rijndael.c rijndael-internal.h rijndael-tables.h \ + rijndael-aesni.c rijndael-padlock.c \ + rijndael-amd64.S rijndael-arm.S \ +Index: libgcrypt-1.10.2/cipher/chacha20-p10le-8x.s +=================================================================== +--- /dev/null ++++ libgcrypt-1.10.2/cipher/chacha20-p10le-8x.s +@@ -0,0 +1,864 @@ ++# Copyright 2021- IBM Inc. All rights reserved ++# ++# This file is part of Libgcrypt. ++# ++# Libgcrypt is free software; you can redistribute it and/or modify ++# it under the terms of the GNU Lesser General Public License as ++# published by the Free Software Foundation; either version 2.1 of ++# the License, or (at your option) any later version. ++# ++# Libgcrypt 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 Lesser General Public License for more details. ++# ++# You should have received a copy of the GNU Lesser General Public ++# License along with this program; if not, see . ++# ++#=================================================================================== ++# Written by Danny Tsen ++# ++# This function handles multiple 64-byte block data length ++# and the length should be more than 512 bytes. ++# ++# unsigned int _gcry_chacha20_p10le_8x(u32 *state, byte *dst, const byte *src, size_t len); ++# ++# r1 - top of the stack ++# r3 to r10 input parameters ++# r3 - out ++# r4 - inp ++# r5 - len ++# r6 - key[8] ++# r7 - counter[4] ++# ++# do rounds, 8 quarter rounds ++# 1. a += b; d ^= a; d <<<= 16; ++# 2. c += d; b ^= c; b <<<= 12; ++# 3. a += b; d ^= a; d <<<= 8; ++# 4. c += d; b ^= c; b <<<= 7 ++# ++# row1 = (row1 + row2), row4 = row1 xor row4, row4 rotate each word by 16 ++# row3 = (row3 + row4), row2 = row3 xor row2, row2 rotate each word by 12 ++# row1 = (row1 + row2), row4 = row1 xor row4, row4 rotate each word by 8 ++# row3 = (row3 + row4), row2 = row3 xor row2, row2 rotate each word by 7 ++# ++# 4 blocks (a b c d) ++# ++# a0 b0 c0 d0 ++# a1 b1 c1 d1 ++# ... ++# a4 b4 c4 d4 ++# ... ++# a8 b8 c8 d8 ++# ... ++# a12 b12 c12 d12 ++# a13 ... ++# a14 ... ++# a15 b15 c15 d15 ++# ++# Column round (v0, v4, v8, v12, v1, v5, v9, v13, v2, v6, v10, v14, v3, v7, v11, v15) ++# Diagnal round (v0, v5, v10, v15, v1, v6, v11, v12, v2, v7, v8, v13, v3, v4, v9, v14) ++# ++.text ++ ++.macro QT_loop_8x ++ # QR(v0, v4, v8, v12, v1, v5, v9, v13, v2, v6, v10, v14, v3, v7, v11, v15) ++ xxlor 0, 32+25, 32+25 ++ xxlor 32+25, 20, 20 ++ vadduwm 0, 0, 4 ++ vadduwm 1, 1, 5 ++ vadduwm 2, 2, 6 ++ vadduwm 3, 3, 7 ++ vadduwm 16, 16, 20 ++ vadduwm 17, 17, 21 ++ vadduwm 18, 18, 22 ++ vadduwm 19, 19, 23 ++ ++ vpermxor 12, 12, 0, 25 ++ vpermxor 13, 13, 1, 25 ++ vpermxor 14, 14, 2, 25 ++ vpermxor 15, 15, 3, 25 ++ vpermxor 28, 28, 16, 25 ++ vpermxor 29, 29, 17, 25 ++ vpermxor 30, 30, 18, 25 ++ vpermxor 31, 31, 19, 25 ++ xxlor 32+25, 0, 0 ++ vadduwm 8, 8, 12 ++ vadduwm 9, 9, 13 ++ vadduwm 10, 10, 14 ++ vadduwm 11, 11, 15 ++ vadduwm 24, 24, 28 ++ vadduwm 25, 25, 29 ++ vadduwm 26, 26, 30 ++ vadduwm 27, 27, 31 ++ vxor 4, 4, 8 ++ vxor 5, 5, 9 ++ vxor 6, 6, 10 ++ vxor 7, 7, 11 ++ vxor 20, 20, 24 ++ vxor 21, 21, 25 ++ vxor 22, 22, 26 ++ vxor 23, 23, 27 ++ ++ xxlor 0, 32+25, 32+25 ++ xxlor 32+25, 21, 21 ++ vrlw 4, 4, 25 # ++ vrlw 5, 5, 25 ++ vrlw 6, 6, 25 ++ vrlw 7, 7, 25 ++ vrlw 20, 20, 25 # ++ vrlw 21, 21, 25 ++ vrlw 22, 22, 25 ++ vrlw 23, 23, 25 ++ xxlor 32+25, 0, 0 ++ vadduwm 0, 0, 4 ++ vadduwm 1, 1, 5 ++ vadduwm 2, 2, 6 ++ vadduwm 3, 3, 7 ++ vadduwm 16, 16, 20 ++ vadduwm 17, 17, 21 ++ vadduwm 18, 18, 22 ++ vadduwm 19, 19, 23 ++ ++ xxlor 0, 32+25, 32+25 ++ xxlor 32+25, 22, 22 ++ vpermxor 12, 12, 0, 25 ++ vpermxor 13, 13, 1, 25 ++ vpermxor 14, 14, 2, 25 ++ vpermxor 15, 15, 3, 25 ++ vpermxor 28, 28, 16, 25 ++ vpermxor 29, 29, 17, 25 ++ vpermxor 30, 30, 18, 25 ++ vpermxor 31, 31, 19, 25 ++ xxlor 32+25, 0, 0 ++ vadduwm 8, 8, 12 ++ vadduwm 9, 9, 13 ++ vadduwm 10, 10, 14 ++ vadduwm 11, 11, 15 ++ vadduwm 24, 24, 28 ++ vadduwm 25, 25, 29 ++ vadduwm 26, 26, 30 ++ vadduwm 27, 27, 31 ++ xxlor 0, 32+28, 32+28 ++ xxlor 32+28, 23, 23 ++ vxor 4, 4, 8 ++ vxor 5, 5, 9 ++ vxor 6, 6, 10 ++ vxor 7, 7, 11 ++ vxor 20, 20, 24 ++ vxor 21, 21, 25 ++ vxor 22, 22, 26 ++ vxor 23, 23, 27 ++ vrlw 4, 4, 28 # ++ vrlw 5, 5, 28 ++ vrlw 6, 6, 28 ++ vrlw 7, 7, 28 ++ vrlw 20, 20, 28 # ++ vrlw 21, 21, 28 ++ vrlw 22, 22, 28 ++ vrlw 23, 23, 28 ++ xxlor 32+28, 0, 0 ++ ++ # QR(v0, v5, v10, v15, v1, v6, v11, v12, v2, v7, v8, v13, v3, v4, v9, v14) ++ xxlor 0, 32+25, 32+25 ++ xxlor 32+25, 20, 20 ++ vadduwm 0, 0, 5 ++ vadduwm 1, 1, 6 ++ vadduwm 2, 2, 7 ++ vadduwm 3, 3, 4 ++ vadduwm 16, 16, 21 ++ vadduwm 17, 17, 22 ++ vadduwm 18, 18, 23 ++ vadduwm 19, 19, 20 ++ ++ vpermxor 15, 15, 0, 25 ++ vpermxor 12, 12, 1, 25 ++ vpermxor 13, 13, 2, 25 ++ vpermxor 14, 14, 3, 25 ++ vpermxor 31, 31, 16, 25 ++ vpermxor 28, 28, 17, 25 ++ vpermxor 29, 29, 18, 25 ++ vpermxor 30, 30, 19, 25 ++ ++ xxlor 32+25, 0, 0 ++ vadduwm 10, 10, 15 ++ vadduwm 11, 11, 12 ++ vadduwm 8, 8, 13 ++ vadduwm 9, 9, 14 ++ vadduwm 26, 26, 31 ++ vadduwm 27, 27, 28 ++ vadduwm 24, 24, 29 ++ vadduwm 25, 25, 30 ++ vxor 5, 5, 10 ++ vxor 6, 6, 11 ++ vxor 7, 7, 8 ++ vxor 4, 4, 9 ++ vxor 21, 21, 26 ++ vxor 22, 22, 27 ++ vxor 23, 23, 24 ++ vxor 20, 20, 25 ++ ++ xxlor 0, 32+25, 32+25 ++ xxlor 32+25, 21, 21 ++ vrlw 5, 5, 25 ++ vrlw 6, 6, 25 ++ vrlw 7, 7, 25 ++ vrlw 4, 4, 25 ++ vrlw 21, 21, 25 ++ vrlw 22, 22, 25 ++ vrlw 23, 23, 25 ++ vrlw 20, 20, 25 ++ xxlor 32+25, 0, 0 ++ ++ vadduwm 0, 0, 5 ++ vadduwm 1, 1, 6 ++ vadduwm 2, 2, 7 ++ vadduwm 3, 3, 4 ++ vadduwm 16, 16, 21 ++ vadduwm 17, 17, 22 ++ vadduwm 18, 18, 23 ++ vadduwm 19, 19, 20 ++ ++ xxlor 0, 32+25, 32+25 ++ xxlor 32+25, 22, 22 ++ vpermxor 15, 15, 0, 25 ++ vpermxor 12, 12, 1, 25 ++ vpermxor 13, 13, 2, 25 ++ vpermxor 14, 14, 3, 25 ++ vpermxor 31, 31, 16, 25 ++ vpermxor 28, 28, 17, 25 ++ vpermxor 29, 29, 18, 25 ++ vpermxor 30, 30, 19, 25 ++ xxlor 32+25, 0, 0 ++ ++ vadduwm 10, 10, 15 ++ vadduwm 11, 11, 12 ++ vadduwm 8, 8, 13 ++ vadduwm 9, 9, 14 ++ vadduwm 26, 26, 31 ++ vadduwm 27, 27, 28 ++ vadduwm 24, 24, 29 ++ vadduwm 25, 25, 30 ++ ++ xxlor 0, 32+28, 32+28 ++ xxlor 32+28, 23, 23 ++ vxor 5, 5, 10 ++ vxor 6, 6, 11 ++ vxor 7, 7, 8 ++ vxor 4, 4, 9 ++ vxor 21, 21, 26 ++ vxor 22, 22, 27 ++ vxor 23, 23, 24 ++ vxor 20, 20, 25 ++ vrlw 5, 5, 28 ++ vrlw 6, 6, 28 ++ vrlw 7, 7, 28 ++ vrlw 4, 4, 28 ++ vrlw 21, 21, 28 ++ vrlw 22, 22, 28 ++ vrlw 23, 23, 28 ++ vrlw 20, 20, 28 ++ xxlor 32+28, 0, 0 ++.endm ++ ++.macro QT_loop_4x ++ # QR(v0, v4, v8, v12, v1, v5, v9, v13, v2, v6, v10, v14, v3, v7, v11, v15) ++ vadduwm 0, 0, 4 ++ vadduwm 1, 1, 5 ++ vadduwm 2, 2, 6 ++ vadduwm 3, 3, 7 ++ vpermxor 12, 12, 0, 20 ++ vpermxor 13, 13, 1, 20 ++ vpermxor 14, 14, 2, 20 ++ vpermxor 15, 15, 3, 20 ++ vadduwm 8, 8, 12 ++ vadduwm 9, 9, 13 ++ vadduwm 10, 10, 14 ++ vadduwm 11, 11, 15 ++ vxor 4, 4, 8 ++ vxor 5, 5, 9 ++ vxor 6, 6, 10 ++ vxor 7, 7, 11 ++ vrlw 4, 4, 21 ++ vrlw 5, 5, 21 ++ vrlw 6, 6, 21 ++ vrlw 7, 7, 21 ++ vadduwm 0, 0, 4 ++ vadduwm 1, 1, 5 ++ vadduwm 2, 2, 6 ++ vadduwm 3, 3, 7 ++ vpermxor 12, 12, 0, 22 ++ vpermxor 13, 13, 1, 22 ++ vpermxor 14, 14, 2, 22 ++ vpermxor 15, 15, 3, 22 ++ vadduwm 8, 8, 12 ++ vadduwm 9, 9, 13 ++ vadduwm 10, 10, 14 ++ vadduwm 11, 11, 15 ++ vxor 4, 4, 8 ++ vxor 5, 5, 9 ++ vxor 6, 6, 10 ++ vxor 7, 7, 11 ++ vrlw 4, 4, 23 ++ vrlw 5, 5, 23 ++ vrlw 6, 6, 23 ++ vrlw 7, 7, 23 ++ ++ # QR(v0, v5, v10, v15, v1, v6, v11, v12, v2, v7, v8, v13, v3, v4, v9, v14) ++ vadduwm 0, 0, 5 ++ vadduwm 1, 1, 6 ++ vadduwm 2, 2, 7 ++ vadduwm 3, 3, 4 ++ vpermxor 15, 15, 0, 20 ++ vpermxor 12, 12, 1, 20 ++ vpermxor 13, 13, 2, 20 ++ vpermxor 14, 14, 3, 20 ++ vadduwm 10, 10, 15 ++ vadduwm 11, 11, 12 ++ vadduwm 8, 8, 13 ++ vadduwm 9, 9, 14 ++ vxor 5, 5, 10 ++ vxor 6, 6, 11 ++ vxor 7, 7, 8 ++ vxor 4, 4, 9 ++ vrlw 5, 5, 21 ++ vrlw 6, 6, 21 ++ vrlw 7, 7, 21 ++ vrlw 4, 4, 21 ++ vadduwm 0, 0, 5 ++ vadduwm 1, 1, 6 ++ vadduwm 2, 2, 7 ++ vadduwm 3, 3, 4 ++ vpermxor 15, 15, 0, 22 ++ vpermxor 12, 12, 1, 22 ++ vpermxor 13, 13, 2, 22 ++ vpermxor 14, 14, 3, 22 ++ vadduwm 10, 10, 15 ++ vadduwm 11, 11, 12 ++ vadduwm 8, 8, 13 ++ vadduwm 9, 9, 14 ++ vxor 5, 5, 10 ++ vxor 6, 6, 11 ++ vxor 7, 7, 8 ++ vxor 4, 4, 9 ++ vrlw 5, 5, 23 ++ vrlw 6, 6, 23 ++ vrlw 7, 7, 23 ++ vrlw 4, 4, 23 ++.endm ++ ++# Transpose ++.macro TP_4x a0 a1 a2 a3 ++ xxmrghw 10, 32+\a0, 32+\a1 # a0, a1, b0, b1 ++ xxmrghw 11, 32+\a2, 32+\a3 # a2, a3, b2, b3 ++ xxmrglw 12, 32+\a0, 32+\a1 # c0, c1, d0, d1 ++ xxmrglw 13, 32+\a2, 32+\a3 # c2, c3, d2, d3 ++ xxpermdi 32+\a0, 10, 11, 0 # a0, a1, a2, a3 ++ xxpermdi 32+\a1, 10, 11, 3 # b0, b1, b2, b3 ++ xxpermdi 32+\a2, 12, 13, 0 # c0, c1, c2, c3 ++ xxpermdi 32+\a3, 12, 13, 3 # d0, d1, d2, d3 ++.endm ++ ++# key stream = working state + state ++.macro Add_state S ++ vadduwm \S+0, \S+0, 16-\S ++ vadduwm \S+4, \S+4, 17-\S ++ vadduwm \S+8, \S+8, 18-\S ++ vadduwm \S+12, \S+12, 19-\S ++ ++ vadduwm \S+1, \S+1, 16-\S ++ vadduwm \S+5, \S+5, 17-\S ++ vadduwm \S+9, \S+9, 18-\S ++ vadduwm \S+13, \S+13, 19-\S ++ ++ vadduwm \S+2, \S+2, 16-\S ++ vadduwm \S+6, \S+6, 17-\S ++ vadduwm \S+10, \S+10, 18-\S ++ vadduwm \S+14, \S+14, 19-\S ++ ++ vadduwm \S+3, \S+3, 16-\S ++ vadduwm \S+7, \S+7, 17-\S ++ vadduwm \S+11, \S+11, 18-\S ++ vadduwm \S+15, \S+15, 19-\S ++.endm ++ ++# ++# write 256 bytes ++# ++.macro Write_256 S ++ add 9, 14, 5 ++ add 16, 14, 4 ++ lxvw4x 0, 0, 9 ++ lxvw4x 1, 17, 9 ++ lxvw4x 2, 18, 9 ++ lxvw4x 3, 19, 9 ++ lxvw4x 4, 20, 9 ++ lxvw4x 5, 21, 9 ++ lxvw4x 6, 22, 9 ++ lxvw4x 7, 23, 9 ++ lxvw4x 8, 24, 9 ++ lxvw4x 9, 25, 9 ++ lxvw4x 10, 26, 9 ++ lxvw4x 11, 27, 9 ++ lxvw4x 12, 28, 9 ++ lxvw4x 13, 29, 9 ++ lxvw4x 14, 30, 9 ++ lxvw4x 15, 31, 9 ++ ++ xxlxor \S+32, \S+32, 0 ++ xxlxor \S+36, \S+36, 1 ++ xxlxor \S+40, \S+40, 2 ++ xxlxor \S+44, \S+44, 3 ++ xxlxor \S+33, \S+33, 4 ++ xxlxor \S+37, \S+37, 5 ++ xxlxor \S+41, \S+41, 6 ++ xxlxor \S+45, \S+45, 7 ++ xxlxor \S+34, \S+34, 8 ++ xxlxor \S+38, \S+38, 9 ++ xxlxor \S+42, \S+42, 10 ++ xxlxor \S+46, \S+46, 11 ++ xxlxor \S+35, \S+35, 12 ++ xxlxor \S+39, \S+39, 13 ++ xxlxor \S+43, \S+43, 14 ++ xxlxor \S+47, \S+47, 15 ++ ++ stxvw4x \S+32, 0, 16 ++ stxvw4x \S+36, 17, 16 ++ stxvw4x \S+40, 18, 16 ++ stxvw4x \S+44, 19, 16 ++ ++ stxvw4x \S+33, 20, 16 ++ stxvw4x \S+37, 21, 16 ++ stxvw4x \S+41, 22, 16 ++ stxvw4x \S+45, 23, 16 ++ ++ stxvw4x \S+34, 24, 16 ++ stxvw4x \S+38, 25, 16 ++ stxvw4x \S+42, 26, 16 ++ stxvw4x \S+46, 27, 16 ++ ++ stxvw4x \S+35, 28, 16 ++ stxvw4x \S+39, 29, 16 ++ stxvw4x \S+43, 30, 16 ++ stxvw4x \S+47, 31, 16 ++ ++.endm ++ ++# ++# unsigned int _gcry_chacha20_p10le_8x(u32 *state, byte *dst, const byte *src, size_t len); ++# ++.global _gcry_chacha20_p10le_8x ++.align 5 ++_gcry_chacha20_p10le_8x: ++ cmpdi 6, 512 ++ blt Out_no_chacha ++ ++ stdu 1,-1024(1) ++ mflr 0 ++ ++ std 14,112(1) ++ std 15,120(1) ++ std 16,128(1) ++ std 17,136(1) ++ std 18,144(1) ++ std 19,152(1) ++ std 20,160(1) ++ std 21,168(1) ++ std 22,176(1) ++ std 23,184(1) ++ std 24,192(1) ++ std 25,200(1) ++ std 26,208(1) ++ std 27,216(1) ++ std 28,224(1) ++ std 29,232(1) ++ std 30,240(1) ++ std 31,248(1) ++ std 0, 1040(1) ++ ++ li 17, 16 ++ li 18, 32 ++ li 19, 48 ++ li 20, 64 ++ li 21, 80 ++ li 22, 96 ++ li 23, 112 ++ li 24, 128 ++ li 25, 144 ++ li 26, 160 ++ li 27, 176 ++ li 28, 192 ++ li 29, 208 ++ li 30, 224 ++ li 31, 240 ++ addi 9, 1, 256 ++ stvx 20, 0, 9 ++ stvx 21, 17, 9 ++ stvx 22, 18, 9 ++ stvx 23, 19, 9 ++ stvx 24, 20, 9 ++ stvx 25, 21, 9 ++ stvx 26, 22, 9 ++ stvx 27, 23, 9 ++ stvx 28, 24, 9 ++ stvx 29, 25, 9 ++ stvx 30, 26, 9 ++ stvx 31, 27, 9 ++ ++ add 9, 9, 27 ++ addi 14, 17, 16 ++ stxvx 14, 14, 9 ++ addi 14, 14, 16 ++ stxvx 15, 14, 9 ++ addi 14, 14, 16 ++ stxvx 16, 14, 9 ++ addi 14, 14, 16 ++ stxvx 17, 14, 9 ++ addi 14, 14, 16 ++ stxvx 18, 14, 9 ++ addi 14, 14, 16 ++ stxvx 19, 14, 9 ++ addi 14, 14, 16 ++ stxvx 20, 14, 9 ++ addi 14, 14, 16 ++ stxvx 21, 14, 9 ++ addi 14, 14, 16 ++ stxvx 22, 14, 9 ++ addi 14, 14, 16 ++ stxvx 23, 14, 9 ++ addi 14, 14, 16 ++ stxvx 24, 14, 9 ++ addi 14, 14, 16 ++ stxvx 25, 14, 9 ++ addi 14, 14, 16 ++ stxvx 26, 14, 9 ++ addi 14, 14, 16 ++ stxvx 27, 14, 9 ++ addi 14, 14, 16 ++ stxvx 28, 14, 9 ++ addi 14, 14, 16 ++ stxvx 29, 14, 9 ++ addi 14, 14, 16 ++ stxvx 30, 14, 9 ++ addi 14, 14, 16 ++ stxvx 31, 14, 9 ++ ++ mr 15, 6 # len ++ li 14, 0 # offset to inp and outp ++ ++ ld 10, sigma@got(2) ++ ++ lxvw4x 48, 0, 3 # vr16, constants ++ lxvw4x 49, 17, 3 # vr17, key 1 ++ lxvw4x 50, 18, 3 # vr18, key 2 ++ lxvw4x 51, 19, 3 # vr19, counter, nonce ++ ++ lxvw4x 62, 19, 10 # vr30, 4 ++ ++ vspltisw 21, 12 ++ vspltisw 23, 7 ++ ++ ld 11, permx@got(2) ++ lxvw4x 32+20, 0, 11 ++ lxvw4x 32+22, 17, 11 ++ ++ li 8, 10 ++ mtctr 8 ++ ++ xxlor 16, 48, 48 ++ xxlor 17, 49, 49 ++ xxlor 18, 50, 50 ++ xxlor 19, 51, 51 ++ ++ vspltisw 25, 4 ++ vspltisw 26, 8 ++ ++ xxlor 16, 48, 48 ++ xxlor 17, 49, 49 ++ xxlor 18, 50, 50 ++ xxlor 19, 51, 51 ++ ++ xxlor 25, 32+26, 32+26 ++ xxlor 24, 32+25, 32+25 ++ ++ vadduwm 31, 30, 25 # (0, 1, 2, 3) + (4, 4, 4, 4) ++ xxlor 30, 32+30, 32+30 ++ xxlor 31, 32+31, 32+31 ++ ++ xxlor 20, 32+20, 32+20 ++ xxlor 21, 32+21, 32+21 ++ xxlor 22, 32+22, 32+22 ++ xxlor 23, 32+23, 32+23 ++ ++Loop_8x: ++ lvx 0, 20, 10 ++ lvx 1, 21, 10 ++ lvx 2, 22, 10 ++ lvx 3, 23, 10 ++ xxspltw 32+4, 17, 0 ++ xxspltw 32+5, 17, 1 ++ xxspltw 32+6, 17, 2 ++ xxspltw 32+7, 17, 3 ++ xxspltw 32+8, 18, 0 ++ xxspltw 32+9, 18, 1 ++ xxspltw 32+10, 18, 2 ++ xxspltw 32+11, 18, 3 ++ xxspltw 32+12, 19, 0 ++ xxspltw 32+13, 19, 1 ++ xxspltw 32+14, 19, 2 ++ xxspltw 32+15, 19, 3 ++ vadduwm 12, 12, 30 # increase counter ++ ++ lvx 16, 20, 10 ++ lvx 17, 21, 10 ++ lvx 18, 22, 10 ++ lvx 19, 23, 10 ++ xxspltw 32+20, 17, 0 ++ xxspltw 32+21, 17, 1 ++ xxspltw 32+22, 17, 2 ++ xxspltw 32+23, 17, 3 ++ xxspltw 32+24, 18, 0 ++ xxspltw 32+25, 18, 1 ++ xxspltw 32+26, 18, 2 ++ xxspltw 32+27, 18, 3 ++ xxspltw 32+28, 19, 0 ++ xxspltw 32+29, 19, 1 ++ vadduwm 28, 28, 31 # increase counter ++ xxspltw 32+30, 19, 2 ++ xxspltw 32+31, 19, 3 ++ ++.align 5 ++quarter_loop_8x: ++ QT_loop_8x ++ ++ bdnz quarter_loop_8x ++ ++ xxlor 0, 32+30, 32+30 ++ xxlor 32+30, 30, 30 ++ vadduwm 12, 12, 30 ++ xxlor 32+30, 0, 0 ++ TP_4x 0, 1, 2, 3 ++ TP_4x 4, 5, 6, 7 ++ TP_4x 8, 9, 10, 11 ++ TP_4x 12, 13, 14, 15 ++ ++ xxlor 0, 48, 48 ++ xxlor 1, 49, 49 ++ xxlor 2, 50, 50 ++ xxlor 3, 51, 51 ++ xxlor 48, 16, 16 ++ xxlor 49, 17, 17 ++ xxlor 50, 18, 18 ++ xxlor 51, 19, 19 ++ Add_state 0 ++ xxlor 48, 0, 0 ++ xxlor 49, 1, 1 ++ xxlor 50, 2, 2 ++ xxlor 51, 3, 3 ++ Write_256 0 ++ addi 14, 14, 256 ++ addi 15, 15, -256 ++ ++ xxlor 5, 32+31, 32+31 ++ xxlor 32+31, 31, 31 ++ vadduwm 28, 28, 31 ++ xxlor 32+31, 5, 5 ++ TP_4x 16+0, 16+1, 16+2, 16+3 ++ TP_4x 16+4, 16+5, 16+6, 16+7 ++ TP_4x 16+8, 16+9, 16+10, 16+11 ++ TP_4x 16+12, 16+13, 16+14, 16+15 ++ ++ xxlor 32, 16, 16 ++ xxlor 33, 17, 17 ++ xxlor 34, 18, 18 ++ xxlor 35, 19, 19 ++ Add_state 16 ++ Write_256 16 ++ addi 14, 14, 256 ++ addi 15, 15, -256 ++ ++ # should update counter before out? ++ xxlor 32+24, 24, 24 ++ xxlor 32+25, 25, 25 ++ xxlor 32+30, 30, 30 ++ vadduwm 30, 30, 25 ++ vadduwm 31, 30, 24 ++ xxlor 30, 32+30, 32+30 ++ xxlor 31, 32+31, 32+31 ++ ++ cmpdi 15, 0 ++ beq Out_loop ++ ++ cmpdi 15, 512 ++ blt Loop_last ++ ++ mtctr 8 ++ b Loop_8x ++ ++Loop_last: ++ lxvw4x 48, 0, 3 # vr16, constants ++ lxvw4x 49, 17, 3 # vr17, key 1 ++ lxvw4x 50, 18, 3 # vr18, key 2 ++ lxvw4x 51, 19, 3 # vr19, counter, nonce ++ ++ vspltisw 21, 12 ++ vspltisw 23, 7 ++ lxvw4x 32+20, 0, 11 ++ lxvw4x 32+22, 17, 11 ++ ++ li 8, 10 ++ mtctr 8 ++ ++Loop_4x: ++ lvx 0, 20, 10 ++ lvx 1, 21, 10 ++ lvx 2, 22, 10 ++ lvx 3, 23, 10 ++ vspltw 4, 17, 0 ++ vspltw 5, 17, 1 ++ vspltw 6, 17, 2 ++ vspltw 7, 17, 3 ++ vspltw 8, 18, 0 ++ vspltw 9, 18, 1 ++ vspltw 10, 18, 2 ++ vspltw 11, 18, 3 ++ vspltw 12, 19, 0 ++ vadduwm 12, 12, 30 # increase counter ++ vspltw 13, 19, 1 ++ vspltw 14, 19, 2 ++ vspltw 15, 19, 3 ++ ++.align 5 ++quarter_loop: ++ QT_loop_4x ++ ++ bdnz quarter_loop ++ ++ vadduwm 12, 12, 30 ++ TP_4x 0, 1, 2, 3 ++ TP_4x 4, 5, 6, 7 ++ TP_4x 8, 9, 10, 11 ++ TP_4x 12, 13, 14, 15 ++ ++ Add_state 0 ++ Write_256 0 ++ addi 14, 14, 256 ++ addi 15, 15, -256 ++ ++ # Update state counter ++ vspltisw 25, 4 ++ vadduwm 30, 30, 25 ++ ++ cmpdi 15, 0 ++ beq Out_loop ++ ++ mtctr 8 ++ b Loop_4x ++ ++Out_loop: ++ # ++ # Update state counter ++ # ++ vspltisb 16, -1 # first 16 bytes - 0xffff...ff ++ vspltisb 17, 0 # second 16 bytes - 0x0000...00 ++ vsldoi 18, 16, 17, 12 ++ vand 18, 18, 30 ++ xxlor 32+19, 19, 19 ++ vadduwm 18, 19, 18 ++ stxvw4x 32+18, 19, 3 ++ li 3, 0 ++ ++ addi 9, 1, 256 ++ lvx 20, 0, 9 ++ lvx 21, 17, 9 ++ lvx 22, 18, 9 ++ lvx 23, 19, 9 ++ lvx 24, 20, 9 ++ lvx 25, 21, 9 ++ lvx 26, 22, 9 ++ lvx 27, 23, 9 ++ lvx 28, 24, 9 ++ lvx 29, 25, 9 ++ lvx 30, 26, 9 ++ lvx 31, 27, 9 ++ ++ add 9, 9, 27 ++ addi 14, 17, 16 ++ lxvx 14, 14, 9 ++ addi 14, 14, 16 ++ lxvx 15, 14, 9 ++ addi 14, 14, 16 ++ lxvx 16, 14, 9 ++ addi 14, 14, 16 ++ lxvx 17, 14, 9 ++ addi 14, 14, 16 ++ lxvx 18, 14, 9 ++ addi 14, 14, 16 ++ lxvx 19, 14, 9 ++ addi 14, 14, 16 ++ lxvx 20, 14, 9 ++ addi 14, 14, 16 ++ lxvx 21, 14, 9 ++ addi 14, 14, 16 ++ lxvx 22, 14, 9 ++ addi 14, 14, 16 ++ lxvx 23, 14, 9 ++ addi 14, 14, 16 ++ lxvx 24, 14, 9 ++ addi 14, 14, 16 ++ lxvx 25, 14, 9 ++ addi 14, 14, 16 ++ lxvx 26, 14, 9 ++ addi 14, 14, 16 ++ lxvx 27, 14, 9 ++ addi 14, 14, 16 ++ lxvx 28, 14, 9 ++ addi 14, 14, 16 ++ lxvx 29, 14, 9 ++ addi 14, 14, 16 ++ lxvx 30, 14, 9 ++ addi 14, 14, 16 ++ lxvx 31, 14, 9 ++ ++ ld 0, 1040(1) ++ ld 14,112(1) ++ ld 15,120(1) ++ ld 16,128(1) ++ ld 17,136(1) ++ ld 18,144(1) ++ ld 19,152(1) ++ ld 20,160(1) ++ ld 21,168(1) ++ ld 22,176(1) ++ ld 23,184(1) ++ ld 24,192(1) ++ ld 25,200(1) ++ ld 26,208(1) ++ ld 27,216(1) ++ ld 28,224(1) ++ ld 29,232(1) ++ ld 30,240(1) ++ ld 31,248(1) ++ ++ mtlr 0 ++ addi 1, 1, 1024 ++ blr ++ ++Out_no_chacha: ++ li 3, 0 ++ blr ++ ++.data ++.align 4 ++sigma: ++.long 0x61707865, 0x3320646e, 0x79622d32, 0x6b206574 ++.long 0x0c0d0e0f, 0x08090a0b, 0x04050607, 0x00010203 ++.long 1, 0, 0, 0 ++.long 0, 1, 2, 3 ++.long 0x61707865, 0x61707865, 0x61707865, 0x61707865 ++.long 0x3320646e, 0x3320646e, 0x3320646e, 0x3320646e ++.long 0x79622d32, 0x79622d32, 0x79622d32, 0x79622d32 ++.long 0x6b206574, 0x6b206574, 0x6b206574, 0x6b206574 ++permx: ++.long 0x22330011, 0x66774455, 0xaabb8899, 0xeeffccdd ++.long 0x11223300, 0x55667744, 0x99aabb88, 0xddeeffcc +Index: libgcrypt-1.10.2/cipher/chacha20.c +=================================================================== +--- libgcrypt-1.10.2.orig/cipher/chacha20.c ++++ libgcrypt-1.10.2/cipher/chacha20.c +@@ -125,6 +125,7 @@ typedef struct CHACHA20_context_s + unsigned int use_avx2:1; + unsigned int use_neon:1; + unsigned int use_ppc:1; ++ unsigned int use_p10:1; + unsigned int use_s390x:1; + } CHACHA20_context_t; + +@@ -163,6 +164,12 @@ unsigned int _gcry_chacha20_poly1305_amd + + #ifdef USE_PPC_VEC + ++#ifndef WORDS_BIGENDIAN ++unsigned int _gcry_chacha20_p10le_8x(u32 *state, byte *dst, ++ const byte *src, ++ size_t len); ++#endif ++ + unsigned int _gcry_chacha20_ppc8_blocks4(u32 *state, byte *dst, + const byte *src, + size_t nblks); +@@ -475,6 +482,9 @@ chacha20_do_setkey (CHACHA20_context_t * + #endif + #ifdef USE_PPC_VEC + ctx->use_ppc = (features & HWF_PPC_ARCH_2_07) != 0; ++# ifndef WORDS_BIGENDIAN ++ ctx->use_p10 = (features & HWF_PPC_ARCH_3_10) != 0; ++# endif + #endif + #ifdef USE_S390X_VX + ctx->use_s390x = (features & HWF_S390X_VX) != 0; +@@ -571,7 +581,22 @@ do_chacha20_encrypt_stream_tail (CHACHA2 + { + size_t nblocks = length / CHACHA20_BLOCK_SIZE; + nblocks -= nblocks % 4; +- nburn = _gcry_chacha20_ppc8_blocks4(ctx->input, outbuf, inbuf, nblocks); ++#ifndef WORDS_BIGENDIAN ++ /* ++ * A workaround to skip counter overflow. This is rare. ++ */ ++ if (ctx->use_p10 && nblocks >= 8 ++ && ((u64)ctx->input[12] + nblocks) <= 0xffffffffU) ++ { ++ size_t len = nblocks * CHACHA20_BLOCK_SIZE; ++ nburn = _gcry_chacha20_p10le_8x(ctx->input, outbuf, inbuf, len); ++ } ++ else ++#endif ++ { ++ nburn = _gcry_chacha20_ppc8_blocks4(ctx->input, outbuf, inbuf, ++ nblocks); ++ } + burn = nburn > burn ? nburn : burn; + length -= nblocks * CHACHA20_BLOCK_SIZE; + outbuf += nblocks * CHACHA20_BLOCK_SIZE; +@@ -760,6 +785,11 @@ _gcry_chacha20_poly1305_encrypt(gcry_cip + } + #endif + #ifdef USE_PPC_VEC_POLY1305 ++ else if (ctx->use_ppc && ctx->use_p10) ++ { ++ /* Skip stitched chacha20-poly1305 for P10. */ ++ authptr = NULL; ++ } + else if (ctx->use_ppc && length >= CHACHA20_BLOCK_SIZE * 4) + { + nburn = _gcry_chacha20_ppc8_blocks4(ctx->input, outbuf, inbuf, 4); +@@ -998,6 +1028,7 @@ _gcry_chacha20_poly1305_decrypt(gcry_cip + { + CHACHA20_context_t *ctx = (void *) &c->context.c; + unsigned int nburn, burn = 0; ++ int skip_stitched = 0; + + if (!length) + return 0; +@@ -1049,6 +1080,13 @@ _gcry_chacha20_poly1305_decrypt(gcry_cip + inbuf += nblocks * CHACHA20_BLOCK_SIZE; + } + #endif ++#ifdef USE_PPC_VEC_POLY1305 ++ if (ctx->use_ppc && ctx->use_p10) ++ { ++ /* Skip stitched chacha20-poly1305 for P10. */ ++ skip_stitched = 1; ++ } ++#endif + + #ifdef USE_SSSE3 + if (ctx->use_ssse3) +@@ -1102,7 +1140,8 @@ _gcry_chacha20_poly1305_decrypt(gcry_cip + #endif + + #ifdef USE_PPC_VEC_POLY1305 +- if (ctx->use_ppc && length >= 4 * CHACHA20_BLOCK_SIZE) ++ /* skip stitch for p10 */ ++ if (!skip_stitched && ctx->use_ppc && length >= 4 * CHACHA20_BLOCK_SIZE) + { + size_t nblocks = length / CHACHA20_BLOCK_SIZE; + nblocks -= nblocks % 4; +Index: libgcrypt-1.10.2/cipher/poly1305-internal.h +=================================================================== +--- libgcrypt-1.10.2.orig/cipher/poly1305-internal.h ++++ libgcrypt-1.10.2/cipher/poly1305-internal.h +@@ -33,6 +33,17 @@ + #define POLY1305_KEYLEN 32 + #define POLY1305_BLOCKSIZE 16 + ++/* POLY1305_USE_PPC_VEC indicates whether to enable PowerPC vector code. */ ++#undef POLY1305_USE_PPC_VEC ++#ifdef ENABLE_PPC_CRYPTO_SUPPORT ++# if defined(HAVE_COMPATIBLE_CC_PPC_ALTIVEC) && \ ++ defined(HAVE_GCC_INLINE_ASM_PPC_ALTIVEC) && \ ++ !defined(WORDS_BIGENDIAN) ++# if __GNUC__ >= 4 ++# define POLY1305_USE_PPC_VEC 1 ++# endif ++# endif ++#endif + + typedef struct + { +@@ -46,6 +57,9 @@ typedef struct poly1305_context_s + POLY1305_STATE state; + byte buffer[POLY1305_BLOCKSIZE]; + unsigned int leftover; ++#ifdef POLY1305_USE_PPC_VEC ++ unsigned int use_p10:1; ++#endif + } poly1305_context_t; + + +Index: libgcrypt-1.10.2/cipher/poly1305-p10le.s +=================================================================== +--- /dev/null ++++ libgcrypt-1.10.2/cipher/poly1305-p10le.s +@@ -0,0 +1,841 @@ ++# Copyright 2021- IBM Inc. All rights reserved ++# ++# This file is part of Libgcrypt. ++# ++# Libgcrypt is free software; you can redistribute it and/or modify ++# it under the terms of the GNU Lesser General Public License as ++# published by the Free Software Foundation; either version 2.1 of ++# the License, or (at your option) any later version. ++# ++# Libgcrypt 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 Lesser General Public License for more details. ++# ++# You should have received a copy of the GNU Lesser General Public ++# License along with this program; if not, see . ++# ++#=================================================================================== ++# Written by Danny Tsen ++# ++# Poly1305 - this version mainly using vector/VSX/Scalar ++# - 26 bits limbs ++# - Handle multiple 64 byte blcoks but need at least 2 64 bytes block ++# ++# Improve performance by breaking down polynominal to the sum of products with ++# h4 = m1 * r⁴ + m2 * r³ + m3 * r² + m4 * r ++# ++# 07/22/21 - this revison based on the above sum of products. Setup r^4, r^3, r^2, r and s3, s2, s1, s0 ++# to 9 vectors for multiplications. ++# ++# setup r^4, r^3, r^2, r vectors ++# vs [r^1, r^3, r^2, r^4] ++# vs0 = [r0,.....] ++# vs1 = [r1,.....] ++# vs2 = [r2,.....] ++# vs3 = [r3,.....] ++# vs4 = [r4,.....] ++# vs5 = [r1*5,...] ++# vs6 = [r2*5,...] ++# vs7 = [r2*5,...] ++# vs8 = [r4*5,...] ++# ++# Each word in a vector consists a member of a "r/s" in [a * r/s]. ++# ++# r0, r4*5, r3*5, r2*5, r1*5; ++# r1, r0, r4*5, r3*5, r2*5; ++# r2, r1, r0, r4*5, r3*5; ++# r3, r2, r1, r0, r4*5; ++# r4, r3, r2, r1, r0 ; ++# ++# ++# gcry_poly1305_p10le_4blocks( uint8_t *k, uint32_t mlen, uint8_t *m) ++# k = 32 bytes key ++# r3 = k (r, s) ++# r4 = mlen ++# r5 = m ++# ++.text ++ ++# Block size 16 bytes ++# key = (r, s) ++# clamp r &= 0x0FFFFFFC0FFFFFFC 0x0FFFFFFC0FFFFFFF ++# p = 2^130 - 5 ++# a += m ++# a = (r + a) % p ++# a += s ++# 16 bytes (a) ++# ++# p[0] = a0*r0 + a1*r4*5 + a2*r3*5 + a3*r2*5 + a4*r1*5; ++# p[1] = a0*r1 + a1*r0 + a2*r4*5 + a3*r3*5 + a4*r2*5; ++# p[2] = a0*r2 + a1*r1 + a2*r0 + a3*r4*5 + a4*r3*5; ++# p[3] = a0*r3 + a1*r2 + a2*r1 + a3*r0 + a4*r4*5; ++# p[4] = a0*r4 + a1*r3 + a2*r2 + a3*r1 + a4*r0 ; ++# ++# [r^2, r^3, r^1, r^4] ++# [m3, m2, m4, m1] ++# ++# multiply odd and even words ++.macro mul_odd ++ vmulouw 14, 4, 26 ++ vmulouw 10, 5, 3 ++ vmulouw 11, 6, 2 ++ vmulouw 12, 7, 1 ++ vmulouw 13, 8, 0 ++ vmulouw 15, 4, 27 ++ vaddudm 14, 14, 10 ++ vaddudm 14, 14, 11 ++ vmulouw 10, 5, 26 ++ vmulouw 11, 6, 3 ++ vaddudm 14, 14, 12 ++ vaddudm 14, 14, 13 # x0 ++ vaddudm 15, 15, 10 ++ vaddudm 15, 15, 11 ++ vmulouw 12, 7, 2 ++ vmulouw 13, 8, 1 ++ vaddudm 15, 15, 12 ++ vaddudm 15, 15, 13 # x1 ++ vmulouw 16, 4, 28 ++ vmulouw 10, 5, 27 ++ vmulouw 11, 6, 26 ++ vaddudm 16, 16, 10 ++ vaddudm 16, 16, 11 ++ vmulouw 12, 7, 3 ++ vmulouw 13, 8, 2 ++ vaddudm 16, 16, 12 ++ vaddudm 16, 16, 13 # x2 ++ vmulouw 17, 4, 29 ++ vmulouw 10, 5, 28 ++ vmulouw 11, 6, 27 ++ vaddudm 17, 17, 10 ++ vaddudm 17, 17, 11 ++ vmulouw 12, 7, 26 ++ vmulouw 13, 8, 3 ++ vaddudm 17, 17, 12 ++ vaddudm 17, 17, 13 # x3 ++ vmulouw 18, 4, 30 ++ vmulouw 10, 5, 29 ++ vmulouw 11, 6, 28 ++ vaddudm 18, 18, 10 ++ vaddudm 18, 18, 11 ++ vmulouw 12, 7, 27 ++ vmulouw 13, 8, 26 ++ vaddudm 18, 18, 12 ++ vaddudm 18, 18, 13 # x4 ++.endm ++ ++.macro mul_even ++ vmuleuw 9, 4, 26 ++ vmuleuw 10, 5, 3 ++ vmuleuw 11, 6, 2 ++ vmuleuw 12, 7, 1 ++ vmuleuw 13, 8, 0 ++ vaddudm 14, 14, 9 ++ vaddudm 14, 14, 10 ++ vaddudm 14, 14, 11 ++ vaddudm 14, 14, 12 ++ vaddudm 14, 14, 13 # x0 ++ ++ vmuleuw 9, 4, 27 ++ vmuleuw 10, 5, 26 ++ vmuleuw 11, 6, 3 ++ vmuleuw 12, 7, 2 ++ vmuleuw 13, 8, 1 ++ vaddudm 15, 15, 9 ++ vaddudm 15, 15, 10 ++ vaddudm 15, 15, 11 ++ vaddudm 15, 15, 12 ++ vaddudm 15, 15, 13 # x1 ++ ++ vmuleuw 9, 4, 28 ++ vmuleuw 10, 5, 27 ++ vmuleuw 11, 6, 26 ++ vmuleuw 12, 7, 3 ++ vmuleuw 13, 8, 2 ++ vaddudm 16, 16, 9 ++ vaddudm 16, 16, 10 ++ vaddudm 16, 16, 11 ++ vaddudm 16, 16, 12 ++ vaddudm 16, 16, 13 # x2 ++ ++ vmuleuw 9, 4, 29 ++ vmuleuw 10, 5, 28 ++ vmuleuw 11, 6, 27 ++ vmuleuw 12, 7, 26 ++ vmuleuw 13, 8, 3 ++ vaddudm 17, 17, 9 ++ vaddudm 17, 17, 10 ++ vaddudm 17, 17, 11 ++ vaddudm 17, 17, 12 ++ vaddudm 17, 17, 13 # x3 ++ ++ vmuleuw 9, 4, 30 ++ vmuleuw 10, 5, 29 ++ vmuleuw 11, 6, 28 ++ vmuleuw 12, 7, 27 ++ vmuleuw 13, 8, 26 ++ vaddudm 18, 18, 9 ++ vaddudm 18, 18, 10 ++ vaddudm 18, 18, 11 ++ vaddudm 18, 18, 12 ++ vaddudm 18, 18, 13 # x4 ++.endm ++ ++# setup r^4, r^3, r^2, r vectors ++# [r, r^3, r^2, r^4] ++# vs0 = [r0,...] ++# vs1 = [r1,...] ++# vs2 = [r2,...] ++# vs3 = [r3,...] ++# vs4 = [r4,...] ++# vs5 = [r4*5,...] ++# vs6 = [r3*5,...] ++# vs7 = [r2*5,...] ++# vs8 = [r1*5,...] ++# ++# r0, r4*5, r3*5, r2*5, r1*5; ++# r1, r0, r4*5, r3*5, r2*5; ++# r2, r1, r0, r4*5, r3*5; ++# r3, r2, r1, r0, r4*5; ++# r4, r3, r2, r1, r0 ; ++# ++.macro poly1305_setup_r ++ ++ # save r ++ xxlor 26, 58, 58 ++ xxlor 27, 59, 59 ++ xxlor 28, 60, 60 ++ xxlor 29, 61, 61 ++ xxlor 30, 62, 62 ++ ++ xxlxor 31, 31, 31 ++ ++# [r, r^3, r^2, r^4] ++ # compute r^2 ++ vmr 4, 26 ++ vmr 5, 27 ++ vmr 6, 28 ++ vmr 7, 29 ++ vmr 8, 30 ++ bl do_mul # r^2 r^1 ++ xxpermdi 58, 58, 36, 0x3 # r0 ++ xxpermdi 59, 59, 37, 0x3 # r1 ++ xxpermdi 60, 60, 38, 0x3 # r2 ++ xxpermdi 61, 61, 39, 0x3 # r3 ++ xxpermdi 62, 62, 40, 0x3 # r4 ++ xxpermdi 36, 36, 36, 0x3 ++ xxpermdi 37, 37, 37, 0x3 ++ xxpermdi 38, 38, 38, 0x3 ++ xxpermdi 39, 39, 39, 0x3 ++ xxpermdi 40, 40, 40, 0x3 ++ vspltisb 13, 2 ++ vsld 9, 27, 13 ++ vsld 10, 28, 13 ++ vsld 11, 29, 13 ++ vsld 12, 30, 13 ++ vaddudm 0, 9, 27 ++ vaddudm 1, 10, 28 ++ vaddudm 2, 11, 29 ++ vaddudm 3, 12, 30 ++ ++ bl do_mul # r^4 r^3 ++ vmrgow 26, 26, 4 ++ vmrgow 27, 27, 5 ++ vmrgow 28, 28, 6 ++ vmrgow 29, 29, 7 ++ vmrgow 30, 30, 8 ++ vspltisb 13, 2 ++ vsld 9, 27, 13 ++ vsld 10, 28, 13 ++ vsld 11, 29, 13 ++ vsld 12, 30, 13 ++ vaddudm 0, 9, 27 ++ vaddudm 1, 10, 28 ++ vaddudm 2, 11, 29 ++ vaddudm 3, 12, 30 ++ ++ # r^2 r^4 ++ xxlor 0, 58, 58 ++ xxlor 1, 59, 59 ++ xxlor 2, 60, 60 ++ xxlor 3, 61, 61 ++ xxlor 4, 62, 62 ++ xxlor 5, 32, 32 ++ xxlor 6, 33, 33 ++ xxlor 7, 34, 34 ++ xxlor 8, 35, 35 ++ ++ vspltw 9, 26, 3 ++ vspltw 10, 26, 2 ++ vmrgow 26, 10, 9 ++ vspltw 9, 27, 3 ++ vspltw 10, 27, 2 ++ vmrgow 27, 10, 9 ++ vspltw 9, 28, 3 ++ vspltw 10, 28, 2 ++ vmrgow 28, 10, 9 ++ vspltw 9, 29, 3 ++ vspltw 10, 29, 2 ++ vmrgow 29, 10, 9 ++ vspltw 9, 30, 3 ++ vspltw 10, 30, 2 ++ vmrgow 30, 10, 9 ++ ++ vsld 9, 27, 13 ++ vsld 10, 28, 13 ++ vsld 11, 29, 13 ++ vsld 12, 30, 13 ++ vaddudm 0, 9, 27 ++ vaddudm 1, 10, 28 ++ vaddudm 2, 11, 29 ++ vaddudm 3, 12, 30 ++.endm ++ ++do_mul: ++ mul_odd ++ ++ # do reduction ( h %= p ) ++ # carry reduction ++ vspltisb 9, 2 ++ vsrd 10, 14, 31 ++ vsrd 11, 17, 31 ++ vand 7, 17, 25 ++ vand 4, 14, 25 ++ vaddudm 18, 18, 11 ++ vsrd 12, 18, 31 ++ vaddudm 15, 15, 10 ++ ++ vsrd 11, 15, 31 ++ vand 8, 18, 25 ++ vand 5, 15, 25 ++ vaddudm 4, 4, 12 ++ vsld 10, 12, 9 ++ vaddudm 6, 16, 11 ++ ++ vsrd 13, 6, 31 ++ vand 6, 6, 25 ++ vaddudm 4, 4, 10 ++ vsrd 10, 4, 31 ++ vaddudm 7, 7, 13 ++ ++ vsrd 11, 7, 31 ++ vand 7, 7, 25 ++ vand 4, 4, 25 ++ vaddudm 5, 5, 10 ++ vaddudm 8, 8, 11 ++ blr ++ ++# ++# init key ++# ++do_poly1305_init: ++ ld 10, rmask@got(2) ++ ld 11, 0(10) ++ ld 12, 8(10) ++ ++ li 14, 16 ++ li 15, 32 ++ ld 10, cnum@got(2) ++ lvx 25, 0, 10 # v25 - mask ++ lvx 31, 14, 10 # v31 = 1a ++ lvx 19, 15, 10 # v19 = 1 << 24 ++ lxv 24, 48(10) # vs24 ++ lxv 25, 64(10) # vs25 ++ ++ # initialize ++ # load key from r3 to vectors ++ ld 9, 16(3) ++ ld 10, 24(3) ++ ld 11, 0(3) ++ ld 12, 8(3) ++ ++ # break 26 bits ++ extrdi 14, 9, 26, 38 ++ extrdi 15, 9, 26, 12 ++ extrdi 16, 9, 12, 0 ++ mtvsrdd 58, 0, 14 ++ insrdi 16, 10, 14, 38 ++ mtvsrdd 59, 0, 15 ++ extrdi 17, 10, 26, 24 ++ mtvsrdd 60, 0, 16 ++ extrdi 18, 10, 24, 0 ++ mtvsrdd 61, 0, 17 ++ mtvsrdd 62, 0, 18 ++ ++ # r1 = r1 * 5, r2 = r2 * 5, r3 = r3 * 5, r4 = r4 * 5 ++ li 9, 5 ++ mtvsrdd 36, 0, 9 ++ vmulouw 0, 27, 4 # v0 = rr0 ++ vmulouw 1, 28, 4 # v1 = rr1 ++ vmulouw 2, 29, 4 # v2 = rr2 ++ vmulouw 3, 30, 4 # v3 = rr3 ++ blr ++ ++# ++# gcry_poly1305_p10le_4blocks( uint8_t *k, uint32_t mlen, uint8_t *m) ++# k = 32 bytes key ++# r3 = k (r, s) ++# r4 = mlen ++# r5 = m ++# ++.global gcry_poly1305_p10le_4blocks ++.align 5 ++gcry_poly1305_p10le_4blocks: ++_gcry_poly1305_p10le_4blocks: ++ cmpdi 5, 128 ++ blt Out_no_poly1305 ++ ++ stdu 1,-1024(1) ++ mflr 0 ++ ++ std 14,112(1) ++ std 15,120(1) ++ std 16,128(1) ++ std 17,136(1) ++ std 18,144(1) ++ std 19,152(1) ++ std 20,160(1) ++ std 21,168(1) ++ std 31,248(1) ++ li 14, 256 ++ stvx 20, 14, 1 ++ addi 14, 14, 16 ++ stvx 21, 14, 1 ++ addi 14, 14, 16 ++ stvx 22, 14, 1 ++ addi 14, 14, 16 ++ stvx 23, 14, 1 ++ addi 14, 14, 16 ++ stvx 24, 14, 1 ++ addi 14, 14, 16 ++ stvx 25, 14, 1 ++ addi 14, 14, 16 ++ stvx 26, 14, 1 ++ addi 14, 14, 16 ++ stvx 27, 14, 1 ++ addi 14, 14, 16 ++ stvx 28, 14, 1 ++ addi 14, 14, 16 ++ stvx 29, 14, 1 ++ addi 14, 14, 16 ++ stvx 30, 14, 1 ++ addi 14, 14, 16 ++ stvx 31, 14, 1 ++ ++ addi 14, 14, 16 ++ stxvx 14, 14, 1 ++ addi 14, 14, 16 ++ stxvx 15, 14, 1 ++ addi 14, 14, 16 ++ stxvx 16, 14, 1 ++ addi 14, 14, 16 ++ stxvx 17, 14, 1 ++ addi 14, 14, 16 ++ stxvx 18, 14, 1 ++ addi 14, 14, 16 ++ stxvx 19, 14, 1 ++ addi 14, 14, 16 ++ stxvx 20, 14, 1 ++ addi 14, 14, 16 ++ stxvx 21, 14, 1 ++ addi 14, 14, 16 ++ stxvx 22, 14, 1 ++ addi 14, 14, 16 ++ stxvx 23, 14, 1 ++ addi 14, 14, 16 ++ stxvx 24, 14, 1 ++ addi 14, 14, 16 ++ stxvx 25, 14, 1 ++ addi 14, 14, 16 ++ stxvx 26, 14, 1 ++ addi 14, 14, 16 ++ stxvx 27, 14, 1 ++ addi 14, 14, 16 ++ stxvx 28, 14, 1 ++ addi 14, 14, 16 ++ stxvx 29, 14, 1 ++ addi 14, 14, 16 ++ stxvx 30, 14, 1 ++ addi 14, 14, 16 ++ stxvx 31, 14, 1 ++ std 0, 1040(1) ++ ++ bl do_poly1305_init ++ ++ li 21, 0 # counter to message ++ ++ poly1305_setup_r ++ ++ # load previous state ++ # break/convert r6 to 26 bits ++ ld 9, 32(3) ++ ld 10, 40(3) ++ lwz 19, 48(3) ++ sldi 19, 19, 24 ++ mtvsrdd 41, 0, 19 ++ extrdi 14, 9, 26, 38 ++ extrdi 15, 9, 26, 12 ++ extrdi 16, 9, 12, 0 ++ mtvsrdd 36, 0, 14 ++ insrdi 16, 10, 14, 38 ++ mtvsrdd 37, 0, 15 ++ extrdi 17, 10, 26, 24 ++ mtvsrdd 38, 0, 16 ++ extrdi 18, 10, 24, 0 ++ mtvsrdd 39, 0, 17 ++ mtvsrdd 40, 0, 18 ++ vor 8, 8, 9 ++ ++ # input m1 m2 ++ add 20, 4, 21 ++ xxlor 49, 24, 24 ++ xxlor 50, 25, 25 ++ lxvw4x 43, 0, 20 ++ addi 17, 20, 16 ++ lxvw4x 44, 0, 17 ++ vperm 14, 11, 12, 17 ++ vperm 15, 11, 12, 18 ++ vand 9, 14, 25 # a0 ++ vsrd 10, 14, 31 # >> 26 ++ vsrd 11, 10, 31 # 12 bits left ++ vand 10, 10, 25 # a1 ++ vspltisb 13, 12 ++ vand 16, 15, 25 ++ vsld 12, 16, 13 ++ vor 11, 11, 12 ++ vand 11, 11, 25 # a2 ++ vspltisb 13, 14 ++ vsrd 12, 15, 13 # >> 14 ++ vsrd 13, 12, 31 # >> 26, a4 ++ vand 12, 12, 25 # a3 ++ ++ vaddudm 20, 4, 9 ++ vaddudm 21, 5, 10 ++ vaddudm 22, 6, 11 ++ vaddudm 23, 7, 12 ++ vaddudm 24, 8, 13 ++ ++ # m3 m4 ++ addi 17, 17, 16 ++ lxvw4x 43, 0, 17 ++ addi 17, 17, 16 ++ lxvw4x 44, 0, 17 ++ vperm 14, 11, 12, 17 ++ vperm 15, 11, 12, 18 ++ vand 9, 14, 25 # a0 ++ vsrd 10, 14, 31 # >> 26 ++ vsrd 11, 10, 31 # 12 bits left ++ vand 10, 10, 25 # a1 ++ vspltisb 13, 12 ++ vand 16, 15, 25 ++ vsld 12, 16, 13 ++ vspltisb 13, 14 ++ vor 11, 11, 12 ++ vand 11, 11, 25 # a2 ++ vsrd 12, 15, 13 # >> 14 ++ vsrd 13, 12, 31 # >> 26, a4 ++ vand 12, 12, 25 # a3 ++ ++ # Smash 4 message blocks into 5 vectors of [m4, m2, m3, m1] ++ vmrgow 4, 9, 20 ++ vmrgow 5, 10, 21 ++ vmrgow 6, 11, 22 ++ vmrgow 7, 12, 23 ++ vmrgow 8, 13, 24 ++ vaddudm 8, 8, 19 ++ ++ addi 5, 5, -64 ++ addi 21, 21, 64 ++ ++ li 9, 64 ++ divdu 31, 5, 9 ++ ++ mtctr 31 ++ ++# h4 = m1 * r⁴ + m2 * r³ + m3 * r² + m4 * r ++# Rewrite the polynominal sum of product as follows, ++# h1 = (h0 + m1) * r^2, h2 = (h0 + m2) * r^2 ++# h3 = (h1 + m3) * r^2, h4 = (h2 + m4) * r^2 --> (h0 + m1) r*4 + (h3 + m3) r^2, (h0 + m2) r^4 + (h0 + m4) r^2 ++# .... Repeat ++# h5 = (h3 + m5) * r^2, h6 = (h4 + m6) * r^2 --> ++# h7 = (h5 + m7) * r^2, h8 = (h6 + m8) * r^1 --> m5 * r^4 + m6 * r^3 + m7 * r^2 + m8 * r ++# ++loop_4blocks: ++ ++ # Multiply odd words and even words ++ mul_odd ++ mul_even ++ # carry reduction ++ vspltisb 9, 2 ++ vsrd 10, 14, 31 ++ vsrd 11, 17, 31 ++ vand 7, 17, 25 ++ vand 4, 14, 25 ++ vaddudm 18, 18, 11 ++ vsrd 12, 18, 31 ++ vaddudm 15, 15, 10 ++ ++ vsrd 11, 15, 31 ++ vand 8, 18, 25 ++ vand 5, 15, 25 ++ vaddudm 4, 4, 12 ++ vsld 10, 12, 9 ++ vaddudm 6, 16, 11 ++ ++ vsrd 13, 6, 31 ++ vand 6, 6, 25 ++ vaddudm 4, 4, 10 ++ vsrd 10, 4, 31 ++ vaddudm 7, 7, 13 ++ ++ vsrd 11, 7, 31 ++ vand 7, 7, 25 ++ vand 4, 4, 25 ++ vaddudm 5, 5, 10 ++ vaddudm 8, 8, 11 ++ ++ # input m1 m2 m3 m4 ++ add 20, 4, 21 ++ xxlor 49, 24, 24 ++ xxlor 50, 25, 25 ++ lxvw4x 43, 0, 20 ++ addi 17, 20, 16 ++ lxvw4x 44, 0, 17 ++ vperm 14, 11, 12, 17 ++ vperm 15, 11, 12, 18 ++ addi 17, 17, 16 ++ lxvw4x 43, 0, 17 ++ addi 17, 17, 16 ++ lxvw4x 44, 0, 17 ++ vperm 17, 11, 12, 17 ++ vperm 18, 11, 12, 18 ++ ++ vand 20, 14, 25 # a0 ++ vand 9, 17, 25 # a0 ++ vsrd 21, 14, 31 # >> 26 ++ vsrd 22, 21, 31 # 12 bits left ++ vsrd 10, 17, 31 # >> 26 ++ vsrd 11, 10, 31 # 12 bits left ++ ++ vand 21, 21, 25 # a1 ++ vand 10, 10, 25 # a1 ++ ++ vspltisb 13, 12 ++ vand 16, 15, 25 ++ vsld 23, 16, 13 ++ vor 22, 22, 23 ++ vand 22, 22, 25 # a2 ++ vand 16, 18, 25 ++ vsld 12, 16, 13 ++ vor 11, 11, 12 ++ vand 11, 11, 25 # a2 ++ vspltisb 13, 14 ++ vsrd 23, 15, 13 # >> 14 ++ vsrd 24, 23, 31 # >> 26, a4 ++ vand 23, 23, 25 # a3 ++ vsrd 12, 18, 13 # >> 14 ++ vsrd 13, 12, 31 # >> 26, a4 ++ vand 12, 12, 25 # a3 ++ ++ vaddudm 4, 4, 20 ++ vaddudm 5, 5, 21 ++ vaddudm 6, 6, 22 ++ vaddudm 7, 7, 23 ++ vaddudm 8, 8, 24 ++ ++ # Smash 4 message blocks into 5 vectors of [m4, m2, m3, m1] ++ vmrgow 4, 9, 4 ++ vmrgow 5, 10, 5 ++ vmrgow 6, 11, 6 ++ vmrgow 7, 12, 7 ++ vmrgow 8, 13, 8 ++ vaddudm 8, 8, 19 ++ ++ addi 5, 5, -64 ++ addi 21, 21, 64 ++ ++ bdnz loop_4blocks ++ ++ xxlor 58, 0, 0 ++ xxlor 59, 1, 1 ++ xxlor 60, 2, 2 ++ xxlor 61, 3, 3 ++ xxlor 62, 4, 4 ++ xxlor 32, 5, 5 ++ xxlor 33, 6, 6 ++ xxlor 34, 7, 7 ++ xxlor 35, 8, 8 ++ ++ # Multiply odd words and even words ++ mul_odd ++ mul_even ++ ++ # Sum the products. ++ xxpermdi 41, 31, 46, 0 ++ xxpermdi 42, 31, 47, 0 ++ vaddudm 4, 14, 9 ++ xxpermdi 36, 31, 36, 3 ++ vaddudm 5, 15, 10 ++ xxpermdi 37, 31, 37, 3 ++ xxpermdi 43, 31, 48, 0 ++ vaddudm 6, 16, 11 ++ xxpermdi 38, 31, 38, 3 ++ xxpermdi 44, 31, 49, 0 ++ vaddudm 7, 17, 12 ++ xxpermdi 39, 31, 39, 3 ++ xxpermdi 45, 31, 50, 0 ++ vaddudm 8, 18, 13 ++ xxpermdi 40, 31, 40, 3 ++ ++ # carry reduction ++ vspltisb 9, 2 ++ vsrd 10, 4, 31 ++ vsrd 11, 7, 31 ++ vand 7, 7, 25 ++ vand 4, 4, 25 ++ vaddudm 8, 8, 11 ++ vsrd 12, 8, 31 ++ vaddudm 5, 5, 10 ++ ++ vsrd 11, 5, 31 ++ vand 8, 8, 25 ++ vand 5, 5, 25 ++ vaddudm 4, 4, 12 ++ vsld 10, 12, 9 ++ vaddudm 6, 6, 11 ++ ++ vsrd 13, 6, 31 ++ vand 6, 6, 25 ++ vaddudm 4, 4, 10 ++ vsrd 10, 4, 31 ++ vaddudm 7, 7, 13 ++ ++ vsrd 11, 7, 31 ++ vand 7, 7, 25 ++ vand 4, 4, 25 ++ vaddudm 5, 5, 10 ++ vaddudm 8, 8, 11 ++ ++ b do_final_update ++ ++do_final_update: ++ # v4, v5, v6, v7 and v8 are 26 bit vectors ++ vsld 5, 5, 31 ++ vor 20, 4, 5 ++ vspltisb 11, 12 ++ vsrd 12, 6, 11 ++ vsld 6, 6, 31 ++ vsld 6, 6, 31 ++ vor 20, 20, 6 ++ vspltisb 11, 14 ++ vsld 7, 7, 11 ++ vor 21, 7, 12 ++ mfvsrld 16, 40 # save last 2 bytes ++ vsld 8, 8, 11 ++ vsld 8, 8, 31 ++ vor 21, 21, 8 ++ mfvsrld 17, 52 ++ mfvsrld 19, 53 ++ srdi 16, 16, 24 ++ ++ std 17, 32(3) ++ std 19, 40(3) ++ stw 16, 48(3) ++ ++Out_loop: ++ li 3, 0 ++ ++ li 14, 256 ++ lvx 20, 14, 1 ++ addi 14, 14, 16 ++ lvx 21, 14, 1 ++ addi 14, 14, 16 ++ lvx 22, 14, 1 ++ addi 14, 14, 16 ++ lvx 23, 14, 1 ++ addi 14, 14, 16 ++ lvx 24, 14, 1 ++ addi 14, 14, 16 ++ lvx 25, 14, 1 ++ addi 14, 14, 16 ++ lvx 26, 14, 1 ++ addi 14, 14, 16 ++ lvx 27, 14, 1 ++ addi 14, 14, 16 ++ lvx 28, 14, 1 ++ addi 14, 14, 16 ++ lvx 29, 14, 1 ++ addi 14, 14, 16 ++ lvx 30, 14, 1 ++ addi 14, 14, 16 ++ lvx 31, 14, 1 ++ ++ addi 14, 14, 16 ++ lxvx 14, 14, 1 ++ addi 14, 14, 16 ++ lxvx 15, 14, 1 ++ addi 14, 14, 16 ++ lxvx 16, 14, 1 ++ addi 14, 14, 16 ++ lxvx 17, 14, 1 ++ addi 14, 14, 16 ++ lxvx 18, 14, 1 ++ addi 14, 14, 16 ++ lxvx 19, 14, 1 ++ addi 14, 14, 16 ++ lxvx 20, 14, 1 ++ addi 14, 14, 16 ++ lxvx 21, 14, 1 ++ addi 14, 14, 16 ++ lxvx 22, 14, 1 ++ addi 14, 14, 16 ++ lxvx 23, 14, 1 ++ addi 14, 14, 16 ++ lxvx 24, 14, 1 ++ addi 14, 14, 16 ++ lxvx 25, 14, 1 ++ addi 14, 14, 16 ++ lxvx 26, 14, 1 ++ addi 14, 14, 16 ++ lxvx 27, 14, 1 ++ addi 14, 14, 16 ++ lxvx 28, 14, 1 ++ addi 14, 14, 16 ++ lxvx 29, 14, 1 ++ addi 14, 14, 16 ++ lxvx 30, 14, 1 ++ addi 14, 14, 16 ++ lxvx 31, 14, 1 ++ ++ ld 0, 1040(1) ++ ld 14,112(1) ++ ld 15,120(1) ++ ld 16,128(1) ++ ld 17,136(1) ++ ld 18,144(1) ++ ld 19,152(1) ++ ld 20,160(1) ++ ld 21,168(1) ++ ld 31,248(1) ++ ++ mtlr 0 ++ addi 1, 1, 1024 ++ blr ++ ++Out_no_poly1305: ++ li 3, 0 ++ blr ++ ++.data ++.align 5 ++rmask: ++.byte 0xff, 0xff, 0xff, 0x0f, 0xfc, 0xff, 0xff, 0x0f, 0xfc, 0xff, 0xff, 0x0f, 0xfc, 0xff, 0xff, 0x0f ++cnum: ++.long 0x03ffffff, 0x00000000, 0x03ffffff, 0x00000000 ++.long 0x1a, 0x00, 0x1a, 0x00 ++.long 0x01000000, 0x01000000, 0x01000000, 0x01000000 ++.long 0x00010203, 0x04050607, 0x10111213, 0x14151617 ++.long 0x08090a0b, 0x0c0d0e0f, 0x18191a1b, 0x1c1d1e1f ++.long 0x05, 0x00, 0x00, 0x00 ++.long 0x02020202, 0x02020202, 0x02020202, 0x02020202 ++.long 0xffffffff, 0xffffffff, 0x00000000, 0x00000000 +Index: libgcrypt-1.10.2/cipher/poly1305.c +=================================================================== +--- libgcrypt-1.10.2.orig/cipher/poly1305.c ++++ libgcrypt-1.10.2/cipher/poly1305.c +@@ -78,11 +78,23 @@ poly1305_blocks (poly1305_context_t *ctx + #endif /* USE_S390X_ASM */ + + ++#ifdef POLY1305_USE_PPC_VEC ++ ++extern unsigned int ++gcry_poly1305_p10le_4blocks(unsigned char *key, const byte *m, size_t len); ++ ++#endif /* POLY1305_USE_PPC_VEC */ ++ ++ + static void poly1305_init (poly1305_context_t *ctx, + const byte key[POLY1305_KEYLEN]) + { + POLY1305_STATE *st = &ctx->state; + ++#ifdef POLY1305_USE_PPC_VEC ++ ctx->use_p10 = (_gcry_get_hw_features () & HWF_PPC_ARCH_3_10) != 0; ++#endif ++ + ctx->leftover = 0; + + st->h[0] = 0; +@@ -533,6 +545,7 @@ _gcry_poly1305_update_burn (poly1305_con + size_t bytes) + { + unsigned int burn = 0; ++ unsigned int nburn; + + /* handle leftover */ + if (ctx->leftover) +@@ -546,15 +559,31 @@ _gcry_poly1305_update_burn (poly1305_con + ctx->leftover += want; + if (ctx->leftover < POLY1305_BLOCKSIZE) + return 0; +- burn = poly1305_blocks (ctx, ctx->buffer, POLY1305_BLOCKSIZE, 1); ++ nburn = poly1305_blocks (ctx, ctx->buffer, POLY1305_BLOCKSIZE, 1); ++ burn = nburn > burn ? nburn : burn; + ctx->leftover = 0; + } + ++#ifdef POLY1305_USE_PPC_VEC ++ /* PPC-P10/little-endian: bulk process multiples of eight blocks */ ++ if (ctx->use_p10 && bytes >= POLY1305_BLOCKSIZE * 8) ++ { ++ size_t nblks = bytes / (POLY1305_BLOCKSIZE * 8); ++ size_t len = nblks * (POLY1305_BLOCKSIZE * 8); ++ POLY1305_STATE *st = &ctx->state; ++ nburn = gcry_poly1305_p10le_4blocks ((unsigned char *) st, m, len); ++ burn = nburn > burn ? nburn : burn; ++ m += len; ++ bytes -= len; ++ } ++#endif /* POLY1305_USE_PPC_VEC */ ++ + /* process full blocks */ + if (bytes >= POLY1305_BLOCKSIZE) + { + size_t nblks = bytes / POLY1305_BLOCKSIZE; +- burn = poly1305_blocks (ctx, m, nblks * POLY1305_BLOCKSIZE, 1); ++ nburn = poly1305_blocks (ctx, m, nblks * POLY1305_BLOCKSIZE, 1); ++ burn = nburn > burn ? nburn : burn; + m += nblks * POLY1305_BLOCKSIZE; + bytes -= nblks * POLY1305_BLOCKSIZE; + } +Index: libgcrypt-1.10.2/configure.ac +=================================================================== +--- libgcrypt-1.10.2.orig/configure.ac ++++ libgcrypt-1.10.2/configure.ac +@@ -2779,6 +2779,11 @@ if test "$found" = "1" ; then + powerpc64le-*-*) + # Build with the ppc8 vector implementation + GCRYPT_ASM_CIPHERS="$GCRYPT_ASM_CIPHERS chacha20-ppc.lo" ++ # Build with the assembly implementation ++ if test "$gcry_cv_gcc_inline_asm_ppc_altivec" = "yes" && ++ test "$gcry_cv_gcc_inline_asm_ppc_arch_3_00" = "yes" ; then ++ GCRYPT_ASM_CIPHERS="$GCRYPT_ASM_CIPHERS chacha20-p10le-8x.lo" ++ fi + ;; + powerpc64-*-*) + # Build with the ppc8 vector implementation +@@ -3117,6 +3122,13 @@ case "${host}" in + s390x-*-*) + GCRYPT_ASM_DIGESTS="$GCRYPT_ASM_DIGESTS poly1305-s390x.lo" + ;; ++ powerpc64le-*-*) ++ # Build with the assembly implementation ++ if test "$gcry_cv_gcc_inline_asm_ppc_altivec" = "yes" && ++ test "$gcry_cv_gcc_inline_asm_ppc_arch_3_00" = "yes" ; then ++ GCRYPT_ASM_DIGESTS="$GCRYPT_ASM_DIGESTS poly1305-p10le.lo" ++ fi ++ ;; + esac + + LIST_MEMBER(scrypt, $enabled_kdfs) diff --git a/libgcrypt-FIPS-SLI-hash-mac.patch b/libgcrypt-FIPS-SLI-hash-mac.patch new file mode 100644 index 0000000..f0f56f2 --- /dev/null +++ b/libgcrypt-FIPS-SLI-hash-mac.patch @@ -0,0 +1,172 @@ +Index: libgcrypt-1.11.0/doc/gcrypt.texi +=================================================================== +--- libgcrypt-1.11.0.orig/doc/gcrypt.texi ++++ libgcrypt-1.11.0/doc/gcrypt.texi +@@ -998,13 +998,21 @@ certification. If the function is approv + @code{GPG_ERR_NO_ERROR} (other restrictions might still apply). + Otherwise @code{GPG_ERR_NOT_SUPPORTED} is returned. + +-@item GCRYCTL_FIPS_SERVICE_INDICATOR_MAC; Arguments: enum gcry_mac_algos ++@item GCRYCTL_FIPS_SERVICE_INDICATOR_HASH; Arguments: enum gcry_md_algos + +-Check if the given MAC is approved under the current FIPS 140-3 +-certification. If the MAC is approved, this function returns +-@code{GPG_ERR_NO_ERROR}. Otherwise @code{GPG_ERR_NOT_SUPPORTED} ++Check if the given HASH is approved under the current FIPS 140-3 ++certification. If the HASH is approved, this function returns ++@code{GPS_ERR_NO_ERROR}. Otherwise @code{GPG_ERR_NOT_SUPPORTED} + is returned. + ++@item GCRYCTL_FIPS_SERVICE_INDICATOR_MAC; Arguments: enum gcry_mac_algos [, unsigned int] ++ ++Check if the given MAC is approved under the current FIPS 140-3 ++certification. The second parameter provides the keylen (if the ++algorithm supports different key sizes). If the MAC is approved, ++this function returns @code{GPS_ERR_NO_ERROR}. Otherwise ++@code{GPG_ERR_NOT_SUPPORTED} is returned. ++ + @item GCRYCTL_FIPS_SERVICE_INDICATOR_MD; Arguments: enum gcry_md_algos + + Check if the given message digest algorithm is approved under the current +Index: libgcrypt-1.11.0/src/fips.c +=================================================================== +--- libgcrypt-1.11.0.orig/src/fips.c ++++ libgcrypt-1.11.0/src/fips.c +@@ -378,31 +378,6 @@ _gcry_fips_indicator_cipher (va_list arg + } + } + +-int +-_gcry_fips_indicator_mac (va_list arg_ptr) +-{ +- enum gcry_mac_algos alg = va_arg (arg_ptr, enum gcry_mac_algos); +- +- switch (alg) +- { +- case GCRY_MAC_CMAC_AES: +- case GCRY_MAC_HMAC_SHA1: +- case GCRY_MAC_HMAC_SHA224: +- case GCRY_MAC_HMAC_SHA256: +- case GCRY_MAC_HMAC_SHA384: +- case GCRY_MAC_HMAC_SHA512: +- case GCRY_MAC_HMAC_SHA512_224: +- case GCRY_MAC_HMAC_SHA512_256: +- case GCRY_MAC_HMAC_SHA3_224: +- case GCRY_MAC_HMAC_SHA3_256: +- case GCRY_MAC_HMAC_SHA3_384: +- case GCRY_MAC_HMAC_SHA3_512: +- return GPG_ERR_NO_ERROR; +- default: +- return GPG_ERR_NOT_SUPPORTED; +- } +-} +- + /* FIPS approved curves, extracted from: + * cipher/ecc-curves.c:curve_aliases[] and domain_parms[]. */ + static const struct +@@ -602,6 +577,62 @@ _gcry_fips_indicator_pk_flags (va_list a + return GPG_ERR_NOT_SUPPORTED; + } + ++int ++_gcry_fips_indicator_hash (va_list arg_ptr) ++{ ++ enum gcry_md_algos alg = va_arg (arg_ptr, enum gcry_md_algos); ++ ++ switch (alg) ++ { ++ case GCRY_MD_SHA1: ++ case GCRY_MD_SHA224: ++ case GCRY_MD_SHA256: ++ case GCRY_MD_SHA384: ++ case GCRY_MD_SHA512: ++ case GCRY_MD_SHA512_224: ++ case GCRY_MD_SHA512_256: ++ case GCRY_MD_SHA3_224: ++ case GCRY_MD_SHA3_256: ++ case GCRY_MD_SHA3_384: ++ case GCRY_MD_SHA3_512: ++ case GCRY_MD_SHAKE128: ++ case GCRY_MD_SHAKE256: ++ return GPG_ERR_NO_ERROR; ++ default: ++ return GPG_ERR_NOT_SUPPORTED; ++ } ++} ++ ++int ++_gcry_fips_indicator_mac (va_list arg_ptr) ++{ ++ enum gcry_mac_algos alg = va_arg (arg_ptr, enum gcry_mac_algos); ++ unsigned int keylen = va_arg (arg_ptr, unsigned int); ++ ++ switch (alg) ++ { ++ case GCRY_MAC_HMAC_SHA1: ++ case GCRY_MAC_HMAC_SHA224: ++ case GCRY_MAC_HMAC_SHA256: ++ case GCRY_MAC_HMAC_SHA384: ++ case GCRY_MAC_HMAC_SHA512: ++ case GCRY_MAC_HMAC_SHA512_224: ++ case GCRY_MAC_HMAC_SHA512_256: ++ case GCRY_MAC_HMAC_SHA3_224: ++ case GCRY_MAC_HMAC_SHA3_256: ++ case GCRY_MAC_HMAC_SHA3_384: ++ case GCRY_MAC_HMAC_SHA3_512: ++ if (keylen >= 112) { ++ return GPG_ERR_NO_ERROR; ++ } ++ case GCRY_MAC_CMAC_AES: ++ if (keylen == 128 || keylen == 192 || keylen == 256) { ++ return GPG_ERR_NO_ERROR; ++ } ++ default: ++ return GPG_ERR_NOT_SUPPORTED; ++ } ++} + + /* This is a test on whether the library is in the error or + operational state. */ +Index: libgcrypt-1.11.0/src/g10lib.h +=================================================================== +--- libgcrypt-1.11.0.orig/src/g10lib.h ++++ libgcrypt-1.11.0/src/g10lib.h +@@ -469,6 +469,7 @@ void _gcry_fips_signal_error (const char + #endif + + int _gcry_fips_indicator_cipher (va_list arg_ptr); ++int _gcry_fips_indicator_hash (va_list arg_ptr); + int _gcry_fips_indicator_mac (va_list arg_ptr); + int _gcry_fips_indicator_md (va_list arg_ptr); + int _gcry_fips_indicator_kdf (va_list arg_ptr); +Index: libgcrypt-1.11.0/src/gcrypt.h.in +=================================================================== +--- libgcrypt-1.11.0.orig/src/gcrypt.h.in ++++ libgcrypt-1.11.0/src/gcrypt.h.in +@@ -336,7 +336,8 @@ enum gcry_ctl_cmds + GCRYCTL_FIPS_SERVICE_INDICATOR_MD = 86, + GCRYCTL_FIPS_SERVICE_INDICATOR_PK_FLAGS = 87, + GCRYCTL_MD_CUSTOMIZE = 88, +- GCRYCTL_FIPS_SERVICE_INDICATOR_PK = 89 ++ GCRYCTL_FIPS_SERVICE_INDICATOR_PK = 89, ++ GCRYCTL_FIPS_SERVICE_INDICATOR_HASH = 90 + }; + + /* Perform various operations defined by CMD. */ +Index: libgcrypt-1.11.0/src/global.c +=================================================================== +--- libgcrypt-1.11.0.orig/src/global.c ++++ libgcrypt-1.11.0/src/global.c +@@ -794,6 +794,12 @@ _gcry_vcontrol (enum gcry_ctl_cmds cmd, + rc = _gcry_fips_indicator_cipher (arg_ptr); + break; + ++ case GCRYCTL_FIPS_SERVICE_INDICATOR_HASH: ++ /* Get FIPS Service Indicator for a given HASH. Returns GPG_ERR_NO_ERROR ++ * if algorithm is allowed or GPG_ERR_NOT_SUPPORTED otherwise */ ++ rc = _gcry_fips_indicator_hash (arg_ptr); ++ break; ++ + case GCRYCTL_FIPS_SERVICE_INDICATOR_MAC: + /* Get FIPS Service Indicator for a given message authentication code. + * Returns GPG_ERR_NO_ERROR if algorithm is allowed or diff --git a/libgcrypt-FIPS-SLI-kdf-leylength.patch b/libgcrypt-FIPS-SLI-kdf-leylength.patch new file mode 100644 index 0000000..4a55513 --- /dev/null +++ b/libgcrypt-FIPS-SLI-kdf-leylength.patch @@ -0,0 +1,42 @@ +Index: libgcrypt-1.10.2/src/fips.c +=================================================================== +--- libgcrypt-1.10.2.orig/src/fips.c ++++ libgcrypt-1.10.2/src/fips.c +@@ -520,10 +520,15 @@ int + _gcry_fips_indicator_kdf (va_list arg_ptr) + { + enum gcry_kdf_algos alg = va_arg (arg_ptr, enum gcry_kdf_algos); ++ unsigned int keylen = 0; + + switch (alg) + { + case GCRY_KDF_PBKDF2: ++ keylen = va_arg (arg_ptr, unsigned int); ++ if (keylen < 112) { ++ return GPG_ERR_NOT_SUPPORTED; ++ } + return GPG_ERR_NO_ERROR; + default: + return GPG_ERR_NOT_SUPPORTED; +Index: libgcrypt-1.10.2/doc/gcrypt.texi +=================================================================== +--- libgcrypt-1.10.2.orig/doc/gcrypt.texi ++++ libgcrypt-1.10.2/doc/gcrypt.texi +@@ -970,12 +970,13 @@ is approved under the current FIPS 140-3 + combination is approved, this function returns @code{GPG_ERR_NO_ERROR}. + Otherwise @code{GPG_ERR_NOT_SUPPORTED} is returned. + +-@item GCRYCTL_FIPS_SERVICE_INDICATOR_KDF; Arguments: enum gcry_kdf_algos ++@item GCRYCTL_FIPS_SERVICE_INDICATOR_KDF; Arguments: enum gcry_kdf_algos [, unsigned int] + + Check if the given KDF is approved under the current FIPS 140-3 +-certification. If the KDF is approved, this function returns +-@code{GPG_ERR_NO_ERROR}. Otherwise @code{GPG_ERR_NOT_SUPPORTED} +-is returned. ++certification. The second parameter provides the keylength in bits. ++Keylength values of less that 112 bits are considered non-approved. ++If the KDF is approved, this function returns @code{GPG_ERR_NO_ERROR}. ++Otherwise @code{GPG_ERR_NOT_SUPPORTED} is returned. + + @item GCRYCTL_FIPS_SERVICE_INDICATOR_FUNCTION; Arguments: const char * + diff --git a/libgcrypt-FIPS-SLI-pk.patch b/libgcrypt-FIPS-SLI-pk.patch new file mode 100644 index 0000000..304fd37 --- /dev/null +++ b/libgcrypt-FIPS-SLI-pk.patch @@ -0,0 +1,177 @@ +Index: libgcrypt-1.11.0/src/fips.c +=================================================================== +--- libgcrypt-1.11.0.orig/src/fips.c ++++ libgcrypt-1.11.0/src/fips.c +@@ -38,6 +38,7 @@ + + #include "g10lib.h" + #include "cipher-proto.h" ++#include "cipher.h" + #include "../random/random.h" + + /* The states of the finite state machine used in fips mode. */ +@@ -400,6 +401,94 @@ _gcry_fips_indicator_mac (va_list arg_pt + default: + return GPG_ERR_NOT_SUPPORTED; + } ++} ++ ++/* FIPS approved curves, extracted from: ++ * cipher/ecc-curves.c:curve_aliases[] and domain_parms[]. */ ++static const struct ++{ ++ const char *name; /* Our name. */ ++ const char *other; /* Other name. */ ++} fips_approved_curve[] = ++ { ++ /* "NIST P-192" is non-approved if FIPS 140-3 */ ++ /* { "NIST P-192", "1.2.840.10045.3.1.1" }, /\* X9.62 OID *\/ */ ++ /* { "NIST P-192", "prime192v1" }, /\* X9.62 name. *\/ */ ++ /* { "NIST P-192", "secp192r1" }, /\* SECP name. *\/ */ ++ /* { "NIST P-192", "nistp192" }, /\* rfc5656. *\/ */ ++ ++ { "NIST P-224", "secp224r1" }, ++ { "NIST P-224", "1.3.132.0.33" }, /* SECP OID. */ ++ { "NIST P-224", "nistp224" }, /* rfc5656. */ ++ ++ { "NIST P-256", "1.2.840.10045.3.1.7" }, /* From NIST SP 800-78-1. */ ++ { "NIST P-256", "prime256v1" }, ++ { "NIST P-256", "secp256r1" }, ++ { "NIST P-256", "nistp256" }, /* rfc5656. */ ++ ++ { "NIST P-384", "secp384r1" }, ++ { "NIST P-384", "1.3.132.0.34" }, ++ { "NIST P-384", "nistp384" }, /* rfc5656. */ ++ ++ { "NIST P-521", "secp521r1" }, ++ { "NIST P-521", "1.3.132.0.35" }, ++ { "NIST P-521", "nistp521" }, /* rfc5656. */ ++ { NULL, NULL} ++ }; ++ ++enum pk_operation convert_from_pk_usage(unsigned int pk_usage) ++{ ++ switch (pk_usage) ++ { ++ case GCRY_PK_USAGE_SIGN: ++ return PUBKEY_OP_SIGN; ++ case GCRY_PK_USAGE_ENCR: ++ return PUBKEY_OP_ENCRYPT; ++ default: ++ return PUBKEY_OP_DECRYPT; ++ } ++} ++ ++int ++_gcry_fips_indicator_pk (va_list arg_ptr) ++{ ++ enum gcry_pk_algos alg = va_arg (arg_ptr, enum gcry_pk_algos); ++ enum pk_operation oper; ++ unsigned int keylen; ++ const char *curve_name; ++ ++ switch (alg) ++ { ++ case GCRY_PK_RSA: ++ case GCRY_PK_RSA_E: ++ case GCRY_PK_RSA_S: ++ oper = convert_from_pk_usage(va_arg (arg_ptr, unsigned int)); ++ switch (oper) ++ { ++ case PUBKEY_OP_ENCRYPT: ++ case PUBKEY_OP_DECRYPT: ++ return GPG_ERR_NOT_SUPPORTED; ++ default: ++ keylen = va_arg (arg_ptr, unsigned int); ++ if (keylen < 2048) ++ return GPG_ERR_NOT_SUPPORTED; ++ return GPG_ERR_NO_ERROR; ++ } ++ case GCRY_PK_ECC: ++ case GCRY_PK_ECDH: ++ case GCRY_PK_ECDSA: ++ curve_name = va_arg (arg_ptr, const char *); ++ for (int idx = 0; fips_approved_curve[idx].name; ++idx) ++ { ++ /* Check for the usual name and an alias. */ ++ if (!strcmp (curve_name, fips_approved_curve[idx].name) || ++ !strcmp (curve_name, fips_approved_curve[idx].other)) ++ return GPG_ERR_NO_ERROR; ++ } ++ return GPG_ERR_NOT_SUPPORTED; ++ default: ++ return GPG_ERR_NOT_SUPPORTED; ++ } + } + + int +Index: libgcrypt-1.11.0/src/gcrypt.h.in +=================================================================== +--- libgcrypt-1.11.0.orig/src/gcrypt.h.in ++++ libgcrypt-1.11.0/src/gcrypt.h.in +@@ -335,7 +335,8 @@ enum gcry_ctl_cmds + GCRYCTL_FIPS_SERVICE_INDICATOR_MAC = 85, + GCRYCTL_FIPS_SERVICE_INDICATOR_MD = 86, + GCRYCTL_FIPS_SERVICE_INDICATOR_PK_FLAGS = 87, +- GCRYCTL_MD_CUSTOMIZE = 88 ++ GCRYCTL_MD_CUSTOMIZE = 88, ++ GCRYCTL_FIPS_SERVICE_INDICATOR_PK = 89 + }; + + /* Perform various operations defined by CMD. */ +Index: libgcrypt-1.11.0/doc/gcrypt.texi +=================================================================== +--- libgcrypt-1.11.0.orig/doc/gcrypt.texi ++++ libgcrypt-1.11.0/doc/gcrypt.texi +@@ -1010,6 +1010,19 @@ Check if the given message digest algori + FIPS 140-3 certification. If the algorithm is approved, this function returns + @code{GPG_ERR_NO_ERROR}. Otherwise @code{GPG_ERR_NOT_SUPPORTED} is returned. + ++@item GCRYCTL_FIPS_SERVICE_INDICATOR_PK; Arguments: enum gcry_pk_algos [, constantsGCRY_PK_USAGE_ENCR or GCRY_PK_USAGE_SIGN, unsigned int (only for GCRY_PK_RSA)] [, const char * (only for GCRY_PK_ECC, GCRY_PK_ECDH or GCRY_PK_ECDSA)] ++ ++Check if the given asymmetric cipher is approved under the current ++FIPS 140-3 certification. For GCRY_PK_RSA, two additional parameter ++are required: first describes the purpose of the algorithm through one ++of the constants (GCRY_PK_USAGE_ENCR for encryption or decryption ++operations; GCRY_PK_USAGE_SIGN for sign or verify operations). Second ++one is the key length. For GCRY_PK_ECC, GCRY_PK_ECDH and ++GCRY_PK_ECDSA, only a single parameter is needed: the curve name or ++its alias as @code{const char *}. If the combination is approved, this ++function returns @code{GPG_ERR_NO_ERROR}. Otherwise ++@code{GPG_ERR_NOT_SUPPORTED} is returned. ++ + @item GCRYCTL_FIPS_SERVICE_INDICATOR_PK_FLAGS; Arguments: const char * + + Check if the given public key operation flag or s-expression object name is +Index: libgcrypt-1.11.0/src/g10lib.h +=================================================================== +--- libgcrypt-1.11.0.orig/src/g10lib.h ++++ libgcrypt-1.11.0/src/g10lib.h +@@ -473,6 +473,7 @@ int _gcry_fips_indicator_mac (va_list ar + int _gcry_fips_indicator_md (va_list arg_ptr); + int _gcry_fips_indicator_kdf (va_list arg_ptr); + int _gcry_fips_indicator_function (va_list arg_ptr); ++int _gcry_fips_indicator_pk (va_list arg_ptr); + int _gcry_fips_indicator_pk_flags (va_list arg_ptr); + + int _gcry_fips_is_operational (void); +Index: libgcrypt-1.11.0/src/global.c +=================================================================== +--- libgcrypt-1.11.0.orig/src/global.c ++++ libgcrypt-1.11.0/src/global.c +@@ -828,6 +828,15 @@ _gcry_vcontrol (enum gcry_ctl_cmds cmd, + rc = _gcry_fips_indicator_pk_flags (arg_ptr); + break; + ++ case GCRYCTL_FIPS_SERVICE_INDICATOR_PK: ++ /* Get FIPS Service Indicator for a given asymmetric algorithm. For ++ * GCRY_PK_RSA, an additional parameter for the operation mode is ++ * required. For ECC, ECDH and ECDSA, the additional parameter is the ++ * curve name or its alias. Returns GPG_ERR_NO_ERROR if the ++ * algorithm is allowed or GPG_ERR_NOT_SUPPORTED otherwise. */ ++ rc = _gcry_fips_indicator_pk (arg_ptr); ++ break; ++ + case PRIV_CTL_INIT_EXTRNG_TEST: /* Init external random test. */ + rc = GPG_ERR_NOT_SUPPORTED; + break; diff --git a/libgcrypt-FIPS-jitter-errorcodes.patch b/libgcrypt-FIPS-jitter-errorcodes.patch new file mode 100644 index 0000000..d6d314e --- /dev/null +++ b/libgcrypt-FIPS-jitter-errorcodes.patch @@ -0,0 +1,16 @@ +Index: libgcrypt-1.10.3/random/rndjent.c +=================================================================== +--- libgcrypt-1.10.3.orig/random/rndjent.c ++++ libgcrypt-1.10.3/random/rndjent.c +@@ -319,7 +319,10 @@ _gcry_rndjent_poll (void (*add)(const vo + jent_rng_totalcalls++; + rc = jent_read_entropy_safe (&jent_rng_collector, buffer, n); + if (rc < 0) +- break; ++ { ++ fips_signal_error ("jitter entropy failed"); ++ break; ++ } + /* We need to hash the output to conform to the BSI + * NTG.1 specs. */ + _gcry_md_hash_buffer (GCRY_MD_SHA256, buffer, buffer, rc); diff --git a/libgcrypt-FIPS-jitter-standalone.patch b/libgcrypt-FIPS-jitter-standalone.patch new file mode 100644 index 0000000..4f931c3 --- /dev/null +++ b/libgcrypt-FIPS-jitter-standalone.patch @@ -0,0 +1,183 @@ +Index: libgcrypt-1.10.3/random/Makefile.am +=================================================================== +--- libgcrypt-1.10.3.orig/random/Makefile.am ++++ libgcrypt-1.10.3/random/Makefile.am +@@ -21,7 +21,7 @@ + # Need to include ../src in addition to top_srcdir because gcrypt.h is + # a built header. + AM_CPPFLAGS = -I../src -I$(top_srcdir)/src +-AM_CFLAGS = $(GPG_ERROR_CFLAGS) ++AM_CFLAGS = $(GPG_ERROR_CFLAGS) -ljitterentropy + + noinst_LTLIBRARIES = librandom.la + +@@ -45,14 +45,7 @@ rndoldlinux.c \ + rndegd.c \ + rndunix.c \ + rndw32.c \ +-rndw32ce.c \ +-jitterentropy-gcd.c jitterentropy-gcd.h \ +-jitterentropy-health.c jitterentropy-health.h \ +-jitterentropy-noise.c jitterentropy-noise.h \ +-jitterentropy-sha3.c jitterentropy-sha3.h \ +-jitterentropy-timer.c jitterentropy-timer.h \ +-jitterentropy-base.h \ +-jitterentropy-base.c jitterentropy.h jitterentropy-base-user.h ++rndw32ce.c + + # The rndjent module needs to be compiled without optimization. */ + if ENABLE_O_FLAG_MUNGING +@@ -61,20 +54,8 @@ else + o_flag_munging = cat + endif + +-rndjent.o: $(srcdir)/rndjent.c jitterentropy-base-user.h \ +- $(srcdir)/jitterentropy-gcd.c $(srcdir)/jitterentropy-gcd.h \ +- $(srcdir)/jitterentropy-health.c $(srcdir)/jitterentropy-health.h \ +- $(srcdir)/jitterentropy-noise.c $(srcdir)/jitterentropy-noise.h \ +- $(srcdir)/jitterentropy-sha3.c $(srcdir)/jitterentropy-sha3.h \ +- $(srcdir)/jitterentropy-timer.c $(srcdir)/jitterentropy-timer.h \ +- $(srcdir)/jitterentropy-base.c $(srcdir)/jitterentropy.h ++rndjent.o: $(srcdir)/rndjent.c + `echo $(COMPILE) -c $(srcdir)/rndjent.c | $(o_flag_munging) ` + +-rndjent.lo: $(srcdir)/rndjent.c jitterentropy-base-user.h \ +- $(srcdir)/jitterentropy-gcd.c $(srcdir)/jitterentropy-gcd.h \ +- $(srcdir)/jitterentropy-health.c $(srcdir)/jitterentropy-health.h \ +- $(srcdir)/jitterentropy-noise.c $(srcdir)/jitterentropy-noise.h \ +- $(srcdir)/jitterentropy-sha3.c $(srcdir)/jitterentropy-sha3.h \ +- $(srcdir)/jitterentropy-timer.c $(srcdir)/jitterentropy-timer.h \ +- $(srcdir)/jitterentropy-base.c $(srcdir)/jitterentropy.h ++rndjent.lo: $(srcdir)/rndjent.c + `echo $(LTCOMPILE) -c $(srcdir)/rndjent.c | $(o_flag_munging) ` +Index: libgcrypt-1.10.3/random/rndjent.c +=================================================================== +--- libgcrypt-1.10.3.orig/random/rndjent.c ++++ libgcrypt-1.10.3/random/rndjent.c +@@ -94,17 +94,12 @@ + * jitterentropy-user-base.h file. */ + + /* Tell jitterentropy* that all functions shall be static. */ +-#define JENT_PRIVATE_COMPILE 1 ++#undef JENT_PRIVATE_COMPILE + +-#include "jitterentropy-base.c" + #ifdef JENT_CONF_ENABLE_INTERNAL_TIMER + #include + #endif /* JENT_CONF_ENABLE_INTERNAL_TIMER */ +-#include "jitterentropy-gcd.c" +-#include "jitterentropy-health.c" +-#include "jitterentropy-noise.c" +-#include "jitterentropy-sha3.c" +-#include "jitterentropy-timer.c" ++#include + + /* This is the lock we use to serialize access to this RNG. The extra + * integer variable is only used to check the locking state; that is, +Index: libgcrypt-1.10.3/random/Makefile.in +=================================================================== +--- libgcrypt-1.10.3.orig/random/Makefile.in ++++ libgcrypt-1.10.3/random/Makefile.in +@@ -147,12 +147,7 @@ am__v_at_1 = + DEFAULT_INCLUDES = -I.@am__isrc@ -I$(top_builddir) + depcomp = $(SHELL) $(top_srcdir)/build-aux/depcomp + am__maybe_remake_depfiles = depfiles +-am__depfiles_remade = ./$(DEPDIR)/jitterentropy-base.Plo \ +- ./$(DEPDIR)/jitterentropy-gcd.Plo \ +- ./$(DEPDIR)/jitterentropy-health.Plo \ +- ./$(DEPDIR)/jitterentropy-noise.Plo \ +- ./$(DEPDIR)/jitterentropy-sha3.Plo \ +- ./$(DEPDIR)/jitterentropy-timer.Plo \ ++am__depfiles_remade = \ + ./$(DEPDIR)/random-csprng.Plo ./$(DEPDIR)/random-drbg.Plo \ + ./$(DEPDIR)/random-system.Plo ./$(DEPDIR)/random.Plo \ + ./$(DEPDIR)/rndegd.Plo ./$(DEPDIR)/rndgetentropy.Plo \ +@@ -378,7 +373,7 @@ top_srcdir = @top_srcdir@ + # Need to include ../src in addition to top_srcdir because gcrypt.h is + # a built header. + AM_CPPFLAGS = -I../src -I$(top_srcdir)/src +-AM_CFLAGS = $(GPG_ERROR_CFLAGS) ++AM_CFLAGS = $(GPG_ERROR_CFLAGS) -ljitterentropy + noinst_LTLIBRARIES = librandom.la + GCRYPT_MODULES = @GCRYPT_RANDOM@ + librandom_la_DEPENDENCIES = $(GCRYPT_MODULES) +@@ -398,14 +393,7 @@ rndoldlinux.c \ + rndegd.c \ + rndunix.c \ + rndw32.c \ +-rndw32ce.c \ +-jitterentropy-gcd.c jitterentropy-gcd.h \ +-jitterentropy-health.c jitterentropy-health.h \ +-jitterentropy-noise.c jitterentropy-noise.h \ +-jitterentropy-sha3.c jitterentropy-sha3.h \ +-jitterentropy-timer.c jitterentropy-timer.h \ +-jitterentropy-base.h \ +-jitterentropy-base.c jitterentropy.h jitterentropy-base-user.h ++rndw32ce.c + + @ENABLE_O_FLAG_MUNGING_FALSE@o_flag_munging = cat + +@@ -465,12 +453,6 @@ mostlyclean-compile: + distclean-compile: + -rm -f *.tab.c + +-@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/jitterentropy-base.Plo@am__quote@ # am--include-marker +-@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/jitterentropy-gcd.Plo@am__quote@ # am--include-marker +-@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/jitterentropy-health.Plo@am__quote@ # am--include-marker +-@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/jitterentropy-noise.Plo@am__quote@ # am--include-marker +-@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/jitterentropy-sha3.Plo@am__quote@ # am--include-marker +-@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/jitterentropy-timer.Plo@am__quote@ # am--include-marker + @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/random-csprng.Plo@am__quote@ # am--include-marker + @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/random-drbg.Plo@am__quote@ # am--include-marker + @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/random-system.Plo@am__quote@ # am--include-marker +@@ -641,12 +623,6 @@ clean-am: clean-generic clean-libtool cl + mostlyclean-am + + distclean: distclean-am +- -rm -f ./$(DEPDIR)/jitterentropy-base.Plo +- -rm -f ./$(DEPDIR)/jitterentropy-gcd.Plo +- -rm -f ./$(DEPDIR)/jitterentropy-health.Plo +- -rm -f ./$(DEPDIR)/jitterentropy-noise.Plo +- -rm -f ./$(DEPDIR)/jitterentropy-sha3.Plo +- -rm -f ./$(DEPDIR)/jitterentropy-timer.Plo + -rm -f ./$(DEPDIR)/random-csprng.Plo + -rm -f ./$(DEPDIR)/random-drbg.Plo + -rm -f ./$(DEPDIR)/random-system.Plo +@@ -704,12 +680,6 @@ install-ps-am: + installcheck-am: + + maintainer-clean: maintainer-clean-am +- -rm -f ./$(DEPDIR)/jitterentropy-base.Plo +- -rm -f ./$(DEPDIR)/jitterentropy-gcd.Plo +- -rm -f ./$(DEPDIR)/jitterentropy-health.Plo +- -rm -f ./$(DEPDIR)/jitterentropy-noise.Plo +- -rm -f ./$(DEPDIR)/jitterentropy-sha3.Plo +- -rm -f ./$(DEPDIR)/jitterentropy-timer.Plo + -rm -f ./$(DEPDIR)/random-csprng.Plo + -rm -f ./$(DEPDIR)/random-drbg.Plo + -rm -f ./$(DEPDIR)/random-system.Plo +@@ -759,22 +729,10 @@ uninstall-am: + .PRECIOUS: Makefile + + +-rndjent.o: $(srcdir)/rndjent.c jitterentropy-base-user.h \ +- $(srcdir)/jitterentropy-gcd.c $(srcdir)/jitterentropy-gcd.h \ +- $(srcdir)/jitterentropy-health.c $(srcdir)/jitterentropy-health.h \ +- $(srcdir)/jitterentropy-noise.c $(srcdir)/jitterentropy-noise.h \ +- $(srcdir)/jitterentropy-sha3.c $(srcdir)/jitterentropy-sha3.h \ +- $(srcdir)/jitterentropy-timer.c $(srcdir)/jitterentropy-timer.h \ +- $(srcdir)/jitterentropy-base.c $(srcdir)/jitterentropy.h ++rndjent.o: $(srcdir)/rndjent.c + `echo $(COMPILE) -c $(srcdir)/rndjent.c | $(o_flag_munging) ` + +-rndjent.lo: $(srcdir)/rndjent.c jitterentropy-base-user.h \ +- $(srcdir)/jitterentropy-gcd.c $(srcdir)/jitterentropy-gcd.h \ +- $(srcdir)/jitterentropy-health.c $(srcdir)/jitterentropy-health.h \ +- $(srcdir)/jitterentropy-noise.c $(srcdir)/jitterentropy-noise.h \ +- $(srcdir)/jitterentropy-sha3.c $(srcdir)/jitterentropy-sha3.h \ +- $(srcdir)/jitterentropy-timer.c $(srcdir)/jitterentropy-timer.h \ +- $(srcdir)/jitterentropy-base.c $(srcdir)/jitterentropy.h ++rndjent.lo: $(srcdir)/rndjent.c + `echo $(LTCOMPILE) -c $(srcdir)/rndjent.c | $(o_flag_munging) ` + + # Tell versions [3.59,3.63) of GNU make to not export all variables. diff --git a/libgcrypt-FIPS-jitter-whole-entropy.patch b/libgcrypt-FIPS-jitter-whole-entropy.patch new file mode 100644 index 0000000..6c16472 --- /dev/null +++ b/libgcrypt-FIPS-jitter-whole-entropy.patch @@ -0,0 +1,41 @@ +Index: libgcrypt-1.10.3/random/rndgetentropy.c +=================================================================== +--- libgcrypt-1.10.3.orig/random/rndgetentropy.c ++++ libgcrypt-1.10.3/random/rndgetentropy.c +@@ -53,16 +53,30 @@ _gcry_rndgetentropy_gather_random (void + + /* When using a blocking random generator try to get some entropy + * from the jitter based RNG. In this case we take up to 50% of the +- * remaining requested bytes. */ ++ * remaining requested bytes. In FIPS mode, we get all the entropy ++ * from the jitter RNG. */ + if (level >= GCRY_VERY_STRONG_RANDOM) + { + size_t n; + +- n = _gcry_rndjent_poll (add, origin, length/2); +- if (n > length/2) +- n = length/2; +- if (length > 1) +- length -= n; ++ /* In FIPS mode, use the whole length of the entropy buffer from ++ * Jitter RNG */ ++ if (fips_mode ()) ++ { ++ n = _gcry_rndjent_poll (add, origin, length); ++ if (n != length) ++ fips_signal_error ("jitter entropy failed"); ++ else ++ length = 0; ++ } ++ else ++ { ++ n = _gcry_rndjent_poll (add, origin, length/2); ++ if (n > length/2) ++ n = length/2; ++ if (length > 1) ++ length -= n; ++ } + } + + /* Enter the loop. */ diff --git a/libgcrypt-FIPS-rndjent_poll.patch b/libgcrypt-FIPS-rndjent_poll.patch new file mode 100644 index 0000000..f837842 --- /dev/null +++ b/libgcrypt-FIPS-rndjent_poll.patch @@ -0,0 +1,114 @@ +Index: libgcrypt-1.10.0/random/rndoldlinux.c +=================================================================== +--- libgcrypt-1.10.0.orig/random/rndoldlinux.c ++++ libgcrypt-1.10.0/random/rndoldlinux.c +@@ -132,7 +132,7 @@ _gcry_rndoldlinux_gather_random (void (* + volatile pid_t apid; + int fd; + int n; +- byte buffer[768]; ++ byte buffer[256]; + size_t n_hw; + size_t want = length; + size_t last_so_far = 0; +@@ -187,26 +187,43 @@ _gcry_rndoldlinux_gather_random (void (* + my_pid = apid; + } + ++ if (fips_mode()) ++ { ++ if (level >= GCRY_VERY_STRONG_RANDOM) ++ { ++ size_t n; + +- /* First read from a hardware source. Note that _gcry_rndhw_poll_slow lets +- it account only for up to 50% (or 25% for RDRAND) of the requested +- bytes. */ +- n_hw = _gcry_rndhw_poll_slow (add, origin, length); +- if (length > 1) +- length -= n_hw; +- +- /* When using a blocking random generator try to get some entropy +- * from the jitter based RNG. In this case we take up to 50% of the +- * remaining requested bytes. */ +- if (level >= GCRY_VERY_STRONG_RANDOM) +- { +- n_hw = _gcry_rndjent_poll (add, origin, length/2); +- if (n_hw > length/2) +- n_hw = length/2; ++ n = _gcry_rndjent_poll (add, origin, length); ++ if (n == 0) ++ log_fatal ("unexpected error from rndjent: %s\n", ++ strerror (errno)); ++ if (n > length) ++ n = length; ++ if (length > 1) ++ length -= n; ++ } ++ } ++ else ++ { ++ /* First read from a hardware source. Note that _gcry_rndhw_poll_slow lets ++ it account only for up to 50% (or 25% for RDRAND) of the requested ++ bytes. */ ++ n_hw = _gcry_rndhw_poll_slow (add, origin, length); + if (length > 1) + length -= n_hw; +- } + ++ /* When using a blocking random generator try to get some entropy ++ * from the jitter based RNG. In this case we take up to 50% of the ++ * remaining requested bytes. */ ++ if (level >= GCRY_VERY_STRONG_RANDOM) ++ { ++ n_hw = _gcry_rndjent_poll (add, origin, length/2); ++ if (n_hw > length/2) ++ n_hw = length/2; ++ if (length > 1) ++ length -= n_hw; ++ } ++ } + + /* Open the requested device. The first time a device is to be + opened we fail with a fatal error if the device does not exists. +@@ -262,8 +279,6 @@ _gcry_rndoldlinux_gather_random (void (* + do + { + nbytes = length < sizeof(buffer)? length : sizeof(buffer); +- if (nbytes > 256) +- nbytes = 256; + _gcry_pre_syscall (); + ret = getentropy (buffer, nbytes); + _gcry_post_syscall (); +Index: libgcrypt-1.10.0/random/rndjent.c +=================================================================== +--- libgcrypt-1.10.0.orig/random/rndjent.c ++++ libgcrypt-1.10.0/random/rndjent.c +@@ -279,13 +279,24 @@ _gcry_rndjent_poll (void (*add)(const vo + if (!jent_rng_is_initialized) + { + /* Auto-initialize. */ +- jent_rng_is_initialized = 1; + jent_entropy_collector_free (jent_rng_collector); + jent_rng_collector = NULL; + if ( !(_gcry_random_read_conf () & RANDOM_CONF_DISABLE_JENT)) + { +- if (!jent_entropy_init ()) +- jent_rng_collector = jent_entropy_collector_alloc (1, 0); ++ if (!jent_entropy_init_ex (1, 0)) ++ { ++ jent_rng_collector = jent_entropy_collector_alloc (1, 0); ++ jent_rng_is_initialized = 1; ++ } ++ } ++ } ++ ++ if (!jent_rng_collector) ++ { ++ if (!jent_entropy_init_ex (1, 0)) ++ { ++ jent_rng_collector = jent_entropy_collector_alloc (1, 0); ++ jent_rng_is_initialized = 1; + } + } + diff --git a/libgcrypt-jitterentropy-3.4.0.patch b/libgcrypt-jitterentropy-3.4.0.patch new file mode 100644 index 0000000..dbb77ba --- /dev/null +++ b/libgcrypt-jitterentropy-3.4.0.patch @@ -0,0 +1,618 @@ +Index: libgcrypt-1.10.0/random/jitterentropy-base.c +=================================================================== +--- libgcrypt-1.10.0.orig/random/jitterentropy-base.c ++++ libgcrypt-1.10.0/random/jitterentropy-base.c +@@ -42,7 +42,7 @@ + * require consumer to be updated (as long as this number + * is zero, the API is not considered stable and can + * change without a bump of the major version) */ +-#define MINVERSION 3 /* API compatible, ABI may change, functional ++#define MINVERSION 4 /* API compatible, ABI may change, functional + * enhancements only, consumer can be left unchanged if + * enhancements are not considered */ + #define PATCHLEVEL 0 /* API / ABI compatible, no functional changes, no +@@ -200,29 +200,38 @@ ssize_t jent_read_entropy(struct rand_da + tocopy = (DATA_SIZE_BITS / 8); + else + tocopy = len; +- memcpy(p, &ec->data, tocopy); ++ ++ jent_read_random_block(ec, p, tocopy); + + len -= tocopy; + p += tocopy; + } + + /* +- * To be on the safe side, we generate one more round of entropy +- * which we do not give out to the caller. That round shall ensure +- * that in case the calling application crashes, memory dumps, pages +- * out, or due to the CPU Jitter RNG lingering in memory for long +- * time without being moved and an attacker cracks the application, +- * all he reads in the entropy pool is a value that is NEVER EVER +- * being used for anything. Thus, he does NOT see the previous value +- * that was returned to the caller for cryptographic purposes. ++ * Enhanced backtracking support: At this point, the hash state ++ * contains the digest of the previous Jitter RNG collection round ++ * which is inserted there by jent_read_random_block with the SHA ++ * update operation. At the current code location we completed ++ * one request for a caller and we do not know how long it will ++ * take until a new request is sent to us. To guarantee enhanced ++ * backtracking resistance at this point (i.e. ensure that an attacker ++ * cannot obtain information about prior random numbers we generated), ++ * but still stirring the hash state with old data the Jitter RNG ++ * obtains a new message digest from its state and re-inserts it. ++ * After this operation, the Jitter RNG state is still stirred with ++ * the old data, but an attacker who gets access to the memory after ++ * this point cannot deduce the random numbers produced by the ++ * Jitter RNG prior to this point. + */ + /* +- * If we use secured memory, do not use that precaution as the secure +- * memory protects the entropy pool. Moreover, note that using this +- * call reduces the speed of the RNG by up to half ++ * If we use secured memory, where backtracking support may not be ++ * needed because the state is protected in a different method, ++ * it is permissible to drop this support. But strongly weigh the ++ * pros and cons considering that the SHA3 operation is not that ++ * expensive. + */ + #ifndef JENT_CPU_JITTERENTROPY_SECURE_MEMORY +- jent_random_data(ec); ++ jent_read_random_block(ec, NULL, 0); + #endif + + err: +@@ -379,6 +388,7 @@ static struct rand_data + *jent_entropy_collector_alloc_internal(unsigned int osr, unsigned int flags) + { + struct rand_data *entropy_collector; ++ uint32_t memsize = 0; + + /* + * Requesting disabling and forcing of internal timer +@@ -405,7 +415,7 @@ static struct rand_data + return NULL; + + if (!(flags & JENT_DISABLE_MEMORY_ACCESS)) { +- uint32_t memsize = jent_memsize(flags); ++ memsize = jent_memsize(flags); + + entropy_collector->mem = _gcry_calloc (1, memsize); + +@@ -431,13 +441,19 @@ static struct rand_data + entropy_collector->memaccessloops = JENT_MEMORY_ACCESSLOOPS; + } + ++ if (sha3_alloc(&entropy_collector->hash_state)) ++ goto err; ++ ++ /* Initialize the hash state */ ++ sha3_256_init(entropy_collector->hash_state); ++ + /* verify and set the oversampling rate */ + if (osr < JENT_MIN_OSR) + osr = JENT_MIN_OSR; + entropy_collector->osr = osr; + entropy_collector->flags = flags; + +- if (jent_fips_enabled() || (flags & JENT_FORCE_FIPS)) ++ if ((flags & JENT_FORCE_FIPS) || jent_fips_enabled()) + entropy_collector->fips_enabled = 1; + + /* Initialize the APT */ +@@ -469,7 +485,7 @@ static struct rand_data + + err: + if (entropy_collector->mem != NULL) +- jent_zfree(entropy_collector->mem, JENT_MEMORY_SIZE); ++ jent_zfree(entropy_collector->mem, memsize); + jent_zfree(entropy_collector, sizeof(struct rand_data)); + return NULL; + } +@@ -511,6 +527,7 @@ JENT_PRIVATE_STATIC + void jent_entropy_collector_free(struct rand_data *entropy_collector) + { + if (entropy_collector != NULL) { ++ sha3_dealloc(entropy_collector->hash_state); + jent_notime_disable(entropy_collector); + if (entropy_collector->mem != NULL) { + jent_zfree(entropy_collector->mem, +@@ -664,6 +681,7 @@ static inline int jent_entropy_init_comm + int ret; + + jent_notime_block_switch(); ++ jent_health_cb_block_switch(); + + if (sha3_tester()) + return EHASH; +@@ -710,6 +728,8 @@ int jent_entropy_init_ex(unsigned int os + if (ret) + return ret; + ++ ret = ENOTIME; ++ + /* Test without internal timer unless caller does not want it */ + if (!(flags & JENT_FORCE_INTERNAL_TIMER)) + ret = jent_time_entropy_init(osr, +@@ -732,3 +752,9 @@ int jent_entropy_switch_notime_impl(stru + return jent_notime_switch(new_thread); + } + #endif ++ ++JENT_PRIVATE_STATIC ++int jent_set_fips_failure_callback(jent_fips_failure_cb cb) ++{ ++ return jent_set_fips_failure_callback_internal(cb); ++} +Index: libgcrypt-1.10.0/random/jitterentropy-gcd.c +=================================================================== +--- libgcrypt-1.10.0.orig/random/jitterentropy-gcd.c ++++ libgcrypt-1.10.0/random/jitterentropy-gcd.c +@@ -113,12 +113,8 @@ int jent_gcd_analyze(uint64_t *delta_his + goto out; + } + +- /* +- * Ensure that we have variations in the time stamp below 100 for at +- * least 10% of all checks -- on some platforms, the counter increments +- * in multiples of 100, but not always +- */ +- if (running_gcd >= 100) { ++ /* Set a sensible maximum value. */ ++ if (running_gcd >= UINT32_MAX / 2) { + ret = ECOARSETIME; + goto out; + } +Index: libgcrypt-1.10.0/random/jitterentropy-health.c +=================================================================== +--- libgcrypt-1.10.0.orig/random/jitterentropy-health.c ++++ libgcrypt-1.10.0/random/jitterentropy-health.c +@@ -19,9 +19,24 @@ + * DAMAGE. + */ + +-#include "jitterentropy.h" + #include "jitterentropy-health.h" + ++static jent_fips_failure_cb fips_cb = NULL; ++static int jent_health_cb_switch_blocked = 0; ++ ++void jent_health_cb_block_switch(void) ++{ ++ jent_health_cb_switch_blocked = 1; ++} ++ ++int jent_set_fips_failure_callback_internal(jent_fips_failure_cb cb) ++{ ++ if (jent_health_cb_switch_blocked) ++ return -EAGAIN; ++ fips_cb = cb; ++ return 0; ++} ++ + /*************************************************************************** + * Lag Predictor Test + * +@@ -434,5 +449,9 @@ unsigned int jent_health_failure(struct + if (!ec->fips_enabled) + return 0; + ++ if (fips_cb && ec->health_failure) { ++ fips_cb(ec, ec->health_failure); ++ } ++ + return ec->health_failure; + } +Index: libgcrypt-1.10.0/random/jitterentropy-health.h +=================================================================== +--- libgcrypt-1.10.0.orig/random/jitterentropy-health.h ++++ libgcrypt-1.10.0/random/jitterentropy-health.h +@@ -20,11 +20,16 @@ + #ifndef JITTERENTROPY_HEALTH_H + #define JITTERENTROPY_HEALTH_H + ++#include "jitterentropy.h" ++ + #ifdef __cplusplus + extern "C" + { + #endif + ++void jent_health_cb_block_switch(void); ++int jent_set_fips_failure_callback_internal(jent_fips_failure_cb cb); ++ + static inline uint64_t jent_delta(uint64_t prev, uint64_t next) + { + return (next - prev); +Index: libgcrypt-1.10.0/random/jitterentropy-noise.c +=================================================================== +--- libgcrypt-1.10.0.orig/random/jitterentropy-noise.c ++++ libgcrypt-1.10.0/random/jitterentropy-noise.c +@@ -33,7 +33,7 @@ + * Update of the loop count used for the next round of + * an entropy collection. + * +- * @ec [in] entropy collector struct -- may be NULL ++ * @ec [in] entropy collector struct + * @bits [in] is the number of low bits of the timer to consider + * @min [in] is the number of bits we shift the timer value to the right at + * the end to make sure we have a guaranteed minimum value +@@ -61,16 +61,13 @@ static uint64_t jent_loop_shuffle(struct + * Mix the current state of the random number into the shuffle + * calculation to balance that shuffle a bit more. + */ +- if (ec) { +- jent_get_nstime_internal(ec, &time); +- time ^= ec->data[0]; +- } ++ jent_get_nstime_internal(ec, &time); + + /* + * We fold the time value as much as possible to ensure that as many + * bits of the time stamp are included as possible. + */ +- for (i = 0; ((DATA_SIZE_BITS + bits - 1) / bits) > i; i++) { ++ for (i = 0; (((sizeof(time) << 3) + bits - 1) / bits) > i; i++) { + shuffle ^= time & mask; + time = time >> bits; + } +@@ -91,11 +88,11 @@ static uint64_t jent_loop_shuffle(struct + * This function injects the individual bits of the time value into the + * entropy pool using a hash. + * +- * @ec [in] entropy collector struct -- may be NULL +- * @time [in] time stamp to be injected ++ * @ec [in] entropy collector struct ++ * @time [in] time delta to be injected + * @loop_cnt [in] if a value not equal to 0 is set, use the given value as + * number of loops to perform the hash operation +- * @stuck [in] Is the time stamp identified as stuck? ++ * @stuck [in] Is the time delta identified as stuck? + * + * Output: + * updated hash context +@@ -104,17 +101,19 @@ static void jent_hash_time(struct rand_d + uint64_t loop_cnt, unsigned int stuck) + { + HASH_CTX_ON_STACK(ctx); +- uint8_t itermediary[SHA3_256_SIZE_DIGEST]; ++ uint8_t intermediary[SHA3_256_SIZE_DIGEST]; + uint64_t j = 0; +- uint64_t hash_loop_cnt; + #define MAX_HASH_LOOP 3 + #define MIN_HASH_LOOP 0 + + /* Ensure that macros cannot overflow jent_loop_shuffle() */ + BUILD_BUG_ON((MAX_HASH_LOOP + MIN_HASH_LOOP) > 63); +- hash_loop_cnt = ++ uint64_t hash_loop_cnt = + jent_loop_shuffle(ec, MAX_HASH_LOOP, MIN_HASH_LOOP); + ++ /* Use the memset to shut up valgrind */ ++ memset(intermediary, 0, sizeof(intermediary)); ++ + sha3_256_init(&ctx); + + /* +@@ -125,35 +124,54 @@ static void jent_hash_time(struct rand_d + hash_loop_cnt = loop_cnt; + + /* +- * This loop basically slows down the SHA-3 operation depending +- * on the hash_loop_cnt. Each iteration of the loop generates the +- * same result. ++ * This loop fills a buffer which is injected into the entropy pool. ++ * The main reason for this loop is to execute something over which we ++ * can perform a timing measurement. The injection of the resulting ++ * data into the pool is performed to ensure the result is used and ++ * the compiler cannot optimize the loop away in case the result is not ++ * used at all. Yet that data is considered "additional information" ++ * considering the terminology from SP800-90A without any entropy. ++ * ++ * Note, it does not matter which or how much data you inject, we are ++ * interested in one Keccack1600 compression operation performed with ++ * the sha3_final. + */ + for (j = 0; j < hash_loop_cnt; j++) { +- sha3_update(&ctx, ec->data, SHA3_256_SIZE_DIGEST); +- sha3_update(&ctx, (uint8_t *)&time, sizeof(uint64_t)); ++ sha3_update(&ctx, intermediary, sizeof(intermediary)); ++ sha3_update(&ctx, (uint8_t *)&ec->rct_count, ++ sizeof(ec->rct_count)); ++ sha3_update(&ctx, (uint8_t *)&ec->apt_cutoff, ++ sizeof(ec->apt_cutoff)); ++ sha3_update(&ctx, (uint8_t *)&ec->apt_observations, ++ sizeof(ec->apt_observations)); ++ sha3_update(&ctx, (uint8_t *)&ec->apt_count, ++ sizeof(ec->apt_count)); ++ sha3_update(&ctx,(uint8_t *) &ec->apt_base, ++ sizeof(ec->apt_base)); + sha3_update(&ctx, (uint8_t *)&j, sizeof(uint64_t)); ++ sha3_final(&ctx, intermediary); ++ } + +- /* +- * If the time stamp is stuck, do not finally insert the value +- * into the entropy pool. Although this operation should not do +- * any harm even when the time stamp has no entropy, SP800-90B +- * requires that any conditioning operation to have an identical +- * amount of input data according to section 3.1.5. +- */ ++ /* ++ * Inject the data from the previous loop into the pool. This data is ++ * not considered to contain any entropy, but it stirs the pool a bit. ++ */ ++ sha3_update(ec->hash_state, intermediary, sizeof(intermediary)); + +- /* +- * The sha3_final operations re-initialize the context for the +- * next loop iteration. +- */ +- if (stuck || (j < hash_loop_cnt - 1)) +- sha3_final(&ctx, itermediary); +- else +- sha3_final(&ctx, ec->data); +- } ++ /* ++ * Insert the time stamp into the hash context representing the pool. ++ * ++ * If the time stamp is stuck, do not finally insert the value into the ++ * entropy pool. Although this operation should not do any harm even ++ * when the time stamp has no entropy, SP800-90B requires that any ++ * conditioning operation to have an identical amount of input data ++ * according to section 3.1.5. ++ */ ++ if (!stuck) ++ sha3_update(ec->hash_state, (uint8_t *)&time, sizeof(uint64_t)); + + jent_memset_secure(&ctx, SHA_MAX_CTX_SIZE); +- jent_memset_secure(itermediary, sizeof(itermediary)); ++ jent_memset_secure(intermediary, sizeof(intermediary)); + } + + #define MAX_ACC_LOOP_BIT 7 +@@ -184,13 +202,12 @@ static inline uint32_t xoshiro128starsta + + static void jent_memaccess(struct rand_data *ec, uint64_t loop_cnt) + { +- uint64_t i = 0; ++ uint64_t i = 0, time = 0; + union { + uint32_t u[4]; + uint8_t b[sizeof(uint32_t) * 4]; + } prngState = { .u = {0x8e93eec0, 0xce65608a, 0xa8d46b46, 0xe83cef69} }; + uint32_t addressMask; +- uint64_t acc_loop_cnt; + + if (NULL == ec || NULL == ec->mem) + return; +@@ -199,7 +216,7 @@ static void jent_memaccess(struct rand_d + + /* Ensure that macros cannot overflow jent_loop_shuffle() */ + BUILD_BUG_ON((MAX_ACC_LOOP_BIT + MIN_ACC_LOOP_BIT) > 63); +- acc_loop_cnt = ++ uint64_t acc_loop_cnt = + jent_loop_shuffle(ec, MAX_ACC_LOOP_BIT, MIN_ACC_LOOP_BIT); + + /* +@@ -213,8 +230,10 @@ static void jent_memaccess(struct rand_d + * "per-update: timing, it gets you mostly independent "per-update" + * timing, so we can now benefit from the Central Limit Theorem! + */ +- for (i = 0; i < sizeof(prngState); i++) +- prngState.b[i] ^= ec->data[i]; ++ for (i = 0; i < sizeof(prngState); i++) { ++ jent_get_nstime_internal(ec, &time); ++ prngState.b[i] ^= (uint8_t)(time & 0xff); ++ } + + /* + * testing purposes -- allow test app to set the counter, not +@@ -358,21 +377,21 @@ unsigned int jent_measure_jitter(struct + + /** + * Generator of one 256 bit random number +- * Function fills rand_data->data ++ * Function fills rand_data->hash_state + * + * @ec [in] Reference to entropy collector + */ + void jent_random_data(struct rand_data *ec) + { +- unsigned int k = 0, safety_factor = ENTROPY_SAFETY_FACTOR; ++ unsigned int k = 0, safety_factor = 0; + +- if (!ec->fips_enabled) +- safety_factor = 0; ++ if (ec->fips_enabled) ++ safety_factor = ENTROPY_SAFETY_FACTOR; + + /* priming of the ->prev_time value */ + jent_measure_jitter(ec, 0, NULL); + +- while (1) { ++ while (!jent_health_failure(ec)) { + /* If a stuck measurement is received, repeat measurement */ + if (jent_measure_jitter(ec, 0, NULL)) + continue; +@@ -385,3 +404,22 @@ void jent_random_data(struct rand_data * + break; + } + } ++ ++void jent_read_random_block(struct rand_data *ec, char *dst, size_t dst_len) ++{ ++ uint8_t jent_block[SHA3_256_SIZE_DIGEST]; ++ ++ BUILD_BUG_ON(SHA3_256_SIZE_DIGEST != (DATA_SIZE_BITS / 8)); ++ ++ /* The final operation automatically re-initializes the ->hash_state */ ++ sha3_final(ec->hash_state, jent_block); ++ if (dst_len) ++ memcpy(dst, jent_block, dst_len); ++ ++ /* ++ * Stir the new state with the data from the old state - the digest ++ * of the old data is not considered to have entropy. ++ */ ++ sha3_update(ec->hash_state, jent_block, sizeof(jent_block)); ++ jent_memset_secure(jent_block, sizeof(jent_block)); ++} +Index: libgcrypt-1.10.0/random/jitterentropy-noise.h +=================================================================== +--- libgcrypt-1.10.0.orig/random/jitterentropy-noise.h ++++ libgcrypt-1.10.0/random/jitterentropy-noise.h +@@ -31,6 +31,7 @@ unsigned int jent_measure_jitter(struct + uint64_t loop_cnt, + uint64_t *ret_current_delta); + void jent_random_data(struct rand_data *ec); ++void jent_read_random_block(struct rand_data *ec, char *dst, size_t dst_len); + + #ifdef __cplusplus + } +Index: libgcrypt-1.10.0/random/jitterentropy-sha3.c +=================================================================== +--- libgcrypt-1.10.0.orig/random/jitterentropy-sha3.c ++++ libgcrypt-1.10.0/random/jitterentropy-sha3.c +@@ -19,6 +19,7 @@ + */ + + #include "jitterentropy-sha3.h" ++#include "jitterentropy.h" + + /*************************************************************************** + * Message Digest Implementation +@@ -380,3 +381,23 @@ int sha3_tester(void) + + return 0; + } ++ ++int sha3_alloc(void **hash_state) ++{ ++ struct sha_ctx *tmp; ++ ++ tmp = jent_zalloc(SHA_MAX_CTX_SIZE); ++ if (!tmp) ++ return 1; ++ ++ *hash_state = tmp; ++ ++ return 0; ++} ++ ++void sha3_dealloc(void *hash_state) ++{ ++ struct sha_ctx *ctx = (struct sha_ctx *)hash_state; ++ ++ jent_zfree(ctx, SHA_MAX_CTX_SIZE); ++} +Index: libgcrypt-1.10.0/random/jitterentropy-sha3.h +=================================================================== +--- libgcrypt-1.10.0.orig/random/jitterentropy-sha3.h ++++ libgcrypt-1.10.0/random/jitterentropy-sha3.h +@@ -47,6 +47,8 @@ struct sha_ctx { + void sha3_256_init(struct sha_ctx *ctx); + void sha3_update(struct sha_ctx *ctx, const uint8_t *in, size_t inlen); + void sha3_final(struct sha_ctx *ctx, uint8_t *digest); ++int sha3_alloc(void **hash_state); ++void sha3_dealloc(void *hash_state); + int sha3_tester(void); + + #ifdef __cplusplus +Index: libgcrypt-1.10.0/random/jitterentropy-timer.c +=================================================================== +--- libgcrypt-1.10.0.orig/random/jitterentropy-timer.c ++++ libgcrypt-1.10.0/random/jitterentropy-timer.c +@@ -202,8 +202,8 @@ int jent_notime_enable(struct rand_data + if (jent_force_internal_timer || (flags & JENT_FORCE_INTERNAL_TIMER)) { + /* Self test not run yet */ + if (!jent_force_internal_timer && +- jent_time_entropy_init(flags | JENT_FORCE_INTERNAL_TIMER, +- ec->osr)) ++ jent_time_entropy_init(ec->osr, ++ flags | JENT_FORCE_INTERNAL_TIMER)) + return EHEALTH; + + ec->enable_notime = 1; +Index: libgcrypt-1.10.0/random/jitterentropy.h +=================================================================== +--- libgcrypt-1.10.0.orig/random/jitterentropy.h ++++ libgcrypt-1.10.0/random/jitterentropy.h +@@ -49,7 +49,7 @@ + ***************************************************************************/ + + /* +- * Enable timer-less timer support ++ * Enable timer-less timer support with JENT_CONF_ENABLE_INTERNAL_TIMER + * + * In case the hardware is identified to not provide a high-resolution time + * stamp, this option enables a built-in high-resolution time stamp mechanism. +@@ -166,7 +166,7 @@ struct rand_data + * of the RNG are marked as SENSITIVE. A user must not + * access that information while the RNG executes its loops to + * calculate the next random value. */ +- uint8_t data[SHA3_256_SIZE_DIGEST]; /* SENSITIVE Actual random number */ ++ void *hash_state; /* SENSITIVE hash state entropy pool */ + uint64_t prev_time; /* SENSITIVE Previous time stamp */ + #define DATA_SIZE_BITS (SHA3_256_SIZE_DIGEST_BITS) + +@@ -378,28 +378,34 @@ int jent_entropy_init(void); + JENT_PRIVATE_STATIC + int jent_entropy_init_ex(unsigned int osr, unsigned int flags); + ++/* ++ * Set a callback to run on health failure in FIPS mode. ++ * This function will take an action determined by the caller. ++ */ ++typedef void (*jent_fips_failure_cb)(struct rand_data *ec, ++ unsigned int health_failure); ++JENT_PRIVATE_STATIC ++int jent_set_fips_failure_callback(jent_fips_failure_cb cb); ++ + /* return version number of core library */ + JENT_PRIVATE_STATIC + unsigned int jent_version(void); + +-#ifdef JENT_CONF_ENABLE_INTERNAL_TIMER + /* Set a different thread handling logic for the notimer support */ + JENT_PRIVATE_STATIC + int jent_entropy_switch_notime_impl(struct jent_notime_thread *new_thread); +-#endif + + /* -- END of Main interface functions -- */ + + /* -- BEGIN timer-less threading support functions to prevent code dupes -- */ + +-struct jent_notime_ctx { + #ifdef JENT_CONF_ENABLE_INTERNAL_TIMER ++ ++struct jent_notime_ctx { + pthread_attr_t notime_pthread_attr; /* pthreads library */ + pthread_t notime_thread_id; /* pthreads thread ID */ +-#endif + }; + +-#ifdef JENT_CONF_ENABLE_INTERNAL_TIMER + + JENT_PRIVATE_STATIC + int jent_notime_init(void **ctx); +Index: libgcrypt-1.10.0/random/jitterentropy-base-user.h +=================================================================== +--- libgcrypt-1.10.0.orig/random/jitterentropy-base-user.h ++++ libgcrypt-1.10.0/random/jitterentropy-base-user.h +@@ -213,12 +213,12 @@ static inline void jent_get_cachesize(lo + ext = strstr(buf, "K"); + if (ext) { + shift = 10; +- ext = '\0'; ++ *ext = '\0'; + } else { + ext = strstr(buf, "M"); + if (ext) { + shift = 20; +- ext = '\0'; ++ *ext = '\0'; + } + } + diff --git a/libgcrypt-no-deprecated-grep-alias.patch b/libgcrypt-no-deprecated-grep-alias.patch new file mode 100644 index 0000000..ba0dde8 --- /dev/null +++ b/libgcrypt-no-deprecated-grep-alias.patch @@ -0,0 +1,35 @@ +--- libgcrypt-1.10.3.orig/acinclude.m4 ++++ libgcrypt-1.10.3/acinclude.m4 +@@ -130,10 +130,10 @@ EOF + ac_nlist=conftest.nm + if AC_TRY_EVAL(NM conftest.$ac_objext \| $lt_cv_sys_global_symbol_pipe \| cut -d \' \' -f 2 \> $ac_nlist) && test -s "$ac_nlist"; then + # See whether the symbols have a leading underscore. +- if egrep '^_nm_test_func' "$ac_nlist" >/dev/null; then ++ if grep -E '^_nm_test_func' "$ac_nlist" >/dev/null; then + ac_cv_sys_symbol_underscore=yes + else +- if egrep '^nm_test_func ' "$ac_nlist" >/dev/null; then ++ if grep -E '^nm_test_func ' "$ac_nlist" >/dev/null; then + : + else + echo "configure: cannot find nm_test_func in $ac_nlist" >&AS_MESSAGE_LOG_FD +--- libgcrypt-1.10.3.orig/src/libgcrypt-config.in ++++ libgcrypt-1.10.3/src/libgcrypt-config.in +@@ -154,7 +154,7 @@ if test "$echo_cflags" = "yes"; then + + tmp="" + for i in $includes $cflags_final; do +- if echo "$tmp" | fgrep -v -- "$i" >/dev/null; then ++ if echo "$tmp" | @GREP@ -F -v -- "$i" >/dev/null; then + tmp="$tmp $i" + fi + done +@@ -175,7 +175,7 @@ if test "$echo_libs" = "yes"; then + + tmp="" + for i in $libdirs $libs_final; do +- if echo "$tmp" | fgrep -v -- "$i" >/dev/null; then ++ if echo "$tmp" | @GREP@ -F -v -- "$i" >/dev/null; then + tmp="$tmp $i" + fi + done diff --git a/libgcrypt-nobetasuffix.patch b/libgcrypt-nobetasuffix.patch new file mode 100644 index 0000000..3d4593a --- /dev/null +++ b/libgcrypt-nobetasuffix.patch @@ -0,0 +1,24 @@ +Index: libgcrypt-1.10.2/autogen.sh +=================================================================== +--- libgcrypt-1.10.2.orig/autogen.sh ++++ libgcrypt-1.10.2/autogen.sh +@@ -249,7 +249,7 @@ if [ "$myhost" = "find-version" ]; then + fi + + beta=no +- if [ -e .git ]; then ++ if false; then + ingit=yes + tmp=$(git describe --match "${matchstr1}" --long 2>/dev/null) + tmp=$(echo "$tmp" | sed s/^"$package"//) +@@ -265,8 +265,8 @@ if [ "$myhost" = "find-version" ]; then + rvd=$((0x$(echo ${rev} | dd bs=1 count=4 2>/dev/null))) + else + ingit=no +- beta=yes +- tmp="-unknown" ++ beta=no ++ tmp="" + rev="0000000" + rvd="0" + fi diff --git a/libgcrypt-ppc-enable-P10-assembly-with-ENABLE_FORCE_SOF.patch b/libgcrypt-ppc-enable-P10-assembly-with-ENABLE_FORCE_SOF.patch new file mode 100644 index 0000000..8ef3197 --- /dev/null +++ b/libgcrypt-ppc-enable-P10-assembly-with-ENABLE_FORCE_SOF.patch @@ -0,0 +1,76 @@ +commit 2c5e5ab6843d747c4b877d2c6f47226f61e9ff14 +Author: Jussi Kivilinna +Date: Sun Jun 12 21:51:34 2022 +0300 + + ppc enable P10 assembly with ENABLE_FORCE_SOFT_HWFEATURES on arch 3.00 + + * cipher/chacha20.c (chacha20_do_setkey) [USE_PPC_VEC]: Enable + P10 assembly for HWF_PPC_ARCH_3_00 if ENABLE_FORCE_SOFT_HWFEATURES is + defined. + * cipher/poly1305.c (poly1305_init) [POLY1305_USE_PPC_VEC]: Likewise. + * cipher/rijndael.c (do_setkey) [USE_PPC_CRYPTO_WITH_PPC9LE]: Likewise. + --- + + This change allows testing P10 implementations with P9 and with QEMU-PPC. + + GnuPG-bug-id: 6006 + Signed-off-by: Jussi Kivilinna + +Index: libgcrypt-1.10.2/cipher/chacha20.c +=================================================================== +--- libgcrypt-1.10.2.orig/cipher/chacha20.c ++++ libgcrypt-1.10.2/cipher/chacha20.c +@@ -484,6 +484,11 @@ chacha20_do_setkey (CHACHA20_context_t * + ctx->use_ppc = (features & HWF_PPC_ARCH_2_07) != 0; + # ifndef WORDS_BIGENDIAN + ctx->use_p10 = (features & HWF_PPC_ARCH_3_10) != 0; ++# ifdef ENABLE_FORCE_SOFT_HWFEATURES ++ /* HWF_PPC_ARCH_3_10 above is used as soft HW-feature indicator for P10. ++ * Actual implementation works with HWF_PPC_ARCH_3_00 also. */ ++ ctx->use_p10 |= (features & HWF_PPC_ARCH_3_00) != 0; ++# endif + # endif + #endif + #ifdef USE_S390X_VX +Index: libgcrypt-1.10.2/cipher/poly1305.c +=================================================================== +--- libgcrypt-1.10.2.orig/cipher/poly1305.c ++++ libgcrypt-1.10.2/cipher/poly1305.c +@@ -90,11 +90,19 @@ static void poly1305_init (poly1305_cont + const byte key[POLY1305_KEYLEN]) + { + POLY1305_STATE *st = &ctx->state; ++ unsigned int features = _gcry_get_hw_features (); + + #ifdef POLY1305_USE_PPC_VEC +- ctx->use_p10 = (_gcry_get_hw_features () & HWF_PPC_ARCH_3_10) != 0; ++ ctx->use_p10 = (features & HWF_PPC_ARCH_3_10) != 0; ++# ifdef ENABLE_FORCE_SOFT_HWFEATURES ++ /* HWF_PPC_ARCH_3_10 above is used as soft HW-feature indicator for P10. ++ * Actual implementation works with HWF_PPC_ARCH_3_00 also. */ ++ ctx->use_p10 |= (features & HWF_PPC_ARCH_3_00) != 0; ++# endif + #endif + ++ (void)features; ++ + ctx->leftover = 0; + + st->h[0] = 0; +Index: libgcrypt-1.10.2/cipher/rijndael.c +=================================================================== +--- libgcrypt-1.10.2.orig/cipher/rijndael.c ++++ libgcrypt-1.10.2/cipher/rijndael.c +@@ -605,6 +605,12 @@ do_setkey (RIJNDAEL_context *ctx, const + bulk_ops->xts_crypt = _gcry_aes_ppc9le_xts_crypt; + if (hwfeatures & HWF_PPC_ARCH_3_10) /* for P10 */ + bulk_ops->gcm_crypt = _gcry_aes_p10le_gcm_crypt; ++# ifdef ENABLE_FORCE_SOFT_HWFEATURES ++ /* HWF_PPC_ARCH_3_10 above is used as soft HW-feature indicator for P10. ++ * Actual implementation works with HWF_PPC_ARCH_3_00 also. */ ++ if (hwfeatures & HWF_PPC_ARCH_3_00) ++ bulk_ops->gcm_crypt = _gcry_aes_p10le_gcm_crypt; ++# endif + } + #endif + #ifdef USE_PPC_CRYPTO diff --git a/libgcrypt.changes b/libgcrypt.changes new file mode 100644 index 0000000..7216e78 --- /dev/null +++ b/libgcrypt.changes @@ -0,0 +1,1857 @@ +------------------------------------------------------------------- +Mon Dec 2 10:11:10 UTC 2024 - Pedro Monreal + +- Remove unrecognized option: --enable-m-guard + +------------------------------------------------------------------- +Thu Jun 20 08:11:07 UTC 2024 - Pedro Monreal + +- Update to 1.11.0: + * New and extended interfaces: + - Add an API for Key Encapsulation Mechanism (KEM). [T6755] + - Add Streamlined NTRU Prime sntrup761 algorithm. [rCcf9923e1a5] + - Add Kyber algorithm according to FIPS 203 ipd 2023-08-24. [rC18e5c0d268] + - Add Classic McEliece algorithm. [rC003367b912] + - Add One-Step KDF with hash and MAC. [T5964] + - Add KDF algorithm HKDF of RFC-5869. [T5964] + - Add KDF algorithm X963KDF for use in CMS. [rC3abac420b3] + - Add GMAC-SM4 and Poly1305-SM4. [rCd1ccc409d4] + - Add ARIA block cipher algorithm. [rC316c6d7715] + - Add explicit FIPS indicators for MD and MAC algorithms. [T6376] + - Add support for SHAKE as MGF in RSA. [T6557] + - Add gcry_md_read support for SHAKE algorithms. [T6539] + - Add gcry_md_hash_buffers_ext function. [T7035] + - Add cSHAKE hash algorithm. [rC065b3f4e02] + - Support internal generation of IV for AEAD cipher mode. [T4873] + * Performance: + - Add SM3 ARMv8/AArch64/CE assembly implementation. [rCfe891ff4a3] + - Add SM4 ARMv8/AArch64 assembly implementation. [rCd8825601f1] + - Add SM4 GFNI/AVX2 and GFI/AVX512 implementation. [rC5095d60af4,rCeaed633c16] + - Add SM4 ARMv9 SVE CE assembly implementation. [rC2dc2654006] + - Add PowerPC vector implementation of SM4. [rC0b2da804ee] + - Optimize ChaCha20 and Poly1305 for PPC P10 LE. [T6006] + - Add CTR32LE bulk acceleration for AES on PPC. [rC84f2e2d0b5] + - Add generic bulk acceleration for CTR32LE mode (GCM-SIV) for SM4 + and Camellia. [rCcf956793af] + - Add GFNI/AVX2 implementation of Camellia. [rC4e6896eb9f] + - Add AVX2 and AVX512 accelerated implementations for GHASH (GCM) + and POLYVAL (GCM-SIV). [rCd857e85cb4, rCe6f3600193] + - Add AVX512 implementation for SHA512. [rC089223aa3b] + - Add AVX512 implementation for Serpent. [rCce95b6ec35] + - Add AVX512 implementation for Poly1305 and ChaCha20. [rCcd3ed49770, rC9a63cfd617] + - Add AVX512 accelerated implementation for SHA3 and Blake2. [rCbeaad75f46,rC909daa700e] + - Add VAES/AVX2 accelerated i386 implementation for AES. [rC4a42a042bc] + - Add bulk processing for XTS mode of Camellia and SM4. [rC32b18cdb87, rCaad3381e93] + - Accelerate XTS and ECB modes for Twofish and Serpent. [rCd078a928f5,rC8a1fe5f78f] + - Add AArch64 crypto/SHA512 extension implementation for SHA512. [rCe51d3b8330] + - Add AArch64 crypto-extension implementation for Camellia. [rC898c857206] + - Accelerate OCB authentication on AMD with AVX2. [rC6b47e85d65] + * Bug fixes: + - For PowerPC check for missing optimization level for vector register usage. [T5785] + - Fix EdDSA secret key check. [T6511] + - Fix decoding of PKCS#1-v1.5 and OAEP padding. [rC34c2042792] + - Allow use of PKCS#1-v1.5 with SHA3 algorithms. [T6976] + - Fix AESWRAP padding length check. [T7130] + * Other: + - Allow empty password for Argon2 KDF. [rCa20700c55f] + - Various constant time operation imporvements. + - Add "bp256", "bp384", "bp512" aliases for Brainpool curves. + - Support for the random server has been removed. [T5811] + - The control code GCRYCTL_ENABLE_M_GUARD is deprecated and not + supported any more. Please use valgrind or other tools. [T5822] + - Logging is now done via the libgpg-error logging functions. [rCab0bdc72c7] + * Remove patches fixed upstream: + - libgcrypt-no-deprecated-grep-alias.patch + - libgcrypt-Chacha20-poly1305-Optimized-chacha20-poly1305.patch + - libgcrypt-ppc-enable-P10-assembly-with-ENABLE_FORCE_SOF.patch + * Rebase patches: + - libgcrypt-FIPS-jitter-errorcodes.patch + - libgcrypt-FIPS-jitter-whole-entropy.patch + +------------------------------------------------------------------- +Wed Mar 20 20:31:40 UTC 2024 - Pedro Monreal + +- FIPS: Make sure that Libgcrypt makes use of the built-in Jitter RNG + for the whole length entropy buffer in FIPS mode. [bsc#1220893] + * Add libgcrypt-FIPS-jitter-whole-entropy.patch + +------------------------------------------------------------------- +Wed Mar 20 15:13:04 UTC 2024 - Pedro Monreal + +- FIPS: Set the FSM into error state if Jitter RNG is returning an + error code to the caller when an health test error occurs when + random bytes are requested through the jent_read_entropy_safe() + function. [bsc#1220895] + * Add libgcrypt-FIPS-jitter-errorcodes.patch + +------------------------------------------------------------------- +Mon Mar 11 16:02:55 UTC 2024 - Pedro Monreal + +- FIPS: Replace the built-in jitter rng with standalone version + * Remove the internal jitterentropy copy [bsc#1220896] + * Add libgcrypt-FIPS-jitter-standalone.patch + * Remove not needed libgcrypt-jitterentropy-3.4.0.patch + +------------------------------------------------------------------- +Mon Feb 26 12:13:56 UTC 2024 - Pedro Monreal + +- Update upstream libgcrypt.keyring + +------------------------------------------------------------------- +Sat Jan 27 13:37:34 UTC 2024 - Dirk Müller + +- add libgcrypt-no-deprecated-grep-alias.patch + +------------------------------------------------------------------- +Tue Nov 21 10:36:09 UTC 2023 - Otto Hollmann + +- Re-create HMAC checksum after RPM build strips the library + (bsc#1217058) + +------------------------------------------------------------------- +Wed Nov 15 09:54:00 UTC 2023 - Pedro Monreal + +- Update to 1.10.3: + * Bug fixes: + - Fix public key computation for other EdDSA curves. [rC469919751d6e] + - Remove out of core handler diagnostic in FIPS mode. [T6515] + - Check that the digest size is not zero in gcry_pk_sign_md and + gcry_pk_verify_md. [T6539] + - Make store an s-exp with \0 is considered to be binary. [T6747] + - Various constant-time improvements. + * Portability: + - Use getrandom call only when supported by the platform. [T6442] + - Change the default for --with-libtool-modification to never. [T6619] + * Release-info: https://dev.gnupg.org/T6817 + * Remove patch upstream libgcrypt-1.10.0-out-of-core-handler.patch + +------------------------------------------------------------------- +Tue Oct 17 10:27:15 UTC 2023 - Pedro Monreal + +- Do not pull revision info from GIT when autoconf is run. This + removes the -unknown suffix after the version number. + * Add libgcrypt-nobetasuffix.patch [bsc#1216334] + +------------------------------------------------------------------- +Tue Oct 3 12:58:41 UTC 2023 - Pedro Monreal + +- POWER: performance enhancements for cryptography [jsc#PED-5088] + * Optimize Chacha20 and Poly1305 for PPC P10 LE: [T6006] + - Chacha20/poly1305: Optimized chacha20/poly1305 for + P10 operation [rC88fe7ac33eb4] + - ppc: enable P10 assembly with ENABLE_FORCE_SOFT_HWFEATURES + on arch-3.00 [rC2c5e5ab6843d] + * Add patches: + - libgcrypt-Chacha20-poly1305-Optimized-chacha20-poly1305.patch + - libgcrypt-ppc-enable-P10-assembly-with-ENABLE_FORCE_SOF.patch + +------------------------------------------------------------------- +Mon May 22 11:32:53 UTC 2023 - Pedro Monreal + +- FIPS: Merge the libgcrypt20-hmac package into the library and + remove the "module is complete" trigger file .fips [bsc#1185116] + * Remove libgcrypt-1.10.0-use-fipscheck.patch + +------------------------------------------------------------------- +Tue Apr 11 14:08:24 UTC 2023 - Pedro Monreal + +- Update to 1.10.2: + * Bug fixes: + - Fix Argon2 for the case output > 64. [rC13b5454d26] + - Fix missing HWF_PPC_ARCH_3_10 in HW feature. [rCe073f0ed44] + - Fix RSA key generation failure in forced FIPS mode. [T5919] + - Fix gcry_pk_hash_verify for explicit hash. [T6066] + - Fix a wrong result of gcry_mpi_invm. [T5970] + - Allow building with --disable-asm for HPPA. [T5976] + - Allow building with -Oz. [T6432] + - Enable the fast path to ChaCha20 only when supported. [T6384] + - Use size_t to avoid counter overflow in Keccak when directly + feeding more than 4GiB. [T6217] + * Other: + - Do not use secure memory for a DRBG instance. [T5933] + - Do not allow PKCS#1.5 padding for encryption in FIPS mode. [T5918] + - Fix the behaviour for child process re-seeding in the DRBG. [rC019a40c990] + - Allow verification of small RSA signatures in FIPS mode. [T5975] + - Allow the use of a shorter salt for KDFs in FIPS mode. [T6039] + - Run digest+sign self tests for RSA and ECC in FIPS mode. [rC06c9350165] + - Add function-name based FIPS indicator function. + GCRYCTL_FIPS_SERVICE_INDICATOR_FUNCTION. This is not considered + an ABI changes because the new FIPS features were not yet + approved. [rC822ee57f07] + - Improve PCT in FIPS mode. [rC285bf54b1a, rC4963c127ae, T6397] + - Use getrandom (GRND_RANDOM) in FIPS mode. [rCcf10c74bd9] + - Disable RSA-OAEP padding in FIPS mode. [rCe5bfda492a] + - Check minimum allowed key size in PBKDF in FIPS mode. [T6039,T6219] + - Get maximum 32B of entropy at once in FIPS mode. [rCce0df08bba] + - Prefer gpgrt-config when available. [T5034] + - Mark AESWRAP as approved FIPS algorithm. [T5512] + - Prevent usage of long salt for PSS in FIPS mode. [rCfdd2a8b332] + - Prevent usage of X9.31 keygen in FIPS mode. [rC392e0ccd25] + - Remove GCM mode from the allowed FIPS indicators. [rC1540698389] + - Add explicit FIPS indicators for hash and MAC algorithms. [T6376] + * Release-info: https://dev.gnupg.org/T5905 + * Rebase FIPS patches: + - libgcrypt-FIPS-SLI-hash-mac.patch + - libgcrypt-FIPS-SLI-kdf-leylength.patch + - libgcrypt-FIPS-SLI-pk.patch + +------------------------------------------------------------------- +Wed Mar 8 10:34:34 UTC 2023 - Martin Pluskal + +- Build AVX2 enabled hwcaps library for x86_64-v3 + +------------------------------------------------------------------- +Wed Oct 19 14:01:24 UTC 2022 - Pedro Monreal + +- Update to 1.10.1: + * Bug fixes: + - Fix minor memory leaks in FIPS mode. + - Build fixes for MUSL libc. + * Other: + - More portable integrity check in FIPS mode. + - Add X9.62 OIDs to sha256 and sha512 modules. + * Add the hardware optimizations config file hwf.deny to + the /etc/gcrypt/ directory. This file can be used to globally + disable the use of hardware based optimizations. + * Remove not needed separate_hmac256_binary hmac256 package + +------------------------------------------------------------------- +Wed Sep 14 13:34:13 UTC 2022 - Pedro Monreal + +- Update to 1.10.0: + * New and extended interfaces: + - New control codes to check for FIPS 140-3 approved algorithms. + - New control code to switch into non-FIPS mode. + - New cipher modes SIV and GCM-SIV as specified by RFC-5297. + - Extended cipher mode AESWRAP with padding as specified by + RFC-5649. + - New set of KDF functions. + - New KDF modes Argon2 and Balloon. + - New functions for combining hashing and signing/verification. + * Performance: + - Improved support for PowerPC architectures. + - Improved ECC performance on zSeries/s390x by using accelerated + scalar multiplication. + - Many more assembler performance improvements for several + architectures. + * Bug fixes: + - Fix Elgamal encryption for other implementations. + [bsc#1190239, CVE-2021-40528] + - Check the input length of the point in ECDH. + - Fix an abort in gcry_pk_get_param for "Curve25519". + * Other features: + - The control code GCRYCTL_SET_ENFORCED_FIPS_FLAG is ignored + because it is useless with the FIPS 140-3 related changes. + - Update of the jitter entropy RNG code. + - Simplification of the entropy gatherer when using the getentropy + system call. + * Interface changes relative to the 1.10.0 release: + - GCRYCTL_SET_DECRYPTION_TAG NEW control code. + - GCRYCTL_FIPS_SERVICE_INDICATOR_CIPHER NEW control code. + - GCRYCTL_FIPS_SERVICE_INDICATOR_KDF NEW control code. + - GCRYCTL_NO_FIPS_MODE = 83 NEW control code. + - GCRY_CIPHER_MODE_SIV NEW mode. + - GCRY_CIPHER_MODE_GCM_SIV NEW mode. + - GCRY_CIPHER_EXTENDED NEW flag. + - GCRY_SIV_BLOCK_LEN NEW macro. + - gcry_cipher_set_decryption_tag NEW macro. + - GCRY_KDF_ARGON2 NEW constant. + - GCRY_KDF_BALLOON NEW constant. + - GCRY_KDF_ARGON2D NEW constant. + - GCRY_KDF_ARGON2I NEW constant. + - GCRY_KDF_ARGON2ID NEW constant. + - gcry_kdf_hd_t NEW type. + - gcry_kdf_job_fn_t NEW type. + - gcry_kdf_dispatch_job_fn_t NEW type. + - gcry_kdf_wait_all_jobs_fn_t NEW type. + - struct gcry_kdf_thread_ops NEW struct. + - gcry_kdf_open NEW function. + - gcry_kdf_compute NEW function. + - gcry_kdf_final NEW function. + - gcry_kdf_close NEW function. + - gcry_pk_hash_sign NEW function. + - gcry_pk_hash_verify NEW function. + - gcry_pk_random_override_new NEW function. + * Rebase libgcrypt-1.8.4-allow_FSM_same_state.patch and rename + to libgcrypt-1.10.0-allow_FSM_same_state.patch + * Remove unused CAVS tests and related patches: + - cavs_driver.pl cavs-test.sh + - libgcrypt-1.6.1-fips-cavs.patch + - drbg_test.patch + * Remove DSA sign/verify patches for the FIPS CAVS test since DSA + has been disabled in FIPS mode: + - libgcrypt-fipsdrv-enable-algo-for-dsa-sign.patch + - libgcrypt-fipsdrv-enable-algo-for-dsa-verify.patch + * Rebase libgcrypt-FIPS-SLI-pk.patch + * Rebase libgcrypt_indicators_changes.patch and + libgcrypt-indicate-shake.patch and merge both into + libgcrypt-FIPS-SLI-hash-mac.patch + * Rebase libgcrypt-FIPS-kdf-leylength.patch and rename to + libgcrypt-FIPS-SLI-kdf-leylength.patch + * Rebase libgcrypt-jitterentropy-3.4.0.patch + * Rebase libgcrypt-FIPS-rndjent_poll.patch + * Rebase libgcrypt-out-of-core-handler.patch and rename to + libgcrypt-1.10.0-out-of-core-handler.patch + * Since the FIPS .hmac file is now calculated with the internal + tool hmac256, only the "module is complete" trigger .fips file + is checked. Rename libgcrypt-1.6.1-use-fipscheck.patch + to libgcrypt-1.10.0-use-fipscheck.patch + * Remove patches fixed upstream: + - libgcrypt-1.4.1-rijndael_no_strict_aliasing.patch + - libgcrypt-1.5.0-LIBGCRYPT_FORCE_FIPS_MODE-env.diff + - libgcrypt-fix-rng.patch + - libgcrypt-1.8.3-fips-ctor.patch + - libgcrypt-1.8.4-use_xfree.patch + - libgcrypt-1.8.4-getrandom.patch + - libgcrypt-1.8.4-fips_ctor_skip_integrity_check.patch + - libgcrypt-dsa-rfc6979-test-fix.patch + - libgcrypt-fix-tests-fipsmode.patch + - libgcrypt-FIPS-RSA-DSA-ECDSA-hashing-operation.patch + - libgcrypt-1.8.4-fips-keygen.patch + - libgcrypt-invoke-global_init-from-constructor.patch + - libgcrypt-Restore-self-tests-from-constructor.patch + - libgcrypt-FIPS-GMAC_AES-benckmark.patch + - libgcrypt-global_init-constructor.patch + - libgcrypt-random_selftests-testentropy.patch + - libgcrypt-rsa-no-blinding.patch + - libgcrypt-ecc-ecdsa-no-blinding.patch + - libgcrypt-PCT-DSA.patch + - libgcrypt-PCT-ECC.patch + - libgcrypt-PCT-RSA.patch + - libgcrypt-fips_selftest_trigger_file.patch + - libgcrypt-pthread-in-t-lock-test.patch + - libgcrypt-FIPS-hw-optimizations.patch + - libgcrypt-FIPS-module-version.patch + - libgcrypt-FIPS-disable-3DES.patch + - libgcrypt-FIPS-fix-regression-tests.patch + - libgcrypt-FIPS-RSA-keylen.patch + - libgcrypt-FIPS-RSA-keylen-tests.patch + - libgcrypt-FIPS-fix-gcry_mpi_sub_ui.patch + - libgcrypt-FIPS-verify-unsupported-KDF-test.patch + - libgcrypt-FIPS-HMAC-short-keylen.patch + - libgcrypt-FIPS-service-indicators.patch + - libgcrypt-FIPS-disable-DSA.patch + - libgcrypt-jitterentropy-3.3.0.patch + - libgcrypt-FIPS-Zeroize-hmac.patch + * Update libgcrypt.keyring + +------------------------------------------------------------------- +Thu Sep 8 10:34:53 UTC 2022 - Pedro Monreal + +- FIPS: Get most of the entropy from rndjent_poll [bsc#1202117] + * Add libgcrypt-FIPS-rndjent_poll.patch + * Rebase libgcrypt-jitterentropy-3.4.0.patch + +------------------------------------------------------------------- +Wed Sep 7 22:03:51 UTC 2022 - Pedro Monreal + +- FIPS: Check keylength in gcry_fips_indicator_kdf() [bsc#1190700] + * Consider approved keylength greater or equal to 112 bits. + * Add libgcrypt-FIPS-kdf-leylength.patch + +------------------------------------------------------------------- +Wed Sep 7 12:53:14 UTC 2022 - Pedro Monreal + +- FIPS: Zeroize buffer and digest in check_binary_integrity() + * Add libgcrypt-FIPS-Zeroize-hmac.patch [bsc#1191020] + +------------------------------------------------------------------- +Tue Aug 23 09:19:00 UTC 2022 - Pedro Monreal + +- FIPS: gpg/gpg2 gets out of core handler in FIPS mode while + typing Tab key to Auto-Completion. [bsc#1182983] + * Add libgcrypt-out-of-core-handler.patch + +------------------------------------------------------------------- +Mon Aug 8 11:33:03 UTC 2022 - Pedro Monreal + +- FIPS: Port libgcrypt to use jitterentropy [bsc#1202117, jsc#SLE-24941] + * Enable the jitter based entropy generator by default in random.conf + - Add libgcrypt-jitterentropy-3.3.0.patch + * Update the internal jitterentropy to version 3.4.0 + - Add libgcrypt-jitterentropy-3.4.0.patch + +------------------------------------------------------------------- +Mon Aug 1 07:27:35 UTC 2022 - Stephan Kulow + +- Fix reproducible build problems: + - Do not use %release in binaries (but use SOURCE_DATE_EPOCH) + - Fix date call messed up by spec-cleaner + +------------------------------------------------------------------- +Thu Apr 14 12:30:36 UTC 2022 - Dennis Knorr + +- FIPS: extend the service indicator [bsc#1190700] + * introduced a pk indicator function + * adapted the approved and non approved ciphersuites + * Add libgcrypt_indicators_changes.patch + * Add libgcrypt-indicate-shake.patch + +------------------------------------------------------------------- +Tue Mar 22 12:32:09 UTC 2022 - Pedro Monreal + +- FIPS: Implement a service indicator for asymmetric ciphers [bsc#1190700] + * Mark RSA public key encryption and private key decryption with + padding (e.g. OAEP, PKCS) as non-approved since RSA-OAEP lacks + peer key assurance validation requirements per SP800-56Brev2. + * Mark ECC as approved only for NIST curves P-224, P-256, P-384 + and P-521 with check for common NIST names and aliases. + * Mark DSA, ELG, EDDSA, ECDSA and ECDH as non-approved. + * Add libgcrypt-FIPS-SLI-pk.patch + * Rebase libgcrypt-FIPS-service-indicators.patch +- Run the regression tests also in FIPS mode. + * Disable tests for non-FIPS approved algos. + * Rebase: libgcrypt-FIPS-verify-unsupported-KDF-test.patch + +------------------------------------------------------------------- +Tue Feb 1 11:28:51 UTC 2022 - Pedro Monreal + +- FIPS: Disable DSA in FIPS mode [bsc#1195385] + * Upstream task: https://dev.gnupg.org/T5710 + * Add libgcrypt-FIPS-disable-DSA.patch + +------------------------------------------------------------------- +Wed Jan 19 08:36:58 UTC 2022 - Pedro Monreal + +- FIPS: Service level indicator [bsc#1190700] + * Provide an indicator to check wether the service utilizes an + approved cryptographic algorithm or not. + * Add patches: + - libgcrypt-FIPS-service-indicators.patch + - libgcrypt-FIPS-verify-unsupported-KDF-test.patch + - libgcrypt-FIPS-HMAC-short-keylen.patch + +------------------------------------------------------------------- +Tue Dec 7 09:41:01 UTC 2021 - Pedro Monreal + +- FIPS: Fix gcry_mpi_sub_ui subtraction [bsc#1193480] + * gcry_mpi_sub_ui: fix subtracting from negative value + * Add libgcrypt-FIPS-fix-gcry_mpi_sub_ui.patch + +------------------------------------------------------------------- +Tue Nov 30 09:42:23 UTC 2021 - Pedro Monreal + +- FIPS: Define an entropy source SP800-90B compliant [bsc#1185140] + * Disable jitter entropy by default in random.conf + * Disable only-urandom option by default in random.conf + +------------------------------------------------------------------- +Fri Nov 26 13:10:29 UTC 2021 - Pedro Monreal + +- FIPS: RSA KeyGen/SigGen fail with 4096 bit key sizes [bsc#1192240] + * rsa: Check RSA keylen constraints for key operations. + * rsa: Fix regression in not returning an error for prime generation. + * tests: Add 2k RSA key working in FIPS mode. + * tests: pubkey: Replace RSA key to one of 2k. + * tests: pkcs1v2: Skip tests with small keys in FIPS. + * Add patches: + - libgcrypt-FIPS-RSA-keylen.patch + - libgcrypt-FIPS-RSA-keylen-tests.patch + +------------------------------------------------------------------- +Mon Nov 8 10:21:39 UTC 2021 - Pedro Monreal + +- FIPS: Disable 3DES/Triple-DES in FIPS mode [bsc#1185138] + * Add libgcrypt-FIPS-disable-3DES.patch + +------------------------------------------------------------------- +Tue Nov 2 11:31:19 UTC 2021 - Pedro Monreal + +- FIPS: PBKDF requirements [bsc#1185137] + * The PBKDF2 selftests were introduced in libgcrypt version + 1.9.1 in the function selftest_pbkdf2() + * Upstream task: https://dev.gnupg.org/T5182 + +------------------------------------------------------------------- +Thu Oct 28 19:48:06 UTC 2021 - Pedro Monreal + +- FIPS: Fix regression tests in FIPS mode [bsc#1192131] + * Add libgcrypt-FIPS-fix-regression-tests.patch + * Upstream task: https://dev.gnupg.org/T5520 + +------------------------------------------------------------------- +Thu Sep 21 11:25:06 UTC 2021 - Pedro Monreal + +- FIPS: Provide a module name/identifier and version that can be + mapped to the validation records. [bsc#1190706] + * Add libgcrypt-FIPS-module-version.patch + * Upstream task: https://dev.gnupg.org/T5600 + +------------------------------------------------------------------- +Thu Sep 21 10:23:44 UTC 2021 - Pedro Monreal + +- FIPS: Enable hardware support also in FIPS mode [bsc#1187110] + * Add libgcrypt-FIPS-hw-optimizations.patch + * Upstream task: https://dev.gnupg.org/T5508 + +------------------------------------------------------------------- +Mon Aug 23 12:08:24 UTC 2021 - Pedro Monreal + +- Update to 1.9.4: + * Bug fixes: + - Fix Elgamal encryption for other implementations. [CVE-2021-33560] + - Fix alignment problem on macOS. + - Check the input length of the point in ECDH. + - Fix an abort in gcry_pk_get_param for "Curve25519". + * Other features: + - Add GCM and CCM to OID mapping table for AES. + * Upstream libgcrypt-CVE-2021-33560-fix-ElGamal-enc.patch + +------------------------------------------------------------------- +Mon Aug 23 10:11:55 UTC 2021 - Pedro Monreal + +- Remove not needed patch libgcrypt-sparcv9.diff + +------------------------------------------------------------------- +Thu Jul 15 12:53:45 UTC 2021 - Pedro Monreal + +- Fix building test t-lock with pthread. [bsc#1189745] + * Explicitly add -lpthread to compile the t-lock test. + * Add libgcrypt-pthread-in-t-lock-test.patch + +------------------------------------------------------------------- +Fri Jun 11 13:17:54 UTC 2021 - Pedro Monreal + +- Security fix: [bsc#1187212, CVE-2021-33560] + * cipher: Fix ElGamal encryption for other implementations. + * Exponent blinding was added in version 1.9.3. This patch + fixes ElGamal encryption, see: https://dev.gnupg.org/T5328 +- Add libgcrypt-CVE-2021-33560-fix-ElGamal-enc.patch + +------------------------------------------------------------------- +Tue Apr 20 08:46:11 UTC 2021 - Paolo Stivanin + +- libgcrypt 1.9.3: + * Bug fixes: + - Fix build problems on i386 using gcc-4.7. + - Fix checksum calculation in OCB decryption for AES on s390. + - Fix a regression in gcry_mpi_ec_add related to certain usages + of curve 25519. + - Fix a symbol not found problem on Apple M1. + - Fix for Apple iOS getentropy peculiarity. + - Make keygrip computation work for compressed points. + * Performance: + - Add x86_64 VAES/AVX2 accelerated implementation of Camellia. + - Add x86_64 VAES/AVX2 accelerated implementation of AES. + - Add VPMSUMD acceleration for GCM mode on PPC. + * Internal changes. + - Harden MPI conditional code against EM leakage. + - Harden Elgamal by introducing exponent blinding. + +------------------------------------------------------------------- +Wed Feb 17 09:49:55 UTC 2021 - Andreas Stieger + +- libgcrypt 1.9.2: + * Fix building with --disable-asm on x86 + * Check public key for ECDSA verify operation + * Make sure gcry_get_config (NULL) returns a nul-terminated + string + * Fix a memory leak in the ECDH code + * Fix a reading beyond end of input buffer in SHA2-avx2 +- remove obsolete texinfo packaging macros + +------------------------------------------------------------------- +Tue Feb 2 01:06:47 UTC 2021 - Pedro Monreal + +- Update to 1.9.1 + * *Fix exploitable bug* in hash functions introduced with + 1.9.0. [bsc#1181632, CVE-2021-3345] + * Return an error if a negative MPI is used with sexp scan + functions. + * Check for operational FIPS in the random and KDF functions. + * Fix compile error on ARMv7 with NEON disabled. + * Fix self-test in KDF module. + * Improve assembler checks for better LTO support. + * Fix 32-bit cross build on x86. + * Fix non-NEON ARM assembly implementation for SHA512. + * Fix build problems with the cipher_bulk_ops_t typedef. + * Fix Ed25519 private key handling for preceding ZEROs. + * Fix overflow in modular inverse implementation. + * Fix register access for AVX/AVX2 implementations of Blake2. + * Add optimized cipher and hash functions for s390x/zSeries. + * Use hardware bit counting functionx when available. + * Update DSA functions to match FIPS 186-3. + * New self-tests for CMACs and KDFs. + * Add bulk cipher functions for OFB and GCM modes. +- Update libgpg-error required version + +------------------------------------------------------------------- +Tue Feb 1 12:03:31 UTC 2021 - Pedro Monreal + +- Use the suffix variable correctly in get_hmac_path() +- Rebase libgcrypt-fips_selftest_trigger_file.patch + +------------------------------------------------------------------- +Mon Jan 25 12:38:35 UTC 2021 - Pedro Monreal + +- Add the global config file /etc/gcrypt/random.conf + * This file can be used to globally change parameters of the random + generator with the options: only-urandom and disable-jent. + +------------------------------------------------------------------- +Thu Jan 21 15:42:15 UTC 2021 - Pedro Monreal + +- Update to 1.9.0: + New stable branch of Libgcrypt with full API and ABI compatibility + to the 1.8 series. Release-info: https://dev.gnupg.org/T4294 + * New and extended interfaces: + - New curves Ed448, X448, and SM2. + - New cipher mode EAX. + - New cipher algo SM4. + - New hash algo SM3. + - New hash algo variants SHA512/224 and SHA512/256. + - New MAC algos for Blake-2 algorithms, the new SHA512 variants, + SM3, SM4 and for a GOST variant. + - New convenience function gcry_mpi_get_ui. + - gcry_sexp_extract_param understands new format specifiers to + directly store to integers and strings. + - New function gcry_ecc_mul_point and curve constants for Curve448 + and Curve25519. + - New function gcry_ecc_get_algo_keylen. + - New control code GCRYCTL_AUTO_EXPAND_SECMEM to allow growing the + secure memory area. + * Performance optimizations and bug fixes: See Release-info. + * Other features: + - Add OIDs from RFC-8410 as aliases for Ed25519 and Curve25519. + - Add mitigation against ECC timing attack CVE-2019-13627. + - Internal cleanup of the ECC implementation. + - Support reading EC point in compressed format for some curves. +- Rebase patches: + * libgcrypt-1.4.1-rijndael_no_strict_aliasing.patch + * libgcrypt-1.5.0-LIBGCRYPT_FORCE_FIPS_MODE-env.diff + * libgcrypt-1.6.1-use-fipscheck.patch + * drbg_test.patch + * libgcrypt-fipsdrv-enable-algo-for-dsa-sign.patch + * libgcrypt-FIPS-RSA-DSA-ECDSA-hashing-operation.patch + * libgcrypt-1.8.4-fips-keygen.patch + * libgcrypt-1.8.4-getrandom.patch + * libgcrypt-fix-tests-fipsmode.patch + * libgcrypt-global_init-constructor.patch + * libgcrypt-ecc-ecdsa-no-blinding.patch + * libgcrypt-PCT-RSA.patch + * libgcrypt-PCT-ECC.patch +- Remove patches: + * libgcrypt-unresolved-dladdr.patch + * libgcrypt-CVE-2019-12904-GCM-Prefetch.patch + * libgcrypt-CVE-2019-12904-GCM.patch + * libgcrypt-CVE-2019-12904-AES.patch + * libgcrypt-CMAC-AES-TDES-selftest.patch + * libgcrypt-1.6.1-fips-cfgrandom.patch + * libgcrypt-fips_rsa_no_enforced_mode.patch + +------------------------------------------------------------------- +Sat Oct 24 10:25:13 UTC 2020 - Andreas Stieger + +- libgcrypt 1.8.7: + * Support opaque MPI with gcry_mpi_print + * Fix extra entropy collection via clock_gettime, a fallback code + path for legacy hardware + +------------------------------------------------------------------- +Tue Jul 7 09:12:27 UTC 2020 - Pedro Monreal Gonzalez + +- Update to 1.8.6 + * mpi: Consider +0 and -0 the same in mpi_cmp + * mpi: Fix flags in mpi_copy for opaque MPI + * mpi: Fix the return value of mpi_invm_generic + * mpi: DSA,ECDSA: Fix use of mpi_invm + - Call mpi_invm before _gcry_dsa_modify_k + - Call mpi_invm before _gcry_ecc_ecdsa_sign + * mpi: Constant time mpi_inv with some conditions + - mpi/mpi-inv.c (mpih_add_n_cond, mpih_sub_n_cond, mpih_swap_cond) + - New: mpih_abs_cond, mpi_invm_odd + - Rename from _gcry_mpi_invm: mpi_invm_generic + - Use mpi_invm_odd for usual odd cases: _gcry_mpi_invm + * mpi: Abort on division by zero also in _gcry_mpi_tdiv_qr + * Fix wrong code execution in Poly1305 ARM/NEON implementation + - Set r14 to -1 at function entry: (_gcry_poly1305_armv7_neon_init_ext) + * Set vZZ.16b register to zero before use in armv8 gcm implementation + * random: Fix include of config.h + * Fix declaration of internal function _gcry_mpi_get_ui: Don't use ulong + * ecc: Fix wrong handling of shorten PK bytes + - Zeros are already recovered: (_gcry_ecc_mont_decodepoint) +- Update libgcrypt-ecc-ecdsa-no-blinding.patch + +------------------------------------------------------------------- +Tue May 19 11:25:37 UTC 2020 - Pedro Monreal Gonzalez + +- FIPS: RSA/DSA/ECC test_keys() print out debug messages [bsc#1171872] + * Print the debug messages in test_keys() only in debug mode. +- Update patches: libgcrypt-PCT-RSA.patch libgcrypt-PCT-DSA.patch + libgcrypt-PCT-ECC.patch + +------------------------------------------------------------------- +Mon Apr 27 08:55:12 UTC 2020 - Pedro Monreal Gonzalez + +- FIPS: libgcrypt: Double free in test_keys() on failed signature + verification [bsc#1169944] + * Use safer gcry_mpi_release() instead of mpi_free() +- Update patches: + * libgcrypt-PCT-DSA.patch + * libgcrypt-PCT-RSA.patch + * libgcrypt-PCT-ECC.patch + +------------------------------------------------------------------- +Thu Apr 16 16:45:23 UTC 2020 - Vítězslav Čížek + +- Ship the FIPS checksum file in the shared library package and + create a separate trigger file for the FIPS selftests (bsc#1169569) + * add libgcrypt-fips_selftest_trigger_file.patch + * refresh libgcrypt-global_init-constructor.patch +- Remove libgcrypt-binary_integrity_in_non-FIPS.patch obsoleted + by libgcrypt-global_init-constructor.patch + +------------------------------------------------------------------- +Wed Apr 15 13:55:27 UTC 2020 - Pedro Monreal Gonzalez + +- FIPS: Verify that the generated signature and the original input + differ in test_keys function for RSA, DSA and ECC: [bsc#1165539] +- Add zero-padding when qx and qy have different lengths when + assembling the Q point from affine coordinates. +- Refreshed patches: + * libgcrypt-PCT-DSA.patch + * libgcrypt-PCT-RSA.patch + * libgcrypt-PCT-ECC.patch + +------------------------------------------------------------------- +Mon Mar 30 10:48:02 UTC 2020 - Pedro Monreal Gonzalez + +- FIPS: Switch the PCT to use the new signature operation [bsc#1165539] + * Patches for DSA, RSA and ECDSA test_keys functions: + - libgcrypt-PCT-DSA.patch + - libgcrypt-PCT-RSA.patch + - libgcrypt-PCT-ECC.patch +- Update patch: libgcrypt-FIPS-RSA-DSA-ECDSA-hashing-operation.patch + +------------------------------------------------------------------- +Thu Mar 26 18:09:47 UTC 2020 - Pedro Monreal Gonzalez + +- FIPS: Run self-tests from constructor during power-on [bsc#1166748] + * Set up global_init as the constructor function: + - libgcrypt-global_init-constructor.patch + * Relax the entropy requirements on selftest. This is especially + important for virtual machines to boot properly before the RNG + is available: + - libgcrypt-random_selftests-testentropy.patch + - libgcrypt-rsa-no-blinding.patch + - libgcrypt-ecc-ecdsa-no-blinding.patch + * Fix benchmark regression test in FIPS mode: + - libgcrypt-FIPS-GMAC_AES-benckmark.patch + +------------------------------------------------------------------- +Thu Mar 12 16:54:33 UTC 2020 - Pedro Monreal Gonzalez + +- Remove check not needed in _gcry_global_constructor [bsc#1164950] + * Update libgcrypt-Restore-self-tests-from-constructor.patch + +------------------------------------------------------------------- +Tue Feb 25 22:13:24 UTC 2020 - Pedro Monreal Gonzalez + +- FIPS: Run the self-tests from the constructor [bsc#1164950] + * Add libgcrypt-invoke-global_init-from-constructor.patch + +------------------------------------------------------------------- +Fri Jan 17 17:35:15 UTC 2020 - Pedro Monreal Gonzalez + +- FIPS: libgcrypt DSA PQG parameter generation: Missing value [bsc#1161219] +- FIPS: libgcrypt DSA PQG verification incorrect results [bsc#1161215] +- FIPS: libgcrypt RSA siggen/keygen: 4k not supported [bsc#1161220] + * Add patch from Fedora libgcrypt-1.8.4-fips-keygen.patch + +------------------------------------------------------------------- +Wed Dec 11 10:18:23 UTC 2019 - Pedro Monreal Gonzalez + +- FIPS: RSA/DSA/ECDSA are missing hashing operation [bsc#1155337] + * Add libgcrypt-FIPS-RSA-DSA-ECDSA-hashing-operation.patch + +------------------------------------------------------------------- +Wed Nov 27 14:01:01 UTC 2019 - Pedro Monreal Gonzalez + +- Fix tests in FIPS mode: + * Fix tests: basic benchmark bench-slope pubkey t-cv25519 t-secmem + * Add patch libgcrypt-fix-tests-fipsmode.patch + +------------------------------------------------------------------- +Tue Nov 26 18:48:20 UTC 2019 - Pedro Monreal Gonzalez + +- Fix test dsa-rfc6979 in FIPS mode: + * Disable tests in elliptic curves with 192 bits which are not + recommended in FIPS mode + * Add patch libgcrypt-dsa-rfc6979-test-fix.patch + +------------------------------------------------------------------- +Tue Nov 12 11:05:02 UTC 2019 - Pedro Monreal Gonzalez + +- CMAC AES and TDES FIPS self-tests: + * CMAC AES self test missing [bsc#1155339] + * CMAC TDES self test missing [bsc#1155338] +- Add libgcrypt-CMAC-AES-TDES-selftest.patch + +------------------------------------------------------------------- +Fri Aug 30 14:17:48 UTC 2019 - Andreas Stieger + +- libgcrypt 1.8.5: + * CVE-2019-13627: mitigation against an ECDSA timing attack (boo#1148987) + * Improve ECDSA unblinding + * Provide a pkg-config file + +------------------------------------------------------------------- +Wed Jun 26 06:52:54 UTC 2019 - Jason Sikes + +- Fixed redundant fips tests in some situations causing sudo to stop + working when pam-kwallet is installed. bsc#1133808 + * Added libgcrypt-1.8.4-fips_ctor_skip_integrity_check.patch + * Removed libgcrypt-fips_run_selftest_at_constructor.patch + because it was obsoleted by libgcrypt-1.8.3-fips-ctor.patch + * Removed libgcrypt-fips_ignore_FIPS_MODULE_PATH.patch + because it was obsoleted by libgcrypt-1.8.4-fips_ctor_skip_integrity_check.patch + +------------------------------------------------------------------- +Fri Jun 21 16:53:07 UTC 2019 - Pedro Monreal Gonzalez + +- Fixed env-script-interpreter in cavs_driver.pl + +------------------------------------------------------------------- +Fri Jun 21 16:39:00 UTC 2019 - Pedro Monreal Gonzalez + +- Security fix: [bsc#1138939, CVE-2019-12904] + * The C implementation of AES is vulnerable to a flush-and-reload + side-channel attack because physical addresses are available to + other processes. (The C implementation is used on platforms where + an assembly-language implementation is unavailable.) + * Added patches: + - libgcrypt-CVE-2019-12904-GCM-Prefetch.patch + - libgcrypt-CVE-2019-12904-GCM.patch + - libgcrypt-CVE-2019-12904-AES.patch + +------------------------------------------------------------------- +Fri Apr 26 06:47:45 UTC 2019 - Jason Sikes + +- do not try to open /dev/urandom if getrandom() works + * Added libgcrypt-1.8.4-getrandom.patch +- Drop libgcrypt-init-at-elf-load-fips.patch obsoleted + by libgcrypt-1.8.3-fips-ctor.patch + +------------------------------------------------------------------- +Tue Apr 23 12:38:40 UTC 2019 - Jason Sikes + +- Restored libgcrypt-binary_integrity_in_non-FIPS.patch sans section that + was partially causing bsc#1131183. +- Fixed race condition in multi-threaded applications by allowing a FSM state + transition to the current state. This means some tests are run twice. + * Added libgcrypt-1.8.4-allow_FSM_same_state.patch +- Fixed an issue in malloc/free wrappers so that memory created by the malloc() + wrappers will be destroyed using the free() wrappers. + * Added libgcrypt-1.8.4-use_xfree.patch + +------------------------------------------------------------------- +Fri Apr 5 21:56:00 UTC 2019 - Jason Sikes + +- removed libgcrypt-binary_integrity_in_non-FIPS.patch since it was breaking + libotr. bsc#1131183 + +------------------------------------------------------------------- +Tue Mar 26 16:30:23 UTC 2019 - Vítězslav Čížek + +- libgcrypt-1.8.3-fips-ctor.patch changed the way the fips selftests + are invoked as well as the state transition, adjust the code so + a missing checksum file is not an issue in non-FIPS mode (bsc#1097073) + * update libgcrypt-binary_integrity_in_non-FIPS.patch + +------------------------------------------------------------------- +Tue Mar 26 16:25:18 UTC 2019 - Vítězslav Čížek + +- Enforce the minimal RSA keygen size in fips mode (bsc#1125740) + * add libgcrypt-fips_rsa_no_enforced_mode.patch + +------------------------------------------------------------------- +Fri Mar 22 14:13:05 UTC 2019 - Vítězslav Čížek + +- Don't run full self-tests from constructor (bsc#1097073) + * Don't call global_init() from the constructor, _gcry_global_constructor() + from libgcrypt-1.8.3-fips-ctor.patch takes care of the binary + integrity check instead. + * Only the binary checksum will be verified, the remaining + self-tests will be run upon the library initialization +- Add libgcrypt-fips_ignore_FIPS_MODULE_PATH.patch +- Drop libgcrypt-init-at-elf-load-fips.patch and + libgcrypt-fips_run_selftest_at_constructor.patch obsoleted + by libgcrypt-1.8.3-fips-ctor.patch + +------------------------------------------------------------------- +Thu Mar 7 10:53:40 UTC 2019 - Pedro Monreal Gonzalez + +- Skip all the self-tests except for binary integrity when called + from the constructor (bsc#1097073) + * Added libgcrypt-1.8.3-fips-ctor.patch from Fedora + +------------------------------------------------------------------- +Mon Nov 26 17:09:47 UTC 2018 - Vítězslav Čížek + +- Fail selftests when checksum file is missing in FIPS mode only + (bsc#1117355) + * add libgcrypt-binary_integrity_in_non-FIPS.patch + +------------------------------------------------------------------- +Sun Oct 28 18:57:53 UTC 2018 - astieger@suse.com + +- libgcrypt 1.8.4: + * Fix infinite loop with specific application implementations + * Fix possible leak of a few bits of secret primes to pageable + memory + * Fix possible hang in the RNG (1.8.3) + * Always make use of getrandom if possible and then use + its /dev/urandom behaviour + +------------------------------------------------------------------- +Mon Jul 2 10:38:42 UTC 2018 - schwab@suse.de + +- libgcrypt-1.6.3-aliasing.patch, libgcrypt-ppc64.patch, + libgcrypt-strict-aliasing.patch: Remove obsolete patches +- libgcrypt-1.4.1-rijndael_no_strict_aliasing.patch: Rediff +- Reenable testsuite + +------------------------------------------------------------------- +Wed Jun 13 10:46:33 UTC 2018 - kbabioch@suse.com + +- Update to version 1.8.3: + - Use blinding for ECDSA signing to mitigate a novel side-channel + attack. (CVE-2018-0495 bsc#1097410) + - Fix incorrect counter overflow handling for GCM when using an IV + size other than 96 bit. + - Fix incorrect output of AES-keywrap mode for in-place encryption + on some platforms. + - Fix the gcry_mpi_ec_curve_point point validation function. + - Fix rare assertion failure in gcry_prime_check. +- Applied spec-cleaner + +------------------------------------------------------------------- +Wed May 2 14:31:07 UTC 2018 - pmonrealgonzalez@suse.com + +- Suggest libgcrypt20-hmac for package libgcrypt20 to ensure they + are installed in the right order. [bsc#1090766] + +------------------------------------------------------------------- +Thu Mar 29 06:37:44 UTC 2018 - pmonrealgonzalez@suse.com + +- Extended the fipsdrv dsa-sign and dsa-verify commands with the + --algo parameter for the FIPS testing of DSA SigVer and SigGen + (bsc#1064455). + * Added libgcrypt-fipsdrv-enable-algo-for-dsa-sign.patch + * Added libgcrypt-fipsdrv-enable-algo-for-dsa-verify.patch + +------------------------------------------------------------------- +Thu Feb 22 15:10:36 UTC 2018 - fvogt@suse.com + +- Use %license (boo#1082318) + +------------------------------------------------------------------- +Wed Dec 13 20:09:28 UTC 2017 - astieger@suse.com + +- libgcrypt 1.8.2: + * Fix fatal out of secure memory status in the s-expression + parser on heavy loaded systems. + * Add auto expand secmem feature or use by GnuPG 2.2.4 + +------------------------------------------------------------------- +Mon Aug 28 17:54:24 UTC 2017 - astieger@suse.com + +- libgcrypt 1.8.1: + * Mitigate a local side-channel attack on Curve25519 dubbed "May + the Fourth be With You" CVE-2017-0379 bsc#1055837 + * Add more extra bytes to the pool after reading a seed file + * Add the OID SHA384WithECDSA from RFC-7427 to SHA-384 + * Fix build problems with the Jitter RNG + * Fix assembler code build problems on Rasbian (ARMv8/AArch32-CE) + +------------------------------------------------------------------- +Mon Jul 24 23:43:40 UTC 2017 - jengelh@inai.de + +- RPM group fixes. + +------------------------------------------------------------------- +Fri Jul 21 15:50:14 UTC 2017 - astieger@suse.com + +- libgcrypt 1.8.0: + * New cipher mode XTS + * New hash function Blake-2 + * New function gcry_mpi_point_copy. + * New function gcry_get_config. + * GCRYCTL_REINIT_SYSCALL_CLAMP allows to init nPth after Libgcrypt. + * New gobal configuration file /etc/gcrypt/random.conf. + * GCRYCTL_PRINT_CONFIG does now also print build information for + libgpg-error and the used compiler version. + * GCRY_CIPHER_MODE_CFB8 is now supported. + * A jitter based entropy collector is now used in addition to the + other entropy collectors. + * Optimized gcry_md_hash_buffers for SHA-256 and SHA-512. + random pool lock). + * Interface changes relative to the 1.7.0 release: + gcry_get_config NEW function. + gcry_mpi_point_copy NEW function. + GCRYCTL_REINIT_SYSCALL_CLAMP NEW macro. + GCRY_MD_BLAKE2B_512 NEW constant. + GCRY_MD_BLAKE2B_384 NEW constant. + GCRY_MD_BLAKE2B_256 NEW constant. + GCRY_MD_BLAKE2B_160 NEW constant. + GCRY_MD_BLAKE2S_256 NEW constant. + GCRY_MD_BLAKE2S_224 NEW constant. + GCRY_MD_BLAKE2S_160 NEW constant. + GCRY_MD_BLAKE2S_128 NEW constant. + GCRY_CIPHER_MODE_XTS NEW constant. + gcry_md_info DEPRECATED. +- Refresh patch libgcrypt-1.6.3-aliasing.patch + +------------------------------------------------------------------- +Thu Jun 29 09:49:44 UTC 2017 - astieger@suse.com + +- libgcrypt 1.7.8: + * CVE-2017-7526: Mitigate a flush+reload side-channel attack on + RSA secret keys (bsc#1046607) + +------------------------------------------------------------------- +Sun Jun 4 19:26:12 UTC 2017 - astieger@suse.com + +- libgcrypt 1.7.7: + * Fix possible timing attack on EdDSA session key (previously + patched, drop libgcrypt-secure-EdDSA-session-key.patch) + * Fix long standing bug in secure memory implementation which + could lead to a segv on free + +------------------------------------------------------------------- +Fri Jun 2 10:05:18 UTC 2017 - pmonrealgonzalez@suse.com + +- Added libgcrypt-secure-EdDSA-session-key.patch [bsc#1042326] + * Store the session key in secure memory to ensure that constant + time point operations are used in the MPI library. + +------------------------------------------------------------------- +Fri Jan 20 09:41:15 UTC 2017 - rmaliska@suse.com + +- libgcrypt 1.7.6: + * Fix counter operand from read-only to read/write + * Fix too large jump alignment in mpih-rshift + +------------------------------------------------------------------- +Thu Dec 15 10:32:18 UTC 2016 - astieger@suse.com + +- libgcrypt 1.7.5: + * Fix regression in mlock detection introduced with 1.7.4 + +------------------------------------------------------------------- +Tue Dec 13 12:20:47 UTC 2016 - astieger@suse.com + +- libgcrypt 1.7.4: + * ARMv8/AArch32 performance improvements for AES, GCM, SHA-256, + and SHA-1. + * Add ARMv8/AArch32 assembly implementation for Twofish and + Camellia. + * Add bulk processing implementation for ARMv8/AArch32. + * Add Stribog OIDs. + * Improve the DRBG performance and sync the code with the Linux + version. + * When secure memory is requested by the MPI functions or by + gcry_xmalloc_secure, they do not anymore lead to a fatal error + if the secure memory pool is used up. Instead new pools are + allocated as needed. These new pools are not protected against + being swapped out (mlock can't be used). Mitigation for + minor confidentiality issues is encryption swap space. + * Fix GOST 28147 CryptoPro-B S-box. + * Fix error code handling of mlock calls. + +------------------------------------------------------------------- +Sat Aug 20 10:38:15 UTC 2016 - mpluskal,vcizek,astieger}@suse.com + +- libgcrypt 1.7.3: + * security issue already fixes with 1.6.6 + * Fix building of some asm modules with older compilers and CPUs. + * ARMv8/AArch32 improvements for AES, GCM, SHA-256, and SHA-1. +- includes changes from libgcrypt 1.7.2: + * Bug fixes: + - Fix setting of the ECC cofactor if parameters are specified. + - Fix memory leak in the ECC code. + - Remove debug message about unsupported getrandom syscall. + - Fix build problems related to AVX use. + - Fix bus errors on ARM for Poly1305, ChaCha20, AES, and SHA-512. + * Internal changes: + - Improved fatal error message for wrong use of gcry_md_read. + - Disallow symmetric encryption/decryption if key is not set. +- includes changes from 1.7.1: + * Bug fixes: + - Fix ecc_verify for cofactor support. + - Fix portability bug when using gcc with Solaris 9 SPARC. + - Build fix for OpenBSD/amd64 + - Add OIDs to the Serpent ciphers. + * Internal changes: + - Use getrandom system call on Linux if available. + - Blinding is now also used for RSA signature creation. + - Changed names of debug envvars +- includes changes from 1.7.0: + * New algorithms and modes: + - SHA3-224, SHA3-256, SHA3-384, SHA3-512, and MD2 hash algorithms. + - SHAKE128 and SHAKE256 extendable-output hash algorithms. + - ChaCha20 stream cipher. + - Poly1305 message authentication algorithm + - ChaCha20-Poly1305 Authenticated Encryption with Associated Data + mode. + - OCB mode. + - HMAC-MD2 for use by legacy applications. + * New curves for ECC: + - Curve25519. + - sec256k1. + - GOST R 34.10-2001 and GOST R 34.10-2012. + * Performance: + - Improved performance of KDF functions. + - Assembler optimized implementations of Blowfish and Serpent on + ARM. + - Assembler optimized implementation of 3DES on x86. + - Improved AES using the SSSE3 based vector permutation method by + Mike Hamburg. + - AVX/BMI is used for SHA-1 and SHA-256 on x86. This is for SHA-1 + about 20% faster than SSSE3 and more than 100% faster than the + generic C implementation. + - 40% speedup for SHA-512 and 72% for SHA-1 on ARM Cortex-A8. + - 60-90% speedup for Whirlpool on x86. + - 300% speedup for RIPE MD-160. + - Up to 11 times speedup for CRC functions on x86. + * Other features: + - Improved ECDSA and FIPS 186-4 compliance. + - Support for Montgomery curves. + - gcry_cipher_set_sbox to tweak S-boxes of the gost28147 cipher + algorithm. + - gcry_mpi_ec_sub to subtract two points on a curve. + - gcry_mpi_ec_decode_point to decode an MPI into a point object. + - Emulation for broken Whirlpool code prior to 1.6.0. [from 1.6.1] + - Flag "pkcs1-raw" to enable PCKS#1 padding with a user supplied + hash part. + - Parameter "saltlen" to set a non-default salt length for RSA PSS. + - A SP800-90A conforming DRNG replaces the former X9.31 alternative + random number generator. + - Map deprecated RSA algo number to the RSA algo number for better + backward compatibility. [from 1.6.2] + - Use ciphertext blinding for Elgamal decryption [CVE-2014-3591]. + See http://www.cs.tau.ac.il/~tromer/radioexp/ for details. + [from 1.6.3] + - Fixed data-dependent timing variations in modular exponentiation + [related to CVE-2015-0837, Last-Level Cache Side-Channel Attacks + are Practical]. [from 1.6.3] + - Flag "no-keytest" for ECC key generation. Due to a bug in + the parser that flag will also be accepted but ignored by older + version of Libgcrypt. [from 1.6.4] + - Speed up the random number generator by requiring less extra + seeding. [from 1.6.4] + - Always verify a created RSA signature to avoid private key leaks + due to hardware failures. [from 1.6.4] + - Mitigate side-channel attack on ECDH with Weierstrass curves + [CVE-2015-7511]. See http://www.cs.tau.ac.IL/~tromer/ecdh/ for + details. [from 1.6.5] + * Internal changes: + - Moved locking out to libgpg-error. + - Support of the SYSROOT envvar in the build system. + - Refactor some code. + - The availability of a 64 bit integer type is now mandatory. + * Bug fixes: + - Fixed message digest lookup by OID (regression in 1.6.0). + - Fixed a build problem on NetBSD + - Fixed some asm build problems and feature detection bugs. + * Interface changes relative to the 1.6.0 release: + gcry_cipher_final NEW macro. + GCRY_CIPHER_MODE_CFB8 NEW constant. + GCRY_CIPHER_MODE_OCB NEW. + GCRY_CIPHER_MODE_POLY1305 NEW. + gcry_cipher_set_sbox NEW macro. + gcry_mac_get_algo NEW. + GCRY_MAC_HMAC_MD2 NEW. + GCRY_MAC_HMAC_SHA3_224 NEW. + GCRY_MAC_HMAC_SHA3_256 NEW. + GCRY_MAC_HMAC_SHA3_384 NEW. + GCRY_MAC_HMAC_SHA3_512 NEW. + GCRY_MAC_POLY1305 NEW. + GCRY_MAC_POLY1305_AES NEW. + GCRY_MAC_POLY1305_CAMELLIA NEW. + GCRY_MAC_POLY1305_SEED NEW. + GCRY_MAC_POLY1305_SERPENT NEW. + GCRY_MAC_POLY1305_TWOFISH NEW. + gcry_md_extract NEW. + GCRY_MD_FLAG_BUGEMU1 NEW [from 1.6.1]. + GCRY_MD_GOSTR3411_CP NEW. + GCRY_MD_SHA3_224 NEW. + GCRY_MD_SHA3_256 NEW. + GCRY_MD_SHA3_384 NEW. + GCRY_MD_SHA3_512 NEW. + GCRY_MD_SHAKE128 NEW. + GCRY_MD_SHAKE256 NEW. + gcry_mpi_ec_decode_point NEW. + gcry_mpi_ec_sub NEW. + GCRY_PK_EDDSA NEW constant. + GCRYCTL_GET_TAGLEN NEW. + GCRYCTL_SET_SBOX NEW. + GCRYCTL_SET_TAGLEN NEW. +- Apply libgcrypt-1.6.3-aliasing.patch only on big-endian + architectures +- update drbg_test.patch and install cavs testing directory again +- As DRBG is upstream, drop pateches: + v9-0001-SP800-90A-Deterministic-Random-Bit-Generator.patch + 0002-Compile-DRBG.patch + 0003-Function-definitions-of-interfaces-for-random.c.patch + 0004-Invoke-DRBG-from-common-libgcrypt-RNG-code.patch + 0005-Function-definitions-for-gcry_control-callbacks.patch + 0006-DRBG-specific-gcry_control-requests.patch + v9-0007-User-interface-to-DRBG.patch + libgcrypt-fix-rng.patch +- drop obsolete: + libgcrypt-fips-dsa.patch + libgcrypt-fips_ecdsa.patch + +------------------------------------------------------------------- +Wed Aug 17 18:21:44 UTC 2016 - astieger@suse.com + +- libgcrypt 1.6.6: + * fix CVE-2016-6313: Issue in the mixing functions of the random + number generators allowed an attacker who obtained a number of + bytes from the standard RNG to predict some of the next ouput. + (bsc#994157) + +------------------------------------------------------------------- +Mon May 16 14:37:45 UTC 2016 - pjanouch@suse.de + +- remove conditionals for unsupported distributions (before 13.2), + it would not build anyway because of new dependencies + +------------------------------------------------------------------- +Mon May 16 12:36:14 UTC 2016 - pjanouch@suse.de + +- make the -hmac package depend on the same version of the library, + fixing bsc#979629 FIPS: system fails to reboot after installing + fips pattern + +------------------------------------------------------------------- +Tue Feb 9 20:51:59 UTC 2016 - astieger@suse.com + +- update to 1.6.5: + * CVE-2015-7511: Mitigate side-channel attack on ECDH with + Weierstrass curves (boo#965902) + +------------------------------------------------------------------- +Sat Oct 10 11:56:08 UTC 2015 - astieger@suse.com + +- follow-up to libgcrypt 1.6.4 update: sosuffix is 20.0.4 + +------------------------------------------------------------------- +Tue Sep 8 08:03:19 UTC 2015 - vcizek@suse.com + +- update to 1.6.4 +- fixes libgcrypt equivalent of CVE-2015-5738 (bsc#944456) + * Speed up the random number generator by requiring less extra + seeding. + * New flag "no-keytest" for ECC key generation. Due to a bug in the + parser that flag will also be accepted but ignored by older version + of Libgcrypt. + * Always verify a created RSA signature to avoid private key leaks + due to hardware failures. + * Other minor bug fixes. + +------------------------------------------------------------------- +Tue Jun 23 15:15:30 UTC 2015 - dvaleev@suse.com + +- Fix gpg2 tests on BigEndian architectures: s390x ppc64 + libgcrypt-1.6.3-aliasing.patch + +------------------------------------------------------------------- +Sun Mar 1 21:16:26 UTC 2015 - astieger@suse.com + +- fix sosuffix for 1.6.3 (20.0.3) + +------------------------------------------------------------------- +Sat Feb 28 19:31:10 UTC 2015 - astieger@suse.com + +- libgcrypt 1.6.3 [bnc#920057]: + * Use ciphertext blinding for Elgamal decryption [CVE-2014-3591]. + * Fixed data-dependent timing variations in modular exponentiation + [related to CVE-2015-0837, Last-Level Cache Side-Channel Attacks + are Practical]. +- update upstream signing keyring + +------------------------------------------------------------------- +Fri Feb 6 18:42:28 UTC 2015 - coolo@suse.com + +- making the build reproducible - see + http://lists.gnupg.org/pipermail/gnupg-commits/2014-September/010683.html + for a very similiar problem + +------------------------------------------------------------------- +Fri Feb 6 18:38:55 UTC 2015 - dimstar@opensuse.org + +- Move %install_info_delete calls from postun to preun: the files + must still be present to be parsed. +- Fix the names passed to install_info for gcrypt.info-[12].gz + instead of gcrypt-[12].info.gz. + +------------------------------------------------------------------- +Fri Feb 6 18:30:26 UTC 2015 - coolo@suse.com + +- fix filename for info pages in %post scripts + +------------------------------------------------------------------- +Wed Nov 5 20:37:24 UTC 2014 - andreas.stieger@gmx.de + +- libgcrypt 1.6.2: + * Map deprecated RSA algo number to the RSA algo number for better + backward compatibility. + * Support a 0x40 compression prefix for EdDSA. + * Improve ARM hardware feature detection and building. + * Fix building for the x32 ABI platform. + * Fix some possible NULL deref bugs. +- remove libgcrypt-1.6.0-use-intenal-functions.patch, upstream + via xtrymalloc macro +- remove libgcrypt-fixed-sizet.patch, upstream +- adjust libgcrypt-1.6.1-use-fipscheck.patch for xtrymalloc change + +------------------------------------------------------------------- +Sun Sep 21 10:08:39 UTC 2014 - vcizek@suse.com + +- disabled curve P-192 in FIPS mode (bnc#896202) + * added libgcrypt-fips_ecdsa.patch +- don't use SHA-1 for ECDSA in FIPS mode +- also run the fips self tests only in FIPS mode + +------------------------------------------------------------------- +Tue Sep 16 13:56:01 UTC 2014 - vcizek@suse.com + +- run the fips self tests at the constructor code + * added libgcrypt-fips_run_selftest_at_constructor.patch + +------------------------------------------------------------------- +Tue Sep 16 12:17:17 UTC 2014 - vcizek@suse.com + +- rewrite the DSA-2 code to be FIPS 186-4 compliant (bnc#894216) + * added libgcrypt-fips-dsa.patch + * install fips186_dsa +- use 2048 bit keys in selftests_dsa + +------------------------------------------------------------------- +Mon Sep 1 10:57:06 UTC 2014 - vcizek@suse.com + +- fix an issue in DRBG patchset + * size_t type is 32-bit on 32-bit systems +- fix a potential NULL pointer deference in DRBG patchset + * patches from https://bugs.g10code.com/gnupg/issue1701 +- added v9-0001-SP800-90A-Deterministic-Random-Bit-Generator.patch +- added v9-0007-User-interface-to-DRBG.patch +- removed v7-0001-SP800-90A-Deterministic-Random-Bit-Generator.patch +- removed v7-0007-User-interface-to-DRBG.patch +- add a subpackage for CAVS testing + * add cavs_driver.pl and cavs-test.sh from the kernel cavs package + * added drbg_test.patch + +------------------------------------------------------------------- +Tue Aug 12 07:43:19 UTC 2014 - meissner@suse.com + +- split off the -hmac package that contains the checksums + +------------------------------------------------------------------- +Mon May 26 12:05:17 UTC 2014 - meissner@suse.com + +- libgcrypt-fix-rng.patch: make drbg work again in FIPS mode. +- libgcrypt-1.6.1-use-fipscheck.patch: library to test is libgcrypt.so.20 + and not libgcrypt.so.11 +- libgcrypt-init-at-elf-load-fips.patch: initialize globally on ELF + DSO loading to meet FIPS requirements. + +------------------------------------------------------------------- +Tue May 13 10:47:51 UTC 2014 - vcizek@suse.com + +- add new 0007-User-interface-to-DRBG.patch from upstream + * fixes bnc#877233 + * supersedes the patch from previous entry + +------------------------------------------------------------------- +Sun May 12 13:25:33 UTC 2014 - tittiatcoke@gmail.com + +- Correct patch 0007-User-interface-to-DRBG.patch so that the + struct used in the route matches the header of the function + +------------------------------------------------------------------- +Tue May 6 13:28:33 UTC 2014 - vcizek@suse.com + +- add support for SP800-90A DRBG (fate#316929, bnc#856312) + * patches by Stephan Mueller (http://www.chronox.de/drbg.html): + 0001-SP800-90A-Deterministic-Random-Bit-Generator.patch.bz2 + 0002-Compile-DRBG.patch + 0003-Function-definitions-of-interfaces-for-random.c.patch + 0004-Invoke-DRBG-from-common-libgcrypt-RNG-code.patch + 0005-Function-definitions-for-gcry_control-callbacks.patch + 0006-DRBG-specific-gcry_control-requests.patch + 0007-User-interface-to-DRBG.patch + * only after 13.1 (the patches need libgpg-error 1.13) +- drop libgcrypt-fips-allow-legacy.patch (not needed and wasn't + applied anyway) + +------------------------------------------------------------------- +Thu Apr 3 12:04:46 UTC 2014 - tchvatal@suse.com + +- Cleanup with spec-cleaner to sort out. +- Really apply ppc64 patch as it was ommited probably by mistake. + +------------------------------------------------------------------- +Thu Mar 27 14:57:22 UTC 2014 - meissner@suse.com + +- FIPS changes (from Fedora): + - replaced libgcrypt-1.5.0-etc_gcrypt_rngseed-symlink.diff by + libgcrypt-1.6.1-fips-cfgrandom.patch + - libgcrypt-fixed-sizet.patch: fixed an int type for -flto + - libgcrypt-1.6.1-use-fipscheck.patch: use the fipscheck binary + - libgcrypt-1.6.1-fips-cavs.patch: add CAVS tests +- use fipscheck only after 13.1 +- libgcrypt-fips-allow-legacy.patch: attempt to allow some + legacy algorithms for gpg2 usage even in FIPS mode. + (currently not applied) + +------------------------------------------------------------------- +Thu Jan 30 13:29:49 UTC 2014 - idonmez@suse.com + +- Drop arm-missing-files.diff, fixed upstream + +------------------------------------------------------------------- +Wed Jan 29 18:40:49 UTC 2014 - andreas.stieger@gmx.de + +- libgcrypt 1.6.1, a bugfix release with the folloging fixes: + * Added emulation for broken Whirlpool code prior to 1.6.0. + * Improved performance of KDF functions. + * Improved ECDSA compliance. + * Fixed message digest lookup by OID (regression in 1.6.0). + * Fixed memory leaks in ECC code. + * Fixed some asm build problems and feature detection bugs. + * Interface changes relative to the 1.6.0 release: + GCRY_MD_FLAG_BUGEMU1 NEW (minor API change). + +------------------------------------------------------------------- +Fri Jan 3 16:36:21 UTC 2014 - dmueller@suse.com + +- add arm-missing-files.diff: Add missing files to fix build + +------------------------------------------------------------------- +Fri Jan 3 09:43:39 UTC 2014 - mvyskocil@suse.com + +- fix bnc#856915: can't open /dev/urandom + * correct libgcrypt-1.5.0-etc_gcrypt_rngseed-symlink.diff +- require libgpg-error 1.11 or higher + +------------------------------------------------------------------- +Thu Dec 19 13:53:21 UTC 2013 - mvyskocil@suse.com + +- fix dependency for 32bit devel package +- name hmac files according soname +- fix hmac subpackage dependency + +------------------------------------------------------------------- +Thu Dec 19 09:03:21 UTC 2013 - mvyskocil@suse.com + +- update to 1.6. + * Removed the long deprecated gcry_ac interface. Thus Libgcrypt is + not anymore ABI compatible to previous versions if they used the ac + interface. Check NEWS in libgcrypt-devel for removed interfaces. + * Removed the module register subsystem. + * The deprecated message digest debug macros have been removed. Use + gcry_md_debug instead. + * Removed deprecated control codes. + * Improved performance of most cipher algorithms as well as for the + SHA family of hash functions. + * Added support for the IDEA cipher algorithm. + * Added support for the Salsa20 and reduced Salsa20/12 stream ciphers. + * Added limited support for the GOST 28147-89 cipher algorithm. + * Added support for the GOST R 34.11-94 and R 34.11-2012 (Stribog) + hash algorithms. + * Added a random number generator to directly use the system's RNG. + Also added an interface to prefer the use of a specified RNG. + * Added support for the SCRYPT algorithm. + * Mitigated the Yarom/Falkner flush+reload side-channel attack on RSA + secret keys. See [CVE-2013-4242]. + * Added support for Deterministic DSA as per RFC-6969. + * Added support for curve Ed25519. + * Added a scatter gather hash convenience function. + * Added several MPI amd SEXP helper functions. + * Added support for negative numbers to gcry_mpi_print, + gcry_mpi_aprint and gcry_mpi_scan. + * The algorithm ids GCRY_PK_ECDSA and GCRY_PK_ECDH are now + deprecated. Use GCRY_PK_ECC if you need an algorithm id. + * Changed gcry_pk_genkey for "ecc" to only include the curve name and + not the parameters. The flag "param" may be used to revert this. + * Added a feature to globally disable selected hardware features. + * Added debug helper functions. +- rebased patches + * libgcrypt-1.5.0-etc_gcrypt_rngseed-symlink.diff + * libgcrypt-ppc64.patch +- add libgcrypt-1.6.0-use-intenal-functions.patch to fix fips.c build +- Move all documentation to -devel package + +------------------------------------------------------------------- +Fri Jul 26 22:05:46 UTC 2013 - andreas.stieger@gmx.de + +- update to 1.5.3 [bnc#831359] CVE-2013-4242 + * Mitigate the Yarom/Falkner flush+reload side-channel attack on + RSA secret keys. See . + +------------------------------------------------------------------- +Thu Jul 25 09:15:43 UTC 2013 - mvyskocil@suse.com + +- port SLE enhancenments to Factory (bnc#831028) + * add libgcrypt-unresolved-dladdr.patch (bnc#701267) + * add libgcrypt-1.5.0-etc_gcrypt_rngseed-symlink.diff (bnc#724841) + * add libgcrypt-1.5.0-LIBGCRYPT_FORCE_FIPS_MODE-env.diff +- install .hmac256.hmac (bnc#704068) +- enable varuous new options in configure (m-guard, hmac binary check and + random device linux) +- build with all ciphers, pubkeys and digest by default as whitelist + simply allowed them all + +------------------------------------------------------------------- +Mon Jun 17 13:22:33 UTC 2013 - coolo@suse.com + +- avoid gpg-offline in bootstrap packages + +------------------------------------------------------------------- +Sun Jun 16 22:56:56 UTC 2013 - crrodriguez@opensuse.org + +- Library must be built with large file support in + 32 bit archs. + +------------------------------------------------------------------- +Thu Apr 18 18:23:36 UTC 2013 - andreas.stieger@gmx.de + +- update to 1.5.2 + * The upstream sources now contain the IDEA algorithm, dropping: + idea.c.gz + libgcrypt-1.5.0-idea.patch + libgcrypt-1.5.0-idea_codecleanup.patch + * Made the Padlock code work again (regression since 1.5.0). + * Fixed alignment problems for Serpent. + * Fixed two bugs in ECC computations. + +------------------------------------------------------------------- +Fri Mar 22 09:31:11 UTC 2013 - mvyskocil@suse.com + +- add GPL3.0+ to License tag because of dumpsexp (bnc#810759) + +------------------------------------------------------------------- +Mon Mar 18 20:41:00 UTC 2013 - andreas.stieger@gmx.de + +- update to 1.5.1 + * Allow empty passphrase with PBKDF2. + * Do not abort on an invalid algorithm number in + gcry_cipher_get_algo_keylen and gcry_cipher_get_algo_blklen. + * Fixed some Valgrind warnings. + * Fixed a problem with select and high fd numbers. + * Improved the build system + * Various minor bug fixes. + * Interface changes relative to the 1.5.0 release: + GCRYCTL_SET_ENFORCED_FIPS_FLAG NEW. + GCRYPT_VERSION_NUMBER NEW. +- add verification of source code signatures +- now requires automake 1.11 to build + +------------------------------------------------------------------- +Sat Feb 2 18:51:33 UTC 2013 - coolo@suse.com + +- update license to new format + +------------------------------------------------------------------- +Tue Jun 12 21:19:18 UTC 2012 - chris@computersalat.de + +- fix deps + * libgpg-error-devel >= 1.8 +- add libsoname macro + +------------------------------------------------------------------- +Sun Feb 12 15:23:56 UTC 2012 - crrodriguez@opensuse.org + +- Libraries back into %{_libdir}, /usr merge project + +------------------------------------------------------------------- +Sat Dec 24 23:51:26 UTC 2011 - opensuse@dstoecker.de + +- add the missing IDEA algorithm after the patent is no longer relevant + +------------------------------------------------------------------ +Sun Nov 13 14:37:29 UTC 2011 - jengelh@medozas.de + +- Remove redundant/unwanted tags/section (cf. specfile guidelines) + +------------------------------------------------------------------- +Sun Nov 13 09:16:36 UTC 2011 - coolo@suse.com + +- add libtool as explicit buildrequire to avoid implicit dependency from prjconf + +------------------------------------------------------------------- +Sun Oct 2 18:38:28 UTC 2011 - crrodriguez@opensuse.org + +- Update to version 1.5.0, most important changes + * Uses the Intel AES-NI instructions if available + * Support ECDH. + +------------------------------------------------------------------- +Fri Nov 19 09:59:41 UTC 2010 - mvyskocil@suse.cz + +- update to 1.4.6 + * Fixed minor memory leak in DSA key generation. + * No more switching to FIPS mode if /proc/version is not readable. + * Fixed a sigill during Padlock detection on old CPUs. + * Boosted SHA-512 performance by 30% on ia32 boxes and gcc 4.3; + SHA-256 went up by 25%. + * New variants of the TIGER algorithm. + * New cipher algorithm mode for AES-WRAP. + * Interface changes relative to the 1.4.2 release: + GCRY_MD_TIGER1 NEW + GCRY_MD_TIGER2 NEW + GCRY_CIPHER_MODE_AESWRAP NEW + +------------------------------------------------------------------- +Sun Jul 4 19:07:16 UTC 2010 - jengelh@medozas.de + +- add missing definition of udiv_qrnnd for sparcv9:32 +- use %_smp_mflags + +------------------------------------------------------------------- +Sat Dec 19 12:58:20 CET 2009 - jengelh@medozas.de + +- add baselibs.conf as a source +- disable the use of hand-coded assembler functions on sparc - + this is giving me an infinite loop with ./tests/prime + (specifically ./sparc32v8/mpih-mul1.S:_gcry_mpih_mul_1. + Fedora disables this too. + +------------------------------------------------------------------- +Tue Apr 7 15:45:06 CEST 2009 - crrodriguez@suse.de + +- update to version 1.4.4 + * Publish GCRY_MODULE_ID_USER and GCRY_MODULE_ID_USER_LAST constants. + This functionality has been in Libgcrypt since 1.3.0. + * MD5 may now be used in non-enforced fips mode. + * Fixed HMAC for SHA-384 and SHA-512 with keys longer than 64 bytes. + * In fips mode, RSA keys are now generated using the X9.31 algorithm + and DSA keys using the FIPS 186-2 algorithm. + * The transient-key flag is now also supported for DSA key + generation. DSA domain parameters may be given as well. + +------------------------------------------------------------------- +Thu Jan 29 10:57:01 CET 2009 - olh@suse.de + +- obsolete libgcrypt-error-XXbit in the library subpackage + +------------------------------------------------------------------- +Wed Dec 10 12:34:56 CET 2008 - olh@suse.de + +- use Obsoletes: -XXbit only for ppc64 to help solver during distupgrade + (bnc#437293) + +------------------------------------------------------------------- +Tue Nov 11 17:23:54 CET 2008 - mkoenig@suse.de + +- build rijndael.c with -fno-strict-aliasing [bnc#443693] + +------------------------------------------------------------------- +Thu Oct 30 12:34:56 CET 2008 - olh@suse.de + +- obsolete old -XXbit packages (bnc#437293) + +------------------------------------------------------------------- +Mon Jun 30 11:47:59 CEST 2008 - mkoenig@suse.de + +- update to version 1.4.1 + * Fixed a bug which led to the comsumption of far too much + entropy for the intial seeding + * Improved AES performance for CFB and CBC modes + +------------------------------------------------------------------- +Sun May 11 11:54:39 CEST 2008 - coolo@suse.de + +- fix rename of xxbit packages + +------------------------------------------------------------------- +Thu Apr 10 12:54:45 CEST 2008 - ro@suse.de + +- added baselibs.conf file to build xxbit packages + for multilib support + +------------------------------------------------------------------- +Thu Jan 17 12:20:25 CET 2008 - mkoenig@suse.de + +- update to version 1.4.0: + * The entire library is now under the LGPL. The helper programs and + the manual are under the GPL + * New control code GCRYCTL_PRINT_CONFIG + * Experimental support for ECDSA + * Assembler support for the AMD64 architecture + * Non executable stack support is now used by default + * New configure option --enable-random-daemon + * The new function gcry_md_debug should be used instead of the + gcry_md_start_debug and gcry_md_stop_debug macros. + * Support for DSA2 + * Reserved algorithm ranges for use by applications + * gcry_mpi_rshift does not anymore truncate the shift count + * Support for OFB encryption mode + * Support for the Camellia cipher + * Support for the SEED cipher + * Support for SHA-224 and HMAC using SHA-384 and SHA-512 + * Reading and writing the random seed file is now protected by a + fcntl style file lock + * Made the RNG immune against fork without exec + * Changed the way the RNG gets initialized + * The ASN.1 DER template for SHA-224 has been fixed + * The ACE engine of VIA processors is now used for AES-128 +- changed package layout to conform shlib policy: + new subpackage libgcrypt11 +- disable static library +- for reference: bugzilla entry of last change #304749 + +------------------------------------------------------------------- +Thu Sep 13 01:28:53 CEST 2007 - ltinkl@suse.cz + +- add sanity check for mpi of size 0 (#304479) + +------------------------------------------------------------------- +Mon Feb 5 10:25:21 CET 2007 - mkoenig@suse.de + +- update to version 1.2.4: + * Fixed a bug in the memory allocator which could have been the + reason for some of non-duplicable bugs. + * Other minor bug fixes. + +------------------------------------------------------------------- +Wed Dec 13 12:47:48 CET 2006 - mkoenig@suse.de + +- get rid of .la file and fix devel so link + +------------------------------------------------------------------- +Tue Dec 5 18:30:30 CET 2006 - mkoenig@suse.de + +- move shared lib to /%_lib + +------------------------------------------------------------------- +Thu Aug 31 14:29:56 CEST 2006 - mkoenig@suse.de + +- update to version 1.2.3: + * Rewrote gcry_mpi_rshift to allow arbitrary shift counts. + * Minor bug fixes. +- added libgpg-error-devel and glibc-devel to Requires tag + of devel subpackage + +------------------------------------------------------------------- +Wed Jan 25 21:37:28 CET 2006 - mls@suse.de + +- converted neededforbuild to BuildRequires + +------------------------------------------------------------------- +Wed Nov 2 16:44:48 CET 2005 - hvogel@suse.de + +- enable noexecstack +- build ac.c with fno-strict-aliasing + +------------------------------------------------------------------- +Tue Oct 25 13:40:15 CEST 2005 - hvogel@suse.de + +- update to version 1.2.2 + +------------------------------------------------------------------- +Thu Jun 23 11:26:58 CEST 2005 - hvogel@suse.de + +- call install_info macro in post/postun of the devel package +- depend on libgcrypt +- add clean section + +------------------------------------------------------------------- +Tue Jan 18 11:51:51 CET 2005 - hvogel@suse.de + +- update to version 1.2.1 + +------------------------------------------------------------------- +Tue Jan 11 16:48:10 CET 2005 - schwab@suse.de + +- Fix info dir entry. + +------------------------------------------------------------------- +Wed Nov 17 11:22:44 CET 2004 - hvogel@suse.de + +- require libgpg-error-devel (Bug #48271) +- get rid of the NLD parts + +------------------------------------------------------------------- +Wed Jul 14 11:12:54 CEST 2004 - adrian@suse.de + +- create -devel subpackage +- prepare for nld + +------------------------------------------------------------------- +Wed May 19 14:57:45 CEST 2004 - hvogel@suse.de + +- update to version 1.2.0 + +------------------------------------------------------------------- +Mon Mar 22 16:48:53 CET 2004 - meissner@suse.de + +- disable make check, because it uses /dev/random whihc is + not filled on some server machines. + +------------------------------------------------------------------- +Wed Mar 17 15:01:51 CET 2004 - meissner@suse.de + +- fixed too over enthusiastic powerpc switches to make it work + on ppc64. (It compiled before, but did not work). +- enabled make check. + +------------------------------------------------------------------- +Wed Feb 18 12:14:36 CET 2004 - kukuk@suse.de + +- Build against system pthread library, not pth. + +------------------------------------------------------------------- +Tue Feb 17 21:11:40 CET 2004 - hvogel@suse.de + +- update to version 1.1.91 +- fix autoconf quotations + +------------------------------------------------------------------- +Sat Jan 10 19:20:41 CET 2004 - adrian@suse.de + +- add %run_ldconfig to %postun + +------------------------------------------------------------------- +Sun Jul 27 16:12:54 CEST 2003 - poeml@suse.de + +- add libgcrypt-1.1.12-sexp-valgrind-error.patch from SLEC + +------------------------------------------------------------------- +Thu Apr 24 12:20:23 CEST 2003 - ro@suse.de + +- fix install_info --delete call and move from preun to postun + +------------------------------------------------------------------- +Mon Feb 10 22:51:26 CET 2003 - mmj@suse.de + +- Use %install_info macro [#23433] + +------------------------------------------------------------------- +Mon Feb 10 16:11:55 CET 2003 - mc@suse.de + +- switch to version 1.1.12 +- gcry_pk_sign, gcry_pk_verify and gcry_pk_encrypt can now handle an + optional pkcs1 flags parameter in the S-expression. A similar flag + may be passed to gcry_pk_decrypt but it is only syntactically + implemented. +- New convenience macro gcry_md_get_asnoid. +- There is now some real stuff in the manual. +- New algorithm: MD4 +- Implemented ciphertext stealing. +- Support for plain old DES +- Smaller bugs fixes and a few new OIDs. + +------------------------------------------------------------------- +Tue Jan 14 14:03:27 CET 2003 - nadvornik@suse.cz + +- fixed multi-line string literals + +------------------------------------------------------------------- +Thu Aug 1 23:51:10 CEST 2002 - poeml@suse.de + +- create package + diff --git a/libgcrypt.keyring b/libgcrypt.keyring new file mode 100644 index 0000000..dd3bb0b --- /dev/null +++ b/libgcrypt.keyring @@ -0,0 +1,86 @@ +-----BEGIN PGP PUBLIC KEY BLOCK----- + +mQGNBFjLuq4BDACnM7zNSIaVMAacTwjXa5TGYe13i6ilHe4VL0NShzrgzjcQg531 +3cRgiiiNA7OSOypMqVs73Jez6ZUctn2GVsHBrS/io9NcuC9pVwf8a61WlcEa+EtB +a3G7HlBmEWnwaUdAtWKNuAi9Xn+Ir7H2xEdksmmd5a0/QnL+sX705boVPF/tpYtb +LGpPxa78tNrtxDkSwy8Wmi0IADYLI5yI7/yUGeJd8RSCU/fLRKC9fG7YOZRq0tsO +MhVNWmtUjbG6e73Lu8LKnCZgs1/fC8hvPyARieSV5mdN8s1oWd7oYctfgL4uBleD +ItAA8GhjKejutzHN8Ei/APw6AiiSyEjnPg+cTX8OgvLGJWjks0H6mPZeB1v/kGyZ +hBS9vm540h2/MmlVN2ntiCK5TZGeSWpqddiqusfVXotMRpN4HeLKoZh4RAncaCbZ +F/S+YLeN+kMXY4k3Fqt1fjTX6veFCbthI9pDdHzU9LfUVNp9D/5ktC/tYMORMegV ++wSMxi9G2YWKJkMAEQEAAYkBzgQfAQgAOBYhBFuAxXVCmPDLVdjtarzvfilLCS4o +BQJYy8DdFwyAAZSlyaA8L+XKOwldjh/fcjz0YraxAgcAAAoJELzvfilLCS4oNgoL +/0+K1xIx8JW7Lk5M6bYCvNA4fdlEcwQIT4UidJFM9m+suxYFWIGfebvHpRlEuJTg +dBjkEit8uLAoJXU0BRkKTLrzTF+qDUE79Wfx/R+0nOgJ7aMykQOi0AvuwzMYz4dg +xIVS2Daou4DF7bh/KF8+fqrmq8P8W1ZrkuFDanMWpHeAPx1uj2skYbo7uPqFdvlJ +hlNHrcxlcCkjf1InAt0Xt5lMvEsCRUPf9xAH4mNEhs0lh9c+200YPRmtnLWAzc1K +ckLIC8Q+mUR3DjZDqBlDBEPegXkrI0+MlvRA+9AnAm4YPqTMUfpZ6ZOAWeFjC/6Z +QYxG/AdWGkb4WFindzklQfybEuiekP8vU07ACQwSwH8PYe0UCom1YrlRUjX7QLkn +ZLWoeZg8BZy9GTM1Ut7Q1Q2uTw6mxxISuef+RFgYOHjWwLpFWZpqC88xERl7o/iz +iERJRt/593IctbjO9wenWt2peIAwzR4nz7LqM6ZFTdRAETmcdSvYRhg2Qt8hUE47 +CbQkQW5kcmUgSGVpbmVja2UgKFJlbGVhc2UgU2lnbmluZyBLZXkpiQHUBBMBCAA+ +FiEEW4DFdUKY8MtV2O1qvO9+KUsJLigFAljLuq4CGwMFCRLMAwAFCwkIBwIGFQgJ +CgsCBBYCAwECHgECF4AACgkQvO9+KUsJLihC/QwAhCC+SEvcFLcutgZ8HfcCtoZs +IoVzZEy7DjqIvGgnTssD8HCLnIAHCDvnP7dJW3uMuLCdSqym3cjlEIiQMsaGywkl +fzJISAwJrGQdWSKRd535jXpEXQlXDKal/IwMKAUt0PZtlCc9S3gwixQryxdJ28lJ +6h2T9fVDr8ZswMmTAFG91uctfhjKOMgPt8UhSPGW484WsIsQgkbOvf+Kfswl0eHu +ywX+pKAB5ZQ/9GVC6Ug4xfrdiJL0azJTPnvjMY5JYp6/L9RURs5hP5AnHR2j/PPo +sAtsFCjmbRbOMiASzklnUJPbSz5kfLloDWZmrUScjbzmsXehGyt433JGyRhZJl4x +/jPbzKhaaAHsGd+fRao6vlLOwFywDDVMp6JuyK7UeUb7I8ekTbSkGFA+l2Oa3O6/ +Y7PYhq7hwwAFuZckYI98IpHNCG1fS9W07FyKdvQbK1PbF1JFRKfsUCWYMKqDnbqE +o5jivPEHZImw6iYhhXcyEYl8fjcb9T6/S+wOP7aviQGzBBABCAAdFiEElKXJoDwv +5co7CV2OH99yPPRitrEFAljLv5sACgkQH99yPPRitrFw4gv/XFMFN+/LHsn9hJOP +4rCwl1yUuxXuYmZgc0sRoY3EpeQkJVyKurQuqqKoy2VuoMiF0O1kAQmGoFtVPUk7 +b8hCoutqB5GyeyKcoLP+WINgVhB2gXg7TSp3MPLBKkgqvSDvPitgRxBqFb4LW8LJ +bDbfwGrzIvXfDV3WvsrHVPbc2fhlWdL8d+3AE6mFiXF3eTpgmV3ApSBQV12MkkCk +icLIPmp+ZxZON+OP52ZXkRtfMgOy4Oa/41agrViDAZdMOGeGkhPertQheQZgXzmo +GF5Wz498HPM80Kv35X91l3iGzL+icEtO+tWea2YscsZ6qpRe2lfVPHk3B+anlmCj +m4kM4cBd39xa4HHSVh/bRHbZNtgVr7slQCKxlHgQOGVI5vCxPCwEsgJ2KBk03Nk/ +IA9EKO+czfh3/bHW6uMbEqrYDCnt+hmzZrpKDSGcwS/KOhvMUIMlb7/8vDKum6mp +/8xAtVZ6IAxYZNt3qg7Y7aLRtzCTyqm8rJQrZPtRaQcgLoEimDMEX0PliRYJKwYB +BAHaRw8BAQdAz75Hlekc16JhhfI0MKdEVxLdkxhcMCO0ZG6WMBAmNpe0H1dlcm5l +ciBLb2NoIChkaXN0IHNpZ25pbmcgMjAyMCmImgQTFgoAQhYhBG2qbmSnbShAVxtJ +AlKIl7gmQDraBQJfQ+w1AhsDBQkShccRBQsJCAcCAyICAQYVCgkICwIEFgIDAQIe +BwIXgAAKCRBSiJe4JkA62nmuAP9uL/HOdB0gvwWrH+FpURJLs4bnaZaPIk9ARrU0 +EXRgJgD/YCGfHQXpIPT0ZaXuwJexK04Z+qMFR/bM1q1Leo5CjgaIbQQQEQsAHRYh +BIBhWHD1utaQMzaG0PKthaweQrNnBQJfQ/HmAAoJEPKthaweQrNnIZkA3jG6LcZv +V/URn8Y8OJqsyYa4C3NI4nN+OhEvYhgA4PHzMnALeXIpA2gblvjFIPJPAhDBAU37 +c5PA6+6IdQQQFggAHRYhBK6oTtzwGthsRwHIXGMROuhmWH0KBQJfQ/IlAAoJEGMR +OuhmWH0K1+MA/0uJ5AHcnSfIBEWHNJwwVVLGyrxAWtS2U+zeymp/UvlPAQDErCLZ +l0dBiPG3vlowFx5TNep7tanBs6ZJn8F1ao1tAIkBMwQQAQgAHRYhBNhpISPEBl3q +Xg86tSSbOdJPJeO2BQJfQ/OuAAoJECSbOdJPJeO2DVoH/0o9if66ph6FJrgr+A/W +HNVeHxmM5tUQhpL1wpRS70SKcsJgolf5CxO5iTQf3HlZe544xGbIU/aCTJsWw9zi +UE8KmhAtKV4eL/7oQ7xx4nxPnABLpudtM8A44nsM1x/XiYrJnnDm29QjYEGd2Hi8 +7npc7VWKzLoj+I/WcXquynJi5O9TUxW9Bknd1pjpxFkf8v+msjBzCD5VKJgr0CR8 +wA6peQBWeGZX2HacosMIZH4TfL0r0TFla6LJIkNBz9DyIm1yL4L8oRH0950hQljP +C7TM3L7aRpX+4Kph6llFz6g7MALGFP95kyJ6o+XED9ORuuQVZMBMIkNC0tXOu10V +bdqIdQQQFgoAHRYhBMHTS2khnkruwLocIeP9/yGORbcrBQJfQ/P8AAoJEOP9/yGO +Rbcr3lQBAMas8Vl3Hdl3g2I283lz1uHiGvlwcnk2TLeB+U4zIwC9AQCy0nnazVNt +VQPID1ZCMoaOX7AzOjaqQDLf4j+dVTxgBJgzBGCkgocWCSsGAQQB2kcPAQEHQJmd +fwp8jEN5P3eEjhQiWk6zQi8utvgOvYD57XmE+H8+tCBOaWliZSBZdXRha2EgKEdu +dVBHIFJlbGVhc2UgS2V5KYiaBBMWCgBCFiEErI4RW/c+LY1H+pkI6Y6bLRnGyL0F +AmCkgocCGwMFCQsNBpkFCwkIBwIDIgIBBhUKCQgLAgQWAgMBAh4HAheAAAoJEOmO +my0Zxsi9/4IA/1rvSr3MU+Sv4jhNDzD+CeC3gmHkPew6pi9VHEsEwdgmAQD2BtiX +7w1sJL/CBylGWv5jxj4345mP9YfZm0RsgzPjDIh1BBAWCAAdFiEEJJyzdxdQdF1c +3TI84mewUjZPAo0FAmFAQ54ACgkQ4mewUjZPAo1CiAD+KTT1UVdQTGHMyvHwZocS +QjU8xhcZrTet+dvvjrE5+4MA/RBdJPZgFevUKu68NEy0Lo+RbkeCtmQJ/c8v5ieF +vW0AiQEzBBABCAAdFiEEEkEkvTtIYq96CkLxALRevUynur4FAmFAQ7cACgkQALRe +vUynur4kaAgAolPR8TNWVS0vXMKrr0k0l2M/8QkZTaLZx1GT9Nx1yb4WJKY7ElPM +YkhGDxetvFBETx0pH/6R3jtj6Crmur+NKHVSRY+rCYpFPDn6ciIOryssRx2G4kCZ +t+nFB9JyDbBOZAR8DK4pN1mAxG/yLDt4oKcUQsP2xlEFum+phxyR8KyYCpkwKRxY +eK+6lfilQuveoUwp/Xx5wXPNUy6q4eOOovCW7gS7I7288NGHCa2ul8sD6vA9C4mM +4Zxaole9P9wwJe1zZFtCIy88zHM9vqv+YM9DxMCaW24+rUztr7eD4bCRdG+QlSh+ +7R/TaqSxY1eAAd1J5tma9CNJO73pTKU+/JhTBGFpSqMTCSskAwMCCAEBBwIDBF6X +D9NmUQDgiyYNbhs1DMJ14mIw812wY1HVx/4QWYWiBunhrvSFxVbzsjD7/Wv+v3bm +MPrL+M2DLyFiSewNmcS0JEdudVBHLmNvbSAoUmVsZWFzZSBTaWduaW5nIEtleSAy +MDIxKYiaBBMTCABCFiEEAvON/3Mf+XywOaHaVJ5pXpBboggFAmFpSqMCGwMFCQ9x +14oFCwkIBwIDIgIBBhUKCQgLAgQWAgMBAh4HAheAAAoJEFSeaV6QW6IITkoA/RYa +jaTl1eEBU/Gdm12o3jrI55N5xZK2XTqSx25clVyjAP0XwMW/Og5+ND1ri3bAqADV +WlBDUswz8wYxsb0C4kYBkoh1BBAWCgAdFiEEbapuZKdtKEBXG0kCUoiXuCZAOtoF +AmFpTvEACgkQUoiXuCZAOtrJQAEAh7YyykjAy/Qs1yC3ji8iBfIVnPXvblrIx3SR +RyDwRC8BAKtZbEuKTtPlgkLUgMleTcZJ/vEhJE+GvfQ9o5gWCqEFiHUEEBYKAB0W +IQTB00tpIZ5K7sC6HCHj/f8hjkW3KwUCYWlPWgAKCRDj/f8hjkW3Kx4eAQDp6aGS +N/fU4xLl8RSvQUVjVA+aCTrMQR3hRwqw8liF2wEA3O3ECxz6e1+DoItYoJBBLKLw +eiInsGZ/+h5XYrpXTgA= +=4+Sn +-----END PGP PUBLIC KEY BLOCK----- diff --git a/libgcrypt.spec b/libgcrypt.spec new file mode 100644 index 0000000..ba1fab3 --- /dev/null +++ b/libgcrypt.spec @@ -0,0 +1,192 @@ +# +# spec file for package libgcrypt +# +# Copyright (c) 2024 SUSE LLC +# +# All modifications and additions to the file contributed by third parties +# remain the property of their copyright owners, unless otherwise agreed +# upon. The license for this file, and modifications and additions to the +# file, is the same license as for the pristine package itself (unless the +# license for the pristine package is not an Open Source License, in which +# case the license is the MIT License). An "Open Source License" is a +# license that conforms to the Open Source Definition (Version 1.9) +# published by the Open Source Initiative. + +# Please submit bugfixes or comments via https://bugs.opensuse.org/ +# + + +%define libsover 20 +%define libsoname %{name}%{libsover} +%define hmac_key orboDeJITITejsirpADONivirpUkvarP +Name: libgcrypt +Version: 1.11.0 +Release: 0 +Summary: The GNU Crypto Library +License: GPL-2.0-or-later AND LGPL-2.1-or-later AND GPL-3.0-or-later +Group: Development/Libraries/C and C++ +URL: https://gnupg.org/software/libgcrypt +Source: https://gnupg.org/ftp/gcrypt/libgcrypt/%{name}-%{version}.tar.bz2 +Source1: https://gnupg.org/ftp/gcrypt/libgcrypt/%{name}-%{version}.tar.bz2.sig +Source2: baselibs.conf +Source3: random.conf +Source4: hwf.deny +# https://www.gnupg.org/signature_key.html +Source5: https://gnupg.org/signature_key.asc#/%{name}.keyring +Source99: libgcrypt.changes +Patch1: libgcrypt-1.10.0-allow_FSM_same_state.patch +#PATCH-FIX-OPENSUSE Do not pull revision info from GIT when autoconf is run +Patch2: libgcrypt-nobetasuffix.patch +# FIPS patches: +#PATCH-FIX-SUSE bsc#1190700 FIPS: Provide a service-level indicator for PK +Patch100: libgcrypt-FIPS-SLI-pk.patch +#PATCH-FIX-SUSE bsc#1190700 FIPS: Check keylength in gcry_fips_indicator_kdf() +Patch101: libgcrypt-FIPS-SLI-kdf-leylength.patch +#PATCH-FIX-SUSE bsc#1190700 FIPS add indicators +Patch102: libgcrypt-FIPS-SLI-hash-mac.patch +#PATCH-FIX-SUSE bsc#1202117 FIPS: Get most of the entropy from rndjent_poll +Patch104: libgcrypt-FIPS-rndjent_poll.patch +#PATCH-FIX-SUSE bsc#1220896 FIPS: Replace the built-in jitter rng with standalone version +Patch105: libgcrypt-FIPS-jitter-standalone.patch +#PATCH-FIX-SUSE bsc#1220895 FIPS: Enforce the interpretation and use of jitter rng +Patch106: libgcrypt-FIPS-jitter-errorcodes.patch +#PATCH-FIX-SUSE bsc#1220893 FIPS: Use Jitter RNG for the whole length entropy buffer +Patch107: libgcrypt-FIPS-jitter-whole-entropy.patch +BuildRequires: automake >= 1.14 +BuildRequires: libgpg-error-devel >= 1.49 +BuildRequires: libtool +BuildRequires: makeinfo +BuildRequires: pkgconfig +%{?suse_build_hwcaps_libs} + +%description +Libgcrypt is a general purpose library of cryptographic building +blocks. It is originally based on code used by GnuPG. It does not +provide any implementation of OpenPGP or other protocols. Thorough +understanding of applied cryptography is required to use Libgcrypt. + +%package -n %{libsoname} +Summary: The GNU Crypto Library +License: GPL-2.0-or-later AND LGPL-2.1-or-later +Group: System/Libraries +BuildRequires: jitterentropy-devel >= 3.4.0 +Requires: libjitterentropy3 >= 3.4.0 +Provides: %{libsoname}-hmac = %{version}-%{release} +Obsoletes: %{libsoname}-hmac < %{version}-%{release} + +%description -n %{libsoname} +Libgcrypt is a general purpose crypto library based on the code used in +GnuPG (alpha version). + +%package devel +Summary: The GNU Crypto Library +License: GFDL-1.1-only AND GPL-2.0-or-later AND LGPL-2.1-or-later AND MIT +Group: Development/Libraries/C and C++ +Requires: %{libsoname} = %{version} +Requires: glibc-devel +Requires: jitterentropy-devel >= 3.4.0 +Requires: libgpg-error-devel >= 1.49 + +%description devel +Libgcrypt is a general purpose library of cryptographic building +blocks. It is originally based on code used by GnuPG. It does not +provide any implementation of OpenPGP or other protocols. Thorough +understanding of applied cryptography is required to use Libgcrypt. + +This package contains needed files to compile and link against the +library. + +%prep +%autosetup -p1 + +# Rename the internal .hmac file to include the so library version +sed -i "s/libgcrypt\.so\.hmac/\.libgcrypt\.so\.%{libsover}\.hmac/g" src/Makefile.am src/Makefile.in + +# Replace the built-in jitter rng with the standalone version [bsc#1220896] +find . -type f -name "jitterentropy*" -print -delete + +%build +export PUBKEYS="dsa elgamal rsa ecc" +export CIPHERS="arcfour blowfish cast5 des aes twofish serpent rfc2268 seed camellia idea salsa20 gost28147 chacha20 sm4 aria" +export DIGESTS="crc gostr3411-94 md4 md5 rmd160 sha1 sha256 sha512 sha3 tiger whirlpool stribog blake2 sm3" +export KDFS="s2k pkdf2 scrypt" + +autoreconf -fi +date=$(date -u '+%%Y-%%m-%%dT%%H:%%M+0000' -r %{SOURCE99}) +sed -e "s,BUILD_TIMESTAMP=.*,BUILD_TIMESTAMP=$date," -i configure +export CFLAGS="%{optflags} $(getconf LFS_CFLAGS)" +%configure \ + --with-fips-module-version="Libgcrypt version %{version}-%{release}" \ + --enable-hmac-binary-check="%{hmac_key}" \ + --enable-ciphers="$CIPHERS" \ + --enable-pubkey-ciphers="$PUBKEYS" \ + --enable-digests="$DIGESTS" \ + --enable-kdfs="$KDFS" \ + --enable-noexecstack \ + --disable-static \ +%ifarch %{sparc} + --disable-asm \ +%endif + --enable-random=getentropy \ + --enable-jent-support \ + %{nil} + +%make_build + +%check +make -k check +# run the regression tests also in FIPS mode +LIBGCRYPT_FORCE_FIPS_MODE=1 make -k check || true + +%install +%make_install + +# this is a hack that re-defines the __spec_install_post macro +# for a simple reason: the macro strips the binaries and thereby +# invalidates a HMAC that may have been created earlier. +# solution: create the hashes _after_ the macro runs. +%define libpath %{buildroot}%{_libdir}/libgcrypt.so.%{libsover}.?.? +%define __spec_install_post \ + %{?__debug_package:%{__debug_install_post}} \ + %{__arch_install_post} \ + %{__os_install_post} \ + cd src \ + sed -i -e 's|FILE=.*|FILE=\\\$1|' gen-note-integrity.sh \ + READELF=readelf AWK=awk ECHO_N="-n" bash gen-note-integrity.sh %{libpath} > %{libpath}.hmac \ + objcopy --update-section .note.fdo.integrity=%{libpath}.hmac %{libpath} %{libpath}.new \ + mv -f %{libpath}.new %{libpath} \ + rm -f %{libpath}.hmac \ +%{nil} + +rm %{buildroot}%{_libdir}/%{name}.la + +# Create /etc/gcrypt directory and install random.conf +mkdir -p -m 0755 %{buildroot}%{_sysconfdir}/gcrypt +install -m 644 %{SOURCE3} %{buildroot}%{_sysconfdir}/gcrypt/random.conf +install -m 644 %{SOURCE4} %{buildroot}%{_sysconfdir}/gcrypt/hwf.deny + +%post -n %{libsoname} -p /sbin/ldconfig +%postun -n %{libsoname} -p /sbin/ldconfig + +%files -n %{libsoname} +%license COPYING COPYING.LIB LICENSES +%doc AUTHORS ChangeLog NEWS README THANKS TODO +%{_libdir}/%{name}.so.* +%dir %{_sysconfdir}/gcrypt +%config(noreplace) %{_sysconfdir}/gcrypt/random.conf +%config(noreplace) %{_sysconfdir}/gcrypt/hwf.deny + +%files devel +%license COPYING COPYING.LIB LICENSES +%{_bindir}/dumpsexp +%{_bindir}/hmac256 +%{_bindir}/mpicalc +%{_bindir}/%{name}-config +%{_libdir}/%{name}.so +%{_libdir}/pkgconfig/libgcrypt.pc +%{_datadir}/aclocal/%{name}.m4 +%{_includedir}/gcrypt*.h +%{_infodir}/gcrypt.info*%{ext_info}* +%{_mandir}/man1/* + +%changelog diff --git a/random.conf b/random.conf new file mode 100644 index 0000000..378ba78 --- /dev/null +++ b/random.conf @@ -0,0 +1,9 @@ +# This file can be used to globally change parameters of +# the random generator. Supported options are: + +# Always use the non-blocking /dev/urandom or the respective +# system call instead of the blocking /dev/random. +# only-urandom + +# Disable the use of the jitter based entropy generator. +# disable-jent -- 2.51.1 From b52a99835f78f641458e94fa22e7b6fbfb8b9f3d87bfd80fb919c1c0fcb9bd6c Mon Sep 17 00:00:00 2001 From: Pedro Monreal Gonzalez Date: Wed, 8 Jan 2025 11:10:51 +0000 Subject: [PATCH 2/8] - Fix redefinition error of 'rol64'. Remove not used rol64() definition after removing the built-in jitter rng. * Add libgcrypt-rol64-redefinition.patch OBS-URL: https://build.opensuse.org/package/show/devel:libraries:c_c++/libgcrypt?expand=0&rev=184 --- .gitattributes | 23 + .gitignore | 1 + baselibs.conf | 8 + hwf.deny | 34 + libgcrypt-1.10.0-allow_FSM_same_state.patch | 15 + libgcrypt-1.10.3.tar.bz2 | 3 + libgcrypt-1.10.3.tar.bz2.sig | Bin 0 -> 238 bytes libgcrypt-1.11.0.tar.bz2 | 3 + libgcrypt-1.11.0.tar.bz2.sig | Bin 0 -> 119 bytes ...poly1305-Optimized-chacha20-poly1305.patch | 1993 +++++++++++++++++ libgcrypt-FIPS-SLI-hash-mac.patch | 172 ++ libgcrypt-FIPS-SLI-kdf-leylength.patch | 42 + libgcrypt-FIPS-SLI-pk.patch | 177 ++ libgcrypt-FIPS-jitter-errorcodes.patch | 16 + libgcrypt-FIPS-jitter-standalone.patch | 183 ++ libgcrypt-FIPS-jitter-whole-entropy.patch | 41 + libgcrypt-FIPS-rndjent_poll.patch | 114 + libgcrypt-jitterentropy-3.4.0.patch | 618 +++++ libgcrypt-no-deprecated-grep-alias.patch | 35 + libgcrypt-nobetasuffix.patch | 24 + ...e-P10-assembly-with-ENABLE_FORCE_SOF.patch | 76 + libgcrypt-rol64-redefinition.patch | 16 + libgcrypt.changes | 1864 +++++++++++++++ libgcrypt.keyring | 86 + libgcrypt.spec | 194 ++ random.conf | 9 + 26 files changed, 5747 insertions(+) create mode 100644 .gitattributes create mode 100644 .gitignore create mode 100644 baselibs.conf create mode 100644 hwf.deny create mode 100644 libgcrypt-1.10.0-allow_FSM_same_state.patch create mode 100644 libgcrypt-1.10.3.tar.bz2 create mode 100644 libgcrypt-1.10.3.tar.bz2.sig create mode 100644 libgcrypt-1.11.0.tar.bz2 create mode 100644 libgcrypt-1.11.0.tar.bz2.sig create mode 100644 libgcrypt-Chacha20-poly1305-Optimized-chacha20-poly1305.patch create mode 100644 libgcrypt-FIPS-SLI-hash-mac.patch create mode 100644 libgcrypt-FIPS-SLI-kdf-leylength.patch create mode 100644 libgcrypt-FIPS-SLI-pk.patch create mode 100644 libgcrypt-FIPS-jitter-errorcodes.patch create mode 100644 libgcrypt-FIPS-jitter-standalone.patch create mode 100644 libgcrypt-FIPS-jitter-whole-entropy.patch create mode 100644 libgcrypt-FIPS-rndjent_poll.patch create mode 100644 libgcrypt-jitterentropy-3.4.0.patch create mode 100644 libgcrypt-no-deprecated-grep-alias.patch create mode 100644 libgcrypt-nobetasuffix.patch create mode 100644 libgcrypt-ppc-enable-P10-assembly-with-ENABLE_FORCE_SOF.patch create mode 100644 libgcrypt-rol64-redefinition.patch create mode 100644 libgcrypt.changes create mode 100644 libgcrypt.keyring create mode 100644 libgcrypt.spec create mode 100644 random.conf diff --git a/.gitattributes b/.gitattributes new file mode 100644 index 0000000..9b03811 --- /dev/null +++ b/.gitattributes @@ -0,0 +1,23 @@ +## Default LFS +*.7z filter=lfs diff=lfs merge=lfs -text +*.bsp filter=lfs diff=lfs merge=lfs -text +*.bz2 filter=lfs diff=lfs merge=lfs -text +*.gem filter=lfs diff=lfs merge=lfs -text +*.gz filter=lfs diff=lfs merge=lfs -text +*.jar filter=lfs diff=lfs merge=lfs -text +*.lz filter=lfs diff=lfs merge=lfs -text +*.lzma filter=lfs diff=lfs merge=lfs -text +*.obscpio filter=lfs diff=lfs merge=lfs -text +*.oxt filter=lfs diff=lfs merge=lfs -text +*.pdf filter=lfs diff=lfs merge=lfs -text +*.png filter=lfs diff=lfs merge=lfs -text +*.rpm filter=lfs diff=lfs merge=lfs -text +*.tbz filter=lfs diff=lfs merge=lfs -text +*.tbz2 filter=lfs diff=lfs merge=lfs -text +*.tgz filter=lfs diff=lfs merge=lfs -text +*.ttf filter=lfs diff=lfs merge=lfs -text +*.txz filter=lfs diff=lfs merge=lfs -text +*.whl filter=lfs diff=lfs merge=lfs -text +*.xz filter=lfs diff=lfs merge=lfs -text +*.zip filter=lfs diff=lfs merge=lfs -text +*.zst filter=lfs diff=lfs merge=lfs -text diff --git a/.gitignore b/.gitignore new file mode 100644 index 0000000..57affb6 --- /dev/null +++ b/.gitignore @@ -0,0 +1 @@ +.osc diff --git a/baselibs.conf b/baselibs.conf new file mode 100644 index 0000000..a018a0a --- /dev/null +++ b/baselibs.conf @@ -0,0 +1,8 @@ +libgcrypt20 + provides "libgcrypt- = " + obsoletes "libgcrypt- <= " + provides "libgcrypt20-hmac- = -%release" + obsoletes "libgcrypt20-hmac- < -%release" +libgcrypt-devel + requires -libgcrypt- + requires "libgcrypt20- = " diff --git a/hwf.deny b/hwf.deny new file mode 100644 index 0000000..2236468 --- /dev/null +++ b/hwf.deny @@ -0,0 +1,34 @@ +# This file can be used to globally disable the use of hardware +# based optimizations. Supported options are: +# padlock-rng +# padlock-aes +# padlock-sha +# padlock-mmul +# intel-cpu +# intel-fast-shld +# intel-bmi2 +# intel-ssse3 +# intel-sse4.1 +# intel-pclmul +# intel-aesni +# intel-rdrand +# intel-avx +# intel-avx2 +# intel-fast-vpgather +# intel-rdtsc +# intel-shaext +# intel-vaes-vpclmul +# arm-neon +# arm-aes +# arm-sha1 +# arm-sha2 +# arm-pmull +# ppc-vcrypto +# ppc-arch_3_00 +# ppc-arch_2_07 +# ppc-arch_3_10 +# s390x-msa +# s390x-msa-4 +# s390x-msa-8 +# s390x-msa-9 +# s390x-vx diff --git a/libgcrypt-1.10.0-allow_FSM_same_state.patch b/libgcrypt-1.10.0-allow_FSM_same_state.patch new file mode 100644 index 0000000..843cfea --- /dev/null +++ b/libgcrypt-1.10.0-allow_FSM_same_state.patch @@ -0,0 +1,15 @@ +Index: libgcrypt-1.10.0/src/fips.c +=================================================================== +--- libgcrypt-1.10.0.orig/src/fips.c ++++ libgcrypt-1.10.0/src/fips.c +@@ -890,6 +890,10 @@ fips_new_state (enum module_states new_s + + } + ++ /* Allow a transition to the current state */ ++ if (current_state == new_state) ++ ok = 1; ++ + if (ok) + { + current_state = new_state; diff --git a/libgcrypt-1.10.3.tar.bz2 b/libgcrypt-1.10.3.tar.bz2 new file mode 100644 index 0000000..653803f --- /dev/null +++ b/libgcrypt-1.10.3.tar.bz2 @@ -0,0 +1,3 @@ +version https://git-lfs.github.com/spec/v1 +oid sha256:8b0870897ac5ac67ded568dcfadf45969cfa8a6beb0fd60af2a9eadc2a3272aa +size 3783827 diff --git a/libgcrypt-1.10.3.tar.bz2.sig b/libgcrypt-1.10.3.tar.bz2.sig new file mode 100644 index 0000000000000000000000000000000000000000000000000000000000000000..4172518bc29eafb0304aa2c7def555b970a6accea442a7542087b98c44485773 GIT binary patch literal 238 zcmeAuWnmEGV2~A4WXWBXm$E!p!y#PSlPRcU`VKV*t6Qv0sliEW8MrtFU?N}p82-vF z=ITAZ*qv<_(;dOxrp<8yN$DSFdR>!gz3<7nXwGD1Muyiq%7Ht6>~>#&|Ibh5V-ok6 zm#e%* literal 0 HcmV?d00001 diff --git a/libgcrypt-1.11.0.tar.bz2 b/libgcrypt-1.11.0.tar.bz2 new file mode 100644 index 0000000..28d1068 --- /dev/null +++ b/libgcrypt-1.11.0.tar.bz2 @@ -0,0 +1,3 @@ +version https://git-lfs.github.com/spec/v1 +oid sha256:09120c9867ce7f2081d6aaa1775386b98c2f2f246135761aae47d81f58685b9c +size 4180345 diff --git a/libgcrypt-1.11.0.tar.bz2.sig b/libgcrypt-1.11.0.tar.bz2.sig new file mode 100644 index 0000000000000000000000000000000000000000000000000000000000000000..2debe948a9ffbbc9c835efae5cce0c65517df124ea67ba4cc04d1dffdd7b3160 GIT binary patch literal 119 zcmeAuWnmEGV2~A4WXWBXm$E!p!y#PSlPRcU`VKV*t6Qv0X+=xZ7`QkEU?T178UE=O z)|M}6Y-XM7H2JWvsFP0?XX&fr%U>#e4G(K{b;T<%GJNLLSKO|_Z@vBphsk!en!WkH T(k44uvO>;;f4NZp`vWfkiCryG literal 0 HcmV?d00001 diff --git a/libgcrypt-Chacha20-poly1305-Optimized-chacha20-poly1305.patch b/libgcrypt-Chacha20-poly1305-Optimized-chacha20-poly1305.patch new file mode 100644 index 0000000..5877fee --- /dev/null +++ b/libgcrypt-Chacha20-poly1305-Optimized-chacha20-poly1305.patch @@ -0,0 +1,1993 @@ +commit 88fe7ac33eb4cb4dff76a5cc7fca50da5fb0ee3a +Author: Danny Tsen +Date: Sun Jun 12 21:30:19 2022 +0300 + + Chacha20 poly1305 Optimized chacha20 poly1305 for P10 operation + + * configure.ac: Added chacha20 and poly1305 assembly implementations. + * cipher/chacha20-p10le-8x.s: (New) - support 8 blocks (512 bytes) + unrolling. + * cipher/poly1305-p10le.s: (New) - support 4 blocks (128 bytes) + unrolling. + * cipher/Makefile.am: Added new chacha20 and poly1305 files. + * cipher/chacha20.c: Added PPC p10 le support for 8x chacha20. + * cipher/poly1305.c: Added PPC p10 le support for 4x poly1305. + * cipher/poly1305-internal.h: Added PPC p10 le support for poly1305. + --- + + GnuPG-bug-id: 6006 + Signed-off-by: Danny Tsen + [jk: cosmetic changes to C code] + [jk: fix building on ppc64be] + Signed-off-by: Jussi Kivilinna + +Index: libgcrypt-1.10.2/cipher/Makefile.am +=================================================================== +--- libgcrypt-1.10.2.orig/cipher/Makefile.am ++++ libgcrypt-1.10.2/cipher/Makefile.am +@@ -83,6 +83,7 @@ EXTRA_libcipher_la_SOURCES = \ + chacha20.c chacha20-amd64-ssse3.S chacha20-amd64-avx2.S \ + chacha20-armv7-neon.S chacha20-aarch64.S \ + chacha20-ppc.c chacha20-s390x.S \ ++ chacha20-p10le-8x.s \ + cipher-gcm-ppc.c cipher-gcm-intel-pclmul.c cipher-gcm-armv7-neon.S \ + cipher-gcm-armv8-aarch32-ce.S cipher-gcm-armv8-aarch64-ce.S \ + crc.c crc-intel-pclmul.c crc-armv8-ce.c \ +@@ -99,6 +100,7 @@ EXTRA_libcipher_la_SOURCES = \ + md4.c \ + md5.c \ + poly1305-s390x.S \ ++ poly1305-p10le.s \ + rijndael.c rijndael-internal.h rijndael-tables.h \ + rijndael-aesni.c rijndael-padlock.c \ + rijndael-amd64.S rijndael-arm.S \ +Index: libgcrypt-1.10.2/cipher/chacha20-p10le-8x.s +=================================================================== +--- /dev/null ++++ libgcrypt-1.10.2/cipher/chacha20-p10le-8x.s +@@ -0,0 +1,864 @@ ++# Copyright 2021- IBM Inc. All rights reserved ++# ++# This file is part of Libgcrypt. ++# ++# Libgcrypt is free software; you can redistribute it and/or modify ++# it under the terms of the GNU Lesser General Public License as ++# published by the Free Software Foundation; either version 2.1 of ++# the License, or (at your option) any later version. ++# ++# Libgcrypt 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 Lesser General Public License for more details. ++# ++# You should have received a copy of the GNU Lesser General Public ++# License along with this program; if not, see . ++# ++#=================================================================================== ++# Written by Danny Tsen ++# ++# This function handles multiple 64-byte block data length ++# and the length should be more than 512 bytes. ++# ++# unsigned int _gcry_chacha20_p10le_8x(u32 *state, byte *dst, const byte *src, size_t len); ++# ++# r1 - top of the stack ++# r3 to r10 input parameters ++# r3 - out ++# r4 - inp ++# r5 - len ++# r6 - key[8] ++# r7 - counter[4] ++# ++# do rounds, 8 quarter rounds ++# 1. a += b; d ^= a; d <<<= 16; ++# 2. c += d; b ^= c; b <<<= 12; ++# 3. a += b; d ^= a; d <<<= 8; ++# 4. c += d; b ^= c; b <<<= 7 ++# ++# row1 = (row1 + row2), row4 = row1 xor row4, row4 rotate each word by 16 ++# row3 = (row3 + row4), row2 = row3 xor row2, row2 rotate each word by 12 ++# row1 = (row1 + row2), row4 = row1 xor row4, row4 rotate each word by 8 ++# row3 = (row3 + row4), row2 = row3 xor row2, row2 rotate each word by 7 ++# ++# 4 blocks (a b c d) ++# ++# a0 b0 c0 d0 ++# a1 b1 c1 d1 ++# ... ++# a4 b4 c4 d4 ++# ... ++# a8 b8 c8 d8 ++# ... ++# a12 b12 c12 d12 ++# a13 ... ++# a14 ... ++# a15 b15 c15 d15 ++# ++# Column round (v0, v4, v8, v12, v1, v5, v9, v13, v2, v6, v10, v14, v3, v7, v11, v15) ++# Diagnal round (v0, v5, v10, v15, v1, v6, v11, v12, v2, v7, v8, v13, v3, v4, v9, v14) ++# ++.text ++ ++.macro QT_loop_8x ++ # QR(v0, v4, v8, v12, v1, v5, v9, v13, v2, v6, v10, v14, v3, v7, v11, v15) ++ xxlor 0, 32+25, 32+25 ++ xxlor 32+25, 20, 20 ++ vadduwm 0, 0, 4 ++ vadduwm 1, 1, 5 ++ vadduwm 2, 2, 6 ++ vadduwm 3, 3, 7 ++ vadduwm 16, 16, 20 ++ vadduwm 17, 17, 21 ++ vadduwm 18, 18, 22 ++ vadduwm 19, 19, 23 ++ ++ vpermxor 12, 12, 0, 25 ++ vpermxor 13, 13, 1, 25 ++ vpermxor 14, 14, 2, 25 ++ vpermxor 15, 15, 3, 25 ++ vpermxor 28, 28, 16, 25 ++ vpermxor 29, 29, 17, 25 ++ vpermxor 30, 30, 18, 25 ++ vpermxor 31, 31, 19, 25 ++ xxlor 32+25, 0, 0 ++ vadduwm 8, 8, 12 ++ vadduwm 9, 9, 13 ++ vadduwm 10, 10, 14 ++ vadduwm 11, 11, 15 ++ vadduwm 24, 24, 28 ++ vadduwm 25, 25, 29 ++ vadduwm 26, 26, 30 ++ vadduwm 27, 27, 31 ++ vxor 4, 4, 8 ++ vxor 5, 5, 9 ++ vxor 6, 6, 10 ++ vxor 7, 7, 11 ++ vxor 20, 20, 24 ++ vxor 21, 21, 25 ++ vxor 22, 22, 26 ++ vxor 23, 23, 27 ++ ++ xxlor 0, 32+25, 32+25 ++ xxlor 32+25, 21, 21 ++ vrlw 4, 4, 25 # ++ vrlw 5, 5, 25 ++ vrlw 6, 6, 25 ++ vrlw 7, 7, 25 ++ vrlw 20, 20, 25 # ++ vrlw 21, 21, 25 ++ vrlw 22, 22, 25 ++ vrlw 23, 23, 25 ++ xxlor 32+25, 0, 0 ++ vadduwm 0, 0, 4 ++ vadduwm 1, 1, 5 ++ vadduwm 2, 2, 6 ++ vadduwm 3, 3, 7 ++ vadduwm 16, 16, 20 ++ vadduwm 17, 17, 21 ++ vadduwm 18, 18, 22 ++ vadduwm 19, 19, 23 ++ ++ xxlor 0, 32+25, 32+25 ++ xxlor 32+25, 22, 22 ++ vpermxor 12, 12, 0, 25 ++ vpermxor 13, 13, 1, 25 ++ vpermxor 14, 14, 2, 25 ++ vpermxor 15, 15, 3, 25 ++ vpermxor 28, 28, 16, 25 ++ vpermxor 29, 29, 17, 25 ++ vpermxor 30, 30, 18, 25 ++ vpermxor 31, 31, 19, 25 ++ xxlor 32+25, 0, 0 ++ vadduwm 8, 8, 12 ++ vadduwm 9, 9, 13 ++ vadduwm 10, 10, 14 ++ vadduwm 11, 11, 15 ++ vadduwm 24, 24, 28 ++ vadduwm 25, 25, 29 ++ vadduwm 26, 26, 30 ++ vadduwm 27, 27, 31 ++ xxlor 0, 32+28, 32+28 ++ xxlor 32+28, 23, 23 ++ vxor 4, 4, 8 ++ vxor 5, 5, 9 ++ vxor 6, 6, 10 ++ vxor 7, 7, 11 ++ vxor 20, 20, 24 ++ vxor 21, 21, 25 ++ vxor 22, 22, 26 ++ vxor 23, 23, 27 ++ vrlw 4, 4, 28 # ++ vrlw 5, 5, 28 ++ vrlw 6, 6, 28 ++ vrlw 7, 7, 28 ++ vrlw 20, 20, 28 # ++ vrlw 21, 21, 28 ++ vrlw 22, 22, 28 ++ vrlw 23, 23, 28 ++ xxlor 32+28, 0, 0 ++ ++ # QR(v0, v5, v10, v15, v1, v6, v11, v12, v2, v7, v8, v13, v3, v4, v9, v14) ++ xxlor 0, 32+25, 32+25 ++ xxlor 32+25, 20, 20 ++ vadduwm 0, 0, 5 ++ vadduwm 1, 1, 6 ++ vadduwm 2, 2, 7 ++ vadduwm 3, 3, 4 ++ vadduwm 16, 16, 21 ++ vadduwm 17, 17, 22 ++ vadduwm 18, 18, 23 ++ vadduwm 19, 19, 20 ++ ++ vpermxor 15, 15, 0, 25 ++ vpermxor 12, 12, 1, 25 ++ vpermxor 13, 13, 2, 25 ++ vpermxor 14, 14, 3, 25 ++ vpermxor 31, 31, 16, 25 ++ vpermxor 28, 28, 17, 25 ++ vpermxor 29, 29, 18, 25 ++ vpermxor 30, 30, 19, 25 ++ ++ xxlor 32+25, 0, 0 ++ vadduwm 10, 10, 15 ++ vadduwm 11, 11, 12 ++ vadduwm 8, 8, 13 ++ vadduwm 9, 9, 14 ++ vadduwm 26, 26, 31 ++ vadduwm 27, 27, 28 ++ vadduwm 24, 24, 29 ++ vadduwm 25, 25, 30 ++ vxor 5, 5, 10 ++ vxor 6, 6, 11 ++ vxor 7, 7, 8 ++ vxor 4, 4, 9 ++ vxor 21, 21, 26 ++ vxor 22, 22, 27 ++ vxor 23, 23, 24 ++ vxor 20, 20, 25 ++ ++ xxlor 0, 32+25, 32+25 ++ xxlor 32+25, 21, 21 ++ vrlw 5, 5, 25 ++ vrlw 6, 6, 25 ++ vrlw 7, 7, 25 ++ vrlw 4, 4, 25 ++ vrlw 21, 21, 25 ++ vrlw 22, 22, 25 ++ vrlw 23, 23, 25 ++ vrlw 20, 20, 25 ++ xxlor 32+25, 0, 0 ++ ++ vadduwm 0, 0, 5 ++ vadduwm 1, 1, 6 ++ vadduwm 2, 2, 7 ++ vadduwm 3, 3, 4 ++ vadduwm 16, 16, 21 ++ vadduwm 17, 17, 22 ++ vadduwm 18, 18, 23 ++ vadduwm 19, 19, 20 ++ ++ xxlor 0, 32+25, 32+25 ++ xxlor 32+25, 22, 22 ++ vpermxor 15, 15, 0, 25 ++ vpermxor 12, 12, 1, 25 ++ vpermxor 13, 13, 2, 25 ++ vpermxor 14, 14, 3, 25 ++ vpermxor 31, 31, 16, 25 ++ vpermxor 28, 28, 17, 25 ++ vpermxor 29, 29, 18, 25 ++ vpermxor 30, 30, 19, 25 ++ xxlor 32+25, 0, 0 ++ ++ vadduwm 10, 10, 15 ++ vadduwm 11, 11, 12 ++ vadduwm 8, 8, 13 ++ vadduwm 9, 9, 14 ++ vadduwm 26, 26, 31 ++ vadduwm 27, 27, 28 ++ vadduwm 24, 24, 29 ++ vadduwm 25, 25, 30 ++ ++ xxlor 0, 32+28, 32+28 ++ xxlor 32+28, 23, 23 ++ vxor 5, 5, 10 ++ vxor 6, 6, 11 ++ vxor 7, 7, 8 ++ vxor 4, 4, 9 ++ vxor 21, 21, 26 ++ vxor 22, 22, 27 ++ vxor 23, 23, 24 ++ vxor 20, 20, 25 ++ vrlw 5, 5, 28 ++ vrlw 6, 6, 28 ++ vrlw 7, 7, 28 ++ vrlw 4, 4, 28 ++ vrlw 21, 21, 28 ++ vrlw 22, 22, 28 ++ vrlw 23, 23, 28 ++ vrlw 20, 20, 28 ++ xxlor 32+28, 0, 0 ++.endm ++ ++.macro QT_loop_4x ++ # QR(v0, v4, v8, v12, v1, v5, v9, v13, v2, v6, v10, v14, v3, v7, v11, v15) ++ vadduwm 0, 0, 4 ++ vadduwm 1, 1, 5 ++ vadduwm 2, 2, 6 ++ vadduwm 3, 3, 7 ++ vpermxor 12, 12, 0, 20 ++ vpermxor 13, 13, 1, 20 ++ vpermxor 14, 14, 2, 20 ++ vpermxor 15, 15, 3, 20 ++ vadduwm 8, 8, 12 ++ vadduwm 9, 9, 13 ++ vadduwm 10, 10, 14 ++ vadduwm 11, 11, 15 ++ vxor 4, 4, 8 ++ vxor 5, 5, 9 ++ vxor 6, 6, 10 ++ vxor 7, 7, 11 ++ vrlw 4, 4, 21 ++ vrlw 5, 5, 21 ++ vrlw 6, 6, 21 ++ vrlw 7, 7, 21 ++ vadduwm 0, 0, 4 ++ vadduwm 1, 1, 5 ++ vadduwm 2, 2, 6 ++ vadduwm 3, 3, 7 ++ vpermxor 12, 12, 0, 22 ++ vpermxor 13, 13, 1, 22 ++ vpermxor 14, 14, 2, 22 ++ vpermxor 15, 15, 3, 22 ++ vadduwm 8, 8, 12 ++ vadduwm 9, 9, 13 ++ vadduwm 10, 10, 14 ++ vadduwm 11, 11, 15 ++ vxor 4, 4, 8 ++ vxor 5, 5, 9 ++ vxor 6, 6, 10 ++ vxor 7, 7, 11 ++ vrlw 4, 4, 23 ++ vrlw 5, 5, 23 ++ vrlw 6, 6, 23 ++ vrlw 7, 7, 23 ++ ++ # QR(v0, v5, v10, v15, v1, v6, v11, v12, v2, v7, v8, v13, v3, v4, v9, v14) ++ vadduwm 0, 0, 5 ++ vadduwm 1, 1, 6 ++ vadduwm 2, 2, 7 ++ vadduwm 3, 3, 4 ++ vpermxor 15, 15, 0, 20 ++ vpermxor 12, 12, 1, 20 ++ vpermxor 13, 13, 2, 20 ++ vpermxor 14, 14, 3, 20 ++ vadduwm 10, 10, 15 ++ vadduwm 11, 11, 12 ++ vadduwm 8, 8, 13 ++ vadduwm 9, 9, 14 ++ vxor 5, 5, 10 ++ vxor 6, 6, 11 ++ vxor 7, 7, 8 ++ vxor 4, 4, 9 ++ vrlw 5, 5, 21 ++ vrlw 6, 6, 21 ++ vrlw 7, 7, 21 ++ vrlw 4, 4, 21 ++ vadduwm 0, 0, 5 ++ vadduwm 1, 1, 6 ++ vadduwm 2, 2, 7 ++ vadduwm 3, 3, 4 ++ vpermxor 15, 15, 0, 22 ++ vpermxor 12, 12, 1, 22 ++ vpermxor 13, 13, 2, 22 ++ vpermxor 14, 14, 3, 22 ++ vadduwm 10, 10, 15 ++ vadduwm 11, 11, 12 ++ vadduwm 8, 8, 13 ++ vadduwm 9, 9, 14 ++ vxor 5, 5, 10 ++ vxor 6, 6, 11 ++ vxor 7, 7, 8 ++ vxor 4, 4, 9 ++ vrlw 5, 5, 23 ++ vrlw 6, 6, 23 ++ vrlw 7, 7, 23 ++ vrlw 4, 4, 23 ++.endm ++ ++# Transpose ++.macro TP_4x a0 a1 a2 a3 ++ xxmrghw 10, 32+\a0, 32+\a1 # a0, a1, b0, b1 ++ xxmrghw 11, 32+\a2, 32+\a3 # a2, a3, b2, b3 ++ xxmrglw 12, 32+\a0, 32+\a1 # c0, c1, d0, d1 ++ xxmrglw 13, 32+\a2, 32+\a3 # c2, c3, d2, d3 ++ xxpermdi 32+\a0, 10, 11, 0 # a0, a1, a2, a3 ++ xxpermdi 32+\a1, 10, 11, 3 # b0, b1, b2, b3 ++ xxpermdi 32+\a2, 12, 13, 0 # c0, c1, c2, c3 ++ xxpermdi 32+\a3, 12, 13, 3 # d0, d1, d2, d3 ++.endm ++ ++# key stream = working state + state ++.macro Add_state S ++ vadduwm \S+0, \S+0, 16-\S ++ vadduwm \S+4, \S+4, 17-\S ++ vadduwm \S+8, \S+8, 18-\S ++ vadduwm \S+12, \S+12, 19-\S ++ ++ vadduwm \S+1, \S+1, 16-\S ++ vadduwm \S+5, \S+5, 17-\S ++ vadduwm \S+9, \S+9, 18-\S ++ vadduwm \S+13, \S+13, 19-\S ++ ++ vadduwm \S+2, \S+2, 16-\S ++ vadduwm \S+6, \S+6, 17-\S ++ vadduwm \S+10, \S+10, 18-\S ++ vadduwm \S+14, \S+14, 19-\S ++ ++ vadduwm \S+3, \S+3, 16-\S ++ vadduwm \S+7, \S+7, 17-\S ++ vadduwm \S+11, \S+11, 18-\S ++ vadduwm \S+15, \S+15, 19-\S ++.endm ++ ++# ++# write 256 bytes ++# ++.macro Write_256 S ++ add 9, 14, 5 ++ add 16, 14, 4 ++ lxvw4x 0, 0, 9 ++ lxvw4x 1, 17, 9 ++ lxvw4x 2, 18, 9 ++ lxvw4x 3, 19, 9 ++ lxvw4x 4, 20, 9 ++ lxvw4x 5, 21, 9 ++ lxvw4x 6, 22, 9 ++ lxvw4x 7, 23, 9 ++ lxvw4x 8, 24, 9 ++ lxvw4x 9, 25, 9 ++ lxvw4x 10, 26, 9 ++ lxvw4x 11, 27, 9 ++ lxvw4x 12, 28, 9 ++ lxvw4x 13, 29, 9 ++ lxvw4x 14, 30, 9 ++ lxvw4x 15, 31, 9 ++ ++ xxlxor \S+32, \S+32, 0 ++ xxlxor \S+36, \S+36, 1 ++ xxlxor \S+40, \S+40, 2 ++ xxlxor \S+44, \S+44, 3 ++ xxlxor \S+33, \S+33, 4 ++ xxlxor \S+37, \S+37, 5 ++ xxlxor \S+41, \S+41, 6 ++ xxlxor \S+45, \S+45, 7 ++ xxlxor \S+34, \S+34, 8 ++ xxlxor \S+38, \S+38, 9 ++ xxlxor \S+42, \S+42, 10 ++ xxlxor \S+46, \S+46, 11 ++ xxlxor \S+35, \S+35, 12 ++ xxlxor \S+39, \S+39, 13 ++ xxlxor \S+43, \S+43, 14 ++ xxlxor \S+47, \S+47, 15 ++ ++ stxvw4x \S+32, 0, 16 ++ stxvw4x \S+36, 17, 16 ++ stxvw4x \S+40, 18, 16 ++ stxvw4x \S+44, 19, 16 ++ ++ stxvw4x \S+33, 20, 16 ++ stxvw4x \S+37, 21, 16 ++ stxvw4x \S+41, 22, 16 ++ stxvw4x \S+45, 23, 16 ++ ++ stxvw4x \S+34, 24, 16 ++ stxvw4x \S+38, 25, 16 ++ stxvw4x \S+42, 26, 16 ++ stxvw4x \S+46, 27, 16 ++ ++ stxvw4x \S+35, 28, 16 ++ stxvw4x \S+39, 29, 16 ++ stxvw4x \S+43, 30, 16 ++ stxvw4x \S+47, 31, 16 ++ ++.endm ++ ++# ++# unsigned int _gcry_chacha20_p10le_8x(u32 *state, byte *dst, const byte *src, size_t len); ++# ++.global _gcry_chacha20_p10le_8x ++.align 5 ++_gcry_chacha20_p10le_8x: ++ cmpdi 6, 512 ++ blt Out_no_chacha ++ ++ stdu 1,-1024(1) ++ mflr 0 ++ ++ std 14,112(1) ++ std 15,120(1) ++ std 16,128(1) ++ std 17,136(1) ++ std 18,144(1) ++ std 19,152(1) ++ std 20,160(1) ++ std 21,168(1) ++ std 22,176(1) ++ std 23,184(1) ++ std 24,192(1) ++ std 25,200(1) ++ std 26,208(1) ++ std 27,216(1) ++ std 28,224(1) ++ std 29,232(1) ++ std 30,240(1) ++ std 31,248(1) ++ std 0, 1040(1) ++ ++ li 17, 16 ++ li 18, 32 ++ li 19, 48 ++ li 20, 64 ++ li 21, 80 ++ li 22, 96 ++ li 23, 112 ++ li 24, 128 ++ li 25, 144 ++ li 26, 160 ++ li 27, 176 ++ li 28, 192 ++ li 29, 208 ++ li 30, 224 ++ li 31, 240 ++ addi 9, 1, 256 ++ stvx 20, 0, 9 ++ stvx 21, 17, 9 ++ stvx 22, 18, 9 ++ stvx 23, 19, 9 ++ stvx 24, 20, 9 ++ stvx 25, 21, 9 ++ stvx 26, 22, 9 ++ stvx 27, 23, 9 ++ stvx 28, 24, 9 ++ stvx 29, 25, 9 ++ stvx 30, 26, 9 ++ stvx 31, 27, 9 ++ ++ add 9, 9, 27 ++ addi 14, 17, 16 ++ stxvx 14, 14, 9 ++ addi 14, 14, 16 ++ stxvx 15, 14, 9 ++ addi 14, 14, 16 ++ stxvx 16, 14, 9 ++ addi 14, 14, 16 ++ stxvx 17, 14, 9 ++ addi 14, 14, 16 ++ stxvx 18, 14, 9 ++ addi 14, 14, 16 ++ stxvx 19, 14, 9 ++ addi 14, 14, 16 ++ stxvx 20, 14, 9 ++ addi 14, 14, 16 ++ stxvx 21, 14, 9 ++ addi 14, 14, 16 ++ stxvx 22, 14, 9 ++ addi 14, 14, 16 ++ stxvx 23, 14, 9 ++ addi 14, 14, 16 ++ stxvx 24, 14, 9 ++ addi 14, 14, 16 ++ stxvx 25, 14, 9 ++ addi 14, 14, 16 ++ stxvx 26, 14, 9 ++ addi 14, 14, 16 ++ stxvx 27, 14, 9 ++ addi 14, 14, 16 ++ stxvx 28, 14, 9 ++ addi 14, 14, 16 ++ stxvx 29, 14, 9 ++ addi 14, 14, 16 ++ stxvx 30, 14, 9 ++ addi 14, 14, 16 ++ stxvx 31, 14, 9 ++ ++ mr 15, 6 # len ++ li 14, 0 # offset to inp and outp ++ ++ ld 10, sigma@got(2) ++ ++ lxvw4x 48, 0, 3 # vr16, constants ++ lxvw4x 49, 17, 3 # vr17, key 1 ++ lxvw4x 50, 18, 3 # vr18, key 2 ++ lxvw4x 51, 19, 3 # vr19, counter, nonce ++ ++ lxvw4x 62, 19, 10 # vr30, 4 ++ ++ vspltisw 21, 12 ++ vspltisw 23, 7 ++ ++ ld 11, permx@got(2) ++ lxvw4x 32+20, 0, 11 ++ lxvw4x 32+22, 17, 11 ++ ++ li 8, 10 ++ mtctr 8 ++ ++ xxlor 16, 48, 48 ++ xxlor 17, 49, 49 ++ xxlor 18, 50, 50 ++ xxlor 19, 51, 51 ++ ++ vspltisw 25, 4 ++ vspltisw 26, 8 ++ ++ xxlor 16, 48, 48 ++ xxlor 17, 49, 49 ++ xxlor 18, 50, 50 ++ xxlor 19, 51, 51 ++ ++ xxlor 25, 32+26, 32+26 ++ xxlor 24, 32+25, 32+25 ++ ++ vadduwm 31, 30, 25 # (0, 1, 2, 3) + (4, 4, 4, 4) ++ xxlor 30, 32+30, 32+30 ++ xxlor 31, 32+31, 32+31 ++ ++ xxlor 20, 32+20, 32+20 ++ xxlor 21, 32+21, 32+21 ++ xxlor 22, 32+22, 32+22 ++ xxlor 23, 32+23, 32+23 ++ ++Loop_8x: ++ lvx 0, 20, 10 ++ lvx 1, 21, 10 ++ lvx 2, 22, 10 ++ lvx 3, 23, 10 ++ xxspltw 32+4, 17, 0 ++ xxspltw 32+5, 17, 1 ++ xxspltw 32+6, 17, 2 ++ xxspltw 32+7, 17, 3 ++ xxspltw 32+8, 18, 0 ++ xxspltw 32+9, 18, 1 ++ xxspltw 32+10, 18, 2 ++ xxspltw 32+11, 18, 3 ++ xxspltw 32+12, 19, 0 ++ xxspltw 32+13, 19, 1 ++ xxspltw 32+14, 19, 2 ++ xxspltw 32+15, 19, 3 ++ vadduwm 12, 12, 30 # increase counter ++ ++ lvx 16, 20, 10 ++ lvx 17, 21, 10 ++ lvx 18, 22, 10 ++ lvx 19, 23, 10 ++ xxspltw 32+20, 17, 0 ++ xxspltw 32+21, 17, 1 ++ xxspltw 32+22, 17, 2 ++ xxspltw 32+23, 17, 3 ++ xxspltw 32+24, 18, 0 ++ xxspltw 32+25, 18, 1 ++ xxspltw 32+26, 18, 2 ++ xxspltw 32+27, 18, 3 ++ xxspltw 32+28, 19, 0 ++ xxspltw 32+29, 19, 1 ++ vadduwm 28, 28, 31 # increase counter ++ xxspltw 32+30, 19, 2 ++ xxspltw 32+31, 19, 3 ++ ++.align 5 ++quarter_loop_8x: ++ QT_loop_8x ++ ++ bdnz quarter_loop_8x ++ ++ xxlor 0, 32+30, 32+30 ++ xxlor 32+30, 30, 30 ++ vadduwm 12, 12, 30 ++ xxlor 32+30, 0, 0 ++ TP_4x 0, 1, 2, 3 ++ TP_4x 4, 5, 6, 7 ++ TP_4x 8, 9, 10, 11 ++ TP_4x 12, 13, 14, 15 ++ ++ xxlor 0, 48, 48 ++ xxlor 1, 49, 49 ++ xxlor 2, 50, 50 ++ xxlor 3, 51, 51 ++ xxlor 48, 16, 16 ++ xxlor 49, 17, 17 ++ xxlor 50, 18, 18 ++ xxlor 51, 19, 19 ++ Add_state 0 ++ xxlor 48, 0, 0 ++ xxlor 49, 1, 1 ++ xxlor 50, 2, 2 ++ xxlor 51, 3, 3 ++ Write_256 0 ++ addi 14, 14, 256 ++ addi 15, 15, -256 ++ ++ xxlor 5, 32+31, 32+31 ++ xxlor 32+31, 31, 31 ++ vadduwm 28, 28, 31 ++ xxlor 32+31, 5, 5 ++ TP_4x 16+0, 16+1, 16+2, 16+3 ++ TP_4x 16+4, 16+5, 16+6, 16+7 ++ TP_4x 16+8, 16+9, 16+10, 16+11 ++ TP_4x 16+12, 16+13, 16+14, 16+15 ++ ++ xxlor 32, 16, 16 ++ xxlor 33, 17, 17 ++ xxlor 34, 18, 18 ++ xxlor 35, 19, 19 ++ Add_state 16 ++ Write_256 16 ++ addi 14, 14, 256 ++ addi 15, 15, -256 ++ ++ # should update counter before out? ++ xxlor 32+24, 24, 24 ++ xxlor 32+25, 25, 25 ++ xxlor 32+30, 30, 30 ++ vadduwm 30, 30, 25 ++ vadduwm 31, 30, 24 ++ xxlor 30, 32+30, 32+30 ++ xxlor 31, 32+31, 32+31 ++ ++ cmpdi 15, 0 ++ beq Out_loop ++ ++ cmpdi 15, 512 ++ blt Loop_last ++ ++ mtctr 8 ++ b Loop_8x ++ ++Loop_last: ++ lxvw4x 48, 0, 3 # vr16, constants ++ lxvw4x 49, 17, 3 # vr17, key 1 ++ lxvw4x 50, 18, 3 # vr18, key 2 ++ lxvw4x 51, 19, 3 # vr19, counter, nonce ++ ++ vspltisw 21, 12 ++ vspltisw 23, 7 ++ lxvw4x 32+20, 0, 11 ++ lxvw4x 32+22, 17, 11 ++ ++ li 8, 10 ++ mtctr 8 ++ ++Loop_4x: ++ lvx 0, 20, 10 ++ lvx 1, 21, 10 ++ lvx 2, 22, 10 ++ lvx 3, 23, 10 ++ vspltw 4, 17, 0 ++ vspltw 5, 17, 1 ++ vspltw 6, 17, 2 ++ vspltw 7, 17, 3 ++ vspltw 8, 18, 0 ++ vspltw 9, 18, 1 ++ vspltw 10, 18, 2 ++ vspltw 11, 18, 3 ++ vspltw 12, 19, 0 ++ vadduwm 12, 12, 30 # increase counter ++ vspltw 13, 19, 1 ++ vspltw 14, 19, 2 ++ vspltw 15, 19, 3 ++ ++.align 5 ++quarter_loop: ++ QT_loop_4x ++ ++ bdnz quarter_loop ++ ++ vadduwm 12, 12, 30 ++ TP_4x 0, 1, 2, 3 ++ TP_4x 4, 5, 6, 7 ++ TP_4x 8, 9, 10, 11 ++ TP_4x 12, 13, 14, 15 ++ ++ Add_state 0 ++ Write_256 0 ++ addi 14, 14, 256 ++ addi 15, 15, -256 ++ ++ # Update state counter ++ vspltisw 25, 4 ++ vadduwm 30, 30, 25 ++ ++ cmpdi 15, 0 ++ beq Out_loop ++ ++ mtctr 8 ++ b Loop_4x ++ ++Out_loop: ++ # ++ # Update state counter ++ # ++ vspltisb 16, -1 # first 16 bytes - 0xffff...ff ++ vspltisb 17, 0 # second 16 bytes - 0x0000...00 ++ vsldoi 18, 16, 17, 12 ++ vand 18, 18, 30 ++ xxlor 32+19, 19, 19 ++ vadduwm 18, 19, 18 ++ stxvw4x 32+18, 19, 3 ++ li 3, 0 ++ ++ addi 9, 1, 256 ++ lvx 20, 0, 9 ++ lvx 21, 17, 9 ++ lvx 22, 18, 9 ++ lvx 23, 19, 9 ++ lvx 24, 20, 9 ++ lvx 25, 21, 9 ++ lvx 26, 22, 9 ++ lvx 27, 23, 9 ++ lvx 28, 24, 9 ++ lvx 29, 25, 9 ++ lvx 30, 26, 9 ++ lvx 31, 27, 9 ++ ++ add 9, 9, 27 ++ addi 14, 17, 16 ++ lxvx 14, 14, 9 ++ addi 14, 14, 16 ++ lxvx 15, 14, 9 ++ addi 14, 14, 16 ++ lxvx 16, 14, 9 ++ addi 14, 14, 16 ++ lxvx 17, 14, 9 ++ addi 14, 14, 16 ++ lxvx 18, 14, 9 ++ addi 14, 14, 16 ++ lxvx 19, 14, 9 ++ addi 14, 14, 16 ++ lxvx 20, 14, 9 ++ addi 14, 14, 16 ++ lxvx 21, 14, 9 ++ addi 14, 14, 16 ++ lxvx 22, 14, 9 ++ addi 14, 14, 16 ++ lxvx 23, 14, 9 ++ addi 14, 14, 16 ++ lxvx 24, 14, 9 ++ addi 14, 14, 16 ++ lxvx 25, 14, 9 ++ addi 14, 14, 16 ++ lxvx 26, 14, 9 ++ addi 14, 14, 16 ++ lxvx 27, 14, 9 ++ addi 14, 14, 16 ++ lxvx 28, 14, 9 ++ addi 14, 14, 16 ++ lxvx 29, 14, 9 ++ addi 14, 14, 16 ++ lxvx 30, 14, 9 ++ addi 14, 14, 16 ++ lxvx 31, 14, 9 ++ ++ ld 0, 1040(1) ++ ld 14,112(1) ++ ld 15,120(1) ++ ld 16,128(1) ++ ld 17,136(1) ++ ld 18,144(1) ++ ld 19,152(1) ++ ld 20,160(1) ++ ld 21,168(1) ++ ld 22,176(1) ++ ld 23,184(1) ++ ld 24,192(1) ++ ld 25,200(1) ++ ld 26,208(1) ++ ld 27,216(1) ++ ld 28,224(1) ++ ld 29,232(1) ++ ld 30,240(1) ++ ld 31,248(1) ++ ++ mtlr 0 ++ addi 1, 1, 1024 ++ blr ++ ++Out_no_chacha: ++ li 3, 0 ++ blr ++ ++.data ++.align 4 ++sigma: ++.long 0x61707865, 0x3320646e, 0x79622d32, 0x6b206574 ++.long 0x0c0d0e0f, 0x08090a0b, 0x04050607, 0x00010203 ++.long 1, 0, 0, 0 ++.long 0, 1, 2, 3 ++.long 0x61707865, 0x61707865, 0x61707865, 0x61707865 ++.long 0x3320646e, 0x3320646e, 0x3320646e, 0x3320646e ++.long 0x79622d32, 0x79622d32, 0x79622d32, 0x79622d32 ++.long 0x6b206574, 0x6b206574, 0x6b206574, 0x6b206574 ++permx: ++.long 0x22330011, 0x66774455, 0xaabb8899, 0xeeffccdd ++.long 0x11223300, 0x55667744, 0x99aabb88, 0xddeeffcc +Index: libgcrypt-1.10.2/cipher/chacha20.c +=================================================================== +--- libgcrypt-1.10.2.orig/cipher/chacha20.c ++++ libgcrypt-1.10.2/cipher/chacha20.c +@@ -125,6 +125,7 @@ typedef struct CHACHA20_context_s + unsigned int use_avx2:1; + unsigned int use_neon:1; + unsigned int use_ppc:1; ++ unsigned int use_p10:1; + unsigned int use_s390x:1; + } CHACHA20_context_t; + +@@ -163,6 +164,12 @@ unsigned int _gcry_chacha20_poly1305_amd + + #ifdef USE_PPC_VEC + ++#ifndef WORDS_BIGENDIAN ++unsigned int _gcry_chacha20_p10le_8x(u32 *state, byte *dst, ++ const byte *src, ++ size_t len); ++#endif ++ + unsigned int _gcry_chacha20_ppc8_blocks4(u32 *state, byte *dst, + const byte *src, + size_t nblks); +@@ -475,6 +482,9 @@ chacha20_do_setkey (CHACHA20_context_t * + #endif + #ifdef USE_PPC_VEC + ctx->use_ppc = (features & HWF_PPC_ARCH_2_07) != 0; ++# ifndef WORDS_BIGENDIAN ++ ctx->use_p10 = (features & HWF_PPC_ARCH_3_10) != 0; ++# endif + #endif + #ifdef USE_S390X_VX + ctx->use_s390x = (features & HWF_S390X_VX) != 0; +@@ -571,7 +581,22 @@ do_chacha20_encrypt_stream_tail (CHACHA2 + { + size_t nblocks = length / CHACHA20_BLOCK_SIZE; + nblocks -= nblocks % 4; +- nburn = _gcry_chacha20_ppc8_blocks4(ctx->input, outbuf, inbuf, nblocks); ++#ifndef WORDS_BIGENDIAN ++ /* ++ * A workaround to skip counter overflow. This is rare. ++ */ ++ if (ctx->use_p10 && nblocks >= 8 ++ && ((u64)ctx->input[12] + nblocks) <= 0xffffffffU) ++ { ++ size_t len = nblocks * CHACHA20_BLOCK_SIZE; ++ nburn = _gcry_chacha20_p10le_8x(ctx->input, outbuf, inbuf, len); ++ } ++ else ++#endif ++ { ++ nburn = _gcry_chacha20_ppc8_blocks4(ctx->input, outbuf, inbuf, ++ nblocks); ++ } + burn = nburn > burn ? nburn : burn; + length -= nblocks * CHACHA20_BLOCK_SIZE; + outbuf += nblocks * CHACHA20_BLOCK_SIZE; +@@ -760,6 +785,11 @@ _gcry_chacha20_poly1305_encrypt(gcry_cip + } + #endif + #ifdef USE_PPC_VEC_POLY1305 ++ else if (ctx->use_ppc && ctx->use_p10) ++ { ++ /* Skip stitched chacha20-poly1305 for P10. */ ++ authptr = NULL; ++ } + else if (ctx->use_ppc && length >= CHACHA20_BLOCK_SIZE * 4) + { + nburn = _gcry_chacha20_ppc8_blocks4(ctx->input, outbuf, inbuf, 4); +@@ -998,6 +1028,7 @@ _gcry_chacha20_poly1305_decrypt(gcry_cip + { + CHACHA20_context_t *ctx = (void *) &c->context.c; + unsigned int nburn, burn = 0; ++ int skip_stitched = 0; + + if (!length) + return 0; +@@ -1049,6 +1080,13 @@ _gcry_chacha20_poly1305_decrypt(gcry_cip + inbuf += nblocks * CHACHA20_BLOCK_SIZE; + } + #endif ++#ifdef USE_PPC_VEC_POLY1305 ++ if (ctx->use_ppc && ctx->use_p10) ++ { ++ /* Skip stitched chacha20-poly1305 for P10. */ ++ skip_stitched = 1; ++ } ++#endif + + #ifdef USE_SSSE3 + if (ctx->use_ssse3) +@@ -1102,7 +1140,8 @@ _gcry_chacha20_poly1305_decrypt(gcry_cip + #endif + + #ifdef USE_PPC_VEC_POLY1305 +- if (ctx->use_ppc && length >= 4 * CHACHA20_BLOCK_SIZE) ++ /* skip stitch for p10 */ ++ if (!skip_stitched && ctx->use_ppc && length >= 4 * CHACHA20_BLOCK_SIZE) + { + size_t nblocks = length / CHACHA20_BLOCK_SIZE; + nblocks -= nblocks % 4; +Index: libgcrypt-1.10.2/cipher/poly1305-internal.h +=================================================================== +--- libgcrypt-1.10.2.orig/cipher/poly1305-internal.h ++++ libgcrypt-1.10.2/cipher/poly1305-internal.h +@@ -33,6 +33,17 @@ + #define POLY1305_KEYLEN 32 + #define POLY1305_BLOCKSIZE 16 + ++/* POLY1305_USE_PPC_VEC indicates whether to enable PowerPC vector code. */ ++#undef POLY1305_USE_PPC_VEC ++#ifdef ENABLE_PPC_CRYPTO_SUPPORT ++# if defined(HAVE_COMPATIBLE_CC_PPC_ALTIVEC) && \ ++ defined(HAVE_GCC_INLINE_ASM_PPC_ALTIVEC) && \ ++ !defined(WORDS_BIGENDIAN) ++# if __GNUC__ >= 4 ++# define POLY1305_USE_PPC_VEC 1 ++# endif ++# endif ++#endif + + typedef struct + { +@@ -46,6 +57,9 @@ typedef struct poly1305_context_s + POLY1305_STATE state; + byte buffer[POLY1305_BLOCKSIZE]; + unsigned int leftover; ++#ifdef POLY1305_USE_PPC_VEC ++ unsigned int use_p10:1; ++#endif + } poly1305_context_t; + + +Index: libgcrypt-1.10.2/cipher/poly1305-p10le.s +=================================================================== +--- /dev/null ++++ libgcrypt-1.10.2/cipher/poly1305-p10le.s +@@ -0,0 +1,841 @@ ++# Copyright 2021- IBM Inc. All rights reserved ++# ++# This file is part of Libgcrypt. ++# ++# Libgcrypt is free software; you can redistribute it and/or modify ++# it under the terms of the GNU Lesser General Public License as ++# published by the Free Software Foundation; either version 2.1 of ++# the License, or (at your option) any later version. ++# ++# Libgcrypt 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 Lesser General Public License for more details. ++# ++# You should have received a copy of the GNU Lesser General Public ++# License along with this program; if not, see . ++# ++#=================================================================================== ++# Written by Danny Tsen ++# ++# Poly1305 - this version mainly using vector/VSX/Scalar ++# - 26 bits limbs ++# - Handle multiple 64 byte blcoks but need at least 2 64 bytes block ++# ++# Improve performance by breaking down polynominal to the sum of products with ++# h4 = m1 * r⁴ + m2 * r³ + m3 * r² + m4 * r ++# ++# 07/22/21 - this revison based on the above sum of products. Setup r^4, r^3, r^2, r and s3, s2, s1, s0 ++# to 9 vectors for multiplications. ++# ++# setup r^4, r^3, r^2, r vectors ++# vs [r^1, r^3, r^2, r^4] ++# vs0 = [r0,.....] ++# vs1 = [r1,.....] ++# vs2 = [r2,.....] ++# vs3 = [r3,.....] ++# vs4 = [r4,.....] ++# vs5 = [r1*5,...] ++# vs6 = [r2*5,...] ++# vs7 = [r2*5,...] ++# vs8 = [r4*5,...] ++# ++# Each word in a vector consists a member of a "r/s" in [a * r/s]. ++# ++# r0, r4*5, r3*5, r2*5, r1*5; ++# r1, r0, r4*5, r3*5, r2*5; ++# r2, r1, r0, r4*5, r3*5; ++# r3, r2, r1, r0, r4*5; ++# r4, r3, r2, r1, r0 ; ++# ++# ++# gcry_poly1305_p10le_4blocks( uint8_t *k, uint32_t mlen, uint8_t *m) ++# k = 32 bytes key ++# r3 = k (r, s) ++# r4 = mlen ++# r5 = m ++# ++.text ++ ++# Block size 16 bytes ++# key = (r, s) ++# clamp r &= 0x0FFFFFFC0FFFFFFC 0x0FFFFFFC0FFFFFFF ++# p = 2^130 - 5 ++# a += m ++# a = (r + a) % p ++# a += s ++# 16 bytes (a) ++# ++# p[0] = a0*r0 + a1*r4*5 + a2*r3*5 + a3*r2*5 + a4*r1*5; ++# p[1] = a0*r1 + a1*r0 + a2*r4*5 + a3*r3*5 + a4*r2*5; ++# p[2] = a0*r2 + a1*r1 + a2*r0 + a3*r4*5 + a4*r3*5; ++# p[3] = a0*r3 + a1*r2 + a2*r1 + a3*r0 + a4*r4*5; ++# p[4] = a0*r4 + a1*r3 + a2*r2 + a3*r1 + a4*r0 ; ++# ++# [r^2, r^3, r^1, r^4] ++# [m3, m2, m4, m1] ++# ++# multiply odd and even words ++.macro mul_odd ++ vmulouw 14, 4, 26 ++ vmulouw 10, 5, 3 ++ vmulouw 11, 6, 2 ++ vmulouw 12, 7, 1 ++ vmulouw 13, 8, 0 ++ vmulouw 15, 4, 27 ++ vaddudm 14, 14, 10 ++ vaddudm 14, 14, 11 ++ vmulouw 10, 5, 26 ++ vmulouw 11, 6, 3 ++ vaddudm 14, 14, 12 ++ vaddudm 14, 14, 13 # x0 ++ vaddudm 15, 15, 10 ++ vaddudm 15, 15, 11 ++ vmulouw 12, 7, 2 ++ vmulouw 13, 8, 1 ++ vaddudm 15, 15, 12 ++ vaddudm 15, 15, 13 # x1 ++ vmulouw 16, 4, 28 ++ vmulouw 10, 5, 27 ++ vmulouw 11, 6, 26 ++ vaddudm 16, 16, 10 ++ vaddudm 16, 16, 11 ++ vmulouw 12, 7, 3 ++ vmulouw 13, 8, 2 ++ vaddudm 16, 16, 12 ++ vaddudm 16, 16, 13 # x2 ++ vmulouw 17, 4, 29 ++ vmulouw 10, 5, 28 ++ vmulouw 11, 6, 27 ++ vaddudm 17, 17, 10 ++ vaddudm 17, 17, 11 ++ vmulouw 12, 7, 26 ++ vmulouw 13, 8, 3 ++ vaddudm 17, 17, 12 ++ vaddudm 17, 17, 13 # x3 ++ vmulouw 18, 4, 30 ++ vmulouw 10, 5, 29 ++ vmulouw 11, 6, 28 ++ vaddudm 18, 18, 10 ++ vaddudm 18, 18, 11 ++ vmulouw 12, 7, 27 ++ vmulouw 13, 8, 26 ++ vaddudm 18, 18, 12 ++ vaddudm 18, 18, 13 # x4 ++.endm ++ ++.macro mul_even ++ vmuleuw 9, 4, 26 ++ vmuleuw 10, 5, 3 ++ vmuleuw 11, 6, 2 ++ vmuleuw 12, 7, 1 ++ vmuleuw 13, 8, 0 ++ vaddudm 14, 14, 9 ++ vaddudm 14, 14, 10 ++ vaddudm 14, 14, 11 ++ vaddudm 14, 14, 12 ++ vaddudm 14, 14, 13 # x0 ++ ++ vmuleuw 9, 4, 27 ++ vmuleuw 10, 5, 26 ++ vmuleuw 11, 6, 3 ++ vmuleuw 12, 7, 2 ++ vmuleuw 13, 8, 1 ++ vaddudm 15, 15, 9 ++ vaddudm 15, 15, 10 ++ vaddudm 15, 15, 11 ++ vaddudm 15, 15, 12 ++ vaddudm 15, 15, 13 # x1 ++ ++ vmuleuw 9, 4, 28 ++ vmuleuw 10, 5, 27 ++ vmuleuw 11, 6, 26 ++ vmuleuw 12, 7, 3 ++ vmuleuw 13, 8, 2 ++ vaddudm 16, 16, 9 ++ vaddudm 16, 16, 10 ++ vaddudm 16, 16, 11 ++ vaddudm 16, 16, 12 ++ vaddudm 16, 16, 13 # x2 ++ ++ vmuleuw 9, 4, 29 ++ vmuleuw 10, 5, 28 ++ vmuleuw 11, 6, 27 ++ vmuleuw 12, 7, 26 ++ vmuleuw 13, 8, 3 ++ vaddudm 17, 17, 9 ++ vaddudm 17, 17, 10 ++ vaddudm 17, 17, 11 ++ vaddudm 17, 17, 12 ++ vaddudm 17, 17, 13 # x3 ++ ++ vmuleuw 9, 4, 30 ++ vmuleuw 10, 5, 29 ++ vmuleuw 11, 6, 28 ++ vmuleuw 12, 7, 27 ++ vmuleuw 13, 8, 26 ++ vaddudm 18, 18, 9 ++ vaddudm 18, 18, 10 ++ vaddudm 18, 18, 11 ++ vaddudm 18, 18, 12 ++ vaddudm 18, 18, 13 # x4 ++.endm ++ ++# setup r^4, r^3, r^2, r vectors ++# [r, r^3, r^2, r^4] ++# vs0 = [r0,...] ++# vs1 = [r1,...] ++# vs2 = [r2,...] ++# vs3 = [r3,...] ++# vs4 = [r4,...] ++# vs5 = [r4*5,...] ++# vs6 = [r3*5,...] ++# vs7 = [r2*5,...] ++# vs8 = [r1*5,...] ++# ++# r0, r4*5, r3*5, r2*5, r1*5; ++# r1, r0, r4*5, r3*5, r2*5; ++# r2, r1, r0, r4*5, r3*5; ++# r3, r2, r1, r0, r4*5; ++# r4, r3, r2, r1, r0 ; ++# ++.macro poly1305_setup_r ++ ++ # save r ++ xxlor 26, 58, 58 ++ xxlor 27, 59, 59 ++ xxlor 28, 60, 60 ++ xxlor 29, 61, 61 ++ xxlor 30, 62, 62 ++ ++ xxlxor 31, 31, 31 ++ ++# [r, r^3, r^2, r^4] ++ # compute r^2 ++ vmr 4, 26 ++ vmr 5, 27 ++ vmr 6, 28 ++ vmr 7, 29 ++ vmr 8, 30 ++ bl do_mul # r^2 r^1 ++ xxpermdi 58, 58, 36, 0x3 # r0 ++ xxpermdi 59, 59, 37, 0x3 # r1 ++ xxpermdi 60, 60, 38, 0x3 # r2 ++ xxpermdi 61, 61, 39, 0x3 # r3 ++ xxpermdi 62, 62, 40, 0x3 # r4 ++ xxpermdi 36, 36, 36, 0x3 ++ xxpermdi 37, 37, 37, 0x3 ++ xxpermdi 38, 38, 38, 0x3 ++ xxpermdi 39, 39, 39, 0x3 ++ xxpermdi 40, 40, 40, 0x3 ++ vspltisb 13, 2 ++ vsld 9, 27, 13 ++ vsld 10, 28, 13 ++ vsld 11, 29, 13 ++ vsld 12, 30, 13 ++ vaddudm 0, 9, 27 ++ vaddudm 1, 10, 28 ++ vaddudm 2, 11, 29 ++ vaddudm 3, 12, 30 ++ ++ bl do_mul # r^4 r^3 ++ vmrgow 26, 26, 4 ++ vmrgow 27, 27, 5 ++ vmrgow 28, 28, 6 ++ vmrgow 29, 29, 7 ++ vmrgow 30, 30, 8 ++ vspltisb 13, 2 ++ vsld 9, 27, 13 ++ vsld 10, 28, 13 ++ vsld 11, 29, 13 ++ vsld 12, 30, 13 ++ vaddudm 0, 9, 27 ++ vaddudm 1, 10, 28 ++ vaddudm 2, 11, 29 ++ vaddudm 3, 12, 30 ++ ++ # r^2 r^4 ++ xxlor 0, 58, 58 ++ xxlor 1, 59, 59 ++ xxlor 2, 60, 60 ++ xxlor 3, 61, 61 ++ xxlor 4, 62, 62 ++ xxlor 5, 32, 32 ++ xxlor 6, 33, 33 ++ xxlor 7, 34, 34 ++ xxlor 8, 35, 35 ++ ++ vspltw 9, 26, 3 ++ vspltw 10, 26, 2 ++ vmrgow 26, 10, 9 ++ vspltw 9, 27, 3 ++ vspltw 10, 27, 2 ++ vmrgow 27, 10, 9 ++ vspltw 9, 28, 3 ++ vspltw 10, 28, 2 ++ vmrgow 28, 10, 9 ++ vspltw 9, 29, 3 ++ vspltw 10, 29, 2 ++ vmrgow 29, 10, 9 ++ vspltw 9, 30, 3 ++ vspltw 10, 30, 2 ++ vmrgow 30, 10, 9 ++ ++ vsld 9, 27, 13 ++ vsld 10, 28, 13 ++ vsld 11, 29, 13 ++ vsld 12, 30, 13 ++ vaddudm 0, 9, 27 ++ vaddudm 1, 10, 28 ++ vaddudm 2, 11, 29 ++ vaddudm 3, 12, 30 ++.endm ++ ++do_mul: ++ mul_odd ++ ++ # do reduction ( h %= p ) ++ # carry reduction ++ vspltisb 9, 2 ++ vsrd 10, 14, 31 ++ vsrd 11, 17, 31 ++ vand 7, 17, 25 ++ vand 4, 14, 25 ++ vaddudm 18, 18, 11 ++ vsrd 12, 18, 31 ++ vaddudm 15, 15, 10 ++ ++ vsrd 11, 15, 31 ++ vand 8, 18, 25 ++ vand 5, 15, 25 ++ vaddudm 4, 4, 12 ++ vsld 10, 12, 9 ++ vaddudm 6, 16, 11 ++ ++ vsrd 13, 6, 31 ++ vand 6, 6, 25 ++ vaddudm 4, 4, 10 ++ vsrd 10, 4, 31 ++ vaddudm 7, 7, 13 ++ ++ vsrd 11, 7, 31 ++ vand 7, 7, 25 ++ vand 4, 4, 25 ++ vaddudm 5, 5, 10 ++ vaddudm 8, 8, 11 ++ blr ++ ++# ++# init key ++# ++do_poly1305_init: ++ ld 10, rmask@got(2) ++ ld 11, 0(10) ++ ld 12, 8(10) ++ ++ li 14, 16 ++ li 15, 32 ++ ld 10, cnum@got(2) ++ lvx 25, 0, 10 # v25 - mask ++ lvx 31, 14, 10 # v31 = 1a ++ lvx 19, 15, 10 # v19 = 1 << 24 ++ lxv 24, 48(10) # vs24 ++ lxv 25, 64(10) # vs25 ++ ++ # initialize ++ # load key from r3 to vectors ++ ld 9, 16(3) ++ ld 10, 24(3) ++ ld 11, 0(3) ++ ld 12, 8(3) ++ ++ # break 26 bits ++ extrdi 14, 9, 26, 38 ++ extrdi 15, 9, 26, 12 ++ extrdi 16, 9, 12, 0 ++ mtvsrdd 58, 0, 14 ++ insrdi 16, 10, 14, 38 ++ mtvsrdd 59, 0, 15 ++ extrdi 17, 10, 26, 24 ++ mtvsrdd 60, 0, 16 ++ extrdi 18, 10, 24, 0 ++ mtvsrdd 61, 0, 17 ++ mtvsrdd 62, 0, 18 ++ ++ # r1 = r1 * 5, r2 = r2 * 5, r3 = r3 * 5, r4 = r4 * 5 ++ li 9, 5 ++ mtvsrdd 36, 0, 9 ++ vmulouw 0, 27, 4 # v0 = rr0 ++ vmulouw 1, 28, 4 # v1 = rr1 ++ vmulouw 2, 29, 4 # v2 = rr2 ++ vmulouw 3, 30, 4 # v3 = rr3 ++ blr ++ ++# ++# gcry_poly1305_p10le_4blocks( uint8_t *k, uint32_t mlen, uint8_t *m) ++# k = 32 bytes key ++# r3 = k (r, s) ++# r4 = mlen ++# r5 = m ++# ++.global gcry_poly1305_p10le_4blocks ++.align 5 ++gcry_poly1305_p10le_4blocks: ++_gcry_poly1305_p10le_4blocks: ++ cmpdi 5, 128 ++ blt Out_no_poly1305 ++ ++ stdu 1,-1024(1) ++ mflr 0 ++ ++ std 14,112(1) ++ std 15,120(1) ++ std 16,128(1) ++ std 17,136(1) ++ std 18,144(1) ++ std 19,152(1) ++ std 20,160(1) ++ std 21,168(1) ++ std 31,248(1) ++ li 14, 256 ++ stvx 20, 14, 1 ++ addi 14, 14, 16 ++ stvx 21, 14, 1 ++ addi 14, 14, 16 ++ stvx 22, 14, 1 ++ addi 14, 14, 16 ++ stvx 23, 14, 1 ++ addi 14, 14, 16 ++ stvx 24, 14, 1 ++ addi 14, 14, 16 ++ stvx 25, 14, 1 ++ addi 14, 14, 16 ++ stvx 26, 14, 1 ++ addi 14, 14, 16 ++ stvx 27, 14, 1 ++ addi 14, 14, 16 ++ stvx 28, 14, 1 ++ addi 14, 14, 16 ++ stvx 29, 14, 1 ++ addi 14, 14, 16 ++ stvx 30, 14, 1 ++ addi 14, 14, 16 ++ stvx 31, 14, 1 ++ ++ addi 14, 14, 16 ++ stxvx 14, 14, 1 ++ addi 14, 14, 16 ++ stxvx 15, 14, 1 ++ addi 14, 14, 16 ++ stxvx 16, 14, 1 ++ addi 14, 14, 16 ++ stxvx 17, 14, 1 ++ addi 14, 14, 16 ++ stxvx 18, 14, 1 ++ addi 14, 14, 16 ++ stxvx 19, 14, 1 ++ addi 14, 14, 16 ++ stxvx 20, 14, 1 ++ addi 14, 14, 16 ++ stxvx 21, 14, 1 ++ addi 14, 14, 16 ++ stxvx 22, 14, 1 ++ addi 14, 14, 16 ++ stxvx 23, 14, 1 ++ addi 14, 14, 16 ++ stxvx 24, 14, 1 ++ addi 14, 14, 16 ++ stxvx 25, 14, 1 ++ addi 14, 14, 16 ++ stxvx 26, 14, 1 ++ addi 14, 14, 16 ++ stxvx 27, 14, 1 ++ addi 14, 14, 16 ++ stxvx 28, 14, 1 ++ addi 14, 14, 16 ++ stxvx 29, 14, 1 ++ addi 14, 14, 16 ++ stxvx 30, 14, 1 ++ addi 14, 14, 16 ++ stxvx 31, 14, 1 ++ std 0, 1040(1) ++ ++ bl do_poly1305_init ++ ++ li 21, 0 # counter to message ++ ++ poly1305_setup_r ++ ++ # load previous state ++ # break/convert r6 to 26 bits ++ ld 9, 32(3) ++ ld 10, 40(3) ++ lwz 19, 48(3) ++ sldi 19, 19, 24 ++ mtvsrdd 41, 0, 19 ++ extrdi 14, 9, 26, 38 ++ extrdi 15, 9, 26, 12 ++ extrdi 16, 9, 12, 0 ++ mtvsrdd 36, 0, 14 ++ insrdi 16, 10, 14, 38 ++ mtvsrdd 37, 0, 15 ++ extrdi 17, 10, 26, 24 ++ mtvsrdd 38, 0, 16 ++ extrdi 18, 10, 24, 0 ++ mtvsrdd 39, 0, 17 ++ mtvsrdd 40, 0, 18 ++ vor 8, 8, 9 ++ ++ # input m1 m2 ++ add 20, 4, 21 ++ xxlor 49, 24, 24 ++ xxlor 50, 25, 25 ++ lxvw4x 43, 0, 20 ++ addi 17, 20, 16 ++ lxvw4x 44, 0, 17 ++ vperm 14, 11, 12, 17 ++ vperm 15, 11, 12, 18 ++ vand 9, 14, 25 # a0 ++ vsrd 10, 14, 31 # >> 26 ++ vsrd 11, 10, 31 # 12 bits left ++ vand 10, 10, 25 # a1 ++ vspltisb 13, 12 ++ vand 16, 15, 25 ++ vsld 12, 16, 13 ++ vor 11, 11, 12 ++ vand 11, 11, 25 # a2 ++ vspltisb 13, 14 ++ vsrd 12, 15, 13 # >> 14 ++ vsrd 13, 12, 31 # >> 26, a4 ++ vand 12, 12, 25 # a3 ++ ++ vaddudm 20, 4, 9 ++ vaddudm 21, 5, 10 ++ vaddudm 22, 6, 11 ++ vaddudm 23, 7, 12 ++ vaddudm 24, 8, 13 ++ ++ # m3 m4 ++ addi 17, 17, 16 ++ lxvw4x 43, 0, 17 ++ addi 17, 17, 16 ++ lxvw4x 44, 0, 17 ++ vperm 14, 11, 12, 17 ++ vperm 15, 11, 12, 18 ++ vand 9, 14, 25 # a0 ++ vsrd 10, 14, 31 # >> 26 ++ vsrd 11, 10, 31 # 12 bits left ++ vand 10, 10, 25 # a1 ++ vspltisb 13, 12 ++ vand 16, 15, 25 ++ vsld 12, 16, 13 ++ vspltisb 13, 14 ++ vor 11, 11, 12 ++ vand 11, 11, 25 # a2 ++ vsrd 12, 15, 13 # >> 14 ++ vsrd 13, 12, 31 # >> 26, a4 ++ vand 12, 12, 25 # a3 ++ ++ # Smash 4 message blocks into 5 vectors of [m4, m2, m3, m1] ++ vmrgow 4, 9, 20 ++ vmrgow 5, 10, 21 ++ vmrgow 6, 11, 22 ++ vmrgow 7, 12, 23 ++ vmrgow 8, 13, 24 ++ vaddudm 8, 8, 19 ++ ++ addi 5, 5, -64 ++ addi 21, 21, 64 ++ ++ li 9, 64 ++ divdu 31, 5, 9 ++ ++ mtctr 31 ++ ++# h4 = m1 * r⁴ + m2 * r³ + m3 * r² + m4 * r ++# Rewrite the polynominal sum of product as follows, ++# h1 = (h0 + m1) * r^2, h2 = (h0 + m2) * r^2 ++# h3 = (h1 + m3) * r^2, h4 = (h2 + m4) * r^2 --> (h0 + m1) r*4 + (h3 + m3) r^2, (h0 + m2) r^4 + (h0 + m4) r^2 ++# .... Repeat ++# h5 = (h3 + m5) * r^2, h6 = (h4 + m6) * r^2 --> ++# h7 = (h5 + m7) * r^2, h8 = (h6 + m8) * r^1 --> m5 * r^4 + m6 * r^3 + m7 * r^2 + m8 * r ++# ++loop_4blocks: ++ ++ # Multiply odd words and even words ++ mul_odd ++ mul_even ++ # carry reduction ++ vspltisb 9, 2 ++ vsrd 10, 14, 31 ++ vsrd 11, 17, 31 ++ vand 7, 17, 25 ++ vand 4, 14, 25 ++ vaddudm 18, 18, 11 ++ vsrd 12, 18, 31 ++ vaddudm 15, 15, 10 ++ ++ vsrd 11, 15, 31 ++ vand 8, 18, 25 ++ vand 5, 15, 25 ++ vaddudm 4, 4, 12 ++ vsld 10, 12, 9 ++ vaddudm 6, 16, 11 ++ ++ vsrd 13, 6, 31 ++ vand 6, 6, 25 ++ vaddudm 4, 4, 10 ++ vsrd 10, 4, 31 ++ vaddudm 7, 7, 13 ++ ++ vsrd 11, 7, 31 ++ vand 7, 7, 25 ++ vand 4, 4, 25 ++ vaddudm 5, 5, 10 ++ vaddudm 8, 8, 11 ++ ++ # input m1 m2 m3 m4 ++ add 20, 4, 21 ++ xxlor 49, 24, 24 ++ xxlor 50, 25, 25 ++ lxvw4x 43, 0, 20 ++ addi 17, 20, 16 ++ lxvw4x 44, 0, 17 ++ vperm 14, 11, 12, 17 ++ vperm 15, 11, 12, 18 ++ addi 17, 17, 16 ++ lxvw4x 43, 0, 17 ++ addi 17, 17, 16 ++ lxvw4x 44, 0, 17 ++ vperm 17, 11, 12, 17 ++ vperm 18, 11, 12, 18 ++ ++ vand 20, 14, 25 # a0 ++ vand 9, 17, 25 # a0 ++ vsrd 21, 14, 31 # >> 26 ++ vsrd 22, 21, 31 # 12 bits left ++ vsrd 10, 17, 31 # >> 26 ++ vsrd 11, 10, 31 # 12 bits left ++ ++ vand 21, 21, 25 # a1 ++ vand 10, 10, 25 # a1 ++ ++ vspltisb 13, 12 ++ vand 16, 15, 25 ++ vsld 23, 16, 13 ++ vor 22, 22, 23 ++ vand 22, 22, 25 # a2 ++ vand 16, 18, 25 ++ vsld 12, 16, 13 ++ vor 11, 11, 12 ++ vand 11, 11, 25 # a2 ++ vspltisb 13, 14 ++ vsrd 23, 15, 13 # >> 14 ++ vsrd 24, 23, 31 # >> 26, a4 ++ vand 23, 23, 25 # a3 ++ vsrd 12, 18, 13 # >> 14 ++ vsrd 13, 12, 31 # >> 26, a4 ++ vand 12, 12, 25 # a3 ++ ++ vaddudm 4, 4, 20 ++ vaddudm 5, 5, 21 ++ vaddudm 6, 6, 22 ++ vaddudm 7, 7, 23 ++ vaddudm 8, 8, 24 ++ ++ # Smash 4 message blocks into 5 vectors of [m4, m2, m3, m1] ++ vmrgow 4, 9, 4 ++ vmrgow 5, 10, 5 ++ vmrgow 6, 11, 6 ++ vmrgow 7, 12, 7 ++ vmrgow 8, 13, 8 ++ vaddudm 8, 8, 19 ++ ++ addi 5, 5, -64 ++ addi 21, 21, 64 ++ ++ bdnz loop_4blocks ++ ++ xxlor 58, 0, 0 ++ xxlor 59, 1, 1 ++ xxlor 60, 2, 2 ++ xxlor 61, 3, 3 ++ xxlor 62, 4, 4 ++ xxlor 32, 5, 5 ++ xxlor 33, 6, 6 ++ xxlor 34, 7, 7 ++ xxlor 35, 8, 8 ++ ++ # Multiply odd words and even words ++ mul_odd ++ mul_even ++ ++ # Sum the products. ++ xxpermdi 41, 31, 46, 0 ++ xxpermdi 42, 31, 47, 0 ++ vaddudm 4, 14, 9 ++ xxpermdi 36, 31, 36, 3 ++ vaddudm 5, 15, 10 ++ xxpermdi 37, 31, 37, 3 ++ xxpermdi 43, 31, 48, 0 ++ vaddudm 6, 16, 11 ++ xxpermdi 38, 31, 38, 3 ++ xxpermdi 44, 31, 49, 0 ++ vaddudm 7, 17, 12 ++ xxpermdi 39, 31, 39, 3 ++ xxpermdi 45, 31, 50, 0 ++ vaddudm 8, 18, 13 ++ xxpermdi 40, 31, 40, 3 ++ ++ # carry reduction ++ vspltisb 9, 2 ++ vsrd 10, 4, 31 ++ vsrd 11, 7, 31 ++ vand 7, 7, 25 ++ vand 4, 4, 25 ++ vaddudm 8, 8, 11 ++ vsrd 12, 8, 31 ++ vaddudm 5, 5, 10 ++ ++ vsrd 11, 5, 31 ++ vand 8, 8, 25 ++ vand 5, 5, 25 ++ vaddudm 4, 4, 12 ++ vsld 10, 12, 9 ++ vaddudm 6, 6, 11 ++ ++ vsrd 13, 6, 31 ++ vand 6, 6, 25 ++ vaddudm 4, 4, 10 ++ vsrd 10, 4, 31 ++ vaddudm 7, 7, 13 ++ ++ vsrd 11, 7, 31 ++ vand 7, 7, 25 ++ vand 4, 4, 25 ++ vaddudm 5, 5, 10 ++ vaddudm 8, 8, 11 ++ ++ b do_final_update ++ ++do_final_update: ++ # v4, v5, v6, v7 and v8 are 26 bit vectors ++ vsld 5, 5, 31 ++ vor 20, 4, 5 ++ vspltisb 11, 12 ++ vsrd 12, 6, 11 ++ vsld 6, 6, 31 ++ vsld 6, 6, 31 ++ vor 20, 20, 6 ++ vspltisb 11, 14 ++ vsld 7, 7, 11 ++ vor 21, 7, 12 ++ mfvsrld 16, 40 # save last 2 bytes ++ vsld 8, 8, 11 ++ vsld 8, 8, 31 ++ vor 21, 21, 8 ++ mfvsrld 17, 52 ++ mfvsrld 19, 53 ++ srdi 16, 16, 24 ++ ++ std 17, 32(3) ++ std 19, 40(3) ++ stw 16, 48(3) ++ ++Out_loop: ++ li 3, 0 ++ ++ li 14, 256 ++ lvx 20, 14, 1 ++ addi 14, 14, 16 ++ lvx 21, 14, 1 ++ addi 14, 14, 16 ++ lvx 22, 14, 1 ++ addi 14, 14, 16 ++ lvx 23, 14, 1 ++ addi 14, 14, 16 ++ lvx 24, 14, 1 ++ addi 14, 14, 16 ++ lvx 25, 14, 1 ++ addi 14, 14, 16 ++ lvx 26, 14, 1 ++ addi 14, 14, 16 ++ lvx 27, 14, 1 ++ addi 14, 14, 16 ++ lvx 28, 14, 1 ++ addi 14, 14, 16 ++ lvx 29, 14, 1 ++ addi 14, 14, 16 ++ lvx 30, 14, 1 ++ addi 14, 14, 16 ++ lvx 31, 14, 1 ++ ++ addi 14, 14, 16 ++ lxvx 14, 14, 1 ++ addi 14, 14, 16 ++ lxvx 15, 14, 1 ++ addi 14, 14, 16 ++ lxvx 16, 14, 1 ++ addi 14, 14, 16 ++ lxvx 17, 14, 1 ++ addi 14, 14, 16 ++ lxvx 18, 14, 1 ++ addi 14, 14, 16 ++ lxvx 19, 14, 1 ++ addi 14, 14, 16 ++ lxvx 20, 14, 1 ++ addi 14, 14, 16 ++ lxvx 21, 14, 1 ++ addi 14, 14, 16 ++ lxvx 22, 14, 1 ++ addi 14, 14, 16 ++ lxvx 23, 14, 1 ++ addi 14, 14, 16 ++ lxvx 24, 14, 1 ++ addi 14, 14, 16 ++ lxvx 25, 14, 1 ++ addi 14, 14, 16 ++ lxvx 26, 14, 1 ++ addi 14, 14, 16 ++ lxvx 27, 14, 1 ++ addi 14, 14, 16 ++ lxvx 28, 14, 1 ++ addi 14, 14, 16 ++ lxvx 29, 14, 1 ++ addi 14, 14, 16 ++ lxvx 30, 14, 1 ++ addi 14, 14, 16 ++ lxvx 31, 14, 1 ++ ++ ld 0, 1040(1) ++ ld 14,112(1) ++ ld 15,120(1) ++ ld 16,128(1) ++ ld 17,136(1) ++ ld 18,144(1) ++ ld 19,152(1) ++ ld 20,160(1) ++ ld 21,168(1) ++ ld 31,248(1) ++ ++ mtlr 0 ++ addi 1, 1, 1024 ++ blr ++ ++Out_no_poly1305: ++ li 3, 0 ++ blr ++ ++.data ++.align 5 ++rmask: ++.byte 0xff, 0xff, 0xff, 0x0f, 0xfc, 0xff, 0xff, 0x0f, 0xfc, 0xff, 0xff, 0x0f, 0xfc, 0xff, 0xff, 0x0f ++cnum: ++.long 0x03ffffff, 0x00000000, 0x03ffffff, 0x00000000 ++.long 0x1a, 0x00, 0x1a, 0x00 ++.long 0x01000000, 0x01000000, 0x01000000, 0x01000000 ++.long 0x00010203, 0x04050607, 0x10111213, 0x14151617 ++.long 0x08090a0b, 0x0c0d0e0f, 0x18191a1b, 0x1c1d1e1f ++.long 0x05, 0x00, 0x00, 0x00 ++.long 0x02020202, 0x02020202, 0x02020202, 0x02020202 ++.long 0xffffffff, 0xffffffff, 0x00000000, 0x00000000 +Index: libgcrypt-1.10.2/cipher/poly1305.c +=================================================================== +--- libgcrypt-1.10.2.orig/cipher/poly1305.c ++++ libgcrypt-1.10.2/cipher/poly1305.c +@@ -78,11 +78,23 @@ poly1305_blocks (poly1305_context_t *ctx + #endif /* USE_S390X_ASM */ + + ++#ifdef POLY1305_USE_PPC_VEC ++ ++extern unsigned int ++gcry_poly1305_p10le_4blocks(unsigned char *key, const byte *m, size_t len); ++ ++#endif /* POLY1305_USE_PPC_VEC */ ++ ++ + static void poly1305_init (poly1305_context_t *ctx, + const byte key[POLY1305_KEYLEN]) + { + POLY1305_STATE *st = &ctx->state; + ++#ifdef POLY1305_USE_PPC_VEC ++ ctx->use_p10 = (_gcry_get_hw_features () & HWF_PPC_ARCH_3_10) != 0; ++#endif ++ + ctx->leftover = 0; + + st->h[0] = 0; +@@ -533,6 +545,7 @@ _gcry_poly1305_update_burn (poly1305_con + size_t bytes) + { + unsigned int burn = 0; ++ unsigned int nburn; + + /* handle leftover */ + if (ctx->leftover) +@@ -546,15 +559,31 @@ _gcry_poly1305_update_burn (poly1305_con + ctx->leftover += want; + if (ctx->leftover < POLY1305_BLOCKSIZE) + return 0; +- burn = poly1305_blocks (ctx, ctx->buffer, POLY1305_BLOCKSIZE, 1); ++ nburn = poly1305_blocks (ctx, ctx->buffer, POLY1305_BLOCKSIZE, 1); ++ burn = nburn > burn ? nburn : burn; + ctx->leftover = 0; + } + ++#ifdef POLY1305_USE_PPC_VEC ++ /* PPC-P10/little-endian: bulk process multiples of eight blocks */ ++ if (ctx->use_p10 && bytes >= POLY1305_BLOCKSIZE * 8) ++ { ++ size_t nblks = bytes / (POLY1305_BLOCKSIZE * 8); ++ size_t len = nblks * (POLY1305_BLOCKSIZE * 8); ++ POLY1305_STATE *st = &ctx->state; ++ nburn = gcry_poly1305_p10le_4blocks ((unsigned char *) st, m, len); ++ burn = nburn > burn ? nburn : burn; ++ m += len; ++ bytes -= len; ++ } ++#endif /* POLY1305_USE_PPC_VEC */ ++ + /* process full blocks */ + if (bytes >= POLY1305_BLOCKSIZE) + { + size_t nblks = bytes / POLY1305_BLOCKSIZE; +- burn = poly1305_blocks (ctx, m, nblks * POLY1305_BLOCKSIZE, 1); ++ nburn = poly1305_blocks (ctx, m, nblks * POLY1305_BLOCKSIZE, 1); ++ burn = nburn > burn ? nburn : burn; + m += nblks * POLY1305_BLOCKSIZE; + bytes -= nblks * POLY1305_BLOCKSIZE; + } +Index: libgcrypt-1.10.2/configure.ac +=================================================================== +--- libgcrypt-1.10.2.orig/configure.ac ++++ libgcrypt-1.10.2/configure.ac +@@ -2779,6 +2779,11 @@ if test "$found" = "1" ; then + powerpc64le-*-*) + # Build with the ppc8 vector implementation + GCRYPT_ASM_CIPHERS="$GCRYPT_ASM_CIPHERS chacha20-ppc.lo" ++ # Build with the assembly implementation ++ if test "$gcry_cv_gcc_inline_asm_ppc_altivec" = "yes" && ++ test "$gcry_cv_gcc_inline_asm_ppc_arch_3_00" = "yes" ; then ++ GCRYPT_ASM_CIPHERS="$GCRYPT_ASM_CIPHERS chacha20-p10le-8x.lo" ++ fi + ;; + powerpc64-*-*) + # Build with the ppc8 vector implementation +@@ -3117,6 +3122,13 @@ case "${host}" in + s390x-*-*) + GCRYPT_ASM_DIGESTS="$GCRYPT_ASM_DIGESTS poly1305-s390x.lo" + ;; ++ powerpc64le-*-*) ++ # Build with the assembly implementation ++ if test "$gcry_cv_gcc_inline_asm_ppc_altivec" = "yes" && ++ test "$gcry_cv_gcc_inline_asm_ppc_arch_3_00" = "yes" ; then ++ GCRYPT_ASM_DIGESTS="$GCRYPT_ASM_DIGESTS poly1305-p10le.lo" ++ fi ++ ;; + esac + + LIST_MEMBER(scrypt, $enabled_kdfs) diff --git a/libgcrypt-FIPS-SLI-hash-mac.patch b/libgcrypt-FIPS-SLI-hash-mac.patch new file mode 100644 index 0000000..f0f56f2 --- /dev/null +++ b/libgcrypt-FIPS-SLI-hash-mac.patch @@ -0,0 +1,172 @@ +Index: libgcrypt-1.11.0/doc/gcrypt.texi +=================================================================== +--- libgcrypt-1.11.0.orig/doc/gcrypt.texi ++++ libgcrypt-1.11.0/doc/gcrypt.texi +@@ -998,13 +998,21 @@ certification. If the function is approv + @code{GPG_ERR_NO_ERROR} (other restrictions might still apply). + Otherwise @code{GPG_ERR_NOT_SUPPORTED} is returned. + +-@item GCRYCTL_FIPS_SERVICE_INDICATOR_MAC; Arguments: enum gcry_mac_algos ++@item GCRYCTL_FIPS_SERVICE_INDICATOR_HASH; Arguments: enum gcry_md_algos + +-Check if the given MAC is approved under the current FIPS 140-3 +-certification. If the MAC is approved, this function returns +-@code{GPG_ERR_NO_ERROR}. Otherwise @code{GPG_ERR_NOT_SUPPORTED} ++Check if the given HASH is approved under the current FIPS 140-3 ++certification. If the HASH is approved, this function returns ++@code{GPS_ERR_NO_ERROR}. Otherwise @code{GPG_ERR_NOT_SUPPORTED} + is returned. + ++@item GCRYCTL_FIPS_SERVICE_INDICATOR_MAC; Arguments: enum gcry_mac_algos [, unsigned int] ++ ++Check if the given MAC is approved under the current FIPS 140-3 ++certification. The second parameter provides the keylen (if the ++algorithm supports different key sizes). If the MAC is approved, ++this function returns @code{GPS_ERR_NO_ERROR}. Otherwise ++@code{GPG_ERR_NOT_SUPPORTED} is returned. ++ + @item GCRYCTL_FIPS_SERVICE_INDICATOR_MD; Arguments: enum gcry_md_algos + + Check if the given message digest algorithm is approved under the current +Index: libgcrypt-1.11.0/src/fips.c +=================================================================== +--- libgcrypt-1.11.0.orig/src/fips.c ++++ libgcrypt-1.11.0/src/fips.c +@@ -378,31 +378,6 @@ _gcry_fips_indicator_cipher (va_list arg + } + } + +-int +-_gcry_fips_indicator_mac (va_list arg_ptr) +-{ +- enum gcry_mac_algos alg = va_arg (arg_ptr, enum gcry_mac_algos); +- +- switch (alg) +- { +- case GCRY_MAC_CMAC_AES: +- case GCRY_MAC_HMAC_SHA1: +- case GCRY_MAC_HMAC_SHA224: +- case GCRY_MAC_HMAC_SHA256: +- case GCRY_MAC_HMAC_SHA384: +- case GCRY_MAC_HMAC_SHA512: +- case GCRY_MAC_HMAC_SHA512_224: +- case GCRY_MAC_HMAC_SHA512_256: +- case GCRY_MAC_HMAC_SHA3_224: +- case GCRY_MAC_HMAC_SHA3_256: +- case GCRY_MAC_HMAC_SHA3_384: +- case GCRY_MAC_HMAC_SHA3_512: +- return GPG_ERR_NO_ERROR; +- default: +- return GPG_ERR_NOT_SUPPORTED; +- } +-} +- + /* FIPS approved curves, extracted from: + * cipher/ecc-curves.c:curve_aliases[] and domain_parms[]. */ + static const struct +@@ -602,6 +577,62 @@ _gcry_fips_indicator_pk_flags (va_list a + return GPG_ERR_NOT_SUPPORTED; + } + ++int ++_gcry_fips_indicator_hash (va_list arg_ptr) ++{ ++ enum gcry_md_algos alg = va_arg (arg_ptr, enum gcry_md_algos); ++ ++ switch (alg) ++ { ++ case GCRY_MD_SHA1: ++ case GCRY_MD_SHA224: ++ case GCRY_MD_SHA256: ++ case GCRY_MD_SHA384: ++ case GCRY_MD_SHA512: ++ case GCRY_MD_SHA512_224: ++ case GCRY_MD_SHA512_256: ++ case GCRY_MD_SHA3_224: ++ case GCRY_MD_SHA3_256: ++ case GCRY_MD_SHA3_384: ++ case GCRY_MD_SHA3_512: ++ case GCRY_MD_SHAKE128: ++ case GCRY_MD_SHAKE256: ++ return GPG_ERR_NO_ERROR; ++ default: ++ return GPG_ERR_NOT_SUPPORTED; ++ } ++} ++ ++int ++_gcry_fips_indicator_mac (va_list arg_ptr) ++{ ++ enum gcry_mac_algos alg = va_arg (arg_ptr, enum gcry_mac_algos); ++ unsigned int keylen = va_arg (arg_ptr, unsigned int); ++ ++ switch (alg) ++ { ++ case GCRY_MAC_HMAC_SHA1: ++ case GCRY_MAC_HMAC_SHA224: ++ case GCRY_MAC_HMAC_SHA256: ++ case GCRY_MAC_HMAC_SHA384: ++ case GCRY_MAC_HMAC_SHA512: ++ case GCRY_MAC_HMAC_SHA512_224: ++ case GCRY_MAC_HMAC_SHA512_256: ++ case GCRY_MAC_HMAC_SHA3_224: ++ case GCRY_MAC_HMAC_SHA3_256: ++ case GCRY_MAC_HMAC_SHA3_384: ++ case GCRY_MAC_HMAC_SHA3_512: ++ if (keylen >= 112) { ++ return GPG_ERR_NO_ERROR; ++ } ++ case GCRY_MAC_CMAC_AES: ++ if (keylen == 128 || keylen == 192 || keylen == 256) { ++ return GPG_ERR_NO_ERROR; ++ } ++ default: ++ return GPG_ERR_NOT_SUPPORTED; ++ } ++} + + /* This is a test on whether the library is in the error or + operational state. */ +Index: libgcrypt-1.11.0/src/g10lib.h +=================================================================== +--- libgcrypt-1.11.0.orig/src/g10lib.h ++++ libgcrypt-1.11.0/src/g10lib.h +@@ -469,6 +469,7 @@ void _gcry_fips_signal_error (const char + #endif + + int _gcry_fips_indicator_cipher (va_list arg_ptr); ++int _gcry_fips_indicator_hash (va_list arg_ptr); + int _gcry_fips_indicator_mac (va_list arg_ptr); + int _gcry_fips_indicator_md (va_list arg_ptr); + int _gcry_fips_indicator_kdf (va_list arg_ptr); +Index: libgcrypt-1.11.0/src/gcrypt.h.in +=================================================================== +--- libgcrypt-1.11.0.orig/src/gcrypt.h.in ++++ libgcrypt-1.11.0/src/gcrypt.h.in +@@ -336,7 +336,8 @@ enum gcry_ctl_cmds + GCRYCTL_FIPS_SERVICE_INDICATOR_MD = 86, + GCRYCTL_FIPS_SERVICE_INDICATOR_PK_FLAGS = 87, + GCRYCTL_MD_CUSTOMIZE = 88, +- GCRYCTL_FIPS_SERVICE_INDICATOR_PK = 89 ++ GCRYCTL_FIPS_SERVICE_INDICATOR_PK = 89, ++ GCRYCTL_FIPS_SERVICE_INDICATOR_HASH = 90 + }; + + /* Perform various operations defined by CMD. */ +Index: libgcrypt-1.11.0/src/global.c +=================================================================== +--- libgcrypt-1.11.0.orig/src/global.c ++++ libgcrypt-1.11.0/src/global.c +@@ -794,6 +794,12 @@ _gcry_vcontrol (enum gcry_ctl_cmds cmd, + rc = _gcry_fips_indicator_cipher (arg_ptr); + break; + ++ case GCRYCTL_FIPS_SERVICE_INDICATOR_HASH: ++ /* Get FIPS Service Indicator for a given HASH. Returns GPG_ERR_NO_ERROR ++ * if algorithm is allowed or GPG_ERR_NOT_SUPPORTED otherwise */ ++ rc = _gcry_fips_indicator_hash (arg_ptr); ++ break; ++ + case GCRYCTL_FIPS_SERVICE_INDICATOR_MAC: + /* Get FIPS Service Indicator for a given message authentication code. + * Returns GPG_ERR_NO_ERROR if algorithm is allowed or diff --git a/libgcrypt-FIPS-SLI-kdf-leylength.patch b/libgcrypt-FIPS-SLI-kdf-leylength.patch new file mode 100644 index 0000000..4a55513 --- /dev/null +++ b/libgcrypt-FIPS-SLI-kdf-leylength.patch @@ -0,0 +1,42 @@ +Index: libgcrypt-1.10.2/src/fips.c +=================================================================== +--- libgcrypt-1.10.2.orig/src/fips.c ++++ libgcrypt-1.10.2/src/fips.c +@@ -520,10 +520,15 @@ int + _gcry_fips_indicator_kdf (va_list arg_ptr) + { + enum gcry_kdf_algos alg = va_arg (arg_ptr, enum gcry_kdf_algos); ++ unsigned int keylen = 0; + + switch (alg) + { + case GCRY_KDF_PBKDF2: ++ keylen = va_arg (arg_ptr, unsigned int); ++ if (keylen < 112) { ++ return GPG_ERR_NOT_SUPPORTED; ++ } + return GPG_ERR_NO_ERROR; + default: + return GPG_ERR_NOT_SUPPORTED; +Index: libgcrypt-1.10.2/doc/gcrypt.texi +=================================================================== +--- libgcrypt-1.10.2.orig/doc/gcrypt.texi ++++ libgcrypt-1.10.2/doc/gcrypt.texi +@@ -970,12 +970,13 @@ is approved under the current FIPS 140-3 + combination is approved, this function returns @code{GPG_ERR_NO_ERROR}. + Otherwise @code{GPG_ERR_NOT_SUPPORTED} is returned. + +-@item GCRYCTL_FIPS_SERVICE_INDICATOR_KDF; Arguments: enum gcry_kdf_algos ++@item GCRYCTL_FIPS_SERVICE_INDICATOR_KDF; Arguments: enum gcry_kdf_algos [, unsigned int] + + Check if the given KDF is approved under the current FIPS 140-3 +-certification. If the KDF is approved, this function returns +-@code{GPG_ERR_NO_ERROR}. Otherwise @code{GPG_ERR_NOT_SUPPORTED} +-is returned. ++certification. The second parameter provides the keylength in bits. ++Keylength values of less that 112 bits are considered non-approved. ++If the KDF is approved, this function returns @code{GPG_ERR_NO_ERROR}. ++Otherwise @code{GPG_ERR_NOT_SUPPORTED} is returned. + + @item GCRYCTL_FIPS_SERVICE_INDICATOR_FUNCTION; Arguments: const char * + diff --git a/libgcrypt-FIPS-SLI-pk.patch b/libgcrypt-FIPS-SLI-pk.patch new file mode 100644 index 0000000..304fd37 --- /dev/null +++ b/libgcrypt-FIPS-SLI-pk.patch @@ -0,0 +1,177 @@ +Index: libgcrypt-1.11.0/src/fips.c +=================================================================== +--- libgcrypt-1.11.0.orig/src/fips.c ++++ libgcrypt-1.11.0/src/fips.c +@@ -38,6 +38,7 @@ + + #include "g10lib.h" + #include "cipher-proto.h" ++#include "cipher.h" + #include "../random/random.h" + + /* The states of the finite state machine used in fips mode. */ +@@ -400,6 +401,94 @@ _gcry_fips_indicator_mac (va_list arg_pt + default: + return GPG_ERR_NOT_SUPPORTED; + } ++} ++ ++/* FIPS approved curves, extracted from: ++ * cipher/ecc-curves.c:curve_aliases[] and domain_parms[]. */ ++static const struct ++{ ++ const char *name; /* Our name. */ ++ const char *other; /* Other name. */ ++} fips_approved_curve[] = ++ { ++ /* "NIST P-192" is non-approved if FIPS 140-3 */ ++ /* { "NIST P-192", "1.2.840.10045.3.1.1" }, /\* X9.62 OID *\/ */ ++ /* { "NIST P-192", "prime192v1" }, /\* X9.62 name. *\/ */ ++ /* { "NIST P-192", "secp192r1" }, /\* SECP name. *\/ */ ++ /* { "NIST P-192", "nistp192" }, /\* rfc5656. *\/ */ ++ ++ { "NIST P-224", "secp224r1" }, ++ { "NIST P-224", "1.3.132.0.33" }, /* SECP OID. */ ++ { "NIST P-224", "nistp224" }, /* rfc5656. */ ++ ++ { "NIST P-256", "1.2.840.10045.3.1.7" }, /* From NIST SP 800-78-1. */ ++ { "NIST P-256", "prime256v1" }, ++ { "NIST P-256", "secp256r1" }, ++ { "NIST P-256", "nistp256" }, /* rfc5656. */ ++ ++ { "NIST P-384", "secp384r1" }, ++ { "NIST P-384", "1.3.132.0.34" }, ++ { "NIST P-384", "nistp384" }, /* rfc5656. */ ++ ++ { "NIST P-521", "secp521r1" }, ++ { "NIST P-521", "1.3.132.0.35" }, ++ { "NIST P-521", "nistp521" }, /* rfc5656. */ ++ { NULL, NULL} ++ }; ++ ++enum pk_operation convert_from_pk_usage(unsigned int pk_usage) ++{ ++ switch (pk_usage) ++ { ++ case GCRY_PK_USAGE_SIGN: ++ return PUBKEY_OP_SIGN; ++ case GCRY_PK_USAGE_ENCR: ++ return PUBKEY_OP_ENCRYPT; ++ default: ++ return PUBKEY_OP_DECRYPT; ++ } ++} ++ ++int ++_gcry_fips_indicator_pk (va_list arg_ptr) ++{ ++ enum gcry_pk_algos alg = va_arg (arg_ptr, enum gcry_pk_algos); ++ enum pk_operation oper; ++ unsigned int keylen; ++ const char *curve_name; ++ ++ switch (alg) ++ { ++ case GCRY_PK_RSA: ++ case GCRY_PK_RSA_E: ++ case GCRY_PK_RSA_S: ++ oper = convert_from_pk_usage(va_arg (arg_ptr, unsigned int)); ++ switch (oper) ++ { ++ case PUBKEY_OP_ENCRYPT: ++ case PUBKEY_OP_DECRYPT: ++ return GPG_ERR_NOT_SUPPORTED; ++ default: ++ keylen = va_arg (arg_ptr, unsigned int); ++ if (keylen < 2048) ++ return GPG_ERR_NOT_SUPPORTED; ++ return GPG_ERR_NO_ERROR; ++ } ++ case GCRY_PK_ECC: ++ case GCRY_PK_ECDH: ++ case GCRY_PK_ECDSA: ++ curve_name = va_arg (arg_ptr, const char *); ++ for (int idx = 0; fips_approved_curve[idx].name; ++idx) ++ { ++ /* Check for the usual name and an alias. */ ++ if (!strcmp (curve_name, fips_approved_curve[idx].name) || ++ !strcmp (curve_name, fips_approved_curve[idx].other)) ++ return GPG_ERR_NO_ERROR; ++ } ++ return GPG_ERR_NOT_SUPPORTED; ++ default: ++ return GPG_ERR_NOT_SUPPORTED; ++ } + } + + int +Index: libgcrypt-1.11.0/src/gcrypt.h.in +=================================================================== +--- libgcrypt-1.11.0.orig/src/gcrypt.h.in ++++ libgcrypt-1.11.0/src/gcrypt.h.in +@@ -335,7 +335,8 @@ enum gcry_ctl_cmds + GCRYCTL_FIPS_SERVICE_INDICATOR_MAC = 85, + GCRYCTL_FIPS_SERVICE_INDICATOR_MD = 86, + GCRYCTL_FIPS_SERVICE_INDICATOR_PK_FLAGS = 87, +- GCRYCTL_MD_CUSTOMIZE = 88 ++ GCRYCTL_MD_CUSTOMIZE = 88, ++ GCRYCTL_FIPS_SERVICE_INDICATOR_PK = 89 + }; + + /* Perform various operations defined by CMD. */ +Index: libgcrypt-1.11.0/doc/gcrypt.texi +=================================================================== +--- libgcrypt-1.11.0.orig/doc/gcrypt.texi ++++ libgcrypt-1.11.0/doc/gcrypt.texi +@@ -1010,6 +1010,19 @@ Check if the given message digest algori + FIPS 140-3 certification. If the algorithm is approved, this function returns + @code{GPG_ERR_NO_ERROR}. Otherwise @code{GPG_ERR_NOT_SUPPORTED} is returned. + ++@item GCRYCTL_FIPS_SERVICE_INDICATOR_PK; Arguments: enum gcry_pk_algos [, constantsGCRY_PK_USAGE_ENCR or GCRY_PK_USAGE_SIGN, unsigned int (only for GCRY_PK_RSA)] [, const char * (only for GCRY_PK_ECC, GCRY_PK_ECDH or GCRY_PK_ECDSA)] ++ ++Check if the given asymmetric cipher is approved under the current ++FIPS 140-3 certification. For GCRY_PK_RSA, two additional parameter ++are required: first describes the purpose of the algorithm through one ++of the constants (GCRY_PK_USAGE_ENCR for encryption or decryption ++operations; GCRY_PK_USAGE_SIGN for sign or verify operations). Second ++one is the key length. For GCRY_PK_ECC, GCRY_PK_ECDH and ++GCRY_PK_ECDSA, only a single parameter is needed: the curve name or ++its alias as @code{const char *}. If the combination is approved, this ++function returns @code{GPG_ERR_NO_ERROR}. Otherwise ++@code{GPG_ERR_NOT_SUPPORTED} is returned. ++ + @item GCRYCTL_FIPS_SERVICE_INDICATOR_PK_FLAGS; Arguments: const char * + + Check if the given public key operation flag or s-expression object name is +Index: libgcrypt-1.11.0/src/g10lib.h +=================================================================== +--- libgcrypt-1.11.0.orig/src/g10lib.h ++++ libgcrypt-1.11.0/src/g10lib.h +@@ -473,6 +473,7 @@ int _gcry_fips_indicator_mac (va_list ar + int _gcry_fips_indicator_md (va_list arg_ptr); + int _gcry_fips_indicator_kdf (va_list arg_ptr); + int _gcry_fips_indicator_function (va_list arg_ptr); ++int _gcry_fips_indicator_pk (va_list arg_ptr); + int _gcry_fips_indicator_pk_flags (va_list arg_ptr); + + int _gcry_fips_is_operational (void); +Index: libgcrypt-1.11.0/src/global.c +=================================================================== +--- libgcrypt-1.11.0.orig/src/global.c ++++ libgcrypt-1.11.0/src/global.c +@@ -828,6 +828,15 @@ _gcry_vcontrol (enum gcry_ctl_cmds cmd, + rc = _gcry_fips_indicator_pk_flags (arg_ptr); + break; + ++ case GCRYCTL_FIPS_SERVICE_INDICATOR_PK: ++ /* Get FIPS Service Indicator for a given asymmetric algorithm. For ++ * GCRY_PK_RSA, an additional parameter for the operation mode is ++ * required. For ECC, ECDH and ECDSA, the additional parameter is the ++ * curve name or its alias. Returns GPG_ERR_NO_ERROR if the ++ * algorithm is allowed or GPG_ERR_NOT_SUPPORTED otherwise. */ ++ rc = _gcry_fips_indicator_pk (arg_ptr); ++ break; ++ + case PRIV_CTL_INIT_EXTRNG_TEST: /* Init external random test. */ + rc = GPG_ERR_NOT_SUPPORTED; + break; diff --git a/libgcrypt-FIPS-jitter-errorcodes.patch b/libgcrypt-FIPS-jitter-errorcodes.patch new file mode 100644 index 0000000..d6d314e --- /dev/null +++ b/libgcrypt-FIPS-jitter-errorcodes.patch @@ -0,0 +1,16 @@ +Index: libgcrypt-1.10.3/random/rndjent.c +=================================================================== +--- libgcrypt-1.10.3.orig/random/rndjent.c ++++ libgcrypt-1.10.3/random/rndjent.c +@@ -319,7 +319,10 @@ _gcry_rndjent_poll (void (*add)(const vo + jent_rng_totalcalls++; + rc = jent_read_entropy_safe (&jent_rng_collector, buffer, n); + if (rc < 0) +- break; ++ { ++ fips_signal_error ("jitter entropy failed"); ++ break; ++ } + /* We need to hash the output to conform to the BSI + * NTG.1 specs. */ + _gcry_md_hash_buffer (GCRY_MD_SHA256, buffer, buffer, rc); diff --git a/libgcrypt-FIPS-jitter-standalone.patch b/libgcrypt-FIPS-jitter-standalone.patch new file mode 100644 index 0000000..4f931c3 --- /dev/null +++ b/libgcrypt-FIPS-jitter-standalone.patch @@ -0,0 +1,183 @@ +Index: libgcrypt-1.10.3/random/Makefile.am +=================================================================== +--- libgcrypt-1.10.3.orig/random/Makefile.am ++++ libgcrypt-1.10.3/random/Makefile.am +@@ -21,7 +21,7 @@ + # Need to include ../src in addition to top_srcdir because gcrypt.h is + # a built header. + AM_CPPFLAGS = -I../src -I$(top_srcdir)/src +-AM_CFLAGS = $(GPG_ERROR_CFLAGS) ++AM_CFLAGS = $(GPG_ERROR_CFLAGS) -ljitterentropy + + noinst_LTLIBRARIES = librandom.la + +@@ -45,14 +45,7 @@ rndoldlinux.c \ + rndegd.c \ + rndunix.c \ + rndw32.c \ +-rndw32ce.c \ +-jitterentropy-gcd.c jitterentropy-gcd.h \ +-jitterentropy-health.c jitterentropy-health.h \ +-jitterentropy-noise.c jitterentropy-noise.h \ +-jitterentropy-sha3.c jitterentropy-sha3.h \ +-jitterentropy-timer.c jitterentropy-timer.h \ +-jitterentropy-base.h \ +-jitterentropy-base.c jitterentropy.h jitterentropy-base-user.h ++rndw32ce.c + + # The rndjent module needs to be compiled without optimization. */ + if ENABLE_O_FLAG_MUNGING +@@ -61,20 +54,8 @@ else + o_flag_munging = cat + endif + +-rndjent.o: $(srcdir)/rndjent.c jitterentropy-base-user.h \ +- $(srcdir)/jitterentropy-gcd.c $(srcdir)/jitterentropy-gcd.h \ +- $(srcdir)/jitterentropy-health.c $(srcdir)/jitterentropy-health.h \ +- $(srcdir)/jitterentropy-noise.c $(srcdir)/jitterentropy-noise.h \ +- $(srcdir)/jitterentropy-sha3.c $(srcdir)/jitterentropy-sha3.h \ +- $(srcdir)/jitterentropy-timer.c $(srcdir)/jitterentropy-timer.h \ +- $(srcdir)/jitterentropy-base.c $(srcdir)/jitterentropy.h ++rndjent.o: $(srcdir)/rndjent.c + `echo $(COMPILE) -c $(srcdir)/rndjent.c | $(o_flag_munging) ` + +-rndjent.lo: $(srcdir)/rndjent.c jitterentropy-base-user.h \ +- $(srcdir)/jitterentropy-gcd.c $(srcdir)/jitterentropy-gcd.h \ +- $(srcdir)/jitterentropy-health.c $(srcdir)/jitterentropy-health.h \ +- $(srcdir)/jitterentropy-noise.c $(srcdir)/jitterentropy-noise.h \ +- $(srcdir)/jitterentropy-sha3.c $(srcdir)/jitterentropy-sha3.h \ +- $(srcdir)/jitterentropy-timer.c $(srcdir)/jitterentropy-timer.h \ +- $(srcdir)/jitterentropy-base.c $(srcdir)/jitterentropy.h ++rndjent.lo: $(srcdir)/rndjent.c + `echo $(LTCOMPILE) -c $(srcdir)/rndjent.c | $(o_flag_munging) ` +Index: libgcrypt-1.10.3/random/rndjent.c +=================================================================== +--- libgcrypt-1.10.3.orig/random/rndjent.c ++++ libgcrypt-1.10.3/random/rndjent.c +@@ -94,17 +94,12 @@ + * jitterentropy-user-base.h file. */ + + /* Tell jitterentropy* that all functions shall be static. */ +-#define JENT_PRIVATE_COMPILE 1 ++#undef JENT_PRIVATE_COMPILE + +-#include "jitterentropy-base.c" + #ifdef JENT_CONF_ENABLE_INTERNAL_TIMER + #include + #endif /* JENT_CONF_ENABLE_INTERNAL_TIMER */ +-#include "jitterentropy-gcd.c" +-#include "jitterentropy-health.c" +-#include "jitterentropy-noise.c" +-#include "jitterentropy-sha3.c" +-#include "jitterentropy-timer.c" ++#include + + /* This is the lock we use to serialize access to this RNG. The extra + * integer variable is only used to check the locking state; that is, +Index: libgcrypt-1.10.3/random/Makefile.in +=================================================================== +--- libgcrypt-1.10.3.orig/random/Makefile.in ++++ libgcrypt-1.10.3/random/Makefile.in +@@ -147,12 +147,7 @@ am__v_at_1 = + DEFAULT_INCLUDES = -I.@am__isrc@ -I$(top_builddir) + depcomp = $(SHELL) $(top_srcdir)/build-aux/depcomp + am__maybe_remake_depfiles = depfiles +-am__depfiles_remade = ./$(DEPDIR)/jitterentropy-base.Plo \ +- ./$(DEPDIR)/jitterentropy-gcd.Plo \ +- ./$(DEPDIR)/jitterentropy-health.Plo \ +- ./$(DEPDIR)/jitterentropy-noise.Plo \ +- ./$(DEPDIR)/jitterentropy-sha3.Plo \ +- ./$(DEPDIR)/jitterentropy-timer.Plo \ ++am__depfiles_remade = \ + ./$(DEPDIR)/random-csprng.Plo ./$(DEPDIR)/random-drbg.Plo \ + ./$(DEPDIR)/random-system.Plo ./$(DEPDIR)/random.Plo \ + ./$(DEPDIR)/rndegd.Plo ./$(DEPDIR)/rndgetentropy.Plo \ +@@ -378,7 +373,7 @@ top_srcdir = @top_srcdir@ + # Need to include ../src in addition to top_srcdir because gcrypt.h is + # a built header. + AM_CPPFLAGS = -I../src -I$(top_srcdir)/src +-AM_CFLAGS = $(GPG_ERROR_CFLAGS) ++AM_CFLAGS = $(GPG_ERROR_CFLAGS) -ljitterentropy + noinst_LTLIBRARIES = librandom.la + GCRYPT_MODULES = @GCRYPT_RANDOM@ + librandom_la_DEPENDENCIES = $(GCRYPT_MODULES) +@@ -398,14 +393,7 @@ rndoldlinux.c \ + rndegd.c \ + rndunix.c \ + rndw32.c \ +-rndw32ce.c \ +-jitterentropy-gcd.c jitterentropy-gcd.h \ +-jitterentropy-health.c jitterentropy-health.h \ +-jitterentropy-noise.c jitterentropy-noise.h \ +-jitterentropy-sha3.c jitterentropy-sha3.h \ +-jitterentropy-timer.c jitterentropy-timer.h \ +-jitterentropy-base.h \ +-jitterentropy-base.c jitterentropy.h jitterentropy-base-user.h ++rndw32ce.c + + @ENABLE_O_FLAG_MUNGING_FALSE@o_flag_munging = cat + +@@ -465,12 +453,6 @@ mostlyclean-compile: + distclean-compile: + -rm -f *.tab.c + +-@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/jitterentropy-base.Plo@am__quote@ # am--include-marker +-@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/jitterentropy-gcd.Plo@am__quote@ # am--include-marker +-@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/jitterentropy-health.Plo@am__quote@ # am--include-marker +-@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/jitterentropy-noise.Plo@am__quote@ # am--include-marker +-@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/jitterentropy-sha3.Plo@am__quote@ # am--include-marker +-@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/jitterentropy-timer.Plo@am__quote@ # am--include-marker + @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/random-csprng.Plo@am__quote@ # am--include-marker + @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/random-drbg.Plo@am__quote@ # am--include-marker + @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/random-system.Plo@am__quote@ # am--include-marker +@@ -641,12 +623,6 @@ clean-am: clean-generic clean-libtool cl + mostlyclean-am + + distclean: distclean-am +- -rm -f ./$(DEPDIR)/jitterentropy-base.Plo +- -rm -f ./$(DEPDIR)/jitterentropy-gcd.Plo +- -rm -f ./$(DEPDIR)/jitterentropy-health.Plo +- -rm -f ./$(DEPDIR)/jitterentropy-noise.Plo +- -rm -f ./$(DEPDIR)/jitterentropy-sha3.Plo +- -rm -f ./$(DEPDIR)/jitterentropy-timer.Plo + -rm -f ./$(DEPDIR)/random-csprng.Plo + -rm -f ./$(DEPDIR)/random-drbg.Plo + -rm -f ./$(DEPDIR)/random-system.Plo +@@ -704,12 +680,6 @@ install-ps-am: + installcheck-am: + + maintainer-clean: maintainer-clean-am +- -rm -f ./$(DEPDIR)/jitterentropy-base.Plo +- -rm -f ./$(DEPDIR)/jitterentropy-gcd.Plo +- -rm -f ./$(DEPDIR)/jitterentropy-health.Plo +- -rm -f ./$(DEPDIR)/jitterentropy-noise.Plo +- -rm -f ./$(DEPDIR)/jitterentropy-sha3.Plo +- -rm -f ./$(DEPDIR)/jitterentropy-timer.Plo + -rm -f ./$(DEPDIR)/random-csprng.Plo + -rm -f ./$(DEPDIR)/random-drbg.Plo + -rm -f ./$(DEPDIR)/random-system.Plo +@@ -759,22 +729,10 @@ uninstall-am: + .PRECIOUS: Makefile + + +-rndjent.o: $(srcdir)/rndjent.c jitterentropy-base-user.h \ +- $(srcdir)/jitterentropy-gcd.c $(srcdir)/jitterentropy-gcd.h \ +- $(srcdir)/jitterentropy-health.c $(srcdir)/jitterentropy-health.h \ +- $(srcdir)/jitterentropy-noise.c $(srcdir)/jitterentropy-noise.h \ +- $(srcdir)/jitterentropy-sha3.c $(srcdir)/jitterentropy-sha3.h \ +- $(srcdir)/jitterentropy-timer.c $(srcdir)/jitterentropy-timer.h \ +- $(srcdir)/jitterentropy-base.c $(srcdir)/jitterentropy.h ++rndjent.o: $(srcdir)/rndjent.c + `echo $(COMPILE) -c $(srcdir)/rndjent.c | $(o_flag_munging) ` + +-rndjent.lo: $(srcdir)/rndjent.c jitterentropy-base-user.h \ +- $(srcdir)/jitterentropy-gcd.c $(srcdir)/jitterentropy-gcd.h \ +- $(srcdir)/jitterentropy-health.c $(srcdir)/jitterentropy-health.h \ +- $(srcdir)/jitterentropy-noise.c $(srcdir)/jitterentropy-noise.h \ +- $(srcdir)/jitterentropy-sha3.c $(srcdir)/jitterentropy-sha3.h \ +- $(srcdir)/jitterentropy-timer.c $(srcdir)/jitterentropy-timer.h \ +- $(srcdir)/jitterentropy-base.c $(srcdir)/jitterentropy.h ++rndjent.lo: $(srcdir)/rndjent.c + `echo $(LTCOMPILE) -c $(srcdir)/rndjent.c | $(o_flag_munging) ` + + # Tell versions [3.59,3.63) of GNU make to not export all variables. diff --git a/libgcrypt-FIPS-jitter-whole-entropy.patch b/libgcrypt-FIPS-jitter-whole-entropy.patch new file mode 100644 index 0000000..6c16472 --- /dev/null +++ b/libgcrypt-FIPS-jitter-whole-entropy.patch @@ -0,0 +1,41 @@ +Index: libgcrypt-1.10.3/random/rndgetentropy.c +=================================================================== +--- libgcrypt-1.10.3.orig/random/rndgetentropy.c ++++ libgcrypt-1.10.3/random/rndgetentropy.c +@@ -53,16 +53,30 @@ _gcry_rndgetentropy_gather_random (void + + /* When using a blocking random generator try to get some entropy + * from the jitter based RNG. In this case we take up to 50% of the +- * remaining requested bytes. */ ++ * remaining requested bytes. In FIPS mode, we get all the entropy ++ * from the jitter RNG. */ + if (level >= GCRY_VERY_STRONG_RANDOM) + { + size_t n; + +- n = _gcry_rndjent_poll (add, origin, length/2); +- if (n > length/2) +- n = length/2; +- if (length > 1) +- length -= n; ++ /* In FIPS mode, use the whole length of the entropy buffer from ++ * Jitter RNG */ ++ if (fips_mode ()) ++ { ++ n = _gcry_rndjent_poll (add, origin, length); ++ if (n != length) ++ fips_signal_error ("jitter entropy failed"); ++ else ++ length = 0; ++ } ++ else ++ { ++ n = _gcry_rndjent_poll (add, origin, length/2); ++ if (n > length/2) ++ n = length/2; ++ if (length > 1) ++ length -= n; ++ } + } + + /* Enter the loop. */ diff --git a/libgcrypt-FIPS-rndjent_poll.patch b/libgcrypt-FIPS-rndjent_poll.patch new file mode 100644 index 0000000..f837842 --- /dev/null +++ b/libgcrypt-FIPS-rndjent_poll.patch @@ -0,0 +1,114 @@ +Index: libgcrypt-1.10.0/random/rndoldlinux.c +=================================================================== +--- libgcrypt-1.10.0.orig/random/rndoldlinux.c ++++ libgcrypt-1.10.0/random/rndoldlinux.c +@@ -132,7 +132,7 @@ _gcry_rndoldlinux_gather_random (void (* + volatile pid_t apid; + int fd; + int n; +- byte buffer[768]; ++ byte buffer[256]; + size_t n_hw; + size_t want = length; + size_t last_so_far = 0; +@@ -187,26 +187,43 @@ _gcry_rndoldlinux_gather_random (void (* + my_pid = apid; + } + ++ if (fips_mode()) ++ { ++ if (level >= GCRY_VERY_STRONG_RANDOM) ++ { ++ size_t n; + +- /* First read from a hardware source. Note that _gcry_rndhw_poll_slow lets +- it account only for up to 50% (or 25% for RDRAND) of the requested +- bytes. */ +- n_hw = _gcry_rndhw_poll_slow (add, origin, length); +- if (length > 1) +- length -= n_hw; +- +- /* When using a blocking random generator try to get some entropy +- * from the jitter based RNG. In this case we take up to 50% of the +- * remaining requested bytes. */ +- if (level >= GCRY_VERY_STRONG_RANDOM) +- { +- n_hw = _gcry_rndjent_poll (add, origin, length/2); +- if (n_hw > length/2) +- n_hw = length/2; ++ n = _gcry_rndjent_poll (add, origin, length); ++ if (n == 0) ++ log_fatal ("unexpected error from rndjent: %s\n", ++ strerror (errno)); ++ if (n > length) ++ n = length; ++ if (length > 1) ++ length -= n; ++ } ++ } ++ else ++ { ++ /* First read from a hardware source. Note that _gcry_rndhw_poll_slow lets ++ it account only for up to 50% (or 25% for RDRAND) of the requested ++ bytes. */ ++ n_hw = _gcry_rndhw_poll_slow (add, origin, length); + if (length > 1) + length -= n_hw; +- } + ++ /* When using a blocking random generator try to get some entropy ++ * from the jitter based RNG. In this case we take up to 50% of the ++ * remaining requested bytes. */ ++ if (level >= GCRY_VERY_STRONG_RANDOM) ++ { ++ n_hw = _gcry_rndjent_poll (add, origin, length/2); ++ if (n_hw > length/2) ++ n_hw = length/2; ++ if (length > 1) ++ length -= n_hw; ++ } ++ } + + /* Open the requested device. The first time a device is to be + opened we fail with a fatal error if the device does not exists. +@@ -262,8 +279,6 @@ _gcry_rndoldlinux_gather_random (void (* + do + { + nbytes = length < sizeof(buffer)? length : sizeof(buffer); +- if (nbytes > 256) +- nbytes = 256; + _gcry_pre_syscall (); + ret = getentropy (buffer, nbytes); + _gcry_post_syscall (); +Index: libgcrypt-1.10.0/random/rndjent.c +=================================================================== +--- libgcrypt-1.10.0.orig/random/rndjent.c ++++ libgcrypt-1.10.0/random/rndjent.c +@@ -279,13 +279,24 @@ _gcry_rndjent_poll (void (*add)(const vo + if (!jent_rng_is_initialized) + { + /* Auto-initialize. */ +- jent_rng_is_initialized = 1; + jent_entropy_collector_free (jent_rng_collector); + jent_rng_collector = NULL; + if ( !(_gcry_random_read_conf () & RANDOM_CONF_DISABLE_JENT)) + { +- if (!jent_entropy_init ()) +- jent_rng_collector = jent_entropy_collector_alloc (1, 0); ++ if (!jent_entropy_init_ex (1, 0)) ++ { ++ jent_rng_collector = jent_entropy_collector_alloc (1, 0); ++ jent_rng_is_initialized = 1; ++ } ++ } ++ } ++ ++ if (!jent_rng_collector) ++ { ++ if (!jent_entropy_init_ex (1, 0)) ++ { ++ jent_rng_collector = jent_entropy_collector_alloc (1, 0); ++ jent_rng_is_initialized = 1; + } + } + diff --git a/libgcrypt-jitterentropy-3.4.0.patch b/libgcrypt-jitterentropy-3.4.0.patch new file mode 100644 index 0000000..dbb77ba --- /dev/null +++ b/libgcrypt-jitterentropy-3.4.0.patch @@ -0,0 +1,618 @@ +Index: libgcrypt-1.10.0/random/jitterentropy-base.c +=================================================================== +--- libgcrypt-1.10.0.orig/random/jitterentropy-base.c ++++ libgcrypt-1.10.0/random/jitterentropy-base.c +@@ -42,7 +42,7 @@ + * require consumer to be updated (as long as this number + * is zero, the API is not considered stable and can + * change without a bump of the major version) */ +-#define MINVERSION 3 /* API compatible, ABI may change, functional ++#define MINVERSION 4 /* API compatible, ABI may change, functional + * enhancements only, consumer can be left unchanged if + * enhancements are not considered */ + #define PATCHLEVEL 0 /* API / ABI compatible, no functional changes, no +@@ -200,29 +200,38 @@ ssize_t jent_read_entropy(struct rand_da + tocopy = (DATA_SIZE_BITS / 8); + else + tocopy = len; +- memcpy(p, &ec->data, tocopy); ++ ++ jent_read_random_block(ec, p, tocopy); + + len -= tocopy; + p += tocopy; + } + + /* +- * To be on the safe side, we generate one more round of entropy +- * which we do not give out to the caller. That round shall ensure +- * that in case the calling application crashes, memory dumps, pages +- * out, or due to the CPU Jitter RNG lingering in memory for long +- * time without being moved and an attacker cracks the application, +- * all he reads in the entropy pool is a value that is NEVER EVER +- * being used for anything. Thus, he does NOT see the previous value +- * that was returned to the caller for cryptographic purposes. ++ * Enhanced backtracking support: At this point, the hash state ++ * contains the digest of the previous Jitter RNG collection round ++ * which is inserted there by jent_read_random_block with the SHA ++ * update operation. At the current code location we completed ++ * one request for a caller and we do not know how long it will ++ * take until a new request is sent to us. To guarantee enhanced ++ * backtracking resistance at this point (i.e. ensure that an attacker ++ * cannot obtain information about prior random numbers we generated), ++ * but still stirring the hash state with old data the Jitter RNG ++ * obtains a new message digest from its state and re-inserts it. ++ * After this operation, the Jitter RNG state is still stirred with ++ * the old data, but an attacker who gets access to the memory after ++ * this point cannot deduce the random numbers produced by the ++ * Jitter RNG prior to this point. + */ + /* +- * If we use secured memory, do not use that precaution as the secure +- * memory protects the entropy pool. Moreover, note that using this +- * call reduces the speed of the RNG by up to half ++ * If we use secured memory, where backtracking support may not be ++ * needed because the state is protected in a different method, ++ * it is permissible to drop this support. But strongly weigh the ++ * pros and cons considering that the SHA3 operation is not that ++ * expensive. + */ + #ifndef JENT_CPU_JITTERENTROPY_SECURE_MEMORY +- jent_random_data(ec); ++ jent_read_random_block(ec, NULL, 0); + #endif + + err: +@@ -379,6 +388,7 @@ static struct rand_data + *jent_entropy_collector_alloc_internal(unsigned int osr, unsigned int flags) + { + struct rand_data *entropy_collector; ++ uint32_t memsize = 0; + + /* + * Requesting disabling and forcing of internal timer +@@ -405,7 +415,7 @@ static struct rand_data + return NULL; + + if (!(flags & JENT_DISABLE_MEMORY_ACCESS)) { +- uint32_t memsize = jent_memsize(flags); ++ memsize = jent_memsize(flags); + + entropy_collector->mem = _gcry_calloc (1, memsize); + +@@ -431,13 +441,19 @@ static struct rand_data + entropy_collector->memaccessloops = JENT_MEMORY_ACCESSLOOPS; + } + ++ if (sha3_alloc(&entropy_collector->hash_state)) ++ goto err; ++ ++ /* Initialize the hash state */ ++ sha3_256_init(entropy_collector->hash_state); ++ + /* verify and set the oversampling rate */ + if (osr < JENT_MIN_OSR) + osr = JENT_MIN_OSR; + entropy_collector->osr = osr; + entropy_collector->flags = flags; + +- if (jent_fips_enabled() || (flags & JENT_FORCE_FIPS)) ++ if ((flags & JENT_FORCE_FIPS) || jent_fips_enabled()) + entropy_collector->fips_enabled = 1; + + /* Initialize the APT */ +@@ -469,7 +485,7 @@ static struct rand_data + + err: + if (entropy_collector->mem != NULL) +- jent_zfree(entropy_collector->mem, JENT_MEMORY_SIZE); ++ jent_zfree(entropy_collector->mem, memsize); + jent_zfree(entropy_collector, sizeof(struct rand_data)); + return NULL; + } +@@ -511,6 +527,7 @@ JENT_PRIVATE_STATIC + void jent_entropy_collector_free(struct rand_data *entropy_collector) + { + if (entropy_collector != NULL) { ++ sha3_dealloc(entropy_collector->hash_state); + jent_notime_disable(entropy_collector); + if (entropy_collector->mem != NULL) { + jent_zfree(entropy_collector->mem, +@@ -664,6 +681,7 @@ static inline int jent_entropy_init_comm + int ret; + + jent_notime_block_switch(); ++ jent_health_cb_block_switch(); + + if (sha3_tester()) + return EHASH; +@@ -710,6 +728,8 @@ int jent_entropy_init_ex(unsigned int os + if (ret) + return ret; + ++ ret = ENOTIME; ++ + /* Test without internal timer unless caller does not want it */ + if (!(flags & JENT_FORCE_INTERNAL_TIMER)) + ret = jent_time_entropy_init(osr, +@@ -732,3 +752,9 @@ int jent_entropy_switch_notime_impl(stru + return jent_notime_switch(new_thread); + } + #endif ++ ++JENT_PRIVATE_STATIC ++int jent_set_fips_failure_callback(jent_fips_failure_cb cb) ++{ ++ return jent_set_fips_failure_callback_internal(cb); ++} +Index: libgcrypt-1.10.0/random/jitterentropy-gcd.c +=================================================================== +--- libgcrypt-1.10.0.orig/random/jitterentropy-gcd.c ++++ libgcrypt-1.10.0/random/jitterentropy-gcd.c +@@ -113,12 +113,8 @@ int jent_gcd_analyze(uint64_t *delta_his + goto out; + } + +- /* +- * Ensure that we have variations in the time stamp below 100 for at +- * least 10% of all checks -- on some platforms, the counter increments +- * in multiples of 100, but not always +- */ +- if (running_gcd >= 100) { ++ /* Set a sensible maximum value. */ ++ if (running_gcd >= UINT32_MAX / 2) { + ret = ECOARSETIME; + goto out; + } +Index: libgcrypt-1.10.0/random/jitterentropy-health.c +=================================================================== +--- libgcrypt-1.10.0.orig/random/jitterentropy-health.c ++++ libgcrypt-1.10.0/random/jitterentropy-health.c +@@ -19,9 +19,24 @@ + * DAMAGE. + */ + +-#include "jitterentropy.h" + #include "jitterentropy-health.h" + ++static jent_fips_failure_cb fips_cb = NULL; ++static int jent_health_cb_switch_blocked = 0; ++ ++void jent_health_cb_block_switch(void) ++{ ++ jent_health_cb_switch_blocked = 1; ++} ++ ++int jent_set_fips_failure_callback_internal(jent_fips_failure_cb cb) ++{ ++ if (jent_health_cb_switch_blocked) ++ return -EAGAIN; ++ fips_cb = cb; ++ return 0; ++} ++ + /*************************************************************************** + * Lag Predictor Test + * +@@ -434,5 +449,9 @@ unsigned int jent_health_failure(struct + if (!ec->fips_enabled) + return 0; + ++ if (fips_cb && ec->health_failure) { ++ fips_cb(ec, ec->health_failure); ++ } ++ + return ec->health_failure; + } +Index: libgcrypt-1.10.0/random/jitterentropy-health.h +=================================================================== +--- libgcrypt-1.10.0.orig/random/jitterentropy-health.h ++++ libgcrypt-1.10.0/random/jitterentropy-health.h +@@ -20,11 +20,16 @@ + #ifndef JITTERENTROPY_HEALTH_H + #define JITTERENTROPY_HEALTH_H + ++#include "jitterentropy.h" ++ + #ifdef __cplusplus + extern "C" + { + #endif + ++void jent_health_cb_block_switch(void); ++int jent_set_fips_failure_callback_internal(jent_fips_failure_cb cb); ++ + static inline uint64_t jent_delta(uint64_t prev, uint64_t next) + { + return (next - prev); +Index: libgcrypt-1.10.0/random/jitterentropy-noise.c +=================================================================== +--- libgcrypt-1.10.0.orig/random/jitterentropy-noise.c ++++ libgcrypt-1.10.0/random/jitterentropy-noise.c +@@ -33,7 +33,7 @@ + * Update of the loop count used for the next round of + * an entropy collection. + * +- * @ec [in] entropy collector struct -- may be NULL ++ * @ec [in] entropy collector struct + * @bits [in] is the number of low bits of the timer to consider + * @min [in] is the number of bits we shift the timer value to the right at + * the end to make sure we have a guaranteed minimum value +@@ -61,16 +61,13 @@ static uint64_t jent_loop_shuffle(struct + * Mix the current state of the random number into the shuffle + * calculation to balance that shuffle a bit more. + */ +- if (ec) { +- jent_get_nstime_internal(ec, &time); +- time ^= ec->data[0]; +- } ++ jent_get_nstime_internal(ec, &time); + + /* + * We fold the time value as much as possible to ensure that as many + * bits of the time stamp are included as possible. + */ +- for (i = 0; ((DATA_SIZE_BITS + bits - 1) / bits) > i; i++) { ++ for (i = 0; (((sizeof(time) << 3) + bits - 1) / bits) > i; i++) { + shuffle ^= time & mask; + time = time >> bits; + } +@@ -91,11 +88,11 @@ static uint64_t jent_loop_shuffle(struct + * This function injects the individual bits of the time value into the + * entropy pool using a hash. + * +- * @ec [in] entropy collector struct -- may be NULL +- * @time [in] time stamp to be injected ++ * @ec [in] entropy collector struct ++ * @time [in] time delta to be injected + * @loop_cnt [in] if a value not equal to 0 is set, use the given value as + * number of loops to perform the hash operation +- * @stuck [in] Is the time stamp identified as stuck? ++ * @stuck [in] Is the time delta identified as stuck? + * + * Output: + * updated hash context +@@ -104,17 +101,19 @@ static void jent_hash_time(struct rand_d + uint64_t loop_cnt, unsigned int stuck) + { + HASH_CTX_ON_STACK(ctx); +- uint8_t itermediary[SHA3_256_SIZE_DIGEST]; ++ uint8_t intermediary[SHA3_256_SIZE_DIGEST]; + uint64_t j = 0; +- uint64_t hash_loop_cnt; + #define MAX_HASH_LOOP 3 + #define MIN_HASH_LOOP 0 + + /* Ensure that macros cannot overflow jent_loop_shuffle() */ + BUILD_BUG_ON((MAX_HASH_LOOP + MIN_HASH_LOOP) > 63); +- hash_loop_cnt = ++ uint64_t hash_loop_cnt = + jent_loop_shuffle(ec, MAX_HASH_LOOP, MIN_HASH_LOOP); + ++ /* Use the memset to shut up valgrind */ ++ memset(intermediary, 0, sizeof(intermediary)); ++ + sha3_256_init(&ctx); + + /* +@@ -125,35 +124,54 @@ static void jent_hash_time(struct rand_d + hash_loop_cnt = loop_cnt; + + /* +- * This loop basically slows down the SHA-3 operation depending +- * on the hash_loop_cnt. Each iteration of the loop generates the +- * same result. ++ * This loop fills a buffer which is injected into the entropy pool. ++ * The main reason for this loop is to execute something over which we ++ * can perform a timing measurement. The injection of the resulting ++ * data into the pool is performed to ensure the result is used and ++ * the compiler cannot optimize the loop away in case the result is not ++ * used at all. Yet that data is considered "additional information" ++ * considering the terminology from SP800-90A without any entropy. ++ * ++ * Note, it does not matter which or how much data you inject, we are ++ * interested in one Keccack1600 compression operation performed with ++ * the sha3_final. + */ + for (j = 0; j < hash_loop_cnt; j++) { +- sha3_update(&ctx, ec->data, SHA3_256_SIZE_DIGEST); +- sha3_update(&ctx, (uint8_t *)&time, sizeof(uint64_t)); ++ sha3_update(&ctx, intermediary, sizeof(intermediary)); ++ sha3_update(&ctx, (uint8_t *)&ec->rct_count, ++ sizeof(ec->rct_count)); ++ sha3_update(&ctx, (uint8_t *)&ec->apt_cutoff, ++ sizeof(ec->apt_cutoff)); ++ sha3_update(&ctx, (uint8_t *)&ec->apt_observations, ++ sizeof(ec->apt_observations)); ++ sha3_update(&ctx, (uint8_t *)&ec->apt_count, ++ sizeof(ec->apt_count)); ++ sha3_update(&ctx,(uint8_t *) &ec->apt_base, ++ sizeof(ec->apt_base)); + sha3_update(&ctx, (uint8_t *)&j, sizeof(uint64_t)); ++ sha3_final(&ctx, intermediary); ++ } + +- /* +- * If the time stamp is stuck, do not finally insert the value +- * into the entropy pool. Although this operation should not do +- * any harm even when the time stamp has no entropy, SP800-90B +- * requires that any conditioning operation to have an identical +- * amount of input data according to section 3.1.5. +- */ ++ /* ++ * Inject the data from the previous loop into the pool. This data is ++ * not considered to contain any entropy, but it stirs the pool a bit. ++ */ ++ sha3_update(ec->hash_state, intermediary, sizeof(intermediary)); + +- /* +- * The sha3_final operations re-initialize the context for the +- * next loop iteration. +- */ +- if (stuck || (j < hash_loop_cnt - 1)) +- sha3_final(&ctx, itermediary); +- else +- sha3_final(&ctx, ec->data); +- } ++ /* ++ * Insert the time stamp into the hash context representing the pool. ++ * ++ * If the time stamp is stuck, do not finally insert the value into the ++ * entropy pool. Although this operation should not do any harm even ++ * when the time stamp has no entropy, SP800-90B requires that any ++ * conditioning operation to have an identical amount of input data ++ * according to section 3.1.5. ++ */ ++ if (!stuck) ++ sha3_update(ec->hash_state, (uint8_t *)&time, sizeof(uint64_t)); + + jent_memset_secure(&ctx, SHA_MAX_CTX_SIZE); +- jent_memset_secure(itermediary, sizeof(itermediary)); ++ jent_memset_secure(intermediary, sizeof(intermediary)); + } + + #define MAX_ACC_LOOP_BIT 7 +@@ -184,13 +202,12 @@ static inline uint32_t xoshiro128starsta + + static void jent_memaccess(struct rand_data *ec, uint64_t loop_cnt) + { +- uint64_t i = 0; ++ uint64_t i = 0, time = 0; + union { + uint32_t u[4]; + uint8_t b[sizeof(uint32_t) * 4]; + } prngState = { .u = {0x8e93eec0, 0xce65608a, 0xa8d46b46, 0xe83cef69} }; + uint32_t addressMask; +- uint64_t acc_loop_cnt; + + if (NULL == ec || NULL == ec->mem) + return; +@@ -199,7 +216,7 @@ static void jent_memaccess(struct rand_d + + /* Ensure that macros cannot overflow jent_loop_shuffle() */ + BUILD_BUG_ON((MAX_ACC_LOOP_BIT + MIN_ACC_LOOP_BIT) > 63); +- acc_loop_cnt = ++ uint64_t acc_loop_cnt = + jent_loop_shuffle(ec, MAX_ACC_LOOP_BIT, MIN_ACC_LOOP_BIT); + + /* +@@ -213,8 +230,10 @@ static void jent_memaccess(struct rand_d + * "per-update: timing, it gets you mostly independent "per-update" + * timing, so we can now benefit from the Central Limit Theorem! + */ +- for (i = 0; i < sizeof(prngState); i++) +- prngState.b[i] ^= ec->data[i]; ++ for (i = 0; i < sizeof(prngState); i++) { ++ jent_get_nstime_internal(ec, &time); ++ prngState.b[i] ^= (uint8_t)(time & 0xff); ++ } + + /* + * testing purposes -- allow test app to set the counter, not +@@ -358,21 +377,21 @@ unsigned int jent_measure_jitter(struct + + /** + * Generator of one 256 bit random number +- * Function fills rand_data->data ++ * Function fills rand_data->hash_state + * + * @ec [in] Reference to entropy collector + */ + void jent_random_data(struct rand_data *ec) + { +- unsigned int k = 0, safety_factor = ENTROPY_SAFETY_FACTOR; ++ unsigned int k = 0, safety_factor = 0; + +- if (!ec->fips_enabled) +- safety_factor = 0; ++ if (ec->fips_enabled) ++ safety_factor = ENTROPY_SAFETY_FACTOR; + + /* priming of the ->prev_time value */ + jent_measure_jitter(ec, 0, NULL); + +- while (1) { ++ while (!jent_health_failure(ec)) { + /* If a stuck measurement is received, repeat measurement */ + if (jent_measure_jitter(ec, 0, NULL)) + continue; +@@ -385,3 +404,22 @@ void jent_random_data(struct rand_data * + break; + } + } ++ ++void jent_read_random_block(struct rand_data *ec, char *dst, size_t dst_len) ++{ ++ uint8_t jent_block[SHA3_256_SIZE_DIGEST]; ++ ++ BUILD_BUG_ON(SHA3_256_SIZE_DIGEST != (DATA_SIZE_BITS / 8)); ++ ++ /* The final operation automatically re-initializes the ->hash_state */ ++ sha3_final(ec->hash_state, jent_block); ++ if (dst_len) ++ memcpy(dst, jent_block, dst_len); ++ ++ /* ++ * Stir the new state with the data from the old state - the digest ++ * of the old data is not considered to have entropy. ++ */ ++ sha3_update(ec->hash_state, jent_block, sizeof(jent_block)); ++ jent_memset_secure(jent_block, sizeof(jent_block)); ++} +Index: libgcrypt-1.10.0/random/jitterentropy-noise.h +=================================================================== +--- libgcrypt-1.10.0.orig/random/jitterentropy-noise.h ++++ libgcrypt-1.10.0/random/jitterentropy-noise.h +@@ -31,6 +31,7 @@ unsigned int jent_measure_jitter(struct + uint64_t loop_cnt, + uint64_t *ret_current_delta); + void jent_random_data(struct rand_data *ec); ++void jent_read_random_block(struct rand_data *ec, char *dst, size_t dst_len); + + #ifdef __cplusplus + } +Index: libgcrypt-1.10.0/random/jitterentropy-sha3.c +=================================================================== +--- libgcrypt-1.10.0.orig/random/jitterentropy-sha3.c ++++ libgcrypt-1.10.0/random/jitterentropy-sha3.c +@@ -19,6 +19,7 @@ + */ + + #include "jitterentropy-sha3.h" ++#include "jitterentropy.h" + + /*************************************************************************** + * Message Digest Implementation +@@ -380,3 +381,23 @@ int sha3_tester(void) + + return 0; + } ++ ++int sha3_alloc(void **hash_state) ++{ ++ struct sha_ctx *tmp; ++ ++ tmp = jent_zalloc(SHA_MAX_CTX_SIZE); ++ if (!tmp) ++ return 1; ++ ++ *hash_state = tmp; ++ ++ return 0; ++} ++ ++void sha3_dealloc(void *hash_state) ++{ ++ struct sha_ctx *ctx = (struct sha_ctx *)hash_state; ++ ++ jent_zfree(ctx, SHA_MAX_CTX_SIZE); ++} +Index: libgcrypt-1.10.0/random/jitterentropy-sha3.h +=================================================================== +--- libgcrypt-1.10.0.orig/random/jitterentropy-sha3.h ++++ libgcrypt-1.10.0/random/jitterentropy-sha3.h +@@ -47,6 +47,8 @@ struct sha_ctx { + void sha3_256_init(struct sha_ctx *ctx); + void sha3_update(struct sha_ctx *ctx, const uint8_t *in, size_t inlen); + void sha3_final(struct sha_ctx *ctx, uint8_t *digest); ++int sha3_alloc(void **hash_state); ++void sha3_dealloc(void *hash_state); + int sha3_tester(void); + + #ifdef __cplusplus +Index: libgcrypt-1.10.0/random/jitterentropy-timer.c +=================================================================== +--- libgcrypt-1.10.0.orig/random/jitterentropy-timer.c ++++ libgcrypt-1.10.0/random/jitterentropy-timer.c +@@ -202,8 +202,8 @@ int jent_notime_enable(struct rand_data + if (jent_force_internal_timer || (flags & JENT_FORCE_INTERNAL_TIMER)) { + /* Self test not run yet */ + if (!jent_force_internal_timer && +- jent_time_entropy_init(flags | JENT_FORCE_INTERNAL_TIMER, +- ec->osr)) ++ jent_time_entropy_init(ec->osr, ++ flags | JENT_FORCE_INTERNAL_TIMER)) + return EHEALTH; + + ec->enable_notime = 1; +Index: libgcrypt-1.10.0/random/jitterentropy.h +=================================================================== +--- libgcrypt-1.10.0.orig/random/jitterentropy.h ++++ libgcrypt-1.10.0/random/jitterentropy.h +@@ -49,7 +49,7 @@ + ***************************************************************************/ + + /* +- * Enable timer-less timer support ++ * Enable timer-less timer support with JENT_CONF_ENABLE_INTERNAL_TIMER + * + * In case the hardware is identified to not provide a high-resolution time + * stamp, this option enables a built-in high-resolution time stamp mechanism. +@@ -166,7 +166,7 @@ struct rand_data + * of the RNG are marked as SENSITIVE. A user must not + * access that information while the RNG executes its loops to + * calculate the next random value. */ +- uint8_t data[SHA3_256_SIZE_DIGEST]; /* SENSITIVE Actual random number */ ++ void *hash_state; /* SENSITIVE hash state entropy pool */ + uint64_t prev_time; /* SENSITIVE Previous time stamp */ + #define DATA_SIZE_BITS (SHA3_256_SIZE_DIGEST_BITS) + +@@ -378,28 +378,34 @@ int jent_entropy_init(void); + JENT_PRIVATE_STATIC + int jent_entropy_init_ex(unsigned int osr, unsigned int flags); + ++/* ++ * Set a callback to run on health failure in FIPS mode. ++ * This function will take an action determined by the caller. ++ */ ++typedef void (*jent_fips_failure_cb)(struct rand_data *ec, ++ unsigned int health_failure); ++JENT_PRIVATE_STATIC ++int jent_set_fips_failure_callback(jent_fips_failure_cb cb); ++ + /* return version number of core library */ + JENT_PRIVATE_STATIC + unsigned int jent_version(void); + +-#ifdef JENT_CONF_ENABLE_INTERNAL_TIMER + /* Set a different thread handling logic for the notimer support */ + JENT_PRIVATE_STATIC + int jent_entropy_switch_notime_impl(struct jent_notime_thread *new_thread); +-#endif + + /* -- END of Main interface functions -- */ + + /* -- BEGIN timer-less threading support functions to prevent code dupes -- */ + +-struct jent_notime_ctx { + #ifdef JENT_CONF_ENABLE_INTERNAL_TIMER ++ ++struct jent_notime_ctx { + pthread_attr_t notime_pthread_attr; /* pthreads library */ + pthread_t notime_thread_id; /* pthreads thread ID */ +-#endif + }; + +-#ifdef JENT_CONF_ENABLE_INTERNAL_TIMER + + JENT_PRIVATE_STATIC + int jent_notime_init(void **ctx); +Index: libgcrypt-1.10.0/random/jitterentropy-base-user.h +=================================================================== +--- libgcrypt-1.10.0.orig/random/jitterentropy-base-user.h ++++ libgcrypt-1.10.0/random/jitterentropy-base-user.h +@@ -213,12 +213,12 @@ static inline void jent_get_cachesize(lo + ext = strstr(buf, "K"); + if (ext) { + shift = 10; +- ext = '\0'; ++ *ext = '\0'; + } else { + ext = strstr(buf, "M"); + if (ext) { + shift = 20; +- ext = '\0'; ++ *ext = '\0'; + } + } + diff --git a/libgcrypt-no-deprecated-grep-alias.patch b/libgcrypt-no-deprecated-grep-alias.patch new file mode 100644 index 0000000..ba0dde8 --- /dev/null +++ b/libgcrypt-no-deprecated-grep-alias.patch @@ -0,0 +1,35 @@ +--- libgcrypt-1.10.3.orig/acinclude.m4 ++++ libgcrypt-1.10.3/acinclude.m4 +@@ -130,10 +130,10 @@ EOF + ac_nlist=conftest.nm + if AC_TRY_EVAL(NM conftest.$ac_objext \| $lt_cv_sys_global_symbol_pipe \| cut -d \' \' -f 2 \> $ac_nlist) && test -s "$ac_nlist"; then + # See whether the symbols have a leading underscore. +- if egrep '^_nm_test_func' "$ac_nlist" >/dev/null; then ++ if grep -E '^_nm_test_func' "$ac_nlist" >/dev/null; then + ac_cv_sys_symbol_underscore=yes + else +- if egrep '^nm_test_func ' "$ac_nlist" >/dev/null; then ++ if grep -E '^nm_test_func ' "$ac_nlist" >/dev/null; then + : + else + echo "configure: cannot find nm_test_func in $ac_nlist" >&AS_MESSAGE_LOG_FD +--- libgcrypt-1.10.3.orig/src/libgcrypt-config.in ++++ libgcrypt-1.10.3/src/libgcrypt-config.in +@@ -154,7 +154,7 @@ if test "$echo_cflags" = "yes"; then + + tmp="" + for i in $includes $cflags_final; do +- if echo "$tmp" | fgrep -v -- "$i" >/dev/null; then ++ if echo "$tmp" | @GREP@ -F -v -- "$i" >/dev/null; then + tmp="$tmp $i" + fi + done +@@ -175,7 +175,7 @@ if test "$echo_libs" = "yes"; then + + tmp="" + for i in $libdirs $libs_final; do +- if echo "$tmp" | fgrep -v -- "$i" >/dev/null; then ++ if echo "$tmp" | @GREP@ -F -v -- "$i" >/dev/null; then + tmp="$tmp $i" + fi + done diff --git a/libgcrypt-nobetasuffix.patch b/libgcrypt-nobetasuffix.patch new file mode 100644 index 0000000..3d4593a --- /dev/null +++ b/libgcrypt-nobetasuffix.patch @@ -0,0 +1,24 @@ +Index: libgcrypt-1.10.2/autogen.sh +=================================================================== +--- libgcrypt-1.10.2.orig/autogen.sh ++++ libgcrypt-1.10.2/autogen.sh +@@ -249,7 +249,7 @@ if [ "$myhost" = "find-version" ]; then + fi + + beta=no +- if [ -e .git ]; then ++ if false; then + ingit=yes + tmp=$(git describe --match "${matchstr1}" --long 2>/dev/null) + tmp=$(echo "$tmp" | sed s/^"$package"//) +@@ -265,8 +265,8 @@ if [ "$myhost" = "find-version" ]; then + rvd=$((0x$(echo ${rev} | dd bs=1 count=4 2>/dev/null))) + else + ingit=no +- beta=yes +- tmp="-unknown" ++ beta=no ++ tmp="" + rev="0000000" + rvd="0" + fi diff --git a/libgcrypt-ppc-enable-P10-assembly-with-ENABLE_FORCE_SOF.patch b/libgcrypt-ppc-enable-P10-assembly-with-ENABLE_FORCE_SOF.patch new file mode 100644 index 0000000..8ef3197 --- /dev/null +++ b/libgcrypt-ppc-enable-P10-assembly-with-ENABLE_FORCE_SOF.patch @@ -0,0 +1,76 @@ +commit 2c5e5ab6843d747c4b877d2c6f47226f61e9ff14 +Author: Jussi Kivilinna +Date: Sun Jun 12 21:51:34 2022 +0300 + + ppc enable P10 assembly with ENABLE_FORCE_SOFT_HWFEATURES on arch 3.00 + + * cipher/chacha20.c (chacha20_do_setkey) [USE_PPC_VEC]: Enable + P10 assembly for HWF_PPC_ARCH_3_00 if ENABLE_FORCE_SOFT_HWFEATURES is + defined. + * cipher/poly1305.c (poly1305_init) [POLY1305_USE_PPC_VEC]: Likewise. + * cipher/rijndael.c (do_setkey) [USE_PPC_CRYPTO_WITH_PPC9LE]: Likewise. + --- + + This change allows testing P10 implementations with P9 and with QEMU-PPC. + + GnuPG-bug-id: 6006 + Signed-off-by: Jussi Kivilinna + +Index: libgcrypt-1.10.2/cipher/chacha20.c +=================================================================== +--- libgcrypt-1.10.2.orig/cipher/chacha20.c ++++ libgcrypt-1.10.2/cipher/chacha20.c +@@ -484,6 +484,11 @@ chacha20_do_setkey (CHACHA20_context_t * + ctx->use_ppc = (features & HWF_PPC_ARCH_2_07) != 0; + # ifndef WORDS_BIGENDIAN + ctx->use_p10 = (features & HWF_PPC_ARCH_3_10) != 0; ++# ifdef ENABLE_FORCE_SOFT_HWFEATURES ++ /* HWF_PPC_ARCH_3_10 above is used as soft HW-feature indicator for P10. ++ * Actual implementation works with HWF_PPC_ARCH_3_00 also. */ ++ ctx->use_p10 |= (features & HWF_PPC_ARCH_3_00) != 0; ++# endif + # endif + #endif + #ifdef USE_S390X_VX +Index: libgcrypt-1.10.2/cipher/poly1305.c +=================================================================== +--- libgcrypt-1.10.2.orig/cipher/poly1305.c ++++ libgcrypt-1.10.2/cipher/poly1305.c +@@ -90,11 +90,19 @@ static void poly1305_init (poly1305_cont + const byte key[POLY1305_KEYLEN]) + { + POLY1305_STATE *st = &ctx->state; ++ unsigned int features = _gcry_get_hw_features (); + + #ifdef POLY1305_USE_PPC_VEC +- ctx->use_p10 = (_gcry_get_hw_features () & HWF_PPC_ARCH_3_10) != 0; ++ ctx->use_p10 = (features & HWF_PPC_ARCH_3_10) != 0; ++# ifdef ENABLE_FORCE_SOFT_HWFEATURES ++ /* HWF_PPC_ARCH_3_10 above is used as soft HW-feature indicator for P10. ++ * Actual implementation works with HWF_PPC_ARCH_3_00 also. */ ++ ctx->use_p10 |= (features & HWF_PPC_ARCH_3_00) != 0; ++# endif + #endif + ++ (void)features; ++ + ctx->leftover = 0; + + st->h[0] = 0; +Index: libgcrypt-1.10.2/cipher/rijndael.c +=================================================================== +--- libgcrypt-1.10.2.orig/cipher/rijndael.c ++++ libgcrypt-1.10.2/cipher/rijndael.c +@@ -605,6 +605,12 @@ do_setkey (RIJNDAEL_context *ctx, const + bulk_ops->xts_crypt = _gcry_aes_ppc9le_xts_crypt; + if (hwfeatures & HWF_PPC_ARCH_3_10) /* for P10 */ + bulk_ops->gcm_crypt = _gcry_aes_p10le_gcm_crypt; ++# ifdef ENABLE_FORCE_SOFT_HWFEATURES ++ /* HWF_PPC_ARCH_3_10 above is used as soft HW-feature indicator for P10. ++ * Actual implementation works with HWF_PPC_ARCH_3_00 also. */ ++ if (hwfeatures & HWF_PPC_ARCH_3_00) ++ bulk_ops->gcm_crypt = _gcry_aes_p10le_gcm_crypt; ++# endif + } + #endif + #ifdef USE_PPC_CRYPTO diff --git a/libgcrypt-rol64-redefinition.patch b/libgcrypt-rol64-redefinition.patch new file mode 100644 index 0000000..bb76b2f --- /dev/null +++ b/libgcrypt-rol64-redefinition.patch @@ -0,0 +1,16 @@ +Index: libgcrypt-1.11.0/cipher/bithelp.h +=================================================================== +--- libgcrypt-1.11.0.orig/cipher/bithelp.h ++++ libgcrypt-1.11.0/cipher/bithelp.h +@@ -35,11 +35,6 @@ static inline u32 ror(u32 x, int n) + return ( (x >> (n&(32-1))) | (x << ((32-n)&(32-1))) ); + } + +-static inline u64 rol64(u64 x, int n) +-{ +- return ( (x << (n&(64-1))) | (x >> ((64-n)&(64-1))) ); +-} +- + /* Byte swap for 32-bit and 64-bit integers. If available, use compiler + provided helpers. */ + #ifdef HAVE_BUILTIN_BSWAP32 diff --git a/libgcrypt.changes b/libgcrypt.changes new file mode 100644 index 0000000..3795d7c --- /dev/null +++ b/libgcrypt.changes @@ -0,0 +1,1864 @@ +------------------------------------------------------------------- +Tue Jan 7 09:28:25 UTC 2025 - Pedro Monreal + +- Fix redefinition error of 'rol64'. Remove not used rol64() + definition after removing the built-in jitter rng. + * Add libgcrypt-rol64-redefinition.patch + +------------------------------------------------------------------- +Mon Dec 2 10:11:10 UTC 2024 - Pedro Monreal + +- Remove unrecognized option: --enable-m-guard + +------------------------------------------------------------------- +Thu Jun 20 08:11:07 UTC 2024 - Pedro Monreal + +- Update to 1.11.0: + * New and extended interfaces: + - Add an API for Key Encapsulation Mechanism (KEM). [T6755] + - Add Streamlined NTRU Prime sntrup761 algorithm. [rCcf9923e1a5] + - Add Kyber algorithm according to FIPS 203 ipd 2023-08-24. [rC18e5c0d268] + - Add Classic McEliece algorithm. [rC003367b912] + - Add One-Step KDF with hash and MAC. [T5964] + - Add KDF algorithm HKDF of RFC-5869. [T5964] + - Add KDF algorithm X963KDF for use in CMS. [rC3abac420b3] + - Add GMAC-SM4 and Poly1305-SM4. [rCd1ccc409d4] + - Add ARIA block cipher algorithm. [rC316c6d7715] + - Add explicit FIPS indicators for MD and MAC algorithms. [T6376] + - Add support for SHAKE as MGF in RSA. [T6557] + - Add gcry_md_read support for SHAKE algorithms. [T6539] + - Add gcry_md_hash_buffers_ext function. [T7035] + - Add cSHAKE hash algorithm. [rC065b3f4e02] + - Support internal generation of IV for AEAD cipher mode. [T4873] + * Performance: + - Add SM3 ARMv8/AArch64/CE assembly implementation. [rCfe891ff4a3] + - Add SM4 ARMv8/AArch64 assembly implementation. [rCd8825601f1] + - Add SM4 GFNI/AVX2 and GFI/AVX512 implementation. [rC5095d60af4,rCeaed633c16] + - Add SM4 ARMv9 SVE CE assembly implementation. [rC2dc2654006] + - Add PowerPC vector implementation of SM4. [rC0b2da804ee] + - Optimize ChaCha20 and Poly1305 for PPC P10 LE. [T6006] + - Add CTR32LE bulk acceleration for AES on PPC. [rC84f2e2d0b5] + - Add generic bulk acceleration for CTR32LE mode (GCM-SIV) for SM4 + and Camellia. [rCcf956793af] + - Add GFNI/AVX2 implementation of Camellia. [rC4e6896eb9f] + - Add AVX2 and AVX512 accelerated implementations for GHASH (GCM) + and POLYVAL (GCM-SIV). [rCd857e85cb4, rCe6f3600193] + - Add AVX512 implementation for SHA512. [rC089223aa3b] + - Add AVX512 implementation for Serpent. [rCce95b6ec35] + - Add AVX512 implementation for Poly1305 and ChaCha20. [rCcd3ed49770, rC9a63cfd617] + - Add AVX512 accelerated implementation for SHA3 and Blake2. [rCbeaad75f46,rC909daa700e] + - Add VAES/AVX2 accelerated i386 implementation for AES. [rC4a42a042bc] + - Add bulk processing for XTS mode of Camellia and SM4. [rC32b18cdb87, rCaad3381e93] + - Accelerate XTS and ECB modes for Twofish and Serpent. [rCd078a928f5,rC8a1fe5f78f] + - Add AArch64 crypto/SHA512 extension implementation for SHA512. [rCe51d3b8330] + - Add AArch64 crypto-extension implementation for Camellia. [rC898c857206] + - Accelerate OCB authentication on AMD with AVX2. [rC6b47e85d65] + * Bug fixes: + - For PowerPC check for missing optimization level for vector register usage. [T5785] + - Fix EdDSA secret key check. [T6511] + - Fix decoding of PKCS#1-v1.5 and OAEP padding. [rC34c2042792] + - Allow use of PKCS#1-v1.5 with SHA3 algorithms. [T6976] + - Fix AESWRAP padding length check. [T7130] + * Other: + - Allow empty password for Argon2 KDF. [rCa20700c55f] + - Various constant time operation imporvements. + - Add "bp256", "bp384", "bp512" aliases for Brainpool curves. + - Support for the random server has been removed. [T5811] + - The control code GCRYCTL_ENABLE_M_GUARD is deprecated and not + supported any more. Please use valgrind or other tools. [T5822] + - Logging is now done via the libgpg-error logging functions. [rCab0bdc72c7] + * Remove patches fixed upstream: + - libgcrypt-no-deprecated-grep-alias.patch + - libgcrypt-Chacha20-poly1305-Optimized-chacha20-poly1305.patch + - libgcrypt-ppc-enable-P10-assembly-with-ENABLE_FORCE_SOF.patch + * Rebase patches: + - libgcrypt-FIPS-jitter-errorcodes.patch + - libgcrypt-FIPS-jitter-whole-entropy.patch + +------------------------------------------------------------------- +Wed Mar 20 20:31:40 UTC 2024 - Pedro Monreal + +- FIPS: Make sure that Libgcrypt makes use of the built-in Jitter RNG + for the whole length entropy buffer in FIPS mode. [bsc#1220893] + * Add libgcrypt-FIPS-jitter-whole-entropy.patch + +------------------------------------------------------------------- +Wed Mar 20 15:13:04 UTC 2024 - Pedro Monreal + +- FIPS: Set the FSM into error state if Jitter RNG is returning an + error code to the caller when an health test error occurs when + random bytes are requested through the jent_read_entropy_safe() + function. [bsc#1220895] + * Add libgcrypt-FIPS-jitter-errorcodes.patch + +------------------------------------------------------------------- +Mon Mar 11 16:02:55 UTC 2024 - Pedro Monreal + +- FIPS: Replace the built-in jitter rng with standalone version + * Remove the internal jitterentropy copy [bsc#1220896] + * Add libgcrypt-FIPS-jitter-standalone.patch + * Remove not needed libgcrypt-jitterentropy-3.4.0.patch + +------------------------------------------------------------------- +Mon Feb 26 12:13:56 UTC 2024 - Pedro Monreal + +- Update upstream libgcrypt.keyring + +------------------------------------------------------------------- +Sat Jan 27 13:37:34 UTC 2024 - Dirk Müller + +- add libgcrypt-no-deprecated-grep-alias.patch + +------------------------------------------------------------------- +Tue Nov 21 10:36:09 UTC 2023 - Otto Hollmann + +- Re-create HMAC checksum after RPM build strips the library + (bsc#1217058) + +------------------------------------------------------------------- +Wed Nov 15 09:54:00 UTC 2023 - Pedro Monreal + +- Update to 1.10.3: + * Bug fixes: + - Fix public key computation for other EdDSA curves. [rC469919751d6e] + - Remove out of core handler diagnostic in FIPS mode. [T6515] + - Check that the digest size is not zero in gcry_pk_sign_md and + gcry_pk_verify_md. [T6539] + - Make store an s-exp with \0 is considered to be binary. [T6747] + - Various constant-time improvements. + * Portability: + - Use getrandom call only when supported by the platform. [T6442] + - Change the default for --with-libtool-modification to never. [T6619] + * Release-info: https://dev.gnupg.org/T6817 + * Remove patch upstream libgcrypt-1.10.0-out-of-core-handler.patch + +------------------------------------------------------------------- +Tue Oct 17 10:27:15 UTC 2023 - Pedro Monreal + +- Do not pull revision info from GIT when autoconf is run. This + removes the -unknown suffix after the version number. + * Add libgcrypt-nobetasuffix.patch [bsc#1216334] + +------------------------------------------------------------------- +Tue Oct 3 12:58:41 UTC 2023 - Pedro Monreal + +- POWER: performance enhancements for cryptography [jsc#PED-5088] + * Optimize Chacha20 and Poly1305 for PPC P10 LE: [T6006] + - Chacha20/poly1305: Optimized chacha20/poly1305 for + P10 operation [rC88fe7ac33eb4] + - ppc: enable P10 assembly with ENABLE_FORCE_SOFT_HWFEATURES + on arch-3.00 [rC2c5e5ab6843d] + * Add patches: + - libgcrypt-Chacha20-poly1305-Optimized-chacha20-poly1305.patch + - libgcrypt-ppc-enable-P10-assembly-with-ENABLE_FORCE_SOF.patch + +------------------------------------------------------------------- +Mon May 22 11:32:53 UTC 2023 - Pedro Monreal + +- FIPS: Merge the libgcrypt20-hmac package into the library and + remove the "module is complete" trigger file .fips [bsc#1185116] + * Remove libgcrypt-1.10.0-use-fipscheck.patch + +------------------------------------------------------------------- +Tue Apr 11 14:08:24 UTC 2023 - Pedro Monreal + +- Update to 1.10.2: + * Bug fixes: + - Fix Argon2 for the case output > 64. [rC13b5454d26] + - Fix missing HWF_PPC_ARCH_3_10 in HW feature. [rCe073f0ed44] + - Fix RSA key generation failure in forced FIPS mode. [T5919] + - Fix gcry_pk_hash_verify for explicit hash. [T6066] + - Fix a wrong result of gcry_mpi_invm. [T5970] + - Allow building with --disable-asm for HPPA. [T5976] + - Allow building with -Oz. [T6432] + - Enable the fast path to ChaCha20 only when supported. [T6384] + - Use size_t to avoid counter overflow in Keccak when directly + feeding more than 4GiB. [T6217] + * Other: + - Do not use secure memory for a DRBG instance. [T5933] + - Do not allow PKCS#1.5 padding for encryption in FIPS mode. [T5918] + - Fix the behaviour for child process re-seeding in the DRBG. [rC019a40c990] + - Allow verification of small RSA signatures in FIPS mode. [T5975] + - Allow the use of a shorter salt for KDFs in FIPS mode. [T6039] + - Run digest+sign self tests for RSA and ECC in FIPS mode. [rC06c9350165] + - Add function-name based FIPS indicator function. + GCRYCTL_FIPS_SERVICE_INDICATOR_FUNCTION. This is not considered + an ABI changes because the new FIPS features were not yet + approved. [rC822ee57f07] + - Improve PCT in FIPS mode. [rC285bf54b1a, rC4963c127ae, T6397] + - Use getrandom (GRND_RANDOM) in FIPS mode. [rCcf10c74bd9] + - Disable RSA-OAEP padding in FIPS mode. [rCe5bfda492a] + - Check minimum allowed key size in PBKDF in FIPS mode. [T6039,T6219] + - Get maximum 32B of entropy at once in FIPS mode. [rCce0df08bba] + - Prefer gpgrt-config when available. [T5034] + - Mark AESWRAP as approved FIPS algorithm. [T5512] + - Prevent usage of long salt for PSS in FIPS mode. [rCfdd2a8b332] + - Prevent usage of X9.31 keygen in FIPS mode. [rC392e0ccd25] + - Remove GCM mode from the allowed FIPS indicators. [rC1540698389] + - Add explicit FIPS indicators for hash and MAC algorithms. [T6376] + * Release-info: https://dev.gnupg.org/T5905 + * Rebase FIPS patches: + - libgcrypt-FIPS-SLI-hash-mac.patch + - libgcrypt-FIPS-SLI-kdf-leylength.patch + - libgcrypt-FIPS-SLI-pk.patch + +------------------------------------------------------------------- +Wed Mar 8 10:34:34 UTC 2023 - Martin Pluskal + +- Build AVX2 enabled hwcaps library for x86_64-v3 + +------------------------------------------------------------------- +Wed Oct 19 14:01:24 UTC 2022 - Pedro Monreal + +- Update to 1.10.1: + * Bug fixes: + - Fix minor memory leaks in FIPS mode. + - Build fixes for MUSL libc. + * Other: + - More portable integrity check in FIPS mode. + - Add X9.62 OIDs to sha256 and sha512 modules. + * Add the hardware optimizations config file hwf.deny to + the /etc/gcrypt/ directory. This file can be used to globally + disable the use of hardware based optimizations. + * Remove not needed separate_hmac256_binary hmac256 package + +------------------------------------------------------------------- +Wed Sep 14 13:34:13 UTC 2022 - Pedro Monreal + +- Update to 1.10.0: + * New and extended interfaces: + - New control codes to check for FIPS 140-3 approved algorithms. + - New control code to switch into non-FIPS mode. + - New cipher modes SIV and GCM-SIV as specified by RFC-5297. + - Extended cipher mode AESWRAP with padding as specified by + RFC-5649. + - New set of KDF functions. + - New KDF modes Argon2 and Balloon. + - New functions for combining hashing and signing/verification. + * Performance: + - Improved support for PowerPC architectures. + - Improved ECC performance on zSeries/s390x by using accelerated + scalar multiplication. + - Many more assembler performance improvements for several + architectures. + * Bug fixes: + - Fix Elgamal encryption for other implementations. + [bsc#1190239, CVE-2021-40528] + - Check the input length of the point in ECDH. + - Fix an abort in gcry_pk_get_param for "Curve25519". + * Other features: + - The control code GCRYCTL_SET_ENFORCED_FIPS_FLAG is ignored + because it is useless with the FIPS 140-3 related changes. + - Update of the jitter entropy RNG code. + - Simplification of the entropy gatherer when using the getentropy + system call. + * Interface changes relative to the 1.10.0 release: + - GCRYCTL_SET_DECRYPTION_TAG NEW control code. + - GCRYCTL_FIPS_SERVICE_INDICATOR_CIPHER NEW control code. + - GCRYCTL_FIPS_SERVICE_INDICATOR_KDF NEW control code. + - GCRYCTL_NO_FIPS_MODE = 83 NEW control code. + - GCRY_CIPHER_MODE_SIV NEW mode. + - GCRY_CIPHER_MODE_GCM_SIV NEW mode. + - GCRY_CIPHER_EXTENDED NEW flag. + - GCRY_SIV_BLOCK_LEN NEW macro. + - gcry_cipher_set_decryption_tag NEW macro. + - GCRY_KDF_ARGON2 NEW constant. + - GCRY_KDF_BALLOON NEW constant. + - GCRY_KDF_ARGON2D NEW constant. + - GCRY_KDF_ARGON2I NEW constant. + - GCRY_KDF_ARGON2ID NEW constant. + - gcry_kdf_hd_t NEW type. + - gcry_kdf_job_fn_t NEW type. + - gcry_kdf_dispatch_job_fn_t NEW type. + - gcry_kdf_wait_all_jobs_fn_t NEW type. + - struct gcry_kdf_thread_ops NEW struct. + - gcry_kdf_open NEW function. + - gcry_kdf_compute NEW function. + - gcry_kdf_final NEW function. + - gcry_kdf_close NEW function. + - gcry_pk_hash_sign NEW function. + - gcry_pk_hash_verify NEW function. + - gcry_pk_random_override_new NEW function. + * Rebase libgcrypt-1.8.4-allow_FSM_same_state.patch and rename + to libgcrypt-1.10.0-allow_FSM_same_state.patch + * Remove unused CAVS tests and related patches: + - cavs_driver.pl cavs-test.sh + - libgcrypt-1.6.1-fips-cavs.patch + - drbg_test.patch + * Remove DSA sign/verify patches for the FIPS CAVS test since DSA + has been disabled in FIPS mode: + - libgcrypt-fipsdrv-enable-algo-for-dsa-sign.patch + - libgcrypt-fipsdrv-enable-algo-for-dsa-verify.patch + * Rebase libgcrypt-FIPS-SLI-pk.patch + * Rebase libgcrypt_indicators_changes.patch and + libgcrypt-indicate-shake.patch and merge both into + libgcrypt-FIPS-SLI-hash-mac.patch + * Rebase libgcrypt-FIPS-kdf-leylength.patch and rename to + libgcrypt-FIPS-SLI-kdf-leylength.patch + * Rebase libgcrypt-jitterentropy-3.4.0.patch + * Rebase libgcrypt-FIPS-rndjent_poll.patch + * Rebase libgcrypt-out-of-core-handler.patch and rename to + libgcrypt-1.10.0-out-of-core-handler.patch + * Since the FIPS .hmac file is now calculated with the internal + tool hmac256, only the "module is complete" trigger .fips file + is checked. Rename libgcrypt-1.6.1-use-fipscheck.patch + to libgcrypt-1.10.0-use-fipscheck.patch + * Remove patches fixed upstream: + - libgcrypt-1.4.1-rijndael_no_strict_aliasing.patch + - libgcrypt-1.5.0-LIBGCRYPT_FORCE_FIPS_MODE-env.diff + - libgcrypt-fix-rng.patch + - libgcrypt-1.8.3-fips-ctor.patch + - libgcrypt-1.8.4-use_xfree.patch + - libgcrypt-1.8.4-getrandom.patch + - libgcrypt-1.8.4-fips_ctor_skip_integrity_check.patch + - libgcrypt-dsa-rfc6979-test-fix.patch + - libgcrypt-fix-tests-fipsmode.patch + - libgcrypt-FIPS-RSA-DSA-ECDSA-hashing-operation.patch + - libgcrypt-1.8.4-fips-keygen.patch + - libgcrypt-invoke-global_init-from-constructor.patch + - libgcrypt-Restore-self-tests-from-constructor.patch + - libgcrypt-FIPS-GMAC_AES-benckmark.patch + - libgcrypt-global_init-constructor.patch + - libgcrypt-random_selftests-testentropy.patch + - libgcrypt-rsa-no-blinding.patch + - libgcrypt-ecc-ecdsa-no-blinding.patch + - libgcrypt-PCT-DSA.patch + - libgcrypt-PCT-ECC.patch + - libgcrypt-PCT-RSA.patch + - libgcrypt-fips_selftest_trigger_file.patch + - libgcrypt-pthread-in-t-lock-test.patch + - libgcrypt-FIPS-hw-optimizations.patch + - libgcrypt-FIPS-module-version.patch + - libgcrypt-FIPS-disable-3DES.patch + - libgcrypt-FIPS-fix-regression-tests.patch + - libgcrypt-FIPS-RSA-keylen.patch + - libgcrypt-FIPS-RSA-keylen-tests.patch + - libgcrypt-FIPS-fix-gcry_mpi_sub_ui.patch + - libgcrypt-FIPS-verify-unsupported-KDF-test.patch + - libgcrypt-FIPS-HMAC-short-keylen.patch + - libgcrypt-FIPS-service-indicators.patch + - libgcrypt-FIPS-disable-DSA.patch + - libgcrypt-jitterentropy-3.3.0.patch + - libgcrypt-FIPS-Zeroize-hmac.patch + * Update libgcrypt.keyring + +------------------------------------------------------------------- +Thu Sep 8 10:34:53 UTC 2022 - Pedro Monreal + +- FIPS: Get most of the entropy from rndjent_poll [bsc#1202117] + * Add libgcrypt-FIPS-rndjent_poll.patch + * Rebase libgcrypt-jitterentropy-3.4.0.patch + +------------------------------------------------------------------- +Wed Sep 7 22:03:51 UTC 2022 - Pedro Monreal + +- FIPS: Check keylength in gcry_fips_indicator_kdf() [bsc#1190700] + * Consider approved keylength greater or equal to 112 bits. + * Add libgcrypt-FIPS-kdf-leylength.patch + +------------------------------------------------------------------- +Wed Sep 7 12:53:14 UTC 2022 - Pedro Monreal + +- FIPS: Zeroize buffer and digest in check_binary_integrity() + * Add libgcrypt-FIPS-Zeroize-hmac.patch [bsc#1191020] + +------------------------------------------------------------------- +Tue Aug 23 09:19:00 UTC 2022 - Pedro Monreal + +- FIPS: gpg/gpg2 gets out of core handler in FIPS mode while + typing Tab key to Auto-Completion. [bsc#1182983] + * Add libgcrypt-out-of-core-handler.patch + +------------------------------------------------------------------- +Mon Aug 8 11:33:03 UTC 2022 - Pedro Monreal + +- FIPS: Port libgcrypt to use jitterentropy [bsc#1202117, jsc#SLE-24941] + * Enable the jitter based entropy generator by default in random.conf + - Add libgcrypt-jitterentropy-3.3.0.patch + * Update the internal jitterentropy to version 3.4.0 + - Add libgcrypt-jitterentropy-3.4.0.patch + +------------------------------------------------------------------- +Mon Aug 1 07:27:35 UTC 2022 - Stephan Kulow + +- Fix reproducible build problems: + - Do not use %release in binaries (but use SOURCE_DATE_EPOCH) + - Fix date call messed up by spec-cleaner + +------------------------------------------------------------------- +Thu Apr 14 12:30:36 UTC 2022 - Dennis Knorr + +- FIPS: extend the service indicator [bsc#1190700] + * introduced a pk indicator function + * adapted the approved and non approved ciphersuites + * Add libgcrypt_indicators_changes.patch + * Add libgcrypt-indicate-shake.patch + +------------------------------------------------------------------- +Tue Mar 22 12:32:09 UTC 2022 - Pedro Monreal + +- FIPS: Implement a service indicator for asymmetric ciphers [bsc#1190700] + * Mark RSA public key encryption and private key decryption with + padding (e.g. OAEP, PKCS) as non-approved since RSA-OAEP lacks + peer key assurance validation requirements per SP800-56Brev2. + * Mark ECC as approved only for NIST curves P-224, P-256, P-384 + and P-521 with check for common NIST names and aliases. + * Mark DSA, ELG, EDDSA, ECDSA and ECDH as non-approved. + * Add libgcrypt-FIPS-SLI-pk.patch + * Rebase libgcrypt-FIPS-service-indicators.patch +- Run the regression tests also in FIPS mode. + * Disable tests for non-FIPS approved algos. + * Rebase: libgcrypt-FIPS-verify-unsupported-KDF-test.patch + +------------------------------------------------------------------- +Tue Feb 1 11:28:51 UTC 2022 - Pedro Monreal + +- FIPS: Disable DSA in FIPS mode [bsc#1195385] + * Upstream task: https://dev.gnupg.org/T5710 + * Add libgcrypt-FIPS-disable-DSA.patch + +------------------------------------------------------------------- +Wed Jan 19 08:36:58 UTC 2022 - Pedro Monreal + +- FIPS: Service level indicator [bsc#1190700] + * Provide an indicator to check wether the service utilizes an + approved cryptographic algorithm or not. + * Add patches: + - libgcrypt-FIPS-service-indicators.patch + - libgcrypt-FIPS-verify-unsupported-KDF-test.patch + - libgcrypt-FIPS-HMAC-short-keylen.patch + +------------------------------------------------------------------- +Tue Dec 7 09:41:01 UTC 2021 - Pedro Monreal + +- FIPS: Fix gcry_mpi_sub_ui subtraction [bsc#1193480] + * gcry_mpi_sub_ui: fix subtracting from negative value + * Add libgcrypt-FIPS-fix-gcry_mpi_sub_ui.patch + +------------------------------------------------------------------- +Tue Nov 30 09:42:23 UTC 2021 - Pedro Monreal + +- FIPS: Define an entropy source SP800-90B compliant [bsc#1185140] + * Disable jitter entropy by default in random.conf + * Disable only-urandom option by default in random.conf + +------------------------------------------------------------------- +Fri Nov 26 13:10:29 UTC 2021 - Pedro Monreal + +- FIPS: RSA KeyGen/SigGen fail with 4096 bit key sizes [bsc#1192240] + * rsa: Check RSA keylen constraints for key operations. + * rsa: Fix regression in not returning an error for prime generation. + * tests: Add 2k RSA key working in FIPS mode. + * tests: pubkey: Replace RSA key to one of 2k. + * tests: pkcs1v2: Skip tests with small keys in FIPS. + * Add patches: + - libgcrypt-FIPS-RSA-keylen.patch + - libgcrypt-FIPS-RSA-keylen-tests.patch + +------------------------------------------------------------------- +Mon Nov 8 10:21:39 UTC 2021 - Pedro Monreal + +- FIPS: Disable 3DES/Triple-DES in FIPS mode [bsc#1185138] + * Add libgcrypt-FIPS-disable-3DES.patch + +------------------------------------------------------------------- +Tue Nov 2 11:31:19 UTC 2021 - Pedro Monreal + +- FIPS: PBKDF requirements [bsc#1185137] + * The PBKDF2 selftests were introduced in libgcrypt version + 1.9.1 in the function selftest_pbkdf2() + * Upstream task: https://dev.gnupg.org/T5182 + +------------------------------------------------------------------- +Thu Oct 28 19:48:06 UTC 2021 - Pedro Monreal + +- FIPS: Fix regression tests in FIPS mode [bsc#1192131] + * Add libgcrypt-FIPS-fix-regression-tests.patch + * Upstream task: https://dev.gnupg.org/T5520 + +------------------------------------------------------------------- +Thu Sep 21 11:25:06 UTC 2021 - Pedro Monreal + +- FIPS: Provide a module name/identifier and version that can be + mapped to the validation records. [bsc#1190706] + * Add libgcrypt-FIPS-module-version.patch + * Upstream task: https://dev.gnupg.org/T5600 + +------------------------------------------------------------------- +Thu Sep 21 10:23:44 UTC 2021 - Pedro Monreal + +- FIPS: Enable hardware support also in FIPS mode [bsc#1187110] + * Add libgcrypt-FIPS-hw-optimizations.patch + * Upstream task: https://dev.gnupg.org/T5508 + +------------------------------------------------------------------- +Mon Aug 23 12:08:24 UTC 2021 - Pedro Monreal + +- Update to 1.9.4: + * Bug fixes: + - Fix Elgamal encryption for other implementations. [CVE-2021-33560] + - Fix alignment problem on macOS. + - Check the input length of the point in ECDH. + - Fix an abort in gcry_pk_get_param for "Curve25519". + * Other features: + - Add GCM and CCM to OID mapping table for AES. + * Upstream libgcrypt-CVE-2021-33560-fix-ElGamal-enc.patch + +------------------------------------------------------------------- +Mon Aug 23 10:11:55 UTC 2021 - Pedro Monreal + +- Remove not needed patch libgcrypt-sparcv9.diff + +------------------------------------------------------------------- +Thu Jul 15 12:53:45 UTC 2021 - Pedro Monreal + +- Fix building test t-lock with pthread. [bsc#1189745] + * Explicitly add -lpthread to compile the t-lock test. + * Add libgcrypt-pthread-in-t-lock-test.patch + +------------------------------------------------------------------- +Fri Jun 11 13:17:54 UTC 2021 - Pedro Monreal + +- Security fix: [bsc#1187212, CVE-2021-33560] + * cipher: Fix ElGamal encryption for other implementations. + * Exponent blinding was added in version 1.9.3. This patch + fixes ElGamal encryption, see: https://dev.gnupg.org/T5328 +- Add libgcrypt-CVE-2021-33560-fix-ElGamal-enc.patch + +------------------------------------------------------------------- +Tue Apr 20 08:46:11 UTC 2021 - Paolo Stivanin + +- libgcrypt 1.9.3: + * Bug fixes: + - Fix build problems on i386 using gcc-4.7. + - Fix checksum calculation in OCB decryption for AES on s390. + - Fix a regression in gcry_mpi_ec_add related to certain usages + of curve 25519. + - Fix a symbol not found problem on Apple M1. + - Fix for Apple iOS getentropy peculiarity. + - Make keygrip computation work for compressed points. + * Performance: + - Add x86_64 VAES/AVX2 accelerated implementation of Camellia. + - Add x86_64 VAES/AVX2 accelerated implementation of AES. + - Add VPMSUMD acceleration for GCM mode on PPC. + * Internal changes. + - Harden MPI conditional code against EM leakage. + - Harden Elgamal by introducing exponent blinding. + +------------------------------------------------------------------- +Wed Feb 17 09:49:55 UTC 2021 - Andreas Stieger + +- libgcrypt 1.9.2: + * Fix building with --disable-asm on x86 + * Check public key for ECDSA verify operation + * Make sure gcry_get_config (NULL) returns a nul-terminated + string + * Fix a memory leak in the ECDH code + * Fix a reading beyond end of input buffer in SHA2-avx2 +- remove obsolete texinfo packaging macros + +------------------------------------------------------------------- +Tue Feb 2 01:06:47 UTC 2021 - Pedro Monreal + +- Update to 1.9.1 + * *Fix exploitable bug* in hash functions introduced with + 1.9.0. [bsc#1181632, CVE-2021-3345] + * Return an error if a negative MPI is used with sexp scan + functions. + * Check for operational FIPS in the random and KDF functions. + * Fix compile error on ARMv7 with NEON disabled. + * Fix self-test in KDF module. + * Improve assembler checks for better LTO support. + * Fix 32-bit cross build on x86. + * Fix non-NEON ARM assembly implementation for SHA512. + * Fix build problems with the cipher_bulk_ops_t typedef. + * Fix Ed25519 private key handling for preceding ZEROs. + * Fix overflow in modular inverse implementation. + * Fix register access for AVX/AVX2 implementations of Blake2. + * Add optimized cipher and hash functions for s390x/zSeries. + * Use hardware bit counting functionx when available. + * Update DSA functions to match FIPS 186-3. + * New self-tests for CMACs and KDFs. + * Add bulk cipher functions for OFB and GCM modes. +- Update libgpg-error required version + +------------------------------------------------------------------- +Tue Feb 1 12:03:31 UTC 2021 - Pedro Monreal + +- Use the suffix variable correctly in get_hmac_path() +- Rebase libgcrypt-fips_selftest_trigger_file.patch + +------------------------------------------------------------------- +Mon Jan 25 12:38:35 UTC 2021 - Pedro Monreal + +- Add the global config file /etc/gcrypt/random.conf + * This file can be used to globally change parameters of the random + generator with the options: only-urandom and disable-jent. + +------------------------------------------------------------------- +Thu Jan 21 15:42:15 UTC 2021 - Pedro Monreal + +- Update to 1.9.0: + New stable branch of Libgcrypt with full API and ABI compatibility + to the 1.8 series. Release-info: https://dev.gnupg.org/T4294 + * New and extended interfaces: + - New curves Ed448, X448, and SM2. + - New cipher mode EAX. + - New cipher algo SM4. + - New hash algo SM3. + - New hash algo variants SHA512/224 and SHA512/256. + - New MAC algos for Blake-2 algorithms, the new SHA512 variants, + SM3, SM4 and for a GOST variant. + - New convenience function gcry_mpi_get_ui. + - gcry_sexp_extract_param understands new format specifiers to + directly store to integers and strings. + - New function gcry_ecc_mul_point and curve constants for Curve448 + and Curve25519. + - New function gcry_ecc_get_algo_keylen. + - New control code GCRYCTL_AUTO_EXPAND_SECMEM to allow growing the + secure memory area. + * Performance optimizations and bug fixes: See Release-info. + * Other features: + - Add OIDs from RFC-8410 as aliases for Ed25519 and Curve25519. + - Add mitigation against ECC timing attack CVE-2019-13627. + - Internal cleanup of the ECC implementation. + - Support reading EC point in compressed format for some curves. +- Rebase patches: + * libgcrypt-1.4.1-rijndael_no_strict_aliasing.patch + * libgcrypt-1.5.0-LIBGCRYPT_FORCE_FIPS_MODE-env.diff + * libgcrypt-1.6.1-use-fipscheck.patch + * drbg_test.patch + * libgcrypt-fipsdrv-enable-algo-for-dsa-sign.patch + * libgcrypt-FIPS-RSA-DSA-ECDSA-hashing-operation.patch + * libgcrypt-1.8.4-fips-keygen.patch + * libgcrypt-1.8.4-getrandom.patch + * libgcrypt-fix-tests-fipsmode.patch + * libgcrypt-global_init-constructor.patch + * libgcrypt-ecc-ecdsa-no-blinding.patch + * libgcrypt-PCT-RSA.patch + * libgcrypt-PCT-ECC.patch +- Remove patches: + * libgcrypt-unresolved-dladdr.patch + * libgcrypt-CVE-2019-12904-GCM-Prefetch.patch + * libgcrypt-CVE-2019-12904-GCM.patch + * libgcrypt-CVE-2019-12904-AES.patch + * libgcrypt-CMAC-AES-TDES-selftest.patch + * libgcrypt-1.6.1-fips-cfgrandom.patch + * libgcrypt-fips_rsa_no_enforced_mode.patch + +------------------------------------------------------------------- +Sat Oct 24 10:25:13 UTC 2020 - Andreas Stieger + +- libgcrypt 1.8.7: + * Support opaque MPI with gcry_mpi_print + * Fix extra entropy collection via clock_gettime, a fallback code + path for legacy hardware + +------------------------------------------------------------------- +Tue Jul 7 09:12:27 UTC 2020 - Pedro Monreal Gonzalez + +- Update to 1.8.6 + * mpi: Consider +0 and -0 the same in mpi_cmp + * mpi: Fix flags in mpi_copy for opaque MPI + * mpi: Fix the return value of mpi_invm_generic + * mpi: DSA,ECDSA: Fix use of mpi_invm + - Call mpi_invm before _gcry_dsa_modify_k + - Call mpi_invm before _gcry_ecc_ecdsa_sign + * mpi: Constant time mpi_inv with some conditions + - mpi/mpi-inv.c (mpih_add_n_cond, mpih_sub_n_cond, mpih_swap_cond) + - New: mpih_abs_cond, mpi_invm_odd + - Rename from _gcry_mpi_invm: mpi_invm_generic + - Use mpi_invm_odd for usual odd cases: _gcry_mpi_invm + * mpi: Abort on division by zero also in _gcry_mpi_tdiv_qr + * Fix wrong code execution in Poly1305 ARM/NEON implementation + - Set r14 to -1 at function entry: (_gcry_poly1305_armv7_neon_init_ext) + * Set vZZ.16b register to zero before use in armv8 gcm implementation + * random: Fix include of config.h + * Fix declaration of internal function _gcry_mpi_get_ui: Don't use ulong + * ecc: Fix wrong handling of shorten PK bytes + - Zeros are already recovered: (_gcry_ecc_mont_decodepoint) +- Update libgcrypt-ecc-ecdsa-no-blinding.patch + +------------------------------------------------------------------- +Tue May 19 11:25:37 UTC 2020 - Pedro Monreal Gonzalez + +- FIPS: RSA/DSA/ECC test_keys() print out debug messages [bsc#1171872] + * Print the debug messages in test_keys() only in debug mode. +- Update patches: libgcrypt-PCT-RSA.patch libgcrypt-PCT-DSA.patch + libgcrypt-PCT-ECC.patch + +------------------------------------------------------------------- +Mon Apr 27 08:55:12 UTC 2020 - Pedro Monreal Gonzalez + +- FIPS: libgcrypt: Double free in test_keys() on failed signature + verification [bsc#1169944] + * Use safer gcry_mpi_release() instead of mpi_free() +- Update patches: + * libgcrypt-PCT-DSA.patch + * libgcrypt-PCT-RSA.patch + * libgcrypt-PCT-ECC.patch + +------------------------------------------------------------------- +Thu Apr 16 16:45:23 UTC 2020 - Vítězslav Čížek + +- Ship the FIPS checksum file in the shared library package and + create a separate trigger file for the FIPS selftests (bsc#1169569) + * add libgcrypt-fips_selftest_trigger_file.patch + * refresh libgcrypt-global_init-constructor.patch +- Remove libgcrypt-binary_integrity_in_non-FIPS.patch obsoleted + by libgcrypt-global_init-constructor.patch + +------------------------------------------------------------------- +Wed Apr 15 13:55:27 UTC 2020 - Pedro Monreal Gonzalez + +- FIPS: Verify that the generated signature and the original input + differ in test_keys function for RSA, DSA and ECC: [bsc#1165539] +- Add zero-padding when qx and qy have different lengths when + assembling the Q point from affine coordinates. +- Refreshed patches: + * libgcrypt-PCT-DSA.patch + * libgcrypt-PCT-RSA.patch + * libgcrypt-PCT-ECC.patch + +------------------------------------------------------------------- +Mon Mar 30 10:48:02 UTC 2020 - Pedro Monreal Gonzalez + +- FIPS: Switch the PCT to use the new signature operation [bsc#1165539] + * Patches for DSA, RSA and ECDSA test_keys functions: + - libgcrypt-PCT-DSA.patch + - libgcrypt-PCT-RSA.patch + - libgcrypt-PCT-ECC.patch +- Update patch: libgcrypt-FIPS-RSA-DSA-ECDSA-hashing-operation.patch + +------------------------------------------------------------------- +Thu Mar 26 18:09:47 UTC 2020 - Pedro Monreal Gonzalez + +- FIPS: Run self-tests from constructor during power-on [bsc#1166748] + * Set up global_init as the constructor function: + - libgcrypt-global_init-constructor.patch + * Relax the entropy requirements on selftest. This is especially + important for virtual machines to boot properly before the RNG + is available: + - libgcrypt-random_selftests-testentropy.patch + - libgcrypt-rsa-no-blinding.patch + - libgcrypt-ecc-ecdsa-no-blinding.patch + * Fix benchmark regression test in FIPS mode: + - libgcrypt-FIPS-GMAC_AES-benckmark.patch + +------------------------------------------------------------------- +Thu Mar 12 16:54:33 UTC 2020 - Pedro Monreal Gonzalez + +- Remove check not needed in _gcry_global_constructor [bsc#1164950] + * Update libgcrypt-Restore-self-tests-from-constructor.patch + +------------------------------------------------------------------- +Tue Feb 25 22:13:24 UTC 2020 - Pedro Monreal Gonzalez + +- FIPS: Run the self-tests from the constructor [bsc#1164950] + * Add libgcrypt-invoke-global_init-from-constructor.patch + +------------------------------------------------------------------- +Fri Jan 17 17:35:15 UTC 2020 - Pedro Monreal Gonzalez + +- FIPS: libgcrypt DSA PQG parameter generation: Missing value [bsc#1161219] +- FIPS: libgcrypt DSA PQG verification incorrect results [bsc#1161215] +- FIPS: libgcrypt RSA siggen/keygen: 4k not supported [bsc#1161220] + * Add patch from Fedora libgcrypt-1.8.4-fips-keygen.patch + +------------------------------------------------------------------- +Wed Dec 11 10:18:23 UTC 2019 - Pedro Monreal Gonzalez + +- FIPS: RSA/DSA/ECDSA are missing hashing operation [bsc#1155337] + * Add libgcrypt-FIPS-RSA-DSA-ECDSA-hashing-operation.patch + +------------------------------------------------------------------- +Wed Nov 27 14:01:01 UTC 2019 - Pedro Monreal Gonzalez + +- Fix tests in FIPS mode: + * Fix tests: basic benchmark bench-slope pubkey t-cv25519 t-secmem + * Add patch libgcrypt-fix-tests-fipsmode.patch + +------------------------------------------------------------------- +Tue Nov 26 18:48:20 UTC 2019 - Pedro Monreal Gonzalez + +- Fix test dsa-rfc6979 in FIPS mode: + * Disable tests in elliptic curves with 192 bits which are not + recommended in FIPS mode + * Add patch libgcrypt-dsa-rfc6979-test-fix.patch + +------------------------------------------------------------------- +Tue Nov 12 11:05:02 UTC 2019 - Pedro Monreal Gonzalez + +- CMAC AES and TDES FIPS self-tests: + * CMAC AES self test missing [bsc#1155339] + * CMAC TDES self test missing [bsc#1155338] +- Add libgcrypt-CMAC-AES-TDES-selftest.patch + +------------------------------------------------------------------- +Fri Aug 30 14:17:48 UTC 2019 - Andreas Stieger + +- libgcrypt 1.8.5: + * CVE-2019-13627: mitigation against an ECDSA timing attack (boo#1148987) + * Improve ECDSA unblinding + * Provide a pkg-config file + +------------------------------------------------------------------- +Wed Jun 26 06:52:54 UTC 2019 - Jason Sikes + +- Fixed redundant fips tests in some situations causing sudo to stop + working when pam-kwallet is installed. bsc#1133808 + * Added libgcrypt-1.8.4-fips_ctor_skip_integrity_check.patch + * Removed libgcrypt-fips_run_selftest_at_constructor.patch + because it was obsoleted by libgcrypt-1.8.3-fips-ctor.patch + * Removed libgcrypt-fips_ignore_FIPS_MODULE_PATH.patch + because it was obsoleted by libgcrypt-1.8.4-fips_ctor_skip_integrity_check.patch + +------------------------------------------------------------------- +Fri Jun 21 16:53:07 UTC 2019 - Pedro Monreal Gonzalez + +- Fixed env-script-interpreter in cavs_driver.pl + +------------------------------------------------------------------- +Fri Jun 21 16:39:00 UTC 2019 - Pedro Monreal Gonzalez + +- Security fix: [bsc#1138939, CVE-2019-12904] + * The C implementation of AES is vulnerable to a flush-and-reload + side-channel attack because physical addresses are available to + other processes. (The C implementation is used on platforms where + an assembly-language implementation is unavailable.) + * Added patches: + - libgcrypt-CVE-2019-12904-GCM-Prefetch.patch + - libgcrypt-CVE-2019-12904-GCM.patch + - libgcrypt-CVE-2019-12904-AES.patch + +------------------------------------------------------------------- +Fri Apr 26 06:47:45 UTC 2019 - Jason Sikes + +- do not try to open /dev/urandom if getrandom() works + * Added libgcrypt-1.8.4-getrandom.patch +- Drop libgcrypt-init-at-elf-load-fips.patch obsoleted + by libgcrypt-1.8.3-fips-ctor.patch + +------------------------------------------------------------------- +Tue Apr 23 12:38:40 UTC 2019 - Jason Sikes + +- Restored libgcrypt-binary_integrity_in_non-FIPS.patch sans section that + was partially causing bsc#1131183. +- Fixed race condition in multi-threaded applications by allowing a FSM state + transition to the current state. This means some tests are run twice. + * Added libgcrypt-1.8.4-allow_FSM_same_state.patch +- Fixed an issue in malloc/free wrappers so that memory created by the malloc() + wrappers will be destroyed using the free() wrappers. + * Added libgcrypt-1.8.4-use_xfree.patch + +------------------------------------------------------------------- +Fri Apr 5 21:56:00 UTC 2019 - Jason Sikes + +- removed libgcrypt-binary_integrity_in_non-FIPS.patch since it was breaking + libotr. bsc#1131183 + +------------------------------------------------------------------- +Tue Mar 26 16:30:23 UTC 2019 - Vítězslav Čížek + +- libgcrypt-1.8.3-fips-ctor.patch changed the way the fips selftests + are invoked as well as the state transition, adjust the code so + a missing checksum file is not an issue in non-FIPS mode (bsc#1097073) + * update libgcrypt-binary_integrity_in_non-FIPS.patch + +------------------------------------------------------------------- +Tue Mar 26 16:25:18 UTC 2019 - Vítězslav Čížek + +- Enforce the minimal RSA keygen size in fips mode (bsc#1125740) + * add libgcrypt-fips_rsa_no_enforced_mode.patch + +------------------------------------------------------------------- +Fri Mar 22 14:13:05 UTC 2019 - Vítězslav Čížek + +- Don't run full self-tests from constructor (bsc#1097073) + * Don't call global_init() from the constructor, _gcry_global_constructor() + from libgcrypt-1.8.3-fips-ctor.patch takes care of the binary + integrity check instead. + * Only the binary checksum will be verified, the remaining + self-tests will be run upon the library initialization +- Add libgcrypt-fips_ignore_FIPS_MODULE_PATH.patch +- Drop libgcrypt-init-at-elf-load-fips.patch and + libgcrypt-fips_run_selftest_at_constructor.patch obsoleted + by libgcrypt-1.8.3-fips-ctor.patch + +------------------------------------------------------------------- +Thu Mar 7 10:53:40 UTC 2019 - Pedro Monreal Gonzalez + +- Skip all the self-tests except for binary integrity when called + from the constructor (bsc#1097073) + * Added libgcrypt-1.8.3-fips-ctor.patch from Fedora + +------------------------------------------------------------------- +Mon Nov 26 17:09:47 UTC 2018 - Vítězslav Čížek + +- Fail selftests when checksum file is missing in FIPS mode only + (bsc#1117355) + * add libgcrypt-binary_integrity_in_non-FIPS.patch + +------------------------------------------------------------------- +Sun Oct 28 18:57:53 UTC 2018 - astieger@suse.com + +- libgcrypt 1.8.4: + * Fix infinite loop with specific application implementations + * Fix possible leak of a few bits of secret primes to pageable + memory + * Fix possible hang in the RNG (1.8.3) + * Always make use of getrandom if possible and then use + its /dev/urandom behaviour + +------------------------------------------------------------------- +Mon Jul 2 10:38:42 UTC 2018 - schwab@suse.de + +- libgcrypt-1.6.3-aliasing.patch, libgcrypt-ppc64.patch, + libgcrypt-strict-aliasing.patch: Remove obsolete patches +- libgcrypt-1.4.1-rijndael_no_strict_aliasing.patch: Rediff +- Reenable testsuite + +------------------------------------------------------------------- +Wed Jun 13 10:46:33 UTC 2018 - kbabioch@suse.com + +- Update to version 1.8.3: + - Use blinding for ECDSA signing to mitigate a novel side-channel + attack. (CVE-2018-0495 bsc#1097410) + - Fix incorrect counter overflow handling for GCM when using an IV + size other than 96 bit. + - Fix incorrect output of AES-keywrap mode for in-place encryption + on some platforms. + - Fix the gcry_mpi_ec_curve_point point validation function. + - Fix rare assertion failure in gcry_prime_check. +- Applied spec-cleaner + +------------------------------------------------------------------- +Wed May 2 14:31:07 UTC 2018 - pmonrealgonzalez@suse.com + +- Suggest libgcrypt20-hmac for package libgcrypt20 to ensure they + are installed in the right order. [bsc#1090766] + +------------------------------------------------------------------- +Thu Mar 29 06:37:44 UTC 2018 - pmonrealgonzalez@suse.com + +- Extended the fipsdrv dsa-sign and dsa-verify commands with the + --algo parameter for the FIPS testing of DSA SigVer and SigGen + (bsc#1064455). + * Added libgcrypt-fipsdrv-enable-algo-for-dsa-sign.patch + * Added libgcrypt-fipsdrv-enable-algo-for-dsa-verify.patch + +------------------------------------------------------------------- +Thu Feb 22 15:10:36 UTC 2018 - fvogt@suse.com + +- Use %license (boo#1082318) + +------------------------------------------------------------------- +Wed Dec 13 20:09:28 UTC 2017 - astieger@suse.com + +- libgcrypt 1.8.2: + * Fix fatal out of secure memory status in the s-expression + parser on heavy loaded systems. + * Add auto expand secmem feature or use by GnuPG 2.2.4 + +------------------------------------------------------------------- +Mon Aug 28 17:54:24 UTC 2017 - astieger@suse.com + +- libgcrypt 1.8.1: + * Mitigate a local side-channel attack on Curve25519 dubbed "May + the Fourth be With You" CVE-2017-0379 bsc#1055837 + * Add more extra bytes to the pool after reading a seed file + * Add the OID SHA384WithECDSA from RFC-7427 to SHA-384 + * Fix build problems with the Jitter RNG + * Fix assembler code build problems on Rasbian (ARMv8/AArch32-CE) + +------------------------------------------------------------------- +Mon Jul 24 23:43:40 UTC 2017 - jengelh@inai.de + +- RPM group fixes. + +------------------------------------------------------------------- +Fri Jul 21 15:50:14 UTC 2017 - astieger@suse.com + +- libgcrypt 1.8.0: + * New cipher mode XTS + * New hash function Blake-2 + * New function gcry_mpi_point_copy. + * New function gcry_get_config. + * GCRYCTL_REINIT_SYSCALL_CLAMP allows to init nPth after Libgcrypt. + * New gobal configuration file /etc/gcrypt/random.conf. + * GCRYCTL_PRINT_CONFIG does now also print build information for + libgpg-error and the used compiler version. + * GCRY_CIPHER_MODE_CFB8 is now supported. + * A jitter based entropy collector is now used in addition to the + other entropy collectors. + * Optimized gcry_md_hash_buffers for SHA-256 and SHA-512. + random pool lock). + * Interface changes relative to the 1.7.0 release: + gcry_get_config NEW function. + gcry_mpi_point_copy NEW function. + GCRYCTL_REINIT_SYSCALL_CLAMP NEW macro. + GCRY_MD_BLAKE2B_512 NEW constant. + GCRY_MD_BLAKE2B_384 NEW constant. + GCRY_MD_BLAKE2B_256 NEW constant. + GCRY_MD_BLAKE2B_160 NEW constant. + GCRY_MD_BLAKE2S_256 NEW constant. + GCRY_MD_BLAKE2S_224 NEW constant. + GCRY_MD_BLAKE2S_160 NEW constant. + GCRY_MD_BLAKE2S_128 NEW constant. + GCRY_CIPHER_MODE_XTS NEW constant. + gcry_md_info DEPRECATED. +- Refresh patch libgcrypt-1.6.3-aliasing.patch + +------------------------------------------------------------------- +Thu Jun 29 09:49:44 UTC 2017 - astieger@suse.com + +- libgcrypt 1.7.8: + * CVE-2017-7526: Mitigate a flush+reload side-channel attack on + RSA secret keys (bsc#1046607) + +------------------------------------------------------------------- +Sun Jun 4 19:26:12 UTC 2017 - astieger@suse.com + +- libgcrypt 1.7.7: + * Fix possible timing attack on EdDSA session key (previously + patched, drop libgcrypt-secure-EdDSA-session-key.patch) + * Fix long standing bug in secure memory implementation which + could lead to a segv on free + +------------------------------------------------------------------- +Fri Jun 2 10:05:18 UTC 2017 - pmonrealgonzalez@suse.com + +- Added libgcrypt-secure-EdDSA-session-key.patch [bsc#1042326] + * Store the session key in secure memory to ensure that constant + time point operations are used in the MPI library. + +------------------------------------------------------------------- +Fri Jan 20 09:41:15 UTC 2017 - rmaliska@suse.com + +- libgcrypt 1.7.6: + * Fix counter operand from read-only to read/write + * Fix too large jump alignment in mpih-rshift + +------------------------------------------------------------------- +Thu Dec 15 10:32:18 UTC 2016 - astieger@suse.com + +- libgcrypt 1.7.5: + * Fix regression in mlock detection introduced with 1.7.4 + +------------------------------------------------------------------- +Tue Dec 13 12:20:47 UTC 2016 - astieger@suse.com + +- libgcrypt 1.7.4: + * ARMv8/AArch32 performance improvements for AES, GCM, SHA-256, + and SHA-1. + * Add ARMv8/AArch32 assembly implementation for Twofish and + Camellia. + * Add bulk processing implementation for ARMv8/AArch32. + * Add Stribog OIDs. + * Improve the DRBG performance and sync the code with the Linux + version. + * When secure memory is requested by the MPI functions or by + gcry_xmalloc_secure, they do not anymore lead to a fatal error + if the secure memory pool is used up. Instead new pools are + allocated as needed. These new pools are not protected against + being swapped out (mlock can't be used). Mitigation for + minor confidentiality issues is encryption swap space. + * Fix GOST 28147 CryptoPro-B S-box. + * Fix error code handling of mlock calls. + +------------------------------------------------------------------- +Sat Aug 20 10:38:15 UTC 2016 - mpluskal,vcizek,astieger}@suse.com + +- libgcrypt 1.7.3: + * security issue already fixes with 1.6.6 + * Fix building of some asm modules with older compilers and CPUs. + * ARMv8/AArch32 improvements for AES, GCM, SHA-256, and SHA-1. +- includes changes from libgcrypt 1.7.2: + * Bug fixes: + - Fix setting of the ECC cofactor if parameters are specified. + - Fix memory leak in the ECC code. + - Remove debug message about unsupported getrandom syscall. + - Fix build problems related to AVX use. + - Fix bus errors on ARM for Poly1305, ChaCha20, AES, and SHA-512. + * Internal changes: + - Improved fatal error message for wrong use of gcry_md_read. + - Disallow symmetric encryption/decryption if key is not set. +- includes changes from 1.7.1: + * Bug fixes: + - Fix ecc_verify for cofactor support. + - Fix portability bug when using gcc with Solaris 9 SPARC. + - Build fix for OpenBSD/amd64 + - Add OIDs to the Serpent ciphers. + * Internal changes: + - Use getrandom system call on Linux if available. + - Blinding is now also used for RSA signature creation. + - Changed names of debug envvars +- includes changes from 1.7.0: + * New algorithms and modes: + - SHA3-224, SHA3-256, SHA3-384, SHA3-512, and MD2 hash algorithms. + - SHAKE128 and SHAKE256 extendable-output hash algorithms. + - ChaCha20 stream cipher. + - Poly1305 message authentication algorithm + - ChaCha20-Poly1305 Authenticated Encryption with Associated Data + mode. + - OCB mode. + - HMAC-MD2 for use by legacy applications. + * New curves for ECC: + - Curve25519. + - sec256k1. + - GOST R 34.10-2001 and GOST R 34.10-2012. + * Performance: + - Improved performance of KDF functions. + - Assembler optimized implementations of Blowfish and Serpent on + ARM. + - Assembler optimized implementation of 3DES on x86. + - Improved AES using the SSSE3 based vector permutation method by + Mike Hamburg. + - AVX/BMI is used for SHA-1 and SHA-256 on x86. This is for SHA-1 + about 20% faster than SSSE3 and more than 100% faster than the + generic C implementation. + - 40% speedup for SHA-512 and 72% for SHA-1 on ARM Cortex-A8. + - 60-90% speedup for Whirlpool on x86. + - 300% speedup for RIPE MD-160. + - Up to 11 times speedup for CRC functions on x86. + * Other features: + - Improved ECDSA and FIPS 186-4 compliance. + - Support for Montgomery curves. + - gcry_cipher_set_sbox to tweak S-boxes of the gost28147 cipher + algorithm. + - gcry_mpi_ec_sub to subtract two points on a curve. + - gcry_mpi_ec_decode_point to decode an MPI into a point object. + - Emulation for broken Whirlpool code prior to 1.6.0. [from 1.6.1] + - Flag "pkcs1-raw" to enable PCKS#1 padding with a user supplied + hash part. + - Parameter "saltlen" to set a non-default salt length for RSA PSS. + - A SP800-90A conforming DRNG replaces the former X9.31 alternative + random number generator. + - Map deprecated RSA algo number to the RSA algo number for better + backward compatibility. [from 1.6.2] + - Use ciphertext blinding for Elgamal decryption [CVE-2014-3591]. + See http://www.cs.tau.ac.il/~tromer/radioexp/ for details. + [from 1.6.3] + - Fixed data-dependent timing variations in modular exponentiation + [related to CVE-2015-0837, Last-Level Cache Side-Channel Attacks + are Practical]. [from 1.6.3] + - Flag "no-keytest" for ECC key generation. Due to a bug in + the parser that flag will also be accepted but ignored by older + version of Libgcrypt. [from 1.6.4] + - Speed up the random number generator by requiring less extra + seeding. [from 1.6.4] + - Always verify a created RSA signature to avoid private key leaks + due to hardware failures. [from 1.6.4] + - Mitigate side-channel attack on ECDH with Weierstrass curves + [CVE-2015-7511]. See http://www.cs.tau.ac.IL/~tromer/ecdh/ for + details. [from 1.6.5] + * Internal changes: + - Moved locking out to libgpg-error. + - Support of the SYSROOT envvar in the build system. + - Refactor some code. + - The availability of a 64 bit integer type is now mandatory. + * Bug fixes: + - Fixed message digest lookup by OID (regression in 1.6.0). + - Fixed a build problem on NetBSD + - Fixed some asm build problems and feature detection bugs. + * Interface changes relative to the 1.6.0 release: + gcry_cipher_final NEW macro. + GCRY_CIPHER_MODE_CFB8 NEW constant. + GCRY_CIPHER_MODE_OCB NEW. + GCRY_CIPHER_MODE_POLY1305 NEW. + gcry_cipher_set_sbox NEW macro. + gcry_mac_get_algo NEW. + GCRY_MAC_HMAC_MD2 NEW. + GCRY_MAC_HMAC_SHA3_224 NEW. + GCRY_MAC_HMAC_SHA3_256 NEW. + GCRY_MAC_HMAC_SHA3_384 NEW. + GCRY_MAC_HMAC_SHA3_512 NEW. + GCRY_MAC_POLY1305 NEW. + GCRY_MAC_POLY1305_AES NEW. + GCRY_MAC_POLY1305_CAMELLIA NEW. + GCRY_MAC_POLY1305_SEED NEW. + GCRY_MAC_POLY1305_SERPENT NEW. + GCRY_MAC_POLY1305_TWOFISH NEW. + gcry_md_extract NEW. + GCRY_MD_FLAG_BUGEMU1 NEW [from 1.6.1]. + GCRY_MD_GOSTR3411_CP NEW. + GCRY_MD_SHA3_224 NEW. + GCRY_MD_SHA3_256 NEW. + GCRY_MD_SHA3_384 NEW. + GCRY_MD_SHA3_512 NEW. + GCRY_MD_SHAKE128 NEW. + GCRY_MD_SHAKE256 NEW. + gcry_mpi_ec_decode_point NEW. + gcry_mpi_ec_sub NEW. + GCRY_PK_EDDSA NEW constant. + GCRYCTL_GET_TAGLEN NEW. + GCRYCTL_SET_SBOX NEW. + GCRYCTL_SET_TAGLEN NEW. +- Apply libgcrypt-1.6.3-aliasing.patch only on big-endian + architectures +- update drbg_test.patch and install cavs testing directory again +- As DRBG is upstream, drop pateches: + v9-0001-SP800-90A-Deterministic-Random-Bit-Generator.patch + 0002-Compile-DRBG.patch + 0003-Function-definitions-of-interfaces-for-random.c.patch + 0004-Invoke-DRBG-from-common-libgcrypt-RNG-code.patch + 0005-Function-definitions-for-gcry_control-callbacks.patch + 0006-DRBG-specific-gcry_control-requests.patch + v9-0007-User-interface-to-DRBG.patch + libgcrypt-fix-rng.patch +- drop obsolete: + libgcrypt-fips-dsa.patch + libgcrypt-fips_ecdsa.patch + +------------------------------------------------------------------- +Wed Aug 17 18:21:44 UTC 2016 - astieger@suse.com + +- libgcrypt 1.6.6: + * fix CVE-2016-6313: Issue in the mixing functions of the random + number generators allowed an attacker who obtained a number of + bytes from the standard RNG to predict some of the next ouput. + (bsc#994157) + +------------------------------------------------------------------- +Mon May 16 14:37:45 UTC 2016 - pjanouch@suse.de + +- remove conditionals for unsupported distributions (before 13.2), + it would not build anyway because of new dependencies + +------------------------------------------------------------------- +Mon May 16 12:36:14 UTC 2016 - pjanouch@suse.de + +- make the -hmac package depend on the same version of the library, + fixing bsc#979629 FIPS: system fails to reboot after installing + fips pattern + +------------------------------------------------------------------- +Tue Feb 9 20:51:59 UTC 2016 - astieger@suse.com + +- update to 1.6.5: + * CVE-2015-7511: Mitigate side-channel attack on ECDH with + Weierstrass curves (boo#965902) + +------------------------------------------------------------------- +Sat Oct 10 11:56:08 UTC 2015 - astieger@suse.com + +- follow-up to libgcrypt 1.6.4 update: sosuffix is 20.0.4 + +------------------------------------------------------------------- +Tue Sep 8 08:03:19 UTC 2015 - vcizek@suse.com + +- update to 1.6.4 +- fixes libgcrypt equivalent of CVE-2015-5738 (bsc#944456) + * Speed up the random number generator by requiring less extra + seeding. + * New flag "no-keytest" for ECC key generation. Due to a bug in the + parser that flag will also be accepted but ignored by older version + of Libgcrypt. + * Always verify a created RSA signature to avoid private key leaks + due to hardware failures. + * Other minor bug fixes. + +------------------------------------------------------------------- +Tue Jun 23 15:15:30 UTC 2015 - dvaleev@suse.com + +- Fix gpg2 tests on BigEndian architectures: s390x ppc64 + libgcrypt-1.6.3-aliasing.patch + +------------------------------------------------------------------- +Sun Mar 1 21:16:26 UTC 2015 - astieger@suse.com + +- fix sosuffix for 1.6.3 (20.0.3) + +------------------------------------------------------------------- +Sat Feb 28 19:31:10 UTC 2015 - astieger@suse.com + +- libgcrypt 1.6.3 [bnc#920057]: + * Use ciphertext blinding for Elgamal decryption [CVE-2014-3591]. + * Fixed data-dependent timing variations in modular exponentiation + [related to CVE-2015-0837, Last-Level Cache Side-Channel Attacks + are Practical]. +- update upstream signing keyring + +------------------------------------------------------------------- +Fri Feb 6 18:42:28 UTC 2015 - coolo@suse.com + +- making the build reproducible - see + http://lists.gnupg.org/pipermail/gnupg-commits/2014-September/010683.html + for a very similiar problem + +------------------------------------------------------------------- +Fri Feb 6 18:38:55 UTC 2015 - dimstar@opensuse.org + +- Move %install_info_delete calls from postun to preun: the files + must still be present to be parsed. +- Fix the names passed to install_info for gcrypt.info-[12].gz + instead of gcrypt-[12].info.gz. + +------------------------------------------------------------------- +Fri Feb 6 18:30:26 UTC 2015 - coolo@suse.com + +- fix filename for info pages in %post scripts + +------------------------------------------------------------------- +Wed Nov 5 20:37:24 UTC 2014 - andreas.stieger@gmx.de + +- libgcrypt 1.6.2: + * Map deprecated RSA algo number to the RSA algo number for better + backward compatibility. + * Support a 0x40 compression prefix for EdDSA. + * Improve ARM hardware feature detection and building. + * Fix building for the x32 ABI platform. + * Fix some possible NULL deref bugs. +- remove libgcrypt-1.6.0-use-intenal-functions.patch, upstream + via xtrymalloc macro +- remove libgcrypt-fixed-sizet.patch, upstream +- adjust libgcrypt-1.6.1-use-fipscheck.patch for xtrymalloc change + +------------------------------------------------------------------- +Sun Sep 21 10:08:39 UTC 2014 - vcizek@suse.com + +- disabled curve P-192 in FIPS mode (bnc#896202) + * added libgcrypt-fips_ecdsa.patch +- don't use SHA-1 for ECDSA in FIPS mode +- also run the fips self tests only in FIPS mode + +------------------------------------------------------------------- +Tue Sep 16 13:56:01 UTC 2014 - vcizek@suse.com + +- run the fips self tests at the constructor code + * added libgcrypt-fips_run_selftest_at_constructor.patch + +------------------------------------------------------------------- +Tue Sep 16 12:17:17 UTC 2014 - vcizek@suse.com + +- rewrite the DSA-2 code to be FIPS 186-4 compliant (bnc#894216) + * added libgcrypt-fips-dsa.patch + * install fips186_dsa +- use 2048 bit keys in selftests_dsa + +------------------------------------------------------------------- +Mon Sep 1 10:57:06 UTC 2014 - vcizek@suse.com + +- fix an issue in DRBG patchset + * size_t type is 32-bit on 32-bit systems +- fix a potential NULL pointer deference in DRBG patchset + * patches from https://bugs.g10code.com/gnupg/issue1701 +- added v9-0001-SP800-90A-Deterministic-Random-Bit-Generator.patch +- added v9-0007-User-interface-to-DRBG.patch +- removed v7-0001-SP800-90A-Deterministic-Random-Bit-Generator.patch +- removed v7-0007-User-interface-to-DRBG.patch +- add a subpackage for CAVS testing + * add cavs_driver.pl and cavs-test.sh from the kernel cavs package + * added drbg_test.patch + +------------------------------------------------------------------- +Tue Aug 12 07:43:19 UTC 2014 - meissner@suse.com + +- split off the -hmac package that contains the checksums + +------------------------------------------------------------------- +Mon May 26 12:05:17 UTC 2014 - meissner@suse.com + +- libgcrypt-fix-rng.patch: make drbg work again in FIPS mode. +- libgcrypt-1.6.1-use-fipscheck.patch: library to test is libgcrypt.so.20 + and not libgcrypt.so.11 +- libgcrypt-init-at-elf-load-fips.patch: initialize globally on ELF + DSO loading to meet FIPS requirements. + +------------------------------------------------------------------- +Tue May 13 10:47:51 UTC 2014 - vcizek@suse.com + +- add new 0007-User-interface-to-DRBG.patch from upstream + * fixes bnc#877233 + * supersedes the patch from previous entry + +------------------------------------------------------------------- +Sun May 12 13:25:33 UTC 2014 - tittiatcoke@gmail.com + +- Correct patch 0007-User-interface-to-DRBG.patch so that the + struct used in the route matches the header of the function + +------------------------------------------------------------------- +Tue May 6 13:28:33 UTC 2014 - vcizek@suse.com + +- add support for SP800-90A DRBG (fate#316929, bnc#856312) + * patches by Stephan Mueller (http://www.chronox.de/drbg.html): + 0001-SP800-90A-Deterministic-Random-Bit-Generator.patch.bz2 + 0002-Compile-DRBG.patch + 0003-Function-definitions-of-interfaces-for-random.c.patch + 0004-Invoke-DRBG-from-common-libgcrypt-RNG-code.patch + 0005-Function-definitions-for-gcry_control-callbacks.patch + 0006-DRBG-specific-gcry_control-requests.patch + 0007-User-interface-to-DRBG.patch + * only after 13.1 (the patches need libgpg-error 1.13) +- drop libgcrypt-fips-allow-legacy.patch (not needed and wasn't + applied anyway) + +------------------------------------------------------------------- +Thu Apr 3 12:04:46 UTC 2014 - tchvatal@suse.com + +- Cleanup with spec-cleaner to sort out. +- Really apply ppc64 patch as it was ommited probably by mistake. + +------------------------------------------------------------------- +Thu Mar 27 14:57:22 UTC 2014 - meissner@suse.com + +- FIPS changes (from Fedora): + - replaced libgcrypt-1.5.0-etc_gcrypt_rngseed-symlink.diff by + libgcrypt-1.6.1-fips-cfgrandom.patch + - libgcrypt-fixed-sizet.patch: fixed an int type for -flto + - libgcrypt-1.6.1-use-fipscheck.patch: use the fipscheck binary + - libgcrypt-1.6.1-fips-cavs.patch: add CAVS tests +- use fipscheck only after 13.1 +- libgcrypt-fips-allow-legacy.patch: attempt to allow some + legacy algorithms for gpg2 usage even in FIPS mode. + (currently not applied) + +------------------------------------------------------------------- +Thu Jan 30 13:29:49 UTC 2014 - idonmez@suse.com + +- Drop arm-missing-files.diff, fixed upstream + +------------------------------------------------------------------- +Wed Jan 29 18:40:49 UTC 2014 - andreas.stieger@gmx.de + +- libgcrypt 1.6.1, a bugfix release with the folloging fixes: + * Added emulation for broken Whirlpool code prior to 1.6.0. + * Improved performance of KDF functions. + * Improved ECDSA compliance. + * Fixed message digest lookup by OID (regression in 1.6.0). + * Fixed memory leaks in ECC code. + * Fixed some asm build problems and feature detection bugs. + * Interface changes relative to the 1.6.0 release: + GCRY_MD_FLAG_BUGEMU1 NEW (minor API change). + +------------------------------------------------------------------- +Fri Jan 3 16:36:21 UTC 2014 - dmueller@suse.com + +- add arm-missing-files.diff: Add missing files to fix build + +------------------------------------------------------------------- +Fri Jan 3 09:43:39 UTC 2014 - mvyskocil@suse.com + +- fix bnc#856915: can't open /dev/urandom + * correct libgcrypt-1.5.0-etc_gcrypt_rngseed-symlink.diff +- require libgpg-error 1.11 or higher + +------------------------------------------------------------------- +Thu Dec 19 13:53:21 UTC 2013 - mvyskocil@suse.com + +- fix dependency for 32bit devel package +- name hmac files according soname +- fix hmac subpackage dependency + +------------------------------------------------------------------- +Thu Dec 19 09:03:21 UTC 2013 - mvyskocil@suse.com + +- update to 1.6. + * Removed the long deprecated gcry_ac interface. Thus Libgcrypt is + not anymore ABI compatible to previous versions if they used the ac + interface. Check NEWS in libgcrypt-devel for removed interfaces. + * Removed the module register subsystem. + * The deprecated message digest debug macros have been removed. Use + gcry_md_debug instead. + * Removed deprecated control codes. + * Improved performance of most cipher algorithms as well as for the + SHA family of hash functions. + * Added support for the IDEA cipher algorithm. + * Added support for the Salsa20 and reduced Salsa20/12 stream ciphers. + * Added limited support for the GOST 28147-89 cipher algorithm. + * Added support for the GOST R 34.11-94 and R 34.11-2012 (Stribog) + hash algorithms. + * Added a random number generator to directly use the system's RNG. + Also added an interface to prefer the use of a specified RNG. + * Added support for the SCRYPT algorithm. + * Mitigated the Yarom/Falkner flush+reload side-channel attack on RSA + secret keys. See [CVE-2013-4242]. + * Added support for Deterministic DSA as per RFC-6969. + * Added support for curve Ed25519. + * Added a scatter gather hash convenience function. + * Added several MPI amd SEXP helper functions. + * Added support for negative numbers to gcry_mpi_print, + gcry_mpi_aprint and gcry_mpi_scan. + * The algorithm ids GCRY_PK_ECDSA and GCRY_PK_ECDH are now + deprecated. Use GCRY_PK_ECC if you need an algorithm id. + * Changed gcry_pk_genkey for "ecc" to only include the curve name and + not the parameters. The flag "param" may be used to revert this. + * Added a feature to globally disable selected hardware features. + * Added debug helper functions. +- rebased patches + * libgcrypt-1.5.0-etc_gcrypt_rngseed-symlink.diff + * libgcrypt-ppc64.patch +- add libgcrypt-1.6.0-use-intenal-functions.patch to fix fips.c build +- Move all documentation to -devel package + +------------------------------------------------------------------- +Fri Jul 26 22:05:46 UTC 2013 - andreas.stieger@gmx.de + +- update to 1.5.3 [bnc#831359] CVE-2013-4242 + * Mitigate the Yarom/Falkner flush+reload side-channel attack on + RSA secret keys. See . + +------------------------------------------------------------------- +Thu Jul 25 09:15:43 UTC 2013 - mvyskocil@suse.com + +- port SLE enhancenments to Factory (bnc#831028) + * add libgcrypt-unresolved-dladdr.patch (bnc#701267) + * add libgcrypt-1.5.0-etc_gcrypt_rngseed-symlink.diff (bnc#724841) + * add libgcrypt-1.5.0-LIBGCRYPT_FORCE_FIPS_MODE-env.diff +- install .hmac256.hmac (bnc#704068) +- enable varuous new options in configure (m-guard, hmac binary check and + random device linux) +- build with all ciphers, pubkeys and digest by default as whitelist + simply allowed them all + +------------------------------------------------------------------- +Mon Jun 17 13:22:33 UTC 2013 - coolo@suse.com + +- avoid gpg-offline in bootstrap packages + +------------------------------------------------------------------- +Sun Jun 16 22:56:56 UTC 2013 - crrodriguez@opensuse.org + +- Library must be built with large file support in + 32 bit archs. + +------------------------------------------------------------------- +Thu Apr 18 18:23:36 UTC 2013 - andreas.stieger@gmx.de + +- update to 1.5.2 + * The upstream sources now contain the IDEA algorithm, dropping: + idea.c.gz + libgcrypt-1.5.0-idea.patch + libgcrypt-1.5.0-idea_codecleanup.patch + * Made the Padlock code work again (regression since 1.5.0). + * Fixed alignment problems for Serpent. + * Fixed two bugs in ECC computations. + +------------------------------------------------------------------- +Fri Mar 22 09:31:11 UTC 2013 - mvyskocil@suse.com + +- add GPL3.0+ to License tag because of dumpsexp (bnc#810759) + +------------------------------------------------------------------- +Mon Mar 18 20:41:00 UTC 2013 - andreas.stieger@gmx.de + +- update to 1.5.1 + * Allow empty passphrase with PBKDF2. + * Do not abort on an invalid algorithm number in + gcry_cipher_get_algo_keylen and gcry_cipher_get_algo_blklen. + * Fixed some Valgrind warnings. + * Fixed a problem with select and high fd numbers. + * Improved the build system + * Various minor bug fixes. + * Interface changes relative to the 1.5.0 release: + GCRYCTL_SET_ENFORCED_FIPS_FLAG NEW. + GCRYPT_VERSION_NUMBER NEW. +- add verification of source code signatures +- now requires automake 1.11 to build + +------------------------------------------------------------------- +Sat Feb 2 18:51:33 UTC 2013 - coolo@suse.com + +- update license to new format + +------------------------------------------------------------------- +Tue Jun 12 21:19:18 UTC 2012 - chris@computersalat.de + +- fix deps + * libgpg-error-devel >= 1.8 +- add libsoname macro + +------------------------------------------------------------------- +Sun Feb 12 15:23:56 UTC 2012 - crrodriguez@opensuse.org + +- Libraries back into %{_libdir}, /usr merge project + +------------------------------------------------------------------- +Sat Dec 24 23:51:26 UTC 2011 - opensuse@dstoecker.de + +- add the missing IDEA algorithm after the patent is no longer relevant + +------------------------------------------------------------------ +Sun Nov 13 14:37:29 UTC 2011 - jengelh@medozas.de + +- Remove redundant/unwanted tags/section (cf. specfile guidelines) + +------------------------------------------------------------------- +Sun Nov 13 09:16:36 UTC 2011 - coolo@suse.com + +- add libtool as explicit buildrequire to avoid implicit dependency from prjconf + +------------------------------------------------------------------- +Sun Oct 2 18:38:28 UTC 2011 - crrodriguez@opensuse.org + +- Update to version 1.5.0, most important changes + * Uses the Intel AES-NI instructions if available + * Support ECDH. + +------------------------------------------------------------------- +Fri Nov 19 09:59:41 UTC 2010 - mvyskocil@suse.cz + +- update to 1.4.6 + * Fixed minor memory leak in DSA key generation. + * No more switching to FIPS mode if /proc/version is not readable. + * Fixed a sigill during Padlock detection on old CPUs. + * Boosted SHA-512 performance by 30% on ia32 boxes and gcc 4.3; + SHA-256 went up by 25%. + * New variants of the TIGER algorithm. + * New cipher algorithm mode for AES-WRAP. + * Interface changes relative to the 1.4.2 release: + GCRY_MD_TIGER1 NEW + GCRY_MD_TIGER2 NEW + GCRY_CIPHER_MODE_AESWRAP NEW + +------------------------------------------------------------------- +Sun Jul 4 19:07:16 UTC 2010 - jengelh@medozas.de + +- add missing definition of udiv_qrnnd for sparcv9:32 +- use %_smp_mflags + +------------------------------------------------------------------- +Sat Dec 19 12:58:20 CET 2009 - jengelh@medozas.de + +- add baselibs.conf as a source +- disable the use of hand-coded assembler functions on sparc - + this is giving me an infinite loop with ./tests/prime + (specifically ./sparc32v8/mpih-mul1.S:_gcry_mpih_mul_1. + Fedora disables this too. + +------------------------------------------------------------------- +Tue Apr 7 15:45:06 CEST 2009 - crrodriguez@suse.de + +- update to version 1.4.4 + * Publish GCRY_MODULE_ID_USER and GCRY_MODULE_ID_USER_LAST constants. + This functionality has been in Libgcrypt since 1.3.0. + * MD5 may now be used in non-enforced fips mode. + * Fixed HMAC for SHA-384 and SHA-512 with keys longer than 64 bytes. + * In fips mode, RSA keys are now generated using the X9.31 algorithm + and DSA keys using the FIPS 186-2 algorithm. + * The transient-key flag is now also supported for DSA key + generation. DSA domain parameters may be given as well. + +------------------------------------------------------------------- +Thu Jan 29 10:57:01 CET 2009 - olh@suse.de + +- obsolete libgcrypt-error-XXbit in the library subpackage + +------------------------------------------------------------------- +Wed Dec 10 12:34:56 CET 2008 - olh@suse.de + +- use Obsoletes: -XXbit only for ppc64 to help solver during distupgrade + (bnc#437293) + +------------------------------------------------------------------- +Tue Nov 11 17:23:54 CET 2008 - mkoenig@suse.de + +- build rijndael.c with -fno-strict-aliasing [bnc#443693] + +------------------------------------------------------------------- +Thu Oct 30 12:34:56 CET 2008 - olh@suse.de + +- obsolete old -XXbit packages (bnc#437293) + +------------------------------------------------------------------- +Mon Jun 30 11:47:59 CEST 2008 - mkoenig@suse.de + +- update to version 1.4.1 + * Fixed a bug which led to the comsumption of far too much + entropy for the intial seeding + * Improved AES performance for CFB and CBC modes + +------------------------------------------------------------------- +Sun May 11 11:54:39 CEST 2008 - coolo@suse.de + +- fix rename of xxbit packages + +------------------------------------------------------------------- +Thu Apr 10 12:54:45 CEST 2008 - ro@suse.de + +- added baselibs.conf file to build xxbit packages + for multilib support + +------------------------------------------------------------------- +Thu Jan 17 12:20:25 CET 2008 - mkoenig@suse.de + +- update to version 1.4.0: + * The entire library is now under the LGPL. The helper programs and + the manual are under the GPL + * New control code GCRYCTL_PRINT_CONFIG + * Experimental support for ECDSA + * Assembler support for the AMD64 architecture + * Non executable stack support is now used by default + * New configure option --enable-random-daemon + * The new function gcry_md_debug should be used instead of the + gcry_md_start_debug and gcry_md_stop_debug macros. + * Support for DSA2 + * Reserved algorithm ranges for use by applications + * gcry_mpi_rshift does not anymore truncate the shift count + * Support for OFB encryption mode + * Support for the Camellia cipher + * Support for the SEED cipher + * Support for SHA-224 and HMAC using SHA-384 and SHA-512 + * Reading and writing the random seed file is now protected by a + fcntl style file lock + * Made the RNG immune against fork without exec + * Changed the way the RNG gets initialized + * The ASN.1 DER template for SHA-224 has been fixed + * The ACE engine of VIA processors is now used for AES-128 +- changed package layout to conform shlib policy: + new subpackage libgcrypt11 +- disable static library +- for reference: bugzilla entry of last change #304749 + +------------------------------------------------------------------- +Thu Sep 13 01:28:53 CEST 2007 - ltinkl@suse.cz + +- add sanity check for mpi of size 0 (#304479) + +------------------------------------------------------------------- +Mon Feb 5 10:25:21 CET 2007 - mkoenig@suse.de + +- update to version 1.2.4: + * Fixed a bug in the memory allocator which could have been the + reason for some of non-duplicable bugs. + * Other minor bug fixes. + +------------------------------------------------------------------- +Wed Dec 13 12:47:48 CET 2006 - mkoenig@suse.de + +- get rid of .la file and fix devel so link + +------------------------------------------------------------------- +Tue Dec 5 18:30:30 CET 2006 - mkoenig@suse.de + +- move shared lib to /%_lib + +------------------------------------------------------------------- +Thu Aug 31 14:29:56 CEST 2006 - mkoenig@suse.de + +- update to version 1.2.3: + * Rewrote gcry_mpi_rshift to allow arbitrary shift counts. + * Minor bug fixes. +- added libgpg-error-devel and glibc-devel to Requires tag + of devel subpackage + +------------------------------------------------------------------- +Wed Jan 25 21:37:28 CET 2006 - mls@suse.de + +- converted neededforbuild to BuildRequires + +------------------------------------------------------------------- +Wed Nov 2 16:44:48 CET 2005 - hvogel@suse.de + +- enable noexecstack +- build ac.c with fno-strict-aliasing + +------------------------------------------------------------------- +Tue Oct 25 13:40:15 CEST 2005 - hvogel@suse.de + +- update to version 1.2.2 + +------------------------------------------------------------------- +Thu Jun 23 11:26:58 CEST 2005 - hvogel@suse.de + +- call install_info macro in post/postun of the devel package +- depend on libgcrypt +- add clean section + +------------------------------------------------------------------- +Tue Jan 18 11:51:51 CET 2005 - hvogel@suse.de + +- update to version 1.2.1 + +------------------------------------------------------------------- +Tue Jan 11 16:48:10 CET 2005 - schwab@suse.de + +- Fix info dir entry. + +------------------------------------------------------------------- +Wed Nov 17 11:22:44 CET 2004 - hvogel@suse.de + +- require libgpg-error-devel (Bug #48271) +- get rid of the NLD parts + +------------------------------------------------------------------- +Wed Jul 14 11:12:54 CEST 2004 - adrian@suse.de + +- create -devel subpackage +- prepare for nld + +------------------------------------------------------------------- +Wed May 19 14:57:45 CEST 2004 - hvogel@suse.de + +- update to version 1.2.0 + +------------------------------------------------------------------- +Mon Mar 22 16:48:53 CET 2004 - meissner@suse.de + +- disable make check, because it uses /dev/random whihc is + not filled on some server machines. + +------------------------------------------------------------------- +Wed Mar 17 15:01:51 CET 2004 - meissner@suse.de + +- fixed too over enthusiastic powerpc switches to make it work + on ppc64. (It compiled before, but did not work). +- enabled make check. + +------------------------------------------------------------------- +Wed Feb 18 12:14:36 CET 2004 - kukuk@suse.de + +- Build against system pthread library, not pth. + +------------------------------------------------------------------- +Tue Feb 17 21:11:40 CET 2004 - hvogel@suse.de + +- update to version 1.1.91 +- fix autoconf quotations + +------------------------------------------------------------------- +Sat Jan 10 19:20:41 CET 2004 - adrian@suse.de + +- add %run_ldconfig to %postun + +------------------------------------------------------------------- +Sun Jul 27 16:12:54 CEST 2003 - poeml@suse.de + +- add libgcrypt-1.1.12-sexp-valgrind-error.patch from SLEC + +------------------------------------------------------------------- +Thu Apr 24 12:20:23 CEST 2003 - ro@suse.de + +- fix install_info --delete call and move from preun to postun + +------------------------------------------------------------------- +Mon Feb 10 22:51:26 CET 2003 - mmj@suse.de + +- Use %install_info macro [#23433] + +------------------------------------------------------------------- +Mon Feb 10 16:11:55 CET 2003 - mc@suse.de + +- switch to version 1.1.12 +- gcry_pk_sign, gcry_pk_verify and gcry_pk_encrypt can now handle an + optional pkcs1 flags parameter in the S-expression. A similar flag + may be passed to gcry_pk_decrypt but it is only syntactically + implemented. +- New convenience macro gcry_md_get_asnoid. +- There is now some real stuff in the manual. +- New algorithm: MD4 +- Implemented ciphertext stealing. +- Support for plain old DES +- Smaller bugs fixes and a few new OIDs. + +------------------------------------------------------------------- +Tue Jan 14 14:03:27 CET 2003 - nadvornik@suse.cz + +- fixed multi-line string literals + +------------------------------------------------------------------- +Thu Aug 1 23:51:10 CEST 2002 - poeml@suse.de + +- create package + diff --git a/libgcrypt.keyring b/libgcrypt.keyring new file mode 100644 index 0000000..dd3bb0b --- /dev/null +++ b/libgcrypt.keyring @@ -0,0 +1,86 @@ +-----BEGIN PGP PUBLIC KEY BLOCK----- + +mQGNBFjLuq4BDACnM7zNSIaVMAacTwjXa5TGYe13i6ilHe4VL0NShzrgzjcQg531 +3cRgiiiNA7OSOypMqVs73Jez6ZUctn2GVsHBrS/io9NcuC9pVwf8a61WlcEa+EtB +a3G7HlBmEWnwaUdAtWKNuAi9Xn+Ir7H2xEdksmmd5a0/QnL+sX705boVPF/tpYtb +LGpPxa78tNrtxDkSwy8Wmi0IADYLI5yI7/yUGeJd8RSCU/fLRKC9fG7YOZRq0tsO +MhVNWmtUjbG6e73Lu8LKnCZgs1/fC8hvPyARieSV5mdN8s1oWd7oYctfgL4uBleD +ItAA8GhjKejutzHN8Ei/APw6AiiSyEjnPg+cTX8OgvLGJWjks0H6mPZeB1v/kGyZ +hBS9vm540h2/MmlVN2ntiCK5TZGeSWpqddiqusfVXotMRpN4HeLKoZh4RAncaCbZ +F/S+YLeN+kMXY4k3Fqt1fjTX6veFCbthI9pDdHzU9LfUVNp9D/5ktC/tYMORMegV ++wSMxi9G2YWKJkMAEQEAAYkBzgQfAQgAOBYhBFuAxXVCmPDLVdjtarzvfilLCS4o +BQJYy8DdFwyAAZSlyaA8L+XKOwldjh/fcjz0YraxAgcAAAoJELzvfilLCS4oNgoL +/0+K1xIx8JW7Lk5M6bYCvNA4fdlEcwQIT4UidJFM9m+suxYFWIGfebvHpRlEuJTg +dBjkEit8uLAoJXU0BRkKTLrzTF+qDUE79Wfx/R+0nOgJ7aMykQOi0AvuwzMYz4dg +xIVS2Daou4DF7bh/KF8+fqrmq8P8W1ZrkuFDanMWpHeAPx1uj2skYbo7uPqFdvlJ +hlNHrcxlcCkjf1InAt0Xt5lMvEsCRUPf9xAH4mNEhs0lh9c+200YPRmtnLWAzc1K +ckLIC8Q+mUR3DjZDqBlDBEPegXkrI0+MlvRA+9AnAm4YPqTMUfpZ6ZOAWeFjC/6Z +QYxG/AdWGkb4WFindzklQfybEuiekP8vU07ACQwSwH8PYe0UCom1YrlRUjX7QLkn +ZLWoeZg8BZy9GTM1Ut7Q1Q2uTw6mxxISuef+RFgYOHjWwLpFWZpqC88xERl7o/iz +iERJRt/593IctbjO9wenWt2peIAwzR4nz7LqM6ZFTdRAETmcdSvYRhg2Qt8hUE47 +CbQkQW5kcmUgSGVpbmVja2UgKFJlbGVhc2UgU2lnbmluZyBLZXkpiQHUBBMBCAA+ +FiEEW4DFdUKY8MtV2O1qvO9+KUsJLigFAljLuq4CGwMFCRLMAwAFCwkIBwIGFQgJ +CgsCBBYCAwECHgECF4AACgkQvO9+KUsJLihC/QwAhCC+SEvcFLcutgZ8HfcCtoZs +IoVzZEy7DjqIvGgnTssD8HCLnIAHCDvnP7dJW3uMuLCdSqym3cjlEIiQMsaGywkl +fzJISAwJrGQdWSKRd535jXpEXQlXDKal/IwMKAUt0PZtlCc9S3gwixQryxdJ28lJ +6h2T9fVDr8ZswMmTAFG91uctfhjKOMgPt8UhSPGW484WsIsQgkbOvf+Kfswl0eHu +ywX+pKAB5ZQ/9GVC6Ug4xfrdiJL0azJTPnvjMY5JYp6/L9RURs5hP5AnHR2j/PPo +sAtsFCjmbRbOMiASzklnUJPbSz5kfLloDWZmrUScjbzmsXehGyt433JGyRhZJl4x +/jPbzKhaaAHsGd+fRao6vlLOwFywDDVMp6JuyK7UeUb7I8ekTbSkGFA+l2Oa3O6/ +Y7PYhq7hwwAFuZckYI98IpHNCG1fS9W07FyKdvQbK1PbF1JFRKfsUCWYMKqDnbqE +o5jivPEHZImw6iYhhXcyEYl8fjcb9T6/S+wOP7aviQGzBBABCAAdFiEElKXJoDwv +5co7CV2OH99yPPRitrEFAljLv5sACgkQH99yPPRitrFw4gv/XFMFN+/LHsn9hJOP +4rCwl1yUuxXuYmZgc0sRoY3EpeQkJVyKurQuqqKoy2VuoMiF0O1kAQmGoFtVPUk7 +b8hCoutqB5GyeyKcoLP+WINgVhB2gXg7TSp3MPLBKkgqvSDvPitgRxBqFb4LW8LJ +bDbfwGrzIvXfDV3WvsrHVPbc2fhlWdL8d+3AE6mFiXF3eTpgmV3ApSBQV12MkkCk +icLIPmp+ZxZON+OP52ZXkRtfMgOy4Oa/41agrViDAZdMOGeGkhPertQheQZgXzmo +GF5Wz498HPM80Kv35X91l3iGzL+icEtO+tWea2YscsZ6qpRe2lfVPHk3B+anlmCj +m4kM4cBd39xa4HHSVh/bRHbZNtgVr7slQCKxlHgQOGVI5vCxPCwEsgJ2KBk03Nk/ +IA9EKO+czfh3/bHW6uMbEqrYDCnt+hmzZrpKDSGcwS/KOhvMUIMlb7/8vDKum6mp +/8xAtVZ6IAxYZNt3qg7Y7aLRtzCTyqm8rJQrZPtRaQcgLoEimDMEX0PliRYJKwYB +BAHaRw8BAQdAz75Hlekc16JhhfI0MKdEVxLdkxhcMCO0ZG6WMBAmNpe0H1dlcm5l +ciBLb2NoIChkaXN0IHNpZ25pbmcgMjAyMCmImgQTFgoAQhYhBG2qbmSnbShAVxtJ +AlKIl7gmQDraBQJfQ+w1AhsDBQkShccRBQsJCAcCAyICAQYVCgkICwIEFgIDAQIe +BwIXgAAKCRBSiJe4JkA62nmuAP9uL/HOdB0gvwWrH+FpURJLs4bnaZaPIk9ARrU0 +EXRgJgD/YCGfHQXpIPT0ZaXuwJexK04Z+qMFR/bM1q1Leo5CjgaIbQQQEQsAHRYh +BIBhWHD1utaQMzaG0PKthaweQrNnBQJfQ/HmAAoJEPKthaweQrNnIZkA3jG6LcZv +V/URn8Y8OJqsyYa4C3NI4nN+OhEvYhgA4PHzMnALeXIpA2gblvjFIPJPAhDBAU37 +c5PA6+6IdQQQFggAHRYhBK6oTtzwGthsRwHIXGMROuhmWH0KBQJfQ/IlAAoJEGMR +OuhmWH0K1+MA/0uJ5AHcnSfIBEWHNJwwVVLGyrxAWtS2U+zeymp/UvlPAQDErCLZ +l0dBiPG3vlowFx5TNep7tanBs6ZJn8F1ao1tAIkBMwQQAQgAHRYhBNhpISPEBl3q +Xg86tSSbOdJPJeO2BQJfQ/OuAAoJECSbOdJPJeO2DVoH/0o9if66ph6FJrgr+A/W +HNVeHxmM5tUQhpL1wpRS70SKcsJgolf5CxO5iTQf3HlZe544xGbIU/aCTJsWw9zi +UE8KmhAtKV4eL/7oQ7xx4nxPnABLpudtM8A44nsM1x/XiYrJnnDm29QjYEGd2Hi8 +7npc7VWKzLoj+I/WcXquynJi5O9TUxW9Bknd1pjpxFkf8v+msjBzCD5VKJgr0CR8 +wA6peQBWeGZX2HacosMIZH4TfL0r0TFla6LJIkNBz9DyIm1yL4L8oRH0950hQljP +C7TM3L7aRpX+4Kph6llFz6g7MALGFP95kyJ6o+XED9ORuuQVZMBMIkNC0tXOu10V +bdqIdQQQFgoAHRYhBMHTS2khnkruwLocIeP9/yGORbcrBQJfQ/P8AAoJEOP9/yGO +Rbcr3lQBAMas8Vl3Hdl3g2I283lz1uHiGvlwcnk2TLeB+U4zIwC9AQCy0nnazVNt +VQPID1ZCMoaOX7AzOjaqQDLf4j+dVTxgBJgzBGCkgocWCSsGAQQB2kcPAQEHQJmd +fwp8jEN5P3eEjhQiWk6zQi8utvgOvYD57XmE+H8+tCBOaWliZSBZdXRha2EgKEdu +dVBHIFJlbGVhc2UgS2V5KYiaBBMWCgBCFiEErI4RW/c+LY1H+pkI6Y6bLRnGyL0F +AmCkgocCGwMFCQsNBpkFCwkIBwIDIgIBBhUKCQgLAgQWAgMBAh4HAheAAAoJEOmO +my0Zxsi9/4IA/1rvSr3MU+Sv4jhNDzD+CeC3gmHkPew6pi9VHEsEwdgmAQD2BtiX +7w1sJL/CBylGWv5jxj4345mP9YfZm0RsgzPjDIh1BBAWCAAdFiEEJJyzdxdQdF1c +3TI84mewUjZPAo0FAmFAQ54ACgkQ4mewUjZPAo1CiAD+KTT1UVdQTGHMyvHwZocS +QjU8xhcZrTet+dvvjrE5+4MA/RBdJPZgFevUKu68NEy0Lo+RbkeCtmQJ/c8v5ieF +vW0AiQEzBBABCAAdFiEEEkEkvTtIYq96CkLxALRevUynur4FAmFAQ7cACgkQALRe +vUynur4kaAgAolPR8TNWVS0vXMKrr0k0l2M/8QkZTaLZx1GT9Nx1yb4WJKY7ElPM +YkhGDxetvFBETx0pH/6R3jtj6Crmur+NKHVSRY+rCYpFPDn6ciIOryssRx2G4kCZ +t+nFB9JyDbBOZAR8DK4pN1mAxG/yLDt4oKcUQsP2xlEFum+phxyR8KyYCpkwKRxY +eK+6lfilQuveoUwp/Xx5wXPNUy6q4eOOovCW7gS7I7288NGHCa2ul8sD6vA9C4mM +4Zxaole9P9wwJe1zZFtCIy88zHM9vqv+YM9DxMCaW24+rUztr7eD4bCRdG+QlSh+ +7R/TaqSxY1eAAd1J5tma9CNJO73pTKU+/JhTBGFpSqMTCSskAwMCCAEBBwIDBF6X +D9NmUQDgiyYNbhs1DMJ14mIw812wY1HVx/4QWYWiBunhrvSFxVbzsjD7/Wv+v3bm +MPrL+M2DLyFiSewNmcS0JEdudVBHLmNvbSAoUmVsZWFzZSBTaWduaW5nIEtleSAy +MDIxKYiaBBMTCABCFiEEAvON/3Mf+XywOaHaVJ5pXpBboggFAmFpSqMCGwMFCQ9x +14oFCwkIBwIDIgIBBhUKCQgLAgQWAgMBAh4HAheAAAoJEFSeaV6QW6IITkoA/RYa +jaTl1eEBU/Gdm12o3jrI55N5xZK2XTqSx25clVyjAP0XwMW/Og5+ND1ri3bAqADV +WlBDUswz8wYxsb0C4kYBkoh1BBAWCgAdFiEEbapuZKdtKEBXG0kCUoiXuCZAOtoF +AmFpTvEACgkQUoiXuCZAOtrJQAEAh7YyykjAy/Qs1yC3ji8iBfIVnPXvblrIx3SR +RyDwRC8BAKtZbEuKTtPlgkLUgMleTcZJ/vEhJE+GvfQ9o5gWCqEFiHUEEBYKAB0W +IQTB00tpIZ5K7sC6HCHj/f8hjkW3KwUCYWlPWgAKCRDj/f8hjkW3Kx4eAQDp6aGS +N/fU4xLl8RSvQUVjVA+aCTrMQR3hRwqw8liF2wEA3O3ECxz6e1+DoItYoJBBLKLw +eiInsGZ/+h5XYrpXTgA= +=4+Sn +-----END PGP PUBLIC KEY BLOCK----- diff --git a/libgcrypt.spec b/libgcrypt.spec new file mode 100644 index 0000000..c5b865b --- /dev/null +++ b/libgcrypt.spec @@ -0,0 +1,194 @@ +# +# spec file for package libgcrypt +# +# Copyright (c) 2025 SUSE LLC +# +# All modifications and additions to the file contributed by third parties +# remain the property of their copyright owners, unless otherwise agreed +# upon. The license for this file, and modifications and additions to the +# file, is the same license as for the pristine package itself (unless the +# license for the pristine package is not an Open Source License, in which +# case the license is the MIT License). An "Open Source License" is a +# license that conforms to the Open Source Definition (Version 1.9) +# published by the Open Source Initiative. + +# Please submit bugfixes or comments via https://bugs.opensuse.org/ +# + + +%define libsover 20 +%define libsoname %{name}%{libsover} +%define hmac_key orboDeJITITejsirpADONivirpUkvarP +Name: libgcrypt +Version: 1.11.0 +Release: 0 +Summary: The GNU Crypto Library +License: GPL-2.0-or-later AND LGPL-2.1-or-later AND GPL-3.0-or-later +Group: Development/Libraries/C and C++ +URL: https://gnupg.org/software/libgcrypt +Source: https://gnupg.org/ftp/gcrypt/libgcrypt/%{name}-%{version}.tar.bz2 +Source1: https://gnupg.org/ftp/gcrypt/libgcrypt/%{name}-%{version}.tar.bz2.sig +Source2: baselibs.conf +Source3: random.conf +Source4: hwf.deny +# https://www.gnupg.org/signature_key.html +Source5: https://gnupg.org/signature_key.asc#/%{name}.keyring +Source99: libgcrypt.changes +Patch1: libgcrypt-1.10.0-allow_FSM_same_state.patch +#PATCH-FIX-OPENSUSE Do not pull revision info from GIT when autoconf is run +Patch2: libgcrypt-nobetasuffix.patch +# FIPS patches: +#PATCH-FIX-SUSE bsc#1190700 FIPS: Provide a service-level indicator for PK +Patch100: libgcrypt-FIPS-SLI-pk.patch +#PATCH-FIX-SUSE bsc#1190700 FIPS: Check keylength in gcry_fips_indicator_kdf() +Patch101: libgcrypt-FIPS-SLI-kdf-leylength.patch +#PATCH-FIX-SUSE bsc#1190700 FIPS add indicators +Patch102: libgcrypt-FIPS-SLI-hash-mac.patch +#PATCH-FIX-SUSE bsc#1202117 FIPS: Get most of the entropy from rndjent_poll +Patch104: libgcrypt-FIPS-rndjent_poll.patch +#PATCH-FIX-SUSE bsc#1220896 FIPS: Replace the built-in jitter rng with standalone version +Patch105: libgcrypt-FIPS-jitter-standalone.patch +#PATCH-FIX-SUSE bsc#1220895 FIPS: Enforce the interpretation and use of jitter rng +Patch106: libgcrypt-FIPS-jitter-errorcodes.patch +#PATCH-FIX-SUSE bsc#1220893 FIPS: Use Jitter RNG for the whole length entropy buffer +Patch107: libgcrypt-FIPS-jitter-whole-entropy.patch +#PATCH-FIX-SUSE Remove not used rol64() definition after removing the built-in jitter rng +Patch108: libgcrypt-rol64-redefinition.patch +BuildRequires: automake >= 1.14 +BuildRequires: libgpg-error-devel >= 1.49 +BuildRequires: libtool +BuildRequires: makeinfo +BuildRequires: pkgconfig +%{?suse_build_hwcaps_libs} + +%description +Libgcrypt is a general purpose library of cryptographic building +blocks. It is originally based on code used by GnuPG. It does not +provide any implementation of OpenPGP or other protocols. Thorough +understanding of applied cryptography is required to use Libgcrypt. + +%package -n %{libsoname} +Summary: The GNU Crypto Library +License: GPL-2.0-or-later AND LGPL-2.1-or-later +Group: System/Libraries +BuildRequires: jitterentropy-devel >= 3.4.0 +Requires: libjitterentropy3 >= 3.4.0 +Provides: %{libsoname}-hmac = %{version}-%{release} +Obsoletes: %{libsoname}-hmac < %{version}-%{release} + +%description -n %{libsoname} +Libgcrypt is a general purpose crypto library based on the code used in +GnuPG (alpha version). + +%package devel +Summary: The GNU Crypto Library +License: GFDL-1.1-only AND GPL-2.0-or-later AND LGPL-2.1-or-later AND MIT +Group: Development/Libraries/C and C++ +Requires: %{libsoname} = %{version} +Requires: glibc-devel +Requires: jitterentropy-devel >= 3.4.0 +Requires: libgpg-error-devel >= 1.49 + +%description devel +Libgcrypt is a general purpose library of cryptographic building +blocks. It is originally based on code used by GnuPG. It does not +provide any implementation of OpenPGP or other protocols. Thorough +understanding of applied cryptography is required to use Libgcrypt. + +This package contains needed files to compile and link against the +library. + +%prep +%autosetup -p1 + +# Rename the internal .hmac file to include the so library version +sed -i "s/libgcrypt\.so\.hmac/\.libgcrypt\.so\.%{libsover}\.hmac/g" src/Makefile.am src/Makefile.in + +# Replace the built-in jitter rng with the standalone version [bsc#1220896] +find . -type f -name "jitterentropy*" -print -delete + +%build +export PUBKEYS="dsa elgamal rsa ecc" +export CIPHERS="arcfour blowfish cast5 des aes twofish serpent rfc2268 seed camellia idea salsa20 gost28147 chacha20 sm4 aria" +export DIGESTS="crc gostr3411-94 md4 md5 rmd160 sha1 sha256 sha512 sha3 tiger whirlpool stribog blake2 sm3" +export KDFS="s2k pkdf2 scrypt" + +autoreconf -fi +date=$(date -u '+%%Y-%%m-%%dT%%H:%%M+0000' -r %{SOURCE99}) +sed -e "s,BUILD_TIMESTAMP=.*,BUILD_TIMESTAMP=$date," -i configure +export CFLAGS="%{optflags} $(getconf LFS_CFLAGS)" +%configure \ + --with-fips-module-version="Libgcrypt version %{version}-%{release}" \ + --enable-hmac-binary-check="%{hmac_key}" \ + --enable-ciphers="$CIPHERS" \ + --enable-pubkey-ciphers="$PUBKEYS" \ + --enable-digests="$DIGESTS" \ + --enable-kdfs="$KDFS" \ + --enable-noexecstack \ + --disable-static \ +%ifarch %{sparc} + --disable-asm \ +%endif + --enable-random=getentropy \ + --enable-jent-support \ + %{nil} + +%make_build + +%check +make -k check +# run the regression tests also in FIPS mode +LIBGCRYPT_FORCE_FIPS_MODE=1 make -k check || true + +%install +%make_install + +# this is a hack that re-defines the __spec_install_post macro +# for a simple reason: the macro strips the binaries and thereby +# invalidates a HMAC that may have been created earlier. +# solution: create the hashes _after_ the macro runs. +%define libpath %{buildroot}%{_libdir}/libgcrypt.so.%{libsover}.?.? +%define __spec_install_post \ + %{?__debug_package:%{__debug_install_post}} \ + %{__arch_install_post} \ + %{__os_install_post} \ + cd src \ + sed -i -e 's|FILE=.*|FILE=\\\$1|' gen-note-integrity.sh \ + READELF=readelf AWK=awk ECHO_N="-n" bash gen-note-integrity.sh %{libpath} > %{libpath}.hmac \ + objcopy --update-section .note.fdo.integrity=%{libpath}.hmac %{libpath} %{libpath}.new \ + mv -f %{libpath}.new %{libpath} \ + rm -f %{libpath}.hmac \ +%{nil} + +rm %{buildroot}%{_libdir}/%{name}.la + +# Create /etc/gcrypt directory and install random.conf +mkdir -p -m 0755 %{buildroot}%{_sysconfdir}/gcrypt +install -m 644 %{SOURCE3} %{buildroot}%{_sysconfdir}/gcrypt/random.conf +install -m 644 %{SOURCE4} %{buildroot}%{_sysconfdir}/gcrypt/hwf.deny + +%post -n %{libsoname} -p /sbin/ldconfig +%postun -n %{libsoname} -p /sbin/ldconfig + +%files -n %{libsoname} +%license COPYING COPYING.LIB LICENSES +%doc AUTHORS ChangeLog NEWS README THANKS TODO +%{_libdir}/%{name}.so.* +%dir %{_sysconfdir}/gcrypt +%config(noreplace) %{_sysconfdir}/gcrypt/random.conf +%config(noreplace) %{_sysconfdir}/gcrypt/hwf.deny + +%files devel +%license COPYING COPYING.LIB LICENSES +%{_bindir}/dumpsexp +%{_bindir}/hmac256 +%{_bindir}/mpicalc +%{_bindir}/%{name}-config +%{_libdir}/%{name}.so +%{_libdir}/pkgconfig/libgcrypt.pc +%{_datadir}/aclocal/%{name}.m4 +%{_includedir}/gcrypt*.h +%{_infodir}/gcrypt.info*%{ext_info}* +%{_mandir}/man1/* + +%changelog diff --git a/random.conf b/random.conf new file mode 100644 index 0000000..378ba78 --- /dev/null +++ b/random.conf @@ -0,0 +1,9 @@ +# This file can be used to globally change parameters of +# the random generator. Supported options are: + +# Always use the non-blocking /dev/urandom or the respective +# system call instead of the blocking /dev/random. +# only-urandom + +# Disable the use of the jitter based entropy generator. +# disable-jent -- 2.51.1 From 63766c912b4b310cb4063241bceb2e35ec6b6d822003c4b9d75737e00b1fd283 Mon Sep 17 00:00:00 2001 From: Pedro Monreal Gonzalez Date: Wed, 16 Apr 2025 12:33:55 +0000 Subject: [PATCH 3/8] - Differentiate use of SHA1 in the service level indicator [jsc#PED-12227] * Include upstream SLI revamp and fips certification fixes * Add patches: - libgcrypt-fips-Introduce-an-internal-API-for-FIPS-service-indicator.patch - libgcrypt-fips-Introduce-GCRYCTL_FIPS_SERVICE_INDICATOR-and-the-macro.patch - libgcrypt-fips-kdf-Implement-new-FIPS-service-indicator-for-gcry_kdf_derive.patch - libgcrypt-fips-md-Implement-new-FIPS-service-indicator-for-gcry_md_hash_.patch - libgcrypt-fips-tests-Add-t-digest.patch - libgcrypt-fips-Change-the-internal-API-for-new-FIPS-service-indicator.patch - libgcrypt-fips-md-Implement-new-FIPS-service-indicator-for-gcry_md_open-API.patch - libgcrypt-fips-tests-Add-tests-for-md_open-write-read-close-for-t-digest.patch - libgcrypt-fips-mac-Implement-new-FIPS-service-indicator-for-gcry_mac_open.patch - libgcrypt-fips-cipher-Implement-new-FIPS-service-indicator-for-cipher_open.patch - libgcrypt-tests-fips-Add-gcry_mac_open-tests.patch - libgcrypt-tests-fips-Rename-t-fips-service-ind.patch - libgcrypt-tests-fips-Move-KDF-tests-to-t-fips-service-ind.patch - libgcrypt-tests-fips-Add-gcry_cipher_open-tests.patch - libgcrypt-fips-md-gcry_md_copy-should-care-about-FIPS-service-indicator.patch - libgcrypt-fips-cipher-Implement-FIPS-service-indicator-for-gcry_pk_hash_-API.patch - libgcrypt-fips-Introduce-GCRYCTL_FIPS_REJECT_NON_FIPS.patch - libgcrypt-Fix-the-previous-change.patch - libgcrypt-fips-Rejection-by-GCRYCTL_FIPS_REJECT_NON_FIPS-not-by-open-flags.patch - libgcrypt-fips-cipher-Add-behavior-not-to-reject-but-mark-non-compliant.patch - libgcrypt-fips-ecc-Add-rejecting-or-marking-for-gcry_pk_get_curve.patch - libgcrypt-tests-Add-more-tests-to-tests-t-fips-service-ind.patch - libgcrypt-fips-ecc-Check-DATA-in-gcry_pk_sign-verify-in-FIPS-mode.patch - libgcrypt-fips-cipher-Fix-memory-leak-for-gcry_pk_hash_sign.patch - libgcrypt-build-Improve-__thread-specifier-check.patch - libgcrypt-cipher-Check-and-mark-non-compliant-cipher-modes-in-the-SLI.patch - libgcrypt-cipher-Rename-_gcry_cipher_is_mode_fips_compliant.patch OBS-URL: https://build.opensuse.org/package/show/devel:libraries:c_c++/libgcrypt?expand=0&rev=186 --- .gitattributes | 23 + .gitignore | 1 + baselibs.conf | 8 + hwf.deny | 34 + libgcrypt-1.10.0-allow_FSM_same_state.patch | 15 + libgcrypt-1.10.3.tar.bz2 | 3 + libgcrypt-1.10.3.tar.bz2.sig | Bin 0 -> 238 bytes libgcrypt-1.11.0.tar.bz2 | 3 + libgcrypt-1.11.0.tar.bz2.sig | Bin 0 -> 119 bytes ...poly1305-Optimized-chacha20-poly1305.patch | 1993 +++++++++++++++++ libgcrypt-FIPS-SLI-hash-mac.patch | 172 ++ libgcrypt-FIPS-SLI-kdf-leylength.patch | 60 + libgcrypt-FIPS-SLI-pk.patch | 177 ++ libgcrypt-FIPS-jitter-errorcodes.patch | 16 + libgcrypt-FIPS-jitter-standalone.patch | 183 ++ libgcrypt-FIPS-jitter-whole-entropy.patch | 41 + libgcrypt-FIPS-rndjent_poll.patch | 114 + libgcrypt-Fix-the-previous-change.patch | 45 + ...ild-Improve-__thread-specifier-check.patch | 41 + ...T-for-non-rfc6979-ECDSA-with-fixed-k.patch | 94 + ...on-compliant-cipher-modes-in-the-SLI.patch | 236 ++ ...-Differentiate-igninvflag-in-the-SLI.patch | 40 + ...rentiate-no-blinding-flag-in-the-SLI.patch | 70 + ...ferentiate-use-of-label-K-in-the-SLI.patch | 139 ++ ...e-GCRY_CIPHER_MODE_CMAC-in-FIPS-mode.patch | 98 + ...-_gcry_cipher_is_mode_fips_compliant.patch | 64 + libgcrypt-cipher-ecc-Fix-for-supplied-K.patch | 88 + ...-cipher-fips-Fix-for-random-override.patch | 83 + ...nknown-with-RSA-signature-generation.patch | 445 ++++ ...te-use-of-random-override-in-the-SLI.patch | 107 + ...about-GCRYCTL_FIPS_SERVICE_INDICATOR.patch | 66 + libgcrypt-doc-Fix-syntax-error.patch | 31 + ...l-API-for-new-FIPS-service-indicator.patch | 140 ++ ...pt-fips-Fix-GCRY_FIPS_FLAG_REJECT_MD.patch | 42 + ...troduce-GCRYCTL_FIPS_REJECT_NON_FIPS.patch | 261 +++ ...FIPS_SERVICE_INDICATOR-and-the-macro.patch | 101 + ...ernal-API-for-FIPS-service-indicator.patch | 332 +++ ...PS_REJECT_NON_FIPS-not-by-open-flags.patch | 498 ++++ ...r-Add-GCRY_FIPS_FLAG_REJECT_PK_FLAGS.patch | 80 + ...not-to-reject-but-mark-non-compliant.patch | 300 +++ ...mputation-when-marking-non-compliant.patch | 160 ++ ...ix-memory-leak-for-gcry_pk_hash_sign.patch | 76 + ...vice-indicator-for-gcry_pk_hash_-API.patch | 360 +++ ...PS-service-indicator-for-cipher_open.patch | 122 + ...ing-or-marking-for-gcry_pk_get_curve.patch | 43 + ...-in-gcry_pk_sign-verify-in-FIPS-mode.patch | 282 +++ ...ervice-indicator-for-gcry_kdf_derive.patch | 265 +++ ...-service-indicator-for-gcry_mac_open.patch | 115 + ...-service-indicator-for-gcry_md_hash_.patch | 188 ++ ...rvice-indicator-for-gcry_md_open-API.patch | 298 +++ ...ld-care-about-FIPS-service-indicator.patch | 85 + libgcrypt-fips-tests-Add-t-digest.patch | 243 ++ ...d_open-write-read-close-for-t-digest.patch | 172 ++ libgcrypt-jitterentropy-3.4.0.patch | 618 +++++ ..._info-to-mark-reject-under-FIPS-mode.patch | 82 + ...A-1-non-FIPS-internally-for-1.12-API.patch | 154 ++ ...igest_algo_spec-in-_gcry_md_selftest.patch | 74 + libgcrypt-no-deprecated-grep-alias.patch | 35 + libgcrypt-nobetasuffix.patch | 24 + ...e-P10-assembly-with-ENABLE_FORCE_SOF.patch | 76 + libgcrypt-rol64-redefinition.patch | 16 + ...re-tests-to-tests-t-fips-service-ind.patch | 382 ++++ ...crypt-tests-Allow-tests-with-USE_RSA.patch | 44 + ...d-using-GCRY_MD_SHA256-for-KDF-tests.patch | 106 + ...ests-fips-Add-gcry_cipher_open-tests.patch | 199 ++ ...t-tests-fips-Add-gcry_mac_open-tests.patch | 206 ++ ...Move-KDF-tests-to-t-fips-service-ind.patch | 375 ++++ ...tests-fips-Rename-t-fips-service-ind.patch | 60 + libgcrypt.changes | 1919 ++++++++++++++++ libgcrypt.keyring | 86 + libgcrypt.spec | 242 ++ random.conf | 9 + 72 files changed, 13360 insertions(+) create mode 100644 .gitattributes create mode 100644 .gitignore create mode 100644 baselibs.conf create mode 100644 hwf.deny create mode 100644 libgcrypt-1.10.0-allow_FSM_same_state.patch create mode 100644 libgcrypt-1.10.3.tar.bz2 create mode 100644 libgcrypt-1.10.3.tar.bz2.sig create mode 100644 libgcrypt-1.11.0.tar.bz2 create mode 100644 libgcrypt-1.11.0.tar.bz2.sig create mode 100644 libgcrypt-Chacha20-poly1305-Optimized-chacha20-poly1305.patch create mode 100644 libgcrypt-FIPS-SLI-hash-mac.patch create mode 100644 libgcrypt-FIPS-SLI-kdf-leylength.patch create mode 100644 libgcrypt-FIPS-SLI-pk.patch create mode 100644 libgcrypt-FIPS-jitter-errorcodes.patch create mode 100644 libgcrypt-FIPS-jitter-standalone.patch create mode 100644 libgcrypt-FIPS-jitter-whole-entropy.patch create mode 100644 libgcrypt-FIPS-rndjent_poll.patch create mode 100644 libgcrypt-Fix-the-previous-change.patch create mode 100644 libgcrypt-build-Improve-__thread-specifier-check.patch create mode 100644 libgcrypt-cipher-Add-KAT-for-non-rfc6979-ECDSA-with-fixed-k.patch create mode 100644 libgcrypt-cipher-Check-and-mark-non-compliant-cipher-modes-in-the-SLI.patch create mode 100644 libgcrypt-cipher-Differentiate-igninvflag-in-the-SLI.patch create mode 100644 libgcrypt-cipher-Differentiate-no-blinding-flag-in-the-SLI.patch create mode 100644 libgcrypt-cipher-Differentiate-use-of-label-K-in-the-SLI.patch create mode 100644 libgcrypt-cipher-Don-t-differentiate-GCRY_CIPHER_MODE_CMAC-in-FIPS-mode.patch create mode 100644 libgcrypt-cipher-Rename-_gcry_cipher_is_mode_fips_compliant.patch create mode 100644 libgcrypt-cipher-ecc-Fix-for-supplied-K.patch create mode 100644 libgcrypt-cipher-fips-Fix-for-random-override.patch create mode 100644 libgcrypt-cipher-rsa-Mark-reject-SHA1-unknown-with-RSA-signature-generation.patch create mode 100644 libgcrypt-cipher-visibility-Differentiate-use-of-random-override-in-the-SLI.patch create mode 100644 libgcrypt-doc-Add-about-GCRYCTL_FIPS_SERVICE_INDICATOR.patch create mode 100644 libgcrypt-doc-Fix-syntax-error.patch create mode 100644 libgcrypt-fips-Change-the-internal-API-for-new-FIPS-service-indicator.patch create mode 100644 libgcrypt-fips-Fix-GCRY_FIPS_FLAG_REJECT_MD.patch create mode 100644 libgcrypt-fips-Introduce-GCRYCTL_FIPS_REJECT_NON_FIPS.patch create mode 100644 libgcrypt-fips-Introduce-GCRYCTL_FIPS_SERVICE_INDICATOR-and-the-macro.patch create mode 100644 libgcrypt-fips-Introduce-an-internal-API-for-FIPS-service-indicator.patch create mode 100644 libgcrypt-fips-Rejection-by-GCRYCTL_FIPS_REJECT_NON_FIPS-not-by-open-flags.patch create mode 100644 libgcrypt-fips-cipher-Add-GCRY_FIPS_FLAG_REJECT_PK_FLAGS.patch create mode 100644 libgcrypt-fips-cipher-Add-behavior-not-to-reject-but-mark-non-compliant.patch create mode 100644 libgcrypt-fips-cipher-Do-the-computation-when-marking-non-compliant.patch create mode 100644 libgcrypt-fips-cipher-Fix-memory-leak-for-gcry_pk_hash_sign.patch create mode 100644 libgcrypt-fips-cipher-Implement-FIPS-service-indicator-for-gcry_pk_hash_-API.patch create mode 100644 libgcrypt-fips-cipher-Implement-new-FIPS-service-indicator-for-cipher_open.patch create mode 100644 libgcrypt-fips-ecc-Add-rejecting-or-marking-for-gcry_pk_get_curve.patch create mode 100644 libgcrypt-fips-ecc-Check-DATA-in-gcry_pk_sign-verify-in-FIPS-mode.patch create mode 100644 libgcrypt-fips-kdf-Implement-new-FIPS-service-indicator-for-gcry_kdf_derive.patch create mode 100644 libgcrypt-fips-mac-Implement-new-FIPS-service-indicator-for-gcry_mac_open.patch create mode 100644 libgcrypt-fips-md-Implement-new-FIPS-service-indicator-for-gcry_md_hash_.patch create mode 100644 libgcrypt-fips-md-Implement-new-FIPS-service-indicator-for-gcry_md_open-API.patch create mode 100644 libgcrypt-fips-md-gcry_md_copy-should-care-about-FIPS-service-indicator.patch create mode 100644 libgcrypt-fips-tests-Add-t-digest.patch create mode 100644 libgcrypt-fips-tests-Add-tests-for-md_open-write-read-close-for-t-digest.patch create mode 100644 libgcrypt-jitterentropy-3.4.0.patch create mode 100644 libgcrypt-md-Fix-gcry_md_algo_info-to-mark-reject-under-FIPS-mode.patch create mode 100644 libgcrypt-md-Make-SHA-1-non-FIPS-internally-for-1.12-API.patch create mode 100644 libgcrypt-md-Use-check_digest_algo_spec-in-_gcry_md_selftest.patch create mode 100644 libgcrypt-no-deprecated-grep-alias.patch create mode 100644 libgcrypt-nobetasuffix.patch create mode 100644 libgcrypt-ppc-enable-P10-assembly-with-ENABLE_FORCE_SOF.patch create mode 100644 libgcrypt-rol64-redefinition.patch create mode 100644 libgcrypt-tests-Add-more-tests-to-tests-t-fips-service-ind.patch create mode 100644 libgcrypt-tests-Allow-tests-with-USE_RSA.patch create mode 100644 libgcrypt-tests-Update-t-fips-service-ind-using-GCRY_MD_SHA256-for-KDF-tests.patch create mode 100644 libgcrypt-tests-fips-Add-gcry_cipher_open-tests.patch create mode 100644 libgcrypt-tests-fips-Add-gcry_mac_open-tests.patch create mode 100644 libgcrypt-tests-fips-Move-KDF-tests-to-t-fips-service-ind.patch create mode 100644 libgcrypt-tests-fips-Rename-t-fips-service-ind.patch create mode 100644 libgcrypt.changes create mode 100644 libgcrypt.keyring create mode 100644 libgcrypt.spec create mode 100644 random.conf diff --git a/.gitattributes b/.gitattributes new file mode 100644 index 0000000..9b03811 --- /dev/null +++ b/.gitattributes @@ -0,0 +1,23 @@ +## Default LFS +*.7z filter=lfs diff=lfs merge=lfs -text +*.bsp filter=lfs diff=lfs merge=lfs -text +*.bz2 filter=lfs diff=lfs merge=lfs -text +*.gem filter=lfs diff=lfs merge=lfs -text +*.gz filter=lfs diff=lfs merge=lfs -text +*.jar filter=lfs diff=lfs merge=lfs -text +*.lz filter=lfs diff=lfs merge=lfs -text +*.lzma filter=lfs diff=lfs merge=lfs -text +*.obscpio filter=lfs diff=lfs merge=lfs -text +*.oxt filter=lfs diff=lfs merge=lfs -text +*.pdf filter=lfs diff=lfs merge=lfs -text +*.png filter=lfs diff=lfs merge=lfs -text +*.rpm filter=lfs diff=lfs merge=lfs -text +*.tbz filter=lfs diff=lfs merge=lfs -text +*.tbz2 filter=lfs diff=lfs merge=lfs -text +*.tgz filter=lfs diff=lfs merge=lfs -text +*.ttf filter=lfs diff=lfs merge=lfs -text +*.txz filter=lfs diff=lfs merge=lfs -text +*.whl filter=lfs diff=lfs merge=lfs -text +*.xz filter=lfs diff=lfs merge=lfs -text +*.zip filter=lfs diff=lfs merge=lfs -text +*.zst filter=lfs diff=lfs merge=lfs -text diff --git a/.gitignore b/.gitignore new file mode 100644 index 0000000..57affb6 --- /dev/null +++ b/.gitignore @@ -0,0 +1 @@ +.osc diff --git a/baselibs.conf b/baselibs.conf new file mode 100644 index 0000000..a018a0a --- /dev/null +++ b/baselibs.conf @@ -0,0 +1,8 @@ +libgcrypt20 + provides "libgcrypt- = " + obsoletes "libgcrypt- <= " + provides "libgcrypt20-hmac- = -%release" + obsoletes "libgcrypt20-hmac- < -%release" +libgcrypt-devel + requires -libgcrypt- + requires "libgcrypt20- = " diff --git a/hwf.deny b/hwf.deny new file mode 100644 index 0000000..2236468 --- /dev/null +++ b/hwf.deny @@ -0,0 +1,34 @@ +# This file can be used to globally disable the use of hardware +# based optimizations. Supported options are: +# padlock-rng +# padlock-aes +# padlock-sha +# padlock-mmul +# intel-cpu +# intel-fast-shld +# intel-bmi2 +# intel-ssse3 +# intel-sse4.1 +# intel-pclmul +# intel-aesni +# intel-rdrand +# intel-avx +# intel-avx2 +# intel-fast-vpgather +# intel-rdtsc +# intel-shaext +# intel-vaes-vpclmul +# arm-neon +# arm-aes +# arm-sha1 +# arm-sha2 +# arm-pmull +# ppc-vcrypto +# ppc-arch_3_00 +# ppc-arch_2_07 +# ppc-arch_3_10 +# s390x-msa +# s390x-msa-4 +# s390x-msa-8 +# s390x-msa-9 +# s390x-vx diff --git a/libgcrypt-1.10.0-allow_FSM_same_state.patch b/libgcrypt-1.10.0-allow_FSM_same_state.patch new file mode 100644 index 0000000..843cfea --- /dev/null +++ b/libgcrypt-1.10.0-allow_FSM_same_state.patch @@ -0,0 +1,15 @@ +Index: libgcrypt-1.10.0/src/fips.c +=================================================================== +--- libgcrypt-1.10.0.orig/src/fips.c ++++ libgcrypt-1.10.0/src/fips.c +@@ -890,6 +890,10 @@ fips_new_state (enum module_states new_s + + } + ++ /* Allow a transition to the current state */ ++ if (current_state == new_state) ++ ok = 1; ++ + if (ok) + { + current_state = new_state; diff --git a/libgcrypt-1.10.3.tar.bz2 b/libgcrypt-1.10.3.tar.bz2 new file mode 100644 index 0000000..653803f --- /dev/null +++ b/libgcrypt-1.10.3.tar.bz2 @@ -0,0 +1,3 @@ +version https://git-lfs.github.com/spec/v1 +oid sha256:8b0870897ac5ac67ded568dcfadf45969cfa8a6beb0fd60af2a9eadc2a3272aa +size 3783827 diff --git a/libgcrypt-1.10.3.tar.bz2.sig b/libgcrypt-1.10.3.tar.bz2.sig new file mode 100644 index 0000000000000000000000000000000000000000000000000000000000000000..4172518bc29eafb0304aa2c7def555b970a6accea442a7542087b98c44485773 GIT binary patch literal 238 zcmeAuWnmEGV2~A4WXWBXm$E!p!y#PSlPRcU`VKV*t6Qv0sliEW8MrtFU?N}p82-vF z=ITAZ*qv<_(;dOxrp<8yN$DSFdR>!gz3<7nXwGD1Muyiq%7Ht6>~>#&|Ibh5V-ok6 zm#e%* literal 0 HcmV?d00001 diff --git a/libgcrypt-1.11.0.tar.bz2 b/libgcrypt-1.11.0.tar.bz2 new file mode 100644 index 0000000..28d1068 --- /dev/null +++ b/libgcrypt-1.11.0.tar.bz2 @@ -0,0 +1,3 @@ +version https://git-lfs.github.com/spec/v1 +oid sha256:09120c9867ce7f2081d6aaa1775386b98c2f2f246135761aae47d81f58685b9c +size 4180345 diff --git a/libgcrypt-1.11.0.tar.bz2.sig b/libgcrypt-1.11.0.tar.bz2.sig new file mode 100644 index 0000000000000000000000000000000000000000000000000000000000000000..2debe948a9ffbbc9c835efae5cce0c65517df124ea67ba4cc04d1dffdd7b3160 GIT binary patch literal 119 zcmeAuWnmEGV2~A4WXWBXm$E!p!y#PSlPRcU`VKV*t6Qv0X+=xZ7`QkEU?T178UE=O z)|M}6Y-XM7H2JWvsFP0?XX&fr%U>#e4G(K{b;T<%GJNLLSKO|_Z@vBphsk!en!WkH T(k44uvO>;;f4NZp`vWfkiCryG literal 0 HcmV?d00001 diff --git a/libgcrypt-Chacha20-poly1305-Optimized-chacha20-poly1305.patch b/libgcrypt-Chacha20-poly1305-Optimized-chacha20-poly1305.patch new file mode 100644 index 0000000..5877fee --- /dev/null +++ b/libgcrypt-Chacha20-poly1305-Optimized-chacha20-poly1305.patch @@ -0,0 +1,1993 @@ +commit 88fe7ac33eb4cb4dff76a5cc7fca50da5fb0ee3a +Author: Danny Tsen +Date: Sun Jun 12 21:30:19 2022 +0300 + + Chacha20 poly1305 Optimized chacha20 poly1305 for P10 operation + + * configure.ac: Added chacha20 and poly1305 assembly implementations. + * cipher/chacha20-p10le-8x.s: (New) - support 8 blocks (512 bytes) + unrolling. + * cipher/poly1305-p10le.s: (New) - support 4 blocks (128 bytes) + unrolling. + * cipher/Makefile.am: Added new chacha20 and poly1305 files. + * cipher/chacha20.c: Added PPC p10 le support for 8x chacha20. + * cipher/poly1305.c: Added PPC p10 le support for 4x poly1305. + * cipher/poly1305-internal.h: Added PPC p10 le support for poly1305. + --- + + GnuPG-bug-id: 6006 + Signed-off-by: Danny Tsen + [jk: cosmetic changes to C code] + [jk: fix building on ppc64be] + Signed-off-by: Jussi Kivilinna + +Index: libgcrypt-1.10.2/cipher/Makefile.am +=================================================================== +--- libgcrypt-1.10.2.orig/cipher/Makefile.am ++++ libgcrypt-1.10.2/cipher/Makefile.am +@@ -83,6 +83,7 @@ EXTRA_libcipher_la_SOURCES = \ + chacha20.c chacha20-amd64-ssse3.S chacha20-amd64-avx2.S \ + chacha20-armv7-neon.S chacha20-aarch64.S \ + chacha20-ppc.c chacha20-s390x.S \ ++ chacha20-p10le-8x.s \ + cipher-gcm-ppc.c cipher-gcm-intel-pclmul.c cipher-gcm-armv7-neon.S \ + cipher-gcm-armv8-aarch32-ce.S cipher-gcm-armv8-aarch64-ce.S \ + crc.c crc-intel-pclmul.c crc-armv8-ce.c \ +@@ -99,6 +100,7 @@ EXTRA_libcipher_la_SOURCES = \ + md4.c \ + md5.c \ + poly1305-s390x.S \ ++ poly1305-p10le.s \ + rijndael.c rijndael-internal.h rijndael-tables.h \ + rijndael-aesni.c rijndael-padlock.c \ + rijndael-amd64.S rijndael-arm.S \ +Index: libgcrypt-1.10.2/cipher/chacha20-p10le-8x.s +=================================================================== +--- /dev/null ++++ libgcrypt-1.10.2/cipher/chacha20-p10le-8x.s +@@ -0,0 +1,864 @@ ++# Copyright 2021- IBM Inc. All rights reserved ++# ++# This file is part of Libgcrypt. ++# ++# Libgcrypt is free software; you can redistribute it and/or modify ++# it under the terms of the GNU Lesser General Public License as ++# published by the Free Software Foundation; either version 2.1 of ++# the License, or (at your option) any later version. ++# ++# Libgcrypt 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 Lesser General Public License for more details. ++# ++# You should have received a copy of the GNU Lesser General Public ++# License along with this program; if not, see . ++# ++#=================================================================================== ++# Written by Danny Tsen ++# ++# This function handles multiple 64-byte block data length ++# and the length should be more than 512 bytes. ++# ++# unsigned int _gcry_chacha20_p10le_8x(u32 *state, byte *dst, const byte *src, size_t len); ++# ++# r1 - top of the stack ++# r3 to r10 input parameters ++# r3 - out ++# r4 - inp ++# r5 - len ++# r6 - key[8] ++# r7 - counter[4] ++# ++# do rounds, 8 quarter rounds ++# 1. a += b; d ^= a; d <<<= 16; ++# 2. c += d; b ^= c; b <<<= 12; ++# 3. a += b; d ^= a; d <<<= 8; ++# 4. c += d; b ^= c; b <<<= 7 ++# ++# row1 = (row1 + row2), row4 = row1 xor row4, row4 rotate each word by 16 ++# row3 = (row3 + row4), row2 = row3 xor row2, row2 rotate each word by 12 ++# row1 = (row1 + row2), row4 = row1 xor row4, row4 rotate each word by 8 ++# row3 = (row3 + row4), row2 = row3 xor row2, row2 rotate each word by 7 ++# ++# 4 blocks (a b c d) ++# ++# a0 b0 c0 d0 ++# a1 b1 c1 d1 ++# ... ++# a4 b4 c4 d4 ++# ... ++# a8 b8 c8 d8 ++# ... ++# a12 b12 c12 d12 ++# a13 ... ++# a14 ... ++# a15 b15 c15 d15 ++# ++# Column round (v0, v4, v8, v12, v1, v5, v9, v13, v2, v6, v10, v14, v3, v7, v11, v15) ++# Diagnal round (v0, v5, v10, v15, v1, v6, v11, v12, v2, v7, v8, v13, v3, v4, v9, v14) ++# ++.text ++ ++.macro QT_loop_8x ++ # QR(v0, v4, v8, v12, v1, v5, v9, v13, v2, v6, v10, v14, v3, v7, v11, v15) ++ xxlor 0, 32+25, 32+25 ++ xxlor 32+25, 20, 20 ++ vadduwm 0, 0, 4 ++ vadduwm 1, 1, 5 ++ vadduwm 2, 2, 6 ++ vadduwm 3, 3, 7 ++ vadduwm 16, 16, 20 ++ vadduwm 17, 17, 21 ++ vadduwm 18, 18, 22 ++ vadduwm 19, 19, 23 ++ ++ vpermxor 12, 12, 0, 25 ++ vpermxor 13, 13, 1, 25 ++ vpermxor 14, 14, 2, 25 ++ vpermxor 15, 15, 3, 25 ++ vpermxor 28, 28, 16, 25 ++ vpermxor 29, 29, 17, 25 ++ vpermxor 30, 30, 18, 25 ++ vpermxor 31, 31, 19, 25 ++ xxlor 32+25, 0, 0 ++ vadduwm 8, 8, 12 ++ vadduwm 9, 9, 13 ++ vadduwm 10, 10, 14 ++ vadduwm 11, 11, 15 ++ vadduwm 24, 24, 28 ++ vadduwm 25, 25, 29 ++ vadduwm 26, 26, 30 ++ vadduwm 27, 27, 31 ++ vxor 4, 4, 8 ++ vxor 5, 5, 9 ++ vxor 6, 6, 10 ++ vxor 7, 7, 11 ++ vxor 20, 20, 24 ++ vxor 21, 21, 25 ++ vxor 22, 22, 26 ++ vxor 23, 23, 27 ++ ++ xxlor 0, 32+25, 32+25 ++ xxlor 32+25, 21, 21 ++ vrlw 4, 4, 25 # ++ vrlw 5, 5, 25 ++ vrlw 6, 6, 25 ++ vrlw 7, 7, 25 ++ vrlw 20, 20, 25 # ++ vrlw 21, 21, 25 ++ vrlw 22, 22, 25 ++ vrlw 23, 23, 25 ++ xxlor 32+25, 0, 0 ++ vadduwm 0, 0, 4 ++ vadduwm 1, 1, 5 ++ vadduwm 2, 2, 6 ++ vadduwm 3, 3, 7 ++ vadduwm 16, 16, 20 ++ vadduwm 17, 17, 21 ++ vadduwm 18, 18, 22 ++ vadduwm 19, 19, 23 ++ ++ xxlor 0, 32+25, 32+25 ++ xxlor 32+25, 22, 22 ++ vpermxor 12, 12, 0, 25 ++ vpermxor 13, 13, 1, 25 ++ vpermxor 14, 14, 2, 25 ++ vpermxor 15, 15, 3, 25 ++ vpermxor 28, 28, 16, 25 ++ vpermxor 29, 29, 17, 25 ++ vpermxor 30, 30, 18, 25 ++ vpermxor 31, 31, 19, 25 ++ xxlor 32+25, 0, 0 ++ vadduwm 8, 8, 12 ++ vadduwm 9, 9, 13 ++ vadduwm 10, 10, 14 ++ vadduwm 11, 11, 15 ++ vadduwm 24, 24, 28 ++ vadduwm 25, 25, 29 ++ vadduwm 26, 26, 30 ++ vadduwm 27, 27, 31 ++ xxlor 0, 32+28, 32+28 ++ xxlor 32+28, 23, 23 ++ vxor 4, 4, 8 ++ vxor 5, 5, 9 ++ vxor 6, 6, 10 ++ vxor 7, 7, 11 ++ vxor 20, 20, 24 ++ vxor 21, 21, 25 ++ vxor 22, 22, 26 ++ vxor 23, 23, 27 ++ vrlw 4, 4, 28 # ++ vrlw 5, 5, 28 ++ vrlw 6, 6, 28 ++ vrlw 7, 7, 28 ++ vrlw 20, 20, 28 # ++ vrlw 21, 21, 28 ++ vrlw 22, 22, 28 ++ vrlw 23, 23, 28 ++ xxlor 32+28, 0, 0 ++ ++ # QR(v0, v5, v10, v15, v1, v6, v11, v12, v2, v7, v8, v13, v3, v4, v9, v14) ++ xxlor 0, 32+25, 32+25 ++ xxlor 32+25, 20, 20 ++ vadduwm 0, 0, 5 ++ vadduwm 1, 1, 6 ++ vadduwm 2, 2, 7 ++ vadduwm 3, 3, 4 ++ vadduwm 16, 16, 21 ++ vadduwm 17, 17, 22 ++ vadduwm 18, 18, 23 ++ vadduwm 19, 19, 20 ++ ++ vpermxor 15, 15, 0, 25 ++ vpermxor 12, 12, 1, 25 ++ vpermxor 13, 13, 2, 25 ++ vpermxor 14, 14, 3, 25 ++ vpermxor 31, 31, 16, 25 ++ vpermxor 28, 28, 17, 25 ++ vpermxor 29, 29, 18, 25 ++ vpermxor 30, 30, 19, 25 ++ ++ xxlor 32+25, 0, 0 ++ vadduwm 10, 10, 15 ++ vadduwm 11, 11, 12 ++ vadduwm 8, 8, 13 ++ vadduwm 9, 9, 14 ++ vadduwm 26, 26, 31 ++ vadduwm 27, 27, 28 ++ vadduwm 24, 24, 29 ++ vadduwm 25, 25, 30 ++ vxor 5, 5, 10 ++ vxor 6, 6, 11 ++ vxor 7, 7, 8 ++ vxor 4, 4, 9 ++ vxor 21, 21, 26 ++ vxor 22, 22, 27 ++ vxor 23, 23, 24 ++ vxor 20, 20, 25 ++ ++ xxlor 0, 32+25, 32+25 ++ xxlor 32+25, 21, 21 ++ vrlw 5, 5, 25 ++ vrlw 6, 6, 25 ++ vrlw 7, 7, 25 ++ vrlw 4, 4, 25 ++ vrlw 21, 21, 25 ++ vrlw 22, 22, 25 ++ vrlw 23, 23, 25 ++ vrlw 20, 20, 25 ++ xxlor 32+25, 0, 0 ++ ++ vadduwm 0, 0, 5 ++ vadduwm 1, 1, 6 ++ vadduwm 2, 2, 7 ++ vadduwm 3, 3, 4 ++ vadduwm 16, 16, 21 ++ vadduwm 17, 17, 22 ++ vadduwm 18, 18, 23 ++ vadduwm 19, 19, 20 ++ ++ xxlor 0, 32+25, 32+25 ++ xxlor 32+25, 22, 22 ++ vpermxor 15, 15, 0, 25 ++ vpermxor 12, 12, 1, 25 ++ vpermxor 13, 13, 2, 25 ++ vpermxor 14, 14, 3, 25 ++ vpermxor 31, 31, 16, 25 ++ vpermxor 28, 28, 17, 25 ++ vpermxor 29, 29, 18, 25 ++ vpermxor 30, 30, 19, 25 ++ xxlor 32+25, 0, 0 ++ ++ vadduwm 10, 10, 15 ++ vadduwm 11, 11, 12 ++ vadduwm 8, 8, 13 ++ vadduwm 9, 9, 14 ++ vadduwm 26, 26, 31 ++ vadduwm 27, 27, 28 ++ vadduwm 24, 24, 29 ++ vadduwm 25, 25, 30 ++ ++ xxlor 0, 32+28, 32+28 ++ xxlor 32+28, 23, 23 ++ vxor 5, 5, 10 ++ vxor 6, 6, 11 ++ vxor 7, 7, 8 ++ vxor 4, 4, 9 ++ vxor 21, 21, 26 ++ vxor 22, 22, 27 ++ vxor 23, 23, 24 ++ vxor 20, 20, 25 ++ vrlw 5, 5, 28 ++ vrlw 6, 6, 28 ++ vrlw 7, 7, 28 ++ vrlw 4, 4, 28 ++ vrlw 21, 21, 28 ++ vrlw 22, 22, 28 ++ vrlw 23, 23, 28 ++ vrlw 20, 20, 28 ++ xxlor 32+28, 0, 0 ++.endm ++ ++.macro QT_loop_4x ++ # QR(v0, v4, v8, v12, v1, v5, v9, v13, v2, v6, v10, v14, v3, v7, v11, v15) ++ vadduwm 0, 0, 4 ++ vadduwm 1, 1, 5 ++ vadduwm 2, 2, 6 ++ vadduwm 3, 3, 7 ++ vpermxor 12, 12, 0, 20 ++ vpermxor 13, 13, 1, 20 ++ vpermxor 14, 14, 2, 20 ++ vpermxor 15, 15, 3, 20 ++ vadduwm 8, 8, 12 ++ vadduwm 9, 9, 13 ++ vadduwm 10, 10, 14 ++ vadduwm 11, 11, 15 ++ vxor 4, 4, 8 ++ vxor 5, 5, 9 ++ vxor 6, 6, 10 ++ vxor 7, 7, 11 ++ vrlw 4, 4, 21 ++ vrlw 5, 5, 21 ++ vrlw 6, 6, 21 ++ vrlw 7, 7, 21 ++ vadduwm 0, 0, 4 ++ vadduwm 1, 1, 5 ++ vadduwm 2, 2, 6 ++ vadduwm 3, 3, 7 ++ vpermxor 12, 12, 0, 22 ++ vpermxor 13, 13, 1, 22 ++ vpermxor 14, 14, 2, 22 ++ vpermxor 15, 15, 3, 22 ++ vadduwm 8, 8, 12 ++ vadduwm 9, 9, 13 ++ vadduwm 10, 10, 14 ++ vadduwm 11, 11, 15 ++ vxor 4, 4, 8 ++ vxor 5, 5, 9 ++ vxor 6, 6, 10 ++ vxor 7, 7, 11 ++ vrlw 4, 4, 23 ++ vrlw 5, 5, 23 ++ vrlw 6, 6, 23 ++ vrlw 7, 7, 23 ++ ++ # QR(v0, v5, v10, v15, v1, v6, v11, v12, v2, v7, v8, v13, v3, v4, v9, v14) ++ vadduwm 0, 0, 5 ++ vadduwm 1, 1, 6 ++ vadduwm 2, 2, 7 ++ vadduwm 3, 3, 4 ++ vpermxor 15, 15, 0, 20 ++ vpermxor 12, 12, 1, 20 ++ vpermxor 13, 13, 2, 20 ++ vpermxor 14, 14, 3, 20 ++ vadduwm 10, 10, 15 ++ vadduwm 11, 11, 12 ++ vadduwm 8, 8, 13 ++ vadduwm 9, 9, 14 ++ vxor 5, 5, 10 ++ vxor 6, 6, 11 ++ vxor 7, 7, 8 ++ vxor 4, 4, 9 ++ vrlw 5, 5, 21 ++ vrlw 6, 6, 21 ++ vrlw 7, 7, 21 ++ vrlw 4, 4, 21 ++ vadduwm 0, 0, 5 ++ vadduwm 1, 1, 6 ++ vadduwm 2, 2, 7 ++ vadduwm 3, 3, 4 ++ vpermxor 15, 15, 0, 22 ++ vpermxor 12, 12, 1, 22 ++ vpermxor 13, 13, 2, 22 ++ vpermxor 14, 14, 3, 22 ++ vadduwm 10, 10, 15 ++ vadduwm 11, 11, 12 ++ vadduwm 8, 8, 13 ++ vadduwm 9, 9, 14 ++ vxor 5, 5, 10 ++ vxor 6, 6, 11 ++ vxor 7, 7, 8 ++ vxor 4, 4, 9 ++ vrlw 5, 5, 23 ++ vrlw 6, 6, 23 ++ vrlw 7, 7, 23 ++ vrlw 4, 4, 23 ++.endm ++ ++# Transpose ++.macro TP_4x a0 a1 a2 a3 ++ xxmrghw 10, 32+\a0, 32+\a1 # a0, a1, b0, b1 ++ xxmrghw 11, 32+\a2, 32+\a3 # a2, a3, b2, b3 ++ xxmrglw 12, 32+\a0, 32+\a1 # c0, c1, d0, d1 ++ xxmrglw 13, 32+\a2, 32+\a3 # c2, c3, d2, d3 ++ xxpermdi 32+\a0, 10, 11, 0 # a0, a1, a2, a3 ++ xxpermdi 32+\a1, 10, 11, 3 # b0, b1, b2, b3 ++ xxpermdi 32+\a2, 12, 13, 0 # c0, c1, c2, c3 ++ xxpermdi 32+\a3, 12, 13, 3 # d0, d1, d2, d3 ++.endm ++ ++# key stream = working state + state ++.macro Add_state S ++ vadduwm \S+0, \S+0, 16-\S ++ vadduwm \S+4, \S+4, 17-\S ++ vadduwm \S+8, \S+8, 18-\S ++ vadduwm \S+12, \S+12, 19-\S ++ ++ vadduwm \S+1, \S+1, 16-\S ++ vadduwm \S+5, \S+5, 17-\S ++ vadduwm \S+9, \S+9, 18-\S ++ vadduwm \S+13, \S+13, 19-\S ++ ++ vadduwm \S+2, \S+2, 16-\S ++ vadduwm \S+6, \S+6, 17-\S ++ vadduwm \S+10, \S+10, 18-\S ++ vadduwm \S+14, \S+14, 19-\S ++ ++ vadduwm \S+3, \S+3, 16-\S ++ vadduwm \S+7, \S+7, 17-\S ++ vadduwm \S+11, \S+11, 18-\S ++ vadduwm \S+15, \S+15, 19-\S ++.endm ++ ++# ++# write 256 bytes ++# ++.macro Write_256 S ++ add 9, 14, 5 ++ add 16, 14, 4 ++ lxvw4x 0, 0, 9 ++ lxvw4x 1, 17, 9 ++ lxvw4x 2, 18, 9 ++ lxvw4x 3, 19, 9 ++ lxvw4x 4, 20, 9 ++ lxvw4x 5, 21, 9 ++ lxvw4x 6, 22, 9 ++ lxvw4x 7, 23, 9 ++ lxvw4x 8, 24, 9 ++ lxvw4x 9, 25, 9 ++ lxvw4x 10, 26, 9 ++ lxvw4x 11, 27, 9 ++ lxvw4x 12, 28, 9 ++ lxvw4x 13, 29, 9 ++ lxvw4x 14, 30, 9 ++ lxvw4x 15, 31, 9 ++ ++ xxlxor \S+32, \S+32, 0 ++ xxlxor \S+36, \S+36, 1 ++ xxlxor \S+40, \S+40, 2 ++ xxlxor \S+44, \S+44, 3 ++ xxlxor \S+33, \S+33, 4 ++ xxlxor \S+37, \S+37, 5 ++ xxlxor \S+41, \S+41, 6 ++ xxlxor \S+45, \S+45, 7 ++ xxlxor \S+34, \S+34, 8 ++ xxlxor \S+38, \S+38, 9 ++ xxlxor \S+42, \S+42, 10 ++ xxlxor \S+46, \S+46, 11 ++ xxlxor \S+35, \S+35, 12 ++ xxlxor \S+39, \S+39, 13 ++ xxlxor \S+43, \S+43, 14 ++ xxlxor \S+47, \S+47, 15 ++ ++ stxvw4x \S+32, 0, 16 ++ stxvw4x \S+36, 17, 16 ++ stxvw4x \S+40, 18, 16 ++ stxvw4x \S+44, 19, 16 ++ ++ stxvw4x \S+33, 20, 16 ++ stxvw4x \S+37, 21, 16 ++ stxvw4x \S+41, 22, 16 ++ stxvw4x \S+45, 23, 16 ++ ++ stxvw4x \S+34, 24, 16 ++ stxvw4x \S+38, 25, 16 ++ stxvw4x \S+42, 26, 16 ++ stxvw4x \S+46, 27, 16 ++ ++ stxvw4x \S+35, 28, 16 ++ stxvw4x \S+39, 29, 16 ++ stxvw4x \S+43, 30, 16 ++ stxvw4x \S+47, 31, 16 ++ ++.endm ++ ++# ++# unsigned int _gcry_chacha20_p10le_8x(u32 *state, byte *dst, const byte *src, size_t len); ++# ++.global _gcry_chacha20_p10le_8x ++.align 5 ++_gcry_chacha20_p10le_8x: ++ cmpdi 6, 512 ++ blt Out_no_chacha ++ ++ stdu 1,-1024(1) ++ mflr 0 ++ ++ std 14,112(1) ++ std 15,120(1) ++ std 16,128(1) ++ std 17,136(1) ++ std 18,144(1) ++ std 19,152(1) ++ std 20,160(1) ++ std 21,168(1) ++ std 22,176(1) ++ std 23,184(1) ++ std 24,192(1) ++ std 25,200(1) ++ std 26,208(1) ++ std 27,216(1) ++ std 28,224(1) ++ std 29,232(1) ++ std 30,240(1) ++ std 31,248(1) ++ std 0, 1040(1) ++ ++ li 17, 16 ++ li 18, 32 ++ li 19, 48 ++ li 20, 64 ++ li 21, 80 ++ li 22, 96 ++ li 23, 112 ++ li 24, 128 ++ li 25, 144 ++ li 26, 160 ++ li 27, 176 ++ li 28, 192 ++ li 29, 208 ++ li 30, 224 ++ li 31, 240 ++ addi 9, 1, 256 ++ stvx 20, 0, 9 ++ stvx 21, 17, 9 ++ stvx 22, 18, 9 ++ stvx 23, 19, 9 ++ stvx 24, 20, 9 ++ stvx 25, 21, 9 ++ stvx 26, 22, 9 ++ stvx 27, 23, 9 ++ stvx 28, 24, 9 ++ stvx 29, 25, 9 ++ stvx 30, 26, 9 ++ stvx 31, 27, 9 ++ ++ add 9, 9, 27 ++ addi 14, 17, 16 ++ stxvx 14, 14, 9 ++ addi 14, 14, 16 ++ stxvx 15, 14, 9 ++ addi 14, 14, 16 ++ stxvx 16, 14, 9 ++ addi 14, 14, 16 ++ stxvx 17, 14, 9 ++ addi 14, 14, 16 ++ stxvx 18, 14, 9 ++ addi 14, 14, 16 ++ stxvx 19, 14, 9 ++ addi 14, 14, 16 ++ stxvx 20, 14, 9 ++ addi 14, 14, 16 ++ stxvx 21, 14, 9 ++ addi 14, 14, 16 ++ stxvx 22, 14, 9 ++ addi 14, 14, 16 ++ stxvx 23, 14, 9 ++ addi 14, 14, 16 ++ stxvx 24, 14, 9 ++ addi 14, 14, 16 ++ stxvx 25, 14, 9 ++ addi 14, 14, 16 ++ stxvx 26, 14, 9 ++ addi 14, 14, 16 ++ stxvx 27, 14, 9 ++ addi 14, 14, 16 ++ stxvx 28, 14, 9 ++ addi 14, 14, 16 ++ stxvx 29, 14, 9 ++ addi 14, 14, 16 ++ stxvx 30, 14, 9 ++ addi 14, 14, 16 ++ stxvx 31, 14, 9 ++ ++ mr 15, 6 # len ++ li 14, 0 # offset to inp and outp ++ ++ ld 10, sigma@got(2) ++ ++ lxvw4x 48, 0, 3 # vr16, constants ++ lxvw4x 49, 17, 3 # vr17, key 1 ++ lxvw4x 50, 18, 3 # vr18, key 2 ++ lxvw4x 51, 19, 3 # vr19, counter, nonce ++ ++ lxvw4x 62, 19, 10 # vr30, 4 ++ ++ vspltisw 21, 12 ++ vspltisw 23, 7 ++ ++ ld 11, permx@got(2) ++ lxvw4x 32+20, 0, 11 ++ lxvw4x 32+22, 17, 11 ++ ++ li 8, 10 ++ mtctr 8 ++ ++ xxlor 16, 48, 48 ++ xxlor 17, 49, 49 ++ xxlor 18, 50, 50 ++ xxlor 19, 51, 51 ++ ++ vspltisw 25, 4 ++ vspltisw 26, 8 ++ ++ xxlor 16, 48, 48 ++ xxlor 17, 49, 49 ++ xxlor 18, 50, 50 ++ xxlor 19, 51, 51 ++ ++ xxlor 25, 32+26, 32+26 ++ xxlor 24, 32+25, 32+25 ++ ++ vadduwm 31, 30, 25 # (0, 1, 2, 3) + (4, 4, 4, 4) ++ xxlor 30, 32+30, 32+30 ++ xxlor 31, 32+31, 32+31 ++ ++ xxlor 20, 32+20, 32+20 ++ xxlor 21, 32+21, 32+21 ++ xxlor 22, 32+22, 32+22 ++ xxlor 23, 32+23, 32+23 ++ ++Loop_8x: ++ lvx 0, 20, 10 ++ lvx 1, 21, 10 ++ lvx 2, 22, 10 ++ lvx 3, 23, 10 ++ xxspltw 32+4, 17, 0 ++ xxspltw 32+5, 17, 1 ++ xxspltw 32+6, 17, 2 ++ xxspltw 32+7, 17, 3 ++ xxspltw 32+8, 18, 0 ++ xxspltw 32+9, 18, 1 ++ xxspltw 32+10, 18, 2 ++ xxspltw 32+11, 18, 3 ++ xxspltw 32+12, 19, 0 ++ xxspltw 32+13, 19, 1 ++ xxspltw 32+14, 19, 2 ++ xxspltw 32+15, 19, 3 ++ vadduwm 12, 12, 30 # increase counter ++ ++ lvx 16, 20, 10 ++ lvx 17, 21, 10 ++ lvx 18, 22, 10 ++ lvx 19, 23, 10 ++ xxspltw 32+20, 17, 0 ++ xxspltw 32+21, 17, 1 ++ xxspltw 32+22, 17, 2 ++ xxspltw 32+23, 17, 3 ++ xxspltw 32+24, 18, 0 ++ xxspltw 32+25, 18, 1 ++ xxspltw 32+26, 18, 2 ++ xxspltw 32+27, 18, 3 ++ xxspltw 32+28, 19, 0 ++ xxspltw 32+29, 19, 1 ++ vadduwm 28, 28, 31 # increase counter ++ xxspltw 32+30, 19, 2 ++ xxspltw 32+31, 19, 3 ++ ++.align 5 ++quarter_loop_8x: ++ QT_loop_8x ++ ++ bdnz quarter_loop_8x ++ ++ xxlor 0, 32+30, 32+30 ++ xxlor 32+30, 30, 30 ++ vadduwm 12, 12, 30 ++ xxlor 32+30, 0, 0 ++ TP_4x 0, 1, 2, 3 ++ TP_4x 4, 5, 6, 7 ++ TP_4x 8, 9, 10, 11 ++ TP_4x 12, 13, 14, 15 ++ ++ xxlor 0, 48, 48 ++ xxlor 1, 49, 49 ++ xxlor 2, 50, 50 ++ xxlor 3, 51, 51 ++ xxlor 48, 16, 16 ++ xxlor 49, 17, 17 ++ xxlor 50, 18, 18 ++ xxlor 51, 19, 19 ++ Add_state 0 ++ xxlor 48, 0, 0 ++ xxlor 49, 1, 1 ++ xxlor 50, 2, 2 ++ xxlor 51, 3, 3 ++ Write_256 0 ++ addi 14, 14, 256 ++ addi 15, 15, -256 ++ ++ xxlor 5, 32+31, 32+31 ++ xxlor 32+31, 31, 31 ++ vadduwm 28, 28, 31 ++ xxlor 32+31, 5, 5 ++ TP_4x 16+0, 16+1, 16+2, 16+3 ++ TP_4x 16+4, 16+5, 16+6, 16+7 ++ TP_4x 16+8, 16+9, 16+10, 16+11 ++ TP_4x 16+12, 16+13, 16+14, 16+15 ++ ++ xxlor 32, 16, 16 ++ xxlor 33, 17, 17 ++ xxlor 34, 18, 18 ++ xxlor 35, 19, 19 ++ Add_state 16 ++ Write_256 16 ++ addi 14, 14, 256 ++ addi 15, 15, -256 ++ ++ # should update counter before out? ++ xxlor 32+24, 24, 24 ++ xxlor 32+25, 25, 25 ++ xxlor 32+30, 30, 30 ++ vadduwm 30, 30, 25 ++ vadduwm 31, 30, 24 ++ xxlor 30, 32+30, 32+30 ++ xxlor 31, 32+31, 32+31 ++ ++ cmpdi 15, 0 ++ beq Out_loop ++ ++ cmpdi 15, 512 ++ blt Loop_last ++ ++ mtctr 8 ++ b Loop_8x ++ ++Loop_last: ++ lxvw4x 48, 0, 3 # vr16, constants ++ lxvw4x 49, 17, 3 # vr17, key 1 ++ lxvw4x 50, 18, 3 # vr18, key 2 ++ lxvw4x 51, 19, 3 # vr19, counter, nonce ++ ++ vspltisw 21, 12 ++ vspltisw 23, 7 ++ lxvw4x 32+20, 0, 11 ++ lxvw4x 32+22, 17, 11 ++ ++ li 8, 10 ++ mtctr 8 ++ ++Loop_4x: ++ lvx 0, 20, 10 ++ lvx 1, 21, 10 ++ lvx 2, 22, 10 ++ lvx 3, 23, 10 ++ vspltw 4, 17, 0 ++ vspltw 5, 17, 1 ++ vspltw 6, 17, 2 ++ vspltw 7, 17, 3 ++ vspltw 8, 18, 0 ++ vspltw 9, 18, 1 ++ vspltw 10, 18, 2 ++ vspltw 11, 18, 3 ++ vspltw 12, 19, 0 ++ vadduwm 12, 12, 30 # increase counter ++ vspltw 13, 19, 1 ++ vspltw 14, 19, 2 ++ vspltw 15, 19, 3 ++ ++.align 5 ++quarter_loop: ++ QT_loop_4x ++ ++ bdnz quarter_loop ++ ++ vadduwm 12, 12, 30 ++ TP_4x 0, 1, 2, 3 ++ TP_4x 4, 5, 6, 7 ++ TP_4x 8, 9, 10, 11 ++ TP_4x 12, 13, 14, 15 ++ ++ Add_state 0 ++ Write_256 0 ++ addi 14, 14, 256 ++ addi 15, 15, -256 ++ ++ # Update state counter ++ vspltisw 25, 4 ++ vadduwm 30, 30, 25 ++ ++ cmpdi 15, 0 ++ beq Out_loop ++ ++ mtctr 8 ++ b Loop_4x ++ ++Out_loop: ++ # ++ # Update state counter ++ # ++ vspltisb 16, -1 # first 16 bytes - 0xffff...ff ++ vspltisb 17, 0 # second 16 bytes - 0x0000...00 ++ vsldoi 18, 16, 17, 12 ++ vand 18, 18, 30 ++ xxlor 32+19, 19, 19 ++ vadduwm 18, 19, 18 ++ stxvw4x 32+18, 19, 3 ++ li 3, 0 ++ ++ addi 9, 1, 256 ++ lvx 20, 0, 9 ++ lvx 21, 17, 9 ++ lvx 22, 18, 9 ++ lvx 23, 19, 9 ++ lvx 24, 20, 9 ++ lvx 25, 21, 9 ++ lvx 26, 22, 9 ++ lvx 27, 23, 9 ++ lvx 28, 24, 9 ++ lvx 29, 25, 9 ++ lvx 30, 26, 9 ++ lvx 31, 27, 9 ++ ++ add 9, 9, 27 ++ addi 14, 17, 16 ++ lxvx 14, 14, 9 ++ addi 14, 14, 16 ++ lxvx 15, 14, 9 ++ addi 14, 14, 16 ++ lxvx 16, 14, 9 ++ addi 14, 14, 16 ++ lxvx 17, 14, 9 ++ addi 14, 14, 16 ++ lxvx 18, 14, 9 ++ addi 14, 14, 16 ++ lxvx 19, 14, 9 ++ addi 14, 14, 16 ++ lxvx 20, 14, 9 ++ addi 14, 14, 16 ++ lxvx 21, 14, 9 ++ addi 14, 14, 16 ++ lxvx 22, 14, 9 ++ addi 14, 14, 16 ++ lxvx 23, 14, 9 ++ addi 14, 14, 16 ++ lxvx 24, 14, 9 ++ addi 14, 14, 16 ++ lxvx 25, 14, 9 ++ addi 14, 14, 16 ++ lxvx 26, 14, 9 ++ addi 14, 14, 16 ++ lxvx 27, 14, 9 ++ addi 14, 14, 16 ++ lxvx 28, 14, 9 ++ addi 14, 14, 16 ++ lxvx 29, 14, 9 ++ addi 14, 14, 16 ++ lxvx 30, 14, 9 ++ addi 14, 14, 16 ++ lxvx 31, 14, 9 ++ ++ ld 0, 1040(1) ++ ld 14,112(1) ++ ld 15,120(1) ++ ld 16,128(1) ++ ld 17,136(1) ++ ld 18,144(1) ++ ld 19,152(1) ++ ld 20,160(1) ++ ld 21,168(1) ++ ld 22,176(1) ++ ld 23,184(1) ++ ld 24,192(1) ++ ld 25,200(1) ++ ld 26,208(1) ++ ld 27,216(1) ++ ld 28,224(1) ++ ld 29,232(1) ++ ld 30,240(1) ++ ld 31,248(1) ++ ++ mtlr 0 ++ addi 1, 1, 1024 ++ blr ++ ++Out_no_chacha: ++ li 3, 0 ++ blr ++ ++.data ++.align 4 ++sigma: ++.long 0x61707865, 0x3320646e, 0x79622d32, 0x6b206574 ++.long 0x0c0d0e0f, 0x08090a0b, 0x04050607, 0x00010203 ++.long 1, 0, 0, 0 ++.long 0, 1, 2, 3 ++.long 0x61707865, 0x61707865, 0x61707865, 0x61707865 ++.long 0x3320646e, 0x3320646e, 0x3320646e, 0x3320646e ++.long 0x79622d32, 0x79622d32, 0x79622d32, 0x79622d32 ++.long 0x6b206574, 0x6b206574, 0x6b206574, 0x6b206574 ++permx: ++.long 0x22330011, 0x66774455, 0xaabb8899, 0xeeffccdd ++.long 0x11223300, 0x55667744, 0x99aabb88, 0xddeeffcc +Index: libgcrypt-1.10.2/cipher/chacha20.c +=================================================================== +--- libgcrypt-1.10.2.orig/cipher/chacha20.c ++++ libgcrypt-1.10.2/cipher/chacha20.c +@@ -125,6 +125,7 @@ typedef struct CHACHA20_context_s + unsigned int use_avx2:1; + unsigned int use_neon:1; + unsigned int use_ppc:1; ++ unsigned int use_p10:1; + unsigned int use_s390x:1; + } CHACHA20_context_t; + +@@ -163,6 +164,12 @@ unsigned int _gcry_chacha20_poly1305_amd + + #ifdef USE_PPC_VEC + ++#ifndef WORDS_BIGENDIAN ++unsigned int _gcry_chacha20_p10le_8x(u32 *state, byte *dst, ++ const byte *src, ++ size_t len); ++#endif ++ + unsigned int _gcry_chacha20_ppc8_blocks4(u32 *state, byte *dst, + const byte *src, + size_t nblks); +@@ -475,6 +482,9 @@ chacha20_do_setkey (CHACHA20_context_t * + #endif + #ifdef USE_PPC_VEC + ctx->use_ppc = (features & HWF_PPC_ARCH_2_07) != 0; ++# ifndef WORDS_BIGENDIAN ++ ctx->use_p10 = (features & HWF_PPC_ARCH_3_10) != 0; ++# endif + #endif + #ifdef USE_S390X_VX + ctx->use_s390x = (features & HWF_S390X_VX) != 0; +@@ -571,7 +581,22 @@ do_chacha20_encrypt_stream_tail (CHACHA2 + { + size_t nblocks = length / CHACHA20_BLOCK_SIZE; + nblocks -= nblocks % 4; +- nburn = _gcry_chacha20_ppc8_blocks4(ctx->input, outbuf, inbuf, nblocks); ++#ifndef WORDS_BIGENDIAN ++ /* ++ * A workaround to skip counter overflow. This is rare. ++ */ ++ if (ctx->use_p10 && nblocks >= 8 ++ && ((u64)ctx->input[12] + nblocks) <= 0xffffffffU) ++ { ++ size_t len = nblocks * CHACHA20_BLOCK_SIZE; ++ nburn = _gcry_chacha20_p10le_8x(ctx->input, outbuf, inbuf, len); ++ } ++ else ++#endif ++ { ++ nburn = _gcry_chacha20_ppc8_blocks4(ctx->input, outbuf, inbuf, ++ nblocks); ++ } + burn = nburn > burn ? nburn : burn; + length -= nblocks * CHACHA20_BLOCK_SIZE; + outbuf += nblocks * CHACHA20_BLOCK_SIZE; +@@ -760,6 +785,11 @@ _gcry_chacha20_poly1305_encrypt(gcry_cip + } + #endif + #ifdef USE_PPC_VEC_POLY1305 ++ else if (ctx->use_ppc && ctx->use_p10) ++ { ++ /* Skip stitched chacha20-poly1305 for P10. */ ++ authptr = NULL; ++ } + else if (ctx->use_ppc && length >= CHACHA20_BLOCK_SIZE * 4) + { + nburn = _gcry_chacha20_ppc8_blocks4(ctx->input, outbuf, inbuf, 4); +@@ -998,6 +1028,7 @@ _gcry_chacha20_poly1305_decrypt(gcry_cip + { + CHACHA20_context_t *ctx = (void *) &c->context.c; + unsigned int nburn, burn = 0; ++ int skip_stitched = 0; + + if (!length) + return 0; +@@ -1049,6 +1080,13 @@ _gcry_chacha20_poly1305_decrypt(gcry_cip + inbuf += nblocks * CHACHA20_BLOCK_SIZE; + } + #endif ++#ifdef USE_PPC_VEC_POLY1305 ++ if (ctx->use_ppc && ctx->use_p10) ++ { ++ /* Skip stitched chacha20-poly1305 for P10. */ ++ skip_stitched = 1; ++ } ++#endif + + #ifdef USE_SSSE3 + if (ctx->use_ssse3) +@@ -1102,7 +1140,8 @@ _gcry_chacha20_poly1305_decrypt(gcry_cip + #endif + + #ifdef USE_PPC_VEC_POLY1305 +- if (ctx->use_ppc && length >= 4 * CHACHA20_BLOCK_SIZE) ++ /* skip stitch for p10 */ ++ if (!skip_stitched && ctx->use_ppc && length >= 4 * CHACHA20_BLOCK_SIZE) + { + size_t nblocks = length / CHACHA20_BLOCK_SIZE; + nblocks -= nblocks % 4; +Index: libgcrypt-1.10.2/cipher/poly1305-internal.h +=================================================================== +--- libgcrypt-1.10.2.orig/cipher/poly1305-internal.h ++++ libgcrypt-1.10.2/cipher/poly1305-internal.h +@@ -33,6 +33,17 @@ + #define POLY1305_KEYLEN 32 + #define POLY1305_BLOCKSIZE 16 + ++/* POLY1305_USE_PPC_VEC indicates whether to enable PowerPC vector code. */ ++#undef POLY1305_USE_PPC_VEC ++#ifdef ENABLE_PPC_CRYPTO_SUPPORT ++# if defined(HAVE_COMPATIBLE_CC_PPC_ALTIVEC) && \ ++ defined(HAVE_GCC_INLINE_ASM_PPC_ALTIVEC) && \ ++ !defined(WORDS_BIGENDIAN) ++# if __GNUC__ >= 4 ++# define POLY1305_USE_PPC_VEC 1 ++# endif ++# endif ++#endif + + typedef struct + { +@@ -46,6 +57,9 @@ typedef struct poly1305_context_s + POLY1305_STATE state; + byte buffer[POLY1305_BLOCKSIZE]; + unsigned int leftover; ++#ifdef POLY1305_USE_PPC_VEC ++ unsigned int use_p10:1; ++#endif + } poly1305_context_t; + + +Index: libgcrypt-1.10.2/cipher/poly1305-p10le.s +=================================================================== +--- /dev/null ++++ libgcrypt-1.10.2/cipher/poly1305-p10le.s +@@ -0,0 +1,841 @@ ++# Copyright 2021- IBM Inc. All rights reserved ++# ++# This file is part of Libgcrypt. ++# ++# Libgcrypt is free software; you can redistribute it and/or modify ++# it under the terms of the GNU Lesser General Public License as ++# published by the Free Software Foundation; either version 2.1 of ++# the License, or (at your option) any later version. ++# ++# Libgcrypt 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 Lesser General Public License for more details. ++# ++# You should have received a copy of the GNU Lesser General Public ++# License along with this program; if not, see . ++# ++#=================================================================================== ++# Written by Danny Tsen ++# ++# Poly1305 - this version mainly using vector/VSX/Scalar ++# - 26 bits limbs ++# - Handle multiple 64 byte blcoks but need at least 2 64 bytes block ++# ++# Improve performance by breaking down polynominal to the sum of products with ++# h4 = m1 * r⁴ + m2 * r³ + m3 * r² + m4 * r ++# ++# 07/22/21 - this revison based on the above sum of products. Setup r^4, r^3, r^2, r and s3, s2, s1, s0 ++# to 9 vectors for multiplications. ++# ++# setup r^4, r^3, r^2, r vectors ++# vs [r^1, r^3, r^2, r^4] ++# vs0 = [r0,.....] ++# vs1 = [r1,.....] ++# vs2 = [r2,.....] ++# vs3 = [r3,.....] ++# vs4 = [r4,.....] ++# vs5 = [r1*5,...] ++# vs6 = [r2*5,...] ++# vs7 = [r2*5,...] ++# vs8 = [r4*5,...] ++# ++# Each word in a vector consists a member of a "r/s" in [a * r/s]. ++# ++# r0, r4*5, r3*5, r2*5, r1*5; ++# r1, r0, r4*5, r3*5, r2*5; ++# r2, r1, r0, r4*5, r3*5; ++# r3, r2, r1, r0, r4*5; ++# r4, r3, r2, r1, r0 ; ++# ++# ++# gcry_poly1305_p10le_4blocks( uint8_t *k, uint32_t mlen, uint8_t *m) ++# k = 32 bytes key ++# r3 = k (r, s) ++# r4 = mlen ++# r5 = m ++# ++.text ++ ++# Block size 16 bytes ++# key = (r, s) ++# clamp r &= 0x0FFFFFFC0FFFFFFC 0x0FFFFFFC0FFFFFFF ++# p = 2^130 - 5 ++# a += m ++# a = (r + a) % p ++# a += s ++# 16 bytes (a) ++# ++# p[0] = a0*r0 + a1*r4*5 + a2*r3*5 + a3*r2*5 + a4*r1*5; ++# p[1] = a0*r1 + a1*r0 + a2*r4*5 + a3*r3*5 + a4*r2*5; ++# p[2] = a0*r2 + a1*r1 + a2*r0 + a3*r4*5 + a4*r3*5; ++# p[3] = a0*r3 + a1*r2 + a2*r1 + a3*r0 + a4*r4*5; ++# p[4] = a0*r4 + a1*r3 + a2*r2 + a3*r1 + a4*r0 ; ++# ++# [r^2, r^3, r^1, r^4] ++# [m3, m2, m4, m1] ++# ++# multiply odd and even words ++.macro mul_odd ++ vmulouw 14, 4, 26 ++ vmulouw 10, 5, 3 ++ vmulouw 11, 6, 2 ++ vmulouw 12, 7, 1 ++ vmulouw 13, 8, 0 ++ vmulouw 15, 4, 27 ++ vaddudm 14, 14, 10 ++ vaddudm 14, 14, 11 ++ vmulouw 10, 5, 26 ++ vmulouw 11, 6, 3 ++ vaddudm 14, 14, 12 ++ vaddudm 14, 14, 13 # x0 ++ vaddudm 15, 15, 10 ++ vaddudm 15, 15, 11 ++ vmulouw 12, 7, 2 ++ vmulouw 13, 8, 1 ++ vaddudm 15, 15, 12 ++ vaddudm 15, 15, 13 # x1 ++ vmulouw 16, 4, 28 ++ vmulouw 10, 5, 27 ++ vmulouw 11, 6, 26 ++ vaddudm 16, 16, 10 ++ vaddudm 16, 16, 11 ++ vmulouw 12, 7, 3 ++ vmulouw 13, 8, 2 ++ vaddudm 16, 16, 12 ++ vaddudm 16, 16, 13 # x2 ++ vmulouw 17, 4, 29 ++ vmulouw 10, 5, 28 ++ vmulouw 11, 6, 27 ++ vaddudm 17, 17, 10 ++ vaddudm 17, 17, 11 ++ vmulouw 12, 7, 26 ++ vmulouw 13, 8, 3 ++ vaddudm 17, 17, 12 ++ vaddudm 17, 17, 13 # x3 ++ vmulouw 18, 4, 30 ++ vmulouw 10, 5, 29 ++ vmulouw 11, 6, 28 ++ vaddudm 18, 18, 10 ++ vaddudm 18, 18, 11 ++ vmulouw 12, 7, 27 ++ vmulouw 13, 8, 26 ++ vaddudm 18, 18, 12 ++ vaddudm 18, 18, 13 # x4 ++.endm ++ ++.macro mul_even ++ vmuleuw 9, 4, 26 ++ vmuleuw 10, 5, 3 ++ vmuleuw 11, 6, 2 ++ vmuleuw 12, 7, 1 ++ vmuleuw 13, 8, 0 ++ vaddudm 14, 14, 9 ++ vaddudm 14, 14, 10 ++ vaddudm 14, 14, 11 ++ vaddudm 14, 14, 12 ++ vaddudm 14, 14, 13 # x0 ++ ++ vmuleuw 9, 4, 27 ++ vmuleuw 10, 5, 26 ++ vmuleuw 11, 6, 3 ++ vmuleuw 12, 7, 2 ++ vmuleuw 13, 8, 1 ++ vaddudm 15, 15, 9 ++ vaddudm 15, 15, 10 ++ vaddudm 15, 15, 11 ++ vaddudm 15, 15, 12 ++ vaddudm 15, 15, 13 # x1 ++ ++ vmuleuw 9, 4, 28 ++ vmuleuw 10, 5, 27 ++ vmuleuw 11, 6, 26 ++ vmuleuw 12, 7, 3 ++ vmuleuw 13, 8, 2 ++ vaddudm 16, 16, 9 ++ vaddudm 16, 16, 10 ++ vaddudm 16, 16, 11 ++ vaddudm 16, 16, 12 ++ vaddudm 16, 16, 13 # x2 ++ ++ vmuleuw 9, 4, 29 ++ vmuleuw 10, 5, 28 ++ vmuleuw 11, 6, 27 ++ vmuleuw 12, 7, 26 ++ vmuleuw 13, 8, 3 ++ vaddudm 17, 17, 9 ++ vaddudm 17, 17, 10 ++ vaddudm 17, 17, 11 ++ vaddudm 17, 17, 12 ++ vaddudm 17, 17, 13 # x3 ++ ++ vmuleuw 9, 4, 30 ++ vmuleuw 10, 5, 29 ++ vmuleuw 11, 6, 28 ++ vmuleuw 12, 7, 27 ++ vmuleuw 13, 8, 26 ++ vaddudm 18, 18, 9 ++ vaddudm 18, 18, 10 ++ vaddudm 18, 18, 11 ++ vaddudm 18, 18, 12 ++ vaddudm 18, 18, 13 # x4 ++.endm ++ ++# setup r^4, r^3, r^2, r vectors ++# [r, r^3, r^2, r^4] ++# vs0 = [r0,...] ++# vs1 = [r1,...] ++# vs2 = [r2,...] ++# vs3 = [r3,...] ++# vs4 = [r4,...] ++# vs5 = [r4*5,...] ++# vs6 = [r3*5,...] ++# vs7 = [r2*5,...] ++# vs8 = [r1*5,...] ++# ++# r0, r4*5, r3*5, r2*5, r1*5; ++# r1, r0, r4*5, r3*5, r2*5; ++# r2, r1, r0, r4*5, r3*5; ++# r3, r2, r1, r0, r4*5; ++# r4, r3, r2, r1, r0 ; ++# ++.macro poly1305_setup_r ++ ++ # save r ++ xxlor 26, 58, 58 ++ xxlor 27, 59, 59 ++ xxlor 28, 60, 60 ++ xxlor 29, 61, 61 ++ xxlor 30, 62, 62 ++ ++ xxlxor 31, 31, 31 ++ ++# [r, r^3, r^2, r^4] ++ # compute r^2 ++ vmr 4, 26 ++ vmr 5, 27 ++ vmr 6, 28 ++ vmr 7, 29 ++ vmr 8, 30 ++ bl do_mul # r^2 r^1 ++ xxpermdi 58, 58, 36, 0x3 # r0 ++ xxpermdi 59, 59, 37, 0x3 # r1 ++ xxpermdi 60, 60, 38, 0x3 # r2 ++ xxpermdi 61, 61, 39, 0x3 # r3 ++ xxpermdi 62, 62, 40, 0x3 # r4 ++ xxpermdi 36, 36, 36, 0x3 ++ xxpermdi 37, 37, 37, 0x3 ++ xxpermdi 38, 38, 38, 0x3 ++ xxpermdi 39, 39, 39, 0x3 ++ xxpermdi 40, 40, 40, 0x3 ++ vspltisb 13, 2 ++ vsld 9, 27, 13 ++ vsld 10, 28, 13 ++ vsld 11, 29, 13 ++ vsld 12, 30, 13 ++ vaddudm 0, 9, 27 ++ vaddudm 1, 10, 28 ++ vaddudm 2, 11, 29 ++ vaddudm 3, 12, 30 ++ ++ bl do_mul # r^4 r^3 ++ vmrgow 26, 26, 4 ++ vmrgow 27, 27, 5 ++ vmrgow 28, 28, 6 ++ vmrgow 29, 29, 7 ++ vmrgow 30, 30, 8 ++ vspltisb 13, 2 ++ vsld 9, 27, 13 ++ vsld 10, 28, 13 ++ vsld 11, 29, 13 ++ vsld 12, 30, 13 ++ vaddudm 0, 9, 27 ++ vaddudm 1, 10, 28 ++ vaddudm 2, 11, 29 ++ vaddudm 3, 12, 30 ++ ++ # r^2 r^4 ++ xxlor 0, 58, 58 ++ xxlor 1, 59, 59 ++ xxlor 2, 60, 60 ++ xxlor 3, 61, 61 ++ xxlor 4, 62, 62 ++ xxlor 5, 32, 32 ++ xxlor 6, 33, 33 ++ xxlor 7, 34, 34 ++ xxlor 8, 35, 35 ++ ++ vspltw 9, 26, 3 ++ vspltw 10, 26, 2 ++ vmrgow 26, 10, 9 ++ vspltw 9, 27, 3 ++ vspltw 10, 27, 2 ++ vmrgow 27, 10, 9 ++ vspltw 9, 28, 3 ++ vspltw 10, 28, 2 ++ vmrgow 28, 10, 9 ++ vspltw 9, 29, 3 ++ vspltw 10, 29, 2 ++ vmrgow 29, 10, 9 ++ vspltw 9, 30, 3 ++ vspltw 10, 30, 2 ++ vmrgow 30, 10, 9 ++ ++ vsld 9, 27, 13 ++ vsld 10, 28, 13 ++ vsld 11, 29, 13 ++ vsld 12, 30, 13 ++ vaddudm 0, 9, 27 ++ vaddudm 1, 10, 28 ++ vaddudm 2, 11, 29 ++ vaddudm 3, 12, 30 ++.endm ++ ++do_mul: ++ mul_odd ++ ++ # do reduction ( h %= p ) ++ # carry reduction ++ vspltisb 9, 2 ++ vsrd 10, 14, 31 ++ vsrd 11, 17, 31 ++ vand 7, 17, 25 ++ vand 4, 14, 25 ++ vaddudm 18, 18, 11 ++ vsrd 12, 18, 31 ++ vaddudm 15, 15, 10 ++ ++ vsrd 11, 15, 31 ++ vand 8, 18, 25 ++ vand 5, 15, 25 ++ vaddudm 4, 4, 12 ++ vsld 10, 12, 9 ++ vaddudm 6, 16, 11 ++ ++ vsrd 13, 6, 31 ++ vand 6, 6, 25 ++ vaddudm 4, 4, 10 ++ vsrd 10, 4, 31 ++ vaddudm 7, 7, 13 ++ ++ vsrd 11, 7, 31 ++ vand 7, 7, 25 ++ vand 4, 4, 25 ++ vaddudm 5, 5, 10 ++ vaddudm 8, 8, 11 ++ blr ++ ++# ++# init key ++# ++do_poly1305_init: ++ ld 10, rmask@got(2) ++ ld 11, 0(10) ++ ld 12, 8(10) ++ ++ li 14, 16 ++ li 15, 32 ++ ld 10, cnum@got(2) ++ lvx 25, 0, 10 # v25 - mask ++ lvx 31, 14, 10 # v31 = 1a ++ lvx 19, 15, 10 # v19 = 1 << 24 ++ lxv 24, 48(10) # vs24 ++ lxv 25, 64(10) # vs25 ++ ++ # initialize ++ # load key from r3 to vectors ++ ld 9, 16(3) ++ ld 10, 24(3) ++ ld 11, 0(3) ++ ld 12, 8(3) ++ ++ # break 26 bits ++ extrdi 14, 9, 26, 38 ++ extrdi 15, 9, 26, 12 ++ extrdi 16, 9, 12, 0 ++ mtvsrdd 58, 0, 14 ++ insrdi 16, 10, 14, 38 ++ mtvsrdd 59, 0, 15 ++ extrdi 17, 10, 26, 24 ++ mtvsrdd 60, 0, 16 ++ extrdi 18, 10, 24, 0 ++ mtvsrdd 61, 0, 17 ++ mtvsrdd 62, 0, 18 ++ ++ # r1 = r1 * 5, r2 = r2 * 5, r3 = r3 * 5, r4 = r4 * 5 ++ li 9, 5 ++ mtvsrdd 36, 0, 9 ++ vmulouw 0, 27, 4 # v0 = rr0 ++ vmulouw 1, 28, 4 # v1 = rr1 ++ vmulouw 2, 29, 4 # v2 = rr2 ++ vmulouw 3, 30, 4 # v3 = rr3 ++ blr ++ ++# ++# gcry_poly1305_p10le_4blocks( uint8_t *k, uint32_t mlen, uint8_t *m) ++# k = 32 bytes key ++# r3 = k (r, s) ++# r4 = mlen ++# r5 = m ++# ++.global gcry_poly1305_p10le_4blocks ++.align 5 ++gcry_poly1305_p10le_4blocks: ++_gcry_poly1305_p10le_4blocks: ++ cmpdi 5, 128 ++ blt Out_no_poly1305 ++ ++ stdu 1,-1024(1) ++ mflr 0 ++ ++ std 14,112(1) ++ std 15,120(1) ++ std 16,128(1) ++ std 17,136(1) ++ std 18,144(1) ++ std 19,152(1) ++ std 20,160(1) ++ std 21,168(1) ++ std 31,248(1) ++ li 14, 256 ++ stvx 20, 14, 1 ++ addi 14, 14, 16 ++ stvx 21, 14, 1 ++ addi 14, 14, 16 ++ stvx 22, 14, 1 ++ addi 14, 14, 16 ++ stvx 23, 14, 1 ++ addi 14, 14, 16 ++ stvx 24, 14, 1 ++ addi 14, 14, 16 ++ stvx 25, 14, 1 ++ addi 14, 14, 16 ++ stvx 26, 14, 1 ++ addi 14, 14, 16 ++ stvx 27, 14, 1 ++ addi 14, 14, 16 ++ stvx 28, 14, 1 ++ addi 14, 14, 16 ++ stvx 29, 14, 1 ++ addi 14, 14, 16 ++ stvx 30, 14, 1 ++ addi 14, 14, 16 ++ stvx 31, 14, 1 ++ ++ addi 14, 14, 16 ++ stxvx 14, 14, 1 ++ addi 14, 14, 16 ++ stxvx 15, 14, 1 ++ addi 14, 14, 16 ++ stxvx 16, 14, 1 ++ addi 14, 14, 16 ++ stxvx 17, 14, 1 ++ addi 14, 14, 16 ++ stxvx 18, 14, 1 ++ addi 14, 14, 16 ++ stxvx 19, 14, 1 ++ addi 14, 14, 16 ++ stxvx 20, 14, 1 ++ addi 14, 14, 16 ++ stxvx 21, 14, 1 ++ addi 14, 14, 16 ++ stxvx 22, 14, 1 ++ addi 14, 14, 16 ++ stxvx 23, 14, 1 ++ addi 14, 14, 16 ++ stxvx 24, 14, 1 ++ addi 14, 14, 16 ++ stxvx 25, 14, 1 ++ addi 14, 14, 16 ++ stxvx 26, 14, 1 ++ addi 14, 14, 16 ++ stxvx 27, 14, 1 ++ addi 14, 14, 16 ++ stxvx 28, 14, 1 ++ addi 14, 14, 16 ++ stxvx 29, 14, 1 ++ addi 14, 14, 16 ++ stxvx 30, 14, 1 ++ addi 14, 14, 16 ++ stxvx 31, 14, 1 ++ std 0, 1040(1) ++ ++ bl do_poly1305_init ++ ++ li 21, 0 # counter to message ++ ++ poly1305_setup_r ++ ++ # load previous state ++ # break/convert r6 to 26 bits ++ ld 9, 32(3) ++ ld 10, 40(3) ++ lwz 19, 48(3) ++ sldi 19, 19, 24 ++ mtvsrdd 41, 0, 19 ++ extrdi 14, 9, 26, 38 ++ extrdi 15, 9, 26, 12 ++ extrdi 16, 9, 12, 0 ++ mtvsrdd 36, 0, 14 ++ insrdi 16, 10, 14, 38 ++ mtvsrdd 37, 0, 15 ++ extrdi 17, 10, 26, 24 ++ mtvsrdd 38, 0, 16 ++ extrdi 18, 10, 24, 0 ++ mtvsrdd 39, 0, 17 ++ mtvsrdd 40, 0, 18 ++ vor 8, 8, 9 ++ ++ # input m1 m2 ++ add 20, 4, 21 ++ xxlor 49, 24, 24 ++ xxlor 50, 25, 25 ++ lxvw4x 43, 0, 20 ++ addi 17, 20, 16 ++ lxvw4x 44, 0, 17 ++ vperm 14, 11, 12, 17 ++ vperm 15, 11, 12, 18 ++ vand 9, 14, 25 # a0 ++ vsrd 10, 14, 31 # >> 26 ++ vsrd 11, 10, 31 # 12 bits left ++ vand 10, 10, 25 # a1 ++ vspltisb 13, 12 ++ vand 16, 15, 25 ++ vsld 12, 16, 13 ++ vor 11, 11, 12 ++ vand 11, 11, 25 # a2 ++ vspltisb 13, 14 ++ vsrd 12, 15, 13 # >> 14 ++ vsrd 13, 12, 31 # >> 26, a4 ++ vand 12, 12, 25 # a3 ++ ++ vaddudm 20, 4, 9 ++ vaddudm 21, 5, 10 ++ vaddudm 22, 6, 11 ++ vaddudm 23, 7, 12 ++ vaddudm 24, 8, 13 ++ ++ # m3 m4 ++ addi 17, 17, 16 ++ lxvw4x 43, 0, 17 ++ addi 17, 17, 16 ++ lxvw4x 44, 0, 17 ++ vperm 14, 11, 12, 17 ++ vperm 15, 11, 12, 18 ++ vand 9, 14, 25 # a0 ++ vsrd 10, 14, 31 # >> 26 ++ vsrd 11, 10, 31 # 12 bits left ++ vand 10, 10, 25 # a1 ++ vspltisb 13, 12 ++ vand 16, 15, 25 ++ vsld 12, 16, 13 ++ vspltisb 13, 14 ++ vor 11, 11, 12 ++ vand 11, 11, 25 # a2 ++ vsrd 12, 15, 13 # >> 14 ++ vsrd 13, 12, 31 # >> 26, a4 ++ vand 12, 12, 25 # a3 ++ ++ # Smash 4 message blocks into 5 vectors of [m4, m2, m3, m1] ++ vmrgow 4, 9, 20 ++ vmrgow 5, 10, 21 ++ vmrgow 6, 11, 22 ++ vmrgow 7, 12, 23 ++ vmrgow 8, 13, 24 ++ vaddudm 8, 8, 19 ++ ++ addi 5, 5, -64 ++ addi 21, 21, 64 ++ ++ li 9, 64 ++ divdu 31, 5, 9 ++ ++ mtctr 31 ++ ++# h4 = m1 * r⁴ + m2 * r³ + m3 * r² + m4 * r ++# Rewrite the polynominal sum of product as follows, ++# h1 = (h0 + m1) * r^2, h2 = (h0 + m2) * r^2 ++# h3 = (h1 + m3) * r^2, h4 = (h2 + m4) * r^2 --> (h0 + m1) r*4 + (h3 + m3) r^2, (h0 + m2) r^4 + (h0 + m4) r^2 ++# .... Repeat ++# h5 = (h3 + m5) * r^2, h6 = (h4 + m6) * r^2 --> ++# h7 = (h5 + m7) * r^2, h8 = (h6 + m8) * r^1 --> m5 * r^4 + m6 * r^3 + m7 * r^2 + m8 * r ++# ++loop_4blocks: ++ ++ # Multiply odd words and even words ++ mul_odd ++ mul_even ++ # carry reduction ++ vspltisb 9, 2 ++ vsrd 10, 14, 31 ++ vsrd 11, 17, 31 ++ vand 7, 17, 25 ++ vand 4, 14, 25 ++ vaddudm 18, 18, 11 ++ vsrd 12, 18, 31 ++ vaddudm 15, 15, 10 ++ ++ vsrd 11, 15, 31 ++ vand 8, 18, 25 ++ vand 5, 15, 25 ++ vaddudm 4, 4, 12 ++ vsld 10, 12, 9 ++ vaddudm 6, 16, 11 ++ ++ vsrd 13, 6, 31 ++ vand 6, 6, 25 ++ vaddudm 4, 4, 10 ++ vsrd 10, 4, 31 ++ vaddudm 7, 7, 13 ++ ++ vsrd 11, 7, 31 ++ vand 7, 7, 25 ++ vand 4, 4, 25 ++ vaddudm 5, 5, 10 ++ vaddudm 8, 8, 11 ++ ++ # input m1 m2 m3 m4 ++ add 20, 4, 21 ++ xxlor 49, 24, 24 ++ xxlor 50, 25, 25 ++ lxvw4x 43, 0, 20 ++ addi 17, 20, 16 ++ lxvw4x 44, 0, 17 ++ vperm 14, 11, 12, 17 ++ vperm 15, 11, 12, 18 ++ addi 17, 17, 16 ++ lxvw4x 43, 0, 17 ++ addi 17, 17, 16 ++ lxvw4x 44, 0, 17 ++ vperm 17, 11, 12, 17 ++ vperm 18, 11, 12, 18 ++ ++ vand 20, 14, 25 # a0 ++ vand 9, 17, 25 # a0 ++ vsrd 21, 14, 31 # >> 26 ++ vsrd 22, 21, 31 # 12 bits left ++ vsrd 10, 17, 31 # >> 26 ++ vsrd 11, 10, 31 # 12 bits left ++ ++ vand 21, 21, 25 # a1 ++ vand 10, 10, 25 # a1 ++ ++ vspltisb 13, 12 ++ vand 16, 15, 25 ++ vsld 23, 16, 13 ++ vor 22, 22, 23 ++ vand 22, 22, 25 # a2 ++ vand 16, 18, 25 ++ vsld 12, 16, 13 ++ vor 11, 11, 12 ++ vand 11, 11, 25 # a2 ++ vspltisb 13, 14 ++ vsrd 23, 15, 13 # >> 14 ++ vsrd 24, 23, 31 # >> 26, a4 ++ vand 23, 23, 25 # a3 ++ vsrd 12, 18, 13 # >> 14 ++ vsrd 13, 12, 31 # >> 26, a4 ++ vand 12, 12, 25 # a3 ++ ++ vaddudm 4, 4, 20 ++ vaddudm 5, 5, 21 ++ vaddudm 6, 6, 22 ++ vaddudm 7, 7, 23 ++ vaddudm 8, 8, 24 ++ ++ # Smash 4 message blocks into 5 vectors of [m4, m2, m3, m1] ++ vmrgow 4, 9, 4 ++ vmrgow 5, 10, 5 ++ vmrgow 6, 11, 6 ++ vmrgow 7, 12, 7 ++ vmrgow 8, 13, 8 ++ vaddudm 8, 8, 19 ++ ++ addi 5, 5, -64 ++ addi 21, 21, 64 ++ ++ bdnz loop_4blocks ++ ++ xxlor 58, 0, 0 ++ xxlor 59, 1, 1 ++ xxlor 60, 2, 2 ++ xxlor 61, 3, 3 ++ xxlor 62, 4, 4 ++ xxlor 32, 5, 5 ++ xxlor 33, 6, 6 ++ xxlor 34, 7, 7 ++ xxlor 35, 8, 8 ++ ++ # Multiply odd words and even words ++ mul_odd ++ mul_even ++ ++ # Sum the products. ++ xxpermdi 41, 31, 46, 0 ++ xxpermdi 42, 31, 47, 0 ++ vaddudm 4, 14, 9 ++ xxpermdi 36, 31, 36, 3 ++ vaddudm 5, 15, 10 ++ xxpermdi 37, 31, 37, 3 ++ xxpermdi 43, 31, 48, 0 ++ vaddudm 6, 16, 11 ++ xxpermdi 38, 31, 38, 3 ++ xxpermdi 44, 31, 49, 0 ++ vaddudm 7, 17, 12 ++ xxpermdi 39, 31, 39, 3 ++ xxpermdi 45, 31, 50, 0 ++ vaddudm 8, 18, 13 ++ xxpermdi 40, 31, 40, 3 ++ ++ # carry reduction ++ vspltisb 9, 2 ++ vsrd 10, 4, 31 ++ vsrd 11, 7, 31 ++ vand 7, 7, 25 ++ vand 4, 4, 25 ++ vaddudm 8, 8, 11 ++ vsrd 12, 8, 31 ++ vaddudm 5, 5, 10 ++ ++ vsrd 11, 5, 31 ++ vand 8, 8, 25 ++ vand 5, 5, 25 ++ vaddudm 4, 4, 12 ++ vsld 10, 12, 9 ++ vaddudm 6, 6, 11 ++ ++ vsrd 13, 6, 31 ++ vand 6, 6, 25 ++ vaddudm 4, 4, 10 ++ vsrd 10, 4, 31 ++ vaddudm 7, 7, 13 ++ ++ vsrd 11, 7, 31 ++ vand 7, 7, 25 ++ vand 4, 4, 25 ++ vaddudm 5, 5, 10 ++ vaddudm 8, 8, 11 ++ ++ b do_final_update ++ ++do_final_update: ++ # v4, v5, v6, v7 and v8 are 26 bit vectors ++ vsld 5, 5, 31 ++ vor 20, 4, 5 ++ vspltisb 11, 12 ++ vsrd 12, 6, 11 ++ vsld 6, 6, 31 ++ vsld 6, 6, 31 ++ vor 20, 20, 6 ++ vspltisb 11, 14 ++ vsld 7, 7, 11 ++ vor 21, 7, 12 ++ mfvsrld 16, 40 # save last 2 bytes ++ vsld 8, 8, 11 ++ vsld 8, 8, 31 ++ vor 21, 21, 8 ++ mfvsrld 17, 52 ++ mfvsrld 19, 53 ++ srdi 16, 16, 24 ++ ++ std 17, 32(3) ++ std 19, 40(3) ++ stw 16, 48(3) ++ ++Out_loop: ++ li 3, 0 ++ ++ li 14, 256 ++ lvx 20, 14, 1 ++ addi 14, 14, 16 ++ lvx 21, 14, 1 ++ addi 14, 14, 16 ++ lvx 22, 14, 1 ++ addi 14, 14, 16 ++ lvx 23, 14, 1 ++ addi 14, 14, 16 ++ lvx 24, 14, 1 ++ addi 14, 14, 16 ++ lvx 25, 14, 1 ++ addi 14, 14, 16 ++ lvx 26, 14, 1 ++ addi 14, 14, 16 ++ lvx 27, 14, 1 ++ addi 14, 14, 16 ++ lvx 28, 14, 1 ++ addi 14, 14, 16 ++ lvx 29, 14, 1 ++ addi 14, 14, 16 ++ lvx 30, 14, 1 ++ addi 14, 14, 16 ++ lvx 31, 14, 1 ++ ++ addi 14, 14, 16 ++ lxvx 14, 14, 1 ++ addi 14, 14, 16 ++ lxvx 15, 14, 1 ++ addi 14, 14, 16 ++ lxvx 16, 14, 1 ++ addi 14, 14, 16 ++ lxvx 17, 14, 1 ++ addi 14, 14, 16 ++ lxvx 18, 14, 1 ++ addi 14, 14, 16 ++ lxvx 19, 14, 1 ++ addi 14, 14, 16 ++ lxvx 20, 14, 1 ++ addi 14, 14, 16 ++ lxvx 21, 14, 1 ++ addi 14, 14, 16 ++ lxvx 22, 14, 1 ++ addi 14, 14, 16 ++ lxvx 23, 14, 1 ++ addi 14, 14, 16 ++ lxvx 24, 14, 1 ++ addi 14, 14, 16 ++ lxvx 25, 14, 1 ++ addi 14, 14, 16 ++ lxvx 26, 14, 1 ++ addi 14, 14, 16 ++ lxvx 27, 14, 1 ++ addi 14, 14, 16 ++ lxvx 28, 14, 1 ++ addi 14, 14, 16 ++ lxvx 29, 14, 1 ++ addi 14, 14, 16 ++ lxvx 30, 14, 1 ++ addi 14, 14, 16 ++ lxvx 31, 14, 1 ++ ++ ld 0, 1040(1) ++ ld 14,112(1) ++ ld 15,120(1) ++ ld 16,128(1) ++ ld 17,136(1) ++ ld 18,144(1) ++ ld 19,152(1) ++ ld 20,160(1) ++ ld 21,168(1) ++ ld 31,248(1) ++ ++ mtlr 0 ++ addi 1, 1, 1024 ++ blr ++ ++Out_no_poly1305: ++ li 3, 0 ++ blr ++ ++.data ++.align 5 ++rmask: ++.byte 0xff, 0xff, 0xff, 0x0f, 0xfc, 0xff, 0xff, 0x0f, 0xfc, 0xff, 0xff, 0x0f, 0xfc, 0xff, 0xff, 0x0f ++cnum: ++.long 0x03ffffff, 0x00000000, 0x03ffffff, 0x00000000 ++.long 0x1a, 0x00, 0x1a, 0x00 ++.long 0x01000000, 0x01000000, 0x01000000, 0x01000000 ++.long 0x00010203, 0x04050607, 0x10111213, 0x14151617 ++.long 0x08090a0b, 0x0c0d0e0f, 0x18191a1b, 0x1c1d1e1f ++.long 0x05, 0x00, 0x00, 0x00 ++.long 0x02020202, 0x02020202, 0x02020202, 0x02020202 ++.long 0xffffffff, 0xffffffff, 0x00000000, 0x00000000 +Index: libgcrypt-1.10.2/cipher/poly1305.c +=================================================================== +--- libgcrypt-1.10.2.orig/cipher/poly1305.c ++++ libgcrypt-1.10.2/cipher/poly1305.c +@@ -78,11 +78,23 @@ poly1305_blocks (poly1305_context_t *ctx + #endif /* USE_S390X_ASM */ + + ++#ifdef POLY1305_USE_PPC_VEC ++ ++extern unsigned int ++gcry_poly1305_p10le_4blocks(unsigned char *key, const byte *m, size_t len); ++ ++#endif /* POLY1305_USE_PPC_VEC */ ++ ++ + static void poly1305_init (poly1305_context_t *ctx, + const byte key[POLY1305_KEYLEN]) + { + POLY1305_STATE *st = &ctx->state; + ++#ifdef POLY1305_USE_PPC_VEC ++ ctx->use_p10 = (_gcry_get_hw_features () & HWF_PPC_ARCH_3_10) != 0; ++#endif ++ + ctx->leftover = 0; + + st->h[0] = 0; +@@ -533,6 +545,7 @@ _gcry_poly1305_update_burn (poly1305_con + size_t bytes) + { + unsigned int burn = 0; ++ unsigned int nburn; + + /* handle leftover */ + if (ctx->leftover) +@@ -546,15 +559,31 @@ _gcry_poly1305_update_burn (poly1305_con + ctx->leftover += want; + if (ctx->leftover < POLY1305_BLOCKSIZE) + return 0; +- burn = poly1305_blocks (ctx, ctx->buffer, POLY1305_BLOCKSIZE, 1); ++ nburn = poly1305_blocks (ctx, ctx->buffer, POLY1305_BLOCKSIZE, 1); ++ burn = nburn > burn ? nburn : burn; + ctx->leftover = 0; + } + ++#ifdef POLY1305_USE_PPC_VEC ++ /* PPC-P10/little-endian: bulk process multiples of eight blocks */ ++ if (ctx->use_p10 && bytes >= POLY1305_BLOCKSIZE * 8) ++ { ++ size_t nblks = bytes / (POLY1305_BLOCKSIZE * 8); ++ size_t len = nblks * (POLY1305_BLOCKSIZE * 8); ++ POLY1305_STATE *st = &ctx->state; ++ nburn = gcry_poly1305_p10le_4blocks ((unsigned char *) st, m, len); ++ burn = nburn > burn ? nburn : burn; ++ m += len; ++ bytes -= len; ++ } ++#endif /* POLY1305_USE_PPC_VEC */ ++ + /* process full blocks */ + if (bytes >= POLY1305_BLOCKSIZE) + { + size_t nblks = bytes / POLY1305_BLOCKSIZE; +- burn = poly1305_blocks (ctx, m, nblks * POLY1305_BLOCKSIZE, 1); ++ nburn = poly1305_blocks (ctx, m, nblks * POLY1305_BLOCKSIZE, 1); ++ burn = nburn > burn ? nburn : burn; + m += nblks * POLY1305_BLOCKSIZE; + bytes -= nblks * POLY1305_BLOCKSIZE; + } +Index: libgcrypt-1.10.2/configure.ac +=================================================================== +--- libgcrypt-1.10.2.orig/configure.ac ++++ libgcrypt-1.10.2/configure.ac +@@ -2779,6 +2779,11 @@ if test "$found" = "1" ; then + powerpc64le-*-*) + # Build with the ppc8 vector implementation + GCRYPT_ASM_CIPHERS="$GCRYPT_ASM_CIPHERS chacha20-ppc.lo" ++ # Build with the assembly implementation ++ if test "$gcry_cv_gcc_inline_asm_ppc_altivec" = "yes" && ++ test "$gcry_cv_gcc_inline_asm_ppc_arch_3_00" = "yes" ; then ++ GCRYPT_ASM_CIPHERS="$GCRYPT_ASM_CIPHERS chacha20-p10le-8x.lo" ++ fi + ;; + powerpc64-*-*) + # Build with the ppc8 vector implementation +@@ -3117,6 +3122,13 @@ case "${host}" in + s390x-*-*) + GCRYPT_ASM_DIGESTS="$GCRYPT_ASM_DIGESTS poly1305-s390x.lo" + ;; ++ powerpc64le-*-*) ++ # Build with the assembly implementation ++ if test "$gcry_cv_gcc_inline_asm_ppc_altivec" = "yes" && ++ test "$gcry_cv_gcc_inline_asm_ppc_arch_3_00" = "yes" ; then ++ GCRYPT_ASM_DIGESTS="$GCRYPT_ASM_DIGESTS poly1305-p10le.lo" ++ fi ++ ;; + esac + + LIST_MEMBER(scrypt, $enabled_kdfs) diff --git a/libgcrypt-FIPS-SLI-hash-mac.patch b/libgcrypt-FIPS-SLI-hash-mac.patch new file mode 100644 index 0000000..f0f56f2 --- /dev/null +++ b/libgcrypt-FIPS-SLI-hash-mac.patch @@ -0,0 +1,172 @@ +Index: libgcrypt-1.11.0/doc/gcrypt.texi +=================================================================== +--- libgcrypt-1.11.0.orig/doc/gcrypt.texi ++++ libgcrypt-1.11.0/doc/gcrypt.texi +@@ -998,13 +998,21 @@ certification. If the function is approv + @code{GPG_ERR_NO_ERROR} (other restrictions might still apply). + Otherwise @code{GPG_ERR_NOT_SUPPORTED} is returned. + +-@item GCRYCTL_FIPS_SERVICE_INDICATOR_MAC; Arguments: enum gcry_mac_algos ++@item GCRYCTL_FIPS_SERVICE_INDICATOR_HASH; Arguments: enum gcry_md_algos + +-Check if the given MAC is approved under the current FIPS 140-3 +-certification. If the MAC is approved, this function returns +-@code{GPG_ERR_NO_ERROR}. Otherwise @code{GPG_ERR_NOT_SUPPORTED} ++Check if the given HASH is approved under the current FIPS 140-3 ++certification. If the HASH is approved, this function returns ++@code{GPS_ERR_NO_ERROR}. Otherwise @code{GPG_ERR_NOT_SUPPORTED} + is returned. + ++@item GCRYCTL_FIPS_SERVICE_INDICATOR_MAC; Arguments: enum gcry_mac_algos [, unsigned int] ++ ++Check if the given MAC is approved under the current FIPS 140-3 ++certification. The second parameter provides the keylen (if the ++algorithm supports different key sizes). If the MAC is approved, ++this function returns @code{GPS_ERR_NO_ERROR}. Otherwise ++@code{GPG_ERR_NOT_SUPPORTED} is returned. ++ + @item GCRYCTL_FIPS_SERVICE_INDICATOR_MD; Arguments: enum gcry_md_algos + + Check if the given message digest algorithm is approved under the current +Index: libgcrypt-1.11.0/src/fips.c +=================================================================== +--- libgcrypt-1.11.0.orig/src/fips.c ++++ libgcrypt-1.11.0/src/fips.c +@@ -378,31 +378,6 @@ _gcry_fips_indicator_cipher (va_list arg + } + } + +-int +-_gcry_fips_indicator_mac (va_list arg_ptr) +-{ +- enum gcry_mac_algos alg = va_arg (arg_ptr, enum gcry_mac_algos); +- +- switch (alg) +- { +- case GCRY_MAC_CMAC_AES: +- case GCRY_MAC_HMAC_SHA1: +- case GCRY_MAC_HMAC_SHA224: +- case GCRY_MAC_HMAC_SHA256: +- case GCRY_MAC_HMAC_SHA384: +- case GCRY_MAC_HMAC_SHA512: +- case GCRY_MAC_HMAC_SHA512_224: +- case GCRY_MAC_HMAC_SHA512_256: +- case GCRY_MAC_HMAC_SHA3_224: +- case GCRY_MAC_HMAC_SHA3_256: +- case GCRY_MAC_HMAC_SHA3_384: +- case GCRY_MAC_HMAC_SHA3_512: +- return GPG_ERR_NO_ERROR; +- default: +- return GPG_ERR_NOT_SUPPORTED; +- } +-} +- + /* FIPS approved curves, extracted from: + * cipher/ecc-curves.c:curve_aliases[] and domain_parms[]. */ + static const struct +@@ -602,6 +577,62 @@ _gcry_fips_indicator_pk_flags (va_list a + return GPG_ERR_NOT_SUPPORTED; + } + ++int ++_gcry_fips_indicator_hash (va_list arg_ptr) ++{ ++ enum gcry_md_algos alg = va_arg (arg_ptr, enum gcry_md_algos); ++ ++ switch (alg) ++ { ++ case GCRY_MD_SHA1: ++ case GCRY_MD_SHA224: ++ case GCRY_MD_SHA256: ++ case GCRY_MD_SHA384: ++ case GCRY_MD_SHA512: ++ case GCRY_MD_SHA512_224: ++ case GCRY_MD_SHA512_256: ++ case GCRY_MD_SHA3_224: ++ case GCRY_MD_SHA3_256: ++ case GCRY_MD_SHA3_384: ++ case GCRY_MD_SHA3_512: ++ case GCRY_MD_SHAKE128: ++ case GCRY_MD_SHAKE256: ++ return GPG_ERR_NO_ERROR; ++ default: ++ return GPG_ERR_NOT_SUPPORTED; ++ } ++} ++ ++int ++_gcry_fips_indicator_mac (va_list arg_ptr) ++{ ++ enum gcry_mac_algos alg = va_arg (arg_ptr, enum gcry_mac_algos); ++ unsigned int keylen = va_arg (arg_ptr, unsigned int); ++ ++ switch (alg) ++ { ++ case GCRY_MAC_HMAC_SHA1: ++ case GCRY_MAC_HMAC_SHA224: ++ case GCRY_MAC_HMAC_SHA256: ++ case GCRY_MAC_HMAC_SHA384: ++ case GCRY_MAC_HMAC_SHA512: ++ case GCRY_MAC_HMAC_SHA512_224: ++ case GCRY_MAC_HMAC_SHA512_256: ++ case GCRY_MAC_HMAC_SHA3_224: ++ case GCRY_MAC_HMAC_SHA3_256: ++ case GCRY_MAC_HMAC_SHA3_384: ++ case GCRY_MAC_HMAC_SHA3_512: ++ if (keylen >= 112) { ++ return GPG_ERR_NO_ERROR; ++ } ++ case GCRY_MAC_CMAC_AES: ++ if (keylen == 128 || keylen == 192 || keylen == 256) { ++ return GPG_ERR_NO_ERROR; ++ } ++ default: ++ return GPG_ERR_NOT_SUPPORTED; ++ } ++} + + /* This is a test on whether the library is in the error or + operational state. */ +Index: libgcrypt-1.11.0/src/g10lib.h +=================================================================== +--- libgcrypt-1.11.0.orig/src/g10lib.h ++++ libgcrypt-1.11.0/src/g10lib.h +@@ -469,6 +469,7 @@ void _gcry_fips_signal_error (const char + #endif + + int _gcry_fips_indicator_cipher (va_list arg_ptr); ++int _gcry_fips_indicator_hash (va_list arg_ptr); + int _gcry_fips_indicator_mac (va_list arg_ptr); + int _gcry_fips_indicator_md (va_list arg_ptr); + int _gcry_fips_indicator_kdf (va_list arg_ptr); +Index: libgcrypt-1.11.0/src/gcrypt.h.in +=================================================================== +--- libgcrypt-1.11.0.orig/src/gcrypt.h.in ++++ libgcrypt-1.11.0/src/gcrypt.h.in +@@ -336,7 +336,8 @@ enum gcry_ctl_cmds + GCRYCTL_FIPS_SERVICE_INDICATOR_MD = 86, + GCRYCTL_FIPS_SERVICE_INDICATOR_PK_FLAGS = 87, + GCRYCTL_MD_CUSTOMIZE = 88, +- GCRYCTL_FIPS_SERVICE_INDICATOR_PK = 89 ++ GCRYCTL_FIPS_SERVICE_INDICATOR_PK = 89, ++ GCRYCTL_FIPS_SERVICE_INDICATOR_HASH = 90 + }; + + /* Perform various operations defined by CMD. */ +Index: libgcrypt-1.11.0/src/global.c +=================================================================== +--- libgcrypt-1.11.0.orig/src/global.c ++++ libgcrypt-1.11.0/src/global.c +@@ -794,6 +794,12 @@ _gcry_vcontrol (enum gcry_ctl_cmds cmd, + rc = _gcry_fips_indicator_cipher (arg_ptr); + break; + ++ case GCRYCTL_FIPS_SERVICE_INDICATOR_HASH: ++ /* Get FIPS Service Indicator for a given HASH. Returns GPG_ERR_NO_ERROR ++ * if algorithm is allowed or GPG_ERR_NOT_SUPPORTED otherwise */ ++ rc = _gcry_fips_indicator_hash (arg_ptr); ++ break; ++ + case GCRYCTL_FIPS_SERVICE_INDICATOR_MAC: + /* Get FIPS Service Indicator for a given message authentication code. + * Returns GPG_ERR_NO_ERROR if algorithm is allowed or diff --git a/libgcrypt-FIPS-SLI-kdf-leylength.patch b/libgcrypt-FIPS-SLI-kdf-leylength.patch new file mode 100644 index 0000000..d3693ac --- /dev/null +++ b/libgcrypt-FIPS-SLI-kdf-leylength.patch @@ -0,0 +1,60 @@ +Index: libgcrypt-1.11.0/src/fips.c +=================================================================== +--- libgcrypt-1.11.0.orig/src/fips.c ++++ libgcrypt-1.11.0/src/fips.c +@@ -523,10 +523,15 @@ int + _gcry_fips_indicator_kdf (va_list arg_ptr) + { + enum gcry_kdf_algos alg = va_arg (arg_ptr, enum gcry_kdf_algos); ++ unsigned int keylen = 0; + + switch (alg) + { + case GCRY_KDF_PBKDF2: ++ keylen = va_arg (arg_ptr, unsigned int); ++ if (keylen < 112) { ++ return GPG_ERR_NOT_SUPPORTED; ++ } + return GPG_ERR_NO_ERROR; + default: + return GPG_ERR_NOT_SUPPORTED; +Index: libgcrypt-1.11.0/doc/gcrypt.texi +=================================================================== +--- libgcrypt-1.11.0.orig/doc/gcrypt.texi ++++ libgcrypt-1.11.0/doc/gcrypt.texi +@@ -983,12 +983,13 @@ is approved under the current FIPS 140-3 + combination is approved, this function returns @code{GPG_ERR_NO_ERROR}. + Otherwise @code{GPG_ERR_NOT_SUPPORTED} is returned. + +-@item GCRYCTL_FIPS_SERVICE_INDICATOR_KDF; Arguments: enum gcry_kdf_algos ++@item GCRYCTL_FIPS_SERVICE_INDICATOR_KDF; Arguments: enum gcry_kdf_algos [, unsigned int] + + Check if the given KDF is approved under the current FIPS 140-3 +-certification. If the KDF is approved, this function returns +-@code{GPG_ERR_NO_ERROR}. Otherwise @code{GPG_ERR_NOT_SUPPORTED} +-is returned. ++certification. The second parameter provides the keylength in bits. ++Keylength values of less that 112 bits are considered non-approved. ++If the KDF is approved, this function returns @code{GPG_ERR_NO_ERROR}. ++Otherwise @code{GPG_ERR_NOT_SUPPORTED} is returned. + + @item GCRYCTL_FIPS_SERVICE_INDICATOR_FUNCTION; Arguments: const char * + +Index: libgcrypt-1.11.0/tests/t-kdf.c +=================================================================== +--- libgcrypt-1.11.0.orig/tests/t-kdf.c ++++ libgcrypt-1.11.0/tests/t-kdf.c +@@ -1889,7 +1889,12 @@ check_fips_indicators (void) + for (i = 0; i < sizeof(kdf_algos) / sizeof(*kdf_algos); i++) + { + int is_fips_kdf_algo = 0; +- gcry_error_t err = gcry_control (GCRYCTL_FIPS_SERVICE_INDICATOR_KDF, kdf_algos[i]); ++ gcry_error_t err; ++ // On SUSE/openSUSE builds PBKDF2 with keysize < 112 is not allowed ++ if (kdf_algos[i] == GCRY_KDF_PBKDF2) ++ err = gcry_control (GCRYCTL_FIPS_SERVICE_INDICATOR_KDF, kdf_algos[i], 112); ++ else ++ err = gcry_control (GCRYCTL_FIPS_SERVICE_INDICATOR_KDF, kdf_algos[i]); + + if (verbose) + fprintf (stderr, "checking FIPS indicator for KDF %d: %s\n", diff --git a/libgcrypt-FIPS-SLI-pk.patch b/libgcrypt-FIPS-SLI-pk.patch new file mode 100644 index 0000000..304fd37 --- /dev/null +++ b/libgcrypt-FIPS-SLI-pk.patch @@ -0,0 +1,177 @@ +Index: libgcrypt-1.11.0/src/fips.c +=================================================================== +--- libgcrypt-1.11.0.orig/src/fips.c ++++ libgcrypt-1.11.0/src/fips.c +@@ -38,6 +38,7 @@ + + #include "g10lib.h" + #include "cipher-proto.h" ++#include "cipher.h" + #include "../random/random.h" + + /* The states of the finite state machine used in fips mode. */ +@@ -400,6 +401,94 @@ _gcry_fips_indicator_mac (va_list arg_pt + default: + return GPG_ERR_NOT_SUPPORTED; + } ++} ++ ++/* FIPS approved curves, extracted from: ++ * cipher/ecc-curves.c:curve_aliases[] and domain_parms[]. */ ++static const struct ++{ ++ const char *name; /* Our name. */ ++ const char *other; /* Other name. */ ++} fips_approved_curve[] = ++ { ++ /* "NIST P-192" is non-approved if FIPS 140-3 */ ++ /* { "NIST P-192", "1.2.840.10045.3.1.1" }, /\* X9.62 OID *\/ */ ++ /* { "NIST P-192", "prime192v1" }, /\* X9.62 name. *\/ */ ++ /* { "NIST P-192", "secp192r1" }, /\* SECP name. *\/ */ ++ /* { "NIST P-192", "nistp192" }, /\* rfc5656. *\/ */ ++ ++ { "NIST P-224", "secp224r1" }, ++ { "NIST P-224", "1.3.132.0.33" }, /* SECP OID. */ ++ { "NIST P-224", "nistp224" }, /* rfc5656. */ ++ ++ { "NIST P-256", "1.2.840.10045.3.1.7" }, /* From NIST SP 800-78-1. */ ++ { "NIST P-256", "prime256v1" }, ++ { "NIST P-256", "secp256r1" }, ++ { "NIST P-256", "nistp256" }, /* rfc5656. */ ++ ++ { "NIST P-384", "secp384r1" }, ++ { "NIST P-384", "1.3.132.0.34" }, ++ { "NIST P-384", "nistp384" }, /* rfc5656. */ ++ ++ { "NIST P-521", "secp521r1" }, ++ { "NIST P-521", "1.3.132.0.35" }, ++ { "NIST P-521", "nistp521" }, /* rfc5656. */ ++ { NULL, NULL} ++ }; ++ ++enum pk_operation convert_from_pk_usage(unsigned int pk_usage) ++{ ++ switch (pk_usage) ++ { ++ case GCRY_PK_USAGE_SIGN: ++ return PUBKEY_OP_SIGN; ++ case GCRY_PK_USAGE_ENCR: ++ return PUBKEY_OP_ENCRYPT; ++ default: ++ return PUBKEY_OP_DECRYPT; ++ } ++} ++ ++int ++_gcry_fips_indicator_pk (va_list arg_ptr) ++{ ++ enum gcry_pk_algos alg = va_arg (arg_ptr, enum gcry_pk_algos); ++ enum pk_operation oper; ++ unsigned int keylen; ++ const char *curve_name; ++ ++ switch (alg) ++ { ++ case GCRY_PK_RSA: ++ case GCRY_PK_RSA_E: ++ case GCRY_PK_RSA_S: ++ oper = convert_from_pk_usage(va_arg (arg_ptr, unsigned int)); ++ switch (oper) ++ { ++ case PUBKEY_OP_ENCRYPT: ++ case PUBKEY_OP_DECRYPT: ++ return GPG_ERR_NOT_SUPPORTED; ++ default: ++ keylen = va_arg (arg_ptr, unsigned int); ++ if (keylen < 2048) ++ return GPG_ERR_NOT_SUPPORTED; ++ return GPG_ERR_NO_ERROR; ++ } ++ case GCRY_PK_ECC: ++ case GCRY_PK_ECDH: ++ case GCRY_PK_ECDSA: ++ curve_name = va_arg (arg_ptr, const char *); ++ for (int idx = 0; fips_approved_curve[idx].name; ++idx) ++ { ++ /* Check for the usual name and an alias. */ ++ if (!strcmp (curve_name, fips_approved_curve[idx].name) || ++ !strcmp (curve_name, fips_approved_curve[idx].other)) ++ return GPG_ERR_NO_ERROR; ++ } ++ return GPG_ERR_NOT_SUPPORTED; ++ default: ++ return GPG_ERR_NOT_SUPPORTED; ++ } + } + + int +Index: libgcrypt-1.11.0/src/gcrypt.h.in +=================================================================== +--- libgcrypt-1.11.0.orig/src/gcrypt.h.in ++++ libgcrypt-1.11.0/src/gcrypt.h.in +@@ -335,7 +335,8 @@ enum gcry_ctl_cmds + GCRYCTL_FIPS_SERVICE_INDICATOR_MAC = 85, + GCRYCTL_FIPS_SERVICE_INDICATOR_MD = 86, + GCRYCTL_FIPS_SERVICE_INDICATOR_PK_FLAGS = 87, +- GCRYCTL_MD_CUSTOMIZE = 88 ++ GCRYCTL_MD_CUSTOMIZE = 88, ++ GCRYCTL_FIPS_SERVICE_INDICATOR_PK = 89 + }; + + /* Perform various operations defined by CMD. */ +Index: libgcrypt-1.11.0/doc/gcrypt.texi +=================================================================== +--- libgcrypt-1.11.0.orig/doc/gcrypt.texi ++++ libgcrypt-1.11.0/doc/gcrypt.texi +@@ -1010,6 +1010,19 @@ Check if the given message digest algori + FIPS 140-3 certification. If the algorithm is approved, this function returns + @code{GPG_ERR_NO_ERROR}. Otherwise @code{GPG_ERR_NOT_SUPPORTED} is returned. + ++@item GCRYCTL_FIPS_SERVICE_INDICATOR_PK; Arguments: enum gcry_pk_algos [, constantsGCRY_PK_USAGE_ENCR or GCRY_PK_USAGE_SIGN, unsigned int (only for GCRY_PK_RSA)] [, const char * (only for GCRY_PK_ECC, GCRY_PK_ECDH or GCRY_PK_ECDSA)] ++ ++Check if the given asymmetric cipher is approved under the current ++FIPS 140-3 certification. For GCRY_PK_RSA, two additional parameter ++are required: first describes the purpose of the algorithm through one ++of the constants (GCRY_PK_USAGE_ENCR for encryption or decryption ++operations; GCRY_PK_USAGE_SIGN for sign or verify operations). Second ++one is the key length. For GCRY_PK_ECC, GCRY_PK_ECDH and ++GCRY_PK_ECDSA, only a single parameter is needed: the curve name or ++its alias as @code{const char *}. If the combination is approved, this ++function returns @code{GPG_ERR_NO_ERROR}. Otherwise ++@code{GPG_ERR_NOT_SUPPORTED} is returned. ++ + @item GCRYCTL_FIPS_SERVICE_INDICATOR_PK_FLAGS; Arguments: const char * + + Check if the given public key operation flag or s-expression object name is +Index: libgcrypt-1.11.0/src/g10lib.h +=================================================================== +--- libgcrypt-1.11.0.orig/src/g10lib.h ++++ libgcrypt-1.11.0/src/g10lib.h +@@ -473,6 +473,7 @@ int _gcry_fips_indicator_mac (va_list ar + int _gcry_fips_indicator_md (va_list arg_ptr); + int _gcry_fips_indicator_kdf (va_list arg_ptr); + int _gcry_fips_indicator_function (va_list arg_ptr); ++int _gcry_fips_indicator_pk (va_list arg_ptr); + int _gcry_fips_indicator_pk_flags (va_list arg_ptr); + + int _gcry_fips_is_operational (void); +Index: libgcrypt-1.11.0/src/global.c +=================================================================== +--- libgcrypt-1.11.0.orig/src/global.c ++++ libgcrypt-1.11.0/src/global.c +@@ -828,6 +828,15 @@ _gcry_vcontrol (enum gcry_ctl_cmds cmd, + rc = _gcry_fips_indicator_pk_flags (arg_ptr); + break; + ++ case GCRYCTL_FIPS_SERVICE_INDICATOR_PK: ++ /* Get FIPS Service Indicator for a given asymmetric algorithm. For ++ * GCRY_PK_RSA, an additional parameter for the operation mode is ++ * required. For ECC, ECDH and ECDSA, the additional parameter is the ++ * curve name or its alias. Returns GPG_ERR_NO_ERROR if the ++ * algorithm is allowed or GPG_ERR_NOT_SUPPORTED otherwise. */ ++ rc = _gcry_fips_indicator_pk (arg_ptr); ++ break; ++ + case PRIV_CTL_INIT_EXTRNG_TEST: /* Init external random test. */ + rc = GPG_ERR_NOT_SUPPORTED; + break; diff --git a/libgcrypt-FIPS-jitter-errorcodes.patch b/libgcrypt-FIPS-jitter-errorcodes.patch new file mode 100644 index 0000000..d6d314e --- /dev/null +++ b/libgcrypt-FIPS-jitter-errorcodes.patch @@ -0,0 +1,16 @@ +Index: libgcrypt-1.10.3/random/rndjent.c +=================================================================== +--- libgcrypt-1.10.3.orig/random/rndjent.c ++++ libgcrypt-1.10.3/random/rndjent.c +@@ -319,7 +319,10 @@ _gcry_rndjent_poll (void (*add)(const vo + jent_rng_totalcalls++; + rc = jent_read_entropy_safe (&jent_rng_collector, buffer, n); + if (rc < 0) +- break; ++ { ++ fips_signal_error ("jitter entropy failed"); ++ break; ++ } + /* We need to hash the output to conform to the BSI + * NTG.1 specs. */ + _gcry_md_hash_buffer (GCRY_MD_SHA256, buffer, buffer, rc); diff --git a/libgcrypt-FIPS-jitter-standalone.patch b/libgcrypt-FIPS-jitter-standalone.patch new file mode 100644 index 0000000..4f931c3 --- /dev/null +++ b/libgcrypt-FIPS-jitter-standalone.patch @@ -0,0 +1,183 @@ +Index: libgcrypt-1.10.3/random/Makefile.am +=================================================================== +--- libgcrypt-1.10.3.orig/random/Makefile.am ++++ libgcrypt-1.10.3/random/Makefile.am +@@ -21,7 +21,7 @@ + # Need to include ../src in addition to top_srcdir because gcrypt.h is + # a built header. + AM_CPPFLAGS = -I../src -I$(top_srcdir)/src +-AM_CFLAGS = $(GPG_ERROR_CFLAGS) ++AM_CFLAGS = $(GPG_ERROR_CFLAGS) -ljitterentropy + + noinst_LTLIBRARIES = librandom.la + +@@ -45,14 +45,7 @@ rndoldlinux.c \ + rndegd.c \ + rndunix.c \ + rndw32.c \ +-rndw32ce.c \ +-jitterentropy-gcd.c jitterentropy-gcd.h \ +-jitterentropy-health.c jitterentropy-health.h \ +-jitterentropy-noise.c jitterentropy-noise.h \ +-jitterentropy-sha3.c jitterentropy-sha3.h \ +-jitterentropy-timer.c jitterentropy-timer.h \ +-jitterentropy-base.h \ +-jitterentropy-base.c jitterentropy.h jitterentropy-base-user.h ++rndw32ce.c + + # The rndjent module needs to be compiled without optimization. */ + if ENABLE_O_FLAG_MUNGING +@@ -61,20 +54,8 @@ else + o_flag_munging = cat + endif + +-rndjent.o: $(srcdir)/rndjent.c jitterentropy-base-user.h \ +- $(srcdir)/jitterentropy-gcd.c $(srcdir)/jitterentropy-gcd.h \ +- $(srcdir)/jitterentropy-health.c $(srcdir)/jitterentropy-health.h \ +- $(srcdir)/jitterentropy-noise.c $(srcdir)/jitterentropy-noise.h \ +- $(srcdir)/jitterentropy-sha3.c $(srcdir)/jitterentropy-sha3.h \ +- $(srcdir)/jitterentropy-timer.c $(srcdir)/jitterentropy-timer.h \ +- $(srcdir)/jitterentropy-base.c $(srcdir)/jitterentropy.h ++rndjent.o: $(srcdir)/rndjent.c + `echo $(COMPILE) -c $(srcdir)/rndjent.c | $(o_flag_munging) ` + +-rndjent.lo: $(srcdir)/rndjent.c jitterentropy-base-user.h \ +- $(srcdir)/jitterentropy-gcd.c $(srcdir)/jitterentropy-gcd.h \ +- $(srcdir)/jitterentropy-health.c $(srcdir)/jitterentropy-health.h \ +- $(srcdir)/jitterentropy-noise.c $(srcdir)/jitterentropy-noise.h \ +- $(srcdir)/jitterentropy-sha3.c $(srcdir)/jitterentropy-sha3.h \ +- $(srcdir)/jitterentropy-timer.c $(srcdir)/jitterentropy-timer.h \ +- $(srcdir)/jitterentropy-base.c $(srcdir)/jitterentropy.h ++rndjent.lo: $(srcdir)/rndjent.c + `echo $(LTCOMPILE) -c $(srcdir)/rndjent.c | $(o_flag_munging) ` +Index: libgcrypt-1.10.3/random/rndjent.c +=================================================================== +--- libgcrypt-1.10.3.orig/random/rndjent.c ++++ libgcrypt-1.10.3/random/rndjent.c +@@ -94,17 +94,12 @@ + * jitterentropy-user-base.h file. */ + + /* Tell jitterentropy* that all functions shall be static. */ +-#define JENT_PRIVATE_COMPILE 1 ++#undef JENT_PRIVATE_COMPILE + +-#include "jitterentropy-base.c" + #ifdef JENT_CONF_ENABLE_INTERNAL_TIMER + #include + #endif /* JENT_CONF_ENABLE_INTERNAL_TIMER */ +-#include "jitterentropy-gcd.c" +-#include "jitterentropy-health.c" +-#include "jitterentropy-noise.c" +-#include "jitterentropy-sha3.c" +-#include "jitterentropy-timer.c" ++#include + + /* This is the lock we use to serialize access to this RNG. The extra + * integer variable is only used to check the locking state; that is, +Index: libgcrypt-1.10.3/random/Makefile.in +=================================================================== +--- libgcrypt-1.10.3.orig/random/Makefile.in ++++ libgcrypt-1.10.3/random/Makefile.in +@@ -147,12 +147,7 @@ am__v_at_1 = + DEFAULT_INCLUDES = -I.@am__isrc@ -I$(top_builddir) + depcomp = $(SHELL) $(top_srcdir)/build-aux/depcomp + am__maybe_remake_depfiles = depfiles +-am__depfiles_remade = ./$(DEPDIR)/jitterentropy-base.Plo \ +- ./$(DEPDIR)/jitterentropy-gcd.Plo \ +- ./$(DEPDIR)/jitterentropy-health.Plo \ +- ./$(DEPDIR)/jitterentropy-noise.Plo \ +- ./$(DEPDIR)/jitterentropy-sha3.Plo \ +- ./$(DEPDIR)/jitterentropy-timer.Plo \ ++am__depfiles_remade = \ + ./$(DEPDIR)/random-csprng.Plo ./$(DEPDIR)/random-drbg.Plo \ + ./$(DEPDIR)/random-system.Plo ./$(DEPDIR)/random.Plo \ + ./$(DEPDIR)/rndegd.Plo ./$(DEPDIR)/rndgetentropy.Plo \ +@@ -378,7 +373,7 @@ top_srcdir = @top_srcdir@ + # Need to include ../src in addition to top_srcdir because gcrypt.h is + # a built header. + AM_CPPFLAGS = -I../src -I$(top_srcdir)/src +-AM_CFLAGS = $(GPG_ERROR_CFLAGS) ++AM_CFLAGS = $(GPG_ERROR_CFLAGS) -ljitterentropy + noinst_LTLIBRARIES = librandom.la + GCRYPT_MODULES = @GCRYPT_RANDOM@ + librandom_la_DEPENDENCIES = $(GCRYPT_MODULES) +@@ -398,14 +393,7 @@ rndoldlinux.c \ + rndegd.c \ + rndunix.c \ + rndw32.c \ +-rndw32ce.c \ +-jitterentropy-gcd.c jitterentropy-gcd.h \ +-jitterentropy-health.c jitterentropy-health.h \ +-jitterentropy-noise.c jitterentropy-noise.h \ +-jitterentropy-sha3.c jitterentropy-sha3.h \ +-jitterentropy-timer.c jitterentropy-timer.h \ +-jitterentropy-base.h \ +-jitterentropy-base.c jitterentropy.h jitterentropy-base-user.h ++rndw32ce.c + + @ENABLE_O_FLAG_MUNGING_FALSE@o_flag_munging = cat + +@@ -465,12 +453,6 @@ mostlyclean-compile: + distclean-compile: + -rm -f *.tab.c + +-@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/jitterentropy-base.Plo@am__quote@ # am--include-marker +-@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/jitterentropy-gcd.Plo@am__quote@ # am--include-marker +-@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/jitterentropy-health.Plo@am__quote@ # am--include-marker +-@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/jitterentropy-noise.Plo@am__quote@ # am--include-marker +-@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/jitterentropy-sha3.Plo@am__quote@ # am--include-marker +-@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/jitterentropy-timer.Plo@am__quote@ # am--include-marker + @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/random-csprng.Plo@am__quote@ # am--include-marker + @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/random-drbg.Plo@am__quote@ # am--include-marker + @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/random-system.Plo@am__quote@ # am--include-marker +@@ -641,12 +623,6 @@ clean-am: clean-generic clean-libtool cl + mostlyclean-am + + distclean: distclean-am +- -rm -f ./$(DEPDIR)/jitterentropy-base.Plo +- -rm -f ./$(DEPDIR)/jitterentropy-gcd.Plo +- -rm -f ./$(DEPDIR)/jitterentropy-health.Plo +- -rm -f ./$(DEPDIR)/jitterentropy-noise.Plo +- -rm -f ./$(DEPDIR)/jitterentropy-sha3.Plo +- -rm -f ./$(DEPDIR)/jitterentropy-timer.Plo + -rm -f ./$(DEPDIR)/random-csprng.Plo + -rm -f ./$(DEPDIR)/random-drbg.Plo + -rm -f ./$(DEPDIR)/random-system.Plo +@@ -704,12 +680,6 @@ install-ps-am: + installcheck-am: + + maintainer-clean: maintainer-clean-am +- -rm -f ./$(DEPDIR)/jitterentropy-base.Plo +- -rm -f ./$(DEPDIR)/jitterentropy-gcd.Plo +- -rm -f ./$(DEPDIR)/jitterentropy-health.Plo +- -rm -f ./$(DEPDIR)/jitterentropy-noise.Plo +- -rm -f ./$(DEPDIR)/jitterentropy-sha3.Plo +- -rm -f ./$(DEPDIR)/jitterentropy-timer.Plo + -rm -f ./$(DEPDIR)/random-csprng.Plo + -rm -f ./$(DEPDIR)/random-drbg.Plo + -rm -f ./$(DEPDIR)/random-system.Plo +@@ -759,22 +729,10 @@ uninstall-am: + .PRECIOUS: Makefile + + +-rndjent.o: $(srcdir)/rndjent.c jitterentropy-base-user.h \ +- $(srcdir)/jitterentropy-gcd.c $(srcdir)/jitterentropy-gcd.h \ +- $(srcdir)/jitterentropy-health.c $(srcdir)/jitterentropy-health.h \ +- $(srcdir)/jitterentropy-noise.c $(srcdir)/jitterentropy-noise.h \ +- $(srcdir)/jitterentropy-sha3.c $(srcdir)/jitterentropy-sha3.h \ +- $(srcdir)/jitterentropy-timer.c $(srcdir)/jitterentropy-timer.h \ +- $(srcdir)/jitterentropy-base.c $(srcdir)/jitterentropy.h ++rndjent.o: $(srcdir)/rndjent.c + `echo $(COMPILE) -c $(srcdir)/rndjent.c | $(o_flag_munging) ` + +-rndjent.lo: $(srcdir)/rndjent.c jitterentropy-base-user.h \ +- $(srcdir)/jitterentropy-gcd.c $(srcdir)/jitterentropy-gcd.h \ +- $(srcdir)/jitterentropy-health.c $(srcdir)/jitterentropy-health.h \ +- $(srcdir)/jitterentropy-noise.c $(srcdir)/jitterentropy-noise.h \ +- $(srcdir)/jitterentropy-sha3.c $(srcdir)/jitterentropy-sha3.h \ +- $(srcdir)/jitterentropy-timer.c $(srcdir)/jitterentropy-timer.h \ +- $(srcdir)/jitterentropy-base.c $(srcdir)/jitterentropy.h ++rndjent.lo: $(srcdir)/rndjent.c + `echo $(LTCOMPILE) -c $(srcdir)/rndjent.c | $(o_flag_munging) ` + + # Tell versions [3.59,3.63) of GNU make to not export all variables. diff --git a/libgcrypt-FIPS-jitter-whole-entropy.patch b/libgcrypt-FIPS-jitter-whole-entropy.patch new file mode 100644 index 0000000..6c16472 --- /dev/null +++ b/libgcrypt-FIPS-jitter-whole-entropy.patch @@ -0,0 +1,41 @@ +Index: libgcrypt-1.10.3/random/rndgetentropy.c +=================================================================== +--- libgcrypt-1.10.3.orig/random/rndgetentropy.c ++++ libgcrypt-1.10.3/random/rndgetentropy.c +@@ -53,16 +53,30 @@ _gcry_rndgetentropy_gather_random (void + + /* When using a blocking random generator try to get some entropy + * from the jitter based RNG. In this case we take up to 50% of the +- * remaining requested bytes. */ ++ * remaining requested bytes. In FIPS mode, we get all the entropy ++ * from the jitter RNG. */ + if (level >= GCRY_VERY_STRONG_RANDOM) + { + size_t n; + +- n = _gcry_rndjent_poll (add, origin, length/2); +- if (n > length/2) +- n = length/2; +- if (length > 1) +- length -= n; ++ /* In FIPS mode, use the whole length of the entropy buffer from ++ * Jitter RNG */ ++ if (fips_mode ()) ++ { ++ n = _gcry_rndjent_poll (add, origin, length); ++ if (n != length) ++ fips_signal_error ("jitter entropy failed"); ++ else ++ length = 0; ++ } ++ else ++ { ++ n = _gcry_rndjent_poll (add, origin, length/2); ++ if (n > length/2) ++ n = length/2; ++ if (length > 1) ++ length -= n; ++ } + } + + /* Enter the loop. */ diff --git a/libgcrypt-FIPS-rndjent_poll.patch b/libgcrypt-FIPS-rndjent_poll.patch new file mode 100644 index 0000000..f837842 --- /dev/null +++ b/libgcrypt-FIPS-rndjent_poll.patch @@ -0,0 +1,114 @@ +Index: libgcrypt-1.10.0/random/rndoldlinux.c +=================================================================== +--- libgcrypt-1.10.0.orig/random/rndoldlinux.c ++++ libgcrypt-1.10.0/random/rndoldlinux.c +@@ -132,7 +132,7 @@ _gcry_rndoldlinux_gather_random (void (* + volatile pid_t apid; + int fd; + int n; +- byte buffer[768]; ++ byte buffer[256]; + size_t n_hw; + size_t want = length; + size_t last_so_far = 0; +@@ -187,26 +187,43 @@ _gcry_rndoldlinux_gather_random (void (* + my_pid = apid; + } + ++ if (fips_mode()) ++ { ++ if (level >= GCRY_VERY_STRONG_RANDOM) ++ { ++ size_t n; + +- /* First read from a hardware source. Note that _gcry_rndhw_poll_slow lets +- it account only for up to 50% (or 25% for RDRAND) of the requested +- bytes. */ +- n_hw = _gcry_rndhw_poll_slow (add, origin, length); +- if (length > 1) +- length -= n_hw; +- +- /* When using a blocking random generator try to get some entropy +- * from the jitter based RNG. In this case we take up to 50% of the +- * remaining requested bytes. */ +- if (level >= GCRY_VERY_STRONG_RANDOM) +- { +- n_hw = _gcry_rndjent_poll (add, origin, length/2); +- if (n_hw > length/2) +- n_hw = length/2; ++ n = _gcry_rndjent_poll (add, origin, length); ++ if (n == 0) ++ log_fatal ("unexpected error from rndjent: %s\n", ++ strerror (errno)); ++ if (n > length) ++ n = length; ++ if (length > 1) ++ length -= n; ++ } ++ } ++ else ++ { ++ /* First read from a hardware source. Note that _gcry_rndhw_poll_slow lets ++ it account only for up to 50% (or 25% for RDRAND) of the requested ++ bytes. */ ++ n_hw = _gcry_rndhw_poll_slow (add, origin, length); + if (length > 1) + length -= n_hw; +- } + ++ /* When using a blocking random generator try to get some entropy ++ * from the jitter based RNG. In this case we take up to 50% of the ++ * remaining requested bytes. */ ++ if (level >= GCRY_VERY_STRONG_RANDOM) ++ { ++ n_hw = _gcry_rndjent_poll (add, origin, length/2); ++ if (n_hw > length/2) ++ n_hw = length/2; ++ if (length > 1) ++ length -= n_hw; ++ } ++ } + + /* Open the requested device. The first time a device is to be + opened we fail with a fatal error if the device does not exists. +@@ -262,8 +279,6 @@ _gcry_rndoldlinux_gather_random (void (* + do + { + nbytes = length < sizeof(buffer)? length : sizeof(buffer); +- if (nbytes > 256) +- nbytes = 256; + _gcry_pre_syscall (); + ret = getentropy (buffer, nbytes); + _gcry_post_syscall (); +Index: libgcrypt-1.10.0/random/rndjent.c +=================================================================== +--- libgcrypt-1.10.0.orig/random/rndjent.c ++++ libgcrypt-1.10.0/random/rndjent.c +@@ -279,13 +279,24 @@ _gcry_rndjent_poll (void (*add)(const vo + if (!jent_rng_is_initialized) + { + /* Auto-initialize. */ +- jent_rng_is_initialized = 1; + jent_entropy_collector_free (jent_rng_collector); + jent_rng_collector = NULL; + if ( !(_gcry_random_read_conf () & RANDOM_CONF_DISABLE_JENT)) + { +- if (!jent_entropy_init ()) +- jent_rng_collector = jent_entropy_collector_alloc (1, 0); ++ if (!jent_entropy_init_ex (1, 0)) ++ { ++ jent_rng_collector = jent_entropy_collector_alloc (1, 0); ++ jent_rng_is_initialized = 1; ++ } ++ } ++ } ++ ++ if (!jent_rng_collector) ++ { ++ if (!jent_entropy_init_ex (1, 0)) ++ { ++ jent_rng_collector = jent_entropy_collector_alloc (1, 0); ++ jent_rng_is_initialized = 1; + } + } + diff --git a/libgcrypt-Fix-the-previous-change.patch b/libgcrypt-Fix-the-previous-change.patch new file mode 100644 index 0000000..4735528 --- /dev/null +++ b/libgcrypt-Fix-the-previous-change.patch @@ -0,0 +1,45 @@ +From b4eb23dc01a40e13d542fbfc5169dffa7fae5677 Mon Sep 17 00:00:00 2001 +From: NIIBE Yutaka +Date: Thu, 19 Dec 2024 14:16:02 +0900 +Subject: [PATCH 13/19] Fix the previous change. +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* cipher/pubkey.c (_gcry_pk_sign_md): Fix memory leak. +(_gcry_pk_verify_md): Likewise. + +-- + +GnuPG-bug-id: 7338 +Signed-off-by: NIIBE Yutaka +Signed-off-by: Lucas Mülling +--- + cipher/pubkey.c | 4 ++-- + 1 file changed, 2 insertions(+), 2 deletions(-) + +diff --git a/cipher/pubkey.c b/cipher/pubkey.c +index 11bf1ec9..4d7743cc 100644 +--- a/cipher/pubkey.c ++++ b/cipher/pubkey.c +@@ -626,7 +626,7 @@ _gcry_pk_sign_md (gcry_sexp_t *r_sig, const char *tmpl, gcry_md_hd_t hd_orig, + else if (!spec->flags.fips && fips_mode ()) + { + if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) +- return GPG_ERR_PUBKEY_ALGO; ++ rc = GPG_ERR_PUBKEY_ALGO; + else + fips_service_indicator_mark_non_compliant (); + } +@@ -708,7 +708,7 @@ _gcry_pk_verify_md (gcry_sexp_t s_sig, const char *tmpl, gcry_md_hd_t hd_orig, + else if (!spec->flags.fips && fips_mode ()) + { + if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) +- return GPG_ERR_PUBKEY_ALGO; ++ rc = GPG_ERR_PUBKEY_ALGO; + else + fips_service_indicator_mark_non_compliant (); + } +-- +2.49.0 + diff --git a/libgcrypt-build-Improve-__thread-specifier-check.patch b/libgcrypt-build-Improve-__thread-specifier-check.patch new file mode 100644 index 0000000..9167adc --- /dev/null +++ b/libgcrypt-build-Improve-__thread-specifier-check.patch @@ -0,0 +1,41 @@ +From 42e8858566e32080aaf818b168f34c698a9ef084 Mon Sep 17 00:00:00 2001 +From: NIIBE Yutaka +Date: Thu, 9 Jan 2025 10:15:50 +0900 +Subject: [PATCH 1/1] build: Improve __thread specifier check. +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* configure.ac (AC_COMPILE_IFELSE __thread): Move the declaration to +global, referring the variable with (void) in main to avoid an error +buidling with -Werror=unused-variable. Don't need to include +stdlib.h. + +-- + +Reported-by: Lucas Mulling +Signed-off-by: NIIBE Yutaka +Signed-off-by: Lucas Mülling +--- + configure.ac | 5 +++-- + 1 file changed, 3 insertions(+), 2 deletions(-) + +diff --git a/configure.ac b/configure.ac +index d708f89a..f38e20c5 100644 +--- a/configure.ac ++++ b/configure.ac +@@ -1495,8 +1495,9 @@ fi + AC_CACHE_CHECK([whether compiler supports '__thread' storage class specifier], + [gcry_cv_gcc_storage_class__thread], + [gcry_cv_gcc_storage_class__thread=no +- AC_COMPILE_IFELSE([AC_LANG_PROGRAM([#include ], +- [static __thread int bar;] ++ AC_COMPILE_IFELSE([AC_LANG_PROGRAM( ++ [[static __thread int bar;]], ++ [[(void)bar;]] + )], + [gcry_cv_gcc_storage_class__thread=yes])]) + if test "$gcry_cv_gcc_storage_class__thread" = "yes" ; then +-- +2.49.0 + diff --git a/libgcrypt-cipher-Add-KAT-for-non-rfc6979-ECDSA-with-fixed-k.patch b/libgcrypt-cipher-Add-KAT-for-non-rfc6979-ECDSA-with-fixed-k.patch new file mode 100644 index 0000000..ff9ae28 --- /dev/null +++ b/libgcrypt-cipher-Add-KAT-for-non-rfc6979-ECDSA-with-fixed-k.patch @@ -0,0 +1,94 @@ +From be57179f42f8a7cb64f72f73ccea753400573b4f Mon Sep 17 00:00:00 2001 +From: Lucas Mulling via Gcrypt-devel +Date: Wed, 26 Feb 2025 12:29:53 -0300 +Subject: [PATCH 02/14] cipher: Add KAT for non-rfc6979 ECDSA with fixed k +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* cipher/ecc.c (run_selftests): Implement KAT for non-deterministic +ECDSA. +* cipher/ecc. (rfc6979_ecdsa_sample_data, rfc6979_ecdsa_sample_data_bad, +rfc6979_ecdsa_data_tmpl): New. + +Signed-off-by: Lucas Mulling +Signed-off-by: Lucas Mülling +--- + cipher/ecc.c | 40 +++++++++++++++++++++++++++++++++++++--- + 1 file changed, 37 insertions(+), 3 deletions(-) + +diff --git a/cipher/ecc.c b/cipher/ecc.c +index 525523ed..d331a014 100644 +--- a/cipher/ecc.c ++++ b/cipher/ecc.c +@@ -93,23 +93,47 @@ static const char ecdsa_sample_secret_key_secp256[] = + /**/ "7903FE1008B8BC99A41AE9E95628BC64F2F1B20C2D7E9F5177A3C294D4462299#)))"; + + /* Sample data from RFC 6979 section A.2.5, hash is of message "sample" */ +-static const char ecdsa_sample_data[] = ++static const char rfc6979_ecdsa_sample_data[] = + "(data (flags rfc6979 prehash)" + " (hash-algo sha256)" + " (value 6:sample))"; + +-static const char ecdsa_sample_data_bad[] = ++static const char rfc6979_ecdsa_sample_data_bad[] = + "(data (flags rfc6979)" + " (hash sha256 #bf2bdbe1aa9b6ec1e2ade1d694f41fc71a831d0268e98915" + /**/ "62113d8a62add1bf#))"; + ++static const char *rfc6979_ecdsa_data_tmpl = ++ "(data (flags rfc6979)" ++ " (hash %s %b))"; ++ ++/* ++ * Sample data from RFC 6979 section A.2.5, with fixed k, ++ * hash is of message "sample". ++ */ ++static const char ecdsa_sample_data[] = ++ "(data (flags raw prehash)" ++ " (label #A6E3C57DD01ABE90086538398355DD4C3B17AA873382B0F24D6129493D8AAD60#)" ++ " (hash-algo sha256)" ++ " (value 6:sample))"; ++ ++static const char ecdsa_sample_data_bad[] = ++ "(data (flags raw)" ++ " (label #A6E3C57DD01ABE90086538398355DD4C3B17AA873382B0F24D6129493D8AAD60#)" ++ " (hash sha256 #bf2bdbe1aa9b6ec1e2ade1d694f41fc71a831d0268e98915" ++ /**/ "62113d8a62add1bf#))"; ++ ++static const char *ecdsa_data_tmpl = ++ "(data (flags raw)" ++ " (label #A6E3C57DD01ABE90086538398355DD4C3B17AA873382B0F24D6129493D8AAD60#)" ++ " (hash %s %b))"; ++ + static const char ecdsa_signature_r[] = + "efd48b2aacb6a8fd1140dd9cd45e81d69d2c877b56aaf991c34d0ea84eaf3716"; + + static const char ecdsa_signature_s[] = + "f7cb1c942d657c41d436c7a1b6e29f65f3e900dbb9aff4064dc4ab2f843acda8"; + +-static const char *ecdsa_data_tmpl = "(data (flags rfc6979) (hash %s %b))"; + /* Sample data from RFC 6979 section A.2.5, hash is of message "sample" */ + static const char ecdsa_sample_data_string[] = "sample"; + static const char ecdsa_sample_data_bad_string[] = "sbmple"; +@@ -2409,6 +2433,16 @@ run_selftests (int algo, int extended, selftest_report_func_t report) + if (r) + return r; + ++ r = selftests_ecc (report, extended, 0, ++ ecdsa_sample_secret_key_secp256, ++ ecdsa_sample_public_key_secp256, ++ rfc6979_ecdsa_sample_data, rfc6979_ecdsa_sample_data_bad, ++ rfc6979_ecdsa_data_tmpl, ++ ecdsa_sample_data_string, ecdsa_sample_data_bad_string, ++ ecdsa_signature_r, ecdsa_signature_s); ++ if (r) ++ return r; ++ + r = selftests_ecc (report, extended, 1, + ed25519_sample_secret_key, + ed25519_sample_public_key, +-- +2.49.0 + diff --git a/libgcrypt-cipher-Check-and-mark-non-compliant-cipher-modes-in-the-SLI.patch b/libgcrypt-cipher-Check-and-mark-non-compliant-cipher-modes-in-the-SLI.patch new file mode 100644 index 0000000..e922808 --- /dev/null +++ b/libgcrypt-cipher-Check-and-mark-non-compliant-cipher-modes-in-the-SLI.patch @@ -0,0 +1,236 @@ +From 9f0fd2656d7d7ba26fcf95cc64d2514ae9ac8ec1 Mon Sep 17 00:00:00 2001 +From: Lucas Mulling +Date: Fri, 24 Jan 2025 09:57:49 -0300 +Subject: [PATCH] cipher: Check and mark non-compliant cipher modes in the SLI +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* cipher/cipher.c (_gcry_cipher_open_internal): Check and mark if the +cipher mode is compliant and reject accordingly. +(_gcry_cipher_is_mode_fips_compliant): New. +* src/gcrypt.h.in (GCRY_FIPS_FLAG_REJECT_CIPHER_MODE): New. +* tests/t-fips-service-ind.c (check_cipher_o_s_e_d_c): Add test to +verify that the service level indication is correctly set for non- +compliant cipher modes, and correctly rejected if +GCRY_FIPS_FLAG_REJECT_CIPHER_MODE is set. + +-- + +GnuPG-bug-id: 7338 +Signed-off-by: Lucas Mulling +Signed-off-by: Lucas Mülling +--- + cipher/cipher.c | 43 ++++++++++++++++++---- + src/gcrypt.h.in | 1 + + tests/t-fips-service-ind.c | 74 +++++++++++++++++++++++++++++++++----- + 3 files changed, 104 insertions(+), 14 deletions(-) + +diff --git a/cipher/cipher.c b/cipher/cipher.c +index 74dc2df7..b5420671 100644 +--- a/cipher/cipher.c ++++ b/cipher/cipher.c +@@ -504,6 +504,26 @@ _gcry_cipher_open (gcry_cipher_hd_t *handle, + return rc; + } + ++int ++_gcry_cipher_is_mode_fips_compliant(int mode) ++{ ++ switch (mode) ++ { ++ case GCRY_CIPHER_MODE_ECB: ++ case GCRY_CIPHER_MODE_CBC: ++ case GCRY_CIPHER_MODE_CFB: ++ case GCRY_CIPHER_MODE_CFB8: ++ case GCRY_CIPHER_MODE_OFB: ++ case GCRY_CIPHER_MODE_CTR: ++ case GCRY_CIPHER_MODE_CCM: ++ case GCRY_CIPHER_MODE_XTS: ++ case GCRY_CIPHER_MODE_AESWRAP: ++ return GPG_ERR_NO_ERROR; ++ default: ++ return GPG_ERR_NOT_SUPPORTED; ++ } ++} ++ + + gcry_err_code_t + _gcry_cipher_open_internal (gcry_cipher_hd_t *handle, +@@ -523,14 +543,25 @@ _gcry_cipher_open_internal (gcry_cipher_hd_t *handle, + err = GPG_ERR_CIPHER_ALGO; + else if (spec->flags.disabled) + err = GPG_ERR_CIPHER_ALGO; +- else if (!spec->flags.fips && fips_mode ()) ++ else if (fips_mode ()) + { +- if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_CIPHER)) +- err = GPG_ERR_CIPHER_ALGO; +- else ++ if (!spec->flags.fips) + { +- fips_service_indicator_mark_non_compliant (); +- err = 0; ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_CIPHER)) ++ err = GPG_ERR_CIPHER_ALGO; ++ else ++ { ++ fips_service_indicator_mark_non_compliant (); ++ err = 0; ++ } ++ } ++ else if ((err = _gcry_cipher_is_mode_fips_compliant(mode))) ++ { ++ if (!fips_check_rejection (GCRY_FIPS_FLAG_REJECT_CIPHER_MODE)) ++ { ++ fips_service_indicator_mark_non_compliant (); ++ err = 0; ++ } + } + } + else +diff --git a/src/gcrypt.h.in b/src/gcrypt.h.in +index fcb6a327..1a6f7269 100644 +--- a/src/gcrypt.h.in ++++ b/src/gcrypt.h.in +@@ -1988,6 +1988,7 @@ char *gcry_get_config (int mode, const char *what); + #define GCRY_FIPS_FLAG_REJECT_PK (1 << 5) + #define GCRY_FIPS_FLAG_REJECT_PK_MD (1 << 6) + #define GCRY_FIPS_FLAG_REJECT_PK_GOST_SM2 (1 << 7) ++#define GCRY_FIPS_FLAG_REJECT_CIPHER_MODE (1 << 8) + + #define GCRY_FIPS_FLAG_REJECT_MD \ + (GCRY_FIPS_FLAG_REJECT_MD_MD5 | GCRY_FIPS_FLAG_REJECT_MD_OTHERS) +diff --git a/tests/t-fips-service-ind.c b/tests/t-fips-service-ind.c +index fe963fa5..74521bb3 100644 +--- a/tests/t-fips-service-ind.c ++++ b/tests/t-fips-service-ind.c +@@ -606,27 +606,41 @@ check_cipher_o_s_e_d_c (int reject) + { + static struct { + int algo; ++ int mode; + const char *key; + int keylen; ++ const char *tag; ++ int taglen; + const char *expect; + int expect_failure; + } tv[] = { + #if USE_DES +- { GCRY_CIPHER_3DES, +- "\xe3\x34\x7a\x6b\x0b\xc1\x15\x2c\x64\x2a\x25\xcb\xd3\xbc\x31\xab" +- "\xfb\xa1\x62\xa8\x1f\x19\x7c\x15", 24, +- "\x3f\x1a\xb8\x83\x18\x8b\xb5\x97", 1 }, ++ { GCRY_CIPHER_3DES, GCRY_CIPHER_MODE_ECB, ++ "\xe3\x34\x7a\x6b\x0b\xc1\x15\x2c\x64\x2a\x25\xcb\xd3\xbc\x31\xab" ++ "\xfb\xa1\x62\xa8\x1f\x19\x7c\x15", 24, ++ "", -1, ++ "\x3f\x1a\xb8\x83\x18\x8b\xb5\x97", 1 }, + #endif +- { GCRY_CIPHER_AES, +- "\x2b\x7e\x15\x16\x28\xae\xd2\xa6\xab\xf7\x15\x88\x09\xcf\x4f\x3c", 16, +- "\x5c\x71\xd8\x5d\x26\x5e\xcd\xb5\x95\x40\x41\xab\xff\x25\x6f\xd1" } ++ { GCRY_CIPHER_AES, GCRY_CIPHER_MODE_ECB, ++ "\x2b\x7e\x15\x16\x28\xae\xd2\xa6\xab\xf7\x15\x88\x09\xcf\x4f\x3c", 16, ++ "", -1, ++ "\x5c\x71\xd8\x5d\x26\x5e\xcd\xb5\x95\x40\x41\xab\xff\x25\x6f\xd1" }, ++ { GCRY_CIPHER_AES128, GCRY_CIPHER_MODE_SIV, ++ "\xff\xfe\xfd\xfc\xfb\xfa\xf9\xf8\xf7\xf6\xf5\xf4\xf3\xf2\xf1\xf0" ++ "\xf0\xf1\xf2\xf3\xf4\xf5\xf6\xf7\xf8\xf9\xfa\xfb\xfc\xfd\xfe\xff", 32, ++ "\x51\x66\x54\xc4\xe1\xb5\xd9\x37\x31\x52\xdb\xea\x35\x10\x8b\x7b", 16, ++ "\x83\x69\xf6\xf3\x20\xff\xa2\x72\x31\x67\x15\xcf\xf4\x75\x01\x9a", 1 } + }; ++ + const char *pt = "Shohei Ohtani 2024: 54 HR, 59 SB"; + int ptlen; + int tvidx; + unsigned char out[MAX_DATA_LEN]; + gpg_error_t err; + ++ unsigned char tag[16]; ++ size_t taglen = 0; ++ + ptlen = strlen (pt); + assert (ptlen == 32); + for (tvidx=0; tvidx < DIM(tv); tvidx++) +@@ -640,10 +654,12 @@ check_cipher_o_s_e_d_c (int reject) + tvidx); + + blklen = gcry_cipher_get_algo_blklen (tv[tvidx].algo); ++ + assert (blklen != 0); + assert (blklen <= ptlen); + assert (blklen <= DIM (out)); +- err = gcry_cipher_open (&h, tv[tvidx].algo, GCRY_CIPHER_MODE_ECB, 0); ++ assert (tv[tvidx].taglen <= 16); ++ err = gcry_cipher_open (&h, tv[tvidx].algo, tv[tvidx].mode, 0); + if (err) + { + if (in_fips_mode && reject && tv[tvidx].expect_failure) +@@ -694,6 +710,18 @@ check_cipher_o_s_e_d_c (int reject) + continue; + } + ++ if (tv[tvidx].taglen >= 0) ++ { ++ err = gcry_cipher_info (h, GCRYCTL_GET_TAGLEN, NULL, &taglen); ++ if (err) ++ fail ("gcry_cipher_info %d failed: %s\n", tvidx, ++ gpg_strerror (err)); ++ ++ if (taglen != tv[tvidx].taglen) ++ fail ("gcry_cipher_info %d failed: taglen mismatch %d != %ld\n", tvidx, ++ tv[tvidx].taglen, taglen); ++ } ++ + err = gcry_cipher_encrypt (h, out, MAX_DATA_LEN, pt, blklen); + if (err) + { +@@ -714,6 +742,35 @@ check_cipher_o_s_e_d_c (int reject) + putc ('\n', stderr); + } + ++ if (tv[tvidx].taglen >= 0) ++ { ++ err = gcry_cipher_gettag (h, tag, tv[tvidx].taglen); ++ if (err) ++ fail ("gcry_cipher_gettag %d failed: %s", tvidx, ++ gpg_strerror(err)); ++ ++ if (memcmp (tv[tvidx].tag, tag, tv[tvidx].taglen)) ++ { ++ int i; ++ ++ fail ("gcry_cipher_gettag %d: tag mismatch\n", tvidx); ++ fputs ("got:", stderr); ++ for (i=0; i < 16 ; i++) ++ fprintf (stderr, " %02x", tag[i]); ++ putc ('\n', stderr); ++ } ++ ++ err = gcry_cipher_reset (h); ++ if (err) ++ fail("gcry_cipher_reset %d failed: %s", tvidx, ++ gpg_strerror(err)); ++ ++ err = gcry_cipher_set_decryption_tag (h, tag, 16); ++ if (err) ++ fail ("gcry_cipher_set_decryption_tag %d failed: %s\n", tvidx< ++ gpg_strerror (err)); ++ } ++ + err = gcry_cipher_decrypt (h, out, blklen, NULL, 0); + if (err) + { +@@ -1483,6 +1540,7 @@ main (int argc, char **argv) + + xgcry_control ((GCRYCTL_FIPS_REJECT_NON_FIPS, + (GCRY_FIPS_FLAG_REJECT_MD_MD5 ++ | GCRY_FIPS_FLAG_REJECT_CIPHER_MODE + | GCRY_FIPS_FLAG_REJECT_PK_MD + | GCRY_FIPS_FLAG_REJECT_PK_GOST_SM2 + | GCRY_FIPS_FLAG_REJECT_COMPAT110))); +-- +2.49.0 + diff --git a/libgcrypt-cipher-Differentiate-igninvflag-in-the-SLI.patch b/libgcrypt-cipher-Differentiate-igninvflag-in-the-SLI.patch new file mode 100644 index 0000000..7763815 --- /dev/null +++ b/libgcrypt-cipher-Differentiate-igninvflag-in-the-SLI.patch @@ -0,0 +1,40 @@ +From 3bdb59c21b77711cf7d44d692a7a02f5f469033e Mon Sep 17 00:00:00 2001 +From: Lucas Mulling via Gcrypt-devel +Date: Wed, 26 Feb 2025 17:19:22 -0300 +Subject: [PATCH 04/14] cipher: Differentiate igninvflag in the SLI +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* cipher/pubkey-util.c (_gcry_pk_util_parse_flaglist): Differentiate use +of igninvflag. + +GnuPG-bug-id: 7338 +Signed-off-by: Lucas Mulling +Signed-off-by: Lucas Mülling +--- + cipher/pubkey-util.c | 8 ++++++++ + 1 file changed, 8 insertions(+) + +diff --git a/cipher/pubkey-util.c b/cipher/pubkey-util.c +index 68defea6..9c927638 100644 +--- a/cipher/pubkey-util.c ++++ b/cipher/pubkey-util.c +@@ -200,6 +200,14 @@ _gcry_pk_util_parse_flaglist (gcry_sexp_t list, + } + } + ++ if (fips_mode () && igninvflag) ++ { ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) ++ rc = GPG_ERR_INV_FLAG; ++ else ++ fips_service_indicator_mark_non_compliant (); ++ } ++ + if (r_flags) + *r_flags = flags; + if (r_encoding) +-- +2.49.0 + diff --git a/libgcrypt-cipher-Differentiate-no-blinding-flag-in-the-SLI.patch b/libgcrypt-cipher-Differentiate-no-blinding-flag-in-the-SLI.patch new file mode 100644 index 0000000..92b9073 --- /dev/null +++ b/libgcrypt-cipher-Differentiate-no-blinding-flag-in-the-SLI.patch @@ -0,0 +1,70 @@ +From cc0a40bd74120dc06fd80f163b30abb91f60b63b Mon Sep 17 00:00:00 2001 +From: Lucas Mulling via Gcrypt-devel +Date: Wed, 26 Feb 2025 17:19:23 -0300 +Subject: [PATCH 05/14] cipher: Differentiate no-blinding flag in the SLI +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* cipher/rsa.c (rsa_decrypt, rsa_encrypt): Differentiate use of flag +no-blinding in the service level indicator. + +GnuPG-bug-id: 7338 +Signed-off-by: Lucas Mulling +Signed-off-by: Lucas Mülling +--- + cipher/rsa.c | 30 ++++++++++++++++++++++++++++-- + 1 file changed, 28 insertions(+), 2 deletions(-) + +diff --git a/cipher/rsa.c b/cipher/rsa.c +index c1329644..dce76414 100644 +--- a/cipher/rsa.c ++++ b/cipher/rsa.c +@@ -1501,7 +1501,19 @@ rsa_decrypt (gcry_sexp_t *r_plain, gcry_sexp_t s_data, gcry_sexp_t keyparms) + be practically mounted over the network as shown by Brumley and + Boney in 2003. */ + if ((ctx.flags & PUBKEY_FLAG_NO_BLINDING)) +- secret (plain, data, &sk); ++ { ++ if (fips_mode ()) ++ { ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) ++ { ++ rc = GPG_ERR_INV_FLAG; ++ goto leave; ++ } ++ else ++ fips_service_indicator_mark_non_compliant (); ++ } ++ secret (plain, data, &sk); ++ } + else + secret_blinded (plain, data, &sk, nbits); + +@@ -1632,8 +1644,22 @@ rsa_sign (gcry_sexp_t *r_sig, gcry_sexp_t s_data, gcry_sexp_t keyparms) + + /* Do RSA computation. */ + sig = mpi_new (0); ++ + if ((ctx.flags & PUBKEY_FLAG_NO_BLINDING)) +- secret (sig, data, &sk); ++ { ++ if (fips_mode ()) ++ { ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) ++ { ++ rc = GPG_ERR_INV_FLAG; ++ goto leave; ++ } ++ else ++ fips_service_indicator_mark_non_compliant (); ++ } ++ ++ secret (sig, data, &sk); ++ } + else + secret_blinded (sig, data, &sk, nbits); + if (DBG_CIPHER) +-- +2.49.0 + diff --git a/libgcrypt-cipher-Differentiate-use-of-label-K-in-the-SLI.patch b/libgcrypt-cipher-Differentiate-use-of-label-K-in-the-SLI.patch new file mode 100644 index 0000000..a054b64 --- /dev/null +++ b/libgcrypt-cipher-Differentiate-use-of-label-K-in-the-SLI.patch @@ -0,0 +1,139 @@ +From 2f6d2db1a4c28775a568c1f81ca127d2daebaf1c Mon Sep 17 00:00:00 2001 +From: Lucas Mulling via Gcrypt-devel +Date: Wed, 26 Feb 2025 12:29:54 -0300 +Subject: [PATCH 03/14] cipher: Differentiate use of label K in the SLI +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* cipher/ecc.c (ecc_sign, ecc_verify): Use of label K is not allowed in +fips mode, differentiate with the GCRY_FIPS_FLAG_REJECT_PK_ECC_K flag. +* src/gcrypt.h.in: New GCRY_FIPS_FLAG_REJECT_PK_ECC_K. +* tests/t-fips-service-ind.c (check_pk_hash_sign_verify): Mark non +compliant use of label. + +Signed-off-by: Lucas Mulling +Signed-off-by: Lucas Mülling +--- + cipher/ecc.c | 26 +++++++++++++++++++++++++- + src/gcrypt.h.in | 2 ++ + tests/t-fips-service-ind.c | 11 ++++++----- + 3 files changed, 33 insertions(+), 6 deletions(-) + +diff --git a/cipher/ecc.c b/cipher/ecc.c +index d331a014..569e41f6 100644 +--- a/cipher/ecc.c ++++ b/cipher/ecc.c +@@ -961,7 +961,16 @@ ecc_sign (gcry_sexp_t *r_sig, gcry_sexp_t s_data, gcry_sexp_t keyparms) + log_mpidump ("ecc_sign data", data); + + if (ctx.label) +- rc = _gcry_mpi_scan (&k, GCRYMPI_FMT_USG, ctx.label, ctx.labellen, NULL); ++ { ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK_ECC_K)) ++ { ++ rc = GPG_ERR_INV_DATA; ++ goto leave; ++ } ++ else ++ fips_service_indicator_mark_non_compliant (); ++ rc = _gcry_mpi_scan (&k, GCRYMPI_FMT_USG, ctx.label, ctx.labellen, NULL); ++ } + if (rc) + goto leave; + +@@ -1118,6 +1127,21 @@ ecc_verify (gcry_sexp_t s_sig, gcry_sexp_t s_data, gcry_sexp_t s_keyparms) + rc = _gcry_pk_util_data_to_mpi (s_data, &data, &ctx); + if (rc) + goto leave; ++ ++ if (ctx.label) ++ { ++ if (fips_mode ()) ++ { ++ if(fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK_ECC_K)) ++ { ++ rc = GPG_ERR_INV_DATA; ++ goto leave; ++ } ++ else ++ fips_service_indicator_mark_non_compliant (); ++ } ++ } ++ + if (DBG_CIPHER) + log_mpidump ("ecc_verify data", data); + +diff --git a/src/gcrypt.h.in b/src/gcrypt.h.in +index 1a6f7269..fe3db16a 100644 +--- a/src/gcrypt.h.in ++++ b/src/gcrypt.h.in +@@ -1989,6 +1989,8 @@ char *gcry_get_config (int mode, const char *what); + #define GCRY_FIPS_FLAG_REJECT_PK_MD (1 << 6) + #define GCRY_FIPS_FLAG_REJECT_PK_GOST_SM2 (1 << 7) + #define GCRY_FIPS_FLAG_REJECT_CIPHER_MODE (1 << 8) ++/**/ ++#define GCRY_FIPS_FLAG_REJECT_PK_ECC_K (1 << 10) + + #define GCRY_FIPS_FLAG_REJECT_MD \ + (GCRY_FIPS_FLAG_REJECT_MD_MD5 | GCRY_FIPS_FLAG_REJECT_MD_OTHERS) +diff --git a/tests/t-fips-service-ind.c b/tests/t-fips-service-ind.c +index a082b258..0ece55b8 100644 +--- a/tests/t-fips-service-ind.c ++++ b/tests/t-fips-service-ind.c +@@ -728,7 +728,7 @@ check_pk_hash_sign_verify (void) + "ce4014c68811f9a21a1fdb2c0e6113e06db7ca93b7404e78dc7ccd5ca89a4ca9#)))", + "(data(flags raw)(hash %s %b)(label %b))", + "94a1bbb14b906a61a280f245f9e93c7f3b4a6247824f5d33b9670787642a68de", +- 0, 0 ++ 1, 0, + } + }; + int tvidx; +@@ -827,7 +827,7 @@ check_pk_hash_sign_verify (void) + if (ec == GPG_ERR_INV_OP) + { + /* libgcrypt is old, no support of the FIPS service indicator. */ +- fail ("gcry_pk_hash test %d unexpectedly failed to check the FIPS service indicator.\n", ++ fail ("gcry_pk_hash_sign test %d unexpectedly failed to check the FIPS service indicator.\n", + tvidx); + goto next; + } +@@ -835,7 +835,7 @@ check_pk_hash_sign_verify (void) + if (in_fips_mode && !tv[tvidx].expect_failure && ec) + { + /* Success with the FIPS service indicator == 0 expected, but != 0. */ +- fail ("gcry_pk_hash test %d unexpectedly set the indicator in FIPS mode.\n", ++ fail ("gcry_pk_hash_sign test %d unexpectedly set the indicator in FIPS mode.\n", + tvidx); + goto next; + } +@@ -859,7 +859,7 @@ check_pk_hash_sign_verify (void) + if (ec == GPG_ERR_INV_OP) + { + /* libgcrypt is old, no support of the FIPS service indicator. */ +- fail ("gcry_pk_hash test %d unexpectedly failed to check the FIPS service indicator.\n", ++ fail ("gcry_pk_hash_verify test %d unexpectedly failed to check the FIPS service indicator.\n", + tvidx); + goto next; + } +@@ -867,7 +867,7 @@ check_pk_hash_sign_verify (void) + if (in_fips_mode && !tv[tvidx].expect_failure && ec) + { + /* Success with the FIPS service indicator == 0 expected, but != 0. */ +- fail ("gcry_pk_hash test %d unexpectedly set the indicator in FIPS mode.\n", ++ fail ("gcry_pk_hash_verify test %d unexpectedly set the indicator in FIPS mode.\n", + tvidx); + goto next; + } +@@ -1834,6 +1834,7 @@ main (int argc, char **argv) + | GCRY_FIPS_FLAG_REJECT_CIPHER_MODE + | GCRY_FIPS_FLAG_REJECT_PK_MD + | GCRY_FIPS_FLAG_REJECT_PK_GOST_SM2 ++ | GCRY_FIPS_FLAG_REJECT_PK_ECC_K + | GCRY_FIPS_FLAG_REJECT_COMPAT110))); + + check_md_o_w_r_c (1); +-- +2.49.0 + diff --git a/libgcrypt-cipher-Don-t-differentiate-GCRY_CIPHER_MODE_CMAC-in-FIPS-mode.patch b/libgcrypt-cipher-Don-t-differentiate-GCRY_CIPHER_MODE_CMAC-in-FIPS-mode.patch new file mode 100644 index 0000000..fc8d335 --- /dev/null +++ b/libgcrypt-cipher-Don-t-differentiate-GCRY_CIPHER_MODE_CMAC-in-FIPS-mode.patch @@ -0,0 +1,98 @@ +From 608ff4b2261e2d8961f0ef4189e74b1173b2802c Mon Sep 17 00:00:00 2001 +From: Lucas Mulling +Date: Sun, 2 Feb 2025 12:58:21 -0300 +Subject: [PATCH 2/2] cipher: Don't differentiate GCRY_CIPHER_MODE_CMAC in FIPS + mode. +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* cipher/cipher.c (_gcry_cipher_mode_fips_compliance): Allow +GCRY_CIPHER_MODE_CMAC in fips mode. +* cipher/cipher.c (cipher_modes_fips_compliance) +(cipher_int_modes_fips_compliance): New. +-- + +Signed-off-by: Lucas Mulling + +Added some comments, changed scope of the new functions and shorted +their names. Also added restructured the switch and added all other +modes. + +Signed-off-by: Werner Koch +Signed-off-by: Lucas Mülling +--- + cipher/cipher.c | 49 ++++++++++++++++++++++++++++++++++++++++++++----- + 1 file changed, 44 insertions(+), 5 deletions(-) + +diff --git a/cipher/cipher.c b/cipher/cipher.c +index 3b7970b3..fc130907 100644 +--- a/cipher/cipher.c ++++ b/cipher/cipher.c +@@ -505,8 +505,9 @@ _gcry_cipher_open (gcry_cipher_hd_t *handle, + } + + +-gcry_err_code_t +-_gcry_cipher_mode_fips_compliance (enum gcry_cipher_modes mode) ++/* Return an error if the give cipher mode is non-FIPS compliant. */ ++static gcry_err_code_t ++cipher_modes_fips_compliance (enum gcry_cipher_modes mode) + { + switch (mode) + { +@@ -519,10 +520,48 @@ _gcry_cipher_mode_fips_compliance (enum gcry_cipher_modes mode) + case GCRY_CIPHER_MODE_CCM: + case GCRY_CIPHER_MODE_XTS: + case GCRY_CIPHER_MODE_AESWRAP: +- return GPG_ERR_NO_ERROR; +- default: +- return GPG_ERR_NOT_SUPPORTED; ++ return 0; ++ case GCRY_CIPHER_MODE_NONE: ++ case GCRY_CIPHER_MODE_STREAM: ++ case GCRY_CIPHER_MODE_GCM: ++ case GCRY_CIPHER_MODE_POLY1305: ++ case GCRY_CIPHER_MODE_OCB: ++ case GCRY_CIPHER_MODE_EAX: ++ case GCRY_CIPHER_MODE_SIV: ++ case GCRY_CIPHER_MODE_GCM_SIV: ++ break; + } ++ return GPG_ERR_NOT_SUPPORTED; ++} ++ ++ ++/* This is similar to cipher_modes_fips_compliance but only for the ++ * internal modes (i.e. CMAC). Return an error if the mode is ++ * non-FIPS compliant. */ ++static gcry_err_code_t ++cipher_int_modes_fips_compliance (enum gcry_cipher_internal_modes mode) ++{ ++ switch (mode) ++ { ++ case GCRY_CIPHER_MODE_INTERNAL: ++ break; ++ case GCRY_CIPHER_MODE_CMAC: ++ return 0; ++ } ++ return GPG_ERR_NOT_SUPPORTED; ++} ++ ++ ++/* Return an error if the give cipher mode is non-FIPS compliant. The ++ * mode is not an enum here so that we can use it for real modes and ++ * for internal modes. */ ++gcry_err_code_t ++_gcry_cipher_mode_fips_compliance (int mode) ++{ ++ if (mode >= GCRY_CIPHER_MODE_INTERNAL) ++ return cipher_int_modes_fips_compliance (mode); ++ else ++ return cipher_modes_fips_compliance (mode); + } + + +-- +2.49.0 + diff --git a/libgcrypt-cipher-Rename-_gcry_cipher_is_mode_fips_compliant.patch b/libgcrypt-cipher-Rename-_gcry_cipher_is_mode_fips_compliant.patch new file mode 100644 index 0000000..e98f6ab --- /dev/null +++ b/libgcrypt-cipher-Rename-_gcry_cipher_is_mode_fips_compliant.patch @@ -0,0 +1,64 @@ +From 6b0fbb7e5e0da77787e3a87d74359ee21c44904e Mon Sep 17 00:00:00 2001 +From: Lucas Mulling +Date: Tue, 28 Jan 2025 13:45:39 -0300 +Subject: [PATCH 1/2] cipher: Rename _gcry_cipher_is_mode_fips_compliant +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* cipher/cipher.c (_gcry_cipher_is_mode_fips_compliant): Rename to +_gcry_cipher_mode_fips_compliance for better clarity and change the +return type to gcry_err_code_t. +* cipher/cipher.c (_gcry_cipher_mode_fips_compliance): Use +gcry_cipher_modes instead of int for mode. +* tests/t-fips-service-ind.c (check_cipher_o_s_e_d_c): Fix typo in fail. +-- + +Signed-off-by: Lucas Mulling +Signed-off-by: Lucas Mülling +--- + cipher/cipher.c | 7 ++++--- + tests/t-fips-service-ind.c | 2 +- + 2 files changed, 5 insertions(+), 4 deletions(-) + +diff --git a/cipher/cipher.c b/cipher/cipher.c +index b5420671..3b7970b3 100644 +--- a/cipher/cipher.c ++++ b/cipher/cipher.c +@@ -504,8 +504,9 @@ _gcry_cipher_open (gcry_cipher_hd_t *handle, + return rc; + } + +-int +-_gcry_cipher_is_mode_fips_compliant(int mode) ++ ++gcry_err_code_t ++_gcry_cipher_mode_fips_compliance (enum gcry_cipher_modes mode) + { + switch (mode) + { +@@ -555,7 +556,7 @@ _gcry_cipher_open_internal (gcry_cipher_hd_t *handle, + err = 0; + } + } +- else if ((err = _gcry_cipher_is_mode_fips_compliant(mode))) ++ else if ((err = _gcry_cipher_mode_fips_compliance (mode))) + { + if (!fips_check_rejection (GCRY_FIPS_FLAG_REJECT_CIPHER_MODE)) + { +diff --git a/tests/t-fips-service-ind.c b/tests/t-fips-service-ind.c +index 74521bb3..ed5f8d3f 100644 +--- a/tests/t-fips-service-ind.c ++++ b/tests/t-fips-service-ind.c +@@ -767,7 +767,7 @@ check_cipher_o_s_e_d_c (int reject) + + err = gcry_cipher_set_decryption_tag (h, tag, 16); + if (err) +- fail ("gcry_cipher_set_decryption_tag %d failed: %s\n", tvidx< ++ fail ("gcry_cipher_set_decryption_tag %d failed: %s\n", tvidx, + gpg_strerror (err)); + } + +-- +2.49.0 + diff --git a/libgcrypt-cipher-ecc-Fix-for-supplied-K.patch b/libgcrypt-cipher-ecc-Fix-for-supplied-K.patch new file mode 100644 index 0000000..743468d --- /dev/null +++ b/libgcrypt-cipher-ecc-Fix-for-supplied-K.patch @@ -0,0 +1,88 @@ +From 755e6dce727915249cbb1a98f22832d940b99c24 Mon Sep 17 00:00:00 2001 +From: NIIBE Yutaka +Date: Thu, 6 Mar 2025 09:12:36 +0900 +Subject: [PATCH 07/14] cipher,ecc: Fix for supplied K. +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* cipher/ecc.c (ecc_sign): Check if it's under FIPS mode. +(ecc_verify): Supplied K does no sense for verification, but add +comment of clarification mark/reject-ing under FIPS mode. + +-- + +GnuPG-bug-id: 7338 +Signed-off-by: NIIBE Yutaka +Signed-off-by: Lucas Mülling +--- + cipher/ecc.c | 39 +++++++++++++++++++++++---------------- + 1 file changed, 23 insertions(+), 16 deletions(-) + +diff --git a/cipher/ecc.c b/cipher/ecc.c +index 569e41f6..a165bb7a 100644 +--- a/cipher/ecc.c ++++ b/cipher/ecc.c +@@ -962,17 +962,21 @@ ecc_sign (gcry_sexp_t *r_sig, gcry_sexp_t s_data, gcry_sexp_t keyparms) + + if (ctx.label) + { +- if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK_ECC_K)) ++ /* ECDSA signing can have supplied K (for testing, deterministic). */ ++ if (fips_mode ()) + { +- rc = GPG_ERR_INV_DATA; +- goto leave; ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK_ECC_K)) ++ { ++ rc = GPG_ERR_INV_DATA; ++ goto leave; ++ } ++ else ++ fips_service_indicator_mark_non_compliant (); + } +- else +- fips_service_indicator_mark_non_compliant (); + rc = _gcry_mpi_scan (&k, GCRYMPI_FMT_USG, ctx.label, ctx.labellen, NULL); ++ if (rc) ++ goto leave; + } +- if (rc) +- goto leave; + + if (fips_mode () + && ((ctx.flags & PUBKEY_FLAG_GOST) || (ctx.flags & PUBKEY_FLAG_SM2))) +@@ -1128,18 +1132,21 @@ ecc_verify (gcry_sexp_t s_sig, gcry_sexp_t s_data, gcry_sexp_t s_keyparms) + if (rc) + goto leave; + +- if (ctx.label) ++ /* ++ * ECDSA signing can have supplied K (for testing, deterministic), ++ * but it's non-compliant. For ECDSA signature verification, having ++ * K is irrelevant, but an application may use same flags as the one ++ * for signing. ++ */ ++ if (ctx.label && fips_mode ()) + { +- if (fips_mode ()) ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK_ECC_K)) + { +- if(fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK_ECC_K)) +- { +- rc = GPG_ERR_INV_DATA; +- goto leave; +- } +- else +- fips_service_indicator_mark_non_compliant (); ++ rc = GPG_ERR_INV_DATA; ++ goto leave; + } ++ else ++ fips_service_indicator_mark_non_compliant (); + } + + if (DBG_CIPHER) +-- +2.49.0 + diff --git a/libgcrypt-cipher-fips-Fix-for-random-override.patch b/libgcrypt-cipher-fips-Fix-for-random-override.patch new file mode 100644 index 0000000..076f66f --- /dev/null +++ b/libgcrypt-cipher-fips-Fix-for-random-override.patch @@ -0,0 +1,83 @@ +From ca8bf05e111b41e482a2a4b34cda6bcf5aa1f27e Mon Sep 17 00:00:00 2001 +From: NIIBE Yutaka +Date: Thu, 6 Mar 2025 09:45:36 +0900 +Subject: [PATCH 09/14] cipher,fips: Fix for random-override. +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* cipher/pubkey-util.c (gcry_pk_util_data_to_mpi): Keep +the behavior of 1.10. +* src/visibility.c (gcry_pk_random_override_new): Likewise. +* tests/t-fips-service-ind.c (main): Use GCRY_FIPS_FLAG_REJECT_PK_FLAGS. + +-- + +GnuPG-bug-id: 7338 +Signed-off-by: NIIBE Yutaka +Signed-off-by: Lucas Mülling +--- + cipher/pubkey-util.c | 6 +++--- + src/visibility.c | 2 +- + tests/t-fips-service-ind.c | 1 + + 3 files changed, 5 insertions(+), 4 deletions(-) + +diff --git a/cipher/pubkey-util.c b/cipher/pubkey-util.c +index 66a04f13..0e67f892 100644 +--- a/cipher/pubkey-util.c ++++ b/cipher/pubkey-util.c +@@ -975,7 +975,7 @@ _gcry_pk_util_data_to_mpi (gcry_sexp_t input, gcry_mpi_t *ret_mpi, + { + if (fips_mode ()) + { +- if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK_FLAGS)) + { + sexp_release (list); + rc = GPG_ERR_INV_FLAG; +@@ -1162,7 +1162,7 @@ _gcry_pk_util_data_to_mpi (gcry_sexp_t input, gcry_mpi_t *ret_mpi, + { + if (fips_mode ()) + { +- if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK_FLAGS)) + { + sexp_release (list); + rc = GPG_ERR_INV_FLAG; +@@ -1272,7 +1272,7 @@ _gcry_pk_util_data_to_mpi (gcry_sexp_t input, gcry_mpi_t *ret_mpi, + { + if (fips_mode ()) + { +- if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK_FLAGS)) + { + sexp_release (list); + rc = GPG_ERR_INV_FLAG; +diff --git a/src/visibility.c b/src/visibility.c +index ccd0de69..edb972bc 100644 +--- a/src/visibility.c ++++ b/src/visibility.c +@@ -1091,7 +1091,7 @@ gcry_pk_random_override_new (gcry_ctx_t *r_ctx, const unsigned char *p, size_t l + + if (fips_mode ()) + { +- if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK_FLAGS)) + return gpg_error (GPG_ERR_INV_OP); + else + fips_service_indicator_mark_non_compliant (); +diff --git a/tests/t-fips-service-ind.c b/tests/t-fips-service-ind.c +index 0ece55b8..0a270b38 100644 +--- a/tests/t-fips-service-ind.c ++++ b/tests/t-fips-service-ind.c +@@ -1835,6 +1835,7 @@ main (int argc, char **argv) + | GCRY_FIPS_FLAG_REJECT_PK_MD + | GCRY_FIPS_FLAG_REJECT_PK_GOST_SM2 + | GCRY_FIPS_FLAG_REJECT_PK_ECC_K ++ | GCRY_FIPS_FLAG_REJECT_PK_FLAGS + | GCRY_FIPS_FLAG_REJECT_COMPAT110))); + + check_md_o_w_r_c (1); +-- +2.49.0 + diff --git a/libgcrypt-cipher-rsa-Mark-reject-SHA1-unknown-with-RSA-signature-generation.patch b/libgcrypt-cipher-rsa-Mark-reject-SHA1-unknown-with-RSA-signature-generation.patch new file mode 100644 index 0000000..7ff18ce --- /dev/null +++ b/libgcrypt-cipher-rsa-Mark-reject-SHA1-unknown-with-RSA-signature-generation.patch @@ -0,0 +1,445 @@ +From 60e5039793c2474d29ded039cf1a6b8107733a20 Mon Sep 17 00:00:00 2001 +From: NIIBE Yutaka +Date: Fri, 21 Feb 2025 14:24:41 +0900 +Subject: [PATCH] cipher:rsa: Mark/reject SHA1/unknown with RSA signature + generation. +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* cipher/rsa-common.c (_gcry_rsa_pkcs1_encode_raw_for_sig): We can't +determine if it's compliant when raw PKCS1 encoding is used. +(_gcry_rsa_pss_encode): Add the behavior of marking non-compliant use. +(_gcry_rsa_pss_verify): Likewise. +* cipher/rsa.c (rsa_sign): Handle the check for SHA1. +(rsa_verify): Likewise. +* tests/t-fips-service-ind.c (check_pk_s_v): Add use cases for RSA +and Ed25519. + +-- + +GnuPG-bug-id: 7338 +Signed-off-by: NIIBE Yutaka +Signed-off-by: Lucas Mülling +--- + cipher/rsa-common.c | 28 +++- + cipher/rsa.c | 34 +++++ + tests/t-fips-service-ind.c | 290 ++++++++++++++++++++++++++++++++++++- + 3 files changed, 347 insertions(+), 5 deletions(-) + +diff --git a/cipher/rsa-common.c b/cipher/rsa-common.c +index 1920eedd..c1d2dcd5 100644 +--- a/cipher/rsa-common.c ++++ b/cipher/rsa-common.c +@@ -380,6 +380,16 @@ _gcry_rsa_pkcs1_encode_raw_for_sig (gcry_mpi_t *r_result, unsigned int nbits, + int i; + size_t n; + ++ /* With RAW encoding, we can't know if the hash used is compliant or ++ * not. Reject or mark it's non-compliant. */ ++ if (fips_mode ()) ++ { ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK_MD)) ++ return GPG_ERR_DIGEST_ALGO; ++ else ++ fips_service_indicator_mark_non_compliant (); ++ } ++ + if ( !valuelen || valuelen + 4 > nframe) + { + /* Can't encode an DLEN byte digest MD into an NFRAME byte +@@ -840,8 +850,13 @@ _gcry_rsa_pss_encode (gcry_mpi_t *r_result, unsigned int nbits, int algo, + /* The FIPS 186-4 Section 5.5 allows only 0 <= sLen <= hLen */ + if (fips_mode () && saltlen > hlen) + { +- rc = GPG_ERR_INV_ARG; +- goto leave; ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) ++ { ++ rc = GPG_ERR_INV_ARG; ++ goto leave; ++ } ++ else ++ fips_service_indicator_mark_non_compliant (); + } + + /* Allocate a help buffer and setup some pointers. */ +@@ -1006,8 +1021,13 @@ _gcry_rsa_pss_verify (gcry_mpi_t value, int hashed_already, + /* The FIPS 186-4 Section 5.5 allows only 0 <= sLen <= hLen */ + if (fips_mode () && saltlen > hlen) + { +- rc = GPG_ERR_INV_ARG; +- goto leave; ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) ++ { ++ rc = GPG_ERR_INV_ARG; ++ goto leave; ++ } ++ else ++ fips_service_indicator_mark_non_compliant (); + } + + /* Allocate a help buffer and setup some pointers. +diff --git a/cipher/rsa.c b/cipher/rsa.c +index c7a809f4..c1329644 100644 +--- a/cipher/rsa.c ++++ b/cipher/rsa.c +@@ -1613,6 +1613,23 @@ rsa_sign (gcry_sexp_t *r_sig, gcry_sexp_t s_data, gcry_sexp_t keyparms) + } + } + ++ /* Check if use of the hash is compliant. */ ++ if (fips_mode ()) ++ { ++ /* SHA1 is approved hash function, but not for digital signature. */ ++ if (_gcry_md_algo_info (ctx.hash_algo, GCRYCTL_TEST_ALGO, NULL, NULL) ++ || ctx.hash_algo == GCRY_MD_SHA1) ++ { ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK_MD)) ++ { ++ rc = GPG_ERR_DIGEST_ALGO; ++ goto leave; ++ } ++ else ++ fips_service_indicator_mark_non_compliant (); ++ } ++ } ++ + /* Do RSA computation. */ + sig = mpi_new (0); + if ((ctx.flags & PUBKEY_FLAG_NO_BLINDING)) +@@ -1720,6 +1737,23 @@ rsa_verify (gcry_sexp_t s_sig, gcry_sexp_t s_data, gcry_sexp_t keyparms) + log_printmpi ("rsa_verify e", pk.e); + } + ++ /* Check if use of the hash is compliant. */ ++ if (fips_mode ()) ++ { ++ /* SHA1 is approved hash function, but not for digital signature. */ ++ if (_gcry_md_algo_info (ctx.hash_algo, GCRYCTL_TEST_ALGO, NULL, NULL) ++ || ctx.hash_algo == GCRY_MD_SHA1) ++ { ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK_MD)) ++ { ++ rc = GPG_ERR_DIGEST_ALGO; ++ goto leave; ++ } ++ else ++ fips_service_indicator_mark_non_compliant (); ++ } ++ } ++ + /* Do RSA computation and compare. */ + result = mpi_new (0); + public (result, sig, &pk); +diff --git a/tests/t-fips-service-ind.c b/tests/t-fips-service-ind.c +index ed5f8d3f..bec6c27e 100644 +--- a/tests/t-fips-service-ind.c ++++ b/tests/t-fips-service-ind.c +@@ -231,7 +231,8 @@ check_pk_s_v (int reject) + const char *data; + int expect_failure; + } tv[] = { +- { ++ { /* Hashing is done externally, and feeded ++ to gcry_pk_sign, specifing the hash used */ + "(private-key (ecc (curve nistp256)" + " (d #519b423d715f8b581f4fa8ee59f4771a5b44c8130b4e3eacca54a56dda72b464#)))", + "(public-key (ecc (curve nistp256)" +@@ -271,6 +272,293 @@ check_pk_s_v (int reject) + "#00112233445566778899AABBCCDDEEFF00010203#))", + 1 + }, ++ { /* Hashing is done internally in ++ gcry_pk_sign with the hash-algo specified. */ ++ "(private-key\n" ++ " (ecc\n" ++ " (curve Ed25519)(flags eddsa)\n" ++ " (q #4014DB483F15527253B25B4C72BEA8BB70255029636BD71DBBCCD5D8BF48A35F17#)" ++ " (d #09A0C38E0F1699073541447C19DA12E3A07A7BFDB0C186E4AC5BCE6F23D55252#)" ++ "))", ++ "(public-key\n" ++ " (ecc\n" ++ " (curve Ed25519)(flags eddsa)\n" ++ " (q #4014DB483F15527253B25B4C72BEA8BB70255029636BD71DBBCCD5D8BF48A35F17#)" ++ "))", ++ "(data(flags eddsa)(hash-algo sha512)(value " ++ "#00112233445566778899AABBCCDDEEFF000102030405060708090A0B0C0D0E0F" ++ " 00112233445566778899AABBCCDDEEFF000102030405060708090A0B0C0D0E0F" ++ " 00112233445566778899AABBCCDDEEFF000102030405060708090A0B0C0D0E0F#))", ++ 0 ++ }, ++ { /* RSA with compliant hash for signing */ ++ "(private-key" ++ " (rsa" ++ " (n #009F56231A3D82E3E7D613D59D53E9AB921BEF9F08A782AED0B6E46ADBC853EC" ++ " 7C71C422435A3CD8FA0DB9EFD55CD3295BADC4E8E2E2B94E15AE82866AB8ADE8" ++ " 7E469FAE76DC3577DE87F1F419C4EB41123DFAF8D16922D5EDBAD6E9076D5A1C" ++ " 958106F0AE5E2E9193C6B49124C64C2A241C4075D4AF16299EB87A6585BAE917" ++ " DEF27FCDD165764D069BC18D16527B29DAAB549F7BBED4A7C6A842D203ED6613" ++ " 6E2411744E432CD26D940132F25874483DCAEECDFD95744819CBCF1EA810681C" ++ " 42907EBCB1C7EAFBE75C87EC32C5413EA10476545D3FC7B2ADB1B66B7F200918" ++ " 664B0E5261C2895AA28B0DE321E921B3F877172CCCAB81F43EF98002916156F6" ++ " CB#)\n" ++ " (e #010001#)\n" ++ " (d #07EF82500C403899934FE993AC5A36F14FF2DF38CF1EF315F205EE4C83EDAA19" ++ " 8890FC23DE9AA933CAFB37B6A8A8DBA675411958337287310D3FF2F1DDC0CB93" ++ " 7E70F57F75F833C021852B631D2B9A520E4431A03C5C3FCB5742DCD841D9FB12" ++ " 771AA1620DCEC3F1583426066ED9DC3F7028C5B59202C88FDF20396E2FA0EC4F" ++ " 5A22D9008F3043673931BC14A5046D6327398327900867E39CC61B2D1AFE2F48" ++ " EC8E1E3861C68D257D7425F4E6F99ABD77D61F10CA100EFC14389071831B33DD" ++ " 69CC8EABEF860D1DC2AAA84ABEAE5DFC91BC124DAF0F4C8EF5BBEA436751DE84" ++ " 3A8063E827A024466F44C28614F93B0732A100D4A0D86D532FE1E22C7725E401" ++ " #)\n" ++ " (p #00C29D438F115825779631CD665A5739367F3E128ADC29766483A46CA80897E0" ++ " 79B32881860B8F9A6A04C2614A904F6F2578DAE13EA67CD60AE3D0AA00A1FF9B" ++ " 441485E44B2DC3D0B60260FBFE073B5AC72FAF67964DE15C8212C389D20DB9CF" ++ " 54AF6AEF5C4196EAA56495DD30CF709F499D5AB30CA35E086C2A1589D6283F17" ++ " 83#)\n" ++ " (q #00D1984135231CB243FE959C0CBEF551EDD986AD7BEDF71EDF447BE3DA27AF46" ++ " 79C974A6FA69E4D52FE796650623DE70622862713932AA2FD9F2EC856EAEAA77" ++ " 88B4EA6084DC81C902F014829B18EA8B2666EC41586818E0589E18876065F97E" ++ " 8D22CE2DA53A05951EC132DCEF41E70A9C35F4ACC268FFAC2ADF54FA1DA110B9" ++ " 19#)\n" ++ " (u #67CF0FD7635205DD80FA814EE9E9C267C17376BF3209FB5D1BC42890D2822A04" ++ " 479DAF4D5B6ED69D0F8D1AF94164D07F8CD52ECEFE880641FA0F41DDAB1785E4" ++ " A37A32F997A516480B4CD4F6482B9466A1765093ED95023CA32D5EDC1E34CEE9" ++ " AF595BC51FE43C4BF810FA225AF697FB473B83815966188A4312C048B885E3F7" ++ " #)))\n", ++ "(public-key\n" ++ " (rsa\n" ++ " (n #009F56231A3D82E3E7D613D59D53E9AB921BEF9F08A782AED0B6E46ADBC853EC" ++ " 7C71C422435A3CD8FA0DB9EFD55CD3295BADC4E8E2E2B94E15AE82866AB8ADE8" ++ " 7E469FAE76DC3577DE87F1F419C4EB41123DFAF8D16922D5EDBAD6E9076D5A1C" ++ " 958106F0AE5E2E9193C6B49124C64C2A241C4075D4AF16299EB87A6585BAE917" ++ " DEF27FCDD165764D069BC18D16527B29DAAB549F7BBED4A7C6A842D203ED6613" ++ " 6E2411744E432CD26D940132F25874483DCAEECDFD95744819CBCF1EA810681C" ++ " 42907EBCB1C7EAFBE75C87EC32C5413EA10476545D3FC7B2ADB1B66B7F200918" ++ " 664B0E5261C2895AA28B0DE321E921B3F877172CCCAB81F43EF98002916156F6" ++ " CB#)\n" ++ " (e #010001#)))\n", ++ "(data\n (flags pkcs1)\n" ++ " (hash sha256 " ++ "#00112233445566778899AABBCCDDEEFF000102030405060708090A0B0C0D0E0F#))\n", ++ 0 ++ }, ++ { /* RSA with non-compliant hash for signing */ ++ "(private-key" ++ " (rsa" ++ " (n #009F56231A3D82E3E7D613D59D53E9AB921BEF9F08A782AED0B6E46ADBC853EC" ++ " 7C71C422435A3CD8FA0DB9EFD55CD3295BADC4E8E2E2B94E15AE82866AB8ADE8" ++ " 7E469FAE76DC3577DE87F1F419C4EB41123DFAF8D16922D5EDBAD6E9076D5A1C" ++ " 958106F0AE5E2E9193C6B49124C64C2A241C4075D4AF16299EB87A6585BAE917" ++ " DEF27FCDD165764D069BC18D16527B29DAAB549F7BBED4A7C6A842D203ED6613" ++ " 6E2411744E432CD26D940132F25874483DCAEECDFD95744819CBCF1EA810681C" ++ " 42907EBCB1C7EAFBE75C87EC32C5413EA10476545D3FC7B2ADB1B66B7F200918" ++ " 664B0E5261C2895AA28B0DE321E921B3F877172CCCAB81F43EF98002916156F6" ++ " CB#)\n" ++ " (e #010001#)\n" ++ " (d #07EF82500C403899934FE993AC5A36F14FF2DF38CF1EF315F205EE4C83EDAA19" ++ " 8890FC23DE9AA933CAFB37B6A8A8DBA675411958337287310D3FF2F1DDC0CB93" ++ " 7E70F57F75F833C021852B631D2B9A520E4431A03C5C3FCB5742DCD841D9FB12" ++ " 771AA1620DCEC3F1583426066ED9DC3F7028C5B59202C88FDF20396E2FA0EC4F" ++ " 5A22D9008F3043673931BC14A5046D6327398327900867E39CC61B2D1AFE2F48" ++ " EC8E1E3861C68D257D7425F4E6F99ABD77D61F10CA100EFC14389071831B33DD" ++ " 69CC8EABEF860D1DC2AAA84ABEAE5DFC91BC124DAF0F4C8EF5BBEA436751DE84" ++ " 3A8063E827A024466F44C28614F93B0732A100D4A0D86D532FE1E22C7725E401" ++ " #)\n" ++ " (p #00C29D438F115825779631CD665A5739367F3E128ADC29766483A46CA80897E0" ++ " 79B32881860B8F9A6A04C2614A904F6F2578DAE13EA67CD60AE3D0AA00A1FF9B" ++ " 441485E44B2DC3D0B60260FBFE073B5AC72FAF67964DE15C8212C389D20DB9CF" ++ " 54AF6AEF5C4196EAA56495DD30CF709F499D5AB30CA35E086C2A1589D6283F17" ++ " 83#)\n" ++ " (q #00D1984135231CB243FE959C0CBEF551EDD986AD7BEDF71EDF447BE3DA27AF46" ++ " 79C974A6FA69E4D52FE796650623DE70622862713932AA2FD9F2EC856EAEAA77" ++ " 88B4EA6084DC81C902F014829B18EA8B2666EC41586818E0589E18876065F97E" ++ " 8D22CE2DA53A05951EC132DCEF41E70A9C35F4ACC268FFAC2ADF54FA1DA110B9" ++ " 19#)\n" ++ " (u #67CF0FD7635205DD80FA814EE9E9C267C17376BF3209FB5D1BC42890D2822A04" ++ " 479DAF4D5B6ED69D0F8D1AF94164D07F8CD52ECEFE880641FA0F41DDAB1785E4" ++ " A37A32F997A516480B4CD4F6482B9466A1765093ED95023CA32D5EDC1E34CEE9" ++ " AF595BC51FE43C4BF810FA225AF697FB473B83815966188A4312C048B885E3F7" ++ " #)))\n", ++ "(public-key\n" ++ " (rsa\n" ++ " (n #009F56231A3D82E3E7D613D59D53E9AB921BEF9F08A782AED0B6E46ADBC853EC" ++ " 7C71C422435A3CD8FA0DB9EFD55CD3295BADC4E8E2E2B94E15AE82866AB8ADE8" ++ " 7E469FAE76DC3577DE87F1F419C4EB41123DFAF8D16922D5EDBAD6E9076D5A1C" ++ " 958106F0AE5E2E9193C6B49124C64C2A241C4075D4AF16299EB87A6585BAE917" ++ " DEF27FCDD165764D069BC18D16527B29DAAB549F7BBED4A7C6A842D203ED6613" ++ " 6E2411744E432CD26D940132F25874483DCAEECDFD95744819CBCF1EA810681C" ++ " 42907EBCB1C7EAFBE75C87EC32C5413EA10476545D3FC7B2ADB1B66B7F200918" ++ " 664B0E5261C2895AA28B0DE321E921B3F877172CCCAB81F43EF98002916156F6" ++ " CB#)\n" ++ " (e #010001#)))\n", ++ "(data\n (flags pkcs1)\n" ++ " (hash sha1 #11223344556677889900AABBCCDDEEFF10203040#))\n", ++ 1 ++ }, ++ { /* RSA with unknown hash for signing */ ++ "(private-key" ++ " (rsa" ++ " (n #009F56231A3D82E3E7D613D59D53E9AB921BEF9F08A782AED0B6E46ADBC853EC" ++ " 7C71C422435A3CD8FA0DB9EFD55CD3295BADC4E8E2E2B94E15AE82866AB8ADE8" ++ " 7E469FAE76DC3577DE87F1F419C4EB41123DFAF8D16922D5EDBAD6E9076D5A1C" ++ " 958106F0AE5E2E9193C6B49124C64C2A241C4075D4AF16299EB87A6585BAE917" ++ " DEF27FCDD165764D069BC18D16527B29DAAB549F7BBED4A7C6A842D203ED6613" ++ " 6E2411744E432CD26D940132F25874483DCAEECDFD95744819CBCF1EA810681C" ++ " 42907EBCB1C7EAFBE75C87EC32C5413EA10476545D3FC7B2ADB1B66B7F200918" ++ " 664B0E5261C2895AA28B0DE321E921B3F877172CCCAB81F43EF98002916156F6" ++ " CB#)\n" ++ " (e #010001#)\n" ++ " (d #07EF82500C403899934FE993AC5A36F14FF2DF38CF1EF315F205EE4C83EDAA19" ++ " 8890FC23DE9AA933CAFB37B6A8A8DBA675411958337287310D3FF2F1DDC0CB93" ++ " 7E70F57F75F833C021852B631D2B9A520E4431A03C5C3FCB5742DCD841D9FB12" ++ " 771AA1620DCEC3F1583426066ED9DC3F7028C5B59202C88FDF20396E2FA0EC4F" ++ " 5A22D9008F3043673931BC14A5046D6327398327900867E39CC61B2D1AFE2F48" ++ " EC8E1E3861C68D257D7425F4E6F99ABD77D61F10CA100EFC14389071831B33DD" ++ " 69CC8EABEF860D1DC2AAA84ABEAE5DFC91BC124DAF0F4C8EF5BBEA436751DE84" ++ " 3A8063E827A024466F44C28614F93B0732A100D4A0D86D532FE1E22C7725E401" ++ " #)\n" ++ " (p #00C29D438F115825779631CD665A5739367F3E128ADC29766483A46CA80897E0" ++ " 79B32881860B8F9A6A04C2614A904F6F2578DAE13EA67CD60AE3D0AA00A1FF9B" ++ " 441485E44B2DC3D0B60260FBFE073B5AC72FAF67964DE15C8212C389D20DB9CF" ++ " 54AF6AEF5C4196EAA56495DD30CF709F499D5AB30CA35E086C2A1589D6283F17" ++ " 83#)\n" ++ " (q #00D1984135231CB243FE959C0CBEF551EDD986AD7BEDF71EDF447BE3DA27AF46" ++ " 79C974A6FA69E4D52FE796650623DE70622862713932AA2FD9F2EC856EAEAA77" ++ " 88B4EA6084DC81C902F014829B18EA8B2666EC41586818E0589E18876065F97E" ++ " 8D22CE2DA53A05951EC132DCEF41E70A9C35F4ACC268FFAC2ADF54FA1DA110B9" ++ " 19#)\n" ++ " (u #67CF0FD7635205DD80FA814EE9E9C267C17376BF3209FB5D1BC42890D2822A04" ++ " 479DAF4D5B6ED69D0F8D1AF94164D07F8CD52ECEFE880641FA0F41DDAB1785E4" ++ " A37A32F997A516480B4CD4F6482B9466A1765093ED95023CA32D5EDC1E34CEE9" ++ " AF595BC51FE43C4BF810FA225AF697FB473B83815966188A4312C048B885E3F7" ++ " #)))\n", ++ "(public-key\n" ++ " (rsa\n" ++ " (n #009F56231A3D82E3E7D613D59D53E9AB921BEF9F08A782AED0B6E46ADBC853EC" ++ " 7C71C422435A3CD8FA0DB9EFD55CD3295BADC4E8E2E2B94E15AE82866AB8ADE8" ++ " 7E469FAE76DC3577DE87F1F419C4EB41123DFAF8D16922D5EDBAD6E9076D5A1C" ++ " 958106F0AE5E2E9193C6B49124C64C2A241C4075D4AF16299EB87A6585BAE917" ++ " DEF27FCDD165764D069BC18D16527B29DAAB549F7BBED4A7C6A842D203ED6613" ++ " 6E2411744E432CD26D940132F25874483DCAEECDFD95744819CBCF1EA810681C" ++ " 42907EBCB1C7EAFBE75C87EC32C5413EA10476545D3FC7B2ADB1B66B7F200918" ++ " 664B0E5261C2895AA28B0DE321E921B3F877172CCCAB81F43EF98002916156F6" ++ " CB#)\n" ++ " (e #010001#)))\n", ++ "(data\n (flags pkcs1-raw)\n" ++ " (value " ++ "#00112233445566778899AABBCCDDEEFF000102030405060708090A0B0C0D0E0F#))\n", ++ 1 ++ }, ++ { /* RSA with compliant hash for signing */ ++ "(private-key" ++ " (rsa" ++ " (n #009F56231A3D82E3E7D613D59D53E9AB921BEF9F08A782AED0B6E46ADBC853EC" ++ " 7C71C422435A3CD8FA0DB9EFD55CD3295BADC4E8E2E2B94E15AE82866AB8ADE8" ++ " 7E469FAE76DC3577DE87F1F419C4EB41123DFAF8D16922D5EDBAD6E9076D5A1C" ++ " 958106F0AE5E2E9193C6B49124C64C2A241C4075D4AF16299EB87A6585BAE917" ++ " DEF27FCDD165764D069BC18D16527B29DAAB549F7BBED4A7C6A842D203ED6613" ++ " 6E2411744E432CD26D940132F25874483DCAEECDFD95744819CBCF1EA810681C" ++ " 42907EBCB1C7EAFBE75C87EC32C5413EA10476545D3FC7B2ADB1B66B7F200918" ++ " 664B0E5261C2895AA28B0DE321E921B3F877172CCCAB81F43EF98002916156F6" ++ " CB#)\n" ++ " (e #010001#)\n" ++ " (d #07EF82500C403899934FE993AC5A36F14FF2DF38CF1EF315F205EE4C83EDAA19" ++ " 8890FC23DE9AA933CAFB37B6A8A8DBA675411958337287310D3FF2F1DDC0CB93" ++ " 7E70F57F75F833C021852B631D2B9A520E4431A03C5C3FCB5742DCD841D9FB12" ++ " 771AA1620DCEC3F1583426066ED9DC3F7028C5B59202C88FDF20396E2FA0EC4F" ++ " 5A22D9008F3043673931BC14A5046D6327398327900867E39CC61B2D1AFE2F48" ++ " EC8E1E3861C68D257D7425F4E6F99ABD77D61F10CA100EFC14389071831B33DD" ++ " 69CC8EABEF860D1DC2AAA84ABEAE5DFC91BC124DAF0F4C8EF5BBEA436751DE84" ++ " 3A8063E827A024466F44C28614F93B0732A100D4A0D86D532FE1E22C7725E401" ++ " #)\n" ++ " (p #00C29D438F115825779631CD665A5739367F3E128ADC29766483A46CA80897E0" ++ " 79B32881860B8F9A6A04C2614A904F6F2578DAE13EA67CD60AE3D0AA00A1FF9B" ++ " 441485E44B2DC3D0B60260FBFE073B5AC72FAF67964DE15C8212C389D20DB9CF" ++ " 54AF6AEF5C4196EAA56495DD30CF709F499D5AB30CA35E086C2A1589D6283F17" ++ " 83#)\n" ++ " (q #00D1984135231CB243FE959C0CBEF551EDD986AD7BEDF71EDF447BE3DA27AF46" ++ " 79C974A6FA69E4D52FE796650623DE70622862713932AA2FD9F2EC856EAEAA77" ++ " 88B4EA6084DC81C902F014829B18EA8B2666EC41586818E0589E18876065F97E" ++ " 8D22CE2DA53A05951EC132DCEF41E70A9C35F4ACC268FFAC2ADF54FA1DA110B9" ++ " 19#)\n" ++ " (u #67CF0FD7635205DD80FA814EE9E9C267C17376BF3209FB5D1BC42890D2822A04" ++ " 479DAF4D5B6ED69D0F8D1AF94164D07F8CD52ECEFE880641FA0F41DDAB1785E4" ++ " A37A32F997A516480B4CD4F6482B9466A1765093ED95023CA32D5EDC1E34CEE9" ++ " AF595BC51FE43C4BF810FA225AF697FB473B83815966188A4312C048B885E3F7" ++ " #)))\n", ++ "(public-key\n" ++ " (rsa\n" ++ " (n #009F56231A3D82E3E7D613D59D53E9AB921BEF9F08A782AED0B6E46ADBC853EC" ++ " 7C71C422435A3CD8FA0DB9EFD55CD3295BADC4E8E2E2B94E15AE82866AB8ADE8" ++ " 7E469FAE76DC3577DE87F1F419C4EB41123DFAF8D16922D5EDBAD6E9076D5A1C" ++ " 958106F0AE5E2E9193C6B49124C64C2A241C4075D4AF16299EB87A6585BAE917" ++ " DEF27FCDD165764D069BC18D16527B29DAAB549F7BBED4A7C6A842D203ED6613" ++ " 6E2411744E432CD26D940132F25874483DCAEECDFD95744819CBCF1EA810681C" ++ " 42907EBCB1C7EAFBE75C87EC32C5413EA10476545D3FC7B2ADB1B66B7F200918" ++ " 664B0E5261C2895AA28B0DE321E921B3F877172CCCAB81F43EF98002916156F6" ++ " CB#)\n" ++ " (e #010001#)))\n", ++ "(data\n (flags pss)\n" ++ " (hash sha256 " ++ "#00112233445566778899AABBCCDDEEFF000102030405060708090A0B0C0D0E0F#))\n", ++ 0 ++ }, ++ { /* RSA with non-compliant hash for signing */ ++ "(private-key" ++ " (rsa" ++ " (n #009F56231A3D82E3E7D613D59D53E9AB921BEF9F08A782AED0B6E46ADBC853EC" ++ " 7C71C422435A3CD8FA0DB9EFD55CD3295BADC4E8E2E2B94E15AE82866AB8ADE8" ++ " 7E469FAE76DC3577DE87F1F419C4EB41123DFAF8D16922D5EDBAD6E9076D5A1C" ++ " 958106F0AE5E2E9193C6B49124C64C2A241C4075D4AF16299EB87A6585BAE917" ++ " DEF27FCDD165764D069BC18D16527B29DAAB549F7BBED4A7C6A842D203ED6613" ++ " 6E2411744E432CD26D940132F25874483DCAEECDFD95744819CBCF1EA810681C" ++ " 42907EBCB1C7EAFBE75C87EC32C5413EA10476545D3FC7B2ADB1B66B7F200918" ++ " 664B0E5261C2895AA28B0DE321E921B3F877172CCCAB81F43EF98002916156F6" ++ " CB#)\n" ++ " (e #010001#)\n" ++ " (d #07EF82500C403899934FE993AC5A36F14FF2DF38CF1EF315F205EE4C83EDAA19" ++ " 8890FC23DE9AA933CAFB37B6A8A8DBA675411958337287310D3FF2F1DDC0CB93" ++ " 7E70F57F75F833C021852B631D2B9A520E4431A03C5C3FCB5742DCD841D9FB12" ++ " 771AA1620DCEC3F1583426066ED9DC3F7028C5B59202C88FDF20396E2FA0EC4F" ++ " 5A22D9008F3043673931BC14A5046D6327398327900867E39CC61B2D1AFE2F48" ++ " EC8E1E3861C68D257D7425F4E6F99ABD77D61F10CA100EFC14389071831B33DD" ++ " 69CC8EABEF860D1DC2AAA84ABEAE5DFC91BC124DAF0F4C8EF5BBEA436751DE84" ++ " 3A8063E827A024466F44C28614F93B0732A100D4A0D86D532FE1E22C7725E401" ++ " #)\n" ++ " (p #00C29D438F115825779631CD665A5739367F3E128ADC29766483A46CA80897E0" ++ " 79B32881860B8F9A6A04C2614A904F6F2578DAE13EA67CD60AE3D0AA00A1FF9B" ++ " 441485E44B2DC3D0B60260FBFE073B5AC72FAF67964DE15C8212C389D20DB9CF" ++ " 54AF6AEF5C4196EAA56495DD30CF709F499D5AB30CA35E086C2A1589D6283F17" ++ " 83#)\n" ++ " (q #00D1984135231CB243FE959C0CBEF551EDD986AD7BEDF71EDF447BE3DA27AF46" ++ " 79C974A6FA69E4D52FE796650623DE70622862713932AA2FD9F2EC856EAEAA77" ++ " 88B4EA6084DC81C902F014829B18EA8B2666EC41586818E0589E18876065F97E" ++ " 8D22CE2DA53A05951EC132DCEF41E70A9C35F4ACC268FFAC2ADF54FA1DA110B9" ++ " 19#)\n" ++ " (u #67CF0FD7635205DD80FA814EE9E9C267C17376BF3209FB5D1BC42890D2822A04" ++ " 479DAF4D5B6ED69D0F8D1AF94164D07F8CD52ECEFE880641FA0F41DDAB1785E4" ++ " A37A32F997A516480B4CD4F6482B9466A1765093ED95023CA32D5EDC1E34CEE9" ++ " AF595BC51FE43C4BF810FA225AF697FB473B83815966188A4312C048B885E3F7" ++ " #)))\n", ++ "(public-key\n" ++ " (rsa\n" ++ " (n #009F56231A3D82E3E7D613D59D53E9AB921BEF9F08A782AED0B6E46ADBC853EC" ++ " 7C71C422435A3CD8FA0DB9EFD55CD3295BADC4E8E2E2B94E15AE82866AB8ADE8" ++ " 7E469FAE76DC3577DE87F1F419C4EB41123DFAF8D16922D5EDBAD6E9076D5A1C" ++ " 958106F0AE5E2E9193C6B49124C64C2A241C4075D4AF16299EB87A6585BAE917" ++ " DEF27FCDD165764D069BC18D16527B29DAAB549F7BBED4A7C6A842D203ED6613" ++ " 6E2411744E432CD26D940132F25874483DCAEECDFD95744819CBCF1EA810681C" ++ " 42907EBCB1C7EAFBE75C87EC32C5413EA10476545D3FC7B2ADB1B66B7F200918" ++ " 664B0E5261C2895AA28B0DE321E921B3F877172CCCAB81F43EF98002916156F6" ++ " CB#)\n" ++ " (e #010001#)))\n", ++ "(data\n (flags pss)\n" ++ " (hash sha1 #11223344556677889900AABBCCDDEEFF10203040#))\n", ++ 1 ++ } + }; + int tvidx; + gpg_error_t err; +-- +2.49.0 + diff --git a/libgcrypt-cipher-visibility-Differentiate-use-of-random-override-in-the-SLI.patch b/libgcrypt-cipher-visibility-Differentiate-use-of-random-override-in-the-SLI.patch new file mode 100644 index 0000000..413aa34 --- /dev/null +++ b/libgcrypt-cipher-visibility-Differentiate-use-of-random-override-in-the-SLI.patch @@ -0,0 +1,107 @@ +From 234eb316b0a04c50e8511a570775ded45060f18b Mon Sep 17 00:00:00 2001 +From: Lucas Mulling via Gcrypt-devel +Date: Wed, 26 Feb 2025 17:19:24 -0300 +Subject: [PATCH 08/14] cipher,visibility: Differentiate use of random-override + in the SLI +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* cipher/pubkey-util.c (_gcry_pk_util_data_to_mpi, +_gcry_pk_single_data_push, _gcry_pk_util_free_encoding_ctx): +Differentiate use of random-override in the SLI. +* src/visibility.c (gcry_pk_random_override_new): +Differentiate use explicit random override in the SLI. + +GnuPG-bug-id: 7338 +Signed-off-by: Lucas Mulling +Signed-off-by: Lucas Mülling +--- + cipher/pubkey-util.c | 33 +++++++++++++++++++++++++++++++++ + src/visibility.c | 12 ++++++++++++ + 2 files changed, 45 insertions(+) + +diff --git a/cipher/pubkey-util.c b/cipher/pubkey-util.c +index e7355569..66a04f13 100644 +--- a/cipher/pubkey-util.c ++++ b/cipher/pubkey-util.c +@@ -973,6 +973,17 @@ _gcry_pk_util_data_to_mpi (gcry_sexp_t input, gcry_mpi_t *ret_mpi, + list = sexp_find_token (ldata, "random-override", 0); + if (list) + { ++ if (fips_mode ()) ++ { ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) ++ { ++ sexp_release (list); ++ rc = GPG_ERR_INV_FLAG; ++ goto leave; ++ } ++ else ++ fips_service_indicator_mark_non_compliant (); ++ } + s = sexp_nth_data (list, 1, &n); + if (!s) + rc = GPG_ERR_NO_OBJ; +@@ -1149,6 +1160,17 @@ _gcry_pk_util_data_to_mpi (gcry_sexp_t input, gcry_mpi_t *ret_mpi, + list = sexp_find_token (ldata, "random-override", 0); + if (list) + { ++ if (fips_mode ()) ++ { ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) ++ { ++ sexp_release (list); ++ rc = GPG_ERR_INV_FLAG; ++ goto leave; ++ } ++ else ++ fips_service_indicator_mark_non_compliant (); ++ } + s = sexp_nth_data (list, 1, &n); + if (!s) + rc = GPG_ERR_NO_OBJ; +@@ -1248,6 +1270,17 @@ _gcry_pk_util_data_to_mpi (gcry_sexp_t input, gcry_mpi_t *ret_mpi, + list = sexp_find_token (ldata, "random-override", 0); + if (list) + { ++ if (fips_mode ()) ++ { ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) ++ { ++ sexp_release (list); ++ rc = GPG_ERR_INV_FLAG; ++ goto leave; ++ } ++ else ++ fips_service_indicator_mark_non_compliant (); ++ } + s = sexp_nth_data (list, 1, &n); + if (!s) + rc = GPG_ERR_NO_OBJ; +diff --git a/src/visibility.c b/src/visibility.c +index 4134446a..ccd0de69 100644 +--- a/src/visibility.c ++++ b/src/visibility.c +@@ -1085,6 +1085,18 @@ gcry_pk_hash_verify (gcry_sexp_t sigval, const char *data_tmpl, gcry_sexp_t pkey + gcry_error_t + gcry_pk_random_override_new (gcry_ctx_t *r_ctx, const unsigned char *p, size_t len) + { ++ if (!fips_is_operational ()) ++ return gpg_error (fips_not_operational ()); ++ fips_service_indicator_init (); ++ ++ if (fips_mode ()) ++ { ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) ++ return gpg_error (GPG_ERR_INV_OP); ++ else ++ fips_service_indicator_mark_non_compliant (); ++ } ++ + return gpg_error (_gcry_pk_single_data_push (r_ctx, p, len)); + } + +-- +2.49.0 + diff --git a/libgcrypt-doc-Add-about-GCRYCTL_FIPS_SERVICE_INDICATOR.patch b/libgcrypt-doc-Add-about-GCRYCTL_FIPS_SERVICE_INDICATOR.patch new file mode 100644 index 0000000..a9e9522 --- /dev/null +++ b/libgcrypt-doc-Add-about-GCRYCTL_FIPS_SERVICE_INDICATOR.patch @@ -0,0 +1,66 @@ +From 636f40cb78587635ef663bfc3430937cf140f245 Mon Sep 17 00:00:00 2001 +From: NIIBE Yutaka +Date: Thu, 13 Mar 2025 15:02:58 +0900 +Subject: [PATCH 13/14] doc: Add about GCRYCTL_FIPS_SERVICE_INDICATOR. +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* doc/gcrypt.texi (GCRYCTL_FIPS_SERVICE_INDICATOR): Add a description. +(GCRYCTL_FIPS_REJECT_NON_FIPS): Likewise. + +-- + +GnuPG-bug-id: 7338 +Signed-off-by: NIIBE Yutaka +Signed-off-by: Lucas Mülling +--- + doc/gcrypt.texi | 32 ++++++++++++++++++++++++++++++++ + 1 file changed, 32 insertions(+) + +diff --git a/doc/gcrypt.texi b/doc/gcrypt.texi +index 5d428738..6e82a41b 100644 +--- a/doc/gcrypt.texi ++++ b/doc/gcrypt.texi +@@ -1052,6 +1052,38 @@ is responsible to check also the internal members. For example: + /* ok */ + @end example + ++@item GCRYCTL_FIPS_SERVICE_INDICATOR; Arguments: none ++This commands provides ``dynamic'' service indicator. ++ ++After a function call (of the use of security services), this command ++can be used to check if the call is valid or not. If the computation ++is done in an approved way, it returns @code{GPG_ERR_NO_ERROR}. ++Otherwise @code{GPG_ERR_NOT_SUPPORTED} is returned. ++ ++An application may use this command directly or use the convenience ++macro below. ++ ++@deftypefun gcry_error_t gcry_get_fips_service_indicator (void) ++ ++Returns @code{GPG_ERR_NO_ERROR} if a preceeding function call is ++valid. Otherwise @code{GPG_ERR_NOT_SUPPORTED} is returned. ++@end deftypefun ++ ++@item GCRYCTL_FIPS_REJECT_NON_FIPS; Arguments: unsigned int flags ++In Libgcrypt 1.10, static implicit indicator is used; For an approved ++function (which can be checked by ++GCRYCTL_FIPS_SERVICE_INDICATOR_FUNCTION command) with an approved ++algo/operation (which can be checked GCRYCTL_FIPS_SERVICE_INDICATOR_* ++command), success of the function call means that it's valid and error ++return (rejection) means it's invalid. This command controls thread ++specific behavior of the rejection. ++ ++When using ``dynamic'' service indicator, this command with FLAGS=0 ++disables all rejections. ++@example ++ gcry_control (GCRYCTL_FIPS_REJECT_NON_FIPS, 0); ++@endexample ++ + @end table + + @end deftypefun +-- +2.49.0 + diff --git a/libgcrypt-doc-Fix-syntax-error.patch b/libgcrypt-doc-Fix-syntax-error.patch new file mode 100644 index 0000000..b85eb54 --- /dev/null +++ b/libgcrypt-doc-Fix-syntax-error.patch @@ -0,0 +1,31 @@ +From 22e65f6f5b8dbddf925151894426e4c06d33803b Mon Sep 17 00:00:00 2001 +From: Werner Koch +Date: Thu, 13 Mar 2025 18:06:37 +0100 +Subject: [PATCH 14/14] doc: Fix syntax error +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +-- + +Signed-off-by: Lucas Mülling +--- + doc/gcrypt.texi | 2 +- + 1 file changed, 1 insertion(+), 1 deletion(-) + +diff --git a/doc/gcrypt.texi b/doc/gcrypt.texi +index 6e82a41b..eeab1a78 100644 +--- a/doc/gcrypt.texi ++++ b/doc/gcrypt.texi +@@ -1082,7 +1082,7 @@ When using ``dynamic'' service indicator, this command with FLAGS=0 + disables all rejections. + @example + gcry_control (GCRYCTL_FIPS_REJECT_NON_FIPS, 0); +-@endexample ++@end example + + @end table + +-- +2.49.0 + diff --git a/libgcrypt-fips-Change-the-internal-API-for-new-FIPS-service-indicator.patch b/libgcrypt-fips-Change-the-internal-API-for-new-FIPS-service-indicator.patch new file mode 100644 index 0000000..8638218 --- /dev/null +++ b/libgcrypt-fips-Change-the-internal-API-for-new-FIPS-service-indicator.patch @@ -0,0 +1,140 @@ +From 4799914966a7f94f41e1ed5b7b62fded7ba09704 Mon Sep 17 00:00:00 2001 +From: NIIBE Yutaka +Date: Thu, 12 Dec 2024 11:03:38 +0900 +Subject: [PATCH 01/19] fips: Change the internal API for new FIPS service + indicator. +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* src/gcrypt-int.h (fips_service_indicator_init): Initialize by 0. +(fips_service_indicator_mark_success): Remove. +(fips_service_indicator_mark_non_compliant): New. +* cipher/kdf.c (_gcry_kdf_derive): Follow the change of the API. +* cipher/md.c (_gcry_md_hash_buffer): Likewise. +(_gcry_md_hash_buffers_extract): Likewise. + +-- + +GnuPG-bug-id: 7338 +Signed-off-by: NIIBE Yutaka +Signed-off-by: Lucas Mülling +--- + cipher/kdf.c | 17 +++++++++-------- + cipher/md.c | 8 ++++---- + src/gcrypt-int.h | 9 +++------ + 3 files changed, 16 insertions(+), 18 deletions(-) + +diff --git a/cipher/kdf.c b/cipher/kdf.c +index 1eae2b90..71156ea4 100644 +--- a/cipher/kdf.c ++++ b/cipher/kdf.c +@@ -248,6 +248,7 @@ _gcry_kdf_derive (const void *passphrase, size_t passphraselen, + size_t keysize, void *keybuffer) + { + gpg_err_code_t ec; ++ int is_compliant_algo = 0; + + if (!passphrase) + { +@@ -279,35 +280,32 @@ _gcry_kdf_derive (const void *passphrase, size_t passphraselen, + break; + + case GCRY_KDF_PBKDF2: ++ is_compliant_algo = 1; + if (!saltlen || !iterations) + ec = GPG_ERR_INV_VALUE; + else + { +- int is_compliant = 1; +- + if (fips_mode ()) + { + /* FIPS requires minimum passphrase length, see FIPS 140-3 IG D.N */ + if (passphraselen < 8) +- is_compliant &= 0; ++ fips_service_indicator_mark_non_compliant (); + + /* FIPS requires minimum salt length of 128 b (SP 800-132 sec. 5.1, p.6) */ + if (saltlen < 16) +- is_compliant &= 0; ++ fips_service_indicator_mark_non_compliant (); + + /* FIPS requires minimum iterations bound (SP 800-132 sec 5.2, p.6) */ + if (iterations < 1000) +- is_compliant &= 0; ++ fips_service_indicator_mark_non_compliant (); + + /* Check minimum key size */ + if (keysize < 14) +- is_compliant &= 0; ++ fips_service_indicator_mark_non_compliant (); + } + + ec = _gcry_kdf_pkdf2 (passphrase, passphraselen, subalgo, + salt, saltlen, iterations, keysize, keybuffer); +- if (!ec) +- fips_service_indicator_mark_success (is_compliant); + } + break; + +@@ -326,6 +324,9 @@ _gcry_kdf_derive (const void *passphrase, size_t passphraselen, + break; + } + ++ if (!ec && !is_compliant_algo && fips_mode ()) ++ fips_service_indicator_mark_non_compliant (); ++ + leave: + return ec; + } +diff --git a/cipher/md.c b/cipher/md.c +index c2bd18c6..ef2fc5a4 100644 +--- a/cipher/md.c ++++ b/cipher/md.c +@@ -1286,8 +1286,8 @@ _gcry_md_hash_buffer (int algo, void *digest, + + if (fips_mode ()) + { +- int is_compliant = spec->flags.fips; +- fips_service_indicator_mark_success (is_compliant); ++ if (!spec->flags.fips) ++ fips_service_indicator_mark_non_compliant (); + } + } + +@@ -1384,8 +1384,8 @@ _gcry_md_hash_buffers_extract (int algo, unsigned int flags, void *digest, + + if (fips_mode ()) + { +- int is_compliant = spec->flags.fips; +- fips_service_indicator_mark_success (is_compliant); ++ if (!spec->flags.fips) ++ fips_service_indicator_mark_non_compliant (); + } + + return 0; +diff --git a/src/gcrypt-int.h b/src/gcrypt-int.h +index 7f894737..aa49d766 100644 +--- a/src/gcrypt-int.h ++++ b/src/gcrypt-int.h +@@ -303,13 +303,10 @@ unsigned long _gcry_thread_context_get_fsi (void); + #define fips_service_indicator_init() do \ + { \ + if (fips_mode ()) \ +- _gcry_thread_context_set_fsi (1); \ +- } while (0) +-#define fips_service_indicator_mark_success(is_compliant) do \ +- { \ +- if (is_compliant && fips_mode ()) \ +- _gcry_thread_context_set_fsi (0); \ ++ _gcry_thread_context_set_fsi (0); \ + } while (0) ++/* Should be used only when fips_mode()==TRUE. */ ++#define fips_service_indicator_mark_non_compliant() _gcry_thread_context_set_fsi (1) + + /* Return a pointer to a string containing a description of the error + code in the error value ERR. */ +-- +2.49.0 + diff --git a/libgcrypt-fips-Fix-GCRY_FIPS_FLAG_REJECT_MD.patch b/libgcrypt-fips-Fix-GCRY_FIPS_FLAG_REJECT_MD.patch new file mode 100644 index 0000000..aa6f093 --- /dev/null +++ b/libgcrypt-fips-Fix-GCRY_FIPS_FLAG_REJECT_MD.patch @@ -0,0 +1,42 @@ +From b9eb8f4cb81801d68580627ad2188607a8c5f2ec Mon Sep 17 00:00:00 2001 +From: NIIBE Yutaka +Date: Thu, 13 Mar 2025 15:01:21 +0900 +Subject: [PATCH 12/14] fips: Fix GCRY_FIPS_FLAG_REJECT_MD. +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* src/gcrypt.h.in (GCRY_FIPS_FLAG_REJECT_MD): Include SHA1. + +-- + +Fixes-commit: 4ee91a94bcdad32aed4364d09e3daf8841fa579f +Signed-off-by: NIIBE Yutaka +Signed-off-by: Lucas Mülling +--- + src/gcrypt.h.in | 8 +++++--- + 1 file changed, 5 insertions(+), 3 deletions(-) + +diff --git a/src/gcrypt.h.in b/src/gcrypt.h.in +index b2b8853f..a9c36aa6 100644 +--- a/src/gcrypt.h.in ++++ b/src/gcrypt.h.in +@@ -1994,10 +1994,12 @@ char *gcry_get_config (int mode, const char *what); + #define GCRY_FIPS_FLAG_REJECT_PK_ECC_K (1 << 10) + #define GCRY_FIPS_FLAG_REJECT_PK_FLAGS (1 << 11) + +-#define GCRY_FIPS_FLAG_REJECT_MD \ +- (GCRY_FIPS_FLAG_REJECT_MD_MD5 | GCRY_FIPS_FLAG_REJECT_MD_OTHERS) ++#define GCRY_FIPS_FLAG_REJECT_MD \ ++ (GCRY_FIPS_FLAG_REJECT_MD_MD5 | GCRY_FIPS_FLAG_REJECT_MD_SHA1 \ ++ | GCRY_FIPS_FLAG_REJECT_MD_OTHERS) + +-/* Note: Don't reject MD5, PK MD, PK GOST, PK SM2, PK ECC K, and PK FLAGS */ ++/* Note: Don't reject MD5, PK MD, PK GOST, PK SM2, ++ SHA1, PK ECC K, and PK FLAGS */ + #define GCRY_FIPS_FLAG_REJECT_COMPAT110 \ + (GCRY_FIPS_FLAG_REJECT_MD_OTHERS \ + | GCRY_FIPS_FLAG_REJECT_MAC \ +-- +2.49.0 + diff --git a/libgcrypt-fips-Introduce-GCRYCTL_FIPS_REJECT_NON_FIPS.patch b/libgcrypt-fips-Introduce-GCRYCTL_FIPS_REJECT_NON_FIPS.patch new file mode 100644 index 0000000..d08a59a --- /dev/null +++ b/libgcrypt-fips-Introduce-GCRYCTL_FIPS_REJECT_NON_FIPS.patch @@ -0,0 +1,261 @@ +From e52adf0948c60b2e9accd7996fcece0f9b443763 Mon Sep 17 00:00:00 2001 +From: NIIBE Yutaka +Date: Thu, 19 Dec 2024 11:30:28 +0900 +Subject: [PATCH 12/19] fips: Introduce GCRYCTL_FIPS_REJECT_NON_FIPS. +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* src/gcrypt.h.in (GCRYCTL_FIPS_REJECT_NON_FIPS): New. +(GCRY_FIPS_FLAG_REJECT_*): New. +* src/fips.c (struct gcry_thread_context): Add flags_reject_non_fips. +(the_tc): Add initial value. +(_gcry_thread_context_set_reject): New. +(_gcry_thread_context_check_rejection): New. +* src/gcrypt-int.h (fips_check_rejection): New. +* src/global.c (_gcry_vcontrol): Handle GCRYCTL_FIPS_REJECT_NON_FIPS. +* tests/t-fips-service-ind.c (main): Use GCRYCTL_FIPS_REJECT_NON_FIPS. + +-- + +GnuPG-bug-id: 7338 +Signed-off-by: NIIBE Yutaka +Signed-off-by: Lucas Mülling +--- + cipher/ecc-curves.c | 7 ++++++- + cipher/pubkey.c | 34 ++++++++++++++++++++++++++-------- + src/fips.c | 17 ++++++++++++++++- + src/gcrypt-int.h | 9 ++++++++- + src/gcrypt.h.in | 28 ++++++++++++++++++++++++++-- + src/global.c | 7 +++++++ + tests/t-fips-service-ind.c | 2 ++ + 7 files changed, 91 insertions(+), 13 deletions(-) + +Index: libgcrypt-1.11.0/cipher/ecc-curves.c +=================================================================== +--- libgcrypt-1.11.0.orig/cipher/ecc-curves.c ++++ libgcrypt-1.11.0/cipher/ecc-curves.c +@@ -645,7 +645,12 @@ _gcry_ecc_fill_in_curve (unsigned int nb + possible to bypass this check by specifying the curve parameters + directly. */ + if (fips_mode () && !domain_parms[idx].fips ) +- fips_service_indicator_mark_non_compliant (); ++ { ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) ++ return GPG_ERR_NOT_SUPPORTED; ++ else ++ fips_service_indicator_mark_non_compliant (); ++ } + + switch (domain_parms[idx].model) + { +Index: libgcrypt-1.11.0/cipher/pubkey.c +=================================================================== +--- libgcrypt-1.11.0.orig/cipher/pubkey.c ++++ libgcrypt-1.11.0/cipher/pubkey.c +@@ -510,7 +510,12 @@ prepare_datasexp_to_be_signed (const cha + algo = _gcry_md_get_algo (hd); + + if (fips_mode () && algo == GCRY_MD_SHA1) +- fips_service_indicator_mark_non_compliant (); ++ { ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) ++ return GPG_ERR_DIGEST_ALGO; ++ else ++ fips_service_indicator_mark_non_compliant (); ++ } + + digest_name = _gcry_md_algo_name (algo); + digest_size = (int)_gcry_md_get_algo_dlen (algo); +@@ -538,7 +543,12 @@ prepare_datasexp_to_be_signed (const cha + return GPG_ERR_DIGEST_ALGO; + } + else if (fips_mode () && algo == GCRY_MD_SHA1) +- fips_service_indicator_mark_non_compliant (); ++ { ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) ++ return GPG_ERR_DIGEST_ALGO; ++ else ++ fips_service_indicator_mark_non_compliant (); ++ } + + digest_size = (int)_gcry_md_get_algo_dlen (algo); + digest = _gcry_md_read (hd, algo); +@@ -611,11 +621,15 @@ _gcry_pk_sign_md (gcry_sexp_t *r_sig, co + if (rc) + goto leave; + +- if (!spec->flags.fips && fips_mode ()) +- fips_service_indicator_mark_non_compliant (); +- + if (spec->flags.disabled) + rc = GPG_ERR_PUBKEY_ALGO; ++ else if (!spec->flags.fips && fips_mode ()) ++ { ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) ++ return GPG_ERR_PUBKEY_ALGO; ++ else ++ fips_service_indicator_mark_non_compliant (); ++ } + else if (spec->sign) + rc = spec->sign (r_sig, s_data, keyparms); + else +@@ -689,11 +703,15 @@ _gcry_pk_verify_md (gcry_sexp_t s_sig, c + if (rc) + goto leave; + +- if (!spec->flags.fips && fips_mode ()) +- fips_service_indicator_mark_non_compliant (); +- + if (spec->flags.disabled) + rc = GPG_ERR_PUBKEY_ALGO; ++ else if (!spec->flags.fips && fips_mode ()) ++ { ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) ++ return GPG_ERR_PUBKEY_ALGO; ++ else ++ fips_service_indicator_mark_non_compliant (); ++ } + else if (spec->verify) + rc = spec->verify (s_sig, s_data, keyparms); + else +Index: libgcrypt-1.11.0/src/fips.c +=================================================================== +--- libgcrypt-1.11.0.orig/src/fips.c ++++ libgcrypt-1.11.0/src/fips.c +@@ -70,15 +70,30 @@ static enum module_states current_state; + + struct gcry_thread_context { + unsigned long fips_service_indicator; ++ unsigned int flags_reject_non_fips; + }; + + #ifdef HAVE_GCC_STORAGE_CLASS__THREAD +-static __thread struct gcry_thread_context the_tc; ++static __thread struct gcry_thread_context the_tc = { ++ 0, GCRY_FIPS_FLAG_REJECT_DEFAULT ++}; + #else + #error libgcrypt requires thread-local storage to support FIPS mode + #endif + + void ++_gcry_thread_context_set_reject (unsigned int flags) ++{ ++ the_tc.flags_reject_non_fips = flags; ++} ++ ++int ++_gcry_thread_context_check_rejection (unsigned int flag) ++{ ++ return !!(the_tc.flags_reject_non_fips & flag); ++} ++ ++void + _gcry_thread_context_set_fsi (unsigned long fsi) + { + the_tc.fips_service_indicator = fsi; +Index: libgcrypt-1.11.0/src/gcrypt-int.h +=================================================================== +--- libgcrypt-1.11.0.orig/src/gcrypt-int.h ++++ libgcrypt-1.11.0/src/gcrypt-int.h +@@ -297,6 +297,12 @@ void _gcry_set_log_handler (gcry_handler + void _gcry_set_gettext_handler (const char *(*f)(const char*)); + void _gcry_set_progress_handler (gcry_handler_progress_t cb, void *cb_data); + ++void _gcry_thread_context_set_reject (unsigned int flags); ++int _gcry_thread_context_check_rejection (unsigned int flag); ++ ++#define fips_check_rejection(flag) \ ++ _gcry_thread_context_check_rejection (flag) ++ + void _gcry_thread_context_set_fsi (unsigned long fsi); + unsigned long _gcry_thread_context_get_fsi (void); + #define fips_service_indicator_init() do \ +@@ -305,7 +311,8 @@ unsigned long _gcry_thread_context_get_f + _gcry_thread_context_set_fsi (0); \ + } while (0) + /* Should be used only when fips_mode()==TRUE. */ +-#define fips_service_indicator_mark_non_compliant() _gcry_thread_context_set_fsi (1) ++#define fips_service_indicator_mark_non_compliant() \ ++ _gcry_thread_context_set_fsi (1) + + /* Return a pointer to a string containing a description of the error + code in the error value ERR. */ +Index: libgcrypt-1.11.0/src/gcrypt.h.in +=================================================================== +--- libgcrypt-1.11.0.orig/src/gcrypt.h.in ++++ libgcrypt-1.11.0/src/gcrypt.h.in +@@ -338,7 +338,8 @@ enum gcry_ctl_cmds + GCRYCTL_MD_CUSTOMIZE = 88, + GCRYCTL_FIPS_SERVICE_INDICATOR_PK = 89, + GCRYCTL_FIPS_SERVICE_INDICATOR_HASH = 90, +- GCRYCTL_FIPS_SERVICE_INDICATOR = 91 ++ GCRYCTL_FIPS_SERVICE_INDICATOR = 91, ++ GCRYCTL_FIPS_REJECT_NON_FIPS = 92 + }; + + /* Perform various operations defined by CMD. */ +@@ -1971,7 +1972,30 @@ void gcry_log_debugsxp (const char *text + char *gcry_get_config (int mode, const char *what); + + /* Convinience macro to access the FIPS service indicator. */ +-#define gcry_get_fips_service_indicator() gcry_control (GCRYCTL_FIPS_SERVICE_INDICATOR) ++#define gcry_get_fips_service_indicator() \ ++ gcry_control (GCRYCTL_FIPS_SERVICE_INDICATOR) ++ ++#define GCRY_FIPS_FLAG_REJECT_KDF (1 << 0) ++#define GCRY_FIPS_FLAG_REJECT_MD_MD5 (1 << 1) ++#define GCRY_FIPS_FLAG_REJECT_MD_OTHERS (1 << 2) ++#define GCRY_FIPS_FLAG_REJECT_MAC (1 << 3) ++#define GCRY_FIPS_FLAG_REJECT_CIPHER (1 << 4) ++#define GCRY_FIPS_FLAG_REJECT_PK (1 << 5) ++ ++#define GCRY_FIPS_FLAG_REJECT_MD \ ++ (GCRY_FIPS_FLAG_REJECT_MD_MD5 | GCRY_FIPS_FLAG_REJECT_MD_OTHERS) ++ ++/* Note: Don't reject MD5 */ ++#define GCRY_FIPS_FLAG_REJECT_COMPAT110 \ ++ (GCRY_FIPS_FLAG_REJECT_MD_OTHERS \ ++ | GCRY_FIPS_FLAG_REJECT_MAC \ ++ | GCRY_FIPS_FLAG_REJECT_CIPHER \ ++ | GCRY_FIPS_FLAG_REJECT_KDF \ ++ | GCRY_FIPS_FLAG_REJECT_PK) ++ ++#define GCRY_FIPS_FLAG_REJECT_DEFAULT \ ++ GCRY_FIPS_FLAG_REJECT_COMPAT110 ++ + + /* Log levels used by the internal logging facility. */ + enum gcry_log_levels +Index: libgcrypt-1.11.0/src/global.c +=================================================================== +--- libgcrypt-1.11.0.orig/src/global.c ++++ libgcrypt-1.11.0/src/global.c +@@ -791,6 +791,13 @@ _gcry_vcontrol (enum gcry_ctl_cmds cmd, + rc = _gcry_fips_indicator (); + break; + ++ case GCRYCTL_FIPS_REJECT_NON_FIPS: ++ { ++ unsigned int flags = va_arg (arg_ptr, unsigned int); ++ _gcry_thread_context_set_reject (flags); ++ } ++ break; ++ + case GCRYCTL_FIPS_SERVICE_INDICATOR_CIPHER: + /* Get FIPS Service Indicator for a given symmetric algorithm and + * optional mode. Returns GPG_ERR_NO_ERROR if algorithm is allowed or +Index: libgcrypt-1.11.0/tests/t-fips-service-ind.c +=================================================================== +--- libgcrypt-1.11.0.orig/tests/t-fips-service-ind.c ++++ libgcrypt-1.11.0/tests/t-fips-service-ind.c +@@ -1007,6 +1007,8 @@ main (int argc, char **argv) + if (debug) + xgcry_control ((GCRYCTL_SET_DEBUG_FLAGS, 1u , 0)); + ++ xgcry_control ((GCRYCTL_FIPS_REJECT_NON_FIPS, 0)); ++ + check_digests (); + check_kdf_derive (); + check_md_o_w_r_c (); diff --git a/libgcrypt-fips-Introduce-GCRYCTL_FIPS_SERVICE_INDICATOR-and-the-macro.patch b/libgcrypt-fips-Introduce-GCRYCTL_FIPS_SERVICE_INDICATOR-and-the-macro.patch new file mode 100644 index 0000000..9355299 --- /dev/null +++ b/libgcrypt-fips-Introduce-GCRYCTL_FIPS_SERVICE_INDICATOR-and-the-macro.patch @@ -0,0 +1,101 @@ +From f51f4e98930e6b2175e85fe8a95b8b6a15ad5efa Mon Sep 17 00:00:00 2001 +From: NIIBE Yutaka +Date: Thu, 5 Dec 2024 11:34:32 +0900 +Subject: [PATCH 2/5] fips: Introduce GCRYCTL_FIPS_SERVICE_INDICATOR and the + macro. +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* src/fips.c (_gcry_fips_indicator): New. +* src/g10lib.h (_gcry_fips_indicator): New. +* src/gcrypt.h.in (GCRYCTL_FIPS_SERVICE_INDICATOR): New. +(gcry_get_fips_service_indicator): New. +* src/global.c (_gcry_vcontrol): Handle GCRYCTL_FIPS_SERVICE_INDICATOR. + +-- + +GnuPG-bug-id: 7338 +Signed-off-by: NIIBE Yutaka +Signed-off-by: Lucas Mülling +--- + src/fips.c | 11 +++++++++++ + src/g10lib.h | 2 ++ + src/gcrypt.h.in | 6 +++++- + src/global.c | 4 ++++ + 4 files changed, 22 insertions(+), 1 deletion(-) + +Index: libgcrypt-1.11.0/src/fips.c +=================================================================== +--- libgcrypt-1.11.0.orig/src/fips.c ++++ libgcrypt-1.11.0/src/fips.c +@@ -364,6 +364,17 @@ _gcry_fips_test_operational (void) + return result; + } + ++gpg_err_code_t ++_gcry_fips_indicator (void) ++{ ++ /* If anything recorded, it means that the operation is not ++ supported under FIPS mode. */ ++ if (_gcry_thread_context_get_fsi ()) ++ return GPG_ERR_NOT_SUPPORTED; ++ ++ return 0; ++} ++ + int + _gcry_fips_indicator_cipher (va_list arg_ptr) + { +Index: libgcrypt-1.11.0/src/g10lib.h +=================================================================== +--- libgcrypt-1.11.0.orig/src/g10lib.h ++++ libgcrypt-1.11.0/src/g10lib.h +@@ -468,6 +468,8 @@ void _gcry_fips_signal_error (const char + _gcry_fips_signal_error (__FILE__, __LINE__, NULL, 1, (a)) + #endif + ++gpg_err_code_t _gcry_fips_indicator (void); ++ + int _gcry_fips_indicator_cipher (va_list arg_ptr); + int _gcry_fips_indicator_hash (va_list arg_ptr); + int _gcry_fips_indicator_mac (va_list arg_ptr); +Index: libgcrypt-1.11.0/src/gcrypt.h.in +=================================================================== +--- libgcrypt-1.11.0.orig/src/gcrypt.h.in ++++ libgcrypt-1.11.0/src/gcrypt.h.in +@@ -337,7 +337,8 @@ enum gcry_ctl_cmds + GCRYCTL_FIPS_SERVICE_INDICATOR_PK_FLAGS = 87, + GCRYCTL_MD_CUSTOMIZE = 88, + GCRYCTL_FIPS_SERVICE_INDICATOR_PK = 89, +- GCRYCTL_FIPS_SERVICE_INDICATOR_HASH = 90 ++ GCRYCTL_FIPS_SERVICE_INDICATOR_HASH = 90, ++ GCRYCTL_FIPS_SERVICE_INDICATOR = 91 + }; + + /* Perform various operations defined by CMD. */ +@@ -1966,6 +1967,9 @@ void gcry_log_debugsxp (const char *text + + char *gcry_get_config (int mode, const char *what); + ++/* Convinience macro to access the FIPS service indicator. */ ++#define gcry_get_fips_service_indicator() gcry_control (GCRYCTL_FIPS_SERVICE_INDICATOR) ++ + /* Log levels used by the internal logging facility. */ + enum gcry_log_levels + { +Index: libgcrypt-1.11.0/src/global.c +=================================================================== +--- libgcrypt-1.11.0.orig/src/global.c ++++ libgcrypt-1.11.0/src/global.c +@@ -787,6 +787,10 @@ _gcry_vcontrol (enum gcry_ctl_cmds cmd, + rc = _gcry_fips_run_selftests (1); + break; + ++ case GCRYCTL_FIPS_SERVICE_INDICATOR: ++ rc = _gcry_fips_indicator (); ++ break; ++ + case GCRYCTL_FIPS_SERVICE_INDICATOR_CIPHER: + /* Get FIPS Service Indicator for a given symmetric algorithm and + * optional mode. Returns GPG_ERR_NO_ERROR if algorithm is allowed or diff --git a/libgcrypt-fips-Introduce-an-internal-API-for-FIPS-service-indicator.patch b/libgcrypt-fips-Introduce-an-internal-API-for-FIPS-service-indicator.patch new file mode 100644 index 0000000..b452626 --- /dev/null +++ b/libgcrypt-fips-Introduce-an-internal-API-for-FIPS-service-indicator.patch @@ -0,0 +1,332 @@ +From e1cf3123282525693b646499eb7efe4f2be4010a Mon Sep 17 00:00:00 2001 +From: NIIBE Yutaka +Date: Thu, 5 Dec 2024 11:06:37 +0900 +Subject: [PATCH 1/5] fips: Introduce an internal API for FIPS service + indicator. +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* configure.ac (HAVE_GCC_STORAGE_CLASS__THREAD): New. +* src/fips.c (struct gcry_thread_context): New. +(_gcry_thread_context_set_fsi, _gcry_thread_context_get_fsi): New. +* src/gcrypt-int.h (fips_service_indicator_init): New macro. +(fips_service_indicator_mark_success): New macro. +* tests/Makefile.am (tests_bin): Add t-thread-local. +* tests/t-thread-local.c: New. + +-- + +GnuPG-bug-id: 7340 +Signed-off-by: NIIBE Yutaka +Signed-off-by: Lucas Mülling +--- + configure.ac | 14 +++ + src/fips.c | 21 ++++- + src/gcrypt-int.h | 12 +++ + tests/Makefile.am | 2 +- + tests/t-thread-local.c | 196 +++++++++++++++++++++++++++++++++++++++++ + 5 files changed, 243 insertions(+), 2 deletions(-) + create mode 100644 tests/t-thread-local.c + +diff --git a/configure.ac b/configure.ac +index a7f922b1..d708f89a 100644 +--- a/configure.ac ++++ b/configure.ac +@@ -1489,6 +1489,20 @@ if test "$gcry_cv_gcc_attribute_sysv_abi" = "yes" ; then + fi + fi + ++# ++# Check whether compiler support '__thread' storage class specifier. ++# ++AC_CACHE_CHECK([whether compiler supports '__thread' storage class specifier], ++ [gcry_cv_gcc_storage_class__thread], ++ [gcry_cv_gcc_storage_class__thread=no ++ AC_COMPILE_IFELSE([AC_LANG_PROGRAM([#include ], ++ [static __thread int bar;] ++ )], ++ [gcry_cv_gcc_storage_class__thread=yes])]) ++if test "$gcry_cv_gcc_storage_class__thread" = "yes" ; then ++ AC_DEFINE(HAVE_GCC_STORAGE_CLASS__THREAD,1, ++ [Defined if compiler supports "__thread" storage class specifier]) ++fi + + # Restore flags. + CFLAGS=$_gcc_cflags_save; +diff --git a/src/fips.c b/src/fips.c +index cf91baa8..58fb69df 100644 +--- a/src/fips.c ++++ b/src/fips.c +@@ -67,10 +67,29 @@ GPGRT_LOCK_DEFINE (fsm_lock); + used while in fips mode. Change this only while holding fsm_lock. */ + static enum module_states current_state; + ++struct gcry_thread_context { ++ unsigned long fips_service_indicator; ++}; ++ ++#ifdef HAVE_GCC_STORAGE_CLASS__THREAD ++static __thread struct gcry_thread_context the_tc; ++#else ++#error libgcrypt requires thread-local storage to support FIPS mode ++#endif ++ ++void ++_gcry_thread_context_set_fsi (unsigned long fsi) ++{ ++ the_tc.fips_service_indicator = fsi; ++} + ++unsigned long ++_gcry_thread_context_get_fsi (void) ++{ ++ return the_tc.fips_service_indicator; ++} + + +- + static void fips_new_state (enum module_states new_state); + + +diff --git a/src/gcrypt-int.h b/src/gcrypt-int.h +index 074ea071..7f894737 100644 +--- a/src/gcrypt-int.h ++++ b/src/gcrypt-int.h +@@ -298,6 +298,18 @@ void _gcry_set_log_handler (gcry_handler_log_t f, void *opaque); + void _gcry_set_gettext_handler (const char *(*f)(const char*)); + void _gcry_set_progress_handler (gcry_handler_progress_t cb, void *cb_data); + ++void _gcry_thread_context_set_fsi (unsigned long fsi); ++unsigned long _gcry_thread_context_get_fsi (void); ++#define fips_service_indicator_init() do \ ++ { \ ++ if (fips_mode ()) \ ++ _gcry_thread_context_set_fsi (1); \ ++ } while (0) ++#define fips_service_indicator_mark_success(is_compliant) do \ ++ { \ ++ if (is_compliant && fips_mode ()) \ ++ _gcry_thread_context_set_fsi (0); \ ++ } while (0) + + /* Return a pointer to a string containing a description of the error + code in the error value ERR. */ +diff --git a/tests/Makefile.am b/tests/Makefile.am +index 423bc1cd..52f7dd61 100644 +--- a/tests/Makefile.am ++++ b/tests/Makefile.am +@@ -25,7 +25,7 @@ tests_bin = \ + version t-secmem mpitests t-sexp t-convert \ + t-mpi-bit t-mpi-point t-lock \ + prime basic keygen pubkey hmac hashtest t-kdf keygrip \ +- aeswrap random t-kem t-mlkem ++ aeswrap random t-kem t-mlkem t-thread-local + + if USE_RSA + tests_bin += pkcs1v2 t-rsa-pss t-rsa-15 t-rsa-testparm +diff --git a/tests/t-thread-local.c b/tests/t-thread-local.c +new file mode 100644 +index 00000000..285f197f +--- /dev/null ++++ b/tests/t-thread-local.c +@@ -0,0 +1,196 @@ ++/* t-mlkem.c - Check the thread local storage ++ * Copyright (C) 2024 g10 Code GmbH ++ * ++ * This file is part of Libgcrypt. ++ * ++ * Libgcrypt is free software; you can redistribute it and/or modify ++ * it under the terms of the GNU Lesser General Public License as ++ * published by the Free Software Foundation; either version 2.1 of ++ * the License, or (at your option) any later version. ++ * ++ * Libgcrypt 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 Lesser General Public License for more details. ++ * ++ * You should have received a copy of the GNU Lesser General Public License ++ * along with this program; if not, see . ++ * SPDX-License-Identifier: LGPL-2.1+ ++ */ ++ ++/* For now, this program simply test __thread storage class specifier. ++ * After we implement thread local context for libgcrypt, we will ++ * modity to test the feature. */ ++ ++#ifdef HAVE_CONFIG_H ++#include ++#endif ++#include ++#include ++#include ++#include ++#include ++#include ++#if HAVE_PTHREAD ++# include ++#endif ++ ++#define PGM "t-thread-local" ++ ++#include "t-common.h" ++#include "../src/gcrypt-testapi.h" ++ ++/* Mingw requires us to include windows.h after winsock2.h which is ++ included by gcrypt.h. */ ++#ifdef _WIN32 ++# include ++#endif ++ ++#ifdef _WIN32 ++# define THREAD_RET_TYPE DWORD WINAPI ++# define THREAD_RET_VALUE 0 ++#else ++# define THREAD_RET_TYPE void * ++# define THREAD_RET_VALUE NULL ++#endif ++ ++#define N_TESTS 1 ++ ++#define N_THREADS 19 ++ ++static __thread unsigned long t; ++ ++struct thread_arg_s ++{ ++ int no; ++}; ++ ++#if defined(HAVE_PTHREAD) || defined(_WIN32) ++/* Checking the local storage thread. */ ++static THREAD_RET_TYPE ++check_ls_thread (void *argarg) ++{ ++ struct thread_arg_s *arg = argarg; ++ ++ t = arg->no; ++ info ("a thread update the local storage: %lu", t); ++ ++ gcry_free (arg); ++ return THREAD_RET_VALUE; ++} ++#endif ++ ++static void ++check_thread_local (void) ++{ ++ struct thread_arg_s *arg; ++ ++#ifdef _WIN32 ++ HANDLE threads[N_THREADS]; ++ int i; ++ int rc; ++ ++ t = N_THREADS; ++ for (i=0; i < N_THREADS; i++) ++ { ++ arg = gcry_xmalloc (sizeof *arg); ++ arg->no = i; ++ threads[i] = CreateThread (NULL, 0, check_ls_thread, arg, 0, NULL); ++ if (!threads[i]) ++ die ("error creating a thread %d: rc=%d", ++ i, (int)GetLastError ()); ++ } ++ ++ for (i=0; i < N_THREADS; i++) ++ { ++ rc = WaitForSingleObject (threads[i], INFINITE); ++ if (rc == WAIT_OBJECT_0) ++ info ("a thread %d has terminated", i); ++ else ++ fail ("waiting for a thread %d failed: %d", ++ i, (int)GetLastError ()); ++ CloseHandle (threads[i]); ++ } ++ ++#elif HAVE_PTHREAD ++ pthread_t threads[N_THREADS]; ++ int rc, i; ++ ++ t = N_THREADS; ++ for (i=0; i < N_THREADS; i++) ++ { ++ arg = gcry_xmalloc (sizeof *arg); ++ arg->no = i; ++ pthread_create (&threads[i], NULL, check_ls_thread, arg); ++ } ++ ++ for (i=0; i < N_THREADS; i++) ++ { ++ rc = pthread_join (threads[i], NULL); ++ if (rc) ++ fail ("pthread_join failed for a thread %d: %s", ++ i, strerror (errno)); ++ else ++ info ("a thread %d has terminated", i); ++ } ++#else ++ (void)arg; ++#endif /*!_WIN32*/ ++ if (t != N_THREADS) ++ fail ("failed t=%lu\n", t); ++ else ++ info ("success"); ++} ++ ++int ++main (int argc, char **argv) ++{ ++ int last_argc = -1; ++ ++ if (argc) ++ { argc--; argv++; } ++ ++ while (argc && last_argc != argc) ++ { ++ last_argc = argc; ++ if (!strcmp (*argv, "--")) ++ { ++ argc--; argv++; ++ break; ++ } ++ else if (!strcmp (*argv, "--help")) ++ { ++ fputs ("usage: " PGM " [options]\n" ++ "Options:\n" ++ " --verbose print timings etc.\n" ++ " --debug flyswatter\n", ++ stdout); ++ exit (0); ++ } ++ else if (!strcmp (*argv, "--verbose")) ++ { ++ verbose++; ++ argc--; argv++; ++ } ++ else if (!strcmp (*argv, "--debug")) ++ { ++ verbose += 2; ++ debug++; ++ argc--; argv++; ++ } ++ else if (!strncmp (*argv, "--", 2)) ++ die ("unknown option '%s'", *argv); ++ } ++ ++ xgcry_control ((GCRYCTL_DISABLE_SECMEM, 0)); ++ if (!gcry_check_version (GCRYPT_VERSION)) ++ die ("version mismatch\n"); ++ if (debug) ++ xgcry_control ((GCRYCTL_SET_DEBUG_FLAGS, 1u , 0)); ++ xgcry_control ((GCRYCTL_ENABLE_QUICK_RANDOM, 0)); ++ xgcry_control ((GCRYCTL_INITIALIZATION_FINISHED, 0)); ++ ++ check_thread_local (); ++ ++ return !!error_count; ++} +-- +2.49.0 + diff --git a/libgcrypt-fips-Rejection-by-GCRYCTL_FIPS_REJECT_NON_FIPS-not-by-open-flags.patch b/libgcrypt-fips-Rejection-by-GCRYCTL_FIPS_REJECT_NON_FIPS-not-by-open-flags.patch new file mode 100644 index 0000000..6d18f18 --- /dev/null +++ b/libgcrypt-fips-Rejection-by-GCRYCTL_FIPS_REJECT_NON_FIPS-not-by-open-flags.patch @@ -0,0 +1,498 @@ +From d060dd58b82882dec0d8bfcc593536bc0083b4b1 Mon Sep 17 00:00:00 2001 +From: NIIBE Yutaka +Date: Fri, 20 Dec 2024 09:38:13 +0900 +Subject: [PATCH 14/19] fips: Rejection by GCRYCTL_FIPS_REJECT_NON_FIPS, not by + open flags. +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* src/gcrypt.h.in (GCRY_CIPHER_FLAG_REJECT_NON_FIPS): Remove. +(GCRY_MD_FLAG_REJECT_NON_FIPS): Remove. +(GCRY_MAC_FLAG_REJECT_NON_FIPS): Remove. +* tests/t-fips-service-ind.c: Update tests with +GCRYCTL_FIPS_REJECT_NON_FIPS. +* cipher/cipher.c (_gcry_cipher_open_internal, cipher_setkey): Use +fips_check_rejection. +* cipher/mac.c (mac_open): Likewise. +* cipher/md.c (struct gcry_md_context): Remove reject_non_fips. +(md_open, md_enable): Use fips_check_rejection. +(_gcry_md_enable, md_copy): Likewise. + +-- + +GnuPG-bug-id: 7338 +Signed-off-by: NIIBE Yutaka +Signed-off-by: Lucas Mülling +--- + cipher/cipher.c | 8 ++-- + cipher/mac.c | 5 +-- + cipher/md.c | 81 ++++++++++++++++++++++++++++++-------- + src/gcrypt.h.in | 7 +--- + tests/t-fips-service-ind.c | 59 +++++++++++---------------- + 5 files changed, 94 insertions(+), 66 deletions(-) + +Index: libgcrypt-1.11.0/cipher/cipher.c +=================================================================== +--- libgcrypt-1.11.0.orig/cipher/cipher.c ++++ libgcrypt-1.11.0/cipher/cipher.c +@@ -510,7 +510,6 @@ _gcry_cipher_open_internal (gcry_cipher_ + int algo, int mode, unsigned int flags) + { + int secure = !!(flags & GCRY_CIPHER_SECURE); +- int reject_non_fips = !!(flags & GCRY_CIPHER_FLAG_REJECT_NON_FIPS); + gcry_cipher_spec_t *spec; + gcry_cipher_hd_t h = NULL; + gcry_err_code_t err; +@@ -526,7 +525,7 @@ _gcry_cipher_open_internal (gcry_cipher_ + err = GPG_ERR_CIPHER_ALGO; + else if (!spec->flags.fips && fips_mode ()) + { +- if (reject_non_fips) ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_CIPHER)) + err = GPG_ERR_CIPHER_ALGO; + else + { +@@ -544,8 +543,7 @@ _gcry_cipher_open_internal (gcry_cipher_ + | GCRY_CIPHER_ENABLE_SYNC + | GCRY_CIPHER_CBC_CTS + | GCRY_CIPHER_CBC_MAC +- | GCRY_CIPHER_EXTENDED +- | GCRY_CIPHER_FLAG_REJECT_NON_FIPS)) ++ | GCRY_CIPHER_EXTENDED)) + || ((flags & GCRY_CIPHER_CBC_CTS) && (flags & GCRY_CIPHER_CBC_MAC)))) + err = GPG_ERR_CIPHER_ALGO; + +@@ -776,7 +774,7 @@ cipher_setkey (gcry_cipher_hd_t c, byte + Key Generation Requirements" for details. */ + if (buf_eq_const (key, key + keylen, keylen)) + { +- if ((c->flags & GCRY_CIPHER_FLAG_REJECT_NON_FIPS)) ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_CIPHER)) + return GPG_ERR_WEAK_KEY; + else + fips_service_indicator_mark_non_compliant (); +Index: libgcrypt-1.11.0/cipher/mac.c +=================================================================== +--- libgcrypt-1.11.0.orig/cipher/mac.c ++++ libgcrypt-1.11.0/cipher/mac.c +@@ -519,7 +519,6 @@ mac_open (gcry_mac_hd_t * hd, int algo, + gcry_err_code_t err; + gcry_mac_hd_t h; + int secure = !!(flags & GCRY_MAC_FLAG_SECURE); +- int reject_non_fips = !!(flags & GCRY_MAC_FLAG_REJECT_NON_FIPS); + + spec = spec_from_algo (algo); + if (!spec) +@@ -528,7 +527,7 @@ mac_open (gcry_mac_hd_t * hd, int algo, + return GPG_ERR_MAC_ALGO; + else if (!spec->flags.fips && fips_mode ()) + { +- if (reject_non_fips) ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_MAC)) + return GPG_ERR_MAC_ALGO; + else + fips_service_indicator_mark_non_compliant (); +@@ -650,7 +649,7 @@ _gcry_mac_open (gcry_mac_hd_t * h, int a + gcry_err_code_t rc; + gcry_mac_hd_t hd = NULL; + +- if ((flags & ~(GCRY_MAC_FLAG_SECURE | GCRY_MAC_FLAG_REJECT_NON_FIPS))) ++ if ((flags & ~GCRY_MAC_FLAG_SECURE)) + rc = GPG_ERR_INV_ARG; + else + rc = mac_open (&hd, algo, flags, ctx); +Index: libgcrypt-1.11.0/cipher/md.c +=================================================================== +--- libgcrypt-1.11.0.orig/cipher/md.c ++++ libgcrypt-1.11.0/cipher/md.c +@@ -275,7 +275,6 @@ struct gcry_md_context + unsigned int finalized:1; + unsigned int bugemu1:1; + unsigned int hmac:1; +- unsigned int reject_non_fips:1; + } flags; + size_t actual_handle_size; /* Allocated size of this handle. */ + FILE *debug; +@@ -509,7 +508,6 @@ md_open (gcry_md_hd_t *h, int algo, unsi + ctx->flags.secure = secure; + ctx->flags.hmac = hmac; + ctx->flags.bugemu1 = !!(flags & GCRY_MD_FLAG_BUGEMU1); +- ctx->flags.reject_non_fips = !!(flags & GCRY_MD_FLAG_REJECT_NON_FIPS); + } + + if (! err) +@@ -544,14 +542,11 @@ _gcry_md_open (gcry_md_hd_t *h, int algo + + if ((flags & ~(GCRY_MD_FLAG_SECURE + | GCRY_MD_FLAG_HMAC +- | GCRY_MD_FLAG_REJECT_NON_FIPS + | GCRY_MD_FLAG_BUGEMU1))) + rc = GPG_ERR_INV_ARG; + else + rc = md_open (&hd, algo, flags); + +- *h = rc? NULL : hd; +- + if (!rc && fips_mode ()) + { + GcryDigestEntry *entry = hd->ctx->list; +@@ -566,9 +561,26 @@ _gcry_md_open (gcry_md_hd_t *h, int algo + } + + if (!is_compliant_algo) +- fips_service_indicator_mark_non_compliant (); ++ { ++ int reject = 0; ++ ++ if (algo == GCRY_MD_MD5) ++ reject = fips_check_rejection (GCRY_FIPS_FLAG_REJECT_MD_MD5); ++ else ++ reject = fips_check_rejection (GCRY_FIPS_FLAG_REJECT_MD_OTHERS); ++ ++ if (reject) ++ { ++ md_close (hd); ++ hd = NULL; ++ rc = GPG_ERR_DIGEST_ALGO; ++ } ++ else ++ fips_service_indicator_mark_non_compliant (); ++ } + } + ++ *h = rc? NULL : hd; + return rc; + } + +@@ -581,12 +593,17 @@ md_enable (gcry_md_hd_t hd, int algorith + const gcry_md_spec_t *spec; + GcryDigestEntry *entry; + gcry_err_code_t err = 0; +- int reject_non_fips = h->flags.reject_non_fips; ++ int reject; + + for (entry = h->list; entry; entry = entry->next) + if (entry->spec->algo == algorithm) + return 0; /* Already enabled */ + ++ if (algorithm == GCRY_MD_MD5) ++ reject = fips_check_rejection (GCRY_FIPS_FLAG_REJECT_MD_MD5); ++ else ++ reject = fips_check_rejection (GCRY_FIPS_FLAG_REJECT_MD_OTHERS); ++ + spec = spec_from_algo (algorithm); + if (!spec) + { +@@ -598,7 +615,7 @@ md_enable (gcry_md_hd_t hd, int algorith + err = GPG_ERR_DIGEST_ALGO; + + /* Any non-FIPS algorithm should go this way */ +- if (!err && reject_non_fips && !spec->flags.fips && fips_mode ()) ++ if (!err && reject && !spec->flags.fips && fips_mode ()) + err = GPG_ERR_DIGEST_ALGO; + + if (!err && h->flags.hmac && spec->read == NULL) +@@ -657,7 +674,19 @@ _gcry_md_enable (gcry_md_hd_t hd, int al + } + + if (!is_compliant_algo) +- fips_service_indicator_mark_non_compliant (); ++ { ++ int reject = 0; ++ ++ if (algorithm == GCRY_MD_MD5) ++ reject = fips_check_rejection (GCRY_FIPS_FLAG_REJECT_MD_MD5); ++ else ++ reject = fips_check_rejection (GCRY_FIPS_FLAG_REJECT_MD_OTHERS); ++ ++ if (reject) ++ rc = GPG_ERR_DIGEST_ALGO; ++ else ++ fips_service_indicator_mark_non_compliant (); ++ } + } + + return rc; +@@ -667,13 +696,14 @@ _gcry_md_enable (gcry_md_hd_t hd, int al + static gcry_err_code_t + md_copy (gcry_md_hd_t ahd, gcry_md_hd_t *b_hd) + { +- gcry_err_code_t err = 0; ++ gcry_err_code_t rc = 0; + struct gcry_md_context *a = ahd->ctx; + struct gcry_md_context *b; + GcryDigestEntry *ar, *br; + gcry_md_hd_t bhd; + size_t n; + int is_compliant_algo = 1; ++ int reject = 0; + + if (ahd->bufpos) + md_write (ahd, NULL, 0); +@@ -686,7 +716,7 @@ md_copy (gcry_md_hd_t ahd, gcry_md_hd_t + + if (!bhd) + { +- err = gpg_err_code_from_syserror (); ++ rc = gpg_err_code_from_syserror (); + goto leave; + } + +@@ -715,12 +745,20 @@ md_copy (gcry_md_hd_t ahd, gcry_md_hd_t + br = xtrymalloc (ar->actual_struct_size); + if (!br) + { +- err = gpg_err_code_from_syserror (); ++ rc = gpg_err_code_from_syserror (); + md_close (bhd); + goto leave; + } + +- is_compliant_algo &= spec->flags.fips; ++ if (!spec->flags.fips) ++ { ++ is_compliant_algo = 0; ++ ++ if (spec->algo == GCRY_MD_MD5) ++ reject |= fips_check_rejection (GCRY_FIPS_FLAG_REJECT_MD_MD5); ++ else ++ reject |= fips_check_rejection (GCRY_FIPS_FLAG_REJECT_MD_OTHERS); ++ } + + memcpy (br, ar, ar->actual_struct_size); + br->next = b->list; +@@ -730,13 +768,22 @@ md_copy (gcry_md_hd_t ahd, gcry_md_hd_t + if (a->debug) + md_start_debug (bhd, "unknown"); + +- *b_hd = bhd; ++ if (!is_compliant_algo && fips_mode ()) ++ { ++ if (reject) ++ { ++ rc = GPG_ERR_DIGEST_ALGO; ++ md_close (bhd); ++ } ++ else ++ fips_service_indicator_mark_non_compliant (); ++ } + +- if (!is_compliant_algo) +- fips_service_indicator_mark_non_compliant (); ++ if (!rc) ++ *b_hd = bhd; + + leave: +- return err; ++ return rc; + } + + +Index: libgcrypt-1.11.0/src/gcrypt.h.in +=================================================================== +--- libgcrypt-1.11.0.orig/src/gcrypt.h.in ++++ libgcrypt-1.11.0/src/gcrypt.h.in +@@ -995,8 +995,7 @@ enum gcry_cipher_flags + GCRY_CIPHER_ENABLE_SYNC = 2, /* Enable CFB sync mode. */ + GCRY_CIPHER_CBC_CTS = 4, /* Enable CBC cipher text stealing (CTS). */ + GCRY_CIPHER_CBC_MAC = 8, /* Enable CBC message auth. code (MAC). */ +- GCRY_CIPHER_EXTENDED = 16, /* Enable extended AES-WRAP. */ +- GCRY_CIPHER_FLAG_REJECT_NON_FIPS = 32 /* Reject non-FIPS-compliant algo. */ ++ GCRY_CIPHER_EXTENDED = 16 /* Enable extended AES-WRAP. */ + }; + + /* Methods used for AEAD IV generation. */ +@@ -1322,7 +1321,6 @@ enum gcry_md_flags + { + GCRY_MD_FLAG_SECURE = 1, /* Allocate all buffers in "secure" memory. */ + GCRY_MD_FLAG_HMAC = 2, /* Make an HMAC out of this algorithm. */ +- GCRY_MD_FLAG_REJECT_NON_FIPS = 4, /* Reject non-FIPS-compliant algo. */ + GCRY_MD_FLAG_BUGEMU1 = 0x0100 + }; + +@@ -1564,8 +1562,7 @@ enum gcry_mac_algos + /* Flags used with the open function. */ + enum gcry_mac_flags + { +- GCRY_MAC_FLAG_SECURE = 1, /* Allocate all buffers in "secure" memory. */ +- GCRY_MAC_FLAG_REJECT_NON_FIPS = 2 /* Reject non-FIPS-compliant algo. */ ++ GCRY_MAC_FLAG_SECURE = 1 /* Allocate all buffers in "secure" memory. */ + }; + + /* Create a MAC handle for algorithm ALGO. FLAGS may be given as an bitwise OR +Index: libgcrypt-1.11.0/tests/t-fips-service-ind.c +=================================================================== +--- libgcrypt-1.11.0.orig/tests/t-fips-service-ind.c ++++ libgcrypt-1.11.0/tests/t-fips-service-ind.c +@@ -250,7 +250,7 @@ check_pk_hash_sign_verify (void) + /* Check gcry_cipher_open, gcry_cipher_setkey, gcry_cipher_encrypt, + gcry_cipher_decrypt, gcry_cipher_close API. */ + static void +-check_cipher_o_s_e_d_c (void) ++check_cipher_o_s_e_d_c (int reject) + { + static struct { + int algo; +@@ -258,18 +258,12 @@ check_cipher_o_s_e_d_c (void) + int keylen; + const char *expect; + int expect_failure; +- unsigned int flags; + } tv[] = { + #if USE_DES + { GCRY_CIPHER_3DES, + "\xe3\x34\x7a\x6b\x0b\xc1\x15\x2c\x64\x2a\x25\xcb\xd3\xbc\x31\xab" + "\xfb\xa1\x62\xa8\x1f\x19\x7c\x15", 24, + "\x3f\x1a\xb8\x83\x18\x8b\xb5\x97", 1 }, +- { GCRY_CIPHER_3DES, +- "\xe3\x34\x7a\x6b\x0b\xc1\x15\x2c\x64\x2a\x25\xcb\xd3\xbc\x31\xab" +- "\xfb\xa1\x62\xa8\x1f\x19\x7c\x15", 24, +- "\x3f\x1a\xb8\x83\x18\x8b\xb5\x97", +- 1, GCRY_CIPHER_FLAG_REJECT_NON_FIPS }, + #endif + { GCRY_CIPHER_AES, + "\x2b\x7e\x15\x16\x28\xae\xd2\xa6\xab\xf7\x15\x88\x09\xcf\x4f\x3c", 16, +@@ -297,12 +291,10 @@ check_cipher_o_s_e_d_c (void) + assert (blklen != 0); + assert (blklen <= ptlen); + assert (blklen <= DIM (out)); +- err = gcry_cipher_open (&h, tv[tvidx].algo, GCRY_CIPHER_MODE_ECB, +- tv[tvidx].flags); ++ err = gcry_cipher_open (&h, tv[tvidx].algo, GCRY_CIPHER_MODE_ECB, 0); + if (err) + { +- if (in_fips_mode && (tv[tvidx].flags & GCRY_CIPHER_FLAG_REJECT_NON_FIPS) +- && tv[tvidx].expect_failure) ++ if (in_fips_mode && reject && tv[tvidx].expect_failure) + /* Here, an error is expected */ + ; + else +@@ -312,8 +304,7 @@ check_cipher_o_s_e_d_c (void) + } + else + { +- if (in_fips_mode && (tv[tvidx].flags & GCRY_CIPHER_FLAG_REJECT_NON_FIPS) +- && tv[tvidx].expect_failure) ++ if (in_fips_mode && reject && tv[tvidx].expect_failure) + /* This case, an error is expected, but we observed success */ + fail ("gcry_cipher_open test %d unexpectedly succeeded\n", tvidx); + } +@@ -398,7 +389,7 @@ check_cipher_o_s_e_d_c (void) + /* Check gcry_mac_open, gcry_mac_write, gcry_mac_write, gcry_mac_read, + gcry_mac_close API. */ + static void +-check_mac_o_w_r_c (void) ++check_mac_o_w_r_c (int reject) + { + static struct { + int algo; +@@ -408,14 +399,10 @@ check_mac_o_w_r_c (void) + int keylen; + const char *expect; + int expect_failure; +- unsigned int flags; + } tv[] = { + #if USE_MD5 + { GCRY_MAC_HMAC_MD5, "hmac input abc", 14, "hmac key input", 14, + "\x0d\x72\xd0\x60\xaf\x34\xf2\xca\x33\x58\xa9\xcc\xd3\x5a\xac\xb5", 1 }, +- { GCRY_MAC_HMAC_MD5, "hmac input abc", 14, "hmac key input", 14, +- "\x0d\x72\xd0\x60\xaf\x34\xf2\xca\x33\x58\xa9\xcc\xd3\x5a\xac\xb5", 1, +- GCRY_MAC_FLAG_REJECT_NON_FIPS }, + #endif + #if USE_SHA1 + { GCRY_MAC_HMAC_SHA1, "hmac input abc", 14, "hmac key input", 14, +@@ -471,11 +458,10 @@ check_mac_o_w_r_c (void) + expectlen = gcry_mac_get_algo_maclen (tv[tvidx].algo); + assert (expectlen != 0); + assert (expectlen <= DIM (mac)); +- err = gcry_mac_open (&h, tv[tvidx].algo, tv[tvidx].flags, NULL); ++ err = gcry_mac_open (&h, tv[tvidx].algo, 0, NULL); + if (err) + { +- if (in_fips_mode && (tv[tvidx].flags & GCRY_MAC_FLAG_REJECT_NON_FIPS) +- && tv[tvidx].expect_failure) ++ if (in_fips_mode && reject && tv[tvidx].expect_failure) + /* Here, an error is expected */ + ; + else +@@ -485,8 +471,7 @@ check_mac_o_w_r_c (void) + } + else + { +- if (in_fips_mode && (tv[tvidx].flags & GCRY_MAC_FLAG_REJECT_NON_FIPS) +- && tv[tvidx].expect_failure) ++ if (in_fips_mode && reject && tv[tvidx].expect_failure) + /* This case, an error is expected, but we observed success */ + fail ("gcry_mac_open test %d unexpectedly succeeded\n", tvidx); + } +@@ -563,7 +548,7 @@ check_mac_o_w_r_c (void) + /* Check gcry_md_open, gcry_md_write, gcry_md_write, gcry_md_read, + gcry_md_close API. */ + static void +-check_md_o_w_r_c (void) ++check_md_o_w_r_c (int reject) + { + static struct { + int algo; +@@ -571,14 +556,10 @@ check_md_o_w_r_c (void) + int datalen; + const char *expect; + int expect_failure; +- unsigned int flags; + } tv[] = { + #if USE_MD5 + { GCRY_MD_MD5, "abc", 3, + "\x90\x01\x50\x98\x3C\xD2\x4F\xB0\xD6\x96\x3F\x7D\x28\xE1\x7F\x72", 1 }, +- { GCRY_MD_MD5, "abc", 3, +- "\x90\x01\x50\x98\x3C\xD2\x4F\xB0\xD6\x96\x3F\x7D\x28\xE1\x7F\x72", 1, +- GCRY_MD_FLAG_REJECT_NON_FIPS }, + #endif + #if USE_SHA1 + { GCRY_MD_SHA1, "abc", 3, +@@ -632,11 +613,10 @@ check_md_o_w_r_c (void) + + expectlen = gcry_md_get_algo_dlen (tv[tvidx].algo); + assert (expectlen != 0); +- err = gcry_md_open (&h, tv[tvidx].algo, tv[tvidx].flags); ++ err = gcry_md_open (&h, tv[tvidx].algo, 0); + if (err) + { +- if (in_fips_mode && (tv[tvidx].flags & GCRY_MD_FLAG_REJECT_NON_FIPS) +- && tv[tvidx].expect_failure) ++ if (in_fips_mode && reject && tv[tvidx].expect_failure) + /* Here, an error is expected */ + ; + else +@@ -646,8 +626,7 @@ check_md_o_w_r_c (void) + } + else + { +- if (in_fips_mode && (tv[tvidx].flags & GCRY_MD_FLAG_REJECT_NON_FIPS) +- && tv[tvidx].expect_failure) ++ if (in_fips_mode && reject && tv[tvidx].expect_failure) + /* This case, an error is expected, but we observed success */ + fail ("gcry_md_open test %d unexpectedly succeeded\n", tvidx); + } +@@ -1011,10 +990,18 @@ main (int argc, char **argv) + + check_digests (); + check_kdf_derive (); +- check_md_o_w_r_c (); +- check_mac_o_w_r_c (); +- check_cipher_o_s_e_d_c (); ++ check_md_o_w_r_c (0); ++ check_mac_o_w_r_c (0); ++ check_cipher_o_s_e_d_c (0); + check_pk_hash_sign_verify (); + ++ xgcry_control ((GCRYCTL_FIPS_REJECT_NON_FIPS, ++ (GCRY_FIPS_FLAG_REJECT_MD_MD5 ++ | GCRY_FIPS_FLAG_REJECT_COMPAT110))); ++ ++ check_md_o_w_r_c (1); ++ check_mac_o_w_r_c (1); ++ check_cipher_o_s_e_d_c (1); ++ + return !!error_count; + } diff --git a/libgcrypt-fips-cipher-Add-GCRY_FIPS_FLAG_REJECT_PK_FLAGS.patch b/libgcrypt-fips-cipher-Add-GCRY_FIPS_FLAG_REJECT_PK_FLAGS.patch new file mode 100644 index 0000000..310e5e5 --- /dev/null +++ b/libgcrypt-fips-cipher-Add-GCRY_FIPS_FLAG_REJECT_PK_FLAGS.patch @@ -0,0 +1,80 @@ +From 0414e126b939f0b11ecf441908d923e87c1caf02 Mon Sep 17 00:00:00 2001 +From: NIIBE Yutaka +Date: Thu, 6 Mar 2025 08:57:51 +0900 +Subject: [PATCH 06/14] fips,cipher: Add GCRY_FIPS_FLAG_REJECT_PK_FLAGS. +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* src/gcrypt.h.in (GCRY_FIPS_FLAG_REJECT_PK_FLAGS): New. +* cipher/pubkey-util.c (_gcry_pk_util_parse_flaglist): Keep the +behavior of 1.10. +* cipher/rsa.c (rsa_decrypt, rsa_sign): Likewise. + +-- + +GnuPG-bug-id: 7338 +Signed-off-by: NIIBE Yutaka +Signed-off-by: Lucas Mülling +--- + cipher/pubkey-util.c | 2 +- + cipher/rsa.c | 4 ++-- + src/gcrypt.h.in | 3 ++- + 3 files changed, 5 insertions(+), 4 deletions(-) + +diff --git a/cipher/pubkey-util.c b/cipher/pubkey-util.c +index 9c927638..e7355569 100644 +--- a/cipher/pubkey-util.c ++++ b/cipher/pubkey-util.c +@@ -202,7 +202,7 @@ _gcry_pk_util_parse_flaglist (gcry_sexp_t list, + + if (fips_mode () && igninvflag) + { +- if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK_FLAGS)) + rc = GPG_ERR_INV_FLAG; + else + fips_service_indicator_mark_non_compliant (); +diff --git a/cipher/rsa.c b/cipher/rsa.c +index dce76414..7e086df4 100644 +--- a/cipher/rsa.c ++++ b/cipher/rsa.c +@@ -1504,7 +1504,7 @@ rsa_decrypt (gcry_sexp_t *r_plain, gcry_sexp_t s_data, gcry_sexp_t keyparms) + { + if (fips_mode ()) + { +- if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK_FLAGS)) + { + rc = GPG_ERR_INV_FLAG; + goto leave; +@@ -1649,7 +1649,7 @@ rsa_sign (gcry_sexp_t *r_sig, gcry_sexp_t s_data, gcry_sexp_t keyparms) + { + if (fips_mode ()) + { +- if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK_FLAGS)) + { + rc = GPG_ERR_INV_FLAG; + goto leave; +diff --git a/src/gcrypt.h.in b/src/gcrypt.h.in +index fe3db16a..a282268d 100644 +--- a/src/gcrypt.h.in ++++ b/src/gcrypt.h.in +@@ -1991,11 +1991,12 @@ char *gcry_get_config (int mode, const char *what); + #define GCRY_FIPS_FLAG_REJECT_CIPHER_MODE (1 << 8) + /**/ + #define GCRY_FIPS_FLAG_REJECT_PK_ECC_K (1 << 10) ++#define GCRY_FIPS_FLAG_REJECT_PK_FLAGS (1 << 11) + + #define GCRY_FIPS_FLAG_REJECT_MD \ + (GCRY_FIPS_FLAG_REJECT_MD_MD5 | GCRY_FIPS_FLAG_REJECT_MD_OTHERS) + +-/* Note: Don't reject MD5, PK MD, PK GOST and PK SM2 */ ++/* Note: Don't reject MD5, PK MD, PK GOST, PK SM2, PK ECC K, and PK FLAGS */ + #define GCRY_FIPS_FLAG_REJECT_COMPAT110 \ + (GCRY_FIPS_FLAG_REJECT_MD_OTHERS \ + | GCRY_FIPS_FLAG_REJECT_MAC \ +-- +2.49.0 + diff --git a/libgcrypt-fips-cipher-Add-behavior-not-to-reject-but-mark-non-compliant.patch b/libgcrypt-fips-cipher-Add-behavior-not-to-reject-but-mark-non-compliant.patch new file mode 100644 index 0000000..9fc7734 --- /dev/null +++ b/libgcrypt-fips-cipher-Add-behavior-not-to-reject-but-mark-non-compliant.patch @@ -0,0 +1,300 @@ +From a776b692669af7a6c089779989b626c4795e30b0 Mon Sep 17 00:00:00 2001 +From: NIIBE Yutaka +Date: Fri, 20 Dec 2024 13:36:12 +0900 +Subject: [PATCH 15/19] fips,cipher: Add behavior not to reject but mark + non-compliant. +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* cipher/dsa.c (dsa_check_keysize): Check reject flag for rejection, +or mark non-comliant in FIPS mode. +* cipher/ecc-ecdsa.c (_gcry_ecc_ecdsa_sign): Likewise. +* cipher/ecc.c (ecc_sign, ecc_verify): Likewise. +* cipher/pubkey.c (_gcry_pk_encrypt, _gcry_pk_sign): Likewise. +(_gcry_pk_verify, _gcry_pk_testkey, _gcry_pk_genkey): Likewise. +(_gcry_pk_get_nbits, _gcry_pk_get_curve): Likewise. +* src/visibility.c (gcry_pk_encrypt): Initialize the indicator. +(gcry_pk_decrypt, gcry_pk_sign, gcry_pk_verify): Likewise. +(gcry_pk_testkey, gcry_pk_genkey), gcry_pk_get_nbits) +(gcry_pk_get_curve): Likewise. +-- + +GnuPG-bug-id: 7338 +Signed-off-by: NIIBE Yutaka +Signed-off-by: Lucas Mülling +--- + cipher/dsa.c | 7 ++++- + cipher/ecc-ecdsa.c | 5 +++- + cipher/ecc.c | 10 +++++-- + cipher/pubkey.c | 74 ++++++++++++++++++++++++++++++++++++++-------- + src/visibility.c | 9 +++++- + 5 files changed, 87 insertions(+), 18 deletions(-) + +diff --git a/cipher/dsa.c b/cipher/dsa.c +index e559f9f5..564edf8d 100644 +--- a/cipher/dsa.c ++++ b/cipher/dsa.c +@@ -150,7 +150,12 @@ static gpg_err_code_t + dsa_check_keysize (unsigned int nbits) + { + if (fips_mode () && nbits < 2048) +- return GPG_ERR_INV_VALUE; ++ { ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) ++ return GPG_ERR_INV_VALUE; ++ else ++ fips_service_indicator_mark_non_compliant (); ++ } + + return 0; + } +diff --git a/cipher/ecc-ecdsa.c b/cipher/ecc-ecdsa.c +index 871b0371..cb9a001c 100644 +--- a/cipher/ecc-ecdsa.c ++++ b/cipher/ecc-ecdsa.c +@@ -110,7 +110,10 @@ _gcry_ecc_ecdsa_sign (gcry_mpi_t input, gcry_mpi_t k_supplied, mpi_ec_t ec, + (hashalgo == GCRY_MD_SHAKE128 + || hashalgo == GCRY_MD_SHAKE256)) + { +- rc = GPG_ERR_DIGEST_ALGO; ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) ++ rc = GPG_ERR_DIGEST_ALGO; ++ else ++ fips_service_indicator_mark_non_compliant (); + goto leave; + } + +diff --git a/cipher/ecc.c b/cipher/ecc.c +index 65525207..8896afd0 100644 +--- a/cipher/ecc.c ++++ b/cipher/ecc.c +@@ -952,7 +952,10 @@ ecc_sign (gcry_sexp_t *r_sig, gcry_sexp_t s_data, gcry_sexp_t keyparms) + || (ec->dialect == ECC_DIALECT_SAFECURVE + && ctx.hash_algo != GCRY_MD_SHAKE256))) + { +- rc = GPG_ERR_DIGEST_ALGO; ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) ++ rc = GPG_ERR_DIGEST_ALGO; ++ else ++ fips_service_indicator_mark_non_compliant (); + goto leave; + } + } +@@ -1074,7 +1077,10 @@ ecc_verify (gcry_sexp_t s_sig, gcry_sexp_t s_data, gcry_sexp_t s_keyparms) + || (ec->dialect == ECC_DIALECT_SAFECURVE + && ctx.hash_algo != GCRY_MD_SHAKE256))) + { +- rc = GPG_ERR_DIGEST_ALGO; ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) ++ rc = GPG_ERR_DIGEST_ALGO; ++ else ++ fips_service_indicator_mark_non_compliant (); + goto leave; + } + } +diff --git a/cipher/pubkey.c b/cipher/pubkey.c +index 4d7743cc..aacf9f5a 100644 +--- a/cipher/pubkey.c ++++ b/cipher/pubkey.c +@@ -328,7 +328,12 @@ _gcry_pk_encrypt (gcry_sexp_t *r_ciph, gcry_sexp_t s_data, gcry_sexp_t s_pkey) + if (spec->flags.disabled) + rc = GPG_ERR_PUBKEY_ALGO; + else if (!spec->flags.fips && fips_mode ()) +- rc = GPG_ERR_PUBKEY_ALGO; ++ { ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) ++ rc = GPG_ERR_PUBKEY_ALGO; ++ else ++ fips_service_indicator_mark_non_compliant (); ++ } + else if (spec->encrypt) + rc = spec->encrypt (r_ciph, s_data, keyparms); + else +@@ -441,7 +446,12 @@ _gcry_pk_sign (gcry_sexp_t *r_sig, gcry_sexp_t s_hash, gcry_sexp_t s_skey) + if (spec->flags.disabled) + rc = GPG_ERR_PUBKEY_ALGO; + else if (!spec->flags.fips && fips_mode ()) +- rc = GPG_ERR_PUBKEY_ALGO; ++ { ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) ++ rc = GPG_ERR_PUBKEY_ALGO; ++ else ++ fips_service_indicator_mark_non_compliant (); ++ } + else if (spec->sign) + rc = spec->sign (r_sig, s_hash, keyparms); + else +@@ -663,7 +673,12 @@ _gcry_pk_verify (gcry_sexp_t s_sig, gcry_sexp_t s_hash, gcry_sexp_t s_pkey) + if (spec->flags.disabled) + rc = GPG_ERR_PUBKEY_ALGO; + else if (!spec->flags.fips && fips_mode ()) +- rc = GPG_ERR_PUBKEY_ALGO; ++ { ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) ++ rc = GPG_ERR_PUBKEY_ALGO; ++ else ++ fips_service_indicator_mark_non_compliant (); ++ } + else if (spec->verify) + rc = spec->verify (s_sig, s_hash, keyparms); + else +@@ -747,7 +762,12 @@ _gcry_pk_testkey (gcry_sexp_t s_key) + if (spec->flags.disabled) + rc = GPG_ERR_PUBKEY_ALGO; + else if (!spec->flags.fips && fips_mode ()) +- rc = GPG_ERR_PUBKEY_ALGO; ++ { ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) ++ rc = GPG_ERR_PUBKEY_ALGO; ++ else ++ fips_service_indicator_mark_non_compliant (); ++ } + else if (spec->check_secret_key) + rc = spec->check_secret_key (keyparms); + else +@@ -826,11 +846,21 @@ _gcry_pk_genkey (gcry_sexp_t *r_key, gcry_sexp_t s_parms) + spec = spec_from_name (name); + xfree (name); + name = NULL; +- if (!spec || spec->flags.disabled || (!spec->flags.fips && fips_mode ())) ++ if (!spec || spec->flags.disabled) + { + rc = GPG_ERR_PUBKEY_ALGO; /* Unknown algorithm. */ + goto leave; + } ++ else if (!spec->flags.fips && fips_mode ()) ++ { ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) ++ { ++ rc = GPG_ERR_PUBKEY_ALGO; ++ goto leave; ++ } ++ else ++ fips_service_indicator_mark_non_compliant (); ++ } + + if (spec->generate) + rc = spec->generate (list, r_key); +@@ -866,12 +896,22 @@ _gcry_pk_get_nbits (gcry_sexp_t key) + + if (spec_from_sexp (key, 0, &spec, &parms)) + return 0; /* Error - 0 is a suitable indication for that. */ ++ + if (spec->flags.disabled) +- return 0; +- if (!spec->flags.fips && fips_mode ()) +- return 0; ++ nbits = 0; /* Error */ ++ else if (!spec->flags.fips && fips_mode ()) ++ { ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) ++ nbits = 0; /* Error */ ++ else ++ { ++ fips_service_indicator_mark_non_compliant (); ++ nbits = spec->get_nbits (parms); ++ } ++ } ++ else ++ nbits = spec->get_nbits (parms); + +- nbits = spec->get_nbits (parms); + sexp_release (parms); + return nbits; + } +@@ -1004,10 +1044,18 @@ _gcry_pk_get_curve (gcry_sexp_t key, int iterator, unsigned int *r_nbits) + } + + if (spec->flags.disabled) +- return NULL; +- if (!spec->flags.fips && fips_mode ()) +- return NULL; +- if (spec->get_curve) ++ result = NULL; ++ else if (!spec->flags.fips && fips_mode ()) ++ { ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) ++ result = NULL; ++ else ++ { ++ fips_service_indicator_mark_non_compliant (); ++ result = spec->get_curve (keyparms, iterator, r_nbits); ++ } ++ } ++ else if (spec->get_curve) + result = spec->get_curve (keyparms, iterator, r_nbits); + + sexp_release (keyparms); +diff --git a/src/visibility.c b/src/visibility.c +index d22c8b59..e02d6cfe 100644 +--- a/src/visibility.c ++++ b/src/visibility.c +@@ -1022,6 +1022,7 @@ gcry_pk_encrypt (gcry_sexp_t *result, gcry_sexp_t data, gcry_sexp_t pkey) + *result = NULL; + return gpg_error (fips_not_operational ()); + } ++ fips_service_indicator_init (); + return gpg_error (_gcry_pk_encrypt (result, data, pkey)); + } + +@@ -1033,6 +1034,7 @@ gcry_pk_decrypt (gcry_sexp_t *result, gcry_sexp_t data, gcry_sexp_t skey) + *result = NULL; + return gpg_error (fips_not_operational ()); + } ++ fips_service_indicator_init (); + return gpg_error (_gcry_pk_decrypt (result, data, skey)); + } + +@@ -1044,6 +1046,7 @@ gcry_pk_sign (gcry_sexp_t *result, gcry_sexp_t data, gcry_sexp_t skey) + *result = NULL; + return gpg_error (fips_not_operational ()); + } ++ fips_service_indicator_init (); + return gpg_error (_gcry_pk_sign (result, data, skey)); + } + +@@ -1065,6 +1068,7 @@ gcry_pk_verify (gcry_sexp_t sigval, gcry_sexp_t data, gcry_sexp_t pkey) + { + if (!fips_is_operational ()) + return gpg_error (fips_not_operational ()); ++ fips_service_indicator_init (); + return gpg_error (_gcry_pk_verify (sigval, data, pkey)); + } + +@@ -1089,6 +1093,7 @@ gcry_pk_testkey (gcry_sexp_t key) + { + if (!fips_is_operational ()) + return gpg_error (fips_not_operational ()); ++ fips_service_indicator_init (); + return gpg_error (_gcry_pk_testkey (key)); + } + +@@ -1100,6 +1105,7 @@ gcry_pk_genkey (gcry_sexp_t *r_key, gcry_sexp_t s_parms) + *r_key = NULL; + return gpg_error (fips_not_operational ()); + } ++ fips_service_indicator_init (); + return gpg_error (_gcry_pk_genkey (r_key, s_parms)); + } + +@@ -1138,7 +1144,7 @@ gcry_pk_get_nbits (gcry_sexp_t key) + (void)fips_not_operational (); + return 0; + } +- ++ fips_service_indicator_init (); + return _gcry_pk_get_nbits (key); + } + +@@ -1161,6 +1167,7 @@ gcry_pk_get_curve (gcry_sexp_t key, int iterator, unsigned int *r_nbits) + (void)fips_not_operational (); + return NULL; + } ++ fips_service_indicator_init (); + return _gcry_pk_get_curve (key, iterator, r_nbits); + } + +-- +2.49.0 + diff --git a/libgcrypt-fips-cipher-Do-the-computation-when-marking-non-compliant.patch b/libgcrypt-fips-cipher-Do-the-computation-when-marking-non-compliant.patch new file mode 100644 index 0000000..8f71866 --- /dev/null +++ b/libgcrypt-fips-cipher-Do-the-computation-when-marking-non-compliant.patch @@ -0,0 +1,160 @@ +From 54a6617b3679cfeb6d986ddf3c9c73641929f02c Mon Sep 17 00:00:00 2001 +From: NIIBE Yutaka +Date: Tue, 4 Mar 2025 10:32:49 +0900 +Subject: [PATCH 4/4] fips,cipher: Do the computation when marking + non-compliant. +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* cipher/ecc-ecdsa.c (_gcry_ecc_ecdsa_sign): Continue the computation +when marking non-compliant. +* cipher/pubkey.c (_gcry_pk_encrypt, _gcry_pk_sign): Likewise. +(_gcry_pk_sign_md, _gcry_pk_verify, _gcry_pk_verify_md): Likewise. +(_gcry_pk_testkey): Likewise. + +-- + +Fixes-commit: a776b692669af7a6c089779989b626c4795e30b0 +GnuPG-bug-id: 7338 +Signed-off-by: NIIBE Yutaka +Signed-off-by: Lucas Mülling +--- + cipher/ecc-ecdsa.c | 6 ++++-- + cipher/pubkey.c | 48 ++++++++++++++++++++++++++++++++++------------ + 2 files changed, 40 insertions(+), 14 deletions(-) + +diff --git a/cipher/ecc-ecdsa.c b/cipher/ecc-ecdsa.c +index cb9a001c..9da8e6dc 100644 +--- a/cipher/ecc-ecdsa.c ++++ b/cipher/ecc-ecdsa.c +@@ -111,10 +111,12 @@ _gcry_ecc_ecdsa_sign (gcry_mpi_t input, gcry_mpi_t k_supplied, mpi_ec_t ec, + || hashalgo == GCRY_MD_SHAKE256)) + { + if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) +- rc = GPG_ERR_DIGEST_ALGO; ++ { ++ rc = GPG_ERR_DIGEST_ALGO; ++ goto leave; ++ } + else + fips_service_indicator_mark_non_compliant (); +- goto leave; + } + + /* Use Pornin's method for deterministic DSA. If this +diff --git a/cipher/pubkey.c b/cipher/pubkey.c +index c28ec124..3778f482 100644 +--- a/cipher/pubkey.c ++++ b/cipher/pubkey.c +@@ -330,11 +330,15 @@ _gcry_pk_encrypt (gcry_sexp_t *r_ciph, gcry_sexp_t s_data, gcry_sexp_t s_pkey) + else if (!spec->flags.fips && fips_mode ()) + { + if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) +- rc = GPG_ERR_PUBKEY_ALGO; ++ { ++ rc = GPG_ERR_PUBKEY_ALGO; ++ goto leave; ++ } + else + fips_service_indicator_mark_non_compliant (); + } +- else if (spec->encrypt) ++ ++ if (spec->encrypt) + rc = spec->encrypt (r_ciph, s_data, keyparms); + else + rc = GPG_ERR_NOT_IMPLEMENTED; +@@ -448,11 +452,15 @@ _gcry_pk_sign (gcry_sexp_t *r_sig, gcry_sexp_t s_hash, gcry_sexp_t s_skey) + else if (!spec->flags.fips && fips_mode ()) + { + if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) +- rc = GPG_ERR_PUBKEY_ALGO; ++ { ++ rc = GPG_ERR_PUBKEY_ALGO; ++ goto leave; ++ } + else + fips_service_indicator_mark_non_compliant (); + } +- else if (spec->sign) ++ ++ if (spec->sign) + rc = spec->sign (r_sig, s_hash, keyparms); + else + rc = GPG_ERR_NOT_IMPLEMENTED; +@@ -649,11 +657,15 @@ _gcry_pk_sign_md (gcry_sexp_t *r_sig, const char *tmpl, gcry_md_hd_t hd_orig, + else if (!spec->flags.fips && fips_mode ()) + { + if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) +- rc = GPG_ERR_PUBKEY_ALGO; ++ { ++ rc = GPG_ERR_PUBKEY_ALGO; ++ goto leave; ++ } + else + fips_service_indicator_mark_non_compliant (); + } +- else if (spec->sign) ++ ++ if (spec->sign) + rc = spec->sign (r_sig, s_data, keyparms); + else + rc = GPG_ERR_NOT_IMPLEMENTED; +@@ -688,11 +700,15 @@ _gcry_pk_verify (gcry_sexp_t s_sig, gcry_sexp_t s_hash, gcry_sexp_t s_pkey) + else if (!spec->flags.fips && fips_mode ()) + { + if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) +- rc = GPG_ERR_PUBKEY_ALGO; ++ { ++ rc = GPG_ERR_PUBKEY_ALGO; ++ goto leave; ++ } + else + fips_service_indicator_mark_non_compliant (); + } +- else if (spec->verify) ++ ++ if (spec->verify) + rc = spec->verify (s_sig, s_hash, keyparms); + else + rc = GPG_ERR_NOT_IMPLEMENTED; +@@ -736,11 +752,15 @@ _gcry_pk_verify_md (gcry_sexp_t s_sig, const char *tmpl, gcry_md_hd_t hd_orig, + else if (!spec->flags.fips && fips_mode ()) + { + if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) +- rc = GPG_ERR_PUBKEY_ALGO; ++ { ++ rc = GPG_ERR_PUBKEY_ALGO; ++ goto leave; ++ } + else + fips_service_indicator_mark_non_compliant (); + } +- else if (spec->verify) ++ ++ if (spec->verify) + rc = spec->verify (s_sig, s_data, keyparms); + else + rc = GPG_ERR_NOT_IMPLEMENTED; +@@ -777,11 +797,15 @@ _gcry_pk_testkey (gcry_sexp_t s_key) + else if (!spec->flags.fips && fips_mode ()) + { + if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) +- rc = GPG_ERR_PUBKEY_ALGO; ++ { ++ rc = GPG_ERR_PUBKEY_ALGO; ++ goto leave; ++ } + else + fips_service_indicator_mark_non_compliant (); + } +- else if (spec->check_secret_key) ++ ++ if (spec->check_secret_key) + rc = spec->check_secret_key (keyparms); + else + rc = GPG_ERR_NOT_IMPLEMENTED; +-- +2.49.0 + diff --git a/libgcrypt-fips-cipher-Fix-memory-leak-for-gcry_pk_hash_sign.patch b/libgcrypt-fips-cipher-Fix-memory-leak-for-gcry_pk_hash_sign.patch new file mode 100644 index 0000000..445136e --- /dev/null +++ b/libgcrypt-fips-cipher-Fix-memory-leak-for-gcry_pk_hash_sign.patch @@ -0,0 +1,76 @@ +From 5e925e6c348450bf80b4560abac9a035903bff59 Mon Sep 17 00:00:00 2001 +From: NIIBE Yutaka +Date: Mon, 6 Jan 2025 12:01:56 +0900 +Subject: [PATCH 19/19] fips,cipher: Fix memory leak for gcry_pk_hash_sign. +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* cipher/pubkey.c (prepare_datasexp_to_be_signed): Release +copied HD when error. + +-- + +GnuPG-bug-id: 7338 +Signed-off-by: NIIBE Yutaka +Signed-off-by: Lucas Mülling +--- + cipher/pubkey.c | 21 +++++++++++++++++---- + 1 file changed, 17 insertions(+), 4 deletions(-) + +diff --git a/cipher/pubkey.c b/cipher/pubkey.c +index aacf9f5a..c28ec124 100644 +--- a/cipher/pubkey.c ++++ b/cipher/pubkey.c +@@ -512,7 +512,10 @@ prepare_datasexp_to_be_signed (const char *tmpl, gcry_md_hd_t hd, + /* Check if it has fixed hash name or %s */ + s = strstr (tmpl, "(hash "); + if (s == NULL) +- return GPG_ERR_DIGEST_ALGO; ++ { ++ _gcry_md_close (hd); ++ return GPG_ERR_DIGEST_ALGO; ++ } + + s += 6; + if (!strncmp (s, "%s", 2)) +@@ -522,7 +525,10 @@ prepare_datasexp_to_be_signed (const char *tmpl, gcry_md_hd_t hd, + if (fips_mode () && algo == GCRY_MD_SHA1) + { + if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) +- return GPG_ERR_DIGEST_ALGO; ++ { ++ _gcry_md_close (hd); ++ return GPG_ERR_DIGEST_ALGO; ++ } + else + fips_service_indicator_mark_non_compliant (); + } +@@ -541,7 +547,11 @@ prepare_datasexp_to_be_signed (const char *tmpl, gcry_md_hd_t hd, + + digest_name_supplied = xtrymalloc (p - s + 1); + if (!digest_name_supplied) +- return gpg_error_from_syserror (); ++ { ++ rc = gpg_err_code_from_syserror (); ++ _gcry_md_close (hd); ++ return rc; ++ } + memcpy (digest_name_supplied, s, p - s); + digest_name_supplied[p - s] = 0; + +@@ -555,7 +565,10 @@ prepare_datasexp_to_be_signed (const char *tmpl, gcry_md_hd_t hd, + else if (fips_mode () && algo == GCRY_MD_SHA1) + { + if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) +- return GPG_ERR_DIGEST_ALGO; ++ { ++ _gcry_md_close (hd); ++ return GPG_ERR_DIGEST_ALGO; ++ } + else + fips_service_indicator_mark_non_compliant (); + } +-- +2.49.0 + diff --git a/libgcrypt-fips-cipher-Implement-FIPS-service-indicator-for-gcry_pk_hash_-API.patch b/libgcrypt-fips-cipher-Implement-FIPS-service-indicator-for-gcry_pk_hash_-API.patch new file mode 100644 index 0000000..0490e38 --- /dev/null +++ b/libgcrypt-fips-cipher-Implement-FIPS-service-indicator-for-gcry_pk_hash_-API.patch @@ -0,0 +1,360 @@ +From edb43bc290046bd22548bf69ae2fbeb453112e44 Mon Sep 17 00:00:00 2001 +From: NIIBE Yutaka +Date: Wed, 18 Dec 2024 14:18:26 +0900 +Subject: [PATCH 11/19] fips,cipher: Implement FIPS service indicator for + gcry_pk_hash_ API. +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* src/visibility.c (gcry_pk_hash_sign): Initialize the indicator. +(gcry_pk_hash_verify): Likewise. +* tests/t-fips-service-ind.c (check_pk_hash_sign_verify): New. +(main): Call check_pk_hash_sign_verify. +* cipher/ecc-curves.c (_gcry_ecc_fill_in_curve): Don't reject, but +mark non-compliance. +* cipher/pubkey.c (prepare_datasexp_to_be_signed): Likewise. +(_gcry_pk_sign_md, _gcry_pk_verify_md): Likewise. + +-- + +GnuPG-bug-id: 7338 +Signed-off-by: NIIBE Yutaka +Signed-off-by: Lucas Mülling +--- + cipher/ecc-curves.c | 2 +- + cipher/pubkey.c | 20 ++-- + src/visibility.c | 2 + + tests/t-fips-service-ind.c | 209 +++++++++++++++++++++++++++++++++++++ + 4 files changed, 222 insertions(+), 11 deletions(-) + +diff --git a/cipher/ecc-curves.c b/cipher/ecc-curves.c +index 17fa5505..ddf9cbe1 100644 +--- a/cipher/ecc-curves.c ++++ b/cipher/ecc-curves.c +@@ -645,7 +645,7 @@ _gcry_ecc_fill_in_curve (unsigned int nbits, const char *name, + possible to bypass this check by specifying the curve parameters + directly. */ + if (fips_mode () && !domain_parms[idx].fips ) +- return GPG_ERR_NOT_SUPPORTED; ++ fips_service_indicator_mark_non_compliant (); + + switch (domain_parms[idx].model) + { +diff --git a/cipher/pubkey.c b/cipher/pubkey.c +index 214bd611..e2e54199 100644 +--- a/cipher/pubkey.c ++++ b/cipher/pubkey.c +@@ -510,10 +510,7 @@ prepare_datasexp_to_be_signed (const char *tmpl, gcry_md_hd_t hd, + algo = _gcry_md_get_algo (hd); + + if (fips_mode () && algo == GCRY_MD_SHA1) +- { +- _gcry_md_close (hd); +- return GPG_ERR_DIGEST_ALGO; +- } ++ fips_service_indicator_mark_non_compliant (); + + digest_name = _gcry_md_algo_name (algo); + digest_size = (int)_gcry_md_get_algo_dlen (algo); +@@ -535,12 +532,13 @@ prepare_datasexp_to_be_signed (const char *tmpl, gcry_md_hd_t hd, + + algo = _gcry_md_map_name (digest_name_supplied); + xfree (digest_name_supplied); +- if (algo == 0 +- || (fips_mode () && algo == GCRY_MD_SHA1)) ++ if (algo == 0) + { + _gcry_md_close (hd); + return GPG_ERR_DIGEST_ALGO; + } ++ else if (fips_mode () && algo == GCRY_MD_SHA1) ++ fips_service_indicator_mark_non_compliant (); + + digest_size = (int)_gcry_md_get_algo_dlen (algo); + digest = _gcry_md_read (hd, algo); +@@ -613,10 +611,11 @@ _gcry_pk_sign_md (gcry_sexp_t *r_sig, const char *tmpl, gcry_md_hd_t hd_orig, + if (rc) + goto leave; + ++ if (!spec->flags.fips && fips_mode ()) ++ fips_service_indicator_mark_non_compliant (); ++ + if (spec->flags.disabled) + rc = GPG_ERR_PUBKEY_ALGO; +- else if (!spec->flags.fips && fips_mode ()) +- rc = GPG_ERR_PUBKEY_ALGO; + else if (spec->sign) + rc = spec->sign (r_sig, s_data, keyparms); + else +@@ -690,10 +689,11 @@ _gcry_pk_verify_md (gcry_sexp_t s_sig, const char *tmpl, gcry_md_hd_t hd_orig, + if (rc) + goto leave; + ++ if (!spec->flags.fips && fips_mode ()) ++ fips_service_indicator_mark_non_compliant (); ++ + if (spec->flags.disabled) + rc = GPG_ERR_PUBKEY_ALGO; +- else if (!spec->flags.fips && fips_mode ()) +- rc = GPG_ERR_PUBKEY_ALGO; + else if (spec->verify) + rc = spec->verify (s_sig, s_data, keyparms); + else +diff --git a/src/visibility.c b/src/visibility.c +index c9d07f0b..d22c8b59 100644 +--- a/src/visibility.c ++++ b/src/visibility.c +@@ -1056,6 +1056,7 @@ gcry_pk_hash_sign (gcry_sexp_t *result, const char *data_tmpl, gcry_sexp_t skey, + *result = NULL; + return gpg_error (fips_not_operational ()); + } ++ fips_service_indicator_init (); + return gpg_error (_gcry_pk_sign_md (result, data_tmpl, hd, skey, ctx)); + } + +@@ -1073,6 +1074,7 @@ gcry_pk_hash_verify (gcry_sexp_t sigval, const char *data_tmpl, gcry_sexp_t pkey + { + if (!fips_is_operational ()) + return gpg_error (fips_not_operational ()); ++ fips_service_indicator_init (); + return gpg_error (_gcry_pk_verify_md (sigval, data_tmpl, hd, pkey, ctx)); + } + +diff --git a/tests/t-fips-service-ind.c b/tests/t-fips-service-ind.c +index 4b13436f..9a22d696 100644 +--- a/tests/t-fips-service-ind.c ++++ b/tests/t-fips-service-ind.c +@@ -29,6 +29,7 @@ + + #define PGM "t-fips-service-ind" + ++#define NEED_HEX2BUFFER + #include "t-common.h" + static int in_fips_mode; + #define MAX_DATA_LEN 1040 +@@ -39,6 +40,213 @@ static int in_fips_mode; + # include + #endif + ++/* Check gcry_pk_hash_sign, gcry_pk_hash_verify API. */ ++static void ++check_pk_hash_sign_verify (void) ++{ ++ static struct { ++ int md_algo; ++ const char *prvkey; ++ const char *pubkey; ++ const char *data_tmpl; ++ const char *k; ++ int expect_failure; ++ int expect_failure_hash; ++ } tv[] = { ++ { /* non-compliant hash */ ++ GCRY_MD_BLAKE2B_512, ++ "(private-key (ecc (curve nistp256)" ++ " (d #519b423d715f8b581f4fa8ee59f4771a5b44c8130b4e3eacca54a56dda72b464#)))", ++ "(public-key (ecc (curve nistp256)" ++ " (q #041ccbe91c075fc7f4f033bfa248db8fccd3565de94bbfb12f3c59ff46c271bf83" ++ "ce4014c68811f9a21a1fdb2c0e6113e06db7ca93b7404e78dc7ccd5ca89a4ca9#)))", ++ "(data(flags raw)(hash %s %b)(label %b))", ++ "94a1bbb14b906a61a280f245f9e93c7f3b4a6247824f5d33b9670787642a68de", ++ 1, 1 ++ }, ++ { /* non-compliant curve */ ++ GCRY_MD_SHA256, ++ "(private-key (ecc (curve secp256k1)" ++ " (d #c2cdf0a8b0a83b35ace53f097b5e6e6a0a1f2d40535eff1cf434f52a43d59d8f#)))", ++ ++ "(public-key (ecc (curve secp256k1)" ++ " (q #046fcc37ea5e9e09fec6c83e5fbd7a745e3eee81d16ebd861c9e66f55518c19798" ++ "4e9f113c07f875691df8afc1029496fc4cb9509b39dcd38f251a83359cc8b4f7#)))", ++ "(data(flags raw)(hash %s %b)(label %b))", ++ "94a1bbb14b906a61a280f245f9e93c7f3b4a6247824f5d33b9670787642a68de", ++ 1, 0 ++ }, ++ { ++ GCRY_MD_SHA256, ++ "(private-key (ecc (curve nistp256)" ++ " (d #519b423d715f8b581f4fa8ee59f4771a5b44c8130b4e3eacca54a56dda72b464#)))", ++ "(public-key (ecc (curve nistp256)" ++ " (q #041ccbe91c075fc7f4f033bfa248db8fccd3565de94bbfb12f3c59ff46c271bf83" ++ "ce4014c68811f9a21a1fdb2c0e6113e06db7ca93b7404e78dc7ccd5ca89a4ca9#)))", ++ "(data(flags raw)(hash %s %b)(label %b))", ++ "94a1bbb14b906a61a280f245f9e93c7f3b4a6247824f5d33b9670787642a68de", ++ 0, 0 ++ } ++ }; ++ int tvidx; ++ gpg_error_t err; ++ gpg_err_code_t ec; ++ const char *msg = "Takerufuji Mikiya, who won the championship in March 2024"; ++ int msglen; ++ ++ msglen = strlen (msg); ++ for (tvidx=0; tvidx < DIM(tv); tvidx++) ++ { ++ gcry_md_hd_t hd = NULL; ++ gcry_sexp_t s_sk = NULL; ++ gcry_sexp_t s_pk = NULL; ++ void *buffer = NULL; ++ size_t buflen; ++ gcry_ctx_t ctx = NULL; ++ gcry_sexp_t s_sig= NULL; ++ ++ if (verbose) ++ info ("checking gcry_pk_hash_ test %d\n", tvidx); ++ ++ err = gcry_md_open (&hd, tv[tvidx].md_algo, 0); ++ if (err) ++ { ++ fail ("algo %d, gcry_md_open failed: %s\n", tv[tvidx].md_algo, ++ gpg_strerror (err)); ++ goto next; ++ } ++ ++ ec = gcry_get_fips_service_indicator (); ++ if (ec == GPG_ERR_INV_OP) ++ { ++ /* libgcrypt is old, no support of the FIPS service indicator. */ ++ fail ("gcry_pk_hash test %d unexpectedly failed to check the FIPS service indicator.\n", ++ tvidx); ++ goto next; ++ } ++ ++ if (in_fips_mode && !tv[tvidx].expect_failure_hash && ec) ++ { ++ /* Success with the FIPS service indicator == 0 expected, but != 0. */ ++ fail ("gcry_pk_hash test %d unexpectedly set the indicator in FIPS mode.\n", ++ tvidx); ++ goto next; ++ } ++ else if (in_fips_mode && tv[tvidx].expect_failure_hash && !ec) ++ { ++ /* Success with the FIPS service indicator != 0 expected, but == 0. */ ++ fail ("gcry_pk_hash test %d unexpectedly cleared the indicator in FIPS mode.\n", ++ tvidx); ++ goto next; ++ } ++ ++ err = gcry_sexp_build (&s_sk, NULL, tv[tvidx].prvkey); ++ if (err) ++ { ++ fail ("error building SEXP for test, %s: %s", ++ "sk", gpg_strerror (err)); ++ goto next; ++ } ++ ++ err = gcry_sexp_build (&s_pk, NULL, tv[tvidx].pubkey); ++ if (err) ++ { ++ fail ("error building SEXP for test, %s: %s", ++ "pk", gpg_strerror (err)); ++ goto next; ++ } ++ ++ if (!(buffer = hex2buffer (tv[tvidx].k, &buflen))) ++ { ++ fail ("error parsing for test, %s: %s", ++ "msg", "invalid hex string"); ++ goto next; ++ } ++ ++ err = gcry_pk_random_override_new (&ctx, buffer, buflen); ++ if (err) ++ { ++ fail ("error setting 'k' for test: %s", ++ gpg_strerror (err)); ++ goto next; ++ } ++ ++ gcry_md_write (hd, msg, msglen); ++ ++ err = gcry_pk_hash_sign (&s_sig, tv[tvidx].data_tmpl, s_sk, hd, ctx); ++ if (err) ++ { ++ fail ("gcry_pk_hash_sign failed: %s", gpg_strerror (err)); ++ goto next; ++ } ++ ++ ec = gcry_get_fips_service_indicator (); ++ if (ec == GPG_ERR_INV_OP) ++ { ++ /* libgcrypt is old, no support of the FIPS service indicator. */ ++ fail ("gcry_pk_hash test %d unexpectedly failed to check the FIPS service indicator.\n", ++ tvidx); ++ goto next; ++ } ++ ++ if (in_fips_mode && !tv[tvidx].expect_failure && ec) ++ { ++ /* Success with the FIPS service indicator == 0 expected, but != 0. */ ++ fail ("gcry_pk_hash test %d unexpectedly set the indicator in FIPS mode.\n", ++ tvidx); ++ goto next; ++ } ++ else if (in_fips_mode && tv[tvidx].expect_failure && !ec) ++ { ++ /* Success with the FIPS service indicator != 0 expected, but == 0. */ ++ fail ("gcry_pk_hash_sign test %d unexpectedly cleared the indicator in FIPS mode.\n", ++ tvidx); ++ goto next; ++ } ++ ++ err = gcry_pk_hash_verify (s_sig, tv[tvidx].data_tmpl, s_pk, hd, ctx); ++ if (err) ++ { ++ fail ("gcry_pk_hash_verify failed for test: %s", ++ gpg_strerror (err)); ++ goto next; ++ } ++ ++ ec = gcry_get_fips_service_indicator (); ++ if (ec == GPG_ERR_INV_OP) ++ { ++ /* libgcrypt is old, no support of the FIPS service indicator. */ ++ fail ("gcry_pk_hash test %d unexpectedly failed to check the FIPS service indicator.\n", ++ tvidx); ++ goto next; ++ } ++ ++ if (in_fips_mode && !tv[tvidx].expect_failure && ec) ++ { ++ /* Success with the FIPS service indicator == 0 expected, but != 0. */ ++ fail ("gcry_pk_hash test %d unexpectedly set the indicator in FIPS mode.\n", ++ tvidx); ++ goto next; ++ } ++ else if (in_fips_mode && tv[tvidx].expect_failure && !ec) ++ { ++ /* Success with the FIPS service indicator != 0 expected, but == 0. */ ++ fail ("gcry_pk_hash_verify test %d unexpectedly cleared the indicator in FIPS mode.\n", ++ tvidx); ++ goto next; ++ } ++ ++ next: ++ gcry_sexp_release (s_sig); ++ xfree (buffer); ++ gcry_ctx_release (ctx); ++ gcry_sexp_release (s_pk); ++ gcry_sexp_release (s_sk); ++ if (hd) ++ gcry_md_close (hd); ++ } ++} ++ + /* Check gcry_cipher_open, gcry_cipher_setkey, gcry_cipher_encrypt, + gcry_cipher_decrypt, gcry_cipher_close API. */ + static void +@@ -936,6 +1144,7 @@ main (int argc, char **argv) + check_md_o_w_r_c (); + check_mac_o_w_r_c (); + check_cipher_o_s_e_d_c (); ++ check_pk_hash_sign_verify (); + + return !!error_count; + } +-- +2.49.0 + diff --git a/libgcrypt-fips-cipher-Implement-new-FIPS-service-indicator-for-cipher_open.patch b/libgcrypt-fips-cipher-Implement-new-FIPS-service-indicator-for-cipher_open.patch new file mode 100644 index 0000000..2124c48 --- /dev/null +++ b/libgcrypt-fips-cipher-Implement-new-FIPS-service-indicator-for-cipher_open.patch @@ -0,0 +1,122 @@ +From 69a5d0ed18a3ddc6f297de783c7cef5ad2257df0 Mon Sep 17 00:00:00 2001 +From: NIIBE Yutaka +Date: Fri, 13 Dec 2024 14:40:53 +0900 +Subject: [PATCH 05/19] fips,cipher: Implement new FIPS service indicator for + cipher_open. +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* src/gcrypt.h.in (GCRY_CIPHER_FLAG_REJECT_NON_FIPS): New. +* cipher/cipher.c (_gcry_cipher_open_internal): Don't reject +but mark the service indicator in FIPS mode. +(cipher_setkey): Likewise. +* src/visibility.c (gcry_cipher_open): Initialize the service +indicator. +(gcry_cipher_setkey): Likewise. + +-- + +GnuPG-bug-id: 7338 +Signed-off-by: NIIBE Yutaka +Signed-off-by: Lucas Mülling +--- + cipher/cipher.c | 23 +++++++++++++++++++---- + src/gcrypt.h.in | 3 ++- + src/visibility.c | 4 ++-- + 3 files changed, 23 insertions(+), 7 deletions(-) + +diff --git a/cipher/cipher.c b/cipher/cipher.c +index 898bb58f..7ffacf05 100644 +--- a/cipher/cipher.c ++++ b/cipher/cipher.c +@@ -509,7 +509,8 @@ gcry_err_code_t + _gcry_cipher_open_internal (gcry_cipher_hd_t *handle, + int algo, int mode, unsigned int flags) + { +- int secure = (flags & GCRY_CIPHER_SECURE); ++ int secure = !!(flags & GCRY_CIPHER_SECURE); ++ int reject_non_fips = !!(flags & GCRY_CIPHER_FLAG_REJECT_NON_FIPS); + gcry_cipher_spec_t *spec; + gcry_cipher_hd_t h = NULL; + gcry_err_code_t err; +@@ -524,7 +525,15 @@ _gcry_cipher_open_internal (gcry_cipher_hd_t *handle, + else if (spec->flags.disabled) + err = GPG_ERR_CIPHER_ALGO; + else if (!spec->flags.fips && fips_mode ()) +- err = GPG_ERR_CIPHER_ALGO; ++ { ++ if (reject_non_fips) ++ err = GPG_ERR_CIPHER_ALGO; ++ else ++ { ++ fips_service_indicator_mark_non_compliant (); ++ err = 0; ++ } ++ } + else + err = 0; + +@@ -535,7 +544,8 @@ _gcry_cipher_open_internal (gcry_cipher_hd_t *handle, + | GCRY_CIPHER_ENABLE_SYNC + | GCRY_CIPHER_CBC_CTS + | GCRY_CIPHER_CBC_MAC +- | GCRY_CIPHER_EXTENDED)) ++ | GCRY_CIPHER_EXTENDED ++ | GCRY_CIPHER_FLAG_REJECT_NON_FIPS)) + || ((flags & GCRY_CIPHER_CBC_CTS) && (flags & GCRY_CIPHER_CBC_MAC)))) + err = GPG_ERR_CIPHER_ALGO; + +@@ -765,7 +775,12 @@ cipher_setkey (gcry_cipher_hd_t c, byte *key, size_t keylen) + See "Implementation Guidance for FIPS 140-2, A.9 XTS-AES + Key Generation Requirements" for details. */ + if (buf_eq_const (key, key + keylen, keylen)) +- return GPG_ERR_WEAK_KEY; ++ { ++ if ((c->flags & GCRY_CIPHER_FLAG_REJECT_NON_FIPS)) ++ return GPG_ERR_WEAK_KEY; ++ else ++ fips_service_indicator_mark_non_compliant (); ++ } + } + } + else if (c->mode == GCRY_CIPHER_MODE_SIV) +diff --git a/src/gcrypt.h.in b/src/gcrypt.h.in +index 2a378639..2ed9914b 100644 +--- a/src/gcrypt.h.in ++++ b/src/gcrypt.h.in +@@ -992,7 +992,8 @@ enum gcry_cipher_flags + GCRY_CIPHER_ENABLE_SYNC = 2, /* Enable CFB sync mode. */ + GCRY_CIPHER_CBC_CTS = 4, /* Enable CBC cipher text stealing (CTS). */ + GCRY_CIPHER_CBC_MAC = 8, /* Enable CBC message auth. code (MAC). */ +- GCRY_CIPHER_EXTENDED = 16 /* Enable extended AES-WRAP. */ ++ GCRY_CIPHER_EXTENDED = 16, /* Enable extended AES-WRAP. */ ++ GCRY_CIPHER_FLAG_REJECT_NON_FIPS = 32 /* Reject non-FIPS-compliant algo. */ + }; + + /* Methods used for AEAD IV generation. */ +diff --git a/src/visibility.c b/src/visibility.c +index 7699f14f..d219f1a6 100644 +--- a/src/visibility.c ++++ b/src/visibility.c +@@ -736,7 +736,7 @@ gcry_cipher_open (gcry_cipher_hd_t *handle, + *handle = NULL; + return gpg_error (fips_not_operational ()); + } +- ++ fips_service_indicator_init (); + return gpg_error (_gcry_cipher_open (handle, algo, mode, flags)); + } + +@@ -751,7 +751,7 @@ gcry_cipher_setkey (gcry_cipher_hd_t hd, const void *key, size_t keylen) + { + if (!fips_is_operational ()) + return gpg_error (fips_not_operational ()); +- ++ fips_service_indicator_init (); + return gcry_error (_gcry_cipher_setkey (hd, key, keylen)); + } + +-- +2.49.0 + diff --git a/libgcrypt-fips-ecc-Add-rejecting-or-marking-for-gcry_pk_get_curve.patch b/libgcrypt-fips-ecc-Add-rejecting-or-marking-for-gcry_pk_get_curve.patch new file mode 100644 index 0000000..27fd75b --- /dev/null +++ b/libgcrypt-fips-ecc-Add-rejecting-or-marking-for-gcry_pk_get_curve.patch @@ -0,0 +1,43 @@ +From c6a092abbe7bea315394b15f28fd231dae0e4d7c Mon Sep 17 00:00:00 2001 +From: NIIBE Yutaka +Date: Tue, 24 Dec 2024 17:01:45 +0900 +Subject: [PATCH 16/19] fips,ecc: Add rejecting or marking for + gcry_pk_get_curve. +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* cipher/ecc-curves.c (_gcry_ecc_get_curve): Check under FIPS mode. + +-- + +GnuPG-bug-id: 7338 +Signed-off-by: NIIBE Yutaka +Signed-off-by: Lucas Mülling +--- + cipher/ecc-curves.c | 9 +++++++++ + 1 file changed, 9 insertions(+) + +diff --git a/cipher/ecc-curves.c b/cipher/ecc-curves.c +index fe0a1eb2..975f6a07 100644 +--- a/cipher/ecc-curves.c ++++ b/cipher/ecc-curves.c +@@ -844,6 +844,15 @@ _gcry_ecc_get_curve (gcry_sexp_t keyparms, int iterator, unsigned int *r_nbits) + if (r_nbits) + *r_nbits = domain_parms[idx].nbits; + } ++ ++ if (fips_mode () && !domain_parms[idx].fips) ++ { ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) ++ return NULL; ++ else ++ fips_service_indicator_mark_non_compliant (); ++ } ++ + return result; + } + +-- +2.49.0 + diff --git a/libgcrypt-fips-ecc-Check-DATA-in-gcry_pk_sign-verify-in-FIPS-mode.patch b/libgcrypt-fips-ecc-Check-DATA-in-gcry_pk_sign-verify-in-FIPS-mode.patch new file mode 100644 index 0000000..310c5c9 --- /dev/null +++ b/libgcrypt-fips-ecc-Check-DATA-in-gcry_pk_sign-verify-in-FIPS-mode.patch @@ -0,0 +1,282 @@ +From 53c97483b17fee280e24f595bc0d82d9b362ffde Mon Sep 17 00:00:00 2001 +From: NIIBE Yutaka +Date: Thu, 26 Dec 2024 11:12:48 +0900 +Subject: [PATCH 18/19] fips,ecc: Check DATA in gcry_pk_sign/verify in FIPS + mode. +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* src/gcrypt.h.in (GCRY_FIPS_FLAG_REJECT_PK_MD): New. +(GCRY_FIPS_FLAG_REJECT_PK_GOST_SM2): New. + +* cipher/ecc.c (ecc_sign): Check if GOST or SM2. Check if hash is +compliant. +(ecc_verify): Likewise. +* tests/t-fips-service-ind.c (check_pk_s_v): Modify tests including +hash compliance. + +-- + +GnuPG-bug-id: 7338 +Signed-off-by: NIIBE Yutaka +Signed-off-by: Lucas Mülling +--- + cipher/ecc.c | 70 +++++++++++++++++++++++++++++++++++--- + src/gcrypt.h.in | 4 ++- + tests/t-fips-service-ind.c | 52 ++++++++++++++++++++-------- + 3 files changed, 107 insertions(+), 19 deletions(-) + +diff --git a/cipher/ecc.c b/cipher/ecc.c +index 8896afd0..525523ed 100644 +--- a/cipher/ecc.c ++++ b/cipher/ecc.c +@@ -941,6 +941,18 @@ ecc_sign (gcry_sexp_t *r_sig, gcry_sexp_t s_data, gcry_sexp_t keyparms) + if (rc) + goto leave; + ++ if (fips_mode () ++ && ((ctx.flags & PUBKEY_FLAG_GOST) || (ctx.flags & PUBKEY_FLAG_SM2))) ++ { ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK_GOST_SM2)) ++ { ++ rc = GPG_ERR_INV_DATA; ++ goto leave; ++ } ++ else ++ fips_service_indicator_mark_non_compliant (); ++ } ++ + /* Hash algo is determined by curve in EdDSA. */ + if ((ctx.flags & PUBKEY_FLAG_EDDSA)) + { +@@ -953,10 +965,12 @@ ecc_sign (gcry_sexp_t *r_sig, gcry_sexp_t s_data, gcry_sexp_t keyparms) + && ctx.hash_algo != GCRY_MD_SHAKE256))) + { + if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) +- rc = GPG_ERR_DIGEST_ALGO; ++ { ++ rc = GPG_ERR_DIGEST_ALGO; ++ goto leave; ++ } + else + fips_service_indicator_mark_non_compliant (); +- goto leave; + } + } + else +@@ -967,6 +981,23 @@ ecc_sign (gcry_sexp_t *r_sig, gcry_sexp_t s_data, gcry_sexp_t keyparms) + ctx.hash_algo = GCRY_MD_SHAKE256; + } + } ++ else ++ { ++ if (fips_mode ()) ++ { ++ if (_gcry_md_algo_info (ctx.hash_algo, GCRYCTL_TEST_ALGO, NULL, NULL) ++ || ctx.hash_algo == GCRY_MD_SHA1) ++ { ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK_MD)) ++ { ++ rc = GPG_ERR_DIGEST_ALGO; ++ goto leave; ++ } ++ else ++ fips_service_indicator_mark_non_compliant (); ++ } ++ } ++ } + + sig_r = mpi_new (0); + sig_s = mpi_new (0); +@@ -1066,6 +1097,18 @@ ecc_verify (gcry_sexp_t s_sig, gcry_sexp_t s_data, gcry_sexp_t s_keyparms) + if (DBG_CIPHER) + log_mpidump ("ecc_verify data", data); + ++ if (fips_mode () ++ && ((ctx.flags & PUBKEY_FLAG_GOST) || (ctx.flags & PUBKEY_FLAG_SM2))) ++ { ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK_GOST_SM2)) ++ { ++ rc = GPG_ERR_INV_DATA; ++ goto leave; ++ } ++ else ++ fips_service_indicator_mark_non_compliant (); ++ } ++ + /* Hash algo is determined by curve in EdDSA. */ + if ((ctx.flags & PUBKEY_FLAG_EDDSA)) + { +@@ -1078,10 +1121,12 @@ ecc_verify (gcry_sexp_t s_sig, gcry_sexp_t s_data, gcry_sexp_t s_keyparms) + && ctx.hash_algo != GCRY_MD_SHAKE256))) + { + if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) +- rc = GPG_ERR_DIGEST_ALGO; ++ { ++ rc = GPG_ERR_DIGEST_ALGO; ++ goto leave; ++ } + else + fips_service_indicator_mark_non_compliant (); +- goto leave; + } + } + else +@@ -1092,6 +1137,23 @@ ecc_verify (gcry_sexp_t s_sig, gcry_sexp_t s_data, gcry_sexp_t s_keyparms) + ctx.hash_algo = GCRY_MD_SHAKE256; + } + } ++ else ++ { ++ if (fips_mode ()) ++ { ++ if (_gcry_md_algo_info (ctx.hash_algo, GCRYCTL_TEST_ALGO, NULL, NULL) ++ || ctx.hash_algo == GCRY_MD_SHA1) ++ { ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK_MD)) ++ { ++ rc = GPG_ERR_DIGEST_ALGO; ++ goto leave; ++ } ++ else ++ fips_service_indicator_mark_non_compliant (); ++ } ++ } ++ } + + /* + * Extract the signature value. +diff --git a/src/gcrypt.h.in b/src/gcrypt.h.in +index 7bee45e9..fcb6a327 100644 +--- a/src/gcrypt.h.in ++++ b/src/gcrypt.h.in +@@ -1986,11 +1986,13 @@ char *gcry_get_config (int mode, const char *what); + #define GCRY_FIPS_FLAG_REJECT_MAC (1 << 3) + #define GCRY_FIPS_FLAG_REJECT_CIPHER (1 << 4) + #define GCRY_FIPS_FLAG_REJECT_PK (1 << 5) ++#define GCRY_FIPS_FLAG_REJECT_PK_MD (1 << 6) ++#define GCRY_FIPS_FLAG_REJECT_PK_GOST_SM2 (1 << 7) + + #define GCRY_FIPS_FLAG_REJECT_MD \ + (GCRY_FIPS_FLAG_REJECT_MD_MD5 | GCRY_FIPS_FLAG_REJECT_MD_OTHERS) + +-/* Note: Don't reject MD5 */ ++/* Note: Don't reject MD5, PK MD, PK GOST and PK SM2 */ + #define GCRY_FIPS_FLAG_REJECT_COMPAT110 \ + (GCRY_FIPS_FLAG_REJECT_MD_OTHERS \ + | GCRY_FIPS_FLAG_REJECT_MAC \ +diff --git a/tests/t-fips-service-ind.c b/tests/t-fips-service-ind.c +index 90d92c70..fe963fa5 100644 +--- a/tests/t-fips-service-ind.c ++++ b/tests/t-fips-service-ind.c +@@ -228,6 +228,7 @@ check_pk_s_v (int reject) + static struct { + const char *prvkey; + const char *pubkey; ++ const char *data; + int expect_failure; + } tv[] = { + { +@@ -236,6 +237,8 @@ check_pk_s_v (int reject) + "(public-key (ecc (curve nistp256)" + " (q #041ccbe91c075fc7f4f033bfa248db8fccd3565de94bbfb12f3c59ff46c271bf83" + "ce4014c68811f9a21a1fdb2c0e6113e06db7ca93b7404e78dc7ccd5ca89a4ca9#)))", ++ "(data (flags raw)(hash sha256 " ++ "#00112233445566778899AABBCCDDEEFF000102030405060708090A0B0C0D0E0F#))", + 0 + }, + { /* non-compliant curve */ +@@ -244,28 +247,40 @@ check_pk_s_v (int reject) + "(public-key (ecc (curve secp256k1)" + " (q #046fcc37ea5e9e09fec6c83e5fbd7a745e3eee81d16ebd861c9e66f55518c19798" + "4e9f113c07f875691df8afc1029496fc4cb9509b39dcd38f251a83359cc8b4f7#)))", ++ "(data (flags raw)(hash sha256 " ++ "#00112233445566778899AABBCCDDEEFF000102030405060708090A0B0C0D0E0F#))", + 1 +- } ++ }, ++ { /* non-compliant hash */ ++ "(private-key (ecc (curve nistp256)" ++ " (d #519b423d715f8b581f4fa8ee59f4771a5b44c8130b4e3eacca54a56dda72b464#)))", ++ "(public-key (ecc (curve nistp256)" ++ " (q #041ccbe91c075fc7f4f033bfa248db8fccd3565de94bbfb12f3c59ff46c271bf83" ++ "ce4014c68811f9a21a1fdb2c0e6113e06db7ca93b7404e78dc7ccd5ca89a4ca9#)))", ++ "(data (flags raw)(hash ripemd160 " ++ "#00112233445566778899AABBCCDDEEFF00010203#))", ++ 1 ++ }, ++ { /* non-compliant hash for signing */ ++ "(private-key (ecc (curve nistp256)" ++ " (d #519b423d715f8b581f4fa8ee59f4771a5b44c8130b4e3eacca54a56dda72b464#)))", ++ "(public-key (ecc (curve nistp256)" ++ " (q #041ccbe91c075fc7f4f033bfa248db8fccd3565de94bbfb12f3c59ff46c271bf83" ++ "ce4014c68811f9a21a1fdb2c0e6113e06db7ca93b7404e78dc7ccd5ca89a4ca9#)))", ++ "(data (flags raw)(hash sha1 " ++ "#00112233445566778899AABBCCDDEEFF00010203#))", ++ 1 ++ }, + }; + int tvidx; + gpg_error_t err; + gpg_err_code_t ec; +- const char *data = "(data (flags raw)" +- "(hash sha256 #00112233445566778899AABBCCDDEEFF000102030405060708090A0B0C0D0E0F#))"; +- gcry_sexp_t s_data = NULL; +- +- err = gcry_sexp_build (&s_data, NULL, data); +- if (err) +- { +- fail ("error building SEXP for test, %s: %s", +- "data", gpg_strerror (err)); +- return; +- } + + for (tvidx=0; tvidx < DIM(tv); tvidx++) + { + gcry_sexp_t s_pk = NULL; + gcry_sexp_t s_sk = NULL; ++ gcry_sexp_t s_data = NULL; + gcry_sexp_t s_sig= NULL; + + if (verbose) +@@ -287,6 +302,14 @@ check_pk_s_v (int reject) + goto next; + } + ++ err = gcry_sexp_build (&s_data, NULL, tv[tvidx].data); ++ if (err) ++ { ++ fail ("error building SEXP for test, %s: %s", ++ "data", gpg_strerror (err)); ++ goto next; ++ } ++ + err = gcry_pk_sign (&s_sig, s_data, s_sk); + if (err) + { +@@ -363,11 +386,10 @@ check_pk_s_v (int reject) + + next: + gcry_sexp_release (s_sig); ++ gcry_sexp_release (s_data); + gcry_sexp_release (s_pk); + gcry_sexp_release (s_sk); + } +- +- gcry_sexp_release (s_data); + } + + /* Check gcry_pk_hash_sign, gcry_pk_hash_verify API. */ +@@ -1461,6 +1483,8 @@ main (int argc, char **argv) + + xgcry_control ((GCRYCTL_FIPS_REJECT_NON_FIPS, + (GCRY_FIPS_FLAG_REJECT_MD_MD5 ++ | GCRY_FIPS_FLAG_REJECT_PK_MD ++ | GCRY_FIPS_FLAG_REJECT_PK_GOST_SM2 + | GCRY_FIPS_FLAG_REJECT_COMPAT110))); + + check_md_o_w_r_c (1); +-- +2.49.0 + diff --git a/libgcrypt-fips-kdf-Implement-new-FIPS-service-indicator-for-gcry_kdf_derive.patch b/libgcrypt-fips-kdf-Implement-new-FIPS-service-indicator-for-gcry_kdf_derive.patch new file mode 100644 index 0000000..a1710b9 --- /dev/null +++ b/libgcrypt-fips-kdf-Implement-new-FIPS-service-indicator-for-gcry_kdf_derive.patch @@ -0,0 +1,265 @@ +From 5cfa1aee5b98baf0d66333344e0fa45b79cca28b Mon Sep 17 00:00:00 2001 +From: NIIBE Yutaka +Date: Thu, 5 Dec 2024 14:52:17 +0900 +Subject: [PATCH 3/5] fips,kdf: Implement new FIPS service indicator for + gcry_kdf_derive. +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* cipher/kdf.c (_gcry_kdf_derive): Don't reject by GPG_ERR_INV_VALUE +but continue the computation, clearing IS_COMPLIANT. After successful +computation, call fips_service_indicator_mark_success with +IS_COMPLIANT. +* src/visibility.c (gcry_kdf_derive): Call fips_service_indicator_init. +* tests/t-kdf.c (check_fips_gcry_kdf_derive): New. +(main): Call check_fips_gcry_kdf_derive. + +-- + +GnuPG-bug-id: 7338 +Co-authored-by: David Sugar +Suggested-by: Stephan Mueller +Signed-off-by: NIIBE Yutaka +Signed-off-by: Lucas Mülling +--- + cipher/kdf.c | 33 ++++++----- + src/visibility.c | 1 + + tests/t-kdf.c | 149 ++++++++++++++++++++++++++++++++++++++++++++++- + 3 files changed, 169 insertions(+), 14 deletions(-) + +diff --git a/cipher/kdf.c b/cipher/kdf.c +index b4c5f83a..52e6a9ba 100644 +--- a/cipher/kdf.c ++++ b/cipher/kdf.c +@@ -279,28 +279,35 @@ _gcry_kdf_derive (const void *passphrase, size_t passphraselen, + break; + + case GCRY_KDF_PBKDF2: +- if (!saltlen) ++ if (!saltlen || !iterations) + ec = GPG_ERR_INV_VALUE; + else + { +- /* FIPS requires minimum passphrase length, see FIPS 140-3 IG D.N */ +- if (fips_mode () && passphraselen < 8) +- return GPG_ERR_INV_VALUE; ++ int is_compliant = 1; ++ ++ if (fips_mode ()) ++ { ++ /* FIPS requires minimum passphrase length, see FIPS 140-3 IG D.N */ ++ if (passphraselen < 8) ++ is_compliant &= 0; + +- /* FIPS requires minimum salt length of 128 b (SP 800-132 sec. 5.1, p.6) */ +- if (fips_mode () && saltlen < 16) +- return GPG_ERR_INV_VALUE; ++ /* FIPS requires minimum salt length of 128 b (SP 800-132 sec. 5.1, p.6) */ ++ if (saltlen < 16) ++ is_compliant &= 0; + +- /* FIPS requires minimum iterations bound (SP 800-132 sec 5.2, p.6) */ +- if (fips_mode () && iterations < 1000) +- return GPG_ERR_INV_VALUE; ++ /* FIPS requires minimum iterations bound (SP 800-132 sec 5.2, p.6) */ ++ if (iterations < 1000) ++ is_compliant &= 0; + +- /* Check minimum key size */ +- if (fips_mode () && keysize < 14) +- return GPG_ERR_INV_VALUE; ++ /* Check minimum key size */ ++ if (keysize < 14) ++ is_compliant &= 0; ++ } + + ec = _gcry_kdf_pkdf2 (passphrase, passphraselen, subalgo, + salt, saltlen, iterations, keysize, keybuffer); ++ if (!ec) ++ fips_service_indicator_mark_success (is_compliant); + } + break; + +diff --git a/src/visibility.c b/src/visibility.c +index 006e8f80..8f76b854 100644 +--- a/src/visibility.c ++++ b/src/visibility.c +@@ -1400,6 +1400,7 @@ gcry_kdf_derive (const void *passphrase, size_t passphraselen, + { + if (!fips_is_operational ()) + return gpg_error (fips_not_operational ()); ++ fips_service_indicator_init (); + return gpg_error (_gcry_kdf_derive (passphrase, passphraselen, algo, hashalgo, + salt, saltlen, iterations, + keysize, keybuffer)); +diff --git a/tests/t-kdf.c b/tests/t-kdf.c +index 10f64a7c..4b92bd30 100644 +--- a/tests/t-kdf.c ++++ b/tests/t-kdf.c +@@ -1927,6 +1927,151 @@ check_fips_indicators (void) + } + + ++static void ++check_fips_gcry_kdf_derive (void) ++{ ++ static struct { ++ const char *p; /* Passphrase. */ ++ size_t plen; /* Length of P. */ ++ int algo; ++ int subalgo; ++ const char *salt; ++ size_t saltlen; ++ unsigned long iterations; ++ int dklen; /* Requested key length. */ ++ const char *dk; /* Derived key. */ ++ int expect_failure; ++ } tv[] = { ++ { ++ "passwordPASSWORDpassword", 24, ++ GCRY_KDF_PBKDF2, GCRY_MD_SHA1, ++ "saltSALTsaltSALTsaltSALTsaltSALTsalt", 36, ++ 4096, ++ 25, ++ "\x3d\x2e\xec\x4f\xe4\x1c\x84\x9b\x80\xc8" ++ "\xd8\x36\x62\xc0\xe4\x4a\x8b\x29\x1a\x96" ++ "\x4c\xf2\xf0\x70\x38", ++ 0 ++ }, ++ { ++ "pleaseletmein", 13, ++ GCRY_KDF_SCRYPT, 16384, ++ "SodiumChloride", 14, ++ 1, ++ 64, ++ "\x70\x23\xbd\xcb\x3a\xfd\x73\x48\x46\x1c\x06\xcd\x81\xfd\x38\xeb" ++ "\xfd\xa8\xfb\xba\x90\x4f\x8e\x3e\xa9\xb5\x43\xf6\x54\x5d\xa1\xf2" ++ "\xd5\x43\x29\x55\x61\x3f\x0f\xcf\x62\xd4\x97\x05\x24\x2a\x9a\xf9" ++ "\xe6\x1e\x85\xdc\x0d\x65\x1e\x40\xdf\xcf\x01\x7b\x45\x57\x58\x87", ++ 1 /* not-compliant because unallowed algo */ ++ }, ++ { ++ "passwor", 7, ++ GCRY_KDF_PBKDF2, GCRY_MD_SHA1, ++ "saltSALTsaltSALTsaltSALTsaltSALTsalt", 36, ++ 4096, ++ 25, ++ "\xf4\x93\xee\x2b\xbf\x44\x0b\x9e\x64\x53" ++ "\xc2\xb3\x87\xdc\x73\xf8\xfd\xe6\x97\xda" ++ "\xb8\x24\xa0\x26\x50", ++ 1 /* not-compliant because passphrase len is too small */ ++ }, ++ { ++ "passwordPASSWORDpassword", 24, ++ GCRY_KDF_PBKDF2, GCRY_MD_SHA1, ++ "saltSALTsaltSAL", 15, ++ 4096, ++ 25, ++ "\x14\x05\xa4\x2a\xf4\xa8\x12\x14\x7b\x65" ++ "\x8f\xaa\xf0\x7f\x25\xe5\x0f\x0b\x2b\xb7" ++ "\xcf\x8d\x29\x23\x4b", ++ 1 /* not-compliant because salt len is too small */ ++ }, ++ { ++ "passwordPASSWORDpassword", 24, ++ GCRY_KDF_PBKDF2, GCRY_MD_SHA1, ++ "saltSALTsaltSALTsaltSALTsaltSALTsalt", 36, ++ 999, ++ 25, ++ "\xac\xf8\xb4\x67\x41\xc7\xf3\xd1\xa0\xc0" ++ "\x08\xbe\x9b\x23\x96\x78\xbd\x93\xda\x4a" ++ "\x30\xd4\xfb\xf0\x33", ++ 1 /* not-compliant because too few iterations */ ++ }, ++ { ++ "passwordPASSWORDpassword", 24, ++ GCRY_KDF_PBKDF2, GCRY_MD_SHA1, ++ "saltSALTsaltSALTsaltSALTsaltSALTsalt", 36, ++ 4096, ++ 13, ++ "\x3d\x2e\xec\x4f\xe4\x1c\x84\x9b\x80\xc8" ++ "\xd8\x36\x62", ++ 1 /* not-compliant because key size too small */ ++ }, ++ }; ++ ++ int tvidx; ++ gpg_error_t err; ++ unsigned char outbuf[100]; ++ int i; ++ ++ for (tvidx=0; tvidx < DIM(tv); tvidx++) ++ { ++ if (verbose) ++ fprintf (stderr, "checking gcry_kdf_derive test vector %d algo %d for FIPS\n", ++ tvidx, tv[tvidx].algo); ++ assert (tv[tvidx].dklen <= sizeof outbuf); ++ err = gcry_kdf_derive (tv[tvidx].p, tv[tvidx].plen, ++ tv[tvidx].algo, tv[tvidx].subalgo, ++ tv[tvidx].salt, tv[tvidx].saltlen, ++ tv[tvidx].iterations, tv[tvidx].dklen, outbuf); ++ ++ if (err) ++ { ++ fail ("gcry_kdf_derive test %d unexpectedly returned an error in FIPS mode: %s\n", ++ tvidx, gpg_strerror (err)); ++ } ++ else ++ { ++ gpg_err_code_t ec; ++ ++ ec = gcry_get_fips_service_indicator (); ++ if (ec == GPG_ERR_INV_OP) ++ { ++ /* libgcrypt is old, no support of the FIPS service indicator. */ ++ fail ("gcry_kdf_derive test %d unexpectedly failed to check the FIPS service indicator.\n", ++ tvidx); ++ continue; ++ } ++ ++ if (!tv[tvidx].expect_failure && ec) ++ { ++ /* Success with the FIPS service indicator == 0 expected, but != 0. */ ++ fail ("gcry_kdf_derive test %d unexpectedly set the indicator in FIPS mode.\n", ++ tvidx); ++ continue; ++ } ++ else if (tv[tvidx].expect_failure && !ec) ++ { ++ /* Success with the FIPS service indicator != 0 expected, but == 0. */ ++ fail ("gcry_kdf_derive test %d unexpectedly cleared the indicator in FIPS mode.\n", ++ tvidx); ++ continue; ++ } ++ ++ if (memcmp (outbuf, tv[tvidx].dk, tv[tvidx].dklen)) ++ { ++ fail ("gcry_kdf_derive test %d failed: mismatch\n", tvidx); ++ fputs ("got:", stderr); ++ for (i=0; i < tv[tvidx].dklen; i++) ++ fprintf (stderr, " %02x", outbuf[i]); ++ putc ('\n', stderr); ++ } ++ } ++ } ++} ++ ++ + int + main (int argc, char **argv) + { +@@ -2008,7 +2153,9 @@ main (int argc, char **argv) + check_onestep_kdf (); + check_hkdf (); + if (in_fips_mode) +- check_fips_indicators(); ++ check_fips_indicators (); ++ if (in_fips_mode) ++ check_fips_gcry_kdf_derive (); + } + + return error_count ? 1 : 0; +-- +2.49.0 + diff --git a/libgcrypt-fips-mac-Implement-new-FIPS-service-indicator-for-gcry_mac_open.patch b/libgcrypt-fips-mac-Implement-new-FIPS-service-indicator-for-gcry_mac_open.patch new file mode 100644 index 0000000..7843a39 --- /dev/null +++ b/libgcrypt-fips-mac-Implement-new-FIPS-service-indicator-for-gcry_mac_open.patch @@ -0,0 +1,115 @@ +From fcb0c7004b0b6b318fdcced2bf61d9acb1e28cfc Mon Sep 17 00:00:00 2001 +From: NIIBE Yutaka +Date: Fri, 13 Dec 2024 14:25:02 +0900 +Subject: [PATCH 04/19] fips,mac: Implement new FIPS service indicator for + gcry_mac_open. +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* src/gcrypt.h.in (GCRY_MAC_FLAG_REJECT_NON_FIPS): New. +* cipher/mac.c (mac_open): Have FLAGS, instead of SECURE. Reject when +GCRY_MAC_FLAG_REJECT_NON_FIPS, otherwise, mark non compliant. +(_gcry_mac_open): Follow the change. +* src/visibility.c (gcry_mac_open): Add initialization for FIPS +service indicator. +(gcry_mac_setkey): Likewise. Don't reject but mark. + +-- + +GnuPG-bug-id: 7338 +Signed-off-by: NIIBE Yutaka +Signed-off-by: Lucas Mülling +--- + cipher/mac.c | 15 +++++++++++---- + src/gcrypt.h.in | 3 ++- + src/visibility.c | 5 +++-- + 3 files changed, 16 insertions(+), 7 deletions(-) + +diff --git a/cipher/mac.c b/cipher/mac.c +index 128ac53d..0df48fd7 100644 +--- a/cipher/mac.c ++++ b/cipher/mac.c +@@ -513,11 +513,13 @@ check_mac_algo (int algorithm) + * Open a message digest handle for use with algorithm ALGO. + */ + static gcry_err_code_t +-mac_open (gcry_mac_hd_t * hd, int algo, int secure, gcry_ctx_t ctx) ++mac_open (gcry_mac_hd_t * hd, int algo, unsigned int flags, gcry_ctx_t ctx) + { + const gcry_mac_spec_t *spec; + gcry_err_code_t err; + gcry_mac_hd_t h; ++ int secure = !!(flags & GCRY_MAC_FLAG_SECURE); ++ int reject_non_fips = !!(flags & GCRY_MAC_FLAG_REJECT_NON_FIPS); + + spec = spec_from_algo (algo); + if (!spec) +@@ -525,7 +527,12 @@ mac_open (gcry_mac_hd_t * hd, int algo, int secure, gcry_ctx_t ctx) + else if (spec->flags.disabled) + return GPG_ERR_MAC_ALGO; + else if (!spec->flags.fips && fips_mode ()) +- return GPG_ERR_MAC_ALGO; ++ { ++ if (reject_non_fips) ++ return GPG_ERR_MAC_ALGO; ++ else ++ fips_service_indicator_mark_non_compliant (); ++ } + else if (!spec->ops) + return GPG_ERR_MAC_ALGO; + else if (!spec->ops->open || !spec->ops->write || !spec->ops->setkey || +@@ -643,10 +650,10 @@ _gcry_mac_open (gcry_mac_hd_t * h, int algo, unsigned int flags, + gcry_err_code_t rc; + gcry_mac_hd_t hd = NULL; + +- if ((flags & ~GCRY_MAC_FLAG_SECURE)) ++ if ((flags & ~(GCRY_MAC_FLAG_SECURE | GCRY_MAC_FLAG_REJECT_NON_FIPS))) + rc = GPG_ERR_INV_ARG; + else +- rc = mac_open (&hd, algo, !!(flags & GCRY_MAC_FLAG_SECURE), ctx); ++ rc = mac_open (&hd, algo, flags, ctx); + + *h = rc ? NULL : hd; + return rc; +diff --git a/src/gcrypt.h.in b/src/gcrypt.h.in +index 96bf88f6..2a378639 100644 +--- a/src/gcrypt.h.in ++++ b/src/gcrypt.h.in +@@ -1560,7 +1560,8 @@ enum gcry_mac_algos + /* Flags used with the open function. */ + enum gcry_mac_flags + { +- GCRY_MAC_FLAG_SECURE = 1 /* Allocate all buffers in "secure" memory. */ ++ GCRY_MAC_FLAG_SECURE = 1, /* Allocate all buffers in "secure" memory. */ ++ GCRY_MAC_FLAG_REJECT_NON_FIPS = 2 /* Reject non-FIPS-compliant algo. */ + }; + + /* Create a MAC handle for algorithm ALGO. FLAGS may be given as an bitwise OR +diff --git a/src/visibility.c b/src/visibility.c +index 44b05eb2..7699f14f 100644 +--- a/src/visibility.c ++++ b/src/visibility.c +@@ -946,7 +946,7 @@ gcry_mac_open (gcry_mac_hd_t *handle, int algo, unsigned int flags, + *handle = NULL; + return gpg_error (fips_not_operational ()); + } +- ++ fips_service_indicator_init (); + return gpg_error (_gcry_mac_open (handle, algo, flags, ctx)); + } + +@@ -962,8 +962,9 @@ gcry_mac_setkey (gcry_mac_hd_t hd, const void *key, size_t keylen) + if (!fips_is_operational ()) + return gpg_error (fips_not_operational ()); + ++ fips_service_indicator_init (); + if (fips_mode () && keylen < 14) +- return GPG_ERR_INV_VALUE; ++ fips_service_indicator_mark_non_compliant (); + + return gpg_error (_gcry_mac_setkey (hd, key, keylen)); + } +-- +2.49.0 + diff --git a/libgcrypt-fips-md-Implement-new-FIPS-service-indicator-for-gcry_md_hash_.patch b/libgcrypt-fips-md-Implement-new-FIPS-service-indicator-for-gcry_md_hash_.patch new file mode 100644 index 0000000..71f1671 --- /dev/null +++ b/libgcrypt-fips-md-Implement-new-FIPS-service-indicator-for-gcry_md_hash_.patch @@ -0,0 +1,188 @@ +From 3478caac62c712547f7c0e07f4cf9602bc317997 Mon Sep 17 00:00:00 2001 +From: NIIBE Yutaka +Date: Fri, 6 Dec 2024 14:33:58 +0900 +Subject: [PATCH 4/5] fips,md: Implement new FIPS service indicator for + gcry_md_hash_*. +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* cipher/md.c (md_enable): Add an NO_REJECT argument. +(md_open): Check flags against GCRY_MD_FLAG_FIPS_NO_REJECTION to +call md_enable. +(_gcry_md_enable): Follow the change. +(_gcry_md_hash_buffer): Don't reject but keep the computation. +Call fips_service_indicator_mark_success. +(_gcry_md_hash_buffers_extract): Likewise. +* src/gcrypt.h.in (GCRY_MD_FLAG_FIPS_NO_REJECTION): New. +* src/visibility.c (gcry_md_hash_buffer, gcry_md_hash_buffers): Call +fips_service_indicator_init. +(gcry_md_hash_buffers_ext): Likewise. + +-- + +GnuPG-bug-id: 7338 +Signed-off-by: NIIBE Yutaka +Signed-off-by: Lucas Mülling +--- + cipher/md.c | 32 +++++++++++++++++++++++--------- + src/gcrypt.h.in | 1 + + src/visibility.c | 3 +++ + 3 files changed, 27 insertions(+), 9 deletions(-) + +diff --git a/cipher/md.c b/cipher/md.c +index 1991c331..c2bd18c6 100644 +--- a/cipher/md.c ++++ b/cipher/md.c +@@ -285,7 +285,7 @@ struct gcry_md_context + #define CTX_MAGIC_NORMAL 0x11071961 + #define CTX_MAGIC_SECURE 0x16917011 + +-static gcry_err_code_t md_enable (gcry_md_hd_t hd, int algo); ++static gcry_err_code_t md_enable (gcry_md_hd_t hd, int algo, int no_reject); + static void md_close (gcry_md_hd_t a); + static void md_write (gcry_md_hd_t a, const void *inbuf, size_t inlen); + static byte *md_read( gcry_md_hd_t a, int algo ); +@@ -517,7 +517,8 @@ md_open (gcry_md_hd_t *h, int algo, unsigned int flags) + + if (algo) + { +- err = md_enable (hd, algo); ++ err = md_enable (hd, algo, ++ !!(flags & GCRY_MD_FLAG_FIPS_NO_REJECTION)); + if (err) + md_close (hd); + } +@@ -554,7 +555,7 @@ _gcry_md_open (gcry_md_hd_t *h, int algo, unsigned int flags) + + + static gcry_err_code_t +-md_enable (gcry_md_hd_t hd, int algorithm) ++md_enable (gcry_md_hd_t hd, int algorithm, int no_reject) + { + struct gcry_md_context *h = hd->ctx; + const gcry_md_spec_t *spec; +@@ -576,7 +577,7 @@ md_enable (gcry_md_hd_t hd, int algorithm) + err = GPG_ERR_DIGEST_ALGO; + + /* Any non-FIPS algorithm should go this way */ +- if (!err && !spec->flags.fips && fips_mode ()) ++ if (!err && !no_reject && !spec->flags.fips && fips_mode ()) + err = GPG_ERR_DIGEST_ALGO; + + if (!err && h->flags.hmac && spec->read == NULL) +@@ -619,7 +620,7 @@ md_enable (gcry_md_hd_t hd, int algorithm) + gcry_err_code_t + _gcry_md_enable (gcry_md_hd_t hd, int algorithm) + { +- return md_enable (hd, algorithm); ++ return md_enable (hd, algorithm, 0); + } + + +@@ -1260,7 +1261,7 @@ _gcry_md_hash_buffer (int algo, void *digest, + iov.off = 0; + iov.len = length; + +- if (spec->flags.disabled || (!spec->flags.fips && fips_mode ())) ++ if (spec->flags.disabled) + log_bug ("gcry_md_hash_buffer failed for algo %d: %s", + algo, gpg_strerror (gcry_error (GPG_ERR_DIGEST_ALGO))); + +@@ -1273,7 +1274,7 @@ _gcry_md_hash_buffer (int algo, void *digest, + gcry_md_hd_t h; + gpg_err_code_t err; + +- err = md_open (&h, algo, 0); ++ err = md_open (&h, algo, GCRY_MD_FLAG_FIPS_NO_REJECTION); + if (err) + log_bug ("gcry_md_open failed for algo %d: %s", + algo, gpg_strerror (gcry_error(err))); +@@ -1282,6 +1283,12 @@ _gcry_md_hash_buffer (int algo, void *digest, + memcpy (digest, md_read (h, algo), md_digest_length (algo)); + md_close (h); + } ++ ++ if (fips_mode ()) ++ { ++ int is_compliant = spec->flags.fips; ++ fips_service_indicator_mark_success (is_compliant); ++ } + } + + +@@ -1336,7 +1343,7 @@ _gcry_md_hash_buffers_extract (int algo, unsigned int flags, void *digest, + + if (!hmac && spec->hash_buffers) + { +- if (spec->flags.disabled || (!spec->flags.fips && fips_mode ())) ++ if (spec->flags.disabled) + return GPG_ERR_DIGEST_ALGO; + + spec->hash_buffers (digest, digestlen, iov, iovcnt); +@@ -1348,7 +1355,8 @@ _gcry_md_hash_buffers_extract (int algo, unsigned int flags, void *digest, + gcry_md_hd_t h; + gpg_err_code_t rc; + +- rc = md_open (&h, algo, (hmac? GCRY_MD_FLAG_HMAC:0)); ++ rc = md_open (&h, algo, ((hmac? GCRY_MD_FLAG_HMAC:0) ++ | GCRY_MD_FLAG_FIPS_NO_REJECTION)); + if (rc) + return rc; + +@@ -1374,6 +1382,12 @@ _gcry_md_hash_buffers_extract (int algo, unsigned int flags, void *digest, + md_close (h); + } + ++ if (fips_mode ()) ++ { ++ int is_compliant = spec->flags.fips; ++ fips_service_indicator_mark_success (is_compliant); ++ } ++ + return 0; + } + +diff --git a/src/gcrypt.h.in b/src/gcrypt.h.in +index 2f61a0bc..18d04a38 100644 +--- a/src/gcrypt.h.in ++++ b/src/gcrypt.h.in +@@ -1318,6 +1318,7 @@ enum gcry_md_flags + { + GCRY_MD_FLAG_SECURE = 1, /* Allocate all buffers in "secure" memory. */ + GCRY_MD_FLAG_HMAC = 2, /* Make an HMAC out of this algorithm. */ ++ GCRY_MD_FLAG_FIPS_NO_REJECTION = 4, /* Don't reject for FIPS. */ + GCRY_MD_FLAG_BUGEMU1 = 0x0100 + }; + +diff --git a/src/visibility.c b/src/visibility.c +index 8f76b854..be5deda1 100644 +--- a/src/visibility.c ++++ b/src/visibility.c +@@ -1281,6 +1281,7 @@ gcry_md_hash_buffer (int algo, void *digest, + (void)fips_not_operational (); + fips_signal_error ("called in non-operational state"); + } ++ fips_service_indicator_init (); + _gcry_md_hash_buffer (algo, digest, buffer, length); + } + +@@ -1293,6 +1294,7 @@ gcry_md_hash_buffers (int algo, unsigned int flags, void *digest, + (void)fips_not_operational (); + fips_signal_error ("called in non-operational state"); + } ++ fips_service_indicator_init (); + return gpg_error (_gcry_md_hash_buffers (algo, flags, digest, iov, iovcnt)); + } + +@@ -1306,6 +1308,7 @@ gcry_md_hash_buffers_ext (int algo, unsigned int flags, void *digest, + (void)fips_not_operational (); + fips_signal_error ("called in non-operational state"); + } ++ fips_service_indicator_init (); + return gpg_error (_gcry_md_hash_buffers_extract (algo, flags, digest, + digestlen, iov, iovcnt)); + } +-- +2.49.0 + diff --git a/libgcrypt-fips-md-Implement-new-FIPS-service-indicator-for-gcry_md_open-API.patch b/libgcrypt-fips-md-Implement-new-FIPS-service-indicator-for-gcry_md_open-API.patch new file mode 100644 index 0000000..0f580b1 --- /dev/null +++ b/libgcrypt-fips-md-Implement-new-FIPS-service-indicator-for-gcry_md_open-API.patch @@ -0,0 +1,298 @@ +From 9757e280794f537efc82c4eaa9a2944ece6a068a Mon Sep 17 00:00:00 2001 +From: NIIBE Yutaka +Date: Thu, 12 Dec 2024 11:40:31 +0900 +Subject: [PATCH] fips,md: Implement new FIPS service indicator for + gcry_md_open API. +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* src/gcrypt.h.in (GCRY_MD_FLAG_FIPS_NO_REJECTION): Remove. +(GCRY_MD_FLAG_REJECT_NON_FIPS): New. +* cipher/md.c (struct gcry_md_context): Add reject_non_fips. +(md_enable): Remove NO_REJECT argument. +(md_open): Change the FLAGS handling. +(_gcry_md_open): Add checking of FIPS compliance against ALGO. +(_gcry_md_enable): Likewise. +(_gcry_md_hash_buffer): Follow the change of md_open change +which now defaults to no rejection. +(_gcry_md_hash_buffers_extract): Likewise. +* src/visibility.c (gcry_md_open): Add fips_service_indicator_init. +(gcry_md_enable): Likewise. +(gcry_md_setkey): Don't reject but mark non-compliance. +* tests/t-kdf.c (check_fips_gcry_kdf_derive): Add a test with +non-compliant hash function. +* cipher/mac-hmac.c (_gcry_mac_type_spec_hmac_md5): It's not +compliant. +* cipher/md5.c (gcry_md_oid_spec_t oid_spec_md5): It's not compliant. +* tests/t-digest.c (check_hash_buffer, check_hash_buffers): MD5 +tests enabled. + +-- + +See 6376 for the MD5 compliance change in the past. This commit +reverts the change in: + dc4a60e2d70bc52ba2955f8e676341d675ab89a0 + +GnuPG-bug-id: 7338 +Signed-off-by: NIIBE Yutaka +Signed-off-by: Lucas Mülling +--- + cipher/mac-hmac.c | 2 +- + cipher/md.c | 57 +++++++++++++++++++++++++++++++++++++++-------- + cipher/md5.c | 2 +- + src/gcrypt.h.in | 2 +- + src/visibility.c | 6 +++-- + tests/t-digest.c | 6 ++--- + tests/t-kdf.c | 12 ++++++++++ + 7 files changed, 69 insertions(+), 18 deletions(-) + +Index: libgcrypt-1.11.0/cipher/mac-hmac.c +=================================================================== +--- libgcrypt-1.11.0.orig/cipher/mac-hmac.c ++++ libgcrypt-1.11.0/cipher/mac-hmac.c +@@ -1413,7 +1413,7 @@ const gcry_mac_spec_t _gcry_mac_type_spe + #endif + #if USE_MD5 + const gcry_mac_spec_t _gcry_mac_type_spec_hmac_md5 = { +- GCRY_MAC_HMAC_MD5, {0, 1}, "HMAC_MD5", ++ GCRY_MAC_HMAC_MD5, {0, 0}, "HMAC_MD5", + &hmac_ops + }; + #endif +Index: libgcrypt-1.11.0/cipher/md.c +=================================================================== +--- libgcrypt-1.11.0.orig/cipher/md.c ++++ libgcrypt-1.11.0/cipher/md.c +@@ -275,6 +275,7 @@ struct gcry_md_context + unsigned int finalized:1; + unsigned int bugemu1:1; + unsigned int hmac:1; ++ unsigned int reject_non_fips:1; + } flags; + size_t actual_handle_size; /* Allocated size of this handle. */ + FILE *debug; +@@ -285,7 +286,7 @@ struct gcry_md_context + #define CTX_MAGIC_NORMAL 0x11071961 + #define CTX_MAGIC_SECURE 0x16917011 + +-static gcry_err_code_t md_enable (gcry_md_hd_t hd, int algo, int no_reject); ++static gcry_err_code_t md_enable (gcry_md_hd_t hd, int algo); + static void md_close (gcry_md_hd_t a); + static void md_write (gcry_md_hd_t a, const void *inbuf, size_t inlen); + static byte *md_read( gcry_md_hd_t a, int algo ); +@@ -508,6 +509,7 @@ md_open (gcry_md_hd_t *h, int algo, unsi + ctx->flags.secure = secure; + ctx->flags.hmac = hmac; + ctx->flags.bugemu1 = !!(flags & GCRY_MD_FLAG_BUGEMU1); ++ ctx->flags.reject_non_fips = !!(flags & GCRY_MD_FLAG_REJECT_NON_FIPS); + } + + if (! err) +@@ -517,8 +519,7 @@ md_open (gcry_md_hd_t *h, int algo, unsi + + if (algo) + { +- err = md_enable (hd, algo, +- !!(flags & GCRY_MD_FLAG_FIPS_NO_REJECTION)); ++ err = md_enable (hd, algo); + if (err) + md_close (hd); + } +@@ -543,24 +544,44 @@ _gcry_md_open (gcry_md_hd_t *h, int algo + + if ((flags & ~(GCRY_MD_FLAG_SECURE + | GCRY_MD_FLAG_HMAC ++ | GCRY_MD_FLAG_REJECT_NON_FIPS + | GCRY_MD_FLAG_BUGEMU1))) + rc = GPG_ERR_INV_ARG; + else + rc = md_open (&hd, algo, flags); + + *h = rc? NULL : hd; ++ ++ if (!rc && fips_mode ()) ++ { ++ GcryDigestEntry *entry = hd->ctx->list; ++ /* No ENTRY means that ALGO==0. ++ It's not yet known, if it's FIPS compliant or not. */ ++ int is_compliant_algo = 1; ++ ++ if (entry) ++ { ++ const gcry_md_spec_t *spec = entry->spec; ++ is_compliant_algo = spec->flags.fips; ++ } ++ ++ if (!is_compliant_algo) ++ fips_service_indicator_mark_non_compliant (); ++ } ++ + return rc; + } + + + + static gcry_err_code_t +-md_enable (gcry_md_hd_t hd, int algorithm, int no_reject) ++md_enable (gcry_md_hd_t hd, int algorithm) + { + struct gcry_md_context *h = hd->ctx; + const gcry_md_spec_t *spec; + GcryDigestEntry *entry; + gcry_err_code_t err = 0; ++ int reject_non_fips = h->flags.reject_non_fips; + + for (entry = h->list; entry; entry = entry->next) + if (entry->spec->algo == algorithm) +@@ -577,7 +598,7 @@ md_enable (gcry_md_hd_t hd, int algorith + err = GPG_ERR_DIGEST_ALGO; + + /* Any non-FIPS algorithm should go this way */ +- if (!err && !no_reject && !spec->flags.fips && fips_mode ()) ++ if (!err && reject_non_fips && !spec->flags.fips && fips_mode ()) + err = GPG_ERR_DIGEST_ALGO; + + if (!err && h->flags.hmac && spec->read == NULL) +@@ -620,7 +641,26 @@ md_enable (gcry_md_hd_t hd, int algorith + gcry_err_code_t + _gcry_md_enable (gcry_md_hd_t hd, int algorithm) + { +- return md_enable (hd, algorithm, 0); ++ gcry_err_code_t rc; ++ ++ rc = md_enable (hd, algorithm); ++ if (!rc && fips_mode ()) ++ { ++ GcryDigestEntry *entry = hd->ctx->list; ++ /* No ENTRY means, something goes wrong. */ ++ int is_compliant_algo = 0; ++ ++ if (entry) ++ { ++ const gcry_md_spec_t *spec = entry->spec; ++ is_compliant_algo = spec->flags.fips; ++ } ++ ++ if (!is_compliant_algo) ++ fips_service_indicator_mark_non_compliant (); ++ } ++ ++ return rc; + } + + +@@ -1274,7 +1314,7 @@ _gcry_md_hash_buffer (int algo, void *di + gcry_md_hd_t h; + gpg_err_code_t err; + +- err = md_open (&h, algo, GCRY_MD_FLAG_FIPS_NO_REJECTION); ++ err = md_open (&h, algo, 0); + if (err) + log_bug ("gcry_md_open failed for algo %d: %s", + algo, gpg_strerror (gcry_error(err))); +@@ -1355,8 +1395,7 @@ _gcry_md_hash_buffers_extract (int algo, + gcry_md_hd_t h; + gpg_err_code_t rc; + +- rc = md_open (&h, algo, ((hmac? GCRY_MD_FLAG_HMAC:0) +- | GCRY_MD_FLAG_FIPS_NO_REJECTION)); ++ rc = md_open (&h, algo, (hmac? GCRY_MD_FLAG_HMAC:0)); + if (rc) + return rc; + +Index: libgcrypt-1.11.0/cipher/md5.c +=================================================================== +--- libgcrypt-1.11.0.orig/cipher/md5.c ++++ libgcrypt-1.11.0/cipher/md5.c +@@ -314,7 +314,7 @@ static const gcry_md_oid_spec_t oid_spec + + const gcry_md_spec_t _gcry_digest_spec_md5 = + { +- GCRY_MD_MD5, {0, 1}, ++ GCRY_MD_MD5, {0, 0}, + "MD5", asn, DIM (asn), oid_spec_md5, 16, + md5_init, _gcry_md_block_write, md5_final, md5_read, NULL, + NULL, +Index: libgcrypt-1.11.0/src/gcrypt.h.in +=================================================================== +--- libgcrypt-1.11.0.orig/src/gcrypt.h.in ++++ libgcrypt-1.11.0/src/gcrypt.h.in +@@ -1320,7 +1320,7 @@ enum gcry_md_flags + { + GCRY_MD_FLAG_SECURE = 1, /* Allocate all buffers in "secure" memory. */ + GCRY_MD_FLAG_HMAC = 2, /* Make an HMAC out of this algorithm. */ +- GCRY_MD_FLAG_FIPS_NO_REJECTION = 4, /* Don't reject for FIPS. */ ++ GCRY_MD_FLAG_REJECT_NON_FIPS = 4, /* Reject non-FIPS-compliant algo. */ + GCRY_MD_FLAG_BUGEMU1 = 0x0100 + }; + +Index: libgcrypt-1.11.0/src/visibility.c +=================================================================== +--- libgcrypt-1.11.0.orig/src/visibility.c ++++ libgcrypt-1.11.0/src/visibility.c +@@ -1204,7 +1204,7 @@ gcry_md_open (gcry_md_hd_t *h, int algo, + *h = NULL; + return gpg_error (fips_not_operational ()); + } +- ++ fips_service_indicator_init (); + return gpg_error (_gcry_md_open (h, algo, flags)); + } + +@@ -1219,6 +1219,7 @@ gcry_md_enable (gcry_md_hd_t hd, int alg + { + if (!fips_is_operational ()) + return gpg_error (fips_not_operational ()); ++ fips_service_indicator_init (); + return gpg_error (_gcry_md_enable (hd, algo)); + } + +@@ -1382,8 +1383,9 @@ gcry_md_setkey (gcry_md_hd_t hd, const v + if (!fips_is_operational ()) + return gpg_error (fips_not_operational ()); + ++ fips_service_indicator_init (); + if (fips_mode () && keylen < 14) +- return GPG_ERR_INV_VALUE; ++ fips_service_indicator_mark_non_compliant (); + + return gpg_error (_gcry_md_setkey (hd, key, keylen)); + } +Index: libgcrypt-1.11.0/tests/t-digest.c +=================================================================== +--- libgcrypt-1.11.0.orig/tests/t-digest.c ++++ libgcrypt-1.11.0/tests/t-digest.c +@@ -48,8 +48,7 @@ check_digests (void) + const char *expect; + int expect_failure; + } tv[] = { +-#undef ENABLE_THIS_AFTER_T6376_CHANGE_REVISED +-#ifdef ENABLE_THIS_AFTER_T6376_CHANGE_REVISED ++#if USE_MD5 + { GCRY_MD_MD5, "abc", 3, + "\x90\x01\x50\x98\x3C\xD2\x4F\xB0\xD6\x96\x3F\x7D\x28\xE1\x7F\x72", 1 }, + #endif +Index: libgcrypt-1.11.0/tests/t-kdf.c +=================================================================== +--- libgcrypt-1.11.0.orig/tests/t-kdf.c ++++ libgcrypt-1.11.0/tests/t-kdf.c +@@ -2008,6 +2008,18 @@ check_fips_gcry_kdf_derive (void) + "\xd8\x36\x62", + 1 /* not-compliant because key size too small */ + }, ++ { ++ "passwordPASSWORDpassword", 24, ++ GCRY_KDF_PBKDF2, GCRY_MD_BLAKE2B_512, ++ "saltSALTsaltSALTsaltSALTsaltSALTsalt", 36, ++ 4096, ++ 60, ++ "\xa4\x6b\x53\x35\xdb\xdd\xa3\xd2\x5d\x19\xbb\x11\xfe\xdd\xd9\x9e" ++ "\x45\x2a\x7c\x34\x47\x41\x98\xca\x31\x74\xb6\x34\x22\xac\x83\xb0" ++ "\x38\x6e\xf5\x93\x0f\xf5\x16\x46\x0b\x97\xdc\x6c\x27\x5b\xe7\x25" ++ "\xc2\xcb\xec\x50\x02\xc6\x52\x8b\x34\x68\x53\x65", ++ 1 /* not-compliant because subalgo is not the one of approved */ ++ } + }; + + int tvidx; diff --git a/libgcrypt-fips-md-gcry_md_copy-should-care-about-FIPS-service-indicator.patch b/libgcrypt-fips-md-gcry_md_copy-should-care-about-FIPS-service-indicator.patch new file mode 100644 index 0000000..5edccac --- /dev/null +++ b/libgcrypt-fips-md-gcry_md_copy-should-care-about-FIPS-service-indicator.patch @@ -0,0 +1,85 @@ +From 60db2a175d120aba6818de49638b36006878abf7 Mon Sep 17 00:00:00 2001 +From: NIIBE Yutaka +Date: Wed, 18 Dec 2024 14:14:37 +0900 +Subject: [PATCH 10/19] fips,md: gcry_md_copy should care about FIPS service + indicator. +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* cipher/md.c (md_copy): In a case of non-compliant, mark with +fips_service_indicator_mark_non_compliant. +* src/visibility.c (gcry_md_copy): Initialize the indicator. + +-- + +GnuPG-bug-id: 7338 +Signed-off-by: NIIBE Yutaka +Signed-off-by: Lucas Mülling +--- + cipher/md.c | 11 +++++++++++ + src/visibility.c | 1 + + 2 files changed, 12 insertions(+) + +diff --git a/cipher/md.c b/cipher/md.c +index 666e1dfa..08a564ad 100644 +--- a/cipher/md.c ++++ b/cipher/md.c +@@ -673,6 +673,7 @@ md_copy (gcry_md_hd_t ahd, gcry_md_hd_t *b_hd) + GcryDigestEntry *ar, *br; + gcry_md_hd_t bhd; + size_t n; ++ int is_compliant_algo = 1; + + if (ahd->bufpos) + md_write (ahd, NULL, 0); +@@ -699,10 +700,15 @@ md_copy (gcry_md_hd_t ahd, gcry_md_hd_t *b_hd) + b->list = NULL; + b->debug = NULL; + ++ if (!a->list) ++ is_compliant_algo = 0; ++ + /* Copy the complete list of algorithms. The copied list is + reversed, but that doesn't matter. */ + for (ar = a->list; ar; ar = ar->next) + { ++ const gcry_md_spec_t *spec = ar->spec; ++ + if (a->flags.secure) + br = xtrymalloc_secure (ar->actual_struct_size); + else +@@ -714,6 +720,8 @@ md_copy (gcry_md_hd_t ahd, gcry_md_hd_t *b_hd) + goto leave; + } + ++ is_compliant_algo &= spec->flags.fips; ++ + memcpy (br, ar, ar->actual_struct_size); + br->next = b->list; + b->list = br; +@@ -724,6 +732,9 @@ md_copy (gcry_md_hd_t ahd, gcry_md_hd_t *b_hd) + + *b_hd = bhd; + ++ if (!is_compliant_algo) ++ fips_service_indicator_mark_non_compliant (); ++ + leave: + return err; + } +diff --git a/src/visibility.c b/src/visibility.c +index d219f1a6..c9d07f0b 100644 +--- a/src/visibility.c ++++ b/src/visibility.c +@@ -1232,6 +1232,7 @@ gcry_md_copy (gcry_md_hd_t *bhd, gcry_md_hd_t ahd) + *bhd = NULL; + return gpg_error (fips_not_operational ()); + } ++ fips_service_indicator_init (); + return gpg_error (_gcry_md_copy (bhd, ahd)); + } + +-- +2.49.0 + diff --git a/libgcrypt-fips-tests-Add-t-digest.patch b/libgcrypt-fips-tests-Add-t-digest.patch new file mode 100644 index 0000000..fc5e8e8 --- /dev/null +++ b/libgcrypt-fips-tests-Add-t-digest.patch @@ -0,0 +1,243 @@ +From 7faf542f157330f3b247fa2542182ac805f06737 Mon Sep 17 00:00:00 2001 +From: NIIBE Yutaka +Date: Mon, 9 Dec 2024 14:05:59 +0900 +Subject: [PATCH 5/5] fips,tests: Add t-digest. +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* tests/Makefile.am (tests_bin): Add t-digest. +* tests/t-digest.c: New. + +-- + +GnuPG-bug-id: 7338 +Signed-off-by: NIIBE Yutaka +Signed-off-by: Lucas Mülling +--- + tests/Makefile.am | 2 +- + tests/t-digest.c | 199 ++++++++++++++++++++++++++++++++++++++++++++++ + 2 files changed, 200 insertions(+), 1 deletion(-) + create mode 100644 tests/t-digest.c + +diff --git a/tests/Makefile.am b/tests/Makefile.am +index 52f7dd61..93774fe9 100644 +--- a/tests/Makefile.am ++++ b/tests/Makefile.am +@@ -25,7 +25,7 @@ tests_bin = \ + version t-secmem mpitests t-sexp t-convert \ + t-mpi-bit t-mpi-point t-lock \ + prime basic keygen pubkey hmac hashtest t-kdf keygrip \ +- aeswrap random t-kem t-mlkem t-thread-local ++ aeswrap random t-kem t-mlkem t-thread-local t-digest + + if USE_RSA + tests_bin += pkcs1v2 t-rsa-pss t-rsa-15 t-rsa-testparm +diff --git a/tests/t-digest.c b/tests/t-digest.c +new file mode 100644 +index 00000000..3a94fa69 +--- /dev/null ++++ b/tests/t-digest.c +@@ -0,0 +1,199 @@ ++/* t-digest.c - MD regression tests ++ * Copyright (C) 2024 g10 Code GmbH ++ * ++ * This file is part of Libgcrypt. ++ * ++ * Libgcrypt is free software; you can redistribute it and/or modify ++ * it under the terms of the GNU Lesser General Public License as ++ * published by the Free Software Foundation; either version 2.1 of ++ * the License, or (at your option) any later version. ++ * ++ * Libgcrypt 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 Lesser General Public License for more details. ++ * ++ * You should have received a copy of the GNU Lesser General Public License ++ * along with this program; if not, see . ++ * SPDX-License-Identifier: LGPL-2.1+ ++ */ ++ ++#ifdef HAVE_CONFIG_H ++#include ++#endif ++#include ++#include ++#include ++#include ++#include ++ ++#define PGM "t-digest" ++ ++#include "t-common.h" ++static int in_fips_mode; ++ ++/* Mingw requires us to include windows.h after winsock2.h which is ++ included by gcrypt.h. */ ++#ifdef _WIN32 ++# include ++#endif ++ ++static void ++check_digests (void) ++{ ++ static struct { ++ int algo; ++ const char *data; ++ int datalen; ++ const char *expect; ++ int expect_failure; ++ } tv[] = { ++#undef ENABLE_THIS_AFTER_T6376_CHANGE_REVISED ++#ifdef ENABLE_THIS_AFTER_T6376_CHANGE_REVISED ++ { GCRY_MD_MD5, "abc", 3, ++ "\x90\x01\x50\x98\x3C\xD2\x4F\xB0\xD6\x96\x3F\x7D\x28\xE1\x7F\x72", 1 }, ++#endif ++ { GCRY_MD_SHA1, "abc", 3, ++ "\xA9\x99\x3E\x36\x47\x06\x81\x6A\xBA\x3E" ++ "\x25\x71\x78\x50\xC2\x6C\x9C\xD0\xD8\x9D" }, ++ { GCRY_MD_SHA256, "abc", 3, ++ "\xba\x78\x16\xbf\x8f\x01\xcf\xea\x41\x41\x40\xde\x5d\xae\x22\x23" ++ "\xb0\x03\x61\xa3\x96\x17\x7a\x9c\xb4\x10\xff\x61\xf2\x00\x15\xad" }, ++ { GCRY_MD_SHA384, "abc", 3, ++ "\xcb\x00\x75\x3f\x45\xa3\x5e\x8b\xb5\xa0\x3d\x69\x9a\xc6\x50\x07" ++ "\x27\x2c\x32\xab\x0e\xde\xd1\x63\x1a\x8b\x60\x5a\x43\xff\x5b\xed" ++ "\x80\x86\x07\x2b\xa1\xe7\xcc\x23\x58\xba\xec\xa1\x34\xc8\x25\xa7" }, ++ { GCRY_MD_SHA512, "abc", 3, ++ "\xDD\xAF\x35\xA1\x93\x61\x7A\xBA\xCC\x41\x73\x49\xAE\x20\x41\x31" ++ "\x12\xE6\xFA\x4E\x89\xA9\x7E\xA2\x0A\x9E\xEE\xE6\x4B\x55\xD3\x9A" ++ "\x21\x92\x99\x2A\x27\x4F\xC1\xA8\x36\xBA\x3C\x23\xA3\xFE\xEB\xBD" ++ "\x45\x4D\x44\x23\x64\x3C\xE8\x0E\x2A\x9A\xC9\x4F\xA5\x4C\xA4\x9F" }, ++ { GCRY_MD_SHA3_256, "abc", 3, ++ "\x3a\x98\x5d\xa7\x4f\xe2\x25\xb2\x04\x5c\x17\x2d\x6b\xd3\x90\xbd" ++ "\x85\x5f\x08\x6e\x3e\x9d\x52\x5b\x46\xbf\xe2\x45\x11\x43\x15\x32" }, ++ { GCRY_MD_SHA3_384, "abc", 3, ++ "\xec\x01\x49\x82\x88\x51\x6f\xc9\x26\x45\x9f\x58\xe2\xc6\xad\x8d" ++ "\xf9\xb4\x73\xcb\x0f\xc0\x8c\x25\x96\xda\x7c\xf0\xe4\x9b\xe4\xb2" ++ "\x98\xd8\x8c\xea\x92\x7a\xc7\xf5\x39\xf1\xed\xf2\x28\x37\x6d\x25" }, ++ { GCRY_MD_SHA3_512, "abc", 3, ++ "\xb7\x51\x85\x0b\x1a\x57\x16\x8a\x56\x93\xcd\x92\x4b\x6b\x09\x6e" ++ "\x08\xf6\x21\x82\x74\x44\xf7\x0d\x88\x4f\x5d\x02\x40\xd2\x71\x2e" ++ "\x10\xe1\x16\xe9\x19\x2a\xf3\xc9\x1a\x7e\xc5\x76\x47\xe3\x93\x40" ++ "\x57\x34\x0b\x4c\xf4\x08\xd5\xa5\x65\x92\xf8\x27\x4e\xec\x53\xf0" }, ++ { GCRY_MD_RMD160, "abc", 3, ++ "\x8e\xb2\x08\xf7\xe0\x5d\x98\x7a\x9b\x04" ++ "\x4a\x8e\x98\xc6\xb0\x87\xf1\x5a\x0b\xfc", 1 }, ++ }; ++ int tvidx; ++ unsigned char hash[64]; ++ int expectlen; ++ ++ for (tvidx=0; tvidx < DIM(tv); tvidx++) ++ { ++ gpg_err_code_t ec; ++ ++ if (verbose) ++ fprintf (stderr, "checking gcry_md_hash_buffer test %d\n", ++ tvidx); ++ ++ expectlen = gcry_md_get_algo_dlen (tv[tvidx].algo); ++ assert (expectlen != 0); ++ assert (expectlen <= sizeof hash); ++ gcry_md_hash_buffer (tv[tvidx].algo, hash, ++ tv[tvidx].data, tv[tvidx].datalen); ++ ++ ec = gcry_get_fips_service_indicator (); ++ if (ec == GPG_ERR_INV_OP) ++ { ++ /* libgcrypt is old, no support of the FIPS service indicator. */ ++ fail ("gcry_md_hash_buffer test %d unexpectedly failed to check the FIPS service indicator.\n", ++ tvidx); ++ continue; ++ } ++ ++ if (in_fips_mode && !tv[tvidx].expect_failure && ec) ++ { ++ /* Success with the FIPS service indicator == 0 expected, but != 0. */ ++ fail ("gcry_md_hash_buffer test %d unexpectedly set the indicator in FIPS mode.\n", ++ tvidx); ++ continue; ++ } ++ else if (in_fips_mode && tv[tvidx].expect_failure && !ec) ++ { ++ /* Success with the FIPS service indicator != 0 expected, but == 0. */ ++ fail ("gcry_md_hash_buffer test %d unexpectedly cleared the indicator in FIPS mode.\n", ++ tvidx); ++ continue; ++ } ++ ++ if (memcmp (hash, tv[tvidx].expect, expectlen)) ++ { ++ int i; ++ ++ fail ("gcry_md_hash_buffer test %d failed: mismatch\n", tvidx); ++ fputs ("got:", stderr); ++ for (i=0; i < expectlen; i++) ++ fprintf (stderr, " %02x", hash[i]); ++ putc ('\n', stderr); ++ } ++ } ++} ++ ++ ++int ++main (int argc, char **argv) ++{ ++ int last_argc = -1; ++ ++ if (argc) ++ { argc--; argv++; } ++ ++ while (argc && last_argc != argc) ++ { ++ last_argc = argc; ++ if (!strcmp (*argv, "--")) ++ { ++ argc--; argv++; ++ break; ++ } ++ else if (!strcmp (*argv, "--help")) ++ { ++ fputs ("usage: " PGM " [options]\n" ++ "Options:\n" ++ " --verbose print timings etc.\n" ++ " --debug flyswatter\n", ++ stdout); ++ exit (0); ++ } ++ else if (!strcmp (*argv, "--verbose")) ++ { ++ verbose++; ++ argc--; argv++; ++ } ++ else if (!strcmp (*argv, "--debug")) ++ { ++ verbose += 2; ++ debug++; ++ argc--; argv++; ++ } ++ else if (!strncmp (*argv, "--", 2)) ++ die ("unknown option '%s'", *argv); ++ } ++ ++ if (!gcry_check_version (GCRYPT_VERSION)) ++ die ("version mismatch\n"); ++ ++ if (gcry_fips_mode_active ()) ++ in_fips_mode = 1; ++ ++ if (!in_fips_mode) ++ xgcry_control ((GCRYCTL_DISABLE_SECMEM, 0)); ++ ++ xgcry_control ((GCRYCTL_INITIALIZATION_FINISHED, 0)); ++ if (debug) ++ xgcry_control ((GCRYCTL_SET_DEBUG_FLAGS, 1u , 0)); ++ ++ check_digests (); ++ ++ return !!error_count; ++} +-- +2.49.0 + diff --git a/libgcrypt-fips-tests-Add-tests-for-md_open-write-read-close-for-t-digest.patch b/libgcrypt-fips-tests-Add-tests-for-md_open-write-read-close-for-t-digest.patch new file mode 100644 index 0000000..699c1eb --- /dev/null +++ b/libgcrypt-fips-tests-Add-tests-for-md_open-write-read-close-for-t-digest.patch @@ -0,0 +1,172 @@ +From 917fc6000dfebd8854f0d1c220b85dec0dbf4676 Mon Sep 17 00:00:00 2001 +From: NIIBE Yutaka +Date: Fri, 13 Dec 2024 11:54:31 +0900 +Subject: [PATCH 03/19] fips,tests: Add tests for md_open/write/read/close for + t-digest. +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* tests/t-digest.c (check_md_o_w_r_c): New. +(main): Call check_md_o_w_r_c. + +-- + +GnuPG-bug-id: 7338 +Signed-off-by: NIIBE Yutaka +Signed-off-by: Lucas Mülling +--- + tests/t-digest.c | 133 +++++++++++++++++++++++++++++++++++++++++++++++ + 1 file changed, 133 insertions(+) + +Index: libgcrypt-1.11.0/tests/t-digest.c +=================================================================== +--- libgcrypt-1.11.0.orig/tests/t-digest.c ++++ libgcrypt-1.11.0/tests/t-digest.c +@@ -39,6 +39,138 @@ static int in_fips_mode; + #endif + + static void ++check_md_o_w_r_c (void) ++{ ++ static struct { ++ int algo; ++ const char *data; ++ int datalen; ++ const char *expect; ++ int expect_failure; ++ unsigned int flags; ++ } tv[] = { ++#if USE_MD5 ++ { GCRY_MD_MD5, "abc", 3, ++ "\x90\x01\x50\x98\x3C\xD2\x4F\xB0\xD6\x96\x3F\x7D\x28\xE1\x7F\x72", 1 }, ++ { GCRY_MD_MD5, "abc", 3, ++ "\x90\x01\x50\x98\x3C\xD2\x4F\xB0\xD6\x96\x3F\x7D\x28\xE1\x7F\x72", 1, ++ GCRY_MD_FLAG_REJECT_NON_FIPS }, ++#endif ++#if USE_SHA1 ++ { GCRY_MD_SHA1, "abc", 3, ++ "\xA9\x99\x3E\x36\x47\x06\x81\x6A\xBA\x3E" ++ "\x25\x71\x78\x50\xC2\x6C\x9C\xD0\xD8\x9D" }, ++#endif ++ { GCRY_MD_SHA256, "abc", 3, ++ "\xba\x78\x16\xbf\x8f\x01\xcf\xea\x41\x41\x40\xde\x5d\xae\x22\x23" ++ "\xb0\x03\x61\xa3\x96\x17\x7a\x9c\xb4\x10\xff\x61\xf2\x00\x15\xad" }, ++ { GCRY_MD_SHA384, "abc", 3, ++ "\xcb\x00\x75\x3f\x45\xa3\x5e\x8b\xb5\xa0\x3d\x69\x9a\xc6\x50\x07" ++ "\x27\x2c\x32\xab\x0e\xde\xd1\x63\x1a\x8b\x60\x5a\x43\xff\x5b\xed" ++ "\x80\x86\x07\x2b\xa1\xe7\xcc\x23\x58\xba\xec\xa1\x34\xc8\x25\xa7" }, ++ { GCRY_MD_SHA512, "abc", 3, ++ "\xDD\xAF\x35\xA1\x93\x61\x7A\xBA\xCC\x41\x73\x49\xAE\x20\x41\x31" ++ "\x12\xE6\xFA\x4E\x89\xA9\x7E\xA2\x0A\x9E\xEE\xE6\x4B\x55\xD3\x9A" ++ "\x21\x92\x99\x2A\x27\x4F\xC1\xA8\x36\xBA\x3C\x23\xA3\xFE\xEB\xBD" ++ "\x45\x4D\x44\x23\x64\x3C\xE8\x0E\x2A\x9A\xC9\x4F\xA5\x4C\xA4\x9F" }, ++ { GCRY_MD_SHA3_256, "abc", 3, ++ "\x3a\x98\x5d\xa7\x4f\xe2\x25\xb2\x04\x5c\x17\x2d\x6b\xd3\x90\xbd" ++ "\x85\x5f\x08\x6e\x3e\x9d\x52\x5b\x46\xbf\xe2\x45\x11\x43\x15\x32" }, ++ { GCRY_MD_SHA3_384, "abc", 3, ++ "\xec\x01\x49\x82\x88\x51\x6f\xc9\x26\x45\x9f\x58\xe2\xc6\xad\x8d" ++ "\xf9\xb4\x73\xcb\x0f\xc0\x8c\x25\x96\xda\x7c\xf0\xe4\x9b\xe4\xb2" ++ "\x98\xd8\x8c\xea\x92\x7a\xc7\xf5\x39\xf1\xed\xf2\x28\x37\x6d\x25" }, ++ { GCRY_MD_SHA3_512, "abc", 3, ++ "\xb7\x51\x85\x0b\x1a\x57\x16\x8a\x56\x93\xcd\x92\x4b\x6b\x09\x6e" ++ "\x08\xf6\x21\x82\x74\x44\xf7\x0d\x88\x4f\x5d\x02\x40\xd2\x71\x2e" ++ "\x10\xe1\x16\xe9\x19\x2a\xf3\xc9\x1a\x7e\xc5\x76\x47\xe3\x93\x40" ++ "\x57\x34\x0b\x4c\xf4\x08\xd5\xa5\x65\x92\xf8\x27\x4e\xec\x53\xf0" } ++#if USE_RMD160 ++ , ++ { GCRY_MD_RMD160, "abc", 3, ++ "\x8e\xb2\x08\xf7\xe0\x5d\x98\x7a\x9b\x04" ++ "\x4a\x8e\x98\xc6\xb0\x87\xf1\x5a\x0b\xfc", 1 } ++#endif ++ }; ++ int tvidx; ++ unsigned char *hash; ++ int expectlen; ++ gpg_error_t err; ++ ++ for (tvidx=0; tvidx < DIM(tv); tvidx++) ++ { ++ gpg_err_code_t ec; ++ gcry_md_hd_t h; ++ ++ if (verbose) ++ fprintf (stderr, "checking gcry_md_open test %d\n", ++ tvidx); ++ ++ expectlen = gcry_md_get_algo_dlen (tv[tvidx].algo); ++ assert (expectlen != 0); ++ err = gcry_md_open (&h, tv[tvidx].algo, tv[tvidx].flags); ++ if (err) ++ { ++ if (in_fips_mode && (tv[tvidx].flags & GCRY_MD_FLAG_REJECT_NON_FIPS) ++ && tv[tvidx].expect_failure) ++ /* Here, an error is expected */ ++ ; ++ else ++ fail ("gcry_md_open test %d unexpectedly failed: %s\n", ++ tvidx, gpg_strerror (err)); ++ continue; ++ } ++ else ++ { ++ if (in_fips_mode && (tv[tvidx].flags & GCRY_MD_FLAG_REJECT_NON_FIPS) ++ && tv[tvidx].expect_failure) ++ /* This case, an error is expected, but we observed success */ ++ fail ("gcry_md_open test %d unexpectedly succeeded\n", tvidx); ++ } ++ ++ ++ ec = gcry_get_fips_service_indicator (); ++ if (ec == GPG_ERR_INV_OP) ++ { ++ /* libgcrypt is old, no support of the FIPS service indicator. */ ++ fail ("gcry_md_open test %d unexpectedly failed to check the FIPS service indicator.\n", ++ tvidx); ++ continue; ++ } ++ ++ if (in_fips_mode && !tv[tvidx].expect_failure && ec) ++ { ++ /* Success with the FIPS service indicator == 0 expected, but != 0. */ ++ fail ("gcry_md_open test %d unexpectedly set the indicator in FIPS mode.\n", ++ tvidx); ++ continue; ++ } ++ else if (in_fips_mode && tv[tvidx].expect_failure && !ec) ++ { ++ /* Success with the FIPS service indicator != 0 expected, but == 0. */ ++ fail ("gcry_md_open test %d unexpectedly cleared the indicator in FIPS mode.\n", ++ tvidx); ++ continue; ++ } ++ ++ gcry_md_write (h, tv[tvidx].data, tv[tvidx].datalen); ++ hash = gcry_md_read (h, tv[tvidx].algo); ++ if (memcmp (hash, tv[tvidx].expect, expectlen)) ++ { ++ int i; ++ ++ fail ("gcry_md_open test %d failed: mismatch\n", tvidx); ++ fputs ("got:", stderr); ++ for (i=0; i < expectlen; i++) ++ fprintf (stderr, " %02x", hash[i]); ++ putc ('\n', stderr); ++ } ++ ++ gcry_md_close (h); ++ } ++} ++ ++static void + check_digests (void) + { + static struct { +@@ -194,6 +326,7 @@ main (int argc, char **argv) + xgcry_control ((GCRYCTL_SET_DEBUG_FLAGS, 1u , 0)); + + check_digests (); ++ check_md_o_w_r_c (); + + return !!error_count; + } diff --git a/libgcrypt-jitterentropy-3.4.0.patch b/libgcrypt-jitterentropy-3.4.0.patch new file mode 100644 index 0000000..dbb77ba --- /dev/null +++ b/libgcrypt-jitterentropy-3.4.0.patch @@ -0,0 +1,618 @@ +Index: libgcrypt-1.10.0/random/jitterentropy-base.c +=================================================================== +--- libgcrypt-1.10.0.orig/random/jitterentropy-base.c ++++ libgcrypt-1.10.0/random/jitterentropy-base.c +@@ -42,7 +42,7 @@ + * require consumer to be updated (as long as this number + * is zero, the API is not considered stable and can + * change without a bump of the major version) */ +-#define MINVERSION 3 /* API compatible, ABI may change, functional ++#define MINVERSION 4 /* API compatible, ABI may change, functional + * enhancements only, consumer can be left unchanged if + * enhancements are not considered */ + #define PATCHLEVEL 0 /* API / ABI compatible, no functional changes, no +@@ -200,29 +200,38 @@ ssize_t jent_read_entropy(struct rand_da + tocopy = (DATA_SIZE_BITS / 8); + else + tocopy = len; +- memcpy(p, &ec->data, tocopy); ++ ++ jent_read_random_block(ec, p, tocopy); + + len -= tocopy; + p += tocopy; + } + + /* +- * To be on the safe side, we generate one more round of entropy +- * which we do not give out to the caller. That round shall ensure +- * that in case the calling application crashes, memory dumps, pages +- * out, or due to the CPU Jitter RNG lingering in memory for long +- * time without being moved and an attacker cracks the application, +- * all he reads in the entropy pool is a value that is NEVER EVER +- * being used for anything. Thus, he does NOT see the previous value +- * that was returned to the caller for cryptographic purposes. ++ * Enhanced backtracking support: At this point, the hash state ++ * contains the digest of the previous Jitter RNG collection round ++ * which is inserted there by jent_read_random_block with the SHA ++ * update operation. At the current code location we completed ++ * one request for a caller and we do not know how long it will ++ * take until a new request is sent to us. To guarantee enhanced ++ * backtracking resistance at this point (i.e. ensure that an attacker ++ * cannot obtain information about prior random numbers we generated), ++ * but still stirring the hash state with old data the Jitter RNG ++ * obtains a new message digest from its state and re-inserts it. ++ * After this operation, the Jitter RNG state is still stirred with ++ * the old data, but an attacker who gets access to the memory after ++ * this point cannot deduce the random numbers produced by the ++ * Jitter RNG prior to this point. + */ + /* +- * If we use secured memory, do not use that precaution as the secure +- * memory protects the entropy pool. Moreover, note that using this +- * call reduces the speed of the RNG by up to half ++ * If we use secured memory, where backtracking support may not be ++ * needed because the state is protected in a different method, ++ * it is permissible to drop this support. But strongly weigh the ++ * pros and cons considering that the SHA3 operation is not that ++ * expensive. + */ + #ifndef JENT_CPU_JITTERENTROPY_SECURE_MEMORY +- jent_random_data(ec); ++ jent_read_random_block(ec, NULL, 0); + #endif + + err: +@@ -379,6 +388,7 @@ static struct rand_data + *jent_entropy_collector_alloc_internal(unsigned int osr, unsigned int flags) + { + struct rand_data *entropy_collector; ++ uint32_t memsize = 0; + + /* + * Requesting disabling and forcing of internal timer +@@ -405,7 +415,7 @@ static struct rand_data + return NULL; + + if (!(flags & JENT_DISABLE_MEMORY_ACCESS)) { +- uint32_t memsize = jent_memsize(flags); ++ memsize = jent_memsize(flags); + + entropy_collector->mem = _gcry_calloc (1, memsize); + +@@ -431,13 +441,19 @@ static struct rand_data + entropy_collector->memaccessloops = JENT_MEMORY_ACCESSLOOPS; + } + ++ if (sha3_alloc(&entropy_collector->hash_state)) ++ goto err; ++ ++ /* Initialize the hash state */ ++ sha3_256_init(entropy_collector->hash_state); ++ + /* verify and set the oversampling rate */ + if (osr < JENT_MIN_OSR) + osr = JENT_MIN_OSR; + entropy_collector->osr = osr; + entropy_collector->flags = flags; + +- if (jent_fips_enabled() || (flags & JENT_FORCE_FIPS)) ++ if ((flags & JENT_FORCE_FIPS) || jent_fips_enabled()) + entropy_collector->fips_enabled = 1; + + /* Initialize the APT */ +@@ -469,7 +485,7 @@ static struct rand_data + + err: + if (entropy_collector->mem != NULL) +- jent_zfree(entropy_collector->mem, JENT_MEMORY_SIZE); ++ jent_zfree(entropy_collector->mem, memsize); + jent_zfree(entropy_collector, sizeof(struct rand_data)); + return NULL; + } +@@ -511,6 +527,7 @@ JENT_PRIVATE_STATIC + void jent_entropy_collector_free(struct rand_data *entropy_collector) + { + if (entropy_collector != NULL) { ++ sha3_dealloc(entropy_collector->hash_state); + jent_notime_disable(entropy_collector); + if (entropy_collector->mem != NULL) { + jent_zfree(entropy_collector->mem, +@@ -664,6 +681,7 @@ static inline int jent_entropy_init_comm + int ret; + + jent_notime_block_switch(); ++ jent_health_cb_block_switch(); + + if (sha3_tester()) + return EHASH; +@@ -710,6 +728,8 @@ int jent_entropy_init_ex(unsigned int os + if (ret) + return ret; + ++ ret = ENOTIME; ++ + /* Test without internal timer unless caller does not want it */ + if (!(flags & JENT_FORCE_INTERNAL_TIMER)) + ret = jent_time_entropy_init(osr, +@@ -732,3 +752,9 @@ int jent_entropy_switch_notime_impl(stru + return jent_notime_switch(new_thread); + } + #endif ++ ++JENT_PRIVATE_STATIC ++int jent_set_fips_failure_callback(jent_fips_failure_cb cb) ++{ ++ return jent_set_fips_failure_callback_internal(cb); ++} +Index: libgcrypt-1.10.0/random/jitterentropy-gcd.c +=================================================================== +--- libgcrypt-1.10.0.orig/random/jitterentropy-gcd.c ++++ libgcrypt-1.10.0/random/jitterentropy-gcd.c +@@ -113,12 +113,8 @@ int jent_gcd_analyze(uint64_t *delta_his + goto out; + } + +- /* +- * Ensure that we have variations in the time stamp below 100 for at +- * least 10% of all checks -- on some platforms, the counter increments +- * in multiples of 100, but not always +- */ +- if (running_gcd >= 100) { ++ /* Set a sensible maximum value. */ ++ if (running_gcd >= UINT32_MAX / 2) { + ret = ECOARSETIME; + goto out; + } +Index: libgcrypt-1.10.0/random/jitterentropy-health.c +=================================================================== +--- libgcrypt-1.10.0.orig/random/jitterentropy-health.c ++++ libgcrypt-1.10.0/random/jitterentropy-health.c +@@ -19,9 +19,24 @@ + * DAMAGE. + */ + +-#include "jitterentropy.h" + #include "jitterentropy-health.h" + ++static jent_fips_failure_cb fips_cb = NULL; ++static int jent_health_cb_switch_blocked = 0; ++ ++void jent_health_cb_block_switch(void) ++{ ++ jent_health_cb_switch_blocked = 1; ++} ++ ++int jent_set_fips_failure_callback_internal(jent_fips_failure_cb cb) ++{ ++ if (jent_health_cb_switch_blocked) ++ return -EAGAIN; ++ fips_cb = cb; ++ return 0; ++} ++ + /*************************************************************************** + * Lag Predictor Test + * +@@ -434,5 +449,9 @@ unsigned int jent_health_failure(struct + if (!ec->fips_enabled) + return 0; + ++ if (fips_cb && ec->health_failure) { ++ fips_cb(ec, ec->health_failure); ++ } ++ + return ec->health_failure; + } +Index: libgcrypt-1.10.0/random/jitterentropy-health.h +=================================================================== +--- libgcrypt-1.10.0.orig/random/jitterentropy-health.h ++++ libgcrypt-1.10.0/random/jitterentropy-health.h +@@ -20,11 +20,16 @@ + #ifndef JITTERENTROPY_HEALTH_H + #define JITTERENTROPY_HEALTH_H + ++#include "jitterentropy.h" ++ + #ifdef __cplusplus + extern "C" + { + #endif + ++void jent_health_cb_block_switch(void); ++int jent_set_fips_failure_callback_internal(jent_fips_failure_cb cb); ++ + static inline uint64_t jent_delta(uint64_t prev, uint64_t next) + { + return (next - prev); +Index: libgcrypt-1.10.0/random/jitterentropy-noise.c +=================================================================== +--- libgcrypt-1.10.0.orig/random/jitterentropy-noise.c ++++ libgcrypt-1.10.0/random/jitterentropy-noise.c +@@ -33,7 +33,7 @@ + * Update of the loop count used for the next round of + * an entropy collection. + * +- * @ec [in] entropy collector struct -- may be NULL ++ * @ec [in] entropy collector struct + * @bits [in] is the number of low bits of the timer to consider + * @min [in] is the number of bits we shift the timer value to the right at + * the end to make sure we have a guaranteed minimum value +@@ -61,16 +61,13 @@ static uint64_t jent_loop_shuffle(struct + * Mix the current state of the random number into the shuffle + * calculation to balance that shuffle a bit more. + */ +- if (ec) { +- jent_get_nstime_internal(ec, &time); +- time ^= ec->data[0]; +- } ++ jent_get_nstime_internal(ec, &time); + + /* + * We fold the time value as much as possible to ensure that as many + * bits of the time stamp are included as possible. + */ +- for (i = 0; ((DATA_SIZE_BITS + bits - 1) / bits) > i; i++) { ++ for (i = 0; (((sizeof(time) << 3) + bits - 1) / bits) > i; i++) { + shuffle ^= time & mask; + time = time >> bits; + } +@@ -91,11 +88,11 @@ static uint64_t jent_loop_shuffle(struct + * This function injects the individual bits of the time value into the + * entropy pool using a hash. + * +- * @ec [in] entropy collector struct -- may be NULL +- * @time [in] time stamp to be injected ++ * @ec [in] entropy collector struct ++ * @time [in] time delta to be injected + * @loop_cnt [in] if a value not equal to 0 is set, use the given value as + * number of loops to perform the hash operation +- * @stuck [in] Is the time stamp identified as stuck? ++ * @stuck [in] Is the time delta identified as stuck? + * + * Output: + * updated hash context +@@ -104,17 +101,19 @@ static void jent_hash_time(struct rand_d + uint64_t loop_cnt, unsigned int stuck) + { + HASH_CTX_ON_STACK(ctx); +- uint8_t itermediary[SHA3_256_SIZE_DIGEST]; ++ uint8_t intermediary[SHA3_256_SIZE_DIGEST]; + uint64_t j = 0; +- uint64_t hash_loop_cnt; + #define MAX_HASH_LOOP 3 + #define MIN_HASH_LOOP 0 + + /* Ensure that macros cannot overflow jent_loop_shuffle() */ + BUILD_BUG_ON((MAX_HASH_LOOP + MIN_HASH_LOOP) > 63); +- hash_loop_cnt = ++ uint64_t hash_loop_cnt = + jent_loop_shuffle(ec, MAX_HASH_LOOP, MIN_HASH_LOOP); + ++ /* Use the memset to shut up valgrind */ ++ memset(intermediary, 0, sizeof(intermediary)); ++ + sha3_256_init(&ctx); + + /* +@@ -125,35 +124,54 @@ static void jent_hash_time(struct rand_d + hash_loop_cnt = loop_cnt; + + /* +- * This loop basically slows down the SHA-3 operation depending +- * on the hash_loop_cnt. Each iteration of the loop generates the +- * same result. ++ * This loop fills a buffer which is injected into the entropy pool. ++ * The main reason for this loop is to execute something over which we ++ * can perform a timing measurement. The injection of the resulting ++ * data into the pool is performed to ensure the result is used and ++ * the compiler cannot optimize the loop away in case the result is not ++ * used at all. Yet that data is considered "additional information" ++ * considering the terminology from SP800-90A without any entropy. ++ * ++ * Note, it does not matter which or how much data you inject, we are ++ * interested in one Keccack1600 compression operation performed with ++ * the sha3_final. + */ + for (j = 0; j < hash_loop_cnt; j++) { +- sha3_update(&ctx, ec->data, SHA3_256_SIZE_DIGEST); +- sha3_update(&ctx, (uint8_t *)&time, sizeof(uint64_t)); ++ sha3_update(&ctx, intermediary, sizeof(intermediary)); ++ sha3_update(&ctx, (uint8_t *)&ec->rct_count, ++ sizeof(ec->rct_count)); ++ sha3_update(&ctx, (uint8_t *)&ec->apt_cutoff, ++ sizeof(ec->apt_cutoff)); ++ sha3_update(&ctx, (uint8_t *)&ec->apt_observations, ++ sizeof(ec->apt_observations)); ++ sha3_update(&ctx, (uint8_t *)&ec->apt_count, ++ sizeof(ec->apt_count)); ++ sha3_update(&ctx,(uint8_t *) &ec->apt_base, ++ sizeof(ec->apt_base)); + sha3_update(&ctx, (uint8_t *)&j, sizeof(uint64_t)); ++ sha3_final(&ctx, intermediary); ++ } + +- /* +- * If the time stamp is stuck, do not finally insert the value +- * into the entropy pool. Although this operation should not do +- * any harm even when the time stamp has no entropy, SP800-90B +- * requires that any conditioning operation to have an identical +- * amount of input data according to section 3.1.5. +- */ ++ /* ++ * Inject the data from the previous loop into the pool. This data is ++ * not considered to contain any entropy, but it stirs the pool a bit. ++ */ ++ sha3_update(ec->hash_state, intermediary, sizeof(intermediary)); + +- /* +- * The sha3_final operations re-initialize the context for the +- * next loop iteration. +- */ +- if (stuck || (j < hash_loop_cnt - 1)) +- sha3_final(&ctx, itermediary); +- else +- sha3_final(&ctx, ec->data); +- } ++ /* ++ * Insert the time stamp into the hash context representing the pool. ++ * ++ * If the time stamp is stuck, do not finally insert the value into the ++ * entropy pool. Although this operation should not do any harm even ++ * when the time stamp has no entropy, SP800-90B requires that any ++ * conditioning operation to have an identical amount of input data ++ * according to section 3.1.5. ++ */ ++ if (!stuck) ++ sha3_update(ec->hash_state, (uint8_t *)&time, sizeof(uint64_t)); + + jent_memset_secure(&ctx, SHA_MAX_CTX_SIZE); +- jent_memset_secure(itermediary, sizeof(itermediary)); ++ jent_memset_secure(intermediary, sizeof(intermediary)); + } + + #define MAX_ACC_LOOP_BIT 7 +@@ -184,13 +202,12 @@ static inline uint32_t xoshiro128starsta + + static void jent_memaccess(struct rand_data *ec, uint64_t loop_cnt) + { +- uint64_t i = 0; ++ uint64_t i = 0, time = 0; + union { + uint32_t u[4]; + uint8_t b[sizeof(uint32_t) * 4]; + } prngState = { .u = {0x8e93eec0, 0xce65608a, 0xa8d46b46, 0xe83cef69} }; + uint32_t addressMask; +- uint64_t acc_loop_cnt; + + if (NULL == ec || NULL == ec->mem) + return; +@@ -199,7 +216,7 @@ static void jent_memaccess(struct rand_d + + /* Ensure that macros cannot overflow jent_loop_shuffle() */ + BUILD_BUG_ON((MAX_ACC_LOOP_BIT + MIN_ACC_LOOP_BIT) > 63); +- acc_loop_cnt = ++ uint64_t acc_loop_cnt = + jent_loop_shuffle(ec, MAX_ACC_LOOP_BIT, MIN_ACC_LOOP_BIT); + + /* +@@ -213,8 +230,10 @@ static void jent_memaccess(struct rand_d + * "per-update: timing, it gets you mostly independent "per-update" + * timing, so we can now benefit from the Central Limit Theorem! + */ +- for (i = 0; i < sizeof(prngState); i++) +- prngState.b[i] ^= ec->data[i]; ++ for (i = 0; i < sizeof(prngState); i++) { ++ jent_get_nstime_internal(ec, &time); ++ prngState.b[i] ^= (uint8_t)(time & 0xff); ++ } + + /* + * testing purposes -- allow test app to set the counter, not +@@ -358,21 +377,21 @@ unsigned int jent_measure_jitter(struct + + /** + * Generator of one 256 bit random number +- * Function fills rand_data->data ++ * Function fills rand_data->hash_state + * + * @ec [in] Reference to entropy collector + */ + void jent_random_data(struct rand_data *ec) + { +- unsigned int k = 0, safety_factor = ENTROPY_SAFETY_FACTOR; ++ unsigned int k = 0, safety_factor = 0; + +- if (!ec->fips_enabled) +- safety_factor = 0; ++ if (ec->fips_enabled) ++ safety_factor = ENTROPY_SAFETY_FACTOR; + + /* priming of the ->prev_time value */ + jent_measure_jitter(ec, 0, NULL); + +- while (1) { ++ while (!jent_health_failure(ec)) { + /* If a stuck measurement is received, repeat measurement */ + if (jent_measure_jitter(ec, 0, NULL)) + continue; +@@ -385,3 +404,22 @@ void jent_random_data(struct rand_data * + break; + } + } ++ ++void jent_read_random_block(struct rand_data *ec, char *dst, size_t dst_len) ++{ ++ uint8_t jent_block[SHA3_256_SIZE_DIGEST]; ++ ++ BUILD_BUG_ON(SHA3_256_SIZE_DIGEST != (DATA_SIZE_BITS / 8)); ++ ++ /* The final operation automatically re-initializes the ->hash_state */ ++ sha3_final(ec->hash_state, jent_block); ++ if (dst_len) ++ memcpy(dst, jent_block, dst_len); ++ ++ /* ++ * Stir the new state with the data from the old state - the digest ++ * of the old data is not considered to have entropy. ++ */ ++ sha3_update(ec->hash_state, jent_block, sizeof(jent_block)); ++ jent_memset_secure(jent_block, sizeof(jent_block)); ++} +Index: libgcrypt-1.10.0/random/jitterentropy-noise.h +=================================================================== +--- libgcrypt-1.10.0.orig/random/jitterentropy-noise.h ++++ libgcrypt-1.10.0/random/jitterentropy-noise.h +@@ -31,6 +31,7 @@ unsigned int jent_measure_jitter(struct + uint64_t loop_cnt, + uint64_t *ret_current_delta); + void jent_random_data(struct rand_data *ec); ++void jent_read_random_block(struct rand_data *ec, char *dst, size_t dst_len); + + #ifdef __cplusplus + } +Index: libgcrypt-1.10.0/random/jitterentropy-sha3.c +=================================================================== +--- libgcrypt-1.10.0.orig/random/jitterentropy-sha3.c ++++ libgcrypt-1.10.0/random/jitterentropy-sha3.c +@@ -19,6 +19,7 @@ + */ + + #include "jitterentropy-sha3.h" ++#include "jitterentropy.h" + + /*************************************************************************** + * Message Digest Implementation +@@ -380,3 +381,23 @@ int sha3_tester(void) + + return 0; + } ++ ++int sha3_alloc(void **hash_state) ++{ ++ struct sha_ctx *tmp; ++ ++ tmp = jent_zalloc(SHA_MAX_CTX_SIZE); ++ if (!tmp) ++ return 1; ++ ++ *hash_state = tmp; ++ ++ return 0; ++} ++ ++void sha3_dealloc(void *hash_state) ++{ ++ struct sha_ctx *ctx = (struct sha_ctx *)hash_state; ++ ++ jent_zfree(ctx, SHA_MAX_CTX_SIZE); ++} +Index: libgcrypt-1.10.0/random/jitterentropy-sha3.h +=================================================================== +--- libgcrypt-1.10.0.orig/random/jitterentropy-sha3.h ++++ libgcrypt-1.10.0/random/jitterentropy-sha3.h +@@ -47,6 +47,8 @@ struct sha_ctx { + void sha3_256_init(struct sha_ctx *ctx); + void sha3_update(struct sha_ctx *ctx, const uint8_t *in, size_t inlen); + void sha3_final(struct sha_ctx *ctx, uint8_t *digest); ++int sha3_alloc(void **hash_state); ++void sha3_dealloc(void *hash_state); + int sha3_tester(void); + + #ifdef __cplusplus +Index: libgcrypt-1.10.0/random/jitterentropy-timer.c +=================================================================== +--- libgcrypt-1.10.0.orig/random/jitterentropy-timer.c ++++ libgcrypt-1.10.0/random/jitterentropy-timer.c +@@ -202,8 +202,8 @@ int jent_notime_enable(struct rand_data + if (jent_force_internal_timer || (flags & JENT_FORCE_INTERNAL_TIMER)) { + /* Self test not run yet */ + if (!jent_force_internal_timer && +- jent_time_entropy_init(flags | JENT_FORCE_INTERNAL_TIMER, +- ec->osr)) ++ jent_time_entropy_init(ec->osr, ++ flags | JENT_FORCE_INTERNAL_TIMER)) + return EHEALTH; + + ec->enable_notime = 1; +Index: libgcrypt-1.10.0/random/jitterentropy.h +=================================================================== +--- libgcrypt-1.10.0.orig/random/jitterentropy.h ++++ libgcrypt-1.10.0/random/jitterentropy.h +@@ -49,7 +49,7 @@ + ***************************************************************************/ + + /* +- * Enable timer-less timer support ++ * Enable timer-less timer support with JENT_CONF_ENABLE_INTERNAL_TIMER + * + * In case the hardware is identified to not provide a high-resolution time + * stamp, this option enables a built-in high-resolution time stamp mechanism. +@@ -166,7 +166,7 @@ struct rand_data + * of the RNG are marked as SENSITIVE. A user must not + * access that information while the RNG executes its loops to + * calculate the next random value. */ +- uint8_t data[SHA3_256_SIZE_DIGEST]; /* SENSITIVE Actual random number */ ++ void *hash_state; /* SENSITIVE hash state entropy pool */ + uint64_t prev_time; /* SENSITIVE Previous time stamp */ + #define DATA_SIZE_BITS (SHA3_256_SIZE_DIGEST_BITS) + +@@ -378,28 +378,34 @@ int jent_entropy_init(void); + JENT_PRIVATE_STATIC + int jent_entropy_init_ex(unsigned int osr, unsigned int flags); + ++/* ++ * Set a callback to run on health failure in FIPS mode. ++ * This function will take an action determined by the caller. ++ */ ++typedef void (*jent_fips_failure_cb)(struct rand_data *ec, ++ unsigned int health_failure); ++JENT_PRIVATE_STATIC ++int jent_set_fips_failure_callback(jent_fips_failure_cb cb); ++ + /* return version number of core library */ + JENT_PRIVATE_STATIC + unsigned int jent_version(void); + +-#ifdef JENT_CONF_ENABLE_INTERNAL_TIMER + /* Set a different thread handling logic for the notimer support */ + JENT_PRIVATE_STATIC + int jent_entropy_switch_notime_impl(struct jent_notime_thread *new_thread); +-#endif + + /* -- END of Main interface functions -- */ + + /* -- BEGIN timer-less threading support functions to prevent code dupes -- */ + +-struct jent_notime_ctx { + #ifdef JENT_CONF_ENABLE_INTERNAL_TIMER ++ ++struct jent_notime_ctx { + pthread_attr_t notime_pthread_attr; /* pthreads library */ + pthread_t notime_thread_id; /* pthreads thread ID */ +-#endif + }; + +-#ifdef JENT_CONF_ENABLE_INTERNAL_TIMER + + JENT_PRIVATE_STATIC + int jent_notime_init(void **ctx); +Index: libgcrypt-1.10.0/random/jitterentropy-base-user.h +=================================================================== +--- libgcrypt-1.10.0.orig/random/jitterentropy-base-user.h ++++ libgcrypt-1.10.0/random/jitterentropy-base-user.h +@@ -213,12 +213,12 @@ static inline void jent_get_cachesize(lo + ext = strstr(buf, "K"); + if (ext) { + shift = 10; +- ext = '\0'; ++ *ext = '\0'; + } else { + ext = strstr(buf, "M"); + if (ext) { + shift = 20; +- ext = '\0'; ++ *ext = '\0'; + } + } + diff --git a/libgcrypt-md-Fix-gcry_md_algo_info-to-mark-reject-under-FIPS-mode.patch b/libgcrypt-md-Fix-gcry_md_algo_info-to-mark-reject-under-FIPS-mode.patch new file mode 100644 index 0000000..25f5904 --- /dev/null +++ b/libgcrypt-md-Fix-gcry_md_algo_info-to-mark-reject-under-FIPS-mode.patch @@ -0,0 +1,82 @@ +From 2f17a98a80b155e750ab77d4703e33612e545d58 Mon Sep 17 00:00:00 2001 +From: NIIBE Yutaka +Date: Tue, 25 Feb 2025 16:27:25 +0900 +Subject: [PATCH 1/4] md: Fix gcry_md_algo_info to mark/reject under FIPS mode. +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* cipher/md.c (check_digest_algo): Fix for marking non-compliance. +* src/visibility.c (gcry_md_algo_info): Add check with +fips_is_operational. + +-- + +GnuPG-bug-id: 7338 +Signed-off-by: NIIBE Yutaka +Signed-off-by: Lucas Mülling +--- + cipher/md.c | 26 ++++++++++++++++++++++---- + src/visibility.c | 3 +++ + 2 files changed, 25 insertions(+), 4 deletions(-) + +diff --git a/cipher/md.c b/cipher/md.c +index f600e7bb..caf33afc 100644 +--- a/cipher/md.c ++++ b/cipher/md.c +@@ -436,16 +436,34 @@ _gcry_md_algo_name (int algorithm) + + + static gcry_err_code_t +-check_digest_algo (int algorithm) ++check_digest_algo (int algo) + { + const gcry_md_spec_t *spec; ++ int reject = 0; + +- spec = spec_from_algo (algorithm); +- if (spec && !spec->flags.disabled && (spec->flags.fips || !fips_mode ())) ++ spec = spec_from_algo (algo); ++ if (!spec) ++ return GPG_ERR_DIGEST_ALGO; ++ ++ if (spec->flags.disabled) ++ return GPG_ERR_DIGEST_ALGO; ++ ++ if (!fips_mode ()) + return 0; + +- return GPG_ERR_DIGEST_ALGO; ++ if (spec->flags.fips) ++ return 0; ++ ++ if (algo == GCRY_MD_MD5) ++ reject = fips_check_rejection (GCRY_FIPS_FLAG_REJECT_MD_MD5); ++ else ++ reject = fips_check_rejection (GCRY_FIPS_FLAG_REJECT_MD_OTHERS); ++ ++ if (reject) ++ return GPG_ERR_DIGEST_ALGO; + ++ fips_service_indicator_mark_non_compliant (); ++ return 0; + } + + +diff --git a/src/visibility.c b/src/visibility.c +index e02d6cfe..4134446a 100644 +--- a/src/visibility.c ++++ b/src/visibility.c +@@ -1373,6 +1373,9 @@ gcry_md_info (gcry_md_hd_t h, int what, void *buffer, size_t *nbytes) + gcry_error_t + gcry_md_algo_info (int algo, int what, void *buffer, size_t *nbytes) + { ++ if (!fips_is_operational ()) ++ return gpg_error (fips_not_operational ()); ++ fips_service_indicator_init (); + return gpg_error (_gcry_md_algo_info (algo, what, buffer, nbytes)); + } + +-- +2.49.0 + diff --git a/libgcrypt-md-Make-SHA-1-non-FIPS-internally-for-1.12-API.patch b/libgcrypt-md-Make-SHA-1-non-FIPS-internally-for-1.12-API.patch new file mode 100644 index 0000000..bbea9bb --- /dev/null +++ b/libgcrypt-md-Make-SHA-1-non-FIPS-internally-for-1.12-API.patch @@ -0,0 +1,154 @@ +From 4ee91a94bcdad32aed4364d09e3daf8841fa579f Mon Sep 17 00:00:00 2001 +From: NIIBE Yutaka +Date: Tue, 11 Mar 2025 14:01:11 +0900 +Subject: [PATCH 11/14] md: Make SHA-1 non-FIPS internally for 1.12 API. +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* src/gcrypt.h.in (GCRY_FIPS_FLAG_REJECT_MD_SHA1): New. +* cipher/md.c (check_digest_algo_spec, _gcry_md_open, md_enable) +(_gcry_md_enable, md_copy): Care about SHA1. +* cipher/sha1.c (_gcry_digest_spec_sha1): Make SHA1 non-FIPS. +* tests/t-fips-service-ind.c (check_mac_o_w_r_c): SHA1 is non-FIPS. +(check_md_o_w_r_c, check_hash_buffer, check_hash_buffers): Likewise. +(main): Add GCRY_FIPS_FLAG_REJECT_MD_SHA1 for gcry_control. + +-- + +For 1.10 ABI (which 1.11 keeps), SHA1 is an approved hash function +(while its use in public key crypto is non-FIPS). + +For 1.12 API, the dynamic FIPS service indicator is going to be added. + +In 1.11.1 implementation, we are trying to support 1.12 dynamic FIPS +service indicator in forward-compatible way. For this purpose, +internally, it's specified as non-FIPS in _gcry_digest_spec_sha1. + +Note that update for tests/basic.c and tests/pkcs1v2.c are needed to +use SHA256 (or one of approved hash functions) in 1.12, so that test +program can be a reference for programmers. + +Co-authored-by: Lucas Mulling +Signed-off-by: NIIBE Yutaka +Signed-off-by: Lucas Mülling +--- + cipher/md.c | 10 ++++++++++ + cipher/sha1.c | 2 +- + src/gcrypt.h.in | 1 + + tests/t-fips-service-ind.c | 9 +++++---- + 4 files changed, 17 insertions(+), 5 deletions(-) + +Index: libgcrypt-1.11.0/cipher/md.c +=================================================================== +--- libgcrypt-1.11.0.orig/cipher/md.c ++++ libgcrypt-1.11.0/cipher/md.c +@@ -451,6 +451,8 @@ check_digest_algo_spec (int algo, const + + if (algo == GCRY_MD_MD5) + reject = fips_check_rejection (GCRY_FIPS_FLAG_REJECT_MD_MD5); ++ else if (algo == GCRY_MD_SHA1) ++ reject = fips_check_rejection (GCRY_FIPS_FLAG_REJECT_MD_SHA1); + else + reject = fips_check_rejection (GCRY_FIPS_FLAG_REJECT_MD_OTHERS); + +@@ -590,6 +592,8 @@ _gcry_md_open (gcry_md_hd_t *h, int algo + + if (algo == GCRY_MD_MD5) + reject = fips_check_rejection (GCRY_FIPS_FLAG_REJECT_MD_MD5); ++ else if (algo == GCRY_MD_SHA1) ++ reject = fips_check_rejection (GCRY_FIPS_FLAG_REJECT_MD_SHA1); + else + reject = fips_check_rejection (GCRY_FIPS_FLAG_REJECT_MD_OTHERS); + +@@ -625,6 +629,8 @@ md_enable (gcry_md_hd_t hd, int algorith + + if (algorithm == GCRY_MD_MD5) + reject = fips_check_rejection (GCRY_FIPS_FLAG_REJECT_MD_MD5); ++ else if (algorithm == GCRY_MD_SHA1) ++ reject = fips_check_rejection (GCRY_FIPS_FLAG_REJECT_MD_SHA1); + else + reject = fips_check_rejection (GCRY_FIPS_FLAG_REJECT_MD_OTHERS); + +@@ -703,6 +709,8 @@ _gcry_md_enable (gcry_md_hd_t hd, int al + + if (algorithm == GCRY_MD_MD5) + reject = fips_check_rejection (GCRY_FIPS_FLAG_REJECT_MD_MD5); ++ else if (algorithm == GCRY_MD_SHA1) ++ reject = fips_check_rejection (GCRY_FIPS_FLAG_REJECT_MD_SHA1); + else + reject = fips_check_rejection (GCRY_FIPS_FLAG_REJECT_MD_OTHERS); + +@@ -780,6 +788,8 @@ md_copy (gcry_md_hd_t ahd, gcry_md_hd_t + + if (spec->algo == GCRY_MD_MD5) + reject |= fips_check_rejection (GCRY_FIPS_FLAG_REJECT_MD_MD5); ++ else if (spec->algo == GCRY_MD_SHA1) ++ reject = fips_check_rejection (GCRY_FIPS_FLAG_REJECT_MD_SHA1); + else + reject |= fips_check_rejection (GCRY_FIPS_FLAG_REJECT_MD_OTHERS); + } +Index: libgcrypt-1.11.0/cipher/sha1.c +=================================================================== +--- libgcrypt-1.11.0.orig/cipher/sha1.c ++++ libgcrypt-1.11.0/cipher/sha1.c +@@ -759,7 +759,7 @@ static const gcry_md_oid_spec_t oid_spec + + const gcry_md_spec_t _gcry_digest_spec_sha1 = + { +- GCRY_MD_SHA1, {0, 1}, ++ GCRY_MD_SHA1, {0, 0}, + "SHA1", asn, DIM (asn), oid_spec_sha1, 20, + sha1_init, _gcry_md_block_write, sha1_final, sha1_read, NULL, + _gcry_sha1_hash_buffers, +Index: libgcrypt-1.11.0/src/gcrypt.h.in +=================================================================== +--- libgcrypt-1.11.0.orig/src/gcrypt.h.in ++++ libgcrypt-1.11.0/src/gcrypt.h.in +@@ -1982,6 +1982,7 @@ char *gcry_get_config (int mode, const c + #define GCRY_FIPS_FLAG_REJECT_PK_GOST_SM2 (1 << 7) + #define GCRY_FIPS_FLAG_REJECT_CIPHER_MODE (1 << 8) + /**/ ++#define GCRY_FIPS_FLAG_REJECT_MD_SHA1 (1 << 9) + #define GCRY_FIPS_FLAG_REJECT_PK_ECC_K (1 << 10) + #define GCRY_FIPS_FLAG_REJECT_PK_FLAGS (1 << 11) + +Index: libgcrypt-1.11.0/tests/t-fips-service-ind.c +=================================================================== +--- libgcrypt-1.11.0.orig/tests/t-fips-service-ind.c ++++ libgcrypt-1.11.0/tests/t-fips-service-ind.c +@@ -1107,7 +1107,7 @@ check_mac_o_w_r_c (int reject) + #if USE_SHA1 + { GCRY_MAC_HMAC_SHA1, "hmac input abc", 14, "hmac key input", 14, + "\xc9\x62\x9d\x16\x0f\xc2\xc4\xcd\x38\xac\x3a\x00\xdc\x29\x61\x03" +- "\x69\x50\xd7\x3a" }, ++ "\x69\x50\xd7\x3a", 1 }, + #endif + { GCRY_MAC_HMAC_SHA256, "hmac input abc", 14, "hmac key input", 14, + "\x6a\xda\x4d\xd5\xf3\xa7\x32\x9d\xd2\x55\xc0\x7f\xe6\x0a\x93\xb8" +@@ -1264,7 +1264,7 @@ check_md_o_w_r_c (int reject) + #if USE_SHA1 + { GCRY_MD_SHA1, "abc", 3, + "\xA9\x99\x3E\x36\x47\x06\x81\x6A\xBA\x3E" +- "\x25\x71\x78\x50\xC2\x6C\x9C\xD0\xD8\x9D" }, ++ "\x25\x71\x78\x50\xC2\x6C\x9C\xD0\xD8\x9D", 1 }, + #endif + { GCRY_MD_SHA256, "abc", 3, + "\xba\x78\x16\xbf\x8f\x01\xcf\xea\x41\x41\x40\xde\x5d\xae\x22\x23" +@@ -1389,7 +1389,7 @@ check_digests (void) + #endif + { GCRY_MD_SHA1, "abc", 3, + "\xA9\x99\x3E\x36\x47\x06\x81\x6A\xBA\x3E" +- "\x25\x71\x78\x50\xC2\x6C\x9C\xD0\xD8\x9D" }, ++ "\x25\x71\x78\x50\xC2\x6C\x9C\xD0\xD8\x9D", 1 }, + { GCRY_MD_SHA256, "abc", 3, + "\xba\x78\x16\xbf\x8f\x01\xcf\xea\x41\x41\x40\xde\x5d\xae\x22\x23" + "\xb0\x03\x61\xa3\x96\x17\x7a\x9c\xb4\x10\xff\x61\xf2\x00\x15\xad" }, +@@ -1701,6 +1701,7 @@ main (int argc, char **argv) + | GCRY_FIPS_FLAG_REJECT_CIPHER_MODE + | GCRY_FIPS_FLAG_REJECT_PK_MD + | GCRY_FIPS_FLAG_REJECT_PK_GOST_SM2 ++ | GCRY_FIPS_FLAG_REJECT_MD_SHA1 + | GCRY_FIPS_FLAG_REJECT_PK_ECC_K + | GCRY_FIPS_FLAG_REJECT_PK_FLAGS + | GCRY_FIPS_FLAG_REJECT_COMPAT110))); diff --git a/libgcrypt-md-Use-check_digest_algo_spec-in-_gcry_md_selftest.patch b/libgcrypt-md-Use-check_digest_algo_spec-in-_gcry_md_selftest.patch new file mode 100644 index 0000000..75489df --- /dev/null +++ b/libgcrypt-md-Use-check_digest_algo_spec-in-_gcry_md_selftest.patch @@ -0,0 +1,74 @@ +From ce4755d5c5500cede6d7d380fdab2d15f5d77796 Mon Sep 17 00:00:00 2001 +From: NIIBE Yutaka +Date: Wed, 26 Feb 2025 10:23:28 +0900 +Subject: [PATCH 2/4] md: Use check_digest_algo_spec in _gcry_md_selftest. +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* cipher/md.c (check_digest_algo_spec): New. +(check_digest_algo): Use check_digest_algo_spec. +(_gcry_md_selftest): Likewise. + +-- + +GnuPG-bug-id: 7338 +Signed-off-by: NIIBE Yutaka +Signed-off-by: Lucas Mülling +--- + cipher/md.c | 22 +++++++++++++--------- + 1 file changed, 13 insertions(+), 9 deletions(-) + +diff --git a/cipher/md.c b/cipher/md.c +index caf33afc..a8027e9e 100644 +--- a/cipher/md.c ++++ b/cipher/md.c +@@ -436,15 +436,10 @@ _gcry_md_algo_name (int algorithm) + + + static gcry_err_code_t +-check_digest_algo (int algo) ++check_digest_algo_spec (int algo, const gcry_md_spec_t *spec) + { +- const gcry_md_spec_t *spec; + int reject = 0; + +- spec = spec_from_algo (algo); +- if (!spec) +- return GPG_ERR_DIGEST_ALGO; +- + if (spec->flags.disabled) + return GPG_ERR_DIGEST_ALGO; + +@@ -466,6 +461,17 @@ check_digest_algo (int algo) + return 0; + } + ++static gcry_err_code_t ++check_digest_algo (int algo) ++{ ++ const gcry_md_spec_t *spec = spec_from_algo (algo); ++ ++ if (!spec) ++ return GPG_ERR_DIGEST_ALGO; ++ else ++ return check_digest_algo_spec (algo, spec); ++} ++ + + /**************** + * Open a message digest handle for use with algorithm ALGO. +@@ -1808,9 +1814,7 @@ _gcry_md_selftest (int algo, int extended, selftest_report_func_t report) + const gcry_md_spec_t *spec; + + spec = spec_from_algo (algo); +- if (spec && !spec->flags.disabled +- && (spec->flags.fips || !fips_mode ()) +- && spec->selftest) ++ if (spec && !check_digest_algo_spec (algo, spec) && spec->selftest) + ec = spec->selftest (algo, extended, report); + else + { +-- +2.49.0 + diff --git a/libgcrypt-no-deprecated-grep-alias.patch b/libgcrypt-no-deprecated-grep-alias.patch new file mode 100644 index 0000000..ba0dde8 --- /dev/null +++ b/libgcrypt-no-deprecated-grep-alias.patch @@ -0,0 +1,35 @@ +--- libgcrypt-1.10.3.orig/acinclude.m4 ++++ libgcrypt-1.10.3/acinclude.m4 +@@ -130,10 +130,10 @@ EOF + ac_nlist=conftest.nm + if AC_TRY_EVAL(NM conftest.$ac_objext \| $lt_cv_sys_global_symbol_pipe \| cut -d \' \' -f 2 \> $ac_nlist) && test -s "$ac_nlist"; then + # See whether the symbols have a leading underscore. +- if egrep '^_nm_test_func' "$ac_nlist" >/dev/null; then ++ if grep -E '^_nm_test_func' "$ac_nlist" >/dev/null; then + ac_cv_sys_symbol_underscore=yes + else +- if egrep '^nm_test_func ' "$ac_nlist" >/dev/null; then ++ if grep -E '^nm_test_func ' "$ac_nlist" >/dev/null; then + : + else + echo "configure: cannot find nm_test_func in $ac_nlist" >&AS_MESSAGE_LOG_FD +--- libgcrypt-1.10.3.orig/src/libgcrypt-config.in ++++ libgcrypt-1.10.3/src/libgcrypt-config.in +@@ -154,7 +154,7 @@ if test "$echo_cflags" = "yes"; then + + tmp="" + for i in $includes $cflags_final; do +- if echo "$tmp" | fgrep -v -- "$i" >/dev/null; then ++ if echo "$tmp" | @GREP@ -F -v -- "$i" >/dev/null; then + tmp="$tmp $i" + fi + done +@@ -175,7 +175,7 @@ if test "$echo_libs" = "yes"; then + + tmp="" + for i in $libdirs $libs_final; do +- if echo "$tmp" | fgrep -v -- "$i" >/dev/null; then ++ if echo "$tmp" | @GREP@ -F -v -- "$i" >/dev/null; then + tmp="$tmp $i" + fi + done diff --git a/libgcrypt-nobetasuffix.patch b/libgcrypt-nobetasuffix.patch new file mode 100644 index 0000000..3d4593a --- /dev/null +++ b/libgcrypt-nobetasuffix.patch @@ -0,0 +1,24 @@ +Index: libgcrypt-1.10.2/autogen.sh +=================================================================== +--- libgcrypt-1.10.2.orig/autogen.sh ++++ libgcrypt-1.10.2/autogen.sh +@@ -249,7 +249,7 @@ if [ "$myhost" = "find-version" ]; then + fi + + beta=no +- if [ -e .git ]; then ++ if false; then + ingit=yes + tmp=$(git describe --match "${matchstr1}" --long 2>/dev/null) + tmp=$(echo "$tmp" | sed s/^"$package"//) +@@ -265,8 +265,8 @@ if [ "$myhost" = "find-version" ]; then + rvd=$((0x$(echo ${rev} | dd bs=1 count=4 2>/dev/null))) + else + ingit=no +- beta=yes +- tmp="-unknown" ++ beta=no ++ tmp="" + rev="0000000" + rvd="0" + fi diff --git a/libgcrypt-ppc-enable-P10-assembly-with-ENABLE_FORCE_SOF.patch b/libgcrypt-ppc-enable-P10-assembly-with-ENABLE_FORCE_SOF.patch new file mode 100644 index 0000000..8ef3197 --- /dev/null +++ b/libgcrypt-ppc-enable-P10-assembly-with-ENABLE_FORCE_SOF.patch @@ -0,0 +1,76 @@ +commit 2c5e5ab6843d747c4b877d2c6f47226f61e9ff14 +Author: Jussi Kivilinna +Date: Sun Jun 12 21:51:34 2022 +0300 + + ppc enable P10 assembly with ENABLE_FORCE_SOFT_HWFEATURES on arch 3.00 + + * cipher/chacha20.c (chacha20_do_setkey) [USE_PPC_VEC]: Enable + P10 assembly for HWF_PPC_ARCH_3_00 if ENABLE_FORCE_SOFT_HWFEATURES is + defined. + * cipher/poly1305.c (poly1305_init) [POLY1305_USE_PPC_VEC]: Likewise. + * cipher/rijndael.c (do_setkey) [USE_PPC_CRYPTO_WITH_PPC9LE]: Likewise. + --- + + This change allows testing P10 implementations with P9 and with QEMU-PPC. + + GnuPG-bug-id: 6006 + Signed-off-by: Jussi Kivilinna + +Index: libgcrypt-1.10.2/cipher/chacha20.c +=================================================================== +--- libgcrypt-1.10.2.orig/cipher/chacha20.c ++++ libgcrypt-1.10.2/cipher/chacha20.c +@@ -484,6 +484,11 @@ chacha20_do_setkey (CHACHA20_context_t * + ctx->use_ppc = (features & HWF_PPC_ARCH_2_07) != 0; + # ifndef WORDS_BIGENDIAN + ctx->use_p10 = (features & HWF_PPC_ARCH_3_10) != 0; ++# ifdef ENABLE_FORCE_SOFT_HWFEATURES ++ /* HWF_PPC_ARCH_3_10 above is used as soft HW-feature indicator for P10. ++ * Actual implementation works with HWF_PPC_ARCH_3_00 also. */ ++ ctx->use_p10 |= (features & HWF_PPC_ARCH_3_00) != 0; ++# endif + # endif + #endif + #ifdef USE_S390X_VX +Index: libgcrypt-1.10.2/cipher/poly1305.c +=================================================================== +--- libgcrypt-1.10.2.orig/cipher/poly1305.c ++++ libgcrypt-1.10.2/cipher/poly1305.c +@@ -90,11 +90,19 @@ static void poly1305_init (poly1305_cont + const byte key[POLY1305_KEYLEN]) + { + POLY1305_STATE *st = &ctx->state; ++ unsigned int features = _gcry_get_hw_features (); + + #ifdef POLY1305_USE_PPC_VEC +- ctx->use_p10 = (_gcry_get_hw_features () & HWF_PPC_ARCH_3_10) != 0; ++ ctx->use_p10 = (features & HWF_PPC_ARCH_3_10) != 0; ++# ifdef ENABLE_FORCE_SOFT_HWFEATURES ++ /* HWF_PPC_ARCH_3_10 above is used as soft HW-feature indicator for P10. ++ * Actual implementation works with HWF_PPC_ARCH_3_00 also. */ ++ ctx->use_p10 |= (features & HWF_PPC_ARCH_3_00) != 0; ++# endif + #endif + ++ (void)features; ++ + ctx->leftover = 0; + + st->h[0] = 0; +Index: libgcrypt-1.10.2/cipher/rijndael.c +=================================================================== +--- libgcrypt-1.10.2.orig/cipher/rijndael.c ++++ libgcrypt-1.10.2/cipher/rijndael.c +@@ -605,6 +605,12 @@ do_setkey (RIJNDAEL_context *ctx, const + bulk_ops->xts_crypt = _gcry_aes_ppc9le_xts_crypt; + if (hwfeatures & HWF_PPC_ARCH_3_10) /* for P10 */ + bulk_ops->gcm_crypt = _gcry_aes_p10le_gcm_crypt; ++# ifdef ENABLE_FORCE_SOFT_HWFEATURES ++ /* HWF_PPC_ARCH_3_10 above is used as soft HW-feature indicator for P10. ++ * Actual implementation works with HWF_PPC_ARCH_3_00 also. */ ++ if (hwfeatures & HWF_PPC_ARCH_3_00) ++ bulk_ops->gcm_crypt = _gcry_aes_p10le_gcm_crypt; ++# endif + } + #endif + #ifdef USE_PPC_CRYPTO diff --git a/libgcrypt-rol64-redefinition.patch b/libgcrypt-rol64-redefinition.patch new file mode 100644 index 0000000..bb76b2f --- /dev/null +++ b/libgcrypt-rol64-redefinition.patch @@ -0,0 +1,16 @@ +Index: libgcrypt-1.11.0/cipher/bithelp.h +=================================================================== +--- libgcrypt-1.11.0.orig/cipher/bithelp.h ++++ libgcrypt-1.11.0/cipher/bithelp.h +@@ -35,11 +35,6 @@ static inline u32 ror(u32 x, int n) + return ( (x >> (n&(32-1))) | (x << ((32-n)&(32-1))) ); + } + +-static inline u64 rol64(u64 x, int n) +-{ +- return ( (x << (n&(64-1))) | (x >> ((64-n)&(64-1))) ); +-} +- + /* Byte swap for 32-bit and 64-bit integers. If available, use compiler + provided helpers. */ + #ifdef HAVE_BUILTIN_BSWAP32 diff --git a/libgcrypt-tests-Add-more-tests-to-tests-t-fips-service-ind.patch b/libgcrypt-tests-Add-more-tests-to-tests-t-fips-service-ind.patch new file mode 100644 index 0000000..c0058d2 --- /dev/null +++ b/libgcrypt-tests-Add-more-tests-to-tests-t-fips-service-ind.patch @@ -0,0 +1,382 @@ +From d71c88f78a4f1b72f92de90791fc6fe81a3cb861 Mon Sep 17 00:00:00 2001 +From: NIIBE Yutaka +Date: Tue, 24 Dec 2024 17:03:48 +0900 +Subject: [PATCH 17/19] tests: Add more tests to tests/t-fips-service-ind. +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* tests/t-fips-service-ind.c (check_pk_g_t_n_c, check_pk_s_v): New. +(main): Call check_pk_g_t_n_c and check_pk_s_v. + +-- + +GnuPG-bug-id: 7338 +Signed-off-by: NIIBE Yutaka +Signed-off-by: Lucas Mülling +--- + tests/t-fips-service-ind.c | 334 +++++++++++++++++++++++++++++++++++++ + 1 file changed, 334 insertions(+) + +diff --git a/tests/t-fips-service-ind.c b/tests/t-fips-service-ind.c +index 64e1e135..90d92c70 100644 +--- a/tests/t-fips-service-ind.c ++++ b/tests/t-fips-service-ind.c +@@ -40,6 +40,336 @@ static int in_fips_mode; + # include + #endif + ++/* Check gcry_pk_genkey, gcry_pk_testkey, gcry_pk_get_nbits, gcry_pk_get_curve API. */ ++static void ++check_pk_g_t_n_c (int reject) ++{ ++ static struct { ++ const char *keyparms; ++ int expect_failure; ++ } tv[] = { ++ { ++ "(genkey (ecc (curve nistp256)))", ++ 0 ++ }, ++ { /* non-compliant curve */ ++ "(genkey (ecc (curve secp256k1)))", ++ 1 ++ } ++ }; ++ int tvidx; ++ gpg_error_t err; ++ gpg_err_code_t ec; ++ ++ for (tvidx=0; tvidx < DIM(tv); tvidx++) ++ { ++ gcry_sexp_t s_kp = NULL; ++ gcry_sexp_t s_sk = NULL; ++ int nbits; ++ const char *name; ++ ++ if (verbose) ++ info ("checking gcry_pk_{genkey,testkey,get_nbits,get_curve} test %d\n", tvidx); ++ ++ err = gcry_sexp_build (&s_kp, NULL, tv[tvidx].keyparms); ++ if (err) ++ { ++ fail ("error building SEXP for test, %s: %s", ++ "keyparms", gpg_strerror (err)); ++ goto next; ++ } ++ ++ err = gcry_pk_genkey (&s_sk, s_kp); ++ if (err) ++ { ++ if (in_fips_mode && reject && tv[tvidx].expect_failure) ++ /* Here, an error is expected */ ++ ; ++ else ++ fail ("gcry_pk_genkey failed: %s", gpg_strerror (err)); ++ goto next; ++ } ++ else ++ { ++ if (in_fips_mode && reject && tv[tvidx].expect_failure) ++ { ++ fail ("gcry_pk_genkey test %d unexpectedly succeeded", tvidx); ++ goto next; ++ } ++ } ++ ++ ec = gcry_get_fips_service_indicator (); ++ if (ec == GPG_ERR_INV_OP) ++ { ++ /* libgcrypt is old, no support of the FIPS service indicator. */ ++ fail ("gcry_pk_genkey test %d unexpectedly failed to check the FIPS service indicator.\n", ++ tvidx); ++ goto next; ++ } ++ ++ if (in_fips_mode && !tv[tvidx].expect_failure && ec) ++ { ++ /* Success with the FIPS service indicator == 0 expected, but != 0. */ ++ fail ("gcry_pk_genkey test %d unexpectedly set the indicator in FIPS mode.\n", ++ tvidx); ++ goto next; ++ } ++ else if (in_fips_mode && tv[tvidx].expect_failure && !ec) ++ { ++ /* Success with the FIPS service indicator != 0 expected, but == 0. */ ++ fail ("gcry_pk_genkey test %d unexpectedly cleared the indicator in FIPS mode.\n", ++ tvidx); ++ goto next; ++ } ++ ++ err = gcry_pk_testkey (s_sk); ++ if (err) ++ { ++ fail ("gcry_pk_testkey failed for test: %s", gpg_strerror (err)); ++ goto next; ++ } ++ ++ ec = gcry_get_fips_service_indicator (); ++ if (ec == GPG_ERR_INV_OP) ++ { ++ /* libgcrypt is old, no support of the FIPS service indicator. */ ++ fail ("gcry_pk_testkey test %d unexpectedly failed to check the FIPS service indicator.\n", ++ tvidx); ++ goto next; ++ } ++ ++ if (in_fips_mode && !tv[tvidx].expect_failure && ec) ++ { ++ /* Success with the FIPS service indicator == 0 expected, but != 0. */ ++ fail ("gcry_pk_testkey test %d unexpectedly set the indicator in FIPS mode.\n", ++ tvidx); ++ goto next; ++ } ++ else if (in_fips_mode && tv[tvidx].expect_failure && !ec) ++ { ++ /* Success with the FIPS service indicator != 0 expected, but == 0. */ ++ fail ("gcry_pk_testkey test %d unexpectedly cleared the indicator in FIPS mode.\n", ++ tvidx); ++ goto next; ++ } ++ ++ nbits = gcry_pk_get_nbits (s_sk); ++ if (!nbits) ++ { ++ fail ("gcry_pk_get_nbits failed for test"); ++ goto next; ++ } ++ ++ ec = gcry_get_fips_service_indicator (); ++ if (ec == GPG_ERR_INV_OP) ++ { ++ /* libgcrypt is old, no support of the FIPS service indicator. */ ++ fail ("gcry_pk_get_nbits test %d unexpectedly failed to check the FIPS service indicator.\n", ++ tvidx); ++ goto next; ++ } ++ ++ if (in_fips_mode && !tv[tvidx].expect_failure && ec) ++ { ++ /* Success with the FIPS service indicator == 0 expected, but != 0. */ ++ fail ("gcry_pk_get_nbits test %d unexpectedly set the indicator in FIPS mode.\n", ++ tvidx); ++ goto next; ++ } ++ else if (in_fips_mode && tv[tvidx].expect_failure && !ec) ++ { ++ /* Success with the FIPS service indicator != 0 expected, but == 0. */ ++ fail ("gcry_pk_get_nbits test %d unexpectedly cleared the indicator in FIPS mode.\n", ++ tvidx); ++ goto next; ++ } ++ ++ name = gcry_pk_get_curve (s_sk, 0, NULL); ++ if (!name) ++ { ++ fail ("gcry_pk_get_curve failed for test: %s", gpg_strerror (err)); ++ goto next; ++ } ++ ++ ec = gcry_get_fips_service_indicator (); ++ if (ec == GPG_ERR_INV_OP) ++ { ++ /* libgcrypt is old, no support of the FIPS service indicator. */ ++ fail ("gcry_pk_get_curve test %d unexpectedly failed to check the FIPS service indicator.\n", ++ tvidx); ++ goto next; ++ } ++ ++ if (in_fips_mode && !tv[tvidx].expect_failure && ec) ++ { ++ /* Success with the FIPS service indicator == 0 expected, but != 0. */ ++ fail ("gcry_pk_get_curve test %d unexpectedly set the indicator in FIPS mode.\n", ++ tvidx); ++ goto next; ++ } ++ else if (in_fips_mode && tv[tvidx].expect_failure && !ec) ++ { ++ /* Success with the FIPS service indicator != 0 expected, but == 0. */ ++ fail ("gcry_pk_get_curve test %d unexpectedly cleared the indicator in FIPS mode.\n", ++ tvidx); ++ goto next; ++ } ++ ++ next: ++ gcry_sexp_release (s_kp); ++ gcry_sexp_release (s_sk); ++ } ++} ++ ++/* Check gcry_pk_sign, gcry_verify API. */ ++static void ++check_pk_s_v (int reject) ++{ ++ static struct { ++ const char *prvkey; ++ const char *pubkey; ++ int expect_failure; ++ } tv[] = { ++ { ++ "(private-key (ecc (curve nistp256)" ++ " (d #519b423d715f8b581f4fa8ee59f4771a5b44c8130b4e3eacca54a56dda72b464#)))", ++ "(public-key (ecc (curve nistp256)" ++ " (q #041ccbe91c075fc7f4f033bfa248db8fccd3565de94bbfb12f3c59ff46c271bf83" ++ "ce4014c68811f9a21a1fdb2c0e6113e06db7ca93b7404e78dc7ccd5ca89a4ca9#)))", ++ 0 ++ }, ++ { /* non-compliant curve */ ++ "(private-key (ecc (curve secp256k1)" ++ " (d #c2cdf0a8b0a83b35ace53f097b5e6e6a0a1f2d40535eff1cf434f52a43d59d8f#)))", ++ "(public-key (ecc (curve secp256k1)" ++ " (q #046fcc37ea5e9e09fec6c83e5fbd7a745e3eee81d16ebd861c9e66f55518c19798" ++ "4e9f113c07f875691df8afc1029496fc4cb9509b39dcd38f251a83359cc8b4f7#)))", ++ 1 ++ } ++ }; ++ int tvidx; ++ gpg_error_t err; ++ gpg_err_code_t ec; ++ const char *data = "(data (flags raw)" ++ "(hash sha256 #00112233445566778899AABBCCDDEEFF000102030405060708090A0B0C0D0E0F#))"; ++ gcry_sexp_t s_data = NULL; ++ ++ err = gcry_sexp_build (&s_data, NULL, data); ++ if (err) ++ { ++ fail ("error building SEXP for test, %s: %s", ++ "data", gpg_strerror (err)); ++ return; ++ } ++ ++ for (tvidx=0; tvidx < DIM(tv); tvidx++) ++ { ++ gcry_sexp_t s_pk = NULL; ++ gcry_sexp_t s_sk = NULL; ++ gcry_sexp_t s_sig= NULL; ++ ++ if (verbose) ++ info ("checking gcry_pk_{sign,verify} test %d\n", tvidx); ++ ++ err = gcry_sexp_build (&s_sk, NULL, tv[tvidx].prvkey); ++ if (err) ++ { ++ fail ("error building SEXP for test, %s: %s", ++ "sk", gpg_strerror (err)); ++ goto next; ++ } ++ ++ err = gcry_sexp_build (&s_pk, NULL, tv[tvidx].pubkey); ++ if (err) ++ { ++ fail ("error building SEXP for test, %s: %s", ++ "pk", gpg_strerror (err)); ++ goto next; ++ } ++ ++ err = gcry_pk_sign (&s_sig, s_data, s_sk); ++ if (err) ++ { ++ if (in_fips_mode && reject && tv[tvidx].expect_failure) ++ /* Here, an error is expected */ ++ ; ++ else ++ fail ("gcry_pk_sign failed: %s", gpg_strerror (err)); ++ goto next; ++ } ++ else ++ { ++ if (in_fips_mode && reject && tv[tvidx].expect_failure) ++ { ++ fail ("gcry_pk_sign test %d unexpectedly succeeded", tvidx); ++ goto next; ++ } ++ } ++ ++ ec = gcry_get_fips_service_indicator (); ++ if (ec == GPG_ERR_INV_OP) ++ { ++ /* libgcrypt is old, no support of the FIPS service indicator. */ ++ fail ("gcry_pk_sign test %d unexpectedly failed to check the FIPS service indicator.\n", ++ tvidx); ++ goto next; ++ } ++ ++ if (in_fips_mode && !tv[tvidx].expect_failure && ec) ++ { ++ /* Success with the FIPS service indicator == 0 expected, but != 0. */ ++ fail ("gcry_pk_sign test %d unexpectedly set the indicator in FIPS mode.\n", ++ tvidx); ++ goto next; ++ } ++ else if (in_fips_mode && tv[tvidx].expect_failure && !ec) ++ { ++ /* Success with the FIPS service indicator != 0 expected, but == 0. */ ++ fail ("gcry_pk_sign test %d unexpectedly cleared the indicator in FIPS mode.\n", ++ tvidx); ++ goto next; ++ } ++ ++ err = gcry_pk_verify (s_sig, s_data, s_pk); ++ if (err) ++ { ++ fail ("gcry_pk_verify failed for test: %s", gpg_strerror (err)); ++ goto next; ++ } ++ ++ ec = gcry_get_fips_service_indicator (); ++ if (ec == GPG_ERR_INV_OP) ++ { ++ /* libgcrypt is old, no support of the FIPS service indicator. */ ++ fail ("gcry_pk_verify test %d unexpectedly failed to check the FIPS service indicator.\n", ++ tvidx); ++ goto next; ++ } ++ ++ if (in_fips_mode && !tv[tvidx].expect_failure && ec) ++ { ++ /* Success with the FIPS service indicator == 0 expected, but != 0. */ ++ fail ("gcry_pk_verify test %d unexpectedly set the indicator in FIPS mode.\n", ++ tvidx); ++ goto next; ++ } ++ else if (in_fips_mode && tv[tvidx].expect_failure && !ec) ++ { ++ /* Success with the FIPS service indicator != 0 expected, but == 0. */ ++ fail ("gcry_pk_verify test %d unexpectedly cleared the indicator in FIPS mode.\n", ++ tvidx); ++ goto next; ++ } ++ ++ next: ++ gcry_sexp_release (s_sig); ++ gcry_sexp_release (s_pk); ++ gcry_sexp_release (s_sk); ++ } ++ ++ gcry_sexp_release (s_data); ++} ++ + /* Check gcry_pk_hash_sign, gcry_pk_hash_verify API. */ + static void + check_pk_hash_sign_verify (void) +@@ -1126,6 +1456,8 @@ main (int argc, char **argv) + check_mac_o_w_r_c (0); + check_cipher_o_s_e_d_c (0); + check_pk_hash_sign_verify (); ++ check_pk_s_v (0); ++ check_pk_g_t_n_c (0); + + xgcry_control ((GCRYCTL_FIPS_REJECT_NON_FIPS, + (GCRY_FIPS_FLAG_REJECT_MD_MD5 +@@ -1134,6 +1466,8 @@ main (int argc, char **argv) + check_md_o_w_r_c (1); + check_mac_o_w_r_c (1); + check_cipher_o_s_e_d_c (1); ++ check_pk_s_v (1); ++ check_pk_g_t_n_c (1); + + return !!error_count; + } +-- +2.49.0 + diff --git a/libgcrypt-tests-Allow-tests-with-USE_RSA.patch b/libgcrypt-tests-Allow-tests-with-USE_RSA.patch new file mode 100644 index 0000000..cc29fb0 --- /dev/null +++ b/libgcrypt-tests-Allow-tests-with-USE_RSA.patch @@ -0,0 +1,44 @@ +From 8404a048b7c58eb903717e09cffaa7735f7d8520 Mon Sep 17 00:00:00 2001 +From: NIIBE Yutaka +Date: Tue, 4 Mar 2025 13:29:28 +0900 +Subject: [PATCH 01/14] tests: Allow tests with !USE_RSA. +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* tests/t-fips-service-ind.c [USE_RSA] (check_pk_s_v): Ifdef-out. + +-- + +Signed-off-by: NIIBE Yutaka +Signed-off-by: Lucas Mülling +--- + tests/t-fips-service-ind.c | 5 ++++- + 1 file changed, 4 insertions(+), 1 deletion(-) + +diff --git a/tests/t-fips-service-ind.c b/tests/t-fips-service-ind.c +index 99b84c8f..a082b258 100644 +--- a/tests/t-fips-service-ind.c ++++ b/tests/t-fips-service-ind.c +@@ -290,7 +290,9 @@ check_pk_s_v (int reject) + " 00112233445566778899AABBCCDDEEFF000102030405060708090A0B0C0D0E0F" + " 00112233445566778899AABBCCDDEEFF000102030405060708090A0B0C0D0E0F#))", + 0 +- }, ++ } ++#if USE_RSA ++ , + { /* RSA with compliant hash for signing */ + "(private-key" + " (rsa" +@@ -559,6 +561,7 @@ check_pk_s_v (int reject) + " (hash sha1 #11223344556677889900AABBCCDDEEFF10203040#))\n", + 1 + } ++#endif /* USE_RSA */ + }; + int tvidx; + gpg_error_t err; +-- +2.49.0 + diff --git a/libgcrypt-tests-Update-t-fips-service-ind-using-GCRY_MD_SHA256-for-KDF-tests.patch b/libgcrypt-tests-Update-t-fips-service-ind-using-GCRY_MD_SHA256-for-KDF-tests.patch new file mode 100644 index 0000000..dd009fd --- /dev/null +++ b/libgcrypt-tests-Update-t-fips-service-ind-using-GCRY_MD_SHA256-for-KDF-tests.patch @@ -0,0 +1,106 @@ +From e5989e08a556117ec3f19f098765963358b71051 Mon Sep 17 00:00:00 2001 +From: NIIBE Yutaka +Date: Wed, 26 Feb 2025 13:51:36 +0900 +Subject: [PATCH 3/4] tests: Update t-fips-service-ind using GCRY_MD_SHA256 for + KDF tests. +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* tests/t-fips-service-ind.c (check_kdf_derive): Use GCRY_MD_SHA256. + +-- + +GnuPG-bug-id: 7338 +Signed-off-by: NIIBE Yutaka +Signed-off-by: Lucas Mülling +--- + tests/t-fips-service-ind.c | 38 +++++++++++++++++++------------------- + 1 file changed, 19 insertions(+), 19 deletions(-) + +diff --git a/tests/t-fips-service-ind.c b/tests/t-fips-service-ind.c +index bec6c27e..99b84c8f 100644 +--- a/tests/t-fips-service-ind.c ++++ b/tests/t-fips-service-ind.c +@@ -1621,13 +1621,13 @@ check_kdf_derive (void) + } tv[] = { + { + "passwordPASSWORDpassword", 24, +- GCRY_KDF_PBKDF2, GCRY_MD_SHA1, ++ GCRY_KDF_PBKDF2, GCRY_MD_SHA256, + "saltSALTsaltSALTsaltSALTsaltSALTsalt", 36, + 4096, + 25, +- "\x3d\x2e\xec\x4f\xe4\x1c\x84\x9b\x80\xc8" +- "\xd8\x36\x62\xc0\xe4\x4a\x8b\x29\x1a\x96" +- "\x4c\xf2\xf0\x70\x38", ++ "\x34\x8c\x89\xdb\xcb\xd3\x2b\x2f\x32\xd8" ++ "\x14\xb8\x11\x6e\x84\xcf\x2b\x17\x34\x7e" ++ "\xbc\x18\x00\x18\x1c", + 0 + }, + { +@@ -1644,45 +1644,45 @@ check_kdf_derive (void) + }, + { + "passwor", 7, +- GCRY_KDF_PBKDF2, GCRY_MD_SHA1, ++ GCRY_KDF_PBKDF2, GCRY_MD_SHA256, + "saltSALTsaltSALTsaltSALTsaltSALTsalt", 36, + 4096, + 25, +- "\xf4\x93\xee\x2b\xbf\x44\x0b\x9e\x64\x53" +- "\xc2\xb3\x87\xdc\x73\xf8\xfd\xe6\x97\xda" +- "\xb8\x24\xa0\x26\x50", ++ "\x2d\x72\xa9\xe5\x4e\x2f\x37\x6e\xe5\xe4" ++ "\xf5\x55\x76\xb5\xaa\x49\x73\x01\x97\x1c" ++ "\xad\x3a\x7c\xc4\xde", + 1 /* not-compliant because passphrase len is too small */ + }, + { + "passwordPASSWORDpassword", 24, +- GCRY_KDF_PBKDF2, GCRY_MD_SHA1, ++ GCRY_KDF_PBKDF2, GCRY_MD_SHA256, + "saltSALTsaltSAL", 15, + 4096, + 25, +- "\x14\x05\xa4\x2a\xf4\xa8\x12\x14\x7b\x65" +- "\x8f\xaa\xf0\x7f\x25\xe5\x0f\x0b\x2b\xb7" +- "\xcf\x8d\x29\x23\x4b", ++ "\xf7\x55\xdd\x3c\x5e\xfb\x23\x06\xa7\x85" ++ "\x94\xa7\x31\x12\x45\xcf\x5a\x4b\xdc\x09" ++ "\xee\x65\x4b\x50\x3f", + 1 /* not-compliant because salt len is too small */ + }, + { + "passwordPASSWORDpassword", 24, +- GCRY_KDF_PBKDF2, GCRY_MD_SHA1, ++ GCRY_KDF_PBKDF2, GCRY_MD_SHA256, + "saltSALTsaltSALTsaltSALTsaltSALTsalt", 36, + 999, + 25, +- "\xac\xf8\xb4\x67\x41\xc7\xf3\xd1\xa0\xc0" +- "\x08\xbe\x9b\x23\x96\x78\xbd\x93\xda\x4a" +- "\x30\xd4\xfb\xf0\x33", ++ "\x09\x3e\x1a\xd8\x63\x30\x71\x9c\x17\xcf" ++ "\xb0\x53\x3e\x1f\xc8\x51\x29\x71\x54\x28" ++ "\x5d\xf7\x8e\x41\xaa", + 1 /* not-compliant because too few iterations */ + }, + { + "passwordPASSWORDpassword", 24, +- GCRY_KDF_PBKDF2, GCRY_MD_SHA1, ++ GCRY_KDF_PBKDF2, GCRY_MD_SHA256, + "saltSALTsaltSALTsaltSALTsaltSALTsalt", 36, + 4096, + 13, +- "\x3d\x2e\xec\x4f\xe4\x1c\x84\x9b\x80\xc8" +- "\xd8\x36\x62", ++ "\x34\x8c\x89\xdb\xcb\xd3\x2b\x2f\x32\xd8" ++ "\x14\xb8\x11", + 1 /* not-compliant because key size too small */ + }, + { +-- +2.49.0 + diff --git a/libgcrypt-tests-fips-Add-gcry_cipher_open-tests.patch b/libgcrypt-tests-fips-Add-gcry_cipher_open-tests.patch new file mode 100644 index 0000000..0e0f7e5 --- /dev/null +++ b/libgcrypt-tests-fips-Add-gcry_cipher_open-tests.patch @@ -0,0 +1,199 @@ +From cfd2d2f41ad4aef40d83f8f7237d1da13c7e240c Mon Sep 17 00:00:00 2001 +From: NIIBE Yutaka +Date: Tue, 17 Dec 2024 10:33:33 +0900 +Subject: [PATCH 09/19] tests,fips: Add gcry_cipher_open tests. +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* tests/t-fips-service-ind.c (check_cipher_o_s_e_d_c): New. +(main): Call check_cipher_o_s_e_d_c. + +-- + +GnuPG-bug-id: 7338 +Signed-off-by: NIIBE Yutaka +Signed-off-by: Lucas Mülling +--- + tests/t-fips-service-ind.c | 152 ++++++++++++++++++++++++++++++++++++- + 1 file changed, 151 insertions(+), 1 deletion(-) + +Index: libgcrypt-1.11.0/tests/t-fips-service-ind.c +=================================================================== +--- libgcrypt-1.11.0.orig/tests/t-fips-service-ind.c ++++ libgcrypt-1.11.0/tests/t-fips-service-ind.c +@@ -31,6 +31,7 @@ + + #include "t-common.h" + static int in_fips_mode; ++#define MAX_DATA_LEN 1040 + + /* Mingw requires us to include windows.h after winsock2.h which is + included by gcrypt.h. */ +@@ -38,6 +39,154 @@ static int in_fips_mode; + # include + #endif + ++/* Check gcry_cipher_open, gcry_cipher_setkey, gcry_cipher_encrypt, ++ gcry_cipher_decrypt, gcry_cipher_close API. */ ++static void ++check_cipher_o_s_e_d_c (void) ++{ ++ static struct { ++ int algo; ++ const char *key; ++ int keylen; ++ const char *expect; ++ int expect_failure; ++ unsigned int flags; ++ } tv[] = { ++#if USE_DES ++ { GCRY_CIPHER_3DES, ++ "\xe3\x34\x7a\x6b\x0b\xc1\x15\x2c\x64\x2a\x25\xcb\xd3\xbc\x31\xab" ++ "\xfb\xa1\x62\xa8\x1f\x19\x7c\x15", 24, ++ "\x3f\x1a\xb8\x83\x18\x8b\xb5\x97", 1 }, ++ { GCRY_CIPHER_3DES, ++ "\xe3\x34\x7a\x6b\x0b\xc1\x15\x2c\x64\x2a\x25\xcb\xd3\xbc\x31\xab" ++ "\xfb\xa1\x62\xa8\x1f\x19\x7c\x15", 24, ++ "\x3f\x1a\xb8\x83\x18\x8b\xb5\x97", ++ 1, GCRY_CIPHER_FLAG_REJECT_NON_FIPS }, ++#endif ++ { GCRY_CIPHER_AES, ++ "\x2b\x7e\x15\x16\x28\xae\xd2\xa6\xab\xf7\x15\x88\x09\xcf\x4f\x3c", 16, ++ "\x5c\x71\xd8\x5d\x26\x5e\xcd\xb5\x95\x40\x41\xab\xff\x25\x6f\xd1" } ++ }; ++ const char *pt = "Shohei Ohtani 2024: 54 HR, 59 SB"; ++ int ptlen; ++ int tvidx; ++ unsigned char out[MAX_DATA_LEN]; ++ gpg_error_t err; ++ ++ ptlen = strlen (pt); ++ assert (ptlen == 32); ++ for (tvidx=0; tvidx < DIM(tv); tvidx++) ++ { ++ gpg_err_code_t ec; ++ gcry_cipher_hd_t h; ++ size_t blklen; ++ ++ if (verbose) ++ fprintf (stderr, "checking gcry_cipher_open test %d\n", ++ tvidx); ++ ++ blklen = gcry_cipher_get_algo_blklen (tv[tvidx].algo); ++ assert (blklen != 0); ++ assert (blklen <= ptlen); ++ assert (blklen <= DIM (out)); ++ err = gcry_cipher_open (&h, tv[tvidx].algo, GCRY_CIPHER_MODE_ECB, ++ tv[tvidx].flags); ++ if (err) ++ { ++ if (in_fips_mode && (tv[tvidx].flags & GCRY_CIPHER_FLAG_REJECT_NON_FIPS) ++ && tv[tvidx].expect_failure) ++ /* Here, an error is expected */ ++ ; ++ else ++ fail ("gcry_cipher_open test %d unexpectedly failed: %s\n", ++ tvidx, gpg_strerror (err)); ++ continue; ++ } ++ else ++ { ++ if (in_fips_mode && (tv[tvidx].flags & GCRY_CIPHER_FLAG_REJECT_NON_FIPS) ++ && tv[tvidx].expect_failure) ++ /* This case, an error is expected, but we observed success */ ++ fail ("gcry_cipher_open test %d unexpectedly succeeded\n", tvidx); ++ } ++ ++ ec = gcry_get_fips_service_indicator (); ++ if (ec == GPG_ERR_INV_OP) ++ { ++ /* libgcrypt is old, no support of the FIPS service indicator. */ ++ fail ("gcry_cipher_open test %d unexpectedly failed to check the FIPS service indicator.\n", ++ tvidx); ++ continue; ++ } ++ ++ if (in_fips_mode && !tv[tvidx].expect_failure && ec) ++ { ++ /* Success with the FIPS service indicator == 0 expected, but != 0. */ ++ fail ("gcry_cipher_open test %d unexpectedly set the indicator in FIPS mode.\n", ++ tvidx); ++ continue; ++ } ++ else if (in_fips_mode && tv[tvidx].expect_failure && !ec) ++ { ++ /* Success with the FIPS service indicator != 0 expected, but == 0. */ ++ fail ("gcry_cipher_open test %d unexpectedly cleared the indicator in FIPS mode.\n", ++ tvidx); ++ continue; ++ } ++ ++ err = gcry_cipher_setkey (h, tv[tvidx].key, tv[tvidx].keylen); ++ if (err) ++ { ++ fail ("gcry_cipher_setkey %d failed: %s\n", tvidx, ++ gpg_strerror (err)); ++ gcry_cipher_close (h); ++ continue; ++ } ++ ++ err = gcry_cipher_encrypt (h, out, MAX_DATA_LEN, pt, blklen); ++ if (err) ++ { ++ fail ("gcry_cipher_encrypt %d failed: %s\n", tvidx, ++ gpg_strerror (err)); ++ gcry_cipher_close (h); ++ continue; ++ } ++ ++ if (memcmp (out, tv[tvidx].expect, blklen)) ++ { ++ int i; ++ ++ fail ("gcry_cipher_open test %d failed: encryption mismatch\n", tvidx); ++ fputs ("got:", stderr); ++ for (i=0; i < blklen; i++) ++ fprintf (stderr, " %02x", out[i]); ++ putc ('\n', stderr); ++ } ++ ++ err = gcry_cipher_decrypt (h, out, blklen, NULL, 0); ++ if (err) ++ { ++ fail ("gcry_cipher_decrypt %d failed: %s\n", tvidx, ++ gpg_strerror (err)); ++ gcry_cipher_close (h); ++ continue; ++ } ++ ++ if (memcmp (out, pt, blklen)) ++ { ++ int i; ++ ++ fail ("gcry_cipher_open test %d failed: decryption mismatch\n", tvidx); ++ fputs ("got:", stderr); ++ for (i=0; i < blklen; i++) ++ fprintf (stderr, " %02x", out[i]); ++ putc ('\n', stderr); ++ } ++ ++ gcry_cipher_close (h); ++ } ++} ++ + /* Check gcry_mac_open, gcry_mac_write, gcry_mac_write, gcry_mac_read, + gcry_mac_close API. */ + static void +@@ -651,9 +800,10 @@ main (int argc, char **argv) + xgcry_control ((GCRYCTL_SET_DEBUG_FLAGS, 1u , 0)); + + check_digests (); ++ check_kdf_derive (); + check_md_o_w_r_c (); + check_mac_o_w_r_c (); +- check_kdf_derive (); ++ check_cipher_o_s_e_d_c (); + + return !!error_count; + } diff --git a/libgcrypt-tests-fips-Add-gcry_mac_open-tests.patch b/libgcrypt-tests-fips-Add-gcry_mac_open-tests.patch new file mode 100644 index 0000000..c2e3ed4 --- /dev/null +++ b/libgcrypt-tests-fips-Add-gcry_mac_open-tests.patch @@ -0,0 +1,206 @@ +From c4f75014cb8af732f87c02fe7c2e7a488fe71c6d Mon Sep 17 00:00:00 2001 +From: NIIBE Yutaka +Date: Mon, 16 Dec 2024 14:09:10 +0900 +Subject: [PATCH 06/19] tests,fips: Add gcry_mac_open tests. +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* tests/t-digest.c (check_mac_o_w_r_c): New. +(main): Call check_mac_o_w_r_c. + +-- + +GnuPG-bug-id: 7338 +Signed-off-by: NIIBE Yutaka +Signed-off-by: Lucas Mülling +--- + tests/t-digest.c | 168 +++++++++++++++++++++++++++++++++++++++++++++++ + 1 file changed, 168 insertions(+) + +Index: libgcrypt-1.11.0/tests/t-digest.c +=================================================================== +--- libgcrypt-1.11.0.orig/tests/t-digest.c ++++ libgcrypt-1.11.0/tests/t-digest.c +@@ -38,6 +38,173 @@ static int in_fips_mode; + # include + #endif + ++/* Check gcry_mac_open, gcry_mac_write, gcry_mac_write, gcry_mac_read, ++ gcry_mac_close API. */ ++static void ++check_mac_o_w_r_c (void) ++{ ++ static struct { ++ int algo; ++ const char *data; ++ int datalen; ++ const char *key; ++ int keylen; ++ const char *expect; ++ int expect_failure; ++ unsigned int flags; ++ } tv[] = { ++#if USE_MD5 ++ { GCRY_MAC_HMAC_MD5, "hmac input abc", 14, "hmac key input", 14, ++ "\x0d\x72\xd0\x60\xaf\x34\xf2\xca\x33\x58\xa9\xcc\xd3\x5a\xac\xb5", 1 }, ++ { GCRY_MAC_HMAC_MD5, "hmac input abc", 14, "hmac key input", 14, ++ "\x0d\x72\xd0\x60\xaf\x34\xf2\xca\x33\x58\xa9\xcc\xd3\x5a\xac\xb5", 1, ++ GCRY_MAC_FLAG_REJECT_NON_FIPS }, ++#endif ++#if USE_SHA1 ++ { GCRY_MAC_HMAC_SHA1, "hmac input abc", 14, "hmac key input", 14, ++ "\xc9\x62\x9d\x16\x0f\xc2\xc4\xcd\x38\xac\x3a\x00\xdc\x29\x61\x03" ++ "\x69\x50\xd7\x3a" }, ++#endif ++ { GCRY_MAC_HMAC_SHA256, "hmac input abc", 14, "hmac key input", 14, ++ "\x6a\xda\x4d\xd5\xf3\xa7\x32\x9d\xd2\x55\xc0\x7f\xe6\x0a\x93\xb8" ++ "\x7a\x6e\x76\x68\x46\x34\x67\xf9\xc2\x29\xb8\x24\x2e\xc8\xe3\xb4" }, ++ { GCRY_MAC_HMAC_SHA384, "hmac input abc", 14, "hmac key input", 14, ++ "\xc6\x59\x14\x4a\xac\x4d\xd5\x62\x09\x2c\xbd\x5e\xbf\x41\x94\xf9" ++ "\xa4\x78\x18\x46\xfa\xd6\xd1\x12\x90\x4f\x65\xd4\xe8\x44\xcc\xcc" ++ "\x3d\xcc\xf3\xe4\x27\xd8\xf0\xff\x01\xe8\x70\xcd\xfb\xfa\x24\x45" }, ++ { GCRY_MAC_HMAC_SHA512, "hmac input abc", 14, "hmac key input", 14, ++ "\xfa\x77\x49\x49\x24\x3d\x7e\x03\x1b\x0e\xd1\xfc\x20\x81\xcf\x95" ++ "\x81\x21\xa4\x4f\x3b\xe5\x69\x9a\xe6\x67\x27\x10\xbc\x62\xc7\xb3" ++ "\xb3\xcf\x2b\x1e\xda\x20\x48\x25\xc5\x6a\x52\xc7\xc9\xd9\x77\xf6" ++ "\xf6\x49\x9d\x70\xe6\x04\x33\xab\x6a\xdf\x7e\x9f\xf4\xd1\x59\x6e" }, ++ { GCRY_MAC_HMAC_SHA3_256, "hmac input abc", 14, "hmac key input", 14, ++ "\x2b\xe9\x02\x92\xc2\x37\xbe\x91\x06\xbf\x9c\x8e\x7b\xa3\xf2\xfc" ++ "\x68\x10\x8a\x71\xd5\xc7\x84\x3c\x0b\xdd\x7d\x1e\xdf\xa5\xf6\xa7" }, ++ { GCRY_MAC_HMAC_SHA3_384, "hmac input abc", 14, "hmac key input", 14, ++ "\x9f\x6b\x9f\x49\x95\x57\xed\x33\xb1\xe7\x22\x2f\xda\x40\x68\xb0" ++ "\x28\xd2\xdb\x6f\x73\x3c\x2e\x2b\x29\x51\x64\x53\xc4\xc5\x63\x8a" ++ "\x98\xca\x78\x1a\xe7\x1b\x7d\xf6\xbf\xf3\x6a\xf3\x2a\x0e\xa0\x5b" }, ++ { GCRY_MAC_HMAC_SHA3_512, "hmac input abc", 14, "hmac key input", 14, ++ "\xf3\x19\x70\x54\x25\xdf\x0f\xde\x09\xe9\xea\x3b\x34\x67\x14\x32" ++ "\xe6\xe2\x58\x9d\x76\x38\xa4\xbd\x90\x35\x4c\x07\x7c\xa3\xdb\x23" ++ "\x3c\x78\x0c\x45\xee\x8e\x39\xd5\x81\xd8\x5c\x13\x20\x40\xba\x34" ++ "\xd0\x0b\x75\x31\x38\x4b\xe7\x74\x87\xa9\xc5\x68\x7f\xbc\x19\xa1" } ++#if USE_RMD160 ++ , ++ { GCRY_MAC_HMAC_RMD160, "hmac input abc", 14, "hmac key input", 14, ++ "\xf2\x45\x5c\x7e\x48\x1a\xbb\xe5\xe8\xec\x40\xa4\x1b\x89\x26\x2b" ++ "\xdc\xa1\x79\x59", 1 } ++#endif ++ }; ++ int tvidx; ++ unsigned char mac[64]; ++ int expectlen; ++ gpg_error_t err; ++ size_t buflen; ++ ++ for (tvidx=0; tvidx < DIM(tv); tvidx++) ++ { ++ gpg_err_code_t ec; ++ gcry_mac_hd_t h; ++ ++ if (verbose) ++ fprintf (stderr, "checking gcry_mac_open test %d\n", ++ tvidx); ++ ++ expectlen = gcry_mac_get_algo_maclen (tv[tvidx].algo); ++ assert (expectlen != 0); ++ assert (expectlen <= DIM (mac)); ++ err = gcry_mac_open (&h, tv[tvidx].algo, tv[tvidx].flags, NULL); ++ if (err) ++ { ++ if (in_fips_mode && (tv[tvidx].flags & GCRY_MAC_FLAG_REJECT_NON_FIPS) ++ && tv[tvidx].expect_failure) ++ /* Here, an error is expected */ ++ ; ++ else ++ fail ("gcry_mac_open test %d unexpectedly failed: %s\n", ++ tvidx, gpg_strerror (err)); ++ continue; ++ } ++ else ++ { ++ if (in_fips_mode && (tv[tvidx].flags & GCRY_MAC_FLAG_REJECT_NON_FIPS) ++ && tv[tvidx].expect_failure) ++ /* This case, an error is expected, but we observed success */ ++ fail ("gcry_mac_open test %d unexpectedly succeeded\n", tvidx); ++ } ++ ++ ++ ec = gcry_get_fips_service_indicator (); ++ if (ec == GPG_ERR_INV_OP) ++ { ++ /* libgcrypt is old, no support of the FIPS service indicator. */ ++ fail ("gcry_mac_open test %d unexpectedly failed to check the FIPS service indicator.\n", ++ tvidx); ++ continue; ++ } ++ ++ if (in_fips_mode && !tv[tvidx].expect_failure && ec) ++ { ++ /* Success with the FIPS service indicator == 0 expected, but != 0. */ ++ fail ("gcry_mac_open test %d unexpectedly set the indicator in FIPS mode.\n", ++ tvidx); ++ continue; ++ } ++ else if (in_fips_mode && tv[tvidx].expect_failure && !ec) ++ { ++ /* Success with the FIPS service indicator != 0 expected, but == 0. */ ++ fail ("gcry_mac_open test %d unexpectedly cleared the indicator in FIPS mode.\n", ++ tvidx); ++ continue; ++ } ++ ++ err = gcry_mac_setkey (h, tv[tvidx].key, tv[tvidx].keylen); ++ if (err) ++ { ++ fail ("gcry_mac_setkey test %d unexpectedly failed: %s\n", ++ tvidx, gpg_strerror (err)); ++ gcry_mac_close (h); ++ continue; ++ } ++ ++ err = gcry_mac_write (h, tv[tvidx].data, tv[tvidx].datalen); ++ if (err) ++ { ++ fail ("gcry_mac_write test %d unexpectedly failed: %s\n", ++ tvidx, gpg_strerror (err)); ++ gcry_mac_close (h); ++ continue; ++ } ++ ++ buflen = expectlen; ++ err = gcry_mac_read (h, mac, &buflen); ++ if (err || buflen != expectlen) ++ { ++ fail ("gcry_mac_read test %d unexpectedly failed: %s\n", ++ tvidx, gpg_strerror (err)); ++ gcry_mac_close (h); ++ continue; ++ } ++ ++ if (memcmp (mac, tv[tvidx].expect, expectlen)) ++ { ++ int i; ++ ++ fail ("gcry_mac_open test %d failed: mismatch\n", tvidx); ++ fputs ("got:", stderr); ++ for (i=0; i < expectlen; i++) ++ fprintf (stderr, " %02x", mac[i]); ++ putc ('\n', stderr); ++ } ++ ++ gcry_mac_close (h); ++ } ++} ++ ++ ++/* Check gcry_md_open, gcry_md_write, gcry_md_write, gcry_md_read, ++ gcry_md_close API. */ + static void + check_md_o_w_r_c (void) + { +@@ -327,6 +494,7 @@ main (int argc, char **argv) + + check_digests (); + check_md_o_w_r_c (); ++ check_mac_o_w_r_c (); + + return !!error_count; + } diff --git a/libgcrypt-tests-fips-Move-KDF-tests-to-t-fips-service-ind.patch b/libgcrypt-tests-fips-Move-KDF-tests-to-t-fips-service-ind.patch new file mode 100644 index 0000000..7adbac5 --- /dev/null +++ b/libgcrypt-tests-fips-Move-KDF-tests-to-t-fips-service-ind.patch @@ -0,0 +1,375 @@ +From b59bde31ded9e829e2a53ddb8c533bf35a144972 Mon Sep 17 00:00:00 2001 +From: NIIBE Yutaka +Date: Mon, 16 Dec 2024 14:21:06 +0900 +Subject: [PATCH 08/19] tests,fips: Move KDF tests to t-fips-service-ind. +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* tests/t-fips-service-ind.c (check_kdf_derive): Move from... +* tests/t-kdf.c (check_fips_gcry_kdf_derive): ... here. + +-- + +GnuPG-bug-id: 7338 +Signed-off-by: NIIBE Yutaka +Signed-off-by: Lucas Mülling +--- + tests/t-fips-service-ind.c | 159 +++++++++++++++++++++++++++++++++++++ + tests/t-kdf.c | 159 ------------------------------------- + 2 files changed, 159 insertions(+), 159 deletions(-) + +Index: libgcrypt-1.11.0/tests/t-fips-service-ind.c +=================================================================== +--- libgcrypt-1.11.0.orig/tests/t-fips-service-ind.c ++++ libgcrypt-1.11.0/tests/t-fips-service-ind.c +@@ -439,6 +439,164 @@ check_digests (void) + } + + ++ ++static void ++check_kdf_derive (void) ++{ ++ static struct { ++ const char *p; /* Passphrase. */ ++ size_t plen; /* Length of P. */ ++ int algo; ++ int subalgo; ++ const char *salt; ++ size_t saltlen; ++ unsigned long iterations; ++ int dklen; /* Requested key length. */ ++ const char *dk; /* Derived key. */ ++ int expect_failure; ++ } tv[] = { ++ { ++ "passwordPASSWORDpassword", 24, ++ GCRY_KDF_PBKDF2, GCRY_MD_SHA1, ++ "saltSALTsaltSALTsaltSALTsaltSALTsalt", 36, ++ 4096, ++ 25, ++ "\x3d\x2e\xec\x4f\xe4\x1c\x84\x9b\x80\xc8" ++ "\xd8\x36\x62\xc0\xe4\x4a\x8b\x29\x1a\x96" ++ "\x4c\xf2\xf0\x70\x38", ++ 0 ++ }, ++ { ++ "pleaseletmein", 13, ++ GCRY_KDF_SCRYPT, 16384, ++ "SodiumChloride", 14, ++ 1, ++ 64, ++ "\x70\x23\xbd\xcb\x3a\xfd\x73\x48\x46\x1c\x06\xcd\x81\xfd\x38\xeb" ++ "\xfd\xa8\xfb\xba\x90\x4f\x8e\x3e\xa9\xb5\x43\xf6\x54\x5d\xa1\xf2" ++ "\xd5\x43\x29\x55\x61\x3f\x0f\xcf\x62\xd4\x97\x05\x24\x2a\x9a\xf9" ++ "\xe6\x1e\x85\xdc\x0d\x65\x1e\x40\xdf\xcf\x01\x7b\x45\x57\x58\x87", ++ 1 /* not-compliant because unallowed algo */ ++ }, ++ { ++ "passwor", 7, ++ GCRY_KDF_PBKDF2, GCRY_MD_SHA1, ++ "saltSALTsaltSALTsaltSALTsaltSALTsalt", 36, ++ 4096, ++ 25, ++ "\xf4\x93\xee\x2b\xbf\x44\x0b\x9e\x64\x53" ++ "\xc2\xb3\x87\xdc\x73\xf8\xfd\xe6\x97\xda" ++ "\xb8\x24\xa0\x26\x50", ++ 1 /* not-compliant because passphrase len is too small */ ++ }, ++ { ++ "passwordPASSWORDpassword", 24, ++ GCRY_KDF_PBKDF2, GCRY_MD_SHA1, ++ "saltSALTsaltSAL", 15, ++ 4096, ++ 25, ++ "\x14\x05\xa4\x2a\xf4\xa8\x12\x14\x7b\x65" ++ "\x8f\xaa\xf0\x7f\x25\xe5\x0f\x0b\x2b\xb7" ++ "\xcf\x8d\x29\x23\x4b", ++ 1 /* not-compliant because salt len is too small */ ++ }, ++ { ++ "passwordPASSWORDpassword", 24, ++ GCRY_KDF_PBKDF2, GCRY_MD_SHA1, ++ "saltSALTsaltSALTsaltSALTsaltSALTsalt", 36, ++ 999, ++ 25, ++ "\xac\xf8\xb4\x67\x41\xc7\xf3\xd1\xa0\xc0" ++ "\x08\xbe\x9b\x23\x96\x78\xbd\x93\xda\x4a" ++ "\x30\xd4\xfb\xf0\x33", ++ 1 /* not-compliant because too few iterations */ ++ }, ++ { ++ "passwordPASSWORDpassword", 24, ++ GCRY_KDF_PBKDF2, GCRY_MD_SHA1, ++ "saltSALTsaltSALTsaltSALTsaltSALTsalt", 36, ++ 4096, ++ 13, ++ "\x3d\x2e\xec\x4f\xe4\x1c\x84\x9b\x80\xc8" ++ "\xd8\x36\x62", ++ 1 /* not-compliant because key size too small */ ++ }, ++ { ++ "passwordPASSWORDpassword", 24, ++ GCRY_KDF_PBKDF2, GCRY_MD_BLAKE2B_512, ++ "saltSALTsaltSALTsaltSALTsaltSALTsalt", 36, ++ 4096, ++ 60, ++ "\xa4\x6b\x53\x35\xdb\xdd\xa3\xd2\x5d\x19\xbb\x11\xfe\xdd\xd9\x9e" ++ "\x45\x2a\x7c\x34\x47\x41\x98\xca\x31\x74\xb6\x34\x22\xac\x83\xb0" ++ "\x38\x6e\xf5\x93\x0f\xf5\x16\x46\x0b\x97\xdc\x6c\x27\x5b\xe7\x25" ++ "\xc2\xcb\xec\x50\x02\xc6\x52\x8b\x34\x68\x53\x65", ++ 1 /* not-compliant because subalgo is not the one of approved */ ++ } ++ }; ++ ++ int tvidx; ++ gpg_error_t err; ++ unsigned char outbuf[100]; ++ int i; ++ ++ for (tvidx=0; tvidx < DIM(tv); tvidx++) ++ { ++ if (verbose) ++ fprintf (stderr, "checking gcry_kdf_derive test vector %d algo %d for FIPS\n", ++ tvidx, tv[tvidx].algo); ++ assert (tv[tvidx].dklen <= sizeof outbuf); ++ err = gcry_kdf_derive (tv[tvidx].p, tv[tvidx].plen, ++ tv[tvidx].algo, tv[tvidx].subalgo, ++ tv[tvidx].salt, tv[tvidx].saltlen, ++ tv[tvidx].iterations, tv[tvidx].dklen, outbuf); ++ ++ if (err) ++ { ++ fail ("gcry_kdf_derive test %d unexpectedly returned an error in FIPS mode: %s\n", ++ tvidx, gpg_strerror (err)); ++ } ++ else ++ { ++ gpg_err_code_t ec; ++ ++ ec = gcry_get_fips_service_indicator (); ++ if (ec == GPG_ERR_INV_OP) ++ { ++ /* libgcrypt is old, no support of the FIPS service indicator. */ ++ fail ("gcry_kdf_derive test %d unexpectedly failed to check the FIPS service indicator.\n", ++ tvidx); ++ continue; ++ } ++ ++ if (!tv[tvidx].expect_failure && ec) ++ { ++ /* Success with the FIPS service indicator == 0 expected, but != 0. */ ++ fail ("gcry_kdf_derive test %d unexpectedly set the indicator in FIPS mode.\n", ++ tvidx); ++ continue; ++ } ++ else if (tv[tvidx].expect_failure && !ec && in_fips_mode) ++ { ++ /* Success with the FIPS service indicator != 0 expected, but == 0. */ ++ fail ("gcry_kdf_derive test %d unexpectedly cleared the indicator in FIPS mode.\n", ++ tvidx); ++ continue; ++ } ++ ++ if (memcmp (outbuf, tv[tvidx].dk, tv[tvidx].dklen)) ++ { ++ fail ("gcry_kdf_derive test %d failed: mismatch\n", tvidx); ++ fputs ("got:", stderr); ++ for (i=0; i < tv[tvidx].dklen; i++) ++ fprintf (stderr, " %02x", outbuf[i]); ++ putc ('\n', stderr); ++ } ++ } ++ } ++} ++ ++ + int + main (int argc, char **argv) + { +@@ -495,6 +653,7 @@ main (int argc, char **argv) + check_digests (); + check_md_o_w_r_c (); + check_mac_o_w_r_c (); ++ check_kdf_derive (); + + return !!error_count; + } +Index: libgcrypt-1.11.0/tests/t-kdf.c +=================================================================== +--- libgcrypt-1.11.0.orig/tests/t-kdf.c ++++ libgcrypt-1.11.0/tests/t-kdf.c +@@ -1927,163 +1927,6 @@ check_fips_indicators (void) + } + + +-static void +-check_fips_gcry_kdf_derive (void) +-{ +- static struct { +- const char *p; /* Passphrase. */ +- size_t plen; /* Length of P. */ +- int algo; +- int subalgo; +- const char *salt; +- size_t saltlen; +- unsigned long iterations; +- int dklen; /* Requested key length. */ +- const char *dk; /* Derived key. */ +- int expect_failure; +- } tv[] = { +- { +- "passwordPASSWORDpassword", 24, +- GCRY_KDF_PBKDF2, GCRY_MD_SHA1, +- "saltSALTsaltSALTsaltSALTsaltSALTsalt", 36, +- 4096, +- 25, +- "\x3d\x2e\xec\x4f\xe4\x1c\x84\x9b\x80\xc8" +- "\xd8\x36\x62\xc0\xe4\x4a\x8b\x29\x1a\x96" +- "\x4c\xf2\xf0\x70\x38", +- 0 +- }, +- { +- "pleaseletmein", 13, +- GCRY_KDF_SCRYPT, 16384, +- "SodiumChloride", 14, +- 1, +- 64, +- "\x70\x23\xbd\xcb\x3a\xfd\x73\x48\x46\x1c\x06\xcd\x81\xfd\x38\xeb" +- "\xfd\xa8\xfb\xba\x90\x4f\x8e\x3e\xa9\xb5\x43\xf6\x54\x5d\xa1\xf2" +- "\xd5\x43\x29\x55\x61\x3f\x0f\xcf\x62\xd4\x97\x05\x24\x2a\x9a\xf9" +- "\xe6\x1e\x85\xdc\x0d\x65\x1e\x40\xdf\xcf\x01\x7b\x45\x57\x58\x87", +- 1 /* not-compliant because unallowed algo */ +- }, +- { +- "passwor", 7, +- GCRY_KDF_PBKDF2, GCRY_MD_SHA1, +- "saltSALTsaltSALTsaltSALTsaltSALTsalt", 36, +- 4096, +- 25, +- "\xf4\x93\xee\x2b\xbf\x44\x0b\x9e\x64\x53" +- "\xc2\xb3\x87\xdc\x73\xf8\xfd\xe6\x97\xda" +- "\xb8\x24\xa0\x26\x50", +- 1 /* not-compliant because passphrase len is too small */ +- }, +- { +- "passwordPASSWORDpassword", 24, +- GCRY_KDF_PBKDF2, GCRY_MD_SHA1, +- "saltSALTsaltSAL", 15, +- 4096, +- 25, +- "\x14\x05\xa4\x2a\xf4\xa8\x12\x14\x7b\x65" +- "\x8f\xaa\xf0\x7f\x25\xe5\x0f\x0b\x2b\xb7" +- "\xcf\x8d\x29\x23\x4b", +- 1 /* not-compliant because salt len is too small */ +- }, +- { +- "passwordPASSWORDpassword", 24, +- GCRY_KDF_PBKDF2, GCRY_MD_SHA1, +- "saltSALTsaltSALTsaltSALTsaltSALTsalt", 36, +- 999, +- 25, +- "\xac\xf8\xb4\x67\x41\xc7\xf3\xd1\xa0\xc0" +- "\x08\xbe\x9b\x23\x96\x78\xbd\x93\xda\x4a" +- "\x30\xd4\xfb\xf0\x33", +- 1 /* not-compliant because too few iterations */ +- }, +- { +- "passwordPASSWORDpassword", 24, +- GCRY_KDF_PBKDF2, GCRY_MD_SHA1, +- "saltSALTsaltSALTsaltSALTsaltSALTsalt", 36, +- 4096, +- 13, +- "\x3d\x2e\xec\x4f\xe4\x1c\x84\x9b\x80\xc8" +- "\xd8\x36\x62", +- 1 /* not-compliant because key size too small */ +- }, +- { +- "passwordPASSWORDpassword", 24, +- GCRY_KDF_PBKDF2, GCRY_MD_BLAKE2B_512, +- "saltSALTsaltSALTsaltSALTsaltSALTsalt", 36, +- 4096, +- 60, +- "\xa4\x6b\x53\x35\xdb\xdd\xa3\xd2\x5d\x19\xbb\x11\xfe\xdd\xd9\x9e" +- "\x45\x2a\x7c\x34\x47\x41\x98\xca\x31\x74\xb6\x34\x22\xac\x83\xb0" +- "\x38\x6e\xf5\x93\x0f\xf5\x16\x46\x0b\x97\xdc\x6c\x27\x5b\xe7\x25" +- "\xc2\xcb\xec\x50\x02\xc6\x52\x8b\x34\x68\x53\x65", +- 1 /* not-compliant because subalgo is not the one of approved */ +- } +- }; +- +- int tvidx; +- gpg_error_t err; +- unsigned char outbuf[100]; +- int i; +- +- for (tvidx=0; tvidx < DIM(tv); tvidx++) +- { +- if (verbose) +- fprintf (stderr, "checking gcry_kdf_derive test vector %d algo %d for FIPS\n", +- tvidx, tv[tvidx].algo); +- assert (tv[tvidx].dklen <= sizeof outbuf); +- err = gcry_kdf_derive (tv[tvidx].p, tv[tvidx].plen, +- tv[tvidx].algo, tv[tvidx].subalgo, +- tv[tvidx].salt, tv[tvidx].saltlen, +- tv[tvidx].iterations, tv[tvidx].dklen, outbuf); +- +- if (err) +- { +- fail ("gcry_kdf_derive test %d unexpectedly returned an error in FIPS mode: %s\n", +- tvidx, gpg_strerror (err)); +- } +- else +- { +- gpg_err_code_t ec; +- +- ec = gcry_get_fips_service_indicator (); +- if (ec == GPG_ERR_INV_OP) +- { +- /* libgcrypt is old, no support of the FIPS service indicator. */ +- fail ("gcry_kdf_derive test %d unexpectedly failed to check the FIPS service indicator.\n", +- tvidx); +- continue; +- } +- +- if (!tv[tvidx].expect_failure && ec) +- { +- /* Success with the FIPS service indicator == 0 expected, but != 0. */ +- fail ("gcry_kdf_derive test %d unexpectedly set the indicator in FIPS mode.\n", +- tvidx); +- continue; +- } +- else if (tv[tvidx].expect_failure && !ec) +- { +- /* Success with the FIPS service indicator != 0 expected, but == 0. */ +- fail ("gcry_kdf_derive test %d unexpectedly cleared the indicator in FIPS mode.\n", +- tvidx); +- continue; +- } +- +- if (memcmp (outbuf, tv[tvidx].dk, tv[tvidx].dklen)) +- { +- fail ("gcry_kdf_derive test %d failed: mismatch\n", tvidx); +- fputs ("got:", stderr); +- for (i=0; i < tv[tvidx].dklen; i++) +- fprintf (stderr, " %02x", outbuf[i]); +- putc ('\n', stderr); +- } +- } +- } +-} +- +- + int + main (int argc, char **argv) + { +@@ -2166,8 +2009,6 @@ main (int argc, char **argv) + check_hkdf (); + if (in_fips_mode) + check_fips_indicators (); +- if (in_fips_mode) +- check_fips_gcry_kdf_derive (); + } + + return error_count ? 1 : 0; diff --git a/libgcrypt-tests-fips-Rename-t-fips-service-ind.patch b/libgcrypt-tests-fips-Rename-t-fips-service-ind.patch new file mode 100644 index 0000000..bb32094 --- /dev/null +++ b/libgcrypt-tests-fips-Rename-t-fips-service-ind.patch @@ -0,0 +1,60 @@ +From 132f346232b33fe41ffee3b3870ec189626676e7 Mon Sep 17 00:00:00 2001 +From: NIIBE Yutaka +Date: Mon, 16 Dec 2024 14:14:24 +0900 +Subject: [PATCH 07/19] tests,fips: Rename t-fips-service-ind. +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* tests/t-fips-service-ind.c: Rename from t-digest.c. +* tests/Makefile.am (tests_bin): Follow the change. + +-- + +GnuPG-bug-id: 7338 +Signed-off-by: NIIBE Yutaka +Signed-off-by: Lucas Mülling +--- + tests/Makefile.am | 2 +- + tests/{t-digest.c => t-fips-service-ind.c} | 4 ++-- + 2 files changed, 3 insertions(+), 3 deletions(-) + rename tests/{t-digest.c => t-fips-service-ind.c} (99%) + +diff --git a/tests/Makefile.am b/tests/Makefile.am +index 93774fe9..3170a58e 100644 +--- a/tests/Makefile.am ++++ b/tests/Makefile.am +@@ -25,7 +25,7 @@ tests_bin = \ + version t-secmem mpitests t-sexp t-convert \ + t-mpi-bit t-mpi-point t-lock \ + prime basic keygen pubkey hmac hashtest t-kdf keygrip \ +- aeswrap random t-kem t-mlkem t-thread-local t-digest ++ aeswrap random t-kem t-mlkem t-thread-local t-fips-service-ind + + if USE_RSA + tests_bin += pkcs1v2 t-rsa-pss t-rsa-15 t-rsa-testparm +diff --git a/tests/t-digest.c b/tests/t-fips-service-ind.c +similarity index 99% +rename from tests/t-digest.c +rename to tests/t-fips-service-ind.c +index e2b1ce32..31c1fc72 100644 +--- a/tests/t-digest.c ++++ b/tests/t-fips-service-ind.c +@@ -1,4 +1,4 @@ +-/* t-digest.c - MD regression tests ++/* t-fips-service-ind.c - FIPS service indicator regression tests + * Copyright (C) 2024 g10 Code GmbH + * + * This file is part of Libgcrypt. +@@ -27,7 +27,7 @@ + #include + #include + +-#define PGM "t-digest" ++#define PGM "t-fips-service-ind" + + #include "t-common.h" + static int in_fips_mode; +-- +2.49.0 + diff --git a/libgcrypt.changes b/libgcrypt.changes new file mode 100644 index 0000000..9ae2875 --- /dev/null +++ b/libgcrypt.changes @@ -0,0 +1,1919 @@ +------------------------------------------------------------------- +Sun Apr 13 20:10:16 UTC 2025 - Lucas Mulling + +- Differentiate use of SHA1 in the service level indicator [jsc#PED-12227] + * Include upstream SLI revamp and fips certification fixes + * Add patches: + - libgcrypt-fips-Introduce-an-internal-API-for-FIPS-service-indicator.patch + - libgcrypt-fips-Introduce-GCRYCTL_FIPS_SERVICE_INDICATOR-and-the-macro.patch + - libgcrypt-fips-kdf-Implement-new-FIPS-service-indicator-for-gcry_kdf_derive.patch + - libgcrypt-fips-md-Implement-new-FIPS-service-indicator-for-gcry_md_hash_.patch + - libgcrypt-fips-tests-Add-t-digest.patch + - libgcrypt-fips-Change-the-internal-API-for-new-FIPS-service-indicator.patch + - libgcrypt-fips-md-Implement-new-FIPS-service-indicator-for-gcry_md_open-API.patch + - libgcrypt-fips-tests-Add-tests-for-md_open-write-read-close-for-t-digest.patch + - libgcrypt-fips-mac-Implement-new-FIPS-service-indicator-for-gcry_mac_open.patch + - libgcrypt-fips-cipher-Implement-new-FIPS-service-indicator-for-cipher_open.patch + - libgcrypt-tests-fips-Add-gcry_mac_open-tests.patch + - libgcrypt-tests-fips-Rename-t-fips-service-ind.patch + - libgcrypt-tests-fips-Move-KDF-tests-to-t-fips-service-ind.patch + - libgcrypt-tests-fips-Add-gcry_cipher_open-tests.patch + - libgcrypt-fips-md-gcry_md_copy-should-care-about-FIPS-service-indicator.patch + - libgcrypt-fips-cipher-Implement-FIPS-service-indicator-for-gcry_pk_hash_-API.patch + - libgcrypt-fips-Introduce-GCRYCTL_FIPS_REJECT_NON_FIPS.patch + - libgcrypt-Fix-the-previous-change.patch + - libgcrypt-fips-Rejection-by-GCRYCTL_FIPS_REJECT_NON_FIPS-not-by-open-flags.patch + - libgcrypt-fips-cipher-Add-behavior-not-to-reject-but-mark-non-compliant.patch + - libgcrypt-fips-ecc-Add-rejecting-or-marking-for-gcry_pk_get_curve.patch + - libgcrypt-tests-Add-more-tests-to-tests-t-fips-service-ind.patch + - libgcrypt-fips-ecc-Check-DATA-in-gcry_pk_sign-verify-in-FIPS-mode.patch + - libgcrypt-fips-cipher-Fix-memory-leak-for-gcry_pk_hash_sign.patch + - libgcrypt-build-Improve-__thread-specifier-check.patch + - libgcrypt-cipher-Check-and-mark-non-compliant-cipher-modes-in-the-SLI.patch + - libgcrypt-cipher-Rename-_gcry_cipher_is_mode_fips_compliant.patch + - libgcrypt-cipher-Don-t-differentiate-GCRY_CIPHER_MODE_CMAC-in-FIPS-mode.patch + - libgcrypt-cipher-rsa-Mark-reject-SHA1-unknown-with-RSA-signature-generation.patch + - libgcrypt-md-Fix-gcry_md_algo_info-to-mark-reject-under-FIPS-mode.patch + - libgcrypt-md-Use-check_digest_algo_spec-in-_gcry_md_selftest.patch + - libgcrypt-tests-Update-t-fips-service-ind-using-GCRY_MD_SHA256-for-KDF-tests.patch + - libgcrypt-fips-cipher-Do-the-computation-when-marking-non-compliant.patch + - libgcrypt-tests-Allow-tests-with-USE_RSA.patch + - libgcrypt-cipher-Add-KAT-for-non-rfc6979-ECDSA-with-fixed-k.patch + - libgcrypt-cipher-Differentiate-use-of-label-K-in-the-SLI.patch + - libgcrypt-cipher-Differentiate-igninvflag-in-the-SLI.patch + - libgcrypt-cipher-Differentiate-no-blinding-flag-in-the-SLI.patch + - libgcrypt-fips-cipher-Add-GCRY_FIPS_FLAG_REJECT_PK_FLAGS.patch + - libgcrypt-cipher-ecc-Fix-for-supplied-K.patch + - libgcrypt-cipher-visibility-Differentiate-use-of-random-override-in-the-SLI.patch + - libgcrypt-cipher-fips-Fix-for-random-override.patch + - libgcrypt-md-Make-SHA-1-non-FIPS-internally-for-1.12-API.patch + - libgcrypt-fips-Fix-GCRY_FIPS_FLAG_REJECT_MD.patch + - libgcrypt-doc-Add-about-GCRYCTL_FIPS_SERVICE_INDICATOR.patch + - libgcrypt-doc-Fix-syntax-error.patch + * Rebase patches: + - libgcrypt-FIPS-SLI-kdf-leylength.patch + +------------------------------------------------------------------- +Tue Jan 7 09:28:25 UTC 2025 - Pedro Monreal + +- Fix redefinition error of 'rol64'. Remove not used rol64() + definition after removing the built-in jitter rng. + * Add libgcrypt-rol64-redefinition.patch + +------------------------------------------------------------------- +Mon Dec 2 10:11:10 UTC 2024 - Pedro Monreal + +- Remove unrecognized option: --enable-m-guard + +------------------------------------------------------------------- +Thu Jun 20 08:11:07 UTC 2024 - Pedro Monreal + +- Update to 1.11.0: + * New and extended interfaces: + - Add an API for Key Encapsulation Mechanism (KEM). [T6755] + - Add Streamlined NTRU Prime sntrup761 algorithm. [rCcf9923e1a5] + - Add Kyber algorithm according to FIPS 203 ipd 2023-08-24. [rC18e5c0d268] + - Add Classic McEliece algorithm. [rC003367b912] + - Add One-Step KDF with hash and MAC. [T5964] + - Add KDF algorithm HKDF of RFC-5869. [T5964] + - Add KDF algorithm X963KDF for use in CMS. [rC3abac420b3] + - Add GMAC-SM4 and Poly1305-SM4. [rCd1ccc409d4] + - Add ARIA block cipher algorithm. [rC316c6d7715] + - Add explicit FIPS indicators for MD and MAC algorithms. [T6376] + - Add support for SHAKE as MGF in RSA. [T6557] + - Add gcry_md_read support for SHAKE algorithms. [T6539] + - Add gcry_md_hash_buffers_ext function. [T7035] + - Add cSHAKE hash algorithm. [rC065b3f4e02] + - Support internal generation of IV for AEAD cipher mode. [T4873] + * Performance: + - Add SM3 ARMv8/AArch64/CE assembly implementation. [rCfe891ff4a3] + - Add SM4 ARMv8/AArch64 assembly implementation. [rCd8825601f1] + - Add SM4 GFNI/AVX2 and GFI/AVX512 implementation. [rC5095d60af4,rCeaed633c16] + - Add SM4 ARMv9 SVE CE assembly implementation. [rC2dc2654006] + - Add PowerPC vector implementation of SM4. [rC0b2da804ee] + - Optimize ChaCha20 and Poly1305 for PPC P10 LE. [T6006] + - Add CTR32LE bulk acceleration for AES on PPC. [rC84f2e2d0b5] + - Add generic bulk acceleration for CTR32LE mode (GCM-SIV) for SM4 + and Camellia. [rCcf956793af] + - Add GFNI/AVX2 implementation of Camellia. [rC4e6896eb9f] + - Add AVX2 and AVX512 accelerated implementations for GHASH (GCM) + and POLYVAL (GCM-SIV). [rCd857e85cb4, rCe6f3600193] + - Add AVX512 implementation for SHA512. [rC089223aa3b] + - Add AVX512 implementation for Serpent. [rCce95b6ec35] + - Add AVX512 implementation for Poly1305 and ChaCha20. [rCcd3ed49770, rC9a63cfd617] + - Add AVX512 accelerated implementation for SHA3 and Blake2. [rCbeaad75f46,rC909daa700e] + - Add VAES/AVX2 accelerated i386 implementation for AES. [rC4a42a042bc] + - Add bulk processing for XTS mode of Camellia and SM4. [rC32b18cdb87, rCaad3381e93] + - Accelerate XTS and ECB modes for Twofish and Serpent. [rCd078a928f5,rC8a1fe5f78f] + - Add AArch64 crypto/SHA512 extension implementation for SHA512. [rCe51d3b8330] + - Add AArch64 crypto-extension implementation for Camellia. [rC898c857206] + - Accelerate OCB authentication on AMD with AVX2. [rC6b47e85d65] + * Bug fixes: + - For PowerPC check for missing optimization level for vector register usage. [T5785] + - Fix EdDSA secret key check. [T6511] + - Fix decoding of PKCS#1-v1.5 and OAEP padding. [rC34c2042792] + - Allow use of PKCS#1-v1.5 with SHA3 algorithms. [T6976] + - Fix AESWRAP padding length check. [T7130] + * Other: + - Allow empty password for Argon2 KDF. [rCa20700c55f] + - Various constant time operation imporvements. + - Add "bp256", "bp384", "bp512" aliases for Brainpool curves. + - Support for the random server has been removed. [T5811] + - The control code GCRYCTL_ENABLE_M_GUARD is deprecated and not + supported any more. Please use valgrind or other tools. [T5822] + - Logging is now done via the libgpg-error logging functions. [rCab0bdc72c7] + * Remove patches fixed upstream: + - libgcrypt-no-deprecated-grep-alias.patch + - libgcrypt-Chacha20-poly1305-Optimized-chacha20-poly1305.patch + - libgcrypt-ppc-enable-P10-assembly-with-ENABLE_FORCE_SOF.patch + * Rebase patches: + - libgcrypt-FIPS-jitter-errorcodes.patch + - libgcrypt-FIPS-jitter-whole-entropy.patch + +------------------------------------------------------------------- +Wed Mar 20 20:31:40 UTC 2024 - Pedro Monreal + +- FIPS: Make sure that Libgcrypt makes use of the built-in Jitter RNG + for the whole length entropy buffer in FIPS mode. [bsc#1220893] + * Add libgcrypt-FIPS-jitter-whole-entropy.patch + +------------------------------------------------------------------- +Wed Mar 20 15:13:04 UTC 2024 - Pedro Monreal + +- FIPS: Set the FSM into error state if Jitter RNG is returning an + error code to the caller when an health test error occurs when + random bytes are requested through the jent_read_entropy_safe() + function. [bsc#1220895] + * Add libgcrypt-FIPS-jitter-errorcodes.patch + +------------------------------------------------------------------- +Mon Mar 11 16:02:55 UTC 2024 - Pedro Monreal + +- FIPS: Replace the built-in jitter rng with standalone version + * Remove the internal jitterentropy copy [bsc#1220896] + * Add libgcrypt-FIPS-jitter-standalone.patch + * Remove not needed libgcrypt-jitterentropy-3.4.0.patch + +------------------------------------------------------------------- +Mon Feb 26 12:13:56 UTC 2024 - Pedro Monreal + +- Update upstream libgcrypt.keyring + +------------------------------------------------------------------- +Sat Jan 27 13:37:34 UTC 2024 - Dirk Müller + +- add libgcrypt-no-deprecated-grep-alias.patch + +------------------------------------------------------------------- +Tue Nov 21 10:36:09 UTC 2023 - Otto Hollmann + +- Re-create HMAC checksum after RPM build strips the library + (bsc#1217058) + +------------------------------------------------------------------- +Wed Nov 15 09:54:00 UTC 2023 - Pedro Monreal + +- Update to 1.10.3: + * Bug fixes: + - Fix public key computation for other EdDSA curves. [rC469919751d6e] + - Remove out of core handler diagnostic in FIPS mode. [T6515] + - Check that the digest size is not zero in gcry_pk_sign_md and + gcry_pk_verify_md. [T6539] + - Make store an s-exp with \0 is considered to be binary. [T6747] + - Various constant-time improvements. + * Portability: + - Use getrandom call only when supported by the platform. [T6442] + - Change the default for --with-libtool-modification to never. [T6619] + * Release-info: https://dev.gnupg.org/T6817 + * Remove patch upstream libgcrypt-1.10.0-out-of-core-handler.patch + +------------------------------------------------------------------- +Tue Oct 17 10:27:15 UTC 2023 - Pedro Monreal + +- Do not pull revision info from GIT when autoconf is run. This + removes the -unknown suffix after the version number. + * Add libgcrypt-nobetasuffix.patch [bsc#1216334] + +------------------------------------------------------------------- +Tue Oct 3 12:58:41 UTC 2023 - Pedro Monreal + +- POWER: performance enhancements for cryptography [jsc#PED-5088] + * Optimize Chacha20 and Poly1305 for PPC P10 LE: [T6006] + - Chacha20/poly1305: Optimized chacha20/poly1305 for + P10 operation [rC88fe7ac33eb4] + - ppc: enable P10 assembly with ENABLE_FORCE_SOFT_HWFEATURES + on arch-3.00 [rC2c5e5ab6843d] + * Add patches: + - libgcrypt-Chacha20-poly1305-Optimized-chacha20-poly1305.patch + - libgcrypt-ppc-enable-P10-assembly-with-ENABLE_FORCE_SOF.patch + +------------------------------------------------------------------- +Mon May 22 11:32:53 UTC 2023 - Pedro Monreal + +- FIPS: Merge the libgcrypt20-hmac package into the library and + remove the "module is complete" trigger file .fips [bsc#1185116] + * Remove libgcrypt-1.10.0-use-fipscheck.patch + +------------------------------------------------------------------- +Tue Apr 11 14:08:24 UTC 2023 - Pedro Monreal + +- Update to 1.10.2: + * Bug fixes: + - Fix Argon2 for the case output > 64. [rC13b5454d26] + - Fix missing HWF_PPC_ARCH_3_10 in HW feature. [rCe073f0ed44] + - Fix RSA key generation failure in forced FIPS mode. [T5919] + - Fix gcry_pk_hash_verify for explicit hash. [T6066] + - Fix a wrong result of gcry_mpi_invm. [T5970] + - Allow building with --disable-asm for HPPA. [T5976] + - Allow building with -Oz. [T6432] + - Enable the fast path to ChaCha20 only when supported. [T6384] + - Use size_t to avoid counter overflow in Keccak when directly + feeding more than 4GiB. [T6217] + * Other: + - Do not use secure memory for a DRBG instance. [T5933] + - Do not allow PKCS#1.5 padding for encryption in FIPS mode. [T5918] + - Fix the behaviour for child process re-seeding in the DRBG. [rC019a40c990] + - Allow verification of small RSA signatures in FIPS mode. [T5975] + - Allow the use of a shorter salt for KDFs in FIPS mode. [T6039] + - Run digest+sign self tests for RSA and ECC in FIPS mode. [rC06c9350165] + - Add function-name based FIPS indicator function. + GCRYCTL_FIPS_SERVICE_INDICATOR_FUNCTION. This is not considered + an ABI changes because the new FIPS features were not yet + approved. [rC822ee57f07] + - Improve PCT in FIPS mode. [rC285bf54b1a, rC4963c127ae, T6397] + - Use getrandom (GRND_RANDOM) in FIPS mode. [rCcf10c74bd9] + - Disable RSA-OAEP padding in FIPS mode. [rCe5bfda492a] + - Check minimum allowed key size in PBKDF in FIPS mode. [T6039,T6219] + - Get maximum 32B of entropy at once in FIPS mode. [rCce0df08bba] + - Prefer gpgrt-config when available. [T5034] + - Mark AESWRAP as approved FIPS algorithm. [T5512] + - Prevent usage of long salt for PSS in FIPS mode. [rCfdd2a8b332] + - Prevent usage of X9.31 keygen in FIPS mode. [rC392e0ccd25] + - Remove GCM mode from the allowed FIPS indicators. [rC1540698389] + - Add explicit FIPS indicators for hash and MAC algorithms. [T6376] + * Release-info: https://dev.gnupg.org/T5905 + * Rebase FIPS patches: + - libgcrypt-FIPS-SLI-hash-mac.patch + - libgcrypt-FIPS-SLI-kdf-leylength.patch + - libgcrypt-FIPS-SLI-pk.patch + +------------------------------------------------------------------- +Wed Mar 8 10:34:34 UTC 2023 - Martin Pluskal + +- Build AVX2 enabled hwcaps library for x86_64-v3 + +------------------------------------------------------------------- +Wed Oct 19 14:01:24 UTC 2022 - Pedro Monreal + +- Update to 1.10.1: + * Bug fixes: + - Fix minor memory leaks in FIPS mode. + - Build fixes for MUSL libc. + * Other: + - More portable integrity check in FIPS mode. + - Add X9.62 OIDs to sha256 and sha512 modules. + * Add the hardware optimizations config file hwf.deny to + the /etc/gcrypt/ directory. This file can be used to globally + disable the use of hardware based optimizations. + * Remove not needed separate_hmac256_binary hmac256 package + +------------------------------------------------------------------- +Wed Sep 14 13:34:13 UTC 2022 - Pedro Monreal + +- Update to 1.10.0: + * New and extended interfaces: + - New control codes to check for FIPS 140-3 approved algorithms. + - New control code to switch into non-FIPS mode. + - New cipher modes SIV and GCM-SIV as specified by RFC-5297. + - Extended cipher mode AESWRAP with padding as specified by + RFC-5649. + - New set of KDF functions. + - New KDF modes Argon2 and Balloon. + - New functions for combining hashing and signing/verification. + * Performance: + - Improved support for PowerPC architectures. + - Improved ECC performance on zSeries/s390x by using accelerated + scalar multiplication. + - Many more assembler performance improvements for several + architectures. + * Bug fixes: + - Fix Elgamal encryption for other implementations. + [bsc#1190239, CVE-2021-40528] + - Check the input length of the point in ECDH. + - Fix an abort in gcry_pk_get_param for "Curve25519". + * Other features: + - The control code GCRYCTL_SET_ENFORCED_FIPS_FLAG is ignored + because it is useless with the FIPS 140-3 related changes. + - Update of the jitter entropy RNG code. + - Simplification of the entropy gatherer when using the getentropy + system call. + * Interface changes relative to the 1.10.0 release: + - GCRYCTL_SET_DECRYPTION_TAG NEW control code. + - GCRYCTL_FIPS_SERVICE_INDICATOR_CIPHER NEW control code. + - GCRYCTL_FIPS_SERVICE_INDICATOR_KDF NEW control code. + - GCRYCTL_NO_FIPS_MODE = 83 NEW control code. + - GCRY_CIPHER_MODE_SIV NEW mode. + - GCRY_CIPHER_MODE_GCM_SIV NEW mode. + - GCRY_CIPHER_EXTENDED NEW flag. + - GCRY_SIV_BLOCK_LEN NEW macro. + - gcry_cipher_set_decryption_tag NEW macro. + - GCRY_KDF_ARGON2 NEW constant. + - GCRY_KDF_BALLOON NEW constant. + - GCRY_KDF_ARGON2D NEW constant. + - GCRY_KDF_ARGON2I NEW constant. + - GCRY_KDF_ARGON2ID NEW constant. + - gcry_kdf_hd_t NEW type. + - gcry_kdf_job_fn_t NEW type. + - gcry_kdf_dispatch_job_fn_t NEW type. + - gcry_kdf_wait_all_jobs_fn_t NEW type. + - struct gcry_kdf_thread_ops NEW struct. + - gcry_kdf_open NEW function. + - gcry_kdf_compute NEW function. + - gcry_kdf_final NEW function. + - gcry_kdf_close NEW function. + - gcry_pk_hash_sign NEW function. + - gcry_pk_hash_verify NEW function. + - gcry_pk_random_override_new NEW function. + * Rebase libgcrypt-1.8.4-allow_FSM_same_state.patch and rename + to libgcrypt-1.10.0-allow_FSM_same_state.patch + * Remove unused CAVS tests and related patches: + - cavs_driver.pl cavs-test.sh + - libgcrypt-1.6.1-fips-cavs.patch + - drbg_test.patch + * Remove DSA sign/verify patches for the FIPS CAVS test since DSA + has been disabled in FIPS mode: + - libgcrypt-fipsdrv-enable-algo-for-dsa-sign.patch + - libgcrypt-fipsdrv-enable-algo-for-dsa-verify.patch + * Rebase libgcrypt-FIPS-SLI-pk.patch + * Rebase libgcrypt_indicators_changes.patch and + libgcrypt-indicate-shake.patch and merge both into + libgcrypt-FIPS-SLI-hash-mac.patch + * Rebase libgcrypt-FIPS-kdf-leylength.patch and rename to + libgcrypt-FIPS-SLI-kdf-leylength.patch + * Rebase libgcrypt-jitterentropy-3.4.0.patch + * Rebase libgcrypt-FIPS-rndjent_poll.patch + * Rebase libgcrypt-out-of-core-handler.patch and rename to + libgcrypt-1.10.0-out-of-core-handler.patch + * Since the FIPS .hmac file is now calculated with the internal + tool hmac256, only the "module is complete" trigger .fips file + is checked. Rename libgcrypt-1.6.1-use-fipscheck.patch + to libgcrypt-1.10.0-use-fipscheck.patch + * Remove patches fixed upstream: + - libgcrypt-1.4.1-rijndael_no_strict_aliasing.patch + - libgcrypt-1.5.0-LIBGCRYPT_FORCE_FIPS_MODE-env.diff + - libgcrypt-fix-rng.patch + - libgcrypt-1.8.3-fips-ctor.patch + - libgcrypt-1.8.4-use_xfree.patch + - libgcrypt-1.8.4-getrandom.patch + - libgcrypt-1.8.4-fips_ctor_skip_integrity_check.patch + - libgcrypt-dsa-rfc6979-test-fix.patch + - libgcrypt-fix-tests-fipsmode.patch + - libgcrypt-FIPS-RSA-DSA-ECDSA-hashing-operation.patch + - libgcrypt-1.8.4-fips-keygen.patch + - libgcrypt-invoke-global_init-from-constructor.patch + - libgcrypt-Restore-self-tests-from-constructor.patch + - libgcrypt-FIPS-GMAC_AES-benckmark.patch + - libgcrypt-global_init-constructor.patch + - libgcrypt-random_selftests-testentropy.patch + - libgcrypt-rsa-no-blinding.patch + - libgcrypt-ecc-ecdsa-no-blinding.patch + - libgcrypt-PCT-DSA.patch + - libgcrypt-PCT-ECC.patch + - libgcrypt-PCT-RSA.patch + - libgcrypt-fips_selftest_trigger_file.patch + - libgcrypt-pthread-in-t-lock-test.patch + - libgcrypt-FIPS-hw-optimizations.patch + - libgcrypt-FIPS-module-version.patch + - libgcrypt-FIPS-disable-3DES.patch + - libgcrypt-FIPS-fix-regression-tests.patch + - libgcrypt-FIPS-RSA-keylen.patch + - libgcrypt-FIPS-RSA-keylen-tests.patch + - libgcrypt-FIPS-fix-gcry_mpi_sub_ui.patch + - libgcrypt-FIPS-verify-unsupported-KDF-test.patch + - libgcrypt-FIPS-HMAC-short-keylen.patch + - libgcrypt-FIPS-service-indicators.patch + - libgcrypt-FIPS-disable-DSA.patch + - libgcrypt-jitterentropy-3.3.0.patch + - libgcrypt-FIPS-Zeroize-hmac.patch + * Update libgcrypt.keyring + +------------------------------------------------------------------- +Thu Sep 8 10:34:53 UTC 2022 - Pedro Monreal + +- FIPS: Get most of the entropy from rndjent_poll [bsc#1202117] + * Add libgcrypt-FIPS-rndjent_poll.patch + * Rebase libgcrypt-jitterentropy-3.4.0.patch + +------------------------------------------------------------------- +Wed Sep 7 22:03:51 UTC 2022 - Pedro Monreal + +- FIPS: Check keylength in gcry_fips_indicator_kdf() [bsc#1190700] + * Consider approved keylength greater or equal to 112 bits. + * Add libgcrypt-FIPS-kdf-leylength.patch + +------------------------------------------------------------------- +Wed Sep 7 12:53:14 UTC 2022 - Pedro Monreal + +- FIPS: Zeroize buffer and digest in check_binary_integrity() + * Add libgcrypt-FIPS-Zeroize-hmac.patch [bsc#1191020] + +------------------------------------------------------------------- +Tue Aug 23 09:19:00 UTC 2022 - Pedro Monreal + +- FIPS: gpg/gpg2 gets out of core handler in FIPS mode while + typing Tab key to Auto-Completion. [bsc#1182983] + * Add libgcrypt-out-of-core-handler.patch + +------------------------------------------------------------------- +Mon Aug 8 11:33:03 UTC 2022 - Pedro Monreal + +- FIPS: Port libgcrypt to use jitterentropy [bsc#1202117, jsc#SLE-24941] + * Enable the jitter based entropy generator by default in random.conf + - Add libgcrypt-jitterentropy-3.3.0.patch + * Update the internal jitterentropy to version 3.4.0 + - Add libgcrypt-jitterentropy-3.4.0.patch + +------------------------------------------------------------------- +Mon Aug 1 07:27:35 UTC 2022 - Stephan Kulow + +- Fix reproducible build problems: + - Do not use %release in binaries (but use SOURCE_DATE_EPOCH) + - Fix date call messed up by spec-cleaner + +------------------------------------------------------------------- +Thu Apr 14 12:30:36 UTC 2022 - Dennis Knorr + +- FIPS: extend the service indicator [bsc#1190700] + * introduced a pk indicator function + * adapted the approved and non approved ciphersuites + * Add libgcrypt_indicators_changes.patch + * Add libgcrypt-indicate-shake.patch + +------------------------------------------------------------------- +Tue Mar 22 12:32:09 UTC 2022 - Pedro Monreal + +- FIPS: Implement a service indicator for asymmetric ciphers [bsc#1190700] + * Mark RSA public key encryption and private key decryption with + padding (e.g. OAEP, PKCS) as non-approved since RSA-OAEP lacks + peer key assurance validation requirements per SP800-56Brev2. + * Mark ECC as approved only for NIST curves P-224, P-256, P-384 + and P-521 with check for common NIST names and aliases. + * Mark DSA, ELG, EDDSA, ECDSA and ECDH as non-approved. + * Add libgcrypt-FIPS-SLI-pk.patch + * Rebase libgcrypt-FIPS-service-indicators.patch +- Run the regression tests also in FIPS mode. + * Disable tests for non-FIPS approved algos. + * Rebase: libgcrypt-FIPS-verify-unsupported-KDF-test.patch + +------------------------------------------------------------------- +Tue Feb 1 11:28:51 UTC 2022 - Pedro Monreal + +- FIPS: Disable DSA in FIPS mode [bsc#1195385] + * Upstream task: https://dev.gnupg.org/T5710 + * Add libgcrypt-FIPS-disable-DSA.patch + +------------------------------------------------------------------- +Wed Jan 19 08:36:58 UTC 2022 - Pedro Monreal + +- FIPS: Service level indicator [bsc#1190700] + * Provide an indicator to check wether the service utilizes an + approved cryptographic algorithm or not. + * Add patches: + - libgcrypt-FIPS-service-indicators.patch + - libgcrypt-FIPS-verify-unsupported-KDF-test.patch + - libgcrypt-FIPS-HMAC-short-keylen.patch + +------------------------------------------------------------------- +Tue Dec 7 09:41:01 UTC 2021 - Pedro Monreal + +- FIPS: Fix gcry_mpi_sub_ui subtraction [bsc#1193480] + * gcry_mpi_sub_ui: fix subtracting from negative value + * Add libgcrypt-FIPS-fix-gcry_mpi_sub_ui.patch + +------------------------------------------------------------------- +Tue Nov 30 09:42:23 UTC 2021 - Pedro Monreal + +- FIPS: Define an entropy source SP800-90B compliant [bsc#1185140] + * Disable jitter entropy by default in random.conf + * Disable only-urandom option by default in random.conf + +------------------------------------------------------------------- +Fri Nov 26 13:10:29 UTC 2021 - Pedro Monreal + +- FIPS: RSA KeyGen/SigGen fail with 4096 bit key sizes [bsc#1192240] + * rsa: Check RSA keylen constraints for key operations. + * rsa: Fix regression in not returning an error for prime generation. + * tests: Add 2k RSA key working in FIPS mode. + * tests: pubkey: Replace RSA key to one of 2k. + * tests: pkcs1v2: Skip tests with small keys in FIPS. + * Add patches: + - libgcrypt-FIPS-RSA-keylen.patch + - libgcrypt-FIPS-RSA-keylen-tests.patch + +------------------------------------------------------------------- +Mon Nov 8 10:21:39 UTC 2021 - Pedro Monreal + +- FIPS: Disable 3DES/Triple-DES in FIPS mode [bsc#1185138] + * Add libgcrypt-FIPS-disable-3DES.patch + +------------------------------------------------------------------- +Tue Nov 2 11:31:19 UTC 2021 - Pedro Monreal + +- FIPS: PBKDF requirements [bsc#1185137] + * The PBKDF2 selftests were introduced in libgcrypt version + 1.9.1 in the function selftest_pbkdf2() + * Upstream task: https://dev.gnupg.org/T5182 + +------------------------------------------------------------------- +Thu Oct 28 19:48:06 UTC 2021 - Pedro Monreal + +- FIPS: Fix regression tests in FIPS mode [bsc#1192131] + * Add libgcrypt-FIPS-fix-regression-tests.patch + * Upstream task: https://dev.gnupg.org/T5520 + +------------------------------------------------------------------- +Thu Sep 21 11:25:06 UTC 2021 - Pedro Monreal + +- FIPS: Provide a module name/identifier and version that can be + mapped to the validation records. [bsc#1190706] + * Add libgcrypt-FIPS-module-version.patch + * Upstream task: https://dev.gnupg.org/T5600 + +------------------------------------------------------------------- +Thu Sep 21 10:23:44 UTC 2021 - Pedro Monreal + +- FIPS: Enable hardware support also in FIPS mode [bsc#1187110] + * Add libgcrypt-FIPS-hw-optimizations.patch + * Upstream task: https://dev.gnupg.org/T5508 + +------------------------------------------------------------------- +Mon Aug 23 12:08:24 UTC 2021 - Pedro Monreal + +- Update to 1.9.4: + * Bug fixes: + - Fix Elgamal encryption for other implementations. [CVE-2021-33560] + - Fix alignment problem on macOS. + - Check the input length of the point in ECDH. + - Fix an abort in gcry_pk_get_param for "Curve25519". + * Other features: + - Add GCM and CCM to OID mapping table for AES. + * Upstream libgcrypt-CVE-2021-33560-fix-ElGamal-enc.patch + +------------------------------------------------------------------- +Mon Aug 23 10:11:55 UTC 2021 - Pedro Monreal + +- Remove not needed patch libgcrypt-sparcv9.diff + +------------------------------------------------------------------- +Thu Jul 15 12:53:45 UTC 2021 - Pedro Monreal + +- Fix building test t-lock with pthread. [bsc#1189745] + * Explicitly add -lpthread to compile the t-lock test. + * Add libgcrypt-pthread-in-t-lock-test.patch + +------------------------------------------------------------------- +Fri Jun 11 13:17:54 UTC 2021 - Pedro Monreal + +- Security fix: [bsc#1187212, CVE-2021-33560] + * cipher: Fix ElGamal encryption for other implementations. + * Exponent blinding was added in version 1.9.3. This patch + fixes ElGamal encryption, see: https://dev.gnupg.org/T5328 +- Add libgcrypt-CVE-2021-33560-fix-ElGamal-enc.patch + +------------------------------------------------------------------- +Tue Apr 20 08:46:11 UTC 2021 - Paolo Stivanin + +- libgcrypt 1.9.3: + * Bug fixes: + - Fix build problems on i386 using gcc-4.7. + - Fix checksum calculation in OCB decryption for AES on s390. + - Fix a regression in gcry_mpi_ec_add related to certain usages + of curve 25519. + - Fix a symbol not found problem on Apple M1. + - Fix for Apple iOS getentropy peculiarity. + - Make keygrip computation work for compressed points. + * Performance: + - Add x86_64 VAES/AVX2 accelerated implementation of Camellia. + - Add x86_64 VAES/AVX2 accelerated implementation of AES. + - Add VPMSUMD acceleration for GCM mode on PPC. + * Internal changes. + - Harden MPI conditional code against EM leakage. + - Harden Elgamal by introducing exponent blinding. + +------------------------------------------------------------------- +Wed Feb 17 09:49:55 UTC 2021 - Andreas Stieger + +- libgcrypt 1.9.2: + * Fix building with --disable-asm on x86 + * Check public key for ECDSA verify operation + * Make sure gcry_get_config (NULL) returns a nul-terminated + string + * Fix a memory leak in the ECDH code + * Fix a reading beyond end of input buffer in SHA2-avx2 +- remove obsolete texinfo packaging macros + +------------------------------------------------------------------- +Tue Feb 2 01:06:47 UTC 2021 - Pedro Monreal + +- Update to 1.9.1 + * *Fix exploitable bug* in hash functions introduced with + 1.9.0. [bsc#1181632, CVE-2021-3345] + * Return an error if a negative MPI is used with sexp scan + functions. + * Check for operational FIPS in the random and KDF functions. + * Fix compile error on ARMv7 with NEON disabled. + * Fix self-test in KDF module. + * Improve assembler checks for better LTO support. + * Fix 32-bit cross build on x86. + * Fix non-NEON ARM assembly implementation for SHA512. + * Fix build problems with the cipher_bulk_ops_t typedef. + * Fix Ed25519 private key handling for preceding ZEROs. + * Fix overflow in modular inverse implementation. + * Fix register access for AVX/AVX2 implementations of Blake2. + * Add optimized cipher and hash functions for s390x/zSeries. + * Use hardware bit counting functionx when available. + * Update DSA functions to match FIPS 186-3. + * New self-tests for CMACs and KDFs. + * Add bulk cipher functions for OFB and GCM modes. +- Update libgpg-error required version + +------------------------------------------------------------------- +Tue Feb 1 12:03:31 UTC 2021 - Pedro Monreal + +- Use the suffix variable correctly in get_hmac_path() +- Rebase libgcrypt-fips_selftest_trigger_file.patch + +------------------------------------------------------------------- +Mon Jan 25 12:38:35 UTC 2021 - Pedro Monreal + +- Add the global config file /etc/gcrypt/random.conf + * This file can be used to globally change parameters of the random + generator with the options: only-urandom and disable-jent. + +------------------------------------------------------------------- +Thu Jan 21 15:42:15 UTC 2021 - Pedro Monreal + +- Update to 1.9.0: + New stable branch of Libgcrypt with full API and ABI compatibility + to the 1.8 series. Release-info: https://dev.gnupg.org/T4294 + * New and extended interfaces: + - New curves Ed448, X448, and SM2. + - New cipher mode EAX. + - New cipher algo SM4. + - New hash algo SM3. + - New hash algo variants SHA512/224 and SHA512/256. + - New MAC algos for Blake-2 algorithms, the new SHA512 variants, + SM3, SM4 and for a GOST variant. + - New convenience function gcry_mpi_get_ui. + - gcry_sexp_extract_param understands new format specifiers to + directly store to integers and strings. + - New function gcry_ecc_mul_point and curve constants for Curve448 + and Curve25519. + - New function gcry_ecc_get_algo_keylen. + - New control code GCRYCTL_AUTO_EXPAND_SECMEM to allow growing the + secure memory area. + * Performance optimizations and bug fixes: See Release-info. + * Other features: + - Add OIDs from RFC-8410 as aliases for Ed25519 and Curve25519. + - Add mitigation against ECC timing attack CVE-2019-13627. + - Internal cleanup of the ECC implementation. + - Support reading EC point in compressed format for some curves. +- Rebase patches: + * libgcrypt-1.4.1-rijndael_no_strict_aliasing.patch + * libgcrypt-1.5.0-LIBGCRYPT_FORCE_FIPS_MODE-env.diff + * libgcrypt-1.6.1-use-fipscheck.patch + * drbg_test.patch + * libgcrypt-fipsdrv-enable-algo-for-dsa-sign.patch + * libgcrypt-FIPS-RSA-DSA-ECDSA-hashing-operation.patch + * libgcrypt-1.8.4-fips-keygen.patch + * libgcrypt-1.8.4-getrandom.patch + * libgcrypt-fix-tests-fipsmode.patch + * libgcrypt-global_init-constructor.patch + * libgcrypt-ecc-ecdsa-no-blinding.patch + * libgcrypt-PCT-RSA.patch + * libgcrypt-PCT-ECC.patch +- Remove patches: + * libgcrypt-unresolved-dladdr.patch + * libgcrypt-CVE-2019-12904-GCM-Prefetch.patch + * libgcrypt-CVE-2019-12904-GCM.patch + * libgcrypt-CVE-2019-12904-AES.patch + * libgcrypt-CMAC-AES-TDES-selftest.patch + * libgcrypt-1.6.1-fips-cfgrandom.patch + * libgcrypt-fips_rsa_no_enforced_mode.patch + +------------------------------------------------------------------- +Sat Oct 24 10:25:13 UTC 2020 - Andreas Stieger + +- libgcrypt 1.8.7: + * Support opaque MPI with gcry_mpi_print + * Fix extra entropy collection via clock_gettime, a fallback code + path for legacy hardware + +------------------------------------------------------------------- +Tue Jul 7 09:12:27 UTC 2020 - Pedro Monreal Gonzalez + +- Update to 1.8.6 + * mpi: Consider +0 and -0 the same in mpi_cmp + * mpi: Fix flags in mpi_copy for opaque MPI + * mpi: Fix the return value of mpi_invm_generic + * mpi: DSA,ECDSA: Fix use of mpi_invm + - Call mpi_invm before _gcry_dsa_modify_k + - Call mpi_invm before _gcry_ecc_ecdsa_sign + * mpi: Constant time mpi_inv with some conditions + - mpi/mpi-inv.c (mpih_add_n_cond, mpih_sub_n_cond, mpih_swap_cond) + - New: mpih_abs_cond, mpi_invm_odd + - Rename from _gcry_mpi_invm: mpi_invm_generic + - Use mpi_invm_odd for usual odd cases: _gcry_mpi_invm + * mpi: Abort on division by zero also in _gcry_mpi_tdiv_qr + * Fix wrong code execution in Poly1305 ARM/NEON implementation + - Set r14 to -1 at function entry: (_gcry_poly1305_armv7_neon_init_ext) + * Set vZZ.16b register to zero before use in armv8 gcm implementation + * random: Fix include of config.h + * Fix declaration of internal function _gcry_mpi_get_ui: Don't use ulong + * ecc: Fix wrong handling of shorten PK bytes + - Zeros are already recovered: (_gcry_ecc_mont_decodepoint) +- Update libgcrypt-ecc-ecdsa-no-blinding.patch + +------------------------------------------------------------------- +Tue May 19 11:25:37 UTC 2020 - Pedro Monreal Gonzalez + +- FIPS: RSA/DSA/ECC test_keys() print out debug messages [bsc#1171872] + * Print the debug messages in test_keys() only in debug mode. +- Update patches: libgcrypt-PCT-RSA.patch libgcrypt-PCT-DSA.patch + libgcrypt-PCT-ECC.patch + +------------------------------------------------------------------- +Mon Apr 27 08:55:12 UTC 2020 - Pedro Monreal Gonzalez + +- FIPS: libgcrypt: Double free in test_keys() on failed signature + verification [bsc#1169944] + * Use safer gcry_mpi_release() instead of mpi_free() +- Update patches: + * libgcrypt-PCT-DSA.patch + * libgcrypt-PCT-RSA.patch + * libgcrypt-PCT-ECC.patch + +------------------------------------------------------------------- +Thu Apr 16 16:45:23 UTC 2020 - Vítězslav Čížek + +- Ship the FIPS checksum file in the shared library package and + create a separate trigger file for the FIPS selftests (bsc#1169569) + * add libgcrypt-fips_selftest_trigger_file.patch + * refresh libgcrypt-global_init-constructor.patch +- Remove libgcrypt-binary_integrity_in_non-FIPS.patch obsoleted + by libgcrypt-global_init-constructor.patch + +------------------------------------------------------------------- +Wed Apr 15 13:55:27 UTC 2020 - Pedro Monreal Gonzalez + +- FIPS: Verify that the generated signature and the original input + differ in test_keys function for RSA, DSA and ECC: [bsc#1165539] +- Add zero-padding when qx and qy have different lengths when + assembling the Q point from affine coordinates. +- Refreshed patches: + * libgcrypt-PCT-DSA.patch + * libgcrypt-PCT-RSA.patch + * libgcrypt-PCT-ECC.patch + +------------------------------------------------------------------- +Mon Mar 30 10:48:02 UTC 2020 - Pedro Monreal Gonzalez + +- FIPS: Switch the PCT to use the new signature operation [bsc#1165539] + * Patches for DSA, RSA and ECDSA test_keys functions: + - libgcrypt-PCT-DSA.patch + - libgcrypt-PCT-RSA.patch + - libgcrypt-PCT-ECC.patch +- Update patch: libgcrypt-FIPS-RSA-DSA-ECDSA-hashing-operation.patch + +------------------------------------------------------------------- +Thu Mar 26 18:09:47 UTC 2020 - Pedro Monreal Gonzalez + +- FIPS: Run self-tests from constructor during power-on [bsc#1166748] + * Set up global_init as the constructor function: + - libgcrypt-global_init-constructor.patch + * Relax the entropy requirements on selftest. This is especially + important for virtual machines to boot properly before the RNG + is available: + - libgcrypt-random_selftests-testentropy.patch + - libgcrypt-rsa-no-blinding.patch + - libgcrypt-ecc-ecdsa-no-blinding.patch + * Fix benchmark regression test in FIPS mode: + - libgcrypt-FIPS-GMAC_AES-benckmark.patch + +------------------------------------------------------------------- +Thu Mar 12 16:54:33 UTC 2020 - Pedro Monreal Gonzalez + +- Remove check not needed in _gcry_global_constructor [bsc#1164950] + * Update libgcrypt-Restore-self-tests-from-constructor.patch + +------------------------------------------------------------------- +Tue Feb 25 22:13:24 UTC 2020 - Pedro Monreal Gonzalez + +- FIPS: Run the self-tests from the constructor [bsc#1164950] + * Add libgcrypt-invoke-global_init-from-constructor.patch + +------------------------------------------------------------------- +Fri Jan 17 17:35:15 UTC 2020 - Pedro Monreal Gonzalez + +- FIPS: libgcrypt DSA PQG parameter generation: Missing value [bsc#1161219] +- FIPS: libgcrypt DSA PQG verification incorrect results [bsc#1161215] +- FIPS: libgcrypt RSA siggen/keygen: 4k not supported [bsc#1161220] + * Add patch from Fedora libgcrypt-1.8.4-fips-keygen.patch + +------------------------------------------------------------------- +Wed Dec 11 10:18:23 UTC 2019 - Pedro Monreal Gonzalez + +- FIPS: RSA/DSA/ECDSA are missing hashing operation [bsc#1155337] + * Add libgcrypt-FIPS-RSA-DSA-ECDSA-hashing-operation.patch + +------------------------------------------------------------------- +Wed Nov 27 14:01:01 UTC 2019 - Pedro Monreal Gonzalez + +- Fix tests in FIPS mode: + * Fix tests: basic benchmark bench-slope pubkey t-cv25519 t-secmem + * Add patch libgcrypt-fix-tests-fipsmode.patch + +------------------------------------------------------------------- +Tue Nov 26 18:48:20 UTC 2019 - Pedro Monreal Gonzalez + +- Fix test dsa-rfc6979 in FIPS mode: + * Disable tests in elliptic curves with 192 bits which are not + recommended in FIPS mode + * Add patch libgcrypt-dsa-rfc6979-test-fix.patch + +------------------------------------------------------------------- +Tue Nov 12 11:05:02 UTC 2019 - Pedro Monreal Gonzalez + +- CMAC AES and TDES FIPS self-tests: + * CMAC AES self test missing [bsc#1155339] + * CMAC TDES self test missing [bsc#1155338] +- Add libgcrypt-CMAC-AES-TDES-selftest.patch + +------------------------------------------------------------------- +Fri Aug 30 14:17:48 UTC 2019 - Andreas Stieger + +- libgcrypt 1.8.5: + * CVE-2019-13627: mitigation against an ECDSA timing attack (boo#1148987) + * Improve ECDSA unblinding + * Provide a pkg-config file + +------------------------------------------------------------------- +Wed Jun 26 06:52:54 UTC 2019 - Jason Sikes + +- Fixed redundant fips tests in some situations causing sudo to stop + working when pam-kwallet is installed. bsc#1133808 + * Added libgcrypt-1.8.4-fips_ctor_skip_integrity_check.patch + * Removed libgcrypt-fips_run_selftest_at_constructor.patch + because it was obsoleted by libgcrypt-1.8.3-fips-ctor.patch + * Removed libgcrypt-fips_ignore_FIPS_MODULE_PATH.patch + because it was obsoleted by libgcrypt-1.8.4-fips_ctor_skip_integrity_check.patch + +------------------------------------------------------------------- +Fri Jun 21 16:53:07 UTC 2019 - Pedro Monreal Gonzalez + +- Fixed env-script-interpreter in cavs_driver.pl + +------------------------------------------------------------------- +Fri Jun 21 16:39:00 UTC 2019 - Pedro Monreal Gonzalez + +- Security fix: [bsc#1138939, CVE-2019-12904] + * The C implementation of AES is vulnerable to a flush-and-reload + side-channel attack because physical addresses are available to + other processes. (The C implementation is used on platforms where + an assembly-language implementation is unavailable.) + * Added patches: + - libgcrypt-CVE-2019-12904-GCM-Prefetch.patch + - libgcrypt-CVE-2019-12904-GCM.patch + - libgcrypt-CVE-2019-12904-AES.patch + +------------------------------------------------------------------- +Fri Apr 26 06:47:45 UTC 2019 - Jason Sikes + +- do not try to open /dev/urandom if getrandom() works + * Added libgcrypt-1.8.4-getrandom.patch +- Drop libgcrypt-init-at-elf-load-fips.patch obsoleted + by libgcrypt-1.8.3-fips-ctor.patch + +------------------------------------------------------------------- +Tue Apr 23 12:38:40 UTC 2019 - Jason Sikes + +- Restored libgcrypt-binary_integrity_in_non-FIPS.patch sans section that + was partially causing bsc#1131183. +- Fixed race condition in multi-threaded applications by allowing a FSM state + transition to the current state. This means some tests are run twice. + * Added libgcrypt-1.8.4-allow_FSM_same_state.patch +- Fixed an issue in malloc/free wrappers so that memory created by the malloc() + wrappers will be destroyed using the free() wrappers. + * Added libgcrypt-1.8.4-use_xfree.patch + +------------------------------------------------------------------- +Fri Apr 5 21:56:00 UTC 2019 - Jason Sikes + +- removed libgcrypt-binary_integrity_in_non-FIPS.patch since it was breaking + libotr. bsc#1131183 + +------------------------------------------------------------------- +Tue Mar 26 16:30:23 UTC 2019 - Vítězslav Čížek + +- libgcrypt-1.8.3-fips-ctor.patch changed the way the fips selftests + are invoked as well as the state transition, adjust the code so + a missing checksum file is not an issue in non-FIPS mode (bsc#1097073) + * update libgcrypt-binary_integrity_in_non-FIPS.patch + +------------------------------------------------------------------- +Tue Mar 26 16:25:18 UTC 2019 - Vítězslav Čížek + +- Enforce the minimal RSA keygen size in fips mode (bsc#1125740) + * add libgcrypt-fips_rsa_no_enforced_mode.patch + +------------------------------------------------------------------- +Fri Mar 22 14:13:05 UTC 2019 - Vítězslav Čížek + +- Don't run full self-tests from constructor (bsc#1097073) + * Don't call global_init() from the constructor, _gcry_global_constructor() + from libgcrypt-1.8.3-fips-ctor.patch takes care of the binary + integrity check instead. + * Only the binary checksum will be verified, the remaining + self-tests will be run upon the library initialization +- Add libgcrypt-fips_ignore_FIPS_MODULE_PATH.patch +- Drop libgcrypt-init-at-elf-load-fips.patch and + libgcrypt-fips_run_selftest_at_constructor.patch obsoleted + by libgcrypt-1.8.3-fips-ctor.patch + +------------------------------------------------------------------- +Thu Mar 7 10:53:40 UTC 2019 - Pedro Monreal Gonzalez + +- Skip all the self-tests except for binary integrity when called + from the constructor (bsc#1097073) + * Added libgcrypt-1.8.3-fips-ctor.patch from Fedora + +------------------------------------------------------------------- +Mon Nov 26 17:09:47 UTC 2018 - Vítězslav Čížek + +- Fail selftests when checksum file is missing in FIPS mode only + (bsc#1117355) + * add libgcrypt-binary_integrity_in_non-FIPS.patch + +------------------------------------------------------------------- +Sun Oct 28 18:57:53 UTC 2018 - astieger@suse.com + +- libgcrypt 1.8.4: + * Fix infinite loop with specific application implementations + * Fix possible leak of a few bits of secret primes to pageable + memory + * Fix possible hang in the RNG (1.8.3) + * Always make use of getrandom if possible and then use + its /dev/urandom behaviour + +------------------------------------------------------------------- +Mon Jul 2 10:38:42 UTC 2018 - schwab@suse.de + +- libgcrypt-1.6.3-aliasing.patch, libgcrypt-ppc64.patch, + libgcrypt-strict-aliasing.patch: Remove obsolete patches +- libgcrypt-1.4.1-rijndael_no_strict_aliasing.patch: Rediff +- Reenable testsuite + +------------------------------------------------------------------- +Wed Jun 13 10:46:33 UTC 2018 - kbabioch@suse.com + +- Update to version 1.8.3: + - Use blinding for ECDSA signing to mitigate a novel side-channel + attack. (CVE-2018-0495 bsc#1097410) + - Fix incorrect counter overflow handling for GCM when using an IV + size other than 96 bit. + - Fix incorrect output of AES-keywrap mode for in-place encryption + on some platforms. + - Fix the gcry_mpi_ec_curve_point point validation function. + - Fix rare assertion failure in gcry_prime_check. +- Applied spec-cleaner + +------------------------------------------------------------------- +Wed May 2 14:31:07 UTC 2018 - pmonrealgonzalez@suse.com + +- Suggest libgcrypt20-hmac for package libgcrypt20 to ensure they + are installed in the right order. [bsc#1090766] + +------------------------------------------------------------------- +Thu Mar 29 06:37:44 UTC 2018 - pmonrealgonzalez@suse.com + +- Extended the fipsdrv dsa-sign and dsa-verify commands with the + --algo parameter for the FIPS testing of DSA SigVer and SigGen + (bsc#1064455). + * Added libgcrypt-fipsdrv-enable-algo-for-dsa-sign.patch + * Added libgcrypt-fipsdrv-enable-algo-for-dsa-verify.patch + +------------------------------------------------------------------- +Thu Feb 22 15:10:36 UTC 2018 - fvogt@suse.com + +- Use %license (boo#1082318) + +------------------------------------------------------------------- +Wed Dec 13 20:09:28 UTC 2017 - astieger@suse.com + +- libgcrypt 1.8.2: + * Fix fatal out of secure memory status in the s-expression + parser on heavy loaded systems. + * Add auto expand secmem feature or use by GnuPG 2.2.4 + +------------------------------------------------------------------- +Mon Aug 28 17:54:24 UTC 2017 - astieger@suse.com + +- libgcrypt 1.8.1: + * Mitigate a local side-channel attack on Curve25519 dubbed "May + the Fourth be With You" CVE-2017-0379 bsc#1055837 + * Add more extra bytes to the pool after reading a seed file + * Add the OID SHA384WithECDSA from RFC-7427 to SHA-384 + * Fix build problems with the Jitter RNG + * Fix assembler code build problems on Rasbian (ARMv8/AArch32-CE) + +------------------------------------------------------------------- +Mon Jul 24 23:43:40 UTC 2017 - jengelh@inai.de + +- RPM group fixes. + +------------------------------------------------------------------- +Fri Jul 21 15:50:14 UTC 2017 - astieger@suse.com + +- libgcrypt 1.8.0: + * New cipher mode XTS + * New hash function Blake-2 + * New function gcry_mpi_point_copy. + * New function gcry_get_config. + * GCRYCTL_REINIT_SYSCALL_CLAMP allows to init nPth after Libgcrypt. + * New gobal configuration file /etc/gcrypt/random.conf. + * GCRYCTL_PRINT_CONFIG does now also print build information for + libgpg-error and the used compiler version. + * GCRY_CIPHER_MODE_CFB8 is now supported. + * A jitter based entropy collector is now used in addition to the + other entropy collectors. + * Optimized gcry_md_hash_buffers for SHA-256 and SHA-512. + random pool lock). + * Interface changes relative to the 1.7.0 release: + gcry_get_config NEW function. + gcry_mpi_point_copy NEW function. + GCRYCTL_REINIT_SYSCALL_CLAMP NEW macro. + GCRY_MD_BLAKE2B_512 NEW constant. + GCRY_MD_BLAKE2B_384 NEW constant. + GCRY_MD_BLAKE2B_256 NEW constant. + GCRY_MD_BLAKE2B_160 NEW constant. + GCRY_MD_BLAKE2S_256 NEW constant. + GCRY_MD_BLAKE2S_224 NEW constant. + GCRY_MD_BLAKE2S_160 NEW constant. + GCRY_MD_BLAKE2S_128 NEW constant. + GCRY_CIPHER_MODE_XTS NEW constant. + gcry_md_info DEPRECATED. +- Refresh patch libgcrypt-1.6.3-aliasing.patch + +------------------------------------------------------------------- +Thu Jun 29 09:49:44 UTC 2017 - astieger@suse.com + +- libgcrypt 1.7.8: + * CVE-2017-7526: Mitigate a flush+reload side-channel attack on + RSA secret keys (bsc#1046607) + +------------------------------------------------------------------- +Sun Jun 4 19:26:12 UTC 2017 - astieger@suse.com + +- libgcrypt 1.7.7: + * Fix possible timing attack on EdDSA session key (previously + patched, drop libgcrypt-secure-EdDSA-session-key.patch) + * Fix long standing bug in secure memory implementation which + could lead to a segv on free + +------------------------------------------------------------------- +Fri Jun 2 10:05:18 UTC 2017 - pmonrealgonzalez@suse.com + +- Added libgcrypt-secure-EdDSA-session-key.patch [bsc#1042326] + * Store the session key in secure memory to ensure that constant + time point operations are used in the MPI library. + +------------------------------------------------------------------- +Fri Jan 20 09:41:15 UTC 2017 - rmaliska@suse.com + +- libgcrypt 1.7.6: + * Fix counter operand from read-only to read/write + * Fix too large jump alignment in mpih-rshift + +------------------------------------------------------------------- +Thu Dec 15 10:32:18 UTC 2016 - astieger@suse.com + +- libgcrypt 1.7.5: + * Fix regression in mlock detection introduced with 1.7.4 + +------------------------------------------------------------------- +Tue Dec 13 12:20:47 UTC 2016 - astieger@suse.com + +- libgcrypt 1.7.4: + * ARMv8/AArch32 performance improvements for AES, GCM, SHA-256, + and SHA-1. + * Add ARMv8/AArch32 assembly implementation for Twofish and + Camellia. + * Add bulk processing implementation for ARMv8/AArch32. + * Add Stribog OIDs. + * Improve the DRBG performance and sync the code with the Linux + version. + * When secure memory is requested by the MPI functions or by + gcry_xmalloc_secure, they do not anymore lead to a fatal error + if the secure memory pool is used up. Instead new pools are + allocated as needed. These new pools are not protected against + being swapped out (mlock can't be used). Mitigation for + minor confidentiality issues is encryption swap space. + * Fix GOST 28147 CryptoPro-B S-box. + * Fix error code handling of mlock calls. + +------------------------------------------------------------------- +Sat Aug 20 10:38:15 UTC 2016 - mpluskal,vcizek,astieger}@suse.com + +- libgcrypt 1.7.3: + * security issue already fixes with 1.6.6 + * Fix building of some asm modules with older compilers and CPUs. + * ARMv8/AArch32 improvements for AES, GCM, SHA-256, and SHA-1. +- includes changes from libgcrypt 1.7.2: + * Bug fixes: + - Fix setting of the ECC cofactor if parameters are specified. + - Fix memory leak in the ECC code. + - Remove debug message about unsupported getrandom syscall. + - Fix build problems related to AVX use. + - Fix bus errors on ARM for Poly1305, ChaCha20, AES, and SHA-512. + * Internal changes: + - Improved fatal error message for wrong use of gcry_md_read. + - Disallow symmetric encryption/decryption if key is not set. +- includes changes from 1.7.1: + * Bug fixes: + - Fix ecc_verify for cofactor support. + - Fix portability bug when using gcc with Solaris 9 SPARC. + - Build fix for OpenBSD/amd64 + - Add OIDs to the Serpent ciphers. + * Internal changes: + - Use getrandom system call on Linux if available. + - Blinding is now also used for RSA signature creation. + - Changed names of debug envvars +- includes changes from 1.7.0: + * New algorithms and modes: + - SHA3-224, SHA3-256, SHA3-384, SHA3-512, and MD2 hash algorithms. + - SHAKE128 and SHAKE256 extendable-output hash algorithms. + - ChaCha20 stream cipher. + - Poly1305 message authentication algorithm + - ChaCha20-Poly1305 Authenticated Encryption with Associated Data + mode. + - OCB mode. + - HMAC-MD2 for use by legacy applications. + * New curves for ECC: + - Curve25519. + - sec256k1. + - GOST R 34.10-2001 and GOST R 34.10-2012. + * Performance: + - Improved performance of KDF functions. + - Assembler optimized implementations of Blowfish and Serpent on + ARM. + - Assembler optimized implementation of 3DES on x86. + - Improved AES using the SSSE3 based vector permutation method by + Mike Hamburg. + - AVX/BMI is used for SHA-1 and SHA-256 on x86. This is for SHA-1 + about 20% faster than SSSE3 and more than 100% faster than the + generic C implementation. + - 40% speedup for SHA-512 and 72% for SHA-1 on ARM Cortex-A8. + - 60-90% speedup for Whirlpool on x86. + - 300% speedup for RIPE MD-160. + - Up to 11 times speedup for CRC functions on x86. + * Other features: + - Improved ECDSA and FIPS 186-4 compliance. + - Support for Montgomery curves. + - gcry_cipher_set_sbox to tweak S-boxes of the gost28147 cipher + algorithm. + - gcry_mpi_ec_sub to subtract two points on a curve. + - gcry_mpi_ec_decode_point to decode an MPI into a point object. + - Emulation for broken Whirlpool code prior to 1.6.0. [from 1.6.1] + - Flag "pkcs1-raw" to enable PCKS#1 padding with a user supplied + hash part. + - Parameter "saltlen" to set a non-default salt length for RSA PSS. + - A SP800-90A conforming DRNG replaces the former X9.31 alternative + random number generator. + - Map deprecated RSA algo number to the RSA algo number for better + backward compatibility. [from 1.6.2] + - Use ciphertext blinding for Elgamal decryption [CVE-2014-3591]. + See http://www.cs.tau.ac.il/~tromer/radioexp/ for details. + [from 1.6.3] + - Fixed data-dependent timing variations in modular exponentiation + [related to CVE-2015-0837, Last-Level Cache Side-Channel Attacks + are Practical]. [from 1.6.3] + - Flag "no-keytest" for ECC key generation. Due to a bug in + the parser that flag will also be accepted but ignored by older + version of Libgcrypt. [from 1.6.4] + - Speed up the random number generator by requiring less extra + seeding. [from 1.6.4] + - Always verify a created RSA signature to avoid private key leaks + due to hardware failures. [from 1.6.4] + - Mitigate side-channel attack on ECDH with Weierstrass curves + [CVE-2015-7511]. See http://www.cs.tau.ac.IL/~tromer/ecdh/ for + details. [from 1.6.5] + * Internal changes: + - Moved locking out to libgpg-error. + - Support of the SYSROOT envvar in the build system. + - Refactor some code. + - The availability of a 64 bit integer type is now mandatory. + * Bug fixes: + - Fixed message digest lookup by OID (regression in 1.6.0). + - Fixed a build problem on NetBSD + - Fixed some asm build problems and feature detection bugs. + * Interface changes relative to the 1.6.0 release: + gcry_cipher_final NEW macro. + GCRY_CIPHER_MODE_CFB8 NEW constant. + GCRY_CIPHER_MODE_OCB NEW. + GCRY_CIPHER_MODE_POLY1305 NEW. + gcry_cipher_set_sbox NEW macro. + gcry_mac_get_algo NEW. + GCRY_MAC_HMAC_MD2 NEW. + GCRY_MAC_HMAC_SHA3_224 NEW. + GCRY_MAC_HMAC_SHA3_256 NEW. + GCRY_MAC_HMAC_SHA3_384 NEW. + GCRY_MAC_HMAC_SHA3_512 NEW. + GCRY_MAC_POLY1305 NEW. + GCRY_MAC_POLY1305_AES NEW. + GCRY_MAC_POLY1305_CAMELLIA NEW. + GCRY_MAC_POLY1305_SEED NEW. + GCRY_MAC_POLY1305_SERPENT NEW. + GCRY_MAC_POLY1305_TWOFISH NEW. + gcry_md_extract NEW. + GCRY_MD_FLAG_BUGEMU1 NEW [from 1.6.1]. + GCRY_MD_GOSTR3411_CP NEW. + GCRY_MD_SHA3_224 NEW. + GCRY_MD_SHA3_256 NEW. + GCRY_MD_SHA3_384 NEW. + GCRY_MD_SHA3_512 NEW. + GCRY_MD_SHAKE128 NEW. + GCRY_MD_SHAKE256 NEW. + gcry_mpi_ec_decode_point NEW. + gcry_mpi_ec_sub NEW. + GCRY_PK_EDDSA NEW constant. + GCRYCTL_GET_TAGLEN NEW. + GCRYCTL_SET_SBOX NEW. + GCRYCTL_SET_TAGLEN NEW. +- Apply libgcrypt-1.6.3-aliasing.patch only on big-endian + architectures +- update drbg_test.patch and install cavs testing directory again +- As DRBG is upstream, drop pateches: + v9-0001-SP800-90A-Deterministic-Random-Bit-Generator.patch + 0002-Compile-DRBG.patch + 0003-Function-definitions-of-interfaces-for-random.c.patch + 0004-Invoke-DRBG-from-common-libgcrypt-RNG-code.patch + 0005-Function-definitions-for-gcry_control-callbacks.patch + 0006-DRBG-specific-gcry_control-requests.patch + v9-0007-User-interface-to-DRBG.patch + libgcrypt-fix-rng.patch +- drop obsolete: + libgcrypt-fips-dsa.patch + libgcrypt-fips_ecdsa.patch + +------------------------------------------------------------------- +Wed Aug 17 18:21:44 UTC 2016 - astieger@suse.com + +- libgcrypt 1.6.6: + * fix CVE-2016-6313: Issue in the mixing functions of the random + number generators allowed an attacker who obtained a number of + bytes from the standard RNG to predict some of the next ouput. + (bsc#994157) + +------------------------------------------------------------------- +Mon May 16 14:37:45 UTC 2016 - pjanouch@suse.de + +- remove conditionals for unsupported distributions (before 13.2), + it would not build anyway because of new dependencies + +------------------------------------------------------------------- +Mon May 16 12:36:14 UTC 2016 - pjanouch@suse.de + +- make the -hmac package depend on the same version of the library, + fixing bsc#979629 FIPS: system fails to reboot after installing + fips pattern + +------------------------------------------------------------------- +Tue Feb 9 20:51:59 UTC 2016 - astieger@suse.com + +- update to 1.6.5: + * CVE-2015-7511: Mitigate side-channel attack on ECDH with + Weierstrass curves (boo#965902) + +------------------------------------------------------------------- +Sat Oct 10 11:56:08 UTC 2015 - astieger@suse.com + +- follow-up to libgcrypt 1.6.4 update: sosuffix is 20.0.4 + +------------------------------------------------------------------- +Tue Sep 8 08:03:19 UTC 2015 - vcizek@suse.com + +- update to 1.6.4 +- fixes libgcrypt equivalent of CVE-2015-5738 (bsc#944456) + * Speed up the random number generator by requiring less extra + seeding. + * New flag "no-keytest" for ECC key generation. Due to a bug in the + parser that flag will also be accepted but ignored by older version + of Libgcrypt. + * Always verify a created RSA signature to avoid private key leaks + due to hardware failures. + * Other minor bug fixes. + +------------------------------------------------------------------- +Tue Jun 23 15:15:30 UTC 2015 - dvaleev@suse.com + +- Fix gpg2 tests on BigEndian architectures: s390x ppc64 + libgcrypt-1.6.3-aliasing.patch + +------------------------------------------------------------------- +Sun Mar 1 21:16:26 UTC 2015 - astieger@suse.com + +- fix sosuffix for 1.6.3 (20.0.3) + +------------------------------------------------------------------- +Sat Feb 28 19:31:10 UTC 2015 - astieger@suse.com + +- libgcrypt 1.6.3 [bnc#920057]: + * Use ciphertext blinding for Elgamal decryption [CVE-2014-3591]. + * Fixed data-dependent timing variations in modular exponentiation + [related to CVE-2015-0837, Last-Level Cache Side-Channel Attacks + are Practical]. +- update upstream signing keyring + +------------------------------------------------------------------- +Fri Feb 6 18:42:28 UTC 2015 - coolo@suse.com + +- making the build reproducible - see + http://lists.gnupg.org/pipermail/gnupg-commits/2014-September/010683.html + for a very similiar problem + +------------------------------------------------------------------- +Fri Feb 6 18:38:55 UTC 2015 - dimstar@opensuse.org + +- Move %install_info_delete calls from postun to preun: the files + must still be present to be parsed. +- Fix the names passed to install_info for gcrypt.info-[12].gz + instead of gcrypt-[12].info.gz. + +------------------------------------------------------------------- +Fri Feb 6 18:30:26 UTC 2015 - coolo@suse.com + +- fix filename for info pages in %post scripts + +------------------------------------------------------------------- +Wed Nov 5 20:37:24 UTC 2014 - andreas.stieger@gmx.de + +- libgcrypt 1.6.2: + * Map deprecated RSA algo number to the RSA algo number for better + backward compatibility. + * Support a 0x40 compression prefix for EdDSA. + * Improve ARM hardware feature detection and building. + * Fix building for the x32 ABI platform. + * Fix some possible NULL deref bugs. +- remove libgcrypt-1.6.0-use-intenal-functions.patch, upstream + via xtrymalloc macro +- remove libgcrypt-fixed-sizet.patch, upstream +- adjust libgcrypt-1.6.1-use-fipscheck.patch for xtrymalloc change + +------------------------------------------------------------------- +Sun Sep 21 10:08:39 UTC 2014 - vcizek@suse.com + +- disabled curve P-192 in FIPS mode (bnc#896202) + * added libgcrypt-fips_ecdsa.patch +- don't use SHA-1 for ECDSA in FIPS mode +- also run the fips self tests only in FIPS mode + +------------------------------------------------------------------- +Tue Sep 16 13:56:01 UTC 2014 - vcizek@suse.com + +- run the fips self tests at the constructor code + * added libgcrypt-fips_run_selftest_at_constructor.patch + +------------------------------------------------------------------- +Tue Sep 16 12:17:17 UTC 2014 - vcizek@suse.com + +- rewrite the DSA-2 code to be FIPS 186-4 compliant (bnc#894216) + * added libgcrypt-fips-dsa.patch + * install fips186_dsa +- use 2048 bit keys in selftests_dsa + +------------------------------------------------------------------- +Mon Sep 1 10:57:06 UTC 2014 - vcizek@suse.com + +- fix an issue in DRBG patchset + * size_t type is 32-bit on 32-bit systems +- fix a potential NULL pointer deference in DRBG patchset + * patches from https://bugs.g10code.com/gnupg/issue1701 +- added v9-0001-SP800-90A-Deterministic-Random-Bit-Generator.patch +- added v9-0007-User-interface-to-DRBG.patch +- removed v7-0001-SP800-90A-Deterministic-Random-Bit-Generator.patch +- removed v7-0007-User-interface-to-DRBG.patch +- add a subpackage for CAVS testing + * add cavs_driver.pl and cavs-test.sh from the kernel cavs package + * added drbg_test.patch + +------------------------------------------------------------------- +Tue Aug 12 07:43:19 UTC 2014 - meissner@suse.com + +- split off the -hmac package that contains the checksums + +------------------------------------------------------------------- +Mon May 26 12:05:17 UTC 2014 - meissner@suse.com + +- libgcrypt-fix-rng.patch: make drbg work again in FIPS mode. +- libgcrypt-1.6.1-use-fipscheck.patch: library to test is libgcrypt.so.20 + and not libgcrypt.so.11 +- libgcrypt-init-at-elf-load-fips.patch: initialize globally on ELF + DSO loading to meet FIPS requirements. + +------------------------------------------------------------------- +Tue May 13 10:47:51 UTC 2014 - vcizek@suse.com + +- add new 0007-User-interface-to-DRBG.patch from upstream + * fixes bnc#877233 + * supersedes the patch from previous entry + +------------------------------------------------------------------- +Sun May 12 13:25:33 UTC 2014 - tittiatcoke@gmail.com + +- Correct patch 0007-User-interface-to-DRBG.patch so that the + struct used in the route matches the header of the function + +------------------------------------------------------------------- +Tue May 6 13:28:33 UTC 2014 - vcizek@suse.com + +- add support for SP800-90A DRBG (fate#316929, bnc#856312) + * patches by Stephan Mueller (http://www.chronox.de/drbg.html): + 0001-SP800-90A-Deterministic-Random-Bit-Generator.patch.bz2 + 0002-Compile-DRBG.patch + 0003-Function-definitions-of-interfaces-for-random.c.patch + 0004-Invoke-DRBG-from-common-libgcrypt-RNG-code.patch + 0005-Function-definitions-for-gcry_control-callbacks.patch + 0006-DRBG-specific-gcry_control-requests.patch + 0007-User-interface-to-DRBG.patch + * only after 13.1 (the patches need libgpg-error 1.13) +- drop libgcrypt-fips-allow-legacy.patch (not needed and wasn't + applied anyway) + +------------------------------------------------------------------- +Thu Apr 3 12:04:46 UTC 2014 - tchvatal@suse.com + +- Cleanup with spec-cleaner to sort out. +- Really apply ppc64 patch as it was ommited probably by mistake. + +------------------------------------------------------------------- +Thu Mar 27 14:57:22 UTC 2014 - meissner@suse.com + +- FIPS changes (from Fedora): + - replaced libgcrypt-1.5.0-etc_gcrypt_rngseed-symlink.diff by + libgcrypt-1.6.1-fips-cfgrandom.patch + - libgcrypt-fixed-sizet.patch: fixed an int type for -flto + - libgcrypt-1.6.1-use-fipscheck.patch: use the fipscheck binary + - libgcrypt-1.6.1-fips-cavs.patch: add CAVS tests +- use fipscheck only after 13.1 +- libgcrypt-fips-allow-legacy.patch: attempt to allow some + legacy algorithms for gpg2 usage even in FIPS mode. + (currently not applied) + +------------------------------------------------------------------- +Thu Jan 30 13:29:49 UTC 2014 - idonmez@suse.com + +- Drop arm-missing-files.diff, fixed upstream + +------------------------------------------------------------------- +Wed Jan 29 18:40:49 UTC 2014 - andreas.stieger@gmx.de + +- libgcrypt 1.6.1, a bugfix release with the folloging fixes: + * Added emulation for broken Whirlpool code prior to 1.6.0. + * Improved performance of KDF functions. + * Improved ECDSA compliance. + * Fixed message digest lookup by OID (regression in 1.6.0). + * Fixed memory leaks in ECC code. + * Fixed some asm build problems and feature detection bugs. + * Interface changes relative to the 1.6.0 release: + GCRY_MD_FLAG_BUGEMU1 NEW (minor API change). + +------------------------------------------------------------------- +Fri Jan 3 16:36:21 UTC 2014 - dmueller@suse.com + +- add arm-missing-files.diff: Add missing files to fix build + +------------------------------------------------------------------- +Fri Jan 3 09:43:39 UTC 2014 - mvyskocil@suse.com + +- fix bnc#856915: can't open /dev/urandom + * correct libgcrypt-1.5.0-etc_gcrypt_rngseed-symlink.diff +- require libgpg-error 1.11 or higher + +------------------------------------------------------------------- +Thu Dec 19 13:53:21 UTC 2013 - mvyskocil@suse.com + +- fix dependency for 32bit devel package +- name hmac files according soname +- fix hmac subpackage dependency + +------------------------------------------------------------------- +Thu Dec 19 09:03:21 UTC 2013 - mvyskocil@suse.com + +- update to 1.6. + * Removed the long deprecated gcry_ac interface. Thus Libgcrypt is + not anymore ABI compatible to previous versions if they used the ac + interface. Check NEWS in libgcrypt-devel for removed interfaces. + * Removed the module register subsystem. + * The deprecated message digest debug macros have been removed. Use + gcry_md_debug instead. + * Removed deprecated control codes. + * Improved performance of most cipher algorithms as well as for the + SHA family of hash functions. + * Added support for the IDEA cipher algorithm. + * Added support for the Salsa20 and reduced Salsa20/12 stream ciphers. + * Added limited support for the GOST 28147-89 cipher algorithm. + * Added support for the GOST R 34.11-94 and R 34.11-2012 (Stribog) + hash algorithms. + * Added a random number generator to directly use the system's RNG. + Also added an interface to prefer the use of a specified RNG. + * Added support for the SCRYPT algorithm. + * Mitigated the Yarom/Falkner flush+reload side-channel attack on RSA + secret keys. See [CVE-2013-4242]. + * Added support for Deterministic DSA as per RFC-6969. + * Added support for curve Ed25519. + * Added a scatter gather hash convenience function. + * Added several MPI amd SEXP helper functions. + * Added support for negative numbers to gcry_mpi_print, + gcry_mpi_aprint and gcry_mpi_scan. + * The algorithm ids GCRY_PK_ECDSA and GCRY_PK_ECDH are now + deprecated. Use GCRY_PK_ECC if you need an algorithm id. + * Changed gcry_pk_genkey for "ecc" to only include the curve name and + not the parameters. The flag "param" may be used to revert this. + * Added a feature to globally disable selected hardware features. + * Added debug helper functions. +- rebased patches + * libgcrypt-1.5.0-etc_gcrypt_rngseed-symlink.diff + * libgcrypt-ppc64.patch +- add libgcrypt-1.6.0-use-intenal-functions.patch to fix fips.c build +- Move all documentation to -devel package + +------------------------------------------------------------------- +Fri Jul 26 22:05:46 UTC 2013 - andreas.stieger@gmx.de + +- update to 1.5.3 [bnc#831359] CVE-2013-4242 + * Mitigate the Yarom/Falkner flush+reload side-channel attack on + RSA secret keys. See . + +------------------------------------------------------------------- +Thu Jul 25 09:15:43 UTC 2013 - mvyskocil@suse.com + +- port SLE enhancenments to Factory (bnc#831028) + * add libgcrypt-unresolved-dladdr.patch (bnc#701267) + * add libgcrypt-1.5.0-etc_gcrypt_rngseed-symlink.diff (bnc#724841) + * add libgcrypt-1.5.0-LIBGCRYPT_FORCE_FIPS_MODE-env.diff +- install .hmac256.hmac (bnc#704068) +- enable varuous new options in configure (m-guard, hmac binary check and + random device linux) +- build with all ciphers, pubkeys and digest by default as whitelist + simply allowed them all + +------------------------------------------------------------------- +Mon Jun 17 13:22:33 UTC 2013 - coolo@suse.com + +- avoid gpg-offline in bootstrap packages + +------------------------------------------------------------------- +Sun Jun 16 22:56:56 UTC 2013 - crrodriguez@opensuse.org + +- Library must be built with large file support in + 32 bit archs. + +------------------------------------------------------------------- +Thu Apr 18 18:23:36 UTC 2013 - andreas.stieger@gmx.de + +- update to 1.5.2 + * The upstream sources now contain the IDEA algorithm, dropping: + idea.c.gz + libgcrypt-1.5.0-idea.patch + libgcrypt-1.5.0-idea_codecleanup.patch + * Made the Padlock code work again (regression since 1.5.0). + * Fixed alignment problems for Serpent. + * Fixed two bugs in ECC computations. + +------------------------------------------------------------------- +Fri Mar 22 09:31:11 UTC 2013 - mvyskocil@suse.com + +- add GPL3.0+ to License tag because of dumpsexp (bnc#810759) + +------------------------------------------------------------------- +Mon Mar 18 20:41:00 UTC 2013 - andreas.stieger@gmx.de + +- update to 1.5.1 + * Allow empty passphrase with PBKDF2. + * Do not abort on an invalid algorithm number in + gcry_cipher_get_algo_keylen and gcry_cipher_get_algo_blklen. + * Fixed some Valgrind warnings. + * Fixed a problem with select and high fd numbers. + * Improved the build system + * Various minor bug fixes. + * Interface changes relative to the 1.5.0 release: + GCRYCTL_SET_ENFORCED_FIPS_FLAG NEW. + GCRYPT_VERSION_NUMBER NEW. +- add verification of source code signatures +- now requires automake 1.11 to build + +------------------------------------------------------------------- +Sat Feb 2 18:51:33 UTC 2013 - coolo@suse.com + +- update license to new format + +------------------------------------------------------------------- +Tue Jun 12 21:19:18 UTC 2012 - chris@computersalat.de + +- fix deps + * libgpg-error-devel >= 1.8 +- add libsoname macro + +------------------------------------------------------------------- +Sun Feb 12 15:23:56 UTC 2012 - crrodriguez@opensuse.org + +- Libraries back into %{_libdir}, /usr merge project + +------------------------------------------------------------------- +Sat Dec 24 23:51:26 UTC 2011 - opensuse@dstoecker.de + +- add the missing IDEA algorithm after the patent is no longer relevant + +------------------------------------------------------------------ +Sun Nov 13 14:37:29 UTC 2011 - jengelh@medozas.de + +- Remove redundant/unwanted tags/section (cf. specfile guidelines) + +------------------------------------------------------------------- +Sun Nov 13 09:16:36 UTC 2011 - coolo@suse.com + +- add libtool as explicit buildrequire to avoid implicit dependency from prjconf + +------------------------------------------------------------------- +Sun Oct 2 18:38:28 UTC 2011 - crrodriguez@opensuse.org + +- Update to version 1.5.0, most important changes + * Uses the Intel AES-NI instructions if available + * Support ECDH. + +------------------------------------------------------------------- +Fri Nov 19 09:59:41 UTC 2010 - mvyskocil@suse.cz + +- update to 1.4.6 + * Fixed minor memory leak in DSA key generation. + * No more switching to FIPS mode if /proc/version is not readable. + * Fixed a sigill during Padlock detection on old CPUs. + * Boosted SHA-512 performance by 30% on ia32 boxes and gcc 4.3; + SHA-256 went up by 25%. + * New variants of the TIGER algorithm. + * New cipher algorithm mode for AES-WRAP. + * Interface changes relative to the 1.4.2 release: + GCRY_MD_TIGER1 NEW + GCRY_MD_TIGER2 NEW + GCRY_CIPHER_MODE_AESWRAP NEW + +------------------------------------------------------------------- +Sun Jul 4 19:07:16 UTC 2010 - jengelh@medozas.de + +- add missing definition of udiv_qrnnd for sparcv9:32 +- use %_smp_mflags + +------------------------------------------------------------------- +Sat Dec 19 12:58:20 CET 2009 - jengelh@medozas.de + +- add baselibs.conf as a source +- disable the use of hand-coded assembler functions on sparc - + this is giving me an infinite loop with ./tests/prime + (specifically ./sparc32v8/mpih-mul1.S:_gcry_mpih_mul_1. + Fedora disables this too. + +------------------------------------------------------------------- +Tue Apr 7 15:45:06 CEST 2009 - crrodriguez@suse.de + +- update to version 1.4.4 + * Publish GCRY_MODULE_ID_USER and GCRY_MODULE_ID_USER_LAST constants. + This functionality has been in Libgcrypt since 1.3.0. + * MD5 may now be used in non-enforced fips mode. + * Fixed HMAC for SHA-384 and SHA-512 with keys longer than 64 bytes. + * In fips mode, RSA keys are now generated using the X9.31 algorithm + and DSA keys using the FIPS 186-2 algorithm. + * The transient-key flag is now also supported for DSA key + generation. DSA domain parameters may be given as well. + +------------------------------------------------------------------- +Thu Jan 29 10:57:01 CET 2009 - olh@suse.de + +- obsolete libgcrypt-error-XXbit in the library subpackage + +------------------------------------------------------------------- +Wed Dec 10 12:34:56 CET 2008 - olh@suse.de + +- use Obsoletes: -XXbit only for ppc64 to help solver during distupgrade + (bnc#437293) + +------------------------------------------------------------------- +Tue Nov 11 17:23:54 CET 2008 - mkoenig@suse.de + +- build rijndael.c with -fno-strict-aliasing [bnc#443693] + +------------------------------------------------------------------- +Thu Oct 30 12:34:56 CET 2008 - olh@suse.de + +- obsolete old -XXbit packages (bnc#437293) + +------------------------------------------------------------------- +Mon Jun 30 11:47:59 CEST 2008 - mkoenig@suse.de + +- update to version 1.4.1 + * Fixed a bug which led to the comsumption of far too much + entropy for the intial seeding + * Improved AES performance for CFB and CBC modes + +------------------------------------------------------------------- +Sun May 11 11:54:39 CEST 2008 - coolo@suse.de + +- fix rename of xxbit packages + +------------------------------------------------------------------- +Thu Apr 10 12:54:45 CEST 2008 - ro@suse.de + +- added baselibs.conf file to build xxbit packages + for multilib support + +------------------------------------------------------------------- +Thu Jan 17 12:20:25 CET 2008 - mkoenig@suse.de + +- update to version 1.4.0: + * The entire library is now under the LGPL. The helper programs and + the manual are under the GPL + * New control code GCRYCTL_PRINT_CONFIG + * Experimental support for ECDSA + * Assembler support for the AMD64 architecture + * Non executable stack support is now used by default + * New configure option --enable-random-daemon + * The new function gcry_md_debug should be used instead of the + gcry_md_start_debug and gcry_md_stop_debug macros. + * Support for DSA2 + * Reserved algorithm ranges for use by applications + * gcry_mpi_rshift does not anymore truncate the shift count + * Support for OFB encryption mode + * Support for the Camellia cipher + * Support for the SEED cipher + * Support for SHA-224 and HMAC using SHA-384 and SHA-512 + * Reading and writing the random seed file is now protected by a + fcntl style file lock + * Made the RNG immune against fork without exec + * Changed the way the RNG gets initialized + * The ASN.1 DER template for SHA-224 has been fixed + * The ACE engine of VIA processors is now used for AES-128 +- changed package layout to conform shlib policy: + new subpackage libgcrypt11 +- disable static library +- for reference: bugzilla entry of last change #304749 + +------------------------------------------------------------------- +Thu Sep 13 01:28:53 CEST 2007 - ltinkl@suse.cz + +- add sanity check for mpi of size 0 (#304479) + +------------------------------------------------------------------- +Mon Feb 5 10:25:21 CET 2007 - mkoenig@suse.de + +- update to version 1.2.4: + * Fixed a bug in the memory allocator which could have been the + reason for some of non-duplicable bugs. + * Other minor bug fixes. + +------------------------------------------------------------------- +Wed Dec 13 12:47:48 CET 2006 - mkoenig@suse.de + +- get rid of .la file and fix devel so link + +------------------------------------------------------------------- +Tue Dec 5 18:30:30 CET 2006 - mkoenig@suse.de + +- move shared lib to /%_lib + +------------------------------------------------------------------- +Thu Aug 31 14:29:56 CEST 2006 - mkoenig@suse.de + +- update to version 1.2.3: + * Rewrote gcry_mpi_rshift to allow arbitrary shift counts. + * Minor bug fixes. +- added libgpg-error-devel and glibc-devel to Requires tag + of devel subpackage + +------------------------------------------------------------------- +Wed Jan 25 21:37:28 CET 2006 - mls@suse.de + +- converted neededforbuild to BuildRequires + +------------------------------------------------------------------- +Wed Nov 2 16:44:48 CET 2005 - hvogel@suse.de + +- enable noexecstack +- build ac.c with fno-strict-aliasing + +------------------------------------------------------------------- +Tue Oct 25 13:40:15 CEST 2005 - hvogel@suse.de + +- update to version 1.2.2 + +------------------------------------------------------------------- +Thu Jun 23 11:26:58 CEST 2005 - hvogel@suse.de + +- call install_info macro in post/postun of the devel package +- depend on libgcrypt +- add clean section + +------------------------------------------------------------------- +Tue Jan 18 11:51:51 CET 2005 - hvogel@suse.de + +- update to version 1.2.1 + +------------------------------------------------------------------- +Tue Jan 11 16:48:10 CET 2005 - schwab@suse.de + +- Fix info dir entry. + +------------------------------------------------------------------- +Wed Nov 17 11:22:44 CET 2004 - hvogel@suse.de + +- require libgpg-error-devel (Bug #48271) +- get rid of the NLD parts + +------------------------------------------------------------------- +Wed Jul 14 11:12:54 CEST 2004 - adrian@suse.de + +- create -devel subpackage +- prepare for nld + +------------------------------------------------------------------- +Wed May 19 14:57:45 CEST 2004 - hvogel@suse.de + +- update to version 1.2.0 + +------------------------------------------------------------------- +Mon Mar 22 16:48:53 CET 2004 - meissner@suse.de + +- disable make check, because it uses /dev/random whihc is + not filled on some server machines. + +------------------------------------------------------------------- +Wed Mar 17 15:01:51 CET 2004 - meissner@suse.de + +- fixed too over enthusiastic powerpc switches to make it work + on ppc64. (It compiled before, but did not work). +- enabled make check. + +------------------------------------------------------------------- +Wed Feb 18 12:14:36 CET 2004 - kukuk@suse.de + +- Build against system pthread library, not pth. + +------------------------------------------------------------------- +Tue Feb 17 21:11:40 CET 2004 - hvogel@suse.de + +- update to version 1.1.91 +- fix autoconf quotations + +------------------------------------------------------------------- +Sat Jan 10 19:20:41 CET 2004 - adrian@suse.de + +- add %run_ldconfig to %postun + +------------------------------------------------------------------- +Sun Jul 27 16:12:54 CEST 2003 - poeml@suse.de + +- add libgcrypt-1.1.12-sexp-valgrind-error.patch from SLEC + +------------------------------------------------------------------- +Thu Apr 24 12:20:23 CEST 2003 - ro@suse.de + +- fix install_info --delete call and move from preun to postun + +------------------------------------------------------------------- +Mon Feb 10 22:51:26 CET 2003 - mmj@suse.de + +- Use %install_info macro [#23433] + +------------------------------------------------------------------- +Mon Feb 10 16:11:55 CET 2003 - mc@suse.de + +- switch to version 1.1.12 +- gcry_pk_sign, gcry_pk_verify and gcry_pk_encrypt can now handle an + optional pkcs1 flags parameter in the S-expression. A similar flag + may be passed to gcry_pk_decrypt but it is only syntactically + implemented. +- New convenience macro gcry_md_get_asnoid. +- There is now some real stuff in the manual. +- New algorithm: MD4 +- Implemented ciphertext stealing. +- Support for plain old DES +- Smaller bugs fixes and a few new OIDs. + +------------------------------------------------------------------- +Tue Jan 14 14:03:27 CET 2003 - nadvornik@suse.cz + +- fixed multi-line string literals + +------------------------------------------------------------------- +Thu Aug 1 23:51:10 CEST 2002 - poeml@suse.de + +- create package + diff --git a/libgcrypt.keyring b/libgcrypt.keyring new file mode 100644 index 0000000..dd3bb0b --- /dev/null +++ b/libgcrypt.keyring @@ -0,0 +1,86 @@ +-----BEGIN PGP PUBLIC KEY BLOCK----- + +mQGNBFjLuq4BDACnM7zNSIaVMAacTwjXa5TGYe13i6ilHe4VL0NShzrgzjcQg531 +3cRgiiiNA7OSOypMqVs73Jez6ZUctn2GVsHBrS/io9NcuC9pVwf8a61WlcEa+EtB +a3G7HlBmEWnwaUdAtWKNuAi9Xn+Ir7H2xEdksmmd5a0/QnL+sX705boVPF/tpYtb +LGpPxa78tNrtxDkSwy8Wmi0IADYLI5yI7/yUGeJd8RSCU/fLRKC9fG7YOZRq0tsO +MhVNWmtUjbG6e73Lu8LKnCZgs1/fC8hvPyARieSV5mdN8s1oWd7oYctfgL4uBleD +ItAA8GhjKejutzHN8Ei/APw6AiiSyEjnPg+cTX8OgvLGJWjks0H6mPZeB1v/kGyZ +hBS9vm540h2/MmlVN2ntiCK5TZGeSWpqddiqusfVXotMRpN4HeLKoZh4RAncaCbZ +F/S+YLeN+kMXY4k3Fqt1fjTX6veFCbthI9pDdHzU9LfUVNp9D/5ktC/tYMORMegV ++wSMxi9G2YWKJkMAEQEAAYkBzgQfAQgAOBYhBFuAxXVCmPDLVdjtarzvfilLCS4o +BQJYy8DdFwyAAZSlyaA8L+XKOwldjh/fcjz0YraxAgcAAAoJELzvfilLCS4oNgoL +/0+K1xIx8JW7Lk5M6bYCvNA4fdlEcwQIT4UidJFM9m+suxYFWIGfebvHpRlEuJTg +dBjkEit8uLAoJXU0BRkKTLrzTF+qDUE79Wfx/R+0nOgJ7aMykQOi0AvuwzMYz4dg +xIVS2Daou4DF7bh/KF8+fqrmq8P8W1ZrkuFDanMWpHeAPx1uj2skYbo7uPqFdvlJ +hlNHrcxlcCkjf1InAt0Xt5lMvEsCRUPf9xAH4mNEhs0lh9c+200YPRmtnLWAzc1K +ckLIC8Q+mUR3DjZDqBlDBEPegXkrI0+MlvRA+9AnAm4YPqTMUfpZ6ZOAWeFjC/6Z +QYxG/AdWGkb4WFindzklQfybEuiekP8vU07ACQwSwH8PYe0UCom1YrlRUjX7QLkn +ZLWoeZg8BZy9GTM1Ut7Q1Q2uTw6mxxISuef+RFgYOHjWwLpFWZpqC88xERl7o/iz +iERJRt/593IctbjO9wenWt2peIAwzR4nz7LqM6ZFTdRAETmcdSvYRhg2Qt8hUE47 +CbQkQW5kcmUgSGVpbmVja2UgKFJlbGVhc2UgU2lnbmluZyBLZXkpiQHUBBMBCAA+ +FiEEW4DFdUKY8MtV2O1qvO9+KUsJLigFAljLuq4CGwMFCRLMAwAFCwkIBwIGFQgJ +CgsCBBYCAwECHgECF4AACgkQvO9+KUsJLihC/QwAhCC+SEvcFLcutgZ8HfcCtoZs +IoVzZEy7DjqIvGgnTssD8HCLnIAHCDvnP7dJW3uMuLCdSqym3cjlEIiQMsaGywkl +fzJISAwJrGQdWSKRd535jXpEXQlXDKal/IwMKAUt0PZtlCc9S3gwixQryxdJ28lJ +6h2T9fVDr8ZswMmTAFG91uctfhjKOMgPt8UhSPGW484WsIsQgkbOvf+Kfswl0eHu +ywX+pKAB5ZQ/9GVC6Ug4xfrdiJL0azJTPnvjMY5JYp6/L9RURs5hP5AnHR2j/PPo +sAtsFCjmbRbOMiASzklnUJPbSz5kfLloDWZmrUScjbzmsXehGyt433JGyRhZJl4x +/jPbzKhaaAHsGd+fRao6vlLOwFywDDVMp6JuyK7UeUb7I8ekTbSkGFA+l2Oa3O6/ +Y7PYhq7hwwAFuZckYI98IpHNCG1fS9W07FyKdvQbK1PbF1JFRKfsUCWYMKqDnbqE +o5jivPEHZImw6iYhhXcyEYl8fjcb9T6/S+wOP7aviQGzBBABCAAdFiEElKXJoDwv +5co7CV2OH99yPPRitrEFAljLv5sACgkQH99yPPRitrFw4gv/XFMFN+/LHsn9hJOP +4rCwl1yUuxXuYmZgc0sRoY3EpeQkJVyKurQuqqKoy2VuoMiF0O1kAQmGoFtVPUk7 +b8hCoutqB5GyeyKcoLP+WINgVhB2gXg7TSp3MPLBKkgqvSDvPitgRxBqFb4LW8LJ +bDbfwGrzIvXfDV3WvsrHVPbc2fhlWdL8d+3AE6mFiXF3eTpgmV3ApSBQV12MkkCk +icLIPmp+ZxZON+OP52ZXkRtfMgOy4Oa/41agrViDAZdMOGeGkhPertQheQZgXzmo +GF5Wz498HPM80Kv35X91l3iGzL+icEtO+tWea2YscsZ6qpRe2lfVPHk3B+anlmCj +m4kM4cBd39xa4HHSVh/bRHbZNtgVr7slQCKxlHgQOGVI5vCxPCwEsgJ2KBk03Nk/ +IA9EKO+czfh3/bHW6uMbEqrYDCnt+hmzZrpKDSGcwS/KOhvMUIMlb7/8vDKum6mp +/8xAtVZ6IAxYZNt3qg7Y7aLRtzCTyqm8rJQrZPtRaQcgLoEimDMEX0PliRYJKwYB +BAHaRw8BAQdAz75Hlekc16JhhfI0MKdEVxLdkxhcMCO0ZG6WMBAmNpe0H1dlcm5l +ciBLb2NoIChkaXN0IHNpZ25pbmcgMjAyMCmImgQTFgoAQhYhBG2qbmSnbShAVxtJ +AlKIl7gmQDraBQJfQ+w1AhsDBQkShccRBQsJCAcCAyICAQYVCgkICwIEFgIDAQIe +BwIXgAAKCRBSiJe4JkA62nmuAP9uL/HOdB0gvwWrH+FpURJLs4bnaZaPIk9ARrU0 +EXRgJgD/YCGfHQXpIPT0ZaXuwJexK04Z+qMFR/bM1q1Leo5CjgaIbQQQEQsAHRYh +BIBhWHD1utaQMzaG0PKthaweQrNnBQJfQ/HmAAoJEPKthaweQrNnIZkA3jG6LcZv +V/URn8Y8OJqsyYa4C3NI4nN+OhEvYhgA4PHzMnALeXIpA2gblvjFIPJPAhDBAU37 +c5PA6+6IdQQQFggAHRYhBK6oTtzwGthsRwHIXGMROuhmWH0KBQJfQ/IlAAoJEGMR +OuhmWH0K1+MA/0uJ5AHcnSfIBEWHNJwwVVLGyrxAWtS2U+zeymp/UvlPAQDErCLZ +l0dBiPG3vlowFx5TNep7tanBs6ZJn8F1ao1tAIkBMwQQAQgAHRYhBNhpISPEBl3q +Xg86tSSbOdJPJeO2BQJfQ/OuAAoJECSbOdJPJeO2DVoH/0o9if66ph6FJrgr+A/W +HNVeHxmM5tUQhpL1wpRS70SKcsJgolf5CxO5iTQf3HlZe544xGbIU/aCTJsWw9zi +UE8KmhAtKV4eL/7oQ7xx4nxPnABLpudtM8A44nsM1x/XiYrJnnDm29QjYEGd2Hi8 +7npc7VWKzLoj+I/WcXquynJi5O9TUxW9Bknd1pjpxFkf8v+msjBzCD5VKJgr0CR8 +wA6peQBWeGZX2HacosMIZH4TfL0r0TFla6LJIkNBz9DyIm1yL4L8oRH0950hQljP +C7TM3L7aRpX+4Kph6llFz6g7MALGFP95kyJ6o+XED9ORuuQVZMBMIkNC0tXOu10V +bdqIdQQQFgoAHRYhBMHTS2khnkruwLocIeP9/yGORbcrBQJfQ/P8AAoJEOP9/yGO +Rbcr3lQBAMas8Vl3Hdl3g2I283lz1uHiGvlwcnk2TLeB+U4zIwC9AQCy0nnazVNt +VQPID1ZCMoaOX7AzOjaqQDLf4j+dVTxgBJgzBGCkgocWCSsGAQQB2kcPAQEHQJmd +fwp8jEN5P3eEjhQiWk6zQi8utvgOvYD57XmE+H8+tCBOaWliZSBZdXRha2EgKEdu +dVBHIFJlbGVhc2UgS2V5KYiaBBMWCgBCFiEErI4RW/c+LY1H+pkI6Y6bLRnGyL0F +AmCkgocCGwMFCQsNBpkFCwkIBwIDIgIBBhUKCQgLAgQWAgMBAh4HAheAAAoJEOmO +my0Zxsi9/4IA/1rvSr3MU+Sv4jhNDzD+CeC3gmHkPew6pi9VHEsEwdgmAQD2BtiX +7w1sJL/CBylGWv5jxj4345mP9YfZm0RsgzPjDIh1BBAWCAAdFiEEJJyzdxdQdF1c +3TI84mewUjZPAo0FAmFAQ54ACgkQ4mewUjZPAo1CiAD+KTT1UVdQTGHMyvHwZocS +QjU8xhcZrTet+dvvjrE5+4MA/RBdJPZgFevUKu68NEy0Lo+RbkeCtmQJ/c8v5ieF +vW0AiQEzBBABCAAdFiEEEkEkvTtIYq96CkLxALRevUynur4FAmFAQ7cACgkQALRe +vUynur4kaAgAolPR8TNWVS0vXMKrr0k0l2M/8QkZTaLZx1GT9Nx1yb4WJKY7ElPM +YkhGDxetvFBETx0pH/6R3jtj6Crmur+NKHVSRY+rCYpFPDn6ciIOryssRx2G4kCZ +t+nFB9JyDbBOZAR8DK4pN1mAxG/yLDt4oKcUQsP2xlEFum+phxyR8KyYCpkwKRxY +eK+6lfilQuveoUwp/Xx5wXPNUy6q4eOOovCW7gS7I7288NGHCa2ul8sD6vA9C4mM +4Zxaole9P9wwJe1zZFtCIy88zHM9vqv+YM9DxMCaW24+rUztr7eD4bCRdG+QlSh+ +7R/TaqSxY1eAAd1J5tma9CNJO73pTKU+/JhTBGFpSqMTCSskAwMCCAEBBwIDBF6X +D9NmUQDgiyYNbhs1DMJ14mIw812wY1HVx/4QWYWiBunhrvSFxVbzsjD7/Wv+v3bm +MPrL+M2DLyFiSewNmcS0JEdudVBHLmNvbSAoUmVsZWFzZSBTaWduaW5nIEtleSAy +MDIxKYiaBBMTCABCFiEEAvON/3Mf+XywOaHaVJ5pXpBboggFAmFpSqMCGwMFCQ9x +14oFCwkIBwIDIgIBBhUKCQgLAgQWAgMBAh4HAheAAAoJEFSeaV6QW6IITkoA/RYa +jaTl1eEBU/Gdm12o3jrI55N5xZK2XTqSx25clVyjAP0XwMW/Og5+ND1ri3bAqADV +WlBDUswz8wYxsb0C4kYBkoh1BBAWCgAdFiEEbapuZKdtKEBXG0kCUoiXuCZAOtoF +AmFpTvEACgkQUoiXuCZAOtrJQAEAh7YyykjAy/Qs1yC3ji8iBfIVnPXvblrIx3SR +RyDwRC8BAKtZbEuKTtPlgkLUgMleTcZJ/vEhJE+GvfQ9o5gWCqEFiHUEEBYKAB0W +IQTB00tpIZ5K7sC6HCHj/f8hjkW3KwUCYWlPWgAKCRDj/f8hjkW3Kx4eAQDp6aGS +N/fU4xLl8RSvQUVjVA+aCTrMQR3hRwqw8liF2wEA3O3ECxz6e1+DoItYoJBBLKLw +eiInsGZ/+h5XYrpXTgA= +=4+Sn +-----END PGP PUBLIC KEY BLOCK----- diff --git a/libgcrypt.spec b/libgcrypt.spec new file mode 100644 index 0000000..3056104 --- /dev/null +++ b/libgcrypt.spec @@ -0,0 +1,242 @@ +# +# spec file for package libgcrypt +# +# Copyright (c) 2025 SUSE LLC +# +# All modifications and additions to the file contributed by third parties +# remain the property of their copyright owners, unless otherwise agreed +# upon. The license for this file, and modifications and additions to the +# file, is the same license as for the pristine package itself (unless the +# license for the pristine package is not an Open Source License, in which +# case the license is the MIT License). An "Open Source License" is a +# license that conforms to the Open Source Definition (Version 1.9) +# published by the Open Source Initiative. + +# Please submit bugfixes or comments via https://bugs.opensuse.org/ +# + + +%define libsover 20 +%define libsoname %{name}%{libsover} +%define hmac_key orboDeJITITejsirpADONivirpUkvarP +Name: libgcrypt +Version: 1.11.0 +Release: 0 +Summary: The GNU Crypto Library +License: GPL-2.0-or-later AND LGPL-2.1-or-later AND GPL-3.0-or-later +Group: Development/Libraries/C and C++ +URL: https://gnupg.org/software/libgcrypt +Source: https://gnupg.org/ftp/gcrypt/libgcrypt/%{name}-%{version}.tar.bz2 +Source1: https://gnupg.org/ftp/gcrypt/libgcrypt/%{name}-%{version}.tar.bz2.sig +Source2: baselibs.conf +Source3: random.conf +Source4: hwf.deny +# https://www.gnupg.org/signature_key.html +Source5: https://gnupg.org/signature_key.asc#/%{name}.keyring +Source99: libgcrypt.changes +Patch1: libgcrypt-1.10.0-allow_FSM_same_state.patch +#PATCH-FIX-OPENSUSE Do not pull revision info from GIT when autoconf is run +Patch2: libgcrypt-nobetasuffix.patch +# FIPS patches: +#PATCH-FIX-SUSE bsc#1190700 FIPS: Provide a service-level indicator for PK +Patch100: libgcrypt-FIPS-SLI-pk.patch +#PATCH-FIX-SUSE bsc#1190700 FIPS: Check keylength in gcry_fips_indicator_kdf() +Patch101: libgcrypt-FIPS-SLI-kdf-leylength.patch +#PATCH-FIX-SUSE bsc#1190700 FIPS add indicators +Patch102: libgcrypt-FIPS-SLI-hash-mac.patch +#PATCH-FIX-SUSE bsc#1202117 FIPS: Get most of the entropy from rndjent_poll +Patch104: libgcrypt-FIPS-rndjent_poll.patch +#PATCH-FIX-SUSE bsc#1220896 FIPS: Replace the built-in jitter rng with standalone version +Patch105: libgcrypt-FIPS-jitter-standalone.patch +#PATCH-FIX-SUSE bsc#1220895 FIPS: Enforce the interpretation and use of jitter rng +Patch106: libgcrypt-FIPS-jitter-errorcodes.patch +#PATCH-FIX-SUSE bsc#1220893 FIPS: Use Jitter RNG for the whole length entropy buffer +Patch107: libgcrypt-FIPS-jitter-whole-entropy.patch +#PATCH-FIX-SUSE Remove not used rol64() definition after removing the built-in jitter rng +Patch108: libgcrypt-rol64-redefinition.patch +#PATCH-FIX-UPSTREAM jsc#PED-12227: SLI revamp and differentiate SHA1 in the service level indicator +Patch200: libgcrypt-fips-Introduce-an-internal-API-for-FIPS-service-indicator.patch +Patch201: libgcrypt-fips-Introduce-GCRYCTL_FIPS_SERVICE_INDICATOR-and-the-macro.patch +Patch202: libgcrypt-fips-kdf-Implement-new-FIPS-service-indicator-for-gcry_kdf_derive.patch +Patch203: libgcrypt-fips-md-Implement-new-FIPS-service-indicator-for-gcry_md_hash_.patch +Patch204: libgcrypt-fips-tests-Add-t-digest.patch +Patch205: libgcrypt-fips-Change-the-internal-API-for-new-FIPS-service-indicator.patch +Patch206: libgcrypt-fips-md-Implement-new-FIPS-service-indicator-for-gcry_md_open-API.patch +Patch207: libgcrypt-fips-tests-Add-tests-for-md_open-write-read-close-for-t-digest.patch +Patch208: libgcrypt-fips-mac-Implement-new-FIPS-service-indicator-for-gcry_mac_open.patch +Patch209: libgcrypt-fips-cipher-Implement-new-FIPS-service-indicator-for-cipher_open.patch +Patch210: libgcrypt-tests-fips-Add-gcry_mac_open-tests.patch +Patch211: libgcrypt-tests-fips-Rename-t-fips-service-ind.patch +Patch212: libgcrypt-tests-fips-Move-KDF-tests-to-t-fips-service-ind.patch +Patch213: libgcrypt-tests-fips-Add-gcry_cipher_open-tests.patch +Patch214: libgcrypt-fips-md-gcry_md_copy-should-care-about-FIPS-service-indicator.patch +Patch215: libgcrypt-fips-cipher-Implement-FIPS-service-indicator-for-gcry_pk_hash_-API.patch +Patch216: libgcrypt-fips-Introduce-GCRYCTL_FIPS_REJECT_NON_FIPS.patch +Patch217: libgcrypt-Fix-the-previous-change.patch +Patch218: libgcrypt-fips-Rejection-by-GCRYCTL_FIPS_REJECT_NON_FIPS-not-by-open-flags.patch +Patch219: libgcrypt-fips-cipher-Add-behavior-not-to-reject-but-mark-non-compliant.patch +Patch220: libgcrypt-fips-ecc-Add-rejecting-or-marking-for-gcry_pk_get_curve.patch +Patch221: libgcrypt-tests-Add-more-tests-to-tests-t-fips-service-ind.patch +Patch222: libgcrypt-fips-ecc-Check-DATA-in-gcry_pk_sign-verify-in-FIPS-mode.patch +Patch223: libgcrypt-fips-cipher-Fix-memory-leak-for-gcry_pk_hash_sign.patch +Patch224: libgcrypt-build-Improve-__thread-specifier-check.patch +Patch225: libgcrypt-cipher-Check-and-mark-non-compliant-cipher-modes-in-the-SLI.patch +Patch226: libgcrypt-cipher-Rename-_gcry_cipher_is_mode_fips_compliant.patch +Patch227: libgcrypt-cipher-Don-t-differentiate-GCRY_CIPHER_MODE_CMAC-in-FIPS-mode.patch +Patch228: libgcrypt-cipher-rsa-Mark-reject-SHA1-unknown-with-RSA-signature-generation.patch +Patch229: libgcrypt-md-Fix-gcry_md_algo_info-to-mark-reject-under-FIPS-mode.patch +Patch230: libgcrypt-md-Use-check_digest_algo_spec-in-_gcry_md_selftest.patch +Patch231: libgcrypt-tests-Update-t-fips-service-ind-using-GCRY_MD_SHA256-for-KDF-tests.patch +Patch232: libgcrypt-fips-cipher-Do-the-computation-when-marking-non-compliant.patch +Patch233: libgcrypt-tests-Allow-tests-with-USE_RSA.patch +Patch234: libgcrypt-cipher-Add-KAT-for-non-rfc6979-ECDSA-with-fixed-k.patch +Patch235: libgcrypt-cipher-Differentiate-use-of-label-K-in-the-SLI.patch +Patch236: libgcrypt-cipher-Differentiate-igninvflag-in-the-SLI.patch +Patch237: libgcrypt-cipher-Differentiate-no-blinding-flag-in-the-SLI.patch +Patch238: libgcrypt-fips-cipher-Add-GCRY_FIPS_FLAG_REJECT_PK_FLAGS.patch +Patch239: libgcrypt-cipher-ecc-Fix-for-supplied-K.patch +Patch240: libgcrypt-cipher-visibility-Differentiate-use-of-random-override-in-the-SLI.patch +Patch241: libgcrypt-cipher-fips-Fix-for-random-override.patch +Patch243: libgcrypt-md-Make-SHA-1-non-FIPS-internally-for-1.12-API.patch +Patch244: libgcrypt-fips-Fix-GCRY_FIPS_FLAG_REJECT_MD.patch +Patch245: libgcrypt-doc-Add-about-GCRYCTL_FIPS_SERVICE_INDICATOR.patch +Patch246: libgcrypt-doc-Fix-syntax-error.patch + +BuildRequires: automake >= 1.14 +BuildRequires: libgpg-error-devel >= 1.49 +BuildRequires: libtool +BuildRequires: makeinfo +BuildRequires: pkgconfig +%{?suse_build_hwcaps_libs} + +%description +Libgcrypt is a general purpose library of cryptographic building +blocks. It is originally based on code used by GnuPG. It does not +provide any implementation of OpenPGP or other protocols. Thorough +understanding of applied cryptography is required to use Libgcrypt. + +%package -n %{libsoname} +Summary: The GNU Crypto Library +License: GPL-2.0-or-later AND LGPL-2.1-or-later +Group: System/Libraries +BuildRequires: jitterentropy-devel >= 3.4.0 +Requires: libjitterentropy3 >= 3.4.0 +Provides: %{libsoname}-hmac = %{version}-%{release} +Obsoletes: %{libsoname}-hmac < %{version}-%{release} + +%description -n %{libsoname} +Libgcrypt is a general purpose crypto library based on the code used in +GnuPG (alpha version). + +%package devel +Summary: The GNU Crypto Library +License: GFDL-1.1-only AND GPL-2.0-or-later AND LGPL-2.1-or-later AND MIT +Group: Development/Libraries/C and C++ +Requires: %{libsoname} = %{version} +Requires: glibc-devel +Requires: jitterentropy-devel >= 3.4.0 +Requires: libgpg-error-devel >= 1.49 + +%description devel +Libgcrypt is a general purpose library of cryptographic building +blocks. It is originally based on code used by GnuPG. It does not +provide any implementation of OpenPGP or other protocols. Thorough +understanding of applied cryptography is required to use Libgcrypt. + +This package contains needed files to compile and link against the +library. + +%prep +%autosetup -p1 + +# Rename the internal .hmac file to include the so library version +sed -i "s/libgcrypt\.so\.hmac/\.libgcrypt\.so\.%{libsover}\.hmac/g" src/Makefile.am src/Makefile.in + +# Replace the built-in jitter rng with the standalone version [bsc#1220896] +find . -type f -name "jitterentropy*" -print -delete + +%build +export PUBKEYS="dsa elgamal rsa ecc" +export CIPHERS="arcfour blowfish cast5 des aes twofish serpent rfc2268 seed camellia idea salsa20 gost28147 chacha20 sm4 aria" +export DIGESTS="crc gostr3411-94 md4 md5 rmd160 sha1 sha256 sha512 sha3 tiger whirlpool stribog blake2 sm3" +export KDFS="s2k pkdf2 scrypt" + +autoreconf -fi +date=$(date -u '+%%Y-%%m-%%dT%%H:%%M+0000' -r %{SOURCE99}) +sed -e "s,BUILD_TIMESTAMP=.*,BUILD_TIMESTAMP=$date," -i configure +export CFLAGS="%{optflags} $(getconf LFS_CFLAGS)" +%configure \ + --with-fips-module-version="Libgcrypt version %{version}-%{release}" \ + --enable-hmac-binary-check="%{hmac_key}" \ + --enable-ciphers="$CIPHERS" \ + --enable-pubkey-ciphers="$PUBKEYS" \ + --enable-digests="$DIGESTS" \ + --enable-kdfs="$KDFS" \ + --enable-noexecstack \ + --disable-static \ +%ifarch %{sparc} + --disable-asm \ +%endif + --enable-random=getentropy \ + --enable-jent-support \ + %{nil} + +%make_build + +%check +make -k check +# run the regression tests also in FIPS mode +LIBGCRYPT_FORCE_FIPS_MODE=1 make -k check + +%install +%make_install + +# this is a hack that re-defines the __spec_install_post macro +# for a simple reason: the macro strips the binaries and thereby +# invalidates a HMAC that may have been created earlier. +# solution: create the hashes _after_ the macro runs. +%define libpath %{buildroot}%{_libdir}/libgcrypt.so.%{libsover}.?.? +%define __spec_install_post \ + %{?__debug_package:%{__debug_install_post}} \ + %{__arch_install_post} \ + %{__os_install_post} \ + cd src \ + sed -i -e 's|FILE=.*|FILE=\\\$1|' gen-note-integrity.sh \ + READELF=readelf AWK=awk ECHO_N="-n" bash gen-note-integrity.sh %{libpath} > %{libpath}.hmac \ + objcopy --update-section .note.fdo.integrity=%{libpath}.hmac %{libpath} %{libpath}.new \ + mv -f %{libpath}.new %{libpath} \ + rm -f %{libpath}.hmac \ +%{nil} + +rm %{buildroot}%{_libdir}/%{name}.la + +# Create /etc/gcrypt directory and install random.conf +mkdir -p -m 0755 %{buildroot}%{_sysconfdir}/gcrypt +install -m 644 %{SOURCE3} %{buildroot}%{_sysconfdir}/gcrypt/random.conf +install -m 644 %{SOURCE4} %{buildroot}%{_sysconfdir}/gcrypt/hwf.deny + +%post -n %{libsoname} -p /sbin/ldconfig +%postun -n %{libsoname} -p /sbin/ldconfig + +%files -n %{libsoname} +%license COPYING COPYING.LIB LICENSES +%doc AUTHORS ChangeLog NEWS README THANKS TODO +%{_libdir}/%{name}.so.* +%dir %{_sysconfdir}/gcrypt +%config(noreplace) %{_sysconfdir}/gcrypt/random.conf +%config(noreplace) %{_sysconfdir}/gcrypt/hwf.deny + +%files devel +%license COPYING COPYING.LIB LICENSES +%{_bindir}/dumpsexp +%{_bindir}/hmac256 +%{_bindir}/mpicalc +%{_bindir}/%{name}-config +%{_libdir}/%{name}.so +%{_libdir}/pkgconfig/libgcrypt.pc +%{_datadir}/aclocal/%{name}.m4 +%{_includedir}/gcrypt*.h +%{_infodir}/gcrypt.info*%{ext_info}* +%{_mandir}/man1/* + +%changelog diff --git a/random.conf b/random.conf new file mode 100644 index 0000000..378ba78 --- /dev/null +++ b/random.conf @@ -0,0 +1,9 @@ +# This file can be used to globally change parameters of +# the random generator. Supported options are: + +# Always use the non-blocking /dev/urandom or the respective +# system call instead of the blocking /dev/random. +# only-urandom + +# Disable the use of the jitter based entropy generator. +# disable-jent -- 2.51.1 From 06032641d5aa61781333cfb58e277bffa01f43166bb12d1c2acd7ffe758aed61 Mon Sep 17 00:00:00 2001 From: Pedro Monreal Gonzalez Date: Tue, 6 May 2025 07:37:32 +0000 Subject: [PATCH 4/8] - CSHAKE basic regression test failure in s390x [bsc#1242419 * Disable SHA3 s390x acceleration for CSHAKE [rC2486d9b5ae01] * Add libgcrypt-Disable-SHA3-s390x-acceleration-for-CSHAKE.patch OBS-URL: https://build.opensuse.org/package/show/devel:libraries:c_c++/libgcrypt?expand=0&rev=188 --- .gitattributes | 23 + .gitignore | 1 + baselibs.conf | 8 + hwf.deny | 34 + libgcrypt-1.10.0-allow_FSM_same_state.patch | 15 + libgcrypt-1.10.3.tar.bz2 | 3 + libgcrypt-1.10.3.tar.bz2.sig | Bin 0 -> 238 bytes libgcrypt-1.11.0.tar.bz2 | 3 + libgcrypt-1.11.0.tar.bz2.sig | Bin 0 -> 119 bytes ...poly1305-Optimized-chacha20-poly1305.patch | 1993 +++++++++++++++++ ...e-SHA3-s390x-acceleration-for-CSHAKE.patch | 61 + libgcrypt-FIPS-SLI-hash-mac.patch | 172 ++ libgcrypt-FIPS-SLI-kdf-leylength.patch | 60 + libgcrypt-FIPS-SLI-pk.patch | 177 ++ libgcrypt-FIPS-jitter-errorcodes.patch | 16 + libgcrypt-FIPS-jitter-standalone.patch | 183 ++ libgcrypt-FIPS-jitter-whole-entropy.patch | 41 + libgcrypt-FIPS-rndjent_poll.patch | 114 + libgcrypt-Fix-the-previous-change.patch | 45 + ...ild-Improve-__thread-specifier-check.patch | 41 + ...T-for-non-rfc6979-ECDSA-with-fixed-k.patch | 94 + ...on-compliant-cipher-modes-in-the-SLI.patch | 236 ++ ...-Differentiate-igninvflag-in-the-SLI.patch | 40 + ...rentiate-no-blinding-flag-in-the-SLI.patch | 70 + ...ferentiate-use-of-label-K-in-the-SLI.patch | 139 ++ ...e-GCRY_CIPHER_MODE_CMAC-in-FIPS-mode.patch | 98 + ...-_gcry_cipher_is_mode_fips_compliant.patch | 64 + libgcrypt-cipher-ecc-Fix-for-supplied-K.patch | 88 + ...-cipher-fips-Fix-for-random-override.patch | 83 + ...nknown-with-RSA-signature-generation.patch | 445 ++++ ...te-use-of-random-override-in-the-SLI.patch | 107 + ...about-GCRYCTL_FIPS_SERVICE_INDICATOR.patch | 66 + libgcrypt-doc-Fix-syntax-error.patch | 31 + ...l-API-for-new-FIPS-service-indicator.patch | 140 ++ ...pt-fips-Fix-GCRY_FIPS_FLAG_REJECT_MD.patch | 42 + ...troduce-GCRYCTL_FIPS_REJECT_NON_FIPS.patch | 261 +++ ...FIPS_SERVICE_INDICATOR-and-the-macro.patch | 101 + ...ernal-API-for-FIPS-service-indicator.patch | 332 +++ ...PS_REJECT_NON_FIPS-not-by-open-flags.patch | 498 ++++ ...r-Add-GCRY_FIPS_FLAG_REJECT_PK_FLAGS.patch | 80 + ...not-to-reject-but-mark-non-compliant.patch | 300 +++ ...mputation-when-marking-non-compliant.patch | 160 ++ ...ix-memory-leak-for-gcry_pk_hash_sign.patch | 76 + ...vice-indicator-for-gcry_pk_hash_-API.patch | 360 +++ ...PS-service-indicator-for-cipher_open.patch | 122 + ...ing-or-marking-for-gcry_pk_get_curve.patch | 43 + ...-in-gcry_pk_sign-verify-in-FIPS-mode.patch | 282 +++ ...ervice-indicator-for-gcry_kdf_derive.patch | 265 +++ ...-service-indicator-for-gcry_mac_open.patch | 115 + ...-service-indicator-for-gcry_md_hash_.patch | 188 ++ ...rvice-indicator-for-gcry_md_open-API.patch | 298 +++ ...ld-care-about-FIPS-service-indicator.patch | 85 + libgcrypt-fips-tests-Add-t-digest.patch | 243 ++ ...d_open-write-read-close-for-t-digest.patch | 172 ++ libgcrypt-jitterentropy-3.4.0.patch | 618 +++++ ..._info-to-mark-reject-under-FIPS-mode.patch | 82 + ...A-1-non-FIPS-internally-for-1.12-API.patch | 154 ++ ...igest_algo_spec-in-_gcry_md_selftest.patch | 74 + libgcrypt-no-deprecated-grep-alias.patch | 35 + libgcrypt-nobetasuffix.patch | 24 + ...e-P10-assembly-with-ENABLE_FORCE_SOF.patch | 76 + libgcrypt-rol64-redefinition.patch | 16 + ...re-tests-to-tests-t-fips-service-ind.patch | 382 ++++ ...crypt-tests-Allow-tests-with-USE_RSA.patch | 44 + ...d-using-GCRY_MD_SHA256-for-KDF-tests.patch | 106 + ...ests-fips-Add-gcry_cipher_open-tests.patch | 199 ++ ...t-tests-fips-Add-gcry_mac_open-tests.patch | 206 ++ ...Move-KDF-tests-to-t-fips-service-ind.patch | 375 ++++ ...tests-fips-Rename-t-fips-service-ind.patch | 60 + libgcrypt.changes | 1926 ++++++++++++++++ libgcrypt.keyring | 86 + libgcrypt.spec | 244 ++ random.conf | 9 + 73 files changed, 13430 insertions(+) create mode 100644 .gitattributes create mode 100644 .gitignore create mode 100644 baselibs.conf create mode 100644 hwf.deny create mode 100644 libgcrypt-1.10.0-allow_FSM_same_state.patch create mode 100644 libgcrypt-1.10.3.tar.bz2 create mode 100644 libgcrypt-1.10.3.tar.bz2.sig create mode 100644 libgcrypt-1.11.0.tar.bz2 create mode 100644 libgcrypt-1.11.0.tar.bz2.sig create mode 100644 libgcrypt-Chacha20-poly1305-Optimized-chacha20-poly1305.patch create mode 100644 libgcrypt-Disable-SHA3-s390x-acceleration-for-CSHAKE.patch create mode 100644 libgcrypt-FIPS-SLI-hash-mac.patch create mode 100644 libgcrypt-FIPS-SLI-kdf-leylength.patch create mode 100644 libgcrypt-FIPS-SLI-pk.patch create mode 100644 libgcrypt-FIPS-jitter-errorcodes.patch create mode 100644 libgcrypt-FIPS-jitter-standalone.patch create mode 100644 libgcrypt-FIPS-jitter-whole-entropy.patch create mode 100644 libgcrypt-FIPS-rndjent_poll.patch create mode 100644 libgcrypt-Fix-the-previous-change.patch create mode 100644 libgcrypt-build-Improve-__thread-specifier-check.patch create mode 100644 libgcrypt-cipher-Add-KAT-for-non-rfc6979-ECDSA-with-fixed-k.patch create mode 100644 libgcrypt-cipher-Check-and-mark-non-compliant-cipher-modes-in-the-SLI.patch create mode 100644 libgcrypt-cipher-Differentiate-igninvflag-in-the-SLI.patch create mode 100644 libgcrypt-cipher-Differentiate-no-blinding-flag-in-the-SLI.patch create mode 100644 libgcrypt-cipher-Differentiate-use-of-label-K-in-the-SLI.patch create mode 100644 libgcrypt-cipher-Don-t-differentiate-GCRY_CIPHER_MODE_CMAC-in-FIPS-mode.patch create mode 100644 libgcrypt-cipher-Rename-_gcry_cipher_is_mode_fips_compliant.patch create mode 100644 libgcrypt-cipher-ecc-Fix-for-supplied-K.patch create mode 100644 libgcrypt-cipher-fips-Fix-for-random-override.patch create mode 100644 libgcrypt-cipher-rsa-Mark-reject-SHA1-unknown-with-RSA-signature-generation.patch create mode 100644 libgcrypt-cipher-visibility-Differentiate-use-of-random-override-in-the-SLI.patch create mode 100644 libgcrypt-doc-Add-about-GCRYCTL_FIPS_SERVICE_INDICATOR.patch create mode 100644 libgcrypt-doc-Fix-syntax-error.patch create mode 100644 libgcrypt-fips-Change-the-internal-API-for-new-FIPS-service-indicator.patch create mode 100644 libgcrypt-fips-Fix-GCRY_FIPS_FLAG_REJECT_MD.patch create mode 100644 libgcrypt-fips-Introduce-GCRYCTL_FIPS_REJECT_NON_FIPS.patch create mode 100644 libgcrypt-fips-Introduce-GCRYCTL_FIPS_SERVICE_INDICATOR-and-the-macro.patch create mode 100644 libgcrypt-fips-Introduce-an-internal-API-for-FIPS-service-indicator.patch create mode 100644 libgcrypt-fips-Rejection-by-GCRYCTL_FIPS_REJECT_NON_FIPS-not-by-open-flags.patch create mode 100644 libgcrypt-fips-cipher-Add-GCRY_FIPS_FLAG_REJECT_PK_FLAGS.patch create mode 100644 libgcrypt-fips-cipher-Add-behavior-not-to-reject-but-mark-non-compliant.patch create mode 100644 libgcrypt-fips-cipher-Do-the-computation-when-marking-non-compliant.patch create mode 100644 libgcrypt-fips-cipher-Fix-memory-leak-for-gcry_pk_hash_sign.patch create mode 100644 libgcrypt-fips-cipher-Implement-FIPS-service-indicator-for-gcry_pk_hash_-API.patch create mode 100644 libgcrypt-fips-cipher-Implement-new-FIPS-service-indicator-for-cipher_open.patch create mode 100644 libgcrypt-fips-ecc-Add-rejecting-or-marking-for-gcry_pk_get_curve.patch create mode 100644 libgcrypt-fips-ecc-Check-DATA-in-gcry_pk_sign-verify-in-FIPS-mode.patch create mode 100644 libgcrypt-fips-kdf-Implement-new-FIPS-service-indicator-for-gcry_kdf_derive.patch create mode 100644 libgcrypt-fips-mac-Implement-new-FIPS-service-indicator-for-gcry_mac_open.patch create mode 100644 libgcrypt-fips-md-Implement-new-FIPS-service-indicator-for-gcry_md_hash_.patch create mode 100644 libgcrypt-fips-md-Implement-new-FIPS-service-indicator-for-gcry_md_open-API.patch create mode 100644 libgcrypt-fips-md-gcry_md_copy-should-care-about-FIPS-service-indicator.patch create mode 100644 libgcrypt-fips-tests-Add-t-digest.patch create mode 100644 libgcrypt-fips-tests-Add-tests-for-md_open-write-read-close-for-t-digest.patch create mode 100644 libgcrypt-jitterentropy-3.4.0.patch create mode 100644 libgcrypt-md-Fix-gcry_md_algo_info-to-mark-reject-under-FIPS-mode.patch create mode 100644 libgcrypt-md-Make-SHA-1-non-FIPS-internally-for-1.12-API.patch create mode 100644 libgcrypt-md-Use-check_digest_algo_spec-in-_gcry_md_selftest.patch create mode 100644 libgcrypt-no-deprecated-grep-alias.patch create mode 100644 libgcrypt-nobetasuffix.patch create mode 100644 libgcrypt-ppc-enable-P10-assembly-with-ENABLE_FORCE_SOF.patch create mode 100644 libgcrypt-rol64-redefinition.patch create mode 100644 libgcrypt-tests-Add-more-tests-to-tests-t-fips-service-ind.patch create mode 100644 libgcrypt-tests-Allow-tests-with-USE_RSA.patch create mode 100644 libgcrypt-tests-Update-t-fips-service-ind-using-GCRY_MD_SHA256-for-KDF-tests.patch create mode 100644 libgcrypt-tests-fips-Add-gcry_cipher_open-tests.patch create mode 100644 libgcrypt-tests-fips-Add-gcry_mac_open-tests.patch create mode 100644 libgcrypt-tests-fips-Move-KDF-tests-to-t-fips-service-ind.patch create mode 100644 libgcrypt-tests-fips-Rename-t-fips-service-ind.patch create mode 100644 libgcrypt.changes create mode 100644 libgcrypt.keyring create mode 100644 libgcrypt.spec create mode 100644 random.conf diff --git a/.gitattributes b/.gitattributes new file mode 100644 index 0000000..9b03811 --- /dev/null +++ b/.gitattributes @@ -0,0 +1,23 @@ +## Default LFS +*.7z filter=lfs diff=lfs merge=lfs -text +*.bsp filter=lfs diff=lfs merge=lfs -text +*.bz2 filter=lfs diff=lfs merge=lfs -text +*.gem filter=lfs diff=lfs merge=lfs -text +*.gz filter=lfs diff=lfs merge=lfs -text +*.jar filter=lfs diff=lfs merge=lfs -text +*.lz filter=lfs diff=lfs merge=lfs -text +*.lzma filter=lfs diff=lfs merge=lfs -text +*.obscpio filter=lfs diff=lfs merge=lfs -text +*.oxt filter=lfs diff=lfs merge=lfs -text +*.pdf filter=lfs diff=lfs merge=lfs -text +*.png filter=lfs diff=lfs merge=lfs -text +*.rpm filter=lfs diff=lfs merge=lfs -text +*.tbz filter=lfs diff=lfs merge=lfs -text +*.tbz2 filter=lfs diff=lfs merge=lfs -text +*.tgz filter=lfs diff=lfs merge=lfs -text +*.ttf filter=lfs diff=lfs merge=lfs -text +*.txz filter=lfs diff=lfs merge=lfs -text +*.whl filter=lfs diff=lfs merge=lfs -text +*.xz filter=lfs diff=lfs merge=lfs -text +*.zip filter=lfs diff=lfs merge=lfs -text +*.zst filter=lfs diff=lfs merge=lfs -text diff --git a/.gitignore b/.gitignore new file mode 100644 index 0000000..57affb6 --- /dev/null +++ b/.gitignore @@ -0,0 +1 @@ +.osc diff --git a/baselibs.conf b/baselibs.conf new file mode 100644 index 0000000..a018a0a --- /dev/null +++ b/baselibs.conf @@ -0,0 +1,8 @@ +libgcrypt20 + provides "libgcrypt- = " + obsoletes "libgcrypt- <= " + provides "libgcrypt20-hmac- = -%release" + obsoletes "libgcrypt20-hmac- < -%release" +libgcrypt-devel + requires -libgcrypt- + requires "libgcrypt20- = " diff --git a/hwf.deny b/hwf.deny new file mode 100644 index 0000000..2236468 --- /dev/null +++ b/hwf.deny @@ -0,0 +1,34 @@ +# This file can be used to globally disable the use of hardware +# based optimizations. Supported options are: +# padlock-rng +# padlock-aes +# padlock-sha +# padlock-mmul +# intel-cpu +# intel-fast-shld +# intel-bmi2 +# intel-ssse3 +# intel-sse4.1 +# intel-pclmul +# intel-aesni +# intel-rdrand +# intel-avx +# intel-avx2 +# intel-fast-vpgather +# intel-rdtsc +# intel-shaext +# intel-vaes-vpclmul +# arm-neon +# arm-aes +# arm-sha1 +# arm-sha2 +# arm-pmull +# ppc-vcrypto +# ppc-arch_3_00 +# ppc-arch_2_07 +# ppc-arch_3_10 +# s390x-msa +# s390x-msa-4 +# s390x-msa-8 +# s390x-msa-9 +# s390x-vx diff --git a/libgcrypt-1.10.0-allow_FSM_same_state.patch b/libgcrypt-1.10.0-allow_FSM_same_state.patch new file mode 100644 index 0000000..843cfea --- /dev/null +++ b/libgcrypt-1.10.0-allow_FSM_same_state.patch @@ -0,0 +1,15 @@ +Index: libgcrypt-1.10.0/src/fips.c +=================================================================== +--- libgcrypt-1.10.0.orig/src/fips.c ++++ libgcrypt-1.10.0/src/fips.c +@@ -890,6 +890,10 @@ fips_new_state (enum module_states new_s + + } + ++ /* Allow a transition to the current state */ ++ if (current_state == new_state) ++ ok = 1; ++ + if (ok) + { + current_state = new_state; diff --git a/libgcrypt-1.10.3.tar.bz2 b/libgcrypt-1.10.3.tar.bz2 new file mode 100644 index 0000000..653803f --- /dev/null +++ b/libgcrypt-1.10.3.tar.bz2 @@ -0,0 +1,3 @@ +version https://git-lfs.github.com/spec/v1 +oid sha256:8b0870897ac5ac67ded568dcfadf45969cfa8a6beb0fd60af2a9eadc2a3272aa +size 3783827 diff --git a/libgcrypt-1.10.3.tar.bz2.sig b/libgcrypt-1.10.3.tar.bz2.sig new file mode 100644 index 0000000000000000000000000000000000000000000000000000000000000000..4172518bc29eafb0304aa2c7def555b970a6accea442a7542087b98c44485773 GIT binary patch literal 238 zcmeAuWnmEGV2~A4WXWBXm$E!p!y#PSlPRcU`VKV*t6Qv0sliEW8MrtFU?N}p82-vF z=ITAZ*qv<_(;dOxrp<8yN$DSFdR>!gz3<7nXwGD1Muyiq%7Ht6>~>#&|Ibh5V-ok6 zm#e%* literal 0 HcmV?d00001 diff --git a/libgcrypt-1.11.0.tar.bz2 b/libgcrypt-1.11.0.tar.bz2 new file mode 100644 index 0000000..28d1068 --- /dev/null +++ b/libgcrypt-1.11.0.tar.bz2 @@ -0,0 +1,3 @@ +version https://git-lfs.github.com/spec/v1 +oid sha256:09120c9867ce7f2081d6aaa1775386b98c2f2f246135761aae47d81f58685b9c +size 4180345 diff --git a/libgcrypt-1.11.0.tar.bz2.sig b/libgcrypt-1.11.0.tar.bz2.sig new file mode 100644 index 0000000000000000000000000000000000000000000000000000000000000000..2debe948a9ffbbc9c835efae5cce0c65517df124ea67ba4cc04d1dffdd7b3160 GIT binary patch literal 119 zcmeAuWnmEGV2~A4WXWBXm$E!p!y#PSlPRcU`VKV*t6Qv0X+=xZ7`QkEU?T178UE=O z)|M}6Y-XM7H2JWvsFP0?XX&fr%U>#e4G(K{b;T<%GJNLLSKO|_Z@vBphsk!en!WkH T(k44uvO>;;f4NZp`vWfkiCryG literal 0 HcmV?d00001 diff --git a/libgcrypt-Chacha20-poly1305-Optimized-chacha20-poly1305.patch b/libgcrypt-Chacha20-poly1305-Optimized-chacha20-poly1305.patch new file mode 100644 index 0000000..5877fee --- /dev/null +++ b/libgcrypt-Chacha20-poly1305-Optimized-chacha20-poly1305.patch @@ -0,0 +1,1993 @@ +commit 88fe7ac33eb4cb4dff76a5cc7fca50da5fb0ee3a +Author: Danny Tsen +Date: Sun Jun 12 21:30:19 2022 +0300 + + Chacha20 poly1305 Optimized chacha20 poly1305 for P10 operation + + * configure.ac: Added chacha20 and poly1305 assembly implementations. + * cipher/chacha20-p10le-8x.s: (New) - support 8 blocks (512 bytes) + unrolling. + * cipher/poly1305-p10le.s: (New) - support 4 blocks (128 bytes) + unrolling. + * cipher/Makefile.am: Added new chacha20 and poly1305 files. + * cipher/chacha20.c: Added PPC p10 le support for 8x chacha20. + * cipher/poly1305.c: Added PPC p10 le support for 4x poly1305. + * cipher/poly1305-internal.h: Added PPC p10 le support for poly1305. + --- + + GnuPG-bug-id: 6006 + Signed-off-by: Danny Tsen + [jk: cosmetic changes to C code] + [jk: fix building on ppc64be] + Signed-off-by: Jussi Kivilinna + +Index: libgcrypt-1.10.2/cipher/Makefile.am +=================================================================== +--- libgcrypt-1.10.2.orig/cipher/Makefile.am ++++ libgcrypt-1.10.2/cipher/Makefile.am +@@ -83,6 +83,7 @@ EXTRA_libcipher_la_SOURCES = \ + chacha20.c chacha20-amd64-ssse3.S chacha20-amd64-avx2.S \ + chacha20-armv7-neon.S chacha20-aarch64.S \ + chacha20-ppc.c chacha20-s390x.S \ ++ chacha20-p10le-8x.s \ + cipher-gcm-ppc.c cipher-gcm-intel-pclmul.c cipher-gcm-armv7-neon.S \ + cipher-gcm-armv8-aarch32-ce.S cipher-gcm-armv8-aarch64-ce.S \ + crc.c crc-intel-pclmul.c crc-armv8-ce.c \ +@@ -99,6 +100,7 @@ EXTRA_libcipher_la_SOURCES = \ + md4.c \ + md5.c \ + poly1305-s390x.S \ ++ poly1305-p10le.s \ + rijndael.c rijndael-internal.h rijndael-tables.h \ + rijndael-aesni.c rijndael-padlock.c \ + rijndael-amd64.S rijndael-arm.S \ +Index: libgcrypt-1.10.2/cipher/chacha20-p10le-8x.s +=================================================================== +--- /dev/null ++++ libgcrypt-1.10.2/cipher/chacha20-p10le-8x.s +@@ -0,0 +1,864 @@ ++# Copyright 2021- IBM Inc. All rights reserved ++# ++# This file is part of Libgcrypt. ++# ++# Libgcrypt is free software; you can redistribute it and/or modify ++# it under the terms of the GNU Lesser General Public License as ++# published by the Free Software Foundation; either version 2.1 of ++# the License, or (at your option) any later version. ++# ++# Libgcrypt 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 Lesser General Public License for more details. ++# ++# You should have received a copy of the GNU Lesser General Public ++# License along with this program; if not, see . ++# ++#=================================================================================== ++# Written by Danny Tsen ++# ++# This function handles multiple 64-byte block data length ++# and the length should be more than 512 bytes. ++# ++# unsigned int _gcry_chacha20_p10le_8x(u32 *state, byte *dst, const byte *src, size_t len); ++# ++# r1 - top of the stack ++# r3 to r10 input parameters ++# r3 - out ++# r4 - inp ++# r5 - len ++# r6 - key[8] ++# r7 - counter[4] ++# ++# do rounds, 8 quarter rounds ++# 1. a += b; d ^= a; d <<<= 16; ++# 2. c += d; b ^= c; b <<<= 12; ++# 3. a += b; d ^= a; d <<<= 8; ++# 4. c += d; b ^= c; b <<<= 7 ++# ++# row1 = (row1 + row2), row4 = row1 xor row4, row4 rotate each word by 16 ++# row3 = (row3 + row4), row2 = row3 xor row2, row2 rotate each word by 12 ++# row1 = (row1 + row2), row4 = row1 xor row4, row4 rotate each word by 8 ++# row3 = (row3 + row4), row2 = row3 xor row2, row2 rotate each word by 7 ++# ++# 4 blocks (a b c d) ++# ++# a0 b0 c0 d0 ++# a1 b1 c1 d1 ++# ... ++# a4 b4 c4 d4 ++# ... ++# a8 b8 c8 d8 ++# ... ++# a12 b12 c12 d12 ++# a13 ... ++# a14 ... ++# a15 b15 c15 d15 ++# ++# Column round (v0, v4, v8, v12, v1, v5, v9, v13, v2, v6, v10, v14, v3, v7, v11, v15) ++# Diagnal round (v0, v5, v10, v15, v1, v6, v11, v12, v2, v7, v8, v13, v3, v4, v9, v14) ++# ++.text ++ ++.macro QT_loop_8x ++ # QR(v0, v4, v8, v12, v1, v5, v9, v13, v2, v6, v10, v14, v3, v7, v11, v15) ++ xxlor 0, 32+25, 32+25 ++ xxlor 32+25, 20, 20 ++ vadduwm 0, 0, 4 ++ vadduwm 1, 1, 5 ++ vadduwm 2, 2, 6 ++ vadduwm 3, 3, 7 ++ vadduwm 16, 16, 20 ++ vadduwm 17, 17, 21 ++ vadduwm 18, 18, 22 ++ vadduwm 19, 19, 23 ++ ++ vpermxor 12, 12, 0, 25 ++ vpermxor 13, 13, 1, 25 ++ vpermxor 14, 14, 2, 25 ++ vpermxor 15, 15, 3, 25 ++ vpermxor 28, 28, 16, 25 ++ vpermxor 29, 29, 17, 25 ++ vpermxor 30, 30, 18, 25 ++ vpermxor 31, 31, 19, 25 ++ xxlor 32+25, 0, 0 ++ vadduwm 8, 8, 12 ++ vadduwm 9, 9, 13 ++ vadduwm 10, 10, 14 ++ vadduwm 11, 11, 15 ++ vadduwm 24, 24, 28 ++ vadduwm 25, 25, 29 ++ vadduwm 26, 26, 30 ++ vadduwm 27, 27, 31 ++ vxor 4, 4, 8 ++ vxor 5, 5, 9 ++ vxor 6, 6, 10 ++ vxor 7, 7, 11 ++ vxor 20, 20, 24 ++ vxor 21, 21, 25 ++ vxor 22, 22, 26 ++ vxor 23, 23, 27 ++ ++ xxlor 0, 32+25, 32+25 ++ xxlor 32+25, 21, 21 ++ vrlw 4, 4, 25 # ++ vrlw 5, 5, 25 ++ vrlw 6, 6, 25 ++ vrlw 7, 7, 25 ++ vrlw 20, 20, 25 # ++ vrlw 21, 21, 25 ++ vrlw 22, 22, 25 ++ vrlw 23, 23, 25 ++ xxlor 32+25, 0, 0 ++ vadduwm 0, 0, 4 ++ vadduwm 1, 1, 5 ++ vadduwm 2, 2, 6 ++ vadduwm 3, 3, 7 ++ vadduwm 16, 16, 20 ++ vadduwm 17, 17, 21 ++ vadduwm 18, 18, 22 ++ vadduwm 19, 19, 23 ++ ++ xxlor 0, 32+25, 32+25 ++ xxlor 32+25, 22, 22 ++ vpermxor 12, 12, 0, 25 ++ vpermxor 13, 13, 1, 25 ++ vpermxor 14, 14, 2, 25 ++ vpermxor 15, 15, 3, 25 ++ vpermxor 28, 28, 16, 25 ++ vpermxor 29, 29, 17, 25 ++ vpermxor 30, 30, 18, 25 ++ vpermxor 31, 31, 19, 25 ++ xxlor 32+25, 0, 0 ++ vadduwm 8, 8, 12 ++ vadduwm 9, 9, 13 ++ vadduwm 10, 10, 14 ++ vadduwm 11, 11, 15 ++ vadduwm 24, 24, 28 ++ vadduwm 25, 25, 29 ++ vadduwm 26, 26, 30 ++ vadduwm 27, 27, 31 ++ xxlor 0, 32+28, 32+28 ++ xxlor 32+28, 23, 23 ++ vxor 4, 4, 8 ++ vxor 5, 5, 9 ++ vxor 6, 6, 10 ++ vxor 7, 7, 11 ++ vxor 20, 20, 24 ++ vxor 21, 21, 25 ++ vxor 22, 22, 26 ++ vxor 23, 23, 27 ++ vrlw 4, 4, 28 # ++ vrlw 5, 5, 28 ++ vrlw 6, 6, 28 ++ vrlw 7, 7, 28 ++ vrlw 20, 20, 28 # ++ vrlw 21, 21, 28 ++ vrlw 22, 22, 28 ++ vrlw 23, 23, 28 ++ xxlor 32+28, 0, 0 ++ ++ # QR(v0, v5, v10, v15, v1, v6, v11, v12, v2, v7, v8, v13, v3, v4, v9, v14) ++ xxlor 0, 32+25, 32+25 ++ xxlor 32+25, 20, 20 ++ vadduwm 0, 0, 5 ++ vadduwm 1, 1, 6 ++ vadduwm 2, 2, 7 ++ vadduwm 3, 3, 4 ++ vadduwm 16, 16, 21 ++ vadduwm 17, 17, 22 ++ vadduwm 18, 18, 23 ++ vadduwm 19, 19, 20 ++ ++ vpermxor 15, 15, 0, 25 ++ vpermxor 12, 12, 1, 25 ++ vpermxor 13, 13, 2, 25 ++ vpermxor 14, 14, 3, 25 ++ vpermxor 31, 31, 16, 25 ++ vpermxor 28, 28, 17, 25 ++ vpermxor 29, 29, 18, 25 ++ vpermxor 30, 30, 19, 25 ++ ++ xxlor 32+25, 0, 0 ++ vadduwm 10, 10, 15 ++ vadduwm 11, 11, 12 ++ vadduwm 8, 8, 13 ++ vadduwm 9, 9, 14 ++ vadduwm 26, 26, 31 ++ vadduwm 27, 27, 28 ++ vadduwm 24, 24, 29 ++ vadduwm 25, 25, 30 ++ vxor 5, 5, 10 ++ vxor 6, 6, 11 ++ vxor 7, 7, 8 ++ vxor 4, 4, 9 ++ vxor 21, 21, 26 ++ vxor 22, 22, 27 ++ vxor 23, 23, 24 ++ vxor 20, 20, 25 ++ ++ xxlor 0, 32+25, 32+25 ++ xxlor 32+25, 21, 21 ++ vrlw 5, 5, 25 ++ vrlw 6, 6, 25 ++ vrlw 7, 7, 25 ++ vrlw 4, 4, 25 ++ vrlw 21, 21, 25 ++ vrlw 22, 22, 25 ++ vrlw 23, 23, 25 ++ vrlw 20, 20, 25 ++ xxlor 32+25, 0, 0 ++ ++ vadduwm 0, 0, 5 ++ vadduwm 1, 1, 6 ++ vadduwm 2, 2, 7 ++ vadduwm 3, 3, 4 ++ vadduwm 16, 16, 21 ++ vadduwm 17, 17, 22 ++ vadduwm 18, 18, 23 ++ vadduwm 19, 19, 20 ++ ++ xxlor 0, 32+25, 32+25 ++ xxlor 32+25, 22, 22 ++ vpermxor 15, 15, 0, 25 ++ vpermxor 12, 12, 1, 25 ++ vpermxor 13, 13, 2, 25 ++ vpermxor 14, 14, 3, 25 ++ vpermxor 31, 31, 16, 25 ++ vpermxor 28, 28, 17, 25 ++ vpermxor 29, 29, 18, 25 ++ vpermxor 30, 30, 19, 25 ++ xxlor 32+25, 0, 0 ++ ++ vadduwm 10, 10, 15 ++ vadduwm 11, 11, 12 ++ vadduwm 8, 8, 13 ++ vadduwm 9, 9, 14 ++ vadduwm 26, 26, 31 ++ vadduwm 27, 27, 28 ++ vadduwm 24, 24, 29 ++ vadduwm 25, 25, 30 ++ ++ xxlor 0, 32+28, 32+28 ++ xxlor 32+28, 23, 23 ++ vxor 5, 5, 10 ++ vxor 6, 6, 11 ++ vxor 7, 7, 8 ++ vxor 4, 4, 9 ++ vxor 21, 21, 26 ++ vxor 22, 22, 27 ++ vxor 23, 23, 24 ++ vxor 20, 20, 25 ++ vrlw 5, 5, 28 ++ vrlw 6, 6, 28 ++ vrlw 7, 7, 28 ++ vrlw 4, 4, 28 ++ vrlw 21, 21, 28 ++ vrlw 22, 22, 28 ++ vrlw 23, 23, 28 ++ vrlw 20, 20, 28 ++ xxlor 32+28, 0, 0 ++.endm ++ ++.macro QT_loop_4x ++ # QR(v0, v4, v8, v12, v1, v5, v9, v13, v2, v6, v10, v14, v3, v7, v11, v15) ++ vadduwm 0, 0, 4 ++ vadduwm 1, 1, 5 ++ vadduwm 2, 2, 6 ++ vadduwm 3, 3, 7 ++ vpermxor 12, 12, 0, 20 ++ vpermxor 13, 13, 1, 20 ++ vpermxor 14, 14, 2, 20 ++ vpermxor 15, 15, 3, 20 ++ vadduwm 8, 8, 12 ++ vadduwm 9, 9, 13 ++ vadduwm 10, 10, 14 ++ vadduwm 11, 11, 15 ++ vxor 4, 4, 8 ++ vxor 5, 5, 9 ++ vxor 6, 6, 10 ++ vxor 7, 7, 11 ++ vrlw 4, 4, 21 ++ vrlw 5, 5, 21 ++ vrlw 6, 6, 21 ++ vrlw 7, 7, 21 ++ vadduwm 0, 0, 4 ++ vadduwm 1, 1, 5 ++ vadduwm 2, 2, 6 ++ vadduwm 3, 3, 7 ++ vpermxor 12, 12, 0, 22 ++ vpermxor 13, 13, 1, 22 ++ vpermxor 14, 14, 2, 22 ++ vpermxor 15, 15, 3, 22 ++ vadduwm 8, 8, 12 ++ vadduwm 9, 9, 13 ++ vadduwm 10, 10, 14 ++ vadduwm 11, 11, 15 ++ vxor 4, 4, 8 ++ vxor 5, 5, 9 ++ vxor 6, 6, 10 ++ vxor 7, 7, 11 ++ vrlw 4, 4, 23 ++ vrlw 5, 5, 23 ++ vrlw 6, 6, 23 ++ vrlw 7, 7, 23 ++ ++ # QR(v0, v5, v10, v15, v1, v6, v11, v12, v2, v7, v8, v13, v3, v4, v9, v14) ++ vadduwm 0, 0, 5 ++ vadduwm 1, 1, 6 ++ vadduwm 2, 2, 7 ++ vadduwm 3, 3, 4 ++ vpermxor 15, 15, 0, 20 ++ vpermxor 12, 12, 1, 20 ++ vpermxor 13, 13, 2, 20 ++ vpermxor 14, 14, 3, 20 ++ vadduwm 10, 10, 15 ++ vadduwm 11, 11, 12 ++ vadduwm 8, 8, 13 ++ vadduwm 9, 9, 14 ++ vxor 5, 5, 10 ++ vxor 6, 6, 11 ++ vxor 7, 7, 8 ++ vxor 4, 4, 9 ++ vrlw 5, 5, 21 ++ vrlw 6, 6, 21 ++ vrlw 7, 7, 21 ++ vrlw 4, 4, 21 ++ vadduwm 0, 0, 5 ++ vadduwm 1, 1, 6 ++ vadduwm 2, 2, 7 ++ vadduwm 3, 3, 4 ++ vpermxor 15, 15, 0, 22 ++ vpermxor 12, 12, 1, 22 ++ vpermxor 13, 13, 2, 22 ++ vpermxor 14, 14, 3, 22 ++ vadduwm 10, 10, 15 ++ vadduwm 11, 11, 12 ++ vadduwm 8, 8, 13 ++ vadduwm 9, 9, 14 ++ vxor 5, 5, 10 ++ vxor 6, 6, 11 ++ vxor 7, 7, 8 ++ vxor 4, 4, 9 ++ vrlw 5, 5, 23 ++ vrlw 6, 6, 23 ++ vrlw 7, 7, 23 ++ vrlw 4, 4, 23 ++.endm ++ ++# Transpose ++.macro TP_4x a0 a1 a2 a3 ++ xxmrghw 10, 32+\a0, 32+\a1 # a0, a1, b0, b1 ++ xxmrghw 11, 32+\a2, 32+\a3 # a2, a3, b2, b3 ++ xxmrglw 12, 32+\a0, 32+\a1 # c0, c1, d0, d1 ++ xxmrglw 13, 32+\a2, 32+\a3 # c2, c3, d2, d3 ++ xxpermdi 32+\a0, 10, 11, 0 # a0, a1, a2, a3 ++ xxpermdi 32+\a1, 10, 11, 3 # b0, b1, b2, b3 ++ xxpermdi 32+\a2, 12, 13, 0 # c0, c1, c2, c3 ++ xxpermdi 32+\a3, 12, 13, 3 # d0, d1, d2, d3 ++.endm ++ ++# key stream = working state + state ++.macro Add_state S ++ vadduwm \S+0, \S+0, 16-\S ++ vadduwm \S+4, \S+4, 17-\S ++ vadduwm \S+8, \S+8, 18-\S ++ vadduwm \S+12, \S+12, 19-\S ++ ++ vadduwm \S+1, \S+1, 16-\S ++ vadduwm \S+5, \S+5, 17-\S ++ vadduwm \S+9, \S+9, 18-\S ++ vadduwm \S+13, \S+13, 19-\S ++ ++ vadduwm \S+2, \S+2, 16-\S ++ vadduwm \S+6, \S+6, 17-\S ++ vadduwm \S+10, \S+10, 18-\S ++ vadduwm \S+14, \S+14, 19-\S ++ ++ vadduwm \S+3, \S+3, 16-\S ++ vadduwm \S+7, \S+7, 17-\S ++ vadduwm \S+11, \S+11, 18-\S ++ vadduwm \S+15, \S+15, 19-\S ++.endm ++ ++# ++# write 256 bytes ++# ++.macro Write_256 S ++ add 9, 14, 5 ++ add 16, 14, 4 ++ lxvw4x 0, 0, 9 ++ lxvw4x 1, 17, 9 ++ lxvw4x 2, 18, 9 ++ lxvw4x 3, 19, 9 ++ lxvw4x 4, 20, 9 ++ lxvw4x 5, 21, 9 ++ lxvw4x 6, 22, 9 ++ lxvw4x 7, 23, 9 ++ lxvw4x 8, 24, 9 ++ lxvw4x 9, 25, 9 ++ lxvw4x 10, 26, 9 ++ lxvw4x 11, 27, 9 ++ lxvw4x 12, 28, 9 ++ lxvw4x 13, 29, 9 ++ lxvw4x 14, 30, 9 ++ lxvw4x 15, 31, 9 ++ ++ xxlxor \S+32, \S+32, 0 ++ xxlxor \S+36, \S+36, 1 ++ xxlxor \S+40, \S+40, 2 ++ xxlxor \S+44, \S+44, 3 ++ xxlxor \S+33, \S+33, 4 ++ xxlxor \S+37, \S+37, 5 ++ xxlxor \S+41, \S+41, 6 ++ xxlxor \S+45, \S+45, 7 ++ xxlxor \S+34, \S+34, 8 ++ xxlxor \S+38, \S+38, 9 ++ xxlxor \S+42, \S+42, 10 ++ xxlxor \S+46, \S+46, 11 ++ xxlxor \S+35, \S+35, 12 ++ xxlxor \S+39, \S+39, 13 ++ xxlxor \S+43, \S+43, 14 ++ xxlxor \S+47, \S+47, 15 ++ ++ stxvw4x \S+32, 0, 16 ++ stxvw4x \S+36, 17, 16 ++ stxvw4x \S+40, 18, 16 ++ stxvw4x \S+44, 19, 16 ++ ++ stxvw4x \S+33, 20, 16 ++ stxvw4x \S+37, 21, 16 ++ stxvw4x \S+41, 22, 16 ++ stxvw4x \S+45, 23, 16 ++ ++ stxvw4x \S+34, 24, 16 ++ stxvw4x \S+38, 25, 16 ++ stxvw4x \S+42, 26, 16 ++ stxvw4x \S+46, 27, 16 ++ ++ stxvw4x \S+35, 28, 16 ++ stxvw4x \S+39, 29, 16 ++ stxvw4x \S+43, 30, 16 ++ stxvw4x \S+47, 31, 16 ++ ++.endm ++ ++# ++# unsigned int _gcry_chacha20_p10le_8x(u32 *state, byte *dst, const byte *src, size_t len); ++# ++.global _gcry_chacha20_p10le_8x ++.align 5 ++_gcry_chacha20_p10le_8x: ++ cmpdi 6, 512 ++ blt Out_no_chacha ++ ++ stdu 1,-1024(1) ++ mflr 0 ++ ++ std 14,112(1) ++ std 15,120(1) ++ std 16,128(1) ++ std 17,136(1) ++ std 18,144(1) ++ std 19,152(1) ++ std 20,160(1) ++ std 21,168(1) ++ std 22,176(1) ++ std 23,184(1) ++ std 24,192(1) ++ std 25,200(1) ++ std 26,208(1) ++ std 27,216(1) ++ std 28,224(1) ++ std 29,232(1) ++ std 30,240(1) ++ std 31,248(1) ++ std 0, 1040(1) ++ ++ li 17, 16 ++ li 18, 32 ++ li 19, 48 ++ li 20, 64 ++ li 21, 80 ++ li 22, 96 ++ li 23, 112 ++ li 24, 128 ++ li 25, 144 ++ li 26, 160 ++ li 27, 176 ++ li 28, 192 ++ li 29, 208 ++ li 30, 224 ++ li 31, 240 ++ addi 9, 1, 256 ++ stvx 20, 0, 9 ++ stvx 21, 17, 9 ++ stvx 22, 18, 9 ++ stvx 23, 19, 9 ++ stvx 24, 20, 9 ++ stvx 25, 21, 9 ++ stvx 26, 22, 9 ++ stvx 27, 23, 9 ++ stvx 28, 24, 9 ++ stvx 29, 25, 9 ++ stvx 30, 26, 9 ++ stvx 31, 27, 9 ++ ++ add 9, 9, 27 ++ addi 14, 17, 16 ++ stxvx 14, 14, 9 ++ addi 14, 14, 16 ++ stxvx 15, 14, 9 ++ addi 14, 14, 16 ++ stxvx 16, 14, 9 ++ addi 14, 14, 16 ++ stxvx 17, 14, 9 ++ addi 14, 14, 16 ++ stxvx 18, 14, 9 ++ addi 14, 14, 16 ++ stxvx 19, 14, 9 ++ addi 14, 14, 16 ++ stxvx 20, 14, 9 ++ addi 14, 14, 16 ++ stxvx 21, 14, 9 ++ addi 14, 14, 16 ++ stxvx 22, 14, 9 ++ addi 14, 14, 16 ++ stxvx 23, 14, 9 ++ addi 14, 14, 16 ++ stxvx 24, 14, 9 ++ addi 14, 14, 16 ++ stxvx 25, 14, 9 ++ addi 14, 14, 16 ++ stxvx 26, 14, 9 ++ addi 14, 14, 16 ++ stxvx 27, 14, 9 ++ addi 14, 14, 16 ++ stxvx 28, 14, 9 ++ addi 14, 14, 16 ++ stxvx 29, 14, 9 ++ addi 14, 14, 16 ++ stxvx 30, 14, 9 ++ addi 14, 14, 16 ++ stxvx 31, 14, 9 ++ ++ mr 15, 6 # len ++ li 14, 0 # offset to inp and outp ++ ++ ld 10, sigma@got(2) ++ ++ lxvw4x 48, 0, 3 # vr16, constants ++ lxvw4x 49, 17, 3 # vr17, key 1 ++ lxvw4x 50, 18, 3 # vr18, key 2 ++ lxvw4x 51, 19, 3 # vr19, counter, nonce ++ ++ lxvw4x 62, 19, 10 # vr30, 4 ++ ++ vspltisw 21, 12 ++ vspltisw 23, 7 ++ ++ ld 11, permx@got(2) ++ lxvw4x 32+20, 0, 11 ++ lxvw4x 32+22, 17, 11 ++ ++ li 8, 10 ++ mtctr 8 ++ ++ xxlor 16, 48, 48 ++ xxlor 17, 49, 49 ++ xxlor 18, 50, 50 ++ xxlor 19, 51, 51 ++ ++ vspltisw 25, 4 ++ vspltisw 26, 8 ++ ++ xxlor 16, 48, 48 ++ xxlor 17, 49, 49 ++ xxlor 18, 50, 50 ++ xxlor 19, 51, 51 ++ ++ xxlor 25, 32+26, 32+26 ++ xxlor 24, 32+25, 32+25 ++ ++ vadduwm 31, 30, 25 # (0, 1, 2, 3) + (4, 4, 4, 4) ++ xxlor 30, 32+30, 32+30 ++ xxlor 31, 32+31, 32+31 ++ ++ xxlor 20, 32+20, 32+20 ++ xxlor 21, 32+21, 32+21 ++ xxlor 22, 32+22, 32+22 ++ xxlor 23, 32+23, 32+23 ++ ++Loop_8x: ++ lvx 0, 20, 10 ++ lvx 1, 21, 10 ++ lvx 2, 22, 10 ++ lvx 3, 23, 10 ++ xxspltw 32+4, 17, 0 ++ xxspltw 32+5, 17, 1 ++ xxspltw 32+6, 17, 2 ++ xxspltw 32+7, 17, 3 ++ xxspltw 32+8, 18, 0 ++ xxspltw 32+9, 18, 1 ++ xxspltw 32+10, 18, 2 ++ xxspltw 32+11, 18, 3 ++ xxspltw 32+12, 19, 0 ++ xxspltw 32+13, 19, 1 ++ xxspltw 32+14, 19, 2 ++ xxspltw 32+15, 19, 3 ++ vadduwm 12, 12, 30 # increase counter ++ ++ lvx 16, 20, 10 ++ lvx 17, 21, 10 ++ lvx 18, 22, 10 ++ lvx 19, 23, 10 ++ xxspltw 32+20, 17, 0 ++ xxspltw 32+21, 17, 1 ++ xxspltw 32+22, 17, 2 ++ xxspltw 32+23, 17, 3 ++ xxspltw 32+24, 18, 0 ++ xxspltw 32+25, 18, 1 ++ xxspltw 32+26, 18, 2 ++ xxspltw 32+27, 18, 3 ++ xxspltw 32+28, 19, 0 ++ xxspltw 32+29, 19, 1 ++ vadduwm 28, 28, 31 # increase counter ++ xxspltw 32+30, 19, 2 ++ xxspltw 32+31, 19, 3 ++ ++.align 5 ++quarter_loop_8x: ++ QT_loop_8x ++ ++ bdnz quarter_loop_8x ++ ++ xxlor 0, 32+30, 32+30 ++ xxlor 32+30, 30, 30 ++ vadduwm 12, 12, 30 ++ xxlor 32+30, 0, 0 ++ TP_4x 0, 1, 2, 3 ++ TP_4x 4, 5, 6, 7 ++ TP_4x 8, 9, 10, 11 ++ TP_4x 12, 13, 14, 15 ++ ++ xxlor 0, 48, 48 ++ xxlor 1, 49, 49 ++ xxlor 2, 50, 50 ++ xxlor 3, 51, 51 ++ xxlor 48, 16, 16 ++ xxlor 49, 17, 17 ++ xxlor 50, 18, 18 ++ xxlor 51, 19, 19 ++ Add_state 0 ++ xxlor 48, 0, 0 ++ xxlor 49, 1, 1 ++ xxlor 50, 2, 2 ++ xxlor 51, 3, 3 ++ Write_256 0 ++ addi 14, 14, 256 ++ addi 15, 15, -256 ++ ++ xxlor 5, 32+31, 32+31 ++ xxlor 32+31, 31, 31 ++ vadduwm 28, 28, 31 ++ xxlor 32+31, 5, 5 ++ TP_4x 16+0, 16+1, 16+2, 16+3 ++ TP_4x 16+4, 16+5, 16+6, 16+7 ++ TP_4x 16+8, 16+9, 16+10, 16+11 ++ TP_4x 16+12, 16+13, 16+14, 16+15 ++ ++ xxlor 32, 16, 16 ++ xxlor 33, 17, 17 ++ xxlor 34, 18, 18 ++ xxlor 35, 19, 19 ++ Add_state 16 ++ Write_256 16 ++ addi 14, 14, 256 ++ addi 15, 15, -256 ++ ++ # should update counter before out? ++ xxlor 32+24, 24, 24 ++ xxlor 32+25, 25, 25 ++ xxlor 32+30, 30, 30 ++ vadduwm 30, 30, 25 ++ vadduwm 31, 30, 24 ++ xxlor 30, 32+30, 32+30 ++ xxlor 31, 32+31, 32+31 ++ ++ cmpdi 15, 0 ++ beq Out_loop ++ ++ cmpdi 15, 512 ++ blt Loop_last ++ ++ mtctr 8 ++ b Loop_8x ++ ++Loop_last: ++ lxvw4x 48, 0, 3 # vr16, constants ++ lxvw4x 49, 17, 3 # vr17, key 1 ++ lxvw4x 50, 18, 3 # vr18, key 2 ++ lxvw4x 51, 19, 3 # vr19, counter, nonce ++ ++ vspltisw 21, 12 ++ vspltisw 23, 7 ++ lxvw4x 32+20, 0, 11 ++ lxvw4x 32+22, 17, 11 ++ ++ li 8, 10 ++ mtctr 8 ++ ++Loop_4x: ++ lvx 0, 20, 10 ++ lvx 1, 21, 10 ++ lvx 2, 22, 10 ++ lvx 3, 23, 10 ++ vspltw 4, 17, 0 ++ vspltw 5, 17, 1 ++ vspltw 6, 17, 2 ++ vspltw 7, 17, 3 ++ vspltw 8, 18, 0 ++ vspltw 9, 18, 1 ++ vspltw 10, 18, 2 ++ vspltw 11, 18, 3 ++ vspltw 12, 19, 0 ++ vadduwm 12, 12, 30 # increase counter ++ vspltw 13, 19, 1 ++ vspltw 14, 19, 2 ++ vspltw 15, 19, 3 ++ ++.align 5 ++quarter_loop: ++ QT_loop_4x ++ ++ bdnz quarter_loop ++ ++ vadduwm 12, 12, 30 ++ TP_4x 0, 1, 2, 3 ++ TP_4x 4, 5, 6, 7 ++ TP_4x 8, 9, 10, 11 ++ TP_4x 12, 13, 14, 15 ++ ++ Add_state 0 ++ Write_256 0 ++ addi 14, 14, 256 ++ addi 15, 15, -256 ++ ++ # Update state counter ++ vspltisw 25, 4 ++ vadduwm 30, 30, 25 ++ ++ cmpdi 15, 0 ++ beq Out_loop ++ ++ mtctr 8 ++ b Loop_4x ++ ++Out_loop: ++ # ++ # Update state counter ++ # ++ vspltisb 16, -1 # first 16 bytes - 0xffff...ff ++ vspltisb 17, 0 # second 16 bytes - 0x0000...00 ++ vsldoi 18, 16, 17, 12 ++ vand 18, 18, 30 ++ xxlor 32+19, 19, 19 ++ vadduwm 18, 19, 18 ++ stxvw4x 32+18, 19, 3 ++ li 3, 0 ++ ++ addi 9, 1, 256 ++ lvx 20, 0, 9 ++ lvx 21, 17, 9 ++ lvx 22, 18, 9 ++ lvx 23, 19, 9 ++ lvx 24, 20, 9 ++ lvx 25, 21, 9 ++ lvx 26, 22, 9 ++ lvx 27, 23, 9 ++ lvx 28, 24, 9 ++ lvx 29, 25, 9 ++ lvx 30, 26, 9 ++ lvx 31, 27, 9 ++ ++ add 9, 9, 27 ++ addi 14, 17, 16 ++ lxvx 14, 14, 9 ++ addi 14, 14, 16 ++ lxvx 15, 14, 9 ++ addi 14, 14, 16 ++ lxvx 16, 14, 9 ++ addi 14, 14, 16 ++ lxvx 17, 14, 9 ++ addi 14, 14, 16 ++ lxvx 18, 14, 9 ++ addi 14, 14, 16 ++ lxvx 19, 14, 9 ++ addi 14, 14, 16 ++ lxvx 20, 14, 9 ++ addi 14, 14, 16 ++ lxvx 21, 14, 9 ++ addi 14, 14, 16 ++ lxvx 22, 14, 9 ++ addi 14, 14, 16 ++ lxvx 23, 14, 9 ++ addi 14, 14, 16 ++ lxvx 24, 14, 9 ++ addi 14, 14, 16 ++ lxvx 25, 14, 9 ++ addi 14, 14, 16 ++ lxvx 26, 14, 9 ++ addi 14, 14, 16 ++ lxvx 27, 14, 9 ++ addi 14, 14, 16 ++ lxvx 28, 14, 9 ++ addi 14, 14, 16 ++ lxvx 29, 14, 9 ++ addi 14, 14, 16 ++ lxvx 30, 14, 9 ++ addi 14, 14, 16 ++ lxvx 31, 14, 9 ++ ++ ld 0, 1040(1) ++ ld 14,112(1) ++ ld 15,120(1) ++ ld 16,128(1) ++ ld 17,136(1) ++ ld 18,144(1) ++ ld 19,152(1) ++ ld 20,160(1) ++ ld 21,168(1) ++ ld 22,176(1) ++ ld 23,184(1) ++ ld 24,192(1) ++ ld 25,200(1) ++ ld 26,208(1) ++ ld 27,216(1) ++ ld 28,224(1) ++ ld 29,232(1) ++ ld 30,240(1) ++ ld 31,248(1) ++ ++ mtlr 0 ++ addi 1, 1, 1024 ++ blr ++ ++Out_no_chacha: ++ li 3, 0 ++ blr ++ ++.data ++.align 4 ++sigma: ++.long 0x61707865, 0x3320646e, 0x79622d32, 0x6b206574 ++.long 0x0c0d0e0f, 0x08090a0b, 0x04050607, 0x00010203 ++.long 1, 0, 0, 0 ++.long 0, 1, 2, 3 ++.long 0x61707865, 0x61707865, 0x61707865, 0x61707865 ++.long 0x3320646e, 0x3320646e, 0x3320646e, 0x3320646e ++.long 0x79622d32, 0x79622d32, 0x79622d32, 0x79622d32 ++.long 0x6b206574, 0x6b206574, 0x6b206574, 0x6b206574 ++permx: ++.long 0x22330011, 0x66774455, 0xaabb8899, 0xeeffccdd ++.long 0x11223300, 0x55667744, 0x99aabb88, 0xddeeffcc +Index: libgcrypt-1.10.2/cipher/chacha20.c +=================================================================== +--- libgcrypt-1.10.2.orig/cipher/chacha20.c ++++ libgcrypt-1.10.2/cipher/chacha20.c +@@ -125,6 +125,7 @@ typedef struct CHACHA20_context_s + unsigned int use_avx2:1; + unsigned int use_neon:1; + unsigned int use_ppc:1; ++ unsigned int use_p10:1; + unsigned int use_s390x:1; + } CHACHA20_context_t; + +@@ -163,6 +164,12 @@ unsigned int _gcry_chacha20_poly1305_amd + + #ifdef USE_PPC_VEC + ++#ifndef WORDS_BIGENDIAN ++unsigned int _gcry_chacha20_p10le_8x(u32 *state, byte *dst, ++ const byte *src, ++ size_t len); ++#endif ++ + unsigned int _gcry_chacha20_ppc8_blocks4(u32 *state, byte *dst, + const byte *src, + size_t nblks); +@@ -475,6 +482,9 @@ chacha20_do_setkey (CHACHA20_context_t * + #endif + #ifdef USE_PPC_VEC + ctx->use_ppc = (features & HWF_PPC_ARCH_2_07) != 0; ++# ifndef WORDS_BIGENDIAN ++ ctx->use_p10 = (features & HWF_PPC_ARCH_3_10) != 0; ++# endif + #endif + #ifdef USE_S390X_VX + ctx->use_s390x = (features & HWF_S390X_VX) != 0; +@@ -571,7 +581,22 @@ do_chacha20_encrypt_stream_tail (CHACHA2 + { + size_t nblocks = length / CHACHA20_BLOCK_SIZE; + nblocks -= nblocks % 4; +- nburn = _gcry_chacha20_ppc8_blocks4(ctx->input, outbuf, inbuf, nblocks); ++#ifndef WORDS_BIGENDIAN ++ /* ++ * A workaround to skip counter overflow. This is rare. ++ */ ++ if (ctx->use_p10 && nblocks >= 8 ++ && ((u64)ctx->input[12] + nblocks) <= 0xffffffffU) ++ { ++ size_t len = nblocks * CHACHA20_BLOCK_SIZE; ++ nburn = _gcry_chacha20_p10le_8x(ctx->input, outbuf, inbuf, len); ++ } ++ else ++#endif ++ { ++ nburn = _gcry_chacha20_ppc8_blocks4(ctx->input, outbuf, inbuf, ++ nblocks); ++ } + burn = nburn > burn ? nburn : burn; + length -= nblocks * CHACHA20_BLOCK_SIZE; + outbuf += nblocks * CHACHA20_BLOCK_SIZE; +@@ -760,6 +785,11 @@ _gcry_chacha20_poly1305_encrypt(gcry_cip + } + #endif + #ifdef USE_PPC_VEC_POLY1305 ++ else if (ctx->use_ppc && ctx->use_p10) ++ { ++ /* Skip stitched chacha20-poly1305 for P10. */ ++ authptr = NULL; ++ } + else if (ctx->use_ppc && length >= CHACHA20_BLOCK_SIZE * 4) + { + nburn = _gcry_chacha20_ppc8_blocks4(ctx->input, outbuf, inbuf, 4); +@@ -998,6 +1028,7 @@ _gcry_chacha20_poly1305_decrypt(gcry_cip + { + CHACHA20_context_t *ctx = (void *) &c->context.c; + unsigned int nburn, burn = 0; ++ int skip_stitched = 0; + + if (!length) + return 0; +@@ -1049,6 +1080,13 @@ _gcry_chacha20_poly1305_decrypt(gcry_cip + inbuf += nblocks * CHACHA20_BLOCK_SIZE; + } + #endif ++#ifdef USE_PPC_VEC_POLY1305 ++ if (ctx->use_ppc && ctx->use_p10) ++ { ++ /* Skip stitched chacha20-poly1305 for P10. */ ++ skip_stitched = 1; ++ } ++#endif + + #ifdef USE_SSSE3 + if (ctx->use_ssse3) +@@ -1102,7 +1140,8 @@ _gcry_chacha20_poly1305_decrypt(gcry_cip + #endif + + #ifdef USE_PPC_VEC_POLY1305 +- if (ctx->use_ppc && length >= 4 * CHACHA20_BLOCK_SIZE) ++ /* skip stitch for p10 */ ++ if (!skip_stitched && ctx->use_ppc && length >= 4 * CHACHA20_BLOCK_SIZE) + { + size_t nblocks = length / CHACHA20_BLOCK_SIZE; + nblocks -= nblocks % 4; +Index: libgcrypt-1.10.2/cipher/poly1305-internal.h +=================================================================== +--- libgcrypt-1.10.2.orig/cipher/poly1305-internal.h ++++ libgcrypt-1.10.2/cipher/poly1305-internal.h +@@ -33,6 +33,17 @@ + #define POLY1305_KEYLEN 32 + #define POLY1305_BLOCKSIZE 16 + ++/* POLY1305_USE_PPC_VEC indicates whether to enable PowerPC vector code. */ ++#undef POLY1305_USE_PPC_VEC ++#ifdef ENABLE_PPC_CRYPTO_SUPPORT ++# if defined(HAVE_COMPATIBLE_CC_PPC_ALTIVEC) && \ ++ defined(HAVE_GCC_INLINE_ASM_PPC_ALTIVEC) && \ ++ !defined(WORDS_BIGENDIAN) ++# if __GNUC__ >= 4 ++# define POLY1305_USE_PPC_VEC 1 ++# endif ++# endif ++#endif + + typedef struct + { +@@ -46,6 +57,9 @@ typedef struct poly1305_context_s + POLY1305_STATE state; + byte buffer[POLY1305_BLOCKSIZE]; + unsigned int leftover; ++#ifdef POLY1305_USE_PPC_VEC ++ unsigned int use_p10:1; ++#endif + } poly1305_context_t; + + +Index: libgcrypt-1.10.2/cipher/poly1305-p10le.s +=================================================================== +--- /dev/null ++++ libgcrypt-1.10.2/cipher/poly1305-p10le.s +@@ -0,0 +1,841 @@ ++# Copyright 2021- IBM Inc. All rights reserved ++# ++# This file is part of Libgcrypt. ++# ++# Libgcrypt is free software; you can redistribute it and/or modify ++# it under the terms of the GNU Lesser General Public License as ++# published by the Free Software Foundation; either version 2.1 of ++# the License, or (at your option) any later version. ++# ++# Libgcrypt 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 Lesser General Public License for more details. ++# ++# You should have received a copy of the GNU Lesser General Public ++# License along with this program; if not, see . ++# ++#=================================================================================== ++# Written by Danny Tsen ++# ++# Poly1305 - this version mainly using vector/VSX/Scalar ++# - 26 bits limbs ++# - Handle multiple 64 byte blcoks but need at least 2 64 bytes block ++# ++# Improve performance by breaking down polynominal to the sum of products with ++# h4 = m1 * r⁴ + m2 * r³ + m3 * r² + m4 * r ++# ++# 07/22/21 - this revison based on the above sum of products. Setup r^4, r^3, r^2, r and s3, s2, s1, s0 ++# to 9 vectors for multiplications. ++# ++# setup r^4, r^3, r^2, r vectors ++# vs [r^1, r^3, r^2, r^4] ++# vs0 = [r0,.....] ++# vs1 = [r1,.....] ++# vs2 = [r2,.....] ++# vs3 = [r3,.....] ++# vs4 = [r4,.....] ++# vs5 = [r1*5,...] ++# vs6 = [r2*5,...] ++# vs7 = [r2*5,...] ++# vs8 = [r4*5,...] ++# ++# Each word in a vector consists a member of a "r/s" in [a * r/s]. ++# ++# r0, r4*5, r3*5, r2*5, r1*5; ++# r1, r0, r4*5, r3*5, r2*5; ++# r2, r1, r0, r4*5, r3*5; ++# r3, r2, r1, r0, r4*5; ++# r4, r3, r2, r1, r0 ; ++# ++# ++# gcry_poly1305_p10le_4blocks( uint8_t *k, uint32_t mlen, uint8_t *m) ++# k = 32 bytes key ++# r3 = k (r, s) ++# r4 = mlen ++# r5 = m ++# ++.text ++ ++# Block size 16 bytes ++# key = (r, s) ++# clamp r &= 0x0FFFFFFC0FFFFFFC 0x0FFFFFFC0FFFFFFF ++# p = 2^130 - 5 ++# a += m ++# a = (r + a) % p ++# a += s ++# 16 bytes (a) ++# ++# p[0] = a0*r0 + a1*r4*5 + a2*r3*5 + a3*r2*5 + a4*r1*5; ++# p[1] = a0*r1 + a1*r0 + a2*r4*5 + a3*r3*5 + a4*r2*5; ++# p[2] = a0*r2 + a1*r1 + a2*r0 + a3*r4*5 + a4*r3*5; ++# p[3] = a0*r3 + a1*r2 + a2*r1 + a3*r0 + a4*r4*5; ++# p[4] = a0*r4 + a1*r3 + a2*r2 + a3*r1 + a4*r0 ; ++# ++# [r^2, r^3, r^1, r^4] ++# [m3, m2, m4, m1] ++# ++# multiply odd and even words ++.macro mul_odd ++ vmulouw 14, 4, 26 ++ vmulouw 10, 5, 3 ++ vmulouw 11, 6, 2 ++ vmulouw 12, 7, 1 ++ vmulouw 13, 8, 0 ++ vmulouw 15, 4, 27 ++ vaddudm 14, 14, 10 ++ vaddudm 14, 14, 11 ++ vmulouw 10, 5, 26 ++ vmulouw 11, 6, 3 ++ vaddudm 14, 14, 12 ++ vaddudm 14, 14, 13 # x0 ++ vaddudm 15, 15, 10 ++ vaddudm 15, 15, 11 ++ vmulouw 12, 7, 2 ++ vmulouw 13, 8, 1 ++ vaddudm 15, 15, 12 ++ vaddudm 15, 15, 13 # x1 ++ vmulouw 16, 4, 28 ++ vmulouw 10, 5, 27 ++ vmulouw 11, 6, 26 ++ vaddudm 16, 16, 10 ++ vaddudm 16, 16, 11 ++ vmulouw 12, 7, 3 ++ vmulouw 13, 8, 2 ++ vaddudm 16, 16, 12 ++ vaddudm 16, 16, 13 # x2 ++ vmulouw 17, 4, 29 ++ vmulouw 10, 5, 28 ++ vmulouw 11, 6, 27 ++ vaddudm 17, 17, 10 ++ vaddudm 17, 17, 11 ++ vmulouw 12, 7, 26 ++ vmulouw 13, 8, 3 ++ vaddudm 17, 17, 12 ++ vaddudm 17, 17, 13 # x3 ++ vmulouw 18, 4, 30 ++ vmulouw 10, 5, 29 ++ vmulouw 11, 6, 28 ++ vaddudm 18, 18, 10 ++ vaddudm 18, 18, 11 ++ vmulouw 12, 7, 27 ++ vmulouw 13, 8, 26 ++ vaddudm 18, 18, 12 ++ vaddudm 18, 18, 13 # x4 ++.endm ++ ++.macro mul_even ++ vmuleuw 9, 4, 26 ++ vmuleuw 10, 5, 3 ++ vmuleuw 11, 6, 2 ++ vmuleuw 12, 7, 1 ++ vmuleuw 13, 8, 0 ++ vaddudm 14, 14, 9 ++ vaddudm 14, 14, 10 ++ vaddudm 14, 14, 11 ++ vaddudm 14, 14, 12 ++ vaddudm 14, 14, 13 # x0 ++ ++ vmuleuw 9, 4, 27 ++ vmuleuw 10, 5, 26 ++ vmuleuw 11, 6, 3 ++ vmuleuw 12, 7, 2 ++ vmuleuw 13, 8, 1 ++ vaddudm 15, 15, 9 ++ vaddudm 15, 15, 10 ++ vaddudm 15, 15, 11 ++ vaddudm 15, 15, 12 ++ vaddudm 15, 15, 13 # x1 ++ ++ vmuleuw 9, 4, 28 ++ vmuleuw 10, 5, 27 ++ vmuleuw 11, 6, 26 ++ vmuleuw 12, 7, 3 ++ vmuleuw 13, 8, 2 ++ vaddudm 16, 16, 9 ++ vaddudm 16, 16, 10 ++ vaddudm 16, 16, 11 ++ vaddudm 16, 16, 12 ++ vaddudm 16, 16, 13 # x2 ++ ++ vmuleuw 9, 4, 29 ++ vmuleuw 10, 5, 28 ++ vmuleuw 11, 6, 27 ++ vmuleuw 12, 7, 26 ++ vmuleuw 13, 8, 3 ++ vaddudm 17, 17, 9 ++ vaddudm 17, 17, 10 ++ vaddudm 17, 17, 11 ++ vaddudm 17, 17, 12 ++ vaddudm 17, 17, 13 # x3 ++ ++ vmuleuw 9, 4, 30 ++ vmuleuw 10, 5, 29 ++ vmuleuw 11, 6, 28 ++ vmuleuw 12, 7, 27 ++ vmuleuw 13, 8, 26 ++ vaddudm 18, 18, 9 ++ vaddudm 18, 18, 10 ++ vaddudm 18, 18, 11 ++ vaddudm 18, 18, 12 ++ vaddudm 18, 18, 13 # x4 ++.endm ++ ++# setup r^4, r^3, r^2, r vectors ++# [r, r^3, r^2, r^4] ++# vs0 = [r0,...] ++# vs1 = [r1,...] ++# vs2 = [r2,...] ++# vs3 = [r3,...] ++# vs4 = [r4,...] ++# vs5 = [r4*5,...] ++# vs6 = [r3*5,...] ++# vs7 = [r2*5,...] ++# vs8 = [r1*5,...] ++# ++# r0, r4*5, r3*5, r2*5, r1*5; ++# r1, r0, r4*5, r3*5, r2*5; ++# r2, r1, r0, r4*5, r3*5; ++# r3, r2, r1, r0, r4*5; ++# r4, r3, r2, r1, r0 ; ++# ++.macro poly1305_setup_r ++ ++ # save r ++ xxlor 26, 58, 58 ++ xxlor 27, 59, 59 ++ xxlor 28, 60, 60 ++ xxlor 29, 61, 61 ++ xxlor 30, 62, 62 ++ ++ xxlxor 31, 31, 31 ++ ++# [r, r^3, r^2, r^4] ++ # compute r^2 ++ vmr 4, 26 ++ vmr 5, 27 ++ vmr 6, 28 ++ vmr 7, 29 ++ vmr 8, 30 ++ bl do_mul # r^2 r^1 ++ xxpermdi 58, 58, 36, 0x3 # r0 ++ xxpermdi 59, 59, 37, 0x3 # r1 ++ xxpermdi 60, 60, 38, 0x3 # r2 ++ xxpermdi 61, 61, 39, 0x3 # r3 ++ xxpermdi 62, 62, 40, 0x3 # r4 ++ xxpermdi 36, 36, 36, 0x3 ++ xxpermdi 37, 37, 37, 0x3 ++ xxpermdi 38, 38, 38, 0x3 ++ xxpermdi 39, 39, 39, 0x3 ++ xxpermdi 40, 40, 40, 0x3 ++ vspltisb 13, 2 ++ vsld 9, 27, 13 ++ vsld 10, 28, 13 ++ vsld 11, 29, 13 ++ vsld 12, 30, 13 ++ vaddudm 0, 9, 27 ++ vaddudm 1, 10, 28 ++ vaddudm 2, 11, 29 ++ vaddudm 3, 12, 30 ++ ++ bl do_mul # r^4 r^3 ++ vmrgow 26, 26, 4 ++ vmrgow 27, 27, 5 ++ vmrgow 28, 28, 6 ++ vmrgow 29, 29, 7 ++ vmrgow 30, 30, 8 ++ vspltisb 13, 2 ++ vsld 9, 27, 13 ++ vsld 10, 28, 13 ++ vsld 11, 29, 13 ++ vsld 12, 30, 13 ++ vaddudm 0, 9, 27 ++ vaddudm 1, 10, 28 ++ vaddudm 2, 11, 29 ++ vaddudm 3, 12, 30 ++ ++ # r^2 r^4 ++ xxlor 0, 58, 58 ++ xxlor 1, 59, 59 ++ xxlor 2, 60, 60 ++ xxlor 3, 61, 61 ++ xxlor 4, 62, 62 ++ xxlor 5, 32, 32 ++ xxlor 6, 33, 33 ++ xxlor 7, 34, 34 ++ xxlor 8, 35, 35 ++ ++ vspltw 9, 26, 3 ++ vspltw 10, 26, 2 ++ vmrgow 26, 10, 9 ++ vspltw 9, 27, 3 ++ vspltw 10, 27, 2 ++ vmrgow 27, 10, 9 ++ vspltw 9, 28, 3 ++ vspltw 10, 28, 2 ++ vmrgow 28, 10, 9 ++ vspltw 9, 29, 3 ++ vspltw 10, 29, 2 ++ vmrgow 29, 10, 9 ++ vspltw 9, 30, 3 ++ vspltw 10, 30, 2 ++ vmrgow 30, 10, 9 ++ ++ vsld 9, 27, 13 ++ vsld 10, 28, 13 ++ vsld 11, 29, 13 ++ vsld 12, 30, 13 ++ vaddudm 0, 9, 27 ++ vaddudm 1, 10, 28 ++ vaddudm 2, 11, 29 ++ vaddudm 3, 12, 30 ++.endm ++ ++do_mul: ++ mul_odd ++ ++ # do reduction ( h %= p ) ++ # carry reduction ++ vspltisb 9, 2 ++ vsrd 10, 14, 31 ++ vsrd 11, 17, 31 ++ vand 7, 17, 25 ++ vand 4, 14, 25 ++ vaddudm 18, 18, 11 ++ vsrd 12, 18, 31 ++ vaddudm 15, 15, 10 ++ ++ vsrd 11, 15, 31 ++ vand 8, 18, 25 ++ vand 5, 15, 25 ++ vaddudm 4, 4, 12 ++ vsld 10, 12, 9 ++ vaddudm 6, 16, 11 ++ ++ vsrd 13, 6, 31 ++ vand 6, 6, 25 ++ vaddudm 4, 4, 10 ++ vsrd 10, 4, 31 ++ vaddudm 7, 7, 13 ++ ++ vsrd 11, 7, 31 ++ vand 7, 7, 25 ++ vand 4, 4, 25 ++ vaddudm 5, 5, 10 ++ vaddudm 8, 8, 11 ++ blr ++ ++# ++# init key ++# ++do_poly1305_init: ++ ld 10, rmask@got(2) ++ ld 11, 0(10) ++ ld 12, 8(10) ++ ++ li 14, 16 ++ li 15, 32 ++ ld 10, cnum@got(2) ++ lvx 25, 0, 10 # v25 - mask ++ lvx 31, 14, 10 # v31 = 1a ++ lvx 19, 15, 10 # v19 = 1 << 24 ++ lxv 24, 48(10) # vs24 ++ lxv 25, 64(10) # vs25 ++ ++ # initialize ++ # load key from r3 to vectors ++ ld 9, 16(3) ++ ld 10, 24(3) ++ ld 11, 0(3) ++ ld 12, 8(3) ++ ++ # break 26 bits ++ extrdi 14, 9, 26, 38 ++ extrdi 15, 9, 26, 12 ++ extrdi 16, 9, 12, 0 ++ mtvsrdd 58, 0, 14 ++ insrdi 16, 10, 14, 38 ++ mtvsrdd 59, 0, 15 ++ extrdi 17, 10, 26, 24 ++ mtvsrdd 60, 0, 16 ++ extrdi 18, 10, 24, 0 ++ mtvsrdd 61, 0, 17 ++ mtvsrdd 62, 0, 18 ++ ++ # r1 = r1 * 5, r2 = r2 * 5, r3 = r3 * 5, r4 = r4 * 5 ++ li 9, 5 ++ mtvsrdd 36, 0, 9 ++ vmulouw 0, 27, 4 # v0 = rr0 ++ vmulouw 1, 28, 4 # v1 = rr1 ++ vmulouw 2, 29, 4 # v2 = rr2 ++ vmulouw 3, 30, 4 # v3 = rr3 ++ blr ++ ++# ++# gcry_poly1305_p10le_4blocks( uint8_t *k, uint32_t mlen, uint8_t *m) ++# k = 32 bytes key ++# r3 = k (r, s) ++# r4 = mlen ++# r5 = m ++# ++.global gcry_poly1305_p10le_4blocks ++.align 5 ++gcry_poly1305_p10le_4blocks: ++_gcry_poly1305_p10le_4blocks: ++ cmpdi 5, 128 ++ blt Out_no_poly1305 ++ ++ stdu 1,-1024(1) ++ mflr 0 ++ ++ std 14,112(1) ++ std 15,120(1) ++ std 16,128(1) ++ std 17,136(1) ++ std 18,144(1) ++ std 19,152(1) ++ std 20,160(1) ++ std 21,168(1) ++ std 31,248(1) ++ li 14, 256 ++ stvx 20, 14, 1 ++ addi 14, 14, 16 ++ stvx 21, 14, 1 ++ addi 14, 14, 16 ++ stvx 22, 14, 1 ++ addi 14, 14, 16 ++ stvx 23, 14, 1 ++ addi 14, 14, 16 ++ stvx 24, 14, 1 ++ addi 14, 14, 16 ++ stvx 25, 14, 1 ++ addi 14, 14, 16 ++ stvx 26, 14, 1 ++ addi 14, 14, 16 ++ stvx 27, 14, 1 ++ addi 14, 14, 16 ++ stvx 28, 14, 1 ++ addi 14, 14, 16 ++ stvx 29, 14, 1 ++ addi 14, 14, 16 ++ stvx 30, 14, 1 ++ addi 14, 14, 16 ++ stvx 31, 14, 1 ++ ++ addi 14, 14, 16 ++ stxvx 14, 14, 1 ++ addi 14, 14, 16 ++ stxvx 15, 14, 1 ++ addi 14, 14, 16 ++ stxvx 16, 14, 1 ++ addi 14, 14, 16 ++ stxvx 17, 14, 1 ++ addi 14, 14, 16 ++ stxvx 18, 14, 1 ++ addi 14, 14, 16 ++ stxvx 19, 14, 1 ++ addi 14, 14, 16 ++ stxvx 20, 14, 1 ++ addi 14, 14, 16 ++ stxvx 21, 14, 1 ++ addi 14, 14, 16 ++ stxvx 22, 14, 1 ++ addi 14, 14, 16 ++ stxvx 23, 14, 1 ++ addi 14, 14, 16 ++ stxvx 24, 14, 1 ++ addi 14, 14, 16 ++ stxvx 25, 14, 1 ++ addi 14, 14, 16 ++ stxvx 26, 14, 1 ++ addi 14, 14, 16 ++ stxvx 27, 14, 1 ++ addi 14, 14, 16 ++ stxvx 28, 14, 1 ++ addi 14, 14, 16 ++ stxvx 29, 14, 1 ++ addi 14, 14, 16 ++ stxvx 30, 14, 1 ++ addi 14, 14, 16 ++ stxvx 31, 14, 1 ++ std 0, 1040(1) ++ ++ bl do_poly1305_init ++ ++ li 21, 0 # counter to message ++ ++ poly1305_setup_r ++ ++ # load previous state ++ # break/convert r6 to 26 bits ++ ld 9, 32(3) ++ ld 10, 40(3) ++ lwz 19, 48(3) ++ sldi 19, 19, 24 ++ mtvsrdd 41, 0, 19 ++ extrdi 14, 9, 26, 38 ++ extrdi 15, 9, 26, 12 ++ extrdi 16, 9, 12, 0 ++ mtvsrdd 36, 0, 14 ++ insrdi 16, 10, 14, 38 ++ mtvsrdd 37, 0, 15 ++ extrdi 17, 10, 26, 24 ++ mtvsrdd 38, 0, 16 ++ extrdi 18, 10, 24, 0 ++ mtvsrdd 39, 0, 17 ++ mtvsrdd 40, 0, 18 ++ vor 8, 8, 9 ++ ++ # input m1 m2 ++ add 20, 4, 21 ++ xxlor 49, 24, 24 ++ xxlor 50, 25, 25 ++ lxvw4x 43, 0, 20 ++ addi 17, 20, 16 ++ lxvw4x 44, 0, 17 ++ vperm 14, 11, 12, 17 ++ vperm 15, 11, 12, 18 ++ vand 9, 14, 25 # a0 ++ vsrd 10, 14, 31 # >> 26 ++ vsrd 11, 10, 31 # 12 bits left ++ vand 10, 10, 25 # a1 ++ vspltisb 13, 12 ++ vand 16, 15, 25 ++ vsld 12, 16, 13 ++ vor 11, 11, 12 ++ vand 11, 11, 25 # a2 ++ vspltisb 13, 14 ++ vsrd 12, 15, 13 # >> 14 ++ vsrd 13, 12, 31 # >> 26, a4 ++ vand 12, 12, 25 # a3 ++ ++ vaddudm 20, 4, 9 ++ vaddudm 21, 5, 10 ++ vaddudm 22, 6, 11 ++ vaddudm 23, 7, 12 ++ vaddudm 24, 8, 13 ++ ++ # m3 m4 ++ addi 17, 17, 16 ++ lxvw4x 43, 0, 17 ++ addi 17, 17, 16 ++ lxvw4x 44, 0, 17 ++ vperm 14, 11, 12, 17 ++ vperm 15, 11, 12, 18 ++ vand 9, 14, 25 # a0 ++ vsrd 10, 14, 31 # >> 26 ++ vsrd 11, 10, 31 # 12 bits left ++ vand 10, 10, 25 # a1 ++ vspltisb 13, 12 ++ vand 16, 15, 25 ++ vsld 12, 16, 13 ++ vspltisb 13, 14 ++ vor 11, 11, 12 ++ vand 11, 11, 25 # a2 ++ vsrd 12, 15, 13 # >> 14 ++ vsrd 13, 12, 31 # >> 26, a4 ++ vand 12, 12, 25 # a3 ++ ++ # Smash 4 message blocks into 5 vectors of [m4, m2, m3, m1] ++ vmrgow 4, 9, 20 ++ vmrgow 5, 10, 21 ++ vmrgow 6, 11, 22 ++ vmrgow 7, 12, 23 ++ vmrgow 8, 13, 24 ++ vaddudm 8, 8, 19 ++ ++ addi 5, 5, -64 ++ addi 21, 21, 64 ++ ++ li 9, 64 ++ divdu 31, 5, 9 ++ ++ mtctr 31 ++ ++# h4 = m1 * r⁴ + m2 * r³ + m3 * r² + m4 * r ++# Rewrite the polynominal sum of product as follows, ++# h1 = (h0 + m1) * r^2, h2 = (h0 + m2) * r^2 ++# h3 = (h1 + m3) * r^2, h4 = (h2 + m4) * r^2 --> (h0 + m1) r*4 + (h3 + m3) r^2, (h0 + m2) r^4 + (h0 + m4) r^2 ++# .... Repeat ++# h5 = (h3 + m5) * r^2, h6 = (h4 + m6) * r^2 --> ++# h7 = (h5 + m7) * r^2, h8 = (h6 + m8) * r^1 --> m5 * r^4 + m6 * r^3 + m7 * r^2 + m8 * r ++# ++loop_4blocks: ++ ++ # Multiply odd words and even words ++ mul_odd ++ mul_even ++ # carry reduction ++ vspltisb 9, 2 ++ vsrd 10, 14, 31 ++ vsrd 11, 17, 31 ++ vand 7, 17, 25 ++ vand 4, 14, 25 ++ vaddudm 18, 18, 11 ++ vsrd 12, 18, 31 ++ vaddudm 15, 15, 10 ++ ++ vsrd 11, 15, 31 ++ vand 8, 18, 25 ++ vand 5, 15, 25 ++ vaddudm 4, 4, 12 ++ vsld 10, 12, 9 ++ vaddudm 6, 16, 11 ++ ++ vsrd 13, 6, 31 ++ vand 6, 6, 25 ++ vaddudm 4, 4, 10 ++ vsrd 10, 4, 31 ++ vaddudm 7, 7, 13 ++ ++ vsrd 11, 7, 31 ++ vand 7, 7, 25 ++ vand 4, 4, 25 ++ vaddudm 5, 5, 10 ++ vaddudm 8, 8, 11 ++ ++ # input m1 m2 m3 m4 ++ add 20, 4, 21 ++ xxlor 49, 24, 24 ++ xxlor 50, 25, 25 ++ lxvw4x 43, 0, 20 ++ addi 17, 20, 16 ++ lxvw4x 44, 0, 17 ++ vperm 14, 11, 12, 17 ++ vperm 15, 11, 12, 18 ++ addi 17, 17, 16 ++ lxvw4x 43, 0, 17 ++ addi 17, 17, 16 ++ lxvw4x 44, 0, 17 ++ vperm 17, 11, 12, 17 ++ vperm 18, 11, 12, 18 ++ ++ vand 20, 14, 25 # a0 ++ vand 9, 17, 25 # a0 ++ vsrd 21, 14, 31 # >> 26 ++ vsrd 22, 21, 31 # 12 bits left ++ vsrd 10, 17, 31 # >> 26 ++ vsrd 11, 10, 31 # 12 bits left ++ ++ vand 21, 21, 25 # a1 ++ vand 10, 10, 25 # a1 ++ ++ vspltisb 13, 12 ++ vand 16, 15, 25 ++ vsld 23, 16, 13 ++ vor 22, 22, 23 ++ vand 22, 22, 25 # a2 ++ vand 16, 18, 25 ++ vsld 12, 16, 13 ++ vor 11, 11, 12 ++ vand 11, 11, 25 # a2 ++ vspltisb 13, 14 ++ vsrd 23, 15, 13 # >> 14 ++ vsrd 24, 23, 31 # >> 26, a4 ++ vand 23, 23, 25 # a3 ++ vsrd 12, 18, 13 # >> 14 ++ vsrd 13, 12, 31 # >> 26, a4 ++ vand 12, 12, 25 # a3 ++ ++ vaddudm 4, 4, 20 ++ vaddudm 5, 5, 21 ++ vaddudm 6, 6, 22 ++ vaddudm 7, 7, 23 ++ vaddudm 8, 8, 24 ++ ++ # Smash 4 message blocks into 5 vectors of [m4, m2, m3, m1] ++ vmrgow 4, 9, 4 ++ vmrgow 5, 10, 5 ++ vmrgow 6, 11, 6 ++ vmrgow 7, 12, 7 ++ vmrgow 8, 13, 8 ++ vaddudm 8, 8, 19 ++ ++ addi 5, 5, -64 ++ addi 21, 21, 64 ++ ++ bdnz loop_4blocks ++ ++ xxlor 58, 0, 0 ++ xxlor 59, 1, 1 ++ xxlor 60, 2, 2 ++ xxlor 61, 3, 3 ++ xxlor 62, 4, 4 ++ xxlor 32, 5, 5 ++ xxlor 33, 6, 6 ++ xxlor 34, 7, 7 ++ xxlor 35, 8, 8 ++ ++ # Multiply odd words and even words ++ mul_odd ++ mul_even ++ ++ # Sum the products. ++ xxpermdi 41, 31, 46, 0 ++ xxpermdi 42, 31, 47, 0 ++ vaddudm 4, 14, 9 ++ xxpermdi 36, 31, 36, 3 ++ vaddudm 5, 15, 10 ++ xxpermdi 37, 31, 37, 3 ++ xxpermdi 43, 31, 48, 0 ++ vaddudm 6, 16, 11 ++ xxpermdi 38, 31, 38, 3 ++ xxpermdi 44, 31, 49, 0 ++ vaddudm 7, 17, 12 ++ xxpermdi 39, 31, 39, 3 ++ xxpermdi 45, 31, 50, 0 ++ vaddudm 8, 18, 13 ++ xxpermdi 40, 31, 40, 3 ++ ++ # carry reduction ++ vspltisb 9, 2 ++ vsrd 10, 4, 31 ++ vsrd 11, 7, 31 ++ vand 7, 7, 25 ++ vand 4, 4, 25 ++ vaddudm 8, 8, 11 ++ vsrd 12, 8, 31 ++ vaddudm 5, 5, 10 ++ ++ vsrd 11, 5, 31 ++ vand 8, 8, 25 ++ vand 5, 5, 25 ++ vaddudm 4, 4, 12 ++ vsld 10, 12, 9 ++ vaddudm 6, 6, 11 ++ ++ vsrd 13, 6, 31 ++ vand 6, 6, 25 ++ vaddudm 4, 4, 10 ++ vsrd 10, 4, 31 ++ vaddudm 7, 7, 13 ++ ++ vsrd 11, 7, 31 ++ vand 7, 7, 25 ++ vand 4, 4, 25 ++ vaddudm 5, 5, 10 ++ vaddudm 8, 8, 11 ++ ++ b do_final_update ++ ++do_final_update: ++ # v4, v5, v6, v7 and v8 are 26 bit vectors ++ vsld 5, 5, 31 ++ vor 20, 4, 5 ++ vspltisb 11, 12 ++ vsrd 12, 6, 11 ++ vsld 6, 6, 31 ++ vsld 6, 6, 31 ++ vor 20, 20, 6 ++ vspltisb 11, 14 ++ vsld 7, 7, 11 ++ vor 21, 7, 12 ++ mfvsrld 16, 40 # save last 2 bytes ++ vsld 8, 8, 11 ++ vsld 8, 8, 31 ++ vor 21, 21, 8 ++ mfvsrld 17, 52 ++ mfvsrld 19, 53 ++ srdi 16, 16, 24 ++ ++ std 17, 32(3) ++ std 19, 40(3) ++ stw 16, 48(3) ++ ++Out_loop: ++ li 3, 0 ++ ++ li 14, 256 ++ lvx 20, 14, 1 ++ addi 14, 14, 16 ++ lvx 21, 14, 1 ++ addi 14, 14, 16 ++ lvx 22, 14, 1 ++ addi 14, 14, 16 ++ lvx 23, 14, 1 ++ addi 14, 14, 16 ++ lvx 24, 14, 1 ++ addi 14, 14, 16 ++ lvx 25, 14, 1 ++ addi 14, 14, 16 ++ lvx 26, 14, 1 ++ addi 14, 14, 16 ++ lvx 27, 14, 1 ++ addi 14, 14, 16 ++ lvx 28, 14, 1 ++ addi 14, 14, 16 ++ lvx 29, 14, 1 ++ addi 14, 14, 16 ++ lvx 30, 14, 1 ++ addi 14, 14, 16 ++ lvx 31, 14, 1 ++ ++ addi 14, 14, 16 ++ lxvx 14, 14, 1 ++ addi 14, 14, 16 ++ lxvx 15, 14, 1 ++ addi 14, 14, 16 ++ lxvx 16, 14, 1 ++ addi 14, 14, 16 ++ lxvx 17, 14, 1 ++ addi 14, 14, 16 ++ lxvx 18, 14, 1 ++ addi 14, 14, 16 ++ lxvx 19, 14, 1 ++ addi 14, 14, 16 ++ lxvx 20, 14, 1 ++ addi 14, 14, 16 ++ lxvx 21, 14, 1 ++ addi 14, 14, 16 ++ lxvx 22, 14, 1 ++ addi 14, 14, 16 ++ lxvx 23, 14, 1 ++ addi 14, 14, 16 ++ lxvx 24, 14, 1 ++ addi 14, 14, 16 ++ lxvx 25, 14, 1 ++ addi 14, 14, 16 ++ lxvx 26, 14, 1 ++ addi 14, 14, 16 ++ lxvx 27, 14, 1 ++ addi 14, 14, 16 ++ lxvx 28, 14, 1 ++ addi 14, 14, 16 ++ lxvx 29, 14, 1 ++ addi 14, 14, 16 ++ lxvx 30, 14, 1 ++ addi 14, 14, 16 ++ lxvx 31, 14, 1 ++ ++ ld 0, 1040(1) ++ ld 14,112(1) ++ ld 15,120(1) ++ ld 16,128(1) ++ ld 17,136(1) ++ ld 18,144(1) ++ ld 19,152(1) ++ ld 20,160(1) ++ ld 21,168(1) ++ ld 31,248(1) ++ ++ mtlr 0 ++ addi 1, 1, 1024 ++ blr ++ ++Out_no_poly1305: ++ li 3, 0 ++ blr ++ ++.data ++.align 5 ++rmask: ++.byte 0xff, 0xff, 0xff, 0x0f, 0xfc, 0xff, 0xff, 0x0f, 0xfc, 0xff, 0xff, 0x0f, 0xfc, 0xff, 0xff, 0x0f ++cnum: ++.long 0x03ffffff, 0x00000000, 0x03ffffff, 0x00000000 ++.long 0x1a, 0x00, 0x1a, 0x00 ++.long 0x01000000, 0x01000000, 0x01000000, 0x01000000 ++.long 0x00010203, 0x04050607, 0x10111213, 0x14151617 ++.long 0x08090a0b, 0x0c0d0e0f, 0x18191a1b, 0x1c1d1e1f ++.long 0x05, 0x00, 0x00, 0x00 ++.long 0x02020202, 0x02020202, 0x02020202, 0x02020202 ++.long 0xffffffff, 0xffffffff, 0x00000000, 0x00000000 +Index: libgcrypt-1.10.2/cipher/poly1305.c +=================================================================== +--- libgcrypt-1.10.2.orig/cipher/poly1305.c ++++ libgcrypt-1.10.2/cipher/poly1305.c +@@ -78,11 +78,23 @@ poly1305_blocks (poly1305_context_t *ctx + #endif /* USE_S390X_ASM */ + + ++#ifdef POLY1305_USE_PPC_VEC ++ ++extern unsigned int ++gcry_poly1305_p10le_4blocks(unsigned char *key, const byte *m, size_t len); ++ ++#endif /* POLY1305_USE_PPC_VEC */ ++ ++ + static void poly1305_init (poly1305_context_t *ctx, + const byte key[POLY1305_KEYLEN]) + { + POLY1305_STATE *st = &ctx->state; + ++#ifdef POLY1305_USE_PPC_VEC ++ ctx->use_p10 = (_gcry_get_hw_features () & HWF_PPC_ARCH_3_10) != 0; ++#endif ++ + ctx->leftover = 0; + + st->h[0] = 0; +@@ -533,6 +545,7 @@ _gcry_poly1305_update_burn (poly1305_con + size_t bytes) + { + unsigned int burn = 0; ++ unsigned int nburn; + + /* handle leftover */ + if (ctx->leftover) +@@ -546,15 +559,31 @@ _gcry_poly1305_update_burn (poly1305_con + ctx->leftover += want; + if (ctx->leftover < POLY1305_BLOCKSIZE) + return 0; +- burn = poly1305_blocks (ctx, ctx->buffer, POLY1305_BLOCKSIZE, 1); ++ nburn = poly1305_blocks (ctx, ctx->buffer, POLY1305_BLOCKSIZE, 1); ++ burn = nburn > burn ? nburn : burn; + ctx->leftover = 0; + } + ++#ifdef POLY1305_USE_PPC_VEC ++ /* PPC-P10/little-endian: bulk process multiples of eight blocks */ ++ if (ctx->use_p10 && bytes >= POLY1305_BLOCKSIZE * 8) ++ { ++ size_t nblks = bytes / (POLY1305_BLOCKSIZE * 8); ++ size_t len = nblks * (POLY1305_BLOCKSIZE * 8); ++ POLY1305_STATE *st = &ctx->state; ++ nburn = gcry_poly1305_p10le_4blocks ((unsigned char *) st, m, len); ++ burn = nburn > burn ? nburn : burn; ++ m += len; ++ bytes -= len; ++ } ++#endif /* POLY1305_USE_PPC_VEC */ ++ + /* process full blocks */ + if (bytes >= POLY1305_BLOCKSIZE) + { + size_t nblks = bytes / POLY1305_BLOCKSIZE; +- burn = poly1305_blocks (ctx, m, nblks * POLY1305_BLOCKSIZE, 1); ++ nburn = poly1305_blocks (ctx, m, nblks * POLY1305_BLOCKSIZE, 1); ++ burn = nburn > burn ? nburn : burn; + m += nblks * POLY1305_BLOCKSIZE; + bytes -= nblks * POLY1305_BLOCKSIZE; + } +Index: libgcrypt-1.10.2/configure.ac +=================================================================== +--- libgcrypt-1.10.2.orig/configure.ac ++++ libgcrypt-1.10.2/configure.ac +@@ -2779,6 +2779,11 @@ if test "$found" = "1" ; then + powerpc64le-*-*) + # Build with the ppc8 vector implementation + GCRYPT_ASM_CIPHERS="$GCRYPT_ASM_CIPHERS chacha20-ppc.lo" ++ # Build with the assembly implementation ++ if test "$gcry_cv_gcc_inline_asm_ppc_altivec" = "yes" && ++ test "$gcry_cv_gcc_inline_asm_ppc_arch_3_00" = "yes" ; then ++ GCRYPT_ASM_CIPHERS="$GCRYPT_ASM_CIPHERS chacha20-p10le-8x.lo" ++ fi + ;; + powerpc64-*-*) + # Build with the ppc8 vector implementation +@@ -3117,6 +3122,13 @@ case "${host}" in + s390x-*-*) + GCRYPT_ASM_DIGESTS="$GCRYPT_ASM_DIGESTS poly1305-s390x.lo" + ;; ++ powerpc64le-*-*) ++ # Build with the assembly implementation ++ if test "$gcry_cv_gcc_inline_asm_ppc_altivec" = "yes" && ++ test "$gcry_cv_gcc_inline_asm_ppc_arch_3_00" = "yes" ; then ++ GCRYPT_ASM_DIGESTS="$GCRYPT_ASM_DIGESTS poly1305-p10le.lo" ++ fi ++ ;; + esac + + LIST_MEMBER(scrypt, $enabled_kdfs) diff --git a/libgcrypt-Disable-SHA3-s390x-acceleration-for-CSHAKE.patch b/libgcrypt-Disable-SHA3-s390x-acceleration-for-CSHAKE.patch new file mode 100644 index 0000000..ee40bc2 --- /dev/null +++ b/libgcrypt-Disable-SHA3-s390x-acceleration-for-CSHAKE.patch @@ -0,0 +1,61 @@ +From 2486d9b5ae015c1786cb84466a751da4bc0d7122 Mon Sep 17 00:00:00 2001 +From: Jussi Kivilinna +Date: Thu, 20 Jun 2024 20:10:09 +0300 +Subject: Disable SHA3 s390x acceleration for CSHAKE + +* cipher/keccak.c (keccak_final_s390x): Add assert check for +expected SHAKE suffix. +(_gcry_cshake_customize, cshake_hash_buffers): Disable s390x +acceleration when selecting CSHAKE suffix. +-- + +Signed-off-by: Jussi Kivilinna + +diff --git a/cipher/keccak.c b/cipher/keccak.c +index aaf83a62..44cc9f71 100644 +--- a/cipher/keccak.c ++++ b/cipher/keccak.c +@@ -745,6 +745,8 @@ keccak_final_s390x (void *context) + } + else + { ++ gcry_assert(ctx->suffix == SHAKE_DELIMITED_SUFFIX); ++ + klmd_shake_execute (ctx->kimd_func, &ctx->state, NULL, 0, ctx->buf, + ctx->count); + ctx->count = 0; +@@ -1497,9 +1499,14 @@ _gcry_cshake_customize (void *context, struct gcry_cshake_customization *p) + /* No customization */ + return 0; + ++ ctx->suffix = CSHAKE_DELIMITED_SUFFIX; ++#ifdef USE_S390X_CRYPTO ++ /* CSHAKE suffix is not supported by s390x/kimd. */ ++ ctx->kimd_func = 0; ++#endif ++ + len_written = cshake_input_n (ctx, p->n, p->n_len); + cshake_input_s (ctx, p->s, p->s_len, len_written); +- ctx->suffix = CSHAKE_DELIMITED_SUFFIX; + return 0; + } + +@@ -1536,9 +1543,14 @@ cshake_hash_buffers (const gcry_md_spec_t *spec, void *outbuf, size_t nbytes, + size_t s_len = iov[1].len; + size_t len; + ++ ctx.suffix = CSHAKE_DELIMITED_SUFFIX; ++#ifdef USE_S390X_CRYPTO ++ /* CSHAKE suffix is not supported by s390x/kimd. */ ++ ctx.kimd_func = 0; ++#endif ++ + len = cshake_input_n (&ctx, n, n_len); + cshake_input_s (&ctx, s, s_len, len); +- ctx.suffix = CSHAKE_DELIMITED_SUFFIX; + } + iovcnt -= 2; + iov += 2; +-- +2.49.0 + diff --git a/libgcrypt-FIPS-SLI-hash-mac.patch b/libgcrypt-FIPS-SLI-hash-mac.patch new file mode 100644 index 0000000..f0f56f2 --- /dev/null +++ b/libgcrypt-FIPS-SLI-hash-mac.patch @@ -0,0 +1,172 @@ +Index: libgcrypt-1.11.0/doc/gcrypt.texi +=================================================================== +--- libgcrypt-1.11.0.orig/doc/gcrypt.texi ++++ libgcrypt-1.11.0/doc/gcrypt.texi +@@ -998,13 +998,21 @@ certification. If the function is approv + @code{GPG_ERR_NO_ERROR} (other restrictions might still apply). + Otherwise @code{GPG_ERR_NOT_SUPPORTED} is returned. + +-@item GCRYCTL_FIPS_SERVICE_INDICATOR_MAC; Arguments: enum gcry_mac_algos ++@item GCRYCTL_FIPS_SERVICE_INDICATOR_HASH; Arguments: enum gcry_md_algos + +-Check if the given MAC is approved under the current FIPS 140-3 +-certification. If the MAC is approved, this function returns +-@code{GPG_ERR_NO_ERROR}. Otherwise @code{GPG_ERR_NOT_SUPPORTED} ++Check if the given HASH is approved under the current FIPS 140-3 ++certification. If the HASH is approved, this function returns ++@code{GPS_ERR_NO_ERROR}. Otherwise @code{GPG_ERR_NOT_SUPPORTED} + is returned. + ++@item GCRYCTL_FIPS_SERVICE_INDICATOR_MAC; Arguments: enum gcry_mac_algos [, unsigned int] ++ ++Check if the given MAC is approved under the current FIPS 140-3 ++certification. The second parameter provides the keylen (if the ++algorithm supports different key sizes). If the MAC is approved, ++this function returns @code{GPS_ERR_NO_ERROR}. Otherwise ++@code{GPG_ERR_NOT_SUPPORTED} is returned. ++ + @item GCRYCTL_FIPS_SERVICE_INDICATOR_MD; Arguments: enum gcry_md_algos + + Check if the given message digest algorithm is approved under the current +Index: libgcrypt-1.11.0/src/fips.c +=================================================================== +--- libgcrypt-1.11.0.orig/src/fips.c ++++ libgcrypt-1.11.0/src/fips.c +@@ -378,31 +378,6 @@ _gcry_fips_indicator_cipher (va_list arg + } + } + +-int +-_gcry_fips_indicator_mac (va_list arg_ptr) +-{ +- enum gcry_mac_algos alg = va_arg (arg_ptr, enum gcry_mac_algos); +- +- switch (alg) +- { +- case GCRY_MAC_CMAC_AES: +- case GCRY_MAC_HMAC_SHA1: +- case GCRY_MAC_HMAC_SHA224: +- case GCRY_MAC_HMAC_SHA256: +- case GCRY_MAC_HMAC_SHA384: +- case GCRY_MAC_HMAC_SHA512: +- case GCRY_MAC_HMAC_SHA512_224: +- case GCRY_MAC_HMAC_SHA512_256: +- case GCRY_MAC_HMAC_SHA3_224: +- case GCRY_MAC_HMAC_SHA3_256: +- case GCRY_MAC_HMAC_SHA3_384: +- case GCRY_MAC_HMAC_SHA3_512: +- return GPG_ERR_NO_ERROR; +- default: +- return GPG_ERR_NOT_SUPPORTED; +- } +-} +- + /* FIPS approved curves, extracted from: + * cipher/ecc-curves.c:curve_aliases[] and domain_parms[]. */ + static const struct +@@ -602,6 +577,62 @@ _gcry_fips_indicator_pk_flags (va_list a + return GPG_ERR_NOT_SUPPORTED; + } + ++int ++_gcry_fips_indicator_hash (va_list arg_ptr) ++{ ++ enum gcry_md_algos alg = va_arg (arg_ptr, enum gcry_md_algos); ++ ++ switch (alg) ++ { ++ case GCRY_MD_SHA1: ++ case GCRY_MD_SHA224: ++ case GCRY_MD_SHA256: ++ case GCRY_MD_SHA384: ++ case GCRY_MD_SHA512: ++ case GCRY_MD_SHA512_224: ++ case GCRY_MD_SHA512_256: ++ case GCRY_MD_SHA3_224: ++ case GCRY_MD_SHA3_256: ++ case GCRY_MD_SHA3_384: ++ case GCRY_MD_SHA3_512: ++ case GCRY_MD_SHAKE128: ++ case GCRY_MD_SHAKE256: ++ return GPG_ERR_NO_ERROR; ++ default: ++ return GPG_ERR_NOT_SUPPORTED; ++ } ++} ++ ++int ++_gcry_fips_indicator_mac (va_list arg_ptr) ++{ ++ enum gcry_mac_algos alg = va_arg (arg_ptr, enum gcry_mac_algos); ++ unsigned int keylen = va_arg (arg_ptr, unsigned int); ++ ++ switch (alg) ++ { ++ case GCRY_MAC_HMAC_SHA1: ++ case GCRY_MAC_HMAC_SHA224: ++ case GCRY_MAC_HMAC_SHA256: ++ case GCRY_MAC_HMAC_SHA384: ++ case GCRY_MAC_HMAC_SHA512: ++ case GCRY_MAC_HMAC_SHA512_224: ++ case GCRY_MAC_HMAC_SHA512_256: ++ case GCRY_MAC_HMAC_SHA3_224: ++ case GCRY_MAC_HMAC_SHA3_256: ++ case GCRY_MAC_HMAC_SHA3_384: ++ case GCRY_MAC_HMAC_SHA3_512: ++ if (keylen >= 112) { ++ return GPG_ERR_NO_ERROR; ++ } ++ case GCRY_MAC_CMAC_AES: ++ if (keylen == 128 || keylen == 192 || keylen == 256) { ++ return GPG_ERR_NO_ERROR; ++ } ++ default: ++ return GPG_ERR_NOT_SUPPORTED; ++ } ++} + + /* This is a test on whether the library is in the error or + operational state. */ +Index: libgcrypt-1.11.0/src/g10lib.h +=================================================================== +--- libgcrypt-1.11.0.orig/src/g10lib.h ++++ libgcrypt-1.11.0/src/g10lib.h +@@ -469,6 +469,7 @@ void _gcry_fips_signal_error (const char + #endif + + int _gcry_fips_indicator_cipher (va_list arg_ptr); ++int _gcry_fips_indicator_hash (va_list arg_ptr); + int _gcry_fips_indicator_mac (va_list arg_ptr); + int _gcry_fips_indicator_md (va_list arg_ptr); + int _gcry_fips_indicator_kdf (va_list arg_ptr); +Index: libgcrypt-1.11.0/src/gcrypt.h.in +=================================================================== +--- libgcrypt-1.11.0.orig/src/gcrypt.h.in ++++ libgcrypt-1.11.0/src/gcrypt.h.in +@@ -336,7 +336,8 @@ enum gcry_ctl_cmds + GCRYCTL_FIPS_SERVICE_INDICATOR_MD = 86, + GCRYCTL_FIPS_SERVICE_INDICATOR_PK_FLAGS = 87, + GCRYCTL_MD_CUSTOMIZE = 88, +- GCRYCTL_FIPS_SERVICE_INDICATOR_PK = 89 ++ GCRYCTL_FIPS_SERVICE_INDICATOR_PK = 89, ++ GCRYCTL_FIPS_SERVICE_INDICATOR_HASH = 90 + }; + + /* Perform various operations defined by CMD. */ +Index: libgcrypt-1.11.0/src/global.c +=================================================================== +--- libgcrypt-1.11.0.orig/src/global.c ++++ libgcrypt-1.11.0/src/global.c +@@ -794,6 +794,12 @@ _gcry_vcontrol (enum gcry_ctl_cmds cmd, + rc = _gcry_fips_indicator_cipher (arg_ptr); + break; + ++ case GCRYCTL_FIPS_SERVICE_INDICATOR_HASH: ++ /* Get FIPS Service Indicator for a given HASH. Returns GPG_ERR_NO_ERROR ++ * if algorithm is allowed or GPG_ERR_NOT_SUPPORTED otherwise */ ++ rc = _gcry_fips_indicator_hash (arg_ptr); ++ break; ++ + case GCRYCTL_FIPS_SERVICE_INDICATOR_MAC: + /* Get FIPS Service Indicator for a given message authentication code. + * Returns GPG_ERR_NO_ERROR if algorithm is allowed or diff --git a/libgcrypt-FIPS-SLI-kdf-leylength.patch b/libgcrypt-FIPS-SLI-kdf-leylength.patch new file mode 100644 index 0000000..d3693ac --- /dev/null +++ b/libgcrypt-FIPS-SLI-kdf-leylength.patch @@ -0,0 +1,60 @@ +Index: libgcrypt-1.11.0/src/fips.c +=================================================================== +--- libgcrypt-1.11.0.orig/src/fips.c ++++ libgcrypt-1.11.0/src/fips.c +@@ -523,10 +523,15 @@ int + _gcry_fips_indicator_kdf (va_list arg_ptr) + { + enum gcry_kdf_algos alg = va_arg (arg_ptr, enum gcry_kdf_algos); ++ unsigned int keylen = 0; + + switch (alg) + { + case GCRY_KDF_PBKDF2: ++ keylen = va_arg (arg_ptr, unsigned int); ++ if (keylen < 112) { ++ return GPG_ERR_NOT_SUPPORTED; ++ } + return GPG_ERR_NO_ERROR; + default: + return GPG_ERR_NOT_SUPPORTED; +Index: libgcrypt-1.11.0/doc/gcrypt.texi +=================================================================== +--- libgcrypt-1.11.0.orig/doc/gcrypt.texi ++++ libgcrypt-1.11.0/doc/gcrypt.texi +@@ -983,12 +983,13 @@ is approved under the current FIPS 140-3 + combination is approved, this function returns @code{GPG_ERR_NO_ERROR}. + Otherwise @code{GPG_ERR_NOT_SUPPORTED} is returned. + +-@item GCRYCTL_FIPS_SERVICE_INDICATOR_KDF; Arguments: enum gcry_kdf_algos ++@item GCRYCTL_FIPS_SERVICE_INDICATOR_KDF; Arguments: enum gcry_kdf_algos [, unsigned int] + + Check if the given KDF is approved under the current FIPS 140-3 +-certification. If the KDF is approved, this function returns +-@code{GPG_ERR_NO_ERROR}. Otherwise @code{GPG_ERR_NOT_SUPPORTED} +-is returned. ++certification. The second parameter provides the keylength in bits. ++Keylength values of less that 112 bits are considered non-approved. ++If the KDF is approved, this function returns @code{GPG_ERR_NO_ERROR}. ++Otherwise @code{GPG_ERR_NOT_SUPPORTED} is returned. + + @item GCRYCTL_FIPS_SERVICE_INDICATOR_FUNCTION; Arguments: const char * + +Index: libgcrypt-1.11.0/tests/t-kdf.c +=================================================================== +--- libgcrypt-1.11.0.orig/tests/t-kdf.c ++++ libgcrypt-1.11.0/tests/t-kdf.c +@@ -1889,7 +1889,12 @@ check_fips_indicators (void) + for (i = 0; i < sizeof(kdf_algos) / sizeof(*kdf_algos); i++) + { + int is_fips_kdf_algo = 0; +- gcry_error_t err = gcry_control (GCRYCTL_FIPS_SERVICE_INDICATOR_KDF, kdf_algos[i]); ++ gcry_error_t err; ++ // On SUSE/openSUSE builds PBKDF2 with keysize < 112 is not allowed ++ if (kdf_algos[i] == GCRY_KDF_PBKDF2) ++ err = gcry_control (GCRYCTL_FIPS_SERVICE_INDICATOR_KDF, kdf_algos[i], 112); ++ else ++ err = gcry_control (GCRYCTL_FIPS_SERVICE_INDICATOR_KDF, kdf_algos[i]); + + if (verbose) + fprintf (stderr, "checking FIPS indicator for KDF %d: %s\n", diff --git a/libgcrypt-FIPS-SLI-pk.patch b/libgcrypt-FIPS-SLI-pk.patch new file mode 100644 index 0000000..304fd37 --- /dev/null +++ b/libgcrypt-FIPS-SLI-pk.patch @@ -0,0 +1,177 @@ +Index: libgcrypt-1.11.0/src/fips.c +=================================================================== +--- libgcrypt-1.11.0.orig/src/fips.c ++++ libgcrypt-1.11.0/src/fips.c +@@ -38,6 +38,7 @@ + + #include "g10lib.h" + #include "cipher-proto.h" ++#include "cipher.h" + #include "../random/random.h" + + /* The states of the finite state machine used in fips mode. */ +@@ -400,6 +401,94 @@ _gcry_fips_indicator_mac (va_list arg_pt + default: + return GPG_ERR_NOT_SUPPORTED; + } ++} ++ ++/* FIPS approved curves, extracted from: ++ * cipher/ecc-curves.c:curve_aliases[] and domain_parms[]. */ ++static const struct ++{ ++ const char *name; /* Our name. */ ++ const char *other; /* Other name. */ ++} fips_approved_curve[] = ++ { ++ /* "NIST P-192" is non-approved if FIPS 140-3 */ ++ /* { "NIST P-192", "1.2.840.10045.3.1.1" }, /\* X9.62 OID *\/ */ ++ /* { "NIST P-192", "prime192v1" }, /\* X9.62 name. *\/ */ ++ /* { "NIST P-192", "secp192r1" }, /\* SECP name. *\/ */ ++ /* { "NIST P-192", "nistp192" }, /\* rfc5656. *\/ */ ++ ++ { "NIST P-224", "secp224r1" }, ++ { "NIST P-224", "1.3.132.0.33" }, /* SECP OID. */ ++ { "NIST P-224", "nistp224" }, /* rfc5656. */ ++ ++ { "NIST P-256", "1.2.840.10045.3.1.7" }, /* From NIST SP 800-78-1. */ ++ { "NIST P-256", "prime256v1" }, ++ { "NIST P-256", "secp256r1" }, ++ { "NIST P-256", "nistp256" }, /* rfc5656. */ ++ ++ { "NIST P-384", "secp384r1" }, ++ { "NIST P-384", "1.3.132.0.34" }, ++ { "NIST P-384", "nistp384" }, /* rfc5656. */ ++ ++ { "NIST P-521", "secp521r1" }, ++ { "NIST P-521", "1.3.132.0.35" }, ++ { "NIST P-521", "nistp521" }, /* rfc5656. */ ++ { NULL, NULL} ++ }; ++ ++enum pk_operation convert_from_pk_usage(unsigned int pk_usage) ++{ ++ switch (pk_usage) ++ { ++ case GCRY_PK_USAGE_SIGN: ++ return PUBKEY_OP_SIGN; ++ case GCRY_PK_USAGE_ENCR: ++ return PUBKEY_OP_ENCRYPT; ++ default: ++ return PUBKEY_OP_DECRYPT; ++ } ++} ++ ++int ++_gcry_fips_indicator_pk (va_list arg_ptr) ++{ ++ enum gcry_pk_algos alg = va_arg (arg_ptr, enum gcry_pk_algos); ++ enum pk_operation oper; ++ unsigned int keylen; ++ const char *curve_name; ++ ++ switch (alg) ++ { ++ case GCRY_PK_RSA: ++ case GCRY_PK_RSA_E: ++ case GCRY_PK_RSA_S: ++ oper = convert_from_pk_usage(va_arg (arg_ptr, unsigned int)); ++ switch (oper) ++ { ++ case PUBKEY_OP_ENCRYPT: ++ case PUBKEY_OP_DECRYPT: ++ return GPG_ERR_NOT_SUPPORTED; ++ default: ++ keylen = va_arg (arg_ptr, unsigned int); ++ if (keylen < 2048) ++ return GPG_ERR_NOT_SUPPORTED; ++ return GPG_ERR_NO_ERROR; ++ } ++ case GCRY_PK_ECC: ++ case GCRY_PK_ECDH: ++ case GCRY_PK_ECDSA: ++ curve_name = va_arg (arg_ptr, const char *); ++ for (int idx = 0; fips_approved_curve[idx].name; ++idx) ++ { ++ /* Check for the usual name and an alias. */ ++ if (!strcmp (curve_name, fips_approved_curve[idx].name) || ++ !strcmp (curve_name, fips_approved_curve[idx].other)) ++ return GPG_ERR_NO_ERROR; ++ } ++ return GPG_ERR_NOT_SUPPORTED; ++ default: ++ return GPG_ERR_NOT_SUPPORTED; ++ } + } + + int +Index: libgcrypt-1.11.0/src/gcrypt.h.in +=================================================================== +--- libgcrypt-1.11.0.orig/src/gcrypt.h.in ++++ libgcrypt-1.11.0/src/gcrypt.h.in +@@ -335,7 +335,8 @@ enum gcry_ctl_cmds + GCRYCTL_FIPS_SERVICE_INDICATOR_MAC = 85, + GCRYCTL_FIPS_SERVICE_INDICATOR_MD = 86, + GCRYCTL_FIPS_SERVICE_INDICATOR_PK_FLAGS = 87, +- GCRYCTL_MD_CUSTOMIZE = 88 ++ GCRYCTL_MD_CUSTOMIZE = 88, ++ GCRYCTL_FIPS_SERVICE_INDICATOR_PK = 89 + }; + + /* Perform various operations defined by CMD. */ +Index: libgcrypt-1.11.0/doc/gcrypt.texi +=================================================================== +--- libgcrypt-1.11.0.orig/doc/gcrypt.texi ++++ libgcrypt-1.11.0/doc/gcrypt.texi +@@ -1010,6 +1010,19 @@ Check if the given message digest algori + FIPS 140-3 certification. If the algorithm is approved, this function returns + @code{GPG_ERR_NO_ERROR}. Otherwise @code{GPG_ERR_NOT_SUPPORTED} is returned. + ++@item GCRYCTL_FIPS_SERVICE_INDICATOR_PK; Arguments: enum gcry_pk_algos [, constantsGCRY_PK_USAGE_ENCR or GCRY_PK_USAGE_SIGN, unsigned int (only for GCRY_PK_RSA)] [, const char * (only for GCRY_PK_ECC, GCRY_PK_ECDH or GCRY_PK_ECDSA)] ++ ++Check if the given asymmetric cipher is approved under the current ++FIPS 140-3 certification. For GCRY_PK_RSA, two additional parameter ++are required: first describes the purpose of the algorithm through one ++of the constants (GCRY_PK_USAGE_ENCR for encryption or decryption ++operations; GCRY_PK_USAGE_SIGN for sign or verify operations). Second ++one is the key length. For GCRY_PK_ECC, GCRY_PK_ECDH and ++GCRY_PK_ECDSA, only a single parameter is needed: the curve name or ++its alias as @code{const char *}. If the combination is approved, this ++function returns @code{GPG_ERR_NO_ERROR}. Otherwise ++@code{GPG_ERR_NOT_SUPPORTED} is returned. ++ + @item GCRYCTL_FIPS_SERVICE_INDICATOR_PK_FLAGS; Arguments: const char * + + Check if the given public key operation flag or s-expression object name is +Index: libgcrypt-1.11.0/src/g10lib.h +=================================================================== +--- libgcrypt-1.11.0.orig/src/g10lib.h ++++ libgcrypt-1.11.0/src/g10lib.h +@@ -473,6 +473,7 @@ int _gcry_fips_indicator_mac (va_list ar + int _gcry_fips_indicator_md (va_list arg_ptr); + int _gcry_fips_indicator_kdf (va_list arg_ptr); + int _gcry_fips_indicator_function (va_list arg_ptr); ++int _gcry_fips_indicator_pk (va_list arg_ptr); + int _gcry_fips_indicator_pk_flags (va_list arg_ptr); + + int _gcry_fips_is_operational (void); +Index: libgcrypt-1.11.0/src/global.c +=================================================================== +--- libgcrypt-1.11.0.orig/src/global.c ++++ libgcrypt-1.11.0/src/global.c +@@ -828,6 +828,15 @@ _gcry_vcontrol (enum gcry_ctl_cmds cmd, + rc = _gcry_fips_indicator_pk_flags (arg_ptr); + break; + ++ case GCRYCTL_FIPS_SERVICE_INDICATOR_PK: ++ /* Get FIPS Service Indicator for a given asymmetric algorithm. For ++ * GCRY_PK_RSA, an additional parameter for the operation mode is ++ * required. For ECC, ECDH and ECDSA, the additional parameter is the ++ * curve name or its alias. Returns GPG_ERR_NO_ERROR if the ++ * algorithm is allowed or GPG_ERR_NOT_SUPPORTED otherwise. */ ++ rc = _gcry_fips_indicator_pk (arg_ptr); ++ break; ++ + case PRIV_CTL_INIT_EXTRNG_TEST: /* Init external random test. */ + rc = GPG_ERR_NOT_SUPPORTED; + break; diff --git a/libgcrypt-FIPS-jitter-errorcodes.patch b/libgcrypt-FIPS-jitter-errorcodes.patch new file mode 100644 index 0000000..d6d314e --- /dev/null +++ b/libgcrypt-FIPS-jitter-errorcodes.patch @@ -0,0 +1,16 @@ +Index: libgcrypt-1.10.3/random/rndjent.c +=================================================================== +--- libgcrypt-1.10.3.orig/random/rndjent.c ++++ libgcrypt-1.10.3/random/rndjent.c +@@ -319,7 +319,10 @@ _gcry_rndjent_poll (void (*add)(const vo + jent_rng_totalcalls++; + rc = jent_read_entropy_safe (&jent_rng_collector, buffer, n); + if (rc < 0) +- break; ++ { ++ fips_signal_error ("jitter entropy failed"); ++ break; ++ } + /* We need to hash the output to conform to the BSI + * NTG.1 specs. */ + _gcry_md_hash_buffer (GCRY_MD_SHA256, buffer, buffer, rc); diff --git a/libgcrypt-FIPS-jitter-standalone.patch b/libgcrypt-FIPS-jitter-standalone.patch new file mode 100644 index 0000000..4f931c3 --- /dev/null +++ b/libgcrypt-FIPS-jitter-standalone.patch @@ -0,0 +1,183 @@ +Index: libgcrypt-1.10.3/random/Makefile.am +=================================================================== +--- libgcrypt-1.10.3.orig/random/Makefile.am ++++ libgcrypt-1.10.3/random/Makefile.am +@@ -21,7 +21,7 @@ + # Need to include ../src in addition to top_srcdir because gcrypt.h is + # a built header. + AM_CPPFLAGS = -I../src -I$(top_srcdir)/src +-AM_CFLAGS = $(GPG_ERROR_CFLAGS) ++AM_CFLAGS = $(GPG_ERROR_CFLAGS) -ljitterentropy + + noinst_LTLIBRARIES = librandom.la + +@@ -45,14 +45,7 @@ rndoldlinux.c \ + rndegd.c \ + rndunix.c \ + rndw32.c \ +-rndw32ce.c \ +-jitterentropy-gcd.c jitterentropy-gcd.h \ +-jitterentropy-health.c jitterentropy-health.h \ +-jitterentropy-noise.c jitterentropy-noise.h \ +-jitterentropy-sha3.c jitterentropy-sha3.h \ +-jitterentropy-timer.c jitterentropy-timer.h \ +-jitterentropy-base.h \ +-jitterentropy-base.c jitterentropy.h jitterentropy-base-user.h ++rndw32ce.c + + # The rndjent module needs to be compiled without optimization. */ + if ENABLE_O_FLAG_MUNGING +@@ -61,20 +54,8 @@ else + o_flag_munging = cat + endif + +-rndjent.o: $(srcdir)/rndjent.c jitterentropy-base-user.h \ +- $(srcdir)/jitterentropy-gcd.c $(srcdir)/jitterentropy-gcd.h \ +- $(srcdir)/jitterentropy-health.c $(srcdir)/jitterentropy-health.h \ +- $(srcdir)/jitterentropy-noise.c $(srcdir)/jitterentropy-noise.h \ +- $(srcdir)/jitterentropy-sha3.c $(srcdir)/jitterentropy-sha3.h \ +- $(srcdir)/jitterentropy-timer.c $(srcdir)/jitterentropy-timer.h \ +- $(srcdir)/jitterentropy-base.c $(srcdir)/jitterentropy.h ++rndjent.o: $(srcdir)/rndjent.c + `echo $(COMPILE) -c $(srcdir)/rndjent.c | $(o_flag_munging) ` + +-rndjent.lo: $(srcdir)/rndjent.c jitterentropy-base-user.h \ +- $(srcdir)/jitterentropy-gcd.c $(srcdir)/jitterentropy-gcd.h \ +- $(srcdir)/jitterentropy-health.c $(srcdir)/jitterentropy-health.h \ +- $(srcdir)/jitterentropy-noise.c $(srcdir)/jitterentropy-noise.h \ +- $(srcdir)/jitterentropy-sha3.c $(srcdir)/jitterentropy-sha3.h \ +- $(srcdir)/jitterentropy-timer.c $(srcdir)/jitterentropy-timer.h \ +- $(srcdir)/jitterentropy-base.c $(srcdir)/jitterentropy.h ++rndjent.lo: $(srcdir)/rndjent.c + `echo $(LTCOMPILE) -c $(srcdir)/rndjent.c | $(o_flag_munging) ` +Index: libgcrypt-1.10.3/random/rndjent.c +=================================================================== +--- libgcrypt-1.10.3.orig/random/rndjent.c ++++ libgcrypt-1.10.3/random/rndjent.c +@@ -94,17 +94,12 @@ + * jitterentropy-user-base.h file. */ + + /* Tell jitterentropy* that all functions shall be static. */ +-#define JENT_PRIVATE_COMPILE 1 ++#undef JENT_PRIVATE_COMPILE + +-#include "jitterentropy-base.c" + #ifdef JENT_CONF_ENABLE_INTERNAL_TIMER + #include + #endif /* JENT_CONF_ENABLE_INTERNAL_TIMER */ +-#include "jitterentropy-gcd.c" +-#include "jitterentropy-health.c" +-#include "jitterentropy-noise.c" +-#include "jitterentropy-sha3.c" +-#include "jitterentropy-timer.c" ++#include + + /* This is the lock we use to serialize access to this RNG. The extra + * integer variable is only used to check the locking state; that is, +Index: libgcrypt-1.10.3/random/Makefile.in +=================================================================== +--- libgcrypt-1.10.3.orig/random/Makefile.in ++++ libgcrypt-1.10.3/random/Makefile.in +@@ -147,12 +147,7 @@ am__v_at_1 = + DEFAULT_INCLUDES = -I.@am__isrc@ -I$(top_builddir) + depcomp = $(SHELL) $(top_srcdir)/build-aux/depcomp + am__maybe_remake_depfiles = depfiles +-am__depfiles_remade = ./$(DEPDIR)/jitterentropy-base.Plo \ +- ./$(DEPDIR)/jitterentropy-gcd.Plo \ +- ./$(DEPDIR)/jitterentropy-health.Plo \ +- ./$(DEPDIR)/jitterentropy-noise.Plo \ +- ./$(DEPDIR)/jitterentropy-sha3.Plo \ +- ./$(DEPDIR)/jitterentropy-timer.Plo \ ++am__depfiles_remade = \ + ./$(DEPDIR)/random-csprng.Plo ./$(DEPDIR)/random-drbg.Plo \ + ./$(DEPDIR)/random-system.Plo ./$(DEPDIR)/random.Plo \ + ./$(DEPDIR)/rndegd.Plo ./$(DEPDIR)/rndgetentropy.Plo \ +@@ -378,7 +373,7 @@ top_srcdir = @top_srcdir@ + # Need to include ../src in addition to top_srcdir because gcrypt.h is + # a built header. + AM_CPPFLAGS = -I../src -I$(top_srcdir)/src +-AM_CFLAGS = $(GPG_ERROR_CFLAGS) ++AM_CFLAGS = $(GPG_ERROR_CFLAGS) -ljitterentropy + noinst_LTLIBRARIES = librandom.la + GCRYPT_MODULES = @GCRYPT_RANDOM@ + librandom_la_DEPENDENCIES = $(GCRYPT_MODULES) +@@ -398,14 +393,7 @@ rndoldlinux.c \ + rndegd.c \ + rndunix.c \ + rndw32.c \ +-rndw32ce.c \ +-jitterentropy-gcd.c jitterentropy-gcd.h \ +-jitterentropy-health.c jitterentropy-health.h \ +-jitterentropy-noise.c jitterentropy-noise.h \ +-jitterentropy-sha3.c jitterentropy-sha3.h \ +-jitterentropy-timer.c jitterentropy-timer.h \ +-jitterentropy-base.h \ +-jitterentropy-base.c jitterentropy.h jitterentropy-base-user.h ++rndw32ce.c + + @ENABLE_O_FLAG_MUNGING_FALSE@o_flag_munging = cat + +@@ -465,12 +453,6 @@ mostlyclean-compile: + distclean-compile: + -rm -f *.tab.c + +-@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/jitterentropy-base.Plo@am__quote@ # am--include-marker +-@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/jitterentropy-gcd.Plo@am__quote@ # am--include-marker +-@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/jitterentropy-health.Plo@am__quote@ # am--include-marker +-@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/jitterentropy-noise.Plo@am__quote@ # am--include-marker +-@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/jitterentropy-sha3.Plo@am__quote@ # am--include-marker +-@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/jitterentropy-timer.Plo@am__quote@ # am--include-marker + @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/random-csprng.Plo@am__quote@ # am--include-marker + @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/random-drbg.Plo@am__quote@ # am--include-marker + @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/random-system.Plo@am__quote@ # am--include-marker +@@ -641,12 +623,6 @@ clean-am: clean-generic clean-libtool cl + mostlyclean-am + + distclean: distclean-am +- -rm -f ./$(DEPDIR)/jitterentropy-base.Plo +- -rm -f ./$(DEPDIR)/jitterentropy-gcd.Plo +- -rm -f ./$(DEPDIR)/jitterentropy-health.Plo +- -rm -f ./$(DEPDIR)/jitterentropy-noise.Plo +- -rm -f ./$(DEPDIR)/jitterentropy-sha3.Plo +- -rm -f ./$(DEPDIR)/jitterentropy-timer.Plo + -rm -f ./$(DEPDIR)/random-csprng.Plo + -rm -f ./$(DEPDIR)/random-drbg.Plo + -rm -f ./$(DEPDIR)/random-system.Plo +@@ -704,12 +680,6 @@ install-ps-am: + installcheck-am: + + maintainer-clean: maintainer-clean-am +- -rm -f ./$(DEPDIR)/jitterentropy-base.Plo +- -rm -f ./$(DEPDIR)/jitterentropy-gcd.Plo +- -rm -f ./$(DEPDIR)/jitterentropy-health.Plo +- -rm -f ./$(DEPDIR)/jitterentropy-noise.Plo +- -rm -f ./$(DEPDIR)/jitterentropy-sha3.Plo +- -rm -f ./$(DEPDIR)/jitterentropy-timer.Plo + -rm -f ./$(DEPDIR)/random-csprng.Plo + -rm -f ./$(DEPDIR)/random-drbg.Plo + -rm -f ./$(DEPDIR)/random-system.Plo +@@ -759,22 +729,10 @@ uninstall-am: + .PRECIOUS: Makefile + + +-rndjent.o: $(srcdir)/rndjent.c jitterentropy-base-user.h \ +- $(srcdir)/jitterentropy-gcd.c $(srcdir)/jitterentropy-gcd.h \ +- $(srcdir)/jitterentropy-health.c $(srcdir)/jitterentropy-health.h \ +- $(srcdir)/jitterentropy-noise.c $(srcdir)/jitterentropy-noise.h \ +- $(srcdir)/jitterentropy-sha3.c $(srcdir)/jitterentropy-sha3.h \ +- $(srcdir)/jitterentropy-timer.c $(srcdir)/jitterentropy-timer.h \ +- $(srcdir)/jitterentropy-base.c $(srcdir)/jitterentropy.h ++rndjent.o: $(srcdir)/rndjent.c + `echo $(COMPILE) -c $(srcdir)/rndjent.c | $(o_flag_munging) ` + +-rndjent.lo: $(srcdir)/rndjent.c jitterentropy-base-user.h \ +- $(srcdir)/jitterentropy-gcd.c $(srcdir)/jitterentropy-gcd.h \ +- $(srcdir)/jitterentropy-health.c $(srcdir)/jitterentropy-health.h \ +- $(srcdir)/jitterentropy-noise.c $(srcdir)/jitterentropy-noise.h \ +- $(srcdir)/jitterentropy-sha3.c $(srcdir)/jitterentropy-sha3.h \ +- $(srcdir)/jitterentropy-timer.c $(srcdir)/jitterentropy-timer.h \ +- $(srcdir)/jitterentropy-base.c $(srcdir)/jitterentropy.h ++rndjent.lo: $(srcdir)/rndjent.c + `echo $(LTCOMPILE) -c $(srcdir)/rndjent.c | $(o_flag_munging) ` + + # Tell versions [3.59,3.63) of GNU make to not export all variables. diff --git a/libgcrypt-FIPS-jitter-whole-entropy.patch b/libgcrypt-FIPS-jitter-whole-entropy.patch new file mode 100644 index 0000000..6c16472 --- /dev/null +++ b/libgcrypt-FIPS-jitter-whole-entropy.patch @@ -0,0 +1,41 @@ +Index: libgcrypt-1.10.3/random/rndgetentropy.c +=================================================================== +--- libgcrypt-1.10.3.orig/random/rndgetentropy.c ++++ libgcrypt-1.10.3/random/rndgetentropy.c +@@ -53,16 +53,30 @@ _gcry_rndgetentropy_gather_random (void + + /* When using a blocking random generator try to get some entropy + * from the jitter based RNG. In this case we take up to 50% of the +- * remaining requested bytes. */ ++ * remaining requested bytes. In FIPS mode, we get all the entropy ++ * from the jitter RNG. */ + if (level >= GCRY_VERY_STRONG_RANDOM) + { + size_t n; + +- n = _gcry_rndjent_poll (add, origin, length/2); +- if (n > length/2) +- n = length/2; +- if (length > 1) +- length -= n; ++ /* In FIPS mode, use the whole length of the entropy buffer from ++ * Jitter RNG */ ++ if (fips_mode ()) ++ { ++ n = _gcry_rndjent_poll (add, origin, length); ++ if (n != length) ++ fips_signal_error ("jitter entropy failed"); ++ else ++ length = 0; ++ } ++ else ++ { ++ n = _gcry_rndjent_poll (add, origin, length/2); ++ if (n > length/2) ++ n = length/2; ++ if (length > 1) ++ length -= n; ++ } + } + + /* Enter the loop. */ diff --git a/libgcrypt-FIPS-rndjent_poll.patch b/libgcrypt-FIPS-rndjent_poll.patch new file mode 100644 index 0000000..f837842 --- /dev/null +++ b/libgcrypt-FIPS-rndjent_poll.patch @@ -0,0 +1,114 @@ +Index: libgcrypt-1.10.0/random/rndoldlinux.c +=================================================================== +--- libgcrypt-1.10.0.orig/random/rndoldlinux.c ++++ libgcrypt-1.10.0/random/rndoldlinux.c +@@ -132,7 +132,7 @@ _gcry_rndoldlinux_gather_random (void (* + volatile pid_t apid; + int fd; + int n; +- byte buffer[768]; ++ byte buffer[256]; + size_t n_hw; + size_t want = length; + size_t last_so_far = 0; +@@ -187,26 +187,43 @@ _gcry_rndoldlinux_gather_random (void (* + my_pid = apid; + } + ++ if (fips_mode()) ++ { ++ if (level >= GCRY_VERY_STRONG_RANDOM) ++ { ++ size_t n; + +- /* First read from a hardware source. Note that _gcry_rndhw_poll_slow lets +- it account only for up to 50% (or 25% for RDRAND) of the requested +- bytes. */ +- n_hw = _gcry_rndhw_poll_slow (add, origin, length); +- if (length > 1) +- length -= n_hw; +- +- /* When using a blocking random generator try to get some entropy +- * from the jitter based RNG. In this case we take up to 50% of the +- * remaining requested bytes. */ +- if (level >= GCRY_VERY_STRONG_RANDOM) +- { +- n_hw = _gcry_rndjent_poll (add, origin, length/2); +- if (n_hw > length/2) +- n_hw = length/2; ++ n = _gcry_rndjent_poll (add, origin, length); ++ if (n == 0) ++ log_fatal ("unexpected error from rndjent: %s\n", ++ strerror (errno)); ++ if (n > length) ++ n = length; ++ if (length > 1) ++ length -= n; ++ } ++ } ++ else ++ { ++ /* First read from a hardware source. Note that _gcry_rndhw_poll_slow lets ++ it account only for up to 50% (or 25% for RDRAND) of the requested ++ bytes. */ ++ n_hw = _gcry_rndhw_poll_slow (add, origin, length); + if (length > 1) + length -= n_hw; +- } + ++ /* When using a blocking random generator try to get some entropy ++ * from the jitter based RNG. In this case we take up to 50% of the ++ * remaining requested bytes. */ ++ if (level >= GCRY_VERY_STRONG_RANDOM) ++ { ++ n_hw = _gcry_rndjent_poll (add, origin, length/2); ++ if (n_hw > length/2) ++ n_hw = length/2; ++ if (length > 1) ++ length -= n_hw; ++ } ++ } + + /* Open the requested device. The first time a device is to be + opened we fail with a fatal error if the device does not exists. +@@ -262,8 +279,6 @@ _gcry_rndoldlinux_gather_random (void (* + do + { + nbytes = length < sizeof(buffer)? length : sizeof(buffer); +- if (nbytes > 256) +- nbytes = 256; + _gcry_pre_syscall (); + ret = getentropy (buffer, nbytes); + _gcry_post_syscall (); +Index: libgcrypt-1.10.0/random/rndjent.c +=================================================================== +--- libgcrypt-1.10.0.orig/random/rndjent.c ++++ libgcrypt-1.10.0/random/rndjent.c +@@ -279,13 +279,24 @@ _gcry_rndjent_poll (void (*add)(const vo + if (!jent_rng_is_initialized) + { + /* Auto-initialize. */ +- jent_rng_is_initialized = 1; + jent_entropy_collector_free (jent_rng_collector); + jent_rng_collector = NULL; + if ( !(_gcry_random_read_conf () & RANDOM_CONF_DISABLE_JENT)) + { +- if (!jent_entropy_init ()) +- jent_rng_collector = jent_entropy_collector_alloc (1, 0); ++ if (!jent_entropy_init_ex (1, 0)) ++ { ++ jent_rng_collector = jent_entropy_collector_alloc (1, 0); ++ jent_rng_is_initialized = 1; ++ } ++ } ++ } ++ ++ if (!jent_rng_collector) ++ { ++ if (!jent_entropy_init_ex (1, 0)) ++ { ++ jent_rng_collector = jent_entropy_collector_alloc (1, 0); ++ jent_rng_is_initialized = 1; + } + } + diff --git a/libgcrypt-Fix-the-previous-change.patch b/libgcrypt-Fix-the-previous-change.patch new file mode 100644 index 0000000..4735528 --- /dev/null +++ b/libgcrypt-Fix-the-previous-change.patch @@ -0,0 +1,45 @@ +From b4eb23dc01a40e13d542fbfc5169dffa7fae5677 Mon Sep 17 00:00:00 2001 +From: NIIBE Yutaka +Date: Thu, 19 Dec 2024 14:16:02 +0900 +Subject: [PATCH 13/19] Fix the previous change. +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* cipher/pubkey.c (_gcry_pk_sign_md): Fix memory leak. +(_gcry_pk_verify_md): Likewise. + +-- + +GnuPG-bug-id: 7338 +Signed-off-by: NIIBE Yutaka +Signed-off-by: Lucas Mülling +--- + cipher/pubkey.c | 4 ++-- + 1 file changed, 2 insertions(+), 2 deletions(-) + +diff --git a/cipher/pubkey.c b/cipher/pubkey.c +index 11bf1ec9..4d7743cc 100644 +--- a/cipher/pubkey.c ++++ b/cipher/pubkey.c +@@ -626,7 +626,7 @@ _gcry_pk_sign_md (gcry_sexp_t *r_sig, const char *tmpl, gcry_md_hd_t hd_orig, + else if (!spec->flags.fips && fips_mode ()) + { + if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) +- return GPG_ERR_PUBKEY_ALGO; ++ rc = GPG_ERR_PUBKEY_ALGO; + else + fips_service_indicator_mark_non_compliant (); + } +@@ -708,7 +708,7 @@ _gcry_pk_verify_md (gcry_sexp_t s_sig, const char *tmpl, gcry_md_hd_t hd_orig, + else if (!spec->flags.fips && fips_mode ()) + { + if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) +- return GPG_ERR_PUBKEY_ALGO; ++ rc = GPG_ERR_PUBKEY_ALGO; + else + fips_service_indicator_mark_non_compliant (); + } +-- +2.49.0 + diff --git a/libgcrypt-build-Improve-__thread-specifier-check.patch b/libgcrypt-build-Improve-__thread-specifier-check.patch new file mode 100644 index 0000000..9167adc --- /dev/null +++ b/libgcrypt-build-Improve-__thread-specifier-check.patch @@ -0,0 +1,41 @@ +From 42e8858566e32080aaf818b168f34c698a9ef084 Mon Sep 17 00:00:00 2001 +From: NIIBE Yutaka +Date: Thu, 9 Jan 2025 10:15:50 +0900 +Subject: [PATCH 1/1] build: Improve __thread specifier check. +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* configure.ac (AC_COMPILE_IFELSE __thread): Move the declaration to +global, referring the variable with (void) in main to avoid an error +buidling with -Werror=unused-variable. Don't need to include +stdlib.h. + +-- + +Reported-by: Lucas Mulling +Signed-off-by: NIIBE Yutaka +Signed-off-by: Lucas Mülling +--- + configure.ac | 5 +++-- + 1 file changed, 3 insertions(+), 2 deletions(-) + +diff --git a/configure.ac b/configure.ac +index d708f89a..f38e20c5 100644 +--- a/configure.ac ++++ b/configure.ac +@@ -1495,8 +1495,9 @@ fi + AC_CACHE_CHECK([whether compiler supports '__thread' storage class specifier], + [gcry_cv_gcc_storage_class__thread], + [gcry_cv_gcc_storage_class__thread=no +- AC_COMPILE_IFELSE([AC_LANG_PROGRAM([#include ], +- [static __thread int bar;] ++ AC_COMPILE_IFELSE([AC_LANG_PROGRAM( ++ [[static __thread int bar;]], ++ [[(void)bar;]] + )], + [gcry_cv_gcc_storage_class__thread=yes])]) + if test "$gcry_cv_gcc_storage_class__thread" = "yes" ; then +-- +2.49.0 + diff --git a/libgcrypt-cipher-Add-KAT-for-non-rfc6979-ECDSA-with-fixed-k.patch b/libgcrypt-cipher-Add-KAT-for-non-rfc6979-ECDSA-with-fixed-k.patch new file mode 100644 index 0000000..ff9ae28 --- /dev/null +++ b/libgcrypt-cipher-Add-KAT-for-non-rfc6979-ECDSA-with-fixed-k.patch @@ -0,0 +1,94 @@ +From be57179f42f8a7cb64f72f73ccea753400573b4f Mon Sep 17 00:00:00 2001 +From: Lucas Mulling via Gcrypt-devel +Date: Wed, 26 Feb 2025 12:29:53 -0300 +Subject: [PATCH 02/14] cipher: Add KAT for non-rfc6979 ECDSA with fixed k +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* cipher/ecc.c (run_selftests): Implement KAT for non-deterministic +ECDSA. +* cipher/ecc. (rfc6979_ecdsa_sample_data, rfc6979_ecdsa_sample_data_bad, +rfc6979_ecdsa_data_tmpl): New. + +Signed-off-by: Lucas Mulling +Signed-off-by: Lucas Mülling +--- + cipher/ecc.c | 40 +++++++++++++++++++++++++++++++++++++--- + 1 file changed, 37 insertions(+), 3 deletions(-) + +diff --git a/cipher/ecc.c b/cipher/ecc.c +index 525523ed..d331a014 100644 +--- a/cipher/ecc.c ++++ b/cipher/ecc.c +@@ -93,23 +93,47 @@ static const char ecdsa_sample_secret_key_secp256[] = + /**/ "7903FE1008B8BC99A41AE9E95628BC64F2F1B20C2D7E9F5177A3C294D4462299#)))"; + + /* Sample data from RFC 6979 section A.2.5, hash is of message "sample" */ +-static const char ecdsa_sample_data[] = ++static const char rfc6979_ecdsa_sample_data[] = + "(data (flags rfc6979 prehash)" + " (hash-algo sha256)" + " (value 6:sample))"; + +-static const char ecdsa_sample_data_bad[] = ++static const char rfc6979_ecdsa_sample_data_bad[] = + "(data (flags rfc6979)" + " (hash sha256 #bf2bdbe1aa9b6ec1e2ade1d694f41fc71a831d0268e98915" + /**/ "62113d8a62add1bf#))"; + ++static const char *rfc6979_ecdsa_data_tmpl = ++ "(data (flags rfc6979)" ++ " (hash %s %b))"; ++ ++/* ++ * Sample data from RFC 6979 section A.2.5, with fixed k, ++ * hash is of message "sample". ++ */ ++static const char ecdsa_sample_data[] = ++ "(data (flags raw prehash)" ++ " (label #A6E3C57DD01ABE90086538398355DD4C3B17AA873382B0F24D6129493D8AAD60#)" ++ " (hash-algo sha256)" ++ " (value 6:sample))"; ++ ++static const char ecdsa_sample_data_bad[] = ++ "(data (flags raw)" ++ " (label #A6E3C57DD01ABE90086538398355DD4C3B17AA873382B0F24D6129493D8AAD60#)" ++ " (hash sha256 #bf2bdbe1aa9b6ec1e2ade1d694f41fc71a831d0268e98915" ++ /**/ "62113d8a62add1bf#))"; ++ ++static const char *ecdsa_data_tmpl = ++ "(data (flags raw)" ++ " (label #A6E3C57DD01ABE90086538398355DD4C3B17AA873382B0F24D6129493D8AAD60#)" ++ " (hash %s %b))"; ++ + static const char ecdsa_signature_r[] = + "efd48b2aacb6a8fd1140dd9cd45e81d69d2c877b56aaf991c34d0ea84eaf3716"; + + static const char ecdsa_signature_s[] = + "f7cb1c942d657c41d436c7a1b6e29f65f3e900dbb9aff4064dc4ab2f843acda8"; + +-static const char *ecdsa_data_tmpl = "(data (flags rfc6979) (hash %s %b))"; + /* Sample data from RFC 6979 section A.2.5, hash is of message "sample" */ + static const char ecdsa_sample_data_string[] = "sample"; + static const char ecdsa_sample_data_bad_string[] = "sbmple"; +@@ -2409,6 +2433,16 @@ run_selftests (int algo, int extended, selftest_report_func_t report) + if (r) + return r; + ++ r = selftests_ecc (report, extended, 0, ++ ecdsa_sample_secret_key_secp256, ++ ecdsa_sample_public_key_secp256, ++ rfc6979_ecdsa_sample_data, rfc6979_ecdsa_sample_data_bad, ++ rfc6979_ecdsa_data_tmpl, ++ ecdsa_sample_data_string, ecdsa_sample_data_bad_string, ++ ecdsa_signature_r, ecdsa_signature_s); ++ if (r) ++ return r; ++ + r = selftests_ecc (report, extended, 1, + ed25519_sample_secret_key, + ed25519_sample_public_key, +-- +2.49.0 + diff --git a/libgcrypt-cipher-Check-and-mark-non-compliant-cipher-modes-in-the-SLI.patch b/libgcrypt-cipher-Check-and-mark-non-compliant-cipher-modes-in-the-SLI.patch new file mode 100644 index 0000000..e922808 --- /dev/null +++ b/libgcrypt-cipher-Check-and-mark-non-compliant-cipher-modes-in-the-SLI.patch @@ -0,0 +1,236 @@ +From 9f0fd2656d7d7ba26fcf95cc64d2514ae9ac8ec1 Mon Sep 17 00:00:00 2001 +From: Lucas Mulling +Date: Fri, 24 Jan 2025 09:57:49 -0300 +Subject: [PATCH] cipher: Check and mark non-compliant cipher modes in the SLI +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* cipher/cipher.c (_gcry_cipher_open_internal): Check and mark if the +cipher mode is compliant and reject accordingly. +(_gcry_cipher_is_mode_fips_compliant): New. +* src/gcrypt.h.in (GCRY_FIPS_FLAG_REJECT_CIPHER_MODE): New. +* tests/t-fips-service-ind.c (check_cipher_o_s_e_d_c): Add test to +verify that the service level indication is correctly set for non- +compliant cipher modes, and correctly rejected if +GCRY_FIPS_FLAG_REJECT_CIPHER_MODE is set. + +-- + +GnuPG-bug-id: 7338 +Signed-off-by: Lucas Mulling +Signed-off-by: Lucas Mülling +--- + cipher/cipher.c | 43 ++++++++++++++++++---- + src/gcrypt.h.in | 1 + + tests/t-fips-service-ind.c | 74 +++++++++++++++++++++++++++++++++----- + 3 files changed, 104 insertions(+), 14 deletions(-) + +diff --git a/cipher/cipher.c b/cipher/cipher.c +index 74dc2df7..b5420671 100644 +--- a/cipher/cipher.c ++++ b/cipher/cipher.c +@@ -504,6 +504,26 @@ _gcry_cipher_open (gcry_cipher_hd_t *handle, + return rc; + } + ++int ++_gcry_cipher_is_mode_fips_compliant(int mode) ++{ ++ switch (mode) ++ { ++ case GCRY_CIPHER_MODE_ECB: ++ case GCRY_CIPHER_MODE_CBC: ++ case GCRY_CIPHER_MODE_CFB: ++ case GCRY_CIPHER_MODE_CFB8: ++ case GCRY_CIPHER_MODE_OFB: ++ case GCRY_CIPHER_MODE_CTR: ++ case GCRY_CIPHER_MODE_CCM: ++ case GCRY_CIPHER_MODE_XTS: ++ case GCRY_CIPHER_MODE_AESWRAP: ++ return GPG_ERR_NO_ERROR; ++ default: ++ return GPG_ERR_NOT_SUPPORTED; ++ } ++} ++ + + gcry_err_code_t + _gcry_cipher_open_internal (gcry_cipher_hd_t *handle, +@@ -523,14 +543,25 @@ _gcry_cipher_open_internal (gcry_cipher_hd_t *handle, + err = GPG_ERR_CIPHER_ALGO; + else if (spec->flags.disabled) + err = GPG_ERR_CIPHER_ALGO; +- else if (!spec->flags.fips && fips_mode ()) ++ else if (fips_mode ()) + { +- if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_CIPHER)) +- err = GPG_ERR_CIPHER_ALGO; +- else ++ if (!spec->flags.fips) + { +- fips_service_indicator_mark_non_compliant (); +- err = 0; ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_CIPHER)) ++ err = GPG_ERR_CIPHER_ALGO; ++ else ++ { ++ fips_service_indicator_mark_non_compliant (); ++ err = 0; ++ } ++ } ++ else if ((err = _gcry_cipher_is_mode_fips_compliant(mode))) ++ { ++ if (!fips_check_rejection (GCRY_FIPS_FLAG_REJECT_CIPHER_MODE)) ++ { ++ fips_service_indicator_mark_non_compliant (); ++ err = 0; ++ } + } + } + else +diff --git a/src/gcrypt.h.in b/src/gcrypt.h.in +index fcb6a327..1a6f7269 100644 +--- a/src/gcrypt.h.in ++++ b/src/gcrypt.h.in +@@ -1988,6 +1988,7 @@ char *gcry_get_config (int mode, const char *what); + #define GCRY_FIPS_FLAG_REJECT_PK (1 << 5) + #define GCRY_FIPS_FLAG_REJECT_PK_MD (1 << 6) + #define GCRY_FIPS_FLAG_REJECT_PK_GOST_SM2 (1 << 7) ++#define GCRY_FIPS_FLAG_REJECT_CIPHER_MODE (1 << 8) + + #define GCRY_FIPS_FLAG_REJECT_MD \ + (GCRY_FIPS_FLAG_REJECT_MD_MD5 | GCRY_FIPS_FLAG_REJECT_MD_OTHERS) +diff --git a/tests/t-fips-service-ind.c b/tests/t-fips-service-ind.c +index fe963fa5..74521bb3 100644 +--- a/tests/t-fips-service-ind.c ++++ b/tests/t-fips-service-ind.c +@@ -606,27 +606,41 @@ check_cipher_o_s_e_d_c (int reject) + { + static struct { + int algo; ++ int mode; + const char *key; + int keylen; ++ const char *tag; ++ int taglen; + const char *expect; + int expect_failure; + } tv[] = { + #if USE_DES +- { GCRY_CIPHER_3DES, +- "\xe3\x34\x7a\x6b\x0b\xc1\x15\x2c\x64\x2a\x25\xcb\xd3\xbc\x31\xab" +- "\xfb\xa1\x62\xa8\x1f\x19\x7c\x15", 24, +- "\x3f\x1a\xb8\x83\x18\x8b\xb5\x97", 1 }, ++ { GCRY_CIPHER_3DES, GCRY_CIPHER_MODE_ECB, ++ "\xe3\x34\x7a\x6b\x0b\xc1\x15\x2c\x64\x2a\x25\xcb\xd3\xbc\x31\xab" ++ "\xfb\xa1\x62\xa8\x1f\x19\x7c\x15", 24, ++ "", -1, ++ "\x3f\x1a\xb8\x83\x18\x8b\xb5\x97", 1 }, + #endif +- { GCRY_CIPHER_AES, +- "\x2b\x7e\x15\x16\x28\xae\xd2\xa6\xab\xf7\x15\x88\x09\xcf\x4f\x3c", 16, +- "\x5c\x71\xd8\x5d\x26\x5e\xcd\xb5\x95\x40\x41\xab\xff\x25\x6f\xd1" } ++ { GCRY_CIPHER_AES, GCRY_CIPHER_MODE_ECB, ++ "\x2b\x7e\x15\x16\x28\xae\xd2\xa6\xab\xf7\x15\x88\x09\xcf\x4f\x3c", 16, ++ "", -1, ++ "\x5c\x71\xd8\x5d\x26\x5e\xcd\xb5\x95\x40\x41\xab\xff\x25\x6f\xd1" }, ++ { GCRY_CIPHER_AES128, GCRY_CIPHER_MODE_SIV, ++ "\xff\xfe\xfd\xfc\xfb\xfa\xf9\xf8\xf7\xf6\xf5\xf4\xf3\xf2\xf1\xf0" ++ "\xf0\xf1\xf2\xf3\xf4\xf5\xf6\xf7\xf8\xf9\xfa\xfb\xfc\xfd\xfe\xff", 32, ++ "\x51\x66\x54\xc4\xe1\xb5\xd9\x37\x31\x52\xdb\xea\x35\x10\x8b\x7b", 16, ++ "\x83\x69\xf6\xf3\x20\xff\xa2\x72\x31\x67\x15\xcf\xf4\x75\x01\x9a", 1 } + }; ++ + const char *pt = "Shohei Ohtani 2024: 54 HR, 59 SB"; + int ptlen; + int tvidx; + unsigned char out[MAX_DATA_LEN]; + gpg_error_t err; + ++ unsigned char tag[16]; ++ size_t taglen = 0; ++ + ptlen = strlen (pt); + assert (ptlen == 32); + for (tvidx=0; tvidx < DIM(tv); tvidx++) +@@ -640,10 +654,12 @@ check_cipher_o_s_e_d_c (int reject) + tvidx); + + blklen = gcry_cipher_get_algo_blklen (tv[tvidx].algo); ++ + assert (blklen != 0); + assert (blklen <= ptlen); + assert (blklen <= DIM (out)); +- err = gcry_cipher_open (&h, tv[tvidx].algo, GCRY_CIPHER_MODE_ECB, 0); ++ assert (tv[tvidx].taglen <= 16); ++ err = gcry_cipher_open (&h, tv[tvidx].algo, tv[tvidx].mode, 0); + if (err) + { + if (in_fips_mode && reject && tv[tvidx].expect_failure) +@@ -694,6 +710,18 @@ check_cipher_o_s_e_d_c (int reject) + continue; + } + ++ if (tv[tvidx].taglen >= 0) ++ { ++ err = gcry_cipher_info (h, GCRYCTL_GET_TAGLEN, NULL, &taglen); ++ if (err) ++ fail ("gcry_cipher_info %d failed: %s\n", tvidx, ++ gpg_strerror (err)); ++ ++ if (taglen != tv[tvidx].taglen) ++ fail ("gcry_cipher_info %d failed: taglen mismatch %d != %ld\n", tvidx, ++ tv[tvidx].taglen, taglen); ++ } ++ + err = gcry_cipher_encrypt (h, out, MAX_DATA_LEN, pt, blklen); + if (err) + { +@@ -714,6 +742,35 @@ check_cipher_o_s_e_d_c (int reject) + putc ('\n', stderr); + } + ++ if (tv[tvidx].taglen >= 0) ++ { ++ err = gcry_cipher_gettag (h, tag, tv[tvidx].taglen); ++ if (err) ++ fail ("gcry_cipher_gettag %d failed: %s", tvidx, ++ gpg_strerror(err)); ++ ++ if (memcmp (tv[tvidx].tag, tag, tv[tvidx].taglen)) ++ { ++ int i; ++ ++ fail ("gcry_cipher_gettag %d: tag mismatch\n", tvidx); ++ fputs ("got:", stderr); ++ for (i=0; i < 16 ; i++) ++ fprintf (stderr, " %02x", tag[i]); ++ putc ('\n', stderr); ++ } ++ ++ err = gcry_cipher_reset (h); ++ if (err) ++ fail("gcry_cipher_reset %d failed: %s", tvidx, ++ gpg_strerror(err)); ++ ++ err = gcry_cipher_set_decryption_tag (h, tag, 16); ++ if (err) ++ fail ("gcry_cipher_set_decryption_tag %d failed: %s\n", tvidx< ++ gpg_strerror (err)); ++ } ++ + err = gcry_cipher_decrypt (h, out, blklen, NULL, 0); + if (err) + { +@@ -1483,6 +1540,7 @@ main (int argc, char **argv) + + xgcry_control ((GCRYCTL_FIPS_REJECT_NON_FIPS, + (GCRY_FIPS_FLAG_REJECT_MD_MD5 ++ | GCRY_FIPS_FLAG_REJECT_CIPHER_MODE + | GCRY_FIPS_FLAG_REJECT_PK_MD + | GCRY_FIPS_FLAG_REJECT_PK_GOST_SM2 + | GCRY_FIPS_FLAG_REJECT_COMPAT110))); +-- +2.49.0 + diff --git a/libgcrypt-cipher-Differentiate-igninvflag-in-the-SLI.patch b/libgcrypt-cipher-Differentiate-igninvflag-in-the-SLI.patch new file mode 100644 index 0000000..7763815 --- /dev/null +++ b/libgcrypt-cipher-Differentiate-igninvflag-in-the-SLI.patch @@ -0,0 +1,40 @@ +From 3bdb59c21b77711cf7d44d692a7a02f5f469033e Mon Sep 17 00:00:00 2001 +From: Lucas Mulling via Gcrypt-devel +Date: Wed, 26 Feb 2025 17:19:22 -0300 +Subject: [PATCH 04/14] cipher: Differentiate igninvflag in the SLI +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* cipher/pubkey-util.c (_gcry_pk_util_parse_flaglist): Differentiate use +of igninvflag. + +GnuPG-bug-id: 7338 +Signed-off-by: Lucas Mulling +Signed-off-by: Lucas Mülling +--- + cipher/pubkey-util.c | 8 ++++++++ + 1 file changed, 8 insertions(+) + +diff --git a/cipher/pubkey-util.c b/cipher/pubkey-util.c +index 68defea6..9c927638 100644 +--- a/cipher/pubkey-util.c ++++ b/cipher/pubkey-util.c +@@ -200,6 +200,14 @@ _gcry_pk_util_parse_flaglist (gcry_sexp_t list, + } + } + ++ if (fips_mode () && igninvflag) ++ { ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) ++ rc = GPG_ERR_INV_FLAG; ++ else ++ fips_service_indicator_mark_non_compliant (); ++ } ++ + if (r_flags) + *r_flags = flags; + if (r_encoding) +-- +2.49.0 + diff --git a/libgcrypt-cipher-Differentiate-no-blinding-flag-in-the-SLI.patch b/libgcrypt-cipher-Differentiate-no-blinding-flag-in-the-SLI.patch new file mode 100644 index 0000000..92b9073 --- /dev/null +++ b/libgcrypt-cipher-Differentiate-no-blinding-flag-in-the-SLI.patch @@ -0,0 +1,70 @@ +From cc0a40bd74120dc06fd80f163b30abb91f60b63b Mon Sep 17 00:00:00 2001 +From: Lucas Mulling via Gcrypt-devel +Date: Wed, 26 Feb 2025 17:19:23 -0300 +Subject: [PATCH 05/14] cipher: Differentiate no-blinding flag in the SLI +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* cipher/rsa.c (rsa_decrypt, rsa_encrypt): Differentiate use of flag +no-blinding in the service level indicator. + +GnuPG-bug-id: 7338 +Signed-off-by: Lucas Mulling +Signed-off-by: Lucas Mülling +--- + cipher/rsa.c | 30 ++++++++++++++++++++++++++++-- + 1 file changed, 28 insertions(+), 2 deletions(-) + +diff --git a/cipher/rsa.c b/cipher/rsa.c +index c1329644..dce76414 100644 +--- a/cipher/rsa.c ++++ b/cipher/rsa.c +@@ -1501,7 +1501,19 @@ rsa_decrypt (gcry_sexp_t *r_plain, gcry_sexp_t s_data, gcry_sexp_t keyparms) + be practically mounted over the network as shown by Brumley and + Boney in 2003. */ + if ((ctx.flags & PUBKEY_FLAG_NO_BLINDING)) +- secret (plain, data, &sk); ++ { ++ if (fips_mode ()) ++ { ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) ++ { ++ rc = GPG_ERR_INV_FLAG; ++ goto leave; ++ } ++ else ++ fips_service_indicator_mark_non_compliant (); ++ } ++ secret (plain, data, &sk); ++ } + else + secret_blinded (plain, data, &sk, nbits); + +@@ -1632,8 +1644,22 @@ rsa_sign (gcry_sexp_t *r_sig, gcry_sexp_t s_data, gcry_sexp_t keyparms) + + /* Do RSA computation. */ + sig = mpi_new (0); ++ + if ((ctx.flags & PUBKEY_FLAG_NO_BLINDING)) +- secret (sig, data, &sk); ++ { ++ if (fips_mode ()) ++ { ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) ++ { ++ rc = GPG_ERR_INV_FLAG; ++ goto leave; ++ } ++ else ++ fips_service_indicator_mark_non_compliant (); ++ } ++ ++ secret (sig, data, &sk); ++ } + else + secret_blinded (sig, data, &sk, nbits); + if (DBG_CIPHER) +-- +2.49.0 + diff --git a/libgcrypt-cipher-Differentiate-use-of-label-K-in-the-SLI.patch b/libgcrypt-cipher-Differentiate-use-of-label-K-in-the-SLI.patch new file mode 100644 index 0000000..a054b64 --- /dev/null +++ b/libgcrypt-cipher-Differentiate-use-of-label-K-in-the-SLI.patch @@ -0,0 +1,139 @@ +From 2f6d2db1a4c28775a568c1f81ca127d2daebaf1c Mon Sep 17 00:00:00 2001 +From: Lucas Mulling via Gcrypt-devel +Date: Wed, 26 Feb 2025 12:29:54 -0300 +Subject: [PATCH 03/14] cipher: Differentiate use of label K in the SLI +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* cipher/ecc.c (ecc_sign, ecc_verify): Use of label K is not allowed in +fips mode, differentiate with the GCRY_FIPS_FLAG_REJECT_PK_ECC_K flag. +* src/gcrypt.h.in: New GCRY_FIPS_FLAG_REJECT_PK_ECC_K. +* tests/t-fips-service-ind.c (check_pk_hash_sign_verify): Mark non +compliant use of label. + +Signed-off-by: Lucas Mulling +Signed-off-by: Lucas Mülling +--- + cipher/ecc.c | 26 +++++++++++++++++++++++++- + src/gcrypt.h.in | 2 ++ + tests/t-fips-service-ind.c | 11 ++++++----- + 3 files changed, 33 insertions(+), 6 deletions(-) + +diff --git a/cipher/ecc.c b/cipher/ecc.c +index d331a014..569e41f6 100644 +--- a/cipher/ecc.c ++++ b/cipher/ecc.c +@@ -961,7 +961,16 @@ ecc_sign (gcry_sexp_t *r_sig, gcry_sexp_t s_data, gcry_sexp_t keyparms) + log_mpidump ("ecc_sign data", data); + + if (ctx.label) +- rc = _gcry_mpi_scan (&k, GCRYMPI_FMT_USG, ctx.label, ctx.labellen, NULL); ++ { ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK_ECC_K)) ++ { ++ rc = GPG_ERR_INV_DATA; ++ goto leave; ++ } ++ else ++ fips_service_indicator_mark_non_compliant (); ++ rc = _gcry_mpi_scan (&k, GCRYMPI_FMT_USG, ctx.label, ctx.labellen, NULL); ++ } + if (rc) + goto leave; + +@@ -1118,6 +1127,21 @@ ecc_verify (gcry_sexp_t s_sig, gcry_sexp_t s_data, gcry_sexp_t s_keyparms) + rc = _gcry_pk_util_data_to_mpi (s_data, &data, &ctx); + if (rc) + goto leave; ++ ++ if (ctx.label) ++ { ++ if (fips_mode ()) ++ { ++ if(fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK_ECC_K)) ++ { ++ rc = GPG_ERR_INV_DATA; ++ goto leave; ++ } ++ else ++ fips_service_indicator_mark_non_compliant (); ++ } ++ } ++ + if (DBG_CIPHER) + log_mpidump ("ecc_verify data", data); + +diff --git a/src/gcrypt.h.in b/src/gcrypt.h.in +index 1a6f7269..fe3db16a 100644 +--- a/src/gcrypt.h.in ++++ b/src/gcrypt.h.in +@@ -1989,6 +1989,8 @@ char *gcry_get_config (int mode, const char *what); + #define GCRY_FIPS_FLAG_REJECT_PK_MD (1 << 6) + #define GCRY_FIPS_FLAG_REJECT_PK_GOST_SM2 (1 << 7) + #define GCRY_FIPS_FLAG_REJECT_CIPHER_MODE (1 << 8) ++/**/ ++#define GCRY_FIPS_FLAG_REJECT_PK_ECC_K (1 << 10) + + #define GCRY_FIPS_FLAG_REJECT_MD \ + (GCRY_FIPS_FLAG_REJECT_MD_MD5 | GCRY_FIPS_FLAG_REJECT_MD_OTHERS) +diff --git a/tests/t-fips-service-ind.c b/tests/t-fips-service-ind.c +index a082b258..0ece55b8 100644 +--- a/tests/t-fips-service-ind.c ++++ b/tests/t-fips-service-ind.c +@@ -728,7 +728,7 @@ check_pk_hash_sign_verify (void) + "ce4014c68811f9a21a1fdb2c0e6113e06db7ca93b7404e78dc7ccd5ca89a4ca9#)))", + "(data(flags raw)(hash %s %b)(label %b))", + "94a1bbb14b906a61a280f245f9e93c7f3b4a6247824f5d33b9670787642a68de", +- 0, 0 ++ 1, 0, + } + }; + int tvidx; +@@ -827,7 +827,7 @@ check_pk_hash_sign_verify (void) + if (ec == GPG_ERR_INV_OP) + { + /* libgcrypt is old, no support of the FIPS service indicator. */ +- fail ("gcry_pk_hash test %d unexpectedly failed to check the FIPS service indicator.\n", ++ fail ("gcry_pk_hash_sign test %d unexpectedly failed to check the FIPS service indicator.\n", + tvidx); + goto next; + } +@@ -835,7 +835,7 @@ check_pk_hash_sign_verify (void) + if (in_fips_mode && !tv[tvidx].expect_failure && ec) + { + /* Success with the FIPS service indicator == 0 expected, but != 0. */ +- fail ("gcry_pk_hash test %d unexpectedly set the indicator in FIPS mode.\n", ++ fail ("gcry_pk_hash_sign test %d unexpectedly set the indicator in FIPS mode.\n", + tvidx); + goto next; + } +@@ -859,7 +859,7 @@ check_pk_hash_sign_verify (void) + if (ec == GPG_ERR_INV_OP) + { + /* libgcrypt is old, no support of the FIPS service indicator. */ +- fail ("gcry_pk_hash test %d unexpectedly failed to check the FIPS service indicator.\n", ++ fail ("gcry_pk_hash_verify test %d unexpectedly failed to check the FIPS service indicator.\n", + tvidx); + goto next; + } +@@ -867,7 +867,7 @@ check_pk_hash_sign_verify (void) + if (in_fips_mode && !tv[tvidx].expect_failure && ec) + { + /* Success with the FIPS service indicator == 0 expected, but != 0. */ +- fail ("gcry_pk_hash test %d unexpectedly set the indicator in FIPS mode.\n", ++ fail ("gcry_pk_hash_verify test %d unexpectedly set the indicator in FIPS mode.\n", + tvidx); + goto next; + } +@@ -1834,6 +1834,7 @@ main (int argc, char **argv) + | GCRY_FIPS_FLAG_REJECT_CIPHER_MODE + | GCRY_FIPS_FLAG_REJECT_PK_MD + | GCRY_FIPS_FLAG_REJECT_PK_GOST_SM2 ++ | GCRY_FIPS_FLAG_REJECT_PK_ECC_K + | GCRY_FIPS_FLAG_REJECT_COMPAT110))); + + check_md_o_w_r_c (1); +-- +2.49.0 + diff --git a/libgcrypt-cipher-Don-t-differentiate-GCRY_CIPHER_MODE_CMAC-in-FIPS-mode.patch b/libgcrypt-cipher-Don-t-differentiate-GCRY_CIPHER_MODE_CMAC-in-FIPS-mode.patch new file mode 100644 index 0000000..fc8d335 --- /dev/null +++ b/libgcrypt-cipher-Don-t-differentiate-GCRY_CIPHER_MODE_CMAC-in-FIPS-mode.patch @@ -0,0 +1,98 @@ +From 608ff4b2261e2d8961f0ef4189e74b1173b2802c Mon Sep 17 00:00:00 2001 +From: Lucas Mulling +Date: Sun, 2 Feb 2025 12:58:21 -0300 +Subject: [PATCH 2/2] cipher: Don't differentiate GCRY_CIPHER_MODE_CMAC in FIPS + mode. +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* cipher/cipher.c (_gcry_cipher_mode_fips_compliance): Allow +GCRY_CIPHER_MODE_CMAC in fips mode. +* cipher/cipher.c (cipher_modes_fips_compliance) +(cipher_int_modes_fips_compliance): New. +-- + +Signed-off-by: Lucas Mulling + +Added some comments, changed scope of the new functions and shorted +their names. Also added restructured the switch and added all other +modes. + +Signed-off-by: Werner Koch +Signed-off-by: Lucas Mülling +--- + cipher/cipher.c | 49 ++++++++++++++++++++++++++++++++++++++++++++----- + 1 file changed, 44 insertions(+), 5 deletions(-) + +diff --git a/cipher/cipher.c b/cipher/cipher.c +index 3b7970b3..fc130907 100644 +--- a/cipher/cipher.c ++++ b/cipher/cipher.c +@@ -505,8 +505,9 @@ _gcry_cipher_open (gcry_cipher_hd_t *handle, + } + + +-gcry_err_code_t +-_gcry_cipher_mode_fips_compliance (enum gcry_cipher_modes mode) ++/* Return an error if the give cipher mode is non-FIPS compliant. */ ++static gcry_err_code_t ++cipher_modes_fips_compliance (enum gcry_cipher_modes mode) + { + switch (mode) + { +@@ -519,10 +520,48 @@ _gcry_cipher_mode_fips_compliance (enum gcry_cipher_modes mode) + case GCRY_CIPHER_MODE_CCM: + case GCRY_CIPHER_MODE_XTS: + case GCRY_CIPHER_MODE_AESWRAP: +- return GPG_ERR_NO_ERROR; +- default: +- return GPG_ERR_NOT_SUPPORTED; ++ return 0; ++ case GCRY_CIPHER_MODE_NONE: ++ case GCRY_CIPHER_MODE_STREAM: ++ case GCRY_CIPHER_MODE_GCM: ++ case GCRY_CIPHER_MODE_POLY1305: ++ case GCRY_CIPHER_MODE_OCB: ++ case GCRY_CIPHER_MODE_EAX: ++ case GCRY_CIPHER_MODE_SIV: ++ case GCRY_CIPHER_MODE_GCM_SIV: ++ break; + } ++ return GPG_ERR_NOT_SUPPORTED; ++} ++ ++ ++/* This is similar to cipher_modes_fips_compliance but only for the ++ * internal modes (i.e. CMAC). Return an error if the mode is ++ * non-FIPS compliant. */ ++static gcry_err_code_t ++cipher_int_modes_fips_compliance (enum gcry_cipher_internal_modes mode) ++{ ++ switch (mode) ++ { ++ case GCRY_CIPHER_MODE_INTERNAL: ++ break; ++ case GCRY_CIPHER_MODE_CMAC: ++ return 0; ++ } ++ return GPG_ERR_NOT_SUPPORTED; ++} ++ ++ ++/* Return an error if the give cipher mode is non-FIPS compliant. The ++ * mode is not an enum here so that we can use it for real modes and ++ * for internal modes. */ ++gcry_err_code_t ++_gcry_cipher_mode_fips_compliance (int mode) ++{ ++ if (mode >= GCRY_CIPHER_MODE_INTERNAL) ++ return cipher_int_modes_fips_compliance (mode); ++ else ++ return cipher_modes_fips_compliance (mode); + } + + +-- +2.49.0 + diff --git a/libgcrypt-cipher-Rename-_gcry_cipher_is_mode_fips_compliant.patch b/libgcrypt-cipher-Rename-_gcry_cipher_is_mode_fips_compliant.patch new file mode 100644 index 0000000..e98f6ab --- /dev/null +++ b/libgcrypt-cipher-Rename-_gcry_cipher_is_mode_fips_compliant.patch @@ -0,0 +1,64 @@ +From 6b0fbb7e5e0da77787e3a87d74359ee21c44904e Mon Sep 17 00:00:00 2001 +From: Lucas Mulling +Date: Tue, 28 Jan 2025 13:45:39 -0300 +Subject: [PATCH 1/2] cipher: Rename _gcry_cipher_is_mode_fips_compliant +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* cipher/cipher.c (_gcry_cipher_is_mode_fips_compliant): Rename to +_gcry_cipher_mode_fips_compliance for better clarity and change the +return type to gcry_err_code_t. +* cipher/cipher.c (_gcry_cipher_mode_fips_compliance): Use +gcry_cipher_modes instead of int for mode. +* tests/t-fips-service-ind.c (check_cipher_o_s_e_d_c): Fix typo in fail. +-- + +Signed-off-by: Lucas Mulling +Signed-off-by: Lucas Mülling +--- + cipher/cipher.c | 7 ++++--- + tests/t-fips-service-ind.c | 2 +- + 2 files changed, 5 insertions(+), 4 deletions(-) + +diff --git a/cipher/cipher.c b/cipher/cipher.c +index b5420671..3b7970b3 100644 +--- a/cipher/cipher.c ++++ b/cipher/cipher.c +@@ -504,8 +504,9 @@ _gcry_cipher_open (gcry_cipher_hd_t *handle, + return rc; + } + +-int +-_gcry_cipher_is_mode_fips_compliant(int mode) ++ ++gcry_err_code_t ++_gcry_cipher_mode_fips_compliance (enum gcry_cipher_modes mode) + { + switch (mode) + { +@@ -555,7 +556,7 @@ _gcry_cipher_open_internal (gcry_cipher_hd_t *handle, + err = 0; + } + } +- else if ((err = _gcry_cipher_is_mode_fips_compliant(mode))) ++ else if ((err = _gcry_cipher_mode_fips_compliance (mode))) + { + if (!fips_check_rejection (GCRY_FIPS_FLAG_REJECT_CIPHER_MODE)) + { +diff --git a/tests/t-fips-service-ind.c b/tests/t-fips-service-ind.c +index 74521bb3..ed5f8d3f 100644 +--- a/tests/t-fips-service-ind.c ++++ b/tests/t-fips-service-ind.c +@@ -767,7 +767,7 @@ check_cipher_o_s_e_d_c (int reject) + + err = gcry_cipher_set_decryption_tag (h, tag, 16); + if (err) +- fail ("gcry_cipher_set_decryption_tag %d failed: %s\n", tvidx< ++ fail ("gcry_cipher_set_decryption_tag %d failed: %s\n", tvidx, + gpg_strerror (err)); + } + +-- +2.49.0 + diff --git a/libgcrypt-cipher-ecc-Fix-for-supplied-K.patch b/libgcrypt-cipher-ecc-Fix-for-supplied-K.patch new file mode 100644 index 0000000..743468d --- /dev/null +++ b/libgcrypt-cipher-ecc-Fix-for-supplied-K.patch @@ -0,0 +1,88 @@ +From 755e6dce727915249cbb1a98f22832d940b99c24 Mon Sep 17 00:00:00 2001 +From: NIIBE Yutaka +Date: Thu, 6 Mar 2025 09:12:36 +0900 +Subject: [PATCH 07/14] cipher,ecc: Fix for supplied K. +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* cipher/ecc.c (ecc_sign): Check if it's under FIPS mode. +(ecc_verify): Supplied K does no sense for verification, but add +comment of clarification mark/reject-ing under FIPS mode. + +-- + +GnuPG-bug-id: 7338 +Signed-off-by: NIIBE Yutaka +Signed-off-by: Lucas Mülling +--- + cipher/ecc.c | 39 +++++++++++++++++++++++---------------- + 1 file changed, 23 insertions(+), 16 deletions(-) + +diff --git a/cipher/ecc.c b/cipher/ecc.c +index 569e41f6..a165bb7a 100644 +--- a/cipher/ecc.c ++++ b/cipher/ecc.c +@@ -962,17 +962,21 @@ ecc_sign (gcry_sexp_t *r_sig, gcry_sexp_t s_data, gcry_sexp_t keyparms) + + if (ctx.label) + { +- if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK_ECC_K)) ++ /* ECDSA signing can have supplied K (for testing, deterministic). */ ++ if (fips_mode ()) + { +- rc = GPG_ERR_INV_DATA; +- goto leave; ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK_ECC_K)) ++ { ++ rc = GPG_ERR_INV_DATA; ++ goto leave; ++ } ++ else ++ fips_service_indicator_mark_non_compliant (); + } +- else +- fips_service_indicator_mark_non_compliant (); + rc = _gcry_mpi_scan (&k, GCRYMPI_FMT_USG, ctx.label, ctx.labellen, NULL); ++ if (rc) ++ goto leave; + } +- if (rc) +- goto leave; + + if (fips_mode () + && ((ctx.flags & PUBKEY_FLAG_GOST) || (ctx.flags & PUBKEY_FLAG_SM2))) +@@ -1128,18 +1132,21 @@ ecc_verify (gcry_sexp_t s_sig, gcry_sexp_t s_data, gcry_sexp_t s_keyparms) + if (rc) + goto leave; + +- if (ctx.label) ++ /* ++ * ECDSA signing can have supplied K (for testing, deterministic), ++ * but it's non-compliant. For ECDSA signature verification, having ++ * K is irrelevant, but an application may use same flags as the one ++ * for signing. ++ */ ++ if (ctx.label && fips_mode ()) + { +- if (fips_mode ()) ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK_ECC_K)) + { +- if(fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK_ECC_K)) +- { +- rc = GPG_ERR_INV_DATA; +- goto leave; +- } +- else +- fips_service_indicator_mark_non_compliant (); ++ rc = GPG_ERR_INV_DATA; ++ goto leave; + } ++ else ++ fips_service_indicator_mark_non_compliant (); + } + + if (DBG_CIPHER) +-- +2.49.0 + diff --git a/libgcrypt-cipher-fips-Fix-for-random-override.patch b/libgcrypt-cipher-fips-Fix-for-random-override.patch new file mode 100644 index 0000000..076f66f --- /dev/null +++ b/libgcrypt-cipher-fips-Fix-for-random-override.patch @@ -0,0 +1,83 @@ +From ca8bf05e111b41e482a2a4b34cda6bcf5aa1f27e Mon Sep 17 00:00:00 2001 +From: NIIBE Yutaka +Date: Thu, 6 Mar 2025 09:45:36 +0900 +Subject: [PATCH 09/14] cipher,fips: Fix for random-override. +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* cipher/pubkey-util.c (gcry_pk_util_data_to_mpi): Keep +the behavior of 1.10. +* src/visibility.c (gcry_pk_random_override_new): Likewise. +* tests/t-fips-service-ind.c (main): Use GCRY_FIPS_FLAG_REJECT_PK_FLAGS. + +-- + +GnuPG-bug-id: 7338 +Signed-off-by: NIIBE Yutaka +Signed-off-by: Lucas Mülling +--- + cipher/pubkey-util.c | 6 +++--- + src/visibility.c | 2 +- + tests/t-fips-service-ind.c | 1 + + 3 files changed, 5 insertions(+), 4 deletions(-) + +diff --git a/cipher/pubkey-util.c b/cipher/pubkey-util.c +index 66a04f13..0e67f892 100644 +--- a/cipher/pubkey-util.c ++++ b/cipher/pubkey-util.c +@@ -975,7 +975,7 @@ _gcry_pk_util_data_to_mpi (gcry_sexp_t input, gcry_mpi_t *ret_mpi, + { + if (fips_mode ()) + { +- if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK_FLAGS)) + { + sexp_release (list); + rc = GPG_ERR_INV_FLAG; +@@ -1162,7 +1162,7 @@ _gcry_pk_util_data_to_mpi (gcry_sexp_t input, gcry_mpi_t *ret_mpi, + { + if (fips_mode ()) + { +- if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK_FLAGS)) + { + sexp_release (list); + rc = GPG_ERR_INV_FLAG; +@@ -1272,7 +1272,7 @@ _gcry_pk_util_data_to_mpi (gcry_sexp_t input, gcry_mpi_t *ret_mpi, + { + if (fips_mode ()) + { +- if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK_FLAGS)) + { + sexp_release (list); + rc = GPG_ERR_INV_FLAG; +diff --git a/src/visibility.c b/src/visibility.c +index ccd0de69..edb972bc 100644 +--- a/src/visibility.c ++++ b/src/visibility.c +@@ -1091,7 +1091,7 @@ gcry_pk_random_override_new (gcry_ctx_t *r_ctx, const unsigned char *p, size_t l + + if (fips_mode ()) + { +- if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK_FLAGS)) + return gpg_error (GPG_ERR_INV_OP); + else + fips_service_indicator_mark_non_compliant (); +diff --git a/tests/t-fips-service-ind.c b/tests/t-fips-service-ind.c +index 0ece55b8..0a270b38 100644 +--- a/tests/t-fips-service-ind.c ++++ b/tests/t-fips-service-ind.c +@@ -1835,6 +1835,7 @@ main (int argc, char **argv) + | GCRY_FIPS_FLAG_REJECT_PK_MD + | GCRY_FIPS_FLAG_REJECT_PK_GOST_SM2 + | GCRY_FIPS_FLAG_REJECT_PK_ECC_K ++ | GCRY_FIPS_FLAG_REJECT_PK_FLAGS + | GCRY_FIPS_FLAG_REJECT_COMPAT110))); + + check_md_o_w_r_c (1); +-- +2.49.0 + diff --git a/libgcrypt-cipher-rsa-Mark-reject-SHA1-unknown-with-RSA-signature-generation.patch b/libgcrypt-cipher-rsa-Mark-reject-SHA1-unknown-with-RSA-signature-generation.patch new file mode 100644 index 0000000..7ff18ce --- /dev/null +++ b/libgcrypt-cipher-rsa-Mark-reject-SHA1-unknown-with-RSA-signature-generation.patch @@ -0,0 +1,445 @@ +From 60e5039793c2474d29ded039cf1a6b8107733a20 Mon Sep 17 00:00:00 2001 +From: NIIBE Yutaka +Date: Fri, 21 Feb 2025 14:24:41 +0900 +Subject: [PATCH] cipher:rsa: Mark/reject SHA1/unknown with RSA signature + generation. +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* cipher/rsa-common.c (_gcry_rsa_pkcs1_encode_raw_for_sig): We can't +determine if it's compliant when raw PKCS1 encoding is used. +(_gcry_rsa_pss_encode): Add the behavior of marking non-compliant use. +(_gcry_rsa_pss_verify): Likewise. +* cipher/rsa.c (rsa_sign): Handle the check for SHA1. +(rsa_verify): Likewise. +* tests/t-fips-service-ind.c (check_pk_s_v): Add use cases for RSA +and Ed25519. + +-- + +GnuPG-bug-id: 7338 +Signed-off-by: NIIBE Yutaka +Signed-off-by: Lucas Mülling +--- + cipher/rsa-common.c | 28 +++- + cipher/rsa.c | 34 +++++ + tests/t-fips-service-ind.c | 290 ++++++++++++++++++++++++++++++++++++- + 3 files changed, 347 insertions(+), 5 deletions(-) + +diff --git a/cipher/rsa-common.c b/cipher/rsa-common.c +index 1920eedd..c1d2dcd5 100644 +--- a/cipher/rsa-common.c ++++ b/cipher/rsa-common.c +@@ -380,6 +380,16 @@ _gcry_rsa_pkcs1_encode_raw_for_sig (gcry_mpi_t *r_result, unsigned int nbits, + int i; + size_t n; + ++ /* With RAW encoding, we can't know if the hash used is compliant or ++ * not. Reject or mark it's non-compliant. */ ++ if (fips_mode ()) ++ { ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK_MD)) ++ return GPG_ERR_DIGEST_ALGO; ++ else ++ fips_service_indicator_mark_non_compliant (); ++ } ++ + if ( !valuelen || valuelen + 4 > nframe) + { + /* Can't encode an DLEN byte digest MD into an NFRAME byte +@@ -840,8 +850,13 @@ _gcry_rsa_pss_encode (gcry_mpi_t *r_result, unsigned int nbits, int algo, + /* The FIPS 186-4 Section 5.5 allows only 0 <= sLen <= hLen */ + if (fips_mode () && saltlen > hlen) + { +- rc = GPG_ERR_INV_ARG; +- goto leave; ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) ++ { ++ rc = GPG_ERR_INV_ARG; ++ goto leave; ++ } ++ else ++ fips_service_indicator_mark_non_compliant (); + } + + /* Allocate a help buffer and setup some pointers. */ +@@ -1006,8 +1021,13 @@ _gcry_rsa_pss_verify (gcry_mpi_t value, int hashed_already, + /* The FIPS 186-4 Section 5.5 allows only 0 <= sLen <= hLen */ + if (fips_mode () && saltlen > hlen) + { +- rc = GPG_ERR_INV_ARG; +- goto leave; ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) ++ { ++ rc = GPG_ERR_INV_ARG; ++ goto leave; ++ } ++ else ++ fips_service_indicator_mark_non_compliant (); + } + + /* Allocate a help buffer and setup some pointers. +diff --git a/cipher/rsa.c b/cipher/rsa.c +index c7a809f4..c1329644 100644 +--- a/cipher/rsa.c ++++ b/cipher/rsa.c +@@ -1613,6 +1613,23 @@ rsa_sign (gcry_sexp_t *r_sig, gcry_sexp_t s_data, gcry_sexp_t keyparms) + } + } + ++ /* Check if use of the hash is compliant. */ ++ if (fips_mode ()) ++ { ++ /* SHA1 is approved hash function, but not for digital signature. */ ++ if (_gcry_md_algo_info (ctx.hash_algo, GCRYCTL_TEST_ALGO, NULL, NULL) ++ || ctx.hash_algo == GCRY_MD_SHA1) ++ { ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK_MD)) ++ { ++ rc = GPG_ERR_DIGEST_ALGO; ++ goto leave; ++ } ++ else ++ fips_service_indicator_mark_non_compliant (); ++ } ++ } ++ + /* Do RSA computation. */ + sig = mpi_new (0); + if ((ctx.flags & PUBKEY_FLAG_NO_BLINDING)) +@@ -1720,6 +1737,23 @@ rsa_verify (gcry_sexp_t s_sig, gcry_sexp_t s_data, gcry_sexp_t keyparms) + log_printmpi ("rsa_verify e", pk.e); + } + ++ /* Check if use of the hash is compliant. */ ++ if (fips_mode ()) ++ { ++ /* SHA1 is approved hash function, but not for digital signature. */ ++ if (_gcry_md_algo_info (ctx.hash_algo, GCRYCTL_TEST_ALGO, NULL, NULL) ++ || ctx.hash_algo == GCRY_MD_SHA1) ++ { ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK_MD)) ++ { ++ rc = GPG_ERR_DIGEST_ALGO; ++ goto leave; ++ } ++ else ++ fips_service_indicator_mark_non_compliant (); ++ } ++ } ++ + /* Do RSA computation and compare. */ + result = mpi_new (0); + public (result, sig, &pk); +diff --git a/tests/t-fips-service-ind.c b/tests/t-fips-service-ind.c +index ed5f8d3f..bec6c27e 100644 +--- a/tests/t-fips-service-ind.c ++++ b/tests/t-fips-service-ind.c +@@ -231,7 +231,8 @@ check_pk_s_v (int reject) + const char *data; + int expect_failure; + } tv[] = { +- { ++ { /* Hashing is done externally, and feeded ++ to gcry_pk_sign, specifing the hash used */ + "(private-key (ecc (curve nistp256)" + " (d #519b423d715f8b581f4fa8ee59f4771a5b44c8130b4e3eacca54a56dda72b464#)))", + "(public-key (ecc (curve nistp256)" +@@ -271,6 +272,293 @@ check_pk_s_v (int reject) + "#00112233445566778899AABBCCDDEEFF00010203#))", + 1 + }, ++ { /* Hashing is done internally in ++ gcry_pk_sign with the hash-algo specified. */ ++ "(private-key\n" ++ " (ecc\n" ++ " (curve Ed25519)(flags eddsa)\n" ++ " (q #4014DB483F15527253B25B4C72BEA8BB70255029636BD71DBBCCD5D8BF48A35F17#)" ++ " (d #09A0C38E0F1699073541447C19DA12E3A07A7BFDB0C186E4AC5BCE6F23D55252#)" ++ "))", ++ "(public-key\n" ++ " (ecc\n" ++ " (curve Ed25519)(flags eddsa)\n" ++ " (q #4014DB483F15527253B25B4C72BEA8BB70255029636BD71DBBCCD5D8BF48A35F17#)" ++ "))", ++ "(data(flags eddsa)(hash-algo sha512)(value " ++ "#00112233445566778899AABBCCDDEEFF000102030405060708090A0B0C0D0E0F" ++ " 00112233445566778899AABBCCDDEEFF000102030405060708090A0B0C0D0E0F" ++ " 00112233445566778899AABBCCDDEEFF000102030405060708090A0B0C0D0E0F#))", ++ 0 ++ }, ++ { /* RSA with compliant hash for signing */ ++ "(private-key" ++ " (rsa" ++ " (n #009F56231A3D82E3E7D613D59D53E9AB921BEF9F08A782AED0B6E46ADBC853EC" ++ " 7C71C422435A3CD8FA0DB9EFD55CD3295BADC4E8E2E2B94E15AE82866AB8ADE8" ++ " 7E469FAE76DC3577DE87F1F419C4EB41123DFAF8D16922D5EDBAD6E9076D5A1C" ++ " 958106F0AE5E2E9193C6B49124C64C2A241C4075D4AF16299EB87A6585BAE917" ++ " DEF27FCDD165764D069BC18D16527B29DAAB549F7BBED4A7C6A842D203ED6613" ++ " 6E2411744E432CD26D940132F25874483DCAEECDFD95744819CBCF1EA810681C" ++ " 42907EBCB1C7EAFBE75C87EC32C5413EA10476545D3FC7B2ADB1B66B7F200918" ++ " 664B0E5261C2895AA28B0DE321E921B3F877172CCCAB81F43EF98002916156F6" ++ " CB#)\n" ++ " (e #010001#)\n" ++ " (d #07EF82500C403899934FE993AC5A36F14FF2DF38CF1EF315F205EE4C83EDAA19" ++ " 8890FC23DE9AA933CAFB37B6A8A8DBA675411958337287310D3FF2F1DDC0CB93" ++ " 7E70F57F75F833C021852B631D2B9A520E4431A03C5C3FCB5742DCD841D9FB12" ++ " 771AA1620DCEC3F1583426066ED9DC3F7028C5B59202C88FDF20396E2FA0EC4F" ++ " 5A22D9008F3043673931BC14A5046D6327398327900867E39CC61B2D1AFE2F48" ++ " EC8E1E3861C68D257D7425F4E6F99ABD77D61F10CA100EFC14389071831B33DD" ++ " 69CC8EABEF860D1DC2AAA84ABEAE5DFC91BC124DAF0F4C8EF5BBEA436751DE84" ++ " 3A8063E827A024466F44C28614F93B0732A100D4A0D86D532FE1E22C7725E401" ++ " #)\n" ++ " (p #00C29D438F115825779631CD665A5739367F3E128ADC29766483A46CA80897E0" ++ " 79B32881860B8F9A6A04C2614A904F6F2578DAE13EA67CD60AE3D0AA00A1FF9B" ++ " 441485E44B2DC3D0B60260FBFE073B5AC72FAF67964DE15C8212C389D20DB9CF" ++ " 54AF6AEF5C4196EAA56495DD30CF709F499D5AB30CA35E086C2A1589D6283F17" ++ " 83#)\n" ++ " (q #00D1984135231CB243FE959C0CBEF551EDD986AD7BEDF71EDF447BE3DA27AF46" ++ " 79C974A6FA69E4D52FE796650623DE70622862713932AA2FD9F2EC856EAEAA77" ++ " 88B4EA6084DC81C902F014829B18EA8B2666EC41586818E0589E18876065F97E" ++ " 8D22CE2DA53A05951EC132DCEF41E70A9C35F4ACC268FFAC2ADF54FA1DA110B9" ++ " 19#)\n" ++ " (u #67CF0FD7635205DD80FA814EE9E9C267C17376BF3209FB5D1BC42890D2822A04" ++ " 479DAF4D5B6ED69D0F8D1AF94164D07F8CD52ECEFE880641FA0F41DDAB1785E4" ++ " A37A32F997A516480B4CD4F6482B9466A1765093ED95023CA32D5EDC1E34CEE9" ++ " AF595BC51FE43C4BF810FA225AF697FB473B83815966188A4312C048B885E3F7" ++ " #)))\n", ++ "(public-key\n" ++ " (rsa\n" ++ " (n #009F56231A3D82E3E7D613D59D53E9AB921BEF9F08A782AED0B6E46ADBC853EC" ++ " 7C71C422435A3CD8FA0DB9EFD55CD3295BADC4E8E2E2B94E15AE82866AB8ADE8" ++ " 7E469FAE76DC3577DE87F1F419C4EB41123DFAF8D16922D5EDBAD6E9076D5A1C" ++ " 958106F0AE5E2E9193C6B49124C64C2A241C4075D4AF16299EB87A6585BAE917" ++ " DEF27FCDD165764D069BC18D16527B29DAAB549F7BBED4A7C6A842D203ED6613" ++ " 6E2411744E432CD26D940132F25874483DCAEECDFD95744819CBCF1EA810681C" ++ " 42907EBCB1C7EAFBE75C87EC32C5413EA10476545D3FC7B2ADB1B66B7F200918" ++ " 664B0E5261C2895AA28B0DE321E921B3F877172CCCAB81F43EF98002916156F6" ++ " CB#)\n" ++ " (e #010001#)))\n", ++ "(data\n (flags pkcs1)\n" ++ " (hash sha256 " ++ "#00112233445566778899AABBCCDDEEFF000102030405060708090A0B0C0D0E0F#))\n", ++ 0 ++ }, ++ { /* RSA with non-compliant hash for signing */ ++ "(private-key" ++ " (rsa" ++ " (n #009F56231A3D82E3E7D613D59D53E9AB921BEF9F08A782AED0B6E46ADBC853EC" ++ " 7C71C422435A3CD8FA0DB9EFD55CD3295BADC4E8E2E2B94E15AE82866AB8ADE8" ++ " 7E469FAE76DC3577DE87F1F419C4EB41123DFAF8D16922D5EDBAD6E9076D5A1C" ++ " 958106F0AE5E2E9193C6B49124C64C2A241C4075D4AF16299EB87A6585BAE917" ++ " DEF27FCDD165764D069BC18D16527B29DAAB549F7BBED4A7C6A842D203ED6613" ++ " 6E2411744E432CD26D940132F25874483DCAEECDFD95744819CBCF1EA810681C" ++ " 42907EBCB1C7EAFBE75C87EC32C5413EA10476545D3FC7B2ADB1B66B7F200918" ++ " 664B0E5261C2895AA28B0DE321E921B3F877172CCCAB81F43EF98002916156F6" ++ " CB#)\n" ++ " (e #010001#)\n" ++ " (d #07EF82500C403899934FE993AC5A36F14FF2DF38CF1EF315F205EE4C83EDAA19" ++ " 8890FC23DE9AA933CAFB37B6A8A8DBA675411958337287310D3FF2F1DDC0CB93" ++ " 7E70F57F75F833C021852B631D2B9A520E4431A03C5C3FCB5742DCD841D9FB12" ++ " 771AA1620DCEC3F1583426066ED9DC3F7028C5B59202C88FDF20396E2FA0EC4F" ++ " 5A22D9008F3043673931BC14A5046D6327398327900867E39CC61B2D1AFE2F48" ++ " EC8E1E3861C68D257D7425F4E6F99ABD77D61F10CA100EFC14389071831B33DD" ++ " 69CC8EABEF860D1DC2AAA84ABEAE5DFC91BC124DAF0F4C8EF5BBEA436751DE84" ++ " 3A8063E827A024466F44C28614F93B0732A100D4A0D86D532FE1E22C7725E401" ++ " #)\n" ++ " (p #00C29D438F115825779631CD665A5739367F3E128ADC29766483A46CA80897E0" ++ " 79B32881860B8F9A6A04C2614A904F6F2578DAE13EA67CD60AE3D0AA00A1FF9B" ++ " 441485E44B2DC3D0B60260FBFE073B5AC72FAF67964DE15C8212C389D20DB9CF" ++ " 54AF6AEF5C4196EAA56495DD30CF709F499D5AB30CA35E086C2A1589D6283F17" ++ " 83#)\n" ++ " (q #00D1984135231CB243FE959C0CBEF551EDD986AD7BEDF71EDF447BE3DA27AF46" ++ " 79C974A6FA69E4D52FE796650623DE70622862713932AA2FD9F2EC856EAEAA77" ++ " 88B4EA6084DC81C902F014829B18EA8B2666EC41586818E0589E18876065F97E" ++ " 8D22CE2DA53A05951EC132DCEF41E70A9C35F4ACC268FFAC2ADF54FA1DA110B9" ++ " 19#)\n" ++ " (u #67CF0FD7635205DD80FA814EE9E9C267C17376BF3209FB5D1BC42890D2822A04" ++ " 479DAF4D5B6ED69D0F8D1AF94164D07F8CD52ECEFE880641FA0F41DDAB1785E4" ++ " A37A32F997A516480B4CD4F6482B9466A1765093ED95023CA32D5EDC1E34CEE9" ++ " AF595BC51FE43C4BF810FA225AF697FB473B83815966188A4312C048B885E3F7" ++ " #)))\n", ++ "(public-key\n" ++ " (rsa\n" ++ " (n #009F56231A3D82E3E7D613D59D53E9AB921BEF9F08A782AED0B6E46ADBC853EC" ++ " 7C71C422435A3CD8FA0DB9EFD55CD3295BADC4E8E2E2B94E15AE82866AB8ADE8" ++ " 7E469FAE76DC3577DE87F1F419C4EB41123DFAF8D16922D5EDBAD6E9076D5A1C" ++ " 958106F0AE5E2E9193C6B49124C64C2A241C4075D4AF16299EB87A6585BAE917" ++ " DEF27FCDD165764D069BC18D16527B29DAAB549F7BBED4A7C6A842D203ED6613" ++ " 6E2411744E432CD26D940132F25874483DCAEECDFD95744819CBCF1EA810681C" ++ " 42907EBCB1C7EAFBE75C87EC32C5413EA10476545D3FC7B2ADB1B66B7F200918" ++ " 664B0E5261C2895AA28B0DE321E921B3F877172CCCAB81F43EF98002916156F6" ++ " CB#)\n" ++ " (e #010001#)))\n", ++ "(data\n (flags pkcs1)\n" ++ " (hash sha1 #11223344556677889900AABBCCDDEEFF10203040#))\n", ++ 1 ++ }, ++ { /* RSA with unknown hash for signing */ ++ "(private-key" ++ " (rsa" ++ " (n #009F56231A3D82E3E7D613D59D53E9AB921BEF9F08A782AED0B6E46ADBC853EC" ++ " 7C71C422435A3CD8FA0DB9EFD55CD3295BADC4E8E2E2B94E15AE82866AB8ADE8" ++ " 7E469FAE76DC3577DE87F1F419C4EB41123DFAF8D16922D5EDBAD6E9076D5A1C" ++ " 958106F0AE5E2E9193C6B49124C64C2A241C4075D4AF16299EB87A6585BAE917" ++ " DEF27FCDD165764D069BC18D16527B29DAAB549F7BBED4A7C6A842D203ED6613" ++ " 6E2411744E432CD26D940132F25874483DCAEECDFD95744819CBCF1EA810681C" ++ " 42907EBCB1C7EAFBE75C87EC32C5413EA10476545D3FC7B2ADB1B66B7F200918" ++ " 664B0E5261C2895AA28B0DE321E921B3F877172CCCAB81F43EF98002916156F6" ++ " CB#)\n" ++ " (e #010001#)\n" ++ " (d #07EF82500C403899934FE993AC5A36F14FF2DF38CF1EF315F205EE4C83EDAA19" ++ " 8890FC23DE9AA933CAFB37B6A8A8DBA675411958337287310D3FF2F1DDC0CB93" ++ " 7E70F57F75F833C021852B631D2B9A520E4431A03C5C3FCB5742DCD841D9FB12" ++ " 771AA1620DCEC3F1583426066ED9DC3F7028C5B59202C88FDF20396E2FA0EC4F" ++ " 5A22D9008F3043673931BC14A5046D6327398327900867E39CC61B2D1AFE2F48" ++ " EC8E1E3861C68D257D7425F4E6F99ABD77D61F10CA100EFC14389071831B33DD" ++ " 69CC8EABEF860D1DC2AAA84ABEAE5DFC91BC124DAF0F4C8EF5BBEA436751DE84" ++ " 3A8063E827A024466F44C28614F93B0732A100D4A0D86D532FE1E22C7725E401" ++ " #)\n" ++ " (p #00C29D438F115825779631CD665A5739367F3E128ADC29766483A46CA80897E0" ++ " 79B32881860B8F9A6A04C2614A904F6F2578DAE13EA67CD60AE3D0AA00A1FF9B" ++ " 441485E44B2DC3D0B60260FBFE073B5AC72FAF67964DE15C8212C389D20DB9CF" ++ " 54AF6AEF5C4196EAA56495DD30CF709F499D5AB30CA35E086C2A1589D6283F17" ++ " 83#)\n" ++ " (q #00D1984135231CB243FE959C0CBEF551EDD986AD7BEDF71EDF447BE3DA27AF46" ++ " 79C974A6FA69E4D52FE796650623DE70622862713932AA2FD9F2EC856EAEAA77" ++ " 88B4EA6084DC81C902F014829B18EA8B2666EC41586818E0589E18876065F97E" ++ " 8D22CE2DA53A05951EC132DCEF41E70A9C35F4ACC268FFAC2ADF54FA1DA110B9" ++ " 19#)\n" ++ " (u #67CF0FD7635205DD80FA814EE9E9C267C17376BF3209FB5D1BC42890D2822A04" ++ " 479DAF4D5B6ED69D0F8D1AF94164D07F8CD52ECEFE880641FA0F41DDAB1785E4" ++ " A37A32F997A516480B4CD4F6482B9466A1765093ED95023CA32D5EDC1E34CEE9" ++ " AF595BC51FE43C4BF810FA225AF697FB473B83815966188A4312C048B885E3F7" ++ " #)))\n", ++ "(public-key\n" ++ " (rsa\n" ++ " (n #009F56231A3D82E3E7D613D59D53E9AB921BEF9F08A782AED0B6E46ADBC853EC" ++ " 7C71C422435A3CD8FA0DB9EFD55CD3295BADC4E8E2E2B94E15AE82866AB8ADE8" ++ " 7E469FAE76DC3577DE87F1F419C4EB41123DFAF8D16922D5EDBAD6E9076D5A1C" ++ " 958106F0AE5E2E9193C6B49124C64C2A241C4075D4AF16299EB87A6585BAE917" ++ " DEF27FCDD165764D069BC18D16527B29DAAB549F7BBED4A7C6A842D203ED6613" ++ " 6E2411744E432CD26D940132F25874483DCAEECDFD95744819CBCF1EA810681C" ++ " 42907EBCB1C7EAFBE75C87EC32C5413EA10476545D3FC7B2ADB1B66B7F200918" ++ " 664B0E5261C2895AA28B0DE321E921B3F877172CCCAB81F43EF98002916156F6" ++ " CB#)\n" ++ " (e #010001#)))\n", ++ "(data\n (flags pkcs1-raw)\n" ++ " (value " ++ "#00112233445566778899AABBCCDDEEFF000102030405060708090A0B0C0D0E0F#))\n", ++ 1 ++ }, ++ { /* RSA with compliant hash for signing */ ++ "(private-key" ++ " (rsa" ++ " (n #009F56231A3D82E3E7D613D59D53E9AB921BEF9F08A782AED0B6E46ADBC853EC" ++ " 7C71C422435A3CD8FA0DB9EFD55CD3295BADC4E8E2E2B94E15AE82866AB8ADE8" ++ " 7E469FAE76DC3577DE87F1F419C4EB41123DFAF8D16922D5EDBAD6E9076D5A1C" ++ " 958106F0AE5E2E9193C6B49124C64C2A241C4075D4AF16299EB87A6585BAE917" ++ " DEF27FCDD165764D069BC18D16527B29DAAB549F7BBED4A7C6A842D203ED6613" ++ " 6E2411744E432CD26D940132F25874483DCAEECDFD95744819CBCF1EA810681C" ++ " 42907EBCB1C7EAFBE75C87EC32C5413EA10476545D3FC7B2ADB1B66B7F200918" ++ " 664B0E5261C2895AA28B0DE321E921B3F877172CCCAB81F43EF98002916156F6" ++ " CB#)\n" ++ " (e #010001#)\n" ++ " (d #07EF82500C403899934FE993AC5A36F14FF2DF38CF1EF315F205EE4C83EDAA19" ++ " 8890FC23DE9AA933CAFB37B6A8A8DBA675411958337287310D3FF2F1DDC0CB93" ++ " 7E70F57F75F833C021852B631D2B9A520E4431A03C5C3FCB5742DCD841D9FB12" ++ " 771AA1620DCEC3F1583426066ED9DC3F7028C5B59202C88FDF20396E2FA0EC4F" ++ " 5A22D9008F3043673931BC14A5046D6327398327900867E39CC61B2D1AFE2F48" ++ " EC8E1E3861C68D257D7425F4E6F99ABD77D61F10CA100EFC14389071831B33DD" ++ " 69CC8EABEF860D1DC2AAA84ABEAE5DFC91BC124DAF0F4C8EF5BBEA436751DE84" ++ " 3A8063E827A024466F44C28614F93B0732A100D4A0D86D532FE1E22C7725E401" ++ " #)\n" ++ " (p #00C29D438F115825779631CD665A5739367F3E128ADC29766483A46CA80897E0" ++ " 79B32881860B8F9A6A04C2614A904F6F2578DAE13EA67CD60AE3D0AA00A1FF9B" ++ " 441485E44B2DC3D0B60260FBFE073B5AC72FAF67964DE15C8212C389D20DB9CF" ++ " 54AF6AEF5C4196EAA56495DD30CF709F499D5AB30CA35E086C2A1589D6283F17" ++ " 83#)\n" ++ " (q #00D1984135231CB243FE959C0CBEF551EDD986AD7BEDF71EDF447BE3DA27AF46" ++ " 79C974A6FA69E4D52FE796650623DE70622862713932AA2FD9F2EC856EAEAA77" ++ " 88B4EA6084DC81C902F014829B18EA8B2666EC41586818E0589E18876065F97E" ++ " 8D22CE2DA53A05951EC132DCEF41E70A9C35F4ACC268FFAC2ADF54FA1DA110B9" ++ " 19#)\n" ++ " (u #67CF0FD7635205DD80FA814EE9E9C267C17376BF3209FB5D1BC42890D2822A04" ++ " 479DAF4D5B6ED69D0F8D1AF94164D07F8CD52ECEFE880641FA0F41DDAB1785E4" ++ " A37A32F997A516480B4CD4F6482B9466A1765093ED95023CA32D5EDC1E34CEE9" ++ " AF595BC51FE43C4BF810FA225AF697FB473B83815966188A4312C048B885E3F7" ++ " #)))\n", ++ "(public-key\n" ++ " (rsa\n" ++ " (n #009F56231A3D82E3E7D613D59D53E9AB921BEF9F08A782AED0B6E46ADBC853EC" ++ " 7C71C422435A3CD8FA0DB9EFD55CD3295BADC4E8E2E2B94E15AE82866AB8ADE8" ++ " 7E469FAE76DC3577DE87F1F419C4EB41123DFAF8D16922D5EDBAD6E9076D5A1C" ++ " 958106F0AE5E2E9193C6B49124C64C2A241C4075D4AF16299EB87A6585BAE917" ++ " DEF27FCDD165764D069BC18D16527B29DAAB549F7BBED4A7C6A842D203ED6613" ++ " 6E2411744E432CD26D940132F25874483DCAEECDFD95744819CBCF1EA810681C" ++ " 42907EBCB1C7EAFBE75C87EC32C5413EA10476545D3FC7B2ADB1B66B7F200918" ++ " 664B0E5261C2895AA28B0DE321E921B3F877172CCCAB81F43EF98002916156F6" ++ " CB#)\n" ++ " (e #010001#)))\n", ++ "(data\n (flags pss)\n" ++ " (hash sha256 " ++ "#00112233445566778899AABBCCDDEEFF000102030405060708090A0B0C0D0E0F#))\n", ++ 0 ++ }, ++ { /* RSA with non-compliant hash for signing */ ++ "(private-key" ++ " (rsa" ++ " (n #009F56231A3D82E3E7D613D59D53E9AB921BEF9F08A782AED0B6E46ADBC853EC" ++ " 7C71C422435A3CD8FA0DB9EFD55CD3295BADC4E8E2E2B94E15AE82866AB8ADE8" ++ " 7E469FAE76DC3577DE87F1F419C4EB41123DFAF8D16922D5EDBAD6E9076D5A1C" ++ " 958106F0AE5E2E9193C6B49124C64C2A241C4075D4AF16299EB87A6585BAE917" ++ " DEF27FCDD165764D069BC18D16527B29DAAB549F7BBED4A7C6A842D203ED6613" ++ " 6E2411744E432CD26D940132F25874483DCAEECDFD95744819CBCF1EA810681C" ++ " 42907EBCB1C7EAFBE75C87EC32C5413EA10476545D3FC7B2ADB1B66B7F200918" ++ " 664B0E5261C2895AA28B0DE321E921B3F877172CCCAB81F43EF98002916156F6" ++ " CB#)\n" ++ " (e #010001#)\n" ++ " (d #07EF82500C403899934FE993AC5A36F14FF2DF38CF1EF315F205EE4C83EDAA19" ++ " 8890FC23DE9AA933CAFB37B6A8A8DBA675411958337287310D3FF2F1DDC0CB93" ++ " 7E70F57F75F833C021852B631D2B9A520E4431A03C5C3FCB5742DCD841D9FB12" ++ " 771AA1620DCEC3F1583426066ED9DC3F7028C5B59202C88FDF20396E2FA0EC4F" ++ " 5A22D9008F3043673931BC14A5046D6327398327900867E39CC61B2D1AFE2F48" ++ " EC8E1E3861C68D257D7425F4E6F99ABD77D61F10CA100EFC14389071831B33DD" ++ " 69CC8EABEF860D1DC2AAA84ABEAE5DFC91BC124DAF0F4C8EF5BBEA436751DE84" ++ " 3A8063E827A024466F44C28614F93B0732A100D4A0D86D532FE1E22C7725E401" ++ " #)\n" ++ " (p #00C29D438F115825779631CD665A5739367F3E128ADC29766483A46CA80897E0" ++ " 79B32881860B8F9A6A04C2614A904F6F2578DAE13EA67CD60AE3D0AA00A1FF9B" ++ " 441485E44B2DC3D0B60260FBFE073B5AC72FAF67964DE15C8212C389D20DB9CF" ++ " 54AF6AEF5C4196EAA56495DD30CF709F499D5AB30CA35E086C2A1589D6283F17" ++ " 83#)\n" ++ " (q #00D1984135231CB243FE959C0CBEF551EDD986AD7BEDF71EDF447BE3DA27AF46" ++ " 79C974A6FA69E4D52FE796650623DE70622862713932AA2FD9F2EC856EAEAA77" ++ " 88B4EA6084DC81C902F014829B18EA8B2666EC41586818E0589E18876065F97E" ++ " 8D22CE2DA53A05951EC132DCEF41E70A9C35F4ACC268FFAC2ADF54FA1DA110B9" ++ " 19#)\n" ++ " (u #67CF0FD7635205DD80FA814EE9E9C267C17376BF3209FB5D1BC42890D2822A04" ++ " 479DAF4D5B6ED69D0F8D1AF94164D07F8CD52ECEFE880641FA0F41DDAB1785E4" ++ " A37A32F997A516480B4CD4F6482B9466A1765093ED95023CA32D5EDC1E34CEE9" ++ " AF595BC51FE43C4BF810FA225AF697FB473B83815966188A4312C048B885E3F7" ++ " #)))\n", ++ "(public-key\n" ++ " (rsa\n" ++ " (n #009F56231A3D82E3E7D613D59D53E9AB921BEF9F08A782AED0B6E46ADBC853EC" ++ " 7C71C422435A3CD8FA0DB9EFD55CD3295BADC4E8E2E2B94E15AE82866AB8ADE8" ++ " 7E469FAE76DC3577DE87F1F419C4EB41123DFAF8D16922D5EDBAD6E9076D5A1C" ++ " 958106F0AE5E2E9193C6B49124C64C2A241C4075D4AF16299EB87A6585BAE917" ++ " DEF27FCDD165764D069BC18D16527B29DAAB549F7BBED4A7C6A842D203ED6613" ++ " 6E2411744E432CD26D940132F25874483DCAEECDFD95744819CBCF1EA810681C" ++ " 42907EBCB1C7EAFBE75C87EC32C5413EA10476545D3FC7B2ADB1B66B7F200918" ++ " 664B0E5261C2895AA28B0DE321E921B3F877172CCCAB81F43EF98002916156F6" ++ " CB#)\n" ++ " (e #010001#)))\n", ++ "(data\n (flags pss)\n" ++ " (hash sha1 #11223344556677889900AABBCCDDEEFF10203040#))\n", ++ 1 ++ } + }; + int tvidx; + gpg_error_t err; +-- +2.49.0 + diff --git a/libgcrypt-cipher-visibility-Differentiate-use-of-random-override-in-the-SLI.patch b/libgcrypt-cipher-visibility-Differentiate-use-of-random-override-in-the-SLI.patch new file mode 100644 index 0000000..413aa34 --- /dev/null +++ b/libgcrypt-cipher-visibility-Differentiate-use-of-random-override-in-the-SLI.patch @@ -0,0 +1,107 @@ +From 234eb316b0a04c50e8511a570775ded45060f18b Mon Sep 17 00:00:00 2001 +From: Lucas Mulling via Gcrypt-devel +Date: Wed, 26 Feb 2025 17:19:24 -0300 +Subject: [PATCH 08/14] cipher,visibility: Differentiate use of random-override + in the SLI +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* cipher/pubkey-util.c (_gcry_pk_util_data_to_mpi, +_gcry_pk_single_data_push, _gcry_pk_util_free_encoding_ctx): +Differentiate use of random-override in the SLI. +* src/visibility.c (gcry_pk_random_override_new): +Differentiate use explicit random override in the SLI. + +GnuPG-bug-id: 7338 +Signed-off-by: Lucas Mulling +Signed-off-by: Lucas Mülling +--- + cipher/pubkey-util.c | 33 +++++++++++++++++++++++++++++++++ + src/visibility.c | 12 ++++++++++++ + 2 files changed, 45 insertions(+) + +diff --git a/cipher/pubkey-util.c b/cipher/pubkey-util.c +index e7355569..66a04f13 100644 +--- a/cipher/pubkey-util.c ++++ b/cipher/pubkey-util.c +@@ -973,6 +973,17 @@ _gcry_pk_util_data_to_mpi (gcry_sexp_t input, gcry_mpi_t *ret_mpi, + list = sexp_find_token (ldata, "random-override", 0); + if (list) + { ++ if (fips_mode ()) ++ { ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) ++ { ++ sexp_release (list); ++ rc = GPG_ERR_INV_FLAG; ++ goto leave; ++ } ++ else ++ fips_service_indicator_mark_non_compliant (); ++ } + s = sexp_nth_data (list, 1, &n); + if (!s) + rc = GPG_ERR_NO_OBJ; +@@ -1149,6 +1160,17 @@ _gcry_pk_util_data_to_mpi (gcry_sexp_t input, gcry_mpi_t *ret_mpi, + list = sexp_find_token (ldata, "random-override", 0); + if (list) + { ++ if (fips_mode ()) ++ { ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) ++ { ++ sexp_release (list); ++ rc = GPG_ERR_INV_FLAG; ++ goto leave; ++ } ++ else ++ fips_service_indicator_mark_non_compliant (); ++ } + s = sexp_nth_data (list, 1, &n); + if (!s) + rc = GPG_ERR_NO_OBJ; +@@ -1248,6 +1270,17 @@ _gcry_pk_util_data_to_mpi (gcry_sexp_t input, gcry_mpi_t *ret_mpi, + list = sexp_find_token (ldata, "random-override", 0); + if (list) + { ++ if (fips_mode ()) ++ { ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) ++ { ++ sexp_release (list); ++ rc = GPG_ERR_INV_FLAG; ++ goto leave; ++ } ++ else ++ fips_service_indicator_mark_non_compliant (); ++ } + s = sexp_nth_data (list, 1, &n); + if (!s) + rc = GPG_ERR_NO_OBJ; +diff --git a/src/visibility.c b/src/visibility.c +index 4134446a..ccd0de69 100644 +--- a/src/visibility.c ++++ b/src/visibility.c +@@ -1085,6 +1085,18 @@ gcry_pk_hash_verify (gcry_sexp_t sigval, const char *data_tmpl, gcry_sexp_t pkey + gcry_error_t + gcry_pk_random_override_new (gcry_ctx_t *r_ctx, const unsigned char *p, size_t len) + { ++ if (!fips_is_operational ()) ++ return gpg_error (fips_not_operational ()); ++ fips_service_indicator_init (); ++ ++ if (fips_mode ()) ++ { ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) ++ return gpg_error (GPG_ERR_INV_OP); ++ else ++ fips_service_indicator_mark_non_compliant (); ++ } ++ + return gpg_error (_gcry_pk_single_data_push (r_ctx, p, len)); + } + +-- +2.49.0 + diff --git a/libgcrypt-doc-Add-about-GCRYCTL_FIPS_SERVICE_INDICATOR.patch b/libgcrypt-doc-Add-about-GCRYCTL_FIPS_SERVICE_INDICATOR.patch new file mode 100644 index 0000000..a9e9522 --- /dev/null +++ b/libgcrypt-doc-Add-about-GCRYCTL_FIPS_SERVICE_INDICATOR.patch @@ -0,0 +1,66 @@ +From 636f40cb78587635ef663bfc3430937cf140f245 Mon Sep 17 00:00:00 2001 +From: NIIBE Yutaka +Date: Thu, 13 Mar 2025 15:02:58 +0900 +Subject: [PATCH 13/14] doc: Add about GCRYCTL_FIPS_SERVICE_INDICATOR. +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* doc/gcrypt.texi (GCRYCTL_FIPS_SERVICE_INDICATOR): Add a description. +(GCRYCTL_FIPS_REJECT_NON_FIPS): Likewise. + +-- + +GnuPG-bug-id: 7338 +Signed-off-by: NIIBE Yutaka +Signed-off-by: Lucas Mülling +--- + doc/gcrypt.texi | 32 ++++++++++++++++++++++++++++++++ + 1 file changed, 32 insertions(+) + +diff --git a/doc/gcrypt.texi b/doc/gcrypt.texi +index 5d428738..6e82a41b 100644 +--- a/doc/gcrypt.texi ++++ b/doc/gcrypt.texi +@@ -1052,6 +1052,38 @@ is responsible to check also the internal members. For example: + /* ok */ + @end example + ++@item GCRYCTL_FIPS_SERVICE_INDICATOR; Arguments: none ++This commands provides ``dynamic'' service indicator. ++ ++After a function call (of the use of security services), this command ++can be used to check if the call is valid or not. If the computation ++is done in an approved way, it returns @code{GPG_ERR_NO_ERROR}. ++Otherwise @code{GPG_ERR_NOT_SUPPORTED} is returned. ++ ++An application may use this command directly or use the convenience ++macro below. ++ ++@deftypefun gcry_error_t gcry_get_fips_service_indicator (void) ++ ++Returns @code{GPG_ERR_NO_ERROR} if a preceeding function call is ++valid. Otherwise @code{GPG_ERR_NOT_SUPPORTED} is returned. ++@end deftypefun ++ ++@item GCRYCTL_FIPS_REJECT_NON_FIPS; Arguments: unsigned int flags ++In Libgcrypt 1.10, static implicit indicator is used; For an approved ++function (which can be checked by ++GCRYCTL_FIPS_SERVICE_INDICATOR_FUNCTION command) with an approved ++algo/operation (which can be checked GCRYCTL_FIPS_SERVICE_INDICATOR_* ++command), success of the function call means that it's valid and error ++return (rejection) means it's invalid. This command controls thread ++specific behavior of the rejection. ++ ++When using ``dynamic'' service indicator, this command with FLAGS=0 ++disables all rejections. ++@example ++ gcry_control (GCRYCTL_FIPS_REJECT_NON_FIPS, 0); ++@endexample ++ + @end table + + @end deftypefun +-- +2.49.0 + diff --git a/libgcrypt-doc-Fix-syntax-error.patch b/libgcrypt-doc-Fix-syntax-error.patch new file mode 100644 index 0000000..b85eb54 --- /dev/null +++ b/libgcrypt-doc-Fix-syntax-error.patch @@ -0,0 +1,31 @@ +From 22e65f6f5b8dbddf925151894426e4c06d33803b Mon Sep 17 00:00:00 2001 +From: Werner Koch +Date: Thu, 13 Mar 2025 18:06:37 +0100 +Subject: [PATCH 14/14] doc: Fix syntax error +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +-- + +Signed-off-by: Lucas Mülling +--- + doc/gcrypt.texi | 2 +- + 1 file changed, 1 insertion(+), 1 deletion(-) + +diff --git a/doc/gcrypt.texi b/doc/gcrypt.texi +index 6e82a41b..eeab1a78 100644 +--- a/doc/gcrypt.texi ++++ b/doc/gcrypt.texi +@@ -1082,7 +1082,7 @@ When using ``dynamic'' service indicator, this command with FLAGS=0 + disables all rejections. + @example + gcry_control (GCRYCTL_FIPS_REJECT_NON_FIPS, 0); +-@endexample ++@end example + + @end table + +-- +2.49.0 + diff --git a/libgcrypt-fips-Change-the-internal-API-for-new-FIPS-service-indicator.patch b/libgcrypt-fips-Change-the-internal-API-for-new-FIPS-service-indicator.patch new file mode 100644 index 0000000..8638218 --- /dev/null +++ b/libgcrypt-fips-Change-the-internal-API-for-new-FIPS-service-indicator.patch @@ -0,0 +1,140 @@ +From 4799914966a7f94f41e1ed5b7b62fded7ba09704 Mon Sep 17 00:00:00 2001 +From: NIIBE Yutaka +Date: Thu, 12 Dec 2024 11:03:38 +0900 +Subject: [PATCH 01/19] fips: Change the internal API for new FIPS service + indicator. +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* src/gcrypt-int.h (fips_service_indicator_init): Initialize by 0. +(fips_service_indicator_mark_success): Remove. +(fips_service_indicator_mark_non_compliant): New. +* cipher/kdf.c (_gcry_kdf_derive): Follow the change of the API. +* cipher/md.c (_gcry_md_hash_buffer): Likewise. +(_gcry_md_hash_buffers_extract): Likewise. + +-- + +GnuPG-bug-id: 7338 +Signed-off-by: NIIBE Yutaka +Signed-off-by: Lucas Mülling +--- + cipher/kdf.c | 17 +++++++++-------- + cipher/md.c | 8 ++++---- + src/gcrypt-int.h | 9 +++------ + 3 files changed, 16 insertions(+), 18 deletions(-) + +diff --git a/cipher/kdf.c b/cipher/kdf.c +index 1eae2b90..71156ea4 100644 +--- a/cipher/kdf.c ++++ b/cipher/kdf.c +@@ -248,6 +248,7 @@ _gcry_kdf_derive (const void *passphrase, size_t passphraselen, + size_t keysize, void *keybuffer) + { + gpg_err_code_t ec; ++ int is_compliant_algo = 0; + + if (!passphrase) + { +@@ -279,35 +280,32 @@ _gcry_kdf_derive (const void *passphrase, size_t passphraselen, + break; + + case GCRY_KDF_PBKDF2: ++ is_compliant_algo = 1; + if (!saltlen || !iterations) + ec = GPG_ERR_INV_VALUE; + else + { +- int is_compliant = 1; +- + if (fips_mode ()) + { + /* FIPS requires minimum passphrase length, see FIPS 140-3 IG D.N */ + if (passphraselen < 8) +- is_compliant &= 0; ++ fips_service_indicator_mark_non_compliant (); + + /* FIPS requires minimum salt length of 128 b (SP 800-132 sec. 5.1, p.6) */ + if (saltlen < 16) +- is_compliant &= 0; ++ fips_service_indicator_mark_non_compliant (); + + /* FIPS requires minimum iterations bound (SP 800-132 sec 5.2, p.6) */ + if (iterations < 1000) +- is_compliant &= 0; ++ fips_service_indicator_mark_non_compliant (); + + /* Check minimum key size */ + if (keysize < 14) +- is_compliant &= 0; ++ fips_service_indicator_mark_non_compliant (); + } + + ec = _gcry_kdf_pkdf2 (passphrase, passphraselen, subalgo, + salt, saltlen, iterations, keysize, keybuffer); +- if (!ec) +- fips_service_indicator_mark_success (is_compliant); + } + break; + +@@ -326,6 +324,9 @@ _gcry_kdf_derive (const void *passphrase, size_t passphraselen, + break; + } + ++ if (!ec && !is_compliant_algo && fips_mode ()) ++ fips_service_indicator_mark_non_compliant (); ++ + leave: + return ec; + } +diff --git a/cipher/md.c b/cipher/md.c +index c2bd18c6..ef2fc5a4 100644 +--- a/cipher/md.c ++++ b/cipher/md.c +@@ -1286,8 +1286,8 @@ _gcry_md_hash_buffer (int algo, void *digest, + + if (fips_mode ()) + { +- int is_compliant = spec->flags.fips; +- fips_service_indicator_mark_success (is_compliant); ++ if (!spec->flags.fips) ++ fips_service_indicator_mark_non_compliant (); + } + } + +@@ -1384,8 +1384,8 @@ _gcry_md_hash_buffers_extract (int algo, unsigned int flags, void *digest, + + if (fips_mode ()) + { +- int is_compliant = spec->flags.fips; +- fips_service_indicator_mark_success (is_compliant); ++ if (!spec->flags.fips) ++ fips_service_indicator_mark_non_compliant (); + } + + return 0; +diff --git a/src/gcrypt-int.h b/src/gcrypt-int.h +index 7f894737..aa49d766 100644 +--- a/src/gcrypt-int.h ++++ b/src/gcrypt-int.h +@@ -303,13 +303,10 @@ unsigned long _gcry_thread_context_get_fsi (void); + #define fips_service_indicator_init() do \ + { \ + if (fips_mode ()) \ +- _gcry_thread_context_set_fsi (1); \ +- } while (0) +-#define fips_service_indicator_mark_success(is_compliant) do \ +- { \ +- if (is_compliant && fips_mode ()) \ +- _gcry_thread_context_set_fsi (0); \ ++ _gcry_thread_context_set_fsi (0); \ + } while (0) ++/* Should be used only when fips_mode()==TRUE. */ ++#define fips_service_indicator_mark_non_compliant() _gcry_thread_context_set_fsi (1) + + /* Return a pointer to a string containing a description of the error + code in the error value ERR. */ +-- +2.49.0 + diff --git a/libgcrypt-fips-Fix-GCRY_FIPS_FLAG_REJECT_MD.patch b/libgcrypt-fips-Fix-GCRY_FIPS_FLAG_REJECT_MD.patch new file mode 100644 index 0000000..aa6f093 --- /dev/null +++ b/libgcrypt-fips-Fix-GCRY_FIPS_FLAG_REJECT_MD.patch @@ -0,0 +1,42 @@ +From b9eb8f4cb81801d68580627ad2188607a8c5f2ec Mon Sep 17 00:00:00 2001 +From: NIIBE Yutaka +Date: Thu, 13 Mar 2025 15:01:21 +0900 +Subject: [PATCH 12/14] fips: Fix GCRY_FIPS_FLAG_REJECT_MD. +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* src/gcrypt.h.in (GCRY_FIPS_FLAG_REJECT_MD): Include SHA1. + +-- + +Fixes-commit: 4ee91a94bcdad32aed4364d09e3daf8841fa579f +Signed-off-by: NIIBE Yutaka +Signed-off-by: Lucas Mülling +--- + src/gcrypt.h.in | 8 +++++--- + 1 file changed, 5 insertions(+), 3 deletions(-) + +diff --git a/src/gcrypt.h.in b/src/gcrypt.h.in +index b2b8853f..a9c36aa6 100644 +--- a/src/gcrypt.h.in ++++ b/src/gcrypt.h.in +@@ -1994,10 +1994,12 @@ char *gcry_get_config (int mode, const char *what); + #define GCRY_FIPS_FLAG_REJECT_PK_ECC_K (1 << 10) + #define GCRY_FIPS_FLAG_REJECT_PK_FLAGS (1 << 11) + +-#define GCRY_FIPS_FLAG_REJECT_MD \ +- (GCRY_FIPS_FLAG_REJECT_MD_MD5 | GCRY_FIPS_FLAG_REJECT_MD_OTHERS) ++#define GCRY_FIPS_FLAG_REJECT_MD \ ++ (GCRY_FIPS_FLAG_REJECT_MD_MD5 | GCRY_FIPS_FLAG_REJECT_MD_SHA1 \ ++ | GCRY_FIPS_FLAG_REJECT_MD_OTHERS) + +-/* Note: Don't reject MD5, PK MD, PK GOST, PK SM2, PK ECC K, and PK FLAGS */ ++/* Note: Don't reject MD5, PK MD, PK GOST, PK SM2, ++ SHA1, PK ECC K, and PK FLAGS */ + #define GCRY_FIPS_FLAG_REJECT_COMPAT110 \ + (GCRY_FIPS_FLAG_REJECT_MD_OTHERS \ + | GCRY_FIPS_FLAG_REJECT_MAC \ +-- +2.49.0 + diff --git a/libgcrypt-fips-Introduce-GCRYCTL_FIPS_REJECT_NON_FIPS.patch b/libgcrypt-fips-Introduce-GCRYCTL_FIPS_REJECT_NON_FIPS.patch new file mode 100644 index 0000000..d08a59a --- /dev/null +++ b/libgcrypt-fips-Introduce-GCRYCTL_FIPS_REJECT_NON_FIPS.patch @@ -0,0 +1,261 @@ +From e52adf0948c60b2e9accd7996fcece0f9b443763 Mon Sep 17 00:00:00 2001 +From: NIIBE Yutaka +Date: Thu, 19 Dec 2024 11:30:28 +0900 +Subject: [PATCH 12/19] fips: Introduce GCRYCTL_FIPS_REJECT_NON_FIPS. +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* src/gcrypt.h.in (GCRYCTL_FIPS_REJECT_NON_FIPS): New. +(GCRY_FIPS_FLAG_REJECT_*): New. +* src/fips.c (struct gcry_thread_context): Add flags_reject_non_fips. +(the_tc): Add initial value. +(_gcry_thread_context_set_reject): New. +(_gcry_thread_context_check_rejection): New. +* src/gcrypt-int.h (fips_check_rejection): New. +* src/global.c (_gcry_vcontrol): Handle GCRYCTL_FIPS_REJECT_NON_FIPS. +* tests/t-fips-service-ind.c (main): Use GCRYCTL_FIPS_REJECT_NON_FIPS. + +-- + +GnuPG-bug-id: 7338 +Signed-off-by: NIIBE Yutaka +Signed-off-by: Lucas Mülling +--- + cipher/ecc-curves.c | 7 ++++++- + cipher/pubkey.c | 34 ++++++++++++++++++++++++++-------- + src/fips.c | 17 ++++++++++++++++- + src/gcrypt-int.h | 9 ++++++++- + src/gcrypt.h.in | 28 ++++++++++++++++++++++++++-- + src/global.c | 7 +++++++ + tests/t-fips-service-ind.c | 2 ++ + 7 files changed, 91 insertions(+), 13 deletions(-) + +Index: libgcrypt-1.11.0/cipher/ecc-curves.c +=================================================================== +--- libgcrypt-1.11.0.orig/cipher/ecc-curves.c ++++ libgcrypt-1.11.0/cipher/ecc-curves.c +@@ -645,7 +645,12 @@ _gcry_ecc_fill_in_curve (unsigned int nb + possible to bypass this check by specifying the curve parameters + directly. */ + if (fips_mode () && !domain_parms[idx].fips ) +- fips_service_indicator_mark_non_compliant (); ++ { ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) ++ return GPG_ERR_NOT_SUPPORTED; ++ else ++ fips_service_indicator_mark_non_compliant (); ++ } + + switch (domain_parms[idx].model) + { +Index: libgcrypt-1.11.0/cipher/pubkey.c +=================================================================== +--- libgcrypt-1.11.0.orig/cipher/pubkey.c ++++ libgcrypt-1.11.0/cipher/pubkey.c +@@ -510,7 +510,12 @@ prepare_datasexp_to_be_signed (const cha + algo = _gcry_md_get_algo (hd); + + if (fips_mode () && algo == GCRY_MD_SHA1) +- fips_service_indicator_mark_non_compliant (); ++ { ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) ++ return GPG_ERR_DIGEST_ALGO; ++ else ++ fips_service_indicator_mark_non_compliant (); ++ } + + digest_name = _gcry_md_algo_name (algo); + digest_size = (int)_gcry_md_get_algo_dlen (algo); +@@ -538,7 +543,12 @@ prepare_datasexp_to_be_signed (const cha + return GPG_ERR_DIGEST_ALGO; + } + else if (fips_mode () && algo == GCRY_MD_SHA1) +- fips_service_indicator_mark_non_compliant (); ++ { ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) ++ return GPG_ERR_DIGEST_ALGO; ++ else ++ fips_service_indicator_mark_non_compliant (); ++ } + + digest_size = (int)_gcry_md_get_algo_dlen (algo); + digest = _gcry_md_read (hd, algo); +@@ -611,11 +621,15 @@ _gcry_pk_sign_md (gcry_sexp_t *r_sig, co + if (rc) + goto leave; + +- if (!spec->flags.fips && fips_mode ()) +- fips_service_indicator_mark_non_compliant (); +- + if (spec->flags.disabled) + rc = GPG_ERR_PUBKEY_ALGO; ++ else if (!spec->flags.fips && fips_mode ()) ++ { ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) ++ return GPG_ERR_PUBKEY_ALGO; ++ else ++ fips_service_indicator_mark_non_compliant (); ++ } + else if (spec->sign) + rc = spec->sign (r_sig, s_data, keyparms); + else +@@ -689,11 +703,15 @@ _gcry_pk_verify_md (gcry_sexp_t s_sig, c + if (rc) + goto leave; + +- if (!spec->flags.fips && fips_mode ()) +- fips_service_indicator_mark_non_compliant (); +- + if (spec->flags.disabled) + rc = GPG_ERR_PUBKEY_ALGO; ++ else if (!spec->flags.fips && fips_mode ()) ++ { ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) ++ return GPG_ERR_PUBKEY_ALGO; ++ else ++ fips_service_indicator_mark_non_compliant (); ++ } + else if (spec->verify) + rc = spec->verify (s_sig, s_data, keyparms); + else +Index: libgcrypt-1.11.0/src/fips.c +=================================================================== +--- libgcrypt-1.11.0.orig/src/fips.c ++++ libgcrypt-1.11.0/src/fips.c +@@ -70,15 +70,30 @@ static enum module_states current_state; + + struct gcry_thread_context { + unsigned long fips_service_indicator; ++ unsigned int flags_reject_non_fips; + }; + + #ifdef HAVE_GCC_STORAGE_CLASS__THREAD +-static __thread struct gcry_thread_context the_tc; ++static __thread struct gcry_thread_context the_tc = { ++ 0, GCRY_FIPS_FLAG_REJECT_DEFAULT ++}; + #else + #error libgcrypt requires thread-local storage to support FIPS mode + #endif + + void ++_gcry_thread_context_set_reject (unsigned int flags) ++{ ++ the_tc.flags_reject_non_fips = flags; ++} ++ ++int ++_gcry_thread_context_check_rejection (unsigned int flag) ++{ ++ return !!(the_tc.flags_reject_non_fips & flag); ++} ++ ++void + _gcry_thread_context_set_fsi (unsigned long fsi) + { + the_tc.fips_service_indicator = fsi; +Index: libgcrypt-1.11.0/src/gcrypt-int.h +=================================================================== +--- libgcrypt-1.11.0.orig/src/gcrypt-int.h ++++ libgcrypt-1.11.0/src/gcrypt-int.h +@@ -297,6 +297,12 @@ void _gcry_set_log_handler (gcry_handler + void _gcry_set_gettext_handler (const char *(*f)(const char*)); + void _gcry_set_progress_handler (gcry_handler_progress_t cb, void *cb_data); + ++void _gcry_thread_context_set_reject (unsigned int flags); ++int _gcry_thread_context_check_rejection (unsigned int flag); ++ ++#define fips_check_rejection(flag) \ ++ _gcry_thread_context_check_rejection (flag) ++ + void _gcry_thread_context_set_fsi (unsigned long fsi); + unsigned long _gcry_thread_context_get_fsi (void); + #define fips_service_indicator_init() do \ +@@ -305,7 +311,8 @@ unsigned long _gcry_thread_context_get_f + _gcry_thread_context_set_fsi (0); \ + } while (0) + /* Should be used only when fips_mode()==TRUE. */ +-#define fips_service_indicator_mark_non_compliant() _gcry_thread_context_set_fsi (1) ++#define fips_service_indicator_mark_non_compliant() \ ++ _gcry_thread_context_set_fsi (1) + + /* Return a pointer to a string containing a description of the error + code in the error value ERR. */ +Index: libgcrypt-1.11.0/src/gcrypt.h.in +=================================================================== +--- libgcrypt-1.11.0.orig/src/gcrypt.h.in ++++ libgcrypt-1.11.0/src/gcrypt.h.in +@@ -338,7 +338,8 @@ enum gcry_ctl_cmds + GCRYCTL_MD_CUSTOMIZE = 88, + GCRYCTL_FIPS_SERVICE_INDICATOR_PK = 89, + GCRYCTL_FIPS_SERVICE_INDICATOR_HASH = 90, +- GCRYCTL_FIPS_SERVICE_INDICATOR = 91 ++ GCRYCTL_FIPS_SERVICE_INDICATOR = 91, ++ GCRYCTL_FIPS_REJECT_NON_FIPS = 92 + }; + + /* Perform various operations defined by CMD. */ +@@ -1971,7 +1972,30 @@ void gcry_log_debugsxp (const char *text + char *gcry_get_config (int mode, const char *what); + + /* Convinience macro to access the FIPS service indicator. */ +-#define gcry_get_fips_service_indicator() gcry_control (GCRYCTL_FIPS_SERVICE_INDICATOR) ++#define gcry_get_fips_service_indicator() \ ++ gcry_control (GCRYCTL_FIPS_SERVICE_INDICATOR) ++ ++#define GCRY_FIPS_FLAG_REJECT_KDF (1 << 0) ++#define GCRY_FIPS_FLAG_REJECT_MD_MD5 (1 << 1) ++#define GCRY_FIPS_FLAG_REJECT_MD_OTHERS (1 << 2) ++#define GCRY_FIPS_FLAG_REJECT_MAC (1 << 3) ++#define GCRY_FIPS_FLAG_REJECT_CIPHER (1 << 4) ++#define GCRY_FIPS_FLAG_REJECT_PK (1 << 5) ++ ++#define GCRY_FIPS_FLAG_REJECT_MD \ ++ (GCRY_FIPS_FLAG_REJECT_MD_MD5 | GCRY_FIPS_FLAG_REJECT_MD_OTHERS) ++ ++/* Note: Don't reject MD5 */ ++#define GCRY_FIPS_FLAG_REJECT_COMPAT110 \ ++ (GCRY_FIPS_FLAG_REJECT_MD_OTHERS \ ++ | GCRY_FIPS_FLAG_REJECT_MAC \ ++ | GCRY_FIPS_FLAG_REJECT_CIPHER \ ++ | GCRY_FIPS_FLAG_REJECT_KDF \ ++ | GCRY_FIPS_FLAG_REJECT_PK) ++ ++#define GCRY_FIPS_FLAG_REJECT_DEFAULT \ ++ GCRY_FIPS_FLAG_REJECT_COMPAT110 ++ + + /* Log levels used by the internal logging facility. */ + enum gcry_log_levels +Index: libgcrypt-1.11.0/src/global.c +=================================================================== +--- libgcrypt-1.11.0.orig/src/global.c ++++ libgcrypt-1.11.0/src/global.c +@@ -791,6 +791,13 @@ _gcry_vcontrol (enum gcry_ctl_cmds cmd, + rc = _gcry_fips_indicator (); + break; + ++ case GCRYCTL_FIPS_REJECT_NON_FIPS: ++ { ++ unsigned int flags = va_arg (arg_ptr, unsigned int); ++ _gcry_thread_context_set_reject (flags); ++ } ++ break; ++ + case GCRYCTL_FIPS_SERVICE_INDICATOR_CIPHER: + /* Get FIPS Service Indicator for a given symmetric algorithm and + * optional mode. Returns GPG_ERR_NO_ERROR if algorithm is allowed or +Index: libgcrypt-1.11.0/tests/t-fips-service-ind.c +=================================================================== +--- libgcrypt-1.11.0.orig/tests/t-fips-service-ind.c ++++ libgcrypt-1.11.0/tests/t-fips-service-ind.c +@@ -1007,6 +1007,8 @@ main (int argc, char **argv) + if (debug) + xgcry_control ((GCRYCTL_SET_DEBUG_FLAGS, 1u , 0)); + ++ xgcry_control ((GCRYCTL_FIPS_REJECT_NON_FIPS, 0)); ++ + check_digests (); + check_kdf_derive (); + check_md_o_w_r_c (); diff --git a/libgcrypt-fips-Introduce-GCRYCTL_FIPS_SERVICE_INDICATOR-and-the-macro.patch b/libgcrypt-fips-Introduce-GCRYCTL_FIPS_SERVICE_INDICATOR-and-the-macro.patch new file mode 100644 index 0000000..9355299 --- /dev/null +++ b/libgcrypt-fips-Introduce-GCRYCTL_FIPS_SERVICE_INDICATOR-and-the-macro.patch @@ -0,0 +1,101 @@ +From f51f4e98930e6b2175e85fe8a95b8b6a15ad5efa Mon Sep 17 00:00:00 2001 +From: NIIBE Yutaka +Date: Thu, 5 Dec 2024 11:34:32 +0900 +Subject: [PATCH 2/5] fips: Introduce GCRYCTL_FIPS_SERVICE_INDICATOR and the + macro. +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* src/fips.c (_gcry_fips_indicator): New. +* src/g10lib.h (_gcry_fips_indicator): New. +* src/gcrypt.h.in (GCRYCTL_FIPS_SERVICE_INDICATOR): New. +(gcry_get_fips_service_indicator): New. +* src/global.c (_gcry_vcontrol): Handle GCRYCTL_FIPS_SERVICE_INDICATOR. + +-- + +GnuPG-bug-id: 7338 +Signed-off-by: NIIBE Yutaka +Signed-off-by: Lucas Mülling +--- + src/fips.c | 11 +++++++++++ + src/g10lib.h | 2 ++ + src/gcrypt.h.in | 6 +++++- + src/global.c | 4 ++++ + 4 files changed, 22 insertions(+), 1 deletion(-) + +Index: libgcrypt-1.11.0/src/fips.c +=================================================================== +--- libgcrypt-1.11.0.orig/src/fips.c ++++ libgcrypt-1.11.0/src/fips.c +@@ -364,6 +364,17 @@ _gcry_fips_test_operational (void) + return result; + } + ++gpg_err_code_t ++_gcry_fips_indicator (void) ++{ ++ /* If anything recorded, it means that the operation is not ++ supported under FIPS mode. */ ++ if (_gcry_thread_context_get_fsi ()) ++ return GPG_ERR_NOT_SUPPORTED; ++ ++ return 0; ++} ++ + int + _gcry_fips_indicator_cipher (va_list arg_ptr) + { +Index: libgcrypt-1.11.0/src/g10lib.h +=================================================================== +--- libgcrypt-1.11.0.orig/src/g10lib.h ++++ libgcrypt-1.11.0/src/g10lib.h +@@ -468,6 +468,8 @@ void _gcry_fips_signal_error (const char + _gcry_fips_signal_error (__FILE__, __LINE__, NULL, 1, (a)) + #endif + ++gpg_err_code_t _gcry_fips_indicator (void); ++ + int _gcry_fips_indicator_cipher (va_list arg_ptr); + int _gcry_fips_indicator_hash (va_list arg_ptr); + int _gcry_fips_indicator_mac (va_list arg_ptr); +Index: libgcrypt-1.11.0/src/gcrypt.h.in +=================================================================== +--- libgcrypt-1.11.0.orig/src/gcrypt.h.in ++++ libgcrypt-1.11.0/src/gcrypt.h.in +@@ -337,7 +337,8 @@ enum gcry_ctl_cmds + GCRYCTL_FIPS_SERVICE_INDICATOR_PK_FLAGS = 87, + GCRYCTL_MD_CUSTOMIZE = 88, + GCRYCTL_FIPS_SERVICE_INDICATOR_PK = 89, +- GCRYCTL_FIPS_SERVICE_INDICATOR_HASH = 90 ++ GCRYCTL_FIPS_SERVICE_INDICATOR_HASH = 90, ++ GCRYCTL_FIPS_SERVICE_INDICATOR = 91 + }; + + /* Perform various operations defined by CMD. */ +@@ -1966,6 +1967,9 @@ void gcry_log_debugsxp (const char *text + + char *gcry_get_config (int mode, const char *what); + ++/* Convinience macro to access the FIPS service indicator. */ ++#define gcry_get_fips_service_indicator() gcry_control (GCRYCTL_FIPS_SERVICE_INDICATOR) ++ + /* Log levels used by the internal logging facility. */ + enum gcry_log_levels + { +Index: libgcrypt-1.11.0/src/global.c +=================================================================== +--- libgcrypt-1.11.0.orig/src/global.c ++++ libgcrypt-1.11.0/src/global.c +@@ -787,6 +787,10 @@ _gcry_vcontrol (enum gcry_ctl_cmds cmd, + rc = _gcry_fips_run_selftests (1); + break; + ++ case GCRYCTL_FIPS_SERVICE_INDICATOR: ++ rc = _gcry_fips_indicator (); ++ break; ++ + case GCRYCTL_FIPS_SERVICE_INDICATOR_CIPHER: + /* Get FIPS Service Indicator for a given symmetric algorithm and + * optional mode. Returns GPG_ERR_NO_ERROR if algorithm is allowed or diff --git a/libgcrypt-fips-Introduce-an-internal-API-for-FIPS-service-indicator.patch b/libgcrypt-fips-Introduce-an-internal-API-for-FIPS-service-indicator.patch new file mode 100644 index 0000000..b452626 --- /dev/null +++ b/libgcrypt-fips-Introduce-an-internal-API-for-FIPS-service-indicator.patch @@ -0,0 +1,332 @@ +From e1cf3123282525693b646499eb7efe4f2be4010a Mon Sep 17 00:00:00 2001 +From: NIIBE Yutaka +Date: Thu, 5 Dec 2024 11:06:37 +0900 +Subject: [PATCH 1/5] fips: Introduce an internal API for FIPS service + indicator. +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* configure.ac (HAVE_GCC_STORAGE_CLASS__THREAD): New. +* src/fips.c (struct gcry_thread_context): New. +(_gcry_thread_context_set_fsi, _gcry_thread_context_get_fsi): New. +* src/gcrypt-int.h (fips_service_indicator_init): New macro. +(fips_service_indicator_mark_success): New macro. +* tests/Makefile.am (tests_bin): Add t-thread-local. +* tests/t-thread-local.c: New. + +-- + +GnuPG-bug-id: 7340 +Signed-off-by: NIIBE Yutaka +Signed-off-by: Lucas Mülling +--- + configure.ac | 14 +++ + src/fips.c | 21 ++++- + src/gcrypt-int.h | 12 +++ + tests/Makefile.am | 2 +- + tests/t-thread-local.c | 196 +++++++++++++++++++++++++++++++++++++++++ + 5 files changed, 243 insertions(+), 2 deletions(-) + create mode 100644 tests/t-thread-local.c + +diff --git a/configure.ac b/configure.ac +index a7f922b1..d708f89a 100644 +--- a/configure.ac ++++ b/configure.ac +@@ -1489,6 +1489,20 @@ if test "$gcry_cv_gcc_attribute_sysv_abi" = "yes" ; then + fi + fi + ++# ++# Check whether compiler support '__thread' storage class specifier. ++# ++AC_CACHE_CHECK([whether compiler supports '__thread' storage class specifier], ++ [gcry_cv_gcc_storage_class__thread], ++ [gcry_cv_gcc_storage_class__thread=no ++ AC_COMPILE_IFELSE([AC_LANG_PROGRAM([#include ], ++ [static __thread int bar;] ++ )], ++ [gcry_cv_gcc_storage_class__thread=yes])]) ++if test "$gcry_cv_gcc_storage_class__thread" = "yes" ; then ++ AC_DEFINE(HAVE_GCC_STORAGE_CLASS__THREAD,1, ++ [Defined if compiler supports "__thread" storage class specifier]) ++fi + + # Restore flags. + CFLAGS=$_gcc_cflags_save; +diff --git a/src/fips.c b/src/fips.c +index cf91baa8..58fb69df 100644 +--- a/src/fips.c ++++ b/src/fips.c +@@ -67,10 +67,29 @@ GPGRT_LOCK_DEFINE (fsm_lock); + used while in fips mode. Change this only while holding fsm_lock. */ + static enum module_states current_state; + ++struct gcry_thread_context { ++ unsigned long fips_service_indicator; ++}; ++ ++#ifdef HAVE_GCC_STORAGE_CLASS__THREAD ++static __thread struct gcry_thread_context the_tc; ++#else ++#error libgcrypt requires thread-local storage to support FIPS mode ++#endif ++ ++void ++_gcry_thread_context_set_fsi (unsigned long fsi) ++{ ++ the_tc.fips_service_indicator = fsi; ++} + ++unsigned long ++_gcry_thread_context_get_fsi (void) ++{ ++ return the_tc.fips_service_indicator; ++} + + +- + static void fips_new_state (enum module_states new_state); + + +diff --git a/src/gcrypt-int.h b/src/gcrypt-int.h +index 074ea071..7f894737 100644 +--- a/src/gcrypt-int.h ++++ b/src/gcrypt-int.h +@@ -298,6 +298,18 @@ void _gcry_set_log_handler (gcry_handler_log_t f, void *opaque); + void _gcry_set_gettext_handler (const char *(*f)(const char*)); + void _gcry_set_progress_handler (gcry_handler_progress_t cb, void *cb_data); + ++void _gcry_thread_context_set_fsi (unsigned long fsi); ++unsigned long _gcry_thread_context_get_fsi (void); ++#define fips_service_indicator_init() do \ ++ { \ ++ if (fips_mode ()) \ ++ _gcry_thread_context_set_fsi (1); \ ++ } while (0) ++#define fips_service_indicator_mark_success(is_compliant) do \ ++ { \ ++ if (is_compliant && fips_mode ()) \ ++ _gcry_thread_context_set_fsi (0); \ ++ } while (0) + + /* Return a pointer to a string containing a description of the error + code in the error value ERR. */ +diff --git a/tests/Makefile.am b/tests/Makefile.am +index 423bc1cd..52f7dd61 100644 +--- a/tests/Makefile.am ++++ b/tests/Makefile.am +@@ -25,7 +25,7 @@ tests_bin = \ + version t-secmem mpitests t-sexp t-convert \ + t-mpi-bit t-mpi-point t-lock \ + prime basic keygen pubkey hmac hashtest t-kdf keygrip \ +- aeswrap random t-kem t-mlkem ++ aeswrap random t-kem t-mlkem t-thread-local + + if USE_RSA + tests_bin += pkcs1v2 t-rsa-pss t-rsa-15 t-rsa-testparm +diff --git a/tests/t-thread-local.c b/tests/t-thread-local.c +new file mode 100644 +index 00000000..285f197f +--- /dev/null ++++ b/tests/t-thread-local.c +@@ -0,0 +1,196 @@ ++/* t-mlkem.c - Check the thread local storage ++ * Copyright (C) 2024 g10 Code GmbH ++ * ++ * This file is part of Libgcrypt. ++ * ++ * Libgcrypt is free software; you can redistribute it and/or modify ++ * it under the terms of the GNU Lesser General Public License as ++ * published by the Free Software Foundation; either version 2.1 of ++ * the License, or (at your option) any later version. ++ * ++ * Libgcrypt 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 Lesser General Public License for more details. ++ * ++ * You should have received a copy of the GNU Lesser General Public License ++ * along with this program; if not, see . ++ * SPDX-License-Identifier: LGPL-2.1+ ++ */ ++ ++/* For now, this program simply test __thread storage class specifier. ++ * After we implement thread local context for libgcrypt, we will ++ * modity to test the feature. */ ++ ++#ifdef HAVE_CONFIG_H ++#include ++#endif ++#include ++#include ++#include ++#include ++#include ++#include ++#if HAVE_PTHREAD ++# include ++#endif ++ ++#define PGM "t-thread-local" ++ ++#include "t-common.h" ++#include "../src/gcrypt-testapi.h" ++ ++/* Mingw requires us to include windows.h after winsock2.h which is ++ included by gcrypt.h. */ ++#ifdef _WIN32 ++# include ++#endif ++ ++#ifdef _WIN32 ++# define THREAD_RET_TYPE DWORD WINAPI ++# define THREAD_RET_VALUE 0 ++#else ++# define THREAD_RET_TYPE void * ++# define THREAD_RET_VALUE NULL ++#endif ++ ++#define N_TESTS 1 ++ ++#define N_THREADS 19 ++ ++static __thread unsigned long t; ++ ++struct thread_arg_s ++{ ++ int no; ++}; ++ ++#if defined(HAVE_PTHREAD) || defined(_WIN32) ++/* Checking the local storage thread. */ ++static THREAD_RET_TYPE ++check_ls_thread (void *argarg) ++{ ++ struct thread_arg_s *arg = argarg; ++ ++ t = arg->no; ++ info ("a thread update the local storage: %lu", t); ++ ++ gcry_free (arg); ++ return THREAD_RET_VALUE; ++} ++#endif ++ ++static void ++check_thread_local (void) ++{ ++ struct thread_arg_s *arg; ++ ++#ifdef _WIN32 ++ HANDLE threads[N_THREADS]; ++ int i; ++ int rc; ++ ++ t = N_THREADS; ++ for (i=0; i < N_THREADS; i++) ++ { ++ arg = gcry_xmalloc (sizeof *arg); ++ arg->no = i; ++ threads[i] = CreateThread (NULL, 0, check_ls_thread, arg, 0, NULL); ++ if (!threads[i]) ++ die ("error creating a thread %d: rc=%d", ++ i, (int)GetLastError ()); ++ } ++ ++ for (i=0; i < N_THREADS; i++) ++ { ++ rc = WaitForSingleObject (threads[i], INFINITE); ++ if (rc == WAIT_OBJECT_0) ++ info ("a thread %d has terminated", i); ++ else ++ fail ("waiting for a thread %d failed: %d", ++ i, (int)GetLastError ()); ++ CloseHandle (threads[i]); ++ } ++ ++#elif HAVE_PTHREAD ++ pthread_t threads[N_THREADS]; ++ int rc, i; ++ ++ t = N_THREADS; ++ for (i=0; i < N_THREADS; i++) ++ { ++ arg = gcry_xmalloc (sizeof *arg); ++ arg->no = i; ++ pthread_create (&threads[i], NULL, check_ls_thread, arg); ++ } ++ ++ for (i=0; i < N_THREADS; i++) ++ { ++ rc = pthread_join (threads[i], NULL); ++ if (rc) ++ fail ("pthread_join failed for a thread %d: %s", ++ i, strerror (errno)); ++ else ++ info ("a thread %d has terminated", i); ++ } ++#else ++ (void)arg; ++#endif /*!_WIN32*/ ++ if (t != N_THREADS) ++ fail ("failed t=%lu\n", t); ++ else ++ info ("success"); ++} ++ ++int ++main (int argc, char **argv) ++{ ++ int last_argc = -1; ++ ++ if (argc) ++ { argc--; argv++; } ++ ++ while (argc && last_argc != argc) ++ { ++ last_argc = argc; ++ if (!strcmp (*argv, "--")) ++ { ++ argc--; argv++; ++ break; ++ } ++ else if (!strcmp (*argv, "--help")) ++ { ++ fputs ("usage: " PGM " [options]\n" ++ "Options:\n" ++ " --verbose print timings etc.\n" ++ " --debug flyswatter\n", ++ stdout); ++ exit (0); ++ } ++ else if (!strcmp (*argv, "--verbose")) ++ { ++ verbose++; ++ argc--; argv++; ++ } ++ else if (!strcmp (*argv, "--debug")) ++ { ++ verbose += 2; ++ debug++; ++ argc--; argv++; ++ } ++ else if (!strncmp (*argv, "--", 2)) ++ die ("unknown option '%s'", *argv); ++ } ++ ++ xgcry_control ((GCRYCTL_DISABLE_SECMEM, 0)); ++ if (!gcry_check_version (GCRYPT_VERSION)) ++ die ("version mismatch\n"); ++ if (debug) ++ xgcry_control ((GCRYCTL_SET_DEBUG_FLAGS, 1u , 0)); ++ xgcry_control ((GCRYCTL_ENABLE_QUICK_RANDOM, 0)); ++ xgcry_control ((GCRYCTL_INITIALIZATION_FINISHED, 0)); ++ ++ check_thread_local (); ++ ++ return !!error_count; ++} +-- +2.49.0 + diff --git a/libgcrypt-fips-Rejection-by-GCRYCTL_FIPS_REJECT_NON_FIPS-not-by-open-flags.patch b/libgcrypt-fips-Rejection-by-GCRYCTL_FIPS_REJECT_NON_FIPS-not-by-open-flags.patch new file mode 100644 index 0000000..6d18f18 --- /dev/null +++ b/libgcrypt-fips-Rejection-by-GCRYCTL_FIPS_REJECT_NON_FIPS-not-by-open-flags.patch @@ -0,0 +1,498 @@ +From d060dd58b82882dec0d8bfcc593536bc0083b4b1 Mon Sep 17 00:00:00 2001 +From: NIIBE Yutaka +Date: Fri, 20 Dec 2024 09:38:13 +0900 +Subject: [PATCH 14/19] fips: Rejection by GCRYCTL_FIPS_REJECT_NON_FIPS, not by + open flags. +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* src/gcrypt.h.in (GCRY_CIPHER_FLAG_REJECT_NON_FIPS): Remove. +(GCRY_MD_FLAG_REJECT_NON_FIPS): Remove. +(GCRY_MAC_FLAG_REJECT_NON_FIPS): Remove. +* tests/t-fips-service-ind.c: Update tests with +GCRYCTL_FIPS_REJECT_NON_FIPS. +* cipher/cipher.c (_gcry_cipher_open_internal, cipher_setkey): Use +fips_check_rejection. +* cipher/mac.c (mac_open): Likewise. +* cipher/md.c (struct gcry_md_context): Remove reject_non_fips. +(md_open, md_enable): Use fips_check_rejection. +(_gcry_md_enable, md_copy): Likewise. + +-- + +GnuPG-bug-id: 7338 +Signed-off-by: NIIBE Yutaka +Signed-off-by: Lucas Mülling +--- + cipher/cipher.c | 8 ++-- + cipher/mac.c | 5 +-- + cipher/md.c | 81 ++++++++++++++++++++++++++++++-------- + src/gcrypt.h.in | 7 +--- + tests/t-fips-service-ind.c | 59 +++++++++++---------------- + 5 files changed, 94 insertions(+), 66 deletions(-) + +Index: libgcrypt-1.11.0/cipher/cipher.c +=================================================================== +--- libgcrypt-1.11.0.orig/cipher/cipher.c ++++ libgcrypt-1.11.0/cipher/cipher.c +@@ -510,7 +510,6 @@ _gcry_cipher_open_internal (gcry_cipher_ + int algo, int mode, unsigned int flags) + { + int secure = !!(flags & GCRY_CIPHER_SECURE); +- int reject_non_fips = !!(flags & GCRY_CIPHER_FLAG_REJECT_NON_FIPS); + gcry_cipher_spec_t *spec; + gcry_cipher_hd_t h = NULL; + gcry_err_code_t err; +@@ -526,7 +525,7 @@ _gcry_cipher_open_internal (gcry_cipher_ + err = GPG_ERR_CIPHER_ALGO; + else if (!spec->flags.fips && fips_mode ()) + { +- if (reject_non_fips) ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_CIPHER)) + err = GPG_ERR_CIPHER_ALGO; + else + { +@@ -544,8 +543,7 @@ _gcry_cipher_open_internal (gcry_cipher_ + | GCRY_CIPHER_ENABLE_SYNC + | GCRY_CIPHER_CBC_CTS + | GCRY_CIPHER_CBC_MAC +- | GCRY_CIPHER_EXTENDED +- | GCRY_CIPHER_FLAG_REJECT_NON_FIPS)) ++ | GCRY_CIPHER_EXTENDED)) + || ((flags & GCRY_CIPHER_CBC_CTS) && (flags & GCRY_CIPHER_CBC_MAC)))) + err = GPG_ERR_CIPHER_ALGO; + +@@ -776,7 +774,7 @@ cipher_setkey (gcry_cipher_hd_t c, byte + Key Generation Requirements" for details. */ + if (buf_eq_const (key, key + keylen, keylen)) + { +- if ((c->flags & GCRY_CIPHER_FLAG_REJECT_NON_FIPS)) ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_CIPHER)) + return GPG_ERR_WEAK_KEY; + else + fips_service_indicator_mark_non_compliant (); +Index: libgcrypt-1.11.0/cipher/mac.c +=================================================================== +--- libgcrypt-1.11.0.orig/cipher/mac.c ++++ libgcrypt-1.11.0/cipher/mac.c +@@ -519,7 +519,6 @@ mac_open (gcry_mac_hd_t * hd, int algo, + gcry_err_code_t err; + gcry_mac_hd_t h; + int secure = !!(flags & GCRY_MAC_FLAG_SECURE); +- int reject_non_fips = !!(flags & GCRY_MAC_FLAG_REJECT_NON_FIPS); + + spec = spec_from_algo (algo); + if (!spec) +@@ -528,7 +527,7 @@ mac_open (gcry_mac_hd_t * hd, int algo, + return GPG_ERR_MAC_ALGO; + else if (!spec->flags.fips && fips_mode ()) + { +- if (reject_non_fips) ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_MAC)) + return GPG_ERR_MAC_ALGO; + else + fips_service_indicator_mark_non_compliant (); +@@ -650,7 +649,7 @@ _gcry_mac_open (gcry_mac_hd_t * h, int a + gcry_err_code_t rc; + gcry_mac_hd_t hd = NULL; + +- if ((flags & ~(GCRY_MAC_FLAG_SECURE | GCRY_MAC_FLAG_REJECT_NON_FIPS))) ++ if ((flags & ~GCRY_MAC_FLAG_SECURE)) + rc = GPG_ERR_INV_ARG; + else + rc = mac_open (&hd, algo, flags, ctx); +Index: libgcrypt-1.11.0/cipher/md.c +=================================================================== +--- libgcrypt-1.11.0.orig/cipher/md.c ++++ libgcrypt-1.11.0/cipher/md.c +@@ -275,7 +275,6 @@ struct gcry_md_context + unsigned int finalized:1; + unsigned int bugemu1:1; + unsigned int hmac:1; +- unsigned int reject_non_fips:1; + } flags; + size_t actual_handle_size; /* Allocated size of this handle. */ + FILE *debug; +@@ -509,7 +508,6 @@ md_open (gcry_md_hd_t *h, int algo, unsi + ctx->flags.secure = secure; + ctx->flags.hmac = hmac; + ctx->flags.bugemu1 = !!(flags & GCRY_MD_FLAG_BUGEMU1); +- ctx->flags.reject_non_fips = !!(flags & GCRY_MD_FLAG_REJECT_NON_FIPS); + } + + if (! err) +@@ -544,14 +542,11 @@ _gcry_md_open (gcry_md_hd_t *h, int algo + + if ((flags & ~(GCRY_MD_FLAG_SECURE + | GCRY_MD_FLAG_HMAC +- | GCRY_MD_FLAG_REJECT_NON_FIPS + | GCRY_MD_FLAG_BUGEMU1))) + rc = GPG_ERR_INV_ARG; + else + rc = md_open (&hd, algo, flags); + +- *h = rc? NULL : hd; +- + if (!rc && fips_mode ()) + { + GcryDigestEntry *entry = hd->ctx->list; +@@ -566,9 +561,26 @@ _gcry_md_open (gcry_md_hd_t *h, int algo + } + + if (!is_compliant_algo) +- fips_service_indicator_mark_non_compliant (); ++ { ++ int reject = 0; ++ ++ if (algo == GCRY_MD_MD5) ++ reject = fips_check_rejection (GCRY_FIPS_FLAG_REJECT_MD_MD5); ++ else ++ reject = fips_check_rejection (GCRY_FIPS_FLAG_REJECT_MD_OTHERS); ++ ++ if (reject) ++ { ++ md_close (hd); ++ hd = NULL; ++ rc = GPG_ERR_DIGEST_ALGO; ++ } ++ else ++ fips_service_indicator_mark_non_compliant (); ++ } + } + ++ *h = rc? NULL : hd; + return rc; + } + +@@ -581,12 +593,17 @@ md_enable (gcry_md_hd_t hd, int algorith + const gcry_md_spec_t *spec; + GcryDigestEntry *entry; + gcry_err_code_t err = 0; +- int reject_non_fips = h->flags.reject_non_fips; ++ int reject; + + for (entry = h->list; entry; entry = entry->next) + if (entry->spec->algo == algorithm) + return 0; /* Already enabled */ + ++ if (algorithm == GCRY_MD_MD5) ++ reject = fips_check_rejection (GCRY_FIPS_FLAG_REJECT_MD_MD5); ++ else ++ reject = fips_check_rejection (GCRY_FIPS_FLAG_REJECT_MD_OTHERS); ++ + spec = spec_from_algo (algorithm); + if (!spec) + { +@@ -598,7 +615,7 @@ md_enable (gcry_md_hd_t hd, int algorith + err = GPG_ERR_DIGEST_ALGO; + + /* Any non-FIPS algorithm should go this way */ +- if (!err && reject_non_fips && !spec->flags.fips && fips_mode ()) ++ if (!err && reject && !spec->flags.fips && fips_mode ()) + err = GPG_ERR_DIGEST_ALGO; + + if (!err && h->flags.hmac && spec->read == NULL) +@@ -657,7 +674,19 @@ _gcry_md_enable (gcry_md_hd_t hd, int al + } + + if (!is_compliant_algo) +- fips_service_indicator_mark_non_compliant (); ++ { ++ int reject = 0; ++ ++ if (algorithm == GCRY_MD_MD5) ++ reject = fips_check_rejection (GCRY_FIPS_FLAG_REJECT_MD_MD5); ++ else ++ reject = fips_check_rejection (GCRY_FIPS_FLAG_REJECT_MD_OTHERS); ++ ++ if (reject) ++ rc = GPG_ERR_DIGEST_ALGO; ++ else ++ fips_service_indicator_mark_non_compliant (); ++ } + } + + return rc; +@@ -667,13 +696,14 @@ _gcry_md_enable (gcry_md_hd_t hd, int al + static gcry_err_code_t + md_copy (gcry_md_hd_t ahd, gcry_md_hd_t *b_hd) + { +- gcry_err_code_t err = 0; ++ gcry_err_code_t rc = 0; + struct gcry_md_context *a = ahd->ctx; + struct gcry_md_context *b; + GcryDigestEntry *ar, *br; + gcry_md_hd_t bhd; + size_t n; + int is_compliant_algo = 1; ++ int reject = 0; + + if (ahd->bufpos) + md_write (ahd, NULL, 0); +@@ -686,7 +716,7 @@ md_copy (gcry_md_hd_t ahd, gcry_md_hd_t + + if (!bhd) + { +- err = gpg_err_code_from_syserror (); ++ rc = gpg_err_code_from_syserror (); + goto leave; + } + +@@ -715,12 +745,20 @@ md_copy (gcry_md_hd_t ahd, gcry_md_hd_t + br = xtrymalloc (ar->actual_struct_size); + if (!br) + { +- err = gpg_err_code_from_syserror (); ++ rc = gpg_err_code_from_syserror (); + md_close (bhd); + goto leave; + } + +- is_compliant_algo &= spec->flags.fips; ++ if (!spec->flags.fips) ++ { ++ is_compliant_algo = 0; ++ ++ if (spec->algo == GCRY_MD_MD5) ++ reject |= fips_check_rejection (GCRY_FIPS_FLAG_REJECT_MD_MD5); ++ else ++ reject |= fips_check_rejection (GCRY_FIPS_FLAG_REJECT_MD_OTHERS); ++ } + + memcpy (br, ar, ar->actual_struct_size); + br->next = b->list; +@@ -730,13 +768,22 @@ md_copy (gcry_md_hd_t ahd, gcry_md_hd_t + if (a->debug) + md_start_debug (bhd, "unknown"); + +- *b_hd = bhd; ++ if (!is_compliant_algo && fips_mode ()) ++ { ++ if (reject) ++ { ++ rc = GPG_ERR_DIGEST_ALGO; ++ md_close (bhd); ++ } ++ else ++ fips_service_indicator_mark_non_compliant (); ++ } + +- if (!is_compliant_algo) +- fips_service_indicator_mark_non_compliant (); ++ if (!rc) ++ *b_hd = bhd; + + leave: +- return err; ++ return rc; + } + + +Index: libgcrypt-1.11.0/src/gcrypt.h.in +=================================================================== +--- libgcrypt-1.11.0.orig/src/gcrypt.h.in ++++ libgcrypt-1.11.0/src/gcrypt.h.in +@@ -995,8 +995,7 @@ enum gcry_cipher_flags + GCRY_CIPHER_ENABLE_SYNC = 2, /* Enable CFB sync mode. */ + GCRY_CIPHER_CBC_CTS = 4, /* Enable CBC cipher text stealing (CTS). */ + GCRY_CIPHER_CBC_MAC = 8, /* Enable CBC message auth. code (MAC). */ +- GCRY_CIPHER_EXTENDED = 16, /* Enable extended AES-WRAP. */ +- GCRY_CIPHER_FLAG_REJECT_NON_FIPS = 32 /* Reject non-FIPS-compliant algo. */ ++ GCRY_CIPHER_EXTENDED = 16 /* Enable extended AES-WRAP. */ + }; + + /* Methods used for AEAD IV generation. */ +@@ -1322,7 +1321,6 @@ enum gcry_md_flags + { + GCRY_MD_FLAG_SECURE = 1, /* Allocate all buffers in "secure" memory. */ + GCRY_MD_FLAG_HMAC = 2, /* Make an HMAC out of this algorithm. */ +- GCRY_MD_FLAG_REJECT_NON_FIPS = 4, /* Reject non-FIPS-compliant algo. */ + GCRY_MD_FLAG_BUGEMU1 = 0x0100 + }; + +@@ -1564,8 +1562,7 @@ enum gcry_mac_algos + /* Flags used with the open function. */ + enum gcry_mac_flags + { +- GCRY_MAC_FLAG_SECURE = 1, /* Allocate all buffers in "secure" memory. */ +- GCRY_MAC_FLAG_REJECT_NON_FIPS = 2 /* Reject non-FIPS-compliant algo. */ ++ GCRY_MAC_FLAG_SECURE = 1 /* Allocate all buffers in "secure" memory. */ + }; + + /* Create a MAC handle for algorithm ALGO. FLAGS may be given as an bitwise OR +Index: libgcrypt-1.11.0/tests/t-fips-service-ind.c +=================================================================== +--- libgcrypt-1.11.0.orig/tests/t-fips-service-ind.c ++++ libgcrypt-1.11.0/tests/t-fips-service-ind.c +@@ -250,7 +250,7 @@ check_pk_hash_sign_verify (void) + /* Check gcry_cipher_open, gcry_cipher_setkey, gcry_cipher_encrypt, + gcry_cipher_decrypt, gcry_cipher_close API. */ + static void +-check_cipher_o_s_e_d_c (void) ++check_cipher_o_s_e_d_c (int reject) + { + static struct { + int algo; +@@ -258,18 +258,12 @@ check_cipher_o_s_e_d_c (void) + int keylen; + const char *expect; + int expect_failure; +- unsigned int flags; + } tv[] = { + #if USE_DES + { GCRY_CIPHER_3DES, + "\xe3\x34\x7a\x6b\x0b\xc1\x15\x2c\x64\x2a\x25\xcb\xd3\xbc\x31\xab" + "\xfb\xa1\x62\xa8\x1f\x19\x7c\x15", 24, + "\x3f\x1a\xb8\x83\x18\x8b\xb5\x97", 1 }, +- { GCRY_CIPHER_3DES, +- "\xe3\x34\x7a\x6b\x0b\xc1\x15\x2c\x64\x2a\x25\xcb\xd3\xbc\x31\xab" +- "\xfb\xa1\x62\xa8\x1f\x19\x7c\x15", 24, +- "\x3f\x1a\xb8\x83\x18\x8b\xb5\x97", +- 1, GCRY_CIPHER_FLAG_REJECT_NON_FIPS }, + #endif + { GCRY_CIPHER_AES, + "\x2b\x7e\x15\x16\x28\xae\xd2\xa6\xab\xf7\x15\x88\x09\xcf\x4f\x3c", 16, +@@ -297,12 +291,10 @@ check_cipher_o_s_e_d_c (void) + assert (blklen != 0); + assert (blklen <= ptlen); + assert (blklen <= DIM (out)); +- err = gcry_cipher_open (&h, tv[tvidx].algo, GCRY_CIPHER_MODE_ECB, +- tv[tvidx].flags); ++ err = gcry_cipher_open (&h, tv[tvidx].algo, GCRY_CIPHER_MODE_ECB, 0); + if (err) + { +- if (in_fips_mode && (tv[tvidx].flags & GCRY_CIPHER_FLAG_REJECT_NON_FIPS) +- && tv[tvidx].expect_failure) ++ if (in_fips_mode && reject && tv[tvidx].expect_failure) + /* Here, an error is expected */ + ; + else +@@ -312,8 +304,7 @@ check_cipher_o_s_e_d_c (void) + } + else + { +- if (in_fips_mode && (tv[tvidx].flags & GCRY_CIPHER_FLAG_REJECT_NON_FIPS) +- && tv[tvidx].expect_failure) ++ if (in_fips_mode && reject && tv[tvidx].expect_failure) + /* This case, an error is expected, but we observed success */ + fail ("gcry_cipher_open test %d unexpectedly succeeded\n", tvidx); + } +@@ -398,7 +389,7 @@ check_cipher_o_s_e_d_c (void) + /* Check gcry_mac_open, gcry_mac_write, gcry_mac_write, gcry_mac_read, + gcry_mac_close API. */ + static void +-check_mac_o_w_r_c (void) ++check_mac_o_w_r_c (int reject) + { + static struct { + int algo; +@@ -408,14 +399,10 @@ check_mac_o_w_r_c (void) + int keylen; + const char *expect; + int expect_failure; +- unsigned int flags; + } tv[] = { + #if USE_MD5 + { GCRY_MAC_HMAC_MD5, "hmac input abc", 14, "hmac key input", 14, + "\x0d\x72\xd0\x60\xaf\x34\xf2\xca\x33\x58\xa9\xcc\xd3\x5a\xac\xb5", 1 }, +- { GCRY_MAC_HMAC_MD5, "hmac input abc", 14, "hmac key input", 14, +- "\x0d\x72\xd0\x60\xaf\x34\xf2\xca\x33\x58\xa9\xcc\xd3\x5a\xac\xb5", 1, +- GCRY_MAC_FLAG_REJECT_NON_FIPS }, + #endif + #if USE_SHA1 + { GCRY_MAC_HMAC_SHA1, "hmac input abc", 14, "hmac key input", 14, +@@ -471,11 +458,10 @@ check_mac_o_w_r_c (void) + expectlen = gcry_mac_get_algo_maclen (tv[tvidx].algo); + assert (expectlen != 0); + assert (expectlen <= DIM (mac)); +- err = gcry_mac_open (&h, tv[tvidx].algo, tv[tvidx].flags, NULL); ++ err = gcry_mac_open (&h, tv[tvidx].algo, 0, NULL); + if (err) + { +- if (in_fips_mode && (tv[tvidx].flags & GCRY_MAC_FLAG_REJECT_NON_FIPS) +- && tv[tvidx].expect_failure) ++ if (in_fips_mode && reject && tv[tvidx].expect_failure) + /* Here, an error is expected */ + ; + else +@@ -485,8 +471,7 @@ check_mac_o_w_r_c (void) + } + else + { +- if (in_fips_mode && (tv[tvidx].flags & GCRY_MAC_FLAG_REJECT_NON_FIPS) +- && tv[tvidx].expect_failure) ++ if (in_fips_mode && reject && tv[tvidx].expect_failure) + /* This case, an error is expected, but we observed success */ + fail ("gcry_mac_open test %d unexpectedly succeeded\n", tvidx); + } +@@ -563,7 +548,7 @@ check_mac_o_w_r_c (void) + /* Check gcry_md_open, gcry_md_write, gcry_md_write, gcry_md_read, + gcry_md_close API. */ + static void +-check_md_o_w_r_c (void) ++check_md_o_w_r_c (int reject) + { + static struct { + int algo; +@@ -571,14 +556,10 @@ check_md_o_w_r_c (void) + int datalen; + const char *expect; + int expect_failure; +- unsigned int flags; + } tv[] = { + #if USE_MD5 + { GCRY_MD_MD5, "abc", 3, + "\x90\x01\x50\x98\x3C\xD2\x4F\xB0\xD6\x96\x3F\x7D\x28\xE1\x7F\x72", 1 }, +- { GCRY_MD_MD5, "abc", 3, +- "\x90\x01\x50\x98\x3C\xD2\x4F\xB0\xD6\x96\x3F\x7D\x28\xE1\x7F\x72", 1, +- GCRY_MD_FLAG_REJECT_NON_FIPS }, + #endif + #if USE_SHA1 + { GCRY_MD_SHA1, "abc", 3, +@@ -632,11 +613,10 @@ check_md_o_w_r_c (void) + + expectlen = gcry_md_get_algo_dlen (tv[tvidx].algo); + assert (expectlen != 0); +- err = gcry_md_open (&h, tv[tvidx].algo, tv[tvidx].flags); ++ err = gcry_md_open (&h, tv[tvidx].algo, 0); + if (err) + { +- if (in_fips_mode && (tv[tvidx].flags & GCRY_MD_FLAG_REJECT_NON_FIPS) +- && tv[tvidx].expect_failure) ++ if (in_fips_mode && reject && tv[tvidx].expect_failure) + /* Here, an error is expected */ + ; + else +@@ -646,8 +626,7 @@ check_md_o_w_r_c (void) + } + else + { +- if (in_fips_mode && (tv[tvidx].flags & GCRY_MD_FLAG_REJECT_NON_FIPS) +- && tv[tvidx].expect_failure) ++ if (in_fips_mode && reject && tv[tvidx].expect_failure) + /* This case, an error is expected, but we observed success */ + fail ("gcry_md_open test %d unexpectedly succeeded\n", tvidx); + } +@@ -1011,10 +990,18 @@ main (int argc, char **argv) + + check_digests (); + check_kdf_derive (); +- check_md_o_w_r_c (); +- check_mac_o_w_r_c (); +- check_cipher_o_s_e_d_c (); ++ check_md_o_w_r_c (0); ++ check_mac_o_w_r_c (0); ++ check_cipher_o_s_e_d_c (0); + check_pk_hash_sign_verify (); + ++ xgcry_control ((GCRYCTL_FIPS_REJECT_NON_FIPS, ++ (GCRY_FIPS_FLAG_REJECT_MD_MD5 ++ | GCRY_FIPS_FLAG_REJECT_COMPAT110))); ++ ++ check_md_o_w_r_c (1); ++ check_mac_o_w_r_c (1); ++ check_cipher_o_s_e_d_c (1); ++ + return !!error_count; + } diff --git a/libgcrypt-fips-cipher-Add-GCRY_FIPS_FLAG_REJECT_PK_FLAGS.patch b/libgcrypt-fips-cipher-Add-GCRY_FIPS_FLAG_REJECT_PK_FLAGS.patch new file mode 100644 index 0000000..310e5e5 --- /dev/null +++ b/libgcrypt-fips-cipher-Add-GCRY_FIPS_FLAG_REJECT_PK_FLAGS.patch @@ -0,0 +1,80 @@ +From 0414e126b939f0b11ecf441908d923e87c1caf02 Mon Sep 17 00:00:00 2001 +From: NIIBE Yutaka +Date: Thu, 6 Mar 2025 08:57:51 +0900 +Subject: [PATCH 06/14] fips,cipher: Add GCRY_FIPS_FLAG_REJECT_PK_FLAGS. +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* src/gcrypt.h.in (GCRY_FIPS_FLAG_REJECT_PK_FLAGS): New. +* cipher/pubkey-util.c (_gcry_pk_util_parse_flaglist): Keep the +behavior of 1.10. +* cipher/rsa.c (rsa_decrypt, rsa_sign): Likewise. + +-- + +GnuPG-bug-id: 7338 +Signed-off-by: NIIBE Yutaka +Signed-off-by: Lucas Mülling +--- + cipher/pubkey-util.c | 2 +- + cipher/rsa.c | 4 ++-- + src/gcrypt.h.in | 3 ++- + 3 files changed, 5 insertions(+), 4 deletions(-) + +diff --git a/cipher/pubkey-util.c b/cipher/pubkey-util.c +index 9c927638..e7355569 100644 +--- a/cipher/pubkey-util.c ++++ b/cipher/pubkey-util.c +@@ -202,7 +202,7 @@ _gcry_pk_util_parse_flaglist (gcry_sexp_t list, + + if (fips_mode () && igninvflag) + { +- if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK_FLAGS)) + rc = GPG_ERR_INV_FLAG; + else + fips_service_indicator_mark_non_compliant (); +diff --git a/cipher/rsa.c b/cipher/rsa.c +index dce76414..7e086df4 100644 +--- a/cipher/rsa.c ++++ b/cipher/rsa.c +@@ -1504,7 +1504,7 @@ rsa_decrypt (gcry_sexp_t *r_plain, gcry_sexp_t s_data, gcry_sexp_t keyparms) + { + if (fips_mode ()) + { +- if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK_FLAGS)) + { + rc = GPG_ERR_INV_FLAG; + goto leave; +@@ -1649,7 +1649,7 @@ rsa_sign (gcry_sexp_t *r_sig, gcry_sexp_t s_data, gcry_sexp_t keyparms) + { + if (fips_mode ()) + { +- if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK_FLAGS)) + { + rc = GPG_ERR_INV_FLAG; + goto leave; +diff --git a/src/gcrypt.h.in b/src/gcrypt.h.in +index fe3db16a..a282268d 100644 +--- a/src/gcrypt.h.in ++++ b/src/gcrypt.h.in +@@ -1991,11 +1991,12 @@ char *gcry_get_config (int mode, const char *what); + #define GCRY_FIPS_FLAG_REJECT_CIPHER_MODE (1 << 8) + /**/ + #define GCRY_FIPS_FLAG_REJECT_PK_ECC_K (1 << 10) ++#define GCRY_FIPS_FLAG_REJECT_PK_FLAGS (1 << 11) + + #define GCRY_FIPS_FLAG_REJECT_MD \ + (GCRY_FIPS_FLAG_REJECT_MD_MD5 | GCRY_FIPS_FLAG_REJECT_MD_OTHERS) + +-/* Note: Don't reject MD5, PK MD, PK GOST and PK SM2 */ ++/* Note: Don't reject MD5, PK MD, PK GOST, PK SM2, PK ECC K, and PK FLAGS */ + #define GCRY_FIPS_FLAG_REJECT_COMPAT110 \ + (GCRY_FIPS_FLAG_REJECT_MD_OTHERS \ + | GCRY_FIPS_FLAG_REJECT_MAC \ +-- +2.49.0 + diff --git a/libgcrypt-fips-cipher-Add-behavior-not-to-reject-but-mark-non-compliant.patch b/libgcrypt-fips-cipher-Add-behavior-not-to-reject-but-mark-non-compliant.patch new file mode 100644 index 0000000..9fc7734 --- /dev/null +++ b/libgcrypt-fips-cipher-Add-behavior-not-to-reject-but-mark-non-compliant.patch @@ -0,0 +1,300 @@ +From a776b692669af7a6c089779989b626c4795e30b0 Mon Sep 17 00:00:00 2001 +From: NIIBE Yutaka +Date: Fri, 20 Dec 2024 13:36:12 +0900 +Subject: [PATCH 15/19] fips,cipher: Add behavior not to reject but mark + non-compliant. +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* cipher/dsa.c (dsa_check_keysize): Check reject flag for rejection, +or mark non-comliant in FIPS mode. +* cipher/ecc-ecdsa.c (_gcry_ecc_ecdsa_sign): Likewise. +* cipher/ecc.c (ecc_sign, ecc_verify): Likewise. +* cipher/pubkey.c (_gcry_pk_encrypt, _gcry_pk_sign): Likewise. +(_gcry_pk_verify, _gcry_pk_testkey, _gcry_pk_genkey): Likewise. +(_gcry_pk_get_nbits, _gcry_pk_get_curve): Likewise. +* src/visibility.c (gcry_pk_encrypt): Initialize the indicator. +(gcry_pk_decrypt, gcry_pk_sign, gcry_pk_verify): Likewise. +(gcry_pk_testkey, gcry_pk_genkey), gcry_pk_get_nbits) +(gcry_pk_get_curve): Likewise. +-- + +GnuPG-bug-id: 7338 +Signed-off-by: NIIBE Yutaka +Signed-off-by: Lucas Mülling +--- + cipher/dsa.c | 7 ++++- + cipher/ecc-ecdsa.c | 5 +++- + cipher/ecc.c | 10 +++++-- + cipher/pubkey.c | 74 ++++++++++++++++++++++++++++++++++++++-------- + src/visibility.c | 9 +++++- + 5 files changed, 87 insertions(+), 18 deletions(-) + +diff --git a/cipher/dsa.c b/cipher/dsa.c +index e559f9f5..564edf8d 100644 +--- a/cipher/dsa.c ++++ b/cipher/dsa.c +@@ -150,7 +150,12 @@ static gpg_err_code_t + dsa_check_keysize (unsigned int nbits) + { + if (fips_mode () && nbits < 2048) +- return GPG_ERR_INV_VALUE; ++ { ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) ++ return GPG_ERR_INV_VALUE; ++ else ++ fips_service_indicator_mark_non_compliant (); ++ } + + return 0; + } +diff --git a/cipher/ecc-ecdsa.c b/cipher/ecc-ecdsa.c +index 871b0371..cb9a001c 100644 +--- a/cipher/ecc-ecdsa.c ++++ b/cipher/ecc-ecdsa.c +@@ -110,7 +110,10 @@ _gcry_ecc_ecdsa_sign (gcry_mpi_t input, gcry_mpi_t k_supplied, mpi_ec_t ec, + (hashalgo == GCRY_MD_SHAKE128 + || hashalgo == GCRY_MD_SHAKE256)) + { +- rc = GPG_ERR_DIGEST_ALGO; ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) ++ rc = GPG_ERR_DIGEST_ALGO; ++ else ++ fips_service_indicator_mark_non_compliant (); + goto leave; + } + +diff --git a/cipher/ecc.c b/cipher/ecc.c +index 65525207..8896afd0 100644 +--- a/cipher/ecc.c ++++ b/cipher/ecc.c +@@ -952,7 +952,10 @@ ecc_sign (gcry_sexp_t *r_sig, gcry_sexp_t s_data, gcry_sexp_t keyparms) + || (ec->dialect == ECC_DIALECT_SAFECURVE + && ctx.hash_algo != GCRY_MD_SHAKE256))) + { +- rc = GPG_ERR_DIGEST_ALGO; ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) ++ rc = GPG_ERR_DIGEST_ALGO; ++ else ++ fips_service_indicator_mark_non_compliant (); + goto leave; + } + } +@@ -1074,7 +1077,10 @@ ecc_verify (gcry_sexp_t s_sig, gcry_sexp_t s_data, gcry_sexp_t s_keyparms) + || (ec->dialect == ECC_DIALECT_SAFECURVE + && ctx.hash_algo != GCRY_MD_SHAKE256))) + { +- rc = GPG_ERR_DIGEST_ALGO; ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) ++ rc = GPG_ERR_DIGEST_ALGO; ++ else ++ fips_service_indicator_mark_non_compliant (); + goto leave; + } + } +diff --git a/cipher/pubkey.c b/cipher/pubkey.c +index 4d7743cc..aacf9f5a 100644 +--- a/cipher/pubkey.c ++++ b/cipher/pubkey.c +@@ -328,7 +328,12 @@ _gcry_pk_encrypt (gcry_sexp_t *r_ciph, gcry_sexp_t s_data, gcry_sexp_t s_pkey) + if (spec->flags.disabled) + rc = GPG_ERR_PUBKEY_ALGO; + else if (!spec->flags.fips && fips_mode ()) +- rc = GPG_ERR_PUBKEY_ALGO; ++ { ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) ++ rc = GPG_ERR_PUBKEY_ALGO; ++ else ++ fips_service_indicator_mark_non_compliant (); ++ } + else if (spec->encrypt) + rc = spec->encrypt (r_ciph, s_data, keyparms); + else +@@ -441,7 +446,12 @@ _gcry_pk_sign (gcry_sexp_t *r_sig, gcry_sexp_t s_hash, gcry_sexp_t s_skey) + if (spec->flags.disabled) + rc = GPG_ERR_PUBKEY_ALGO; + else if (!spec->flags.fips && fips_mode ()) +- rc = GPG_ERR_PUBKEY_ALGO; ++ { ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) ++ rc = GPG_ERR_PUBKEY_ALGO; ++ else ++ fips_service_indicator_mark_non_compliant (); ++ } + else if (spec->sign) + rc = spec->sign (r_sig, s_hash, keyparms); + else +@@ -663,7 +673,12 @@ _gcry_pk_verify (gcry_sexp_t s_sig, gcry_sexp_t s_hash, gcry_sexp_t s_pkey) + if (spec->flags.disabled) + rc = GPG_ERR_PUBKEY_ALGO; + else if (!spec->flags.fips && fips_mode ()) +- rc = GPG_ERR_PUBKEY_ALGO; ++ { ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) ++ rc = GPG_ERR_PUBKEY_ALGO; ++ else ++ fips_service_indicator_mark_non_compliant (); ++ } + else if (spec->verify) + rc = spec->verify (s_sig, s_hash, keyparms); + else +@@ -747,7 +762,12 @@ _gcry_pk_testkey (gcry_sexp_t s_key) + if (spec->flags.disabled) + rc = GPG_ERR_PUBKEY_ALGO; + else if (!spec->flags.fips && fips_mode ()) +- rc = GPG_ERR_PUBKEY_ALGO; ++ { ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) ++ rc = GPG_ERR_PUBKEY_ALGO; ++ else ++ fips_service_indicator_mark_non_compliant (); ++ } + else if (spec->check_secret_key) + rc = spec->check_secret_key (keyparms); + else +@@ -826,11 +846,21 @@ _gcry_pk_genkey (gcry_sexp_t *r_key, gcry_sexp_t s_parms) + spec = spec_from_name (name); + xfree (name); + name = NULL; +- if (!spec || spec->flags.disabled || (!spec->flags.fips && fips_mode ())) ++ if (!spec || spec->flags.disabled) + { + rc = GPG_ERR_PUBKEY_ALGO; /* Unknown algorithm. */ + goto leave; + } ++ else if (!spec->flags.fips && fips_mode ()) ++ { ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) ++ { ++ rc = GPG_ERR_PUBKEY_ALGO; ++ goto leave; ++ } ++ else ++ fips_service_indicator_mark_non_compliant (); ++ } + + if (spec->generate) + rc = spec->generate (list, r_key); +@@ -866,12 +896,22 @@ _gcry_pk_get_nbits (gcry_sexp_t key) + + if (spec_from_sexp (key, 0, &spec, &parms)) + return 0; /* Error - 0 is a suitable indication for that. */ ++ + if (spec->flags.disabled) +- return 0; +- if (!spec->flags.fips && fips_mode ()) +- return 0; ++ nbits = 0; /* Error */ ++ else if (!spec->flags.fips && fips_mode ()) ++ { ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) ++ nbits = 0; /* Error */ ++ else ++ { ++ fips_service_indicator_mark_non_compliant (); ++ nbits = spec->get_nbits (parms); ++ } ++ } ++ else ++ nbits = spec->get_nbits (parms); + +- nbits = spec->get_nbits (parms); + sexp_release (parms); + return nbits; + } +@@ -1004,10 +1044,18 @@ _gcry_pk_get_curve (gcry_sexp_t key, int iterator, unsigned int *r_nbits) + } + + if (spec->flags.disabled) +- return NULL; +- if (!spec->flags.fips && fips_mode ()) +- return NULL; +- if (spec->get_curve) ++ result = NULL; ++ else if (!spec->flags.fips && fips_mode ()) ++ { ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) ++ result = NULL; ++ else ++ { ++ fips_service_indicator_mark_non_compliant (); ++ result = spec->get_curve (keyparms, iterator, r_nbits); ++ } ++ } ++ else if (spec->get_curve) + result = spec->get_curve (keyparms, iterator, r_nbits); + + sexp_release (keyparms); +diff --git a/src/visibility.c b/src/visibility.c +index d22c8b59..e02d6cfe 100644 +--- a/src/visibility.c ++++ b/src/visibility.c +@@ -1022,6 +1022,7 @@ gcry_pk_encrypt (gcry_sexp_t *result, gcry_sexp_t data, gcry_sexp_t pkey) + *result = NULL; + return gpg_error (fips_not_operational ()); + } ++ fips_service_indicator_init (); + return gpg_error (_gcry_pk_encrypt (result, data, pkey)); + } + +@@ -1033,6 +1034,7 @@ gcry_pk_decrypt (gcry_sexp_t *result, gcry_sexp_t data, gcry_sexp_t skey) + *result = NULL; + return gpg_error (fips_not_operational ()); + } ++ fips_service_indicator_init (); + return gpg_error (_gcry_pk_decrypt (result, data, skey)); + } + +@@ -1044,6 +1046,7 @@ gcry_pk_sign (gcry_sexp_t *result, gcry_sexp_t data, gcry_sexp_t skey) + *result = NULL; + return gpg_error (fips_not_operational ()); + } ++ fips_service_indicator_init (); + return gpg_error (_gcry_pk_sign (result, data, skey)); + } + +@@ -1065,6 +1068,7 @@ gcry_pk_verify (gcry_sexp_t sigval, gcry_sexp_t data, gcry_sexp_t pkey) + { + if (!fips_is_operational ()) + return gpg_error (fips_not_operational ()); ++ fips_service_indicator_init (); + return gpg_error (_gcry_pk_verify (sigval, data, pkey)); + } + +@@ -1089,6 +1093,7 @@ gcry_pk_testkey (gcry_sexp_t key) + { + if (!fips_is_operational ()) + return gpg_error (fips_not_operational ()); ++ fips_service_indicator_init (); + return gpg_error (_gcry_pk_testkey (key)); + } + +@@ -1100,6 +1105,7 @@ gcry_pk_genkey (gcry_sexp_t *r_key, gcry_sexp_t s_parms) + *r_key = NULL; + return gpg_error (fips_not_operational ()); + } ++ fips_service_indicator_init (); + return gpg_error (_gcry_pk_genkey (r_key, s_parms)); + } + +@@ -1138,7 +1144,7 @@ gcry_pk_get_nbits (gcry_sexp_t key) + (void)fips_not_operational (); + return 0; + } +- ++ fips_service_indicator_init (); + return _gcry_pk_get_nbits (key); + } + +@@ -1161,6 +1167,7 @@ gcry_pk_get_curve (gcry_sexp_t key, int iterator, unsigned int *r_nbits) + (void)fips_not_operational (); + return NULL; + } ++ fips_service_indicator_init (); + return _gcry_pk_get_curve (key, iterator, r_nbits); + } + +-- +2.49.0 + diff --git a/libgcrypt-fips-cipher-Do-the-computation-when-marking-non-compliant.patch b/libgcrypt-fips-cipher-Do-the-computation-when-marking-non-compliant.patch new file mode 100644 index 0000000..8f71866 --- /dev/null +++ b/libgcrypt-fips-cipher-Do-the-computation-when-marking-non-compliant.patch @@ -0,0 +1,160 @@ +From 54a6617b3679cfeb6d986ddf3c9c73641929f02c Mon Sep 17 00:00:00 2001 +From: NIIBE Yutaka +Date: Tue, 4 Mar 2025 10:32:49 +0900 +Subject: [PATCH 4/4] fips,cipher: Do the computation when marking + non-compliant. +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* cipher/ecc-ecdsa.c (_gcry_ecc_ecdsa_sign): Continue the computation +when marking non-compliant. +* cipher/pubkey.c (_gcry_pk_encrypt, _gcry_pk_sign): Likewise. +(_gcry_pk_sign_md, _gcry_pk_verify, _gcry_pk_verify_md): Likewise. +(_gcry_pk_testkey): Likewise. + +-- + +Fixes-commit: a776b692669af7a6c089779989b626c4795e30b0 +GnuPG-bug-id: 7338 +Signed-off-by: NIIBE Yutaka +Signed-off-by: Lucas Mülling +--- + cipher/ecc-ecdsa.c | 6 ++++-- + cipher/pubkey.c | 48 ++++++++++++++++++++++++++++++++++------------ + 2 files changed, 40 insertions(+), 14 deletions(-) + +diff --git a/cipher/ecc-ecdsa.c b/cipher/ecc-ecdsa.c +index cb9a001c..9da8e6dc 100644 +--- a/cipher/ecc-ecdsa.c ++++ b/cipher/ecc-ecdsa.c +@@ -111,10 +111,12 @@ _gcry_ecc_ecdsa_sign (gcry_mpi_t input, gcry_mpi_t k_supplied, mpi_ec_t ec, + || hashalgo == GCRY_MD_SHAKE256)) + { + if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) +- rc = GPG_ERR_DIGEST_ALGO; ++ { ++ rc = GPG_ERR_DIGEST_ALGO; ++ goto leave; ++ } + else + fips_service_indicator_mark_non_compliant (); +- goto leave; + } + + /* Use Pornin's method for deterministic DSA. If this +diff --git a/cipher/pubkey.c b/cipher/pubkey.c +index c28ec124..3778f482 100644 +--- a/cipher/pubkey.c ++++ b/cipher/pubkey.c +@@ -330,11 +330,15 @@ _gcry_pk_encrypt (gcry_sexp_t *r_ciph, gcry_sexp_t s_data, gcry_sexp_t s_pkey) + else if (!spec->flags.fips && fips_mode ()) + { + if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) +- rc = GPG_ERR_PUBKEY_ALGO; ++ { ++ rc = GPG_ERR_PUBKEY_ALGO; ++ goto leave; ++ } + else + fips_service_indicator_mark_non_compliant (); + } +- else if (spec->encrypt) ++ ++ if (spec->encrypt) + rc = spec->encrypt (r_ciph, s_data, keyparms); + else + rc = GPG_ERR_NOT_IMPLEMENTED; +@@ -448,11 +452,15 @@ _gcry_pk_sign (gcry_sexp_t *r_sig, gcry_sexp_t s_hash, gcry_sexp_t s_skey) + else if (!spec->flags.fips && fips_mode ()) + { + if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) +- rc = GPG_ERR_PUBKEY_ALGO; ++ { ++ rc = GPG_ERR_PUBKEY_ALGO; ++ goto leave; ++ } + else + fips_service_indicator_mark_non_compliant (); + } +- else if (spec->sign) ++ ++ if (spec->sign) + rc = spec->sign (r_sig, s_hash, keyparms); + else + rc = GPG_ERR_NOT_IMPLEMENTED; +@@ -649,11 +657,15 @@ _gcry_pk_sign_md (gcry_sexp_t *r_sig, const char *tmpl, gcry_md_hd_t hd_orig, + else if (!spec->flags.fips && fips_mode ()) + { + if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) +- rc = GPG_ERR_PUBKEY_ALGO; ++ { ++ rc = GPG_ERR_PUBKEY_ALGO; ++ goto leave; ++ } + else + fips_service_indicator_mark_non_compliant (); + } +- else if (spec->sign) ++ ++ if (spec->sign) + rc = spec->sign (r_sig, s_data, keyparms); + else + rc = GPG_ERR_NOT_IMPLEMENTED; +@@ -688,11 +700,15 @@ _gcry_pk_verify (gcry_sexp_t s_sig, gcry_sexp_t s_hash, gcry_sexp_t s_pkey) + else if (!spec->flags.fips && fips_mode ()) + { + if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) +- rc = GPG_ERR_PUBKEY_ALGO; ++ { ++ rc = GPG_ERR_PUBKEY_ALGO; ++ goto leave; ++ } + else + fips_service_indicator_mark_non_compliant (); + } +- else if (spec->verify) ++ ++ if (spec->verify) + rc = spec->verify (s_sig, s_hash, keyparms); + else + rc = GPG_ERR_NOT_IMPLEMENTED; +@@ -736,11 +752,15 @@ _gcry_pk_verify_md (gcry_sexp_t s_sig, const char *tmpl, gcry_md_hd_t hd_orig, + else if (!spec->flags.fips && fips_mode ()) + { + if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) +- rc = GPG_ERR_PUBKEY_ALGO; ++ { ++ rc = GPG_ERR_PUBKEY_ALGO; ++ goto leave; ++ } + else + fips_service_indicator_mark_non_compliant (); + } +- else if (spec->verify) ++ ++ if (spec->verify) + rc = spec->verify (s_sig, s_data, keyparms); + else + rc = GPG_ERR_NOT_IMPLEMENTED; +@@ -777,11 +797,15 @@ _gcry_pk_testkey (gcry_sexp_t s_key) + else if (!spec->flags.fips && fips_mode ()) + { + if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) +- rc = GPG_ERR_PUBKEY_ALGO; ++ { ++ rc = GPG_ERR_PUBKEY_ALGO; ++ goto leave; ++ } + else + fips_service_indicator_mark_non_compliant (); + } +- else if (spec->check_secret_key) ++ ++ if (spec->check_secret_key) + rc = spec->check_secret_key (keyparms); + else + rc = GPG_ERR_NOT_IMPLEMENTED; +-- +2.49.0 + diff --git a/libgcrypt-fips-cipher-Fix-memory-leak-for-gcry_pk_hash_sign.patch b/libgcrypt-fips-cipher-Fix-memory-leak-for-gcry_pk_hash_sign.patch new file mode 100644 index 0000000..445136e --- /dev/null +++ b/libgcrypt-fips-cipher-Fix-memory-leak-for-gcry_pk_hash_sign.patch @@ -0,0 +1,76 @@ +From 5e925e6c348450bf80b4560abac9a035903bff59 Mon Sep 17 00:00:00 2001 +From: NIIBE Yutaka +Date: Mon, 6 Jan 2025 12:01:56 +0900 +Subject: [PATCH 19/19] fips,cipher: Fix memory leak for gcry_pk_hash_sign. +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* cipher/pubkey.c (prepare_datasexp_to_be_signed): Release +copied HD when error. + +-- + +GnuPG-bug-id: 7338 +Signed-off-by: NIIBE Yutaka +Signed-off-by: Lucas Mülling +--- + cipher/pubkey.c | 21 +++++++++++++++++---- + 1 file changed, 17 insertions(+), 4 deletions(-) + +diff --git a/cipher/pubkey.c b/cipher/pubkey.c +index aacf9f5a..c28ec124 100644 +--- a/cipher/pubkey.c ++++ b/cipher/pubkey.c +@@ -512,7 +512,10 @@ prepare_datasexp_to_be_signed (const char *tmpl, gcry_md_hd_t hd, + /* Check if it has fixed hash name or %s */ + s = strstr (tmpl, "(hash "); + if (s == NULL) +- return GPG_ERR_DIGEST_ALGO; ++ { ++ _gcry_md_close (hd); ++ return GPG_ERR_DIGEST_ALGO; ++ } + + s += 6; + if (!strncmp (s, "%s", 2)) +@@ -522,7 +525,10 @@ prepare_datasexp_to_be_signed (const char *tmpl, gcry_md_hd_t hd, + if (fips_mode () && algo == GCRY_MD_SHA1) + { + if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) +- return GPG_ERR_DIGEST_ALGO; ++ { ++ _gcry_md_close (hd); ++ return GPG_ERR_DIGEST_ALGO; ++ } + else + fips_service_indicator_mark_non_compliant (); + } +@@ -541,7 +547,11 @@ prepare_datasexp_to_be_signed (const char *tmpl, gcry_md_hd_t hd, + + digest_name_supplied = xtrymalloc (p - s + 1); + if (!digest_name_supplied) +- return gpg_error_from_syserror (); ++ { ++ rc = gpg_err_code_from_syserror (); ++ _gcry_md_close (hd); ++ return rc; ++ } + memcpy (digest_name_supplied, s, p - s); + digest_name_supplied[p - s] = 0; + +@@ -555,7 +565,10 @@ prepare_datasexp_to_be_signed (const char *tmpl, gcry_md_hd_t hd, + else if (fips_mode () && algo == GCRY_MD_SHA1) + { + if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) +- return GPG_ERR_DIGEST_ALGO; ++ { ++ _gcry_md_close (hd); ++ return GPG_ERR_DIGEST_ALGO; ++ } + else + fips_service_indicator_mark_non_compliant (); + } +-- +2.49.0 + diff --git a/libgcrypt-fips-cipher-Implement-FIPS-service-indicator-for-gcry_pk_hash_-API.patch b/libgcrypt-fips-cipher-Implement-FIPS-service-indicator-for-gcry_pk_hash_-API.patch new file mode 100644 index 0000000..0490e38 --- /dev/null +++ b/libgcrypt-fips-cipher-Implement-FIPS-service-indicator-for-gcry_pk_hash_-API.patch @@ -0,0 +1,360 @@ +From edb43bc290046bd22548bf69ae2fbeb453112e44 Mon Sep 17 00:00:00 2001 +From: NIIBE Yutaka +Date: Wed, 18 Dec 2024 14:18:26 +0900 +Subject: [PATCH 11/19] fips,cipher: Implement FIPS service indicator for + gcry_pk_hash_ API. +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* src/visibility.c (gcry_pk_hash_sign): Initialize the indicator. +(gcry_pk_hash_verify): Likewise. +* tests/t-fips-service-ind.c (check_pk_hash_sign_verify): New. +(main): Call check_pk_hash_sign_verify. +* cipher/ecc-curves.c (_gcry_ecc_fill_in_curve): Don't reject, but +mark non-compliance. +* cipher/pubkey.c (prepare_datasexp_to_be_signed): Likewise. +(_gcry_pk_sign_md, _gcry_pk_verify_md): Likewise. + +-- + +GnuPG-bug-id: 7338 +Signed-off-by: NIIBE Yutaka +Signed-off-by: Lucas Mülling +--- + cipher/ecc-curves.c | 2 +- + cipher/pubkey.c | 20 ++-- + src/visibility.c | 2 + + tests/t-fips-service-ind.c | 209 +++++++++++++++++++++++++++++++++++++ + 4 files changed, 222 insertions(+), 11 deletions(-) + +diff --git a/cipher/ecc-curves.c b/cipher/ecc-curves.c +index 17fa5505..ddf9cbe1 100644 +--- a/cipher/ecc-curves.c ++++ b/cipher/ecc-curves.c +@@ -645,7 +645,7 @@ _gcry_ecc_fill_in_curve (unsigned int nbits, const char *name, + possible to bypass this check by specifying the curve parameters + directly. */ + if (fips_mode () && !domain_parms[idx].fips ) +- return GPG_ERR_NOT_SUPPORTED; ++ fips_service_indicator_mark_non_compliant (); + + switch (domain_parms[idx].model) + { +diff --git a/cipher/pubkey.c b/cipher/pubkey.c +index 214bd611..e2e54199 100644 +--- a/cipher/pubkey.c ++++ b/cipher/pubkey.c +@@ -510,10 +510,7 @@ prepare_datasexp_to_be_signed (const char *tmpl, gcry_md_hd_t hd, + algo = _gcry_md_get_algo (hd); + + if (fips_mode () && algo == GCRY_MD_SHA1) +- { +- _gcry_md_close (hd); +- return GPG_ERR_DIGEST_ALGO; +- } ++ fips_service_indicator_mark_non_compliant (); + + digest_name = _gcry_md_algo_name (algo); + digest_size = (int)_gcry_md_get_algo_dlen (algo); +@@ -535,12 +532,13 @@ prepare_datasexp_to_be_signed (const char *tmpl, gcry_md_hd_t hd, + + algo = _gcry_md_map_name (digest_name_supplied); + xfree (digest_name_supplied); +- if (algo == 0 +- || (fips_mode () && algo == GCRY_MD_SHA1)) ++ if (algo == 0) + { + _gcry_md_close (hd); + return GPG_ERR_DIGEST_ALGO; + } ++ else if (fips_mode () && algo == GCRY_MD_SHA1) ++ fips_service_indicator_mark_non_compliant (); + + digest_size = (int)_gcry_md_get_algo_dlen (algo); + digest = _gcry_md_read (hd, algo); +@@ -613,10 +611,11 @@ _gcry_pk_sign_md (gcry_sexp_t *r_sig, const char *tmpl, gcry_md_hd_t hd_orig, + if (rc) + goto leave; + ++ if (!spec->flags.fips && fips_mode ()) ++ fips_service_indicator_mark_non_compliant (); ++ + if (spec->flags.disabled) + rc = GPG_ERR_PUBKEY_ALGO; +- else if (!spec->flags.fips && fips_mode ()) +- rc = GPG_ERR_PUBKEY_ALGO; + else if (spec->sign) + rc = spec->sign (r_sig, s_data, keyparms); + else +@@ -690,10 +689,11 @@ _gcry_pk_verify_md (gcry_sexp_t s_sig, const char *tmpl, gcry_md_hd_t hd_orig, + if (rc) + goto leave; + ++ if (!spec->flags.fips && fips_mode ()) ++ fips_service_indicator_mark_non_compliant (); ++ + if (spec->flags.disabled) + rc = GPG_ERR_PUBKEY_ALGO; +- else if (!spec->flags.fips && fips_mode ()) +- rc = GPG_ERR_PUBKEY_ALGO; + else if (spec->verify) + rc = spec->verify (s_sig, s_data, keyparms); + else +diff --git a/src/visibility.c b/src/visibility.c +index c9d07f0b..d22c8b59 100644 +--- a/src/visibility.c ++++ b/src/visibility.c +@@ -1056,6 +1056,7 @@ gcry_pk_hash_sign (gcry_sexp_t *result, const char *data_tmpl, gcry_sexp_t skey, + *result = NULL; + return gpg_error (fips_not_operational ()); + } ++ fips_service_indicator_init (); + return gpg_error (_gcry_pk_sign_md (result, data_tmpl, hd, skey, ctx)); + } + +@@ -1073,6 +1074,7 @@ gcry_pk_hash_verify (gcry_sexp_t sigval, const char *data_tmpl, gcry_sexp_t pkey + { + if (!fips_is_operational ()) + return gpg_error (fips_not_operational ()); ++ fips_service_indicator_init (); + return gpg_error (_gcry_pk_verify_md (sigval, data_tmpl, hd, pkey, ctx)); + } + +diff --git a/tests/t-fips-service-ind.c b/tests/t-fips-service-ind.c +index 4b13436f..9a22d696 100644 +--- a/tests/t-fips-service-ind.c ++++ b/tests/t-fips-service-ind.c +@@ -29,6 +29,7 @@ + + #define PGM "t-fips-service-ind" + ++#define NEED_HEX2BUFFER + #include "t-common.h" + static int in_fips_mode; + #define MAX_DATA_LEN 1040 +@@ -39,6 +40,213 @@ static int in_fips_mode; + # include + #endif + ++/* Check gcry_pk_hash_sign, gcry_pk_hash_verify API. */ ++static void ++check_pk_hash_sign_verify (void) ++{ ++ static struct { ++ int md_algo; ++ const char *prvkey; ++ const char *pubkey; ++ const char *data_tmpl; ++ const char *k; ++ int expect_failure; ++ int expect_failure_hash; ++ } tv[] = { ++ { /* non-compliant hash */ ++ GCRY_MD_BLAKE2B_512, ++ "(private-key (ecc (curve nistp256)" ++ " (d #519b423d715f8b581f4fa8ee59f4771a5b44c8130b4e3eacca54a56dda72b464#)))", ++ "(public-key (ecc (curve nistp256)" ++ " (q #041ccbe91c075fc7f4f033bfa248db8fccd3565de94bbfb12f3c59ff46c271bf83" ++ "ce4014c68811f9a21a1fdb2c0e6113e06db7ca93b7404e78dc7ccd5ca89a4ca9#)))", ++ "(data(flags raw)(hash %s %b)(label %b))", ++ "94a1bbb14b906a61a280f245f9e93c7f3b4a6247824f5d33b9670787642a68de", ++ 1, 1 ++ }, ++ { /* non-compliant curve */ ++ GCRY_MD_SHA256, ++ "(private-key (ecc (curve secp256k1)" ++ " (d #c2cdf0a8b0a83b35ace53f097b5e6e6a0a1f2d40535eff1cf434f52a43d59d8f#)))", ++ ++ "(public-key (ecc (curve secp256k1)" ++ " (q #046fcc37ea5e9e09fec6c83e5fbd7a745e3eee81d16ebd861c9e66f55518c19798" ++ "4e9f113c07f875691df8afc1029496fc4cb9509b39dcd38f251a83359cc8b4f7#)))", ++ "(data(flags raw)(hash %s %b)(label %b))", ++ "94a1bbb14b906a61a280f245f9e93c7f3b4a6247824f5d33b9670787642a68de", ++ 1, 0 ++ }, ++ { ++ GCRY_MD_SHA256, ++ "(private-key (ecc (curve nistp256)" ++ " (d #519b423d715f8b581f4fa8ee59f4771a5b44c8130b4e3eacca54a56dda72b464#)))", ++ "(public-key (ecc (curve nistp256)" ++ " (q #041ccbe91c075fc7f4f033bfa248db8fccd3565de94bbfb12f3c59ff46c271bf83" ++ "ce4014c68811f9a21a1fdb2c0e6113e06db7ca93b7404e78dc7ccd5ca89a4ca9#)))", ++ "(data(flags raw)(hash %s %b)(label %b))", ++ "94a1bbb14b906a61a280f245f9e93c7f3b4a6247824f5d33b9670787642a68de", ++ 0, 0 ++ } ++ }; ++ int tvidx; ++ gpg_error_t err; ++ gpg_err_code_t ec; ++ const char *msg = "Takerufuji Mikiya, who won the championship in March 2024"; ++ int msglen; ++ ++ msglen = strlen (msg); ++ for (tvidx=0; tvidx < DIM(tv); tvidx++) ++ { ++ gcry_md_hd_t hd = NULL; ++ gcry_sexp_t s_sk = NULL; ++ gcry_sexp_t s_pk = NULL; ++ void *buffer = NULL; ++ size_t buflen; ++ gcry_ctx_t ctx = NULL; ++ gcry_sexp_t s_sig= NULL; ++ ++ if (verbose) ++ info ("checking gcry_pk_hash_ test %d\n", tvidx); ++ ++ err = gcry_md_open (&hd, tv[tvidx].md_algo, 0); ++ if (err) ++ { ++ fail ("algo %d, gcry_md_open failed: %s\n", tv[tvidx].md_algo, ++ gpg_strerror (err)); ++ goto next; ++ } ++ ++ ec = gcry_get_fips_service_indicator (); ++ if (ec == GPG_ERR_INV_OP) ++ { ++ /* libgcrypt is old, no support of the FIPS service indicator. */ ++ fail ("gcry_pk_hash test %d unexpectedly failed to check the FIPS service indicator.\n", ++ tvidx); ++ goto next; ++ } ++ ++ if (in_fips_mode && !tv[tvidx].expect_failure_hash && ec) ++ { ++ /* Success with the FIPS service indicator == 0 expected, but != 0. */ ++ fail ("gcry_pk_hash test %d unexpectedly set the indicator in FIPS mode.\n", ++ tvidx); ++ goto next; ++ } ++ else if (in_fips_mode && tv[tvidx].expect_failure_hash && !ec) ++ { ++ /* Success with the FIPS service indicator != 0 expected, but == 0. */ ++ fail ("gcry_pk_hash test %d unexpectedly cleared the indicator in FIPS mode.\n", ++ tvidx); ++ goto next; ++ } ++ ++ err = gcry_sexp_build (&s_sk, NULL, tv[tvidx].prvkey); ++ if (err) ++ { ++ fail ("error building SEXP for test, %s: %s", ++ "sk", gpg_strerror (err)); ++ goto next; ++ } ++ ++ err = gcry_sexp_build (&s_pk, NULL, tv[tvidx].pubkey); ++ if (err) ++ { ++ fail ("error building SEXP for test, %s: %s", ++ "pk", gpg_strerror (err)); ++ goto next; ++ } ++ ++ if (!(buffer = hex2buffer (tv[tvidx].k, &buflen))) ++ { ++ fail ("error parsing for test, %s: %s", ++ "msg", "invalid hex string"); ++ goto next; ++ } ++ ++ err = gcry_pk_random_override_new (&ctx, buffer, buflen); ++ if (err) ++ { ++ fail ("error setting 'k' for test: %s", ++ gpg_strerror (err)); ++ goto next; ++ } ++ ++ gcry_md_write (hd, msg, msglen); ++ ++ err = gcry_pk_hash_sign (&s_sig, tv[tvidx].data_tmpl, s_sk, hd, ctx); ++ if (err) ++ { ++ fail ("gcry_pk_hash_sign failed: %s", gpg_strerror (err)); ++ goto next; ++ } ++ ++ ec = gcry_get_fips_service_indicator (); ++ if (ec == GPG_ERR_INV_OP) ++ { ++ /* libgcrypt is old, no support of the FIPS service indicator. */ ++ fail ("gcry_pk_hash test %d unexpectedly failed to check the FIPS service indicator.\n", ++ tvidx); ++ goto next; ++ } ++ ++ if (in_fips_mode && !tv[tvidx].expect_failure && ec) ++ { ++ /* Success with the FIPS service indicator == 0 expected, but != 0. */ ++ fail ("gcry_pk_hash test %d unexpectedly set the indicator in FIPS mode.\n", ++ tvidx); ++ goto next; ++ } ++ else if (in_fips_mode && tv[tvidx].expect_failure && !ec) ++ { ++ /* Success with the FIPS service indicator != 0 expected, but == 0. */ ++ fail ("gcry_pk_hash_sign test %d unexpectedly cleared the indicator in FIPS mode.\n", ++ tvidx); ++ goto next; ++ } ++ ++ err = gcry_pk_hash_verify (s_sig, tv[tvidx].data_tmpl, s_pk, hd, ctx); ++ if (err) ++ { ++ fail ("gcry_pk_hash_verify failed for test: %s", ++ gpg_strerror (err)); ++ goto next; ++ } ++ ++ ec = gcry_get_fips_service_indicator (); ++ if (ec == GPG_ERR_INV_OP) ++ { ++ /* libgcrypt is old, no support of the FIPS service indicator. */ ++ fail ("gcry_pk_hash test %d unexpectedly failed to check the FIPS service indicator.\n", ++ tvidx); ++ goto next; ++ } ++ ++ if (in_fips_mode && !tv[tvidx].expect_failure && ec) ++ { ++ /* Success with the FIPS service indicator == 0 expected, but != 0. */ ++ fail ("gcry_pk_hash test %d unexpectedly set the indicator in FIPS mode.\n", ++ tvidx); ++ goto next; ++ } ++ else if (in_fips_mode && tv[tvidx].expect_failure && !ec) ++ { ++ /* Success with the FIPS service indicator != 0 expected, but == 0. */ ++ fail ("gcry_pk_hash_verify test %d unexpectedly cleared the indicator in FIPS mode.\n", ++ tvidx); ++ goto next; ++ } ++ ++ next: ++ gcry_sexp_release (s_sig); ++ xfree (buffer); ++ gcry_ctx_release (ctx); ++ gcry_sexp_release (s_pk); ++ gcry_sexp_release (s_sk); ++ if (hd) ++ gcry_md_close (hd); ++ } ++} ++ + /* Check gcry_cipher_open, gcry_cipher_setkey, gcry_cipher_encrypt, + gcry_cipher_decrypt, gcry_cipher_close API. */ + static void +@@ -936,6 +1144,7 @@ main (int argc, char **argv) + check_md_o_w_r_c (); + check_mac_o_w_r_c (); + check_cipher_o_s_e_d_c (); ++ check_pk_hash_sign_verify (); + + return !!error_count; + } +-- +2.49.0 + diff --git a/libgcrypt-fips-cipher-Implement-new-FIPS-service-indicator-for-cipher_open.patch b/libgcrypt-fips-cipher-Implement-new-FIPS-service-indicator-for-cipher_open.patch new file mode 100644 index 0000000..2124c48 --- /dev/null +++ b/libgcrypt-fips-cipher-Implement-new-FIPS-service-indicator-for-cipher_open.patch @@ -0,0 +1,122 @@ +From 69a5d0ed18a3ddc6f297de783c7cef5ad2257df0 Mon Sep 17 00:00:00 2001 +From: NIIBE Yutaka +Date: Fri, 13 Dec 2024 14:40:53 +0900 +Subject: [PATCH 05/19] fips,cipher: Implement new FIPS service indicator for + cipher_open. +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* src/gcrypt.h.in (GCRY_CIPHER_FLAG_REJECT_NON_FIPS): New. +* cipher/cipher.c (_gcry_cipher_open_internal): Don't reject +but mark the service indicator in FIPS mode. +(cipher_setkey): Likewise. +* src/visibility.c (gcry_cipher_open): Initialize the service +indicator. +(gcry_cipher_setkey): Likewise. + +-- + +GnuPG-bug-id: 7338 +Signed-off-by: NIIBE Yutaka +Signed-off-by: Lucas Mülling +--- + cipher/cipher.c | 23 +++++++++++++++++++---- + src/gcrypt.h.in | 3 ++- + src/visibility.c | 4 ++-- + 3 files changed, 23 insertions(+), 7 deletions(-) + +diff --git a/cipher/cipher.c b/cipher/cipher.c +index 898bb58f..7ffacf05 100644 +--- a/cipher/cipher.c ++++ b/cipher/cipher.c +@@ -509,7 +509,8 @@ gcry_err_code_t + _gcry_cipher_open_internal (gcry_cipher_hd_t *handle, + int algo, int mode, unsigned int flags) + { +- int secure = (flags & GCRY_CIPHER_SECURE); ++ int secure = !!(flags & GCRY_CIPHER_SECURE); ++ int reject_non_fips = !!(flags & GCRY_CIPHER_FLAG_REJECT_NON_FIPS); + gcry_cipher_spec_t *spec; + gcry_cipher_hd_t h = NULL; + gcry_err_code_t err; +@@ -524,7 +525,15 @@ _gcry_cipher_open_internal (gcry_cipher_hd_t *handle, + else if (spec->flags.disabled) + err = GPG_ERR_CIPHER_ALGO; + else if (!spec->flags.fips && fips_mode ()) +- err = GPG_ERR_CIPHER_ALGO; ++ { ++ if (reject_non_fips) ++ err = GPG_ERR_CIPHER_ALGO; ++ else ++ { ++ fips_service_indicator_mark_non_compliant (); ++ err = 0; ++ } ++ } + else + err = 0; + +@@ -535,7 +544,8 @@ _gcry_cipher_open_internal (gcry_cipher_hd_t *handle, + | GCRY_CIPHER_ENABLE_SYNC + | GCRY_CIPHER_CBC_CTS + | GCRY_CIPHER_CBC_MAC +- | GCRY_CIPHER_EXTENDED)) ++ | GCRY_CIPHER_EXTENDED ++ | GCRY_CIPHER_FLAG_REJECT_NON_FIPS)) + || ((flags & GCRY_CIPHER_CBC_CTS) && (flags & GCRY_CIPHER_CBC_MAC)))) + err = GPG_ERR_CIPHER_ALGO; + +@@ -765,7 +775,12 @@ cipher_setkey (gcry_cipher_hd_t c, byte *key, size_t keylen) + See "Implementation Guidance for FIPS 140-2, A.9 XTS-AES + Key Generation Requirements" for details. */ + if (buf_eq_const (key, key + keylen, keylen)) +- return GPG_ERR_WEAK_KEY; ++ { ++ if ((c->flags & GCRY_CIPHER_FLAG_REJECT_NON_FIPS)) ++ return GPG_ERR_WEAK_KEY; ++ else ++ fips_service_indicator_mark_non_compliant (); ++ } + } + } + else if (c->mode == GCRY_CIPHER_MODE_SIV) +diff --git a/src/gcrypt.h.in b/src/gcrypt.h.in +index 2a378639..2ed9914b 100644 +--- a/src/gcrypt.h.in ++++ b/src/gcrypt.h.in +@@ -992,7 +992,8 @@ enum gcry_cipher_flags + GCRY_CIPHER_ENABLE_SYNC = 2, /* Enable CFB sync mode. */ + GCRY_CIPHER_CBC_CTS = 4, /* Enable CBC cipher text stealing (CTS). */ + GCRY_CIPHER_CBC_MAC = 8, /* Enable CBC message auth. code (MAC). */ +- GCRY_CIPHER_EXTENDED = 16 /* Enable extended AES-WRAP. */ ++ GCRY_CIPHER_EXTENDED = 16, /* Enable extended AES-WRAP. */ ++ GCRY_CIPHER_FLAG_REJECT_NON_FIPS = 32 /* Reject non-FIPS-compliant algo. */ + }; + + /* Methods used for AEAD IV generation. */ +diff --git a/src/visibility.c b/src/visibility.c +index 7699f14f..d219f1a6 100644 +--- a/src/visibility.c ++++ b/src/visibility.c +@@ -736,7 +736,7 @@ gcry_cipher_open (gcry_cipher_hd_t *handle, + *handle = NULL; + return gpg_error (fips_not_operational ()); + } +- ++ fips_service_indicator_init (); + return gpg_error (_gcry_cipher_open (handle, algo, mode, flags)); + } + +@@ -751,7 +751,7 @@ gcry_cipher_setkey (gcry_cipher_hd_t hd, const void *key, size_t keylen) + { + if (!fips_is_operational ()) + return gpg_error (fips_not_operational ()); +- ++ fips_service_indicator_init (); + return gcry_error (_gcry_cipher_setkey (hd, key, keylen)); + } + +-- +2.49.0 + diff --git a/libgcrypt-fips-ecc-Add-rejecting-or-marking-for-gcry_pk_get_curve.patch b/libgcrypt-fips-ecc-Add-rejecting-or-marking-for-gcry_pk_get_curve.patch new file mode 100644 index 0000000..27fd75b --- /dev/null +++ b/libgcrypt-fips-ecc-Add-rejecting-or-marking-for-gcry_pk_get_curve.patch @@ -0,0 +1,43 @@ +From c6a092abbe7bea315394b15f28fd231dae0e4d7c Mon Sep 17 00:00:00 2001 +From: NIIBE Yutaka +Date: Tue, 24 Dec 2024 17:01:45 +0900 +Subject: [PATCH 16/19] fips,ecc: Add rejecting or marking for + gcry_pk_get_curve. +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* cipher/ecc-curves.c (_gcry_ecc_get_curve): Check under FIPS mode. + +-- + +GnuPG-bug-id: 7338 +Signed-off-by: NIIBE Yutaka +Signed-off-by: Lucas Mülling +--- + cipher/ecc-curves.c | 9 +++++++++ + 1 file changed, 9 insertions(+) + +diff --git a/cipher/ecc-curves.c b/cipher/ecc-curves.c +index fe0a1eb2..975f6a07 100644 +--- a/cipher/ecc-curves.c ++++ b/cipher/ecc-curves.c +@@ -844,6 +844,15 @@ _gcry_ecc_get_curve (gcry_sexp_t keyparms, int iterator, unsigned int *r_nbits) + if (r_nbits) + *r_nbits = domain_parms[idx].nbits; + } ++ ++ if (fips_mode () && !domain_parms[idx].fips) ++ { ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) ++ return NULL; ++ else ++ fips_service_indicator_mark_non_compliant (); ++ } ++ + return result; + } + +-- +2.49.0 + diff --git a/libgcrypt-fips-ecc-Check-DATA-in-gcry_pk_sign-verify-in-FIPS-mode.patch b/libgcrypt-fips-ecc-Check-DATA-in-gcry_pk_sign-verify-in-FIPS-mode.patch new file mode 100644 index 0000000..310c5c9 --- /dev/null +++ b/libgcrypt-fips-ecc-Check-DATA-in-gcry_pk_sign-verify-in-FIPS-mode.patch @@ -0,0 +1,282 @@ +From 53c97483b17fee280e24f595bc0d82d9b362ffde Mon Sep 17 00:00:00 2001 +From: NIIBE Yutaka +Date: Thu, 26 Dec 2024 11:12:48 +0900 +Subject: [PATCH 18/19] fips,ecc: Check DATA in gcry_pk_sign/verify in FIPS + mode. +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* src/gcrypt.h.in (GCRY_FIPS_FLAG_REJECT_PK_MD): New. +(GCRY_FIPS_FLAG_REJECT_PK_GOST_SM2): New. + +* cipher/ecc.c (ecc_sign): Check if GOST or SM2. Check if hash is +compliant. +(ecc_verify): Likewise. +* tests/t-fips-service-ind.c (check_pk_s_v): Modify tests including +hash compliance. + +-- + +GnuPG-bug-id: 7338 +Signed-off-by: NIIBE Yutaka +Signed-off-by: Lucas Mülling +--- + cipher/ecc.c | 70 +++++++++++++++++++++++++++++++++++--- + src/gcrypt.h.in | 4 ++- + tests/t-fips-service-ind.c | 52 ++++++++++++++++++++-------- + 3 files changed, 107 insertions(+), 19 deletions(-) + +diff --git a/cipher/ecc.c b/cipher/ecc.c +index 8896afd0..525523ed 100644 +--- a/cipher/ecc.c ++++ b/cipher/ecc.c +@@ -941,6 +941,18 @@ ecc_sign (gcry_sexp_t *r_sig, gcry_sexp_t s_data, gcry_sexp_t keyparms) + if (rc) + goto leave; + ++ if (fips_mode () ++ && ((ctx.flags & PUBKEY_FLAG_GOST) || (ctx.flags & PUBKEY_FLAG_SM2))) ++ { ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK_GOST_SM2)) ++ { ++ rc = GPG_ERR_INV_DATA; ++ goto leave; ++ } ++ else ++ fips_service_indicator_mark_non_compliant (); ++ } ++ + /* Hash algo is determined by curve in EdDSA. */ + if ((ctx.flags & PUBKEY_FLAG_EDDSA)) + { +@@ -953,10 +965,12 @@ ecc_sign (gcry_sexp_t *r_sig, gcry_sexp_t s_data, gcry_sexp_t keyparms) + && ctx.hash_algo != GCRY_MD_SHAKE256))) + { + if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) +- rc = GPG_ERR_DIGEST_ALGO; ++ { ++ rc = GPG_ERR_DIGEST_ALGO; ++ goto leave; ++ } + else + fips_service_indicator_mark_non_compliant (); +- goto leave; + } + } + else +@@ -967,6 +981,23 @@ ecc_sign (gcry_sexp_t *r_sig, gcry_sexp_t s_data, gcry_sexp_t keyparms) + ctx.hash_algo = GCRY_MD_SHAKE256; + } + } ++ else ++ { ++ if (fips_mode ()) ++ { ++ if (_gcry_md_algo_info (ctx.hash_algo, GCRYCTL_TEST_ALGO, NULL, NULL) ++ || ctx.hash_algo == GCRY_MD_SHA1) ++ { ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK_MD)) ++ { ++ rc = GPG_ERR_DIGEST_ALGO; ++ goto leave; ++ } ++ else ++ fips_service_indicator_mark_non_compliant (); ++ } ++ } ++ } + + sig_r = mpi_new (0); + sig_s = mpi_new (0); +@@ -1066,6 +1097,18 @@ ecc_verify (gcry_sexp_t s_sig, gcry_sexp_t s_data, gcry_sexp_t s_keyparms) + if (DBG_CIPHER) + log_mpidump ("ecc_verify data", data); + ++ if (fips_mode () ++ && ((ctx.flags & PUBKEY_FLAG_GOST) || (ctx.flags & PUBKEY_FLAG_SM2))) ++ { ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK_GOST_SM2)) ++ { ++ rc = GPG_ERR_INV_DATA; ++ goto leave; ++ } ++ else ++ fips_service_indicator_mark_non_compliant (); ++ } ++ + /* Hash algo is determined by curve in EdDSA. */ + if ((ctx.flags & PUBKEY_FLAG_EDDSA)) + { +@@ -1078,10 +1121,12 @@ ecc_verify (gcry_sexp_t s_sig, gcry_sexp_t s_data, gcry_sexp_t s_keyparms) + && ctx.hash_algo != GCRY_MD_SHAKE256))) + { + if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) +- rc = GPG_ERR_DIGEST_ALGO; ++ { ++ rc = GPG_ERR_DIGEST_ALGO; ++ goto leave; ++ } + else + fips_service_indicator_mark_non_compliant (); +- goto leave; + } + } + else +@@ -1092,6 +1137,23 @@ ecc_verify (gcry_sexp_t s_sig, gcry_sexp_t s_data, gcry_sexp_t s_keyparms) + ctx.hash_algo = GCRY_MD_SHAKE256; + } + } ++ else ++ { ++ if (fips_mode ()) ++ { ++ if (_gcry_md_algo_info (ctx.hash_algo, GCRYCTL_TEST_ALGO, NULL, NULL) ++ || ctx.hash_algo == GCRY_MD_SHA1) ++ { ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK_MD)) ++ { ++ rc = GPG_ERR_DIGEST_ALGO; ++ goto leave; ++ } ++ else ++ fips_service_indicator_mark_non_compliant (); ++ } ++ } ++ } + + /* + * Extract the signature value. +diff --git a/src/gcrypt.h.in b/src/gcrypt.h.in +index 7bee45e9..fcb6a327 100644 +--- a/src/gcrypt.h.in ++++ b/src/gcrypt.h.in +@@ -1986,11 +1986,13 @@ char *gcry_get_config (int mode, const char *what); + #define GCRY_FIPS_FLAG_REJECT_MAC (1 << 3) + #define GCRY_FIPS_FLAG_REJECT_CIPHER (1 << 4) + #define GCRY_FIPS_FLAG_REJECT_PK (1 << 5) ++#define GCRY_FIPS_FLAG_REJECT_PK_MD (1 << 6) ++#define GCRY_FIPS_FLAG_REJECT_PK_GOST_SM2 (1 << 7) + + #define GCRY_FIPS_FLAG_REJECT_MD \ + (GCRY_FIPS_FLAG_REJECT_MD_MD5 | GCRY_FIPS_FLAG_REJECT_MD_OTHERS) + +-/* Note: Don't reject MD5 */ ++/* Note: Don't reject MD5, PK MD, PK GOST and PK SM2 */ + #define GCRY_FIPS_FLAG_REJECT_COMPAT110 \ + (GCRY_FIPS_FLAG_REJECT_MD_OTHERS \ + | GCRY_FIPS_FLAG_REJECT_MAC \ +diff --git a/tests/t-fips-service-ind.c b/tests/t-fips-service-ind.c +index 90d92c70..fe963fa5 100644 +--- a/tests/t-fips-service-ind.c ++++ b/tests/t-fips-service-ind.c +@@ -228,6 +228,7 @@ check_pk_s_v (int reject) + static struct { + const char *prvkey; + const char *pubkey; ++ const char *data; + int expect_failure; + } tv[] = { + { +@@ -236,6 +237,8 @@ check_pk_s_v (int reject) + "(public-key (ecc (curve nistp256)" + " (q #041ccbe91c075fc7f4f033bfa248db8fccd3565de94bbfb12f3c59ff46c271bf83" + "ce4014c68811f9a21a1fdb2c0e6113e06db7ca93b7404e78dc7ccd5ca89a4ca9#)))", ++ "(data (flags raw)(hash sha256 " ++ "#00112233445566778899AABBCCDDEEFF000102030405060708090A0B0C0D0E0F#))", + 0 + }, + { /* non-compliant curve */ +@@ -244,28 +247,40 @@ check_pk_s_v (int reject) + "(public-key (ecc (curve secp256k1)" + " (q #046fcc37ea5e9e09fec6c83e5fbd7a745e3eee81d16ebd861c9e66f55518c19798" + "4e9f113c07f875691df8afc1029496fc4cb9509b39dcd38f251a83359cc8b4f7#)))", ++ "(data (flags raw)(hash sha256 " ++ "#00112233445566778899AABBCCDDEEFF000102030405060708090A0B0C0D0E0F#))", + 1 +- } ++ }, ++ { /* non-compliant hash */ ++ "(private-key (ecc (curve nistp256)" ++ " (d #519b423d715f8b581f4fa8ee59f4771a5b44c8130b4e3eacca54a56dda72b464#)))", ++ "(public-key (ecc (curve nistp256)" ++ " (q #041ccbe91c075fc7f4f033bfa248db8fccd3565de94bbfb12f3c59ff46c271bf83" ++ "ce4014c68811f9a21a1fdb2c0e6113e06db7ca93b7404e78dc7ccd5ca89a4ca9#)))", ++ "(data (flags raw)(hash ripemd160 " ++ "#00112233445566778899AABBCCDDEEFF00010203#))", ++ 1 ++ }, ++ { /* non-compliant hash for signing */ ++ "(private-key (ecc (curve nistp256)" ++ " (d #519b423d715f8b581f4fa8ee59f4771a5b44c8130b4e3eacca54a56dda72b464#)))", ++ "(public-key (ecc (curve nistp256)" ++ " (q #041ccbe91c075fc7f4f033bfa248db8fccd3565de94bbfb12f3c59ff46c271bf83" ++ "ce4014c68811f9a21a1fdb2c0e6113e06db7ca93b7404e78dc7ccd5ca89a4ca9#)))", ++ "(data (flags raw)(hash sha1 " ++ "#00112233445566778899AABBCCDDEEFF00010203#))", ++ 1 ++ }, + }; + int tvidx; + gpg_error_t err; + gpg_err_code_t ec; +- const char *data = "(data (flags raw)" +- "(hash sha256 #00112233445566778899AABBCCDDEEFF000102030405060708090A0B0C0D0E0F#))"; +- gcry_sexp_t s_data = NULL; +- +- err = gcry_sexp_build (&s_data, NULL, data); +- if (err) +- { +- fail ("error building SEXP for test, %s: %s", +- "data", gpg_strerror (err)); +- return; +- } + + for (tvidx=0; tvidx < DIM(tv); tvidx++) + { + gcry_sexp_t s_pk = NULL; + gcry_sexp_t s_sk = NULL; ++ gcry_sexp_t s_data = NULL; + gcry_sexp_t s_sig= NULL; + + if (verbose) +@@ -287,6 +302,14 @@ check_pk_s_v (int reject) + goto next; + } + ++ err = gcry_sexp_build (&s_data, NULL, tv[tvidx].data); ++ if (err) ++ { ++ fail ("error building SEXP for test, %s: %s", ++ "data", gpg_strerror (err)); ++ goto next; ++ } ++ + err = gcry_pk_sign (&s_sig, s_data, s_sk); + if (err) + { +@@ -363,11 +386,10 @@ check_pk_s_v (int reject) + + next: + gcry_sexp_release (s_sig); ++ gcry_sexp_release (s_data); + gcry_sexp_release (s_pk); + gcry_sexp_release (s_sk); + } +- +- gcry_sexp_release (s_data); + } + + /* Check gcry_pk_hash_sign, gcry_pk_hash_verify API. */ +@@ -1461,6 +1483,8 @@ main (int argc, char **argv) + + xgcry_control ((GCRYCTL_FIPS_REJECT_NON_FIPS, + (GCRY_FIPS_FLAG_REJECT_MD_MD5 ++ | GCRY_FIPS_FLAG_REJECT_PK_MD ++ | GCRY_FIPS_FLAG_REJECT_PK_GOST_SM2 + | GCRY_FIPS_FLAG_REJECT_COMPAT110))); + + check_md_o_w_r_c (1); +-- +2.49.0 + diff --git a/libgcrypt-fips-kdf-Implement-new-FIPS-service-indicator-for-gcry_kdf_derive.patch b/libgcrypt-fips-kdf-Implement-new-FIPS-service-indicator-for-gcry_kdf_derive.patch new file mode 100644 index 0000000..a1710b9 --- /dev/null +++ b/libgcrypt-fips-kdf-Implement-new-FIPS-service-indicator-for-gcry_kdf_derive.patch @@ -0,0 +1,265 @@ +From 5cfa1aee5b98baf0d66333344e0fa45b79cca28b Mon Sep 17 00:00:00 2001 +From: NIIBE Yutaka +Date: Thu, 5 Dec 2024 14:52:17 +0900 +Subject: [PATCH 3/5] fips,kdf: Implement new FIPS service indicator for + gcry_kdf_derive. +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* cipher/kdf.c (_gcry_kdf_derive): Don't reject by GPG_ERR_INV_VALUE +but continue the computation, clearing IS_COMPLIANT. After successful +computation, call fips_service_indicator_mark_success with +IS_COMPLIANT. +* src/visibility.c (gcry_kdf_derive): Call fips_service_indicator_init. +* tests/t-kdf.c (check_fips_gcry_kdf_derive): New. +(main): Call check_fips_gcry_kdf_derive. + +-- + +GnuPG-bug-id: 7338 +Co-authored-by: David Sugar +Suggested-by: Stephan Mueller +Signed-off-by: NIIBE Yutaka +Signed-off-by: Lucas Mülling +--- + cipher/kdf.c | 33 ++++++----- + src/visibility.c | 1 + + tests/t-kdf.c | 149 ++++++++++++++++++++++++++++++++++++++++++++++- + 3 files changed, 169 insertions(+), 14 deletions(-) + +diff --git a/cipher/kdf.c b/cipher/kdf.c +index b4c5f83a..52e6a9ba 100644 +--- a/cipher/kdf.c ++++ b/cipher/kdf.c +@@ -279,28 +279,35 @@ _gcry_kdf_derive (const void *passphrase, size_t passphraselen, + break; + + case GCRY_KDF_PBKDF2: +- if (!saltlen) ++ if (!saltlen || !iterations) + ec = GPG_ERR_INV_VALUE; + else + { +- /* FIPS requires minimum passphrase length, see FIPS 140-3 IG D.N */ +- if (fips_mode () && passphraselen < 8) +- return GPG_ERR_INV_VALUE; ++ int is_compliant = 1; ++ ++ if (fips_mode ()) ++ { ++ /* FIPS requires minimum passphrase length, see FIPS 140-3 IG D.N */ ++ if (passphraselen < 8) ++ is_compliant &= 0; + +- /* FIPS requires minimum salt length of 128 b (SP 800-132 sec. 5.1, p.6) */ +- if (fips_mode () && saltlen < 16) +- return GPG_ERR_INV_VALUE; ++ /* FIPS requires minimum salt length of 128 b (SP 800-132 sec. 5.1, p.6) */ ++ if (saltlen < 16) ++ is_compliant &= 0; + +- /* FIPS requires minimum iterations bound (SP 800-132 sec 5.2, p.6) */ +- if (fips_mode () && iterations < 1000) +- return GPG_ERR_INV_VALUE; ++ /* FIPS requires minimum iterations bound (SP 800-132 sec 5.2, p.6) */ ++ if (iterations < 1000) ++ is_compliant &= 0; + +- /* Check minimum key size */ +- if (fips_mode () && keysize < 14) +- return GPG_ERR_INV_VALUE; ++ /* Check minimum key size */ ++ if (keysize < 14) ++ is_compliant &= 0; ++ } + + ec = _gcry_kdf_pkdf2 (passphrase, passphraselen, subalgo, + salt, saltlen, iterations, keysize, keybuffer); ++ if (!ec) ++ fips_service_indicator_mark_success (is_compliant); + } + break; + +diff --git a/src/visibility.c b/src/visibility.c +index 006e8f80..8f76b854 100644 +--- a/src/visibility.c ++++ b/src/visibility.c +@@ -1400,6 +1400,7 @@ gcry_kdf_derive (const void *passphrase, size_t passphraselen, + { + if (!fips_is_operational ()) + return gpg_error (fips_not_operational ()); ++ fips_service_indicator_init (); + return gpg_error (_gcry_kdf_derive (passphrase, passphraselen, algo, hashalgo, + salt, saltlen, iterations, + keysize, keybuffer)); +diff --git a/tests/t-kdf.c b/tests/t-kdf.c +index 10f64a7c..4b92bd30 100644 +--- a/tests/t-kdf.c ++++ b/tests/t-kdf.c +@@ -1927,6 +1927,151 @@ check_fips_indicators (void) + } + + ++static void ++check_fips_gcry_kdf_derive (void) ++{ ++ static struct { ++ const char *p; /* Passphrase. */ ++ size_t plen; /* Length of P. */ ++ int algo; ++ int subalgo; ++ const char *salt; ++ size_t saltlen; ++ unsigned long iterations; ++ int dklen; /* Requested key length. */ ++ const char *dk; /* Derived key. */ ++ int expect_failure; ++ } tv[] = { ++ { ++ "passwordPASSWORDpassword", 24, ++ GCRY_KDF_PBKDF2, GCRY_MD_SHA1, ++ "saltSALTsaltSALTsaltSALTsaltSALTsalt", 36, ++ 4096, ++ 25, ++ "\x3d\x2e\xec\x4f\xe4\x1c\x84\x9b\x80\xc8" ++ "\xd8\x36\x62\xc0\xe4\x4a\x8b\x29\x1a\x96" ++ "\x4c\xf2\xf0\x70\x38", ++ 0 ++ }, ++ { ++ "pleaseletmein", 13, ++ GCRY_KDF_SCRYPT, 16384, ++ "SodiumChloride", 14, ++ 1, ++ 64, ++ "\x70\x23\xbd\xcb\x3a\xfd\x73\x48\x46\x1c\x06\xcd\x81\xfd\x38\xeb" ++ "\xfd\xa8\xfb\xba\x90\x4f\x8e\x3e\xa9\xb5\x43\xf6\x54\x5d\xa1\xf2" ++ "\xd5\x43\x29\x55\x61\x3f\x0f\xcf\x62\xd4\x97\x05\x24\x2a\x9a\xf9" ++ "\xe6\x1e\x85\xdc\x0d\x65\x1e\x40\xdf\xcf\x01\x7b\x45\x57\x58\x87", ++ 1 /* not-compliant because unallowed algo */ ++ }, ++ { ++ "passwor", 7, ++ GCRY_KDF_PBKDF2, GCRY_MD_SHA1, ++ "saltSALTsaltSALTsaltSALTsaltSALTsalt", 36, ++ 4096, ++ 25, ++ "\xf4\x93\xee\x2b\xbf\x44\x0b\x9e\x64\x53" ++ "\xc2\xb3\x87\xdc\x73\xf8\xfd\xe6\x97\xda" ++ "\xb8\x24\xa0\x26\x50", ++ 1 /* not-compliant because passphrase len is too small */ ++ }, ++ { ++ "passwordPASSWORDpassword", 24, ++ GCRY_KDF_PBKDF2, GCRY_MD_SHA1, ++ "saltSALTsaltSAL", 15, ++ 4096, ++ 25, ++ "\x14\x05\xa4\x2a\xf4\xa8\x12\x14\x7b\x65" ++ "\x8f\xaa\xf0\x7f\x25\xe5\x0f\x0b\x2b\xb7" ++ "\xcf\x8d\x29\x23\x4b", ++ 1 /* not-compliant because salt len is too small */ ++ }, ++ { ++ "passwordPASSWORDpassword", 24, ++ GCRY_KDF_PBKDF2, GCRY_MD_SHA1, ++ "saltSALTsaltSALTsaltSALTsaltSALTsalt", 36, ++ 999, ++ 25, ++ "\xac\xf8\xb4\x67\x41\xc7\xf3\xd1\xa0\xc0" ++ "\x08\xbe\x9b\x23\x96\x78\xbd\x93\xda\x4a" ++ "\x30\xd4\xfb\xf0\x33", ++ 1 /* not-compliant because too few iterations */ ++ }, ++ { ++ "passwordPASSWORDpassword", 24, ++ GCRY_KDF_PBKDF2, GCRY_MD_SHA1, ++ "saltSALTsaltSALTsaltSALTsaltSALTsalt", 36, ++ 4096, ++ 13, ++ "\x3d\x2e\xec\x4f\xe4\x1c\x84\x9b\x80\xc8" ++ "\xd8\x36\x62", ++ 1 /* not-compliant because key size too small */ ++ }, ++ }; ++ ++ int tvidx; ++ gpg_error_t err; ++ unsigned char outbuf[100]; ++ int i; ++ ++ for (tvidx=0; tvidx < DIM(tv); tvidx++) ++ { ++ if (verbose) ++ fprintf (stderr, "checking gcry_kdf_derive test vector %d algo %d for FIPS\n", ++ tvidx, tv[tvidx].algo); ++ assert (tv[tvidx].dklen <= sizeof outbuf); ++ err = gcry_kdf_derive (tv[tvidx].p, tv[tvidx].plen, ++ tv[tvidx].algo, tv[tvidx].subalgo, ++ tv[tvidx].salt, tv[tvidx].saltlen, ++ tv[tvidx].iterations, tv[tvidx].dklen, outbuf); ++ ++ if (err) ++ { ++ fail ("gcry_kdf_derive test %d unexpectedly returned an error in FIPS mode: %s\n", ++ tvidx, gpg_strerror (err)); ++ } ++ else ++ { ++ gpg_err_code_t ec; ++ ++ ec = gcry_get_fips_service_indicator (); ++ if (ec == GPG_ERR_INV_OP) ++ { ++ /* libgcrypt is old, no support of the FIPS service indicator. */ ++ fail ("gcry_kdf_derive test %d unexpectedly failed to check the FIPS service indicator.\n", ++ tvidx); ++ continue; ++ } ++ ++ if (!tv[tvidx].expect_failure && ec) ++ { ++ /* Success with the FIPS service indicator == 0 expected, but != 0. */ ++ fail ("gcry_kdf_derive test %d unexpectedly set the indicator in FIPS mode.\n", ++ tvidx); ++ continue; ++ } ++ else if (tv[tvidx].expect_failure && !ec) ++ { ++ /* Success with the FIPS service indicator != 0 expected, but == 0. */ ++ fail ("gcry_kdf_derive test %d unexpectedly cleared the indicator in FIPS mode.\n", ++ tvidx); ++ continue; ++ } ++ ++ if (memcmp (outbuf, tv[tvidx].dk, tv[tvidx].dklen)) ++ { ++ fail ("gcry_kdf_derive test %d failed: mismatch\n", tvidx); ++ fputs ("got:", stderr); ++ for (i=0; i < tv[tvidx].dklen; i++) ++ fprintf (stderr, " %02x", outbuf[i]); ++ putc ('\n', stderr); ++ } ++ } ++ } ++} ++ ++ + int + main (int argc, char **argv) + { +@@ -2008,7 +2153,9 @@ main (int argc, char **argv) + check_onestep_kdf (); + check_hkdf (); + if (in_fips_mode) +- check_fips_indicators(); ++ check_fips_indicators (); ++ if (in_fips_mode) ++ check_fips_gcry_kdf_derive (); + } + + return error_count ? 1 : 0; +-- +2.49.0 + diff --git a/libgcrypt-fips-mac-Implement-new-FIPS-service-indicator-for-gcry_mac_open.patch b/libgcrypt-fips-mac-Implement-new-FIPS-service-indicator-for-gcry_mac_open.patch new file mode 100644 index 0000000..7843a39 --- /dev/null +++ b/libgcrypt-fips-mac-Implement-new-FIPS-service-indicator-for-gcry_mac_open.patch @@ -0,0 +1,115 @@ +From fcb0c7004b0b6b318fdcced2bf61d9acb1e28cfc Mon Sep 17 00:00:00 2001 +From: NIIBE Yutaka +Date: Fri, 13 Dec 2024 14:25:02 +0900 +Subject: [PATCH 04/19] fips,mac: Implement new FIPS service indicator for + gcry_mac_open. +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* src/gcrypt.h.in (GCRY_MAC_FLAG_REJECT_NON_FIPS): New. +* cipher/mac.c (mac_open): Have FLAGS, instead of SECURE. Reject when +GCRY_MAC_FLAG_REJECT_NON_FIPS, otherwise, mark non compliant. +(_gcry_mac_open): Follow the change. +* src/visibility.c (gcry_mac_open): Add initialization for FIPS +service indicator. +(gcry_mac_setkey): Likewise. Don't reject but mark. + +-- + +GnuPG-bug-id: 7338 +Signed-off-by: NIIBE Yutaka +Signed-off-by: Lucas Mülling +--- + cipher/mac.c | 15 +++++++++++---- + src/gcrypt.h.in | 3 ++- + src/visibility.c | 5 +++-- + 3 files changed, 16 insertions(+), 7 deletions(-) + +diff --git a/cipher/mac.c b/cipher/mac.c +index 128ac53d..0df48fd7 100644 +--- a/cipher/mac.c ++++ b/cipher/mac.c +@@ -513,11 +513,13 @@ check_mac_algo (int algorithm) + * Open a message digest handle for use with algorithm ALGO. + */ + static gcry_err_code_t +-mac_open (gcry_mac_hd_t * hd, int algo, int secure, gcry_ctx_t ctx) ++mac_open (gcry_mac_hd_t * hd, int algo, unsigned int flags, gcry_ctx_t ctx) + { + const gcry_mac_spec_t *spec; + gcry_err_code_t err; + gcry_mac_hd_t h; ++ int secure = !!(flags & GCRY_MAC_FLAG_SECURE); ++ int reject_non_fips = !!(flags & GCRY_MAC_FLAG_REJECT_NON_FIPS); + + spec = spec_from_algo (algo); + if (!spec) +@@ -525,7 +527,12 @@ mac_open (gcry_mac_hd_t * hd, int algo, int secure, gcry_ctx_t ctx) + else if (spec->flags.disabled) + return GPG_ERR_MAC_ALGO; + else if (!spec->flags.fips && fips_mode ()) +- return GPG_ERR_MAC_ALGO; ++ { ++ if (reject_non_fips) ++ return GPG_ERR_MAC_ALGO; ++ else ++ fips_service_indicator_mark_non_compliant (); ++ } + else if (!spec->ops) + return GPG_ERR_MAC_ALGO; + else if (!spec->ops->open || !spec->ops->write || !spec->ops->setkey || +@@ -643,10 +650,10 @@ _gcry_mac_open (gcry_mac_hd_t * h, int algo, unsigned int flags, + gcry_err_code_t rc; + gcry_mac_hd_t hd = NULL; + +- if ((flags & ~GCRY_MAC_FLAG_SECURE)) ++ if ((flags & ~(GCRY_MAC_FLAG_SECURE | GCRY_MAC_FLAG_REJECT_NON_FIPS))) + rc = GPG_ERR_INV_ARG; + else +- rc = mac_open (&hd, algo, !!(flags & GCRY_MAC_FLAG_SECURE), ctx); ++ rc = mac_open (&hd, algo, flags, ctx); + + *h = rc ? NULL : hd; + return rc; +diff --git a/src/gcrypt.h.in b/src/gcrypt.h.in +index 96bf88f6..2a378639 100644 +--- a/src/gcrypt.h.in ++++ b/src/gcrypt.h.in +@@ -1560,7 +1560,8 @@ enum gcry_mac_algos + /* Flags used with the open function. */ + enum gcry_mac_flags + { +- GCRY_MAC_FLAG_SECURE = 1 /* Allocate all buffers in "secure" memory. */ ++ GCRY_MAC_FLAG_SECURE = 1, /* Allocate all buffers in "secure" memory. */ ++ GCRY_MAC_FLAG_REJECT_NON_FIPS = 2 /* Reject non-FIPS-compliant algo. */ + }; + + /* Create a MAC handle for algorithm ALGO. FLAGS may be given as an bitwise OR +diff --git a/src/visibility.c b/src/visibility.c +index 44b05eb2..7699f14f 100644 +--- a/src/visibility.c ++++ b/src/visibility.c +@@ -946,7 +946,7 @@ gcry_mac_open (gcry_mac_hd_t *handle, int algo, unsigned int flags, + *handle = NULL; + return gpg_error (fips_not_operational ()); + } +- ++ fips_service_indicator_init (); + return gpg_error (_gcry_mac_open (handle, algo, flags, ctx)); + } + +@@ -962,8 +962,9 @@ gcry_mac_setkey (gcry_mac_hd_t hd, const void *key, size_t keylen) + if (!fips_is_operational ()) + return gpg_error (fips_not_operational ()); + ++ fips_service_indicator_init (); + if (fips_mode () && keylen < 14) +- return GPG_ERR_INV_VALUE; ++ fips_service_indicator_mark_non_compliant (); + + return gpg_error (_gcry_mac_setkey (hd, key, keylen)); + } +-- +2.49.0 + diff --git a/libgcrypt-fips-md-Implement-new-FIPS-service-indicator-for-gcry_md_hash_.patch b/libgcrypt-fips-md-Implement-new-FIPS-service-indicator-for-gcry_md_hash_.patch new file mode 100644 index 0000000..71f1671 --- /dev/null +++ b/libgcrypt-fips-md-Implement-new-FIPS-service-indicator-for-gcry_md_hash_.patch @@ -0,0 +1,188 @@ +From 3478caac62c712547f7c0e07f4cf9602bc317997 Mon Sep 17 00:00:00 2001 +From: NIIBE Yutaka +Date: Fri, 6 Dec 2024 14:33:58 +0900 +Subject: [PATCH 4/5] fips,md: Implement new FIPS service indicator for + gcry_md_hash_*. +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* cipher/md.c (md_enable): Add an NO_REJECT argument. +(md_open): Check flags against GCRY_MD_FLAG_FIPS_NO_REJECTION to +call md_enable. +(_gcry_md_enable): Follow the change. +(_gcry_md_hash_buffer): Don't reject but keep the computation. +Call fips_service_indicator_mark_success. +(_gcry_md_hash_buffers_extract): Likewise. +* src/gcrypt.h.in (GCRY_MD_FLAG_FIPS_NO_REJECTION): New. +* src/visibility.c (gcry_md_hash_buffer, gcry_md_hash_buffers): Call +fips_service_indicator_init. +(gcry_md_hash_buffers_ext): Likewise. + +-- + +GnuPG-bug-id: 7338 +Signed-off-by: NIIBE Yutaka +Signed-off-by: Lucas Mülling +--- + cipher/md.c | 32 +++++++++++++++++++++++--------- + src/gcrypt.h.in | 1 + + src/visibility.c | 3 +++ + 3 files changed, 27 insertions(+), 9 deletions(-) + +diff --git a/cipher/md.c b/cipher/md.c +index 1991c331..c2bd18c6 100644 +--- a/cipher/md.c ++++ b/cipher/md.c +@@ -285,7 +285,7 @@ struct gcry_md_context + #define CTX_MAGIC_NORMAL 0x11071961 + #define CTX_MAGIC_SECURE 0x16917011 + +-static gcry_err_code_t md_enable (gcry_md_hd_t hd, int algo); ++static gcry_err_code_t md_enable (gcry_md_hd_t hd, int algo, int no_reject); + static void md_close (gcry_md_hd_t a); + static void md_write (gcry_md_hd_t a, const void *inbuf, size_t inlen); + static byte *md_read( gcry_md_hd_t a, int algo ); +@@ -517,7 +517,8 @@ md_open (gcry_md_hd_t *h, int algo, unsigned int flags) + + if (algo) + { +- err = md_enable (hd, algo); ++ err = md_enable (hd, algo, ++ !!(flags & GCRY_MD_FLAG_FIPS_NO_REJECTION)); + if (err) + md_close (hd); + } +@@ -554,7 +555,7 @@ _gcry_md_open (gcry_md_hd_t *h, int algo, unsigned int flags) + + + static gcry_err_code_t +-md_enable (gcry_md_hd_t hd, int algorithm) ++md_enable (gcry_md_hd_t hd, int algorithm, int no_reject) + { + struct gcry_md_context *h = hd->ctx; + const gcry_md_spec_t *spec; +@@ -576,7 +577,7 @@ md_enable (gcry_md_hd_t hd, int algorithm) + err = GPG_ERR_DIGEST_ALGO; + + /* Any non-FIPS algorithm should go this way */ +- if (!err && !spec->flags.fips && fips_mode ()) ++ if (!err && !no_reject && !spec->flags.fips && fips_mode ()) + err = GPG_ERR_DIGEST_ALGO; + + if (!err && h->flags.hmac && spec->read == NULL) +@@ -619,7 +620,7 @@ md_enable (gcry_md_hd_t hd, int algorithm) + gcry_err_code_t + _gcry_md_enable (gcry_md_hd_t hd, int algorithm) + { +- return md_enable (hd, algorithm); ++ return md_enable (hd, algorithm, 0); + } + + +@@ -1260,7 +1261,7 @@ _gcry_md_hash_buffer (int algo, void *digest, + iov.off = 0; + iov.len = length; + +- if (spec->flags.disabled || (!spec->flags.fips && fips_mode ())) ++ if (spec->flags.disabled) + log_bug ("gcry_md_hash_buffer failed for algo %d: %s", + algo, gpg_strerror (gcry_error (GPG_ERR_DIGEST_ALGO))); + +@@ -1273,7 +1274,7 @@ _gcry_md_hash_buffer (int algo, void *digest, + gcry_md_hd_t h; + gpg_err_code_t err; + +- err = md_open (&h, algo, 0); ++ err = md_open (&h, algo, GCRY_MD_FLAG_FIPS_NO_REJECTION); + if (err) + log_bug ("gcry_md_open failed for algo %d: %s", + algo, gpg_strerror (gcry_error(err))); +@@ -1282,6 +1283,12 @@ _gcry_md_hash_buffer (int algo, void *digest, + memcpy (digest, md_read (h, algo), md_digest_length (algo)); + md_close (h); + } ++ ++ if (fips_mode ()) ++ { ++ int is_compliant = spec->flags.fips; ++ fips_service_indicator_mark_success (is_compliant); ++ } + } + + +@@ -1336,7 +1343,7 @@ _gcry_md_hash_buffers_extract (int algo, unsigned int flags, void *digest, + + if (!hmac && spec->hash_buffers) + { +- if (spec->flags.disabled || (!spec->flags.fips && fips_mode ())) ++ if (spec->flags.disabled) + return GPG_ERR_DIGEST_ALGO; + + spec->hash_buffers (digest, digestlen, iov, iovcnt); +@@ -1348,7 +1355,8 @@ _gcry_md_hash_buffers_extract (int algo, unsigned int flags, void *digest, + gcry_md_hd_t h; + gpg_err_code_t rc; + +- rc = md_open (&h, algo, (hmac? GCRY_MD_FLAG_HMAC:0)); ++ rc = md_open (&h, algo, ((hmac? GCRY_MD_FLAG_HMAC:0) ++ | GCRY_MD_FLAG_FIPS_NO_REJECTION)); + if (rc) + return rc; + +@@ -1374,6 +1382,12 @@ _gcry_md_hash_buffers_extract (int algo, unsigned int flags, void *digest, + md_close (h); + } + ++ if (fips_mode ()) ++ { ++ int is_compliant = spec->flags.fips; ++ fips_service_indicator_mark_success (is_compliant); ++ } ++ + return 0; + } + +diff --git a/src/gcrypt.h.in b/src/gcrypt.h.in +index 2f61a0bc..18d04a38 100644 +--- a/src/gcrypt.h.in ++++ b/src/gcrypt.h.in +@@ -1318,6 +1318,7 @@ enum gcry_md_flags + { + GCRY_MD_FLAG_SECURE = 1, /* Allocate all buffers in "secure" memory. */ + GCRY_MD_FLAG_HMAC = 2, /* Make an HMAC out of this algorithm. */ ++ GCRY_MD_FLAG_FIPS_NO_REJECTION = 4, /* Don't reject for FIPS. */ + GCRY_MD_FLAG_BUGEMU1 = 0x0100 + }; + +diff --git a/src/visibility.c b/src/visibility.c +index 8f76b854..be5deda1 100644 +--- a/src/visibility.c ++++ b/src/visibility.c +@@ -1281,6 +1281,7 @@ gcry_md_hash_buffer (int algo, void *digest, + (void)fips_not_operational (); + fips_signal_error ("called in non-operational state"); + } ++ fips_service_indicator_init (); + _gcry_md_hash_buffer (algo, digest, buffer, length); + } + +@@ -1293,6 +1294,7 @@ gcry_md_hash_buffers (int algo, unsigned int flags, void *digest, + (void)fips_not_operational (); + fips_signal_error ("called in non-operational state"); + } ++ fips_service_indicator_init (); + return gpg_error (_gcry_md_hash_buffers (algo, flags, digest, iov, iovcnt)); + } + +@@ -1306,6 +1308,7 @@ gcry_md_hash_buffers_ext (int algo, unsigned int flags, void *digest, + (void)fips_not_operational (); + fips_signal_error ("called in non-operational state"); + } ++ fips_service_indicator_init (); + return gpg_error (_gcry_md_hash_buffers_extract (algo, flags, digest, + digestlen, iov, iovcnt)); + } +-- +2.49.0 + diff --git a/libgcrypt-fips-md-Implement-new-FIPS-service-indicator-for-gcry_md_open-API.patch b/libgcrypt-fips-md-Implement-new-FIPS-service-indicator-for-gcry_md_open-API.patch new file mode 100644 index 0000000..0f580b1 --- /dev/null +++ b/libgcrypt-fips-md-Implement-new-FIPS-service-indicator-for-gcry_md_open-API.patch @@ -0,0 +1,298 @@ +From 9757e280794f537efc82c4eaa9a2944ece6a068a Mon Sep 17 00:00:00 2001 +From: NIIBE Yutaka +Date: Thu, 12 Dec 2024 11:40:31 +0900 +Subject: [PATCH] fips,md: Implement new FIPS service indicator for + gcry_md_open API. +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* src/gcrypt.h.in (GCRY_MD_FLAG_FIPS_NO_REJECTION): Remove. +(GCRY_MD_FLAG_REJECT_NON_FIPS): New. +* cipher/md.c (struct gcry_md_context): Add reject_non_fips. +(md_enable): Remove NO_REJECT argument. +(md_open): Change the FLAGS handling. +(_gcry_md_open): Add checking of FIPS compliance against ALGO. +(_gcry_md_enable): Likewise. +(_gcry_md_hash_buffer): Follow the change of md_open change +which now defaults to no rejection. +(_gcry_md_hash_buffers_extract): Likewise. +* src/visibility.c (gcry_md_open): Add fips_service_indicator_init. +(gcry_md_enable): Likewise. +(gcry_md_setkey): Don't reject but mark non-compliance. +* tests/t-kdf.c (check_fips_gcry_kdf_derive): Add a test with +non-compliant hash function. +* cipher/mac-hmac.c (_gcry_mac_type_spec_hmac_md5): It's not +compliant. +* cipher/md5.c (gcry_md_oid_spec_t oid_spec_md5): It's not compliant. +* tests/t-digest.c (check_hash_buffer, check_hash_buffers): MD5 +tests enabled. + +-- + +See 6376 for the MD5 compliance change in the past. This commit +reverts the change in: + dc4a60e2d70bc52ba2955f8e676341d675ab89a0 + +GnuPG-bug-id: 7338 +Signed-off-by: NIIBE Yutaka +Signed-off-by: Lucas Mülling +--- + cipher/mac-hmac.c | 2 +- + cipher/md.c | 57 +++++++++++++++++++++++++++++++++++++++-------- + cipher/md5.c | 2 +- + src/gcrypt.h.in | 2 +- + src/visibility.c | 6 +++-- + tests/t-digest.c | 6 ++--- + tests/t-kdf.c | 12 ++++++++++ + 7 files changed, 69 insertions(+), 18 deletions(-) + +Index: libgcrypt-1.11.0/cipher/mac-hmac.c +=================================================================== +--- libgcrypt-1.11.0.orig/cipher/mac-hmac.c ++++ libgcrypt-1.11.0/cipher/mac-hmac.c +@@ -1413,7 +1413,7 @@ const gcry_mac_spec_t _gcry_mac_type_spe + #endif + #if USE_MD5 + const gcry_mac_spec_t _gcry_mac_type_spec_hmac_md5 = { +- GCRY_MAC_HMAC_MD5, {0, 1}, "HMAC_MD5", ++ GCRY_MAC_HMAC_MD5, {0, 0}, "HMAC_MD5", + &hmac_ops + }; + #endif +Index: libgcrypt-1.11.0/cipher/md.c +=================================================================== +--- libgcrypt-1.11.0.orig/cipher/md.c ++++ libgcrypt-1.11.0/cipher/md.c +@@ -275,6 +275,7 @@ struct gcry_md_context + unsigned int finalized:1; + unsigned int bugemu1:1; + unsigned int hmac:1; ++ unsigned int reject_non_fips:1; + } flags; + size_t actual_handle_size; /* Allocated size of this handle. */ + FILE *debug; +@@ -285,7 +286,7 @@ struct gcry_md_context + #define CTX_MAGIC_NORMAL 0x11071961 + #define CTX_MAGIC_SECURE 0x16917011 + +-static gcry_err_code_t md_enable (gcry_md_hd_t hd, int algo, int no_reject); ++static gcry_err_code_t md_enable (gcry_md_hd_t hd, int algo); + static void md_close (gcry_md_hd_t a); + static void md_write (gcry_md_hd_t a, const void *inbuf, size_t inlen); + static byte *md_read( gcry_md_hd_t a, int algo ); +@@ -508,6 +509,7 @@ md_open (gcry_md_hd_t *h, int algo, unsi + ctx->flags.secure = secure; + ctx->flags.hmac = hmac; + ctx->flags.bugemu1 = !!(flags & GCRY_MD_FLAG_BUGEMU1); ++ ctx->flags.reject_non_fips = !!(flags & GCRY_MD_FLAG_REJECT_NON_FIPS); + } + + if (! err) +@@ -517,8 +519,7 @@ md_open (gcry_md_hd_t *h, int algo, unsi + + if (algo) + { +- err = md_enable (hd, algo, +- !!(flags & GCRY_MD_FLAG_FIPS_NO_REJECTION)); ++ err = md_enable (hd, algo); + if (err) + md_close (hd); + } +@@ -543,24 +544,44 @@ _gcry_md_open (gcry_md_hd_t *h, int algo + + if ((flags & ~(GCRY_MD_FLAG_SECURE + | GCRY_MD_FLAG_HMAC ++ | GCRY_MD_FLAG_REJECT_NON_FIPS + | GCRY_MD_FLAG_BUGEMU1))) + rc = GPG_ERR_INV_ARG; + else + rc = md_open (&hd, algo, flags); + + *h = rc? NULL : hd; ++ ++ if (!rc && fips_mode ()) ++ { ++ GcryDigestEntry *entry = hd->ctx->list; ++ /* No ENTRY means that ALGO==0. ++ It's not yet known, if it's FIPS compliant or not. */ ++ int is_compliant_algo = 1; ++ ++ if (entry) ++ { ++ const gcry_md_spec_t *spec = entry->spec; ++ is_compliant_algo = spec->flags.fips; ++ } ++ ++ if (!is_compliant_algo) ++ fips_service_indicator_mark_non_compliant (); ++ } ++ + return rc; + } + + + + static gcry_err_code_t +-md_enable (gcry_md_hd_t hd, int algorithm, int no_reject) ++md_enable (gcry_md_hd_t hd, int algorithm) + { + struct gcry_md_context *h = hd->ctx; + const gcry_md_spec_t *spec; + GcryDigestEntry *entry; + gcry_err_code_t err = 0; ++ int reject_non_fips = h->flags.reject_non_fips; + + for (entry = h->list; entry; entry = entry->next) + if (entry->spec->algo == algorithm) +@@ -577,7 +598,7 @@ md_enable (gcry_md_hd_t hd, int algorith + err = GPG_ERR_DIGEST_ALGO; + + /* Any non-FIPS algorithm should go this way */ +- if (!err && !no_reject && !spec->flags.fips && fips_mode ()) ++ if (!err && reject_non_fips && !spec->flags.fips && fips_mode ()) + err = GPG_ERR_DIGEST_ALGO; + + if (!err && h->flags.hmac && spec->read == NULL) +@@ -620,7 +641,26 @@ md_enable (gcry_md_hd_t hd, int algorith + gcry_err_code_t + _gcry_md_enable (gcry_md_hd_t hd, int algorithm) + { +- return md_enable (hd, algorithm, 0); ++ gcry_err_code_t rc; ++ ++ rc = md_enable (hd, algorithm); ++ if (!rc && fips_mode ()) ++ { ++ GcryDigestEntry *entry = hd->ctx->list; ++ /* No ENTRY means, something goes wrong. */ ++ int is_compliant_algo = 0; ++ ++ if (entry) ++ { ++ const gcry_md_spec_t *spec = entry->spec; ++ is_compliant_algo = spec->flags.fips; ++ } ++ ++ if (!is_compliant_algo) ++ fips_service_indicator_mark_non_compliant (); ++ } ++ ++ return rc; + } + + +@@ -1274,7 +1314,7 @@ _gcry_md_hash_buffer (int algo, void *di + gcry_md_hd_t h; + gpg_err_code_t err; + +- err = md_open (&h, algo, GCRY_MD_FLAG_FIPS_NO_REJECTION); ++ err = md_open (&h, algo, 0); + if (err) + log_bug ("gcry_md_open failed for algo %d: %s", + algo, gpg_strerror (gcry_error(err))); +@@ -1355,8 +1395,7 @@ _gcry_md_hash_buffers_extract (int algo, + gcry_md_hd_t h; + gpg_err_code_t rc; + +- rc = md_open (&h, algo, ((hmac? GCRY_MD_FLAG_HMAC:0) +- | GCRY_MD_FLAG_FIPS_NO_REJECTION)); ++ rc = md_open (&h, algo, (hmac? GCRY_MD_FLAG_HMAC:0)); + if (rc) + return rc; + +Index: libgcrypt-1.11.0/cipher/md5.c +=================================================================== +--- libgcrypt-1.11.0.orig/cipher/md5.c ++++ libgcrypt-1.11.0/cipher/md5.c +@@ -314,7 +314,7 @@ static const gcry_md_oid_spec_t oid_spec + + const gcry_md_spec_t _gcry_digest_spec_md5 = + { +- GCRY_MD_MD5, {0, 1}, ++ GCRY_MD_MD5, {0, 0}, + "MD5", asn, DIM (asn), oid_spec_md5, 16, + md5_init, _gcry_md_block_write, md5_final, md5_read, NULL, + NULL, +Index: libgcrypt-1.11.0/src/gcrypt.h.in +=================================================================== +--- libgcrypt-1.11.0.orig/src/gcrypt.h.in ++++ libgcrypt-1.11.0/src/gcrypt.h.in +@@ -1320,7 +1320,7 @@ enum gcry_md_flags + { + GCRY_MD_FLAG_SECURE = 1, /* Allocate all buffers in "secure" memory. */ + GCRY_MD_FLAG_HMAC = 2, /* Make an HMAC out of this algorithm. */ +- GCRY_MD_FLAG_FIPS_NO_REJECTION = 4, /* Don't reject for FIPS. */ ++ GCRY_MD_FLAG_REJECT_NON_FIPS = 4, /* Reject non-FIPS-compliant algo. */ + GCRY_MD_FLAG_BUGEMU1 = 0x0100 + }; + +Index: libgcrypt-1.11.0/src/visibility.c +=================================================================== +--- libgcrypt-1.11.0.orig/src/visibility.c ++++ libgcrypt-1.11.0/src/visibility.c +@@ -1204,7 +1204,7 @@ gcry_md_open (gcry_md_hd_t *h, int algo, + *h = NULL; + return gpg_error (fips_not_operational ()); + } +- ++ fips_service_indicator_init (); + return gpg_error (_gcry_md_open (h, algo, flags)); + } + +@@ -1219,6 +1219,7 @@ gcry_md_enable (gcry_md_hd_t hd, int alg + { + if (!fips_is_operational ()) + return gpg_error (fips_not_operational ()); ++ fips_service_indicator_init (); + return gpg_error (_gcry_md_enable (hd, algo)); + } + +@@ -1382,8 +1383,9 @@ gcry_md_setkey (gcry_md_hd_t hd, const v + if (!fips_is_operational ()) + return gpg_error (fips_not_operational ()); + ++ fips_service_indicator_init (); + if (fips_mode () && keylen < 14) +- return GPG_ERR_INV_VALUE; ++ fips_service_indicator_mark_non_compliant (); + + return gpg_error (_gcry_md_setkey (hd, key, keylen)); + } +Index: libgcrypt-1.11.0/tests/t-digest.c +=================================================================== +--- libgcrypt-1.11.0.orig/tests/t-digest.c ++++ libgcrypt-1.11.0/tests/t-digest.c +@@ -48,8 +48,7 @@ check_digests (void) + const char *expect; + int expect_failure; + } tv[] = { +-#undef ENABLE_THIS_AFTER_T6376_CHANGE_REVISED +-#ifdef ENABLE_THIS_AFTER_T6376_CHANGE_REVISED ++#if USE_MD5 + { GCRY_MD_MD5, "abc", 3, + "\x90\x01\x50\x98\x3C\xD2\x4F\xB0\xD6\x96\x3F\x7D\x28\xE1\x7F\x72", 1 }, + #endif +Index: libgcrypt-1.11.0/tests/t-kdf.c +=================================================================== +--- libgcrypt-1.11.0.orig/tests/t-kdf.c ++++ libgcrypt-1.11.0/tests/t-kdf.c +@@ -2008,6 +2008,18 @@ check_fips_gcry_kdf_derive (void) + "\xd8\x36\x62", + 1 /* not-compliant because key size too small */ + }, ++ { ++ "passwordPASSWORDpassword", 24, ++ GCRY_KDF_PBKDF2, GCRY_MD_BLAKE2B_512, ++ "saltSALTsaltSALTsaltSALTsaltSALTsalt", 36, ++ 4096, ++ 60, ++ "\xa4\x6b\x53\x35\xdb\xdd\xa3\xd2\x5d\x19\xbb\x11\xfe\xdd\xd9\x9e" ++ "\x45\x2a\x7c\x34\x47\x41\x98\xca\x31\x74\xb6\x34\x22\xac\x83\xb0" ++ "\x38\x6e\xf5\x93\x0f\xf5\x16\x46\x0b\x97\xdc\x6c\x27\x5b\xe7\x25" ++ "\xc2\xcb\xec\x50\x02\xc6\x52\x8b\x34\x68\x53\x65", ++ 1 /* not-compliant because subalgo is not the one of approved */ ++ } + }; + + int tvidx; diff --git a/libgcrypt-fips-md-gcry_md_copy-should-care-about-FIPS-service-indicator.patch b/libgcrypt-fips-md-gcry_md_copy-should-care-about-FIPS-service-indicator.patch new file mode 100644 index 0000000..5edccac --- /dev/null +++ b/libgcrypt-fips-md-gcry_md_copy-should-care-about-FIPS-service-indicator.patch @@ -0,0 +1,85 @@ +From 60db2a175d120aba6818de49638b36006878abf7 Mon Sep 17 00:00:00 2001 +From: NIIBE Yutaka +Date: Wed, 18 Dec 2024 14:14:37 +0900 +Subject: [PATCH 10/19] fips,md: gcry_md_copy should care about FIPS service + indicator. +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* cipher/md.c (md_copy): In a case of non-compliant, mark with +fips_service_indicator_mark_non_compliant. +* src/visibility.c (gcry_md_copy): Initialize the indicator. + +-- + +GnuPG-bug-id: 7338 +Signed-off-by: NIIBE Yutaka +Signed-off-by: Lucas Mülling +--- + cipher/md.c | 11 +++++++++++ + src/visibility.c | 1 + + 2 files changed, 12 insertions(+) + +diff --git a/cipher/md.c b/cipher/md.c +index 666e1dfa..08a564ad 100644 +--- a/cipher/md.c ++++ b/cipher/md.c +@@ -673,6 +673,7 @@ md_copy (gcry_md_hd_t ahd, gcry_md_hd_t *b_hd) + GcryDigestEntry *ar, *br; + gcry_md_hd_t bhd; + size_t n; ++ int is_compliant_algo = 1; + + if (ahd->bufpos) + md_write (ahd, NULL, 0); +@@ -699,10 +700,15 @@ md_copy (gcry_md_hd_t ahd, gcry_md_hd_t *b_hd) + b->list = NULL; + b->debug = NULL; + ++ if (!a->list) ++ is_compliant_algo = 0; ++ + /* Copy the complete list of algorithms. The copied list is + reversed, but that doesn't matter. */ + for (ar = a->list; ar; ar = ar->next) + { ++ const gcry_md_spec_t *spec = ar->spec; ++ + if (a->flags.secure) + br = xtrymalloc_secure (ar->actual_struct_size); + else +@@ -714,6 +720,8 @@ md_copy (gcry_md_hd_t ahd, gcry_md_hd_t *b_hd) + goto leave; + } + ++ is_compliant_algo &= spec->flags.fips; ++ + memcpy (br, ar, ar->actual_struct_size); + br->next = b->list; + b->list = br; +@@ -724,6 +732,9 @@ md_copy (gcry_md_hd_t ahd, gcry_md_hd_t *b_hd) + + *b_hd = bhd; + ++ if (!is_compliant_algo) ++ fips_service_indicator_mark_non_compliant (); ++ + leave: + return err; + } +diff --git a/src/visibility.c b/src/visibility.c +index d219f1a6..c9d07f0b 100644 +--- a/src/visibility.c ++++ b/src/visibility.c +@@ -1232,6 +1232,7 @@ gcry_md_copy (gcry_md_hd_t *bhd, gcry_md_hd_t ahd) + *bhd = NULL; + return gpg_error (fips_not_operational ()); + } ++ fips_service_indicator_init (); + return gpg_error (_gcry_md_copy (bhd, ahd)); + } + +-- +2.49.0 + diff --git a/libgcrypt-fips-tests-Add-t-digest.patch b/libgcrypt-fips-tests-Add-t-digest.patch new file mode 100644 index 0000000..fc5e8e8 --- /dev/null +++ b/libgcrypt-fips-tests-Add-t-digest.patch @@ -0,0 +1,243 @@ +From 7faf542f157330f3b247fa2542182ac805f06737 Mon Sep 17 00:00:00 2001 +From: NIIBE Yutaka +Date: Mon, 9 Dec 2024 14:05:59 +0900 +Subject: [PATCH 5/5] fips,tests: Add t-digest. +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* tests/Makefile.am (tests_bin): Add t-digest. +* tests/t-digest.c: New. + +-- + +GnuPG-bug-id: 7338 +Signed-off-by: NIIBE Yutaka +Signed-off-by: Lucas Mülling +--- + tests/Makefile.am | 2 +- + tests/t-digest.c | 199 ++++++++++++++++++++++++++++++++++++++++++++++ + 2 files changed, 200 insertions(+), 1 deletion(-) + create mode 100644 tests/t-digest.c + +diff --git a/tests/Makefile.am b/tests/Makefile.am +index 52f7dd61..93774fe9 100644 +--- a/tests/Makefile.am ++++ b/tests/Makefile.am +@@ -25,7 +25,7 @@ tests_bin = \ + version t-secmem mpitests t-sexp t-convert \ + t-mpi-bit t-mpi-point t-lock \ + prime basic keygen pubkey hmac hashtest t-kdf keygrip \ +- aeswrap random t-kem t-mlkem t-thread-local ++ aeswrap random t-kem t-mlkem t-thread-local t-digest + + if USE_RSA + tests_bin += pkcs1v2 t-rsa-pss t-rsa-15 t-rsa-testparm +diff --git a/tests/t-digest.c b/tests/t-digest.c +new file mode 100644 +index 00000000..3a94fa69 +--- /dev/null ++++ b/tests/t-digest.c +@@ -0,0 +1,199 @@ ++/* t-digest.c - MD regression tests ++ * Copyright (C) 2024 g10 Code GmbH ++ * ++ * This file is part of Libgcrypt. ++ * ++ * Libgcrypt is free software; you can redistribute it and/or modify ++ * it under the terms of the GNU Lesser General Public License as ++ * published by the Free Software Foundation; either version 2.1 of ++ * the License, or (at your option) any later version. ++ * ++ * Libgcrypt 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 Lesser General Public License for more details. ++ * ++ * You should have received a copy of the GNU Lesser General Public License ++ * along with this program; if not, see . ++ * SPDX-License-Identifier: LGPL-2.1+ ++ */ ++ ++#ifdef HAVE_CONFIG_H ++#include ++#endif ++#include ++#include ++#include ++#include ++#include ++ ++#define PGM "t-digest" ++ ++#include "t-common.h" ++static int in_fips_mode; ++ ++/* Mingw requires us to include windows.h after winsock2.h which is ++ included by gcrypt.h. */ ++#ifdef _WIN32 ++# include ++#endif ++ ++static void ++check_digests (void) ++{ ++ static struct { ++ int algo; ++ const char *data; ++ int datalen; ++ const char *expect; ++ int expect_failure; ++ } tv[] = { ++#undef ENABLE_THIS_AFTER_T6376_CHANGE_REVISED ++#ifdef ENABLE_THIS_AFTER_T6376_CHANGE_REVISED ++ { GCRY_MD_MD5, "abc", 3, ++ "\x90\x01\x50\x98\x3C\xD2\x4F\xB0\xD6\x96\x3F\x7D\x28\xE1\x7F\x72", 1 }, ++#endif ++ { GCRY_MD_SHA1, "abc", 3, ++ "\xA9\x99\x3E\x36\x47\x06\x81\x6A\xBA\x3E" ++ "\x25\x71\x78\x50\xC2\x6C\x9C\xD0\xD8\x9D" }, ++ { GCRY_MD_SHA256, "abc", 3, ++ "\xba\x78\x16\xbf\x8f\x01\xcf\xea\x41\x41\x40\xde\x5d\xae\x22\x23" ++ "\xb0\x03\x61\xa3\x96\x17\x7a\x9c\xb4\x10\xff\x61\xf2\x00\x15\xad" }, ++ { GCRY_MD_SHA384, "abc", 3, ++ "\xcb\x00\x75\x3f\x45\xa3\x5e\x8b\xb5\xa0\x3d\x69\x9a\xc6\x50\x07" ++ "\x27\x2c\x32\xab\x0e\xde\xd1\x63\x1a\x8b\x60\x5a\x43\xff\x5b\xed" ++ "\x80\x86\x07\x2b\xa1\xe7\xcc\x23\x58\xba\xec\xa1\x34\xc8\x25\xa7" }, ++ { GCRY_MD_SHA512, "abc", 3, ++ "\xDD\xAF\x35\xA1\x93\x61\x7A\xBA\xCC\x41\x73\x49\xAE\x20\x41\x31" ++ "\x12\xE6\xFA\x4E\x89\xA9\x7E\xA2\x0A\x9E\xEE\xE6\x4B\x55\xD3\x9A" ++ "\x21\x92\x99\x2A\x27\x4F\xC1\xA8\x36\xBA\x3C\x23\xA3\xFE\xEB\xBD" ++ "\x45\x4D\x44\x23\x64\x3C\xE8\x0E\x2A\x9A\xC9\x4F\xA5\x4C\xA4\x9F" }, ++ { GCRY_MD_SHA3_256, "abc", 3, ++ "\x3a\x98\x5d\xa7\x4f\xe2\x25\xb2\x04\x5c\x17\x2d\x6b\xd3\x90\xbd" ++ "\x85\x5f\x08\x6e\x3e\x9d\x52\x5b\x46\xbf\xe2\x45\x11\x43\x15\x32" }, ++ { GCRY_MD_SHA3_384, "abc", 3, ++ "\xec\x01\x49\x82\x88\x51\x6f\xc9\x26\x45\x9f\x58\xe2\xc6\xad\x8d" ++ "\xf9\xb4\x73\xcb\x0f\xc0\x8c\x25\x96\xda\x7c\xf0\xe4\x9b\xe4\xb2" ++ "\x98\xd8\x8c\xea\x92\x7a\xc7\xf5\x39\xf1\xed\xf2\x28\x37\x6d\x25" }, ++ { GCRY_MD_SHA3_512, "abc", 3, ++ "\xb7\x51\x85\x0b\x1a\x57\x16\x8a\x56\x93\xcd\x92\x4b\x6b\x09\x6e" ++ "\x08\xf6\x21\x82\x74\x44\xf7\x0d\x88\x4f\x5d\x02\x40\xd2\x71\x2e" ++ "\x10\xe1\x16\xe9\x19\x2a\xf3\xc9\x1a\x7e\xc5\x76\x47\xe3\x93\x40" ++ "\x57\x34\x0b\x4c\xf4\x08\xd5\xa5\x65\x92\xf8\x27\x4e\xec\x53\xf0" }, ++ { GCRY_MD_RMD160, "abc", 3, ++ "\x8e\xb2\x08\xf7\xe0\x5d\x98\x7a\x9b\x04" ++ "\x4a\x8e\x98\xc6\xb0\x87\xf1\x5a\x0b\xfc", 1 }, ++ }; ++ int tvidx; ++ unsigned char hash[64]; ++ int expectlen; ++ ++ for (tvidx=0; tvidx < DIM(tv); tvidx++) ++ { ++ gpg_err_code_t ec; ++ ++ if (verbose) ++ fprintf (stderr, "checking gcry_md_hash_buffer test %d\n", ++ tvidx); ++ ++ expectlen = gcry_md_get_algo_dlen (tv[tvidx].algo); ++ assert (expectlen != 0); ++ assert (expectlen <= sizeof hash); ++ gcry_md_hash_buffer (tv[tvidx].algo, hash, ++ tv[tvidx].data, tv[tvidx].datalen); ++ ++ ec = gcry_get_fips_service_indicator (); ++ if (ec == GPG_ERR_INV_OP) ++ { ++ /* libgcrypt is old, no support of the FIPS service indicator. */ ++ fail ("gcry_md_hash_buffer test %d unexpectedly failed to check the FIPS service indicator.\n", ++ tvidx); ++ continue; ++ } ++ ++ if (in_fips_mode && !tv[tvidx].expect_failure && ec) ++ { ++ /* Success with the FIPS service indicator == 0 expected, but != 0. */ ++ fail ("gcry_md_hash_buffer test %d unexpectedly set the indicator in FIPS mode.\n", ++ tvidx); ++ continue; ++ } ++ else if (in_fips_mode && tv[tvidx].expect_failure && !ec) ++ { ++ /* Success with the FIPS service indicator != 0 expected, but == 0. */ ++ fail ("gcry_md_hash_buffer test %d unexpectedly cleared the indicator in FIPS mode.\n", ++ tvidx); ++ continue; ++ } ++ ++ if (memcmp (hash, tv[tvidx].expect, expectlen)) ++ { ++ int i; ++ ++ fail ("gcry_md_hash_buffer test %d failed: mismatch\n", tvidx); ++ fputs ("got:", stderr); ++ for (i=0; i < expectlen; i++) ++ fprintf (stderr, " %02x", hash[i]); ++ putc ('\n', stderr); ++ } ++ } ++} ++ ++ ++int ++main (int argc, char **argv) ++{ ++ int last_argc = -1; ++ ++ if (argc) ++ { argc--; argv++; } ++ ++ while (argc && last_argc != argc) ++ { ++ last_argc = argc; ++ if (!strcmp (*argv, "--")) ++ { ++ argc--; argv++; ++ break; ++ } ++ else if (!strcmp (*argv, "--help")) ++ { ++ fputs ("usage: " PGM " [options]\n" ++ "Options:\n" ++ " --verbose print timings etc.\n" ++ " --debug flyswatter\n", ++ stdout); ++ exit (0); ++ } ++ else if (!strcmp (*argv, "--verbose")) ++ { ++ verbose++; ++ argc--; argv++; ++ } ++ else if (!strcmp (*argv, "--debug")) ++ { ++ verbose += 2; ++ debug++; ++ argc--; argv++; ++ } ++ else if (!strncmp (*argv, "--", 2)) ++ die ("unknown option '%s'", *argv); ++ } ++ ++ if (!gcry_check_version (GCRYPT_VERSION)) ++ die ("version mismatch\n"); ++ ++ if (gcry_fips_mode_active ()) ++ in_fips_mode = 1; ++ ++ if (!in_fips_mode) ++ xgcry_control ((GCRYCTL_DISABLE_SECMEM, 0)); ++ ++ xgcry_control ((GCRYCTL_INITIALIZATION_FINISHED, 0)); ++ if (debug) ++ xgcry_control ((GCRYCTL_SET_DEBUG_FLAGS, 1u , 0)); ++ ++ check_digests (); ++ ++ return !!error_count; ++} +-- +2.49.0 + diff --git a/libgcrypt-fips-tests-Add-tests-for-md_open-write-read-close-for-t-digest.patch b/libgcrypt-fips-tests-Add-tests-for-md_open-write-read-close-for-t-digest.patch new file mode 100644 index 0000000..699c1eb --- /dev/null +++ b/libgcrypt-fips-tests-Add-tests-for-md_open-write-read-close-for-t-digest.patch @@ -0,0 +1,172 @@ +From 917fc6000dfebd8854f0d1c220b85dec0dbf4676 Mon Sep 17 00:00:00 2001 +From: NIIBE Yutaka +Date: Fri, 13 Dec 2024 11:54:31 +0900 +Subject: [PATCH 03/19] fips,tests: Add tests for md_open/write/read/close for + t-digest. +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* tests/t-digest.c (check_md_o_w_r_c): New. +(main): Call check_md_o_w_r_c. + +-- + +GnuPG-bug-id: 7338 +Signed-off-by: NIIBE Yutaka +Signed-off-by: Lucas Mülling +--- + tests/t-digest.c | 133 +++++++++++++++++++++++++++++++++++++++++++++++ + 1 file changed, 133 insertions(+) + +Index: libgcrypt-1.11.0/tests/t-digest.c +=================================================================== +--- libgcrypt-1.11.0.orig/tests/t-digest.c ++++ libgcrypt-1.11.0/tests/t-digest.c +@@ -39,6 +39,138 @@ static int in_fips_mode; + #endif + + static void ++check_md_o_w_r_c (void) ++{ ++ static struct { ++ int algo; ++ const char *data; ++ int datalen; ++ const char *expect; ++ int expect_failure; ++ unsigned int flags; ++ } tv[] = { ++#if USE_MD5 ++ { GCRY_MD_MD5, "abc", 3, ++ "\x90\x01\x50\x98\x3C\xD2\x4F\xB0\xD6\x96\x3F\x7D\x28\xE1\x7F\x72", 1 }, ++ { GCRY_MD_MD5, "abc", 3, ++ "\x90\x01\x50\x98\x3C\xD2\x4F\xB0\xD6\x96\x3F\x7D\x28\xE1\x7F\x72", 1, ++ GCRY_MD_FLAG_REJECT_NON_FIPS }, ++#endif ++#if USE_SHA1 ++ { GCRY_MD_SHA1, "abc", 3, ++ "\xA9\x99\x3E\x36\x47\x06\x81\x6A\xBA\x3E" ++ "\x25\x71\x78\x50\xC2\x6C\x9C\xD0\xD8\x9D" }, ++#endif ++ { GCRY_MD_SHA256, "abc", 3, ++ "\xba\x78\x16\xbf\x8f\x01\xcf\xea\x41\x41\x40\xde\x5d\xae\x22\x23" ++ "\xb0\x03\x61\xa3\x96\x17\x7a\x9c\xb4\x10\xff\x61\xf2\x00\x15\xad" }, ++ { GCRY_MD_SHA384, "abc", 3, ++ "\xcb\x00\x75\x3f\x45\xa3\x5e\x8b\xb5\xa0\x3d\x69\x9a\xc6\x50\x07" ++ "\x27\x2c\x32\xab\x0e\xde\xd1\x63\x1a\x8b\x60\x5a\x43\xff\x5b\xed" ++ "\x80\x86\x07\x2b\xa1\xe7\xcc\x23\x58\xba\xec\xa1\x34\xc8\x25\xa7" }, ++ { GCRY_MD_SHA512, "abc", 3, ++ "\xDD\xAF\x35\xA1\x93\x61\x7A\xBA\xCC\x41\x73\x49\xAE\x20\x41\x31" ++ "\x12\xE6\xFA\x4E\x89\xA9\x7E\xA2\x0A\x9E\xEE\xE6\x4B\x55\xD3\x9A" ++ "\x21\x92\x99\x2A\x27\x4F\xC1\xA8\x36\xBA\x3C\x23\xA3\xFE\xEB\xBD" ++ "\x45\x4D\x44\x23\x64\x3C\xE8\x0E\x2A\x9A\xC9\x4F\xA5\x4C\xA4\x9F" }, ++ { GCRY_MD_SHA3_256, "abc", 3, ++ "\x3a\x98\x5d\xa7\x4f\xe2\x25\xb2\x04\x5c\x17\x2d\x6b\xd3\x90\xbd" ++ "\x85\x5f\x08\x6e\x3e\x9d\x52\x5b\x46\xbf\xe2\x45\x11\x43\x15\x32" }, ++ { GCRY_MD_SHA3_384, "abc", 3, ++ "\xec\x01\x49\x82\x88\x51\x6f\xc9\x26\x45\x9f\x58\xe2\xc6\xad\x8d" ++ "\xf9\xb4\x73\xcb\x0f\xc0\x8c\x25\x96\xda\x7c\xf0\xe4\x9b\xe4\xb2" ++ "\x98\xd8\x8c\xea\x92\x7a\xc7\xf5\x39\xf1\xed\xf2\x28\x37\x6d\x25" }, ++ { GCRY_MD_SHA3_512, "abc", 3, ++ "\xb7\x51\x85\x0b\x1a\x57\x16\x8a\x56\x93\xcd\x92\x4b\x6b\x09\x6e" ++ "\x08\xf6\x21\x82\x74\x44\xf7\x0d\x88\x4f\x5d\x02\x40\xd2\x71\x2e" ++ "\x10\xe1\x16\xe9\x19\x2a\xf3\xc9\x1a\x7e\xc5\x76\x47\xe3\x93\x40" ++ "\x57\x34\x0b\x4c\xf4\x08\xd5\xa5\x65\x92\xf8\x27\x4e\xec\x53\xf0" } ++#if USE_RMD160 ++ , ++ { GCRY_MD_RMD160, "abc", 3, ++ "\x8e\xb2\x08\xf7\xe0\x5d\x98\x7a\x9b\x04" ++ "\x4a\x8e\x98\xc6\xb0\x87\xf1\x5a\x0b\xfc", 1 } ++#endif ++ }; ++ int tvidx; ++ unsigned char *hash; ++ int expectlen; ++ gpg_error_t err; ++ ++ for (tvidx=0; tvidx < DIM(tv); tvidx++) ++ { ++ gpg_err_code_t ec; ++ gcry_md_hd_t h; ++ ++ if (verbose) ++ fprintf (stderr, "checking gcry_md_open test %d\n", ++ tvidx); ++ ++ expectlen = gcry_md_get_algo_dlen (tv[tvidx].algo); ++ assert (expectlen != 0); ++ err = gcry_md_open (&h, tv[tvidx].algo, tv[tvidx].flags); ++ if (err) ++ { ++ if (in_fips_mode && (tv[tvidx].flags & GCRY_MD_FLAG_REJECT_NON_FIPS) ++ && tv[tvidx].expect_failure) ++ /* Here, an error is expected */ ++ ; ++ else ++ fail ("gcry_md_open test %d unexpectedly failed: %s\n", ++ tvidx, gpg_strerror (err)); ++ continue; ++ } ++ else ++ { ++ if (in_fips_mode && (tv[tvidx].flags & GCRY_MD_FLAG_REJECT_NON_FIPS) ++ && tv[tvidx].expect_failure) ++ /* This case, an error is expected, but we observed success */ ++ fail ("gcry_md_open test %d unexpectedly succeeded\n", tvidx); ++ } ++ ++ ++ ec = gcry_get_fips_service_indicator (); ++ if (ec == GPG_ERR_INV_OP) ++ { ++ /* libgcrypt is old, no support of the FIPS service indicator. */ ++ fail ("gcry_md_open test %d unexpectedly failed to check the FIPS service indicator.\n", ++ tvidx); ++ continue; ++ } ++ ++ if (in_fips_mode && !tv[tvidx].expect_failure && ec) ++ { ++ /* Success with the FIPS service indicator == 0 expected, but != 0. */ ++ fail ("gcry_md_open test %d unexpectedly set the indicator in FIPS mode.\n", ++ tvidx); ++ continue; ++ } ++ else if (in_fips_mode && tv[tvidx].expect_failure && !ec) ++ { ++ /* Success with the FIPS service indicator != 0 expected, but == 0. */ ++ fail ("gcry_md_open test %d unexpectedly cleared the indicator in FIPS mode.\n", ++ tvidx); ++ continue; ++ } ++ ++ gcry_md_write (h, tv[tvidx].data, tv[tvidx].datalen); ++ hash = gcry_md_read (h, tv[tvidx].algo); ++ if (memcmp (hash, tv[tvidx].expect, expectlen)) ++ { ++ int i; ++ ++ fail ("gcry_md_open test %d failed: mismatch\n", tvidx); ++ fputs ("got:", stderr); ++ for (i=0; i < expectlen; i++) ++ fprintf (stderr, " %02x", hash[i]); ++ putc ('\n', stderr); ++ } ++ ++ gcry_md_close (h); ++ } ++} ++ ++static void + check_digests (void) + { + static struct { +@@ -194,6 +326,7 @@ main (int argc, char **argv) + xgcry_control ((GCRYCTL_SET_DEBUG_FLAGS, 1u , 0)); + + check_digests (); ++ check_md_o_w_r_c (); + + return !!error_count; + } diff --git a/libgcrypt-jitterentropy-3.4.0.patch b/libgcrypt-jitterentropy-3.4.0.patch new file mode 100644 index 0000000..dbb77ba --- /dev/null +++ b/libgcrypt-jitterentropy-3.4.0.patch @@ -0,0 +1,618 @@ +Index: libgcrypt-1.10.0/random/jitterentropy-base.c +=================================================================== +--- libgcrypt-1.10.0.orig/random/jitterentropy-base.c ++++ libgcrypt-1.10.0/random/jitterentropy-base.c +@@ -42,7 +42,7 @@ + * require consumer to be updated (as long as this number + * is zero, the API is not considered stable and can + * change without a bump of the major version) */ +-#define MINVERSION 3 /* API compatible, ABI may change, functional ++#define MINVERSION 4 /* API compatible, ABI may change, functional + * enhancements only, consumer can be left unchanged if + * enhancements are not considered */ + #define PATCHLEVEL 0 /* API / ABI compatible, no functional changes, no +@@ -200,29 +200,38 @@ ssize_t jent_read_entropy(struct rand_da + tocopy = (DATA_SIZE_BITS / 8); + else + tocopy = len; +- memcpy(p, &ec->data, tocopy); ++ ++ jent_read_random_block(ec, p, tocopy); + + len -= tocopy; + p += tocopy; + } + + /* +- * To be on the safe side, we generate one more round of entropy +- * which we do not give out to the caller. That round shall ensure +- * that in case the calling application crashes, memory dumps, pages +- * out, or due to the CPU Jitter RNG lingering in memory for long +- * time without being moved and an attacker cracks the application, +- * all he reads in the entropy pool is a value that is NEVER EVER +- * being used for anything. Thus, he does NOT see the previous value +- * that was returned to the caller for cryptographic purposes. ++ * Enhanced backtracking support: At this point, the hash state ++ * contains the digest of the previous Jitter RNG collection round ++ * which is inserted there by jent_read_random_block with the SHA ++ * update operation. At the current code location we completed ++ * one request for a caller and we do not know how long it will ++ * take until a new request is sent to us. To guarantee enhanced ++ * backtracking resistance at this point (i.e. ensure that an attacker ++ * cannot obtain information about prior random numbers we generated), ++ * but still stirring the hash state with old data the Jitter RNG ++ * obtains a new message digest from its state and re-inserts it. ++ * After this operation, the Jitter RNG state is still stirred with ++ * the old data, but an attacker who gets access to the memory after ++ * this point cannot deduce the random numbers produced by the ++ * Jitter RNG prior to this point. + */ + /* +- * If we use secured memory, do not use that precaution as the secure +- * memory protects the entropy pool. Moreover, note that using this +- * call reduces the speed of the RNG by up to half ++ * If we use secured memory, where backtracking support may not be ++ * needed because the state is protected in a different method, ++ * it is permissible to drop this support. But strongly weigh the ++ * pros and cons considering that the SHA3 operation is not that ++ * expensive. + */ + #ifndef JENT_CPU_JITTERENTROPY_SECURE_MEMORY +- jent_random_data(ec); ++ jent_read_random_block(ec, NULL, 0); + #endif + + err: +@@ -379,6 +388,7 @@ static struct rand_data + *jent_entropy_collector_alloc_internal(unsigned int osr, unsigned int flags) + { + struct rand_data *entropy_collector; ++ uint32_t memsize = 0; + + /* + * Requesting disabling and forcing of internal timer +@@ -405,7 +415,7 @@ static struct rand_data + return NULL; + + if (!(flags & JENT_DISABLE_MEMORY_ACCESS)) { +- uint32_t memsize = jent_memsize(flags); ++ memsize = jent_memsize(flags); + + entropy_collector->mem = _gcry_calloc (1, memsize); + +@@ -431,13 +441,19 @@ static struct rand_data + entropy_collector->memaccessloops = JENT_MEMORY_ACCESSLOOPS; + } + ++ if (sha3_alloc(&entropy_collector->hash_state)) ++ goto err; ++ ++ /* Initialize the hash state */ ++ sha3_256_init(entropy_collector->hash_state); ++ + /* verify and set the oversampling rate */ + if (osr < JENT_MIN_OSR) + osr = JENT_MIN_OSR; + entropy_collector->osr = osr; + entropy_collector->flags = flags; + +- if (jent_fips_enabled() || (flags & JENT_FORCE_FIPS)) ++ if ((flags & JENT_FORCE_FIPS) || jent_fips_enabled()) + entropy_collector->fips_enabled = 1; + + /* Initialize the APT */ +@@ -469,7 +485,7 @@ static struct rand_data + + err: + if (entropy_collector->mem != NULL) +- jent_zfree(entropy_collector->mem, JENT_MEMORY_SIZE); ++ jent_zfree(entropy_collector->mem, memsize); + jent_zfree(entropy_collector, sizeof(struct rand_data)); + return NULL; + } +@@ -511,6 +527,7 @@ JENT_PRIVATE_STATIC + void jent_entropy_collector_free(struct rand_data *entropy_collector) + { + if (entropy_collector != NULL) { ++ sha3_dealloc(entropy_collector->hash_state); + jent_notime_disable(entropy_collector); + if (entropy_collector->mem != NULL) { + jent_zfree(entropy_collector->mem, +@@ -664,6 +681,7 @@ static inline int jent_entropy_init_comm + int ret; + + jent_notime_block_switch(); ++ jent_health_cb_block_switch(); + + if (sha3_tester()) + return EHASH; +@@ -710,6 +728,8 @@ int jent_entropy_init_ex(unsigned int os + if (ret) + return ret; + ++ ret = ENOTIME; ++ + /* Test without internal timer unless caller does not want it */ + if (!(flags & JENT_FORCE_INTERNAL_TIMER)) + ret = jent_time_entropy_init(osr, +@@ -732,3 +752,9 @@ int jent_entropy_switch_notime_impl(stru + return jent_notime_switch(new_thread); + } + #endif ++ ++JENT_PRIVATE_STATIC ++int jent_set_fips_failure_callback(jent_fips_failure_cb cb) ++{ ++ return jent_set_fips_failure_callback_internal(cb); ++} +Index: libgcrypt-1.10.0/random/jitterentropy-gcd.c +=================================================================== +--- libgcrypt-1.10.0.orig/random/jitterentropy-gcd.c ++++ libgcrypt-1.10.0/random/jitterentropy-gcd.c +@@ -113,12 +113,8 @@ int jent_gcd_analyze(uint64_t *delta_his + goto out; + } + +- /* +- * Ensure that we have variations in the time stamp below 100 for at +- * least 10% of all checks -- on some platforms, the counter increments +- * in multiples of 100, but not always +- */ +- if (running_gcd >= 100) { ++ /* Set a sensible maximum value. */ ++ if (running_gcd >= UINT32_MAX / 2) { + ret = ECOARSETIME; + goto out; + } +Index: libgcrypt-1.10.0/random/jitterentropy-health.c +=================================================================== +--- libgcrypt-1.10.0.orig/random/jitterentropy-health.c ++++ libgcrypt-1.10.0/random/jitterentropy-health.c +@@ -19,9 +19,24 @@ + * DAMAGE. + */ + +-#include "jitterentropy.h" + #include "jitterentropy-health.h" + ++static jent_fips_failure_cb fips_cb = NULL; ++static int jent_health_cb_switch_blocked = 0; ++ ++void jent_health_cb_block_switch(void) ++{ ++ jent_health_cb_switch_blocked = 1; ++} ++ ++int jent_set_fips_failure_callback_internal(jent_fips_failure_cb cb) ++{ ++ if (jent_health_cb_switch_blocked) ++ return -EAGAIN; ++ fips_cb = cb; ++ return 0; ++} ++ + /*************************************************************************** + * Lag Predictor Test + * +@@ -434,5 +449,9 @@ unsigned int jent_health_failure(struct + if (!ec->fips_enabled) + return 0; + ++ if (fips_cb && ec->health_failure) { ++ fips_cb(ec, ec->health_failure); ++ } ++ + return ec->health_failure; + } +Index: libgcrypt-1.10.0/random/jitterentropy-health.h +=================================================================== +--- libgcrypt-1.10.0.orig/random/jitterentropy-health.h ++++ libgcrypt-1.10.0/random/jitterentropy-health.h +@@ -20,11 +20,16 @@ + #ifndef JITTERENTROPY_HEALTH_H + #define JITTERENTROPY_HEALTH_H + ++#include "jitterentropy.h" ++ + #ifdef __cplusplus + extern "C" + { + #endif + ++void jent_health_cb_block_switch(void); ++int jent_set_fips_failure_callback_internal(jent_fips_failure_cb cb); ++ + static inline uint64_t jent_delta(uint64_t prev, uint64_t next) + { + return (next - prev); +Index: libgcrypt-1.10.0/random/jitterentropy-noise.c +=================================================================== +--- libgcrypt-1.10.0.orig/random/jitterentropy-noise.c ++++ libgcrypt-1.10.0/random/jitterentropy-noise.c +@@ -33,7 +33,7 @@ + * Update of the loop count used for the next round of + * an entropy collection. + * +- * @ec [in] entropy collector struct -- may be NULL ++ * @ec [in] entropy collector struct + * @bits [in] is the number of low bits of the timer to consider + * @min [in] is the number of bits we shift the timer value to the right at + * the end to make sure we have a guaranteed minimum value +@@ -61,16 +61,13 @@ static uint64_t jent_loop_shuffle(struct + * Mix the current state of the random number into the shuffle + * calculation to balance that shuffle a bit more. + */ +- if (ec) { +- jent_get_nstime_internal(ec, &time); +- time ^= ec->data[0]; +- } ++ jent_get_nstime_internal(ec, &time); + + /* + * We fold the time value as much as possible to ensure that as many + * bits of the time stamp are included as possible. + */ +- for (i = 0; ((DATA_SIZE_BITS + bits - 1) / bits) > i; i++) { ++ for (i = 0; (((sizeof(time) << 3) + bits - 1) / bits) > i; i++) { + shuffle ^= time & mask; + time = time >> bits; + } +@@ -91,11 +88,11 @@ static uint64_t jent_loop_shuffle(struct + * This function injects the individual bits of the time value into the + * entropy pool using a hash. + * +- * @ec [in] entropy collector struct -- may be NULL +- * @time [in] time stamp to be injected ++ * @ec [in] entropy collector struct ++ * @time [in] time delta to be injected + * @loop_cnt [in] if a value not equal to 0 is set, use the given value as + * number of loops to perform the hash operation +- * @stuck [in] Is the time stamp identified as stuck? ++ * @stuck [in] Is the time delta identified as stuck? + * + * Output: + * updated hash context +@@ -104,17 +101,19 @@ static void jent_hash_time(struct rand_d + uint64_t loop_cnt, unsigned int stuck) + { + HASH_CTX_ON_STACK(ctx); +- uint8_t itermediary[SHA3_256_SIZE_DIGEST]; ++ uint8_t intermediary[SHA3_256_SIZE_DIGEST]; + uint64_t j = 0; +- uint64_t hash_loop_cnt; + #define MAX_HASH_LOOP 3 + #define MIN_HASH_LOOP 0 + + /* Ensure that macros cannot overflow jent_loop_shuffle() */ + BUILD_BUG_ON((MAX_HASH_LOOP + MIN_HASH_LOOP) > 63); +- hash_loop_cnt = ++ uint64_t hash_loop_cnt = + jent_loop_shuffle(ec, MAX_HASH_LOOP, MIN_HASH_LOOP); + ++ /* Use the memset to shut up valgrind */ ++ memset(intermediary, 0, sizeof(intermediary)); ++ + sha3_256_init(&ctx); + + /* +@@ -125,35 +124,54 @@ static void jent_hash_time(struct rand_d + hash_loop_cnt = loop_cnt; + + /* +- * This loop basically slows down the SHA-3 operation depending +- * on the hash_loop_cnt. Each iteration of the loop generates the +- * same result. ++ * This loop fills a buffer which is injected into the entropy pool. ++ * The main reason for this loop is to execute something over which we ++ * can perform a timing measurement. The injection of the resulting ++ * data into the pool is performed to ensure the result is used and ++ * the compiler cannot optimize the loop away in case the result is not ++ * used at all. Yet that data is considered "additional information" ++ * considering the terminology from SP800-90A without any entropy. ++ * ++ * Note, it does not matter which or how much data you inject, we are ++ * interested in one Keccack1600 compression operation performed with ++ * the sha3_final. + */ + for (j = 0; j < hash_loop_cnt; j++) { +- sha3_update(&ctx, ec->data, SHA3_256_SIZE_DIGEST); +- sha3_update(&ctx, (uint8_t *)&time, sizeof(uint64_t)); ++ sha3_update(&ctx, intermediary, sizeof(intermediary)); ++ sha3_update(&ctx, (uint8_t *)&ec->rct_count, ++ sizeof(ec->rct_count)); ++ sha3_update(&ctx, (uint8_t *)&ec->apt_cutoff, ++ sizeof(ec->apt_cutoff)); ++ sha3_update(&ctx, (uint8_t *)&ec->apt_observations, ++ sizeof(ec->apt_observations)); ++ sha3_update(&ctx, (uint8_t *)&ec->apt_count, ++ sizeof(ec->apt_count)); ++ sha3_update(&ctx,(uint8_t *) &ec->apt_base, ++ sizeof(ec->apt_base)); + sha3_update(&ctx, (uint8_t *)&j, sizeof(uint64_t)); ++ sha3_final(&ctx, intermediary); ++ } + +- /* +- * If the time stamp is stuck, do not finally insert the value +- * into the entropy pool. Although this operation should not do +- * any harm even when the time stamp has no entropy, SP800-90B +- * requires that any conditioning operation to have an identical +- * amount of input data according to section 3.1.5. +- */ ++ /* ++ * Inject the data from the previous loop into the pool. This data is ++ * not considered to contain any entropy, but it stirs the pool a bit. ++ */ ++ sha3_update(ec->hash_state, intermediary, sizeof(intermediary)); + +- /* +- * The sha3_final operations re-initialize the context for the +- * next loop iteration. +- */ +- if (stuck || (j < hash_loop_cnt - 1)) +- sha3_final(&ctx, itermediary); +- else +- sha3_final(&ctx, ec->data); +- } ++ /* ++ * Insert the time stamp into the hash context representing the pool. ++ * ++ * If the time stamp is stuck, do not finally insert the value into the ++ * entropy pool. Although this operation should not do any harm even ++ * when the time stamp has no entropy, SP800-90B requires that any ++ * conditioning operation to have an identical amount of input data ++ * according to section 3.1.5. ++ */ ++ if (!stuck) ++ sha3_update(ec->hash_state, (uint8_t *)&time, sizeof(uint64_t)); + + jent_memset_secure(&ctx, SHA_MAX_CTX_SIZE); +- jent_memset_secure(itermediary, sizeof(itermediary)); ++ jent_memset_secure(intermediary, sizeof(intermediary)); + } + + #define MAX_ACC_LOOP_BIT 7 +@@ -184,13 +202,12 @@ static inline uint32_t xoshiro128starsta + + static void jent_memaccess(struct rand_data *ec, uint64_t loop_cnt) + { +- uint64_t i = 0; ++ uint64_t i = 0, time = 0; + union { + uint32_t u[4]; + uint8_t b[sizeof(uint32_t) * 4]; + } prngState = { .u = {0x8e93eec0, 0xce65608a, 0xa8d46b46, 0xe83cef69} }; + uint32_t addressMask; +- uint64_t acc_loop_cnt; + + if (NULL == ec || NULL == ec->mem) + return; +@@ -199,7 +216,7 @@ static void jent_memaccess(struct rand_d + + /* Ensure that macros cannot overflow jent_loop_shuffle() */ + BUILD_BUG_ON((MAX_ACC_LOOP_BIT + MIN_ACC_LOOP_BIT) > 63); +- acc_loop_cnt = ++ uint64_t acc_loop_cnt = + jent_loop_shuffle(ec, MAX_ACC_LOOP_BIT, MIN_ACC_LOOP_BIT); + + /* +@@ -213,8 +230,10 @@ static void jent_memaccess(struct rand_d + * "per-update: timing, it gets you mostly independent "per-update" + * timing, so we can now benefit from the Central Limit Theorem! + */ +- for (i = 0; i < sizeof(prngState); i++) +- prngState.b[i] ^= ec->data[i]; ++ for (i = 0; i < sizeof(prngState); i++) { ++ jent_get_nstime_internal(ec, &time); ++ prngState.b[i] ^= (uint8_t)(time & 0xff); ++ } + + /* + * testing purposes -- allow test app to set the counter, not +@@ -358,21 +377,21 @@ unsigned int jent_measure_jitter(struct + + /** + * Generator of one 256 bit random number +- * Function fills rand_data->data ++ * Function fills rand_data->hash_state + * + * @ec [in] Reference to entropy collector + */ + void jent_random_data(struct rand_data *ec) + { +- unsigned int k = 0, safety_factor = ENTROPY_SAFETY_FACTOR; ++ unsigned int k = 0, safety_factor = 0; + +- if (!ec->fips_enabled) +- safety_factor = 0; ++ if (ec->fips_enabled) ++ safety_factor = ENTROPY_SAFETY_FACTOR; + + /* priming of the ->prev_time value */ + jent_measure_jitter(ec, 0, NULL); + +- while (1) { ++ while (!jent_health_failure(ec)) { + /* If a stuck measurement is received, repeat measurement */ + if (jent_measure_jitter(ec, 0, NULL)) + continue; +@@ -385,3 +404,22 @@ void jent_random_data(struct rand_data * + break; + } + } ++ ++void jent_read_random_block(struct rand_data *ec, char *dst, size_t dst_len) ++{ ++ uint8_t jent_block[SHA3_256_SIZE_DIGEST]; ++ ++ BUILD_BUG_ON(SHA3_256_SIZE_DIGEST != (DATA_SIZE_BITS / 8)); ++ ++ /* The final operation automatically re-initializes the ->hash_state */ ++ sha3_final(ec->hash_state, jent_block); ++ if (dst_len) ++ memcpy(dst, jent_block, dst_len); ++ ++ /* ++ * Stir the new state with the data from the old state - the digest ++ * of the old data is not considered to have entropy. ++ */ ++ sha3_update(ec->hash_state, jent_block, sizeof(jent_block)); ++ jent_memset_secure(jent_block, sizeof(jent_block)); ++} +Index: libgcrypt-1.10.0/random/jitterentropy-noise.h +=================================================================== +--- libgcrypt-1.10.0.orig/random/jitterentropy-noise.h ++++ libgcrypt-1.10.0/random/jitterentropy-noise.h +@@ -31,6 +31,7 @@ unsigned int jent_measure_jitter(struct + uint64_t loop_cnt, + uint64_t *ret_current_delta); + void jent_random_data(struct rand_data *ec); ++void jent_read_random_block(struct rand_data *ec, char *dst, size_t dst_len); + + #ifdef __cplusplus + } +Index: libgcrypt-1.10.0/random/jitterentropy-sha3.c +=================================================================== +--- libgcrypt-1.10.0.orig/random/jitterentropy-sha3.c ++++ libgcrypt-1.10.0/random/jitterentropy-sha3.c +@@ -19,6 +19,7 @@ + */ + + #include "jitterentropy-sha3.h" ++#include "jitterentropy.h" + + /*************************************************************************** + * Message Digest Implementation +@@ -380,3 +381,23 @@ int sha3_tester(void) + + return 0; + } ++ ++int sha3_alloc(void **hash_state) ++{ ++ struct sha_ctx *tmp; ++ ++ tmp = jent_zalloc(SHA_MAX_CTX_SIZE); ++ if (!tmp) ++ return 1; ++ ++ *hash_state = tmp; ++ ++ return 0; ++} ++ ++void sha3_dealloc(void *hash_state) ++{ ++ struct sha_ctx *ctx = (struct sha_ctx *)hash_state; ++ ++ jent_zfree(ctx, SHA_MAX_CTX_SIZE); ++} +Index: libgcrypt-1.10.0/random/jitterentropy-sha3.h +=================================================================== +--- libgcrypt-1.10.0.orig/random/jitterentropy-sha3.h ++++ libgcrypt-1.10.0/random/jitterentropy-sha3.h +@@ -47,6 +47,8 @@ struct sha_ctx { + void sha3_256_init(struct sha_ctx *ctx); + void sha3_update(struct sha_ctx *ctx, const uint8_t *in, size_t inlen); + void sha3_final(struct sha_ctx *ctx, uint8_t *digest); ++int sha3_alloc(void **hash_state); ++void sha3_dealloc(void *hash_state); + int sha3_tester(void); + + #ifdef __cplusplus +Index: libgcrypt-1.10.0/random/jitterentropy-timer.c +=================================================================== +--- libgcrypt-1.10.0.orig/random/jitterentropy-timer.c ++++ libgcrypt-1.10.0/random/jitterentropy-timer.c +@@ -202,8 +202,8 @@ int jent_notime_enable(struct rand_data + if (jent_force_internal_timer || (flags & JENT_FORCE_INTERNAL_TIMER)) { + /* Self test not run yet */ + if (!jent_force_internal_timer && +- jent_time_entropy_init(flags | JENT_FORCE_INTERNAL_TIMER, +- ec->osr)) ++ jent_time_entropy_init(ec->osr, ++ flags | JENT_FORCE_INTERNAL_TIMER)) + return EHEALTH; + + ec->enable_notime = 1; +Index: libgcrypt-1.10.0/random/jitterentropy.h +=================================================================== +--- libgcrypt-1.10.0.orig/random/jitterentropy.h ++++ libgcrypt-1.10.0/random/jitterentropy.h +@@ -49,7 +49,7 @@ + ***************************************************************************/ + + /* +- * Enable timer-less timer support ++ * Enable timer-less timer support with JENT_CONF_ENABLE_INTERNAL_TIMER + * + * In case the hardware is identified to not provide a high-resolution time + * stamp, this option enables a built-in high-resolution time stamp mechanism. +@@ -166,7 +166,7 @@ struct rand_data + * of the RNG are marked as SENSITIVE. A user must not + * access that information while the RNG executes its loops to + * calculate the next random value. */ +- uint8_t data[SHA3_256_SIZE_DIGEST]; /* SENSITIVE Actual random number */ ++ void *hash_state; /* SENSITIVE hash state entropy pool */ + uint64_t prev_time; /* SENSITIVE Previous time stamp */ + #define DATA_SIZE_BITS (SHA3_256_SIZE_DIGEST_BITS) + +@@ -378,28 +378,34 @@ int jent_entropy_init(void); + JENT_PRIVATE_STATIC + int jent_entropy_init_ex(unsigned int osr, unsigned int flags); + ++/* ++ * Set a callback to run on health failure in FIPS mode. ++ * This function will take an action determined by the caller. ++ */ ++typedef void (*jent_fips_failure_cb)(struct rand_data *ec, ++ unsigned int health_failure); ++JENT_PRIVATE_STATIC ++int jent_set_fips_failure_callback(jent_fips_failure_cb cb); ++ + /* return version number of core library */ + JENT_PRIVATE_STATIC + unsigned int jent_version(void); + +-#ifdef JENT_CONF_ENABLE_INTERNAL_TIMER + /* Set a different thread handling logic for the notimer support */ + JENT_PRIVATE_STATIC + int jent_entropy_switch_notime_impl(struct jent_notime_thread *new_thread); +-#endif + + /* -- END of Main interface functions -- */ + + /* -- BEGIN timer-less threading support functions to prevent code dupes -- */ + +-struct jent_notime_ctx { + #ifdef JENT_CONF_ENABLE_INTERNAL_TIMER ++ ++struct jent_notime_ctx { + pthread_attr_t notime_pthread_attr; /* pthreads library */ + pthread_t notime_thread_id; /* pthreads thread ID */ +-#endif + }; + +-#ifdef JENT_CONF_ENABLE_INTERNAL_TIMER + + JENT_PRIVATE_STATIC + int jent_notime_init(void **ctx); +Index: libgcrypt-1.10.0/random/jitterentropy-base-user.h +=================================================================== +--- libgcrypt-1.10.0.orig/random/jitterentropy-base-user.h ++++ libgcrypt-1.10.0/random/jitterentropy-base-user.h +@@ -213,12 +213,12 @@ static inline void jent_get_cachesize(lo + ext = strstr(buf, "K"); + if (ext) { + shift = 10; +- ext = '\0'; ++ *ext = '\0'; + } else { + ext = strstr(buf, "M"); + if (ext) { + shift = 20; +- ext = '\0'; ++ *ext = '\0'; + } + } + diff --git a/libgcrypt-md-Fix-gcry_md_algo_info-to-mark-reject-under-FIPS-mode.patch b/libgcrypt-md-Fix-gcry_md_algo_info-to-mark-reject-under-FIPS-mode.patch new file mode 100644 index 0000000..25f5904 --- /dev/null +++ b/libgcrypt-md-Fix-gcry_md_algo_info-to-mark-reject-under-FIPS-mode.patch @@ -0,0 +1,82 @@ +From 2f17a98a80b155e750ab77d4703e33612e545d58 Mon Sep 17 00:00:00 2001 +From: NIIBE Yutaka +Date: Tue, 25 Feb 2025 16:27:25 +0900 +Subject: [PATCH 1/4] md: Fix gcry_md_algo_info to mark/reject under FIPS mode. +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* cipher/md.c (check_digest_algo): Fix for marking non-compliance. +* src/visibility.c (gcry_md_algo_info): Add check with +fips_is_operational. + +-- + +GnuPG-bug-id: 7338 +Signed-off-by: NIIBE Yutaka +Signed-off-by: Lucas Mülling +--- + cipher/md.c | 26 ++++++++++++++++++++++---- + src/visibility.c | 3 +++ + 2 files changed, 25 insertions(+), 4 deletions(-) + +diff --git a/cipher/md.c b/cipher/md.c +index f600e7bb..caf33afc 100644 +--- a/cipher/md.c ++++ b/cipher/md.c +@@ -436,16 +436,34 @@ _gcry_md_algo_name (int algorithm) + + + static gcry_err_code_t +-check_digest_algo (int algorithm) ++check_digest_algo (int algo) + { + const gcry_md_spec_t *spec; ++ int reject = 0; + +- spec = spec_from_algo (algorithm); +- if (spec && !spec->flags.disabled && (spec->flags.fips || !fips_mode ())) ++ spec = spec_from_algo (algo); ++ if (!spec) ++ return GPG_ERR_DIGEST_ALGO; ++ ++ if (spec->flags.disabled) ++ return GPG_ERR_DIGEST_ALGO; ++ ++ if (!fips_mode ()) + return 0; + +- return GPG_ERR_DIGEST_ALGO; ++ if (spec->flags.fips) ++ return 0; ++ ++ if (algo == GCRY_MD_MD5) ++ reject = fips_check_rejection (GCRY_FIPS_FLAG_REJECT_MD_MD5); ++ else ++ reject = fips_check_rejection (GCRY_FIPS_FLAG_REJECT_MD_OTHERS); ++ ++ if (reject) ++ return GPG_ERR_DIGEST_ALGO; + ++ fips_service_indicator_mark_non_compliant (); ++ return 0; + } + + +diff --git a/src/visibility.c b/src/visibility.c +index e02d6cfe..4134446a 100644 +--- a/src/visibility.c ++++ b/src/visibility.c +@@ -1373,6 +1373,9 @@ gcry_md_info (gcry_md_hd_t h, int what, void *buffer, size_t *nbytes) + gcry_error_t + gcry_md_algo_info (int algo, int what, void *buffer, size_t *nbytes) + { ++ if (!fips_is_operational ()) ++ return gpg_error (fips_not_operational ()); ++ fips_service_indicator_init (); + return gpg_error (_gcry_md_algo_info (algo, what, buffer, nbytes)); + } + +-- +2.49.0 + diff --git a/libgcrypt-md-Make-SHA-1-non-FIPS-internally-for-1.12-API.patch b/libgcrypt-md-Make-SHA-1-non-FIPS-internally-for-1.12-API.patch new file mode 100644 index 0000000..bbea9bb --- /dev/null +++ b/libgcrypt-md-Make-SHA-1-non-FIPS-internally-for-1.12-API.patch @@ -0,0 +1,154 @@ +From 4ee91a94bcdad32aed4364d09e3daf8841fa579f Mon Sep 17 00:00:00 2001 +From: NIIBE Yutaka +Date: Tue, 11 Mar 2025 14:01:11 +0900 +Subject: [PATCH 11/14] md: Make SHA-1 non-FIPS internally for 1.12 API. +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* src/gcrypt.h.in (GCRY_FIPS_FLAG_REJECT_MD_SHA1): New. +* cipher/md.c (check_digest_algo_spec, _gcry_md_open, md_enable) +(_gcry_md_enable, md_copy): Care about SHA1. +* cipher/sha1.c (_gcry_digest_spec_sha1): Make SHA1 non-FIPS. +* tests/t-fips-service-ind.c (check_mac_o_w_r_c): SHA1 is non-FIPS. +(check_md_o_w_r_c, check_hash_buffer, check_hash_buffers): Likewise. +(main): Add GCRY_FIPS_FLAG_REJECT_MD_SHA1 for gcry_control. + +-- + +For 1.10 ABI (which 1.11 keeps), SHA1 is an approved hash function +(while its use in public key crypto is non-FIPS). + +For 1.12 API, the dynamic FIPS service indicator is going to be added. + +In 1.11.1 implementation, we are trying to support 1.12 dynamic FIPS +service indicator in forward-compatible way. For this purpose, +internally, it's specified as non-FIPS in _gcry_digest_spec_sha1. + +Note that update for tests/basic.c and tests/pkcs1v2.c are needed to +use SHA256 (or one of approved hash functions) in 1.12, so that test +program can be a reference for programmers. + +Co-authored-by: Lucas Mulling +Signed-off-by: NIIBE Yutaka +Signed-off-by: Lucas Mülling +--- + cipher/md.c | 10 ++++++++++ + cipher/sha1.c | 2 +- + src/gcrypt.h.in | 1 + + tests/t-fips-service-ind.c | 9 +++++---- + 4 files changed, 17 insertions(+), 5 deletions(-) + +Index: libgcrypt-1.11.0/cipher/md.c +=================================================================== +--- libgcrypt-1.11.0.orig/cipher/md.c ++++ libgcrypt-1.11.0/cipher/md.c +@@ -451,6 +451,8 @@ check_digest_algo_spec (int algo, const + + if (algo == GCRY_MD_MD5) + reject = fips_check_rejection (GCRY_FIPS_FLAG_REJECT_MD_MD5); ++ else if (algo == GCRY_MD_SHA1) ++ reject = fips_check_rejection (GCRY_FIPS_FLAG_REJECT_MD_SHA1); + else + reject = fips_check_rejection (GCRY_FIPS_FLAG_REJECT_MD_OTHERS); + +@@ -590,6 +592,8 @@ _gcry_md_open (gcry_md_hd_t *h, int algo + + if (algo == GCRY_MD_MD5) + reject = fips_check_rejection (GCRY_FIPS_FLAG_REJECT_MD_MD5); ++ else if (algo == GCRY_MD_SHA1) ++ reject = fips_check_rejection (GCRY_FIPS_FLAG_REJECT_MD_SHA1); + else + reject = fips_check_rejection (GCRY_FIPS_FLAG_REJECT_MD_OTHERS); + +@@ -625,6 +629,8 @@ md_enable (gcry_md_hd_t hd, int algorith + + if (algorithm == GCRY_MD_MD5) + reject = fips_check_rejection (GCRY_FIPS_FLAG_REJECT_MD_MD5); ++ else if (algorithm == GCRY_MD_SHA1) ++ reject = fips_check_rejection (GCRY_FIPS_FLAG_REJECT_MD_SHA1); + else + reject = fips_check_rejection (GCRY_FIPS_FLAG_REJECT_MD_OTHERS); + +@@ -703,6 +709,8 @@ _gcry_md_enable (gcry_md_hd_t hd, int al + + if (algorithm == GCRY_MD_MD5) + reject = fips_check_rejection (GCRY_FIPS_FLAG_REJECT_MD_MD5); ++ else if (algorithm == GCRY_MD_SHA1) ++ reject = fips_check_rejection (GCRY_FIPS_FLAG_REJECT_MD_SHA1); + else + reject = fips_check_rejection (GCRY_FIPS_FLAG_REJECT_MD_OTHERS); + +@@ -780,6 +788,8 @@ md_copy (gcry_md_hd_t ahd, gcry_md_hd_t + + if (spec->algo == GCRY_MD_MD5) + reject |= fips_check_rejection (GCRY_FIPS_FLAG_REJECT_MD_MD5); ++ else if (spec->algo == GCRY_MD_SHA1) ++ reject = fips_check_rejection (GCRY_FIPS_FLAG_REJECT_MD_SHA1); + else + reject |= fips_check_rejection (GCRY_FIPS_FLAG_REJECT_MD_OTHERS); + } +Index: libgcrypt-1.11.0/cipher/sha1.c +=================================================================== +--- libgcrypt-1.11.0.orig/cipher/sha1.c ++++ libgcrypt-1.11.0/cipher/sha1.c +@@ -759,7 +759,7 @@ static const gcry_md_oid_spec_t oid_spec + + const gcry_md_spec_t _gcry_digest_spec_sha1 = + { +- GCRY_MD_SHA1, {0, 1}, ++ GCRY_MD_SHA1, {0, 0}, + "SHA1", asn, DIM (asn), oid_spec_sha1, 20, + sha1_init, _gcry_md_block_write, sha1_final, sha1_read, NULL, + _gcry_sha1_hash_buffers, +Index: libgcrypt-1.11.0/src/gcrypt.h.in +=================================================================== +--- libgcrypt-1.11.0.orig/src/gcrypt.h.in ++++ libgcrypt-1.11.0/src/gcrypt.h.in +@@ -1982,6 +1982,7 @@ char *gcry_get_config (int mode, const c + #define GCRY_FIPS_FLAG_REJECT_PK_GOST_SM2 (1 << 7) + #define GCRY_FIPS_FLAG_REJECT_CIPHER_MODE (1 << 8) + /**/ ++#define GCRY_FIPS_FLAG_REJECT_MD_SHA1 (1 << 9) + #define GCRY_FIPS_FLAG_REJECT_PK_ECC_K (1 << 10) + #define GCRY_FIPS_FLAG_REJECT_PK_FLAGS (1 << 11) + +Index: libgcrypt-1.11.0/tests/t-fips-service-ind.c +=================================================================== +--- libgcrypt-1.11.0.orig/tests/t-fips-service-ind.c ++++ libgcrypt-1.11.0/tests/t-fips-service-ind.c +@@ -1107,7 +1107,7 @@ check_mac_o_w_r_c (int reject) + #if USE_SHA1 + { GCRY_MAC_HMAC_SHA1, "hmac input abc", 14, "hmac key input", 14, + "\xc9\x62\x9d\x16\x0f\xc2\xc4\xcd\x38\xac\x3a\x00\xdc\x29\x61\x03" +- "\x69\x50\xd7\x3a" }, ++ "\x69\x50\xd7\x3a", 1 }, + #endif + { GCRY_MAC_HMAC_SHA256, "hmac input abc", 14, "hmac key input", 14, + "\x6a\xda\x4d\xd5\xf3\xa7\x32\x9d\xd2\x55\xc0\x7f\xe6\x0a\x93\xb8" +@@ -1264,7 +1264,7 @@ check_md_o_w_r_c (int reject) + #if USE_SHA1 + { GCRY_MD_SHA1, "abc", 3, + "\xA9\x99\x3E\x36\x47\x06\x81\x6A\xBA\x3E" +- "\x25\x71\x78\x50\xC2\x6C\x9C\xD0\xD8\x9D" }, ++ "\x25\x71\x78\x50\xC2\x6C\x9C\xD0\xD8\x9D", 1 }, + #endif + { GCRY_MD_SHA256, "abc", 3, + "\xba\x78\x16\xbf\x8f\x01\xcf\xea\x41\x41\x40\xde\x5d\xae\x22\x23" +@@ -1389,7 +1389,7 @@ check_digests (void) + #endif + { GCRY_MD_SHA1, "abc", 3, + "\xA9\x99\x3E\x36\x47\x06\x81\x6A\xBA\x3E" +- "\x25\x71\x78\x50\xC2\x6C\x9C\xD0\xD8\x9D" }, ++ "\x25\x71\x78\x50\xC2\x6C\x9C\xD0\xD8\x9D", 1 }, + { GCRY_MD_SHA256, "abc", 3, + "\xba\x78\x16\xbf\x8f\x01\xcf\xea\x41\x41\x40\xde\x5d\xae\x22\x23" + "\xb0\x03\x61\xa3\x96\x17\x7a\x9c\xb4\x10\xff\x61\xf2\x00\x15\xad" }, +@@ -1701,6 +1701,7 @@ main (int argc, char **argv) + | GCRY_FIPS_FLAG_REJECT_CIPHER_MODE + | GCRY_FIPS_FLAG_REJECT_PK_MD + | GCRY_FIPS_FLAG_REJECT_PK_GOST_SM2 ++ | GCRY_FIPS_FLAG_REJECT_MD_SHA1 + | GCRY_FIPS_FLAG_REJECT_PK_ECC_K + | GCRY_FIPS_FLAG_REJECT_PK_FLAGS + | GCRY_FIPS_FLAG_REJECT_COMPAT110))); diff --git a/libgcrypt-md-Use-check_digest_algo_spec-in-_gcry_md_selftest.patch b/libgcrypt-md-Use-check_digest_algo_spec-in-_gcry_md_selftest.patch new file mode 100644 index 0000000..75489df --- /dev/null +++ b/libgcrypt-md-Use-check_digest_algo_spec-in-_gcry_md_selftest.patch @@ -0,0 +1,74 @@ +From ce4755d5c5500cede6d7d380fdab2d15f5d77796 Mon Sep 17 00:00:00 2001 +From: NIIBE Yutaka +Date: Wed, 26 Feb 2025 10:23:28 +0900 +Subject: [PATCH 2/4] md: Use check_digest_algo_spec in _gcry_md_selftest. +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* cipher/md.c (check_digest_algo_spec): New. +(check_digest_algo): Use check_digest_algo_spec. +(_gcry_md_selftest): Likewise. + +-- + +GnuPG-bug-id: 7338 +Signed-off-by: NIIBE Yutaka +Signed-off-by: Lucas Mülling +--- + cipher/md.c | 22 +++++++++++++--------- + 1 file changed, 13 insertions(+), 9 deletions(-) + +diff --git a/cipher/md.c b/cipher/md.c +index caf33afc..a8027e9e 100644 +--- a/cipher/md.c ++++ b/cipher/md.c +@@ -436,15 +436,10 @@ _gcry_md_algo_name (int algorithm) + + + static gcry_err_code_t +-check_digest_algo (int algo) ++check_digest_algo_spec (int algo, const gcry_md_spec_t *spec) + { +- const gcry_md_spec_t *spec; + int reject = 0; + +- spec = spec_from_algo (algo); +- if (!spec) +- return GPG_ERR_DIGEST_ALGO; +- + if (spec->flags.disabled) + return GPG_ERR_DIGEST_ALGO; + +@@ -466,6 +461,17 @@ check_digest_algo (int algo) + return 0; + } + ++static gcry_err_code_t ++check_digest_algo (int algo) ++{ ++ const gcry_md_spec_t *spec = spec_from_algo (algo); ++ ++ if (!spec) ++ return GPG_ERR_DIGEST_ALGO; ++ else ++ return check_digest_algo_spec (algo, spec); ++} ++ + + /**************** + * Open a message digest handle for use with algorithm ALGO. +@@ -1808,9 +1814,7 @@ _gcry_md_selftest (int algo, int extended, selftest_report_func_t report) + const gcry_md_spec_t *spec; + + spec = spec_from_algo (algo); +- if (spec && !spec->flags.disabled +- && (spec->flags.fips || !fips_mode ()) +- && spec->selftest) ++ if (spec && !check_digest_algo_spec (algo, spec) && spec->selftest) + ec = spec->selftest (algo, extended, report); + else + { +-- +2.49.0 + diff --git a/libgcrypt-no-deprecated-grep-alias.patch b/libgcrypt-no-deprecated-grep-alias.patch new file mode 100644 index 0000000..ba0dde8 --- /dev/null +++ b/libgcrypt-no-deprecated-grep-alias.patch @@ -0,0 +1,35 @@ +--- libgcrypt-1.10.3.orig/acinclude.m4 ++++ libgcrypt-1.10.3/acinclude.m4 +@@ -130,10 +130,10 @@ EOF + ac_nlist=conftest.nm + if AC_TRY_EVAL(NM conftest.$ac_objext \| $lt_cv_sys_global_symbol_pipe \| cut -d \' \' -f 2 \> $ac_nlist) && test -s "$ac_nlist"; then + # See whether the symbols have a leading underscore. +- if egrep '^_nm_test_func' "$ac_nlist" >/dev/null; then ++ if grep -E '^_nm_test_func' "$ac_nlist" >/dev/null; then + ac_cv_sys_symbol_underscore=yes + else +- if egrep '^nm_test_func ' "$ac_nlist" >/dev/null; then ++ if grep -E '^nm_test_func ' "$ac_nlist" >/dev/null; then + : + else + echo "configure: cannot find nm_test_func in $ac_nlist" >&AS_MESSAGE_LOG_FD +--- libgcrypt-1.10.3.orig/src/libgcrypt-config.in ++++ libgcrypt-1.10.3/src/libgcrypt-config.in +@@ -154,7 +154,7 @@ if test "$echo_cflags" = "yes"; then + + tmp="" + for i in $includes $cflags_final; do +- if echo "$tmp" | fgrep -v -- "$i" >/dev/null; then ++ if echo "$tmp" | @GREP@ -F -v -- "$i" >/dev/null; then + tmp="$tmp $i" + fi + done +@@ -175,7 +175,7 @@ if test "$echo_libs" = "yes"; then + + tmp="" + for i in $libdirs $libs_final; do +- if echo "$tmp" | fgrep -v -- "$i" >/dev/null; then ++ if echo "$tmp" | @GREP@ -F -v -- "$i" >/dev/null; then + tmp="$tmp $i" + fi + done diff --git a/libgcrypt-nobetasuffix.patch b/libgcrypt-nobetasuffix.patch new file mode 100644 index 0000000..3d4593a --- /dev/null +++ b/libgcrypt-nobetasuffix.patch @@ -0,0 +1,24 @@ +Index: libgcrypt-1.10.2/autogen.sh +=================================================================== +--- libgcrypt-1.10.2.orig/autogen.sh ++++ libgcrypt-1.10.2/autogen.sh +@@ -249,7 +249,7 @@ if [ "$myhost" = "find-version" ]; then + fi + + beta=no +- if [ -e .git ]; then ++ if false; then + ingit=yes + tmp=$(git describe --match "${matchstr1}" --long 2>/dev/null) + tmp=$(echo "$tmp" | sed s/^"$package"//) +@@ -265,8 +265,8 @@ if [ "$myhost" = "find-version" ]; then + rvd=$((0x$(echo ${rev} | dd bs=1 count=4 2>/dev/null))) + else + ingit=no +- beta=yes +- tmp="-unknown" ++ beta=no ++ tmp="" + rev="0000000" + rvd="0" + fi diff --git a/libgcrypt-ppc-enable-P10-assembly-with-ENABLE_FORCE_SOF.patch b/libgcrypt-ppc-enable-P10-assembly-with-ENABLE_FORCE_SOF.patch new file mode 100644 index 0000000..8ef3197 --- /dev/null +++ b/libgcrypt-ppc-enable-P10-assembly-with-ENABLE_FORCE_SOF.patch @@ -0,0 +1,76 @@ +commit 2c5e5ab6843d747c4b877d2c6f47226f61e9ff14 +Author: Jussi Kivilinna +Date: Sun Jun 12 21:51:34 2022 +0300 + + ppc enable P10 assembly with ENABLE_FORCE_SOFT_HWFEATURES on arch 3.00 + + * cipher/chacha20.c (chacha20_do_setkey) [USE_PPC_VEC]: Enable + P10 assembly for HWF_PPC_ARCH_3_00 if ENABLE_FORCE_SOFT_HWFEATURES is + defined. + * cipher/poly1305.c (poly1305_init) [POLY1305_USE_PPC_VEC]: Likewise. + * cipher/rijndael.c (do_setkey) [USE_PPC_CRYPTO_WITH_PPC9LE]: Likewise. + --- + + This change allows testing P10 implementations with P9 and with QEMU-PPC. + + GnuPG-bug-id: 6006 + Signed-off-by: Jussi Kivilinna + +Index: libgcrypt-1.10.2/cipher/chacha20.c +=================================================================== +--- libgcrypt-1.10.2.orig/cipher/chacha20.c ++++ libgcrypt-1.10.2/cipher/chacha20.c +@@ -484,6 +484,11 @@ chacha20_do_setkey (CHACHA20_context_t * + ctx->use_ppc = (features & HWF_PPC_ARCH_2_07) != 0; + # ifndef WORDS_BIGENDIAN + ctx->use_p10 = (features & HWF_PPC_ARCH_3_10) != 0; ++# ifdef ENABLE_FORCE_SOFT_HWFEATURES ++ /* HWF_PPC_ARCH_3_10 above is used as soft HW-feature indicator for P10. ++ * Actual implementation works with HWF_PPC_ARCH_3_00 also. */ ++ ctx->use_p10 |= (features & HWF_PPC_ARCH_3_00) != 0; ++# endif + # endif + #endif + #ifdef USE_S390X_VX +Index: libgcrypt-1.10.2/cipher/poly1305.c +=================================================================== +--- libgcrypt-1.10.2.orig/cipher/poly1305.c ++++ libgcrypt-1.10.2/cipher/poly1305.c +@@ -90,11 +90,19 @@ static void poly1305_init (poly1305_cont + const byte key[POLY1305_KEYLEN]) + { + POLY1305_STATE *st = &ctx->state; ++ unsigned int features = _gcry_get_hw_features (); + + #ifdef POLY1305_USE_PPC_VEC +- ctx->use_p10 = (_gcry_get_hw_features () & HWF_PPC_ARCH_3_10) != 0; ++ ctx->use_p10 = (features & HWF_PPC_ARCH_3_10) != 0; ++# ifdef ENABLE_FORCE_SOFT_HWFEATURES ++ /* HWF_PPC_ARCH_3_10 above is used as soft HW-feature indicator for P10. ++ * Actual implementation works with HWF_PPC_ARCH_3_00 also. */ ++ ctx->use_p10 |= (features & HWF_PPC_ARCH_3_00) != 0; ++# endif + #endif + ++ (void)features; ++ + ctx->leftover = 0; + + st->h[0] = 0; +Index: libgcrypt-1.10.2/cipher/rijndael.c +=================================================================== +--- libgcrypt-1.10.2.orig/cipher/rijndael.c ++++ libgcrypt-1.10.2/cipher/rijndael.c +@@ -605,6 +605,12 @@ do_setkey (RIJNDAEL_context *ctx, const + bulk_ops->xts_crypt = _gcry_aes_ppc9le_xts_crypt; + if (hwfeatures & HWF_PPC_ARCH_3_10) /* for P10 */ + bulk_ops->gcm_crypt = _gcry_aes_p10le_gcm_crypt; ++# ifdef ENABLE_FORCE_SOFT_HWFEATURES ++ /* HWF_PPC_ARCH_3_10 above is used as soft HW-feature indicator for P10. ++ * Actual implementation works with HWF_PPC_ARCH_3_00 also. */ ++ if (hwfeatures & HWF_PPC_ARCH_3_00) ++ bulk_ops->gcm_crypt = _gcry_aes_p10le_gcm_crypt; ++# endif + } + #endif + #ifdef USE_PPC_CRYPTO diff --git a/libgcrypt-rol64-redefinition.patch b/libgcrypt-rol64-redefinition.patch new file mode 100644 index 0000000..bb76b2f --- /dev/null +++ b/libgcrypt-rol64-redefinition.patch @@ -0,0 +1,16 @@ +Index: libgcrypt-1.11.0/cipher/bithelp.h +=================================================================== +--- libgcrypt-1.11.0.orig/cipher/bithelp.h ++++ libgcrypt-1.11.0/cipher/bithelp.h +@@ -35,11 +35,6 @@ static inline u32 ror(u32 x, int n) + return ( (x >> (n&(32-1))) | (x << ((32-n)&(32-1))) ); + } + +-static inline u64 rol64(u64 x, int n) +-{ +- return ( (x << (n&(64-1))) | (x >> ((64-n)&(64-1))) ); +-} +- + /* Byte swap for 32-bit and 64-bit integers. If available, use compiler + provided helpers. */ + #ifdef HAVE_BUILTIN_BSWAP32 diff --git a/libgcrypt-tests-Add-more-tests-to-tests-t-fips-service-ind.patch b/libgcrypt-tests-Add-more-tests-to-tests-t-fips-service-ind.patch new file mode 100644 index 0000000..c0058d2 --- /dev/null +++ b/libgcrypt-tests-Add-more-tests-to-tests-t-fips-service-ind.patch @@ -0,0 +1,382 @@ +From d71c88f78a4f1b72f92de90791fc6fe81a3cb861 Mon Sep 17 00:00:00 2001 +From: NIIBE Yutaka +Date: Tue, 24 Dec 2024 17:03:48 +0900 +Subject: [PATCH 17/19] tests: Add more tests to tests/t-fips-service-ind. +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* tests/t-fips-service-ind.c (check_pk_g_t_n_c, check_pk_s_v): New. +(main): Call check_pk_g_t_n_c and check_pk_s_v. + +-- + +GnuPG-bug-id: 7338 +Signed-off-by: NIIBE Yutaka +Signed-off-by: Lucas Mülling +--- + tests/t-fips-service-ind.c | 334 +++++++++++++++++++++++++++++++++++++ + 1 file changed, 334 insertions(+) + +diff --git a/tests/t-fips-service-ind.c b/tests/t-fips-service-ind.c +index 64e1e135..90d92c70 100644 +--- a/tests/t-fips-service-ind.c ++++ b/tests/t-fips-service-ind.c +@@ -40,6 +40,336 @@ static int in_fips_mode; + # include + #endif + ++/* Check gcry_pk_genkey, gcry_pk_testkey, gcry_pk_get_nbits, gcry_pk_get_curve API. */ ++static void ++check_pk_g_t_n_c (int reject) ++{ ++ static struct { ++ const char *keyparms; ++ int expect_failure; ++ } tv[] = { ++ { ++ "(genkey (ecc (curve nistp256)))", ++ 0 ++ }, ++ { /* non-compliant curve */ ++ "(genkey (ecc (curve secp256k1)))", ++ 1 ++ } ++ }; ++ int tvidx; ++ gpg_error_t err; ++ gpg_err_code_t ec; ++ ++ for (tvidx=0; tvidx < DIM(tv); tvidx++) ++ { ++ gcry_sexp_t s_kp = NULL; ++ gcry_sexp_t s_sk = NULL; ++ int nbits; ++ const char *name; ++ ++ if (verbose) ++ info ("checking gcry_pk_{genkey,testkey,get_nbits,get_curve} test %d\n", tvidx); ++ ++ err = gcry_sexp_build (&s_kp, NULL, tv[tvidx].keyparms); ++ if (err) ++ { ++ fail ("error building SEXP for test, %s: %s", ++ "keyparms", gpg_strerror (err)); ++ goto next; ++ } ++ ++ err = gcry_pk_genkey (&s_sk, s_kp); ++ if (err) ++ { ++ if (in_fips_mode && reject && tv[tvidx].expect_failure) ++ /* Here, an error is expected */ ++ ; ++ else ++ fail ("gcry_pk_genkey failed: %s", gpg_strerror (err)); ++ goto next; ++ } ++ else ++ { ++ if (in_fips_mode && reject && tv[tvidx].expect_failure) ++ { ++ fail ("gcry_pk_genkey test %d unexpectedly succeeded", tvidx); ++ goto next; ++ } ++ } ++ ++ ec = gcry_get_fips_service_indicator (); ++ if (ec == GPG_ERR_INV_OP) ++ { ++ /* libgcrypt is old, no support of the FIPS service indicator. */ ++ fail ("gcry_pk_genkey test %d unexpectedly failed to check the FIPS service indicator.\n", ++ tvidx); ++ goto next; ++ } ++ ++ if (in_fips_mode && !tv[tvidx].expect_failure && ec) ++ { ++ /* Success with the FIPS service indicator == 0 expected, but != 0. */ ++ fail ("gcry_pk_genkey test %d unexpectedly set the indicator in FIPS mode.\n", ++ tvidx); ++ goto next; ++ } ++ else if (in_fips_mode && tv[tvidx].expect_failure && !ec) ++ { ++ /* Success with the FIPS service indicator != 0 expected, but == 0. */ ++ fail ("gcry_pk_genkey test %d unexpectedly cleared the indicator in FIPS mode.\n", ++ tvidx); ++ goto next; ++ } ++ ++ err = gcry_pk_testkey (s_sk); ++ if (err) ++ { ++ fail ("gcry_pk_testkey failed for test: %s", gpg_strerror (err)); ++ goto next; ++ } ++ ++ ec = gcry_get_fips_service_indicator (); ++ if (ec == GPG_ERR_INV_OP) ++ { ++ /* libgcrypt is old, no support of the FIPS service indicator. */ ++ fail ("gcry_pk_testkey test %d unexpectedly failed to check the FIPS service indicator.\n", ++ tvidx); ++ goto next; ++ } ++ ++ if (in_fips_mode && !tv[tvidx].expect_failure && ec) ++ { ++ /* Success with the FIPS service indicator == 0 expected, but != 0. */ ++ fail ("gcry_pk_testkey test %d unexpectedly set the indicator in FIPS mode.\n", ++ tvidx); ++ goto next; ++ } ++ else if (in_fips_mode && tv[tvidx].expect_failure && !ec) ++ { ++ /* Success with the FIPS service indicator != 0 expected, but == 0. */ ++ fail ("gcry_pk_testkey test %d unexpectedly cleared the indicator in FIPS mode.\n", ++ tvidx); ++ goto next; ++ } ++ ++ nbits = gcry_pk_get_nbits (s_sk); ++ if (!nbits) ++ { ++ fail ("gcry_pk_get_nbits failed for test"); ++ goto next; ++ } ++ ++ ec = gcry_get_fips_service_indicator (); ++ if (ec == GPG_ERR_INV_OP) ++ { ++ /* libgcrypt is old, no support of the FIPS service indicator. */ ++ fail ("gcry_pk_get_nbits test %d unexpectedly failed to check the FIPS service indicator.\n", ++ tvidx); ++ goto next; ++ } ++ ++ if (in_fips_mode && !tv[tvidx].expect_failure && ec) ++ { ++ /* Success with the FIPS service indicator == 0 expected, but != 0. */ ++ fail ("gcry_pk_get_nbits test %d unexpectedly set the indicator in FIPS mode.\n", ++ tvidx); ++ goto next; ++ } ++ else if (in_fips_mode && tv[tvidx].expect_failure && !ec) ++ { ++ /* Success with the FIPS service indicator != 0 expected, but == 0. */ ++ fail ("gcry_pk_get_nbits test %d unexpectedly cleared the indicator in FIPS mode.\n", ++ tvidx); ++ goto next; ++ } ++ ++ name = gcry_pk_get_curve (s_sk, 0, NULL); ++ if (!name) ++ { ++ fail ("gcry_pk_get_curve failed for test: %s", gpg_strerror (err)); ++ goto next; ++ } ++ ++ ec = gcry_get_fips_service_indicator (); ++ if (ec == GPG_ERR_INV_OP) ++ { ++ /* libgcrypt is old, no support of the FIPS service indicator. */ ++ fail ("gcry_pk_get_curve test %d unexpectedly failed to check the FIPS service indicator.\n", ++ tvidx); ++ goto next; ++ } ++ ++ if (in_fips_mode && !tv[tvidx].expect_failure && ec) ++ { ++ /* Success with the FIPS service indicator == 0 expected, but != 0. */ ++ fail ("gcry_pk_get_curve test %d unexpectedly set the indicator in FIPS mode.\n", ++ tvidx); ++ goto next; ++ } ++ else if (in_fips_mode && tv[tvidx].expect_failure && !ec) ++ { ++ /* Success with the FIPS service indicator != 0 expected, but == 0. */ ++ fail ("gcry_pk_get_curve test %d unexpectedly cleared the indicator in FIPS mode.\n", ++ tvidx); ++ goto next; ++ } ++ ++ next: ++ gcry_sexp_release (s_kp); ++ gcry_sexp_release (s_sk); ++ } ++} ++ ++/* Check gcry_pk_sign, gcry_verify API. */ ++static void ++check_pk_s_v (int reject) ++{ ++ static struct { ++ const char *prvkey; ++ const char *pubkey; ++ int expect_failure; ++ } tv[] = { ++ { ++ "(private-key (ecc (curve nistp256)" ++ " (d #519b423d715f8b581f4fa8ee59f4771a5b44c8130b4e3eacca54a56dda72b464#)))", ++ "(public-key (ecc (curve nistp256)" ++ " (q #041ccbe91c075fc7f4f033bfa248db8fccd3565de94bbfb12f3c59ff46c271bf83" ++ "ce4014c68811f9a21a1fdb2c0e6113e06db7ca93b7404e78dc7ccd5ca89a4ca9#)))", ++ 0 ++ }, ++ { /* non-compliant curve */ ++ "(private-key (ecc (curve secp256k1)" ++ " (d #c2cdf0a8b0a83b35ace53f097b5e6e6a0a1f2d40535eff1cf434f52a43d59d8f#)))", ++ "(public-key (ecc (curve secp256k1)" ++ " (q #046fcc37ea5e9e09fec6c83e5fbd7a745e3eee81d16ebd861c9e66f55518c19798" ++ "4e9f113c07f875691df8afc1029496fc4cb9509b39dcd38f251a83359cc8b4f7#)))", ++ 1 ++ } ++ }; ++ int tvidx; ++ gpg_error_t err; ++ gpg_err_code_t ec; ++ const char *data = "(data (flags raw)" ++ "(hash sha256 #00112233445566778899AABBCCDDEEFF000102030405060708090A0B0C0D0E0F#))"; ++ gcry_sexp_t s_data = NULL; ++ ++ err = gcry_sexp_build (&s_data, NULL, data); ++ if (err) ++ { ++ fail ("error building SEXP for test, %s: %s", ++ "data", gpg_strerror (err)); ++ return; ++ } ++ ++ for (tvidx=0; tvidx < DIM(tv); tvidx++) ++ { ++ gcry_sexp_t s_pk = NULL; ++ gcry_sexp_t s_sk = NULL; ++ gcry_sexp_t s_sig= NULL; ++ ++ if (verbose) ++ info ("checking gcry_pk_{sign,verify} test %d\n", tvidx); ++ ++ err = gcry_sexp_build (&s_sk, NULL, tv[tvidx].prvkey); ++ if (err) ++ { ++ fail ("error building SEXP for test, %s: %s", ++ "sk", gpg_strerror (err)); ++ goto next; ++ } ++ ++ err = gcry_sexp_build (&s_pk, NULL, tv[tvidx].pubkey); ++ if (err) ++ { ++ fail ("error building SEXP for test, %s: %s", ++ "pk", gpg_strerror (err)); ++ goto next; ++ } ++ ++ err = gcry_pk_sign (&s_sig, s_data, s_sk); ++ if (err) ++ { ++ if (in_fips_mode && reject && tv[tvidx].expect_failure) ++ /* Here, an error is expected */ ++ ; ++ else ++ fail ("gcry_pk_sign failed: %s", gpg_strerror (err)); ++ goto next; ++ } ++ else ++ { ++ if (in_fips_mode && reject && tv[tvidx].expect_failure) ++ { ++ fail ("gcry_pk_sign test %d unexpectedly succeeded", tvidx); ++ goto next; ++ } ++ } ++ ++ ec = gcry_get_fips_service_indicator (); ++ if (ec == GPG_ERR_INV_OP) ++ { ++ /* libgcrypt is old, no support of the FIPS service indicator. */ ++ fail ("gcry_pk_sign test %d unexpectedly failed to check the FIPS service indicator.\n", ++ tvidx); ++ goto next; ++ } ++ ++ if (in_fips_mode && !tv[tvidx].expect_failure && ec) ++ { ++ /* Success with the FIPS service indicator == 0 expected, but != 0. */ ++ fail ("gcry_pk_sign test %d unexpectedly set the indicator in FIPS mode.\n", ++ tvidx); ++ goto next; ++ } ++ else if (in_fips_mode && tv[tvidx].expect_failure && !ec) ++ { ++ /* Success with the FIPS service indicator != 0 expected, but == 0. */ ++ fail ("gcry_pk_sign test %d unexpectedly cleared the indicator in FIPS mode.\n", ++ tvidx); ++ goto next; ++ } ++ ++ err = gcry_pk_verify (s_sig, s_data, s_pk); ++ if (err) ++ { ++ fail ("gcry_pk_verify failed for test: %s", gpg_strerror (err)); ++ goto next; ++ } ++ ++ ec = gcry_get_fips_service_indicator (); ++ if (ec == GPG_ERR_INV_OP) ++ { ++ /* libgcrypt is old, no support of the FIPS service indicator. */ ++ fail ("gcry_pk_verify test %d unexpectedly failed to check the FIPS service indicator.\n", ++ tvidx); ++ goto next; ++ } ++ ++ if (in_fips_mode && !tv[tvidx].expect_failure && ec) ++ { ++ /* Success with the FIPS service indicator == 0 expected, but != 0. */ ++ fail ("gcry_pk_verify test %d unexpectedly set the indicator in FIPS mode.\n", ++ tvidx); ++ goto next; ++ } ++ else if (in_fips_mode && tv[tvidx].expect_failure && !ec) ++ { ++ /* Success with the FIPS service indicator != 0 expected, but == 0. */ ++ fail ("gcry_pk_verify test %d unexpectedly cleared the indicator in FIPS mode.\n", ++ tvidx); ++ goto next; ++ } ++ ++ next: ++ gcry_sexp_release (s_sig); ++ gcry_sexp_release (s_pk); ++ gcry_sexp_release (s_sk); ++ } ++ ++ gcry_sexp_release (s_data); ++} ++ + /* Check gcry_pk_hash_sign, gcry_pk_hash_verify API. */ + static void + check_pk_hash_sign_verify (void) +@@ -1126,6 +1456,8 @@ main (int argc, char **argv) + check_mac_o_w_r_c (0); + check_cipher_o_s_e_d_c (0); + check_pk_hash_sign_verify (); ++ check_pk_s_v (0); ++ check_pk_g_t_n_c (0); + + xgcry_control ((GCRYCTL_FIPS_REJECT_NON_FIPS, + (GCRY_FIPS_FLAG_REJECT_MD_MD5 +@@ -1134,6 +1466,8 @@ main (int argc, char **argv) + check_md_o_w_r_c (1); + check_mac_o_w_r_c (1); + check_cipher_o_s_e_d_c (1); ++ check_pk_s_v (1); ++ check_pk_g_t_n_c (1); + + return !!error_count; + } +-- +2.49.0 + diff --git a/libgcrypt-tests-Allow-tests-with-USE_RSA.patch b/libgcrypt-tests-Allow-tests-with-USE_RSA.patch new file mode 100644 index 0000000..cc29fb0 --- /dev/null +++ b/libgcrypt-tests-Allow-tests-with-USE_RSA.patch @@ -0,0 +1,44 @@ +From 8404a048b7c58eb903717e09cffaa7735f7d8520 Mon Sep 17 00:00:00 2001 +From: NIIBE Yutaka +Date: Tue, 4 Mar 2025 13:29:28 +0900 +Subject: [PATCH 01/14] tests: Allow tests with !USE_RSA. +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* tests/t-fips-service-ind.c [USE_RSA] (check_pk_s_v): Ifdef-out. + +-- + +Signed-off-by: NIIBE Yutaka +Signed-off-by: Lucas Mülling +--- + tests/t-fips-service-ind.c | 5 ++++- + 1 file changed, 4 insertions(+), 1 deletion(-) + +diff --git a/tests/t-fips-service-ind.c b/tests/t-fips-service-ind.c +index 99b84c8f..a082b258 100644 +--- a/tests/t-fips-service-ind.c ++++ b/tests/t-fips-service-ind.c +@@ -290,7 +290,9 @@ check_pk_s_v (int reject) + " 00112233445566778899AABBCCDDEEFF000102030405060708090A0B0C0D0E0F" + " 00112233445566778899AABBCCDDEEFF000102030405060708090A0B0C0D0E0F#))", + 0 +- }, ++ } ++#if USE_RSA ++ , + { /* RSA with compliant hash for signing */ + "(private-key" + " (rsa" +@@ -559,6 +561,7 @@ check_pk_s_v (int reject) + " (hash sha1 #11223344556677889900AABBCCDDEEFF10203040#))\n", + 1 + } ++#endif /* USE_RSA */ + }; + int tvidx; + gpg_error_t err; +-- +2.49.0 + diff --git a/libgcrypt-tests-Update-t-fips-service-ind-using-GCRY_MD_SHA256-for-KDF-tests.patch b/libgcrypt-tests-Update-t-fips-service-ind-using-GCRY_MD_SHA256-for-KDF-tests.patch new file mode 100644 index 0000000..dd009fd --- /dev/null +++ b/libgcrypt-tests-Update-t-fips-service-ind-using-GCRY_MD_SHA256-for-KDF-tests.patch @@ -0,0 +1,106 @@ +From e5989e08a556117ec3f19f098765963358b71051 Mon Sep 17 00:00:00 2001 +From: NIIBE Yutaka +Date: Wed, 26 Feb 2025 13:51:36 +0900 +Subject: [PATCH 3/4] tests: Update t-fips-service-ind using GCRY_MD_SHA256 for + KDF tests. +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* tests/t-fips-service-ind.c (check_kdf_derive): Use GCRY_MD_SHA256. + +-- + +GnuPG-bug-id: 7338 +Signed-off-by: NIIBE Yutaka +Signed-off-by: Lucas Mülling +--- + tests/t-fips-service-ind.c | 38 +++++++++++++++++++------------------- + 1 file changed, 19 insertions(+), 19 deletions(-) + +diff --git a/tests/t-fips-service-ind.c b/tests/t-fips-service-ind.c +index bec6c27e..99b84c8f 100644 +--- a/tests/t-fips-service-ind.c ++++ b/tests/t-fips-service-ind.c +@@ -1621,13 +1621,13 @@ check_kdf_derive (void) + } tv[] = { + { + "passwordPASSWORDpassword", 24, +- GCRY_KDF_PBKDF2, GCRY_MD_SHA1, ++ GCRY_KDF_PBKDF2, GCRY_MD_SHA256, + "saltSALTsaltSALTsaltSALTsaltSALTsalt", 36, + 4096, + 25, +- "\x3d\x2e\xec\x4f\xe4\x1c\x84\x9b\x80\xc8" +- "\xd8\x36\x62\xc0\xe4\x4a\x8b\x29\x1a\x96" +- "\x4c\xf2\xf0\x70\x38", ++ "\x34\x8c\x89\xdb\xcb\xd3\x2b\x2f\x32\xd8" ++ "\x14\xb8\x11\x6e\x84\xcf\x2b\x17\x34\x7e" ++ "\xbc\x18\x00\x18\x1c", + 0 + }, + { +@@ -1644,45 +1644,45 @@ check_kdf_derive (void) + }, + { + "passwor", 7, +- GCRY_KDF_PBKDF2, GCRY_MD_SHA1, ++ GCRY_KDF_PBKDF2, GCRY_MD_SHA256, + "saltSALTsaltSALTsaltSALTsaltSALTsalt", 36, + 4096, + 25, +- "\xf4\x93\xee\x2b\xbf\x44\x0b\x9e\x64\x53" +- "\xc2\xb3\x87\xdc\x73\xf8\xfd\xe6\x97\xda" +- "\xb8\x24\xa0\x26\x50", ++ "\x2d\x72\xa9\xe5\x4e\x2f\x37\x6e\xe5\xe4" ++ "\xf5\x55\x76\xb5\xaa\x49\x73\x01\x97\x1c" ++ "\xad\x3a\x7c\xc4\xde", + 1 /* not-compliant because passphrase len is too small */ + }, + { + "passwordPASSWORDpassword", 24, +- GCRY_KDF_PBKDF2, GCRY_MD_SHA1, ++ GCRY_KDF_PBKDF2, GCRY_MD_SHA256, + "saltSALTsaltSAL", 15, + 4096, + 25, +- "\x14\x05\xa4\x2a\xf4\xa8\x12\x14\x7b\x65" +- "\x8f\xaa\xf0\x7f\x25\xe5\x0f\x0b\x2b\xb7" +- "\xcf\x8d\x29\x23\x4b", ++ "\xf7\x55\xdd\x3c\x5e\xfb\x23\x06\xa7\x85" ++ "\x94\xa7\x31\x12\x45\xcf\x5a\x4b\xdc\x09" ++ "\xee\x65\x4b\x50\x3f", + 1 /* not-compliant because salt len is too small */ + }, + { + "passwordPASSWORDpassword", 24, +- GCRY_KDF_PBKDF2, GCRY_MD_SHA1, ++ GCRY_KDF_PBKDF2, GCRY_MD_SHA256, + "saltSALTsaltSALTsaltSALTsaltSALTsalt", 36, + 999, + 25, +- "\xac\xf8\xb4\x67\x41\xc7\xf3\xd1\xa0\xc0" +- "\x08\xbe\x9b\x23\x96\x78\xbd\x93\xda\x4a" +- "\x30\xd4\xfb\xf0\x33", ++ "\x09\x3e\x1a\xd8\x63\x30\x71\x9c\x17\xcf" ++ "\xb0\x53\x3e\x1f\xc8\x51\x29\x71\x54\x28" ++ "\x5d\xf7\x8e\x41\xaa", + 1 /* not-compliant because too few iterations */ + }, + { + "passwordPASSWORDpassword", 24, +- GCRY_KDF_PBKDF2, GCRY_MD_SHA1, ++ GCRY_KDF_PBKDF2, GCRY_MD_SHA256, + "saltSALTsaltSALTsaltSALTsaltSALTsalt", 36, + 4096, + 13, +- "\x3d\x2e\xec\x4f\xe4\x1c\x84\x9b\x80\xc8" +- "\xd8\x36\x62", ++ "\x34\x8c\x89\xdb\xcb\xd3\x2b\x2f\x32\xd8" ++ "\x14\xb8\x11", + 1 /* not-compliant because key size too small */ + }, + { +-- +2.49.0 + diff --git a/libgcrypt-tests-fips-Add-gcry_cipher_open-tests.patch b/libgcrypt-tests-fips-Add-gcry_cipher_open-tests.patch new file mode 100644 index 0000000..0e0f7e5 --- /dev/null +++ b/libgcrypt-tests-fips-Add-gcry_cipher_open-tests.patch @@ -0,0 +1,199 @@ +From cfd2d2f41ad4aef40d83f8f7237d1da13c7e240c Mon Sep 17 00:00:00 2001 +From: NIIBE Yutaka +Date: Tue, 17 Dec 2024 10:33:33 +0900 +Subject: [PATCH 09/19] tests,fips: Add gcry_cipher_open tests. +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* tests/t-fips-service-ind.c (check_cipher_o_s_e_d_c): New. +(main): Call check_cipher_o_s_e_d_c. + +-- + +GnuPG-bug-id: 7338 +Signed-off-by: NIIBE Yutaka +Signed-off-by: Lucas Mülling +--- + tests/t-fips-service-ind.c | 152 ++++++++++++++++++++++++++++++++++++- + 1 file changed, 151 insertions(+), 1 deletion(-) + +Index: libgcrypt-1.11.0/tests/t-fips-service-ind.c +=================================================================== +--- libgcrypt-1.11.0.orig/tests/t-fips-service-ind.c ++++ libgcrypt-1.11.0/tests/t-fips-service-ind.c +@@ -31,6 +31,7 @@ + + #include "t-common.h" + static int in_fips_mode; ++#define MAX_DATA_LEN 1040 + + /* Mingw requires us to include windows.h after winsock2.h which is + included by gcrypt.h. */ +@@ -38,6 +39,154 @@ static int in_fips_mode; + # include + #endif + ++/* Check gcry_cipher_open, gcry_cipher_setkey, gcry_cipher_encrypt, ++ gcry_cipher_decrypt, gcry_cipher_close API. */ ++static void ++check_cipher_o_s_e_d_c (void) ++{ ++ static struct { ++ int algo; ++ const char *key; ++ int keylen; ++ const char *expect; ++ int expect_failure; ++ unsigned int flags; ++ } tv[] = { ++#if USE_DES ++ { GCRY_CIPHER_3DES, ++ "\xe3\x34\x7a\x6b\x0b\xc1\x15\x2c\x64\x2a\x25\xcb\xd3\xbc\x31\xab" ++ "\xfb\xa1\x62\xa8\x1f\x19\x7c\x15", 24, ++ "\x3f\x1a\xb8\x83\x18\x8b\xb5\x97", 1 }, ++ { GCRY_CIPHER_3DES, ++ "\xe3\x34\x7a\x6b\x0b\xc1\x15\x2c\x64\x2a\x25\xcb\xd3\xbc\x31\xab" ++ "\xfb\xa1\x62\xa8\x1f\x19\x7c\x15", 24, ++ "\x3f\x1a\xb8\x83\x18\x8b\xb5\x97", ++ 1, GCRY_CIPHER_FLAG_REJECT_NON_FIPS }, ++#endif ++ { GCRY_CIPHER_AES, ++ "\x2b\x7e\x15\x16\x28\xae\xd2\xa6\xab\xf7\x15\x88\x09\xcf\x4f\x3c", 16, ++ "\x5c\x71\xd8\x5d\x26\x5e\xcd\xb5\x95\x40\x41\xab\xff\x25\x6f\xd1" } ++ }; ++ const char *pt = "Shohei Ohtani 2024: 54 HR, 59 SB"; ++ int ptlen; ++ int tvidx; ++ unsigned char out[MAX_DATA_LEN]; ++ gpg_error_t err; ++ ++ ptlen = strlen (pt); ++ assert (ptlen == 32); ++ for (tvidx=0; tvidx < DIM(tv); tvidx++) ++ { ++ gpg_err_code_t ec; ++ gcry_cipher_hd_t h; ++ size_t blklen; ++ ++ if (verbose) ++ fprintf (stderr, "checking gcry_cipher_open test %d\n", ++ tvidx); ++ ++ blklen = gcry_cipher_get_algo_blklen (tv[tvidx].algo); ++ assert (blklen != 0); ++ assert (blklen <= ptlen); ++ assert (blklen <= DIM (out)); ++ err = gcry_cipher_open (&h, tv[tvidx].algo, GCRY_CIPHER_MODE_ECB, ++ tv[tvidx].flags); ++ if (err) ++ { ++ if (in_fips_mode && (tv[tvidx].flags & GCRY_CIPHER_FLAG_REJECT_NON_FIPS) ++ && tv[tvidx].expect_failure) ++ /* Here, an error is expected */ ++ ; ++ else ++ fail ("gcry_cipher_open test %d unexpectedly failed: %s\n", ++ tvidx, gpg_strerror (err)); ++ continue; ++ } ++ else ++ { ++ if (in_fips_mode && (tv[tvidx].flags & GCRY_CIPHER_FLAG_REJECT_NON_FIPS) ++ && tv[tvidx].expect_failure) ++ /* This case, an error is expected, but we observed success */ ++ fail ("gcry_cipher_open test %d unexpectedly succeeded\n", tvidx); ++ } ++ ++ ec = gcry_get_fips_service_indicator (); ++ if (ec == GPG_ERR_INV_OP) ++ { ++ /* libgcrypt is old, no support of the FIPS service indicator. */ ++ fail ("gcry_cipher_open test %d unexpectedly failed to check the FIPS service indicator.\n", ++ tvidx); ++ continue; ++ } ++ ++ if (in_fips_mode && !tv[tvidx].expect_failure && ec) ++ { ++ /* Success with the FIPS service indicator == 0 expected, but != 0. */ ++ fail ("gcry_cipher_open test %d unexpectedly set the indicator in FIPS mode.\n", ++ tvidx); ++ continue; ++ } ++ else if (in_fips_mode && tv[tvidx].expect_failure && !ec) ++ { ++ /* Success with the FIPS service indicator != 0 expected, but == 0. */ ++ fail ("gcry_cipher_open test %d unexpectedly cleared the indicator in FIPS mode.\n", ++ tvidx); ++ continue; ++ } ++ ++ err = gcry_cipher_setkey (h, tv[tvidx].key, tv[tvidx].keylen); ++ if (err) ++ { ++ fail ("gcry_cipher_setkey %d failed: %s\n", tvidx, ++ gpg_strerror (err)); ++ gcry_cipher_close (h); ++ continue; ++ } ++ ++ err = gcry_cipher_encrypt (h, out, MAX_DATA_LEN, pt, blklen); ++ if (err) ++ { ++ fail ("gcry_cipher_encrypt %d failed: %s\n", tvidx, ++ gpg_strerror (err)); ++ gcry_cipher_close (h); ++ continue; ++ } ++ ++ if (memcmp (out, tv[tvidx].expect, blklen)) ++ { ++ int i; ++ ++ fail ("gcry_cipher_open test %d failed: encryption mismatch\n", tvidx); ++ fputs ("got:", stderr); ++ for (i=0; i < blklen; i++) ++ fprintf (stderr, " %02x", out[i]); ++ putc ('\n', stderr); ++ } ++ ++ err = gcry_cipher_decrypt (h, out, blklen, NULL, 0); ++ if (err) ++ { ++ fail ("gcry_cipher_decrypt %d failed: %s\n", tvidx, ++ gpg_strerror (err)); ++ gcry_cipher_close (h); ++ continue; ++ } ++ ++ if (memcmp (out, pt, blklen)) ++ { ++ int i; ++ ++ fail ("gcry_cipher_open test %d failed: decryption mismatch\n", tvidx); ++ fputs ("got:", stderr); ++ for (i=0; i < blklen; i++) ++ fprintf (stderr, " %02x", out[i]); ++ putc ('\n', stderr); ++ } ++ ++ gcry_cipher_close (h); ++ } ++} ++ + /* Check gcry_mac_open, gcry_mac_write, gcry_mac_write, gcry_mac_read, + gcry_mac_close API. */ + static void +@@ -651,9 +800,10 @@ main (int argc, char **argv) + xgcry_control ((GCRYCTL_SET_DEBUG_FLAGS, 1u , 0)); + + check_digests (); ++ check_kdf_derive (); + check_md_o_w_r_c (); + check_mac_o_w_r_c (); +- check_kdf_derive (); ++ check_cipher_o_s_e_d_c (); + + return !!error_count; + } diff --git a/libgcrypt-tests-fips-Add-gcry_mac_open-tests.patch b/libgcrypt-tests-fips-Add-gcry_mac_open-tests.patch new file mode 100644 index 0000000..c2e3ed4 --- /dev/null +++ b/libgcrypt-tests-fips-Add-gcry_mac_open-tests.patch @@ -0,0 +1,206 @@ +From c4f75014cb8af732f87c02fe7c2e7a488fe71c6d Mon Sep 17 00:00:00 2001 +From: NIIBE Yutaka +Date: Mon, 16 Dec 2024 14:09:10 +0900 +Subject: [PATCH 06/19] tests,fips: Add gcry_mac_open tests. +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* tests/t-digest.c (check_mac_o_w_r_c): New. +(main): Call check_mac_o_w_r_c. + +-- + +GnuPG-bug-id: 7338 +Signed-off-by: NIIBE Yutaka +Signed-off-by: Lucas Mülling +--- + tests/t-digest.c | 168 +++++++++++++++++++++++++++++++++++++++++++++++ + 1 file changed, 168 insertions(+) + +Index: libgcrypt-1.11.0/tests/t-digest.c +=================================================================== +--- libgcrypt-1.11.0.orig/tests/t-digest.c ++++ libgcrypt-1.11.0/tests/t-digest.c +@@ -38,6 +38,173 @@ static int in_fips_mode; + # include + #endif + ++/* Check gcry_mac_open, gcry_mac_write, gcry_mac_write, gcry_mac_read, ++ gcry_mac_close API. */ ++static void ++check_mac_o_w_r_c (void) ++{ ++ static struct { ++ int algo; ++ const char *data; ++ int datalen; ++ const char *key; ++ int keylen; ++ const char *expect; ++ int expect_failure; ++ unsigned int flags; ++ } tv[] = { ++#if USE_MD5 ++ { GCRY_MAC_HMAC_MD5, "hmac input abc", 14, "hmac key input", 14, ++ "\x0d\x72\xd0\x60\xaf\x34\xf2\xca\x33\x58\xa9\xcc\xd3\x5a\xac\xb5", 1 }, ++ { GCRY_MAC_HMAC_MD5, "hmac input abc", 14, "hmac key input", 14, ++ "\x0d\x72\xd0\x60\xaf\x34\xf2\xca\x33\x58\xa9\xcc\xd3\x5a\xac\xb5", 1, ++ GCRY_MAC_FLAG_REJECT_NON_FIPS }, ++#endif ++#if USE_SHA1 ++ { GCRY_MAC_HMAC_SHA1, "hmac input abc", 14, "hmac key input", 14, ++ "\xc9\x62\x9d\x16\x0f\xc2\xc4\xcd\x38\xac\x3a\x00\xdc\x29\x61\x03" ++ "\x69\x50\xd7\x3a" }, ++#endif ++ { GCRY_MAC_HMAC_SHA256, "hmac input abc", 14, "hmac key input", 14, ++ "\x6a\xda\x4d\xd5\xf3\xa7\x32\x9d\xd2\x55\xc0\x7f\xe6\x0a\x93\xb8" ++ "\x7a\x6e\x76\x68\x46\x34\x67\xf9\xc2\x29\xb8\x24\x2e\xc8\xe3\xb4" }, ++ { GCRY_MAC_HMAC_SHA384, "hmac input abc", 14, "hmac key input", 14, ++ "\xc6\x59\x14\x4a\xac\x4d\xd5\x62\x09\x2c\xbd\x5e\xbf\x41\x94\xf9" ++ "\xa4\x78\x18\x46\xfa\xd6\xd1\x12\x90\x4f\x65\xd4\xe8\x44\xcc\xcc" ++ "\x3d\xcc\xf3\xe4\x27\xd8\xf0\xff\x01\xe8\x70\xcd\xfb\xfa\x24\x45" }, ++ { GCRY_MAC_HMAC_SHA512, "hmac input abc", 14, "hmac key input", 14, ++ "\xfa\x77\x49\x49\x24\x3d\x7e\x03\x1b\x0e\xd1\xfc\x20\x81\xcf\x95" ++ "\x81\x21\xa4\x4f\x3b\xe5\x69\x9a\xe6\x67\x27\x10\xbc\x62\xc7\xb3" ++ "\xb3\xcf\x2b\x1e\xda\x20\x48\x25\xc5\x6a\x52\xc7\xc9\xd9\x77\xf6" ++ "\xf6\x49\x9d\x70\xe6\x04\x33\xab\x6a\xdf\x7e\x9f\xf4\xd1\x59\x6e" }, ++ { GCRY_MAC_HMAC_SHA3_256, "hmac input abc", 14, "hmac key input", 14, ++ "\x2b\xe9\x02\x92\xc2\x37\xbe\x91\x06\xbf\x9c\x8e\x7b\xa3\xf2\xfc" ++ "\x68\x10\x8a\x71\xd5\xc7\x84\x3c\x0b\xdd\x7d\x1e\xdf\xa5\xf6\xa7" }, ++ { GCRY_MAC_HMAC_SHA3_384, "hmac input abc", 14, "hmac key input", 14, ++ "\x9f\x6b\x9f\x49\x95\x57\xed\x33\xb1\xe7\x22\x2f\xda\x40\x68\xb0" ++ "\x28\xd2\xdb\x6f\x73\x3c\x2e\x2b\x29\x51\x64\x53\xc4\xc5\x63\x8a" ++ "\x98\xca\x78\x1a\xe7\x1b\x7d\xf6\xbf\xf3\x6a\xf3\x2a\x0e\xa0\x5b" }, ++ { GCRY_MAC_HMAC_SHA3_512, "hmac input abc", 14, "hmac key input", 14, ++ "\xf3\x19\x70\x54\x25\xdf\x0f\xde\x09\xe9\xea\x3b\x34\x67\x14\x32" ++ "\xe6\xe2\x58\x9d\x76\x38\xa4\xbd\x90\x35\x4c\x07\x7c\xa3\xdb\x23" ++ "\x3c\x78\x0c\x45\xee\x8e\x39\xd5\x81\xd8\x5c\x13\x20\x40\xba\x34" ++ "\xd0\x0b\x75\x31\x38\x4b\xe7\x74\x87\xa9\xc5\x68\x7f\xbc\x19\xa1" } ++#if USE_RMD160 ++ , ++ { GCRY_MAC_HMAC_RMD160, "hmac input abc", 14, "hmac key input", 14, ++ "\xf2\x45\x5c\x7e\x48\x1a\xbb\xe5\xe8\xec\x40\xa4\x1b\x89\x26\x2b" ++ "\xdc\xa1\x79\x59", 1 } ++#endif ++ }; ++ int tvidx; ++ unsigned char mac[64]; ++ int expectlen; ++ gpg_error_t err; ++ size_t buflen; ++ ++ for (tvidx=0; tvidx < DIM(tv); tvidx++) ++ { ++ gpg_err_code_t ec; ++ gcry_mac_hd_t h; ++ ++ if (verbose) ++ fprintf (stderr, "checking gcry_mac_open test %d\n", ++ tvidx); ++ ++ expectlen = gcry_mac_get_algo_maclen (tv[tvidx].algo); ++ assert (expectlen != 0); ++ assert (expectlen <= DIM (mac)); ++ err = gcry_mac_open (&h, tv[tvidx].algo, tv[tvidx].flags, NULL); ++ if (err) ++ { ++ if (in_fips_mode && (tv[tvidx].flags & GCRY_MAC_FLAG_REJECT_NON_FIPS) ++ && tv[tvidx].expect_failure) ++ /* Here, an error is expected */ ++ ; ++ else ++ fail ("gcry_mac_open test %d unexpectedly failed: %s\n", ++ tvidx, gpg_strerror (err)); ++ continue; ++ } ++ else ++ { ++ if (in_fips_mode && (tv[tvidx].flags & GCRY_MAC_FLAG_REJECT_NON_FIPS) ++ && tv[tvidx].expect_failure) ++ /* This case, an error is expected, but we observed success */ ++ fail ("gcry_mac_open test %d unexpectedly succeeded\n", tvidx); ++ } ++ ++ ++ ec = gcry_get_fips_service_indicator (); ++ if (ec == GPG_ERR_INV_OP) ++ { ++ /* libgcrypt is old, no support of the FIPS service indicator. */ ++ fail ("gcry_mac_open test %d unexpectedly failed to check the FIPS service indicator.\n", ++ tvidx); ++ continue; ++ } ++ ++ if (in_fips_mode && !tv[tvidx].expect_failure && ec) ++ { ++ /* Success with the FIPS service indicator == 0 expected, but != 0. */ ++ fail ("gcry_mac_open test %d unexpectedly set the indicator in FIPS mode.\n", ++ tvidx); ++ continue; ++ } ++ else if (in_fips_mode && tv[tvidx].expect_failure && !ec) ++ { ++ /* Success with the FIPS service indicator != 0 expected, but == 0. */ ++ fail ("gcry_mac_open test %d unexpectedly cleared the indicator in FIPS mode.\n", ++ tvidx); ++ continue; ++ } ++ ++ err = gcry_mac_setkey (h, tv[tvidx].key, tv[tvidx].keylen); ++ if (err) ++ { ++ fail ("gcry_mac_setkey test %d unexpectedly failed: %s\n", ++ tvidx, gpg_strerror (err)); ++ gcry_mac_close (h); ++ continue; ++ } ++ ++ err = gcry_mac_write (h, tv[tvidx].data, tv[tvidx].datalen); ++ if (err) ++ { ++ fail ("gcry_mac_write test %d unexpectedly failed: %s\n", ++ tvidx, gpg_strerror (err)); ++ gcry_mac_close (h); ++ continue; ++ } ++ ++ buflen = expectlen; ++ err = gcry_mac_read (h, mac, &buflen); ++ if (err || buflen != expectlen) ++ { ++ fail ("gcry_mac_read test %d unexpectedly failed: %s\n", ++ tvidx, gpg_strerror (err)); ++ gcry_mac_close (h); ++ continue; ++ } ++ ++ if (memcmp (mac, tv[tvidx].expect, expectlen)) ++ { ++ int i; ++ ++ fail ("gcry_mac_open test %d failed: mismatch\n", tvidx); ++ fputs ("got:", stderr); ++ for (i=0; i < expectlen; i++) ++ fprintf (stderr, " %02x", mac[i]); ++ putc ('\n', stderr); ++ } ++ ++ gcry_mac_close (h); ++ } ++} ++ ++ ++/* Check gcry_md_open, gcry_md_write, gcry_md_write, gcry_md_read, ++ gcry_md_close API. */ + static void + check_md_o_w_r_c (void) + { +@@ -327,6 +494,7 @@ main (int argc, char **argv) + + check_digests (); + check_md_o_w_r_c (); ++ check_mac_o_w_r_c (); + + return !!error_count; + } diff --git a/libgcrypt-tests-fips-Move-KDF-tests-to-t-fips-service-ind.patch b/libgcrypt-tests-fips-Move-KDF-tests-to-t-fips-service-ind.patch new file mode 100644 index 0000000..7adbac5 --- /dev/null +++ b/libgcrypt-tests-fips-Move-KDF-tests-to-t-fips-service-ind.patch @@ -0,0 +1,375 @@ +From b59bde31ded9e829e2a53ddb8c533bf35a144972 Mon Sep 17 00:00:00 2001 +From: NIIBE Yutaka +Date: Mon, 16 Dec 2024 14:21:06 +0900 +Subject: [PATCH 08/19] tests,fips: Move KDF tests to t-fips-service-ind. +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* tests/t-fips-service-ind.c (check_kdf_derive): Move from... +* tests/t-kdf.c (check_fips_gcry_kdf_derive): ... here. + +-- + +GnuPG-bug-id: 7338 +Signed-off-by: NIIBE Yutaka +Signed-off-by: Lucas Mülling +--- + tests/t-fips-service-ind.c | 159 +++++++++++++++++++++++++++++++++++++ + tests/t-kdf.c | 159 ------------------------------------- + 2 files changed, 159 insertions(+), 159 deletions(-) + +Index: libgcrypt-1.11.0/tests/t-fips-service-ind.c +=================================================================== +--- libgcrypt-1.11.0.orig/tests/t-fips-service-ind.c ++++ libgcrypt-1.11.0/tests/t-fips-service-ind.c +@@ -439,6 +439,164 @@ check_digests (void) + } + + ++ ++static void ++check_kdf_derive (void) ++{ ++ static struct { ++ const char *p; /* Passphrase. */ ++ size_t plen; /* Length of P. */ ++ int algo; ++ int subalgo; ++ const char *salt; ++ size_t saltlen; ++ unsigned long iterations; ++ int dklen; /* Requested key length. */ ++ const char *dk; /* Derived key. */ ++ int expect_failure; ++ } tv[] = { ++ { ++ "passwordPASSWORDpassword", 24, ++ GCRY_KDF_PBKDF2, GCRY_MD_SHA1, ++ "saltSALTsaltSALTsaltSALTsaltSALTsalt", 36, ++ 4096, ++ 25, ++ "\x3d\x2e\xec\x4f\xe4\x1c\x84\x9b\x80\xc8" ++ "\xd8\x36\x62\xc0\xe4\x4a\x8b\x29\x1a\x96" ++ "\x4c\xf2\xf0\x70\x38", ++ 0 ++ }, ++ { ++ "pleaseletmein", 13, ++ GCRY_KDF_SCRYPT, 16384, ++ "SodiumChloride", 14, ++ 1, ++ 64, ++ "\x70\x23\xbd\xcb\x3a\xfd\x73\x48\x46\x1c\x06\xcd\x81\xfd\x38\xeb" ++ "\xfd\xa8\xfb\xba\x90\x4f\x8e\x3e\xa9\xb5\x43\xf6\x54\x5d\xa1\xf2" ++ "\xd5\x43\x29\x55\x61\x3f\x0f\xcf\x62\xd4\x97\x05\x24\x2a\x9a\xf9" ++ "\xe6\x1e\x85\xdc\x0d\x65\x1e\x40\xdf\xcf\x01\x7b\x45\x57\x58\x87", ++ 1 /* not-compliant because unallowed algo */ ++ }, ++ { ++ "passwor", 7, ++ GCRY_KDF_PBKDF2, GCRY_MD_SHA1, ++ "saltSALTsaltSALTsaltSALTsaltSALTsalt", 36, ++ 4096, ++ 25, ++ "\xf4\x93\xee\x2b\xbf\x44\x0b\x9e\x64\x53" ++ "\xc2\xb3\x87\xdc\x73\xf8\xfd\xe6\x97\xda" ++ "\xb8\x24\xa0\x26\x50", ++ 1 /* not-compliant because passphrase len is too small */ ++ }, ++ { ++ "passwordPASSWORDpassword", 24, ++ GCRY_KDF_PBKDF2, GCRY_MD_SHA1, ++ "saltSALTsaltSAL", 15, ++ 4096, ++ 25, ++ "\x14\x05\xa4\x2a\xf4\xa8\x12\x14\x7b\x65" ++ "\x8f\xaa\xf0\x7f\x25\xe5\x0f\x0b\x2b\xb7" ++ "\xcf\x8d\x29\x23\x4b", ++ 1 /* not-compliant because salt len is too small */ ++ }, ++ { ++ "passwordPASSWORDpassword", 24, ++ GCRY_KDF_PBKDF2, GCRY_MD_SHA1, ++ "saltSALTsaltSALTsaltSALTsaltSALTsalt", 36, ++ 999, ++ 25, ++ "\xac\xf8\xb4\x67\x41\xc7\xf3\xd1\xa0\xc0" ++ "\x08\xbe\x9b\x23\x96\x78\xbd\x93\xda\x4a" ++ "\x30\xd4\xfb\xf0\x33", ++ 1 /* not-compliant because too few iterations */ ++ }, ++ { ++ "passwordPASSWORDpassword", 24, ++ GCRY_KDF_PBKDF2, GCRY_MD_SHA1, ++ "saltSALTsaltSALTsaltSALTsaltSALTsalt", 36, ++ 4096, ++ 13, ++ "\x3d\x2e\xec\x4f\xe4\x1c\x84\x9b\x80\xc8" ++ "\xd8\x36\x62", ++ 1 /* not-compliant because key size too small */ ++ }, ++ { ++ "passwordPASSWORDpassword", 24, ++ GCRY_KDF_PBKDF2, GCRY_MD_BLAKE2B_512, ++ "saltSALTsaltSALTsaltSALTsaltSALTsalt", 36, ++ 4096, ++ 60, ++ "\xa4\x6b\x53\x35\xdb\xdd\xa3\xd2\x5d\x19\xbb\x11\xfe\xdd\xd9\x9e" ++ "\x45\x2a\x7c\x34\x47\x41\x98\xca\x31\x74\xb6\x34\x22\xac\x83\xb0" ++ "\x38\x6e\xf5\x93\x0f\xf5\x16\x46\x0b\x97\xdc\x6c\x27\x5b\xe7\x25" ++ "\xc2\xcb\xec\x50\x02\xc6\x52\x8b\x34\x68\x53\x65", ++ 1 /* not-compliant because subalgo is not the one of approved */ ++ } ++ }; ++ ++ int tvidx; ++ gpg_error_t err; ++ unsigned char outbuf[100]; ++ int i; ++ ++ for (tvidx=0; tvidx < DIM(tv); tvidx++) ++ { ++ if (verbose) ++ fprintf (stderr, "checking gcry_kdf_derive test vector %d algo %d for FIPS\n", ++ tvidx, tv[tvidx].algo); ++ assert (tv[tvidx].dklen <= sizeof outbuf); ++ err = gcry_kdf_derive (tv[tvidx].p, tv[tvidx].plen, ++ tv[tvidx].algo, tv[tvidx].subalgo, ++ tv[tvidx].salt, tv[tvidx].saltlen, ++ tv[tvidx].iterations, tv[tvidx].dklen, outbuf); ++ ++ if (err) ++ { ++ fail ("gcry_kdf_derive test %d unexpectedly returned an error in FIPS mode: %s\n", ++ tvidx, gpg_strerror (err)); ++ } ++ else ++ { ++ gpg_err_code_t ec; ++ ++ ec = gcry_get_fips_service_indicator (); ++ if (ec == GPG_ERR_INV_OP) ++ { ++ /* libgcrypt is old, no support of the FIPS service indicator. */ ++ fail ("gcry_kdf_derive test %d unexpectedly failed to check the FIPS service indicator.\n", ++ tvidx); ++ continue; ++ } ++ ++ if (!tv[tvidx].expect_failure && ec) ++ { ++ /* Success with the FIPS service indicator == 0 expected, but != 0. */ ++ fail ("gcry_kdf_derive test %d unexpectedly set the indicator in FIPS mode.\n", ++ tvidx); ++ continue; ++ } ++ else if (tv[tvidx].expect_failure && !ec && in_fips_mode) ++ { ++ /* Success with the FIPS service indicator != 0 expected, but == 0. */ ++ fail ("gcry_kdf_derive test %d unexpectedly cleared the indicator in FIPS mode.\n", ++ tvidx); ++ continue; ++ } ++ ++ if (memcmp (outbuf, tv[tvidx].dk, tv[tvidx].dklen)) ++ { ++ fail ("gcry_kdf_derive test %d failed: mismatch\n", tvidx); ++ fputs ("got:", stderr); ++ for (i=0; i < tv[tvidx].dklen; i++) ++ fprintf (stderr, " %02x", outbuf[i]); ++ putc ('\n', stderr); ++ } ++ } ++ } ++} ++ ++ + int + main (int argc, char **argv) + { +@@ -495,6 +653,7 @@ main (int argc, char **argv) + check_digests (); + check_md_o_w_r_c (); + check_mac_o_w_r_c (); ++ check_kdf_derive (); + + return !!error_count; + } +Index: libgcrypt-1.11.0/tests/t-kdf.c +=================================================================== +--- libgcrypt-1.11.0.orig/tests/t-kdf.c ++++ libgcrypt-1.11.0/tests/t-kdf.c +@@ -1927,163 +1927,6 @@ check_fips_indicators (void) + } + + +-static void +-check_fips_gcry_kdf_derive (void) +-{ +- static struct { +- const char *p; /* Passphrase. */ +- size_t plen; /* Length of P. */ +- int algo; +- int subalgo; +- const char *salt; +- size_t saltlen; +- unsigned long iterations; +- int dklen; /* Requested key length. */ +- const char *dk; /* Derived key. */ +- int expect_failure; +- } tv[] = { +- { +- "passwordPASSWORDpassword", 24, +- GCRY_KDF_PBKDF2, GCRY_MD_SHA1, +- "saltSALTsaltSALTsaltSALTsaltSALTsalt", 36, +- 4096, +- 25, +- "\x3d\x2e\xec\x4f\xe4\x1c\x84\x9b\x80\xc8" +- "\xd8\x36\x62\xc0\xe4\x4a\x8b\x29\x1a\x96" +- "\x4c\xf2\xf0\x70\x38", +- 0 +- }, +- { +- "pleaseletmein", 13, +- GCRY_KDF_SCRYPT, 16384, +- "SodiumChloride", 14, +- 1, +- 64, +- "\x70\x23\xbd\xcb\x3a\xfd\x73\x48\x46\x1c\x06\xcd\x81\xfd\x38\xeb" +- "\xfd\xa8\xfb\xba\x90\x4f\x8e\x3e\xa9\xb5\x43\xf6\x54\x5d\xa1\xf2" +- "\xd5\x43\x29\x55\x61\x3f\x0f\xcf\x62\xd4\x97\x05\x24\x2a\x9a\xf9" +- "\xe6\x1e\x85\xdc\x0d\x65\x1e\x40\xdf\xcf\x01\x7b\x45\x57\x58\x87", +- 1 /* not-compliant because unallowed algo */ +- }, +- { +- "passwor", 7, +- GCRY_KDF_PBKDF2, GCRY_MD_SHA1, +- "saltSALTsaltSALTsaltSALTsaltSALTsalt", 36, +- 4096, +- 25, +- "\xf4\x93\xee\x2b\xbf\x44\x0b\x9e\x64\x53" +- "\xc2\xb3\x87\xdc\x73\xf8\xfd\xe6\x97\xda" +- "\xb8\x24\xa0\x26\x50", +- 1 /* not-compliant because passphrase len is too small */ +- }, +- { +- "passwordPASSWORDpassword", 24, +- GCRY_KDF_PBKDF2, GCRY_MD_SHA1, +- "saltSALTsaltSAL", 15, +- 4096, +- 25, +- "\x14\x05\xa4\x2a\xf4\xa8\x12\x14\x7b\x65" +- "\x8f\xaa\xf0\x7f\x25\xe5\x0f\x0b\x2b\xb7" +- "\xcf\x8d\x29\x23\x4b", +- 1 /* not-compliant because salt len is too small */ +- }, +- { +- "passwordPASSWORDpassword", 24, +- GCRY_KDF_PBKDF2, GCRY_MD_SHA1, +- "saltSALTsaltSALTsaltSALTsaltSALTsalt", 36, +- 999, +- 25, +- "\xac\xf8\xb4\x67\x41\xc7\xf3\xd1\xa0\xc0" +- "\x08\xbe\x9b\x23\x96\x78\xbd\x93\xda\x4a" +- "\x30\xd4\xfb\xf0\x33", +- 1 /* not-compliant because too few iterations */ +- }, +- { +- "passwordPASSWORDpassword", 24, +- GCRY_KDF_PBKDF2, GCRY_MD_SHA1, +- "saltSALTsaltSALTsaltSALTsaltSALTsalt", 36, +- 4096, +- 13, +- "\x3d\x2e\xec\x4f\xe4\x1c\x84\x9b\x80\xc8" +- "\xd8\x36\x62", +- 1 /* not-compliant because key size too small */ +- }, +- { +- "passwordPASSWORDpassword", 24, +- GCRY_KDF_PBKDF2, GCRY_MD_BLAKE2B_512, +- "saltSALTsaltSALTsaltSALTsaltSALTsalt", 36, +- 4096, +- 60, +- "\xa4\x6b\x53\x35\xdb\xdd\xa3\xd2\x5d\x19\xbb\x11\xfe\xdd\xd9\x9e" +- "\x45\x2a\x7c\x34\x47\x41\x98\xca\x31\x74\xb6\x34\x22\xac\x83\xb0" +- "\x38\x6e\xf5\x93\x0f\xf5\x16\x46\x0b\x97\xdc\x6c\x27\x5b\xe7\x25" +- "\xc2\xcb\xec\x50\x02\xc6\x52\x8b\x34\x68\x53\x65", +- 1 /* not-compliant because subalgo is not the one of approved */ +- } +- }; +- +- int tvidx; +- gpg_error_t err; +- unsigned char outbuf[100]; +- int i; +- +- for (tvidx=0; tvidx < DIM(tv); tvidx++) +- { +- if (verbose) +- fprintf (stderr, "checking gcry_kdf_derive test vector %d algo %d for FIPS\n", +- tvidx, tv[tvidx].algo); +- assert (tv[tvidx].dklen <= sizeof outbuf); +- err = gcry_kdf_derive (tv[tvidx].p, tv[tvidx].plen, +- tv[tvidx].algo, tv[tvidx].subalgo, +- tv[tvidx].salt, tv[tvidx].saltlen, +- tv[tvidx].iterations, tv[tvidx].dklen, outbuf); +- +- if (err) +- { +- fail ("gcry_kdf_derive test %d unexpectedly returned an error in FIPS mode: %s\n", +- tvidx, gpg_strerror (err)); +- } +- else +- { +- gpg_err_code_t ec; +- +- ec = gcry_get_fips_service_indicator (); +- if (ec == GPG_ERR_INV_OP) +- { +- /* libgcrypt is old, no support of the FIPS service indicator. */ +- fail ("gcry_kdf_derive test %d unexpectedly failed to check the FIPS service indicator.\n", +- tvidx); +- continue; +- } +- +- if (!tv[tvidx].expect_failure && ec) +- { +- /* Success with the FIPS service indicator == 0 expected, but != 0. */ +- fail ("gcry_kdf_derive test %d unexpectedly set the indicator in FIPS mode.\n", +- tvidx); +- continue; +- } +- else if (tv[tvidx].expect_failure && !ec) +- { +- /* Success with the FIPS service indicator != 0 expected, but == 0. */ +- fail ("gcry_kdf_derive test %d unexpectedly cleared the indicator in FIPS mode.\n", +- tvidx); +- continue; +- } +- +- if (memcmp (outbuf, tv[tvidx].dk, tv[tvidx].dklen)) +- { +- fail ("gcry_kdf_derive test %d failed: mismatch\n", tvidx); +- fputs ("got:", stderr); +- for (i=0; i < tv[tvidx].dklen; i++) +- fprintf (stderr, " %02x", outbuf[i]); +- putc ('\n', stderr); +- } +- } +- } +-} +- +- + int + main (int argc, char **argv) + { +@@ -2166,8 +2009,6 @@ main (int argc, char **argv) + check_hkdf (); + if (in_fips_mode) + check_fips_indicators (); +- if (in_fips_mode) +- check_fips_gcry_kdf_derive (); + } + + return error_count ? 1 : 0; diff --git a/libgcrypt-tests-fips-Rename-t-fips-service-ind.patch b/libgcrypt-tests-fips-Rename-t-fips-service-ind.patch new file mode 100644 index 0000000..bb32094 --- /dev/null +++ b/libgcrypt-tests-fips-Rename-t-fips-service-ind.patch @@ -0,0 +1,60 @@ +From 132f346232b33fe41ffee3b3870ec189626676e7 Mon Sep 17 00:00:00 2001 +From: NIIBE Yutaka +Date: Mon, 16 Dec 2024 14:14:24 +0900 +Subject: [PATCH 07/19] tests,fips: Rename t-fips-service-ind. +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* tests/t-fips-service-ind.c: Rename from t-digest.c. +* tests/Makefile.am (tests_bin): Follow the change. + +-- + +GnuPG-bug-id: 7338 +Signed-off-by: NIIBE Yutaka +Signed-off-by: Lucas Mülling +--- + tests/Makefile.am | 2 +- + tests/{t-digest.c => t-fips-service-ind.c} | 4 ++-- + 2 files changed, 3 insertions(+), 3 deletions(-) + rename tests/{t-digest.c => t-fips-service-ind.c} (99%) + +diff --git a/tests/Makefile.am b/tests/Makefile.am +index 93774fe9..3170a58e 100644 +--- a/tests/Makefile.am ++++ b/tests/Makefile.am +@@ -25,7 +25,7 @@ tests_bin = \ + version t-secmem mpitests t-sexp t-convert \ + t-mpi-bit t-mpi-point t-lock \ + prime basic keygen pubkey hmac hashtest t-kdf keygrip \ +- aeswrap random t-kem t-mlkem t-thread-local t-digest ++ aeswrap random t-kem t-mlkem t-thread-local t-fips-service-ind + + if USE_RSA + tests_bin += pkcs1v2 t-rsa-pss t-rsa-15 t-rsa-testparm +diff --git a/tests/t-digest.c b/tests/t-fips-service-ind.c +similarity index 99% +rename from tests/t-digest.c +rename to tests/t-fips-service-ind.c +index e2b1ce32..31c1fc72 100644 +--- a/tests/t-digest.c ++++ b/tests/t-fips-service-ind.c +@@ -1,4 +1,4 @@ +-/* t-digest.c - MD regression tests ++/* t-fips-service-ind.c - FIPS service indicator regression tests + * Copyright (C) 2024 g10 Code GmbH + * + * This file is part of Libgcrypt. +@@ -27,7 +27,7 @@ + #include + #include + +-#define PGM "t-digest" ++#define PGM "t-fips-service-ind" + + #include "t-common.h" + static int in_fips_mode; +-- +2.49.0 + diff --git a/libgcrypt.changes b/libgcrypt.changes new file mode 100644 index 0000000..1fee6bc --- /dev/null +++ b/libgcrypt.changes @@ -0,0 +1,1926 @@ +------------------------------------------------------------------- +Tue May 6 07:24:14 UTC 2025 - Pedro Monreal + +- CSHAKE basic regression test failure in s390x [bsc#1242419 + * Disable SHA3 s390x acceleration for CSHAKE [rC2486d9b5ae01] + * Add libgcrypt-Disable-SHA3-s390x-acceleration-for-CSHAKE.patch + +------------------------------------------------------------------- +Sun Apr 13 20:10:16 UTC 2025 - Lucas Mulling + +- Differentiate use of SHA1 in the service level indicator [jsc#PED-12227] + * Include upstream SLI revamp and fips certification fixes + * Add patches: + - libgcrypt-fips-Introduce-an-internal-API-for-FIPS-service-indicator.patch + - libgcrypt-fips-Introduce-GCRYCTL_FIPS_SERVICE_INDICATOR-and-the-macro.patch + - libgcrypt-fips-kdf-Implement-new-FIPS-service-indicator-for-gcry_kdf_derive.patch + - libgcrypt-fips-md-Implement-new-FIPS-service-indicator-for-gcry_md_hash_.patch + - libgcrypt-fips-tests-Add-t-digest.patch + - libgcrypt-fips-Change-the-internal-API-for-new-FIPS-service-indicator.patch + - libgcrypt-fips-md-Implement-new-FIPS-service-indicator-for-gcry_md_open-API.patch + - libgcrypt-fips-tests-Add-tests-for-md_open-write-read-close-for-t-digest.patch + - libgcrypt-fips-mac-Implement-new-FIPS-service-indicator-for-gcry_mac_open.patch + - libgcrypt-fips-cipher-Implement-new-FIPS-service-indicator-for-cipher_open.patch + - libgcrypt-tests-fips-Add-gcry_mac_open-tests.patch + - libgcrypt-tests-fips-Rename-t-fips-service-ind.patch + - libgcrypt-tests-fips-Move-KDF-tests-to-t-fips-service-ind.patch + - libgcrypt-tests-fips-Add-gcry_cipher_open-tests.patch + - libgcrypt-fips-md-gcry_md_copy-should-care-about-FIPS-service-indicator.patch + - libgcrypt-fips-cipher-Implement-FIPS-service-indicator-for-gcry_pk_hash_-API.patch + - libgcrypt-fips-Introduce-GCRYCTL_FIPS_REJECT_NON_FIPS.patch + - libgcrypt-Fix-the-previous-change.patch + - libgcrypt-fips-Rejection-by-GCRYCTL_FIPS_REJECT_NON_FIPS-not-by-open-flags.patch + - libgcrypt-fips-cipher-Add-behavior-not-to-reject-but-mark-non-compliant.patch + - libgcrypt-fips-ecc-Add-rejecting-or-marking-for-gcry_pk_get_curve.patch + - libgcrypt-tests-Add-more-tests-to-tests-t-fips-service-ind.patch + - libgcrypt-fips-ecc-Check-DATA-in-gcry_pk_sign-verify-in-FIPS-mode.patch + - libgcrypt-fips-cipher-Fix-memory-leak-for-gcry_pk_hash_sign.patch + - libgcrypt-build-Improve-__thread-specifier-check.patch + - libgcrypt-cipher-Check-and-mark-non-compliant-cipher-modes-in-the-SLI.patch + - libgcrypt-cipher-Rename-_gcry_cipher_is_mode_fips_compliant.patch + - libgcrypt-cipher-Don-t-differentiate-GCRY_CIPHER_MODE_CMAC-in-FIPS-mode.patch + - libgcrypt-cipher-rsa-Mark-reject-SHA1-unknown-with-RSA-signature-generation.patch + - libgcrypt-md-Fix-gcry_md_algo_info-to-mark-reject-under-FIPS-mode.patch + - libgcrypt-md-Use-check_digest_algo_spec-in-_gcry_md_selftest.patch + - libgcrypt-tests-Update-t-fips-service-ind-using-GCRY_MD_SHA256-for-KDF-tests.patch + - libgcrypt-fips-cipher-Do-the-computation-when-marking-non-compliant.patch + - libgcrypt-tests-Allow-tests-with-USE_RSA.patch + - libgcrypt-cipher-Add-KAT-for-non-rfc6979-ECDSA-with-fixed-k.patch + - libgcrypt-cipher-Differentiate-use-of-label-K-in-the-SLI.patch + - libgcrypt-cipher-Differentiate-igninvflag-in-the-SLI.patch + - libgcrypt-cipher-Differentiate-no-blinding-flag-in-the-SLI.patch + - libgcrypt-fips-cipher-Add-GCRY_FIPS_FLAG_REJECT_PK_FLAGS.patch + - libgcrypt-cipher-ecc-Fix-for-supplied-K.patch + - libgcrypt-cipher-visibility-Differentiate-use-of-random-override-in-the-SLI.patch + - libgcrypt-cipher-fips-Fix-for-random-override.patch + - libgcrypt-md-Make-SHA-1-non-FIPS-internally-for-1.12-API.patch + - libgcrypt-fips-Fix-GCRY_FIPS_FLAG_REJECT_MD.patch + - libgcrypt-doc-Add-about-GCRYCTL_FIPS_SERVICE_INDICATOR.patch + - libgcrypt-doc-Fix-syntax-error.patch + * Rebase patches: + - libgcrypt-FIPS-SLI-kdf-leylength.patch + +------------------------------------------------------------------- +Tue Jan 7 09:28:25 UTC 2025 - Pedro Monreal + +- Fix redefinition error of 'rol64'. Remove not used rol64() + definition after removing the built-in jitter rng. + * Add libgcrypt-rol64-redefinition.patch + +------------------------------------------------------------------- +Mon Dec 2 10:11:10 UTC 2024 - Pedro Monreal + +- Remove unrecognized option: --enable-m-guard + +------------------------------------------------------------------- +Thu Jun 20 08:11:07 UTC 2024 - Pedro Monreal + +- Update to 1.11.0: + * New and extended interfaces: + - Add an API for Key Encapsulation Mechanism (KEM). [T6755] + - Add Streamlined NTRU Prime sntrup761 algorithm. [rCcf9923e1a5] + - Add Kyber algorithm according to FIPS 203 ipd 2023-08-24. [rC18e5c0d268] + - Add Classic McEliece algorithm. [rC003367b912] + - Add One-Step KDF with hash and MAC. [T5964] + - Add KDF algorithm HKDF of RFC-5869. [T5964] + - Add KDF algorithm X963KDF for use in CMS. [rC3abac420b3] + - Add GMAC-SM4 and Poly1305-SM4. [rCd1ccc409d4] + - Add ARIA block cipher algorithm. [rC316c6d7715] + - Add explicit FIPS indicators for MD and MAC algorithms. [T6376] + - Add support for SHAKE as MGF in RSA. [T6557] + - Add gcry_md_read support for SHAKE algorithms. [T6539] + - Add gcry_md_hash_buffers_ext function. [T7035] + - Add cSHAKE hash algorithm. [rC065b3f4e02] + - Support internal generation of IV for AEAD cipher mode. [T4873] + * Performance: + - Add SM3 ARMv8/AArch64/CE assembly implementation. [rCfe891ff4a3] + - Add SM4 ARMv8/AArch64 assembly implementation. [rCd8825601f1] + - Add SM4 GFNI/AVX2 and GFI/AVX512 implementation. [rC5095d60af4,rCeaed633c16] + - Add SM4 ARMv9 SVE CE assembly implementation. [rC2dc2654006] + - Add PowerPC vector implementation of SM4. [rC0b2da804ee] + - Optimize ChaCha20 and Poly1305 for PPC P10 LE. [T6006] + - Add CTR32LE bulk acceleration for AES on PPC. [rC84f2e2d0b5] + - Add generic bulk acceleration for CTR32LE mode (GCM-SIV) for SM4 + and Camellia. [rCcf956793af] + - Add GFNI/AVX2 implementation of Camellia. [rC4e6896eb9f] + - Add AVX2 and AVX512 accelerated implementations for GHASH (GCM) + and POLYVAL (GCM-SIV). [rCd857e85cb4, rCe6f3600193] + - Add AVX512 implementation for SHA512. [rC089223aa3b] + - Add AVX512 implementation for Serpent. [rCce95b6ec35] + - Add AVX512 implementation for Poly1305 and ChaCha20. [rCcd3ed49770, rC9a63cfd617] + - Add AVX512 accelerated implementation for SHA3 and Blake2. [rCbeaad75f46,rC909daa700e] + - Add VAES/AVX2 accelerated i386 implementation for AES. [rC4a42a042bc] + - Add bulk processing for XTS mode of Camellia and SM4. [rC32b18cdb87, rCaad3381e93] + - Accelerate XTS and ECB modes for Twofish and Serpent. [rCd078a928f5,rC8a1fe5f78f] + - Add AArch64 crypto/SHA512 extension implementation for SHA512. [rCe51d3b8330] + - Add AArch64 crypto-extension implementation for Camellia. [rC898c857206] + - Accelerate OCB authentication on AMD with AVX2. [rC6b47e85d65] + * Bug fixes: + - For PowerPC check for missing optimization level for vector register usage. [T5785] + - Fix EdDSA secret key check. [T6511] + - Fix decoding of PKCS#1-v1.5 and OAEP padding. [rC34c2042792] + - Allow use of PKCS#1-v1.5 with SHA3 algorithms. [T6976] + - Fix AESWRAP padding length check. [T7130] + * Other: + - Allow empty password for Argon2 KDF. [rCa20700c55f] + - Various constant time operation imporvements. + - Add "bp256", "bp384", "bp512" aliases for Brainpool curves. + - Support for the random server has been removed. [T5811] + - The control code GCRYCTL_ENABLE_M_GUARD is deprecated and not + supported any more. Please use valgrind or other tools. [T5822] + - Logging is now done via the libgpg-error logging functions. [rCab0bdc72c7] + * Remove patches fixed upstream: + - libgcrypt-no-deprecated-grep-alias.patch + - libgcrypt-Chacha20-poly1305-Optimized-chacha20-poly1305.patch + - libgcrypt-ppc-enable-P10-assembly-with-ENABLE_FORCE_SOF.patch + * Rebase patches: + - libgcrypt-FIPS-jitter-errorcodes.patch + - libgcrypt-FIPS-jitter-whole-entropy.patch + +------------------------------------------------------------------- +Wed Mar 20 20:31:40 UTC 2024 - Pedro Monreal + +- FIPS: Make sure that Libgcrypt makes use of the built-in Jitter RNG + for the whole length entropy buffer in FIPS mode. [bsc#1220893] + * Add libgcrypt-FIPS-jitter-whole-entropy.patch + +------------------------------------------------------------------- +Wed Mar 20 15:13:04 UTC 2024 - Pedro Monreal + +- FIPS: Set the FSM into error state if Jitter RNG is returning an + error code to the caller when an health test error occurs when + random bytes are requested through the jent_read_entropy_safe() + function. [bsc#1220895] + * Add libgcrypt-FIPS-jitter-errorcodes.patch + +------------------------------------------------------------------- +Mon Mar 11 16:02:55 UTC 2024 - Pedro Monreal + +- FIPS: Replace the built-in jitter rng with standalone version + * Remove the internal jitterentropy copy [bsc#1220896] + * Add libgcrypt-FIPS-jitter-standalone.patch + * Remove not needed libgcrypt-jitterentropy-3.4.0.patch + +------------------------------------------------------------------- +Mon Feb 26 12:13:56 UTC 2024 - Pedro Monreal + +- Update upstream libgcrypt.keyring + +------------------------------------------------------------------- +Sat Jan 27 13:37:34 UTC 2024 - Dirk Müller + +- add libgcrypt-no-deprecated-grep-alias.patch + +------------------------------------------------------------------- +Tue Nov 21 10:36:09 UTC 2023 - Otto Hollmann + +- Re-create HMAC checksum after RPM build strips the library + (bsc#1217058) + +------------------------------------------------------------------- +Wed Nov 15 09:54:00 UTC 2023 - Pedro Monreal + +- Update to 1.10.3: + * Bug fixes: + - Fix public key computation for other EdDSA curves. [rC469919751d6e] + - Remove out of core handler diagnostic in FIPS mode. [T6515] + - Check that the digest size is not zero in gcry_pk_sign_md and + gcry_pk_verify_md. [T6539] + - Make store an s-exp with \0 is considered to be binary. [T6747] + - Various constant-time improvements. + * Portability: + - Use getrandom call only when supported by the platform. [T6442] + - Change the default for --with-libtool-modification to never. [T6619] + * Release-info: https://dev.gnupg.org/T6817 + * Remove patch upstream libgcrypt-1.10.0-out-of-core-handler.patch + +------------------------------------------------------------------- +Tue Oct 17 10:27:15 UTC 2023 - Pedro Monreal + +- Do not pull revision info from GIT when autoconf is run. This + removes the -unknown suffix after the version number. + * Add libgcrypt-nobetasuffix.patch [bsc#1216334] + +------------------------------------------------------------------- +Tue Oct 3 12:58:41 UTC 2023 - Pedro Monreal + +- POWER: performance enhancements for cryptography [jsc#PED-5088] + * Optimize Chacha20 and Poly1305 for PPC P10 LE: [T6006] + - Chacha20/poly1305: Optimized chacha20/poly1305 for + P10 operation [rC88fe7ac33eb4] + - ppc: enable P10 assembly with ENABLE_FORCE_SOFT_HWFEATURES + on arch-3.00 [rC2c5e5ab6843d] + * Add patches: + - libgcrypt-Chacha20-poly1305-Optimized-chacha20-poly1305.patch + - libgcrypt-ppc-enable-P10-assembly-with-ENABLE_FORCE_SOF.patch + +------------------------------------------------------------------- +Mon May 22 11:32:53 UTC 2023 - Pedro Monreal + +- FIPS: Merge the libgcrypt20-hmac package into the library and + remove the "module is complete" trigger file .fips [bsc#1185116] + * Remove libgcrypt-1.10.0-use-fipscheck.patch + +------------------------------------------------------------------- +Tue Apr 11 14:08:24 UTC 2023 - Pedro Monreal + +- Update to 1.10.2: + * Bug fixes: + - Fix Argon2 for the case output > 64. [rC13b5454d26] + - Fix missing HWF_PPC_ARCH_3_10 in HW feature. [rCe073f0ed44] + - Fix RSA key generation failure in forced FIPS mode. [T5919] + - Fix gcry_pk_hash_verify for explicit hash. [T6066] + - Fix a wrong result of gcry_mpi_invm. [T5970] + - Allow building with --disable-asm for HPPA. [T5976] + - Allow building with -Oz. [T6432] + - Enable the fast path to ChaCha20 only when supported. [T6384] + - Use size_t to avoid counter overflow in Keccak when directly + feeding more than 4GiB. [T6217] + * Other: + - Do not use secure memory for a DRBG instance. [T5933] + - Do not allow PKCS#1.5 padding for encryption in FIPS mode. [T5918] + - Fix the behaviour for child process re-seeding in the DRBG. [rC019a40c990] + - Allow verification of small RSA signatures in FIPS mode. [T5975] + - Allow the use of a shorter salt for KDFs in FIPS mode. [T6039] + - Run digest+sign self tests for RSA and ECC in FIPS mode. [rC06c9350165] + - Add function-name based FIPS indicator function. + GCRYCTL_FIPS_SERVICE_INDICATOR_FUNCTION. This is not considered + an ABI changes because the new FIPS features were not yet + approved. [rC822ee57f07] + - Improve PCT in FIPS mode. [rC285bf54b1a, rC4963c127ae, T6397] + - Use getrandom (GRND_RANDOM) in FIPS mode. [rCcf10c74bd9] + - Disable RSA-OAEP padding in FIPS mode. [rCe5bfda492a] + - Check minimum allowed key size in PBKDF in FIPS mode. [T6039,T6219] + - Get maximum 32B of entropy at once in FIPS mode. [rCce0df08bba] + - Prefer gpgrt-config when available. [T5034] + - Mark AESWRAP as approved FIPS algorithm. [T5512] + - Prevent usage of long salt for PSS in FIPS mode. [rCfdd2a8b332] + - Prevent usage of X9.31 keygen in FIPS mode. [rC392e0ccd25] + - Remove GCM mode from the allowed FIPS indicators. [rC1540698389] + - Add explicit FIPS indicators for hash and MAC algorithms. [T6376] + * Release-info: https://dev.gnupg.org/T5905 + * Rebase FIPS patches: + - libgcrypt-FIPS-SLI-hash-mac.patch + - libgcrypt-FIPS-SLI-kdf-leylength.patch + - libgcrypt-FIPS-SLI-pk.patch + +------------------------------------------------------------------- +Wed Mar 8 10:34:34 UTC 2023 - Martin Pluskal + +- Build AVX2 enabled hwcaps library for x86_64-v3 + +------------------------------------------------------------------- +Wed Oct 19 14:01:24 UTC 2022 - Pedro Monreal + +- Update to 1.10.1: + * Bug fixes: + - Fix minor memory leaks in FIPS mode. + - Build fixes for MUSL libc. + * Other: + - More portable integrity check in FIPS mode. + - Add X9.62 OIDs to sha256 and sha512 modules. + * Add the hardware optimizations config file hwf.deny to + the /etc/gcrypt/ directory. This file can be used to globally + disable the use of hardware based optimizations. + * Remove not needed separate_hmac256_binary hmac256 package + +------------------------------------------------------------------- +Wed Sep 14 13:34:13 UTC 2022 - Pedro Monreal + +- Update to 1.10.0: + * New and extended interfaces: + - New control codes to check for FIPS 140-3 approved algorithms. + - New control code to switch into non-FIPS mode. + - New cipher modes SIV and GCM-SIV as specified by RFC-5297. + - Extended cipher mode AESWRAP with padding as specified by + RFC-5649. + - New set of KDF functions. + - New KDF modes Argon2 and Balloon. + - New functions for combining hashing and signing/verification. + * Performance: + - Improved support for PowerPC architectures. + - Improved ECC performance on zSeries/s390x by using accelerated + scalar multiplication. + - Many more assembler performance improvements for several + architectures. + * Bug fixes: + - Fix Elgamal encryption for other implementations. + [bsc#1190239, CVE-2021-40528] + - Check the input length of the point in ECDH. + - Fix an abort in gcry_pk_get_param for "Curve25519". + * Other features: + - The control code GCRYCTL_SET_ENFORCED_FIPS_FLAG is ignored + because it is useless with the FIPS 140-3 related changes. + - Update of the jitter entropy RNG code. + - Simplification of the entropy gatherer when using the getentropy + system call. + * Interface changes relative to the 1.10.0 release: + - GCRYCTL_SET_DECRYPTION_TAG NEW control code. + - GCRYCTL_FIPS_SERVICE_INDICATOR_CIPHER NEW control code. + - GCRYCTL_FIPS_SERVICE_INDICATOR_KDF NEW control code. + - GCRYCTL_NO_FIPS_MODE = 83 NEW control code. + - GCRY_CIPHER_MODE_SIV NEW mode. + - GCRY_CIPHER_MODE_GCM_SIV NEW mode. + - GCRY_CIPHER_EXTENDED NEW flag. + - GCRY_SIV_BLOCK_LEN NEW macro. + - gcry_cipher_set_decryption_tag NEW macro. + - GCRY_KDF_ARGON2 NEW constant. + - GCRY_KDF_BALLOON NEW constant. + - GCRY_KDF_ARGON2D NEW constant. + - GCRY_KDF_ARGON2I NEW constant. + - GCRY_KDF_ARGON2ID NEW constant. + - gcry_kdf_hd_t NEW type. + - gcry_kdf_job_fn_t NEW type. + - gcry_kdf_dispatch_job_fn_t NEW type. + - gcry_kdf_wait_all_jobs_fn_t NEW type. + - struct gcry_kdf_thread_ops NEW struct. + - gcry_kdf_open NEW function. + - gcry_kdf_compute NEW function. + - gcry_kdf_final NEW function. + - gcry_kdf_close NEW function. + - gcry_pk_hash_sign NEW function. + - gcry_pk_hash_verify NEW function. + - gcry_pk_random_override_new NEW function. + * Rebase libgcrypt-1.8.4-allow_FSM_same_state.patch and rename + to libgcrypt-1.10.0-allow_FSM_same_state.patch + * Remove unused CAVS tests and related patches: + - cavs_driver.pl cavs-test.sh + - libgcrypt-1.6.1-fips-cavs.patch + - drbg_test.patch + * Remove DSA sign/verify patches for the FIPS CAVS test since DSA + has been disabled in FIPS mode: + - libgcrypt-fipsdrv-enable-algo-for-dsa-sign.patch + - libgcrypt-fipsdrv-enable-algo-for-dsa-verify.patch + * Rebase libgcrypt-FIPS-SLI-pk.patch + * Rebase libgcrypt_indicators_changes.patch and + libgcrypt-indicate-shake.patch and merge both into + libgcrypt-FIPS-SLI-hash-mac.patch + * Rebase libgcrypt-FIPS-kdf-leylength.patch and rename to + libgcrypt-FIPS-SLI-kdf-leylength.patch + * Rebase libgcrypt-jitterentropy-3.4.0.patch + * Rebase libgcrypt-FIPS-rndjent_poll.patch + * Rebase libgcrypt-out-of-core-handler.patch and rename to + libgcrypt-1.10.0-out-of-core-handler.patch + * Since the FIPS .hmac file is now calculated with the internal + tool hmac256, only the "module is complete" trigger .fips file + is checked. Rename libgcrypt-1.6.1-use-fipscheck.patch + to libgcrypt-1.10.0-use-fipscheck.patch + * Remove patches fixed upstream: + - libgcrypt-1.4.1-rijndael_no_strict_aliasing.patch + - libgcrypt-1.5.0-LIBGCRYPT_FORCE_FIPS_MODE-env.diff + - libgcrypt-fix-rng.patch + - libgcrypt-1.8.3-fips-ctor.patch + - libgcrypt-1.8.4-use_xfree.patch + - libgcrypt-1.8.4-getrandom.patch + - libgcrypt-1.8.4-fips_ctor_skip_integrity_check.patch + - libgcrypt-dsa-rfc6979-test-fix.patch + - libgcrypt-fix-tests-fipsmode.patch + - libgcrypt-FIPS-RSA-DSA-ECDSA-hashing-operation.patch + - libgcrypt-1.8.4-fips-keygen.patch + - libgcrypt-invoke-global_init-from-constructor.patch + - libgcrypt-Restore-self-tests-from-constructor.patch + - libgcrypt-FIPS-GMAC_AES-benckmark.patch + - libgcrypt-global_init-constructor.patch + - libgcrypt-random_selftests-testentropy.patch + - libgcrypt-rsa-no-blinding.patch + - libgcrypt-ecc-ecdsa-no-blinding.patch + - libgcrypt-PCT-DSA.patch + - libgcrypt-PCT-ECC.patch + - libgcrypt-PCT-RSA.patch + - libgcrypt-fips_selftest_trigger_file.patch + - libgcrypt-pthread-in-t-lock-test.patch + - libgcrypt-FIPS-hw-optimizations.patch + - libgcrypt-FIPS-module-version.patch + - libgcrypt-FIPS-disable-3DES.patch + - libgcrypt-FIPS-fix-regression-tests.patch + - libgcrypt-FIPS-RSA-keylen.patch + - libgcrypt-FIPS-RSA-keylen-tests.patch + - libgcrypt-FIPS-fix-gcry_mpi_sub_ui.patch + - libgcrypt-FIPS-verify-unsupported-KDF-test.patch + - libgcrypt-FIPS-HMAC-short-keylen.patch + - libgcrypt-FIPS-service-indicators.patch + - libgcrypt-FIPS-disable-DSA.patch + - libgcrypt-jitterentropy-3.3.0.patch + - libgcrypt-FIPS-Zeroize-hmac.patch + * Update libgcrypt.keyring + +------------------------------------------------------------------- +Thu Sep 8 10:34:53 UTC 2022 - Pedro Monreal + +- FIPS: Get most of the entropy from rndjent_poll [bsc#1202117] + * Add libgcrypt-FIPS-rndjent_poll.patch + * Rebase libgcrypt-jitterentropy-3.4.0.patch + +------------------------------------------------------------------- +Wed Sep 7 22:03:51 UTC 2022 - Pedro Monreal + +- FIPS: Check keylength in gcry_fips_indicator_kdf() [bsc#1190700] + * Consider approved keylength greater or equal to 112 bits. + * Add libgcrypt-FIPS-kdf-leylength.patch + +------------------------------------------------------------------- +Wed Sep 7 12:53:14 UTC 2022 - Pedro Monreal + +- FIPS: Zeroize buffer and digest in check_binary_integrity() + * Add libgcrypt-FIPS-Zeroize-hmac.patch [bsc#1191020] + +------------------------------------------------------------------- +Tue Aug 23 09:19:00 UTC 2022 - Pedro Monreal + +- FIPS: gpg/gpg2 gets out of core handler in FIPS mode while + typing Tab key to Auto-Completion. [bsc#1182983] + * Add libgcrypt-out-of-core-handler.patch + +------------------------------------------------------------------- +Mon Aug 8 11:33:03 UTC 2022 - Pedro Monreal + +- FIPS: Port libgcrypt to use jitterentropy [bsc#1202117, jsc#SLE-24941] + * Enable the jitter based entropy generator by default in random.conf + - Add libgcrypt-jitterentropy-3.3.0.patch + * Update the internal jitterentropy to version 3.4.0 + - Add libgcrypt-jitterentropy-3.4.0.patch + +------------------------------------------------------------------- +Mon Aug 1 07:27:35 UTC 2022 - Stephan Kulow + +- Fix reproducible build problems: + - Do not use %release in binaries (but use SOURCE_DATE_EPOCH) + - Fix date call messed up by spec-cleaner + +------------------------------------------------------------------- +Thu Apr 14 12:30:36 UTC 2022 - Dennis Knorr + +- FIPS: extend the service indicator [bsc#1190700] + * introduced a pk indicator function + * adapted the approved and non approved ciphersuites + * Add libgcrypt_indicators_changes.patch + * Add libgcrypt-indicate-shake.patch + +------------------------------------------------------------------- +Tue Mar 22 12:32:09 UTC 2022 - Pedro Monreal + +- FIPS: Implement a service indicator for asymmetric ciphers [bsc#1190700] + * Mark RSA public key encryption and private key decryption with + padding (e.g. OAEP, PKCS) as non-approved since RSA-OAEP lacks + peer key assurance validation requirements per SP800-56Brev2. + * Mark ECC as approved only for NIST curves P-224, P-256, P-384 + and P-521 with check for common NIST names and aliases. + * Mark DSA, ELG, EDDSA, ECDSA and ECDH as non-approved. + * Add libgcrypt-FIPS-SLI-pk.patch + * Rebase libgcrypt-FIPS-service-indicators.patch +- Run the regression tests also in FIPS mode. + * Disable tests for non-FIPS approved algos. + * Rebase: libgcrypt-FIPS-verify-unsupported-KDF-test.patch + +------------------------------------------------------------------- +Tue Feb 1 11:28:51 UTC 2022 - Pedro Monreal + +- FIPS: Disable DSA in FIPS mode [bsc#1195385] + * Upstream task: https://dev.gnupg.org/T5710 + * Add libgcrypt-FIPS-disable-DSA.patch + +------------------------------------------------------------------- +Wed Jan 19 08:36:58 UTC 2022 - Pedro Monreal + +- FIPS: Service level indicator [bsc#1190700] + * Provide an indicator to check wether the service utilizes an + approved cryptographic algorithm or not. + * Add patches: + - libgcrypt-FIPS-service-indicators.patch + - libgcrypt-FIPS-verify-unsupported-KDF-test.patch + - libgcrypt-FIPS-HMAC-short-keylen.patch + +------------------------------------------------------------------- +Tue Dec 7 09:41:01 UTC 2021 - Pedro Monreal + +- FIPS: Fix gcry_mpi_sub_ui subtraction [bsc#1193480] + * gcry_mpi_sub_ui: fix subtracting from negative value + * Add libgcrypt-FIPS-fix-gcry_mpi_sub_ui.patch + +------------------------------------------------------------------- +Tue Nov 30 09:42:23 UTC 2021 - Pedro Monreal + +- FIPS: Define an entropy source SP800-90B compliant [bsc#1185140] + * Disable jitter entropy by default in random.conf + * Disable only-urandom option by default in random.conf + +------------------------------------------------------------------- +Fri Nov 26 13:10:29 UTC 2021 - Pedro Monreal + +- FIPS: RSA KeyGen/SigGen fail with 4096 bit key sizes [bsc#1192240] + * rsa: Check RSA keylen constraints for key operations. + * rsa: Fix regression in not returning an error for prime generation. + * tests: Add 2k RSA key working in FIPS mode. + * tests: pubkey: Replace RSA key to one of 2k. + * tests: pkcs1v2: Skip tests with small keys in FIPS. + * Add patches: + - libgcrypt-FIPS-RSA-keylen.patch + - libgcrypt-FIPS-RSA-keylen-tests.patch + +------------------------------------------------------------------- +Mon Nov 8 10:21:39 UTC 2021 - Pedro Monreal + +- FIPS: Disable 3DES/Triple-DES in FIPS mode [bsc#1185138] + * Add libgcrypt-FIPS-disable-3DES.patch + +------------------------------------------------------------------- +Tue Nov 2 11:31:19 UTC 2021 - Pedro Monreal + +- FIPS: PBKDF requirements [bsc#1185137] + * The PBKDF2 selftests were introduced in libgcrypt version + 1.9.1 in the function selftest_pbkdf2() + * Upstream task: https://dev.gnupg.org/T5182 + +------------------------------------------------------------------- +Thu Oct 28 19:48:06 UTC 2021 - Pedro Monreal + +- FIPS: Fix regression tests in FIPS mode [bsc#1192131] + * Add libgcrypt-FIPS-fix-regression-tests.patch + * Upstream task: https://dev.gnupg.org/T5520 + +------------------------------------------------------------------- +Thu Sep 21 11:25:06 UTC 2021 - Pedro Monreal + +- FIPS: Provide a module name/identifier and version that can be + mapped to the validation records. [bsc#1190706] + * Add libgcrypt-FIPS-module-version.patch + * Upstream task: https://dev.gnupg.org/T5600 + +------------------------------------------------------------------- +Thu Sep 21 10:23:44 UTC 2021 - Pedro Monreal + +- FIPS: Enable hardware support also in FIPS mode [bsc#1187110] + * Add libgcrypt-FIPS-hw-optimizations.patch + * Upstream task: https://dev.gnupg.org/T5508 + +------------------------------------------------------------------- +Mon Aug 23 12:08:24 UTC 2021 - Pedro Monreal + +- Update to 1.9.4: + * Bug fixes: + - Fix Elgamal encryption for other implementations. [CVE-2021-33560] + - Fix alignment problem on macOS. + - Check the input length of the point in ECDH. + - Fix an abort in gcry_pk_get_param for "Curve25519". + * Other features: + - Add GCM and CCM to OID mapping table for AES. + * Upstream libgcrypt-CVE-2021-33560-fix-ElGamal-enc.patch + +------------------------------------------------------------------- +Mon Aug 23 10:11:55 UTC 2021 - Pedro Monreal + +- Remove not needed patch libgcrypt-sparcv9.diff + +------------------------------------------------------------------- +Thu Jul 15 12:53:45 UTC 2021 - Pedro Monreal + +- Fix building test t-lock with pthread. [bsc#1189745] + * Explicitly add -lpthread to compile the t-lock test. + * Add libgcrypt-pthread-in-t-lock-test.patch + +------------------------------------------------------------------- +Fri Jun 11 13:17:54 UTC 2021 - Pedro Monreal + +- Security fix: [bsc#1187212, CVE-2021-33560] + * cipher: Fix ElGamal encryption for other implementations. + * Exponent blinding was added in version 1.9.3. This patch + fixes ElGamal encryption, see: https://dev.gnupg.org/T5328 +- Add libgcrypt-CVE-2021-33560-fix-ElGamal-enc.patch + +------------------------------------------------------------------- +Tue Apr 20 08:46:11 UTC 2021 - Paolo Stivanin + +- libgcrypt 1.9.3: + * Bug fixes: + - Fix build problems on i386 using gcc-4.7. + - Fix checksum calculation in OCB decryption for AES on s390. + - Fix a regression in gcry_mpi_ec_add related to certain usages + of curve 25519. + - Fix a symbol not found problem on Apple M1. + - Fix for Apple iOS getentropy peculiarity. + - Make keygrip computation work for compressed points. + * Performance: + - Add x86_64 VAES/AVX2 accelerated implementation of Camellia. + - Add x86_64 VAES/AVX2 accelerated implementation of AES. + - Add VPMSUMD acceleration for GCM mode on PPC. + * Internal changes. + - Harden MPI conditional code against EM leakage. + - Harden Elgamal by introducing exponent blinding. + +------------------------------------------------------------------- +Wed Feb 17 09:49:55 UTC 2021 - Andreas Stieger + +- libgcrypt 1.9.2: + * Fix building with --disable-asm on x86 + * Check public key for ECDSA verify operation + * Make sure gcry_get_config (NULL) returns a nul-terminated + string + * Fix a memory leak in the ECDH code + * Fix a reading beyond end of input buffer in SHA2-avx2 +- remove obsolete texinfo packaging macros + +------------------------------------------------------------------- +Tue Feb 2 01:06:47 UTC 2021 - Pedro Monreal + +- Update to 1.9.1 + * *Fix exploitable bug* in hash functions introduced with + 1.9.0. [bsc#1181632, CVE-2021-3345] + * Return an error if a negative MPI is used with sexp scan + functions. + * Check for operational FIPS in the random and KDF functions. + * Fix compile error on ARMv7 with NEON disabled. + * Fix self-test in KDF module. + * Improve assembler checks for better LTO support. + * Fix 32-bit cross build on x86. + * Fix non-NEON ARM assembly implementation for SHA512. + * Fix build problems with the cipher_bulk_ops_t typedef. + * Fix Ed25519 private key handling for preceding ZEROs. + * Fix overflow in modular inverse implementation. + * Fix register access for AVX/AVX2 implementations of Blake2. + * Add optimized cipher and hash functions for s390x/zSeries. + * Use hardware bit counting functionx when available. + * Update DSA functions to match FIPS 186-3. + * New self-tests for CMACs and KDFs. + * Add bulk cipher functions for OFB and GCM modes. +- Update libgpg-error required version + +------------------------------------------------------------------- +Tue Feb 1 12:03:31 UTC 2021 - Pedro Monreal + +- Use the suffix variable correctly in get_hmac_path() +- Rebase libgcrypt-fips_selftest_trigger_file.patch + +------------------------------------------------------------------- +Mon Jan 25 12:38:35 UTC 2021 - Pedro Monreal + +- Add the global config file /etc/gcrypt/random.conf + * This file can be used to globally change parameters of the random + generator with the options: only-urandom and disable-jent. + +------------------------------------------------------------------- +Thu Jan 21 15:42:15 UTC 2021 - Pedro Monreal + +- Update to 1.9.0: + New stable branch of Libgcrypt with full API and ABI compatibility + to the 1.8 series. Release-info: https://dev.gnupg.org/T4294 + * New and extended interfaces: + - New curves Ed448, X448, and SM2. + - New cipher mode EAX. + - New cipher algo SM4. + - New hash algo SM3. + - New hash algo variants SHA512/224 and SHA512/256. + - New MAC algos for Blake-2 algorithms, the new SHA512 variants, + SM3, SM4 and for a GOST variant. + - New convenience function gcry_mpi_get_ui. + - gcry_sexp_extract_param understands new format specifiers to + directly store to integers and strings. + - New function gcry_ecc_mul_point and curve constants for Curve448 + and Curve25519. + - New function gcry_ecc_get_algo_keylen. + - New control code GCRYCTL_AUTO_EXPAND_SECMEM to allow growing the + secure memory area. + * Performance optimizations and bug fixes: See Release-info. + * Other features: + - Add OIDs from RFC-8410 as aliases for Ed25519 and Curve25519. + - Add mitigation against ECC timing attack CVE-2019-13627. + - Internal cleanup of the ECC implementation. + - Support reading EC point in compressed format for some curves. +- Rebase patches: + * libgcrypt-1.4.1-rijndael_no_strict_aliasing.patch + * libgcrypt-1.5.0-LIBGCRYPT_FORCE_FIPS_MODE-env.diff + * libgcrypt-1.6.1-use-fipscheck.patch + * drbg_test.patch + * libgcrypt-fipsdrv-enable-algo-for-dsa-sign.patch + * libgcrypt-FIPS-RSA-DSA-ECDSA-hashing-operation.patch + * libgcrypt-1.8.4-fips-keygen.patch + * libgcrypt-1.8.4-getrandom.patch + * libgcrypt-fix-tests-fipsmode.patch + * libgcrypt-global_init-constructor.patch + * libgcrypt-ecc-ecdsa-no-blinding.patch + * libgcrypt-PCT-RSA.patch + * libgcrypt-PCT-ECC.patch +- Remove patches: + * libgcrypt-unresolved-dladdr.patch + * libgcrypt-CVE-2019-12904-GCM-Prefetch.patch + * libgcrypt-CVE-2019-12904-GCM.patch + * libgcrypt-CVE-2019-12904-AES.patch + * libgcrypt-CMAC-AES-TDES-selftest.patch + * libgcrypt-1.6.1-fips-cfgrandom.patch + * libgcrypt-fips_rsa_no_enforced_mode.patch + +------------------------------------------------------------------- +Sat Oct 24 10:25:13 UTC 2020 - Andreas Stieger + +- libgcrypt 1.8.7: + * Support opaque MPI with gcry_mpi_print + * Fix extra entropy collection via clock_gettime, a fallback code + path for legacy hardware + +------------------------------------------------------------------- +Tue Jul 7 09:12:27 UTC 2020 - Pedro Monreal Gonzalez + +- Update to 1.8.6 + * mpi: Consider +0 and -0 the same in mpi_cmp + * mpi: Fix flags in mpi_copy for opaque MPI + * mpi: Fix the return value of mpi_invm_generic + * mpi: DSA,ECDSA: Fix use of mpi_invm + - Call mpi_invm before _gcry_dsa_modify_k + - Call mpi_invm before _gcry_ecc_ecdsa_sign + * mpi: Constant time mpi_inv with some conditions + - mpi/mpi-inv.c (mpih_add_n_cond, mpih_sub_n_cond, mpih_swap_cond) + - New: mpih_abs_cond, mpi_invm_odd + - Rename from _gcry_mpi_invm: mpi_invm_generic + - Use mpi_invm_odd for usual odd cases: _gcry_mpi_invm + * mpi: Abort on division by zero also in _gcry_mpi_tdiv_qr + * Fix wrong code execution in Poly1305 ARM/NEON implementation + - Set r14 to -1 at function entry: (_gcry_poly1305_armv7_neon_init_ext) + * Set vZZ.16b register to zero before use in armv8 gcm implementation + * random: Fix include of config.h + * Fix declaration of internal function _gcry_mpi_get_ui: Don't use ulong + * ecc: Fix wrong handling of shorten PK bytes + - Zeros are already recovered: (_gcry_ecc_mont_decodepoint) +- Update libgcrypt-ecc-ecdsa-no-blinding.patch + +------------------------------------------------------------------- +Tue May 19 11:25:37 UTC 2020 - Pedro Monreal Gonzalez + +- FIPS: RSA/DSA/ECC test_keys() print out debug messages [bsc#1171872] + * Print the debug messages in test_keys() only in debug mode. +- Update patches: libgcrypt-PCT-RSA.patch libgcrypt-PCT-DSA.patch + libgcrypt-PCT-ECC.patch + +------------------------------------------------------------------- +Mon Apr 27 08:55:12 UTC 2020 - Pedro Monreal Gonzalez + +- FIPS: libgcrypt: Double free in test_keys() on failed signature + verification [bsc#1169944] + * Use safer gcry_mpi_release() instead of mpi_free() +- Update patches: + * libgcrypt-PCT-DSA.patch + * libgcrypt-PCT-RSA.patch + * libgcrypt-PCT-ECC.patch + +------------------------------------------------------------------- +Thu Apr 16 16:45:23 UTC 2020 - Vítězslav Čížek + +- Ship the FIPS checksum file in the shared library package and + create a separate trigger file for the FIPS selftests (bsc#1169569) + * add libgcrypt-fips_selftest_trigger_file.patch + * refresh libgcrypt-global_init-constructor.patch +- Remove libgcrypt-binary_integrity_in_non-FIPS.patch obsoleted + by libgcrypt-global_init-constructor.patch + +------------------------------------------------------------------- +Wed Apr 15 13:55:27 UTC 2020 - Pedro Monreal Gonzalez + +- FIPS: Verify that the generated signature and the original input + differ in test_keys function for RSA, DSA and ECC: [bsc#1165539] +- Add zero-padding when qx and qy have different lengths when + assembling the Q point from affine coordinates. +- Refreshed patches: + * libgcrypt-PCT-DSA.patch + * libgcrypt-PCT-RSA.patch + * libgcrypt-PCT-ECC.patch + +------------------------------------------------------------------- +Mon Mar 30 10:48:02 UTC 2020 - Pedro Monreal Gonzalez + +- FIPS: Switch the PCT to use the new signature operation [bsc#1165539] + * Patches for DSA, RSA and ECDSA test_keys functions: + - libgcrypt-PCT-DSA.patch + - libgcrypt-PCT-RSA.patch + - libgcrypt-PCT-ECC.patch +- Update patch: libgcrypt-FIPS-RSA-DSA-ECDSA-hashing-operation.patch + +------------------------------------------------------------------- +Thu Mar 26 18:09:47 UTC 2020 - Pedro Monreal Gonzalez + +- FIPS: Run self-tests from constructor during power-on [bsc#1166748] + * Set up global_init as the constructor function: + - libgcrypt-global_init-constructor.patch + * Relax the entropy requirements on selftest. This is especially + important for virtual machines to boot properly before the RNG + is available: + - libgcrypt-random_selftests-testentropy.patch + - libgcrypt-rsa-no-blinding.patch + - libgcrypt-ecc-ecdsa-no-blinding.patch + * Fix benchmark regression test in FIPS mode: + - libgcrypt-FIPS-GMAC_AES-benckmark.patch + +------------------------------------------------------------------- +Thu Mar 12 16:54:33 UTC 2020 - Pedro Monreal Gonzalez + +- Remove check not needed in _gcry_global_constructor [bsc#1164950] + * Update libgcrypt-Restore-self-tests-from-constructor.patch + +------------------------------------------------------------------- +Tue Feb 25 22:13:24 UTC 2020 - Pedro Monreal Gonzalez + +- FIPS: Run the self-tests from the constructor [bsc#1164950] + * Add libgcrypt-invoke-global_init-from-constructor.patch + +------------------------------------------------------------------- +Fri Jan 17 17:35:15 UTC 2020 - Pedro Monreal Gonzalez + +- FIPS: libgcrypt DSA PQG parameter generation: Missing value [bsc#1161219] +- FIPS: libgcrypt DSA PQG verification incorrect results [bsc#1161215] +- FIPS: libgcrypt RSA siggen/keygen: 4k not supported [bsc#1161220] + * Add patch from Fedora libgcrypt-1.8.4-fips-keygen.patch + +------------------------------------------------------------------- +Wed Dec 11 10:18:23 UTC 2019 - Pedro Monreal Gonzalez + +- FIPS: RSA/DSA/ECDSA are missing hashing operation [bsc#1155337] + * Add libgcrypt-FIPS-RSA-DSA-ECDSA-hashing-operation.patch + +------------------------------------------------------------------- +Wed Nov 27 14:01:01 UTC 2019 - Pedro Monreal Gonzalez + +- Fix tests in FIPS mode: + * Fix tests: basic benchmark bench-slope pubkey t-cv25519 t-secmem + * Add patch libgcrypt-fix-tests-fipsmode.patch + +------------------------------------------------------------------- +Tue Nov 26 18:48:20 UTC 2019 - Pedro Monreal Gonzalez + +- Fix test dsa-rfc6979 in FIPS mode: + * Disable tests in elliptic curves with 192 bits which are not + recommended in FIPS mode + * Add patch libgcrypt-dsa-rfc6979-test-fix.patch + +------------------------------------------------------------------- +Tue Nov 12 11:05:02 UTC 2019 - Pedro Monreal Gonzalez + +- CMAC AES and TDES FIPS self-tests: + * CMAC AES self test missing [bsc#1155339] + * CMAC TDES self test missing [bsc#1155338] +- Add libgcrypt-CMAC-AES-TDES-selftest.patch + +------------------------------------------------------------------- +Fri Aug 30 14:17:48 UTC 2019 - Andreas Stieger + +- libgcrypt 1.8.5: + * CVE-2019-13627: mitigation against an ECDSA timing attack (boo#1148987) + * Improve ECDSA unblinding + * Provide a pkg-config file + +------------------------------------------------------------------- +Wed Jun 26 06:52:54 UTC 2019 - Jason Sikes + +- Fixed redundant fips tests in some situations causing sudo to stop + working when pam-kwallet is installed. bsc#1133808 + * Added libgcrypt-1.8.4-fips_ctor_skip_integrity_check.patch + * Removed libgcrypt-fips_run_selftest_at_constructor.patch + because it was obsoleted by libgcrypt-1.8.3-fips-ctor.patch + * Removed libgcrypt-fips_ignore_FIPS_MODULE_PATH.patch + because it was obsoleted by libgcrypt-1.8.4-fips_ctor_skip_integrity_check.patch + +------------------------------------------------------------------- +Fri Jun 21 16:53:07 UTC 2019 - Pedro Monreal Gonzalez + +- Fixed env-script-interpreter in cavs_driver.pl + +------------------------------------------------------------------- +Fri Jun 21 16:39:00 UTC 2019 - Pedro Monreal Gonzalez + +- Security fix: [bsc#1138939, CVE-2019-12904] + * The C implementation of AES is vulnerable to a flush-and-reload + side-channel attack because physical addresses are available to + other processes. (The C implementation is used on platforms where + an assembly-language implementation is unavailable.) + * Added patches: + - libgcrypt-CVE-2019-12904-GCM-Prefetch.patch + - libgcrypt-CVE-2019-12904-GCM.patch + - libgcrypt-CVE-2019-12904-AES.patch + +------------------------------------------------------------------- +Fri Apr 26 06:47:45 UTC 2019 - Jason Sikes + +- do not try to open /dev/urandom if getrandom() works + * Added libgcrypt-1.8.4-getrandom.patch +- Drop libgcrypt-init-at-elf-load-fips.patch obsoleted + by libgcrypt-1.8.3-fips-ctor.patch + +------------------------------------------------------------------- +Tue Apr 23 12:38:40 UTC 2019 - Jason Sikes + +- Restored libgcrypt-binary_integrity_in_non-FIPS.patch sans section that + was partially causing bsc#1131183. +- Fixed race condition in multi-threaded applications by allowing a FSM state + transition to the current state. This means some tests are run twice. + * Added libgcrypt-1.8.4-allow_FSM_same_state.patch +- Fixed an issue in malloc/free wrappers so that memory created by the malloc() + wrappers will be destroyed using the free() wrappers. + * Added libgcrypt-1.8.4-use_xfree.patch + +------------------------------------------------------------------- +Fri Apr 5 21:56:00 UTC 2019 - Jason Sikes + +- removed libgcrypt-binary_integrity_in_non-FIPS.patch since it was breaking + libotr. bsc#1131183 + +------------------------------------------------------------------- +Tue Mar 26 16:30:23 UTC 2019 - Vítězslav Čížek + +- libgcrypt-1.8.3-fips-ctor.patch changed the way the fips selftests + are invoked as well as the state transition, adjust the code so + a missing checksum file is not an issue in non-FIPS mode (bsc#1097073) + * update libgcrypt-binary_integrity_in_non-FIPS.patch + +------------------------------------------------------------------- +Tue Mar 26 16:25:18 UTC 2019 - Vítězslav Čížek + +- Enforce the minimal RSA keygen size in fips mode (bsc#1125740) + * add libgcrypt-fips_rsa_no_enforced_mode.patch + +------------------------------------------------------------------- +Fri Mar 22 14:13:05 UTC 2019 - Vítězslav Čížek + +- Don't run full self-tests from constructor (bsc#1097073) + * Don't call global_init() from the constructor, _gcry_global_constructor() + from libgcrypt-1.8.3-fips-ctor.patch takes care of the binary + integrity check instead. + * Only the binary checksum will be verified, the remaining + self-tests will be run upon the library initialization +- Add libgcrypt-fips_ignore_FIPS_MODULE_PATH.patch +- Drop libgcrypt-init-at-elf-load-fips.patch and + libgcrypt-fips_run_selftest_at_constructor.patch obsoleted + by libgcrypt-1.8.3-fips-ctor.patch + +------------------------------------------------------------------- +Thu Mar 7 10:53:40 UTC 2019 - Pedro Monreal Gonzalez + +- Skip all the self-tests except for binary integrity when called + from the constructor (bsc#1097073) + * Added libgcrypt-1.8.3-fips-ctor.patch from Fedora + +------------------------------------------------------------------- +Mon Nov 26 17:09:47 UTC 2018 - Vítězslav Čížek + +- Fail selftests when checksum file is missing in FIPS mode only + (bsc#1117355) + * add libgcrypt-binary_integrity_in_non-FIPS.patch + +------------------------------------------------------------------- +Sun Oct 28 18:57:53 UTC 2018 - astieger@suse.com + +- libgcrypt 1.8.4: + * Fix infinite loop with specific application implementations + * Fix possible leak of a few bits of secret primes to pageable + memory + * Fix possible hang in the RNG (1.8.3) + * Always make use of getrandom if possible and then use + its /dev/urandom behaviour + +------------------------------------------------------------------- +Mon Jul 2 10:38:42 UTC 2018 - schwab@suse.de + +- libgcrypt-1.6.3-aliasing.patch, libgcrypt-ppc64.patch, + libgcrypt-strict-aliasing.patch: Remove obsolete patches +- libgcrypt-1.4.1-rijndael_no_strict_aliasing.patch: Rediff +- Reenable testsuite + +------------------------------------------------------------------- +Wed Jun 13 10:46:33 UTC 2018 - kbabioch@suse.com + +- Update to version 1.8.3: + - Use blinding for ECDSA signing to mitigate a novel side-channel + attack. (CVE-2018-0495 bsc#1097410) + - Fix incorrect counter overflow handling for GCM when using an IV + size other than 96 bit. + - Fix incorrect output of AES-keywrap mode for in-place encryption + on some platforms. + - Fix the gcry_mpi_ec_curve_point point validation function. + - Fix rare assertion failure in gcry_prime_check. +- Applied spec-cleaner + +------------------------------------------------------------------- +Wed May 2 14:31:07 UTC 2018 - pmonrealgonzalez@suse.com + +- Suggest libgcrypt20-hmac for package libgcrypt20 to ensure they + are installed in the right order. [bsc#1090766] + +------------------------------------------------------------------- +Thu Mar 29 06:37:44 UTC 2018 - pmonrealgonzalez@suse.com + +- Extended the fipsdrv dsa-sign and dsa-verify commands with the + --algo parameter for the FIPS testing of DSA SigVer and SigGen + (bsc#1064455). + * Added libgcrypt-fipsdrv-enable-algo-for-dsa-sign.patch + * Added libgcrypt-fipsdrv-enable-algo-for-dsa-verify.patch + +------------------------------------------------------------------- +Thu Feb 22 15:10:36 UTC 2018 - fvogt@suse.com + +- Use %license (boo#1082318) + +------------------------------------------------------------------- +Wed Dec 13 20:09:28 UTC 2017 - astieger@suse.com + +- libgcrypt 1.8.2: + * Fix fatal out of secure memory status in the s-expression + parser on heavy loaded systems. + * Add auto expand secmem feature or use by GnuPG 2.2.4 + +------------------------------------------------------------------- +Mon Aug 28 17:54:24 UTC 2017 - astieger@suse.com + +- libgcrypt 1.8.1: + * Mitigate a local side-channel attack on Curve25519 dubbed "May + the Fourth be With You" CVE-2017-0379 bsc#1055837 + * Add more extra bytes to the pool after reading a seed file + * Add the OID SHA384WithECDSA from RFC-7427 to SHA-384 + * Fix build problems with the Jitter RNG + * Fix assembler code build problems on Rasbian (ARMv8/AArch32-CE) + +------------------------------------------------------------------- +Mon Jul 24 23:43:40 UTC 2017 - jengelh@inai.de + +- RPM group fixes. + +------------------------------------------------------------------- +Fri Jul 21 15:50:14 UTC 2017 - astieger@suse.com + +- libgcrypt 1.8.0: + * New cipher mode XTS + * New hash function Blake-2 + * New function gcry_mpi_point_copy. + * New function gcry_get_config. + * GCRYCTL_REINIT_SYSCALL_CLAMP allows to init nPth after Libgcrypt. + * New gobal configuration file /etc/gcrypt/random.conf. + * GCRYCTL_PRINT_CONFIG does now also print build information for + libgpg-error and the used compiler version. + * GCRY_CIPHER_MODE_CFB8 is now supported. + * A jitter based entropy collector is now used in addition to the + other entropy collectors. + * Optimized gcry_md_hash_buffers for SHA-256 and SHA-512. + random pool lock). + * Interface changes relative to the 1.7.0 release: + gcry_get_config NEW function. + gcry_mpi_point_copy NEW function. + GCRYCTL_REINIT_SYSCALL_CLAMP NEW macro. + GCRY_MD_BLAKE2B_512 NEW constant. + GCRY_MD_BLAKE2B_384 NEW constant. + GCRY_MD_BLAKE2B_256 NEW constant. + GCRY_MD_BLAKE2B_160 NEW constant. + GCRY_MD_BLAKE2S_256 NEW constant. + GCRY_MD_BLAKE2S_224 NEW constant. + GCRY_MD_BLAKE2S_160 NEW constant. + GCRY_MD_BLAKE2S_128 NEW constant. + GCRY_CIPHER_MODE_XTS NEW constant. + gcry_md_info DEPRECATED. +- Refresh patch libgcrypt-1.6.3-aliasing.patch + +------------------------------------------------------------------- +Thu Jun 29 09:49:44 UTC 2017 - astieger@suse.com + +- libgcrypt 1.7.8: + * CVE-2017-7526: Mitigate a flush+reload side-channel attack on + RSA secret keys (bsc#1046607) + +------------------------------------------------------------------- +Sun Jun 4 19:26:12 UTC 2017 - astieger@suse.com + +- libgcrypt 1.7.7: + * Fix possible timing attack on EdDSA session key (previously + patched, drop libgcrypt-secure-EdDSA-session-key.patch) + * Fix long standing bug in secure memory implementation which + could lead to a segv on free + +------------------------------------------------------------------- +Fri Jun 2 10:05:18 UTC 2017 - pmonrealgonzalez@suse.com + +- Added libgcrypt-secure-EdDSA-session-key.patch [bsc#1042326] + * Store the session key in secure memory to ensure that constant + time point operations are used in the MPI library. + +------------------------------------------------------------------- +Fri Jan 20 09:41:15 UTC 2017 - rmaliska@suse.com + +- libgcrypt 1.7.6: + * Fix counter operand from read-only to read/write + * Fix too large jump alignment in mpih-rshift + +------------------------------------------------------------------- +Thu Dec 15 10:32:18 UTC 2016 - astieger@suse.com + +- libgcrypt 1.7.5: + * Fix regression in mlock detection introduced with 1.7.4 + +------------------------------------------------------------------- +Tue Dec 13 12:20:47 UTC 2016 - astieger@suse.com + +- libgcrypt 1.7.4: + * ARMv8/AArch32 performance improvements for AES, GCM, SHA-256, + and SHA-1. + * Add ARMv8/AArch32 assembly implementation for Twofish and + Camellia. + * Add bulk processing implementation for ARMv8/AArch32. + * Add Stribog OIDs. + * Improve the DRBG performance and sync the code with the Linux + version. + * When secure memory is requested by the MPI functions or by + gcry_xmalloc_secure, they do not anymore lead to a fatal error + if the secure memory pool is used up. Instead new pools are + allocated as needed. These new pools are not protected against + being swapped out (mlock can't be used). Mitigation for + minor confidentiality issues is encryption swap space. + * Fix GOST 28147 CryptoPro-B S-box. + * Fix error code handling of mlock calls. + +------------------------------------------------------------------- +Sat Aug 20 10:38:15 UTC 2016 - mpluskal,vcizek,astieger}@suse.com + +- libgcrypt 1.7.3: + * security issue already fixes with 1.6.6 + * Fix building of some asm modules with older compilers and CPUs. + * ARMv8/AArch32 improvements for AES, GCM, SHA-256, and SHA-1. +- includes changes from libgcrypt 1.7.2: + * Bug fixes: + - Fix setting of the ECC cofactor if parameters are specified. + - Fix memory leak in the ECC code. + - Remove debug message about unsupported getrandom syscall. + - Fix build problems related to AVX use. + - Fix bus errors on ARM for Poly1305, ChaCha20, AES, and SHA-512. + * Internal changes: + - Improved fatal error message for wrong use of gcry_md_read. + - Disallow symmetric encryption/decryption if key is not set. +- includes changes from 1.7.1: + * Bug fixes: + - Fix ecc_verify for cofactor support. + - Fix portability bug when using gcc with Solaris 9 SPARC. + - Build fix for OpenBSD/amd64 + - Add OIDs to the Serpent ciphers. + * Internal changes: + - Use getrandom system call on Linux if available. + - Blinding is now also used for RSA signature creation. + - Changed names of debug envvars +- includes changes from 1.7.0: + * New algorithms and modes: + - SHA3-224, SHA3-256, SHA3-384, SHA3-512, and MD2 hash algorithms. + - SHAKE128 and SHAKE256 extendable-output hash algorithms. + - ChaCha20 stream cipher. + - Poly1305 message authentication algorithm + - ChaCha20-Poly1305 Authenticated Encryption with Associated Data + mode. + - OCB mode. + - HMAC-MD2 for use by legacy applications. + * New curves for ECC: + - Curve25519. + - sec256k1. + - GOST R 34.10-2001 and GOST R 34.10-2012. + * Performance: + - Improved performance of KDF functions. + - Assembler optimized implementations of Blowfish and Serpent on + ARM. + - Assembler optimized implementation of 3DES on x86. + - Improved AES using the SSSE3 based vector permutation method by + Mike Hamburg. + - AVX/BMI is used for SHA-1 and SHA-256 on x86. This is for SHA-1 + about 20% faster than SSSE3 and more than 100% faster than the + generic C implementation. + - 40% speedup for SHA-512 and 72% for SHA-1 on ARM Cortex-A8. + - 60-90% speedup for Whirlpool on x86. + - 300% speedup for RIPE MD-160. + - Up to 11 times speedup for CRC functions on x86. + * Other features: + - Improved ECDSA and FIPS 186-4 compliance. + - Support for Montgomery curves. + - gcry_cipher_set_sbox to tweak S-boxes of the gost28147 cipher + algorithm. + - gcry_mpi_ec_sub to subtract two points on a curve. + - gcry_mpi_ec_decode_point to decode an MPI into a point object. + - Emulation for broken Whirlpool code prior to 1.6.0. [from 1.6.1] + - Flag "pkcs1-raw" to enable PCKS#1 padding with a user supplied + hash part. + - Parameter "saltlen" to set a non-default salt length for RSA PSS. + - A SP800-90A conforming DRNG replaces the former X9.31 alternative + random number generator. + - Map deprecated RSA algo number to the RSA algo number for better + backward compatibility. [from 1.6.2] + - Use ciphertext blinding for Elgamal decryption [CVE-2014-3591]. + See http://www.cs.tau.ac.il/~tromer/radioexp/ for details. + [from 1.6.3] + - Fixed data-dependent timing variations in modular exponentiation + [related to CVE-2015-0837, Last-Level Cache Side-Channel Attacks + are Practical]. [from 1.6.3] + - Flag "no-keytest" for ECC key generation. Due to a bug in + the parser that flag will also be accepted but ignored by older + version of Libgcrypt. [from 1.6.4] + - Speed up the random number generator by requiring less extra + seeding. [from 1.6.4] + - Always verify a created RSA signature to avoid private key leaks + due to hardware failures. [from 1.6.4] + - Mitigate side-channel attack on ECDH with Weierstrass curves + [CVE-2015-7511]. See http://www.cs.tau.ac.IL/~tromer/ecdh/ for + details. [from 1.6.5] + * Internal changes: + - Moved locking out to libgpg-error. + - Support of the SYSROOT envvar in the build system. + - Refactor some code. + - The availability of a 64 bit integer type is now mandatory. + * Bug fixes: + - Fixed message digest lookup by OID (regression in 1.6.0). + - Fixed a build problem on NetBSD + - Fixed some asm build problems and feature detection bugs. + * Interface changes relative to the 1.6.0 release: + gcry_cipher_final NEW macro. + GCRY_CIPHER_MODE_CFB8 NEW constant. + GCRY_CIPHER_MODE_OCB NEW. + GCRY_CIPHER_MODE_POLY1305 NEW. + gcry_cipher_set_sbox NEW macro. + gcry_mac_get_algo NEW. + GCRY_MAC_HMAC_MD2 NEW. + GCRY_MAC_HMAC_SHA3_224 NEW. + GCRY_MAC_HMAC_SHA3_256 NEW. + GCRY_MAC_HMAC_SHA3_384 NEW. + GCRY_MAC_HMAC_SHA3_512 NEW. + GCRY_MAC_POLY1305 NEW. + GCRY_MAC_POLY1305_AES NEW. + GCRY_MAC_POLY1305_CAMELLIA NEW. + GCRY_MAC_POLY1305_SEED NEW. + GCRY_MAC_POLY1305_SERPENT NEW. + GCRY_MAC_POLY1305_TWOFISH NEW. + gcry_md_extract NEW. + GCRY_MD_FLAG_BUGEMU1 NEW [from 1.6.1]. + GCRY_MD_GOSTR3411_CP NEW. + GCRY_MD_SHA3_224 NEW. + GCRY_MD_SHA3_256 NEW. + GCRY_MD_SHA3_384 NEW. + GCRY_MD_SHA3_512 NEW. + GCRY_MD_SHAKE128 NEW. + GCRY_MD_SHAKE256 NEW. + gcry_mpi_ec_decode_point NEW. + gcry_mpi_ec_sub NEW. + GCRY_PK_EDDSA NEW constant. + GCRYCTL_GET_TAGLEN NEW. + GCRYCTL_SET_SBOX NEW. + GCRYCTL_SET_TAGLEN NEW. +- Apply libgcrypt-1.6.3-aliasing.patch only on big-endian + architectures +- update drbg_test.patch and install cavs testing directory again +- As DRBG is upstream, drop pateches: + v9-0001-SP800-90A-Deterministic-Random-Bit-Generator.patch + 0002-Compile-DRBG.patch + 0003-Function-definitions-of-interfaces-for-random.c.patch + 0004-Invoke-DRBG-from-common-libgcrypt-RNG-code.patch + 0005-Function-definitions-for-gcry_control-callbacks.patch + 0006-DRBG-specific-gcry_control-requests.patch + v9-0007-User-interface-to-DRBG.patch + libgcrypt-fix-rng.patch +- drop obsolete: + libgcrypt-fips-dsa.patch + libgcrypt-fips_ecdsa.patch + +------------------------------------------------------------------- +Wed Aug 17 18:21:44 UTC 2016 - astieger@suse.com + +- libgcrypt 1.6.6: + * fix CVE-2016-6313: Issue in the mixing functions of the random + number generators allowed an attacker who obtained a number of + bytes from the standard RNG to predict some of the next ouput. + (bsc#994157) + +------------------------------------------------------------------- +Mon May 16 14:37:45 UTC 2016 - pjanouch@suse.de + +- remove conditionals for unsupported distributions (before 13.2), + it would not build anyway because of new dependencies + +------------------------------------------------------------------- +Mon May 16 12:36:14 UTC 2016 - pjanouch@suse.de + +- make the -hmac package depend on the same version of the library, + fixing bsc#979629 FIPS: system fails to reboot after installing + fips pattern + +------------------------------------------------------------------- +Tue Feb 9 20:51:59 UTC 2016 - astieger@suse.com + +- update to 1.6.5: + * CVE-2015-7511: Mitigate side-channel attack on ECDH with + Weierstrass curves (boo#965902) + +------------------------------------------------------------------- +Sat Oct 10 11:56:08 UTC 2015 - astieger@suse.com + +- follow-up to libgcrypt 1.6.4 update: sosuffix is 20.0.4 + +------------------------------------------------------------------- +Tue Sep 8 08:03:19 UTC 2015 - vcizek@suse.com + +- update to 1.6.4 +- fixes libgcrypt equivalent of CVE-2015-5738 (bsc#944456) + * Speed up the random number generator by requiring less extra + seeding. + * New flag "no-keytest" for ECC key generation. Due to a bug in the + parser that flag will also be accepted but ignored by older version + of Libgcrypt. + * Always verify a created RSA signature to avoid private key leaks + due to hardware failures. + * Other minor bug fixes. + +------------------------------------------------------------------- +Tue Jun 23 15:15:30 UTC 2015 - dvaleev@suse.com + +- Fix gpg2 tests on BigEndian architectures: s390x ppc64 + libgcrypt-1.6.3-aliasing.patch + +------------------------------------------------------------------- +Sun Mar 1 21:16:26 UTC 2015 - astieger@suse.com + +- fix sosuffix for 1.6.3 (20.0.3) + +------------------------------------------------------------------- +Sat Feb 28 19:31:10 UTC 2015 - astieger@suse.com + +- libgcrypt 1.6.3 [bnc#920057]: + * Use ciphertext blinding for Elgamal decryption [CVE-2014-3591]. + * Fixed data-dependent timing variations in modular exponentiation + [related to CVE-2015-0837, Last-Level Cache Side-Channel Attacks + are Practical]. +- update upstream signing keyring + +------------------------------------------------------------------- +Fri Feb 6 18:42:28 UTC 2015 - coolo@suse.com + +- making the build reproducible - see + http://lists.gnupg.org/pipermail/gnupg-commits/2014-September/010683.html + for a very similiar problem + +------------------------------------------------------------------- +Fri Feb 6 18:38:55 UTC 2015 - dimstar@opensuse.org + +- Move %install_info_delete calls from postun to preun: the files + must still be present to be parsed. +- Fix the names passed to install_info for gcrypt.info-[12].gz + instead of gcrypt-[12].info.gz. + +------------------------------------------------------------------- +Fri Feb 6 18:30:26 UTC 2015 - coolo@suse.com + +- fix filename for info pages in %post scripts + +------------------------------------------------------------------- +Wed Nov 5 20:37:24 UTC 2014 - andreas.stieger@gmx.de + +- libgcrypt 1.6.2: + * Map deprecated RSA algo number to the RSA algo number for better + backward compatibility. + * Support a 0x40 compression prefix for EdDSA. + * Improve ARM hardware feature detection and building. + * Fix building for the x32 ABI platform. + * Fix some possible NULL deref bugs. +- remove libgcrypt-1.6.0-use-intenal-functions.patch, upstream + via xtrymalloc macro +- remove libgcrypt-fixed-sizet.patch, upstream +- adjust libgcrypt-1.6.1-use-fipscheck.patch for xtrymalloc change + +------------------------------------------------------------------- +Sun Sep 21 10:08:39 UTC 2014 - vcizek@suse.com + +- disabled curve P-192 in FIPS mode (bnc#896202) + * added libgcrypt-fips_ecdsa.patch +- don't use SHA-1 for ECDSA in FIPS mode +- also run the fips self tests only in FIPS mode + +------------------------------------------------------------------- +Tue Sep 16 13:56:01 UTC 2014 - vcizek@suse.com + +- run the fips self tests at the constructor code + * added libgcrypt-fips_run_selftest_at_constructor.patch + +------------------------------------------------------------------- +Tue Sep 16 12:17:17 UTC 2014 - vcizek@suse.com + +- rewrite the DSA-2 code to be FIPS 186-4 compliant (bnc#894216) + * added libgcrypt-fips-dsa.patch + * install fips186_dsa +- use 2048 bit keys in selftests_dsa + +------------------------------------------------------------------- +Mon Sep 1 10:57:06 UTC 2014 - vcizek@suse.com + +- fix an issue in DRBG patchset + * size_t type is 32-bit on 32-bit systems +- fix a potential NULL pointer deference in DRBG patchset + * patches from https://bugs.g10code.com/gnupg/issue1701 +- added v9-0001-SP800-90A-Deterministic-Random-Bit-Generator.patch +- added v9-0007-User-interface-to-DRBG.patch +- removed v7-0001-SP800-90A-Deterministic-Random-Bit-Generator.patch +- removed v7-0007-User-interface-to-DRBG.patch +- add a subpackage for CAVS testing + * add cavs_driver.pl and cavs-test.sh from the kernel cavs package + * added drbg_test.patch + +------------------------------------------------------------------- +Tue Aug 12 07:43:19 UTC 2014 - meissner@suse.com + +- split off the -hmac package that contains the checksums + +------------------------------------------------------------------- +Mon May 26 12:05:17 UTC 2014 - meissner@suse.com + +- libgcrypt-fix-rng.patch: make drbg work again in FIPS mode. +- libgcrypt-1.6.1-use-fipscheck.patch: library to test is libgcrypt.so.20 + and not libgcrypt.so.11 +- libgcrypt-init-at-elf-load-fips.patch: initialize globally on ELF + DSO loading to meet FIPS requirements. + +------------------------------------------------------------------- +Tue May 13 10:47:51 UTC 2014 - vcizek@suse.com + +- add new 0007-User-interface-to-DRBG.patch from upstream + * fixes bnc#877233 + * supersedes the patch from previous entry + +------------------------------------------------------------------- +Sun May 12 13:25:33 UTC 2014 - tittiatcoke@gmail.com + +- Correct patch 0007-User-interface-to-DRBG.patch so that the + struct used in the route matches the header of the function + +------------------------------------------------------------------- +Tue May 6 13:28:33 UTC 2014 - vcizek@suse.com + +- add support for SP800-90A DRBG (fate#316929, bnc#856312) + * patches by Stephan Mueller (http://www.chronox.de/drbg.html): + 0001-SP800-90A-Deterministic-Random-Bit-Generator.patch.bz2 + 0002-Compile-DRBG.patch + 0003-Function-definitions-of-interfaces-for-random.c.patch + 0004-Invoke-DRBG-from-common-libgcrypt-RNG-code.patch + 0005-Function-definitions-for-gcry_control-callbacks.patch + 0006-DRBG-specific-gcry_control-requests.patch + 0007-User-interface-to-DRBG.patch + * only after 13.1 (the patches need libgpg-error 1.13) +- drop libgcrypt-fips-allow-legacy.patch (not needed and wasn't + applied anyway) + +------------------------------------------------------------------- +Thu Apr 3 12:04:46 UTC 2014 - tchvatal@suse.com + +- Cleanup with spec-cleaner to sort out. +- Really apply ppc64 patch as it was ommited probably by mistake. + +------------------------------------------------------------------- +Thu Mar 27 14:57:22 UTC 2014 - meissner@suse.com + +- FIPS changes (from Fedora): + - replaced libgcrypt-1.5.0-etc_gcrypt_rngseed-symlink.diff by + libgcrypt-1.6.1-fips-cfgrandom.patch + - libgcrypt-fixed-sizet.patch: fixed an int type for -flto + - libgcrypt-1.6.1-use-fipscheck.patch: use the fipscheck binary + - libgcrypt-1.6.1-fips-cavs.patch: add CAVS tests +- use fipscheck only after 13.1 +- libgcrypt-fips-allow-legacy.patch: attempt to allow some + legacy algorithms for gpg2 usage even in FIPS mode. + (currently not applied) + +------------------------------------------------------------------- +Thu Jan 30 13:29:49 UTC 2014 - idonmez@suse.com + +- Drop arm-missing-files.diff, fixed upstream + +------------------------------------------------------------------- +Wed Jan 29 18:40:49 UTC 2014 - andreas.stieger@gmx.de + +- libgcrypt 1.6.1, a bugfix release with the folloging fixes: + * Added emulation for broken Whirlpool code prior to 1.6.0. + * Improved performance of KDF functions. + * Improved ECDSA compliance. + * Fixed message digest lookup by OID (regression in 1.6.0). + * Fixed memory leaks in ECC code. + * Fixed some asm build problems and feature detection bugs. + * Interface changes relative to the 1.6.0 release: + GCRY_MD_FLAG_BUGEMU1 NEW (minor API change). + +------------------------------------------------------------------- +Fri Jan 3 16:36:21 UTC 2014 - dmueller@suse.com + +- add arm-missing-files.diff: Add missing files to fix build + +------------------------------------------------------------------- +Fri Jan 3 09:43:39 UTC 2014 - mvyskocil@suse.com + +- fix bnc#856915: can't open /dev/urandom + * correct libgcrypt-1.5.0-etc_gcrypt_rngseed-symlink.diff +- require libgpg-error 1.11 or higher + +------------------------------------------------------------------- +Thu Dec 19 13:53:21 UTC 2013 - mvyskocil@suse.com + +- fix dependency for 32bit devel package +- name hmac files according soname +- fix hmac subpackage dependency + +------------------------------------------------------------------- +Thu Dec 19 09:03:21 UTC 2013 - mvyskocil@suse.com + +- update to 1.6. + * Removed the long deprecated gcry_ac interface. Thus Libgcrypt is + not anymore ABI compatible to previous versions if they used the ac + interface. Check NEWS in libgcrypt-devel for removed interfaces. + * Removed the module register subsystem. + * The deprecated message digest debug macros have been removed. Use + gcry_md_debug instead. + * Removed deprecated control codes. + * Improved performance of most cipher algorithms as well as for the + SHA family of hash functions. + * Added support for the IDEA cipher algorithm. + * Added support for the Salsa20 and reduced Salsa20/12 stream ciphers. + * Added limited support for the GOST 28147-89 cipher algorithm. + * Added support for the GOST R 34.11-94 and R 34.11-2012 (Stribog) + hash algorithms. + * Added a random number generator to directly use the system's RNG. + Also added an interface to prefer the use of a specified RNG. + * Added support for the SCRYPT algorithm. + * Mitigated the Yarom/Falkner flush+reload side-channel attack on RSA + secret keys. See [CVE-2013-4242]. + * Added support for Deterministic DSA as per RFC-6969. + * Added support for curve Ed25519. + * Added a scatter gather hash convenience function. + * Added several MPI amd SEXP helper functions. + * Added support for negative numbers to gcry_mpi_print, + gcry_mpi_aprint and gcry_mpi_scan. + * The algorithm ids GCRY_PK_ECDSA and GCRY_PK_ECDH are now + deprecated. Use GCRY_PK_ECC if you need an algorithm id. + * Changed gcry_pk_genkey for "ecc" to only include the curve name and + not the parameters. The flag "param" may be used to revert this. + * Added a feature to globally disable selected hardware features. + * Added debug helper functions. +- rebased patches + * libgcrypt-1.5.0-etc_gcrypt_rngseed-symlink.diff + * libgcrypt-ppc64.patch +- add libgcrypt-1.6.0-use-intenal-functions.patch to fix fips.c build +- Move all documentation to -devel package + +------------------------------------------------------------------- +Fri Jul 26 22:05:46 UTC 2013 - andreas.stieger@gmx.de + +- update to 1.5.3 [bnc#831359] CVE-2013-4242 + * Mitigate the Yarom/Falkner flush+reload side-channel attack on + RSA secret keys. See . + +------------------------------------------------------------------- +Thu Jul 25 09:15:43 UTC 2013 - mvyskocil@suse.com + +- port SLE enhancenments to Factory (bnc#831028) + * add libgcrypt-unresolved-dladdr.patch (bnc#701267) + * add libgcrypt-1.5.0-etc_gcrypt_rngseed-symlink.diff (bnc#724841) + * add libgcrypt-1.5.0-LIBGCRYPT_FORCE_FIPS_MODE-env.diff +- install .hmac256.hmac (bnc#704068) +- enable varuous new options in configure (m-guard, hmac binary check and + random device linux) +- build with all ciphers, pubkeys and digest by default as whitelist + simply allowed them all + +------------------------------------------------------------------- +Mon Jun 17 13:22:33 UTC 2013 - coolo@suse.com + +- avoid gpg-offline in bootstrap packages + +------------------------------------------------------------------- +Sun Jun 16 22:56:56 UTC 2013 - crrodriguez@opensuse.org + +- Library must be built with large file support in + 32 bit archs. + +------------------------------------------------------------------- +Thu Apr 18 18:23:36 UTC 2013 - andreas.stieger@gmx.de + +- update to 1.5.2 + * The upstream sources now contain the IDEA algorithm, dropping: + idea.c.gz + libgcrypt-1.5.0-idea.patch + libgcrypt-1.5.0-idea_codecleanup.patch + * Made the Padlock code work again (regression since 1.5.0). + * Fixed alignment problems for Serpent. + * Fixed two bugs in ECC computations. + +------------------------------------------------------------------- +Fri Mar 22 09:31:11 UTC 2013 - mvyskocil@suse.com + +- add GPL3.0+ to License tag because of dumpsexp (bnc#810759) + +------------------------------------------------------------------- +Mon Mar 18 20:41:00 UTC 2013 - andreas.stieger@gmx.de + +- update to 1.5.1 + * Allow empty passphrase with PBKDF2. + * Do not abort on an invalid algorithm number in + gcry_cipher_get_algo_keylen and gcry_cipher_get_algo_blklen. + * Fixed some Valgrind warnings. + * Fixed a problem with select and high fd numbers. + * Improved the build system + * Various minor bug fixes. + * Interface changes relative to the 1.5.0 release: + GCRYCTL_SET_ENFORCED_FIPS_FLAG NEW. + GCRYPT_VERSION_NUMBER NEW. +- add verification of source code signatures +- now requires automake 1.11 to build + +------------------------------------------------------------------- +Sat Feb 2 18:51:33 UTC 2013 - coolo@suse.com + +- update license to new format + +------------------------------------------------------------------- +Tue Jun 12 21:19:18 UTC 2012 - chris@computersalat.de + +- fix deps + * libgpg-error-devel >= 1.8 +- add libsoname macro + +------------------------------------------------------------------- +Sun Feb 12 15:23:56 UTC 2012 - crrodriguez@opensuse.org + +- Libraries back into %{_libdir}, /usr merge project + +------------------------------------------------------------------- +Sat Dec 24 23:51:26 UTC 2011 - opensuse@dstoecker.de + +- add the missing IDEA algorithm after the patent is no longer relevant + +------------------------------------------------------------------ +Sun Nov 13 14:37:29 UTC 2011 - jengelh@medozas.de + +- Remove redundant/unwanted tags/section (cf. specfile guidelines) + +------------------------------------------------------------------- +Sun Nov 13 09:16:36 UTC 2011 - coolo@suse.com + +- add libtool as explicit buildrequire to avoid implicit dependency from prjconf + +------------------------------------------------------------------- +Sun Oct 2 18:38:28 UTC 2011 - crrodriguez@opensuse.org + +- Update to version 1.5.0, most important changes + * Uses the Intel AES-NI instructions if available + * Support ECDH. + +------------------------------------------------------------------- +Fri Nov 19 09:59:41 UTC 2010 - mvyskocil@suse.cz + +- update to 1.4.6 + * Fixed minor memory leak in DSA key generation. + * No more switching to FIPS mode if /proc/version is not readable. + * Fixed a sigill during Padlock detection on old CPUs. + * Boosted SHA-512 performance by 30% on ia32 boxes and gcc 4.3; + SHA-256 went up by 25%. + * New variants of the TIGER algorithm. + * New cipher algorithm mode for AES-WRAP. + * Interface changes relative to the 1.4.2 release: + GCRY_MD_TIGER1 NEW + GCRY_MD_TIGER2 NEW + GCRY_CIPHER_MODE_AESWRAP NEW + +------------------------------------------------------------------- +Sun Jul 4 19:07:16 UTC 2010 - jengelh@medozas.de + +- add missing definition of udiv_qrnnd for sparcv9:32 +- use %_smp_mflags + +------------------------------------------------------------------- +Sat Dec 19 12:58:20 CET 2009 - jengelh@medozas.de + +- add baselibs.conf as a source +- disable the use of hand-coded assembler functions on sparc - + this is giving me an infinite loop with ./tests/prime + (specifically ./sparc32v8/mpih-mul1.S:_gcry_mpih_mul_1. + Fedora disables this too. + +------------------------------------------------------------------- +Tue Apr 7 15:45:06 CEST 2009 - crrodriguez@suse.de + +- update to version 1.4.4 + * Publish GCRY_MODULE_ID_USER and GCRY_MODULE_ID_USER_LAST constants. + This functionality has been in Libgcrypt since 1.3.0. + * MD5 may now be used in non-enforced fips mode. + * Fixed HMAC for SHA-384 and SHA-512 with keys longer than 64 bytes. + * In fips mode, RSA keys are now generated using the X9.31 algorithm + and DSA keys using the FIPS 186-2 algorithm. + * The transient-key flag is now also supported for DSA key + generation. DSA domain parameters may be given as well. + +------------------------------------------------------------------- +Thu Jan 29 10:57:01 CET 2009 - olh@suse.de + +- obsolete libgcrypt-error-XXbit in the library subpackage + +------------------------------------------------------------------- +Wed Dec 10 12:34:56 CET 2008 - olh@suse.de + +- use Obsoletes: -XXbit only for ppc64 to help solver during distupgrade + (bnc#437293) + +------------------------------------------------------------------- +Tue Nov 11 17:23:54 CET 2008 - mkoenig@suse.de + +- build rijndael.c with -fno-strict-aliasing [bnc#443693] + +------------------------------------------------------------------- +Thu Oct 30 12:34:56 CET 2008 - olh@suse.de + +- obsolete old -XXbit packages (bnc#437293) + +------------------------------------------------------------------- +Mon Jun 30 11:47:59 CEST 2008 - mkoenig@suse.de + +- update to version 1.4.1 + * Fixed a bug which led to the comsumption of far too much + entropy for the intial seeding + * Improved AES performance for CFB and CBC modes + +------------------------------------------------------------------- +Sun May 11 11:54:39 CEST 2008 - coolo@suse.de + +- fix rename of xxbit packages + +------------------------------------------------------------------- +Thu Apr 10 12:54:45 CEST 2008 - ro@suse.de + +- added baselibs.conf file to build xxbit packages + for multilib support + +------------------------------------------------------------------- +Thu Jan 17 12:20:25 CET 2008 - mkoenig@suse.de + +- update to version 1.4.0: + * The entire library is now under the LGPL. The helper programs and + the manual are under the GPL + * New control code GCRYCTL_PRINT_CONFIG + * Experimental support for ECDSA + * Assembler support for the AMD64 architecture + * Non executable stack support is now used by default + * New configure option --enable-random-daemon + * The new function gcry_md_debug should be used instead of the + gcry_md_start_debug and gcry_md_stop_debug macros. + * Support for DSA2 + * Reserved algorithm ranges for use by applications + * gcry_mpi_rshift does not anymore truncate the shift count + * Support for OFB encryption mode + * Support for the Camellia cipher + * Support for the SEED cipher + * Support for SHA-224 and HMAC using SHA-384 and SHA-512 + * Reading and writing the random seed file is now protected by a + fcntl style file lock + * Made the RNG immune against fork without exec + * Changed the way the RNG gets initialized + * The ASN.1 DER template for SHA-224 has been fixed + * The ACE engine of VIA processors is now used for AES-128 +- changed package layout to conform shlib policy: + new subpackage libgcrypt11 +- disable static library +- for reference: bugzilla entry of last change #304749 + +------------------------------------------------------------------- +Thu Sep 13 01:28:53 CEST 2007 - ltinkl@suse.cz + +- add sanity check for mpi of size 0 (#304479) + +------------------------------------------------------------------- +Mon Feb 5 10:25:21 CET 2007 - mkoenig@suse.de + +- update to version 1.2.4: + * Fixed a bug in the memory allocator which could have been the + reason for some of non-duplicable bugs. + * Other minor bug fixes. + +------------------------------------------------------------------- +Wed Dec 13 12:47:48 CET 2006 - mkoenig@suse.de + +- get rid of .la file and fix devel so link + +------------------------------------------------------------------- +Tue Dec 5 18:30:30 CET 2006 - mkoenig@suse.de + +- move shared lib to /%_lib + +------------------------------------------------------------------- +Thu Aug 31 14:29:56 CEST 2006 - mkoenig@suse.de + +- update to version 1.2.3: + * Rewrote gcry_mpi_rshift to allow arbitrary shift counts. + * Minor bug fixes. +- added libgpg-error-devel and glibc-devel to Requires tag + of devel subpackage + +------------------------------------------------------------------- +Wed Jan 25 21:37:28 CET 2006 - mls@suse.de + +- converted neededforbuild to BuildRequires + +------------------------------------------------------------------- +Wed Nov 2 16:44:48 CET 2005 - hvogel@suse.de + +- enable noexecstack +- build ac.c with fno-strict-aliasing + +------------------------------------------------------------------- +Tue Oct 25 13:40:15 CEST 2005 - hvogel@suse.de + +- update to version 1.2.2 + +------------------------------------------------------------------- +Thu Jun 23 11:26:58 CEST 2005 - hvogel@suse.de + +- call install_info macro in post/postun of the devel package +- depend on libgcrypt +- add clean section + +------------------------------------------------------------------- +Tue Jan 18 11:51:51 CET 2005 - hvogel@suse.de + +- update to version 1.2.1 + +------------------------------------------------------------------- +Tue Jan 11 16:48:10 CET 2005 - schwab@suse.de + +- Fix info dir entry. + +------------------------------------------------------------------- +Wed Nov 17 11:22:44 CET 2004 - hvogel@suse.de + +- require libgpg-error-devel (Bug #48271) +- get rid of the NLD parts + +------------------------------------------------------------------- +Wed Jul 14 11:12:54 CEST 2004 - adrian@suse.de + +- create -devel subpackage +- prepare for nld + +------------------------------------------------------------------- +Wed May 19 14:57:45 CEST 2004 - hvogel@suse.de + +- update to version 1.2.0 + +------------------------------------------------------------------- +Mon Mar 22 16:48:53 CET 2004 - meissner@suse.de + +- disable make check, because it uses /dev/random whihc is + not filled on some server machines. + +------------------------------------------------------------------- +Wed Mar 17 15:01:51 CET 2004 - meissner@suse.de + +- fixed too over enthusiastic powerpc switches to make it work + on ppc64. (It compiled before, but did not work). +- enabled make check. + +------------------------------------------------------------------- +Wed Feb 18 12:14:36 CET 2004 - kukuk@suse.de + +- Build against system pthread library, not pth. + +------------------------------------------------------------------- +Tue Feb 17 21:11:40 CET 2004 - hvogel@suse.de + +- update to version 1.1.91 +- fix autoconf quotations + +------------------------------------------------------------------- +Sat Jan 10 19:20:41 CET 2004 - adrian@suse.de + +- add %run_ldconfig to %postun + +------------------------------------------------------------------- +Sun Jul 27 16:12:54 CEST 2003 - poeml@suse.de + +- add libgcrypt-1.1.12-sexp-valgrind-error.patch from SLEC + +------------------------------------------------------------------- +Thu Apr 24 12:20:23 CEST 2003 - ro@suse.de + +- fix install_info --delete call and move from preun to postun + +------------------------------------------------------------------- +Mon Feb 10 22:51:26 CET 2003 - mmj@suse.de + +- Use %install_info macro [#23433] + +------------------------------------------------------------------- +Mon Feb 10 16:11:55 CET 2003 - mc@suse.de + +- switch to version 1.1.12 +- gcry_pk_sign, gcry_pk_verify and gcry_pk_encrypt can now handle an + optional pkcs1 flags parameter in the S-expression. A similar flag + may be passed to gcry_pk_decrypt but it is only syntactically + implemented. +- New convenience macro gcry_md_get_asnoid. +- There is now some real stuff in the manual. +- New algorithm: MD4 +- Implemented ciphertext stealing. +- Support for plain old DES +- Smaller bugs fixes and a few new OIDs. + +------------------------------------------------------------------- +Tue Jan 14 14:03:27 CET 2003 - nadvornik@suse.cz + +- fixed multi-line string literals + +------------------------------------------------------------------- +Thu Aug 1 23:51:10 CEST 2002 - poeml@suse.de + +- create package + diff --git a/libgcrypt.keyring b/libgcrypt.keyring new file mode 100644 index 0000000..dd3bb0b --- /dev/null +++ b/libgcrypt.keyring @@ -0,0 +1,86 @@ +-----BEGIN PGP PUBLIC KEY BLOCK----- + +mQGNBFjLuq4BDACnM7zNSIaVMAacTwjXa5TGYe13i6ilHe4VL0NShzrgzjcQg531 +3cRgiiiNA7OSOypMqVs73Jez6ZUctn2GVsHBrS/io9NcuC9pVwf8a61WlcEa+EtB +a3G7HlBmEWnwaUdAtWKNuAi9Xn+Ir7H2xEdksmmd5a0/QnL+sX705boVPF/tpYtb +LGpPxa78tNrtxDkSwy8Wmi0IADYLI5yI7/yUGeJd8RSCU/fLRKC9fG7YOZRq0tsO +MhVNWmtUjbG6e73Lu8LKnCZgs1/fC8hvPyARieSV5mdN8s1oWd7oYctfgL4uBleD +ItAA8GhjKejutzHN8Ei/APw6AiiSyEjnPg+cTX8OgvLGJWjks0H6mPZeB1v/kGyZ +hBS9vm540h2/MmlVN2ntiCK5TZGeSWpqddiqusfVXotMRpN4HeLKoZh4RAncaCbZ +F/S+YLeN+kMXY4k3Fqt1fjTX6veFCbthI9pDdHzU9LfUVNp9D/5ktC/tYMORMegV ++wSMxi9G2YWKJkMAEQEAAYkBzgQfAQgAOBYhBFuAxXVCmPDLVdjtarzvfilLCS4o +BQJYy8DdFwyAAZSlyaA8L+XKOwldjh/fcjz0YraxAgcAAAoJELzvfilLCS4oNgoL +/0+K1xIx8JW7Lk5M6bYCvNA4fdlEcwQIT4UidJFM9m+suxYFWIGfebvHpRlEuJTg +dBjkEit8uLAoJXU0BRkKTLrzTF+qDUE79Wfx/R+0nOgJ7aMykQOi0AvuwzMYz4dg +xIVS2Daou4DF7bh/KF8+fqrmq8P8W1ZrkuFDanMWpHeAPx1uj2skYbo7uPqFdvlJ +hlNHrcxlcCkjf1InAt0Xt5lMvEsCRUPf9xAH4mNEhs0lh9c+200YPRmtnLWAzc1K +ckLIC8Q+mUR3DjZDqBlDBEPegXkrI0+MlvRA+9AnAm4YPqTMUfpZ6ZOAWeFjC/6Z +QYxG/AdWGkb4WFindzklQfybEuiekP8vU07ACQwSwH8PYe0UCom1YrlRUjX7QLkn +ZLWoeZg8BZy9GTM1Ut7Q1Q2uTw6mxxISuef+RFgYOHjWwLpFWZpqC88xERl7o/iz +iERJRt/593IctbjO9wenWt2peIAwzR4nz7LqM6ZFTdRAETmcdSvYRhg2Qt8hUE47 +CbQkQW5kcmUgSGVpbmVja2UgKFJlbGVhc2UgU2lnbmluZyBLZXkpiQHUBBMBCAA+ +FiEEW4DFdUKY8MtV2O1qvO9+KUsJLigFAljLuq4CGwMFCRLMAwAFCwkIBwIGFQgJ +CgsCBBYCAwECHgECF4AACgkQvO9+KUsJLihC/QwAhCC+SEvcFLcutgZ8HfcCtoZs +IoVzZEy7DjqIvGgnTssD8HCLnIAHCDvnP7dJW3uMuLCdSqym3cjlEIiQMsaGywkl +fzJISAwJrGQdWSKRd535jXpEXQlXDKal/IwMKAUt0PZtlCc9S3gwixQryxdJ28lJ +6h2T9fVDr8ZswMmTAFG91uctfhjKOMgPt8UhSPGW484WsIsQgkbOvf+Kfswl0eHu +ywX+pKAB5ZQ/9GVC6Ug4xfrdiJL0azJTPnvjMY5JYp6/L9RURs5hP5AnHR2j/PPo +sAtsFCjmbRbOMiASzklnUJPbSz5kfLloDWZmrUScjbzmsXehGyt433JGyRhZJl4x +/jPbzKhaaAHsGd+fRao6vlLOwFywDDVMp6JuyK7UeUb7I8ekTbSkGFA+l2Oa3O6/ +Y7PYhq7hwwAFuZckYI98IpHNCG1fS9W07FyKdvQbK1PbF1JFRKfsUCWYMKqDnbqE +o5jivPEHZImw6iYhhXcyEYl8fjcb9T6/S+wOP7aviQGzBBABCAAdFiEElKXJoDwv +5co7CV2OH99yPPRitrEFAljLv5sACgkQH99yPPRitrFw4gv/XFMFN+/LHsn9hJOP +4rCwl1yUuxXuYmZgc0sRoY3EpeQkJVyKurQuqqKoy2VuoMiF0O1kAQmGoFtVPUk7 +b8hCoutqB5GyeyKcoLP+WINgVhB2gXg7TSp3MPLBKkgqvSDvPitgRxBqFb4LW8LJ +bDbfwGrzIvXfDV3WvsrHVPbc2fhlWdL8d+3AE6mFiXF3eTpgmV3ApSBQV12MkkCk +icLIPmp+ZxZON+OP52ZXkRtfMgOy4Oa/41agrViDAZdMOGeGkhPertQheQZgXzmo +GF5Wz498HPM80Kv35X91l3iGzL+icEtO+tWea2YscsZ6qpRe2lfVPHk3B+anlmCj +m4kM4cBd39xa4HHSVh/bRHbZNtgVr7slQCKxlHgQOGVI5vCxPCwEsgJ2KBk03Nk/ +IA9EKO+czfh3/bHW6uMbEqrYDCnt+hmzZrpKDSGcwS/KOhvMUIMlb7/8vDKum6mp +/8xAtVZ6IAxYZNt3qg7Y7aLRtzCTyqm8rJQrZPtRaQcgLoEimDMEX0PliRYJKwYB +BAHaRw8BAQdAz75Hlekc16JhhfI0MKdEVxLdkxhcMCO0ZG6WMBAmNpe0H1dlcm5l +ciBLb2NoIChkaXN0IHNpZ25pbmcgMjAyMCmImgQTFgoAQhYhBG2qbmSnbShAVxtJ +AlKIl7gmQDraBQJfQ+w1AhsDBQkShccRBQsJCAcCAyICAQYVCgkICwIEFgIDAQIe +BwIXgAAKCRBSiJe4JkA62nmuAP9uL/HOdB0gvwWrH+FpURJLs4bnaZaPIk9ARrU0 +EXRgJgD/YCGfHQXpIPT0ZaXuwJexK04Z+qMFR/bM1q1Leo5CjgaIbQQQEQsAHRYh +BIBhWHD1utaQMzaG0PKthaweQrNnBQJfQ/HmAAoJEPKthaweQrNnIZkA3jG6LcZv +V/URn8Y8OJqsyYa4C3NI4nN+OhEvYhgA4PHzMnALeXIpA2gblvjFIPJPAhDBAU37 +c5PA6+6IdQQQFggAHRYhBK6oTtzwGthsRwHIXGMROuhmWH0KBQJfQ/IlAAoJEGMR +OuhmWH0K1+MA/0uJ5AHcnSfIBEWHNJwwVVLGyrxAWtS2U+zeymp/UvlPAQDErCLZ +l0dBiPG3vlowFx5TNep7tanBs6ZJn8F1ao1tAIkBMwQQAQgAHRYhBNhpISPEBl3q +Xg86tSSbOdJPJeO2BQJfQ/OuAAoJECSbOdJPJeO2DVoH/0o9if66ph6FJrgr+A/W +HNVeHxmM5tUQhpL1wpRS70SKcsJgolf5CxO5iTQf3HlZe544xGbIU/aCTJsWw9zi +UE8KmhAtKV4eL/7oQ7xx4nxPnABLpudtM8A44nsM1x/XiYrJnnDm29QjYEGd2Hi8 +7npc7VWKzLoj+I/WcXquynJi5O9TUxW9Bknd1pjpxFkf8v+msjBzCD5VKJgr0CR8 +wA6peQBWeGZX2HacosMIZH4TfL0r0TFla6LJIkNBz9DyIm1yL4L8oRH0950hQljP +C7TM3L7aRpX+4Kph6llFz6g7MALGFP95kyJ6o+XED9ORuuQVZMBMIkNC0tXOu10V +bdqIdQQQFgoAHRYhBMHTS2khnkruwLocIeP9/yGORbcrBQJfQ/P8AAoJEOP9/yGO +Rbcr3lQBAMas8Vl3Hdl3g2I283lz1uHiGvlwcnk2TLeB+U4zIwC9AQCy0nnazVNt +VQPID1ZCMoaOX7AzOjaqQDLf4j+dVTxgBJgzBGCkgocWCSsGAQQB2kcPAQEHQJmd +fwp8jEN5P3eEjhQiWk6zQi8utvgOvYD57XmE+H8+tCBOaWliZSBZdXRha2EgKEdu +dVBHIFJlbGVhc2UgS2V5KYiaBBMWCgBCFiEErI4RW/c+LY1H+pkI6Y6bLRnGyL0F +AmCkgocCGwMFCQsNBpkFCwkIBwIDIgIBBhUKCQgLAgQWAgMBAh4HAheAAAoJEOmO +my0Zxsi9/4IA/1rvSr3MU+Sv4jhNDzD+CeC3gmHkPew6pi9VHEsEwdgmAQD2BtiX +7w1sJL/CBylGWv5jxj4345mP9YfZm0RsgzPjDIh1BBAWCAAdFiEEJJyzdxdQdF1c +3TI84mewUjZPAo0FAmFAQ54ACgkQ4mewUjZPAo1CiAD+KTT1UVdQTGHMyvHwZocS +QjU8xhcZrTet+dvvjrE5+4MA/RBdJPZgFevUKu68NEy0Lo+RbkeCtmQJ/c8v5ieF +vW0AiQEzBBABCAAdFiEEEkEkvTtIYq96CkLxALRevUynur4FAmFAQ7cACgkQALRe +vUynur4kaAgAolPR8TNWVS0vXMKrr0k0l2M/8QkZTaLZx1GT9Nx1yb4WJKY7ElPM +YkhGDxetvFBETx0pH/6R3jtj6Crmur+NKHVSRY+rCYpFPDn6ciIOryssRx2G4kCZ +t+nFB9JyDbBOZAR8DK4pN1mAxG/yLDt4oKcUQsP2xlEFum+phxyR8KyYCpkwKRxY +eK+6lfilQuveoUwp/Xx5wXPNUy6q4eOOovCW7gS7I7288NGHCa2ul8sD6vA9C4mM +4Zxaole9P9wwJe1zZFtCIy88zHM9vqv+YM9DxMCaW24+rUztr7eD4bCRdG+QlSh+ +7R/TaqSxY1eAAd1J5tma9CNJO73pTKU+/JhTBGFpSqMTCSskAwMCCAEBBwIDBF6X +D9NmUQDgiyYNbhs1DMJ14mIw812wY1HVx/4QWYWiBunhrvSFxVbzsjD7/Wv+v3bm +MPrL+M2DLyFiSewNmcS0JEdudVBHLmNvbSAoUmVsZWFzZSBTaWduaW5nIEtleSAy +MDIxKYiaBBMTCABCFiEEAvON/3Mf+XywOaHaVJ5pXpBboggFAmFpSqMCGwMFCQ9x +14oFCwkIBwIDIgIBBhUKCQgLAgQWAgMBAh4HAheAAAoJEFSeaV6QW6IITkoA/RYa +jaTl1eEBU/Gdm12o3jrI55N5xZK2XTqSx25clVyjAP0XwMW/Og5+ND1ri3bAqADV +WlBDUswz8wYxsb0C4kYBkoh1BBAWCgAdFiEEbapuZKdtKEBXG0kCUoiXuCZAOtoF +AmFpTvEACgkQUoiXuCZAOtrJQAEAh7YyykjAy/Qs1yC3ji8iBfIVnPXvblrIx3SR +RyDwRC8BAKtZbEuKTtPlgkLUgMleTcZJ/vEhJE+GvfQ9o5gWCqEFiHUEEBYKAB0W +IQTB00tpIZ5K7sC6HCHj/f8hjkW3KwUCYWlPWgAKCRDj/f8hjkW3Kx4eAQDp6aGS +N/fU4xLl8RSvQUVjVA+aCTrMQR3hRwqw8liF2wEA3O3ECxz6e1+DoItYoJBBLKLw +eiInsGZ/+h5XYrpXTgA= +=4+Sn +-----END PGP PUBLIC KEY BLOCK----- diff --git a/libgcrypt.spec b/libgcrypt.spec new file mode 100644 index 0000000..8a58bdd --- /dev/null +++ b/libgcrypt.spec @@ -0,0 +1,244 @@ +# +# spec file for package libgcrypt +# +# Copyright (c) 2025 SUSE LLC +# +# All modifications and additions to the file contributed by third parties +# remain the property of their copyright owners, unless otherwise agreed +# upon. The license for this file, and modifications and additions to the +# file, is the same license as for the pristine package itself (unless the +# license for the pristine package is not an Open Source License, in which +# case the license is the MIT License). An "Open Source License" is a +# license that conforms to the Open Source Definition (Version 1.9) +# published by the Open Source Initiative. + +# Please submit bugfixes or comments via https://bugs.opensuse.org/ +# + + +%define libsover 20 +%define libsoname %{name}%{libsover} +%define hmac_key orboDeJITITejsirpADONivirpUkvarP +Name: libgcrypt +Version: 1.11.0 +Release: 0 +Summary: The GNU Crypto Library +License: GPL-2.0-or-later AND LGPL-2.1-or-later AND GPL-3.0-or-later +Group: Development/Libraries/C and C++ +URL: https://gnupg.org/software/libgcrypt +Source: https://gnupg.org/ftp/gcrypt/libgcrypt/%{name}-%{version}.tar.bz2 +Source1: https://gnupg.org/ftp/gcrypt/libgcrypt/%{name}-%{version}.tar.bz2.sig +Source2: baselibs.conf +Source3: random.conf +Source4: hwf.deny +# https://www.gnupg.org/signature_key.html +Source5: https://gnupg.org/signature_key.asc#/%{name}.keyring +Source99: libgcrypt.changes +Patch1: libgcrypt-1.10.0-allow_FSM_same_state.patch +#PATCH-FIX-OPENSUSE Do not pull revision info from GIT when autoconf is run +Patch2: libgcrypt-nobetasuffix.patch +# FIPS patches: +#PATCH-FIX-SUSE bsc#1190700 FIPS: Provide a service-level indicator for PK +Patch100: libgcrypt-FIPS-SLI-pk.patch +#PATCH-FIX-SUSE bsc#1190700 FIPS: Check keylength in gcry_fips_indicator_kdf() +Patch101: libgcrypt-FIPS-SLI-kdf-leylength.patch +#PATCH-FIX-SUSE bsc#1190700 FIPS add indicators +Patch102: libgcrypt-FIPS-SLI-hash-mac.patch +#PATCH-FIX-SUSE bsc#1202117 FIPS: Get most of the entropy from rndjent_poll +Patch104: libgcrypt-FIPS-rndjent_poll.patch +#PATCH-FIX-SUSE bsc#1220896 FIPS: Replace the built-in jitter rng with standalone version +Patch105: libgcrypt-FIPS-jitter-standalone.patch +#PATCH-FIX-SUSE bsc#1220895 FIPS: Enforce the interpretation and use of jitter rng +Patch106: libgcrypt-FIPS-jitter-errorcodes.patch +#PATCH-FIX-SUSE bsc#1220893 FIPS: Use Jitter RNG for the whole length entropy buffer +Patch107: libgcrypt-FIPS-jitter-whole-entropy.patch +#PATCH-FIX-SUSE Remove not used rol64() definition after removing the built-in jitter rng +Patch108: libgcrypt-rol64-redefinition.patch +#PATCH-FIX-UPSTREAM jsc#PED-12227: SLI revamp and differentiate SHA1 in the service level indicator +Patch200: libgcrypt-fips-Introduce-an-internal-API-for-FIPS-service-indicator.patch +Patch201: libgcrypt-fips-Introduce-GCRYCTL_FIPS_SERVICE_INDICATOR-and-the-macro.patch +Patch202: libgcrypt-fips-kdf-Implement-new-FIPS-service-indicator-for-gcry_kdf_derive.patch +Patch203: libgcrypt-fips-md-Implement-new-FIPS-service-indicator-for-gcry_md_hash_.patch +Patch204: libgcrypt-fips-tests-Add-t-digest.patch +Patch205: libgcrypt-fips-Change-the-internal-API-for-new-FIPS-service-indicator.patch +Patch206: libgcrypt-fips-md-Implement-new-FIPS-service-indicator-for-gcry_md_open-API.patch +Patch207: libgcrypt-fips-tests-Add-tests-for-md_open-write-read-close-for-t-digest.patch +Patch208: libgcrypt-fips-mac-Implement-new-FIPS-service-indicator-for-gcry_mac_open.patch +Patch209: libgcrypt-fips-cipher-Implement-new-FIPS-service-indicator-for-cipher_open.patch +Patch210: libgcrypt-tests-fips-Add-gcry_mac_open-tests.patch +Patch211: libgcrypt-tests-fips-Rename-t-fips-service-ind.patch +Patch212: libgcrypt-tests-fips-Move-KDF-tests-to-t-fips-service-ind.patch +Patch213: libgcrypt-tests-fips-Add-gcry_cipher_open-tests.patch +Patch214: libgcrypt-fips-md-gcry_md_copy-should-care-about-FIPS-service-indicator.patch +Patch215: libgcrypt-fips-cipher-Implement-FIPS-service-indicator-for-gcry_pk_hash_-API.patch +Patch216: libgcrypt-fips-Introduce-GCRYCTL_FIPS_REJECT_NON_FIPS.patch +Patch217: libgcrypt-Fix-the-previous-change.patch +Patch218: libgcrypt-fips-Rejection-by-GCRYCTL_FIPS_REJECT_NON_FIPS-not-by-open-flags.patch +Patch219: libgcrypt-fips-cipher-Add-behavior-not-to-reject-but-mark-non-compliant.patch +Patch220: libgcrypt-fips-ecc-Add-rejecting-or-marking-for-gcry_pk_get_curve.patch +Patch221: libgcrypt-tests-Add-more-tests-to-tests-t-fips-service-ind.patch +Patch222: libgcrypt-fips-ecc-Check-DATA-in-gcry_pk_sign-verify-in-FIPS-mode.patch +Patch223: libgcrypt-fips-cipher-Fix-memory-leak-for-gcry_pk_hash_sign.patch +Patch224: libgcrypt-build-Improve-__thread-specifier-check.patch +Patch225: libgcrypt-cipher-Check-and-mark-non-compliant-cipher-modes-in-the-SLI.patch +Patch226: libgcrypt-cipher-Rename-_gcry_cipher_is_mode_fips_compliant.patch +Patch227: libgcrypt-cipher-Don-t-differentiate-GCRY_CIPHER_MODE_CMAC-in-FIPS-mode.patch +Patch228: libgcrypt-cipher-rsa-Mark-reject-SHA1-unknown-with-RSA-signature-generation.patch +Patch229: libgcrypt-md-Fix-gcry_md_algo_info-to-mark-reject-under-FIPS-mode.patch +Patch230: libgcrypt-md-Use-check_digest_algo_spec-in-_gcry_md_selftest.patch +Patch231: libgcrypt-tests-Update-t-fips-service-ind-using-GCRY_MD_SHA256-for-KDF-tests.patch +Patch232: libgcrypt-fips-cipher-Do-the-computation-when-marking-non-compliant.patch +Patch233: libgcrypt-tests-Allow-tests-with-USE_RSA.patch +Patch234: libgcrypt-cipher-Add-KAT-for-non-rfc6979-ECDSA-with-fixed-k.patch +Patch235: libgcrypt-cipher-Differentiate-use-of-label-K-in-the-SLI.patch +Patch236: libgcrypt-cipher-Differentiate-igninvflag-in-the-SLI.patch +Patch237: libgcrypt-cipher-Differentiate-no-blinding-flag-in-the-SLI.patch +Patch238: libgcrypt-fips-cipher-Add-GCRY_FIPS_FLAG_REJECT_PK_FLAGS.patch +Patch239: libgcrypt-cipher-ecc-Fix-for-supplied-K.patch +Patch240: libgcrypt-cipher-visibility-Differentiate-use-of-random-override-in-the-SLI.patch +Patch241: libgcrypt-cipher-fips-Fix-for-random-override.patch +Patch243: libgcrypt-md-Make-SHA-1-non-FIPS-internally-for-1.12-API.patch +Patch244: libgcrypt-fips-Fix-GCRY_FIPS_FLAG_REJECT_MD.patch +Patch245: libgcrypt-doc-Add-about-GCRYCTL_FIPS_SERVICE_INDICATOR.patch +Patch246: libgcrypt-doc-Fix-syntax-error.patch +# PATCH-FIX-UPSTREAM bsc#1242419 CSHAKE basic regression test failure in s390x +Patch247: libgcrypt-Disable-SHA3-s390x-acceleration-for-CSHAKE.patch + +BuildRequires: automake >= 1.14 +BuildRequires: libgpg-error-devel >= 1.49 +BuildRequires: libtool +BuildRequires: makeinfo +BuildRequires: pkgconfig +%{?suse_build_hwcaps_libs} + +%description +Libgcrypt is a general purpose library of cryptographic building +blocks. It is originally based on code used by GnuPG. It does not +provide any implementation of OpenPGP or other protocols. Thorough +understanding of applied cryptography is required to use Libgcrypt. + +%package -n %{libsoname} +Summary: The GNU Crypto Library +License: GPL-2.0-or-later AND LGPL-2.1-or-later +Group: System/Libraries +BuildRequires: jitterentropy-devel >= 3.4.0 +Requires: libjitterentropy3 >= 3.4.0 +Provides: %{libsoname}-hmac = %{version}-%{release} +Obsoletes: %{libsoname}-hmac < %{version}-%{release} + +%description -n %{libsoname} +Libgcrypt is a general purpose crypto library based on the code used in +GnuPG (alpha version). + +%package devel +Summary: The GNU Crypto Library +License: GFDL-1.1-only AND GPL-2.0-or-later AND LGPL-2.1-or-later AND MIT +Group: Development/Libraries/C and C++ +Requires: %{libsoname} = %{version} +Requires: glibc-devel +Requires: jitterentropy-devel >= 3.4.0 +Requires: libgpg-error-devel >= 1.49 + +%description devel +Libgcrypt is a general purpose library of cryptographic building +blocks. It is originally based on code used by GnuPG. It does not +provide any implementation of OpenPGP or other protocols. Thorough +understanding of applied cryptography is required to use Libgcrypt. + +This package contains needed files to compile and link against the +library. + +%prep +%autosetup -p1 + +# Rename the internal .hmac file to include the so library version +sed -i "s/libgcrypt\.so\.hmac/\.libgcrypt\.so\.%{libsover}\.hmac/g" src/Makefile.am src/Makefile.in + +# Replace the built-in jitter rng with the standalone version [bsc#1220896] +find . -type f -name "jitterentropy*" -print -delete + +%build +export PUBKEYS="dsa elgamal rsa ecc" +export CIPHERS="arcfour blowfish cast5 des aes twofish serpent rfc2268 seed camellia idea salsa20 gost28147 chacha20 sm4 aria" +export DIGESTS="crc gostr3411-94 md4 md5 rmd160 sha1 sha256 sha512 sha3 tiger whirlpool stribog blake2 sm3" +export KDFS="s2k pkdf2 scrypt" + +autoreconf -fi +date=$(date -u '+%%Y-%%m-%%dT%%H:%%M+0000' -r %{SOURCE99}) +sed -e "s,BUILD_TIMESTAMP=.*,BUILD_TIMESTAMP=$date," -i configure +export CFLAGS="%{optflags} $(getconf LFS_CFLAGS)" +%configure \ + --with-fips-module-version="Libgcrypt version %{version}-%{release}" \ + --enable-hmac-binary-check="%{hmac_key}" \ + --enable-ciphers="$CIPHERS" \ + --enable-pubkey-ciphers="$PUBKEYS" \ + --enable-digests="$DIGESTS" \ + --enable-kdfs="$KDFS" \ + --enable-noexecstack \ + --disable-static \ +%ifarch %{sparc} + --disable-asm \ +%endif + --enable-random=getentropy \ + --enable-jent-support \ + %{nil} + +%make_build + +%check +make -k check +# run the regression tests also in FIPS mode +LIBGCRYPT_FORCE_FIPS_MODE=1 make -k check + +%install +%make_install + +# this is a hack that re-defines the __spec_install_post macro +# for a simple reason: the macro strips the binaries and thereby +# invalidates a HMAC that may have been created earlier. +# solution: create the hashes _after_ the macro runs. +%define libpath %{buildroot}%{_libdir}/libgcrypt.so.%{libsover}.?.? +%define __spec_install_post \ + %{?__debug_package:%{__debug_install_post}} \ + %{__arch_install_post} \ + %{__os_install_post} \ + cd src \ + sed -i -e 's|FILE=.*|FILE=\\\$1|' gen-note-integrity.sh \ + READELF=readelf AWK=awk ECHO_N="-n" bash gen-note-integrity.sh %{libpath} > %{libpath}.hmac \ + objcopy --update-section .note.fdo.integrity=%{libpath}.hmac %{libpath} %{libpath}.new \ + mv -f %{libpath}.new %{libpath} \ + rm -f %{libpath}.hmac \ +%{nil} + +rm %{buildroot}%{_libdir}/%{name}.la + +# Create /etc/gcrypt directory and install random.conf +mkdir -p -m 0755 %{buildroot}%{_sysconfdir}/gcrypt +install -m 644 %{SOURCE3} %{buildroot}%{_sysconfdir}/gcrypt/random.conf +install -m 644 %{SOURCE4} %{buildroot}%{_sysconfdir}/gcrypt/hwf.deny + +%post -n %{libsoname} -p /sbin/ldconfig +%postun -n %{libsoname} -p /sbin/ldconfig + +%files -n %{libsoname} +%license COPYING COPYING.LIB LICENSES +%doc AUTHORS ChangeLog NEWS README THANKS TODO +%{_libdir}/%{name}.so.* +%dir %{_sysconfdir}/gcrypt +%config(noreplace) %{_sysconfdir}/gcrypt/random.conf +%config(noreplace) %{_sysconfdir}/gcrypt/hwf.deny + +%files devel +%license COPYING COPYING.LIB LICENSES +%{_bindir}/dumpsexp +%{_bindir}/hmac256 +%{_bindir}/mpicalc +%{_bindir}/%{name}-config +%{_libdir}/%{name}.so +%{_libdir}/pkgconfig/libgcrypt.pc +%{_datadir}/aclocal/%{name}.m4 +%{_includedir}/gcrypt*.h +%{_infodir}/gcrypt.info*%{ext_info}* +%{_mandir}/man1/* + +%changelog diff --git a/random.conf b/random.conf new file mode 100644 index 0000000..378ba78 --- /dev/null +++ b/random.conf @@ -0,0 +1,9 @@ +# This file can be used to globally change parameters of +# the random generator. Supported options are: + +# Always use the non-blocking /dev/urandom or the respective +# system call instead of the blocking /dev/random. +# only-urandom + +# Disable the use of the jitter based entropy generator. +# disable-jent -- 2.51.1 From f7ff22f6aa6340473c240164bae6fa3243eeaad0825d69dcc907e34225f6f061 Mon Sep 17 00:00:00 2001 From: Pedro Monreal Gonzalez Date: Thu, 8 May 2025 17:28:12 +0000 Subject: [PATCH 5/8] - Update to 1.11.1: [jsc#PED-12227] * Bug fixes: - Fix Kyber secret-dependent branch introduced by recent versions of Clang. [rCf765778e82] - Fix build regression due to the use of AVX512 in Blake. [T7184] - Do not build i386 asm on amd64 and vice versa. [T7220] - Fix build regression on armhf with gcc-14. [T7226] - Return the proper error code on malloc failure in hex2buffer. [rCc51151f5b0] - Fix long standing bug for PRIME % 2 == 0. [rC639b0fca15] * Performance: - Add AES Vector Permute intrinsics implementation for AArch64. [rC94a63aedbb] - Add GHASH AArch64/SIMD intrinsics implementation. [rCfec871fd18] - Add RISC-V vector permute AES. [rCb24ebd6163] - Add GHASH RISC-V Zbb+Zbc implementation. [rC0f1fec12b0] - Add ChaCha20 RISC-V vector intrinsics implementation. [rC8dbee93ac2] - Add SHA3 acceleration for RISC-V Zbb extension. [rC1a660068ba] * Other: - Add CET support for i386 and amd64 assembly. [T7220] - Add PAC/BTI support for AArch64 asm. [T7220] - Apply changes to Kyber from upstream for final FIPS 203. [rCcc95c36e7f] - Introduce an internal API for a revampled FIPS service indicator. [T7340] - Several improvements for constant time operation by the introduction of Least Leak Intended (LLI) variants of internal functions. [T7519,T7490] * Rebase patches: - libgcrypt-FIPS-SLI-hash-mac.patch - libgcrypt-FIPS-SLI-pk.patch - libgcrypt-FIPS-jitter-standalone.patch * Remove patches: - libgcrypt-fips-Introduce-an-internal-API-for-FIPS-service-indicator.patch - libgcrypt-fips-Introduce-GCRYCTL_FIPS_SERVICE_INDICATOR-and-the-macro.patch - libgcrypt-fips-kdf-Implement-new-FIPS-service-indicator-for-gcry_kdf_derive.patch - libgcrypt-fips-md-Implement-new-FIPS-service-indicator-for-gcry_md_hash_.patch OBS-URL: https://build.opensuse.org/package/show/devel:libraries:c_c++/libgcrypt?expand=0&rev=190 --- .gitattributes | 23 + .gitignore | 1 + baselibs.conf | 8 + hwf.deny | 34 + libgcrypt-1.10.0-allow_FSM_same_state.patch | 15 + libgcrypt-1.10.3.tar.bz2 | 3 + libgcrypt-1.10.3.tar.bz2.sig | Bin 0 -> 238 bytes libgcrypt-1.11.0.tar.bz2 | 3 + libgcrypt-1.11.0.tar.bz2.sig | Bin 0 -> 119 bytes libgcrypt-1.11.1-public-SLI-API.patch | 37 + libgcrypt-1.11.1.tar.bz2 | 3 + libgcrypt-1.11.1.tar.bz2.sig | Bin 0 -> 119 bytes ...poly1305-Optimized-chacha20-poly1305.patch | 1993 ++++++++++++++++ ...e-SHA3-s390x-acceleration-for-CSHAKE.patch | 61 + libgcrypt-FIPS-SLI-hash-mac.patch | 172 ++ libgcrypt-FIPS-SLI-kdf-leylength.patch | 60 + libgcrypt-FIPS-SLI-pk.patch | 177 ++ libgcrypt-FIPS-jitter-errorcodes.patch | 16 + libgcrypt-FIPS-jitter-standalone.patch | 183 ++ libgcrypt-FIPS-jitter-whole-entropy.patch | 41 + libgcrypt-FIPS-rndjent_poll.patch | 114 + libgcrypt-Fix-the-previous-change.patch | 45 + ...ild-Improve-__thread-specifier-check.patch | 41 + ...T-for-non-rfc6979-ECDSA-with-fixed-k.patch | 94 + ...on-compliant-cipher-modes-in-the-SLI.patch | 236 ++ ...-Differentiate-igninvflag-in-the-SLI.patch | 40 + ...rentiate-no-blinding-flag-in-the-SLI.patch | 70 + ...ferentiate-use-of-label-K-in-the-SLI.patch | 139 ++ ...e-GCRY_CIPHER_MODE_CMAC-in-FIPS-mode.patch | 98 + ...-_gcry_cipher_is_mode_fips_compliant.patch | 64 + libgcrypt-cipher-ecc-Fix-for-supplied-K.patch | 88 + ...-cipher-fips-Fix-for-random-override.patch | 83 + ...nknown-with-RSA-signature-generation.patch | 445 ++++ ...te-use-of-random-override-in-the-SLI.patch | 107 + ...about-GCRYCTL_FIPS_SERVICE_INDICATOR.patch | 66 + libgcrypt-doc-Fix-syntax-error.patch | 31 + ...l-API-for-new-FIPS-service-indicator.patch | 140 ++ ...pt-fips-Fix-GCRY_FIPS_FLAG_REJECT_MD.patch | 42 + ...troduce-GCRYCTL_FIPS_REJECT_NON_FIPS.patch | 261 +++ ...FIPS_SERVICE_INDICATOR-and-the-macro.patch | 101 + ...ernal-API-for-FIPS-service-indicator.patch | 332 +++ ...PS_REJECT_NON_FIPS-not-by-open-flags.patch | 498 ++++ ...r-Add-GCRY_FIPS_FLAG_REJECT_PK_FLAGS.patch | 80 + ...not-to-reject-but-mark-non-compliant.patch | 300 +++ ...mputation-when-marking-non-compliant.patch | 160 ++ ...ix-memory-leak-for-gcry_pk_hash_sign.patch | 76 + ...vice-indicator-for-gcry_pk_hash_-API.patch | 360 +++ ...PS-service-indicator-for-cipher_open.patch | 122 + ...ing-or-marking-for-gcry_pk_get_curve.patch | 43 + ...-in-gcry_pk_sign-verify-in-FIPS-mode.patch | 282 +++ ...ervice-indicator-for-gcry_kdf_derive.patch | 265 +++ ...-service-indicator-for-gcry_mac_open.patch | 115 + ...-service-indicator-for-gcry_md_hash_.patch | 188 ++ ...rvice-indicator-for-gcry_md_open-API.patch | 298 +++ ...ld-care-about-FIPS-service-indicator.patch | 85 + libgcrypt-fips-tests-Add-t-digest.patch | 243 ++ ...d_open-write-read-close-for-t-digest.patch | 172 ++ libgcrypt-jitterentropy-3.4.0.patch | 618 +++++ ..._info-to-mark-reject-under-FIPS-mode.patch | 82 + ...A-1-non-FIPS-internally-for-1.12-API.patch | 154 ++ ...igest_algo_spec-in-_gcry_md_selftest.patch | 74 + libgcrypt-no-deprecated-grep-alias.patch | 35 + libgcrypt-nobetasuffix.patch | 24 + ...e-P10-assembly-with-ENABLE_FORCE_SOF.patch | 76 + libgcrypt-rol64-redefinition.patch | 16 + ...re-tests-to-tests-t-fips-service-ind.patch | 382 ++++ ...crypt-tests-Allow-tests-with-USE_RSA.patch | 44 + ...d-using-GCRY_MD_SHA256-for-KDF-tests.patch | 106 + ...ests-fips-Add-gcry_cipher_open-tests.patch | 199 ++ ...t-tests-fips-Add-gcry_mac_open-tests.patch | 206 ++ ...Move-KDF-tests-to-t-fips-service-ind.patch | 375 +++ ...tests-fips-Rename-t-fips-service-ind.patch | 60 + libgcrypt.changes | 2003 +++++++++++++++++ libgcrypt.keyring | 86 + libgcrypt.spec | 197 ++ random.conf | 9 + 76 files changed, 13500 insertions(+) create mode 100644 .gitattributes create mode 100644 .gitignore create mode 100644 baselibs.conf create mode 100644 hwf.deny create mode 100644 libgcrypt-1.10.0-allow_FSM_same_state.patch create mode 100644 libgcrypt-1.10.3.tar.bz2 create mode 100644 libgcrypt-1.10.3.tar.bz2.sig create mode 100644 libgcrypt-1.11.0.tar.bz2 create mode 100644 libgcrypt-1.11.0.tar.bz2.sig create mode 100644 libgcrypt-1.11.1-public-SLI-API.patch create mode 100644 libgcrypt-1.11.1.tar.bz2 create mode 100644 libgcrypt-1.11.1.tar.bz2.sig create mode 100644 libgcrypt-Chacha20-poly1305-Optimized-chacha20-poly1305.patch create mode 100644 libgcrypt-Disable-SHA3-s390x-acceleration-for-CSHAKE.patch create mode 100644 libgcrypt-FIPS-SLI-hash-mac.patch create mode 100644 libgcrypt-FIPS-SLI-kdf-leylength.patch create mode 100644 libgcrypt-FIPS-SLI-pk.patch create mode 100644 libgcrypt-FIPS-jitter-errorcodes.patch create mode 100644 libgcrypt-FIPS-jitter-standalone.patch create mode 100644 libgcrypt-FIPS-jitter-whole-entropy.patch create mode 100644 libgcrypt-FIPS-rndjent_poll.patch create mode 100644 libgcrypt-Fix-the-previous-change.patch create mode 100644 libgcrypt-build-Improve-__thread-specifier-check.patch create mode 100644 libgcrypt-cipher-Add-KAT-for-non-rfc6979-ECDSA-with-fixed-k.patch create mode 100644 libgcrypt-cipher-Check-and-mark-non-compliant-cipher-modes-in-the-SLI.patch create mode 100644 libgcrypt-cipher-Differentiate-igninvflag-in-the-SLI.patch create mode 100644 libgcrypt-cipher-Differentiate-no-blinding-flag-in-the-SLI.patch create mode 100644 libgcrypt-cipher-Differentiate-use-of-label-K-in-the-SLI.patch create mode 100644 libgcrypt-cipher-Don-t-differentiate-GCRY_CIPHER_MODE_CMAC-in-FIPS-mode.patch create mode 100644 libgcrypt-cipher-Rename-_gcry_cipher_is_mode_fips_compliant.patch create mode 100644 libgcrypt-cipher-ecc-Fix-for-supplied-K.patch create mode 100644 libgcrypt-cipher-fips-Fix-for-random-override.patch create mode 100644 libgcrypt-cipher-rsa-Mark-reject-SHA1-unknown-with-RSA-signature-generation.patch create mode 100644 libgcrypt-cipher-visibility-Differentiate-use-of-random-override-in-the-SLI.patch create mode 100644 libgcrypt-doc-Add-about-GCRYCTL_FIPS_SERVICE_INDICATOR.patch create mode 100644 libgcrypt-doc-Fix-syntax-error.patch create mode 100644 libgcrypt-fips-Change-the-internal-API-for-new-FIPS-service-indicator.patch create mode 100644 libgcrypt-fips-Fix-GCRY_FIPS_FLAG_REJECT_MD.patch create mode 100644 libgcrypt-fips-Introduce-GCRYCTL_FIPS_REJECT_NON_FIPS.patch create mode 100644 libgcrypt-fips-Introduce-GCRYCTL_FIPS_SERVICE_INDICATOR-and-the-macro.patch create mode 100644 libgcrypt-fips-Introduce-an-internal-API-for-FIPS-service-indicator.patch create mode 100644 libgcrypt-fips-Rejection-by-GCRYCTL_FIPS_REJECT_NON_FIPS-not-by-open-flags.patch create mode 100644 libgcrypt-fips-cipher-Add-GCRY_FIPS_FLAG_REJECT_PK_FLAGS.patch create mode 100644 libgcrypt-fips-cipher-Add-behavior-not-to-reject-but-mark-non-compliant.patch create mode 100644 libgcrypt-fips-cipher-Do-the-computation-when-marking-non-compliant.patch create mode 100644 libgcrypt-fips-cipher-Fix-memory-leak-for-gcry_pk_hash_sign.patch create mode 100644 libgcrypt-fips-cipher-Implement-FIPS-service-indicator-for-gcry_pk_hash_-API.patch create mode 100644 libgcrypt-fips-cipher-Implement-new-FIPS-service-indicator-for-cipher_open.patch create mode 100644 libgcrypt-fips-ecc-Add-rejecting-or-marking-for-gcry_pk_get_curve.patch create mode 100644 libgcrypt-fips-ecc-Check-DATA-in-gcry_pk_sign-verify-in-FIPS-mode.patch create mode 100644 libgcrypt-fips-kdf-Implement-new-FIPS-service-indicator-for-gcry_kdf_derive.patch create mode 100644 libgcrypt-fips-mac-Implement-new-FIPS-service-indicator-for-gcry_mac_open.patch create mode 100644 libgcrypt-fips-md-Implement-new-FIPS-service-indicator-for-gcry_md_hash_.patch create mode 100644 libgcrypt-fips-md-Implement-new-FIPS-service-indicator-for-gcry_md_open-API.patch create mode 100644 libgcrypt-fips-md-gcry_md_copy-should-care-about-FIPS-service-indicator.patch create mode 100644 libgcrypt-fips-tests-Add-t-digest.patch create mode 100644 libgcrypt-fips-tests-Add-tests-for-md_open-write-read-close-for-t-digest.patch create mode 100644 libgcrypt-jitterentropy-3.4.0.patch create mode 100644 libgcrypt-md-Fix-gcry_md_algo_info-to-mark-reject-under-FIPS-mode.patch create mode 100644 libgcrypt-md-Make-SHA-1-non-FIPS-internally-for-1.12-API.patch create mode 100644 libgcrypt-md-Use-check_digest_algo_spec-in-_gcry_md_selftest.patch create mode 100644 libgcrypt-no-deprecated-grep-alias.patch create mode 100644 libgcrypt-nobetasuffix.patch create mode 100644 libgcrypt-ppc-enable-P10-assembly-with-ENABLE_FORCE_SOF.patch create mode 100644 libgcrypt-rol64-redefinition.patch create mode 100644 libgcrypt-tests-Add-more-tests-to-tests-t-fips-service-ind.patch create mode 100644 libgcrypt-tests-Allow-tests-with-USE_RSA.patch create mode 100644 libgcrypt-tests-Update-t-fips-service-ind-using-GCRY_MD_SHA256-for-KDF-tests.patch create mode 100644 libgcrypt-tests-fips-Add-gcry_cipher_open-tests.patch create mode 100644 libgcrypt-tests-fips-Add-gcry_mac_open-tests.patch create mode 100644 libgcrypt-tests-fips-Move-KDF-tests-to-t-fips-service-ind.patch create mode 100644 libgcrypt-tests-fips-Rename-t-fips-service-ind.patch create mode 100644 libgcrypt.changes create mode 100644 libgcrypt.keyring create mode 100644 libgcrypt.spec create mode 100644 random.conf diff --git a/.gitattributes b/.gitattributes new file mode 100644 index 0000000..9b03811 --- /dev/null +++ b/.gitattributes @@ -0,0 +1,23 @@ +## Default LFS +*.7z filter=lfs diff=lfs merge=lfs -text +*.bsp filter=lfs diff=lfs merge=lfs -text +*.bz2 filter=lfs diff=lfs merge=lfs -text +*.gem filter=lfs diff=lfs merge=lfs -text +*.gz filter=lfs diff=lfs merge=lfs -text +*.jar filter=lfs diff=lfs merge=lfs -text +*.lz filter=lfs diff=lfs merge=lfs -text +*.lzma filter=lfs diff=lfs merge=lfs -text +*.obscpio filter=lfs diff=lfs merge=lfs -text +*.oxt filter=lfs diff=lfs merge=lfs -text +*.pdf filter=lfs diff=lfs merge=lfs -text +*.png filter=lfs diff=lfs merge=lfs -text +*.rpm filter=lfs diff=lfs merge=lfs -text +*.tbz filter=lfs diff=lfs merge=lfs -text +*.tbz2 filter=lfs diff=lfs merge=lfs -text +*.tgz filter=lfs diff=lfs merge=lfs -text +*.ttf filter=lfs diff=lfs merge=lfs -text +*.txz filter=lfs diff=lfs merge=lfs -text +*.whl filter=lfs diff=lfs merge=lfs -text +*.xz filter=lfs diff=lfs merge=lfs -text +*.zip filter=lfs diff=lfs merge=lfs -text +*.zst filter=lfs diff=lfs merge=lfs -text diff --git a/.gitignore b/.gitignore new file mode 100644 index 0000000..57affb6 --- /dev/null +++ b/.gitignore @@ -0,0 +1 @@ +.osc diff --git a/baselibs.conf b/baselibs.conf new file mode 100644 index 0000000..a018a0a --- /dev/null +++ b/baselibs.conf @@ -0,0 +1,8 @@ +libgcrypt20 + provides "libgcrypt- = " + obsoletes "libgcrypt- <= " + provides "libgcrypt20-hmac- = -%release" + obsoletes "libgcrypt20-hmac- < -%release" +libgcrypt-devel + requires -libgcrypt- + requires "libgcrypt20- = " diff --git a/hwf.deny b/hwf.deny new file mode 100644 index 0000000..2236468 --- /dev/null +++ b/hwf.deny @@ -0,0 +1,34 @@ +# This file can be used to globally disable the use of hardware +# based optimizations. Supported options are: +# padlock-rng +# padlock-aes +# padlock-sha +# padlock-mmul +# intel-cpu +# intel-fast-shld +# intel-bmi2 +# intel-ssse3 +# intel-sse4.1 +# intel-pclmul +# intel-aesni +# intel-rdrand +# intel-avx +# intel-avx2 +# intel-fast-vpgather +# intel-rdtsc +# intel-shaext +# intel-vaes-vpclmul +# arm-neon +# arm-aes +# arm-sha1 +# arm-sha2 +# arm-pmull +# ppc-vcrypto +# ppc-arch_3_00 +# ppc-arch_2_07 +# ppc-arch_3_10 +# s390x-msa +# s390x-msa-4 +# s390x-msa-8 +# s390x-msa-9 +# s390x-vx diff --git a/libgcrypt-1.10.0-allow_FSM_same_state.patch b/libgcrypt-1.10.0-allow_FSM_same_state.patch new file mode 100644 index 0000000..843cfea --- /dev/null +++ b/libgcrypt-1.10.0-allow_FSM_same_state.patch @@ -0,0 +1,15 @@ +Index: libgcrypt-1.10.0/src/fips.c +=================================================================== +--- libgcrypt-1.10.0.orig/src/fips.c ++++ libgcrypt-1.10.0/src/fips.c +@@ -890,6 +890,10 @@ fips_new_state (enum module_states new_s + + } + ++ /* Allow a transition to the current state */ ++ if (current_state == new_state) ++ ok = 1; ++ + if (ok) + { + current_state = new_state; diff --git a/libgcrypt-1.10.3.tar.bz2 b/libgcrypt-1.10.3.tar.bz2 new file mode 100644 index 0000000..653803f --- /dev/null +++ b/libgcrypt-1.10.3.tar.bz2 @@ -0,0 +1,3 @@ +version https://git-lfs.github.com/spec/v1 +oid sha256:8b0870897ac5ac67ded568dcfadf45969cfa8a6beb0fd60af2a9eadc2a3272aa +size 3783827 diff --git a/libgcrypt-1.10.3.tar.bz2.sig b/libgcrypt-1.10.3.tar.bz2.sig new file mode 100644 index 0000000000000000000000000000000000000000000000000000000000000000..4172518bc29eafb0304aa2c7def555b970a6accea442a7542087b98c44485773 GIT binary patch literal 238 zcmeAuWnmEGV2~A4WXWBXm$E!p!y#PSlPRcU`VKV*t6Qv0sliEW8MrtFU?N}p82-vF z=ITAZ*qv<_(;dOxrp<8yN$DSFdR>!gz3<7nXwGD1Muyiq%7Ht6>~>#&|Ibh5V-ok6 zm#e%* literal 0 HcmV?d00001 diff --git a/libgcrypt-1.11.0.tar.bz2 b/libgcrypt-1.11.0.tar.bz2 new file mode 100644 index 0000000..28d1068 --- /dev/null +++ b/libgcrypt-1.11.0.tar.bz2 @@ -0,0 +1,3 @@ +version https://git-lfs.github.com/spec/v1 +oid sha256:09120c9867ce7f2081d6aaa1775386b98c2f2f246135761aae47d81f58685b9c +size 4180345 diff --git a/libgcrypt-1.11.0.tar.bz2.sig b/libgcrypt-1.11.0.tar.bz2.sig new file mode 100644 index 0000000000000000000000000000000000000000000000000000000000000000..2debe948a9ffbbc9c835efae5cce0c65517df124ea67ba4cc04d1dffdd7b3160 GIT binary patch literal 119 zcmeAuWnmEGV2~A4WXWBXm$E!p!y#PSlPRcU`VKV*t6Qv0X+=xZ7`QkEU?T178UE=O z)|M}6Y-XM7H2JWvsFP0?XX&fr%U>#e4G(K{b;T<%GJNLLSKO|_Z@vBphsk!en!WkH T(k44uvO>;;f4NZp`vWfkiCryG literal 0 HcmV?d00001 diff --git a/libgcrypt-1.11.1-public-SLI-API.patch b/libgcrypt-1.11.1-public-SLI-API.patch new file mode 100644 index 0000000..42a9276 --- /dev/null +++ b/libgcrypt-1.11.1-public-SLI-API.patch @@ -0,0 +1,37 @@ +Index: libgcrypt-1.11.1/src/gcrypt.h.in +=================================================================== +--- libgcrypt-1.11.1.orig/src/gcrypt.h.in ++++ libgcrypt-1.11.1/src/gcrypt.h.in +@@ -335,12 +335,9 @@ enum gcry_ctl_cmds + GCRYCTL_FIPS_SERVICE_INDICATOR_MAC = 85, + GCRYCTL_FIPS_SERVICE_INDICATOR_MD = 86, + GCRYCTL_FIPS_SERVICE_INDICATOR_PK_FLAGS = 87, +- GCRYCTL_MD_CUSTOMIZE = 88 +-#ifdef _GCRYPT_IN_LIBGCRYPT /* This is not yet part of the public API. */ +- , ++ GCRYCTL_MD_CUSTOMIZE = 88, + GCRYCTL_FIPS_SERVICE_INDICATOR = 89, + GCRYCTL_FIPS_REJECT_NON_FIPS = 90 +-#endif /*_GCRYPT_IN_LIBGCRYPT*/ + }; + + /* Perform various operations defined by CMD. */ +@@ -1977,8 +1974,6 @@ void gcry_log_debugsxp (const char *text + char *gcry_get_config (int mode, const char *what); + + /* Convinience macro to access the FIPS service indicator. */ +-#ifdef _GCRYPT_IN_LIBGCRYPT /* This is not yet part of the public API. */ +- + #define gcry_get_fips_service_indicator() \ + gcry_control (GCRYCTL_FIPS_SERVICE_INDICATOR) + +@@ -2012,9 +2007,6 @@ char *gcry_get_config (int mode, const c + #define GCRY_FIPS_FLAG_REJECT_DEFAULT \ + GCRY_FIPS_FLAG_REJECT_COMPAT110 + +-#endif /*_GCRYPT_IN_LIBGCRYPT*/ +- +- + /* Log levels used by the internal logging facility. */ + enum gcry_log_levels + { diff --git a/libgcrypt-1.11.1.tar.bz2 b/libgcrypt-1.11.1.tar.bz2 new file mode 100644 index 0000000..aa03790 --- /dev/null +++ b/libgcrypt-1.11.1.tar.bz2 @@ -0,0 +1,3 @@ +version https://git-lfs.github.com/spec/v1 +oid sha256:24e91c9123a46c54e8371f3a3a2502f1198f2893fbfbf59af95bc1c21499b00e +size 4233557 diff --git a/libgcrypt-1.11.1.tar.bz2.sig b/libgcrypt-1.11.1.tar.bz2.sig new file mode 100644 index 0000000000000000000000000000000000000000000000000000000000000000..62de6154dfc87f2d93e84b8fd2f4a26b2e9f2dfc6cd988e73e4a8305d7d1021d GIT binary patch literal 119 zcmeAuWnmEGVvrS6WXWBXm$E!p!y#PSlPRcU`VKV*t6Qv08Pbh^7`QkEU?N-QFfvR& zliXh{lxlF3mDxiqReAqxzNuWrYmP2DYpc_Eedm)rhJS|Foa@@920I1Y1WdHyG literal 0 HcmV?d00001 diff --git a/libgcrypt-Chacha20-poly1305-Optimized-chacha20-poly1305.patch b/libgcrypt-Chacha20-poly1305-Optimized-chacha20-poly1305.patch new file mode 100644 index 0000000..5877fee --- /dev/null +++ b/libgcrypt-Chacha20-poly1305-Optimized-chacha20-poly1305.patch @@ -0,0 +1,1993 @@ +commit 88fe7ac33eb4cb4dff76a5cc7fca50da5fb0ee3a +Author: Danny Tsen +Date: Sun Jun 12 21:30:19 2022 +0300 + + Chacha20 poly1305 Optimized chacha20 poly1305 for P10 operation + + * configure.ac: Added chacha20 and poly1305 assembly implementations. + * cipher/chacha20-p10le-8x.s: (New) - support 8 blocks (512 bytes) + unrolling. + * cipher/poly1305-p10le.s: (New) - support 4 blocks (128 bytes) + unrolling. + * cipher/Makefile.am: Added new chacha20 and poly1305 files. + * cipher/chacha20.c: Added PPC p10 le support for 8x chacha20. + * cipher/poly1305.c: Added PPC p10 le support for 4x poly1305. + * cipher/poly1305-internal.h: Added PPC p10 le support for poly1305. + --- + + GnuPG-bug-id: 6006 + Signed-off-by: Danny Tsen + [jk: cosmetic changes to C code] + [jk: fix building on ppc64be] + Signed-off-by: Jussi Kivilinna + +Index: libgcrypt-1.10.2/cipher/Makefile.am +=================================================================== +--- libgcrypt-1.10.2.orig/cipher/Makefile.am ++++ libgcrypt-1.10.2/cipher/Makefile.am +@@ -83,6 +83,7 @@ EXTRA_libcipher_la_SOURCES = \ + chacha20.c chacha20-amd64-ssse3.S chacha20-amd64-avx2.S \ + chacha20-armv7-neon.S chacha20-aarch64.S \ + chacha20-ppc.c chacha20-s390x.S \ ++ chacha20-p10le-8x.s \ + cipher-gcm-ppc.c cipher-gcm-intel-pclmul.c cipher-gcm-armv7-neon.S \ + cipher-gcm-armv8-aarch32-ce.S cipher-gcm-armv8-aarch64-ce.S \ + crc.c crc-intel-pclmul.c crc-armv8-ce.c \ +@@ -99,6 +100,7 @@ EXTRA_libcipher_la_SOURCES = \ + md4.c \ + md5.c \ + poly1305-s390x.S \ ++ poly1305-p10le.s \ + rijndael.c rijndael-internal.h rijndael-tables.h \ + rijndael-aesni.c rijndael-padlock.c \ + rijndael-amd64.S rijndael-arm.S \ +Index: libgcrypt-1.10.2/cipher/chacha20-p10le-8x.s +=================================================================== +--- /dev/null ++++ libgcrypt-1.10.2/cipher/chacha20-p10le-8x.s +@@ -0,0 +1,864 @@ ++# Copyright 2021- IBM Inc. All rights reserved ++# ++# This file is part of Libgcrypt. ++# ++# Libgcrypt is free software; you can redistribute it and/or modify ++# it under the terms of the GNU Lesser General Public License as ++# published by the Free Software Foundation; either version 2.1 of ++# the License, or (at your option) any later version. ++# ++# Libgcrypt 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 Lesser General Public License for more details. ++# ++# You should have received a copy of the GNU Lesser General Public ++# License along with this program; if not, see . ++# ++#=================================================================================== ++# Written by Danny Tsen ++# ++# This function handles multiple 64-byte block data length ++# and the length should be more than 512 bytes. ++# ++# unsigned int _gcry_chacha20_p10le_8x(u32 *state, byte *dst, const byte *src, size_t len); ++# ++# r1 - top of the stack ++# r3 to r10 input parameters ++# r3 - out ++# r4 - inp ++# r5 - len ++# r6 - key[8] ++# r7 - counter[4] ++# ++# do rounds, 8 quarter rounds ++# 1. a += b; d ^= a; d <<<= 16; ++# 2. c += d; b ^= c; b <<<= 12; ++# 3. a += b; d ^= a; d <<<= 8; ++# 4. c += d; b ^= c; b <<<= 7 ++# ++# row1 = (row1 + row2), row4 = row1 xor row4, row4 rotate each word by 16 ++# row3 = (row3 + row4), row2 = row3 xor row2, row2 rotate each word by 12 ++# row1 = (row1 + row2), row4 = row1 xor row4, row4 rotate each word by 8 ++# row3 = (row3 + row4), row2 = row3 xor row2, row2 rotate each word by 7 ++# ++# 4 blocks (a b c d) ++# ++# a0 b0 c0 d0 ++# a1 b1 c1 d1 ++# ... ++# a4 b4 c4 d4 ++# ... ++# a8 b8 c8 d8 ++# ... ++# a12 b12 c12 d12 ++# a13 ... ++# a14 ... ++# a15 b15 c15 d15 ++# ++# Column round (v0, v4, v8, v12, v1, v5, v9, v13, v2, v6, v10, v14, v3, v7, v11, v15) ++# Diagnal round (v0, v5, v10, v15, v1, v6, v11, v12, v2, v7, v8, v13, v3, v4, v9, v14) ++# ++.text ++ ++.macro QT_loop_8x ++ # QR(v0, v4, v8, v12, v1, v5, v9, v13, v2, v6, v10, v14, v3, v7, v11, v15) ++ xxlor 0, 32+25, 32+25 ++ xxlor 32+25, 20, 20 ++ vadduwm 0, 0, 4 ++ vadduwm 1, 1, 5 ++ vadduwm 2, 2, 6 ++ vadduwm 3, 3, 7 ++ vadduwm 16, 16, 20 ++ vadduwm 17, 17, 21 ++ vadduwm 18, 18, 22 ++ vadduwm 19, 19, 23 ++ ++ vpermxor 12, 12, 0, 25 ++ vpermxor 13, 13, 1, 25 ++ vpermxor 14, 14, 2, 25 ++ vpermxor 15, 15, 3, 25 ++ vpermxor 28, 28, 16, 25 ++ vpermxor 29, 29, 17, 25 ++ vpermxor 30, 30, 18, 25 ++ vpermxor 31, 31, 19, 25 ++ xxlor 32+25, 0, 0 ++ vadduwm 8, 8, 12 ++ vadduwm 9, 9, 13 ++ vadduwm 10, 10, 14 ++ vadduwm 11, 11, 15 ++ vadduwm 24, 24, 28 ++ vadduwm 25, 25, 29 ++ vadduwm 26, 26, 30 ++ vadduwm 27, 27, 31 ++ vxor 4, 4, 8 ++ vxor 5, 5, 9 ++ vxor 6, 6, 10 ++ vxor 7, 7, 11 ++ vxor 20, 20, 24 ++ vxor 21, 21, 25 ++ vxor 22, 22, 26 ++ vxor 23, 23, 27 ++ ++ xxlor 0, 32+25, 32+25 ++ xxlor 32+25, 21, 21 ++ vrlw 4, 4, 25 # ++ vrlw 5, 5, 25 ++ vrlw 6, 6, 25 ++ vrlw 7, 7, 25 ++ vrlw 20, 20, 25 # ++ vrlw 21, 21, 25 ++ vrlw 22, 22, 25 ++ vrlw 23, 23, 25 ++ xxlor 32+25, 0, 0 ++ vadduwm 0, 0, 4 ++ vadduwm 1, 1, 5 ++ vadduwm 2, 2, 6 ++ vadduwm 3, 3, 7 ++ vadduwm 16, 16, 20 ++ vadduwm 17, 17, 21 ++ vadduwm 18, 18, 22 ++ vadduwm 19, 19, 23 ++ ++ xxlor 0, 32+25, 32+25 ++ xxlor 32+25, 22, 22 ++ vpermxor 12, 12, 0, 25 ++ vpermxor 13, 13, 1, 25 ++ vpermxor 14, 14, 2, 25 ++ vpermxor 15, 15, 3, 25 ++ vpermxor 28, 28, 16, 25 ++ vpermxor 29, 29, 17, 25 ++ vpermxor 30, 30, 18, 25 ++ vpermxor 31, 31, 19, 25 ++ xxlor 32+25, 0, 0 ++ vadduwm 8, 8, 12 ++ vadduwm 9, 9, 13 ++ vadduwm 10, 10, 14 ++ vadduwm 11, 11, 15 ++ vadduwm 24, 24, 28 ++ vadduwm 25, 25, 29 ++ vadduwm 26, 26, 30 ++ vadduwm 27, 27, 31 ++ xxlor 0, 32+28, 32+28 ++ xxlor 32+28, 23, 23 ++ vxor 4, 4, 8 ++ vxor 5, 5, 9 ++ vxor 6, 6, 10 ++ vxor 7, 7, 11 ++ vxor 20, 20, 24 ++ vxor 21, 21, 25 ++ vxor 22, 22, 26 ++ vxor 23, 23, 27 ++ vrlw 4, 4, 28 # ++ vrlw 5, 5, 28 ++ vrlw 6, 6, 28 ++ vrlw 7, 7, 28 ++ vrlw 20, 20, 28 # ++ vrlw 21, 21, 28 ++ vrlw 22, 22, 28 ++ vrlw 23, 23, 28 ++ xxlor 32+28, 0, 0 ++ ++ # QR(v0, v5, v10, v15, v1, v6, v11, v12, v2, v7, v8, v13, v3, v4, v9, v14) ++ xxlor 0, 32+25, 32+25 ++ xxlor 32+25, 20, 20 ++ vadduwm 0, 0, 5 ++ vadduwm 1, 1, 6 ++ vadduwm 2, 2, 7 ++ vadduwm 3, 3, 4 ++ vadduwm 16, 16, 21 ++ vadduwm 17, 17, 22 ++ vadduwm 18, 18, 23 ++ vadduwm 19, 19, 20 ++ ++ vpermxor 15, 15, 0, 25 ++ vpermxor 12, 12, 1, 25 ++ vpermxor 13, 13, 2, 25 ++ vpermxor 14, 14, 3, 25 ++ vpermxor 31, 31, 16, 25 ++ vpermxor 28, 28, 17, 25 ++ vpermxor 29, 29, 18, 25 ++ vpermxor 30, 30, 19, 25 ++ ++ xxlor 32+25, 0, 0 ++ vadduwm 10, 10, 15 ++ vadduwm 11, 11, 12 ++ vadduwm 8, 8, 13 ++ vadduwm 9, 9, 14 ++ vadduwm 26, 26, 31 ++ vadduwm 27, 27, 28 ++ vadduwm 24, 24, 29 ++ vadduwm 25, 25, 30 ++ vxor 5, 5, 10 ++ vxor 6, 6, 11 ++ vxor 7, 7, 8 ++ vxor 4, 4, 9 ++ vxor 21, 21, 26 ++ vxor 22, 22, 27 ++ vxor 23, 23, 24 ++ vxor 20, 20, 25 ++ ++ xxlor 0, 32+25, 32+25 ++ xxlor 32+25, 21, 21 ++ vrlw 5, 5, 25 ++ vrlw 6, 6, 25 ++ vrlw 7, 7, 25 ++ vrlw 4, 4, 25 ++ vrlw 21, 21, 25 ++ vrlw 22, 22, 25 ++ vrlw 23, 23, 25 ++ vrlw 20, 20, 25 ++ xxlor 32+25, 0, 0 ++ ++ vadduwm 0, 0, 5 ++ vadduwm 1, 1, 6 ++ vadduwm 2, 2, 7 ++ vadduwm 3, 3, 4 ++ vadduwm 16, 16, 21 ++ vadduwm 17, 17, 22 ++ vadduwm 18, 18, 23 ++ vadduwm 19, 19, 20 ++ ++ xxlor 0, 32+25, 32+25 ++ xxlor 32+25, 22, 22 ++ vpermxor 15, 15, 0, 25 ++ vpermxor 12, 12, 1, 25 ++ vpermxor 13, 13, 2, 25 ++ vpermxor 14, 14, 3, 25 ++ vpermxor 31, 31, 16, 25 ++ vpermxor 28, 28, 17, 25 ++ vpermxor 29, 29, 18, 25 ++ vpermxor 30, 30, 19, 25 ++ xxlor 32+25, 0, 0 ++ ++ vadduwm 10, 10, 15 ++ vadduwm 11, 11, 12 ++ vadduwm 8, 8, 13 ++ vadduwm 9, 9, 14 ++ vadduwm 26, 26, 31 ++ vadduwm 27, 27, 28 ++ vadduwm 24, 24, 29 ++ vadduwm 25, 25, 30 ++ ++ xxlor 0, 32+28, 32+28 ++ xxlor 32+28, 23, 23 ++ vxor 5, 5, 10 ++ vxor 6, 6, 11 ++ vxor 7, 7, 8 ++ vxor 4, 4, 9 ++ vxor 21, 21, 26 ++ vxor 22, 22, 27 ++ vxor 23, 23, 24 ++ vxor 20, 20, 25 ++ vrlw 5, 5, 28 ++ vrlw 6, 6, 28 ++ vrlw 7, 7, 28 ++ vrlw 4, 4, 28 ++ vrlw 21, 21, 28 ++ vrlw 22, 22, 28 ++ vrlw 23, 23, 28 ++ vrlw 20, 20, 28 ++ xxlor 32+28, 0, 0 ++.endm ++ ++.macro QT_loop_4x ++ # QR(v0, v4, v8, v12, v1, v5, v9, v13, v2, v6, v10, v14, v3, v7, v11, v15) ++ vadduwm 0, 0, 4 ++ vadduwm 1, 1, 5 ++ vadduwm 2, 2, 6 ++ vadduwm 3, 3, 7 ++ vpermxor 12, 12, 0, 20 ++ vpermxor 13, 13, 1, 20 ++ vpermxor 14, 14, 2, 20 ++ vpermxor 15, 15, 3, 20 ++ vadduwm 8, 8, 12 ++ vadduwm 9, 9, 13 ++ vadduwm 10, 10, 14 ++ vadduwm 11, 11, 15 ++ vxor 4, 4, 8 ++ vxor 5, 5, 9 ++ vxor 6, 6, 10 ++ vxor 7, 7, 11 ++ vrlw 4, 4, 21 ++ vrlw 5, 5, 21 ++ vrlw 6, 6, 21 ++ vrlw 7, 7, 21 ++ vadduwm 0, 0, 4 ++ vadduwm 1, 1, 5 ++ vadduwm 2, 2, 6 ++ vadduwm 3, 3, 7 ++ vpermxor 12, 12, 0, 22 ++ vpermxor 13, 13, 1, 22 ++ vpermxor 14, 14, 2, 22 ++ vpermxor 15, 15, 3, 22 ++ vadduwm 8, 8, 12 ++ vadduwm 9, 9, 13 ++ vadduwm 10, 10, 14 ++ vadduwm 11, 11, 15 ++ vxor 4, 4, 8 ++ vxor 5, 5, 9 ++ vxor 6, 6, 10 ++ vxor 7, 7, 11 ++ vrlw 4, 4, 23 ++ vrlw 5, 5, 23 ++ vrlw 6, 6, 23 ++ vrlw 7, 7, 23 ++ ++ # QR(v0, v5, v10, v15, v1, v6, v11, v12, v2, v7, v8, v13, v3, v4, v9, v14) ++ vadduwm 0, 0, 5 ++ vadduwm 1, 1, 6 ++ vadduwm 2, 2, 7 ++ vadduwm 3, 3, 4 ++ vpermxor 15, 15, 0, 20 ++ vpermxor 12, 12, 1, 20 ++ vpermxor 13, 13, 2, 20 ++ vpermxor 14, 14, 3, 20 ++ vadduwm 10, 10, 15 ++ vadduwm 11, 11, 12 ++ vadduwm 8, 8, 13 ++ vadduwm 9, 9, 14 ++ vxor 5, 5, 10 ++ vxor 6, 6, 11 ++ vxor 7, 7, 8 ++ vxor 4, 4, 9 ++ vrlw 5, 5, 21 ++ vrlw 6, 6, 21 ++ vrlw 7, 7, 21 ++ vrlw 4, 4, 21 ++ vadduwm 0, 0, 5 ++ vadduwm 1, 1, 6 ++ vadduwm 2, 2, 7 ++ vadduwm 3, 3, 4 ++ vpermxor 15, 15, 0, 22 ++ vpermxor 12, 12, 1, 22 ++ vpermxor 13, 13, 2, 22 ++ vpermxor 14, 14, 3, 22 ++ vadduwm 10, 10, 15 ++ vadduwm 11, 11, 12 ++ vadduwm 8, 8, 13 ++ vadduwm 9, 9, 14 ++ vxor 5, 5, 10 ++ vxor 6, 6, 11 ++ vxor 7, 7, 8 ++ vxor 4, 4, 9 ++ vrlw 5, 5, 23 ++ vrlw 6, 6, 23 ++ vrlw 7, 7, 23 ++ vrlw 4, 4, 23 ++.endm ++ ++# Transpose ++.macro TP_4x a0 a1 a2 a3 ++ xxmrghw 10, 32+\a0, 32+\a1 # a0, a1, b0, b1 ++ xxmrghw 11, 32+\a2, 32+\a3 # a2, a3, b2, b3 ++ xxmrglw 12, 32+\a0, 32+\a1 # c0, c1, d0, d1 ++ xxmrglw 13, 32+\a2, 32+\a3 # c2, c3, d2, d3 ++ xxpermdi 32+\a0, 10, 11, 0 # a0, a1, a2, a3 ++ xxpermdi 32+\a1, 10, 11, 3 # b0, b1, b2, b3 ++ xxpermdi 32+\a2, 12, 13, 0 # c0, c1, c2, c3 ++ xxpermdi 32+\a3, 12, 13, 3 # d0, d1, d2, d3 ++.endm ++ ++# key stream = working state + state ++.macro Add_state S ++ vadduwm \S+0, \S+0, 16-\S ++ vadduwm \S+4, \S+4, 17-\S ++ vadduwm \S+8, \S+8, 18-\S ++ vadduwm \S+12, \S+12, 19-\S ++ ++ vadduwm \S+1, \S+1, 16-\S ++ vadduwm \S+5, \S+5, 17-\S ++ vadduwm \S+9, \S+9, 18-\S ++ vadduwm \S+13, \S+13, 19-\S ++ ++ vadduwm \S+2, \S+2, 16-\S ++ vadduwm \S+6, \S+6, 17-\S ++ vadduwm \S+10, \S+10, 18-\S ++ vadduwm \S+14, \S+14, 19-\S ++ ++ vadduwm \S+3, \S+3, 16-\S ++ vadduwm \S+7, \S+7, 17-\S ++ vadduwm \S+11, \S+11, 18-\S ++ vadduwm \S+15, \S+15, 19-\S ++.endm ++ ++# ++# write 256 bytes ++# ++.macro Write_256 S ++ add 9, 14, 5 ++ add 16, 14, 4 ++ lxvw4x 0, 0, 9 ++ lxvw4x 1, 17, 9 ++ lxvw4x 2, 18, 9 ++ lxvw4x 3, 19, 9 ++ lxvw4x 4, 20, 9 ++ lxvw4x 5, 21, 9 ++ lxvw4x 6, 22, 9 ++ lxvw4x 7, 23, 9 ++ lxvw4x 8, 24, 9 ++ lxvw4x 9, 25, 9 ++ lxvw4x 10, 26, 9 ++ lxvw4x 11, 27, 9 ++ lxvw4x 12, 28, 9 ++ lxvw4x 13, 29, 9 ++ lxvw4x 14, 30, 9 ++ lxvw4x 15, 31, 9 ++ ++ xxlxor \S+32, \S+32, 0 ++ xxlxor \S+36, \S+36, 1 ++ xxlxor \S+40, \S+40, 2 ++ xxlxor \S+44, \S+44, 3 ++ xxlxor \S+33, \S+33, 4 ++ xxlxor \S+37, \S+37, 5 ++ xxlxor \S+41, \S+41, 6 ++ xxlxor \S+45, \S+45, 7 ++ xxlxor \S+34, \S+34, 8 ++ xxlxor \S+38, \S+38, 9 ++ xxlxor \S+42, \S+42, 10 ++ xxlxor \S+46, \S+46, 11 ++ xxlxor \S+35, \S+35, 12 ++ xxlxor \S+39, \S+39, 13 ++ xxlxor \S+43, \S+43, 14 ++ xxlxor \S+47, \S+47, 15 ++ ++ stxvw4x \S+32, 0, 16 ++ stxvw4x \S+36, 17, 16 ++ stxvw4x \S+40, 18, 16 ++ stxvw4x \S+44, 19, 16 ++ ++ stxvw4x \S+33, 20, 16 ++ stxvw4x \S+37, 21, 16 ++ stxvw4x \S+41, 22, 16 ++ stxvw4x \S+45, 23, 16 ++ ++ stxvw4x \S+34, 24, 16 ++ stxvw4x \S+38, 25, 16 ++ stxvw4x \S+42, 26, 16 ++ stxvw4x \S+46, 27, 16 ++ ++ stxvw4x \S+35, 28, 16 ++ stxvw4x \S+39, 29, 16 ++ stxvw4x \S+43, 30, 16 ++ stxvw4x \S+47, 31, 16 ++ ++.endm ++ ++# ++# unsigned int _gcry_chacha20_p10le_8x(u32 *state, byte *dst, const byte *src, size_t len); ++# ++.global _gcry_chacha20_p10le_8x ++.align 5 ++_gcry_chacha20_p10le_8x: ++ cmpdi 6, 512 ++ blt Out_no_chacha ++ ++ stdu 1,-1024(1) ++ mflr 0 ++ ++ std 14,112(1) ++ std 15,120(1) ++ std 16,128(1) ++ std 17,136(1) ++ std 18,144(1) ++ std 19,152(1) ++ std 20,160(1) ++ std 21,168(1) ++ std 22,176(1) ++ std 23,184(1) ++ std 24,192(1) ++ std 25,200(1) ++ std 26,208(1) ++ std 27,216(1) ++ std 28,224(1) ++ std 29,232(1) ++ std 30,240(1) ++ std 31,248(1) ++ std 0, 1040(1) ++ ++ li 17, 16 ++ li 18, 32 ++ li 19, 48 ++ li 20, 64 ++ li 21, 80 ++ li 22, 96 ++ li 23, 112 ++ li 24, 128 ++ li 25, 144 ++ li 26, 160 ++ li 27, 176 ++ li 28, 192 ++ li 29, 208 ++ li 30, 224 ++ li 31, 240 ++ addi 9, 1, 256 ++ stvx 20, 0, 9 ++ stvx 21, 17, 9 ++ stvx 22, 18, 9 ++ stvx 23, 19, 9 ++ stvx 24, 20, 9 ++ stvx 25, 21, 9 ++ stvx 26, 22, 9 ++ stvx 27, 23, 9 ++ stvx 28, 24, 9 ++ stvx 29, 25, 9 ++ stvx 30, 26, 9 ++ stvx 31, 27, 9 ++ ++ add 9, 9, 27 ++ addi 14, 17, 16 ++ stxvx 14, 14, 9 ++ addi 14, 14, 16 ++ stxvx 15, 14, 9 ++ addi 14, 14, 16 ++ stxvx 16, 14, 9 ++ addi 14, 14, 16 ++ stxvx 17, 14, 9 ++ addi 14, 14, 16 ++ stxvx 18, 14, 9 ++ addi 14, 14, 16 ++ stxvx 19, 14, 9 ++ addi 14, 14, 16 ++ stxvx 20, 14, 9 ++ addi 14, 14, 16 ++ stxvx 21, 14, 9 ++ addi 14, 14, 16 ++ stxvx 22, 14, 9 ++ addi 14, 14, 16 ++ stxvx 23, 14, 9 ++ addi 14, 14, 16 ++ stxvx 24, 14, 9 ++ addi 14, 14, 16 ++ stxvx 25, 14, 9 ++ addi 14, 14, 16 ++ stxvx 26, 14, 9 ++ addi 14, 14, 16 ++ stxvx 27, 14, 9 ++ addi 14, 14, 16 ++ stxvx 28, 14, 9 ++ addi 14, 14, 16 ++ stxvx 29, 14, 9 ++ addi 14, 14, 16 ++ stxvx 30, 14, 9 ++ addi 14, 14, 16 ++ stxvx 31, 14, 9 ++ ++ mr 15, 6 # len ++ li 14, 0 # offset to inp and outp ++ ++ ld 10, sigma@got(2) ++ ++ lxvw4x 48, 0, 3 # vr16, constants ++ lxvw4x 49, 17, 3 # vr17, key 1 ++ lxvw4x 50, 18, 3 # vr18, key 2 ++ lxvw4x 51, 19, 3 # vr19, counter, nonce ++ ++ lxvw4x 62, 19, 10 # vr30, 4 ++ ++ vspltisw 21, 12 ++ vspltisw 23, 7 ++ ++ ld 11, permx@got(2) ++ lxvw4x 32+20, 0, 11 ++ lxvw4x 32+22, 17, 11 ++ ++ li 8, 10 ++ mtctr 8 ++ ++ xxlor 16, 48, 48 ++ xxlor 17, 49, 49 ++ xxlor 18, 50, 50 ++ xxlor 19, 51, 51 ++ ++ vspltisw 25, 4 ++ vspltisw 26, 8 ++ ++ xxlor 16, 48, 48 ++ xxlor 17, 49, 49 ++ xxlor 18, 50, 50 ++ xxlor 19, 51, 51 ++ ++ xxlor 25, 32+26, 32+26 ++ xxlor 24, 32+25, 32+25 ++ ++ vadduwm 31, 30, 25 # (0, 1, 2, 3) + (4, 4, 4, 4) ++ xxlor 30, 32+30, 32+30 ++ xxlor 31, 32+31, 32+31 ++ ++ xxlor 20, 32+20, 32+20 ++ xxlor 21, 32+21, 32+21 ++ xxlor 22, 32+22, 32+22 ++ xxlor 23, 32+23, 32+23 ++ ++Loop_8x: ++ lvx 0, 20, 10 ++ lvx 1, 21, 10 ++ lvx 2, 22, 10 ++ lvx 3, 23, 10 ++ xxspltw 32+4, 17, 0 ++ xxspltw 32+5, 17, 1 ++ xxspltw 32+6, 17, 2 ++ xxspltw 32+7, 17, 3 ++ xxspltw 32+8, 18, 0 ++ xxspltw 32+9, 18, 1 ++ xxspltw 32+10, 18, 2 ++ xxspltw 32+11, 18, 3 ++ xxspltw 32+12, 19, 0 ++ xxspltw 32+13, 19, 1 ++ xxspltw 32+14, 19, 2 ++ xxspltw 32+15, 19, 3 ++ vadduwm 12, 12, 30 # increase counter ++ ++ lvx 16, 20, 10 ++ lvx 17, 21, 10 ++ lvx 18, 22, 10 ++ lvx 19, 23, 10 ++ xxspltw 32+20, 17, 0 ++ xxspltw 32+21, 17, 1 ++ xxspltw 32+22, 17, 2 ++ xxspltw 32+23, 17, 3 ++ xxspltw 32+24, 18, 0 ++ xxspltw 32+25, 18, 1 ++ xxspltw 32+26, 18, 2 ++ xxspltw 32+27, 18, 3 ++ xxspltw 32+28, 19, 0 ++ xxspltw 32+29, 19, 1 ++ vadduwm 28, 28, 31 # increase counter ++ xxspltw 32+30, 19, 2 ++ xxspltw 32+31, 19, 3 ++ ++.align 5 ++quarter_loop_8x: ++ QT_loop_8x ++ ++ bdnz quarter_loop_8x ++ ++ xxlor 0, 32+30, 32+30 ++ xxlor 32+30, 30, 30 ++ vadduwm 12, 12, 30 ++ xxlor 32+30, 0, 0 ++ TP_4x 0, 1, 2, 3 ++ TP_4x 4, 5, 6, 7 ++ TP_4x 8, 9, 10, 11 ++ TP_4x 12, 13, 14, 15 ++ ++ xxlor 0, 48, 48 ++ xxlor 1, 49, 49 ++ xxlor 2, 50, 50 ++ xxlor 3, 51, 51 ++ xxlor 48, 16, 16 ++ xxlor 49, 17, 17 ++ xxlor 50, 18, 18 ++ xxlor 51, 19, 19 ++ Add_state 0 ++ xxlor 48, 0, 0 ++ xxlor 49, 1, 1 ++ xxlor 50, 2, 2 ++ xxlor 51, 3, 3 ++ Write_256 0 ++ addi 14, 14, 256 ++ addi 15, 15, -256 ++ ++ xxlor 5, 32+31, 32+31 ++ xxlor 32+31, 31, 31 ++ vadduwm 28, 28, 31 ++ xxlor 32+31, 5, 5 ++ TP_4x 16+0, 16+1, 16+2, 16+3 ++ TP_4x 16+4, 16+5, 16+6, 16+7 ++ TP_4x 16+8, 16+9, 16+10, 16+11 ++ TP_4x 16+12, 16+13, 16+14, 16+15 ++ ++ xxlor 32, 16, 16 ++ xxlor 33, 17, 17 ++ xxlor 34, 18, 18 ++ xxlor 35, 19, 19 ++ Add_state 16 ++ Write_256 16 ++ addi 14, 14, 256 ++ addi 15, 15, -256 ++ ++ # should update counter before out? ++ xxlor 32+24, 24, 24 ++ xxlor 32+25, 25, 25 ++ xxlor 32+30, 30, 30 ++ vadduwm 30, 30, 25 ++ vadduwm 31, 30, 24 ++ xxlor 30, 32+30, 32+30 ++ xxlor 31, 32+31, 32+31 ++ ++ cmpdi 15, 0 ++ beq Out_loop ++ ++ cmpdi 15, 512 ++ blt Loop_last ++ ++ mtctr 8 ++ b Loop_8x ++ ++Loop_last: ++ lxvw4x 48, 0, 3 # vr16, constants ++ lxvw4x 49, 17, 3 # vr17, key 1 ++ lxvw4x 50, 18, 3 # vr18, key 2 ++ lxvw4x 51, 19, 3 # vr19, counter, nonce ++ ++ vspltisw 21, 12 ++ vspltisw 23, 7 ++ lxvw4x 32+20, 0, 11 ++ lxvw4x 32+22, 17, 11 ++ ++ li 8, 10 ++ mtctr 8 ++ ++Loop_4x: ++ lvx 0, 20, 10 ++ lvx 1, 21, 10 ++ lvx 2, 22, 10 ++ lvx 3, 23, 10 ++ vspltw 4, 17, 0 ++ vspltw 5, 17, 1 ++ vspltw 6, 17, 2 ++ vspltw 7, 17, 3 ++ vspltw 8, 18, 0 ++ vspltw 9, 18, 1 ++ vspltw 10, 18, 2 ++ vspltw 11, 18, 3 ++ vspltw 12, 19, 0 ++ vadduwm 12, 12, 30 # increase counter ++ vspltw 13, 19, 1 ++ vspltw 14, 19, 2 ++ vspltw 15, 19, 3 ++ ++.align 5 ++quarter_loop: ++ QT_loop_4x ++ ++ bdnz quarter_loop ++ ++ vadduwm 12, 12, 30 ++ TP_4x 0, 1, 2, 3 ++ TP_4x 4, 5, 6, 7 ++ TP_4x 8, 9, 10, 11 ++ TP_4x 12, 13, 14, 15 ++ ++ Add_state 0 ++ Write_256 0 ++ addi 14, 14, 256 ++ addi 15, 15, -256 ++ ++ # Update state counter ++ vspltisw 25, 4 ++ vadduwm 30, 30, 25 ++ ++ cmpdi 15, 0 ++ beq Out_loop ++ ++ mtctr 8 ++ b Loop_4x ++ ++Out_loop: ++ # ++ # Update state counter ++ # ++ vspltisb 16, -1 # first 16 bytes - 0xffff...ff ++ vspltisb 17, 0 # second 16 bytes - 0x0000...00 ++ vsldoi 18, 16, 17, 12 ++ vand 18, 18, 30 ++ xxlor 32+19, 19, 19 ++ vadduwm 18, 19, 18 ++ stxvw4x 32+18, 19, 3 ++ li 3, 0 ++ ++ addi 9, 1, 256 ++ lvx 20, 0, 9 ++ lvx 21, 17, 9 ++ lvx 22, 18, 9 ++ lvx 23, 19, 9 ++ lvx 24, 20, 9 ++ lvx 25, 21, 9 ++ lvx 26, 22, 9 ++ lvx 27, 23, 9 ++ lvx 28, 24, 9 ++ lvx 29, 25, 9 ++ lvx 30, 26, 9 ++ lvx 31, 27, 9 ++ ++ add 9, 9, 27 ++ addi 14, 17, 16 ++ lxvx 14, 14, 9 ++ addi 14, 14, 16 ++ lxvx 15, 14, 9 ++ addi 14, 14, 16 ++ lxvx 16, 14, 9 ++ addi 14, 14, 16 ++ lxvx 17, 14, 9 ++ addi 14, 14, 16 ++ lxvx 18, 14, 9 ++ addi 14, 14, 16 ++ lxvx 19, 14, 9 ++ addi 14, 14, 16 ++ lxvx 20, 14, 9 ++ addi 14, 14, 16 ++ lxvx 21, 14, 9 ++ addi 14, 14, 16 ++ lxvx 22, 14, 9 ++ addi 14, 14, 16 ++ lxvx 23, 14, 9 ++ addi 14, 14, 16 ++ lxvx 24, 14, 9 ++ addi 14, 14, 16 ++ lxvx 25, 14, 9 ++ addi 14, 14, 16 ++ lxvx 26, 14, 9 ++ addi 14, 14, 16 ++ lxvx 27, 14, 9 ++ addi 14, 14, 16 ++ lxvx 28, 14, 9 ++ addi 14, 14, 16 ++ lxvx 29, 14, 9 ++ addi 14, 14, 16 ++ lxvx 30, 14, 9 ++ addi 14, 14, 16 ++ lxvx 31, 14, 9 ++ ++ ld 0, 1040(1) ++ ld 14,112(1) ++ ld 15,120(1) ++ ld 16,128(1) ++ ld 17,136(1) ++ ld 18,144(1) ++ ld 19,152(1) ++ ld 20,160(1) ++ ld 21,168(1) ++ ld 22,176(1) ++ ld 23,184(1) ++ ld 24,192(1) ++ ld 25,200(1) ++ ld 26,208(1) ++ ld 27,216(1) ++ ld 28,224(1) ++ ld 29,232(1) ++ ld 30,240(1) ++ ld 31,248(1) ++ ++ mtlr 0 ++ addi 1, 1, 1024 ++ blr ++ ++Out_no_chacha: ++ li 3, 0 ++ blr ++ ++.data ++.align 4 ++sigma: ++.long 0x61707865, 0x3320646e, 0x79622d32, 0x6b206574 ++.long 0x0c0d0e0f, 0x08090a0b, 0x04050607, 0x00010203 ++.long 1, 0, 0, 0 ++.long 0, 1, 2, 3 ++.long 0x61707865, 0x61707865, 0x61707865, 0x61707865 ++.long 0x3320646e, 0x3320646e, 0x3320646e, 0x3320646e ++.long 0x79622d32, 0x79622d32, 0x79622d32, 0x79622d32 ++.long 0x6b206574, 0x6b206574, 0x6b206574, 0x6b206574 ++permx: ++.long 0x22330011, 0x66774455, 0xaabb8899, 0xeeffccdd ++.long 0x11223300, 0x55667744, 0x99aabb88, 0xddeeffcc +Index: libgcrypt-1.10.2/cipher/chacha20.c +=================================================================== +--- libgcrypt-1.10.2.orig/cipher/chacha20.c ++++ libgcrypt-1.10.2/cipher/chacha20.c +@@ -125,6 +125,7 @@ typedef struct CHACHA20_context_s + unsigned int use_avx2:1; + unsigned int use_neon:1; + unsigned int use_ppc:1; ++ unsigned int use_p10:1; + unsigned int use_s390x:1; + } CHACHA20_context_t; + +@@ -163,6 +164,12 @@ unsigned int _gcry_chacha20_poly1305_amd + + #ifdef USE_PPC_VEC + ++#ifndef WORDS_BIGENDIAN ++unsigned int _gcry_chacha20_p10le_8x(u32 *state, byte *dst, ++ const byte *src, ++ size_t len); ++#endif ++ + unsigned int _gcry_chacha20_ppc8_blocks4(u32 *state, byte *dst, + const byte *src, + size_t nblks); +@@ -475,6 +482,9 @@ chacha20_do_setkey (CHACHA20_context_t * + #endif + #ifdef USE_PPC_VEC + ctx->use_ppc = (features & HWF_PPC_ARCH_2_07) != 0; ++# ifndef WORDS_BIGENDIAN ++ ctx->use_p10 = (features & HWF_PPC_ARCH_3_10) != 0; ++# endif + #endif + #ifdef USE_S390X_VX + ctx->use_s390x = (features & HWF_S390X_VX) != 0; +@@ -571,7 +581,22 @@ do_chacha20_encrypt_stream_tail (CHACHA2 + { + size_t nblocks = length / CHACHA20_BLOCK_SIZE; + nblocks -= nblocks % 4; +- nburn = _gcry_chacha20_ppc8_blocks4(ctx->input, outbuf, inbuf, nblocks); ++#ifndef WORDS_BIGENDIAN ++ /* ++ * A workaround to skip counter overflow. This is rare. ++ */ ++ if (ctx->use_p10 && nblocks >= 8 ++ && ((u64)ctx->input[12] + nblocks) <= 0xffffffffU) ++ { ++ size_t len = nblocks * CHACHA20_BLOCK_SIZE; ++ nburn = _gcry_chacha20_p10le_8x(ctx->input, outbuf, inbuf, len); ++ } ++ else ++#endif ++ { ++ nburn = _gcry_chacha20_ppc8_blocks4(ctx->input, outbuf, inbuf, ++ nblocks); ++ } + burn = nburn > burn ? nburn : burn; + length -= nblocks * CHACHA20_BLOCK_SIZE; + outbuf += nblocks * CHACHA20_BLOCK_SIZE; +@@ -760,6 +785,11 @@ _gcry_chacha20_poly1305_encrypt(gcry_cip + } + #endif + #ifdef USE_PPC_VEC_POLY1305 ++ else if (ctx->use_ppc && ctx->use_p10) ++ { ++ /* Skip stitched chacha20-poly1305 for P10. */ ++ authptr = NULL; ++ } + else if (ctx->use_ppc && length >= CHACHA20_BLOCK_SIZE * 4) + { + nburn = _gcry_chacha20_ppc8_blocks4(ctx->input, outbuf, inbuf, 4); +@@ -998,6 +1028,7 @@ _gcry_chacha20_poly1305_decrypt(gcry_cip + { + CHACHA20_context_t *ctx = (void *) &c->context.c; + unsigned int nburn, burn = 0; ++ int skip_stitched = 0; + + if (!length) + return 0; +@@ -1049,6 +1080,13 @@ _gcry_chacha20_poly1305_decrypt(gcry_cip + inbuf += nblocks * CHACHA20_BLOCK_SIZE; + } + #endif ++#ifdef USE_PPC_VEC_POLY1305 ++ if (ctx->use_ppc && ctx->use_p10) ++ { ++ /* Skip stitched chacha20-poly1305 for P10. */ ++ skip_stitched = 1; ++ } ++#endif + + #ifdef USE_SSSE3 + if (ctx->use_ssse3) +@@ -1102,7 +1140,8 @@ _gcry_chacha20_poly1305_decrypt(gcry_cip + #endif + + #ifdef USE_PPC_VEC_POLY1305 +- if (ctx->use_ppc && length >= 4 * CHACHA20_BLOCK_SIZE) ++ /* skip stitch for p10 */ ++ if (!skip_stitched && ctx->use_ppc && length >= 4 * CHACHA20_BLOCK_SIZE) + { + size_t nblocks = length / CHACHA20_BLOCK_SIZE; + nblocks -= nblocks % 4; +Index: libgcrypt-1.10.2/cipher/poly1305-internal.h +=================================================================== +--- libgcrypt-1.10.2.orig/cipher/poly1305-internal.h ++++ libgcrypt-1.10.2/cipher/poly1305-internal.h +@@ -33,6 +33,17 @@ + #define POLY1305_KEYLEN 32 + #define POLY1305_BLOCKSIZE 16 + ++/* POLY1305_USE_PPC_VEC indicates whether to enable PowerPC vector code. */ ++#undef POLY1305_USE_PPC_VEC ++#ifdef ENABLE_PPC_CRYPTO_SUPPORT ++# if defined(HAVE_COMPATIBLE_CC_PPC_ALTIVEC) && \ ++ defined(HAVE_GCC_INLINE_ASM_PPC_ALTIVEC) && \ ++ !defined(WORDS_BIGENDIAN) ++# if __GNUC__ >= 4 ++# define POLY1305_USE_PPC_VEC 1 ++# endif ++# endif ++#endif + + typedef struct + { +@@ -46,6 +57,9 @@ typedef struct poly1305_context_s + POLY1305_STATE state; + byte buffer[POLY1305_BLOCKSIZE]; + unsigned int leftover; ++#ifdef POLY1305_USE_PPC_VEC ++ unsigned int use_p10:1; ++#endif + } poly1305_context_t; + + +Index: libgcrypt-1.10.2/cipher/poly1305-p10le.s +=================================================================== +--- /dev/null ++++ libgcrypt-1.10.2/cipher/poly1305-p10le.s +@@ -0,0 +1,841 @@ ++# Copyright 2021- IBM Inc. All rights reserved ++# ++# This file is part of Libgcrypt. ++# ++# Libgcrypt is free software; you can redistribute it and/or modify ++# it under the terms of the GNU Lesser General Public License as ++# published by the Free Software Foundation; either version 2.1 of ++# the License, or (at your option) any later version. ++# ++# Libgcrypt 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 Lesser General Public License for more details. ++# ++# You should have received a copy of the GNU Lesser General Public ++# License along with this program; if not, see . ++# ++#=================================================================================== ++# Written by Danny Tsen ++# ++# Poly1305 - this version mainly using vector/VSX/Scalar ++# - 26 bits limbs ++# - Handle multiple 64 byte blcoks but need at least 2 64 bytes block ++# ++# Improve performance by breaking down polynominal to the sum of products with ++# h4 = m1 * r⁴ + m2 * r³ + m3 * r² + m4 * r ++# ++# 07/22/21 - this revison based on the above sum of products. Setup r^4, r^3, r^2, r and s3, s2, s1, s0 ++# to 9 vectors for multiplications. ++# ++# setup r^4, r^3, r^2, r vectors ++# vs [r^1, r^3, r^2, r^4] ++# vs0 = [r0,.....] ++# vs1 = [r1,.....] ++# vs2 = [r2,.....] ++# vs3 = [r3,.....] ++# vs4 = [r4,.....] ++# vs5 = [r1*5,...] ++# vs6 = [r2*5,...] ++# vs7 = [r2*5,...] ++# vs8 = [r4*5,...] ++# ++# Each word in a vector consists a member of a "r/s" in [a * r/s]. ++# ++# r0, r4*5, r3*5, r2*5, r1*5; ++# r1, r0, r4*5, r3*5, r2*5; ++# r2, r1, r0, r4*5, r3*5; ++# r3, r2, r1, r0, r4*5; ++# r4, r3, r2, r1, r0 ; ++# ++# ++# gcry_poly1305_p10le_4blocks( uint8_t *k, uint32_t mlen, uint8_t *m) ++# k = 32 bytes key ++# r3 = k (r, s) ++# r4 = mlen ++# r5 = m ++# ++.text ++ ++# Block size 16 bytes ++# key = (r, s) ++# clamp r &= 0x0FFFFFFC0FFFFFFC 0x0FFFFFFC0FFFFFFF ++# p = 2^130 - 5 ++# a += m ++# a = (r + a) % p ++# a += s ++# 16 bytes (a) ++# ++# p[0] = a0*r0 + a1*r4*5 + a2*r3*5 + a3*r2*5 + a4*r1*5; ++# p[1] = a0*r1 + a1*r0 + a2*r4*5 + a3*r3*5 + a4*r2*5; ++# p[2] = a0*r2 + a1*r1 + a2*r0 + a3*r4*5 + a4*r3*5; ++# p[3] = a0*r3 + a1*r2 + a2*r1 + a3*r0 + a4*r4*5; ++# p[4] = a0*r4 + a1*r3 + a2*r2 + a3*r1 + a4*r0 ; ++# ++# [r^2, r^3, r^1, r^4] ++# [m3, m2, m4, m1] ++# ++# multiply odd and even words ++.macro mul_odd ++ vmulouw 14, 4, 26 ++ vmulouw 10, 5, 3 ++ vmulouw 11, 6, 2 ++ vmulouw 12, 7, 1 ++ vmulouw 13, 8, 0 ++ vmulouw 15, 4, 27 ++ vaddudm 14, 14, 10 ++ vaddudm 14, 14, 11 ++ vmulouw 10, 5, 26 ++ vmulouw 11, 6, 3 ++ vaddudm 14, 14, 12 ++ vaddudm 14, 14, 13 # x0 ++ vaddudm 15, 15, 10 ++ vaddudm 15, 15, 11 ++ vmulouw 12, 7, 2 ++ vmulouw 13, 8, 1 ++ vaddudm 15, 15, 12 ++ vaddudm 15, 15, 13 # x1 ++ vmulouw 16, 4, 28 ++ vmulouw 10, 5, 27 ++ vmulouw 11, 6, 26 ++ vaddudm 16, 16, 10 ++ vaddudm 16, 16, 11 ++ vmulouw 12, 7, 3 ++ vmulouw 13, 8, 2 ++ vaddudm 16, 16, 12 ++ vaddudm 16, 16, 13 # x2 ++ vmulouw 17, 4, 29 ++ vmulouw 10, 5, 28 ++ vmulouw 11, 6, 27 ++ vaddudm 17, 17, 10 ++ vaddudm 17, 17, 11 ++ vmulouw 12, 7, 26 ++ vmulouw 13, 8, 3 ++ vaddudm 17, 17, 12 ++ vaddudm 17, 17, 13 # x3 ++ vmulouw 18, 4, 30 ++ vmulouw 10, 5, 29 ++ vmulouw 11, 6, 28 ++ vaddudm 18, 18, 10 ++ vaddudm 18, 18, 11 ++ vmulouw 12, 7, 27 ++ vmulouw 13, 8, 26 ++ vaddudm 18, 18, 12 ++ vaddudm 18, 18, 13 # x4 ++.endm ++ ++.macro mul_even ++ vmuleuw 9, 4, 26 ++ vmuleuw 10, 5, 3 ++ vmuleuw 11, 6, 2 ++ vmuleuw 12, 7, 1 ++ vmuleuw 13, 8, 0 ++ vaddudm 14, 14, 9 ++ vaddudm 14, 14, 10 ++ vaddudm 14, 14, 11 ++ vaddudm 14, 14, 12 ++ vaddudm 14, 14, 13 # x0 ++ ++ vmuleuw 9, 4, 27 ++ vmuleuw 10, 5, 26 ++ vmuleuw 11, 6, 3 ++ vmuleuw 12, 7, 2 ++ vmuleuw 13, 8, 1 ++ vaddudm 15, 15, 9 ++ vaddudm 15, 15, 10 ++ vaddudm 15, 15, 11 ++ vaddudm 15, 15, 12 ++ vaddudm 15, 15, 13 # x1 ++ ++ vmuleuw 9, 4, 28 ++ vmuleuw 10, 5, 27 ++ vmuleuw 11, 6, 26 ++ vmuleuw 12, 7, 3 ++ vmuleuw 13, 8, 2 ++ vaddudm 16, 16, 9 ++ vaddudm 16, 16, 10 ++ vaddudm 16, 16, 11 ++ vaddudm 16, 16, 12 ++ vaddudm 16, 16, 13 # x2 ++ ++ vmuleuw 9, 4, 29 ++ vmuleuw 10, 5, 28 ++ vmuleuw 11, 6, 27 ++ vmuleuw 12, 7, 26 ++ vmuleuw 13, 8, 3 ++ vaddudm 17, 17, 9 ++ vaddudm 17, 17, 10 ++ vaddudm 17, 17, 11 ++ vaddudm 17, 17, 12 ++ vaddudm 17, 17, 13 # x3 ++ ++ vmuleuw 9, 4, 30 ++ vmuleuw 10, 5, 29 ++ vmuleuw 11, 6, 28 ++ vmuleuw 12, 7, 27 ++ vmuleuw 13, 8, 26 ++ vaddudm 18, 18, 9 ++ vaddudm 18, 18, 10 ++ vaddudm 18, 18, 11 ++ vaddudm 18, 18, 12 ++ vaddudm 18, 18, 13 # x4 ++.endm ++ ++# setup r^4, r^3, r^2, r vectors ++# [r, r^3, r^2, r^4] ++# vs0 = [r0,...] ++# vs1 = [r1,...] ++# vs2 = [r2,...] ++# vs3 = [r3,...] ++# vs4 = [r4,...] ++# vs5 = [r4*5,...] ++# vs6 = [r3*5,...] ++# vs7 = [r2*5,...] ++# vs8 = [r1*5,...] ++# ++# r0, r4*5, r3*5, r2*5, r1*5; ++# r1, r0, r4*5, r3*5, r2*5; ++# r2, r1, r0, r4*5, r3*5; ++# r3, r2, r1, r0, r4*5; ++# r4, r3, r2, r1, r0 ; ++# ++.macro poly1305_setup_r ++ ++ # save r ++ xxlor 26, 58, 58 ++ xxlor 27, 59, 59 ++ xxlor 28, 60, 60 ++ xxlor 29, 61, 61 ++ xxlor 30, 62, 62 ++ ++ xxlxor 31, 31, 31 ++ ++# [r, r^3, r^2, r^4] ++ # compute r^2 ++ vmr 4, 26 ++ vmr 5, 27 ++ vmr 6, 28 ++ vmr 7, 29 ++ vmr 8, 30 ++ bl do_mul # r^2 r^1 ++ xxpermdi 58, 58, 36, 0x3 # r0 ++ xxpermdi 59, 59, 37, 0x3 # r1 ++ xxpermdi 60, 60, 38, 0x3 # r2 ++ xxpermdi 61, 61, 39, 0x3 # r3 ++ xxpermdi 62, 62, 40, 0x3 # r4 ++ xxpermdi 36, 36, 36, 0x3 ++ xxpermdi 37, 37, 37, 0x3 ++ xxpermdi 38, 38, 38, 0x3 ++ xxpermdi 39, 39, 39, 0x3 ++ xxpermdi 40, 40, 40, 0x3 ++ vspltisb 13, 2 ++ vsld 9, 27, 13 ++ vsld 10, 28, 13 ++ vsld 11, 29, 13 ++ vsld 12, 30, 13 ++ vaddudm 0, 9, 27 ++ vaddudm 1, 10, 28 ++ vaddudm 2, 11, 29 ++ vaddudm 3, 12, 30 ++ ++ bl do_mul # r^4 r^3 ++ vmrgow 26, 26, 4 ++ vmrgow 27, 27, 5 ++ vmrgow 28, 28, 6 ++ vmrgow 29, 29, 7 ++ vmrgow 30, 30, 8 ++ vspltisb 13, 2 ++ vsld 9, 27, 13 ++ vsld 10, 28, 13 ++ vsld 11, 29, 13 ++ vsld 12, 30, 13 ++ vaddudm 0, 9, 27 ++ vaddudm 1, 10, 28 ++ vaddudm 2, 11, 29 ++ vaddudm 3, 12, 30 ++ ++ # r^2 r^4 ++ xxlor 0, 58, 58 ++ xxlor 1, 59, 59 ++ xxlor 2, 60, 60 ++ xxlor 3, 61, 61 ++ xxlor 4, 62, 62 ++ xxlor 5, 32, 32 ++ xxlor 6, 33, 33 ++ xxlor 7, 34, 34 ++ xxlor 8, 35, 35 ++ ++ vspltw 9, 26, 3 ++ vspltw 10, 26, 2 ++ vmrgow 26, 10, 9 ++ vspltw 9, 27, 3 ++ vspltw 10, 27, 2 ++ vmrgow 27, 10, 9 ++ vspltw 9, 28, 3 ++ vspltw 10, 28, 2 ++ vmrgow 28, 10, 9 ++ vspltw 9, 29, 3 ++ vspltw 10, 29, 2 ++ vmrgow 29, 10, 9 ++ vspltw 9, 30, 3 ++ vspltw 10, 30, 2 ++ vmrgow 30, 10, 9 ++ ++ vsld 9, 27, 13 ++ vsld 10, 28, 13 ++ vsld 11, 29, 13 ++ vsld 12, 30, 13 ++ vaddudm 0, 9, 27 ++ vaddudm 1, 10, 28 ++ vaddudm 2, 11, 29 ++ vaddudm 3, 12, 30 ++.endm ++ ++do_mul: ++ mul_odd ++ ++ # do reduction ( h %= p ) ++ # carry reduction ++ vspltisb 9, 2 ++ vsrd 10, 14, 31 ++ vsrd 11, 17, 31 ++ vand 7, 17, 25 ++ vand 4, 14, 25 ++ vaddudm 18, 18, 11 ++ vsrd 12, 18, 31 ++ vaddudm 15, 15, 10 ++ ++ vsrd 11, 15, 31 ++ vand 8, 18, 25 ++ vand 5, 15, 25 ++ vaddudm 4, 4, 12 ++ vsld 10, 12, 9 ++ vaddudm 6, 16, 11 ++ ++ vsrd 13, 6, 31 ++ vand 6, 6, 25 ++ vaddudm 4, 4, 10 ++ vsrd 10, 4, 31 ++ vaddudm 7, 7, 13 ++ ++ vsrd 11, 7, 31 ++ vand 7, 7, 25 ++ vand 4, 4, 25 ++ vaddudm 5, 5, 10 ++ vaddudm 8, 8, 11 ++ blr ++ ++# ++# init key ++# ++do_poly1305_init: ++ ld 10, rmask@got(2) ++ ld 11, 0(10) ++ ld 12, 8(10) ++ ++ li 14, 16 ++ li 15, 32 ++ ld 10, cnum@got(2) ++ lvx 25, 0, 10 # v25 - mask ++ lvx 31, 14, 10 # v31 = 1a ++ lvx 19, 15, 10 # v19 = 1 << 24 ++ lxv 24, 48(10) # vs24 ++ lxv 25, 64(10) # vs25 ++ ++ # initialize ++ # load key from r3 to vectors ++ ld 9, 16(3) ++ ld 10, 24(3) ++ ld 11, 0(3) ++ ld 12, 8(3) ++ ++ # break 26 bits ++ extrdi 14, 9, 26, 38 ++ extrdi 15, 9, 26, 12 ++ extrdi 16, 9, 12, 0 ++ mtvsrdd 58, 0, 14 ++ insrdi 16, 10, 14, 38 ++ mtvsrdd 59, 0, 15 ++ extrdi 17, 10, 26, 24 ++ mtvsrdd 60, 0, 16 ++ extrdi 18, 10, 24, 0 ++ mtvsrdd 61, 0, 17 ++ mtvsrdd 62, 0, 18 ++ ++ # r1 = r1 * 5, r2 = r2 * 5, r3 = r3 * 5, r4 = r4 * 5 ++ li 9, 5 ++ mtvsrdd 36, 0, 9 ++ vmulouw 0, 27, 4 # v0 = rr0 ++ vmulouw 1, 28, 4 # v1 = rr1 ++ vmulouw 2, 29, 4 # v2 = rr2 ++ vmulouw 3, 30, 4 # v3 = rr3 ++ blr ++ ++# ++# gcry_poly1305_p10le_4blocks( uint8_t *k, uint32_t mlen, uint8_t *m) ++# k = 32 bytes key ++# r3 = k (r, s) ++# r4 = mlen ++# r5 = m ++# ++.global gcry_poly1305_p10le_4blocks ++.align 5 ++gcry_poly1305_p10le_4blocks: ++_gcry_poly1305_p10le_4blocks: ++ cmpdi 5, 128 ++ blt Out_no_poly1305 ++ ++ stdu 1,-1024(1) ++ mflr 0 ++ ++ std 14,112(1) ++ std 15,120(1) ++ std 16,128(1) ++ std 17,136(1) ++ std 18,144(1) ++ std 19,152(1) ++ std 20,160(1) ++ std 21,168(1) ++ std 31,248(1) ++ li 14, 256 ++ stvx 20, 14, 1 ++ addi 14, 14, 16 ++ stvx 21, 14, 1 ++ addi 14, 14, 16 ++ stvx 22, 14, 1 ++ addi 14, 14, 16 ++ stvx 23, 14, 1 ++ addi 14, 14, 16 ++ stvx 24, 14, 1 ++ addi 14, 14, 16 ++ stvx 25, 14, 1 ++ addi 14, 14, 16 ++ stvx 26, 14, 1 ++ addi 14, 14, 16 ++ stvx 27, 14, 1 ++ addi 14, 14, 16 ++ stvx 28, 14, 1 ++ addi 14, 14, 16 ++ stvx 29, 14, 1 ++ addi 14, 14, 16 ++ stvx 30, 14, 1 ++ addi 14, 14, 16 ++ stvx 31, 14, 1 ++ ++ addi 14, 14, 16 ++ stxvx 14, 14, 1 ++ addi 14, 14, 16 ++ stxvx 15, 14, 1 ++ addi 14, 14, 16 ++ stxvx 16, 14, 1 ++ addi 14, 14, 16 ++ stxvx 17, 14, 1 ++ addi 14, 14, 16 ++ stxvx 18, 14, 1 ++ addi 14, 14, 16 ++ stxvx 19, 14, 1 ++ addi 14, 14, 16 ++ stxvx 20, 14, 1 ++ addi 14, 14, 16 ++ stxvx 21, 14, 1 ++ addi 14, 14, 16 ++ stxvx 22, 14, 1 ++ addi 14, 14, 16 ++ stxvx 23, 14, 1 ++ addi 14, 14, 16 ++ stxvx 24, 14, 1 ++ addi 14, 14, 16 ++ stxvx 25, 14, 1 ++ addi 14, 14, 16 ++ stxvx 26, 14, 1 ++ addi 14, 14, 16 ++ stxvx 27, 14, 1 ++ addi 14, 14, 16 ++ stxvx 28, 14, 1 ++ addi 14, 14, 16 ++ stxvx 29, 14, 1 ++ addi 14, 14, 16 ++ stxvx 30, 14, 1 ++ addi 14, 14, 16 ++ stxvx 31, 14, 1 ++ std 0, 1040(1) ++ ++ bl do_poly1305_init ++ ++ li 21, 0 # counter to message ++ ++ poly1305_setup_r ++ ++ # load previous state ++ # break/convert r6 to 26 bits ++ ld 9, 32(3) ++ ld 10, 40(3) ++ lwz 19, 48(3) ++ sldi 19, 19, 24 ++ mtvsrdd 41, 0, 19 ++ extrdi 14, 9, 26, 38 ++ extrdi 15, 9, 26, 12 ++ extrdi 16, 9, 12, 0 ++ mtvsrdd 36, 0, 14 ++ insrdi 16, 10, 14, 38 ++ mtvsrdd 37, 0, 15 ++ extrdi 17, 10, 26, 24 ++ mtvsrdd 38, 0, 16 ++ extrdi 18, 10, 24, 0 ++ mtvsrdd 39, 0, 17 ++ mtvsrdd 40, 0, 18 ++ vor 8, 8, 9 ++ ++ # input m1 m2 ++ add 20, 4, 21 ++ xxlor 49, 24, 24 ++ xxlor 50, 25, 25 ++ lxvw4x 43, 0, 20 ++ addi 17, 20, 16 ++ lxvw4x 44, 0, 17 ++ vperm 14, 11, 12, 17 ++ vperm 15, 11, 12, 18 ++ vand 9, 14, 25 # a0 ++ vsrd 10, 14, 31 # >> 26 ++ vsrd 11, 10, 31 # 12 bits left ++ vand 10, 10, 25 # a1 ++ vspltisb 13, 12 ++ vand 16, 15, 25 ++ vsld 12, 16, 13 ++ vor 11, 11, 12 ++ vand 11, 11, 25 # a2 ++ vspltisb 13, 14 ++ vsrd 12, 15, 13 # >> 14 ++ vsrd 13, 12, 31 # >> 26, a4 ++ vand 12, 12, 25 # a3 ++ ++ vaddudm 20, 4, 9 ++ vaddudm 21, 5, 10 ++ vaddudm 22, 6, 11 ++ vaddudm 23, 7, 12 ++ vaddudm 24, 8, 13 ++ ++ # m3 m4 ++ addi 17, 17, 16 ++ lxvw4x 43, 0, 17 ++ addi 17, 17, 16 ++ lxvw4x 44, 0, 17 ++ vperm 14, 11, 12, 17 ++ vperm 15, 11, 12, 18 ++ vand 9, 14, 25 # a0 ++ vsrd 10, 14, 31 # >> 26 ++ vsrd 11, 10, 31 # 12 bits left ++ vand 10, 10, 25 # a1 ++ vspltisb 13, 12 ++ vand 16, 15, 25 ++ vsld 12, 16, 13 ++ vspltisb 13, 14 ++ vor 11, 11, 12 ++ vand 11, 11, 25 # a2 ++ vsrd 12, 15, 13 # >> 14 ++ vsrd 13, 12, 31 # >> 26, a4 ++ vand 12, 12, 25 # a3 ++ ++ # Smash 4 message blocks into 5 vectors of [m4, m2, m3, m1] ++ vmrgow 4, 9, 20 ++ vmrgow 5, 10, 21 ++ vmrgow 6, 11, 22 ++ vmrgow 7, 12, 23 ++ vmrgow 8, 13, 24 ++ vaddudm 8, 8, 19 ++ ++ addi 5, 5, -64 ++ addi 21, 21, 64 ++ ++ li 9, 64 ++ divdu 31, 5, 9 ++ ++ mtctr 31 ++ ++# h4 = m1 * r⁴ + m2 * r³ + m3 * r² + m4 * r ++# Rewrite the polynominal sum of product as follows, ++# h1 = (h0 + m1) * r^2, h2 = (h0 + m2) * r^2 ++# h3 = (h1 + m3) * r^2, h4 = (h2 + m4) * r^2 --> (h0 + m1) r*4 + (h3 + m3) r^2, (h0 + m2) r^4 + (h0 + m4) r^2 ++# .... Repeat ++# h5 = (h3 + m5) * r^2, h6 = (h4 + m6) * r^2 --> ++# h7 = (h5 + m7) * r^2, h8 = (h6 + m8) * r^1 --> m5 * r^4 + m6 * r^3 + m7 * r^2 + m8 * r ++# ++loop_4blocks: ++ ++ # Multiply odd words and even words ++ mul_odd ++ mul_even ++ # carry reduction ++ vspltisb 9, 2 ++ vsrd 10, 14, 31 ++ vsrd 11, 17, 31 ++ vand 7, 17, 25 ++ vand 4, 14, 25 ++ vaddudm 18, 18, 11 ++ vsrd 12, 18, 31 ++ vaddudm 15, 15, 10 ++ ++ vsrd 11, 15, 31 ++ vand 8, 18, 25 ++ vand 5, 15, 25 ++ vaddudm 4, 4, 12 ++ vsld 10, 12, 9 ++ vaddudm 6, 16, 11 ++ ++ vsrd 13, 6, 31 ++ vand 6, 6, 25 ++ vaddudm 4, 4, 10 ++ vsrd 10, 4, 31 ++ vaddudm 7, 7, 13 ++ ++ vsrd 11, 7, 31 ++ vand 7, 7, 25 ++ vand 4, 4, 25 ++ vaddudm 5, 5, 10 ++ vaddudm 8, 8, 11 ++ ++ # input m1 m2 m3 m4 ++ add 20, 4, 21 ++ xxlor 49, 24, 24 ++ xxlor 50, 25, 25 ++ lxvw4x 43, 0, 20 ++ addi 17, 20, 16 ++ lxvw4x 44, 0, 17 ++ vperm 14, 11, 12, 17 ++ vperm 15, 11, 12, 18 ++ addi 17, 17, 16 ++ lxvw4x 43, 0, 17 ++ addi 17, 17, 16 ++ lxvw4x 44, 0, 17 ++ vperm 17, 11, 12, 17 ++ vperm 18, 11, 12, 18 ++ ++ vand 20, 14, 25 # a0 ++ vand 9, 17, 25 # a0 ++ vsrd 21, 14, 31 # >> 26 ++ vsrd 22, 21, 31 # 12 bits left ++ vsrd 10, 17, 31 # >> 26 ++ vsrd 11, 10, 31 # 12 bits left ++ ++ vand 21, 21, 25 # a1 ++ vand 10, 10, 25 # a1 ++ ++ vspltisb 13, 12 ++ vand 16, 15, 25 ++ vsld 23, 16, 13 ++ vor 22, 22, 23 ++ vand 22, 22, 25 # a2 ++ vand 16, 18, 25 ++ vsld 12, 16, 13 ++ vor 11, 11, 12 ++ vand 11, 11, 25 # a2 ++ vspltisb 13, 14 ++ vsrd 23, 15, 13 # >> 14 ++ vsrd 24, 23, 31 # >> 26, a4 ++ vand 23, 23, 25 # a3 ++ vsrd 12, 18, 13 # >> 14 ++ vsrd 13, 12, 31 # >> 26, a4 ++ vand 12, 12, 25 # a3 ++ ++ vaddudm 4, 4, 20 ++ vaddudm 5, 5, 21 ++ vaddudm 6, 6, 22 ++ vaddudm 7, 7, 23 ++ vaddudm 8, 8, 24 ++ ++ # Smash 4 message blocks into 5 vectors of [m4, m2, m3, m1] ++ vmrgow 4, 9, 4 ++ vmrgow 5, 10, 5 ++ vmrgow 6, 11, 6 ++ vmrgow 7, 12, 7 ++ vmrgow 8, 13, 8 ++ vaddudm 8, 8, 19 ++ ++ addi 5, 5, -64 ++ addi 21, 21, 64 ++ ++ bdnz loop_4blocks ++ ++ xxlor 58, 0, 0 ++ xxlor 59, 1, 1 ++ xxlor 60, 2, 2 ++ xxlor 61, 3, 3 ++ xxlor 62, 4, 4 ++ xxlor 32, 5, 5 ++ xxlor 33, 6, 6 ++ xxlor 34, 7, 7 ++ xxlor 35, 8, 8 ++ ++ # Multiply odd words and even words ++ mul_odd ++ mul_even ++ ++ # Sum the products. ++ xxpermdi 41, 31, 46, 0 ++ xxpermdi 42, 31, 47, 0 ++ vaddudm 4, 14, 9 ++ xxpermdi 36, 31, 36, 3 ++ vaddudm 5, 15, 10 ++ xxpermdi 37, 31, 37, 3 ++ xxpermdi 43, 31, 48, 0 ++ vaddudm 6, 16, 11 ++ xxpermdi 38, 31, 38, 3 ++ xxpermdi 44, 31, 49, 0 ++ vaddudm 7, 17, 12 ++ xxpermdi 39, 31, 39, 3 ++ xxpermdi 45, 31, 50, 0 ++ vaddudm 8, 18, 13 ++ xxpermdi 40, 31, 40, 3 ++ ++ # carry reduction ++ vspltisb 9, 2 ++ vsrd 10, 4, 31 ++ vsrd 11, 7, 31 ++ vand 7, 7, 25 ++ vand 4, 4, 25 ++ vaddudm 8, 8, 11 ++ vsrd 12, 8, 31 ++ vaddudm 5, 5, 10 ++ ++ vsrd 11, 5, 31 ++ vand 8, 8, 25 ++ vand 5, 5, 25 ++ vaddudm 4, 4, 12 ++ vsld 10, 12, 9 ++ vaddudm 6, 6, 11 ++ ++ vsrd 13, 6, 31 ++ vand 6, 6, 25 ++ vaddudm 4, 4, 10 ++ vsrd 10, 4, 31 ++ vaddudm 7, 7, 13 ++ ++ vsrd 11, 7, 31 ++ vand 7, 7, 25 ++ vand 4, 4, 25 ++ vaddudm 5, 5, 10 ++ vaddudm 8, 8, 11 ++ ++ b do_final_update ++ ++do_final_update: ++ # v4, v5, v6, v7 and v8 are 26 bit vectors ++ vsld 5, 5, 31 ++ vor 20, 4, 5 ++ vspltisb 11, 12 ++ vsrd 12, 6, 11 ++ vsld 6, 6, 31 ++ vsld 6, 6, 31 ++ vor 20, 20, 6 ++ vspltisb 11, 14 ++ vsld 7, 7, 11 ++ vor 21, 7, 12 ++ mfvsrld 16, 40 # save last 2 bytes ++ vsld 8, 8, 11 ++ vsld 8, 8, 31 ++ vor 21, 21, 8 ++ mfvsrld 17, 52 ++ mfvsrld 19, 53 ++ srdi 16, 16, 24 ++ ++ std 17, 32(3) ++ std 19, 40(3) ++ stw 16, 48(3) ++ ++Out_loop: ++ li 3, 0 ++ ++ li 14, 256 ++ lvx 20, 14, 1 ++ addi 14, 14, 16 ++ lvx 21, 14, 1 ++ addi 14, 14, 16 ++ lvx 22, 14, 1 ++ addi 14, 14, 16 ++ lvx 23, 14, 1 ++ addi 14, 14, 16 ++ lvx 24, 14, 1 ++ addi 14, 14, 16 ++ lvx 25, 14, 1 ++ addi 14, 14, 16 ++ lvx 26, 14, 1 ++ addi 14, 14, 16 ++ lvx 27, 14, 1 ++ addi 14, 14, 16 ++ lvx 28, 14, 1 ++ addi 14, 14, 16 ++ lvx 29, 14, 1 ++ addi 14, 14, 16 ++ lvx 30, 14, 1 ++ addi 14, 14, 16 ++ lvx 31, 14, 1 ++ ++ addi 14, 14, 16 ++ lxvx 14, 14, 1 ++ addi 14, 14, 16 ++ lxvx 15, 14, 1 ++ addi 14, 14, 16 ++ lxvx 16, 14, 1 ++ addi 14, 14, 16 ++ lxvx 17, 14, 1 ++ addi 14, 14, 16 ++ lxvx 18, 14, 1 ++ addi 14, 14, 16 ++ lxvx 19, 14, 1 ++ addi 14, 14, 16 ++ lxvx 20, 14, 1 ++ addi 14, 14, 16 ++ lxvx 21, 14, 1 ++ addi 14, 14, 16 ++ lxvx 22, 14, 1 ++ addi 14, 14, 16 ++ lxvx 23, 14, 1 ++ addi 14, 14, 16 ++ lxvx 24, 14, 1 ++ addi 14, 14, 16 ++ lxvx 25, 14, 1 ++ addi 14, 14, 16 ++ lxvx 26, 14, 1 ++ addi 14, 14, 16 ++ lxvx 27, 14, 1 ++ addi 14, 14, 16 ++ lxvx 28, 14, 1 ++ addi 14, 14, 16 ++ lxvx 29, 14, 1 ++ addi 14, 14, 16 ++ lxvx 30, 14, 1 ++ addi 14, 14, 16 ++ lxvx 31, 14, 1 ++ ++ ld 0, 1040(1) ++ ld 14,112(1) ++ ld 15,120(1) ++ ld 16,128(1) ++ ld 17,136(1) ++ ld 18,144(1) ++ ld 19,152(1) ++ ld 20,160(1) ++ ld 21,168(1) ++ ld 31,248(1) ++ ++ mtlr 0 ++ addi 1, 1, 1024 ++ blr ++ ++Out_no_poly1305: ++ li 3, 0 ++ blr ++ ++.data ++.align 5 ++rmask: ++.byte 0xff, 0xff, 0xff, 0x0f, 0xfc, 0xff, 0xff, 0x0f, 0xfc, 0xff, 0xff, 0x0f, 0xfc, 0xff, 0xff, 0x0f ++cnum: ++.long 0x03ffffff, 0x00000000, 0x03ffffff, 0x00000000 ++.long 0x1a, 0x00, 0x1a, 0x00 ++.long 0x01000000, 0x01000000, 0x01000000, 0x01000000 ++.long 0x00010203, 0x04050607, 0x10111213, 0x14151617 ++.long 0x08090a0b, 0x0c0d0e0f, 0x18191a1b, 0x1c1d1e1f ++.long 0x05, 0x00, 0x00, 0x00 ++.long 0x02020202, 0x02020202, 0x02020202, 0x02020202 ++.long 0xffffffff, 0xffffffff, 0x00000000, 0x00000000 +Index: libgcrypt-1.10.2/cipher/poly1305.c +=================================================================== +--- libgcrypt-1.10.2.orig/cipher/poly1305.c ++++ libgcrypt-1.10.2/cipher/poly1305.c +@@ -78,11 +78,23 @@ poly1305_blocks (poly1305_context_t *ctx + #endif /* USE_S390X_ASM */ + + ++#ifdef POLY1305_USE_PPC_VEC ++ ++extern unsigned int ++gcry_poly1305_p10le_4blocks(unsigned char *key, const byte *m, size_t len); ++ ++#endif /* POLY1305_USE_PPC_VEC */ ++ ++ + static void poly1305_init (poly1305_context_t *ctx, + const byte key[POLY1305_KEYLEN]) + { + POLY1305_STATE *st = &ctx->state; + ++#ifdef POLY1305_USE_PPC_VEC ++ ctx->use_p10 = (_gcry_get_hw_features () & HWF_PPC_ARCH_3_10) != 0; ++#endif ++ + ctx->leftover = 0; + + st->h[0] = 0; +@@ -533,6 +545,7 @@ _gcry_poly1305_update_burn (poly1305_con + size_t bytes) + { + unsigned int burn = 0; ++ unsigned int nburn; + + /* handle leftover */ + if (ctx->leftover) +@@ -546,15 +559,31 @@ _gcry_poly1305_update_burn (poly1305_con + ctx->leftover += want; + if (ctx->leftover < POLY1305_BLOCKSIZE) + return 0; +- burn = poly1305_blocks (ctx, ctx->buffer, POLY1305_BLOCKSIZE, 1); ++ nburn = poly1305_blocks (ctx, ctx->buffer, POLY1305_BLOCKSIZE, 1); ++ burn = nburn > burn ? nburn : burn; + ctx->leftover = 0; + } + ++#ifdef POLY1305_USE_PPC_VEC ++ /* PPC-P10/little-endian: bulk process multiples of eight blocks */ ++ if (ctx->use_p10 && bytes >= POLY1305_BLOCKSIZE * 8) ++ { ++ size_t nblks = bytes / (POLY1305_BLOCKSIZE * 8); ++ size_t len = nblks * (POLY1305_BLOCKSIZE * 8); ++ POLY1305_STATE *st = &ctx->state; ++ nburn = gcry_poly1305_p10le_4blocks ((unsigned char *) st, m, len); ++ burn = nburn > burn ? nburn : burn; ++ m += len; ++ bytes -= len; ++ } ++#endif /* POLY1305_USE_PPC_VEC */ ++ + /* process full blocks */ + if (bytes >= POLY1305_BLOCKSIZE) + { + size_t nblks = bytes / POLY1305_BLOCKSIZE; +- burn = poly1305_blocks (ctx, m, nblks * POLY1305_BLOCKSIZE, 1); ++ nburn = poly1305_blocks (ctx, m, nblks * POLY1305_BLOCKSIZE, 1); ++ burn = nburn > burn ? nburn : burn; + m += nblks * POLY1305_BLOCKSIZE; + bytes -= nblks * POLY1305_BLOCKSIZE; + } +Index: libgcrypt-1.10.2/configure.ac +=================================================================== +--- libgcrypt-1.10.2.orig/configure.ac ++++ libgcrypt-1.10.2/configure.ac +@@ -2779,6 +2779,11 @@ if test "$found" = "1" ; then + powerpc64le-*-*) + # Build with the ppc8 vector implementation + GCRYPT_ASM_CIPHERS="$GCRYPT_ASM_CIPHERS chacha20-ppc.lo" ++ # Build with the assembly implementation ++ if test "$gcry_cv_gcc_inline_asm_ppc_altivec" = "yes" && ++ test "$gcry_cv_gcc_inline_asm_ppc_arch_3_00" = "yes" ; then ++ GCRYPT_ASM_CIPHERS="$GCRYPT_ASM_CIPHERS chacha20-p10le-8x.lo" ++ fi + ;; + powerpc64-*-*) + # Build with the ppc8 vector implementation +@@ -3117,6 +3122,13 @@ case "${host}" in + s390x-*-*) + GCRYPT_ASM_DIGESTS="$GCRYPT_ASM_DIGESTS poly1305-s390x.lo" + ;; ++ powerpc64le-*-*) ++ # Build with the assembly implementation ++ if test "$gcry_cv_gcc_inline_asm_ppc_altivec" = "yes" && ++ test "$gcry_cv_gcc_inline_asm_ppc_arch_3_00" = "yes" ; then ++ GCRYPT_ASM_DIGESTS="$GCRYPT_ASM_DIGESTS poly1305-p10le.lo" ++ fi ++ ;; + esac + + LIST_MEMBER(scrypt, $enabled_kdfs) diff --git a/libgcrypt-Disable-SHA3-s390x-acceleration-for-CSHAKE.patch b/libgcrypt-Disable-SHA3-s390x-acceleration-for-CSHAKE.patch new file mode 100644 index 0000000..ee40bc2 --- /dev/null +++ b/libgcrypt-Disable-SHA3-s390x-acceleration-for-CSHAKE.patch @@ -0,0 +1,61 @@ +From 2486d9b5ae015c1786cb84466a751da4bc0d7122 Mon Sep 17 00:00:00 2001 +From: Jussi Kivilinna +Date: Thu, 20 Jun 2024 20:10:09 +0300 +Subject: Disable SHA3 s390x acceleration for CSHAKE + +* cipher/keccak.c (keccak_final_s390x): Add assert check for +expected SHAKE suffix. +(_gcry_cshake_customize, cshake_hash_buffers): Disable s390x +acceleration when selecting CSHAKE suffix. +-- + +Signed-off-by: Jussi Kivilinna + +diff --git a/cipher/keccak.c b/cipher/keccak.c +index aaf83a62..44cc9f71 100644 +--- a/cipher/keccak.c ++++ b/cipher/keccak.c +@@ -745,6 +745,8 @@ keccak_final_s390x (void *context) + } + else + { ++ gcry_assert(ctx->suffix == SHAKE_DELIMITED_SUFFIX); ++ + klmd_shake_execute (ctx->kimd_func, &ctx->state, NULL, 0, ctx->buf, + ctx->count); + ctx->count = 0; +@@ -1497,9 +1499,14 @@ _gcry_cshake_customize (void *context, struct gcry_cshake_customization *p) + /* No customization */ + return 0; + ++ ctx->suffix = CSHAKE_DELIMITED_SUFFIX; ++#ifdef USE_S390X_CRYPTO ++ /* CSHAKE suffix is not supported by s390x/kimd. */ ++ ctx->kimd_func = 0; ++#endif ++ + len_written = cshake_input_n (ctx, p->n, p->n_len); + cshake_input_s (ctx, p->s, p->s_len, len_written); +- ctx->suffix = CSHAKE_DELIMITED_SUFFIX; + return 0; + } + +@@ -1536,9 +1543,14 @@ cshake_hash_buffers (const gcry_md_spec_t *spec, void *outbuf, size_t nbytes, + size_t s_len = iov[1].len; + size_t len; + ++ ctx.suffix = CSHAKE_DELIMITED_SUFFIX; ++#ifdef USE_S390X_CRYPTO ++ /* CSHAKE suffix is not supported by s390x/kimd. */ ++ ctx.kimd_func = 0; ++#endif ++ + len = cshake_input_n (&ctx, n, n_len); + cshake_input_s (&ctx, s, s_len, len); +- ctx.suffix = CSHAKE_DELIMITED_SUFFIX; + } + iovcnt -= 2; + iov += 2; +-- +2.49.0 + diff --git a/libgcrypt-FIPS-SLI-hash-mac.patch b/libgcrypt-FIPS-SLI-hash-mac.patch new file mode 100644 index 0000000..ff03fae --- /dev/null +++ b/libgcrypt-FIPS-SLI-hash-mac.patch @@ -0,0 +1,172 @@ +Index: libgcrypt-1.11.1/doc/gcrypt.texi +=================================================================== +--- libgcrypt-1.11.1.orig/doc/gcrypt.texi ++++ libgcrypt-1.11.1/doc/gcrypt.texi +@@ -998,13 +998,21 @@ certification. If the function is approv + @code{GPG_ERR_NO_ERROR} (other restrictions might still apply). + Otherwise @code{GPG_ERR_NOT_SUPPORTED} is returned. + +-@item GCRYCTL_FIPS_SERVICE_INDICATOR_MAC; Arguments: enum gcry_mac_algos ++@item GCRYCTL_FIPS_SERVICE_INDICATOR_HASH; Arguments: enum gcry_md_algos + +-Check if the given MAC is approved under the current FIPS 140-3 +-certification. If the MAC is approved, this function returns +-@code{GPG_ERR_NO_ERROR}. Otherwise @code{GPG_ERR_NOT_SUPPORTED} ++Check if the given HASH is approved under the current FIPS 140-3 ++certification. If the HASH is approved, this function returns ++@code{GPS_ERR_NO_ERROR}. Otherwise @code{GPG_ERR_NOT_SUPPORTED} + is returned. + ++@item GCRYCTL_FIPS_SERVICE_INDICATOR_MAC; Arguments: enum gcry_mac_algos [, unsigned int] ++ ++Check if the given MAC is approved under the current FIPS 140-3 ++certification. The second parameter provides the keylen (if the ++algorithm supports different key sizes). If the MAC is approved, ++this function returns @code{GPS_ERR_NO_ERROR}. Otherwise ++@code{GPG_ERR_NOT_SUPPORTED} is returned. ++ + @item GCRYCTL_FIPS_SERVICE_INDICATOR_MD; Arguments: enum gcry_md_algos + + Check if the given message digest algorithm is approved under the current +Index: libgcrypt-1.11.1/src/fips.c +=================================================================== +--- libgcrypt-1.11.1.orig/src/fips.c ++++ libgcrypt-1.11.1/src/fips.c +@@ -512,31 +512,6 @@ _gcry_fips_indicator_pk (va_list arg_ptr + } + + int +-_gcry_fips_indicator_mac (va_list arg_ptr) +-{ +- enum gcry_mac_algos alg = va_arg (arg_ptr, enum gcry_mac_algos); +- +- switch (alg) +- { +- case GCRY_MAC_CMAC_AES: +- case GCRY_MAC_HMAC_SHA1: +- case GCRY_MAC_HMAC_SHA224: +- case GCRY_MAC_HMAC_SHA256: +- case GCRY_MAC_HMAC_SHA384: +- case GCRY_MAC_HMAC_SHA512: +- case GCRY_MAC_HMAC_SHA512_224: +- case GCRY_MAC_HMAC_SHA512_256: +- case GCRY_MAC_HMAC_SHA3_224: +- case GCRY_MAC_HMAC_SHA3_256: +- case GCRY_MAC_HMAC_SHA3_384: +- case GCRY_MAC_HMAC_SHA3_512: +- return GPG_ERR_NO_ERROR; +- default: +- return GPG_ERR_NOT_SUPPORTED; +- } +-} +- +-int + _gcry_fips_indicator_md (va_list arg_ptr) + { + enum gcry_md_algos alg = va_arg (arg_ptr, enum gcry_md_algos); +@@ -647,6 +622,62 @@ _gcry_fips_indicator_pk_flags (va_list a + return GPG_ERR_NOT_SUPPORTED; + } + ++int ++_gcry_fips_indicator_hash (va_list arg_ptr) ++{ ++ enum gcry_md_algos alg = va_arg (arg_ptr, enum gcry_md_algos); ++ ++ switch (alg) ++ { ++ case GCRY_MD_SHA1: ++ case GCRY_MD_SHA224: ++ case GCRY_MD_SHA256: ++ case GCRY_MD_SHA384: ++ case GCRY_MD_SHA512: ++ case GCRY_MD_SHA512_224: ++ case GCRY_MD_SHA512_256: ++ case GCRY_MD_SHA3_224: ++ case GCRY_MD_SHA3_256: ++ case GCRY_MD_SHA3_384: ++ case GCRY_MD_SHA3_512: ++ case GCRY_MD_SHAKE128: ++ case GCRY_MD_SHAKE256: ++ return GPG_ERR_NO_ERROR; ++ default: ++ return GPG_ERR_NOT_SUPPORTED; ++ } ++} ++ ++int ++_gcry_fips_indicator_mac (va_list arg_ptr) ++{ ++ enum gcry_mac_algos alg = va_arg (arg_ptr, enum gcry_mac_algos); ++ unsigned int keylen = va_arg (arg_ptr, unsigned int); ++ ++ switch (alg) ++ { ++ case GCRY_MAC_HMAC_SHA1: ++ case GCRY_MAC_HMAC_SHA224: ++ case GCRY_MAC_HMAC_SHA256: ++ case GCRY_MAC_HMAC_SHA384: ++ case GCRY_MAC_HMAC_SHA512: ++ case GCRY_MAC_HMAC_SHA512_224: ++ case GCRY_MAC_HMAC_SHA512_256: ++ case GCRY_MAC_HMAC_SHA3_224: ++ case GCRY_MAC_HMAC_SHA3_256: ++ case GCRY_MAC_HMAC_SHA3_384: ++ case GCRY_MAC_HMAC_SHA3_512: ++ if (keylen >= 112) { ++ return GPG_ERR_NO_ERROR; ++ } ++ case GCRY_MAC_CMAC_AES: ++ if (keylen == 128 || keylen == 192 || keylen == 256) { ++ return GPG_ERR_NO_ERROR; ++ } ++ default: ++ return GPG_ERR_NOT_SUPPORTED; ++ } ++} + + /* This is a test on whether the library is in the error or + operational state. */ +Index: libgcrypt-1.11.1/src/g10lib.h +=================================================================== +--- libgcrypt-1.11.1.orig/src/g10lib.h ++++ libgcrypt-1.11.1/src/g10lib.h +@@ -478,6 +478,7 @@ void _gcry_fips_signal_error (const char + gpg_err_code_t _gcry_fips_indicator (void); + + int _gcry_fips_indicator_cipher (va_list arg_ptr); ++int _gcry_fips_indicator_hash (va_list arg_ptr); + int _gcry_fips_indicator_mac (va_list arg_ptr); + int _gcry_fips_indicator_md (va_list arg_ptr); + int _gcry_fips_indicator_kdf (va_list arg_ptr); +Index: libgcrypt-1.11.1/src/gcrypt.h.in +=================================================================== +--- libgcrypt-1.11.1.orig/src/gcrypt.h.in ++++ libgcrypt-1.11.1/src/gcrypt.h.in +@@ -338,7 +338,8 @@ enum gcry_ctl_cmds + GCRYCTL_MD_CUSTOMIZE = 88, + GCRYCTL_FIPS_SERVICE_INDICATOR = 89, + GCRYCTL_FIPS_REJECT_NON_FIPS = 90, +- GCRYCTL_FIPS_SERVICE_INDICATOR_PK = 91 ++ GCRYCTL_FIPS_SERVICE_INDICATOR_PK = 91, ++ GCRYCTL_FIPS_SERVICE_INDICATOR_HASH = 92 + }; + + /* Perform various operations defined by CMD. */ +Index: libgcrypt-1.11.1/src/global.c +=================================================================== +--- libgcrypt-1.11.1.orig/src/global.c ++++ libgcrypt-1.11.1/src/global.c +@@ -808,6 +808,12 @@ _gcry_vcontrol (enum gcry_ctl_cmds cmd, + rc = _gcry_fips_indicator_cipher (arg_ptr); + break; + ++ case GCRYCTL_FIPS_SERVICE_INDICATOR_HASH: ++ /* Get FIPS Service Indicator for a given HASH. Returns GPG_ERR_NO_ERROR ++ * if algorithm is allowed or GPG_ERR_NOT_SUPPORTED otherwise */ ++ rc = _gcry_fips_indicator_hash (arg_ptr); ++ break; ++ + case GCRYCTL_FIPS_SERVICE_INDICATOR_MAC: + /* Get FIPS Service Indicator for a given message authentication code. + * Returns GPG_ERR_NO_ERROR if algorithm is allowed or diff --git a/libgcrypt-FIPS-SLI-kdf-leylength.patch b/libgcrypt-FIPS-SLI-kdf-leylength.patch new file mode 100644 index 0000000..d3693ac --- /dev/null +++ b/libgcrypt-FIPS-SLI-kdf-leylength.patch @@ -0,0 +1,60 @@ +Index: libgcrypt-1.11.0/src/fips.c +=================================================================== +--- libgcrypt-1.11.0.orig/src/fips.c ++++ libgcrypt-1.11.0/src/fips.c +@@ -523,10 +523,15 @@ int + _gcry_fips_indicator_kdf (va_list arg_ptr) + { + enum gcry_kdf_algos alg = va_arg (arg_ptr, enum gcry_kdf_algos); ++ unsigned int keylen = 0; + + switch (alg) + { + case GCRY_KDF_PBKDF2: ++ keylen = va_arg (arg_ptr, unsigned int); ++ if (keylen < 112) { ++ return GPG_ERR_NOT_SUPPORTED; ++ } + return GPG_ERR_NO_ERROR; + default: + return GPG_ERR_NOT_SUPPORTED; +Index: libgcrypt-1.11.0/doc/gcrypt.texi +=================================================================== +--- libgcrypt-1.11.0.orig/doc/gcrypt.texi ++++ libgcrypt-1.11.0/doc/gcrypt.texi +@@ -983,12 +983,13 @@ is approved under the current FIPS 140-3 + combination is approved, this function returns @code{GPG_ERR_NO_ERROR}. + Otherwise @code{GPG_ERR_NOT_SUPPORTED} is returned. + +-@item GCRYCTL_FIPS_SERVICE_INDICATOR_KDF; Arguments: enum gcry_kdf_algos ++@item GCRYCTL_FIPS_SERVICE_INDICATOR_KDF; Arguments: enum gcry_kdf_algos [, unsigned int] + + Check if the given KDF is approved under the current FIPS 140-3 +-certification. If the KDF is approved, this function returns +-@code{GPG_ERR_NO_ERROR}. Otherwise @code{GPG_ERR_NOT_SUPPORTED} +-is returned. ++certification. The second parameter provides the keylength in bits. ++Keylength values of less that 112 bits are considered non-approved. ++If the KDF is approved, this function returns @code{GPG_ERR_NO_ERROR}. ++Otherwise @code{GPG_ERR_NOT_SUPPORTED} is returned. + + @item GCRYCTL_FIPS_SERVICE_INDICATOR_FUNCTION; Arguments: const char * + +Index: libgcrypt-1.11.0/tests/t-kdf.c +=================================================================== +--- libgcrypt-1.11.0.orig/tests/t-kdf.c ++++ libgcrypt-1.11.0/tests/t-kdf.c +@@ -1889,7 +1889,12 @@ check_fips_indicators (void) + for (i = 0; i < sizeof(kdf_algos) / sizeof(*kdf_algos); i++) + { + int is_fips_kdf_algo = 0; +- gcry_error_t err = gcry_control (GCRYCTL_FIPS_SERVICE_INDICATOR_KDF, kdf_algos[i]); ++ gcry_error_t err; ++ // On SUSE/openSUSE builds PBKDF2 with keysize < 112 is not allowed ++ if (kdf_algos[i] == GCRY_KDF_PBKDF2) ++ err = gcry_control (GCRYCTL_FIPS_SERVICE_INDICATOR_KDF, kdf_algos[i], 112); ++ else ++ err = gcry_control (GCRYCTL_FIPS_SERVICE_INDICATOR_KDF, kdf_algos[i]); + + if (verbose) + fprintf (stderr, "checking FIPS indicator for KDF %d: %s\n", diff --git a/libgcrypt-FIPS-SLI-pk.patch b/libgcrypt-FIPS-SLI-pk.patch new file mode 100644 index 0000000..4dd3d97 --- /dev/null +++ b/libgcrypt-FIPS-SLI-pk.patch @@ -0,0 +1,177 @@ +Index: libgcrypt-1.11.1/src/fips.c +=================================================================== +--- libgcrypt-1.11.1.orig/src/fips.c ++++ libgcrypt-1.11.1/src/fips.c +@@ -38,6 +38,7 @@ + + #include "g10lib.h" + #include "cipher-proto.h" ++#include "cipher.h" + #include "../random/random.h" + + /* The states of the finite state machine used in fips mode. */ +@@ -420,6 +421,94 @@ _gcry_fips_indicator_cipher (va_list arg + default: + return GPG_ERR_NOT_SUPPORTED; + } ++} ++ ++/* FIPS approved curves, extracted from: ++ * cipher/ecc-curves.c:curve_aliases[] and domain_parms[]. */ ++static const struct ++{ ++ const char *name; /* Our name. */ ++ const char *other; /* Other name. */ ++} fips_approved_curve[] = ++ { ++ /* "NIST P-192" is non-approved if FIPS 140-3 */ ++ /* { "NIST P-192", "1.2.840.10045.3.1.1" }, /\* X9.62 OID *\/ */ ++ /* { "NIST P-192", "prime192v1" }, /\* X9.62 name. *\/ */ ++ /* { "NIST P-192", "secp192r1" }, /\* SECP name. *\/ */ ++ /* { "NIST P-192", "nistp192" }, /\* rfc5656. *\/ */ ++ ++ { "NIST P-224", "secp224r1" }, ++ { "NIST P-224", "1.3.132.0.33" }, /* SECP OID. */ ++ { "NIST P-224", "nistp224" }, /* rfc5656. */ ++ ++ { "NIST P-256", "1.2.840.10045.3.1.7" }, /* From NIST SP 800-78-1. */ ++ { "NIST P-256", "prime256v1" }, ++ { "NIST P-256", "secp256r1" }, ++ { "NIST P-256", "nistp256" }, /* rfc5656. */ ++ ++ { "NIST P-384", "secp384r1" }, ++ { "NIST P-384", "1.3.132.0.34" }, ++ { "NIST P-384", "nistp384" }, /* rfc5656. */ ++ ++ { "NIST P-521", "secp521r1" }, ++ { "NIST P-521", "1.3.132.0.35" }, ++ { "NIST P-521", "nistp521" }, /* rfc5656. */ ++ { NULL, NULL} ++ }; ++ ++enum pk_operation convert_from_pk_usage(unsigned int pk_usage) ++{ ++ switch (pk_usage) ++ { ++ case GCRY_PK_USAGE_SIGN: ++ return PUBKEY_OP_SIGN; ++ case GCRY_PK_USAGE_ENCR: ++ return PUBKEY_OP_ENCRYPT; ++ default: ++ return PUBKEY_OP_DECRYPT; ++ } ++} ++ ++int ++_gcry_fips_indicator_pk (va_list arg_ptr) ++{ ++ enum gcry_pk_algos alg = va_arg (arg_ptr, enum gcry_pk_algos); ++ enum pk_operation oper; ++ unsigned int keylen; ++ const char *curve_name; ++ ++ switch (alg) ++ { ++ case GCRY_PK_RSA: ++ case GCRY_PK_RSA_E: ++ case GCRY_PK_RSA_S: ++ oper = convert_from_pk_usage(va_arg (arg_ptr, unsigned int)); ++ switch (oper) ++ { ++ case PUBKEY_OP_ENCRYPT: ++ case PUBKEY_OP_DECRYPT: ++ return GPG_ERR_NOT_SUPPORTED; ++ default: ++ keylen = va_arg (arg_ptr, unsigned int); ++ if (keylen < 2048) ++ return GPG_ERR_NOT_SUPPORTED; ++ return GPG_ERR_NO_ERROR; ++ } ++ case GCRY_PK_ECC: ++ case GCRY_PK_ECDH: ++ case GCRY_PK_ECDSA: ++ curve_name = va_arg (arg_ptr, const char *); ++ for (int idx = 0; fips_approved_curve[idx].name; ++idx) ++ { ++ /* Check for the usual name and an alias. */ ++ if (!strcmp (curve_name, fips_approved_curve[idx].name) || ++ !strcmp (curve_name, fips_approved_curve[idx].other)) ++ return GPG_ERR_NO_ERROR; ++ } ++ return GPG_ERR_NOT_SUPPORTED; ++ default: ++ return GPG_ERR_NOT_SUPPORTED; ++ } + } + + int +Index: libgcrypt-1.11.1/src/gcrypt.h.in +=================================================================== +--- libgcrypt-1.11.1.orig/src/gcrypt.h.in ++++ libgcrypt-1.11.1/src/gcrypt.h.in +@@ -337,7 +337,8 @@ enum gcry_ctl_cmds + GCRYCTL_FIPS_SERVICE_INDICATOR_PK_FLAGS = 87, + GCRYCTL_MD_CUSTOMIZE = 88, + GCRYCTL_FIPS_SERVICE_INDICATOR = 89, +- GCRYCTL_FIPS_REJECT_NON_FIPS = 90 ++ GCRYCTL_FIPS_REJECT_NON_FIPS = 90, ++ GCRYCTL_FIPS_SERVICE_INDICATOR_PK = 91 + }; + + /* Perform various operations defined by CMD. */ +Index: libgcrypt-1.11.1/doc/gcrypt.texi +=================================================================== +--- libgcrypt-1.11.1.orig/doc/gcrypt.texi ++++ libgcrypt-1.11.1/doc/gcrypt.texi +@@ -1010,6 +1010,19 @@ Check if the given message digest algori + FIPS 140-3 certification. If the algorithm is approved, this function returns + @code{GPG_ERR_NO_ERROR}. Otherwise @code{GPG_ERR_NOT_SUPPORTED} is returned. + ++@item GCRYCTL_FIPS_SERVICE_INDICATOR_PK; Arguments: enum gcry_pk_algos [, constantsGCRY_PK_USAGE_ENCR or GCRY_PK_USAGE_SIGN, unsigned int (only for GCRY_PK_RSA)] [, const char * (only for GCRY_PK_ECC, GCRY_PK_ECDH or GCRY_PK_ECDSA)] ++ ++Check if the given asymmetric cipher is approved under the current ++FIPS 140-3 certification. For GCRY_PK_RSA, two additional parameter ++are required: first describes the purpose of the algorithm through one ++of the constants (GCRY_PK_USAGE_ENCR for encryption or decryption ++operations; GCRY_PK_USAGE_SIGN for sign or verify operations). Second ++one is the key length. For GCRY_PK_ECC, GCRY_PK_ECDH and ++GCRY_PK_ECDSA, only a single parameter is needed: the curve name or ++its alias as @code{const char *}. If the combination is approved, this ++function returns @code{GPG_ERR_NO_ERROR}. Otherwise ++@code{GPG_ERR_NOT_SUPPORTED} is returned. ++ + @item GCRYCTL_FIPS_SERVICE_INDICATOR_PK_FLAGS; Arguments: const char * + + Check if the given public key operation flag or s-expression object name is +Index: libgcrypt-1.11.1/src/g10lib.h +=================================================================== +--- libgcrypt-1.11.1.orig/src/g10lib.h ++++ libgcrypt-1.11.1/src/g10lib.h +@@ -482,6 +482,7 @@ int _gcry_fips_indicator_mac (va_list ar + int _gcry_fips_indicator_md (va_list arg_ptr); + int _gcry_fips_indicator_kdf (va_list arg_ptr); + int _gcry_fips_indicator_function (va_list arg_ptr); ++int _gcry_fips_indicator_pk (va_list arg_ptr); + int _gcry_fips_indicator_pk_flags (va_list arg_ptr); + + int _gcry_fips_is_operational (void); +Index: libgcrypt-1.11.1/src/global.c +=================================================================== +--- libgcrypt-1.11.1.orig/src/global.c ++++ libgcrypt-1.11.1/src/global.c +@@ -842,6 +842,15 @@ _gcry_vcontrol (enum gcry_ctl_cmds cmd, + rc = _gcry_fips_indicator_pk_flags (arg_ptr); + break; + ++ case GCRYCTL_FIPS_SERVICE_INDICATOR_PK: ++ /* Get FIPS Service Indicator for a given asymmetric algorithm. For ++ * GCRY_PK_RSA, an additional parameter for the operation mode is ++ * required. For ECC, ECDH and ECDSA, the additional parameter is the ++ * curve name or its alias. Returns GPG_ERR_NO_ERROR if the ++ * algorithm is allowed or GPG_ERR_NOT_SUPPORTED otherwise. */ ++ rc = _gcry_fips_indicator_pk (arg_ptr); ++ break; ++ + case PRIV_CTL_INIT_EXTRNG_TEST: /* Init external random test. */ + rc = GPG_ERR_NOT_SUPPORTED; + break; diff --git a/libgcrypt-FIPS-jitter-errorcodes.patch b/libgcrypt-FIPS-jitter-errorcodes.patch new file mode 100644 index 0000000..d6d314e --- /dev/null +++ b/libgcrypt-FIPS-jitter-errorcodes.patch @@ -0,0 +1,16 @@ +Index: libgcrypt-1.10.3/random/rndjent.c +=================================================================== +--- libgcrypt-1.10.3.orig/random/rndjent.c ++++ libgcrypt-1.10.3/random/rndjent.c +@@ -319,7 +319,10 @@ _gcry_rndjent_poll (void (*add)(const vo + jent_rng_totalcalls++; + rc = jent_read_entropy_safe (&jent_rng_collector, buffer, n); + if (rc < 0) +- break; ++ { ++ fips_signal_error ("jitter entropy failed"); ++ break; ++ } + /* We need to hash the output to conform to the BSI + * NTG.1 specs. */ + _gcry_md_hash_buffer (GCRY_MD_SHA256, buffer, buffer, rc); diff --git a/libgcrypt-FIPS-jitter-standalone.patch b/libgcrypt-FIPS-jitter-standalone.patch new file mode 100644 index 0000000..fb375fa --- /dev/null +++ b/libgcrypt-FIPS-jitter-standalone.patch @@ -0,0 +1,183 @@ +Index: libgcrypt-1.11.1/random/Makefile.am +=================================================================== +--- libgcrypt-1.11.1.orig/random/Makefile.am ++++ libgcrypt-1.11.1/random/Makefile.am +@@ -21,7 +21,7 @@ + # Need to include ../src in addition to top_srcdir because gcrypt.h is + # a built header. + AM_CPPFLAGS = -I../src -I$(top_srcdir)/src +-AM_CFLAGS = $(GPG_ERROR_CFLAGS) ++AM_CFLAGS = $(GPG_ERROR_CFLAGS) -ljitterentropy + + noinst_LTLIBRARIES = librandom.la + +@@ -44,14 +44,7 @@ rndgetentropy.c \ + rndoldlinux.c \ + rndegd.c \ + rndunix.c \ +-rndw32.c \ +-jitterentropy-gcd.c jitterentropy-gcd.h \ +-jitterentropy-health.c jitterentropy-health.h \ +-jitterentropy-noise.c jitterentropy-noise.h \ +-jitterentropy-sha3.c jitterentropy-sha3.h \ +-jitterentropy-timer.c jitterentropy-timer.h \ +-jitterentropy-base.h \ +-jitterentropy-base.c jitterentropy.h jitterentropy-base-user.h ++rndw32.c + + # The rndjent module needs to be compiled without optimization. */ + if ENABLE_O_FLAG_MUNGING +@@ -60,20 +53,8 @@ else + o_flag_munging = cat + endif + +-rndjent.o: $(srcdir)/rndjent.c jitterentropy-base-user.h \ +- $(srcdir)/jitterentropy-gcd.c $(srcdir)/jitterentropy-gcd.h \ +- $(srcdir)/jitterentropy-health.c $(srcdir)/jitterentropy-health.h \ +- $(srcdir)/jitterentropy-noise.c $(srcdir)/jitterentropy-noise.h \ +- $(srcdir)/jitterentropy-sha3.c $(srcdir)/jitterentropy-sha3.h \ +- $(srcdir)/jitterentropy-timer.c $(srcdir)/jitterentropy-timer.h \ +- $(srcdir)/jitterentropy-base.c $(srcdir)/jitterentropy.h ++rndjent.o: $(srcdir)/rndjent.c + `echo $(COMPILE) -c $(srcdir)/rndjent.c | $(o_flag_munging) ` + +-rndjent.lo: $(srcdir)/rndjent.c jitterentropy-base-user.h \ +- $(srcdir)/jitterentropy-gcd.c $(srcdir)/jitterentropy-gcd.h \ +- $(srcdir)/jitterentropy-health.c $(srcdir)/jitterentropy-health.h \ +- $(srcdir)/jitterentropy-noise.c $(srcdir)/jitterentropy-noise.h \ +- $(srcdir)/jitterentropy-sha3.c $(srcdir)/jitterentropy-sha3.h \ +- $(srcdir)/jitterentropy-timer.c $(srcdir)/jitterentropy-timer.h \ +- $(srcdir)/jitterentropy-base.c $(srcdir)/jitterentropy.h ++rndjent.lo: $(srcdir)/rndjent.c + `echo $(LTCOMPILE) -c $(srcdir)/rndjent.c | $(o_flag_munging) ` +Index: libgcrypt-1.11.1/random/rndjent.c +=================================================================== +--- libgcrypt-1.11.1.orig/random/rndjent.c ++++ libgcrypt-1.11.1/random/rndjent.c +@@ -94,17 +94,12 @@ + * jitterentropy-user-base.h file. */ + + /* Tell jitterentropy* that all functions shall be static. */ +-#define JENT_PRIVATE_COMPILE 1 ++#undef JENT_PRIVATE_COMPILE + +-#include "jitterentropy-base.c" + #ifdef JENT_CONF_ENABLE_INTERNAL_TIMER + #include + #endif /* JENT_CONF_ENABLE_INTERNAL_TIMER */ +-#include "jitterentropy-gcd.c" +-#include "jitterentropy-health.c" +-#include "jitterentropy-noise.c" +-#include "jitterentropy-sha3.c" +-#include "jitterentropy-timer.c" ++#include + + /* This is the lock we use to serialize access to this RNG. The extra + * integer variable is only used to check the locking state; that is, +Index: libgcrypt-1.11.1/random/Makefile.in +=================================================================== +--- libgcrypt-1.11.1.orig/random/Makefile.in ++++ libgcrypt-1.11.1/random/Makefile.in +@@ -147,12 +147,7 @@ am__v_at_1 = + DEFAULT_INCLUDES = -I.@am__isrc@ -I$(top_builddir) + depcomp = $(SHELL) $(top_srcdir)/build-aux/depcomp + am__maybe_remake_depfiles = depfiles +-am__depfiles_remade = ./$(DEPDIR)/jitterentropy-base.Plo \ +- ./$(DEPDIR)/jitterentropy-gcd.Plo \ +- ./$(DEPDIR)/jitterentropy-health.Plo \ +- ./$(DEPDIR)/jitterentropy-noise.Plo \ +- ./$(DEPDIR)/jitterentropy-sha3.Plo \ +- ./$(DEPDIR)/jitterentropy-timer.Plo \ ++am__depfiles_remade = \ + ./$(DEPDIR)/random-csprng.Plo ./$(DEPDIR)/random-drbg.Plo \ + ./$(DEPDIR)/random-system.Plo ./$(DEPDIR)/random.Plo \ + ./$(DEPDIR)/rndegd.Plo ./$(DEPDIR)/rndgetentropy.Plo \ +@@ -375,7 +370,7 @@ top_srcdir = @top_srcdir@ + # Need to include ../src in addition to top_srcdir because gcrypt.h is + # a built header. + AM_CPPFLAGS = -I../src -I$(top_srcdir)/src +-AM_CFLAGS = $(GPG_ERROR_CFLAGS) ++AM_CFLAGS = $(GPG_ERROR_CFLAGS) -ljitterentropy + noinst_LTLIBRARIES = librandom.la + GCRYPT_MODULES = @GCRYPT_RANDOM@ + librandom_la_DEPENDENCIES = $(GCRYPT_MODULES) +@@ -394,14 +389,7 @@ rndgetentropy.c \ + rndoldlinux.c \ + rndegd.c \ + rndunix.c \ +-rndw32.c \ +-jitterentropy-gcd.c jitterentropy-gcd.h \ +-jitterentropy-health.c jitterentropy-health.h \ +-jitterentropy-noise.c jitterentropy-noise.h \ +-jitterentropy-sha3.c jitterentropy-sha3.h \ +-jitterentropy-timer.c jitterentropy-timer.h \ +-jitterentropy-base.h \ +-jitterentropy-base.c jitterentropy.h jitterentropy-base-user.h ++rndw32.c + + @ENABLE_O_FLAG_MUNGING_FALSE@o_flag_munging = cat + +@@ -461,12 +449,6 @@ mostlyclean-compile: + distclean-compile: + -rm -f *.tab.c + +-@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/jitterentropy-base.Plo@am__quote@ # am--include-marker +-@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/jitterentropy-gcd.Plo@am__quote@ # am--include-marker +-@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/jitterentropy-health.Plo@am__quote@ # am--include-marker +-@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/jitterentropy-noise.Plo@am__quote@ # am--include-marker +-@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/jitterentropy-sha3.Plo@am__quote@ # am--include-marker +-@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/jitterentropy-timer.Plo@am__quote@ # am--include-marker + @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/random-csprng.Plo@am__quote@ # am--include-marker + @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/random-drbg.Plo@am__quote@ # am--include-marker + @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/random-system.Plo@am__quote@ # am--include-marker +@@ -636,12 +618,6 @@ clean-am: clean-generic clean-libtool cl + mostlyclean-am + + distclean: distclean-am +- -rm -f ./$(DEPDIR)/jitterentropy-base.Plo +- -rm -f ./$(DEPDIR)/jitterentropy-gcd.Plo +- -rm -f ./$(DEPDIR)/jitterentropy-health.Plo +- -rm -f ./$(DEPDIR)/jitterentropy-noise.Plo +- -rm -f ./$(DEPDIR)/jitterentropy-sha3.Plo +- -rm -f ./$(DEPDIR)/jitterentropy-timer.Plo + -rm -f ./$(DEPDIR)/random-csprng.Plo + -rm -f ./$(DEPDIR)/random-drbg.Plo + -rm -f ./$(DEPDIR)/random-system.Plo +@@ -698,12 +674,6 @@ install-ps-am: + installcheck-am: + + maintainer-clean: maintainer-clean-am +- -rm -f ./$(DEPDIR)/jitterentropy-base.Plo +- -rm -f ./$(DEPDIR)/jitterentropy-gcd.Plo +- -rm -f ./$(DEPDIR)/jitterentropy-health.Plo +- -rm -f ./$(DEPDIR)/jitterentropy-noise.Plo +- -rm -f ./$(DEPDIR)/jitterentropy-sha3.Plo +- -rm -f ./$(DEPDIR)/jitterentropy-timer.Plo + -rm -f ./$(DEPDIR)/random-csprng.Plo + -rm -f ./$(DEPDIR)/random-drbg.Plo + -rm -f ./$(DEPDIR)/random-system.Plo +@@ -752,22 +722,10 @@ uninstall-am: + .PRECIOUS: Makefile + + +-rndjent.o: $(srcdir)/rndjent.c jitterentropy-base-user.h \ +- $(srcdir)/jitterentropy-gcd.c $(srcdir)/jitterentropy-gcd.h \ +- $(srcdir)/jitterentropy-health.c $(srcdir)/jitterentropy-health.h \ +- $(srcdir)/jitterentropy-noise.c $(srcdir)/jitterentropy-noise.h \ +- $(srcdir)/jitterentropy-sha3.c $(srcdir)/jitterentropy-sha3.h \ +- $(srcdir)/jitterentropy-timer.c $(srcdir)/jitterentropy-timer.h \ +- $(srcdir)/jitterentropy-base.c $(srcdir)/jitterentropy.h ++rndjent.o: $(srcdir)/rndjent.c + `echo $(COMPILE) -c $(srcdir)/rndjent.c | $(o_flag_munging) ` + +-rndjent.lo: $(srcdir)/rndjent.c jitterentropy-base-user.h \ +- $(srcdir)/jitterentropy-gcd.c $(srcdir)/jitterentropy-gcd.h \ +- $(srcdir)/jitterentropy-health.c $(srcdir)/jitterentropy-health.h \ +- $(srcdir)/jitterentropy-noise.c $(srcdir)/jitterentropy-noise.h \ +- $(srcdir)/jitterentropy-sha3.c $(srcdir)/jitterentropy-sha3.h \ +- $(srcdir)/jitterentropy-timer.c $(srcdir)/jitterentropy-timer.h \ +- $(srcdir)/jitterentropy-base.c $(srcdir)/jitterentropy.h ++rndjent.lo: $(srcdir)/rndjent.c + `echo $(LTCOMPILE) -c $(srcdir)/rndjent.c | $(o_flag_munging) ` + + # Tell versions [3.59,3.63) of GNU make to not export all variables. diff --git a/libgcrypt-FIPS-jitter-whole-entropy.patch b/libgcrypt-FIPS-jitter-whole-entropy.patch new file mode 100644 index 0000000..6c16472 --- /dev/null +++ b/libgcrypt-FIPS-jitter-whole-entropy.patch @@ -0,0 +1,41 @@ +Index: libgcrypt-1.10.3/random/rndgetentropy.c +=================================================================== +--- libgcrypt-1.10.3.orig/random/rndgetentropy.c ++++ libgcrypt-1.10.3/random/rndgetentropy.c +@@ -53,16 +53,30 @@ _gcry_rndgetentropy_gather_random (void + + /* When using a blocking random generator try to get some entropy + * from the jitter based RNG. In this case we take up to 50% of the +- * remaining requested bytes. */ ++ * remaining requested bytes. In FIPS mode, we get all the entropy ++ * from the jitter RNG. */ + if (level >= GCRY_VERY_STRONG_RANDOM) + { + size_t n; + +- n = _gcry_rndjent_poll (add, origin, length/2); +- if (n > length/2) +- n = length/2; +- if (length > 1) +- length -= n; ++ /* In FIPS mode, use the whole length of the entropy buffer from ++ * Jitter RNG */ ++ if (fips_mode ()) ++ { ++ n = _gcry_rndjent_poll (add, origin, length); ++ if (n != length) ++ fips_signal_error ("jitter entropy failed"); ++ else ++ length = 0; ++ } ++ else ++ { ++ n = _gcry_rndjent_poll (add, origin, length/2); ++ if (n > length/2) ++ n = length/2; ++ if (length > 1) ++ length -= n; ++ } + } + + /* Enter the loop. */ diff --git a/libgcrypt-FIPS-rndjent_poll.patch b/libgcrypt-FIPS-rndjent_poll.patch new file mode 100644 index 0000000..f837842 --- /dev/null +++ b/libgcrypt-FIPS-rndjent_poll.patch @@ -0,0 +1,114 @@ +Index: libgcrypt-1.10.0/random/rndoldlinux.c +=================================================================== +--- libgcrypt-1.10.0.orig/random/rndoldlinux.c ++++ libgcrypt-1.10.0/random/rndoldlinux.c +@@ -132,7 +132,7 @@ _gcry_rndoldlinux_gather_random (void (* + volatile pid_t apid; + int fd; + int n; +- byte buffer[768]; ++ byte buffer[256]; + size_t n_hw; + size_t want = length; + size_t last_so_far = 0; +@@ -187,26 +187,43 @@ _gcry_rndoldlinux_gather_random (void (* + my_pid = apid; + } + ++ if (fips_mode()) ++ { ++ if (level >= GCRY_VERY_STRONG_RANDOM) ++ { ++ size_t n; + +- /* First read from a hardware source. Note that _gcry_rndhw_poll_slow lets +- it account only for up to 50% (or 25% for RDRAND) of the requested +- bytes. */ +- n_hw = _gcry_rndhw_poll_slow (add, origin, length); +- if (length > 1) +- length -= n_hw; +- +- /* When using a blocking random generator try to get some entropy +- * from the jitter based RNG. In this case we take up to 50% of the +- * remaining requested bytes. */ +- if (level >= GCRY_VERY_STRONG_RANDOM) +- { +- n_hw = _gcry_rndjent_poll (add, origin, length/2); +- if (n_hw > length/2) +- n_hw = length/2; ++ n = _gcry_rndjent_poll (add, origin, length); ++ if (n == 0) ++ log_fatal ("unexpected error from rndjent: %s\n", ++ strerror (errno)); ++ if (n > length) ++ n = length; ++ if (length > 1) ++ length -= n; ++ } ++ } ++ else ++ { ++ /* First read from a hardware source. Note that _gcry_rndhw_poll_slow lets ++ it account only for up to 50% (or 25% for RDRAND) of the requested ++ bytes. */ ++ n_hw = _gcry_rndhw_poll_slow (add, origin, length); + if (length > 1) + length -= n_hw; +- } + ++ /* When using a blocking random generator try to get some entropy ++ * from the jitter based RNG. In this case we take up to 50% of the ++ * remaining requested bytes. */ ++ if (level >= GCRY_VERY_STRONG_RANDOM) ++ { ++ n_hw = _gcry_rndjent_poll (add, origin, length/2); ++ if (n_hw > length/2) ++ n_hw = length/2; ++ if (length > 1) ++ length -= n_hw; ++ } ++ } + + /* Open the requested device. The first time a device is to be + opened we fail with a fatal error if the device does not exists. +@@ -262,8 +279,6 @@ _gcry_rndoldlinux_gather_random (void (* + do + { + nbytes = length < sizeof(buffer)? length : sizeof(buffer); +- if (nbytes > 256) +- nbytes = 256; + _gcry_pre_syscall (); + ret = getentropy (buffer, nbytes); + _gcry_post_syscall (); +Index: libgcrypt-1.10.0/random/rndjent.c +=================================================================== +--- libgcrypt-1.10.0.orig/random/rndjent.c ++++ libgcrypt-1.10.0/random/rndjent.c +@@ -279,13 +279,24 @@ _gcry_rndjent_poll (void (*add)(const vo + if (!jent_rng_is_initialized) + { + /* Auto-initialize. */ +- jent_rng_is_initialized = 1; + jent_entropy_collector_free (jent_rng_collector); + jent_rng_collector = NULL; + if ( !(_gcry_random_read_conf () & RANDOM_CONF_DISABLE_JENT)) + { +- if (!jent_entropy_init ()) +- jent_rng_collector = jent_entropy_collector_alloc (1, 0); ++ if (!jent_entropy_init_ex (1, 0)) ++ { ++ jent_rng_collector = jent_entropy_collector_alloc (1, 0); ++ jent_rng_is_initialized = 1; ++ } ++ } ++ } ++ ++ if (!jent_rng_collector) ++ { ++ if (!jent_entropy_init_ex (1, 0)) ++ { ++ jent_rng_collector = jent_entropy_collector_alloc (1, 0); ++ jent_rng_is_initialized = 1; + } + } + diff --git a/libgcrypt-Fix-the-previous-change.patch b/libgcrypt-Fix-the-previous-change.patch new file mode 100644 index 0000000..4735528 --- /dev/null +++ b/libgcrypt-Fix-the-previous-change.patch @@ -0,0 +1,45 @@ +From b4eb23dc01a40e13d542fbfc5169dffa7fae5677 Mon Sep 17 00:00:00 2001 +From: NIIBE Yutaka +Date: Thu, 19 Dec 2024 14:16:02 +0900 +Subject: [PATCH 13/19] Fix the previous change. +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* cipher/pubkey.c (_gcry_pk_sign_md): Fix memory leak. +(_gcry_pk_verify_md): Likewise. + +-- + +GnuPG-bug-id: 7338 +Signed-off-by: NIIBE Yutaka +Signed-off-by: Lucas Mülling +--- + cipher/pubkey.c | 4 ++-- + 1 file changed, 2 insertions(+), 2 deletions(-) + +diff --git a/cipher/pubkey.c b/cipher/pubkey.c +index 11bf1ec9..4d7743cc 100644 +--- a/cipher/pubkey.c ++++ b/cipher/pubkey.c +@@ -626,7 +626,7 @@ _gcry_pk_sign_md (gcry_sexp_t *r_sig, const char *tmpl, gcry_md_hd_t hd_orig, + else if (!spec->flags.fips && fips_mode ()) + { + if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) +- return GPG_ERR_PUBKEY_ALGO; ++ rc = GPG_ERR_PUBKEY_ALGO; + else + fips_service_indicator_mark_non_compliant (); + } +@@ -708,7 +708,7 @@ _gcry_pk_verify_md (gcry_sexp_t s_sig, const char *tmpl, gcry_md_hd_t hd_orig, + else if (!spec->flags.fips && fips_mode ()) + { + if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) +- return GPG_ERR_PUBKEY_ALGO; ++ rc = GPG_ERR_PUBKEY_ALGO; + else + fips_service_indicator_mark_non_compliant (); + } +-- +2.49.0 + diff --git a/libgcrypt-build-Improve-__thread-specifier-check.patch b/libgcrypt-build-Improve-__thread-specifier-check.patch new file mode 100644 index 0000000..9167adc --- /dev/null +++ b/libgcrypt-build-Improve-__thread-specifier-check.patch @@ -0,0 +1,41 @@ +From 42e8858566e32080aaf818b168f34c698a9ef084 Mon Sep 17 00:00:00 2001 +From: NIIBE Yutaka +Date: Thu, 9 Jan 2025 10:15:50 +0900 +Subject: [PATCH 1/1] build: Improve __thread specifier check. +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* configure.ac (AC_COMPILE_IFELSE __thread): Move the declaration to +global, referring the variable with (void) in main to avoid an error +buidling with -Werror=unused-variable. Don't need to include +stdlib.h. + +-- + +Reported-by: Lucas Mulling +Signed-off-by: NIIBE Yutaka +Signed-off-by: Lucas Mülling +--- + configure.ac | 5 +++-- + 1 file changed, 3 insertions(+), 2 deletions(-) + +diff --git a/configure.ac b/configure.ac +index d708f89a..f38e20c5 100644 +--- a/configure.ac ++++ b/configure.ac +@@ -1495,8 +1495,9 @@ fi + AC_CACHE_CHECK([whether compiler supports '__thread' storage class specifier], + [gcry_cv_gcc_storage_class__thread], + [gcry_cv_gcc_storage_class__thread=no +- AC_COMPILE_IFELSE([AC_LANG_PROGRAM([#include ], +- [static __thread int bar;] ++ AC_COMPILE_IFELSE([AC_LANG_PROGRAM( ++ [[static __thread int bar;]], ++ [[(void)bar;]] + )], + [gcry_cv_gcc_storage_class__thread=yes])]) + if test "$gcry_cv_gcc_storage_class__thread" = "yes" ; then +-- +2.49.0 + diff --git a/libgcrypt-cipher-Add-KAT-for-non-rfc6979-ECDSA-with-fixed-k.patch b/libgcrypt-cipher-Add-KAT-for-non-rfc6979-ECDSA-with-fixed-k.patch new file mode 100644 index 0000000..ff9ae28 --- /dev/null +++ b/libgcrypt-cipher-Add-KAT-for-non-rfc6979-ECDSA-with-fixed-k.patch @@ -0,0 +1,94 @@ +From be57179f42f8a7cb64f72f73ccea753400573b4f Mon Sep 17 00:00:00 2001 +From: Lucas Mulling via Gcrypt-devel +Date: Wed, 26 Feb 2025 12:29:53 -0300 +Subject: [PATCH 02/14] cipher: Add KAT for non-rfc6979 ECDSA with fixed k +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* cipher/ecc.c (run_selftests): Implement KAT for non-deterministic +ECDSA. +* cipher/ecc. (rfc6979_ecdsa_sample_data, rfc6979_ecdsa_sample_data_bad, +rfc6979_ecdsa_data_tmpl): New. + +Signed-off-by: Lucas Mulling +Signed-off-by: Lucas Mülling +--- + cipher/ecc.c | 40 +++++++++++++++++++++++++++++++++++++--- + 1 file changed, 37 insertions(+), 3 deletions(-) + +diff --git a/cipher/ecc.c b/cipher/ecc.c +index 525523ed..d331a014 100644 +--- a/cipher/ecc.c ++++ b/cipher/ecc.c +@@ -93,23 +93,47 @@ static const char ecdsa_sample_secret_key_secp256[] = + /**/ "7903FE1008B8BC99A41AE9E95628BC64F2F1B20C2D7E9F5177A3C294D4462299#)))"; + + /* Sample data from RFC 6979 section A.2.5, hash is of message "sample" */ +-static const char ecdsa_sample_data[] = ++static const char rfc6979_ecdsa_sample_data[] = + "(data (flags rfc6979 prehash)" + " (hash-algo sha256)" + " (value 6:sample))"; + +-static const char ecdsa_sample_data_bad[] = ++static const char rfc6979_ecdsa_sample_data_bad[] = + "(data (flags rfc6979)" + " (hash sha256 #bf2bdbe1aa9b6ec1e2ade1d694f41fc71a831d0268e98915" + /**/ "62113d8a62add1bf#))"; + ++static const char *rfc6979_ecdsa_data_tmpl = ++ "(data (flags rfc6979)" ++ " (hash %s %b))"; ++ ++/* ++ * Sample data from RFC 6979 section A.2.5, with fixed k, ++ * hash is of message "sample". ++ */ ++static const char ecdsa_sample_data[] = ++ "(data (flags raw prehash)" ++ " (label #A6E3C57DD01ABE90086538398355DD4C3B17AA873382B0F24D6129493D8AAD60#)" ++ " (hash-algo sha256)" ++ " (value 6:sample))"; ++ ++static const char ecdsa_sample_data_bad[] = ++ "(data (flags raw)" ++ " (label #A6E3C57DD01ABE90086538398355DD4C3B17AA873382B0F24D6129493D8AAD60#)" ++ " (hash sha256 #bf2bdbe1aa9b6ec1e2ade1d694f41fc71a831d0268e98915" ++ /**/ "62113d8a62add1bf#))"; ++ ++static const char *ecdsa_data_tmpl = ++ "(data (flags raw)" ++ " (label #A6E3C57DD01ABE90086538398355DD4C3B17AA873382B0F24D6129493D8AAD60#)" ++ " (hash %s %b))"; ++ + static const char ecdsa_signature_r[] = + "efd48b2aacb6a8fd1140dd9cd45e81d69d2c877b56aaf991c34d0ea84eaf3716"; + + static const char ecdsa_signature_s[] = + "f7cb1c942d657c41d436c7a1b6e29f65f3e900dbb9aff4064dc4ab2f843acda8"; + +-static const char *ecdsa_data_tmpl = "(data (flags rfc6979) (hash %s %b))"; + /* Sample data from RFC 6979 section A.2.5, hash is of message "sample" */ + static const char ecdsa_sample_data_string[] = "sample"; + static const char ecdsa_sample_data_bad_string[] = "sbmple"; +@@ -2409,6 +2433,16 @@ run_selftests (int algo, int extended, selftest_report_func_t report) + if (r) + return r; + ++ r = selftests_ecc (report, extended, 0, ++ ecdsa_sample_secret_key_secp256, ++ ecdsa_sample_public_key_secp256, ++ rfc6979_ecdsa_sample_data, rfc6979_ecdsa_sample_data_bad, ++ rfc6979_ecdsa_data_tmpl, ++ ecdsa_sample_data_string, ecdsa_sample_data_bad_string, ++ ecdsa_signature_r, ecdsa_signature_s); ++ if (r) ++ return r; ++ + r = selftests_ecc (report, extended, 1, + ed25519_sample_secret_key, + ed25519_sample_public_key, +-- +2.49.0 + diff --git a/libgcrypt-cipher-Check-and-mark-non-compliant-cipher-modes-in-the-SLI.patch b/libgcrypt-cipher-Check-and-mark-non-compliant-cipher-modes-in-the-SLI.patch new file mode 100644 index 0000000..e922808 --- /dev/null +++ b/libgcrypt-cipher-Check-and-mark-non-compliant-cipher-modes-in-the-SLI.patch @@ -0,0 +1,236 @@ +From 9f0fd2656d7d7ba26fcf95cc64d2514ae9ac8ec1 Mon Sep 17 00:00:00 2001 +From: Lucas Mulling +Date: Fri, 24 Jan 2025 09:57:49 -0300 +Subject: [PATCH] cipher: Check and mark non-compliant cipher modes in the SLI +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* cipher/cipher.c (_gcry_cipher_open_internal): Check and mark if the +cipher mode is compliant and reject accordingly. +(_gcry_cipher_is_mode_fips_compliant): New. +* src/gcrypt.h.in (GCRY_FIPS_FLAG_REJECT_CIPHER_MODE): New. +* tests/t-fips-service-ind.c (check_cipher_o_s_e_d_c): Add test to +verify that the service level indication is correctly set for non- +compliant cipher modes, and correctly rejected if +GCRY_FIPS_FLAG_REJECT_CIPHER_MODE is set. + +-- + +GnuPG-bug-id: 7338 +Signed-off-by: Lucas Mulling +Signed-off-by: Lucas Mülling +--- + cipher/cipher.c | 43 ++++++++++++++++++---- + src/gcrypt.h.in | 1 + + tests/t-fips-service-ind.c | 74 +++++++++++++++++++++++++++++++++----- + 3 files changed, 104 insertions(+), 14 deletions(-) + +diff --git a/cipher/cipher.c b/cipher/cipher.c +index 74dc2df7..b5420671 100644 +--- a/cipher/cipher.c ++++ b/cipher/cipher.c +@@ -504,6 +504,26 @@ _gcry_cipher_open (gcry_cipher_hd_t *handle, + return rc; + } + ++int ++_gcry_cipher_is_mode_fips_compliant(int mode) ++{ ++ switch (mode) ++ { ++ case GCRY_CIPHER_MODE_ECB: ++ case GCRY_CIPHER_MODE_CBC: ++ case GCRY_CIPHER_MODE_CFB: ++ case GCRY_CIPHER_MODE_CFB8: ++ case GCRY_CIPHER_MODE_OFB: ++ case GCRY_CIPHER_MODE_CTR: ++ case GCRY_CIPHER_MODE_CCM: ++ case GCRY_CIPHER_MODE_XTS: ++ case GCRY_CIPHER_MODE_AESWRAP: ++ return GPG_ERR_NO_ERROR; ++ default: ++ return GPG_ERR_NOT_SUPPORTED; ++ } ++} ++ + + gcry_err_code_t + _gcry_cipher_open_internal (gcry_cipher_hd_t *handle, +@@ -523,14 +543,25 @@ _gcry_cipher_open_internal (gcry_cipher_hd_t *handle, + err = GPG_ERR_CIPHER_ALGO; + else if (spec->flags.disabled) + err = GPG_ERR_CIPHER_ALGO; +- else if (!spec->flags.fips && fips_mode ()) ++ else if (fips_mode ()) + { +- if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_CIPHER)) +- err = GPG_ERR_CIPHER_ALGO; +- else ++ if (!spec->flags.fips) + { +- fips_service_indicator_mark_non_compliant (); +- err = 0; ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_CIPHER)) ++ err = GPG_ERR_CIPHER_ALGO; ++ else ++ { ++ fips_service_indicator_mark_non_compliant (); ++ err = 0; ++ } ++ } ++ else if ((err = _gcry_cipher_is_mode_fips_compliant(mode))) ++ { ++ if (!fips_check_rejection (GCRY_FIPS_FLAG_REJECT_CIPHER_MODE)) ++ { ++ fips_service_indicator_mark_non_compliant (); ++ err = 0; ++ } + } + } + else +diff --git a/src/gcrypt.h.in b/src/gcrypt.h.in +index fcb6a327..1a6f7269 100644 +--- a/src/gcrypt.h.in ++++ b/src/gcrypt.h.in +@@ -1988,6 +1988,7 @@ char *gcry_get_config (int mode, const char *what); + #define GCRY_FIPS_FLAG_REJECT_PK (1 << 5) + #define GCRY_FIPS_FLAG_REJECT_PK_MD (1 << 6) + #define GCRY_FIPS_FLAG_REJECT_PK_GOST_SM2 (1 << 7) ++#define GCRY_FIPS_FLAG_REJECT_CIPHER_MODE (1 << 8) + + #define GCRY_FIPS_FLAG_REJECT_MD \ + (GCRY_FIPS_FLAG_REJECT_MD_MD5 | GCRY_FIPS_FLAG_REJECT_MD_OTHERS) +diff --git a/tests/t-fips-service-ind.c b/tests/t-fips-service-ind.c +index fe963fa5..74521bb3 100644 +--- a/tests/t-fips-service-ind.c ++++ b/tests/t-fips-service-ind.c +@@ -606,27 +606,41 @@ check_cipher_o_s_e_d_c (int reject) + { + static struct { + int algo; ++ int mode; + const char *key; + int keylen; ++ const char *tag; ++ int taglen; + const char *expect; + int expect_failure; + } tv[] = { + #if USE_DES +- { GCRY_CIPHER_3DES, +- "\xe3\x34\x7a\x6b\x0b\xc1\x15\x2c\x64\x2a\x25\xcb\xd3\xbc\x31\xab" +- "\xfb\xa1\x62\xa8\x1f\x19\x7c\x15", 24, +- "\x3f\x1a\xb8\x83\x18\x8b\xb5\x97", 1 }, ++ { GCRY_CIPHER_3DES, GCRY_CIPHER_MODE_ECB, ++ "\xe3\x34\x7a\x6b\x0b\xc1\x15\x2c\x64\x2a\x25\xcb\xd3\xbc\x31\xab" ++ "\xfb\xa1\x62\xa8\x1f\x19\x7c\x15", 24, ++ "", -1, ++ "\x3f\x1a\xb8\x83\x18\x8b\xb5\x97", 1 }, + #endif +- { GCRY_CIPHER_AES, +- "\x2b\x7e\x15\x16\x28\xae\xd2\xa6\xab\xf7\x15\x88\x09\xcf\x4f\x3c", 16, +- "\x5c\x71\xd8\x5d\x26\x5e\xcd\xb5\x95\x40\x41\xab\xff\x25\x6f\xd1" } ++ { GCRY_CIPHER_AES, GCRY_CIPHER_MODE_ECB, ++ "\x2b\x7e\x15\x16\x28\xae\xd2\xa6\xab\xf7\x15\x88\x09\xcf\x4f\x3c", 16, ++ "", -1, ++ "\x5c\x71\xd8\x5d\x26\x5e\xcd\xb5\x95\x40\x41\xab\xff\x25\x6f\xd1" }, ++ { GCRY_CIPHER_AES128, GCRY_CIPHER_MODE_SIV, ++ "\xff\xfe\xfd\xfc\xfb\xfa\xf9\xf8\xf7\xf6\xf5\xf4\xf3\xf2\xf1\xf0" ++ "\xf0\xf1\xf2\xf3\xf4\xf5\xf6\xf7\xf8\xf9\xfa\xfb\xfc\xfd\xfe\xff", 32, ++ "\x51\x66\x54\xc4\xe1\xb5\xd9\x37\x31\x52\xdb\xea\x35\x10\x8b\x7b", 16, ++ "\x83\x69\xf6\xf3\x20\xff\xa2\x72\x31\x67\x15\xcf\xf4\x75\x01\x9a", 1 } + }; ++ + const char *pt = "Shohei Ohtani 2024: 54 HR, 59 SB"; + int ptlen; + int tvidx; + unsigned char out[MAX_DATA_LEN]; + gpg_error_t err; + ++ unsigned char tag[16]; ++ size_t taglen = 0; ++ + ptlen = strlen (pt); + assert (ptlen == 32); + for (tvidx=0; tvidx < DIM(tv); tvidx++) +@@ -640,10 +654,12 @@ check_cipher_o_s_e_d_c (int reject) + tvidx); + + blklen = gcry_cipher_get_algo_blklen (tv[tvidx].algo); ++ + assert (blklen != 0); + assert (blklen <= ptlen); + assert (blklen <= DIM (out)); +- err = gcry_cipher_open (&h, tv[tvidx].algo, GCRY_CIPHER_MODE_ECB, 0); ++ assert (tv[tvidx].taglen <= 16); ++ err = gcry_cipher_open (&h, tv[tvidx].algo, tv[tvidx].mode, 0); + if (err) + { + if (in_fips_mode && reject && tv[tvidx].expect_failure) +@@ -694,6 +710,18 @@ check_cipher_o_s_e_d_c (int reject) + continue; + } + ++ if (tv[tvidx].taglen >= 0) ++ { ++ err = gcry_cipher_info (h, GCRYCTL_GET_TAGLEN, NULL, &taglen); ++ if (err) ++ fail ("gcry_cipher_info %d failed: %s\n", tvidx, ++ gpg_strerror (err)); ++ ++ if (taglen != tv[tvidx].taglen) ++ fail ("gcry_cipher_info %d failed: taglen mismatch %d != %ld\n", tvidx, ++ tv[tvidx].taglen, taglen); ++ } ++ + err = gcry_cipher_encrypt (h, out, MAX_DATA_LEN, pt, blklen); + if (err) + { +@@ -714,6 +742,35 @@ check_cipher_o_s_e_d_c (int reject) + putc ('\n', stderr); + } + ++ if (tv[tvidx].taglen >= 0) ++ { ++ err = gcry_cipher_gettag (h, tag, tv[tvidx].taglen); ++ if (err) ++ fail ("gcry_cipher_gettag %d failed: %s", tvidx, ++ gpg_strerror(err)); ++ ++ if (memcmp (tv[tvidx].tag, tag, tv[tvidx].taglen)) ++ { ++ int i; ++ ++ fail ("gcry_cipher_gettag %d: tag mismatch\n", tvidx); ++ fputs ("got:", stderr); ++ for (i=0; i < 16 ; i++) ++ fprintf (stderr, " %02x", tag[i]); ++ putc ('\n', stderr); ++ } ++ ++ err = gcry_cipher_reset (h); ++ if (err) ++ fail("gcry_cipher_reset %d failed: %s", tvidx, ++ gpg_strerror(err)); ++ ++ err = gcry_cipher_set_decryption_tag (h, tag, 16); ++ if (err) ++ fail ("gcry_cipher_set_decryption_tag %d failed: %s\n", tvidx< ++ gpg_strerror (err)); ++ } ++ + err = gcry_cipher_decrypt (h, out, blklen, NULL, 0); + if (err) + { +@@ -1483,6 +1540,7 @@ main (int argc, char **argv) + + xgcry_control ((GCRYCTL_FIPS_REJECT_NON_FIPS, + (GCRY_FIPS_FLAG_REJECT_MD_MD5 ++ | GCRY_FIPS_FLAG_REJECT_CIPHER_MODE + | GCRY_FIPS_FLAG_REJECT_PK_MD + | GCRY_FIPS_FLAG_REJECT_PK_GOST_SM2 + | GCRY_FIPS_FLAG_REJECT_COMPAT110))); +-- +2.49.0 + diff --git a/libgcrypt-cipher-Differentiate-igninvflag-in-the-SLI.patch b/libgcrypt-cipher-Differentiate-igninvflag-in-the-SLI.patch new file mode 100644 index 0000000..7763815 --- /dev/null +++ b/libgcrypt-cipher-Differentiate-igninvflag-in-the-SLI.patch @@ -0,0 +1,40 @@ +From 3bdb59c21b77711cf7d44d692a7a02f5f469033e Mon Sep 17 00:00:00 2001 +From: Lucas Mulling via Gcrypt-devel +Date: Wed, 26 Feb 2025 17:19:22 -0300 +Subject: [PATCH 04/14] cipher: Differentiate igninvflag in the SLI +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* cipher/pubkey-util.c (_gcry_pk_util_parse_flaglist): Differentiate use +of igninvflag. + +GnuPG-bug-id: 7338 +Signed-off-by: Lucas Mulling +Signed-off-by: Lucas Mülling +--- + cipher/pubkey-util.c | 8 ++++++++ + 1 file changed, 8 insertions(+) + +diff --git a/cipher/pubkey-util.c b/cipher/pubkey-util.c +index 68defea6..9c927638 100644 +--- a/cipher/pubkey-util.c ++++ b/cipher/pubkey-util.c +@@ -200,6 +200,14 @@ _gcry_pk_util_parse_flaglist (gcry_sexp_t list, + } + } + ++ if (fips_mode () && igninvflag) ++ { ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) ++ rc = GPG_ERR_INV_FLAG; ++ else ++ fips_service_indicator_mark_non_compliant (); ++ } ++ + if (r_flags) + *r_flags = flags; + if (r_encoding) +-- +2.49.0 + diff --git a/libgcrypt-cipher-Differentiate-no-blinding-flag-in-the-SLI.patch b/libgcrypt-cipher-Differentiate-no-blinding-flag-in-the-SLI.patch new file mode 100644 index 0000000..92b9073 --- /dev/null +++ b/libgcrypt-cipher-Differentiate-no-blinding-flag-in-the-SLI.patch @@ -0,0 +1,70 @@ +From cc0a40bd74120dc06fd80f163b30abb91f60b63b Mon Sep 17 00:00:00 2001 +From: Lucas Mulling via Gcrypt-devel +Date: Wed, 26 Feb 2025 17:19:23 -0300 +Subject: [PATCH 05/14] cipher: Differentiate no-blinding flag in the SLI +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* cipher/rsa.c (rsa_decrypt, rsa_encrypt): Differentiate use of flag +no-blinding in the service level indicator. + +GnuPG-bug-id: 7338 +Signed-off-by: Lucas Mulling +Signed-off-by: Lucas Mülling +--- + cipher/rsa.c | 30 ++++++++++++++++++++++++++++-- + 1 file changed, 28 insertions(+), 2 deletions(-) + +diff --git a/cipher/rsa.c b/cipher/rsa.c +index c1329644..dce76414 100644 +--- a/cipher/rsa.c ++++ b/cipher/rsa.c +@@ -1501,7 +1501,19 @@ rsa_decrypt (gcry_sexp_t *r_plain, gcry_sexp_t s_data, gcry_sexp_t keyparms) + be practically mounted over the network as shown by Brumley and + Boney in 2003. */ + if ((ctx.flags & PUBKEY_FLAG_NO_BLINDING)) +- secret (plain, data, &sk); ++ { ++ if (fips_mode ()) ++ { ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) ++ { ++ rc = GPG_ERR_INV_FLAG; ++ goto leave; ++ } ++ else ++ fips_service_indicator_mark_non_compliant (); ++ } ++ secret (plain, data, &sk); ++ } + else + secret_blinded (plain, data, &sk, nbits); + +@@ -1632,8 +1644,22 @@ rsa_sign (gcry_sexp_t *r_sig, gcry_sexp_t s_data, gcry_sexp_t keyparms) + + /* Do RSA computation. */ + sig = mpi_new (0); ++ + if ((ctx.flags & PUBKEY_FLAG_NO_BLINDING)) +- secret (sig, data, &sk); ++ { ++ if (fips_mode ()) ++ { ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) ++ { ++ rc = GPG_ERR_INV_FLAG; ++ goto leave; ++ } ++ else ++ fips_service_indicator_mark_non_compliant (); ++ } ++ ++ secret (sig, data, &sk); ++ } + else + secret_blinded (sig, data, &sk, nbits); + if (DBG_CIPHER) +-- +2.49.0 + diff --git a/libgcrypt-cipher-Differentiate-use-of-label-K-in-the-SLI.patch b/libgcrypt-cipher-Differentiate-use-of-label-K-in-the-SLI.patch new file mode 100644 index 0000000..a054b64 --- /dev/null +++ b/libgcrypt-cipher-Differentiate-use-of-label-K-in-the-SLI.patch @@ -0,0 +1,139 @@ +From 2f6d2db1a4c28775a568c1f81ca127d2daebaf1c Mon Sep 17 00:00:00 2001 +From: Lucas Mulling via Gcrypt-devel +Date: Wed, 26 Feb 2025 12:29:54 -0300 +Subject: [PATCH 03/14] cipher: Differentiate use of label K in the SLI +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* cipher/ecc.c (ecc_sign, ecc_verify): Use of label K is not allowed in +fips mode, differentiate with the GCRY_FIPS_FLAG_REJECT_PK_ECC_K flag. +* src/gcrypt.h.in: New GCRY_FIPS_FLAG_REJECT_PK_ECC_K. +* tests/t-fips-service-ind.c (check_pk_hash_sign_verify): Mark non +compliant use of label. + +Signed-off-by: Lucas Mulling +Signed-off-by: Lucas Mülling +--- + cipher/ecc.c | 26 +++++++++++++++++++++++++- + src/gcrypt.h.in | 2 ++ + tests/t-fips-service-ind.c | 11 ++++++----- + 3 files changed, 33 insertions(+), 6 deletions(-) + +diff --git a/cipher/ecc.c b/cipher/ecc.c +index d331a014..569e41f6 100644 +--- a/cipher/ecc.c ++++ b/cipher/ecc.c +@@ -961,7 +961,16 @@ ecc_sign (gcry_sexp_t *r_sig, gcry_sexp_t s_data, gcry_sexp_t keyparms) + log_mpidump ("ecc_sign data", data); + + if (ctx.label) +- rc = _gcry_mpi_scan (&k, GCRYMPI_FMT_USG, ctx.label, ctx.labellen, NULL); ++ { ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK_ECC_K)) ++ { ++ rc = GPG_ERR_INV_DATA; ++ goto leave; ++ } ++ else ++ fips_service_indicator_mark_non_compliant (); ++ rc = _gcry_mpi_scan (&k, GCRYMPI_FMT_USG, ctx.label, ctx.labellen, NULL); ++ } + if (rc) + goto leave; + +@@ -1118,6 +1127,21 @@ ecc_verify (gcry_sexp_t s_sig, gcry_sexp_t s_data, gcry_sexp_t s_keyparms) + rc = _gcry_pk_util_data_to_mpi (s_data, &data, &ctx); + if (rc) + goto leave; ++ ++ if (ctx.label) ++ { ++ if (fips_mode ()) ++ { ++ if(fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK_ECC_K)) ++ { ++ rc = GPG_ERR_INV_DATA; ++ goto leave; ++ } ++ else ++ fips_service_indicator_mark_non_compliant (); ++ } ++ } ++ + if (DBG_CIPHER) + log_mpidump ("ecc_verify data", data); + +diff --git a/src/gcrypt.h.in b/src/gcrypt.h.in +index 1a6f7269..fe3db16a 100644 +--- a/src/gcrypt.h.in ++++ b/src/gcrypt.h.in +@@ -1989,6 +1989,8 @@ char *gcry_get_config (int mode, const char *what); + #define GCRY_FIPS_FLAG_REJECT_PK_MD (1 << 6) + #define GCRY_FIPS_FLAG_REJECT_PK_GOST_SM2 (1 << 7) + #define GCRY_FIPS_FLAG_REJECT_CIPHER_MODE (1 << 8) ++/**/ ++#define GCRY_FIPS_FLAG_REJECT_PK_ECC_K (1 << 10) + + #define GCRY_FIPS_FLAG_REJECT_MD \ + (GCRY_FIPS_FLAG_REJECT_MD_MD5 | GCRY_FIPS_FLAG_REJECT_MD_OTHERS) +diff --git a/tests/t-fips-service-ind.c b/tests/t-fips-service-ind.c +index a082b258..0ece55b8 100644 +--- a/tests/t-fips-service-ind.c ++++ b/tests/t-fips-service-ind.c +@@ -728,7 +728,7 @@ check_pk_hash_sign_verify (void) + "ce4014c68811f9a21a1fdb2c0e6113e06db7ca93b7404e78dc7ccd5ca89a4ca9#)))", + "(data(flags raw)(hash %s %b)(label %b))", + "94a1bbb14b906a61a280f245f9e93c7f3b4a6247824f5d33b9670787642a68de", +- 0, 0 ++ 1, 0, + } + }; + int tvidx; +@@ -827,7 +827,7 @@ check_pk_hash_sign_verify (void) + if (ec == GPG_ERR_INV_OP) + { + /* libgcrypt is old, no support of the FIPS service indicator. */ +- fail ("gcry_pk_hash test %d unexpectedly failed to check the FIPS service indicator.\n", ++ fail ("gcry_pk_hash_sign test %d unexpectedly failed to check the FIPS service indicator.\n", + tvidx); + goto next; + } +@@ -835,7 +835,7 @@ check_pk_hash_sign_verify (void) + if (in_fips_mode && !tv[tvidx].expect_failure && ec) + { + /* Success with the FIPS service indicator == 0 expected, but != 0. */ +- fail ("gcry_pk_hash test %d unexpectedly set the indicator in FIPS mode.\n", ++ fail ("gcry_pk_hash_sign test %d unexpectedly set the indicator in FIPS mode.\n", + tvidx); + goto next; + } +@@ -859,7 +859,7 @@ check_pk_hash_sign_verify (void) + if (ec == GPG_ERR_INV_OP) + { + /* libgcrypt is old, no support of the FIPS service indicator. */ +- fail ("gcry_pk_hash test %d unexpectedly failed to check the FIPS service indicator.\n", ++ fail ("gcry_pk_hash_verify test %d unexpectedly failed to check the FIPS service indicator.\n", + tvidx); + goto next; + } +@@ -867,7 +867,7 @@ check_pk_hash_sign_verify (void) + if (in_fips_mode && !tv[tvidx].expect_failure && ec) + { + /* Success with the FIPS service indicator == 0 expected, but != 0. */ +- fail ("gcry_pk_hash test %d unexpectedly set the indicator in FIPS mode.\n", ++ fail ("gcry_pk_hash_verify test %d unexpectedly set the indicator in FIPS mode.\n", + tvidx); + goto next; + } +@@ -1834,6 +1834,7 @@ main (int argc, char **argv) + | GCRY_FIPS_FLAG_REJECT_CIPHER_MODE + | GCRY_FIPS_FLAG_REJECT_PK_MD + | GCRY_FIPS_FLAG_REJECT_PK_GOST_SM2 ++ | GCRY_FIPS_FLAG_REJECT_PK_ECC_K + | GCRY_FIPS_FLAG_REJECT_COMPAT110))); + + check_md_o_w_r_c (1); +-- +2.49.0 + diff --git a/libgcrypt-cipher-Don-t-differentiate-GCRY_CIPHER_MODE_CMAC-in-FIPS-mode.patch b/libgcrypt-cipher-Don-t-differentiate-GCRY_CIPHER_MODE_CMAC-in-FIPS-mode.patch new file mode 100644 index 0000000..fc8d335 --- /dev/null +++ b/libgcrypt-cipher-Don-t-differentiate-GCRY_CIPHER_MODE_CMAC-in-FIPS-mode.patch @@ -0,0 +1,98 @@ +From 608ff4b2261e2d8961f0ef4189e74b1173b2802c Mon Sep 17 00:00:00 2001 +From: Lucas Mulling +Date: Sun, 2 Feb 2025 12:58:21 -0300 +Subject: [PATCH 2/2] cipher: Don't differentiate GCRY_CIPHER_MODE_CMAC in FIPS + mode. +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* cipher/cipher.c (_gcry_cipher_mode_fips_compliance): Allow +GCRY_CIPHER_MODE_CMAC in fips mode. +* cipher/cipher.c (cipher_modes_fips_compliance) +(cipher_int_modes_fips_compliance): New. +-- + +Signed-off-by: Lucas Mulling + +Added some comments, changed scope of the new functions and shorted +their names. Also added restructured the switch and added all other +modes. + +Signed-off-by: Werner Koch +Signed-off-by: Lucas Mülling +--- + cipher/cipher.c | 49 ++++++++++++++++++++++++++++++++++++++++++++----- + 1 file changed, 44 insertions(+), 5 deletions(-) + +diff --git a/cipher/cipher.c b/cipher/cipher.c +index 3b7970b3..fc130907 100644 +--- a/cipher/cipher.c ++++ b/cipher/cipher.c +@@ -505,8 +505,9 @@ _gcry_cipher_open (gcry_cipher_hd_t *handle, + } + + +-gcry_err_code_t +-_gcry_cipher_mode_fips_compliance (enum gcry_cipher_modes mode) ++/* Return an error if the give cipher mode is non-FIPS compliant. */ ++static gcry_err_code_t ++cipher_modes_fips_compliance (enum gcry_cipher_modes mode) + { + switch (mode) + { +@@ -519,10 +520,48 @@ _gcry_cipher_mode_fips_compliance (enum gcry_cipher_modes mode) + case GCRY_CIPHER_MODE_CCM: + case GCRY_CIPHER_MODE_XTS: + case GCRY_CIPHER_MODE_AESWRAP: +- return GPG_ERR_NO_ERROR; +- default: +- return GPG_ERR_NOT_SUPPORTED; ++ return 0; ++ case GCRY_CIPHER_MODE_NONE: ++ case GCRY_CIPHER_MODE_STREAM: ++ case GCRY_CIPHER_MODE_GCM: ++ case GCRY_CIPHER_MODE_POLY1305: ++ case GCRY_CIPHER_MODE_OCB: ++ case GCRY_CIPHER_MODE_EAX: ++ case GCRY_CIPHER_MODE_SIV: ++ case GCRY_CIPHER_MODE_GCM_SIV: ++ break; + } ++ return GPG_ERR_NOT_SUPPORTED; ++} ++ ++ ++/* This is similar to cipher_modes_fips_compliance but only for the ++ * internal modes (i.e. CMAC). Return an error if the mode is ++ * non-FIPS compliant. */ ++static gcry_err_code_t ++cipher_int_modes_fips_compliance (enum gcry_cipher_internal_modes mode) ++{ ++ switch (mode) ++ { ++ case GCRY_CIPHER_MODE_INTERNAL: ++ break; ++ case GCRY_CIPHER_MODE_CMAC: ++ return 0; ++ } ++ return GPG_ERR_NOT_SUPPORTED; ++} ++ ++ ++/* Return an error if the give cipher mode is non-FIPS compliant. The ++ * mode is not an enum here so that we can use it for real modes and ++ * for internal modes. */ ++gcry_err_code_t ++_gcry_cipher_mode_fips_compliance (int mode) ++{ ++ if (mode >= GCRY_CIPHER_MODE_INTERNAL) ++ return cipher_int_modes_fips_compliance (mode); ++ else ++ return cipher_modes_fips_compliance (mode); + } + + +-- +2.49.0 + diff --git a/libgcrypt-cipher-Rename-_gcry_cipher_is_mode_fips_compliant.patch b/libgcrypt-cipher-Rename-_gcry_cipher_is_mode_fips_compliant.patch new file mode 100644 index 0000000..e98f6ab --- /dev/null +++ b/libgcrypt-cipher-Rename-_gcry_cipher_is_mode_fips_compliant.patch @@ -0,0 +1,64 @@ +From 6b0fbb7e5e0da77787e3a87d74359ee21c44904e Mon Sep 17 00:00:00 2001 +From: Lucas Mulling +Date: Tue, 28 Jan 2025 13:45:39 -0300 +Subject: [PATCH 1/2] cipher: Rename _gcry_cipher_is_mode_fips_compliant +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* cipher/cipher.c (_gcry_cipher_is_mode_fips_compliant): Rename to +_gcry_cipher_mode_fips_compliance for better clarity and change the +return type to gcry_err_code_t. +* cipher/cipher.c (_gcry_cipher_mode_fips_compliance): Use +gcry_cipher_modes instead of int for mode. +* tests/t-fips-service-ind.c (check_cipher_o_s_e_d_c): Fix typo in fail. +-- + +Signed-off-by: Lucas Mulling +Signed-off-by: Lucas Mülling +--- + cipher/cipher.c | 7 ++++--- + tests/t-fips-service-ind.c | 2 +- + 2 files changed, 5 insertions(+), 4 deletions(-) + +diff --git a/cipher/cipher.c b/cipher/cipher.c +index b5420671..3b7970b3 100644 +--- a/cipher/cipher.c ++++ b/cipher/cipher.c +@@ -504,8 +504,9 @@ _gcry_cipher_open (gcry_cipher_hd_t *handle, + return rc; + } + +-int +-_gcry_cipher_is_mode_fips_compliant(int mode) ++ ++gcry_err_code_t ++_gcry_cipher_mode_fips_compliance (enum gcry_cipher_modes mode) + { + switch (mode) + { +@@ -555,7 +556,7 @@ _gcry_cipher_open_internal (gcry_cipher_hd_t *handle, + err = 0; + } + } +- else if ((err = _gcry_cipher_is_mode_fips_compliant(mode))) ++ else if ((err = _gcry_cipher_mode_fips_compliance (mode))) + { + if (!fips_check_rejection (GCRY_FIPS_FLAG_REJECT_CIPHER_MODE)) + { +diff --git a/tests/t-fips-service-ind.c b/tests/t-fips-service-ind.c +index 74521bb3..ed5f8d3f 100644 +--- a/tests/t-fips-service-ind.c ++++ b/tests/t-fips-service-ind.c +@@ -767,7 +767,7 @@ check_cipher_o_s_e_d_c (int reject) + + err = gcry_cipher_set_decryption_tag (h, tag, 16); + if (err) +- fail ("gcry_cipher_set_decryption_tag %d failed: %s\n", tvidx< ++ fail ("gcry_cipher_set_decryption_tag %d failed: %s\n", tvidx, + gpg_strerror (err)); + } + +-- +2.49.0 + diff --git a/libgcrypt-cipher-ecc-Fix-for-supplied-K.patch b/libgcrypt-cipher-ecc-Fix-for-supplied-K.patch new file mode 100644 index 0000000..743468d --- /dev/null +++ b/libgcrypt-cipher-ecc-Fix-for-supplied-K.patch @@ -0,0 +1,88 @@ +From 755e6dce727915249cbb1a98f22832d940b99c24 Mon Sep 17 00:00:00 2001 +From: NIIBE Yutaka +Date: Thu, 6 Mar 2025 09:12:36 +0900 +Subject: [PATCH 07/14] cipher,ecc: Fix for supplied K. +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* cipher/ecc.c (ecc_sign): Check if it's under FIPS mode. +(ecc_verify): Supplied K does no sense for verification, but add +comment of clarification mark/reject-ing under FIPS mode. + +-- + +GnuPG-bug-id: 7338 +Signed-off-by: NIIBE Yutaka +Signed-off-by: Lucas Mülling +--- + cipher/ecc.c | 39 +++++++++++++++++++++++---------------- + 1 file changed, 23 insertions(+), 16 deletions(-) + +diff --git a/cipher/ecc.c b/cipher/ecc.c +index 569e41f6..a165bb7a 100644 +--- a/cipher/ecc.c ++++ b/cipher/ecc.c +@@ -962,17 +962,21 @@ ecc_sign (gcry_sexp_t *r_sig, gcry_sexp_t s_data, gcry_sexp_t keyparms) + + if (ctx.label) + { +- if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK_ECC_K)) ++ /* ECDSA signing can have supplied K (for testing, deterministic). */ ++ if (fips_mode ()) + { +- rc = GPG_ERR_INV_DATA; +- goto leave; ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK_ECC_K)) ++ { ++ rc = GPG_ERR_INV_DATA; ++ goto leave; ++ } ++ else ++ fips_service_indicator_mark_non_compliant (); + } +- else +- fips_service_indicator_mark_non_compliant (); + rc = _gcry_mpi_scan (&k, GCRYMPI_FMT_USG, ctx.label, ctx.labellen, NULL); ++ if (rc) ++ goto leave; + } +- if (rc) +- goto leave; + + if (fips_mode () + && ((ctx.flags & PUBKEY_FLAG_GOST) || (ctx.flags & PUBKEY_FLAG_SM2))) +@@ -1128,18 +1132,21 @@ ecc_verify (gcry_sexp_t s_sig, gcry_sexp_t s_data, gcry_sexp_t s_keyparms) + if (rc) + goto leave; + +- if (ctx.label) ++ /* ++ * ECDSA signing can have supplied K (for testing, deterministic), ++ * but it's non-compliant. For ECDSA signature verification, having ++ * K is irrelevant, but an application may use same flags as the one ++ * for signing. ++ */ ++ if (ctx.label && fips_mode ()) + { +- if (fips_mode ()) ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK_ECC_K)) + { +- if(fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK_ECC_K)) +- { +- rc = GPG_ERR_INV_DATA; +- goto leave; +- } +- else +- fips_service_indicator_mark_non_compliant (); ++ rc = GPG_ERR_INV_DATA; ++ goto leave; + } ++ else ++ fips_service_indicator_mark_non_compliant (); + } + + if (DBG_CIPHER) +-- +2.49.0 + diff --git a/libgcrypt-cipher-fips-Fix-for-random-override.patch b/libgcrypt-cipher-fips-Fix-for-random-override.patch new file mode 100644 index 0000000..076f66f --- /dev/null +++ b/libgcrypt-cipher-fips-Fix-for-random-override.patch @@ -0,0 +1,83 @@ +From ca8bf05e111b41e482a2a4b34cda6bcf5aa1f27e Mon Sep 17 00:00:00 2001 +From: NIIBE Yutaka +Date: Thu, 6 Mar 2025 09:45:36 +0900 +Subject: [PATCH 09/14] cipher,fips: Fix for random-override. +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* cipher/pubkey-util.c (gcry_pk_util_data_to_mpi): Keep +the behavior of 1.10. +* src/visibility.c (gcry_pk_random_override_new): Likewise. +* tests/t-fips-service-ind.c (main): Use GCRY_FIPS_FLAG_REJECT_PK_FLAGS. + +-- + +GnuPG-bug-id: 7338 +Signed-off-by: NIIBE Yutaka +Signed-off-by: Lucas Mülling +--- + cipher/pubkey-util.c | 6 +++--- + src/visibility.c | 2 +- + tests/t-fips-service-ind.c | 1 + + 3 files changed, 5 insertions(+), 4 deletions(-) + +diff --git a/cipher/pubkey-util.c b/cipher/pubkey-util.c +index 66a04f13..0e67f892 100644 +--- a/cipher/pubkey-util.c ++++ b/cipher/pubkey-util.c +@@ -975,7 +975,7 @@ _gcry_pk_util_data_to_mpi (gcry_sexp_t input, gcry_mpi_t *ret_mpi, + { + if (fips_mode ()) + { +- if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK_FLAGS)) + { + sexp_release (list); + rc = GPG_ERR_INV_FLAG; +@@ -1162,7 +1162,7 @@ _gcry_pk_util_data_to_mpi (gcry_sexp_t input, gcry_mpi_t *ret_mpi, + { + if (fips_mode ()) + { +- if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK_FLAGS)) + { + sexp_release (list); + rc = GPG_ERR_INV_FLAG; +@@ -1272,7 +1272,7 @@ _gcry_pk_util_data_to_mpi (gcry_sexp_t input, gcry_mpi_t *ret_mpi, + { + if (fips_mode ()) + { +- if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK_FLAGS)) + { + sexp_release (list); + rc = GPG_ERR_INV_FLAG; +diff --git a/src/visibility.c b/src/visibility.c +index ccd0de69..edb972bc 100644 +--- a/src/visibility.c ++++ b/src/visibility.c +@@ -1091,7 +1091,7 @@ gcry_pk_random_override_new (gcry_ctx_t *r_ctx, const unsigned char *p, size_t l + + if (fips_mode ()) + { +- if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK_FLAGS)) + return gpg_error (GPG_ERR_INV_OP); + else + fips_service_indicator_mark_non_compliant (); +diff --git a/tests/t-fips-service-ind.c b/tests/t-fips-service-ind.c +index 0ece55b8..0a270b38 100644 +--- a/tests/t-fips-service-ind.c ++++ b/tests/t-fips-service-ind.c +@@ -1835,6 +1835,7 @@ main (int argc, char **argv) + | GCRY_FIPS_FLAG_REJECT_PK_MD + | GCRY_FIPS_FLAG_REJECT_PK_GOST_SM2 + | GCRY_FIPS_FLAG_REJECT_PK_ECC_K ++ | GCRY_FIPS_FLAG_REJECT_PK_FLAGS + | GCRY_FIPS_FLAG_REJECT_COMPAT110))); + + check_md_o_w_r_c (1); +-- +2.49.0 + diff --git a/libgcrypt-cipher-rsa-Mark-reject-SHA1-unknown-with-RSA-signature-generation.patch b/libgcrypt-cipher-rsa-Mark-reject-SHA1-unknown-with-RSA-signature-generation.patch new file mode 100644 index 0000000..7ff18ce --- /dev/null +++ b/libgcrypt-cipher-rsa-Mark-reject-SHA1-unknown-with-RSA-signature-generation.patch @@ -0,0 +1,445 @@ +From 60e5039793c2474d29ded039cf1a6b8107733a20 Mon Sep 17 00:00:00 2001 +From: NIIBE Yutaka +Date: Fri, 21 Feb 2025 14:24:41 +0900 +Subject: [PATCH] cipher:rsa: Mark/reject SHA1/unknown with RSA signature + generation. +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* cipher/rsa-common.c (_gcry_rsa_pkcs1_encode_raw_for_sig): We can't +determine if it's compliant when raw PKCS1 encoding is used. +(_gcry_rsa_pss_encode): Add the behavior of marking non-compliant use. +(_gcry_rsa_pss_verify): Likewise. +* cipher/rsa.c (rsa_sign): Handle the check for SHA1. +(rsa_verify): Likewise. +* tests/t-fips-service-ind.c (check_pk_s_v): Add use cases for RSA +and Ed25519. + +-- + +GnuPG-bug-id: 7338 +Signed-off-by: NIIBE Yutaka +Signed-off-by: Lucas Mülling +--- + cipher/rsa-common.c | 28 +++- + cipher/rsa.c | 34 +++++ + tests/t-fips-service-ind.c | 290 ++++++++++++++++++++++++++++++++++++- + 3 files changed, 347 insertions(+), 5 deletions(-) + +diff --git a/cipher/rsa-common.c b/cipher/rsa-common.c +index 1920eedd..c1d2dcd5 100644 +--- a/cipher/rsa-common.c ++++ b/cipher/rsa-common.c +@@ -380,6 +380,16 @@ _gcry_rsa_pkcs1_encode_raw_for_sig (gcry_mpi_t *r_result, unsigned int nbits, + int i; + size_t n; + ++ /* With RAW encoding, we can't know if the hash used is compliant or ++ * not. Reject or mark it's non-compliant. */ ++ if (fips_mode ()) ++ { ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK_MD)) ++ return GPG_ERR_DIGEST_ALGO; ++ else ++ fips_service_indicator_mark_non_compliant (); ++ } ++ + if ( !valuelen || valuelen + 4 > nframe) + { + /* Can't encode an DLEN byte digest MD into an NFRAME byte +@@ -840,8 +850,13 @@ _gcry_rsa_pss_encode (gcry_mpi_t *r_result, unsigned int nbits, int algo, + /* The FIPS 186-4 Section 5.5 allows only 0 <= sLen <= hLen */ + if (fips_mode () && saltlen > hlen) + { +- rc = GPG_ERR_INV_ARG; +- goto leave; ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) ++ { ++ rc = GPG_ERR_INV_ARG; ++ goto leave; ++ } ++ else ++ fips_service_indicator_mark_non_compliant (); + } + + /* Allocate a help buffer and setup some pointers. */ +@@ -1006,8 +1021,13 @@ _gcry_rsa_pss_verify (gcry_mpi_t value, int hashed_already, + /* The FIPS 186-4 Section 5.5 allows only 0 <= sLen <= hLen */ + if (fips_mode () && saltlen > hlen) + { +- rc = GPG_ERR_INV_ARG; +- goto leave; ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) ++ { ++ rc = GPG_ERR_INV_ARG; ++ goto leave; ++ } ++ else ++ fips_service_indicator_mark_non_compliant (); + } + + /* Allocate a help buffer and setup some pointers. +diff --git a/cipher/rsa.c b/cipher/rsa.c +index c7a809f4..c1329644 100644 +--- a/cipher/rsa.c ++++ b/cipher/rsa.c +@@ -1613,6 +1613,23 @@ rsa_sign (gcry_sexp_t *r_sig, gcry_sexp_t s_data, gcry_sexp_t keyparms) + } + } + ++ /* Check if use of the hash is compliant. */ ++ if (fips_mode ()) ++ { ++ /* SHA1 is approved hash function, but not for digital signature. */ ++ if (_gcry_md_algo_info (ctx.hash_algo, GCRYCTL_TEST_ALGO, NULL, NULL) ++ || ctx.hash_algo == GCRY_MD_SHA1) ++ { ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK_MD)) ++ { ++ rc = GPG_ERR_DIGEST_ALGO; ++ goto leave; ++ } ++ else ++ fips_service_indicator_mark_non_compliant (); ++ } ++ } ++ + /* Do RSA computation. */ + sig = mpi_new (0); + if ((ctx.flags & PUBKEY_FLAG_NO_BLINDING)) +@@ -1720,6 +1737,23 @@ rsa_verify (gcry_sexp_t s_sig, gcry_sexp_t s_data, gcry_sexp_t keyparms) + log_printmpi ("rsa_verify e", pk.e); + } + ++ /* Check if use of the hash is compliant. */ ++ if (fips_mode ()) ++ { ++ /* SHA1 is approved hash function, but not for digital signature. */ ++ if (_gcry_md_algo_info (ctx.hash_algo, GCRYCTL_TEST_ALGO, NULL, NULL) ++ || ctx.hash_algo == GCRY_MD_SHA1) ++ { ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK_MD)) ++ { ++ rc = GPG_ERR_DIGEST_ALGO; ++ goto leave; ++ } ++ else ++ fips_service_indicator_mark_non_compliant (); ++ } ++ } ++ + /* Do RSA computation and compare. */ + result = mpi_new (0); + public (result, sig, &pk); +diff --git a/tests/t-fips-service-ind.c b/tests/t-fips-service-ind.c +index ed5f8d3f..bec6c27e 100644 +--- a/tests/t-fips-service-ind.c ++++ b/tests/t-fips-service-ind.c +@@ -231,7 +231,8 @@ check_pk_s_v (int reject) + const char *data; + int expect_failure; + } tv[] = { +- { ++ { /* Hashing is done externally, and feeded ++ to gcry_pk_sign, specifing the hash used */ + "(private-key (ecc (curve nistp256)" + " (d #519b423d715f8b581f4fa8ee59f4771a5b44c8130b4e3eacca54a56dda72b464#)))", + "(public-key (ecc (curve nistp256)" +@@ -271,6 +272,293 @@ check_pk_s_v (int reject) + "#00112233445566778899AABBCCDDEEFF00010203#))", + 1 + }, ++ { /* Hashing is done internally in ++ gcry_pk_sign with the hash-algo specified. */ ++ "(private-key\n" ++ " (ecc\n" ++ " (curve Ed25519)(flags eddsa)\n" ++ " (q #4014DB483F15527253B25B4C72BEA8BB70255029636BD71DBBCCD5D8BF48A35F17#)" ++ " (d #09A0C38E0F1699073541447C19DA12E3A07A7BFDB0C186E4AC5BCE6F23D55252#)" ++ "))", ++ "(public-key\n" ++ " (ecc\n" ++ " (curve Ed25519)(flags eddsa)\n" ++ " (q #4014DB483F15527253B25B4C72BEA8BB70255029636BD71DBBCCD5D8BF48A35F17#)" ++ "))", ++ "(data(flags eddsa)(hash-algo sha512)(value " ++ "#00112233445566778899AABBCCDDEEFF000102030405060708090A0B0C0D0E0F" ++ " 00112233445566778899AABBCCDDEEFF000102030405060708090A0B0C0D0E0F" ++ " 00112233445566778899AABBCCDDEEFF000102030405060708090A0B0C0D0E0F#))", ++ 0 ++ }, ++ { /* RSA with compliant hash for signing */ ++ "(private-key" ++ " (rsa" ++ " (n #009F56231A3D82E3E7D613D59D53E9AB921BEF9F08A782AED0B6E46ADBC853EC" ++ " 7C71C422435A3CD8FA0DB9EFD55CD3295BADC4E8E2E2B94E15AE82866AB8ADE8" ++ " 7E469FAE76DC3577DE87F1F419C4EB41123DFAF8D16922D5EDBAD6E9076D5A1C" ++ " 958106F0AE5E2E9193C6B49124C64C2A241C4075D4AF16299EB87A6585BAE917" ++ " DEF27FCDD165764D069BC18D16527B29DAAB549F7BBED4A7C6A842D203ED6613" ++ " 6E2411744E432CD26D940132F25874483DCAEECDFD95744819CBCF1EA810681C" ++ " 42907EBCB1C7EAFBE75C87EC32C5413EA10476545D3FC7B2ADB1B66B7F200918" ++ " 664B0E5261C2895AA28B0DE321E921B3F877172CCCAB81F43EF98002916156F6" ++ " CB#)\n" ++ " (e #010001#)\n" ++ " (d #07EF82500C403899934FE993AC5A36F14FF2DF38CF1EF315F205EE4C83EDAA19" ++ " 8890FC23DE9AA933CAFB37B6A8A8DBA675411958337287310D3FF2F1DDC0CB93" ++ " 7E70F57F75F833C021852B631D2B9A520E4431A03C5C3FCB5742DCD841D9FB12" ++ " 771AA1620DCEC3F1583426066ED9DC3F7028C5B59202C88FDF20396E2FA0EC4F" ++ " 5A22D9008F3043673931BC14A5046D6327398327900867E39CC61B2D1AFE2F48" ++ " EC8E1E3861C68D257D7425F4E6F99ABD77D61F10CA100EFC14389071831B33DD" ++ " 69CC8EABEF860D1DC2AAA84ABEAE5DFC91BC124DAF0F4C8EF5BBEA436751DE84" ++ " 3A8063E827A024466F44C28614F93B0732A100D4A0D86D532FE1E22C7725E401" ++ " #)\n" ++ " (p #00C29D438F115825779631CD665A5739367F3E128ADC29766483A46CA80897E0" ++ " 79B32881860B8F9A6A04C2614A904F6F2578DAE13EA67CD60AE3D0AA00A1FF9B" ++ " 441485E44B2DC3D0B60260FBFE073B5AC72FAF67964DE15C8212C389D20DB9CF" ++ " 54AF6AEF5C4196EAA56495DD30CF709F499D5AB30CA35E086C2A1589D6283F17" ++ " 83#)\n" ++ " (q #00D1984135231CB243FE959C0CBEF551EDD986AD7BEDF71EDF447BE3DA27AF46" ++ " 79C974A6FA69E4D52FE796650623DE70622862713932AA2FD9F2EC856EAEAA77" ++ " 88B4EA6084DC81C902F014829B18EA8B2666EC41586818E0589E18876065F97E" ++ " 8D22CE2DA53A05951EC132DCEF41E70A9C35F4ACC268FFAC2ADF54FA1DA110B9" ++ " 19#)\n" ++ " (u #67CF0FD7635205DD80FA814EE9E9C267C17376BF3209FB5D1BC42890D2822A04" ++ " 479DAF4D5B6ED69D0F8D1AF94164D07F8CD52ECEFE880641FA0F41DDAB1785E4" ++ " A37A32F997A516480B4CD4F6482B9466A1765093ED95023CA32D5EDC1E34CEE9" ++ " AF595BC51FE43C4BF810FA225AF697FB473B83815966188A4312C048B885E3F7" ++ " #)))\n", ++ "(public-key\n" ++ " (rsa\n" ++ " (n #009F56231A3D82E3E7D613D59D53E9AB921BEF9F08A782AED0B6E46ADBC853EC" ++ " 7C71C422435A3CD8FA0DB9EFD55CD3295BADC4E8E2E2B94E15AE82866AB8ADE8" ++ " 7E469FAE76DC3577DE87F1F419C4EB41123DFAF8D16922D5EDBAD6E9076D5A1C" ++ " 958106F0AE5E2E9193C6B49124C64C2A241C4075D4AF16299EB87A6585BAE917" ++ " DEF27FCDD165764D069BC18D16527B29DAAB549F7BBED4A7C6A842D203ED6613" ++ " 6E2411744E432CD26D940132F25874483DCAEECDFD95744819CBCF1EA810681C" ++ " 42907EBCB1C7EAFBE75C87EC32C5413EA10476545D3FC7B2ADB1B66B7F200918" ++ " 664B0E5261C2895AA28B0DE321E921B3F877172CCCAB81F43EF98002916156F6" ++ " CB#)\n" ++ " (e #010001#)))\n", ++ "(data\n (flags pkcs1)\n" ++ " (hash sha256 " ++ "#00112233445566778899AABBCCDDEEFF000102030405060708090A0B0C0D0E0F#))\n", ++ 0 ++ }, ++ { /* RSA with non-compliant hash for signing */ ++ "(private-key" ++ " (rsa" ++ " (n #009F56231A3D82E3E7D613D59D53E9AB921BEF9F08A782AED0B6E46ADBC853EC" ++ " 7C71C422435A3CD8FA0DB9EFD55CD3295BADC4E8E2E2B94E15AE82866AB8ADE8" ++ " 7E469FAE76DC3577DE87F1F419C4EB41123DFAF8D16922D5EDBAD6E9076D5A1C" ++ " 958106F0AE5E2E9193C6B49124C64C2A241C4075D4AF16299EB87A6585BAE917" ++ " DEF27FCDD165764D069BC18D16527B29DAAB549F7BBED4A7C6A842D203ED6613" ++ " 6E2411744E432CD26D940132F25874483DCAEECDFD95744819CBCF1EA810681C" ++ " 42907EBCB1C7EAFBE75C87EC32C5413EA10476545D3FC7B2ADB1B66B7F200918" ++ " 664B0E5261C2895AA28B0DE321E921B3F877172CCCAB81F43EF98002916156F6" ++ " CB#)\n" ++ " (e #010001#)\n" ++ " (d #07EF82500C403899934FE993AC5A36F14FF2DF38CF1EF315F205EE4C83EDAA19" ++ " 8890FC23DE9AA933CAFB37B6A8A8DBA675411958337287310D3FF2F1DDC0CB93" ++ " 7E70F57F75F833C021852B631D2B9A520E4431A03C5C3FCB5742DCD841D9FB12" ++ " 771AA1620DCEC3F1583426066ED9DC3F7028C5B59202C88FDF20396E2FA0EC4F" ++ " 5A22D9008F3043673931BC14A5046D6327398327900867E39CC61B2D1AFE2F48" ++ " EC8E1E3861C68D257D7425F4E6F99ABD77D61F10CA100EFC14389071831B33DD" ++ " 69CC8EABEF860D1DC2AAA84ABEAE5DFC91BC124DAF0F4C8EF5BBEA436751DE84" ++ " 3A8063E827A024466F44C28614F93B0732A100D4A0D86D532FE1E22C7725E401" ++ " #)\n" ++ " (p #00C29D438F115825779631CD665A5739367F3E128ADC29766483A46CA80897E0" ++ " 79B32881860B8F9A6A04C2614A904F6F2578DAE13EA67CD60AE3D0AA00A1FF9B" ++ " 441485E44B2DC3D0B60260FBFE073B5AC72FAF67964DE15C8212C389D20DB9CF" ++ " 54AF6AEF5C4196EAA56495DD30CF709F499D5AB30CA35E086C2A1589D6283F17" ++ " 83#)\n" ++ " (q #00D1984135231CB243FE959C0CBEF551EDD986AD7BEDF71EDF447BE3DA27AF46" ++ " 79C974A6FA69E4D52FE796650623DE70622862713932AA2FD9F2EC856EAEAA77" ++ " 88B4EA6084DC81C902F014829B18EA8B2666EC41586818E0589E18876065F97E" ++ " 8D22CE2DA53A05951EC132DCEF41E70A9C35F4ACC268FFAC2ADF54FA1DA110B9" ++ " 19#)\n" ++ " (u #67CF0FD7635205DD80FA814EE9E9C267C17376BF3209FB5D1BC42890D2822A04" ++ " 479DAF4D5B6ED69D0F8D1AF94164D07F8CD52ECEFE880641FA0F41DDAB1785E4" ++ " A37A32F997A516480B4CD4F6482B9466A1765093ED95023CA32D5EDC1E34CEE9" ++ " AF595BC51FE43C4BF810FA225AF697FB473B83815966188A4312C048B885E3F7" ++ " #)))\n", ++ "(public-key\n" ++ " (rsa\n" ++ " (n #009F56231A3D82E3E7D613D59D53E9AB921BEF9F08A782AED0B6E46ADBC853EC" ++ " 7C71C422435A3CD8FA0DB9EFD55CD3295BADC4E8E2E2B94E15AE82866AB8ADE8" ++ " 7E469FAE76DC3577DE87F1F419C4EB41123DFAF8D16922D5EDBAD6E9076D5A1C" ++ " 958106F0AE5E2E9193C6B49124C64C2A241C4075D4AF16299EB87A6585BAE917" ++ " DEF27FCDD165764D069BC18D16527B29DAAB549F7BBED4A7C6A842D203ED6613" ++ " 6E2411744E432CD26D940132F25874483DCAEECDFD95744819CBCF1EA810681C" ++ " 42907EBCB1C7EAFBE75C87EC32C5413EA10476545D3FC7B2ADB1B66B7F200918" ++ " 664B0E5261C2895AA28B0DE321E921B3F877172CCCAB81F43EF98002916156F6" ++ " CB#)\n" ++ " (e #010001#)))\n", ++ "(data\n (flags pkcs1)\n" ++ " (hash sha1 #11223344556677889900AABBCCDDEEFF10203040#))\n", ++ 1 ++ }, ++ { /* RSA with unknown hash for signing */ ++ "(private-key" ++ " (rsa" ++ " (n #009F56231A3D82E3E7D613D59D53E9AB921BEF9F08A782AED0B6E46ADBC853EC" ++ " 7C71C422435A3CD8FA0DB9EFD55CD3295BADC4E8E2E2B94E15AE82866AB8ADE8" ++ " 7E469FAE76DC3577DE87F1F419C4EB41123DFAF8D16922D5EDBAD6E9076D5A1C" ++ " 958106F0AE5E2E9193C6B49124C64C2A241C4075D4AF16299EB87A6585BAE917" ++ " DEF27FCDD165764D069BC18D16527B29DAAB549F7BBED4A7C6A842D203ED6613" ++ " 6E2411744E432CD26D940132F25874483DCAEECDFD95744819CBCF1EA810681C" ++ " 42907EBCB1C7EAFBE75C87EC32C5413EA10476545D3FC7B2ADB1B66B7F200918" ++ " 664B0E5261C2895AA28B0DE321E921B3F877172CCCAB81F43EF98002916156F6" ++ " CB#)\n" ++ " (e #010001#)\n" ++ " (d #07EF82500C403899934FE993AC5A36F14FF2DF38CF1EF315F205EE4C83EDAA19" ++ " 8890FC23DE9AA933CAFB37B6A8A8DBA675411958337287310D3FF2F1DDC0CB93" ++ " 7E70F57F75F833C021852B631D2B9A520E4431A03C5C3FCB5742DCD841D9FB12" ++ " 771AA1620DCEC3F1583426066ED9DC3F7028C5B59202C88FDF20396E2FA0EC4F" ++ " 5A22D9008F3043673931BC14A5046D6327398327900867E39CC61B2D1AFE2F48" ++ " EC8E1E3861C68D257D7425F4E6F99ABD77D61F10CA100EFC14389071831B33DD" ++ " 69CC8EABEF860D1DC2AAA84ABEAE5DFC91BC124DAF0F4C8EF5BBEA436751DE84" ++ " 3A8063E827A024466F44C28614F93B0732A100D4A0D86D532FE1E22C7725E401" ++ " #)\n" ++ " (p #00C29D438F115825779631CD665A5739367F3E128ADC29766483A46CA80897E0" ++ " 79B32881860B8F9A6A04C2614A904F6F2578DAE13EA67CD60AE3D0AA00A1FF9B" ++ " 441485E44B2DC3D0B60260FBFE073B5AC72FAF67964DE15C8212C389D20DB9CF" ++ " 54AF6AEF5C4196EAA56495DD30CF709F499D5AB30CA35E086C2A1589D6283F17" ++ " 83#)\n" ++ " (q #00D1984135231CB243FE959C0CBEF551EDD986AD7BEDF71EDF447BE3DA27AF46" ++ " 79C974A6FA69E4D52FE796650623DE70622862713932AA2FD9F2EC856EAEAA77" ++ " 88B4EA6084DC81C902F014829B18EA8B2666EC41586818E0589E18876065F97E" ++ " 8D22CE2DA53A05951EC132DCEF41E70A9C35F4ACC268FFAC2ADF54FA1DA110B9" ++ " 19#)\n" ++ " (u #67CF0FD7635205DD80FA814EE9E9C267C17376BF3209FB5D1BC42890D2822A04" ++ " 479DAF4D5B6ED69D0F8D1AF94164D07F8CD52ECEFE880641FA0F41DDAB1785E4" ++ " A37A32F997A516480B4CD4F6482B9466A1765093ED95023CA32D5EDC1E34CEE9" ++ " AF595BC51FE43C4BF810FA225AF697FB473B83815966188A4312C048B885E3F7" ++ " #)))\n", ++ "(public-key\n" ++ " (rsa\n" ++ " (n #009F56231A3D82E3E7D613D59D53E9AB921BEF9F08A782AED0B6E46ADBC853EC" ++ " 7C71C422435A3CD8FA0DB9EFD55CD3295BADC4E8E2E2B94E15AE82866AB8ADE8" ++ " 7E469FAE76DC3577DE87F1F419C4EB41123DFAF8D16922D5EDBAD6E9076D5A1C" ++ " 958106F0AE5E2E9193C6B49124C64C2A241C4075D4AF16299EB87A6585BAE917" ++ " DEF27FCDD165764D069BC18D16527B29DAAB549F7BBED4A7C6A842D203ED6613" ++ " 6E2411744E432CD26D940132F25874483DCAEECDFD95744819CBCF1EA810681C" ++ " 42907EBCB1C7EAFBE75C87EC32C5413EA10476545D3FC7B2ADB1B66B7F200918" ++ " 664B0E5261C2895AA28B0DE321E921B3F877172CCCAB81F43EF98002916156F6" ++ " CB#)\n" ++ " (e #010001#)))\n", ++ "(data\n (flags pkcs1-raw)\n" ++ " (value " ++ "#00112233445566778899AABBCCDDEEFF000102030405060708090A0B0C0D0E0F#))\n", ++ 1 ++ }, ++ { /* RSA with compliant hash for signing */ ++ "(private-key" ++ " (rsa" ++ " (n #009F56231A3D82E3E7D613D59D53E9AB921BEF9F08A782AED0B6E46ADBC853EC" ++ " 7C71C422435A3CD8FA0DB9EFD55CD3295BADC4E8E2E2B94E15AE82866AB8ADE8" ++ " 7E469FAE76DC3577DE87F1F419C4EB41123DFAF8D16922D5EDBAD6E9076D5A1C" ++ " 958106F0AE5E2E9193C6B49124C64C2A241C4075D4AF16299EB87A6585BAE917" ++ " DEF27FCDD165764D069BC18D16527B29DAAB549F7BBED4A7C6A842D203ED6613" ++ " 6E2411744E432CD26D940132F25874483DCAEECDFD95744819CBCF1EA810681C" ++ " 42907EBCB1C7EAFBE75C87EC32C5413EA10476545D3FC7B2ADB1B66B7F200918" ++ " 664B0E5261C2895AA28B0DE321E921B3F877172CCCAB81F43EF98002916156F6" ++ " CB#)\n" ++ " (e #010001#)\n" ++ " (d #07EF82500C403899934FE993AC5A36F14FF2DF38CF1EF315F205EE4C83EDAA19" ++ " 8890FC23DE9AA933CAFB37B6A8A8DBA675411958337287310D3FF2F1DDC0CB93" ++ " 7E70F57F75F833C021852B631D2B9A520E4431A03C5C3FCB5742DCD841D9FB12" ++ " 771AA1620DCEC3F1583426066ED9DC3F7028C5B59202C88FDF20396E2FA0EC4F" ++ " 5A22D9008F3043673931BC14A5046D6327398327900867E39CC61B2D1AFE2F48" ++ " EC8E1E3861C68D257D7425F4E6F99ABD77D61F10CA100EFC14389071831B33DD" ++ " 69CC8EABEF860D1DC2AAA84ABEAE5DFC91BC124DAF0F4C8EF5BBEA436751DE84" ++ " 3A8063E827A024466F44C28614F93B0732A100D4A0D86D532FE1E22C7725E401" ++ " #)\n" ++ " (p #00C29D438F115825779631CD665A5739367F3E128ADC29766483A46CA80897E0" ++ " 79B32881860B8F9A6A04C2614A904F6F2578DAE13EA67CD60AE3D0AA00A1FF9B" ++ " 441485E44B2DC3D0B60260FBFE073B5AC72FAF67964DE15C8212C389D20DB9CF" ++ " 54AF6AEF5C4196EAA56495DD30CF709F499D5AB30CA35E086C2A1589D6283F17" ++ " 83#)\n" ++ " (q #00D1984135231CB243FE959C0CBEF551EDD986AD7BEDF71EDF447BE3DA27AF46" ++ " 79C974A6FA69E4D52FE796650623DE70622862713932AA2FD9F2EC856EAEAA77" ++ " 88B4EA6084DC81C902F014829B18EA8B2666EC41586818E0589E18876065F97E" ++ " 8D22CE2DA53A05951EC132DCEF41E70A9C35F4ACC268FFAC2ADF54FA1DA110B9" ++ " 19#)\n" ++ " (u #67CF0FD7635205DD80FA814EE9E9C267C17376BF3209FB5D1BC42890D2822A04" ++ " 479DAF4D5B6ED69D0F8D1AF94164D07F8CD52ECEFE880641FA0F41DDAB1785E4" ++ " A37A32F997A516480B4CD4F6482B9466A1765093ED95023CA32D5EDC1E34CEE9" ++ " AF595BC51FE43C4BF810FA225AF697FB473B83815966188A4312C048B885E3F7" ++ " #)))\n", ++ "(public-key\n" ++ " (rsa\n" ++ " (n #009F56231A3D82E3E7D613D59D53E9AB921BEF9F08A782AED0B6E46ADBC853EC" ++ " 7C71C422435A3CD8FA0DB9EFD55CD3295BADC4E8E2E2B94E15AE82866AB8ADE8" ++ " 7E469FAE76DC3577DE87F1F419C4EB41123DFAF8D16922D5EDBAD6E9076D5A1C" ++ " 958106F0AE5E2E9193C6B49124C64C2A241C4075D4AF16299EB87A6585BAE917" ++ " DEF27FCDD165764D069BC18D16527B29DAAB549F7BBED4A7C6A842D203ED6613" ++ " 6E2411744E432CD26D940132F25874483DCAEECDFD95744819CBCF1EA810681C" ++ " 42907EBCB1C7EAFBE75C87EC32C5413EA10476545D3FC7B2ADB1B66B7F200918" ++ " 664B0E5261C2895AA28B0DE321E921B3F877172CCCAB81F43EF98002916156F6" ++ " CB#)\n" ++ " (e #010001#)))\n", ++ "(data\n (flags pss)\n" ++ " (hash sha256 " ++ "#00112233445566778899AABBCCDDEEFF000102030405060708090A0B0C0D0E0F#))\n", ++ 0 ++ }, ++ { /* RSA with non-compliant hash for signing */ ++ "(private-key" ++ " (rsa" ++ " (n #009F56231A3D82E3E7D613D59D53E9AB921BEF9F08A782AED0B6E46ADBC853EC" ++ " 7C71C422435A3CD8FA0DB9EFD55CD3295BADC4E8E2E2B94E15AE82866AB8ADE8" ++ " 7E469FAE76DC3577DE87F1F419C4EB41123DFAF8D16922D5EDBAD6E9076D5A1C" ++ " 958106F0AE5E2E9193C6B49124C64C2A241C4075D4AF16299EB87A6585BAE917" ++ " DEF27FCDD165764D069BC18D16527B29DAAB549F7BBED4A7C6A842D203ED6613" ++ " 6E2411744E432CD26D940132F25874483DCAEECDFD95744819CBCF1EA810681C" ++ " 42907EBCB1C7EAFBE75C87EC32C5413EA10476545D3FC7B2ADB1B66B7F200918" ++ " 664B0E5261C2895AA28B0DE321E921B3F877172CCCAB81F43EF98002916156F6" ++ " CB#)\n" ++ " (e #010001#)\n" ++ " (d #07EF82500C403899934FE993AC5A36F14FF2DF38CF1EF315F205EE4C83EDAA19" ++ " 8890FC23DE9AA933CAFB37B6A8A8DBA675411958337287310D3FF2F1DDC0CB93" ++ " 7E70F57F75F833C021852B631D2B9A520E4431A03C5C3FCB5742DCD841D9FB12" ++ " 771AA1620DCEC3F1583426066ED9DC3F7028C5B59202C88FDF20396E2FA0EC4F" ++ " 5A22D9008F3043673931BC14A5046D6327398327900867E39CC61B2D1AFE2F48" ++ " EC8E1E3861C68D257D7425F4E6F99ABD77D61F10CA100EFC14389071831B33DD" ++ " 69CC8EABEF860D1DC2AAA84ABEAE5DFC91BC124DAF0F4C8EF5BBEA436751DE84" ++ " 3A8063E827A024466F44C28614F93B0732A100D4A0D86D532FE1E22C7725E401" ++ " #)\n" ++ " (p #00C29D438F115825779631CD665A5739367F3E128ADC29766483A46CA80897E0" ++ " 79B32881860B8F9A6A04C2614A904F6F2578DAE13EA67CD60AE3D0AA00A1FF9B" ++ " 441485E44B2DC3D0B60260FBFE073B5AC72FAF67964DE15C8212C389D20DB9CF" ++ " 54AF6AEF5C4196EAA56495DD30CF709F499D5AB30CA35E086C2A1589D6283F17" ++ " 83#)\n" ++ " (q #00D1984135231CB243FE959C0CBEF551EDD986AD7BEDF71EDF447BE3DA27AF46" ++ " 79C974A6FA69E4D52FE796650623DE70622862713932AA2FD9F2EC856EAEAA77" ++ " 88B4EA6084DC81C902F014829B18EA8B2666EC41586818E0589E18876065F97E" ++ " 8D22CE2DA53A05951EC132DCEF41E70A9C35F4ACC268FFAC2ADF54FA1DA110B9" ++ " 19#)\n" ++ " (u #67CF0FD7635205DD80FA814EE9E9C267C17376BF3209FB5D1BC42890D2822A04" ++ " 479DAF4D5B6ED69D0F8D1AF94164D07F8CD52ECEFE880641FA0F41DDAB1785E4" ++ " A37A32F997A516480B4CD4F6482B9466A1765093ED95023CA32D5EDC1E34CEE9" ++ " AF595BC51FE43C4BF810FA225AF697FB473B83815966188A4312C048B885E3F7" ++ " #)))\n", ++ "(public-key\n" ++ " (rsa\n" ++ " (n #009F56231A3D82E3E7D613D59D53E9AB921BEF9F08A782AED0B6E46ADBC853EC" ++ " 7C71C422435A3CD8FA0DB9EFD55CD3295BADC4E8E2E2B94E15AE82866AB8ADE8" ++ " 7E469FAE76DC3577DE87F1F419C4EB41123DFAF8D16922D5EDBAD6E9076D5A1C" ++ " 958106F0AE5E2E9193C6B49124C64C2A241C4075D4AF16299EB87A6585BAE917" ++ " DEF27FCDD165764D069BC18D16527B29DAAB549F7BBED4A7C6A842D203ED6613" ++ " 6E2411744E432CD26D940132F25874483DCAEECDFD95744819CBCF1EA810681C" ++ " 42907EBCB1C7EAFBE75C87EC32C5413EA10476545D3FC7B2ADB1B66B7F200918" ++ " 664B0E5261C2895AA28B0DE321E921B3F877172CCCAB81F43EF98002916156F6" ++ " CB#)\n" ++ " (e #010001#)))\n", ++ "(data\n (flags pss)\n" ++ " (hash sha1 #11223344556677889900AABBCCDDEEFF10203040#))\n", ++ 1 ++ } + }; + int tvidx; + gpg_error_t err; +-- +2.49.0 + diff --git a/libgcrypt-cipher-visibility-Differentiate-use-of-random-override-in-the-SLI.patch b/libgcrypt-cipher-visibility-Differentiate-use-of-random-override-in-the-SLI.patch new file mode 100644 index 0000000..413aa34 --- /dev/null +++ b/libgcrypt-cipher-visibility-Differentiate-use-of-random-override-in-the-SLI.patch @@ -0,0 +1,107 @@ +From 234eb316b0a04c50e8511a570775ded45060f18b Mon Sep 17 00:00:00 2001 +From: Lucas Mulling via Gcrypt-devel +Date: Wed, 26 Feb 2025 17:19:24 -0300 +Subject: [PATCH 08/14] cipher,visibility: Differentiate use of random-override + in the SLI +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* cipher/pubkey-util.c (_gcry_pk_util_data_to_mpi, +_gcry_pk_single_data_push, _gcry_pk_util_free_encoding_ctx): +Differentiate use of random-override in the SLI. +* src/visibility.c (gcry_pk_random_override_new): +Differentiate use explicit random override in the SLI. + +GnuPG-bug-id: 7338 +Signed-off-by: Lucas Mulling +Signed-off-by: Lucas Mülling +--- + cipher/pubkey-util.c | 33 +++++++++++++++++++++++++++++++++ + src/visibility.c | 12 ++++++++++++ + 2 files changed, 45 insertions(+) + +diff --git a/cipher/pubkey-util.c b/cipher/pubkey-util.c +index e7355569..66a04f13 100644 +--- a/cipher/pubkey-util.c ++++ b/cipher/pubkey-util.c +@@ -973,6 +973,17 @@ _gcry_pk_util_data_to_mpi (gcry_sexp_t input, gcry_mpi_t *ret_mpi, + list = sexp_find_token (ldata, "random-override", 0); + if (list) + { ++ if (fips_mode ()) ++ { ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) ++ { ++ sexp_release (list); ++ rc = GPG_ERR_INV_FLAG; ++ goto leave; ++ } ++ else ++ fips_service_indicator_mark_non_compliant (); ++ } + s = sexp_nth_data (list, 1, &n); + if (!s) + rc = GPG_ERR_NO_OBJ; +@@ -1149,6 +1160,17 @@ _gcry_pk_util_data_to_mpi (gcry_sexp_t input, gcry_mpi_t *ret_mpi, + list = sexp_find_token (ldata, "random-override", 0); + if (list) + { ++ if (fips_mode ()) ++ { ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) ++ { ++ sexp_release (list); ++ rc = GPG_ERR_INV_FLAG; ++ goto leave; ++ } ++ else ++ fips_service_indicator_mark_non_compliant (); ++ } + s = sexp_nth_data (list, 1, &n); + if (!s) + rc = GPG_ERR_NO_OBJ; +@@ -1248,6 +1270,17 @@ _gcry_pk_util_data_to_mpi (gcry_sexp_t input, gcry_mpi_t *ret_mpi, + list = sexp_find_token (ldata, "random-override", 0); + if (list) + { ++ if (fips_mode ()) ++ { ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) ++ { ++ sexp_release (list); ++ rc = GPG_ERR_INV_FLAG; ++ goto leave; ++ } ++ else ++ fips_service_indicator_mark_non_compliant (); ++ } + s = sexp_nth_data (list, 1, &n); + if (!s) + rc = GPG_ERR_NO_OBJ; +diff --git a/src/visibility.c b/src/visibility.c +index 4134446a..ccd0de69 100644 +--- a/src/visibility.c ++++ b/src/visibility.c +@@ -1085,6 +1085,18 @@ gcry_pk_hash_verify (gcry_sexp_t sigval, const char *data_tmpl, gcry_sexp_t pkey + gcry_error_t + gcry_pk_random_override_new (gcry_ctx_t *r_ctx, const unsigned char *p, size_t len) + { ++ if (!fips_is_operational ()) ++ return gpg_error (fips_not_operational ()); ++ fips_service_indicator_init (); ++ ++ if (fips_mode ()) ++ { ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) ++ return gpg_error (GPG_ERR_INV_OP); ++ else ++ fips_service_indicator_mark_non_compliant (); ++ } ++ + return gpg_error (_gcry_pk_single_data_push (r_ctx, p, len)); + } + +-- +2.49.0 + diff --git a/libgcrypt-doc-Add-about-GCRYCTL_FIPS_SERVICE_INDICATOR.patch b/libgcrypt-doc-Add-about-GCRYCTL_FIPS_SERVICE_INDICATOR.patch new file mode 100644 index 0000000..a9e9522 --- /dev/null +++ b/libgcrypt-doc-Add-about-GCRYCTL_FIPS_SERVICE_INDICATOR.patch @@ -0,0 +1,66 @@ +From 636f40cb78587635ef663bfc3430937cf140f245 Mon Sep 17 00:00:00 2001 +From: NIIBE Yutaka +Date: Thu, 13 Mar 2025 15:02:58 +0900 +Subject: [PATCH 13/14] doc: Add about GCRYCTL_FIPS_SERVICE_INDICATOR. +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* doc/gcrypt.texi (GCRYCTL_FIPS_SERVICE_INDICATOR): Add a description. +(GCRYCTL_FIPS_REJECT_NON_FIPS): Likewise. + +-- + +GnuPG-bug-id: 7338 +Signed-off-by: NIIBE Yutaka +Signed-off-by: Lucas Mülling +--- + doc/gcrypt.texi | 32 ++++++++++++++++++++++++++++++++ + 1 file changed, 32 insertions(+) + +diff --git a/doc/gcrypt.texi b/doc/gcrypt.texi +index 5d428738..6e82a41b 100644 +--- a/doc/gcrypt.texi ++++ b/doc/gcrypt.texi +@@ -1052,6 +1052,38 @@ is responsible to check also the internal members. For example: + /* ok */ + @end example + ++@item GCRYCTL_FIPS_SERVICE_INDICATOR; Arguments: none ++This commands provides ``dynamic'' service indicator. ++ ++After a function call (of the use of security services), this command ++can be used to check if the call is valid or not. If the computation ++is done in an approved way, it returns @code{GPG_ERR_NO_ERROR}. ++Otherwise @code{GPG_ERR_NOT_SUPPORTED} is returned. ++ ++An application may use this command directly or use the convenience ++macro below. ++ ++@deftypefun gcry_error_t gcry_get_fips_service_indicator (void) ++ ++Returns @code{GPG_ERR_NO_ERROR} if a preceeding function call is ++valid. Otherwise @code{GPG_ERR_NOT_SUPPORTED} is returned. ++@end deftypefun ++ ++@item GCRYCTL_FIPS_REJECT_NON_FIPS; Arguments: unsigned int flags ++In Libgcrypt 1.10, static implicit indicator is used; For an approved ++function (which can be checked by ++GCRYCTL_FIPS_SERVICE_INDICATOR_FUNCTION command) with an approved ++algo/operation (which can be checked GCRYCTL_FIPS_SERVICE_INDICATOR_* ++command), success of the function call means that it's valid and error ++return (rejection) means it's invalid. This command controls thread ++specific behavior of the rejection. ++ ++When using ``dynamic'' service indicator, this command with FLAGS=0 ++disables all rejections. ++@example ++ gcry_control (GCRYCTL_FIPS_REJECT_NON_FIPS, 0); ++@endexample ++ + @end table + + @end deftypefun +-- +2.49.0 + diff --git a/libgcrypt-doc-Fix-syntax-error.patch b/libgcrypt-doc-Fix-syntax-error.patch new file mode 100644 index 0000000..b85eb54 --- /dev/null +++ b/libgcrypt-doc-Fix-syntax-error.patch @@ -0,0 +1,31 @@ +From 22e65f6f5b8dbddf925151894426e4c06d33803b Mon Sep 17 00:00:00 2001 +From: Werner Koch +Date: Thu, 13 Mar 2025 18:06:37 +0100 +Subject: [PATCH 14/14] doc: Fix syntax error +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +-- + +Signed-off-by: Lucas Mülling +--- + doc/gcrypt.texi | 2 +- + 1 file changed, 1 insertion(+), 1 deletion(-) + +diff --git a/doc/gcrypt.texi b/doc/gcrypt.texi +index 6e82a41b..eeab1a78 100644 +--- a/doc/gcrypt.texi ++++ b/doc/gcrypt.texi +@@ -1082,7 +1082,7 @@ When using ``dynamic'' service indicator, this command with FLAGS=0 + disables all rejections. + @example + gcry_control (GCRYCTL_FIPS_REJECT_NON_FIPS, 0); +-@endexample ++@end example + + @end table + +-- +2.49.0 + diff --git a/libgcrypt-fips-Change-the-internal-API-for-new-FIPS-service-indicator.patch b/libgcrypt-fips-Change-the-internal-API-for-new-FIPS-service-indicator.patch new file mode 100644 index 0000000..8638218 --- /dev/null +++ b/libgcrypt-fips-Change-the-internal-API-for-new-FIPS-service-indicator.patch @@ -0,0 +1,140 @@ +From 4799914966a7f94f41e1ed5b7b62fded7ba09704 Mon Sep 17 00:00:00 2001 +From: NIIBE Yutaka +Date: Thu, 12 Dec 2024 11:03:38 +0900 +Subject: [PATCH 01/19] fips: Change the internal API for new FIPS service + indicator. +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* src/gcrypt-int.h (fips_service_indicator_init): Initialize by 0. +(fips_service_indicator_mark_success): Remove. +(fips_service_indicator_mark_non_compliant): New. +* cipher/kdf.c (_gcry_kdf_derive): Follow the change of the API. +* cipher/md.c (_gcry_md_hash_buffer): Likewise. +(_gcry_md_hash_buffers_extract): Likewise. + +-- + +GnuPG-bug-id: 7338 +Signed-off-by: NIIBE Yutaka +Signed-off-by: Lucas Mülling +--- + cipher/kdf.c | 17 +++++++++-------- + cipher/md.c | 8 ++++---- + src/gcrypt-int.h | 9 +++------ + 3 files changed, 16 insertions(+), 18 deletions(-) + +diff --git a/cipher/kdf.c b/cipher/kdf.c +index 1eae2b90..71156ea4 100644 +--- a/cipher/kdf.c ++++ b/cipher/kdf.c +@@ -248,6 +248,7 @@ _gcry_kdf_derive (const void *passphrase, size_t passphraselen, + size_t keysize, void *keybuffer) + { + gpg_err_code_t ec; ++ int is_compliant_algo = 0; + + if (!passphrase) + { +@@ -279,35 +280,32 @@ _gcry_kdf_derive (const void *passphrase, size_t passphraselen, + break; + + case GCRY_KDF_PBKDF2: ++ is_compliant_algo = 1; + if (!saltlen || !iterations) + ec = GPG_ERR_INV_VALUE; + else + { +- int is_compliant = 1; +- + if (fips_mode ()) + { + /* FIPS requires minimum passphrase length, see FIPS 140-3 IG D.N */ + if (passphraselen < 8) +- is_compliant &= 0; ++ fips_service_indicator_mark_non_compliant (); + + /* FIPS requires minimum salt length of 128 b (SP 800-132 sec. 5.1, p.6) */ + if (saltlen < 16) +- is_compliant &= 0; ++ fips_service_indicator_mark_non_compliant (); + + /* FIPS requires minimum iterations bound (SP 800-132 sec 5.2, p.6) */ + if (iterations < 1000) +- is_compliant &= 0; ++ fips_service_indicator_mark_non_compliant (); + + /* Check minimum key size */ + if (keysize < 14) +- is_compliant &= 0; ++ fips_service_indicator_mark_non_compliant (); + } + + ec = _gcry_kdf_pkdf2 (passphrase, passphraselen, subalgo, + salt, saltlen, iterations, keysize, keybuffer); +- if (!ec) +- fips_service_indicator_mark_success (is_compliant); + } + break; + +@@ -326,6 +324,9 @@ _gcry_kdf_derive (const void *passphrase, size_t passphraselen, + break; + } + ++ if (!ec && !is_compliant_algo && fips_mode ()) ++ fips_service_indicator_mark_non_compliant (); ++ + leave: + return ec; + } +diff --git a/cipher/md.c b/cipher/md.c +index c2bd18c6..ef2fc5a4 100644 +--- a/cipher/md.c ++++ b/cipher/md.c +@@ -1286,8 +1286,8 @@ _gcry_md_hash_buffer (int algo, void *digest, + + if (fips_mode ()) + { +- int is_compliant = spec->flags.fips; +- fips_service_indicator_mark_success (is_compliant); ++ if (!spec->flags.fips) ++ fips_service_indicator_mark_non_compliant (); + } + } + +@@ -1384,8 +1384,8 @@ _gcry_md_hash_buffers_extract (int algo, unsigned int flags, void *digest, + + if (fips_mode ()) + { +- int is_compliant = spec->flags.fips; +- fips_service_indicator_mark_success (is_compliant); ++ if (!spec->flags.fips) ++ fips_service_indicator_mark_non_compliant (); + } + + return 0; +diff --git a/src/gcrypt-int.h b/src/gcrypt-int.h +index 7f894737..aa49d766 100644 +--- a/src/gcrypt-int.h ++++ b/src/gcrypt-int.h +@@ -303,13 +303,10 @@ unsigned long _gcry_thread_context_get_fsi (void); + #define fips_service_indicator_init() do \ + { \ + if (fips_mode ()) \ +- _gcry_thread_context_set_fsi (1); \ +- } while (0) +-#define fips_service_indicator_mark_success(is_compliant) do \ +- { \ +- if (is_compliant && fips_mode ()) \ +- _gcry_thread_context_set_fsi (0); \ ++ _gcry_thread_context_set_fsi (0); \ + } while (0) ++/* Should be used only when fips_mode()==TRUE. */ ++#define fips_service_indicator_mark_non_compliant() _gcry_thread_context_set_fsi (1) + + /* Return a pointer to a string containing a description of the error + code in the error value ERR. */ +-- +2.49.0 + diff --git a/libgcrypt-fips-Fix-GCRY_FIPS_FLAG_REJECT_MD.patch b/libgcrypt-fips-Fix-GCRY_FIPS_FLAG_REJECT_MD.patch new file mode 100644 index 0000000..aa6f093 --- /dev/null +++ b/libgcrypt-fips-Fix-GCRY_FIPS_FLAG_REJECT_MD.patch @@ -0,0 +1,42 @@ +From b9eb8f4cb81801d68580627ad2188607a8c5f2ec Mon Sep 17 00:00:00 2001 +From: NIIBE Yutaka +Date: Thu, 13 Mar 2025 15:01:21 +0900 +Subject: [PATCH 12/14] fips: Fix GCRY_FIPS_FLAG_REJECT_MD. +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* src/gcrypt.h.in (GCRY_FIPS_FLAG_REJECT_MD): Include SHA1. + +-- + +Fixes-commit: 4ee91a94bcdad32aed4364d09e3daf8841fa579f +Signed-off-by: NIIBE Yutaka +Signed-off-by: Lucas Mülling +--- + src/gcrypt.h.in | 8 +++++--- + 1 file changed, 5 insertions(+), 3 deletions(-) + +diff --git a/src/gcrypt.h.in b/src/gcrypt.h.in +index b2b8853f..a9c36aa6 100644 +--- a/src/gcrypt.h.in ++++ b/src/gcrypt.h.in +@@ -1994,10 +1994,12 @@ char *gcry_get_config (int mode, const char *what); + #define GCRY_FIPS_FLAG_REJECT_PK_ECC_K (1 << 10) + #define GCRY_FIPS_FLAG_REJECT_PK_FLAGS (1 << 11) + +-#define GCRY_FIPS_FLAG_REJECT_MD \ +- (GCRY_FIPS_FLAG_REJECT_MD_MD5 | GCRY_FIPS_FLAG_REJECT_MD_OTHERS) ++#define GCRY_FIPS_FLAG_REJECT_MD \ ++ (GCRY_FIPS_FLAG_REJECT_MD_MD5 | GCRY_FIPS_FLAG_REJECT_MD_SHA1 \ ++ | GCRY_FIPS_FLAG_REJECT_MD_OTHERS) + +-/* Note: Don't reject MD5, PK MD, PK GOST, PK SM2, PK ECC K, and PK FLAGS */ ++/* Note: Don't reject MD5, PK MD, PK GOST, PK SM2, ++ SHA1, PK ECC K, and PK FLAGS */ + #define GCRY_FIPS_FLAG_REJECT_COMPAT110 \ + (GCRY_FIPS_FLAG_REJECT_MD_OTHERS \ + | GCRY_FIPS_FLAG_REJECT_MAC \ +-- +2.49.0 + diff --git a/libgcrypt-fips-Introduce-GCRYCTL_FIPS_REJECT_NON_FIPS.patch b/libgcrypt-fips-Introduce-GCRYCTL_FIPS_REJECT_NON_FIPS.patch new file mode 100644 index 0000000..d08a59a --- /dev/null +++ b/libgcrypt-fips-Introduce-GCRYCTL_FIPS_REJECT_NON_FIPS.patch @@ -0,0 +1,261 @@ +From e52adf0948c60b2e9accd7996fcece0f9b443763 Mon Sep 17 00:00:00 2001 +From: NIIBE Yutaka +Date: Thu, 19 Dec 2024 11:30:28 +0900 +Subject: [PATCH 12/19] fips: Introduce GCRYCTL_FIPS_REJECT_NON_FIPS. +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* src/gcrypt.h.in (GCRYCTL_FIPS_REJECT_NON_FIPS): New. +(GCRY_FIPS_FLAG_REJECT_*): New. +* src/fips.c (struct gcry_thread_context): Add flags_reject_non_fips. +(the_tc): Add initial value. +(_gcry_thread_context_set_reject): New. +(_gcry_thread_context_check_rejection): New. +* src/gcrypt-int.h (fips_check_rejection): New. +* src/global.c (_gcry_vcontrol): Handle GCRYCTL_FIPS_REJECT_NON_FIPS. +* tests/t-fips-service-ind.c (main): Use GCRYCTL_FIPS_REJECT_NON_FIPS. + +-- + +GnuPG-bug-id: 7338 +Signed-off-by: NIIBE Yutaka +Signed-off-by: Lucas Mülling +--- + cipher/ecc-curves.c | 7 ++++++- + cipher/pubkey.c | 34 ++++++++++++++++++++++++++-------- + src/fips.c | 17 ++++++++++++++++- + src/gcrypt-int.h | 9 ++++++++- + src/gcrypt.h.in | 28 ++++++++++++++++++++++++++-- + src/global.c | 7 +++++++ + tests/t-fips-service-ind.c | 2 ++ + 7 files changed, 91 insertions(+), 13 deletions(-) + +Index: libgcrypt-1.11.0/cipher/ecc-curves.c +=================================================================== +--- libgcrypt-1.11.0.orig/cipher/ecc-curves.c ++++ libgcrypt-1.11.0/cipher/ecc-curves.c +@@ -645,7 +645,12 @@ _gcry_ecc_fill_in_curve (unsigned int nb + possible to bypass this check by specifying the curve parameters + directly. */ + if (fips_mode () && !domain_parms[idx].fips ) +- fips_service_indicator_mark_non_compliant (); ++ { ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) ++ return GPG_ERR_NOT_SUPPORTED; ++ else ++ fips_service_indicator_mark_non_compliant (); ++ } + + switch (domain_parms[idx].model) + { +Index: libgcrypt-1.11.0/cipher/pubkey.c +=================================================================== +--- libgcrypt-1.11.0.orig/cipher/pubkey.c ++++ libgcrypt-1.11.0/cipher/pubkey.c +@@ -510,7 +510,12 @@ prepare_datasexp_to_be_signed (const cha + algo = _gcry_md_get_algo (hd); + + if (fips_mode () && algo == GCRY_MD_SHA1) +- fips_service_indicator_mark_non_compliant (); ++ { ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) ++ return GPG_ERR_DIGEST_ALGO; ++ else ++ fips_service_indicator_mark_non_compliant (); ++ } + + digest_name = _gcry_md_algo_name (algo); + digest_size = (int)_gcry_md_get_algo_dlen (algo); +@@ -538,7 +543,12 @@ prepare_datasexp_to_be_signed (const cha + return GPG_ERR_DIGEST_ALGO; + } + else if (fips_mode () && algo == GCRY_MD_SHA1) +- fips_service_indicator_mark_non_compliant (); ++ { ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) ++ return GPG_ERR_DIGEST_ALGO; ++ else ++ fips_service_indicator_mark_non_compliant (); ++ } + + digest_size = (int)_gcry_md_get_algo_dlen (algo); + digest = _gcry_md_read (hd, algo); +@@ -611,11 +621,15 @@ _gcry_pk_sign_md (gcry_sexp_t *r_sig, co + if (rc) + goto leave; + +- if (!spec->flags.fips && fips_mode ()) +- fips_service_indicator_mark_non_compliant (); +- + if (spec->flags.disabled) + rc = GPG_ERR_PUBKEY_ALGO; ++ else if (!spec->flags.fips && fips_mode ()) ++ { ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) ++ return GPG_ERR_PUBKEY_ALGO; ++ else ++ fips_service_indicator_mark_non_compliant (); ++ } + else if (spec->sign) + rc = spec->sign (r_sig, s_data, keyparms); + else +@@ -689,11 +703,15 @@ _gcry_pk_verify_md (gcry_sexp_t s_sig, c + if (rc) + goto leave; + +- if (!spec->flags.fips && fips_mode ()) +- fips_service_indicator_mark_non_compliant (); +- + if (spec->flags.disabled) + rc = GPG_ERR_PUBKEY_ALGO; ++ else if (!spec->flags.fips && fips_mode ()) ++ { ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) ++ return GPG_ERR_PUBKEY_ALGO; ++ else ++ fips_service_indicator_mark_non_compliant (); ++ } + else if (spec->verify) + rc = spec->verify (s_sig, s_data, keyparms); + else +Index: libgcrypt-1.11.0/src/fips.c +=================================================================== +--- libgcrypt-1.11.0.orig/src/fips.c ++++ libgcrypt-1.11.0/src/fips.c +@@ -70,15 +70,30 @@ static enum module_states current_state; + + struct gcry_thread_context { + unsigned long fips_service_indicator; ++ unsigned int flags_reject_non_fips; + }; + + #ifdef HAVE_GCC_STORAGE_CLASS__THREAD +-static __thread struct gcry_thread_context the_tc; ++static __thread struct gcry_thread_context the_tc = { ++ 0, GCRY_FIPS_FLAG_REJECT_DEFAULT ++}; + #else + #error libgcrypt requires thread-local storage to support FIPS mode + #endif + + void ++_gcry_thread_context_set_reject (unsigned int flags) ++{ ++ the_tc.flags_reject_non_fips = flags; ++} ++ ++int ++_gcry_thread_context_check_rejection (unsigned int flag) ++{ ++ return !!(the_tc.flags_reject_non_fips & flag); ++} ++ ++void + _gcry_thread_context_set_fsi (unsigned long fsi) + { + the_tc.fips_service_indicator = fsi; +Index: libgcrypt-1.11.0/src/gcrypt-int.h +=================================================================== +--- libgcrypt-1.11.0.orig/src/gcrypt-int.h ++++ libgcrypt-1.11.0/src/gcrypt-int.h +@@ -297,6 +297,12 @@ void _gcry_set_log_handler (gcry_handler + void _gcry_set_gettext_handler (const char *(*f)(const char*)); + void _gcry_set_progress_handler (gcry_handler_progress_t cb, void *cb_data); + ++void _gcry_thread_context_set_reject (unsigned int flags); ++int _gcry_thread_context_check_rejection (unsigned int flag); ++ ++#define fips_check_rejection(flag) \ ++ _gcry_thread_context_check_rejection (flag) ++ + void _gcry_thread_context_set_fsi (unsigned long fsi); + unsigned long _gcry_thread_context_get_fsi (void); + #define fips_service_indicator_init() do \ +@@ -305,7 +311,8 @@ unsigned long _gcry_thread_context_get_f + _gcry_thread_context_set_fsi (0); \ + } while (0) + /* Should be used only when fips_mode()==TRUE. */ +-#define fips_service_indicator_mark_non_compliant() _gcry_thread_context_set_fsi (1) ++#define fips_service_indicator_mark_non_compliant() \ ++ _gcry_thread_context_set_fsi (1) + + /* Return a pointer to a string containing a description of the error + code in the error value ERR. */ +Index: libgcrypt-1.11.0/src/gcrypt.h.in +=================================================================== +--- libgcrypt-1.11.0.orig/src/gcrypt.h.in ++++ libgcrypt-1.11.0/src/gcrypt.h.in +@@ -338,7 +338,8 @@ enum gcry_ctl_cmds + GCRYCTL_MD_CUSTOMIZE = 88, + GCRYCTL_FIPS_SERVICE_INDICATOR_PK = 89, + GCRYCTL_FIPS_SERVICE_INDICATOR_HASH = 90, +- GCRYCTL_FIPS_SERVICE_INDICATOR = 91 ++ GCRYCTL_FIPS_SERVICE_INDICATOR = 91, ++ GCRYCTL_FIPS_REJECT_NON_FIPS = 92 + }; + + /* Perform various operations defined by CMD. */ +@@ -1971,7 +1972,30 @@ void gcry_log_debugsxp (const char *text + char *gcry_get_config (int mode, const char *what); + + /* Convinience macro to access the FIPS service indicator. */ +-#define gcry_get_fips_service_indicator() gcry_control (GCRYCTL_FIPS_SERVICE_INDICATOR) ++#define gcry_get_fips_service_indicator() \ ++ gcry_control (GCRYCTL_FIPS_SERVICE_INDICATOR) ++ ++#define GCRY_FIPS_FLAG_REJECT_KDF (1 << 0) ++#define GCRY_FIPS_FLAG_REJECT_MD_MD5 (1 << 1) ++#define GCRY_FIPS_FLAG_REJECT_MD_OTHERS (1 << 2) ++#define GCRY_FIPS_FLAG_REJECT_MAC (1 << 3) ++#define GCRY_FIPS_FLAG_REJECT_CIPHER (1 << 4) ++#define GCRY_FIPS_FLAG_REJECT_PK (1 << 5) ++ ++#define GCRY_FIPS_FLAG_REJECT_MD \ ++ (GCRY_FIPS_FLAG_REJECT_MD_MD5 | GCRY_FIPS_FLAG_REJECT_MD_OTHERS) ++ ++/* Note: Don't reject MD5 */ ++#define GCRY_FIPS_FLAG_REJECT_COMPAT110 \ ++ (GCRY_FIPS_FLAG_REJECT_MD_OTHERS \ ++ | GCRY_FIPS_FLAG_REJECT_MAC \ ++ | GCRY_FIPS_FLAG_REJECT_CIPHER \ ++ | GCRY_FIPS_FLAG_REJECT_KDF \ ++ | GCRY_FIPS_FLAG_REJECT_PK) ++ ++#define GCRY_FIPS_FLAG_REJECT_DEFAULT \ ++ GCRY_FIPS_FLAG_REJECT_COMPAT110 ++ + + /* Log levels used by the internal logging facility. */ + enum gcry_log_levels +Index: libgcrypt-1.11.0/src/global.c +=================================================================== +--- libgcrypt-1.11.0.orig/src/global.c ++++ libgcrypt-1.11.0/src/global.c +@@ -791,6 +791,13 @@ _gcry_vcontrol (enum gcry_ctl_cmds cmd, + rc = _gcry_fips_indicator (); + break; + ++ case GCRYCTL_FIPS_REJECT_NON_FIPS: ++ { ++ unsigned int flags = va_arg (arg_ptr, unsigned int); ++ _gcry_thread_context_set_reject (flags); ++ } ++ break; ++ + case GCRYCTL_FIPS_SERVICE_INDICATOR_CIPHER: + /* Get FIPS Service Indicator for a given symmetric algorithm and + * optional mode. Returns GPG_ERR_NO_ERROR if algorithm is allowed or +Index: libgcrypt-1.11.0/tests/t-fips-service-ind.c +=================================================================== +--- libgcrypt-1.11.0.orig/tests/t-fips-service-ind.c ++++ libgcrypt-1.11.0/tests/t-fips-service-ind.c +@@ -1007,6 +1007,8 @@ main (int argc, char **argv) + if (debug) + xgcry_control ((GCRYCTL_SET_DEBUG_FLAGS, 1u , 0)); + ++ xgcry_control ((GCRYCTL_FIPS_REJECT_NON_FIPS, 0)); ++ + check_digests (); + check_kdf_derive (); + check_md_o_w_r_c (); diff --git a/libgcrypt-fips-Introduce-GCRYCTL_FIPS_SERVICE_INDICATOR-and-the-macro.patch b/libgcrypt-fips-Introduce-GCRYCTL_FIPS_SERVICE_INDICATOR-and-the-macro.patch new file mode 100644 index 0000000..9355299 --- /dev/null +++ b/libgcrypt-fips-Introduce-GCRYCTL_FIPS_SERVICE_INDICATOR-and-the-macro.patch @@ -0,0 +1,101 @@ +From f51f4e98930e6b2175e85fe8a95b8b6a15ad5efa Mon Sep 17 00:00:00 2001 +From: NIIBE Yutaka +Date: Thu, 5 Dec 2024 11:34:32 +0900 +Subject: [PATCH 2/5] fips: Introduce GCRYCTL_FIPS_SERVICE_INDICATOR and the + macro. +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* src/fips.c (_gcry_fips_indicator): New. +* src/g10lib.h (_gcry_fips_indicator): New. +* src/gcrypt.h.in (GCRYCTL_FIPS_SERVICE_INDICATOR): New. +(gcry_get_fips_service_indicator): New. +* src/global.c (_gcry_vcontrol): Handle GCRYCTL_FIPS_SERVICE_INDICATOR. + +-- + +GnuPG-bug-id: 7338 +Signed-off-by: NIIBE Yutaka +Signed-off-by: Lucas Mülling +--- + src/fips.c | 11 +++++++++++ + src/g10lib.h | 2 ++ + src/gcrypt.h.in | 6 +++++- + src/global.c | 4 ++++ + 4 files changed, 22 insertions(+), 1 deletion(-) + +Index: libgcrypt-1.11.0/src/fips.c +=================================================================== +--- libgcrypt-1.11.0.orig/src/fips.c ++++ libgcrypt-1.11.0/src/fips.c +@@ -364,6 +364,17 @@ _gcry_fips_test_operational (void) + return result; + } + ++gpg_err_code_t ++_gcry_fips_indicator (void) ++{ ++ /* If anything recorded, it means that the operation is not ++ supported under FIPS mode. */ ++ if (_gcry_thread_context_get_fsi ()) ++ return GPG_ERR_NOT_SUPPORTED; ++ ++ return 0; ++} ++ + int + _gcry_fips_indicator_cipher (va_list arg_ptr) + { +Index: libgcrypt-1.11.0/src/g10lib.h +=================================================================== +--- libgcrypt-1.11.0.orig/src/g10lib.h ++++ libgcrypt-1.11.0/src/g10lib.h +@@ -468,6 +468,8 @@ void _gcry_fips_signal_error (const char + _gcry_fips_signal_error (__FILE__, __LINE__, NULL, 1, (a)) + #endif + ++gpg_err_code_t _gcry_fips_indicator (void); ++ + int _gcry_fips_indicator_cipher (va_list arg_ptr); + int _gcry_fips_indicator_hash (va_list arg_ptr); + int _gcry_fips_indicator_mac (va_list arg_ptr); +Index: libgcrypt-1.11.0/src/gcrypt.h.in +=================================================================== +--- libgcrypt-1.11.0.orig/src/gcrypt.h.in ++++ libgcrypt-1.11.0/src/gcrypt.h.in +@@ -337,7 +337,8 @@ enum gcry_ctl_cmds + GCRYCTL_FIPS_SERVICE_INDICATOR_PK_FLAGS = 87, + GCRYCTL_MD_CUSTOMIZE = 88, + GCRYCTL_FIPS_SERVICE_INDICATOR_PK = 89, +- GCRYCTL_FIPS_SERVICE_INDICATOR_HASH = 90 ++ GCRYCTL_FIPS_SERVICE_INDICATOR_HASH = 90, ++ GCRYCTL_FIPS_SERVICE_INDICATOR = 91 + }; + + /* Perform various operations defined by CMD. */ +@@ -1966,6 +1967,9 @@ void gcry_log_debugsxp (const char *text + + char *gcry_get_config (int mode, const char *what); + ++/* Convinience macro to access the FIPS service indicator. */ ++#define gcry_get_fips_service_indicator() gcry_control (GCRYCTL_FIPS_SERVICE_INDICATOR) ++ + /* Log levels used by the internal logging facility. */ + enum gcry_log_levels + { +Index: libgcrypt-1.11.0/src/global.c +=================================================================== +--- libgcrypt-1.11.0.orig/src/global.c ++++ libgcrypt-1.11.0/src/global.c +@@ -787,6 +787,10 @@ _gcry_vcontrol (enum gcry_ctl_cmds cmd, + rc = _gcry_fips_run_selftests (1); + break; + ++ case GCRYCTL_FIPS_SERVICE_INDICATOR: ++ rc = _gcry_fips_indicator (); ++ break; ++ + case GCRYCTL_FIPS_SERVICE_INDICATOR_CIPHER: + /* Get FIPS Service Indicator for a given symmetric algorithm and + * optional mode. Returns GPG_ERR_NO_ERROR if algorithm is allowed or diff --git a/libgcrypt-fips-Introduce-an-internal-API-for-FIPS-service-indicator.patch b/libgcrypt-fips-Introduce-an-internal-API-for-FIPS-service-indicator.patch new file mode 100644 index 0000000..b452626 --- /dev/null +++ b/libgcrypt-fips-Introduce-an-internal-API-for-FIPS-service-indicator.patch @@ -0,0 +1,332 @@ +From e1cf3123282525693b646499eb7efe4f2be4010a Mon Sep 17 00:00:00 2001 +From: NIIBE Yutaka +Date: Thu, 5 Dec 2024 11:06:37 +0900 +Subject: [PATCH 1/5] fips: Introduce an internal API for FIPS service + indicator. +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* configure.ac (HAVE_GCC_STORAGE_CLASS__THREAD): New. +* src/fips.c (struct gcry_thread_context): New. +(_gcry_thread_context_set_fsi, _gcry_thread_context_get_fsi): New. +* src/gcrypt-int.h (fips_service_indicator_init): New macro. +(fips_service_indicator_mark_success): New macro. +* tests/Makefile.am (tests_bin): Add t-thread-local. +* tests/t-thread-local.c: New. + +-- + +GnuPG-bug-id: 7340 +Signed-off-by: NIIBE Yutaka +Signed-off-by: Lucas Mülling +--- + configure.ac | 14 +++ + src/fips.c | 21 ++++- + src/gcrypt-int.h | 12 +++ + tests/Makefile.am | 2 +- + tests/t-thread-local.c | 196 +++++++++++++++++++++++++++++++++++++++++ + 5 files changed, 243 insertions(+), 2 deletions(-) + create mode 100644 tests/t-thread-local.c + +diff --git a/configure.ac b/configure.ac +index a7f922b1..d708f89a 100644 +--- a/configure.ac ++++ b/configure.ac +@@ -1489,6 +1489,20 @@ if test "$gcry_cv_gcc_attribute_sysv_abi" = "yes" ; then + fi + fi + ++# ++# Check whether compiler support '__thread' storage class specifier. ++# ++AC_CACHE_CHECK([whether compiler supports '__thread' storage class specifier], ++ [gcry_cv_gcc_storage_class__thread], ++ [gcry_cv_gcc_storage_class__thread=no ++ AC_COMPILE_IFELSE([AC_LANG_PROGRAM([#include ], ++ [static __thread int bar;] ++ )], ++ [gcry_cv_gcc_storage_class__thread=yes])]) ++if test "$gcry_cv_gcc_storage_class__thread" = "yes" ; then ++ AC_DEFINE(HAVE_GCC_STORAGE_CLASS__THREAD,1, ++ [Defined if compiler supports "__thread" storage class specifier]) ++fi + + # Restore flags. + CFLAGS=$_gcc_cflags_save; +diff --git a/src/fips.c b/src/fips.c +index cf91baa8..58fb69df 100644 +--- a/src/fips.c ++++ b/src/fips.c +@@ -67,10 +67,29 @@ GPGRT_LOCK_DEFINE (fsm_lock); + used while in fips mode. Change this only while holding fsm_lock. */ + static enum module_states current_state; + ++struct gcry_thread_context { ++ unsigned long fips_service_indicator; ++}; ++ ++#ifdef HAVE_GCC_STORAGE_CLASS__THREAD ++static __thread struct gcry_thread_context the_tc; ++#else ++#error libgcrypt requires thread-local storage to support FIPS mode ++#endif ++ ++void ++_gcry_thread_context_set_fsi (unsigned long fsi) ++{ ++ the_tc.fips_service_indicator = fsi; ++} + ++unsigned long ++_gcry_thread_context_get_fsi (void) ++{ ++ return the_tc.fips_service_indicator; ++} + + +- + static void fips_new_state (enum module_states new_state); + + +diff --git a/src/gcrypt-int.h b/src/gcrypt-int.h +index 074ea071..7f894737 100644 +--- a/src/gcrypt-int.h ++++ b/src/gcrypt-int.h +@@ -298,6 +298,18 @@ void _gcry_set_log_handler (gcry_handler_log_t f, void *opaque); + void _gcry_set_gettext_handler (const char *(*f)(const char*)); + void _gcry_set_progress_handler (gcry_handler_progress_t cb, void *cb_data); + ++void _gcry_thread_context_set_fsi (unsigned long fsi); ++unsigned long _gcry_thread_context_get_fsi (void); ++#define fips_service_indicator_init() do \ ++ { \ ++ if (fips_mode ()) \ ++ _gcry_thread_context_set_fsi (1); \ ++ } while (0) ++#define fips_service_indicator_mark_success(is_compliant) do \ ++ { \ ++ if (is_compliant && fips_mode ()) \ ++ _gcry_thread_context_set_fsi (0); \ ++ } while (0) + + /* Return a pointer to a string containing a description of the error + code in the error value ERR. */ +diff --git a/tests/Makefile.am b/tests/Makefile.am +index 423bc1cd..52f7dd61 100644 +--- a/tests/Makefile.am ++++ b/tests/Makefile.am +@@ -25,7 +25,7 @@ tests_bin = \ + version t-secmem mpitests t-sexp t-convert \ + t-mpi-bit t-mpi-point t-lock \ + prime basic keygen pubkey hmac hashtest t-kdf keygrip \ +- aeswrap random t-kem t-mlkem ++ aeswrap random t-kem t-mlkem t-thread-local + + if USE_RSA + tests_bin += pkcs1v2 t-rsa-pss t-rsa-15 t-rsa-testparm +diff --git a/tests/t-thread-local.c b/tests/t-thread-local.c +new file mode 100644 +index 00000000..285f197f +--- /dev/null ++++ b/tests/t-thread-local.c +@@ -0,0 +1,196 @@ ++/* t-mlkem.c - Check the thread local storage ++ * Copyright (C) 2024 g10 Code GmbH ++ * ++ * This file is part of Libgcrypt. ++ * ++ * Libgcrypt is free software; you can redistribute it and/or modify ++ * it under the terms of the GNU Lesser General Public License as ++ * published by the Free Software Foundation; either version 2.1 of ++ * the License, or (at your option) any later version. ++ * ++ * Libgcrypt 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 Lesser General Public License for more details. ++ * ++ * You should have received a copy of the GNU Lesser General Public License ++ * along with this program; if not, see . ++ * SPDX-License-Identifier: LGPL-2.1+ ++ */ ++ ++/* For now, this program simply test __thread storage class specifier. ++ * After we implement thread local context for libgcrypt, we will ++ * modity to test the feature. */ ++ ++#ifdef HAVE_CONFIG_H ++#include ++#endif ++#include ++#include ++#include ++#include ++#include ++#include ++#if HAVE_PTHREAD ++# include ++#endif ++ ++#define PGM "t-thread-local" ++ ++#include "t-common.h" ++#include "../src/gcrypt-testapi.h" ++ ++/* Mingw requires us to include windows.h after winsock2.h which is ++ included by gcrypt.h. */ ++#ifdef _WIN32 ++# include ++#endif ++ ++#ifdef _WIN32 ++# define THREAD_RET_TYPE DWORD WINAPI ++# define THREAD_RET_VALUE 0 ++#else ++# define THREAD_RET_TYPE void * ++# define THREAD_RET_VALUE NULL ++#endif ++ ++#define N_TESTS 1 ++ ++#define N_THREADS 19 ++ ++static __thread unsigned long t; ++ ++struct thread_arg_s ++{ ++ int no; ++}; ++ ++#if defined(HAVE_PTHREAD) || defined(_WIN32) ++/* Checking the local storage thread. */ ++static THREAD_RET_TYPE ++check_ls_thread (void *argarg) ++{ ++ struct thread_arg_s *arg = argarg; ++ ++ t = arg->no; ++ info ("a thread update the local storage: %lu", t); ++ ++ gcry_free (arg); ++ return THREAD_RET_VALUE; ++} ++#endif ++ ++static void ++check_thread_local (void) ++{ ++ struct thread_arg_s *arg; ++ ++#ifdef _WIN32 ++ HANDLE threads[N_THREADS]; ++ int i; ++ int rc; ++ ++ t = N_THREADS; ++ for (i=0; i < N_THREADS; i++) ++ { ++ arg = gcry_xmalloc (sizeof *arg); ++ arg->no = i; ++ threads[i] = CreateThread (NULL, 0, check_ls_thread, arg, 0, NULL); ++ if (!threads[i]) ++ die ("error creating a thread %d: rc=%d", ++ i, (int)GetLastError ()); ++ } ++ ++ for (i=0; i < N_THREADS; i++) ++ { ++ rc = WaitForSingleObject (threads[i], INFINITE); ++ if (rc == WAIT_OBJECT_0) ++ info ("a thread %d has terminated", i); ++ else ++ fail ("waiting for a thread %d failed: %d", ++ i, (int)GetLastError ()); ++ CloseHandle (threads[i]); ++ } ++ ++#elif HAVE_PTHREAD ++ pthread_t threads[N_THREADS]; ++ int rc, i; ++ ++ t = N_THREADS; ++ for (i=0; i < N_THREADS; i++) ++ { ++ arg = gcry_xmalloc (sizeof *arg); ++ arg->no = i; ++ pthread_create (&threads[i], NULL, check_ls_thread, arg); ++ } ++ ++ for (i=0; i < N_THREADS; i++) ++ { ++ rc = pthread_join (threads[i], NULL); ++ if (rc) ++ fail ("pthread_join failed for a thread %d: %s", ++ i, strerror (errno)); ++ else ++ info ("a thread %d has terminated", i); ++ } ++#else ++ (void)arg; ++#endif /*!_WIN32*/ ++ if (t != N_THREADS) ++ fail ("failed t=%lu\n", t); ++ else ++ info ("success"); ++} ++ ++int ++main (int argc, char **argv) ++{ ++ int last_argc = -1; ++ ++ if (argc) ++ { argc--; argv++; } ++ ++ while (argc && last_argc != argc) ++ { ++ last_argc = argc; ++ if (!strcmp (*argv, "--")) ++ { ++ argc--; argv++; ++ break; ++ } ++ else if (!strcmp (*argv, "--help")) ++ { ++ fputs ("usage: " PGM " [options]\n" ++ "Options:\n" ++ " --verbose print timings etc.\n" ++ " --debug flyswatter\n", ++ stdout); ++ exit (0); ++ } ++ else if (!strcmp (*argv, "--verbose")) ++ { ++ verbose++; ++ argc--; argv++; ++ } ++ else if (!strcmp (*argv, "--debug")) ++ { ++ verbose += 2; ++ debug++; ++ argc--; argv++; ++ } ++ else if (!strncmp (*argv, "--", 2)) ++ die ("unknown option '%s'", *argv); ++ } ++ ++ xgcry_control ((GCRYCTL_DISABLE_SECMEM, 0)); ++ if (!gcry_check_version (GCRYPT_VERSION)) ++ die ("version mismatch\n"); ++ if (debug) ++ xgcry_control ((GCRYCTL_SET_DEBUG_FLAGS, 1u , 0)); ++ xgcry_control ((GCRYCTL_ENABLE_QUICK_RANDOM, 0)); ++ xgcry_control ((GCRYCTL_INITIALIZATION_FINISHED, 0)); ++ ++ check_thread_local (); ++ ++ return !!error_count; ++} +-- +2.49.0 + diff --git a/libgcrypt-fips-Rejection-by-GCRYCTL_FIPS_REJECT_NON_FIPS-not-by-open-flags.patch b/libgcrypt-fips-Rejection-by-GCRYCTL_FIPS_REJECT_NON_FIPS-not-by-open-flags.patch new file mode 100644 index 0000000..6d18f18 --- /dev/null +++ b/libgcrypt-fips-Rejection-by-GCRYCTL_FIPS_REJECT_NON_FIPS-not-by-open-flags.patch @@ -0,0 +1,498 @@ +From d060dd58b82882dec0d8bfcc593536bc0083b4b1 Mon Sep 17 00:00:00 2001 +From: NIIBE Yutaka +Date: Fri, 20 Dec 2024 09:38:13 +0900 +Subject: [PATCH 14/19] fips: Rejection by GCRYCTL_FIPS_REJECT_NON_FIPS, not by + open flags. +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* src/gcrypt.h.in (GCRY_CIPHER_FLAG_REJECT_NON_FIPS): Remove. +(GCRY_MD_FLAG_REJECT_NON_FIPS): Remove. +(GCRY_MAC_FLAG_REJECT_NON_FIPS): Remove. +* tests/t-fips-service-ind.c: Update tests with +GCRYCTL_FIPS_REJECT_NON_FIPS. +* cipher/cipher.c (_gcry_cipher_open_internal, cipher_setkey): Use +fips_check_rejection. +* cipher/mac.c (mac_open): Likewise. +* cipher/md.c (struct gcry_md_context): Remove reject_non_fips. +(md_open, md_enable): Use fips_check_rejection. +(_gcry_md_enable, md_copy): Likewise. + +-- + +GnuPG-bug-id: 7338 +Signed-off-by: NIIBE Yutaka +Signed-off-by: Lucas Mülling +--- + cipher/cipher.c | 8 ++-- + cipher/mac.c | 5 +-- + cipher/md.c | 81 ++++++++++++++++++++++++++++++-------- + src/gcrypt.h.in | 7 +--- + tests/t-fips-service-ind.c | 59 +++++++++++---------------- + 5 files changed, 94 insertions(+), 66 deletions(-) + +Index: libgcrypt-1.11.0/cipher/cipher.c +=================================================================== +--- libgcrypt-1.11.0.orig/cipher/cipher.c ++++ libgcrypt-1.11.0/cipher/cipher.c +@@ -510,7 +510,6 @@ _gcry_cipher_open_internal (gcry_cipher_ + int algo, int mode, unsigned int flags) + { + int secure = !!(flags & GCRY_CIPHER_SECURE); +- int reject_non_fips = !!(flags & GCRY_CIPHER_FLAG_REJECT_NON_FIPS); + gcry_cipher_spec_t *spec; + gcry_cipher_hd_t h = NULL; + gcry_err_code_t err; +@@ -526,7 +525,7 @@ _gcry_cipher_open_internal (gcry_cipher_ + err = GPG_ERR_CIPHER_ALGO; + else if (!spec->flags.fips && fips_mode ()) + { +- if (reject_non_fips) ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_CIPHER)) + err = GPG_ERR_CIPHER_ALGO; + else + { +@@ -544,8 +543,7 @@ _gcry_cipher_open_internal (gcry_cipher_ + | GCRY_CIPHER_ENABLE_SYNC + | GCRY_CIPHER_CBC_CTS + | GCRY_CIPHER_CBC_MAC +- | GCRY_CIPHER_EXTENDED +- | GCRY_CIPHER_FLAG_REJECT_NON_FIPS)) ++ | GCRY_CIPHER_EXTENDED)) + || ((flags & GCRY_CIPHER_CBC_CTS) && (flags & GCRY_CIPHER_CBC_MAC)))) + err = GPG_ERR_CIPHER_ALGO; + +@@ -776,7 +774,7 @@ cipher_setkey (gcry_cipher_hd_t c, byte + Key Generation Requirements" for details. */ + if (buf_eq_const (key, key + keylen, keylen)) + { +- if ((c->flags & GCRY_CIPHER_FLAG_REJECT_NON_FIPS)) ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_CIPHER)) + return GPG_ERR_WEAK_KEY; + else + fips_service_indicator_mark_non_compliant (); +Index: libgcrypt-1.11.0/cipher/mac.c +=================================================================== +--- libgcrypt-1.11.0.orig/cipher/mac.c ++++ libgcrypt-1.11.0/cipher/mac.c +@@ -519,7 +519,6 @@ mac_open (gcry_mac_hd_t * hd, int algo, + gcry_err_code_t err; + gcry_mac_hd_t h; + int secure = !!(flags & GCRY_MAC_FLAG_SECURE); +- int reject_non_fips = !!(flags & GCRY_MAC_FLAG_REJECT_NON_FIPS); + + spec = spec_from_algo (algo); + if (!spec) +@@ -528,7 +527,7 @@ mac_open (gcry_mac_hd_t * hd, int algo, + return GPG_ERR_MAC_ALGO; + else if (!spec->flags.fips && fips_mode ()) + { +- if (reject_non_fips) ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_MAC)) + return GPG_ERR_MAC_ALGO; + else + fips_service_indicator_mark_non_compliant (); +@@ -650,7 +649,7 @@ _gcry_mac_open (gcry_mac_hd_t * h, int a + gcry_err_code_t rc; + gcry_mac_hd_t hd = NULL; + +- if ((flags & ~(GCRY_MAC_FLAG_SECURE | GCRY_MAC_FLAG_REJECT_NON_FIPS))) ++ if ((flags & ~GCRY_MAC_FLAG_SECURE)) + rc = GPG_ERR_INV_ARG; + else + rc = mac_open (&hd, algo, flags, ctx); +Index: libgcrypt-1.11.0/cipher/md.c +=================================================================== +--- libgcrypt-1.11.0.orig/cipher/md.c ++++ libgcrypt-1.11.0/cipher/md.c +@@ -275,7 +275,6 @@ struct gcry_md_context + unsigned int finalized:1; + unsigned int bugemu1:1; + unsigned int hmac:1; +- unsigned int reject_non_fips:1; + } flags; + size_t actual_handle_size; /* Allocated size of this handle. */ + FILE *debug; +@@ -509,7 +508,6 @@ md_open (gcry_md_hd_t *h, int algo, unsi + ctx->flags.secure = secure; + ctx->flags.hmac = hmac; + ctx->flags.bugemu1 = !!(flags & GCRY_MD_FLAG_BUGEMU1); +- ctx->flags.reject_non_fips = !!(flags & GCRY_MD_FLAG_REJECT_NON_FIPS); + } + + if (! err) +@@ -544,14 +542,11 @@ _gcry_md_open (gcry_md_hd_t *h, int algo + + if ((flags & ~(GCRY_MD_FLAG_SECURE + | GCRY_MD_FLAG_HMAC +- | GCRY_MD_FLAG_REJECT_NON_FIPS + | GCRY_MD_FLAG_BUGEMU1))) + rc = GPG_ERR_INV_ARG; + else + rc = md_open (&hd, algo, flags); + +- *h = rc? NULL : hd; +- + if (!rc && fips_mode ()) + { + GcryDigestEntry *entry = hd->ctx->list; +@@ -566,9 +561,26 @@ _gcry_md_open (gcry_md_hd_t *h, int algo + } + + if (!is_compliant_algo) +- fips_service_indicator_mark_non_compliant (); ++ { ++ int reject = 0; ++ ++ if (algo == GCRY_MD_MD5) ++ reject = fips_check_rejection (GCRY_FIPS_FLAG_REJECT_MD_MD5); ++ else ++ reject = fips_check_rejection (GCRY_FIPS_FLAG_REJECT_MD_OTHERS); ++ ++ if (reject) ++ { ++ md_close (hd); ++ hd = NULL; ++ rc = GPG_ERR_DIGEST_ALGO; ++ } ++ else ++ fips_service_indicator_mark_non_compliant (); ++ } + } + ++ *h = rc? NULL : hd; + return rc; + } + +@@ -581,12 +593,17 @@ md_enable (gcry_md_hd_t hd, int algorith + const gcry_md_spec_t *spec; + GcryDigestEntry *entry; + gcry_err_code_t err = 0; +- int reject_non_fips = h->flags.reject_non_fips; ++ int reject; + + for (entry = h->list; entry; entry = entry->next) + if (entry->spec->algo == algorithm) + return 0; /* Already enabled */ + ++ if (algorithm == GCRY_MD_MD5) ++ reject = fips_check_rejection (GCRY_FIPS_FLAG_REJECT_MD_MD5); ++ else ++ reject = fips_check_rejection (GCRY_FIPS_FLAG_REJECT_MD_OTHERS); ++ + spec = spec_from_algo (algorithm); + if (!spec) + { +@@ -598,7 +615,7 @@ md_enable (gcry_md_hd_t hd, int algorith + err = GPG_ERR_DIGEST_ALGO; + + /* Any non-FIPS algorithm should go this way */ +- if (!err && reject_non_fips && !spec->flags.fips && fips_mode ()) ++ if (!err && reject && !spec->flags.fips && fips_mode ()) + err = GPG_ERR_DIGEST_ALGO; + + if (!err && h->flags.hmac && spec->read == NULL) +@@ -657,7 +674,19 @@ _gcry_md_enable (gcry_md_hd_t hd, int al + } + + if (!is_compliant_algo) +- fips_service_indicator_mark_non_compliant (); ++ { ++ int reject = 0; ++ ++ if (algorithm == GCRY_MD_MD5) ++ reject = fips_check_rejection (GCRY_FIPS_FLAG_REJECT_MD_MD5); ++ else ++ reject = fips_check_rejection (GCRY_FIPS_FLAG_REJECT_MD_OTHERS); ++ ++ if (reject) ++ rc = GPG_ERR_DIGEST_ALGO; ++ else ++ fips_service_indicator_mark_non_compliant (); ++ } + } + + return rc; +@@ -667,13 +696,14 @@ _gcry_md_enable (gcry_md_hd_t hd, int al + static gcry_err_code_t + md_copy (gcry_md_hd_t ahd, gcry_md_hd_t *b_hd) + { +- gcry_err_code_t err = 0; ++ gcry_err_code_t rc = 0; + struct gcry_md_context *a = ahd->ctx; + struct gcry_md_context *b; + GcryDigestEntry *ar, *br; + gcry_md_hd_t bhd; + size_t n; + int is_compliant_algo = 1; ++ int reject = 0; + + if (ahd->bufpos) + md_write (ahd, NULL, 0); +@@ -686,7 +716,7 @@ md_copy (gcry_md_hd_t ahd, gcry_md_hd_t + + if (!bhd) + { +- err = gpg_err_code_from_syserror (); ++ rc = gpg_err_code_from_syserror (); + goto leave; + } + +@@ -715,12 +745,20 @@ md_copy (gcry_md_hd_t ahd, gcry_md_hd_t + br = xtrymalloc (ar->actual_struct_size); + if (!br) + { +- err = gpg_err_code_from_syserror (); ++ rc = gpg_err_code_from_syserror (); + md_close (bhd); + goto leave; + } + +- is_compliant_algo &= spec->flags.fips; ++ if (!spec->flags.fips) ++ { ++ is_compliant_algo = 0; ++ ++ if (spec->algo == GCRY_MD_MD5) ++ reject |= fips_check_rejection (GCRY_FIPS_FLAG_REJECT_MD_MD5); ++ else ++ reject |= fips_check_rejection (GCRY_FIPS_FLAG_REJECT_MD_OTHERS); ++ } + + memcpy (br, ar, ar->actual_struct_size); + br->next = b->list; +@@ -730,13 +768,22 @@ md_copy (gcry_md_hd_t ahd, gcry_md_hd_t + if (a->debug) + md_start_debug (bhd, "unknown"); + +- *b_hd = bhd; ++ if (!is_compliant_algo && fips_mode ()) ++ { ++ if (reject) ++ { ++ rc = GPG_ERR_DIGEST_ALGO; ++ md_close (bhd); ++ } ++ else ++ fips_service_indicator_mark_non_compliant (); ++ } + +- if (!is_compliant_algo) +- fips_service_indicator_mark_non_compliant (); ++ if (!rc) ++ *b_hd = bhd; + + leave: +- return err; ++ return rc; + } + + +Index: libgcrypt-1.11.0/src/gcrypt.h.in +=================================================================== +--- libgcrypt-1.11.0.orig/src/gcrypt.h.in ++++ libgcrypt-1.11.0/src/gcrypt.h.in +@@ -995,8 +995,7 @@ enum gcry_cipher_flags + GCRY_CIPHER_ENABLE_SYNC = 2, /* Enable CFB sync mode. */ + GCRY_CIPHER_CBC_CTS = 4, /* Enable CBC cipher text stealing (CTS). */ + GCRY_CIPHER_CBC_MAC = 8, /* Enable CBC message auth. code (MAC). */ +- GCRY_CIPHER_EXTENDED = 16, /* Enable extended AES-WRAP. */ +- GCRY_CIPHER_FLAG_REJECT_NON_FIPS = 32 /* Reject non-FIPS-compliant algo. */ ++ GCRY_CIPHER_EXTENDED = 16 /* Enable extended AES-WRAP. */ + }; + + /* Methods used for AEAD IV generation. */ +@@ -1322,7 +1321,6 @@ enum gcry_md_flags + { + GCRY_MD_FLAG_SECURE = 1, /* Allocate all buffers in "secure" memory. */ + GCRY_MD_FLAG_HMAC = 2, /* Make an HMAC out of this algorithm. */ +- GCRY_MD_FLAG_REJECT_NON_FIPS = 4, /* Reject non-FIPS-compliant algo. */ + GCRY_MD_FLAG_BUGEMU1 = 0x0100 + }; + +@@ -1564,8 +1562,7 @@ enum gcry_mac_algos + /* Flags used with the open function. */ + enum gcry_mac_flags + { +- GCRY_MAC_FLAG_SECURE = 1, /* Allocate all buffers in "secure" memory. */ +- GCRY_MAC_FLAG_REJECT_NON_FIPS = 2 /* Reject non-FIPS-compliant algo. */ ++ GCRY_MAC_FLAG_SECURE = 1 /* Allocate all buffers in "secure" memory. */ + }; + + /* Create a MAC handle for algorithm ALGO. FLAGS may be given as an bitwise OR +Index: libgcrypt-1.11.0/tests/t-fips-service-ind.c +=================================================================== +--- libgcrypt-1.11.0.orig/tests/t-fips-service-ind.c ++++ libgcrypt-1.11.0/tests/t-fips-service-ind.c +@@ -250,7 +250,7 @@ check_pk_hash_sign_verify (void) + /* Check gcry_cipher_open, gcry_cipher_setkey, gcry_cipher_encrypt, + gcry_cipher_decrypt, gcry_cipher_close API. */ + static void +-check_cipher_o_s_e_d_c (void) ++check_cipher_o_s_e_d_c (int reject) + { + static struct { + int algo; +@@ -258,18 +258,12 @@ check_cipher_o_s_e_d_c (void) + int keylen; + const char *expect; + int expect_failure; +- unsigned int flags; + } tv[] = { + #if USE_DES + { GCRY_CIPHER_3DES, + "\xe3\x34\x7a\x6b\x0b\xc1\x15\x2c\x64\x2a\x25\xcb\xd3\xbc\x31\xab" + "\xfb\xa1\x62\xa8\x1f\x19\x7c\x15", 24, + "\x3f\x1a\xb8\x83\x18\x8b\xb5\x97", 1 }, +- { GCRY_CIPHER_3DES, +- "\xe3\x34\x7a\x6b\x0b\xc1\x15\x2c\x64\x2a\x25\xcb\xd3\xbc\x31\xab" +- "\xfb\xa1\x62\xa8\x1f\x19\x7c\x15", 24, +- "\x3f\x1a\xb8\x83\x18\x8b\xb5\x97", +- 1, GCRY_CIPHER_FLAG_REJECT_NON_FIPS }, + #endif + { GCRY_CIPHER_AES, + "\x2b\x7e\x15\x16\x28\xae\xd2\xa6\xab\xf7\x15\x88\x09\xcf\x4f\x3c", 16, +@@ -297,12 +291,10 @@ check_cipher_o_s_e_d_c (void) + assert (blklen != 0); + assert (blklen <= ptlen); + assert (blklen <= DIM (out)); +- err = gcry_cipher_open (&h, tv[tvidx].algo, GCRY_CIPHER_MODE_ECB, +- tv[tvidx].flags); ++ err = gcry_cipher_open (&h, tv[tvidx].algo, GCRY_CIPHER_MODE_ECB, 0); + if (err) + { +- if (in_fips_mode && (tv[tvidx].flags & GCRY_CIPHER_FLAG_REJECT_NON_FIPS) +- && tv[tvidx].expect_failure) ++ if (in_fips_mode && reject && tv[tvidx].expect_failure) + /* Here, an error is expected */ + ; + else +@@ -312,8 +304,7 @@ check_cipher_o_s_e_d_c (void) + } + else + { +- if (in_fips_mode && (tv[tvidx].flags & GCRY_CIPHER_FLAG_REJECT_NON_FIPS) +- && tv[tvidx].expect_failure) ++ if (in_fips_mode && reject && tv[tvidx].expect_failure) + /* This case, an error is expected, but we observed success */ + fail ("gcry_cipher_open test %d unexpectedly succeeded\n", tvidx); + } +@@ -398,7 +389,7 @@ check_cipher_o_s_e_d_c (void) + /* Check gcry_mac_open, gcry_mac_write, gcry_mac_write, gcry_mac_read, + gcry_mac_close API. */ + static void +-check_mac_o_w_r_c (void) ++check_mac_o_w_r_c (int reject) + { + static struct { + int algo; +@@ -408,14 +399,10 @@ check_mac_o_w_r_c (void) + int keylen; + const char *expect; + int expect_failure; +- unsigned int flags; + } tv[] = { + #if USE_MD5 + { GCRY_MAC_HMAC_MD5, "hmac input abc", 14, "hmac key input", 14, + "\x0d\x72\xd0\x60\xaf\x34\xf2\xca\x33\x58\xa9\xcc\xd3\x5a\xac\xb5", 1 }, +- { GCRY_MAC_HMAC_MD5, "hmac input abc", 14, "hmac key input", 14, +- "\x0d\x72\xd0\x60\xaf\x34\xf2\xca\x33\x58\xa9\xcc\xd3\x5a\xac\xb5", 1, +- GCRY_MAC_FLAG_REJECT_NON_FIPS }, + #endif + #if USE_SHA1 + { GCRY_MAC_HMAC_SHA1, "hmac input abc", 14, "hmac key input", 14, +@@ -471,11 +458,10 @@ check_mac_o_w_r_c (void) + expectlen = gcry_mac_get_algo_maclen (tv[tvidx].algo); + assert (expectlen != 0); + assert (expectlen <= DIM (mac)); +- err = gcry_mac_open (&h, tv[tvidx].algo, tv[tvidx].flags, NULL); ++ err = gcry_mac_open (&h, tv[tvidx].algo, 0, NULL); + if (err) + { +- if (in_fips_mode && (tv[tvidx].flags & GCRY_MAC_FLAG_REJECT_NON_FIPS) +- && tv[tvidx].expect_failure) ++ if (in_fips_mode && reject && tv[tvidx].expect_failure) + /* Here, an error is expected */ + ; + else +@@ -485,8 +471,7 @@ check_mac_o_w_r_c (void) + } + else + { +- if (in_fips_mode && (tv[tvidx].flags & GCRY_MAC_FLAG_REJECT_NON_FIPS) +- && tv[tvidx].expect_failure) ++ if (in_fips_mode && reject && tv[tvidx].expect_failure) + /* This case, an error is expected, but we observed success */ + fail ("gcry_mac_open test %d unexpectedly succeeded\n", tvidx); + } +@@ -563,7 +548,7 @@ check_mac_o_w_r_c (void) + /* Check gcry_md_open, gcry_md_write, gcry_md_write, gcry_md_read, + gcry_md_close API. */ + static void +-check_md_o_w_r_c (void) ++check_md_o_w_r_c (int reject) + { + static struct { + int algo; +@@ -571,14 +556,10 @@ check_md_o_w_r_c (void) + int datalen; + const char *expect; + int expect_failure; +- unsigned int flags; + } tv[] = { + #if USE_MD5 + { GCRY_MD_MD5, "abc", 3, + "\x90\x01\x50\x98\x3C\xD2\x4F\xB0\xD6\x96\x3F\x7D\x28\xE1\x7F\x72", 1 }, +- { GCRY_MD_MD5, "abc", 3, +- "\x90\x01\x50\x98\x3C\xD2\x4F\xB0\xD6\x96\x3F\x7D\x28\xE1\x7F\x72", 1, +- GCRY_MD_FLAG_REJECT_NON_FIPS }, + #endif + #if USE_SHA1 + { GCRY_MD_SHA1, "abc", 3, +@@ -632,11 +613,10 @@ check_md_o_w_r_c (void) + + expectlen = gcry_md_get_algo_dlen (tv[tvidx].algo); + assert (expectlen != 0); +- err = gcry_md_open (&h, tv[tvidx].algo, tv[tvidx].flags); ++ err = gcry_md_open (&h, tv[tvidx].algo, 0); + if (err) + { +- if (in_fips_mode && (tv[tvidx].flags & GCRY_MD_FLAG_REJECT_NON_FIPS) +- && tv[tvidx].expect_failure) ++ if (in_fips_mode && reject && tv[tvidx].expect_failure) + /* Here, an error is expected */ + ; + else +@@ -646,8 +626,7 @@ check_md_o_w_r_c (void) + } + else + { +- if (in_fips_mode && (tv[tvidx].flags & GCRY_MD_FLAG_REJECT_NON_FIPS) +- && tv[tvidx].expect_failure) ++ if (in_fips_mode && reject && tv[tvidx].expect_failure) + /* This case, an error is expected, but we observed success */ + fail ("gcry_md_open test %d unexpectedly succeeded\n", tvidx); + } +@@ -1011,10 +990,18 @@ main (int argc, char **argv) + + check_digests (); + check_kdf_derive (); +- check_md_o_w_r_c (); +- check_mac_o_w_r_c (); +- check_cipher_o_s_e_d_c (); ++ check_md_o_w_r_c (0); ++ check_mac_o_w_r_c (0); ++ check_cipher_o_s_e_d_c (0); + check_pk_hash_sign_verify (); + ++ xgcry_control ((GCRYCTL_FIPS_REJECT_NON_FIPS, ++ (GCRY_FIPS_FLAG_REJECT_MD_MD5 ++ | GCRY_FIPS_FLAG_REJECT_COMPAT110))); ++ ++ check_md_o_w_r_c (1); ++ check_mac_o_w_r_c (1); ++ check_cipher_o_s_e_d_c (1); ++ + return !!error_count; + } diff --git a/libgcrypt-fips-cipher-Add-GCRY_FIPS_FLAG_REJECT_PK_FLAGS.patch b/libgcrypt-fips-cipher-Add-GCRY_FIPS_FLAG_REJECT_PK_FLAGS.patch new file mode 100644 index 0000000..310e5e5 --- /dev/null +++ b/libgcrypt-fips-cipher-Add-GCRY_FIPS_FLAG_REJECT_PK_FLAGS.patch @@ -0,0 +1,80 @@ +From 0414e126b939f0b11ecf441908d923e87c1caf02 Mon Sep 17 00:00:00 2001 +From: NIIBE Yutaka +Date: Thu, 6 Mar 2025 08:57:51 +0900 +Subject: [PATCH 06/14] fips,cipher: Add GCRY_FIPS_FLAG_REJECT_PK_FLAGS. +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* src/gcrypt.h.in (GCRY_FIPS_FLAG_REJECT_PK_FLAGS): New. +* cipher/pubkey-util.c (_gcry_pk_util_parse_flaglist): Keep the +behavior of 1.10. +* cipher/rsa.c (rsa_decrypt, rsa_sign): Likewise. + +-- + +GnuPG-bug-id: 7338 +Signed-off-by: NIIBE Yutaka +Signed-off-by: Lucas Mülling +--- + cipher/pubkey-util.c | 2 +- + cipher/rsa.c | 4 ++-- + src/gcrypt.h.in | 3 ++- + 3 files changed, 5 insertions(+), 4 deletions(-) + +diff --git a/cipher/pubkey-util.c b/cipher/pubkey-util.c +index 9c927638..e7355569 100644 +--- a/cipher/pubkey-util.c ++++ b/cipher/pubkey-util.c +@@ -202,7 +202,7 @@ _gcry_pk_util_parse_flaglist (gcry_sexp_t list, + + if (fips_mode () && igninvflag) + { +- if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK_FLAGS)) + rc = GPG_ERR_INV_FLAG; + else + fips_service_indicator_mark_non_compliant (); +diff --git a/cipher/rsa.c b/cipher/rsa.c +index dce76414..7e086df4 100644 +--- a/cipher/rsa.c ++++ b/cipher/rsa.c +@@ -1504,7 +1504,7 @@ rsa_decrypt (gcry_sexp_t *r_plain, gcry_sexp_t s_data, gcry_sexp_t keyparms) + { + if (fips_mode ()) + { +- if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK_FLAGS)) + { + rc = GPG_ERR_INV_FLAG; + goto leave; +@@ -1649,7 +1649,7 @@ rsa_sign (gcry_sexp_t *r_sig, gcry_sexp_t s_data, gcry_sexp_t keyparms) + { + if (fips_mode ()) + { +- if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK_FLAGS)) + { + rc = GPG_ERR_INV_FLAG; + goto leave; +diff --git a/src/gcrypt.h.in b/src/gcrypt.h.in +index fe3db16a..a282268d 100644 +--- a/src/gcrypt.h.in ++++ b/src/gcrypt.h.in +@@ -1991,11 +1991,12 @@ char *gcry_get_config (int mode, const char *what); + #define GCRY_FIPS_FLAG_REJECT_CIPHER_MODE (1 << 8) + /**/ + #define GCRY_FIPS_FLAG_REJECT_PK_ECC_K (1 << 10) ++#define GCRY_FIPS_FLAG_REJECT_PK_FLAGS (1 << 11) + + #define GCRY_FIPS_FLAG_REJECT_MD \ + (GCRY_FIPS_FLAG_REJECT_MD_MD5 | GCRY_FIPS_FLAG_REJECT_MD_OTHERS) + +-/* Note: Don't reject MD5, PK MD, PK GOST and PK SM2 */ ++/* Note: Don't reject MD5, PK MD, PK GOST, PK SM2, PK ECC K, and PK FLAGS */ + #define GCRY_FIPS_FLAG_REJECT_COMPAT110 \ + (GCRY_FIPS_FLAG_REJECT_MD_OTHERS \ + | GCRY_FIPS_FLAG_REJECT_MAC \ +-- +2.49.0 + diff --git a/libgcrypt-fips-cipher-Add-behavior-not-to-reject-but-mark-non-compliant.patch b/libgcrypt-fips-cipher-Add-behavior-not-to-reject-but-mark-non-compliant.patch new file mode 100644 index 0000000..9fc7734 --- /dev/null +++ b/libgcrypt-fips-cipher-Add-behavior-not-to-reject-but-mark-non-compliant.patch @@ -0,0 +1,300 @@ +From a776b692669af7a6c089779989b626c4795e30b0 Mon Sep 17 00:00:00 2001 +From: NIIBE Yutaka +Date: Fri, 20 Dec 2024 13:36:12 +0900 +Subject: [PATCH 15/19] fips,cipher: Add behavior not to reject but mark + non-compliant. +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* cipher/dsa.c (dsa_check_keysize): Check reject flag for rejection, +or mark non-comliant in FIPS mode. +* cipher/ecc-ecdsa.c (_gcry_ecc_ecdsa_sign): Likewise. +* cipher/ecc.c (ecc_sign, ecc_verify): Likewise. +* cipher/pubkey.c (_gcry_pk_encrypt, _gcry_pk_sign): Likewise. +(_gcry_pk_verify, _gcry_pk_testkey, _gcry_pk_genkey): Likewise. +(_gcry_pk_get_nbits, _gcry_pk_get_curve): Likewise. +* src/visibility.c (gcry_pk_encrypt): Initialize the indicator. +(gcry_pk_decrypt, gcry_pk_sign, gcry_pk_verify): Likewise. +(gcry_pk_testkey, gcry_pk_genkey), gcry_pk_get_nbits) +(gcry_pk_get_curve): Likewise. +-- + +GnuPG-bug-id: 7338 +Signed-off-by: NIIBE Yutaka +Signed-off-by: Lucas Mülling +--- + cipher/dsa.c | 7 ++++- + cipher/ecc-ecdsa.c | 5 +++- + cipher/ecc.c | 10 +++++-- + cipher/pubkey.c | 74 ++++++++++++++++++++++++++++++++++++++-------- + src/visibility.c | 9 +++++- + 5 files changed, 87 insertions(+), 18 deletions(-) + +diff --git a/cipher/dsa.c b/cipher/dsa.c +index e559f9f5..564edf8d 100644 +--- a/cipher/dsa.c ++++ b/cipher/dsa.c +@@ -150,7 +150,12 @@ static gpg_err_code_t + dsa_check_keysize (unsigned int nbits) + { + if (fips_mode () && nbits < 2048) +- return GPG_ERR_INV_VALUE; ++ { ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) ++ return GPG_ERR_INV_VALUE; ++ else ++ fips_service_indicator_mark_non_compliant (); ++ } + + return 0; + } +diff --git a/cipher/ecc-ecdsa.c b/cipher/ecc-ecdsa.c +index 871b0371..cb9a001c 100644 +--- a/cipher/ecc-ecdsa.c ++++ b/cipher/ecc-ecdsa.c +@@ -110,7 +110,10 @@ _gcry_ecc_ecdsa_sign (gcry_mpi_t input, gcry_mpi_t k_supplied, mpi_ec_t ec, + (hashalgo == GCRY_MD_SHAKE128 + || hashalgo == GCRY_MD_SHAKE256)) + { +- rc = GPG_ERR_DIGEST_ALGO; ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) ++ rc = GPG_ERR_DIGEST_ALGO; ++ else ++ fips_service_indicator_mark_non_compliant (); + goto leave; + } + +diff --git a/cipher/ecc.c b/cipher/ecc.c +index 65525207..8896afd0 100644 +--- a/cipher/ecc.c ++++ b/cipher/ecc.c +@@ -952,7 +952,10 @@ ecc_sign (gcry_sexp_t *r_sig, gcry_sexp_t s_data, gcry_sexp_t keyparms) + || (ec->dialect == ECC_DIALECT_SAFECURVE + && ctx.hash_algo != GCRY_MD_SHAKE256))) + { +- rc = GPG_ERR_DIGEST_ALGO; ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) ++ rc = GPG_ERR_DIGEST_ALGO; ++ else ++ fips_service_indicator_mark_non_compliant (); + goto leave; + } + } +@@ -1074,7 +1077,10 @@ ecc_verify (gcry_sexp_t s_sig, gcry_sexp_t s_data, gcry_sexp_t s_keyparms) + || (ec->dialect == ECC_DIALECT_SAFECURVE + && ctx.hash_algo != GCRY_MD_SHAKE256))) + { +- rc = GPG_ERR_DIGEST_ALGO; ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) ++ rc = GPG_ERR_DIGEST_ALGO; ++ else ++ fips_service_indicator_mark_non_compliant (); + goto leave; + } + } +diff --git a/cipher/pubkey.c b/cipher/pubkey.c +index 4d7743cc..aacf9f5a 100644 +--- a/cipher/pubkey.c ++++ b/cipher/pubkey.c +@@ -328,7 +328,12 @@ _gcry_pk_encrypt (gcry_sexp_t *r_ciph, gcry_sexp_t s_data, gcry_sexp_t s_pkey) + if (spec->flags.disabled) + rc = GPG_ERR_PUBKEY_ALGO; + else if (!spec->flags.fips && fips_mode ()) +- rc = GPG_ERR_PUBKEY_ALGO; ++ { ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) ++ rc = GPG_ERR_PUBKEY_ALGO; ++ else ++ fips_service_indicator_mark_non_compliant (); ++ } + else if (spec->encrypt) + rc = spec->encrypt (r_ciph, s_data, keyparms); + else +@@ -441,7 +446,12 @@ _gcry_pk_sign (gcry_sexp_t *r_sig, gcry_sexp_t s_hash, gcry_sexp_t s_skey) + if (spec->flags.disabled) + rc = GPG_ERR_PUBKEY_ALGO; + else if (!spec->flags.fips && fips_mode ()) +- rc = GPG_ERR_PUBKEY_ALGO; ++ { ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) ++ rc = GPG_ERR_PUBKEY_ALGO; ++ else ++ fips_service_indicator_mark_non_compliant (); ++ } + else if (spec->sign) + rc = spec->sign (r_sig, s_hash, keyparms); + else +@@ -663,7 +673,12 @@ _gcry_pk_verify (gcry_sexp_t s_sig, gcry_sexp_t s_hash, gcry_sexp_t s_pkey) + if (spec->flags.disabled) + rc = GPG_ERR_PUBKEY_ALGO; + else if (!spec->flags.fips && fips_mode ()) +- rc = GPG_ERR_PUBKEY_ALGO; ++ { ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) ++ rc = GPG_ERR_PUBKEY_ALGO; ++ else ++ fips_service_indicator_mark_non_compliant (); ++ } + else if (spec->verify) + rc = spec->verify (s_sig, s_hash, keyparms); + else +@@ -747,7 +762,12 @@ _gcry_pk_testkey (gcry_sexp_t s_key) + if (spec->flags.disabled) + rc = GPG_ERR_PUBKEY_ALGO; + else if (!spec->flags.fips && fips_mode ()) +- rc = GPG_ERR_PUBKEY_ALGO; ++ { ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) ++ rc = GPG_ERR_PUBKEY_ALGO; ++ else ++ fips_service_indicator_mark_non_compliant (); ++ } + else if (spec->check_secret_key) + rc = spec->check_secret_key (keyparms); + else +@@ -826,11 +846,21 @@ _gcry_pk_genkey (gcry_sexp_t *r_key, gcry_sexp_t s_parms) + spec = spec_from_name (name); + xfree (name); + name = NULL; +- if (!spec || spec->flags.disabled || (!spec->flags.fips && fips_mode ())) ++ if (!spec || spec->flags.disabled) + { + rc = GPG_ERR_PUBKEY_ALGO; /* Unknown algorithm. */ + goto leave; + } ++ else if (!spec->flags.fips && fips_mode ()) ++ { ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) ++ { ++ rc = GPG_ERR_PUBKEY_ALGO; ++ goto leave; ++ } ++ else ++ fips_service_indicator_mark_non_compliant (); ++ } + + if (spec->generate) + rc = spec->generate (list, r_key); +@@ -866,12 +896,22 @@ _gcry_pk_get_nbits (gcry_sexp_t key) + + if (spec_from_sexp (key, 0, &spec, &parms)) + return 0; /* Error - 0 is a suitable indication for that. */ ++ + if (spec->flags.disabled) +- return 0; +- if (!spec->flags.fips && fips_mode ()) +- return 0; ++ nbits = 0; /* Error */ ++ else if (!spec->flags.fips && fips_mode ()) ++ { ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) ++ nbits = 0; /* Error */ ++ else ++ { ++ fips_service_indicator_mark_non_compliant (); ++ nbits = spec->get_nbits (parms); ++ } ++ } ++ else ++ nbits = spec->get_nbits (parms); + +- nbits = spec->get_nbits (parms); + sexp_release (parms); + return nbits; + } +@@ -1004,10 +1044,18 @@ _gcry_pk_get_curve (gcry_sexp_t key, int iterator, unsigned int *r_nbits) + } + + if (spec->flags.disabled) +- return NULL; +- if (!spec->flags.fips && fips_mode ()) +- return NULL; +- if (spec->get_curve) ++ result = NULL; ++ else if (!spec->flags.fips && fips_mode ()) ++ { ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) ++ result = NULL; ++ else ++ { ++ fips_service_indicator_mark_non_compliant (); ++ result = spec->get_curve (keyparms, iterator, r_nbits); ++ } ++ } ++ else if (spec->get_curve) + result = spec->get_curve (keyparms, iterator, r_nbits); + + sexp_release (keyparms); +diff --git a/src/visibility.c b/src/visibility.c +index d22c8b59..e02d6cfe 100644 +--- a/src/visibility.c ++++ b/src/visibility.c +@@ -1022,6 +1022,7 @@ gcry_pk_encrypt (gcry_sexp_t *result, gcry_sexp_t data, gcry_sexp_t pkey) + *result = NULL; + return gpg_error (fips_not_operational ()); + } ++ fips_service_indicator_init (); + return gpg_error (_gcry_pk_encrypt (result, data, pkey)); + } + +@@ -1033,6 +1034,7 @@ gcry_pk_decrypt (gcry_sexp_t *result, gcry_sexp_t data, gcry_sexp_t skey) + *result = NULL; + return gpg_error (fips_not_operational ()); + } ++ fips_service_indicator_init (); + return gpg_error (_gcry_pk_decrypt (result, data, skey)); + } + +@@ -1044,6 +1046,7 @@ gcry_pk_sign (gcry_sexp_t *result, gcry_sexp_t data, gcry_sexp_t skey) + *result = NULL; + return gpg_error (fips_not_operational ()); + } ++ fips_service_indicator_init (); + return gpg_error (_gcry_pk_sign (result, data, skey)); + } + +@@ -1065,6 +1068,7 @@ gcry_pk_verify (gcry_sexp_t sigval, gcry_sexp_t data, gcry_sexp_t pkey) + { + if (!fips_is_operational ()) + return gpg_error (fips_not_operational ()); ++ fips_service_indicator_init (); + return gpg_error (_gcry_pk_verify (sigval, data, pkey)); + } + +@@ -1089,6 +1093,7 @@ gcry_pk_testkey (gcry_sexp_t key) + { + if (!fips_is_operational ()) + return gpg_error (fips_not_operational ()); ++ fips_service_indicator_init (); + return gpg_error (_gcry_pk_testkey (key)); + } + +@@ -1100,6 +1105,7 @@ gcry_pk_genkey (gcry_sexp_t *r_key, gcry_sexp_t s_parms) + *r_key = NULL; + return gpg_error (fips_not_operational ()); + } ++ fips_service_indicator_init (); + return gpg_error (_gcry_pk_genkey (r_key, s_parms)); + } + +@@ -1138,7 +1144,7 @@ gcry_pk_get_nbits (gcry_sexp_t key) + (void)fips_not_operational (); + return 0; + } +- ++ fips_service_indicator_init (); + return _gcry_pk_get_nbits (key); + } + +@@ -1161,6 +1167,7 @@ gcry_pk_get_curve (gcry_sexp_t key, int iterator, unsigned int *r_nbits) + (void)fips_not_operational (); + return NULL; + } ++ fips_service_indicator_init (); + return _gcry_pk_get_curve (key, iterator, r_nbits); + } + +-- +2.49.0 + diff --git a/libgcrypt-fips-cipher-Do-the-computation-when-marking-non-compliant.patch b/libgcrypt-fips-cipher-Do-the-computation-when-marking-non-compliant.patch new file mode 100644 index 0000000..8f71866 --- /dev/null +++ b/libgcrypt-fips-cipher-Do-the-computation-when-marking-non-compliant.patch @@ -0,0 +1,160 @@ +From 54a6617b3679cfeb6d986ddf3c9c73641929f02c Mon Sep 17 00:00:00 2001 +From: NIIBE Yutaka +Date: Tue, 4 Mar 2025 10:32:49 +0900 +Subject: [PATCH 4/4] fips,cipher: Do the computation when marking + non-compliant. +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* cipher/ecc-ecdsa.c (_gcry_ecc_ecdsa_sign): Continue the computation +when marking non-compliant. +* cipher/pubkey.c (_gcry_pk_encrypt, _gcry_pk_sign): Likewise. +(_gcry_pk_sign_md, _gcry_pk_verify, _gcry_pk_verify_md): Likewise. +(_gcry_pk_testkey): Likewise. + +-- + +Fixes-commit: a776b692669af7a6c089779989b626c4795e30b0 +GnuPG-bug-id: 7338 +Signed-off-by: NIIBE Yutaka +Signed-off-by: Lucas Mülling +--- + cipher/ecc-ecdsa.c | 6 ++++-- + cipher/pubkey.c | 48 ++++++++++++++++++++++++++++++++++------------ + 2 files changed, 40 insertions(+), 14 deletions(-) + +diff --git a/cipher/ecc-ecdsa.c b/cipher/ecc-ecdsa.c +index cb9a001c..9da8e6dc 100644 +--- a/cipher/ecc-ecdsa.c ++++ b/cipher/ecc-ecdsa.c +@@ -111,10 +111,12 @@ _gcry_ecc_ecdsa_sign (gcry_mpi_t input, gcry_mpi_t k_supplied, mpi_ec_t ec, + || hashalgo == GCRY_MD_SHAKE256)) + { + if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) +- rc = GPG_ERR_DIGEST_ALGO; ++ { ++ rc = GPG_ERR_DIGEST_ALGO; ++ goto leave; ++ } + else + fips_service_indicator_mark_non_compliant (); +- goto leave; + } + + /* Use Pornin's method for deterministic DSA. If this +diff --git a/cipher/pubkey.c b/cipher/pubkey.c +index c28ec124..3778f482 100644 +--- a/cipher/pubkey.c ++++ b/cipher/pubkey.c +@@ -330,11 +330,15 @@ _gcry_pk_encrypt (gcry_sexp_t *r_ciph, gcry_sexp_t s_data, gcry_sexp_t s_pkey) + else if (!spec->flags.fips && fips_mode ()) + { + if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) +- rc = GPG_ERR_PUBKEY_ALGO; ++ { ++ rc = GPG_ERR_PUBKEY_ALGO; ++ goto leave; ++ } + else + fips_service_indicator_mark_non_compliant (); + } +- else if (spec->encrypt) ++ ++ if (spec->encrypt) + rc = spec->encrypt (r_ciph, s_data, keyparms); + else + rc = GPG_ERR_NOT_IMPLEMENTED; +@@ -448,11 +452,15 @@ _gcry_pk_sign (gcry_sexp_t *r_sig, gcry_sexp_t s_hash, gcry_sexp_t s_skey) + else if (!spec->flags.fips && fips_mode ()) + { + if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) +- rc = GPG_ERR_PUBKEY_ALGO; ++ { ++ rc = GPG_ERR_PUBKEY_ALGO; ++ goto leave; ++ } + else + fips_service_indicator_mark_non_compliant (); + } +- else if (spec->sign) ++ ++ if (spec->sign) + rc = spec->sign (r_sig, s_hash, keyparms); + else + rc = GPG_ERR_NOT_IMPLEMENTED; +@@ -649,11 +657,15 @@ _gcry_pk_sign_md (gcry_sexp_t *r_sig, const char *tmpl, gcry_md_hd_t hd_orig, + else if (!spec->flags.fips && fips_mode ()) + { + if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) +- rc = GPG_ERR_PUBKEY_ALGO; ++ { ++ rc = GPG_ERR_PUBKEY_ALGO; ++ goto leave; ++ } + else + fips_service_indicator_mark_non_compliant (); + } +- else if (spec->sign) ++ ++ if (spec->sign) + rc = spec->sign (r_sig, s_data, keyparms); + else + rc = GPG_ERR_NOT_IMPLEMENTED; +@@ -688,11 +700,15 @@ _gcry_pk_verify (gcry_sexp_t s_sig, gcry_sexp_t s_hash, gcry_sexp_t s_pkey) + else if (!spec->flags.fips && fips_mode ()) + { + if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) +- rc = GPG_ERR_PUBKEY_ALGO; ++ { ++ rc = GPG_ERR_PUBKEY_ALGO; ++ goto leave; ++ } + else + fips_service_indicator_mark_non_compliant (); + } +- else if (spec->verify) ++ ++ if (spec->verify) + rc = spec->verify (s_sig, s_hash, keyparms); + else + rc = GPG_ERR_NOT_IMPLEMENTED; +@@ -736,11 +752,15 @@ _gcry_pk_verify_md (gcry_sexp_t s_sig, const char *tmpl, gcry_md_hd_t hd_orig, + else if (!spec->flags.fips && fips_mode ()) + { + if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) +- rc = GPG_ERR_PUBKEY_ALGO; ++ { ++ rc = GPG_ERR_PUBKEY_ALGO; ++ goto leave; ++ } + else + fips_service_indicator_mark_non_compliant (); + } +- else if (spec->verify) ++ ++ if (spec->verify) + rc = spec->verify (s_sig, s_data, keyparms); + else + rc = GPG_ERR_NOT_IMPLEMENTED; +@@ -777,11 +797,15 @@ _gcry_pk_testkey (gcry_sexp_t s_key) + else if (!spec->flags.fips && fips_mode ()) + { + if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) +- rc = GPG_ERR_PUBKEY_ALGO; ++ { ++ rc = GPG_ERR_PUBKEY_ALGO; ++ goto leave; ++ } + else + fips_service_indicator_mark_non_compliant (); + } +- else if (spec->check_secret_key) ++ ++ if (spec->check_secret_key) + rc = spec->check_secret_key (keyparms); + else + rc = GPG_ERR_NOT_IMPLEMENTED; +-- +2.49.0 + diff --git a/libgcrypt-fips-cipher-Fix-memory-leak-for-gcry_pk_hash_sign.patch b/libgcrypt-fips-cipher-Fix-memory-leak-for-gcry_pk_hash_sign.patch new file mode 100644 index 0000000..445136e --- /dev/null +++ b/libgcrypt-fips-cipher-Fix-memory-leak-for-gcry_pk_hash_sign.patch @@ -0,0 +1,76 @@ +From 5e925e6c348450bf80b4560abac9a035903bff59 Mon Sep 17 00:00:00 2001 +From: NIIBE Yutaka +Date: Mon, 6 Jan 2025 12:01:56 +0900 +Subject: [PATCH 19/19] fips,cipher: Fix memory leak for gcry_pk_hash_sign. +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* cipher/pubkey.c (prepare_datasexp_to_be_signed): Release +copied HD when error. + +-- + +GnuPG-bug-id: 7338 +Signed-off-by: NIIBE Yutaka +Signed-off-by: Lucas Mülling +--- + cipher/pubkey.c | 21 +++++++++++++++++---- + 1 file changed, 17 insertions(+), 4 deletions(-) + +diff --git a/cipher/pubkey.c b/cipher/pubkey.c +index aacf9f5a..c28ec124 100644 +--- a/cipher/pubkey.c ++++ b/cipher/pubkey.c +@@ -512,7 +512,10 @@ prepare_datasexp_to_be_signed (const char *tmpl, gcry_md_hd_t hd, + /* Check if it has fixed hash name or %s */ + s = strstr (tmpl, "(hash "); + if (s == NULL) +- return GPG_ERR_DIGEST_ALGO; ++ { ++ _gcry_md_close (hd); ++ return GPG_ERR_DIGEST_ALGO; ++ } + + s += 6; + if (!strncmp (s, "%s", 2)) +@@ -522,7 +525,10 @@ prepare_datasexp_to_be_signed (const char *tmpl, gcry_md_hd_t hd, + if (fips_mode () && algo == GCRY_MD_SHA1) + { + if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) +- return GPG_ERR_DIGEST_ALGO; ++ { ++ _gcry_md_close (hd); ++ return GPG_ERR_DIGEST_ALGO; ++ } + else + fips_service_indicator_mark_non_compliant (); + } +@@ -541,7 +547,11 @@ prepare_datasexp_to_be_signed (const char *tmpl, gcry_md_hd_t hd, + + digest_name_supplied = xtrymalloc (p - s + 1); + if (!digest_name_supplied) +- return gpg_error_from_syserror (); ++ { ++ rc = gpg_err_code_from_syserror (); ++ _gcry_md_close (hd); ++ return rc; ++ } + memcpy (digest_name_supplied, s, p - s); + digest_name_supplied[p - s] = 0; + +@@ -555,7 +565,10 @@ prepare_datasexp_to_be_signed (const char *tmpl, gcry_md_hd_t hd, + else if (fips_mode () && algo == GCRY_MD_SHA1) + { + if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) +- return GPG_ERR_DIGEST_ALGO; ++ { ++ _gcry_md_close (hd); ++ return GPG_ERR_DIGEST_ALGO; ++ } + else + fips_service_indicator_mark_non_compliant (); + } +-- +2.49.0 + diff --git a/libgcrypt-fips-cipher-Implement-FIPS-service-indicator-for-gcry_pk_hash_-API.patch b/libgcrypt-fips-cipher-Implement-FIPS-service-indicator-for-gcry_pk_hash_-API.patch new file mode 100644 index 0000000..0490e38 --- /dev/null +++ b/libgcrypt-fips-cipher-Implement-FIPS-service-indicator-for-gcry_pk_hash_-API.patch @@ -0,0 +1,360 @@ +From edb43bc290046bd22548bf69ae2fbeb453112e44 Mon Sep 17 00:00:00 2001 +From: NIIBE Yutaka +Date: Wed, 18 Dec 2024 14:18:26 +0900 +Subject: [PATCH 11/19] fips,cipher: Implement FIPS service indicator for + gcry_pk_hash_ API. +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* src/visibility.c (gcry_pk_hash_sign): Initialize the indicator. +(gcry_pk_hash_verify): Likewise. +* tests/t-fips-service-ind.c (check_pk_hash_sign_verify): New. +(main): Call check_pk_hash_sign_verify. +* cipher/ecc-curves.c (_gcry_ecc_fill_in_curve): Don't reject, but +mark non-compliance. +* cipher/pubkey.c (prepare_datasexp_to_be_signed): Likewise. +(_gcry_pk_sign_md, _gcry_pk_verify_md): Likewise. + +-- + +GnuPG-bug-id: 7338 +Signed-off-by: NIIBE Yutaka +Signed-off-by: Lucas Mülling +--- + cipher/ecc-curves.c | 2 +- + cipher/pubkey.c | 20 ++-- + src/visibility.c | 2 + + tests/t-fips-service-ind.c | 209 +++++++++++++++++++++++++++++++++++++ + 4 files changed, 222 insertions(+), 11 deletions(-) + +diff --git a/cipher/ecc-curves.c b/cipher/ecc-curves.c +index 17fa5505..ddf9cbe1 100644 +--- a/cipher/ecc-curves.c ++++ b/cipher/ecc-curves.c +@@ -645,7 +645,7 @@ _gcry_ecc_fill_in_curve (unsigned int nbits, const char *name, + possible to bypass this check by specifying the curve parameters + directly. */ + if (fips_mode () && !domain_parms[idx].fips ) +- return GPG_ERR_NOT_SUPPORTED; ++ fips_service_indicator_mark_non_compliant (); + + switch (domain_parms[idx].model) + { +diff --git a/cipher/pubkey.c b/cipher/pubkey.c +index 214bd611..e2e54199 100644 +--- a/cipher/pubkey.c ++++ b/cipher/pubkey.c +@@ -510,10 +510,7 @@ prepare_datasexp_to_be_signed (const char *tmpl, gcry_md_hd_t hd, + algo = _gcry_md_get_algo (hd); + + if (fips_mode () && algo == GCRY_MD_SHA1) +- { +- _gcry_md_close (hd); +- return GPG_ERR_DIGEST_ALGO; +- } ++ fips_service_indicator_mark_non_compliant (); + + digest_name = _gcry_md_algo_name (algo); + digest_size = (int)_gcry_md_get_algo_dlen (algo); +@@ -535,12 +532,13 @@ prepare_datasexp_to_be_signed (const char *tmpl, gcry_md_hd_t hd, + + algo = _gcry_md_map_name (digest_name_supplied); + xfree (digest_name_supplied); +- if (algo == 0 +- || (fips_mode () && algo == GCRY_MD_SHA1)) ++ if (algo == 0) + { + _gcry_md_close (hd); + return GPG_ERR_DIGEST_ALGO; + } ++ else if (fips_mode () && algo == GCRY_MD_SHA1) ++ fips_service_indicator_mark_non_compliant (); + + digest_size = (int)_gcry_md_get_algo_dlen (algo); + digest = _gcry_md_read (hd, algo); +@@ -613,10 +611,11 @@ _gcry_pk_sign_md (gcry_sexp_t *r_sig, const char *tmpl, gcry_md_hd_t hd_orig, + if (rc) + goto leave; + ++ if (!spec->flags.fips && fips_mode ()) ++ fips_service_indicator_mark_non_compliant (); ++ + if (spec->flags.disabled) + rc = GPG_ERR_PUBKEY_ALGO; +- else if (!spec->flags.fips && fips_mode ()) +- rc = GPG_ERR_PUBKEY_ALGO; + else if (spec->sign) + rc = spec->sign (r_sig, s_data, keyparms); + else +@@ -690,10 +689,11 @@ _gcry_pk_verify_md (gcry_sexp_t s_sig, const char *tmpl, gcry_md_hd_t hd_orig, + if (rc) + goto leave; + ++ if (!spec->flags.fips && fips_mode ()) ++ fips_service_indicator_mark_non_compliant (); ++ + if (spec->flags.disabled) + rc = GPG_ERR_PUBKEY_ALGO; +- else if (!spec->flags.fips && fips_mode ()) +- rc = GPG_ERR_PUBKEY_ALGO; + else if (spec->verify) + rc = spec->verify (s_sig, s_data, keyparms); + else +diff --git a/src/visibility.c b/src/visibility.c +index c9d07f0b..d22c8b59 100644 +--- a/src/visibility.c ++++ b/src/visibility.c +@@ -1056,6 +1056,7 @@ gcry_pk_hash_sign (gcry_sexp_t *result, const char *data_tmpl, gcry_sexp_t skey, + *result = NULL; + return gpg_error (fips_not_operational ()); + } ++ fips_service_indicator_init (); + return gpg_error (_gcry_pk_sign_md (result, data_tmpl, hd, skey, ctx)); + } + +@@ -1073,6 +1074,7 @@ gcry_pk_hash_verify (gcry_sexp_t sigval, const char *data_tmpl, gcry_sexp_t pkey + { + if (!fips_is_operational ()) + return gpg_error (fips_not_operational ()); ++ fips_service_indicator_init (); + return gpg_error (_gcry_pk_verify_md (sigval, data_tmpl, hd, pkey, ctx)); + } + +diff --git a/tests/t-fips-service-ind.c b/tests/t-fips-service-ind.c +index 4b13436f..9a22d696 100644 +--- a/tests/t-fips-service-ind.c ++++ b/tests/t-fips-service-ind.c +@@ -29,6 +29,7 @@ + + #define PGM "t-fips-service-ind" + ++#define NEED_HEX2BUFFER + #include "t-common.h" + static int in_fips_mode; + #define MAX_DATA_LEN 1040 +@@ -39,6 +40,213 @@ static int in_fips_mode; + # include + #endif + ++/* Check gcry_pk_hash_sign, gcry_pk_hash_verify API. */ ++static void ++check_pk_hash_sign_verify (void) ++{ ++ static struct { ++ int md_algo; ++ const char *prvkey; ++ const char *pubkey; ++ const char *data_tmpl; ++ const char *k; ++ int expect_failure; ++ int expect_failure_hash; ++ } tv[] = { ++ { /* non-compliant hash */ ++ GCRY_MD_BLAKE2B_512, ++ "(private-key (ecc (curve nistp256)" ++ " (d #519b423d715f8b581f4fa8ee59f4771a5b44c8130b4e3eacca54a56dda72b464#)))", ++ "(public-key (ecc (curve nistp256)" ++ " (q #041ccbe91c075fc7f4f033bfa248db8fccd3565de94bbfb12f3c59ff46c271bf83" ++ "ce4014c68811f9a21a1fdb2c0e6113e06db7ca93b7404e78dc7ccd5ca89a4ca9#)))", ++ "(data(flags raw)(hash %s %b)(label %b))", ++ "94a1bbb14b906a61a280f245f9e93c7f3b4a6247824f5d33b9670787642a68de", ++ 1, 1 ++ }, ++ { /* non-compliant curve */ ++ GCRY_MD_SHA256, ++ "(private-key (ecc (curve secp256k1)" ++ " (d #c2cdf0a8b0a83b35ace53f097b5e6e6a0a1f2d40535eff1cf434f52a43d59d8f#)))", ++ ++ "(public-key (ecc (curve secp256k1)" ++ " (q #046fcc37ea5e9e09fec6c83e5fbd7a745e3eee81d16ebd861c9e66f55518c19798" ++ "4e9f113c07f875691df8afc1029496fc4cb9509b39dcd38f251a83359cc8b4f7#)))", ++ "(data(flags raw)(hash %s %b)(label %b))", ++ "94a1bbb14b906a61a280f245f9e93c7f3b4a6247824f5d33b9670787642a68de", ++ 1, 0 ++ }, ++ { ++ GCRY_MD_SHA256, ++ "(private-key (ecc (curve nistp256)" ++ " (d #519b423d715f8b581f4fa8ee59f4771a5b44c8130b4e3eacca54a56dda72b464#)))", ++ "(public-key (ecc (curve nistp256)" ++ " (q #041ccbe91c075fc7f4f033bfa248db8fccd3565de94bbfb12f3c59ff46c271bf83" ++ "ce4014c68811f9a21a1fdb2c0e6113e06db7ca93b7404e78dc7ccd5ca89a4ca9#)))", ++ "(data(flags raw)(hash %s %b)(label %b))", ++ "94a1bbb14b906a61a280f245f9e93c7f3b4a6247824f5d33b9670787642a68de", ++ 0, 0 ++ } ++ }; ++ int tvidx; ++ gpg_error_t err; ++ gpg_err_code_t ec; ++ const char *msg = "Takerufuji Mikiya, who won the championship in March 2024"; ++ int msglen; ++ ++ msglen = strlen (msg); ++ for (tvidx=0; tvidx < DIM(tv); tvidx++) ++ { ++ gcry_md_hd_t hd = NULL; ++ gcry_sexp_t s_sk = NULL; ++ gcry_sexp_t s_pk = NULL; ++ void *buffer = NULL; ++ size_t buflen; ++ gcry_ctx_t ctx = NULL; ++ gcry_sexp_t s_sig= NULL; ++ ++ if (verbose) ++ info ("checking gcry_pk_hash_ test %d\n", tvidx); ++ ++ err = gcry_md_open (&hd, tv[tvidx].md_algo, 0); ++ if (err) ++ { ++ fail ("algo %d, gcry_md_open failed: %s\n", tv[tvidx].md_algo, ++ gpg_strerror (err)); ++ goto next; ++ } ++ ++ ec = gcry_get_fips_service_indicator (); ++ if (ec == GPG_ERR_INV_OP) ++ { ++ /* libgcrypt is old, no support of the FIPS service indicator. */ ++ fail ("gcry_pk_hash test %d unexpectedly failed to check the FIPS service indicator.\n", ++ tvidx); ++ goto next; ++ } ++ ++ if (in_fips_mode && !tv[tvidx].expect_failure_hash && ec) ++ { ++ /* Success with the FIPS service indicator == 0 expected, but != 0. */ ++ fail ("gcry_pk_hash test %d unexpectedly set the indicator in FIPS mode.\n", ++ tvidx); ++ goto next; ++ } ++ else if (in_fips_mode && tv[tvidx].expect_failure_hash && !ec) ++ { ++ /* Success with the FIPS service indicator != 0 expected, but == 0. */ ++ fail ("gcry_pk_hash test %d unexpectedly cleared the indicator in FIPS mode.\n", ++ tvidx); ++ goto next; ++ } ++ ++ err = gcry_sexp_build (&s_sk, NULL, tv[tvidx].prvkey); ++ if (err) ++ { ++ fail ("error building SEXP for test, %s: %s", ++ "sk", gpg_strerror (err)); ++ goto next; ++ } ++ ++ err = gcry_sexp_build (&s_pk, NULL, tv[tvidx].pubkey); ++ if (err) ++ { ++ fail ("error building SEXP for test, %s: %s", ++ "pk", gpg_strerror (err)); ++ goto next; ++ } ++ ++ if (!(buffer = hex2buffer (tv[tvidx].k, &buflen))) ++ { ++ fail ("error parsing for test, %s: %s", ++ "msg", "invalid hex string"); ++ goto next; ++ } ++ ++ err = gcry_pk_random_override_new (&ctx, buffer, buflen); ++ if (err) ++ { ++ fail ("error setting 'k' for test: %s", ++ gpg_strerror (err)); ++ goto next; ++ } ++ ++ gcry_md_write (hd, msg, msglen); ++ ++ err = gcry_pk_hash_sign (&s_sig, tv[tvidx].data_tmpl, s_sk, hd, ctx); ++ if (err) ++ { ++ fail ("gcry_pk_hash_sign failed: %s", gpg_strerror (err)); ++ goto next; ++ } ++ ++ ec = gcry_get_fips_service_indicator (); ++ if (ec == GPG_ERR_INV_OP) ++ { ++ /* libgcrypt is old, no support of the FIPS service indicator. */ ++ fail ("gcry_pk_hash test %d unexpectedly failed to check the FIPS service indicator.\n", ++ tvidx); ++ goto next; ++ } ++ ++ if (in_fips_mode && !tv[tvidx].expect_failure && ec) ++ { ++ /* Success with the FIPS service indicator == 0 expected, but != 0. */ ++ fail ("gcry_pk_hash test %d unexpectedly set the indicator in FIPS mode.\n", ++ tvidx); ++ goto next; ++ } ++ else if (in_fips_mode && tv[tvidx].expect_failure && !ec) ++ { ++ /* Success with the FIPS service indicator != 0 expected, but == 0. */ ++ fail ("gcry_pk_hash_sign test %d unexpectedly cleared the indicator in FIPS mode.\n", ++ tvidx); ++ goto next; ++ } ++ ++ err = gcry_pk_hash_verify (s_sig, tv[tvidx].data_tmpl, s_pk, hd, ctx); ++ if (err) ++ { ++ fail ("gcry_pk_hash_verify failed for test: %s", ++ gpg_strerror (err)); ++ goto next; ++ } ++ ++ ec = gcry_get_fips_service_indicator (); ++ if (ec == GPG_ERR_INV_OP) ++ { ++ /* libgcrypt is old, no support of the FIPS service indicator. */ ++ fail ("gcry_pk_hash test %d unexpectedly failed to check the FIPS service indicator.\n", ++ tvidx); ++ goto next; ++ } ++ ++ if (in_fips_mode && !tv[tvidx].expect_failure && ec) ++ { ++ /* Success with the FIPS service indicator == 0 expected, but != 0. */ ++ fail ("gcry_pk_hash test %d unexpectedly set the indicator in FIPS mode.\n", ++ tvidx); ++ goto next; ++ } ++ else if (in_fips_mode && tv[tvidx].expect_failure && !ec) ++ { ++ /* Success with the FIPS service indicator != 0 expected, but == 0. */ ++ fail ("gcry_pk_hash_verify test %d unexpectedly cleared the indicator in FIPS mode.\n", ++ tvidx); ++ goto next; ++ } ++ ++ next: ++ gcry_sexp_release (s_sig); ++ xfree (buffer); ++ gcry_ctx_release (ctx); ++ gcry_sexp_release (s_pk); ++ gcry_sexp_release (s_sk); ++ if (hd) ++ gcry_md_close (hd); ++ } ++} ++ + /* Check gcry_cipher_open, gcry_cipher_setkey, gcry_cipher_encrypt, + gcry_cipher_decrypt, gcry_cipher_close API. */ + static void +@@ -936,6 +1144,7 @@ main (int argc, char **argv) + check_md_o_w_r_c (); + check_mac_o_w_r_c (); + check_cipher_o_s_e_d_c (); ++ check_pk_hash_sign_verify (); + + return !!error_count; + } +-- +2.49.0 + diff --git a/libgcrypt-fips-cipher-Implement-new-FIPS-service-indicator-for-cipher_open.patch b/libgcrypt-fips-cipher-Implement-new-FIPS-service-indicator-for-cipher_open.patch new file mode 100644 index 0000000..2124c48 --- /dev/null +++ b/libgcrypt-fips-cipher-Implement-new-FIPS-service-indicator-for-cipher_open.patch @@ -0,0 +1,122 @@ +From 69a5d0ed18a3ddc6f297de783c7cef5ad2257df0 Mon Sep 17 00:00:00 2001 +From: NIIBE Yutaka +Date: Fri, 13 Dec 2024 14:40:53 +0900 +Subject: [PATCH 05/19] fips,cipher: Implement new FIPS service indicator for + cipher_open. +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* src/gcrypt.h.in (GCRY_CIPHER_FLAG_REJECT_NON_FIPS): New. +* cipher/cipher.c (_gcry_cipher_open_internal): Don't reject +but mark the service indicator in FIPS mode. +(cipher_setkey): Likewise. +* src/visibility.c (gcry_cipher_open): Initialize the service +indicator. +(gcry_cipher_setkey): Likewise. + +-- + +GnuPG-bug-id: 7338 +Signed-off-by: NIIBE Yutaka +Signed-off-by: Lucas Mülling +--- + cipher/cipher.c | 23 +++++++++++++++++++---- + src/gcrypt.h.in | 3 ++- + src/visibility.c | 4 ++-- + 3 files changed, 23 insertions(+), 7 deletions(-) + +diff --git a/cipher/cipher.c b/cipher/cipher.c +index 898bb58f..7ffacf05 100644 +--- a/cipher/cipher.c ++++ b/cipher/cipher.c +@@ -509,7 +509,8 @@ gcry_err_code_t + _gcry_cipher_open_internal (gcry_cipher_hd_t *handle, + int algo, int mode, unsigned int flags) + { +- int secure = (flags & GCRY_CIPHER_SECURE); ++ int secure = !!(flags & GCRY_CIPHER_SECURE); ++ int reject_non_fips = !!(flags & GCRY_CIPHER_FLAG_REJECT_NON_FIPS); + gcry_cipher_spec_t *spec; + gcry_cipher_hd_t h = NULL; + gcry_err_code_t err; +@@ -524,7 +525,15 @@ _gcry_cipher_open_internal (gcry_cipher_hd_t *handle, + else if (spec->flags.disabled) + err = GPG_ERR_CIPHER_ALGO; + else if (!spec->flags.fips && fips_mode ()) +- err = GPG_ERR_CIPHER_ALGO; ++ { ++ if (reject_non_fips) ++ err = GPG_ERR_CIPHER_ALGO; ++ else ++ { ++ fips_service_indicator_mark_non_compliant (); ++ err = 0; ++ } ++ } + else + err = 0; + +@@ -535,7 +544,8 @@ _gcry_cipher_open_internal (gcry_cipher_hd_t *handle, + | GCRY_CIPHER_ENABLE_SYNC + | GCRY_CIPHER_CBC_CTS + | GCRY_CIPHER_CBC_MAC +- | GCRY_CIPHER_EXTENDED)) ++ | GCRY_CIPHER_EXTENDED ++ | GCRY_CIPHER_FLAG_REJECT_NON_FIPS)) + || ((flags & GCRY_CIPHER_CBC_CTS) && (flags & GCRY_CIPHER_CBC_MAC)))) + err = GPG_ERR_CIPHER_ALGO; + +@@ -765,7 +775,12 @@ cipher_setkey (gcry_cipher_hd_t c, byte *key, size_t keylen) + See "Implementation Guidance for FIPS 140-2, A.9 XTS-AES + Key Generation Requirements" for details. */ + if (buf_eq_const (key, key + keylen, keylen)) +- return GPG_ERR_WEAK_KEY; ++ { ++ if ((c->flags & GCRY_CIPHER_FLAG_REJECT_NON_FIPS)) ++ return GPG_ERR_WEAK_KEY; ++ else ++ fips_service_indicator_mark_non_compliant (); ++ } + } + } + else if (c->mode == GCRY_CIPHER_MODE_SIV) +diff --git a/src/gcrypt.h.in b/src/gcrypt.h.in +index 2a378639..2ed9914b 100644 +--- a/src/gcrypt.h.in ++++ b/src/gcrypt.h.in +@@ -992,7 +992,8 @@ enum gcry_cipher_flags + GCRY_CIPHER_ENABLE_SYNC = 2, /* Enable CFB sync mode. */ + GCRY_CIPHER_CBC_CTS = 4, /* Enable CBC cipher text stealing (CTS). */ + GCRY_CIPHER_CBC_MAC = 8, /* Enable CBC message auth. code (MAC). */ +- GCRY_CIPHER_EXTENDED = 16 /* Enable extended AES-WRAP. */ ++ GCRY_CIPHER_EXTENDED = 16, /* Enable extended AES-WRAP. */ ++ GCRY_CIPHER_FLAG_REJECT_NON_FIPS = 32 /* Reject non-FIPS-compliant algo. */ + }; + + /* Methods used for AEAD IV generation. */ +diff --git a/src/visibility.c b/src/visibility.c +index 7699f14f..d219f1a6 100644 +--- a/src/visibility.c ++++ b/src/visibility.c +@@ -736,7 +736,7 @@ gcry_cipher_open (gcry_cipher_hd_t *handle, + *handle = NULL; + return gpg_error (fips_not_operational ()); + } +- ++ fips_service_indicator_init (); + return gpg_error (_gcry_cipher_open (handle, algo, mode, flags)); + } + +@@ -751,7 +751,7 @@ gcry_cipher_setkey (gcry_cipher_hd_t hd, const void *key, size_t keylen) + { + if (!fips_is_operational ()) + return gpg_error (fips_not_operational ()); +- ++ fips_service_indicator_init (); + return gcry_error (_gcry_cipher_setkey (hd, key, keylen)); + } + +-- +2.49.0 + diff --git a/libgcrypt-fips-ecc-Add-rejecting-or-marking-for-gcry_pk_get_curve.patch b/libgcrypt-fips-ecc-Add-rejecting-or-marking-for-gcry_pk_get_curve.patch new file mode 100644 index 0000000..27fd75b --- /dev/null +++ b/libgcrypt-fips-ecc-Add-rejecting-or-marking-for-gcry_pk_get_curve.patch @@ -0,0 +1,43 @@ +From c6a092abbe7bea315394b15f28fd231dae0e4d7c Mon Sep 17 00:00:00 2001 +From: NIIBE Yutaka +Date: Tue, 24 Dec 2024 17:01:45 +0900 +Subject: [PATCH 16/19] fips,ecc: Add rejecting or marking for + gcry_pk_get_curve. +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* cipher/ecc-curves.c (_gcry_ecc_get_curve): Check under FIPS mode. + +-- + +GnuPG-bug-id: 7338 +Signed-off-by: NIIBE Yutaka +Signed-off-by: Lucas Mülling +--- + cipher/ecc-curves.c | 9 +++++++++ + 1 file changed, 9 insertions(+) + +diff --git a/cipher/ecc-curves.c b/cipher/ecc-curves.c +index fe0a1eb2..975f6a07 100644 +--- a/cipher/ecc-curves.c ++++ b/cipher/ecc-curves.c +@@ -844,6 +844,15 @@ _gcry_ecc_get_curve (gcry_sexp_t keyparms, int iterator, unsigned int *r_nbits) + if (r_nbits) + *r_nbits = domain_parms[idx].nbits; + } ++ ++ if (fips_mode () && !domain_parms[idx].fips) ++ { ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) ++ return NULL; ++ else ++ fips_service_indicator_mark_non_compliant (); ++ } ++ + return result; + } + +-- +2.49.0 + diff --git a/libgcrypt-fips-ecc-Check-DATA-in-gcry_pk_sign-verify-in-FIPS-mode.patch b/libgcrypt-fips-ecc-Check-DATA-in-gcry_pk_sign-verify-in-FIPS-mode.patch new file mode 100644 index 0000000..310c5c9 --- /dev/null +++ b/libgcrypt-fips-ecc-Check-DATA-in-gcry_pk_sign-verify-in-FIPS-mode.patch @@ -0,0 +1,282 @@ +From 53c97483b17fee280e24f595bc0d82d9b362ffde Mon Sep 17 00:00:00 2001 +From: NIIBE Yutaka +Date: Thu, 26 Dec 2024 11:12:48 +0900 +Subject: [PATCH 18/19] fips,ecc: Check DATA in gcry_pk_sign/verify in FIPS + mode. +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* src/gcrypt.h.in (GCRY_FIPS_FLAG_REJECT_PK_MD): New. +(GCRY_FIPS_FLAG_REJECT_PK_GOST_SM2): New. + +* cipher/ecc.c (ecc_sign): Check if GOST or SM2. Check if hash is +compliant. +(ecc_verify): Likewise. +* tests/t-fips-service-ind.c (check_pk_s_v): Modify tests including +hash compliance. + +-- + +GnuPG-bug-id: 7338 +Signed-off-by: NIIBE Yutaka +Signed-off-by: Lucas Mülling +--- + cipher/ecc.c | 70 +++++++++++++++++++++++++++++++++++--- + src/gcrypt.h.in | 4 ++- + tests/t-fips-service-ind.c | 52 ++++++++++++++++++++-------- + 3 files changed, 107 insertions(+), 19 deletions(-) + +diff --git a/cipher/ecc.c b/cipher/ecc.c +index 8896afd0..525523ed 100644 +--- a/cipher/ecc.c ++++ b/cipher/ecc.c +@@ -941,6 +941,18 @@ ecc_sign (gcry_sexp_t *r_sig, gcry_sexp_t s_data, gcry_sexp_t keyparms) + if (rc) + goto leave; + ++ if (fips_mode () ++ && ((ctx.flags & PUBKEY_FLAG_GOST) || (ctx.flags & PUBKEY_FLAG_SM2))) ++ { ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK_GOST_SM2)) ++ { ++ rc = GPG_ERR_INV_DATA; ++ goto leave; ++ } ++ else ++ fips_service_indicator_mark_non_compliant (); ++ } ++ + /* Hash algo is determined by curve in EdDSA. */ + if ((ctx.flags & PUBKEY_FLAG_EDDSA)) + { +@@ -953,10 +965,12 @@ ecc_sign (gcry_sexp_t *r_sig, gcry_sexp_t s_data, gcry_sexp_t keyparms) + && ctx.hash_algo != GCRY_MD_SHAKE256))) + { + if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) +- rc = GPG_ERR_DIGEST_ALGO; ++ { ++ rc = GPG_ERR_DIGEST_ALGO; ++ goto leave; ++ } + else + fips_service_indicator_mark_non_compliant (); +- goto leave; + } + } + else +@@ -967,6 +981,23 @@ ecc_sign (gcry_sexp_t *r_sig, gcry_sexp_t s_data, gcry_sexp_t keyparms) + ctx.hash_algo = GCRY_MD_SHAKE256; + } + } ++ else ++ { ++ if (fips_mode ()) ++ { ++ if (_gcry_md_algo_info (ctx.hash_algo, GCRYCTL_TEST_ALGO, NULL, NULL) ++ || ctx.hash_algo == GCRY_MD_SHA1) ++ { ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK_MD)) ++ { ++ rc = GPG_ERR_DIGEST_ALGO; ++ goto leave; ++ } ++ else ++ fips_service_indicator_mark_non_compliant (); ++ } ++ } ++ } + + sig_r = mpi_new (0); + sig_s = mpi_new (0); +@@ -1066,6 +1097,18 @@ ecc_verify (gcry_sexp_t s_sig, gcry_sexp_t s_data, gcry_sexp_t s_keyparms) + if (DBG_CIPHER) + log_mpidump ("ecc_verify data", data); + ++ if (fips_mode () ++ && ((ctx.flags & PUBKEY_FLAG_GOST) || (ctx.flags & PUBKEY_FLAG_SM2))) ++ { ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK_GOST_SM2)) ++ { ++ rc = GPG_ERR_INV_DATA; ++ goto leave; ++ } ++ else ++ fips_service_indicator_mark_non_compliant (); ++ } ++ + /* Hash algo is determined by curve in EdDSA. */ + if ((ctx.flags & PUBKEY_FLAG_EDDSA)) + { +@@ -1078,10 +1121,12 @@ ecc_verify (gcry_sexp_t s_sig, gcry_sexp_t s_data, gcry_sexp_t s_keyparms) + && ctx.hash_algo != GCRY_MD_SHAKE256))) + { + if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) +- rc = GPG_ERR_DIGEST_ALGO; ++ { ++ rc = GPG_ERR_DIGEST_ALGO; ++ goto leave; ++ } + else + fips_service_indicator_mark_non_compliant (); +- goto leave; + } + } + else +@@ -1092,6 +1137,23 @@ ecc_verify (gcry_sexp_t s_sig, gcry_sexp_t s_data, gcry_sexp_t s_keyparms) + ctx.hash_algo = GCRY_MD_SHAKE256; + } + } ++ else ++ { ++ if (fips_mode ()) ++ { ++ if (_gcry_md_algo_info (ctx.hash_algo, GCRYCTL_TEST_ALGO, NULL, NULL) ++ || ctx.hash_algo == GCRY_MD_SHA1) ++ { ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK_MD)) ++ { ++ rc = GPG_ERR_DIGEST_ALGO; ++ goto leave; ++ } ++ else ++ fips_service_indicator_mark_non_compliant (); ++ } ++ } ++ } + + /* + * Extract the signature value. +diff --git a/src/gcrypt.h.in b/src/gcrypt.h.in +index 7bee45e9..fcb6a327 100644 +--- a/src/gcrypt.h.in ++++ b/src/gcrypt.h.in +@@ -1986,11 +1986,13 @@ char *gcry_get_config (int mode, const char *what); + #define GCRY_FIPS_FLAG_REJECT_MAC (1 << 3) + #define GCRY_FIPS_FLAG_REJECT_CIPHER (1 << 4) + #define GCRY_FIPS_FLAG_REJECT_PK (1 << 5) ++#define GCRY_FIPS_FLAG_REJECT_PK_MD (1 << 6) ++#define GCRY_FIPS_FLAG_REJECT_PK_GOST_SM2 (1 << 7) + + #define GCRY_FIPS_FLAG_REJECT_MD \ + (GCRY_FIPS_FLAG_REJECT_MD_MD5 | GCRY_FIPS_FLAG_REJECT_MD_OTHERS) + +-/* Note: Don't reject MD5 */ ++/* Note: Don't reject MD5, PK MD, PK GOST and PK SM2 */ + #define GCRY_FIPS_FLAG_REJECT_COMPAT110 \ + (GCRY_FIPS_FLAG_REJECT_MD_OTHERS \ + | GCRY_FIPS_FLAG_REJECT_MAC \ +diff --git a/tests/t-fips-service-ind.c b/tests/t-fips-service-ind.c +index 90d92c70..fe963fa5 100644 +--- a/tests/t-fips-service-ind.c ++++ b/tests/t-fips-service-ind.c +@@ -228,6 +228,7 @@ check_pk_s_v (int reject) + static struct { + const char *prvkey; + const char *pubkey; ++ const char *data; + int expect_failure; + } tv[] = { + { +@@ -236,6 +237,8 @@ check_pk_s_v (int reject) + "(public-key (ecc (curve nistp256)" + " (q #041ccbe91c075fc7f4f033bfa248db8fccd3565de94bbfb12f3c59ff46c271bf83" + "ce4014c68811f9a21a1fdb2c0e6113e06db7ca93b7404e78dc7ccd5ca89a4ca9#)))", ++ "(data (flags raw)(hash sha256 " ++ "#00112233445566778899AABBCCDDEEFF000102030405060708090A0B0C0D0E0F#))", + 0 + }, + { /* non-compliant curve */ +@@ -244,28 +247,40 @@ check_pk_s_v (int reject) + "(public-key (ecc (curve secp256k1)" + " (q #046fcc37ea5e9e09fec6c83e5fbd7a745e3eee81d16ebd861c9e66f55518c19798" + "4e9f113c07f875691df8afc1029496fc4cb9509b39dcd38f251a83359cc8b4f7#)))", ++ "(data (flags raw)(hash sha256 " ++ "#00112233445566778899AABBCCDDEEFF000102030405060708090A0B0C0D0E0F#))", + 1 +- } ++ }, ++ { /* non-compliant hash */ ++ "(private-key (ecc (curve nistp256)" ++ " (d #519b423d715f8b581f4fa8ee59f4771a5b44c8130b4e3eacca54a56dda72b464#)))", ++ "(public-key (ecc (curve nistp256)" ++ " (q #041ccbe91c075fc7f4f033bfa248db8fccd3565de94bbfb12f3c59ff46c271bf83" ++ "ce4014c68811f9a21a1fdb2c0e6113e06db7ca93b7404e78dc7ccd5ca89a4ca9#)))", ++ "(data (flags raw)(hash ripemd160 " ++ "#00112233445566778899AABBCCDDEEFF00010203#))", ++ 1 ++ }, ++ { /* non-compliant hash for signing */ ++ "(private-key (ecc (curve nistp256)" ++ " (d #519b423d715f8b581f4fa8ee59f4771a5b44c8130b4e3eacca54a56dda72b464#)))", ++ "(public-key (ecc (curve nistp256)" ++ " (q #041ccbe91c075fc7f4f033bfa248db8fccd3565de94bbfb12f3c59ff46c271bf83" ++ "ce4014c68811f9a21a1fdb2c0e6113e06db7ca93b7404e78dc7ccd5ca89a4ca9#)))", ++ "(data (flags raw)(hash sha1 " ++ "#00112233445566778899AABBCCDDEEFF00010203#))", ++ 1 ++ }, + }; + int tvidx; + gpg_error_t err; + gpg_err_code_t ec; +- const char *data = "(data (flags raw)" +- "(hash sha256 #00112233445566778899AABBCCDDEEFF000102030405060708090A0B0C0D0E0F#))"; +- gcry_sexp_t s_data = NULL; +- +- err = gcry_sexp_build (&s_data, NULL, data); +- if (err) +- { +- fail ("error building SEXP for test, %s: %s", +- "data", gpg_strerror (err)); +- return; +- } + + for (tvidx=0; tvidx < DIM(tv); tvidx++) + { + gcry_sexp_t s_pk = NULL; + gcry_sexp_t s_sk = NULL; ++ gcry_sexp_t s_data = NULL; + gcry_sexp_t s_sig= NULL; + + if (verbose) +@@ -287,6 +302,14 @@ check_pk_s_v (int reject) + goto next; + } + ++ err = gcry_sexp_build (&s_data, NULL, tv[tvidx].data); ++ if (err) ++ { ++ fail ("error building SEXP for test, %s: %s", ++ "data", gpg_strerror (err)); ++ goto next; ++ } ++ + err = gcry_pk_sign (&s_sig, s_data, s_sk); + if (err) + { +@@ -363,11 +386,10 @@ check_pk_s_v (int reject) + + next: + gcry_sexp_release (s_sig); ++ gcry_sexp_release (s_data); + gcry_sexp_release (s_pk); + gcry_sexp_release (s_sk); + } +- +- gcry_sexp_release (s_data); + } + + /* Check gcry_pk_hash_sign, gcry_pk_hash_verify API. */ +@@ -1461,6 +1483,8 @@ main (int argc, char **argv) + + xgcry_control ((GCRYCTL_FIPS_REJECT_NON_FIPS, + (GCRY_FIPS_FLAG_REJECT_MD_MD5 ++ | GCRY_FIPS_FLAG_REJECT_PK_MD ++ | GCRY_FIPS_FLAG_REJECT_PK_GOST_SM2 + | GCRY_FIPS_FLAG_REJECT_COMPAT110))); + + check_md_o_w_r_c (1); +-- +2.49.0 + diff --git a/libgcrypt-fips-kdf-Implement-new-FIPS-service-indicator-for-gcry_kdf_derive.patch b/libgcrypt-fips-kdf-Implement-new-FIPS-service-indicator-for-gcry_kdf_derive.patch new file mode 100644 index 0000000..a1710b9 --- /dev/null +++ b/libgcrypt-fips-kdf-Implement-new-FIPS-service-indicator-for-gcry_kdf_derive.patch @@ -0,0 +1,265 @@ +From 5cfa1aee5b98baf0d66333344e0fa45b79cca28b Mon Sep 17 00:00:00 2001 +From: NIIBE Yutaka +Date: Thu, 5 Dec 2024 14:52:17 +0900 +Subject: [PATCH 3/5] fips,kdf: Implement new FIPS service indicator for + gcry_kdf_derive. +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* cipher/kdf.c (_gcry_kdf_derive): Don't reject by GPG_ERR_INV_VALUE +but continue the computation, clearing IS_COMPLIANT. After successful +computation, call fips_service_indicator_mark_success with +IS_COMPLIANT. +* src/visibility.c (gcry_kdf_derive): Call fips_service_indicator_init. +* tests/t-kdf.c (check_fips_gcry_kdf_derive): New. +(main): Call check_fips_gcry_kdf_derive. + +-- + +GnuPG-bug-id: 7338 +Co-authored-by: David Sugar +Suggested-by: Stephan Mueller +Signed-off-by: NIIBE Yutaka +Signed-off-by: Lucas Mülling +--- + cipher/kdf.c | 33 ++++++----- + src/visibility.c | 1 + + tests/t-kdf.c | 149 ++++++++++++++++++++++++++++++++++++++++++++++- + 3 files changed, 169 insertions(+), 14 deletions(-) + +diff --git a/cipher/kdf.c b/cipher/kdf.c +index b4c5f83a..52e6a9ba 100644 +--- a/cipher/kdf.c ++++ b/cipher/kdf.c +@@ -279,28 +279,35 @@ _gcry_kdf_derive (const void *passphrase, size_t passphraselen, + break; + + case GCRY_KDF_PBKDF2: +- if (!saltlen) ++ if (!saltlen || !iterations) + ec = GPG_ERR_INV_VALUE; + else + { +- /* FIPS requires minimum passphrase length, see FIPS 140-3 IG D.N */ +- if (fips_mode () && passphraselen < 8) +- return GPG_ERR_INV_VALUE; ++ int is_compliant = 1; ++ ++ if (fips_mode ()) ++ { ++ /* FIPS requires minimum passphrase length, see FIPS 140-3 IG D.N */ ++ if (passphraselen < 8) ++ is_compliant &= 0; + +- /* FIPS requires minimum salt length of 128 b (SP 800-132 sec. 5.1, p.6) */ +- if (fips_mode () && saltlen < 16) +- return GPG_ERR_INV_VALUE; ++ /* FIPS requires minimum salt length of 128 b (SP 800-132 sec. 5.1, p.6) */ ++ if (saltlen < 16) ++ is_compliant &= 0; + +- /* FIPS requires minimum iterations bound (SP 800-132 sec 5.2, p.6) */ +- if (fips_mode () && iterations < 1000) +- return GPG_ERR_INV_VALUE; ++ /* FIPS requires minimum iterations bound (SP 800-132 sec 5.2, p.6) */ ++ if (iterations < 1000) ++ is_compliant &= 0; + +- /* Check minimum key size */ +- if (fips_mode () && keysize < 14) +- return GPG_ERR_INV_VALUE; ++ /* Check minimum key size */ ++ if (keysize < 14) ++ is_compliant &= 0; ++ } + + ec = _gcry_kdf_pkdf2 (passphrase, passphraselen, subalgo, + salt, saltlen, iterations, keysize, keybuffer); ++ if (!ec) ++ fips_service_indicator_mark_success (is_compliant); + } + break; + +diff --git a/src/visibility.c b/src/visibility.c +index 006e8f80..8f76b854 100644 +--- a/src/visibility.c ++++ b/src/visibility.c +@@ -1400,6 +1400,7 @@ gcry_kdf_derive (const void *passphrase, size_t passphraselen, + { + if (!fips_is_operational ()) + return gpg_error (fips_not_operational ()); ++ fips_service_indicator_init (); + return gpg_error (_gcry_kdf_derive (passphrase, passphraselen, algo, hashalgo, + salt, saltlen, iterations, + keysize, keybuffer)); +diff --git a/tests/t-kdf.c b/tests/t-kdf.c +index 10f64a7c..4b92bd30 100644 +--- a/tests/t-kdf.c ++++ b/tests/t-kdf.c +@@ -1927,6 +1927,151 @@ check_fips_indicators (void) + } + + ++static void ++check_fips_gcry_kdf_derive (void) ++{ ++ static struct { ++ const char *p; /* Passphrase. */ ++ size_t plen; /* Length of P. */ ++ int algo; ++ int subalgo; ++ const char *salt; ++ size_t saltlen; ++ unsigned long iterations; ++ int dklen; /* Requested key length. */ ++ const char *dk; /* Derived key. */ ++ int expect_failure; ++ } tv[] = { ++ { ++ "passwordPASSWORDpassword", 24, ++ GCRY_KDF_PBKDF2, GCRY_MD_SHA1, ++ "saltSALTsaltSALTsaltSALTsaltSALTsalt", 36, ++ 4096, ++ 25, ++ "\x3d\x2e\xec\x4f\xe4\x1c\x84\x9b\x80\xc8" ++ "\xd8\x36\x62\xc0\xe4\x4a\x8b\x29\x1a\x96" ++ "\x4c\xf2\xf0\x70\x38", ++ 0 ++ }, ++ { ++ "pleaseletmein", 13, ++ GCRY_KDF_SCRYPT, 16384, ++ "SodiumChloride", 14, ++ 1, ++ 64, ++ "\x70\x23\xbd\xcb\x3a\xfd\x73\x48\x46\x1c\x06\xcd\x81\xfd\x38\xeb" ++ "\xfd\xa8\xfb\xba\x90\x4f\x8e\x3e\xa9\xb5\x43\xf6\x54\x5d\xa1\xf2" ++ "\xd5\x43\x29\x55\x61\x3f\x0f\xcf\x62\xd4\x97\x05\x24\x2a\x9a\xf9" ++ "\xe6\x1e\x85\xdc\x0d\x65\x1e\x40\xdf\xcf\x01\x7b\x45\x57\x58\x87", ++ 1 /* not-compliant because unallowed algo */ ++ }, ++ { ++ "passwor", 7, ++ GCRY_KDF_PBKDF2, GCRY_MD_SHA1, ++ "saltSALTsaltSALTsaltSALTsaltSALTsalt", 36, ++ 4096, ++ 25, ++ "\xf4\x93\xee\x2b\xbf\x44\x0b\x9e\x64\x53" ++ "\xc2\xb3\x87\xdc\x73\xf8\xfd\xe6\x97\xda" ++ "\xb8\x24\xa0\x26\x50", ++ 1 /* not-compliant because passphrase len is too small */ ++ }, ++ { ++ "passwordPASSWORDpassword", 24, ++ GCRY_KDF_PBKDF2, GCRY_MD_SHA1, ++ "saltSALTsaltSAL", 15, ++ 4096, ++ 25, ++ "\x14\x05\xa4\x2a\xf4\xa8\x12\x14\x7b\x65" ++ "\x8f\xaa\xf0\x7f\x25\xe5\x0f\x0b\x2b\xb7" ++ "\xcf\x8d\x29\x23\x4b", ++ 1 /* not-compliant because salt len is too small */ ++ }, ++ { ++ "passwordPASSWORDpassword", 24, ++ GCRY_KDF_PBKDF2, GCRY_MD_SHA1, ++ "saltSALTsaltSALTsaltSALTsaltSALTsalt", 36, ++ 999, ++ 25, ++ "\xac\xf8\xb4\x67\x41\xc7\xf3\xd1\xa0\xc0" ++ "\x08\xbe\x9b\x23\x96\x78\xbd\x93\xda\x4a" ++ "\x30\xd4\xfb\xf0\x33", ++ 1 /* not-compliant because too few iterations */ ++ }, ++ { ++ "passwordPASSWORDpassword", 24, ++ GCRY_KDF_PBKDF2, GCRY_MD_SHA1, ++ "saltSALTsaltSALTsaltSALTsaltSALTsalt", 36, ++ 4096, ++ 13, ++ "\x3d\x2e\xec\x4f\xe4\x1c\x84\x9b\x80\xc8" ++ "\xd8\x36\x62", ++ 1 /* not-compliant because key size too small */ ++ }, ++ }; ++ ++ int tvidx; ++ gpg_error_t err; ++ unsigned char outbuf[100]; ++ int i; ++ ++ for (tvidx=0; tvidx < DIM(tv); tvidx++) ++ { ++ if (verbose) ++ fprintf (stderr, "checking gcry_kdf_derive test vector %d algo %d for FIPS\n", ++ tvidx, tv[tvidx].algo); ++ assert (tv[tvidx].dklen <= sizeof outbuf); ++ err = gcry_kdf_derive (tv[tvidx].p, tv[tvidx].plen, ++ tv[tvidx].algo, tv[tvidx].subalgo, ++ tv[tvidx].salt, tv[tvidx].saltlen, ++ tv[tvidx].iterations, tv[tvidx].dklen, outbuf); ++ ++ if (err) ++ { ++ fail ("gcry_kdf_derive test %d unexpectedly returned an error in FIPS mode: %s\n", ++ tvidx, gpg_strerror (err)); ++ } ++ else ++ { ++ gpg_err_code_t ec; ++ ++ ec = gcry_get_fips_service_indicator (); ++ if (ec == GPG_ERR_INV_OP) ++ { ++ /* libgcrypt is old, no support of the FIPS service indicator. */ ++ fail ("gcry_kdf_derive test %d unexpectedly failed to check the FIPS service indicator.\n", ++ tvidx); ++ continue; ++ } ++ ++ if (!tv[tvidx].expect_failure && ec) ++ { ++ /* Success with the FIPS service indicator == 0 expected, but != 0. */ ++ fail ("gcry_kdf_derive test %d unexpectedly set the indicator in FIPS mode.\n", ++ tvidx); ++ continue; ++ } ++ else if (tv[tvidx].expect_failure && !ec) ++ { ++ /* Success with the FIPS service indicator != 0 expected, but == 0. */ ++ fail ("gcry_kdf_derive test %d unexpectedly cleared the indicator in FIPS mode.\n", ++ tvidx); ++ continue; ++ } ++ ++ if (memcmp (outbuf, tv[tvidx].dk, tv[tvidx].dklen)) ++ { ++ fail ("gcry_kdf_derive test %d failed: mismatch\n", tvidx); ++ fputs ("got:", stderr); ++ for (i=0; i < tv[tvidx].dklen; i++) ++ fprintf (stderr, " %02x", outbuf[i]); ++ putc ('\n', stderr); ++ } ++ } ++ } ++} ++ ++ + int + main (int argc, char **argv) + { +@@ -2008,7 +2153,9 @@ main (int argc, char **argv) + check_onestep_kdf (); + check_hkdf (); + if (in_fips_mode) +- check_fips_indicators(); ++ check_fips_indicators (); ++ if (in_fips_mode) ++ check_fips_gcry_kdf_derive (); + } + + return error_count ? 1 : 0; +-- +2.49.0 + diff --git a/libgcrypt-fips-mac-Implement-new-FIPS-service-indicator-for-gcry_mac_open.patch b/libgcrypt-fips-mac-Implement-new-FIPS-service-indicator-for-gcry_mac_open.patch new file mode 100644 index 0000000..7843a39 --- /dev/null +++ b/libgcrypt-fips-mac-Implement-new-FIPS-service-indicator-for-gcry_mac_open.patch @@ -0,0 +1,115 @@ +From fcb0c7004b0b6b318fdcced2bf61d9acb1e28cfc Mon Sep 17 00:00:00 2001 +From: NIIBE Yutaka +Date: Fri, 13 Dec 2024 14:25:02 +0900 +Subject: [PATCH 04/19] fips,mac: Implement new FIPS service indicator for + gcry_mac_open. +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* src/gcrypt.h.in (GCRY_MAC_FLAG_REJECT_NON_FIPS): New. +* cipher/mac.c (mac_open): Have FLAGS, instead of SECURE. Reject when +GCRY_MAC_FLAG_REJECT_NON_FIPS, otherwise, mark non compliant. +(_gcry_mac_open): Follow the change. +* src/visibility.c (gcry_mac_open): Add initialization for FIPS +service indicator. +(gcry_mac_setkey): Likewise. Don't reject but mark. + +-- + +GnuPG-bug-id: 7338 +Signed-off-by: NIIBE Yutaka +Signed-off-by: Lucas Mülling +--- + cipher/mac.c | 15 +++++++++++---- + src/gcrypt.h.in | 3 ++- + src/visibility.c | 5 +++-- + 3 files changed, 16 insertions(+), 7 deletions(-) + +diff --git a/cipher/mac.c b/cipher/mac.c +index 128ac53d..0df48fd7 100644 +--- a/cipher/mac.c ++++ b/cipher/mac.c +@@ -513,11 +513,13 @@ check_mac_algo (int algorithm) + * Open a message digest handle for use with algorithm ALGO. + */ + static gcry_err_code_t +-mac_open (gcry_mac_hd_t * hd, int algo, int secure, gcry_ctx_t ctx) ++mac_open (gcry_mac_hd_t * hd, int algo, unsigned int flags, gcry_ctx_t ctx) + { + const gcry_mac_spec_t *spec; + gcry_err_code_t err; + gcry_mac_hd_t h; ++ int secure = !!(flags & GCRY_MAC_FLAG_SECURE); ++ int reject_non_fips = !!(flags & GCRY_MAC_FLAG_REJECT_NON_FIPS); + + spec = spec_from_algo (algo); + if (!spec) +@@ -525,7 +527,12 @@ mac_open (gcry_mac_hd_t * hd, int algo, int secure, gcry_ctx_t ctx) + else if (spec->flags.disabled) + return GPG_ERR_MAC_ALGO; + else if (!spec->flags.fips && fips_mode ()) +- return GPG_ERR_MAC_ALGO; ++ { ++ if (reject_non_fips) ++ return GPG_ERR_MAC_ALGO; ++ else ++ fips_service_indicator_mark_non_compliant (); ++ } + else if (!spec->ops) + return GPG_ERR_MAC_ALGO; + else if (!spec->ops->open || !spec->ops->write || !spec->ops->setkey || +@@ -643,10 +650,10 @@ _gcry_mac_open (gcry_mac_hd_t * h, int algo, unsigned int flags, + gcry_err_code_t rc; + gcry_mac_hd_t hd = NULL; + +- if ((flags & ~GCRY_MAC_FLAG_SECURE)) ++ if ((flags & ~(GCRY_MAC_FLAG_SECURE | GCRY_MAC_FLAG_REJECT_NON_FIPS))) + rc = GPG_ERR_INV_ARG; + else +- rc = mac_open (&hd, algo, !!(flags & GCRY_MAC_FLAG_SECURE), ctx); ++ rc = mac_open (&hd, algo, flags, ctx); + + *h = rc ? NULL : hd; + return rc; +diff --git a/src/gcrypt.h.in b/src/gcrypt.h.in +index 96bf88f6..2a378639 100644 +--- a/src/gcrypt.h.in ++++ b/src/gcrypt.h.in +@@ -1560,7 +1560,8 @@ enum gcry_mac_algos + /* Flags used with the open function. */ + enum gcry_mac_flags + { +- GCRY_MAC_FLAG_SECURE = 1 /* Allocate all buffers in "secure" memory. */ ++ GCRY_MAC_FLAG_SECURE = 1, /* Allocate all buffers in "secure" memory. */ ++ GCRY_MAC_FLAG_REJECT_NON_FIPS = 2 /* Reject non-FIPS-compliant algo. */ + }; + + /* Create a MAC handle for algorithm ALGO. FLAGS may be given as an bitwise OR +diff --git a/src/visibility.c b/src/visibility.c +index 44b05eb2..7699f14f 100644 +--- a/src/visibility.c ++++ b/src/visibility.c +@@ -946,7 +946,7 @@ gcry_mac_open (gcry_mac_hd_t *handle, int algo, unsigned int flags, + *handle = NULL; + return gpg_error (fips_not_operational ()); + } +- ++ fips_service_indicator_init (); + return gpg_error (_gcry_mac_open (handle, algo, flags, ctx)); + } + +@@ -962,8 +962,9 @@ gcry_mac_setkey (gcry_mac_hd_t hd, const void *key, size_t keylen) + if (!fips_is_operational ()) + return gpg_error (fips_not_operational ()); + ++ fips_service_indicator_init (); + if (fips_mode () && keylen < 14) +- return GPG_ERR_INV_VALUE; ++ fips_service_indicator_mark_non_compliant (); + + return gpg_error (_gcry_mac_setkey (hd, key, keylen)); + } +-- +2.49.0 + diff --git a/libgcrypt-fips-md-Implement-new-FIPS-service-indicator-for-gcry_md_hash_.patch b/libgcrypt-fips-md-Implement-new-FIPS-service-indicator-for-gcry_md_hash_.patch new file mode 100644 index 0000000..71f1671 --- /dev/null +++ b/libgcrypt-fips-md-Implement-new-FIPS-service-indicator-for-gcry_md_hash_.patch @@ -0,0 +1,188 @@ +From 3478caac62c712547f7c0e07f4cf9602bc317997 Mon Sep 17 00:00:00 2001 +From: NIIBE Yutaka +Date: Fri, 6 Dec 2024 14:33:58 +0900 +Subject: [PATCH 4/5] fips,md: Implement new FIPS service indicator for + gcry_md_hash_*. +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* cipher/md.c (md_enable): Add an NO_REJECT argument. +(md_open): Check flags against GCRY_MD_FLAG_FIPS_NO_REJECTION to +call md_enable. +(_gcry_md_enable): Follow the change. +(_gcry_md_hash_buffer): Don't reject but keep the computation. +Call fips_service_indicator_mark_success. +(_gcry_md_hash_buffers_extract): Likewise. +* src/gcrypt.h.in (GCRY_MD_FLAG_FIPS_NO_REJECTION): New. +* src/visibility.c (gcry_md_hash_buffer, gcry_md_hash_buffers): Call +fips_service_indicator_init. +(gcry_md_hash_buffers_ext): Likewise. + +-- + +GnuPG-bug-id: 7338 +Signed-off-by: NIIBE Yutaka +Signed-off-by: Lucas Mülling +--- + cipher/md.c | 32 +++++++++++++++++++++++--------- + src/gcrypt.h.in | 1 + + src/visibility.c | 3 +++ + 3 files changed, 27 insertions(+), 9 deletions(-) + +diff --git a/cipher/md.c b/cipher/md.c +index 1991c331..c2bd18c6 100644 +--- a/cipher/md.c ++++ b/cipher/md.c +@@ -285,7 +285,7 @@ struct gcry_md_context + #define CTX_MAGIC_NORMAL 0x11071961 + #define CTX_MAGIC_SECURE 0x16917011 + +-static gcry_err_code_t md_enable (gcry_md_hd_t hd, int algo); ++static gcry_err_code_t md_enable (gcry_md_hd_t hd, int algo, int no_reject); + static void md_close (gcry_md_hd_t a); + static void md_write (gcry_md_hd_t a, const void *inbuf, size_t inlen); + static byte *md_read( gcry_md_hd_t a, int algo ); +@@ -517,7 +517,8 @@ md_open (gcry_md_hd_t *h, int algo, unsigned int flags) + + if (algo) + { +- err = md_enable (hd, algo); ++ err = md_enable (hd, algo, ++ !!(flags & GCRY_MD_FLAG_FIPS_NO_REJECTION)); + if (err) + md_close (hd); + } +@@ -554,7 +555,7 @@ _gcry_md_open (gcry_md_hd_t *h, int algo, unsigned int flags) + + + static gcry_err_code_t +-md_enable (gcry_md_hd_t hd, int algorithm) ++md_enable (gcry_md_hd_t hd, int algorithm, int no_reject) + { + struct gcry_md_context *h = hd->ctx; + const gcry_md_spec_t *spec; +@@ -576,7 +577,7 @@ md_enable (gcry_md_hd_t hd, int algorithm) + err = GPG_ERR_DIGEST_ALGO; + + /* Any non-FIPS algorithm should go this way */ +- if (!err && !spec->flags.fips && fips_mode ()) ++ if (!err && !no_reject && !spec->flags.fips && fips_mode ()) + err = GPG_ERR_DIGEST_ALGO; + + if (!err && h->flags.hmac && spec->read == NULL) +@@ -619,7 +620,7 @@ md_enable (gcry_md_hd_t hd, int algorithm) + gcry_err_code_t + _gcry_md_enable (gcry_md_hd_t hd, int algorithm) + { +- return md_enable (hd, algorithm); ++ return md_enable (hd, algorithm, 0); + } + + +@@ -1260,7 +1261,7 @@ _gcry_md_hash_buffer (int algo, void *digest, + iov.off = 0; + iov.len = length; + +- if (spec->flags.disabled || (!spec->flags.fips && fips_mode ())) ++ if (spec->flags.disabled) + log_bug ("gcry_md_hash_buffer failed for algo %d: %s", + algo, gpg_strerror (gcry_error (GPG_ERR_DIGEST_ALGO))); + +@@ -1273,7 +1274,7 @@ _gcry_md_hash_buffer (int algo, void *digest, + gcry_md_hd_t h; + gpg_err_code_t err; + +- err = md_open (&h, algo, 0); ++ err = md_open (&h, algo, GCRY_MD_FLAG_FIPS_NO_REJECTION); + if (err) + log_bug ("gcry_md_open failed for algo %d: %s", + algo, gpg_strerror (gcry_error(err))); +@@ -1282,6 +1283,12 @@ _gcry_md_hash_buffer (int algo, void *digest, + memcpy (digest, md_read (h, algo), md_digest_length (algo)); + md_close (h); + } ++ ++ if (fips_mode ()) ++ { ++ int is_compliant = spec->flags.fips; ++ fips_service_indicator_mark_success (is_compliant); ++ } + } + + +@@ -1336,7 +1343,7 @@ _gcry_md_hash_buffers_extract (int algo, unsigned int flags, void *digest, + + if (!hmac && spec->hash_buffers) + { +- if (spec->flags.disabled || (!spec->flags.fips && fips_mode ())) ++ if (spec->flags.disabled) + return GPG_ERR_DIGEST_ALGO; + + spec->hash_buffers (digest, digestlen, iov, iovcnt); +@@ -1348,7 +1355,8 @@ _gcry_md_hash_buffers_extract (int algo, unsigned int flags, void *digest, + gcry_md_hd_t h; + gpg_err_code_t rc; + +- rc = md_open (&h, algo, (hmac? GCRY_MD_FLAG_HMAC:0)); ++ rc = md_open (&h, algo, ((hmac? GCRY_MD_FLAG_HMAC:0) ++ | GCRY_MD_FLAG_FIPS_NO_REJECTION)); + if (rc) + return rc; + +@@ -1374,6 +1382,12 @@ _gcry_md_hash_buffers_extract (int algo, unsigned int flags, void *digest, + md_close (h); + } + ++ if (fips_mode ()) ++ { ++ int is_compliant = spec->flags.fips; ++ fips_service_indicator_mark_success (is_compliant); ++ } ++ + return 0; + } + +diff --git a/src/gcrypt.h.in b/src/gcrypt.h.in +index 2f61a0bc..18d04a38 100644 +--- a/src/gcrypt.h.in ++++ b/src/gcrypt.h.in +@@ -1318,6 +1318,7 @@ enum gcry_md_flags + { + GCRY_MD_FLAG_SECURE = 1, /* Allocate all buffers in "secure" memory. */ + GCRY_MD_FLAG_HMAC = 2, /* Make an HMAC out of this algorithm. */ ++ GCRY_MD_FLAG_FIPS_NO_REJECTION = 4, /* Don't reject for FIPS. */ + GCRY_MD_FLAG_BUGEMU1 = 0x0100 + }; + +diff --git a/src/visibility.c b/src/visibility.c +index 8f76b854..be5deda1 100644 +--- a/src/visibility.c ++++ b/src/visibility.c +@@ -1281,6 +1281,7 @@ gcry_md_hash_buffer (int algo, void *digest, + (void)fips_not_operational (); + fips_signal_error ("called in non-operational state"); + } ++ fips_service_indicator_init (); + _gcry_md_hash_buffer (algo, digest, buffer, length); + } + +@@ -1293,6 +1294,7 @@ gcry_md_hash_buffers (int algo, unsigned int flags, void *digest, + (void)fips_not_operational (); + fips_signal_error ("called in non-operational state"); + } ++ fips_service_indicator_init (); + return gpg_error (_gcry_md_hash_buffers (algo, flags, digest, iov, iovcnt)); + } + +@@ -1306,6 +1308,7 @@ gcry_md_hash_buffers_ext (int algo, unsigned int flags, void *digest, + (void)fips_not_operational (); + fips_signal_error ("called in non-operational state"); + } ++ fips_service_indicator_init (); + return gpg_error (_gcry_md_hash_buffers_extract (algo, flags, digest, + digestlen, iov, iovcnt)); + } +-- +2.49.0 + diff --git a/libgcrypt-fips-md-Implement-new-FIPS-service-indicator-for-gcry_md_open-API.patch b/libgcrypt-fips-md-Implement-new-FIPS-service-indicator-for-gcry_md_open-API.patch new file mode 100644 index 0000000..0f580b1 --- /dev/null +++ b/libgcrypt-fips-md-Implement-new-FIPS-service-indicator-for-gcry_md_open-API.patch @@ -0,0 +1,298 @@ +From 9757e280794f537efc82c4eaa9a2944ece6a068a Mon Sep 17 00:00:00 2001 +From: NIIBE Yutaka +Date: Thu, 12 Dec 2024 11:40:31 +0900 +Subject: [PATCH] fips,md: Implement new FIPS service indicator for + gcry_md_open API. +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* src/gcrypt.h.in (GCRY_MD_FLAG_FIPS_NO_REJECTION): Remove. +(GCRY_MD_FLAG_REJECT_NON_FIPS): New. +* cipher/md.c (struct gcry_md_context): Add reject_non_fips. +(md_enable): Remove NO_REJECT argument. +(md_open): Change the FLAGS handling. +(_gcry_md_open): Add checking of FIPS compliance against ALGO. +(_gcry_md_enable): Likewise. +(_gcry_md_hash_buffer): Follow the change of md_open change +which now defaults to no rejection. +(_gcry_md_hash_buffers_extract): Likewise. +* src/visibility.c (gcry_md_open): Add fips_service_indicator_init. +(gcry_md_enable): Likewise. +(gcry_md_setkey): Don't reject but mark non-compliance. +* tests/t-kdf.c (check_fips_gcry_kdf_derive): Add a test with +non-compliant hash function. +* cipher/mac-hmac.c (_gcry_mac_type_spec_hmac_md5): It's not +compliant. +* cipher/md5.c (gcry_md_oid_spec_t oid_spec_md5): It's not compliant. +* tests/t-digest.c (check_hash_buffer, check_hash_buffers): MD5 +tests enabled. + +-- + +See 6376 for the MD5 compliance change in the past. This commit +reverts the change in: + dc4a60e2d70bc52ba2955f8e676341d675ab89a0 + +GnuPG-bug-id: 7338 +Signed-off-by: NIIBE Yutaka +Signed-off-by: Lucas Mülling +--- + cipher/mac-hmac.c | 2 +- + cipher/md.c | 57 +++++++++++++++++++++++++++++++++++++++-------- + cipher/md5.c | 2 +- + src/gcrypt.h.in | 2 +- + src/visibility.c | 6 +++-- + tests/t-digest.c | 6 ++--- + tests/t-kdf.c | 12 ++++++++++ + 7 files changed, 69 insertions(+), 18 deletions(-) + +Index: libgcrypt-1.11.0/cipher/mac-hmac.c +=================================================================== +--- libgcrypt-1.11.0.orig/cipher/mac-hmac.c ++++ libgcrypt-1.11.0/cipher/mac-hmac.c +@@ -1413,7 +1413,7 @@ const gcry_mac_spec_t _gcry_mac_type_spe + #endif + #if USE_MD5 + const gcry_mac_spec_t _gcry_mac_type_spec_hmac_md5 = { +- GCRY_MAC_HMAC_MD5, {0, 1}, "HMAC_MD5", ++ GCRY_MAC_HMAC_MD5, {0, 0}, "HMAC_MD5", + &hmac_ops + }; + #endif +Index: libgcrypt-1.11.0/cipher/md.c +=================================================================== +--- libgcrypt-1.11.0.orig/cipher/md.c ++++ libgcrypt-1.11.0/cipher/md.c +@@ -275,6 +275,7 @@ struct gcry_md_context + unsigned int finalized:1; + unsigned int bugemu1:1; + unsigned int hmac:1; ++ unsigned int reject_non_fips:1; + } flags; + size_t actual_handle_size; /* Allocated size of this handle. */ + FILE *debug; +@@ -285,7 +286,7 @@ struct gcry_md_context + #define CTX_MAGIC_NORMAL 0x11071961 + #define CTX_MAGIC_SECURE 0x16917011 + +-static gcry_err_code_t md_enable (gcry_md_hd_t hd, int algo, int no_reject); ++static gcry_err_code_t md_enable (gcry_md_hd_t hd, int algo); + static void md_close (gcry_md_hd_t a); + static void md_write (gcry_md_hd_t a, const void *inbuf, size_t inlen); + static byte *md_read( gcry_md_hd_t a, int algo ); +@@ -508,6 +509,7 @@ md_open (gcry_md_hd_t *h, int algo, unsi + ctx->flags.secure = secure; + ctx->flags.hmac = hmac; + ctx->flags.bugemu1 = !!(flags & GCRY_MD_FLAG_BUGEMU1); ++ ctx->flags.reject_non_fips = !!(flags & GCRY_MD_FLAG_REJECT_NON_FIPS); + } + + if (! err) +@@ -517,8 +519,7 @@ md_open (gcry_md_hd_t *h, int algo, unsi + + if (algo) + { +- err = md_enable (hd, algo, +- !!(flags & GCRY_MD_FLAG_FIPS_NO_REJECTION)); ++ err = md_enable (hd, algo); + if (err) + md_close (hd); + } +@@ -543,24 +544,44 @@ _gcry_md_open (gcry_md_hd_t *h, int algo + + if ((flags & ~(GCRY_MD_FLAG_SECURE + | GCRY_MD_FLAG_HMAC ++ | GCRY_MD_FLAG_REJECT_NON_FIPS + | GCRY_MD_FLAG_BUGEMU1))) + rc = GPG_ERR_INV_ARG; + else + rc = md_open (&hd, algo, flags); + + *h = rc? NULL : hd; ++ ++ if (!rc && fips_mode ()) ++ { ++ GcryDigestEntry *entry = hd->ctx->list; ++ /* No ENTRY means that ALGO==0. ++ It's not yet known, if it's FIPS compliant or not. */ ++ int is_compliant_algo = 1; ++ ++ if (entry) ++ { ++ const gcry_md_spec_t *spec = entry->spec; ++ is_compliant_algo = spec->flags.fips; ++ } ++ ++ if (!is_compliant_algo) ++ fips_service_indicator_mark_non_compliant (); ++ } ++ + return rc; + } + + + + static gcry_err_code_t +-md_enable (gcry_md_hd_t hd, int algorithm, int no_reject) ++md_enable (gcry_md_hd_t hd, int algorithm) + { + struct gcry_md_context *h = hd->ctx; + const gcry_md_spec_t *spec; + GcryDigestEntry *entry; + gcry_err_code_t err = 0; ++ int reject_non_fips = h->flags.reject_non_fips; + + for (entry = h->list; entry; entry = entry->next) + if (entry->spec->algo == algorithm) +@@ -577,7 +598,7 @@ md_enable (gcry_md_hd_t hd, int algorith + err = GPG_ERR_DIGEST_ALGO; + + /* Any non-FIPS algorithm should go this way */ +- if (!err && !no_reject && !spec->flags.fips && fips_mode ()) ++ if (!err && reject_non_fips && !spec->flags.fips && fips_mode ()) + err = GPG_ERR_DIGEST_ALGO; + + if (!err && h->flags.hmac && spec->read == NULL) +@@ -620,7 +641,26 @@ md_enable (gcry_md_hd_t hd, int algorith + gcry_err_code_t + _gcry_md_enable (gcry_md_hd_t hd, int algorithm) + { +- return md_enable (hd, algorithm, 0); ++ gcry_err_code_t rc; ++ ++ rc = md_enable (hd, algorithm); ++ if (!rc && fips_mode ()) ++ { ++ GcryDigestEntry *entry = hd->ctx->list; ++ /* No ENTRY means, something goes wrong. */ ++ int is_compliant_algo = 0; ++ ++ if (entry) ++ { ++ const gcry_md_spec_t *spec = entry->spec; ++ is_compliant_algo = spec->flags.fips; ++ } ++ ++ if (!is_compliant_algo) ++ fips_service_indicator_mark_non_compliant (); ++ } ++ ++ return rc; + } + + +@@ -1274,7 +1314,7 @@ _gcry_md_hash_buffer (int algo, void *di + gcry_md_hd_t h; + gpg_err_code_t err; + +- err = md_open (&h, algo, GCRY_MD_FLAG_FIPS_NO_REJECTION); ++ err = md_open (&h, algo, 0); + if (err) + log_bug ("gcry_md_open failed for algo %d: %s", + algo, gpg_strerror (gcry_error(err))); +@@ -1355,8 +1395,7 @@ _gcry_md_hash_buffers_extract (int algo, + gcry_md_hd_t h; + gpg_err_code_t rc; + +- rc = md_open (&h, algo, ((hmac? GCRY_MD_FLAG_HMAC:0) +- | GCRY_MD_FLAG_FIPS_NO_REJECTION)); ++ rc = md_open (&h, algo, (hmac? GCRY_MD_FLAG_HMAC:0)); + if (rc) + return rc; + +Index: libgcrypt-1.11.0/cipher/md5.c +=================================================================== +--- libgcrypt-1.11.0.orig/cipher/md5.c ++++ libgcrypt-1.11.0/cipher/md5.c +@@ -314,7 +314,7 @@ static const gcry_md_oid_spec_t oid_spec + + const gcry_md_spec_t _gcry_digest_spec_md5 = + { +- GCRY_MD_MD5, {0, 1}, ++ GCRY_MD_MD5, {0, 0}, + "MD5", asn, DIM (asn), oid_spec_md5, 16, + md5_init, _gcry_md_block_write, md5_final, md5_read, NULL, + NULL, +Index: libgcrypt-1.11.0/src/gcrypt.h.in +=================================================================== +--- libgcrypt-1.11.0.orig/src/gcrypt.h.in ++++ libgcrypt-1.11.0/src/gcrypt.h.in +@@ -1320,7 +1320,7 @@ enum gcry_md_flags + { + GCRY_MD_FLAG_SECURE = 1, /* Allocate all buffers in "secure" memory. */ + GCRY_MD_FLAG_HMAC = 2, /* Make an HMAC out of this algorithm. */ +- GCRY_MD_FLAG_FIPS_NO_REJECTION = 4, /* Don't reject for FIPS. */ ++ GCRY_MD_FLAG_REJECT_NON_FIPS = 4, /* Reject non-FIPS-compliant algo. */ + GCRY_MD_FLAG_BUGEMU1 = 0x0100 + }; + +Index: libgcrypt-1.11.0/src/visibility.c +=================================================================== +--- libgcrypt-1.11.0.orig/src/visibility.c ++++ libgcrypt-1.11.0/src/visibility.c +@@ -1204,7 +1204,7 @@ gcry_md_open (gcry_md_hd_t *h, int algo, + *h = NULL; + return gpg_error (fips_not_operational ()); + } +- ++ fips_service_indicator_init (); + return gpg_error (_gcry_md_open (h, algo, flags)); + } + +@@ -1219,6 +1219,7 @@ gcry_md_enable (gcry_md_hd_t hd, int alg + { + if (!fips_is_operational ()) + return gpg_error (fips_not_operational ()); ++ fips_service_indicator_init (); + return gpg_error (_gcry_md_enable (hd, algo)); + } + +@@ -1382,8 +1383,9 @@ gcry_md_setkey (gcry_md_hd_t hd, const v + if (!fips_is_operational ()) + return gpg_error (fips_not_operational ()); + ++ fips_service_indicator_init (); + if (fips_mode () && keylen < 14) +- return GPG_ERR_INV_VALUE; ++ fips_service_indicator_mark_non_compliant (); + + return gpg_error (_gcry_md_setkey (hd, key, keylen)); + } +Index: libgcrypt-1.11.0/tests/t-digest.c +=================================================================== +--- libgcrypt-1.11.0.orig/tests/t-digest.c ++++ libgcrypt-1.11.0/tests/t-digest.c +@@ -48,8 +48,7 @@ check_digests (void) + const char *expect; + int expect_failure; + } tv[] = { +-#undef ENABLE_THIS_AFTER_T6376_CHANGE_REVISED +-#ifdef ENABLE_THIS_AFTER_T6376_CHANGE_REVISED ++#if USE_MD5 + { GCRY_MD_MD5, "abc", 3, + "\x90\x01\x50\x98\x3C\xD2\x4F\xB0\xD6\x96\x3F\x7D\x28\xE1\x7F\x72", 1 }, + #endif +Index: libgcrypt-1.11.0/tests/t-kdf.c +=================================================================== +--- libgcrypt-1.11.0.orig/tests/t-kdf.c ++++ libgcrypt-1.11.0/tests/t-kdf.c +@@ -2008,6 +2008,18 @@ check_fips_gcry_kdf_derive (void) + "\xd8\x36\x62", + 1 /* not-compliant because key size too small */ + }, ++ { ++ "passwordPASSWORDpassword", 24, ++ GCRY_KDF_PBKDF2, GCRY_MD_BLAKE2B_512, ++ "saltSALTsaltSALTsaltSALTsaltSALTsalt", 36, ++ 4096, ++ 60, ++ "\xa4\x6b\x53\x35\xdb\xdd\xa3\xd2\x5d\x19\xbb\x11\xfe\xdd\xd9\x9e" ++ "\x45\x2a\x7c\x34\x47\x41\x98\xca\x31\x74\xb6\x34\x22\xac\x83\xb0" ++ "\x38\x6e\xf5\x93\x0f\xf5\x16\x46\x0b\x97\xdc\x6c\x27\x5b\xe7\x25" ++ "\xc2\xcb\xec\x50\x02\xc6\x52\x8b\x34\x68\x53\x65", ++ 1 /* not-compliant because subalgo is not the one of approved */ ++ } + }; + + int tvidx; diff --git a/libgcrypt-fips-md-gcry_md_copy-should-care-about-FIPS-service-indicator.patch b/libgcrypt-fips-md-gcry_md_copy-should-care-about-FIPS-service-indicator.patch new file mode 100644 index 0000000..5edccac --- /dev/null +++ b/libgcrypt-fips-md-gcry_md_copy-should-care-about-FIPS-service-indicator.patch @@ -0,0 +1,85 @@ +From 60db2a175d120aba6818de49638b36006878abf7 Mon Sep 17 00:00:00 2001 +From: NIIBE Yutaka +Date: Wed, 18 Dec 2024 14:14:37 +0900 +Subject: [PATCH 10/19] fips,md: gcry_md_copy should care about FIPS service + indicator. +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* cipher/md.c (md_copy): In a case of non-compliant, mark with +fips_service_indicator_mark_non_compliant. +* src/visibility.c (gcry_md_copy): Initialize the indicator. + +-- + +GnuPG-bug-id: 7338 +Signed-off-by: NIIBE Yutaka +Signed-off-by: Lucas Mülling +--- + cipher/md.c | 11 +++++++++++ + src/visibility.c | 1 + + 2 files changed, 12 insertions(+) + +diff --git a/cipher/md.c b/cipher/md.c +index 666e1dfa..08a564ad 100644 +--- a/cipher/md.c ++++ b/cipher/md.c +@@ -673,6 +673,7 @@ md_copy (gcry_md_hd_t ahd, gcry_md_hd_t *b_hd) + GcryDigestEntry *ar, *br; + gcry_md_hd_t bhd; + size_t n; ++ int is_compliant_algo = 1; + + if (ahd->bufpos) + md_write (ahd, NULL, 0); +@@ -699,10 +700,15 @@ md_copy (gcry_md_hd_t ahd, gcry_md_hd_t *b_hd) + b->list = NULL; + b->debug = NULL; + ++ if (!a->list) ++ is_compliant_algo = 0; ++ + /* Copy the complete list of algorithms. The copied list is + reversed, but that doesn't matter. */ + for (ar = a->list; ar; ar = ar->next) + { ++ const gcry_md_spec_t *spec = ar->spec; ++ + if (a->flags.secure) + br = xtrymalloc_secure (ar->actual_struct_size); + else +@@ -714,6 +720,8 @@ md_copy (gcry_md_hd_t ahd, gcry_md_hd_t *b_hd) + goto leave; + } + ++ is_compliant_algo &= spec->flags.fips; ++ + memcpy (br, ar, ar->actual_struct_size); + br->next = b->list; + b->list = br; +@@ -724,6 +732,9 @@ md_copy (gcry_md_hd_t ahd, gcry_md_hd_t *b_hd) + + *b_hd = bhd; + ++ if (!is_compliant_algo) ++ fips_service_indicator_mark_non_compliant (); ++ + leave: + return err; + } +diff --git a/src/visibility.c b/src/visibility.c +index d219f1a6..c9d07f0b 100644 +--- a/src/visibility.c ++++ b/src/visibility.c +@@ -1232,6 +1232,7 @@ gcry_md_copy (gcry_md_hd_t *bhd, gcry_md_hd_t ahd) + *bhd = NULL; + return gpg_error (fips_not_operational ()); + } ++ fips_service_indicator_init (); + return gpg_error (_gcry_md_copy (bhd, ahd)); + } + +-- +2.49.0 + diff --git a/libgcrypt-fips-tests-Add-t-digest.patch b/libgcrypt-fips-tests-Add-t-digest.patch new file mode 100644 index 0000000..fc5e8e8 --- /dev/null +++ b/libgcrypt-fips-tests-Add-t-digest.patch @@ -0,0 +1,243 @@ +From 7faf542f157330f3b247fa2542182ac805f06737 Mon Sep 17 00:00:00 2001 +From: NIIBE Yutaka +Date: Mon, 9 Dec 2024 14:05:59 +0900 +Subject: [PATCH 5/5] fips,tests: Add t-digest. +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* tests/Makefile.am (tests_bin): Add t-digest. +* tests/t-digest.c: New. + +-- + +GnuPG-bug-id: 7338 +Signed-off-by: NIIBE Yutaka +Signed-off-by: Lucas Mülling +--- + tests/Makefile.am | 2 +- + tests/t-digest.c | 199 ++++++++++++++++++++++++++++++++++++++++++++++ + 2 files changed, 200 insertions(+), 1 deletion(-) + create mode 100644 tests/t-digest.c + +diff --git a/tests/Makefile.am b/tests/Makefile.am +index 52f7dd61..93774fe9 100644 +--- a/tests/Makefile.am ++++ b/tests/Makefile.am +@@ -25,7 +25,7 @@ tests_bin = \ + version t-secmem mpitests t-sexp t-convert \ + t-mpi-bit t-mpi-point t-lock \ + prime basic keygen pubkey hmac hashtest t-kdf keygrip \ +- aeswrap random t-kem t-mlkem t-thread-local ++ aeswrap random t-kem t-mlkem t-thread-local t-digest + + if USE_RSA + tests_bin += pkcs1v2 t-rsa-pss t-rsa-15 t-rsa-testparm +diff --git a/tests/t-digest.c b/tests/t-digest.c +new file mode 100644 +index 00000000..3a94fa69 +--- /dev/null ++++ b/tests/t-digest.c +@@ -0,0 +1,199 @@ ++/* t-digest.c - MD regression tests ++ * Copyright (C) 2024 g10 Code GmbH ++ * ++ * This file is part of Libgcrypt. ++ * ++ * Libgcrypt is free software; you can redistribute it and/or modify ++ * it under the terms of the GNU Lesser General Public License as ++ * published by the Free Software Foundation; either version 2.1 of ++ * the License, or (at your option) any later version. ++ * ++ * Libgcrypt 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 Lesser General Public License for more details. ++ * ++ * You should have received a copy of the GNU Lesser General Public License ++ * along with this program; if not, see . ++ * SPDX-License-Identifier: LGPL-2.1+ ++ */ ++ ++#ifdef HAVE_CONFIG_H ++#include ++#endif ++#include ++#include ++#include ++#include ++#include ++ ++#define PGM "t-digest" ++ ++#include "t-common.h" ++static int in_fips_mode; ++ ++/* Mingw requires us to include windows.h after winsock2.h which is ++ included by gcrypt.h. */ ++#ifdef _WIN32 ++# include ++#endif ++ ++static void ++check_digests (void) ++{ ++ static struct { ++ int algo; ++ const char *data; ++ int datalen; ++ const char *expect; ++ int expect_failure; ++ } tv[] = { ++#undef ENABLE_THIS_AFTER_T6376_CHANGE_REVISED ++#ifdef ENABLE_THIS_AFTER_T6376_CHANGE_REVISED ++ { GCRY_MD_MD5, "abc", 3, ++ "\x90\x01\x50\x98\x3C\xD2\x4F\xB0\xD6\x96\x3F\x7D\x28\xE1\x7F\x72", 1 }, ++#endif ++ { GCRY_MD_SHA1, "abc", 3, ++ "\xA9\x99\x3E\x36\x47\x06\x81\x6A\xBA\x3E" ++ "\x25\x71\x78\x50\xC2\x6C\x9C\xD0\xD8\x9D" }, ++ { GCRY_MD_SHA256, "abc", 3, ++ "\xba\x78\x16\xbf\x8f\x01\xcf\xea\x41\x41\x40\xde\x5d\xae\x22\x23" ++ "\xb0\x03\x61\xa3\x96\x17\x7a\x9c\xb4\x10\xff\x61\xf2\x00\x15\xad" }, ++ { GCRY_MD_SHA384, "abc", 3, ++ "\xcb\x00\x75\x3f\x45\xa3\x5e\x8b\xb5\xa0\x3d\x69\x9a\xc6\x50\x07" ++ "\x27\x2c\x32\xab\x0e\xde\xd1\x63\x1a\x8b\x60\x5a\x43\xff\x5b\xed" ++ "\x80\x86\x07\x2b\xa1\xe7\xcc\x23\x58\xba\xec\xa1\x34\xc8\x25\xa7" }, ++ { GCRY_MD_SHA512, "abc", 3, ++ "\xDD\xAF\x35\xA1\x93\x61\x7A\xBA\xCC\x41\x73\x49\xAE\x20\x41\x31" ++ "\x12\xE6\xFA\x4E\x89\xA9\x7E\xA2\x0A\x9E\xEE\xE6\x4B\x55\xD3\x9A" ++ "\x21\x92\x99\x2A\x27\x4F\xC1\xA8\x36\xBA\x3C\x23\xA3\xFE\xEB\xBD" ++ "\x45\x4D\x44\x23\x64\x3C\xE8\x0E\x2A\x9A\xC9\x4F\xA5\x4C\xA4\x9F" }, ++ { GCRY_MD_SHA3_256, "abc", 3, ++ "\x3a\x98\x5d\xa7\x4f\xe2\x25\xb2\x04\x5c\x17\x2d\x6b\xd3\x90\xbd" ++ "\x85\x5f\x08\x6e\x3e\x9d\x52\x5b\x46\xbf\xe2\x45\x11\x43\x15\x32" }, ++ { GCRY_MD_SHA3_384, "abc", 3, ++ "\xec\x01\x49\x82\x88\x51\x6f\xc9\x26\x45\x9f\x58\xe2\xc6\xad\x8d" ++ "\xf9\xb4\x73\xcb\x0f\xc0\x8c\x25\x96\xda\x7c\xf0\xe4\x9b\xe4\xb2" ++ "\x98\xd8\x8c\xea\x92\x7a\xc7\xf5\x39\xf1\xed\xf2\x28\x37\x6d\x25" }, ++ { GCRY_MD_SHA3_512, "abc", 3, ++ "\xb7\x51\x85\x0b\x1a\x57\x16\x8a\x56\x93\xcd\x92\x4b\x6b\x09\x6e" ++ "\x08\xf6\x21\x82\x74\x44\xf7\x0d\x88\x4f\x5d\x02\x40\xd2\x71\x2e" ++ "\x10\xe1\x16\xe9\x19\x2a\xf3\xc9\x1a\x7e\xc5\x76\x47\xe3\x93\x40" ++ "\x57\x34\x0b\x4c\xf4\x08\xd5\xa5\x65\x92\xf8\x27\x4e\xec\x53\xf0" }, ++ { GCRY_MD_RMD160, "abc", 3, ++ "\x8e\xb2\x08\xf7\xe0\x5d\x98\x7a\x9b\x04" ++ "\x4a\x8e\x98\xc6\xb0\x87\xf1\x5a\x0b\xfc", 1 }, ++ }; ++ int tvidx; ++ unsigned char hash[64]; ++ int expectlen; ++ ++ for (tvidx=0; tvidx < DIM(tv); tvidx++) ++ { ++ gpg_err_code_t ec; ++ ++ if (verbose) ++ fprintf (stderr, "checking gcry_md_hash_buffer test %d\n", ++ tvidx); ++ ++ expectlen = gcry_md_get_algo_dlen (tv[tvidx].algo); ++ assert (expectlen != 0); ++ assert (expectlen <= sizeof hash); ++ gcry_md_hash_buffer (tv[tvidx].algo, hash, ++ tv[tvidx].data, tv[tvidx].datalen); ++ ++ ec = gcry_get_fips_service_indicator (); ++ if (ec == GPG_ERR_INV_OP) ++ { ++ /* libgcrypt is old, no support of the FIPS service indicator. */ ++ fail ("gcry_md_hash_buffer test %d unexpectedly failed to check the FIPS service indicator.\n", ++ tvidx); ++ continue; ++ } ++ ++ if (in_fips_mode && !tv[tvidx].expect_failure && ec) ++ { ++ /* Success with the FIPS service indicator == 0 expected, but != 0. */ ++ fail ("gcry_md_hash_buffer test %d unexpectedly set the indicator in FIPS mode.\n", ++ tvidx); ++ continue; ++ } ++ else if (in_fips_mode && tv[tvidx].expect_failure && !ec) ++ { ++ /* Success with the FIPS service indicator != 0 expected, but == 0. */ ++ fail ("gcry_md_hash_buffer test %d unexpectedly cleared the indicator in FIPS mode.\n", ++ tvidx); ++ continue; ++ } ++ ++ if (memcmp (hash, tv[tvidx].expect, expectlen)) ++ { ++ int i; ++ ++ fail ("gcry_md_hash_buffer test %d failed: mismatch\n", tvidx); ++ fputs ("got:", stderr); ++ for (i=0; i < expectlen; i++) ++ fprintf (stderr, " %02x", hash[i]); ++ putc ('\n', stderr); ++ } ++ } ++} ++ ++ ++int ++main (int argc, char **argv) ++{ ++ int last_argc = -1; ++ ++ if (argc) ++ { argc--; argv++; } ++ ++ while (argc && last_argc != argc) ++ { ++ last_argc = argc; ++ if (!strcmp (*argv, "--")) ++ { ++ argc--; argv++; ++ break; ++ } ++ else if (!strcmp (*argv, "--help")) ++ { ++ fputs ("usage: " PGM " [options]\n" ++ "Options:\n" ++ " --verbose print timings etc.\n" ++ " --debug flyswatter\n", ++ stdout); ++ exit (0); ++ } ++ else if (!strcmp (*argv, "--verbose")) ++ { ++ verbose++; ++ argc--; argv++; ++ } ++ else if (!strcmp (*argv, "--debug")) ++ { ++ verbose += 2; ++ debug++; ++ argc--; argv++; ++ } ++ else if (!strncmp (*argv, "--", 2)) ++ die ("unknown option '%s'", *argv); ++ } ++ ++ if (!gcry_check_version (GCRYPT_VERSION)) ++ die ("version mismatch\n"); ++ ++ if (gcry_fips_mode_active ()) ++ in_fips_mode = 1; ++ ++ if (!in_fips_mode) ++ xgcry_control ((GCRYCTL_DISABLE_SECMEM, 0)); ++ ++ xgcry_control ((GCRYCTL_INITIALIZATION_FINISHED, 0)); ++ if (debug) ++ xgcry_control ((GCRYCTL_SET_DEBUG_FLAGS, 1u , 0)); ++ ++ check_digests (); ++ ++ return !!error_count; ++} +-- +2.49.0 + diff --git a/libgcrypt-fips-tests-Add-tests-for-md_open-write-read-close-for-t-digest.patch b/libgcrypt-fips-tests-Add-tests-for-md_open-write-read-close-for-t-digest.patch new file mode 100644 index 0000000..699c1eb --- /dev/null +++ b/libgcrypt-fips-tests-Add-tests-for-md_open-write-read-close-for-t-digest.patch @@ -0,0 +1,172 @@ +From 917fc6000dfebd8854f0d1c220b85dec0dbf4676 Mon Sep 17 00:00:00 2001 +From: NIIBE Yutaka +Date: Fri, 13 Dec 2024 11:54:31 +0900 +Subject: [PATCH 03/19] fips,tests: Add tests for md_open/write/read/close for + t-digest. +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* tests/t-digest.c (check_md_o_w_r_c): New. +(main): Call check_md_o_w_r_c. + +-- + +GnuPG-bug-id: 7338 +Signed-off-by: NIIBE Yutaka +Signed-off-by: Lucas Mülling +--- + tests/t-digest.c | 133 +++++++++++++++++++++++++++++++++++++++++++++++ + 1 file changed, 133 insertions(+) + +Index: libgcrypt-1.11.0/tests/t-digest.c +=================================================================== +--- libgcrypt-1.11.0.orig/tests/t-digest.c ++++ libgcrypt-1.11.0/tests/t-digest.c +@@ -39,6 +39,138 @@ static int in_fips_mode; + #endif + + static void ++check_md_o_w_r_c (void) ++{ ++ static struct { ++ int algo; ++ const char *data; ++ int datalen; ++ const char *expect; ++ int expect_failure; ++ unsigned int flags; ++ } tv[] = { ++#if USE_MD5 ++ { GCRY_MD_MD5, "abc", 3, ++ "\x90\x01\x50\x98\x3C\xD2\x4F\xB0\xD6\x96\x3F\x7D\x28\xE1\x7F\x72", 1 }, ++ { GCRY_MD_MD5, "abc", 3, ++ "\x90\x01\x50\x98\x3C\xD2\x4F\xB0\xD6\x96\x3F\x7D\x28\xE1\x7F\x72", 1, ++ GCRY_MD_FLAG_REJECT_NON_FIPS }, ++#endif ++#if USE_SHA1 ++ { GCRY_MD_SHA1, "abc", 3, ++ "\xA9\x99\x3E\x36\x47\x06\x81\x6A\xBA\x3E" ++ "\x25\x71\x78\x50\xC2\x6C\x9C\xD0\xD8\x9D" }, ++#endif ++ { GCRY_MD_SHA256, "abc", 3, ++ "\xba\x78\x16\xbf\x8f\x01\xcf\xea\x41\x41\x40\xde\x5d\xae\x22\x23" ++ "\xb0\x03\x61\xa3\x96\x17\x7a\x9c\xb4\x10\xff\x61\xf2\x00\x15\xad" }, ++ { GCRY_MD_SHA384, "abc", 3, ++ "\xcb\x00\x75\x3f\x45\xa3\x5e\x8b\xb5\xa0\x3d\x69\x9a\xc6\x50\x07" ++ "\x27\x2c\x32\xab\x0e\xde\xd1\x63\x1a\x8b\x60\x5a\x43\xff\x5b\xed" ++ "\x80\x86\x07\x2b\xa1\xe7\xcc\x23\x58\xba\xec\xa1\x34\xc8\x25\xa7" }, ++ { GCRY_MD_SHA512, "abc", 3, ++ "\xDD\xAF\x35\xA1\x93\x61\x7A\xBA\xCC\x41\x73\x49\xAE\x20\x41\x31" ++ "\x12\xE6\xFA\x4E\x89\xA9\x7E\xA2\x0A\x9E\xEE\xE6\x4B\x55\xD3\x9A" ++ "\x21\x92\x99\x2A\x27\x4F\xC1\xA8\x36\xBA\x3C\x23\xA3\xFE\xEB\xBD" ++ "\x45\x4D\x44\x23\x64\x3C\xE8\x0E\x2A\x9A\xC9\x4F\xA5\x4C\xA4\x9F" }, ++ { GCRY_MD_SHA3_256, "abc", 3, ++ "\x3a\x98\x5d\xa7\x4f\xe2\x25\xb2\x04\x5c\x17\x2d\x6b\xd3\x90\xbd" ++ "\x85\x5f\x08\x6e\x3e\x9d\x52\x5b\x46\xbf\xe2\x45\x11\x43\x15\x32" }, ++ { GCRY_MD_SHA3_384, "abc", 3, ++ "\xec\x01\x49\x82\x88\x51\x6f\xc9\x26\x45\x9f\x58\xe2\xc6\xad\x8d" ++ "\xf9\xb4\x73\xcb\x0f\xc0\x8c\x25\x96\xda\x7c\xf0\xe4\x9b\xe4\xb2" ++ "\x98\xd8\x8c\xea\x92\x7a\xc7\xf5\x39\xf1\xed\xf2\x28\x37\x6d\x25" }, ++ { GCRY_MD_SHA3_512, "abc", 3, ++ "\xb7\x51\x85\x0b\x1a\x57\x16\x8a\x56\x93\xcd\x92\x4b\x6b\x09\x6e" ++ "\x08\xf6\x21\x82\x74\x44\xf7\x0d\x88\x4f\x5d\x02\x40\xd2\x71\x2e" ++ "\x10\xe1\x16\xe9\x19\x2a\xf3\xc9\x1a\x7e\xc5\x76\x47\xe3\x93\x40" ++ "\x57\x34\x0b\x4c\xf4\x08\xd5\xa5\x65\x92\xf8\x27\x4e\xec\x53\xf0" } ++#if USE_RMD160 ++ , ++ { GCRY_MD_RMD160, "abc", 3, ++ "\x8e\xb2\x08\xf7\xe0\x5d\x98\x7a\x9b\x04" ++ "\x4a\x8e\x98\xc6\xb0\x87\xf1\x5a\x0b\xfc", 1 } ++#endif ++ }; ++ int tvidx; ++ unsigned char *hash; ++ int expectlen; ++ gpg_error_t err; ++ ++ for (tvidx=0; tvidx < DIM(tv); tvidx++) ++ { ++ gpg_err_code_t ec; ++ gcry_md_hd_t h; ++ ++ if (verbose) ++ fprintf (stderr, "checking gcry_md_open test %d\n", ++ tvidx); ++ ++ expectlen = gcry_md_get_algo_dlen (tv[tvidx].algo); ++ assert (expectlen != 0); ++ err = gcry_md_open (&h, tv[tvidx].algo, tv[tvidx].flags); ++ if (err) ++ { ++ if (in_fips_mode && (tv[tvidx].flags & GCRY_MD_FLAG_REJECT_NON_FIPS) ++ && tv[tvidx].expect_failure) ++ /* Here, an error is expected */ ++ ; ++ else ++ fail ("gcry_md_open test %d unexpectedly failed: %s\n", ++ tvidx, gpg_strerror (err)); ++ continue; ++ } ++ else ++ { ++ if (in_fips_mode && (tv[tvidx].flags & GCRY_MD_FLAG_REJECT_NON_FIPS) ++ && tv[tvidx].expect_failure) ++ /* This case, an error is expected, but we observed success */ ++ fail ("gcry_md_open test %d unexpectedly succeeded\n", tvidx); ++ } ++ ++ ++ ec = gcry_get_fips_service_indicator (); ++ if (ec == GPG_ERR_INV_OP) ++ { ++ /* libgcrypt is old, no support of the FIPS service indicator. */ ++ fail ("gcry_md_open test %d unexpectedly failed to check the FIPS service indicator.\n", ++ tvidx); ++ continue; ++ } ++ ++ if (in_fips_mode && !tv[tvidx].expect_failure && ec) ++ { ++ /* Success with the FIPS service indicator == 0 expected, but != 0. */ ++ fail ("gcry_md_open test %d unexpectedly set the indicator in FIPS mode.\n", ++ tvidx); ++ continue; ++ } ++ else if (in_fips_mode && tv[tvidx].expect_failure && !ec) ++ { ++ /* Success with the FIPS service indicator != 0 expected, but == 0. */ ++ fail ("gcry_md_open test %d unexpectedly cleared the indicator in FIPS mode.\n", ++ tvidx); ++ continue; ++ } ++ ++ gcry_md_write (h, tv[tvidx].data, tv[tvidx].datalen); ++ hash = gcry_md_read (h, tv[tvidx].algo); ++ if (memcmp (hash, tv[tvidx].expect, expectlen)) ++ { ++ int i; ++ ++ fail ("gcry_md_open test %d failed: mismatch\n", tvidx); ++ fputs ("got:", stderr); ++ for (i=0; i < expectlen; i++) ++ fprintf (stderr, " %02x", hash[i]); ++ putc ('\n', stderr); ++ } ++ ++ gcry_md_close (h); ++ } ++} ++ ++static void + check_digests (void) + { + static struct { +@@ -194,6 +326,7 @@ main (int argc, char **argv) + xgcry_control ((GCRYCTL_SET_DEBUG_FLAGS, 1u , 0)); + + check_digests (); ++ check_md_o_w_r_c (); + + return !!error_count; + } diff --git a/libgcrypt-jitterentropy-3.4.0.patch b/libgcrypt-jitterentropy-3.4.0.patch new file mode 100644 index 0000000..dbb77ba --- /dev/null +++ b/libgcrypt-jitterentropy-3.4.0.patch @@ -0,0 +1,618 @@ +Index: libgcrypt-1.10.0/random/jitterentropy-base.c +=================================================================== +--- libgcrypt-1.10.0.orig/random/jitterentropy-base.c ++++ libgcrypt-1.10.0/random/jitterentropy-base.c +@@ -42,7 +42,7 @@ + * require consumer to be updated (as long as this number + * is zero, the API is not considered stable and can + * change without a bump of the major version) */ +-#define MINVERSION 3 /* API compatible, ABI may change, functional ++#define MINVERSION 4 /* API compatible, ABI may change, functional + * enhancements only, consumer can be left unchanged if + * enhancements are not considered */ + #define PATCHLEVEL 0 /* API / ABI compatible, no functional changes, no +@@ -200,29 +200,38 @@ ssize_t jent_read_entropy(struct rand_da + tocopy = (DATA_SIZE_BITS / 8); + else + tocopy = len; +- memcpy(p, &ec->data, tocopy); ++ ++ jent_read_random_block(ec, p, tocopy); + + len -= tocopy; + p += tocopy; + } + + /* +- * To be on the safe side, we generate one more round of entropy +- * which we do not give out to the caller. That round shall ensure +- * that in case the calling application crashes, memory dumps, pages +- * out, or due to the CPU Jitter RNG lingering in memory for long +- * time without being moved and an attacker cracks the application, +- * all he reads in the entropy pool is a value that is NEVER EVER +- * being used for anything. Thus, he does NOT see the previous value +- * that was returned to the caller for cryptographic purposes. ++ * Enhanced backtracking support: At this point, the hash state ++ * contains the digest of the previous Jitter RNG collection round ++ * which is inserted there by jent_read_random_block with the SHA ++ * update operation. At the current code location we completed ++ * one request for a caller and we do not know how long it will ++ * take until a new request is sent to us. To guarantee enhanced ++ * backtracking resistance at this point (i.e. ensure that an attacker ++ * cannot obtain information about prior random numbers we generated), ++ * but still stirring the hash state with old data the Jitter RNG ++ * obtains a new message digest from its state and re-inserts it. ++ * After this operation, the Jitter RNG state is still stirred with ++ * the old data, but an attacker who gets access to the memory after ++ * this point cannot deduce the random numbers produced by the ++ * Jitter RNG prior to this point. + */ + /* +- * If we use secured memory, do not use that precaution as the secure +- * memory protects the entropy pool. Moreover, note that using this +- * call reduces the speed of the RNG by up to half ++ * If we use secured memory, where backtracking support may not be ++ * needed because the state is protected in a different method, ++ * it is permissible to drop this support. But strongly weigh the ++ * pros and cons considering that the SHA3 operation is not that ++ * expensive. + */ + #ifndef JENT_CPU_JITTERENTROPY_SECURE_MEMORY +- jent_random_data(ec); ++ jent_read_random_block(ec, NULL, 0); + #endif + + err: +@@ -379,6 +388,7 @@ static struct rand_data + *jent_entropy_collector_alloc_internal(unsigned int osr, unsigned int flags) + { + struct rand_data *entropy_collector; ++ uint32_t memsize = 0; + + /* + * Requesting disabling and forcing of internal timer +@@ -405,7 +415,7 @@ static struct rand_data + return NULL; + + if (!(flags & JENT_DISABLE_MEMORY_ACCESS)) { +- uint32_t memsize = jent_memsize(flags); ++ memsize = jent_memsize(flags); + + entropy_collector->mem = _gcry_calloc (1, memsize); + +@@ -431,13 +441,19 @@ static struct rand_data + entropy_collector->memaccessloops = JENT_MEMORY_ACCESSLOOPS; + } + ++ if (sha3_alloc(&entropy_collector->hash_state)) ++ goto err; ++ ++ /* Initialize the hash state */ ++ sha3_256_init(entropy_collector->hash_state); ++ + /* verify and set the oversampling rate */ + if (osr < JENT_MIN_OSR) + osr = JENT_MIN_OSR; + entropy_collector->osr = osr; + entropy_collector->flags = flags; + +- if (jent_fips_enabled() || (flags & JENT_FORCE_FIPS)) ++ if ((flags & JENT_FORCE_FIPS) || jent_fips_enabled()) + entropy_collector->fips_enabled = 1; + + /* Initialize the APT */ +@@ -469,7 +485,7 @@ static struct rand_data + + err: + if (entropy_collector->mem != NULL) +- jent_zfree(entropy_collector->mem, JENT_MEMORY_SIZE); ++ jent_zfree(entropy_collector->mem, memsize); + jent_zfree(entropy_collector, sizeof(struct rand_data)); + return NULL; + } +@@ -511,6 +527,7 @@ JENT_PRIVATE_STATIC + void jent_entropy_collector_free(struct rand_data *entropy_collector) + { + if (entropy_collector != NULL) { ++ sha3_dealloc(entropy_collector->hash_state); + jent_notime_disable(entropy_collector); + if (entropy_collector->mem != NULL) { + jent_zfree(entropy_collector->mem, +@@ -664,6 +681,7 @@ static inline int jent_entropy_init_comm + int ret; + + jent_notime_block_switch(); ++ jent_health_cb_block_switch(); + + if (sha3_tester()) + return EHASH; +@@ -710,6 +728,8 @@ int jent_entropy_init_ex(unsigned int os + if (ret) + return ret; + ++ ret = ENOTIME; ++ + /* Test without internal timer unless caller does not want it */ + if (!(flags & JENT_FORCE_INTERNAL_TIMER)) + ret = jent_time_entropy_init(osr, +@@ -732,3 +752,9 @@ int jent_entropy_switch_notime_impl(stru + return jent_notime_switch(new_thread); + } + #endif ++ ++JENT_PRIVATE_STATIC ++int jent_set_fips_failure_callback(jent_fips_failure_cb cb) ++{ ++ return jent_set_fips_failure_callback_internal(cb); ++} +Index: libgcrypt-1.10.0/random/jitterentropy-gcd.c +=================================================================== +--- libgcrypt-1.10.0.orig/random/jitterentropy-gcd.c ++++ libgcrypt-1.10.0/random/jitterentropy-gcd.c +@@ -113,12 +113,8 @@ int jent_gcd_analyze(uint64_t *delta_his + goto out; + } + +- /* +- * Ensure that we have variations in the time stamp below 100 for at +- * least 10% of all checks -- on some platforms, the counter increments +- * in multiples of 100, but not always +- */ +- if (running_gcd >= 100) { ++ /* Set a sensible maximum value. */ ++ if (running_gcd >= UINT32_MAX / 2) { + ret = ECOARSETIME; + goto out; + } +Index: libgcrypt-1.10.0/random/jitterentropy-health.c +=================================================================== +--- libgcrypt-1.10.0.orig/random/jitterentropy-health.c ++++ libgcrypt-1.10.0/random/jitterentropy-health.c +@@ -19,9 +19,24 @@ + * DAMAGE. + */ + +-#include "jitterentropy.h" + #include "jitterentropy-health.h" + ++static jent_fips_failure_cb fips_cb = NULL; ++static int jent_health_cb_switch_blocked = 0; ++ ++void jent_health_cb_block_switch(void) ++{ ++ jent_health_cb_switch_blocked = 1; ++} ++ ++int jent_set_fips_failure_callback_internal(jent_fips_failure_cb cb) ++{ ++ if (jent_health_cb_switch_blocked) ++ return -EAGAIN; ++ fips_cb = cb; ++ return 0; ++} ++ + /*************************************************************************** + * Lag Predictor Test + * +@@ -434,5 +449,9 @@ unsigned int jent_health_failure(struct + if (!ec->fips_enabled) + return 0; + ++ if (fips_cb && ec->health_failure) { ++ fips_cb(ec, ec->health_failure); ++ } ++ + return ec->health_failure; + } +Index: libgcrypt-1.10.0/random/jitterentropy-health.h +=================================================================== +--- libgcrypt-1.10.0.orig/random/jitterentropy-health.h ++++ libgcrypt-1.10.0/random/jitterentropy-health.h +@@ -20,11 +20,16 @@ + #ifndef JITTERENTROPY_HEALTH_H + #define JITTERENTROPY_HEALTH_H + ++#include "jitterentropy.h" ++ + #ifdef __cplusplus + extern "C" + { + #endif + ++void jent_health_cb_block_switch(void); ++int jent_set_fips_failure_callback_internal(jent_fips_failure_cb cb); ++ + static inline uint64_t jent_delta(uint64_t prev, uint64_t next) + { + return (next - prev); +Index: libgcrypt-1.10.0/random/jitterentropy-noise.c +=================================================================== +--- libgcrypt-1.10.0.orig/random/jitterentropy-noise.c ++++ libgcrypt-1.10.0/random/jitterentropy-noise.c +@@ -33,7 +33,7 @@ + * Update of the loop count used for the next round of + * an entropy collection. + * +- * @ec [in] entropy collector struct -- may be NULL ++ * @ec [in] entropy collector struct + * @bits [in] is the number of low bits of the timer to consider + * @min [in] is the number of bits we shift the timer value to the right at + * the end to make sure we have a guaranteed minimum value +@@ -61,16 +61,13 @@ static uint64_t jent_loop_shuffle(struct + * Mix the current state of the random number into the shuffle + * calculation to balance that shuffle a bit more. + */ +- if (ec) { +- jent_get_nstime_internal(ec, &time); +- time ^= ec->data[0]; +- } ++ jent_get_nstime_internal(ec, &time); + + /* + * We fold the time value as much as possible to ensure that as many + * bits of the time stamp are included as possible. + */ +- for (i = 0; ((DATA_SIZE_BITS + bits - 1) / bits) > i; i++) { ++ for (i = 0; (((sizeof(time) << 3) + bits - 1) / bits) > i; i++) { + shuffle ^= time & mask; + time = time >> bits; + } +@@ -91,11 +88,11 @@ static uint64_t jent_loop_shuffle(struct + * This function injects the individual bits of the time value into the + * entropy pool using a hash. + * +- * @ec [in] entropy collector struct -- may be NULL +- * @time [in] time stamp to be injected ++ * @ec [in] entropy collector struct ++ * @time [in] time delta to be injected + * @loop_cnt [in] if a value not equal to 0 is set, use the given value as + * number of loops to perform the hash operation +- * @stuck [in] Is the time stamp identified as stuck? ++ * @stuck [in] Is the time delta identified as stuck? + * + * Output: + * updated hash context +@@ -104,17 +101,19 @@ static void jent_hash_time(struct rand_d + uint64_t loop_cnt, unsigned int stuck) + { + HASH_CTX_ON_STACK(ctx); +- uint8_t itermediary[SHA3_256_SIZE_DIGEST]; ++ uint8_t intermediary[SHA3_256_SIZE_DIGEST]; + uint64_t j = 0; +- uint64_t hash_loop_cnt; + #define MAX_HASH_LOOP 3 + #define MIN_HASH_LOOP 0 + + /* Ensure that macros cannot overflow jent_loop_shuffle() */ + BUILD_BUG_ON((MAX_HASH_LOOP + MIN_HASH_LOOP) > 63); +- hash_loop_cnt = ++ uint64_t hash_loop_cnt = + jent_loop_shuffle(ec, MAX_HASH_LOOP, MIN_HASH_LOOP); + ++ /* Use the memset to shut up valgrind */ ++ memset(intermediary, 0, sizeof(intermediary)); ++ + sha3_256_init(&ctx); + + /* +@@ -125,35 +124,54 @@ static void jent_hash_time(struct rand_d + hash_loop_cnt = loop_cnt; + + /* +- * This loop basically slows down the SHA-3 operation depending +- * on the hash_loop_cnt. Each iteration of the loop generates the +- * same result. ++ * This loop fills a buffer which is injected into the entropy pool. ++ * The main reason for this loop is to execute something over which we ++ * can perform a timing measurement. The injection of the resulting ++ * data into the pool is performed to ensure the result is used and ++ * the compiler cannot optimize the loop away in case the result is not ++ * used at all. Yet that data is considered "additional information" ++ * considering the terminology from SP800-90A without any entropy. ++ * ++ * Note, it does not matter which or how much data you inject, we are ++ * interested in one Keccack1600 compression operation performed with ++ * the sha3_final. + */ + for (j = 0; j < hash_loop_cnt; j++) { +- sha3_update(&ctx, ec->data, SHA3_256_SIZE_DIGEST); +- sha3_update(&ctx, (uint8_t *)&time, sizeof(uint64_t)); ++ sha3_update(&ctx, intermediary, sizeof(intermediary)); ++ sha3_update(&ctx, (uint8_t *)&ec->rct_count, ++ sizeof(ec->rct_count)); ++ sha3_update(&ctx, (uint8_t *)&ec->apt_cutoff, ++ sizeof(ec->apt_cutoff)); ++ sha3_update(&ctx, (uint8_t *)&ec->apt_observations, ++ sizeof(ec->apt_observations)); ++ sha3_update(&ctx, (uint8_t *)&ec->apt_count, ++ sizeof(ec->apt_count)); ++ sha3_update(&ctx,(uint8_t *) &ec->apt_base, ++ sizeof(ec->apt_base)); + sha3_update(&ctx, (uint8_t *)&j, sizeof(uint64_t)); ++ sha3_final(&ctx, intermediary); ++ } + +- /* +- * If the time stamp is stuck, do not finally insert the value +- * into the entropy pool. Although this operation should not do +- * any harm even when the time stamp has no entropy, SP800-90B +- * requires that any conditioning operation to have an identical +- * amount of input data according to section 3.1.5. +- */ ++ /* ++ * Inject the data from the previous loop into the pool. This data is ++ * not considered to contain any entropy, but it stirs the pool a bit. ++ */ ++ sha3_update(ec->hash_state, intermediary, sizeof(intermediary)); + +- /* +- * The sha3_final operations re-initialize the context for the +- * next loop iteration. +- */ +- if (stuck || (j < hash_loop_cnt - 1)) +- sha3_final(&ctx, itermediary); +- else +- sha3_final(&ctx, ec->data); +- } ++ /* ++ * Insert the time stamp into the hash context representing the pool. ++ * ++ * If the time stamp is stuck, do not finally insert the value into the ++ * entropy pool. Although this operation should not do any harm even ++ * when the time stamp has no entropy, SP800-90B requires that any ++ * conditioning operation to have an identical amount of input data ++ * according to section 3.1.5. ++ */ ++ if (!stuck) ++ sha3_update(ec->hash_state, (uint8_t *)&time, sizeof(uint64_t)); + + jent_memset_secure(&ctx, SHA_MAX_CTX_SIZE); +- jent_memset_secure(itermediary, sizeof(itermediary)); ++ jent_memset_secure(intermediary, sizeof(intermediary)); + } + + #define MAX_ACC_LOOP_BIT 7 +@@ -184,13 +202,12 @@ static inline uint32_t xoshiro128starsta + + static void jent_memaccess(struct rand_data *ec, uint64_t loop_cnt) + { +- uint64_t i = 0; ++ uint64_t i = 0, time = 0; + union { + uint32_t u[4]; + uint8_t b[sizeof(uint32_t) * 4]; + } prngState = { .u = {0x8e93eec0, 0xce65608a, 0xa8d46b46, 0xe83cef69} }; + uint32_t addressMask; +- uint64_t acc_loop_cnt; + + if (NULL == ec || NULL == ec->mem) + return; +@@ -199,7 +216,7 @@ static void jent_memaccess(struct rand_d + + /* Ensure that macros cannot overflow jent_loop_shuffle() */ + BUILD_BUG_ON((MAX_ACC_LOOP_BIT + MIN_ACC_LOOP_BIT) > 63); +- acc_loop_cnt = ++ uint64_t acc_loop_cnt = + jent_loop_shuffle(ec, MAX_ACC_LOOP_BIT, MIN_ACC_LOOP_BIT); + + /* +@@ -213,8 +230,10 @@ static void jent_memaccess(struct rand_d + * "per-update: timing, it gets you mostly independent "per-update" + * timing, so we can now benefit from the Central Limit Theorem! + */ +- for (i = 0; i < sizeof(prngState); i++) +- prngState.b[i] ^= ec->data[i]; ++ for (i = 0; i < sizeof(prngState); i++) { ++ jent_get_nstime_internal(ec, &time); ++ prngState.b[i] ^= (uint8_t)(time & 0xff); ++ } + + /* + * testing purposes -- allow test app to set the counter, not +@@ -358,21 +377,21 @@ unsigned int jent_measure_jitter(struct + + /** + * Generator of one 256 bit random number +- * Function fills rand_data->data ++ * Function fills rand_data->hash_state + * + * @ec [in] Reference to entropy collector + */ + void jent_random_data(struct rand_data *ec) + { +- unsigned int k = 0, safety_factor = ENTROPY_SAFETY_FACTOR; ++ unsigned int k = 0, safety_factor = 0; + +- if (!ec->fips_enabled) +- safety_factor = 0; ++ if (ec->fips_enabled) ++ safety_factor = ENTROPY_SAFETY_FACTOR; + + /* priming of the ->prev_time value */ + jent_measure_jitter(ec, 0, NULL); + +- while (1) { ++ while (!jent_health_failure(ec)) { + /* If a stuck measurement is received, repeat measurement */ + if (jent_measure_jitter(ec, 0, NULL)) + continue; +@@ -385,3 +404,22 @@ void jent_random_data(struct rand_data * + break; + } + } ++ ++void jent_read_random_block(struct rand_data *ec, char *dst, size_t dst_len) ++{ ++ uint8_t jent_block[SHA3_256_SIZE_DIGEST]; ++ ++ BUILD_BUG_ON(SHA3_256_SIZE_DIGEST != (DATA_SIZE_BITS / 8)); ++ ++ /* The final operation automatically re-initializes the ->hash_state */ ++ sha3_final(ec->hash_state, jent_block); ++ if (dst_len) ++ memcpy(dst, jent_block, dst_len); ++ ++ /* ++ * Stir the new state with the data from the old state - the digest ++ * of the old data is not considered to have entropy. ++ */ ++ sha3_update(ec->hash_state, jent_block, sizeof(jent_block)); ++ jent_memset_secure(jent_block, sizeof(jent_block)); ++} +Index: libgcrypt-1.10.0/random/jitterentropy-noise.h +=================================================================== +--- libgcrypt-1.10.0.orig/random/jitterentropy-noise.h ++++ libgcrypt-1.10.0/random/jitterentropy-noise.h +@@ -31,6 +31,7 @@ unsigned int jent_measure_jitter(struct + uint64_t loop_cnt, + uint64_t *ret_current_delta); + void jent_random_data(struct rand_data *ec); ++void jent_read_random_block(struct rand_data *ec, char *dst, size_t dst_len); + + #ifdef __cplusplus + } +Index: libgcrypt-1.10.0/random/jitterentropy-sha3.c +=================================================================== +--- libgcrypt-1.10.0.orig/random/jitterentropy-sha3.c ++++ libgcrypt-1.10.0/random/jitterentropy-sha3.c +@@ -19,6 +19,7 @@ + */ + + #include "jitterentropy-sha3.h" ++#include "jitterentropy.h" + + /*************************************************************************** + * Message Digest Implementation +@@ -380,3 +381,23 @@ int sha3_tester(void) + + return 0; + } ++ ++int sha3_alloc(void **hash_state) ++{ ++ struct sha_ctx *tmp; ++ ++ tmp = jent_zalloc(SHA_MAX_CTX_SIZE); ++ if (!tmp) ++ return 1; ++ ++ *hash_state = tmp; ++ ++ return 0; ++} ++ ++void sha3_dealloc(void *hash_state) ++{ ++ struct sha_ctx *ctx = (struct sha_ctx *)hash_state; ++ ++ jent_zfree(ctx, SHA_MAX_CTX_SIZE); ++} +Index: libgcrypt-1.10.0/random/jitterentropy-sha3.h +=================================================================== +--- libgcrypt-1.10.0.orig/random/jitterentropy-sha3.h ++++ libgcrypt-1.10.0/random/jitterentropy-sha3.h +@@ -47,6 +47,8 @@ struct sha_ctx { + void sha3_256_init(struct sha_ctx *ctx); + void sha3_update(struct sha_ctx *ctx, const uint8_t *in, size_t inlen); + void sha3_final(struct sha_ctx *ctx, uint8_t *digest); ++int sha3_alloc(void **hash_state); ++void sha3_dealloc(void *hash_state); + int sha3_tester(void); + + #ifdef __cplusplus +Index: libgcrypt-1.10.0/random/jitterentropy-timer.c +=================================================================== +--- libgcrypt-1.10.0.orig/random/jitterentropy-timer.c ++++ libgcrypt-1.10.0/random/jitterentropy-timer.c +@@ -202,8 +202,8 @@ int jent_notime_enable(struct rand_data + if (jent_force_internal_timer || (flags & JENT_FORCE_INTERNAL_TIMER)) { + /* Self test not run yet */ + if (!jent_force_internal_timer && +- jent_time_entropy_init(flags | JENT_FORCE_INTERNAL_TIMER, +- ec->osr)) ++ jent_time_entropy_init(ec->osr, ++ flags | JENT_FORCE_INTERNAL_TIMER)) + return EHEALTH; + + ec->enable_notime = 1; +Index: libgcrypt-1.10.0/random/jitterentropy.h +=================================================================== +--- libgcrypt-1.10.0.orig/random/jitterentropy.h ++++ libgcrypt-1.10.0/random/jitterentropy.h +@@ -49,7 +49,7 @@ + ***************************************************************************/ + + /* +- * Enable timer-less timer support ++ * Enable timer-less timer support with JENT_CONF_ENABLE_INTERNAL_TIMER + * + * In case the hardware is identified to not provide a high-resolution time + * stamp, this option enables a built-in high-resolution time stamp mechanism. +@@ -166,7 +166,7 @@ struct rand_data + * of the RNG are marked as SENSITIVE. A user must not + * access that information while the RNG executes its loops to + * calculate the next random value. */ +- uint8_t data[SHA3_256_SIZE_DIGEST]; /* SENSITIVE Actual random number */ ++ void *hash_state; /* SENSITIVE hash state entropy pool */ + uint64_t prev_time; /* SENSITIVE Previous time stamp */ + #define DATA_SIZE_BITS (SHA3_256_SIZE_DIGEST_BITS) + +@@ -378,28 +378,34 @@ int jent_entropy_init(void); + JENT_PRIVATE_STATIC + int jent_entropy_init_ex(unsigned int osr, unsigned int flags); + ++/* ++ * Set a callback to run on health failure in FIPS mode. ++ * This function will take an action determined by the caller. ++ */ ++typedef void (*jent_fips_failure_cb)(struct rand_data *ec, ++ unsigned int health_failure); ++JENT_PRIVATE_STATIC ++int jent_set_fips_failure_callback(jent_fips_failure_cb cb); ++ + /* return version number of core library */ + JENT_PRIVATE_STATIC + unsigned int jent_version(void); + +-#ifdef JENT_CONF_ENABLE_INTERNAL_TIMER + /* Set a different thread handling logic for the notimer support */ + JENT_PRIVATE_STATIC + int jent_entropy_switch_notime_impl(struct jent_notime_thread *new_thread); +-#endif + + /* -- END of Main interface functions -- */ + + /* -- BEGIN timer-less threading support functions to prevent code dupes -- */ + +-struct jent_notime_ctx { + #ifdef JENT_CONF_ENABLE_INTERNAL_TIMER ++ ++struct jent_notime_ctx { + pthread_attr_t notime_pthread_attr; /* pthreads library */ + pthread_t notime_thread_id; /* pthreads thread ID */ +-#endif + }; + +-#ifdef JENT_CONF_ENABLE_INTERNAL_TIMER + + JENT_PRIVATE_STATIC + int jent_notime_init(void **ctx); +Index: libgcrypt-1.10.0/random/jitterentropy-base-user.h +=================================================================== +--- libgcrypt-1.10.0.orig/random/jitterentropy-base-user.h ++++ libgcrypt-1.10.0/random/jitterentropy-base-user.h +@@ -213,12 +213,12 @@ static inline void jent_get_cachesize(lo + ext = strstr(buf, "K"); + if (ext) { + shift = 10; +- ext = '\0'; ++ *ext = '\0'; + } else { + ext = strstr(buf, "M"); + if (ext) { + shift = 20; +- ext = '\0'; ++ *ext = '\0'; + } + } + diff --git a/libgcrypt-md-Fix-gcry_md_algo_info-to-mark-reject-under-FIPS-mode.patch b/libgcrypt-md-Fix-gcry_md_algo_info-to-mark-reject-under-FIPS-mode.patch new file mode 100644 index 0000000..25f5904 --- /dev/null +++ b/libgcrypt-md-Fix-gcry_md_algo_info-to-mark-reject-under-FIPS-mode.patch @@ -0,0 +1,82 @@ +From 2f17a98a80b155e750ab77d4703e33612e545d58 Mon Sep 17 00:00:00 2001 +From: NIIBE Yutaka +Date: Tue, 25 Feb 2025 16:27:25 +0900 +Subject: [PATCH 1/4] md: Fix gcry_md_algo_info to mark/reject under FIPS mode. +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* cipher/md.c (check_digest_algo): Fix for marking non-compliance. +* src/visibility.c (gcry_md_algo_info): Add check with +fips_is_operational. + +-- + +GnuPG-bug-id: 7338 +Signed-off-by: NIIBE Yutaka +Signed-off-by: Lucas Mülling +--- + cipher/md.c | 26 ++++++++++++++++++++++---- + src/visibility.c | 3 +++ + 2 files changed, 25 insertions(+), 4 deletions(-) + +diff --git a/cipher/md.c b/cipher/md.c +index f600e7bb..caf33afc 100644 +--- a/cipher/md.c ++++ b/cipher/md.c +@@ -436,16 +436,34 @@ _gcry_md_algo_name (int algorithm) + + + static gcry_err_code_t +-check_digest_algo (int algorithm) ++check_digest_algo (int algo) + { + const gcry_md_spec_t *spec; ++ int reject = 0; + +- spec = spec_from_algo (algorithm); +- if (spec && !spec->flags.disabled && (spec->flags.fips || !fips_mode ())) ++ spec = spec_from_algo (algo); ++ if (!spec) ++ return GPG_ERR_DIGEST_ALGO; ++ ++ if (spec->flags.disabled) ++ return GPG_ERR_DIGEST_ALGO; ++ ++ if (!fips_mode ()) + return 0; + +- return GPG_ERR_DIGEST_ALGO; ++ if (spec->flags.fips) ++ return 0; ++ ++ if (algo == GCRY_MD_MD5) ++ reject = fips_check_rejection (GCRY_FIPS_FLAG_REJECT_MD_MD5); ++ else ++ reject = fips_check_rejection (GCRY_FIPS_FLAG_REJECT_MD_OTHERS); ++ ++ if (reject) ++ return GPG_ERR_DIGEST_ALGO; + ++ fips_service_indicator_mark_non_compliant (); ++ return 0; + } + + +diff --git a/src/visibility.c b/src/visibility.c +index e02d6cfe..4134446a 100644 +--- a/src/visibility.c ++++ b/src/visibility.c +@@ -1373,6 +1373,9 @@ gcry_md_info (gcry_md_hd_t h, int what, void *buffer, size_t *nbytes) + gcry_error_t + gcry_md_algo_info (int algo, int what, void *buffer, size_t *nbytes) + { ++ if (!fips_is_operational ()) ++ return gpg_error (fips_not_operational ()); ++ fips_service_indicator_init (); + return gpg_error (_gcry_md_algo_info (algo, what, buffer, nbytes)); + } + +-- +2.49.0 + diff --git a/libgcrypt-md-Make-SHA-1-non-FIPS-internally-for-1.12-API.patch b/libgcrypt-md-Make-SHA-1-non-FIPS-internally-for-1.12-API.patch new file mode 100644 index 0000000..bbea9bb --- /dev/null +++ b/libgcrypt-md-Make-SHA-1-non-FIPS-internally-for-1.12-API.patch @@ -0,0 +1,154 @@ +From 4ee91a94bcdad32aed4364d09e3daf8841fa579f Mon Sep 17 00:00:00 2001 +From: NIIBE Yutaka +Date: Tue, 11 Mar 2025 14:01:11 +0900 +Subject: [PATCH 11/14] md: Make SHA-1 non-FIPS internally for 1.12 API. +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* src/gcrypt.h.in (GCRY_FIPS_FLAG_REJECT_MD_SHA1): New. +* cipher/md.c (check_digest_algo_spec, _gcry_md_open, md_enable) +(_gcry_md_enable, md_copy): Care about SHA1. +* cipher/sha1.c (_gcry_digest_spec_sha1): Make SHA1 non-FIPS. +* tests/t-fips-service-ind.c (check_mac_o_w_r_c): SHA1 is non-FIPS. +(check_md_o_w_r_c, check_hash_buffer, check_hash_buffers): Likewise. +(main): Add GCRY_FIPS_FLAG_REJECT_MD_SHA1 for gcry_control. + +-- + +For 1.10 ABI (which 1.11 keeps), SHA1 is an approved hash function +(while its use in public key crypto is non-FIPS). + +For 1.12 API, the dynamic FIPS service indicator is going to be added. + +In 1.11.1 implementation, we are trying to support 1.12 dynamic FIPS +service indicator in forward-compatible way. For this purpose, +internally, it's specified as non-FIPS in _gcry_digest_spec_sha1. + +Note that update for tests/basic.c and tests/pkcs1v2.c are needed to +use SHA256 (or one of approved hash functions) in 1.12, so that test +program can be a reference for programmers. + +Co-authored-by: Lucas Mulling +Signed-off-by: NIIBE Yutaka +Signed-off-by: Lucas Mülling +--- + cipher/md.c | 10 ++++++++++ + cipher/sha1.c | 2 +- + src/gcrypt.h.in | 1 + + tests/t-fips-service-ind.c | 9 +++++---- + 4 files changed, 17 insertions(+), 5 deletions(-) + +Index: libgcrypt-1.11.0/cipher/md.c +=================================================================== +--- libgcrypt-1.11.0.orig/cipher/md.c ++++ libgcrypt-1.11.0/cipher/md.c +@@ -451,6 +451,8 @@ check_digest_algo_spec (int algo, const + + if (algo == GCRY_MD_MD5) + reject = fips_check_rejection (GCRY_FIPS_FLAG_REJECT_MD_MD5); ++ else if (algo == GCRY_MD_SHA1) ++ reject = fips_check_rejection (GCRY_FIPS_FLAG_REJECT_MD_SHA1); + else + reject = fips_check_rejection (GCRY_FIPS_FLAG_REJECT_MD_OTHERS); + +@@ -590,6 +592,8 @@ _gcry_md_open (gcry_md_hd_t *h, int algo + + if (algo == GCRY_MD_MD5) + reject = fips_check_rejection (GCRY_FIPS_FLAG_REJECT_MD_MD5); ++ else if (algo == GCRY_MD_SHA1) ++ reject = fips_check_rejection (GCRY_FIPS_FLAG_REJECT_MD_SHA1); + else + reject = fips_check_rejection (GCRY_FIPS_FLAG_REJECT_MD_OTHERS); + +@@ -625,6 +629,8 @@ md_enable (gcry_md_hd_t hd, int algorith + + if (algorithm == GCRY_MD_MD5) + reject = fips_check_rejection (GCRY_FIPS_FLAG_REJECT_MD_MD5); ++ else if (algorithm == GCRY_MD_SHA1) ++ reject = fips_check_rejection (GCRY_FIPS_FLAG_REJECT_MD_SHA1); + else + reject = fips_check_rejection (GCRY_FIPS_FLAG_REJECT_MD_OTHERS); + +@@ -703,6 +709,8 @@ _gcry_md_enable (gcry_md_hd_t hd, int al + + if (algorithm == GCRY_MD_MD5) + reject = fips_check_rejection (GCRY_FIPS_FLAG_REJECT_MD_MD5); ++ else if (algorithm == GCRY_MD_SHA1) ++ reject = fips_check_rejection (GCRY_FIPS_FLAG_REJECT_MD_SHA1); + else + reject = fips_check_rejection (GCRY_FIPS_FLAG_REJECT_MD_OTHERS); + +@@ -780,6 +788,8 @@ md_copy (gcry_md_hd_t ahd, gcry_md_hd_t + + if (spec->algo == GCRY_MD_MD5) + reject |= fips_check_rejection (GCRY_FIPS_FLAG_REJECT_MD_MD5); ++ else if (spec->algo == GCRY_MD_SHA1) ++ reject = fips_check_rejection (GCRY_FIPS_FLAG_REJECT_MD_SHA1); + else + reject |= fips_check_rejection (GCRY_FIPS_FLAG_REJECT_MD_OTHERS); + } +Index: libgcrypt-1.11.0/cipher/sha1.c +=================================================================== +--- libgcrypt-1.11.0.orig/cipher/sha1.c ++++ libgcrypt-1.11.0/cipher/sha1.c +@@ -759,7 +759,7 @@ static const gcry_md_oid_spec_t oid_spec + + const gcry_md_spec_t _gcry_digest_spec_sha1 = + { +- GCRY_MD_SHA1, {0, 1}, ++ GCRY_MD_SHA1, {0, 0}, + "SHA1", asn, DIM (asn), oid_spec_sha1, 20, + sha1_init, _gcry_md_block_write, sha1_final, sha1_read, NULL, + _gcry_sha1_hash_buffers, +Index: libgcrypt-1.11.0/src/gcrypt.h.in +=================================================================== +--- libgcrypt-1.11.0.orig/src/gcrypt.h.in ++++ libgcrypt-1.11.0/src/gcrypt.h.in +@@ -1982,6 +1982,7 @@ char *gcry_get_config (int mode, const c + #define GCRY_FIPS_FLAG_REJECT_PK_GOST_SM2 (1 << 7) + #define GCRY_FIPS_FLAG_REJECT_CIPHER_MODE (1 << 8) + /**/ ++#define GCRY_FIPS_FLAG_REJECT_MD_SHA1 (1 << 9) + #define GCRY_FIPS_FLAG_REJECT_PK_ECC_K (1 << 10) + #define GCRY_FIPS_FLAG_REJECT_PK_FLAGS (1 << 11) + +Index: libgcrypt-1.11.0/tests/t-fips-service-ind.c +=================================================================== +--- libgcrypt-1.11.0.orig/tests/t-fips-service-ind.c ++++ libgcrypt-1.11.0/tests/t-fips-service-ind.c +@@ -1107,7 +1107,7 @@ check_mac_o_w_r_c (int reject) + #if USE_SHA1 + { GCRY_MAC_HMAC_SHA1, "hmac input abc", 14, "hmac key input", 14, + "\xc9\x62\x9d\x16\x0f\xc2\xc4\xcd\x38\xac\x3a\x00\xdc\x29\x61\x03" +- "\x69\x50\xd7\x3a" }, ++ "\x69\x50\xd7\x3a", 1 }, + #endif + { GCRY_MAC_HMAC_SHA256, "hmac input abc", 14, "hmac key input", 14, + "\x6a\xda\x4d\xd5\xf3\xa7\x32\x9d\xd2\x55\xc0\x7f\xe6\x0a\x93\xb8" +@@ -1264,7 +1264,7 @@ check_md_o_w_r_c (int reject) + #if USE_SHA1 + { GCRY_MD_SHA1, "abc", 3, + "\xA9\x99\x3E\x36\x47\x06\x81\x6A\xBA\x3E" +- "\x25\x71\x78\x50\xC2\x6C\x9C\xD0\xD8\x9D" }, ++ "\x25\x71\x78\x50\xC2\x6C\x9C\xD0\xD8\x9D", 1 }, + #endif + { GCRY_MD_SHA256, "abc", 3, + "\xba\x78\x16\xbf\x8f\x01\xcf\xea\x41\x41\x40\xde\x5d\xae\x22\x23" +@@ -1389,7 +1389,7 @@ check_digests (void) + #endif + { GCRY_MD_SHA1, "abc", 3, + "\xA9\x99\x3E\x36\x47\x06\x81\x6A\xBA\x3E" +- "\x25\x71\x78\x50\xC2\x6C\x9C\xD0\xD8\x9D" }, ++ "\x25\x71\x78\x50\xC2\x6C\x9C\xD0\xD8\x9D", 1 }, + { GCRY_MD_SHA256, "abc", 3, + "\xba\x78\x16\xbf\x8f\x01\xcf\xea\x41\x41\x40\xde\x5d\xae\x22\x23" + "\xb0\x03\x61\xa3\x96\x17\x7a\x9c\xb4\x10\xff\x61\xf2\x00\x15\xad" }, +@@ -1701,6 +1701,7 @@ main (int argc, char **argv) + | GCRY_FIPS_FLAG_REJECT_CIPHER_MODE + | GCRY_FIPS_FLAG_REJECT_PK_MD + | GCRY_FIPS_FLAG_REJECT_PK_GOST_SM2 ++ | GCRY_FIPS_FLAG_REJECT_MD_SHA1 + | GCRY_FIPS_FLAG_REJECT_PK_ECC_K + | GCRY_FIPS_FLAG_REJECT_PK_FLAGS + | GCRY_FIPS_FLAG_REJECT_COMPAT110))); diff --git a/libgcrypt-md-Use-check_digest_algo_spec-in-_gcry_md_selftest.patch b/libgcrypt-md-Use-check_digest_algo_spec-in-_gcry_md_selftest.patch new file mode 100644 index 0000000..75489df --- /dev/null +++ b/libgcrypt-md-Use-check_digest_algo_spec-in-_gcry_md_selftest.patch @@ -0,0 +1,74 @@ +From ce4755d5c5500cede6d7d380fdab2d15f5d77796 Mon Sep 17 00:00:00 2001 +From: NIIBE Yutaka +Date: Wed, 26 Feb 2025 10:23:28 +0900 +Subject: [PATCH 2/4] md: Use check_digest_algo_spec in _gcry_md_selftest. +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* cipher/md.c (check_digest_algo_spec): New. +(check_digest_algo): Use check_digest_algo_spec. +(_gcry_md_selftest): Likewise. + +-- + +GnuPG-bug-id: 7338 +Signed-off-by: NIIBE Yutaka +Signed-off-by: Lucas Mülling +--- + cipher/md.c | 22 +++++++++++++--------- + 1 file changed, 13 insertions(+), 9 deletions(-) + +diff --git a/cipher/md.c b/cipher/md.c +index caf33afc..a8027e9e 100644 +--- a/cipher/md.c ++++ b/cipher/md.c +@@ -436,15 +436,10 @@ _gcry_md_algo_name (int algorithm) + + + static gcry_err_code_t +-check_digest_algo (int algo) ++check_digest_algo_spec (int algo, const gcry_md_spec_t *spec) + { +- const gcry_md_spec_t *spec; + int reject = 0; + +- spec = spec_from_algo (algo); +- if (!spec) +- return GPG_ERR_DIGEST_ALGO; +- + if (spec->flags.disabled) + return GPG_ERR_DIGEST_ALGO; + +@@ -466,6 +461,17 @@ check_digest_algo (int algo) + return 0; + } + ++static gcry_err_code_t ++check_digest_algo (int algo) ++{ ++ const gcry_md_spec_t *spec = spec_from_algo (algo); ++ ++ if (!spec) ++ return GPG_ERR_DIGEST_ALGO; ++ else ++ return check_digest_algo_spec (algo, spec); ++} ++ + + /**************** + * Open a message digest handle for use with algorithm ALGO. +@@ -1808,9 +1814,7 @@ _gcry_md_selftest (int algo, int extended, selftest_report_func_t report) + const gcry_md_spec_t *spec; + + spec = spec_from_algo (algo); +- if (spec && !spec->flags.disabled +- && (spec->flags.fips || !fips_mode ()) +- && spec->selftest) ++ if (spec && !check_digest_algo_spec (algo, spec) && spec->selftest) + ec = spec->selftest (algo, extended, report); + else + { +-- +2.49.0 + diff --git a/libgcrypt-no-deprecated-grep-alias.patch b/libgcrypt-no-deprecated-grep-alias.patch new file mode 100644 index 0000000..ba0dde8 --- /dev/null +++ b/libgcrypt-no-deprecated-grep-alias.patch @@ -0,0 +1,35 @@ +--- libgcrypt-1.10.3.orig/acinclude.m4 ++++ libgcrypt-1.10.3/acinclude.m4 +@@ -130,10 +130,10 @@ EOF + ac_nlist=conftest.nm + if AC_TRY_EVAL(NM conftest.$ac_objext \| $lt_cv_sys_global_symbol_pipe \| cut -d \' \' -f 2 \> $ac_nlist) && test -s "$ac_nlist"; then + # See whether the symbols have a leading underscore. +- if egrep '^_nm_test_func' "$ac_nlist" >/dev/null; then ++ if grep -E '^_nm_test_func' "$ac_nlist" >/dev/null; then + ac_cv_sys_symbol_underscore=yes + else +- if egrep '^nm_test_func ' "$ac_nlist" >/dev/null; then ++ if grep -E '^nm_test_func ' "$ac_nlist" >/dev/null; then + : + else + echo "configure: cannot find nm_test_func in $ac_nlist" >&AS_MESSAGE_LOG_FD +--- libgcrypt-1.10.3.orig/src/libgcrypt-config.in ++++ libgcrypt-1.10.3/src/libgcrypt-config.in +@@ -154,7 +154,7 @@ if test "$echo_cflags" = "yes"; then + + tmp="" + for i in $includes $cflags_final; do +- if echo "$tmp" | fgrep -v -- "$i" >/dev/null; then ++ if echo "$tmp" | @GREP@ -F -v -- "$i" >/dev/null; then + tmp="$tmp $i" + fi + done +@@ -175,7 +175,7 @@ if test "$echo_libs" = "yes"; then + + tmp="" + for i in $libdirs $libs_final; do +- if echo "$tmp" | fgrep -v -- "$i" >/dev/null; then ++ if echo "$tmp" | @GREP@ -F -v -- "$i" >/dev/null; then + tmp="$tmp $i" + fi + done diff --git a/libgcrypt-nobetasuffix.patch b/libgcrypt-nobetasuffix.patch new file mode 100644 index 0000000..3d4593a --- /dev/null +++ b/libgcrypt-nobetasuffix.patch @@ -0,0 +1,24 @@ +Index: libgcrypt-1.10.2/autogen.sh +=================================================================== +--- libgcrypt-1.10.2.orig/autogen.sh ++++ libgcrypt-1.10.2/autogen.sh +@@ -249,7 +249,7 @@ if [ "$myhost" = "find-version" ]; then + fi + + beta=no +- if [ -e .git ]; then ++ if false; then + ingit=yes + tmp=$(git describe --match "${matchstr1}" --long 2>/dev/null) + tmp=$(echo "$tmp" | sed s/^"$package"//) +@@ -265,8 +265,8 @@ if [ "$myhost" = "find-version" ]; then + rvd=$((0x$(echo ${rev} | dd bs=1 count=4 2>/dev/null))) + else + ingit=no +- beta=yes +- tmp="-unknown" ++ beta=no ++ tmp="" + rev="0000000" + rvd="0" + fi diff --git a/libgcrypt-ppc-enable-P10-assembly-with-ENABLE_FORCE_SOF.patch b/libgcrypt-ppc-enable-P10-assembly-with-ENABLE_FORCE_SOF.patch new file mode 100644 index 0000000..8ef3197 --- /dev/null +++ b/libgcrypt-ppc-enable-P10-assembly-with-ENABLE_FORCE_SOF.patch @@ -0,0 +1,76 @@ +commit 2c5e5ab6843d747c4b877d2c6f47226f61e9ff14 +Author: Jussi Kivilinna +Date: Sun Jun 12 21:51:34 2022 +0300 + + ppc enable P10 assembly with ENABLE_FORCE_SOFT_HWFEATURES on arch 3.00 + + * cipher/chacha20.c (chacha20_do_setkey) [USE_PPC_VEC]: Enable + P10 assembly for HWF_PPC_ARCH_3_00 if ENABLE_FORCE_SOFT_HWFEATURES is + defined. + * cipher/poly1305.c (poly1305_init) [POLY1305_USE_PPC_VEC]: Likewise. + * cipher/rijndael.c (do_setkey) [USE_PPC_CRYPTO_WITH_PPC9LE]: Likewise. + --- + + This change allows testing P10 implementations with P9 and with QEMU-PPC. + + GnuPG-bug-id: 6006 + Signed-off-by: Jussi Kivilinna + +Index: libgcrypt-1.10.2/cipher/chacha20.c +=================================================================== +--- libgcrypt-1.10.2.orig/cipher/chacha20.c ++++ libgcrypt-1.10.2/cipher/chacha20.c +@@ -484,6 +484,11 @@ chacha20_do_setkey (CHACHA20_context_t * + ctx->use_ppc = (features & HWF_PPC_ARCH_2_07) != 0; + # ifndef WORDS_BIGENDIAN + ctx->use_p10 = (features & HWF_PPC_ARCH_3_10) != 0; ++# ifdef ENABLE_FORCE_SOFT_HWFEATURES ++ /* HWF_PPC_ARCH_3_10 above is used as soft HW-feature indicator for P10. ++ * Actual implementation works with HWF_PPC_ARCH_3_00 also. */ ++ ctx->use_p10 |= (features & HWF_PPC_ARCH_3_00) != 0; ++# endif + # endif + #endif + #ifdef USE_S390X_VX +Index: libgcrypt-1.10.2/cipher/poly1305.c +=================================================================== +--- libgcrypt-1.10.2.orig/cipher/poly1305.c ++++ libgcrypt-1.10.2/cipher/poly1305.c +@@ -90,11 +90,19 @@ static void poly1305_init (poly1305_cont + const byte key[POLY1305_KEYLEN]) + { + POLY1305_STATE *st = &ctx->state; ++ unsigned int features = _gcry_get_hw_features (); + + #ifdef POLY1305_USE_PPC_VEC +- ctx->use_p10 = (_gcry_get_hw_features () & HWF_PPC_ARCH_3_10) != 0; ++ ctx->use_p10 = (features & HWF_PPC_ARCH_3_10) != 0; ++# ifdef ENABLE_FORCE_SOFT_HWFEATURES ++ /* HWF_PPC_ARCH_3_10 above is used as soft HW-feature indicator for P10. ++ * Actual implementation works with HWF_PPC_ARCH_3_00 also. */ ++ ctx->use_p10 |= (features & HWF_PPC_ARCH_3_00) != 0; ++# endif + #endif + ++ (void)features; ++ + ctx->leftover = 0; + + st->h[0] = 0; +Index: libgcrypt-1.10.2/cipher/rijndael.c +=================================================================== +--- libgcrypt-1.10.2.orig/cipher/rijndael.c ++++ libgcrypt-1.10.2/cipher/rijndael.c +@@ -605,6 +605,12 @@ do_setkey (RIJNDAEL_context *ctx, const + bulk_ops->xts_crypt = _gcry_aes_ppc9le_xts_crypt; + if (hwfeatures & HWF_PPC_ARCH_3_10) /* for P10 */ + bulk_ops->gcm_crypt = _gcry_aes_p10le_gcm_crypt; ++# ifdef ENABLE_FORCE_SOFT_HWFEATURES ++ /* HWF_PPC_ARCH_3_10 above is used as soft HW-feature indicator for P10. ++ * Actual implementation works with HWF_PPC_ARCH_3_00 also. */ ++ if (hwfeatures & HWF_PPC_ARCH_3_00) ++ bulk_ops->gcm_crypt = _gcry_aes_p10le_gcm_crypt; ++# endif + } + #endif + #ifdef USE_PPC_CRYPTO diff --git a/libgcrypt-rol64-redefinition.patch b/libgcrypt-rol64-redefinition.patch new file mode 100644 index 0000000..bb76b2f --- /dev/null +++ b/libgcrypt-rol64-redefinition.patch @@ -0,0 +1,16 @@ +Index: libgcrypt-1.11.0/cipher/bithelp.h +=================================================================== +--- libgcrypt-1.11.0.orig/cipher/bithelp.h ++++ libgcrypt-1.11.0/cipher/bithelp.h +@@ -35,11 +35,6 @@ static inline u32 ror(u32 x, int n) + return ( (x >> (n&(32-1))) | (x << ((32-n)&(32-1))) ); + } + +-static inline u64 rol64(u64 x, int n) +-{ +- return ( (x << (n&(64-1))) | (x >> ((64-n)&(64-1))) ); +-} +- + /* Byte swap for 32-bit and 64-bit integers. If available, use compiler + provided helpers. */ + #ifdef HAVE_BUILTIN_BSWAP32 diff --git a/libgcrypt-tests-Add-more-tests-to-tests-t-fips-service-ind.patch b/libgcrypt-tests-Add-more-tests-to-tests-t-fips-service-ind.patch new file mode 100644 index 0000000..c0058d2 --- /dev/null +++ b/libgcrypt-tests-Add-more-tests-to-tests-t-fips-service-ind.patch @@ -0,0 +1,382 @@ +From d71c88f78a4f1b72f92de90791fc6fe81a3cb861 Mon Sep 17 00:00:00 2001 +From: NIIBE Yutaka +Date: Tue, 24 Dec 2024 17:03:48 +0900 +Subject: [PATCH 17/19] tests: Add more tests to tests/t-fips-service-ind. +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* tests/t-fips-service-ind.c (check_pk_g_t_n_c, check_pk_s_v): New. +(main): Call check_pk_g_t_n_c and check_pk_s_v. + +-- + +GnuPG-bug-id: 7338 +Signed-off-by: NIIBE Yutaka +Signed-off-by: Lucas Mülling +--- + tests/t-fips-service-ind.c | 334 +++++++++++++++++++++++++++++++++++++ + 1 file changed, 334 insertions(+) + +diff --git a/tests/t-fips-service-ind.c b/tests/t-fips-service-ind.c +index 64e1e135..90d92c70 100644 +--- a/tests/t-fips-service-ind.c ++++ b/tests/t-fips-service-ind.c +@@ -40,6 +40,336 @@ static int in_fips_mode; + # include + #endif + ++/* Check gcry_pk_genkey, gcry_pk_testkey, gcry_pk_get_nbits, gcry_pk_get_curve API. */ ++static void ++check_pk_g_t_n_c (int reject) ++{ ++ static struct { ++ const char *keyparms; ++ int expect_failure; ++ } tv[] = { ++ { ++ "(genkey (ecc (curve nistp256)))", ++ 0 ++ }, ++ { /* non-compliant curve */ ++ "(genkey (ecc (curve secp256k1)))", ++ 1 ++ } ++ }; ++ int tvidx; ++ gpg_error_t err; ++ gpg_err_code_t ec; ++ ++ for (tvidx=0; tvidx < DIM(tv); tvidx++) ++ { ++ gcry_sexp_t s_kp = NULL; ++ gcry_sexp_t s_sk = NULL; ++ int nbits; ++ const char *name; ++ ++ if (verbose) ++ info ("checking gcry_pk_{genkey,testkey,get_nbits,get_curve} test %d\n", tvidx); ++ ++ err = gcry_sexp_build (&s_kp, NULL, tv[tvidx].keyparms); ++ if (err) ++ { ++ fail ("error building SEXP for test, %s: %s", ++ "keyparms", gpg_strerror (err)); ++ goto next; ++ } ++ ++ err = gcry_pk_genkey (&s_sk, s_kp); ++ if (err) ++ { ++ if (in_fips_mode && reject && tv[tvidx].expect_failure) ++ /* Here, an error is expected */ ++ ; ++ else ++ fail ("gcry_pk_genkey failed: %s", gpg_strerror (err)); ++ goto next; ++ } ++ else ++ { ++ if (in_fips_mode && reject && tv[tvidx].expect_failure) ++ { ++ fail ("gcry_pk_genkey test %d unexpectedly succeeded", tvidx); ++ goto next; ++ } ++ } ++ ++ ec = gcry_get_fips_service_indicator (); ++ if (ec == GPG_ERR_INV_OP) ++ { ++ /* libgcrypt is old, no support of the FIPS service indicator. */ ++ fail ("gcry_pk_genkey test %d unexpectedly failed to check the FIPS service indicator.\n", ++ tvidx); ++ goto next; ++ } ++ ++ if (in_fips_mode && !tv[tvidx].expect_failure && ec) ++ { ++ /* Success with the FIPS service indicator == 0 expected, but != 0. */ ++ fail ("gcry_pk_genkey test %d unexpectedly set the indicator in FIPS mode.\n", ++ tvidx); ++ goto next; ++ } ++ else if (in_fips_mode && tv[tvidx].expect_failure && !ec) ++ { ++ /* Success with the FIPS service indicator != 0 expected, but == 0. */ ++ fail ("gcry_pk_genkey test %d unexpectedly cleared the indicator in FIPS mode.\n", ++ tvidx); ++ goto next; ++ } ++ ++ err = gcry_pk_testkey (s_sk); ++ if (err) ++ { ++ fail ("gcry_pk_testkey failed for test: %s", gpg_strerror (err)); ++ goto next; ++ } ++ ++ ec = gcry_get_fips_service_indicator (); ++ if (ec == GPG_ERR_INV_OP) ++ { ++ /* libgcrypt is old, no support of the FIPS service indicator. */ ++ fail ("gcry_pk_testkey test %d unexpectedly failed to check the FIPS service indicator.\n", ++ tvidx); ++ goto next; ++ } ++ ++ if (in_fips_mode && !tv[tvidx].expect_failure && ec) ++ { ++ /* Success with the FIPS service indicator == 0 expected, but != 0. */ ++ fail ("gcry_pk_testkey test %d unexpectedly set the indicator in FIPS mode.\n", ++ tvidx); ++ goto next; ++ } ++ else if (in_fips_mode && tv[tvidx].expect_failure && !ec) ++ { ++ /* Success with the FIPS service indicator != 0 expected, but == 0. */ ++ fail ("gcry_pk_testkey test %d unexpectedly cleared the indicator in FIPS mode.\n", ++ tvidx); ++ goto next; ++ } ++ ++ nbits = gcry_pk_get_nbits (s_sk); ++ if (!nbits) ++ { ++ fail ("gcry_pk_get_nbits failed for test"); ++ goto next; ++ } ++ ++ ec = gcry_get_fips_service_indicator (); ++ if (ec == GPG_ERR_INV_OP) ++ { ++ /* libgcrypt is old, no support of the FIPS service indicator. */ ++ fail ("gcry_pk_get_nbits test %d unexpectedly failed to check the FIPS service indicator.\n", ++ tvidx); ++ goto next; ++ } ++ ++ if (in_fips_mode && !tv[tvidx].expect_failure && ec) ++ { ++ /* Success with the FIPS service indicator == 0 expected, but != 0. */ ++ fail ("gcry_pk_get_nbits test %d unexpectedly set the indicator in FIPS mode.\n", ++ tvidx); ++ goto next; ++ } ++ else if (in_fips_mode && tv[tvidx].expect_failure && !ec) ++ { ++ /* Success with the FIPS service indicator != 0 expected, but == 0. */ ++ fail ("gcry_pk_get_nbits test %d unexpectedly cleared the indicator in FIPS mode.\n", ++ tvidx); ++ goto next; ++ } ++ ++ name = gcry_pk_get_curve (s_sk, 0, NULL); ++ if (!name) ++ { ++ fail ("gcry_pk_get_curve failed for test: %s", gpg_strerror (err)); ++ goto next; ++ } ++ ++ ec = gcry_get_fips_service_indicator (); ++ if (ec == GPG_ERR_INV_OP) ++ { ++ /* libgcrypt is old, no support of the FIPS service indicator. */ ++ fail ("gcry_pk_get_curve test %d unexpectedly failed to check the FIPS service indicator.\n", ++ tvidx); ++ goto next; ++ } ++ ++ if (in_fips_mode && !tv[tvidx].expect_failure && ec) ++ { ++ /* Success with the FIPS service indicator == 0 expected, but != 0. */ ++ fail ("gcry_pk_get_curve test %d unexpectedly set the indicator in FIPS mode.\n", ++ tvidx); ++ goto next; ++ } ++ else if (in_fips_mode && tv[tvidx].expect_failure && !ec) ++ { ++ /* Success with the FIPS service indicator != 0 expected, but == 0. */ ++ fail ("gcry_pk_get_curve test %d unexpectedly cleared the indicator in FIPS mode.\n", ++ tvidx); ++ goto next; ++ } ++ ++ next: ++ gcry_sexp_release (s_kp); ++ gcry_sexp_release (s_sk); ++ } ++} ++ ++/* Check gcry_pk_sign, gcry_verify API. */ ++static void ++check_pk_s_v (int reject) ++{ ++ static struct { ++ const char *prvkey; ++ const char *pubkey; ++ int expect_failure; ++ } tv[] = { ++ { ++ "(private-key (ecc (curve nistp256)" ++ " (d #519b423d715f8b581f4fa8ee59f4771a5b44c8130b4e3eacca54a56dda72b464#)))", ++ "(public-key (ecc (curve nistp256)" ++ " (q #041ccbe91c075fc7f4f033bfa248db8fccd3565de94bbfb12f3c59ff46c271bf83" ++ "ce4014c68811f9a21a1fdb2c0e6113e06db7ca93b7404e78dc7ccd5ca89a4ca9#)))", ++ 0 ++ }, ++ { /* non-compliant curve */ ++ "(private-key (ecc (curve secp256k1)" ++ " (d #c2cdf0a8b0a83b35ace53f097b5e6e6a0a1f2d40535eff1cf434f52a43d59d8f#)))", ++ "(public-key (ecc (curve secp256k1)" ++ " (q #046fcc37ea5e9e09fec6c83e5fbd7a745e3eee81d16ebd861c9e66f55518c19798" ++ "4e9f113c07f875691df8afc1029496fc4cb9509b39dcd38f251a83359cc8b4f7#)))", ++ 1 ++ } ++ }; ++ int tvidx; ++ gpg_error_t err; ++ gpg_err_code_t ec; ++ const char *data = "(data (flags raw)" ++ "(hash sha256 #00112233445566778899AABBCCDDEEFF000102030405060708090A0B0C0D0E0F#))"; ++ gcry_sexp_t s_data = NULL; ++ ++ err = gcry_sexp_build (&s_data, NULL, data); ++ if (err) ++ { ++ fail ("error building SEXP for test, %s: %s", ++ "data", gpg_strerror (err)); ++ return; ++ } ++ ++ for (tvidx=0; tvidx < DIM(tv); tvidx++) ++ { ++ gcry_sexp_t s_pk = NULL; ++ gcry_sexp_t s_sk = NULL; ++ gcry_sexp_t s_sig= NULL; ++ ++ if (verbose) ++ info ("checking gcry_pk_{sign,verify} test %d\n", tvidx); ++ ++ err = gcry_sexp_build (&s_sk, NULL, tv[tvidx].prvkey); ++ if (err) ++ { ++ fail ("error building SEXP for test, %s: %s", ++ "sk", gpg_strerror (err)); ++ goto next; ++ } ++ ++ err = gcry_sexp_build (&s_pk, NULL, tv[tvidx].pubkey); ++ if (err) ++ { ++ fail ("error building SEXP for test, %s: %s", ++ "pk", gpg_strerror (err)); ++ goto next; ++ } ++ ++ err = gcry_pk_sign (&s_sig, s_data, s_sk); ++ if (err) ++ { ++ if (in_fips_mode && reject && tv[tvidx].expect_failure) ++ /* Here, an error is expected */ ++ ; ++ else ++ fail ("gcry_pk_sign failed: %s", gpg_strerror (err)); ++ goto next; ++ } ++ else ++ { ++ if (in_fips_mode && reject && tv[tvidx].expect_failure) ++ { ++ fail ("gcry_pk_sign test %d unexpectedly succeeded", tvidx); ++ goto next; ++ } ++ } ++ ++ ec = gcry_get_fips_service_indicator (); ++ if (ec == GPG_ERR_INV_OP) ++ { ++ /* libgcrypt is old, no support of the FIPS service indicator. */ ++ fail ("gcry_pk_sign test %d unexpectedly failed to check the FIPS service indicator.\n", ++ tvidx); ++ goto next; ++ } ++ ++ if (in_fips_mode && !tv[tvidx].expect_failure && ec) ++ { ++ /* Success with the FIPS service indicator == 0 expected, but != 0. */ ++ fail ("gcry_pk_sign test %d unexpectedly set the indicator in FIPS mode.\n", ++ tvidx); ++ goto next; ++ } ++ else if (in_fips_mode && tv[tvidx].expect_failure && !ec) ++ { ++ /* Success with the FIPS service indicator != 0 expected, but == 0. */ ++ fail ("gcry_pk_sign test %d unexpectedly cleared the indicator in FIPS mode.\n", ++ tvidx); ++ goto next; ++ } ++ ++ err = gcry_pk_verify (s_sig, s_data, s_pk); ++ if (err) ++ { ++ fail ("gcry_pk_verify failed for test: %s", gpg_strerror (err)); ++ goto next; ++ } ++ ++ ec = gcry_get_fips_service_indicator (); ++ if (ec == GPG_ERR_INV_OP) ++ { ++ /* libgcrypt is old, no support of the FIPS service indicator. */ ++ fail ("gcry_pk_verify test %d unexpectedly failed to check the FIPS service indicator.\n", ++ tvidx); ++ goto next; ++ } ++ ++ if (in_fips_mode && !tv[tvidx].expect_failure && ec) ++ { ++ /* Success with the FIPS service indicator == 0 expected, but != 0. */ ++ fail ("gcry_pk_verify test %d unexpectedly set the indicator in FIPS mode.\n", ++ tvidx); ++ goto next; ++ } ++ else if (in_fips_mode && tv[tvidx].expect_failure && !ec) ++ { ++ /* Success with the FIPS service indicator != 0 expected, but == 0. */ ++ fail ("gcry_pk_verify test %d unexpectedly cleared the indicator in FIPS mode.\n", ++ tvidx); ++ goto next; ++ } ++ ++ next: ++ gcry_sexp_release (s_sig); ++ gcry_sexp_release (s_pk); ++ gcry_sexp_release (s_sk); ++ } ++ ++ gcry_sexp_release (s_data); ++} ++ + /* Check gcry_pk_hash_sign, gcry_pk_hash_verify API. */ + static void + check_pk_hash_sign_verify (void) +@@ -1126,6 +1456,8 @@ main (int argc, char **argv) + check_mac_o_w_r_c (0); + check_cipher_o_s_e_d_c (0); + check_pk_hash_sign_verify (); ++ check_pk_s_v (0); ++ check_pk_g_t_n_c (0); + + xgcry_control ((GCRYCTL_FIPS_REJECT_NON_FIPS, + (GCRY_FIPS_FLAG_REJECT_MD_MD5 +@@ -1134,6 +1466,8 @@ main (int argc, char **argv) + check_md_o_w_r_c (1); + check_mac_o_w_r_c (1); + check_cipher_o_s_e_d_c (1); ++ check_pk_s_v (1); ++ check_pk_g_t_n_c (1); + + return !!error_count; + } +-- +2.49.0 + diff --git a/libgcrypt-tests-Allow-tests-with-USE_RSA.patch b/libgcrypt-tests-Allow-tests-with-USE_RSA.patch new file mode 100644 index 0000000..cc29fb0 --- /dev/null +++ b/libgcrypt-tests-Allow-tests-with-USE_RSA.patch @@ -0,0 +1,44 @@ +From 8404a048b7c58eb903717e09cffaa7735f7d8520 Mon Sep 17 00:00:00 2001 +From: NIIBE Yutaka +Date: Tue, 4 Mar 2025 13:29:28 +0900 +Subject: [PATCH 01/14] tests: Allow tests with !USE_RSA. +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* tests/t-fips-service-ind.c [USE_RSA] (check_pk_s_v): Ifdef-out. + +-- + +Signed-off-by: NIIBE Yutaka +Signed-off-by: Lucas Mülling +--- + tests/t-fips-service-ind.c | 5 ++++- + 1 file changed, 4 insertions(+), 1 deletion(-) + +diff --git a/tests/t-fips-service-ind.c b/tests/t-fips-service-ind.c +index 99b84c8f..a082b258 100644 +--- a/tests/t-fips-service-ind.c ++++ b/tests/t-fips-service-ind.c +@@ -290,7 +290,9 @@ check_pk_s_v (int reject) + " 00112233445566778899AABBCCDDEEFF000102030405060708090A0B0C0D0E0F" + " 00112233445566778899AABBCCDDEEFF000102030405060708090A0B0C0D0E0F#))", + 0 +- }, ++ } ++#if USE_RSA ++ , + { /* RSA with compliant hash for signing */ + "(private-key" + " (rsa" +@@ -559,6 +561,7 @@ check_pk_s_v (int reject) + " (hash sha1 #11223344556677889900AABBCCDDEEFF10203040#))\n", + 1 + } ++#endif /* USE_RSA */ + }; + int tvidx; + gpg_error_t err; +-- +2.49.0 + diff --git a/libgcrypt-tests-Update-t-fips-service-ind-using-GCRY_MD_SHA256-for-KDF-tests.patch b/libgcrypt-tests-Update-t-fips-service-ind-using-GCRY_MD_SHA256-for-KDF-tests.patch new file mode 100644 index 0000000..dd009fd --- /dev/null +++ b/libgcrypt-tests-Update-t-fips-service-ind-using-GCRY_MD_SHA256-for-KDF-tests.patch @@ -0,0 +1,106 @@ +From e5989e08a556117ec3f19f098765963358b71051 Mon Sep 17 00:00:00 2001 +From: NIIBE Yutaka +Date: Wed, 26 Feb 2025 13:51:36 +0900 +Subject: [PATCH 3/4] tests: Update t-fips-service-ind using GCRY_MD_SHA256 for + KDF tests. +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* tests/t-fips-service-ind.c (check_kdf_derive): Use GCRY_MD_SHA256. + +-- + +GnuPG-bug-id: 7338 +Signed-off-by: NIIBE Yutaka +Signed-off-by: Lucas Mülling +--- + tests/t-fips-service-ind.c | 38 +++++++++++++++++++------------------- + 1 file changed, 19 insertions(+), 19 deletions(-) + +diff --git a/tests/t-fips-service-ind.c b/tests/t-fips-service-ind.c +index bec6c27e..99b84c8f 100644 +--- a/tests/t-fips-service-ind.c ++++ b/tests/t-fips-service-ind.c +@@ -1621,13 +1621,13 @@ check_kdf_derive (void) + } tv[] = { + { + "passwordPASSWORDpassword", 24, +- GCRY_KDF_PBKDF2, GCRY_MD_SHA1, ++ GCRY_KDF_PBKDF2, GCRY_MD_SHA256, + "saltSALTsaltSALTsaltSALTsaltSALTsalt", 36, + 4096, + 25, +- "\x3d\x2e\xec\x4f\xe4\x1c\x84\x9b\x80\xc8" +- "\xd8\x36\x62\xc0\xe4\x4a\x8b\x29\x1a\x96" +- "\x4c\xf2\xf0\x70\x38", ++ "\x34\x8c\x89\xdb\xcb\xd3\x2b\x2f\x32\xd8" ++ "\x14\xb8\x11\x6e\x84\xcf\x2b\x17\x34\x7e" ++ "\xbc\x18\x00\x18\x1c", + 0 + }, + { +@@ -1644,45 +1644,45 @@ check_kdf_derive (void) + }, + { + "passwor", 7, +- GCRY_KDF_PBKDF2, GCRY_MD_SHA1, ++ GCRY_KDF_PBKDF2, GCRY_MD_SHA256, + "saltSALTsaltSALTsaltSALTsaltSALTsalt", 36, + 4096, + 25, +- "\xf4\x93\xee\x2b\xbf\x44\x0b\x9e\x64\x53" +- "\xc2\xb3\x87\xdc\x73\xf8\xfd\xe6\x97\xda" +- "\xb8\x24\xa0\x26\x50", ++ "\x2d\x72\xa9\xe5\x4e\x2f\x37\x6e\xe5\xe4" ++ "\xf5\x55\x76\xb5\xaa\x49\x73\x01\x97\x1c" ++ "\xad\x3a\x7c\xc4\xde", + 1 /* not-compliant because passphrase len is too small */ + }, + { + "passwordPASSWORDpassword", 24, +- GCRY_KDF_PBKDF2, GCRY_MD_SHA1, ++ GCRY_KDF_PBKDF2, GCRY_MD_SHA256, + "saltSALTsaltSAL", 15, + 4096, + 25, +- "\x14\x05\xa4\x2a\xf4\xa8\x12\x14\x7b\x65" +- "\x8f\xaa\xf0\x7f\x25\xe5\x0f\x0b\x2b\xb7" +- "\xcf\x8d\x29\x23\x4b", ++ "\xf7\x55\xdd\x3c\x5e\xfb\x23\x06\xa7\x85" ++ "\x94\xa7\x31\x12\x45\xcf\x5a\x4b\xdc\x09" ++ "\xee\x65\x4b\x50\x3f", + 1 /* not-compliant because salt len is too small */ + }, + { + "passwordPASSWORDpassword", 24, +- GCRY_KDF_PBKDF2, GCRY_MD_SHA1, ++ GCRY_KDF_PBKDF2, GCRY_MD_SHA256, + "saltSALTsaltSALTsaltSALTsaltSALTsalt", 36, + 999, + 25, +- "\xac\xf8\xb4\x67\x41\xc7\xf3\xd1\xa0\xc0" +- "\x08\xbe\x9b\x23\x96\x78\xbd\x93\xda\x4a" +- "\x30\xd4\xfb\xf0\x33", ++ "\x09\x3e\x1a\xd8\x63\x30\x71\x9c\x17\xcf" ++ "\xb0\x53\x3e\x1f\xc8\x51\x29\x71\x54\x28" ++ "\x5d\xf7\x8e\x41\xaa", + 1 /* not-compliant because too few iterations */ + }, + { + "passwordPASSWORDpassword", 24, +- GCRY_KDF_PBKDF2, GCRY_MD_SHA1, ++ GCRY_KDF_PBKDF2, GCRY_MD_SHA256, + "saltSALTsaltSALTsaltSALTsaltSALTsalt", 36, + 4096, + 13, +- "\x3d\x2e\xec\x4f\xe4\x1c\x84\x9b\x80\xc8" +- "\xd8\x36\x62", ++ "\x34\x8c\x89\xdb\xcb\xd3\x2b\x2f\x32\xd8" ++ "\x14\xb8\x11", + 1 /* not-compliant because key size too small */ + }, + { +-- +2.49.0 + diff --git a/libgcrypt-tests-fips-Add-gcry_cipher_open-tests.patch b/libgcrypt-tests-fips-Add-gcry_cipher_open-tests.patch new file mode 100644 index 0000000..0e0f7e5 --- /dev/null +++ b/libgcrypt-tests-fips-Add-gcry_cipher_open-tests.patch @@ -0,0 +1,199 @@ +From cfd2d2f41ad4aef40d83f8f7237d1da13c7e240c Mon Sep 17 00:00:00 2001 +From: NIIBE Yutaka +Date: Tue, 17 Dec 2024 10:33:33 +0900 +Subject: [PATCH 09/19] tests,fips: Add gcry_cipher_open tests. +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* tests/t-fips-service-ind.c (check_cipher_o_s_e_d_c): New. +(main): Call check_cipher_o_s_e_d_c. + +-- + +GnuPG-bug-id: 7338 +Signed-off-by: NIIBE Yutaka +Signed-off-by: Lucas Mülling +--- + tests/t-fips-service-ind.c | 152 ++++++++++++++++++++++++++++++++++++- + 1 file changed, 151 insertions(+), 1 deletion(-) + +Index: libgcrypt-1.11.0/tests/t-fips-service-ind.c +=================================================================== +--- libgcrypt-1.11.0.orig/tests/t-fips-service-ind.c ++++ libgcrypt-1.11.0/tests/t-fips-service-ind.c +@@ -31,6 +31,7 @@ + + #include "t-common.h" + static int in_fips_mode; ++#define MAX_DATA_LEN 1040 + + /* Mingw requires us to include windows.h after winsock2.h which is + included by gcrypt.h. */ +@@ -38,6 +39,154 @@ static int in_fips_mode; + # include + #endif + ++/* Check gcry_cipher_open, gcry_cipher_setkey, gcry_cipher_encrypt, ++ gcry_cipher_decrypt, gcry_cipher_close API. */ ++static void ++check_cipher_o_s_e_d_c (void) ++{ ++ static struct { ++ int algo; ++ const char *key; ++ int keylen; ++ const char *expect; ++ int expect_failure; ++ unsigned int flags; ++ } tv[] = { ++#if USE_DES ++ { GCRY_CIPHER_3DES, ++ "\xe3\x34\x7a\x6b\x0b\xc1\x15\x2c\x64\x2a\x25\xcb\xd3\xbc\x31\xab" ++ "\xfb\xa1\x62\xa8\x1f\x19\x7c\x15", 24, ++ "\x3f\x1a\xb8\x83\x18\x8b\xb5\x97", 1 }, ++ { GCRY_CIPHER_3DES, ++ "\xe3\x34\x7a\x6b\x0b\xc1\x15\x2c\x64\x2a\x25\xcb\xd3\xbc\x31\xab" ++ "\xfb\xa1\x62\xa8\x1f\x19\x7c\x15", 24, ++ "\x3f\x1a\xb8\x83\x18\x8b\xb5\x97", ++ 1, GCRY_CIPHER_FLAG_REJECT_NON_FIPS }, ++#endif ++ { GCRY_CIPHER_AES, ++ "\x2b\x7e\x15\x16\x28\xae\xd2\xa6\xab\xf7\x15\x88\x09\xcf\x4f\x3c", 16, ++ "\x5c\x71\xd8\x5d\x26\x5e\xcd\xb5\x95\x40\x41\xab\xff\x25\x6f\xd1" } ++ }; ++ const char *pt = "Shohei Ohtani 2024: 54 HR, 59 SB"; ++ int ptlen; ++ int tvidx; ++ unsigned char out[MAX_DATA_LEN]; ++ gpg_error_t err; ++ ++ ptlen = strlen (pt); ++ assert (ptlen == 32); ++ for (tvidx=0; tvidx < DIM(tv); tvidx++) ++ { ++ gpg_err_code_t ec; ++ gcry_cipher_hd_t h; ++ size_t blklen; ++ ++ if (verbose) ++ fprintf (stderr, "checking gcry_cipher_open test %d\n", ++ tvidx); ++ ++ blklen = gcry_cipher_get_algo_blklen (tv[tvidx].algo); ++ assert (blklen != 0); ++ assert (blklen <= ptlen); ++ assert (blklen <= DIM (out)); ++ err = gcry_cipher_open (&h, tv[tvidx].algo, GCRY_CIPHER_MODE_ECB, ++ tv[tvidx].flags); ++ if (err) ++ { ++ if (in_fips_mode && (tv[tvidx].flags & GCRY_CIPHER_FLAG_REJECT_NON_FIPS) ++ && tv[tvidx].expect_failure) ++ /* Here, an error is expected */ ++ ; ++ else ++ fail ("gcry_cipher_open test %d unexpectedly failed: %s\n", ++ tvidx, gpg_strerror (err)); ++ continue; ++ } ++ else ++ { ++ if (in_fips_mode && (tv[tvidx].flags & GCRY_CIPHER_FLAG_REJECT_NON_FIPS) ++ && tv[tvidx].expect_failure) ++ /* This case, an error is expected, but we observed success */ ++ fail ("gcry_cipher_open test %d unexpectedly succeeded\n", tvidx); ++ } ++ ++ ec = gcry_get_fips_service_indicator (); ++ if (ec == GPG_ERR_INV_OP) ++ { ++ /* libgcrypt is old, no support of the FIPS service indicator. */ ++ fail ("gcry_cipher_open test %d unexpectedly failed to check the FIPS service indicator.\n", ++ tvidx); ++ continue; ++ } ++ ++ if (in_fips_mode && !tv[tvidx].expect_failure && ec) ++ { ++ /* Success with the FIPS service indicator == 0 expected, but != 0. */ ++ fail ("gcry_cipher_open test %d unexpectedly set the indicator in FIPS mode.\n", ++ tvidx); ++ continue; ++ } ++ else if (in_fips_mode && tv[tvidx].expect_failure && !ec) ++ { ++ /* Success with the FIPS service indicator != 0 expected, but == 0. */ ++ fail ("gcry_cipher_open test %d unexpectedly cleared the indicator in FIPS mode.\n", ++ tvidx); ++ continue; ++ } ++ ++ err = gcry_cipher_setkey (h, tv[tvidx].key, tv[tvidx].keylen); ++ if (err) ++ { ++ fail ("gcry_cipher_setkey %d failed: %s\n", tvidx, ++ gpg_strerror (err)); ++ gcry_cipher_close (h); ++ continue; ++ } ++ ++ err = gcry_cipher_encrypt (h, out, MAX_DATA_LEN, pt, blklen); ++ if (err) ++ { ++ fail ("gcry_cipher_encrypt %d failed: %s\n", tvidx, ++ gpg_strerror (err)); ++ gcry_cipher_close (h); ++ continue; ++ } ++ ++ if (memcmp (out, tv[tvidx].expect, blklen)) ++ { ++ int i; ++ ++ fail ("gcry_cipher_open test %d failed: encryption mismatch\n", tvidx); ++ fputs ("got:", stderr); ++ for (i=0; i < blklen; i++) ++ fprintf (stderr, " %02x", out[i]); ++ putc ('\n', stderr); ++ } ++ ++ err = gcry_cipher_decrypt (h, out, blklen, NULL, 0); ++ if (err) ++ { ++ fail ("gcry_cipher_decrypt %d failed: %s\n", tvidx, ++ gpg_strerror (err)); ++ gcry_cipher_close (h); ++ continue; ++ } ++ ++ if (memcmp (out, pt, blklen)) ++ { ++ int i; ++ ++ fail ("gcry_cipher_open test %d failed: decryption mismatch\n", tvidx); ++ fputs ("got:", stderr); ++ for (i=0; i < blklen; i++) ++ fprintf (stderr, " %02x", out[i]); ++ putc ('\n', stderr); ++ } ++ ++ gcry_cipher_close (h); ++ } ++} ++ + /* Check gcry_mac_open, gcry_mac_write, gcry_mac_write, gcry_mac_read, + gcry_mac_close API. */ + static void +@@ -651,9 +800,10 @@ main (int argc, char **argv) + xgcry_control ((GCRYCTL_SET_DEBUG_FLAGS, 1u , 0)); + + check_digests (); ++ check_kdf_derive (); + check_md_o_w_r_c (); + check_mac_o_w_r_c (); +- check_kdf_derive (); ++ check_cipher_o_s_e_d_c (); + + return !!error_count; + } diff --git a/libgcrypt-tests-fips-Add-gcry_mac_open-tests.patch b/libgcrypt-tests-fips-Add-gcry_mac_open-tests.patch new file mode 100644 index 0000000..c2e3ed4 --- /dev/null +++ b/libgcrypt-tests-fips-Add-gcry_mac_open-tests.patch @@ -0,0 +1,206 @@ +From c4f75014cb8af732f87c02fe7c2e7a488fe71c6d Mon Sep 17 00:00:00 2001 +From: NIIBE Yutaka +Date: Mon, 16 Dec 2024 14:09:10 +0900 +Subject: [PATCH 06/19] tests,fips: Add gcry_mac_open tests. +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* tests/t-digest.c (check_mac_o_w_r_c): New. +(main): Call check_mac_o_w_r_c. + +-- + +GnuPG-bug-id: 7338 +Signed-off-by: NIIBE Yutaka +Signed-off-by: Lucas Mülling +--- + tests/t-digest.c | 168 +++++++++++++++++++++++++++++++++++++++++++++++ + 1 file changed, 168 insertions(+) + +Index: libgcrypt-1.11.0/tests/t-digest.c +=================================================================== +--- libgcrypt-1.11.0.orig/tests/t-digest.c ++++ libgcrypt-1.11.0/tests/t-digest.c +@@ -38,6 +38,173 @@ static int in_fips_mode; + # include + #endif + ++/* Check gcry_mac_open, gcry_mac_write, gcry_mac_write, gcry_mac_read, ++ gcry_mac_close API. */ ++static void ++check_mac_o_w_r_c (void) ++{ ++ static struct { ++ int algo; ++ const char *data; ++ int datalen; ++ const char *key; ++ int keylen; ++ const char *expect; ++ int expect_failure; ++ unsigned int flags; ++ } tv[] = { ++#if USE_MD5 ++ { GCRY_MAC_HMAC_MD5, "hmac input abc", 14, "hmac key input", 14, ++ "\x0d\x72\xd0\x60\xaf\x34\xf2\xca\x33\x58\xa9\xcc\xd3\x5a\xac\xb5", 1 }, ++ { GCRY_MAC_HMAC_MD5, "hmac input abc", 14, "hmac key input", 14, ++ "\x0d\x72\xd0\x60\xaf\x34\xf2\xca\x33\x58\xa9\xcc\xd3\x5a\xac\xb5", 1, ++ GCRY_MAC_FLAG_REJECT_NON_FIPS }, ++#endif ++#if USE_SHA1 ++ { GCRY_MAC_HMAC_SHA1, "hmac input abc", 14, "hmac key input", 14, ++ "\xc9\x62\x9d\x16\x0f\xc2\xc4\xcd\x38\xac\x3a\x00\xdc\x29\x61\x03" ++ "\x69\x50\xd7\x3a" }, ++#endif ++ { GCRY_MAC_HMAC_SHA256, "hmac input abc", 14, "hmac key input", 14, ++ "\x6a\xda\x4d\xd5\xf3\xa7\x32\x9d\xd2\x55\xc0\x7f\xe6\x0a\x93\xb8" ++ "\x7a\x6e\x76\x68\x46\x34\x67\xf9\xc2\x29\xb8\x24\x2e\xc8\xe3\xb4" }, ++ { GCRY_MAC_HMAC_SHA384, "hmac input abc", 14, "hmac key input", 14, ++ "\xc6\x59\x14\x4a\xac\x4d\xd5\x62\x09\x2c\xbd\x5e\xbf\x41\x94\xf9" ++ "\xa4\x78\x18\x46\xfa\xd6\xd1\x12\x90\x4f\x65\xd4\xe8\x44\xcc\xcc" ++ "\x3d\xcc\xf3\xe4\x27\xd8\xf0\xff\x01\xe8\x70\xcd\xfb\xfa\x24\x45" }, ++ { GCRY_MAC_HMAC_SHA512, "hmac input abc", 14, "hmac key input", 14, ++ "\xfa\x77\x49\x49\x24\x3d\x7e\x03\x1b\x0e\xd1\xfc\x20\x81\xcf\x95" ++ "\x81\x21\xa4\x4f\x3b\xe5\x69\x9a\xe6\x67\x27\x10\xbc\x62\xc7\xb3" ++ "\xb3\xcf\x2b\x1e\xda\x20\x48\x25\xc5\x6a\x52\xc7\xc9\xd9\x77\xf6" ++ "\xf6\x49\x9d\x70\xe6\x04\x33\xab\x6a\xdf\x7e\x9f\xf4\xd1\x59\x6e" }, ++ { GCRY_MAC_HMAC_SHA3_256, "hmac input abc", 14, "hmac key input", 14, ++ "\x2b\xe9\x02\x92\xc2\x37\xbe\x91\x06\xbf\x9c\x8e\x7b\xa3\xf2\xfc" ++ "\x68\x10\x8a\x71\xd5\xc7\x84\x3c\x0b\xdd\x7d\x1e\xdf\xa5\xf6\xa7" }, ++ { GCRY_MAC_HMAC_SHA3_384, "hmac input abc", 14, "hmac key input", 14, ++ "\x9f\x6b\x9f\x49\x95\x57\xed\x33\xb1\xe7\x22\x2f\xda\x40\x68\xb0" ++ "\x28\xd2\xdb\x6f\x73\x3c\x2e\x2b\x29\x51\x64\x53\xc4\xc5\x63\x8a" ++ "\x98\xca\x78\x1a\xe7\x1b\x7d\xf6\xbf\xf3\x6a\xf3\x2a\x0e\xa0\x5b" }, ++ { GCRY_MAC_HMAC_SHA3_512, "hmac input abc", 14, "hmac key input", 14, ++ "\xf3\x19\x70\x54\x25\xdf\x0f\xde\x09\xe9\xea\x3b\x34\x67\x14\x32" ++ "\xe6\xe2\x58\x9d\x76\x38\xa4\xbd\x90\x35\x4c\x07\x7c\xa3\xdb\x23" ++ "\x3c\x78\x0c\x45\xee\x8e\x39\xd5\x81\xd8\x5c\x13\x20\x40\xba\x34" ++ "\xd0\x0b\x75\x31\x38\x4b\xe7\x74\x87\xa9\xc5\x68\x7f\xbc\x19\xa1" } ++#if USE_RMD160 ++ , ++ { GCRY_MAC_HMAC_RMD160, "hmac input abc", 14, "hmac key input", 14, ++ "\xf2\x45\x5c\x7e\x48\x1a\xbb\xe5\xe8\xec\x40\xa4\x1b\x89\x26\x2b" ++ "\xdc\xa1\x79\x59", 1 } ++#endif ++ }; ++ int tvidx; ++ unsigned char mac[64]; ++ int expectlen; ++ gpg_error_t err; ++ size_t buflen; ++ ++ for (tvidx=0; tvidx < DIM(tv); tvidx++) ++ { ++ gpg_err_code_t ec; ++ gcry_mac_hd_t h; ++ ++ if (verbose) ++ fprintf (stderr, "checking gcry_mac_open test %d\n", ++ tvidx); ++ ++ expectlen = gcry_mac_get_algo_maclen (tv[tvidx].algo); ++ assert (expectlen != 0); ++ assert (expectlen <= DIM (mac)); ++ err = gcry_mac_open (&h, tv[tvidx].algo, tv[tvidx].flags, NULL); ++ if (err) ++ { ++ if (in_fips_mode && (tv[tvidx].flags & GCRY_MAC_FLAG_REJECT_NON_FIPS) ++ && tv[tvidx].expect_failure) ++ /* Here, an error is expected */ ++ ; ++ else ++ fail ("gcry_mac_open test %d unexpectedly failed: %s\n", ++ tvidx, gpg_strerror (err)); ++ continue; ++ } ++ else ++ { ++ if (in_fips_mode && (tv[tvidx].flags & GCRY_MAC_FLAG_REJECT_NON_FIPS) ++ && tv[tvidx].expect_failure) ++ /* This case, an error is expected, but we observed success */ ++ fail ("gcry_mac_open test %d unexpectedly succeeded\n", tvidx); ++ } ++ ++ ++ ec = gcry_get_fips_service_indicator (); ++ if (ec == GPG_ERR_INV_OP) ++ { ++ /* libgcrypt is old, no support of the FIPS service indicator. */ ++ fail ("gcry_mac_open test %d unexpectedly failed to check the FIPS service indicator.\n", ++ tvidx); ++ continue; ++ } ++ ++ if (in_fips_mode && !tv[tvidx].expect_failure && ec) ++ { ++ /* Success with the FIPS service indicator == 0 expected, but != 0. */ ++ fail ("gcry_mac_open test %d unexpectedly set the indicator in FIPS mode.\n", ++ tvidx); ++ continue; ++ } ++ else if (in_fips_mode && tv[tvidx].expect_failure && !ec) ++ { ++ /* Success with the FIPS service indicator != 0 expected, but == 0. */ ++ fail ("gcry_mac_open test %d unexpectedly cleared the indicator in FIPS mode.\n", ++ tvidx); ++ continue; ++ } ++ ++ err = gcry_mac_setkey (h, tv[tvidx].key, tv[tvidx].keylen); ++ if (err) ++ { ++ fail ("gcry_mac_setkey test %d unexpectedly failed: %s\n", ++ tvidx, gpg_strerror (err)); ++ gcry_mac_close (h); ++ continue; ++ } ++ ++ err = gcry_mac_write (h, tv[tvidx].data, tv[tvidx].datalen); ++ if (err) ++ { ++ fail ("gcry_mac_write test %d unexpectedly failed: %s\n", ++ tvidx, gpg_strerror (err)); ++ gcry_mac_close (h); ++ continue; ++ } ++ ++ buflen = expectlen; ++ err = gcry_mac_read (h, mac, &buflen); ++ if (err || buflen != expectlen) ++ { ++ fail ("gcry_mac_read test %d unexpectedly failed: %s\n", ++ tvidx, gpg_strerror (err)); ++ gcry_mac_close (h); ++ continue; ++ } ++ ++ if (memcmp (mac, tv[tvidx].expect, expectlen)) ++ { ++ int i; ++ ++ fail ("gcry_mac_open test %d failed: mismatch\n", tvidx); ++ fputs ("got:", stderr); ++ for (i=0; i < expectlen; i++) ++ fprintf (stderr, " %02x", mac[i]); ++ putc ('\n', stderr); ++ } ++ ++ gcry_mac_close (h); ++ } ++} ++ ++ ++/* Check gcry_md_open, gcry_md_write, gcry_md_write, gcry_md_read, ++ gcry_md_close API. */ + static void + check_md_o_w_r_c (void) + { +@@ -327,6 +494,7 @@ main (int argc, char **argv) + + check_digests (); + check_md_o_w_r_c (); ++ check_mac_o_w_r_c (); + + return !!error_count; + } diff --git a/libgcrypt-tests-fips-Move-KDF-tests-to-t-fips-service-ind.patch b/libgcrypt-tests-fips-Move-KDF-tests-to-t-fips-service-ind.patch new file mode 100644 index 0000000..7adbac5 --- /dev/null +++ b/libgcrypt-tests-fips-Move-KDF-tests-to-t-fips-service-ind.patch @@ -0,0 +1,375 @@ +From b59bde31ded9e829e2a53ddb8c533bf35a144972 Mon Sep 17 00:00:00 2001 +From: NIIBE Yutaka +Date: Mon, 16 Dec 2024 14:21:06 +0900 +Subject: [PATCH 08/19] tests,fips: Move KDF tests to t-fips-service-ind. +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* tests/t-fips-service-ind.c (check_kdf_derive): Move from... +* tests/t-kdf.c (check_fips_gcry_kdf_derive): ... here. + +-- + +GnuPG-bug-id: 7338 +Signed-off-by: NIIBE Yutaka +Signed-off-by: Lucas Mülling +--- + tests/t-fips-service-ind.c | 159 +++++++++++++++++++++++++++++++++++++ + tests/t-kdf.c | 159 ------------------------------------- + 2 files changed, 159 insertions(+), 159 deletions(-) + +Index: libgcrypt-1.11.0/tests/t-fips-service-ind.c +=================================================================== +--- libgcrypt-1.11.0.orig/tests/t-fips-service-ind.c ++++ libgcrypt-1.11.0/tests/t-fips-service-ind.c +@@ -439,6 +439,164 @@ check_digests (void) + } + + ++ ++static void ++check_kdf_derive (void) ++{ ++ static struct { ++ const char *p; /* Passphrase. */ ++ size_t plen; /* Length of P. */ ++ int algo; ++ int subalgo; ++ const char *salt; ++ size_t saltlen; ++ unsigned long iterations; ++ int dklen; /* Requested key length. */ ++ const char *dk; /* Derived key. */ ++ int expect_failure; ++ } tv[] = { ++ { ++ "passwordPASSWORDpassword", 24, ++ GCRY_KDF_PBKDF2, GCRY_MD_SHA1, ++ "saltSALTsaltSALTsaltSALTsaltSALTsalt", 36, ++ 4096, ++ 25, ++ "\x3d\x2e\xec\x4f\xe4\x1c\x84\x9b\x80\xc8" ++ "\xd8\x36\x62\xc0\xe4\x4a\x8b\x29\x1a\x96" ++ "\x4c\xf2\xf0\x70\x38", ++ 0 ++ }, ++ { ++ "pleaseletmein", 13, ++ GCRY_KDF_SCRYPT, 16384, ++ "SodiumChloride", 14, ++ 1, ++ 64, ++ "\x70\x23\xbd\xcb\x3a\xfd\x73\x48\x46\x1c\x06\xcd\x81\xfd\x38\xeb" ++ "\xfd\xa8\xfb\xba\x90\x4f\x8e\x3e\xa9\xb5\x43\xf6\x54\x5d\xa1\xf2" ++ "\xd5\x43\x29\x55\x61\x3f\x0f\xcf\x62\xd4\x97\x05\x24\x2a\x9a\xf9" ++ "\xe6\x1e\x85\xdc\x0d\x65\x1e\x40\xdf\xcf\x01\x7b\x45\x57\x58\x87", ++ 1 /* not-compliant because unallowed algo */ ++ }, ++ { ++ "passwor", 7, ++ GCRY_KDF_PBKDF2, GCRY_MD_SHA1, ++ "saltSALTsaltSALTsaltSALTsaltSALTsalt", 36, ++ 4096, ++ 25, ++ "\xf4\x93\xee\x2b\xbf\x44\x0b\x9e\x64\x53" ++ "\xc2\xb3\x87\xdc\x73\xf8\xfd\xe6\x97\xda" ++ "\xb8\x24\xa0\x26\x50", ++ 1 /* not-compliant because passphrase len is too small */ ++ }, ++ { ++ "passwordPASSWORDpassword", 24, ++ GCRY_KDF_PBKDF2, GCRY_MD_SHA1, ++ "saltSALTsaltSAL", 15, ++ 4096, ++ 25, ++ "\x14\x05\xa4\x2a\xf4\xa8\x12\x14\x7b\x65" ++ "\x8f\xaa\xf0\x7f\x25\xe5\x0f\x0b\x2b\xb7" ++ "\xcf\x8d\x29\x23\x4b", ++ 1 /* not-compliant because salt len is too small */ ++ }, ++ { ++ "passwordPASSWORDpassword", 24, ++ GCRY_KDF_PBKDF2, GCRY_MD_SHA1, ++ "saltSALTsaltSALTsaltSALTsaltSALTsalt", 36, ++ 999, ++ 25, ++ "\xac\xf8\xb4\x67\x41\xc7\xf3\xd1\xa0\xc0" ++ "\x08\xbe\x9b\x23\x96\x78\xbd\x93\xda\x4a" ++ "\x30\xd4\xfb\xf0\x33", ++ 1 /* not-compliant because too few iterations */ ++ }, ++ { ++ "passwordPASSWORDpassword", 24, ++ GCRY_KDF_PBKDF2, GCRY_MD_SHA1, ++ "saltSALTsaltSALTsaltSALTsaltSALTsalt", 36, ++ 4096, ++ 13, ++ "\x3d\x2e\xec\x4f\xe4\x1c\x84\x9b\x80\xc8" ++ "\xd8\x36\x62", ++ 1 /* not-compliant because key size too small */ ++ }, ++ { ++ "passwordPASSWORDpassword", 24, ++ GCRY_KDF_PBKDF2, GCRY_MD_BLAKE2B_512, ++ "saltSALTsaltSALTsaltSALTsaltSALTsalt", 36, ++ 4096, ++ 60, ++ "\xa4\x6b\x53\x35\xdb\xdd\xa3\xd2\x5d\x19\xbb\x11\xfe\xdd\xd9\x9e" ++ "\x45\x2a\x7c\x34\x47\x41\x98\xca\x31\x74\xb6\x34\x22\xac\x83\xb0" ++ "\x38\x6e\xf5\x93\x0f\xf5\x16\x46\x0b\x97\xdc\x6c\x27\x5b\xe7\x25" ++ "\xc2\xcb\xec\x50\x02\xc6\x52\x8b\x34\x68\x53\x65", ++ 1 /* not-compliant because subalgo is not the one of approved */ ++ } ++ }; ++ ++ int tvidx; ++ gpg_error_t err; ++ unsigned char outbuf[100]; ++ int i; ++ ++ for (tvidx=0; tvidx < DIM(tv); tvidx++) ++ { ++ if (verbose) ++ fprintf (stderr, "checking gcry_kdf_derive test vector %d algo %d for FIPS\n", ++ tvidx, tv[tvidx].algo); ++ assert (tv[tvidx].dklen <= sizeof outbuf); ++ err = gcry_kdf_derive (tv[tvidx].p, tv[tvidx].plen, ++ tv[tvidx].algo, tv[tvidx].subalgo, ++ tv[tvidx].salt, tv[tvidx].saltlen, ++ tv[tvidx].iterations, tv[tvidx].dklen, outbuf); ++ ++ if (err) ++ { ++ fail ("gcry_kdf_derive test %d unexpectedly returned an error in FIPS mode: %s\n", ++ tvidx, gpg_strerror (err)); ++ } ++ else ++ { ++ gpg_err_code_t ec; ++ ++ ec = gcry_get_fips_service_indicator (); ++ if (ec == GPG_ERR_INV_OP) ++ { ++ /* libgcrypt is old, no support of the FIPS service indicator. */ ++ fail ("gcry_kdf_derive test %d unexpectedly failed to check the FIPS service indicator.\n", ++ tvidx); ++ continue; ++ } ++ ++ if (!tv[tvidx].expect_failure && ec) ++ { ++ /* Success with the FIPS service indicator == 0 expected, but != 0. */ ++ fail ("gcry_kdf_derive test %d unexpectedly set the indicator in FIPS mode.\n", ++ tvidx); ++ continue; ++ } ++ else if (tv[tvidx].expect_failure && !ec && in_fips_mode) ++ { ++ /* Success with the FIPS service indicator != 0 expected, but == 0. */ ++ fail ("gcry_kdf_derive test %d unexpectedly cleared the indicator in FIPS mode.\n", ++ tvidx); ++ continue; ++ } ++ ++ if (memcmp (outbuf, tv[tvidx].dk, tv[tvidx].dklen)) ++ { ++ fail ("gcry_kdf_derive test %d failed: mismatch\n", tvidx); ++ fputs ("got:", stderr); ++ for (i=0; i < tv[tvidx].dklen; i++) ++ fprintf (stderr, " %02x", outbuf[i]); ++ putc ('\n', stderr); ++ } ++ } ++ } ++} ++ ++ + int + main (int argc, char **argv) + { +@@ -495,6 +653,7 @@ main (int argc, char **argv) + check_digests (); + check_md_o_w_r_c (); + check_mac_o_w_r_c (); ++ check_kdf_derive (); + + return !!error_count; + } +Index: libgcrypt-1.11.0/tests/t-kdf.c +=================================================================== +--- libgcrypt-1.11.0.orig/tests/t-kdf.c ++++ libgcrypt-1.11.0/tests/t-kdf.c +@@ -1927,163 +1927,6 @@ check_fips_indicators (void) + } + + +-static void +-check_fips_gcry_kdf_derive (void) +-{ +- static struct { +- const char *p; /* Passphrase. */ +- size_t plen; /* Length of P. */ +- int algo; +- int subalgo; +- const char *salt; +- size_t saltlen; +- unsigned long iterations; +- int dklen; /* Requested key length. */ +- const char *dk; /* Derived key. */ +- int expect_failure; +- } tv[] = { +- { +- "passwordPASSWORDpassword", 24, +- GCRY_KDF_PBKDF2, GCRY_MD_SHA1, +- "saltSALTsaltSALTsaltSALTsaltSALTsalt", 36, +- 4096, +- 25, +- "\x3d\x2e\xec\x4f\xe4\x1c\x84\x9b\x80\xc8" +- "\xd8\x36\x62\xc0\xe4\x4a\x8b\x29\x1a\x96" +- "\x4c\xf2\xf0\x70\x38", +- 0 +- }, +- { +- "pleaseletmein", 13, +- GCRY_KDF_SCRYPT, 16384, +- "SodiumChloride", 14, +- 1, +- 64, +- "\x70\x23\xbd\xcb\x3a\xfd\x73\x48\x46\x1c\x06\xcd\x81\xfd\x38\xeb" +- "\xfd\xa8\xfb\xba\x90\x4f\x8e\x3e\xa9\xb5\x43\xf6\x54\x5d\xa1\xf2" +- "\xd5\x43\x29\x55\x61\x3f\x0f\xcf\x62\xd4\x97\x05\x24\x2a\x9a\xf9" +- "\xe6\x1e\x85\xdc\x0d\x65\x1e\x40\xdf\xcf\x01\x7b\x45\x57\x58\x87", +- 1 /* not-compliant because unallowed algo */ +- }, +- { +- "passwor", 7, +- GCRY_KDF_PBKDF2, GCRY_MD_SHA1, +- "saltSALTsaltSALTsaltSALTsaltSALTsalt", 36, +- 4096, +- 25, +- "\xf4\x93\xee\x2b\xbf\x44\x0b\x9e\x64\x53" +- "\xc2\xb3\x87\xdc\x73\xf8\xfd\xe6\x97\xda" +- "\xb8\x24\xa0\x26\x50", +- 1 /* not-compliant because passphrase len is too small */ +- }, +- { +- "passwordPASSWORDpassword", 24, +- GCRY_KDF_PBKDF2, GCRY_MD_SHA1, +- "saltSALTsaltSAL", 15, +- 4096, +- 25, +- "\x14\x05\xa4\x2a\xf4\xa8\x12\x14\x7b\x65" +- "\x8f\xaa\xf0\x7f\x25\xe5\x0f\x0b\x2b\xb7" +- "\xcf\x8d\x29\x23\x4b", +- 1 /* not-compliant because salt len is too small */ +- }, +- { +- "passwordPASSWORDpassword", 24, +- GCRY_KDF_PBKDF2, GCRY_MD_SHA1, +- "saltSALTsaltSALTsaltSALTsaltSALTsalt", 36, +- 999, +- 25, +- "\xac\xf8\xb4\x67\x41\xc7\xf3\xd1\xa0\xc0" +- "\x08\xbe\x9b\x23\x96\x78\xbd\x93\xda\x4a" +- "\x30\xd4\xfb\xf0\x33", +- 1 /* not-compliant because too few iterations */ +- }, +- { +- "passwordPASSWORDpassword", 24, +- GCRY_KDF_PBKDF2, GCRY_MD_SHA1, +- "saltSALTsaltSALTsaltSALTsaltSALTsalt", 36, +- 4096, +- 13, +- "\x3d\x2e\xec\x4f\xe4\x1c\x84\x9b\x80\xc8" +- "\xd8\x36\x62", +- 1 /* not-compliant because key size too small */ +- }, +- { +- "passwordPASSWORDpassword", 24, +- GCRY_KDF_PBKDF2, GCRY_MD_BLAKE2B_512, +- "saltSALTsaltSALTsaltSALTsaltSALTsalt", 36, +- 4096, +- 60, +- "\xa4\x6b\x53\x35\xdb\xdd\xa3\xd2\x5d\x19\xbb\x11\xfe\xdd\xd9\x9e" +- "\x45\x2a\x7c\x34\x47\x41\x98\xca\x31\x74\xb6\x34\x22\xac\x83\xb0" +- "\x38\x6e\xf5\x93\x0f\xf5\x16\x46\x0b\x97\xdc\x6c\x27\x5b\xe7\x25" +- "\xc2\xcb\xec\x50\x02\xc6\x52\x8b\x34\x68\x53\x65", +- 1 /* not-compliant because subalgo is not the one of approved */ +- } +- }; +- +- int tvidx; +- gpg_error_t err; +- unsigned char outbuf[100]; +- int i; +- +- for (tvidx=0; tvidx < DIM(tv); tvidx++) +- { +- if (verbose) +- fprintf (stderr, "checking gcry_kdf_derive test vector %d algo %d for FIPS\n", +- tvidx, tv[tvidx].algo); +- assert (tv[tvidx].dklen <= sizeof outbuf); +- err = gcry_kdf_derive (tv[tvidx].p, tv[tvidx].plen, +- tv[tvidx].algo, tv[tvidx].subalgo, +- tv[tvidx].salt, tv[tvidx].saltlen, +- tv[tvidx].iterations, tv[tvidx].dklen, outbuf); +- +- if (err) +- { +- fail ("gcry_kdf_derive test %d unexpectedly returned an error in FIPS mode: %s\n", +- tvidx, gpg_strerror (err)); +- } +- else +- { +- gpg_err_code_t ec; +- +- ec = gcry_get_fips_service_indicator (); +- if (ec == GPG_ERR_INV_OP) +- { +- /* libgcrypt is old, no support of the FIPS service indicator. */ +- fail ("gcry_kdf_derive test %d unexpectedly failed to check the FIPS service indicator.\n", +- tvidx); +- continue; +- } +- +- if (!tv[tvidx].expect_failure && ec) +- { +- /* Success with the FIPS service indicator == 0 expected, but != 0. */ +- fail ("gcry_kdf_derive test %d unexpectedly set the indicator in FIPS mode.\n", +- tvidx); +- continue; +- } +- else if (tv[tvidx].expect_failure && !ec) +- { +- /* Success with the FIPS service indicator != 0 expected, but == 0. */ +- fail ("gcry_kdf_derive test %d unexpectedly cleared the indicator in FIPS mode.\n", +- tvidx); +- continue; +- } +- +- if (memcmp (outbuf, tv[tvidx].dk, tv[tvidx].dklen)) +- { +- fail ("gcry_kdf_derive test %d failed: mismatch\n", tvidx); +- fputs ("got:", stderr); +- for (i=0; i < tv[tvidx].dklen; i++) +- fprintf (stderr, " %02x", outbuf[i]); +- putc ('\n', stderr); +- } +- } +- } +-} +- +- + int + main (int argc, char **argv) + { +@@ -2166,8 +2009,6 @@ main (int argc, char **argv) + check_hkdf (); + if (in_fips_mode) + check_fips_indicators (); +- if (in_fips_mode) +- check_fips_gcry_kdf_derive (); + } + + return error_count ? 1 : 0; diff --git a/libgcrypt-tests-fips-Rename-t-fips-service-ind.patch b/libgcrypt-tests-fips-Rename-t-fips-service-ind.patch new file mode 100644 index 0000000..bb32094 --- /dev/null +++ b/libgcrypt-tests-fips-Rename-t-fips-service-ind.patch @@ -0,0 +1,60 @@ +From 132f346232b33fe41ffee3b3870ec189626676e7 Mon Sep 17 00:00:00 2001 +From: NIIBE Yutaka +Date: Mon, 16 Dec 2024 14:14:24 +0900 +Subject: [PATCH 07/19] tests,fips: Rename t-fips-service-ind. +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* tests/t-fips-service-ind.c: Rename from t-digest.c. +* tests/Makefile.am (tests_bin): Follow the change. + +-- + +GnuPG-bug-id: 7338 +Signed-off-by: NIIBE Yutaka +Signed-off-by: Lucas Mülling +--- + tests/Makefile.am | 2 +- + tests/{t-digest.c => t-fips-service-ind.c} | 4 ++-- + 2 files changed, 3 insertions(+), 3 deletions(-) + rename tests/{t-digest.c => t-fips-service-ind.c} (99%) + +diff --git a/tests/Makefile.am b/tests/Makefile.am +index 93774fe9..3170a58e 100644 +--- a/tests/Makefile.am ++++ b/tests/Makefile.am +@@ -25,7 +25,7 @@ tests_bin = \ + version t-secmem mpitests t-sexp t-convert \ + t-mpi-bit t-mpi-point t-lock \ + prime basic keygen pubkey hmac hashtest t-kdf keygrip \ +- aeswrap random t-kem t-mlkem t-thread-local t-digest ++ aeswrap random t-kem t-mlkem t-thread-local t-fips-service-ind + + if USE_RSA + tests_bin += pkcs1v2 t-rsa-pss t-rsa-15 t-rsa-testparm +diff --git a/tests/t-digest.c b/tests/t-fips-service-ind.c +similarity index 99% +rename from tests/t-digest.c +rename to tests/t-fips-service-ind.c +index e2b1ce32..31c1fc72 100644 +--- a/tests/t-digest.c ++++ b/tests/t-fips-service-ind.c +@@ -1,4 +1,4 @@ +-/* t-digest.c - MD regression tests ++/* t-fips-service-ind.c - FIPS service indicator regression tests + * Copyright (C) 2024 g10 Code GmbH + * + * This file is part of Libgcrypt. +@@ -27,7 +27,7 @@ + #include + #include + +-#define PGM "t-digest" ++#define PGM "t-fips-service-ind" + + #include "t-common.h" + static int in_fips_mode; +-- +2.49.0 + diff --git a/libgcrypt.changes b/libgcrypt.changes new file mode 100644 index 0000000..76e23bd --- /dev/null +++ b/libgcrypt.changes @@ -0,0 +1,2003 @@ +------------------------------------------------------------------- +Thu May 8 14:28:42 UTC 2025 - Lucas Mulling + +- Update to 1.11.1: [jsc#PED-12227] + * Bug fixes: + - Fix Kyber secret-dependent branch introduced by recent versions of Clang. [rCf765778e82] + - Fix build regression due to the use of AVX512 in Blake. [T7184] + - Do not build i386 asm on amd64 and vice versa. [T7220] + - Fix build regression on armhf with gcc-14. [T7226] + - Return the proper error code on malloc failure in hex2buffer. [rCc51151f5b0] + - Fix long standing bug for PRIME % 2 == 0. [rC639b0fca15] + * Performance: + - Add AES Vector Permute intrinsics implementation for AArch64. [rC94a63aedbb] + - Add GHASH AArch64/SIMD intrinsics implementation. [rCfec871fd18] + - Add RISC-V vector permute AES. [rCb24ebd6163] + - Add GHASH RISC-V Zbb+Zbc implementation. [rC0f1fec12b0] + - Add ChaCha20 RISC-V vector intrinsics implementation. [rC8dbee93ac2] + - Add SHA3 acceleration for RISC-V Zbb extension. [rC1a660068ba] + * Other: + - Add CET support for i386 and amd64 assembly. [T7220] + - Add PAC/BTI support for AArch64 asm. [T7220] + - Apply changes to Kyber from upstream for final FIPS 203. [rCcc95c36e7f] + - Introduce an internal API for a revampled FIPS service indicator. [T7340] + - Several improvements for constant time operation by the introduction of Least Leak Intended (LLI) variants of internal functions. [T7519,T7490] + * Rebase patches: + - libgcrypt-FIPS-SLI-hash-mac.patch + - libgcrypt-FIPS-SLI-pk.patch + - libgcrypt-FIPS-jitter-standalone.patch + * Remove patches: + - libgcrypt-fips-Introduce-an-internal-API-for-FIPS-service-indicator.patch + - libgcrypt-fips-Introduce-GCRYCTL_FIPS_SERVICE_INDICATOR-and-the-macro.patch + - libgcrypt-fips-kdf-Implement-new-FIPS-service-indicator-for-gcry_kdf_derive.patch + - libgcrypt-fips-md-Implement-new-FIPS-service-indicator-for-gcry_md_hash_.patch + - libgcrypt-fips-tests-Add-t-digest.patch + - libgcrypt-fips-Change-the-internal-API-for-new-FIPS-service-indicator.patch + - libgcrypt-fips-md-Implement-new-FIPS-service-indicator-for-gcry_md_open-API.patch + - libgcrypt-fips-tests-Add-tests-for-md_open-write-read-close-for-t-digest.patch + - libgcrypt-fips-mac-Implement-new-FIPS-service-indicator-for-gcry_mac_open.patch + - libgcrypt-fips-cipher-Implement-new-FIPS-service-indicator-for-cipher_open.patch + - libgcrypt-tests-fips-Add-gcry_mac_open-tests.patch + - libgcrypt-tests-fips-Rename-t-fips-service-ind.patch + - libgcrypt-tests-fips-Move-KDF-tests-to-t-fips-service-ind.patch + - libgcrypt-tests-fips-Add-gcry_cipher_open-tests.patch + - libgcrypt-fips-md-gcry_md_copy-should-care-about-FIPS-service-indicator.patch + - libgcrypt-fips-cipher-Implement-FIPS-service-indicator-for-gcry_pk_hash_-API.patch + - libgcrypt-fips-Introduce-GCRYCTL_FIPS_REJECT_NON_FIPS.patch + - libgcrypt-Fix-the-previous-change.patch + - libgcrypt-fips-Rejection-by-GCRYCTL_FIPS_REJECT_NON_FIPS-not-by-open-flags.patch + - libgcrypt-fips-cipher-Add-behavior-not-to-reject-but-mark-non-compliant.patch + - libgcrypt-fips-ecc-Add-rejecting-or-marking-for-gcry_pk_get_curve.patch + - libgcrypt-tests-Add-more-tests-to-tests-t-fips-service-ind.patch + - libgcrypt-fips-ecc-Check-DATA-in-gcry_pk_sign-verify-in-FIPS-mode.patch + - libgcrypt-fips-cipher-Fix-memory-leak-for-gcry_pk_hash_sign.patch + - libgcrypt-build-Improve-__thread-specifier-check.patch + - libgcrypt-cipher-Check-and-mark-non-compliant-cipher-modes-in-the-SLI.patch + - libgcrypt-cipher-Rename-_gcry_cipher_is_mode_fips_compliant.patch + - libgcrypt-cipher-Don-t-differentiate-GCRY_CIPHER_MODE_CMAC-in-FIPS-mode.patch + - libgcrypt-cipher-rsa-Mark-reject-SHA1-unknown-with-RSA-signature-generation.patch + - libgcrypt-md-Fix-gcry_md_algo_info-to-mark-reject-under-FIPS-mode.patch + - libgcrypt-md-Use-check_digest_algo_spec-in-_gcry_md_selftest.patch + - libgcrypt-tests-Update-t-fips-service-ind-using-GCRY_MD_SHA256-for-KDF-tests.patch + - libgcrypt-fips-cipher-Do-the-computation-when-marking-non-compliant.patch + - libgcrypt-tests-Allow-tests-with-USE_RSA.patch + - libgcrypt-cipher-Add-KAT-for-non-rfc6979-ECDSA-with-fixed-k.patch + - libgcrypt-cipher-Differentiate-use-of-label-K-in-the-SLI.patch + - libgcrypt-cipher-Differentiate-igninvflag-in-the-SLI.patch + - libgcrypt-cipher-Differentiate-no-blinding-flag-in-the-SLI.patch + - libgcrypt-fips-cipher-Add-GCRY_FIPS_FLAG_REJECT_PK_FLAGS.patch + - libgcrypt-cipher-ecc-Fix-for-supplied-K.patch + - libgcrypt-cipher-visibility-Differentiate-use-of-random-override-in-the-SLI.patch + - libgcrypt-cipher-fips-Fix-for-random-override.patch + - libgcrypt-md-Make-SHA-1-non-FIPS-internally-for-1.12-API.patch + - libgcrypt-fips-Fix-GCRY_FIPS_FLAG_REJECT_MD.patch + - libgcrypt-doc-Add-about-GCRYCTL_FIPS_SERVICE_INDICATOR.patch + - libgcrypt-doc-Fix-syntax-error.patch + - libgcrypt-Disable-SHA3-s390x-acceleration-for-CSHAKE.patch + +------------------------------------------------------------------- +Tue May 6 07:24:14 UTC 2025 - Pedro Monreal + +- CSHAKE basic regression test failure in s390x [bsc#1242419] + * Disable SHA3 s390x acceleration for CSHAKE [rC2486d9b5ae01] + * Add libgcrypt-Disable-SHA3-s390x-acceleration-for-CSHAKE.patch + +------------------------------------------------------------------- +Sun Apr 13 20:10:16 UTC 2025 - Lucas Mulling + +- Differentiate use of SHA1 in the service level indicator [jsc#PED-12227] + * Include upstream SLI revamp and fips certification fixes + * Add patches: + - libgcrypt-fips-Introduce-an-internal-API-for-FIPS-service-indicator.patch + - libgcrypt-fips-Introduce-GCRYCTL_FIPS_SERVICE_INDICATOR-and-the-macro.patch + - libgcrypt-fips-kdf-Implement-new-FIPS-service-indicator-for-gcry_kdf_derive.patch + - libgcrypt-fips-md-Implement-new-FIPS-service-indicator-for-gcry_md_hash_.patch + - libgcrypt-fips-tests-Add-t-digest.patch + - libgcrypt-fips-Change-the-internal-API-for-new-FIPS-service-indicator.patch + - libgcrypt-fips-md-Implement-new-FIPS-service-indicator-for-gcry_md_open-API.patch + - libgcrypt-fips-tests-Add-tests-for-md_open-write-read-close-for-t-digest.patch + - libgcrypt-fips-mac-Implement-new-FIPS-service-indicator-for-gcry_mac_open.patch + - libgcrypt-fips-cipher-Implement-new-FIPS-service-indicator-for-cipher_open.patch + - libgcrypt-tests-fips-Add-gcry_mac_open-tests.patch + - libgcrypt-tests-fips-Rename-t-fips-service-ind.patch + - libgcrypt-tests-fips-Move-KDF-tests-to-t-fips-service-ind.patch + - libgcrypt-tests-fips-Add-gcry_cipher_open-tests.patch + - libgcrypt-fips-md-gcry_md_copy-should-care-about-FIPS-service-indicator.patch + - libgcrypt-fips-cipher-Implement-FIPS-service-indicator-for-gcry_pk_hash_-API.patch + - libgcrypt-fips-Introduce-GCRYCTL_FIPS_REJECT_NON_FIPS.patch + - libgcrypt-Fix-the-previous-change.patch + - libgcrypt-fips-Rejection-by-GCRYCTL_FIPS_REJECT_NON_FIPS-not-by-open-flags.patch + - libgcrypt-fips-cipher-Add-behavior-not-to-reject-but-mark-non-compliant.patch + - libgcrypt-fips-ecc-Add-rejecting-or-marking-for-gcry_pk_get_curve.patch + - libgcrypt-tests-Add-more-tests-to-tests-t-fips-service-ind.patch + - libgcrypt-fips-ecc-Check-DATA-in-gcry_pk_sign-verify-in-FIPS-mode.patch + - libgcrypt-fips-cipher-Fix-memory-leak-for-gcry_pk_hash_sign.patch + - libgcrypt-build-Improve-__thread-specifier-check.patch + - libgcrypt-cipher-Check-and-mark-non-compliant-cipher-modes-in-the-SLI.patch + - libgcrypt-cipher-Rename-_gcry_cipher_is_mode_fips_compliant.patch + - libgcrypt-cipher-Don-t-differentiate-GCRY_CIPHER_MODE_CMAC-in-FIPS-mode.patch + - libgcrypt-cipher-rsa-Mark-reject-SHA1-unknown-with-RSA-signature-generation.patch + - libgcrypt-md-Fix-gcry_md_algo_info-to-mark-reject-under-FIPS-mode.patch + - libgcrypt-md-Use-check_digest_algo_spec-in-_gcry_md_selftest.patch + - libgcrypt-tests-Update-t-fips-service-ind-using-GCRY_MD_SHA256-for-KDF-tests.patch + - libgcrypt-fips-cipher-Do-the-computation-when-marking-non-compliant.patch + - libgcrypt-tests-Allow-tests-with-USE_RSA.patch + - libgcrypt-cipher-Add-KAT-for-non-rfc6979-ECDSA-with-fixed-k.patch + - libgcrypt-cipher-Differentiate-use-of-label-K-in-the-SLI.patch + - libgcrypt-cipher-Differentiate-igninvflag-in-the-SLI.patch + - libgcrypt-cipher-Differentiate-no-blinding-flag-in-the-SLI.patch + - libgcrypt-fips-cipher-Add-GCRY_FIPS_FLAG_REJECT_PK_FLAGS.patch + - libgcrypt-cipher-ecc-Fix-for-supplied-K.patch + - libgcrypt-cipher-visibility-Differentiate-use-of-random-override-in-the-SLI.patch + - libgcrypt-cipher-fips-Fix-for-random-override.patch + - libgcrypt-md-Make-SHA-1-non-FIPS-internally-for-1.12-API.patch + - libgcrypt-fips-Fix-GCRY_FIPS_FLAG_REJECT_MD.patch + - libgcrypt-doc-Add-about-GCRYCTL_FIPS_SERVICE_INDICATOR.patch + - libgcrypt-doc-Fix-syntax-error.patch + * Rebase patches: + - libgcrypt-FIPS-SLI-kdf-leylength.patch + +------------------------------------------------------------------- +Tue Jan 7 09:28:25 UTC 2025 - Pedro Monreal + +- Fix redefinition error of 'rol64'. Remove not used rol64() + definition after removing the built-in jitter rng. + * Add libgcrypt-rol64-redefinition.patch + +------------------------------------------------------------------- +Mon Dec 2 10:11:10 UTC 2024 - Pedro Monreal + +- Remove unrecognized option: --enable-m-guard + +------------------------------------------------------------------- +Thu Jun 20 08:11:07 UTC 2024 - Pedro Monreal + +- Update to 1.11.0: + * New and extended interfaces: + - Add an API for Key Encapsulation Mechanism (KEM). [T6755] + - Add Streamlined NTRU Prime sntrup761 algorithm. [rCcf9923e1a5] + - Add Kyber algorithm according to FIPS 203 ipd 2023-08-24. [rC18e5c0d268] + - Add Classic McEliece algorithm. [rC003367b912] + - Add One-Step KDF with hash and MAC. [T5964] + - Add KDF algorithm HKDF of RFC-5869. [T5964] + - Add KDF algorithm X963KDF for use in CMS. [rC3abac420b3] + - Add GMAC-SM4 and Poly1305-SM4. [rCd1ccc409d4] + - Add ARIA block cipher algorithm. [rC316c6d7715] + - Add explicit FIPS indicators for MD and MAC algorithms. [T6376] + - Add support for SHAKE as MGF in RSA. [T6557] + - Add gcry_md_read support for SHAKE algorithms. [T6539] + - Add gcry_md_hash_buffers_ext function. [T7035] + - Add cSHAKE hash algorithm. [rC065b3f4e02] + - Support internal generation of IV for AEAD cipher mode. [T4873] + * Performance: + - Add SM3 ARMv8/AArch64/CE assembly implementation. [rCfe891ff4a3] + - Add SM4 ARMv8/AArch64 assembly implementation. [rCd8825601f1] + - Add SM4 GFNI/AVX2 and GFI/AVX512 implementation. [rC5095d60af4,rCeaed633c16] + - Add SM4 ARMv9 SVE CE assembly implementation. [rC2dc2654006] + - Add PowerPC vector implementation of SM4. [rC0b2da804ee] + - Optimize ChaCha20 and Poly1305 for PPC P10 LE. [T6006] + - Add CTR32LE bulk acceleration for AES on PPC. [rC84f2e2d0b5] + - Add generic bulk acceleration for CTR32LE mode (GCM-SIV) for SM4 + and Camellia. [rCcf956793af] + - Add GFNI/AVX2 implementation of Camellia. [rC4e6896eb9f] + - Add AVX2 and AVX512 accelerated implementations for GHASH (GCM) + and POLYVAL (GCM-SIV). [rCd857e85cb4, rCe6f3600193] + - Add AVX512 implementation for SHA512. [rC089223aa3b] + - Add AVX512 implementation for Serpent. [rCce95b6ec35] + - Add AVX512 implementation for Poly1305 and ChaCha20. [rCcd3ed49770, rC9a63cfd617] + - Add AVX512 accelerated implementation for SHA3 and Blake2. [rCbeaad75f46,rC909daa700e] + - Add VAES/AVX2 accelerated i386 implementation for AES. [rC4a42a042bc] + - Add bulk processing for XTS mode of Camellia and SM4. [rC32b18cdb87, rCaad3381e93] + - Accelerate XTS and ECB modes for Twofish and Serpent. [rCd078a928f5,rC8a1fe5f78f] + - Add AArch64 crypto/SHA512 extension implementation for SHA512. [rCe51d3b8330] + - Add AArch64 crypto-extension implementation for Camellia. [rC898c857206] + - Accelerate OCB authentication on AMD with AVX2. [rC6b47e85d65] + * Bug fixes: + - For PowerPC check for missing optimization level for vector register usage. [T5785] + - Fix EdDSA secret key check. [T6511] + - Fix decoding of PKCS#1-v1.5 and OAEP padding. [rC34c2042792] + - Allow use of PKCS#1-v1.5 with SHA3 algorithms. [T6976] + - Fix AESWRAP padding length check. [T7130] + * Other: + - Allow empty password for Argon2 KDF. [rCa20700c55f] + - Various constant time operation imporvements. + - Add "bp256", "bp384", "bp512" aliases for Brainpool curves. + - Support for the random server has been removed. [T5811] + - The control code GCRYCTL_ENABLE_M_GUARD is deprecated and not + supported any more. Please use valgrind or other tools. [T5822] + - Logging is now done via the libgpg-error logging functions. [rCab0bdc72c7] + * Remove patches fixed upstream: + - libgcrypt-no-deprecated-grep-alias.patch + - libgcrypt-Chacha20-poly1305-Optimized-chacha20-poly1305.patch + - libgcrypt-ppc-enable-P10-assembly-with-ENABLE_FORCE_SOF.patch + * Rebase patches: + - libgcrypt-FIPS-jitter-errorcodes.patch + - libgcrypt-FIPS-jitter-whole-entropy.patch + +------------------------------------------------------------------- +Wed Mar 20 20:31:40 UTC 2024 - Pedro Monreal + +- FIPS: Make sure that Libgcrypt makes use of the built-in Jitter RNG + for the whole length entropy buffer in FIPS mode. [bsc#1220893] + * Add libgcrypt-FIPS-jitter-whole-entropy.patch + +------------------------------------------------------------------- +Wed Mar 20 15:13:04 UTC 2024 - Pedro Monreal + +- FIPS: Set the FSM into error state if Jitter RNG is returning an + error code to the caller when an health test error occurs when + random bytes are requested through the jent_read_entropy_safe() + function. [bsc#1220895] + * Add libgcrypt-FIPS-jitter-errorcodes.patch + +------------------------------------------------------------------- +Mon Mar 11 16:02:55 UTC 2024 - Pedro Monreal + +- FIPS: Replace the built-in jitter rng with standalone version + * Remove the internal jitterentropy copy [bsc#1220896] + * Add libgcrypt-FIPS-jitter-standalone.patch + * Remove not needed libgcrypt-jitterentropy-3.4.0.patch + +------------------------------------------------------------------- +Mon Feb 26 12:13:56 UTC 2024 - Pedro Monreal + +- Update upstream libgcrypt.keyring + +------------------------------------------------------------------- +Sat Jan 27 13:37:34 UTC 2024 - Dirk Müller + +- add libgcrypt-no-deprecated-grep-alias.patch + +------------------------------------------------------------------- +Tue Nov 21 10:36:09 UTC 2023 - Otto Hollmann + +- Re-create HMAC checksum after RPM build strips the library + (bsc#1217058) + +------------------------------------------------------------------- +Wed Nov 15 09:54:00 UTC 2023 - Pedro Monreal + +- Update to 1.10.3: + * Bug fixes: + - Fix public key computation for other EdDSA curves. [rC469919751d6e] + - Remove out of core handler diagnostic in FIPS mode. [T6515] + - Check that the digest size is not zero in gcry_pk_sign_md and + gcry_pk_verify_md. [T6539] + - Make store an s-exp with \0 is considered to be binary. [T6747] + - Various constant-time improvements. + * Portability: + - Use getrandom call only when supported by the platform. [T6442] + - Change the default for --with-libtool-modification to never. [T6619] + * Release-info: https://dev.gnupg.org/T6817 + * Remove patch upstream libgcrypt-1.10.0-out-of-core-handler.patch + +------------------------------------------------------------------- +Tue Oct 17 10:27:15 UTC 2023 - Pedro Monreal + +- Do not pull revision info from GIT when autoconf is run. This + removes the -unknown suffix after the version number. + * Add libgcrypt-nobetasuffix.patch [bsc#1216334] + +------------------------------------------------------------------- +Tue Oct 3 12:58:41 UTC 2023 - Pedro Monreal + +- POWER: performance enhancements for cryptography [jsc#PED-5088] + * Optimize Chacha20 and Poly1305 for PPC P10 LE: [T6006] + - Chacha20/poly1305: Optimized chacha20/poly1305 for + P10 operation [rC88fe7ac33eb4] + - ppc: enable P10 assembly with ENABLE_FORCE_SOFT_HWFEATURES + on arch-3.00 [rC2c5e5ab6843d] + * Add patches: + - libgcrypt-Chacha20-poly1305-Optimized-chacha20-poly1305.patch + - libgcrypt-ppc-enable-P10-assembly-with-ENABLE_FORCE_SOF.patch + +------------------------------------------------------------------- +Mon May 22 11:32:53 UTC 2023 - Pedro Monreal + +- FIPS: Merge the libgcrypt20-hmac package into the library and + remove the "module is complete" trigger file .fips [bsc#1185116] + * Remove libgcrypt-1.10.0-use-fipscheck.patch + +------------------------------------------------------------------- +Tue Apr 11 14:08:24 UTC 2023 - Pedro Monreal + +- Update to 1.10.2: + * Bug fixes: + - Fix Argon2 for the case output > 64. [rC13b5454d26] + - Fix missing HWF_PPC_ARCH_3_10 in HW feature. [rCe073f0ed44] + - Fix RSA key generation failure in forced FIPS mode. [T5919] + - Fix gcry_pk_hash_verify for explicit hash. [T6066] + - Fix a wrong result of gcry_mpi_invm. [T5970] + - Allow building with --disable-asm for HPPA. [T5976] + - Allow building with -Oz. [T6432] + - Enable the fast path to ChaCha20 only when supported. [T6384] + - Use size_t to avoid counter overflow in Keccak when directly + feeding more than 4GiB. [T6217] + * Other: + - Do not use secure memory for a DRBG instance. [T5933] + - Do not allow PKCS#1.5 padding for encryption in FIPS mode. [T5918] + - Fix the behaviour for child process re-seeding in the DRBG. [rC019a40c990] + - Allow verification of small RSA signatures in FIPS mode. [T5975] + - Allow the use of a shorter salt for KDFs in FIPS mode. [T6039] + - Run digest+sign self tests for RSA and ECC in FIPS mode. [rC06c9350165] + - Add function-name based FIPS indicator function. + GCRYCTL_FIPS_SERVICE_INDICATOR_FUNCTION. This is not considered + an ABI changes because the new FIPS features were not yet + approved. [rC822ee57f07] + - Improve PCT in FIPS mode. [rC285bf54b1a, rC4963c127ae, T6397] + - Use getrandom (GRND_RANDOM) in FIPS mode. [rCcf10c74bd9] + - Disable RSA-OAEP padding in FIPS mode. [rCe5bfda492a] + - Check minimum allowed key size in PBKDF in FIPS mode. [T6039,T6219] + - Get maximum 32B of entropy at once in FIPS mode. [rCce0df08bba] + - Prefer gpgrt-config when available. [T5034] + - Mark AESWRAP as approved FIPS algorithm. [T5512] + - Prevent usage of long salt for PSS in FIPS mode. [rCfdd2a8b332] + - Prevent usage of X9.31 keygen in FIPS mode. [rC392e0ccd25] + - Remove GCM mode from the allowed FIPS indicators. [rC1540698389] + - Add explicit FIPS indicators for hash and MAC algorithms. [T6376] + * Release-info: https://dev.gnupg.org/T5905 + * Rebase FIPS patches: + - libgcrypt-FIPS-SLI-hash-mac.patch + - libgcrypt-FIPS-SLI-kdf-leylength.patch + - libgcrypt-FIPS-SLI-pk.patch + +------------------------------------------------------------------- +Wed Mar 8 10:34:34 UTC 2023 - Martin Pluskal + +- Build AVX2 enabled hwcaps library for x86_64-v3 + +------------------------------------------------------------------- +Wed Oct 19 14:01:24 UTC 2022 - Pedro Monreal + +- Update to 1.10.1: + * Bug fixes: + - Fix minor memory leaks in FIPS mode. + - Build fixes for MUSL libc. + * Other: + - More portable integrity check in FIPS mode. + - Add X9.62 OIDs to sha256 and sha512 modules. + * Add the hardware optimizations config file hwf.deny to + the /etc/gcrypt/ directory. This file can be used to globally + disable the use of hardware based optimizations. + * Remove not needed separate_hmac256_binary hmac256 package + +------------------------------------------------------------------- +Wed Sep 14 13:34:13 UTC 2022 - Pedro Monreal + +- Update to 1.10.0: + * New and extended interfaces: + - New control codes to check for FIPS 140-3 approved algorithms. + - New control code to switch into non-FIPS mode. + - New cipher modes SIV and GCM-SIV as specified by RFC-5297. + - Extended cipher mode AESWRAP with padding as specified by + RFC-5649. + - New set of KDF functions. + - New KDF modes Argon2 and Balloon. + - New functions for combining hashing and signing/verification. + * Performance: + - Improved support for PowerPC architectures. + - Improved ECC performance on zSeries/s390x by using accelerated + scalar multiplication. + - Many more assembler performance improvements for several + architectures. + * Bug fixes: + - Fix Elgamal encryption for other implementations. + [bsc#1190239, CVE-2021-40528] + - Check the input length of the point in ECDH. + - Fix an abort in gcry_pk_get_param for "Curve25519". + * Other features: + - The control code GCRYCTL_SET_ENFORCED_FIPS_FLAG is ignored + because it is useless with the FIPS 140-3 related changes. + - Update of the jitter entropy RNG code. + - Simplification of the entropy gatherer when using the getentropy + system call. + * Interface changes relative to the 1.10.0 release: + - GCRYCTL_SET_DECRYPTION_TAG NEW control code. + - GCRYCTL_FIPS_SERVICE_INDICATOR_CIPHER NEW control code. + - GCRYCTL_FIPS_SERVICE_INDICATOR_KDF NEW control code. + - GCRYCTL_NO_FIPS_MODE = 83 NEW control code. + - GCRY_CIPHER_MODE_SIV NEW mode. + - GCRY_CIPHER_MODE_GCM_SIV NEW mode. + - GCRY_CIPHER_EXTENDED NEW flag. + - GCRY_SIV_BLOCK_LEN NEW macro. + - gcry_cipher_set_decryption_tag NEW macro. + - GCRY_KDF_ARGON2 NEW constant. + - GCRY_KDF_BALLOON NEW constant. + - GCRY_KDF_ARGON2D NEW constant. + - GCRY_KDF_ARGON2I NEW constant. + - GCRY_KDF_ARGON2ID NEW constant. + - gcry_kdf_hd_t NEW type. + - gcry_kdf_job_fn_t NEW type. + - gcry_kdf_dispatch_job_fn_t NEW type. + - gcry_kdf_wait_all_jobs_fn_t NEW type. + - struct gcry_kdf_thread_ops NEW struct. + - gcry_kdf_open NEW function. + - gcry_kdf_compute NEW function. + - gcry_kdf_final NEW function. + - gcry_kdf_close NEW function. + - gcry_pk_hash_sign NEW function. + - gcry_pk_hash_verify NEW function. + - gcry_pk_random_override_new NEW function. + * Rebase libgcrypt-1.8.4-allow_FSM_same_state.patch and rename + to libgcrypt-1.10.0-allow_FSM_same_state.patch + * Remove unused CAVS tests and related patches: + - cavs_driver.pl cavs-test.sh + - libgcrypt-1.6.1-fips-cavs.patch + - drbg_test.patch + * Remove DSA sign/verify patches for the FIPS CAVS test since DSA + has been disabled in FIPS mode: + - libgcrypt-fipsdrv-enable-algo-for-dsa-sign.patch + - libgcrypt-fipsdrv-enable-algo-for-dsa-verify.patch + * Rebase libgcrypt-FIPS-SLI-pk.patch + * Rebase libgcrypt_indicators_changes.patch and + libgcrypt-indicate-shake.patch and merge both into + libgcrypt-FIPS-SLI-hash-mac.patch + * Rebase libgcrypt-FIPS-kdf-leylength.patch and rename to + libgcrypt-FIPS-SLI-kdf-leylength.patch + * Rebase libgcrypt-jitterentropy-3.4.0.patch + * Rebase libgcrypt-FIPS-rndjent_poll.patch + * Rebase libgcrypt-out-of-core-handler.patch and rename to + libgcrypt-1.10.0-out-of-core-handler.patch + * Since the FIPS .hmac file is now calculated with the internal + tool hmac256, only the "module is complete" trigger .fips file + is checked. Rename libgcrypt-1.6.1-use-fipscheck.patch + to libgcrypt-1.10.0-use-fipscheck.patch + * Remove patches fixed upstream: + - libgcrypt-1.4.1-rijndael_no_strict_aliasing.patch + - libgcrypt-1.5.0-LIBGCRYPT_FORCE_FIPS_MODE-env.diff + - libgcrypt-fix-rng.patch + - libgcrypt-1.8.3-fips-ctor.patch + - libgcrypt-1.8.4-use_xfree.patch + - libgcrypt-1.8.4-getrandom.patch + - libgcrypt-1.8.4-fips_ctor_skip_integrity_check.patch + - libgcrypt-dsa-rfc6979-test-fix.patch + - libgcrypt-fix-tests-fipsmode.patch + - libgcrypt-FIPS-RSA-DSA-ECDSA-hashing-operation.patch + - libgcrypt-1.8.4-fips-keygen.patch + - libgcrypt-invoke-global_init-from-constructor.patch + - libgcrypt-Restore-self-tests-from-constructor.patch + - libgcrypt-FIPS-GMAC_AES-benckmark.patch + - libgcrypt-global_init-constructor.patch + - libgcrypt-random_selftests-testentropy.patch + - libgcrypt-rsa-no-blinding.patch + - libgcrypt-ecc-ecdsa-no-blinding.patch + - libgcrypt-PCT-DSA.patch + - libgcrypt-PCT-ECC.patch + - libgcrypt-PCT-RSA.patch + - libgcrypt-fips_selftest_trigger_file.patch + - libgcrypt-pthread-in-t-lock-test.patch + - libgcrypt-FIPS-hw-optimizations.patch + - libgcrypt-FIPS-module-version.patch + - libgcrypt-FIPS-disable-3DES.patch + - libgcrypt-FIPS-fix-regression-tests.patch + - libgcrypt-FIPS-RSA-keylen.patch + - libgcrypt-FIPS-RSA-keylen-tests.patch + - libgcrypt-FIPS-fix-gcry_mpi_sub_ui.patch + - libgcrypt-FIPS-verify-unsupported-KDF-test.patch + - libgcrypt-FIPS-HMAC-short-keylen.patch + - libgcrypt-FIPS-service-indicators.patch + - libgcrypt-FIPS-disable-DSA.patch + - libgcrypt-jitterentropy-3.3.0.patch + - libgcrypt-FIPS-Zeroize-hmac.patch + * Update libgcrypt.keyring + +------------------------------------------------------------------- +Thu Sep 8 10:34:53 UTC 2022 - Pedro Monreal + +- FIPS: Get most of the entropy from rndjent_poll [bsc#1202117] + * Add libgcrypt-FIPS-rndjent_poll.patch + * Rebase libgcrypt-jitterentropy-3.4.0.patch + +------------------------------------------------------------------- +Wed Sep 7 22:03:51 UTC 2022 - Pedro Monreal + +- FIPS: Check keylength in gcry_fips_indicator_kdf() [bsc#1190700] + * Consider approved keylength greater or equal to 112 bits. + * Add libgcrypt-FIPS-kdf-leylength.patch + +------------------------------------------------------------------- +Wed Sep 7 12:53:14 UTC 2022 - Pedro Monreal + +- FIPS: Zeroize buffer and digest in check_binary_integrity() + * Add libgcrypt-FIPS-Zeroize-hmac.patch [bsc#1191020] + +------------------------------------------------------------------- +Tue Aug 23 09:19:00 UTC 2022 - Pedro Monreal + +- FIPS: gpg/gpg2 gets out of core handler in FIPS mode while + typing Tab key to Auto-Completion. [bsc#1182983] + * Add libgcrypt-out-of-core-handler.patch + +------------------------------------------------------------------- +Mon Aug 8 11:33:03 UTC 2022 - Pedro Monreal + +- FIPS: Port libgcrypt to use jitterentropy [bsc#1202117, jsc#SLE-24941] + * Enable the jitter based entropy generator by default in random.conf + - Add libgcrypt-jitterentropy-3.3.0.patch + * Update the internal jitterentropy to version 3.4.0 + - Add libgcrypt-jitterentropy-3.4.0.patch + +------------------------------------------------------------------- +Mon Aug 1 07:27:35 UTC 2022 - Stephan Kulow + +- Fix reproducible build problems: + - Do not use %release in binaries (but use SOURCE_DATE_EPOCH) + - Fix date call messed up by spec-cleaner + +------------------------------------------------------------------- +Thu Apr 14 12:30:36 UTC 2022 - Dennis Knorr + +- FIPS: extend the service indicator [bsc#1190700] + * introduced a pk indicator function + * adapted the approved and non approved ciphersuites + * Add libgcrypt_indicators_changes.patch + * Add libgcrypt-indicate-shake.patch + +------------------------------------------------------------------- +Tue Mar 22 12:32:09 UTC 2022 - Pedro Monreal + +- FIPS: Implement a service indicator for asymmetric ciphers [bsc#1190700] + * Mark RSA public key encryption and private key decryption with + padding (e.g. OAEP, PKCS) as non-approved since RSA-OAEP lacks + peer key assurance validation requirements per SP800-56Brev2. + * Mark ECC as approved only for NIST curves P-224, P-256, P-384 + and P-521 with check for common NIST names and aliases. + * Mark DSA, ELG, EDDSA, ECDSA and ECDH as non-approved. + * Add libgcrypt-FIPS-SLI-pk.patch + * Rebase libgcrypt-FIPS-service-indicators.patch +- Run the regression tests also in FIPS mode. + * Disable tests for non-FIPS approved algos. + * Rebase: libgcrypt-FIPS-verify-unsupported-KDF-test.patch + +------------------------------------------------------------------- +Tue Feb 1 11:28:51 UTC 2022 - Pedro Monreal + +- FIPS: Disable DSA in FIPS mode [bsc#1195385] + * Upstream task: https://dev.gnupg.org/T5710 + * Add libgcrypt-FIPS-disable-DSA.patch + +------------------------------------------------------------------- +Wed Jan 19 08:36:58 UTC 2022 - Pedro Monreal + +- FIPS: Service level indicator [bsc#1190700] + * Provide an indicator to check wether the service utilizes an + approved cryptographic algorithm or not. + * Add patches: + - libgcrypt-FIPS-service-indicators.patch + - libgcrypt-FIPS-verify-unsupported-KDF-test.patch + - libgcrypt-FIPS-HMAC-short-keylen.patch + +------------------------------------------------------------------- +Tue Dec 7 09:41:01 UTC 2021 - Pedro Monreal + +- FIPS: Fix gcry_mpi_sub_ui subtraction [bsc#1193480] + * gcry_mpi_sub_ui: fix subtracting from negative value + * Add libgcrypt-FIPS-fix-gcry_mpi_sub_ui.patch + +------------------------------------------------------------------- +Tue Nov 30 09:42:23 UTC 2021 - Pedro Monreal + +- FIPS: Define an entropy source SP800-90B compliant [bsc#1185140] + * Disable jitter entropy by default in random.conf + * Disable only-urandom option by default in random.conf + +------------------------------------------------------------------- +Fri Nov 26 13:10:29 UTC 2021 - Pedro Monreal + +- FIPS: RSA KeyGen/SigGen fail with 4096 bit key sizes [bsc#1192240] + * rsa: Check RSA keylen constraints for key operations. + * rsa: Fix regression in not returning an error for prime generation. + * tests: Add 2k RSA key working in FIPS mode. + * tests: pubkey: Replace RSA key to one of 2k. + * tests: pkcs1v2: Skip tests with small keys in FIPS. + * Add patches: + - libgcrypt-FIPS-RSA-keylen.patch + - libgcrypt-FIPS-RSA-keylen-tests.patch + +------------------------------------------------------------------- +Mon Nov 8 10:21:39 UTC 2021 - Pedro Monreal + +- FIPS: Disable 3DES/Triple-DES in FIPS mode [bsc#1185138] + * Add libgcrypt-FIPS-disable-3DES.patch + +------------------------------------------------------------------- +Tue Nov 2 11:31:19 UTC 2021 - Pedro Monreal + +- FIPS: PBKDF requirements [bsc#1185137] + * The PBKDF2 selftests were introduced in libgcrypt version + 1.9.1 in the function selftest_pbkdf2() + * Upstream task: https://dev.gnupg.org/T5182 + +------------------------------------------------------------------- +Thu Oct 28 19:48:06 UTC 2021 - Pedro Monreal + +- FIPS: Fix regression tests in FIPS mode [bsc#1192131] + * Add libgcrypt-FIPS-fix-regression-tests.patch + * Upstream task: https://dev.gnupg.org/T5520 + +------------------------------------------------------------------- +Thu Sep 21 11:25:06 UTC 2021 - Pedro Monreal + +- FIPS: Provide a module name/identifier and version that can be + mapped to the validation records. [bsc#1190706] + * Add libgcrypt-FIPS-module-version.patch + * Upstream task: https://dev.gnupg.org/T5600 + +------------------------------------------------------------------- +Thu Sep 21 10:23:44 UTC 2021 - Pedro Monreal + +- FIPS: Enable hardware support also in FIPS mode [bsc#1187110] + * Add libgcrypt-FIPS-hw-optimizations.patch + * Upstream task: https://dev.gnupg.org/T5508 + +------------------------------------------------------------------- +Mon Aug 23 12:08:24 UTC 2021 - Pedro Monreal + +- Update to 1.9.4: + * Bug fixes: + - Fix Elgamal encryption for other implementations. [CVE-2021-33560] + - Fix alignment problem on macOS. + - Check the input length of the point in ECDH. + - Fix an abort in gcry_pk_get_param for "Curve25519". + * Other features: + - Add GCM and CCM to OID mapping table for AES. + * Upstream libgcrypt-CVE-2021-33560-fix-ElGamal-enc.patch + +------------------------------------------------------------------- +Mon Aug 23 10:11:55 UTC 2021 - Pedro Monreal + +- Remove not needed patch libgcrypt-sparcv9.diff + +------------------------------------------------------------------- +Thu Jul 15 12:53:45 UTC 2021 - Pedro Monreal + +- Fix building test t-lock with pthread. [bsc#1189745] + * Explicitly add -lpthread to compile the t-lock test. + * Add libgcrypt-pthread-in-t-lock-test.patch + +------------------------------------------------------------------- +Fri Jun 11 13:17:54 UTC 2021 - Pedro Monreal + +- Security fix: [bsc#1187212, CVE-2021-33560] + * cipher: Fix ElGamal encryption for other implementations. + * Exponent blinding was added in version 1.9.3. This patch + fixes ElGamal encryption, see: https://dev.gnupg.org/T5328 +- Add libgcrypt-CVE-2021-33560-fix-ElGamal-enc.patch + +------------------------------------------------------------------- +Tue Apr 20 08:46:11 UTC 2021 - Paolo Stivanin + +- libgcrypt 1.9.3: + * Bug fixes: + - Fix build problems on i386 using gcc-4.7. + - Fix checksum calculation in OCB decryption for AES on s390. + - Fix a regression in gcry_mpi_ec_add related to certain usages + of curve 25519. + - Fix a symbol not found problem on Apple M1. + - Fix for Apple iOS getentropy peculiarity. + - Make keygrip computation work for compressed points. + * Performance: + - Add x86_64 VAES/AVX2 accelerated implementation of Camellia. + - Add x86_64 VAES/AVX2 accelerated implementation of AES. + - Add VPMSUMD acceleration for GCM mode on PPC. + * Internal changes. + - Harden MPI conditional code against EM leakage. + - Harden Elgamal by introducing exponent blinding. + +------------------------------------------------------------------- +Wed Feb 17 09:49:55 UTC 2021 - Andreas Stieger + +- libgcrypt 1.9.2: + * Fix building with --disable-asm on x86 + * Check public key for ECDSA verify operation + * Make sure gcry_get_config (NULL) returns a nul-terminated + string + * Fix a memory leak in the ECDH code + * Fix a reading beyond end of input buffer in SHA2-avx2 +- remove obsolete texinfo packaging macros + +------------------------------------------------------------------- +Tue Feb 2 01:06:47 UTC 2021 - Pedro Monreal + +- Update to 1.9.1 + * *Fix exploitable bug* in hash functions introduced with + 1.9.0. [bsc#1181632, CVE-2021-3345] + * Return an error if a negative MPI is used with sexp scan + functions. + * Check for operational FIPS in the random and KDF functions. + * Fix compile error on ARMv7 with NEON disabled. + * Fix self-test in KDF module. + * Improve assembler checks for better LTO support. + * Fix 32-bit cross build on x86. + * Fix non-NEON ARM assembly implementation for SHA512. + * Fix build problems with the cipher_bulk_ops_t typedef. + * Fix Ed25519 private key handling for preceding ZEROs. + * Fix overflow in modular inverse implementation. + * Fix register access for AVX/AVX2 implementations of Blake2. + * Add optimized cipher and hash functions for s390x/zSeries. + * Use hardware bit counting functionx when available. + * Update DSA functions to match FIPS 186-3. + * New self-tests for CMACs and KDFs. + * Add bulk cipher functions for OFB and GCM modes. +- Update libgpg-error required version + +------------------------------------------------------------------- +Tue Feb 1 12:03:31 UTC 2021 - Pedro Monreal + +- Use the suffix variable correctly in get_hmac_path() +- Rebase libgcrypt-fips_selftest_trigger_file.patch + +------------------------------------------------------------------- +Mon Jan 25 12:38:35 UTC 2021 - Pedro Monreal + +- Add the global config file /etc/gcrypt/random.conf + * This file can be used to globally change parameters of the random + generator with the options: only-urandom and disable-jent. + +------------------------------------------------------------------- +Thu Jan 21 15:42:15 UTC 2021 - Pedro Monreal + +- Update to 1.9.0: + New stable branch of Libgcrypt with full API and ABI compatibility + to the 1.8 series. Release-info: https://dev.gnupg.org/T4294 + * New and extended interfaces: + - New curves Ed448, X448, and SM2. + - New cipher mode EAX. + - New cipher algo SM4. + - New hash algo SM3. + - New hash algo variants SHA512/224 and SHA512/256. + - New MAC algos for Blake-2 algorithms, the new SHA512 variants, + SM3, SM4 and for a GOST variant. + - New convenience function gcry_mpi_get_ui. + - gcry_sexp_extract_param understands new format specifiers to + directly store to integers and strings. + - New function gcry_ecc_mul_point and curve constants for Curve448 + and Curve25519. + - New function gcry_ecc_get_algo_keylen. + - New control code GCRYCTL_AUTO_EXPAND_SECMEM to allow growing the + secure memory area. + * Performance optimizations and bug fixes: See Release-info. + * Other features: + - Add OIDs from RFC-8410 as aliases for Ed25519 and Curve25519. + - Add mitigation against ECC timing attack CVE-2019-13627. + - Internal cleanup of the ECC implementation. + - Support reading EC point in compressed format for some curves. +- Rebase patches: + * libgcrypt-1.4.1-rijndael_no_strict_aliasing.patch + * libgcrypt-1.5.0-LIBGCRYPT_FORCE_FIPS_MODE-env.diff + * libgcrypt-1.6.1-use-fipscheck.patch + * drbg_test.patch + * libgcrypt-fipsdrv-enable-algo-for-dsa-sign.patch + * libgcrypt-FIPS-RSA-DSA-ECDSA-hashing-operation.patch + * libgcrypt-1.8.4-fips-keygen.patch + * libgcrypt-1.8.4-getrandom.patch + * libgcrypt-fix-tests-fipsmode.patch + * libgcrypt-global_init-constructor.patch + * libgcrypt-ecc-ecdsa-no-blinding.patch + * libgcrypt-PCT-RSA.patch + * libgcrypt-PCT-ECC.patch +- Remove patches: + * libgcrypt-unresolved-dladdr.patch + * libgcrypt-CVE-2019-12904-GCM-Prefetch.patch + * libgcrypt-CVE-2019-12904-GCM.patch + * libgcrypt-CVE-2019-12904-AES.patch + * libgcrypt-CMAC-AES-TDES-selftest.patch + * libgcrypt-1.6.1-fips-cfgrandom.patch + * libgcrypt-fips_rsa_no_enforced_mode.patch + +------------------------------------------------------------------- +Sat Oct 24 10:25:13 UTC 2020 - Andreas Stieger + +- libgcrypt 1.8.7: + * Support opaque MPI with gcry_mpi_print + * Fix extra entropy collection via clock_gettime, a fallback code + path for legacy hardware + +------------------------------------------------------------------- +Tue Jul 7 09:12:27 UTC 2020 - Pedro Monreal Gonzalez + +- Update to 1.8.6 + * mpi: Consider +0 and -0 the same in mpi_cmp + * mpi: Fix flags in mpi_copy for opaque MPI + * mpi: Fix the return value of mpi_invm_generic + * mpi: DSA,ECDSA: Fix use of mpi_invm + - Call mpi_invm before _gcry_dsa_modify_k + - Call mpi_invm before _gcry_ecc_ecdsa_sign + * mpi: Constant time mpi_inv with some conditions + - mpi/mpi-inv.c (mpih_add_n_cond, mpih_sub_n_cond, mpih_swap_cond) + - New: mpih_abs_cond, mpi_invm_odd + - Rename from _gcry_mpi_invm: mpi_invm_generic + - Use mpi_invm_odd for usual odd cases: _gcry_mpi_invm + * mpi: Abort on division by zero also in _gcry_mpi_tdiv_qr + * Fix wrong code execution in Poly1305 ARM/NEON implementation + - Set r14 to -1 at function entry: (_gcry_poly1305_armv7_neon_init_ext) + * Set vZZ.16b register to zero before use in armv8 gcm implementation + * random: Fix include of config.h + * Fix declaration of internal function _gcry_mpi_get_ui: Don't use ulong + * ecc: Fix wrong handling of shorten PK bytes + - Zeros are already recovered: (_gcry_ecc_mont_decodepoint) +- Update libgcrypt-ecc-ecdsa-no-blinding.patch + +------------------------------------------------------------------- +Tue May 19 11:25:37 UTC 2020 - Pedro Monreal Gonzalez + +- FIPS: RSA/DSA/ECC test_keys() print out debug messages [bsc#1171872] + * Print the debug messages in test_keys() only in debug mode. +- Update patches: libgcrypt-PCT-RSA.patch libgcrypt-PCT-DSA.patch + libgcrypt-PCT-ECC.patch + +------------------------------------------------------------------- +Mon Apr 27 08:55:12 UTC 2020 - Pedro Monreal Gonzalez + +- FIPS: libgcrypt: Double free in test_keys() on failed signature + verification [bsc#1169944] + * Use safer gcry_mpi_release() instead of mpi_free() +- Update patches: + * libgcrypt-PCT-DSA.patch + * libgcrypt-PCT-RSA.patch + * libgcrypt-PCT-ECC.patch + +------------------------------------------------------------------- +Thu Apr 16 16:45:23 UTC 2020 - Vítězslav Čížek + +- Ship the FIPS checksum file in the shared library package and + create a separate trigger file for the FIPS selftests (bsc#1169569) + * add libgcrypt-fips_selftest_trigger_file.patch + * refresh libgcrypt-global_init-constructor.patch +- Remove libgcrypt-binary_integrity_in_non-FIPS.patch obsoleted + by libgcrypt-global_init-constructor.patch + +------------------------------------------------------------------- +Wed Apr 15 13:55:27 UTC 2020 - Pedro Monreal Gonzalez + +- FIPS: Verify that the generated signature and the original input + differ in test_keys function for RSA, DSA and ECC: [bsc#1165539] +- Add zero-padding when qx and qy have different lengths when + assembling the Q point from affine coordinates. +- Refreshed patches: + * libgcrypt-PCT-DSA.patch + * libgcrypt-PCT-RSA.patch + * libgcrypt-PCT-ECC.patch + +------------------------------------------------------------------- +Mon Mar 30 10:48:02 UTC 2020 - Pedro Monreal Gonzalez + +- FIPS: Switch the PCT to use the new signature operation [bsc#1165539] + * Patches for DSA, RSA and ECDSA test_keys functions: + - libgcrypt-PCT-DSA.patch + - libgcrypt-PCT-RSA.patch + - libgcrypt-PCT-ECC.patch +- Update patch: libgcrypt-FIPS-RSA-DSA-ECDSA-hashing-operation.patch + +------------------------------------------------------------------- +Thu Mar 26 18:09:47 UTC 2020 - Pedro Monreal Gonzalez + +- FIPS: Run self-tests from constructor during power-on [bsc#1166748] + * Set up global_init as the constructor function: + - libgcrypt-global_init-constructor.patch + * Relax the entropy requirements on selftest. This is especially + important for virtual machines to boot properly before the RNG + is available: + - libgcrypt-random_selftests-testentropy.patch + - libgcrypt-rsa-no-blinding.patch + - libgcrypt-ecc-ecdsa-no-blinding.patch + * Fix benchmark regression test in FIPS mode: + - libgcrypt-FIPS-GMAC_AES-benckmark.patch + +------------------------------------------------------------------- +Thu Mar 12 16:54:33 UTC 2020 - Pedro Monreal Gonzalez + +- Remove check not needed in _gcry_global_constructor [bsc#1164950] + * Update libgcrypt-Restore-self-tests-from-constructor.patch + +------------------------------------------------------------------- +Tue Feb 25 22:13:24 UTC 2020 - Pedro Monreal Gonzalez + +- FIPS: Run the self-tests from the constructor [bsc#1164950] + * Add libgcrypt-invoke-global_init-from-constructor.patch + +------------------------------------------------------------------- +Fri Jan 17 17:35:15 UTC 2020 - Pedro Monreal Gonzalez + +- FIPS: libgcrypt DSA PQG parameter generation: Missing value [bsc#1161219] +- FIPS: libgcrypt DSA PQG verification incorrect results [bsc#1161215] +- FIPS: libgcrypt RSA siggen/keygen: 4k not supported [bsc#1161220] + * Add patch from Fedora libgcrypt-1.8.4-fips-keygen.patch + +------------------------------------------------------------------- +Wed Dec 11 10:18:23 UTC 2019 - Pedro Monreal Gonzalez + +- FIPS: RSA/DSA/ECDSA are missing hashing operation [bsc#1155337] + * Add libgcrypt-FIPS-RSA-DSA-ECDSA-hashing-operation.patch + +------------------------------------------------------------------- +Wed Nov 27 14:01:01 UTC 2019 - Pedro Monreal Gonzalez + +- Fix tests in FIPS mode: + * Fix tests: basic benchmark bench-slope pubkey t-cv25519 t-secmem + * Add patch libgcrypt-fix-tests-fipsmode.patch + +------------------------------------------------------------------- +Tue Nov 26 18:48:20 UTC 2019 - Pedro Monreal Gonzalez + +- Fix test dsa-rfc6979 in FIPS mode: + * Disable tests in elliptic curves with 192 bits which are not + recommended in FIPS mode + * Add patch libgcrypt-dsa-rfc6979-test-fix.patch + +------------------------------------------------------------------- +Tue Nov 12 11:05:02 UTC 2019 - Pedro Monreal Gonzalez + +- CMAC AES and TDES FIPS self-tests: + * CMAC AES self test missing [bsc#1155339] + * CMAC TDES self test missing [bsc#1155338] +- Add libgcrypt-CMAC-AES-TDES-selftest.patch + +------------------------------------------------------------------- +Fri Aug 30 14:17:48 UTC 2019 - Andreas Stieger + +- libgcrypt 1.8.5: + * CVE-2019-13627: mitigation against an ECDSA timing attack (boo#1148987) + * Improve ECDSA unblinding + * Provide a pkg-config file + +------------------------------------------------------------------- +Wed Jun 26 06:52:54 UTC 2019 - Jason Sikes + +- Fixed redundant fips tests in some situations causing sudo to stop + working when pam-kwallet is installed. bsc#1133808 + * Added libgcrypt-1.8.4-fips_ctor_skip_integrity_check.patch + * Removed libgcrypt-fips_run_selftest_at_constructor.patch + because it was obsoleted by libgcrypt-1.8.3-fips-ctor.patch + * Removed libgcrypt-fips_ignore_FIPS_MODULE_PATH.patch + because it was obsoleted by libgcrypt-1.8.4-fips_ctor_skip_integrity_check.patch + +------------------------------------------------------------------- +Fri Jun 21 16:53:07 UTC 2019 - Pedro Monreal Gonzalez + +- Fixed env-script-interpreter in cavs_driver.pl + +------------------------------------------------------------------- +Fri Jun 21 16:39:00 UTC 2019 - Pedro Monreal Gonzalez + +- Security fix: [bsc#1138939, CVE-2019-12904] + * The C implementation of AES is vulnerable to a flush-and-reload + side-channel attack because physical addresses are available to + other processes. (The C implementation is used on platforms where + an assembly-language implementation is unavailable.) + * Added patches: + - libgcrypt-CVE-2019-12904-GCM-Prefetch.patch + - libgcrypt-CVE-2019-12904-GCM.patch + - libgcrypt-CVE-2019-12904-AES.patch + +------------------------------------------------------------------- +Fri Apr 26 06:47:45 UTC 2019 - Jason Sikes + +- do not try to open /dev/urandom if getrandom() works + * Added libgcrypt-1.8.4-getrandom.patch +- Drop libgcrypt-init-at-elf-load-fips.patch obsoleted + by libgcrypt-1.8.3-fips-ctor.patch + +------------------------------------------------------------------- +Tue Apr 23 12:38:40 UTC 2019 - Jason Sikes + +- Restored libgcrypt-binary_integrity_in_non-FIPS.patch sans section that + was partially causing bsc#1131183. +- Fixed race condition in multi-threaded applications by allowing a FSM state + transition to the current state. This means some tests are run twice. + * Added libgcrypt-1.8.4-allow_FSM_same_state.patch +- Fixed an issue in malloc/free wrappers so that memory created by the malloc() + wrappers will be destroyed using the free() wrappers. + * Added libgcrypt-1.8.4-use_xfree.patch + +------------------------------------------------------------------- +Fri Apr 5 21:56:00 UTC 2019 - Jason Sikes + +- removed libgcrypt-binary_integrity_in_non-FIPS.patch since it was breaking + libotr. bsc#1131183 + +------------------------------------------------------------------- +Tue Mar 26 16:30:23 UTC 2019 - Vítězslav Čížek + +- libgcrypt-1.8.3-fips-ctor.patch changed the way the fips selftests + are invoked as well as the state transition, adjust the code so + a missing checksum file is not an issue in non-FIPS mode (bsc#1097073) + * update libgcrypt-binary_integrity_in_non-FIPS.patch + +------------------------------------------------------------------- +Tue Mar 26 16:25:18 UTC 2019 - Vítězslav Čížek + +- Enforce the minimal RSA keygen size in fips mode (bsc#1125740) + * add libgcrypt-fips_rsa_no_enforced_mode.patch + +------------------------------------------------------------------- +Fri Mar 22 14:13:05 UTC 2019 - Vítězslav Čížek + +- Don't run full self-tests from constructor (bsc#1097073) + * Don't call global_init() from the constructor, _gcry_global_constructor() + from libgcrypt-1.8.3-fips-ctor.patch takes care of the binary + integrity check instead. + * Only the binary checksum will be verified, the remaining + self-tests will be run upon the library initialization +- Add libgcrypt-fips_ignore_FIPS_MODULE_PATH.patch +- Drop libgcrypt-init-at-elf-load-fips.patch and + libgcrypt-fips_run_selftest_at_constructor.patch obsoleted + by libgcrypt-1.8.3-fips-ctor.patch + +------------------------------------------------------------------- +Thu Mar 7 10:53:40 UTC 2019 - Pedro Monreal Gonzalez + +- Skip all the self-tests except for binary integrity when called + from the constructor (bsc#1097073) + * Added libgcrypt-1.8.3-fips-ctor.patch from Fedora + +------------------------------------------------------------------- +Mon Nov 26 17:09:47 UTC 2018 - Vítězslav Čížek + +- Fail selftests when checksum file is missing in FIPS mode only + (bsc#1117355) + * add libgcrypt-binary_integrity_in_non-FIPS.patch + +------------------------------------------------------------------- +Sun Oct 28 18:57:53 UTC 2018 - astieger@suse.com + +- libgcrypt 1.8.4: + * Fix infinite loop with specific application implementations + * Fix possible leak of a few bits of secret primes to pageable + memory + * Fix possible hang in the RNG (1.8.3) + * Always make use of getrandom if possible and then use + its /dev/urandom behaviour + +------------------------------------------------------------------- +Mon Jul 2 10:38:42 UTC 2018 - schwab@suse.de + +- libgcrypt-1.6.3-aliasing.patch, libgcrypt-ppc64.patch, + libgcrypt-strict-aliasing.patch: Remove obsolete patches +- libgcrypt-1.4.1-rijndael_no_strict_aliasing.patch: Rediff +- Reenable testsuite + +------------------------------------------------------------------- +Wed Jun 13 10:46:33 UTC 2018 - kbabioch@suse.com + +- Update to version 1.8.3: + - Use blinding for ECDSA signing to mitigate a novel side-channel + attack. (CVE-2018-0495 bsc#1097410) + - Fix incorrect counter overflow handling for GCM when using an IV + size other than 96 bit. + - Fix incorrect output of AES-keywrap mode for in-place encryption + on some platforms. + - Fix the gcry_mpi_ec_curve_point point validation function. + - Fix rare assertion failure in gcry_prime_check. +- Applied spec-cleaner + +------------------------------------------------------------------- +Wed May 2 14:31:07 UTC 2018 - pmonrealgonzalez@suse.com + +- Suggest libgcrypt20-hmac for package libgcrypt20 to ensure they + are installed in the right order. [bsc#1090766] + +------------------------------------------------------------------- +Thu Mar 29 06:37:44 UTC 2018 - pmonrealgonzalez@suse.com + +- Extended the fipsdrv dsa-sign and dsa-verify commands with the + --algo parameter for the FIPS testing of DSA SigVer and SigGen + (bsc#1064455). + * Added libgcrypt-fipsdrv-enable-algo-for-dsa-sign.patch + * Added libgcrypt-fipsdrv-enable-algo-for-dsa-verify.patch + +------------------------------------------------------------------- +Thu Feb 22 15:10:36 UTC 2018 - fvogt@suse.com + +- Use %license (boo#1082318) + +------------------------------------------------------------------- +Wed Dec 13 20:09:28 UTC 2017 - astieger@suse.com + +- libgcrypt 1.8.2: + * Fix fatal out of secure memory status in the s-expression + parser on heavy loaded systems. + * Add auto expand secmem feature or use by GnuPG 2.2.4 + +------------------------------------------------------------------- +Mon Aug 28 17:54:24 UTC 2017 - astieger@suse.com + +- libgcrypt 1.8.1: + * Mitigate a local side-channel attack on Curve25519 dubbed "May + the Fourth be With You" CVE-2017-0379 bsc#1055837 + * Add more extra bytes to the pool after reading a seed file + * Add the OID SHA384WithECDSA from RFC-7427 to SHA-384 + * Fix build problems with the Jitter RNG + * Fix assembler code build problems on Rasbian (ARMv8/AArch32-CE) + +------------------------------------------------------------------- +Mon Jul 24 23:43:40 UTC 2017 - jengelh@inai.de + +- RPM group fixes. + +------------------------------------------------------------------- +Fri Jul 21 15:50:14 UTC 2017 - astieger@suse.com + +- libgcrypt 1.8.0: + * New cipher mode XTS + * New hash function Blake-2 + * New function gcry_mpi_point_copy. + * New function gcry_get_config. + * GCRYCTL_REINIT_SYSCALL_CLAMP allows to init nPth after Libgcrypt. + * New gobal configuration file /etc/gcrypt/random.conf. + * GCRYCTL_PRINT_CONFIG does now also print build information for + libgpg-error and the used compiler version. + * GCRY_CIPHER_MODE_CFB8 is now supported. + * A jitter based entropy collector is now used in addition to the + other entropy collectors. + * Optimized gcry_md_hash_buffers for SHA-256 and SHA-512. + random pool lock). + * Interface changes relative to the 1.7.0 release: + gcry_get_config NEW function. + gcry_mpi_point_copy NEW function. + GCRYCTL_REINIT_SYSCALL_CLAMP NEW macro. + GCRY_MD_BLAKE2B_512 NEW constant. + GCRY_MD_BLAKE2B_384 NEW constant. + GCRY_MD_BLAKE2B_256 NEW constant. + GCRY_MD_BLAKE2B_160 NEW constant. + GCRY_MD_BLAKE2S_256 NEW constant. + GCRY_MD_BLAKE2S_224 NEW constant. + GCRY_MD_BLAKE2S_160 NEW constant. + GCRY_MD_BLAKE2S_128 NEW constant. + GCRY_CIPHER_MODE_XTS NEW constant. + gcry_md_info DEPRECATED. +- Refresh patch libgcrypt-1.6.3-aliasing.patch + +------------------------------------------------------------------- +Thu Jun 29 09:49:44 UTC 2017 - astieger@suse.com + +- libgcrypt 1.7.8: + * CVE-2017-7526: Mitigate a flush+reload side-channel attack on + RSA secret keys (bsc#1046607) + +------------------------------------------------------------------- +Sun Jun 4 19:26:12 UTC 2017 - astieger@suse.com + +- libgcrypt 1.7.7: + * Fix possible timing attack on EdDSA session key (previously + patched, drop libgcrypt-secure-EdDSA-session-key.patch) + * Fix long standing bug in secure memory implementation which + could lead to a segv on free + +------------------------------------------------------------------- +Fri Jun 2 10:05:18 UTC 2017 - pmonrealgonzalez@suse.com + +- Added libgcrypt-secure-EdDSA-session-key.patch [bsc#1042326] + * Store the session key in secure memory to ensure that constant + time point operations are used in the MPI library. + +------------------------------------------------------------------- +Fri Jan 20 09:41:15 UTC 2017 - rmaliska@suse.com + +- libgcrypt 1.7.6: + * Fix counter operand from read-only to read/write + * Fix too large jump alignment in mpih-rshift + +------------------------------------------------------------------- +Thu Dec 15 10:32:18 UTC 2016 - astieger@suse.com + +- libgcrypt 1.7.5: + * Fix regression in mlock detection introduced with 1.7.4 + +------------------------------------------------------------------- +Tue Dec 13 12:20:47 UTC 2016 - astieger@suse.com + +- libgcrypt 1.7.4: + * ARMv8/AArch32 performance improvements for AES, GCM, SHA-256, + and SHA-1. + * Add ARMv8/AArch32 assembly implementation for Twofish and + Camellia. + * Add bulk processing implementation for ARMv8/AArch32. + * Add Stribog OIDs. + * Improve the DRBG performance and sync the code with the Linux + version. + * When secure memory is requested by the MPI functions or by + gcry_xmalloc_secure, they do not anymore lead to a fatal error + if the secure memory pool is used up. Instead new pools are + allocated as needed. These new pools are not protected against + being swapped out (mlock can't be used). Mitigation for + minor confidentiality issues is encryption swap space. + * Fix GOST 28147 CryptoPro-B S-box. + * Fix error code handling of mlock calls. + +------------------------------------------------------------------- +Sat Aug 20 10:38:15 UTC 2016 - mpluskal,vcizek,astieger}@suse.com + +- libgcrypt 1.7.3: + * security issue already fixes with 1.6.6 + * Fix building of some asm modules with older compilers and CPUs. + * ARMv8/AArch32 improvements for AES, GCM, SHA-256, and SHA-1. +- includes changes from libgcrypt 1.7.2: + * Bug fixes: + - Fix setting of the ECC cofactor if parameters are specified. + - Fix memory leak in the ECC code. + - Remove debug message about unsupported getrandom syscall. + - Fix build problems related to AVX use. + - Fix bus errors on ARM for Poly1305, ChaCha20, AES, and SHA-512. + * Internal changes: + - Improved fatal error message for wrong use of gcry_md_read. + - Disallow symmetric encryption/decryption if key is not set. +- includes changes from 1.7.1: + * Bug fixes: + - Fix ecc_verify for cofactor support. + - Fix portability bug when using gcc with Solaris 9 SPARC. + - Build fix for OpenBSD/amd64 + - Add OIDs to the Serpent ciphers. + * Internal changes: + - Use getrandom system call on Linux if available. + - Blinding is now also used for RSA signature creation. + - Changed names of debug envvars +- includes changes from 1.7.0: + * New algorithms and modes: + - SHA3-224, SHA3-256, SHA3-384, SHA3-512, and MD2 hash algorithms. + - SHAKE128 and SHAKE256 extendable-output hash algorithms. + - ChaCha20 stream cipher. + - Poly1305 message authentication algorithm + - ChaCha20-Poly1305 Authenticated Encryption with Associated Data + mode. + - OCB mode. + - HMAC-MD2 for use by legacy applications. + * New curves for ECC: + - Curve25519. + - sec256k1. + - GOST R 34.10-2001 and GOST R 34.10-2012. + * Performance: + - Improved performance of KDF functions. + - Assembler optimized implementations of Blowfish and Serpent on + ARM. + - Assembler optimized implementation of 3DES on x86. + - Improved AES using the SSSE3 based vector permutation method by + Mike Hamburg. + - AVX/BMI is used for SHA-1 and SHA-256 on x86. This is for SHA-1 + about 20% faster than SSSE3 and more than 100% faster than the + generic C implementation. + - 40% speedup for SHA-512 and 72% for SHA-1 on ARM Cortex-A8. + - 60-90% speedup for Whirlpool on x86. + - 300% speedup for RIPE MD-160. + - Up to 11 times speedup for CRC functions on x86. + * Other features: + - Improved ECDSA and FIPS 186-4 compliance. + - Support for Montgomery curves. + - gcry_cipher_set_sbox to tweak S-boxes of the gost28147 cipher + algorithm. + - gcry_mpi_ec_sub to subtract two points on a curve. + - gcry_mpi_ec_decode_point to decode an MPI into a point object. + - Emulation for broken Whirlpool code prior to 1.6.0. [from 1.6.1] + - Flag "pkcs1-raw" to enable PCKS#1 padding with a user supplied + hash part. + - Parameter "saltlen" to set a non-default salt length for RSA PSS. + - A SP800-90A conforming DRNG replaces the former X9.31 alternative + random number generator. + - Map deprecated RSA algo number to the RSA algo number for better + backward compatibility. [from 1.6.2] + - Use ciphertext blinding for Elgamal decryption [CVE-2014-3591]. + See http://www.cs.tau.ac.il/~tromer/radioexp/ for details. + [from 1.6.3] + - Fixed data-dependent timing variations in modular exponentiation + [related to CVE-2015-0837, Last-Level Cache Side-Channel Attacks + are Practical]. [from 1.6.3] + - Flag "no-keytest" for ECC key generation. Due to a bug in + the parser that flag will also be accepted but ignored by older + version of Libgcrypt. [from 1.6.4] + - Speed up the random number generator by requiring less extra + seeding. [from 1.6.4] + - Always verify a created RSA signature to avoid private key leaks + due to hardware failures. [from 1.6.4] + - Mitigate side-channel attack on ECDH with Weierstrass curves + [CVE-2015-7511]. See http://www.cs.tau.ac.IL/~tromer/ecdh/ for + details. [from 1.6.5] + * Internal changes: + - Moved locking out to libgpg-error. + - Support of the SYSROOT envvar in the build system. + - Refactor some code. + - The availability of a 64 bit integer type is now mandatory. + * Bug fixes: + - Fixed message digest lookup by OID (regression in 1.6.0). + - Fixed a build problem on NetBSD + - Fixed some asm build problems and feature detection bugs. + * Interface changes relative to the 1.6.0 release: + gcry_cipher_final NEW macro. + GCRY_CIPHER_MODE_CFB8 NEW constant. + GCRY_CIPHER_MODE_OCB NEW. + GCRY_CIPHER_MODE_POLY1305 NEW. + gcry_cipher_set_sbox NEW macro. + gcry_mac_get_algo NEW. + GCRY_MAC_HMAC_MD2 NEW. + GCRY_MAC_HMAC_SHA3_224 NEW. + GCRY_MAC_HMAC_SHA3_256 NEW. + GCRY_MAC_HMAC_SHA3_384 NEW. + GCRY_MAC_HMAC_SHA3_512 NEW. + GCRY_MAC_POLY1305 NEW. + GCRY_MAC_POLY1305_AES NEW. + GCRY_MAC_POLY1305_CAMELLIA NEW. + GCRY_MAC_POLY1305_SEED NEW. + GCRY_MAC_POLY1305_SERPENT NEW. + GCRY_MAC_POLY1305_TWOFISH NEW. + gcry_md_extract NEW. + GCRY_MD_FLAG_BUGEMU1 NEW [from 1.6.1]. + GCRY_MD_GOSTR3411_CP NEW. + GCRY_MD_SHA3_224 NEW. + GCRY_MD_SHA3_256 NEW. + GCRY_MD_SHA3_384 NEW. + GCRY_MD_SHA3_512 NEW. + GCRY_MD_SHAKE128 NEW. + GCRY_MD_SHAKE256 NEW. + gcry_mpi_ec_decode_point NEW. + gcry_mpi_ec_sub NEW. + GCRY_PK_EDDSA NEW constant. + GCRYCTL_GET_TAGLEN NEW. + GCRYCTL_SET_SBOX NEW. + GCRYCTL_SET_TAGLEN NEW. +- Apply libgcrypt-1.6.3-aliasing.patch only on big-endian + architectures +- update drbg_test.patch and install cavs testing directory again +- As DRBG is upstream, drop pateches: + v9-0001-SP800-90A-Deterministic-Random-Bit-Generator.patch + 0002-Compile-DRBG.patch + 0003-Function-definitions-of-interfaces-for-random.c.patch + 0004-Invoke-DRBG-from-common-libgcrypt-RNG-code.patch + 0005-Function-definitions-for-gcry_control-callbacks.patch + 0006-DRBG-specific-gcry_control-requests.patch + v9-0007-User-interface-to-DRBG.patch + libgcrypt-fix-rng.patch +- drop obsolete: + libgcrypt-fips-dsa.patch + libgcrypt-fips_ecdsa.patch + +------------------------------------------------------------------- +Wed Aug 17 18:21:44 UTC 2016 - astieger@suse.com + +- libgcrypt 1.6.6: + * fix CVE-2016-6313: Issue in the mixing functions of the random + number generators allowed an attacker who obtained a number of + bytes from the standard RNG to predict some of the next ouput. + (bsc#994157) + +------------------------------------------------------------------- +Mon May 16 14:37:45 UTC 2016 - pjanouch@suse.de + +- remove conditionals for unsupported distributions (before 13.2), + it would not build anyway because of new dependencies + +------------------------------------------------------------------- +Mon May 16 12:36:14 UTC 2016 - pjanouch@suse.de + +- make the -hmac package depend on the same version of the library, + fixing bsc#979629 FIPS: system fails to reboot after installing + fips pattern + +------------------------------------------------------------------- +Tue Feb 9 20:51:59 UTC 2016 - astieger@suse.com + +- update to 1.6.5: + * CVE-2015-7511: Mitigate side-channel attack on ECDH with + Weierstrass curves (boo#965902) + +------------------------------------------------------------------- +Sat Oct 10 11:56:08 UTC 2015 - astieger@suse.com + +- follow-up to libgcrypt 1.6.4 update: sosuffix is 20.0.4 + +------------------------------------------------------------------- +Tue Sep 8 08:03:19 UTC 2015 - vcizek@suse.com + +- update to 1.6.4 +- fixes libgcrypt equivalent of CVE-2015-5738 (bsc#944456) + * Speed up the random number generator by requiring less extra + seeding. + * New flag "no-keytest" for ECC key generation. Due to a bug in the + parser that flag will also be accepted but ignored by older version + of Libgcrypt. + * Always verify a created RSA signature to avoid private key leaks + due to hardware failures. + * Other minor bug fixes. + +------------------------------------------------------------------- +Tue Jun 23 15:15:30 UTC 2015 - dvaleev@suse.com + +- Fix gpg2 tests on BigEndian architectures: s390x ppc64 + libgcrypt-1.6.3-aliasing.patch + +------------------------------------------------------------------- +Sun Mar 1 21:16:26 UTC 2015 - astieger@suse.com + +- fix sosuffix for 1.6.3 (20.0.3) + +------------------------------------------------------------------- +Sat Feb 28 19:31:10 UTC 2015 - astieger@suse.com + +- libgcrypt 1.6.3 [bnc#920057]: + * Use ciphertext blinding for Elgamal decryption [CVE-2014-3591]. + * Fixed data-dependent timing variations in modular exponentiation + [related to CVE-2015-0837, Last-Level Cache Side-Channel Attacks + are Practical]. +- update upstream signing keyring + +------------------------------------------------------------------- +Fri Feb 6 18:42:28 UTC 2015 - coolo@suse.com + +- making the build reproducible - see + http://lists.gnupg.org/pipermail/gnupg-commits/2014-September/010683.html + for a very similiar problem + +------------------------------------------------------------------- +Fri Feb 6 18:38:55 UTC 2015 - dimstar@opensuse.org + +- Move %install_info_delete calls from postun to preun: the files + must still be present to be parsed. +- Fix the names passed to install_info for gcrypt.info-[12].gz + instead of gcrypt-[12].info.gz. + +------------------------------------------------------------------- +Fri Feb 6 18:30:26 UTC 2015 - coolo@suse.com + +- fix filename for info pages in %post scripts + +------------------------------------------------------------------- +Wed Nov 5 20:37:24 UTC 2014 - andreas.stieger@gmx.de + +- libgcrypt 1.6.2: + * Map deprecated RSA algo number to the RSA algo number for better + backward compatibility. + * Support a 0x40 compression prefix for EdDSA. + * Improve ARM hardware feature detection and building. + * Fix building for the x32 ABI platform. + * Fix some possible NULL deref bugs. +- remove libgcrypt-1.6.0-use-intenal-functions.patch, upstream + via xtrymalloc macro +- remove libgcrypt-fixed-sizet.patch, upstream +- adjust libgcrypt-1.6.1-use-fipscheck.patch for xtrymalloc change + +------------------------------------------------------------------- +Sun Sep 21 10:08:39 UTC 2014 - vcizek@suse.com + +- disabled curve P-192 in FIPS mode (bnc#896202) + * added libgcrypt-fips_ecdsa.patch +- don't use SHA-1 for ECDSA in FIPS mode +- also run the fips self tests only in FIPS mode + +------------------------------------------------------------------- +Tue Sep 16 13:56:01 UTC 2014 - vcizek@suse.com + +- run the fips self tests at the constructor code + * added libgcrypt-fips_run_selftest_at_constructor.patch + +------------------------------------------------------------------- +Tue Sep 16 12:17:17 UTC 2014 - vcizek@suse.com + +- rewrite the DSA-2 code to be FIPS 186-4 compliant (bnc#894216) + * added libgcrypt-fips-dsa.patch + * install fips186_dsa +- use 2048 bit keys in selftests_dsa + +------------------------------------------------------------------- +Mon Sep 1 10:57:06 UTC 2014 - vcizek@suse.com + +- fix an issue in DRBG patchset + * size_t type is 32-bit on 32-bit systems +- fix a potential NULL pointer deference in DRBG patchset + * patches from https://bugs.g10code.com/gnupg/issue1701 +- added v9-0001-SP800-90A-Deterministic-Random-Bit-Generator.patch +- added v9-0007-User-interface-to-DRBG.patch +- removed v7-0001-SP800-90A-Deterministic-Random-Bit-Generator.patch +- removed v7-0007-User-interface-to-DRBG.patch +- add a subpackage for CAVS testing + * add cavs_driver.pl and cavs-test.sh from the kernel cavs package + * added drbg_test.patch + +------------------------------------------------------------------- +Tue Aug 12 07:43:19 UTC 2014 - meissner@suse.com + +- split off the -hmac package that contains the checksums + +------------------------------------------------------------------- +Mon May 26 12:05:17 UTC 2014 - meissner@suse.com + +- libgcrypt-fix-rng.patch: make drbg work again in FIPS mode. +- libgcrypt-1.6.1-use-fipscheck.patch: library to test is libgcrypt.so.20 + and not libgcrypt.so.11 +- libgcrypt-init-at-elf-load-fips.patch: initialize globally on ELF + DSO loading to meet FIPS requirements. + +------------------------------------------------------------------- +Tue May 13 10:47:51 UTC 2014 - vcizek@suse.com + +- add new 0007-User-interface-to-DRBG.patch from upstream + * fixes bnc#877233 + * supersedes the patch from previous entry + +------------------------------------------------------------------- +Sun May 12 13:25:33 UTC 2014 - tittiatcoke@gmail.com + +- Correct patch 0007-User-interface-to-DRBG.patch so that the + struct used in the route matches the header of the function + +------------------------------------------------------------------- +Tue May 6 13:28:33 UTC 2014 - vcizek@suse.com + +- add support for SP800-90A DRBG (fate#316929, bnc#856312) + * patches by Stephan Mueller (http://www.chronox.de/drbg.html): + 0001-SP800-90A-Deterministic-Random-Bit-Generator.patch.bz2 + 0002-Compile-DRBG.patch + 0003-Function-definitions-of-interfaces-for-random.c.patch + 0004-Invoke-DRBG-from-common-libgcrypt-RNG-code.patch + 0005-Function-definitions-for-gcry_control-callbacks.patch + 0006-DRBG-specific-gcry_control-requests.patch + 0007-User-interface-to-DRBG.patch + * only after 13.1 (the patches need libgpg-error 1.13) +- drop libgcrypt-fips-allow-legacy.patch (not needed and wasn't + applied anyway) + +------------------------------------------------------------------- +Thu Apr 3 12:04:46 UTC 2014 - tchvatal@suse.com + +- Cleanup with spec-cleaner to sort out. +- Really apply ppc64 patch as it was ommited probably by mistake. + +------------------------------------------------------------------- +Thu Mar 27 14:57:22 UTC 2014 - meissner@suse.com + +- FIPS changes (from Fedora): + - replaced libgcrypt-1.5.0-etc_gcrypt_rngseed-symlink.diff by + libgcrypt-1.6.1-fips-cfgrandom.patch + - libgcrypt-fixed-sizet.patch: fixed an int type for -flto + - libgcrypt-1.6.1-use-fipscheck.patch: use the fipscheck binary + - libgcrypt-1.6.1-fips-cavs.patch: add CAVS tests +- use fipscheck only after 13.1 +- libgcrypt-fips-allow-legacy.patch: attempt to allow some + legacy algorithms for gpg2 usage even in FIPS mode. + (currently not applied) + +------------------------------------------------------------------- +Thu Jan 30 13:29:49 UTC 2014 - idonmez@suse.com + +- Drop arm-missing-files.diff, fixed upstream + +------------------------------------------------------------------- +Wed Jan 29 18:40:49 UTC 2014 - andreas.stieger@gmx.de + +- libgcrypt 1.6.1, a bugfix release with the folloging fixes: + * Added emulation for broken Whirlpool code prior to 1.6.0. + * Improved performance of KDF functions. + * Improved ECDSA compliance. + * Fixed message digest lookup by OID (regression in 1.6.0). + * Fixed memory leaks in ECC code. + * Fixed some asm build problems and feature detection bugs. + * Interface changes relative to the 1.6.0 release: + GCRY_MD_FLAG_BUGEMU1 NEW (minor API change). + +------------------------------------------------------------------- +Fri Jan 3 16:36:21 UTC 2014 - dmueller@suse.com + +- add arm-missing-files.diff: Add missing files to fix build + +------------------------------------------------------------------- +Fri Jan 3 09:43:39 UTC 2014 - mvyskocil@suse.com + +- fix bnc#856915: can't open /dev/urandom + * correct libgcrypt-1.5.0-etc_gcrypt_rngseed-symlink.diff +- require libgpg-error 1.11 or higher + +------------------------------------------------------------------- +Thu Dec 19 13:53:21 UTC 2013 - mvyskocil@suse.com + +- fix dependency for 32bit devel package +- name hmac files according soname +- fix hmac subpackage dependency + +------------------------------------------------------------------- +Thu Dec 19 09:03:21 UTC 2013 - mvyskocil@suse.com + +- update to 1.6. + * Removed the long deprecated gcry_ac interface. Thus Libgcrypt is + not anymore ABI compatible to previous versions if they used the ac + interface. Check NEWS in libgcrypt-devel for removed interfaces. + * Removed the module register subsystem. + * The deprecated message digest debug macros have been removed. Use + gcry_md_debug instead. + * Removed deprecated control codes. + * Improved performance of most cipher algorithms as well as for the + SHA family of hash functions. + * Added support for the IDEA cipher algorithm. + * Added support for the Salsa20 and reduced Salsa20/12 stream ciphers. + * Added limited support for the GOST 28147-89 cipher algorithm. + * Added support for the GOST R 34.11-94 and R 34.11-2012 (Stribog) + hash algorithms. + * Added a random number generator to directly use the system's RNG. + Also added an interface to prefer the use of a specified RNG. + * Added support for the SCRYPT algorithm. + * Mitigated the Yarom/Falkner flush+reload side-channel attack on RSA + secret keys. See [CVE-2013-4242]. + * Added support for Deterministic DSA as per RFC-6969. + * Added support for curve Ed25519. + * Added a scatter gather hash convenience function. + * Added several MPI amd SEXP helper functions. + * Added support for negative numbers to gcry_mpi_print, + gcry_mpi_aprint and gcry_mpi_scan. + * The algorithm ids GCRY_PK_ECDSA and GCRY_PK_ECDH are now + deprecated. Use GCRY_PK_ECC if you need an algorithm id. + * Changed gcry_pk_genkey for "ecc" to only include the curve name and + not the parameters. The flag "param" may be used to revert this. + * Added a feature to globally disable selected hardware features. + * Added debug helper functions. +- rebased patches + * libgcrypt-1.5.0-etc_gcrypt_rngseed-symlink.diff + * libgcrypt-ppc64.patch +- add libgcrypt-1.6.0-use-intenal-functions.patch to fix fips.c build +- Move all documentation to -devel package + +------------------------------------------------------------------- +Fri Jul 26 22:05:46 UTC 2013 - andreas.stieger@gmx.de + +- update to 1.5.3 [bnc#831359] CVE-2013-4242 + * Mitigate the Yarom/Falkner flush+reload side-channel attack on + RSA secret keys. See . + +------------------------------------------------------------------- +Thu Jul 25 09:15:43 UTC 2013 - mvyskocil@suse.com + +- port SLE enhancenments to Factory (bnc#831028) + * add libgcrypt-unresolved-dladdr.patch (bnc#701267) + * add libgcrypt-1.5.0-etc_gcrypt_rngseed-symlink.diff (bnc#724841) + * add libgcrypt-1.5.0-LIBGCRYPT_FORCE_FIPS_MODE-env.diff +- install .hmac256.hmac (bnc#704068) +- enable varuous new options in configure (m-guard, hmac binary check and + random device linux) +- build with all ciphers, pubkeys and digest by default as whitelist + simply allowed them all + +------------------------------------------------------------------- +Mon Jun 17 13:22:33 UTC 2013 - coolo@suse.com + +- avoid gpg-offline in bootstrap packages + +------------------------------------------------------------------- +Sun Jun 16 22:56:56 UTC 2013 - crrodriguez@opensuse.org + +- Library must be built with large file support in + 32 bit archs. + +------------------------------------------------------------------- +Thu Apr 18 18:23:36 UTC 2013 - andreas.stieger@gmx.de + +- update to 1.5.2 + * The upstream sources now contain the IDEA algorithm, dropping: + idea.c.gz + libgcrypt-1.5.0-idea.patch + libgcrypt-1.5.0-idea_codecleanup.patch + * Made the Padlock code work again (regression since 1.5.0). + * Fixed alignment problems for Serpent. + * Fixed two bugs in ECC computations. + +------------------------------------------------------------------- +Fri Mar 22 09:31:11 UTC 2013 - mvyskocil@suse.com + +- add GPL3.0+ to License tag because of dumpsexp (bnc#810759) + +------------------------------------------------------------------- +Mon Mar 18 20:41:00 UTC 2013 - andreas.stieger@gmx.de + +- update to 1.5.1 + * Allow empty passphrase with PBKDF2. + * Do not abort on an invalid algorithm number in + gcry_cipher_get_algo_keylen and gcry_cipher_get_algo_blklen. + * Fixed some Valgrind warnings. + * Fixed a problem with select and high fd numbers. + * Improved the build system + * Various minor bug fixes. + * Interface changes relative to the 1.5.0 release: + GCRYCTL_SET_ENFORCED_FIPS_FLAG NEW. + GCRYPT_VERSION_NUMBER NEW. +- add verification of source code signatures +- now requires automake 1.11 to build + +------------------------------------------------------------------- +Sat Feb 2 18:51:33 UTC 2013 - coolo@suse.com + +- update license to new format + +------------------------------------------------------------------- +Tue Jun 12 21:19:18 UTC 2012 - chris@computersalat.de + +- fix deps + * libgpg-error-devel >= 1.8 +- add libsoname macro + +------------------------------------------------------------------- +Sun Feb 12 15:23:56 UTC 2012 - crrodriguez@opensuse.org + +- Libraries back into %{_libdir}, /usr merge project + +------------------------------------------------------------------- +Sat Dec 24 23:51:26 UTC 2011 - opensuse@dstoecker.de + +- add the missing IDEA algorithm after the patent is no longer relevant + +------------------------------------------------------------------ +Sun Nov 13 14:37:29 UTC 2011 - jengelh@medozas.de + +- Remove redundant/unwanted tags/section (cf. specfile guidelines) + +------------------------------------------------------------------- +Sun Nov 13 09:16:36 UTC 2011 - coolo@suse.com + +- add libtool as explicit buildrequire to avoid implicit dependency from prjconf + +------------------------------------------------------------------- +Sun Oct 2 18:38:28 UTC 2011 - crrodriguez@opensuse.org + +- Update to version 1.5.0, most important changes + * Uses the Intel AES-NI instructions if available + * Support ECDH. + +------------------------------------------------------------------- +Fri Nov 19 09:59:41 UTC 2010 - mvyskocil@suse.cz + +- update to 1.4.6 + * Fixed minor memory leak in DSA key generation. + * No more switching to FIPS mode if /proc/version is not readable. + * Fixed a sigill during Padlock detection on old CPUs. + * Boosted SHA-512 performance by 30% on ia32 boxes and gcc 4.3; + SHA-256 went up by 25%. + * New variants of the TIGER algorithm. + * New cipher algorithm mode for AES-WRAP. + * Interface changes relative to the 1.4.2 release: + GCRY_MD_TIGER1 NEW + GCRY_MD_TIGER2 NEW + GCRY_CIPHER_MODE_AESWRAP NEW + +------------------------------------------------------------------- +Sun Jul 4 19:07:16 UTC 2010 - jengelh@medozas.de + +- add missing definition of udiv_qrnnd for sparcv9:32 +- use %_smp_mflags + +------------------------------------------------------------------- +Sat Dec 19 12:58:20 CET 2009 - jengelh@medozas.de + +- add baselibs.conf as a source +- disable the use of hand-coded assembler functions on sparc - + this is giving me an infinite loop with ./tests/prime + (specifically ./sparc32v8/mpih-mul1.S:_gcry_mpih_mul_1. + Fedora disables this too. + +------------------------------------------------------------------- +Tue Apr 7 15:45:06 CEST 2009 - crrodriguez@suse.de + +- update to version 1.4.4 + * Publish GCRY_MODULE_ID_USER and GCRY_MODULE_ID_USER_LAST constants. + This functionality has been in Libgcrypt since 1.3.0. + * MD5 may now be used in non-enforced fips mode. + * Fixed HMAC for SHA-384 and SHA-512 with keys longer than 64 bytes. + * In fips mode, RSA keys are now generated using the X9.31 algorithm + and DSA keys using the FIPS 186-2 algorithm. + * The transient-key flag is now also supported for DSA key + generation. DSA domain parameters may be given as well. + +------------------------------------------------------------------- +Thu Jan 29 10:57:01 CET 2009 - olh@suse.de + +- obsolete libgcrypt-error-XXbit in the library subpackage + +------------------------------------------------------------------- +Wed Dec 10 12:34:56 CET 2008 - olh@suse.de + +- use Obsoletes: -XXbit only for ppc64 to help solver during distupgrade + (bnc#437293) + +------------------------------------------------------------------- +Tue Nov 11 17:23:54 CET 2008 - mkoenig@suse.de + +- build rijndael.c with -fno-strict-aliasing [bnc#443693] + +------------------------------------------------------------------- +Thu Oct 30 12:34:56 CET 2008 - olh@suse.de + +- obsolete old -XXbit packages (bnc#437293) + +------------------------------------------------------------------- +Mon Jun 30 11:47:59 CEST 2008 - mkoenig@suse.de + +- update to version 1.4.1 + * Fixed a bug which led to the comsumption of far too much + entropy for the intial seeding + * Improved AES performance for CFB and CBC modes + +------------------------------------------------------------------- +Sun May 11 11:54:39 CEST 2008 - coolo@suse.de + +- fix rename of xxbit packages + +------------------------------------------------------------------- +Thu Apr 10 12:54:45 CEST 2008 - ro@suse.de + +- added baselibs.conf file to build xxbit packages + for multilib support + +------------------------------------------------------------------- +Thu Jan 17 12:20:25 CET 2008 - mkoenig@suse.de + +- update to version 1.4.0: + * The entire library is now under the LGPL. The helper programs and + the manual are under the GPL + * New control code GCRYCTL_PRINT_CONFIG + * Experimental support for ECDSA + * Assembler support for the AMD64 architecture + * Non executable stack support is now used by default + * New configure option --enable-random-daemon + * The new function gcry_md_debug should be used instead of the + gcry_md_start_debug and gcry_md_stop_debug macros. + * Support for DSA2 + * Reserved algorithm ranges for use by applications + * gcry_mpi_rshift does not anymore truncate the shift count + * Support for OFB encryption mode + * Support for the Camellia cipher + * Support for the SEED cipher + * Support for SHA-224 and HMAC using SHA-384 and SHA-512 + * Reading and writing the random seed file is now protected by a + fcntl style file lock + * Made the RNG immune against fork without exec + * Changed the way the RNG gets initialized + * The ASN.1 DER template for SHA-224 has been fixed + * The ACE engine of VIA processors is now used for AES-128 +- changed package layout to conform shlib policy: + new subpackage libgcrypt11 +- disable static library +- for reference: bugzilla entry of last change #304749 + +------------------------------------------------------------------- +Thu Sep 13 01:28:53 CEST 2007 - ltinkl@suse.cz + +- add sanity check for mpi of size 0 (#304479) + +------------------------------------------------------------------- +Mon Feb 5 10:25:21 CET 2007 - mkoenig@suse.de + +- update to version 1.2.4: + * Fixed a bug in the memory allocator which could have been the + reason for some of non-duplicable bugs. + * Other minor bug fixes. + +------------------------------------------------------------------- +Wed Dec 13 12:47:48 CET 2006 - mkoenig@suse.de + +- get rid of .la file and fix devel so link + +------------------------------------------------------------------- +Tue Dec 5 18:30:30 CET 2006 - mkoenig@suse.de + +- move shared lib to /%_lib + +------------------------------------------------------------------- +Thu Aug 31 14:29:56 CEST 2006 - mkoenig@suse.de + +- update to version 1.2.3: + * Rewrote gcry_mpi_rshift to allow arbitrary shift counts. + * Minor bug fixes. +- added libgpg-error-devel and glibc-devel to Requires tag + of devel subpackage + +------------------------------------------------------------------- +Wed Jan 25 21:37:28 CET 2006 - mls@suse.de + +- converted neededforbuild to BuildRequires + +------------------------------------------------------------------- +Wed Nov 2 16:44:48 CET 2005 - hvogel@suse.de + +- enable noexecstack +- build ac.c with fno-strict-aliasing + +------------------------------------------------------------------- +Tue Oct 25 13:40:15 CEST 2005 - hvogel@suse.de + +- update to version 1.2.2 + +------------------------------------------------------------------- +Thu Jun 23 11:26:58 CEST 2005 - hvogel@suse.de + +- call install_info macro in post/postun of the devel package +- depend on libgcrypt +- add clean section + +------------------------------------------------------------------- +Tue Jan 18 11:51:51 CET 2005 - hvogel@suse.de + +- update to version 1.2.1 + +------------------------------------------------------------------- +Tue Jan 11 16:48:10 CET 2005 - schwab@suse.de + +- Fix info dir entry. + +------------------------------------------------------------------- +Wed Nov 17 11:22:44 CET 2004 - hvogel@suse.de + +- require libgpg-error-devel (Bug #48271) +- get rid of the NLD parts + +------------------------------------------------------------------- +Wed Jul 14 11:12:54 CEST 2004 - adrian@suse.de + +- create -devel subpackage +- prepare for nld + +------------------------------------------------------------------- +Wed May 19 14:57:45 CEST 2004 - hvogel@suse.de + +- update to version 1.2.0 + +------------------------------------------------------------------- +Mon Mar 22 16:48:53 CET 2004 - meissner@suse.de + +- disable make check, because it uses /dev/random whihc is + not filled on some server machines. + +------------------------------------------------------------------- +Wed Mar 17 15:01:51 CET 2004 - meissner@suse.de + +- fixed too over enthusiastic powerpc switches to make it work + on ppc64. (It compiled before, but did not work). +- enabled make check. + +------------------------------------------------------------------- +Wed Feb 18 12:14:36 CET 2004 - kukuk@suse.de + +- Build against system pthread library, not pth. + +------------------------------------------------------------------- +Tue Feb 17 21:11:40 CET 2004 - hvogel@suse.de + +- update to version 1.1.91 +- fix autoconf quotations + +------------------------------------------------------------------- +Sat Jan 10 19:20:41 CET 2004 - adrian@suse.de + +- add %run_ldconfig to %postun + +------------------------------------------------------------------- +Sun Jul 27 16:12:54 CEST 2003 - poeml@suse.de + +- add libgcrypt-1.1.12-sexp-valgrind-error.patch from SLEC + +------------------------------------------------------------------- +Thu Apr 24 12:20:23 CEST 2003 - ro@suse.de + +- fix install_info --delete call and move from preun to postun + +------------------------------------------------------------------- +Mon Feb 10 22:51:26 CET 2003 - mmj@suse.de + +- Use %install_info macro [#23433] + +------------------------------------------------------------------- +Mon Feb 10 16:11:55 CET 2003 - mc@suse.de + +- switch to version 1.1.12 +- gcry_pk_sign, gcry_pk_verify and gcry_pk_encrypt can now handle an + optional pkcs1 flags parameter in the S-expression. A similar flag + may be passed to gcry_pk_decrypt but it is only syntactically + implemented. +- New convenience macro gcry_md_get_asnoid. +- There is now some real stuff in the manual. +- New algorithm: MD4 +- Implemented ciphertext stealing. +- Support for plain old DES +- Smaller bugs fixes and a few new OIDs. + +------------------------------------------------------------------- +Tue Jan 14 14:03:27 CET 2003 - nadvornik@suse.cz + +- fixed multi-line string literals + +------------------------------------------------------------------- +Thu Aug 1 23:51:10 CEST 2002 - poeml@suse.de + +- create package + diff --git a/libgcrypt.keyring b/libgcrypt.keyring new file mode 100644 index 0000000..dd3bb0b --- /dev/null +++ b/libgcrypt.keyring @@ -0,0 +1,86 @@ +-----BEGIN PGP PUBLIC KEY BLOCK----- + +mQGNBFjLuq4BDACnM7zNSIaVMAacTwjXa5TGYe13i6ilHe4VL0NShzrgzjcQg531 +3cRgiiiNA7OSOypMqVs73Jez6ZUctn2GVsHBrS/io9NcuC9pVwf8a61WlcEa+EtB +a3G7HlBmEWnwaUdAtWKNuAi9Xn+Ir7H2xEdksmmd5a0/QnL+sX705boVPF/tpYtb +LGpPxa78tNrtxDkSwy8Wmi0IADYLI5yI7/yUGeJd8RSCU/fLRKC9fG7YOZRq0tsO +MhVNWmtUjbG6e73Lu8LKnCZgs1/fC8hvPyARieSV5mdN8s1oWd7oYctfgL4uBleD +ItAA8GhjKejutzHN8Ei/APw6AiiSyEjnPg+cTX8OgvLGJWjks0H6mPZeB1v/kGyZ +hBS9vm540h2/MmlVN2ntiCK5TZGeSWpqddiqusfVXotMRpN4HeLKoZh4RAncaCbZ +F/S+YLeN+kMXY4k3Fqt1fjTX6veFCbthI9pDdHzU9LfUVNp9D/5ktC/tYMORMegV ++wSMxi9G2YWKJkMAEQEAAYkBzgQfAQgAOBYhBFuAxXVCmPDLVdjtarzvfilLCS4o +BQJYy8DdFwyAAZSlyaA8L+XKOwldjh/fcjz0YraxAgcAAAoJELzvfilLCS4oNgoL +/0+K1xIx8JW7Lk5M6bYCvNA4fdlEcwQIT4UidJFM9m+suxYFWIGfebvHpRlEuJTg +dBjkEit8uLAoJXU0BRkKTLrzTF+qDUE79Wfx/R+0nOgJ7aMykQOi0AvuwzMYz4dg +xIVS2Daou4DF7bh/KF8+fqrmq8P8W1ZrkuFDanMWpHeAPx1uj2skYbo7uPqFdvlJ +hlNHrcxlcCkjf1InAt0Xt5lMvEsCRUPf9xAH4mNEhs0lh9c+200YPRmtnLWAzc1K +ckLIC8Q+mUR3DjZDqBlDBEPegXkrI0+MlvRA+9AnAm4YPqTMUfpZ6ZOAWeFjC/6Z +QYxG/AdWGkb4WFindzklQfybEuiekP8vU07ACQwSwH8PYe0UCom1YrlRUjX7QLkn +ZLWoeZg8BZy9GTM1Ut7Q1Q2uTw6mxxISuef+RFgYOHjWwLpFWZpqC88xERl7o/iz +iERJRt/593IctbjO9wenWt2peIAwzR4nz7LqM6ZFTdRAETmcdSvYRhg2Qt8hUE47 +CbQkQW5kcmUgSGVpbmVja2UgKFJlbGVhc2UgU2lnbmluZyBLZXkpiQHUBBMBCAA+ +FiEEW4DFdUKY8MtV2O1qvO9+KUsJLigFAljLuq4CGwMFCRLMAwAFCwkIBwIGFQgJ +CgsCBBYCAwECHgECF4AACgkQvO9+KUsJLihC/QwAhCC+SEvcFLcutgZ8HfcCtoZs +IoVzZEy7DjqIvGgnTssD8HCLnIAHCDvnP7dJW3uMuLCdSqym3cjlEIiQMsaGywkl +fzJISAwJrGQdWSKRd535jXpEXQlXDKal/IwMKAUt0PZtlCc9S3gwixQryxdJ28lJ +6h2T9fVDr8ZswMmTAFG91uctfhjKOMgPt8UhSPGW484WsIsQgkbOvf+Kfswl0eHu +ywX+pKAB5ZQ/9GVC6Ug4xfrdiJL0azJTPnvjMY5JYp6/L9RURs5hP5AnHR2j/PPo +sAtsFCjmbRbOMiASzklnUJPbSz5kfLloDWZmrUScjbzmsXehGyt433JGyRhZJl4x +/jPbzKhaaAHsGd+fRao6vlLOwFywDDVMp6JuyK7UeUb7I8ekTbSkGFA+l2Oa3O6/ +Y7PYhq7hwwAFuZckYI98IpHNCG1fS9W07FyKdvQbK1PbF1JFRKfsUCWYMKqDnbqE +o5jivPEHZImw6iYhhXcyEYl8fjcb9T6/S+wOP7aviQGzBBABCAAdFiEElKXJoDwv +5co7CV2OH99yPPRitrEFAljLv5sACgkQH99yPPRitrFw4gv/XFMFN+/LHsn9hJOP +4rCwl1yUuxXuYmZgc0sRoY3EpeQkJVyKurQuqqKoy2VuoMiF0O1kAQmGoFtVPUk7 +b8hCoutqB5GyeyKcoLP+WINgVhB2gXg7TSp3MPLBKkgqvSDvPitgRxBqFb4LW8LJ +bDbfwGrzIvXfDV3WvsrHVPbc2fhlWdL8d+3AE6mFiXF3eTpgmV3ApSBQV12MkkCk +icLIPmp+ZxZON+OP52ZXkRtfMgOy4Oa/41agrViDAZdMOGeGkhPertQheQZgXzmo +GF5Wz498HPM80Kv35X91l3iGzL+icEtO+tWea2YscsZ6qpRe2lfVPHk3B+anlmCj +m4kM4cBd39xa4HHSVh/bRHbZNtgVr7slQCKxlHgQOGVI5vCxPCwEsgJ2KBk03Nk/ +IA9EKO+czfh3/bHW6uMbEqrYDCnt+hmzZrpKDSGcwS/KOhvMUIMlb7/8vDKum6mp +/8xAtVZ6IAxYZNt3qg7Y7aLRtzCTyqm8rJQrZPtRaQcgLoEimDMEX0PliRYJKwYB +BAHaRw8BAQdAz75Hlekc16JhhfI0MKdEVxLdkxhcMCO0ZG6WMBAmNpe0H1dlcm5l +ciBLb2NoIChkaXN0IHNpZ25pbmcgMjAyMCmImgQTFgoAQhYhBG2qbmSnbShAVxtJ +AlKIl7gmQDraBQJfQ+w1AhsDBQkShccRBQsJCAcCAyICAQYVCgkICwIEFgIDAQIe +BwIXgAAKCRBSiJe4JkA62nmuAP9uL/HOdB0gvwWrH+FpURJLs4bnaZaPIk9ARrU0 +EXRgJgD/YCGfHQXpIPT0ZaXuwJexK04Z+qMFR/bM1q1Leo5CjgaIbQQQEQsAHRYh +BIBhWHD1utaQMzaG0PKthaweQrNnBQJfQ/HmAAoJEPKthaweQrNnIZkA3jG6LcZv +V/URn8Y8OJqsyYa4C3NI4nN+OhEvYhgA4PHzMnALeXIpA2gblvjFIPJPAhDBAU37 +c5PA6+6IdQQQFggAHRYhBK6oTtzwGthsRwHIXGMROuhmWH0KBQJfQ/IlAAoJEGMR +OuhmWH0K1+MA/0uJ5AHcnSfIBEWHNJwwVVLGyrxAWtS2U+zeymp/UvlPAQDErCLZ +l0dBiPG3vlowFx5TNep7tanBs6ZJn8F1ao1tAIkBMwQQAQgAHRYhBNhpISPEBl3q +Xg86tSSbOdJPJeO2BQJfQ/OuAAoJECSbOdJPJeO2DVoH/0o9if66ph6FJrgr+A/W +HNVeHxmM5tUQhpL1wpRS70SKcsJgolf5CxO5iTQf3HlZe544xGbIU/aCTJsWw9zi +UE8KmhAtKV4eL/7oQ7xx4nxPnABLpudtM8A44nsM1x/XiYrJnnDm29QjYEGd2Hi8 +7npc7VWKzLoj+I/WcXquynJi5O9TUxW9Bknd1pjpxFkf8v+msjBzCD5VKJgr0CR8 +wA6peQBWeGZX2HacosMIZH4TfL0r0TFla6LJIkNBz9DyIm1yL4L8oRH0950hQljP +C7TM3L7aRpX+4Kph6llFz6g7MALGFP95kyJ6o+XED9ORuuQVZMBMIkNC0tXOu10V +bdqIdQQQFgoAHRYhBMHTS2khnkruwLocIeP9/yGORbcrBQJfQ/P8AAoJEOP9/yGO +Rbcr3lQBAMas8Vl3Hdl3g2I283lz1uHiGvlwcnk2TLeB+U4zIwC9AQCy0nnazVNt +VQPID1ZCMoaOX7AzOjaqQDLf4j+dVTxgBJgzBGCkgocWCSsGAQQB2kcPAQEHQJmd +fwp8jEN5P3eEjhQiWk6zQi8utvgOvYD57XmE+H8+tCBOaWliZSBZdXRha2EgKEdu +dVBHIFJlbGVhc2UgS2V5KYiaBBMWCgBCFiEErI4RW/c+LY1H+pkI6Y6bLRnGyL0F +AmCkgocCGwMFCQsNBpkFCwkIBwIDIgIBBhUKCQgLAgQWAgMBAh4HAheAAAoJEOmO +my0Zxsi9/4IA/1rvSr3MU+Sv4jhNDzD+CeC3gmHkPew6pi9VHEsEwdgmAQD2BtiX +7w1sJL/CBylGWv5jxj4345mP9YfZm0RsgzPjDIh1BBAWCAAdFiEEJJyzdxdQdF1c +3TI84mewUjZPAo0FAmFAQ54ACgkQ4mewUjZPAo1CiAD+KTT1UVdQTGHMyvHwZocS +QjU8xhcZrTet+dvvjrE5+4MA/RBdJPZgFevUKu68NEy0Lo+RbkeCtmQJ/c8v5ieF +vW0AiQEzBBABCAAdFiEEEkEkvTtIYq96CkLxALRevUynur4FAmFAQ7cACgkQALRe +vUynur4kaAgAolPR8TNWVS0vXMKrr0k0l2M/8QkZTaLZx1GT9Nx1yb4WJKY7ElPM +YkhGDxetvFBETx0pH/6R3jtj6Crmur+NKHVSRY+rCYpFPDn6ciIOryssRx2G4kCZ +t+nFB9JyDbBOZAR8DK4pN1mAxG/yLDt4oKcUQsP2xlEFum+phxyR8KyYCpkwKRxY +eK+6lfilQuveoUwp/Xx5wXPNUy6q4eOOovCW7gS7I7288NGHCa2ul8sD6vA9C4mM +4Zxaole9P9wwJe1zZFtCIy88zHM9vqv+YM9DxMCaW24+rUztr7eD4bCRdG+QlSh+ +7R/TaqSxY1eAAd1J5tma9CNJO73pTKU+/JhTBGFpSqMTCSskAwMCCAEBBwIDBF6X +D9NmUQDgiyYNbhs1DMJ14mIw812wY1HVx/4QWYWiBunhrvSFxVbzsjD7/Wv+v3bm +MPrL+M2DLyFiSewNmcS0JEdudVBHLmNvbSAoUmVsZWFzZSBTaWduaW5nIEtleSAy +MDIxKYiaBBMTCABCFiEEAvON/3Mf+XywOaHaVJ5pXpBboggFAmFpSqMCGwMFCQ9x +14oFCwkIBwIDIgIBBhUKCQgLAgQWAgMBAh4HAheAAAoJEFSeaV6QW6IITkoA/RYa +jaTl1eEBU/Gdm12o3jrI55N5xZK2XTqSx25clVyjAP0XwMW/Og5+ND1ri3bAqADV +WlBDUswz8wYxsb0C4kYBkoh1BBAWCgAdFiEEbapuZKdtKEBXG0kCUoiXuCZAOtoF +AmFpTvEACgkQUoiXuCZAOtrJQAEAh7YyykjAy/Qs1yC3ji8iBfIVnPXvblrIx3SR +RyDwRC8BAKtZbEuKTtPlgkLUgMleTcZJ/vEhJE+GvfQ9o5gWCqEFiHUEEBYKAB0W +IQTB00tpIZ5K7sC6HCHj/f8hjkW3KwUCYWlPWgAKCRDj/f8hjkW3Kx4eAQDp6aGS +N/fU4xLl8RSvQUVjVA+aCTrMQR3hRwqw8liF2wEA3O3ECxz6e1+DoItYoJBBLKLw +eiInsGZ/+h5XYrpXTgA= +=4+Sn +-----END PGP PUBLIC KEY BLOCK----- diff --git a/libgcrypt.spec b/libgcrypt.spec new file mode 100644 index 0000000..a1e7dad --- /dev/null +++ b/libgcrypt.spec @@ -0,0 +1,197 @@ +# +# spec file for package libgcrypt +# +# Copyright (c) 2025 SUSE LLC +# +# All modifications and additions to the file contributed by third parties +# remain the property of their copyright owners, unless otherwise agreed +# upon. The license for this file, and modifications and additions to the +# file, is the same license as for the pristine package itself (unless the +# license for the pristine package is not an Open Source License, in which +# case the license is the MIT License). An "Open Source License" is a +# license that conforms to the Open Source Definition (Version 1.9) +# published by the Open Source Initiative. + +# Please submit bugfixes or comments via https://bugs.opensuse.org/ +# + + +%define libsover 20 +%define libsoname %{name}%{libsover} +%define hmac_key orboDeJITITejsirpADONivirpUkvarP +Name: libgcrypt +Version: 1.11.1 +Release: 0 +Summary: The GNU Crypto Library +License: GPL-2.0-or-later AND LGPL-2.1-or-later AND GPL-3.0-or-later +Group: Development/Libraries/C and C++ +URL: https://gnupg.org/software/libgcrypt +Source: https://gnupg.org/ftp/gcrypt/libgcrypt/%{name}-%{version}.tar.bz2 +Source1: https://gnupg.org/ftp/gcrypt/libgcrypt/%{name}-%{version}.tar.bz2.sig +Source2: baselibs.conf +Source3: random.conf +Source4: hwf.deny +# https://www.gnupg.org/signature_key.html +Source5: https://gnupg.org/signature_key.asc#/%{name}.keyring +Source99: libgcrypt.changes +Patch1: libgcrypt-1.10.0-allow_FSM_same_state.patch +#PATCH-FIX-OPENSUSE Do not pull revision info from GIT when autoconf is run +Patch2: libgcrypt-nobetasuffix.patch +#PATCH-FIX-SUSE: Make the revamped SLI api public +Patch3: libgcrypt-1.11.1-public-SLI-API.patch +# FIPS patches: +#PATCH-FIX-SUSE bsc#1190700 FIPS: Provide a service-level indicator for PK +Patch100: libgcrypt-FIPS-SLI-pk.patch +#PATCH-FIX-SUSE bsc#1190700 FIPS: Check keylength in gcry_fips_indicator_kdf() +Patch101: libgcrypt-FIPS-SLI-kdf-leylength.patch +#PATCH-FIX-SUSE bsc#1190700 FIPS add indicators +Patch102: libgcrypt-FIPS-SLI-hash-mac.patch +#PATCH-FIX-SUSE bsc#1202117 FIPS: Get most of the entropy from rndjent_poll +Patch104: libgcrypt-FIPS-rndjent_poll.patch +#PATCH-FIX-SUSE bsc#1220896 FIPS: Replace the built-in jitter rng with standalone version +Patch105: libgcrypt-FIPS-jitter-standalone.patch +#PATCH-FIX-SUSE bsc#1220895 FIPS: Enforce the interpretation and use of jitter rng +Patch106: libgcrypt-FIPS-jitter-errorcodes.patch +#PATCH-FIX-SUSE bsc#1220893 FIPS: Use Jitter RNG for the whole length entropy buffer +Patch107: libgcrypt-FIPS-jitter-whole-entropy.patch +#PATCH-FIX-SUSE Remove not used rol64() definition after removing the built-in jitter rng +Patch108: libgcrypt-rol64-redefinition.patch + +BuildRequires: automake >= 1.14 +BuildRequires: libgpg-error-devel >= 1.49 +BuildRequires: libtool +BuildRequires: makeinfo +BuildRequires: pkgconfig +%{?suse_build_hwcaps_libs} + +%description +Libgcrypt is a general purpose library of cryptographic building +blocks. It is originally based on code used by GnuPG. It does not +provide any implementation of OpenPGP or other protocols. Thorough +understanding of applied cryptography is required to use Libgcrypt. + +%package -n %{libsoname} +Summary: The GNU Crypto Library +License: GPL-2.0-or-later AND LGPL-2.1-or-later +Group: System/Libraries +BuildRequires: jitterentropy-devel >= 3.4.0 +Requires: libjitterentropy3 >= 3.4.0 +Provides: %{libsoname}-hmac = %{version}-%{release} +Obsoletes: %{libsoname}-hmac < %{version}-%{release} + +%description -n %{libsoname} +Libgcrypt is a general purpose crypto library based on the code used in +GnuPG (alpha version). + +%package devel +Summary: The GNU Crypto Library +License: GFDL-1.1-only AND GPL-2.0-or-later AND LGPL-2.1-or-later AND MIT +Group: Development/Libraries/C and C++ +Requires: %{libsoname} = %{version} +Requires: glibc-devel +Requires: jitterentropy-devel >= 3.4.0 +Requires: libgpg-error-devel >= 1.49 + +%description devel +Libgcrypt is a general purpose library of cryptographic building +blocks. It is originally based on code used by GnuPG. It does not +provide any implementation of OpenPGP or other protocols. Thorough +understanding of applied cryptography is required to use Libgcrypt. + +This package contains needed files to compile and link against the +library. + +%prep +%autosetup -p1 + +# Rename the internal .hmac file to include the so library version +sed -i "s/libgcrypt\.so\.hmac/\.libgcrypt\.so\.%{libsover}\.hmac/g" src/Makefile.am src/Makefile.in + +# Replace the built-in jitter rng with the standalone version [bsc#1220896] +find . -type f -name "jitterentropy*" -print -delete + +%build +export PUBKEYS="dsa elgamal rsa ecc" +export CIPHERS="arcfour blowfish cast5 des aes twofish serpent rfc2268 seed camellia idea salsa20 gost28147 chacha20 sm4 aria" +export DIGESTS="crc gostr3411-94 md4 md5 rmd160 sha1 sha256 sha512 sha3 tiger whirlpool stribog blake2 sm3" +export KDFS="s2k pkdf2 scrypt" + +autoreconf -fi +date=$(date -u '+%%Y-%%m-%%dT%%H:%%M+0000' -r %{SOURCE99}) +sed -e "s,BUILD_TIMESTAMP=.*,BUILD_TIMESTAMP=$date," -i configure +export CFLAGS="%{optflags} $(getconf LFS_CFLAGS)" +%configure \ + --with-fips-module-version="Libgcrypt version %{version}-%{release}" \ + --enable-hmac-binary-check="%{hmac_key}" \ + --enable-ciphers="$CIPHERS" \ + --enable-pubkey-ciphers="$PUBKEYS" \ + --enable-digests="$DIGESTS" \ + --enable-kdfs="$KDFS" \ + --enable-noexecstack \ + --disable-static \ +%ifarch %{sparc} + --disable-asm \ +%endif + --enable-random=getentropy \ + --enable-jent-support \ + %{nil} + +%make_build + +%check +make -k check +# run the regression tests also in FIPS mode +LIBGCRYPT_FORCE_FIPS_MODE=1 make -k check + +%install +%make_install + +# this is a hack that re-defines the __spec_install_post macro +# for a simple reason: the macro strips the binaries and thereby +# invalidates a HMAC that may have been created earlier. +# solution: create the hashes _after_ the macro runs. +%define libpath %{buildroot}%{_libdir}/libgcrypt.so.%{libsover}.?.? +%define __spec_install_post \ + %{?__debug_package:%{__debug_install_post}} \ + %{__arch_install_post} \ + %{__os_install_post} \ + cd src \ + sed -i -e 's|FILE=.*|FILE=\\\$1|' gen-note-integrity.sh \ + READELF=readelf AWK=awk ECHO_N="-n" bash gen-note-integrity.sh %{libpath} > %{libpath}.hmac \ + objcopy --update-section .note.fdo.integrity=%{libpath}.hmac %{libpath} %{libpath}.new \ + mv -f %{libpath}.new %{libpath} \ + rm -f %{libpath}.hmac \ +%{nil} + +rm %{buildroot}%{_libdir}/%{name}.la + +# Create /etc/gcrypt directory and install random.conf +mkdir -p -m 0755 %{buildroot}%{_sysconfdir}/gcrypt +install -m 644 %{SOURCE3} %{buildroot}%{_sysconfdir}/gcrypt/random.conf +install -m 644 %{SOURCE4} %{buildroot}%{_sysconfdir}/gcrypt/hwf.deny + +%post -n %{libsoname} -p /sbin/ldconfig +%postun -n %{libsoname} -p /sbin/ldconfig + +%files -n %{libsoname} +%license COPYING COPYING.LIB LICENSES +%doc AUTHORS ChangeLog NEWS README THANKS TODO +%{_libdir}/%{name}.so.* +%dir %{_sysconfdir}/gcrypt +%config(noreplace) %{_sysconfdir}/gcrypt/random.conf +%config(noreplace) %{_sysconfdir}/gcrypt/hwf.deny + +%files devel +%license COPYING COPYING.LIB LICENSES +%{_bindir}/dumpsexp +%{_bindir}/hmac256 +%{_bindir}/mpicalc +%{_bindir}/%{name}-config +%{_libdir}/%{name}.so +%{_libdir}/pkgconfig/libgcrypt.pc +%{_datadir}/aclocal/%{name}.m4 +%{_includedir}/gcrypt*.h +%{_infodir}/gcrypt.info*%{ext_info}* +%{_mandir}/man1/* + +%changelog diff --git a/random.conf b/random.conf new file mode 100644 index 0000000..378ba78 --- /dev/null +++ b/random.conf @@ -0,0 +1,9 @@ +# This file can be used to globally change parameters of +# the random generator. Supported options are: + +# Always use the non-blocking /dev/urandom or the respective +# system call instead of the blocking /dev/random. +# only-urandom + +# Disable the use of the jitter based entropy generator. +# disable-jent -- 2.51.1 From 4fc6367f292e78ce2b3db594fd32782246a0a37df6ff2e94d1bbba3e0f19dab9 Mon Sep 17 00:00:00 2001 From: Pedro Monreal Gonzalez Date: Fri, 9 May 2025 08:27:38 +0000 Subject: [PATCH 6/8] * Other: - Several improvements for constant time operation by the introduction of Least Leak Intended (LLI) variants of internal functions. [T7519,T7490] * Add libgcrypt-1.11.1-public-SLI-API.patch OBS-URL: https://build.opensuse.org/package/show/devel:libraries:c_c++/libgcrypt?expand=0&rev=191 --- libgcrypt.changes | 6 ++++-- 1 file changed, 4 insertions(+), 2 deletions(-) diff --git a/libgcrypt.changes b/libgcrypt.changes index 76e23bd..c3d0d7d 100644 --- a/libgcrypt.changes +++ b/libgcrypt.changes @@ -16,12 +16,14 @@ Thu May 8 14:28:42 UTC 2025 - Lucas Mulling - Add GHASH RISC-V Zbb+Zbc implementation. [rC0f1fec12b0] - Add ChaCha20 RISC-V vector intrinsics implementation. [rC8dbee93ac2] - Add SHA3 acceleration for RISC-V Zbb extension. [rC1a660068ba] - * Other: + * Other: - Add CET support for i386 and amd64 assembly. [T7220] - Add PAC/BTI support for AArch64 asm. [T7220] - Apply changes to Kyber from upstream for final FIPS 203. [rCcc95c36e7f] - Introduce an internal API for a revampled FIPS service indicator. [T7340] - - Several improvements for constant time operation by the introduction of Least Leak Intended (LLI) variants of internal functions. [T7519,T7490] + - Several improvements for constant time operation by the introduction of + Least Leak Intended (LLI) variants of internal functions. [T7519,T7490] + * Add libgcrypt-1.11.1-public-SLI-API.patch * Rebase patches: - libgcrypt-FIPS-SLI-hash-mac.patch - libgcrypt-FIPS-SLI-pk.patch -- 2.51.1 From b5b243be7f7c4abc2db7716565cbdf73e982e70ba9a9686455d7651d91655063 Mon Sep 17 00:00:00 2001 From: Pedro Monreal Gonzalez Date: Tue, 10 Jun 2025 07:06:49 +0000 Subject: [PATCH 7/8] - Security fix [bsc#1221107, CVE-2024-2236] * Add --enable-marvin-workaround to spec to enable workaround * Fix timing based side-channel in RSA implementation ( Marvin attack ) * Add libgcrypt-CVE-2024-2236.patch OBS-URL: https://build.opensuse.org/package/show/devel:libraries:c_c++/libgcrypt?expand=0&rev=193 --- .gitattributes | 23 + .gitignore | 1 + baselibs.conf | 8 + hwf.deny | 34 + libgcrypt-1.10.0-allow_FSM_same_state.patch | 15 + libgcrypt-1.10.3.tar.bz2 | 3 + libgcrypt-1.10.3.tar.bz2.sig | Bin 0 -> 238 bytes libgcrypt-1.11.0.tar.bz2 | 3 + libgcrypt-1.11.0.tar.bz2.sig | Bin 0 -> 119 bytes libgcrypt-1.11.1-public-SLI-API.patch | 37 + libgcrypt-1.11.1.tar.bz2 | 3 + libgcrypt-1.11.1.tar.bz2.sig | Bin 0 -> 119 bytes libgcrypt-CVE-2024-2236.patch | 1839 +++++++++++++++ ...poly1305-Optimized-chacha20-poly1305.patch | 1993 ++++++++++++++++ ...e-SHA3-s390x-acceleration-for-CSHAKE.patch | 61 + libgcrypt-FIPS-SLI-hash-mac.patch | 172 ++ libgcrypt-FIPS-SLI-kdf-leylength.patch | 60 + libgcrypt-FIPS-SLI-pk.patch | 177 ++ libgcrypt-FIPS-jitter-errorcodes.patch | 16 + libgcrypt-FIPS-jitter-standalone.patch | 183 ++ libgcrypt-FIPS-jitter-whole-entropy.patch | 41 + libgcrypt-FIPS-rndjent_poll.patch | 114 + libgcrypt-Fix-the-previous-change.patch | 45 + ...ild-Improve-__thread-specifier-check.patch | 41 + ...T-for-non-rfc6979-ECDSA-with-fixed-k.patch | 94 + ...on-compliant-cipher-modes-in-the-SLI.patch | 236 ++ ...-Differentiate-igninvflag-in-the-SLI.patch | 40 + ...rentiate-no-blinding-flag-in-the-SLI.patch | 70 + ...ferentiate-use-of-label-K-in-the-SLI.patch | 139 ++ ...e-GCRY_CIPHER_MODE_CMAC-in-FIPS-mode.patch | 98 + ...-_gcry_cipher_is_mode_fips_compliant.patch | 64 + libgcrypt-cipher-ecc-Fix-for-supplied-K.patch | 88 + ...-cipher-fips-Fix-for-random-override.patch | 83 + ...nknown-with-RSA-signature-generation.patch | 445 ++++ ...te-use-of-random-override-in-the-SLI.patch | 107 + ...about-GCRYCTL_FIPS_SERVICE_INDICATOR.patch | 66 + libgcrypt-doc-Fix-syntax-error.patch | 31 + ...l-API-for-new-FIPS-service-indicator.patch | 140 ++ ...pt-fips-Fix-GCRY_FIPS_FLAG_REJECT_MD.patch | 42 + ...troduce-GCRYCTL_FIPS_REJECT_NON_FIPS.patch | 261 +++ ...FIPS_SERVICE_INDICATOR-and-the-macro.patch | 101 + ...ernal-API-for-FIPS-service-indicator.patch | 332 +++ ...PS_REJECT_NON_FIPS-not-by-open-flags.patch | 498 ++++ ...r-Add-GCRY_FIPS_FLAG_REJECT_PK_FLAGS.patch | 80 + ...not-to-reject-but-mark-non-compliant.patch | 300 +++ ...mputation-when-marking-non-compliant.patch | 160 ++ ...ix-memory-leak-for-gcry_pk_hash_sign.patch | 76 + ...vice-indicator-for-gcry_pk_hash_-API.patch | 360 +++ ...PS-service-indicator-for-cipher_open.patch | 122 + ...ing-or-marking-for-gcry_pk_get_curve.patch | 43 + ...-in-gcry_pk_sign-verify-in-FIPS-mode.patch | 282 +++ ...ervice-indicator-for-gcry_kdf_derive.patch | 265 +++ ...-service-indicator-for-gcry_mac_open.patch | 115 + ...-service-indicator-for-gcry_md_hash_.patch | 188 ++ ...rvice-indicator-for-gcry_md_open-API.patch | 298 +++ ...ld-care-about-FIPS-service-indicator.patch | 85 + libgcrypt-fips-tests-Add-t-digest.patch | 243 ++ ...d_open-write-read-close-for-t-digest.patch | 172 ++ libgcrypt-jitterentropy-3.4.0.patch | 618 +++++ ..._info-to-mark-reject-under-FIPS-mode.patch | 82 + ...A-1-non-FIPS-internally-for-1.12-API.patch | 154 ++ ...igest_algo_spec-in-_gcry_md_selftest.patch | 74 + libgcrypt-no-deprecated-grep-alias.patch | 35 + libgcrypt-nobetasuffix.patch | 24 + ...e-P10-assembly-with-ENABLE_FORCE_SOF.patch | 76 + libgcrypt-rol64-redefinition.patch | 16 + ...re-tests-to-tests-t-fips-service-ind.patch | 382 ++++ ...crypt-tests-Allow-tests-with-USE_RSA.patch | 44 + ...d-using-GCRY_MD_SHA256-for-KDF-tests.patch | 106 + ...ests-fips-Add-gcry_cipher_open-tests.patch | 199 ++ ...t-tests-fips-Add-gcry_mac_open-tests.patch | 206 ++ ...Move-KDF-tests-to-t-fips-service-ind.patch | 375 +++ ...tests-fips-Rename-t-fips-service-ind.patch | 60 + libgcrypt.changes | 2013 +++++++++++++++++ libgcrypt.keyring | 86 + libgcrypt.spec | 200 ++ random.conf | 9 + 77 files changed, 15352 insertions(+) create mode 100644 .gitattributes create mode 100644 .gitignore create mode 100644 baselibs.conf create mode 100644 hwf.deny create mode 100644 libgcrypt-1.10.0-allow_FSM_same_state.patch create mode 100644 libgcrypt-1.10.3.tar.bz2 create mode 100644 libgcrypt-1.10.3.tar.bz2.sig create mode 100644 libgcrypt-1.11.0.tar.bz2 create mode 100644 libgcrypt-1.11.0.tar.bz2.sig create mode 100644 libgcrypt-1.11.1-public-SLI-API.patch create mode 100644 libgcrypt-1.11.1.tar.bz2 create mode 100644 libgcrypt-1.11.1.tar.bz2.sig create mode 100644 libgcrypt-CVE-2024-2236.patch create mode 100644 libgcrypt-Chacha20-poly1305-Optimized-chacha20-poly1305.patch create mode 100644 libgcrypt-Disable-SHA3-s390x-acceleration-for-CSHAKE.patch create mode 100644 libgcrypt-FIPS-SLI-hash-mac.patch create mode 100644 libgcrypt-FIPS-SLI-kdf-leylength.patch create mode 100644 libgcrypt-FIPS-SLI-pk.patch create mode 100644 libgcrypt-FIPS-jitter-errorcodes.patch create mode 100644 libgcrypt-FIPS-jitter-standalone.patch create mode 100644 libgcrypt-FIPS-jitter-whole-entropy.patch create mode 100644 libgcrypt-FIPS-rndjent_poll.patch create mode 100644 libgcrypt-Fix-the-previous-change.patch create mode 100644 libgcrypt-build-Improve-__thread-specifier-check.patch create mode 100644 libgcrypt-cipher-Add-KAT-for-non-rfc6979-ECDSA-with-fixed-k.patch create mode 100644 libgcrypt-cipher-Check-and-mark-non-compliant-cipher-modes-in-the-SLI.patch create mode 100644 libgcrypt-cipher-Differentiate-igninvflag-in-the-SLI.patch create mode 100644 libgcrypt-cipher-Differentiate-no-blinding-flag-in-the-SLI.patch create mode 100644 libgcrypt-cipher-Differentiate-use-of-label-K-in-the-SLI.patch create mode 100644 libgcrypt-cipher-Don-t-differentiate-GCRY_CIPHER_MODE_CMAC-in-FIPS-mode.patch create mode 100644 libgcrypt-cipher-Rename-_gcry_cipher_is_mode_fips_compliant.patch create mode 100644 libgcrypt-cipher-ecc-Fix-for-supplied-K.patch create mode 100644 libgcrypt-cipher-fips-Fix-for-random-override.patch create mode 100644 libgcrypt-cipher-rsa-Mark-reject-SHA1-unknown-with-RSA-signature-generation.patch create mode 100644 libgcrypt-cipher-visibility-Differentiate-use-of-random-override-in-the-SLI.patch create mode 100644 libgcrypt-doc-Add-about-GCRYCTL_FIPS_SERVICE_INDICATOR.patch create mode 100644 libgcrypt-doc-Fix-syntax-error.patch create mode 100644 libgcrypt-fips-Change-the-internal-API-for-new-FIPS-service-indicator.patch create mode 100644 libgcrypt-fips-Fix-GCRY_FIPS_FLAG_REJECT_MD.patch create mode 100644 libgcrypt-fips-Introduce-GCRYCTL_FIPS_REJECT_NON_FIPS.patch create mode 100644 libgcrypt-fips-Introduce-GCRYCTL_FIPS_SERVICE_INDICATOR-and-the-macro.patch create mode 100644 libgcrypt-fips-Introduce-an-internal-API-for-FIPS-service-indicator.patch create mode 100644 libgcrypt-fips-Rejection-by-GCRYCTL_FIPS_REJECT_NON_FIPS-not-by-open-flags.patch create mode 100644 libgcrypt-fips-cipher-Add-GCRY_FIPS_FLAG_REJECT_PK_FLAGS.patch create mode 100644 libgcrypt-fips-cipher-Add-behavior-not-to-reject-but-mark-non-compliant.patch create mode 100644 libgcrypt-fips-cipher-Do-the-computation-when-marking-non-compliant.patch create mode 100644 libgcrypt-fips-cipher-Fix-memory-leak-for-gcry_pk_hash_sign.patch create mode 100644 libgcrypt-fips-cipher-Implement-FIPS-service-indicator-for-gcry_pk_hash_-API.patch create mode 100644 libgcrypt-fips-cipher-Implement-new-FIPS-service-indicator-for-cipher_open.patch create mode 100644 libgcrypt-fips-ecc-Add-rejecting-or-marking-for-gcry_pk_get_curve.patch create mode 100644 libgcrypt-fips-ecc-Check-DATA-in-gcry_pk_sign-verify-in-FIPS-mode.patch create mode 100644 libgcrypt-fips-kdf-Implement-new-FIPS-service-indicator-for-gcry_kdf_derive.patch create mode 100644 libgcrypt-fips-mac-Implement-new-FIPS-service-indicator-for-gcry_mac_open.patch create mode 100644 libgcrypt-fips-md-Implement-new-FIPS-service-indicator-for-gcry_md_hash_.patch create mode 100644 libgcrypt-fips-md-Implement-new-FIPS-service-indicator-for-gcry_md_open-API.patch create mode 100644 libgcrypt-fips-md-gcry_md_copy-should-care-about-FIPS-service-indicator.patch create mode 100644 libgcrypt-fips-tests-Add-t-digest.patch create mode 100644 libgcrypt-fips-tests-Add-tests-for-md_open-write-read-close-for-t-digest.patch create mode 100644 libgcrypt-jitterentropy-3.4.0.patch create mode 100644 libgcrypt-md-Fix-gcry_md_algo_info-to-mark-reject-under-FIPS-mode.patch create mode 100644 libgcrypt-md-Make-SHA-1-non-FIPS-internally-for-1.12-API.patch create mode 100644 libgcrypt-md-Use-check_digest_algo_spec-in-_gcry_md_selftest.patch create mode 100644 libgcrypt-no-deprecated-grep-alias.patch create mode 100644 libgcrypt-nobetasuffix.patch create mode 100644 libgcrypt-ppc-enable-P10-assembly-with-ENABLE_FORCE_SOF.patch create mode 100644 libgcrypt-rol64-redefinition.patch create mode 100644 libgcrypt-tests-Add-more-tests-to-tests-t-fips-service-ind.patch create mode 100644 libgcrypt-tests-Allow-tests-with-USE_RSA.patch create mode 100644 libgcrypt-tests-Update-t-fips-service-ind-using-GCRY_MD_SHA256-for-KDF-tests.patch create mode 100644 libgcrypt-tests-fips-Add-gcry_cipher_open-tests.patch create mode 100644 libgcrypt-tests-fips-Add-gcry_mac_open-tests.patch create mode 100644 libgcrypt-tests-fips-Move-KDF-tests-to-t-fips-service-ind.patch create mode 100644 libgcrypt-tests-fips-Rename-t-fips-service-ind.patch create mode 100644 libgcrypt.changes create mode 100644 libgcrypt.keyring create mode 100644 libgcrypt.spec create mode 100644 random.conf diff --git a/.gitattributes b/.gitattributes new file mode 100644 index 0000000..9b03811 --- /dev/null +++ b/.gitattributes @@ -0,0 +1,23 @@ +## Default LFS +*.7z filter=lfs diff=lfs merge=lfs -text +*.bsp filter=lfs diff=lfs merge=lfs -text +*.bz2 filter=lfs diff=lfs merge=lfs -text +*.gem filter=lfs diff=lfs merge=lfs -text +*.gz filter=lfs diff=lfs merge=lfs -text +*.jar filter=lfs diff=lfs merge=lfs -text +*.lz filter=lfs diff=lfs merge=lfs -text +*.lzma filter=lfs diff=lfs merge=lfs -text +*.obscpio filter=lfs diff=lfs merge=lfs -text +*.oxt filter=lfs diff=lfs merge=lfs -text +*.pdf filter=lfs diff=lfs merge=lfs -text +*.png filter=lfs diff=lfs merge=lfs -text +*.rpm filter=lfs diff=lfs merge=lfs -text +*.tbz filter=lfs diff=lfs merge=lfs -text +*.tbz2 filter=lfs diff=lfs merge=lfs -text +*.tgz filter=lfs diff=lfs merge=lfs -text +*.ttf filter=lfs diff=lfs merge=lfs -text +*.txz filter=lfs diff=lfs merge=lfs -text +*.whl filter=lfs diff=lfs merge=lfs -text +*.xz filter=lfs diff=lfs merge=lfs -text +*.zip filter=lfs diff=lfs merge=lfs -text +*.zst filter=lfs diff=lfs merge=lfs -text diff --git a/.gitignore b/.gitignore new file mode 100644 index 0000000..57affb6 --- /dev/null +++ b/.gitignore @@ -0,0 +1 @@ +.osc diff --git a/baselibs.conf b/baselibs.conf new file mode 100644 index 0000000..a018a0a --- /dev/null +++ b/baselibs.conf @@ -0,0 +1,8 @@ +libgcrypt20 + provides "libgcrypt- = " + obsoletes "libgcrypt- <= " + provides "libgcrypt20-hmac- = -%release" + obsoletes "libgcrypt20-hmac- < -%release" +libgcrypt-devel + requires -libgcrypt- + requires "libgcrypt20- = " diff --git a/hwf.deny b/hwf.deny new file mode 100644 index 0000000..2236468 --- /dev/null +++ b/hwf.deny @@ -0,0 +1,34 @@ +# This file can be used to globally disable the use of hardware +# based optimizations. Supported options are: +# padlock-rng +# padlock-aes +# padlock-sha +# padlock-mmul +# intel-cpu +# intel-fast-shld +# intel-bmi2 +# intel-ssse3 +# intel-sse4.1 +# intel-pclmul +# intel-aesni +# intel-rdrand +# intel-avx +# intel-avx2 +# intel-fast-vpgather +# intel-rdtsc +# intel-shaext +# intel-vaes-vpclmul +# arm-neon +# arm-aes +# arm-sha1 +# arm-sha2 +# arm-pmull +# ppc-vcrypto +# ppc-arch_3_00 +# ppc-arch_2_07 +# ppc-arch_3_10 +# s390x-msa +# s390x-msa-4 +# s390x-msa-8 +# s390x-msa-9 +# s390x-vx diff --git a/libgcrypt-1.10.0-allow_FSM_same_state.patch b/libgcrypt-1.10.0-allow_FSM_same_state.patch new file mode 100644 index 0000000..843cfea --- /dev/null +++ b/libgcrypt-1.10.0-allow_FSM_same_state.patch @@ -0,0 +1,15 @@ +Index: libgcrypt-1.10.0/src/fips.c +=================================================================== +--- libgcrypt-1.10.0.orig/src/fips.c ++++ libgcrypt-1.10.0/src/fips.c +@@ -890,6 +890,10 @@ fips_new_state (enum module_states new_s + + } + ++ /* Allow a transition to the current state */ ++ if (current_state == new_state) ++ ok = 1; ++ + if (ok) + { + current_state = new_state; diff --git a/libgcrypt-1.10.3.tar.bz2 b/libgcrypt-1.10.3.tar.bz2 new file mode 100644 index 0000000..653803f --- /dev/null +++ b/libgcrypt-1.10.3.tar.bz2 @@ -0,0 +1,3 @@ +version https://git-lfs.github.com/spec/v1 +oid sha256:8b0870897ac5ac67ded568dcfadf45969cfa8a6beb0fd60af2a9eadc2a3272aa +size 3783827 diff --git a/libgcrypt-1.10.3.tar.bz2.sig b/libgcrypt-1.10.3.tar.bz2.sig new file mode 100644 index 0000000000000000000000000000000000000000000000000000000000000000..4172518bc29eafb0304aa2c7def555b970a6accea442a7542087b98c44485773 GIT binary patch literal 238 zcmeAuWnmEGV2~A4WXWBXm$E!p!y#PSlPRcU`VKV*t6Qv0sliEW8MrtFU?N}p82-vF z=ITAZ*qv<_(;dOxrp<8yN$DSFdR>!gz3<7nXwGD1Muyiq%7Ht6>~>#&|Ibh5V-ok6 zm#e%* literal 0 HcmV?d00001 diff --git a/libgcrypt-1.11.0.tar.bz2 b/libgcrypt-1.11.0.tar.bz2 new file mode 100644 index 0000000..28d1068 --- /dev/null +++ b/libgcrypt-1.11.0.tar.bz2 @@ -0,0 +1,3 @@ +version https://git-lfs.github.com/spec/v1 +oid sha256:09120c9867ce7f2081d6aaa1775386b98c2f2f246135761aae47d81f58685b9c +size 4180345 diff --git a/libgcrypt-1.11.0.tar.bz2.sig b/libgcrypt-1.11.0.tar.bz2.sig new file mode 100644 index 0000000000000000000000000000000000000000000000000000000000000000..2debe948a9ffbbc9c835efae5cce0c65517df124ea67ba4cc04d1dffdd7b3160 GIT binary patch literal 119 zcmeAuWnmEGV2~A4WXWBXm$E!p!y#PSlPRcU`VKV*t6Qv0X+=xZ7`QkEU?T178UE=O z)|M}6Y-XM7H2JWvsFP0?XX&fr%U>#e4G(K{b;T<%GJNLLSKO|_Z@vBphsk!en!WkH T(k44uvO>;;f4NZp`vWfkiCryG literal 0 HcmV?d00001 diff --git a/libgcrypt-1.11.1-public-SLI-API.patch b/libgcrypt-1.11.1-public-SLI-API.patch new file mode 100644 index 0000000..42a9276 --- /dev/null +++ b/libgcrypt-1.11.1-public-SLI-API.patch @@ -0,0 +1,37 @@ +Index: libgcrypt-1.11.1/src/gcrypt.h.in +=================================================================== +--- libgcrypt-1.11.1.orig/src/gcrypt.h.in ++++ libgcrypt-1.11.1/src/gcrypt.h.in +@@ -335,12 +335,9 @@ enum gcry_ctl_cmds + GCRYCTL_FIPS_SERVICE_INDICATOR_MAC = 85, + GCRYCTL_FIPS_SERVICE_INDICATOR_MD = 86, + GCRYCTL_FIPS_SERVICE_INDICATOR_PK_FLAGS = 87, +- GCRYCTL_MD_CUSTOMIZE = 88 +-#ifdef _GCRYPT_IN_LIBGCRYPT /* This is not yet part of the public API. */ +- , ++ GCRYCTL_MD_CUSTOMIZE = 88, + GCRYCTL_FIPS_SERVICE_INDICATOR = 89, + GCRYCTL_FIPS_REJECT_NON_FIPS = 90 +-#endif /*_GCRYPT_IN_LIBGCRYPT*/ + }; + + /* Perform various operations defined by CMD. */ +@@ -1977,8 +1974,6 @@ void gcry_log_debugsxp (const char *text + char *gcry_get_config (int mode, const char *what); + + /* Convinience macro to access the FIPS service indicator. */ +-#ifdef _GCRYPT_IN_LIBGCRYPT /* This is not yet part of the public API. */ +- + #define gcry_get_fips_service_indicator() \ + gcry_control (GCRYCTL_FIPS_SERVICE_INDICATOR) + +@@ -2012,9 +2007,6 @@ char *gcry_get_config (int mode, const c + #define GCRY_FIPS_FLAG_REJECT_DEFAULT \ + GCRY_FIPS_FLAG_REJECT_COMPAT110 + +-#endif /*_GCRYPT_IN_LIBGCRYPT*/ +- +- + /* Log levels used by the internal logging facility. */ + enum gcry_log_levels + { diff --git a/libgcrypt-1.11.1.tar.bz2 b/libgcrypt-1.11.1.tar.bz2 new file mode 100644 index 0000000..aa03790 --- /dev/null +++ b/libgcrypt-1.11.1.tar.bz2 @@ -0,0 +1,3 @@ +version https://git-lfs.github.com/spec/v1 +oid sha256:24e91c9123a46c54e8371f3a3a2502f1198f2893fbfbf59af95bc1c21499b00e +size 4233557 diff --git a/libgcrypt-1.11.1.tar.bz2.sig b/libgcrypt-1.11.1.tar.bz2.sig new file mode 100644 index 0000000000000000000000000000000000000000000000000000000000000000..62de6154dfc87f2d93e84b8fd2f4a26b2e9f2dfc6cd988e73e4a8305d7d1021d GIT binary patch literal 119 zcmeAuWnmEGVvrS6WXWBXm$E!p!y#PSlPRcU`VKV*t6Qv08Pbh^7`QkEU?N-QFfvR& zliXh{lxlF3mDxiqReAqxzNuWrYmP2DYpc_Eedm)rhJS|Foa@@920I1Y1WdHyG literal 0 HcmV?d00001 diff --git a/libgcrypt-CVE-2024-2236.patch b/libgcrypt-CVE-2024-2236.patch new file mode 100644 index 0000000..0d39790 --- /dev/null +++ b/libgcrypt-CVE-2024-2236.patch @@ -0,0 +1,1839 @@ +From 984e245fd21ff6e0058403f620f760013a744a3a Mon Sep 17 00:00:00 2001 +From: Jakub Jelen +Date: Fri, 7 Jun 2024 14:42:33 +0200 +Subject: [PATCH 1/7] rsa: Do not accept invalid PKCS#1.5 padding when + deciphering + +The current code can accept 0-length padding when deciphering +PKCS#1.5 ciphertext. This is against the specification and hopefully +nobody depends on this. + +-- +* cipher/rsa-common.c (_gcry_rsa_pkcs1_decode_for_enc): Fail for too + short padding. +* src/const-time.h (ct_lt_s): New. + +Signed-off-by: Jakub Jelen +--- + cipher/rsa-common.c | 2 ++ + src/const-time.h | 6 ++++++ + 2 files changed, 8 insertions(+) + +Index: libgcrypt-1.11.1/cipher/rsa-common.c +=================================================================== +--- libgcrypt-1.11.1.orig/cipher/rsa-common.c ++++ libgcrypt-1.11.1/cipher/rsa-common.c +@@ -28,6 +28,7 @@ + #include "cipher.h" + #include "pubkey-internal.h" + #include "const-time.h" ++#include "bufhelp.h" + + + /* Turn VALUE into an octet string and store it in an allocated buffer +@@ -191,6 +192,45 @@ memmov_independently (void *dst, const v + } + + ++static unsigned char * ++mpi_to_string(gcry_mpi_t value, size_t nframe) ++{ ++ unsigned char *frame = NULL; ++ unsigned char *p; ++ size_t noff; ++ /* Allocate memory to fit the whole MPI limbs and allow moving it later to the right place */ ++ size_t alloc_len = value->nlimbs * BYTES_PER_MPI_LIMB; ++ ++ /* for too short input, we need to allocate at least modulus length (which might still be valid in case of OAEP) */ ++ noff = (alloc_len < nframe) ? nframe - alloc_len : 0; ++ alloc_len = alloc_len + noff; ++ ++ if ( !(frame = xtrymalloc_secure (alloc_len))) ++ return NULL; ++ ++ if (noff) ++ memset (frame, 0, noff); ++ p = frame + noff; ++ /* shovel the MPI content to the buffer as it is */ ++ for (int i = value->nlimbs - 1; i >= 0; i--) ++ { ++ mpi_limb_t *alimb = &value->d[i]; ++#if BYTES_PER_MPI_LIMB == 4 ++ buf_put_be32 (p, *alimb); ++ p += 4; ++#elif BYTES_PER_MPI_LIMB == 8 ++ buf_put_be64 (p, *alimb); ++ p += 8; ++#else ++# error please implement for this limb size. ++#endif ++ } ++ /* Move the MPI to the right place -- with the least significant bytes aligned to the modulus length ++ * -- this might keep some leading zeroes at the beginning of the buffer, but this might be valid for OAEP */ ++ memmov_independently (frame, frame + (alloc_len - nframe), nframe, alloc_len); ++ return frame; ++} ++ + /* Decode a plaintext in VALUE assuming pkcs#1 block type 2 padding. + NBITS is the size of the secret key. On success the result is + stored as a newly allocated buffer at R_RESULT and its valid length at +@@ -199,7 +239,6 @@ gpg_err_code_t + _gcry_rsa_pkcs1_decode_for_enc (unsigned char **r_result, size_t *r_resultlen, + unsigned int nbits, gcry_mpi_t value) + { +- gcry_error_t err; + unsigned char *frame = NULL; + size_t nframe = (nbits+7) / 8; + size_t n, n0; +@@ -208,6 +247,17 @@ _gcry_rsa_pkcs1_decode_for_enc (unsigned + + *r_result = NULL; + ++ { ++#ifdef WITH_MARVIN_WORKAROUND ++ frame = mpi_to_string(value, nframe); ++ if (frame == NULL) ++ return gpg_err_code_from_syserror (); ++ ++ n = 0; ++ failed |= ct_not_equal_byte (frame[n++], 0x00); ++#else ++ gcry_error_t err; ++ + if ( !(frame = xtrymalloc_secure (nframe))) + return gpg_err_code_from_syserror (); + +@@ -235,6 +285,9 @@ _gcry_rsa_pkcs1_decode_for_enc (unsigned + n = 0; + if (!frame[0]) + n++; ++#endif /* WITH_MARVIN_WORKAROUND */ ++ } ++ + failed |= ct_not_equal_byte (frame[n++], 0x02); + + /* Find the terminating zero byte. */ +@@ -247,6 +300,8 @@ _gcry_rsa_pkcs1_decode_for_enc (unsigned + + failed |= not_found; + n0 += ct_is_zero (not_found); /* Skip the zero byte. */ ++ /* the valid padding is at least 8 bytes -- the plaintext needs to start at index 11 or later */ ++ failed |= ct_lt_s (n0, 11); + + /* To avoid an extra allocation we reuse the frame buffer. The only + caller of this function will anyway free the result soon. */ +@@ -263,6 +318,187 @@ _gcry_rsa_pkcs1_decode_for_enc (unsigned + } + + ++#ifdef WITH_MARVIN_WORKAROUND ++#define SHA256_LEN 32 ++static gcry_err_code_t ++rsa_prf(unsigned char *out, size_t out_len, const char *label, size_t label_len, unsigned char *kdk, size_t nbits) ++{ ++ gcry_err_code_t rc = GPG_ERR_NO_ERROR; ++ size_t pos; ++ uint16_t iter = 0; ++ unsigned char be_iter[2]; ++ unsigned char be_bitlen[2]; ++ gcry_md_hd_t hd; ++ gcry_error_t err; ++ ++ be_bitlen[0] = (nbits >> 8) & 0xff; ++ be_bitlen[1] = nbits & 0xff; ++ ++ err = _gcry_md_open (&hd, GCRY_MD_SHA256, GCRY_MD_FLAG_HMAC); ++ if (err) ++ { ++ return GPG_ERR_INTERNAL; ++ } ++ err = _gcry_md_setkey (hd, kdk, SHA256_LEN); ++ if (err) ++ { ++ _gcry_md_close (hd); ++ return GPG_ERR_INTERNAL; ++ } ++ for (pos = 0; pos < out_len; pos += SHA256_LEN, iter++) ++ { ++ unsigned char *tmp; ++ ++ _gcry_md_reset(hd); ++ ++ be_iter[0] = (iter >> 8) & 0xff; ++ be_iter[1] = iter & 0xff; ++ _gcry_md_write (hd, be_iter, sizeof (be_iter)); ++ _gcry_md_write (hd, label, label_len); ++ _gcry_md_write (hd, be_bitlen, sizeof (be_bitlen)); ++ ++ tmp = _gcry_md_read(hd, 0); ++ if (pos + SHA256_LEN > out_len) ++ { ++ memcpy(out + pos, tmp, out_len - pos); ++ } ++ else ++ { ++ memcpy(out + pos, tmp, SHA256_LEN); ++ } ++ } ++ _gcry_md_close (hd); ++ return rc; ++} ++ ++ ++/* Decode a plaintext in VALUE assuming pkcs#1 block type 2 padding. ++ NBITS is the size of the secret key. On success the result is ++ stored as a newly allocated buffer at R_RESULT and its valid length at ++ R_RESULTLEN. On error R_RESULT contains bogus value of random length. ++ For more information, see description of Implicit Rejection in Marvin paper ++ https://people.redhat.com/~hkario/marvin/marvin-attack-paper.pdf */ ++#define MAX_LEN_GEN_TRIES 128 ++gpg_err_code_t ++_gcry_rsa_pkcs1_decode_for_enc_implicit_rejection (unsigned char **r_result, ++ size_t *r_resultlen, ++ unsigned int nbits, ++ gcry_mpi_t value, ++ unsigned char *kdk) ++{ ++ unsigned char *frame = NULL; ++ size_t nframe = (nbits+7) / 8; ++ size_t n, n0; ++ unsigned int failed = 0; ++ unsigned int not_found = 1; ++ int i, j; ++ uint16_t len_mask; ++ uint16_t max_sep_offset; ++ unsigned char *synthetic = NULL; ++ unsigned long synthethic_length; ++ uint16_t len_candidate; ++ unsigned char candidate_lengths[MAX_LEN_GEN_TRIES * sizeof(len_candidate)]; ++ int synth_msg_index = 0, msg_index; ++ ++ *r_result = NULL; ++ ++ synthetic = xtrymalloc(nframe); ++ if (synthetic == NULL) ++ { ++ free (synthetic); ++ return gpg_err_code_from_syserror (); ++ } ++ ++ if (rsa_prf(synthetic, nframe, "message", 7, kdk, nframe * 8) < 0) ++ { ++ xfree (synthetic); ++ return GPG_ERR_INTERNAL; ++ } ++ ++ /* decide how long the random message should be */ ++ if (rsa_prf(candidate_lengths, sizeof(candidate_lengths), ++ "length", 6, kdk, MAX_LEN_GEN_TRIES * sizeof(len_candidate) * 8) < 0) ++ { ++ xfree (synthetic); ++ return GPG_ERR_INTERNAL; ++ } ++ ++ len_mask = max_sep_offset = nframe - 2 - 8; ++ len_mask |= len_mask >> 1; ++ len_mask |= len_mask >> 2; ++ len_mask |= len_mask >> 4; ++ len_mask |= len_mask >> 8; ++ ++ synthethic_length = 0; ++ for (i = 0; i < MAX_LEN_GEN_TRIES * (int)sizeof(len_candidate); ++ i += sizeof(len_candidate)) ++ { ++ len_candidate = (candidate_lengths[i] << 8) | candidate_lengths[i + 1]; ++ len_candidate &= len_mask; ++ ++ synthethic_length = ct_ulong_select( ++ len_candidate, synthethic_length, ++ ct_lt(len_candidate, max_sep_offset)); ++ } ++ ++ synth_msg_index = nframe - synthethic_length; ++ ++ /* we have alternative message ready, check the real one */ ++ /* mostly copy from _gcry_rsa_pkcs1_decode_for_enc */ ++ frame = mpi_to_string(value, nframe); ++ if (frame == NULL) ++ { ++ xfree (synthetic); ++ return gpg_err_code_from_syserror (); ++ } ++ ++ /* FRAME = 0x00 || 0x02 || PS || 0x00 || M */ ++ n = 0; ++ failed |= ct_not_equal_byte (frame[n++], 0x00); ++ failed |= ct_not_equal_byte (frame[n++], 0x02); ++ ++ /* Find the terminating zero byte. */ ++ n0 = n; ++ for (; n < nframe; n++) ++ { ++ not_found &= ct_not_equal_byte (frame[n], 0x00); ++ n0 += not_found; ++ } ++ ++ failed |= not_found; ++ n0 += ct_is_zero (not_found); /* Skip the zero byte. */ ++ /* the valid padding is at least 8 bytes -- the plaintext needs to start at index 11 or later */ ++ failed |= ct_lt_s (n0, 11); ++ ++ msg_index = ct_ulong_select (synth_msg_index, n0, failed); ++ ++ /* To avoid the need memmove (O(N*log(N))), we use separate buffer where we move either ++ * of the messages. We can now also use the msg_index safely as its timing is not ++ * possible to distinguish valid and invalid padding */ ++ for (i = msg_index, j = 0; i < nframe && j < nframe; i++, j++) ++ { ++ frame[j] = ct_uchar_select (synthetic[i], frame[i], failed); ++ } ++ ++ *r_resultlen = j; ++ *r_result = frame; ++ ++ if (DBG_CIPHER) ++ { ++ if (!failed) ++ log_printhex ("value extracted from PKCS#1 block type 2 encoded data", ++ frame, nframe - n0); ++ else ++ log_printhex ("Synthetic value from implicit rejection", ++ synthetic, synthethic_length); ++ } ++ ++ xfree (synthetic); ++ return 0; ++} ++#endif /* WITH_MARVIN_WORKAROUND */ ++ ++ + /* Encode {VALUE,VALUELEN} for an NBITS keys and hash algorithm ALGO + using the pkcs#1 block type 1 padding. On success the result is + stored as a new MPI at R_RESULT. On error the value at R_RESULT is +@@ -684,14 +920,23 @@ _gcry_rsa_oaep_decode (unsigned char **r + happen due to the leading zero in OAEP frames and due to the + following random octets (seed^mask) which may have leading zero + bytes. This all is needed to cope with our leading zeroes +- suppressing MPI implementation. The code implictly implements ++ suppressing MPI implementation. The code implicitly implements + Step 1b (bail out if NFRAME != N). */ ++#ifdef WITH_MARVIN_WORKAROUND ++ frame = mpi_to_string(value, nkey); ++ if (frame == NULL) ++ { ++ xfree (lhash); ++ return gpg_err_code_from_syserror (); ++ } ++#else + rc = octet_string_from_mpi (&frame, NULL, value, nkey); + if (rc) + { + xfree (lhash); + return GPG_ERR_ENCODING_PROBLEM; + } ++#endif /* WITH_MARVIN_WORKAROUND */ + nframe = nkey; + + /* Step 1c: Check that the key is long enough. */ +@@ -706,7 +951,7 @@ _gcry_rsa_oaep_decode (unsigned char **r + gcry_mpi_aprint above. */ + + /* Allocate space for SEED and DB. */ +- seed = xtrymalloc_secure (nframe - 1); ++ seed = xtrymalloc_secure (nframe); + if (!seed) + { + rc = gpg_err_code_from_syserror (); +Index: libgcrypt-1.11.1/src/const-time.h +=================================================================== +--- libgcrypt-1.11.1.orig/src/const-time.h ++++ libgcrypt-1.11.1/src/const-time.h +@@ -26,6 +26,7 @@ + #define ct_not_memequal _gcry_ct_not_memequal + #define ct_memequal _gcry_ct_memequal + #define ct_memmov_cond _gcry_ct_memmov_cond ++#define ct_memcpy _gcry_ct_memcpy + + + #ifndef HAVE_GCC_ASM_VOLATILE_MEMORY +@@ -33,6 +34,20 @@ extern volatile unsigned int _gcry_ct_vz + extern volatile unsigned int _gcry_ct_vone; + #endif + ++/* ++ * Return 1 if A < B and return 0 otherwise. ++ */ ++static inline int ++ct_lt (unsigned int a, unsigned int b) ++{ ++ return (a ^ ((a ^ b) | ((a - b) ^ b))) >> (sizeof(unsigned int) * 8 - 1); ++} ++ ++static inline size_t ++ct_lt_s (size_t a, size_t b) ++{ ++ return ((a ^ ((a ^ b) | ((a - b) ^ b))) >> (sizeof(size_t) * 8 - 1)); ++} + + /* + * Return 0 if A is 0 and return 1 otherwise. +@@ -114,7 +129,7 @@ unsigned int _gcry_ct_memequal (const vo + DEFINE_CT_TYPE_GEN_MASK(uintptr, uintptr_t) + DEFINE_CT_TYPE_GEN_MASK(ulong, unsigned long) + DEFINE_CT_TYPE_GEN_MASK(int16, int16_t) +- ++DEFINE_CT_TYPE_GEN_MASK(uchar, unsigned char) + /* + * Return all bits set if A is 0 and return 1 otherwise. + */ +@@ -139,7 +154,7 @@ DEFINE_CT_TYPE_GEN_MASK(int16, int16_t) + DEFINE_CT_TYPE_GEN_INV_MASK(uintptr, uintptr_t) + DEFINE_CT_TYPE_GEN_INV_MASK(ulong, unsigned long) + DEFINE_CT_TYPE_GEN_INV_MASK(int16, int16_t) +- ++DEFINE_CT_TYPE_GEN_INV_MASK(uchar, unsigned char) + /* + * Return A when OP_ENABLED=1 + * otherwise, return B +@@ -155,7 +170,7 @@ DEFINE_CT_TYPE_GEN_INV_MASK(int16, int16 + DEFINE_CT_TYPE_SELECT_FUNC(uintptr, uintptr_t) + DEFINE_CT_TYPE_SELECT_FUNC(ulong, unsigned long) + DEFINE_CT_TYPE_SELECT_FUNC(int16, int16_t) +- ++DEFINE_CT_TYPE_SELECT_FUNC(uchar, unsigned char) + /* + * Return NULL when OP_ENABLED=1 + * otherwise, return W +@@ -174,5 +189,6 @@ sexp_null_cond (gcry_sexp_t w, unsigned + */ + void _gcry_ct_memmov_cond (void *dst, const void *src, size_t len, + unsigned long op_enable); ++void _gcry_ct_memcpy (void *dst, const void *src, size_t len, size_t buffer_len); + + #endif /*GCRY_CONST_TIME_H*/ +Index: libgcrypt-1.11.1/cipher/rsa.c +=================================================================== +--- libgcrypt-1.11.1.orig/cipher/rsa.c ++++ libgcrypt-1.11.1/cipher/rsa.c +@@ -1197,7 +1197,11 @@ secret_blinded (gcry_mpi_t output, gcry_ + /* Undo blinding. Here we calculate: y = (x * r^-1) mod n, where x + * is the blinded decrypted data, ri is the modular multiplicative + * inverse of r and n is the RSA modulus. */ ++#ifdef WITH_MARVIN_WORKAROUND ++ mpi_mulm_sec (output, output, ri, sk->n); ++#else + mpi_mulm (output, output, ri, sk->n); ++#endif /* WITH_MARVIN_WORKAROUND */ + + _gcry_mpi_release (r); + _gcry_mpi_release (ri); +@@ -1432,6 +1436,7 @@ rsa_encrypt (gcry_sexp_t *r_ciph, gcry_s + } + + ++#define SHA256_LEN 32 + static gcry_err_code_t + rsa_decrypt (gcry_sexp_t *r_plain, gcry_sexp_t s_data, gcry_sexp_t keyparms) + +@@ -1447,6 +1452,9 @@ rsa_decrypt (gcry_sexp_t *r_plain, gcry_ + unsigned int nbits = rsa_get_nbits (keyparms); + gcry_sexp_t result = NULL; + gcry_sexp_t dummy = NULL; ++#ifdef WITH_MARVIN_WORKAROUND ++ unsigned char kdk[SHA256_LEN]; ++#endif /* WITH_MARVIN_WORKAROUND */ + + rc = rsa_check_keysize (nbits); + if (rc) +@@ -1494,6 +1502,71 @@ rsa_decrypt (gcry_sexp_t *r_plain, gcry_ + mpi_normalize (data); + mpi_fdiv_r (data, data, sk.n); + ++#ifdef WITH_MARVIN_WORKAROUND ++ /* Implicit rejection: Derive KDK */ ++ if (ctx.encoding == PUBKEY_ENC_PKCS1) ++ { ++ unsigned char *buf, *tmp; ++ unsigned int nbytes = (mpi_get_nbits (sk.n)+7)/8; ++ unsigned char key[SHA256_LEN]; ++ gcry_md_hd_t hd; ++ ++ /* (a) Convert `d` to big endian representation, left padded to the length of `n` */ ++ rc = _gcry_mpi_to_octet_string (&buf, NULL, sk.d, nbytes); ++ if (rc) ++ { ++ rc = GPG_ERR_INTERNAL; ++ goto leave; ++ } ++ ++ /* (b) Hash it using SHA-256 */ ++ rc = _gcry_md_open (&hd, GCRY_MD_SHA256, 0); ++ if (rc) ++ { ++ xfree (buf); ++ rc = GPG_ERR_INTERNAL; ++ goto leave; ++ } ++ _gcry_md_write (hd, buf, nbytes); ++ /* keep the buffer around -- it will be needed for the ciphertext */ ++ tmp = _gcry_md_read (hd, GCRY_MD_SHA256); ++ memcpy(key, tmp, SHA256_LEN); ++ _gcry_md_close (hd); ++ ++ /* (c) Use the hash as a SHA-256 HMAC key and ciphertext as a message */ ++ rc = _gcry_md_open (&hd, GCRY_MD_SHA256, GCRY_MD_FLAG_HMAC); ++ if (rc) ++ { ++ xfree (buf); ++ rc = GPG_ERR_INTERNAL; ++ goto leave; ++ } ++ rc = _gcry_md_setkey (hd, key, sizeof (key)); ++ if (rc) ++ { ++ xfree (buf); ++ _gcry_md_close (hd); ++ rc = GPG_ERR_INTERNAL; ++ goto leave; ++ } ++ ++ /* We need to convert the ciphertext to string, padded to the length of modulus */ ++ rc = _gcry_mpi_to_octet_string (NULL, buf, data, nbytes); ++ if (rc) ++ { ++ xfree (buf); ++ _gcry_md_close (hd); ++ rc = GPG_ERR_INTERNAL; ++ goto leave; ++ } ++ _gcry_md_write (hd, buf, nbytes); ++ xfree (buf); ++ buf = _gcry_md_read (hd, 0); ++ memcpy(kdk, buf, SHA256_LEN); ++ _gcry_md_close (hd); ++ } ++#endif /* WITH_MARVIN_WORKAROUND */ ++ + /* Allocate MPI for the plaintext. */ + plain = mpi_snew (nbits); + +@@ -1524,10 +1597,26 @@ rsa_decrypt (gcry_sexp_t *r_plain, gcry_ + switch (ctx.encoding) + { + case PUBKEY_ENC_PKCS1: ++#ifdef WITH_MARVIN_WORKAROUND ++ if (!(ctx.flags & PUBKEY_FLAG_NO_IMPLICIT_REJECTION)) ++ { ++ rc = _gcry_rsa_pkcs1_decode_for_enc_implicit_rejection (&unpad, &unpadlen, nbits, plain, kdk); ++ mpi_free (plain); ++ plain = NULL; ++ rc_sexp = sexp_build (&result, NULL, "(value %c)", (int)unpadlen, unpad, (nbits + 7) / 8); ++ *r_plain = result; ++ rc = ct_ulong_select (rc_sexp, rc, ct_is_zero (rc) & ct_is_not_zero (rc_sexp)); ++ break; ++ } ++#endif /* WITH_MARVIN_WORKAROUND */ + rc = _gcry_rsa_pkcs1_decode_for_enc (&unpad, &unpadlen, nbits, plain); + mpi_free (plain); + plain = NULL; ++#ifdef WITH_MARVIN_WORKAROUND ++ rc_sexp = sexp_build (&result, NULL, "(value %c)", (int)unpadlen, unpad, (nbits + 7) / 8); ++#else + rc_sexp = sexp_build (&result, NULL, "(value %b)", (int)unpadlen, unpad); ++#endif /* WITH_MARVIN_WORKAROUND */ + *r_plain = sexp_null_cond (result, ct_is_not_zero (rc)); + dummy = sexp_null_cond (result, ct_is_zero (rc)); + sexp_release (dummy); +@@ -1541,7 +1630,11 @@ rsa_decrypt (gcry_sexp_t *r_plain, gcry_ + plain, ctx.label, ctx.labellen); + mpi_free (plain); + plain = NULL; ++#ifdef WITH_MARVIN_WORKAROUND ++ rc_sexp = sexp_build (&result, NULL, "(value %c)", (int)unpadlen, unpad, (nbits + 7) / 8); ++#else + rc_sexp = sexp_build (&result, NULL, "(value %b)", (int)unpadlen, unpad); ++#endif /* WITH_MARVIN_WORKAROUND */ + *r_plain = sexp_null_cond (result, ct_is_not_zero (rc)); + dummy = sexp_null_cond (result, ct_is_zero (rc)); + sexp_release (dummy); +Index: libgcrypt-1.11.1/configure.ac +=================================================================== +--- libgcrypt-1.11.1.orig/configure.ac ++++ libgcrypt-1.11.1/configure.ac +@@ -582,6 +582,22 @@ AC_ARG_ENABLE(jent-support, + jentsupport=$enableval,jentsupport=yes) + AC_MSG_RESULT($jentsupport) + ++AC_MSG_CHECKING([whether a Marvin workaround is requested]) ++AC_ARG_ENABLE(marvin-workaround, ++ AS_HELP_STRING([--enable-marvin-workaround], ++ [Enable Marvin workaround for constant time PKCS1.5 depadding]), ++ [with_marvin_workaround="$enableval"], ++ [with_marvin_workaround=no]) ++AC_MSG_RESULT($with_marvin_workaround) ++if test "$with_marvin_workaround" = no ; then ++ WITH_MARVIN_WORKAROUND='' ++else ++ AC_DEFINE(WITH_MARVIN_WORKAROUND,1, ++ [Define to provide constant time PKCS1.5 depadding]) ++fi ++AM_CONDITIONAL(WITH_MARVIN_WORKAROUND, test "x$with_marvin_workaround" != xno) ++AC_SUBST(WITH_MARVIN_WORKAROUND) ++ + # Implementation of the --disable-padlock-support switch. + AC_MSG_CHECKING([whether padlock support is requested]) + AC_ARG_ENABLE(padlock-support, +Index: libgcrypt-1.11.1/mpi/Makefile.am +=================================================================== +--- libgcrypt-1.11.1.orig/mpi/Makefile.am ++++ libgcrypt-1.11.1/mpi/Makefile.am +@@ -181,3 +181,7 @@ EXTRA_libmpi_la_SOURCES = \ + asm-common-aarch64.h \ + asm-common-amd64.h \ + asm-common-i386.h ++ ++if WITH_MARVIN_WORKAROUND ++libmpi_la_SOURCES += mpi-mul-cs.c ++endif +Index: libgcrypt-1.11.1/mpi/mpi-internal.h +=================================================================== +--- libgcrypt-1.11.1.orig/mpi/mpi-internal.h ++++ libgcrypt-1.11.1/mpi/mpi-internal.h +@@ -241,6 +241,12 @@ void _gcry_mpih_mul_karatsuba_case( mpi_ + mpi_ptr_t vp, mpi_size_t vsize, + struct karatsuba_ctx *ctx ); + ++#ifdef WITH_MARVIN_WORKAROUND ++/*-- mpih-mul-cs.c --*/ ++void mul_cs(mpi_limb_t *ret, mpi_limb_t *a, mpi_limb_t *b, size_t n, mpi_limb_t *tmp); ++void mod_cs(mpi_limb_t *ret, mpi_limb_t *a, size_t anum, mpi_limb_t *mod, size_t modnum, mpi_limb_t *tmp); ++size_t mod_limb_numb(size_t anum, size_t modnum); ++#endif /* WITH_MARVIN_WORKAROUND */ + + /*-- mpih-mul_1.c (or xxx/cpu/ *.S) --*/ + mpi_limb_t _gcry_mpih_mul_1( mpi_ptr_t res_ptr, mpi_ptr_t s1_ptr, +Index: libgcrypt-1.11.1/mpi/mpi-mul-cs.c +=================================================================== +--- /dev/null ++++ libgcrypt-1.11.1/mpi/mpi-mul-cs.c +@@ -0,0 +1,263 @@ ++/* Copyright (c) 2024, Hubert Kario, Red Hat ++ * Released under BSD 2-Clause License, see LICENSE for details ++ */ ++#include ++#include ++#include ++#include ++#include ++#include "mpi-internal.h" ++#include "longlong.h" ++ ++/* For multiplication we're using schoolbook multiplication, ++ * so if we have two numbers, each with 6 "digits" (words) ++ * the multiplication is calculated as follows: ++ * A B C D E F ++ * x I J K L M N ++ * -------------- ++ * N*F ++ * N*E ++ * N*D ++ * N*C ++ * N*B ++ * N*A ++ * M*F ++ * M*E ++ * M*D ++ * M*C ++ * M*B ++ * M*A ++ * L*F ++ * L*E ++ * L*D ++ * L*C ++ * L*B ++ * L*A ++ * K*F ++ * K*E ++ * K*D ++ * K*C ++ * K*B ++ * K*A ++ * J*F ++ * J*E ++ * J*D ++ * J*C ++ * J*B ++ * J*A ++ * I*F ++ * I*E ++ * I*D ++ * I*C ++ * I*B ++ * + I*A ++ * ========================== ++ * N*B N*D N*F ++ * + N*A N*C N*E ++ * + M*B M*D M*F ++ * + M*A M*C M*E ++ * + L*B L*D L*F ++ * + L*A L*C L*E ++ * + K*B K*D K*F ++ * + K*A K*C K*E ++ * + J*B J*D J*F ++ * + J*A J*C J*E ++ * + I*B I*D I*F ++ * + I*A I*C I*E ++ * ++ * 1+1 1+3 1+5 ++ * 1+0 1+2 1+4 ++ * 0+1 0+3 0+5 ++ * 0+0 0+2 0+4 ++ * ++ * 0 1 2 3 4 5 6 ++ * which requires n^2 multiplications and 2n full length additions ++ * as we can keep every other result of limb multiplication in two separate ++ * limbs ++ */ ++ ++typedef mpi_limb_t limb_t; ++#if BYTES_PER_MPI_LIMB == SIZEOF_UNSIGNED_LONG_LONG ++#define LIMB_BIT_SIZE 64 ++#define LIMB_BYTE_SIZE 8 ++#elif BYTES_PER_MPI_LIMB == SIZEOF_UNSIGNED_LONG ++#define LIMB_BIT_SIZE 32 ++#define LIMB_BYTE_SIZE 4 ++/* if we're on a 32 bit platform */ ++#else ++#define LIMB_BIT_SIZE 16 ++#define LIMB_BYTE_SIZE 2 ++/* ++ * if the compiler doesn't have either a 128bit data type nor a "return ++ * high 64 bits of multiplication" ++ */ ++#endif ++ ++/* add two limbs with carry in, return carry out */ ++static limb_t ++_add_limb (limb_t *ret, limb_t a, limb_t b, limb_t carry) ++{ ++ limb_t carry1, carry2, t; ++ add_ssaaaa (carry1, t, 0, a, 0, carry); ++ add_ssaaaa (carry2, t, 0, b, 0, t); ++ *ret = t; ++ return carry1 + carry2; ++} ++ ++/* add two numbers of the same size, return overflow ++ * ++ * add a to b, place result in ret; all arrays need to be n limbs long ++ * return overflow from addition (0 or 1) ++ */ ++static limb_t ++add (limb_t *ret, limb_t *a, limb_t *b, size_t n) ++{ ++ limb_t c = 0; ++ for (ssize_t i = n - 1; i > -1; i--) ++ { ++ c = _add_limb (&ret[i], a[i], b[i], c); ++ } ++ return c; ++} ++ ++/* multiply two numbers of the same size ++ * ++ * multiply a by b, place result in ret; a and b need to be n limbs long ++ * ret needs to be 2*n limbs long, tmp needs to be 2 * n 2 limbs ++ * long ++ */ ++void ++mul_cs (limb_t *ret, limb_t *a, limb_t *b, size_t n, limb_t *tmp) ++{ ++ limb_t *r_odd, *r_even; ++ r_odd = tmp; ++ r_even = &tmp[2 * n]; ++ ++ for (size_t i = 0; i < 2 * n; i++) ++ { ++ ret[i] = 0; ++ } ++ ++ for (size_t i=0; i> 1); ++ shift_in = shift_out; ++ } ++} ++ ++/* copy from either a or b to ret based on flag ++ * when flag == 0, then copies from b ++ * when flag == 1, then copies from a ++ */ ++static void ++cselect (limb_t flag, limb_t *ret, limb_t *a, limb_t *b, size_t n) ++{ ++ /* would be more efficient with non volatile mask, but then gcc ++ * generates code with jumps */ ++ limb_t mask1 = ct_limb_gen_mask (flag); ++ limb_t mask2 = ct_limb_gen_inv_mask (flag); ++ for (size_t i = 0; i < n; i++) ++ { ++ ret[i] = (mask1 & a[i]) | (mask2 & b[i]); ++ } ++} ++ ++static limb_t ++_sub_limb (limb_t *ret, limb_t a, limb_t b, limb_t borrow) ++{ ++ limb_t borrow1, borrow2, t; ++ sub_ddmmss (borrow1, t, 0, a, 0, borrow); ++ sub_ddmmss (borrow2, t, 0, t, 0, b); ++ *ret = t; ++ return -(borrow1 + borrow2); ++} ++ ++/* place the result of a - b into ret, return the borrow bit. ++ * All arrays need to be n limbs long ++ */ ++static limb_t ++sub (limb_t *ret, limb_t *a, limb_t *b, size_t n) ++{ ++ limb_t borrow = 0; ++ for (ssize_t i=n-1; i>-1; i--) ++ { ++ borrow = _sub_limb (&ret[i], a[i], b[i], borrow); ++ } ++ return borrow; ++} ++ ++/* return the number of limbs necessary to allocate for the mod() tmp operand */ ++size_t ++mod_limb_numb (size_t anum, size_t modnum) ++{ ++ return (anum + modnum) * 3; ++} ++ ++/* calculate a % mod, place the result in ret ++ * size of a is defined by anum, size of ret and mod is modnum, ++ * size of tmp is returned by mod_limb_numb() ++ */ ++void ++mod_cs (limb_t *ret, limb_t *a, size_t anum, limb_t *mod, size_t modnum, limb_t *tmp) ++{ ++ limb_t *atmp, *modtmp, *rettmp; ++ limb_t res; ++ ++ memset (tmp, 0, mod_limb_numb(anum, modnum) * LIMB_BYTE_SIZE); ++ ++ atmp = tmp; ++ modtmp = &tmp[anum+modnum]; ++ rettmp = &tmp[(anum+modnum)*2]; ++ ++ for (size_t i=modnum; inlimbs < v->nlimbs) ++ { /* Swap U and V. */ ++ usize = v->nlimbs; ++ usign = v->sign; ++ usecure = mpi_is_secure (v); ++ up = v->d; ++ vsize = u->nlimbs; ++ vsign = u->sign; ++ vsecure = mpi_is_secure (u); ++ vp = u->d; ++ } ++ else ++ { ++ usize = u->nlimbs; ++ usign = u->sign; ++ usecure = mpi_is_secure (u); ++ up = u->d; ++ vsize = v->nlimbs; ++ vsign = v->sign; ++ vsecure = mpi_is_secure (v); ++ vp = v->d; ++ } ++ sign_product = usign ^ vsign; ++ wp = w->d; ++ ++ /* make sure u and v have the same length by extending the limbs to the larger one, now u */ ++ if (usize != vsize) ++ { ++ mpi_limb_t *tmp_vp = mpi_alloc_limb_space (usize, vsecure); ++ clean_vp = 1; ++ MPN_ZERO (tmp_vp, (usize - vsize)); ++ MPN_COPY (tmp_vp + (usize - vsize), vp, vsize); ++ vsize = usize; ++ vp = tmp_vp; ++ } ++ ++ /* w == u */ ++ /* Ensure W has space enough to store the result. */ ++ wsize = usize + vsize; ++ if (!mpi_is_secure (w) && (mpi_is_secure (u) || mpi_is_secure (v))) ++ { ++ /* w is not allocated in secure space but u or v is. To make sure ++ * that no temporary results are stored in w, we temporary use ++ * a newly allocated limb space for w */ ++ wp = mpi_alloc_limb_space( wsize, 1 ); ++ assign_wp = 2; /* mark it as 2 so that we can later copy it back to ++ * normal memory */ ++ } ++ else if (w->alloced < wsize ) ++ { ++ if (wp == up || wp == vp) ++ { ++ wp = mpi_alloc_limb_space (wsize, mpi_is_secure (w)); ++ assign_wp = 1; ++ } ++ else ++ { ++ mpi_resize(w, wsize ); ++ wp = w->d; ++ } ++ } ++ else ++ { /* Make U and V not overlap with W. */ ++ if (wp == up) ++ { ++ /* W and U are identical. Allocate temporary space for U. */ ++ tmp_limb_nlimbs = usize; ++ up = tmp_limb = mpi_alloc_limb_space (usize, usecure); ++ /* Is V identical too? Keep it identical with U. */ ++ if (wp == vp) ++ vp = up; ++ /* Copy to the temporary space. */ ++ MPN_COPY (up, wp, usize); ++ } ++ else if (wp == vp) ++ { ++ /* W and V are identical. Allocate temporary space for V. */ ++ tmp_limb_nlimbs = vsize; ++ vp = tmp_limb = mpi_alloc_limb_space (vsize, vsecure); ++ /* Copy to the temporary space. */ ++ MPN_COPY (vp, wp, vsize); ++ } ++ } ++ ++ if (!vsize) ++ wsize = 0; ++ else ++ { ++ mpi_limb_t *tmp = mpi_alloc_limb_space (wsize * 2, mpi_is_secure (w)); ++ mul_cs (wp, up, vp, vsize, tmp); ++ _gcry_mpi_free_limb_space (tmp, wsize * 2); ++ } ++ ++ if (clean_vp) ++ { ++ _gcry_mpi_free_limb_space (vp, vsize); ++ } ++ if (assign_wp) ++ { ++ if (assign_wp == 2) ++ { ++ /* copy the temp wp from secure memory back to normal memory */ ++ mpi_ptr_t tmp_wp = mpi_alloc_limb_space (wsize, 0); ++ MPN_COPY (tmp_wp, wp, wsize); ++ _gcry_mpi_free_limb_space (wp, 0); ++ wp = tmp_wp; ++ } ++ _gcry_mpi_assign_limb_space (w, wp, wsize); ++ } ++ w->nlimbs = wsize; ++ w->sign = sign_product; ++ if (tmp_limb) ++ _gcry_mpi_free_limb_space (tmp_limb, tmp_limb_nlimbs); ++} ++#endif /* WITH_MARVIN_WORKAROUND */ + + void + _gcry_mpi_mulm (gcry_mpi_t w, gcry_mpi_t u, gcry_mpi_t v, gcry_mpi_t m) +@@ -221,3 +348,45 @@ _gcry_mpi_mulm (gcry_mpi_t w, gcry_mpi_t + if (temp_m) + mpi_free(temp_m); + } ++ ++#ifdef WITH_MARVIN_WORKAROUND ++static void ++_gcry_mpi_mod_sec (gcry_mpi_t ret, gcry_mpi_t a, gcry_mpi_t mod) ++{ ++ size_t asize = a->nlimbs; ++ size_t modsize = mod->nlimbs; ++ size_t tmp_size = mod_limb_numb (asize, modsize); ++ mpi_limb_t *tmp_limb = mpi_alloc_limb_space (tmp_size, mpi_is_secure(a)); ++ mod_cs (ret->d, a->d, asize, mod->d, modsize, tmp_limb); ++ /* cut the length to the mod size */ ++ ret->nlimbs = mod->nlimbs; ++ _gcry_mpi_free_limb_space (tmp_limb, tmp_size); ++} ++ ++/* The constant time code uses different order of the limbs ... */ ++static void ++_gcry_mpi_reverse_sec (gcry_mpi_t w) ++{ ++ for (size_t i = 0; i < w->nlimbs/2; i++) ++ { ++ mpi_limb_t t = w->d[i]; ++ w->d[i] = w->d[w->nlimbs - i - 1]; ++ w->d[w->nlimbs - i - 1] = t; ++ } ++} ++ ++void ++_gcry_mpi_mulm_sec (gcry_mpi_t w, gcry_mpi_t u, gcry_mpi_t v, gcry_mpi_t m) ++{ ++ /* w == u */ ++ _gcry_mpi_reverse_sec (u); ++ _gcry_mpi_reverse_sec (v); ++ _gcry_mpi_reverse_sec (m); ++ _gcry_mpi_mul_sec (w, u, v); ++ _gcry_mpi_mod_sec (w, w, m); ++ ++ /* get them back to the order the rest of the code expects */ ++ _gcry_mpi_reverse_sec (w); /* -- this is the result */ ++ _gcry_mpi_reverse_sec (m); /* -- this might be still used by the calling function */ ++} ++#endif /* WITH_MARVIN_WORKAROUND */ +Index: libgcrypt-1.11.1/src/gcrypt-int.h +=================================================================== +--- libgcrypt-1.11.1.orig/src/gcrypt-int.h ++++ libgcrypt-1.11.1/src/gcrypt-int.h +@@ -470,6 +470,9 @@ void _gcry_mpi_subm (gcry_mpi_t w, gcry_ + void _gcry_mpi_mul (gcry_mpi_t w, gcry_mpi_t u, gcry_mpi_t v); + void _gcry_mpi_mul_ui (gcry_mpi_t w, gcry_mpi_t u, unsigned long v ); + void _gcry_mpi_mulm (gcry_mpi_t w, gcry_mpi_t u, gcry_mpi_t v, gcry_mpi_t m); ++#ifdef WITH_MARVIN_WORKAROUND ++void _gcry_mpi_mulm_sec (gcry_mpi_t w, gcry_mpi_t u, gcry_mpi_t v, gcry_mpi_t m); ++#endif /* WITH_MARVIN_WORKAROUND */ + void _gcry_mpi_mul_2exp (gcry_mpi_t w, gcry_mpi_t u, unsigned long cnt); + void _gcry_mpi_div (gcry_mpi_t q, gcry_mpi_t r, + gcry_mpi_t dividend, gcry_mpi_t divisor, int round); +@@ -566,6 +569,9 @@ int _gcry_mpi_get_flag (gcry_mpi_t a, en + #define mpi_mul_2exp(w,u,v) _gcry_mpi_mul_2exp ((w),(u),(v)) + #define mpi_mul(w,u,v) _gcry_mpi_mul ((w),(u),(v)) + #define mpi_mulm(w,u,v,m) _gcry_mpi_mulm ((w),(u),(v),(m)) ++#ifdef WITH_MARVIN_WORKAROUND ++#define mpi_mulm_sec(w,u,v,m) _gcry_mpi_mulm_sec ((w),(u),(v),(m)) ++#endif /* WITH_MARVIN_WORKAROUND */ + #define mpi_powm(w,b,e,m) _gcry_mpi_powm ( (w), (b), (e), (m) ) + #define mpi_tdiv(q,r,a,m) _gcry_mpi_div ( (q), (r), (a), (m), 0) + #define mpi_fdiv(q,r,a,m) _gcry_mpi_div ( (q), (r), (a), (m), -1) +Index: libgcrypt-1.11.1/src/const-time.c +=================================================================== +--- libgcrypt-1.11.1.orig/src/const-time.c ++++ libgcrypt-1.11.1/src/const-time.c +@@ -77,8 +77,8 @@ _gcry_ct_memmov_cond (void *dst, const v + unsigned long op_enable) + { + /* Note: dual mask with AND/OR used for EM leakage mitigation */ +- unsigned char mask1 = ct_ulong_gen_mask(op_enable); +- unsigned char mask2 = ct_ulong_gen_inv_mask(op_enable); ++ volatile unsigned char mask1 = ct_ulong_gen_mask(op_enable); ++ volatile unsigned char mask2 = ct_ulong_gen_inv_mask(op_enable); + unsigned char *b_dst = dst; + const unsigned char *b_src = src; + size_t i; +@@ -86,3 +86,27 @@ _gcry_ct_memmov_cond (void *dst, const v + for (i = 0; i < len; i++) + b_dst[i] = (b_dst[i] & mask2) | (b_src[i] & mask1); + } ++ ++/* ++ * Copy LEN bytes from memory area SRC to memory area DST. The ++ * bytes are read up to the BUFFER_LEN size to keep the operation ++ * not dependent on the message length (both SRC and DST buffers ++ * need to have this size!). ++ */ ++void ++_gcry_ct_memcpy (void *dst, const void *src, size_t len, size_t buffer_len) ++{ ++ volatile unsigned char mask_a, mask_b; ++ unsigned char *b_dst = dst; ++ const unsigned char *b_src = src; ++ unsigned int writing; ++ size_t i; ++ ++ for (i = 0; i < buffer_len; i++) ++ { ++ writing = ct_lt (i, len); ++ mask_b = ct_uchar_gen_inv_mask (writing); ++ mask_a = ct_uchar_gen_mask (writing); ++ b_dst[i] = (b_src[i] & mask_a) | (b_dst[i] & mask_b); ++ } ++} +Index: libgcrypt-1.11.1/src/sexp.c +=================================================================== +--- libgcrypt-1.11.1.orig/src/sexp.c ++++ libgcrypt-1.11.1/src/sexp.c +@@ -31,6 +31,7 @@ + + #define GCRYPT_NO_MPI_MACROS 1 + #include "g10lib.h" ++#include "const-time.h" + + + /* Notes on the internal memory layout. +@@ -1079,6 +1080,10 @@ unquote_string (const char *string, size + * %d - integer stored as string (no autoswitch to secure allocation) + * %b - memory buffer; this takes _two_ arguments: an integer with the + * length of the buffer and a pointer to the buffer. ++ * %c - memory buffer same as %b, but written in constant time; this ++ * takes _three_ arguments: an integer with the length of the buffer, ++ * a pointer to the buffer and the maximum length of the buffer ++ * to avoid potential side channel leaking the buffer length. + * %S - Copy an gcry_sexp_t here. The S-expression needs to be a + * regular one, starting with a parenthesis. + * (no autoswitch to secure allocation) +@@ -1204,7 +1209,7 @@ do_vsexp_sscan (gcry_sexp_t *retsexp, si + { + switch (*p) + { +- case 'b': case 't': case 'v': case 'n': case 'f': ++ case 'b': case 'c': case 't': case 'v': case 'n': case 'f': + case 'r': case '"': case '\'': case '\\': + quoted_esc = 0; + break; +@@ -1538,14 +1543,27 @@ do_vsexp_sscan (gcry_sexp_t *retsexp, si + memcpy (c.pos, astr, alen); + c.pos += alen; + } +- else if (*p == 'b') ++ else if (*p == 'b' || *p == 'c') + { + /* Insert a memory buffer. */ + const char *astr; +- int alen; ++ int alen, buflen = 0, reallen = 0; + + ARG_NEXT (alen, int); + ARG_NEXT (astr, const char *); ++ if (*p == 'c') ++ { ++ ARG_NEXT (buflen, int); ++ if (buflen < alen) ++ { ++ *erroff = p - buffer; ++ err = GPG_ERR_INV_ARG; ++ goto leave; ++ } ++ /* Do all the calculations with the buflen */ ++ reallen = alen; ++ alen = buflen; ++ } + + if (alen < 0) + { +@@ -1578,9 +1596,18 @@ do_vsexp_sscan (gcry_sexp_t *retsexp, si + } + + *c.pos++ = ST_DATA; +- STORE_LEN (c.pos, alen); +- memcpy (c.pos, astr, alen); +- c.pos += alen; ++ if (*p == 'c') ++ { ++ STORE_LEN (c.pos, reallen); ++ ct_memcpy (c.pos, astr, reallen, buflen); ++ c.pos += reallen; ++ } ++ else ++ { ++ STORE_LEN (c.pos, alen); ++ memcpy (c.pos, astr, alen); ++ c.pos += alen; ++ } + } + else if (*p == 'd') + { +Index: libgcrypt-1.11.1/cipher/pubkey-internal.h +=================================================================== +--- libgcrypt-1.11.1.orig/cipher/pubkey-internal.h ++++ libgcrypt-1.11.1/cipher/pubkey-internal.h +@@ -55,6 +55,14 @@ _gcry_rsa_pkcs1_encode_for_enc (gcry_mpi + gpg_err_code_t + _gcry_rsa_pkcs1_decode_for_enc (unsigned char **r_result, size_t *r_resultlen, + unsigned int nbits, gcry_mpi_t value); ++#ifdef WITH_MARVIN_WORKAROUND ++gpg_err_code_t ++_gcry_rsa_pkcs1_decode_for_enc_implicit_rejection (unsigned char **r_result, ++ size_t *r_resultlen, ++ unsigned int nbits, ++ gcry_mpi_t value, ++ unsigned char *kdk); ++#endif /* WITH_MARVIN_WORKAROUND */ + gpg_err_code_t + _gcry_rsa_pkcs1_encode_raw_for_sig (gcry_mpi_t *r_result, unsigned int nbits, + const unsigned char *value, size_t valuelen); +Index: libgcrypt-1.11.1/cipher/pubkey-util.c +=================================================================== +--- libgcrypt-1.11.1.orig/cipher/pubkey-util.c ++++ libgcrypt-1.11.1/cipher/pubkey-util.c +@@ -193,6 +193,15 @@ _gcry_pk_util_parse_flaglist (gcry_sexp_ + rc = GPG_ERR_INV_FLAG; + break; + ++#ifdef WITH_MARVIN_WORKAROUND ++ case 21: ++ if (!memcmp (s, "no-implicit-rejection", 21)) ++ flags |= PUBKEY_FLAG_NO_IMPLICIT_REJECTION; ++ else if (!igninvflag) ++ rc = GPG_ERR_INV_FLAG; ++ break; ++#endif /* WITH_MARVIN_WORKAROUND */ ++ + default: + if (!igninvflag) + rc = GPG_ERR_INV_FLAG; +Index: libgcrypt-1.11.1/src/cipher.h +=================================================================== +--- libgcrypt-1.11.1.orig/src/cipher.h ++++ libgcrypt-1.11.1/src/cipher.h +@@ -26,24 +26,25 @@ + + #include "../random/random.h" + +-#define PUBKEY_FLAG_NO_BLINDING (1 << 0) +-#define PUBKEY_FLAG_RFC6979 (1 << 1) +-#define PUBKEY_FLAG_FIXEDLEN (1 << 2) +-#define PUBKEY_FLAG_LEGACYRESULT (1 << 3) +-#define PUBKEY_FLAG_RAW_FLAG (1 << 4) +-#define PUBKEY_FLAG_TRANSIENT_KEY (1 << 5) +-#define PUBKEY_FLAG_USE_X931 (1 << 6) +-#define PUBKEY_FLAG_USE_FIPS186 (1 << 7) +-#define PUBKEY_FLAG_USE_FIPS186_2 (1 << 8) +-#define PUBKEY_FLAG_PARAM (1 << 9) +-#define PUBKEY_FLAG_COMP (1 << 10) +-#define PUBKEY_FLAG_NOCOMP (1 << 11) +-#define PUBKEY_FLAG_EDDSA (1 << 12) +-#define PUBKEY_FLAG_GOST (1 << 13) +-#define PUBKEY_FLAG_NO_KEYTEST (1 << 14) +-#define PUBKEY_FLAG_DJB_TWEAK (1 << 15) +-#define PUBKEY_FLAG_SM2 (1 << 16) +-#define PUBKEY_FLAG_PREHASH (1 << 17) ++#define PUBKEY_FLAG_NO_BLINDING (1 << 0) ++#define PUBKEY_FLAG_RFC6979 (1 << 1) ++#define PUBKEY_FLAG_FIXEDLEN (1 << 2) ++#define PUBKEY_FLAG_LEGACYRESULT (1 << 3) ++#define PUBKEY_FLAG_RAW_FLAG (1 << 4) ++#define PUBKEY_FLAG_TRANSIENT_KEY (1 << 5) ++#define PUBKEY_FLAG_USE_X931 (1 << 6) ++#define PUBKEY_FLAG_USE_FIPS186 (1 << 7) ++#define PUBKEY_FLAG_USE_FIPS186_2 (1 << 8) ++#define PUBKEY_FLAG_PARAM (1 << 9) ++#define PUBKEY_FLAG_COMP (1 << 10) ++#define PUBKEY_FLAG_NOCOMP (1 << 11) ++#define PUBKEY_FLAG_EDDSA (1 << 12) ++#define PUBKEY_FLAG_GOST (1 << 13) ++#define PUBKEY_FLAG_NO_KEYTEST (1 << 14) ++#define PUBKEY_FLAG_DJB_TWEAK (1 << 15) ++#define PUBKEY_FLAG_SM2 (1 << 16) ++#define PUBKEY_FLAG_PREHASH (1 << 17) ++#define PUBKEY_FLAG_NO_IMPLICIT_REJECTION (1 << 18) + + + enum pk_operation +Index: libgcrypt-1.11.1/tests/pkcs1v2-v15c.h +=================================================================== +--- libgcrypt-1.11.1.orig/tests/pkcs1v2-v15c.h ++++ libgcrypt-1.11.1/tests/pkcs1v2-v15c.h +@@ -21,6 +21,7 @@ + const char *mesg; + const char *seed; + const char *encr; ++ const char *synt; + } m[20]; + } tbl[] = + { +@@ -3915,5 +3916,308 @@ + "25db1dd892b71bb74a5cf68263d8fd58f1a48e6c2fcb8c0b71a251cfc1a20157" + } + } ++ }, ++ { ++ "A 2048-bit RSA Test vectors for the Bleichenbacher workaround", ++ "c8cc839714098da56caa23640f93dc8997c16372968fc1b0c6df5113c1c94e8b21e48ad2297e65419011b4e6d8f5e73b1b78b257400321d1ef6b602d4ec8ce8d141c94905eb4ad306639a49206534b6e7f2607423e97dffd133c88d721399defbc7e96ccdcbd7f3aae1fe892712bfb4929817d511666440a1facb7a208f5ea165910add8a3f2d497202360ccb632024f0d07169c1918f316f794b143aef54ec87522a4c02978f9689980bffbf649c307e81819bff88409638d48bd94be152b59ff649fa0bd629d0ffa1813c3abf4b56bd3c2ea5465dffa14589292a9d8a24ad26be7ee0510741b6382d43c83d5bfa40a46613d062be445517dbcaf0cb4e1a769", ++ "010001", ++ "1455010e0f2d587663a666a6ff1ccdbbf0edd8100646d02a023922908992c4ad39e5565929726ef6508c3a71158ef0b6ff751d39d07580bb2d2f063210442d0603ff50dbbd7b35fe2c9bb19a47a1af85a4c24901e02ca8b58b7919b20edf32aacfbf51adb4bc4b61b9b7e968caa4d570f70ef18d8063228893e47d439efca793259bcf2cd108a3d8688cdf078e7ac799969f2339d2c1f522b969684629a933baaec2681625eab84f4e56f4447e9d88fb9a199cf71023e0e257b14441b33c84d3bc67ca8031d2612618103a7a0a40844262f75d8890cd616e51f9035488fd6e099de8ff6d65a4ff118254807c9f58d2fbba8ba151dc8c68be349c977a204e04c1", ++ { ++ { ++ "1. a random positive test case", ++ NULL, ++ "", ++ "8bfe264e85d3bdeaa6b8851b8e3b956ee3d226fd3f69063a86880173a273d9f283b2eebdd1ed35f7e02d91c571981b6737d5320bd8396b0f3ad5b019daec1b0aab3cbbc026395f4fd14f13673f2dfc81f9b660ec26ac381e6db3299b4e460b43fab9955df2b3cfaa20e900e19c856238fd371899c2bf2ce8c868b76754e5db3b036533fd603746be13c10d4e3e6022ebc905d20c2a7f32b215a4cd53b3f44ca1c327d2c2b651145821c08396c89071f665349c25e44d2733cd9305985ceef6430c3cf57af5fa224089221218fa34737c79c446d28a94c41c96e4e92ac53fbcf384dea8419ea089f8784445a492c812eb0d409467f75afd7d4d1078886205a066", ++ "6c6f72656d20697073756d20646f6c6f722073697420616d6574" ++ },{ ++ "2. a random negative test case decrypting to empty", ++ NULL, ++ "", ++ "20aaa8adbbc593a924ba1c5c7990b5c2242ae4b99d0fe636a19a4cf754edbcee774e472fe028160ed42634f8864900cb514006da642cae6ae8c7d087caebcfa6dad1551301e130344989a1d462d4164505f6393933450c67bc6d39d8f5160907cabc251b737925a1cf21e5c6aa5781b7769f6a2a583d97cce008c0f8b6add5f0b2bd80bee60237aa39bb20719fe75749f4bc4e42466ef5a861ae3a92395c7d858d430bfe38040f445ea93fa2958b503539800ffa5ce5f8cf51fa8171a91f36cb4f4575e8de6b4d3f096ee140b938fd2f50ee13f0d050222e2a72b0a3069ff3a6738e82c87090caa5aed4fcbe882c49646aa250b98f12f83c8d528113614a29e7", ++ "" ++ },{ ++ "3. invalid decrypting to max length message", ++ NULL, ++ "", ++ "48cceab10f39a4db32f60074feea473cbcdb7accf92e150417f76b44756b190e843e79ec12aa85083a21f5437e7bad0a60482e601198f9d86923239c8786ee728285afd0937f7dde12717f28389843d7375912b07b991f4fdb0190fced8ba665314367e8c5f9d2981d0f5128feeb46cb50fc237e64438a86df198dd0209364ae3a842d77532b66b7ef263b83b1541ed671b120dfd660462e2107a4ee7b964e734a7bd68d90dda61770658a3c242948532da32648687e0318286473f675b412d6468f013f14d760a358dfcad3cda2afeec5e268a37d250c37f722f468a70dfd92d7294c3c1ee1e7f8843b7d16f9f37ef35748c3ae93aa155cdcdfeb4e78567303", ++ "22d850137b9eebe092b24f602dc5bb7918c16bd89ddbf20467b119d205f9c2e4bd7d2592cf1e532106e0f33557565923c73a02d4f09c0c22bea89148183e60317f7028b3aa1f261f91c979393101d7e15f4067e63979b32751658ef769610fe97cf9cef3278b3117d384051c3b1d82c251c2305418c8f6840530e631aad63e70e20e025bcd8efb54c92ec6d3b106a2f8e64eeff7d38495b0fc50c97138af4b1c0a67a1c4e27b077b8439332edfa8608dfeae653cd6a628ac550395f7e74390e42c11682234870925eeaa1fa71b76cf1f2ee3bda69f6717033ff8b7c95c9799e7a3bea5e7e4a1c359772fb6b1c6e6c516661dfe30c3" ++ },{ ++ "4. invalid decrypting to message with length specified by second to last value from PRF", ++ NULL, ++ "", ++ "1439e08c3f84c1a7fec74ce07614b20e01f6fa4e8c2a6cffdc3520d8889e5d9a950c6425798f85d4be38d300ea5695f13ecd4cb389d1ff5b82484b494d6280ab7fa78e645933981cb934cce8bfcd114cc0e6811eefa47aae20af638a1cd163d2d3366186d0a07df0c81f6c9f3171cf3561472e98a6006bf75ddb457bed036dcce199369de7d94ef2c68e8467ee0604eea2b3009479162a7891ba5c40cab17f49e1c438cb6eaea4f76ce23cce0e483ff0e96fa790ea15be67671814342d0a23f4a20262b6182e72f3a67cd289711503c85516a9ed225422f98b116f1ab080a80abd6f0216df88d8cfd67c139243be8dd78502a7aaf6bc99d7da71bcdf627e7354", ++ "0f9b" ++ },{ ++ "5. invalid decrypting to message with length specified by third to last value from PRF", ++ NULL, ++ "", ++ "1690ebcceece2ce024f382e467cf8510e74514120937978576caf684d4a02ad569e8d76cbe365a060e00779de2f0865ccf0d923de3b4783a4e2c74f422e2f326086c390b658ba47f31ab013aa80f468c71256e5fa5679b24e83cd82c3d1e05e398208155de2212993cd2b8bab6987cf4cc1293f19909219439d74127545e9ed8a706961b8ee2119f6bfacafbef91b75a789ba65b8b833bc6149cf49b5c4d2c6359f62808659ba6541e1cd24bf7f7410486b5103f6c0ea29334ea6f4975b17387474fe920710ea61568d7b7c0a7916acf21665ad5a31c4eabcde44f8fb6120d8457afa1f3c85d517cda364af620113ae5a3c52a048821731922737307f77a1081", ++ "4f02" ++ },{ ++ "6. positive test with 11 byte long value", ++ NULL, ++ "", ++ "6213634593332c485cef783ea2846e3d6e8b0e005cd8293eaebbaa5079712fd681579bdfbbda138ae4d9d952917a03c92398ec0cb2bb0c6b5a8d55061fed0d0d8d72473563152648cfe640b335dc95331c21cb133a91790fa93ae44497c128708970d2beeb77e8721b061b1c44034143734a77be8220877415a6dba073c3871605380542a9f25252a4babe8331cdd53cf828423f3cc70b560624d0581fb126b2ed4f4ed358f0eb8065cf176399ac1a846a31055f9ae8c9c24a1ba050bc20842125bc1753158f8065f3adb9cc16bfdf83816bdf38b624f12022c5a6fbfe29bc91542be8c0208a770bcd677dc597f5557dc2ce28a11bf3e3857f158717a33f6592", ++ "6c6f72656d20697073756d" ++ },{ ++ "7. positive test with 11 byte long value and zero padded ciphertext", ++ NULL, ++ "", ++ "00a2e8f114ea8d05d12dc843e3cc3b2edc8229ff2a028bda29ba9d55e3cd02911902fef1f42a075bf05e8016e8567213d6f260fa49e360779dd81aeea3e04c2cb567e0d72b98bf754014561b7511e083d20e0bfb9cd23f8a0d3c88900c49d2fcd5843ff0765607b2026f28202a87aa94678aed22a0c20724541394cd8f44e373eba1d2bae98f516c1e2ba3d86852d064f856b1daf24795e767a2b90396e50743e3150664afab131fe40ea405dcf572dd1079af1d3f0392ccadcca0a12740dbb213b925ca2a06b1bc1383e83a658c82ba2e7427342379084d5f66b544579f07664cb26edd4f10fd913fdbc0de05ef887d4d1ec1ac95652397ea7fd4e4759fda8b", ++ "6c6f72656d20697073756d" ++ },{ ++ "8. positive test with 11 byte long value and zero truncated ciphertext", ++ NULL, ++ "", ++ "a2e8f114ea8d05d12dc843e3cc3b2edc8229ff2a028bda29ba9d55e3cd02911902fef1f42a075bf05e8016e8567213d6f260fa49e360779dd81aeea3e04c2cb567e0d72b98bf754014561b7511e083d20e0bfb9cd23f8a0d3c88900c49d2fcd5843ff0765607b2026f28202a87aa94678aed22a0c20724541394cd8f44e373eba1d2bae98f516c1e2ba3d86852d064f856b1daf24795e767a2b90396e50743e3150664afab131fe40ea405dcf572dd1079af1d3f0392ccadcca0a12740dbb213b925ca2a06b1bc1383e83a658c82ba2e7427342379084d5f66b544579f07664cb26edd4f10fd913fdbc0de05ef887d4d1ec1ac95652397ea7fd4e4759fda8b", ++ "6c6f72656d20697073756d" ++ },{ ++ "9. positive test with 11 byte long value and double zero padded ciphertext", ++ NULL, ++ "", ++ "00001f71879b426127f7dead621f7380a7098cf7d22173aa27991b143c46d53383c209bd0c9c00d84078037e715f6b98c65005a77120070522ede51d472c87ef94b94ead4c5428ee108a345561658301911ec5a8f7dd43ed4a3957fd29fb02a3529bf63f8040d3953490939bd8f78b2a3404b6fb5ff70a4bfdaac5c541d6bcce49c9778cc390be24cbef1d1eca7e870457241d3ff72ca44f9f56bdf31a890fa5eb3a9107b603ccc9d06a5dd911a664c82b6abd4fe036f8db8d5a070c2d86386ae18d97adc1847640c211d91ff5c3387574a26f8ef27ca7f48d2dd1f0c7f14b81cc9d33ee6853031d3ecf10a914ffd90947909c8011fd30249219348ebff76bfc", ++ "6c6f72656d20697073756d" ++ },{ ++ "10. a random negative test that generates an 11 byte long message", ++ NULL, ++ "", ++ "5f02f4b1f46935c742ebe62b6f05aa0a3286aab91a49b34780adde6410ab46f7386e05748331864ac98e1da63686e4babe3a19ed40a7f5ceefb89179596aab07ab1015e03b8f825084dab028b6731288f2e511a4b314b6ea3997d2e8fe2825cef8897cbbdfb6c939d441d6e04948414bb69e682927ef8576c9a7090d4aad0e74c520d6d5ce63a154720f00b76de8cc550b1aa14f016d63a7b6d6eaa1f7dbe9e50200d3159b3d099c900116bf4eba3b94204f18b1317b07529751abf64a26b0a0bf1c8ce757333b3d673211b67cc0653f2fe2620d57c8b6ee574a0323a167eab1106d9bc7fd90d415be5f1e9891a0e6c709f4fc0404e8226f8477b4e939b36eb2", ++ "af9ac70191c92413cb9f2d" ++ },{ ++ "11. an otherwise correct plaintext, but with wrong first byte (0x01 instead of 0x00), generates a random 11 byte long plaintext", ++ NULL, ++ "", ++ "9b2ec9c0c917c98f1ad3d0119aec6be51ae3106e9af1914d48600ab6a2c0c0c8ae02a2dc3039906ff3aac904af32ec798fd65f3ad1afa2e69400e7c1de81f5728f3b3291f38263bc7a90a0563e43ce7a0d4ee9c0d8a716621ca5d3d081188769ce1b131af7d35b13dea99153579c86db31fe07d5a2c14d621b77854e48a8df41b5798563af489a291e417b6a334c63222627376118c02c53b6e86310f728734ffc86ef9d7c8bf56c0c841b24b82b59f51aee4526ba1c4268506d301e4ebc498c6aebb6fd5258c876bf900bac8ca4d309dd522f6a6343599a8bc3760f422c10c72d0ad527ce4af1874124ace3d99bb74db8d69d2528db22c3a37644640f95c05f", ++ "a1f8c9255c35cfba403ccc" ++ },{ ++ "12. an otherwise correct plaintext, but with wrong second byte (0x01 instead of 0x02), generates a random 11 byte long plaintext", ++ NULL, ++ "", ++ "782c2b59a21a511243820acedd567c136f6d3090c115232a82a5efb0b178285f55b5ec2d2bac96bf00d6592ea7cdc3341610c8fb07e527e5e2d20cfaf2c7f23e375431f45e998929a02f25fd95354c33838090bca838502259e92d86d568bc2cdb132fab2a399593ca60a015dc2bb1afcd64fef8a3834e17e5358d822980dc446e845b3ab4702b1ee41fe5db716d92348d5091c15d35a110555a35deb4650a5a1d2c98025d42d4544f8b32aa6a5e02dc02deaed9a7313b73b49b0d4772a3768b0ea0db5846ace6569cae677bf67fb0acf3c255dc01ec8400c963b6e49b1067728b4e563d7e1e1515664347b92ee64db7efb5452357a02fff7fcb7437abc2e579", ++ "e6d700309ca0ed62452254" ++ },{ ++ "13. an invalid ciphertext, with a zero byte in first byte of ciphertext, decrypts to a random 11 byte long synthethic plaintext", ++ NULL, ++ "", ++ "0096136621faf36d5290b16bd26295de27f895d1faa51c800dafce73d001d60796cd4e2ac3fa2162131d859cd9da5a0c8a42281d9a63e5f353971b72e36b5722e4ac444d77f892a5443deb3dca49fa732fe855727196e23c26eeac55eeced8267a209ebc0f92f4656d64a6c13f7f7ce544ebeb0f668fe3a6c0f189e4bcd5ea12b73cf63e0c8350ee130dd62f01e5c97a1e13f52fde96a9a1bc9936ce734fdd61f27b18216f1d6de87f49cf4f2ea821fb8efd1f92cdad529baf7e31aff9bff4074f2cad2b4243dd15a711adcf7de900851fbd6bcb53dac399d7c880531d06f25f7002e1aaf1722765865d2c2b902c7736acd27bc6cbd3e38b560e2eecf7d4b576", ++ "ba27b1842e7c21c0e7ef6a" ++ },{ ++ "14. an invalid ciphertext, with a zero byte removed from first byte of ciphertext, decrypts to a random 11 byte long synthethic plaintext", ++ NULL, ++ "", ++ "96136621faf36d5290b16bd26295de27f895d1faa51c800dafce73d001d60796cd4e2ac3fa2162131d859cd9da5a0c8a42281d9a63e5f353971b72e36b5722e4ac444d77f892a5443deb3dca49fa732fe855727196e23c26eeac55eeced8267a209ebc0f92f4656d64a6c13f7f7ce544ebeb0f668fe3a6c0f189e4bcd5ea12b73cf63e0c8350ee130dd62f01e5c97a1e13f52fde96a9a1bc9936ce734fdd61f27b18216f1d6de87f49cf4f2ea821fb8efd1f92cdad529baf7e31aff9bff4074f2cad2b4243dd15a711adcf7de900851fbd6bcb53dac399d7c880531d06f25f7002e1aaf1722765865d2c2b902c7736acd27bc6cbd3e38b560e2eecf7d4b576", ++ "ba27b1842e7c21c0e7ef6a" ++ },{ ++ "15. an invalid ciphertext, with two zero bytes in first bytes of ciphertext, decrypts to a random 11 byte long synthethic plaintext", ++ NULL, ++ "", ++ "0000587cccc6b264bdfe0dc2149a988047fa921801f3502ea64624c510c6033d2f427e3f136c26e88ea9f6519e86a542cec96aad1e5e9013c3cc203b6de15a69183050813af5c9ad79703136d4b92f50ce171eefc6aa7988ecf02f319ffc5eafd6ee7a137f8fce64b255bb1b8dd19cfe767d64fdb468b9b2e9e7a0c24dae03239c8c714d3f40b7ee9c4e59ac15b17e4d328f1100756bce17133e8e7493b54e5006c3cbcdacd134130c5132a1edebdbd01a0c41452d16ed7a0788003c34730d0808e7e14c797a21f2b45a8aa1644357fd5e988f99b017d9df37563a354c788dc0e2f9466045622fa3f3e17db63414d27761f57392623a2bef6467501c63e8d645", ++ "d5cf555b1d6151029a429a" ++ },{ ++ "16. an invalid ciphertext, with two zero bytes removed from first bytes of ciphertext, decrypts to a random 11 byte long synthethic plaintext", ++ NULL, ++ "", ++ "587cccc6b264bdfe0dc2149a988047fa921801f3502ea64624c510c6033d2f427e3f136c26e88ea9f6519e86a542cec96aad1e5e9013c3cc203b6de15a69183050813af5c9ad79703136d4b92f50ce171eefc6aa7988ecf02f319ffc5eafd6ee7a137f8fce64b255bb1b8dd19cfe767d64fdb468b9b2e9e7a0c24dae03239c8c714d3f40b7ee9c4e59ac15b17e4d328f1100756bce17133e8e7493b54e5006c3cbcdacd134130c5132a1edebdbd01a0c41452d16ed7a0788003c34730d0808e7e14c797a21f2b45a8aa1644357fd5e988f99b017d9df37563a354c788dc0e2f9466045622fa3f3e17db63414d27761f57392623a2bef6467501c63e8d645", ++ "d5cf555b1d6151029a429a" ++ },{ ++ "17. and invalid ciphertext, otherwise valid but starting with 000002, decrypts to random 11 byte long synthethic plaintext", ++ NULL, ++ "", ++ "1786550ce8d8433052e01ecba8b76d3019f1355b212ac9d0f5191b023325a7e7714b7802f8e9a17c4cb3cd3a84041891471b10ca1fcfb5d041d34c82e6d0011cf4dc76b90e9c2e0743590579d55bcd7857057152c4a8040361343d1d22ba677d62b011407c652e234b1d663af25e2386251d7409190f19fc8ec3f9374fdf1254633874ce2ec2bff40ad0cb473f9761ec7b68da45a4bd5e33f5d7dac9b9a20821df9406b653f78a95a6c0ea0a4d57f867e4db22c17bf9a12c150f809a7b72b6db86c22a8732241ebf3c6a4f2cf82671d917aba8bc61052b40ccddd743a94ea9b538175106201971cca9d136d25081739aaf6cd18b2aecf9ad320ea3f89502f955", ++ "3d4a054d9358209e9cbbb9" ++ },{ ++ "18. negative test with otherwise valid padding but a zero byte in first byte of padding", ++ NULL, ++ "", ++ "179598823812d2c58a7eb50521150a48bcca8b4eb53414018b6bca19f4801456c5e36a940037ac516b0d6412ba44ec6b4f268a55ef1c5ffbf18a2f4e3522bb7b6ed89774b79bffa22f7d3102165565642de0d43a955e96a1f2e80e5430671d7266eb4f905dc8ff5e106dc5588e5b0289e49a4913940e392a97062616d2bda38155471b7d360cfb94681c702f60ed2d4de614ea72bf1c53160e63179f6c5b897b59492bee219108309f0b7b8cb2b136c346a5e98b8b4b8415fb1d713bae067911e3057f1c335b4b7e39101eafd5d28f0189037e4334f4fdb9038427b1d119a6702aa8233319cc97d496cc289ae8c956ddc84042659a2d43d6aa22f12b81ab884e", ++ "1f037dd717b07d3e7f7359" ++ },{ ++ "19. negative test with otherwise valid padding but a zero byte at the eigth byte of padding", ++ NULL, ++ "", ++ "a7a340675a82c30e22219a55bc07cdf36d47d01834c1834f917f18b517419ce9de2a96460e745024436470ed85e94297b283537d52189c406a3f533cb405cc6a9dba46b482ce98b6e3dd52d8fce2237425617e38c11fbc46b61897ef200d01e4f25f5f6c4c5b38cd0de38ba11908b86595a8036a08a42a3d05b79600a97ac18ba368a08d6cf6ccb624f6e8002afc75599fba4de3d4f3ba7d208391ebe8d21f8282b18e2c10869eb2702e68f9176b42b0ddc9d763f0c86ba0ff92c957aaeab76d9ab8da52ea297ec11d92d770146faa1b300e0f91ef969b53e7d2907ffc984e9a9c9d11fb7d6cba91972059b46506b035efec6575c46d7114a6b935864858445f", ++ "63cb0bf65fc8255dd29e17" ++ },{ ++ "20. negative test with an otherwise valid plaintext but with missing separator byte", ++ NULL, ++ "", ++ "3d1b97e7aa34eaf1f4fc171ceb11dcfffd9a46a5b6961205b10b302818c1fcc9f4ec78bf18ea0cee7e9fa5b16fb4c611463b368b3312ac11cf9c06b7cf72b54e284848a508d3f02328c62c2999d0fb60929f81783c7a256891bc2ff4d91df2af96a24fc5701a1823af939ce6dbdc510608e3d41eec172ad2d51b9fc61b4217c923cadcf5bac321355ef8be5e5f090cdc2bd0c697d9058247db3ad613fdce87d2955a6d1c948a5160f93da21f731d74137f5d1f53a1923adb513d2e6e1589d44cc079f4c6ddd471d38ac82d20d8b1d21f8d65f3b6907086809f4123e08d86fb38729585de026a485d8f0e703fd4772f6668febf67df947b82195fa3867e3a3065", ++ "6f09a0b62699337c497b0b" ++ } ++ } ++ }, ++ { ++ "A 2049-bit RSA Test vectors for the Bleichenbacher workaround", ++ "0155f889556a1775f1c7a7786a50b18bc28c9e986ede5667cab39b84124e90eba75c1db083ac3e443bba94dc23560f75e3a81693a2a43bdc7426d8c4eafe68c85de0fe757f6e49bb9ed447e602430800dbb04ceb22e7fa57a18d338fb66026cdb467e70cc040e7d367ef403c7bf1e3df624650094631f21eafd2fb5bc915ff04379acd1112f732c0b46607c178d38a20f52eda509f2f9c0405d51069e80ccf941554d0470467505c3cf541ea0897dfc9f400cecb298ffc753372d9f6933af174cc40ed96d467031733b97f8cddd3f92bc3a03ea8576c417f24007b5e4f7501105b544de9fadcdffadf98dfb4bb05b8199f3f85acfd91f7a9a094b9a383f5049097", ++ "010001", ++ "0119c2b3f50a7ad6152679d7ff510958ac2d8ca6f0028592f332d55a16736178a8e67f17e705ce300e3e87547251006013f974d0a3db49ef344ca5a26a34c0450704d0e422e0ce23a69425c15fefb6f26e106eeff64cc8b9d7442e4da4e8c85008eaeb365859a2294fa3937bc26be56332e7d81e2c160ef635cc528aa7be55e633a723dbc1e16ba29e52b29aef2f9e5654fdc0666bb0fc254acbe80e63874f0f5f020782e3c9dcfc2520d0c9c4a7b634e4503fbb493e1aafeeb3f88bd7a13398725dae6fe399e775cd5d4cf09fc838347c4c98dab1a4883cce620513615afaa10a63368e6d7b79df4166ab162739ef515a4402ee1e0601c5a55bc71df0e30edf81", ++ { ++ { ++ "1. malformed that generates length specified by 3rd last value from PRF", ++ NULL, ++ "", ++ "00b26f6404b82649629f2704494282443776929122e279a9cf30b0c6fe8122a0a9042870d97cc8ef65490fe58f031eb2442352191f5fbc311026b5147d32df914599f38b825ebb824af0d63f2d541a245c5775d1c4b78630e4996cc5fe413d38455a776cf4edcc0aa7fccb31c584d60502ed2b77398f536e137ff7ba6430e9258e21c2db5b82f5380f566876110ac4c759178900fbad7ab70ea07b1daf7a1639cbb4196543a6cbe8271f35dddb8120304f6eef83059e1c5c5678710f904a6d760c4d1d8ad076be17904b9e69910040b47914a0176fb7eea0c06444a6c4b86d674d19a556a1de5490373cb01ce31bbd15a5633362d3d2cd7d4af1b4c5121288b894", ++ "42" ++ },{ ++ "2. simple positive test case", ++ NULL, ++ "", ++ "013300edbf0bb3571e59889f7ed76970bf6d57e1c89bbb6d1c3991d9df8e65ed54b556d928da7d768facb395bbcc81e9f8573b45cf8195dbd85d83a59281cddf4163aec11b53b4140053e3bd109f787a7c3cec31d535af1f50e0598d85d96d91ea01913d07097d25af99c67464ebf2bb396fb28a9233e56f31f7e105d71a23e9ef3b736d1e80e713d1691713df97334779552fc94b40dd733c7251bc522b673d3ec9354af3dd4ad44fa71c0662213a57ada1d75149697d0eb55c053aaed5ffd0b815832f454179519d3736fb4faf808416071db0d0f801aca8548311ee708c131f4be658b15f6b54256872c2903ac708bd43b017b073b5707bc84c2cd9da70e967", ++ "6c6f72656d20697073756d" ++ },{ ++ "3. positive test case with null padded ciphertext", ++ NULL, ++ "", ++ "0002aadf846a329fadc6760980303dbd87bfadfa78c2015ce4d6c5782fd9d3f1078bd3c0a2c5bfbdd1c024552e5054d98b5bcdc94e476dd280e64d650089326542ce7c61d4f1ab40004c2e6a88a883613568556a10f3f9edeab67ae8dddc1e6b0831c2793d2715de943f7ce34c5c05d1b09f14431fde566d17e76c9feee90d86a2c158616ec81dda0c642f58c0ba8fa4495843124a7235d46fb4069715a51bf710fd024259131ba94da73597ace494856c94e7a3ec261545793b0990279b15fa91c7fd13dbfb1df2f221dab9fa9f7c1d21e48aa49f6aaecbabf5ee76dc6c2af2317ffb4e303115386a97f8729afc3d0c89419669235f1a3a69570e0836c79fc162", ++ "6c6f72656d20697073756d" ++ },{ ++ "4. positive test case with null truncated ciphertext", ++ NULL, ++ "", ++ "02aadf846a329fadc6760980303dbd87bfadfa78c2015ce4d6c5782fd9d3f1078bd3c0a2c5bfbdd1c024552e5054d98b5bcdc94e476dd280e64d650089326542ce7c61d4f1ab40004c2e6a88a883613568556a10f3f9edeab67ae8dddc1e6b0831c2793d2715de943f7ce34c5c05d1b09f14431fde566d17e76c9feee90d86a2c158616ec81dda0c642f58c0ba8fa4495843124a7235d46fb4069715a51bf710fd024259131ba94da73597ace494856c94e7a3ec261545793b0990279b15fa91c7fd13dbfb1df2f221dab9fa9f7c1d21e48aa49f6aaecbabf5ee76dc6c2af2317ffb4e303115386a97f8729afc3d0c89419669235f1a3a69570e0836c79fc162", ++ "6c6f72656d20697073756d" ++ },{ ++ "5. positive test case with double null padded ciphertext", ++ NULL, ++ "", ++ "0000f36da3b72d8ff6ded74e7efd08c01908f3f5f0de7b55eab92b5f875190809c39d4162e1e6649618f854fd84aeab03970d16bb814e999852c06de38d82b95c0f32e2a7b5714021fe303389be9c0eac24c90a6b7210f929d390fabf903d44e04110bb7a7fd6c383c275804721efa6d7c93aa64c0bb2b18d97c5220a846c66a4895ae52adddbe2a9996825e013585adcec4b32ba61d782737bd343e5fabd68e8a95b8b1340318559860792dd70dffbe05a1052b54cbfb48cfa7bb3c19cea52076bddac5c25ee276f153a610f6d06ed696d192d8ae4507ffae4e5bdda10a625d6b67f32f7cffcd48dee2431fe66f6105f9d17e611cdcc674868e81692a360f4052", ++ "6c6f72656d20697073756d" ++ },{ ++ "6. positive test case with double null truncated ciphertext", ++ NULL, ++ "", ++ "f36da3b72d8ff6ded74e7efd08c01908f3f5f0de7b55eab92b5f875190809c39d4162e1e6649618f854fd84aeab03970d16bb814e999852c06de38d82b95c0f32e2a7b5714021fe303389be9c0eac24c90a6b7210f929d390fabf903d44e04110bb7a7fd6c383c275804721efa6d7c93aa64c0bb2b18d97c5220a846c66a4895ae52adddbe2a9996825e013585adcec4b32ba61d782737bd343e5fabd68e8a95b8b1340318559860792dd70dffbe05a1052b54cbfb48cfa7bb3c19cea52076bddac5c25ee276f153a610f6d06ed696d192d8ae4507ffae4e5bdda10a625d6b67f32f7cffcd48dee2431fe66f6105f9d17e611cdcc674868e81692a360f4052", ++ "6c6f72656d20697073756d" ++ },{ ++ "7. a random negative test case that generates an 11 byte long message", ++ NULL, ++ "", ++ "00f910200830fc8fff478e99e145f1474b312e2512d0f90b8cef77f8001d09861688c156d1cbaf8a8957f7ebf35f724466952d0524cad48aad4fba1e45ce8ea27e8f3ba44131b7831b62d60c0762661f4c1d1a88cd06263a259abf1ba9e6b0b172069afb86a7e88387726f8ab3adb30bfd6b3f6be6d85d5dfd044e7ef052395474a9cbb1c3667a92780b43a22693015af6c513041bdaf87d43b24ddd244e791eeaea1066e1f4917117b3a468e22e0f7358852bb981248de4d720add2d15dccba6280355935b67c96f9dcb6c419cc38ab9f6fba2d649ef2066e0c34c9f788ae49babd9025fa85b21113e56ce4f43aa134c512b030dd7ac7ce82e76f0be9ce09ebca", ++ "1189b6f5498fd6df532b00" ++ },{ ++ "8. otherwise correct plaintext, but with wrong first byte (0x01 instead of 0x00)", ++ NULL, ++ "", ++ "002c9ddc36ba4cf0038692b2d3a1c61a4bb3786a97ce2e46a3ba74d03158aeef456ce0f4db04dda3fe062268a1711250a18c69778a6280d88e133a16254e1f0e30ce8dac9b57d2e39a2f7d7be3ee4e08aec2fdbe8dadad7fdbf442a29a8fb40857407bf6be35596b8eefb5c2b3f58b894452c2dc54a6123a1a38d642e23751746597e08d71ac92704adc17803b19e131b4d1927881f43b0200e6f95658f559f912c889b4cd51862784364896cd6e8618f485a992f82997ad6a0917e32ae5872eaf850092b2d6c782ad35f487b79682333c1750c685d7d32ab3e1538f31dcaa5e7d5d2825875242c83947308dcf63ba4bfff20334c9c140c837dbdbae7a8dee72ff", ++ "f6d0f5b78082fe61c04674" ++ },{ ++ "9. otherwise correct plaintext, but with wrong second byte (0x01 instead of 0x02)", ++ NULL, ++ "", ++ "00c5d77826c1ab7a34d6390f9d342d5dbe848942e2618287952ba0350d7de6726112e9cebc391a0fae1839e2bf168229e3e0d71d4161801509f1f28f6e1487ca52df05c466b6b0a6fbbe57a3268a970610ec0beac39ec0fa67babce1ef2a86bf77466dc127d7d0d2962c20e66593126f276863cd38dc6351428f884c1384f67cad0a0ffdbc2af16711fb68dc559b96b37b4f04cd133ffc7d79c43c42ca4948fa895b9daeb853150c8a5169849b730cc77d68b0217d6c0e3dbf38d751a1998186633418367e7576530566c23d6d4e0da9b038d0bb5169ce40133ea076472d055001f0135645940fd08ea44269af2604c8b1ba225053d6db9ab43577689401bdc0f3", ++ "1ab287fcef3ff17067914d" ++ },{ ++ NULL, ++ NULL, ++ NULL, ++ NULL, ++ NULL, ++ } ++ } ++ }, ++ { ++ "RSA decrypt with 3072 bit keys", ++ "afd71caad5e9f5b8c6c367070a47f19d7e66aede18a5b2741fb3c4d33434560692a2d909ef6888ec602ff6b93af258ee74303c301afcd4edbec43311ddc8ddbf00ddbbe386d33b8d0e22b1b44936dc489871b85237b34ce747ad8fdb0c4e4d1daa7aadf07385c5c8732ccb7d5a49e2e50c883c7d7ac10ed6a74d9ac90df9129905a17d4a087210fc78b6d04b1eb969482c11a6eeb79c50e5b16f3f254f7571528b2f1716ab816d6eca0727bdea98059329730eb8c33ce71d61dd4ac393b6256e07ac1d124f0200d1c3e05a4c1bc7f1ed2fc83e57199cfe5908b10087e27fbd97d2c24214619c7147c8fbefca39bc256762a6823531f7e234d68eae7a0d9faf10dd15e9523780c7d5ae58094ad525a9063b4c33f95e1006da2eb12d3743689495c1f2023e407353c5eb3e4ca1c48cff81a10900d14820eb801af4f1a596c4b9ce9a531fcf8a54d9ffd724258b6eec20108df6fdfd76d4ae03ba7ea598dcb0e4a280849587286f4d7f256ce85e5eb5679b1dacc1f9095649b72e5fa072aeb00379", ++ "010001", ++ "2517eacb3afef4bffae60398df9957a5d2a154a83368d8e15842b2f59ee09f79197bd2ef1e9addaf8786f6b4127447405e3042b21f2f50b7aa73771680c3bbcb6c225a5d5ff6b56c471c1882a0a33b0af165a3ed6c249dc7783e6bc758ac37e6572d33fe325078ed952650f2eb9604902ef99a511a1119d13c4fc9a43a175dcdfbfb1a1400fe17093b69cd3cdb895f65432ea2195f90511c7336b58a685dacff2daf4c5e92e565b1665ae60e512baa9965b808d5ff119ceb7cd692cbf920067afacd809f66be706da26810ac790db156c948e6fe581bc9849157f4da493f3a64b0c6e119e031b107f8436ce29160b458b8f9f1095fdeb19263384ff5387557bc4f10b4034de841703bad2c1e769c23853eb630a36d1061dd46e2a6bbaf743a97f0b32c36f50c1a3722def3a394d91c2e078bf09d795ecde5e56b8202f974026f75fc56e9a0dd6a88f2e7cb78ef1298cc6c65207ca45bd37188807b4fcdb1e60dd8e5b85648fb7efa8b6fdd448f39741a8d9809fe163af3de45bac24a5a841c81", ++ { ++ { ++ "1. a random invalid ciphertext that generates an empty synthethic one", ++ NULL, ++ "", ++ "5e956cd9652f4a2ece902931013e09662b6a9257ad1e987fb75f73a0606df2a4b04789770820c2e02322c4e826f767bd895734a01e20609c3be4517a7a2a589ea1cdc137beb73eb38dac781b52e863de9620f79f9b90fd5b953651fcbfef4a9f1cc07421d511a87dd6942caab6a5a0f4df473e62defb529a7de1509ab99c596e1dff1320402298d8be73a896cc86c38ae3f2f576e9ea70cc28ad575cb0f854f0be43186baa9c18e29c47c6ca77135db79c811231b7c1730955887d321fdc06568382b86643cf089b10e35ab23e827d2e5aa7b4e99ff2e914f302351819eb4d1693243b35f8bf1d42d08f8ec4acafa35f747a4a975a28643ec630d8e4fa5be59d81995660a14bb64c1fea5146d6b11f92da6a3956dd5cb5e0d747cf2ea23f81617769185336263d46ef4c144b754de62a6337342d6c85a95f19f015724546ee3fc4823eca603dbc1dc01c2d5ed50bd72d8e96df2dc048edde0081284068283fc5e73a6139851abf2f29977d0b3d160c883a42a37efba1be05c1a0b1741d7ddf59", ++ "" ++ },{ ++ "2. a random invalid that has PRF output with a length one byte too long", ++ NULL, ++ "", ++ "7db0390d75fcf9d4c59cf27b264190d856da9abd11e92334d0e5f71005cfed865a711dfa28b791188374b61916dbc11339bf14b06f5f3f68c206c5607380e13da3129bfb744157e1527dd6fdf6651248b028a496ae1b97702d44706043cdaa7a59c0f41367303f21f268968bf3bd2904db3ae5239b55f8b438d93d7db9d1666c071c0857e2ec37757463769c54e51f052b2a71b04c2869e9e7049a1037b8429206c99726f07289bac18363e7eb2a5b417f47c37a55090cda676517b3549c873f2fe95da9681752ec9864b069089a2ed2f340c8b04ee00079055a817a3355b46ac7dc00d17f4504ccfbcfcadb0c04cb6b22069e179385ae1eafabad5521bac2b8a8ee1dfff59a22eb3fdacfc87175d10d7894cfd869d056057dd9944b869c1784fcc27f731bc46171d39570fbffbadf082d33f6352ecf44aca8d9478e53f5a5b7c852b401e8f5f74da49da91e65bdc97765a9523b7a0885a6f8afe5759d58009fbfa837472a968e6ae92026a5e0202a395483095302d6c3985b5f5831c521a271", ++ "56a3bea054e01338be9b7d7957539c" ++ },{ ++ "3. a random invalid that generates a synthethic of maximum size", ++ NULL, ++ "", ++ "1715065322522dff85049800f6a29ab5f98c465020467414b2a44127fe9446da47fa18047900f99afe67c2df6f50160bb8e90bff296610fde632b3859d4d0d2e644f23835028c46cca01b84b88231d7e03154edec6627bcba23de76740d839851fa12d74c8f92e540c73fe837b91b7d699b311997d5f0f7864c486d499c3a79c111faaacbe4799597a25066c6200215c3d158f3817c1aa57f18bdaad0be1658da9da93f5cc6c3c4dd72788af57adbb6a0c26f42d32d95b8a4f95e8c6feb2f8a5d53b19a50a0b7cbc25e055ad03e5ace8f3f7db13e57759f67b65d143f08cca15992c6b2aae643390483de111c2988d4e76b42596266005103c8de6044fb7398eb3c28a864fa672de5fd8774510ff45e05969a11a4c7d3f343e331190d2dcf24fb9154ba904dc94af98afc5774a9617d0418fe6d13f8245c7d7626c176138dd698a23547c25f27c2b98ea4d8a45c7842b81888e4cc14e5b72e9cf91f56956c93dbf2e5f44a8282a7813157fc481ff1371a0f66b31797e81ebdb09a673d4db96d6", ++ "7b036fcd6243900e4236c894e2462c17738acc87e01a76f4d95cb9a328d9acde81650283b8e8f60a217e3bdee835c7b222ad4c85d0acdb9a309bd2a754609a65dec50f3aa04c6d5891034566b9563d42668ede1f8992b17753a2132e28970584e255efc8b45a41c5dbd7567f014acec5fe6fdb6d484790360a913ebb9defcd74ff377f2a8ba46d2ed85f733c9a3da08eb57ecedfafda806778f03c66b2c5d2874cec1c291b2d49eb194c7b5d0dd2908ae90f4843268a2c45563092ade08acb6ab481a08176102fc803fbb2f8ad11b0e1531bd37df543498daf180b12017f4d4d426ca29b4161075534bfb914968088a9d13785d0adc0e2580d3548494b2a9e91605f2b27e6cc701c796f0de7c6f471f6ab6cb9272a1ed637ca32a60d117505d82af3c1336104afb537d01a8f70b510e1eebf4869cb976c419473795a66c7f5e6e20a8094b1bb603a74330c537c5c0698c31538bd2e138c1275a1bdf24c5fa8ab3b7b526324e7918a382d1363b3d463764222150e04" ++ },{ ++ "4. a positive test case that decrypts to 9 byte long value", ++ NULL, ++ "", ++ "6c60845a854b4571f678941ae35a2ac03f67c21e21146f9db1f2306be9f136453b86ad55647d4f7b5c9e62197aaff0c0e40a3b54c4cde14e774b1c5959b6c2a2302896ffae1f73b00b862a20ff4304fe06cea7ff30ecb3773ca9af27a0b54547350d7c07dfb0a39629c7e71e83fc5af9b2adbaf898e037f1de696a3f328cf45af7ec9aff7173854087fb8fbf34be981efbd8493f9438d1b2ba2a86af082662aa46ae9adfbec51e5f3d9550a4dd1dcb7c8969c9587a6edc82a8cabbc785c40d9fbd12064559fb769450ac3e47e87bc046148130d7eaa843e4b3ccef3675d0630500803cb7ffee3882378c1a404e850c3e20707bb745e42b13c18786c4976076ed9fa8fd0ff15e571bef02cbbe2f90c908ac3734a433b73e778d4d17fcc28f49185ebc6e8536a06d293202d94496453bfdf1c2c7833a3f99fa38ca8a81f42eaa529d603b890308a319c0ab63a35ff8ebac965f6278f5a7e5d622be5d5fe55f0ca3ec993d55430d2bf59c5d3e860e90c16d91a04596f6fdf60d89ed95d88c036dde", ++ "666f7274792074776f" ++ },{ ++ "5. a positive test case with null padded ciphertext", ++ NULL, ++ "", ++ "00f4d565a3286784dbb85327db8807ae557ead229f92aba945cecda5225f606a7d6130edeeb6f26724d1eff1110f9eb18dc3248140ee3837e6688391e78796c526791384f045e21b6b853fb6342a11f309eb77962f37ce23925af600847fbd30e6e07e57de50b606e6b7f288cc777c1a6834f27e6edace508452128916eef7788c8bb227e3548c6a761cc4e9dd1a3584176dc053ba3500adb1d5e1611291654f12dfc5722832f635db3002d73f9defc310ace62c63868d341619c7ee15b20243b3371e05078e11219770c701d9f341af35df1bc729de294825ff2e416aa11526612852777eb131f9c45151eb144980d70608d2fc4043477368369aa0fe487a48bd57e66b00c3c58f941549f5ec050fca64449debe7a0c4ac51e55cb71620a70312aa4bd85fac1410c9c7f9d6ec610b7d11bf8faeffa20255d1a1bead9297d0aa8765cd2805847d639bc439f4a6c896e2008f746f9590ff4596de5ddde000ed666c452c978043ff4298461eb5a26d5e63d821438627f91201924bf7f2aeee1727", ++ "666f7274792074776f" ++ },{ ++ "6. a positive test case with double null padded ciphertext", ++ NULL, ++ "", ++ "00001ec97ac981dfd9dcc7a7389fdfa9d361141dac80c23a060410d472c16094e6cdffc0c3684d84aa402d7051dfccb2f6da33f66985d2a259f5b7fbf39ac537e95c5b7050eb18844a0513abef812cc8e74a3c5240009e6e805dcadf532bc1a2702d5acc9e585fad5b89d461fcc1397351cdce35171523758b171dc041f412e42966de7f94856477356d06f2a6b40e3ff0547562a4d91bbf1338e9e049facbee8b20171164505468cd308997447d3dc4b0acb49e7d368fedd8c734251f30a83491d2506f3f87318cc118823244a393dc7c5c739a2733d93e1b13db6840a9429947357f47b23fbe39b7d2d61e5ee26f9946c4632f6c4699e452f412a26641d4751135400713cd56ec66f0370423d55d2af70f5e7ad0adea8e4a0d904a01e4ac272eba4af1a029dd53eb71f115bf31f7a6c8b19a6523adeecc0d4c3c107575e38572a8f8474ccad163e46e2e8b08111132aa97a16fb588c9b7e37b3b3d7490381f3c55d1a9869a0fd42cd86fed59ecec78cb6b2dfd06a497f5afe3419691314ba0", ++ "666f7274792074776f" ++ },{ ++ "7. a positive test case with double null truncated ciphertext", ++ NULL, ++ "", ++ "1ec97ac981dfd9dcc7a7389fdfa9d361141dac80c23a060410d472c16094e6cdffc0c3684d84aa402d7051dfccb2f6da33f66985d2a259f5b7fbf39ac537e95c5b7050eb18844a0513abef812cc8e74a3c5240009e6e805dcadf532bc1a2702d5acc9e585fad5b89d461fcc1397351cdce35171523758b171dc041f412e42966de7f94856477356d06f2a6b40e3ff0547562a4d91bbf1338e9e049facbee8b20171164505468cd308997447d3dc4b0acb49e7d368fedd8c734251f30a83491d2506f3f87318cc118823244a393dc7c5c739a2733d93e1b13db6840a9429947357f47b23fbe39b7d2d61e5ee26f9946c4632f6c4699e452f412a26641d4751135400713cd56ec66f0370423d55d2af70f5e7ad0adea8e4a0d904a01e4ac272eba4af1a029dd53eb71f115bf31f7a6c8b19a6523adeecc0d4c3c107575e38572a8f8474ccad163e46e2e8b08111132aa97a16fb588c9b7e37b3b3d7490381f3c55d1a9869a0fd42cd86fed59ecec78cb6b2dfd06a497f5afe3419691314ba0", ++ "666f7274792074776f" ++ },{ ++ "8. a random negative test case that generates a 9 byte long message", ++ NULL, ++ "", ++ "5c8555f5cef627c15d37f85c7f5fd6e499264ea4b8e3f9112023aeb722eb38d8eac2be3751fd5a3785ab7f2d59fa3728e5be8c3de78a67464e30b21ee23b5484bb3cd06d0e1c6ad25649c8518165653eb80488bfb491b20c04897a6772f69292222fc5ef50b5cf9efc6d60426a449b6c489569d48c83488df629d695653d409ce49a795447fcec2c58a1a672e4a391401d428baaf781516e11e323d302fcf20f6eab2b2dbe53a48c987e407c4d7e1cb41131329138313d330204173a4f3ff06c6fadf970f0ed1005d0b27e35c3d11693e0429e272d583e57b2c58d24315c397856b34485dcb077665592b747f889d34febf2be8fce66c265fd9fc3575a6286a5ce88b4b413a08efc57a07a8f57a999605a837b0542695c0d189e678b53662ecf7c3d37d9dbeea585eebfaf79141118e06762c2381fe27ca6288edddc19fd67cd64f16b46e06d8a59ac530f22cd83cc0bc4e37feb52015cbb2283043ccf5e78a4eb7146827d7a466b66c8a4a4826c1bad68123a7f2d00fc1736525ff90c058f56", ++ "257906ca6de8307728" ++ },{ ++ "9. a random negative test case that generates a 9 byte long message based on second to last value from PRF", ++ NULL, ++ "", ++ "758c215aa6acd61248062b88284bf43c13cb3b3d02410be4238607442f1c0216706e21a03a2c10eb624a63322d854da195c017b76fea83e274fa371834dcd2f3b7accf433fc212ad76c0bac366e1ed32e25b279f94129be7c64d6e162adc08ccebc0cfe8e926f01c33ab9c065f0e0ac83ae5137a4cb66702615ad68a35707d8676d2740d7c1a954680c83980e19778ed11eed3a7c2dbdfc461a9bbef671c1bc00c882d361d29d5f80c42bdf5efec886c34138f83369c6933b2ac4e93e764265351b4a0083f040e14f511f09b22f96566138864e4e6ff24da4810095da98e0585410951538ced2f757a277ff8e17172f06572c9024eeae503f176fd46eb6c5cd9ba07af11cde31dccac12eb3a4249a7bfd3b19797ad1656984bfcbf6f74e8f99d8f1ac420811f3d166d87f935ef15ae858cf9e72c8e2b547bf16c3fb09a8c9bf88fd2e5d38bf24ed610896131a84df76b9f920fe76d71fff938e9199f3b8cd0c11fd0201f9139d7673a871a9e7d4adc3bbe360c8813617cd60a90128fbe34c9d5", ++ "043383c929060374ed" ++ },{ ++ "10. a random negative test that generates message based on 3rd last value from PRF", ++ NULL, ++ "", ++ "7b22d5e62d287968c6622171a1f75db4b0fd15cdf3134a1895d235d56f8d8fe619f2bf4868174a91d7601a82975d2255190d28b869141d7c395f0b8c4e2be2b2c1b4ffc12ce749a6f6803d4cfe7fba0a8d6949c04151f981c0d84592aa2ff25d1bd3ce5d10cb03daca6b496c6ad40d30bfa8acdfd02cdb9326c4bdd93b949c9dc46caa8f0e5f429785bce64136a429a3695ee674b647452bea1b0c6de9c5f1e8760d5ef6d5a9cfff40457b023d3c233c1dcb323e7808103e73963b2eafc928c9eeb0ee3294955415c1ddd9a1bb7e138fecd79a3cb89c57bd2305524624814aaf0fd1acbf379f7f5b39421f12f115ba488d380586095bb53f174fae424fa4c8e3b299709cd344b9f949b1ab57f1c645d7ed3c8f81d5594197355029fee8960970ff59710dc0e5eb50ea6f4c3938e3f89ed7933023a2c2ddffaba07be147f686828bd7d520f300507ed6e71bdaee05570b27bc92741108ac2eb433f028e138dd6d63067bc206ea2d826a7f41c0d613daed020f0f30f4e272e9618e0a8c39018a83", ++ "70263fa6050534b9e0" ++ },{ ++ "11. an otherwise valid plaintext, but with wrong first byte (0x01 instead of 0x00)", ++ NULL, ++ "", ++ "6db80adb5ff0a768caf1378ecc382a694e7d1bde2eff4ba12c48aaf794ded7a994a5b2b57acec20dbec4ae385c9dd531945c0f197a5496908725fc99d88601a17d3bb0b2d38d2c1c3100f39955a4cb3dbed5a38bf900f23d91e173640e4ec655c84fdfe71fcdb12a386108fcf718c9b7af37d39703e882436224c877a2235e8344fba6c951eb7e2a4d1d1de81fb463ac1b880f6cc0e59ade05c8ce35179ecd09546731fc07b141d3d6b342a97ae747e61a9130f72d37ac5a2c30215b6cbd66c7db893810df58b4c457b4b54f34428247d584e0fa71062446210db08254fb9ead1ba1a393c724bd291f0cf1a7143f32df849051dc896d7d176fef3b57ab6dffd626d0c3044e9edb2e3d012ace202d2581df01bec7e9aa0727a6650dd373d374f0bc0f4a611f8139dfe97d63e70c6188f4df5b672e47c51d8aa567097293fbff127c75ec690b43407578b73c85451710a0cece58fd497d7f7bd36a8a92783ef7dc6265dff52aac8b70340b996508d39217f2783ce6fc91a1cc94bb2ac487b84f62", ++ "6d8d3a094ff3afff4c" ++ },{ ++ "12. an otherwise valid plaintext, but with wrong second byte (0x01 instead of 0x02)", ++ NULL, ++ "", ++ "417328c034458563079a4024817d0150340c34e25ae16dcad690623f702e5c748a6ebb3419ff48f486f83ba9df35c05efbd7f40613f0fc996c53706c30df6bba6dcd4a40825f96133f3c21638a342bd4663dffbd0073980dac47f8c1dd8e97ce1412e4f91f2a8adb1ac2b1071066efe8d718bbb88ca4a59bd61500e826f2365255a409bece0f972df97c3a55e09289ef5fa815a2353ef393fd1aecfc888d611c16aec532e5148be15ef1bf2834b8f75bb26db08b66d2baad6464f8439d1986b533813321dbb180080910f233bcc4dd784fb21871aef41be08b7bfad4ecc3b68f228cb5317ac6ec1227bc7d0e452037ba918ee1da9fdb8393ae93b1e937a8d4691a17871d5092d2384b6190a53df888f65b951b05ed4ad57fe4b0c6a47b5b22f32a7f23c1a234c9feb5d8713d949686760680da4db454f4acad972470033472b9864d63e8d23eefc87ebcf464ecf33f67fbcdd48eab38c5292586b36aef5981ed2fa07b2f9e23fc57d9eb71bfff4111c857e9fff23ceb31e72592e70c874b4936", ++ "c6ae80ffa80bc184b0" ++ },{ ++ "13. an otherwise valid plaintext, but with zero byte in first byte of padding", ++ NULL, ++ "", ++ "8542c626fe533467acffcd4e617692244c9b5a3bf0a215c5d64891ced4bf4f9591b4b2aedff9843057986d81631b0acb3704ec2180e5696e8bd15b217a0ec36d2061b0e2182faa3d1c59bd3f9086a10077a3337a3f5da503ec3753535ffd25b837a12f2541afefd0cffb0224b8f874e4bed13949e105c075ed44e287c5ae03b155e06b90ed247d2c07f1ef3323e3508cce4e4074606c54172ad74d12f8c3a47f654ad671104bf7681e5b061862747d9afd37e07d8e0e2291e01f14a95a1bb4cbb47c304ef067595a3947ee2d722067e38a0f046f43ec29cac6a8801c6e3e9a2331b1d45a7aa2c6af3205be382dd026e389614ee095665a611ab2e8dced2ee1c9d08ac9de11aef5b3803fc9a9ce8231ec87b5fed386fb92ee3db995a89307bcba844bd0a691c29ae51216e949dfc813133cb06a07265fd807bcb3377f6adb0a481d9b7f442003115895939773e6b95371c4febef29edae946fa245e7c50729e2e558cfaad773d1fd5f67b457a6d9d17a847c6fcbdb103a86f35f228cefc06cea0", ++ "a8a9301daa01bb25c7" ++ },{ ++ "14. an otherwise valid plaintext, but with zero byte in eight byte of padding", ++ NULL, ++ "", ++ "449dfa237a70a99cb0351793ec8677882021c2aa743580bf6a0ea672055cffe8303ac42855b1d1f3373aae6af09cb9074180fc963e9d1478a4f98b3b4861d3e7f0aa8560cf603711f139db77667ca14ba3a1acdedfca9ef4603d6d7eb0645bfc805304f9ad9d77d34762ce5cd84bd3ec9d35c30e3be72a1e8d355d5674a141b5530659ad64ebb6082e6f73a80832ab6388912538914654d34602f4b3b1c78589b4a5d964b2efcca1dc7004c41f6cafcb5a7159a7fc7c0398604d0edbd4c8f4f04067da6a153a05e7cbeea13b5ee412400ef7d4f3106f4798da707ec37a11286df2b7a204856d5ff773613fd1e453a7114b78e347d3e8078e1cb3276b3562486ba630bf719697e0073a123c3e60ebb5c7a1ccff4279faffa2402bc1109f8d559d6766e73591943dfcf25ba10c3762f02af85187799b8b4b135c3990793a6fd32642f1557405ba55cc7cf7336a0e967073c5fa50743f9cc5e3017c172d9898d2af83345e71b3e0c22ab791eacb6484a32ec60ebc226ec9deaee91b1a0560c2b571", ++ "6c716fe01d44398018" ++ },{ ++ "15. an otherwise valid plaintext, but with null separator missing", ++ NULL, ++ "", ++ "a7a5c99e50da48769ecb779d9abe86ef9ec8c38c6f43f17c7f2d7af608a4a1bd6cf695b47e97c191c61fb5a27318d02f495a176b9fae5a55b5d3fabd1d8aae4957e3879cb0c60f037724e11be5f30f08fc51c033731f14b44b414d11278cd3dba7e1c8bfe208d2b2bb7ec36366dacb6c88b24cd79ab394adf19dbbc21dfa5788bacbadc6a62f79cf54fd8cf585c615b5c0eb94c35aa9de25321c8ffefb8916bbaa2697cb2dd82ee98939df9b6704cee77793edd2b4947d82e00e5749664970736c59a84197bd72b5c71e36aae29cd39af6ac73a368edbc1ca792e1309f442aafcd77c992c88f8e4863149f221695cb7b0236e75b2339a02c4ea114854372c306b9412d8eedb600a31532002f2cea07b4df963a093185e4607732e46d753b540974fb5a5c3f9432df22e85bb17611370966c5522fd23f2ad3484341ba7fd8885fc8e6d379a611d13a2aca784fba2073208faad2137bf1979a0fa146c1880d4337db3274269493bab44a1bcd0681f7227ffdf589c2e925ed9d36302509d1109ba4", ++ "aa2de6cde4e2442884" ++ },{ ++ NULL, ++ NULL, ++ NULL, ++ NULL, ++ NULL, ++ } ++ } + } + }; +Index: libgcrypt-1.11.1/tests/pkcs1v2.c +=================================================================== +--- libgcrypt-1.11.1.orig/tests/pkcs1v2.c ++++ libgcrypt-1.11.1/tests/pkcs1v2.c +@@ -82,7 +82,7 @@ data_from_hex (const char *string, size_ + + static int + extract_cmp_data (gcry_sexp_t sexp, const char *name, const char *expected, +- const char *description) ++ const char *description, int quiet) + { + gcry_sexp_t l1; + const void *a; +@@ -96,13 +96,15 @@ extract_cmp_data (gcry_sexp_t sexp, cons + b = data_from_hex (expected, &blen); + if (!a) + { +- info ("%s: parameter \"%s\" missing in key\n", description, name); ++ if (!quiet) ++ info ("%s: parameter \"%s\" missing in key\n", description, name); + rc = 1; + } + else if ( alen != blen || memcmp (a, b, alen) ) + { +- info ("%s: parameter \"%s\" does not match expected value\n", +- description, name); ++ if (!quiet) ++ info ("%s: parameter \"%s\" does not match expected value\n", ++ description, name); + rc = 1; + } + gcry_free (b); +@@ -192,7 +194,7 @@ check_oaep (void) + else + { + if (extract_cmp_data (ciph, "a", tbl[tno].m[mno].encr, +- tbl[tno].m[mno].desc)) ++ tbl[tno].m[mno].desc, 0)) + { + show_sexp ("encrypt result:\n", ciph); + fail ("mismatch in gcry_pk_encrypt\n"); +@@ -223,7 +225,7 @@ check_oaep (void) + else + { + if (extract_cmp_data (plain, "value", tbl[tno].m[mno].mesg, +- tbl[tno].m[mno].desc)) ++ tbl[tno].m[mno].desc, 0)) + { + show_sexp ("decrypt result:\n", plain); + fail ("mismatch in gcry_pk_decrypt\n"); +@@ -326,7 +328,7 @@ check_pss (void) + else + { + if (extract_cmp_data (sig, "s", tbl[tno].m[mno].sign, +- tbl[tno].m[mno].desc)) ++ tbl[tno].m[mno].desc, 0)) + { + show_sexp ("sign result:\n", sig); + fail ("mismatch in gcry_pk_sign\n"); +@@ -428,45 +430,89 @@ check_v15crypt (void) + void *mesg, *seed, *encr; + size_t mesg_len, seed_len, encr_len; + gcry_sexp_t plain, ciph; +- ++ if (tbl[tno].m[mno].desc == NULL) ++ break; ++ + if (verbose) + info ("running test: %s\n", tbl[tno].m[mno].desc); + +- mesg = data_from_hex (tbl[tno].m[mno].mesg, &mesg_len); ++ if (tbl[tno].m[mno].mesg) ++ { ++ mesg = data_from_hex (tbl[tno].m[mno].mesg, &mesg_len); ++ seed = data_from_hex (tbl[tno].m[mno].seed, &seed_len); ++ ++ err = gcry_sexp_build (&plain, NULL, ++ "(data (flags pkcs1)" ++ "(value %b)(random-override %b))", ++ (int)mesg_len, mesg, ++ (int)seed_len, seed); ++ if (err) ++ die ("constructing plain data failed: %s\n", gpg_strerror (err)); ++ gcry_free (mesg); ++ gcry_free (seed); ++ ++ err = gcry_pk_encrypt (&ciph, plain, pub_key); ++ if (err) ++ { ++ show_sexp ("plain:\n", ciph); ++ fail ("gcry_pk_encrypt failed: %s\n", gpg_strerror (err)); ++ } ++ else ++ { ++ if (extract_cmp_data (ciph, "a", tbl[tno].m[mno].encr, ++ tbl[tno].m[mno].desc, 0)) ++ { ++ show_sexp ("encrypt result:\n", ciph); ++ fail ("mismatch in gcry_pk_encrypt\n"); ++ } ++ gcry_sexp_release (ciph); ++ ciph = NULL; ++ } ++ gcry_sexp_release (plain); ++ plain = NULL; ++ } ++ ++ /* Now test the decryption. */ ++ encr = data_from_hex (tbl[tno].m[mno].encr, &encr_len); + seed = data_from_hex (tbl[tno].m[mno].seed, &seed_len); + +- err = gcry_sexp_build (&plain, NULL, +- "(data (flags pkcs1)" +- "(value %b)(random-override %b))", +- (int)mesg_len, mesg, +- (int)seed_len, seed); ++#ifdef WITH_MARVIN_WORKAROUND ++ /* First try without implicit rejection -- this should fail for invalid inputs */ ++ err = gcry_sexp_build (&ciph, NULL, ++ "(enc-val (flags pkcs1 no-implicit-rejection)" ++ "(rsa (a %b)))", ++ (int)encr_len, encr); + if (err) +- die ("constructing plain data failed: %s\n", gpg_strerror (err)); +- gcry_free (mesg); +- gcry_free (seed); +- +- err = gcry_pk_encrypt (&ciph, plain, pub_key); ++ die ("constructing cipher data failed: %s\n", gpg_strerror (err)); ++ ++ err = gcry_pk_decrypt (&plain, ciph, sec_key); + if (err) + { +- show_sexp ("plain:\n", ciph); +- fail ("gcry_pk_encrypt failed: %s\n", gpg_strerror (err)); ++ /* If the message is not set, the padding is invalid and failure is expected */ ++ if (tbl[tno].m[mno].mesg != NULL) ++ { ++ show_sexp ("ciph:\n", ciph); ++ fail ("gcry_pk_decrypt failed: %s\n", gpg_strerror (err)); ++ } + } + else + { +- if (extract_cmp_data (ciph, "a", tbl[tno].m[mno].encr, +- tbl[tno].m[mno].desc)) +- { +- show_sexp ("encrypt result:\n", ciph); +- fail ("mismatch in gcry_pk_encrypt\n"); +- } +- gcry_sexp_release (ciph); ++ /* If the message is not set, it is in the synthetic field */ ++ const char *msg = tbl[tno].m[mno].mesg; ++ if (msg == NULL) ++ msg = tbl[tno].m[mno].synt; ++ if (extract_cmp_data (plain, "value", msg, ++ tbl[tno].m[mno].desc, 0)) ++ { ++ show_sexp ("decrypt result:\n", plain); ++ fail ("mismatch in gcry_pk_decrypt.\n"); ++ } ++ gcry_sexp_release (plain); + ciph = NULL; + } +- gcry_sexp_release (plain); +- plain = NULL; +- +- /* Now test the decryption. */ +- encr = data_from_hex (tbl[tno].m[mno].encr, &encr_len); ++ gcry_sexp_release (ciph); ++ ciph = NULL; ++#endif /* WITH_MARVIN_WORKAROUND */ + + err = gcry_sexp_build (&ciph, NULL, + "(enc-val (flags pkcs1)" +@@ -480,19 +526,23 @@ check_v15crypt (void) + if (err) + { + show_sexp ("ciph:\n", ciph); +- fail ("gcry_pk_decrypt failed: %s\n", gpg_strerror (err)); ++ fail ("gcry_pk_decrypt w RSA failed: %s\n", gpg_strerror (err)); + } + else + { +- if (extract_cmp_data (plain, "value", tbl[tno].m[mno].mesg, +- tbl[tno].m[mno].desc)) ++ /* If the message is not set, expect the synthetic message here */ ++ const char *msg = tbl[tno].m[mno].mesg; ++ if (msg == NULL) ++ msg = tbl[tno].m[mno].synt; ++ if (extract_cmp_data (plain, "value", msg, ++ tbl[tno].m[mno].desc, 0)) + { + show_sexp ("decrypt result:\n", plain); +- fail ("mismatch in gcry_pk_decrypt\n"); ++ fail ("mismatch in gcry_pk_decrypt. Expected %s\n", msg); + } +- gcry_sexp_release (plain); +- plain = NULL; + } ++ gcry_sexp_release (plain); ++ plain = NULL; + gcry_sexp_release (ciph); + ciph = NULL; + } +@@ -584,7 +634,7 @@ check_v15sign (void) + else + { + if (extract_cmp_data (sig, "s", tbl[tno].m[mno].sign, +- tbl[tno].m[mno].desc)) ++ tbl[tno].m[mno].desc, 0)) + { + show_sexp ("sign result:\n", sig); + fail ("mismatch in gcry_pk_sign\n"); diff --git a/libgcrypt-Chacha20-poly1305-Optimized-chacha20-poly1305.patch b/libgcrypt-Chacha20-poly1305-Optimized-chacha20-poly1305.patch new file mode 100644 index 0000000..5877fee --- /dev/null +++ b/libgcrypt-Chacha20-poly1305-Optimized-chacha20-poly1305.patch @@ -0,0 +1,1993 @@ +commit 88fe7ac33eb4cb4dff76a5cc7fca50da5fb0ee3a +Author: Danny Tsen +Date: Sun Jun 12 21:30:19 2022 +0300 + + Chacha20 poly1305 Optimized chacha20 poly1305 for P10 operation + + * configure.ac: Added chacha20 and poly1305 assembly implementations. + * cipher/chacha20-p10le-8x.s: (New) - support 8 blocks (512 bytes) + unrolling. + * cipher/poly1305-p10le.s: (New) - support 4 blocks (128 bytes) + unrolling. + * cipher/Makefile.am: Added new chacha20 and poly1305 files. + * cipher/chacha20.c: Added PPC p10 le support for 8x chacha20. + * cipher/poly1305.c: Added PPC p10 le support for 4x poly1305. + * cipher/poly1305-internal.h: Added PPC p10 le support for poly1305. + --- + + GnuPG-bug-id: 6006 + Signed-off-by: Danny Tsen + [jk: cosmetic changes to C code] + [jk: fix building on ppc64be] + Signed-off-by: Jussi Kivilinna + +Index: libgcrypt-1.10.2/cipher/Makefile.am +=================================================================== +--- libgcrypt-1.10.2.orig/cipher/Makefile.am ++++ libgcrypt-1.10.2/cipher/Makefile.am +@@ -83,6 +83,7 @@ EXTRA_libcipher_la_SOURCES = \ + chacha20.c chacha20-amd64-ssse3.S chacha20-amd64-avx2.S \ + chacha20-armv7-neon.S chacha20-aarch64.S \ + chacha20-ppc.c chacha20-s390x.S \ ++ chacha20-p10le-8x.s \ + cipher-gcm-ppc.c cipher-gcm-intel-pclmul.c cipher-gcm-armv7-neon.S \ + cipher-gcm-armv8-aarch32-ce.S cipher-gcm-armv8-aarch64-ce.S \ + crc.c crc-intel-pclmul.c crc-armv8-ce.c \ +@@ -99,6 +100,7 @@ EXTRA_libcipher_la_SOURCES = \ + md4.c \ + md5.c \ + poly1305-s390x.S \ ++ poly1305-p10le.s \ + rijndael.c rijndael-internal.h rijndael-tables.h \ + rijndael-aesni.c rijndael-padlock.c \ + rijndael-amd64.S rijndael-arm.S \ +Index: libgcrypt-1.10.2/cipher/chacha20-p10le-8x.s +=================================================================== +--- /dev/null ++++ libgcrypt-1.10.2/cipher/chacha20-p10le-8x.s +@@ -0,0 +1,864 @@ ++# Copyright 2021- IBM Inc. All rights reserved ++# ++# This file is part of Libgcrypt. ++# ++# Libgcrypt is free software; you can redistribute it and/or modify ++# it under the terms of the GNU Lesser General Public License as ++# published by the Free Software Foundation; either version 2.1 of ++# the License, or (at your option) any later version. ++# ++# Libgcrypt 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 Lesser General Public License for more details. ++# ++# You should have received a copy of the GNU Lesser General Public ++# License along with this program; if not, see . ++# ++#=================================================================================== ++# Written by Danny Tsen ++# ++# This function handles multiple 64-byte block data length ++# and the length should be more than 512 bytes. ++# ++# unsigned int _gcry_chacha20_p10le_8x(u32 *state, byte *dst, const byte *src, size_t len); ++# ++# r1 - top of the stack ++# r3 to r10 input parameters ++# r3 - out ++# r4 - inp ++# r5 - len ++# r6 - key[8] ++# r7 - counter[4] ++# ++# do rounds, 8 quarter rounds ++# 1. a += b; d ^= a; d <<<= 16; ++# 2. c += d; b ^= c; b <<<= 12; ++# 3. a += b; d ^= a; d <<<= 8; ++# 4. c += d; b ^= c; b <<<= 7 ++# ++# row1 = (row1 + row2), row4 = row1 xor row4, row4 rotate each word by 16 ++# row3 = (row3 + row4), row2 = row3 xor row2, row2 rotate each word by 12 ++# row1 = (row1 + row2), row4 = row1 xor row4, row4 rotate each word by 8 ++# row3 = (row3 + row4), row2 = row3 xor row2, row2 rotate each word by 7 ++# ++# 4 blocks (a b c d) ++# ++# a0 b0 c0 d0 ++# a1 b1 c1 d1 ++# ... ++# a4 b4 c4 d4 ++# ... ++# a8 b8 c8 d8 ++# ... ++# a12 b12 c12 d12 ++# a13 ... ++# a14 ... ++# a15 b15 c15 d15 ++# ++# Column round (v0, v4, v8, v12, v1, v5, v9, v13, v2, v6, v10, v14, v3, v7, v11, v15) ++# Diagnal round (v0, v5, v10, v15, v1, v6, v11, v12, v2, v7, v8, v13, v3, v4, v9, v14) ++# ++.text ++ ++.macro QT_loop_8x ++ # QR(v0, v4, v8, v12, v1, v5, v9, v13, v2, v6, v10, v14, v3, v7, v11, v15) ++ xxlor 0, 32+25, 32+25 ++ xxlor 32+25, 20, 20 ++ vadduwm 0, 0, 4 ++ vadduwm 1, 1, 5 ++ vadduwm 2, 2, 6 ++ vadduwm 3, 3, 7 ++ vadduwm 16, 16, 20 ++ vadduwm 17, 17, 21 ++ vadduwm 18, 18, 22 ++ vadduwm 19, 19, 23 ++ ++ vpermxor 12, 12, 0, 25 ++ vpermxor 13, 13, 1, 25 ++ vpermxor 14, 14, 2, 25 ++ vpermxor 15, 15, 3, 25 ++ vpermxor 28, 28, 16, 25 ++ vpermxor 29, 29, 17, 25 ++ vpermxor 30, 30, 18, 25 ++ vpermxor 31, 31, 19, 25 ++ xxlor 32+25, 0, 0 ++ vadduwm 8, 8, 12 ++ vadduwm 9, 9, 13 ++ vadduwm 10, 10, 14 ++ vadduwm 11, 11, 15 ++ vadduwm 24, 24, 28 ++ vadduwm 25, 25, 29 ++ vadduwm 26, 26, 30 ++ vadduwm 27, 27, 31 ++ vxor 4, 4, 8 ++ vxor 5, 5, 9 ++ vxor 6, 6, 10 ++ vxor 7, 7, 11 ++ vxor 20, 20, 24 ++ vxor 21, 21, 25 ++ vxor 22, 22, 26 ++ vxor 23, 23, 27 ++ ++ xxlor 0, 32+25, 32+25 ++ xxlor 32+25, 21, 21 ++ vrlw 4, 4, 25 # ++ vrlw 5, 5, 25 ++ vrlw 6, 6, 25 ++ vrlw 7, 7, 25 ++ vrlw 20, 20, 25 # ++ vrlw 21, 21, 25 ++ vrlw 22, 22, 25 ++ vrlw 23, 23, 25 ++ xxlor 32+25, 0, 0 ++ vadduwm 0, 0, 4 ++ vadduwm 1, 1, 5 ++ vadduwm 2, 2, 6 ++ vadduwm 3, 3, 7 ++ vadduwm 16, 16, 20 ++ vadduwm 17, 17, 21 ++ vadduwm 18, 18, 22 ++ vadduwm 19, 19, 23 ++ ++ xxlor 0, 32+25, 32+25 ++ xxlor 32+25, 22, 22 ++ vpermxor 12, 12, 0, 25 ++ vpermxor 13, 13, 1, 25 ++ vpermxor 14, 14, 2, 25 ++ vpermxor 15, 15, 3, 25 ++ vpermxor 28, 28, 16, 25 ++ vpermxor 29, 29, 17, 25 ++ vpermxor 30, 30, 18, 25 ++ vpermxor 31, 31, 19, 25 ++ xxlor 32+25, 0, 0 ++ vadduwm 8, 8, 12 ++ vadduwm 9, 9, 13 ++ vadduwm 10, 10, 14 ++ vadduwm 11, 11, 15 ++ vadduwm 24, 24, 28 ++ vadduwm 25, 25, 29 ++ vadduwm 26, 26, 30 ++ vadduwm 27, 27, 31 ++ xxlor 0, 32+28, 32+28 ++ xxlor 32+28, 23, 23 ++ vxor 4, 4, 8 ++ vxor 5, 5, 9 ++ vxor 6, 6, 10 ++ vxor 7, 7, 11 ++ vxor 20, 20, 24 ++ vxor 21, 21, 25 ++ vxor 22, 22, 26 ++ vxor 23, 23, 27 ++ vrlw 4, 4, 28 # ++ vrlw 5, 5, 28 ++ vrlw 6, 6, 28 ++ vrlw 7, 7, 28 ++ vrlw 20, 20, 28 # ++ vrlw 21, 21, 28 ++ vrlw 22, 22, 28 ++ vrlw 23, 23, 28 ++ xxlor 32+28, 0, 0 ++ ++ # QR(v0, v5, v10, v15, v1, v6, v11, v12, v2, v7, v8, v13, v3, v4, v9, v14) ++ xxlor 0, 32+25, 32+25 ++ xxlor 32+25, 20, 20 ++ vadduwm 0, 0, 5 ++ vadduwm 1, 1, 6 ++ vadduwm 2, 2, 7 ++ vadduwm 3, 3, 4 ++ vadduwm 16, 16, 21 ++ vadduwm 17, 17, 22 ++ vadduwm 18, 18, 23 ++ vadduwm 19, 19, 20 ++ ++ vpermxor 15, 15, 0, 25 ++ vpermxor 12, 12, 1, 25 ++ vpermxor 13, 13, 2, 25 ++ vpermxor 14, 14, 3, 25 ++ vpermxor 31, 31, 16, 25 ++ vpermxor 28, 28, 17, 25 ++ vpermxor 29, 29, 18, 25 ++ vpermxor 30, 30, 19, 25 ++ ++ xxlor 32+25, 0, 0 ++ vadduwm 10, 10, 15 ++ vadduwm 11, 11, 12 ++ vadduwm 8, 8, 13 ++ vadduwm 9, 9, 14 ++ vadduwm 26, 26, 31 ++ vadduwm 27, 27, 28 ++ vadduwm 24, 24, 29 ++ vadduwm 25, 25, 30 ++ vxor 5, 5, 10 ++ vxor 6, 6, 11 ++ vxor 7, 7, 8 ++ vxor 4, 4, 9 ++ vxor 21, 21, 26 ++ vxor 22, 22, 27 ++ vxor 23, 23, 24 ++ vxor 20, 20, 25 ++ ++ xxlor 0, 32+25, 32+25 ++ xxlor 32+25, 21, 21 ++ vrlw 5, 5, 25 ++ vrlw 6, 6, 25 ++ vrlw 7, 7, 25 ++ vrlw 4, 4, 25 ++ vrlw 21, 21, 25 ++ vrlw 22, 22, 25 ++ vrlw 23, 23, 25 ++ vrlw 20, 20, 25 ++ xxlor 32+25, 0, 0 ++ ++ vadduwm 0, 0, 5 ++ vadduwm 1, 1, 6 ++ vadduwm 2, 2, 7 ++ vadduwm 3, 3, 4 ++ vadduwm 16, 16, 21 ++ vadduwm 17, 17, 22 ++ vadduwm 18, 18, 23 ++ vadduwm 19, 19, 20 ++ ++ xxlor 0, 32+25, 32+25 ++ xxlor 32+25, 22, 22 ++ vpermxor 15, 15, 0, 25 ++ vpermxor 12, 12, 1, 25 ++ vpermxor 13, 13, 2, 25 ++ vpermxor 14, 14, 3, 25 ++ vpermxor 31, 31, 16, 25 ++ vpermxor 28, 28, 17, 25 ++ vpermxor 29, 29, 18, 25 ++ vpermxor 30, 30, 19, 25 ++ xxlor 32+25, 0, 0 ++ ++ vadduwm 10, 10, 15 ++ vadduwm 11, 11, 12 ++ vadduwm 8, 8, 13 ++ vadduwm 9, 9, 14 ++ vadduwm 26, 26, 31 ++ vadduwm 27, 27, 28 ++ vadduwm 24, 24, 29 ++ vadduwm 25, 25, 30 ++ ++ xxlor 0, 32+28, 32+28 ++ xxlor 32+28, 23, 23 ++ vxor 5, 5, 10 ++ vxor 6, 6, 11 ++ vxor 7, 7, 8 ++ vxor 4, 4, 9 ++ vxor 21, 21, 26 ++ vxor 22, 22, 27 ++ vxor 23, 23, 24 ++ vxor 20, 20, 25 ++ vrlw 5, 5, 28 ++ vrlw 6, 6, 28 ++ vrlw 7, 7, 28 ++ vrlw 4, 4, 28 ++ vrlw 21, 21, 28 ++ vrlw 22, 22, 28 ++ vrlw 23, 23, 28 ++ vrlw 20, 20, 28 ++ xxlor 32+28, 0, 0 ++.endm ++ ++.macro QT_loop_4x ++ # QR(v0, v4, v8, v12, v1, v5, v9, v13, v2, v6, v10, v14, v3, v7, v11, v15) ++ vadduwm 0, 0, 4 ++ vadduwm 1, 1, 5 ++ vadduwm 2, 2, 6 ++ vadduwm 3, 3, 7 ++ vpermxor 12, 12, 0, 20 ++ vpermxor 13, 13, 1, 20 ++ vpermxor 14, 14, 2, 20 ++ vpermxor 15, 15, 3, 20 ++ vadduwm 8, 8, 12 ++ vadduwm 9, 9, 13 ++ vadduwm 10, 10, 14 ++ vadduwm 11, 11, 15 ++ vxor 4, 4, 8 ++ vxor 5, 5, 9 ++ vxor 6, 6, 10 ++ vxor 7, 7, 11 ++ vrlw 4, 4, 21 ++ vrlw 5, 5, 21 ++ vrlw 6, 6, 21 ++ vrlw 7, 7, 21 ++ vadduwm 0, 0, 4 ++ vadduwm 1, 1, 5 ++ vadduwm 2, 2, 6 ++ vadduwm 3, 3, 7 ++ vpermxor 12, 12, 0, 22 ++ vpermxor 13, 13, 1, 22 ++ vpermxor 14, 14, 2, 22 ++ vpermxor 15, 15, 3, 22 ++ vadduwm 8, 8, 12 ++ vadduwm 9, 9, 13 ++ vadduwm 10, 10, 14 ++ vadduwm 11, 11, 15 ++ vxor 4, 4, 8 ++ vxor 5, 5, 9 ++ vxor 6, 6, 10 ++ vxor 7, 7, 11 ++ vrlw 4, 4, 23 ++ vrlw 5, 5, 23 ++ vrlw 6, 6, 23 ++ vrlw 7, 7, 23 ++ ++ # QR(v0, v5, v10, v15, v1, v6, v11, v12, v2, v7, v8, v13, v3, v4, v9, v14) ++ vadduwm 0, 0, 5 ++ vadduwm 1, 1, 6 ++ vadduwm 2, 2, 7 ++ vadduwm 3, 3, 4 ++ vpermxor 15, 15, 0, 20 ++ vpermxor 12, 12, 1, 20 ++ vpermxor 13, 13, 2, 20 ++ vpermxor 14, 14, 3, 20 ++ vadduwm 10, 10, 15 ++ vadduwm 11, 11, 12 ++ vadduwm 8, 8, 13 ++ vadduwm 9, 9, 14 ++ vxor 5, 5, 10 ++ vxor 6, 6, 11 ++ vxor 7, 7, 8 ++ vxor 4, 4, 9 ++ vrlw 5, 5, 21 ++ vrlw 6, 6, 21 ++ vrlw 7, 7, 21 ++ vrlw 4, 4, 21 ++ vadduwm 0, 0, 5 ++ vadduwm 1, 1, 6 ++ vadduwm 2, 2, 7 ++ vadduwm 3, 3, 4 ++ vpermxor 15, 15, 0, 22 ++ vpermxor 12, 12, 1, 22 ++ vpermxor 13, 13, 2, 22 ++ vpermxor 14, 14, 3, 22 ++ vadduwm 10, 10, 15 ++ vadduwm 11, 11, 12 ++ vadduwm 8, 8, 13 ++ vadduwm 9, 9, 14 ++ vxor 5, 5, 10 ++ vxor 6, 6, 11 ++ vxor 7, 7, 8 ++ vxor 4, 4, 9 ++ vrlw 5, 5, 23 ++ vrlw 6, 6, 23 ++ vrlw 7, 7, 23 ++ vrlw 4, 4, 23 ++.endm ++ ++# Transpose ++.macro TP_4x a0 a1 a2 a3 ++ xxmrghw 10, 32+\a0, 32+\a1 # a0, a1, b0, b1 ++ xxmrghw 11, 32+\a2, 32+\a3 # a2, a3, b2, b3 ++ xxmrglw 12, 32+\a0, 32+\a1 # c0, c1, d0, d1 ++ xxmrglw 13, 32+\a2, 32+\a3 # c2, c3, d2, d3 ++ xxpermdi 32+\a0, 10, 11, 0 # a0, a1, a2, a3 ++ xxpermdi 32+\a1, 10, 11, 3 # b0, b1, b2, b3 ++ xxpermdi 32+\a2, 12, 13, 0 # c0, c1, c2, c3 ++ xxpermdi 32+\a3, 12, 13, 3 # d0, d1, d2, d3 ++.endm ++ ++# key stream = working state + state ++.macro Add_state S ++ vadduwm \S+0, \S+0, 16-\S ++ vadduwm \S+4, \S+4, 17-\S ++ vadduwm \S+8, \S+8, 18-\S ++ vadduwm \S+12, \S+12, 19-\S ++ ++ vadduwm \S+1, \S+1, 16-\S ++ vadduwm \S+5, \S+5, 17-\S ++ vadduwm \S+9, \S+9, 18-\S ++ vadduwm \S+13, \S+13, 19-\S ++ ++ vadduwm \S+2, \S+2, 16-\S ++ vadduwm \S+6, \S+6, 17-\S ++ vadduwm \S+10, \S+10, 18-\S ++ vadduwm \S+14, \S+14, 19-\S ++ ++ vadduwm \S+3, \S+3, 16-\S ++ vadduwm \S+7, \S+7, 17-\S ++ vadduwm \S+11, \S+11, 18-\S ++ vadduwm \S+15, \S+15, 19-\S ++.endm ++ ++# ++# write 256 bytes ++# ++.macro Write_256 S ++ add 9, 14, 5 ++ add 16, 14, 4 ++ lxvw4x 0, 0, 9 ++ lxvw4x 1, 17, 9 ++ lxvw4x 2, 18, 9 ++ lxvw4x 3, 19, 9 ++ lxvw4x 4, 20, 9 ++ lxvw4x 5, 21, 9 ++ lxvw4x 6, 22, 9 ++ lxvw4x 7, 23, 9 ++ lxvw4x 8, 24, 9 ++ lxvw4x 9, 25, 9 ++ lxvw4x 10, 26, 9 ++ lxvw4x 11, 27, 9 ++ lxvw4x 12, 28, 9 ++ lxvw4x 13, 29, 9 ++ lxvw4x 14, 30, 9 ++ lxvw4x 15, 31, 9 ++ ++ xxlxor \S+32, \S+32, 0 ++ xxlxor \S+36, \S+36, 1 ++ xxlxor \S+40, \S+40, 2 ++ xxlxor \S+44, \S+44, 3 ++ xxlxor \S+33, \S+33, 4 ++ xxlxor \S+37, \S+37, 5 ++ xxlxor \S+41, \S+41, 6 ++ xxlxor \S+45, \S+45, 7 ++ xxlxor \S+34, \S+34, 8 ++ xxlxor \S+38, \S+38, 9 ++ xxlxor \S+42, \S+42, 10 ++ xxlxor \S+46, \S+46, 11 ++ xxlxor \S+35, \S+35, 12 ++ xxlxor \S+39, \S+39, 13 ++ xxlxor \S+43, \S+43, 14 ++ xxlxor \S+47, \S+47, 15 ++ ++ stxvw4x \S+32, 0, 16 ++ stxvw4x \S+36, 17, 16 ++ stxvw4x \S+40, 18, 16 ++ stxvw4x \S+44, 19, 16 ++ ++ stxvw4x \S+33, 20, 16 ++ stxvw4x \S+37, 21, 16 ++ stxvw4x \S+41, 22, 16 ++ stxvw4x \S+45, 23, 16 ++ ++ stxvw4x \S+34, 24, 16 ++ stxvw4x \S+38, 25, 16 ++ stxvw4x \S+42, 26, 16 ++ stxvw4x \S+46, 27, 16 ++ ++ stxvw4x \S+35, 28, 16 ++ stxvw4x \S+39, 29, 16 ++ stxvw4x \S+43, 30, 16 ++ stxvw4x \S+47, 31, 16 ++ ++.endm ++ ++# ++# unsigned int _gcry_chacha20_p10le_8x(u32 *state, byte *dst, const byte *src, size_t len); ++# ++.global _gcry_chacha20_p10le_8x ++.align 5 ++_gcry_chacha20_p10le_8x: ++ cmpdi 6, 512 ++ blt Out_no_chacha ++ ++ stdu 1,-1024(1) ++ mflr 0 ++ ++ std 14,112(1) ++ std 15,120(1) ++ std 16,128(1) ++ std 17,136(1) ++ std 18,144(1) ++ std 19,152(1) ++ std 20,160(1) ++ std 21,168(1) ++ std 22,176(1) ++ std 23,184(1) ++ std 24,192(1) ++ std 25,200(1) ++ std 26,208(1) ++ std 27,216(1) ++ std 28,224(1) ++ std 29,232(1) ++ std 30,240(1) ++ std 31,248(1) ++ std 0, 1040(1) ++ ++ li 17, 16 ++ li 18, 32 ++ li 19, 48 ++ li 20, 64 ++ li 21, 80 ++ li 22, 96 ++ li 23, 112 ++ li 24, 128 ++ li 25, 144 ++ li 26, 160 ++ li 27, 176 ++ li 28, 192 ++ li 29, 208 ++ li 30, 224 ++ li 31, 240 ++ addi 9, 1, 256 ++ stvx 20, 0, 9 ++ stvx 21, 17, 9 ++ stvx 22, 18, 9 ++ stvx 23, 19, 9 ++ stvx 24, 20, 9 ++ stvx 25, 21, 9 ++ stvx 26, 22, 9 ++ stvx 27, 23, 9 ++ stvx 28, 24, 9 ++ stvx 29, 25, 9 ++ stvx 30, 26, 9 ++ stvx 31, 27, 9 ++ ++ add 9, 9, 27 ++ addi 14, 17, 16 ++ stxvx 14, 14, 9 ++ addi 14, 14, 16 ++ stxvx 15, 14, 9 ++ addi 14, 14, 16 ++ stxvx 16, 14, 9 ++ addi 14, 14, 16 ++ stxvx 17, 14, 9 ++ addi 14, 14, 16 ++ stxvx 18, 14, 9 ++ addi 14, 14, 16 ++ stxvx 19, 14, 9 ++ addi 14, 14, 16 ++ stxvx 20, 14, 9 ++ addi 14, 14, 16 ++ stxvx 21, 14, 9 ++ addi 14, 14, 16 ++ stxvx 22, 14, 9 ++ addi 14, 14, 16 ++ stxvx 23, 14, 9 ++ addi 14, 14, 16 ++ stxvx 24, 14, 9 ++ addi 14, 14, 16 ++ stxvx 25, 14, 9 ++ addi 14, 14, 16 ++ stxvx 26, 14, 9 ++ addi 14, 14, 16 ++ stxvx 27, 14, 9 ++ addi 14, 14, 16 ++ stxvx 28, 14, 9 ++ addi 14, 14, 16 ++ stxvx 29, 14, 9 ++ addi 14, 14, 16 ++ stxvx 30, 14, 9 ++ addi 14, 14, 16 ++ stxvx 31, 14, 9 ++ ++ mr 15, 6 # len ++ li 14, 0 # offset to inp and outp ++ ++ ld 10, sigma@got(2) ++ ++ lxvw4x 48, 0, 3 # vr16, constants ++ lxvw4x 49, 17, 3 # vr17, key 1 ++ lxvw4x 50, 18, 3 # vr18, key 2 ++ lxvw4x 51, 19, 3 # vr19, counter, nonce ++ ++ lxvw4x 62, 19, 10 # vr30, 4 ++ ++ vspltisw 21, 12 ++ vspltisw 23, 7 ++ ++ ld 11, permx@got(2) ++ lxvw4x 32+20, 0, 11 ++ lxvw4x 32+22, 17, 11 ++ ++ li 8, 10 ++ mtctr 8 ++ ++ xxlor 16, 48, 48 ++ xxlor 17, 49, 49 ++ xxlor 18, 50, 50 ++ xxlor 19, 51, 51 ++ ++ vspltisw 25, 4 ++ vspltisw 26, 8 ++ ++ xxlor 16, 48, 48 ++ xxlor 17, 49, 49 ++ xxlor 18, 50, 50 ++ xxlor 19, 51, 51 ++ ++ xxlor 25, 32+26, 32+26 ++ xxlor 24, 32+25, 32+25 ++ ++ vadduwm 31, 30, 25 # (0, 1, 2, 3) + (4, 4, 4, 4) ++ xxlor 30, 32+30, 32+30 ++ xxlor 31, 32+31, 32+31 ++ ++ xxlor 20, 32+20, 32+20 ++ xxlor 21, 32+21, 32+21 ++ xxlor 22, 32+22, 32+22 ++ xxlor 23, 32+23, 32+23 ++ ++Loop_8x: ++ lvx 0, 20, 10 ++ lvx 1, 21, 10 ++ lvx 2, 22, 10 ++ lvx 3, 23, 10 ++ xxspltw 32+4, 17, 0 ++ xxspltw 32+5, 17, 1 ++ xxspltw 32+6, 17, 2 ++ xxspltw 32+7, 17, 3 ++ xxspltw 32+8, 18, 0 ++ xxspltw 32+9, 18, 1 ++ xxspltw 32+10, 18, 2 ++ xxspltw 32+11, 18, 3 ++ xxspltw 32+12, 19, 0 ++ xxspltw 32+13, 19, 1 ++ xxspltw 32+14, 19, 2 ++ xxspltw 32+15, 19, 3 ++ vadduwm 12, 12, 30 # increase counter ++ ++ lvx 16, 20, 10 ++ lvx 17, 21, 10 ++ lvx 18, 22, 10 ++ lvx 19, 23, 10 ++ xxspltw 32+20, 17, 0 ++ xxspltw 32+21, 17, 1 ++ xxspltw 32+22, 17, 2 ++ xxspltw 32+23, 17, 3 ++ xxspltw 32+24, 18, 0 ++ xxspltw 32+25, 18, 1 ++ xxspltw 32+26, 18, 2 ++ xxspltw 32+27, 18, 3 ++ xxspltw 32+28, 19, 0 ++ xxspltw 32+29, 19, 1 ++ vadduwm 28, 28, 31 # increase counter ++ xxspltw 32+30, 19, 2 ++ xxspltw 32+31, 19, 3 ++ ++.align 5 ++quarter_loop_8x: ++ QT_loop_8x ++ ++ bdnz quarter_loop_8x ++ ++ xxlor 0, 32+30, 32+30 ++ xxlor 32+30, 30, 30 ++ vadduwm 12, 12, 30 ++ xxlor 32+30, 0, 0 ++ TP_4x 0, 1, 2, 3 ++ TP_4x 4, 5, 6, 7 ++ TP_4x 8, 9, 10, 11 ++ TP_4x 12, 13, 14, 15 ++ ++ xxlor 0, 48, 48 ++ xxlor 1, 49, 49 ++ xxlor 2, 50, 50 ++ xxlor 3, 51, 51 ++ xxlor 48, 16, 16 ++ xxlor 49, 17, 17 ++ xxlor 50, 18, 18 ++ xxlor 51, 19, 19 ++ Add_state 0 ++ xxlor 48, 0, 0 ++ xxlor 49, 1, 1 ++ xxlor 50, 2, 2 ++ xxlor 51, 3, 3 ++ Write_256 0 ++ addi 14, 14, 256 ++ addi 15, 15, -256 ++ ++ xxlor 5, 32+31, 32+31 ++ xxlor 32+31, 31, 31 ++ vadduwm 28, 28, 31 ++ xxlor 32+31, 5, 5 ++ TP_4x 16+0, 16+1, 16+2, 16+3 ++ TP_4x 16+4, 16+5, 16+6, 16+7 ++ TP_4x 16+8, 16+9, 16+10, 16+11 ++ TP_4x 16+12, 16+13, 16+14, 16+15 ++ ++ xxlor 32, 16, 16 ++ xxlor 33, 17, 17 ++ xxlor 34, 18, 18 ++ xxlor 35, 19, 19 ++ Add_state 16 ++ Write_256 16 ++ addi 14, 14, 256 ++ addi 15, 15, -256 ++ ++ # should update counter before out? ++ xxlor 32+24, 24, 24 ++ xxlor 32+25, 25, 25 ++ xxlor 32+30, 30, 30 ++ vadduwm 30, 30, 25 ++ vadduwm 31, 30, 24 ++ xxlor 30, 32+30, 32+30 ++ xxlor 31, 32+31, 32+31 ++ ++ cmpdi 15, 0 ++ beq Out_loop ++ ++ cmpdi 15, 512 ++ blt Loop_last ++ ++ mtctr 8 ++ b Loop_8x ++ ++Loop_last: ++ lxvw4x 48, 0, 3 # vr16, constants ++ lxvw4x 49, 17, 3 # vr17, key 1 ++ lxvw4x 50, 18, 3 # vr18, key 2 ++ lxvw4x 51, 19, 3 # vr19, counter, nonce ++ ++ vspltisw 21, 12 ++ vspltisw 23, 7 ++ lxvw4x 32+20, 0, 11 ++ lxvw4x 32+22, 17, 11 ++ ++ li 8, 10 ++ mtctr 8 ++ ++Loop_4x: ++ lvx 0, 20, 10 ++ lvx 1, 21, 10 ++ lvx 2, 22, 10 ++ lvx 3, 23, 10 ++ vspltw 4, 17, 0 ++ vspltw 5, 17, 1 ++ vspltw 6, 17, 2 ++ vspltw 7, 17, 3 ++ vspltw 8, 18, 0 ++ vspltw 9, 18, 1 ++ vspltw 10, 18, 2 ++ vspltw 11, 18, 3 ++ vspltw 12, 19, 0 ++ vadduwm 12, 12, 30 # increase counter ++ vspltw 13, 19, 1 ++ vspltw 14, 19, 2 ++ vspltw 15, 19, 3 ++ ++.align 5 ++quarter_loop: ++ QT_loop_4x ++ ++ bdnz quarter_loop ++ ++ vadduwm 12, 12, 30 ++ TP_4x 0, 1, 2, 3 ++ TP_4x 4, 5, 6, 7 ++ TP_4x 8, 9, 10, 11 ++ TP_4x 12, 13, 14, 15 ++ ++ Add_state 0 ++ Write_256 0 ++ addi 14, 14, 256 ++ addi 15, 15, -256 ++ ++ # Update state counter ++ vspltisw 25, 4 ++ vadduwm 30, 30, 25 ++ ++ cmpdi 15, 0 ++ beq Out_loop ++ ++ mtctr 8 ++ b Loop_4x ++ ++Out_loop: ++ # ++ # Update state counter ++ # ++ vspltisb 16, -1 # first 16 bytes - 0xffff...ff ++ vspltisb 17, 0 # second 16 bytes - 0x0000...00 ++ vsldoi 18, 16, 17, 12 ++ vand 18, 18, 30 ++ xxlor 32+19, 19, 19 ++ vadduwm 18, 19, 18 ++ stxvw4x 32+18, 19, 3 ++ li 3, 0 ++ ++ addi 9, 1, 256 ++ lvx 20, 0, 9 ++ lvx 21, 17, 9 ++ lvx 22, 18, 9 ++ lvx 23, 19, 9 ++ lvx 24, 20, 9 ++ lvx 25, 21, 9 ++ lvx 26, 22, 9 ++ lvx 27, 23, 9 ++ lvx 28, 24, 9 ++ lvx 29, 25, 9 ++ lvx 30, 26, 9 ++ lvx 31, 27, 9 ++ ++ add 9, 9, 27 ++ addi 14, 17, 16 ++ lxvx 14, 14, 9 ++ addi 14, 14, 16 ++ lxvx 15, 14, 9 ++ addi 14, 14, 16 ++ lxvx 16, 14, 9 ++ addi 14, 14, 16 ++ lxvx 17, 14, 9 ++ addi 14, 14, 16 ++ lxvx 18, 14, 9 ++ addi 14, 14, 16 ++ lxvx 19, 14, 9 ++ addi 14, 14, 16 ++ lxvx 20, 14, 9 ++ addi 14, 14, 16 ++ lxvx 21, 14, 9 ++ addi 14, 14, 16 ++ lxvx 22, 14, 9 ++ addi 14, 14, 16 ++ lxvx 23, 14, 9 ++ addi 14, 14, 16 ++ lxvx 24, 14, 9 ++ addi 14, 14, 16 ++ lxvx 25, 14, 9 ++ addi 14, 14, 16 ++ lxvx 26, 14, 9 ++ addi 14, 14, 16 ++ lxvx 27, 14, 9 ++ addi 14, 14, 16 ++ lxvx 28, 14, 9 ++ addi 14, 14, 16 ++ lxvx 29, 14, 9 ++ addi 14, 14, 16 ++ lxvx 30, 14, 9 ++ addi 14, 14, 16 ++ lxvx 31, 14, 9 ++ ++ ld 0, 1040(1) ++ ld 14,112(1) ++ ld 15,120(1) ++ ld 16,128(1) ++ ld 17,136(1) ++ ld 18,144(1) ++ ld 19,152(1) ++ ld 20,160(1) ++ ld 21,168(1) ++ ld 22,176(1) ++ ld 23,184(1) ++ ld 24,192(1) ++ ld 25,200(1) ++ ld 26,208(1) ++ ld 27,216(1) ++ ld 28,224(1) ++ ld 29,232(1) ++ ld 30,240(1) ++ ld 31,248(1) ++ ++ mtlr 0 ++ addi 1, 1, 1024 ++ blr ++ ++Out_no_chacha: ++ li 3, 0 ++ blr ++ ++.data ++.align 4 ++sigma: ++.long 0x61707865, 0x3320646e, 0x79622d32, 0x6b206574 ++.long 0x0c0d0e0f, 0x08090a0b, 0x04050607, 0x00010203 ++.long 1, 0, 0, 0 ++.long 0, 1, 2, 3 ++.long 0x61707865, 0x61707865, 0x61707865, 0x61707865 ++.long 0x3320646e, 0x3320646e, 0x3320646e, 0x3320646e ++.long 0x79622d32, 0x79622d32, 0x79622d32, 0x79622d32 ++.long 0x6b206574, 0x6b206574, 0x6b206574, 0x6b206574 ++permx: ++.long 0x22330011, 0x66774455, 0xaabb8899, 0xeeffccdd ++.long 0x11223300, 0x55667744, 0x99aabb88, 0xddeeffcc +Index: libgcrypt-1.10.2/cipher/chacha20.c +=================================================================== +--- libgcrypt-1.10.2.orig/cipher/chacha20.c ++++ libgcrypt-1.10.2/cipher/chacha20.c +@@ -125,6 +125,7 @@ typedef struct CHACHA20_context_s + unsigned int use_avx2:1; + unsigned int use_neon:1; + unsigned int use_ppc:1; ++ unsigned int use_p10:1; + unsigned int use_s390x:1; + } CHACHA20_context_t; + +@@ -163,6 +164,12 @@ unsigned int _gcry_chacha20_poly1305_amd + + #ifdef USE_PPC_VEC + ++#ifndef WORDS_BIGENDIAN ++unsigned int _gcry_chacha20_p10le_8x(u32 *state, byte *dst, ++ const byte *src, ++ size_t len); ++#endif ++ + unsigned int _gcry_chacha20_ppc8_blocks4(u32 *state, byte *dst, + const byte *src, + size_t nblks); +@@ -475,6 +482,9 @@ chacha20_do_setkey (CHACHA20_context_t * + #endif + #ifdef USE_PPC_VEC + ctx->use_ppc = (features & HWF_PPC_ARCH_2_07) != 0; ++# ifndef WORDS_BIGENDIAN ++ ctx->use_p10 = (features & HWF_PPC_ARCH_3_10) != 0; ++# endif + #endif + #ifdef USE_S390X_VX + ctx->use_s390x = (features & HWF_S390X_VX) != 0; +@@ -571,7 +581,22 @@ do_chacha20_encrypt_stream_tail (CHACHA2 + { + size_t nblocks = length / CHACHA20_BLOCK_SIZE; + nblocks -= nblocks % 4; +- nburn = _gcry_chacha20_ppc8_blocks4(ctx->input, outbuf, inbuf, nblocks); ++#ifndef WORDS_BIGENDIAN ++ /* ++ * A workaround to skip counter overflow. This is rare. ++ */ ++ if (ctx->use_p10 && nblocks >= 8 ++ && ((u64)ctx->input[12] + nblocks) <= 0xffffffffU) ++ { ++ size_t len = nblocks * CHACHA20_BLOCK_SIZE; ++ nburn = _gcry_chacha20_p10le_8x(ctx->input, outbuf, inbuf, len); ++ } ++ else ++#endif ++ { ++ nburn = _gcry_chacha20_ppc8_blocks4(ctx->input, outbuf, inbuf, ++ nblocks); ++ } + burn = nburn > burn ? nburn : burn; + length -= nblocks * CHACHA20_BLOCK_SIZE; + outbuf += nblocks * CHACHA20_BLOCK_SIZE; +@@ -760,6 +785,11 @@ _gcry_chacha20_poly1305_encrypt(gcry_cip + } + #endif + #ifdef USE_PPC_VEC_POLY1305 ++ else if (ctx->use_ppc && ctx->use_p10) ++ { ++ /* Skip stitched chacha20-poly1305 for P10. */ ++ authptr = NULL; ++ } + else if (ctx->use_ppc && length >= CHACHA20_BLOCK_SIZE * 4) + { + nburn = _gcry_chacha20_ppc8_blocks4(ctx->input, outbuf, inbuf, 4); +@@ -998,6 +1028,7 @@ _gcry_chacha20_poly1305_decrypt(gcry_cip + { + CHACHA20_context_t *ctx = (void *) &c->context.c; + unsigned int nburn, burn = 0; ++ int skip_stitched = 0; + + if (!length) + return 0; +@@ -1049,6 +1080,13 @@ _gcry_chacha20_poly1305_decrypt(gcry_cip + inbuf += nblocks * CHACHA20_BLOCK_SIZE; + } + #endif ++#ifdef USE_PPC_VEC_POLY1305 ++ if (ctx->use_ppc && ctx->use_p10) ++ { ++ /* Skip stitched chacha20-poly1305 for P10. */ ++ skip_stitched = 1; ++ } ++#endif + + #ifdef USE_SSSE3 + if (ctx->use_ssse3) +@@ -1102,7 +1140,8 @@ _gcry_chacha20_poly1305_decrypt(gcry_cip + #endif + + #ifdef USE_PPC_VEC_POLY1305 +- if (ctx->use_ppc && length >= 4 * CHACHA20_BLOCK_SIZE) ++ /* skip stitch for p10 */ ++ if (!skip_stitched && ctx->use_ppc && length >= 4 * CHACHA20_BLOCK_SIZE) + { + size_t nblocks = length / CHACHA20_BLOCK_SIZE; + nblocks -= nblocks % 4; +Index: libgcrypt-1.10.2/cipher/poly1305-internal.h +=================================================================== +--- libgcrypt-1.10.2.orig/cipher/poly1305-internal.h ++++ libgcrypt-1.10.2/cipher/poly1305-internal.h +@@ -33,6 +33,17 @@ + #define POLY1305_KEYLEN 32 + #define POLY1305_BLOCKSIZE 16 + ++/* POLY1305_USE_PPC_VEC indicates whether to enable PowerPC vector code. */ ++#undef POLY1305_USE_PPC_VEC ++#ifdef ENABLE_PPC_CRYPTO_SUPPORT ++# if defined(HAVE_COMPATIBLE_CC_PPC_ALTIVEC) && \ ++ defined(HAVE_GCC_INLINE_ASM_PPC_ALTIVEC) && \ ++ !defined(WORDS_BIGENDIAN) ++# if __GNUC__ >= 4 ++# define POLY1305_USE_PPC_VEC 1 ++# endif ++# endif ++#endif + + typedef struct + { +@@ -46,6 +57,9 @@ typedef struct poly1305_context_s + POLY1305_STATE state; + byte buffer[POLY1305_BLOCKSIZE]; + unsigned int leftover; ++#ifdef POLY1305_USE_PPC_VEC ++ unsigned int use_p10:1; ++#endif + } poly1305_context_t; + + +Index: libgcrypt-1.10.2/cipher/poly1305-p10le.s +=================================================================== +--- /dev/null ++++ libgcrypt-1.10.2/cipher/poly1305-p10le.s +@@ -0,0 +1,841 @@ ++# Copyright 2021- IBM Inc. All rights reserved ++# ++# This file is part of Libgcrypt. ++# ++# Libgcrypt is free software; you can redistribute it and/or modify ++# it under the terms of the GNU Lesser General Public License as ++# published by the Free Software Foundation; either version 2.1 of ++# the License, or (at your option) any later version. ++# ++# Libgcrypt 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 Lesser General Public License for more details. ++# ++# You should have received a copy of the GNU Lesser General Public ++# License along with this program; if not, see . ++# ++#=================================================================================== ++# Written by Danny Tsen ++# ++# Poly1305 - this version mainly using vector/VSX/Scalar ++# - 26 bits limbs ++# - Handle multiple 64 byte blcoks but need at least 2 64 bytes block ++# ++# Improve performance by breaking down polynominal to the sum of products with ++# h4 = m1 * r⁴ + m2 * r³ + m3 * r² + m4 * r ++# ++# 07/22/21 - this revison based on the above sum of products. Setup r^4, r^3, r^2, r and s3, s2, s1, s0 ++# to 9 vectors for multiplications. ++# ++# setup r^4, r^3, r^2, r vectors ++# vs [r^1, r^3, r^2, r^4] ++# vs0 = [r0,.....] ++# vs1 = [r1,.....] ++# vs2 = [r2,.....] ++# vs3 = [r3,.....] ++# vs4 = [r4,.....] ++# vs5 = [r1*5,...] ++# vs6 = [r2*5,...] ++# vs7 = [r2*5,...] ++# vs8 = [r4*5,...] ++# ++# Each word in a vector consists a member of a "r/s" in [a * r/s]. ++# ++# r0, r4*5, r3*5, r2*5, r1*5; ++# r1, r0, r4*5, r3*5, r2*5; ++# r2, r1, r0, r4*5, r3*5; ++# r3, r2, r1, r0, r4*5; ++# r4, r3, r2, r1, r0 ; ++# ++# ++# gcry_poly1305_p10le_4blocks( uint8_t *k, uint32_t mlen, uint8_t *m) ++# k = 32 bytes key ++# r3 = k (r, s) ++# r4 = mlen ++# r5 = m ++# ++.text ++ ++# Block size 16 bytes ++# key = (r, s) ++# clamp r &= 0x0FFFFFFC0FFFFFFC 0x0FFFFFFC0FFFFFFF ++# p = 2^130 - 5 ++# a += m ++# a = (r + a) % p ++# a += s ++# 16 bytes (a) ++# ++# p[0] = a0*r0 + a1*r4*5 + a2*r3*5 + a3*r2*5 + a4*r1*5; ++# p[1] = a0*r1 + a1*r0 + a2*r4*5 + a3*r3*5 + a4*r2*5; ++# p[2] = a0*r2 + a1*r1 + a2*r0 + a3*r4*5 + a4*r3*5; ++# p[3] = a0*r3 + a1*r2 + a2*r1 + a3*r0 + a4*r4*5; ++# p[4] = a0*r4 + a1*r3 + a2*r2 + a3*r1 + a4*r0 ; ++# ++# [r^2, r^3, r^1, r^4] ++# [m3, m2, m4, m1] ++# ++# multiply odd and even words ++.macro mul_odd ++ vmulouw 14, 4, 26 ++ vmulouw 10, 5, 3 ++ vmulouw 11, 6, 2 ++ vmulouw 12, 7, 1 ++ vmulouw 13, 8, 0 ++ vmulouw 15, 4, 27 ++ vaddudm 14, 14, 10 ++ vaddudm 14, 14, 11 ++ vmulouw 10, 5, 26 ++ vmulouw 11, 6, 3 ++ vaddudm 14, 14, 12 ++ vaddudm 14, 14, 13 # x0 ++ vaddudm 15, 15, 10 ++ vaddudm 15, 15, 11 ++ vmulouw 12, 7, 2 ++ vmulouw 13, 8, 1 ++ vaddudm 15, 15, 12 ++ vaddudm 15, 15, 13 # x1 ++ vmulouw 16, 4, 28 ++ vmulouw 10, 5, 27 ++ vmulouw 11, 6, 26 ++ vaddudm 16, 16, 10 ++ vaddudm 16, 16, 11 ++ vmulouw 12, 7, 3 ++ vmulouw 13, 8, 2 ++ vaddudm 16, 16, 12 ++ vaddudm 16, 16, 13 # x2 ++ vmulouw 17, 4, 29 ++ vmulouw 10, 5, 28 ++ vmulouw 11, 6, 27 ++ vaddudm 17, 17, 10 ++ vaddudm 17, 17, 11 ++ vmulouw 12, 7, 26 ++ vmulouw 13, 8, 3 ++ vaddudm 17, 17, 12 ++ vaddudm 17, 17, 13 # x3 ++ vmulouw 18, 4, 30 ++ vmulouw 10, 5, 29 ++ vmulouw 11, 6, 28 ++ vaddudm 18, 18, 10 ++ vaddudm 18, 18, 11 ++ vmulouw 12, 7, 27 ++ vmulouw 13, 8, 26 ++ vaddudm 18, 18, 12 ++ vaddudm 18, 18, 13 # x4 ++.endm ++ ++.macro mul_even ++ vmuleuw 9, 4, 26 ++ vmuleuw 10, 5, 3 ++ vmuleuw 11, 6, 2 ++ vmuleuw 12, 7, 1 ++ vmuleuw 13, 8, 0 ++ vaddudm 14, 14, 9 ++ vaddudm 14, 14, 10 ++ vaddudm 14, 14, 11 ++ vaddudm 14, 14, 12 ++ vaddudm 14, 14, 13 # x0 ++ ++ vmuleuw 9, 4, 27 ++ vmuleuw 10, 5, 26 ++ vmuleuw 11, 6, 3 ++ vmuleuw 12, 7, 2 ++ vmuleuw 13, 8, 1 ++ vaddudm 15, 15, 9 ++ vaddudm 15, 15, 10 ++ vaddudm 15, 15, 11 ++ vaddudm 15, 15, 12 ++ vaddudm 15, 15, 13 # x1 ++ ++ vmuleuw 9, 4, 28 ++ vmuleuw 10, 5, 27 ++ vmuleuw 11, 6, 26 ++ vmuleuw 12, 7, 3 ++ vmuleuw 13, 8, 2 ++ vaddudm 16, 16, 9 ++ vaddudm 16, 16, 10 ++ vaddudm 16, 16, 11 ++ vaddudm 16, 16, 12 ++ vaddudm 16, 16, 13 # x2 ++ ++ vmuleuw 9, 4, 29 ++ vmuleuw 10, 5, 28 ++ vmuleuw 11, 6, 27 ++ vmuleuw 12, 7, 26 ++ vmuleuw 13, 8, 3 ++ vaddudm 17, 17, 9 ++ vaddudm 17, 17, 10 ++ vaddudm 17, 17, 11 ++ vaddudm 17, 17, 12 ++ vaddudm 17, 17, 13 # x3 ++ ++ vmuleuw 9, 4, 30 ++ vmuleuw 10, 5, 29 ++ vmuleuw 11, 6, 28 ++ vmuleuw 12, 7, 27 ++ vmuleuw 13, 8, 26 ++ vaddudm 18, 18, 9 ++ vaddudm 18, 18, 10 ++ vaddudm 18, 18, 11 ++ vaddudm 18, 18, 12 ++ vaddudm 18, 18, 13 # x4 ++.endm ++ ++# setup r^4, r^3, r^2, r vectors ++# [r, r^3, r^2, r^4] ++# vs0 = [r0,...] ++# vs1 = [r1,...] ++# vs2 = [r2,...] ++# vs3 = [r3,...] ++# vs4 = [r4,...] ++# vs5 = [r4*5,...] ++# vs6 = [r3*5,...] ++# vs7 = [r2*5,...] ++# vs8 = [r1*5,...] ++# ++# r0, r4*5, r3*5, r2*5, r1*5; ++# r1, r0, r4*5, r3*5, r2*5; ++# r2, r1, r0, r4*5, r3*5; ++# r3, r2, r1, r0, r4*5; ++# r4, r3, r2, r1, r0 ; ++# ++.macro poly1305_setup_r ++ ++ # save r ++ xxlor 26, 58, 58 ++ xxlor 27, 59, 59 ++ xxlor 28, 60, 60 ++ xxlor 29, 61, 61 ++ xxlor 30, 62, 62 ++ ++ xxlxor 31, 31, 31 ++ ++# [r, r^3, r^2, r^4] ++ # compute r^2 ++ vmr 4, 26 ++ vmr 5, 27 ++ vmr 6, 28 ++ vmr 7, 29 ++ vmr 8, 30 ++ bl do_mul # r^2 r^1 ++ xxpermdi 58, 58, 36, 0x3 # r0 ++ xxpermdi 59, 59, 37, 0x3 # r1 ++ xxpermdi 60, 60, 38, 0x3 # r2 ++ xxpermdi 61, 61, 39, 0x3 # r3 ++ xxpermdi 62, 62, 40, 0x3 # r4 ++ xxpermdi 36, 36, 36, 0x3 ++ xxpermdi 37, 37, 37, 0x3 ++ xxpermdi 38, 38, 38, 0x3 ++ xxpermdi 39, 39, 39, 0x3 ++ xxpermdi 40, 40, 40, 0x3 ++ vspltisb 13, 2 ++ vsld 9, 27, 13 ++ vsld 10, 28, 13 ++ vsld 11, 29, 13 ++ vsld 12, 30, 13 ++ vaddudm 0, 9, 27 ++ vaddudm 1, 10, 28 ++ vaddudm 2, 11, 29 ++ vaddudm 3, 12, 30 ++ ++ bl do_mul # r^4 r^3 ++ vmrgow 26, 26, 4 ++ vmrgow 27, 27, 5 ++ vmrgow 28, 28, 6 ++ vmrgow 29, 29, 7 ++ vmrgow 30, 30, 8 ++ vspltisb 13, 2 ++ vsld 9, 27, 13 ++ vsld 10, 28, 13 ++ vsld 11, 29, 13 ++ vsld 12, 30, 13 ++ vaddudm 0, 9, 27 ++ vaddudm 1, 10, 28 ++ vaddudm 2, 11, 29 ++ vaddudm 3, 12, 30 ++ ++ # r^2 r^4 ++ xxlor 0, 58, 58 ++ xxlor 1, 59, 59 ++ xxlor 2, 60, 60 ++ xxlor 3, 61, 61 ++ xxlor 4, 62, 62 ++ xxlor 5, 32, 32 ++ xxlor 6, 33, 33 ++ xxlor 7, 34, 34 ++ xxlor 8, 35, 35 ++ ++ vspltw 9, 26, 3 ++ vspltw 10, 26, 2 ++ vmrgow 26, 10, 9 ++ vspltw 9, 27, 3 ++ vspltw 10, 27, 2 ++ vmrgow 27, 10, 9 ++ vspltw 9, 28, 3 ++ vspltw 10, 28, 2 ++ vmrgow 28, 10, 9 ++ vspltw 9, 29, 3 ++ vspltw 10, 29, 2 ++ vmrgow 29, 10, 9 ++ vspltw 9, 30, 3 ++ vspltw 10, 30, 2 ++ vmrgow 30, 10, 9 ++ ++ vsld 9, 27, 13 ++ vsld 10, 28, 13 ++ vsld 11, 29, 13 ++ vsld 12, 30, 13 ++ vaddudm 0, 9, 27 ++ vaddudm 1, 10, 28 ++ vaddudm 2, 11, 29 ++ vaddudm 3, 12, 30 ++.endm ++ ++do_mul: ++ mul_odd ++ ++ # do reduction ( h %= p ) ++ # carry reduction ++ vspltisb 9, 2 ++ vsrd 10, 14, 31 ++ vsrd 11, 17, 31 ++ vand 7, 17, 25 ++ vand 4, 14, 25 ++ vaddudm 18, 18, 11 ++ vsrd 12, 18, 31 ++ vaddudm 15, 15, 10 ++ ++ vsrd 11, 15, 31 ++ vand 8, 18, 25 ++ vand 5, 15, 25 ++ vaddudm 4, 4, 12 ++ vsld 10, 12, 9 ++ vaddudm 6, 16, 11 ++ ++ vsrd 13, 6, 31 ++ vand 6, 6, 25 ++ vaddudm 4, 4, 10 ++ vsrd 10, 4, 31 ++ vaddudm 7, 7, 13 ++ ++ vsrd 11, 7, 31 ++ vand 7, 7, 25 ++ vand 4, 4, 25 ++ vaddudm 5, 5, 10 ++ vaddudm 8, 8, 11 ++ blr ++ ++# ++# init key ++# ++do_poly1305_init: ++ ld 10, rmask@got(2) ++ ld 11, 0(10) ++ ld 12, 8(10) ++ ++ li 14, 16 ++ li 15, 32 ++ ld 10, cnum@got(2) ++ lvx 25, 0, 10 # v25 - mask ++ lvx 31, 14, 10 # v31 = 1a ++ lvx 19, 15, 10 # v19 = 1 << 24 ++ lxv 24, 48(10) # vs24 ++ lxv 25, 64(10) # vs25 ++ ++ # initialize ++ # load key from r3 to vectors ++ ld 9, 16(3) ++ ld 10, 24(3) ++ ld 11, 0(3) ++ ld 12, 8(3) ++ ++ # break 26 bits ++ extrdi 14, 9, 26, 38 ++ extrdi 15, 9, 26, 12 ++ extrdi 16, 9, 12, 0 ++ mtvsrdd 58, 0, 14 ++ insrdi 16, 10, 14, 38 ++ mtvsrdd 59, 0, 15 ++ extrdi 17, 10, 26, 24 ++ mtvsrdd 60, 0, 16 ++ extrdi 18, 10, 24, 0 ++ mtvsrdd 61, 0, 17 ++ mtvsrdd 62, 0, 18 ++ ++ # r1 = r1 * 5, r2 = r2 * 5, r3 = r3 * 5, r4 = r4 * 5 ++ li 9, 5 ++ mtvsrdd 36, 0, 9 ++ vmulouw 0, 27, 4 # v0 = rr0 ++ vmulouw 1, 28, 4 # v1 = rr1 ++ vmulouw 2, 29, 4 # v2 = rr2 ++ vmulouw 3, 30, 4 # v3 = rr3 ++ blr ++ ++# ++# gcry_poly1305_p10le_4blocks( uint8_t *k, uint32_t mlen, uint8_t *m) ++# k = 32 bytes key ++# r3 = k (r, s) ++# r4 = mlen ++# r5 = m ++# ++.global gcry_poly1305_p10le_4blocks ++.align 5 ++gcry_poly1305_p10le_4blocks: ++_gcry_poly1305_p10le_4blocks: ++ cmpdi 5, 128 ++ blt Out_no_poly1305 ++ ++ stdu 1,-1024(1) ++ mflr 0 ++ ++ std 14,112(1) ++ std 15,120(1) ++ std 16,128(1) ++ std 17,136(1) ++ std 18,144(1) ++ std 19,152(1) ++ std 20,160(1) ++ std 21,168(1) ++ std 31,248(1) ++ li 14, 256 ++ stvx 20, 14, 1 ++ addi 14, 14, 16 ++ stvx 21, 14, 1 ++ addi 14, 14, 16 ++ stvx 22, 14, 1 ++ addi 14, 14, 16 ++ stvx 23, 14, 1 ++ addi 14, 14, 16 ++ stvx 24, 14, 1 ++ addi 14, 14, 16 ++ stvx 25, 14, 1 ++ addi 14, 14, 16 ++ stvx 26, 14, 1 ++ addi 14, 14, 16 ++ stvx 27, 14, 1 ++ addi 14, 14, 16 ++ stvx 28, 14, 1 ++ addi 14, 14, 16 ++ stvx 29, 14, 1 ++ addi 14, 14, 16 ++ stvx 30, 14, 1 ++ addi 14, 14, 16 ++ stvx 31, 14, 1 ++ ++ addi 14, 14, 16 ++ stxvx 14, 14, 1 ++ addi 14, 14, 16 ++ stxvx 15, 14, 1 ++ addi 14, 14, 16 ++ stxvx 16, 14, 1 ++ addi 14, 14, 16 ++ stxvx 17, 14, 1 ++ addi 14, 14, 16 ++ stxvx 18, 14, 1 ++ addi 14, 14, 16 ++ stxvx 19, 14, 1 ++ addi 14, 14, 16 ++ stxvx 20, 14, 1 ++ addi 14, 14, 16 ++ stxvx 21, 14, 1 ++ addi 14, 14, 16 ++ stxvx 22, 14, 1 ++ addi 14, 14, 16 ++ stxvx 23, 14, 1 ++ addi 14, 14, 16 ++ stxvx 24, 14, 1 ++ addi 14, 14, 16 ++ stxvx 25, 14, 1 ++ addi 14, 14, 16 ++ stxvx 26, 14, 1 ++ addi 14, 14, 16 ++ stxvx 27, 14, 1 ++ addi 14, 14, 16 ++ stxvx 28, 14, 1 ++ addi 14, 14, 16 ++ stxvx 29, 14, 1 ++ addi 14, 14, 16 ++ stxvx 30, 14, 1 ++ addi 14, 14, 16 ++ stxvx 31, 14, 1 ++ std 0, 1040(1) ++ ++ bl do_poly1305_init ++ ++ li 21, 0 # counter to message ++ ++ poly1305_setup_r ++ ++ # load previous state ++ # break/convert r6 to 26 bits ++ ld 9, 32(3) ++ ld 10, 40(3) ++ lwz 19, 48(3) ++ sldi 19, 19, 24 ++ mtvsrdd 41, 0, 19 ++ extrdi 14, 9, 26, 38 ++ extrdi 15, 9, 26, 12 ++ extrdi 16, 9, 12, 0 ++ mtvsrdd 36, 0, 14 ++ insrdi 16, 10, 14, 38 ++ mtvsrdd 37, 0, 15 ++ extrdi 17, 10, 26, 24 ++ mtvsrdd 38, 0, 16 ++ extrdi 18, 10, 24, 0 ++ mtvsrdd 39, 0, 17 ++ mtvsrdd 40, 0, 18 ++ vor 8, 8, 9 ++ ++ # input m1 m2 ++ add 20, 4, 21 ++ xxlor 49, 24, 24 ++ xxlor 50, 25, 25 ++ lxvw4x 43, 0, 20 ++ addi 17, 20, 16 ++ lxvw4x 44, 0, 17 ++ vperm 14, 11, 12, 17 ++ vperm 15, 11, 12, 18 ++ vand 9, 14, 25 # a0 ++ vsrd 10, 14, 31 # >> 26 ++ vsrd 11, 10, 31 # 12 bits left ++ vand 10, 10, 25 # a1 ++ vspltisb 13, 12 ++ vand 16, 15, 25 ++ vsld 12, 16, 13 ++ vor 11, 11, 12 ++ vand 11, 11, 25 # a2 ++ vspltisb 13, 14 ++ vsrd 12, 15, 13 # >> 14 ++ vsrd 13, 12, 31 # >> 26, a4 ++ vand 12, 12, 25 # a3 ++ ++ vaddudm 20, 4, 9 ++ vaddudm 21, 5, 10 ++ vaddudm 22, 6, 11 ++ vaddudm 23, 7, 12 ++ vaddudm 24, 8, 13 ++ ++ # m3 m4 ++ addi 17, 17, 16 ++ lxvw4x 43, 0, 17 ++ addi 17, 17, 16 ++ lxvw4x 44, 0, 17 ++ vperm 14, 11, 12, 17 ++ vperm 15, 11, 12, 18 ++ vand 9, 14, 25 # a0 ++ vsrd 10, 14, 31 # >> 26 ++ vsrd 11, 10, 31 # 12 bits left ++ vand 10, 10, 25 # a1 ++ vspltisb 13, 12 ++ vand 16, 15, 25 ++ vsld 12, 16, 13 ++ vspltisb 13, 14 ++ vor 11, 11, 12 ++ vand 11, 11, 25 # a2 ++ vsrd 12, 15, 13 # >> 14 ++ vsrd 13, 12, 31 # >> 26, a4 ++ vand 12, 12, 25 # a3 ++ ++ # Smash 4 message blocks into 5 vectors of [m4, m2, m3, m1] ++ vmrgow 4, 9, 20 ++ vmrgow 5, 10, 21 ++ vmrgow 6, 11, 22 ++ vmrgow 7, 12, 23 ++ vmrgow 8, 13, 24 ++ vaddudm 8, 8, 19 ++ ++ addi 5, 5, -64 ++ addi 21, 21, 64 ++ ++ li 9, 64 ++ divdu 31, 5, 9 ++ ++ mtctr 31 ++ ++# h4 = m1 * r⁴ + m2 * r³ + m3 * r² + m4 * r ++# Rewrite the polynominal sum of product as follows, ++# h1 = (h0 + m1) * r^2, h2 = (h0 + m2) * r^2 ++# h3 = (h1 + m3) * r^2, h4 = (h2 + m4) * r^2 --> (h0 + m1) r*4 + (h3 + m3) r^2, (h0 + m2) r^4 + (h0 + m4) r^2 ++# .... Repeat ++# h5 = (h3 + m5) * r^2, h6 = (h4 + m6) * r^2 --> ++# h7 = (h5 + m7) * r^2, h8 = (h6 + m8) * r^1 --> m5 * r^4 + m6 * r^3 + m7 * r^2 + m8 * r ++# ++loop_4blocks: ++ ++ # Multiply odd words and even words ++ mul_odd ++ mul_even ++ # carry reduction ++ vspltisb 9, 2 ++ vsrd 10, 14, 31 ++ vsrd 11, 17, 31 ++ vand 7, 17, 25 ++ vand 4, 14, 25 ++ vaddudm 18, 18, 11 ++ vsrd 12, 18, 31 ++ vaddudm 15, 15, 10 ++ ++ vsrd 11, 15, 31 ++ vand 8, 18, 25 ++ vand 5, 15, 25 ++ vaddudm 4, 4, 12 ++ vsld 10, 12, 9 ++ vaddudm 6, 16, 11 ++ ++ vsrd 13, 6, 31 ++ vand 6, 6, 25 ++ vaddudm 4, 4, 10 ++ vsrd 10, 4, 31 ++ vaddudm 7, 7, 13 ++ ++ vsrd 11, 7, 31 ++ vand 7, 7, 25 ++ vand 4, 4, 25 ++ vaddudm 5, 5, 10 ++ vaddudm 8, 8, 11 ++ ++ # input m1 m2 m3 m4 ++ add 20, 4, 21 ++ xxlor 49, 24, 24 ++ xxlor 50, 25, 25 ++ lxvw4x 43, 0, 20 ++ addi 17, 20, 16 ++ lxvw4x 44, 0, 17 ++ vperm 14, 11, 12, 17 ++ vperm 15, 11, 12, 18 ++ addi 17, 17, 16 ++ lxvw4x 43, 0, 17 ++ addi 17, 17, 16 ++ lxvw4x 44, 0, 17 ++ vperm 17, 11, 12, 17 ++ vperm 18, 11, 12, 18 ++ ++ vand 20, 14, 25 # a0 ++ vand 9, 17, 25 # a0 ++ vsrd 21, 14, 31 # >> 26 ++ vsrd 22, 21, 31 # 12 bits left ++ vsrd 10, 17, 31 # >> 26 ++ vsrd 11, 10, 31 # 12 bits left ++ ++ vand 21, 21, 25 # a1 ++ vand 10, 10, 25 # a1 ++ ++ vspltisb 13, 12 ++ vand 16, 15, 25 ++ vsld 23, 16, 13 ++ vor 22, 22, 23 ++ vand 22, 22, 25 # a2 ++ vand 16, 18, 25 ++ vsld 12, 16, 13 ++ vor 11, 11, 12 ++ vand 11, 11, 25 # a2 ++ vspltisb 13, 14 ++ vsrd 23, 15, 13 # >> 14 ++ vsrd 24, 23, 31 # >> 26, a4 ++ vand 23, 23, 25 # a3 ++ vsrd 12, 18, 13 # >> 14 ++ vsrd 13, 12, 31 # >> 26, a4 ++ vand 12, 12, 25 # a3 ++ ++ vaddudm 4, 4, 20 ++ vaddudm 5, 5, 21 ++ vaddudm 6, 6, 22 ++ vaddudm 7, 7, 23 ++ vaddudm 8, 8, 24 ++ ++ # Smash 4 message blocks into 5 vectors of [m4, m2, m3, m1] ++ vmrgow 4, 9, 4 ++ vmrgow 5, 10, 5 ++ vmrgow 6, 11, 6 ++ vmrgow 7, 12, 7 ++ vmrgow 8, 13, 8 ++ vaddudm 8, 8, 19 ++ ++ addi 5, 5, -64 ++ addi 21, 21, 64 ++ ++ bdnz loop_4blocks ++ ++ xxlor 58, 0, 0 ++ xxlor 59, 1, 1 ++ xxlor 60, 2, 2 ++ xxlor 61, 3, 3 ++ xxlor 62, 4, 4 ++ xxlor 32, 5, 5 ++ xxlor 33, 6, 6 ++ xxlor 34, 7, 7 ++ xxlor 35, 8, 8 ++ ++ # Multiply odd words and even words ++ mul_odd ++ mul_even ++ ++ # Sum the products. ++ xxpermdi 41, 31, 46, 0 ++ xxpermdi 42, 31, 47, 0 ++ vaddudm 4, 14, 9 ++ xxpermdi 36, 31, 36, 3 ++ vaddudm 5, 15, 10 ++ xxpermdi 37, 31, 37, 3 ++ xxpermdi 43, 31, 48, 0 ++ vaddudm 6, 16, 11 ++ xxpermdi 38, 31, 38, 3 ++ xxpermdi 44, 31, 49, 0 ++ vaddudm 7, 17, 12 ++ xxpermdi 39, 31, 39, 3 ++ xxpermdi 45, 31, 50, 0 ++ vaddudm 8, 18, 13 ++ xxpermdi 40, 31, 40, 3 ++ ++ # carry reduction ++ vspltisb 9, 2 ++ vsrd 10, 4, 31 ++ vsrd 11, 7, 31 ++ vand 7, 7, 25 ++ vand 4, 4, 25 ++ vaddudm 8, 8, 11 ++ vsrd 12, 8, 31 ++ vaddudm 5, 5, 10 ++ ++ vsrd 11, 5, 31 ++ vand 8, 8, 25 ++ vand 5, 5, 25 ++ vaddudm 4, 4, 12 ++ vsld 10, 12, 9 ++ vaddudm 6, 6, 11 ++ ++ vsrd 13, 6, 31 ++ vand 6, 6, 25 ++ vaddudm 4, 4, 10 ++ vsrd 10, 4, 31 ++ vaddudm 7, 7, 13 ++ ++ vsrd 11, 7, 31 ++ vand 7, 7, 25 ++ vand 4, 4, 25 ++ vaddudm 5, 5, 10 ++ vaddudm 8, 8, 11 ++ ++ b do_final_update ++ ++do_final_update: ++ # v4, v5, v6, v7 and v8 are 26 bit vectors ++ vsld 5, 5, 31 ++ vor 20, 4, 5 ++ vspltisb 11, 12 ++ vsrd 12, 6, 11 ++ vsld 6, 6, 31 ++ vsld 6, 6, 31 ++ vor 20, 20, 6 ++ vspltisb 11, 14 ++ vsld 7, 7, 11 ++ vor 21, 7, 12 ++ mfvsrld 16, 40 # save last 2 bytes ++ vsld 8, 8, 11 ++ vsld 8, 8, 31 ++ vor 21, 21, 8 ++ mfvsrld 17, 52 ++ mfvsrld 19, 53 ++ srdi 16, 16, 24 ++ ++ std 17, 32(3) ++ std 19, 40(3) ++ stw 16, 48(3) ++ ++Out_loop: ++ li 3, 0 ++ ++ li 14, 256 ++ lvx 20, 14, 1 ++ addi 14, 14, 16 ++ lvx 21, 14, 1 ++ addi 14, 14, 16 ++ lvx 22, 14, 1 ++ addi 14, 14, 16 ++ lvx 23, 14, 1 ++ addi 14, 14, 16 ++ lvx 24, 14, 1 ++ addi 14, 14, 16 ++ lvx 25, 14, 1 ++ addi 14, 14, 16 ++ lvx 26, 14, 1 ++ addi 14, 14, 16 ++ lvx 27, 14, 1 ++ addi 14, 14, 16 ++ lvx 28, 14, 1 ++ addi 14, 14, 16 ++ lvx 29, 14, 1 ++ addi 14, 14, 16 ++ lvx 30, 14, 1 ++ addi 14, 14, 16 ++ lvx 31, 14, 1 ++ ++ addi 14, 14, 16 ++ lxvx 14, 14, 1 ++ addi 14, 14, 16 ++ lxvx 15, 14, 1 ++ addi 14, 14, 16 ++ lxvx 16, 14, 1 ++ addi 14, 14, 16 ++ lxvx 17, 14, 1 ++ addi 14, 14, 16 ++ lxvx 18, 14, 1 ++ addi 14, 14, 16 ++ lxvx 19, 14, 1 ++ addi 14, 14, 16 ++ lxvx 20, 14, 1 ++ addi 14, 14, 16 ++ lxvx 21, 14, 1 ++ addi 14, 14, 16 ++ lxvx 22, 14, 1 ++ addi 14, 14, 16 ++ lxvx 23, 14, 1 ++ addi 14, 14, 16 ++ lxvx 24, 14, 1 ++ addi 14, 14, 16 ++ lxvx 25, 14, 1 ++ addi 14, 14, 16 ++ lxvx 26, 14, 1 ++ addi 14, 14, 16 ++ lxvx 27, 14, 1 ++ addi 14, 14, 16 ++ lxvx 28, 14, 1 ++ addi 14, 14, 16 ++ lxvx 29, 14, 1 ++ addi 14, 14, 16 ++ lxvx 30, 14, 1 ++ addi 14, 14, 16 ++ lxvx 31, 14, 1 ++ ++ ld 0, 1040(1) ++ ld 14,112(1) ++ ld 15,120(1) ++ ld 16,128(1) ++ ld 17,136(1) ++ ld 18,144(1) ++ ld 19,152(1) ++ ld 20,160(1) ++ ld 21,168(1) ++ ld 31,248(1) ++ ++ mtlr 0 ++ addi 1, 1, 1024 ++ blr ++ ++Out_no_poly1305: ++ li 3, 0 ++ blr ++ ++.data ++.align 5 ++rmask: ++.byte 0xff, 0xff, 0xff, 0x0f, 0xfc, 0xff, 0xff, 0x0f, 0xfc, 0xff, 0xff, 0x0f, 0xfc, 0xff, 0xff, 0x0f ++cnum: ++.long 0x03ffffff, 0x00000000, 0x03ffffff, 0x00000000 ++.long 0x1a, 0x00, 0x1a, 0x00 ++.long 0x01000000, 0x01000000, 0x01000000, 0x01000000 ++.long 0x00010203, 0x04050607, 0x10111213, 0x14151617 ++.long 0x08090a0b, 0x0c0d0e0f, 0x18191a1b, 0x1c1d1e1f ++.long 0x05, 0x00, 0x00, 0x00 ++.long 0x02020202, 0x02020202, 0x02020202, 0x02020202 ++.long 0xffffffff, 0xffffffff, 0x00000000, 0x00000000 +Index: libgcrypt-1.10.2/cipher/poly1305.c +=================================================================== +--- libgcrypt-1.10.2.orig/cipher/poly1305.c ++++ libgcrypt-1.10.2/cipher/poly1305.c +@@ -78,11 +78,23 @@ poly1305_blocks (poly1305_context_t *ctx + #endif /* USE_S390X_ASM */ + + ++#ifdef POLY1305_USE_PPC_VEC ++ ++extern unsigned int ++gcry_poly1305_p10le_4blocks(unsigned char *key, const byte *m, size_t len); ++ ++#endif /* POLY1305_USE_PPC_VEC */ ++ ++ + static void poly1305_init (poly1305_context_t *ctx, + const byte key[POLY1305_KEYLEN]) + { + POLY1305_STATE *st = &ctx->state; + ++#ifdef POLY1305_USE_PPC_VEC ++ ctx->use_p10 = (_gcry_get_hw_features () & HWF_PPC_ARCH_3_10) != 0; ++#endif ++ + ctx->leftover = 0; + + st->h[0] = 0; +@@ -533,6 +545,7 @@ _gcry_poly1305_update_burn (poly1305_con + size_t bytes) + { + unsigned int burn = 0; ++ unsigned int nburn; + + /* handle leftover */ + if (ctx->leftover) +@@ -546,15 +559,31 @@ _gcry_poly1305_update_burn (poly1305_con + ctx->leftover += want; + if (ctx->leftover < POLY1305_BLOCKSIZE) + return 0; +- burn = poly1305_blocks (ctx, ctx->buffer, POLY1305_BLOCKSIZE, 1); ++ nburn = poly1305_blocks (ctx, ctx->buffer, POLY1305_BLOCKSIZE, 1); ++ burn = nburn > burn ? nburn : burn; + ctx->leftover = 0; + } + ++#ifdef POLY1305_USE_PPC_VEC ++ /* PPC-P10/little-endian: bulk process multiples of eight blocks */ ++ if (ctx->use_p10 && bytes >= POLY1305_BLOCKSIZE * 8) ++ { ++ size_t nblks = bytes / (POLY1305_BLOCKSIZE * 8); ++ size_t len = nblks * (POLY1305_BLOCKSIZE * 8); ++ POLY1305_STATE *st = &ctx->state; ++ nburn = gcry_poly1305_p10le_4blocks ((unsigned char *) st, m, len); ++ burn = nburn > burn ? nburn : burn; ++ m += len; ++ bytes -= len; ++ } ++#endif /* POLY1305_USE_PPC_VEC */ ++ + /* process full blocks */ + if (bytes >= POLY1305_BLOCKSIZE) + { + size_t nblks = bytes / POLY1305_BLOCKSIZE; +- burn = poly1305_blocks (ctx, m, nblks * POLY1305_BLOCKSIZE, 1); ++ nburn = poly1305_blocks (ctx, m, nblks * POLY1305_BLOCKSIZE, 1); ++ burn = nburn > burn ? nburn : burn; + m += nblks * POLY1305_BLOCKSIZE; + bytes -= nblks * POLY1305_BLOCKSIZE; + } +Index: libgcrypt-1.10.2/configure.ac +=================================================================== +--- libgcrypt-1.10.2.orig/configure.ac ++++ libgcrypt-1.10.2/configure.ac +@@ -2779,6 +2779,11 @@ if test "$found" = "1" ; then + powerpc64le-*-*) + # Build with the ppc8 vector implementation + GCRYPT_ASM_CIPHERS="$GCRYPT_ASM_CIPHERS chacha20-ppc.lo" ++ # Build with the assembly implementation ++ if test "$gcry_cv_gcc_inline_asm_ppc_altivec" = "yes" && ++ test "$gcry_cv_gcc_inline_asm_ppc_arch_3_00" = "yes" ; then ++ GCRYPT_ASM_CIPHERS="$GCRYPT_ASM_CIPHERS chacha20-p10le-8x.lo" ++ fi + ;; + powerpc64-*-*) + # Build with the ppc8 vector implementation +@@ -3117,6 +3122,13 @@ case "${host}" in + s390x-*-*) + GCRYPT_ASM_DIGESTS="$GCRYPT_ASM_DIGESTS poly1305-s390x.lo" + ;; ++ powerpc64le-*-*) ++ # Build with the assembly implementation ++ if test "$gcry_cv_gcc_inline_asm_ppc_altivec" = "yes" && ++ test "$gcry_cv_gcc_inline_asm_ppc_arch_3_00" = "yes" ; then ++ GCRYPT_ASM_DIGESTS="$GCRYPT_ASM_DIGESTS poly1305-p10le.lo" ++ fi ++ ;; + esac + + LIST_MEMBER(scrypt, $enabled_kdfs) diff --git a/libgcrypt-Disable-SHA3-s390x-acceleration-for-CSHAKE.patch b/libgcrypt-Disable-SHA3-s390x-acceleration-for-CSHAKE.patch new file mode 100644 index 0000000..ee40bc2 --- /dev/null +++ b/libgcrypt-Disable-SHA3-s390x-acceleration-for-CSHAKE.patch @@ -0,0 +1,61 @@ +From 2486d9b5ae015c1786cb84466a751da4bc0d7122 Mon Sep 17 00:00:00 2001 +From: Jussi Kivilinna +Date: Thu, 20 Jun 2024 20:10:09 +0300 +Subject: Disable SHA3 s390x acceleration for CSHAKE + +* cipher/keccak.c (keccak_final_s390x): Add assert check for +expected SHAKE suffix. +(_gcry_cshake_customize, cshake_hash_buffers): Disable s390x +acceleration when selecting CSHAKE suffix. +-- + +Signed-off-by: Jussi Kivilinna + +diff --git a/cipher/keccak.c b/cipher/keccak.c +index aaf83a62..44cc9f71 100644 +--- a/cipher/keccak.c ++++ b/cipher/keccak.c +@@ -745,6 +745,8 @@ keccak_final_s390x (void *context) + } + else + { ++ gcry_assert(ctx->suffix == SHAKE_DELIMITED_SUFFIX); ++ + klmd_shake_execute (ctx->kimd_func, &ctx->state, NULL, 0, ctx->buf, + ctx->count); + ctx->count = 0; +@@ -1497,9 +1499,14 @@ _gcry_cshake_customize (void *context, struct gcry_cshake_customization *p) + /* No customization */ + return 0; + ++ ctx->suffix = CSHAKE_DELIMITED_SUFFIX; ++#ifdef USE_S390X_CRYPTO ++ /* CSHAKE suffix is not supported by s390x/kimd. */ ++ ctx->kimd_func = 0; ++#endif ++ + len_written = cshake_input_n (ctx, p->n, p->n_len); + cshake_input_s (ctx, p->s, p->s_len, len_written); +- ctx->suffix = CSHAKE_DELIMITED_SUFFIX; + return 0; + } + +@@ -1536,9 +1543,14 @@ cshake_hash_buffers (const gcry_md_spec_t *spec, void *outbuf, size_t nbytes, + size_t s_len = iov[1].len; + size_t len; + ++ ctx.suffix = CSHAKE_DELIMITED_SUFFIX; ++#ifdef USE_S390X_CRYPTO ++ /* CSHAKE suffix is not supported by s390x/kimd. */ ++ ctx.kimd_func = 0; ++#endif ++ + len = cshake_input_n (&ctx, n, n_len); + cshake_input_s (&ctx, s, s_len, len); +- ctx.suffix = CSHAKE_DELIMITED_SUFFIX; + } + iovcnt -= 2; + iov += 2; +-- +2.49.0 + diff --git a/libgcrypt-FIPS-SLI-hash-mac.patch b/libgcrypt-FIPS-SLI-hash-mac.patch new file mode 100644 index 0000000..ff03fae --- /dev/null +++ b/libgcrypt-FIPS-SLI-hash-mac.patch @@ -0,0 +1,172 @@ +Index: libgcrypt-1.11.1/doc/gcrypt.texi +=================================================================== +--- libgcrypt-1.11.1.orig/doc/gcrypt.texi ++++ libgcrypt-1.11.1/doc/gcrypt.texi +@@ -998,13 +998,21 @@ certification. If the function is approv + @code{GPG_ERR_NO_ERROR} (other restrictions might still apply). + Otherwise @code{GPG_ERR_NOT_SUPPORTED} is returned. + +-@item GCRYCTL_FIPS_SERVICE_INDICATOR_MAC; Arguments: enum gcry_mac_algos ++@item GCRYCTL_FIPS_SERVICE_INDICATOR_HASH; Arguments: enum gcry_md_algos + +-Check if the given MAC is approved under the current FIPS 140-3 +-certification. If the MAC is approved, this function returns +-@code{GPG_ERR_NO_ERROR}. Otherwise @code{GPG_ERR_NOT_SUPPORTED} ++Check if the given HASH is approved under the current FIPS 140-3 ++certification. If the HASH is approved, this function returns ++@code{GPS_ERR_NO_ERROR}. Otherwise @code{GPG_ERR_NOT_SUPPORTED} + is returned. + ++@item GCRYCTL_FIPS_SERVICE_INDICATOR_MAC; Arguments: enum gcry_mac_algos [, unsigned int] ++ ++Check if the given MAC is approved under the current FIPS 140-3 ++certification. The second parameter provides the keylen (if the ++algorithm supports different key sizes). If the MAC is approved, ++this function returns @code{GPS_ERR_NO_ERROR}. Otherwise ++@code{GPG_ERR_NOT_SUPPORTED} is returned. ++ + @item GCRYCTL_FIPS_SERVICE_INDICATOR_MD; Arguments: enum gcry_md_algos + + Check if the given message digest algorithm is approved under the current +Index: libgcrypt-1.11.1/src/fips.c +=================================================================== +--- libgcrypt-1.11.1.orig/src/fips.c ++++ libgcrypt-1.11.1/src/fips.c +@@ -512,31 +512,6 @@ _gcry_fips_indicator_pk (va_list arg_ptr + } + + int +-_gcry_fips_indicator_mac (va_list arg_ptr) +-{ +- enum gcry_mac_algos alg = va_arg (arg_ptr, enum gcry_mac_algos); +- +- switch (alg) +- { +- case GCRY_MAC_CMAC_AES: +- case GCRY_MAC_HMAC_SHA1: +- case GCRY_MAC_HMAC_SHA224: +- case GCRY_MAC_HMAC_SHA256: +- case GCRY_MAC_HMAC_SHA384: +- case GCRY_MAC_HMAC_SHA512: +- case GCRY_MAC_HMAC_SHA512_224: +- case GCRY_MAC_HMAC_SHA512_256: +- case GCRY_MAC_HMAC_SHA3_224: +- case GCRY_MAC_HMAC_SHA3_256: +- case GCRY_MAC_HMAC_SHA3_384: +- case GCRY_MAC_HMAC_SHA3_512: +- return GPG_ERR_NO_ERROR; +- default: +- return GPG_ERR_NOT_SUPPORTED; +- } +-} +- +-int + _gcry_fips_indicator_md (va_list arg_ptr) + { + enum gcry_md_algos alg = va_arg (arg_ptr, enum gcry_md_algos); +@@ -647,6 +622,62 @@ _gcry_fips_indicator_pk_flags (va_list a + return GPG_ERR_NOT_SUPPORTED; + } + ++int ++_gcry_fips_indicator_hash (va_list arg_ptr) ++{ ++ enum gcry_md_algos alg = va_arg (arg_ptr, enum gcry_md_algos); ++ ++ switch (alg) ++ { ++ case GCRY_MD_SHA1: ++ case GCRY_MD_SHA224: ++ case GCRY_MD_SHA256: ++ case GCRY_MD_SHA384: ++ case GCRY_MD_SHA512: ++ case GCRY_MD_SHA512_224: ++ case GCRY_MD_SHA512_256: ++ case GCRY_MD_SHA3_224: ++ case GCRY_MD_SHA3_256: ++ case GCRY_MD_SHA3_384: ++ case GCRY_MD_SHA3_512: ++ case GCRY_MD_SHAKE128: ++ case GCRY_MD_SHAKE256: ++ return GPG_ERR_NO_ERROR; ++ default: ++ return GPG_ERR_NOT_SUPPORTED; ++ } ++} ++ ++int ++_gcry_fips_indicator_mac (va_list arg_ptr) ++{ ++ enum gcry_mac_algos alg = va_arg (arg_ptr, enum gcry_mac_algos); ++ unsigned int keylen = va_arg (arg_ptr, unsigned int); ++ ++ switch (alg) ++ { ++ case GCRY_MAC_HMAC_SHA1: ++ case GCRY_MAC_HMAC_SHA224: ++ case GCRY_MAC_HMAC_SHA256: ++ case GCRY_MAC_HMAC_SHA384: ++ case GCRY_MAC_HMAC_SHA512: ++ case GCRY_MAC_HMAC_SHA512_224: ++ case GCRY_MAC_HMAC_SHA512_256: ++ case GCRY_MAC_HMAC_SHA3_224: ++ case GCRY_MAC_HMAC_SHA3_256: ++ case GCRY_MAC_HMAC_SHA3_384: ++ case GCRY_MAC_HMAC_SHA3_512: ++ if (keylen >= 112) { ++ return GPG_ERR_NO_ERROR; ++ } ++ case GCRY_MAC_CMAC_AES: ++ if (keylen == 128 || keylen == 192 || keylen == 256) { ++ return GPG_ERR_NO_ERROR; ++ } ++ default: ++ return GPG_ERR_NOT_SUPPORTED; ++ } ++} + + /* This is a test on whether the library is in the error or + operational state. */ +Index: libgcrypt-1.11.1/src/g10lib.h +=================================================================== +--- libgcrypt-1.11.1.orig/src/g10lib.h ++++ libgcrypt-1.11.1/src/g10lib.h +@@ -478,6 +478,7 @@ void _gcry_fips_signal_error (const char + gpg_err_code_t _gcry_fips_indicator (void); + + int _gcry_fips_indicator_cipher (va_list arg_ptr); ++int _gcry_fips_indicator_hash (va_list arg_ptr); + int _gcry_fips_indicator_mac (va_list arg_ptr); + int _gcry_fips_indicator_md (va_list arg_ptr); + int _gcry_fips_indicator_kdf (va_list arg_ptr); +Index: libgcrypt-1.11.1/src/gcrypt.h.in +=================================================================== +--- libgcrypt-1.11.1.orig/src/gcrypt.h.in ++++ libgcrypt-1.11.1/src/gcrypt.h.in +@@ -338,7 +338,8 @@ enum gcry_ctl_cmds + GCRYCTL_MD_CUSTOMIZE = 88, + GCRYCTL_FIPS_SERVICE_INDICATOR = 89, + GCRYCTL_FIPS_REJECT_NON_FIPS = 90, +- GCRYCTL_FIPS_SERVICE_INDICATOR_PK = 91 ++ GCRYCTL_FIPS_SERVICE_INDICATOR_PK = 91, ++ GCRYCTL_FIPS_SERVICE_INDICATOR_HASH = 92 + }; + + /* Perform various operations defined by CMD. */ +Index: libgcrypt-1.11.1/src/global.c +=================================================================== +--- libgcrypt-1.11.1.orig/src/global.c ++++ libgcrypt-1.11.1/src/global.c +@@ -808,6 +808,12 @@ _gcry_vcontrol (enum gcry_ctl_cmds cmd, + rc = _gcry_fips_indicator_cipher (arg_ptr); + break; + ++ case GCRYCTL_FIPS_SERVICE_INDICATOR_HASH: ++ /* Get FIPS Service Indicator for a given HASH. Returns GPG_ERR_NO_ERROR ++ * if algorithm is allowed or GPG_ERR_NOT_SUPPORTED otherwise */ ++ rc = _gcry_fips_indicator_hash (arg_ptr); ++ break; ++ + case GCRYCTL_FIPS_SERVICE_INDICATOR_MAC: + /* Get FIPS Service Indicator for a given message authentication code. + * Returns GPG_ERR_NO_ERROR if algorithm is allowed or diff --git a/libgcrypt-FIPS-SLI-kdf-leylength.patch b/libgcrypt-FIPS-SLI-kdf-leylength.patch new file mode 100644 index 0000000..d3693ac --- /dev/null +++ b/libgcrypt-FIPS-SLI-kdf-leylength.patch @@ -0,0 +1,60 @@ +Index: libgcrypt-1.11.0/src/fips.c +=================================================================== +--- libgcrypt-1.11.0.orig/src/fips.c ++++ libgcrypt-1.11.0/src/fips.c +@@ -523,10 +523,15 @@ int + _gcry_fips_indicator_kdf (va_list arg_ptr) + { + enum gcry_kdf_algos alg = va_arg (arg_ptr, enum gcry_kdf_algos); ++ unsigned int keylen = 0; + + switch (alg) + { + case GCRY_KDF_PBKDF2: ++ keylen = va_arg (arg_ptr, unsigned int); ++ if (keylen < 112) { ++ return GPG_ERR_NOT_SUPPORTED; ++ } + return GPG_ERR_NO_ERROR; + default: + return GPG_ERR_NOT_SUPPORTED; +Index: libgcrypt-1.11.0/doc/gcrypt.texi +=================================================================== +--- libgcrypt-1.11.0.orig/doc/gcrypt.texi ++++ libgcrypt-1.11.0/doc/gcrypt.texi +@@ -983,12 +983,13 @@ is approved under the current FIPS 140-3 + combination is approved, this function returns @code{GPG_ERR_NO_ERROR}. + Otherwise @code{GPG_ERR_NOT_SUPPORTED} is returned. + +-@item GCRYCTL_FIPS_SERVICE_INDICATOR_KDF; Arguments: enum gcry_kdf_algos ++@item GCRYCTL_FIPS_SERVICE_INDICATOR_KDF; Arguments: enum gcry_kdf_algos [, unsigned int] + + Check if the given KDF is approved under the current FIPS 140-3 +-certification. If the KDF is approved, this function returns +-@code{GPG_ERR_NO_ERROR}. Otherwise @code{GPG_ERR_NOT_SUPPORTED} +-is returned. ++certification. The second parameter provides the keylength in bits. ++Keylength values of less that 112 bits are considered non-approved. ++If the KDF is approved, this function returns @code{GPG_ERR_NO_ERROR}. ++Otherwise @code{GPG_ERR_NOT_SUPPORTED} is returned. + + @item GCRYCTL_FIPS_SERVICE_INDICATOR_FUNCTION; Arguments: const char * + +Index: libgcrypt-1.11.0/tests/t-kdf.c +=================================================================== +--- libgcrypt-1.11.0.orig/tests/t-kdf.c ++++ libgcrypt-1.11.0/tests/t-kdf.c +@@ -1889,7 +1889,12 @@ check_fips_indicators (void) + for (i = 0; i < sizeof(kdf_algos) / sizeof(*kdf_algos); i++) + { + int is_fips_kdf_algo = 0; +- gcry_error_t err = gcry_control (GCRYCTL_FIPS_SERVICE_INDICATOR_KDF, kdf_algos[i]); ++ gcry_error_t err; ++ // On SUSE/openSUSE builds PBKDF2 with keysize < 112 is not allowed ++ if (kdf_algos[i] == GCRY_KDF_PBKDF2) ++ err = gcry_control (GCRYCTL_FIPS_SERVICE_INDICATOR_KDF, kdf_algos[i], 112); ++ else ++ err = gcry_control (GCRYCTL_FIPS_SERVICE_INDICATOR_KDF, kdf_algos[i]); + + if (verbose) + fprintf (stderr, "checking FIPS indicator for KDF %d: %s\n", diff --git a/libgcrypt-FIPS-SLI-pk.patch b/libgcrypt-FIPS-SLI-pk.patch new file mode 100644 index 0000000..4dd3d97 --- /dev/null +++ b/libgcrypt-FIPS-SLI-pk.patch @@ -0,0 +1,177 @@ +Index: libgcrypt-1.11.1/src/fips.c +=================================================================== +--- libgcrypt-1.11.1.orig/src/fips.c ++++ libgcrypt-1.11.1/src/fips.c +@@ -38,6 +38,7 @@ + + #include "g10lib.h" + #include "cipher-proto.h" ++#include "cipher.h" + #include "../random/random.h" + + /* The states of the finite state machine used in fips mode. */ +@@ -420,6 +421,94 @@ _gcry_fips_indicator_cipher (va_list arg + default: + return GPG_ERR_NOT_SUPPORTED; + } ++} ++ ++/* FIPS approved curves, extracted from: ++ * cipher/ecc-curves.c:curve_aliases[] and domain_parms[]. */ ++static const struct ++{ ++ const char *name; /* Our name. */ ++ const char *other; /* Other name. */ ++} fips_approved_curve[] = ++ { ++ /* "NIST P-192" is non-approved if FIPS 140-3 */ ++ /* { "NIST P-192", "1.2.840.10045.3.1.1" }, /\* X9.62 OID *\/ */ ++ /* { "NIST P-192", "prime192v1" }, /\* X9.62 name. *\/ */ ++ /* { "NIST P-192", "secp192r1" }, /\* SECP name. *\/ */ ++ /* { "NIST P-192", "nistp192" }, /\* rfc5656. *\/ */ ++ ++ { "NIST P-224", "secp224r1" }, ++ { "NIST P-224", "1.3.132.0.33" }, /* SECP OID. */ ++ { "NIST P-224", "nistp224" }, /* rfc5656. */ ++ ++ { "NIST P-256", "1.2.840.10045.3.1.7" }, /* From NIST SP 800-78-1. */ ++ { "NIST P-256", "prime256v1" }, ++ { "NIST P-256", "secp256r1" }, ++ { "NIST P-256", "nistp256" }, /* rfc5656. */ ++ ++ { "NIST P-384", "secp384r1" }, ++ { "NIST P-384", "1.3.132.0.34" }, ++ { "NIST P-384", "nistp384" }, /* rfc5656. */ ++ ++ { "NIST P-521", "secp521r1" }, ++ { "NIST P-521", "1.3.132.0.35" }, ++ { "NIST P-521", "nistp521" }, /* rfc5656. */ ++ { NULL, NULL} ++ }; ++ ++enum pk_operation convert_from_pk_usage(unsigned int pk_usage) ++{ ++ switch (pk_usage) ++ { ++ case GCRY_PK_USAGE_SIGN: ++ return PUBKEY_OP_SIGN; ++ case GCRY_PK_USAGE_ENCR: ++ return PUBKEY_OP_ENCRYPT; ++ default: ++ return PUBKEY_OP_DECRYPT; ++ } ++} ++ ++int ++_gcry_fips_indicator_pk (va_list arg_ptr) ++{ ++ enum gcry_pk_algos alg = va_arg (arg_ptr, enum gcry_pk_algos); ++ enum pk_operation oper; ++ unsigned int keylen; ++ const char *curve_name; ++ ++ switch (alg) ++ { ++ case GCRY_PK_RSA: ++ case GCRY_PK_RSA_E: ++ case GCRY_PK_RSA_S: ++ oper = convert_from_pk_usage(va_arg (arg_ptr, unsigned int)); ++ switch (oper) ++ { ++ case PUBKEY_OP_ENCRYPT: ++ case PUBKEY_OP_DECRYPT: ++ return GPG_ERR_NOT_SUPPORTED; ++ default: ++ keylen = va_arg (arg_ptr, unsigned int); ++ if (keylen < 2048) ++ return GPG_ERR_NOT_SUPPORTED; ++ return GPG_ERR_NO_ERROR; ++ } ++ case GCRY_PK_ECC: ++ case GCRY_PK_ECDH: ++ case GCRY_PK_ECDSA: ++ curve_name = va_arg (arg_ptr, const char *); ++ for (int idx = 0; fips_approved_curve[idx].name; ++idx) ++ { ++ /* Check for the usual name and an alias. */ ++ if (!strcmp (curve_name, fips_approved_curve[idx].name) || ++ !strcmp (curve_name, fips_approved_curve[idx].other)) ++ return GPG_ERR_NO_ERROR; ++ } ++ return GPG_ERR_NOT_SUPPORTED; ++ default: ++ return GPG_ERR_NOT_SUPPORTED; ++ } + } + + int +Index: libgcrypt-1.11.1/src/gcrypt.h.in +=================================================================== +--- libgcrypt-1.11.1.orig/src/gcrypt.h.in ++++ libgcrypt-1.11.1/src/gcrypt.h.in +@@ -337,7 +337,8 @@ enum gcry_ctl_cmds + GCRYCTL_FIPS_SERVICE_INDICATOR_PK_FLAGS = 87, + GCRYCTL_MD_CUSTOMIZE = 88, + GCRYCTL_FIPS_SERVICE_INDICATOR = 89, +- GCRYCTL_FIPS_REJECT_NON_FIPS = 90 ++ GCRYCTL_FIPS_REJECT_NON_FIPS = 90, ++ GCRYCTL_FIPS_SERVICE_INDICATOR_PK = 91 + }; + + /* Perform various operations defined by CMD. */ +Index: libgcrypt-1.11.1/doc/gcrypt.texi +=================================================================== +--- libgcrypt-1.11.1.orig/doc/gcrypt.texi ++++ libgcrypt-1.11.1/doc/gcrypt.texi +@@ -1010,6 +1010,19 @@ Check if the given message digest algori + FIPS 140-3 certification. If the algorithm is approved, this function returns + @code{GPG_ERR_NO_ERROR}. Otherwise @code{GPG_ERR_NOT_SUPPORTED} is returned. + ++@item GCRYCTL_FIPS_SERVICE_INDICATOR_PK; Arguments: enum gcry_pk_algos [, constantsGCRY_PK_USAGE_ENCR or GCRY_PK_USAGE_SIGN, unsigned int (only for GCRY_PK_RSA)] [, const char * (only for GCRY_PK_ECC, GCRY_PK_ECDH or GCRY_PK_ECDSA)] ++ ++Check if the given asymmetric cipher is approved under the current ++FIPS 140-3 certification. For GCRY_PK_RSA, two additional parameter ++are required: first describes the purpose of the algorithm through one ++of the constants (GCRY_PK_USAGE_ENCR for encryption or decryption ++operations; GCRY_PK_USAGE_SIGN for sign or verify operations). Second ++one is the key length. For GCRY_PK_ECC, GCRY_PK_ECDH and ++GCRY_PK_ECDSA, only a single parameter is needed: the curve name or ++its alias as @code{const char *}. If the combination is approved, this ++function returns @code{GPG_ERR_NO_ERROR}. Otherwise ++@code{GPG_ERR_NOT_SUPPORTED} is returned. ++ + @item GCRYCTL_FIPS_SERVICE_INDICATOR_PK_FLAGS; Arguments: const char * + + Check if the given public key operation flag or s-expression object name is +Index: libgcrypt-1.11.1/src/g10lib.h +=================================================================== +--- libgcrypt-1.11.1.orig/src/g10lib.h ++++ libgcrypt-1.11.1/src/g10lib.h +@@ -482,6 +482,7 @@ int _gcry_fips_indicator_mac (va_list ar + int _gcry_fips_indicator_md (va_list arg_ptr); + int _gcry_fips_indicator_kdf (va_list arg_ptr); + int _gcry_fips_indicator_function (va_list arg_ptr); ++int _gcry_fips_indicator_pk (va_list arg_ptr); + int _gcry_fips_indicator_pk_flags (va_list arg_ptr); + + int _gcry_fips_is_operational (void); +Index: libgcrypt-1.11.1/src/global.c +=================================================================== +--- libgcrypt-1.11.1.orig/src/global.c ++++ libgcrypt-1.11.1/src/global.c +@@ -842,6 +842,15 @@ _gcry_vcontrol (enum gcry_ctl_cmds cmd, + rc = _gcry_fips_indicator_pk_flags (arg_ptr); + break; + ++ case GCRYCTL_FIPS_SERVICE_INDICATOR_PK: ++ /* Get FIPS Service Indicator for a given asymmetric algorithm. For ++ * GCRY_PK_RSA, an additional parameter for the operation mode is ++ * required. For ECC, ECDH and ECDSA, the additional parameter is the ++ * curve name or its alias. Returns GPG_ERR_NO_ERROR if the ++ * algorithm is allowed or GPG_ERR_NOT_SUPPORTED otherwise. */ ++ rc = _gcry_fips_indicator_pk (arg_ptr); ++ break; ++ + case PRIV_CTL_INIT_EXTRNG_TEST: /* Init external random test. */ + rc = GPG_ERR_NOT_SUPPORTED; + break; diff --git a/libgcrypt-FIPS-jitter-errorcodes.patch b/libgcrypt-FIPS-jitter-errorcodes.patch new file mode 100644 index 0000000..d6d314e --- /dev/null +++ b/libgcrypt-FIPS-jitter-errorcodes.patch @@ -0,0 +1,16 @@ +Index: libgcrypt-1.10.3/random/rndjent.c +=================================================================== +--- libgcrypt-1.10.3.orig/random/rndjent.c ++++ libgcrypt-1.10.3/random/rndjent.c +@@ -319,7 +319,10 @@ _gcry_rndjent_poll (void (*add)(const vo + jent_rng_totalcalls++; + rc = jent_read_entropy_safe (&jent_rng_collector, buffer, n); + if (rc < 0) +- break; ++ { ++ fips_signal_error ("jitter entropy failed"); ++ break; ++ } + /* We need to hash the output to conform to the BSI + * NTG.1 specs. */ + _gcry_md_hash_buffer (GCRY_MD_SHA256, buffer, buffer, rc); diff --git a/libgcrypt-FIPS-jitter-standalone.patch b/libgcrypt-FIPS-jitter-standalone.patch new file mode 100644 index 0000000..fb375fa --- /dev/null +++ b/libgcrypt-FIPS-jitter-standalone.patch @@ -0,0 +1,183 @@ +Index: libgcrypt-1.11.1/random/Makefile.am +=================================================================== +--- libgcrypt-1.11.1.orig/random/Makefile.am ++++ libgcrypt-1.11.1/random/Makefile.am +@@ -21,7 +21,7 @@ + # Need to include ../src in addition to top_srcdir because gcrypt.h is + # a built header. + AM_CPPFLAGS = -I../src -I$(top_srcdir)/src +-AM_CFLAGS = $(GPG_ERROR_CFLAGS) ++AM_CFLAGS = $(GPG_ERROR_CFLAGS) -ljitterentropy + + noinst_LTLIBRARIES = librandom.la + +@@ -44,14 +44,7 @@ rndgetentropy.c \ + rndoldlinux.c \ + rndegd.c \ + rndunix.c \ +-rndw32.c \ +-jitterentropy-gcd.c jitterentropy-gcd.h \ +-jitterentropy-health.c jitterentropy-health.h \ +-jitterentropy-noise.c jitterentropy-noise.h \ +-jitterentropy-sha3.c jitterentropy-sha3.h \ +-jitterentropy-timer.c jitterentropy-timer.h \ +-jitterentropy-base.h \ +-jitterentropy-base.c jitterentropy.h jitterentropy-base-user.h ++rndw32.c + + # The rndjent module needs to be compiled without optimization. */ + if ENABLE_O_FLAG_MUNGING +@@ -60,20 +53,8 @@ else + o_flag_munging = cat + endif + +-rndjent.o: $(srcdir)/rndjent.c jitterentropy-base-user.h \ +- $(srcdir)/jitterentropy-gcd.c $(srcdir)/jitterentropy-gcd.h \ +- $(srcdir)/jitterentropy-health.c $(srcdir)/jitterentropy-health.h \ +- $(srcdir)/jitterentropy-noise.c $(srcdir)/jitterentropy-noise.h \ +- $(srcdir)/jitterentropy-sha3.c $(srcdir)/jitterentropy-sha3.h \ +- $(srcdir)/jitterentropy-timer.c $(srcdir)/jitterentropy-timer.h \ +- $(srcdir)/jitterentropy-base.c $(srcdir)/jitterentropy.h ++rndjent.o: $(srcdir)/rndjent.c + `echo $(COMPILE) -c $(srcdir)/rndjent.c | $(o_flag_munging) ` + +-rndjent.lo: $(srcdir)/rndjent.c jitterentropy-base-user.h \ +- $(srcdir)/jitterentropy-gcd.c $(srcdir)/jitterentropy-gcd.h \ +- $(srcdir)/jitterentropy-health.c $(srcdir)/jitterentropy-health.h \ +- $(srcdir)/jitterentropy-noise.c $(srcdir)/jitterentropy-noise.h \ +- $(srcdir)/jitterentropy-sha3.c $(srcdir)/jitterentropy-sha3.h \ +- $(srcdir)/jitterentropy-timer.c $(srcdir)/jitterentropy-timer.h \ +- $(srcdir)/jitterentropy-base.c $(srcdir)/jitterentropy.h ++rndjent.lo: $(srcdir)/rndjent.c + `echo $(LTCOMPILE) -c $(srcdir)/rndjent.c | $(o_flag_munging) ` +Index: libgcrypt-1.11.1/random/rndjent.c +=================================================================== +--- libgcrypt-1.11.1.orig/random/rndjent.c ++++ libgcrypt-1.11.1/random/rndjent.c +@@ -94,17 +94,12 @@ + * jitterentropy-user-base.h file. */ + + /* Tell jitterentropy* that all functions shall be static. */ +-#define JENT_PRIVATE_COMPILE 1 ++#undef JENT_PRIVATE_COMPILE + +-#include "jitterentropy-base.c" + #ifdef JENT_CONF_ENABLE_INTERNAL_TIMER + #include + #endif /* JENT_CONF_ENABLE_INTERNAL_TIMER */ +-#include "jitterentropy-gcd.c" +-#include "jitterentropy-health.c" +-#include "jitterentropy-noise.c" +-#include "jitterentropy-sha3.c" +-#include "jitterentropy-timer.c" ++#include + + /* This is the lock we use to serialize access to this RNG. The extra + * integer variable is only used to check the locking state; that is, +Index: libgcrypt-1.11.1/random/Makefile.in +=================================================================== +--- libgcrypt-1.11.1.orig/random/Makefile.in ++++ libgcrypt-1.11.1/random/Makefile.in +@@ -147,12 +147,7 @@ am__v_at_1 = + DEFAULT_INCLUDES = -I.@am__isrc@ -I$(top_builddir) + depcomp = $(SHELL) $(top_srcdir)/build-aux/depcomp + am__maybe_remake_depfiles = depfiles +-am__depfiles_remade = ./$(DEPDIR)/jitterentropy-base.Plo \ +- ./$(DEPDIR)/jitterentropy-gcd.Plo \ +- ./$(DEPDIR)/jitterentropy-health.Plo \ +- ./$(DEPDIR)/jitterentropy-noise.Plo \ +- ./$(DEPDIR)/jitterentropy-sha3.Plo \ +- ./$(DEPDIR)/jitterentropy-timer.Plo \ ++am__depfiles_remade = \ + ./$(DEPDIR)/random-csprng.Plo ./$(DEPDIR)/random-drbg.Plo \ + ./$(DEPDIR)/random-system.Plo ./$(DEPDIR)/random.Plo \ + ./$(DEPDIR)/rndegd.Plo ./$(DEPDIR)/rndgetentropy.Plo \ +@@ -375,7 +370,7 @@ top_srcdir = @top_srcdir@ + # Need to include ../src in addition to top_srcdir because gcrypt.h is + # a built header. + AM_CPPFLAGS = -I../src -I$(top_srcdir)/src +-AM_CFLAGS = $(GPG_ERROR_CFLAGS) ++AM_CFLAGS = $(GPG_ERROR_CFLAGS) -ljitterentropy + noinst_LTLIBRARIES = librandom.la + GCRYPT_MODULES = @GCRYPT_RANDOM@ + librandom_la_DEPENDENCIES = $(GCRYPT_MODULES) +@@ -394,14 +389,7 @@ rndgetentropy.c \ + rndoldlinux.c \ + rndegd.c \ + rndunix.c \ +-rndw32.c \ +-jitterentropy-gcd.c jitterentropy-gcd.h \ +-jitterentropy-health.c jitterentropy-health.h \ +-jitterentropy-noise.c jitterentropy-noise.h \ +-jitterentropy-sha3.c jitterentropy-sha3.h \ +-jitterentropy-timer.c jitterentropy-timer.h \ +-jitterentropy-base.h \ +-jitterentropy-base.c jitterentropy.h jitterentropy-base-user.h ++rndw32.c + + @ENABLE_O_FLAG_MUNGING_FALSE@o_flag_munging = cat + +@@ -461,12 +449,6 @@ mostlyclean-compile: + distclean-compile: + -rm -f *.tab.c + +-@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/jitterentropy-base.Plo@am__quote@ # am--include-marker +-@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/jitterentropy-gcd.Plo@am__quote@ # am--include-marker +-@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/jitterentropy-health.Plo@am__quote@ # am--include-marker +-@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/jitterentropy-noise.Plo@am__quote@ # am--include-marker +-@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/jitterentropy-sha3.Plo@am__quote@ # am--include-marker +-@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/jitterentropy-timer.Plo@am__quote@ # am--include-marker + @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/random-csprng.Plo@am__quote@ # am--include-marker + @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/random-drbg.Plo@am__quote@ # am--include-marker + @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/random-system.Plo@am__quote@ # am--include-marker +@@ -636,12 +618,6 @@ clean-am: clean-generic clean-libtool cl + mostlyclean-am + + distclean: distclean-am +- -rm -f ./$(DEPDIR)/jitterentropy-base.Plo +- -rm -f ./$(DEPDIR)/jitterentropy-gcd.Plo +- -rm -f ./$(DEPDIR)/jitterentropy-health.Plo +- -rm -f ./$(DEPDIR)/jitterentropy-noise.Plo +- -rm -f ./$(DEPDIR)/jitterentropy-sha3.Plo +- -rm -f ./$(DEPDIR)/jitterentropy-timer.Plo + -rm -f ./$(DEPDIR)/random-csprng.Plo + -rm -f ./$(DEPDIR)/random-drbg.Plo + -rm -f ./$(DEPDIR)/random-system.Plo +@@ -698,12 +674,6 @@ install-ps-am: + installcheck-am: + + maintainer-clean: maintainer-clean-am +- -rm -f ./$(DEPDIR)/jitterentropy-base.Plo +- -rm -f ./$(DEPDIR)/jitterentropy-gcd.Plo +- -rm -f ./$(DEPDIR)/jitterentropy-health.Plo +- -rm -f ./$(DEPDIR)/jitterentropy-noise.Plo +- -rm -f ./$(DEPDIR)/jitterentropy-sha3.Plo +- -rm -f ./$(DEPDIR)/jitterentropy-timer.Plo + -rm -f ./$(DEPDIR)/random-csprng.Plo + -rm -f ./$(DEPDIR)/random-drbg.Plo + -rm -f ./$(DEPDIR)/random-system.Plo +@@ -752,22 +722,10 @@ uninstall-am: + .PRECIOUS: Makefile + + +-rndjent.o: $(srcdir)/rndjent.c jitterentropy-base-user.h \ +- $(srcdir)/jitterentropy-gcd.c $(srcdir)/jitterentropy-gcd.h \ +- $(srcdir)/jitterentropy-health.c $(srcdir)/jitterentropy-health.h \ +- $(srcdir)/jitterentropy-noise.c $(srcdir)/jitterentropy-noise.h \ +- $(srcdir)/jitterentropy-sha3.c $(srcdir)/jitterentropy-sha3.h \ +- $(srcdir)/jitterentropy-timer.c $(srcdir)/jitterentropy-timer.h \ +- $(srcdir)/jitterentropy-base.c $(srcdir)/jitterentropy.h ++rndjent.o: $(srcdir)/rndjent.c + `echo $(COMPILE) -c $(srcdir)/rndjent.c | $(o_flag_munging) ` + +-rndjent.lo: $(srcdir)/rndjent.c jitterentropy-base-user.h \ +- $(srcdir)/jitterentropy-gcd.c $(srcdir)/jitterentropy-gcd.h \ +- $(srcdir)/jitterentropy-health.c $(srcdir)/jitterentropy-health.h \ +- $(srcdir)/jitterentropy-noise.c $(srcdir)/jitterentropy-noise.h \ +- $(srcdir)/jitterentropy-sha3.c $(srcdir)/jitterentropy-sha3.h \ +- $(srcdir)/jitterentropy-timer.c $(srcdir)/jitterentropy-timer.h \ +- $(srcdir)/jitterentropy-base.c $(srcdir)/jitterentropy.h ++rndjent.lo: $(srcdir)/rndjent.c + `echo $(LTCOMPILE) -c $(srcdir)/rndjent.c | $(o_flag_munging) ` + + # Tell versions [3.59,3.63) of GNU make to not export all variables. diff --git a/libgcrypt-FIPS-jitter-whole-entropy.patch b/libgcrypt-FIPS-jitter-whole-entropy.patch new file mode 100644 index 0000000..6c16472 --- /dev/null +++ b/libgcrypt-FIPS-jitter-whole-entropy.patch @@ -0,0 +1,41 @@ +Index: libgcrypt-1.10.3/random/rndgetentropy.c +=================================================================== +--- libgcrypt-1.10.3.orig/random/rndgetentropy.c ++++ libgcrypt-1.10.3/random/rndgetentropy.c +@@ -53,16 +53,30 @@ _gcry_rndgetentropy_gather_random (void + + /* When using a blocking random generator try to get some entropy + * from the jitter based RNG. In this case we take up to 50% of the +- * remaining requested bytes. */ ++ * remaining requested bytes. In FIPS mode, we get all the entropy ++ * from the jitter RNG. */ + if (level >= GCRY_VERY_STRONG_RANDOM) + { + size_t n; + +- n = _gcry_rndjent_poll (add, origin, length/2); +- if (n > length/2) +- n = length/2; +- if (length > 1) +- length -= n; ++ /* In FIPS mode, use the whole length of the entropy buffer from ++ * Jitter RNG */ ++ if (fips_mode ()) ++ { ++ n = _gcry_rndjent_poll (add, origin, length); ++ if (n != length) ++ fips_signal_error ("jitter entropy failed"); ++ else ++ length = 0; ++ } ++ else ++ { ++ n = _gcry_rndjent_poll (add, origin, length/2); ++ if (n > length/2) ++ n = length/2; ++ if (length > 1) ++ length -= n; ++ } + } + + /* Enter the loop. */ diff --git a/libgcrypt-FIPS-rndjent_poll.patch b/libgcrypt-FIPS-rndjent_poll.patch new file mode 100644 index 0000000..f837842 --- /dev/null +++ b/libgcrypt-FIPS-rndjent_poll.patch @@ -0,0 +1,114 @@ +Index: libgcrypt-1.10.0/random/rndoldlinux.c +=================================================================== +--- libgcrypt-1.10.0.orig/random/rndoldlinux.c ++++ libgcrypt-1.10.0/random/rndoldlinux.c +@@ -132,7 +132,7 @@ _gcry_rndoldlinux_gather_random (void (* + volatile pid_t apid; + int fd; + int n; +- byte buffer[768]; ++ byte buffer[256]; + size_t n_hw; + size_t want = length; + size_t last_so_far = 0; +@@ -187,26 +187,43 @@ _gcry_rndoldlinux_gather_random (void (* + my_pid = apid; + } + ++ if (fips_mode()) ++ { ++ if (level >= GCRY_VERY_STRONG_RANDOM) ++ { ++ size_t n; + +- /* First read from a hardware source. Note that _gcry_rndhw_poll_slow lets +- it account only for up to 50% (or 25% for RDRAND) of the requested +- bytes. */ +- n_hw = _gcry_rndhw_poll_slow (add, origin, length); +- if (length > 1) +- length -= n_hw; +- +- /* When using a blocking random generator try to get some entropy +- * from the jitter based RNG. In this case we take up to 50% of the +- * remaining requested bytes. */ +- if (level >= GCRY_VERY_STRONG_RANDOM) +- { +- n_hw = _gcry_rndjent_poll (add, origin, length/2); +- if (n_hw > length/2) +- n_hw = length/2; ++ n = _gcry_rndjent_poll (add, origin, length); ++ if (n == 0) ++ log_fatal ("unexpected error from rndjent: %s\n", ++ strerror (errno)); ++ if (n > length) ++ n = length; ++ if (length > 1) ++ length -= n; ++ } ++ } ++ else ++ { ++ /* First read from a hardware source. Note that _gcry_rndhw_poll_slow lets ++ it account only for up to 50% (or 25% for RDRAND) of the requested ++ bytes. */ ++ n_hw = _gcry_rndhw_poll_slow (add, origin, length); + if (length > 1) + length -= n_hw; +- } + ++ /* When using a blocking random generator try to get some entropy ++ * from the jitter based RNG. In this case we take up to 50% of the ++ * remaining requested bytes. */ ++ if (level >= GCRY_VERY_STRONG_RANDOM) ++ { ++ n_hw = _gcry_rndjent_poll (add, origin, length/2); ++ if (n_hw > length/2) ++ n_hw = length/2; ++ if (length > 1) ++ length -= n_hw; ++ } ++ } + + /* Open the requested device. The first time a device is to be + opened we fail with a fatal error if the device does not exists. +@@ -262,8 +279,6 @@ _gcry_rndoldlinux_gather_random (void (* + do + { + nbytes = length < sizeof(buffer)? length : sizeof(buffer); +- if (nbytes > 256) +- nbytes = 256; + _gcry_pre_syscall (); + ret = getentropy (buffer, nbytes); + _gcry_post_syscall (); +Index: libgcrypt-1.10.0/random/rndjent.c +=================================================================== +--- libgcrypt-1.10.0.orig/random/rndjent.c ++++ libgcrypt-1.10.0/random/rndjent.c +@@ -279,13 +279,24 @@ _gcry_rndjent_poll (void (*add)(const vo + if (!jent_rng_is_initialized) + { + /* Auto-initialize. */ +- jent_rng_is_initialized = 1; + jent_entropy_collector_free (jent_rng_collector); + jent_rng_collector = NULL; + if ( !(_gcry_random_read_conf () & RANDOM_CONF_DISABLE_JENT)) + { +- if (!jent_entropy_init ()) +- jent_rng_collector = jent_entropy_collector_alloc (1, 0); ++ if (!jent_entropy_init_ex (1, 0)) ++ { ++ jent_rng_collector = jent_entropy_collector_alloc (1, 0); ++ jent_rng_is_initialized = 1; ++ } ++ } ++ } ++ ++ if (!jent_rng_collector) ++ { ++ if (!jent_entropy_init_ex (1, 0)) ++ { ++ jent_rng_collector = jent_entropy_collector_alloc (1, 0); ++ jent_rng_is_initialized = 1; + } + } + diff --git a/libgcrypt-Fix-the-previous-change.patch b/libgcrypt-Fix-the-previous-change.patch new file mode 100644 index 0000000..4735528 --- /dev/null +++ b/libgcrypt-Fix-the-previous-change.patch @@ -0,0 +1,45 @@ +From b4eb23dc01a40e13d542fbfc5169dffa7fae5677 Mon Sep 17 00:00:00 2001 +From: NIIBE Yutaka +Date: Thu, 19 Dec 2024 14:16:02 +0900 +Subject: [PATCH 13/19] Fix the previous change. +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* cipher/pubkey.c (_gcry_pk_sign_md): Fix memory leak. +(_gcry_pk_verify_md): Likewise. + +-- + +GnuPG-bug-id: 7338 +Signed-off-by: NIIBE Yutaka +Signed-off-by: Lucas Mülling +--- + cipher/pubkey.c | 4 ++-- + 1 file changed, 2 insertions(+), 2 deletions(-) + +diff --git a/cipher/pubkey.c b/cipher/pubkey.c +index 11bf1ec9..4d7743cc 100644 +--- a/cipher/pubkey.c ++++ b/cipher/pubkey.c +@@ -626,7 +626,7 @@ _gcry_pk_sign_md (gcry_sexp_t *r_sig, const char *tmpl, gcry_md_hd_t hd_orig, + else if (!spec->flags.fips && fips_mode ()) + { + if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) +- return GPG_ERR_PUBKEY_ALGO; ++ rc = GPG_ERR_PUBKEY_ALGO; + else + fips_service_indicator_mark_non_compliant (); + } +@@ -708,7 +708,7 @@ _gcry_pk_verify_md (gcry_sexp_t s_sig, const char *tmpl, gcry_md_hd_t hd_orig, + else if (!spec->flags.fips && fips_mode ()) + { + if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) +- return GPG_ERR_PUBKEY_ALGO; ++ rc = GPG_ERR_PUBKEY_ALGO; + else + fips_service_indicator_mark_non_compliant (); + } +-- +2.49.0 + diff --git a/libgcrypt-build-Improve-__thread-specifier-check.patch b/libgcrypt-build-Improve-__thread-specifier-check.patch new file mode 100644 index 0000000..9167adc --- /dev/null +++ b/libgcrypt-build-Improve-__thread-specifier-check.patch @@ -0,0 +1,41 @@ +From 42e8858566e32080aaf818b168f34c698a9ef084 Mon Sep 17 00:00:00 2001 +From: NIIBE Yutaka +Date: Thu, 9 Jan 2025 10:15:50 +0900 +Subject: [PATCH 1/1] build: Improve __thread specifier check. +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* configure.ac (AC_COMPILE_IFELSE __thread): Move the declaration to +global, referring the variable with (void) in main to avoid an error +buidling with -Werror=unused-variable. Don't need to include +stdlib.h. + +-- + +Reported-by: Lucas Mulling +Signed-off-by: NIIBE Yutaka +Signed-off-by: Lucas Mülling +--- + configure.ac | 5 +++-- + 1 file changed, 3 insertions(+), 2 deletions(-) + +diff --git a/configure.ac b/configure.ac +index d708f89a..f38e20c5 100644 +--- a/configure.ac ++++ b/configure.ac +@@ -1495,8 +1495,9 @@ fi + AC_CACHE_CHECK([whether compiler supports '__thread' storage class specifier], + [gcry_cv_gcc_storage_class__thread], + [gcry_cv_gcc_storage_class__thread=no +- AC_COMPILE_IFELSE([AC_LANG_PROGRAM([#include ], +- [static __thread int bar;] ++ AC_COMPILE_IFELSE([AC_LANG_PROGRAM( ++ [[static __thread int bar;]], ++ [[(void)bar;]] + )], + [gcry_cv_gcc_storage_class__thread=yes])]) + if test "$gcry_cv_gcc_storage_class__thread" = "yes" ; then +-- +2.49.0 + diff --git a/libgcrypt-cipher-Add-KAT-for-non-rfc6979-ECDSA-with-fixed-k.patch b/libgcrypt-cipher-Add-KAT-for-non-rfc6979-ECDSA-with-fixed-k.patch new file mode 100644 index 0000000..ff9ae28 --- /dev/null +++ b/libgcrypt-cipher-Add-KAT-for-non-rfc6979-ECDSA-with-fixed-k.patch @@ -0,0 +1,94 @@ +From be57179f42f8a7cb64f72f73ccea753400573b4f Mon Sep 17 00:00:00 2001 +From: Lucas Mulling via Gcrypt-devel +Date: Wed, 26 Feb 2025 12:29:53 -0300 +Subject: [PATCH 02/14] cipher: Add KAT for non-rfc6979 ECDSA with fixed k +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* cipher/ecc.c (run_selftests): Implement KAT for non-deterministic +ECDSA. +* cipher/ecc. (rfc6979_ecdsa_sample_data, rfc6979_ecdsa_sample_data_bad, +rfc6979_ecdsa_data_tmpl): New. + +Signed-off-by: Lucas Mulling +Signed-off-by: Lucas Mülling +--- + cipher/ecc.c | 40 +++++++++++++++++++++++++++++++++++++--- + 1 file changed, 37 insertions(+), 3 deletions(-) + +diff --git a/cipher/ecc.c b/cipher/ecc.c +index 525523ed..d331a014 100644 +--- a/cipher/ecc.c ++++ b/cipher/ecc.c +@@ -93,23 +93,47 @@ static const char ecdsa_sample_secret_key_secp256[] = + /**/ "7903FE1008B8BC99A41AE9E95628BC64F2F1B20C2D7E9F5177A3C294D4462299#)))"; + + /* Sample data from RFC 6979 section A.2.5, hash is of message "sample" */ +-static const char ecdsa_sample_data[] = ++static const char rfc6979_ecdsa_sample_data[] = + "(data (flags rfc6979 prehash)" + " (hash-algo sha256)" + " (value 6:sample))"; + +-static const char ecdsa_sample_data_bad[] = ++static const char rfc6979_ecdsa_sample_data_bad[] = + "(data (flags rfc6979)" + " (hash sha256 #bf2bdbe1aa9b6ec1e2ade1d694f41fc71a831d0268e98915" + /**/ "62113d8a62add1bf#))"; + ++static const char *rfc6979_ecdsa_data_tmpl = ++ "(data (flags rfc6979)" ++ " (hash %s %b))"; ++ ++/* ++ * Sample data from RFC 6979 section A.2.5, with fixed k, ++ * hash is of message "sample". ++ */ ++static const char ecdsa_sample_data[] = ++ "(data (flags raw prehash)" ++ " (label #A6E3C57DD01ABE90086538398355DD4C3B17AA873382B0F24D6129493D8AAD60#)" ++ " (hash-algo sha256)" ++ " (value 6:sample))"; ++ ++static const char ecdsa_sample_data_bad[] = ++ "(data (flags raw)" ++ " (label #A6E3C57DD01ABE90086538398355DD4C3B17AA873382B0F24D6129493D8AAD60#)" ++ " (hash sha256 #bf2bdbe1aa9b6ec1e2ade1d694f41fc71a831d0268e98915" ++ /**/ "62113d8a62add1bf#))"; ++ ++static const char *ecdsa_data_tmpl = ++ "(data (flags raw)" ++ " (label #A6E3C57DD01ABE90086538398355DD4C3B17AA873382B0F24D6129493D8AAD60#)" ++ " (hash %s %b))"; ++ + static const char ecdsa_signature_r[] = + "efd48b2aacb6a8fd1140dd9cd45e81d69d2c877b56aaf991c34d0ea84eaf3716"; + + static const char ecdsa_signature_s[] = + "f7cb1c942d657c41d436c7a1b6e29f65f3e900dbb9aff4064dc4ab2f843acda8"; + +-static const char *ecdsa_data_tmpl = "(data (flags rfc6979) (hash %s %b))"; + /* Sample data from RFC 6979 section A.2.5, hash is of message "sample" */ + static const char ecdsa_sample_data_string[] = "sample"; + static const char ecdsa_sample_data_bad_string[] = "sbmple"; +@@ -2409,6 +2433,16 @@ run_selftests (int algo, int extended, selftest_report_func_t report) + if (r) + return r; + ++ r = selftests_ecc (report, extended, 0, ++ ecdsa_sample_secret_key_secp256, ++ ecdsa_sample_public_key_secp256, ++ rfc6979_ecdsa_sample_data, rfc6979_ecdsa_sample_data_bad, ++ rfc6979_ecdsa_data_tmpl, ++ ecdsa_sample_data_string, ecdsa_sample_data_bad_string, ++ ecdsa_signature_r, ecdsa_signature_s); ++ if (r) ++ return r; ++ + r = selftests_ecc (report, extended, 1, + ed25519_sample_secret_key, + ed25519_sample_public_key, +-- +2.49.0 + diff --git a/libgcrypt-cipher-Check-and-mark-non-compliant-cipher-modes-in-the-SLI.patch b/libgcrypt-cipher-Check-and-mark-non-compliant-cipher-modes-in-the-SLI.patch new file mode 100644 index 0000000..e922808 --- /dev/null +++ b/libgcrypt-cipher-Check-and-mark-non-compliant-cipher-modes-in-the-SLI.patch @@ -0,0 +1,236 @@ +From 9f0fd2656d7d7ba26fcf95cc64d2514ae9ac8ec1 Mon Sep 17 00:00:00 2001 +From: Lucas Mulling +Date: Fri, 24 Jan 2025 09:57:49 -0300 +Subject: [PATCH] cipher: Check and mark non-compliant cipher modes in the SLI +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* cipher/cipher.c (_gcry_cipher_open_internal): Check and mark if the +cipher mode is compliant and reject accordingly. +(_gcry_cipher_is_mode_fips_compliant): New. +* src/gcrypt.h.in (GCRY_FIPS_FLAG_REJECT_CIPHER_MODE): New. +* tests/t-fips-service-ind.c (check_cipher_o_s_e_d_c): Add test to +verify that the service level indication is correctly set for non- +compliant cipher modes, and correctly rejected if +GCRY_FIPS_FLAG_REJECT_CIPHER_MODE is set. + +-- + +GnuPG-bug-id: 7338 +Signed-off-by: Lucas Mulling +Signed-off-by: Lucas Mülling +--- + cipher/cipher.c | 43 ++++++++++++++++++---- + src/gcrypt.h.in | 1 + + tests/t-fips-service-ind.c | 74 +++++++++++++++++++++++++++++++++----- + 3 files changed, 104 insertions(+), 14 deletions(-) + +diff --git a/cipher/cipher.c b/cipher/cipher.c +index 74dc2df7..b5420671 100644 +--- a/cipher/cipher.c ++++ b/cipher/cipher.c +@@ -504,6 +504,26 @@ _gcry_cipher_open (gcry_cipher_hd_t *handle, + return rc; + } + ++int ++_gcry_cipher_is_mode_fips_compliant(int mode) ++{ ++ switch (mode) ++ { ++ case GCRY_CIPHER_MODE_ECB: ++ case GCRY_CIPHER_MODE_CBC: ++ case GCRY_CIPHER_MODE_CFB: ++ case GCRY_CIPHER_MODE_CFB8: ++ case GCRY_CIPHER_MODE_OFB: ++ case GCRY_CIPHER_MODE_CTR: ++ case GCRY_CIPHER_MODE_CCM: ++ case GCRY_CIPHER_MODE_XTS: ++ case GCRY_CIPHER_MODE_AESWRAP: ++ return GPG_ERR_NO_ERROR; ++ default: ++ return GPG_ERR_NOT_SUPPORTED; ++ } ++} ++ + + gcry_err_code_t + _gcry_cipher_open_internal (gcry_cipher_hd_t *handle, +@@ -523,14 +543,25 @@ _gcry_cipher_open_internal (gcry_cipher_hd_t *handle, + err = GPG_ERR_CIPHER_ALGO; + else if (spec->flags.disabled) + err = GPG_ERR_CIPHER_ALGO; +- else if (!spec->flags.fips && fips_mode ()) ++ else if (fips_mode ()) + { +- if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_CIPHER)) +- err = GPG_ERR_CIPHER_ALGO; +- else ++ if (!spec->flags.fips) + { +- fips_service_indicator_mark_non_compliant (); +- err = 0; ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_CIPHER)) ++ err = GPG_ERR_CIPHER_ALGO; ++ else ++ { ++ fips_service_indicator_mark_non_compliant (); ++ err = 0; ++ } ++ } ++ else if ((err = _gcry_cipher_is_mode_fips_compliant(mode))) ++ { ++ if (!fips_check_rejection (GCRY_FIPS_FLAG_REJECT_CIPHER_MODE)) ++ { ++ fips_service_indicator_mark_non_compliant (); ++ err = 0; ++ } + } + } + else +diff --git a/src/gcrypt.h.in b/src/gcrypt.h.in +index fcb6a327..1a6f7269 100644 +--- a/src/gcrypt.h.in ++++ b/src/gcrypt.h.in +@@ -1988,6 +1988,7 @@ char *gcry_get_config (int mode, const char *what); + #define GCRY_FIPS_FLAG_REJECT_PK (1 << 5) + #define GCRY_FIPS_FLAG_REJECT_PK_MD (1 << 6) + #define GCRY_FIPS_FLAG_REJECT_PK_GOST_SM2 (1 << 7) ++#define GCRY_FIPS_FLAG_REJECT_CIPHER_MODE (1 << 8) + + #define GCRY_FIPS_FLAG_REJECT_MD \ + (GCRY_FIPS_FLAG_REJECT_MD_MD5 | GCRY_FIPS_FLAG_REJECT_MD_OTHERS) +diff --git a/tests/t-fips-service-ind.c b/tests/t-fips-service-ind.c +index fe963fa5..74521bb3 100644 +--- a/tests/t-fips-service-ind.c ++++ b/tests/t-fips-service-ind.c +@@ -606,27 +606,41 @@ check_cipher_o_s_e_d_c (int reject) + { + static struct { + int algo; ++ int mode; + const char *key; + int keylen; ++ const char *tag; ++ int taglen; + const char *expect; + int expect_failure; + } tv[] = { + #if USE_DES +- { GCRY_CIPHER_3DES, +- "\xe3\x34\x7a\x6b\x0b\xc1\x15\x2c\x64\x2a\x25\xcb\xd3\xbc\x31\xab" +- "\xfb\xa1\x62\xa8\x1f\x19\x7c\x15", 24, +- "\x3f\x1a\xb8\x83\x18\x8b\xb5\x97", 1 }, ++ { GCRY_CIPHER_3DES, GCRY_CIPHER_MODE_ECB, ++ "\xe3\x34\x7a\x6b\x0b\xc1\x15\x2c\x64\x2a\x25\xcb\xd3\xbc\x31\xab" ++ "\xfb\xa1\x62\xa8\x1f\x19\x7c\x15", 24, ++ "", -1, ++ "\x3f\x1a\xb8\x83\x18\x8b\xb5\x97", 1 }, + #endif +- { GCRY_CIPHER_AES, +- "\x2b\x7e\x15\x16\x28\xae\xd2\xa6\xab\xf7\x15\x88\x09\xcf\x4f\x3c", 16, +- "\x5c\x71\xd8\x5d\x26\x5e\xcd\xb5\x95\x40\x41\xab\xff\x25\x6f\xd1" } ++ { GCRY_CIPHER_AES, GCRY_CIPHER_MODE_ECB, ++ "\x2b\x7e\x15\x16\x28\xae\xd2\xa6\xab\xf7\x15\x88\x09\xcf\x4f\x3c", 16, ++ "", -1, ++ "\x5c\x71\xd8\x5d\x26\x5e\xcd\xb5\x95\x40\x41\xab\xff\x25\x6f\xd1" }, ++ { GCRY_CIPHER_AES128, GCRY_CIPHER_MODE_SIV, ++ "\xff\xfe\xfd\xfc\xfb\xfa\xf9\xf8\xf7\xf6\xf5\xf4\xf3\xf2\xf1\xf0" ++ "\xf0\xf1\xf2\xf3\xf4\xf5\xf6\xf7\xf8\xf9\xfa\xfb\xfc\xfd\xfe\xff", 32, ++ "\x51\x66\x54\xc4\xe1\xb5\xd9\x37\x31\x52\xdb\xea\x35\x10\x8b\x7b", 16, ++ "\x83\x69\xf6\xf3\x20\xff\xa2\x72\x31\x67\x15\xcf\xf4\x75\x01\x9a", 1 } + }; ++ + const char *pt = "Shohei Ohtani 2024: 54 HR, 59 SB"; + int ptlen; + int tvidx; + unsigned char out[MAX_DATA_LEN]; + gpg_error_t err; + ++ unsigned char tag[16]; ++ size_t taglen = 0; ++ + ptlen = strlen (pt); + assert (ptlen == 32); + for (tvidx=0; tvidx < DIM(tv); tvidx++) +@@ -640,10 +654,12 @@ check_cipher_o_s_e_d_c (int reject) + tvidx); + + blklen = gcry_cipher_get_algo_blklen (tv[tvidx].algo); ++ + assert (blklen != 0); + assert (blklen <= ptlen); + assert (blklen <= DIM (out)); +- err = gcry_cipher_open (&h, tv[tvidx].algo, GCRY_CIPHER_MODE_ECB, 0); ++ assert (tv[tvidx].taglen <= 16); ++ err = gcry_cipher_open (&h, tv[tvidx].algo, tv[tvidx].mode, 0); + if (err) + { + if (in_fips_mode && reject && tv[tvidx].expect_failure) +@@ -694,6 +710,18 @@ check_cipher_o_s_e_d_c (int reject) + continue; + } + ++ if (tv[tvidx].taglen >= 0) ++ { ++ err = gcry_cipher_info (h, GCRYCTL_GET_TAGLEN, NULL, &taglen); ++ if (err) ++ fail ("gcry_cipher_info %d failed: %s\n", tvidx, ++ gpg_strerror (err)); ++ ++ if (taglen != tv[tvidx].taglen) ++ fail ("gcry_cipher_info %d failed: taglen mismatch %d != %ld\n", tvidx, ++ tv[tvidx].taglen, taglen); ++ } ++ + err = gcry_cipher_encrypt (h, out, MAX_DATA_LEN, pt, blklen); + if (err) + { +@@ -714,6 +742,35 @@ check_cipher_o_s_e_d_c (int reject) + putc ('\n', stderr); + } + ++ if (tv[tvidx].taglen >= 0) ++ { ++ err = gcry_cipher_gettag (h, tag, tv[tvidx].taglen); ++ if (err) ++ fail ("gcry_cipher_gettag %d failed: %s", tvidx, ++ gpg_strerror(err)); ++ ++ if (memcmp (tv[tvidx].tag, tag, tv[tvidx].taglen)) ++ { ++ int i; ++ ++ fail ("gcry_cipher_gettag %d: tag mismatch\n", tvidx); ++ fputs ("got:", stderr); ++ for (i=0; i < 16 ; i++) ++ fprintf (stderr, " %02x", tag[i]); ++ putc ('\n', stderr); ++ } ++ ++ err = gcry_cipher_reset (h); ++ if (err) ++ fail("gcry_cipher_reset %d failed: %s", tvidx, ++ gpg_strerror(err)); ++ ++ err = gcry_cipher_set_decryption_tag (h, tag, 16); ++ if (err) ++ fail ("gcry_cipher_set_decryption_tag %d failed: %s\n", tvidx< ++ gpg_strerror (err)); ++ } ++ + err = gcry_cipher_decrypt (h, out, blklen, NULL, 0); + if (err) + { +@@ -1483,6 +1540,7 @@ main (int argc, char **argv) + + xgcry_control ((GCRYCTL_FIPS_REJECT_NON_FIPS, + (GCRY_FIPS_FLAG_REJECT_MD_MD5 ++ | GCRY_FIPS_FLAG_REJECT_CIPHER_MODE + | GCRY_FIPS_FLAG_REJECT_PK_MD + | GCRY_FIPS_FLAG_REJECT_PK_GOST_SM2 + | GCRY_FIPS_FLAG_REJECT_COMPAT110))); +-- +2.49.0 + diff --git a/libgcrypt-cipher-Differentiate-igninvflag-in-the-SLI.patch b/libgcrypt-cipher-Differentiate-igninvflag-in-the-SLI.patch new file mode 100644 index 0000000..7763815 --- /dev/null +++ b/libgcrypt-cipher-Differentiate-igninvflag-in-the-SLI.patch @@ -0,0 +1,40 @@ +From 3bdb59c21b77711cf7d44d692a7a02f5f469033e Mon Sep 17 00:00:00 2001 +From: Lucas Mulling via Gcrypt-devel +Date: Wed, 26 Feb 2025 17:19:22 -0300 +Subject: [PATCH 04/14] cipher: Differentiate igninvflag in the SLI +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* cipher/pubkey-util.c (_gcry_pk_util_parse_flaglist): Differentiate use +of igninvflag. + +GnuPG-bug-id: 7338 +Signed-off-by: Lucas Mulling +Signed-off-by: Lucas Mülling +--- + cipher/pubkey-util.c | 8 ++++++++ + 1 file changed, 8 insertions(+) + +diff --git a/cipher/pubkey-util.c b/cipher/pubkey-util.c +index 68defea6..9c927638 100644 +--- a/cipher/pubkey-util.c ++++ b/cipher/pubkey-util.c +@@ -200,6 +200,14 @@ _gcry_pk_util_parse_flaglist (gcry_sexp_t list, + } + } + ++ if (fips_mode () && igninvflag) ++ { ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) ++ rc = GPG_ERR_INV_FLAG; ++ else ++ fips_service_indicator_mark_non_compliant (); ++ } ++ + if (r_flags) + *r_flags = flags; + if (r_encoding) +-- +2.49.0 + diff --git a/libgcrypt-cipher-Differentiate-no-blinding-flag-in-the-SLI.patch b/libgcrypt-cipher-Differentiate-no-blinding-flag-in-the-SLI.patch new file mode 100644 index 0000000..92b9073 --- /dev/null +++ b/libgcrypt-cipher-Differentiate-no-blinding-flag-in-the-SLI.patch @@ -0,0 +1,70 @@ +From cc0a40bd74120dc06fd80f163b30abb91f60b63b Mon Sep 17 00:00:00 2001 +From: Lucas Mulling via Gcrypt-devel +Date: Wed, 26 Feb 2025 17:19:23 -0300 +Subject: [PATCH 05/14] cipher: Differentiate no-blinding flag in the SLI +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* cipher/rsa.c (rsa_decrypt, rsa_encrypt): Differentiate use of flag +no-blinding in the service level indicator. + +GnuPG-bug-id: 7338 +Signed-off-by: Lucas Mulling +Signed-off-by: Lucas Mülling +--- + cipher/rsa.c | 30 ++++++++++++++++++++++++++++-- + 1 file changed, 28 insertions(+), 2 deletions(-) + +diff --git a/cipher/rsa.c b/cipher/rsa.c +index c1329644..dce76414 100644 +--- a/cipher/rsa.c ++++ b/cipher/rsa.c +@@ -1501,7 +1501,19 @@ rsa_decrypt (gcry_sexp_t *r_plain, gcry_sexp_t s_data, gcry_sexp_t keyparms) + be practically mounted over the network as shown by Brumley and + Boney in 2003. */ + if ((ctx.flags & PUBKEY_FLAG_NO_BLINDING)) +- secret (plain, data, &sk); ++ { ++ if (fips_mode ()) ++ { ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) ++ { ++ rc = GPG_ERR_INV_FLAG; ++ goto leave; ++ } ++ else ++ fips_service_indicator_mark_non_compliant (); ++ } ++ secret (plain, data, &sk); ++ } + else + secret_blinded (plain, data, &sk, nbits); + +@@ -1632,8 +1644,22 @@ rsa_sign (gcry_sexp_t *r_sig, gcry_sexp_t s_data, gcry_sexp_t keyparms) + + /* Do RSA computation. */ + sig = mpi_new (0); ++ + if ((ctx.flags & PUBKEY_FLAG_NO_BLINDING)) +- secret (sig, data, &sk); ++ { ++ if (fips_mode ()) ++ { ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) ++ { ++ rc = GPG_ERR_INV_FLAG; ++ goto leave; ++ } ++ else ++ fips_service_indicator_mark_non_compliant (); ++ } ++ ++ secret (sig, data, &sk); ++ } + else + secret_blinded (sig, data, &sk, nbits); + if (DBG_CIPHER) +-- +2.49.0 + diff --git a/libgcrypt-cipher-Differentiate-use-of-label-K-in-the-SLI.patch b/libgcrypt-cipher-Differentiate-use-of-label-K-in-the-SLI.patch new file mode 100644 index 0000000..a054b64 --- /dev/null +++ b/libgcrypt-cipher-Differentiate-use-of-label-K-in-the-SLI.patch @@ -0,0 +1,139 @@ +From 2f6d2db1a4c28775a568c1f81ca127d2daebaf1c Mon Sep 17 00:00:00 2001 +From: Lucas Mulling via Gcrypt-devel +Date: Wed, 26 Feb 2025 12:29:54 -0300 +Subject: [PATCH 03/14] cipher: Differentiate use of label K in the SLI +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* cipher/ecc.c (ecc_sign, ecc_verify): Use of label K is not allowed in +fips mode, differentiate with the GCRY_FIPS_FLAG_REJECT_PK_ECC_K flag. +* src/gcrypt.h.in: New GCRY_FIPS_FLAG_REJECT_PK_ECC_K. +* tests/t-fips-service-ind.c (check_pk_hash_sign_verify): Mark non +compliant use of label. + +Signed-off-by: Lucas Mulling +Signed-off-by: Lucas Mülling +--- + cipher/ecc.c | 26 +++++++++++++++++++++++++- + src/gcrypt.h.in | 2 ++ + tests/t-fips-service-ind.c | 11 ++++++----- + 3 files changed, 33 insertions(+), 6 deletions(-) + +diff --git a/cipher/ecc.c b/cipher/ecc.c +index d331a014..569e41f6 100644 +--- a/cipher/ecc.c ++++ b/cipher/ecc.c +@@ -961,7 +961,16 @@ ecc_sign (gcry_sexp_t *r_sig, gcry_sexp_t s_data, gcry_sexp_t keyparms) + log_mpidump ("ecc_sign data", data); + + if (ctx.label) +- rc = _gcry_mpi_scan (&k, GCRYMPI_FMT_USG, ctx.label, ctx.labellen, NULL); ++ { ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK_ECC_K)) ++ { ++ rc = GPG_ERR_INV_DATA; ++ goto leave; ++ } ++ else ++ fips_service_indicator_mark_non_compliant (); ++ rc = _gcry_mpi_scan (&k, GCRYMPI_FMT_USG, ctx.label, ctx.labellen, NULL); ++ } + if (rc) + goto leave; + +@@ -1118,6 +1127,21 @@ ecc_verify (gcry_sexp_t s_sig, gcry_sexp_t s_data, gcry_sexp_t s_keyparms) + rc = _gcry_pk_util_data_to_mpi (s_data, &data, &ctx); + if (rc) + goto leave; ++ ++ if (ctx.label) ++ { ++ if (fips_mode ()) ++ { ++ if(fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK_ECC_K)) ++ { ++ rc = GPG_ERR_INV_DATA; ++ goto leave; ++ } ++ else ++ fips_service_indicator_mark_non_compliant (); ++ } ++ } ++ + if (DBG_CIPHER) + log_mpidump ("ecc_verify data", data); + +diff --git a/src/gcrypt.h.in b/src/gcrypt.h.in +index 1a6f7269..fe3db16a 100644 +--- a/src/gcrypt.h.in ++++ b/src/gcrypt.h.in +@@ -1989,6 +1989,8 @@ char *gcry_get_config (int mode, const char *what); + #define GCRY_FIPS_FLAG_REJECT_PK_MD (1 << 6) + #define GCRY_FIPS_FLAG_REJECT_PK_GOST_SM2 (1 << 7) + #define GCRY_FIPS_FLAG_REJECT_CIPHER_MODE (1 << 8) ++/**/ ++#define GCRY_FIPS_FLAG_REJECT_PK_ECC_K (1 << 10) + + #define GCRY_FIPS_FLAG_REJECT_MD \ + (GCRY_FIPS_FLAG_REJECT_MD_MD5 | GCRY_FIPS_FLAG_REJECT_MD_OTHERS) +diff --git a/tests/t-fips-service-ind.c b/tests/t-fips-service-ind.c +index a082b258..0ece55b8 100644 +--- a/tests/t-fips-service-ind.c ++++ b/tests/t-fips-service-ind.c +@@ -728,7 +728,7 @@ check_pk_hash_sign_verify (void) + "ce4014c68811f9a21a1fdb2c0e6113e06db7ca93b7404e78dc7ccd5ca89a4ca9#)))", + "(data(flags raw)(hash %s %b)(label %b))", + "94a1bbb14b906a61a280f245f9e93c7f3b4a6247824f5d33b9670787642a68de", +- 0, 0 ++ 1, 0, + } + }; + int tvidx; +@@ -827,7 +827,7 @@ check_pk_hash_sign_verify (void) + if (ec == GPG_ERR_INV_OP) + { + /* libgcrypt is old, no support of the FIPS service indicator. */ +- fail ("gcry_pk_hash test %d unexpectedly failed to check the FIPS service indicator.\n", ++ fail ("gcry_pk_hash_sign test %d unexpectedly failed to check the FIPS service indicator.\n", + tvidx); + goto next; + } +@@ -835,7 +835,7 @@ check_pk_hash_sign_verify (void) + if (in_fips_mode && !tv[tvidx].expect_failure && ec) + { + /* Success with the FIPS service indicator == 0 expected, but != 0. */ +- fail ("gcry_pk_hash test %d unexpectedly set the indicator in FIPS mode.\n", ++ fail ("gcry_pk_hash_sign test %d unexpectedly set the indicator in FIPS mode.\n", + tvidx); + goto next; + } +@@ -859,7 +859,7 @@ check_pk_hash_sign_verify (void) + if (ec == GPG_ERR_INV_OP) + { + /* libgcrypt is old, no support of the FIPS service indicator. */ +- fail ("gcry_pk_hash test %d unexpectedly failed to check the FIPS service indicator.\n", ++ fail ("gcry_pk_hash_verify test %d unexpectedly failed to check the FIPS service indicator.\n", + tvidx); + goto next; + } +@@ -867,7 +867,7 @@ check_pk_hash_sign_verify (void) + if (in_fips_mode && !tv[tvidx].expect_failure && ec) + { + /* Success with the FIPS service indicator == 0 expected, but != 0. */ +- fail ("gcry_pk_hash test %d unexpectedly set the indicator in FIPS mode.\n", ++ fail ("gcry_pk_hash_verify test %d unexpectedly set the indicator in FIPS mode.\n", + tvidx); + goto next; + } +@@ -1834,6 +1834,7 @@ main (int argc, char **argv) + | GCRY_FIPS_FLAG_REJECT_CIPHER_MODE + | GCRY_FIPS_FLAG_REJECT_PK_MD + | GCRY_FIPS_FLAG_REJECT_PK_GOST_SM2 ++ | GCRY_FIPS_FLAG_REJECT_PK_ECC_K + | GCRY_FIPS_FLAG_REJECT_COMPAT110))); + + check_md_o_w_r_c (1); +-- +2.49.0 + diff --git a/libgcrypt-cipher-Don-t-differentiate-GCRY_CIPHER_MODE_CMAC-in-FIPS-mode.patch b/libgcrypt-cipher-Don-t-differentiate-GCRY_CIPHER_MODE_CMAC-in-FIPS-mode.patch new file mode 100644 index 0000000..fc8d335 --- /dev/null +++ b/libgcrypt-cipher-Don-t-differentiate-GCRY_CIPHER_MODE_CMAC-in-FIPS-mode.patch @@ -0,0 +1,98 @@ +From 608ff4b2261e2d8961f0ef4189e74b1173b2802c Mon Sep 17 00:00:00 2001 +From: Lucas Mulling +Date: Sun, 2 Feb 2025 12:58:21 -0300 +Subject: [PATCH 2/2] cipher: Don't differentiate GCRY_CIPHER_MODE_CMAC in FIPS + mode. +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* cipher/cipher.c (_gcry_cipher_mode_fips_compliance): Allow +GCRY_CIPHER_MODE_CMAC in fips mode. +* cipher/cipher.c (cipher_modes_fips_compliance) +(cipher_int_modes_fips_compliance): New. +-- + +Signed-off-by: Lucas Mulling + +Added some comments, changed scope of the new functions and shorted +their names. Also added restructured the switch and added all other +modes. + +Signed-off-by: Werner Koch +Signed-off-by: Lucas Mülling +--- + cipher/cipher.c | 49 ++++++++++++++++++++++++++++++++++++++++++++----- + 1 file changed, 44 insertions(+), 5 deletions(-) + +diff --git a/cipher/cipher.c b/cipher/cipher.c +index 3b7970b3..fc130907 100644 +--- a/cipher/cipher.c ++++ b/cipher/cipher.c +@@ -505,8 +505,9 @@ _gcry_cipher_open (gcry_cipher_hd_t *handle, + } + + +-gcry_err_code_t +-_gcry_cipher_mode_fips_compliance (enum gcry_cipher_modes mode) ++/* Return an error if the give cipher mode is non-FIPS compliant. */ ++static gcry_err_code_t ++cipher_modes_fips_compliance (enum gcry_cipher_modes mode) + { + switch (mode) + { +@@ -519,10 +520,48 @@ _gcry_cipher_mode_fips_compliance (enum gcry_cipher_modes mode) + case GCRY_CIPHER_MODE_CCM: + case GCRY_CIPHER_MODE_XTS: + case GCRY_CIPHER_MODE_AESWRAP: +- return GPG_ERR_NO_ERROR; +- default: +- return GPG_ERR_NOT_SUPPORTED; ++ return 0; ++ case GCRY_CIPHER_MODE_NONE: ++ case GCRY_CIPHER_MODE_STREAM: ++ case GCRY_CIPHER_MODE_GCM: ++ case GCRY_CIPHER_MODE_POLY1305: ++ case GCRY_CIPHER_MODE_OCB: ++ case GCRY_CIPHER_MODE_EAX: ++ case GCRY_CIPHER_MODE_SIV: ++ case GCRY_CIPHER_MODE_GCM_SIV: ++ break; + } ++ return GPG_ERR_NOT_SUPPORTED; ++} ++ ++ ++/* This is similar to cipher_modes_fips_compliance but only for the ++ * internal modes (i.e. CMAC). Return an error if the mode is ++ * non-FIPS compliant. */ ++static gcry_err_code_t ++cipher_int_modes_fips_compliance (enum gcry_cipher_internal_modes mode) ++{ ++ switch (mode) ++ { ++ case GCRY_CIPHER_MODE_INTERNAL: ++ break; ++ case GCRY_CIPHER_MODE_CMAC: ++ return 0; ++ } ++ return GPG_ERR_NOT_SUPPORTED; ++} ++ ++ ++/* Return an error if the give cipher mode is non-FIPS compliant. The ++ * mode is not an enum here so that we can use it for real modes and ++ * for internal modes. */ ++gcry_err_code_t ++_gcry_cipher_mode_fips_compliance (int mode) ++{ ++ if (mode >= GCRY_CIPHER_MODE_INTERNAL) ++ return cipher_int_modes_fips_compliance (mode); ++ else ++ return cipher_modes_fips_compliance (mode); + } + + +-- +2.49.0 + diff --git a/libgcrypt-cipher-Rename-_gcry_cipher_is_mode_fips_compliant.patch b/libgcrypt-cipher-Rename-_gcry_cipher_is_mode_fips_compliant.patch new file mode 100644 index 0000000..e98f6ab --- /dev/null +++ b/libgcrypt-cipher-Rename-_gcry_cipher_is_mode_fips_compliant.patch @@ -0,0 +1,64 @@ +From 6b0fbb7e5e0da77787e3a87d74359ee21c44904e Mon Sep 17 00:00:00 2001 +From: Lucas Mulling +Date: Tue, 28 Jan 2025 13:45:39 -0300 +Subject: [PATCH 1/2] cipher: Rename _gcry_cipher_is_mode_fips_compliant +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* cipher/cipher.c (_gcry_cipher_is_mode_fips_compliant): Rename to +_gcry_cipher_mode_fips_compliance for better clarity and change the +return type to gcry_err_code_t. +* cipher/cipher.c (_gcry_cipher_mode_fips_compliance): Use +gcry_cipher_modes instead of int for mode. +* tests/t-fips-service-ind.c (check_cipher_o_s_e_d_c): Fix typo in fail. +-- + +Signed-off-by: Lucas Mulling +Signed-off-by: Lucas Mülling +--- + cipher/cipher.c | 7 ++++--- + tests/t-fips-service-ind.c | 2 +- + 2 files changed, 5 insertions(+), 4 deletions(-) + +diff --git a/cipher/cipher.c b/cipher/cipher.c +index b5420671..3b7970b3 100644 +--- a/cipher/cipher.c ++++ b/cipher/cipher.c +@@ -504,8 +504,9 @@ _gcry_cipher_open (gcry_cipher_hd_t *handle, + return rc; + } + +-int +-_gcry_cipher_is_mode_fips_compliant(int mode) ++ ++gcry_err_code_t ++_gcry_cipher_mode_fips_compliance (enum gcry_cipher_modes mode) + { + switch (mode) + { +@@ -555,7 +556,7 @@ _gcry_cipher_open_internal (gcry_cipher_hd_t *handle, + err = 0; + } + } +- else if ((err = _gcry_cipher_is_mode_fips_compliant(mode))) ++ else if ((err = _gcry_cipher_mode_fips_compliance (mode))) + { + if (!fips_check_rejection (GCRY_FIPS_FLAG_REJECT_CIPHER_MODE)) + { +diff --git a/tests/t-fips-service-ind.c b/tests/t-fips-service-ind.c +index 74521bb3..ed5f8d3f 100644 +--- a/tests/t-fips-service-ind.c ++++ b/tests/t-fips-service-ind.c +@@ -767,7 +767,7 @@ check_cipher_o_s_e_d_c (int reject) + + err = gcry_cipher_set_decryption_tag (h, tag, 16); + if (err) +- fail ("gcry_cipher_set_decryption_tag %d failed: %s\n", tvidx< ++ fail ("gcry_cipher_set_decryption_tag %d failed: %s\n", tvidx, + gpg_strerror (err)); + } + +-- +2.49.0 + diff --git a/libgcrypt-cipher-ecc-Fix-for-supplied-K.patch b/libgcrypt-cipher-ecc-Fix-for-supplied-K.patch new file mode 100644 index 0000000..743468d --- /dev/null +++ b/libgcrypt-cipher-ecc-Fix-for-supplied-K.patch @@ -0,0 +1,88 @@ +From 755e6dce727915249cbb1a98f22832d940b99c24 Mon Sep 17 00:00:00 2001 +From: NIIBE Yutaka +Date: Thu, 6 Mar 2025 09:12:36 +0900 +Subject: [PATCH 07/14] cipher,ecc: Fix for supplied K. +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* cipher/ecc.c (ecc_sign): Check if it's under FIPS mode. +(ecc_verify): Supplied K does no sense for verification, but add +comment of clarification mark/reject-ing under FIPS mode. + +-- + +GnuPG-bug-id: 7338 +Signed-off-by: NIIBE Yutaka +Signed-off-by: Lucas Mülling +--- + cipher/ecc.c | 39 +++++++++++++++++++++++---------------- + 1 file changed, 23 insertions(+), 16 deletions(-) + +diff --git a/cipher/ecc.c b/cipher/ecc.c +index 569e41f6..a165bb7a 100644 +--- a/cipher/ecc.c ++++ b/cipher/ecc.c +@@ -962,17 +962,21 @@ ecc_sign (gcry_sexp_t *r_sig, gcry_sexp_t s_data, gcry_sexp_t keyparms) + + if (ctx.label) + { +- if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK_ECC_K)) ++ /* ECDSA signing can have supplied K (for testing, deterministic). */ ++ if (fips_mode ()) + { +- rc = GPG_ERR_INV_DATA; +- goto leave; ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK_ECC_K)) ++ { ++ rc = GPG_ERR_INV_DATA; ++ goto leave; ++ } ++ else ++ fips_service_indicator_mark_non_compliant (); + } +- else +- fips_service_indicator_mark_non_compliant (); + rc = _gcry_mpi_scan (&k, GCRYMPI_FMT_USG, ctx.label, ctx.labellen, NULL); ++ if (rc) ++ goto leave; + } +- if (rc) +- goto leave; + + if (fips_mode () + && ((ctx.flags & PUBKEY_FLAG_GOST) || (ctx.flags & PUBKEY_FLAG_SM2))) +@@ -1128,18 +1132,21 @@ ecc_verify (gcry_sexp_t s_sig, gcry_sexp_t s_data, gcry_sexp_t s_keyparms) + if (rc) + goto leave; + +- if (ctx.label) ++ /* ++ * ECDSA signing can have supplied K (for testing, deterministic), ++ * but it's non-compliant. For ECDSA signature verification, having ++ * K is irrelevant, but an application may use same flags as the one ++ * for signing. ++ */ ++ if (ctx.label && fips_mode ()) + { +- if (fips_mode ()) ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK_ECC_K)) + { +- if(fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK_ECC_K)) +- { +- rc = GPG_ERR_INV_DATA; +- goto leave; +- } +- else +- fips_service_indicator_mark_non_compliant (); ++ rc = GPG_ERR_INV_DATA; ++ goto leave; + } ++ else ++ fips_service_indicator_mark_non_compliant (); + } + + if (DBG_CIPHER) +-- +2.49.0 + diff --git a/libgcrypt-cipher-fips-Fix-for-random-override.patch b/libgcrypt-cipher-fips-Fix-for-random-override.patch new file mode 100644 index 0000000..076f66f --- /dev/null +++ b/libgcrypt-cipher-fips-Fix-for-random-override.patch @@ -0,0 +1,83 @@ +From ca8bf05e111b41e482a2a4b34cda6bcf5aa1f27e Mon Sep 17 00:00:00 2001 +From: NIIBE Yutaka +Date: Thu, 6 Mar 2025 09:45:36 +0900 +Subject: [PATCH 09/14] cipher,fips: Fix for random-override. +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* cipher/pubkey-util.c (gcry_pk_util_data_to_mpi): Keep +the behavior of 1.10. +* src/visibility.c (gcry_pk_random_override_new): Likewise. +* tests/t-fips-service-ind.c (main): Use GCRY_FIPS_FLAG_REJECT_PK_FLAGS. + +-- + +GnuPG-bug-id: 7338 +Signed-off-by: NIIBE Yutaka +Signed-off-by: Lucas Mülling +--- + cipher/pubkey-util.c | 6 +++--- + src/visibility.c | 2 +- + tests/t-fips-service-ind.c | 1 + + 3 files changed, 5 insertions(+), 4 deletions(-) + +diff --git a/cipher/pubkey-util.c b/cipher/pubkey-util.c +index 66a04f13..0e67f892 100644 +--- a/cipher/pubkey-util.c ++++ b/cipher/pubkey-util.c +@@ -975,7 +975,7 @@ _gcry_pk_util_data_to_mpi (gcry_sexp_t input, gcry_mpi_t *ret_mpi, + { + if (fips_mode ()) + { +- if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK_FLAGS)) + { + sexp_release (list); + rc = GPG_ERR_INV_FLAG; +@@ -1162,7 +1162,7 @@ _gcry_pk_util_data_to_mpi (gcry_sexp_t input, gcry_mpi_t *ret_mpi, + { + if (fips_mode ()) + { +- if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK_FLAGS)) + { + sexp_release (list); + rc = GPG_ERR_INV_FLAG; +@@ -1272,7 +1272,7 @@ _gcry_pk_util_data_to_mpi (gcry_sexp_t input, gcry_mpi_t *ret_mpi, + { + if (fips_mode ()) + { +- if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK_FLAGS)) + { + sexp_release (list); + rc = GPG_ERR_INV_FLAG; +diff --git a/src/visibility.c b/src/visibility.c +index ccd0de69..edb972bc 100644 +--- a/src/visibility.c ++++ b/src/visibility.c +@@ -1091,7 +1091,7 @@ gcry_pk_random_override_new (gcry_ctx_t *r_ctx, const unsigned char *p, size_t l + + if (fips_mode ()) + { +- if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK_FLAGS)) + return gpg_error (GPG_ERR_INV_OP); + else + fips_service_indicator_mark_non_compliant (); +diff --git a/tests/t-fips-service-ind.c b/tests/t-fips-service-ind.c +index 0ece55b8..0a270b38 100644 +--- a/tests/t-fips-service-ind.c ++++ b/tests/t-fips-service-ind.c +@@ -1835,6 +1835,7 @@ main (int argc, char **argv) + | GCRY_FIPS_FLAG_REJECT_PK_MD + | GCRY_FIPS_FLAG_REJECT_PK_GOST_SM2 + | GCRY_FIPS_FLAG_REJECT_PK_ECC_K ++ | GCRY_FIPS_FLAG_REJECT_PK_FLAGS + | GCRY_FIPS_FLAG_REJECT_COMPAT110))); + + check_md_o_w_r_c (1); +-- +2.49.0 + diff --git a/libgcrypt-cipher-rsa-Mark-reject-SHA1-unknown-with-RSA-signature-generation.patch b/libgcrypt-cipher-rsa-Mark-reject-SHA1-unknown-with-RSA-signature-generation.patch new file mode 100644 index 0000000..7ff18ce --- /dev/null +++ b/libgcrypt-cipher-rsa-Mark-reject-SHA1-unknown-with-RSA-signature-generation.patch @@ -0,0 +1,445 @@ +From 60e5039793c2474d29ded039cf1a6b8107733a20 Mon Sep 17 00:00:00 2001 +From: NIIBE Yutaka +Date: Fri, 21 Feb 2025 14:24:41 +0900 +Subject: [PATCH] cipher:rsa: Mark/reject SHA1/unknown with RSA signature + generation. +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* cipher/rsa-common.c (_gcry_rsa_pkcs1_encode_raw_for_sig): We can't +determine if it's compliant when raw PKCS1 encoding is used. +(_gcry_rsa_pss_encode): Add the behavior of marking non-compliant use. +(_gcry_rsa_pss_verify): Likewise. +* cipher/rsa.c (rsa_sign): Handle the check for SHA1. +(rsa_verify): Likewise. +* tests/t-fips-service-ind.c (check_pk_s_v): Add use cases for RSA +and Ed25519. + +-- + +GnuPG-bug-id: 7338 +Signed-off-by: NIIBE Yutaka +Signed-off-by: Lucas Mülling +--- + cipher/rsa-common.c | 28 +++- + cipher/rsa.c | 34 +++++ + tests/t-fips-service-ind.c | 290 ++++++++++++++++++++++++++++++++++++- + 3 files changed, 347 insertions(+), 5 deletions(-) + +diff --git a/cipher/rsa-common.c b/cipher/rsa-common.c +index 1920eedd..c1d2dcd5 100644 +--- a/cipher/rsa-common.c ++++ b/cipher/rsa-common.c +@@ -380,6 +380,16 @@ _gcry_rsa_pkcs1_encode_raw_for_sig (gcry_mpi_t *r_result, unsigned int nbits, + int i; + size_t n; + ++ /* With RAW encoding, we can't know if the hash used is compliant or ++ * not. Reject or mark it's non-compliant. */ ++ if (fips_mode ()) ++ { ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK_MD)) ++ return GPG_ERR_DIGEST_ALGO; ++ else ++ fips_service_indicator_mark_non_compliant (); ++ } ++ + if ( !valuelen || valuelen + 4 > nframe) + { + /* Can't encode an DLEN byte digest MD into an NFRAME byte +@@ -840,8 +850,13 @@ _gcry_rsa_pss_encode (gcry_mpi_t *r_result, unsigned int nbits, int algo, + /* The FIPS 186-4 Section 5.5 allows only 0 <= sLen <= hLen */ + if (fips_mode () && saltlen > hlen) + { +- rc = GPG_ERR_INV_ARG; +- goto leave; ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) ++ { ++ rc = GPG_ERR_INV_ARG; ++ goto leave; ++ } ++ else ++ fips_service_indicator_mark_non_compliant (); + } + + /* Allocate a help buffer and setup some pointers. */ +@@ -1006,8 +1021,13 @@ _gcry_rsa_pss_verify (gcry_mpi_t value, int hashed_already, + /* The FIPS 186-4 Section 5.5 allows only 0 <= sLen <= hLen */ + if (fips_mode () && saltlen > hlen) + { +- rc = GPG_ERR_INV_ARG; +- goto leave; ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) ++ { ++ rc = GPG_ERR_INV_ARG; ++ goto leave; ++ } ++ else ++ fips_service_indicator_mark_non_compliant (); + } + + /* Allocate a help buffer and setup some pointers. +diff --git a/cipher/rsa.c b/cipher/rsa.c +index c7a809f4..c1329644 100644 +--- a/cipher/rsa.c ++++ b/cipher/rsa.c +@@ -1613,6 +1613,23 @@ rsa_sign (gcry_sexp_t *r_sig, gcry_sexp_t s_data, gcry_sexp_t keyparms) + } + } + ++ /* Check if use of the hash is compliant. */ ++ if (fips_mode ()) ++ { ++ /* SHA1 is approved hash function, but not for digital signature. */ ++ if (_gcry_md_algo_info (ctx.hash_algo, GCRYCTL_TEST_ALGO, NULL, NULL) ++ || ctx.hash_algo == GCRY_MD_SHA1) ++ { ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK_MD)) ++ { ++ rc = GPG_ERR_DIGEST_ALGO; ++ goto leave; ++ } ++ else ++ fips_service_indicator_mark_non_compliant (); ++ } ++ } ++ + /* Do RSA computation. */ + sig = mpi_new (0); + if ((ctx.flags & PUBKEY_FLAG_NO_BLINDING)) +@@ -1720,6 +1737,23 @@ rsa_verify (gcry_sexp_t s_sig, gcry_sexp_t s_data, gcry_sexp_t keyparms) + log_printmpi ("rsa_verify e", pk.e); + } + ++ /* Check if use of the hash is compliant. */ ++ if (fips_mode ()) ++ { ++ /* SHA1 is approved hash function, but not for digital signature. */ ++ if (_gcry_md_algo_info (ctx.hash_algo, GCRYCTL_TEST_ALGO, NULL, NULL) ++ || ctx.hash_algo == GCRY_MD_SHA1) ++ { ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK_MD)) ++ { ++ rc = GPG_ERR_DIGEST_ALGO; ++ goto leave; ++ } ++ else ++ fips_service_indicator_mark_non_compliant (); ++ } ++ } ++ + /* Do RSA computation and compare. */ + result = mpi_new (0); + public (result, sig, &pk); +diff --git a/tests/t-fips-service-ind.c b/tests/t-fips-service-ind.c +index ed5f8d3f..bec6c27e 100644 +--- a/tests/t-fips-service-ind.c ++++ b/tests/t-fips-service-ind.c +@@ -231,7 +231,8 @@ check_pk_s_v (int reject) + const char *data; + int expect_failure; + } tv[] = { +- { ++ { /* Hashing is done externally, and feeded ++ to gcry_pk_sign, specifing the hash used */ + "(private-key (ecc (curve nistp256)" + " (d #519b423d715f8b581f4fa8ee59f4771a5b44c8130b4e3eacca54a56dda72b464#)))", + "(public-key (ecc (curve nistp256)" +@@ -271,6 +272,293 @@ check_pk_s_v (int reject) + "#00112233445566778899AABBCCDDEEFF00010203#))", + 1 + }, ++ { /* Hashing is done internally in ++ gcry_pk_sign with the hash-algo specified. */ ++ "(private-key\n" ++ " (ecc\n" ++ " (curve Ed25519)(flags eddsa)\n" ++ " (q #4014DB483F15527253B25B4C72BEA8BB70255029636BD71DBBCCD5D8BF48A35F17#)" ++ " (d #09A0C38E0F1699073541447C19DA12E3A07A7BFDB0C186E4AC5BCE6F23D55252#)" ++ "))", ++ "(public-key\n" ++ " (ecc\n" ++ " (curve Ed25519)(flags eddsa)\n" ++ " (q #4014DB483F15527253B25B4C72BEA8BB70255029636BD71DBBCCD5D8BF48A35F17#)" ++ "))", ++ "(data(flags eddsa)(hash-algo sha512)(value " ++ "#00112233445566778899AABBCCDDEEFF000102030405060708090A0B0C0D0E0F" ++ " 00112233445566778899AABBCCDDEEFF000102030405060708090A0B0C0D0E0F" ++ " 00112233445566778899AABBCCDDEEFF000102030405060708090A0B0C0D0E0F#))", ++ 0 ++ }, ++ { /* RSA with compliant hash for signing */ ++ "(private-key" ++ " (rsa" ++ " (n #009F56231A3D82E3E7D613D59D53E9AB921BEF9F08A782AED0B6E46ADBC853EC" ++ " 7C71C422435A3CD8FA0DB9EFD55CD3295BADC4E8E2E2B94E15AE82866AB8ADE8" ++ " 7E469FAE76DC3577DE87F1F419C4EB41123DFAF8D16922D5EDBAD6E9076D5A1C" ++ " 958106F0AE5E2E9193C6B49124C64C2A241C4075D4AF16299EB87A6585BAE917" ++ " DEF27FCDD165764D069BC18D16527B29DAAB549F7BBED4A7C6A842D203ED6613" ++ " 6E2411744E432CD26D940132F25874483DCAEECDFD95744819CBCF1EA810681C" ++ " 42907EBCB1C7EAFBE75C87EC32C5413EA10476545D3FC7B2ADB1B66B7F200918" ++ " 664B0E5261C2895AA28B0DE321E921B3F877172CCCAB81F43EF98002916156F6" ++ " CB#)\n" ++ " (e #010001#)\n" ++ " (d #07EF82500C403899934FE993AC5A36F14FF2DF38CF1EF315F205EE4C83EDAA19" ++ " 8890FC23DE9AA933CAFB37B6A8A8DBA675411958337287310D3FF2F1DDC0CB93" ++ " 7E70F57F75F833C021852B631D2B9A520E4431A03C5C3FCB5742DCD841D9FB12" ++ " 771AA1620DCEC3F1583426066ED9DC3F7028C5B59202C88FDF20396E2FA0EC4F" ++ " 5A22D9008F3043673931BC14A5046D6327398327900867E39CC61B2D1AFE2F48" ++ " EC8E1E3861C68D257D7425F4E6F99ABD77D61F10CA100EFC14389071831B33DD" ++ " 69CC8EABEF860D1DC2AAA84ABEAE5DFC91BC124DAF0F4C8EF5BBEA436751DE84" ++ " 3A8063E827A024466F44C28614F93B0732A100D4A0D86D532FE1E22C7725E401" ++ " #)\n" ++ " (p #00C29D438F115825779631CD665A5739367F3E128ADC29766483A46CA80897E0" ++ " 79B32881860B8F9A6A04C2614A904F6F2578DAE13EA67CD60AE3D0AA00A1FF9B" ++ " 441485E44B2DC3D0B60260FBFE073B5AC72FAF67964DE15C8212C389D20DB9CF" ++ " 54AF6AEF5C4196EAA56495DD30CF709F499D5AB30CA35E086C2A1589D6283F17" ++ " 83#)\n" ++ " (q #00D1984135231CB243FE959C0CBEF551EDD986AD7BEDF71EDF447BE3DA27AF46" ++ " 79C974A6FA69E4D52FE796650623DE70622862713932AA2FD9F2EC856EAEAA77" ++ " 88B4EA6084DC81C902F014829B18EA8B2666EC41586818E0589E18876065F97E" ++ " 8D22CE2DA53A05951EC132DCEF41E70A9C35F4ACC268FFAC2ADF54FA1DA110B9" ++ " 19#)\n" ++ " (u #67CF0FD7635205DD80FA814EE9E9C267C17376BF3209FB5D1BC42890D2822A04" ++ " 479DAF4D5B6ED69D0F8D1AF94164D07F8CD52ECEFE880641FA0F41DDAB1785E4" ++ " A37A32F997A516480B4CD4F6482B9466A1765093ED95023CA32D5EDC1E34CEE9" ++ " AF595BC51FE43C4BF810FA225AF697FB473B83815966188A4312C048B885E3F7" ++ " #)))\n", ++ "(public-key\n" ++ " (rsa\n" ++ " (n #009F56231A3D82E3E7D613D59D53E9AB921BEF9F08A782AED0B6E46ADBC853EC" ++ " 7C71C422435A3CD8FA0DB9EFD55CD3295BADC4E8E2E2B94E15AE82866AB8ADE8" ++ " 7E469FAE76DC3577DE87F1F419C4EB41123DFAF8D16922D5EDBAD6E9076D5A1C" ++ " 958106F0AE5E2E9193C6B49124C64C2A241C4075D4AF16299EB87A6585BAE917" ++ " DEF27FCDD165764D069BC18D16527B29DAAB549F7BBED4A7C6A842D203ED6613" ++ " 6E2411744E432CD26D940132F25874483DCAEECDFD95744819CBCF1EA810681C" ++ " 42907EBCB1C7EAFBE75C87EC32C5413EA10476545D3FC7B2ADB1B66B7F200918" ++ " 664B0E5261C2895AA28B0DE321E921B3F877172CCCAB81F43EF98002916156F6" ++ " CB#)\n" ++ " (e #010001#)))\n", ++ "(data\n (flags pkcs1)\n" ++ " (hash sha256 " ++ "#00112233445566778899AABBCCDDEEFF000102030405060708090A0B0C0D0E0F#))\n", ++ 0 ++ }, ++ { /* RSA with non-compliant hash for signing */ ++ "(private-key" ++ " (rsa" ++ " (n #009F56231A3D82E3E7D613D59D53E9AB921BEF9F08A782AED0B6E46ADBC853EC" ++ " 7C71C422435A3CD8FA0DB9EFD55CD3295BADC4E8E2E2B94E15AE82866AB8ADE8" ++ " 7E469FAE76DC3577DE87F1F419C4EB41123DFAF8D16922D5EDBAD6E9076D5A1C" ++ " 958106F0AE5E2E9193C6B49124C64C2A241C4075D4AF16299EB87A6585BAE917" ++ " DEF27FCDD165764D069BC18D16527B29DAAB549F7BBED4A7C6A842D203ED6613" ++ " 6E2411744E432CD26D940132F25874483DCAEECDFD95744819CBCF1EA810681C" ++ " 42907EBCB1C7EAFBE75C87EC32C5413EA10476545D3FC7B2ADB1B66B7F200918" ++ " 664B0E5261C2895AA28B0DE321E921B3F877172CCCAB81F43EF98002916156F6" ++ " CB#)\n" ++ " (e #010001#)\n" ++ " (d #07EF82500C403899934FE993AC5A36F14FF2DF38CF1EF315F205EE4C83EDAA19" ++ " 8890FC23DE9AA933CAFB37B6A8A8DBA675411958337287310D3FF2F1DDC0CB93" ++ " 7E70F57F75F833C021852B631D2B9A520E4431A03C5C3FCB5742DCD841D9FB12" ++ " 771AA1620DCEC3F1583426066ED9DC3F7028C5B59202C88FDF20396E2FA0EC4F" ++ " 5A22D9008F3043673931BC14A5046D6327398327900867E39CC61B2D1AFE2F48" ++ " EC8E1E3861C68D257D7425F4E6F99ABD77D61F10CA100EFC14389071831B33DD" ++ " 69CC8EABEF860D1DC2AAA84ABEAE5DFC91BC124DAF0F4C8EF5BBEA436751DE84" ++ " 3A8063E827A024466F44C28614F93B0732A100D4A0D86D532FE1E22C7725E401" ++ " #)\n" ++ " (p #00C29D438F115825779631CD665A5739367F3E128ADC29766483A46CA80897E0" ++ " 79B32881860B8F9A6A04C2614A904F6F2578DAE13EA67CD60AE3D0AA00A1FF9B" ++ " 441485E44B2DC3D0B60260FBFE073B5AC72FAF67964DE15C8212C389D20DB9CF" ++ " 54AF6AEF5C4196EAA56495DD30CF709F499D5AB30CA35E086C2A1589D6283F17" ++ " 83#)\n" ++ " (q #00D1984135231CB243FE959C0CBEF551EDD986AD7BEDF71EDF447BE3DA27AF46" ++ " 79C974A6FA69E4D52FE796650623DE70622862713932AA2FD9F2EC856EAEAA77" ++ " 88B4EA6084DC81C902F014829B18EA8B2666EC41586818E0589E18876065F97E" ++ " 8D22CE2DA53A05951EC132DCEF41E70A9C35F4ACC268FFAC2ADF54FA1DA110B9" ++ " 19#)\n" ++ " (u #67CF0FD7635205DD80FA814EE9E9C267C17376BF3209FB5D1BC42890D2822A04" ++ " 479DAF4D5B6ED69D0F8D1AF94164D07F8CD52ECEFE880641FA0F41DDAB1785E4" ++ " A37A32F997A516480B4CD4F6482B9466A1765093ED95023CA32D5EDC1E34CEE9" ++ " AF595BC51FE43C4BF810FA225AF697FB473B83815966188A4312C048B885E3F7" ++ " #)))\n", ++ "(public-key\n" ++ " (rsa\n" ++ " (n #009F56231A3D82E3E7D613D59D53E9AB921BEF9F08A782AED0B6E46ADBC853EC" ++ " 7C71C422435A3CD8FA0DB9EFD55CD3295BADC4E8E2E2B94E15AE82866AB8ADE8" ++ " 7E469FAE76DC3577DE87F1F419C4EB41123DFAF8D16922D5EDBAD6E9076D5A1C" ++ " 958106F0AE5E2E9193C6B49124C64C2A241C4075D4AF16299EB87A6585BAE917" ++ " DEF27FCDD165764D069BC18D16527B29DAAB549F7BBED4A7C6A842D203ED6613" ++ " 6E2411744E432CD26D940132F25874483DCAEECDFD95744819CBCF1EA810681C" ++ " 42907EBCB1C7EAFBE75C87EC32C5413EA10476545D3FC7B2ADB1B66B7F200918" ++ " 664B0E5261C2895AA28B0DE321E921B3F877172CCCAB81F43EF98002916156F6" ++ " CB#)\n" ++ " (e #010001#)))\n", ++ "(data\n (flags pkcs1)\n" ++ " (hash sha1 #11223344556677889900AABBCCDDEEFF10203040#))\n", ++ 1 ++ }, ++ { /* RSA with unknown hash for signing */ ++ "(private-key" ++ " (rsa" ++ " (n #009F56231A3D82E3E7D613D59D53E9AB921BEF9F08A782AED0B6E46ADBC853EC" ++ " 7C71C422435A3CD8FA0DB9EFD55CD3295BADC4E8E2E2B94E15AE82866AB8ADE8" ++ " 7E469FAE76DC3577DE87F1F419C4EB41123DFAF8D16922D5EDBAD6E9076D5A1C" ++ " 958106F0AE5E2E9193C6B49124C64C2A241C4075D4AF16299EB87A6585BAE917" ++ " DEF27FCDD165764D069BC18D16527B29DAAB549F7BBED4A7C6A842D203ED6613" ++ " 6E2411744E432CD26D940132F25874483DCAEECDFD95744819CBCF1EA810681C" ++ " 42907EBCB1C7EAFBE75C87EC32C5413EA10476545D3FC7B2ADB1B66B7F200918" ++ " 664B0E5261C2895AA28B0DE321E921B3F877172CCCAB81F43EF98002916156F6" ++ " CB#)\n" ++ " (e #010001#)\n" ++ " (d #07EF82500C403899934FE993AC5A36F14FF2DF38CF1EF315F205EE4C83EDAA19" ++ " 8890FC23DE9AA933CAFB37B6A8A8DBA675411958337287310D3FF2F1DDC0CB93" ++ " 7E70F57F75F833C021852B631D2B9A520E4431A03C5C3FCB5742DCD841D9FB12" ++ " 771AA1620DCEC3F1583426066ED9DC3F7028C5B59202C88FDF20396E2FA0EC4F" ++ " 5A22D9008F3043673931BC14A5046D6327398327900867E39CC61B2D1AFE2F48" ++ " EC8E1E3861C68D257D7425F4E6F99ABD77D61F10CA100EFC14389071831B33DD" ++ " 69CC8EABEF860D1DC2AAA84ABEAE5DFC91BC124DAF0F4C8EF5BBEA436751DE84" ++ " 3A8063E827A024466F44C28614F93B0732A100D4A0D86D532FE1E22C7725E401" ++ " #)\n" ++ " (p #00C29D438F115825779631CD665A5739367F3E128ADC29766483A46CA80897E0" ++ " 79B32881860B8F9A6A04C2614A904F6F2578DAE13EA67CD60AE3D0AA00A1FF9B" ++ " 441485E44B2DC3D0B60260FBFE073B5AC72FAF67964DE15C8212C389D20DB9CF" ++ " 54AF6AEF5C4196EAA56495DD30CF709F499D5AB30CA35E086C2A1589D6283F17" ++ " 83#)\n" ++ " (q #00D1984135231CB243FE959C0CBEF551EDD986AD7BEDF71EDF447BE3DA27AF46" ++ " 79C974A6FA69E4D52FE796650623DE70622862713932AA2FD9F2EC856EAEAA77" ++ " 88B4EA6084DC81C902F014829B18EA8B2666EC41586818E0589E18876065F97E" ++ " 8D22CE2DA53A05951EC132DCEF41E70A9C35F4ACC268FFAC2ADF54FA1DA110B9" ++ " 19#)\n" ++ " (u #67CF0FD7635205DD80FA814EE9E9C267C17376BF3209FB5D1BC42890D2822A04" ++ " 479DAF4D5B6ED69D0F8D1AF94164D07F8CD52ECEFE880641FA0F41DDAB1785E4" ++ " A37A32F997A516480B4CD4F6482B9466A1765093ED95023CA32D5EDC1E34CEE9" ++ " AF595BC51FE43C4BF810FA225AF697FB473B83815966188A4312C048B885E3F7" ++ " #)))\n", ++ "(public-key\n" ++ " (rsa\n" ++ " (n #009F56231A3D82E3E7D613D59D53E9AB921BEF9F08A782AED0B6E46ADBC853EC" ++ " 7C71C422435A3CD8FA0DB9EFD55CD3295BADC4E8E2E2B94E15AE82866AB8ADE8" ++ " 7E469FAE76DC3577DE87F1F419C4EB41123DFAF8D16922D5EDBAD6E9076D5A1C" ++ " 958106F0AE5E2E9193C6B49124C64C2A241C4075D4AF16299EB87A6585BAE917" ++ " DEF27FCDD165764D069BC18D16527B29DAAB549F7BBED4A7C6A842D203ED6613" ++ " 6E2411744E432CD26D940132F25874483DCAEECDFD95744819CBCF1EA810681C" ++ " 42907EBCB1C7EAFBE75C87EC32C5413EA10476545D3FC7B2ADB1B66B7F200918" ++ " 664B0E5261C2895AA28B0DE321E921B3F877172CCCAB81F43EF98002916156F6" ++ " CB#)\n" ++ " (e #010001#)))\n", ++ "(data\n (flags pkcs1-raw)\n" ++ " (value " ++ "#00112233445566778899AABBCCDDEEFF000102030405060708090A0B0C0D0E0F#))\n", ++ 1 ++ }, ++ { /* RSA with compliant hash for signing */ ++ "(private-key" ++ " (rsa" ++ " (n #009F56231A3D82E3E7D613D59D53E9AB921BEF9F08A782AED0B6E46ADBC853EC" ++ " 7C71C422435A3CD8FA0DB9EFD55CD3295BADC4E8E2E2B94E15AE82866AB8ADE8" ++ " 7E469FAE76DC3577DE87F1F419C4EB41123DFAF8D16922D5EDBAD6E9076D5A1C" ++ " 958106F0AE5E2E9193C6B49124C64C2A241C4075D4AF16299EB87A6585BAE917" ++ " DEF27FCDD165764D069BC18D16527B29DAAB549F7BBED4A7C6A842D203ED6613" ++ " 6E2411744E432CD26D940132F25874483DCAEECDFD95744819CBCF1EA810681C" ++ " 42907EBCB1C7EAFBE75C87EC32C5413EA10476545D3FC7B2ADB1B66B7F200918" ++ " 664B0E5261C2895AA28B0DE321E921B3F877172CCCAB81F43EF98002916156F6" ++ " CB#)\n" ++ " (e #010001#)\n" ++ " (d #07EF82500C403899934FE993AC5A36F14FF2DF38CF1EF315F205EE4C83EDAA19" ++ " 8890FC23DE9AA933CAFB37B6A8A8DBA675411958337287310D3FF2F1DDC0CB93" ++ " 7E70F57F75F833C021852B631D2B9A520E4431A03C5C3FCB5742DCD841D9FB12" ++ " 771AA1620DCEC3F1583426066ED9DC3F7028C5B59202C88FDF20396E2FA0EC4F" ++ " 5A22D9008F3043673931BC14A5046D6327398327900867E39CC61B2D1AFE2F48" ++ " EC8E1E3861C68D257D7425F4E6F99ABD77D61F10CA100EFC14389071831B33DD" ++ " 69CC8EABEF860D1DC2AAA84ABEAE5DFC91BC124DAF0F4C8EF5BBEA436751DE84" ++ " 3A8063E827A024466F44C28614F93B0732A100D4A0D86D532FE1E22C7725E401" ++ " #)\n" ++ " (p #00C29D438F115825779631CD665A5739367F3E128ADC29766483A46CA80897E0" ++ " 79B32881860B8F9A6A04C2614A904F6F2578DAE13EA67CD60AE3D0AA00A1FF9B" ++ " 441485E44B2DC3D0B60260FBFE073B5AC72FAF67964DE15C8212C389D20DB9CF" ++ " 54AF6AEF5C4196EAA56495DD30CF709F499D5AB30CA35E086C2A1589D6283F17" ++ " 83#)\n" ++ " (q #00D1984135231CB243FE959C0CBEF551EDD986AD7BEDF71EDF447BE3DA27AF46" ++ " 79C974A6FA69E4D52FE796650623DE70622862713932AA2FD9F2EC856EAEAA77" ++ " 88B4EA6084DC81C902F014829B18EA8B2666EC41586818E0589E18876065F97E" ++ " 8D22CE2DA53A05951EC132DCEF41E70A9C35F4ACC268FFAC2ADF54FA1DA110B9" ++ " 19#)\n" ++ " (u #67CF0FD7635205DD80FA814EE9E9C267C17376BF3209FB5D1BC42890D2822A04" ++ " 479DAF4D5B6ED69D0F8D1AF94164D07F8CD52ECEFE880641FA0F41DDAB1785E4" ++ " A37A32F997A516480B4CD4F6482B9466A1765093ED95023CA32D5EDC1E34CEE9" ++ " AF595BC51FE43C4BF810FA225AF697FB473B83815966188A4312C048B885E3F7" ++ " #)))\n", ++ "(public-key\n" ++ " (rsa\n" ++ " (n #009F56231A3D82E3E7D613D59D53E9AB921BEF9F08A782AED0B6E46ADBC853EC" ++ " 7C71C422435A3CD8FA0DB9EFD55CD3295BADC4E8E2E2B94E15AE82866AB8ADE8" ++ " 7E469FAE76DC3577DE87F1F419C4EB41123DFAF8D16922D5EDBAD6E9076D5A1C" ++ " 958106F0AE5E2E9193C6B49124C64C2A241C4075D4AF16299EB87A6585BAE917" ++ " DEF27FCDD165764D069BC18D16527B29DAAB549F7BBED4A7C6A842D203ED6613" ++ " 6E2411744E432CD26D940132F25874483DCAEECDFD95744819CBCF1EA810681C" ++ " 42907EBCB1C7EAFBE75C87EC32C5413EA10476545D3FC7B2ADB1B66B7F200918" ++ " 664B0E5261C2895AA28B0DE321E921B3F877172CCCAB81F43EF98002916156F6" ++ " CB#)\n" ++ " (e #010001#)))\n", ++ "(data\n (flags pss)\n" ++ " (hash sha256 " ++ "#00112233445566778899AABBCCDDEEFF000102030405060708090A0B0C0D0E0F#))\n", ++ 0 ++ }, ++ { /* RSA with non-compliant hash for signing */ ++ "(private-key" ++ " (rsa" ++ " (n #009F56231A3D82E3E7D613D59D53E9AB921BEF9F08A782AED0B6E46ADBC853EC" ++ " 7C71C422435A3CD8FA0DB9EFD55CD3295BADC4E8E2E2B94E15AE82866AB8ADE8" ++ " 7E469FAE76DC3577DE87F1F419C4EB41123DFAF8D16922D5EDBAD6E9076D5A1C" ++ " 958106F0AE5E2E9193C6B49124C64C2A241C4075D4AF16299EB87A6585BAE917" ++ " DEF27FCDD165764D069BC18D16527B29DAAB549F7BBED4A7C6A842D203ED6613" ++ " 6E2411744E432CD26D940132F25874483DCAEECDFD95744819CBCF1EA810681C" ++ " 42907EBCB1C7EAFBE75C87EC32C5413EA10476545D3FC7B2ADB1B66B7F200918" ++ " 664B0E5261C2895AA28B0DE321E921B3F877172CCCAB81F43EF98002916156F6" ++ " CB#)\n" ++ " (e #010001#)\n" ++ " (d #07EF82500C403899934FE993AC5A36F14FF2DF38CF1EF315F205EE4C83EDAA19" ++ " 8890FC23DE9AA933CAFB37B6A8A8DBA675411958337287310D3FF2F1DDC0CB93" ++ " 7E70F57F75F833C021852B631D2B9A520E4431A03C5C3FCB5742DCD841D9FB12" ++ " 771AA1620DCEC3F1583426066ED9DC3F7028C5B59202C88FDF20396E2FA0EC4F" ++ " 5A22D9008F3043673931BC14A5046D6327398327900867E39CC61B2D1AFE2F48" ++ " EC8E1E3861C68D257D7425F4E6F99ABD77D61F10CA100EFC14389071831B33DD" ++ " 69CC8EABEF860D1DC2AAA84ABEAE5DFC91BC124DAF0F4C8EF5BBEA436751DE84" ++ " 3A8063E827A024466F44C28614F93B0732A100D4A0D86D532FE1E22C7725E401" ++ " #)\n" ++ " (p #00C29D438F115825779631CD665A5739367F3E128ADC29766483A46CA80897E0" ++ " 79B32881860B8F9A6A04C2614A904F6F2578DAE13EA67CD60AE3D0AA00A1FF9B" ++ " 441485E44B2DC3D0B60260FBFE073B5AC72FAF67964DE15C8212C389D20DB9CF" ++ " 54AF6AEF5C4196EAA56495DD30CF709F499D5AB30CA35E086C2A1589D6283F17" ++ " 83#)\n" ++ " (q #00D1984135231CB243FE959C0CBEF551EDD986AD7BEDF71EDF447BE3DA27AF46" ++ " 79C974A6FA69E4D52FE796650623DE70622862713932AA2FD9F2EC856EAEAA77" ++ " 88B4EA6084DC81C902F014829B18EA8B2666EC41586818E0589E18876065F97E" ++ " 8D22CE2DA53A05951EC132DCEF41E70A9C35F4ACC268FFAC2ADF54FA1DA110B9" ++ " 19#)\n" ++ " (u #67CF0FD7635205DD80FA814EE9E9C267C17376BF3209FB5D1BC42890D2822A04" ++ " 479DAF4D5B6ED69D0F8D1AF94164D07F8CD52ECEFE880641FA0F41DDAB1785E4" ++ " A37A32F997A516480B4CD4F6482B9466A1765093ED95023CA32D5EDC1E34CEE9" ++ " AF595BC51FE43C4BF810FA225AF697FB473B83815966188A4312C048B885E3F7" ++ " #)))\n", ++ "(public-key\n" ++ " (rsa\n" ++ " (n #009F56231A3D82E3E7D613D59D53E9AB921BEF9F08A782AED0B6E46ADBC853EC" ++ " 7C71C422435A3CD8FA0DB9EFD55CD3295BADC4E8E2E2B94E15AE82866AB8ADE8" ++ " 7E469FAE76DC3577DE87F1F419C4EB41123DFAF8D16922D5EDBAD6E9076D5A1C" ++ " 958106F0AE5E2E9193C6B49124C64C2A241C4075D4AF16299EB87A6585BAE917" ++ " DEF27FCDD165764D069BC18D16527B29DAAB549F7BBED4A7C6A842D203ED6613" ++ " 6E2411744E432CD26D940132F25874483DCAEECDFD95744819CBCF1EA810681C" ++ " 42907EBCB1C7EAFBE75C87EC32C5413EA10476545D3FC7B2ADB1B66B7F200918" ++ " 664B0E5261C2895AA28B0DE321E921B3F877172CCCAB81F43EF98002916156F6" ++ " CB#)\n" ++ " (e #010001#)))\n", ++ "(data\n (flags pss)\n" ++ " (hash sha1 #11223344556677889900AABBCCDDEEFF10203040#))\n", ++ 1 ++ } + }; + int tvidx; + gpg_error_t err; +-- +2.49.0 + diff --git a/libgcrypt-cipher-visibility-Differentiate-use-of-random-override-in-the-SLI.patch b/libgcrypt-cipher-visibility-Differentiate-use-of-random-override-in-the-SLI.patch new file mode 100644 index 0000000..413aa34 --- /dev/null +++ b/libgcrypt-cipher-visibility-Differentiate-use-of-random-override-in-the-SLI.patch @@ -0,0 +1,107 @@ +From 234eb316b0a04c50e8511a570775ded45060f18b Mon Sep 17 00:00:00 2001 +From: Lucas Mulling via Gcrypt-devel +Date: Wed, 26 Feb 2025 17:19:24 -0300 +Subject: [PATCH 08/14] cipher,visibility: Differentiate use of random-override + in the SLI +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* cipher/pubkey-util.c (_gcry_pk_util_data_to_mpi, +_gcry_pk_single_data_push, _gcry_pk_util_free_encoding_ctx): +Differentiate use of random-override in the SLI. +* src/visibility.c (gcry_pk_random_override_new): +Differentiate use explicit random override in the SLI. + +GnuPG-bug-id: 7338 +Signed-off-by: Lucas Mulling +Signed-off-by: Lucas Mülling +--- + cipher/pubkey-util.c | 33 +++++++++++++++++++++++++++++++++ + src/visibility.c | 12 ++++++++++++ + 2 files changed, 45 insertions(+) + +diff --git a/cipher/pubkey-util.c b/cipher/pubkey-util.c +index e7355569..66a04f13 100644 +--- a/cipher/pubkey-util.c ++++ b/cipher/pubkey-util.c +@@ -973,6 +973,17 @@ _gcry_pk_util_data_to_mpi (gcry_sexp_t input, gcry_mpi_t *ret_mpi, + list = sexp_find_token (ldata, "random-override", 0); + if (list) + { ++ if (fips_mode ()) ++ { ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) ++ { ++ sexp_release (list); ++ rc = GPG_ERR_INV_FLAG; ++ goto leave; ++ } ++ else ++ fips_service_indicator_mark_non_compliant (); ++ } + s = sexp_nth_data (list, 1, &n); + if (!s) + rc = GPG_ERR_NO_OBJ; +@@ -1149,6 +1160,17 @@ _gcry_pk_util_data_to_mpi (gcry_sexp_t input, gcry_mpi_t *ret_mpi, + list = sexp_find_token (ldata, "random-override", 0); + if (list) + { ++ if (fips_mode ()) ++ { ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) ++ { ++ sexp_release (list); ++ rc = GPG_ERR_INV_FLAG; ++ goto leave; ++ } ++ else ++ fips_service_indicator_mark_non_compliant (); ++ } + s = sexp_nth_data (list, 1, &n); + if (!s) + rc = GPG_ERR_NO_OBJ; +@@ -1248,6 +1270,17 @@ _gcry_pk_util_data_to_mpi (gcry_sexp_t input, gcry_mpi_t *ret_mpi, + list = sexp_find_token (ldata, "random-override", 0); + if (list) + { ++ if (fips_mode ()) ++ { ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) ++ { ++ sexp_release (list); ++ rc = GPG_ERR_INV_FLAG; ++ goto leave; ++ } ++ else ++ fips_service_indicator_mark_non_compliant (); ++ } + s = sexp_nth_data (list, 1, &n); + if (!s) + rc = GPG_ERR_NO_OBJ; +diff --git a/src/visibility.c b/src/visibility.c +index 4134446a..ccd0de69 100644 +--- a/src/visibility.c ++++ b/src/visibility.c +@@ -1085,6 +1085,18 @@ gcry_pk_hash_verify (gcry_sexp_t sigval, const char *data_tmpl, gcry_sexp_t pkey + gcry_error_t + gcry_pk_random_override_new (gcry_ctx_t *r_ctx, const unsigned char *p, size_t len) + { ++ if (!fips_is_operational ()) ++ return gpg_error (fips_not_operational ()); ++ fips_service_indicator_init (); ++ ++ if (fips_mode ()) ++ { ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) ++ return gpg_error (GPG_ERR_INV_OP); ++ else ++ fips_service_indicator_mark_non_compliant (); ++ } ++ + return gpg_error (_gcry_pk_single_data_push (r_ctx, p, len)); + } + +-- +2.49.0 + diff --git a/libgcrypt-doc-Add-about-GCRYCTL_FIPS_SERVICE_INDICATOR.patch b/libgcrypt-doc-Add-about-GCRYCTL_FIPS_SERVICE_INDICATOR.patch new file mode 100644 index 0000000..a9e9522 --- /dev/null +++ b/libgcrypt-doc-Add-about-GCRYCTL_FIPS_SERVICE_INDICATOR.patch @@ -0,0 +1,66 @@ +From 636f40cb78587635ef663bfc3430937cf140f245 Mon Sep 17 00:00:00 2001 +From: NIIBE Yutaka +Date: Thu, 13 Mar 2025 15:02:58 +0900 +Subject: [PATCH 13/14] doc: Add about GCRYCTL_FIPS_SERVICE_INDICATOR. +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* doc/gcrypt.texi (GCRYCTL_FIPS_SERVICE_INDICATOR): Add a description. +(GCRYCTL_FIPS_REJECT_NON_FIPS): Likewise. + +-- + +GnuPG-bug-id: 7338 +Signed-off-by: NIIBE Yutaka +Signed-off-by: Lucas Mülling +--- + doc/gcrypt.texi | 32 ++++++++++++++++++++++++++++++++ + 1 file changed, 32 insertions(+) + +diff --git a/doc/gcrypt.texi b/doc/gcrypt.texi +index 5d428738..6e82a41b 100644 +--- a/doc/gcrypt.texi ++++ b/doc/gcrypt.texi +@@ -1052,6 +1052,38 @@ is responsible to check also the internal members. For example: + /* ok */ + @end example + ++@item GCRYCTL_FIPS_SERVICE_INDICATOR; Arguments: none ++This commands provides ``dynamic'' service indicator. ++ ++After a function call (of the use of security services), this command ++can be used to check if the call is valid or not. If the computation ++is done in an approved way, it returns @code{GPG_ERR_NO_ERROR}. ++Otherwise @code{GPG_ERR_NOT_SUPPORTED} is returned. ++ ++An application may use this command directly or use the convenience ++macro below. ++ ++@deftypefun gcry_error_t gcry_get_fips_service_indicator (void) ++ ++Returns @code{GPG_ERR_NO_ERROR} if a preceeding function call is ++valid. Otherwise @code{GPG_ERR_NOT_SUPPORTED} is returned. ++@end deftypefun ++ ++@item GCRYCTL_FIPS_REJECT_NON_FIPS; Arguments: unsigned int flags ++In Libgcrypt 1.10, static implicit indicator is used; For an approved ++function (which can be checked by ++GCRYCTL_FIPS_SERVICE_INDICATOR_FUNCTION command) with an approved ++algo/operation (which can be checked GCRYCTL_FIPS_SERVICE_INDICATOR_* ++command), success of the function call means that it's valid and error ++return (rejection) means it's invalid. This command controls thread ++specific behavior of the rejection. ++ ++When using ``dynamic'' service indicator, this command with FLAGS=0 ++disables all rejections. ++@example ++ gcry_control (GCRYCTL_FIPS_REJECT_NON_FIPS, 0); ++@endexample ++ + @end table + + @end deftypefun +-- +2.49.0 + diff --git a/libgcrypt-doc-Fix-syntax-error.patch b/libgcrypt-doc-Fix-syntax-error.patch new file mode 100644 index 0000000..b85eb54 --- /dev/null +++ b/libgcrypt-doc-Fix-syntax-error.patch @@ -0,0 +1,31 @@ +From 22e65f6f5b8dbddf925151894426e4c06d33803b Mon Sep 17 00:00:00 2001 +From: Werner Koch +Date: Thu, 13 Mar 2025 18:06:37 +0100 +Subject: [PATCH 14/14] doc: Fix syntax error +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +-- + +Signed-off-by: Lucas Mülling +--- + doc/gcrypt.texi | 2 +- + 1 file changed, 1 insertion(+), 1 deletion(-) + +diff --git a/doc/gcrypt.texi b/doc/gcrypt.texi +index 6e82a41b..eeab1a78 100644 +--- a/doc/gcrypt.texi ++++ b/doc/gcrypt.texi +@@ -1082,7 +1082,7 @@ When using ``dynamic'' service indicator, this command with FLAGS=0 + disables all rejections. + @example + gcry_control (GCRYCTL_FIPS_REJECT_NON_FIPS, 0); +-@endexample ++@end example + + @end table + +-- +2.49.0 + diff --git a/libgcrypt-fips-Change-the-internal-API-for-new-FIPS-service-indicator.patch b/libgcrypt-fips-Change-the-internal-API-for-new-FIPS-service-indicator.patch new file mode 100644 index 0000000..8638218 --- /dev/null +++ b/libgcrypt-fips-Change-the-internal-API-for-new-FIPS-service-indicator.patch @@ -0,0 +1,140 @@ +From 4799914966a7f94f41e1ed5b7b62fded7ba09704 Mon Sep 17 00:00:00 2001 +From: NIIBE Yutaka +Date: Thu, 12 Dec 2024 11:03:38 +0900 +Subject: [PATCH 01/19] fips: Change the internal API for new FIPS service + indicator. +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* src/gcrypt-int.h (fips_service_indicator_init): Initialize by 0. +(fips_service_indicator_mark_success): Remove. +(fips_service_indicator_mark_non_compliant): New. +* cipher/kdf.c (_gcry_kdf_derive): Follow the change of the API. +* cipher/md.c (_gcry_md_hash_buffer): Likewise. +(_gcry_md_hash_buffers_extract): Likewise. + +-- + +GnuPG-bug-id: 7338 +Signed-off-by: NIIBE Yutaka +Signed-off-by: Lucas Mülling +--- + cipher/kdf.c | 17 +++++++++-------- + cipher/md.c | 8 ++++---- + src/gcrypt-int.h | 9 +++------ + 3 files changed, 16 insertions(+), 18 deletions(-) + +diff --git a/cipher/kdf.c b/cipher/kdf.c +index 1eae2b90..71156ea4 100644 +--- a/cipher/kdf.c ++++ b/cipher/kdf.c +@@ -248,6 +248,7 @@ _gcry_kdf_derive (const void *passphrase, size_t passphraselen, + size_t keysize, void *keybuffer) + { + gpg_err_code_t ec; ++ int is_compliant_algo = 0; + + if (!passphrase) + { +@@ -279,35 +280,32 @@ _gcry_kdf_derive (const void *passphrase, size_t passphraselen, + break; + + case GCRY_KDF_PBKDF2: ++ is_compliant_algo = 1; + if (!saltlen || !iterations) + ec = GPG_ERR_INV_VALUE; + else + { +- int is_compliant = 1; +- + if (fips_mode ()) + { + /* FIPS requires minimum passphrase length, see FIPS 140-3 IG D.N */ + if (passphraselen < 8) +- is_compliant &= 0; ++ fips_service_indicator_mark_non_compliant (); + + /* FIPS requires minimum salt length of 128 b (SP 800-132 sec. 5.1, p.6) */ + if (saltlen < 16) +- is_compliant &= 0; ++ fips_service_indicator_mark_non_compliant (); + + /* FIPS requires minimum iterations bound (SP 800-132 sec 5.2, p.6) */ + if (iterations < 1000) +- is_compliant &= 0; ++ fips_service_indicator_mark_non_compliant (); + + /* Check minimum key size */ + if (keysize < 14) +- is_compliant &= 0; ++ fips_service_indicator_mark_non_compliant (); + } + + ec = _gcry_kdf_pkdf2 (passphrase, passphraselen, subalgo, + salt, saltlen, iterations, keysize, keybuffer); +- if (!ec) +- fips_service_indicator_mark_success (is_compliant); + } + break; + +@@ -326,6 +324,9 @@ _gcry_kdf_derive (const void *passphrase, size_t passphraselen, + break; + } + ++ if (!ec && !is_compliant_algo && fips_mode ()) ++ fips_service_indicator_mark_non_compliant (); ++ + leave: + return ec; + } +diff --git a/cipher/md.c b/cipher/md.c +index c2bd18c6..ef2fc5a4 100644 +--- a/cipher/md.c ++++ b/cipher/md.c +@@ -1286,8 +1286,8 @@ _gcry_md_hash_buffer (int algo, void *digest, + + if (fips_mode ()) + { +- int is_compliant = spec->flags.fips; +- fips_service_indicator_mark_success (is_compliant); ++ if (!spec->flags.fips) ++ fips_service_indicator_mark_non_compliant (); + } + } + +@@ -1384,8 +1384,8 @@ _gcry_md_hash_buffers_extract (int algo, unsigned int flags, void *digest, + + if (fips_mode ()) + { +- int is_compliant = spec->flags.fips; +- fips_service_indicator_mark_success (is_compliant); ++ if (!spec->flags.fips) ++ fips_service_indicator_mark_non_compliant (); + } + + return 0; +diff --git a/src/gcrypt-int.h b/src/gcrypt-int.h +index 7f894737..aa49d766 100644 +--- a/src/gcrypt-int.h ++++ b/src/gcrypt-int.h +@@ -303,13 +303,10 @@ unsigned long _gcry_thread_context_get_fsi (void); + #define fips_service_indicator_init() do \ + { \ + if (fips_mode ()) \ +- _gcry_thread_context_set_fsi (1); \ +- } while (0) +-#define fips_service_indicator_mark_success(is_compliant) do \ +- { \ +- if (is_compliant && fips_mode ()) \ +- _gcry_thread_context_set_fsi (0); \ ++ _gcry_thread_context_set_fsi (0); \ + } while (0) ++/* Should be used only when fips_mode()==TRUE. */ ++#define fips_service_indicator_mark_non_compliant() _gcry_thread_context_set_fsi (1) + + /* Return a pointer to a string containing a description of the error + code in the error value ERR. */ +-- +2.49.0 + diff --git a/libgcrypt-fips-Fix-GCRY_FIPS_FLAG_REJECT_MD.patch b/libgcrypt-fips-Fix-GCRY_FIPS_FLAG_REJECT_MD.patch new file mode 100644 index 0000000..aa6f093 --- /dev/null +++ b/libgcrypt-fips-Fix-GCRY_FIPS_FLAG_REJECT_MD.patch @@ -0,0 +1,42 @@ +From b9eb8f4cb81801d68580627ad2188607a8c5f2ec Mon Sep 17 00:00:00 2001 +From: NIIBE Yutaka +Date: Thu, 13 Mar 2025 15:01:21 +0900 +Subject: [PATCH 12/14] fips: Fix GCRY_FIPS_FLAG_REJECT_MD. +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* src/gcrypt.h.in (GCRY_FIPS_FLAG_REJECT_MD): Include SHA1. + +-- + +Fixes-commit: 4ee91a94bcdad32aed4364d09e3daf8841fa579f +Signed-off-by: NIIBE Yutaka +Signed-off-by: Lucas Mülling +--- + src/gcrypt.h.in | 8 +++++--- + 1 file changed, 5 insertions(+), 3 deletions(-) + +diff --git a/src/gcrypt.h.in b/src/gcrypt.h.in +index b2b8853f..a9c36aa6 100644 +--- a/src/gcrypt.h.in ++++ b/src/gcrypt.h.in +@@ -1994,10 +1994,12 @@ char *gcry_get_config (int mode, const char *what); + #define GCRY_FIPS_FLAG_REJECT_PK_ECC_K (1 << 10) + #define GCRY_FIPS_FLAG_REJECT_PK_FLAGS (1 << 11) + +-#define GCRY_FIPS_FLAG_REJECT_MD \ +- (GCRY_FIPS_FLAG_REJECT_MD_MD5 | GCRY_FIPS_FLAG_REJECT_MD_OTHERS) ++#define GCRY_FIPS_FLAG_REJECT_MD \ ++ (GCRY_FIPS_FLAG_REJECT_MD_MD5 | GCRY_FIPS_FLAG_REJECT_MD_SHA1 \ ++ | GCRY_FIPS_FLAG_REJECT_MD_OTHERS) + +-/* Note: Don't reject MD5, PK MD, PK GOST, PK SM2, PK ECC K, and PK FLAGS */ ++/* Note: Don't reject MD5, PK MD, PK GOST, PK SM2, ++ SHA1, PK ECC K, and PK FLAGS */ + #define GCRY_FIPS_FLAG_REJECT_COMPAT110 \ + (GCRY_FIPS_FLAG_REJECT_MD_OTHERS \ + | GCRY_FIPS_FLAG_REJECT_MAC \ +-- +2.49.0 + diff --git a/libgcrypt-fips-Introduce-GCRYCTL_FIPS_REJECT_NON_FIPS.patch b/libgcrypt-fips-Introduce-GCRYCTL_FIPS_REJECT_NON_FIPS.patch new file mode 100644 index 0000000..d08a59a --- /dev/null +++ b/libgcrypt-fips-Introduce-GCRYCTL_FIPS_REJECT_NON_FIPS.patch @@ -0,0 +1,261 @@ +From e52adf0948c60b2e9accd7996fcece0f9b443763 Mon Sep 17 00:00:00 2001 +From: NIIBE Yutaka +Date: Thu, 19 Dec 2024 11:30:28 +0900 +Subject: [PATCH 12/19] fips: Introduce GCRYCTL_FIPS_REJECT_NON_FIPS. +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* src/gcrypt.h.in (GCRYCTL_FIPS_REJECT_NON_FIPS): New. +(GCRY_FIPS_FLAG_REJECT_*): New. +* src/fips.c (struct gcry_thread_context): Add flags_reject_non_fips. +(the_tc): Add initial value. +(_gcry_thread_context_set_reject): New. +(_gcry_thread_context_check_rejection): New. +* src/gcrypt-int.h (fips_check_rejection): New. +* src/global.c (_gcry_vcontrol): Handle GCRYCTL_FIPS_REJECT_NON_FIPS. +* tests/t-fips-service-ind.c (main): Use GCRYCTL_FIPS_REJECT_NON_FIPS. + +-- + +GnuPG-bug-id: 7338 +Signed-off-by: NIIBE Yutaka +Signed-off-by: Lucas Mülling +--- + cipher/ecc-curves.c | 7 ++++++- + cipher/pubkey.c | 34 ++++++++++++++++++++++++++-------- + src/fips.c | 17 ++++++++++++++++- + src/gcrypt-int.h | 9 ++++++++- + src/gcrypt.h.in | 28 ++++++++++++++++++++++++++-- + src/global.c | 7 +++++++ + tests/t-fips-service-ind.c | 2 ++ + 7 files changed, 91 insertions(+), 13 deletions(-) + +Index: libgcrypt-1.11.0/cipher/ecc-curves.c +=================================================================== +--- libgcrypt-1.11.0.orig/cipher/ecc-curves.c ++++ libgcrypt-1.11.0/cipher/ecc-curves.c +@@ -645,7 +645,12 @@ _gcry_ecc_fill_in_curve (unsigned int nb + possible to bypass this check by specifying the curve parameters + directly. */ + if (fips_mode () && !domain_parms[idx].fips ) +- fips_service_indicator_mark_non_compliant (); ++ { ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) ++ return GPG_ERR_NOT_SUPPORTED; ++ else ++ fips_service_indicator_mark_non_compliant (); ++ } + + switch (domain_parms[idx].model) + { +Index: libgcrypt-1.11.0/cipher/pubkey.c +=================================================================== +--- libgcrypt-1.11.0.orig/cipher/pubkey.c ++++ libgcrypt-1.11.0/cipher/pubkey.c +@@ -510,7 +510,12 @@ prepare_datasexp_to_be_signed (const cha + algo = _gcry_md_get_algo (hd); + + if (fips_mode () && algo == GCRY_MD_SHA1) +- fips_service_indicator_mark_non_compliant (); ++ { ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) ++ return GPG_ERR_DIGEST_ALGO; ++ else ++ fips_service_indicator_mark_non_compliant (); ++ } + + digest_name = _gcry_md_algo_name (algo); + digest_size = (int)_gcry_md_get_algo_dlen (algo); +@@ -538,7 +543,12 @@ prepare_datasexp_to_be_signed (const cha + return GPG_ERR_DIGEST_ALGO; + } + else if (fips_mode () && algo == GCRY_MD_SHA1) +- fips_service_indicator_mark_non_compliant (); ++ { ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) ++ return GPG_ERR_DIGEST_ALGO; ++ else ++ fips_service_indicator_mark_non_compliant (); ++ } + + digest_size = (int)_gcry_md_get_algo_dlen (algo); + digest = _gcry_md_read (hd, algo); +@@ -611,11 +621,15 @@ _gcry_pk_sign_md (gcry_sexp_t *r_sig, co + if (rc) + goto leave; + +- if (!spec->flags.fips && fips_mode ()) +- fips_service_indicator_mark_non_compliant (); +- + if (spec->flags.disabled) + rc = GPG_ERR_PUBKEY_ALGO; ++ else if (!spec->flags.fips && fips_mode ()) ++ { ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) ++ return GPG_ERR_PUBKEY_ALGO; ++ else ++ fips_service_indicator_mark_non_compliant (); ++ } + else if (spec->sign) + rc = spec->sign (r_sig, s_data, keyparms); + else +@@ -689,11 +703,15 @@ _gcry_pk_verify_md (gcry_sexp_t s_sig, c + if (rc) + goto leave; + +- if (!spec->flags.fips && fips_mode ()) +- fips_service_indicator_mark_non_compliant (); +- + if (spec->flags.disabled) + rc = GPG_ERR_PUBKEY_ALGO; ++ else if (!spec->flags.fips && fips_mode ()) ++ { ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) ++ return GPG_ERR_PUBKEY_ALGO; ++ else ++ fips_service_indicator_mark_non_compliant (); ++ } + else if (spec->verify) + rc = spec->verify (s_sig, s_data, keyparms); + else +Index: libgcrypt-1.11.0/src/fips.c +=================================================================== +--- libgcrypt-1.11.0.orig/src/fips.c ++++ libgcrypt-1.11.0/src/fips.c +@@ -70,15 +70,30 @@ static enum module_states current_state; + + struct gcry_thread_context { + unsigned long fips_service_indicator; ++ unsigned int flags_reject_non_fips; + }; + + #ifdef HAVE_GCC_STORAGE_CLASS__THREAD +-static __thread struct gcry_thread_context the_tc; ++static __thread struct gcry_thread_context the_tc = { ++ 0, GCRY_FIPS_FLAG_REJECT_DEFAULT ++}; + #else + #error libgcrypt requires thread-local storage to support FIPS mode + #endif + + void ++_gcry_thread_context_set_reject (unsigned int flags) ++{ ++ the_tc.flags_reject_non_fips = flags; ++} ++ ++int ++_gcry_thread_context_check_rejection (unsigned int flag) ++{ ++ return !!(the_tc.flags_reject_non_fips & flag); ++} ++ ++void + _gcry_thread_context_set_fsi (unsigned long fsi) + { + the_tc.fips_service_indicator = fsi; +Index: libgcrypt-1.11.0/src/gcrypt-int.h +=================================================================== +--- libgcrypt-1.11.0.orig/src/gcrypt-int.h ++++ libgcrypt-1.11.0/src/gcrypt-int.h +@@ -297,6 +297,12 @@ void _gcry_set_log_handler (gcry_handler + void _gcry_set_gettext_handler (const char *(*f)(const char*)); + void _gcry_set_progress_handler (gcry_handler_progress_t cb, void *cb_data); + ++void _gcry_thread_context_set_reject (unsigned int flags); ++int _gcry_thread_context_check_rejection (unsigned int flag); ++ ++#define fips_check_rejection(flag) \ ++ _gcry_thread_context_check_rejection (flag) ++ + void _gcry_thread_context_set_fsi (unsigned long fsi); + unsigned long _gcry_thread_context_get_fsi (void); + #define fips_service_indicator_init() do \ +@@ -305,7 +311,8 @@ unsigned long _gcry_thread_context_get_f + _gcry_thread_context_set_fsi (0); \ + } while (0) + /* Should be used only when fips_mode()==TRUE. */ +-#define fips_service_indicator_mark_non_compliant() _gcry_thread_context_set_fsi (1) ++#define fips_service_indicator_mark_non_compliant() \ ++ _gcry_thread_context_set_fsi (1) + + /* Return a pointer to a string containing a description of the error + code in the error value ERR. */ +Index: libgcrypt-1.11.0/src/gcrypt.h.in +=================================================================== +--- libgcrypt-1.11.0.orig/src/gcrypt.h.in ++++ libgcrypt-1.11.0/src/gcrypt.h.in +@@ -338,7 +338,8 @@ enum gcry_ctl_cmds + GCRYCTL_MD_CUSTOMIZE = 88, + GCRYCTL_FIPS_SERVICE_INDICATOR_PK = 89, + GCRYCTL_FIPS_SERVICE_INDICATOR_HASH = 90, +- GCRYCTL_FIPS_SERVICE_INDICATOR = 91 ++ GCRYCTL_FIPS_SERVICE_INDICATOR = 91, ++ GCRYCTL_FIPS_REJECT_NON_FIPS = 92 + }; + + /* Perform various operations defined by CMD. */ +@@ -1971,7 +1972,30 @@ void gcry_log_debugsxp (const char *text + char *gcry_get_config (int mode, const char *what); + + /* Convinience macro to access the FIPS service indicator. */ +-#define gcry_get_fips_service_indicator() gcry_control (GCRYCTL_FIPS_SERVICE_INDICATOR) ++#define gcry_get_fips_service_indicator() \ ++ gcry_control (GCRYCTL_FIPS_SERVICE_INDICATOR) ++ ++#define GCRY_FIPS_FLAG_REJECT_KDF (1 << 0) ++#define GCRY_FIPS_FLAG_REJECT_MD_MD5 (1 << 1) ++#define GCRY_FIPS_FLAG_REJECT_MD_OTHERS (1 << 2) ++#define GCRY_FIPS_FLAG_REJECT_MAC (1 << 3) ++#define GCRY_FIPS_FLAG_REJECT_CIPHER (1 << 4) ++#define GCRY_FIPS_FLAG_REJECT_PK (1 << 5) ++ ++#define GCRY_FIPS_FLAG_REJECT_MD \ ++ (GCRY_FIPS_FLAG_REJECT_MD_MD5 | GCRY_FIPS_FLAG_REJECT_MD_OTHERS) ++ ++/* Note: Don't reject MD5 */ ++#define GCRY_FIPS_FLAG_REJECT_COMPAT110 \ ++ (GCRY_FIPS_FLAG_REJECT_MD_OTHERS \ ++ | GCRY_FIPS_FLAG_REJECT_MAC \ ++ | GCRY_FIPS_FLAG_REJECT_CIPHER \ ++ | GCRY_FIPS_FLAG_REJECT_KDF \ ++ | GCRY_FIPS_FLAG_REJECT_PK) ++ ++#define GCRY_FIPS_FLAG_REJECT_DEFAULT \ ++ GCRY_FIPS_FLAG_REJECT_COMPAT110 ++ + + /* Log levels used by the internal logging facility. */ + enum gcry_log_levels +Index: libgcrypt-1.11.0/src/global.c +=================================================================== +--- libgcrypt-1.11.0.orig/src/global.c ++++ libgcrypt-1.11.0/src/global.c +@@ -791,6 +791,13 @@ _gcry_vcontrol (enum gcry_ctl_cmds cmd, + rc = _gcry_fips_indicator (); + break; + ++ case GCRYCTL_FIPS_REJECT_NON_FIPS: ++ { ++ unsigned int flags = va_arg (arg_ptr, unsigned int); ++ _gcry_thread_context_set_reject (flags); ++ } ++ break; ++ + case GCRYCTL_FIPS_SERVICE_INDICATOR_CIPHER: + /* Get FIPS Service Indicator for a given symmetric algorithm and + * optional mode. Returns GPG_ERR_NO_ERROR if algorithm is allowed or +Index: libgcrypt-1.11.0/tests/t-fips-service-ind.c +=================================================================== +--- libgcrypt-1.11.0.orig/tests/t-fips-service-ind.c ++++ libgcrypt-1.11.0/tests/t-fips-service-ind.c +@@ -1007,6 +1007,8 @@ main (int argc, char **argv) + if (debug) + xgcry_control ((GCRYCTL_SET_DEBUG_FLAGS, 1u , 0)); + ++ xgcry_control ((GCRYCTL_FIPS_REJECT_NON_FIPS, 0)); ++ + check_digests (); + check_kdf_derive (); + check_md_o_w_r_c (); diff --git a/libgcrypt-fips-Introduce-GCRYCTL_FIPS_SERVICE_INDICATOR-and-the-macro.patch b/libgcrypt-fips-Introduce-GCRYCTL_FIPS_SERVICE_INDICATOR-and-the-macro.patch new file mode 100644 index 0000000..9355299 --- /dev/null +++ b/libgcrypt-fips-Introduce-GCRYCTL_FIPS_SERVICE_INDICATOR-and-the-macro.patch @@ -0,0 +1,101 @@ +From f51f4e98930e6b2175e85fe8a95b8b6a15ad5efa Mon Sep 17 00:00:00 2001 +From: NIIBE Yutaka +Date: Thu, 5 Dec 2024 11:34:32 +0900 +Subject: [PATCH 2/5] fips: Introduce GCRYCTL_FIPS_SERVICE_INDICATOR and the + macro. +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* src/fips.c (_gcry_fips_indicator): New. +* src/g10lib.h (_gcry_fips_indicator): New. +* src/gcrypt.h.in (GCRYCTL_FIPS_SERVICE_INDICATOR): New. +(gcry_get_fips_service_indicator): New. +* src/global.c (_gcry_vcontrol): Handle GCRYCTL_FIPS_SERVICE_INDICATOR. + +-- + +GnuPG-bug-id: 7338 +Signed-off-by: NIIBE Yutaka +Signed-off-by: Lucas Mülling +--- + src/fips.c | 11 +++++++++++ + src/g10lib.h | 2 ++ + src/gcrypt.h.in | 6 +++++- + src/global.c | 4 ++++ + 4 files changed, 22 insertions(+), 1 deletion(-) + +Index: libgcrypt-1.11.0/src/fips.c +=================================================================== +--- libgcrypt-1.11.0.orig/src/fips.c ++++ libgcrypt-1.11.0/src/fips.c +@@ -364,6 +364,17 @@ _gcry_fips_test_operational (void) + return result; + } + ++gpg_err_code_t ++_gcry_fips_indicator (void) ++{ ++ /* If anything recorded, it means that the operation is not ++ supported under FIPS mode. */ ++ if (_gcry_thread_context_get_fsi ()) ++ return GPG_ERR_NOT_SUPPORTED; ++ ++ return 0; ++} ++ + int + _gcry_fips_indicator_cipher (va_list arg_ptr) + { +Index: libgcrypt-1.11.0/src/g10lib.h +=================================================================== +--- libgcrypt-1.11.0.orig/src/g10lib.h ++++ libgcrypt-1.11.0/src/g10lib.h +@@ -468,6 +468,8 @@ void _gcry_fips_signal_error (const char + _gcry_fips_signal_error (__FILE__, __LINE__, NULL, 1, (a)) + #endif + ++gpg_err_code_t _gcry_fips_indicator (void); ++ + int _gcry_fips_indicator_cipher (va_list arg_ptr); + int _gcry_fips_indicator_hash (va_list arg_ptr); + int _gcry_fips_indicator_mac (va_list arg_ptr); +Index: libgcrypt-1.11.0/src/gcrypt.h.in +=================================================================== +--- libgcrypt-1.11.0.orig/src/gcrypt.h.in ++++ libgcrypt-1.11.0/src/gcrypt.h.in +@@ -337,7 +337,8 @@ enum gcry_ctl_cmds + GCRYCTL_FIPS_SERVICE_INDICATOR_PK_FLAGS = 87, + GCRYCTL_MD_CUSTOMIZE = 88, + GCRYCTL_FIPS_SERVICE_INDICATOR_PK = 89, +- GCRYCTL_FIPS_SERVICE_INDICATOR_HASH = 90 ++ GCRYCTL_FIPS_SERVICE_INDICATOR_HASH = 90, ++ GCRYCTL_FIPS_SERVICE_INDICATOR = 91 + }; + + /* Perform various operations defined by CMD. */ +@@ -1966,6 +1967,9 @@ void gcry_log_debugsxp (const char *text + + char *gcry_get_config (int mode, const char *what); + ++/* Convinience macro to access the FIPS service indicator. */ ++#define gcry_get_fips_service_indicator() gcry_control (GCRYCTL_FIPS_SERVICE_INDICATOR) ++ + /* Log levels used by the internal logging facility. */ + enum gcry_log_levels + { +Index: libgcrypt-1.11.0/src/global.c +=================================================================== +--- libgcrypt-1.11.0.orig/src/global.c ++++ libgcrypt-1.11.0/src/global.c +@@ -787,6 +787,10 @@ _gcry_vcontrol (enum gcry_ctl_cmds cmd, + rc = _gcry_fips_run_selftests (1); + break; + ++ case GCRYCTL_FIPS_SERVICE_INDICATOR: ++ rc = _gcry_fips_indicator (); ++ break; ++ + case GCRYCTL_FIPS_SERVICE_INDICATOR_CIPHER: + /* Get FIPS Service Indicator for a given symmetric algorithm and + * optional mode. Returns GPG_ERR_NO_ERROR if algorithm is allowed or diff --git a/libgcrypt-fips-Introduce-an-internal-API-for-FIPS-service-indicator.patch b/libgcrypt-fips-Introduce-an-internal-API-for-FIPS-service-indicator.patch new file mode 100644 index 0000000..b452626 --- /dev/null +++ b/libgcrypt-fips-Introduce-an-internal-API-for-FIPS-service-indicator.patch @@ -0,0 +1,332 @@ +From e1cf3123282525693b646499eb7efe4f2be4010a Mon Sep 17 00:00:00 2001 +From: NIIBE Yutaka +Date: Thu, 5 Dec 2024 11:06:37 +0900 +Subject: [PATCH 1/5] fips: Introduce an internal API for FIPS service + indicator. +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* configure.ac (HAVE_GCC_STORAGE_CLASS__THREAD): New. +* src/fips.c (struct gcry_thread_context): New. +(_gcry_thread_context_set_fsi, _gcry_thread_context_get_fsi): New. +* src/gcrypt-int.h (fips_service_indicator_init): New macro. +(fips_service_indicator_mark_success): New macro. +* tests/Makefile.am (tests_bin): Add t-thread-local. +* tests/t-thread-local.c: New. + +-- + +GnuPG-bug-id: 7340 +Signed-off-by: NIIBE Yutaka +Signed-off-by: Lucas Mülling +--- + configure.ac | 14 +++ + src/fips.c | 21 ++++- + src/gcrypt-int.h | 12 +++ + tests/Makefile.am | 2 +- + tests/t-thread-local.c | 196 +++++++++++++++++++++++++++++++++++++++++ + 5 files changed, 243 insertions(+), 2 deletions(-) + create mode 100644 tests/t-thread-local.c + +diff --git a/configure.ac b/configure.ac +index a7f922b1..d708f89a 100644 +--- a/configure.ac ++++ b/configure.ac +@@ -1489,6 +1489,20 @@ if test "$gcry_cv_gcc_attribute_sysv_abi" = "yes" ; then + fi + fi + ++# ++# Check whether compiler support '__thread' storage class specifier. ++# ++AC_CACHE_CHECK([whether compiler supports '__thread' storage class specifier], ++ [gcry_cv_gcc_storage_class__thread], ++ [gcry_cv_gcc_storage_class__thread=no ++ AC_COMPILE_IFELSE([AC_LANG_PROGRAM([#include ], ++ [static __thread int bar;] ++ )], ++ [gcry_cv_gcc_storage_class__thread=yes])]) ++if test "$gcry_cv_gcc_storage_class__thread" = "yes" ; then ++ AC_DEFINE(HAVE_GCC_STORAGE_CLASS__THREAD,1, ++ [Defined if compiler supports "__thread" storage class specifier]) ++fi + + # Restore flags. + CFLAGS=$_gcc_cflags_save; +diff --git a/src/fips.c b/src/fips.c +index cf91baa8..58fb69df 100644 +--- a/src/fips.c ++++ b/src/fips.c +@@ -67,10 +67,29 @@ GPGRT_LOCK_DEFINE (fsm_lock); + used while in fips mode. Change this only while holding fsm_lock. */ + static enum module_states current_state; + ++struct gcry_thread_context { ++ unsigned long fips_service_indicator; ++}; ++ ++#ifdef HAVE_GCC_STORAGE_CLASS__THREAD ++static __thread struct gcry_thread_context the_tc; ++#else ++#error libgcrypt requires thread-local storage to support FIPS mode ++#endif ++ ++void ++_gcry_thread_context_set_fsi (unsigned long fsi) ++{ ++ the_tc.fips_service_indicator = fsi; ++} + ++unsigned long ++_gcry_thread_context_get_fsi (void) ++{ ++ return the_tc.fips_service_indicator; ++} + + +- + static void fips_new_state (enum module_states new_state); + + +diff --git a/src/gcrypt-int.h b/src/gcrypt-int.h +index 074ea071..7f894737 100644 +--- a/src/gcrypt-int.h ++++ b/src/gcrypt-int.h +@@ -298,6 +298,18 @@ void _gcry_set_log_handler (gcry_handler_log_t f, void *opaque); + void _gcry_set_gettext_handler (const char *(*f)(const char*)); + void _gcry_set_progress_handler (gcry_handler_progress_t cb, void *cb_data); + ++void _gcry_thread_context_set_fsi (unsigned long fsi); ++unsigned long _gcry_thread_context_get_fsi (void); ++#define fips_service_indicator_init() do \ ++ { \ ++ if (fips_mode ()) \ ++ _gcry_thread_context_set_fsi (1); \ ++ } while (0) ++#define fips_service_indicator_mark_success(is_compliant) do \ ++ { \ ++ if (is_compliant && fips_mode ()) \ ++ _gcry_thread_context_set_fsi (0); \ ++ } while (0) + + /* Return a pointer to a string containing a description of the error + code in the error value ERR. */ +diff --git a/tests/Makefile.am b/tests/Makefile.am +index 423bc1cd..52f7dd61 100644 +--- a/tests/Makefile.am ++++ b/tests/Makefile.am +@@ -25,7 +25,7 @@ tests_bin = \ + version t-secmem mpitests t-sexp t-convert \ + t-mpi-bit t-mpi-point t-lock \ + prime basic keygen pubkey hmac hashtest t-kdf keygrip \ +- aeswrap random t-kem t-mlkem ++ aeswrap random t-kem t-mlkem t-thread-local + + if USE_RSA + tests_bin += pkcs1v2 t-rsa-pss t-rsa-15 t-rsa-testparm +diff --git a/tests/t-thread-local.c b/tests/t-thread-local.c +new file mode 100644 +index 00000000..285f197f +--- /dev/null ++++ b/tests/t-thread-local.c +@@ -0,0 +1,196 @@ ++/* t-mlkem.c - Check the thread local storage ++ * Copyright (C) 2024 g10 Code GmbH ++ * ++ * This file is part of Libgcrypt. ++ * ++ * Libgcrypt is free software; you can redistribute it and/or modify ++ * it under the terms of the GNU Lesser General Public License as ++ * published by the Free Software Foundation; either version 2.1 of ++ * the License, or (at your option) any later version. ++ * ++ * Libgcrypt 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 Lesser General Public License for more details. ++ * ++ * You should have received a copy of the GNU Lesser General Public License ++ * along with this program; if not, see . ++ * SPDX-License-Identifier: LGPL-2.1+ ++ */ ++ ++/* For now, this program simply test __thread storage class specifier. ++ * After we implement thread local context for libgcrypt, we will ++ * modity to test the feature. */ ++ ++#ifdef HAVE_CONFIG_H ++#include ++#endif ++#include ++#include ++#include ++#include ++#include ++#include ++#if HAVE_PTHREAD ++# include ++#endif ++ ++#define PGM "t-thread-local" ++ ++#include "t-common.h" ++#include "../src/gcrypt-testapi.h" ++ ++/* Mingw requires us to include windows.h after winsock2.h which is ++ included by gcrypt.h. */ ++#ifdef _WIN32 ++# include ++#endif ++ ++#ifdef _WIN32 ++# define THREAD_RET_TYPE DWORD WINAPI ++# define THREAD_RET_VALUE 0 ++#else ++# define THREAD_RET_TYPE void * ++# define THREAD_RET_VALUE NULL ++#endif ++ ++#define N_TESTS 1 ++ ++#define N_THREADS 19 ++ ++static __thread unsigned long t; ++ ++struct thread_arg_s ++{ ++ int no; ++}; ++ ++#if defined(HAVE_PTHREAD) || defined(_WIN32) ++/* Checking the local storage thread. */ ++static THREAD_RET_TYPE ++check_ls_thread (void *argarg) ++{ ++ struct thread_arg_s *arg = argarg; ++ ++ t = arg->no; ++ info ("a thread update the local storage: %lu", t); ++ ++ gcry_free (arg); ++ return THREAD_RET_VALUE; ++} ++#endif ++ ++static void ++check_thread_local (void) ++{ ++ struct thread_arg_s *arg; ++ ++#ifdef _WIN32 ++ HANDLE threads[N_THREADS]; ++ int i; ++ int rc; ++ ++ t = N_THREADS; ++ for (i=0; i < N_THREADS; i++) ++ { ++ arg = gcry_xmalloc (sizeof *arg); ++ arg->no = i; ++ threads[i] = CreateThread (NULL, 0, check_ls_thread, arg, 0, NULL); ++ if (!threads[i]) ++ die ("error creating a thread %d: rc=%d", ++ i, (int)GetLastError ()); ++ } ++ ++ for (i=0; i < N_THREADS; i++) ++ { ++ rc = WaitForSingleObject (threads[i], INFINITE); ++ if (rc == WAIT_OBJECT_0) ++ info ("a thread %d has terminated", i); ++ else ++ fail ("waiting for a thread %d failed: %d", ++ i, (int)GetLastError ()); ++ CloseHandle (threads[i]); ++ } ++ ++#elif HAVE_PTHREAD ++ pthread_t threads[N_THREADS]; ++ int rc, i; ++ ++ t = N_THREADS; ++ for (i=0; i < N_THREADS; i++) ++ { ++ arg = gcry_xmalloc (sizeof *arg); ++ arg->no = i; ++ pthread_create (&threads[i], NULL, check_ls_thread, arg); ++ } ++ ++ for (i=0; i < N_THREADS; i++) ++ { ++ rc = pthread_join (threads[i], NULL); ++ if (rc) ++ fail ("pthread_join failed for a thread %d: %s", ++ i, strerror (errno)); ++ else ++ info ("a thread %d has terminated", i); ++ } ++#else ++ (void)arg; ++#endif /*!_WIN32*/ ++ if (t != N_THREADS) ++ fail ("failed t=%lu\n", t); ++ else ++ info ("success"); ++} ++ ++int ++main (int argc, char **argv) ++{ ++ int last_argc = -1; ++ ++ if (argc) ++ { argc--; argv++; } ++ ++ while (argc && last_argc != argc) ++ { ++ last_argc = argc; ++ if (!strcmp (*argv, "--")) ++ { ++ argc--; argv++; ++ break; ++ } ++ else if (!strcmp (*argv, "--help")) ++ { ++ fputs ("usage: " PGM " [options]\n" ++ "Options:\n" ++ " --verbose print timings etc.\n" ++ " --debug flyswatter\n", ++ stdout); ++ exit (0); ++ } ++ else if (!strcmp (*argv, "--verbose")) ++ { ++ verbose++; ++ argc--; argv++; ++ } ++ else if (!strcmp (*argv, "--debug")) ++ { ++ verbose += 2; ++ debug++; ++ argc--; argv++; ++ } ++ else if (!strncmp (*argv, "--", 2)) ++ die ("unknown option '%s'", *argv); ++ } ++ ++ xgcry_control ((GCRYCTL_DISABLE_SECMEM, 0)); ++ if (!gcry_check_version (GCRYPT_VERSION)) ++ die ("version mismatch\n"); ++ if (debug) ++ xgcry_control ((GCRYCTL_SET_DEBUG_FLAGS, 1u , 0)); ++ xgcry_control ((GCRYCTL_ENABLE_QUICK_RANDOM, 0)); ++ xgcry_control ((GCRYCTL_INITIALIZATION_FINISHED, 0)); ++ ++ check_thread_local (); ++ ++ return !!error_count; ++} +-- +2.49.0 + diff --git a/libgcrypt-fips-Rejection-by-GCRYCTL_FIPS_REJECT_NON_FIPS-not-by-open-flags.patch b/libgcrypt-fips-Rejection-by-GCRYCTL_FIPS_REJECT_NON_FIPS-not-by-open-flags.patch new file mode 100644 index 0000000..6d18f18 --- /dev/null +++ b/libgcrypt-fips-Rejection-by-GCRYCTL_FIPS_REJECT_NON_FIPS-not-by-open-flags.patch @@ -0,0 +1,498 @@ +From d060dd58b82882dec0d8bfcc593536bc0083b4b1 Mon Sep 17 00:00:00 2001 +From: NIIBE Yutaka +Date: Fri, 20 Dec 2024 09:38:13 +0900 +Subject: [PATCH 14/19] fips: Rejection by GCRYCTL_FIPS_REJECT_NON_FIPS, not by + open flags. +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* src/gcrypt.h.in (GCRY_CIPHER_FLAG_REJECT_NON_FIPS): Remove. +(GCRY_MD_FLAG_REJECT_NON_FIPS): Remove. +(GCRY_MAC_FLAG_REJECT_NON_FIPS): Remove. +* tests/t-fips-service-ind.c: Update tests with +GCRYCTL_FIPS_REJECT_NON_FIPS. +* cipher/cipher.c (_gcry_cipher_open_internal, cipher_setkey): Use +fips_check_rejection. +* cipher/mac.c (mac_open): Likewise. +* cipher/md.c (struct gcry_md_context): Remove reject_non_fips. +(md_open, md_enable): Use fips_check_rejection. +(_gcry_md_enable, md_copy): Likewise. + +-- + +GnuPG-bug-id: 7338 +Signed-off-by: NIIBE Yutaka +Signed-off-by: Lucas Mülling +--- + cipher/cipher.c | 8 ++-- + cipher/mac.c | 5 +-- + cipher/md.c | 81 ++++++++++++++++++++++++++++++-------- + src/gcrypt.h.in | 7 +--- + tests/t-fips-service-ind.c | 59 +++++++++++---------------- + 5 files changed, 94 insertions(+), 66 deletions(-) + +Index: libgcrypt-1.11.0/cipher/cipher.c +=================================================================== +--- libgcrypt-1.11.0.orig/cipher/cipher.c ++++ libgcrypt-1.11.0/cipher/cipher.c +@@ -510,7 +510,6 @@ _gcry_cipher_open_internal (gcry_cipher_ + int algo, int mode, unsigned int flags) + { + int secure = !!(flags & GCRY_CIPHER_SECURE); +- int reject_non_fips = !!(flags & GCRY_CIPHER_FLAG_REJECT_NON_FIPS); + gcry_cipher_spec_t *spec; + gcry_cipher_hd_t h = NULL; + gcry_err_code_t err; +@@ -526,7 +525,7 @@ _gcry_cipher_open_internal (gcry_cipher_ + err = GPG_ERR_CIPHER_ALGO; + else if (!spec->flags.fips && fips_mode ()) + { +- if (reject_non_fips) ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_CIPHER)) + err = GPG_ERR_CIPHER_ALGO; + else + { +@@ -544,8 +543,7 @@ _gcry_cipher_open_internal (gcry_cipher_ + | GCRY_CIPHER_ENABLE_SYNC + | GCRY_CIPHER_CBC_CTS + | GCRY_CIPHER_CBC_MAC +- | GCRY_CIPHER_EXTENDED +- | GCRY_CIPHER_FLAG_REJECT_NON_FIPS)) ++ | GCRY_CIPHER_EXTENDED)) + || ((flags & GCRY_CIPHER_CBC_CTS) && (flags & GCRY_CIPHER_CBC_MAC)))) + err = GPG_ERR_CIPHER_ALGO; + +@@ -776,7 +774,7 @@ cipher_setkey (gcry_cipher_hd_t c, byte + Key Generation Requirements" for details. */ + if (buf_eq_const (key, key + keylen, keylen)) + { +- if ((c->flags & GCRY_CIPHER_FLAG_REJECT_NON_FIPS)) ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_CIPHER)) + return GPG_ERR_WEAK_KEY; + else + fips_service_indicator_mark_non_compliant (); +Index: libgcrypt-1.11.0/cipher/mac.c +=================================================================== +--- libgcrypt-1.11.0.orig/cipher/mac.c ++++ libgcrypt-1.11.0/cipher/mac.c +@@ -519,7 +519,6 @@ mac_open (gcry_mac_hd_t * hd, int algo, + gcry_err_code_t err; + gcry_mac_hd_t h; + int secure = !!(flags & GCRY_MAC_FLAG_SECURE); +- int reject_non_fips = !!(flags & GCRY_MAC_FLAG_REJECT_NON_FIPS); + + spec = spec_from_algo (algo); + if (!spec) +@@ -528,7 +527,7 @@ mac_open (gcry_mac_hd_t * hd, int algo, + return GPG_ERR_MAC_ALGO; + else if (!spec->flags.fips && fips_mode ()) + { +- if (reject_non_fips) ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_MAC)) + return GPG_ERR_MAC_ALGO; + else + fips_service_indicator_mark_non_compliant (); +@@ -650,7 +649,7 @@ _gcry_mac_open (gcry_mac_hd_t * h, int a + gcry_err_code_t rc; + gcry_mac_hd_t hd = NULL; + +- if ((flags & ~(GCRY_MAC_FLAG_SECURE | GCRY_MAC_FLAG_REJECT_NON_FIPS))) ++ if ((flags & ~GCRY_MAC_FLAG_SECURE)) + rc = GPG_ERR_INV_ARG; + else + rc = mac_open (&hd, algo, flags, ctx); +Index: libgcrypt-1.11.0/cipher/md.c +=================================================================== +--- libgcrypt-1.11.0.orig/cipher/md.c ++++ libgcrypt-1.11.0/cipher/md.c +@@ -275,7 +275,6 @@ struct gcry_md_context + unsigned int finalized:1; + unsigned int bugemu1:1; + unsigned int hmac:1; +- unsigned int reject_non_fips:1; + } flags; + size_t actual_handle_size; /* Allocated size of this handle. */ + FILE *debug; +@@ -509,7 +508,6 @@ md_open (gcry_md_hd_t *h, int algo, unsi + ctx->flags.secure = secure; + ctx->flags.hmac = hmac; + ctx->flags.bugemu1 = !!(flags & GCRY_MD_FLAG_BUGEMU1); +- ctx->flags.reject_non_fips = !!(flags & GCRY_MD_FLAG_REJECT_NON_FIPS); + } + + if (! err) +@@ -544,14 +542,11 @@ _gcry_md_open (gcry_md_hd_t *h, int algo + + if ((flags & ~(GCRY_MD_FLAG_SECURE + | GCRY_MD_FLAG_HMAC +- | GCRY_MD_FLAG_REJECT_NON_FIPS + | GCRY_MD_FLAG_BUGEMU1))) + rc = GPG_ERR_INV_ARG; + else + rc = md_open (&hd, algo, flags); + +- *h = rc? NULL : hd; +- + if (!rc && fips_mode ()) + { + GcryDigestEntry *entry = hd->ctx->list; +@@ -566,9 +561,26 @@ _gcry_md_open (gcry_md_hd_t *h, int algo + } + + if (!is_compliant_algo) +- fips_service_indicator_mark_non_compliant (); ++ { ++ int reject = 0; ++ ++ if (algo == GCRY_MD_MD5) ++ reject = fips_check_rejection (GCRY_FIPS_FLAG_REJECT_MD_MD5); ++ else ++ reject = fips_check_rejection (GCRY_FIPS_FLAG_REJECT_MD_OTHERS); ++ ++ if (reject) ++ { ++ md_close (hd); ++ hd = NULL; ++ rc = GPG_ERR_DIGEST_ALGO; ++ } ++ else ++ fips_service_indicator_mark_non_compliant (); ++ } + } + ++ *h = rc? NULL : hd; + return rc; + } + +@@ -581,12 +593,17 @@ md_enable (gcry_md_hd_t hd, int algorith + const gcry_md_spec_t *spec; + GcryDigestEntry *entry; + gcry_err_code_t err = 0; +- int reject_non_fips = h->flags.reject_non_fips; ++ int reject; + + for (entry = h->list; entry; entry = entry->next) + if (entry->spec->algo == algorithm) + return 0; /* Already enabled */ + ++ if (algorithm == GCRY_MD_MD5) ++ reject = fips_check_rejection (GCRY_FIPS_FLAG_REJECT_MD_MD5); ++ else ++ reject = fips_check_rejection (GCRY_FIPS_FLAG_REJECT_MD_OTHERS); ++ + spec = spec_from_algo (algorithm); + if (!spec) + { +@@ -598,7 +615,7 @@ md_enable (gcry_md_hd_t hd, int algorith + err = GPG_ERR_DIGEST_ALGO; + + /* Any non-FIPS algorithm should go this way */ +- if (!err && reject_non_fips && !spec->flags.fips && fips_mode ()) ++ if (!err && reject && !spec->flags.fips && fips_mode ()) + err = GPG_ERR_DIGEST_ALGO; + + if (!err && h->flags.hmac && spec->read == NULL) +@@ -657,7 +674,19 @@ _gcry_md_enable (gcry_md_hd_t hd, int al + } + + if (!is_compliant_algo) +- fips_service_indicator_mark_non_compliant (); ++ { ++ int reject = 0; ++ ++ if (algorithm == GCRY_MD_MD5) ++ reject = fips_check_rejection (GCRY_FIPS_FLAG_REJECT_MD_MD5); ++ else ++ reject = fips_check_rejection (GCRY_FIPS_FLAG_REJECT_MD_OTHERS); ++ ++ if (reject) ++ rc = GPG_ERR_DIGEST_ALGO; ++ else ++ fips_service_indicator_mark_non_compliant (); ++ } + } + + return rc; +@@ -667,13 +696,14 @@ _gcry_md_enable (gcry_md_hd_t hd, int al + static gcry_err_code_t + md_copy (gcry_md_hd_t ahd, gcry_md_hd_t *b_hd) + { +- gcry_err_code_t err = 0; ++ gcry_err_code_t rc = 0; + struct gcry_md_context *a = ahd->ctx; + struct gcry_md_context *b; + GcryDigestEntry *ar, *br; + gcry_md_hd_t bhd; + size_t n; + int is_compliant_algo = 1; ++ int reject = 0; + + if (ahd->bufpos) + md_write (ahd, NULL, 0); +@@ -686,7 +716,7 @@ md_copy (gcry_md_hd_t ahd, gcry_md_hd_t + + if (!bhd) + { +- err = gpg_err_code_from_syserror (); ++ rc = gpg_err_code_from_syserror (); + goto leave; + } + +@@ -715,12 +745,20 @@ md_copy (gcry_md_hd_t ahd, gcry_md_hd_t + br = xtrymalloc (ar->actual_struct_size); + if (!br) + { +- err = gpg_err_code_from_syserror (); ++ rc = gpg_err_code_from_syserror (); + md_close (bhd); + goto leave; + } + +- is_compliant_algo &= spec->flags.fips; ++ if (!spec->flags.fips) ++ { ++ is_compliant_algo = 0; ++ ++ if (spec->algo == GCRY_MD_MD5) ++ reject |= fips_check_rejection (GCRY_FIPS_FLAG_REJECT_MD_MD5); ++ else ++ reject |= fips_check_rejection (GCRY_FIPS_FLAG_REJECT_MD_OTHERS); ++ } + + memcpy (br, ar, ar->actual_struct_size); + br->next = b->list; +@@ -730,13 +768,22 @@ md_copy (gcry_md_hd_t ahd, gcry_md_hd_t + if (a->debug) + md_start_debug (bhd, "unknown"); + +- *b_hd = bhd; ++ if (!is_compliant_algo && fips_mode ()) ++ { ++ if (reject) ++ { ++ rc = GPG_ERR_DIGEST_ALGO; ++ md_close (bhd); ++ } ++ else ++ fips_service_indicator_mark_non_compliant (); ++ } + +- if (!is_compliant_algo) +- fips_service_indicator_mark_non_compliant (); ++ if (!rc) ++ *b_hd = bhd; + + leave: +- return err; ++ return rc; + } + + +Index: libgcrypt-1.11.0/src/gcrypt.h.in +=================================================================== +--- libgcrypt-1.11.0.orig/src/gcrypt.h.in ++++ libgcrypt-1.11.0/src/gcrypt.h.in +@@ -995,8 +995,7 @@ enum gcry_cipher_flags + GCRY_CIPHER_ENABLE_SYNC = 2, /* Enable CFB sync mode. */ + GCRY_CIPHER_CBC_CTS = 4, /* Enable CBC cipher text stealing (CTS). */ + GCRY_CIPHER_CBC_MAC = 8, /* Enable CBC message auth. code (MAC). */ +- GCRY_CIPHER_EXTENDED = 16, /* Enable extended AES-WRAP. */ +- GCRY_CIPHER_FLAG_REJECT_NON_FIPS = 32 /* Reject non-FIPS-compliant algo. */ ++ GCRY_CIPHER_EXTENDED = 16 /* Enable extended AES-WRAP. */ + }; + + /* Methods used for AEAD IV generation. */ +@@ -1322,7 +1321,6 @@ enum gcry_md_flags + { + GCRY_MD_FLAG_SECURE = 1, /* Allocate all buffers in "secure" memory. */ + GCRY_MD_FLAG_HMAC = 2, /* Make an HMAC out of this algorithm. */ +- GCRY_MD_FLAG_REJECT_NON_FIPS = 4, /* Reject non-FIPS-compliant algo. */ + GCRY_MD_FLAG_BUGEMU1 = 0x0100 + }; + +@@ -1564,8 +1562,7 @@ enum gcry_mac_algos + /* Flags used with the open function. */ + enum gcry_mac_flags + { +- GCRY_MAC_FLAG_SECURE = 1, /* Allocate all buffers in "secure" memory. */ +- GCRY_MAC_FLAG_REJECT_NON_FIPS = 2 /* Reject non-FIPS-compliant algo. */ ++ GCRY_MAC_FLAG_SECURE = 1 /* Allocate all buffers in "secure" memory. */ + }; + + /* Create a MAC handle for algorithm ALGO. FLAGS may be given as an bitwise OR +Index: libgcrypt-1.11.0/tests/t-fips-service-ind.c +=================================================================== +--- libgcrypt-1.11.0.orig/tests/t-fips-service-ind.c ++++ libgcrypt-1.11.0/tests/t-fips-service-ind.c +@@ -250,7 +250,7 @@ check_pk_hash_sign_verify (void) + /* Check gcry_cipher_open, gcry_cipher_setkey, gcry_cipher_encrypt, + gcry_cipher_decrypt, gcry_cipher_close API. */ + static void +-check_cipher_o_s_e_d_c (void) ++check_cipher_o_s_e_d_c (int reject) + { + static struct { + int algo; +@@ -258,18 +258,12 @@ check_cipher_o_s_e_d_c (void) + int keylen; + const char *expect; + int expect_failure; +- unsigned int flags; + } tv[] = { + #if USE_DES + { GCRY_CIPHER_3DES, + "\xe3\x34\x7a\x6b\x0b\xc1\x15\x2c\x64\x2a\x25\xcb\xd3\xbc\x31\xab" + "\xfb\xa1\x62\xa8\x1f\x19\x7c\x15", 24, + "\x3f\x1a\xb8\x83\x18\x8b\xb5\x97", 1 }, +- { GCRY_CIPHER_3DES, +- "\xe3\x34\x7a\x6b\x0b\xc1\x15\x2c\x64\x2a\x25\xcb\xd3\xbc\x31\xab" +- "\xfb\xa1\x62\xa8\x1f\x19\x7c\x15", 24, +- "\x3f\x1a\xb8\x83\x18\x8b\xb5\x97", +- 1, GCRY_CIPHER_FLAG_REJECT_NON_FIPS }, + #endif + { GCRY_CIPHER_AES, + "\x2b\x7e\x15\x16\x28\xae\xd2\xa6\xab\xf7\x15\x88\x09\xcf\x4f\x3c", 16, +@@ -297,12 +291,10 @@ check_cipher_o_s_e_d_c (void) + assert (blklen != 0); + assert (blklen <= ptlen); + assert (blklen <= DIM (out)); +- err = gcry_cipher_open (&h, tv[tvidx].algo, GCRY_CIPHER_MODE_ECB, +- tv[tvidx].flags); ++ err = gcry_cipher_open (&h, tv[tvidx].algo, GCRY_CIPHER_MODE_ECB, 0); + if (err) + { +- if (in_fips_mode && (tv[tvidx].flags & GCRY_CIPHER_FLAG_REJECT_NON_FIPS) +- && tv[tvidx].expect_failure) ++ if (in_fips_mode && reject && tv[tvidx].expect_failure) + /* Here, an error is expected */ + ; + else +@@ -312,8 +304,7 @@ check_cipher_o_s_e_d_c (void) + } + else + { +- if (in_fips_mode && (tv[tvidx].flags & GCRY_CIPHER_FLAG_REJECT_NON_FIPS) +- && tv[tvidx].expect_failure) ++ if (in_fips_mode && reject && tv[tvidx].expect_failure) + /* This case, an error is expected, but we observed success */ + fail ("gcry_cipher_open test %d unexpectedly succeeded\n", tvidx); + } +@@ -398,7 +389,7 @@ check_cipher_o_s_e_d_c (void) + /* Check gcry_mac_open, gcry_mac_write, gcry_mac_write, gcry_mac_read, + gcry_mac_close API. */ + static void +-check_mac_o_w_r_c (void) ++check_mac_o_w_r_c (int reject) + { + static struct { + int algo; +@@ -408,14 +399,10 @@ check_mac_o_w_r_c (void) + int keylen; + const char *expect; + int expect_failure; +- unsigned int flags; + } tv[] = { + #if USE_MD5 + { GCRY_MAC_HMAC_MD5, "hmac input abc", 14, "hmac key input", 14, + "\x0d\x72\xd0\x60\xaf\x34\xf2\xca\x33\x58\xa9\xcc\xd3\x5a\xac\xb5", 1 }, +- { GCRY_MAC_HMAC_MD5, "hmac input abc", 14, "hmac key input", 14, +- "\x0d\x72\xd0\x60\xaf\x34\xf2\xca\x33\x58\xa9\xcc\xd3\x5a\xac\xb5", 1, +- GCRY_MAC_FLAG_REJECT_NON_FIPS }, + #endif + #if USE_SHA1 + { GCRY_MAC_HMAC_SHA1, "hmac input abc", 14, "hmac key input", 14, +@@ -471,11 +458,10 @@ check_mac_o_w_r_c (void) + expectlen = gcry_mac_get_algo_maclen (tv[tvidx].algo); + assert (expectlen != 0); + assert (expectlen <= DIM (mac)); +- err = gcry_mac_open (&h, tv[tvidx].algo, tv[tvidx].flags, NULL); ++ err = gcry_mac_open (&h, tv[tvidx].algo, 0, NULL); + if (err) + { +- if (in_fips_mode && (tv[tvidx].flags & GCRY_MAC_FLAG_REJECT_NON_FIPS) +- && tv[tvidx].expect_failure) ++ if (in_fips_mode && reject && tv[tvidx].expect_failure) + /* Here, an error is expected */ + ; + else +@@ -485,8 +471,7 @@ check_mac_o_w_r_c (void) + } + else + { +- if (in_fips_mode && (tv[tvidx].flags & GCRY_MAC_FLAG_REJECT_NON_FIPS) +- && tv[tvidx].expect_failure) ++ if (in_fips_mode && reject && tv[tvidx].expect_failure) + /* This case, an error is expected, but we observed success */ + fail ("gcry_mac_open test %d unexpectedly succeeded\n", tvidx); + } +@@ -563,7 +548,7 @@ check_mac_o_w_r_c (void) + /* Check gcry_md_open, gcry_md_write, gcry_md_write, gcry_md_read, + gcry_md_close API. */ + static void +-check_md_o_w_r_c (void) ++check_md_o_w_r_c (int reject) + { + static struct { + int algo; +@@ -571,14 +556,10 @@ check_md_o_w_r_c (void) + int datalen; + const char *expect; + int expect_failure; +- unsigned int flags; + } tv[] = { + #if USE_MD5 + { GCRY_MD_MD5, "abc", 3, + "\x90\x01\x50\x98\x3C\xD2\x4F\xB0\xD6\x96\x3F\x7D\x28\xE1\x7F\x72", 1 }, +- { GCRY_MD_MD5, "abc", 3, +- "\x90\x01\x50\x98\x3C\xD2\x4F\xB0\xD6\x96\x3F\x7D\x28\xE1\x7F\x72", 1, +- GCRY_MD_FLAG_REJECT_NON_FIPS }, + #endif + #if USE_SHA1 + { GCRY_MD_SHA1, "abc", 3, +@@ -632,11 +613,10 @@ check_md_o_w_r_c (void) + + expectlen = gcry_md_get_algo_dlen (tv[tvidx].algo); + assert (expectlen != 0); +- err = gcry_md_open (&h, tv[tvidx].algo, tv[tvidx].flags); ++ err = gcry_md_open (&h, tv[tvidx].algo, 0); + if (err) + { +- if (in_fips_mode && (tv[tvidx].flags & GCRY_MD_FLAG_REJECT_NON_FIPS) +- && tv[tvidx].expect_failure) ++ if (in_fips_mode && reject && tv[tvidx].expect_failure) + /* Here, an error is expected */ + ; + else +@@ -646,8 +626,7 @@ check_md_o_w_r_c (void) + } + else + { +- if (in_fips_mode && (tv[tvidx].flags & GCRY_MD_FLAG_REJECT_NON_FIPS) +- && tv[tvidx].expect_failure) ++ if (in_fips_mode && reject && tv[tvidx].expect_failure) + /* This case, an error is expected, but we observed success */ + fail ("gcry_md_open test %d unexpectedly succeeded\n", tvidx); + } +@@ -1011,10 +990,18 @@ main (int argc, char **argv) + + check_digests (); + check_kdf_derive (); +- check_md_o_w_r_c (); +- check_mac_o_w_r_c (); +- check_cipher_o_s_e_d_c (); ++ check_md_o_w_r_c (0); ++ check_mac_o_w_r_c (0); ++ check_cipher_o_s_e_d_c (0); + check_pk_hash_sign_verify (); + ++ xgcry_control ((GCRYCTL_FIPS_REJECT_NON_FIPS, ++ (GCRY_FIPS_FLAG_REJECT_MD_MD5 ++ | GCRY_FIPS_FLAG_REJECT_COMPAT110))); ++ ++ check_md_o_w_r_c (1); ++ check_mac_o_w_r_c (1); ++ check_cipher_o_s_e_d_c (1); ++ + return !!error_count; + } diff --git a/libgcrypt-fips-cipher-Add-GCRY_FIPS_FLAG_REJECT_PK_FLAGS.patch b/libgcrypt-fips-cipher-Add-GCRY_FIPS_FLAG_REJECT_PK_FLAGS.patch new file mode 100644 index 0000000..310e5e5 --- /dev/null +++ b/libgcrypt-fips-cipher-Add-GCRY_FIPS_FLAG_REJECT_PK_FLAGS.patch @@ -0,0 +1,80 @@ +From 0414e126b939f0b11ecf441908d923e87c1caf02 Mon Sep 17 00:00:00 2001 +From: NIIBE Yutaka +Date: Thu, 6 Mar 2025 08:57:51 +0900 +Subject: [PATCH 06/14] fips,cipher: Add GCRY_FIPS_FLAG_REJECT_PK_FLAGS. +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* src/gcrypt.h.in (GCRY_FIPS_FLAG_REJECT_PK_FLAGS): New. +* cipher/pubkey-util.c (_gcry_pk_util_parse_flaglist): Keep the +behavior of 1.10. +* cipher/rsa.c (rsa_decrypt, rsa_sign): Likewise. + +-- + +GnuPG-bug-id: 7338 +Signed-off-by: NIIBE Yutaka +Signed-off-by: Lucas Mülling +--- + cipher/pubkey-util.c | 2 +- + cipher/rsa.c | 4 ++-- + src/gcrypt.h.in | 3 ++- + 3 files changed, 5 insertions(+), 4 deletions(-) + +diff --git a/cipher/pubkey-util.c b/cipher/pubkey-util.c +index 9c927638..e7355569 100644 +--- a/cipher/pubkey-util.c ++++ b/cipher/pubkey-util.c +@@ -202,7 +202,7 @@ _gcry_pk_util_parse_flaglist (gcry_sexp_t list, + + if (fips_mode () && igninvflag) + { +- if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK_FLAGS)) + rc = GPG_ERR_INV_FLAG; + else + fips_service_indicator_mark_non_compliant (); +diff --git a/cipher/rsa.c b/cipher/rsa.c +index dce76414..7e086df4 100644 +--- a/cipher/rsa.c ++++ b/cipher/rsa.c +@@ -1504,7 +1504,7 @@ rsa_decrypt (gcry_sexp_t *r_plain, gcry_sexp_t s_data, gcry_sexp_t keyparms) + { + if (fips_mode ()) + { +- if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK_FLAGS)) + { + rc = GPG_ERR_INV_FLAG; + goto leave; +@@ -1649,7 +1649,7 @@ rsa_sign (gcry_sexp_t *r_sig, gcry_sexp_t s_data, gcry_sexp_t keyparms) + { + if (fips_mode ()) + { +- if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK_FLAGS)) + { + rc = GPG_ERR_INV_FLAG; + goto leave; +diff --git a/src/gcrypt.h.in b/src/gcrypt.h.in +index fe3db16a..a282268d 100644 +--- a/src/gcrypt.h.in ++++ b/src/gcrypt.h.in +@@ -1991,11 +1991,12 @@ char *gcry_get_config (int mode, const char *what); + #define GCRY_FIPS_FLAG_REJECT_CIPHER_MODE (1 << 8) + /**/ + #define GCRY_FIPS_FLAG_REJECT_PK_ECC_K (1 << 10) ++#define GCRY_FIPS_FLAG_REJECT_PK_FLAGS (1 << 11) + + #define GCRY_FIPS_FLAG_REJECT_MD \ + (GCRY_FIPS_FLAG_REJECT_MD_MD5 | GCRY_FIPS_FLAG_REJECT_MD_OTHERS) + +-/* Note: Don't reject MD5, PK MD, PK GOST and PK SM2 */ ++/* Note: Don't reject MD5, PK MD, PK GOST, PK SM2, PK ECC K, and PK FLAGS */ + #define GCRY_FIPS_FLAG_REJECT_COMPAT110 \ + (GCRY_FIPS_FLAG_REJECT_MD_OTHERS \ + | GCRY_FIPS_FLAG_REJECT_MAC \ +-- +2.49.0 + diff --git a/libgcrypt-fips-cipher-Add-behavior-not-to-reject-but-mark-non-compliant.patch b/libgcrypt-fips-cipher-Add-behavior-not-to-reject-but-mark-non-compliant.patch new file mode 100644 index 0000000..9fc7734 --- /dev/null +++ b/libgcrypt-fips-cipher-Add-behavior-not-to-reject-but-mark-non-compliant.patch @@ -0,0 +1,300 @@ +From a776b692669af7a6c089779989b626c4795e30b0 Mon Sep 17 00:00:00 2001 +From: NIIBE Yutaka +Date: Fri, 20 Dec 2024 13:36:12 +0900 +Subject: [PATCH 15/19] fips,cipher: Add behavior not to reject but mark + non-compliant. +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* cipher/dsa.c (dsa_check_keysize): Check reject flag for rejection, +or mark non-comliant in FIPS mode. +* cipher/ecc-ecdsa.c (_gcry_ecc_ecdsa_sign): Likewise. +* cipher/ecc.c (ecc_sign, ecc_verify): Likewise. +* cipher/pubkey.c (_gcry_pk_encrypt, _gcry_pk_sign): Likewise. +(_gcry_pk_verify, _gcry_pk_testkey, _gcry_pk_genkey): Likewise. +(_gcry_pk_get_nbits, _gcry_pk_get_curve): Likewise. +* src/visibility.c (gcry_pk_encrypt): Initialize the indicator. +(gcry_pk_decrypt, gcry_pk_sign, gcry_pk_verify): Likewise. +(gcry_pk_testkey, gcry_pk_genkey), gcry_pk_get_nbits) +(gcry_pk_get_curve): Likewise. +-- + +GnuPG-bug-id: 7338 +Signed-off-by: NIIBE Yutaka +Signed-off-by: Lucas Mülling +--- + cipher/dsa.c | 7 ++++- + cipher/ecc-ecdsa.c | 5 +++- + cipher/ecc.c | 10 +++++-- + cipher/pubkey.c | 74 ++++++++++++++++++++++++++++++++++++++-------- + src/visibility.c | 9 +++++- + 5 files changed, 87 insertions(+), 18 deletions(-) + +diff --git a/cipher/dsa.c b/cipher/dsa.c +index e559f9f5..564edf8d 100644 +--- a/cipher/dsa.c ++++ b/cipher/dsa.c +@@ -150,7 +150,12 @@ static gpg_err_code_t + dsa_check_keysize (unsigned int nbits) + { + if (fips_mode () && nbits < 2048) +- return GPG_ERR_INV_VALUE; ++ { ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) ++ return GPG_ERR_INV_VALUE; ++ else ++ fips_service_indicator_mark_non_compliant (); ++ } + + return 0; + } +diff --git a/cipher/ecc-ecdsa.c b/cipher/ecc-ecdsa.c +index 871b0371..cb9a001c 100644 +--- a/cipher/ecc-ecdsa.c ++++ b/cipher/ecc-ecdsa.c +@@ -110,7 +110,10 @@ _gcry_ecc_ecdsa_sign (gcry_mpi_t input, gcry_mpi_t k_supplied, mpi_ec_t ec, + (hashalgo == GCRY_MD_SHAKE128 + || hashalgo == GCRY_MD_SHAKE256)) + { +- rc = GPG_ERR_DIGEST_ALGO; ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) ++ rc = GPG_ERR_DIGEST_ALGO; ++ else ++ fips_service_indicator_mark_non_compliant (); + goto leave; + } + +diff --git a/cipher/ecc.c b/cipher/ecc.c +index 65525207..8896afd0 100644 +--- a/cipher/ecc.c ++++ b/cipher/ecc.c +@@ -952,7 +952,10 @@ ecc_sign (gcry_sexp_t *r_sig, gcry_sexp_t s_data, gcry_sexp_t keyparms) + || (ec->dialect == ECC_DIALECT_SAFECURVE + && ctx.hash_algo != GCRY_MD_SHAKE256))) + { +- rc = GPG_ERR_DIGEST_ALGO; ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) ++ rc = GPG_ERR_DIGEST_ALGO; ++ else ++ fips_service_indicator_mark_non_compliant (); + goto leave; + } + } +@@ -1074,7 +1077,10 @@ ecc_verify (gcry_sexp_t s_sig, gcry_sexp_t s_data, gcry_sexp_t s_keyparms) + || (ec->dialect == ECC_DIALECT_SAFECURVE + && ctx.hash_algo != GCRY_MD_SHAKE256))) + { +- rc = GPG_ERR_DIGEST_ALGO; ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) ++ rc = GPG_ERR_DIGEST_ALGO; ++ else ++ fips_service_indicator_mark_non_compliant (); + goto leave; + } + } +diff --git a/cipher/pubkey.c b/cipher/pubkey.c +index 4d7743cc..aacf9f5a 100644 +--- a/cipher/pubkey.c ++++ b/cipher/pubkey.c +@@ -328,7 +328,12 @@ _gcry_pk_encrypt (gcry_sexp_t *r_ciph, gcry_sexp_t s_data, gcry_sexp_t s_pkey) + if (spec->flags.disabled) + rc = GPG_ERR_PUBKEY_ALGO; + else if (!spec->flags.fips && fips_mode ()) +- rc = GPG_ERR_PUBKEY_ALGO; ++ { ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) ++ rc = GPG_ERR_PUBKEY_ALGO; ++ else ++ fips_service_indicator_mark_non_compliant (); ++ } + else if (spec->encrypt) + rc = spec->encrypt (r_ciph, s_data, keyparms); + else +@@ -441,7 +446,12 @@ _gcry_pk_sign (gcry_sexp_t *r_sig, gcry_sexp_t s_hash, gcry_sexp_t s_skey) + if (spec->flags.disabled) + rc = GPG_ERR_PUBKEY_ALGO; + else if (!spec->flags.fips && fips_mode ()) +- rc = GPG_ERR_PUBKEY_ALGO; ++ { ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) ++ rc = GPG_ERR_PUBKEY_ALGO; ++ else ++ fips_service_indicator_mark_non_compliant (); ++ } + else if (spec->sign) + rc = spec->sign (r_sig, s_hash, keyparms); + else +@@ -663,7 +673,12 @@ _gcry_pk_verify (gcry_sexp_t s_sig, gcry_sexp_t s_hash, gcry_sexp_t s_pkey) + if (spec->flags.disabled) + rc = GPG_ERR_PUBKEY_ALGO; + else if (!spec->flags.fips && fips_mode ()) +- rc = GPG_ERR_PUBKEY_ALGO; ++ { ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) ++ rc = GPG_ERR_PUBKEY_ALGO; ++ else ++ fips_service_indicator_mark_non_compliant (); ++ } + else if (spec->verify) + rc = spec->verify (s_sig, s_hash, keyparms); + else +@@ -747,7 +762,12 @@ _gcry_pk_testkey (gcry_sexp_t s_key) + if (spec->flags.disabled) + rc = GPG_ERR_PUBKEY_ALGO; + else if (!spec->flags.fips && fips_mode ()) +- rc = GPG_ERR_PUBKEY_ALGO; ++ { ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) ++ rc = GPG_ERR_PUBKEY_ALGO; ++ else ++ fips_service_indicator_mark_non_compliant (); ++ } + else if (spec->check_secret_key) + rc = spec->check_secret_key (keyparms); + else +@@ -826,11 +846,21 @@ _gcry_pk_genkey (gcry_sexp_t *r_key, gcry_sexp_t s_parms) + spec = spec_from_name (name); + xfree (name); + name = NULL; +- if (!spec || spec->flags.disabled || (!spec->flags.fips && fips_mode ())) ++ if (!spec || spec->flags.disabled) + { + rc = GPG_ERR_PUBKEY_ALGO; /* Unknown algorithm. */ + goto leave; + } ++ else if (!spec->flags.fips && fips_mode ()) ++ { ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) ++ { ++ rc = GPG_ERR_PUBKEY_ALGO; ++ goto leave; ++ } ++ else ++ fips_service_indicator_mark_non_compliant (); ++ } + + if (spec->generate) + rc = spec->generate (list, r_key); +@@ -866,12 +896,22 @@ _gcry_pk_get_nbits (gcry_sexp_t key) + + if (spec_from_sexp (key, 0, &spec, &parms)) + return 0; /* Error - 0 is a suitable indication for that. */ ++ + if (spec->flags.disabled) +- return 0; +- if (!spec->flags.fips && fips_mode ()) +- return 0; ++ nbits = 0; /* Error */ ++ else if (!spec->flags.fips && fips_mode ()) ++ { ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) ++ nbits = 0; /* Error */ ++ else ++ { ++ fips_service_indicator_mark_non_compliant (); ++ nbits = spec->get_nbits (parms); ++ } ++ } ++ else ++ nbits = spec->get_nbits (parms); + +- nbits = spec->get_nbits (parms); + sexp_release (parms); + return nbits; + } +@@ -1004,10 +1044,18 @@ _gcry_pk_get_curve (gcry_sexp_t key, int iterator, unsigned int *r_nbits) + } + + if (spec->flags.disabled) +- return NULL; +- if (!spec->flags.fips && fips_mode ()) +- return NULL; +- if (spec->get_curve) ++ result = NULL; ++ else if (!spec->flags.fips && fips_mode ()) ++ { ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) ++ result = NULL; ++ else ++ { ++ fips_service_indicator_mark_non_compliant (); ++ result = spec->get_curve (keyparms, iterator, r_nbits); ++ } ++ } ++ else if (spec->get_curve) + result = spec->get_curve (keyparms, iterator, r_nbits); + + sexp_release (keyparms); +diff --git a/src/visibility.c b/src/visibility.c +index d22c8b59..e02d6cfe 100644 +--- a/src/visibility.c ++++ b/src/visibility.c +@@ -1022,6 +1022,7 @@ gcry_pk_encrypt (gcry_sexp_t *result, gcry_sexp_t data, gcry_sexp_t pkey) + *result = NULL; + return gpg_error (fips_not_operational ()); + } ++ fips_service_indicator_init (); + return gpg_error (_gcry_pk_encrypt (result, data, pkey)); + } + +@@ -1033,6 +1034,7 @@ gcry_pk_decrypt (gcry_sexp_t *result, gcry_sexp_t data, gcry_sexp_t skey) + *result = NULL; + return gpg_error (fips_not_operational ()); + } ++ fips_service_indicator_init (); + return gpg_error (_gcry_pk_decrypt (result, data, skey)); + } + +@@ -1044,6 +1046,7 @@ gcry_pk_sign (gcry_sexp_t *result, gcry_sexp_t data, gcry_sexp_t skey) + *result = NULL; + return gpg_error (fips_not_operational ()); + } ++ fips_service_indicator_init (); + return gpg_error (_gcry_pk_sign (result, data, skey)); + } + +@@ -1065,6 +1068,7 @@ gcry_pk_verify (gcry_sexp_t sigval, gcry_sexp_t data, gcry_sexp_t pkey) + { + if (!fips_is_operational ()) + return gpg_error (fips_not_operational ()); ++ fips_service_indicator_init (); + return gpg_error (_gcry_pk_verify (sigval, data, pkey)); + } + +@@ -1089,6 +1093,7 @@ gcry_pk_testkey (gcry_sexp_t key) + { + if (!fips_is_operational ()) + return gpg_error (fips_not_operational ()); ++ fips_service_indicator_init (); + return gpg_error (_gcry_pk_testkey (key)); + } + +@@ -1100,6 +1105,7 @@ gcry_pk_genkey (gcry_sexp_t *r_key, gcry_sexp_t s_parms) + *r_key = NULL; + return gpg_error (fips_not_operational ()); + } ++ fips_service_indicator_init (); + return gpg_error (_gcry_pk_genkey (r_key, s_parms)); + } + +@@ -1138,7 +1144,7 @@ gcry_pk_get_nbits (gcry_sexp_t key) + (void)fips_not_operational (); + return 0; + } +- ++ fips_service_indicator_init (); + return _gcry_pk_get_nbits (key); + } + +@@ -1161,6 +1167,7 @@ gcry_pk_get_curve (gcry_sexp_t key, int iterator, unsigned int *r_nbits) + (void)fips_not_operational (); + return NULL; + } ++ fips_service_indicator_init (); + return _gcry_pk_get_curve (key, iterator, r_nbits); + } + +-- +2.49.0 + diff --git a/libgcrypt-fips-cipher-Do-the-computation-when-marking-non-compliant.patch b/libgcrypt-fips-cipher-Do-the-computation-when-marking-non-compliant.patch new file mode 100644 index 0000000..8f71866 --- /dev/null +++ b/libgcrypt-fips-cipher-Do-the-computation-when-marking-non-compliant.patch @@ -0,0 +1,160 @@ +From 54a6617b3679cfeb6d986ddf3c9c73641929f02c Mon Sep 17 00:00:00 2001 +From: NIIBE Yutaka +Date: Tue, 4 Mar 2025 10:32:49 +0900 +Subject: [PATCH 4/4] fips,cipher: Do the computation when marking + non-compliant. +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* cipher/ecc-ecdsa.c (_gcry_ecc_ecdsa_sign): Continue the computation +when marking non-compliant. +* cipher/pubkey.c (_gcry_pk_encrypt, _gcry_pk_sign): Likewise. +(_gcry_pk_sign_md, _gcry_pk_verify, _gcry_pk_verify_md): Likewise. +(_gcry_pk_testkey): Likewise. + +-- + +Fixes-commit: a776b692669af7a6c089779989b626c4795e30b0 +GnuPG-bug-id: 7338 +Signed-off-by: NIIBE Yutaka +Signed-off-by: Lucas Mülling +--- + cipher/ecc-ecdsa.c | 6 ++++-- + cipher/pubkey.c | 48 ++++++++++++++++++++++++++++++++++------------ + 2 files changed, 40 insertions(+), 14 deletions(-) + +diff --git a/cipher/ecc-ecdsa.c b/cipher/ecc-ecdsa.c +index cb9a001c..9da8e6dc 100644 +--- a/cipher/ecc-ecdsa.c ++++ b/cipher/ecc-ecdsa.c +@@ -111,10 +111,12 @@ _gcry_ecc_ecdsa_sign (gcry_mpi_t input, gcry_mpi_t k_supplied, mpi_ec_t ec, + || hashalgo == GCRY_MD_SHAKE256)) + { + if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) +- rc = GPG_ERR_DIGEST_ALGO; ++ { ++ rc = GPG_ERR_DIGEST_ALGO; ++ goto leave; ++ } + else + fips_service_indicator_mark_non_compliant (); +- goto leave; + } + + /* Use Pornin's method for deterministic DSA. If this +diff --git a/cipher/pubkey.c b/cipher/pubkey.c +index c28ec124..3778f482 100644 +--- a/cipher/pubkey.c ++++ b/cipher/pubkey.c +@@ -330,11 +330,15 @@ _gcry_pk_encrypt (gcry_sexp_t *r_ciph, gcry_sexp_t s_data, gcry_sexp_t s_pkey) + else if (!spec->flags.fips && fips_mode ()) + { + if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) +- rc = GPG_ERR_PUBKEY_ALGO; ++ { ++ rc = GPG_ERR_PUBKEY_ALGO; ++ goto leave; ++ } + else + fips_service_indicator_mark_non_compliant (); + } +- else if (spec->encrypt) ++ ++ if (spec->encrypt) + rc = spec->encrypt (r_ciph, s_data, keyparms); + else + rc = GPG_ERR_NOT_IMPLEMENTED; +@@ -448,11 +452,15 @@ _gcry_pk_sign (gcry_sexp_t *r_sig, gcry_sexp_t s_hash, gcry_sexp_t s_skey) + else if (!spec->flags.fips && fips_mode ()) + { + if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) +- rc = GPG_ERR_PUBKEY_ALGO; ++ { ++ rc = GPG_ERR_PUBKEY_ALGO; ++ goto leave; ++ } + else + fips_service_indicator_mark_non_compliant (); + } +- else if (spec->sign) ++ ++ if (spec->sign) + rc = spec->sign (r_sig, s_hash, keyparms); + else + rc = GPG_ERR_NOT_IMPLEMENTED; +@@ -649,11 +657,15 @@ _gcry_pk_sign_md (gcry_sexp_t *r_sig, const char *tmpl, gcry_md_hd_t hd_orig, + else if (!spec->flags.fips && fips_mode ()) + { + if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) +- rc = GPG_ERR_PUBKEY_ALGO; ++ { ++ rc = GPG_ERR_PUBKEY_ALGO; ++ goto leave; ++ } + else + fips_service_indicator_mark_non_compliant (); + } +- else if (spec->sign) ++ ++ if (spec->sign) + rc = spec->sign (r_sig, s_data, keyparms); + else + rc = GPG_ERR_NOT_IMPLEMENTED; +@@ -688,11 +700,15 @@ _gcry_pk_verify (gcry_sexp_t s_sig, gcry_sexp_t s_hash, gcry_sexp_t s_pkey) + else if (!spec->flags.fips && fips_mode ()) + { + if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) +- rc = GPG_ERR_PUBKEY_ALGO; ++ { ++ rc = GPG_ERR_PUBKEY_ALGO; ++ goto leave; ++ } + else + fips_service_indicator_mark_non_compliant (); + } +- else if (spec->verify) ++ ++ if (spec->verify) + rc = spec->verify (s_sig, s_hash, keyparms); + else + rc = GPG_ERR_NOT_IMPLEMENTED; +@@ -736,11 +752,15 @@ _gcry_pk_verify_md (gcry_sexp_t s_sig, const char *tmpl, gcry_md_hd_t hd_orig, + else if (!spec->flags.fips && fips_mode ()) + { + if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) +- rc = GPG_ERR_PUBKEY_ALGO; ++ { ++ rc = GPG_ERR_PUBKEY_ALGO; ++ goto leave; ++ } + else + fips_service_indicator_mark_non_compliant (); + } +- else if (spec->verify) ++ ++ if (spec->verify) + rc = spec->verify (s_sig, s_data, keyparms); + else + rc = GPG_ERR_NOT_IMPLEMENTED; +@@ -777,11 +797,15 @@ _gcry_pk_testkey (gcry_sexp_t s_key) + else if (!spec->flags.fips && fips_mode ()) + { + if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) +- rc = GPG_ERR_PUBKEY_ALGO; ++ { ++ rc = GPG_ERR_PUBKEY_ALGO; ++ goto leave; ++ } + else + fips_service_indicator_mark_non_compliant (); + } +- else if (spec->check_secret_key) ++ ++ if (spec->check_secret_key) + rc = spec->check_secret_key (keyparms); + else + rc = GPG_ERR_NOT_IMPLEMENTED; +-- +2.49.0 + diff --git a/libgcrypt-fips-cipher-Fix-memory-leak-for-gcry_pk_hash_sign.patch b/libgcrypt-fips-cipher-Fix-memory-leak-for-gcry_pk_hash_sign.patch new file mode 100644 index 0000000..445136e --- /dev/null +++ b/libgcrypt-fips-cipher-Fix-memory-leak-for-gcry_pk_hash_sign.patch @@ -0,0 +1,76 @@ +From 5e925e6c348450bf80b4560abac9a035903bff59 Mon Sep 17 00:00:00 2001 +From: NIIBE Yutaka +Date: Mon, 6 Jan 2025 12:01:56 +0900 +Subject: [PATCH 19/19] fips,cipher: Fix memory leak for gcry_pk_hash_sign. +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* cipher/pubkey.c (prepare_datasexp_to_be_signed): Release +copied HD when error. + +-- + +GnuPG-bug-id: 7338 +Signed-off-by: NIIBE Yutaka +Signed-off-by: Lucas Mülling +--- + cipher/pubkey.c | 21 +++++++++++++++++---- + 1 file changed, 17 insertions(+), 4 deletions(-) + +diff --git a/cipher/pubkey.c b/cipher/pubkey.c +index aacf9f5a..c28ec124 100644 +--- a/cipher/pubkey.c ++++ b/cipher/pubkey.c +@@ -512,7 +512,10 @@ prepare_datasexp_to_be_signed (const char *tmpl, gcry_md_hd_t hd, + /* Check if it has fixed hash name or %s */ + s = strstr (tmpl, "(hash "); + if (s == NULL) +- return GPG_ERR_DIGEST_ALGO; ++ { ++ _gcry_md_close (hd); ++ return GPG_ERR_DIGEST_ALGO; ++ } + + s += 6; + if (!strncmp (s, "%s", 2)) +@@ -522,7 +525,10 @@ prepare_datasexp_to_be_signed (const char *tmpl, gcry_md_hd_t hd, + if (fips_mode () && algo == GCRY_MD_SHA1) + { + if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) +- return GPG_ERR_DIGEST_ALGO; ++ { ++ _gcry_md_close (hd); ++ return GPG_ERR_DIGEST_ALGO; ++ } + else + fips_service_indicator_mark_non_compliant (); + } +@@ -541,7 +547,11 @@ prepare_datasexp_to_be_signed (const char *tmpl, gcry_md_hd_t hd, + + digest_name_supplied = xtrymalloc (p - s + 1); + if (!digest_name_supplied) +- return gpg_error_from_syserror (); ++ { ++ rc = gpg_err_code_from_syserror (); ++ _gcry_md_close (hd); ++ return rc; ++ } + memcpy (digest_name_supplied, s, p - s); + digest_name_supplied[p - s] = 0; + +@@ -555,7 +565,10 @@ prepare_datasexp_to_be_signed (const char *tmpl, gcry_md_hd_t hd, + else if (fips_mode () && algo == GCRY_MD_SHA1) + { + if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) +- return GPG_ERR_DIGEST_ALGO; ++ { ++ _gcry_md_close (hd); ++ return GPG_ERR_DIGEST_ALGO; ++ } + else + fips_service_indicator_mark_non_compliant (); + } +-- +2.49.0 + diff --git a/libgcrypt-fips-cipher-Implement-FIPS-service-indicator-for-gcry_pk_hash_-API.patch b/libgcrypt-fips-cipher-Implement-FIPS-service-indicator-for-gcry_pk_hash_-API.patch new file mode 100644 index 0000000..0490e38 --- /dev/null +++ b/libgcrypt-fips-cipher-Implement-FIPS-service-indicator-for-gcry_pk_hash_-API.patch @@ -0,0 +1,360 @@ +From edb43bc290046bd22548bf69ae2fbeb453112e44 Mon Sep 17 00:00:00 2001 +From: NIIBE Yutaka +Date: Wed, 18 Dec 2024 14:18:26 +0900 +Subject: [PATCH 11/19] fips,cipher: Implement FIPS service indicator for + gcry_pk_hash_ API. +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* src/visibility.c (gcry_pk_hash_sign): Initialize the indicator. +(gcry_pk_hash_verify): Likewise. +* tests/t-fips-service-ind.c (check_pk_hash_sign_verify): New. +(main): Call check_pk_hash_sign_verify. +* cipher/ecc-curves.c (_gcry_ecc_fill_in_curve): Don't reject, but +mark non-compliance. +* cipher/pubkey.c (prepare_datasexp_to_be_signed): Likewise. +(_gcry_pk_sign_md, _gcry_pk_verify_md): Likewise. + +-- + +GnuPG-bug-id: 7338 +Signed-off-by: NIIBE Yutaka +Signed-off-by: Lucas Mülling +--- + cipher/ecc-curves.c | 2 +- + cipher/pubkey.c | 20 ++-- + src/visibility.c | 2 + + tests/t-fips-service-ind.c | 209 +++++++++++++++++++++++++++++++++++++ + 4 files changed, 222 insertions(+), 11 deletions(-) + +diff --git a/cipher/ecc-curves.c b/cipher/ecc-curves.c +index 17fa5505..ddf9cbe1 100644 +--- a/cipher/ecc-curves.c ++++ b/cipher/ecc-curves.c +@@ -645,7 +645,7 @@ _gcry_ecc_fill_in_curve (unsigned int nbits, const char *name, + possible to bypass this check by specifying the curve parameters + directly. */ + if (fips_mode () && !domain_parms[idx].fips ) +- return GPG_ERR_NOT_SUPPORTED; ++ fips_service_indicator_mark_non_compliant (); + + switch (domain_parms[idx].model) + { +diff --git a/cipher/pubkey.c b/cipher/pubkey.c +index 214bd611..e2e54199 100644 +--- a/cipher/pubkey.c ++++ b/cipher/pubkey.c +@@ -510,10 +510,7 @@ prepare_datasexp_to_be_signed (const char *tmpl, gcry_md_hd_t hd, + algo = _gcry_md_get_algo (hd); + + if (fips_mode () && algo == GCRY_MD_SHA1) +- { +- _gcry_md_close (hd); +- return GPG_ERR_DIGEST_ALGO; +- } ++ fips_service_indicator_mark_non_compliant (); + + digest_name = _gcry_md_algo_name (algo); + digest_size = (int)_gcry_md_get_algo_dlen (algo); +@@ -535,12 +532,13 @@ prepare_datasexp_to_be_signed (const char *tmpl, gcry_md_hd_t hd, + + algo = _gcry_md_map_name (digest_name_supplied); + xfree (digest_name_supplied); +- if (algo == 0 +- || (fips_mode () && algo == GCRY_MD_SHA1)) ++ if (algo == 0) + { + _gcry_md_close (hd); + return GPG_ERR_DIGEST_ALGO; + } ++ else if (fips_mode () && algo == GCRY_MD_SHA1) ++ fips_service_indicator_mark_non_compliant (); + + digest_size = (int)_gcry_md_get_algo_dlen (algo); + digest = _gcry_md_read (hd, algo); +@@ -613,10 +611,11 @@ _gcry_pk_sign_md (gcry_sexp_t *r_sig, const char *tmpl, gcry_md_hd_t hd_orig, + if (rc) + goto leave; + ++ if (!spec->flags.fips && fips_mode ()) ++ fips_service_indicator_mark_non_compliant (); ++ + if (spec->flags.disabled) + rc = GPG_ERR_PUBKEY_ALGO; +- else if (!spec->flags.fips && fips_mode ()) +- rc = GPG_ERR_PUBKEY_ALGO; + else if (spec->sign) + rc = spec->sign (r_sig, s_data, keyparms); + else +@@ -690,10 +689,11 @@ _gcry_pk_verify_md (gcry_sexp_t s_sig, const char *tmpl, gcry_md_hd_t hd_orig, + if (rc) + goto leave; + ++ if (!spec->flags.fips && fips_mode ()) ++ fips_service_indicator_mark_non_compliant (); ++ + if (spec->flags.disabled) + rc = GPG_ERR_PUBKEY_ALGO; +- else if (!spec->flags.fips && fips_mode ()) +- rc = GPG_ERR_PUBKEY_ALGO; + else if (spec->verify) + rc = spec->verify (s_sig, s_data, keyparms); + else +diff --git a/src/visibility.c b/src/visibility.c +index c9d07f0b..d22c8b59 100644 +--- a/src/visibility.c ++++ b/src/visibility.c +@@ -1056,6 +1056,7 @@ gcry_pk_hash_sign (gcry_sexp_t *result, const char *data_tmpl, gcry_sexp_t skey, + *result = NULL; + return gpg_error (fips_not_operational ()); + } ++ fips_service_indicator_init (); + return gpg_error (_gcry_pk_sign_md (result, data_tmpl, hd, skey, ctx)); + } + +@@ -1073,6 +1074,7 @@ gcry_pk_hash_verify (gcry_sexp_t sigval, const char *data_tmpl, gcry_sexp_t pkey + { + if (!fips_is_operational ()) + return gpg_error (fips_not_operational ()); ++ fips_service_indicator_init (); + return gpg_error (_gcry_pk_verify_md (sigval, data_tmpl, hd, pkey, ctx)); + } + +diff --git a/tests/t-fips-service-ind.c b/tests/t-fips-service-ind.c +index 4b13436f..9a22d696 100644 +--- a/tests/t-fips-service-ind.c ++++ b/tests/t-fips-service-ind.c +@@ -29,6 +29,7 @@ + + #define PGM "t-fips-service-ind" + ++#define NEED_HEX2BUFFER + #include "t-common.h" + static int in_fips_mode; + #define MAX_DATA_LEN 1040 +@@ -39,6 +40,213 @@ static int in_fips_mode; + # include + #endif + ++/* Check gcry_pk_hash_sign, gcry_pk_hash_verify API. */ ++static void ++check_pk_hash_sign_verify (void) ++{ ++ static struct { ++ int md_algo; ++ const char *prvkey; ++ const char *pubkey; ++ const char *data_tmpl; ++ const char *k; ++ int expect_failure; ++ int expect_failure_hash; ++ } tv[] = { ++ { /* non-compliant hash */ ++ GCRY_MD_BLAKE2B_512, ++ "(private-key (ecc (curve nistp256)" ++ " (d #519b423d715f8b581f4fa8ee59f4771a5b44c8130b4e3eacca54a56dda72b464#)))", ++ "(public-key (ecc (curve nistp256)" ++ " (q #041ccbe91c075fc7f4f033bfa248db8fccd3565de94bbfb12f3c59ff46c271bf83" ++ "ce4014c68811f9a21a1fdb2c0e6113e06db7ca93b7404e78dc7ccd5ca89a4ca9#)))", ++ "(data(flags raw)(hash %s %b)(label %b))", ++ "94a1bbb14b906a61a280f245f9e93c7f3b4a6247824f5d33b9670787642a68de", ++ 1, 1 ++ }, ++ { /* non-compliant curve */ ++ GCRY_MD_SHA256, ++ "(private-key (ecc (curve secp256k1)" ++ " (d #c2cdf0a8b0a83b35ace53f097b5e6e6a0a1f2d40535eff1cf434f52a43d59d8f#)))", ++ ++ "(public-key (ecc (curve secp256k1)" ++ " (q #046fcc37ea5e9e09fec6c83e5fbd7a745e3eee81d16ebd861c9e66f55518c19798" ++ "4e9f113c07f875691df8afc1029496fc4cb9509b39dcd38f251a83359cc8b4f7#)))", ++ "(data(flags raw)(hash %s %b)(label %b))", ++ "94a1bbb14b906a61a280f245f9e93c7f3b4a6247824f5d33b9670787642a68de", ++ 1, 0 ++ }, ++ { ++ GCRY_MD_SHA256, ++ "(private-key (ecc (curve nistp256)" ++ " (d #519b423d715f8b581f4fa8ee59f4771a5b44c8130b4e3eacca54a56dda72b464#)))", ++ "(public-key (ecc (curve nistp256)" ++ " (q #041ccbe91c075fc7f4f033bfa248db8fccd3565de94bbfb12f3c59ff46c271bf83" ++ "ce4014c68811f9a21a1fdb2c0e6113e06db7ca93b7404e78dc7ccd5ca89a4ca9#)))", ++ "(data(flags raw)(hash %s %b)(label %b))", ++ "94a1bbb14b906a61a280f245f9e93c7f3b4a6247824f5d33b9670787642a68de", ++ 0, 0 ++ } ++ }; ++ int tvidx; ++ gpg_error_t err; ++ gpg_err_code_t ec; ++ const char *msg = "Takerufuji Mikiya, who won the championship in March 2024"; ++ int msglen; ++ ++ msglen = strlen (msg); ++ for (tvidx=0; tvidx < DIM(tv); tvidx++) ++ { ++ gcry_md_hd_t hd = NULL; ++ gcry_sexp_t s_sk = NULL; ++ gcry_sexp_t s_pk = NULL; ++ void *buffer = NULL; ++ size_t buflen; ++ gcry_ctx_t ctx = NULL; ++ gcry_sexp_t s_sig= NULL; ++ ++ if (verbose) ++ info ("checking gcry_pk_hash_ test %d\n", tvidx); ++ ++ err = gcry_md_open (&hd, tv[tvidx].md_algo, 0); ++ if (err) ++ { ++ fail ("algo %d, gcry_md_open failed: %s\n", tv[tvidx].md_algo, ++ gpg_strerror (err)); ++ goto next; ++ } ++ ++ ec = gcry_get_fips_service_indicator (); ++ if (ec == GPG_ERR_INV_OP) ++ { ++ /* libgcrypt is old, no support of the FIPS service indicator. */ ++ fail ("gcry_pk_hash test %d unexpectedly failed to check the FIPS service indicator.\n", ++ tvidx); ++ goto next; ++ } ++ ++ if (in_fips_mode && !tv[tvidx].expect_failure_hash && ec) ++ { ++ /* Success with the FIPS service indicator == 0 expected, but != 0. */ ++ fail ("gcry_pk_hash test %d unexpectedly set the indicator in FIPS mode.\n", ++ tvidx); ++ goto next; ++ } ++ else if (in_fips_mode && tv[tvidx].expect_failure_hash && !ec) ++ { ++ /* Success with the FIPS service indicator != 0 expected, but == 0. */ ++ fail ("gcry_pk_hash test %d unexpectedly cleared the indicator in FIPS mode.\n", ++ tvidx); ++ goto next; ++ } ++ ++ err = gcry_sexp_build (&s_sk, NULL, tv[tvidx].prvkey); ++ if (err) ++ { ++ fail ("error building SEXP for test, %s: %s", ++ "sk", gpg_strerror (err)); ++ goto next; ++ } ++ ++ err = gcry_sexp_build (&s_pk, NULL, tv[tvidx].pubkey); ++ if (err) ++ { ++ fail ("error building SEXP for test, %s: %s", ++ "pk", gpg_strerror (err)); ++ goto next; ++ } ++ ++ if (!(buffer = hex2buffer (tv[tvidx].k, &buflen))) ++ { ++ fail ("error parsing for test, %s: %s", ++ "msg", "invalid hex string"); ++ goto next; ++ } ++ ++ err = gcry_pk_random_override_new (&ctx, buffer, buflen); ++ if (err) ++ { ++ fail ("error setting 'k' for test: %s", ++ gpg_strerror (err)); ++ goto next; ++ } ++ ++ gcry_md_write (hd, msg, msglen); ++ ++ err = gcry_pk_hash_sign (&s_sig, tv[tvidx].data_tmpl, s_sk, hd, ctx); ++ if (err) ++ { ++ fail ("gcry_pk_hash_sign failed: %s", gpg_strerror (err)); ++ goto next; ++ } ++ ++ ec = gcry_get_fips_service_indicator (); ++ if (ec == GPG_ERR_INV_OP) ++ { ++ /* libgcrypt is old, no support of the FIPS service indicator. */ ++ fail ("gcry_pk_hash test %d unexpectedly failed to check the FIPS service indicator.\n", ++ tvidx); ++ goto next; ++ } ++ ++ if (in_fips_mode && !tv[tvidx].expect_failure && ec) ++ { ++ /* Success with the FIPS service indicator == 0 expected, but != 0. */ ++ fail ("gcry_pk_hash test %d unexpectedly set the indicator in FIPS mode.\n", ++ tvidx); ++ goto next; ++ } ++ else if (in_fips_mode && tv[tvidx].expect_failure && !ec) ++ { ++ /* Success with the FIPS service indicator != 0 expected, but == 0. */ ++ fail ("gcry_pk_hash_sign test %d unexpectedly cleared the indicator in FIPS mode.\n", ++ tvidx); ++ goto next; ++ } ++ ++ err = gcry_pk_hash_verify (s_sig, tv[tvidx].data_tmpl, s_pk, hd, ctx); ++ if (err) ++ { ++ fail ("gcry_pk_hash_verify failed for test: %s", ++ gpg_strerror (err)); ++ goto next; ++ } ++ ++ ec = gcry_get_fips_service_indicator (); ++ if (ec == GPG_ERR_INV_OP) ++ { ++ /* libgcrypt is old, no support of the FIPS service indicator. */ ++ fail ("gcry_pk_hash test %d unexpectedly failed to check the FIPS service indicator.\n", ++ tvidx); ++ goto next; ++ } ++ ++ if (in_fips_mode && !tv[tvidx].expect_failure && ec) ++ { ++ /* Success with the FIPS service indicator == 0 expected, but != 0. */ ++ fail ("gcry_pk_hash test %d unexpectedly set the indicator in FIPS mode.\n", ++ tvidx); ++ goto next; ++ } ++ else if (in_fips_mode && tv[tvidx].expect_failure && !ec) ++ { ++ /* Success with the FIPS service indicator != 0 expected, but == 0. */ ++ fail ("gcry_pk_hash_verify test %d unexpectedly cleared the indicator in FIPS mode.\n", ++ tvidx); ++ goto next; ++ } ++ ++ next: ++ gcry_sexp_release (s_sig); ++ xfree (buffer); ++ gcry_ctx_release (ctx); ++ gcry_sexp_release (s_pk); ++ gcry_sexp_release (s_sk); ++ if (hd) ++ gcry_md_close (hd); ++ } ++} ++ + /* Check gcry_cipher_open, gcry_cipher_setkey, gcry_cipher_encrypt, + gcry_cipher_decrypt, gcry_cipher_close API. */ + static void +@@ -936,6 +1144,7 @@ main (int argc, char **argv) + check_md_o_w_r_c (); + check_mac_o_w_r_c (); + check_cipher_o_s_e_d_c (); ++ check_pk_hash_sign_verify (); + + return !!error_count; + } +-- +2.49.0 + diff --git a/libgcrypt-fips-cipher-Implement-new-FIPS-service-indicator-for-cipher_open.patch b/libgcrypt-fips-cipher-Implement-new-FIPS-service-indicator-for-cipher_open.patch new file mode 100644 index 0000000..2124c48 --- /dev/null +++ b/libgcrypt-fips-cipher-Implement-new-FIPS-service-indicator-for-cipher_open.patch @@ -0,0 +1,122 @@ +From 69a5d0ed18a3ddc6f297de783c7cef5ad2257df0 Mon Sep 17 00:00:00 2001 +From: NIIBE Yutaka +Date: Fri, 13 Dec 2024 14:40:53 +0900 +Subject: [PATCH 05/19] fips,cipher: Implement new FIPS service indicator for + cipher_open. +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* src/gcrypt.h.in (GCRY_CIPHER_FLAG_REJECT_NON_FIPS): New. +* cipher/cipher.c (_gcry_cipher_open_internal): Don't reject +but mark the service indicator in FIPS mode. +(cipher_setkey): Likewise. +* src/visibility.c (gcry_cipher_open): Initialize the service +indicator. +(gcry_cipher_setkey): Likewise. + +-- + +GnuPG-bug-id: 7338 +Signed-off-by: NIIBE Yutaka +Signed-off-by: Lucas Mülling +--- + cipher/cipher.c | 23 +++++++++++++++++++---- + src/gcrypt.h.in | 3 ++- + src/visibility.c | 4 ++-- + 3 files changed, 23 insertions(+), 7 deletions(-) + +diff --git a/cipher/cipher.c b/cipher/cipher.c +index 898bb58f..7ffacf05 100644 +--- a/cipher/cipher.c ++++ b/cipher/cipher.c +@@ -509,7 +509,8 @@ gcry_err_code_t + _gcry_cipher_open_internal (gcry_cipher_hd_t *handle, + int algo, int mode, unsigned int flags) + { +- int secure = (flags & GCRY_CIPHER_SECURE); ++ int secure = !!(flags & GCRY_CIPHER_SECURE); ++ int reject_non_fips = !!(flags & GCRY_CIPHER_FLAG_REJECT_NON_FIPS); + gcry_cipher_spec_t *spec; + gcry_cipher_hd_t h = NULL; + gcry_err_code_t err; +@@ -524,7 +525,15 @@ _gcry_cipher_open_internal (gcry_cipher_hd_t *handle, + else if (spec->flags.disabled) + err = GPG_ERR_CIPHER_ALGO; + else if (!spec->flags.fips && fips_mode ()) +- err = GPG_ERR_CIPHER_ALGO; ++ { ++ if (reject_non_fips) ++ err = GPG_ERR_CIPHER_ALGO; ++ else ++ { ++ fips_service_indicator_mark_non_compliant (); ++ err = 0; ++ } ++ } + else + err = 0; + +@@ -535,7 +544,8 @@ _gcry_cipher_open_internal (gcry_cipher_hd_t *handle, + | GCRY_CIPHER_ENABLE_SYNC + | GCRY_CIPHER_CBC_CTS + | GCRY_CIPHER_CBC_MAC +- | GCRY_CIPHER_EXTENDED)) ++ | GCRY_CIPHER_EXTENDED ++ | GCRY_CIPHER_FLAG_REJECT_NON_FIPS)) + || ((flags & GCRY_CIPHER_CBC_CTS) && (flags & GCRY_CIPHER_CBC_MAC)))) + err = GPG_ERR_CIPHER_ALGO; + +@@ -765,7 +775,12 @@ cipher_setkey (gcry_cipher_hd_t c, byte *key, size_t keylen) + See "Implementation Guidance for FIPS 140-2, A.9 XTS-AES + Key Generation Requirements" for details. */ + if (buf_eq_const (key, key + keylen, keylen)) +- return GPG_ERR_WEAK_KEY; ++ { ++ if ((c->flags & GCRY_CIPHER_FLAG_REJECT_NON_FIPS)) ++ return GPG_ERR_WEAK_KEY; ++ else ++ fips_service_indicator_mark_non_compliant (); ++ } + } + } + else if (c->mode == GCRY_CIPHER_MODE_SIV) +diff --git a/src/gcrypt.h.in b/src/gcrypt.h.in +index 2a378639..2ed9914b 100644 +--- a/src/gcrypt.h.in ++++ b/src/gcrypt.h.in +@@ -992,7 +992,8 @@ enum gcry_cipher_flags + GCRY_CIPHER_ENABLE_SYNC = 2, /* Enable CFB sync mode. */ + GCRY_CIPHER_CBC_CTS = 4, /* Enable CBC cipher text stealing (CTS). */ + GCRY_CIPHER_CBC_MAC = 8, /* Enable CBC message auth. code (MAC). */ +- GCRY_CIPHER_EXTENDED = 16 /* Enable extended AES-WRAP. */ ++ GCRY_CIPHER_EXTENDED = 16, /* Enable extended AES-WRAP. */ ++ GCRY_CIPHER_FLAG_REJECT_NON_FIPS = 32 /* Reject non-FIPS-compliant algo. */ + }; + + /* Methods used for AEAD IV generation. */ +diff --git a/src/visibility.c b/src/visibility.c +index 7699f14f..d219f1a6 100644 +--- a/src/visibility.c ++++ b/src/visibility.c +@@ -736,7 +736,7 @@ gcry_cipher_open (gcry_cipher_hd_t *handle, + *handle = NULL; + return gpg_error (fips_not_operational ()); + } +- ++ fips_service_indicator_init (); + return gpg_error (_gcry_cipher_open (handle, algo, mode, flags)); + } + +@@ -751,7 +751,7 @@ gcry_cipher_setkey (gcry_cipher_hd_t hd, const void *key, size_t keylen) + { + if (!fips_is_operational ()) + return gpg_error (fips_not_operational ()); +- ++ fips_service_indicator_init (); + return gcry_error (_gcry_cipher_setkey (hd, key, keylen)); + } + +-- +2.49.0 + diff --git a/libgcrypt-fips-ecc-Add-rejecting-or-marking-for-gcry_pk_get_curve.patch b/libgcrypt-fips-ecc-Add-rejecting-or-marking-for-gcry_pk_get_curve.patch new file mode 100644 index 0000000..27fd75b --- /dev/null +++ b/libgcrypt-fips-ecc-Add-rejecting-or-marking-for-gcry_pk_get_curve.patch @@ -0,0 +1,43 @@ +From c6a092abbe7bea315394b15f28fd231dae0e4d7c Mon Sep 17 00:00:00 2001 +From: NIIBE Yutaka +Date: Tue, 24 Dec 2024 17:01:45 +0900 +Subject: [PATCH 16/19] fips,ecc: Add rejecting or marking for + gcry_pk_get_curve. +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* cipher/ecc-curves.c (_gcry_ecc_get_curve): Check under FIPS mode. + +-- + +GnuPG-bug-id: 7338 +Signed-off-by: NIIBE Yutaka +Signed-off-by: Lucas Mülling +--- + cipher/ecc-curves.c | 9 +++++++++ + 1 file changed, 9 insertions(+) + +diff --git a/cipher/ecc-curves.c b/cipher/ecc-curves.c +index fe0a1eb2..975f6a07 100644 +--- a/cipher/ecc-curves.c ++++ b/cipher/ecc-curves.c +@@ -844,6 +844,15 @@ _gcry_ecc_get_curve (gcry_sexp_t keyparms, int iterator, unsigned int *r_nbits) + if (r_nbits) + *r_nbits = domain_parms[idx].nbits; + } ++ ++ if (fips_mode () && !domain_parms[idx].fips) ++ { ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) ++ return NULL; ++ else ++ fips_service_indicator_mark_non_compliant (); ++ } ++ + return result; + } + +-- +2.49.0 + diff --git a/libgcrypt-fips-ecc-Check-DATA-in-gcry_pk_sign-verify-in-FIPS-mode.patch b/libgcrypt-fips-ecc-Check-DATA-in-gcry_pk_sign-verify-in-FIPS-mode.patch new file mode 100644 index 0000000..310c5c9 --- /dev/null +++ b/libgcrypt-fips-ecc-Check-DATA-in-gcry_pk_sign-verify-in-FIPS-mode.patch @@ -0,0 +1,282 @@ +From 53c97483b17fee280e24f595bc0d82d9b362ffde Mon Sep 17 00:00:00 2001 +From: NIIBE Yutaka +Date: Thu, 26 Dec 2024 11:12:48 +0900 +Subject: [PATCH 18/19] fips,ecc: Check DATA in gcry_pk_sign/verify in FIPS + mode. +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* src/gcrypt.h.in (GCRY_FIPS_FLAG_REJECT_PK_MD): New. +(GCRY_FIPS_FLAG_REJECT_PK_GOST_SM2): New. + +* cipher/ecc.c (ecc_sign): Check if GOST or SM2. Check if hash is +compliant. +(ecc_verify): Likewise. +* tests/t-fips-service-ind.c (check_pk_s_v): Modify tests including +hash compliance. + +-- + +GnuPG-bug-id: 7338 +Signed-off-by: NIIBE Yutaka +Signed-off-by: Lucas Mülling +--- + cipher/ecc.c | 70 +++++++++++++++++++++++++++++++++++--- + src/gcrypt.h.in | 4 ++- + tests/t-fips-service-ind.c | 52 ++++++++++++++++++++-------- + 3 files changed, 107 insertions(+), 19 deletions(-) + +diff --git a/cipher/ecc.c b/cipher/ecc.c +index 8896afd0..525523ed 100644 +--- a/cipher/ecc.c ++++ b/cipher/ecc.c +@@ -941,6 +941,18 @@ ecc_sign (gcry_sexp_t *r_sig, gcry_sexp_t s_data, gcry_sexp_t keyparms) + if (rc) + goto leave; + ++ if (fips_mode () ++ && ((ctx.flags & PUBKEY_FLAG_GOST) || (ctx.flags & PUBKEY_FLAG_SM2))) ++ { ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK_GOST_SM2)) ++ { ++ rc = GPG_ERR_INV_DATA; ++ goto leave; ++ } ++ else ++ fips_service_indicator_mark_non_compliant (); ++ } ++ + /* Hash algo is determined by curve in EdDSA. */ + if ((ctx.flags & PUBKEY_FLAG_EDDSA)) + { +@@ -953,10 +965,12 @@ ecc_sign (gcry_sexp_t *r_sig, gcry_sexp_t s_data, gcry_sexp_t keyparms) + && ctx.hash_algo != GCRY_MD_SHAKE256))) + { + if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) +- rc = GPG_ERR_DIGEST_ALGO; ++ { ++ rc = GPG_ERR_DIGEST_ALGO; ++ goto leave; ++ } + else + fips_service_indicator_mark_non_compliant (); +- goto leave; + } + } + else +@@ -967,6 +981,23 @@ ecc_sign (gcry_sexp_t *r_sig, gcry_sexp_t s_data, gcry_sexp_t keyparms) + ctx.hash_algo = GCRY_MD_SHAKE256; + } + } ++ else ++ { ++ if (fips_mode ()) ++ { ++ if (_gcry_md_algo_info (ctx.hash_algo, GCRYCTL_TEST_ALGO, NULL, NULL) ++ || ctx.hash_algo == GCRY_MD_SHA1) ++ { ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK_MD)) ++ { ++ rc = GPG_ERR_DIGEST_ALGO; ++ goto leave; ++ } ++ else ++ fips_service_indicator_mark_non_compliant (); ++ } ++ } ++ } + + sig_r = mpi_new (0); + sig_s = mpi_new (0); +@@ -1066,6 +1097,18 @@ ecc_verify (gcry_sexp_t s_sig, gcry_sexp_t s_data, gcry_sexp_t s_keyparms) + if (DBG_CIPHER) + log_mpidump ("ecc_verify data", data); + ++ if (fips_mode () ++ && ((ctx.flags & PUBKEY_FLAG_GOST) || (ctx.flags & PUBKEY_FLAG_SM2))) ++ { ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK_GOST_SM2)) ++ { ++ rc = GPG_ERR_INV_DATA; ++ goto leave; ++ } ++ else ++ fips_service_indicator_mark_non_compliant (); ++ } ++ + /* Hash algo is determined by curve in EdDSA. */ + if ((ctx.flags & PUBKEY_FLAG_EDDSA)) + { +@@ -1078,10 +1121,12 @@ ecc_verify (gcry_sexp_t s_sig, gcry_sexp_t s_data, gcry_sexp_t s_keyparms) + && ctx.hash_algo != GCRY_MD_SHAKE256))) + { + if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) +- rc = GPG_ERR_DIGEST_ALGO; ++ { ++ rc = GPG_ERR_DIGEST_ALGO; ++ goto leave; ++ } + else + fips_service_indicator_mark_non_compliant (); +- goto leave; + } + } + else +@@ -1092,6 +1137,23 @@ ecc_verify (gcry_sexp_t s_sig, gcry_sexp_t s_data, gcry_sexp_t s_keyparms) + ctx.hash_algo = GCRY_MD_SHAKE256; + } + } ++ else ++ { ++ if (fips_mode ()) ++ { ++ if (_gcry_md_algo_info (ctx.hash_algo, GCRYCTL_TEST_ALGO, NULL, NULL) ++ || ctx.hash_algo == GCRY_MD_SHA1) ++ { ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK_MD)) ++ { ++ rc = GPG_ERR_DIGEST_ALGO; ++ goto leave; ++ } ++ else ++ fips_service_indicator_mark_non_compliant (); ++ } ++ } ++ } + + /* + * Extract the signature value. +diff --git a/src/gcrypt.h.in b/src/gcrypt.h.in +index 7bee45e9..fcb6a327 100644 +--- a/src/gcrypt.h.in ++++ b/src/gcrypt.h.in +@@ -1986,11 +1986,13 @@ char *gcry_get_config (int mode, const char *what); + #define GCRY_FIPS_FLAG_REJECT_MAC (1 << 3) + #define GCRY_FIPS_FLAG_REJECT_CIPHER (1 << 4) + #define GCRY_FIPS_FLAG_REJECT_PK (1 << 5) ++#define GCRY_FIPS_FLAG_REJECT_PK_MD (1 << 6) ++#define GCRY_FIPS_FLAG_REJECT_PK_GOST_SM2 (1 << 7) + + #define GCRY_FIPS_FLAG_REJECT_MD \ + (GCRY_FIPS_FLAG_REJECT_MD_MD5 | GCRY_FIPS_FLAG_REJECT_MD_OTHERS) + +-/* Note: Don't reject MD5 */ ++/* Note: Don't reject MD5, PK MD, PK GOST and PK SM2 */ + #define GCRY_FIPS_FLAG_REJECT_COMPAT110 \ + (GCRY_FIPS_FLAG_REJECT_MD_OTHERS \ + | GCRY_FIPS_FLAG_REJECT_MAC \ +diff --git a/tests/t-fips-service-ind.c b/tests/t-fips-service-ind.c +index 90d92c70..fe963fa5 100644 +--- a/tests/t-fips-service-ind.c ++++ b/tests/t-fips-service-ind.c +@@ -228,6 +228,7 @@ check_pk_s_v (int reject) + static struct { + const char *prvkey; + const char *pubkey; ++ const char *data; + int expect_failure; + } tv[] = { + { +@@ -236,6 +237,8 @@ check_pk_s_v (int reject) + "(public-key (ecc (curve nistp256)" + " (q #041ccbe91c075fc7f4f033bfa248db8fccd3565de94bbfb12f3c59ff46c271bf83" + "ce4014c68811f9a21a1fdb2c0e6113e06db7ca93b7404e78dc7ccd5ca89a4ca9#)))", ++ "(data (flags raw)(hash sha256 " ++ "#00112233445566778899AABBCCDDEEFF000102030405060708090A0B0C0D0E0F#))", + 0 + }, + { /* non-compliant curve */ +@@ -244,28 +247,40 @@ check_pk_s_v (int reject) + "(public-key (ecc (curve secp256k1)" + " (q #046fcc37ea5e9e09fec6c83e5fbd7a745e3eee81d16ebd861c9e66f55518c19798" + "4e9f113c07f875691df8afc1029496fc4cb9509b39dcd38f251a83359cc8b4f7#)))", ++ "(data (flags raw)(hash sha256 " ++ "#00112233445566778899AABBCCDDEEFF000102030405060708090A0B0C0D0E0F#))", + 1 +- } ++ }, ++ { /* non-compliant hash */ ++ "(private-key (ecc (curve nistp256)" ++ " (d #519b423d715f8b581f4fa8ee59f4771a5b44c8130b4e3eacca54a56dda72b464#)))", ++ "(public-key (ecc (curve nistp256)" ++ " (q #041ccbe91c075fc7f4f033bfa248db8fccd3565de94bbfb12f3c59ff46c271bf83" ++ "ce4014c68811f9a21a1fdb2c0e6113e06db7ca93b7404e78dc7ccd5ca89a4ca9#)))", ++ "(data (flags raw)(hash ripemd160 " ++ "#00112233445566778899AABBCCDDEEFF00010203#))", ++ 1 ++ }, ++ { /* non-compliant hash for signing */ ++ "(private-key (ecc (curve nistp256)" ++ " (d #519b423d715f8b581f4fa8ee59f4771a5b44c8130b4e3eacca54a56dda72b464#)))", ++ "(public-key (ecc (curve nistp256)" ++ " (q #041ccbe91c075fc7f4f033bfa248db8fccd3565de94bbfb12f3c59ff46c271bf83" ++ "ce4014c68811f9a21a1fdb2c0e6113e06db7ca93b7404e78dc7ccd5ca89a4ca9#)))", ++ "(data (flags raw)(hash sha1 " ++ "#00112233445566778899AABBCCDDEEFF00010203#))", ++ 1 ++ }, + }; + int tvidx; + gpg_error_t err; + gpg_err_code_t ec; +- const char *data = "(data (flags raw)" +- "(hash sha256 #00112233445566778899AABBCCDDEEFF000102030405060708090A0B0C0D0E0F#))"; +- gcry_sexp_t s_data = NULL; +- +- err = gcry_sexp_build (&s_data, NULL, data); +- if (err) +- { +- fail ("error building SEXP for test, %s: %s", +- "data", gpg_strerror (err)); +- return; +- } + + for (tvidx=0; tvidx < DIM(tv); tvidx++) + { + gcry_sexp_t s_pk = NULL; + gcry_sexp_t s_sk = NULL; ++ gcry_sexp_t s_data = NULL; + gcry_sexp_t s_sig= NULL; + + if (verbose) +@@ -287,6 +302,14 @@ check_pk_s_v (int reject) + goto next; + } + ++ err = gcry_sexp_build (&s_data, NULL, tv[tvidx].data); ++ if (err) ++ { ++ fail ("error building SEXP for test, %s: %s", ++ "data", gpg_strerror (err)); ++ goto next; ++ } ++ + err = gcry_pk_sign (&s_sig, s_data, s_sk); + if (err) + { +@@ -363,11 +386,10 @@ check_pk_s_v (int reject) + + next: + gcry_sexp_release (s_sig); ++ gcry_sexp_release (s_data); + gcry_sexp_release (s_pk); + gcry_sexp_release (s_sk); + } +- +- gcry_sexp_release (s_data); + } + + /* Check gcry_pk_hash_sign, gcry_pk_hash_verify API. */ +@@ -1461,6 +1483,8 @@ main (int argc, char **argv) + + xgcry_control ((GCRYCTL_FIPS_REJECT_NON_FIPS, + (GCRY_FIPS_FLAG_REJECT_MD_MD5 ++ | GCRY_FIPS_FLAG_REJECT_PK_MD ++ | GCRY_FIPS_FLAG_REJECT_PK_GOST_SM2 + | GCRY_FIPS_FLAG_REJECT_COMPAT110))); + + check_md_o_w_r_c (1); +-- +2.49.0 + diff --git a/libgcrypt-fips-kdf-Implement-new-FIPS-service-indicator-for-gcry_kdf_derive.patch b/libgcrypt-fips-kdf-Implement-new-FIPS-service-indicator-for-gcry_kdf_derive.patch new file mode 100644 index 0000000..a1710b9 --- /dev/null +++ b/libgcrypt-fips-kdf-Implement-new-FIPS-service-indicator-for-gcry_kdf_derive.patch @@ -0,0 +1,265 @@ +From 5cfa1aee5b98baf0d66333344e0fa45b79cca28b Mon Sep 17 00:00:00 2001 +From: NIIBE Yutaka +Date: Thu, 5 Dec 2024 14:52:17 +0900 +Subject: [PATCH 3/5] fips,kdf: Implement new FIPS service indicator for + gcry_kdf_derive. +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* cipher/kdf.c (_gcry_kdf_derive): Don't reject by GPG_ERR_INV_VALUE +but continue the computation, clearing IS_COMPLIANT. After successful +computation, call fips_service_indicator_mark_success with +IS_COMPLIANT. +* src/visibility.c (gcry_kdf_derive): Call fips_service_indicator_init. +* tests/t-kdf.c (check_fips_gcry_kdf_derive): New. +(main): Call check_fips_gcry_kdf_derive. + +-- + +GnuPG-bug-id: 7338 +Co-authored-by: David Sugar +Suggested-by: Stephan Mueller +Signed-off-by: NIIBE Yutaka +Signed-off-by: Lucas Mülling +--- + cipher/kdf.c | 33 ++++++----- + src/visibility.c | 1 + + tests/t-kdf.c | 149 ++++++++++++++++++++++++++++++++++++++++++++++- + 3 files changed, 169 insertions(+), 14 deletions(-) + +diff --git a/cipher/kdf.c b/cipher/kdf.c +index b4c5f83a..52e6a9ba 100644 +--- a/cipher/kdf.c ++++ b/cipher/kdf.c +@@ -279,28 +279,35 @@ _gcry_kdf_derive (const void *passphrase, size_t passphraselen, + break; + + case GCRY_KDF_PBKDF2: +- if (!saltlen) ++ if (!saltlen || !iterations) + ec = GPG_ERR_INV_VALUE; + else + { +- /* FIPS requires minimum passphrase length, see FIPS 140-3 IG D.N */ +- if (fips_mode () && passphraselen < 8) +- return GPG_ERR_INV_VALUE; ++ int is_compliant = 1; ++ ++ if (fips_mode ()) ++ { ++ /* FIPS requires minimum passphrase length, see FIPS 140-3 IG D.N */ ++ if (passphraselen < 8) ++ is_compliant &= 0; + +- /* FIPS requires minimum salt length of 128 b (SP 800-132 sec. 5.1, p.6) */ +- if (fips_mode () && saltlen < 16) +- return GPG_ERR_INV_VALUE; ++ /* FIPS requires minimum salt length of 128 b (SP 800-132 sec. 5.1, p.6) */ ++ if (saltlen < 16) ++ is_compliant &= 0; + +- /* FIPS requires minimum iterations bound (SP 800-132 sec 5.2, p.6) */ +- if (fips_mode () && iterations < 1000) +- return GPG_ERR_INV_VALUE; ++ /* FIPS requires minimum iterations bound (SP 800-132 sec 5.2, p.6) */ ++ if (iterations < 1000) ++ is_compliant &= 0; + +- /* Check minimum key size */ +- if (fips_mode () && keysize < 14) +- return GPG_ERR_INV_VALUE; ++ /* Check minimum key size */ ++ if (keysize < 14) ++ is_compliant &= 0; ++ } + + ec = _gcry_kdf_pkdf2 (passphrase, passphraselen, subalgo, + salt, saltlen, iterations, keysize, keybuffer); ++ if (!ec) ++ fips_service_indicator_mark_success (is_compliant); + } + break; + +diff --git a/src/visibility.c b/src/visibility.c +index 006e8f80..8f76b854 100644 +--- a/src/visibility.c ++++ b/src/visibility.c +@@ -1400,6 +1400,7 @@ gcry_kdf_derive (const void *passphrase, size_t passphraselen, + { + if (!fips_is_operational ()) + return gpg_error (fips_not_operational ()); ++ fips_service_indicator_init (); + return gpg_error (_gcry_kdf_derive (passphrase, passphraselen, algo, hashalgo, + salt, saltlen, iterations, + keysize, keybuffer)); +diff --git a/tests/t-kdf.c b/tests/t-kdf.c +index 10f64a7c..4b92bd30 100644 +--- a/tests/t-kdf.c ++++ b/tests/t-kdf.c +@@ -1927,6 +1927,151 @@ check_fips_indicators (void) + } + + ++static void ++check_fips_gcry_kdf_derive (void) ++{ ++ static struct { ++ const char *p; /* Passphrase. */ ++ size_t plen; /* Length of P. */ ++ int algo; ++ int subalgo; ++ const char *salt; ++ size_t saltlen; ++ unsigned long iterations; ++ int dklen; /* Requested key length. */ ++ const char *dk; /* Derived key. */ ++ int expect_failure; ++ } tv[] = { ++ { ++ "passwordPASSWORDpassword", 24, ++ GCRY_KDF_PBKDF2, GCRY_MD_SHA1, ++ "saltSALTsaltSALTsaltSALTsaltSALTsalt", 36, ++ 4096, ++ 25, ++ "\x3d\x2e\xec\x4f\xe4\x1c\x84\x9b\x80\xc8" ++ "\xd8\x36\x62\xc0\xe4\x4a\x8b\x29\x1a\x96" ++ "\x4c\xf2\xf0\x70\x38", ++ 0 ++ }, ++ { ++ "pleaseletmein", 13, ++ GCRY_KDF_SCRYPT, 16384, ++ "SodiumChloride", 14, ++ 1, ++ 64, ++ "\x70\x23\xbd\xcb\x3a\xfd\x73\x48\x46\x1c\x06\xcd\x81\xfd\x38\xeb" ++ "\xfd\xa8\xfb\xba\x90\x4f\x8e\x3e\xa9\xb5\x43\xf6\x54\x5d\xa1\xf2" ++ "\xd5\x43\x29\x55\x61\x3f\x0f\xcf\x62\xd4\x97\x05\x24\x2a\x9a\xf9" ++ "\xe6\x1e\x85\xdc\x0d\x65\x1e\x40\xdf\xcf\x01\x7b\x45\x57\x58\x87", ++ 1 /* not-compliant because unallowed algo */ ++ }, ++ { ++ "passwor", 7, ++ GCRY_KDF_PBKDF2, GCRY_MD_SHA1, ++ "saltSALTsaltSALTsaltSALTsaltSALTsalt", 36, ++ 4096, ++ 25, ++ "\xf4\x93\xee\x2b\xbf\x44\x0b\x9e\x64\x53" ++ "\xc2\xb3\x87\xdc\x73\xf8\xfd\xe6\x97\xda" ++ "\xb8\x24\xa0\x26\x50", ++ 1 /* not-compliant because passphrase len is too small */ ++ }, ++ { ++ "passwordPASSWORDpassword", 24, ++ GCRY_KDF_PBKDF2, GCRY_MD_SHA1, ++ "saltSALTsaltSAL", 15, ++ 4096, ++ 25, ++ "\x14\x05\xa4\x2a\xf4\xa8\x12\x14\x7b\x65" ++ "\x8f\xaa\xf0\x7f\x25\xe5\x0f\x0b\x2b\xb7" ++ "\xcf\x8d\x29\x23\x4b", ++ 1 /* not-compliant because salt len is too small */ ++ }, ++ { ++ "passwordPASSWORDpassword", 24, ++ GCRY_KDF_PBKDF2, GCRY_MD_SHA1, ++ "saltSALTsaltSALTsaltSALTsaltSALTsalt", 36, ++ 999, ++ 25, ++ "\xac\xf8\xb4\x67\x41\xc7\xf3\xd1\xa0\xc0" ++ "\x08\xbe\x9b\x23\x96\x78\xbd\x93\xda\x4a" ++ "\x30\xd4\xfb\xf0\x33", ++ 1 /* not-compliant because too few iterations */ ++ }, ++ { ++ "passwordPASSWORDpassword", 24, ++ GCRY_KDF_PBKDF2, GCRY_MD_SHA1, ++ "saltSALTsaltSALTsaltSALTsaltSALTsalt", 36, ++ 4096, ++ 13, ++ "\x3d\x2e\xec\x4f\xe4\x1c\x84\x9b\x80\xc8" ++ "\xd8\x36\x62", ++ 1 /* not-compliant because key size too small */ ++ }, ++ }; ++ ++ int tvidx; ++ gpg_error_t err; ++ unsigned char outbuf[100]; ++ int i; ++ ++ for (tvidx=0; tvidx < DIM(tv); tvidx++) ++ { ++ if (verbose) ++ fprintf (stderr, "checking gcry_kdf_derive test vector %d algo %d for FIPS\n", ++ tvidx, tv[tvidx].algo); ++ assert (tv[tvidx].dklen <= sizeof outbuf); ++ err = gcry_kdf_derive (tv[tvidx].p, tv[tvidx].plen, ++ tv[tvidx].algo, tv[tvidx].subalgo, ++ tv[tvidx].salt, tv[tvidx].saltlen, ++ tv[tvidx].iterations, tv[tvidx].dklen, outbuf); ++ ++ if (err) ++ { ++ fail ("gcry_kdf_derive test %d unexpectedly returned an error in FIPS mode: %s\n", ++ tvidx, gpg_strerror (err)); ++ } ++ else ++ { ++ gpg_err_code_t ec; ++ ++ ec = gcry_get_fips_service_indicator (); ++ if (ec == GPG_ERR_INV_OP) ++ { ++ /* libgcrypt is old, no support of the FIPS service indicator. */ ++ fail ("gcry_kdf_derive test %d unexpectedly failed to check the FIPS service indicator.\n", ++ tvidx); ++ continue; ++ } ++ ++ if (!tv[tvidx].expect_failure && ec) ++ { ++ /* Success with the FIPS service indicator == 0 expected, but != 0. */ ++ fail ("gcry_kdf_derive test %d unexpectedly set the indicator in FIPS mode.\n", ++ tvidx); ++ continue; ++ } ++ else if (tv[tvidx].expect_failure && !ec) ++ { ++ /* Success with the FIPS service indicator != 0 expected, but == 0. */ ++ fail ("gcry_kdf_derive test %d unexpectedly cleared the indicator in FIPS mode.\n", ++ tvidx); ++ continue; ++ } ++ ++ if (memcmp (outbuf, tv[tvidx].dk, tv[tvidx].dklen)) ++ { ++ fail ("gcry_kdf_derive test %d failed: mismatch\n", tvidx); ++ fputs ("got:", stderr); ++ for (i=0; i < tv[tvidx].dklen; i++) ++ fprintf (stderr, " %02x", outbuf[i]); ++ putc ('\n', stderr); ++ } ++ } ++ } ++} ++ ++ + int + main (int argc, char **argv) + { +@@ -2008,7 +2153,9 @@ main (int argc, char **argv) + check_onestep_kdf (); + check_hkdf (); + if (in_fips_mode) +- check_fips_indicators(); ++ check_fips_indicators (); ++ if (in_fips_mode) ++ check_fips_gcry_kdf_derive (); + } + + return error_count ? 1 : 0; +-- +2.49.0 + diff --git a/libgcrypt-fips-mac-Implement-new-FIPS-service-indicator-for-gcry_mac_open.patch b/libgcrypt-fips-mac-Implement-new-FIPS-service-indicator-for-gcry_mac_open.patch new file mode 100644 index 0000000..7843a39 --- /dev/null +++ b/libgcrypt-fips-mac-Implement-new-FIPS-service-indicator-for-gcry_mac_open.patch @@ -0,0 +1,115 @@ +From fcb0c7004b0b6b318fdcced2bf61d9acb1e28cfc Mon Sep 17 00:00:00 2001 +From: NIIBE Yutaka +Date: Fri, 13 Dec 2024 14:25:02 +0900 +Subject: [PATCH 04/19] fips,mac: Implement new FIPS service indicator for + gcry_mac_open. +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* src/gcrypt.h.in (GCRY_MAC_FLAG_REJECT_NON_FIPS): New. +* cipher/mac.c (mac_open): Have FLAGS, instead of SECURE. Reject when +GCRY_MAC_FLAG_REJECT_NON_FIPS, otherwise, mark non compliant. +(_gcry_mac_open): Follow the change. +* src/visibility.c (gcry_mac_open): Add initialization for FIPS +service indicator. +(gcry_mac_setkey): Likewise. Don't reject but mark. + +-- + +GnuPG-bug-id: 7338 +Signed-off-by: NIIBE Yutaka +Signed-off-by: Lucas Mülling +--- + cipher/mac.c | 15 +++++++++++---- + src/gcrypt.h.in | 3 ++- + src/visibility.c | 5 +++-- + 3 files changed, 16 insertions(+), 7 deletions(-) + +diff --git a/cipher/mac.c b/cipher/mac.c +index 128ac53d..0df48fd7 100644 +--- a/cipher/mac.c ++++ b/cipher/mac.c +@@ -513,11 +513,13 @@ check_mac_algo (int algorithm) + * Open a message digest handle for use with algorithm ALGO. + */ + static gcry_err_code_t +-mac_open (gcry_mac_hd_t * hd, int algo, int secure, gcry_ctx_t ctx) ++mac_open (gcry_mac_hd_t * hd, int algo, unsigned int flags, gcry_ctx_t ctx) + { + const gcry_mac_spec_t *spec; + gcry_err_code_t err; + gcry_mac_hd_t h; ++ int secure = !!(flags & GCRY_MAC_FLAG_SECURE); ++ int reject_non_fips = !!(flags & GCRY_MAC_FLAG_REJECT_NON_FIPS); + + spec = spec_from_algo (algo); + if (!spec) +@@ -525,7 +527,12 @@ mac_open (gcry_mac_hd_t * hd, int algo, int secure, gcry_ctx_t ctx) + else if (spec->flags.disabled) + return GPG_ERR_MAC_ALGO; + else if (!spec->flags.fips && fips_mode ()) +- return GPG_ERR_MAC_ALGO; ++ { ++ if (reject_non_fips) ++ return GPG_ERR_MAC_ALGO; ++ else ++ fips_service_indicator_mark_non_compliant (); ++ } + else if (!spec->ops) + return GPG_ERR_MAC_ALGO; + else if (!spec->ops->open || !spec->ops->write || !spec->ops->setkey || +@@ -643,10 +650,10 @@ _gcry_mac_open (gcry_mac_hd_t * h, int algo, unsigned int flags, + gcry_err_code_t rc; + gcry_mac_hd_t hd = NULL; + +- if ((flags & ~GCRY_MAC_FLAG_SECURE)) ++ if ((flags & ~(GCRY_MAC_FLAG_SECURE | GCRY_MAC_FLAG_REJECT_NON_FIPS))) + rc = GPG_ERR_INV_ARG; + else +- rc = mac_open (&hd, algo, !!(flags & GCRY_MAC_FLAG_SECURE), ctx); ++ rc = mac_open (&hd, algo, flags, ctx); + + *h = rc ? NULL : hd; + return rc; +diff --git a/src/gcrypt.h.in b/src/gcrypt.h.in +index 96bf88f6..2a378639 100644 +--- a/src/gcrypt.h.in ++++ b/src/gcrypt.h.in +@@ -1560,7 +1560,8 @@ enum gcry_mac_algos + /* Flags used with the open function. */ + enum gcry_mac_flags + { +- GCRY_MAC_FLAG_SECURE = 1 /* Allocate all buffers in "secure" memory. */ ++ GCRY_MAC_FLAG_SECURE = 1, /* Allocate all buffers in "secure" memory. */ ++ GCRY_MAC_FLAG_REJECT_NON_FIPS = 2 /* Reject non-FIPS-compliant algo. */ + }; + + /* Create a MAC handle for algorithm ALGO. FLAGS may be given as an bitwise OR +diff --git a/src/visibility.c b/src/visibility.c +index 44b05eb2..7699f14f 100644 +--- a/src/visibility.c ++++ b/src/visibility.c +@@ -946,7 +946,7 @@ gcry_mac_open (gcry_mac_hd_t *handle, int algo, unsigned int flags, + *handle = NULL; + return gpg_error (fips_not_operational ()); + } +- ++ fips_service_indicator_init (); + return gpg_error (_gcry_mac_open (handle, algo, flags, ctx)); + } + +@@ -962,8 +962,9 @@ gcry_mac_setkey (gcry_mac_hd_t hd, const void *key, size_t keylen) + if (!fips_is_operational ()) + return gpg_error (fips_not_operational ()); + ++ fips_service_indicator_init (); + if (fips_mode () && keylen < 14) +- return GPG_ERR_INV_VALUE; ++ fips_service_indicator_mark_non_compliant (); + + return gpg_error (_gcry_mac_setkey (hd, key, keylen)); + } +-- +2.49.0 + diff --git a/libgcrypt-fips-md-Implement-new-FIPS-service-indicator-for-gcry_md_hash_.patch b/libgcrypt-fips-md-Implement-new-FIPS-service-indicator-for-gcry_md_hash_.patch new file mode 100644 index 0000000..71f1671 --- /dev/null +++ b/libgcrypt-fips-md-Implement-new-FIPS-service-indicator-for-gcry_md_hash_.patch @@ -0,0 +1,188 @@ +From 3478caac62c712547f7c0e07f4cf9602bc317997 Mon Sep 17 00:00:00 2001 +From: NIIBE Yutaka +Date: Fri, 6 Dec 2024 14:33:58 +0900 +Subject: [PATCH 4/5] fips,md: Implement new FIPS service indicator for + gcry_md_hash_*. +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* cipher/md.c (md_enable): Add an NO_REJECT argument. +(md_open): Check flags against GCRY_MD_FLAG_FIPS_NO_REJECTION to +call md_enable. +(_gcry_md_enable): Follow the change. +(_gcry_md_hash_buffer): Don't reject but keep the computation. +Call fips_service_indicator_mark_success. +(_gcry_md_hash_buffers_extract): Likewise. +* src/gcrypt.h.in (GCRY_MD_FLAG_FIPS_NO_REJECTION): New. +* src/visibility.c (gcry_md_hash_buffer, gcry_md_hash_buffers): Call +fips_service_indicator_init. +(gcry_md_hash_buffers_ext): Likewise. + +-- + +GnuPG-bug-id: 7338 +Signed-off-by: NIIBE Yutaka +Signed-off-by: Lucas Mülling +--- + cipher/md.c | 32 +++++++++++++++++++++++--------- + src/gcrypt.h.in | 1 + + src/visibility.c | 3 +++ + 3 files changed, 27 insertions(+), 9 deletions(-) + +diff --git a/cipher/md.c b/cipher/md.c +index 1991c331..c2bd18c6 100644 +--- a/cipher/md.c ++++ b/cipher/md.c +@@ -285,7 +285,7 @@ struct gcry_md_context + #define CTX_MAGIC_NORMAL 0x11071961 + #define CTX_MAGIC_SECURE 0x16917011 + +-static gcry_err_code_t md_enable (gcry_md_hd_t hd, int algo); ++static gcry_err_code_t md_enable (gcry_md_hd_t hd, int algo, int no_reject); + static void md_close (gcry_md_hd_t a); + static void md_write (gcry_md_hd_t a, const void *inbuf, size_t inlen); + static byte *md_read( gcry_md_hd_t a, int algo ); +@@ -517,7 +517,8 @@ md_open (gcry_md_hd_t *h, int algo, unsigned int flags) + + if (algo) + { +- err = md_enable (hd, algo); ++ err = md_enable (hd, algo, ++ !!(flags & GCRY_MD_FLAG_FIPS_NO_REJECTION)); + if (err) + md_close (hd); + } +@@ -554,7 +555,7 @@ _gcry_md_open (gcry_md_hd_t *h, int algo, unsigned int flags) + + + static gcry_err_code_t +-md_enable (gcry_md_hd_t hd, int algorithm) ++md_enable (gcry_md_hd_t hd, int algorithm, int no_reject) + { + struct gcry_md_context *h = hd->ctx; + const gcry_md_spec_t *spec; +@@ -576,7 +577,7 @@ md_enable (gcry_md_hd_t hd, int algorithm) + err = GPG_ERR_DIGEST_ALGO; + + /* Any non-FIPS algorithm should go this way */ +- if (!err && !spec->flags.fips && fips_mode ()) ++ if (!err && !no_reject && !spec->flags.fips && fips_mode ()) + err = GPG_ERR_DIGEST_ALGO; + + if (!err && h->flags.hmac && spec->read == NULL) +@@ -619,7 +620,7 @@ md_enable (gcry_md_hd_t hd, int algorithm) + gcry_err_code_t + _gcry_md_enable (gcry_md_hd_t hd, int algorithm) + { +- return md_enable (hd, algorithm); ++ return md_enable (hd, algorithm, 0); + } + + +@@ -1260,7 +1261,7 @@ _gcry_md_hash_buffer (int algo, void *digest, + iov.off = 0; + iov.len = length; + +- if (spec->flags.disabled || (!spec->flags.fips && fips_mode ())) ++ if (spec->flags.disabled) + log_bug ("gcry_md_hash_buffer failed for algo %d: %s", + algo, gpg_strerror (gcry_error (GPG_ERR_DIGEST_ALGO))); + +@@ -1273,7 +1274,7 @@ _gcry_md_hash_buffer (int algo, void *digest, + gcry_md_hd_t h; + gpg_err_code_t err; + +- err = md_open (&h, algo, 0); ++ err = md_open (&h, algo, GCRY_MD_FLAG_FIPS_NO_REJECTION); + if (err) + log_bug ("gcry_md_open failed for algo %d: %s", + algo, gpg_strerror (gcry_error(err))); +@@ -1282,6 +1283,12 @@ _gcry_md_hash_buffer (int algo, void *digest, + memcpy (digest, md_read (h, algo), md_digest_length (algo)); + md_close (h); + } ++ ++ if (fips_mode ()) ++ { ++ int is_compliant = spec->flags.fips; ++ fips_service_indicator_mark_success (is_compliant); ++ } + } + + +@@ -1336,7 +1343,7 @@ _gcry_md_hash_buffers_extract (int algo, unsigned int flags, void *digest, + + if (!hmac && spec->hash_buffers) + { +- if (spec->flags.disabled || (!spec->flags.fips && fips_mode ())) ++ if (spec->flags.disabled) + return GPG_ERR_DIGEST_ALGO; + + spec->hash_buffers (digest, digestlen, iov, iovcnt); +@@ -1348,7 +1355,8 @@ _gcry_md_hash_buffers_extract (int algo, unsigned int flags, void *digest, + gcry_md_hd_t h; + gpg_err_code_t rc; + +- rc = md_open (&h, algo, (hmac? GCRY_MD_FLAG_HMAC:0)); ++ rc = md_open (&h, algo, ((hmac? GCRY_MD_FLAG_HMAC:0) ++ | GCRY_MD_FLAG_FIPS_NO_REJECTION)); + if (rc) + return rc; + +@@ -1374,6 +1382,12 @@ _gcry_md_hash_buffers_extract (int algo, unsigned int flags, void *digest, + md_close (h); + } + ++ if (fips_mode ()) ++ { ++ int is_compliant = spec->flags.fips; ++ fips_service_indicator_mark_success (is_compliant); ++ } ++ + return 0; + } + +diff --git a/src/gcrypt.h.in b/src/gcrypt.h.in +index 2f61a0bc..18d04a38 100644 +--- a/src/gcrypt.h.in ++++ b/src/gcrypt.h.in +@@ -1318,6 +1318,7 @@ enum gcry_md_flags + { + GCRY_MD_FLAG_SECURE = 1, /* Allocate all buffers in "secure" memory. */ + GCRY_MD_FLAG_HMAC = 2, /* Make an HMAC out of this algorithm. */ ++ GCRY_MD_FLAG_FIPS_NO_REJECTION = 4, /* Don't reject for FIPS. */ + GCRY_MD_FLAG_BUGEMU1 = 0x0100 + }; + +diff --git a/src/visibility.c b/src/visibility.c +index 8f76b854..be5deda1 100644 +--- a/src/visibility.c ++++ b/src/visibility.c +@@ -1281,6 +1281,7 @@ gcry_md_hash_buffer (int algo, void *digest, + (void)fips_not_operational (); + fips_signal_error ("called in non-operational state"); + } ++ fips_service_indicator_init (); + _gcry_md_hash_buffer (algo, digest, buffer, length); + } + +@@ -1293,6 +1294,7 @@ gcry_md_hash_buffers (int algo, unsigned int flags, void *digest, + (void)fips_not_operational (); + fips_signal_error ("called in non-operational state"); + } ++ fips_service_indicator_init (); + return gpg_error (_gcry_md_hash_buffers (algo, flags, digest, iov, iovcnt)); + } + +@@ -1306,6 +1308,7 @@ gcry_md_hash_buffers_ext (int algo, unsigned int flags, void *digest, + (void)fips_not_operational (); + fips_signal_error ("called in non-operational state"); + } ++ fips_service_indicator_init (); + return gpg_error (_gcry_md_hash_buffers_extract (algo, flags, digest, + digestlen, iov, iovcnt)); + } +-- +2.49.0 + diff --git a/libgcrypt-fips-md-Implement-new-FIPS-service-indicator-for-gcry_md_open-API.patch b/libgcrypt-fips-md-Implement-new-FIPS-service-indicator-for-gcry_md_open-API.patch new file mode 100644 index 0000000..0f580b1 --- /dev/null +++ b/libgcrypt-fips-md-Implement-new-FIPS-service-indicator-for-gcry_md_open-API.patch @@ -0,0 +1,298 @@ +From 9757e280794f537efc82c4eaa9a2944ece6a068a Mon Sep 17 00:00:00 2001 +From: NIIBE Yutaka +Date: Thu, 12 Dec 2024 11:40:31 +0900 +Subject: [PATCH] fips,md: Implement new FIPS service indicator for + gcry_md_open API. +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* src/gcrypt.h.in (GCRY_MD_FLAG_FIPS_NO_REJECTION): Remove. +(GCRY_MD_FLAG_REJECT_NON_FIPS): New. +* cipher/md.c (struct gcry_md_context): Add reject_non_fips. +(md_enable): Remove NO_REJECT argument. +(md_open): Change the FLAGS handling. +(_gcry_md_open): Add checking of FIPS compliance against ALGO. +(_gcry_md_enable): Likewise. +(_gcry_md_hash_buffer): Follow the change of md_open change +which now defaults to no rejection. +(_gcry_md_hash_buffers_extract): Likewise. +* src/visibility.c (gcry_md_open): Add fips_service_indicator_init. +(gcry_md_enable): Likewise. +(gcry_md_setkey): Don't reject but mark non-compliance. +* tests/t-kdf.c (check_fips_gcry_kdf_derive): Add a test with +non-compliant hash function. +* cipher/mac-hmac.c (_gcry_mac_type_spec_hmac_md5): It's not +compliant. +* cipher/md5.c (gcry_md_oid_spec_t oid_spec_md5): It's not compliant. +* tests/t-digest.c (check_hash_buffer, check_hash_buffers): MD5 +tests enabled. + +-- + +See 6376 for the MD5 compliance change in the past. This commit +reverts the change in: + dc4a60e2d70bc52ba2955f8e676341d675ab89a0 + +GnuPG-bug-id: 7338 +Signed-off-by: NIIBE Yutaka +Signed-off-by: Lucas Mülling +--- + cipher/mac-hmac.c | 2 +- + cipher/md.c | 57 +++++++++++++++++++++++++++++++++++++++-------- + cipher/md5.c | 2 +- + src/gcrypt.h.in | 2 +- + src/visibility.c | 6 +++-- + tests/t-digest.c | 6 ++--- + tests/t-kdf.c | 12 ++++++++++ + 7 files changed, 69 insertions(+), 18 deletions(-) + +Index: libgcrypt-1.11.0/cipher/mac-hmac.c +=================================================================== +--- libgcrypt-1.11.0.orig/cipher/mac-hmac.c ++++ libgcrypt-1.11.0/cipher/mac-hmac.c +@@ -1413,7 +1413,7 @@ const gcry_mac_spec_t _gcry_mac_type_spe + #endif + #if USE_MD5 + const gcry_mac_spec_t _gcry_mac_type_spec_hmac_md5 = { +- GCRY_MAC_HMAC_MD5, {0, 1}, "HMAC_MD5", ++ GCRY_MAC_HMAC_MD5, {0, 0}, "HMAC_MD5", + &hmac_ops + }; + #endif +Index: libgcrypt-1.11.0/cipher/md.c +=================================================================== +--- libgcrypt-1.11.0.orig/cipher/md.c ++++ libgcrypt-1.11.0/cipher/md.c +@@ -275,6 +275,7 @@ struct gcry_md_context + unsigned int finalized:1; + unsigned int bugemu1:1; + unsigned int hmac:1; ++ unsigned int reject_non_fips:1; + } flags; + size_t actual_handle_size; /* Allocated size of this handle. */ + FILE *debug; +@@ -285,7 +286,7 @@ struct gcry_md_context + #define CTX_MAGIC_NORMAL 0x11071961 + #define CTX_MAGIC_SECURE 0x16917011 + +-static gcry_err_code_t md_enable (gcry_md_hd_t hd, int algo, int no_reject); ++static gcry_err_code_t md_enable (gcry_md_hd_t hd, int algo); + static void md_close (gcry_md_hd_t a); + static void md_write (gcry_md_hd_t a, const void *inbuf, size_t inlen); + static byte *md_read( gcry_md_hd_t a, int algo ); +@@ -508,6 +509,7 @@ md_open (gcry_md_hd_t *h, int algo, unsi + ctx->flags.secure = secure; + ctx->flags.hmac = hmac; + ctx->flags.bugemu1 = !!(flags & GCRY_MD_FLAG_BUGEMU1); ++ ctx->flags.reject_non_fips = !!(flags & GCRY_MD_FLAG_REJECT_NON_FIPS); + } + + if (! err) +@@ -517,8 +519,7 @@ md_open (gcry_md_hd_t *h, int algo, unsi + + if (algo) + { +- err = md_enable (hd, algo, +- !!(flags & GCRY_MD_FLAG_FIPS_NO_REJECTION)); ++ err = md_enable (hd, algo); + if (err) + md_close (hd); + } +@@ -543,24 +544,44 @@ _gcry_md_open (gcry_md_hd_t *h, int algo + + if ((flags & ~(GCRY_MD_FLAG_SECURE + | GCRY_MD_FLAG_HMAC ++ | GCRY_MD_FLAG_REJECT_NON_FIPS + | GCRY_MD_FLAG_BUGEMU1))) + rc = GPG_ERR_INV_ARG; + else + rc = md_open (&hd, algo, flags); + + *h = rc? NULL : hd; ++ ++ if (!rc && fips_mode ()) ++ { ++ GcryDigestEntry *entry = hd->ctx->list; ++ /* No ENTRY means that ALGO==0. ++ It's not yet known, if it's FIPS compliant or not. */ ++ int is_compliant_algo = 1; ++ ++ if (entry) ++ { ++ const gcry_md_spec_t *spec = entry->spec; ++ is_compliant_algo = spec->flags.fips; ++ } ++ ++ if (!is_compliant_algo) ++ fips_service_indicator_mark_non_compliant (); ++ } ++ + return rc; + } + + + + static gcry_err_code_t +-md_enable (gcry_md_hd_t hd, int algorithm, int no_reject) ++md_enable (gcry_md_hd_t hd, int algorithm) + { + struct gcry_md_context *h = hd->ctx; + const gcry_md_spec_t *spec; + GcryDigestEntry *entry; + gcry_err_code_t err = 0; ++ int reject_non_fips = h->flags.reject_non_fips; + + for (entry = h->list; entry; entry = entry->next) + if (entry->spec->algo == algorithm) +@@ -577,7 +598,7 @@ md_enable (gcry_md_hd_t hd, int algorith + err = GPG_ERR_DIGEST_ALGO; + + /* Any non-FIPS algorithm should go this way */ +- if (!err && !no_reject && !spec->flags.fips && fips_mode ()) ++ if (!err && reject_non_fips && !spec->flags.fips && fips_mode ()) + err = GPG_ERR_DIGEST_ALGO; + + if (!err && h->flags.hmac && spec->read == NULL) +@@ -620,7 +641,26 @@ md_enable (gcry_md_hd_t hd, int algorith + gcry_err_code_t + _gcry_md_enable (gcry_md_hd_t hd, int algorithm) + { +- return md_enable (hd, algorithm, 0); ++ gcry_err_code_t rc; ++ ++ rc = md_enable (hd, algorithm); ++ if (!rc && fips_mode ()) ++ { ++ GcryDigestEntry *entry = hd->ctx->list; ++ /* No ENTRY means, something goes wrong. */ ++ int is_compliant_algo = 0; ++ ++ if (entry) ++ { ++ const gcry_md_spec_t *spec = entry->spec; ++ is_compliant_algo = spec->flags.fips; ++ } ++ ++ if (!is_compliant_algo) ++ fips_service_indicator_mark_non_compliant (); ++ } ++ ++ return rc; + } + + +@@ -1274,7 +1314,7 @@ _gcry_md_hash_buffer (int algo, void *di + gcry_md_hd_t h; + gpg_err_code_t err; + +- err = md_open (&h, algo, GCRY_MD_FLAG_FIPS_NO_REJECTION); ++ err = md_open (&h, algo, 0); + if (err) + log_bug ("gcry_md_open failed for algo %d: %s", + algo, gpg_strerror (gcry_error(err))); +@@ -1355,8 +1395,7 @@ _gcry_md_hash_buffers_extract (int algo, + gcry_md_hd_t h; + gpg_err_code_t rc; + +- rc = md_open (&h, algo, ((hmac? GCRY_MD_FLAG_HMAC:0) +- | GCRY_MD_FLAG_FIPS_NO_REJECTION)); ++ rc = md_open (&h, algo, (hmac? GCRY_MD_FLAG_HMAC:0)); + if (rc) + return rc; + +Index: libgcrypt-1.11.0/cipher/md5.c +=================================================================== +--- libgcrypt-1.11.0.orig/cipher/md5.c ++++ libgcrypt-1.11.0/cipher/md5.c +@@ -314,7 +314,7 @@ static const gcry_md_oid_spec_t oid_spec + + const gcry_md_spec_t _gcry_digest_spec_md5 = + { +- GCRY_MD_MD5, {0, 1}, ++ GCRY_MD_MD5, {0, 0}, + "MD5", asn, DIM (asn), oid_spec_md5, 16, + md5_init, _gcry_md_block_write, md5_final, md5_read, NULL, + NULL, +Index: libgcrypt-1.11.0/src/gcrypt.h.in +=================================================================== +--- libgcrypt-1.11.0.orig/src/gcrypt.h.in ++++ libgcrypt-1.11.0/src/gcrypt.h.in +@@ -1320,7 +1320,7 @@ enum gcry_md_flags + { + GCRY_MD_FLAG_SECURE = 1, /* Allocate all buffers in "secure" memory. */ + GCRY_MD_FLAG_HMAC = 2, /* Make an HMAC out of this algorithm. */ +- GCRY_MD_FLAG_FIPS_NO_REJECTION = 4, /* Don't reject for FIPS. */ ++ GCRY_MD_FLAG_REJECT_NON_FIPS = 4, /* Reject non-FIPS-compliant algo. */ + GCRY_MD_FLAG_BUGEMU1 = 0x0100 + }; + +Index: libgcrypt-1.11.0/src/visibility.c +=================================================================== +--- libgcrypt-1.11.0.orig/src/visibility.c ++++ libgcrypt-1.11.0/src/visibility.c +@@ -1204,7 +1204,7 @@ gcry_md_open (gcry_md_hd_t *h, int algo, + *h = NULL; + return gpg_error (fips_not_operational ()); + } +- ++ fips_service_indicator_init (); + return gpg_error (_gcry_md_open (h, algo, flags)); + } + +@@ -1219,6 +1219,7 @@ gcry_md_enable (gcry_md_hd_t hd, int alg + { + if (!fips_is_operational ()) + return gpg_error (fips_not_operational ()); ++ fips_service_indicator_init (); + return gpg_error (_gcry_md_enable (hd, algo)); + } + +@@ -1382,8 +1383,9 @@ gcry_md_setkey (gcry_md_hd_t hd, const v + if (!fips_is_operational ()) + return gpg_error (fips_not_operational ()); + ++ fips_service_indicator_init (); + if (fips_mode () && keylen < 14) +- return GPG_ERR_INV_VALUE; ++ fips_service_indicator_mark_non_compliant (); + + return gpg_error (_gcry_md_setkey (hd, key, keylen)); + } +Index: libgcrypt-1.11.0/tests/t-digest.c +=================================================================== +--- libgcrypt-1.11.0.orig/tests/t-digest.c ++++ libgcrypt-1.11.0/tests/t-digest.c +@@ -48,8 +48,7 @@ check_digests (void) + const char *expect; + int expect_failure; + } tv[] = { +-#undef ENABLE_THIS_AFTER_T6376_CHANGE_REVISED +-#ifdef ENABLE_THIS_AFTER_T6376_CHANGE_REVISED ++#if USE_MD5 + { GCRY_MD_MD5, "abc", 3, + "\x90\x01\x50\x98\x3C\xD2\x4F\xB0\xD6\x96\x3F\x7D\x28\xE1\x7F\x72", 1 }, + #endif +Index: libgcrypt-1.11.0/tests/t-kdf.c +=================================================================== +--- libgcrypt-1.11.0.orig/tests/t-kdf.c ++++ libgcrypt-1.11.0/tests/t-kdf.c +@@ -2008,6 +2008,18 @@ check_fips_gcry_kdf_derive (void) + "\xd8\x36\x62", + 1 /* not-compliant because key size too small */ + }, ++ { ++ "passwordPASSWORDpassword", 24, ++ GCRY_KDF_PBKDF2, GCRY_MD_BLAKE2B_512, ++ "saltSALTsaltSALTsaltSALTsaltSALTsalt", 36, ++ 4096, ++ 60, ++ "\xa4\x6b\x53\x35\xdb\xdd\xa3\xd2\x5d\x19\xbb\x11\xfe\xdd\xd9\x9e" ++ "\x45\x2a\x7c\x34\x47\x41\x98\xca\x31\x74\xb6\x34\x22\xac\x83\xb0" ++ "\x38\x6e\xf5\x93\x0f\xf5\x16\x46\x0b\x97\xdc\x6c\x27\x5b\xe7\x25" ++ "\xc2\xcb\xec\x50\x02\xc6\x52\x8b\x34\x68\x53\x65", ++ 1 /* not-compliant because subalgo is not the one of approved */ ++ } + }; + + int tvidx; diff --git a/libgcrypt-fips-md-gcry_md_copy-should-care-about-FIPS-service-indicator.patch b/libgcrypt-fips-md-gcry_md_copy-should-care-about-FIPS-service-indicator.patch new file mode 100644 index 0000000..5edccac --- /dev/null +++ b/libgcrypt-fips-md-gcry_md_copy-should-care-about-FIPS-service-indicator.patch @@ -0,0 +1,85 @@ +From 60db2a175d120aba6818de49638b36006878abf7 Mon Sep 17 00:00:00 2001 +From: NIIBE Yutaka +Date: Wed, 18 Dec 2024 14:14:37 +0900 +Subject: [PATCH 10/19] fips,md: gcry_md_copy should care about FIPS service + indicator. +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* cipher/md.c (md_copy): In a case of non-compliant, mark with +fips_service_indicator_mark_non_compliant. +* src/visibility.c (gcry_md_copy): Initialize the indicator. + +-- + +GnuPG-bug-id: 7338 +Signed-off-by: NIIBE Yutaka +Signed-off-by: Lucas Mülling +--- + cipher/md.c | 11 +++++++++++ + src/visibility.c | 1 + + 2 files changed, 12 insertions(+) + +diff --git a/cipher/md.c b/cipher/md.c +index 666e1dfa..08a564ad 100644 +--- a/cipher/md.c ++++ b/cipher/md.c +@@ -673,6 +673,7 @@ md_copy (gcry_md_hd_t ahd, gcry_md_hd_t *b_hd) + GcryDigestEntry *ar, *br; + gcry_md_hd_t bhd; + size_t n; ++ int is_compliant_algo = 1; + + if (ahd->bufpos) + md_write (ahd, NULL, 0); +@@ -699,10 +700,15 @@ md_copy (gcry_md_hd_t ahd, gcry_md_hd_t *b_hd) + b->list = NULL; + b->debug = NULL; + ++ if (!a->list) ++ is_compliant_algo = 0; ++ + /* Copy the complete list of algorithms. The copied list is + reversed, but that doesn't matter. */ + for (ar = a->list; ar; ar = ar->next) + { ++ const gcry_md_spec_t *spec = ar->spec; ++ + if (a->flags.secure) + br = xtrymalloc_secure (ar->actual_struct_size); + else +@@ -714,6 +720,8 @@ md_copy (gcry_md_hd_t ahd, gcry_md_hd_t *b_hd) + goto leave; + } + ++ is_compliant_algo &= spec->flags.fips; ++ + memcpy (br, ar, ar->actual_struct_size); + br->next = b->list; + b->list = br; +@@ -724,6 +732,9 @@ md_copy (gcry_md_hd_t ahd, gcry_md_hd_t *b_hd) + + *b_hd = bhd; + ++ if (!is_compliant_algo) ++ fips_service_indicator_mark_non_compliant (); ++ + leave: + return err; + } +diff --git a/src/visibility.c b/src/visibility.c +index d219f1a6..c9d07f0b 100644 +--- a/src/visibility.c ++++ b/src/visibility.c +@@ -1232,6 +1232,7 @@ gcry_md_copy (gcry_md_hd_t *bhd, gcry_md_hd_t ahd) + *bhd = NULL; + return gpg_error (fips_not_operational ()); + } ++ fips_service_indicator_init (); + return gpg_error (_gcry_md_copy (bhd, ahd)); + } + +-- +2.49.0 + diff --git a/libgcrypt-fips-tests-Add-t-digest.patch b/libgcrypt-fips-tests-Add-t-digest.patch new file mode 100644 index 0000000..fc5e8e8 --- /dev/null +++ b/libgcrypt-fips-tests-Add-t-digest.patch @@ -0,0 +1,243 @@ +From 7faf542f157330f3b247fa2542182ac805f06737 Mon Sep 17 00:00:00 2001 +From: NIIBE Yutaka +Date: Mon, 9 Dec 2024 14:05:59 +0900 +Subject: [PATCH 5/5] fips,tests: Add t-digest. +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* tests/Makefile.am (tests_bin): Add t-digest. +* tests/t-digest.c: New. + +-- + +GnuPG-bug-id: 7338 +Signed-off-by: NIIBE Yutaka +Signed-off-by: Lucas Mülling +--- + tests/Makefile.am | 2 +- + tests/t-digest.c | 199 ++++++++++++++++++++++++++++++++++++++++++++++ + 2 files changed, 200 insertions(+), 1 deletion(-) + create mode 100644 tests/t-digest.c + +diff --git a/tests/Makefile.am b/tests/Makefile.am +index 52f7dd61..93774fe9 100644 +--- a/tests/Makefile.am ++++ b/tests/Makefile.am +@@ -25,7 +25,7 @@ tests_bin = \ + version t-secmem mpitests t-sexp t-convert \ + t-mpi-bit t-mpi-point t-lock \ + prime basic keygen pubkey hmac hashtest t-kdf keygrip \ +- aeswrap random t-kem t-mlkem t-thread-local ++ aeswrap random t-kem t-mlkem t-thread-local t-digest + + if USE_RSA + tests_bin += pkcs1v2 t-rsa-pss t-rsa-15 t-rsa-testparm +diff --git a/tests/t-digest.c b/tests/t-digest.c +new file mode 100644 +index 00000000..3a94fa69 +--- /dev/null ++++ b/tests/t-digest.c +@@ -0,0 +1,199 @@ ++/* t-digest.c - MD regression tests ++ * Copyright (C) 2024 g10 Code GmbH ++ * ++ * This file is part of Libgcrypt. ++ * ++ * Libgcrypt is free software; you can redistribute it and/or modify ++ * it under the terms of the GNU Lesser General Public License as ++ * published by the Free Software Foundation; either version 2.1 of ++ * the License, or (at your option) any later version. ++ * ++ * Libgcrypt 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 Lesser General Public License for more details. ++ * ++ * You should have received a copy of the GNU Lesser General Public License ++ * along with this program; if not, see . ++ * SPDX-License-Identifier: LGPL-2.1+ ++ */ ++ ++#ifdef HAVE_CONFIG_H ++#include ++#endif ++#include ++#include ++#include ++#include ++#include ++ ++#define PGM "t-digest" ++ ++#include "t-common.h" ++static int in_fips_mode; ++ ++/* Mingw requires us to include windows.h after winsock2.h which is ++ included by gcrypt.h. */ ++#ifdef _WIN32 ++# include ++#endif ++ ++static void ++check_digests (void) ++{ ++ static struct { ++ int algo; ++ const char *data; ++ int datalen; ++ const char *expect; ++ int expect_failure; ++ } tv[] = { ++#undef ENABLE_THIS_AFTER_T6376_CHANGE_REVISED ++#ifdef ENABLE_THIS_AFTER_T6376_CHANGE_REVISED ++ { GCRY_MD_MD5, "abc", 3, ++ "\x90\x01\x50\x98\x3C\xD2\x4F\xB0\xD6\x96\x3F\x7D\x28\xE1\x7F\x72", 1 }, ++#endif ++ { GCRY_MD_SHA1, "abc", 3, ++ "\xA9\x99\x3E\x36\x47\x06\x81\x6A\xBA\x3E" ++ "\x25\x71\x78\x50\xC2\x6C\x9C\xD0\xD8\x9D" }, ++ { GCRY_MD_SHA256, "abc", 3, ++ "\xba\x78\x16\xbf\x8f\x01\xcf\xea\x41\x41\x40\xde\x5d\xae\x22\x23" ++ "\xb0\x03\x61\xa3\x96\x17\x7a\x9c\xb4\x10\xff\x61\xf2\x00\x15\xad" }, ++ { GCRY_MD_SHA384, "abc", 3, ++ "\xcb\x00\x75\x3f\x45\xa3\x5e\x8b\xb5\xa0\x3d\x69\x9a\xc6\x50\x07" ++ "\x27\x2c\x32\xab\x0e\xde\xd1\x63\x1a\x8b\x60\x5a\x43\xff\x5b\xed" ++ "\x80\x86\x07\x2b\xa1\xe7\xcc\x23\x58\xba\xec\xa1\x34\xc8\x25\xa7" }, ++ { GCRY_MD_SHA512, "abc", 3, ++ "\xDD\xAF\x35\xA1\x93\x61\x7A\xBA\xCC\x41\x73\x49\xAE\x20\x41\x31" ++ "\x12\xE6\xFA\x4E\x89\xA9\x7E\xA2\x0A\x9E\xEE\xE6\x4B\x55\xD3\x9A" ++ "\x21\x92\x99\x2A\x27\x4F\xC1\xA8\x36\xBA\x3C\x23\xA3\xFE\xEB\xBD" ++ "\x45\x4D\x44\x23\x64\x3C\xE8\x0E\x2A\x9A\xC9\x4F\xA5\x4C\xA4\x9F" }, ++ { GCRY_MD_SHA3_256, "abc", 3, ++ "\x3a\x98\x5d\xa7\x4f\xe2\x25\xb2\x04\x5c\x17\x2d\x6b\xd3\x90\xbd" ++ "\x85\x5f\x08\x6e\x3e\x9d\x52\x5b\x46\xbf\xe2\x45\x11\x43\x15\x32" }, ++ { GCRY_MD_SHA3_384, "abc", 3, ++ "\xec\x01\x49\x82\x88\x51\x6f\xc9\x26\x45\x9f\x58\xe2\xc6\xad\x8d" ++ "\xf9\xb4\x73\xcb\x0f\xc0\x8c\x25\x96\xda\x7c\xf0\xe4\x9b\xe4\xb2" ++ "\x98\xd8\x8c\xea\x92\x7a\xc7\xf5\x39\xf1\xed\xf2\x28\x37\x6d\x25" }, ++ { GCRY_MD_SHA3_512, "abc", 3, ++ "\xb7\x51\x85\x0b\x1a\x57\x16\x8a\x56\x93\xcd\x92\x4b\x6b\x09\x6e" ++ "\x08\xf6\x21\x82\x74\x44\xf7\x0d\x88\x4f\x5d\x02\x40\xd2\x71\x2e" ++ "\x10\xe1\x16\xe9\x19\x2a\xf3\xc9\x1a\x7e\xc5\x76\x47\xe3\x93\x40" ++ "\x57\x34\x0b\x4c\xf4\x08\xd5\xa5\x65\x92\xf8\x27\x4e\xec\x53\xf0" }, ++ { GCRY_MD_RMD160, "abc", 3, ++ "\x8e\xb2\x08\xf7\xe0\x5d\x98\x7a\x9b\x04" ++ "\x4a\x8e\x98\xc6\xb0\x87\xf1\x5a\x0b\xfc", 1 }, ++ }; ++ int tvidx; ++ unsigned char hash[64]; ++ int expectlen; ++ ++ for (tvidx=0; tvidx < DIM(tv); tvidx++) ++ { ++ gpg_err_code_t ec; ++ ++ if (verbose) ++ fprintf (stderr, "checking gcry_md_hash_buffer test %d\n", ++ tvidx); ++ ++ expectlen = gcry_md_get_algo_dlen (tv[tvidx].algo); ++ assert (expectlen != 0); ++ assert (expectlen <= sizeof hash); ++ gcry_md_hash_buffer (tv[tvidx].algo, hash, ++ tv[tvidx].data, tv[tvidx].datalen); ++ ++ ec = gcry_get_fips_service_indicator (); ++ if (ec == GPG_ERR_INV_OP) ++ { ++ /* libgcrypt is old, no support of the FIPS service indicator. */ ++ fail ("gcry_md_hash_buffer test %d unexpectedly failed to check the FIPS service indicator.\n", ++ tvidx); ++ continue; ++ } ++ ++ if (in_fips_mode && !tv[tvidx].expect_failure && ec) ++ { ++ /* Success with the FIPS service indicator == 0 expected, but != 0. */ ++ fail ("gcry_md_hash_buffer test %d unexpectedly set the indicator in FIPS mode.\n", ++ tvidx); ++ continue; ++ } ++ else if (in_fips_mode && tv[tvidx].expect_failure && !ec) ++ { ++ /* Success with the FIPS service indicator != 0 expected, but == 0. */ ++ fail ("gcry_md_hash_buffer test %d unexpectedly cleared the indicator in FIPS mode.\n", ++ tvidx); ++ continue; ++ } ++ ++ if (memcmp (hash, tv[tvidx].expect, expectlen)) ++ { ++ int i; ++ ++ fail ("gcry_md_hash_buffer test %d failed: mismatch\n", tvidx); ++ fputs ("got:", stderr); ++ for (i=0; i < expectlen; i++) ++ fprintf (stderr, " %02x", hash[i]); ++ putc ('\n', stderr); ++ } ++ } ++} ++ ++ ++int ++main (int argc, char **argv) ++{ ++ int last_argc = -1; ++ ++ if (argc) ++ { argc--; argv++; } ++ ++ while (argc && last_argc != argc) ++ { ++ last_argc = argc; ++ if (!strcmp (*argv, "--")) ++ { ++ argc--; argv++; ++ break; ++ } ++ else if (!strcmp (*argv, "--help")) ++ { ++ fputs ("usage: " PGM " [options]\n" ++ "Options:\n" ++ " --verbose print timings etc.\n" ++ " --debug flyswatter\n", ++ stdout); ++ exit (0); ++ } ++ else if (!strcmp (*argv, "--verbose")) ++ { ++ verbose++; ++ argc--; argv++; ++ } ++ else if (!strcmp (*argv, "--debug")) ++ { ++ verbose += 2; ++ debug++; ++ argc--; argv++; ++ } ++ else if (!strncmp (*argv, "--", 2)) ++ die ("unknown option '%s'", *argv); ++ } ++ ++ if (!gcry_check_version (GCRYPT_VERSION)) ++ die ("version mismatch\n"); ++ ++ if (gcry_fips_mode_active ()) ++ in_fips_mode = 1; ++ ++ if (!in_fips_mode) ++ xgcry_control ((GCRYCTL_DISABLE_SECMEM, 0)); ++ ++ xgcry_control ((GCRYCTL_INITIALIZATION_FINISHED, 0)); ++ if (debug) ++ xgcry_control ((GCRYCTL_SET_DEBUG_FLAGS, 1u , 0)); ++ ++ check_digests (); ++ ++ return !!error_count; ++} +-- +2.49.0 + diff --git a/libgcrypt-fips-tests-Add-tests-for-md_open-write-read-close-for-t-digest.patch b/libgcrypt-fips-tests-Add-tests-for-md_open-write-read-close-for-t-digest.patch new file mode 100644 index 0000000..699c1eb --- /dev/null +++ b/libgcrypt-fips-tests-Add-tests-for-md_open-write-read-close-for-t-digest.patch @@ -0,0 +1,172 @@ +From 917fc6000dfebd8854f0d1c220b85dec0dbf4676 Mon Sep 17 00:00:00 2001 +From: NIIBE Yutaka +Date: Fri, 13 Dec 2024 11:54:31 +0900 +Subject: [PATCH 03/19] fips,tests: Add tests for md_open/write/read/close for + t-digest. +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* tests/t-digest.c (check_md_o_w_r_c): New. +(main): Call check_md_o_w_r_c. + +-- + +GnuPG-bug-id: 7338 +Signed-off-by: NIIBE Yutaka +Signed-off-by: Lucas Mülling +--- + tests/t-digest.c | 133 +++++++++++++++++++++++++++++++++++++++++++++++ + 1 file changed, 133 insertions(+) + +Index: libgcrypt-1.11.0/tests/t-digest.c +=================================================================== +--- libgcrypt-1.11.0.orig/tests/t-digest.c ++++ libgcrypt-1.11.0/tests/t-digest.c +@@ -39,6 +39,138 @@ static int in_fips_mode; + #endif + + static void ++check_md_o_w_r_c (void) ++{ ++ static struct { ++ int algo; ++ const char *data; ++ int datalen; ++ const char *expect; ++ int expect_failure; ++ unsigned int flags; ++ } tv[] = { ++#if USE_MD5 ++ { GCRY_MD_MD5, "abc", 3, ++ "\x90\x01\x50\x98\x3C\xD2\x4F\xB0\xD6\x96\x3F\x7D\x28\xE1\x7F\x72", 1 }, ++ { GCRY_MD_MD5, "abc", 3, ++ "\x90\x01\x50\x98\x3C\xD2\x4F\xB0\xD6\x96\x3F\x7D\x28\xE1\x7F\x72", 1, ++ GCRY_MD_FLAG_REJECT_NON_FIPS }, ++#endif ++#if USE_SHA1 ++ { GCRY_MD_SHA1, "abc", 3, ++ "\xA9\x99\x3E\x36\x47\x06\x81\x6A\xBA\x3E" ++ "\x25\x71\x78\x50\xC2\x6C\x9C\xD0\xD8\x9D" }, ++#endif ++ { GCRY_MD_SHA256, "abc", 3, ++ "\xba\x78\x16\xbf\x8f\x01\xcf\xea\x41\x41\x40\xde\x5d\xae\x22\x23" ++ "\xb0\x03\x61\xa3\x96\x17\x7a\x9c\xb4\x10\xff\x61\xf2\x00\x15\xad" }, ++ { GCRY_MD_SHA384, "abc", 3, ++ "\xcb\x00\x75\x3f\x45\xa3\x5e\x8b\xb5\xa0\x3d\x69\x9a\xc6\x50\x07" ++ "\x27\x2c\x32\xab\x0e\xde\xd1\x63\x1a\x8b\x60\x5a\x43\xff\x5b\xed" ++ "\x80\x86\x07\x2b\xa1\xe7\xcc\x23\x58\xba\xec\xa1\x34\xc8\x25\xa7" }, ++ { GCRY_MD_SHA512, "abc", 3, ++ "\xDD\xAF\x35\xA1\x93\x61\x7A\xBA\xCC\x41\x73\x49\xAE\x20\x41\x31" ++ "\x12\xE6\xFA\x4E\x89\xA9\x7E\xA2\x0A\x9E\xEE\xE6\x4B\x55\xD3\x9A" ++ "\x21\x92\x99\x2A\x27\x4F\xC1\xA8\x36\xBA\x3C\x23\xA3\xFE\xEB\xBD" ++ "\x45\x4D\x44\x23\x64\x3C\xE8\x0E\x2A\x9A\xC9\x4F\xA5\x4C\xA4\x9F" }, ++ { GCRY_MD_SHA3_256, "abc", 3, ++ "\x3a\x98\x5d\xa7\x4f\xe2\x25\xb2\x04\x5c\x17\x2d\x6b\xd3\x90\xbd" ++ "\x85\x5f\x08\x6e\x3e\x9d\x52\x5b\x46\xbf\xe2\x45\x11\x43\x15\x32" }, ++ { GCRY_MD_SHA3_384, "abc", 3, ++ "\xec\x01\x49\x82\x88\x51\x6f\xc9\x26\x45\x9f\x58\xe2\xc6\xad\x8d" ++ "\xf9\xb4\x73\xcb\x0f\xc0\x8c\x25\x96\xda\x7c\xf0\xe4\x9b\xe4\xb2" ++ "\x98\xd8\x8c\xea\x92\x7a\xc7\xf5\x39\xf1\xed\xf2\x28\x37\x6d\x25" }, ++ { GCRY_MD_SHA3_512, "abc", 3, ++ "\xb7\x51\x85\x0b\x1a\x57\x16\x8a\x56\x93\xcd\x92\x4b\x6b\x09\x6e" ++ "\x08\xf6\x21\x82\x74\x44\xf7\x0d\x88\x4f\x5d\x02\x40\xd2\x71\x2e" ++ "\x10\xe1\x16\xe9\x19\x2a\xf3\xc9\x1a\x7e\xc5\x76\x47\xe3\x93\x40" ++ "\x57\x34\x0b\x4c\xf4\x08\xd5\xa5\x65\x92\xf8\x27\x4e\xec\x53\xf0" } ++#if USE_RMD160 ++ , ++ { GCRY_MD_RMD160, "abc", 3, ++ "\x8e\xb2\x08\xf7\xe0\x5d\x98\x7a\x9b\x04" ++ "\x4a\x8e\x98\xc6\xb0\x87\xf1\x5a\x0b\xfc", 1 } ++#endif ++ }; ++ int tvidx; ++ unsigned char *hash; ++ int expectlen; ++ gpg_error_t err; ++ ++ for (tvidx=0; tvidx < DIM(tv); tvidx++) ++ { ++ gpg_err_code_t ec; ++ gcry_md_hd_t h; ++ ++ if (verbose) ++ fprintf (stderr, "checking gcry_md_open test %d\n", ++ tvidx); ++ ++ expectlen = gcry_md_get_algo_dlen (tv[tvidx].algo); ++ assert (expectlen != 0); ++ err = gcry_md_open (&h, tv[tvidx].algo, tv[tvidx].flags); ++ if (err) ++ { ++ if (in_fips_mode && (tv[tvidx].flags & GCRY_MD_FLAG_REJECT_NON_FIPS) ++ && tv[tvidx].expect_failure) ++ /* Here, an error is expected */ ++ ; ++ else ++ fail ("gcry_md_open test %d unexpectedly failed: %s\n", ++ tvidx, gpg_strerror (err)); ++ continue; ++ } ++ else ++ { ++ if (in_fips_mode && (tv[tvidx].flags & GCRY_MD_FLAG_REJECT_NON_FIPS) ++ && tv[tvidx].expect_failure) ++ /* This case, an error is expected, but we observed success */ ++ fail ("gcry_md_open test %d unexpectedly succeeded\n", tvidx); ++ } ++ ++ ++ ec = gcry_get_fips_service_indicator (); ++ if (ec == GPG_ERR_INV_OP) ++ { ++ /* libgcrypt is old, no support of the FIPS service indicator. */ ++ fail ("gcry_md_open test %d unexpectedly failed to check the FIPS service indicator.\n", ++ tvidx); ++ continue; ++ } ++ ++ if (in_fips_mode && !tv[tvidx].expect_failure && ec) ++ { ++ /* Success with the FIPS service indicator == 0 expected, but != 0. */ ++ fail ("gcry_md_open test %d unexpectedly set the indicator in FIPS mode.\n", ++ tvidx); ++ continue; ++ } ++ else if (in_fips_mode && tv[tvidx].expect_failure && !ec) ++ { ++ /* Success with the FIPS service indicator != 0 expected, but == 0. */ ++ fail ("gcry_md_open test %d unexpectedly cleared the indicator in FIPS mode.\n", ++ tvidx); ++ continue; ++ } ++ ++ gcry_md_write (h, tv[tvidx].data, tv[tvidx].datalen); ++ hash = gcry_md_read (h, tv[tvidx].algo); ++ if (memcmp (hash, tv[tvidx].expect, expectlen)) ++ { ++ int i; ++ ++ fail ("gcry_md_open test %d failed: mismatch\n", tvidx); ++ fputs ("got:", stderr); ++ for (i=0; i < expectlen; i++) ++ fprintf (stderr, " %02x", hash[i]); ++ putc ('\n', stderr); ++ } ++ ++ gcry_md_close (h); ++ } ++} ++ ++static void + check_digests (void) + { + static struct { +@@ -194,6 +326,7 @@ main (int argc, char **argv) + xgcry_control ((GCRYCTL_SET_DEBUG_FLAGS, 1u , 0)); + + check_digests (); ++ check_md_o_w_r_c (); + + return !!error_count; + } diff --git a/libgcrypt-jitterentropy-3.4.0.patch b/libgcrypt-jitterentropy-3.4.0.patch new file mode 100644 index 0000000..dbb77ba --- /dev/null +++ b/libgcrypt-jitterentropy-3.4.0.patch @@ -0,0 +1,618 @@ +Index: libgcrypt-1.10.0/random/jitterentropy-base.c +=================================================================== +--- libgcrypt-1.10.0.orig/random/jitterentropy-base.c ++++ libgcrypt-1.10.0/random/jitterentropy-base.c +@@ -42,7 +42,7 @@ + * require consumer to be updated (as long as this number + * is zero, the API is not considered stable and can + * change without a bump of the major version) */ +-#define MINVERSION 3 /* API compatible, ABI may change, functional ++#define MINVERSION 4 /* API compatible, ABI may change, functional + * enhancements only, consumer can be left unchanged if + * enhancements are not considered */ + #define PATCHLEVEL 0 /* API / ABI compatible, no functional changes, no +@@ -200,29 +200,38 @@ ssize_t jent_read_entropy(struct rand_da + tocopy = (DATA_SIZE_BITS / 8); + else + tocopy = len; +- memcpy(p, &ec->data, tocopy); ++ ++ jent_read_random_block(ec, p, tocopy); + + len -= tocopy; + p += tocopy; + } + + /* +- * To be on the safe side, we generate one more round of entropy +- * which we do not give out to the caller. That round shall ensure +- * that in case the calling application crashes, memory dumps, pages +- * out, or due to the CPU Jitter RNG lingering in memory for long +- * time without being moved and an attacker cracks the application, +- * all he reads in the entropy pool is a value that is NEVER EVER +- * being used for anything. Thus, he does NOT see the previous value +- * that was returned to the caller for cryptographic purposes. ++ * Enhanced backtracking support: At this point, the hash state ++ * contains the digest of the previous Jitter RNG collection round ++ * which is inserted there by jent_read_random_block with the SHA ++ * update operation. At the current code location we completed ++ * one request for a caller and we do not know how long it will ++ * take until a new request is sent to us. To guarantee enhanced ++ * backtracking resistance at this point (i.e. ensure that an attacker ++ * cannot obtain information about prior random numbers we generated), ++ * but still stirring the hash state with old data the Jitter RNG ++ * obtains a new message digest from its state and re-inserts it. ++ * After this operation, the Jitter RNG state is still stirred with ++ * the old data, but an attacker who gets access to the memory after ++ * this point cannot deduce the random numbers produced by the ++ * Jitter RNG prior to this point. + */ + /* +- * If we use secured memory, do not use that precaution as the secure +- * memory protects the entropy pool. Moreover, note that using this +- * call reduces the speed of the RNG by up to half ++ * If we use secured memory, where backtracking support may not be ++ * needed because the state is protected in a different method, ++ * it is permissible to drop this support. But strongly weigh the ++ * pros and cons considering that the SHA3 operation is not that ++ * expensive. + */ + #ifndef JENT_CPU_JITTERENTROPY_SECURE_MEMORY +- jent_random_data(ec); ++ jent_read_random_block(ec, NULL, 0); + #endif + + err: +@@ -379,6 +388,7 @@ static struct rand_data + *jent_entropy_collector_alloc_internal(unsigned int osr, unsigned int flags) + { + struct rand_data *entropy_collector; ++ uint32_t memsize = 0; + + /* + * Requesting disabling and forcing of internal timer +@@ -405,7 +415,7 @@ static struct rand_data + return NULL; + + if (!(flags & JENT_DISABLE_MEMORY_ACCESS)) { +- uint32_t memsize = jent_memsize(flags); ++ memsize = jent_memsize(flags); + + entropy_collector->mem = _gcry_calloc (1, memsize); + +@@ -431,13 +441,19 @@ static struct rand_data + entropy_collector->memaccessloops = JENT_MEMORY_ACCESSLOOPS; + } + ++ if (sha3_alloc(&entropy_collector->hash_state)) ++ goto err; ++ ++ /* Initialize the hash state */ ++ sha3_256_init(entropy_collector->hash_state); ++ + /* verify and set the oversampling rate */ + if (osr < JENT_MIN_OSR) + osr = JENT_MIN_OSR; + entropy_collector->osr = osr; + entropy_collector->flags = flags; + +- if (jent_fips_enabled() || (flags & JENT_FORCE_FIPS)) ++ if ((flags & JENT_FORCE_FIPS) || jent_fips_enabled()) + entropy_collector->fips_enabled = 1; + + /* Initialize the APT */ +@@ -469,7 +485,7 @@ static struct rand_data + + err: + if (entropy_collector->mem != NULL) +- jent_zfree(entropy_collector->mem, JENT_MEMORY_SIZE); ++ jent_zfree(entropy_collector->mem, memsize); + jent_zfree(entropy_collector, sizeof(struct rand_data)); + return NULL; + } +@@ -511,6 +527,7 @@ JENT_PRIVATE_STATIC + void jent_entropy_collector_free(struct rand_data *entropy_collector) + { + if (entropy_collector != NULL) { ++ sha3_dealloc(entropy_collector->hash_state); + jent_notime_disable(entropy_collector); + if (entropy_collector->mem != NULL) { + jent_zfree(entropy_collector->mem, +@@ -664,6 +681,7 @@ static inline int jent_entropy_init_comm + int ret; + + jent_notime_block_switch(); ++ jent_health_cb_block_switch(); + + if (sha3_tester()) + return EHASH; +@@ -710,6 +728,8 @@ int jent_entropy_init_ex(unsigned int os + if (ret) + return ret; + ++ ret = ENOTIME; ++ + /* Test without internal timer unless caller does not want it */ + if (!(flags & JENT_FORCE_INTERNAL_TIMER)) + ret = jent_time_entropy_init(osr, +@@ -732,3 +752,9 @@ int jent_entropy_switch_notime_impl(stru + return jent_notime_switch(new_thread); + } + #endif ++ ++JENT_PRIVATE_STATIC ++int jent_set_fips_failure_callback(jent_fips_failure_cb cb) ++{ ++ return jent_set_fips_failure_callback_internal(cb); ++} +Index: libgcrypt-1.10.0/random/jitterentropy-gcd.c +=================================================================== +--- libgcrypt-1.10.0.orig/random/jitterentropy-gcd.c ++++ libgcrypt-1.10.0/random/jitterentropy-gcd.c +@@ -113,12 +113,8 @@ int jent_gcd_analyze(uint64_t *delta_his + goto out; + } + +- /* +- * Ensure that we have variations in the time stamp below 100 for at +- * least 10% of all checks -- on some platforms, the counter increments +- * in multiples of 100, but not always +- */ +- if (running_gcd >= 100) { ++ /* Set a sensible maximum value. */ ++ if (running_gcd >= UINT32_MAX / 2) { + ret = ECOARSETIME; + goto out; + } +Index: libgcrypt-1.10.0/random/jitterentropy-health.c +=================================================================== +--- libgcrypt-1.10.0.orig/random/jitterentropy-health.c ++++ libgcrypt-1.10.0/random/jitterentropy-health.c +@@ -19,9 +19,24 @@ + * DAMAGE. + */ + +-#include "jitterentropy.h" + #include "jitterentropy-health.h" + ++static jent_fips_failure_cb fips_cb = NULL; ++static int jent_health_cb_switch_blocked = 0; ++ ++void jent_health_cb_block_switch(void) ++{ ++ jent_health_cb_switch_blocked = 1; ++} ++ ++int jent_set_fips_failure_callback_internal(jent_fips_failure_cb cb) ++{ ++ if (jent_health_cb_switch_blocked) ++ return -EAGAIN; ++ fips_cb = cb; ++ return 0; ++} ++ + /*************************************************************************** + * Lag Predictor Test + * +@@ -434,5 +449,9 @@ unsigned int jent_health_failure(struct + if (!ec->fips_enabled) + return 0; + ++ if (fips_cb && ec->health_failure) { ++ fips_cb(ec, ec->health_failure); ++ } ++ + return ec->health_failure; + } +Index: libgcrypt-1.10.0/random/jitterentropy-health.h +=================================================================== +--- libgcrypt-1.10.0.orig/random/jitterentropy-health.h ++++ libgcrypt-1.10.0/random/jitterentropy-health.h +@@ -20,11 +20,16 @@ + #ifndef JITTERENTROPY_HEALTH_H + #define JITTERENTROPY_HEALTH_H + ++#include "jitterentropy.h" ++ + #ifdef __cplusplus + extern "C" + { + #endif + ++void jent_health_cb_block_switch(void); ++int jent_set_fips_failure_callback_internal(jent_fips_failure_cb cb); ++ + static inline uint64_t jent_delta(uint64_t prev, uint64_t next) + { + return (next - prev); +Index: libgcrypt-1.10.0/random/jitterentropy-noise.c +=================================================================== +--- libgcrypt-1.10.0.orig/random/jitterentropy-noise.c ++++ libgcrypt-1.10.0/random/jitterentropy-noise.c +@@ -33,7 +33,7 @@ + * Update of the loop count used for the next round of + * an entropy collection. + * +- * @ec [in] entropy collector struct -- may be NULL ++ * @ec [in] entropy collector struct + * @bits [in] is the number of low bits of the timer to consider + * @min [in] is the number of bits we shift the timer value to the right at + * the end to make sure we have a guaranteed minimum value +@@ -61,16 +61,13 @@ static uint64_t jent_loop_shuffle(struct + * Mix the current state of the random number into the shuffle + * calculation to balance that shuffle a bit more. + */ +- if (ec) { +- jent_get_nstime_internal(ec, &time); +- time ^= ec->data[0]; +- } ++ jent_get_nstime_internal(ec, &time); + + /* + * We fold the time value as much as possible to ensure that as many + * bits of the time stamp are included as possible. + */ +- for (i = 0; ((DATA_SIZE_BITS + bits - 1) / bits) > i; i++) { ++ for (i = 0; (((sizeof(time) << 3) + bits - 1) / bits) > i; i++) { + shuffle ^= time & mask; + time = time >> bits; + } +@@ -91,11 +88,11 @@ static uint64_t jent_loop_shuffle(struct + * This function injects the individual bits of the time value into the + * entropy pool using a hash. + * +- * @ec [in] entropy collector struct -- may be NULL +- * @time [in] time stamp to be injected ++ * @ec [in] entropy collector struct ++ * @time [in] time delta to be injected + * @loop_cnt [in] if a value not equal to 0 is set, use the given value as + * number of loops to perform the hash operation +- * @stuck [in] Is the time stamp identified as stuck? ++ * @stuck [in] Is the time delta identified as stuck? + * + * Output: + * updated hash context +@@ -104,17 +101,19 @@ static void jent_hash_time(struct rand_d + uint64_t loop_cnt, unsigned int stuck) + { + HASH_CTX_ON_STACK(ctx); +- uint8_t itermediary[SHA3_256_SIZE_DIGEST]; ++ uint8_t intermediary[SHA3_256_SIZE_DIGEST]; + uint64_t j = 0; +- uint64_t hash_loop_cnt; + #define MAX_HASH_LOOP 3 + #define MIN_HASH_LOOP 0 + + /* Ensure that macros cannot overflow jent_loop_shuffle() */ + BUILD_BUG_ON((MAX_HASH_LOOP + MIN_HASH_LOOP) > 63); +- hash_loop_cnt = ++ uint64_t hash_loop_cnt = + jent_loop_shuffle(ec, MAX_HASH_LOOP, MIN_HASH_LOOP); + ++ /* Use the memset to shut up valgrind */ ++ memset(intermediary, 0, sizeof(intermediary)); ++ + sha3_256_init(&ctx); + + /* +@@ -125,35 +124,54 @@ static void jent_hash_time(struct rand_d + hash_loop_cnt = loop_cnt; + + /* +- * This loop basically slows down the SHA-3 operation depending +- * on the hash_loop_cnt. Each iteration of the loop generates the +- * same result. ++ * This loop fills a buffer which is injected into the entropy pool. ++ * The main reason for this loop is to execute something over which we ++ * can perform a timing measurement. The injection of the resulting ++ * data into the pool is performed to ensure the result is used and ++ * the compiler cannot optimize the loop away in case the result is not ++ * used at all. Yet that data is considered "additional information" ++ * considering the terminology from SP800-90A without any entropy. ++ * ++ * Note, it does not matter which or how much data you inject, we are ++ * interested in one Keccack1600 compression operation performed with ++ * the sha3_final. + */ + for (j = 0; j < hash_loop_cnt; j++) { +- sha3_update(&ctx, ec->data, SHA3_256_SIZE_DIGEST); +- sha3_update(&ctx, (uint8_t *)&time, sizeof(uint64_t)); ++ sha3_update(&ctx, intermediary, sizeof(intermediary)); ++ sha3_update(&ctx, (uint8_t *)&ec->rct_count, ++ sizeof(ec->rct_count)); ++ sha3_update(&ctx, (uint8_t *)&ec->apt_cutoff, ++ sizeof(ec->apt_cutoff)); ++ sha3_update(&ctx, (uint8_t *)&ec->apt_observations, ++ sizeof(ec->apt_observations)); ++ sha3_update(&ctx, (uint8_t *)&ec->apt_count, ++ sizeof(ec->apt_count)); ++ sha3_update(&ctx,(uint8_t *) &ec->apt_base, ++ sizeof(ec->apt_base)); + sha3_update(&ctx, (uint8_t *)&j, sizeof(uint64_t)); ++ sha3_final(&ctx, intermediary); ++ } + +- /* +- * If the time stamp is stuck, do not finally insert the value +- * into the entropy pool. Although this operation should not do +- * any harm even when the time stamp has no entropy, SP800-90B +- * requires that any conditioning operation to have an identical +- * amount of input data according to section 3.1.5. +- */ ++ /* ++ * Inject the data from the previous loop into the pool. This data is ++ * not considered to contain any entropy, but it stirs the pool a bit. ++ */ ++ sha3_update(ec->hash_state, intermediary, sizeof(intermediary)); + +- /* +- * The sha3_final operations re-initialize the context for the +- * next loop iteration. +- */ +- if (stuck || (j < hash_loop_cnt - 1)) +- sha3_final(&ctx, itermediary); +- else +- sha3_final(&ctx, ec->data); +- } ++ /* ++ * Insert the time stamp into the hash context representing the pool. ++ * ++ * If the time stamp is stuck, do not finally insert the value into the ++ * entropy pool. Although this operation should not do any harm even ++ * when the time stamp has no entropy, SP800-90B requires that any ++ * conditioning operation to have an identical amount of input data ++ * according to section 3.1.5. ++ */ ++ if (!stuck) ++ sha3_update(ec->hash_state, (uint8_t *)&time, sizeof(uint64_t)); + + jent_memset_secure(&ctx, SHA_MAX_CTX_SIZE); +- jent_memset_secure(itermediary, sizeof(itermediary)); ++ jent_memset_secure(intermediary, sizeof(intermediary)); + } + + #define MAX_ACC_LOOP_BIT 7 +@@ -184,13 +202,12 @@ static inline uint32_t xoshiro128starsta + + static void jent_memaccess(struct rand_data *ec, uint64_t loop_cnt) + { +- uint64_t i = 0; ++ uint64_t i = 0, time = 0; + union { + uint32_t u[4]; + uint8_t b[sizeof(uint32_t) * 4]; + } prngState = { .u = {0x8e93eec0, 0xce65608a, 0xa8d46b46, 0xe83cef69} }; + uint32_t addressMask; +- uint64_t acc_loop_cnt; + + if (NULL == ec || NULL == ec->mem) + return; +@@ -199,7 +216,7 @@ static void jent_memaccess(struct rand_d + + /* Ensure that macros cannot overflow jent_loop_shuffle() */ + BUILD_BUG_ON((MAX_ACC_LOOP_BIT + MIN_ACC_LOOP_BIT) > 63); +- acc_loop_cnt = ++ uint64_t acc_loop_cnt = + jent_loop_shuffle(ec, MAX_ACC_LOOP_BIT, MIN_ACC_LOOP_BIT); + + /* +@@ -213,8 +230,10 @@ static void jent_memaccess(struct rand_d + * "per-update: timing, it gets you mostly independent "per-update" + * timing, so we can now benefit from the Central Limit Theorem! + */ +- for (i = 0; i < sizeof(prngState); i++) +- prngState.b[i] ^= ec->data[i]; ++ for (i = 0; i < sizeof(prngState); i++) { ++ jent_get_nstime_internal(ec, &time); ++ prngState.b[i] ^= (uint8_t)(time & 0xff); ++ } + + /* + * testing purposes -- allow test app to set the counter, not +@@ -358,21 +377,21 @@ unsigned int jent_measure_jitter(struct + + /** + * Generator of one 256 bit random number +- * Function fills rand_data->data ++ * Function fills rand_data->hash_state + * + * @ec [in] Reference to entropy collector + */ + void jent_random_data(struct rand_data *ec) + { +- unsigned int k = 0, safety_factor = ENTROPY_SAFETY_FACTOR; ++ unsigned int k = 0, safety_factor = 0; + +- if (!ec->fips_enabled) +- safety_factor = 0; ++ if (ec->fips_enabled) ++ safety_factor = ENTROPY_SAFETY_FACTOR; + + /* priming of the ->prev_time value */ + jent_measure_jitter(ec, 0, NULL); + +- while (1) { ++ while (!jent_health_failure(ec)) { + /* If a stuck measurement is received, repeat measurement */ + if (jent_measure_jitter(ec, 0, NULL)) + continue; +@@ -385,3 +404,22 @@ void jent_random_data(struct rand_data * + break; + } + } ++ ++void jent_read_random_block(struct rand_data *ec, char *dst, size_t dst_len) ++{ ++ uint8_t jent_block[SHA3_256_SIZE_DIGEST]; ++ ++ BUILD_BUG_ON(SHA3_256_SIZE_DIGEST != (DATA_SIZE_BITS / 8)); ++ ++ /* The final operation automatically re-initializes the ->hash_state */ ++ sha3_final(ec->hash_state, jent_block); ++ if (dst_len) ++ memcpy(dst, jent_block, dst_len); ++ ++ /* ++ * Stir the new state with the data from the old state - the digest ++ * of the old data is not considered to have entropy. ++ */ ++ sha3_update(ec->hash_state, jent_block, sizeof(jent_block)); ++ jent_memset_secure(jent_block, sizeof(jent_block)); ++} +Index: libgcrypt-1.10.0/random/jitterentropy-noise.h +=================================================================== +--- libgcrypt-1.10.0.orig/random/jitterentropy-noise.h ++++ libgcrypt-1.10.0/random/jitterentropy-noise.h +@@ -31,6 +31,7 @@ unsigned int jent_measure_jitter(struct + uint64_t loop_cnt, + uint64_t *ret_current_delta); + void jent_random_data(struct rand_data *ec); ++void jent_read_random_block(struct rand_data *ec, char *dst, size_t dst_len); + + #ifdef __cplusplus + } +Index: libgcrypt-1.10.0/random/jitterentropy-sha3.c +=================================================================== +--- libgcrypt-1.10.0.orig/random/jitterentropy-sha3.c ++++ libgcrypt-1.10.0/random/jitterentropy-sha3.c +@@ -19,6 +19,7 @@ + */ + + #include "jitterentropy-sha3.h" ++#include "jitterentropy.h" + + /*************************************************************************** + * Message Digest Implementation +@@ -380,3 +381,23 @@ int sha3_tester(void) + + return 0; + } ++ ++int sha3_alloc(void **hash_state) ++{ ++ struct sha_ctx *tmp; ++ ++ tmp = jent_zalloc(SHA_MAX_CTX_SIZE); ++ if (!tmp) ++ return 1; ++ ++ *hash_state = tmp; ++ ++ return 0; ++} ++ ++void sha3_dealloc(void *hash_state) ++{ ++ struct sha_ctx *ctx = (struct sha_ctx *)hash_state; ++ ++ jent_zfree(ctx, SHA_MAX_CTX_SIZE); ++} +Index: libgcrypt-1.10.0/random/jitterentropy-sha3.h +=================================================================== +--- libgcrypt-1.10.0.orig/random/jitterentropy-sha3.h ++++ libgcrypt-1.10.0/random/jitterentropy-sha3.h +@@ -47,6 +47,8 @@ struct sha_ctx { + void sha3_256_init(struct sha_ctx *ctx); + void sha3_update(struct sha_ctx *ctx, const uint8_t *in, size_t inlen); + void sha3_final(struct sha_ctx *ctx, uint8_t *digest); ++int sha3_alloc(void **hash_state); ++void sha3_dealloc(void *hash_state); + int sha3_tester(void); + + #ifdef __cplusplus +Index: libgcrypt-1.10.0/random/jitterentropy-timer.c +=================================================================== +--- libgcrypt-1.10.0.orig/random/jitterentropy-timer.c ++++ libgcrypt-1.10.0/random/jitterentropy-timer.c +@@ -202,8 +202,8 @@ int jent_notime_enable(struct rand_data + if (jent_force_internal_timer || (flags & JENT_FORCE_INTERNAL_TIMER)) { + /* Self test not run yet */ + if (!jent_force_internal_timer && +- jent_time_entropy_init(flags | JENT_FORCE_INTERNAL_TIMER, +- ec->osr)) ++ jent_time_entropy_init(ec->osr, ++ flags | JENT_FORCE_INTERNAL_TIMER)) + return EHEALTH; + + ec->enable_notime = 1; +Index: libgcrypt-1.10.0/random/jitterentropy.h +=================================================================== +--- libgcrypt-1.10.0.orig/random/jitterentropy.h ++++ libgcrypt-1.10.0/random/jitterentropy.h +@@ -49,7 +49,7 @@ + ***************************************************************************/ + + /* +- * Enable timer-less timer support ++ * Enable timer-less timer support with JENT_CONF_ENABLE_INTERNAL_TIMER + * + * In case the hardware is identified to not provide a high-resolution time + * stamp, this option enables a built-in high-resolution time stamp mechanism. +@@ -166,7 +166,7 @@ struct rand_data + * of the RNG are marked as SENSITIVE. A user must not + * access that information while the RNG executes its loops to + * calculate the next random value. */ +- uint8_t data[SHA3_256_SIZE_DIGEST]; /* SENSITIVE Actual random number */ ++ void *hash_state; /* SENSITIVE hash state entropy pool */ + uint64_t prev_time; /* SENSITIVE Previous time stamp */ + #define DATA_SIZE_BITS (SHA3_256_SIZE_DIGEST_BITS) + +@@ -378,28 +378,34 @@ int jent_entropy_init(void); + JENT_PRIVATE_STATIC + int jent_entropy_init_ex(unsigned int osr, unsigned int flags); + ++/* ++ * Set a callback to run on health failure in FIPS mode. ++ * This function will take an action determined by the caller. ++ */ ++typedef void (*jent_fips_failure_cb)(struct rand_data *ec, ++ unsigned int health_failure); ++JENT_PRIVATE_STATIC ++int jent_set_fips_failure_callback(jent_fips_failure_cb cb); ++ + /* return version number of core library */ + JENT_PRIVATE_STATIC + unsigned int jent_version(void); + +-#ifdef JENT_CONF_ENABLE_INTERNAL_TIMER + /* Set a different thread handling logic for the notimer support */ + JENT_PRIVATE_STATIC + int jent_entropy_switch_notime_impl(struct jent_notime_thread *new_thread); +-#endif + + /* -- END of Main interface functions -- */ + + /* -- BEGIN timer-less threading support functions to prevent code dupes -- */ + +-struct jent_notime_ctx { + #ifdef JENT_CONF_ENABLE_INTERNAL_TIMER ++ ++struct jent_notime_ctx { + pthread_attr_t notime_pthread_attr; /* pthreads library */ + pthread_t notime_thread_id; /* pthreads thread ID */ +-#endif + }; + +-#ifdef JENT_CONF_ENABLE_INTERNAL_TIMER + + JENT_PRIVATE_STATIC + int jent_notime_init(void **ctx); +Index: libgcrypt-1.10.0/random/jitterentropy-base-user.h +=================================================================== +--- libgcrypt-1.10.0.orig/random/jitterentropy-base-user.h ++++ libgcrypt-1.10.0/random/jitterentropy-base-user.h +@@ -213,12 +213,12 @@ static inline void jent_get_cachesize(lo + ext = strstr(buf, "K"); + if (ext) { + shift = 10; +- ext = '\0'; ++ *ext = '\0'; + } else { + ext = strstr(buf, "M"); + if (ext) { + shift = 20; +- ext = '\0'; ++ *ext = '\0'; + } + } + diff --git a/libgcrypt-md-Fix-gcry_md_algo_info-to-mark-reject-under-FIPS-mode.patch b/libgcrypt-md-Fix-gcry_md_algo_info-to-mark-reject-under-FIPS-mode.patch new file mode 100644 index 0000000..25f5904 --- /dev/null +++ b/libgcrypt-md-Fix-gcry_md_algo_info-to-mark-reject-under-FIPS-mode.patch @@ -0,0 +1,82 @@ +From 2f17a98a80b155e750ab77d4703e33612e545d58 Mon Sep 17 00:00:00 2001 +From: NIIBE Yutaka +Date: Tue, 25 Feb 2025 16:27:25 +0900 +Subject: [PATCH 1/4] md: Fix gcry_md_algo_info to mark/reject under FIPS mode. +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* cipher/md.c (check_digest_algo): Fix for marking non-compliance. +* src/visibility.c (gcry_md_algo_info): Add check with +fips_is_operational. + +-- + +GnuPG-bug-id: 7338 +Signed-off-by: NIIBE Yutaka +Signed-off-by: Lucas Mülling +--- + cipher/md.c | 26 ++++++++++++++++++++++---- + src/visibility.c | 3 +++ + 2 files changed, 25 insertions(+), 4 deletions(-) + +diff --git a/cipher/md.c b/cipher/md.c +index f600e7bb..caf33afc 100644 +--- a/cipher/md.c ++++ b/cipher/md.c +@@ -436,16 +436,34 @@ _gcry_md_algo_name (int algorithm) + + + static gcry_err_code_t +-check_digest_algo (int algorithm) ++check_digest_algo (int algo) + { + const gcry_md_spec_t *spec; ++ int reject = 0; + +- spec = spec_from_algo (algorithm); +- if (spec && !spec->flags.disabled && (spec->flags.fips || !fips_mode ())) ++ spec = spec_from_algo (algo); ++ if (!spec) ++ return GPG_ERR_DIGEST_ALGO; ++ ++ if (spec->flags.disabled) ++ return GPG_ERR_DIGEST_ALGO; ++ ++ if (!fips_mode ()) + return 0; + +- return GPG_ERR_DIGEST_ALGO; ++ if (spec->flags.fips) ++ return 0; ++ ++ if (algo == GCRY_MD_MD5) ++ reject = fips_check_rejection (GCRY_FIPS_FLAG_REJECT_MD_MD5); ++ else ++ reject = fips_check_rejection (GCRY_FIPS_FLAG_REJECT_MD_OTHERS); ++ ++ if (reject) ++ return GPG_ERR_DIGEST_ALGO; + ++ fips_service_indicator_mark_non_compliant (); ++ return 0; + } + + +diff --git a/src/visibility.c b/src/visibility.c +index e02d6cfe..4134446a 100644 +--- a/src/visibility.c ++++ b/src/visibility.c +@@ -1373,6 +1373,9 @@ gcry_md_info (gcry_md_hd_t h, int what, void *buffer, size_t *nbytes) + gcry_error_t + gcry_md_algo_info (int algo, int what, void *buffer, size_t *nbytes) + { ++ if (!fips_is_operational ()) ++ return gpg_error (fips_not_operational ()); ++ fips_service_indicator_init (); + return gpg_error (_gcry_md_algo_info (algo, what, buffer, nbytes)); + } + +-- +2.49.0 + diff --git a/libgcrypt-md-Make-SHA-1-non-FIPS-internally-for-1.12-API.patch b/libgcrypt-md-Make-SHA-1-non-FIPS-internally-for-1.12-API.patch new file mode 100644 index 0000000..bbea9bb --- /dev/null +++ b/libgcrypt-md-Make-SHA-1-non-FIPS-internally-for-1.12-API.patch @@ -0,0 +1,154 @@ +From 4ee91a94bcdad32aed4364d09e3daf8841fa579f Mon Sep 17 00:00:00 2001 +From: NIIBE Yutaka +Date: Tue, 11 Mar 2025 14:01:11 +0900 +Subject: [PATCH 11/14] md: Make SHA-1 non-FIPS internally for 1.12 API. +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* src/gcrypt.h.in (GCRY_FIPS_FLAG_REJECT_MD_SHA1): New. +* cipher/md.c (check_digest_algo_spec, _gcry_md_open, md_enable) +(_gcry_md_enable, md_copy): Care about SHA1. +* cipher/sha1.c (_gcry_digest_spec_sha1): Make SHA1 non-FIPS. +* tests/t-fips-service-ind.c (check_mac_o_w_r_c): SHA1 is non-FIPS. +(check_md_o_w_r_c, check_hash_buffer, check_hash_buffers): Likewise. +(main): Add GCRY_FIPS_FLAG_REJECT_MD_SHA1 for gcry_control. + +-- + +For 1.10 ABI (which 1.11 keeps), SHA1 is an approved hash function +(while its use in public key crypto is non-FIPS). + +For 1.12 API, the dynamic FIPS service indicator is going to be added. + +In 1.11.1 implementation, we are trying to support 1.12 dynamic FIPS +service indicator in forward-compatible way. For this purpose, +internally, it's specified as non-FIPS in _gcry_digest_spec_sha1. + +Note that update for tests/basic.c and tests/pkcs1v2.c are needed to +use SHA256 (or one of approved hash functions) in 1.12, so that test +program can be a reference for programmers. + +Co-authored-by: Lucas Mulling +Signed-off-by: NIIBE Yutaka +Signed-off-by: Lucas Mülling +--- + cipher/md.c | 10 ++++++++++ + cipher/sha1.c | 2 +- + src/gcrypt.h.in | 1 + + tests/t-fips-service-ind.c | 9 +++++---- + 4 files changed, 17 insertions(+), 5 deletions(-) + +Index: libgcrypt-1.11.0/cipher/md.c +=================================================================== +--- libgcrypt-1.11.0.orig/cipher/md.c ++++ libgcrypt-1.11.0/cipher/md.c +@@ -451,6 +451,8 @@ check_digest_algo_spec (int algo, const + + if (algo == GCRY_MD_MD5) + reject = fips_check_rejection (GCRY_FIPS_FLAG_REJECT_MD_MD5); ++ else if (algo == GCRY_MD_SHA1) ++ reject = fips_check_rejection (GCRY_FIPS_FLAG_REJECT_MD_SHA1); + else + reject = fips_check_rejection (GCRY_FIPS_FLAG_REJECT_MD_OTHERS); + +@@ -590,6 +592,8 @@ _gcry_md_open (gcry_md_hd_t *h, int algo + + if (algo == GCRY_MD_MD5) + reject = fips_check_rejection (GCRY_FIPS_FLAG_REJECT_MD_MD5); ++ else if (algo == GCRY_MD_SHA1) ++ reject = fips_check_rejection (GCRY_FIPS_FLAG_REJECT_MD_SHA1); + else + reject = fips_check_rejection (GCRY_FIPS_FLAG_REJECT_MD_OTHERS); + +@@ -625,6 +629,8 @@ md_enable (gcry_md_hd_t hd, int algorith + + if (algorithm == GCRY_MD_MD5) + reject = fips_check_rejection (GCRY_FIPS_FLAG_REJECT_MD_MD5); ++ else if (algorithm == GCRY_MD_SHA1) ++ reject = fips_check_rejection (GCRY_FIPS_FLAG_REJECT_MD_SHA1); + else + reject = fips_check_rejection (GCRY_FIPS_FLAG_REJECT_MD_OTHERS); + +@@ -703,6 +709,8 @@ _gcry_md_enable (gcry_md_hd_t hd, int al + + if (algorithm == GCRY_MD_MD5) + reject = fips_check_rejection (GCRY_FIPS_FLAG_REJECT_MD_MD5); ++ else if (algorithm == GCRY_MD_SHA1) ++ reject = fips_check_rejection (GCRY_FIPS_FLAG_REJECT_MD_SHA1); + else + reject = fips_check_rejection (GCRY_FIPS_FLAG_REJECT_MD_OTHERS); + +@@ -780,6 +788,8 @@ md_copy (gcry_md_hd_t ahd, gcry_md_hd_t + + if (spec->algo == GCRY_MD_MD5) + reject |= fips_check_rejection (GCRY_FIPS_FLAG_REJECT_MD_MD5); ++ else if (spec->algo == GCRY_MD_SHA1) ++ reject = fips_check_rejection (GCRY_FIPS_FLAG_REJECT_MD_SHA1); + else + reject |= fips_check_rejection (GCRY_FIPS_FLAG_REJECT_MD_OTHERS); + } +Index: libgcrypt-1.11.0/cipher/sha1.c +=================================================================== +--- libgcrypt-1.11.0.orig/cipher/sha1.c ++++ libgcrypt-1.11.0/cipher/sha1.c +@@ -759,7 +759,7 @@ static const gcry_md_oid_spec_t oid_spec + + const gcry_md_spec_t _gcry_digest_spec_sha1 = + { +- GCRY_MD_SHA1, {0, 1}, ++ GCRY_MD_SHA1, {0, 0}, + "SHA1", asn, DIM (asn), oid_spec_sha1, 20, + sha1_init, _gcry_md_block_write, sha1_final, sha1_read, NULL, + _gcry_sha1_hash_buffers, +Index: libgcrypt-1.11.0/src/gcrypt.h.in +=================================================================== +--- libgcrypt-1.11.0.orig/src/gcrypt.h.in ++++ libgcrypt-1.11.0/src/gcrypt.h.in +@@ -1982,6 +1982,7 @@ char *gcry_get_config (int mode, const c + #define GCRY_FIPS_FLAG_REJECT_PK_GOST_SM2 (1 << 7) + #define GCRY_FIPS_FLAG_REJECT_CIPHER_MODE (1 << 8) + /**/ ++#define GCRY_FIPS_FLAG_REJECT_MD_SHA1 (1 << 9) + #define GCRY_FIPS_FLAG_REJECT_PK_ECC_K (1 << 10) + #define GCRY_FIPS_FLAG_REJECT_PK_FLAGS (1 << 11) + +Index: libgcrypt-1.11.0/tests/t-fips-service-ind.c +=================================================================== +--- libgcrypt-1.11.0.orig/tests/t-fips-service-ind.c ++++ libgcrypt-1.11.0/tests/t-fips-service-ind.c +@@ -1107,7 +1107,7 @@ check_mac_o_w_r_c (int reject) + #if USE_SHA1 + { GCRY_MAC_HMAC_SHA1, "hmac input abc", 14, "hmac key input", 14, + "\xc9\x62\x9d\x16\x0f\xc2\xc4\xcd\x38\xac\x3a\x00\xdc\x29\x61\x03" +- "\x69\x50\xd7\x3a" }, ++ "\x69\x50\xd7\x3a", 1 }, + #endif + { GCRY_MAC_HMAC_SHA256, "hmac input abc", 14, "hmac key input", 14, + "\x6a\xda\x4d\xd5\xf3\xa7\x32\x9d\xd2\x55\xc0\x7f\xe6\x0a\x93\xb8" +@@ -1264,7 +1264,7 @@ check_md_o_w_r_c (int reject) + #if USE_SHA1 + { GCRY_MD_SHA1, "abc", 3, + "\xA9\x99\x3E\x36\x47\x06\x81\x6A\xBA\x3E" +- "\x25\x71\x78\x50\xC2\x6C\x9C\xD0\xD8\x9D" }, ++ "\x25\x71\x78\x50\xC2\x6C\x9C\xD0\xD8\x9D", 1 }, + #endif + { GCRY_MD_SHA256, "abc", 3, + "\xba\x78\x16\xbf\x8f\x01\xcf\xea\x41\x41\x40\xde\x5d\xae\x22\x23" +@@ -1389,7 +1389,7 @@ check_digests (void) + #endif + { GCRY_MD_SHA1, "abc", 3, + "\xA9\x99\x3E\x36\x47\x06\x81\x6A\xBA\x3E" +- "\x25\x71\x78\x50\xC2\x6C\x9C\xD0\xD8\x9D" }, ++ "\x25\x71\x78\x50\xC2\x6C\x9C\xD0\xD8\x9D", 1 }, + { GCRY_MD_SHA256, "abc", 3, + "\xba\x78\x16\xbf\x8f\x01\xcf\xea\x41\x41\x40\xde\x5d\xae\x22\x23" + "\xb0\x03\x61\xa3\x96\x17\x7a\x9c\xb4\x10\xff\x61\xf2\x00\x15\xad" }, +@@ -1701,6 +1701,7 @@ main (int argc, char **argv) + | GCRY_FIPS_FLAG_REJECT_CIPHER_MODE + | GCRY_FIPS_FLAG_REJECT_PK_MD + | GCRY_FIPS_FLAG_REJECT_PK_GOST_SM2 ++ | GCRY_FIPS_FLAG_REJECT_MD_SHA1 + | GCRY_FIPS_FLAG_REJECT_PK_ECC_K + | GCRY_FIPS_FLAG_REJECT_PK_FLAGS + | GCRY_FIPS_FLAG_REJECT_COMPAT110))); diff --git a/libgcrypt-md-Use-check_digest_algo_spec-in-_gcry_md_selftest.patch b/libgcrypt-md-Use-check_digest_algo_spec-in-_gcry_md_selftest.patch new file mode 100644 index 0000000..75489df --- /dev/null +++ b/libgcrypt-md-Use-check_digest_algo_spec-in-_gcry_md_selftest.patch @@ -0,0 +1,74 @@ +From ce4755d5c5500cede6d7d380fdab2d15f5d77796 Mon Sep 17 00:00:00 2001 +From: NIIBE Yutaka +Date: Wed, 26 Feb 2025 10:23:28 +0900 +Subject: [PATCH 2/4] md: Use check_digest_algo_spec in _gcry_md_selftest. +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* cipher/md.c (check_digest_algo_spec): New. +(check_digest_algo): Use check_digest_algo_spec. +(_gcry_md_selftest): Likewise. + +-- + +GnuPG-bug-id: 7338 +Signed-off-by: NIIBE Yutaka +Signed-off-by: Lucas Mülling +--- + cipher/md.c | 22 +++++++++++++--------- + 1 file changed, 13 insertions(+), 9 deletions(-) + +diff --git a/cipher/md.c b/cipher/md.c +index caf33afc..a8027e9e 100644 +--- a/cipher/md.c ++++ b/cipher/md.c +@@ -436,15 +436,10 @@ _gcry_md_algo_name (int algorithm) + + + static gcry_err_code_t +-check_digest_algo (int algo) ++check_digest_algo_spec (int algo, const gcry_md_spec_t *spec) + { +- const gcry_md_spec_t *spec; + int reject = 0; + +- spec = spec_from_algo (algo); +- if (!spec) +- return GPG_ERR_DIGEST_ALGO; +- + if (spec->flags.disabled) + return GPG_ERR_DIGEST_ALGO; + +@@ -466,6 +461,17 @@ check_digest_algo (int algo) + return 0; + } + ++static gcry_err_code_t ++check_digest_algo (int algo) ++{ ++ const gcry_md_spec_t *spec = spec_from_algo (algo); ++ ++ if (!spec) ++ return GPG_ERR_DIGEST_ALGO; ++ else ++ return check_digest_algo_spec (algo, spec); ++} ++ + + /**************** + * Open a message digest handle for use with algorithm ALGO. +@@ -1808,9 +1814,7 @@ _gcry_md_selftest (int algo, int extended, selftest_report_func_t report) + const gcry_md_spec_t *spec; + + spec = spec_from_algo (algo); +- if (spec && !spec->flags.disabled +- && (spec->flags.fips || !fips_mode ()) +- && spec->selftest) ++ if (spec && !check_digest_algo_spec (algo, spec) && spec->selftest) + ec = spec->selftest (algo, extended, report); + else + { +-- +2.49.0 + diff --git a/libgcrypt-no-deprecated-grep-alias.patch b/libgcrypt-no-deprecated-grep-alias.patch new file mode 100644 index 0000000..ba0dde8 --- /dev/null +++ b/libgcrypt-no-deprecated-grep-alias.patch @@ -0,0 +1,35 @@ +--- libgcrypt-1.10.3.orig/acinclude.m4 ++++ libgcrypt-1.10.3/acinclude.m4 +@@ -130,10 +130,10 @@ EOF + ac_nlist=conftest.nm + if AC_TRY_EVAL(NM conftest.$ac_objext \| $lt_cv_sys_global_symbol_pipe \| cut -d \' \' -f 2 \> $ac_nlist) && test -s "$ac_nlist"; then + # See whether the symbols have a leading underscore. +- if egrep '^_nm_test_func' "$ac_nlist" >/dev/null; then ++ if grep -E '^_nm_test_func' "$ac_nlist" >/dev/null; then + ac_cv_sys_symbol_underscore=yes + else +- if egrep '^nm_test_func ' "$ac_nlist" >/dev/null; then ++ if grep -E '^nm_test_func ' "$ac_nlist" >/dev/null; then + : + else + echo "configure: cannot find nm_test_func in $ac_nlist" >&AS_MESSAGE_LOG_FD +--- libgcrypt-1.10.3.orig/src/libgcrypt-config.in ++++ libgcrypt-1.10.3/src/libgcrypt-config.in +@@ -154,7 +154,7 @@ if test "$echo_cflags" = "yes"; then + + tmp="" + for i in $includes $cflags_final; do +- if echo "$tmp" | fgrep -v -- "$i" >/dev/null; then ++ if echo "$tmp" | @GREP@ -F -v -- "$i" >/dev/null; then + tmp="$tmp $i" + fi + done +@@ -175,7 +175,7 @@ if test "$echo_libs" = "yes"; then + + tmp="" + for i in $libdirs $libs_final; do +- if echo "$tmp" | fgrep -v -- "$i" >/dev/null; then ++ if echo "$tmp" | @GREP@ -F -v -- "$i" >/dev/null; then + tmp="$tmp $i" + fi + done diff --git a/libgcrypt-nobetasuffix.patch b/libgcrypt-nobetasuffix.patch new file mode 100644 index 0000000..3d4593a --- /dev/null +++ b/libgcrypt-nobetasuffix.patch @@ -0,0 +1,24 @@ +Index: libgcrypt-1.10.2/autogen.sh +=================================================================== +--- libgcrypt-1.10.2.orig/autogen.sh ++++ libgcrypt-1.10.2/autogen.sh +@@ -249,7 +249,7 @@ if [ "$myhost" = "find-version" ]; then + fi + + beta=no +- if [ -e .git ]; then ++ if false; then + ingit=yes + tmp=$(git describe --match "${matchstr1}" --long 2>/dev/null) + tmp=$(echo "$tmp" | sed s/^"$package"//) +@@ -265,8 +265,8 @@ if [ "$myhost" = "find-version" ]; then + rvd=$((0x$(echo ${rev} | dd bs=1 count=4 2>/dev/null))) + else + ingit=no +- beta=yes +- tmp="-unknown" ++ beta=no ++ tmp="" + rev="0000000" + rvd="0" + fi diff --git a/libgcrypt-ppc-enable-P10-assembly-with-ENABLE_FORCE_SOF.patch b/libgcrypt-ppc-enable-P10-assembly-with-ENABLE_FORCE_SOF.patch new file mode 100644 index 0000000..8ef3197 --- /dev/null +++ b/libgcrypt-ppc-enable-P10-assembly-with-ENABLE_FORCE_SOF.patch @@ -0,0 +1,76 @@ +commit 2c5e5ab6843d747c4b877d2c6f47226f61e9ff14 +Author: Jussi Kivilinna +Date: Sun Jun 12 21:51:34 2022 +0300 + + ppc enable P10 assembly with ENABLE_FORCE_SOFT_HWFEATURES on arch 3.00 + + * cipher/chacha20.c (chacha20_do_setkey) [USE_PPC_VEC]: Enable + P10 assembly for HWF_PPC_ARCH_3_00 if ENABLE_FORCE_SOFT_HWFEATURES is + defined. + * cipher/poly1305.c (poly1305_init) [POLY1305_USE_PPC_VEC]: Likewise. + * cipher/rijndael.c (do_setkey) [USE_PPC_CRYPTO_WITH_PPC9LE]: Likewise. + --- + + This change allows testing P10 implementations with P9 and with QEMU-PPC. + + GnuPG-bug-id: 6006 + Signed-off-by: Jussi Kivilinna + +Index: libgcrypt-1.10.2/cipher/chacha20.c +=================================================================== +--- libgcrypt-1.10.2.orig/cipher/chacha20.c ++++ libgcrypt-1.10.2/cipher/chacha20.c +@@ -484,6 +484,11 @@ chacha20_do_setkey (CHACHA20_context_t * + ctx->use_ppc = (features & HWF_PPC_ARCH_2_07) != 0; + # ifndef WORDS_BIGENDIAN + ctx->use_p10 = (features & HWF_PPC_ARCH_3_10) != 0; ++# ifdef ENABLE_FORCE_SOFT_HWFEATURES ++ /* HWF_PPC_ARCH_3_10 above is used as soft HW-feature indicator for P10. ++ * Actual implementation works with HWF_PPC_ARCH_3_00 also. */ ++ ctx->use_p10 |= (features & HWF_PPC_ARCH_3_00) != 0; ++# endif + # endif + #endif + #ifdef USE_S390X_VX +Index: libgcrypt-1.10.2/cipher/poly1305.c +=================================================================== +--- libgcrypt-1.10.2.orig/cipher/poly1305.c ++++ libgcrypt-1.10.2/cipher/poly1305.c +@@ -90,11 +90,19 @@ static void poly1305_init (poly1305_cont + const byte key[POLY1305_KEYLEN]) + { + POLY1305_STATE *st = &ctx->state; ++ unsigned int features = _gcry_get_hw_features (); + + #ifdef POLY1305_USE_PPC_VEC +- ctx->use_p10 = (_gcry_get_hw_features () & HWF_PPC_ARCH_3_10) != 0; ++ ctx->use_p10 = (features & HWF_PPC_ARCH_3_10) != 0; ++# ifdef ENABLE_FORCE_SOFT_HWFEATURES ++ /* HWF_PPC_ARCH_3_10 above is used as soft HW-feature indicator for P10. ++ * Actual implementation works with HWF_PPC_ARCH_3_00 also. */ ++ ctx->use_p10 |= (features & HWF_PPC_ARCH_3_00) != 0; ++# endif + #endif + ++ (void)features; ++ + ctx->leftover = 0; + + st->h[0] = 0; +Index: libgcrypt-1.10.2/cipher/rijndael.c +=================================================================== +--- libgcrypt-1.10.2.orig/cipher/rijndael.c ++++ libgcrypt-1.10.2/cipher/rijndael.c +@@ -605,6 +605,12 @@ do_setkey (RIJNDAEL_context *ctx, const + bulk_ops->xts_crypt = _gcry_aes_ppc9le_xts_crypt; + if (hwfeatures & HWF_PPC_ARCH_3_10) /* for P10 */ + bulk_ops->gcm_crypt = _gcry_aes_p10le_gcm_crypt; ++# ifdef ENABLE_FORCE_SOFT_HWFEATURES ++ /* HWF_PPC_ARCH_3_10 above is used as soft HW-feature indicator for P10. ++ * Actual implementation works with HWF_PPC_ARCH_3_00 also. */ ++ if (hwfeatures & HWF_PPC_ARCH_3_00) ++ bulk_ops->gcm_crypt = _gcry_aes_p10le_gcm_crypt; ++# endif + } + #endif + #ifdef USE_PPC_CRYPTO diff --git a/libgcrypt-rol64-redefinition.patch b/libgcrypt-rol64-redefinition.patch new file mode 100644 index 0000000..bb76b2f --- /dev/null +++ b/libgcrypt-rol64-redefinition.patch @@ -0,0 +1,16 @@ +Index: libgcrypt-1.11.0/cipher/bithelp.h +=================================================================== +--- libgcrypt-1.11.0.orig/cipher/bithelp.h ++++ libgcrypt-1.11.0/cipher/bithelp.h +@@ -35,11 +35,6 @@ static inline u32 ror(u32 x, int n) + return ( (x >> (n&(32-1))) | (x << ((32-n)&(32-1))) ); + } + +-static inline u64 rol64(u64 x, int n) +-{ +- return ( (x << (n&(64-1))) | (x >> ((64-n)&(64-1))) ); +-} +- + /* Byte swap for 32-bit and 64-bit integers. If available, use compiler + provided helpers. */ + #ifdef HAVE_BUILTIN_BSWAP32 diff --git a/libgcrypt-tests-Add-more-tests-to-tests-t-fips-service-ind.patch b/libgcrypt-tests-Add-more-tests-to-tests-t-fips-service-ind.patch new file mode 100644 index 0000000..c0058d2 --- /dev/null +++ b/libgcrypt-tests-Add-more-tests-to-tests-t-fips-service-ind.patch @@ -0,0 +1,382 @@ +From d71c88f78a4f1b72f92de90791fc6fe81a3cb861 Mon Sep 17 00:00:00 2001 +From: NIIBE Yutaka +Date: Tue, 24 Dec 2024 17:03:48 +0900 +Subject: [PATCH 17/19] tests: Add more tests to tests/t-fips-service-ind. +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* tests/t-fips-service-ind.c (check_pk_g_t_n_c, check_pk_s_v): New. +(main): Call check_pk_g_t_n_c and check_pk_s_v. + +-- + +GnuPG-bug-id: 7338 +Signed-off-by: NIIBE Yutaka +Signed-off-by: Lucas Mülling +--- + tests/t-fips-service-ind.c | 334 +++++++++++++++++++++++++++++++++++++ + 1 file changed, 334 insertions(+) + +diff --git a/tests/t-fips-service-ind.c b/tests/t-fips-service-ind.c +index 64e1e135..90d92c70 100644 +--- a/tests/t-fips-service-ind.c ++++ b/tests/t-fips-service-ind.c +@@ -40,6 +40,336 @@ static int in_fips_mode; + # include + #endif + ++/* Check gcry_pk_genkey, gcry_pk_testkey, gcry_pk_get_nbits, gcry_pk_get_curve API. */ ++static void ++check_pk_g_t_n_c (int reject) ++{ ++ static struct { ++ const char *keyparms; ++ int expect_failure; ++ } tv[] = { ++ { ++ "(genkey (ecc (curve nistp256)))", ++ 0 ++ }, ++ { /* non-compliant curve */ ++ "(genkey (ecc (curve secp256k1)))", ++ 1 ++ } ++ }; ++ int tvidx; ++ gpg_error_t err; ++ gpg_err_code_t ec; ++ ++ for (tvidx=0; tvidx < DIM(tv); tvidx++) ++ { ++ gcry_sexp_t s_kp = NULL; ++ gcry_sexp_t s_sk = NULL; ++ int nbits; ++ const char *name; ++ ++ if (verbose) ++ info ("checking gcry_pk_{genkey,testkey,get_nbits,get_curve} test %d\n", tvidx); ++ ++ err = gcry_sexp_build (&s_kp, NULL, tv[tvidx].keyparms); ++ if (err) ++ { ++ fail ("error building SEXP for test, %s: %s", ++ "keyparms", gpg_strerror (err)); ++ goto next; ++ } ++ ++ err = gcry_pk_genkey (&s_sk, s_kp); ++ if (err) ++ { ++ if (in_fips_mode && reject && tv[tvidx].expect_failure) ++ /* Here, an error is expected */ ++ ; ++ else ++ fail ("gcry_pk_genkey failed: %s", gpg_strerror (err)); ++ goto next; ++ } ++ else ++ { ++ if (in_fips_mode && reject && tv[tvidx].expect_failure) ++ { ++ fail ("gcry_pk_genkey test %d unexpectedly succeeded", tvidx); ++ goto next; ++ } ++ } ++ ++ ec = gcry_get_fips_service_indicator (); ++ if (ec == GPG_ERR_INV_OP) ++ { ++ /* libgcrypt is old, no support of the FIPS service indicator. */ ++ fail ("gcry_pk_genkey test %d unexpectedly failed to check the FIPS service indicator.\n", ++ tvidx); ++ goto next; ++ } ++ ++ if (in_fips_mode && !tv[tvidx].expect_failure && ec) ++ { ++ /* Success with the FIPS service indicator == 0 expected, but != 0. */ ++ fail ("gcry_pk_genkey test %d unexpectedly set the indicator in FIPS mode.\n", ++ tvidx); ++ goto next; ++ } ++ else if (in_fips_mode && tv[tvidx].expect_failure && !ec) ++ { ++ /* Success with the FIPS service indicator != 0 expected, but == 0. */ ++ fail ("gcry_pk_genkey test %d unexpectedly cleared the indicator in FIPS mode.\n", ++ tvidx); ++ goto next; ++ } ++ ++ err = gcry_pk_testkey (s_sk); ++ if (err) ++ { ++ fail ("gcry_pk_testkey failed for test: %s", gpg_strerror (err)); ++ goto next; ++ } ++ ++ ec = gcry_get_fips_service_indicator (); ++ if (ec == GPG_ERR_INV_OP) ++ { ++ /* libgcrypt is old, no support of the FIPS service indicator. */ ++ fail ("gcry_pk_testkey test %d unexpectedly failed to check the FIPS service indicator.\n", ++ tvidx); ++ goto next; ++ } ++ ++ if (in_fips_mode && !tv[tvidx].expect_failure && ec) ++ { ++ /* Success with the FIPS service indicator == 0 expected, but != 0. */ ++ fail ("gcry_pk_testkey test %d unexpectedly set the indicator in FIPS mode.\n", ++ tvidx); ++ goto next; ++ } ++ else if (in_fips_mode && tv[tvidx].expect_failure && !ec) ++ { ++ /* Success with the FIPS service indicator != 0 expected, but == 0. */ ++ fail ("gcry_pk_testkey test %d unexpectedly cleared the indicator in FIPS mode.\n", ++ tvidx); ++ goto next; ++ } ++ ++ nbits = gcry_pk_get_nbits (s_sk); ++ if (!nbits) ++ { ++ fail ("gcry_pk_get_nbits failed for test"); ++ goto next; ++ } ++ ++ ec = gcry_get_fips_service_indicator (); ++ if (ec == GPG_ERR_INV_OP) ++ { ++ /* libgcrypt is old, no support of the FIPS service indicator. */ ++ fail ("gcry_pk_get_nbits test %d unexpectedly failed to check the FIPS service indicator.\n", ++ tvidx); ++ goto next; ++ } ++ ++ if (in_fips_mode && !tv[tvidx].expect_failure && ec) ++ { ++ /* Success with the FIPS service indicator == 0 expected, but != 0. */ ++ fail ("gcry_pk_get_nbits test %d unexpectedly set the indicator in FIPS mode.\n", ++ tvidx); ++ goto next; ++ } ++ else if (in_fips_mode && tv[tvidx].expect_failure && !ec) ++ { ++ /* Success with the FIPS service indicator != 0 expected, but == 0. */ ++ fail ("gcry_pk_get_nbits test %d unexpectedly cleared the indicator in FIPS mode.\n", ++ tvidx); ++ goto next; ++ } ++ ++ name = gcry_pk_get_curve (s_sk, 0, NULL); ++ if (!name) ++ { ++ fail ("gcry_pk_get_curve failed for test: %s", gpg_strerror (err)); ++ goto next; ++ } ++ ++ ec = gcry_get_fips_service_indicator (); ++ if (ec == GPG_ERR_INV_OP) ++ { ++ /* libgcrypt is old, no support of the FIPS service indicator. */ ++ fail ("gcry_pk_get_curve test %d unexpectedly failed to check the FIPS service indicator.\n", ++ tvidx); ++ goto next; ++ } ++ ++ if (in_fips_mode && !tv[tvidx].expect_failure && ec) ++ { ++ /* Success with the FIPS service indicator == 0 expected, but != 0. */ ++ fail ("gcry_pk_get_curve test %d unexpectedly set the indicator in FIPS mode.\n", ++ tvidx); ++ goto next; ++ } ++ else if (in_fips_mode && tv[tvidx].expect_failure && !ec) ++ { ++ /* Success with the FIPS service indicator != 0 expected, but == 0. */ ++ fail ("gcry_pk_get_curve test %d unexpectedly cleared the indicator in FIPS mode.\n", ++ tvidx); ++ goto next; ++ } ++ ++ next: ++ gcry_sexp_release (s_kp); ++ gcry_sexp_release (s_sk); ++ } ++} ++ ++/* Check gcry_pk_sign, gcry_verify API. */ ++static void ++check_pk_s_v (int reject) ++{ ++ static struct { ++ const char *prvkey; ++ const char *pubkey; ++ int expect_failure; ++ } tv[] = { ++ { ++ "(private-key (ecc (curve nistp256)" ++ " (d #519b423d715f8b581f4fa8ee59f4771a5b44c8130b4e3eacca54a56dda72b464#)))", ++ "(public-key (ecc (curve nistp256)" ++ " (q #041ccbe91c075fc7f4f033bfa248db8fccd3565de94bbfb12f3c59ff46c271bf83" ++ "ce4014c68811f9a21a1fdb2c0e6113e06db7ca93b7404e78dc7ccd5ca89a4ca9#)))", ++ 0 ++ }, ++ { /* non-compliant curve */ ++ "(private-key (ecc (curve secp256k1)" ++ " (d #c2cdf0a8b0a83b35ace53f097b5e6e6a0a1f2d40535eff1cf434f52a43d59d8f#)))", ++ "(public-key (ecc (curve secp256k1)" ++ " (q #046fcc37ea5e9e09fec6c83e5fbd7a745e3eee81d16ebd861c9e66f55518c19798" ++ "4e9f113c07f875691df8afc1029496fc4cb9509b39dcd38f251a83359cc8b4f7#)))", ++ 1 ++ } ++ }; ++ int tvidx; ++ gpg_error_t err; ++ gpg_err_code_t ec; ++ const char *data = "(data (flags raw)" ++ "(hash sha256 #00112233445566778899AABBCCDDEEFF000102030405060708090A0B0C0D0E0F#))"; ++ gcry_sexp_t s_data = NULL; ++ ++ err = gcry_sexp_build (&s_data, NULL, data); ++ if (err) ++ { ++ fail ("error building SEXP for test, %s: %s", ++ "data", gpg_strerror (err)); ++ return; ++ } ++ ++ for (tvidx=0; tvidx < DIM(tv); tvidx++) ++ { ++ gcry_sexp_t s_pk = NULL; ++ gcry_sexp_t s_sk = NULL; ++ gcry_sexp_t s_sig= NULL; ++ ++ if (verbose) ++ info ("checking gcry_pk_{sign,verify} test %d\n", tvidx); ++ ++ err = gcry_sexp_build (&s_sk, NULL, tv[tvidx].prvkey); ++ if (err) ++ { ++ fail ("error building SEXP for test, %s: %s", ++ "sk", gpg_strerror (err)); ++ goto next; ++ } ++ ++ err = gcry_sexp_build (&s_pk, NULL, tv[tvidx].pubkey); ++ if (err) ++ { ++ fail ("error building SEXP for test, %s: %s", ++ "pk", gpg_strerror (err)); ++ goto next; ++ } ++ ++ err = gcry_pk_sign (&s_sig, s_data, s_sk); ++ if (err) ++ { ++ if (in_fips_mode && reject && tv[tvidx].expect_failure) ++ /* Here, an error is expected */ ++ ; ++ else ++ fail ("gcry_pk_sign failed: %s", gpg_strerror (err)); ++ goto next; ++ } ++ else ++ { ++ if (in_fips_mode && reject && tv[tvidx].expect_failure) ++ { ++ fail ("gcry_pk_sign test %d unexpectedly succeeded", tvidx); ++ goto next; ++ } ++ } ++ ++ ec = gcry_get_fips_service_indicator (); ++ if (ec == GPG_ERR_INV_OP) ++ { ++ /* libgcrypt is old, no support of the FIPS service indicator. */ ++ fail ("gcry_pk_sign test %d unexpectedly failed to check the FIPS service indicator.\n", ++ tvidx); ++ goto next; ++ } ++ ++ if (in_fips_mode && !tv[tvidx].expect_failure && ec) ++ { ++ /* Success with the FIPS service indicator == 0 expected, but != 0. */ ++ fail ("gcry_pk_sign test %d unexpectedly set the indicator in FIPS mode.\n", ++ tvidx); ++ goto next; ++ } ++ else if (in_fips_mode && tv[tvidx].expect_failure && !ec) ++ { ++ /* Success with the FIPS service indicator != 0 expected, but == 0. */ ++ fail ("gcry_pk_sign test %d unexpectedly cleared the indicator in FIPS mode.\n", ++ tvidx); ++ goto next; ++ } ++ ++ err = gcry_pk_verify (s_sig, s_data, s_pk); ++ if (err) ++ { ++ fail ("gcry_pk_verify failed for test: %s", gpg_strerror (err)); ++ goto next; ++ } ++ ++ ec = gcry_get_fips_service_indicator (); ++ if (ec == GPG_ERR_INV_OP) ++ { ++ /* libgcrypt is old, no support of the FIPS service indicator. */ ++ fail ("gcry_pk_verify test %d unexpectedly failed to check the FIPS service indicator.\n", ++ tvidx); ++ goto next; ++ } ++ ++ if (in_fips_mode && !tv[tvidx].expect_failure && ec) ++ { ++ /* Success with the FIPS service indicator == 0 expected, but != 0. */ ++ fail ("gcry_pk_verify test %d unexpectedly set the indicator in FIPS mode.\n", ++ tvidx); ++ goto next; ++ } ++ else if (in_fips_mode && tv[tvidx].expect_failure && !ec) ++ { ++ /* Success with the FIPS service indicator != 0 expected, but == 0. */ ++ fail ("gcry_pk_verify test %d unexpectedly cleared the indicator in FIPS mode.\n", ++ tvidx); ++ goto next; ++ } ++ ++ next: ++ gcry_sexp_release (s_sig); ++ gcry_sexp_release (s_pk); ++ gcry_sexp_release (s_sk); ++ } ++ ++ gcry_sexp_release (s_data); ++} ++ + /* Check gcry_pk_hash_sign, gcry_pk_hash_verify API. */ + static void + check_pk_hash_sign_verify (void) +@@ -1126,6 +1456,8 @@ main (int argc, char **argv) + check_mac_o_w_r_c (0); + check_cipher_o_s_e_d_c (0); + check_pk_hash_sign_verify (); ++ check_pk_s_v (0); ++ check_pk_g_t_n_c (0); + + xgcry_control ((GCRYCTL_FIPS_REJECT_NON_FIPS, + (GCRY_FIPS_FLAG_REJECT_MD_MD5 +@@ -1134,6 +1466,8 @@ main (int argc, char **argv) + check_md_o_w_r_c (1); + check_mac_o_w_r_c (1); + check_cipher_o_s_e_d_c (1); ++ check_pk_s_v (1); ++ check_pk_g_t_n_c (1); + + return !!error_count; + } +-- +2.49.0 + diff --git a/libgcrypt-tests-Allow-tests-with-USE_RSA.patch b/libgcrypt-tests-Allow-tests-with-USE_RSA.patch new file mode 100644 index 0000000..cc29fb0 --- /dev/null +++ b/libgcrypt-tests-Allow-tests-with-USE_RSA.patch @@ -0,0 +1,44 @@ +From 8404a048b7c58eb903717e09cffaa7735f7d8520 Mon Sep 17 00:00:00 2001 +From: NIIBE Yutaka +Date: Tue, 4 Mar 2025 13:29:28 +0900 +Subject: [PATCH 01/14] tests: Allow tests with !USE_RSA. +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* tests/t-fips-service-ind.c [USE_RSA] (check_pk_s_v): Ifdef-out. + +-- + +Signed-off-by: NIIBE Yutaka +Signed-off-by: Lucas Mülling +--- + tests/t-fips-service-ind.c | 5 ++++- + 1 file changed, 4 insertions(+), 1 deletion(-) + +diff --git a/tests/t-fips-service-ind.c b/tests/t-fips-service-ind.c +index 99b84c8f..a082b258 100644 +--- a/tests/t-fips-service-ind.c ++++ b/tests/t-fips-service-ind.c +@@ -290,7 +290,9 @@ check_pk_s_v (int reject) + " 00112233445566778899AABBCCDDEEFF000102030405060708090A0B0C0D0E0F" + " 00112233445566778899AABBCCDDEEFF000102030405060708090A0B0C0D0E0F#))", + 0 +- }, ++ } ++#if USE_RSA ++ , + { /* RSA with compliant hash for signing */ + "(private-key" + " (rsa" +@@ -559,6 +561,7 @@ check_pk_s_v (int reject) + " (hash sha1 #11223344556677889900AABBCCDDEEFF10203040#))\n", + 1 + } ++#endif /* USE_RSA */ + }; + int tvidx; + gpg_error_t err; +-- +2.49.0 + diff --git a/libgcrypt-tests-Update-t-fips-service-ind-using-GCRY_MD_SHA256-for-KDF-tests.patch b/libgcrypt-tests-Update-t-fips-service-ind-using-GCRY_MD_SHA256-for-KDF-tests.patch new file mode 100644 index 0000000..dd009fd --- /dev/null +++ b/libgcrypt-tests-Update-t-fips-service-ind-using-GCRY_MD_SHA256-for-KDF-tests.patch @@ -0,0 +1,106 @@ +From e5989e08a556117ec3f19f098765963358b71051 Mon Sep 17 00:00:00 2001 +From: NIIBE Yutaka +Date: Wed, 26 Feb 2025 13:51:36 +0900 +Subject: [PATCH 3/4] tests: Update t-fips-service-ind using GCRY_MD_SHA256 for + KDF tests. +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* tests/t-fips-service-ind.c (check_kdf_derive): Use GCRY_MD_SHA256. + +-- + +GnuPG-bug-id: 7338 +Signed-off-by: NIIBE Yutaka +Signed-off-by: Lucas Mülling +--- + tests/t-fips-service-ind.c | 38 +++++++++++++++++++------------------- + 1 file changed, 19 insertions(+), 19 deletions(-) + +diff --git a/tests/t-fips-service-ind.c b/tests/t-fips-service-ind.c +index bec6c27e..99b84c8f 100644 +--- a/tests/t-fips-service-ind.c ++++ b/tests/t-fips-service-ind.c +@@ -1621,13 +1621,13 @@ check_kdf_derive (void) + } tv[] = { + { + "passwordPASSWORDpassword", 24, +- GCRY_KDF_PBKDF2, GCRY_MD_SHA1, ++ GCRY_KDF_PBKDF2, GCRY_MD_SHA256, + "saltSALTsaltSALTsaltSALTsaltSALTsalt", 36, + 4096, + 25, +- "\x3d\x2e\xec\x4f\xe4\x1c\x84\x9b\x80\xc8" +- "\xd8\x36\x62\xc0\xe4\x4a\x8b\x29\x1a\x96" +- "\x4c\xf2\xf0\x70\x38", ++ "\x34\x8c\x89\xdb\xcb\xd3\x2b\x2f\x32\xd8" ++ "\x14\xb8\x11\x6e\x84\xcf\x2b\x17\x34\x7e" ++ "\xbc\x18\x00\x18\x1c", + 0 + }, + { +@@ -1644,45 +1644,45 @@ check_kdf_derive (void) + }, + { + "passwor", 7, +- GCRY_KDF_PBKDF2, GCRY_MD_SHA1, ++ GCRY_KDF_PBKDF2, GCRY_MD_SHA256, + "saltSALTsaltSALTsaltSALTsaltSALTsalt", 36, + 4096, + 25, +- "\xf4\x93\xee\x2b\xbf\x44\x0b\x9e\x64\x53" +- "\xc2\xb3\x87\xdc\x73\xf8\xfd\xe6\x97\xda" +- "\xb8\x24\xa0\x26\x50", ++ "\x2d\x72\xa9\xe5\x4e\x2f\x37\x6e\xe5\xe4" ++ "\xf5\x55\x76\xb5\xaa\x49\x73\x01\x97\x1c" ++ "\xad\x3a\x7c\xc4\xde", + 1 /* not-compliant because passphrase len is too small */ + }, + { + "passwordPASSWORDpassword", 24, +- GCRY_KDF_PBKDF2, GCRY_MD_SHA1, ++ GCRY_KDF_PBKDF2, GCRY_MD_SHA256, + "saltSALTsaltSAL", 15, + 4096, + 25, +- "\x14\x05\xa4\x2a\xf4\xa8\x12\x14\x7b\x65" +- "\x8f\xaa\xf0\x7f\x25\xe5\x0f\x0b\x2b\xb7" +- "\xcf\x8d\x29\x23\x4b", ++ "\xf7\x55\xdd\x3c\x5e\xfb\x23\x06\xa7\x85" ++ "\x94\xa7\x31\x12\x45\xcf\x5a\x4b\xdc\x09" ++ "\xee\x65\x4b\x50\x3f", + 1 /* not-compliant because salt len is too small */ + }, + { + "passwordPASSWORDpassword", 24, +- GCRY_KDF_PBKDF2, GCRY_MD_SHA1, ++ GCRY_KDF_PBKDF2, GCRY_MD_SHA256, + "saltSALTsaltSALTsaltSALTsaltSALTsalt", 36, + 999, + 25, +- "\xac\xf8\xb4\x67\x41\xc7\xf3\xd1\xa0\xc0" +- "\x08\xbe\x9b\x23\x96\x78\xbd\x93\xda\x4a" +- "\x30\xd4\xfb\xf0\x33", ++ "\x09\x3e\x1a\xd8\x63\x30\x71\x9c\x17\xcf" ++ "\xb0\x53\x3e\x1f\xc8\x51\x29\x71\x54\x28" ++ "\x5d\xf7\x8e\x41\xaa", + 1 /* not-compliant because too few iterations */ + }, + { + "passwordPASSWORDpassword", 24, +- GCRY_KDF_PBKDF2, GCRY_MD_SHA1, ++ GCRY_KDF_PBKDF2, GCRY_MD_SHA256, + "saltSALTsaltSALTsaltSALTsaltSALTsalt", 36, + 4096, + 13, +- "\x3d\x2e\xec\x4f\xe4\x1c\x84\x9b\x80\xc8" +- "\xd8\x36\x62", ++ "\x34\x8c\x89\xdb\xcb\xd3\x2b\x2f\x32\xd8" ++ "\x14\xb8\x11", + 1 /* not-compliant because key size too small */ + }, + { +-- +2.49.0 + diff --git a/libgcrypt-tests-fips-Add-gcry_cipher_open-tests.patch b/libgcrypt-tests-fips-Add-gcry_cipher_open-tests.patch new file mode 100644 index 0000000..0e0f7e5 --- /dev/null +++ b/libgcrypt-tests-fips-Add-gcry_cipher_open-tests.patch @@ -0,0 +1,199 @@ +From cfd2d2f41ad4aef40d83f8f7237d1da13c7e240c Mon Sep 17 00:00:00 2001 +From: NIIBE Yutaka +Date: Tue, 17 Dec 2024 10:33:33 +0900 +Subject: [PATCH 09/19] tests,fips: Add gcry_cipher_open tests. +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* tests/t-fips-service-ind.c (check_cipher_o_s_e_d_c): New. +(main): Call check_cipher_o_s_e_d_c. + +-- + +GnuPG-bug-id: 7338 +Signed-off-by: NIIBE Yutaka +Signed-off-by: Lucas Mülling +--- + tests/t-fips-service-ind.c | 152 ++++++++++++++++++++++++++++++++++++- + 1 file changed, 151 insertions(+), 1 deletion(-) + +Index: libgcrypt-1.11.0/tests/t-fips-service-ind.c +=================================================================== +--- libgcrypt-1.11.0.orig/tests/t-fips-service-ind.c ++++ libgcrypt-1.11.0/tests/t-fips-service-ind.c +@@ -31,6 +31,7 @@ + + #include "t-common.h" + static int in_fips_mode; ++#define MAX_DATA_LEN 1040 + + /* Mingw requires us to include windows.h after winsock2.h which is + included by gcrypt.h. */ +@@ -38,6 +39,154 @@ static int in_fips_mode; + # include + #endif + ++/* Check gcry_cipher_open, gcry_cipher_setkey, gcry_cipher_encrypt, ++ gcry_cipher_decrypt, gcry_cipher_close API. */ ++static void ++check_cipher_o_s_e_d_c (void) ++{ ++ static struct { ++ int algo; ++ const char *key; ++ int keylen; ++ const char *expect; ++ int expect_failure; ++ unsigned int flags; ++ } tv[] = { ++#if USE_DES ++ { GCRY_CIPHER_3DES, ++ "\xe3\x34\x7a\x6b\x0b\xc1\x15\x2c\x64\x2a\x25\xcb\xd3\xbc\x31\xab" ++ "\xfb\xa1\x62\xa8\x1f\x19\x7c\x15", 24, ++ "\x3f\x1a\xb8\x83\x18\x8b\xb5\x97", 1 }, ++ { GCRY_CIPHER_3DES, ++ "\xe3\x34\x7a\x6b\x0b\xc1\x15\x2c\x64\x2a\x25\xcb\xd3\xbc\x31\xab" ++ "\xfb\xa1\x62\xa8\x1f\x19\x7c\x15", 24, ++ "\x3f\x1a\xb8\x83\x18\x8b\xb5\x97", ++ 1, GCRY_CIPHER_FLAG_REJECT_NON_FIPS }, ++#endif ++ { GCRY_CIPHER_AES, ++ "\x2b\x7e\x15\x16\x28\xae\xd2\xa6\xab\xf7\x15\x88\x09\xcf\x4f\x3c", 16, ++ "\x5c\x71\xd8\x5d\x26\x5e\xcd\xb5\x95\x40\x41\xab\xff\x25\x6f\xd1" } ++ }; ++ const char *pt = "Shohei Ohtani 2024: 54 HR, 59 SB"; ++ int ptlen; ++ int tvidx; ++ unsigned char out[MAX_DATA_LEN]; ++ gpg_error_t err; ++ ++ ptlen = strlen (pt); ++ assert (ptlen == 32); ++ for (tvidx=0; tvidx < DIM(tv); tvidx++) ++ { ++ gpg_err_code_t ec; ++ gcry_cipher_hd_t h; ++ size_t blklen; ++ ++ if (verbose) ++ fprintf (stderr, "checking gcry_cipher_open test %d\n", ++ tvidx); ++ ++ blklen = gcry_cipher_get_algo_blklen (tv[tvidx].algo); ++ assert (blklen != 0); ++ assert (blklen <= ptlen); ++ assert (blklen <= DIM (out)); ++ err = gcry_cipher_open (&h, tv[tvidx].algo, GCRY_CIPHER_MODE_ECB, ++ tv[tvidx].flags); ++ if (err) ++ { ++ if (in_fips_mode && (tv[tvidx].flags & GCRY_CIPHER_FLAG_REJECT_NON_FIPS) ++ && tv[tvidx].expect_failure) ++ /* Here, an error is expected */ ++ ; ++ else ++ fail ("gcry_cipher_open test %d unexpectedly failed: %s\n", ++ tvidx, gpg_strerror (err)); ++ continue; ++ } ++ else ++ { ++ if (in_fips_mode && (tv[tvidx].flags & GCRY_CIPHER_FLAG_REJECT_NON_FIPS) ++ && tv[tvidx].expect_failure) ++ /* This case, an error is expected, but we observed success */ ++ fail ("gcry_cipher_open test %d unexpectedly succeeded\n", tvidx); ++ } ++ ++ ec = gcry_get_fips_service_indicator (); ++ if (ec == GPG_ERR_INV_OP) ++ { ++ /* libgcrypt is old, no support of the FIPS service indicator. */ ++ fail ("gcry_cipher_open test %d unexpectedly failed to check the FIPS service indicator.\n", ++ tvidx); ++ continue; ++ } ++ ++ if (in_fips_mode && !tv[tvidx].expect_failure && ec) ++ { ++ /* Success with the FIPS service indicator == 0 expected, but != 0. */ ++ fail ("gcry_cipher_open test %d unexpectedly set the indicator in FIPS mode.\n", ++ tvidx); ++ continue; ++ } ++ else if (in_fips_mode && tv[tvidx].expect_failure && !ec) ++ { ++ /* Success with the FIPS service indicator != 0 expected, but == 0. */ ++ fail ("gcry_cipher_open test %d unexpectedly cleared the indicator in FIPS mode.\n", ++ tvidx); ++ continue; ++ } ++ ++ err = gcry_cipher_setkey (h, tv[tvidx].key, tv[tvidx].keylen); ++ if (err) ++ { ++ fail ("gcry_cipher_setkey %d failed: %s\n", tvidx, ++ gpg_strerror (err)); ++ gcry_cipher_close (h); ++ continue; ++ } ++ ++ err = gcry_cipher_encrypt (h, out, MAX_DATA_LEN, pt, blklen); ++ if (err) ++ { ++ fail ("gcry_cipher_encrypt %d failed: %s\n", tvidx, ++ gpg_strerror (err)); ++ gcry_cipher_close (h); ++ continue; ++ } ++ ++ if (memcmp (out, tv[tvidx].expect, blklen)) ++ { ++ int i; ++ ++ fail ("gcry_cipher_open test %d failed: encryption mismatch\n", tvidx); ++ fputs ("got:", stderr); ++ for (i=0; i < blklen; i++) ++ fprintf (stderr, " %02x", out[i]); ++ putc ('\n', stderr); ++ } ++ ++ err = gcry_cipher_decrypt (h, out, blklen, NULL, 0); ++ if (err) ++ { ++ fail ("gcry_cipher_decrypt %d failed: %s\n", tvidx, ++ gpg_strerror (err)); ++ gcry_cipher_close (h); ++ continue; ++ } ++ ++ if (memcmp (out, pt, blklen)) ++ { ++ int i; ++ ++ fail ("gcry_cipher_open test %d failed: decryption mismatch\n", tvidx); ++ fputs ("got:", stderr); ++ for (i=0; i < blklen; i++) ++ fprintf (stderr, " %02x", out[i]); ++ putc ('\n', stderr); ++ } ++ ++ gcry_cipher_close (h); ++ } ++} ++ + /* Check gcry_mac_open, gcry_mac_write, gcry_mac_write, gcry_mac_read, + gcry_mac_close API. */ + static void +@@ -651,9 +800,10 @@ main (int argc, char **argv) + xgcry_control ((GCRYCTL_SET_DEBUG_FLAGS, 1u , 0)); + + check_digests (); ++ check_kdf_derive (); + check_md_o_w_r_c (); + check_mac_o_w_r_c (); +- check_kdf_derive (); ++ check_cipher_o_s_e_d_c (); + + return !!error_count; + } diff --git a/libgcrypt-tests-fips-Add-gcry_mac_open-tests.patch b/libgcrypt-tests-fips-Add-gcry_mac_open-tests.patch new file mode 100644 index 0000000..c2e3ed4 --- /dev/null +++ b/libgcrypt-tests-fips-Add-gcry_mac_open-tests.patch @@ -0,0 +1,206 @@ +From c4f75014cb8af732f87c02fe7c2e7a488fe71c6d Mon Sep 17 00:00:00 2001 +From: NIIBE Yutaka +Date: Mon, 16 Dec 2024 14:09:10 +0900 +Subject: [PATCH 06/19] tests,fips: Add gcry_mac_open tests. +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* tests/t-digest.c (check_mac_o_w_r_c): New. +(main): Call check_mac_o_w_r_c. + +-- + +GnuPG-bug-id: 7338 +Signed-off-by: NIIBE Yutaka +Signed-off-by: Lucas Mülling +--- + tests/t-digest.c | 168 +++++++++++++++++++++++++++++++++++++++++++++++ + 1 file changed, 168 insertions(+) + +Index: libgcrypt-1.11.0/tests/t-digest.c +=================================================================== +--- libgcrypt-1.11.0.orig/tests/t-digest.c ++++ libgcrypt-1.11.0/tests/t-digest.c +@@ -38,6 +38,173 @@ static int in_fips_mode; + # include + #endif + ++/* Check gcry_mac_open, gcry_mac_write, gcry_mac_write, gcry_mac_read, ++ gcry_mac_close API. */ ++static void ++check_mac_o_w_r_c (void) ++{ ++ static struct { ++ int algo; ++ const char *data; ++ int datalen; ++ const char *key; ++ int keylen; ++ const char *expect; ++ int expect_failure; ++ unsigned int flags; ++ } tv[] = { ++#if USE_MD5 ++ { GCRY_MAC_HMAC_MD5, "hmac input abc", 14, "hmac key input", 14, ++ "\x0d\x72\xd0\x60\xaf\x34\xf2\xca\x33\x58\xa9\xcc\xd3\x5a\xac\xb5", 1 }, ++ { GCRY_MAC_HMAC_MD5, "hmac input abc", 14, "hmac key input", 14, ++ "\x0d\x72\xd0\x60\xaf\x34\xf2\xca\x33\x58\xa9\xcc\xd3\x5a\xac\xb5", 1, ++ GCRY_MAC_FLAG_REJECT_NON_FIPS }, ++#endif ++#if USE_SHA1 ++ { GCRY_MAC_HMAC_SHA1, "hmac input abc", 14, "hmac key input", 14, ++ "\xc9\x62\x9d\x16\x0f\xc2\xc4\xcd\x38\xac\x3a\x00\xdc\x29\x61\x03" ++ "\x69\x50\xd7\x3a" }, ++#endif ++ { GCRY_MAC_HMAC_SHA256, "hmac input abc", 14, "hmac key input", 14, ++ "\x6a\xda\x4d\xd5\xf3\xa7\x32\x9d\xd2\x55\xc0\x7f\xe6\x0a\x93\xb8" ++ "\x7a\x6e\x76\x68\x46\x34\x67\xf9\xc2\x29\xb8\x24\x2e\xc8\xe3\xb4" }, ++ { GCRY_MAC_HMAC_SHA384, "hmac input abc", 14, "hmac key input", 14, ++ "\xc6\x59\x14\x4a\xac\x4d\xd5\x62\x09\x2c\xbd\x5e\xbf\x41\x94\xf9" ++ "\xa4\x78\x18\x46\xfa\xd6\xd1\x12\x90\x4f\x65\xd4\xe8\x44\xcc\xcc" ++ "\x3d\xcc\xf3\xe4\x27\xd8\xf0\xff\x01\xe8\x70\xcd\xfb\xfa\x24\x45" }, ++ { GCRY_MAC_HMAC_SHA512, "hmac input abc", 14, "hmac key input", 14, ++ "\xfa\x77\x49\x49\x24\x3d\x7e\x03\x1b\x0e\xd1\xfc\x20\x81\xcf\x95" ++ "\x81\x21\xa4\x4f\x3b\xe5\x69\x9a\xe6\x67\x27\x10\xbc\x62\xc7\xb3" ++ "\xb3\xcf\x2b\x1e\xda\x20\x48\x25\xc5\x6a\x52\xc7\xc9\xd9\x77\xf6" ++ "\xf6\x49\x9d\x70\xe6\x04\x33\xab\x6a\xdf\x7e\x9f\xf4\xd1\x59\x6e" }, ++ { GCRY_MAC_HMAC_SHA3_256, "hmac input abc", 14, "hmac key input", 14, ++ "\x2b\xe9\x02\x92\xc2\x37\xbe\x91\x06\xbf\x9c\x8e\x7b\xa3\xf2\xfc" ++ "\x68\x10\x8a\x71\xd5\xc7\x84\x3c\x0b\xdd\x7d\x1e\xdf\xa5\xf6\xa7" }, ++ { GCRY_MAC_HMAC_SHA3_384, "hmac input abc", 14, "hmac key input", 14, ++ "\x9f\x6b\x9f\x49\x95\x57\xed\x33\xb1\xe7\x22\x2f\xda\x40\x68\xb0" ++ "\x28\xd2\xdb\x6f\x73\x3c\x2e\x2b\x29\x51\x64\x53\xc4\xc5\x63\x8a" ++ "\x98\xca\x78\x1a\xe7\x1b\x7d\xf6\xbf\xf3\x6a\xf3\x2a\x0e\xa0\x5b" }, ++ { GCRY_MAC_HMAC_SHA3_512, "hmac input abc", 14, "hmac key input", 14, ++ "\xf3\x19\x70\x54\x25\xdf\x0f\xde\x09\xe9\xea\x3b\x34\x67\x14\x32" ++ "\xe6\xe2\x58\x9d\x76\x38\xa4\xbd\x90\x35\x4c\x07\x7c\xa3\xdb\x23" ++ "\x3c\x78\x0c\x45\xee\x8e\x39\xd5\x81\xd8\x5c\x13\x20\x40\xba\x34" ++ "\xd0\x0b\x75\x31\x38\x4b\xe7\x74\x87\xa9\xc5\x68\x7f\xbc\x19\xa1" } ++#if USE_RMD160 ++ , ++ { GCRY_MAC_HMAC_RMD160, "hmac input abc", 14, "hmac key input", 14, ++ "\xf2\x45\x5c\x7e\x48\x1a\xbb\xe5\xe8\xec\x40\xa4\x1b\x89\x26\x2b" ++ "\xdc\xa1\x79\x59", 1 } ++#endif ++ }; ++ int tvidx; ++ unsigned char mac[64]; ++ int expectlen; ++ gpg_error_t err; ++ size_t buflen; ++ ++ for (tvidx=0; tvidx < DIM(tv); tvidx++) ++ { ++ gpg_err_code_t ec; ++ gcry_mac_hd_t h; ++ ++ if (verbose) ++ fprintf (stderr, "checking gcry_mac_open test %d\n", ++ tvidx); ++ ++ expectlen = gcry_mac_get_algo_maclen (tv[tvidx].algo); ++ assert (expectlen != 0); ++ assert (expectlen <= DIM (mac)); ++ err = gcry_mac_open (&h, tv[tvidx].algo, tv[tvidx].flags, NULL); ++ if (err) ++ { ++ if (in_fips_mode && (tv[tvidx].flags & GCRY_MAC_FLAG_REJECT_NON_FIPS) ++ && tv[tvidx].expect_failure) ++ /* Here, an error is expected */ ++ ; ++ else ++ fail ("gcry_mac_open test %d unexpectedly failed: %s\n", ++ tvidx, gpg_strerror (err)); ++ continue; ++ } ++ else ++ { ++ if (in_fips_mode && (tv[tvidx].flags & GCRY_MAC_FLAG_REJECT_NON_FIPS) ++ && tv[tvidx].expect_failure) ++ /* This case, an error is expected, but we observed success */ ++ fail ("gcry_mac_open test %d unexpectedly succeeded\n", tvidx); ++ } ++ ++ ++ ec = gcry_get_fips_service_indicator (); ++ if (ec == GPG_ERR_INV_OP) ++ { ++ /* libgcrypt is old, no support of the FIPS service indicator. */ ++ fail ("gcry_mac_open test %d unexpectedly failed to check the FIPS service indicator.\n", ++ tvidx); ++ continue; ++ } ++ ++ if (in_fips_mode && !tv[tvidx].expect_failure && ec) ++ { ++ /* Success with the FIPS service indicator == 0 expected, but != 0. */ ++ fail ("gcry_mac_open test %d unexpectedly set the indicator in FIPS mode.\n", ++ tvidx); ++ continue; ++ } ++ else if (in_fips_mode && tv[tvidx].expect_failure && !ec) ++ { ++ /* Success with the FIPS service indicator != 0 expected, but == 0. */ ++ fail ("gcry_mac_open test %d unexpectedly cleared the indicator in FIPS mode.\n", ++ tvidx); ++ continue; ++ } ++ ++ err = gcry_mac_setkey (h, tv[tvidx].key, tv[tvidx].keylen); ++ if (err) ++ { ++ fail ("gcry_mac_setkey test %d unexpectedly failed: %s\n", ++ tvidx, gpg_strerror (err)); ++ gcry_mac_close (h); ++ continue; ++ } ++ ++ err = gcry_mac_write (h, tv[tvidx].data, tv[tvidx].datalen); ++ if (err) ++ { ++ fail ("gcry_mac_write test %d unexpectedly failed: %s\n", ++ tvidx, gpg_strerror (err)); ++ gcry_mac_close (h); ++ continue; ++ } ++ ++ buflen = expectlen; ++ err = gcry_mac_read (h, mac, &buflen); ++ if (err || buflen != expectlen) ++ { ++ fail ("gcry_mac_read test %d unexpectedly failed: %s\n", ++ tvidx, gpg_strerror (err)); ++ gcry_mac_close (h); ++ continue; ++ } ++ ++ if (memcmp (mac, tv[tvidx].expect, expectlen)) ++ { ++ int i; ++ ++ fail ("gcry_mac_open test %d failed: mismatch\n", tvidx); ++ fputs ("got:", stderr); ++ for (i=0; i < expectlen; i++) ++ fprintf (stderr, " %02x", mac[i]); ++ putc ('\n', stderr); ++ } ++ ++ gcry_mac_close (h); ++ } ++} ++ ++ ++/* Check gcry_md_open, gcry_md_write, gcry_md_write, gcry_md_read, ++ gcry_md_close API. */ + static void + check_md_o_w_r_c (void) + { +@@ -327,6 +494,7 @@ main (int argc, char **argv) + + check_digests (); + check_md_o_w_r_c (); ++ check_mac_o_w_r_c (); + + return !!error_count; + } diff --git a/libgcrypt-tests-fips-Move-KDF-tests-to-t-fips-service-ind.patch b/libgcrypt-tests-fips-Move-KDF-tests-to-t-fips-service-ind.patch new file mode 100644 index 0000000..7adbac5 --- /dev/null +++ b/libgcrypt-tests-fips-Move-KDF-tests-to-t-fips-service-ind.patch @@ -0,0 +1,375 @@ +From b59bde31ded9e829e2a53ddb8c533bf35a144972 Mon Sep 17 00:00:00 2001 +From: NIIBE Yutaka +Date: Mon, 16 Dec 2024 14:21:06 +0900 +Subject: [PATCH 08/19] tests,fips: Move KDF tests to t-fips-service-ind. +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* tests/t-fips-service-ind.c (check_kdf_derive): Move from... +* tests/t-kdf.c (check_fips_gcry_kdf_derive): ... here. + +-- + +GnuPG-bug-id: 7338 +Signed-off-by: NIIBE Yutaka +Signed-off-by: Lucas Mülling +--- + tests/t-fips-service-ind.c | 159 +++++++++++++++++++++++++++++++++++++ + tests/t-kdf.c | 159 ------------------------------------- + 2 files changed, 159 insertions(+), 159 deletions(-) + +Index: libgcrypt-1.11.0/tests/t-fips-service-ind.c +=================================================================== +--- libgcrypt-1.11.0.orig/tests/t-fips-service-ind.c ++++ libgcrypt-1.11.0/tests/t-fips-service-ind.c +@@ -439,6 +439,164 @@ check_digests (void) + } + + ++ ++static void ++check_kdf_derive (void) ++{ ++ static struct { ++ const char *p; /* Passphrase. */ ++ size_t plen; /* Length of P. */ ++ int algo; ++ int subalgo; ++ const char *salt; ++ size_t saltlen; ++ unsigned long iterations; ++ int dklen; /* Requested key length. */ ++ const char *dk; /* Derived key. */ ++ int expect_failure; ++ } tv[] = { ++ { ++ "passwordPASSWORDpassword", 24, ++ GCRY_KDF_PBKDF2, GCRY_MD_SHA1, ++ "saltSALTsaltSALTsaltSALTsaltSALTsalt", 36, ++ 4096, ++ 25, ++ "\x3d\x2e\xec\x4f\xe4\x1c\x84\x9b\x80\xc8" ++ "\xd8\x36\x62\xc0\xe4\x4a\x8b\x29\x1a\x96" ++ "\x4c\xf2\xf0\x70\x38", ++ 0 ++ }, ++ { ++ "pleaseletmein", 13, ++ GCRY_KDF_SCRYPT, 16384, ++ "SodiumChloride", 14, ++ 1, ++ 64, ++ "\x70\x23\xbd\xcb\x3a\xfd\x73\x48\x46\x1c\x06\xcd\x81\xfd\x38\xeb" ++ "\xfd\xa8\xfb\xba\x90\x4f\x8e\x3e\xa9\xb5\x43\xf6\x54\x5d\xa1\xf2" ++ "\xd5\x43\x29\x55\x61\x3f\x0f\xcf\x62\xd4\x97\x05\x24\x2a\x9a\xf9" ++ "\xe6\x1e\x85\xdc\x0d\x65\x1e\x40\xdf\xcf\x01\x7b\x45\x57\x58\x87", ++ 1 /* not-compliant because unallowed algo */ ++ }, ++ { ++ "passwor", 7, ++ GCRY_KDF_PBKDF2, GCRY_MD_SHA1, ++ "saltSALTsaltSALTsaltSALTsaltSALTsalt", 36, ++ 4096, ++ 25, ++ "\xf4\x93\xee\x2b\xbf\x44\x0b\x9e\x64\x53" ++ "\xc2\xb3\x87\xdc\x73\xf8\xfd\xe6\x97\xda" ++ "\xb8\x24\xa0\x26\x50", ++ 1 /* not-compliant because passphrase len is too small */ ++ }, ++ { ++ "passwordPASSWORDpassword", 24, ++ GCRY_KDF_PBKDF2, GCRY_MD_SHA1, ++ "saltSALTsaltSAL", 15, ++ 4096, ++ 25, ++ "\x14\x05\xa4\x2a\xf4\xa8\x12\x14\x7b\x65" ++ "\x8f\xaa\xf0\x7f\x25\xe5\x0f\x0b\x2b\xb7" ++ "\xcf\x8d\x29\x23\x4b", ++ 1 /* not-compliant because salt len is too small */ ++ }, ++ { ++ "passwordPASSWORDpassword", 24, ++ GCRY_KDF_PBKDF2, GCRY_MD_SHA1, ++ "saltSALTsaltSALTsaltSALTsaltSALTsalt", 36, ++ 999, ++ 25, ++ "\xac\xf8\xb4\x67\x41\xc7\xf3\xd1\xa0\xc0" ++ "\x08\xbe\x9b\x23\x96\x78\xbd\x93\xda\x4a" ++ "\x30\xd4\xfb\xf0\x33", ++ 1 /* not-compliant because too few iterations */ ++ }, ++ { ++ "passwordPASSWORDpassword", 24, ++ GCRY_KDF_PBKDF2, GCRY_MD_SHA1, ++ "saltSALTsaltSALTsaltSALTsaltSALTsalt", 36, ++ 4096, ++ 13, ++ "\x3d\x2e\xec\x4f\xe4\x1c\x84\x9b\x80\xc8" ++ "\xd8\x36\x62", ++ 1 /* not-compliant because key size too small */ ++ }, ++ { ++ "passwordPASSWORDpassword", 24, ++ GCRY_KDF_PBKDF2, GCRY_MD_BLAKE2B_512, ++ "saltSALTsaltSALTsaltSALTsaltSALTsalt", 36, ++ 4096, ++ 60, ++ "\xa4\x6b\x53\x35\xdb\xdd\xa3\xd2\x5d\x19\xbb\x11\xfe\xdd\xd9\x9e" ++ "\x45\x2a\x7c\x34\x47\x41\x98\xca\x31\x74\xb6\x34\x22\xac\x83\xb0" ++ "\x38\x6e\xf5\x93\x0f\xf5\x16\x46\x0b\x97\xdc\x6c\x27\x5b\xe7\x25" ++ "\xc2\xcb\xec\x50\x02\xc6\x52\x8b\x34\x68\x53\x65", ++ 1 /* not-compliant because subalgo is not the one of approved */ ++ } ++ }; ++ ++ int tvidx; ++ gpg_error_t err; ++ unsigned char outbuf[100]; ++ int i; ++ ++ for (tvidx=0; tvidx < DIM(tv); tvidx++) ++ { ++ if (verbose) ++ fprintf (stderr, "checking gcry_kdf_derive test vector %d algo %d for FIPS\n", ++ tvidx, tv[tvidx].algo); ++ assert (tv[tvidx].dklen <= sizeof outbuf); ++ err = gcry_kdf_derive (tv[tvidx].p, tv[tvidx].plen, ++ tv[tvidx].algo, tv[tvidx].subalgo, ++ tv[tvidx].salt, tv[tvidx].saltlen, ++ tv[tvidx].iterations, tv[tvidx].dklen, outbuf); ++ ++ if (err) ++ { ++ fail ("gcry_kdf_derive test %d unexpectedly returned an error in FIPS mode: %s\n", ++ tvidx, gpg_strerror (err)); ++ } ++ else ++ { ++ gpg_err_code_t ec; ++ ++ ec = gcry_get_fips_service_indicator (); ++ if (ec == GPG_ERR_INV_OP) ++ { ++ /* libgcrypt is old, no support of the FIPS service indicator. */ ++ fail ("gcry_kdf_derive test %d unexpectedly failed to check the FIPS service indicator.\n", ++ tvidx); ++ continue; ++ } ++ ++ if (!tv[tvidx].expect_failure && ec) ++ { ++ /* Success with the FIPS service indicator == 0 expected, but != 0. */ ++ fail ("gcry_kdf_derive test %d unexpectedly set the indicator in FIPS mode.\n", ++ tvidx); ++ continue; ++ } ++ else if (tv[tvidx].expect_failure && !ec && in_fips_mode) ++ { ++ /* Success with the FIPS service indicator != 0 expected, but == 0. */ ++ fail ("gcry_kdf_derive test %d unexpectedly cleared the indicator in FIPS mode.\n", ++ tvidx); ++ continue; ++ } ++ ++ if (memcmp (outbuf, tv[tvidx].dk, tv[tvidx].dklen)) ++ { ++ fail ("gcry_kdf_derive test %d failed: mismatch\n", tvidx); ++ fputs ("got:", stderr); ++ for (i=0; i < tv[tvidx].dklen; i++) ++ fprintf (stderr, " %02x", outbuf[i]); ++ putc ('\n', stderr); ++ } ++ } ++ } ++} ++ ++ + int + main (int argc, char **argv) + { +@@ -495,6 +653,7 @@ main (int argc, char **argv) + check_digests (); + check_md_o_w_r_c (); + check_mac_o_w_r_c (); ++ check_kdf_derive (); + + return !!error_count; + } +Index: libgcrypt-1.11.0/tests/t-kdf.c +=================================================================== +--- libgcrypt-1.11.0.orig/tests/t-kdf.c ++++ libgcrypt-1.11.0/tests/t-kdf.c +@@ -1927,163 +1927,6 @@ check_fips_indicators (void) + } + + +-static void +-check_fips_gcry_kdf_derive (void) +-{ +- static struct { +- const char *p; /* Passphrase. */ +- size_t plen; /* Length of P. */ +- int algo; +- int subalgo; +- const char *salt; +- size_t saltlen; +- unsigned long iterations; +- int dklen; /* Requested key length. */ +- const char *dk; /* Derived key. */ +- int expect_failure; +- } tv[] = { +- { +- "passwordPASSWORDpassword", 24, +- GCRY_KDF_PBKDF2, GCRY_MD_SHA1, +- "saltSALTsaltSALTsaltSALTsaltSALTsalt", 36, +- 4096, +- 25, +- "\x3d\x2e\xec\x4f\xe4\x1c\x84\x9b\x80\xc8" +- "\xd8\x36\x62\xc0\xe4\x4a\x8b\x29\x1a\x96" +- "\x4c\xf2\xf0\x70\x38", +- 0 +- }, +- { +- "pleaseletmein", 13, +- GCRY_KDF_SCRYPT, 16384, +- "SodiumChloride", 14, +- 1, +- 64, +- "\x70\x23\xbd\xcb\x3a\xfd\x73\x48\x46\x1c\x06\xcd\x81\xfd\x38\xeb" +- "\xfd\xa8\xfb\xba\x90\x4f\x8e\x3e\xa9\xb5\x43\xf6\x54\x5d\xa1\xf2" +- "\xd5\x43\x29\x55\x61\x3f\x0f\xcf\x62\xd4\x97\x05\x24\x2a\x9a\xf9" +- "\xe6\x1e\x85\xdc\x0d\x65\x1e\x40\xdf\xcf\x01\x7b\x45\x57\x58\x87", +- 1 /* not-compliant because unallowed algo */ +- }, +- { +- "passwor", 7, +- GCRY_KDF_PBKDF2, GCRY_MD_SHA1, +- "saltSALTsaltSALTsaltSALTsaltSALTsalt", 36, +- 4096, +- 25, +- "\xf4\x93\xee\x2b\xbf\x44\x0b\x9e\x64\x53" +- "\xc2\xb3\x87\xdc\x73\xf8\xfd\xe6\x97\xda" +- "\xb8\x24\xa0\x26\x50", +- 1 /* not-compliant because passphrase len is too small */ +- }, +- { +- "passwordPASSWORDpassword", 24, +- GCRY_KDF_PBKDF2, GCRY_MD_SHA1, +- "saltSALTsaltSAL", 15, +- 4096, +- 25, +- "\x14\x05\xa4\x2a\xf4\xa8\x12\x14\x7b\x65" +- "\x8f\xaa\xf0\x7f\x25\xe5\x0f\x0b\x2b\xb7" +- "\xcf\x8d\x29\x23\x4b", +- 1 /* not-compliant because salt len is too small */ +- }, +- { +- "passwordPASSWORDpassword", 24, +- GCRY_KDF_PBKDF2, GCRY_MD_SHA1, +- "saltSALTsaltSALTsaltSALTsaltSALTsalt", 36, +- 999, +- 25, +- "\xac\xf8\xb4\x67\x41\xc7\xf3\xd1\xa0\xc0" +- "\x08\xbe\x9b\x23\x96\x78\xbd\x93\xda\x4a" +- "\x30\xd4\xfb\xf0\x33", +- 1 /* not-compliant because too few iterations */ +- }, +- { +- "passwordPASSWORDpassword", 24, +- GCRY_KDF_PBKDF2, GCRY_MD_SHA1, +- "saltSALTsaltSALTsaltSALTsaltSALTsalt", 36, +- 4096, +- 13, +- "\x3d\x2e\xec\x4f\xe4\x1c\x84\x9b\x80\xc8" +- "\xd8\x36\x62", +- 1 /* not-compliant because key size too small */ +- }, +- { +- "passwordPASSWORDpassword", 24, +- GCRY_KDF_PBKDF2, GCRY_MD_BLAKE2B_512, +- "saltSALTsaltSALTsaltSALTsaltSALTsalt", 36, +- 4096, +- 60, +- "\xa4\x6b\x53\x35\xdb\xdd\xa3\xd2\x5d\x19\xbb\x11\xfe\xdd\xd9\x9e" +- "\x45\x2a\x7c\x34\x47\x41\x98\xca\x31\x74\xb6\x34\x22\xac\x83\xb0" +- "\x38\x6e\xf5\x93\x0f\xf5\x16\x46\x0b\x97\xdc\x6c\x27\x5b\xe7\x25" +- "\xc2\xcb\xec\x50\x02\xc6\x52\x8b\x34\x68\x53\x65", +- 1 /* not-compliant because subalgo is not the one of approved */ +- } +- }; +- +- int tvidx; +- gpg_error_t err; +- unsigned char outbuf[100]; +- int i; +- +- for (tvidx=0; tvidx < DIM(tv); tvidx++) +- { +- if (verbose) +- fprintf (stderr, "checking gcry_kdf_derive test vector %d algo %d for FIPS\n", +- tvidx, tv[tvidx].algo); +- assert (tv[tvidx].dklen <= sizeof outbuf); +- err = gcry_kdf_derive (tv[tvidx].p, tv[tvidx].plen, +- tv[tvidx].algo, tv[tvidx].subalgo, +- tv[tvidx].salt, tv[tvidx].saltlen, +- tv[tvidx].iterations, tv[tvidx].dklen, outbuf); +- +- if (err) +- { +- fail ("gcry_kdf_derive test %d unexpectedly returned an error in FIPS mode: %s\n", +- tvidx, gpg_strerror (err)); +- } +- else +- { +- gpg_err_code_t ec; +- +- ec = gcry_get_fips_service_indicator (); +- if (ec == GPG_ERR_INV_OP) +- { +- /* libgcrypt is old, no support of the FIPS service indicator. */ +- fail ("gcry_kdf_derive test %d unexpectedly failed to check the FIPS service indicator.\n", +- tvidx); +- continue; +- } +- +- if (!tv[tvidx].expect_failure && ec) +- { +- /* Success with the FIPS service indicator == 0 expected, but != 0. */ +- fail ("gcry_kdf_derive test %d unexpectedly set the indicator in FIPS mode.\n", +- tvidx); +- continue; +- } +- else if (tv[tvidx].expect_failure && !ec) +- { +- /* Success with the FIPS service indicator != 0 expected, but == 0. */ +- fail ("gcry_kdf_derive test %d unexpectedly cleared the indicator in FIPS mode.\n", +- tvidx); +- continue; +- } +- +- if (memcmp (outbuf, tv[tvidx].dk, tv[tvidx].dklen)) +- { +- fail ("gcry_kdf_derive test %d failed: mismatch\n", tvidx); +- fputs ("got:", stderr); +- for (i=0; i < tv[tvidx].dklen; i++) +- fprintf (stderr, " %02x", outbuf[i]); +- putc ('\n', stderr); +- } +- } +- } +-} +- +- + int + main (int argc, char **argv) + { +@@ -2166,8 +2009,6 @@ main (int argc, char **argv) + check_hkdf (); + if (in_fips_mode) + check_fips_indicators (); +- if (in_fips_mode) +- check_fips_gcry_kdf_derive (); + } + + return error_count ? 1 : 0; diff --git a/libgcrypt-tests-fips-Rename-t-fips-service-ind.patch b/libgcrypt-tests-fips-Rename-t-fips-service-ind.patch new file mode 100644 index 0000000..bb32094 --- /dev/null +++ b/libgcrypt-tests-fips-Rename-t-fips-service-ind.patch @@ -0,0 +1,60 @@ +From 132f346232b33fe41ffee3b3870ec189626676e7 Mon Sep 17 00:00:00 2001 +From: NIIBE Yutaka +Date: Mon, 16 Dec 2024 14:14:24 +0900 +Subject: [PATCH 07/19] tests,fips: Rename t-fips-service-ind. +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* tests/t-fips-service-ind.c: Rename from t-digest.c. +* tests/Makefile.am (tests_bin): Follow the change. + +-- + +GnuPG-bug-id: 7338 +Signed-off-by: NIIBE Yutaka +Signed-off-by: Lucas Mülling +--- + tests/Makefile.am | 2 +- + tests/{t-digest.c => t-fips-service-ind.c} | 4 ++-- + 2 files changed, 3 insertions(+), 3 deletions(-) + rename tests/{t-digest.c => t-fips-service-ind.c} (99%) + +diff --git a/tests/Makefile.am b/tests/Makefile.am +index 93774fe9..3170a58e 100644 +--- a/tests/Makefile.am ++++ b/tests/Makefile.am +@@ -25,7 +25,7 @@ tests_bin = \ + version t-secmem mpitests t-sexp t-convert \ + t-mpi-bit t-mpi-point t-lock \ + prime basic keygen pubkey hmac hashtest t-kdf keygrip \ +- aeswrap random t-kem t-mlkem t-thread-local t-digest ++ aeswrap random t-kem t-mlkem t-thread-local t-fips-service-ind + + if USE_RSA + tests_bin += pkcs1v2 t-rsa-pss t-rsa-15 t-rsa-testparm +diff --git a/tests/t-digest.c b/tests/t-fips-service-ind.c +similarity index 99% +rename from tests/t-digest.c +rename to tests/t-fips-service-ind.c +index e2b1ce32..31c1fc72 100644 +--- a/tests/t-digest.c ++++ b/tests/t-fips-service-ind.c +@@ -1,4 +1,4 @@ +-/* t-digest.c - MD regression tests ++/* t-fips-service-ind.c - FIPS service indicator regression tests + * Copyright (C) 2024 g10 Code GmbH + * + * This file is part of Libgcrypt. +@@ -27,7 +27,7 @@ + #include + #include + +-#define PGM "t-digest" ++#define PGM "t-fips-service-ind" + + #include "t-common.h" + static int in_fips_mode; +-- +2.49.0 + diff --git a/libgcrypt.changes b/libgcrypt.changes new file mode 100644 index 0000000..55e060b --- /dev/null +++ b/libgcrypt.changes @@ -0,0 +1,2013 @@ +------------------------------------------------------------------- +Thu Jun 5 13:23:03 UTC 2025 - Angel Yankov + +- Security fix [bsc#1221107, CVE-2024-2236] + * Add --enable-marvin-workaround to spec to enable workaround + * Fix timing based side-channel in RSA implementation ( Marvin attack ) + * Add libgcrypt-CVE-2024-2236.patch + +------------------------------------------------------------------- +Thu May 8 14:28:42 UTC 2025 - Lucas Mulling + +- Update to 1.11.1: [jsc#PED-12227] + * Bug fixes: + - Fix Kyber secret-dependent branch introduced by recent versions of Clang. [rCf765778e82] + - Fix build regression due to the use of AVX512 in Blake. [T7184] + - Do not build i386 asm on amd64 and vice versa. [T7220] + - Fix build regression on armhf with gcc-14. [T7226] + - Return the proper error code on malloc failure in hex2buffer. [rCc51151f5b0] + - Fix long standing bug for PRIME % 2 == 0. [rC639b0fca15] + * Performance: + - Add AES Vector Permute intrinsics implementation for AArch64. [rC94a63aedbb] + - Add GHASH AArch64/SIMD intrinsics implementation. [rCfec871fd18] + - Add RISC-V vector permute AES. [rCb24ebd6163] + - Add GHASH RISC-V Zbb+Zbc implementation. [rC0f1fec12b0] + - Add ChaCha20 RISC-V vector intrinsics implementation. [rC8dbee93ac2] + - Add SHA3 acceleration for RISC-V Zbb extension. [rC1a660068ba] + * Other: + - Add CET support for i386 and amd64 assembly. [T7220] + - Add PAC/BTI support for AArch64 asm. [T7220] + - Apply changes to Kyber from upstream for final FIPS 203. [rCcc95c36e7f] + - Introduce an internal API for a revampled FIPS service indicator. [T7340] + - Several improvements for constant time operation by the introduction of + Least Leak Intended (LLI) variants of internal functions. [T7519,T7490] + * Add libgcrypt-1.11.1-public-SLI-API.patch + * Rebase patches: + - libgcrypt-FIPS-SLI-hash-mac.patch + - libgcrypt-FIPS-SLI-pk.patch + - libgcrypt-FIPS-jitter-standalone.patch + * Remove patches: + - libgcrypt-fips-Introduce-an-internal-API-for-FIPS-service-indicator.patch + - libgcrypt-fips-Introduce-GCRYCTL_FIPS_SERVICE_INDICATOR-and-the-macro.patch + - libgcrypt-fips-kdf-Implement-new-FIPS-service-indicator-for-gcry_kdf_derive.patch + - libgcrypt-fips-md-Implement-new-FIPS-service-indicator-for-gcry_md_hash_.patch + - libgcrypt-fips-tests-Add-t-digest.patch + - libgcrypt-fips-Change-the-internal-API-for-new-FIPS-service-indicator.patch + - libgcrypt-fips-md-Implement-new-FIPS-service-indicator-for-gcry_md_open-API.patch + - libgcrypt-fips-tests-Add-tests-for-md_open-write-read-close-for-t-digest.patch + - libgcrypt-fips-mac-Implement-new-FIPS-service-indicator-for-gcry_mac_open.patch + - libgcrypt-fips-cipher-Implement-new-FIPS-service-indicator-for-cipher_open.patch + - libgcrypt-tests-fips-Add-gcry_mac_open-tests.patch + - libgcrypt-tests-fips-Rename-t-fips-service-ind.patch + - libgcrypt-tests-fips-Move-KDF-tests-to-t-fips-service-ind.patch + - libgcrypt-tests-fips-Add-gcry_cipher_open-tests.patch + - libgcrypt-fips-md-gcry_md_copy-should-care-about-FIPS-service-indicator.patch + - libgcrypt-fips-cipher-Implement-FIPS-service-indicator-for-gcry_pk_hash_-API.patch + - libgcrypt-fips-Introduce-GCRYCTL_FIPS_REJECT_NON_FIPS.patch + - libgcrypt-Fix-the-previous-change.patch + - libgcrypt-fips-Rejection-by-GCRYCTL_FIPS_REJECT_NON_FIPS-not-by-open-flags.patch + - libgcrypt-fips-cipher-Add-behavior-not-to-reject-but-mark-non-compliant.patch + - libgcrypt-fips-ecc-Add-rejecting-or-marking-for-gcry_pk_get_curve.patch + - libgcrypt-tests-Add-more-tests-to-tests-t-fips-service-ind.patch + - libgcrypt-fips-ecc-Check-DATA-in-gcry_pk_sign-verify-in-FIPS-mode.patch + - libgcrypt-fips-cipher-Fix-memory-leak-for-gcry_pk_hash_sign.patch + - libgcrypt-build-Improve-__thread-specifier-check.patch + - libgcrypt-cipher-Check-and-mark-non-compliant-cipher-modes-in-the-SLI.patch + - libgcrypt-cipher-Rename-_gcry_cipher_is_mode_fips_compliant.patch + - libgcrypt-cipher-Don-t-differentiate-GCRY_CIPHER_MODE_CMAC-in-FIPS-mode.patch + - libgcrypt-cipher-rsa-Mark-reject-SHA1-unknown-with-RSA-signature-generation.patch + - libgcrypt-md-Fix-gcry_md_algo_info-to-mark-reject-under-FIPS-mode.patch + - libgcrypt-md-Use-check_digest_algo_spec-in-_gcry_md_selftest.patch + - libgcrypt-tests-Update-t-fips-service-ind-using-GCRY_MD_SHA256-for-KDF-tests.patch + - libgcrypt-fips-cipher-Do-the-computation-when-marking-non-compliant.patch + - libgcrypt-tests-Allow-tests-with-USE_RSA.patch + - libgcrypt-cipher-Add-KAT-for-non-rfc6979-ECDSA-with-fixed-k.patch + - libgcrypt-cipher-Differentiate-use-of-label-K-in-the-SLI.patch + - libgcrypt-cipher-Differentiate-igninvflag-in-the-SLI.patch + - libgcrypt-cipher-Differentiate-no-blinding-flag-in-the-SLI.patch + - libgcrypt-fips-cipher-Add-GCRY_FIPS_FLAG_REJECT_PK_FLAGS.patch + - libgcrypt-cipher-ecc-Fix-for-supplied-K.patch + - libgcrypt-cipher-visibility-Differentiate-use-of-random-override-in-the-SLI.patch + - libgcrypt-cipher-fips-Fix-for-random-override.patch + - libgcrypt-md-Make-SHA-1-non-FIPS-internally-for-1.12-API.patch + - libgcrypt-fips-Fix-GCRY_FIPS_FLAG_REJECT_MD.patch + - libgcrypt-doc-Add-about-GCRYCTL_FIPS_SERVICE_INDICATOR.patch + - libgcrypt-doc-Fix-syntax-error.patch + - libgcrypt-Disable-SHA3-s390x-acceleration-for-CSHAKE.patch + +------------------------------------------------------------------- +Tue May 6 07:24:14 UTC 2025 - Pedro Monreal + +- CSHAKE basic regression test failure in s390x [bsc#1242419] + * Disable SHA3 s390x acceleration for CSHAKE [rC2486d9b5ae01] + * Add libgcrypt-Disable-SHA3-s390x-acceleration-for-CSHAKE.patch + +------------------------------------------------------------------- +Sun Apr 13 20:10:16 UTC 2025 - Lucas Mulling + +- Differentiate use of SHA1 in the service level indicator [jsc#PED-12227] + * Include upstream SLI revamp and fips certification fixes + * Add patches: + - libgcrypt-fips-Introduce-an-internal-API-for-FIPS-service-indicator.patch + - libgcrypt-fips-Introduce-GCRYCTL_FIPS_SERVICE_INDICATOR-and-the-macro.patch + - libgcrypt-fips-kdf-Implement-new-FIPS-service-indicator-for-gcry_kdf_derive.patch + - libgcrypt-fips-md-Implement-new-FIPS-service-indicator-for-gcry_md_hash_.patch + - libgcrypt-fips-tests-Add-t-digest.patch + - libgcrypt-fips-Change-the-internal-API-for-new-FIPS-service-indicator.patch + - libgcrypt-fips-md-Implement-new-FIPS-service-indicator-for-gcry_md_open-API.patch + - libgcrypt-fips-tests-Add-tests-for-md_open-write-read-close-for-t-digest.patch + - libgcrypt-fips-mac-Implement-new-FIPS-service-indicator-for-gcry_mac_open.patch + - libgcrypt-fips-cipher-Implement-new-FIPS-service-indicator-for-cipher_open.patch + - libgcrypt-tests-fips-Add-gcry_mac_open-tests.patch + - libgcrypt-tests-fips-Rename-t-fips-service-ind.patch + - libgcrypt-tests-fips-Move-KDF-tests-to-t-fips-service-ind.patch + - libgcrypt-tests-fips-Add-gcry_cipher_open-tests.patch + - libgcrypt-fips-md-gcry_md_copy-should-care-about-FIPS-service-indicator.patch + - libgcrypt-fips-cipher-Implement-FIPS-service-indicator-for-gcry_pk_hash_-API.patch + - libgcrypt-fips-Introduce-GCRYCTL_FIPS_REJECT_NON_FIPS.patch + - libgcrypt-Fix-the-previous-change.patch + - libgcrypt-fips-Rejection-by-GCRYCTL_FIPS_REJECT_NON_FIPS-not-by-open-flags.patch + - libgcrypt-fips-cipher-Add-behavior-not-to-reject-but-mark-non-compliant.patch + - libgcrypt-fips-ecc-Add-rejecting-or-marking-for-gcry_pk_get_curve.patch + - libgcrypt-tests-Add-more-tests-to-tests-t-fips-service-ind.patch + - libgcrypt-fips-ecc-Check-DATA-in-gcry_pk_sign-verify-in-FIPS-mode.patch + - libgcrypt-fips-cipher-Fix-memory-leak-for-gcry_pk_hash_sign.patch + - libgcrypt-build-Improve-__thread-specifier-check.patch + - libgcrypt-cipher-Check-and-mark-non-compliant-cipher-modes-in-the-SLI.patch + - libgcrypt-cipher-Rename-_gcry_cipher_is_mode_fips_compliant.patch + - libgcrypt-cipher-Don-t-differentiate-GCRY_CIPHER_MODE_CMAC-in-FIPS-mode.patch + - libgcrypt-cipher-rsa-Mark-reject-SHA1-unknown-with-RSA-signature-generation.patch + - libgcrypt-md-Fix-gcry_md_algo_info-to-mark-reject-under-FIPS-mode.patch + - libgcrypt-md-Use-check_digest_algo_spec-in-_gcry_md_selftest.patch + - libgcrypt-tests-Update-t-fips-service-ind-using-GCRY_MD_SHA256-for-KDF-tests.patch + - libgcrypt-fips-cipher-Do-the-computation-when-marking-non-compliant.patch + - libgcrypt-tests-Allow-tests-with-USE_RSA.patch + - libgcrypt-cipher-Add-KAT-for-non-rfc6979-ECDSA-with-fixed-k.patch + - libgcrypt-cipher-Differentiate-use-of-label-K-in-the-SLI.patch + - libgcrypt-cipher-Differentiate-igninvflag-in-the-SLI.patch + - libgcrypt-cipher-Differentiate-no-blinding-flag-in-the-SLI.patch + - libgcrypt-fips-cipher-Add-GCRY_FIPS_FLAG_REJECT_PK_FLAGS.patch + - libgcrypt-cipher-ecc-Fix-for-supplied-K.patch + - libgcrypt-cipher-visibility-Differentiate-use-of-random-override-in-the-SLI.patch + - libgcrypt-cipher-fips-Fix-for-random-override.patch + - libgcrypt-md-Make-SHA-1-non-FIPS-internally-for-1.12-API.patch + - libgcrypt-fips-Fix-GCRY_FIPS_FLAG_REJECT_MD.patch + - libgcrypt-doc-Add-about-GCRYCTL_FIPS_SERVICE_INDICATOR.patch + - libgcrypt-doc-Fix-syntax-error.patch + * Rebase patches: + - libgcrypt-FIPS-SLI-kdf-leylength.patch + +------------------------------------------------------------------- +Tue Jan 7 09:28:25 UTC 2025 - Pedro Monreal + +- Fix redefinition error of 'rol64'. Remove not used rol64() + definition after removing the built-in jitter rng. + * Add libgcrypt-rol64-redefinition.patch + +------------------------------------------------------------------- +Mon Dec 2 10:11:10 UTC 2024 - Pedro Monreal + +- Remove unrecognized option: --enable-m-guard + +------------------------------------------------------------------- +Thu Jun 20 08:11:07 UTC 2024 - Pedro Monreal + +- Update to 1.11.0: + * New and extended interfaces: + - Add an API for Key Encapsulation Mechanism (KEM). [T6755] + - Add Streamlined NTRU Prime sntrup761 algorithm. [rCcf9923e1a5] + - Add Kyber algorithm according to FIPS 203 ipd 2023-08-24. [rC18e5c0d268] + - Add Classic McEliece algorithm. [rC003367b912] + - Add One-Step KDF with hash and MAC. [T5964] + - Add KDF algorithm HKDF of RFC-5869. [T5964] + - Add KDF algorithm X963KDF for use in CMS. [rC3abac420b3] + - Add GMAC-SM4 and Poly1305-SM4. [rCd1ccc409d4] + - Add ARIA block cipher algorithm. [rC316c6d7715] + - Add explicit FIPS indicators for MD and MAC algorithms. [T6376] + - Add support for SHAKE as MGF in RSA. [T6557] + - Add gcry_md_read support for SHAKE algorithms. [T6539] + - Add gcry_md_hash_buffers_ext function. [T7035] + - Add cSHAKE hash algorithm. [rC065b3f4e02] + - Support internal generation of IV for AEAD cipher mode. [T4873] + * Performance: + - Add SM3 ARMv8/AArch64/CE assembly implementation. [rCfe891ff4a3] + - Add SM4 ARMv8/AArch64 assembly implementation. [rCd8825601f1] + - Add SM4 GFNI/AVX2 and GFI/AVX512 implementation. [rC5095d60af4,rCeaed633c16] + - Add SM4 ARMv9 SVE CE assembly implementation. [rC2dc2654006] + - Add PowerPC vector implementation of SM4. [rC0b2da804ee] + - Optimize ChaCha20 and Poly1305 for PPC P10 LE. [T6006] + - Add CTR32LE bulk acceleration for AES on PPC. [rC84f2e2d0b5] + - Add generic bulk acceleration for CTR32LE mode (GCM-SIV) for SM4 + and Camellia. [rCcf956793af] + - Add GFNI/AVX2 implementation of Camellia. [rC4e6896eb9f] + - Add AVX2 and AVX512 accelerated implementations for GHASH (GCM) + and POLYVAL (GCM-SIV). [rCd857e85cb4, rCe6f3600193] + - Add AVX512 implementation for SHA512. [rC089223aa3b] + - Add AVX512 implementation for Serpent. [rCce95b6ec35] + - Add AVX512 implementation for Poly1305 and ChaCha20. [rCcd3ed49770, rC9a63cfd617] + - Add AVX512 accelerated implementation for SHA3 and Blake2. [rCbeaad75f46,rC909daa700e] + - Add VAES/AVX2 accelerated i386 implementation for AES. [rC4a42a042bc] + - Add bulk processing for XTS mode of Camellia and SM4. [rC32b18cdb87, rCaad3381e93] + - Accelerate XTS and ECB modes for Twofish and Serpent. [rCd078a928f5,rC8a1fe5f78f] + - Add AArch64 crypto/SHA512 extension implementation for SHA512. [rCe51d3b8330] + - Add AArch64 crypto-extension implementation for Camellia. [rC898c857206] + - Accelerate OCB authentication on AMD with AVX2. [rC6b47e85d65] + * Bug fixes: + - For PowerPC check for missing optimization level for vector register usage. [T5785] + - Fix EdDSA secret key check. [T6511] + - Fix decoding of PKCS#1-v1.5 and OAEP padding. [rC34c2042792] + - Allow use of PKCS#1-v1.5 with SHA3 algorithms. [T6976] + - Fix AESWRAP padding length check. [T7130] + * Other: + - Allow empty password for Argon2 KDF. [rCa20700c55f] + - Various constant time operation imporvements. + - Add "bp256", "bp384", "bp512" aliases for Brainpool curves. + - Support for the random server has been removed. [T5811] + - The control code GCRYCTL_ENABLE_M_GUARD is deprecated and not + supported any more. Please use valgrind or other tools. [T5822] + - Logging is now done via the libgpg-error logging functions. [rCab0bdc72c7] + * Remove patches fixed upstream: + - libgcrypt-no-deprecated-grep-alias.patch + - libgcrypt-Chacha20-poly1305-Optimized-chacha20-poly1305.patch + - libgcrypt-ppc-enable-P10-assembly-with-ENABLE_FORCE_SOF.patch + * Rebase patches: + - libgcrypt-FIPS-jitter-errorcodes.patch + - libgcrypt-FIPS-jitter-whole-entropy.patch + +------------------------------------------------------------------- +Wed Mar 20 20:31:40 UTC 2024 - Pedro Monreal + +- FIPS: Make sure that Libgcrypt makes use of the built-in Jitter RNG + for the whole length entropy buffer in FIPS mode. [bsc#1220893] + * Add libgcrypt-FIPS-jitter-whole-entropy.patch + +------------------------------------------------------------------- +Wed Mar 20 15:13:04 UTC 2024 - Pedro Monreal + +- FIPS: Set the FSM into error state if Jitter RNG is returning an + error code to the caller when an health test error occurs when + random bytes are requested through the jent_read_entropy_safe() + function. [bsc#1220895] + * Add libgcrypt-FIPS-jitter-errorcodes.patch + +------------------------------------------------------------------- +Mon Mar 11 16:02:55 UTC 2024 - Pedro Monreal + +- FIPS: Replace the built-in jitter rng with standalone version + * Remove the internal jitterentropy copy [bsc#1220896] + * Add libgcrypt-FIPS-jitter-standalone.patch + * Remove not needed libgcrypt-jitterentropy-3.4.0.patch + +------------------------------------------------------------------- +Mon Feb 26 12:13:56 UTC 2024 - Pedro Monreal + +- Update upstream libgcrypt.keyring + +------------------------------------------------------------------- +Sat Jan 27 13:37:34 UTC 2024 - Dirk Müller + +- add libgcrypt-no-deprecated-grep-alias.patch + +------------------------------------------------------------------- +Tue Nov 21 10:36:09 UTC 2023 - Otto Hollmann + +- Re-create HMAC checksum after RPM build strips the library + (bsc#1217058) + +------------------------------------------------------------------- +Wed Nov 15 09:54:00 UTC 2023 - Pedro Monreal + +- Update to 1.10.3: + * Bug fixes: + - Fix public key computation for other EdDSA curves. [rC469919751d6e] + - Remove out of core handler diagnostic in FIPS mode. [T6515] + - Check that the digest size is not zero in gcry_pk_sign_md and + gcry_pk_verify_md. [T6539] + - Make store an s-exp with \0 is considered to be binary. [T6747] + - Various constant-time improvements. + * Portability: + - Use getrandom call only when supported by the platform. [T6442] + - Change the default for --with-libtool-modification to never. [T6619] + * Release-info: https://dev.gnupg.org/T6817 + * Remove patch upstream libgcrypt-1.10.0-out-of-core-handler.patch + +------------------------------------------------------------------- +Tue Oct 17 10:27:15 UTC 2023 - Pedro Monreal + +- Do not pull revision info from GIT when autoconf is run. This + removes the -unknown suffix after the version number. + * Add libgcrypt-nobetasuffix.patch [bsc#1216334] + +------------------------------------------------------------------- +Tue Oct 3 12:58:41 UTC 2023 - Pedro Monreal + +- POWER: performance enhancements for cryptography [jsc#PED-5088] + * Optimize Chacha20 and Poly1305 for PPC P10 LE: [T6006] + - Chacha20/poly1305: Optimized chacha20/poly1305 for + P10 operation [rC88fe7ac33eb4] + - ppc: enable P10 assembly with ENABLE_FORCE_SOFT_HWFEATURES + on arch-3.00 [rC2c5e5ab6843d] + * Add patches: + - libgcrypt-Chacha20-poly1305-Optimized-chacha20-poly1305.patch + - libgcrypt-ppc-enable-P10-assembly-with-ENABLE_FORCE_SOF.patch + +------------------------------------------------------------------- +Mon May 22 11:32:53 UTC 2023 - Pedro Monreal + +- FIPS: Merge the libgcrypt20-hmac package into the library and + remove the "module is complete" trigger file .fips [bsc#1185116] + * Remove libgcrypt-1.10.0-use-fipscheck.patch + +------------------------------------------------------------------- +Tue Apr 11 14:08:24 UTC 2023 - Pedro Monreal + +- Update to 1.10.2: + * Bug fixes: + - Fix Argon2 for the case output > 64. [rC13b5454d26] + - Fix missing HWF_PPC_ARCH_3_10 in HW feature. [rCe073f0ed44] + - Fix RSA key generation failure in forced FIPS mode. [T5919] + - Fix gcry_pk_hash_verify for explicit hash. [T6066] + - Fix a wrong result of gcry_mpi_invm. [T5970] + - Allow building with --disable-asm for HPPA. [T5976] + - Allow building with -Oz. [T6432] + - Enable the fast path to ChaCha20 only when supported. [T6384] + - Use size_t to avoid counter overflow in Keccak when directly + feeding more than 4GiB. [T6217] + * Other: + - Do not use secure memory for a DRBG instance. [T5933] + - Do not allow PKCS#1.5 padding for encryption in FIPS mode. [T5918] + - Fix the behaviour for child process re-seeding in the DRBG. [rC019a40c990] + - Allow verification of small RSA signatures in FIPS mode. [T5975] + - Allow the use of a shorter salt for KDFs in FIPS mode. [T6039] + - Run digest+sign self tests for RSA and ECC in FIPS mode. [rC06c9350165] + - Add function-name based FIPS indicator function. + GCRYCTL_FIPS_SERVICE_INDICATOR_FUNCTION. This is not considered + an ABI changes because the new FIPS features were not yet + approved. [rC822ee57f07] + - Improve PCT in FIPS mode. [rC285bf54b1a, rC4963c127ae, T6397] + - Use getrandom (GRND_RANDOM) in FIPS mode. [rCcf10c74bd9] + - Disable RSA-OAEP padding in FIPS mode. [rCe5bfda492a] + - Check minimum allowed key size in PBKDF in FIPS mode. [T6039,T6219] + - Get maximum 32B of entropy at once in FIPS mode. [rCce0df08bba] + - Prefer gpgrt-config when available. [T5034] + - Mark AESWRAP as approved FIPS algorithm. [T5512] + - Prevent usage of long salt for PSS in FIPS mode. [rCfdd2a8b332] + - Prevent usage of X9.31 keygen in FIPS mode. [rC392e0ccd25] + - Remove GCM mode from the allowed FIPS indicators. [rC1540698389] + - Add explicit FIPS indicators for hash and MAC algorithms. [T6376] + * Release-info: https://dev.gnupg.org/T5905 + * Rebase FIPS patches: + - libgcrypt-FIPS-SLI-hash-mac.patch + - libgcrypt-FIPS-SLI-kdf-leylength.patch + - libgcrypt-FIPS-SLI-pk.patch + +------------------------------------------------------------------- +Wed Mar 8 10:34:34 UTC 2023 - Martin Pluskal + +- Build AVX2 enabled hwcaps library for x86_64-v3 + +------------------------------------------------------------------- +Wed Oct 19 14:01:24 UTC 2022 - Pedro Monreal + +- Update to 1.10.1: + * Bug fixes: + - Fix minor memory leaks in FIPS mode. + - Build fixes for MUSL libc. + * Other: + - More portable integrity check in FIPS mode. + - Add X9.62 OIDs to sha256 and sha512 modules. + * Add the hardware optimizations config file hwf.deny to + the /etc/gcrypt/ directory. This file can be used to globally + disable the use of hardware based optimizations. + * Remove not needed separate_hmac256_binary hmac256 package + +------------------------------------------------------------------- +Wed Sep 14 13:34:13 UTC 2022 - Pedro Monreal + +- Update to 1.10.0: + * New and extended interfaces: + - New control codes to check for FIPS 140-3 approved algorithms. + - New control code to switch into non-FIPS mode. + - New cipher modes SIV and GCM-SIV as specified by RFC-5297. + - Extended cipher mode AESWRAP with padding as specified by + RFC-5649. + - New set of KDF functions. + - New KDF modes Argon2 and Balloon. + - New functions for combining hashing and signing/verification. + * Performance: + - Improved support for PowerPC architectures. + - Improved ECC performance on zSeries/s390x by using accelerated + scalar multiplication. + - Many more assembler performance improvements for several + architectures. + * Bug fixes: + - Fix Elgamal encryption for other implementations. + [bsc#1190239, CVE-2021-40528] + - Check the input length of the point in ECDH. + - Fix an abort in gcry_pk_get_param for "Curve25519". + * Other features: + - The control code GCRYCTL_SET_ENFORCED_FIPS_FLAG is ignored + because it is useless with the FIPS 140-3 related changes. + - Update of the jitter entropy RNG code. + - Simplification of the entropy gatherer when using the getentropy + system call. + * Interface changes relative to the 1.10.0 release: + - GCRYCTL_SET_DECRYPTION_TAG NEW control code. + - GCRYCTL_FIPS_SERVICE_INDICATOR_CIPHER NEW control code. + - GCRYCTL_FIPS_SERVICE_INDICATOR_KDF NEW control code. + - GCRYCTL_NO_FIPS_MODE = 83 NEW control code. + - GCRY_CIPHER_MODE_SIV NEW mode. + - GCRY_CIPHER_MODE_GCM_SIV NEW mode. + - GCRY_CIPHER_EXTENDED NEW flag. + - GCRY_SIV_BLOCK_LEN NEW macro. + - gcry_cipher_set_decryption_tag NEW macro. + - GCRY_KDF_ARGON2 NEW constant. + - GCRY_KDF_BALLOON NEW constant. + - GCRY_KDF_ARGON2D NEW constant. + - GCRY_KDF_ARGON2I NEW constant. + - GCRY_KDF_ARGON2ID NEW constant. + - gcry_kdf_hd_t NEW type. + - gcry_kdf_job_fn_t NEW type. + - gcry_kdf_dispatch_job_fn_t NEW type. + - gcry_kdf_wait_all_jobs_fn_t NEW type. + - struct gcry_kdf_thread_ops NEW struct. + - gcry_kdf_open NEW function. + - gcry_kdf_compute NEW function. + - gcry_kdf_final NEW function. + - gcry_kdf_close NEW function. + - gcry_pk_hash_sign NEW function. + - gcry_pk_hash_verify NEW function. + - gcry_pk_random_override_new NEW function. + * Rebase libgcrypt-1.8.4-allow_FSM_same_state.patch and rename + to libgcrypt-1.10.0-allow_FSM_same_state.patch + * Remove unused CAVS tests and related patches: + - cavs_driver.pl cavs-test.sh + - libgcrypt-1.6.1-fips-cavs.patch + - drbg_test.patch + * Remove DSA sign/verify patches for the FIPS CAVS test since DSA + has been disabled in FIPS mode: + - libgcrypt-fipsdrv-enable-algo-for-dsa-sign.patch + - libgcrypt-fipsdrv-enable-algo-for-dsa-verify.patch + * Rebase libgcrypt-FIPS-SLI-pk.patch + * Rebase libgcrypt_indicators_changes.patch and + libgcrypt-indicate-shake.patch and merge both into + libgcrypt-FIPS-SLI-hash-mac.patch + * Rebase libgcrypt-FIPS-kdf-leylength.patch and rename to + libgcrypt-FIPS-SLI-kdf-leylength.patch + * Rebase libgcrypt-jitterentropy-3.4.0.patch + * Rebase libgcrypt-FIPS-rndjent_poll.patch + * Rebase libgcrypt-out-of-core-handler.patch and rename to + libgcrypt-1.10.0-out-of-core-handler.patch + * Since the FIPS .hmac file is now calculated with the internal + tool hmac256, only the "module is complete" trigger .fips file + is checked. Rename libgcrypt-1.6.1-use-fipscheck.patch + to libgcrypt-1.10.0-use-fipscheck.patch + * Remove patches fixed upstream: + - libgcrypt-1.4.1-rijndael_no_strict_aliasing.patch + - libgcrypt-1.5.0-LIBGCRYPT_FORCE_FIPS_MODE-env.diff + - libgcrypt-fix-rng.patch + - libgcrypt-1.8.3-fips-ctor.patch + - libgcrypt-1.8.4-use_xfree.patch + - libgcrypt-1.8.4-getrandom.patch + - libgcrypt-1.8.4-fips_ctor_skip_integrity_check.patch + - libgcrypt-dsa-rfc6979-test-fix.patch + - libgcrypt-fix-tests-fipsmode.patch + - libgcrypt-FIPS-RSA-DSA-ECDSA-hashing-operation.patch + - libgcrypt-1.8.4-fips-keygen.patch + - libgcrypt-invoke-global_init-from-constructor.patch + - libgcrypt-Restore-self-tests-from-constructor.patch + - libgcrypt-FIPS-GMAC_AES-benckmark.patch + - libgcrypt-global_init-constructor.patch + - libgcrypt-random_selftests-testentropy.patch + - libgcrypt-rsa-no-blinding.patch + - libgcrypt-ecc-ecdsa-no-blinding.patch + - libgcrypt-PCT-DSA.patch + - libgcrypt-PCT-ECC.patch + - libgcrypt-PCT-RSA.patch + - libgcrypt-fips_selftest_trigger_file.patch + - libgcrypt-pthread-in-t-lock-test.patch + - libgcrypt-FIPS-hw-optimizations.patch + - libgcrypt-FIPS-module-version.patch + - libgcrypt-FIPS-disable-3DES.patch + - libgcrypt-FIPS-fix-regression-tests.patch + - libgcrypt-FIPS-RSA-keylen.patch + - libgcrypt-FIPS-RSA-keylen-tests.patch + - libgcrypt-FIPS-fix-gcry_mpi_sub_ui.patch + - libgcrypt-FIPS-verify-unsupported-KDF-test.patch + - libgcrypt-FIPS-HMAC-short-keylen.patch + - libgcrypt-FIPS-service-indicators.patch + - libgcrypt-FIPS-disable-DSA.patch + - libgcrypt-jitterentropy-3.3.0.patch + - libgcrypt-FIPS-Zeroize-hmac.patch + * Update libgcrypt.keyring + +------------------------------------------------------------------- +Thu Sep 8 10:34:53 UTC 2022 - Pedro Monreal + +- FIPS: Get most of the entropy from rndjent_poll [bsc#1202117] + * Add libgcrypt-FIPS-rndjent_poll.patch + * Rebase libgcrypt-jitterentropy-3.4.0.patch + +------------------------------------------------------------------- +Wed Sep 7 22:03:51 UTC 2022 - Pedro Monreal + +- FIPS: Check keylength in gcry_fips_indicator_kdf() [bsc#1190700] + * Consider approved keylength greater or equal to 112 bits. + * Add libgcrypt-FIPS-kdf-leylength.patch + +------------------------------------------------------------------- +Wed Sep 7 12:53:14 UTC 2022 - Pedro Monreal + +- FIPS: Zeroize buffer and digest in check_binary_integrity() + * Add libgcrypt-FIPS-Zeroize-hmac.patch [bsc#1191020] + +------------------------------------------------------------------- +Tue Aug 23 09:19:00 UTC 2022 - Pedro Monreal + +- FIPS: gpg/gpg2 gets out of core handler in FIPS mode while + typing Tab key to Auto-Completion. [bsc#1182983] + * Add libgcrypt-out-of-core-handler.patch + +------------------------------------------------------------------- +Mon Aug 8 11:33:03 UTC 2022 - Pedro Monreal + +- FIPS: Port libgcrypt to use jitterentropy [bsc#1202117, jsc#SLE-24941] + * Enable the jitter based entropy generator by default in random.conf + - Add libgcrypt-jitterentropy-3.3.0.patch + * Update the internal jitterentropy to version 3.4.0 + - Add libgcrypt-jitterentropy-3.4.0.patch + +------------------------------------------------------------------- +Mon Aug 1 07:27:35 UTC 2022 - Stephan Kulow + +- Fix reproducible build problems: + - Do not use %release in binaries (but use SOURCE_DATE_EPOCH) + - Fix date call messed up by spec-cleaner + +------------------------------------------------------------------- +Thu Apr 14 12:30:36 UTC 2022 - Dennis Knorr + +- FIPS: extend the service indicator [bsc#1190700] + * introduced a pk indicator function + * adapted the approved and non approved ciphersuites + * Add libgcrypt_indicators_changes.patch + * Add libgcrypt-indicate-shake.patch + +------------------------------------------------------------------- +Tue Mar 22 12:32:09 UTC 2022 - Pedro Monreal + +- FIPS: Implement a service indicator for asymmetric ciphers [bsc#1190700] + * Mark RSA public key encryption and private key decryption with + padding (e.g. OAEP, PKCS) as non-approved since RSA-OAEP lacks + peer key assurance validation requirements per SP800-56Brev2. + * Mark ECC as approved only for NIST curves P-224, P-256, P-384 + and P-521 with check for common NIST names and aliases. + * Mark DSA, ELG, EDDSA, ECDSA and ECDH as non-approved. + * Add libgcrypt-FIPS-SLI-pk.patch + * Rebase libgcrypt-FIPS-service-indicators.patch +- Run the regression tests also in FIPS mode. + * Disable tests for non-FIPS approved algos. + * Rebase: libgcrypt-FIPS-verify-unsupported-KDF-test.patch + +------------------------------------------------------------------- +Tue Feb 1 11:28:51 UTC 2022 - Pedro Monreal + +- FIPS: Disable DSA in FIPS mode [bsc#1195385] + * Upstream task: https://dev.gnupg.org/T5710 + * Add libgcrypt-FIPS-disable-DSA.patch + +------------------------------------------------------------------- +Wed Jan 19 08:36:58 UTC 2022 - Pedro Monreal + +- FIPS: Service level indicator [bsc#1190700] + * Provide an indicator to check wether the service utilizes an + approved cryptographic algorithm or not. + * Add patches: + - libgcrypt-FIPS-service-indicators.patch + - libgcrypt-FIPS-verify-unsupported-KDF-test.patch + - libgcrypt-FIPS-HMAC-short-keylen.patch + +------------------------------------------------------------------- +Tue Dec 7 09:41:01 UTC 2021 - Pedro Monreal + +- FIPS: Fix gcry_mpi_sub_ui subtraction [bsc#1193480] + * gcry_mpi_sub_ui: fix subtracting from negative value + * Add libgcrypt-FIPS-fix-gcry_mpi_sub_ui.patch + +------------------------------------------------------------------- +Tue Nov 30 09:42:23 UTC 2021 - Pedro Monreal + +- FIPS: Define an entropy source SP800-90B compliant [bsc#1185140] + * Disable jitter entropy by default in random.conf + * Disable only-urandom option by default in random.conf + +------------------------------------------------------------------- +Fri Nov 26 13:10:29 UTC 2021 - Pedro Monreal + +- FIPS: RSA KeyGen/SigGen fail with 4096 bit key sizes [bsc#1192240] + * rsa: Check RSA keylen constraints for key operations. + * rsa: Fix regression in not returning an error for prime generation. + * tests: Add 2k RSA key working in FIPS mode. + * tests: pubkey: Replace RSA key to one of 2k. + * tests: pkcs1v2: Skip tests with small keys in FIPS. + * Add patches: + - libgcrypt-FIPS-RSA-keylen.patch + - libgcrypt-FIPS-RSA-keylen-tests.patch + +------------------------------------------------------------------- +Mon Nov 8 10:21:39 UTC 2021 - Pedro Monreal + +- FIPS: Disable 3DES/Triple-DES in FIPS mode [bsc#1185138] + * Add libgcrypt-FIPS-disable-3DES.patch + +------------------------------------------------------------------- +Tue Nov 2 11:31:19 UTC 2021 - Pedro Monreal + +- FIPS: PBKDF requirements [bsc#1185137] + * The PBKDF2 selftests were introduced in libgcrypt version + 1.9.1 in the function selftest_pbkdf2() + * Upstream task: https://dev.gnupg.org/T5182 + +------------------------------------------------------------------- +Thu Oct 28 19:48:06 UTC 2021 - Pedro Monreal + +- FIPS: Fix regression tests in FIPS mode [bsc#1192131] + * Add libgcrypt-FIPS-fix-regression-tests.patch + * Upstream task: https://dev.gnupg.org/T5520 + +------------------------------------------------------------------- +Thu Sep 21 11:25:06 UTC 2021 - Pedro Monreal + +- FIPS: Provide a module name/identifier and version that can be + mapped to the validation records. [bsc#1190706] + * Add libgcrypt-FIPS-module-version.patch + * Upstream task: https://dev.gnupg.org/T5600 + +------------------------------------------------------------------- +Thu Sep 21 10:23:44 UTC 2021 - Pedro Monreal + +- FIPS: Enable hardware support also in FIPS mode [bsc#1187110] + * Add libgcrypt-FIPS-hw-optimizations.patch + * Upstream task: https://dev.gnupg.org/T5508 + +------------------------------------------------------------------- +Mon Aug 23 12:08:24 UTC 2021 - Pedro Monreal + +- Update to 1.9.4: + * Bug fixes: + - Fix Elgamal encryption for other implementations. [CVE-2021-33560] + - Fix alignment problem on macOS. + - Check the input length of the point in ECDH. + - Fix an abort in gcry_pk_get_param for "Curve25519". + * Other features: + - Add GCM and CCM to OID mapping table for AES. + * Upstream libgcrypt-CVE-2021-33560-fix-ElGamal-enc.patch + +------------------------------------------------------------------- +Mon Aug 23 10:11:55 UTC 2021 - Pedro Monreal + +- Remove not needed patch libgcrypt-sparcv9.diff + +------------------------------------------------------------------- +Thu Jul 15 12:53:45 UTC 2021 - Pedro Monreal + +- Fix building test t-lock with pthread. [bsc#1189745] + * Explicitly add -lpthread to compile the t-lock test. + * Add libgcrypt-pthread-in-t-lock-test.patch + +------------------------------------------------------------------- +Fri Jun 11 13:17:54 UTC 2021 - Pedro Monreal + +- Security fix: [bsc#1187212, CVE-2021-33560] + * cipher: Fix ElGamal encryption for other implementations. + * Exponent blinding was added in version 1.9.3. This patch + fixes ElGamal encryption, see: https://dev.gnupg.org/T5328 +- Add libgcrypt-CVE-2021-33560-fix-ElGamal-enc.patch + +------------------------------------------------------------------- +Tue Apr 20 08:46:11 UTC 2021 - Paolo Stivanin + +- libgcrypt 1.9.3: + * Bug fixes: + - Fix build problems on i386 using gcc-4.7. + - Fix checksum calculation in OCB decryption for AES on s390. + - Fix a regression in gcry_mpi_ec_add related to certain usages + of curve 25519. + - Fix a symbol not found problem on Apple M1. + - Fix for Apple iOS getentropy peculiarity. + - Make keygrip computation work for compressed points. + * Performance: + - Add x86_64 VAES/AVX2 accelerated implementation of Camellia. + - Add x86_64 VAES/AVX2 accelerated implementation of AES. + - Add VPMSUMD acceleration for GCM mode on PPC. + * Internal changes. + - Harden MPI conditional code against EM leakage. + - Harden Elgamal by introducing exponent blinding. + +------------------------------------------------------------------- +Wed Feb 17 09:49:55 UTC 2021 - Andreas Stieger + +- libgcrypt 1.9.2: + * Fix building with --disable-asm on x86 + * Check public key for ECDSA verify operation + * Make sure gcry_get_config (NULL) returns a nul-terminated + string + * Fix a memory leak in the ECDH code + * Fix a reading beyond end of input buffer in SHA2-avx2 +- remove obsolete texinfo packaging macros + +------------------------------------------------------------------- +Tue Feb 2 01:06:47 UTC 2021 - Pedro Monreal + +- Update to 1.9.1 + * *Fix exploitable bug* in hash functions introduced with + 1.9.0. [bsc#1181632, CVE-2021-3345] + * Return an error if a negative MPI is used with sexp scan + functions. + * Check for operational FIPS in the random and KDF functions. + * Fix compile error on ARMv7 with NEON disabled. + * Fix self-test in KDF module. + * Improve assembler checks for better LTO support. + * Fix 32-bit cross build on x86. + * Fix non-NEON ARM assembly implementation for SHA512. + * Fix build problems with the cipher_bulk_ops_t typedef. + * Fix Ed25519 private key handling for preceding ZEROs. + * Fix overflow in modular inverse implementation. + * Fix register access for AVX/AVX2 implementations of Blake2. + * Add optimized cipher and hash functions for s390x/zSeries. + * Use hardware bit counting functionx when available. + * Update DSA functions to match FIPS 186-3. + * New self-tests for CMACs and KDFs. + * Add bulk cipher functions for OFB and GCM modes. +- Update libgpg-error required version + +------------------------------------------------------------------- +Tue Feb 1 12:03:31 UTC 2021 - Pedro Monreal + +- Use the suffix variable correctly in get_hmac_path() +- Rebase libgcrypt-fips_selftest_trigger_file.patch + +------------------------------------------------------------------- +Mon Jan 25 12:38:35 UTC 2021 - Pedro Monreal + +- Add the global config file /etc/gcrypt/random.conf + * This file can be used to globally change parameters of the random + generator with the options: only-urandom and disable-jent. + +------------------------------------------------------------------- +Thu Jan 21 15:42:15 UTC 2021 - Pedro Monreal + +- Update to 1.9.0: + New stable branch of Libgcrypt with full API and ABI compatibility + to the 1.8 series. Release-info: https://dev.gnupg.org/T4294 + * New and extended interfaces: + - New curves Ed448, X448, and SM2. + - New cipher mode EAX. + - New cipher algo SM4. + - New hash algo SM3. + - New hash algo variants SHA512/224 and SHA512/256. + - New MAC algos for Blake-2 algorithms, the new SHA512 variants, + SM3, SM4 and for a GOST variant. + - New convenience function gcry_mpi_get_ui. + - gcry_sexp_extract_param understands new format specifiers to + directly store to integers and strings. + - New function gcry_ecc_mul_point and curve constants for Curve448 + and Curve25519. + - New function gcry_ecc_get_algo_keylen. + - New control code GCRYCTL_AUTO_EXPAND_SECMEM to allow growing the + secure memory area. + * Performance optimizations and bug fixes: See Release-info. + * Other features: + - Add OIDs from RFC-8410 as aliases for Ed25519 and Curve25519. + - Add mitigation against ECC timing attack CVE-2019-13627. + - Internal cleanup of the ECC implementation. + - Support reading EC point in compressed format for some curves. +- Rebase patches: + * libgcrypt-1.4.1-rijndael_no_strict_aliasing.patch + * libgcrypt-1.5.0-LIBGCRYPT_FORCE_FIPS_MODE-env.diff + * libgcrypt-1.6.1-use-fipscheck.patch + * drbg_test.patch + * libgcrypt-fipsdrv-enable-algo-for-dsa-sign.patch + * libgcrypt-FIPS-RSA-DSA-ECDSA-hashing-operation.patch + * libgcrypt-1.8.4-fips-keygen.patch + * libgcrypt-1.8.4-getrandom.patch + * libgcrypt-fix-tests-fipsmode.patch + * libgcrypt-global_init-constructor.patch + * libgcrypt-ecc-ecdsa-no-blinding.patch + * libgcrypt-PCT-RSA.patch + * libgcrypt-PCT-ECC.patch +- Remove patches: + * libgcrypt-unresolved-dladdr.patch + * libgcrypt-CVE-2019-12904-GCM-Prefetch.patch + * libgcrypt-CVE-2019-12904-GCM.patch + * libgcrypt-CVE-2019-12904-AES.patch + * libgcrypt-CMAC-AES-TDES-selftest.patch + * libgcrypt-1.6.1-fips-cfgrandom.patch + * libgcrypt-fips_rsa_no_enforced_mode.patch + +------------------------------------------------------------------- +Sat Oct 24 10:25:13 UTC 2020 - Andreas Stieger + +- libgcrypt 1.8.7: + * Support opaque MPI with gcry_mpi_print + * Fix extra entropy collection via clock_gettime, a fallback code + path for legacy hardware + +------------------------------------------------------------------- +Tue Jul 7 09:12:27 UTC 2020 - Pedro Monreal Gonzalez + +- Update to 1.8.6 + * mpi: Consider +0 and -0 the same in mpi_cmp + * mpi: Fix flags in mpi_copy for opaque MPI + * mpi: Fix the return value of mpi_invm_generic + * mpi: DSA,ECDSA: Fix use of mpi_invm + - Call mpi_invm before _gcry_dsa_modify_k + - Call mpi_invm before _gcry_ecc_ecdsa_sign + * mpi: Constant time mpi_inv with some conditions + - mpi/mpi-inv.c (mpih_add_n_cond, mpih_sub_n_cond, mpih_swap_cond) + - New: mpih_abs_cond, mpi_invm_odd + - Rename from _gcry_mpi_invm: mpi_invm_generic + - Use mpi_invm_odd for usual odd cases: _gcry_mpi_invm + * mpi: Abort on division by zero also in _gcry_mpi_tdiv_qr + * Fix wrong code execution in Poly1305 ARM/NEON implementation + - Set r14 to -1 at function entry: (_gcry_poly1305_armv7_neon_init_ext) + * Set vZZ.16b register to zero before use in armv8 gcm implementation + * random: Fix include of config.h + * Fix declaration of internal function _gcry_mpi_get_ui: Don't use ulong + * ecc: Fix wrong handling of shorten PK bytes + - Zeros are already recovered: (_gcry_ecc_mont_decodepoint) +- Update libgcrypt-ecc-ecdsa-no-blinding.patch + +------------------------------------------------------------------- +Tue May 19 11:25:37 UTC 2020 - Pedro Monreal Gonzalez + +- FIPS: RSA/DSA/ECC test_keys() print out debug messages [bsc#1171872] + * Print the debug messages in test_keys() only in debug mode. +- Update patches: libgcrypt-PCT-RSA.patch libgcrypt-PCT-DSA.patch + libgcrypt-PCT-ECC.patch + +------------------------------------------------------------------- +Mon Apr 27 08:55:12 UTC 2020 - Pedro Monreal Gonzalez + +- FIPS: libgcrypt: Double free in test_keys() on failed signature + verification [bsc#1169944] + * Use safer gcry_mpi_release() instead of mpi_free() +- Update patches: + * libgcrypt-PCT-DSA.patch + * libgcrypt-PCT-RSA.patch + * libgcrypt-PCT-ECC.patch + +------------------------------------------------------------------- +Thu Apr 16 16:45:23 UTC 2020 - Vítězslav Čížek + +- Ship the FIPS checksum file in the shared library package and + create a separate trigger file for the FIPS selftests (bsc#1169569) + * add libgcrypt-fips_selftest_trigger_file.patch + * refresh libgcrypt-global_init-constructor.patch +- Remove libgcrypt-binary_integrity_in_non-FIPS.patch obsoleted + by libgcrypt-global_init-constructor.patch + +------------------------------------------------------------------- +Wed Apr 15 13:55:27 UTC 2020 - Pedro Monreal Gonzalez + +- FIPS: Verify that the generated signature and the original input + differ in test_keys function for RSA, DSA and ECC: [bsc#1165539] +- Add zero-padding when qx and qy have different lengths when + assembling the Q point from affine coordinates. +- Refreshed patches: + * libgcrypt-PCT-DSA.patch + * libgcrypt-PCT-RSA.patch + * libgcrypt-PCT-ECC.patch + +------------------------------------------------------------------- +Mon Mar 30 10:48:02 UTC 2020 - Pedro Monreal Gonzalez + +- FIPS: Switch the PCT to use the new signature operation [bsc#1165539] + * Patches for DSA, RSA and ECDSA test_keys functions: + - libgcrypt-PCT-DSA.patch + - libgcrypt-PCT-RSA.patch + - libgcrypt-PCT-ECC.patch +- Update patch: libgcrypt-FIPS-RSA-DSA-ECDSA-hashing-operation.patch + +------------------------------------------------------------------- +Thu Mar 26 18:09:47 UTC 2020 - Pedro Monreal Gonzalez + +- FIPS: Run self-tests from constructor during power-on [bsc#1166748] + * Set up global_init as the constructor function: + - libgcrypt-global_init-constructor.patch + * Relax the entropy requirements on selftest. This is especially + important for virtual machines to boot properly before the RNG + is available: + - libgcrypt-random_selftests-testentropy.patch + - libgcrypt-rsa-no-blinding.patch + - libgcrypt-ecc-ecdsa-no-blinding.patch + * Fix benchmark regression test in FIPS mode: + - libgcrypt-FIPS-GMAC_AES-benckmark.patch + +------------------------------------------------------------------- +Thu Mar 12 16:54:33 UTC 2020 - Pedro Monreal Gonzalez + +- Remove check not needed in _gcry_global_constructor [bsc#1164950] + * Update libgcrypt-Restore-self-tests-from-constructor.patch + +------------------------------------------------------------------- +Tue Feb 25 22:13:24 UTC 2020 - Pedro Monreal Gonzalez + +- FIPS: Run the self-tests from the constructor [bsc#1164950] + * Add libgcrypt-invoke-global_init-from-constructor.patch + +------------------------------------------------------------------- +Fri Jan 17 17:35:15 UTC 2020 - Pedro Monreal Gonzalez + +- FIPS: libgcrypt DSA PQG parameter generation: Missing value [bsc#1161219] +- FIPS: libgcrypt DSA PQG verification incorrect results [bsc#1161215] +- FIPS: libgcrypt RSA siggen/keygen: 4k not supported [bsc#1161220] + * Add patch from Fedora libgcrypt-1.8.4-fips-keygen.patch + +------------------------------------------------------------------- +Wed Dec 11 10:18:23 UTC 2019 - Pedro Monreal Gonzalez + +- FIPS: RSA/DSA/ECDSA are missing hashing operation [bsc#1155337] + * Add libgcrypt-FIPS-RSA-DSA-ECDSA-hashing-operation.patch + +------------------------------------------------------------------- +Wed Nov 27 14:01:01 UTC 2019 - Pedro Monreal Gonzalez + +- Fix tests in FIPS mode: + * Fix tests: basic benchmark bench-slope pubkey t-cv25519 t-secmem + * Add patch libgcrypt-fix-tests-fipsmode.patch + +------------------------------------------------------------------- +Tue Nov 26 18:48:20 UTC 2019 - Pedro Monreal Gonzalez + +- Fix test dsa-rfc6979 in FIPS mode: + * Disable tests in elliptic curves with 192 bits which are not + recommended in FIPS mode + * Add patch libgcrypt-dsa-rfc6979-test-fix.patch + +------------------------------------------------------------------- +Tue Nov 12 11:05:02 UTC 2019 - Pedro Monreal Gonzalez + +- CMAC AES and TDES FIPS self-tests: + * CMAC AES self test missing [bsc#1155339] + * CMAC TDES self test missing [bsc#1155338] +- Add libgcrypt-CMAC-AES-TDES-selftest.patch + +------------------------------------------------------------------- +Fri Aug 30 14:17:48 UTC 2019 - Andreas Stieger + +- libgcrypt 1.8.5: + * CVE-2019-13627: mitigation against an ECDSA timing attack (boo#1148987) + * Improve ECDSA unblinding + * Provide a pkg-config file + +------------------------------------------------------------------- +Wed Jun 26 06:52:54 UTC 2019 - Jason Sikes + +- Fixed redundant fips tests in some situations causing sudo to stop + working when pam-kwallet is installed. bsc#1133808 + * Added libgcrypt-1.8.4-fips_ctor_skip_integrity_check.patch + * Removed libgcrypt-fips_run_selftest_at_constructor.patch + because it was obsoleted by libgcrypt-1.8.3-fips-ctor.patch + * Removed libgcrypt-fips_ignore_FIPS_MODULE_PATH.patch + because it was obsoleted by libgcrypt-1.8.4-fips_ctor_skip_integrity_check.patch + +------------------------------------------------------------------- +Fri Jun 21 16:53:07 UTC 2019 - Pedro Monreal Gonzalez + +- Fixed env-script-interpreter in cavs_driver.pl + +------------------------------------------------------------------- +Fri Jun 21 16:39:00 UTC 2019 - Pedro Monreal Gonzalez + +- Security fix: [bsc#1138939, CVE-2019-12904] + * The C implementation of AES is vulnerable to a flush-and-reload + side-channel attack because physical addresses are available to + other processes. (The C implementation is used on platforms where + an assembly-language implementation is unavailable.) + * Added patches: + - libgcrypt-CVE-2019-12904-GCM-Prefetch.patch + - libgcrypt-CVE-2019-12904-GCM.patch + - libgcrypt-CVE-2019-12904-AES.patch + +------------------------------------------------------------------- +Fri Apr 26 06:47:45 UTC 2019 - Jason Sikes + +- do not try to open /dev/urandom if getrandom() works + * Added libgcrypt-1.8.4-getrandom.patch +- Drop libgcrypt-init-at-elf-load-fips.patch obsoleted + by libgcrypt-1.8.3-fips-ctor.patch + +------------------------------------------------------------------- +Tue Apr 23 12:38:40 UTC 2019 - Jason Sikes + +- Restored libgcrypt-binary_integrity_in_non-FIPS.patch sans section that + was partially causing bsc#1131183. +- Fixed race condition in multi-threaded applications by allowing a FSM state + transition to the current state. This means some tests are run twice. + * Added libgcrypt-1.8.4-allow_FSM_same_state.patch +- Fixed an issue in malloc/free wrappers so that memory created by the malloc() + wrappers will be destroyed using the free() wrappers. + * Added libgcrypt-1.8.4-use_xfree.patch + +------------------------------------------------------------------- +Fri Apr 5 21:56:00 UTC 2019 - Jason Sikes + +- removed libgcrypt-binary_integrity_in_non-FIPS.patch since it was breaking + libotr. bsc#1131183 + +------------------------------------------------------------------- +Tue Mar 26 16:30:23 UTC 2019 - Vítězslav Čížek + +- libgcrypt-1.8.3-fips-ctor.patch changed the way the fips selftests + are invoked as well as the state transition, adjust the code so + a missing checksum file is not an issue in non-FIPS mode (bsc#1097073) + * update libgcrypt-binary_integrity_in_non-FIPS.patch + +------------------------------------------------------------------- +Tue Mar 26 16:25:18 UTC 2019 - Vítězslav Čížek + +- Enforce the minimal RSA keygen size in fips mode (bsc#1125740) + * add libgcrypt-fips_rsa_no_enforced_mode.patch + +------------------------------------------------------------------- +Fri Mar 22 14:13:05 UTC 2019 - Vítězslav Čížek + +- Don't run full self-tests from constructor (bsc#1097073) + * Don't call global_init() from the constructor, _gcry_global_constructor() + from libgcrypt-1.8.3-fips-ctor.patch takes care of the binary + integrity check instead. + * Only the binary checksum will be verified, the remaining + self-tests will be run upon the library initialization +- Add libgcrypt-fips_ignore_FIPS_MODULE_PATH.patch +- Drop libgcrypt-init-at-elf-load-fips.patch and + libgcrypt-fips_run_selftest_at_constructor.patch obsoleted + by libgcrypt-1.8.3-fips-ctor.patch + +------------------------------------------------------------------- +Thu Mar 7 10:53:40 UTC 2019 - Pedro Monreal Gonzalez + +- Skip all the self-tests except for binary integrity when called + from the constructor (bsc#1097073) + * Added libgcrypt-1.8.3-fips-ctor.patch from Fedora + +------------------------------------------------------------------- +Mon Nov 26 17:09:47 UTC 2018 - Vítězslav Čížek + +- Fail selftests when checksum file is missing in FIPS mode only + (bsc#1117355) + * add libgcrypt-binary_integrity_in_non-FIPS.patch + +------------------------------------------------------------------- +Sun Oct 28 18:57:53 UTC 2018 - astieger@suse.com + +- libgcrypt 1.8.4: + * Fix infinite loop with specific application implementations + * Fix possible leak of a few bits of secret primes to pageable + memory + * Fix possible hang in the RNG (1.8.3) + * Always make use of getrandom if possible and then use + its /dev/urandom behaviour + +------------------------------------------------------------------- +Mon Jul 2 10:38:42 UTC 2018 - schwab@suse.de + +- libgcrypt-1.6.3-aliasing.patch, libgcrypt-ppc64.patch, + libgcrypt-strict-aliasing.patch: Remove obsolete patches +- libgcrypt-1.4.1-rijndael_no_strict_aliasing.patch: Rediff +- Reenable testsuite + +------------------------------------------------------------------- +Wed Jun 13 10:46:33 UTC 2018 - kbabioch@suse.com + +- Update to version 1.8.3: + - Use blinding for ECDSA signing to mitigate a novel side-channel + attack. (CVE-2018-0495 bsc#1097410) + - Fix incorrect counter overflow handling for GCM when using an IV + size other than 96 bit. + - Fix incorrect output of AES-keywrap mode for in-place encryption + on some platforms. + - Fix the gcry_mpi_ec_curve_point point validation function. + - Fix rare assertion failure in gcry_prime_check. +- Applied spec-cleaner + +------------------------------------------------------------------- +Wed May 2 14:31:07 UTC 2018 - pmonrealgonzalez@suse.com + +- Suggest libgcrypt20-hmac for package libgcrypt20 to ensure they + are installed in the right order. [bsc#1090766] + +------------------------------------------------------------------- +Thu Mar 29 06:37:44 UTC 2018 - pmonrealgonzalez@suse.com + +- Extended the fipsdrv dsa-sign and dsa-verify commands with the + --algo parameter for the FIPS testing of DSA SigVer and SigGen + (bsc#1064455). + * Added libgcrypt-fipsdrv-enable-algo-for-dsa-sign.patch + * Added libgcrypt-fipsdrv-enable-algo-for-dsa-verify.patch + +------------------------------------------------------------------- +Thu Feb 22 15:10:36 UTC 2018 - fvogt@suse.com + +- Use %license (boo#1082318) + +------------------------------------------------------------------- +Wed Dec 13 20:09:28 UTC 2017 - astieger@suse.com + +- libgcrypt 1.8.2: + * Fix fatal out of secure memory status in the s-expression + parser on heavy loaded systems. + * Add auto expand secmem feature or use by GnuPG 2.2.4 + +------------------------------------------------------------------- +Mon Aug 28 17:54:24 UTC 2017 - astieger@suse.com + +- libgcrypt 1.8.1: + * Mitigate a local side-channel attack on Curve25519 dubbed "May + the Fourth be With You" CVE-2017-0379 bsc#1055837 + * Add more extra bytes to the pool after reading a seed file + * Add the OID SHA384WithECDSA from RFC-7427 to SHA-384 + * Fix build problems with the Jitter RNG + * Fix assembler code build problems on Rasbian (ARMv8/AArch32-CE) + +------------------------------------------------------------------- +Mon Jul 24 23:43:40 UTC 2017 - jengelh@inai.de + +- RPM group fixes. + +------------------------------------------------------------------- +Fri Jul 21 15:50:14 UTC 2017 - astieger@suse.com + +- libgcrypt 1.8.0: + * New cipher mode XTS + * New hash function Blake-2 + * New function gcry_mpi_point_copy. + * New function gcry_get_config. + * GCRYCTL_REINIT_SYSCALL_CLAMP allows to init nPth after Libgcrypt. + * New gobal configuration file /etc/gcrypt/random.conf. + * GCRYCTL_PRINT_CONFIG does now also print build information for + libgpg-error and the used compiler version. + * GCRY_CIPHER_MODE_CFB8 is now supported. + * A jitter based entropy collector is now used in addition to the + other entropy collectors. + * Optimized gcry_md_hash_buffers for SHA-256 and SHA-512. + random pool lock). + * Interface changes relative to the 1.7.0 release: + gcry_get_config NEW function. + gcry_mpi_point_copy NEW function. + GCRYCTL_REINIT_SYSCALL_CLAMP NEW macro. + GCRY_MD_BLAKE2B_512 NEW constant. + GCRY_MD_BLAKE2B_384 NEW constant. + GCRY_MD_BLAKE2B_256 NEW constant. + GCRY_MD_BLAKE2B_160 NEW constant. + GCRY_MD_BLAKE2S_256 NEW constant. + GCRY_MD_BLAKE2S_224 NEW constant. + GCRY_MD_BLAKE2S_160 NEW constant. + GCRY_MD_BLAKE2S_128 NEW constant. + GCRY_CIPHER_MODE_XTS NEW constant. + gcry_md_info DEPRECATED. +- Refresh patch libgcrypt-1.6.3-aliasing.patch + +------------------------------------------------------------------- +Thu Jun 29 09:49:44 UTC 2017 - astieger@suse.com + +- libgcrypt 1.7.8: + * CVE-2017-7526: Mitigate a flush+reload side-channel attack on + RSA secret keys (bsc#1046607) + +------------------------------------------------------------------- +Sun Jun 4 19:26:12 UTC 2017 - astieger@suse.com + +- libgcrypt 1.7.7: + * Fix possible timing attack on EdDSA session key (previously + patched, drop libgcrypt-secure-EdDSA-session-key.patch) + * Fix long standing bug in secure memory implementation which + could lead to a segv on free + +------------------------------------------------------------------- +Fri Jun 2 10:05:18 UTC 2017 - pmonrealgonzalez@suse.com + +- Added libgcrypt-secure-EdDSA-session-key.patch [bsc#1042326] + * Store the session key in secure memory to ensure that constant + time point operations are used in the MPI library. + +------------------------------------------------------------------- +Fri Jan 20 09:41:15 UTC 2017 - rmaliska@suse.com + +- libgcrypt 1.7.6: + * Fix counter operand from read-only to read/write + * Fix too large jump alignment in mpih-rshift + +------------------------------------------------------------------- +Thu Dec 15 10:32:18 UTC 2016 - astieger@suse.com + +- libgcrypt 1.7.5: + * Fix regression in mlock detection introduced with 1.7.4 + +------------------------------------------------------------------- +Tue Dec 13 12:20:47 UTC 2016 - astieger@suse.com + +- libgcrypt 1.7.4: + * ARMv8/AArch32 performance improvements for AES, GCM, SHA-256, + and SHA-1. + * Add ARMv8/AArch32 assembly implementation for Twofish and + Camellia. + * Add bulk processing implementation for ARMv8/AArch32. + * Add Stribog OIDs. + * Improve the DRBG performance and sync the code with the Linux + version. + * When secure memory is requested by the MPI functions or by + gcry_xmalloc_secure, they do not anymore lead to a fatal error + if the secure memory pool is used up. Instead new pools are + allocated as needed. These new pools are not protected against + being swapped out (mlock can't be used). Mitigation for + minor confidentiality issues is encryption swap space. + * Fix GOST 28147 CryptoPro-B S-box. + * Fix error code handling of mlock calls. + +------------------------------------------------------------------- +Sat Aug 20 10:38:15 UTC 2016 - mpluskal,vcizek,astieger}@suse.com + +- libgcrypt 1.7.3: + * security issue already fixes with 1.6.6 + * Fix building of some asm modules with older compilers and CPUs. + * ARMv8/AArch32 improvements for AES, GCM, SHA-256, and SHA-1. +- includes changes from libgcrypt 1.7.2: + * Bug fixes: + - Fix setting of the ECC cofactor if parameters are specified. + - Fix memory leak in the ECC code. + - Remove debug message about unsupported getrandom syscall. + - Fix build problems related to AVX use. + - Fix bus errors on ARM for Poly1305, ChaCha20, AES, and SHA-512. + * Internal changes: + - Improved fatal error message for wrong use of gcry_md_read. + - Disallow symmetric encryption/decryption if key is not set. +- includes changes from 1.7.1: + * Bug fixes: + - Fix ecc_verify for cofactor support. + - Fix portability bug when using gcc with Solaris 9 SPARC. + - Build fix for OpenBSD/amd64 + - Add OIDs to the Serpent ciphers. + * Internal changes: + - Use getrandom system call on Linux if available. + - Blinding is now also used for RSA signature creation. + - Changed names of debug envvars +- includes changes from 1.7.0: + * New algorithms and modes: + - SHA3-224, SHA3-256, SHA3-384, SHA3-512, and MD2 hash algorithms. + - SHAKE128 and SHAKE256 extendable-output hash algorithms. + - ChaCha20 stream cipher. + - Poly1305 message authentication algorithm + - ChaCha20-Poly1305 Authenticated Encryption with Associated Data + mode. + - OCB mode. + - HMAC-MD2 for use by legacy applications. + * New curves for ECC: + - Curve25519. + - sec256k1. + - GOST R 34.10-2001 and GOST R 34.10-2012. + * Performance: + - Improved performance of KDF functions. + - Assembler optimized implementations of Blowfish and Serpent on + ARM. + - Assembler optimized implementation of 3DES on x86. + - Improved AES using the SSSE3 based vector permutation method by + Mike Hamburg. + - AVX/BMI is used for SHA-1 and SHA-256 on x86. This is for SHA-1 + about 20% faster than SSSE3 and more than 100% faster than the + generic C implementation. + - 40% speedup for SHA-512 and 72% for SHA-1 on ARM Cortex-A8. + - 60-90% speedup for Whirlpool on x86. + - 300% speedup for RIPE MD-160. + - Up to 11 times speedup for CRC functions on x86. + * Other features: + - Improved ECDSA and FIPS 186-4 compliance. + - Support for Montgomery curves. + - gcry_cipher_set_sbox to tweak S-boxes of the gost28147 cipher + algorithm. + - gcry_mpi_ec_sub to subtract two points on a curve. + - gcry_mpi_ec_decode_point to decode an MPI into a point object. + - Emulation for broken Whirlpool code prior to 1.6.0. [from 1.6.1] + - Flag "pkcs1-raw" to enable PCKS#1 padding with a user supplied + hash part. + - Parameter "saltlen" to set a non-default salt length for RSA PSS. + - A SP800-90A conforming DRNG replaces the former X9.31 alternative + random number generator. + - Map deprecated RSA algo number to the RSA algo number for better + backward compatibility. [from 1.6.2] + - Use ciphertext blinding for Elgamal decryption [CVE-2014-3591]. + See http://www.cs.tau.ac.il/~tromer/radioexp/ for details. + [from 1.6.3] + - Fixed data-dependent timing variations in modular exponentiation + [related to CVE-2015-0837, Last-Level Cache Side-Channel Attacks + are Practical]. [from 1.6.3] + - Flag "no-keytest" for ECC key generation. Due to a bug in + the parser that flag will also be accepted but ignored by older + version of Libgcrypt. [from 1.6.4] + - Speed up the random number generator by requiring less extra + seeding. [from 1.6.4] + - Always verify a created RSA signature to avoid private key leaks + due to hardware failures. [from 1.6.4] + - Mitigate side-channel attack on ECDH with Weierstrass curves + [CVE-2015-7511]. See http://www.cs.tau.ac.IL/~tromer/ecdh/ for + details. [from 1.6.5] + * Internal changes: + - Moved locking out to libgpg-error. + - Support of the SYSROOT envvar in the build system. + - Refactor some code. + - The availability of a 64 bit integer type is now mandatory. + * Bug fixes: + - Fixed message digest lookup by OID (regression in 1.6.0). + - Fixed a build problem on NetBSD + - Fixed some asm build problems and feature detection bugs. + * Interface changes relative to the 1.6.0 release: + gcry_cipher_final NEW macro. + GCRY_CIPHER_MODE_CFB8 NEW constant. + GCRY_CIPHER_MODE_OCB NEW. + GCRY_CIPHER_MODE_POLY1305 NEW. + gcry_cipher_set_sbox NEW macro. + gcry_mac_get_algo NEW. + GCRY_MAC_HMAC_MD2 NEW. + GCRY_MAC_HMAC_SHA3_224 NEW. + GCRY_MAC_HMAC_SHA3_256 NEW. + GCRY_MAC_HMAC_SHA3_384 NEW. + GCRY_MAC_HMAC_SHA3_512 NEW. + GCRY_MAC_POLY1305 NEW. + GCRY_MAC_POLY1305_AES NEW. + GCRY_MAC_POLY1305_CAMELLIA NEW. + GCRY_MAC_POLY1305_SEED NEW. + GCRY_MAC_POLY1305_SERPENT NEW. + GCRY_MAC_POLY1305_TWOFISH NEW. + gcry_md_extract NEW. + GCRY_MD_FLAG_BUGEMU1 NEW [from 1.6.1]. + GCRY_MD_GOSTR3411_CP NEW. + GCRY_MD_SHA3_224 NEW. + GCRY_MD_SHA3_256 NEW. + GCRY_MD_SHA3_384 NEW. + GCRY_MD_SHA3_512 NEW. + GCRY_MD_SHAKE128 NEW. + GCRY_MD_SHAKE256 NEW. + gcry_mpi_ec_decode_point NEW. + gcry_mpi_ec_sub NEW. + GCRY_PK_EDDSA NEW constant. + GCRYCTL_GET_TAGLEN NEW. + GCRYCTL_SET_SBOX NEW. + GCRYCTL_SET_TAGLEN NEW. +- Apply libgcrypt-1.6.3-aliasing.patch only on big-endian + architectures +- update drbg_test.patch and install cavs testing directory again +- As DRBG is upstream, drop pateches: + v9-0001-SP800-90A-Deterministic-Random-Bit-Generator.patch + 0002-Compile-DRBG.patch + 0003-Function-definitions-of-interfaces-for-random.c.patch + 0004-Invoke-DRBG-from-common-libgcrypt-RNG-code.patch + 0005-Function-definitions-for-gcry_control-callbacks.patch + 0006-DRBG-specific-gcry_control-requests.patch + v9-0007-User-interface-to-DRBG.patch + libgcrypt-fix-rng.patch +- drop obsolete: + libgcrypt-fips-dsa.patch + libgcrypt-fips_ecdsa.patch + +------------------------------------------------------------------- +Wed Aug 17 18:21:44 UTC 2016 - astieger@suse.com + +- libgcrypt 1.6.6: + * fix CVE-2016-6313: Issue in the mixing functions of the random + number generators allowed an attacker who obtained a number of + bytes from the standard RNG to predict some of the next ouput. + (bsc#994157) + +------------------------------------------------------------------- +Mon May 16 14:37:45 UTC 2016 - pjanouch@suse.de + +- remove conditionals for unsupported distributions (before 13.2), + it would not build anyway because of new dependencies + +------------------------------------------------------------------- +Mon May 16 12:36:14 UTC 2016 - pjanouch@suse.de + +- make the -hmac package depend on the same version of the library, + fixing bsc#979629 FIPS: system fails to reboot after installing + fips pattern + +------------------------------------------------------------------- +Tue Feb 9 20:51:59 UTC 2016 - astieger@suse.com + +- update to 1.6.5: + * CVE-2015-7511: Mitigate side-channel attack on ECDH with + Weierstrass curves (boo#965902) + +------------------------------------------------------------------- +Sat Oct 10 11:56:08 UTC 2015 - astieger@suse.com + +- follow-up to libgcrypt 1.6.4 update: sosuffix is 20.0.4 + +------------------------------------------------------------------- +Tue Sep 8 08:03:19 UTC 2015 - vcizek@suse.com + +- update to 1.6.4 +- fixes libgcrypt equivalent of CVE-2015-5738 (bsc#944456) + * Speed up the random number generator by requiring less extra + seeding. + * New flag "no-keytest" for ECC key generation. Due to a bug in the + parser that flag will also be accepted but ignored by older version + of Libgcrypt. + * Always verify a created RSA signature to avoid private key leaks + due to hardware failures. + * Other minor bug fixes. + +------------------------------------------------------------------- +Tue Jun 23 15:15:30 UTC 2015 - dvaleev@suse.com + +- Fix gpg2 tests on BigEndian architectures: s390x ppc64 + libgcrypt-1.6.3-aliasing.patch + +------------------------------------------------------------------- +Sun Mar 1 21:16:26 UTC 2015 - astieger@suse.com + +- fix sosuffix for 1.6.3 (20.0.3) + +------------------------------------------------------------------- +Sat Feb 28 19:31:10 UTC 2015 - astieger@suse.com + +- libgcrypt 1.6.3 [bnc#920057]: + * Use ciphertext blinding for Elgamal decryption [CVE-2014-3591]. + * Fixed data-dependent timing variations in modular exponentiation + [related to CVE-2015-0837, Last-Level Cache Side-Channel Attacks + are Practical]. +- update upstream signing keyring + +------------------------------------------------------------------- +Fri Feb 6 18:42:28 UTC 2015 - coolo@suse.com + +- making the build reproducible - see + http://lists.gnupg.org/pipermail/gnupg-commits/2014-September/010683.html + for a very similiar problem + +------------------------------------------------------------------- +Fri Feb 6 18:38:55 UTC 2015 - dimstar@opensuse.org + +- Move %install_info_delete calls from postun to preun: the files + must still be present to be parsed. +- Fix the names passed to install_info for gcrypt.info-[12].gz + instead of gcrypt-[12].info.gz. + +------------------------------------------------------------------- +Fri Feb 6 18:30:26 UTC 2015 - coolo@suse.com + +- fix filename for info pages in %post scripts + +------------------------------------------------------------------- +Wed Nov 5 20:37:24 UTC 2014 - andreas.stieger@gmx.de + +- libgcrypt 1.6.2: + * Map deprecated RSA algo number to the RSA algo number for better + backward compatibility. + * Support a 0x40 compression prefix for EdDSA. + * Improve ARM hardware feature detection and building. + * Fix building for the x32 ABI platform. + * Fix some possible NULL deref bugs. +- remove libgcrypt-1.6.0-use-intenal-functions.patch, upstream + via xtrymalloc macro +- remove libgcrypt-fixed-sizet.patch, upstream +- adjust libgcrypt-1.6.1-use-fipscheck.patch for xtrymalloc change + +------------------------------------------------------------------- +Sun Sep 21 10:08:39 UTC 2014 - vcizek@suse.com + +- disabled curve P-192 in FIPS mode (bnc#896202) + * added libgcrypt-fips_ecdsa.patch +- don't use SHA-1 for ECDSA in FIPS mode +- also run the fips self tests only in FIPS mode + +------------------------------------------------------------------- +Tue Sep 16 13:56:01 UTC 2014 - vcizek@suse.com + +- run the fips self tests at the constructor code + * added libgcrypt-fips_run_selftest_at_constructor.patch + +------------------------------------------------------------------- +Tue Sep 16 12:17:17 UTC 2014 - vcizek@suse.com + +- rewrite the DSA-2 code to be FIPS 186-4 compliant (bnc#894216) + * added libgcrypt-fips-dsa.patch + * install fips186_dsa +- use 2048 bit keys in selftests_dsa + +------------------------------------------------------------------- +Mon Sep 1 10:57:06 UTC 2014 - vcizek@suse.com + +- fix an issue in DRBG patchset + * size_t type is 32-bit on 32-bit systems +- fix a potential NULL pointer deference in DRBG patchset + * patches from https://bugs.g10code.com/gnupg/issue1701 +- added v9-0001-SP800-90A-Deterministic-Random-Bit-Generator.patch +- added v9-0007-User-interface-to-DRBG.patch +- removed v7-0001-SP800-90A-Deterministic-Random-Bit-Generator.patch +- removed v7-0007-User-interface-to-DRBG.patch +- add a subpackage for CAVS testing + * add cavs_driver.pl and cavs-test.sh from the kernel cavs package + * added drbg_test.patch + +------------------------------------------------------------------- +Tue Aug 12 07:43:19 UTC 2014 - meissner@suse.com + +- split off the -hmac package that contains the checksums + +------------------------------------------------------------------- +Mon May 26 12:05:17 UTC 2014 - meissner@suse.com + +- libgcrypt-fix-rng.patch: make drbg work again in FIPS mode. +- libgcrypt-1.6.1-use-fipscheck.patch: library to test is libgcrypt.so.20 + and not libgcrypt.so.11 +- libgcrypt-init-at-elf-load-fips.patch: initialize globally on ELF + DSO loading to meet FIPS requirements. + +------------------------------------------------------------------- +Tue May 13 10:47:51 UTC 2014 - vcizek@suse.com + +- add new 0007-User-interface-to-DRBG.patch from upstream + * fixes bnc#877233 + * supersedes the patch from previous entry + +------------------------------------------------------------------- +Sun May 12 13:25:33 UTC 2014 - tittiatcoke@gmail.com + +- Correct patch 0007-User-interface-to-DRBG.patch so that the + struct used in the route matches the header of the function + +------------------------------------------------------------------- +Tue May 6 13:28:33 UTC 2014 - vcizek@suse.com + +- add support for SP800-90A DRBG (fate#316929, bnc#856312) + * patches by Stephan Mueller (http://www.chronox.de/drbg.html): + 0001-SP800-90A-Deterministic-Random-Bit-Generator.patch.bz2 + 0002-Compile-DRBG.patch + 0003-Function-definitions-of-interfaces-for-random.c.patch + 0004-Invoke-DRBG-from-common-libgcrypt-RNG-code.patch + 0005-Function-definitions-for-gcry_control-callbacks.patch + 0006-DRBG-specific-gcry_control-requests.patch + 0007-User-interface-to-DRBG.patch + * only after 13.1 (the patches need libgpg-error 1.13) +- drop libgcrypt-fips-allow-legacy.patch (not needed and wasn't + applied anyway) + +------------------------------------------------------------------- +Thu Apr 3 12:04:46 UTC 2014 - tchvatal@suse.com + +- Cleanup with spec-cleaner to sort out. +- Really apply ppc64 patch as it was ommited probably by mistake. + +------------------------------------------------------------------- +Thu Mar 27 14:57:22 UTC 2014 - meissner@suse.com + +- FIPS changes (from Fedora): + - replaced libgcrypt-1.5.0-etc_gcrypt_rngseed-symlink.diff by + libgcrypt-1.6.1-fips-cfgrandom.patch + - libgcrypt-fixed-sizet.patch: fixed an int type for -flto + - libgcrypt-1.6.1-use-fipscheck.patch: use the fipscheck binary + - libgcrypt-1.6.1-fips-cavs.patch: add CAVS tests +- use fipscheck only after 13.1 +- libgcrypt-fips-allow-legacy.patch: attempt to allow some + legacy algorithms for gpg2 usage even in FIPS mode. + (currently not applied) + +------------------------------------------------------------------- +Thu Jan 30 13:29:49 UTC 2014 - idonmez@suse.com + +- Drop arm-missing-files.diff, fixed upstream + +------------------------------------------------------------------- +Wed Jan 29 18:40:49 UTC 2014 - andreas.stieger@gmx.de + +- libgcrypt 1.6.1, a bugfix release with the folloging fixes: + * Added emulation for broken Whirlpool code prior to 1.6.0. + * Improved performance of KDF functions. + * Improved ECDSA compliance. + * Fixed message digest lookup by OID (regression in 1.6.0). + * Fixed memory leaks in ECC code. + * Fixed some asm build problems and feature detection bugs. + * Interface changes relative to the 1.6.0 release: + GCRY_MD_FLAG_BUGEMU1 NEW (minor API change). + +------------------------------------------------------------------- +Fri Jan 3 16:36:21 UTC 2014 - dmueller@suse.com + +- add arm-missing-files.diff: Add missing files to fix build + +------------------------------------------------------------------- +Fri Jan 3 09:43:39 UTC 2014 - mvyskocil@suse.com + +- fix bnc#856915: can't open /dev/urandom + * correct libgcrypt-1.5.0-etc_gcrypt_rngseed-symlink.diff +- require libgpg-error 1.11 or higher + +------------------------------------------------------------------- +Thu Dec 19 13:53:21 UTC 2013 - mvyskocil@suse.com + +- fix dependency for 32bit devel package +- name hmac files according soname +- fix hmac subpackage dependency + +------------------------------------------------------------------- +Thu Dec 19 09:03:21 UTC 2013 - mvyskocil@suse.com + +- update to 1.6. + * Removed the long deprecated gcry_ac interface. Thus Libgcrypt is + not anymore ABI compatible to previous versions if they used the ac + interface. Check NEWS in libgcrypt-devel for removed interfaces. + * Removed the module register subsystem. + * The deprecated message digest debug macros have been removed. Use + gcry_md_debug instead. + * Removed deprecated control codes. + * Improved performance of most cipher algorithms as well as for the + SHA family of hash functions. + * Added support for the IDEA cipher algorithm. + * Added support for the Salsa20 and reduced Salsa20/12 stream ciphers. + * Added limited support for the GOST 28147-89 cipher algorithm. + * Added support for the GOST R 34.11-94 and R 34.11-2012 (Stribog) + hash algorithms. + * Added a random number generator to directly use the system's RNG. + Also added an interface to prefer the use of a specified RNG. + * Added support for the SCRYPT algorithm. + * Mitigated the Yarom/Falkner flush+reload side-channel attack on RSA + secret keys. See [CVE-2013-4242]. + * Added support for Deterministic DSA as per RFC-6969. + * Added support for curve Ed25519. + * Added a scatter gather hash convenience function. + * Added several MPI amd SEXP helper functions. + * Added support for negative numbers to gcry_mpi_print, + gcry_mpi_aprint and gcry_mpi_scan. + * The algorithm ids GCRY_PK_ECDSA and GCRY_PK_ECDH are now + deprecated. Use GCRY_PK_ECC if you need an algorithm id. + * Changed gcry_pk_genkey for "ecc" to only include the curve name and + not the parameters. The flag "param" may be used to revert this. + * Added a feature to globally disable selected hardware features. + * Added debug helper functions. +- rebased patches + * libgcrypt-1.5.0-etc_gcrypt_rngseed-symlink.diff + * libgcrypt-ppc64.patch +- add libgcrypt-1.6.0-use-intenal-functions.patch to fix fips.c build +- Move all documentation to -devel package + +------------------------------------------------------------------- +Fri Jul 26 22:05:46 UTC 2013 - andreas.stieger@gmx.de + +- update to 1.5.3 [bnc#831359] CVE-2013-4242 + * Mitigate the Yarom/Falkner flush+reload side-channel attack on + RSA secret keys. See . + +------------------------------------------------------------------- +Thu Jul 25 09:15:43 UTC 2013 - mvyskocil@suse.com + +- port SLE enhancenments to Factory (bnc#831028) + * add libgcrypt-unresolved-dladdr.patch (bnc#701267) + * add libgcrypt-1.5.0-etc_gcrypt_rngseed-symlink.diff (bnc#724841) + * add libgcrypt-1.5.0-LIBGCRYPT_FORCE_FIPS_MODE-env.diff +- install .hmac256.hmac (bnc#704068) +- enable varuous new options in configure (m-guard, hmac binary check and + random device linux) +- build with all ciphers, pubkeys and digest by default as whitelist + simply allowed them all + +------------------------------------------------------------------- +Mon Jun 17 13:22:33 UTC 2013 - coolo@suse.com + +- avoid gpg-offline in bootstrap packages + +------------------------------------------------------------------- +Sun Jun 16 22:56:56 UTC 2013 - crrodriguez@opensuse.org + +- Library must be built with large file support in + 32 bit archs. + +------------------------------------------------------------------- +Thu Apr 18 18:23:36 UTC 2013 - andreas.stieger@gmx.de + +- update to 1.5.2 + * The upstream sources now contain the IDEA algorithm, dropping: + idea.c.gz + libgcrypt-1.5.0-idea.patch + libgcrypt-1.5.0-idea_codecleanup.patch + * Made the Padlock code work again (regression since 1.5.0). + * Fixed alignment problems for Serpent. + * Fixed two bugs in ECC computations. + +------------------------------------------------------------------- +Fri Mar 22 09:31:11 UTC 2013 - mvyskocil@suse.com + +- add GPL3.0+ to License tag because of dumpsexp (bnc#810759) + +------------------------------------------------------------------- +Mon Mar 18 20:41:00 UTC 2013 - andreas.stieger@gmx.de + +- update to 1.5.1 + * Allow empty passphrase with PBKDF2. + * Do not abort on an invalid algorithm number in + gcry_cipher_get_algo_keylen and gcry_cipher_get_algo_blklen. + * Fixed some Valgrind warnings. + * Fixed a problem with select and high fd numbers. + * Improved the build system + * Various minor bug fixes. + * Interface changes relative to the 1.5.0 release: + GCRYCTL_SET_ENFORCED_FIPS_FLAG NEW. + GCRYPT_VERSION_NUMBER NEW. +- add verification of source code signatures +- now requires automake 1.11 to build + +------------------------------------------------------------------- +Sat Feb 2 18:51:33 UTC 2013 - coolo@suse.com + +- update license to new format + +------------------------------------------------------------------- +Tue Jun 12 21:19:18 UTC 2012 - chris@computersalat.de + +- fix deps + * libgpg-error-devel >= 1.8 +- add libsoname macro + +------------------------------------------------------------------- +Sun Feb 12 15:23:56 UTC 2012 - crrodriguez@opensuse.org + +- Libraries back into %{_libdir}, /usr merge project + +------------------------------------------------------------------- +Sat Dec 24 23:51:26 UTC 2011 - opensuse@dstoecker.de + +- add the missing IDEA algorithm after the patent is no longer relevant + +------------------------------------------------------------------ +Sun Nov 13 14:37:29 UTC 2011 - jengelh@medozas.de + +- Remove redundant/unwanted tags/section (cf. specfile guidelines) + +------------------------------------------------------------------- +Sun Nov 13 09:16:36 UTC 2011 - coolo@suse.com + +- add libtool as explicit buildrequire to avoid implicit dependency from prjconf + +------------------------------------------------------------------- +Sun Oct 2 18:38:28 UTC 2011 - crrodriguez@opensuse.org + +- Update to version 1.5.0, most important changes + * Uses the Intel AES-NI instructions if available + * Support ECDH. + +------------------------------------------------------------------- +Fri Nov 19 09:59:41 UTC 2010 - mvyskocil@suse.cz + +- update to 1.4.6 + * Fixed minor memory leak in DSA key generation. + * No more switching to FIPS mode if /proc/version is not readable. + * Fixed a sigill during Padlock detection on old CPUs. + * Boosted SHA-512 performance by 30% on ia32 boxes and gcc 4.3; + SHA-256 went up by 25%. + * New variants of the TIGER algorithm. + * New cipher algorithm mode for AES-WRAP. + * Interface changes relative to the 1.4.2 release: + GCRY_MD_TIGER1 NEW + GCRY_MD_TIGER2 NEW + GCRY_CIPHER_MODE_AESWRAP NEW + +------------------------------------------------------------------- +Sun Jul 4 19:07:16 UTC 2010 - jengelh@medozas.de + +- add missing definition of udiv_qrnnd for sparcv9:32 +- use %_smp_mflags + +------------------------------------------------------------------- +Sat Dec 19 12:58:20 CET 2009 - jengelh@medozas.de + +- add baselibs.conf as a source +- disable the use of hand-coded assembler functions on sparc - + this is giving me an infinite loop with ./tests/prime + (specifically ./sparc32v8/mpih-mul1.S:_gcry_mpih_mul_1. + Fedora disables this too. + +------------------------------------------------------------------- +Tue Apr 7 15:45:06 CEST 2009 - crrodriguez@suse.de + +- update to version 1.4.4 + * Publish GCRY_MODULE_ID_USER and GCRY_MODULE_ID_USER_LAST constants. + This functionality has been in Libgcrypt since 1.3.0. + * MD5 may now be used in non-enforced fips mode. + * Fixed HMAC for SHA-384 and SHA-512 with keys longer than 64 bytes. + * In fips mode, RSA keys are now generated using the X9.31 algorithm + and DSA keys using the FIPS 186-2 algorithm. + * The transient-key flag is now also supported for DSA key + generation. DSA domain parameters may be given as well. + +------------------------------------------------------------------- +Thu Jan 29 10:57:01 CET 2009 - olh@suse.de + +- obsolete libgcrypt-error-XXbit in the library subpackage + +------------------------------------------------------------------- +Wed Dec 10 12:34:56 CET 2008 - olh@suse.de + +- use Obsoletes: -XXbit only for ppc64 to help solver during distupgrade + (bnc#437293) + +------------------------------------------------------------------- +Tue Nov 11 17:23:54 CET 2008 - mkoenig@suse.de + +- build rijndael.c with -fno-strict-aliasing [bnc#443693] + +------------------------------------------------------------------- +Thu Oct 30 12:34:56 CET 2008 - olh@suse.de + +- obsolete old -XXbit packages (bnc#437293) + +------------------------------------------------------------------- +Mon Jun 30 11:47:59 CEST 2008 - mkoenig@suse.de + +- update to version 1.4.1 + * Fixed a bug which led to the comsumption of far too much + entropy for the intial seeding + * Improved AES performance for CFB and CBC modes + +------------------------------------------------------------------- +Sun May 11 11:54:39 CEST 2008 - coolo@suse.de + +- fix rename of xxbit packages + +------------------------------------------------------------------- +Thu Apr 10 12:54:45 CEST 2008 - ro@suse.de + +- added baselibs.conf file to build xxbit packages + for multilib support + +------------------------------------------------------------------- +Thu Jan 17 12:20:25 CET 2008 - mkoenig@suse.de + +- update to version 1.4.0: + * The entire library is now under the LGPL. The helper programs and + the manual are under the GPL + * New control code GCRYCTL_PRINT_CONFIG + * Experimental support for ECDSA + * Assembler support for the AMD64 architecture + * Non executable stack support is now used by default + * New configure option --enable-random-daemon + * The new function gcry_md_debug should be used instead of the + gcry_md_start_debug and gcry_md_stop_debug macros. + * Support for DSA2 + * Reserved algorithm ranges for use by applications + * gcry_mpi_rshift does not anymore truncate the shift count + * Support for OFB encryption mode + * Support for the Camellia cipher + * Support for the SEED cipher + * Support for SHA-224 and HMAC using SHA-384 and SHA-512 + * Reading and writing the random seed file is now protected by a + fcntl style file lock + * Made the RNG immune against fork without exec + * Changed the way the RNG gets initialized + * The ASN.1 DER template for SHA-224 has been fixed + * The ACE engine of VIA processors is now used for AES-128 +- changed package layout to conform shlib policy: + new subpackage libgcrypt11 +- disable static library +- for reference: bugzilla entry of last change #304749 + +------------------------------------------------------------------- +Thu Sep 13 01:28:53 CEST 2007 - ltinkl@suse.cz + +- add sanity check for mpi of size 0 (#304479) + +------------------------------------------------------------------- +Mon Feb 5 10:25:21 CET 2007 - mkoenig@suse.de + +- update to version 1.2.4: + * Fixed a bug in the memory allocator which could have been the + reason for some of non-duplicable bugs. + * Other minor bug fixes. + +------------------------------------------------------------------- +Wed Dec 13 12:47:48 CET 2006 - mkoenig@suse.de + +- get rid of .la file and fix devel so link + +------------------------------------------------------------------- +Tue Dec 5 18:30:30 CET 2006 - mkoenig@suse.de + +- move shared lib to /%_lib + +------------------------------------------------------------------- +Thu Aug 31 14:29:56 CEST 2006 - mkoenig@suse.de + +- update to version 1.2.3: + * Rewrote gcry_mpi_rshift to allow arbitrary shift counts. + * Minor bug fixes. +- added libgpg-error-devel and glibc-devel to Requires tag + of devel subpackage + +------------------------------------------------------------------- +Wed Jan 25 21:37:28 CET 2006 - mls@suse.de + +- converted neededforbuild to BuildRequires + +------------------------------------------------------------------- +Wed Nov 2 16:44:48 CET 2005 - hvogel@suse.de + +- enable noexecstack +- build ac.c with fno-strict-aliasing + +------------------------------------------------------------------- +Tue Oct 25 13:40:15 CEST 2005 - hvogel@suse.de + +- update to version 1.2.2 + +------------------------------------------------------------------- +Thu Jun 23 11:26:58 CEST 2005 - hvogel@suse.de + +- call install_info macro in post/postun of the devel package +- depend on libgcrypt +- add clean section + +------------------------------------------------------------------- +Tue Jan 18 11:51:51 CET 2005 - hvogel@suse.de + +- update to version 1.2.1 + +------------------------------------------------------------------- +Tue Jan 11 16:48:10 CET 2005 - schwab@suse.de + +- Fix info dir entry. + +------------------------------------------------------------------- +Wed Nov 17 11:22:44 CET 2004 - hvogel@suse.de + +- require libgpg-error-devel (Bug #48271) +- get rid of the NLD parts + +------------------------------------------------------------------- +Wed Jul 14 11:12:54 CEST 2004 - adrian@suse.de + +- create -devel subpackage +- prepare for nld + +------------------------------------------------------------------- +Wed May 19 14:57:45 CEST 2004 - hvogel@suse.de + +- update to version 1.2.0 + +------------------------------------------------------------------- +Mon Mar 22 16:48:53 CET 2004 - meissner@suse.de + +- disable make check, because it uses /dev/random whihc is + not filled on some server machines. + +------------------------------------------------------------------- +Wed Mar 17 15:01:51 CET 2004 - meissner@suse.de + +- fixed too over enthusiastic powerpc switches to make it work + on ppc64. (It compiled before, but did not work). +- enabled make check. + +------------------------------------------------------------------- +Wed Feb 18 12:14:36 CET 2004 - kukuk@suse.de + +- Build against system pthread library, not pth. + +------------------------------------------------------------------- +Tue Feb 17 21:11:40 CET 2004 - hvogel@suse.de + +- update to version 1.1.91 +- fix autoconf quotations + +------------------------------------------------------------------- +Sat Jan 10 19:20:41 CET 2004 - adrian@suse.de + +- add %run_ldconfig to %postun + +------------------------------------------------------------------- +Sun Jul 27 16:12:54 CEST 2003 - poeml@suse.de + +- add libgcrypt-1.1.12-sexp-valgrind-error.patch from SLEC + +------------------------------------------------------------------- +Thu Apr 24 12:20:23 CEST 2003 - ro@suse.de + +- fix install_info --delete call and move from preun to postun + +------------------------------------------------------------------- +Mon Feb 10 22:51:26 CET 2003 - mmj@suse.de + +- Use %install_info macro [#23433] + +------------------------------------------------------------------- +Mon Feb 10 16:11:55 CET 2003 - mc@suse.de + +- switch to version 1.1.12 +- gcry_pk_sign, gcry_pk_verify and gcry_pk_encrypt can now handle an + optional pkcs1 flags parameter in the S-expression. A similar flag + may be passed to gcry_pk_decrypt but it is only syntactically + implemented. +- New convenience macro gcry_md_get_asnoid. +- There is now some real stuff in the manual. +- New algorithm: MD4 +- Implemented ciphertext stealing. +- Support for plain old DES +- Smaller bugs fixes and a few new OIDs. + +------------------------------------------------------------------- +Tue Jan 14 14:03:27 CET 2003 - nadvornik@suse.cz + +- fixed multi-line string literals + +------------------------------------------------------------------- +Thu Aug 1 23:51:10 CEST 2002 - poeml@suse.de + +- create package + diff --git a/libgcrypt.keyring b/libgcrypt.keyring new file mode 100644 index 0000000..dd3bb0b --- /dev/null +++ b/libgcrypt.keyring @@ -0,0 +1,86 @@ +-----BEGIN PGP PUBLIC KEY BLOCK----- + +mQGNBFjLuq4BDACnM7zNSIaVMAacTwjXa5TGYe13i6ilHe4VL0NShzrgzjcQg531 +3cRgiiiNA7OSOypMqVs73Jez6ZUctn2GVsHBrS/io9NcuC9pVwf8a61WlcEa+EtB +a3G7HlBmEWnwaUdAtWKNuAi9Xn+Ir7H2xEdksmmd5a0/QnL+sX705boVPF/tpYtb +LGpPxa78tNrtxDkSwy8Wmi0IADYLI5yI7/yUGeJd8RSCU/fLRKC9fG7YOZRq0tsO +MhVNWmtUjbG6e73Lu8LKnCZgs1/fC8hvPyARieSV5mdN8s1oWd7oYctfgL4uBleD +ItAA8GhjKejutzHN8Ei/APw6AiiSyEjnPg+cTX8OgvLGJWjks0H6mPZeB1v/kGyZ +hBS9vm540h2/MmlVN2ntiCK5TZGeSWpqddiqusfVXotMRpN4HeLKoZh4RAncaCbZ +F/S+YLeN+kMXY4k3Fqt1fjTX6veFCbthI9pDdHzU9LfUVNp9D/5ktC/tYMORMegV ++wSMxi9G2YWKJkMAEQEAAYkBzgQfAQgAOBYhBFuAxXVCmPDLVdjtarzvfilLCS4o +BQJYy8DdFwyAAZSlyaA8L+XKOwldjh/fcjz0YraxAgcAAAoJELzvfilLCS4oNgoL +/0+K1xIx8JW7Lk5M6bYCvNA4fdlEcwQIT4UidJFM9m+suxYFWIGfebvHpRlEuJTg +dBjkEit8uLAoJXU0BRkKTLrzTF+qDUE79Wfx/R+0nOgJ7aMykQOi0AvuwzMYz4dg +xIVS2Daou4DF7bh/KF8+fqrmq8P8W1ZrkuFDanMWpHeAPx1uj2skYbo7uPqFdvlJ +hlNHrcxlcCkjf1InAt0Xt5lMvEsCRUPf9xAH4mNEhs0lh9c+200YPRmtnLWAzc1K +ckLIC8Q+mUR3DjZDqBlDBEPegXkrI0+MlvRA+9AnAm4YPqTMUfpZ6ZOAWeFjC/6Z +QYxG/AdWGkb4WFindzklQfybEuiekP8vU07ACQwSwH8PYe0UCom1YrlRUjX7QLkn +ZLWoeZg8BZy9GTM1Ut7Q1Q2uTw6mxxISuef+RFgYOHjWwLpFWZpqC88xERl7o/iz +iERJRt/593IctbjO9wenWt2peIAwzR4nz7LqM6ZFTdRAETmcdSvYRhg2Qt8hUE47 +CbQkQW5kcmUgSGVpbmVja2UgKFJlbGVhc2UgU2lnbmluZyBLZXkpiQHUBBMBCAA+ +FiEEW4DFdUKY8MtV2O1qvO9+KUsJLigFAljLuq4CGwMFCRLMAwAFCwkIBwIGFQgJ +CgsCBBYCAwECHgECF4AACgkQvO9+KUsJLihC/QwAhCC+SEvcFLcutgZ8HfcCtoZs +IoVzZEy7DjqIvGgnTssD8HCLnIAHCDvnP7dJW3uMuLCdSqym3cjlEIiQMsaGywkl +fzJISAwJrGQdWSKRd535jXpEXQlXDKal/IwMKAUt0PZtlCc9S3gwixQryxdJ28lJ +6h2T9fVDr8ZswMmTAFG91uctfhjKOMgPt8UhSPGW484WsIsQgkbOvf+Kfswl0eHu +ywX+pKAB5ZQ/9GVC6Ug4xfrdiJL0azJTPnvjMY5JYp6/L9RURs5hP5AnHR2j/PPo +sAtsFCjmbRbOMiASzklnUJPbSz5kfLloDWZmrUScjbzmsXehGyt433JGyRhZJl4x +/jPbzKhaaAHsGd+fRao6vlLOwFywDDVMp6JuyK7UeUb7I8ekTbSkGFA+l2Oa3O6/ +Y7PYhq7hwwAFuZckYI98IpHNCG1fS9W07FyKdvQbK1PbF1JFRKfsUCWYMKqDnbqE +o5jivPEHZImw6iYhhXcyEYl8fjcb9T6/S+wOP7aviQGzBBABCAAdFiEElKXJoDwv +5co7CV2OH99yPPRitrEFAljLv5sACgkQH99yPPRitrFw4gv/XFMFN+/LHsn9hJOP +4rCwl1yUuxXuYmZgc0sRoY3EpeQkJVyKurQuqqKoy2VuoMiF0O1kAQmGoFtVPUk7 +b8hCoutqB5GyeyKcoLP+WINgVhB2gXg7TSp3MPLBKkgqvSDvPitgRxBqFb4LW8LJ +bDbfwGrzIvXfDV3WvsrHVPbc2fhlWdL8d+3AE6mFiXF3eTpgmV3ApSBQV12MkkCk +icLIPmp+ZxZON+OP52ZXkRtfMgOy4Oa/41agrViDAZdMOGeGkhPertQheQZgXzmo +GF5Wz498HPM80Kv35X91l3iGzL+icEtO+tWea2YscsZ6qpRe2lfVPHk3B+anlmCj +m4kM4cBd39xa4HHSVh/bRHbZNtgVr7slQCKxlHgQOGVI5vCxPCwEsgJ2KBk03Nk/ +IA9EKO+czfh3/bHW6uMbEqrYDCnt+hmzZrpKDSGcwS/KOhvMUIMlb7/8vDKum6mp +/8xAtVZ6IAxYZNt3qg7Y7aLRtzCTyqm8rJQrZPtRaQcgLoEimDMEX0PliRYJKwYB +BAHaRw8BAQdAz75Hlekc16JhhfI0MKdEVxLdkxhcMCO0ZG6WMBAmNpe0H1dlcm5l +ciBLb2NoIChkaXN0IHNpZ25pbmcgMjAyMCmImgQTFgoAQhYhBG2qbmSnbShAVxtJ +AlKIl7gmQDraBQJfQ+w1AhsDBQkShccRBQsJCAcCAyICAQYVCgkICwIEFgIDAQIe +BwIXgAAKCRBSiJe4JkA62nmuAP9uL/HOdB0gvwWrH+FpURJLs4bnaZaPIk9ARrU0 +EXRgJgD/YCGfHQXpIPT0ZaXuwJexK04Z+qMFR/bM1q1Leo5CjgaIbQQQEQsAHRYh +BIBhWHD1utaQMzaG0PKthaweQrNnBQJfQ/HmAAoJEPKthaweQrNnIZkA3jG6LcZv +V/URn8Y8OJqsyYa4C3NI4nN+OhEvYhgA4PHzMnALeXIpA2gblvjFIPJPAhDBAU37 +c5PA6+6IdQQQFggAHRYhBK6oTtzwGthsRwHIXGMROuhmWH0KBQJfQ/IlAAoJEGMR +OuhmWH0K1+MA/0uJ5AHcnSfIBEWHNJwwVVLGyrxAWtS2U+zeymp/UvlPAQDErCLZ +l0dBiPG3vlowFx5TNep7tanBs6ZJn8F1ao1tAIkBMwQQAQgAHRYhBNhpISPEBl3q +Xg86tSSbOdJPJeO2BQJfQ/OuAAoJECSbOdJPJeO2DVoH/0o9if66ph6FJrgr+A/W +HNVeHxmM5tUQhpL1wpRS70SKcsJgolf5CxO5iTQf3HlZe544xGbIU/aCTJsWw9zi +UE8KmhAtKV4eL/7oQ7xx4nxPnABLpudtM8A44nsM1x/XiYrJnnDm29QjYEGd2Hi8 +7npc7VWKzLoj+I/WcXquynJi5O9TUxW9Bknd1pjpxFkf8v+msjBzCD5VKJgr0CR8 +wA6peQBWeGZX2HacosMIZH4TfL0r0TFla6LJIkNBz9DyIm1yL4L8oRH0950hQljP +C7TM3L7aRpX+4Kph6llFz6g7MALGFP95kyJ6o+XED9ORuuQVZMBMIkNC0tXOu10V +bdqIdQQQFgoAHRYhBMHTS2khnkruwLocIeP9/yGORbcrBQJfQ/P8AAoJEOP9/yGO +Rbcr3lQBAMas8Vl3Hdl3g2I283lz1uHiGvlwcnk2TLeB+U4zIwC9AQCy0nnazVNt +VQPID1ZCMoaOX7AzOjaqQDLf4j+dVTxgBJgzBGCkgocWCSsGAQQB2kcPAQEHQJmd +fwp8jEN5P3eEjhQiWk6zQi8utvgOvYD57XmE+H8+tCBOaWliZSBZdXRha2EgKEdu +dVBHIFJlbGVhc2UgS2V5KYiaBBMWCgBCFiEErI4RW/c+LY1H+pkI6Y6bLRnGyL0F +AmCkgocCGwMFCQsNBpkFCwkIBwIDIgIBBhUKCQgLAgQWAgMBAh4HAheAAAoJEOmO +my0Zxsi9/4IA/1rvSr3MU+Sv4jhNDzD+CeC3gmHkPew6pi9VHEsEwdgmAQD2BtiX +7w1sJL/CBylGWv5jxj4345mP9YfZm0RsgzPjDIh1BBAWCAAdFiEEJJyzdxdQdF1c +3TI84mewUjZPAo0FAmFAQ54ACgkQ4mewUjZPAo1CiAD+KTT1UVdQTGHMyvHwZocS +QjU8xhcZrTet+dvvjrE5+4MA/RBdJPZgFevUKu68NEy0Lo+RbkeCtmQJ/c8v5ieF +vW0AiQEzBBABCAAdFiEEEkEkvTtIYq96CkLxALRevUynur4FAmFAQ7cACgkQALRe +vUynur4kaAgAolPR8TNWVS0vXMKrr0k0l2M/8QkZTaLZx1GT9Nx1yb4WJKY7ElPM +YkhGDxetvFBETx0pH/6R3jtj6Crmur+NKHVSRY+rCYpFPDn6ciIOryssRx2G4kCZ +t+nFB9JyDbBOZAR8DK4pN1mAxG/yLDt4oKcUQsP2xlEFum+phxyR8KyYCpkwKRxY +eK+6lfilQuveoUwp/Xx5wXPNUy6q4eOOovCW7gS7I7288NGHCa2ul8sD6vA9C4mM +4Zxaole9P9wwJe1zZFtCIy88zHM9vqv+YM9DxMCaW24+rUztr7eD4bCRdG+QlSh+ +7R/TaqSxY1eAAd1J5tma9CNJO73pTKU+/JhTBGFpSqMTCSskAwMCCAEBBwIDBF6X +D9NmUQDgiyYNbhs1DMJ14mIw812wY1HVx/4QWYWiBunhrvSFxVbzsjD7/Wv+v3bm +MPrL+M2DLyFiSewNmcS0JEdudVBHLmNvbSAoUmVsZWFzZSBTaWduaW5nIEtleSAy +MDIxKYiaBBMTCABCFiEEAvON/3Mf+XywOaHaVJ5pXpBboggFAmFpSqMCGwMFCQ9x +14oFCwkIBwIDIgIBBhUKCQgLAgQWAgMBAh4HAheAAAoJEFSeaV6QW6IITkoA/RYa +jaTl1eEBU/Gdm12o3jrI55N5xZK2XTqSx25clVyjAP0XwMW/Og5+ND1ri3bAqADV +WlBDUswz8wYxsb0C4kYBkoh1BBAWCgAdFiEEbapuZKdtKEBXG0kCUoiXuCZAOtoF +AmFpTvEACgkQUoiXuCZAOtrJQAEAh7YyykjAy/Qs1yC3ji8iBfIVnPXvblrIx3SR +RyDwRC8BAKtZbEuKTtPlgkLUgMleTcZJ/vEhJE+GvfQ9o5gWCqEFiHUEEBYKAB0W +IQTB00tpIZ5K7sC6HCHj/f8hjkW3KwUCYWlPWgAKCRDj/f8hjkW3Kx4eAQDp6aGS +N/fU4xLl8RSvQUVjVA+aCTrMQR3hRwqw8liF2wEA3O3ECxz6e1+DoItYoJBBLKLw +eiInsGZ/+h5XYrpXTgA= +=4+Sn +-----END PGP PUBLIC KEY BLOCK----- diff --git a/libgcrypt.spec b/libgcrypt.spec new file mode 100644 index 0000000..26df382 --- /dev/null +++ b/libgcrypt.spec @@ -0,0 +1,200 @@ +# +# spec file for package libgcrypt +# +# Copyright (c) 2025 SUSE LLC +# +# All modifications and additions to the file contributed by third parties +# remain the property of their copyright owners, unless otherwise agreed +# upon. The license for this file, and modifications and additions to the +# file, is the same license as for the pristine package itself (unless the +# license for the pristine package is not an Open Source License, in which +# case the license is the MIT License). An "Open Source License" is a +# license that conforms to the Open Source Definition (Version 1.9) +# published by the Open Source Initiative. + +# Please submit bugfixes or comments via https://bugs.opensuse.org/ +# + + +%define libsover 20 +%define libsoname %{name}%{libsover} +%define hmac_key orboDeJITITejsirpADONivirpUkvarP +Name: libgcrypt +Version: 1.11.1 +Release: 0 +Summary: The GNU Crypto Library +License: GPL-2.0-or-later AND LGPL-2.1-or-later AND GPL-3.0-or-later +Group: Development/Libraries/C and C++ +URL: https://gnupg.org/software/libgcrypt +Source: https://gnupg.org/ftp/gcrypt/libgcrypt/%{name}-%{version}.tar.bz2 +Source1: https://gnupg.org/ftp/gcrypt/libgcrypt/%{name}-%{version}.tar.bz2.sig +Source2: baselibs.conf +Source3: random.conf +Source4: hwf.deny +# https://www.gnupg.org/signature_key.html +Source5: https://gnupg.org/signature_key.asc#/%{name}.keyring +Source99: libgcrypt.changes +Patch1: libgcrypt-1.10.0-allow_FSM_same_state.patch +#PATCH-FIX-OPENSUSE Do not pull revision info from GIT when autoconf is run +Patch2: libgcrypt-nobetasuffix.patch +#PATCH-FIX-SUSE: Make the revamped SLI api public +Patch3: libgcrypt-1.11.1-public-SLI-API.patch +# FIPS patches: +#PATCH-FIX-SUSE bsc#1190700 FIPS: Provide a service-level indicator for PK +Patch100: libgcrypt-FIPS-SLI-pk.patch +#PATCH-FIX-SUSE bsc#1190700 FIPS: Check keylength in gcry_fips_indicator_kdf() +Patch101: libgcrypt-FIPS-SLI-kdf-leylength.patch +#PATCH-FIX-SUSE bsc#1190700 FIPS add indicators +Patch102: libgcrypt-FIPS-SLI-hash-mac.patch +#PATCH-FIX-SUSE bsc#1202117 FIPS: Get most of the entropy from rndjent_poll +Patch104: libgcrypt-FIPS-rndjent_poll.patch +#PATCH-FIX-SUSE bsc#1220896 FIPS: Replace the built-in jitter rng with standalone version +Patch105: libgcrypt-FIPS-jitter-standalone.patch +#PATCH-FIX-SUSE bsc#1220895 FIPS: Enforce the interpretation and use of jitter rng +Patch106: libgcrypt-FIPS-jitter-errorcodes.patch +#PATCH-FIX-SUSE bsc#1220893 FIPS: Use Jitter RNG for the whole length entropy buffer +Patch107: libgcrypt-FIPS-jitter-whole-entropy.patch +#PATCH-FIX-SUSE Remove not used rol64() definition after removing the built-in jitter rng +Patch108: libgcrypt-rol64-redefinition.patch +#PATCH-FIX-CENTOS timing based side-channel in RSA implementation +Patch109: libgcrypt-CVE-2024-2236.patch + +BuildRequires: automake >= 1.14 +BuildRequires: libgpg-error-devel >= 1.49 +BuildRequires: libtool +BuildRequires: makeinfo +BuildRequires: pkgconfig +%{?suse_build_hwcaps_libs} + +%description +Libgcrypt is a general purpose library of cryptographic building +blocks. It is originally based on code used by GnuPG. It does not +provide any implementation of OpenPGP or other protocols. Thorough +understanding of applied cryptography is required to use Libgcrypt. + +%package -n %{libsoname} +Summary: The GNU Crypto Library +License: GPL-2.0-or-later AND LGPL-2.1-or-later +Group: System/Libraries +BuildRequires: jitterentropy-devel >= 3.4.0 +Requires: libjitterentropy3 >= 3.4.0 +Provides: %{libsoname}-hmac = %{version}-%{release} +Obsoletes: %{libsoname}-hmac < %{version}-%{release} + +%description -n %{libsoname} +Libgcrypt is a general purpose crypto library based on the code used in +GnuPG (alpha version). + +%package devel +Summary: The GNU Crypto Library +License: GFDL-1.1-only AND GPL-2.0-or-later AND LGPL-2.1-or-later AND MIT +Group: Development/Libraries/C and C++ +Requires: %{libsoname} = %{version} +Requires: glibc-devel +Requires: jitterentropy-devel >= 3.4.0 +Requires: libgpg-error-devel >= 1.49 + +%description devel +Libgcrypt is a general purpose library of cryptographic building +blocks. It is originally based on code used by GnuPG. It does not +provide any implementation of OpenPGP or other protocols. Thorough +understanding of applied cryptography is required to use Libgcrypt. + +This package contains needed files to compile and link against the +library. + +%prep +%autosetup -p1 + +# Rename the internal .hmac file to include the so library version +sed -i "s/libgcrypt\.so\.hmac/\.libgcrypt\.so\.%{libsover}\.hmac/g" src/Makefile.am src/Makefile.in + +# Replace the built-in jitter rng with the standalone version [bsc#1220896] +find . -type f -name "jitterentropy*" -print -delete + +%build +export PUBKEYS="dsa elgamal rsa ecc" +export CIPHERS="arcfour blowfish cast5 des aes twofish serpent rfc2268 seed camellia idea salsa20 gost28147 chacha20 sm4 aria" +export DIGESTS="crc gostr3411-94 md4 md5 rmd160 sha1 sha256 sha512 sha3 tiger whirlpool stribog blake2 sm3" +export KDFS="s2k pkdf2 scrypt" + +autoreconf -fi +date=$(date -u '+%%Y-%%m-%%dT%%H:%%M+0000' -r %{SOURCE99}) +sed -e "s,BUILD_TIMESTAMP=.*,BUILD_TIMESTAMP=$date," -i configure +export CFLAGS="%{optflags} $(getconf LFS_CFLAGS)" +%configure \ + --with-fips-module-version="Libgcrypt version %{version}-%{release}" \ + --enable-hmac-binary-check="%{hmac_key}" \ + --enable-ciphers="$CIPHERS" \ + --enable-pubkey-ciphers="$PUBKEYS" \ + --enable-digests="$DIGESTS" \ + --enable-kdfs="$KDFS" \ + --enable-noexecstack \ + --enable-marvin-workaround \ + --disable-static \ +%ifarch %{sparc} + --disable-asm \ +%endif + --enable-random=getentropy \ + --enable-jent-support \ + %{nil} + +%make_build + +%check +make -k check +# run the regression tests also in FIPS mode +LIBGCRYPT_FORCE_FIPS_MODE=1 make -k check + +%install +%make_install + +# this is a hack that re-defines the __spec_install_post macro +# for a simple reason: the macro strips the binaries and thereby +# invalidates a HMAC that may have been created earlier. +# solution: create the hashes _after_ the macro runs. +%define libpath %{buildroot}%{_libdir}/libgcrypt.so.%{libsover}.?.? +%define __spec_install_post \ + %{?__debug_package:%{__debug_install_post}} \ + %{__arch_install_post} \ + %{__os_install_post} \ + cd src \ + sed -i -e 's|FILE=.*|FILE=\\\$1|' gen-note-integrity.sh \ + READELF=readelf AWK=awk ECHO_N="-n" bash gen-note-integrity.sh %{libpath} > %{libpath}.hmac \ + objcopy --update-section .note.fdo.integrity=%{libpath}.hmac %{libpath} %{libpath}.new \ + mv -f %{libpath}.new %{libpath} \ + rm -f %{libpath}.hmac \ +%{nil} + +rm %{buildroot}%{_libdir}/%{name}.la + +# Create /etc/gcrypt directory and install random.conf +mkdir -p -m 0755 %{buildroot}%{_sysconfdir}/gcrypt +install -m 644 %{SOURCE3} %{buildroot}%{_sysconfdir}/gcrypt/random.conf +install -m 644 %{SOURCE4} %{buildroot}%{_sysconfdir}/gcrypt/hwf.deny + +%post -n %{libsoname} -p /sbin/ldconfig +%postun -n %{libsoname} -p /sbin/ldconfig + +%files -n %{libsoname} +%license COPYING COPYING.LIB LICENSES +%doc AUTHORS ChangeLog NEWS README THANKS TODO +%{_libdir}/%{name}.so.* +%dir %{_sysconfdir}/gcrypt +%config(noreplace) %{_sysconfdir}/gcrypt/random.conf +%config(noreplace) %{_sysconfdir}/gcrypt/hwf.deny + +%files devel +%license COPYING COPYING.LIB LICENSES +%{_bindir}/dumpsexp +%{_bindir}/hmac256 +%{_bindir}/mpicalc +%{_bindir}/%{name}-config +%{_libdir}/%{name}.so +%{_libdir}/pkgconfig/libgcrypt.pc +%{_datadir}/aclocal/%{name}.m4 +%{_includedir}/gcrypt*.h +%{_infodir}/gcrypt.info*%{ext_info}* +%{_mandir}/man1/* + +%changelog diff --git a/random.conf b/random.conf new file mode 100644 index 0000000..378ba78 --- /dev/null +++ b/random.conf @@ -0,0 +1,9 @@ +# This file can be used to globally change parameters of +# the random generator. Supported options are: + +# Always use the non-blocking /dev/urandom or the respective +# system call instead of the blocking /dev/random. +# only-urandom + +# Disable the use of the jitter based entropy generator. +# disable-jent -- 2.51.1 From c4e721bdfb548c743e7d166b640cacc23af571f28ee05109a89dead0552e925e Mon Sep 17 00:00:00 2001 From: Lucas Mulling Date: Tue, 12 Aug 2025 15:27:49 +0000 Subject: [PATCH 8/8] libgcrypt 1.11.2 OBS-URL: https://build.opensuse.org/package/show/devel:libraries:c_c++/libgcrypt?expand=0&rev=195 --- .gitattributes | 23 + .gitignore | 1 + baselibs.conf | 8 + hwf.deny | 34 + libgcrypt-1.10.0-allow_FSM_same_state.patch | 15 + libgcrypt-1.10.3.tar.bz2 | 3 + libgcrypt-1.10.3.tar.bz2.sig | Bin 0 -> 238 bytes libgcrypt-1.11.0.tar.bz2 | 3 + libgcrypt-1.11.0.tar.bz2.sig | Bin 0 -> 119 bytes libgcrypt-1.11.1-public-SLI-API.patch | 37 + libgcrypt-1.11.1.tar.bz2 | 3 + libgcrypt-1.11.1.tar.bz2.sig | Bin 0 -> 119 bytes libgcrypt-1.11.2.tar.bz2 | 3 + libgcrypt-1.11.2.tar.bz2.sig | Bin 0 -> 147 bytes libgcrypt-CVE-2024-2236.patch | 1839 +++++++++++++++ ...poly1305-Optimized-chacha20-poly1305.patch | 1993 ++++++++++++++++ ...e-SHA3-s390x-acceleration-for-CSHAKE.patch | 61 + libgcrypt-FIPS-SLI-hash-mac.patch | 172 ++ libgcrypt-FIPS-SLI-kdf-leylength.patch | 60 + libgcrypt-FIPS-SLI-pk.patch | 177 ++ libgcrypt-FIPS-jitter-errorcodes.patch | 16 + libgcrypt-FIPS-jitter-standalone.patch | 183 ++ libgcrypt-FIPS-jitter-whole-entropy.patch | 41 + libgcrypt-FIPS-rndjent_poll.patch | 114 + libgcrypt-Fix-the-previous-change.patch | 45 + ...ild-Improve-__thread-specifier-check.patch | 41 + ...T-for-non-rfc6979-ECDSA-with-fixed-k.patch | 94 + ...on-compliant-cipher-modes-in-the-SLI.patch | 236 ++ ...-Differentiate-igninvflag-in-the-SLI.patch | 40 + ...rentiate-no-blinding-flag-in-the-SLI.patch | 70 + ...ferentiate-use-of-label-K-in-the-SLI.patch | 139 ++ ...e-GCRY_CIPHER_MODE_CMAC-in-FIPS-mode.patch | 98 + ...-_gcry_cipher_is_mode_fips_compliant.patch | 64 + libgcrypt-cipher-ecc-Fix-for-supplied-K.patch | 88 + ...-cipher-fips-Fix-for-random-override.patch | 83 + ...nknown-with-RSA-signature-generation.patch | 445 ++++ ...te-use-of-random-override-in-the-SLI.patch | 107 + ...about-GCRYCTL_FIPS_SERVICE_INDICATOR.patch | 66 + libgcrypt-doc-Fix-syntax-error.patch | 31 + ...l-API-for-new-FIPS-service-indicator.patch | 140 ++ ...pt-fips-Fix-GCRY_FIPS_FLAG_REJECT_MD.patch | 42 + ...troduce-GCRYCTL_FIPS_REJECT_NON_FIPS.patch | 261 +++ ...FIPS_SERVICE_INDICATOR-and-the-macro.patch | 101 + ...ernal-API-for-FIPS-service-indicator.patch | 332 +++ ...PS_REJECT_NON_FIPS-not-by-open-flags.patch | 498 ++++ ...r-Add-GCRY_FIPS_FLAG_REJECT_PK_FLAGS.patch | 80 + ...not-to-reject-but-mark-non-compliant.patch | 300 +++ ...mputation-when-marking-non-compliant.patch | 160 ++ ...ix-memory-leak-for-gcry_pk_hash_sign.patch | 76 + ...vice-indicator-for-gcry_pk_hash_-API.patch | 360 +++ ...PS-service-indicator-for-cipher_open.patch | 122 + ...ing-or-marking-for-gcry_pk_get_curve.patch | 43 + ...-in-gcry_pk_sign-verify-in-FIPS-mode.patch | 282 +++ ...ervice-indicator-for-gcry_kdf_derive.patch | 265 +++ ...-service-indicator-for-gcry_mac_open.patch | 115 + ...-service-indicator-for-gcry_md_hash_.patch | 188 ++ ...rvice-indicator-for-gcry_md_open-API.patch | 298 +++ ...ld-care-about-FIPS-service-indicator.patch | 85 + libgcrypt-fips-tests-Add-t-digest.patch | 243 ++ ...d_open-write-read-close-for-t-digest.patch | 172 ++ libgcrypt-jitterentropy-3.4.0.patch | 618 +++++ ..._info-to-mark-reject-under-FIPS-mode.patch | 82 + ...A-1-non-FIPS-internally-for-1.12-API.patch | 154 ++ ...igest_algo_spec-in-_gcry_md_selftest.patch | 74 + libgcrypt-no-deprecated-grep-alias.patch | 35 + libgcrypt-nobetasuffix.patch | 24 + ...e-P10-assembly-with-ENABLE_FORCE_SOF.patch | 76 + libgcrypt-rol64-redefinition.patch | 16 + ...re-tests-to-tests-t-fips-service-ind.patch | 382 ++++ ...crypt-tests-Allow-tests-with-USE_RSA.patch | 44 + ...d-using-GCRY_MD_SHA256-for-KDF-tests.patch | 106 + ...ests-fips-Add-gcry_cipher_open-tests.patch | 199 ++ ...t-tests-fips-Add-gcry_mac_open-tests.patch | 206 ++ ...Move-KDF-tests-to-t-fips-service-ind.patch | 375 +++ ...tests-fips-Rename-t-fips-service-ind.patch | 60 + libgcrypt.changes | 2023 +++++++++++++++++ libgcrypt.keyring | 82 + libgcrypt.spec | 200 ++ random.conf | 9 + 79 files changed, 15361 insertions(+) create mode 100644 .gitattributes create mode 100644 .gitignore create mode 100644 baselibs.conf create mode 100644 hwf.deny create mode 100644 libgcrypt-1.10.0-allow_FSM_same_state.patch create mode 100644 libgcrypt-1.10.3.tar.bz2 create mode 100644 libgcrypt-1.10.3.tar.bz2.sig create mode 100644 libgcrypt-1.11.0.tar.bz2 create mode 100644 libgcrypt-1.11.0.tar.bz2.sig create mode 100644 libgcrypt-1.11.1-public-SLI-API.patch create mode 100644 libgcrypt-1.11.1.tar.bz2 create mode 100644 libgcrypt-1.11.1.tar.bz2.sig create mode 100644 libgcrypt-1.11.2.tar.bz2 create mode 100644 libgcrypt-1.11.2.tar.bz2.sig create mode 100644 libgcrypt-CVE-2024-2236.patch create mode 100644 libgcrypt-Chacha20-poly1305-Optimized-chacha20-poly1305.patch create mode 100644 libgcrypt-Disable-SHA3-s390x-acceleration-for-CSHAKE.patch create mode 100644 libgcrypt-FIPS-SLI-hash-mac.patch create mode 100644 libgcrypt-FIPS-SLI-kdf-leylength.patch create mode 100644 libgcrypt-FIPS-SLI-pk.patch create mode 100644 libgcrypt-FIPS-jitter-errorcodes.patch create mode 100644 libgcrypt-FIPS-jitter-standalone.patch create mode 100644 libgcrypt-FIPS-jitter-whole-entropy.patch create mode 100644 libgcrypt-FIPS-rndjent_poll.patch create mode 100644 libgcrypt-Fix-the-previous-change.patch create mode 100644 libgcrypt-build-Improve-__thread-specifier-check.patch create mode 100644 libgcrypt-cipher-Add-KAT-for-non-rfc6979-ECDSA-with-fixed-k.patch create mode 100644 libgcrypt-cipher-Check-and-mark-non-compliant-cipher-modes-in-the-SLI.patch create mode 100644 libgcrypt-cipher-Differentiate-igninvflag-in-the-SLI.patch create mode 100644 libgcrypt-cipher-Differentiate-no-blinding-flag-in-the-SLI.patch create mode 100644 libgcrypt-cipher-Differentiate-use-of-label-K-in-the-SLI.patch create mode 100644 libgcrypt-cipher-Don-t-differentiate-GCRY_CIPHER_MODE_CMAC-in-FIPS-mode.patch create mode 100644 libgcrypt-cipher-Rename-_gcry_cipher_is_mode_fips_compliant.patch create mode 100644 libgcrypt-cipher-ecc-Fix-for-supplied-K.patch create mode 100644 libgcrypt-cipher-fips-Fix-for-random-override.patch create mode 100644 libgcrypt-cipher-rsa-Mark-reject-SHA1-unknown-with-RSA-signature-generation.patch create mode 100644 libgcrypt-cipher-visibility-Differentiate-use-of-random-override-in-the-SLI.patch create mode 100644 libgcrypt-doc-Add-about-GCRYCTL_FIPS_SERVICE_INDICATOR.patch create mode 100644 libgcrypt-doc-Fix-syntax-error.patch create mode 100644 libgcrypt-fips-Change-the-internal-API-for-new-FIPS-service-indicator.patch create mode 100644 libgcrypt-fips-Fix-GCRY_FIPS_FLAG_REJECT_MD.patch create mode 100644 libgcrypt-fips-Introduce-GCRYCTL_FIPS_REJECT_NON_FIPS.patch create mode 100644 libgcrypt-fips-Introduce-GCRYCTL_FIPS_SERVICE_INDICATOR-and-the-macro.patch create mode 100644 libgcrypt-fips-Introduce-an-internal-API-for-FIPS-service-indicator.patch create mode 100644 libgcrypt-fips-Rejection-by-GCRYCTL_FIPS_REJECT_NON_FIPS-not-by-open-flags.patch create mode 100644 libgcrypt-fips-cipher-Add-GCRY_FIPS_FLAG_REJECT_PK_FLAGS.patch create mode 100644 libgcrypt-fips-cipher-Add-behavior-not-to-reject-but-mark-non-compliant.patch create mode 100644 libgcrypt-fips-cipher-Do-the-computation-when-marking-non-compliant.patch create mode 100644 libgcrypt-fips-cipher-Fix-memory-leak-for-gcry_pk_hash_sign.patch create mode 100644 libgcrypt-fips-cipher-Implement-FIPS-service-indicator-for-gcry_pk_hash_-API.patch create mode 100644 libgcrypt-fips-cipher-Implement-new-FIPS-service-indicator-for-cipher_open.patch create mode 100644 libgcrypt-fips-ecc-Add-rejecting-or-marking-for-gcry_pk_get_curve.patch create mode 100644 libgcrypt-fips-ecc-Check-DATA-in-gcry_pk_sign-verify-in-FIPS-mode.patch create mode 100644 libgcrypt-fips-kdf-Implement-new-FIPS-service-indicator-for-gcry_kdf_derive.patch create mode 100644 libgcrypt-fips-mac-Implement-new-FIPS-service-indicator-for-gcry_mac_open.patch create mode 100644 libgcrypt-fips-md-Implement-new-FIPS-service-indicator-for-gcry_md_hash_.patch create mode 100644 libgcrypt-fips-md-Implement-new-FIPS-service-indicator-for-gcry_md_open-API.patch create mode 100644 libgcrypt-fips-md-gcry_md_copy-should-care-about-FIPS-service-indicator.patch create mode 100644 libgcrypt-fips-tests-Add-t-digest.patch create mode 100644 libgcrypt-fips-tests-Add-tests-for-md_open-write-read-close-for-t-digest.patch create mode 100644 libgcrypt-jitterentropy-3.4.0.patch create mode 100644 libgcrypt-md-Fix-gcry_md_algo_info-to-mark-reject-under-FIPS-mode.patch create mode 100644 libgcrypt-md-Make-SHA-1-non-FIPS-internally-for-1.12-API.patch create mode 100644 libgcrypt-md-Use-check_digest_algo_spec-in-_gcry_md_selftest.patch create mode 100644 libgcrypt-no-deprecated-grep-alias.patch create mode 100644 libgcrypt-nobetasuffix.patch create mode 100644 libgcrypt-ppc-enable-P10-assembly-with-ENABLE_FORCE_SOF.patch create mode 100644 libgcrypt-rol64-redefinition.patch create mode 100644 libgcrypt-tests-Add-more-tests-to-tests-t-fips-service-ind.patch create mode 100644 libgcrypt-tests-Allow-tests-with-USE_RSA.patch create mode 100644 libgcrypt-tests-Update-t-fips-service-ind-using-GCRY_MD_SHA256-for-KDF-tests.patch create mode 100644 libgcrypt-tests-fips-Add-gcry_cipher_open-tests.patch create mode 100644 libgcrypt-tests-fips-Add-gcry_mac_open-tests.patch create mode 100644 libgcrypt-tests-fips-Move-KDF-tests-to-t-fips-service-ind.patch create mode 100644 libgcrypt-tests-fips-Rename-t-fips-service-ind.patch create mode 100644 libgcrypt.changes create mode 100644 libgcrypt.keyring create mode 100644 libgcrypt.spec create mode 100644 random.conf diff --git a/.gitattributes b/.gitattributes new file mode 100644 index 0000000..9b03811 --- /dev/null +++ b/.gitattributes @@ -0,0 +1,23 @@ +## Default LFS +*.7z filter=lfs diff=lfs merge=lfs -text +*.bsp filter=lfs diff=lfs merge=lfs -text +*.bz2 filter=lfs diff=lfs merge=lfs -text +*.gem filter=lfs diff=lfs merge=lfs -text +*.gz filter=lfs diff=lfs merge=lfs -text +*.jar filter=lfs diff=lfs merge=lfs -text +*.lz filter=lfs diff=lfs merge=lfs -text +*.lzma filter=lfs diff=lfs merge=lfs -text +*.obscpio filter=lfs diff=lfs merge=lfs -text +*.oxt filter=lfs diff=lfs merge=lfs -text +*.pdf filter=lfs diff=lfs merge=lfs -text +*.png filter=lfs diff=lfs merge=lfs -text +*.rpm filter=lfs diff=lfs merge=lfs -text +*.tbz filter=lfs diff=lfs merge=lfs -text +*.tbz2 filter=lfs diff=lfs merge=lfs -text +*.tgz filter=lfs diff=lfs merge=lfs -text +*.ttf filter=lfs diff=lfs merge=lfs -text +*.txz filter=lfs diff=lfs merge=lfs -text +*.whl filter=lfs diff=lfs merge=lfs -text +*.xz filter=lfs diff=lfs merge=lfs -text +*.zip filter=lfs diff=lfs merge=lfs -text +*.zst filter=lfs diff=lfs merge=lfs -text diff --git a/.gitignore b/.gitignore new file mode 100644 index 0000000..57affb6 --- /dev/null +++ b/.gitignore @@ -0,0 +1 @@ +.osc diff --git a/baselibs.conf b/baselibs.conf new file mode 100644 index 0000000..a018a0a --- /dev/null +++ b/baselibs.conf @@ -0,0 +1,8 @@ +libgcrypt20 + provides "libgcrypt- = " + obsoletes "libgcrypt- <= " + provides "libgcrypt20-hmac- = -%release" + obsoletes "libgcrypt20-hmac- < -%release" +libgcrypt-devel + requires -libgcrypt- + requires "libgcrypt20- = " diff --git a/hwf.deny b/hwf.deny new file mode 100644 index 0000000..2236468 --- /dev/null +++ b/hwf.deny @@ -0,0 +1,34 @@ +# This file can be used to globally disable the use of hardware +# based optimizations. Supported options are: +# padlock-rng +# padlock-aes +# padlock-sha +# padlock-mmul +# intel-cpu +# intel-fast-shld +# intel-bmi2 +# intel-ssse3 +# intel-sse4.1 +# intel-pclmul +# intel-aesni +# intel-rdrand +# intel-avx +# intel-avx2 +# intel-fast-vpgather +# intel-rdtsc +# intel-shaext +# intel-vaes-vpclmul +# arm-neon +# arm-aes +# arm-sha1 +# arm-sha2 +# arm-pmull +# ppc-vcrypto +# ppc-arch_3_00 +# ppc-arch_2_07 +# ppc-arch_3_10 +# s390x-msa +# s390x-msa-4 +# s390x-msa-8 +# s390x-msa-9 +# s390x-vx diff --git a/libgcrypt-1.10.0-allow_FSM_same_state.patch b/libgcrypt-1.10.0-allow_FSM_same_state.patch new file mode 100644 index 0000000..843cfea --- /dev/null +++ b/libgcrypt-1.10.0-allow_FSM_same_state.patch @@ -0,0 +1,15 @@ +Index: libgcrypt-1.10.0/src/fips.c +=================================================================== +--- libgcrypt-1.10.0.orig/src/fips.c ++++ libgcrypt-1.10.0/src/fips.c +@@ -890,6 +890,10 @@ fips_new_state (enum module_states new_s + + } + ++ /* Allow a transition to the current state */ ++ if (current_state == new_state) ++ ok = 1; ++ + if (ok) + { + current_state = new_state; diff --git a/libgcrypt-1.10.3.tar.bz2 b/libgcrypt-1.10.3.tar.bz2 new file mode 100644 index 0000000..653803f --- /dev/null +++ b/libgcrypt-1.10.3.tar.bz2 @@ -0,0 +1,3 @@ +version https://git-lfs.github.com/spec/v1 +oid sha256:8b0870897ac5ac67ded568dcfadf45969cfa8a6beb0fd60af2a9eadc2a3272aa +size 3783827 diff --git a/libgcrypt-1.10.3.tar.bz2.sig b/libgcrypt-1.10.3.tar.bz2.sig new file mode 100644 index 0000000000000000000000000000000000000000000000000000000000000000..4172518bc29eafb0304aa2c7def555b970a6accea442a7542087b98c44485773 GIT binary patch literal 238 zcmeAuWnmEGV2~A4WXWBXm$E!p!y#PSlPRcU`VKV*t6Qv0sliEW8MrtFU?N}p82-vF z=ITAZ*qv<_(;dOxrp<8yN$DSFdR>!gz3<7nXwGD1Muyiq%7Ht6>~>#&|Ibh5V-ok6 zm#e%* literal 0 HcmV?d00001 diff --git a/libgcrypt-1.11.0.tar.bz2 b/libgcrypt-1.11.0.tar.bz2 new file mode 100644 index 0000000..28d1068 --- /dev/null +++ b/libgcrypt-1.11.0.tar.bz2 @@ -0,0 +1,3 @@ +version https://git-lfs.github.com/spec/v1 +oid sha256:09120c9867ce7f2081d6aaa1775386b98c2f2f246135761aae47d81f58685b9c +size 4180345 diff --git a/libgcrypt-1.11.0.tar.bz2.sig b/libgcrypt-1.11.0.tar.bz2.sig new file mode 100644 index 0000000000000000000000000000000000000000000000000000000000000000..2debe948a9ffbbc9c835efae5cce0c65517df124ea67ba4cc04d1dffdd7b3160 GIT binary patch literal 119 zcmeAuWnmEGV2~A4WXWBXm$E!p!y#PSlPRcU`VKV*t6Qv0X+=xZ7`QkEU?T178UE=O z)|M}6Y-XM7H2JWvsFP0?XX&fr%U>#e4G(K{b;T<%GJNLLSKO|_Z@vBphsk!en!WkH T(k44uvO>;;f4NZp`vWfkiCryG literal 0 HcmV?d00001 diff --git a/libgcrypt-1.11.1-public-SLI-API.patch b/libgcrypt-1.11.1-public-SLI-API.patch new file mode 100644 index 0000000..42a9276 --- /dev/null +++ b/libgcrypt-1.11.1-public-SLI-API.patch @@ -0,0 +1,37 @@ +Index: libgcrypt-1.11.1/src/gcrypt.h.in +=================================================================== +--- libgcrypt-1.11.1.orig/src/gcrypt.h.in ++++ libgcrypt-1.11.1/src/gcrypt.h.in +@@ -335,12 +335,9 @@ enum gcry_ctl_cmds + GCRYCTL_FIPS_SERVICE_INDICATOR_MAC = 85, + GCRYCTL_FIPS_SERVICE_INDICATOR_MD = 86, + GCRYCTL_FIPS_SERVICE_INDICATOR_PK_FLAGS = 87, +- GCRYCTL_MD_CUSTOMIZE = 88 +-#ifdef _GCRYPT_IN_LIBGCRYPT /* This is not yet part of the public API. */ +- , ++ GCRYCTL_MD_CUSTOMIZE = 88, + GCRYCTL_FIPS_SERVICE_INDICATOR = 89, + GCRYCTL_FIPS_REJECT_NON_FIPS = 90 +-#endif /*_GCRYPT_IN_LIBGCRYPT*/ + }; + + /* Perform various operations defined by CMD. */ +@@ -1977,8 +1974,6 @@ void gcry_log_debugsxp (const char *text + char *gcry_get_config (int mode, const char *what); + + /* Convinience macro to access the FIPS service indicator. */ +-#ifdef _GCRYPT_IN_LIBGCRYPT /* This is not yet part of the public API. */ +- + #define gcry_get_fips_service_indicator() \ + gcry_control (GCRYCTL_FIPS_SERVICE_INDICATOR) + +@@ -2012,9 +2007,6 @@ char *gcry_get_config (int mode, const c + #define GCRY_FIPS_FLAG_REJECT_DEFAULT \ + GCRY_FIPS_FLAG_REJECT_COMPAT110 + +-#endif /*_GCRYPT_IN_LIBGCRYPT*/ +- +- + /* Log levels used by the internal logging facility. */ + enum gcry_log_levels + { diff --git a/libgcrypt-1.11.1.tar.bz2 b/libgcrypt-1.11.1.tar.bz2 new file mode 100644 index 0000000..aa03790 --- /dev/null +++ b/libgcrypt-1.11.1.tar.bz2 @@ -0,0 +1,3 @@ +version https://git-lfs.github.com/spec/v1 +oid sha256:24e91c9123a46c54e8371f3a3a2502f1198f2893fbfbf59af95bc1c21499b00e +size 4233557 diff --git a/libgcrypt-1.11.1.tar.bz2.sig b/libgcrypt-1.11.1.tar.bz2.sig new file mode 100644 index 0000000000000000000000000000000000000000000000000000000000000000..62de6154dfc87f2d93e84b8fd2f4a26b2e9f2dfc6cd988e73e4a8305d7d1021d GIT binary patch literal 119 zcmeAuWnmEGVvrS6WXWBXm$E!p!y#PSlPRcU`VKV*t6Qv08Pbh^7`QkEU?N-QFfvR& zliXh{lxlF3mDxiqReAqxzNuWrYmP2DYpc_Eedm)rhJS|Foa@@920I1Y1WdHyG literal 0 HcmV?d00001 diff --git a/libgcrypt-1.11.2.tar.bz2 b/libgcrypt-1.11.2.tar.bz2 new file mode 100644 index 0000000..1a72de8 --- /dev/null +++ b/libgcrypt-1.11.2.tar.bz2 @@ -0,0 +1,3 @@ +version https://git-lfs.github.com/spec/v1 +oid sha256:6ba59dd192270e8c1d22ddb41a07d95dcdbc1f0fb02d03c4b54b235814330aac +size 4237802 diff --git a/libgcrypt-1.11.2.tar.bz2.sig b/libgcrypt-1.11.2.tar.bz2.sig new file mode 100644 index 0000000000000000000000000000000000000000000000000000000000000000..d8a582b8dadd18a0a63920b2dcb27d3ec1f1dc0ed1ded6a2f9a8fb8faeee645a GIT binary patch literal 147 zcmeB}$ig7T#b7C>$dbD%FJ*bIhC{ftCsRel|V; literal 0 HcmV?d00001 diff --git a/libgcrypt-CVE-2024-2236.patch b/libgcrypt-CVE-2024-2236.patch new file mode 100644 index 0000000..0d39790 --- /dev/null +++ b/libgcrypt-CVE-2024-2236.patch @@ -0,0 +1,1839 @@ +From 984e245fd21ff6e0058403f620f760013a744a3a Mon Sep 17 00:00:00 2001 +From: Jakub Jelen +Date: Fri, 7 Jun 2024 14:42:33 +0200 +Subject: [PATCH 1/7] rsa: Do not accept invalid PKCS#1.5 padding when + deciphering + +The current code can accept 0-length padding when deciphering +PKCS#1.5 ciphertext. This is against the specification and hopefully +nobody depends on this. + +-- +* cipher/rsa-common.c (_gcry_rsa_pkcs1_decode_for_enc): Fail for too + short padding. +* src/const-time.h (ct_lt_s): New. + +Signed-off-by: Jakub Jelen +--- + cipher/rsa-common.c | 2 ++ + src/const-time.h | 6 ++++++ + 2 files changed, 8 insertions(+) + +Index: libgcrypt-1.11.1/cipher/rsa-common.c +=================================================================== +--- libgcrypt-1.11.1.orig/cipher/rsa-common.c ++++ libgcrypt-1.11.1/cipher/rsa-common.c +@@ -28,6 +28,7 @@ + #include "cipher.h" + #include "pubkey-internal.h" + #include "const-time.h" ++#include "bufhelp.h" + + + /* Turn VALUE into an octet string and store it in an allocated buffer +@@ -191,6 +192,45 @@ memmov_independently (void *dst, const v + } + + ++static unsigned char * ++mpi_to_string(gcry_mpi_t value, size_t nframe) ++{ ++ unsigned char *frame = NULL; ++ unsigned char *p; ++ size_t noff; ++ /* Allocate memory to fit the whole MPI limbs and allow moving it later to the right place */ ++ size_t alloc_len = value->nlimbs * BYTES_PER_MPI_LIMB; ++ ++ /* for too short input, we need to allocate at least modulus length (which might still be valid in case of OAEP) */ ++ noff = (alloc_len < nframe) ? nframe - alloc_len : 0; ++ alloc_len = alloc_len + noff; ++ ++ if ( !(frame = xtrymalloc_secure (alloc_len))) ++ return NULL; ++ ++ if (noff) ++ memset (frame, 0, noff); ++ p = frame + noff; ++ /* shovel the MPI content to the buffer as it is */ ++ for (int i = value->nlimbs - 1; i >= 0; i--) ++ { ++ mpi_limb_t *alimb = &value->d[i]; ++#if BYTES_PER_MPI_LIMB == 4 ++ buf_put_be32 (p, *alimb); ++ p += 4; ++#elif BYTES_PER_MPI_LIMB == 8 ++ buf_put_be64 (p, *alimb); ++ p += 8; ++#else ++# error please implement for this limb size. ++#endif ++ } ++ /* Move the MPI to the right place -- with the least significant bytes aligned to the modulus length ++ * -- this might keep some leading zeroes at the beginning of the buffer, but this might be valid for OAEP */ ++ memmov_independently (frame, frame + (alloc_len - nframe), nframe, alloc_len); ++ return frame; ++} ++ + /* Decode a plaintext in VALUE assuming pkcs#1 block type 2 padding. + NBITS is the size of the secret key. On success the result is + stored as a newly allocated buffer at R_RESULT and its valid length at +@@ -199,7 +239,6 @@ gpg_err_code_t + _gcry_rsa_pkcs1_decode_for_enc (unsigned char **r_result, size_t *r_resultlen, + unsigned int nbits, gcry_mpi_t value) + { +- gcry_error_t err; + unsigned char *frame = NULL; + size_t nframe = (nbits+7) / 8; + size_t n, n0; +@@ -208,6 +247,17 @@ _gcry_rsa_pkcs1_decode_for_enc (unsigned + + *r_result = NULL; + ++ { ++#ifdef WITH_MARVIN_WORKAROUND ++ frame = mpi_to_string(value, nframe); ++ if (frame == NULL) ++ return gpg_err_code_from_syserror (); ++ ++ n = 0; ++ failed |= ct_not_equal_byte (frame[n++], 0x00); ++#else ++ gcry_error_t err; ++ + if ( !(frame = xtrymalloc_secure (nframe))) + return gpg_err_code_from_syserror (); + +@@ -235,6 +285,9 @@ _gcry_rsa_pkcs1_decode_for_enc (unsigned + n = 0; + if (!frame[0]) + n++; ++#endif /* WITH_MARVIN_WORKAROUND */ ++ } ++ + failed |= ct_not_equal_byte (frame[n++], 0x02); + + /* Find the terminating zero byte. */ +@@ -247,6 +300,8 @@ _gcry_rsa_pkcs1_decode_for_enc (unsigned + + failed |= not_found; + n0 += ct_is_zero (not_found); /* Skip the zero byte. */ ++ /* the valid padding is at least 8 bytes -- the plaintext needs to start at index 11 or later */ ++ failed |= ct_lt_s (n0, 11); + + /* To avoid an extra allocation we reuse the frame buffer. The only + caller of this function will anyway free the result soon. */ +@@ -263,6 +318,187 @@ _gcry_rsa_pkcs1_decode_for_enc (unsigned + } + + ++#ifdef WITH_MARVIN_WORKAROUND ++#define SHA256_LEN 32 ++static gcry_err_code_t ++rsa_prf(unsigned char *out, size_t out_len, const char *label, size_t label_len, unsigned char *kdk, size_t nbits) ++{ ++ gcry_err_code_t rc = GPG_ERR_NO_ERROR; ++ size_t pos; ++ uint16_t iter = 0; ++ unsigned char be_iter[2]; ++ unsigned char be_bitlen[2]; ++ gcry_md_hd_t hd; ++ gcry_error_t err; ++ ++ be_bitlen[0] = (nbits >> 8) & 0xff; ++ be_bitlen[1] = nbits & 0xff; ++ ++ err = _gcry_md_open (&hd, GCRY_MD_SHA256, GCRY_MD_FLAG_HMAC); ++ if (err) ++ { ++ return GPG_ERR_INTERNAL; ++ } ++ err = _gcry_md_setkey (hd, kdk, SHA256_LEN); ++ if (err) ++ { ++ _gcry_md_close (hd); ++ return GPG_ERR_INTERNAL; ++ } ++ for (pos = 0; pos < out_len; pos += SHA256_LEN, iter++) ++ { ++ unsigned char *tmp; ++ ++ _gcry_md_reset(hd); ++ ++ be_iter[0] = (iter >> 8) & 0xff; ++ be_iter[1] = iter & 0xff; ++ _gcry_md_write (hd, be_iter, sizeof (be_iter)); ++ _gcry_md_write (hd, label, label_len); ++ _gcry_md_write (hd, be_bitlen, sizeof (be_bitlen)); ++ ++ tmp = _gcry_md_read(hd, 0); ++ if (pos + SHA256_LEN > out_len) ++ { ++ memcpy(out + pos, tmp, out_len - pos); ++ } ++ else ++ { ++ memcpy(out + pos, tmp, SHA256_LEN); ++ } ++ } ++ _gcry_md_close (hd); ++ return rc; ++} ++ ++ ++/* Decode a plaintext in VALUE assuming pkcs#1 block type 2 padding. ++ NBITS is the size of the secret key. On success the result is ++ stored as a newly allocated buffer at R_RESULT and its valid length at ++ R_RESULTLEN. On error R_RESULT contains bogus value of random length. ++ For more information, see description of Implicit Rejection in Marvin paper ++ https://people.redhat.com/~hkario/marvin/marvin-attack-paper.pdf */ ++#define MAX_LEN_GEN_TRIES 128 ++gpg_err_code_t ++_gcry_rsa_pkcs1_decode_for_enc_implicit_rejection (unsigned char **r_result, ++ size_t *r_resultlen, ++ unsigned int nbits, ++ gcry_mpi_t value, ++ unsigned char *kdk) ++{ ++ unsigned char *frame = NULL; ++ size_t nframe = (nbits+7) / 8; ++ size_t n, n0; ++ unsigned int failed = 0; ++ unsigned int not_found = 1; ++ int i, j; ++ uint16_t len_mask; ++ uint16_t max_sep_offset; ++ unsigned char *synthetic = NULL; ++ unsigned long synthethic_length; ++ uint16_t len_candidate; ++ unsigned char candidate_lengths[MAX_LEN_GEN_TRIES * sizeof(len_candidate)]; ++ int synth_msg_index = 0, msg_index; ++ ++ *r_result = NULL; ++ ++ synthetic = xtrymalloc(nframe); ++ if (synthetic == NULL) ++ { ++ free (synthetic); ++ return gpg_err_code_from_syserror (); ++ } ++ ++ if (rsa_prf(synthetic, nframe, "message", 7, kdk, nframe * 8) < 0) ++ { ++ xfree (synthetic); ++ return GPG_ERR_INTERNAL; ++ } ++ ++ /* decide how long the random message should be */ ++ if (rsa_prf(candidate_lengths, sizeof(candidate_lengths), ++ "length", 6, kdk, MAX_LEN_GEN_TRIES * sizeof(len_candidate) * 8) < 0) ++ { ++ xfree (synthetic); ++ return GPG_ERR_INTERNAL; ++ } ++ ++ len_mask = max_sep_offset = nframe - 2 - 8; ++ len_mask |= len_mask >> 1; ++ len_mask |= len_mask >> 2; ++ len_mask |= len_mask >> 4; ++ len_mask |= len_mask >> 8; ++ ++ synthethic_length = 0; ++ for (i = 0; i < MAX_LEN_GEN_TRIES * (int)sizeof(len_candidate); ++ i += sizeof(len_candidate)) ++ { ++ len_candidate = (candidate_lengths[i] << 8) | candidate_lengths[i + 1]; ++ len_candidate &= len_mask; ++ ++ synthethic_length = ct_ulong_select( ++ len_candidate, synthethic_length, ++ ct_lt(len_candidate, max_sep_offset)); ++ } ++ ++ synth_msg_index = nframe - synthethic_length; ++ ++ /* we have alternative message ready, check the real one */ ++ /* mostly copy from _gcry_rsa_pkcs1_decode_for_enc */ ++ frame = mpi_to_string(value, nframe); ++ if (frame == NULL) ++ { ++ xfree (synthetic); ++ return gpg_err_code_from_syserror (); ++ } ++ ++ /* FRAME = 0x00 || 0x02 || PS || 0x00 || M */ ++ n = 0; ++ failed |= ct_not_equal_byte (frame[n++], 0x00); ++ failed |= ct_not_equal_byte (frame[n++], 0x02); ++ ++ /* Find the terminating zero byte. */ ++ n0 = n; ++ for (; n < nframe; n++) ++ { ++ not_found &= ct_not_equal_byte (frame[n], 0x00); ++ n0 += not_found; ++ } ++ ++ failed |= not_found; ++ n0 += ct_is_zero (not_found); /* Skip the zero byte. */ ++ /* the valid padding is at least 8 bytes -- the plaintext needs to start at index 11 or later */ ++ failed |= ct_lt_s (n0, 11); ++ ++ msg_index = ct_ulong_select (synth_msg_index, n0, failed); ++ ++ /* To avoid the need memmove (O(N*log(N))), we use separate buffer where we move either ++ * of the messages. We can now also use the msg_index safely as its timing is not ++ * possible to distinguish valid and invalid padding */ ++ for (i = msg_index, j = 0; i < nframe && j < nframe; i++, j++) ++ { ++ frame[j] = ct_uchar_select (synthetic[i], frame[i], failed); ++ } ++ ++ *r_resultlen = j; ++ *r_result = frame; ++ ++ if (DBG_CIPHER) ++ { ++ if (!failed) ++ log_printhex ("value extracted from PKCS#1 block type 2 encoded data", ++ frame, nframe - n0); ++ else ++ log_printhex ("Synthetic value from implicit rejection", ++ synthetic, synthethic_length); ++ } ++ ++ xfree (synthetic); ++ return 0; ++} ++#endif /* WITH_MARVIN_WORKAROUND */ ++ ++ + /* Encode {VALUE,VALUELEN} for an NBITS keys and hash algorithm ALGO + using the pkcs#1 block type 1 padding. On success the result is + stored as a new MPI at R_RESULT. On error the value at R_RESULT is +@@ -684,14 +920,23 @@ _gcry_rsa_oaep_decode (unsigned char **r + happen due to the leading zero in OAEP frames and due to the + following random octets (seed^mask) which may have leading zero + bytes. This all is needed to cope with our leading zeroes +- suppressing MPI implementation. The code implictly implements ++ suppressing MPI implementation. The code implicitly implements + Step 1b (bail out if NFRAME != N). */ ++#ifdef WITH_MARVIN_WORKAROUND ++ frame = mpi_to_string(value, nkey); ++ if (frame == NULL) ++ { ++ xfree (lhash); ++ return gpg_err_code_from_syserror (); ++ } ++#else + rc = octet_string_from_mpi (&frame, NULL, value, nkey); + if (rc) + { + xfree (lhash); + return GPG_ERR_ENCODING_PROBLEM; + } ++#endif /* WITH_MARVIN_WORKAROUND */ + nframe = nkey; + + /* Step 1c: Check that the key is long enough. */ +@@ -706,7 +951,7 @@ _gcry_rsa_oaep_decode (unsigned char **r + gcry_mpi_aprint above. */ + + /* Allocate space for SEED and DB. */ +- seed = xtrymalloc_secure (nframe - 1); ++ seed = xtrymalloc_secure (nframe); + if (!seed) + { + rc = gpg_err_code_from_syserror (); +Index: libgcrypt-1.11.1/src/const-time.h +=================================================================== +--- libgcrypt-1.11.1.orig/src/const-time.h ++++ libgcrypt-1.11.1/src/const-time.h +@@ -26,6 +26,7 @@ + #define ct_not_memequal _gcry_ct_not_memequal + #define ct_memequal _gcry_ct_memequal + #define ct_memmov_cond _gcry_ct_memmov_cond ++#define ct_memcpy _gcry_ct_memcpy + + + #ifndef HAVE_GCC_ASM_VOLATILE_MEMORY +@@ -33,6 +34,20 @@ extern volatile unsigned int _gcry_ct_vz + extern volatile unsigned int _gcry_ct_vone; + #endif + ++/* ++ * Return 1 if A < B and return 0 otherwise. ++ */ ++static inline int ++ct_lt (unsigned int a, unsigned int b) ++{ ++ return (a ^ ((a ^ b) | ((a - b) ^ b))) >> (sizeof(unsigned int) * 8 - 1); ++} ++ ++static inline size_t ++ct_lt_s (size_t a, size_t b) ++{ ++ return ((a ^ ((a ^ b) | ((a - b) ^ b))) >> (sizeof(size_t) * 8 - 1)); ++} + + /* + * Return 0 if A is 0 and return 1 otherwise. +@@ -114,7 +129,7 @@ unsigned int _gcry_ct_memequal (const vo + DEFINE_CT_TYPE_GEN_MASK(uintptr, uintptr_t) + DEFINE_CT_TYPE_GEN_MASK(ulong, unsigned long) + DEFINE_CT_TYPE_GEN_MASK(int16, int16_t) +- ++DEFINE_CT_TYPE_GEN_MASK(uchar, unsigned char) + /* + * Return all bits set if A is 0 and return 1 otherwise. + */ +@@ -139,7 +154,7 @@ DEFINE_CT_TYPE_GEN_MASK(int16, int16_t) + DEFINE_CT_TYPE_GEN_INV_MASK(uintptr, uintptr_t) + DEFINE_CT_TYPE_GEN_INV_MASK(ulong, unsigned long) + DEFINE_CT_TYPE_GEN_INV_MASK(int16, int16_t) +- ++DEFINE_CT_TYPE_GEN_INV_MASK(uchar, unsigned char) + /* + * Return A when OP_ENABLED=1 + * otherwise, return B +@@ -155,7 +170,7 @@ DEFINE_CT_TYPE_GEN_INV_MASK(int16, int16 + DEFINE_CT_TYPE_SELECT_FUNC(uintptr, uintptr_t) + DEFINE_CT_TYPE_SELECT_FUNC(ulong, unsigned long) + DEFINE_CT_TYPE_SELECT_FUNC(int16, int16_t) +- ++DEFINE_CT_TYPE_SELECT_FUNC(uchar, unsigned char) + /* + * Return NULL when OP_ENABLED=1 + * otherwise, return W +@@ -174,5 +189,6 @@ sexp_null_cond (gcry_sexp_t w, unsigned + */ + void _gcry_ct_memmov_cond (void *dst, const void *src, size_t len, + unsigned long op_enable); ++void _gcry_ct_memcpy (void *dst, const void *src, size_t len, size_t buffer_len); + + #endif /*GCRY_CONST_TIME_H*/ +Index: libgcrypt-1.11.1/cipher/rsa.c +=================================================================== +--- libgcrypt-1.11.1.orig/cipher/rsa.c ++++ libgcrypt-1.11.1/cipher/rsa.c +@@ -1197,7 +1197,11 @@ secret_blinded (gcry_mpi_t output, gcry_ + /* Undo blinding. Here we calculate: y = (x * r^-1) mod n, where x + * is the blinded decrypted data, ri is the modular multiplicative + * inverse of r and n is the RSA modulus. */ ++#ifdef WITH_MARVIN_WORKAROUND ++ mpi_mulm_sec (output, output, ri, sk->n); ++#else + mpi_mulm (output, output, ri, sk->n); ++#endif /* WITH_MARVIN_WORKAROUND */ + + _gcry_mpi_release (r); + _gcry_mpi_release (ri); +@@ -1432,6 +1436,7 @@ rsa_encrypt (gcry_sexp_t *r_ciph, gcry_s + } + + ++#define SHA256_LEN 32 + static gcry_err_code_t + rsa_decrypt (gcry_sexp_t *r_plain, gcry_sexp_t s_data, gcry_sexp_t keyparms) + +@@ -1447,6 +1452,9 @@ rsa_decrypt (gcry_sexp_t *r_plain, gcry_ + unsigned int nbits = rsa_get_nbits (keyparms); + gcry_sexp_t result = NULL; + gcry_sexp_t dummy = NULL; ++#ifdef WITH_MARVIN_WORKAROUND ++ unsigned char kdk[SHA256_LEN]; ++#endif /* WITH_MARVIN_WORKAROUND */ + + rc = rsa_check_keysize (nbits); + if (rc) +@@ -1494,6 +1502,71 @@ rsa_decrypt (gcry_sexp_t *r_plain, gcry_ + mpi_normalize (data); + mpi_fdiv_r (data, data, sk.n); + ++#ifdef WITH_MARVIN_WORKAROUND ++ /* Implicit rejection: Derive KDK */ ++ if (ctx.encoding == PUBKEY_ENC_PKCS1) ++ { ++ unsigned char *buf, *tmp; ++ unsigned int nbytes = (mpi_get_nbits (sk.n)+7)/8; ++ unsigned char key[SHA256_LEN]; ++ gcry_md_hd_t hd; ++ ++ /* (a) Convert `d` to big endian representation, left padded to the length of `n` */ ++ rc = _gcry_mpi_to_octet_string (&buf, NULL, sk.d, nbytes); ++ if (rc) ++ { ++ rc = GPG_ERR_INTERNAL; ++ goto leave; ++ } ++ ++ /* (b) Hash it using SHA-256 */ ++ rc = _gcry_md_open (&hd, GCRY_MD_SHA256, 0); ++ if (rc) ++ { ++ xfree (buf); ++ rc = GPG_ERR_INTERNAL; ++ goto leave; ++ } ++ _gcry_md_write (hd, buf, nbytes); ++ /* keep the buffer around -- it will be needed for the ciphertext */ ++ tmp = _gcry_md_read (hd, GCRY_MD_SHA256); ++ memcpy(key, tmp, SHA256_LEN); ++ _gcry_md_close (hd); ++ ++ /* (c) Use the hash as a SHA-256 HMAC key and ciphertext as a message */ ++ rc = _gcry_md_open (&hd, GCRY_MD_SHA256, GCRY_MD_FLAG_HMAC); ++ if (rc) ++ { ++ xfree (buf); ++ rc = GPG_ERR_INTERNAL; ++ goto leave; ++ } ++ rc = _gcry_md_setkey (hd, key, sizeof (key)); ++ if (rc) ++ { ++ xfree (buf); ++ _gcry_md_close (hd); ++ rc = GPG_ERR_INTERNAL; ++ goto leave; ++ } ++ ++ /* We need to convert the ciphertext to string, padded to the length of modulus */ ++ rc = _gcry_mpi_to_octet_string (NULL, buf, data, nbytes); ++ if (rc) ++ { ++ xfree (buf); ++ _gcry_md_close (hd); ++ rc = GPG_ERR_INTERNAL; ++ goto leave; ++ } ++ _gcry_md_write (hd, buf, nbytes); ++ xfree (buf); ++ buf = _gcry_md_read (hd, 0); ++ memcpy(kdk, buf, SHA256_LEN); ++ _gcry_md_close (hd); ++ } ++#endif /* WITH_MARVIN_WORKAROUND */ ++ + /* Allocate MPI for the plaintext. */ + plain = mpi_snew (nbits); + +@@ -1524,10 +1597,26 @@ rsa_decrypt (gcry_sexp_t *r_plain, gcry_ + switch (ctx.encoding) + { + case PUBKEY_ENC_PKCS1: ++#ifdef WITH_MARVIN_WORKAROUND ++ if (!(ctx.flags & PUBKEY_FLAG_NO_IMPLICIT_REJECTION)) ++ { ++ rc = _gcry_rsa_pkcs1_decode_for_enc_implicit_rejection (&unpad, &unpadlen, nbits, plain, kdk); ++ mpi_free (plain); ++ plain = NULL; ++ rc_sexp = sexp_build (&result, NULL, "(value %c)", (int)unpadlen, unpad, (nbits + 7) / 8); ++ *r_plain = result; ++ rc = ct_ulong_select (rc_sexp, rc, ct_is_zero (rc) & ct_is_not_zero (rc_sexp)); ++ break; ++ } ++#endif /* WITH_MARVIN_WORKAROUND */ + rc = _gcry_rsa_pkcs1_decode_for_enc (&unpad, &unpadlen, nbits, plain); + mpi_free (plain); + plain = NULL; ++#ifdef WITH_MARVIN_WORKAROUND ++ rc_sexp = sexp_build (&result, NULL, "(value %c)", (int)unpadlen, unpad, (nbits + 7) / 8); ++#else + rc_sexp = sexp_build (&result, NULL, "(value %b)", (int)unpadlen, unpad); ++#endif /* WITH_MARVIN_WORKAROUND */ + *r_plain = sexp_null_cond (result, ct_is_not_zero (rc)); + dummy = sexp_null_cond (result, ct_is_zero (rc)); + sexp_release (dummy); +@@ -1541,7 +1630,11 @@ rsa_decrypt (gcry_sexp_t *r_plain, gcry_ + plain, ctx.label, ctx.labellen); + mpi_free (plain); + plain = NULL; ++#ifdef WITH_MARVIN_WORKAROUND ++ rc_sexp = sexp_build (&result, NULL, "(value %c)", (int)unpadlen, unpad, (nbits + 7) / 8); ++#else + rc_sexp = sexp_build (&result, NULL, "(value %b)", (int)unpadlen, unpad); ++#endif /* WITH_MARVIN_WORKAROUND */ + *r_plain = sexp_null_cond (result, ct_is_not_zero (rc)); + dummy = sexp_null_cond (result, ct_is_zero (rc)); + sexp_release (dummy); +Index: libgcrypt-1.11.1/configure.ac +=================================================================== +--- libgcrypt-1.11.1.orig/configure.ac ++++ libgcrypt-1.11.1/configure.ac +@@ -582,6 +582,22 @@ AC_ARG_ENABLE(jent-support, + jentsupport=$enableval,jentsupport=yes) + AC_MSG_RESULT($jentsupport) + ++AC_MSG_CHECKING([whether a Marvin workaround is requested]) ++AC_ARG_ENABLE(marvin-workaround, ++ AS_HELP_STRING([--enable-marvin-workaround], ++ [Enable Marvin workaround for constant time PKCS1.5 depadding]), ++ [with_marvin_workaround="$enableval"], ++ [with_marvin_workaround=no]) ++AC_MSG_RESULT($with_marvin_workaround) ++if test "$with_marvin_workaround" = no ; then ++ WITH_MARVIN_WORKAROUND='' ++else ++ AC_DEFINE(WITH_MARVIN_WORKAROUND,1, ++ [Define to provide constant time PKCS1.5 depadding]) ++fi ++AM_CONDITIONAL(WITH_MARVIN_WORKAROUND, test "x$with_marvin_workaround" != xno) ++AC_SUBST(WITH_MARVIN_WORKAROUND) ++ + # Implementation of the --disable-padlock-support switch. + AC_MSG_CHECKING([whether padlock support is requested]) + AC_ARG_ENABLE(padlock-support, +Index: libgcrypt-1.11.1/mpi/Makefile.am +=================================================================== +--- libgcrypt-1.11.1.orig/mpi/Makefile.am ++++ libgcrypt-1.11.1/mpi/Makefile.am +@@ -181,3 +181,7 @@ EXTRA_libmpi_la_SOURCES = \ + asm-common-aarch64.h \ + asm-common-amd64.h \ + asm-common-i386.h ++ ++if WITH_MARVIN_WORKAROUND ++libmpi_la_SOURCES += mpi-mul-cs.c ++endif +Index: libgcrypt-1.11.1/mpi/mpi-internal.h +=================================================================== +--- libgcrypt-1.11.1.orig/mpi/mpi-internal.h ++++ libgcrypt-1.11.1/mpi/mpi-internal.h +@@ -241,6 +241,12 @@ void _gcry_mpih_mul_karatsuba_case( mpi_ + mpi_ptr_t vp, mpi_size_t vsize, + struct karatsuba_ctx *ctx ); + ++#ifdef WITH_MARVIN_WORKAROUND ++/*-- mpih-mul-cs.c --*/ ++void mul_cs(mpi_limb_t *ret, mpi_limb_t *a, mpi_limb_t *b, size_t n, mpi_limb_t *tmp); ++void mod_cs(mpi_limb_t *ret, mpi_limb_t *a, size_t anum, mpi_limb_t *mod, size_t modnum, mpi_limb_t *tmp); ++size_t mod_limb_numb(size_t anum, size_t modnum); ++#endif /* WITH_MARVIN_WORKAROUND */ + + /*-- mpih-mul_1.c (or xxx/cpu/ *.S) --*/ + mpi_limb_t _gcry_mpih_mul_1( mpi_ptr_t res_ptr, mpi_ptr_t s1_ptr, +Index: libgcrypt-1.11.1/mpi/mpi-mul-cs.c +=================================================================== +--- /dev/null ++++ libgcrypt-1.11.1/mpi/mpi-mul-cs.c +@@ -0,0 +1,263 @@ ++/* Copyright (c) 2024, Hubert Kario, Red Hat ++ * Released under BSD 2-Clause License, see LICENSE for details ++ */ ++#include ++#include ++#include ++#include ++#include ++#include "mpi-internal.h" ++#include "longlong.h" ++ ++/* For multiplication we're using schoolbook multiplication, ++ * so if we have two numbers, each with 6 "digits" (words) ++ * the multiplication is calculated as follows: ++ * A B C D E F ++ * x I J K L M N ++ * -------------- ++ * N*F ++ * N*E ++ * N*D ++ * N*C ++ * N*B ++ * N*A ++ * M*F ++ * M*E ++ * M*D ++ * M*C ++ * M*B ++ * M*A ++ * L*F ++ * L*E ++ * L*D ++ * L*C ++ * L*B ++ * L*A ++ * K*F ++ * K*E ++ * K*D ++ * K*C ++ * K*B ++ * K*A ++ * J*F ++ * J*E ++ * J*D ++ * J*C ++ * J*B ++ * J*A ++ * I*F ++ * I*E ++ * I*D ++ * I*C ++ * I*B ++ * + I*A ++ * ========================== ++ * N*B N*D N*F ++ * + N*A N*C N*E ++ * + M*B M*D M*F ++ * + M*A M*C M*E ++ * + L*B L*D L*F ++ * + L*A L*C L*E ++ * + K*B K*D K*F ++ * + K*A K*C K*E ++ * + J*B J*D J*F ++ * + J*A J*C J*E ++ * + I*B I*D I*F ++ * + I*A I*C I*E ++ * ++ * 1+1 1+3 1+5 ++ * 1+0 1+2 1+4 ++ * 0+1 0+3 0+5 ++ * 0+0 0+2 0+4 ++ * ++ * 0 1 2 3 4 5 6 ++ * which requires n^2 multiplications and 2n full length additions ++ * as we can keep every other result of limb multiplication in two separate ++ * limbs ++ */ ++ ++typedef mpi_limb_t limb_t; ++#if BYTES_PER_MPI_LIMB == SIZEOF_UNSIGNED_LONG_LONG ++#define LIMB_BIT_SIZE 64 ++#define LIMB_BYTE_SIZE 8 ++#elif BYTES_PER_MPI_LIMB == SIZEOF_UNSIGNED_LONG ++#define LIMB_BIT_SIZE 32 ++#define LIMB_BYTE_SIZE 4 ++/* if we're on a 32 bit platform */ ++#else ++#define LIMB_BIT_SIZE 16 ++#define LIMB_BYTE_SIZE 2 ++/* ++ * if the compiler doesn't have either a 128bit data type nor a "return ++ * high 64 bits of multiplication" ++ */ ++#endif ++ ++/* add two limbs with carry in, return carry out */ ++static limb_t ++_add_limb (limb_t *ret, limb_t a, limb_t b, limb_t carry) ++{ ++ limb_t carry1, carry2, t; ++ add_ssaaaa (carry1, t, 0, a, 0, carry); ++ add_ssaaaa (carry2, t, 0, b, 0, t); ++ *ret = t; ++ return carry1 + carry2; ++} ++ ++/* add two numbers of the same size, return overflow ++ * ++ * add a to b, place result in ret; all arrays need to be n limbs long ++ * return overflow from addition (0 or 1) ++ */ ++static limb_t ++add (limb_t *ret, limb_t *a, limb_t *b, size_t n) ++{ ++ limb_t c = 0; ++ for (ssize_t i = n - 1; i > -1; i--) ++ { ++ c = _add_limb (&ret[i], a[i], b[i], c); ++ } ++ return c; ++} ++ ++/* multiply two numbers of the same size ++ * ++ * multiply a by b, place result in ret; a and b need to be n limbs long ++ * ret needs to be 2*n limbs long, tmp needs to be 2 * n 2 limbs ++ * long ++ */ ++void ++mul_cs (limb_t *ret, limb_t *a, limb_t *b, size_t n, limb_t *tmp) ++{ ++ limb_t *r_odd, *r_even; ++ r_odd = tmp; ++ r_even = &tmp[2 * n]; ++ ++ for (size_t i = 0; i < 2 * n; i++) ++ { ++ ret[i] = 0; ++ } ++ ++ for (size_t i=0; i> 1); ++ shift_in = shift_out; ++ } ++} ++ ++/* copy from either a or b to ret based on flag ++ * when flag == 0, then copies from b ++ * when flag == 1, then copies from a ++ */ ++static void ++cselect (limb_t flag, limb_t *ret, limb_t *a, limb_t *b, size_t n) ++{ ++ /* would be more efficient with non volatile mask, but then gcc ++ * generates code with jumps */ ++ limb_t mask1 = ct_limb_gen_mask (flag); ++ limb_t mask2 = ct_limb_gen_inv_mask (flag); ++ for (size_t i = 0; i < n; i++) ++ { ++ ret[i] = (mask1 & a[i]) | (mask2 & b[i]); ++ } ++} ++ ++static limb_t ++_sub_limb (limb_t *ret, limb_t a, limb_t b, limb_t borrow) ++{ ++ limb_t borrow1, borrow2, t; ++ sub_ddmmss (borrow1, t, 0, a, 0, borrow); ++ sub_ddmmss (borrow2, t, 0, t, 0, b); ++ *ret = t; ++ return -(borrow1 + borrow2); ++} ++ ++/* place the result of a - b into ret, return the borrow bit. ++ * All arrays need to be n limbs long ++ */ ++static limb_t ++sub (limb_t *ret, limb_t *a, limb_t *b, size_t n) ++{ ++ limb_t borrow = 0; ++ for (ssize_t i=n-1; i>-1; i--) ++ { ++ borrow = _sub_limb (&ret[i], a[i], b[i], borrow); ++ } ++ return borrow; ++} ++ ++/* return the number of limbs necessary to allocate for the mod() tmp operand */ ++size_t ++mod_limb_numb (size_t anum, size_t modnum) ++{ ++ return (anum + modnum) * 3; ++} ++ ++/* calculate a % mod, place the result in ret ++ * size of a is defined by anum, size of ret and mod is modnum, ++ * size of tmp is returned by mod_limb_numb() ++ */ ++void ++mod_cs (limb_t *ret, limb_t *a, size_t anum, limb_t *mod, size_t modnum, limb_t *tmp) ++{ ++ limb_t *atmp, *modtmp, *rettmp; ++ limb_t res; ++ ++ memset (tmp, 0, mod_limb_numb(anum, modnum) * LIMB_BYTE_SIZE); ++ ++ atmp = tmp; ++ modtmp = &tmp[anum+modnum]; ++ rettmp = &tmp[(anum+modnum)*2]; ++ ++ for (size_t i=modnum; inlimbs < v->nlimbs) ++ { /* Swap U and V. */ ++ usize = v->nlimbs; ++ usign = v->sign; ++ usecure = mpi_is_secure (v); ++ up = v->d; ++ vsize = u->nlimbs; ++ vsign = u->sign; ++ vsecure = mpi_is_secure (u); ++ vp = u->d; ++ } ++ else ++ { ++ usize = u->nlimbs; ++ usign = u->sign; ++ usecure = mpi_is_secure (u); ++ up = u->d; ++ vsize = v->nlimbs; ++ vsign = v->sign; ++ vsecure = mpi_is_secure (v); ++ vp = v->d; ++ } ++ sign_product = usign ^ vsign; ++ wp = w->d; ++ ++ /* make sure u and v have the same length by extending the limbs to the larger one, now u */ ++ if (usize != vsize) ++ { ++ mpi_limb_t *tmp_vp = mpi_alloc_limb_space (usize, vsecure); ++ clean_vp = 1; ++ MPN_ZERO (tmp_vp, (usize - vsize)); ++ MPN_COPY (tmp_vp + (usize - vsize), vp, vsize); ++ vsize = usize; ++ vp = tmp_vp; ++ } ++ ++ /* w == u */ ++ /* Ensure W has space enough to store the result. */ ++ wsize = usize + vsize; ++ if (!mpi_is_secure (w) && (mpi_is_secure (u) || mpi_is_secure (v))) ++ { ++ /* w is not allocated in secure space but u or v is. To make sure ++ * that no temporary results are stored in w, we temporary use ++ * a newly allocated limb space for w */ ++ wp = mpi_alloc_limb_space( wsize, 1 ); ++ assign_wp = 2; /* mark it as 2 so that we can later copy it back to ++ * normal memory */ ++ } ++ else if (w->alloced < wsize ) ++ { ++ if (wp == up || wp == vp) ++ { ++ wp = mpi_alloc_limb_space (wsize, mpi_is_secure (w)); ++ assign_wp = 1; ++ } ++ else ++ { ++ mpi_resize(w, wsize ); ++ wp = w->d; ++ } ++ } ++ else ++ { /* Make U and V not overlap with W. */ ++ if (wp == up) ++ { ++ /* W and U are identical. Allocate temporary space for U. */ ++ tmp_limb_nlimbs = usize; ++ up = tmp_limb = mpi_alloc_limb_space (usize, usecure); ++ /* Is V identical too? Keep it identical with U. */ ++ if (wp == vp) ++ vp = up; ++ /* Copy to the temporary space. */ ++ MPN_COPY (up, wp, usize); ++ } ++ else if (wp == vp) ++ { ++ /* W and V are identical. Allocate temporary space for V. */ ++ tmp_limb_nlimbs = vsize; ++ vp = tmp_limb = mpi_alloc_limb_space (vsize, vsecure); ++ /* Copy to the temporary space. */ ++ MPN_COPY (vp, wp, vsize); ++ } ++ } ++ ++ if (!vsize) ++ wsize = 0; ++ else ++ { ++ mpi_limb_t *tmp = mpi_alloc_limb_space (wsize * 2, mpi_is_secure (w)); ++ mul_cs (wp, up, vp, vsize, tmp); ++ _gcry_mpi_free_limb_space (tmp, wsize * 2); ++ } ++ ++ if (clean_vp) ++ { ++ _gcry_mpi_free_limb_space (vp, vsize); ++ } ++ if (assign_wp) ++ { ++ if (assign_wp == 2) ++ { ++ /* copy the temp wp from secure memory back to normal memory */ ++ mpi_ptr_t tmp_wp = mpi_alloc_limb_space (wsize, 0); ++ MPN_COPY (tmp_wp, wp, wsize); ++ _gcry_mpi_free_limb_space (wp, 0); ++ wp = tmp_wp; ++ } ++ _gcry_mpi_assign_limb_space (w, wp, wsize); ++ } ++ w->nlimbs = wsize; ++ w->sign = sign_product; ++ if (tmp_limb) ++ _gcry_mpi_free_limb_space (tmp_limb, tmp_limb_nlimbs); ++} ++#endif /* WITH_MARVIN_WORKAROUND */ + + void + _gcry_mpi_mulm (gcry_mpi_t w, gcry_mpi_t u, gcry_mpi_t v, gcry_mpi_t m) +@@ -221,3 +348,45 @@ _gcry_mpi_mulm (gcry_mpi_t w, gcry_mpi_t + if (temp_m) + mpi_free(temp_m); + } ++ ++#ifdef WITH_MARVIN_WORKAROUND ++static void ++_gcry_mpi_mod_sec (gcry_mpi_t ret, gcry_mpi_t a, gcry_mpi_t mod) ++{ ++ size_t asize = a->nlimbs; ++ size_t modsize = mod->nlimbs; ++ size_t tmp_size = mod_limb_numb (asize, modsize); ++ mpi_limb_t *tmp_limb = mpi_alloc_limb_space (tmp_size, mpi_is_secure(a)); ++ mod_cs (ret->d, a->d, asize, mod->d, modsize, tmp_limb); ++ /* cut the length to the mod size */ ++ ret->nlimbs = mod->nlimbs; ++ _gcry_mpi_free_limb_space (tmp_limb, tmp_size); ++} ++ ++/* The constant time code uses different order of the limbs ... */ ++static void ++_gcry_mpi_reverse_sec (gcry_mpi_t w) ++{ ++ for (size_t i = 0; i < w->nlimbs/2; i++) ++ { ++ mpi_limb_t t = w->d[i]; ++ w->d[i] = w->d[w->nlimbs - i - 1]; ++ w->d[w->nlimbs - i - 1] = t; ++ } ++} ++ ++void ++_gcry_mpi_mulm_sec (gcry_mpi_t w, gcry_mpi_t u, gcry_mpi_t v, gcry_mpi_t m) ++{ ++ /* w == u */ ++ _gcry_mpi_reverse_sec (u); ++ _gcry_mpi_reverse_sec (v); ++ _gcry_mpi_reverse_sec (m); ++ _gcry_mpi_mul_sec (w, u, v); ++ _gcry_mpi_mod_sec (w, w, m); ++ ++ /* get them back to the order the rest of the code expects */ ++ _gcry_mpi_reverse_sec (w); /* -- this is the result */ ++ _gcry_mpi_reverse_sec (m); /* -- this might be still used by the calling function */ ++} ++#endif /* WITH_MARVIN_WORKAROUND */ +Index: libgcrypt-1.11.1/src/gcrypt-int.h +=================================================================== +--- libgcrypt-1.11.1.orig/src/gcrypt-int.h ++++ libgcrypt-1.11.1/src/gcrypt-int.h +@@ -470,6 +470,9 @@ void _gcry_mpi_subm (gcry_mpi_t w, gcry_ + void _gcry_mpi_mul (gcry_mpi_t w, gcry_mpi_t u, gcry_mpi_t v); + void _gcry_mpi_mul_ui (gcry_mpi_t w, gcry_mpi_t u, unsigned long v ); + void _gcry_mpi_mulm (gcry_mpi_t w, gcry_mpi_t u, gcry_mpi_t v, gcry_mpi_t m); ++#ifdef WITH_MARVIN_WORKAROUND ++void _gcry_mpi_mulm_sec (gcry_mpi_t w, gcry_mpi_t u, gcry_mpi_t v, gcry_mpi_t m); ++#endif /* WITH_MARVIN_WORKAROUND */ + void _gcry_mpi_mul_2exp (gcry_mpi_t w, gcry_mpi_t u, unsigned long cnt); + void _gcry_mpi_div (gcry_mpi_t q, gcry_mpi_t r, + gcry_mpi_t dividend, gcry_mpi_t divisor, int round); +@@ -566,6 +569,9 @@ int _gcry_mpi_get_flag (gcry_mpi_t a, en + #define mpi_mul_2exp(w,u,v) _gcry_mpi_mul_2exp ((w),(u),(v)) + #define mpi_mul(w,u,v) _gcry_mpi_mul ((w),(u),(v)) + #define mpi_mulm(w,u,v,m) _gcry_mpi_mulm ((w),(u),(v),(m)) ++#ifdef WITH_MARVIN_WORKAROUND ++#define mpi_mulm_sec(w,u,v,m) _gcry_mpi_mulm_sec ((w),(u),(v),(m)) ++#endif /* WITH_MARVIN_WORKAROUND */ + #define mpi_powm(w,b,e,m) _gcry_mpi_powm ( (w), (b), (e), (m) ) + #define mpi_tdiv(q,r,a,m) _gcry_mpi_div ( (q), (r), (a), (m), 0) + #define mpi_fdiv(q,r,a,m) _gcry_mpi_div ( (q), (r), (a), (m), -1) +Index: libgcrypt-1.11.1/src/const-time.c +=================================================================== +--- libgcrypt-1.11.1.orig/src/const-time.c ++++ libgcrypt-1.11.1/src/const-time.c +@@ -77,8 +77,8 @@ _gcry_ct_memmov_cond (void *dst, const v + unsigned long op_enable) + { + /* Note: dual mask with AND/OR used for EM leakage mitigation */ +- unsigned char mask1 = ct_ulong_gen_mask(op_enable); +- unsigned char mask2 = ct_ulong_gen_inv_mask(op_enable); ++ volatile unsigned char mask1 = ct_ulong_gen_mask(op_enable); ++ volatile unsigned char mask2 = ct_ulong_gen_inv_mask(op_enable); + unsigned char *b_dst = dst; + const unsigned char *b_src = src; + size_t i; +@@ -86,3 +86,27 @@ _gcry_ct_memmov_cond (void *dst, const v + for (i = 0; i < len; i++) + b_dst[i] = (b_dst[i] & mask2) | (b_src[i] & mask1); + } ++ ++/* ++ * Copy LEN bytes from memory area SRC to memory area DST. The ++ * bytes are read up to the BUFFER_LEN size to keep the operation ++ * not dependent on the message length (both SRC and DST buffers ++ * need to have this size!). ++ */ ++void ++_gcry_ct_memcpy (void *dst, const void *src, size_t len, size_t buffer_len) ++{ ++ volatile unsigned char mask_a, mask_b; ++ unsigned char *b_dst = dst; ++ const unsigned char *b_src = src; ++ unsigned int writing; ++ size_t i; ++ ++ for (i = 0; i < buffer_len; i++) ++ { ++ writing = ct_lt (i, len); ++ mask_b = ct_uchar_gen_inv_mask (writing); ++ mask_a = ct_uchar_gen_mask (writing); ++ b_dst[i] = (b_src[i] & mask_a) | (b_dst[i] & mask_b); ++ } ++} +Index: libgcrypt-1.11.1/src/sexp.c +=================================================================== +--- libgcrypt-1.11.1.orig/src/sexp.c ++++ libgcrypt-1.11.1/src/sexp.c +@@ -31,6 +31,7 @@ + + #define GCRYPT_NO_MPI_MACROS 1 + #include "g10lib.h" ++#include "const-time.h" + + + /* Notes on the internal memory layout. +@@ -1079,6 +1080,10 @@ unquote_string (const char *string, size + * %d - integer stored as string (no autoswitch to secure allocation) + * %b - memory buffer; this takes _two_ arguments: an integer with the + * length of the buffer and a pointer to the buffer. ++ * %c - memory buffer same as %b, but written in constant time; this ++ * takes _three_ arguments: an integer with the length of the buffer, ++ * a pointer to the buffer and the maximum length of the buffer ++ * to avoid potential side channel leaking the buffer length. + * %S - Copy an gcry_sexp_t here. The S-expression needs to be a + * regular one, starting with a parenthesis. + * (no autoswitch to secure allocation) +@@ -1204,7 +1209,7 @@ do_vsexp_sscan (gcry_sexp_t *retsexp, si + { + switch (*p) + { +- case 'b': case 't': case 'v': case 'n': case 'f': ++ case 'b': case 'c': case 't': case 'v': case 'n': case 'f': + case 'r': case '"': case '\'': case '\\': + quoted_esc = 0; + break; +@@ -1538,14 +1543,27 @@ do_vsexp_sscan (gcry_sexp_t *retsexp, si + memcpy (c.pos, astr, alen); + c.pos += alen; + } +- else if (*p == 'b') ++ else if (*p == 'b' || *p == 'c') + { + /* Insert a memory buffer. */ + const char *astr; +- int alen; ++ int alen, buflen = 0, reallen = 0; + + ARG_NEXT (alen, int); + ARG_NEXT (astr, const char *); ++ if (*p == 'c') ++ { ++ ARG_NEXT (buflen, int); ++ if (buflen < alen) ++ { ++ *erroff = p - buffer; ++ err = GPG_ERR_INV_ARG; ++ goto leave; ++ } ++ /* Do all the calculations with the buflen */ ++ reallen = alen; ++ alen = buflen; ++ } + + if (alen < 0) + { +@@ -1578,9 +1596,18 @@ do_vsexp_sscan (gcry_sexp_t *retsexp, si + } + + *c.pos++ = ST_DATA; +- STORE_LEN (c.pos, alen); +- memcpy (c.pos, astr, alen); +- c.pos += alen; ++ if (*p == 'c') ++ { ++ STORE_LEN (c.pos, reallen); ++ ct_memcpy (c.pos, astr, reallen, buflen); ++ c.pos += reallen; ++ } ++ else ++ { ++ STORE_LEN (c.pos, alen); ++ memcpy (c.pos, astr, alen); ++ c.pos += alen; ++ } + } + else if (*p == 'd') + { +Index: libgcrypt-1.11.1/cipher/pubkey-internal.h +=================================================================== +--- libgcrypt-1.11.1.orig/cipher/pubkey-internal.h ++++ libgcrypt-1.11.1/cipher/pubkey-internal.h +@@ -55,6 +55,14 @@ _gcry_rsa_pkcs1_encode_for_enc (gcry_mpi + gpg_err_code_t + _gcry_rsa_pkcs1_decode_for_enc (unsigned char **r_result, size_t *r_resultlen, + unsigned int nbits, gcry_mpi_t value); ++#ifdef WITH_MARVIN_WORKAROUND ++gpg_err_code_t ++_gcry_rsa_pkcs1_decode_for_enc_implicit_rejection (unsigned char **r_result, ++ size_t *r_resultlen, ++ unsigned int nbits, ++ gcry_mpi_t value, ++ unsigned char *kdk); ++#endif /* WITH_MARVIN_WORKAROUND */ + gpg_err_code_t + _gcry_rsa_pkcs1_encode_raw_for_sig (gcry_mpi_t *r_result, unsigned int nbits, + const unsigned char *value, size_t valuelen); +Index: libgcrypt-1.11.1/cipher/pubkey-util.c +=================================================================== +--- libgcrypt-1.11.1.orig/cipher/pubkey-util.c ++++ libgcrypt-1.11.1/cipher/pubkey-util.c +@@ -193,6 +193,15 @@ _gcry_pk_util_parse_flaglist (gcry_sexp_ + rc = GPG_ERR_INV_FLAG; + break; + ++#ifdef WITH_MARVIN_WORKAROUND ++ case 21: ++ if (!memcmp (s, "no-implicit-rejection", 21)) ++ flags |= PUBKEY_FLAG_NO_IMPLICIT_REJECTION; ++ else if (!igninvflag) ++ rc = GPG_ERR_INV_FLAG; ++ break; ++#endif /* WITH_MARVIN_WORKAROUND */ ++ + default: + if (!igninvflag) + rc = GPG_ERR_INV_FLAG; +Index: libgcrypt-1.11.1/src/cipher.h +=================================================================== +--- libgcrypt-1.11.1.orig/src/cipher.h ++++ libgcrypt-1.11.1/src/cipher.h +@@ -26,24 +26,25 @@ + + #include "../random/random.h" + +-#define PUBKEY_FLAG_NO_BLINDING (1 << 0) +-#define PUBKEY_FLAG_RFC6979 (1 << 1) +-#define PUBKEY_FLAG_FIXEDLEN (1 << 2) +-#define PUBKEY_FLAG_LEGACYRESULT (1 << 3) +-#define PUBKEY_FLAG_RAW_FLAG (1 << 4) +-#define PUBKEY_FLAG_TRANSIENT_KEY (1 << 5) +-#define PUBKEY_FLAG_USE_X931 (1 << 6) +-#define PUBKEY_FLAG_USE_FIPS186 (1 << 7) +-#define PUBKEY_FLAG_USE_FIPS186_2 (1 << 8) +-#define PUBKEY_FLAG_PARAM (1 << 9) +-#define PUBKEY_FLAG_COMP (1 << 10) +-#define PUBKEY_FLAG_NOCOMP (1 << 11) +-#define PUBKEY_FLAG_EDDSA (1 << 12) +-#define PUBKEY_FLAG_GOST (1 << 13) +-#define PUBKEY_FLAG_NO_KEYTEST (1 << 14) +-#define PUBKEY_FLAG_DJB_TWEAK (1 << 15) +-#define PUBKEY_FLAG_SM2 (1 << 16) +-#define PUBKEY_FLAG_PREHASH (1 << 17) ++#define PUBKEY_FLAG_NO_BLINDING (1 << 0) ++#define PUBKEY_FLAG_RFC6979 (1 << 1) ++#define PUBKEY_FLAG_FIXEDLEN (1 << 2) ++#define PUBKEY_FLAG_LEGACYRESULT (1 << 3) ++#define PUBKEY_FLAG_RAW_FLAG (1 << 4) ++#define PUBKEY_FLAG_TRANSIENT_KEY (1 << 5) ++#define PUBKEY_FLAG_USE_X931 (1 << 6) ++#define PUBKEY_FLAG_USE_FIPS186 (1 << 7) ++#define PUBKEY_FLAG_USE_FIPS186_2 (1 << 8) ++#define PUBKEY_FLAG_PARAM (1 << 9) ++#define PUBKEY_FLAG_COMP (1 << 10) ++#define PUBKEY_FLAG_NOCOMP (1 << 11) ++#define PUBKEY_FLAG_EDDSA (1 << 12) ++#define PUBKEY_FLAG_GOST (1 << 13) ++#define PUBKEY_FLAG_NO_KEYTEST (1 << 14) ++#define PUBKEY_FLAG_DJB_TWEAK (1 << 15) ++#define PUBKEY_FLAG_SM2 (1 << 16) ++#define PUBKEY_FLAG_PREHASH (1 << 17) ++#define PUBKEY_FLAG_NO_IMPLICIT_REJECTION (1 << 18) + + + enum pk_operation +Index: libgcrypt-1.11.1/tests/pkcs1v2-v15c.h +=================================================================== +--- libgcrypt-1.11.1.orig/tests/pkcs1v2-v15c.h ++++ libgcrypt-1.11.1/tests/pkcs1v2-v15c.h +@@ -21,6 +21,7 @@ + const char *mesg; + const char *seed; + const char *encr; ++ const char *synt; + } m[20]; + } tbl[] = + { +@@ -3915,5 +3916,308 @@ + "25db1dd892b71bb74a5cf68263d8fd58f1a48e6c2fcb8c0b71a251cfc1a20157" + } + } ++ }, ++ { ++ "A 2048-bit RSA Test vectors for the Bleichenbacher workaround", ++ "c8cc839714098da56caa23640f93dc8997c16372968fc1b0c6df5113c1c94e8b21e48ad2297e65419011b4e6d8f5e73b1b78b257400321d1ef6b602d4ec8ce8d141c94905eb4ad306639a49206534b6e7f2607423e97dffd133c88d721399defbc7e96ccdcbd7f3aae1fe892712bfb4929817d511666440a1facb7a208f5ea165910add8a3f2d497202360ccb632024f0d07169c1918f316f794b143aef54ec87522a4c02978f9689980bffbf649c307e81819bff88409638d48bd94be152b59ff649fa0bd629d0ffa1813c3abf4b56bd3c2ea5465dffa14589292a9d8a24ad26be7ee0510741b6382d43c83d5bfa40a46613d062be445517dbcaf0cb4e1a769", ++ "010001", ++ "1455010e0f2d587663a666a6ff1ccdbbf0edd8100646d02a023922908992c4ad39e5565929726ef6508c3a71158ef0b6ff751d39d07580bb2d2f063210442d0603ff50dbbd7b35fe2c9bb19a47a1af85a4c24901e02ca8b58b7919b20edf32aacfbf51adb4bc4b61b9b7e968caa4d570f70ef18d8063228893e47d439efca793259bcf2cd108a3d8688cdf078e7ac799969f2339d2c1f522b969684629a933baaec2681625eab84f4e56f4447e9d88fb9a199cf71023e0e257b14441b33c84d3bc67ca8031d2612618103a7a0a40844262f75d8890cd616e51f9035488fd6e099de8ff6d65a4ff118254807c9f58d2fbba8ba151dc8c68be349c977a204e04c1", ++ { ++ { ++ "1. a random positive test case", ++ NULL, ++ "", ++ "8bfe264e85d3bdeaa6b8851b8e3b956ee3d226fd3f69063a86880173a273d9f283b2eebdd1ed35f7e02d91c571981b6737d5320bd8396b0f3ad5b019daec1b0aab3cbbc026395f4fd14f13673f2dfc81f9b660ec26ac381e6db3299b4e460b43fab9955df2b3cfaa20e900e19c856238fd371899c2bf2ce8c868b76754e5db3b036533fd603746be13c10d4e3e6022ebc905d20c2a7f32b215a4cd53b3f44ca1c327d2c2b651145821c08396c89071f665349c25e44d2733cd9305985ceef6430c3cf57af5fa224089221218fa34737c79c446d28a94c41c96e4e92ac53fbcf384dea8419ea089f8784445a492c812eb0d409467f75afd7d4d1078886205a066", ++ "6c6f72656d20697073756d20646f6c6f722073697420616d6574" ++ },{ ++ "2. a random negative test case decrypting to empty", ++ NULL, ++ "", ++ "20aaa8adbbc593a924ba1c5c7990b5c2242ae4b99d0fe636a19a4cf754edbcee774e472fe028160ed42634f8864900cb514006da642cae6ae8c7d087caebcfa6dad1551301e130344989a1d462d4164505f6393933450c67bc6d39d8f5160907cabc251b737925a1cf21e5c6aa5781b7769f6a2a583d97cce008c0f8b6add5f0b2bd80bee60237aa39bb20719fe75749f4bc4e42466ef5a861ae3a92395c7d858d430bfe38040f445ea93fa2958b503539800ffa5ce5f8cf51fa8171a91f36cb4f4575e8de6b4d3f096ee140b938fd2f50ee13f0d050222e2a72b0a3069ff3a6738e82c87090caa5aed4fcbe882c49646aa250b98f12f83c8d528113614a29e7", ++ "" ++ },{ ++ "3. invalid decrypting to max length message", ++ NULL, ++ "", ++ "48cceab10f39a4db32f60074feea473cbcdb7accf92e150417f76b44756b190e843e79ec12aa85083a21f5437e7bad0a60482e601198f9d86923239c8786ee728285afd0937f7dde12717f28389843d7375912b07b991f4fdb0190fced8ba665314367e8c5f9d2981d0f5128feeb46cb50fc237e64438a86df198dd0209364ae3a842d77532b66b7ef263b83b1541ed671b120dfd660462e2107a4ee7b964e734a7bd68d90dda61770658a3c242948532da32648687e0318286473f675b412d6468f013f14d760a358dfcad3cda2afeec5e268a37d250c37f722f468a70dfd92d7294c3c1ee1e7f8843b7d16f9f37ef35748c3ae93aa155cdcdfeb4e78567303", ++ "22d850137b9eebe092b24f602dc5bb7918c16bd89ddbf20467b119d205f9c2e4bd7d2592cf1e532106e0f33557565923c73a02d4f09c0c22bea89148183e60317f7028b3aa1f261f91c979393101d7e15f4067e63979b32751658ef769610fe97cf9cef3278b3117d384051c3b1d82c251c2305418c8f6840530e631aad63e70e20e025bcd8efb54c92ec6d3b106a2f8e64eeff7d38495b0fc50c97138af4b1c0a67a1c4e27b077b8439332edfa8608dfeae653cd6a628ac550395f7e74390e42c11682234870925eeaa1fa71b76cf1f2ee3bda69f6717033ff8b7c95c9799e7a3bea5e7e4a1c359772fb6b1c6e6c516661dfe30c3" ++ },{ ++ "4. invalid decrypting to message with length specified by second to last value from PRF", ++ NULL, ++ "", ++ "1439e08c3f84c1a7fec74ce07614b20e01f6fa4e8c2a6cffdc3520d8889e5d9a950c6425798f85d4be38d300ea5695f13ecd4cb389d1ff5b82484b494d6280ab7fa78e645933981cb934cce8bfcd114cc0e6811eefa47aae20af638a1cd163d2d3366186d0a07df0c81f6c9f3171cf3561472e98a6006bf75ddb457bed036dcce199369de7d94ef2c68e8467ee0604eea2b3009479162a7891ba5c40cab17f49e1c438cb6eaea4f76ce23cce0e483ff0e96fa790ea15be67671814342d0a23f4a20262b6182e72f3a67cd289711503c85516a9ed225422f98b116f1ab080a80abd6f0216df88d8cfd67c139243be8dd78502a7aaf6bc99d7da71bcdf627e7354", ++ "0f9b" ++ },{ ++ "5. invalid decrypting to message with length specified by third to last value from PRF", ++ NULL, ++ "", ++ "1690ebcceece2ce024f382e467cf8510e74514120937978576caf684d4a02ad569e8d76cbe365a060e00779de2f0865ccf0d923de3b4783a4e2c74f422e2f326086c390b658ba47f31ab013aa80f468c71256e5fa5679b24e83cd82c3d1e05e398208155de2212993cd2b8bab6987cf4cc1293f19909219439d74127545e9ed8a706961b8ee2119f6bfacafbef91b75a789ba65b8b833bc6149cf49b5c4d2c6359f62808659ba6541e1cd24bf7f7410486b5103f6c0ea29334ea6f4975b17387474fe920710ea61568d7b7c0a7916acf21665ad5a31c4eabcde44f8fb6120d8457afa1f3c85d517cda364af620113ae5a3c52a048821731922737307f77a1081", ++ "4f02" ++ },{ ++ "6. positive test with 11 byte long value", ++ NULL, ++ "", ++ "6213634593332c485cef783ea2846e3d6e8b0e005cd8293eaebbaa5079712fd681579bdfbbda138ae4d9d952917a03c92398ec0cb2bb0c6b5a8d55061fed0d0d8d72473563152648cfe640b335dc95331c21cb133a91790fa93ae44497c128708970d2beeb77e8721b061b1c44034143734a77be8220877415a6dba073c3871605380542a9f25252a4babe8331cdd53cf828423f3cc70b560624d0581fb126b2ed4f4ed358f0eb8065cf176399ac1a846a31055f9ae8c9c24a1ba050bc20842125bc1753158f8065f3adb9cc16bfdf83816bdf38b624f12022c5a6fbfe29bc91542be8c0208a770bcd677dc597f5557dc2ce28a11bf3e3857f158717a33f6592", ++ "6c6f72656d20697073756d" ++ },{ ++ "7. positive test with 11 byte long value and zero padded ciphertext", ++ NULL, ++ "", ++ "00a2e8f114ea8d05d12dc843e3cc3b2edc8229ff2a028bda29ba9d55e3cd02911902fef1f42a075bf05e8016e8567213d6f260fa49e360779dd81aeea3e04c2cb567e0d72b98bf754014561b7511e083d20e0bfb9cd23f8a0d3c88900c49d2fcd5843ff0765607b2026f28202a87aa94678aed22a0c20724541394cd8f44e373eba1d2bae98f516c1e2ba3d86852d064f856b1daf24795e767a2b90396e50743e3150664afab131fe40ea405dcf572dd1079af1d3f0392ccadcca0a12740dbb213b925ca2a06b1bc1383e83a658c82ba2e7427342379084d5f66b544579f07664cb26edd4f10fd913fdbc0de05ef887d4d1ec1ac95652397ea7fd4e4759fda8b", ++ "6c6f72656d20697073756d" ++ },{ ++ "8. positive test with 11 byte long value and zero truncated ciphertext", ++ NULL, ++ "", ++ "a2e8f114ea8d05d12dc843e3cc3b2edc8229ff2a028bda29ba9d55e3cd02911902fef1f42a075bf05e8016e8567213d6f260fa49e360779dd81aeea3e04c2cb567e0d72b98bf754014561b7511e083d20e0bfb9cd23f8a0d3c88900c49d2fcd5843ff0765607b2026f28202a87aa94678aed22a0c20724541394cd8f44e373eba1d2bae98f516c1e2ba3d86852d064f856b1daf24795e767a2b90396e50743e3150664afab131fe40ea405dcf572dd1079af1d3f0392ccadcca0a12740dbb213b925ca2a06b1bc1383e83a658c82ba2e7427342379084d5f66b544579f07664cb26edd4f10fd913fdbc0de05ef887d4d1ec1ac95652397ea7fd4e4759fda8b", ++ "6c6f72656d20697073756d" ++ },{ ++ "9. positive test with 11 byte long value and double zero padded ciphertext", ++ NULL, ++ "", ++ "00001f71879b426127f7dead621f7380a7098cf7d22173aa27991b143c46d53383c209bd0c9c00d84078037e715f6b98c65005a77120070522ede51d472c87ef94b94ead4c5428ee108a345561658301911ec5a8f7dd43ed4a3957fd29fb02a3529bf63f8040d3953490939bd8f78b2a3404b6fb5ff70a4bfdaac5c541d6bcce49c9778cc390be24cbef1d1eca7e870457241d3ff72ca44f9f56bdf31a890fa5eb3a9107b603ccc9d06a5dd911a664c82b6abd4fe036f8db8d5a070c2d86386ae18d97adc1847640c211d91ff5c3387574a26f8ef27ca7f48d2dd1f0c7f14b81cc9d33ee6853031d3ecf10a914ffd90947909c8011fd30249219348ebff76bfc", ++ "6c6f72656d20697073756d" ++ },{ ++ "10. a random negative test that generates an 11 byte long message", ++ NULL, ++ "", ++ "5f02f4b1f46935c742ebe62b6f05aa0a3286aab91a49b34780adde6410ab46f7386e05748331864ac98e1da63686e4babe3a19ed40a7f5ceefb89179596aab07ab1015e03b8f825084dab028b6731288f2e511a4b314b6ea3997d2e8fe2825cef8897cbbdfb6c939d441d6e04948414bb69e682927ef8576c9a7090d4aad0e74c520d6d5ce63a154720f00b76de8cc550b1aa14f016d63a7b6d6eaa1f7dbe9e50200d3159b3d099c900116bf4eba3b94204f18b1317b07529751abf64a26b0a0bf1c8ce757333b3d673211b67cc0653f2fe2620d57c8b6ee574a0323a167eab1106d9bc7fd90d415be5f1e9891a0e6c709f4fc0404e8226f8477b4e939b36eb2", ++ "af9ac70191c92413cb9f2d" ++ },{ ++ "11. an otherwise correct plaintext, but with wrong first byte (0x01 instead of 0x00), generates a random 11 byte long plaintext", ++ NULL, ++ "", ++ "9b2ec9c0c917c98f1ad3d0119aec6be51ae3106e9af1914d48600ab6a2c0c0c8ae02a2dc3039906ff3aac904af32ec798fd65f3ad1afa2e69400e7c1de81f5728f3b3291f38263bc7a90a0563e43ce7a0d4ee9c0d8a716621ca5d3d081188769ce1b131af7d35b13dea99153579c86db31fe07d5a2c14d621b77854e48a8df41b5798563af489a291e417b6a334c63222627376118c02c53b6e86310f728734ffc86ef9d7c8bf56c0c841b24b82b59f51aee4526ba1c4268506d301e4ebc498c6aebb6fd5258c876bf900bac8ca4d309dd522f6a6343599a8bc3760f422c10c72d0ad527ce4af1874124ace3d99bb74db8d69d2528db22c3a37644640f95c05f", ++ "a1f8c9255c35cfba403ccc" ++ },{ ++ "12. an otherwise correct plaintext, but with wrong second byte (0x01 instead of 0x02), generates a random 11 byte long plaintext", ++ NULL, ++ "", ++ "782c2b59a21a511243820acedd567c136f6d3090c115232a82a5efb0b178285f55b5ec2d2bac96bf00d6592ea7cdc3341610c8fb07e527e5e2d20cfaf2c7f23e375431f45e998929a02f25fd95354c33838090bca838502259e92d86d568bc2cdb132fab2a399593ca60a015dc2bb1afcd64fef8a3834e17e5358d822980dc446e845b3ab4702b1ee41fe5db716d92348d5091c15d35a110555a35deb4650a5a1d2c98025d42d4544f8b32aa6a5e02dc02deaed9a7313b73b49b0d4772a3768b0ea0db5846ace6569cae677bf67fb0acf3c255dc01ec8400c963b6e49b1067728b4e563d7e1e1515664347b92ee64db7efb5452357a02fff7fcb7437abc2e579", ++ "e6d700309ca0ed62452254" ++ },{ ++ "13. an invalid ciphertext, with a zero byte in first byte of ciphertext, decrypts to a random 11 byte long synthethic plaintext", ++ NULL, ++ "", ++ "0096136621faf36d5290b16bd26295de27f895d1faa51c800dafce73d001d60796cd4e2ac3fa2162131d859cd9da5a0c8a42281d9a63e5f353971b72e36b5722e4ac444d77f892a5443deb3dca49fa732fe855727196e23c26eeac55eeced8267a209ebc0f92f4656d64a6c13f7f7ce544ebeb0f668fe3a6c0f189e4bcd5ea12b73cf63e0c8350ee130dd62f01e5c97a1e13f52fde96a9a1bc9936ce734fdd61f27b18216f1d6de87f49cf4f2ea821fb8efd1f92cdad529baf7e31aff9bff4074f2cad2b4243dd15a711adcf7de900851fbd6bcb53dac399d7c880531d06f25f7002e1aaf1722765865d2c2b902c7736acd27bc6cbd3e38b560e2eecf7d4b576", ++ "ba27b1842e7c21c0e7ef6a" ++ },{ ++ "14. an invalid ciphertext, with a zero byte removed from first byte of ciphertext, decrypts to a random 11 byte long synthethic plaintext", ++ NULL, ++ "", ++ "96136621faf36d5290b16bd26295de27f895d1faa51c800dafce73d001d60796cd4e2ac3fa2162131d859cd9da5a0c8a42281d9a63e5f353971b72e36b5722e4ac444d77f892a5443deb3dca49fa732fe855727196e23c26eeac55eeced8267a209ebc0f92f4656d64a6c13f7f7ce544ebeb0f668fe3a6c0f189e4bcd5ea12b73cf63e0c8350ee130dd62f01e5c97a1e13f52fde96a9a1bc9936ce734fdd61f27b18216f1d6de87f49cf4f2ea821fb8efd1f92cdad529baf7e31aff9bff4074f2cad2b4243dd15a711adcf7de900851fbd6bcb53dac399d7c880531d06f25f7002e1aaf1722765865d2c2b902c7736acd27bc6cbd3e38b560e2eecf7d4b576", ++ "ba27b1842e7c21c0e7ef6a" ++ },{ ++ "15. an invalid ciphertext, with two zero bytes in first bytes of ciphertext, decrypts to a random 11 byte long synthethic plaintext", ++ NULL, ++ "", ++ "0000587cccc6b264bdfe0dc2149a988047fa921801f3502ea64624c510c6033d2f427e3f136c26e88ea9f6519e86a542cec96aad1e5e9013c3cc203b6de15a69183050813af5c9ad79703136d4b92f50ce171eefc6aa7988ecf02f319ffc5eafd6ee7a137f8fce64b255bb1b8dd19cfe767d64fdb468b9b2e9e7a0c24dae03239c8c714d3f40b7ee9c4e59ac15b17e4d328f1100756bce17133e8e7493b54e5006c3cbcdacd134130c5132a1edebdbd01a0c41452d16ed7a0788003c34730d0808e7e14c797a21f2b45a8aa1644357fd5e988f99b017d9df37563a354c788dc0e2f9466045622fa3f3e17db63414d27761f57392623a2bef6467501c63e8d645", ++ "d5cf555b1d6151029a429a" ++ },{ ++ "16. an invalid ciphertext, with two zero bytes removed from first bytes of ciphertext, decrypts to a random 11 byte long synthethic plaintext", ++ NULL, ++ "", ++ "587cccc6b264bdfe0dc2149a988047fa921801f3502ea64624c510c6033d2f427e3f136c26e88ea9f6519e86a542cec96aad1e5e9013c3cc203b6de15a69183050813af5c9ad79703136d4b92f50ce171eefc6aa7988ecf02f319ffc5eafd6ee7a137f8fce64b255bb1b8dd19cfe767d64fdb468b9b2e9e7a0c24dae03239c8c714d3f40b7ee9c4e59ac15b17e4d328f1100756bce17133e8e7493b54e5006c3cbcdacd134130c5132a1edebdbd01a0c41452d16ed7a0788003c34730d0808e7e14c797a21f2b45a8aa1644357fd5e988f99b017d9df37563a354c788dc0e2f9466045622fa3f3e17db63414d27761f57392623a2bef6467501c63e8d645", ++ "d5cf555b1d6151029a429a" ++ },{ ++ "17. and invalid ciphertext, otherwise valid but starting with 000002, decrypts to random 11 byte long synthethic plaintext", ++ NULL, ++ "", ++ "1786550ce8d8433052e01ecba8b76d3019f1355b212ac9d0f5191b023325a7e7714b7802f8e9a17c4cb3cd3a84041891471b10ca1fcfb5d041d34c82e6d0011cf4dc76b90e9c2e0743590579d55bcd7857057152c4a8040361343d1d22ba677d62b011407c652e234b1d663af25e2386251d7409190f19fc8ec3f9374fdf1254633874ce2ec2bff40ad0cb473f9761ec7b68da45a4bd5e33f5d7dac9b9a20821df9406b653f78a95a6c0ea0a4d57f867e4db22c17bf9a12c150f809a7b72b6db86c22a8732241ebf3c6a4f2cf82671d917aba8bc61052b40ccddd743a94ea9b538175106201971cca9d136d25081739aaf6cd18b2aecf9ad320ea3f89502f955", ++ "3d4a054d9358209e9cbbb9" ++ },{ ++ "18. negative test with otherwise valid padding but a zero byte in first byte of padding", ++ NULL, ++ "", ++ "179598823812d2c58a7eb50521150a48bcca8b4eb53414018b6bca19f4801456c5e36a940037ac516b0d6412ba44ec6b4f268a55ef1c5ffbf18a2f4e3522bb7b6ed89774b79bffa22f7d3102165565642de0d43a955e96a1f2e80e5430671d7266eb4f905dc8ff5e106dc5588e5b0289e49a4913940e392a97062616d2bda38155471b7d360cfb94681c702f60ed2d4de614ea72bf1c53160e63179f6c5b897b59492bee219108309f0b7b8cb2b136c346a5e98b8b4b8415fb1d713bae067911e3057f1c335b4b7e39101eafd5d28f0189037e4334f4fdb9038427b1d119a6702aa8233319cc97d496cc289ae8c956ddc84042659a2d43d6aa22f12b81ab884e", ++ "1f037dd717b07d3e7f7359" ++ },{ ++ "19. negative test with otherwise valid padding but a zero byte at the eigth byte of padding", ++ NULL, ++ "", ++ "a7a340675a82c30e22219a55bc07cdf36d47d01834c1834f917f18b517419ce9de2a96460e745024436470ed85e94297b283537d52189c406a3f533cb405cc6a9dba46b482ce98b6e3dd52d8fce2237425617e38c11fbc46b61897ef200d01e4f25f5f6c4c5b38cd0de38ba11908b86595a8036a08a42a3d05b79600a97ac18ba368a08d6cf6ccb624f6e8002afc75599fba4de3d4f3ba7d208391ebe8d21f8282b18e2c10869eb2702e68f9176b42b0ddc9d763f0c86ba0ff92c957aaeab76d9ab8da52ea297ec11d92d770146faa1b300e0f91ef969b53e7d2907ffc984e9a9c9d11fb7d6cba91972059b46506b035efec6575c46d7114a6b935864858445f", ++ "63cb0bf65fc8255dd29e17" ++ },{ ++ "20. negative test with an otherwise valid plaintext but with missing separator byte", ++ NULL, ++ "", ++ "3d1b97e7aa34eaf1f4fc171ceb11dcfffd9a46a5b6961205b10b302818c1fcc9f4ec78bf18ea0cee7e9fa5b16fb4c611463b368b3312ac11cf9c06b7cf72b54e284848a508d3f02328c62c2999d0fb60929f81783c7a256891bc2ff4d91df2af96a24fc5701a1823af939ce6dbdc510608e3d41eec172ad2d51b9fc61b4217c923cadcf5bac321355ef8be5e5f090cdc2bd0c697d9058247db3ad613fdce87d2955a6d1c948a5160f93da21f731d74137f5d1f53a1923adb513d2e6e1589d44cc079f4c6ddd471d38ac82d20d8b1d21f8d65f3b6907086809f4123e08d86fb38729585de026a485d8f0e703fd4772f6668febf67df947b82195fa3867e3a3065", ++ "6f09a0b62699337c497b0b" ++ } ++ } ++ }, ++ { ++ "A 2049-bit RSA Test vectors for the Bleichenbacher workaround", ++ "0155f889556a1775f1c7a7786a50b18bc28c9e986ede5667cab39b84124e90eba75c1db083ac3e443bba94dc23560f75e3a81693a2a43bdc7426d8c4eafe68c85de0fe757f6e49bb9ed447e602430800dbb04ceb22e7fa57a18d338fb66026cdb467e70cc040e7d367ef403c7bf1e3df624650094631f21eafd2fb5bc915ff04379acd1112f732c0b46607c178d38a20f52eda509f2f9c0405d51069e80ccf941554d0470467505c3cf541ea0897dfc9f400cecb298ffc753372d9f6933af174cc40ed96d467031733b97f8cddd3f92bc3a03ea8576c417f24007b5e4f7501105b544de9fadcdffadf98dfb4bb05b8199f3f85acfd91f7a9a094b9a383f5049097", ++ "010001", ++ "0119c2b3f50a7ad6152679d7ff510958ac2d8ca6f0028592f332d55a16736178a8e67f17e705ce300e3e87547251006013f974d0a3db49ef344ca5a26a34c0450704d0e422e0ce23a69425c15fefb6f26e106eeff64cc8b9d7442e4da4e8c85008eaeb365859a2294fa3937bc26be56332e7d81e2c160ef635cc528aa7be55e633a723dbc1e16ba29e52b29aef2f9e5654fdc0666bb0fc254acbe80e63874f0f5f020782e3c9dcfc2520d0c9c4a7b634e4503fbb493e1aafeeb3f88bd7a13398725dae6fe399e775cd5d4cf09fc838347c4c98dab1a4883cce620513615afaa10a63368e6d7b79df4166ab162739ef515a4402ee1e0601c5a55bc71df0e30edf81", ++ { ++ { ++ "1. malformed that generates length specified by 3rd last value from PRF", ++ NULL, ++ "", ++ "00b26f6404b82649629f2704494282443776929122e279a9cf30b0c6fe8122a0a9042870d97cc8ef65490fe58f031eb2442352191f5fbc311026b5147d32df914599f38b825ebb824af0d63f2d541a245c5775d1c4b78630e4996cc5fe413d38455a776cf4edcc0aa7fccb31c584d60502ed2b77398f536e137ff7ba6430e9258e21c2db5b82f5380f566876110ac4c759178900fbad7ab70ea07b1daf7a1639cbb4196543a6cbe8271f35dddb8120304f6eef83059e1c5c5678710f904a6d760c4d1d8ad076be17904b9e69910040b47914a0176fb7eea0c06444a6c4b86d674d19a556a1de5490373cb01ce31bbd15a5633362d3d2cd7d4af1b4c5121288b894", ++ "42" ++ },{ ++ "2. simple positive test case", ++ NULL, ++ "", ++ "013300edbf0bb3571e59889f7ed76970bf6d57e1c89bbb6d1c3991d9df8e65ed54b556d928da7d768facb395bbcc81e9f8573b45cf8195dbd85d83a59281cddf4163aec11b53b4140053e3bd109f787a7c3cec31d535af1f50e0598d85d96d91ea01913d07097d25af99c67464ebf2bb396fb28a9233e56f31f7e105d71a23e9ef3b736d1e80e713d1691713df97334779552fc94b40dd733c7251bc522b673d3ec9354af3dd4ad44fa71c0662213a57ada1d75149697d0eb55c053aaed5ffd0b815832f454179519d3736fb4faf808416071db0d0f801aca8548311ee708c131f4be658b15f6b54256872c2903ac708bd43b017b073b5707bc84c2cd9da70e967", ++ "6c6f72656d20697073756d" ++ },{ ++ "3. positive test case with null padded ciphertext", ++ NULL, ++ "", ++ "0002aadf846a329fadc6760980303dbd87bfadfa78c2015ce4d6c5782fd9d3f1078bd3c0a2c5bfbdd1c024552e5054d98b5bcdc94e476dd280e64d650089326542ce7c61d4f1ab40004c2e6a88a883613568556a10f3f9edeab67ae8dddc1e6b0831c2793d2715de943f7ce34c5c05d1b09f14431fde566d17e76c9feee90d86a2c158616ec81dda0c642f58c0ba8fa4495843124a7235d46fb4069715a51bf710fd024259131ba94da73597ace494856c94e7a3ec261545793b0990279b15fa91c7fd13dbfb1df2f221dab9fa9f7c1d21e48aa49f6aaecbabf5ee76dc6c2af2317ffb4e303115386a97f8729afc3d0c89419669235f1a3a69570e0836c79fc162", ++ "6c6f72656d20697073756d" ++ },{ ++ "4. positive test case with null truncated ciphertext", ++ NULL, ++ "", ++ "02aadf846a329fadc6760980303dbd87bfadfa78c2015ce4d6c5782fd9d3f1078bd3c0a2c5bfbdd1c024552e5054d98b5bcdc94e476dd280e64d650089326542ce7c61d4f1ab40004c2e6a88a883613568556a10f3f9edeab67ae8dddc1e6b0831c2793d2715de943f7ce34c5c05d1b09f14431fde566d17e76c9feee90d86a2c158616ec81dda0c642f58c0ba8fa4495843124a7235d46fb4069715a51bf710fd024259131ba94da73597ace494856c94e7a3ec261545793b0990279b15fa91c7fd13dbfb1df2f221dab9fa9f7c1d21e48aa49f6aaecbabf5ee76dc6c2af2317ffb4e303115386a97f8729afc3d0c89419669235f1a3a69570e0836c79fc162", ++ "6c6f72656d20697073756d" ++ },{ ++ "5. positive test case with double null padded ciphertext", ++ NULL, ++ "", ++ "0000f36da3b72d8ff6ded74e7efd08c01908f3f5f0de7b55eab92b5f875190809c39d4162e1e6649618f854fd84aeab03970d16bb814e999852c06de38d82b95c0f32e2a7b5714021fe303389be9c0eac24c90a6b7210f929d390fabf903d44e04110bb7a7fd6c383c275804721efa6d7c93aa64c0bb2b18d97c5220a846c66a4895ae52adddbe2a9996825e013585adcec4b32ba61d782737bd343e5fabd68e8a95b8b1340318559860792dd70dffbe05a1052b54cbfb48cfa7bb3c19cea52076bddac5c25ee276f153a610f6d06ed696d192d8ae4507ffae4e5bdda10a625d6b67f32f7cffcd48dee2431fe66f6105f9d17e611cdcc674868e81692a360f4052", ++ "6c6f72656d20697073756d" ++ },{ ++ "6. positive test case with double null truncated ciphertext", ++ NULL, ++ "", ++ "f36da3b72d8ff6ded74e7efd08c01908f3f5f0de7b55eab92b5f875190809c39d4162e1e6649618f854fd84aeab03970d16bb814e999852c06de38d82b95c0f32e2a7b5714021fe303389be9c0eac24c90a6b7210f929d390fabf903d44e04110bb7a7fd6c383c275804721efa6d7c93aa64c0bb2b18d97c5220a846c66a4895ae52adddbe2a9996825e013585adcec4b32ba61d782737bd343e5fabd68e8a95b8b1340318559860792dd70dffbe05a1052b54cbfb48cfa7bb3c19cea52076bddac5c25ee276f153a610f6d06ed696d192d8ae4507ffae4e5bdda10a625d6b67f32f7cffcd48dee2431fe66f6105f9d17e611cdcc674868e81692a360f4052", ++ "6c6f72656d20697073756d" ++ },{ ++ "7. a random negative test case that generates an 11 byte long message", ++ NULL, ++ "", ++ "00f910200830fc8fff478e99e145f1474b312e2512d0f90b8cef77f8001d09861688c156d1cbaf8a8957f7ebf35f724466952d0524cad48aad4fba1e45ce8ea27e8f3ba44131b7831b62d60c0762661f4c1d1a88cd06263a259abf1ba9e6b0b172069afb86a7e88387726f8ab3adb30bfd6b3f6be6d85d5dfd044e7ef052395474a9cbb1c3667a92780b43a22693015af6c513041bdaf87d43b24ddd244e791eeaea1066e1f4917117b3a468e22e0f7358852bb981248de4d720add2d15dccba6280355935b67c96f9dcb6c419cc38ab9f6fba2d649ef2066e0c34c9f788ae49babd9025fa85b21113e56ce4f43aa134c512b030dd7ac7ce82e76f0be9ce09ebca", ++ "1189b6f5498fd6df532b00" ++ },{ ++ "8. otherwise correct plaintext, but with wrong first byte (0x01 instead of 0x00)", ++ NULL, ++ "", ++ "002c9ddc36ba4cf0038692b2d3a1c61a4bb3786a97ce2e46a3ba74d03158aeef456ce0f4db04dda3fe062268a1711250a18c69778a6280d88e133a16254e1f0e30ce8dac9b57d2e39a2f7d7be3ee4e08aec2fdbe8dadad7fdbf442a29a8fb40857407bf6be35596b8eefb5c2b3f58b894452c2dc54a6123a1a38d642e23751746597e08d71ac92704adc17803b19e131b4d1927881f43b0200e6f95658f559f912c889b4cd51862784364896cd6e8618f485a992f82997ad6a0917e32ae5872eaf850092b2d6c782ad35f487b79682333c1750c685d7d32ab3e1538f31dcaa5e7d5d2825875242c83947308dcf63ba4bfff20334c9c140c837dbdbae7a8dee72ff", ++ "f6d0f5b78082fe61c04674" ++ },{ ++ "9. otherwise correct plaintext, but with wrong second byte (0x01 instead of 0x02)", ++ NULL, ++ "", ++ "00c5d77826c1ab7a34d6390f9d342d5dbe848942e2618287952ba0350d7de6726112e9cebc391a0fae1839e2bf168229e3e0d71d4161801509f1f28f6e1487ca52df05c466b6b0a6fbbe57a3268a970610ec0beac39ec0fa67babce1ef2a86bf77466dc127d7d0d2962c20e66593126f276863cd38dc6351428f884c1384f67cad0a0ffdbc2af16711fb68dc559b96b37b4f04cd133ffc7d79c43c42ca4948fa895b9daeb853150c8a5169849b730cc77d68b0217d6c0e3dbf38d751a1998186633418367e7576530566c23d6d4e0da9b038d0bb5169ce40133ea076472d055001f0135645940fd08ea44269af2604c8b1ba225053d6db9ab43577689401bdc0f3", ++ "1ab287fcef3ff17067914d" ++ },{ ++ NULL, ++ NULL, ++ NULL, ++ NULL, ++ NULL, ++ } ++ } ++ }, ++ { ++ "RSA decrypt with 3072 bit keys", ++ "afd71caad5e9f5b8c6c367070a47f19d7e66aede18a5b2741fb3c4d33434560692a2d909ef6888ec602ff6b93af258ee74303c301afcd4edbec43311ddc8ddbf00ddbbe386d33b8d0e22b1b44936dc489871b85237b34ce747ad8fdb0c4e4d1daa7aadf07385c5c8732ccb7d5a49e2e50c883c7d7ac10ed6a74d9ac90df9129905a17d4a087210fc78b6d04b1eb969482c11a6eeb79c50e5b16f3f254f7571528b2f1716ab816d6eca0727bdea98059329730eb8c33ce71d61dd4ac393b6256e07ac1d124f0200d1c3e05a4c1bc7f1ed2fc83e57199cfe5908b10087e27fbd97d2c24214619c7147c8fbefca39bc256762a6823531f7e234d68eae7a0d9faf10dd15e9523780c7d5ae58094ad525a9063b4c33f95e1006da2eb12d3743689495c1f2023e407353c5eb3e4ca1c48cff81a10900d14820eb801af4f1a596c4b9ce9a531fcf8a54d9ffd724258b6eec20108df6fdfd76d4ae03ba7ea598dcb0e4a280849587286f4d7f256ce85e5eb5679b1dacc1f9095649b72e5fa072aeb00379", ++ "010001", ++ "2517eacb3afef4bffae60398df9957a5d2a154a83368d8e15842b2f59ee09f79197bd2ef1e9addaf8786f6b4127447405e3042b21f2f50b7aa73771680c3bbcb6c225a5d5ff6b56c471c1882a0a33b0af165a3ed6c249dc7783e6bc758ac37e6572d33fe325078ed952650f2eb9604902ef99a511a1119d13c4fc9a43a175dcdfbfb1a1400fe17093b69cd3cdb895f65432ea2195f90511c7336b58a685dacff2daf4c5e92e565b1665ae60e512baa9965b808d5ff119ceb7cd692cbf920067afacd809f66be706da26810ac790db156c948e6fe581bc9849157f4da493f3a64b0c6e119e031b107f8436ce29160b458b8f9f1095fdeb19263384ff5387557bc4f10b4034de841703bad2c1e769c23853eb630a36d1061dd46e2a6bbaf743a97f0b32c36f50c1a3722def3a394d91c2e078bf09d795ecde5e56b8202f974026f75fc56e9a0dd6a88f2e7cb78ef1298cc6c65207ca45bd37188807b4fcdb1e60dd8e5b85648fb7efa8b6fdd448f39741a8d9809fe163af3de45bac24a5a841c81", ++ { ++ { ++ "1. a random invalid ciphertext that generates an empty synthethic one", ++ NULL, ++ "", ++ "5e956cd9652f4a2ece902931013e09662b6a9257ad1e987fb75f73a0606df2a4b04789770820c2e02322c4e826f767bd895734a01e20609c3be4517a7a2a589ea1cdc137beb73eb38dac781b52e863de9620f79f9b90fd5b953651fcbfef4a9f1cc07421d511a87dd6942caab6a5a0f4df473e62defb529a7de1509ab99c596e1dff1320402298d8be73a896cc86c38ae3f2f576e9ea70cc28ad575cb0f854f0be43186baa9c18e29c47c6ca77135db79c811231b7c1730955887d321fdc06568382b86643cf089b10e35ab23e827d2e5aa7b4e99ff2e914f302351819eb4d1693243b35f8bf1d42d08f8ec4acafa35f747a4a975a28643ec630d8e4fa5be59d81995660a14bb64c1fea5146d6b11f92da6a3956dd5cb5e0d747cf2ea23f81617769185336263d46ef4c144b754de62a6337342d6c85a95f19f015724546ee3fc4823eca603dbc1dc01c2d5ed50bd72d8e96df2dc048edde0081284068283fc5e73a6139851abf2f29977d0b3d160c883a42a37efba1be05c1a0b1741d7ddf59", ++ "" ++ },{ ++ "2. a random invalid that has PRF output with a length one byte too long", ++ NULL, ++ "", ++ "7db0390d75fcf9d4c59cf27b264190d856da9abd11e92334d0e5f71005cfed865a711dfa28b791188374b61916dbc11339bf14b06f5f3f68c206c5607380e13da3129bfb744157e1527dd6fdf6651248b028a496ae1b97702d44706043cdaa7a59c0f41367303f21f268968bf3bd2904db3ae5239b55f8b438d93d7db9d1666c071c0857e2ec37757463769c54e51f052b2a71b04c2869e9e7049a1037b8429206c99726f07289bac18363e7eb2a5b417f47c37a55090cda676517b3549c873f2fe95da9681752ec9864b069089a2ed2f340c8b04ee00079055a817a3355b46ac7dc00d17f4504ccfbcfcadb0c04cb6b22069e179385ae1eafabad5521bac2b8a8ee1dfff59a22eb3fdacfc87175d10d7894cfd869d056057dd9944b869c1784fcc27f731bc46171d39570fbffbadf082d33f6352ecf44aca8d9478e53f5a5b7c852b401e8f5f74da49da91e65bdc97765a9523b7a0885a6f8afe5759d58009fbfa837472a968e6ae92026a5e0202a395483095302d6c3985b5f5831c521a271", ++ "56a3bea054e01338be9b7d7957539c" ++ },{ ++ "3. a random invalid that generates a synthethic of maximum size", ++ NULL, ++ "", ++ "1715065322522dff85049800f6a29ab5f98c465020467414b2a44127fe9446da47fa18047900f99afe67c2df6f50160bb8e90bff296610fde632b3859d4d0d2e644f23835028c46cca01b84b88231d7e03154edec6627bcba23de76740d839851fa12d74c8f92e540c73fe837b91b7d699b311997d5f0f7864c486d499c3a79c111faaacbe4799597a25066c6200215c3d158f3817c1aa57f18bdaad0be1658da9da93f5cc6c3c4dd72788af57adbb6a0c26f42d32d95b8a4f95e8c6feb2f8a5d53b19a50a0b7cbc25e055ad03e5ace8f3f7db13e57759f67b65d143f08cca15992c6b2aae643390483de111c2988d4e76b42596266005103c8de6044fb7398eb3c28a864fa672de5fd8774510ff45e05969a11a4c7d3f343e331190d2dcf24fb9154ba904dc94af98afc5774a9617d0418fe6d13f8245c7d7626c176138dd698a23547c25f27c2b98ea4d8a45c7842b81888e4cc14e5b72e9cf91f56956c93dbf2e5f44a8282a7813157fc481ff1371a0f66b31797e81ebdb09a673d4db96d6", ++ "7b036fcd6243900e4236c894e2462c17738acc87e01a76f4d95cb9a328d9acde81650283b8e8f60a217e3bdee835c7b222ad4c85d0acdb9a309bd2a754609a65dec50f3aa04c6d5891034566b9563d42668ede1f8992b17753a2132e28970584e255efc8b45a41c5dbd7567f014acec5fe6fdb6d484790360a913ebb9defcd74ff377f2a8ba46d2ed85f733c9a3da08eb57ecedfafda806778f03c66b2c5d2874cec1c291b2d49eb194c7b5d0dd2908ae90f4843268a2c45563092ade08acb6ab481a08176102fc803fbb2f8ad11b0e1531bd37df543498daf180b12017f4d4d426ca29b4161075534bfb914968088a9d13785d0adc0e2580d3548494b2a9e91605f2b27e6cc701c796f0de7c6f471f6ab6cb9272a1ed637ca32a60d117505d82af3c1336104afb537d01a8f70b510e1eebf4869cb976c419473795a66c7f5e6e20a8094b1bb603a74330c537c5c0698c31538bd2e138c1275a1bdf24c5fa8ab3b7b526324e7918a382d1363b3d463764222150e04" ++ },{ ++ "4. a positive test case that decrypts to 9 byte long value", ++ NULL, ++ "", ++ "6c60845a854b4571f678941ae35a2ac03f67c21e21146f9db1f2306be9f136453b86ad55647d4f7b5c9e62197aaff0c0e40a3b54c4cde14e774b1c5959b6c2a2302896ffae1f73b00b862a20ff4304fe06cea7ff30ecb3773ca9af27a0b54547350d7c07dfb0a39629c7e71e83fc5af9b2adbaf898e037f1de696a3f328cf45af7ec9aff7173854087fb8fbf34be981efbd8493f9438d1b2ba2a86af082662aa46ae9adfbec51e5f3d9550a4dd1dcb7c8969c9587a6edc82a8cabbc785c40d9fbd12064559fb769450ac3e47e87bc046148130d7eaa843e4b3ccef3675d0630500803cb7ffee3882378c1a404e850c3e20707bb745e42b13c18786c4976076ed9fa8fd0ff15e571bef02cbbe2f90c908ac3734a433b73e778d4d17fcc28f49185ebc6e8536a06d293202d94496453bfdf1c2c7833a3f99fa38ca8a81f42eaa529d603b890308a319c0ab63a35ff8ebac965f6278f5a7e5d622be5d5fe55f0ca3ec993d55430d2bf59c5d3e860e90c16d91a04596f6fdf60d89ed95d88c036dde", ++ "666f7274792074776f" ++ },{ ++ "5. a positive test case with null padded ciphertext", ++ NULL, ++ "", ++ "00f4d565a3286784dbb85327db8807ae557ead229f92aba945cecda5225f606a7d6130edeeb6f26724d1eff1110f9eb18dc3248140ee3837e6688391e78796c526791384f045e21b6b853fb6342a11f309eb77962f37ce23925af600847fbd30e6e07e57de50b606e6b7f288cc777c1a6834f27e6edace508452128916eef7788c8bb227e3548c6a761cc4e9dd1a3584176dc053ba3500adb1d5e1611291654f12dfc5722832f635db3002d73f9defc310ace62c63868d341619c7ee15b20243b3371e05078e11219770c701d9f341af35df1bc729de294825ff2e416aa11526612852777eb131f9c45151eb144980d70608d2fc4043477368369aa0fe487a48bd57e66b00c3c58f941549f5ec050fca64449debe7a0c4ac51e55cb71620a70312aa4bd85fac1410c9c7f9d6ec610b7d11bf8faeffa20255d1a1bead9297d0aa8765cd2805847d639bc439f4a6c896e2008f746f9590ff4596de5ddde000ed666c452c978043ff4298461eb5a26d5e63d821438627f91201924bf7f2aeee1727", ++ "666f7274792074776f" ++ },{ ++ "6. a positive test case with double null padded ciphertext", ++ NULL, ++ "", ++ "00001ec97ac981dfd9dcc7a7389fdfa9d361141dac80c23a060410d472c16094e6cdffc0c3684d84aa402d7051dfccb2f6da33f66985d2a259f5b7fbf39ac537e95c5b7050eb18844a0513abef812cc8e74a3c5240009e6e805dcadf532bc1a2702d5acc9e585fad5b89d461fcc1397351cdce35171523758b171dc041f412e42966de7f94856477356d06f2a6b40e3ff0547562a4d91bbf1338e9e049facbee8b20171164505468cd308997447d3dc4b0acb49e7d368fedd8c734251f30a83491d2506f3f87318cc118823244a393dc7c5c739a2733d93e1b13db6840a9429947357f47b23fbe39b7d2d61e5ee26f9946c4632f6c4699e452f412a26641d4751135400713cd56ec66f0370423d55d2af70f5e7ad0adea8e4a0d904a01e4ac272eba4af1a029dd53eb71f115bf31f7a6c8b19a6523adeecc0d4c3c107575e38572a8f8474ccad163e46e2e8b08111132aa97a16fb588c9b7e37b3b3d7490381f3c55d1a9869a0fd42cd86fed59ecec78cb6b2dfd06a497f5afe3419691314ba0", ++ "666f7274792074776f" ++ },{ ++ "7. a positive test case with double null truncated ciphertext", ++ NULL, ++ "", ++ "1ec97ac981dfd9dcc7a7389fdfa9d361141dac80c23a060410d472c16094e6cdffc0c3684d84aa402d7051dfccb2f6da33f66985d2a259f5b7fbf39ac537e95c5b7050eb18844a0513abef812cc8e74a3c5240009e6e805dcadf532bc1a2702d5acc9e585fad5b89d461fcc1397351cdce35171523758b171dc041f412e42966de7f94856477356d06f2a6b40e3ff0547562a4d91bbf1338e9e049facbee8b20171164505468cd308997447d3dc4b0acb49e7d368fedd8c734251f30a83491d2506f3f87318cc118823244a393dc7c5c739a2733d93e1b13db6840a9429947357f47b23fbe39b7d2d61e5ee26f9946c4632f6c4699e452f412a26641d4751135400713cd56ec66f0370423d55d2af70f5e7ad0adea8e4a0d904a01e4ac272eba4af1a029dd53eb71f115bf31f7a6c8b19a6523adeecc0d4c3c107575e38572a8f8474ccad163e46e2e8b08111132aa97a16fb588c9b7e37b3b3d7490381f3c55d1a9869a0fd42cd86fed59ecec78cb6b2dfd06a497f5afe3419691314ba0", ++ "666f7274792074776f" ++ },{ ++ "8. a random negative test case that generates a 9 byte long message", ++ NULL, ++ "", ++ "5c8555f5cef627c15d37f85c7f5fd6e499264ea4b8e3f9112023aeb722eb38d8eac2be3751fd5a3785ab7f2d59fa3728e5be8c3de78a67464e30b21ee23b5484bb3cd06d0e1c6ad25649c8518165653eb80488bfb491b20c04897a6772f69292222fc5ef50b5cf9efc6d60426a449b6c489569d48c83488df629d695653d409ce49a795447fcec2c58a1a672e4a391401d428baaf781516e11e323d302fcf20f6eab2b2dbe53a48c987e407c4d7e1cb41131329138313d330204173a4f3ff06c6fadf970f0ed1005d0b27e35c3d11693e0429e272d583e57b2c58d24315c397856b34485dcb077665592b747f889d34febf2be8fce66c265fd9fc3575a6286a5ce88b4b413a08efc57a07a8f57a999605a837b0542695c0d189e678b53662ecf7c3d37d9dbeea585eebfaf79141118e06762c2381fe27ca6288edddc19fd67cd64f16b46e06d8a59ac530f22cd83cc0bc4e37feb52015cbb2283043ccf5e78a4eb7146827d7a466b66c8a4a4826c1bad68123a7f2d00fc1736525ff90c058f56", ++ "257906ca6de8307728" ++ },{ ++ "9. a random negative test case that generates a 9 byte long message based on second to last value from PRF", ++ NULL, ++ "", ++ "758c215aa6acd61248062b88284bf43c13cb3b3d02410be4238607442f1c0216706e21a03a2c10eb624a63322d854da195c017b76fea83e274fa371834dcd2f3b7accf433fc212ad76c0bac366e1ed32e25b279f94129be7c64d6e162adc08ccebc0cfe8e926f01c33ab9c065f0e0ac83ae5137a4cb66702615ad68a35707d8676d2740d7c1a954680c83980e19778ed11eed3a7c2dbdfc461a9bbef671c1bc00c882d361d29d5f80c42bdf5efec886c34138f83369c6933b2ac4e93e764265351b4a0083f040e14f511f09b22f96566138864e4e6ff24da4810095da98e0585410951538ced2f757a277ff8e17172f06572c9024eeae503f176fd46eb6c5cd9ba07af11cde31dccac12eb3a4249a7bfd3b19797ad1656984bfcbf6f74e8f99d8f1ac420811f3d166d87f935ef15ae858cf9e72c8e2b547bf16c3fb09a8c9bf88fd2e5d38bf24ed610896131a84df76b9f920fe76d71fff938e9199f3b8cd0c11fd0201f9139d7673a871a9e7d4adc3bbe360c8813617cd60a90128fbe34c9d5", ++ "043383c929060374ed" ++ },{ ++ "10. a random negative test that generates message based on 3rd last value from PRF", ++ NULL, ++ "", ++ "7b22d5e62d287968c6622171a1f75db4b0fd15cdf3134a1895d235d56f8d8fe619f2bf4868174a91d7601a82975d2255190d28b869141d7c395f0b8c4e2be2b2c1b4ffc12ce749a6f6803d4cfe7fba0a8d6949c04151f981c0d84592aa2ff25d1bd3ce5d10cb03daca6b496c6ad40d30bfa8acdfd02cdb9326c4bdd93b949c9dc46caa8f0e5f429785bce64136a429a3695ee674b647452bea1b0c6de9c5f1e8760d5ef6d5a9cfff40457b023d3c233c1dcb323e7808103e73963b2eafc928c9eeb0ee3294955415c1ddd9a1bb7e138fecd79a3cb89c57bd2305524624814aaf0fd1acbf379f7f5b39421f12f115ba488d380586095bb53f174fae424fa4c8e3b299709cd344b9f949b1ab57f1c645d7ed3c8f81d5594197355029fee8960970ff59710dc0e5eb50ea6f4c3938e3f89ed7933023a2c2ddffaba07be147f686828bd7d520f300507ed6e71bdaee05570b27bc92741108ac2eb433f028e138dd6d63067bc206ea2d826a7f41c0d613daed020f0f30f4e272e9618e0a8c39018a83", ++ "70263fa6050534b9e0" ++ },{ ++ "11. an otherwise valid plaintext, but with wrong first byte (0x01 instead of 0x00)", ++ NULL, ++ "", ++ "6db80adb5ff0a768caf1378ecc382a694e7d1bde2eff4ba12c48aaf794ded7a994a5b2b57acec20dbec4ae385c9dd531945c0f197a5496908725fc99d88601a17d3bb0b2d38d2c1c3100f39955a4cb3dbed5a38bf900f23d91e173640e4ec655c84fdfe71fcdb12a386108fcf718c9b7af37d39703e882436224c877a2235e8344fba6c951eb7e2a4d1d1de81fb463ac1b880f6cc0e59ade05c8ce35179ecd09546731fc07b141d3d6b342a97ae747e61a9130f72d37ac5a2c30215b6cbd66c7db893810df58b4c457b4b54f34428247d584e0fa71062446210db08254fb9ead1ba1a393c724bd291f0cf1a7143f32df849051dc896d7d176fef3b57ab6dffd626d0c3044e9edb2e3d012ace202d2581df01bec7e9aa0727a6650dd373d374f0bc0f4a611f8139dfe97d63e70c6188f4df5b672e47c51d8aa567097293fbff127c75ec690b43407578b73c85451710a0cece58fd497d7f7bd36a8a92783ef7dc6265dff52aac8b70340b996508d39217f2783ce6fc91a1cc94bb2ac487b84f62", ++ "6d8d3a094ff3afff4c" ++ },{ ++ "12. an otherwise valid plaintext, but with wrong second byte (0x01 instead of 0x02)", ++ NULL, ++ "", ++ "417328c034458563079a4024817d0150340c34e25ae16dcad690623f702e5c748a6ebb3419ff48f486f83ba9df35c05efbd7f40613f0fc996c53706c30df6bba6dcd4a40825f96133f3c21638a342bd4663dffbd0073980dac47f8c1dd8e97ce1412e4f91f2a8adb1ac2b1071066efe8d718bbb88ca4a59bd61500e826f2365255a409bece0f972df97c3a55e09289ef5fa815a2353ef393fd1aecfc888d611c16aec532e5148be15ef1bf2834b8f75bb26db08b66d2baad6464f8439d1986b533813321dbb180080910f233bcc4dd784fb21871aef41be08b7bfad4ecc3b68f228cb5317ac6ec1227bc7d0e452037ba918ee1da9fdb8393ae93b1e937a8d4691a17871d5092d2384b6190a53df888f65b951b05ed4ad57fe4b0c6a47b5b22f32a7f23c1a234c9feb5d8713d949686760680da4db454f4acad972470033472b9864d63e8d23eefc87ebcf464ecf33f67fbcdd48eab38c5292586b36aef5981ed2fa07b2f9e23fc57d9eb71bfff4111c857e9fff23ceb31e72592e70c874b4936", ++ "c6ae80ffa80bc184b0" ++ },{ ++ "13. an otherwise valid plaintext, but with zero byte in first byte of padding", ++ NULL, ++ "", ++ "8542c626fe533467acffcd4e617692244c9b5a3bf0a215c5d64891ced4bf4f9591b4b2aedff9843057986d81631b0acb3704ec2180e5696e8bd15b217a0ec36d2061b0e2182faa3d1c59bd3f9086a10077a3337a3f5da503ec3753535ffd25b837a12f2541afefd0cffb0224b8f874e4bed13949e105c075ed44e287c5ae03b155e06b90ed247d2c07f1ef3323e3508cce4e4074606c54172ad74d12f8c3a47f654ad671104bf7681e5b061862747d9afd37e07d8e0e2291e01f14a95a1bb4cbb47c304ef067595a3947ee2d722067e38a0f046f43ec29cac6a8801c6e3e9a2331b1d45a7aa2c6af3205be382dd026e389614ee095665a611ab2e8dced2ee1c9d08ac9de11aef5b3803fc9a9ce8231ec87b5fed386fb92ee3db995a89307bcba844bd0a691c29ae51216e949dfc813133cb06a07265fd807bcb3377f6adb0a481d9b7f442003115895939773e6b95371c4febef29edae946fa245e7c50729e2e558cfaad773d1fd5f67b457a6d9d17a847c6fcbdb103a86f35f228cefc06cea0", ++ "a8a9301daa01bb25c7" ++ },{ ++ "14. an otherwise valid plaintext, but with zero byte in eight byte of padding", ++ NULL, ++ "", ++ "449dfa237a70a99cb0351793ec8677882021c2aa743580bf6a0ea672055cffe8303ac42855b1d1f3373aae6af09cb9074180fc963e9d1478a4f98b3b4861d3e7f0aa8560cf603711f139db77667ca14ba3a1acdedfca9ef4603d6d7eb0645bfc805304f9ad9d77d34762ce5cd84bd3ec9d35c30e3be72a1e8d355d5674a141b5530659ad64ebb6082e6f73a80832ab6388912538914654d34602f4b3b1c78589b4a5d964b2efcca1dc7004c41f6cafcb5a7159a7fc7c0398604d0edbd4c8f4f04067da6a153a05e7cbeea13b5ee412400ef7d4f3106f4798da707ec37a11286df2b7a204856d5ff773613fd1e453a7114b78e347d3e8078e1cb3276b3562486ba630bf719697e0073a123c3e60ebb5c7a1ccff4279faffa2402bc1109f8d559d6766e73591943dfcf25ba10c3762f02af85187799b8b4b135c3990793a6fd32642f1557405ba55cc7cf7336a0e967073c5fa50743f9cc5e3017c172d9898d2af83345e71b3e0c22ab791eacb6484a32ec60ebc226ec9deaee91b1a0560c2b571", ++ "6c716fe01d44398018" ++ },{ ++ "15. an otherwise valid plaintext, but with null separator missing", ++ NULL, ++ "", ++ "a7a5c99e50da48769ecb779d9abe86ef9ec8c38c6f43f17c7f2d7af608a4a1bd6cf695b47e97c191c61fb5a27318d02f495a176b9fae5a55b5d3fabd1d8aae4957e3879cb0c60f037724e11be5f30f08fc51c033731f14b44b414d11278cd3dba7e1c8bfe208d2b2bb7ec36366dacb6c88b24cd79ab394adf19dbbc21dfa5788bacbadc6a62f79cf54fd8cf585c615b5c0eb94c35aa9de25321c8ffefb8916bbaa2697cb2dd82ee98939df9b6704cee77793edd2b4947d82e00e5749664970736c59a84197bd72b5c71e36aae29cd39af6ac73a368edbc1ca792e1309f442aafcd77c992c88f8e4863149f221695cb7b0236e75b2339a02c4ea114854372c306b9412d8eedb600a31532002f2cea07b4df963a093185e4607732e46d753b540974fb5a5c3f9432df22e85bb17611370966c5522fd23f2ad3484341ba7fd8885fc8e6d379a611d13a2aca784fba2073208faad2137bf1979a0fa146c1880d4337db3274269493bab44a1bcd0681f7227ffdf589c2e925ed9d36302509d1109ba4", ++ "aa2de6cde4e2442884" ++ },{ ++ NULL, ++ NULL, ++ NULL, ++ NULL, ++ NULL, ++ } ++ } + } + }; +Index: libgcrypt-1.11.1/tests/pkcs1v2.c +=================================================================== +--- libgcrypt-1.11.1.orig/tests/pkcs1v2.c ++++ libgcrypt-1.11.1/tests/pkcs1v2.c +@@ -82,7 +82,7 @@ data_from_hex (const char *string, size_ + + static int + extract_cmp_data (gcry_sexp_t sexp, const char *name, const char *expected, +- const char *description) ++ const char *description, int quiet) + { + gcry_sexp_t l1; + const void *a; +@@ -96,13 +96,15 @@ extract_cmp_data (gcry_sexp_t sexp, cons + b = data_from_hex (expected, &blen); + if (!a) + { +- info ("%s: parameter \"%s\" missing in key\n", description, name); ++ if (!quiet) ++ info ("%s: parameter \"%s\" missing in key\n", description, name); + rc = 1; + } + else if ( alen != blen || memcmp (a, b, alen) ) + { +- info ("%s: parameter \"%s\" does not match expected value\n", +- description, name); ++ if (!quiet) ++ info ("%s: parameter \"%s\" does not match expected value\n", ++ description, name); + rc = 1; + } + gcry_free (b); +@@ -192,7 +194,7 @@ check_oaep (void) + else + { + if (extract_cmp_data (ciph, "a", tbl[tno].m[mno].encr, +- tbl[tno].m[mno].desc)) ++ tbl[tno].m[mno].desc, 0)) + { + show_sexp ("encrypt result:\n", ciph); + fail ("mismatch in gcry_pk_encrypt\n"); +@@ -223,7 +225,7 @@ check_oaep (void) + else + { + if (extract_cmp_data (plain, "value", tbl[tno].m[mno].mesg, +- tbl[tno].m[mno].desc)) ++ tbl[tno].m[mno].desc, 0)) + { + show_sexp ("decrypt result:\n", plain); + fail ("mismatch in gcry_pk_decrypt\n"); +@@ -326,7 +328,7 @@ check_pss (void) + else + { + if (extract_cmp_data (sig, "s", tbl[tno].m[mno].sign, +- tbl[tno].m[mno].desc)) ++ tbl[tno].m[mno].desc, 0)) + { + show_sexp ("sign result:\n", sig); + fail ("mismatch in gcry_pk_sign\n"); +@@ -428,45 +430,89 @@ check_v15crypt (void) + void *mesg, *seed, *encr; + size_t mesg_len, seed_len, encr_len; + gcry_sexp_t plain, ciph; +- ++ if (tbl[tno].m[mno].desc == NULL) ++ break; ++ + if (verbose) + info ("running test: %s\n", tbl[tno].m[mno].desc); + +- mesg = data_from_hex (tbl[tno].m[mno].mesg, &mesg_len); ++ if (tbl[tno].m[mno].mesg) ++ { ++ mesg = data_from_hex (tbl[tno].m[mno].mesg, &mesg_len); ++ seed = data_from_hex (tbl[tno].m[mno].seed, &seed_len); ++ ++ err = gcry_sexp_build (&plain, NULL, ++ "(data (flags pkcs1)" ++ "(value %b)(random-override %b))", ++ (int)mesg_len, mesg, ++ (int)seed_len, seed); ++ if (err) ++ die ("constructing plain data failed: %s\n", gpg_strerror (err)); ++ gcry_free (mesg); ++ gcry_free (seed); ++ ++ err = gcry_pk_encrypt (&ciph, plain, pub_key); ++ if (err) ++ { ++ show_sexp ("plain:\n", ciph); ++ fail ("gcry_pk_encrypt failed: %s\n", gpg_strerror (err)); ++ } ++ else ++ { ++ if (extract_cmp_data (ciph, "a", tbl[tno].m[mno].encr, ++ tbl[tno].m[mno].desc, 0)) ++ { ++ show_sexp ("encrypt result:\n", ciph); ++ fail ("mismatch in gcry_pk_encrypt\n"); ++ } ++ gcry_sexp_release (ciph); ++ ciph = NULL; ++ } ++ gcry_sexp_release (plain); ++ plain = NULL; ++ } ++ ++ /* Now test the decryption. */ ++ encr = data_from_hex (tbl[tno].m[mno].encr, &encr_len); + seed = data_from_hex (tbl[tno].m[mno].seed, &seed_len); + +- err = gcry_sexp_build (&plain, NULL, +- "(data (flags pkcs1)" +- "(value %b)(random-override %b))", +- (int)mesg_len, mesg, +- (int)seed_len, seed); ++#ifdef WITH_MARVIN_WORKAROUND ++ /* First try without implicit rejection -- this should fail for invalid inputs */ ++ err = gcry_sexp_build (&ciph, NULL, ++ "(enc-val (flags pkcs1 no-implicit-rejection)" ++ "(rsa (a %b)))", ++ (int)encr_len, encr); + if (err) +- die ("constructing plain data failed: %s\n", gpg_strerror (err)); +- gcry_free (mesg); +- gcry_free (seed); +- +- err = gcry_pk_encrypt (&ciph, plain, pub_key); ++ die ("constructing cipher data failed: %s\n", gpg_strerror (err)); ++ ++ err = gcry_pk_decrypt (&plain, ciph, sec_key); + if (err) + { +- show_sexp ("plain:\n", ciph); +- fail ("gcry_pk_encrypt failed: %s\n", gpg_strerror (err)); ++ /* If the message is not set, the padding is invalid and failure is expected */ ++ if (tbl[tno].m[mno].mesg != NULL) ++ { ++ show_sexp ("ciph:\n", ciph); ++ fail ("gcry_pk_decrypt failed: %s\n", gpg_strerror (err)); ++ } + } + else + { +- if (extract_cmp_data (ciph, "a", tbl[tno].m[mno].encr, +- tbl[tno].m[mno].desc)) +- { +- show_sexp ("encrypt result:\n", ciph); +- fail ("mismatch in gcry_pk_encrypt\n"); +- } +- gcry_sexp_release (ciph); ++ /* If the message is not set, it is in the synthetic field */ ++ const char *msg = tbl[tno].m[mno].mesg; ++ if (msg == NULL) ++ msg = tbl[tno].m[mno].synt; ++ if (extract_cmp_data (plain, "value", msg, ++ tbl[tno].m[mno].desc, 0)) ++ { ++ show_sexp ("decrypt result:\n", plain); ++ fail ("mismatch in gcry_pk_decrypt.\n"); ++ } ++ gcry_sexp_release (plain); + ciph = NULL; + } +- gcry_sexp_release (plain); +- plain = NULL; +- +- /* Now test the decryption. */ +- encr = data_from_hex (tbl[tno].m[mno].encr, &encr_len); ++ gcry_sexp_release (ciph); ++ ciph = NULL; ++#endif /* WITH_MARVIN_WORKAROUND */ + + err = gcry_sexp_build (&ciph, NULL, + "(enc-val (flags pkcs1)" +@@ -480,19 +526,23 @@ check_v15crypt (void) + if (err) + { + show_sexp ("ciph:\n", ciph); +- fail ("gcry_pk_decrypt failed: %s\n", gpg_strerror (err)); ++ fail ("gcry_pk_decrypt w RSA failed: %s\n", gpg_strerror (err)); + } + else + { +- if (extract_cmp_data (plain, "value", tbl[tno].m[mno].mesg, +- tbl[tno].m[mno].desc)) ++ /* If the message is not set, expect the synthetic message here */ ++ const char *msg = tbl[tno].m[mno].mesg; ++ if (msg == NULL) ++ msg = tbl[tno].m[mno].synt; ++ if (extract_cmp_data (plain, "value", msg, ++ tbl[tno].m[mno].desc, 0)) + { + show_sexp ("decrypt result:\n", plain); +- fail ("mismatch in gcry_pk_decrypt\n"); ++ fail ("mismatch in gcry_pk_decrypt. Expected %s\n", msg); + } +- gcry_sexp_release (plain); +- plain = NULL; + } ++ gcry_sexp_release (plain); ++ plain = NULL; + gcry_sexp_release (ciph); + ciph = NULL; + } +@@ -584,7 +634,7 @@ check_v15sign (void) + else + { + if (extract_cmp_data (sig, "s", tbl[tno].m[mno].sign, +- tbl[tno].m[mno].desc)) ++ tbl[tno].m[mno].desc, 0)) + { + show_sexp ("sign result:\n", sig); + fail ("mismatch in gcry_pk_sign\n"); diff --git a/libgcrypt-Chacha20-poly1305-Optimized-chacha20-poly1305.patch b/libgcrypt-Chacha20-poly1305-Optimized-chacha20-poly1305.patch new file mode 100644 index 0000000..5877fee --- /dev/null +++ b/libgcrypt-Chacha20-poly1305-Optimized-chacha20-poly1305.patch @@ -0,0 +1,1993 @@ +commit 88fe7ac33eb4cb4dff76a5cc7fca50da5fb0ee3a +Author: Danny Tsen +Date: Sun Jun 12 21:30:19 2022 +0300 + + Chacha20 poly1305 Optimized chacha20 poly1305 for P10 operation + + * configure.ac: Added chacha20 and poly1305 assembly implementations. + * cipher/chacha20-p10le-8x.s: (New) - support 8 blocks (512 bytes) + unrolling. + * cipher/poly1305-p10le.s: (New) - support 4 blocks (128 bytes) + unrolling. + * cipher/Makefile.am: Added new chacha20 and poly1305 files. + * cipher/chacha20.c: Added PPC p10 le support for 8x chacha20. + * cipher/poly1305.c: Added PPC p10 le support for 4x poly1305. + * cipher/poly1305-internal.h: Added PPC p10 le support for poly1305. + --- + + GnuPG-bug-id: 6006 + Signed-off-by: Danny Tsen + [jk: cosmetic changes to C code] + [jk: fix building on ppc64be] + Signed-off-by: Jussi Kivilinna + +Index: libgcrypt-1.10.2/cipher/Makefile.am +=================================================================== +--- libgcrypt-1.10.2.orig/cipher/Makefile.am ++++ libgcrypt-1.10.2/cipher/Makefile.am +@@ -83,6 +83,7 @@ EXTRA_libcipher_la_SOURCES = \ + chacha20.c chacha20-amd64-ssse3.S chacha20-amd64-avx2.S \ + chacha20-armv7-neon.S chacha20-aarch64.S \ + chacha20-ppc.c chacha20-s390x.S \ ++ chacha20-p10le-8x.s \ + cipher-gcm-ppc.c cipher-gcm-intel-pclmul.c cipher-gcm-armv7-neon.S \ + cipher-gcm-armv8-aarch32-ce.S cipher-gcm-armv8-aarch64-ce.S \ + crc.c crc-intel-pclmul.c crc-armv8-ce.c \ +@@ -99,6 +100,7 @@ EXTRA_libcipher_la_SOURCES = \ + md4.c \ + md5.c \ + poly1305-s390x.S \ ++ poly1305-p10le.s \ + rijndael.c rijndael-internal.h rijndael-tables.h \ + rijndael-aesni.c rijndael-padlock.c \ + rijndael-amd64.S rijndael-arm.S \ +Index: libgcrypt-1.10.2/cipher/chacha20-p10le-8x.s +=================================================================== +--- /dev/null ++++ libgcrypt-1.10.2/cipher/chacha20-p10le-8x.s +@@ -0,0 +1,864 @@ ++# Copyright 2021- IBM Inc. All rights reserved ++# ++# This file is part of Libgcrypt. ++# ++# Libgcrypt is free software; you can redistribute it and/or modify ++# it under the terms of the GNU Lesser General Public License as ++# published by the Free Software Foundation; either version 2.1 of ++# the License, or (at your option) any later version. ++# ++# Libgcrypt 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 Lesser General Public License for more details. ++# ++# You should have received a copy of the GNU Lesser General Public ++# License along with this program; if not, see . ++# ++#=================================================================================== ++# Written by Danny Tsen ++# ++# This function handles multiple 64-byte block data length ++# and the length should be more than 512 bytes. ++# ++# unsigned int _gcry_chacha20_p10le_8x(u32 *state, byte *dst, const byte *src, size_t len); ++# ++# r1 - top of the stack ++# r3 to r10 input parameters ++# r3 - out ++# r4 - inp ++# r5 - len ++# r6 - key[8] ++# r7 - counter[4] ++# ++# do rounds, 8 quarter rounds ++# 1. a += b; d ^= a; d <<<= 16; ++# 2. c += d; b ^= c; b <<<= 12; ++# 3. a += b; d ^= a; d <<<= 8; ++# 4. c += d; b ^= c; b <<<= 7 ++# ++# row1 = (row1 + row2), row4 = row1 xor row4, row4 rotate each word by 16 ++# row3 = (row3 + row4), row2 = row3 xor row2, row2 rotate each word by 12 ++# row1 = (row1 + row2), row4 = row1 xor row4, row4 rotate each word by 8 ++# row3 = (row3 + row4), row2 = row3 xor row2, row2 rotate each word by 7 ++# ++# 4 blocks (a b c d) ++# ++# a0 b0 c0 d0 ++# a1 b1 c1 d1 ++# ... ++# a4 b4 c4 d4 ++# ... ++# a8 b8 c8 d8 ++# ... ++# a12 b12 c12 d12 ++# a13 ... ++# a14 ... ++# a15 b15 c15 d15 ++# ++# Column round (v0, v4, v8, v12, v1, v5, v9, v13, v2, v6, v10, v14, v3, v7, v11, v15) ++# Diagnal round (v0, v5, v10, v15, v1, v6, v11, v12, v2, v7, v8, v13, v3, v4, v9, v14) ++# ++.text ++ ++.macro QT_loop_8x ++ # QR(v0, v4, v8, v12, v1, v5, v9, v13, v2, v6, v10, v14, v3, v7, v11, v15) ++ xxlor 0, 32+25, 32+25 ++ xxlor 32+25, 20, 20 ++ vadduwm 0, 0, 4 ++ vadduwm 1, 1, 5 ++ vadduwm 2, 2, 6 ++ vadduwm 3, 3, 7 ++ vadduwm 16, 16, 20 ++ vadduwm 17, 17, 21 ++ vadduwm 18, 18, 22 ++ vadduwm 19, 19, 23 ++ ++ vpermxor 12, 12, 0, 25 ++ vpermxor 13, 13, 1, 25 ++ vpermxor 14, 14, 2, 25 ++ vpermxor 15, 15, 3, 25 ++ vpermxor 28, 28, 16, 25 ++ vpermxor 29, 29, 17, 25 ++ vpermxor 30, 30, 18, 25 ++ vpermxor 31, 31, 19, 25 ++ xxlor 32+25, 0, 0 ++ vadduwm 8, 8, 12 ++ vadduwm 9, 9, 13 ++ vadduwm 10, 10, 14 ++ vadduwm 11, 11, 15 ++ vadduwm 24, 24, 28 ++ vadduwm 25, 25, 29 ++ vadduwm 26, 26, 30 ++ vadduwm 27, 27, 31 ++ vxor 4, 4, 8 ++ vxor 5, 5, 9 ++ vxor 6, 6, 10 ++ vxor 7, 7, 11 ++ vxor 20, 20, 24 ++ vxor 21, 21, 25 ++ vxor 22, 22, 26 ++ vxor 23, 23, 27 ++ ++ xxlor 0, 32+25, 32+25 ++ xxlor 32+25, 21, 21 ++ vrlw 4, 4, 25 # ++ vrlw 5, 5, 25 ++ vrlw 6, 6, 25 ++ vrlw 7, 7, 25 ++ vrlw 20, 20, 25 # ++ vrlw 21, 21, 25 ++ vrlw 22, 22, 25 ++ vrlw 23, 23, 25 ++ xxlor 32+25, 0, 0 ++ vadduwm 0, 0, 4 ++ vadduwm 1, 1, 5 ++ vadduwm 2, 2, 6 ++ vadduwm 3, 3, 7 ++ vadduwm 16, 16, 20 ++ vadduwm 17, 17, 21 ++ vadduwm 18, 18, 22 ++ vadduwm 19, 19, 23 ++ ++ xxlor 0, 32+25, 32+25 ++ xxlor 32+25, 22, 22 ++ vpermxor 12, 12, 0, 25 ++ vpermxor 13, 13, 1, 25 ++ vpermxor 14, 14, 2, 25 ++ vpermxor 15, 15, 3, 25 ++ vpermxor 28, 28, 16, 25 ++ vpermxor 29, 29, 17, 25 ++ vpermxor 30, 30, 18, 25 ++ vpermxor 31, 31, 19, 25 ++ xxlor 32+25, 0, 0 ++ vadduwm 8, 8, 12 ++ vadduwm 9, 9, 13 ++ vadduwm 10, 10, 14 ++ vadduwm 11, 11, 15 ++ vadduwm 24, 24, 28 ++ vadduwm 25, 25, 29 ++ vadduwm 26, 26, 30 ++ vadduwm 27, 27, 31 ++ xxlor 0, 32+28, 32+28 ++ xxlor 32+28, 23, 23 ++ vxor 4, 4, 8 ++ vxor 5, 5, 9 ++ vxor 6, 6, 10 ++ vxor 7, 7, 11 ++ vxor 20, 20, 24 ++ vxor 21, 21, 25 ++ vxor 22, 22, 26 ++ vxor 23, 23, 27 ++ vrlw 4, 4, 28 # ++ vrlw 5, 5, 28 ++ vrlw 6, 6, 28 ++ vrlw 7, 7, 28 ++ vrlw 20, 20, 28 # ++ vrlw 21, 21, 28 ++ vrlw 22, 22, 28 ++ vrlw 23, 23, 28 ++ xxlor 32+28, 0, 0 ++ ++ # QR(v0, v5, v10, v15, v1, v6, v11, v12, v2, v7, v8, v13, v3, v4, v9, v14) ++ xxlor 0, 32+25, 32+25 ++ xxlor 32+25, 20, 20 ++ vadduwm 0, 0, 5 ++ vadduwm 1, 1, 6 ++ vadduwm 2, 2, 7 ++ vadduwm 3, 3, 4 ++ vadduwm 16, 16, 21 ++ vadduwm 17, 17, 22 ++ vadduwm 18, 18, 23 ++ vadduwm 19, 19, 20 ++ ++ vpermxor 15, 15, 0, 25 ++ vpermxor 12, 12, 1, 25 ++ vpermxor 13, 13, 2, 25 ++ vpermxor 14, 14, 3, 25 ++ vpermxor 31, 31, 16, 25 ++ vpermxor 28, 28, 17, 25 ++ vpermxor 29, 29, 18, 25 ++ vpermxor 30, 30, 19, 25 ++ ++ xxlor 32+25, 0, 0 ++ vadduwm 10, 10, 15 ++ vadduwm 11, 11, 12 ++ vadduwm 8, 8, 13 ++ vadduwm 9, 9, 14 ++ vadduwm 26, 26, 31 ++ vadduwm 27, 27, 28 ++ vadduwm 24, 24, 29 ++ vadduwm 25, 25, 30 ++ vxor 5, 5, 10 ++ vxor 6, 6, 11 ++ vxor 7, 7, 8 ++ vxor 4, 4, 9 ++ vxor 21, 21, 26 ++ vxor 22, 22, 27 ++ vxor 23, 23, 24 ++ vxor 20, 20, 25 ++ ++ xxlor 0, 32+25, 32+25 ++ xxlor 32+25, 21, 21 ++ vrlw 5, 5, 25 ++ vrlw 6, 6, 25 ++ vrlw 7, 7, 25 ++ vrlw 4, 4, 25 ++ vrlw 21, 21, 25 ++ vrlw 22, 22, 25 ++ vrlw 23, 23, 25 ++ vrlw 20, 20, 25 ++ xxlor 32+25, 0, 0 ++ ++ vadduwm 0, 0, 5 ++ vadduwm 1, 1, 6 ++ vadduwm 2, 2, 7 ++ vadduwm 3, 3, 4 ++ vadduwm 16, 16, 21 ++ vadduwm 17, 17, 22 ++ vadduwm 18, 18, 23 ++ vadduwm 19, 19, 20 ++ ++ xxlor 0, 32+25, 32+25 ++ xxlor 32+25, 22, 22 ++ vpermxor 15, 15, 0, 25 ++ vpermxor 12, 12, 1, 25 ++ vpermxor 13, 13, 2, 25 ++ vpermxor 14, 14, 3, 25 ++ vpermxor 31, 31, 16, 25 ++ vpermxor 28, 28, 17, 25 ++ vpermxor 29, 29, 18, 25 ++ vpermxor 30, 30, 19, 25 ++ xxlor 32+25, 0, 0 ++ ++ vadduwm 10, 10, 15 ++ vadduwm 11, 11, 12 ++ vadduwm 8, 8, 13 ++ vadduwm 9, 9, 14 ++ vadduwm 26, 26, 31 ++ vadduwm 27, 27, 28 ++ vadduwm 24, 24, 29 ++ vadduwm 25, 25, 30 ++ ++ xxlor 0, 32+28, 32+28 ++ xxlor 32+28, 23, 23 ++ vxor 5, 5, 10 ++ vxor 6, 6, 11 ++ vxor 7, 7, 8 ++ vxor 4, 4, 9 ++ vxor 21, 21, 26 ++ vxor 22, 22, 27 ++ vxor 23, 23, 24 ++ vxor 20, 20, 25 ++ vrlw 5, 5, 28 ++ vrlw 6, 6, 28 ++ vrlw 7, 7, 28 ++ vrlw 4, 4, 28 ++ vrlw 21, 21, 28 ++ vrlw 22, 22, 28 ++ vrlw 23, 23, 28 ++ vrlw 20, 20, 28 ++ xxlor 32+28, 0, 0 ++.endm ++ ++.macro QT_loop_4x ++ # QR(v0, v4, v8, v12, v1, v5, v9, v13, v2, v6, v10, v14, v3, v7, v11, v15) ++ vadduwm 0, 0, 4 ++ vadduwm 1, 1, 5 ++ vadduwm 2, 2, 6 ++ vadduwm 3, 3, 7 ++ vpermxor 12, 12, 0, 20 ++ vpermxor 13, 13, 1, 20 ++ vpermxor 14, 14, 2, 20 ++ vpermxor 15, 15, 3, 20 ++ vadduwm 8, 8, 12 ++ vadduwm 9, 9, 13 ++ vadduwm 10, 10, 14 ++ vadduwm 11, 11, 15 ++ vxor 4, 4, 8 ++ vxor 5, 5, 9 ++ vxor 6, 6, 10 ++ vxor 7, 7, 11 ++ vrlw 4, 4, 21 ++ vrlw 5, 5, 21 ++ vrlw 6, 6, 21 ++ vrlw 7, 7, 21 ++ vadduwm 0, 0, 4 ++ vadduwm 1, 1, 5 ++ vadduwm 2, 2, 6 ++ vadduwm 3, 3, 7 ++ vpermxor 12, 12, 0, 22 ++ vpermxor 13, 13, 1, 22 ++ vpermxor 14, 14, 2, 22 ++ vpermxor 15, 15, 3, 22 ++ vadduwm 8, 8, 12 ++ vadduwm 9, 9, 13 ++ vadduwm 10, 10, 14 ++ vadduwm 11, 11, 15 ++ vxor 4, 4, 8 ++ vxor 5, 5, 9 ++ vxor 6, 6, 10 ++ vxor 7, 7, 11 ++ vrlw 4, 4, 23 ++ vrlw 5, 5, 23 ++ vrlw 6, 6, 23 ++ vrlw 7, 7, 23 ++ ++ # QR(v0, v5, v10, v15, v1, v6, v11, v12, v2, v7, v8, v13, v3, v4, v9, v14) ++ vadduwm 0, 0, 5 ++ vadduwm 1, 1, 6 ++ vadduwm 2, 2, 7 ++ vadduwm 3, 3, 4 ++ vpermxor 15, 15, 0, 20 ++ vpermxor 12, 12, 1, 20 ++ vpermxor 13, 13, 2, 20 ++ vpermxor 14, 14, 3, 20 ++ vadduwm 10, 10, 15 ++ vadduwm 11, 11, 12 ++ vadduwm 8, 8, 13 ++ vadduwm 9, 9, 14 ++ vxor 5, 5, 10 ++ vxor 6, 6, 11 ++ vxor 7, 7, 8 ++ vxor 4, 4, 9 ++ vrlw 5, 5, 21 ++ vrlw 6, 6, 21 ++ vrlw 7, 7, 21 ++ vrlw 4, 4, 21 ++ vadduwm 0, 0, 5 ++ vadduwm 1, 1, 6 ++ vadduwm 2, 2, 7 ++ vadduwm 3, 3, 4 ++ vpermxor 15, 15, 0, 22 ++ vpermxor 12, 12, 1, 22 ++ vpermxor 13, 13, 2, 22 ++ vpermxor 14, 14, 3, 22 ++ vadduwm 10, 10, 15 ++ vadduwm 11, 11, 12 ++ vadduwm 8, 8, 13 ++ vadduwm 9, 9, 14 ++ vxor 5, 5, 10 ++ vxor 6, 6, 11 ++ vxor 7, 7, 8 ++ vxor 4, 4, 9 ++ vrlw 5, 5, 23 ++ vrlw 6, 6, 23 ++ vrlw 7, 7, 23 ++ vrlw 4, 4, 23 ++.endm ++ ++# Transpose ++.macro TP_4x a0 a1 a2 a3 ++ xxmrghw 10, 32+\a0, 32+\a1 # a0, a1, b0, b1 ++ xxmrghw 11, 32+\a2, 32+\a3 # a2, a3, b2, b3 ++ xxmrglw 12, 32+\a0, 32+\a1 # c0, c1, d0, d1 ++ xxmrglw 13, 32+\a2, 32+\a3 # c2, c3, d2, d3 ++ xxpermdi 32+\a0, 10, 11, 0 # a0, a1, a2, a3 ++ xxpermdi 32+\a1, 10, 11, 3 # b0, b1, b2, b3 ++ xxpermdi 32+\a2, 12, 13, 0 # c0, c1, c2, c3 ++ xxpermdi 32+\a3, 12, 13, 3 # d0, d1, d2, d3 ++.endm ++ ++# key stream = working state + state ++.macro Add_state S ++ vadduwm \S+0, \S+0, 16-\S ++ vadduwm \S+4, \S+4, 17-\S ++ vadduwm \S+8, \S+8, 18-\S ++ vadduwm \S+12, \S+12, 19-\S ++ ++ vadduwm \S+1, \S+1, 16-\S ++ vadduwm \S+5, \S+5, 17-\S ++ vadduwm \S+9, \S+9, 18-\S ++ vadduwm \S+13, \S+13, 19-\S ++ ++ vadduwm \S+2, \S+2, 16-\S ++ vadduwm \S+6, \S+6, 17-\S ++ vadduwm \S+10, \S+10, 18-\S ++ vadduwm \S+14, \S+14, 19-\S ++ ++ vadduwm \S+3, \S+3, 16-\S ++ vadduwm \S+7, \S+7, 17-\S ++ vadduwm \S+11, \S+11, 18-\S ++ vadduwm \S+15, \S+15, 19-\S ++.endm ++ ++# ++# write 256 bytes ++# ++.macro Write_256 S ++ add 9, 14, 5 ++ add 16, 14, 4 ++ lxvw4x 0, 0, 9 ++ lxvw4x 1, 17, 9 ++ lxvw4x 2, 18, 9 ++ lxvw4x 3, 19, 9 ++ lxvw4x 4, 20, 9 ++ lxvw4x 5, 21, 9 ++ lxvw4x 6, 22, 9 ++ lxvw4x 7, 23, 9 ++ lxvw4x 8, 24, 9 ++ lxvw4x 9, 25, 9 ++ lxvw4x 10, 26, 9 ++ lxvw4x 11, 27, 9 ++ lxvw4x 12, 28, 9 ++ lxvw4x 13, 29, 9 ++ lxvw4x 14, 30, 9 ++ lxvw4x 15, 31, 9 ++ ++ xxlxor \S+32, \S+32, 0 ++ xxlxor \S+36, \S+36, 1 ++ xxlxor \S+40, \S+40, 2 ++ xxlxor \S+44, \S+44, 3 ++ xxlxor \S+33, \S+33, 4 ++ xxlxor \S+37, \S+37, 5 ++ xxlxor \S+41, \S+41, 6 ++ xxlxor \S+45, \S+45, 7 ++ xxlxor \S+34, \S+34, 8 ++ xxlxor \S+38, \S+38, 9 ++ xxlxor \S+42, \S+42, 10 ++ xxlxor \S+46, \S+46, 11 ++ xxlxor \S+35, \S+35, 12 ++ xxlxor \S+39, \S+39, 13 ++ xxlxor \S+43, \S+43, 14 ++ xxlxor \S+47, \S+47, 15 ++ ++ stxvw4x \S+32, 0, 16 ++ stxvw4x \S+36, 17, 16 ++ stxvw4x \S+40, 18, 16 ++ stxvw4x \S+44, 19, 16 ++ ++ stxvw4x \S+33, 20, 16 ++ stxvw4x \S+37, 21, 16 ++ stxvw4x \S+41, 22, 16 ++ stxvw4x \S+45, 23, 16 ++ ++ stxvw4x \S+34, 24, 16 ++ stxvw4x \S+38, 25, 16 ++ stxvw4x \S+42, 26, 16 ++ stxvw4x \S+46, 27, 16 ++ ++ stxvw4x \S+35, 28, 16 ++ stxvw4x \S+39, 29, 16 ++ stxvw4x \S+43, 30, 16 ++ stxvw4x \S+47, 31, 16 ++ ++.endm ++ ++# ++# unsigned int _gcry_chacha20_p10le_8x(u32 *state, byte *dst, const byte *src, size_t len); ++# ++.global _gcry_chacha20_p10le_8x ++.align 5 ++_gcry_chacha20_p10le_8x: ++ cmpdi 6, 512 ++ blt Out_no_chacha ++ ++ stdu 1,-1024(1) ++ mflr 0 ++ ++ std 14,112(1) ++ std 15,120(1) ++ std 16,128(1) ++ std 17,136(1) ++ std 18,144(1) ++ std 19,152(1) ++ std 20,160(1) ++ std 21,168(1) ++ std 22,176(1) ++ std 23,184(1) ++ std 24,192(1) ++ std 25,200(1) ++ std 26,208(1) ++ std 27,216(1) ++ std 28,224(1) ++ std 29,232(1) ++ std 30,240(1) ++ std 31,248(1) ++ std 0, 1040(1) ++ ++ li 17, 16 ++ li 18, 32 ++ li 19, 48 ++ li 20, 64 ++ li 21, 80 ++ li 22, 96 ++ li 23, 112 ++ li 24, 128 ++ li 25, 144 ++ li 26, 160 ++ li 27, 176 ++ li 28, 192 ++ li 29, 208 ++ li 30, 224 ++ li 31, 240 ++ addi 9, 1, 256 ++ stvx 20, 0, 9 ++ stvx 21, 17, 9 ++ stvx 22, 18, 9 ++ stvx 23, 19, 9 ++ stvx 24, 20, 9 ++ stvx 25, 21, 9 ++ stvx 26, 22, 9 ++ stvx 27, 23, 9 ++ stvx 28, 24, 9 ++ stvx 29, 25, 9 ++ stvx 30, 26, 9 ++ stvx 31, 27, 9 ++ ++ add 9, 9, 27 ++ addi 14, 17, 16 ++ stxvx 14, 14, 9 ++ addi 14, 14, 16 ++ stxvx 15, 14, 9 ++ addi 14, 14, 16 ++ stxvx 16, 14, 9 ++ addi 14, 14, 16 ++ stxvx 17, 14, 9 ++ addi 14, 14, 16 ++ stxvx 18, 14, 9 ++ addi 14, 14, 16 ++ stxvx 19, 14, 9 ++ addi 14, 14, 16 ++ stxvx 20, 14, 9 ++ addi 14, 14, 16 ++ stxvx 21, 14, 9 ++ addi 14, 14, 16 ++ stxvx 22, 14, 9 ++ addi 14, 14, 16 ++ stxvx 23, 14, 9 ++ addi 14, 14, 16 ++ stxvx 24, 14, 9 ++ addi 14, 14, 16 ++ stxvx 25, 14, 9 ++ addi 14, 14, 16 ++ stxvx 26, 14, 9 ++ addi 14, 14, 16 ++ stxvx 27, 14, 9 ++ addi 14, 14, 16 ++ stxvx 28, 14, 9 ++ addi 14, 14, 16 ++ stxvx 29, 14, 9 ++ addi 14, 14, 16 ++ stxvx 30, 14, 9 ++ addi 14, 14, 16 ++ stxvx 31, 14, 9 ++ ++ mr 15, 6 # len ++ li 14, 0 # offset to inp and outp ++ ++ ld 10, sigma@got(2) ++ ++ lxvw4x 48, 0, 3 # vr16, constants ++ lxvw4x 49, 17, 3 # vr17, key 1 ++ lxvw4x 50, 18, 3 # vr18, key 2 ++ lxvw4x 51, 19, 3 # vr19, counter, nonce ++ ++ lxvw4x 62, 19, 10 # vr30, 4 ++ ++ vspltisw 21, 12 ++ vspltisw 23, 7 ++ ++ ld 11, permx@got(2) ++ lxvw4x 32+20, 0, 11 ++ lxvw4x 32+22, 17, 11 ++ ++ li 8, 10 ++ mtctr 8 ++ ++ xxlor 16, 48, 48 ++ xxlor 17, 49, 49 ++ xxlor 18, 50, 50 ++ xxlor 19, 51, 51 ++ ++ vspltisw 25, 4 ++ vspltisw 26, 8 ++ ++ xxlor 16, 48, 48 ++ xxlor 17, 49, 49 ++ xxlor 18, 50, 50 ++ xxlor 19, 51, 51 ++ ++ xxlor 25, 32+26, 32+26 ++ xxlor 24, 32+25, 32+25 ++ ++ vadduwm 31, 30, 25 # (0, 1, 2, 3) + (4, 4, 4, 4) ++ xxlor 30, 32+30, 32+30 ++ xxlor 31, 32+31, 32+31 ++ ++ xxlor 20, 32+20, 32+20 ++ xxlor 21, 32+21, 32+21 ++ xxlor 22, 32+22, 32+22 ++ xxlor 23, 32+23, 32+23 ++ ++Loop_8x: ++ lvx 0, 20, 10 ++ lvx 1, 21, 10 ++ lvx 2, 22, 10 ++ lvx 3, 23, 10 ++ xxspltw 32+4, 17, 0 ++ xxspltw 32+5, 17, 1 ++ xxspltw 32+6, 17, 2 ++ xxspltw 32+7, 17, 3 ++ xxspltw 32+8, 18, 0 ++ xxspltw 32+9, 18, 1 ++ xxspltw 32+10, 18, 2 ++ xxspltw 32+11, 18, 3 ++ xxspltw 32+12, 19, 0 ++ xxspltw 32+13, 19, 1 ++ xxspltw 32+14, 19, 2 ++ xxspltw 32+15, 19, 3 ++ vadduwm 12, 12, 30 # increase counter ++ ++ lvx 16, 20, 10 ++ lvx 17, 21, 10 ++ lvx 18, 22, 10 ++ lvx 19, 23, 10 ++ xxspltw 32+20, 17, 0 ++ xxspltw 32+21, 17, 1 ++ xxspltw 32+22, 17, 2 ++ xxspltw 32+23, 17, 3 ++ xxspltw 32+24, 18, 0 ++ xxspltw 32+25, 18, 1 ++ xxspltw 32+26, 18, 2 ++ xxspltw 32+27, 18, 3 ++ xxspltw 32+28, 19, 0 ++ xxspltw 32+29, 19, 1 ++ vadduwm 28, 28, 31 # increase counter ++ xxspltw 32+30, 19, 2 ++ xxspltw 32+31, 19, 3 ++ ++.align 5 ++quarter_loop_8x: ++ QT_loop_8x ++ ++ bdnz quarter_loop_8x ++ ++ xxlor 0, 32+30, 32+30 ++ xxlor 32+30, 30, 30 ++ vadduwm 12, 12, 30 ++ xxlor 32+30, 0, 0 ++ TP_4x 0, 1, 2, 3 ++ TP_4x 4, 5, 6, 7 ++ TP_4x 8, 9, 10, 11 ++ TP_4x 12, 13, 14, 15 ++ ++ xxlor 0, 48, 48 ++ xxlor 1, 49, 49 ++ xxlor 2, 50, 50 ++ xxlor 3, 51, 51 ++ xxlor 48, 16, 16 ++ xxlor 49, 17, 17 ++ xxlor 50, 18, 18 ++ xxlor 51, 19, 19 ++ Add_state 0 ++ xxlor 48, 0, 0 ++ xxlor 49, 1, 1 ++ xxlor 50, 2, 2 ++ xxlor 51, 3, 3 ++ Write_256 0 ++ addi 14, 14, 256 ++ addi 15, 15, -256 ++ ++ xxlor 5, 32+31, 32+31 ++ xxlor 32+31, 31, 31 ++ vadduwm 28, 28, 31 ++ xxlor 32+31, 5, 5 ++ TP_4x 16+0, 16+1, 16+2, 16+3 ++ TP_4x 16+4, 16+5, 16+6, 16+7 ++ TP_4x 16+8, 16+9, 16+10, 16+11 ++ TP_4x 16+12, 16+13, 16+14, 16+15 ++ ++ xxlor 32, 16, 16 ++ xxlor 33, 17, 17 ++ xxlor 34, 18, 18 ++ xxlor 35, 19, 19 ++ Add_state 16 ++ Write_256 16 ++ addi 14, 14, 256 ++ addi 15, 15, -256 ++ ++ # should update counter before out? ++ xxlor 32+24, 24, 24 ++ xxlor 32+25, 25, 25 ++ xxlor 32+30, 30, 30 ++ vadduwm 30, 30, 25 ++ vadduwm 31, 30, 24 ++ xxlor 30, 32+30, 32+30 ++ xxlor 31, 32+31, 32+31 ++ ++ cmpdi 15, 0 ++ beq Out_loop ++ ++ cmpdi 15, 512 ++ blt Loop_last ++ ++ mtctr 8 ++ b Loop_8x ++ ++Loop_last: ++ lxvw4x 48, 0, 3 # vr16, constants ++ lxvw4x 49, 17, 3 # vr17, key 1 ++ lxvw4x 50, 18, 3 # vr18, key 2 ++ lxvw4x 51, 19, 3 # vr19, counter, nonce ++ ++ vspltisw 21, 12 ++ vspltisw 23, 7 ++ lxvw4x 32+20, 0, 11 ++ lxvw4x 32+22, 17, 11 ++ ++ li 8, 10 ++ mtctr 8 ++ ++Loop_4x: ++ lvx 0, 20, 10 ++ lvx 1, 21, 10 ++ lvx 2, 22, 10 ++ lvx 3, 23, 10 ++ vspltw 4, 17, 0 ++ vspltw 5, 17, 1 ++ vspltw 6, 17, 2 ++ vspltw 7, 17, 3 ++ vspltw 8, 18, 0 ++ vspltw 9, 18, 1 ++ vspltw 10, 18, 2 ++ vspltw 11, 18, 3 ++ vspltw 12, 19, 0 ++ vadduwm 12, 12, 30 # increase counter ++ vspltw 13, 19, 1 ++ vspltw 14, 19, 2 ++ vspltw 15, 19, 3 ++ ++.align 5 ++quarter_loop: ++ QT_loop_4x ++ ++ bdnz quarter_loop ++ ++ vadduwm 12, 12, 30 ++ TP_4x 0, 1, 2, 3 ++ TP_4x 4, 5, 6, 7 ++ TP_4x 8, 9, 10, 11 ++ TP_4x 12, 13, 14, 15 ++ ++ Add_state 0 ++ Write_256 0 ++ addi 14, 14, 256 ++ addi 15, 15, -256 ++ ++ # Update state counter ++ vspltisw 25, 4 ++ vadduwm 30, 30, 25 ++ ++ cmpdi 15, 0 ++ beq Out_loop ++ ++ mtctr 8 ++ b Loop_4x ++ ++Out_loop: ++ # ++ # Update state counter ++ # ++ vspltisb 16, -1 # first 16 bytes - 0xffff...ff ++ vspltisb 17, 0 # second 16 bytes - 0x0000...00 ++ vsldoi 18, 16, 17, 12 ++ vand 18, 18, 30 ++ xxlor 32+19, 19, 19 ++ vadduwm 18, 19, 18 ++ stxvw4x 32+18, 19, 3 ++ li 3, 0 ++ ++ addi 9, 1, 256 ++ lvx 20, 0, 9 ++ lvx 21, 17, 9 ++ lvx 22, 18, 9 ++ lvx 23, 19, 9 ++ lvx 24, 20, 9 ++ lvx 25, 21, 9 ++ lvx 26, 22, 9 ++ lvx 27, 23, 9 ++ lvx 28, 24, 9 ++ lvx 29, 25, 9 ++ lvx 30, 26, 9 ++ lvx 31, 27, 9 ++ ++ add 9, 9, 27 ++ addi 14, 17, 16 ++ lxvx 14, 14, 9 ++ addi 14, 14, 16 ++ lxvx 15, 14, 9 ++ addi 14, 14, 16 ++ lxvx 16, 14, 9 ++ addi 14, 14, 16 ++ lxvx 17, 14, 9 ++ addi 14, 14, 16 ++ lxvx 18, 14, 9 ++ addi 14, 14, 16 ++ lxvx 19, 14, 9 ++ addi 14, 14, 16 ++ lxvx 20, 14, 9 ++ addi 14, 14, 16 ++ lxvx 21, 14, 9 ++ addi 14, 14, 16 ++ lxvx 22, 14, 9 ++ addi 14, 14, 16 ++ lxvx 23, 14, 9 ++ addi 14, 14, 16 ++ lxvx 24, 14, 9 ++ addi 14, 14, 16 ++ lxvx 25, 14, 9 ++ addi 14, 14, 16 ++ lxvx 26, 14, 9 ++ addi 14, 14, 16 ++ lxvx 27, 14, 9 ++ addi 14, 14, 16 ++ lxvx 28, 14, 9 ++ addi 14, 14, 16 ++ lxvx 29, 14, 9 ++ addi 14, 14, 16 ++ lxvx 30, 14, 9 ++ addi 14, 14, 16 ++ lxvx 31, 14, 9 ++ ++ ld 0, 1040(1) ++ ld 14,112(1) ++ ld 15,120(1) ++ ld 16,128(1) ++ ld 17,136(1) ++ ld 18,144(1) ++ ld 19,152(1) ++ ld 20,160(1) ++ ld 21,168(1) ++ ld 22,176(1) ++ ld 23,184(1) ++ ld 24,192(1) ++ ld 25,200(1) ++ ld 26,208(1) ++ ld 27,216(1) ++ ld 28,224(1) ++ ld 29,232(1) ++ ld 30,240(1) ++ ld 31,248(1) ++ ++ mtlr 0 ++ addi 1, 1, 1024 ++ blr ++ ++Out_no_chacha: ++ li 3, 0 ++ blr ++ ++.data ++.align 4 ++sigma: ++.long 0x61707865, 0x3320646e, 0x79622d32, 0x6b206574 ++.long 0x0c0d0e0f, 0x08090a0b, 0x04050607, 0x00010203 ++.long 1, 0, 0, 0 ++.long 0, 1, 2, 3 ++.long 0x61707865, 0x61707865, 0x61707865, 0x61707865 ++.long 0x3320646e, 0x3320646e, 0x3320646e, 0x3320646e ++.long 0x79622d32, 0x79622d32, 0x79622d32, 0x79622d32 ++.long 0x6b206574, 0x6b206574, 0x6b206574, 0x6b206574 ++permx: ++.long 0x22330011, 0x66774455, 0xaabb8899, 0xeeffccdd ++.long 0x11223300, 0x55667744, 0x99aabb88, 0xddeeffcc +Index: libgcrypt-1.10.2/cipher/chacha20.c +=================================================================== +--- libgcrypt-1.10.2.orig/cipher/chacha20.c ++++ libgcrypt-1.10.2/cipher/chacha20.c +@@ -125,6 +125,7 @@ typedef struct CHACHA20_context_s + unsigned int use_avx2:1; + unsigned int use_neon:1; + unsigned int use_ppc:1; ++ unsigned int use_p10:1; + unsigned int use_s390x:1; + } CHACHA20_context_t; + +@@ -163,6 +164,12 @@ unsigned int _gcry_chacha20_poly1305_amd + + #ifdef USE_PPC_VEC + ++#ifndef WORDS_BIGENDIAN ++unsigned int _gcry_chacha20_p10le_8x(u32 *state, byte *dst, ++ const byte *src, ++ size_t len); ++#endif ++ + unsigned int _gcry_chacha20_ppc8_blocks4(u32 *state, byte *dst, + const byte *src, + size_t nblks); +@@ -475,6 +482,9 @@ chacha20_do_setkey (CHACHA20_context_t * + #endif + #ifdef USE_PPC_VEC + ctx->use_ppc = (features & HWF_PPC_ARCH_2_07) != 0; ++# ifndef WORDS_BIGENDIAN ++ ctx->use_p10 = (features & HWF_PPC_ARCH_3_10) != 0; ++# endif + #endif + #ifdef USE_S390X_VX + ctx->use_s390x = (features & HWF_S390X_VX) != 0; +@@ -571,7 +581,22 @@ do_chacha20_encrypt_stream_tail (CHACHA2 + { + size_t nblocks = length / CHACHA20_BLOCK_SIZE; + nblocks -= nblocks % 4; +- nburn = _gcry_chacha20_ppc8_blocks4(ctx->input, outbuf, inbuf, nblocks); ++#ifndef WORDS_BIGENDIAN ++ /* ++ * A workaround to skip counter overflow. This is rare. ++ */ ++ if (ctx->use_p10 && nblocks >= 8 ++ && ((u64)ctx->input[12] + nblocks) <= 0xffffffffU) ++ { ++ size_t len = nblocks * CHACHA20_BLOCK_SIZE; ++ nburn = _gcry_chacha20_p10le_8x(ctx->input, outbuf, inbuf, len); ++ } ++ else ++#endif ++ { ++ nburn = _gcry_chacha20_ppc8_blocks4(ctx->input, outbuf, inbuf, ++ nblocks); ++ } + burn = nburn > burn ? nburn : burn; + length -= nblocks * CHACHA20_BLOCK_SIZE; + outbuf += nblocks * CHACHA20_BLOCK_SIZE; +@@ -760,6 +785,11 @@ _gcry_chacha20_poly1305_encrypt(gcry_cip + } + #endif + #ifdef USE_PPC_VEC_POLY1305 ++ else if (ctx->use_ppc && ctx->use_p10) ++ { ++ /* Skip stitched chacha20-poly1305 for P10. */ ++ authptr = NULL; ++ } + else if (ctx->use_ppc && length >= CHACHA20_BLOCK_SIZE * 4) + { + nburn = _gcry_chacha20_ppc8_blocks4(ctx->input, outbuf, inbuf, 4); +@@ -998,6 +1028,7 @@ _gcry_chacha20_poly1305_decrypt(gcry_cip + { + CHACHA20_context_t *ctx = (void *) &c->context.c; + unsigned int nburn, burn = 0; ++ int skip_stitched = 0; + + if (!length) + return 0; +@@ -1049,6 +1080,13 @@ _gcry_chacha20_poly1305_decrypt(gcry_cip + inbuf += nblocks * CHACHA20_BLOCK_SIZE; + } + #endif ++#ifdef USE_PPC_VEC_POLY1305 ++ if (ctx->use_ppc && ctx->use_p10) ++ { ++ /* Skip stitched chacha20-poly1305 for P10. */ ++ skip_stitched = 1; ++ } ++#endif + + #ifdef USE_SSSE3 + if (ctx->use_ssse3) +@@ -1102,7 +1140,8 @@ _gcry_chacha20_poly1305_decrypt(gcry_cip + #endif + + #ifdef USE_PPC_VEC_POLY1305 +- if (ctx->use_ppc && length >= 4 * CHACHA20_BLOCK_SIZE) ++ /* skip stitch for p10 */ ++ if (!skip_stitched && ctx->use_ppc && length >= 4 * CHACHA20_BLOCK_SIZE) + { + size_t nblocks = length / CHACHA20_BLOCK_SIZE; + nblocks -= nblocks % 4; +Index: libgcrypt-1.10.2/cipher/poly1305-internal.h +=================================================================== +--- libgcrypt-1.10.2.orig/cipher/poly1305-internal.h ++++ libgcrypt-1.10.2/cipher/poly1305-internal.h +@@ -33,6 +33,17 @@ + #define POLY1305_KEYLEN 32 + #define POLY1305_BLOCKSIZE 16 + ++/* POLY1305_USE_PPC_VEC indicates whether to enable PowerPC vector code. */ ++#undef POLY1305_USE_PPC_VEC ++#ifdef ENABLE_PPC_CRYPTO_SUPPORT ++# if defined(HAVE_COMPATIBLE_CC_PPC_ALTIVEC) && \ ++ defined(HAVE_GCC_INLINE_ASM_PPC_ALTIVEC) && \ ++ !defined(WORDS_BIGENDIAN) ++# if __GNUC__ >= 4 ++# define POLY1305_USE_PPC_VEC 1 ++# endif ++# endif ++#endif + + typedef struct + { +@@ -46,6 +57,9 @@ typedef struct poly1305_context_s + POLY1305_STATE state; + byte buffer[POLY1305_BLOCKSIZE]; + unsigned int leftover; ++#ifdef POLY1305_USE_PPC_VEC ++ unsigned int use_p10:1; ++#endif + } poly1305_context_t; + + +Index: libgcrypt-1.10.2/cipher/poly1305-p10le.s +=================================================================== +--- /dev/null ++++ libgcrypt-1.10.2/cipher/poly1305-p10le.s +@@ -0,0 +1,841 @@ ++# Copyright 2021- IBM Inc. All rights reserved ++# ++# This file is part of Libgcrypt. ++# ++# Libgcrypt is free software; you can redistribute it and/or modify ++# it under the terms of the GNU Lesser General Public License as ++# published by the Free Software Foundation; either version 2.1 of ++# the License, or (at your option) any later version. ++# ++# Libgcrypt 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 Lesser General Public License for more details. ++# ++# You should have received a copy of the GNU Lesser General Public ++# License along with this program; if not, see . ++# ++#=================================================================================== ++# Written by Danny Tsen ++# ++# Poly1305 - this version mainly using vector/VSX/Scalar ++# - 26 bits limbs ++# - Handle multiple 64 byte blcoks but need at least 2 64 bytes block ++# ++# Improve performance by breaking down polynominal to the sum of products with ++# h4 = m1 * r⁴ + m2 * r³ + m3 * r² + m4 * r ++# ++# 07/22/21 - this revison based on the above sum of products. Setup r^4, r^3, r^2, r and s3, s2, s1, s0 ++# to 9 vectors for multiplications. ++# ++# setup r^4, r^3, r^2, r vectors ++# vs [r^1, r^3, r^2, r^4] ++# vs0 = [r0,.....] ++# vs1 = [r1,.....] ++# vs2 = [r2,.....] ++# vs3 = [r3,.....] ++# vs4 = [r4,.....] ++# vs5 = [r1*5,...] ++# vs6 = [r2*5,...] ++# vs7 = [r2*5,...] ++# vs8 = [r4*5,...] ++# ++# Each word in a vector consists a member of a "r/s" in [a * r/s]. ++# ++# r0, r4*5, r3*5, r2*5, r1*5; ++# r1, r0, r4*5, r3*5, r2*5; ++# r2, r1, r0, r4*5, r3*5; ++# r3, r2, r1, r0, r4*5; ++# r4, r3, r2, r1, r0 ; ++# ++# ++# gcry_poly1305_p10le_4blocks( uint8_t *k, uint32_t mlen, uint8_t *m) ++# k = 32 bytes key ++# r3 = k (r, s) ++# r4 = mlen ++# r5 = m ++# ++.text ++ ++# Block size 16 bytes ++# key = (r, s) ++# clamp r &= 0x0FFFFFFC0FFFFFFC 0x0FFFFFFC0FFFFFFF ++# p = 2^130 - 5 ++# a += m ++# a = (r + a) % p ++# a += s ++# 16 bytes (a) ++# ++# p[0] = a0*r0 + a1*r4*5 + a2*r3*5 + a3*r2*5 + a4*r1*5; ++# p[1] = a0*r1 + a1*r0 + a2*r4*5 + a3*r3*5 + a4*r2*5; ++# p[2] = a0*r2 + a1*r1 + a2*r0 + a3*r4*5 + a4*r3*5; ++# p[3] = a0*r3 + a1*r2 + a2*r1 + a3*r0 + a4*r4*5; ++# p[4] = a0*r4 + a1*r3 + a2*r2 + a3*r1 + a4*r0 ; ++# ++# [r^2, r^3, r^1, r^4] ++# [m3, m2, m4, m1] ++# ++# multiply odd and even words ++.macro mul_odd ++ vmulouw 14, 4, 26 ++ vmulouw 10, 5, 3 ++ vmulouw 11, 6, 2 ++ vmulouw 12, 7, 1 ++ vmulouw 13, 8, 0 ++ vmulouw 15, 4, 27 ++ vaddudm 14, 14, 10 ++ vaddudm 14, 14, 11 ++ vmulouw 10, 5, 26 ++ vmulouw 11, 6, 3 ++ vaddudm 14, 14, 12 ++ vaddudm 14, 14, 13 # x0 ++ vaddudm 15, 15, 10 ++ vaddudm 15, 15, 11 ++ vmulouw 12, 7, 2 ++ vmulouw 13, 8, 1 ++ vaddudm 15, 15, 12 ++ vaddudm 15, 15, 13 # x1 ++ vmulouw 16, 4, 28 ++ vmulouw 10, 5, 27 ++ vmulouw 11, 6, 26 ++ vaddudm 16, 16, 10 ++ vaddudm 16, 16, 11 ++ vmulouw 12, 7, 3 ++ vmulouw 13, 8, 2 ++ vaddudm 16, 16, 12 ++ vaddudm 16, 16, 13 # x2 ++ vmulouw 17, 4, 29 ++ vmulouw 10, 5, 28 ++ vmulouw 11, 6, 27 ++ vaddudm 17, 17, 10 ++ vaddudm 17, 17, 11 ++ vmulouw 12, 7, 26 ++ vmulouw 13, 8, 3 ++ vaddudm 17, 17, 12 ++ vaddudm 17, 17, 13 # x3 ++ vmulouw 18, 4, 30 ++ vmulouw 10, 5, 29 ++ vmulouw 11, 6, 28 ++ vaddudm 18, 18, 10 ++ vaddudm 18, 18, 11 ++ vmulouw 12, 7, 27 ++ vmulouw 13, 8, 26 ++ vaddudm 18, 18, 12 ++ vaddudm 18, 18, 13 # x4 ++.endm ++ ++.macro mul_even ++ vmuleuw 9, 4, 26 ++ vmuleuw 10, 5, 3 ++ vmuleuw 11, 6, 2 ++ vmuleuw 12, 7, 1 ++ vmuleuw 13, 8, 0 ++ vaddudm 14, 14, 9 ++ vaddudm 14, 14, 10 ++ vaddudm 14, 14, 11 ++ vaddudm 14, 14, 12 ++ vaddudm 14, 14, 13 # x0 ++ ++ vmuleuw 9, 4, 27 ++ vmuleuw 10, 5, 26 ++ vmuleuw 11, 6, 3 ++ vmuleuw 12, 7, 2 ++ vmuleuw 13, 8, 1 ++ vaddudm 15, 15, 9 ++ vaddudm 15, 15, 10 ++ vaddudm 15, 15, 11 ++ vaddudm 15, 15, 12 ++ vaddudm 15, 15, 13 # x1 ++ ++ vmuleuw 9, 4, 28 ++ vmuleuw 10, 5, 27 ++ vmuleuw 11, 6, 26 ++ vmuleuw 12, 7, 3 ++ vmuleuw 13, 8, 2 ++ vaddudm 16, 16, 9 ++ vaddudm 16, 16, 10 ++ vaddudm 16, 16, 11 ++ vaddudm 16, 16, 12 ++ vaddudm 16, 16, 13 # x2 ++ ++ vmuleuw 9, 4, 29 ++ vmuleuw 10, 5, 28 ++ vmuleuw 11, 6, 27 ++ vmuleuw 12, 7, 26 ++ vmuleuw 13, 8, 3 ++ vaddudm 17, 17, 9 ++ vaddudm 17, 17, 10 ++ vaddudm 17, 17, 11 ++ vaddudm 17, 17, 12 ++ vaddudm 17, 17, 13 # x3 ++ ++ vmuleuw 9, 4, 30 ++ vmuleuw 10, 5, 29 ++ vmuleuw 11, 6, 28 ++ vmuleuw 12, 7, 27 ++ vmuleuw 13, 8, 26 ++ vaddudm 18, 18, 9 ++ vaddudm 18, 18, 10 ++ vaddudm 18, 18, 11 ++ vaddudm 18, 18, 12 ++ vaddudm 18, 18, 13 # x4 ++.endm ++ ++# setup r^4, r^3, r^2, r vectors ++# [r, r^3, r^2, r^4] ++# vs0 = [r0,...] ++# vs1 = [r1,...] ++# vs2 = [r2,...] ++# vs3 = [r3,...] ++# vs4 = [r4,...] ++# vs5 = [r4*5,...] ++# vs6 = [r3*5,...] ++# vs7 = [r2*5,...] ++# vs8 = [r1*5,...] ++# ++# r0, r4*5, r3*5, r2*5, r1*5; ++# r1, r0, r4*5, r3*5, r2*5; ++# r2, r1, r0, r4*5, r3*5; ++# r3, r2, r1, r0, r4*5; ++# r4, r3, r2, r1, r0 ; ++# ++.macro poly1305_setup_r ++ ++ # save r ++ xxlor 26, 58, 58 ++ xxlor 27, 59, 59 ++ xxlor 28, 60, 60 ++ xxlor 29, 61, 61 ++ xxlor 30, 62, 62 ++ ++ xxlxor 31, 31, 31 ++ ++# [r, r^3, r^2, r^4] ++ # compute r^2 ++ vmr 4, 26 ++ vmr 5, 27 ++ vmr 6, 28 ++ vmr 7, 29 ++ vmr 8, 30 ++ bl do_mul # r^2 r^1 ++ xxpermdi 58, 58, 36, 0x3 # r0 ++ xxpermdi 59, 59, 37, 0x3 # r1 ++ xxpermdi 60, 60, 38, 0x3 # r2 ++ xxpermdi 61, 61, 39, 0x3 # r3 ++ xxpermdi 62, 62, 40, 0x3 # r4 ++ xxpermdi 36, 36, 36, 0x3 ++ xxpermdi 37, 37, 37, 0x3 ++ xxpermdi 38, 38, 38, 0x3 ++ xxpermdi 39, 39, 39, 0x3 ++ xxpermdi 40, 40, 40, 0x3 ++ vspltisb 13, 2 ++ vsld 9, 27, 13 ++ vsld 10, 28, 13 ++ vsld 11, 29, 13 ++ vsld 12, 30, 13 ++ vaddudm 0, 9, 27 ++ vaddudm 1, 10, 28 ++ vaddudm 2, 11, 29 ++ vaddudm 3, 12, 30 ++ ++ bl do_mul # r^4 r^3 ++ vmrgow 26, 26, 4 ++ vmrgow 27, 27, 5 ++ vmrgow 28, 28, 6 ++ vmrgow 29, 29, 7 ++ vmrgow 30, 30, 8 ++ vspltisb 13, 2 ++ vsld 9, 27, 13 ++ vsld 10, 28, 13 ++ vsld 11, 29, 13 ++ vsld 12, 30, 13 ++ vaddudm 0, 9, 27 ++ vaddudm 1, 10, 28 ++ vaddudm 2, 11, 29 ++ vaddudm 3, 12, 30 ++ ++ # r^2 r^4 ++ xxlor 0, 58, 58 ++ xxlor 1, 59, 59 ++ xxlor 2, 60, 60 ++ xxlor 3, 61, 61 ++ xxlor 4, 62, 62 ++ xxlor 5, 32, 32 ++ xxlor 6, 33, 33 ++ xxlor 7, 34, 34 ++ xxlor 8, 35, 35 ++ ++ vspltw 9, 26, 3 ++ vspltw 10, 26, 2 ++ vmrgow 26, 10, 9 ++ vspltw 9, 27, 3 ++ vspltw 10, 27, 2 ++ vmrgow 27, 10, 9 ++ vspltw 9, 28, 3 ++ vspltw 10, 28, 2 ++ vmrgow 28, 10, 9 ++ vspltw 9, 29, 3 ++ vspltw 10, 29, 2 ++ vmrgow 29, 10, 9 ++ vspltw 9, 30, 3 ++ vspltw 10, 30, 2 ++ vmrgow 30, 10, 9 ++ ++ vsld 9, 27, 13 ++ vsld 10, 28, 13 ++ vsld 11, 29, 13 ++ vsld 12, 30, 13 ++ vaddudm 0, 9, 27 ++ vaddudm 1, 10, 28 ++ vaddudm 2, 11, 29 ++ vaddudm 3, 12, 30 ++.endm ++ ++do_mul: ++ mul_odd ++ ++ # do reduction ( h %= p ) ++ # carry reduction ++ vspltisb 9, 2 ++ vsrd 10, 14, 31 ++ vsrd 11, 17, 31 ++ vand 7, 17, 25 ++ vand 4, 14, 25 ++ vaddudm 18, 18, 11 ++ vsrd 12, 18, 31 ++ vaddudm 15, 15, 10 ++ ++ vsrd 11, 15, 31 ++ vand 8, 18, 25 ++ vand 5, 15, 25 ++ vaddudm 4, 4, 12 ++ vsld 10, 12, 9 ++ vaddudm 6, 16, 11 ++ ++ vsrd 13, 6, 31 ++ vand 6, 6, 25 ++ vaddudm 4, 4, 10 ++ vsrd 10, 4, 31 ++ vaddudm 7, 7, 13 ++ ++ vsrd 11, 7, 31 ++ vand 7, 7, 25 ++ vand 4, 4, 25 ++ vaddudm 5, 5, 10 ++ vaddudm 8, 8, 11 ++ blr ++ ++# ++# init key ++# ++do_poly1305_init: ++ ld 10, rmask@got(2) ++ ld 11, 0(10) ++ ld 12, 8(10) ++ ++ li 14, 16 ++ li 15, 32 ++ ld 10, cnum@got(2) ++ lvx 25, 0, 10 # v25 - mask ++ lvx 31, 14, 10 # v31 = 1a ++ lvx 19, 15, 10 # v19 = 1 << 24 ++ lxv 24, 48(10) # vs24 ++ lxv 25, 64(10) # vs25 ++ ++ # initialize ++ # load key from r3 to vectors ++ ld 9, 16(3) ++ ld 10, 24(3) ++ ld 11, 0(3) ++ ld 12, 8(3) ++ ++ # break 26 bits ++ extrdi 14, 9, 26, 38 ++ extrdi 15, 9, 26, 12 ++ extrdi 16, 9, 12, 0 ++ mtvsrdd 58, 0, 14 ++ insrdi 16, 10, 14, 38 ++ mtvsrdd 59, 0, 15 ++ extrdi 17, 10, 26, 24 ++ mtvsrdd 60, 0, 16 ++ extrdi 18, 10, 24, 0 ++ mtvsrdd 61, 0, 17 ++ mtvsrdd 62, 0, 18 ++ ++ # r1 = r1 * 5, r2 = r2 * 5, r3 = r3 * 5, r4 = r4 * 5 ++ li 9, 5 ++ mtvsrdd 36, 0, 9 ++ vmulouw 0, 27, 4 # v0 = rr0 ++ vmulouw 1, 28, 4 # v1 = rr1 ++ vmulouw 2, 29, 4 # v2 = rr2 ++ vmulouw 3, 30, 4 # v3 = rr3 ++ blr ++ ++# ++# gcry_poly1305_p10le_4blocks( uint8_t *k, uint32_t mlen, uint8_t *m) ++# k = 32 bytes key ++# r3 = k (r, s) ++# r4 = mlen ++# r5 = m ++# ++.global gcry_poly1305_p10le_4blocks ++.align 5 ++gcry_poly1305_p10le_4blocks: ++_gcry_poly1305_p10le_4blocks: ++ cmpdi 5, 128 ++ blt Out_no_poly1305 ++ ++ stdu 1,-1024(1) ++ mflr 0 ++ ++ std 14,112(1) ++ std 15,120(1) ++ std 16,128(1) ++ std 17,136(1) ++ std 18,144(1) ++ std 19,152(1) ++ std 20,160(1) ++ std 21,168(1) ++ std 31,248(1) ++ li 14, 256 ++ stvx 20, 14, 1 ++ addi 14, 14, 16 ++ stvx 21, 14, 1 ++ addi 14, 14, 16 ++ stvx 22, 14, 1 ++ addi 14, 14, 16 ++ stvx 23, 14, 1 ++ addi 14, 14, 16 ++ stvx 24, 14, 1 ++ addi 14, 14, 16 ++ stvx 25, 14, 1 ++ addi 14, 14, 16 ++ stvx 26, 14, 1 ++ addi 14, 14, 16 ++ stvx 27, 14, 1 ++ addi 14, 14, 16 ++ stvx 28, 14, 1 ++ addi 14, 14, 16 ++ stvx 29, 14, 1 ++ addi 14, 14, 16 ++ stvx 30, 14, 1 ++ addi 14, 14, 16 ++ stvx 31, 14, 1 ++ ++ addi 14, 14, 16 ++ stxvx 14, 14, 1 ++ addi 14, 14, 16 ++ stxvx 15, 14, 1 ++ addi 14, 14, 16 ++ stxvx 16, 14, 1 ++ addi 14, 14, 16 ++ stxvx 17, 14, 1 ++ addi 14, 14, 16 ++ stxvx 18, 14, 1 ++ addi 14, 14, 16 ++ stxvx 19, 14, 1 ++ addi 14, 14, 16 ++ stxvx 20, 14, 1 ++ addi 14, 14, 16 ++ stxvx 21, 14, 1 ++ addi 14, 14, 16 ++ stxvx 22, 14, 1 ++ addi 14, 14, 16 ++ stxvx 23, 14, 1 ++ addi 14, 14, 16 ++ stxvx 24, 14, 1 ++ addi 14, 14, 16 ++ stxvx 25, 14, 1 ++ addi 14, 14, 16 ++ stxvx 26, 14, 1 ++ addi 14, 14, 16 ++ stxvx 27, 14, 1 ++ addi 14, 14, 16 ++ stxvx 28, 14, 1 ++ addi 14, 14, 16 ++ stxvx 29, 14, 1 ++ addi 14, 14, 16 ++ stxvx 30, 14, 1 ++ addi 14, 14, 16 ++ stxvx 31, 14, 1 ++ std 0, 1040(1) ++ ++ bl do_poly1305_init ++ ++ li 21, 0 # counter to message ++ ++ poly1305_setup_r ++ ++ # load previous state ++ # break/convert r6 to 26 bits ++ ld 9, 32(3) ++ ld 10, 40(3) ++ lwz 19, 48(3) ++ sldi 19, 19, 24 ++ mtvsrdd 41, 0, 19 ++ extrdi 14, 9, 26, 38 ++ extrdi 15, 9, 26, 12 ++ extrdi 16, 9, 12, 0 ++ mtvsrdd 36, 0, 14 ++ insrdi 16, 10, 14, 38 ++ mtvsrdd 37, 0, 15 ++ extrdi 17, 10, 26, 24 ++ mtvsrdd 38, 0, 16 ++ extrdi 18, 10, 24, 0 ++ mtvsrdd 39, 0, 17 ++ mtvsrdd 40, 0, 18 ++ vor 8, 8, 9 ++ ++ # input m1 m2 ++ add 20, 4, 21 ++ xxlor 49, 24, 24 ++ xxlor 50, 25, 25 ++ lxvw4x 43, 0, 20 ++ addi 17, 20, 16 ++ lxvw4x 44, 0, 17 ++ vperm 14, 11, 12, 17 ++ vperm 15, 11, 12, 18 ++ vand 9, 14, 25 # a0 ++ vsrd 10, 14, 31 # >> 26 ++ vsrd 11, 10, 31 # 12 bits left ++ vand 10, 10, 25 # a1 ++ vspltisb 13, 12 ++ vand 16, 15, 25 ++ vsld 12, 16, 13 ++ vor 11, 11, 12 ++ vand 11, 11, 25 # a2 ++ vspltisb 13, 14 ++ vsrd 12, 15, 13 # >> 14 ++ vsrd 13, 12, 31 # >> 26, a4 ++ vand 12, 12, 25 # a3 ++ ++ vaddudm 20, 4, 9 ++ vaddudm 21, 5, 10 ++ vaddudm 22, 6, 11 ++ vaddudm 23, 7, 12 ++ vaddudm 24, 8, 13 ++ ++ # m3 m4 ++ addi 17, 17, 16 ++ lxvw4x 43, 0, 17 ++ addi 17, 17, 16 ++ lxvw4x 44, 0, 17 ++ vperm 14, 11, 12, 17 ++ vperm 15, 11, 12, 18 ++ vand 9, 14, 25 # a0 ++ vsrd 10, 14, 31 # >> 26 ++ vsrd 11, 10, 31 # 12 bits left ++ vand 10, 10, 25 # a1 ++ vspltisb 13, 12 ++ vand 16, 15, 25 ++ vsld 12, 16, 13 ++ vspltisb 13, 14 ++ vor 11, 11, 12 ++ vand 11, 11, 25 # a2 ++ vsrd 12, 15, 13 # >> 14 ++ vsrd 13, 12, 31 # >> 26, a4 ++ vand 12, 12, 25 # a3 ++ ++ # Smash 4 message blocks into 5 vectors of [m4, m2, m3, m1] ++ vmrgow 4, 9, 20 ++ vmrgow 5, 10, 21 ++ vmrgow 6, 11, 22 ++ vmrgow 7, 12, 23 ++ vmrgow 8, 13, 24 ++ vaddudm 8, 8, 19 ++ ++ addi 5, 5, -64 ++ addi 21, 21, 64 ++ ++ li 9, 64 ++ divdu 31, 5, 9 ++ ++ mtctr 31 ++ ++# h4 = m1 * r⁴ + m2 * r³ + m3 * r² + m4 * r ++# Rewrite the polynominal sum of product as follows, ++# h1 = (h0 + m1) * r^2, h2 = (h0 + m2) * r^2 ++# h3 = (h1 + m3) * r^2, h4 = (h2 + m4) * r^2 --> (h0 + m1) r*4 + (h3 + m3) r^2, (h0 + m2) r^4 + (h0 + m4) r^2 ++# .... Repeat ++# h5 = (h3 + m5) * r^2, h6 = (h4 + m6) * r^2 --> ++# h7 = (h5 + m7) * r^2, h8 = (h6 + m8) * r^1 --> m5 * r^4 + m6 * r^3 + m7 * r^2 + m8 * r ++# ++loop_4blocks: ++ ++ # Multiply odd words and even words ++ mul_odd ++ mul_even ++ # carry reduction ++ vspltisb 9, 2 ++ vsrd 10, 14, 31 ++ vsrd 11, 17, 31 ++ vand 7, 17, 25 ++ vand 4, 14, 25 ++ vaddudm 18, 18, 11 ++ vsrd 12, 18, 31 ++ vaddudm 15, 15, 10 ++ ++ vsrd 11, 15, 31 ++ vand 8, 18, 25 ++ vand 5, 15, 25 ++ vaddudm 4, 4, 12 ++ vsld 10, 12, 9 ++ vaddudm 6, 16, 11 ++ ++ vsrd 13, 6, 31 ++ vand 6, 6, 25 ++ vaddudm 4, 4, 10 ++ vsrd 10, 4, 31 ++ vaddudm 7, 7, 13 ++ ++ vsrd 11, 7, 31 ++ vand 7, 7, 25 ++ vand 4, 4, 25 ++ vaddudm 5, 5, 10 ++ vaddudm 8, 8, 11 ++ ++ # input m1 m2 m3 m4 ++ add 20, 4, 21 ++ xxlor 49, 24, 24 ++ xxlor 50, 25, 25 ++ lxvw4x 43, 0, 20 ++ addi 17, 20, 16 ++ lxvw4x 44, 0, 17 ++ vperm 14, 11, 12, 17 ++ vperm 15, 11, 12, 18 ++ addi 17, 17, 16 ++ lxvw4x 43, 0, 17 ++ addi 17, 17, 16 ++ lxvw4x 44, 0, 17 ++ vperm 17, 11, 12, 17 ++ vperm 18, 11, 12, 18 ++ ++ vand 20, 14, 25 # a0 ++ vand 9, 17, 25 # a0 ++ vsrd 21, 14, 31 # >> 26 ++ vsrd 22, 21, 31 # 12 bits left ++ vsrd 10, 17, 31 # >> 26 ++ vsrd 11, 10, 31 # 12 bits left ++ ++ vand 21, 21, 25 # a1 ++ vand 10, 10, 25 # a1 ++ ++ vspltisb 13, 12 ++ vand 16, 15, 25 ++ vsld 23, 16, 13 ++ vor 22, 22, 23 ++ vand 22, 22, 25 # a2 ++ vand 16, 18, 25 ++ vsld 12, 16, 13 ++ vor 11, 11, 12 ++ vand 11, 11, 25 # a2 ++ vspltisb 13, 14 ++ vsrd 23, 15, 13 # >> 14 ++ vsrd 24, 23, 31 # >> 26, a4 ++ vand 23, 23, 25 # a3 ++ vsrd 12, 18, 13 # >> 14 ++ vsrd 13, 12, 31 # >> 26, a4 ++ vand 12, 12, 25 # a3 ++ ++ vaddudm 4, 4, 20 ++ vaddudm 5, 5, 21 ++ vaddudm 6, 6, 22 ++ vaddudm 7, 7, 23 ++ vaddudm 8, 8, 24 ++ ++ # Smash 4 message blocks into 5 vectors of [m4, m2, m3, m1] ++ vmrgow 4, 9, 4 ++ vmrgow 5, 10, 5 ++ vmrgow 6, 11, 6 ++ vmrgow 7, 12, 7 ++ vmrgow 8, 13, 8 ++ vaddudm 8, 8, 19 ++ ++ addi 5, 5, -64 ++ addi 21, 21, 64 ++ ++ bdnz loop_4blocks ++ ++ xxlor 58, 0, 0 ++ xxlor 59, 1, 1 ++ xxlor 60, 2, 2 ++ xxlor 61, 3, 3 ++ xxlor 62, 4, 4 ++ xxlor 32, 5, 5 ++ xxlor 33, 6, 6 ++ xxlor 34, 7, 7 ++ xxlor 35, 8, 8 ++ ++ # Multiply odd words and even words ++ mul_odd ++ mul_even ++ ++ # Sum the products. ++ xxpermdi 41, 31, 46, 0 ++ xxpermdi 42, 31, 47, 0 ++ vaddudm 4, 14, 9 ++ xxpermdi 36, 31, 36, 3 ++ vaddudm 5, 15, 10 ++ xxpermdi 37, 31, 37, 3 ++ xxpermdi 43, 31, 48, 0 ++ vaddudm 6, 16, 11 ++ xxpermdi 38, 31, 38, 3 ++ xxpermdi 44, 31, 49, 0 ++ vaddudm 7, 17, 12 ++ xxpermdi 39, 31, 39, 3 ++ xxpermdi 45, 31, 50, 0 ++ vaddudm 8, 18, 13 ++ xxpermdi 40, 31, 40, 3 ++ ++ # carry reduction ++ vspltisb 9, 2 ++ vsrd 10, 4, 31 ++ vsrd 11, 7, 31 ++ vand 7, 7, 25 ++ vand 4, 4, 25 ++ vaddudm 8, 8, 11 ++ vsrd 12, 8, 31 ++ vaddudm 5, 5, 10 ++ ++ vsrd 11, 5, 31 ++ vand 8, 8, 25 ++ vand 5, 5, 25 ++ vaddudm 4, 4, 12 ++ vsld 10, 12, 9 ++ vaddudm 6, 6, 11 ++ ++ vsrd 13, 6, 31 ++ vand 6, 6, 25 ++ vaddudm 4, 4, 10 ++ vsrd 10, 4, 31 ++ vaddudm 7, 7, 13 ++ ++ vsrd 11, 7, 31 ++ vand 7, 7, 25 ++ vand 4, 4, 25 ++ vaddudm 5, 5, 10 ++ vaddudm 8, 8, 11 ++ ++ b do_final_update ++ ++do_final_update: ++ # v4, v5, v6, v7 and v8 are 26 bit vectors ++ vsld 5, 5, 31 ++ vor 20, 4, 5 ++ vspltisb 11, 12 ++ vsrd 12, 6, 11 ++ vsld 6, 6, 31 ++ vsld 6, 6, 31 ++ vor 20, 20, 6 ++ vspltisb 11, 14 ++ vsld 7, 7, 11 ++ vor 21, 7, 12 ++ mfvsrld 16, 40 # save last 2 bytes ++ vsld 8, 8, 11 ++ vsld 8, 8, 31 ++ vor 21, 21, 8 ++ mfvsrld 17, 52 ++ mfvsrld 19, 53 ++ srdi 16, 16, 24 ++ ++ std 17, 32(3) ++ std 19, 40(3) ++ stw 16, 48(3) ++ ++Out_loop: ++ li 3, 0 ++ ++ li 14, 256 ++ lvx 20, 14, 1 ++ addi 14, 14, 16 ++ lvx 21, 14, 1 ++ addi 14, 14, 16 ++ lvx 22, 14, 1 ++ addi 14, 14, 16 ++ lvx 23, 14, 1 ++ addi 14, 14, 16 ++ lvx 24, 14, 1 ++ addi 14, 14, 16 ++ lvx 25, 14, 1 ++ addi 14, 14, 16 ++ lvx 26, 14, 1 ++ addi 14, 14, 16 ++ lvx 27, 14, 1 ++ addi 14, 14, 16 ++ lvx 28, 14, 1 ++ addi 14, 14, 16 ++ lvx 29, 14, 1 ++ addi 14, 14, 16 ++ lvx 30, 14, 1 ++ addi 14, 14, 16 ++ lvx 31, 14, 1 ++ ++ addi 14, 14, 16 ++ lxvx 14, 14, 1 ++ addi 14, 14, 16 ++ lxvx 15, 14, 1 ++ addi 14, 14, 16 ++ lxvx 16, 14, 1 ++ addi 14, 14, 16 ++ lxvx 17, 14, 1 ++ addi 14, 14, 16 ++ lxvx 18, 14, 1 ++ addi 14, 14, 16 ++ lxvx 19, 14, 1 ++ addi 14, 14, 16 ++ lxvx 20, 14, 1 ++ addi 14, 14, 16 ++ lxvx 21, 14, 1 ++ addi 14, 14, 16 ++ lxvx 22, 14, 1 ++ addi 14, 14, 16 ++ lxvx 23, 14, 1 ++ addi 14, 14, 16 ++ lxvx 24, 14, 1 ++ addi 14, 14, 16 ++ lxvx 25, 14, 1 ++ addi 14, 14, 16 ++ lxvx 26, 14, 1 ++ addi 14, 14, 16 ++ lxvx 27, 14, 1 ++ addi 14, 14, 16 ++ lxvx 28, 14, 1 ++ addi 14, 14, 16 ++ lxvx 29, 14, 1 ++ addi 14, 14, 16 ++ lxvx 30, 14, 1 ++ addi 14, 14, 16 ++ lxvx 31, 14, 1 ++ ++ ld 0, 1040(1) ++ ld 14,112(1) ++ ld 15,120(1) ++ ld 16,128(1) ++ ld 17,136(1) ++ ld 18,144(1) ++ ld 19,152(1) ++ ld 20,160(1) ++ ld 21,168(1) ++ ld 31,248(1) ++ ++ mtlr 0 ++ addi 1, 1, 1024 ++ blr ++ ++Out_no_poly1305: ++ li 3, 0 ++ blr ++ ++.data ++.align 5 ++rmask: ++.byte 0xff, 0xff, 0xff, 0x0f, 0xfc, 0xff, 0xff, 0x0f, 0xfc, 0xff, 0xff, 0x0f, 0xfc, 0xff, 0xff, 0x0f ++cnum: ++.long 0x03ffffff, 0x00000000, 0x03ffffff, 0x00000000 ++.long 0x1a, 0x00, 0x1a, 0x00 ++.long 0x01000000, 0x01000000, 0x01000000, 0x01000000 ++.long 0x00010203, 0x04050607, 0x10111213, 0x14151617 ++.long 0x08090a0b, 0x0c0d0e0f, 0x18191a1b, 0x1c1d1e1f ++.long 0x05, 0x00, 0x00, 0x00 ++.long 0x02020202, 0x02020202, 0x02020202, 0x02020202 ++.long 0xffffffff, 0xffffffff, 0x00000000, 0x00000000 +Index: libgcrypt-1.10.2/cipher/poly1305.c +=================================================================== +--- libgcrypt-1.10.2.orig/cipher/poly1305.c ++++ libgcrypt-1.10.2/cipher/poly1305.c +@@ -78,11 +78,23 @@ poly1305_blocks (poly1305_context_t *ctx + #endif /* USE_S390X_ASM */ + + ++#ifdef POLY1305_USE_PPC_VEC ++ ++extern unsigned int ++gcry_poly1305_p10le_4blocks(unsigned char *key, const byte *m, size_t len); ++ ++#endif /* POLY1305_USE_PPC_VEC */ ++ ++ + static void poly1305_init (poly1305_context_t *ctx, + const byte key[POLY1305_KEYLEN]) + { + POLY1305_STATE *st = &ctx->state; + ++#ifdef POLY1305_USE_PPC_VEC ++ ctx->use_p10 = (_gcry_get_hw_features () & HWF_PPC_ARCH_3_10) != 0; ++#endif ++ + ctx->leftover = 0; + + st->h[0] = 0; +@@ -533,6 +545,7 @@ _gcry_poly1305_update_burn (poly1305_con + size_t bytes) + { + unsigned int burn = 0; ++ unsigned int nburn; + + /* handle leftover */ + if (ctx->leftover) +@@ -546,15 +559,31 @@ _gcry_poly1305_update_burn (poly1305_con + ctx->leftover += want; + if (ctx->leftover < POLY1305_BLOCKSIZE) + return 0; +- burn = poly1305_blocks (ctx, ctx->buffer, POLY1305_BLOCKSIZE, 1); ++ nburn = poly1305_blocks (ctx, ctx->buffer, POLY1305_BLOCKSIZE, 1); ++ burn = nburn > burn ? nburn : burn; + ctx->leftover = 0; + } + ++#ifdef POLY1305_USE_PPC_VEC ++ /* PPC-P10/little-endian: bulk process multiples of eight blocks */ ++ if (ctx->use_p10 && bytes >= POLY1305_BLOCKSIZE * 8) ++ { ++ size_t nblks = bytes / (POLY1305_BLOCKSIZE * 8); ++ size_t len = nblks * (POLY1305_BLOCKSIZE * 8); ++ POLY1305_STATE *st = &ctx->state; ++ nburn = gcry_poly1305_p10le_4blocks ((unsigned char *) st, m, len); ++ burn = nburn > burn ? nburn : burn; ++ m += len; ++ bytes -= len; ++ } ++#endif /* POLY1305_USE_PPC_VEC */ ++ + /* process full blocks */ + if (bytes >= POLY1305_BLOCKSIZE) + { + size_t nblks = bytes / POLY1305_BLOCKSIZE; +- burn = poly1305_blocks (ctx, m, nblks * POLY1305_BLOCKSIZE, 1); ++ nburn = poly1305_blocks (ctx, m, nblks * POLY1305_BLOCKSIZE, 1); ++ burn = nburn > burn ? nburn : burn; + m += nblks * POLY1305_BLOCKSIZE; + bytes -= nblks * POLY1305_BLOCKSIZE; + } +Index: libgcrypt-1.10.2/configure.ac +=================================================================== +--- libgcrypt-1.10.2.orig/configure.ac ++++ libgcrypt-1.10.2/configure.ac +@@ -2779,6 +2779,11 @@ if test "$found" = "1" ; then + powerpc64le-*-*) + # Build with the ppc8 vector implementation + GCRYPT_ASM_CIPHERS="$GCRYPT_ASM_CIPHERS chacha20-ppc.lo" ++ # Build with the assembly implementation ++ if test "$gcry_cv_gcc_inline_asm_ppc_altivec" = "yes" && ++ test "$gcry_cv_gcc_inline_asm_ppc_arch_3_00" = "yes" ; then ++ GCRYPT_ASM_CIPHERS="$GCRYPT_ASM_CIPHERS chacha20-p10le-8x.lo" ++ fi + ;; + powerpc64-*-*) + # Build with the ppc8 vector implementation +@@ -3117,6 +3122,13 @@ case "${host}" in + s390x-*-*) + GCRYPT_ASM_DIGESTS="$GCRYPT_ASM_DIGESTS poly1305-s390x.lo" + ;; ++ powerpc64le-*-*) ++ # Build with the assembly implementation ++ if test "$gcry_cv_gcc_inline_asm_ppc_altivec" = "yes" && ++ test "$gcry_cv_gcc_inline_asm_ppc_arch_3_00" = "yes" ; then ++ GCRYPT_ASM_DIGESTS="$GCRYPT_ASM_DIGESTS poly1305-p10le.lo" ++ fi ++ ;; + esac + + LIST_MEMBER(scrypt, $enabled_kdfs) diff --git a/libgcrypt-Disable-SHA3-s390x-acceleration-for-CSHAKE.patch b/libgcrypt-Disable-SHA3-s390x-acceleration-for-CSHAKE.patch new file mode 100644 index 0000000..ee40bc2 --- /dev/null +++ b/libgcrypt-Disable-SHA3-s390x-acceleration-for-CSHAKE.patch @@ -0,0 +1,61 @@ +From 2486d9b5ae015c1786cb84466a751da4bc0d7122 Mon Sep 17 00:00:00 2001 +From: Jussi Kivilinna +Date: Thu, 20 Jun 2024 20:10:09 +0300 +Subject: Disable SHA3 s390x acceleration for CSHAKE + +* cipher/keccak.c (keccak_final_s390x): Add assert check for +expected SHAKE suffix. +(_gcry_cshake_customize, cshake_hash_buffers): Disable s390x +acceleration when selecting CSHAKE suffix. +-- + +Signed-off-by: Jussi Kivilinna + +diff --git a/cipher/keccak.c b/cipher/keccak.c +index aaf83a62..44cc9f71 100644 +--- a/cipher/keccak.c ++++ b/cipher/keccak.c +@@ -745,6 +745,8 @@ keccak_final_s390x (void *context) + } + else + { ++ gcry_assert(ctx->suffix == SHAKE_DELIMITED_SUFFIX); ++ + klmd_shake_execute (ctx->kimd_func, &ctx->state, NULL, 0, ctx->buf, + ctx->count); + ctx->count = 0; +@@ -1497,9 +1499,14 @@ _gcry_cshake_customize (void *context, struct gcry_cshake_customization *p) + /* No customization */ + return 0; + ++ ctx->suffix = CSHAKE_DELIMITED_SUFFIX; ++#ifdef USE_S390X_CRYPTO ++ /* CSHAKE suffix is not supported by s390x/kimd. */ ++ ctx->kimd_func = 0; ++#endif ++ + len_written = cshake_input_n (ctx, p->n, p->n_len); + cshake_input_s (ctx, p->s, p->s_len, len_written); +- ctx->suffix = CSHAKE_DELIMITED_SUFFIX; + return 0; + } + +@@ -1536,9 +1543,14 @@ cshake_hash_buffers (const gcry_md_spec_t *spec, void *outbuf, size_t nbytes, + size_t s_len = iov[1].len; + size_t len; + ++ ctx.suffix = CSHAKE_DELIMITED_SUFFIX; ++#ifdef USE_S390X_CRYPTO ++ /* CSHAKE suffix is not supported by s390x/kimd. */ ++ ctx.kimd_func = 0; ++#endif ++ + len = cshake_input_n (&ctx, n, n_len); + cshake_input_s (&ctx, s, s_len, len); +- ctx.suffix = CSHAKE_DELIMITED_SUFFIX; + } + iovcnt -= 2; + iov += 2; +-- +2.49.0 + diff --git a/libgcrypt-FIPS-SLI-hash-mac.patch b/libgcrypt-FIPS-SLI-hash-mac.patch new file mode 100644 index 0000000..ff03fae --- /dev/null +++ b/libgcrypt-FIPS-SLI-hash-mac.patch @@ -0,0 +1,172 @@ +Index: libgcrypt-1.11.1/doc/gcrypt.texi +=================================================================== +--- libgcrypt-1.11.1.orig/doc/gcrypt.texi ++++ libgcrypt-1.11.1/doc/gcrypt.texi +@@ -998,13 +998,21 @@ certification. If the function is approv + @code{GPG_ERR_NO_ERROR} (other restrictions might still apply). + Otherwise @code{GPG_ERR_NOT_SUPPORTED} is returned. + +-@item GCRYCTL_FIPS_SERVICE_INDICATOR_MAC; Arguments: enum gcry_mac_algos ++@item GCRYCTL_FIPS_SERVICE_INDICATOR_HASH; Arguments: enum gcry_md_algos + +-Check if the given MAC is approved under the current FIPS 140-3 +-certification. If the MAC is approved, this function returns +-@code{GPG_ERR_NO_ERROR}. Otherwise @code{GPG_ERR_NOT_SUPPORTED} ++Check if the given HASH is approved under the current FIPS 140-3 ++certification. If the HASH is approved, this function returns ++@code{GPS_ERR_NO_ERROR}. Otherwise @code{GPG_ERR_NOT_SUPPORTED} + is returned. + ++@item GCRYCTL_FIPS_SERVICE_INDICATOR_MAC; Arguments: enum gcry_mac_algos [, unsigned int] ++ ++Check if the given MAC is approved under the current FIPS 140-3 ++certification. The second parameter provides the keylen (if the ++algorithm supports different key sizes). If the MAC is approved, ++this function returns @code{GPS_ERR_NO_ERROR}. Otherwise ++@code{GPG_ERR_NOT_SUPPORTED} is returned. ++ + @item GCRYCTL_FIPS_SERVICE_INDICATOR_MD; Arguments: enum gcry_md_algos + + Check if the given message digest algorithm is approved under the current +Index: libgcrypt-1.11.1/src/fips.c +=================================================================== +--- libgcrypt-1.11.1.orig/src/fips.c ++++ libgcrypt-1.11.1/src/fips.c +@@ -512,31 +512,6 @@ _gcry_fips_indicator_pk (va_list arg_ptr + } + + int +-_gcry_fips_indicator_mac (va_list arg_ptr) +-{ +- enum gcry_mac_algos alg = va_arg (arg_ptr, enum gcry_mac_algos); +- +- switch (alg) +- { +- case GCRY_MAC_CMAC_AES: +- case GCRY_MAC_HMAC_SHA1: +- case GCRY_MAC_HMAC_SHA224: +- case GCRY_MAC_HMAC_SHA256: +- case GCRY_MAC_HMAC_SHA384: +- case GCRY_MAC_HMAC_SHA512: +- case GCRY_MAC_HMAC_SHA512_224: +- case GCRY_MAC_HMAC_SHA512_256: +- case GCRY_MAC_HMAC_SHA3_224: +- case GCRY_MAC_HMAC_SHA3_256: +- case GCRY_MAC_HMAC_SHA3_384: +- case GCRY_MAC_HMAC_SHA3_512: +- return GPG_ERR_NO_ERROR; +- default: +- return GPG_ERR_NOT_SUPPORTED; +- } +-} +- +-int + _gcry_fips_indicator_md (va_list arg_ptr) + { + enum gcry_md_algos alg = va_arg (arg_ptr, enum gcry_md_algos); +@@ -647,6 +622,62 @@ _gcry_fips_indicator_pk_flags (va_list a + return GPG_ERR_NOT_SUPPORTED; + } + ++int ++_gcry_fips_indicator_hash (va_list arg_ptr) ++{ ++ enum gcry_md_algos alg = va_arg (arg_ptr, enum gcry_md_algos); ++ ++ switch (alg) ++ { ++ case GCRY_MD_SHA1: ++ case GCRY_MD_SHA224: ++ case GCRY_MD_SHA256: ++ case GCRY_MD_SHA384: ++ case GCRY_MD_SHA512: ++ case GCRY_MD_SHA512_224: ++ case GCRY_MD_SHA512_256: ++ case GCRY_MD_SHA3_224: ++ case GCRY_MD_SHA3_256: ++ case GCRY_MD_SHA3_384: ++ case GCRY_MD_SHA3_512: ++ case GCRY_MD_SHAKE128: ++ case GCRY_MD_SHAKE256: ++ return GPG_ERR_NO_ERROR; ++ default: ++ return GPG_ERR_NOT_SUPPORTED; ++ } ++} ++ ++int ++_gcry_fips_indicator_mac (va_list arg_ptr) ++{ ++ enum gcry_mac_algos alg = va_arg (arg_ptr, enum gcry_mac_algos); ++ unsigned int keylen = va_arg (arg_ptr, unsigned int); ++ ++ switch (alg) ++ { ++ case GCRY_MAC_HMAC_SHA1: ++ case GCRY_MAC_HMAC_SHA224: ++ case GCRY_MAC_HMAC_SHA256: ++ case GCRY_MAC_HMAC_SHA384: ++ case GCRY_MAC_HMAC_SHA512: ++ case GCRY_MAC_HMAC_SHA512_224: ++ case GCRY_MAC_HMAC_SHA512_256: ++ case GCRY_MAC_HMAC_SHA3_224: ++ case GCRY_MAC_HMAC_SHA3_256: ++ case GCRY_MAC_HMAC_SHA3_384: ++ case GCRY_MAC_HMAC_SHA3_512: ++ if (keylen >= 112) { ++ return GPG_ERR_NO_ERROR; ++ } ++ case GCRY_MAC_CMAC_AES: ++ if (keylen == 128 || keylen == 192 || keylen == 256) { ++ return GPG_ERR_NO_ERROR; ++ } ++ default: ++ return GPG_ERR_NOT_SUPPORTED; ++ } ++} + + /* This is a test on whether the library is in the error or + operational state. */ +Index: libgcrypt-1.11.1/src/g10lib.h +=================================================================== +--- libgcrypt-1.11.1.orig/src/g10lib.h ++++ libgcrypt-1.11.1/src/g10lib.h +@@ -478,6 +478,7 @@ void _gcry_fips_signal_error (const char + gpg_err_code_t _gcry_fips_indicator (void); + + int _gcry_fips_indicator_cipher (va_list arg_ptr); ++int _gcry_fips_indicator_hash (va_list arg_ptr); + int _gcry_fips_indicator_mac (va_list arg_ptr); + int _gcry_fips_indicator_md (va_list arg_ptr); + int _gcry_fips_indicator_kdf (va_list arg_ptr); +Index: libgcrypt-1.11.1/src/gcrypt.h.in +=================================================================== +--- libgcrypt-1.11.1.orig/src/gcrypt.h.in ++++ libgcrypt-1.11.1/src/gcrypt.h.in +@@ -338,7 +338,8 @@ enum gcry_ctl_cmds + GCRYCTL_MD_CUSTOMIZE = 88, + GCRYCTL_FIPS_SERVICE_INDICATOR = 89, + GCRYCTL_FIPS_REJECT_NON_FIPS = 90, +- GCRYCTL_FIPS_SERVICE_INDICATOR_PK = 91 ++ GCRYCTL_FIPS_SERVICE_INDICATOR_PK = 91, ++ GCRYCTL_FIPS_SERVICE_INDICATOR_HASH = 92 + }; + + /* Perform various operations defined by CMD. */ +Index: libgcrypt-1.11.1/src/global.c +=================================================================== +--- libgcrypt-1.11.1.orig/src/global.c ++++ libgcrypt-1.11.1/src/global.c +@@ -808,6 +808,12 @@ _gcry_vcontrol (enum gcry_ctl_cmds cmd, + rc = _gcry_fips_indicator_cipher (arg_ptr); + break; + ++ case GCRYCTL_FIPS_SERVICE_INDICATOR_HASH: ++ /* Get FIPS Service Indicator for a given HASH. Returns GPG_ERR_NO_ERROR ++ * if algorithm is allowed or GPG_ERR_NOT_SUPPORTED otherwise */ ++ rc = _gcry_fips_indicator_hash (arg_ptr); ++ break; ++ + case GCRYCTL_FIPS_SERVICE_INDICATOR_MAC: + /* Get FIPS Service Indicator for a given message authentication code. + * Returns GPG_ERR_NO_ERROR if algorithm is allowed or diff --git a/libgcrypt-FIPS-SLI-kdf-leylength.patch b/libgcrypt-FIPS-SLI-kdf-leylength.patch new file mode 100644 index 0000000..d3693ac --- /dev/null +++ b/libgcrypt-FIPS-SLI-kdf-leylength.patch @@ -0,0 +1,60 @@ +Index: libgcrypt-1.11.0/src/fips.c +=================================================================== +--- libgcrypt-1.11.0.orig/src/fips.c ++++ libgcrypt-1.11.0/src/fips.c +@@ -523,10 +523,15 @@ int + _gcry_fips_indicator_kdf (va_list arg_ptr) + { + enum gcry_kdf_algos alg = va_arg (arg_ptr, enum gcry_kdf_algos); ++ unsigned int keylen = 0; + + switch (alg) + { + case GCRY_KDF_PBKDF2: ++ keylen = va_arg (arg_ptr, unsigned int); ++ if (keylen < 112) { ++ return GPG_ERR_NOT_SUPPORTED; ++ } + return GPG_ERR_NO_ERROR; + default: + return GPG_ERR_NOT_SUPPORTED; +Index: libgcrypt-1.11.0/doc/gcrypt.texi +=================================================================== +--- libgcrypt-1.11.0.orig/doc/gcrypt.texi ++++ libgcrypt-1.11.0/doc/gcrypt.texi +@@ -983,12 +983,13 @@ is approved under the current FIPS 140-3 + combination is approved, this function returns @code{GPG_ERR_NO_ERROR}. + Otherwise @code{GPG_ERR_NOT_SUPPORTED} is returned. + +-@item GCRYCTL_FIPS_SERVICE_INDICATOR_KDF; Arguments: enum gcry_kdf_algos ++@item GCRYCTL_FIPS_SERVICE_INDICATOR_KDF; Arguments: enum gcry_kdf_algos [, unsigned int] + + Check if the given KDF is approved under the current FIPS 140-3 +-certification. If the KDF is approved, this function returns +-@code{GPG_ERR_NO_ERROR}. Otherwise @code{GPG_ERR_NOT_SUPPORTED} +-is returned. ++certification. The second parameter provides the keylength in bits. ++Keylength values of less that 112 bits are considered non-approved. ++If the KDF is approved, this function returns @code{GPG_ERR_NO_ERROR}. ++Otherwise @code{GPG_ERR_NOT_SUPPORTED} is returned. + + @item GCRYCTL_FIPS_SERVICE_INDICATOR_FUNCTION; Arguments: const char * + +Index: libgcrypt-1.11.0/tests/t-kdf.c +=================================================================== +--- libgcrypt-1.11.0.orig/tests/t-kdf.c ++++ libgcrypt-1.11.0/tests/t-kdf.c +@@ -1889,7 +1889,12 @@ check_fips_indicators (void) + for (i = 0; i < sizeof(kdf_algos) / sizeof(*kdf_algos); i++) + { + int is_fips_kdf_algo = 0; +- gcry_error_t err = gcry_control (GCRYCTL_FIPS_SERVICE_INDICATOR_KDF, kdf_algos[i]); ++ gcry_error_t err; ++ // On SUSE/openSUSE builds PBKDF2 with keysize < 112 is not allowed ++ if (kdf_algos[i] == GCRY_KDF_PBKDF2) ++ err = gcry_control (GCRYCTL_FIPS_SERVICE_INDICATOR_KDF, kdf_algos[i], 112); ++ else ++ err = gcry_control (GCRYCTL_FIPS_SERVICE_INDICATOR_KDF, kdf_algos[i]); + + if (verbose) + fprintf (stderr, "checking FIPS indicator for KDF %d: %s\n", diff --git a/libgcrypt-FIPS-SLI-pk.patch b/libgcrypt-FIPS-SLI-pk.patch new file mode 100644 index 0000000..4dd3d97 --- /dev/null +++ b/libgcrypt-FIPS-SLI-pk.patch @@ -0,0 +1,177 @@ +Index: libgcrypt-1.11.1/src/fips.c +=================================================================== +--- libgcrypt-1.11.1.orig/src/fips.c ++++ libgcrypt-1.11.1/src/fips.c +@@ -38,6 +38,7 @@ + + #include "g10lib.h" + #include "cipher-proto.h" ++#include "cipher.h" + #include "../random/random.h" + + /* The states of the finite state machine used in fips mode. */ +@@ -420,6 +421,94 @@ _gcry_fips_indicator_cipher (va_list arg + default: + return GPG_ERR_NOT_SUPPORTED; + } ++} ++ ++/* FIPS approved curves, extracted from: ++ * cipher/ecc-curves.c:curve_aliases[] and domain_parms[]. */ ++static const struct ++{ ++ const char *name; /* Our name. */ ++ const char *other; /* Other name. */ ++} fips_approved_curve[] = ++ { ++ /* "NIST P-192" is non-approved if FIPS 140-3 */ ++ /* { "NIST P-192", "1.2.840.10045.3.1.1" }, /\* X9.62 OID *\/ */ ++ /* { "NIST P-192", "prime192v1" }, /\* X9.62 name. *\/ */ ++ /* { "NIST P-192", "secp192r1" }, /\* SECP name. *\/ */ ++ /* { "NIST P-192", "nistp192" }, /\* rfc5656. *\/ */ ++ ++ { "NIST P-224", "secp224r1" }, ++ { "NIST P-224", "1.3.132.0.33" }, /* SECP OID. */ ++ { "NIST P-224", "nistp224" }, /* rfc5656. */ ++ ++ { "NIST P-256", "1.2.840.10045.3.1.7" }, /* From NIST SP 800-78-1. */ ++ { "NIST P-256", "prime256v1" }, ++ { "NIST P-256", "secp256r1" }, ++ { "NIST P-256", "nistp256" }, /* rfc5656. */ ++ ++ { "NIST P-384", "secp384r1" }, ++ { "NIST P-384", "1.3.132.0.34" }, ++ { "NIST P-384", "nistp384" }, /* rfc5656. */ ++ ++ { "NIST P-521", "secp521r1" }, ++ { "NIST P-521", "1.3.132.0.35" }, ++ { "NIST P-521", "nistp521" }, /* rfc5656. */ ++ { NULL, NULL} ++ }; ++ ++enum pk_operation convert_from_pk_usage(unsigned int pk_usage) ++{ ++ switch (pk_usage) ++ { ++ case GCRY_PK_USAGE_SIGN: ++ return PUBKEY_OP_SIGN; ++ case GCRY_PK_USAGE_ENCR: ++ return PUBKEY_OP_ENCRYPT; ++ default: ++ return PUBKEY_OP_DECRYPT; ++ } ++} ++ ++int ++_gcry_fips_indicator_pk (va_list arg_ptr) ++{ ++ enum gcry_pk_algos alg = va_arg (arg_ptr, enum gcry_pk_algos); ++ enum pk_operation oper; ++ unsigned int keylen; ++ const char *curve_name; ++ ++ switch (alg) ++ { ++ case GCRY_PK_RSA: ++ case GCRY_PK_RSA_E: ++ case GCRY_PK_RSA_S: ++ oper = convert_from_pk_usage(va_arg (arg_ptr, unsigned int)); ++ switch (oper) ++ { ++ case PUBKEY_OP_ENCRYPT: ++ case PUBKEY_OP_DECRYPT: ++ return GPG_ERR_NOT_SUPPORTED; ++ default: ++ keylen = va_arg (arg_ptr, unsigned int); ++ if (keylen < 2048) ++ return GPG_ERR_NOT_SUPPORTED; ++ return GPG_ERR_NO_ERROR; ++ } ++ case GCRY_PK_ECC: ++ case GCRY_PK_ECDH: ++ case GCRY_PK_ECDSA: ++ curve_name = va_arg (arg_ptr, const char *); ++ for (int idx = 0; fips_approved_curve[idx].name; ++idx) ++ { ++ /* Check for the usual name and an alias. */ ++ if (!strcmp (curve_name, fips_approved_curve[idx].name) || ++ !strcmp (curve_name, fips_approved_curve[idx].other)) ++ return GPG_ERR_NO_ERROR; ++ } ++ return GPG_ERR_NOT_SUPPORTED; ++ default: ++ return GPG_ERR_NOT_SUPPORTED; ++ } + } + + int +Index: libgcrypt-1.11.1/src/gcrypt.h.in +=================================================================== +--- libgcrypt-1.11.1.orig/src/gcrypt.h.in ++++ libgcrypt-1.11.1/src/gcrypt.h.in +@@ -337,7 +337,8 @@ enum gcry_ctl_cmds + GCRYCTL_FIPS_SERVICE_INDICATOR_PK_FLAGS = 87, + GCRYCTL_MD_CUSTOMIZE = 88, + GCRYCTL_FIPS_SERVICE_INDICATOR = 89, +- GCRYCTL_FIPS_REJECT_NON_FIPS = 90 ++ GCRYCTL_FIPS_REJECT_NON_FIPS = 90, ++ GCRYCTL_FIPS_SERVICE_INDICATOR_PK = 91 + }; + + /* Perform various operations defined by CMD. */ +Index: libgcrypt-1.11.1/doc/gcrypt.texi +=================================================================== +--- libgcrypt-1.11.1.orig/doc/gcrypt.texi ++++ libgcrypt-1.11.1/doc/gcrypt.texi +@@ -1010,6 +1010,19 @@ Check if the given message digest algori + FIPS 140-3 certification. If the algorithm is approved, this function returns + @code{GPG_ERR_NO_ERROR}. Otherwise @code{GPG_ERR_NOT_SUPPORTED} is returned. + ++@item GCRYCTL_FIPS_SERVICE_INDICATOR_PK; Arguments: enum gcry_pk_algos [, constantsGCRY_PK_USAGE_ENCR or GCRY_PK_USAGE_SIGN, unsigned int (only for GCRY_PK_RSA)] [, const char * (only for GCRY_PK_ECC, GCRY_PK_ECDH or GCRY_PK_ECDSA)] ++ ++Check if the given asymmetric cipher is approved under the current ++FIPS 140-3 certification. For GCRY_PK_RSA, two additional parameter ++are required: first describes the purpose of the algorithm through one ++of the constants (GCRY_PK_USAGE_ENCR for encryption or decryption ++operations; GCRY_PK_USAGE_SIGN for sign or verify operations). Second ++one is the key length. For GCRY_PK_ECC, GCRY_PK_ECDH and ++GCRY_PK_ECDSA, only a single parameter is needed: the curve name or ++its alias as @code{const char *}. If the combination is approved, this ++function returns @code{GPG_ERR_NO_ERROR}. Otherwise ++@code{GPG_ERR_NOT_SUPPORTED} is returned. ++ + @item GCRYCTL_FIPS_SERVICE_INDICATOR_PK_FLAGS; Arguments: const char * + + Check if the given public key operation flag or s-expression object name is +Index: libgcrypt-1.11.1/src/g10lib.h +=================================================================== +--- libgcrypt-1.11.1.orig/src/g10lib.h ++++ libgcrypt-1.11.1/src/g10lib.h +@@ -482,6 +482,7 @@ int _gcry_fips_indicator_mac (va_list ar + int _gcry_fips_indicator_md (va_list arg_ptr); + int _gcry_fips_indicator_kdf (va_list arg_ptr); + int _gcry_fips_indicator_function (va_list arg_ptr); ++int _gcry_fips_indicator_pk (va_list arg_ptr); + int _gcry_fips_indicator_pk_flags (va_list arg_ptr); + + int _gcry_fips_is_operational (void); +Index: libgcrypt-1.11.1/src/global.c +=================================================================== +--- libgcrypt-1.11.1.orig/src/global.c ++++ libgcrypt-1.11.1/src/global.c +@@ -842,6 +842,15 @@ _gcry_vcontrol (enum gcry_ctl_cmds cmd, + rc = _gcry_fips_indicator_pk_flags (arg_ptr); + break; + ++ case GCRYCTL_FIPS_SERVICE_INDICATOR_PK: ++ /* Get FIPS Service Indicator for a given asymmetric algorithm. For ++ * GCRY_PK_RSA, an additional parameter for the operation mode is ++ * required. For ECC, ECDH and ECDSA, the additional parameter is the ++ * curve name or its alias. Returns GPG_ERR_NO_ERROR if the ++ * algorithm is allowed or GPG_ERR_NOT_SUPPORTED otherwise. */ ++ rc = _gcry_fips_indicator_pk (arg_ptr); ++ break; ++ + case PRIV_CTL_INIT_EXTRNG_TEST: /* Init external random test. */ + rc = GPG_ERR_NOT_SUPPORTED; + break; diff --git a/libgcrypt-FIPS-jitter-errorcodes.patch b/libgcrypt-FIPS-jitter-errorcodes.patch new file mode 100644 index 0000000..d6d314e --- /dev/null +++ b/libgcrypt-FIPS-jitter-errorcodes.patch @@ -0,0 +1,16 @@ +Index: libgcrypt-1.10.3/random/rndjent.c +=================================================================== +--- libgcrypt-1.10.3.orig/random/rndjent.c ++++ libgcrypt-1.10.3/random/rndjent.c +@@ -319,7 +319,10 @@ _gcry_rndjent_poll (void (*add)(const vo + jent_rng_totalcalls++; + rc = jent_read_entropy_safe (&jent_rng_collector, buffer, n); + if (rc < 0) +- break; ++ { ++ fips_signal_error ("jitter entropy failed"); ++ break; ++ } + /* We need to hash the output to conform to the BSI + * NTG.1 specs. */ + _gcry_md_hash_buffer (GCRY_MD_SHA256, buffer, buffer, rc); diff --git a/libgcrypt-FIPS-jitter-standalone.patch b/libgcrypt-FIPS-jitter-standalone.patch new file mode 100644 index 0000000..fb375fa --- /dev/null +++ b/libgcrypt-FIPS-jitter-standalone.patch @@ -0,0 +1,183 @@ +Index: libgcrypt-1.11.1/random/Makefile.am +=================================================================== +--- libgcrypt-1.11.1.orig/random/Makefile.am ++++ libgcrypt-1.11.1/random/Makefile.am +@@ -21,7 +21,7 @@ + # Need to include ../src in addition to top_srcdir because gcrypt.h is + # a built header. + AM_CPPFLAGS = -I../src -I$(top_srcdir)/src +-AM_CFLAGS = $(GPG_ERROR_CFLAGS) ++AM_CFLAGS = $(GPG_ERROR_CFLAGS) -ljitterentropy + + noinst_LTLIBRARIES = librandom.la + +@@ -44,14 +44,7 @@ rndgetentropy.c \ + rndoldlinux.c \ + rndegd.c \ + rndunix.c \ +-rndw32.c \ +-jitterentropy-gcd.c jitterentropy-gcd.h \ +-jitterentropy-health.c jitterentropy-health.h \ +-jitterentropy-noise.c jitterentropy-noise.h \ +-jitterentropy-sha3.c jitterentropy-sha3.h \ +-jitterentropy-timer.c jitterentropy-timer.h \ +-jitterentropy-base.h \ +-jitterentropy-base.c jitterentropy.h jitterentropy-base-user.h ++rndw32.c + + # The rndjent module needs to be compiled without optimization. */ + if ENABLE_O_FLAG_MUNGING +@@ -60,20 +53,8 @@ else + o_flag_munging = cat + endif + +-rndjent.o: $(srcdir)/rndjent.c jitterentropy-base-user.h \ +- $(srcdir)/jitterentropy-gcd.c $(srcdir)/jitterentropy-gcd.h \ +- $(srcdir)/jitterentropy-health.c $(srcdir)/jitterentropy-health.h \ +- $(srcdir)/jitterentropy-noise.c $(srcdir)/jitterentropy-noise.h \ +- $(srcdir)/jitterentropy-sha3.c $(srcdir)/jitterentropy-sha3.h \ +- $(srcdir)/jitterentropy-timer.c $(srcdir)/jitterentropy-timer.h \ +- $(srcdir)/jitterentropy-base.c $(srcdir)/jitterentropy.h ++rndjent.o: $(srcdir)/rndjent.c + `echo $(COMPILE) -c $(srcdir)/rndjent.c | $(o_flag_munging) ` + +-rndjent.lo: $(srcdir)/rndjent.c jitterentropy-base-user.h \ +- $(srcdir)/jitterentropy-gcd.c $(srcdir)/jitterentropy-gcd.h \ +- $(srcdir)/jitterentropy-health.c $(srcdir)/jitterentropy-health.h \ +- $(srcdir)/jitterentropy-noise.c $(srcdir)/jitterentropy-noise.h \ +- $(srcdir)/jitterentropy-sha3.c $(srcdir)/jitterentropy-sha3.h \ +- $(srcdir)/jitterentropy-timer.c $(srcdir)/jitterentropy-timer.h \ +- $(srcdir)/jitterentropy-base.c $(srcdir)/jitterentropy.h ++rndjent.lo: $(srcdir)/rndjent.c + `echo $(LTCOMPILE) -c $(srcdir)/rndjent.c | $(o_flag_munging) ` +Index: libgcrypt-1.11.1/random/rndjent.c +=================================================================== +--- libgcrypt-1.11.1.orig/random/rndjent.c ++++ libgcrypt-1.11.1/random/rndjent.c +@@ -94,17 +94,12 @@ + * jitterentropy-user-base.h file. */ + + /* Tell jitterentropy* that all functions shall be static. */ +-#define JENT_PRIVATE_COMPILE 1 ++#undef JENT_PRIVATE_COMPILE + +-#include "jitterentropy-base.c" + #ifdef JENT_CONF_ENABLE_INTERNAL_TIMER + #include + #endif /* JENT_CONF_ENABLE_INTERNAL_TIMER */ +-#include "jitterentropy-gcd.c" +-#include "jitterentropy-health.c" +-#include "jitterentropy-noise.c" +-#include "jitterentropy-sha3.c" +-#include "jitterentropy-timer.c" ++#include + + /* This is the lock we use to serialize access to this RNG. The extra + * integer variable is only used to check the locking state; that is, +Index: libgcrypt-1.11.1/random/Makefile.in +=================================================================== +--- libgcrypt-1.11.1.orig/random/Makefile.in ++++ libgcrypt-1.11.1/random/Makefile.in +@@ -147,12 +147,7 @@ am__v_at_1 = + DEFAULT_INCLUDES = -I.@am__isrc@ -I$(top_builddir) + depcomp = $(SHELL) $(top_srcdir)/build-aux/depcomp + am__maybe_remake_depfiles = depfiles +-am__depfiles_remade = ./$(DEPDIR)/jitterentropy-base.Plo \ +- ./$(DEPDIR)/jitterentropy-gcd.Plo \ +- ./$(DEPDIR)/jitterentropy-health.Plo \ +- ./$(DEPDIR)/jitterentropy-noise.Plo \ +- ./$(DEPDIR)/jitterentropy-sha3.Plo \ +- ./$(DEPDIR)/jitterentropy-timer.Plo \ ++am__depfiles_remade = \ + ./$(DEPDIR)/random-csprng.Plo ./$(DEPDIR)/random-drbg.Plo \ + ./$(DEPDIR)/random-system.Plo ./$(DEPDIR)/random.Plo \ + ./$(DEPDIR)/rndegd.Plo ./$(DEPDIR)/rndgetentropy.Plo \ +@@ -375,7 +370,7 @@ top_srcdir = @top_srcdir@ + # Need to include ../src in addition to top_srcdir because gcrypt.h is + # a built header. + AM_CPPFLAGS = -I../src -I$(top_srcdir)/src +-AM_CFLAGS = $(GPG_ERROR_CFLAGS) ++AM_CFLAGS = $(GPG_ERROR_CFLAGS) -ljitterentropy + noinst_LTLIBRARIES = librandom.la + GCRYPT_MODULES = @GCRYPT_RANDOM@ + librandom_la_DEPENDENCIES = $(GCRYPT_MODULES) +@@ -394,14 +389,7 @@ rndgetentropy.c \ + rndoldlinux.c \ + rndegd.c \ + rndunix.c \ +-rndw32.c \ +-jitterentropy-gcd.c jitterentropy-gcd.h \ +-jitterentropy-health.c jitterentropy-health.h \ +-jitterentropy-noise.c jitterentropy-noise.h \ +-jitterentropy-sha3.c jitterentropy-sha3.h \ +-jitterentropy-timer.c jitterentropy-timer.h \ +-jitterentropy-base.h \ +-jitterentropy-base.c jitterentropy.h jitterentropy-base-user.h ++rndw32.c + + @ENABLE_O_FLAG_MUNGING_FALSE@o_flag_munging = cat + +@@ -461,12 +449,6 @@ mostlyclean-compile: + distclean-compile: + -rm -f *.tab.c + +-@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/jitterentropy-base.Plo@am__quote@ # am--include-marker +-@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/jitterentropy-gcd.Plo@am__quote@ # am--include-marker +-@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/jitterentropy-health.Plo@am__quote@ # am--include-marker +-@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/jitterentropy-noise.Plo@am__quote@ # am--include-marker +-@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/jitterentropy-sha3.Plo@am__quote@ # am--include-marker +-@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/jitterentropy-timer.Plo@am__quote@ # am--include-marker + @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/random-csprng.Plo@am__quote@ # am--include-marker + @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/random-drbg.Plo@am__quote@ # am--include-marker + @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/random-system.Plo@am__quote@ # am--include-marker +@@ -636,12 +618,6 @@ clean-am: clean-generic clean-libtool cl + mostlyclean-am + + distclean: distclean-am +- -rm -f ./$(DEPDIR)/jitterentropy-base.Plo +- -rm -f ./$(DEPDIR)/jitterentropy-gcd.Plo +- -rm -f ./$(DEPDIR)/jitterentropy-health.Plo +- -rm -f ./$(DEPDIR)/jitterentropy-noise.Plo +- -rm -f ./$(DEPDIR)/jitterentropy-sha3.Plo +- -rm -f ./$(DEPDIR)/jitterentropy-timer.Plo + -rm -f ./$(DEPDIR)/random-csprng.Plo + -rm -f ./$(DEPDIR)/random-drbg.Plo + -rm -f ./$(DEPDIR)/random-system.Plo +@@ -698,12 +674,6 @@ install-ps-am: + installcheck-am: + + maintainer-clean: maintainer-clean-am +- -rm -f ./$(DEPDIR)/jitterentropy-base.Plo +- -rm -f ./$(DEPDIR)/jitterentropy-gcd.Plo +- -rm -f ./$(DEPDIR)/jitterentropy-health.Plo +- -rm -f ./$(DEPDIR)/jitterentropy-noise.Plo +- -rm -f ./$(DEPDIR)/jitterentropy-sha3.Plo +- -rm -f ./$(DEPDIR)/jitterentropy-timer.Plo + -rm -f ./$(DEPDIR)/random-csprng.Plo + -rm -f ./$(DEPDIR)/random-drbg.Plo + -rm -f ./$(DEPDIR)/random-system.Plo +@@ -752,22 +722,10 @@ uninstall-am: + .PRECIOUS: Makefile + + +-rndjent.o: $(srcdir)/rndjent.c jitterentropy-base-user.h \ +- $(srcdir)/jitterentropy-gcd.c $(srcdir)/jitterentropy-gcd.h \ +- $(srcdir)/jitterentropy-health.c $(srcdir)/jitterentropy-health.h \ +- $(srcdir)/jitterentropy-noise.c $(srcdir)/jitterentropy-noise.h \ +- $(srcdir)/jitterentropy-sha3.c $(srcdir)/jitterentropy-sha3.h \ +- $(srcdir)/jitterentropy-timer.c $(srcdir)/jitterentropy-timer.h \ +- $(srcdir)/jitterentropy-base.c $(srcdir)/jitterentropy.h ++rndjent.o: $(srcdir)/rndjent.c + `echo $(COMPILE) -c $(srcdir)/rndjent.c | $(o_flag_munging) ` + +-rndjent.lo: $(srcdir)/rndjent.c jitterentropy-base-user.h \ +- $(srcdir)/jitterentropy-gcd.c $(srcdir)/jitterentropy-gcd.h \ +- $(srcdir)/jitterentropy-health.c $(srcdir)/jitterentropy-health.h \ +- $(srcdir)/jitterentropy-noise.c $(srcdir)/jitterentropy-noise.h \ +- $(srcdir)/jitterentropy-sha3.c $(srcdir)/jitterentropy-sha3.h \ +- $(srcdir)/jitterentropy-timer.c $(srcdir)/jitterentropy-timer.h \ +- $(srcdir)/jitterentropy-base.c $(srcdir)/jitterentropy.h ++rndjent.lo: $(srcdir)/rndjent.c + `echo $(LTCOMPILE) -c $(srcdir)/rndjent.c | $(o_flag_munging) ` + + # Tell versions [3.59,3.63) of GNU make to not export all variables. diff --git a/libgcrypt-FIPS-jitter-whole-entropy.patch b/libgcrypt-FIPS-jitter-whole-entropy.patch new file mode 100644 index 0000000..6c16472 --- /dev/null +++ b/libgcrypt-FIPS-jitter-whole-entropy.patch @@ -0,0 +1,41 @@ +Index: libgcrypt-1.10.3/random/rndgetentropy.c +=================================================================== +--- libgcrypt-1.10.3.orig/random/rndgetentropy.c ++++ libgcrypt-1.10.3/random/rndgetentropy.c +@@ -53,16 +53,30 @@ _gcry_rndgetentropy_gather_random (void + + /* When using a blocking random generator try to get some entropy + * from the jitter based RNG. In this case we take up to 50% of the +- * remaining requested bytes. */ ++ * remaining requested bytes. In FIPS mode, we get all the entropy ++ * from the jitter RNG. */ + if (level >= GCRY_VERY_STRONG_RANDOM) + { + size_t n; + +- n = _gcry_rndjent_poll (add, origin, length/2); +- if (n > length/2) +- n = length/2; +- if (length > 1) +- length -= n; ++ /* In FIPS mode, use the whole length of the entropy buffer from ++ * Jitter RNG */ ++ if (fips_mode ()) ++ { ++ n = _gcry_rndjent_poll (add, origin, length); ++ if (n != length) ++ fips_signal_error ("jitter entropy failed"); ++ else ++ length = 0; ++ } ++ else ++ { ++ n = _gcry_rndjent_poll (add, origin, length/2); ++ if (n > length/2) ++ n = length/2; ++ if (length > 1) ++ length -= n; ++ } + } + + /* Enter the loop. */ diff --git a/libgcrypt-FIPS-rndjent_poll.patch b/libgcrypt-FIPS-rndjent_poll.patch new file mode 100644 index 0000000..f837842 --- /dev/null +++ b/libgcrypt-FIPS-rndjent_poll.patch @@ -0,0 +1,114 @@ +Index: libgcrypt-1.10.0/random/rndoldlinux.c +=================================================================== +--- libgcrypt-1.10.0.orig/random/rndoldlinux.c ++++ libgcrypt-1.10.0/random/rndoldlinux.c +@@ -132,7 +132,7 @@ _gcry_rndoldlinux_gather_random (void (* + volatile pid_t apid; + int fd; + int n; +- byte buffer[768]; ++ byte buffer[256]; + size_t n_hw; + size_t want = length; + size_t last_so_far = 0; +@@ -187,26 +187,43 @@ _gcry_rndoldlinux_gather_random (void (* + my_pid = apid; + } + ++ if (fips_mode()) ++ { ++ if (level >= GCRY_VERY_STRONG_RANDOM) ++ { ++ size_t n; + +- /* First read from a hardware source. Note that _gcry_rndhw_poll_slow lets +- it account only for up to 50% (or 25% for RDRAND) of the requested +- bytes. */ +- n_hw = _gcry_rndhw_poll_slow (add, origin, length); +- if (length > 1) +- length -= n_hw; +- +- /* When using a blocking random generator try to get some entropy +- * from the jitter based RNG. In this case we take up to 50% of the +- * remaining requested bytes. */ +- if (level >= GCRY_VERY_STRONG_RANDOM) +- { +- n_hw = _gcry_rndjent_poll (add, origin, length/2); +- if (n_hw > length/2) +- n_hw = length/2; ++ n = _gcry_rndjent_poll (add, origin, length); ++ if (n == 0) ++ log_fatal ("unexpected error from rndjent: %s\n", ++ strerror (errno)); ++ if (n > length) ++ n = length; ++ if (length > 1) ++ length -= n; ++ } ++ } ++ else ++ { ++ /* First read from a hardware source. Note that _gcry_rndhw_poll_slow lets ++ it account only for up to 50% (or 25% for RDRAND) of the requested ++ bytes. */ ++ n_hw = _gcry_rndhw_poll_slow (add, origin, length); + if (length > 1) + length -= n_hw; +- } + ++ /* When using a blocking random generator try to get some entropy ++ * from the jitter based RNG. In this case we take up to 50% of the ++ * remaining requested bytes. */ ++ if (level >= GCRY_VERY_STRONG_RANDOM) ++ { ++ n_hw = _gcry_rndjent_poll (add, origin, length/2); ++ if (n_hw > length/2) ++ n_hw = length/2; ++ if (length > 1) ++ length -= n_hw; ++ } ++ } + + /* Open the requested device. The first time a device is to be + opened we fail with a fatal error if the device does not exists. +@@ -262,8 +279,6 @@ _gcry_rndoldlinux_gather_random (void (* + do + { + nbytes = length < sizeof(buffer)? length : sizeof(buffer); +- if (nbytes > 256) +- nbytes = 256; + _gcry_pre_syscall (); + ret = getentropy (buffer, nbytes); + _gcry_post_syscall (); +Index: libgcrypt-1.10.0/random/rndjent.c +=================================================================== +--- libgcrypt-1.10.0.orig/random/rndjent.c ++++ libgcrypt-1.10.0/random/rndjent.c +@@ -279,13 +279,24 @@ _gcry_rndjent_poll (void (*add)(const vo + if (!jent_rng_is_initialized) + { + /* Auto-initialize. */ +- jent_rng_is_initialized = 1; + jent_entropy_collector_free (jent_rng_collector); + jent_rng_collector = NULL; + if ( !(_gcry_random_read_conf () & RANDOM_CONF_DISABLE_JENT)) + { +- if (!jent_entropy_init ()) +- jent_rng_collector = jent_entropy_collector_alloc (1, 0); ++ if (!jent_entropy_init_ex (1, 0)) ++ { ++ jent_rng_collector = jent_entropy_collector_alloc (1, 0); ++ jent_rng_is_initialized = 1; ++ } ++ } ++ } ++ ++ if (!jent_rng_collector) ++ { ++ if (!jent_entropy_init_ex (1, 0)) ++ { ++ jent_rng_collector = jent_entropy_collector_alloc (1, 0); ++ jent_rng_is_initialized = 1; + } + } + diff --git a/libgcrypt-Fix-the-previous-change.patch b/libgcrypt-Fix-the-previous-change.patch new file mode 100644 index 0000000..4735528 --- /dev/null +++ b/libgcrypt-Fix-the-previous-change.patch @@ -0,0 +1,45 @@ +From b4eb23dc01a40e13d542fbfc5169dffa7fae5677 Mon Sep 17 00:00:00 2001 +From: NIIBE Yutaka +Date: Thu, 19 Dec 2024 14:16:02 +0900 +Subject: [PATCH 13/19] Fix the previous change. +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* cipher/pubkey.c (_gcry_pk_sign_md): Fix memory leak. +(_gcry_pk_verify_md): Likewise. + +-- + +GnuPG-bug-id: 7338 +Signed-off-by: NIIBE Yutaka +Signed-off-by: Lucas Mülling +--- + cipher/pubkey.c | 4 ++-- + 1 file changed, 2 insertions(+), 2 deletions(-) + +diff --git a/cipher/pubkey.c b/cipher/pubkey.c +index 11bf1ec9..4d7743cc 100644 +--- a/cipher/pubkey.c ++++ b/cipher/pubkey.c +@@ -626,7 +626,7 @@ _gcry_pk_sign_md (gcry_sexp_t *r_sig, const char *tmpl, gcry_md_hd_t hd_orig, + else if (!spec->flags.fips && fips_mode ()) + { + if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) +- return GPG_ERR_PUBKEY_ALGO; ++ rc = GPG_ERR_PUBKEY_ALGO; + else + fips_service_indicator_mark_non_compliant (); + } +@@ -708,7 +708,7 @@ _gcry_pk_verify_md (gcry_sexp_t s_sig, const char *tmpl, gcry_md_hd_t hd_orig, + else if (!spec->flags.fips && fips_mode ()) + { + if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) +- return GPG_ERR_PUBKEY_ALGO; ++ rc = GPG_ERR_PUBKEY_ALGO; + else + fips_service_indicator_mark_non_compliant (); + } +-- +2.49.0 + diff --git a/libgcrypt-build-Improve-__thread-specifier-check.patch b/libgcrypt-build-Improve-__thread-specifier-check.patch new file mode 100644 index 0000000..9167adc --- /dev/null +++ b/libgcrypt-build-Improve-__thread-specifier-check.patch @@ -0,0 +1,41 @@ +From 42e8858566e32080aaf818b168f34c698a9ef084 Mon Sep 17 00:00:00 2001 +From: NIIBE Yutaka +Date: Thu, 9 Jan 2025 10:15:50 +0900 +Subject: [PATCH 1/1] build: Improve __thread specifier check. +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* configure.ac (AC_COMPILE_IFELSE __thread): Move the declaration to +global, referring the variable with (void) in main to avoid an error +buidling with -Werror=unused-variable. Don't need to include +stdlib.h. + +-- + +Reported-by: Lucas Mulling +Signed-off-by: NIIBE Yutaka +Signed-off-by: Lucas Mülling +--- + configure.ac | 5 +++-- + 1 file changed, 3 insertions(+), 2 deletions(-) + +diff --git a/configure.ac b/configure.ac +index d708f89a..f38e20c5 100644 +--- a/configure.ac ++++ b/configure.ac +@@ -1495,8 +1495,9 @@ fi + AC_CACHE_CHECK([whether compiler supports '__thread' storage class specifier], + [gcry_cv_gcc_storage_class__thread], + [gcry_cv_gcc_storage_class__thread=no +- AC_COMPILE_IFELSE([AC_LANG_PROGRAM([#include ], +- [static __thread int bar;] ++ AC_COMPILE_IFELSE([AC_LANG_PROGRAM( ++ [[static __thread int bar;]], ++ [[(void)bar;]] + )], + [gcry_cv_gcc_storage_class__thread=yes])]) + if test "$gcry_cv_gcc_storage_class__thread" = "yes" ; then +-- +2.49.0 + diff --git a/libgcrypt-cipher-Add-KAT-for-non-rfc6979-ECDSA-with-fixed-k.patch b/libgcrypt-cipher-Add-KAT-for-non-rfc6979-ECDSA-with-fixed-k.patch new file mode 100644 index 0000000..ff9ae28 --- /dev/null +++ b/libgcrypt-cipher-Add-KAT-for-non-rfc6979-ECDSA-with-fixed-k.patch @@ -0,0 +1,94 @@ +From be57179f42f8a7cb64f72f73ccea753400573b4f Mon Sep 17 00:00:00 2001 +From: Lucas Mulling via Gcrypt-devel +Date: Wed, 26 Feb 2025 12:29:53 -0300 +Subject: [PATCH 02/14] cipher: Add KAT for non-rfc6979 ECDSA with fixed k +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* cipher/ecc.c (run_selftests): Implement KAT for non-deterministic +ECDSA. +* cipher/ecc. (rfc6979_ecdsa_sample_data, rfc6979_ecdsa_sample_data_bad, +rfc6979_ecdsa_data_tmpl): New. + +Signed-off-by: Lucas Mulling +Signed-off-by: Lucas Mülling +--- + cipher/ecc.c | 40 +++++++++++++++++++++++++++++++++++++--- + 1 file changed, 37 insertions(+), 3 deletions(-) + +diff --git a/cipher/ecc.c b/cipher/ecc.c +index 525523ed..d331a014 100644 +--- a/cipher/ecc.c ++++ b/cipher/ecc.c +@@ -93,23 +93,47 @@ static const char ecdsa_sample_secret_key_secp256[] = + /**/ "7903FE1008B8BC99A41AE9E95628BC64F2F1B20C2D7E9F5177A3C294D4462299#)))"; + + /* Sample data from RFC 6979 section A.2.5, hash is of message "sample" */ +-static const char ecdsa_sample_data[] = ++static const char rfc6979_ecdsa_sample_data[] = + "(data (flags rfc6979 prehash)" + " (hash-algo sha256)" + " (value 6:sample))"; + +-static const char ecdsa_sample_data_bad[] = ++static const char rfc6979_ecdsa_sample_data_bad[] = + "(data (flags rfc6979)" + " (hash sha256 #bf2bdbe1aa9b6ec1e2ade1d694f41fc71a831d0268e98915" + /**/ "62113d8a62add1bf#))"; + ++static const char *rfc6979_ecdsa_data_tmpl = ++ "(data (flags rfc6979)" ++ " (hash %s %b))"; ++ ++/* ++ * Sample data from RFC 6979 section A.2.5, with fixed k, ++ * hash is of message "sample". ++ */ ++static const char ecdsa_sample_data[] = ++ "(data (flags raw prehash)" ++ " (label #A6E3C57DD01ABE90086538398355DD4C3B17AA873382B0F24D6129493D8AAD60#)" ++ " (hash-algo sha256)" ++ " (value 6:sample))"; ++ ++static const char ecdsa_sample_data_bad[] = ++ "(data (flags raw)" ++ " (label #A6E3C57DD01ABE90086538398355DD4C3B17AA873382B0F24D6129493D8AAD60#)" ++ " (hash sha256 #bf2bdbe1aa9b6ec1e2ade1d694f41fc71a831d0268e98915" ++ /**/ "62113d8a62add1bf#))"; ++ ++static const char *ecdsa_data_tmpl = ++ "(data (flags raw)" ++ " (label #A6E3C57DD01ABE90086538398355DD4C3B17AA873382B0F24D6129493D8AAD60#)" ++ " (hash %s %b))"; ++ + static const char ecdsa_signature_r[] = + "efd48b2aacb6a8fd1140dd9cd45e81d69d2c877b56aaf991c34d0ea84eaf3716"; + + static const char ecdsa_signature_s[] = + "f7cb1c942d657c41d436c7a1b6e29f65f3e900dbb9aff4064dc4ab2f843acda8"; + +-static const char *ecdsa_data_tmpl = "(data (flags rfc6979) (hash %s %b))"; + /* Sample data from RFC 6979 section A.2.5, hash is of message "sample" */ + static const char ecdsa_sample_data_string[] = "sample"; + static const char ecdsa_sample_data_bad_string[] = "sbmple"; +@@ -2409,6 +2433,16 @@ run_selftests (int algo, int extended, selftest_report_func_t report) + if (r) + return r; + ++ r = selftests_ecc (report, extended, 0, ++ ecdsa_sample_secret_key_secp256, ++ ecdsa_sample_public_key_secp256, ++ rfc6979_ecdsa_sample_data, rfc6979_ecdsa_sample_data_bad, ++ rfc6979_ecdsa_data_tmpl, ++ ecdsa_sample_data_string, ecdsa_sample_data_bad_string, ++ ecdsa_signature_r, ecdsa_signature_s); ++ if (r) ++ return r; ++ + r = selftests_ecc (report, extended, 1, + ed25519_sample_secret_key, + ed25519_sample_public_key, +-- +2.49.0 + diff --git a/libgcrypt-cipher-Check-and-mark-non-compliant-cipher-modes-in-the-SLI.patch b/libgcrypt-cipher-Check-and-mark-non-compliant-cipher-modes-in-the-SLI.patch new file mode 100644 index 0000000..e922808 --- /dev/null +++ b/libgcrypt-cipher-Check-and-mark-non-compliant-cipher-modes-in-the-SLI.patch @@ -0,0 +1,236 @@ +From 9f0fd2656d7d7ba26fcf95cc64d2514ae9ac8ec1 Mon Sep 17 00:00:00 2001 +From: Lucas Mulling +Date: Fri, 24 Jan 2025 09:57:49 -0300 +Subject: [PATCH] cipher: Check and mark non-compliant cipher modes in the SLI +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* cipher/cipher.c (_gcry_cipher_open_internal): Check and mark if the +cipher mode is compliant and reject accordingly. +(_gcry_cipher_is_mode_fips_compliant): New. +* src/gcrypt.h.in (GCRY_FIPS_FLAG_REJECT_CIPHER_MODE): New. +* tests/t-fips-service-ind.c (check_cipher_o_s_e_d_c): Add test to +verify that the service level indication is correctly set for non- +compliant cipher modes, and correctly rejected if +GCRY_FIPS_FLAG_REJECT_CIPHER_MODE is set. + +-- + +GnuPG-bug-id: 7338 +Signed-off-by: Lucas Mulling +Signed-off-by: Lucas Mülling +--- + cipher/cipher.c | 43 ++++++++++++++++++---- + src/gcrypt.h.in | 1 + + tests/t-fips-service-ind.c | 74 +++++++++++++++++++++++++++++++++----- + 3 files changed, 104 insertions(+), 14 deletions(-) + +diff --git a/cipher/cipher.c b/cipher/cipher.c +index 74dc2df7..b5420671 100644 +--- a/cipher/cipher.c ++++ b/cipher/cipher.c +@@ -504,6 +504,26 @@ _gcry_cipher_open (gcry_cipher_hd_t *handle, + return rc; + } + ++int ++_gcry_cipher_is_mode_fips_compliant(int mode) ++{ ++ switch (mode) ++ { ++ case GCRY_CIPHER_MODE_ECB: ++ case GCRY_CIPHER_MODE_CBC: ++ case GCRY_CIPHER_MODE_CFB: ++ case GCRY_CIPHER_MODE_CFB8: ++ case GCRY_CIPHER_MODE_OFB: ++ case GCRY_CIPHER_MODE_CTR: ++ case GCRY_CIPHER_MODE_CCM: ++ case GCRY_CIPHER_MODE_XTS: ++ case GCRY_CIPHER_MODE_AESWRAP: ++ return GPG_ERR_NO_ERROR; ++ default: ++ return GPG_ERR_NOT_SUPPORTED; ++ } ++} ++ + + gcry_err_code_t + _gcry_cipher_open_internal (gcry_cipher_hd_t *handle, +@@ -523,14 +543,25 @@ _gcry_cipher_open_internal (gcry_cipher_hd_t *handle, + err = GPG_ERR_CIPHER_ALGO; + else if (spec->flags.disabled) + err = GPG_ERR_CIPHER_ALGO; +- else if (!spec->flags.fips && fips_mode ()) ++ else if (fips_mode ()) + { +- if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_CIPHER)) +- err = GPG_ERR_CIPHER_ALGO; +- else ++ if (!spec->flags.fips) + { +- fips_service_indicator_mark_non_compliant (); +- err = 0; ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_CIPHER)) ++ err = GPG_ERR_CIPHER_ALGO; ++ else ++ { ++ fips_service_indicator_mark_non_compliant (); ++ err = 0; ++ } ++ } ++ else if ((err = _gcry_cipher_is_mode_fips_compliant(mode))) ++ { ++ if (!fips_check_rejection (GCRY_FIPS_FLAG_REJECT_CIPHER_MODE)) ++ { ++ fips_service_indicator_mark_non_compliant (); ++ err = 0; ++ } + } + } + else +diff --git a/src/gcrypt.h.in b/src/gcrypt.h.in +index fcb6a327..1a6f7269 100644 +--- a/src/gcrypt.h.in ++++ b/src/gcrypt.h.in +@@ -1988,6 +1988,7 @@ char *gcry_get_config (int mode, const char *what); + #define GCRY_FIPS_FLAG_REJECT_PK (1 << 5) + #define GCRY_FIPS_FLAG_REJECT_PK_MD (1 << 6) + #define GCRY_FIPS_FLAG_REJECT_PK_GOST_SM2 (1 << 7) ++#define GCRY_FIPS_FLAG_REJECT_CIPHER_MODE (1 << 8) + + #define GCRY_FIPS_FLAG_REJECT_MD \ + (GCRY_FIPS_FLAG_REJECT_MD_MD5 | GCRY_FIPS_FLAG_REJECT_MD_OTHERS) +diff --git a/tests/t-fips-service-ind.c b/tests/t-fips-service-ind.c +index fe963fa5..74521bb3 100644 +--- a/tests/t-fips-service-ind.c ++++ b/tests/t-fips-service-ind.c +@@ -606,27 +606,41 @@ check_cipher_o_s_e_d_c (int reject) + { + static struct { + int algo; ++ int mode; + const char *key; + int keylen; ++ const char *tag; ++ int taglen; + const char *expect; + int expect_failure; + } tv[] = { + #if USE_DES +- { GCRY_CIPHER_3DES, +- "\xe3\x34\x7a\x6b\x0b\xc1\x15\x2c\x64\x2a\x25\xcb\xd3\xbc\x31\xab" +- "\xfb\xa1\x62\xa8\x1f\x19\x7c\x15", 24, +- "\x3f\x1a\xb8\x83\x18\x8b\xb5\x97", 1 }, ++ { GCRY_CIPHER_3DES, GCRY_CIPHER_MODE_ECB, ++ "\xe3\x34\x7a\x6b\x0b\xc1\x15\x2c\x64\x2a\x25\xcb\xd3\xbc\x31\xab" ++ "\xfb\xa1\x62\xa8\x1f\x19\x7c\x15", 24, ++ "", -1, ++ "\x3f\x1a\xb8\x83\x18\x8b\xb5\x97", 1 }, + #endif +- { GCRY_CIPHER_AES, +- "\x2b\x7e\x15\x16\x28\xae\xd2\xa6\xab\xf7\x15\x88\x09\xcf\x4f\x3c", 16, +- "\x5c\x71\xd8\x5d\x26\x5e\xcd\xb5\x95\x40\x41\xab\xff\x25\x6f\xd1" } ++ { GCRY_CIPHER_AES, GCRY_CIPHER_MODE_ECB, ++ "\x2b\x7e\x15\x16\x28\xae\xd2\xa6\xab\xf7\x15\x88\x09\xcf\x4f\x3c", 16, ++ "", -1, ++ "\x5c\x71\xd8\x5d\x26\x5e\xcd\xb5\x95\x40\x41\xab\xff\x25\x6f\xd1" }, ++ { GCRY_CIPHER_AES128, GCRY_CIPHER_MODE_SIV, ++ "\xff\xfe\xfd\xfc\xfb\xfa\xf9\xf8\xf7\xf6\xf5\xf4\xf3\xf2\xf1\xf0" ++ "\xf0\xf1\xf2\xf3\xf4\xf5\xf6\xf7\xf8\xf9\xfa\xfb\xfc\xfd\xfe\xff", 32, ++ "\x51\x66\x54\xc4\xe1\xb5\xd9\x37\x31\x52\xdb\xea\x35\x10\x8b\x7b", 16, ++ "\x83\x69\xf6\xf3\x20\xff\xa2\x72\x31\x67\x15\xcf\xf4\x75\x01\x9a", 1 } + }; ++ + const char *pt = "Shohei Ohtani 2024: 54 HR, 59 SB"; + int ptlen; + int tvidx; + unsigned char out[MAX_DATA_LEN]; + gpg_error_t err; + ++ unsigned char tag[16]; ++ size_t taglen = 0; ++ + ptlen = strlen (pt); + assert (ptlen == 32); + for (tvidx=0; tvidx < DIM(tv); tvidx++) +@@ -640,10 +654,12 @@ check_cipher_o_s_e_d_c (int reject) + tvidx); + + blklen = gcry_cipher_get_algo_blklen (tv[tvidx].algo); ++ + assert (blklen != 0); + assert (blklen <= ptlen); + assert (blklen <= DIM (out)); +- err = gcry_cipher_open (&h, tv[tvidx].algo, GCRY_CIPHER_MODE_ECB, 0); ++ assert (tv[tvidx].taglen <= 16); ++ err = gcry_cipher_open (&h, tv[tvidx].algo, tv[tvidx].mode, 0); + if (err) + { + if (in_fips_mode && reject && tv[tvidx].expect_failure) +@@ -694,6 +710,18 @@ check_cipher_o_s_e_d_c (int reject) + continue; + } + ++ if (tv[tvidx].taglen >= 0) ++ { ++ err = gcry_cipher_info (h, GCRYCTL_GET_TAGLEN, NULL, &taglen); ++ if (err) ++ fail ("gcry_cipher_info %d failed: %s\n", tvidx, ++ gpg_strerror (err)); ++ ++ if (taglen != tv[tvidx].taglen) ++ fail ("gcry_cipher_info %d failed: taglen mismatch %d != %ld\n", tvidx, ++ tv[tvidx].taglen, taglen); ++ } ++ + err = gcry_cipher_encrypt (h, out, MAX_DATA_LEN, pt, blklen); + if (err) + { +@@ -714,6 +742,35 @@ check_cipher_o_s_e_d_c (int reject) + putc ('\n', stderr); + } + ++ if (tv[tvidx].taglen >= 0) ++ { ++ err = gcry_cipher_gettag (h, tag, tv[tvidx].taglen); ++ if (err) ++ fail ("gcry_cipher_gettag %d failed: %s", tvidx, ++ gpg_strerror(err)); ++ ++ if (memcmp (tv[tvidx].tag, tag, tv[tvidx].taglen)) ++ { ++ int i; ++ ++ fail ("gcry_cipher_gettag %d: tag mismatch\n", tvidx); ++ fputs ("got:", stderr); ++ for (i=0; i < 16 ; i++) ++ fprintf (stderr, " %02x", tag[i]); ++ putc ('\n', stderr); ++ } ++ ++ err = gcry_cipher_reset (h); ++ if (err) ++ fail("gcry_cipher_reset %d failed: %s", tvidx, ++ gpg_strerror(err)); ++ ++ err = gcry_cipher_set_decryption_tag (h, tag, 16); ++ if (err) ++ fail ("gcry_cipher_set_decryption_tag %d failed: %s\n", tvidx< ++ gpg_strerror (err)); ++ } ++ + err = gcry_cipher_decrypt (h, out, blklen, NULL, 0); + if (err) + { +@@ -1483,6 +1540,7 @@ main (int argc, char **argv) + + xgcry_control ((GCRYCTL_FIPS_REJECT_NON_FIPS, + (GCRY_FIPS_FLAG_REJECT_MD_MD5 ++ | GCRY_FIPS_FLAG_REJECT_CIPHER_MODE + | GCRY_FIPS_FLAG_REJECT_PK_MD + | GCRY_FIPS_FLAG_REJECT_PK_GOST_SM2 + | GCRY_FIPS_FLAG_REJECT_COMPAT110))); +-- +2.49.0 + diff --git a/libgcrypt-cipher-Differentiate-igninvflag-in-the-SLI.patch b/libgcrypt-cipher-Differentiate-igninvflag-in-the-SLI.patch new file mode 100644 index 0000000..7763815 --- /dev/null +++ b/libgcrypt-cipher-Differentiate-igninvflag-in-the-SLI.patch @@ -0,0 +1,40 @@ +From 3bdb59c21b77711cf7d44d692a7a02f5f469033e Mon Sep 17 00:00:00 2001 +From: Lucas Mulling via Gcrypt-devel +Date: Wed, 26 Feb 2025 17:19:22 -0300 +Subject: [PATCH 04/14] cipher: Differentiate igninvflag in the SLI +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* cipher/pubkey-util.c (_gcry_pk_util_parse_flaglist): Differentiate use +of igninvflag. + +GnuPG-bug-id: 7338 +Signed-off-by: Lucas Mulling +Signed-off-by: Lucas Mülling +--- + cipher/pubkey-util.c | 8 ++++++++ + 1 file changed, 8 insertions(+) + +diff --git a/cipher/pubkey-util.c b/cipher/pubkey-util.c +index 68defea6..9c927638 100644 +--- a/cipher/pubkey-util.c ++++ b/cipher/pubkey-util.c +@@ -200,6 +200,14 @@ _gcry_pk_util_parse_flaglist (gcry_sexp_t list, + } + } + ++ if (fips_mode () && igninvflag) ++ { ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) ++ rc = GPG_ERR_INV_FLAG; ++ else ++ fips_service_indicator_mark_non_compliant (); ++ } ++ + if (r_flags) + *r_flags = flags; + if (r_encoding) +-- +2.49.0 + diff --git a/libgcrypt-cipher-Differentiate-no-blinding-flag-in-the-SLI.patch b/libgcrypt-cipher-Differentiate-no-blinding-flag-in-the-SLI.patch new file mode 100644 index 0000000..92b9073 --- /dev/null +++ b/libgcrypt-cipher-Differentiate-no-blinding-flag-in-the-SLI.patch @@ -0,0 +1,70 @@ +From cc0a40bd74120dc06fd80f163b30abb91f60b63b Mon Sep 17 00:00:00 2001 +From: Lucas Mulling via Gcrypt-devel +Date: Wed, 26 Feb 2025 17:19:23 -0300 +Subject: [PATCH 05/14] cipher: Differentiate no-blinding flag in the SLI +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* cipher/rsa.c (rsa_decrypt, rsa_encrypt): Differentiate use of flag +no-blinding in the service level indicator. + +GnuPG-bug-id: 7338 +Signed-off-by: Lucas Mulling +Signed-off-by: Lucas Mülling +--- + cipher/rsa.c | 30 ++++++++++++++++++++++++++++-- + 1 file changed, 28 insertions(+), 2 deletions(-) + +diff --git a/cipher/rsa.c b/cipher/rsa.c +index c1329644..dce76414 100644 +--- a/cipher/rsa.c ++++ b/cipher/rsa.c +@@ -1501,7 +1501,19 @@ rsa_decrypt (gcry_sexp_t *r_plain, gcry_sexp_t s_data, gcry_sexp_t keyparms) + be practically mounted over the network as shown by Brumley and + Boney in 2003. */ + if ((ctx.flags & PUBKEY_FLAG_NO_BLINDING)) +- secret (plain, data, &sk); ++ { ++ if (fips_mode ()) ++ { ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) ++ { ++ rc = GPG_ERR_INV_FLAG; ++ goto leave; ++ } ++ else ++ fips_service_indicator_mark_non_compliant (); ++ } ++ secret (plain, data, &sk); ++ } + else + secret_blinded (plain, data, &sk, nbits); + +@@ -1632,8 +1644,22 @@ rsa_sign (gcry_sexp_t *r_sig, gcry_sexp_t s_data, gcry_sexp_t keyparms) + + /* Do RSA computation. */ + sig = mpi_new (0); ++ + if ((ctx.flags & PUBKEY_FLAG_NO_BLINDING)) +- secret (sig, data, &sk); ++ { ++ if (fips_mode ()) ++ { ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) ++ { ++ rc = GPG_ERR_INV_FLAG; ++ goto leave; ++ } ++ else ++ fips_service_indicator_mark_non_compliant (); ++ } ++ ++ secret (sig, data, &sk); ++ } + else + secret_blinded (sig, data, &sk, nbits); + if (DBG_CIPHER) +-- +2.49.0 + diff --git a/libgcrypt-cipher-Differentiate-use-of-label-K-in-the-SLI.patch b/libgcrypt-cipher-Differentiate-use-of-label-K-in-the-SLI.patch new file mode 100644 index 0000000..a054b64 --- /dev/null +++ b/libgcrypt-cipher-Differentiate-use-of-label-K-in-the-SLI.patch @@ -0,0 +1,139 @@ +From 2f6d2db1a4c28775a568c1f81ca127d2daebaf1c Mon Sep 17 00:00:00 2001 +From: Lucas Mulling via Gcrypt-devel +Date: Wed, 26 Feb 2025 12:29:54 -0300 +Subject: [PATCH 03/14] cipher: Differentiate use of label K in the SLI +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* cipher/ecc.c (ecc_sign, ecc_verify): Use of label K is not allowed in +fips mode, differentiate with the GCRY_FIPS_FLAG_REJECT_PK_ECC_K flag. +* src/gcrypt.h.in: New GCRY_FIPS_FLAG_REJECT_PK_ECC_K. +* tests/t-fips-service-ind.c (check_pk_hash_sign_verify): Mark non +compliant use of label. + +Signed-off-by: Lucas Mulling +Signed-off-by: Lucas Mülling +--- + cipher/ecc.c | 26 +++++++++++++++++++++++++- + src/gcrypt.h.in | 2 ++ + tests/t-fips-service-ind.c | 11 ++++++----- + 3 files changed, 33 insertions(+), 6 deletions(-) + +diff --git a/cipher/ecc.c b/cipher/ecc.c +index d331a014..569e41f6 100644 +--- a/cipher/ecc.c ++++ b/cipher/ecc.c +@@ -961,7 +961,16 @@ ecc_sign (gcry_sexp_t *r_sig, gcry_sexp_t s_data, gcry_sexp_t keyparms) + log_mpidump ("ecc_sign data", data); + + if (ctx.label) +- rc = _gcry_mpi_scan (&k, GCRYMPI_FMT_USG, ctx.label, ctx.labellen, NULL); ++ { ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK_ECC_K)) ++ { ++ rc = GPG_ERR_INV_DATA; ++ goto leave; ++ } ++ else ++ fips_service_indicator_mark_non_compliant (); ++ rc = _gcry_mpi_scan (&k, GCRYMPI_FMT_USG, ctx.label, ctx.labellen, NULL); ++ } + if (rc) + goto leave; + +@@ -1118,6 +1127,21 @@ ecc_verify (gcry_sexp_t s_sig, gcry_sexp_t s_data, gcry_sexp_t s_keyparms) + rc = _gcry_pk_util_data_to_mpi (s_data, &data, &ctx); + if (rc) + goto leave; ++ ++ if (ctx.label) ++ { ++ if (fips_mode ()) ++ { ++ if(fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK_ECC_K)) ++ { ++ rc = GPG_ERR_INV_DATA; ++ goto leave; ++ } ++ else ++ fips_service_indicator_mark_non_compliant (); ++ } ++ } ++ + if (DBG_CIPHER) + log_mpidump ("ecc_verify data", data); + +diff --git a/src/gcrypt.h.in b/src/gcrypt.h.in +index 1a6f7269..fe3db16a 100644 +--- a/src/gcrypt.h.in ++++ b/src/gcrypt.h.in +@@ -1989,6 +1989,8 @@ char *gcry_get_config (int mode, const char *what); + #define GCRY_FIPS_FLAG_REJECT_PK_MD (1 << 6) + #define GCRY_FIPS_FLAG_REJECT_PK_GOST_SM2 (1 << 7) + #define GCRY_FIPS_FLAG_REJECT_CIPHER_MODE (1 << 8) ++/**/ ++#define GCRY_FIPS_FLAG_REJECT_PK_ECC_K (1 << 10) + + #define GCRY_FIPS_FLAG_REJECT_MD \ + (GCRY_FIPS_FLAG_REJECT_MD_MD5 | GCRY_FIPS_FLAG_REJECT_MD_OTHERS) +diff --git a/tests/t-fips-service-ind.c b/tests/t-fips-service-ind.c +index a082b258..0ece55b8 100644 +--- a/tests/t-fips-service-ind.c ++++ b/tests/t-fips-service-ind.c +@@ -728,7 +728,7 @@ check_pk_hash_sign_verify (void) + "ce4014c68811f9a21a1fdb2c0e6113e06db7ca93b7404e78dc7ccd5ca89a4ca9#)))", + "(data(flags raw)(hash %s %b)(label %b))", + "94a1bbb14b906a61a280f245f9e93c7f3b4a6247824f5d33b9670787642a68de", +- 0, 0 ++ 1, 0, + } + }; + int tvidx; +@@ -827,7 +827,7 @@ check_pk_hash_sign_verify (void) + if (ec == GPG_ERR_INV_OP) + { + /* libgcrypt is old, no support of the FIPS service indicator. */ +- fail ("gcry_pk_hash test %d unexpectedly failed to check the FIPS service indicator.\n", ++ fail ("gcry_pk_hash_sign test %d unexpectedly failed to check the FIPS service indicator.\n", + tvidx); + goto next; + } +@@ -835,7 +835,7 @@ check_pk_hash_sign_verify (void) + if (in_fips_mode && !tv[tvidx].expect_failure && ec) + { + /* Success with the FIPS service indicator == 0 expected, but != 0. */ +- fail ("gcry_pk_hash test %d unexpectedly set the indicator in FIPS mode.\n", ++ fail ("gcry_pk_hash_sign test %d unexpectedly set the indicator in FIPS mode.\n", + tvidx); + goto next; + } +@@ -859,7 +859,7 @@ check_pk_hash_sign_verify (void) + if (ec == GPG_ERR_INV_OP) + { + /* libgcrypt is old, no support of the FIPS service indicator. */ +- fail ("gcry_pk_hash test %d unexpectedly failed to check the FIPS service indicator.\n", ++ fail ("gcry_pk_hash_verify test %d unexpectedly failed to check the FIPS service indicator.\n", + tvidx); + goto next; + } +@@ -867,7 +867,7 @@ check_pk_hash_sign_verify (void) + if (in_fips_mode && !tv[tvidx].expect_failure && ec) + { + /* Success with the FIPS service indicator == 0 expected, but != 0. */ +- fail ("gcry_pk_hash test %d unexpectedly set the indicator in FIPS mode.\n", ++ fail ("gcry_pk_hash_verify test %d unexpectedly set the indicator in FIPS mode.\n", + tvidx); + goto next; + } +@@ -1834,6 +1834,7 @@ main (int argc, char **argv) + | GCRY_FIPS_FLAG_REJECT_CIPHER_MODE + | GCRY_FIPS_FLAG_REJECT_PK_MD + | GCRY_FIPS_FLAG_REJECT_PK_GOST_SM2 ++ | GCRY_FIPS_FLAG_REJECT_PK_ECC_K + | GCRY_FIPS_FLAG_REJECT_COMPAT110))); + + check_md_o_w_r_c (1); +-- +2.49.0 + diff --git a/libgcrypt-cipher-Don-t-differentiate-GCRY_CIPHER_MODE_CMAC-in-FIPS-mode.patch b/libgcrypt-cipher-Don-t-differentiate-GCRY_CIPHER_MODE_CMAC-in-FIPS-mode.patch new file mode 100644 index 0000000..fc8d335 --- /dev/null +++ b/libgcrypt-cipher-Don-t-differentiate-GCRY_CIPHER_MODE_CMAC-in-FIPS-mode.patch @@ -0,0 +1,98 @@ +From 608ff4b2261e2d8961f0ef4189e74b1173b2802c Mon Sep 17 00:00:00 2001 +From: Lucas Mulling +Date: Sun, 2 Feb 2025 12:58:21 -0300 +Subject: [PATCH 2/2] cipher: Don't differentiate GCRY_CIPHER_MODE_CMAC in FIPS + mode. +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* cipher/cipher.c (_gcry_cipher_mode_fips_compliance): Allow +GCRY_CIPHER_MODE_CMAC in fips mode. +* cipher/cipher.c (cipher_modes_fips_compliance) +(cipher_int_modes_fips_compliance): New. +-- + +Signed-off-by: Lucas Mulling + +Added some comments, changed scope of the new functions and shorted +their names. Also added restructured the switch and added all other +modes. + +Signed-off-by: Werner Koch +Signed-off-by: Lucas Mülling +--- + cipher/cipher.c | 49 ++++++++++++++++++++++++++++++++++++++++++++----- + 1 file changed, 44 insertions(+), 5 deletions(-) + +diff --git a/cipher/cipher.c b/cipher/cipher.c +index 3b7970b3..fc130907 100644 +--- a/cipher/cipher.c ++++ b/cipher/cipher.c +@@ -505,8 +505,9 @@ _gcry_cipher_open (gcry_cipher_hd_t *handle, + } + + +-gcry_err_code_t +-_gcry_cipher_mode_fips_compliance (enum gcry_cipher_modes mode) ++/* Return an error if the give cipher mode is non-FIPS compliant. */ ++static gcry_err_code_t ++cipher_modes_fips_compliance (enum gcry_cipher_modes mode) + { + switch (mode) + { +@@ -519,10 +520,48 @@ _gcry_cipher_mode_fips_compliance (enum gcry_cipher_modes mode) + case GCRY_CIPHER_MODE_CCM: + case GCRY_CIPHER_MODE_XTS: + case GCRY_CIPHER_MODE_AESWRAP: +- return GPG_ERR_NO_ERROR; +- default: +- return GPG_ERR_NOT_SUPPORTED; ++ return 0; ++ case GCRY_CIPHER_MODE_NONE: ++ case GCRY_CIPHER_MODE_STREAM: ++ case GCRY_CIPHER_MODE_GCM: ++ case GCRY_CIPHER_MODE_POLY1305: ++ case GCRY_CIPHER_MODE_OCB: ++ case GCRY_CIPHER_MODE_EAX: ++ case GCRY_CIPHER_MODE_SIV: ++ case GCRY_CIPHER_MODE_GCM_SIV: ++ break; + } ++ return GPG_ERR_NOT_SUPPORTED; ++} ++ ++ ++/* This is similar to cipher_modes_fips_compliance but only for the ++ * internal modes (i.e. CMAC). Return an error if the mode is ++ * non-FIPS compliant. */ ++static gcry_err_code_t ++cipher_int_modes_fips_compliance (enum gcry_cipher_internal_modes mode) ++{ ++ switch (mode) ++ { ++ case GCRY_CIPHER_MODE_INTERNAL: ++ break; ++ case GCRY_CIPHER_MODE_CMAC: ++ return 0; ++ } ++ return GPG_ERR_NOT_SUPPORTED; ++} ++ ++ ++/* Return an error if the give cipher mode is non-FIPS compliant. The ++ * mode is not an enum here so that we can use it for real modes and ++ * for internal modes. */ ++gcry_err_code_t ++_gcry_cipher_mode_fips_compliance (int mode) ++{ ++ if (mode >= GCRY_CIPHER_MODE_INTERNAL) ++ return cipher_int_modes_fips_compliance (mode); ++ else ++ return cipher_modes_fips_compliance (mode); + } + + +-- +2.49.0 + diff --git a/libgcrypt-cipher-Rename-_gcry_cipher_is_mode_fips_compliant.patch b/libgcrypt-cipher-Rename-_gcry_cipher_is_mode_fips_compliant.patch new file mode 100644 index 0000000..e98f6ab --- /dev/null +++ b/libgcrypt-cipher-Rename-_gcry_cipher_is_mode_fips_compliant.patch @@ -0,0 +1,64 @@ +From 6b0fbb7e5e0da77787e3a87d74359ee21c44904e Mon Sep 17 00:00:00 2001 +From: Lucas Mulling +Date: Tue, 28 Jan 2025 13:45:39 -0300 +Subject: [PATCH 1/2] cipher: Rename _gcry_cipher_is_mode_fips_compliant +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* cipher/cipher.c (_gcry_cipher_is_mode_fips_compliant): Rename to +_gcry_cipher_mode_fips_compliance for better clarity and change the +return type to gcry_err_code_t. +* cipher/cipher.c (_gcry_cipher_mode_fips_compliance): Use +gcry_cipher_modes instead of int for mode. +* tests/t-fips-service-ind.c (check_cipher_o_s_e_d_c): Fix typo in fail. +-- + +Signed-off-by: Lucas Mulling +Signed-off-by: Lucas Mülling +--- + cipher/cipher.c | 7 ++++--- + tests/t-fips-service-ind.c | 2 +- + 2 files changed, 5 insertions(+), 4 deletions(-) + +diff --git a/cipher/cipher.c b/cipher/cipher.c +index b5420671..3b7970b3 100644 +--- a/cipher/cipher.c ++++ b/cipher/cipher.c +@@ -504,8 +504,9 @@ _gcry_cipher_open (gcry_cipher_hd_t *handle, + return rc; + } + +-int +-_gcry_cipher_is_mode_fips_compliant(int mode) ++ ++gcry_err_code_t ++_gcry_cipher_mode_fips_compliance (enum gcry_cipher_modes mode) + { + switch (mode) + { +@@ -555,7 +556,7 @@ _gcry_cipher_open_internal (gcry_cipher_hd_t *handle, + err = 0; + } + } +- else if ((err = _gcry_cipher_is_mode_fips_compliant(mode))) ++ else if ((err = _gcry_cipher_mode_fips_compliance (mode))) + { + if (!fips_check_rejection (GCRY_FIPS_FLAG_REJECT_CIPHER_MODE)) + { +diff --git a/tests/t-fips-service-ind.c b/tests/t-fips-service-ind.c +index 74521bb3..ed5f8d3f 100644 +--- a/tests/t-fips-service-ind.c ++++ b/tests/t-fips-service-ind.c +@@ -767,7 +767,7 @@ check_cipher_o_s_e_d_c (int reject) + + err = gcry_cipher_set_decryption_tag (h, tag, 16); + if (err) +- fail ("gcry_cipher_set_decryption_tag %d failed: %s\n", tvidx< ++ fail ("gcry_cipher_set_decryption_tag %d failed: %s\n", tvidx, + gpg_strerror (err)); + } + +-- +2.49.0 + diff --git a/libgcrypt-cipher-ecc-Fix-for-supplied-K.patch b/libgcrypt-cipher-ecc-Fix-for-supplied-K.patch new file mode 100644 index 0000000..743468d --- /dev/null +++ b/libgcrypt-cipher-ecc-Fix-for-supplied-K.patch @@ -0,0 +1,88 @@ +From 755e6dce727915249cbb1a98f22832d940b99c24 Mon Sep 17 00:00:00 2001 +From: NIIBE Yutaka +Date: Thu, 6 Mar 2025 09:12:36 +0900 +Subject: [PATCH 07/14] cipher,ecc: Fix for supplied K. +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* cipher/ecc.c (ecc_sign): Check if it's under FIPS mode. +(ecc_verify): Supplied K does no sense for verification, but add +comment of clarification mark/reject-ing under FIPS mode. + +-- + +GnuPG-bug-id: 7338 +Signed-off-by: NIIBE Yutaka +Signed-off-by: Lucas Mülling +--- + cipher/ecc.c | 39 +++++++++++++++++++++++---------------- + 1 file changed, 23 insertions(+), 16 deletions(-) + +diff --git a/cipher/ecc.c b/cipher/ecc.c +index 569e41f6..a165bb7a 100644 +--- a/cipher/ecc.c ++++ b/cipher/ecc.c +@@ -962,17 +962,21 @@ ecc_sign (gcry_sexp_t *r_sig, gcry_sexp_t s_data, gcry_sexp_t keyparms) + + if (ctx.label) + { +- if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK_ECC_K)) ++ /* ECDSA signing can have supplied K (for testing, deterministic). */ ++ if (fips_mode ()) + { +- rc = GPG_ERR_INV_DATA; +- goto leave; ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK_ECC_K)) ++ { ++ rc = GPG_ERR_INV_DATA; ++ goto leave; ++ } ++ else ++ fips_service_indicator_mark_non_compliant (); + } +- else +- fips_service_indicator_mark_non_compliant (); + rc = _gcry_mpi_scan (&k, GCRYMPI_FMT_USG, ctx.label, ctx.labellen, NULL); ++ if (rc) ++ goto leave; + } +- if (rc) +- goto leave; + + if (fips_mode () + && ((ctx.flags & PUBKEY_FLAG_GOST) || (ctx.flags & PUBKEY_FLAG_SM2))) +@@ -1128,18 +1132,21 @@ ecc_verify (gcry_sexp_t s_sig, gcry_sexp_t s_data, gcry_sexp_t s_keyparms) + if (rc) + goto leave; + +- if (ctx.label) ++ /* ++ * ECDSA signing can have supplied K (for testing, deterministic), ++ * but it's non-compliant. For ECDSA signature verification, having ++ * K is irrelevant, but an application may use same flags as the one ++ * for signing. ++ */ ++ if (ctx.label && fips_mode ()) + { +- if (fips_mode ()) ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK_ECC_K)) + { +- if(fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK_ECC_K)) +- { +- rc = GPG_ERR_INV_DATA; +- goto leave; +- } +- else +- fips_service_indicator_mark_non_compliant (); ++ rc = GPG_ERR_INV_DATA; ++ goto leave; + } ++ else ++ fips_service_indicator_mark_non_compliant (); + } + + if (DBG_CIPHER) +-- +2.49.0 + diff --git a/libgcrypt-cipher-fips-Fix-for-random-override.patch b/libgcrypt-cipher-fips-Fix-for-random-override.patch new file mode 100644 index 0000000..076f66f --- /dev/null +++ b/libgcrypt-cipher-fips-Fix-for-random-override.patch @@ -0,0 +1,83 @@ +From ca8bf05e111b41e482a2a4b34cda6bcf5aa1f27e Mon Sep 17 00:00:00 2001 +From: NIIBE Yutaka +Date: Thu, 6 Mar 2025 09:45:36 +0900 +Subject: [PATCH 09/14] cipher,fips: Fix for random-override. +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* cipher/pubkey-util.c (gcry_pk_util_data_to_mpi): Keep +the behavior of 1.10. +* src/visibility.c (gcry_pk_random_override_new): Likewise. +* tests/t-fips-service-ind.c (main): Use GCRY_FIPS_FLAG_REJECT_PK_FLAGS. + +-- + +GnuPG-bug-id: 7338 +Signed-off-by: NIIBE Yutaka +Signed-off-by: Lucas Mülling +--- + cipher/pubkey-util.c | 6 +++--- + src/visibility.c | 2 +- + tests/t-fips-service-ind.c | 1 + + 3 files changed, 5 insertions(+), 4 deletions(-) + +diff --git a/cipher/pubkey-util.c b/cipher/pubkey-util.c +index 66a04f13..0e67f892 100644 +--- a/cipher/pubkey-util.c ++++ b/cipher/pubkey-util.c +@@ -975,7 +975,7 @@ _gcry_pk_util_data_to_mpi (gcry_sexp_t input, gcry_mpi_t *ret_mpi, + { + if (fips_mode ()) + { +- if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK_FLAGS)) + { + sexp_release (list); + rc = GPG_ERR_INV_FLAG; +@@ -1162,7 +1162,7 @@ _gcry_pk_util_data_to_mpi (gcry_sexp_t input, gcry_mpi_t *ret_mpi, + { + if (fips_mode ()) + { +- if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK_FLAGS)) + { + sexp_release (list); + rc = GPG_ERR_INV_FLAG; +@@ -1272,7 +1272,7 @@ _gcry_pk_util_data_to_mpi (gcry_sexp_t input, gcry_mpi_t *ret_mpi, + { + if (fips_mode ()) + { +- if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK_FLAGS)) + { + sexp_release (list); + rc = GPG_ERR_INV_FLAG; +diff --git a/src/visibility.c b/src/visibility.c +index ccd0de69..edb972bc 100644 +--- a/src/visibility.c ++++ b/src/visibility.c +@@ -1091,7 +1091,7 @@ gcry_pk_random_override_new (gcry_ctx_t *r_ctx, const unsigned char *p, size_t l + + if (fips_mode ()) + { +- if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK_FLAGS)) + return gpg_error (GPG_ERR_INV_OP); + else + fips_service_indicator_mark_non_compliant (); +diff --git a/tests/t-fips-service-ind.c b/tests/t-fips-service-ind.c +index 0ece55b8..0a270b38 100644 +--- a/tests/t-fips-service-ind.c ++++ b/tests/t-fips-service-ind.c +@@ -1835,6 +1835,7 @@ main (int argc, char **argv) + | GCRY_FIPS_FLAG_REJECT_PK_MD + | GCRY_FIPS_FLAG_REJECT_PK_GOST_SM2 + | GCRY_FIPS_FLAG_REJECT_PK_ECC_K ++ | GCRY_FIPS_FLAG_REJECT_PK_FLAGS + | GCRY_FIPS_FLAG_REJECT_COMPAT110))); + + check_md_o_w_r_c (1); +-- +2.49.0 + diff --git a/libgcrypt-cipher-rsa-Mark-reject-SHA1-unknown-with-RSA-signature-generation.patch b/libgcrypt-cipher-rsa-Mark-reject-SHA1-unknown-with-RSA-signature-generation.patch new file mode 100644 index 0000000..7ff18ce --- /dev/null +++ b/libgcrypt-cipher-rsa-Mark-reject-SHA1-unknown-with-RSA-signature-generation.patch @@ -0,0 +1,445 @@ +From 60e5039793c2474d29ded039cf1a6b8107733a20 Mon Sep 17 00:00:00 2001 +From: NIIBE Yutaka +Date: Fri, 21 Feb 2025 14:24:41 +0900 +Subject: [PATCH] cipher:rsa: Mark/reject SHA1/unknown with RSA signature + generation. +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* cipher/rsa-common.c (_gcry_rsa_pkcs1_encode_raw_for_sig): We can't +determine if it's compliant when raw PKCS1 encoding is used. +(_gcry_rsa_pss_encode): Add the behavior of marking non-compliant use. +(_gcry_rsa_pss_verify): Likewise. +* cipher/rsa.c (rsa_sign): Handle the check for SHA1. +(rsa_verify): Likewise. +* tests/t-fips-service-ind.c (check_pk_s_v): Add use cases for RSA +and Ed25519. + +-- + +GnuPG-bug-id: 7338 +Signed-off-by: NIIBE Yutaka +Signed-off-by: Lucas Mülling +--- + cipher/rsa-common.c | 28 +++- + cipher/rsa.c | 34 +++++ + tests/t-fips-service-ind.c | 290 ++++++++++++++++++++++++++++++++++++- + 3 files changed, 347 insertions(+), 5 deletions(-) + +diff --git a/cipher/rsa-common.c b/cipher/rsa-common.c +index 1920eedd..c1d2dcd5 100644 +--- a/cipher/rsa-common.c ++++ b/cipher/rsa-common.c +@@ -380,6 +380,16 @@ _gcry_rsa_pkcs1_encode_raw_for_sig (gcry_mpi_t *r_result, unsigned int nbits, + int i; + size_t n; + ++ /* With RAW encoding, we can't know if the hash used is compliant or ++ * not. Reject or mark it's non-compliant. */ ++ if (fips_mode ()) ++ { ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK_MD)) ++ return GPG_ERR_DIGEST_ALGO; ++ else ++ fips_service_indicator_mark_non_compliant (); ++ } ++ + if ( !valuelen || valuelen + 4 > nframe) + { + /* Can't encode an DLEN byte digest MD into an NFRAME byte +@@ -840,8 +850,13 @@ _gcry_rsa_pss_encode (gcry_mpi_t *r_result, unsigned int nbits, int algo, + /* The FIPS 186-4 Section 5.5 allows only 0 <= sLen <= hLen */ + if (fips_mode () && saltlen > hlen) + { +- rc = GPG_ERR_INV_ARG; +- goto leave; ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) ++ { ++ rc = GPG_ERR_INV_ARG; ++ goto leave; ++ } ++ else ++ fips_service_indicator_mark_non_compliant (); + } + + /* Allocate a help buffer and setup some pointers. */ +@@ -1006,8 +1021,13 @@ _gcry_rsa_pss_verify (gcry_mpi_t value, int hashed_already, + /* The FIPS 186-4 Section 5.5 allows only 0 <= sLen <= hLen */ + if (fips_mode () && saltlen > hlen) + { +- rc = GPG_ERR_INV_ARG; +- goto leave; ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) ++ { ++ rc = GPG_ERR_INV_ARG; ++ goto leave; ++ } ++ else ++ fips_service_indicator_mark_non_compliant (); + } + + /* Allocate a help buffer and setup some pointers. +diff --git a/cipher/rsa.c b/cipher/rsa.c +index c7a809f4..c1329644 100644 +--- a/cipher/rsa.c ++++ b/cipher/rsa.c +@@ -1613,6 +1613,23 @@ rsa_sign (gcry_sexp_t *r_sig, gcry_sexp_t s_data, gcry_sexp_t keyparms) + } + } + ++ /* Check if use of the hash is compliant. */ ++ if (fips_mode ()) ++ { ++ /* SHA1 is approved hash function, but not for digital signature. */ ++ if (_gcry_md_algo_info (ctx.hash_algo, GCRYCTL_TEST_ALGO, NULL, NULL) ++ || ctx.hash_algo == GCRY_MD_SHA1) ++ { ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK_MD)) ++ { ++ rc = GPG_ERR_DIGEST_ALGO; ++ goto leave; ++ } ++ else ++ fips_service_indicator_mark_non_compliant (); ++ } ++ } ++ + /* Do RSA computation. */ + sig = mpi_new (0); + if ((ctx.flags & PUBKEY_FLAG_NO_BLINDING)) +@@ -1720,6 +1737,23 @@ rsa_verify (gcry_sexp_t s_sig, gcry_sexp_t s_data, gcry_sexp_t keyparms) + log_printmpi ("rsa_verify e", pk.e); + } + ++ /* Check if use of the hash is compliant. */ ++ if (fips_mode ()) ++ { ++ /* SHA1 is approved hash function, but not for digital signature. */ ++ if (_gcry_md_algo_info (ctx.hash_algo, GCRYCTL_TEST_ALGO, NULL, NULL) ++ || ctx.hash_algo == GCRY_MD_SHA1) ++ { ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK_MD)) ++ { ++ rc = GPG_ERR_DIGEST_ALGO; ++ goto leave; ++ } ++ else ++ fips_service_indicator_mark_non_compliant (); ++ } ++ } ++ + /* Do RSA computation and compare. */ + result = mpi_new (0); + public (result, sig, &pk); +diff --git a/tests/t-fips-service-ind.c b/tests/t-fips-service-ind.c +index ed5f8d3f..bec6c27e 100644 +--- a/tests/t-fips-service-ind.c ++++ b/tests/t-fips-service-ind.c +@@ -231,7 +231,8 @@ check_pk_s_v (int reject) + const char *data; + int expect_failure; + } tv[] = { +- { ++ { /* Hashing is done externally, and feeded ++ to gcry_pk_sign, specifing the hash used */ + "(private-key (ecc (curve nistp256)" + " (d #519b423d715f8b581f4fa8ee59f4771a5b44c8130b4e3eacca54a56dda72b464#)))", + "(public-key (ecc (curve nistp256)" +@@ -271,6 +272,293 @@ check_pk_s_v (int reject) + "#00112233445566778899AABBCCDDEEFF00010203#))", + 1 + }, ++ { /* Hashing is done internally in ++ gcry_pk_sign with the hash-algo specified. */ ++ "(private-key\n" ++ " (ecc\n" ++ " (curve Ed25519)(flags eddsa)\n" ++ " (q #4014DB483F15527253B25B4C72BEA8BB70255029636BD71DBBCCD5D8BF48A35F17#)" ++ " (d #09A0C38E0F1699073541447C19DA12E3A07A7BFDB0C186E4AC5BCE6F23D55252#)" ++ "))", ++ "(public-key\n" ++ " (ecc\n" ++ " (curve Ed25519)(flags eddsa)\n" ++ " (q #4014DB483F15527253B25B4C72BEA8BB70255029636BD71DBBCCD5D8BF48A35F17#)" ++ "))", ++ "(data(flags eddsa)(hash-algo sha512)(value " ++ "#00112233445566778899AABBCCDDEEFF000102030405060708090A0B0C0D0E0F" ++ " 00112233445566778899AABBCCDDEEFF000102030405060708090A0B0C0D0E0F" ++ " 00112233445566778899AABBCCDDEEFF000102030405060708090A0B0C0D0E0F#))", ++ 0 ++ }, ++ { /* RSA with compliant hash for signing */ ++ "(private-key" ++ " (rsa" ++ " (n #009F56231A3D82E3E7D613D59D53E9AB921BEF9F08A782AED0B6E46ADBC853EC" ++ " 7C71C422435A3CD8FA0DB9EFD55CD3295BADC4E8E2E2B94E15AE82866AB8ADE8" ++ " 7E469FAE76DC3577DE87F1F419C4EB41123DFAF8D16922D5EDBAD6E9076D5A1C" ++ " 958106F0AE5E2E9193C6B49124C64C2A241C4075D4AF16299EB87A6585BAE917" ++ " DEF27FCDD165764D069BC18D16527B29DAAB549F7BBED4A7C6A842D203ED6613" ++ " 6E2411744E432CD26D940132F25874483DCAEECDFD95744819CBCF1EA810681C" ++ " 42907EBCB1C7EAFBE75C87EC32C5413EA10476545D3FC7B2ADB1B66B7F200918" ++ " 664B0E5261C2895AA28B0DE321E921B3F877172CCCAB81F43EF98002916156F6" ++ " CB#)\n" ++ " (e #010001#)\n" ++ " (d #07EF82500C403899934FE993AC5A36F14FF2DF38CF1EF315F205EE4C83EDAA19" ++ " 8890FC23DE9AA933CAFB37B6A8A8DBA675411958337287310D3FF2F1DDC0CB93" ++ " 7E70F57F75F833C021852B631D2B9A520E4431A03C5C3FCB5742DCD841D9FB12" ++ " 771AA1620DCEC3F1583426066ED9DC3F7028C5B59202C88FDF20396E2FA0EC4F" ++ " 5A22D9008F3043673931BC14A5046D6327398327900867E39CC61B2D1AFE2F48" ++ " EC8E1E3861C68D257D7425F4E6F99ABD77D61F10CA100EFC14389071831B33DD" ++ " 69CC8EABEF860D1DC2AAA84ABEAE5DFC91BC124DAF0F4C8EF5BBEA436751DE84" ++ " 3A8063E827A024466F44C28614F93B0732A100D4A0D86D532FE1E22C7725E401" ++ " #)\n" ++ " (p #00C29D438F115825779631CD665A5739367F3E128ADC29766483A46CA80897E0" ++ " 79B32881860B8F9A6A04C2614A904F6F2578DAE13EA67CD60AE3D0AA00A1FF9B" ++ " 441485E44B2DC3D0B60260FBFE073B5AC72FAF67964DE15C8212C389D20DB9CF" ++ " 54AF6AEF5C4196EAA56495DD30CF709F499D5AB30CA35E086C2A1589D6283F17" ++ " 83#)\n" ++ " (q #00D1984135231CB243FE959C0CBEF551EDD986AD7BEDF71EDF447BE3DA27AF46" ++ " 79C974A6FA69E4D52FE796650623DE70622862713932AA2FD9F2EC856EAEAA77" ++ " 88B4EA6084DC81C902F014829B18EA8B2666EC41586818E0589E18876065F97E" ++ " 8D22CE2DA53A05951EC132DCEF41E70A9C35F4ACC268FFAC2ADF54FA1DA110B9" ++ " 19#)\n" ++ " (u #67CF0FD7635205DD80FA814EE9E9C267C17376BF3209FB5D1BC42890D2822A04" ++ " 479DAF4D5B6ED69D0F8D1AF94164D07F8CD52ECEFE880641FA0F41DDAB1785E4" ++ " A37A32F997A516480B4CD4F6482B9466A1765093ED95023CA32D5EDC1E34CEE9" ++ " AF595BC51FE43C4BF810FA225AF697FB473B83815966188A4312C048B885E3F7" ++ " #)))\n", ++ "(public-key\n" ++ " (rsa\n" ++ " (n #009F56231A3D82E3E7D613D59D53E9AB921BEF9F08A782AED0B6E46ADBC853EC" ++ " 7C71C422435A3CD8FA0DB9EFD55CD3295BADC4E8E2E2B94E15AE82866AB8ADE8" ++ " 7E469FAE76DC3577DE87F1F419C4EB41123DFAF8D16922D5EDBAD6E9076D5A1C" ++ " 958106F0AE5E2E9193C6B49124C64C2A241C4075D4AF16299EB87A6585BAE917" ++ " DEF27FCDD165764D069BC18D16527B29DAAB549F7BBED4A7C6A842D203ED6613" ++ " 6E2411744E432CD26D940132F25874483DCAEECDFD95744819CBCF1EA810681C" ++ " 42907EBCB1C7EAFBE75C87EC32C5413EA10476545D3FC7B2ADB1B66B7F200918" ++ " 664B0E5261C2895AA28B0DE321E921B3F877172CCCAB81F43EF98002916156F6" ++ " CB#)\n" ++ " (e #010001#)))\n", ++ "(data\n (flags pkcs1)\n" ++ " (hash sha256 " ++ "#00112233445566778899AABBCCDDEEFF000102030405060708090A0B0C0D0E0F#))\n", ++ 0 ++ }, ++ { /* RSA with non-compliant hash for signing */ ++ "(private-key" ++ " (rsa" ++ " (n #009F56231A3D82E3E7D613D59D53E9AB921BEF9F08A782AED0B6E46ADBC853EC" ++ " 7C71C422435A3CD8FA0DB9EFD55CD3295BADC4E8E2E2B94E15AE82866AB8ADE8" ++ " 7E469FAE76DC3577DE87F1F419C4EB41123DFAF8D16922D5EDBAD6E9076D5A1C" ++ " 958106F0AE5E2E9193C6B49124C64C2A241C4075D4AF16299EB87A6585BAE917" ++ " DEF27FCDD165764D069BC18D16527B29DAAB549F7BBED4A7C6A842D203ED6613" ++ " 6E2411744E432CD26D940132F25874483DCAEECDFD95744819CBCF1EA810681C" ++ " 42907EBCB1C7EAFBE75C87EC32C5413EA10476545D3FC7B2ADB1B66B7F200918" ++ " 664B0E5261C2895AA28B0DE321E921B3F877172CCCAB81F43EF98002916156F6" ++ " CB#)\n" ++ " (e #010001#)\n" ++ " (d #07EF82500C403899934FE993AC5A36F14FF2DF38CF1EF315F205EE4C83EDAA19" ++ " 8890FC23DE9AA933CAFB37B6A8A8DBA675411958337287310D3FF2F1DDC0CB93" ++ " 7E70F57F75F833C021852B631D2B9A520E4431A03C5C3FCB5742DCD841D9FB12" ++ " 771AA1620DCEC3F1583426066ED9DC3F7028C5B59202C88FDF20396E2FA0EC4F" ++ " 5A22D9008F3043673931BC14A5046D6327398327900867E39CC61B2D1AFE2F48" ++ " EC8E1E3861C68D257D7425F4E6F99ABD77D61F10CA100EFC14389071831B33DD" ++ " 69CC8EABEF860D1DC2AAA84ABEAE5DFC91BC124DAF0F4C8EF5BBEA436751DE84" ++ " 3A8063E827A024466F44C28614F93B0732A100D4A0D86D532FE1E22C7725E401" ++ " #)\n" ++ " (p #00C29D438F115825779631CD665A5739367F3E128ADC29766483A46CA80897E0" ++ " 79B32881860B8F9A6A04C2614A904F6F2578DAE13EA67CD60AE3D0AA00A1FF9B" ++ " 441485E44B2DC3D0B60260FBFE073B5AC72FAF67964DE15C8212C389D20DB9CF" ++ " 54AF6AEF5C4196EAA56495DD30CF709F499D5AB30CA35E086C2A1589D6283F17" ++ " 83#)\n" ++ " (q #00D1984135231CB243FE959C0CBEF551EDD986AD7BEDF71EDF447BE3DA27AF46" ++ " 79C974A6FA69E4D52FE796650623DE70622862713932AA2FD9F2EC856EAEAA77" ++ " 88B4EA6084DC81C902F014829B18EA8B2666EC41586818E0589E18876065F97E" ++ " 8D22CE2DA53A05951EC132DCEF41E70A9C35F4ACC268FFAC2ADF54FA1DA110B9" ++ " 19#)\n" ++ " (u #67CF0FD7635205DD80FA814EE9E9C267C17376BF3209FB5D1BC42890D2822A04" ++ " 479DAF4D5B6ED69D0F8D1AF94164D07F8CD52ECEFE880641FA0F41DDAB1785E4" ++ " A37A32F997A516480B4CD4F6482B9466A1765093ED95023CA32D5EDC1E34CEE9" ++ " AF595BC51FE43C4BF810FA225AF697FB473B83815966188A4312C048B885E3F7" ++ " #)))\n", ++ "(public-key\n" ++ " (rsa\n" ++ " (n #009F56231A3D82E3E7D613D59D53E9AB921BEF9F08A782AED0B6E46ADBC853EC" ++ " 7C71C422435A3CD8FA0DB9EFD55CD3295BADC4E8E2E2B94E15AE82866AB8ADE8" ++ " 7E469FAE76DC3577DE87F1F419C4EB41123DFAF8D16922D5EDBAD6E9076D5A1C" ++ " 958106F0AE5E2E9193C6B49124C64C2A241C4075D4AF16299EB87A6585BAE917" ++ " DEF27FCDD165764D069BC18D16527B29DAAB549F7BBED4A7C6A842D203ED6613" ++ " 6E2411744E432CD26D940132F25874483DCAEECDFD95744819CBCF1EA810681C" ++ " 42907EBCB1C7EAFBE75C87EC32C5413EA10476545D3FC7B2ADB1B66B7F200918" ++ " 664B0E5261C2895AA28B0DE321E921B3F877172CCCAB81F43EF98002916156F6" ++ " CB#)\n" ++ " (e #010001#)))\n", ++ "(data\n (flags pkcs1)\n" ++ " (hash sha1 #11223344556677889900AABBCCDDEEFF10203040#))\n", ++ 1 ++ }, ++ { /* RSA with unknown hash for signing */ ++ "(private-key" ++ " (rsa" ++ " (n #009F56231A3D82E3E7D613D59D53E9AB921BEF9F08A782AED0B6E46ADBC853EC" ++ " 7C71C422435A3CD8FA0DB9EFD55CD3295BADC4E8E2E2B94E15AE82866AB8ADE8" ++ " 7E469FAE76DC3577DE87F1F419C4EB41123DFAF8D16922D5EDBAD6E9076D5A1C" ++ " 958106F0AE5E2E9193C6B49124C64C2A241C4075D4AF16299EB87A6585BAE917" ++ " DEF27FCDD165764D069BC18D16527B29DAAB549F7BBED4A7C6A842D203ED6613" ++ " 6E2411744E432CD26D940132F25874483DCAEECDFD95744819CBCF1EA810681C" ++ " 42907EBCB1C7EAFBE75C87EC32C5413EA10476545D3FC7B2ADB1B66B7F200918" ++ " 664B0E5261C2895AA28B0DE321E921B3F877172CCCAB81F43EF98002916156F6" ++ " CB#)\n" ++ " (e #010001#)\n" ++ " (d #07EF82500C403899934FE993AC5A36F14FF2DF38CF1EF315F205EE4C83EDAA19" ++ " 8890FC23DE9AA933CAFB37B6A8A8DBA675411958337287310D3FF2F1DDC0CB93" ++ " 7E70F57F75F833C021852B631D2B9A520E4431A03C5C3FCB5742DCD841D9FB12" ++ " 771AA1620DCEC3F1583426066ED9DC3F7028C5B59202C88FDF20396E2FA0EC4F" ++ " 5A22D9008F3043673931BC14A5046D6327398327900867E39CC61B2D1AFE2F48" ++ " EC8E1E3861C68D257D7425F4E6F99ABD77D61F10CA100EFC14389071831B33DD" ++ " 69CC8EABEF860D1DC2AAA84ABEAE5DFC91BC124DAF0F4C8EF5BBEA436751DE84" ++ " 3A8063E827A024466F44C28614F93B0732A100D4A0D86D532FE1E22C7725E401" ++ " #)\n" ++ " (p #00C29D438F115825779631CD665A5739367F3E128ADC29766483A46CA80897E0" ++ " 79B32881860B8F9A6A04C2614A904F6F2578DAE13EA67CD60AE3D0AA00A1FF9B" ++ " 441485E44B2DC3D0B60260FBFE073B5AC72FAF67964DE15C8212C389D20DB9CF" ++ " 54AF6AEF5C4196EAA56495DD30CF709F499D5AB30CA35E086C2A1589D6283F17" ++ " 83#)\n" ++ " (q #00D1984135231CB243FE959C0CBEF551EDD986AD7BEDF71EDF447BE3DA27AF46" ++ " 79C974A6FA69E4D52FE796650623DE70622862713932AA2FD9F2EC856EAEAA77" ++ " 88B4EA6084DC81C902F014829B18EA8B2666EC41586818E0589E18876065F97E" ++ " 8D22CE2DA53A05951EC132DCEF41E70A9C35F4ACC268FFAC2ADF54FA1DA110B9" ++ " 19#)\n" ++ " (u #67CF0FD7635205DD80FA814EE9E9C267C17376BF3209FB5D1BC42890D2822A04" ++ " 479DAF4D5B6ED69D0F8D1AF94164D07F8CD52ECEFE880641FA0F41DDAB1785E4" ++ " A37A32F997A516480B4CD4F6482B9466A1765093ED95023CA32D5EDC1E34CEE9" ++ " AF595BC51FE43C4BF810FA225AF697FB473B83815966188A4312C048B885E3F7" ++ " #)))\n", ++ "(public-key\n" ++ " (rsa\n" ++ " (n #009F56231A3D82E3E7D613D59D53E9AB921BEF9F08A782AED0B6E46ADBC853EC" ++ " 7C71C422435A3CD8FA0DB9EFD55CD3295BADC4E8E2E2B94E15AE82866AB8ADE8" ++ " 7E469FAE76DC3577DE87F1F419C4EB41123DFAF8D16922D5EDBAD6E9076D5A1C" ++ " 958106F0AE5E2E9193C6B49124C64C2A241C4075D4AF16299EB87A6585BAE917" ++ " DEF27FCDD165764D069BC18D16527B29DAAB549F7BBED4A7C6A842D203ED6613" ++ " 6E2411744E432CD26D940132F25874483DCAEECDFD95744819CBCF1EA810681C" ++ " 42907EBCB1C7EAFBE75C87EC32C5413EA10476545D3FC7B2ADB1B66B7F200918" ++ " 664B0E5261C2895AA28B0DE321E921B3F877172CCCAB81F43EF98002916156F6" ++ " CB#)\n" ++ " (e #010001#)))\n", ++ "(data\n (flags pkcs1-raw)\n" ++ " (value " ++ "#00112233445566778899AABBCCDDEEFF000102030405060708090A0B0C0D0E0F#))\n", ++ 1 ++ }, ++ { /* RSA with compliant hash for signing */ ++ "(private-key" ++ " (rsa" ++ " (n #009F56231A3D82E3E7D613D59D53E9AB921BEF9F08A782AED0B6E46ADBC853EC" ++ " 7C71C422435A3CD8FA0DB9EFD55CD3295BADC4E8E2E2B94E15AE82866AB8ADE8" ++ " 7E469FAE76DC3577DE87F1F419C4EB41123DFAF8D16922D5EDBAD6E9076D5A1C" ++ " 958106F0AE5E2E9193C6B49124C64C2A241C4075D4AF16299EB87A6585BAE917" ++ " DEF27FCDD165764D069BC18D16527B29DAAB549F7BBED4A7C6A842D203ED6613" ++ " 6E2411744E432CD26D940132F25874483DCAEECDFD95744819CBCF1EA810681C" ++ " 42907EBCB1C7EAFBE75C87EC32C5413EA10476545D3FC7B2ADB1B66B7F200918" ++ " 664B0E5261C2895AA28B0DE321E921B3F877172CCCAB81F43EF98002916156F6" ++ " CB#)\n" ++ " (e #010001#)\n" ++ " (d #07EF82500C403899934FE993AC5A36F14FF2DF38CF1EF315F205EE4C83EDAA19" ++ " 8890FC23DE9AA933CAFB37B6A8A8DBA675411958337287310D3FF2F1DDC0CB93" ++ " 7E70F57F75F833C021852B631D2B9A520E4431A03C5C3FCB5742DCD841D9FB12" ++ " 771AA1620DCEC3F1583426066ED9DC3F7028C5B59202C88FDF20396E2FA0EC4F" ++ " 5A22D9008F3043673931BC14A5046D6327398327900867E39CC61B2D1AFE2F48" ++ " EC8E1E3861C68D257D7425F4E6F99ABD77D61F10CA100EFC14389071831B33DD" ++ " 69CC8EABEF860D1DC2AAA84ABEAE5DFC91BC124DAF0F4C8EF5BBEA436751DE84" ++ " 3A8063E827A024466F44C28614F93B0732A100D4A0D86D532FE1E22C7725E401" ++ " #)\n" ++ " (p #00C29D438F115825779631CD665A5739367F3E128ADC29766483A46CA80897E0" ++ " 79B32881860B8F9A6A04C2614A904F6F2578DAE13EA67CD60AE3D0AA00A1FF9B" ++ " 441485E44B2DC3D0B60260FBFE073B5AC72FAF67964DE15C8212C389D20DB9CF" ++ " 54AF6AEF5C4196EAA56495DD30CF709F499D5AB30CA35E086C2A1589D6283F17" ++ " 83#)\n" ++ " (q #00D1984135231CB243FE959C0CBEF551EDD986AD7BEDF71EDF447BE3DA27AF46" ++ " 79C974A6FA69E4D52FE796650623DE70622862713932AA2FD9F2EC856EAEAA77" ++ " 88B4EA6084DC81C902F014829B18EA8B2666EC41586818E0589E18876065F97E" ++ " 8D22CE2DA53A05951EC132DCEF41E70A9C35F4ACC268FFAC2ADF54FA1DA110B9" ++ " 19#)\n" ++ " (u #67CF0FD7635205DD80FA814EE9E9C267C17376BF3209FB5D1BC42890D2822A04" ++ " 479DAF4D5B6ED69D0F8D1AF94164D07F8CD52ECEFE880641FA0F41DDAB1785E4" ++ " A37A32F997A516480B4CD4F6482B9466A1765093ED95023CA32D5EDC1E34CEE9" ++ " AF595BC51FE43C4BF810FA225AF697FB473B83815966188A4312C048B885E3F7" ++ " #)))\n", ++ "(public-key\n" ++ " (rsa\n" ++ " (n #009F56231A3D82E3E7D613D59D53E9AB921BEF9F08A782AED0B6E46ADBC853EC" ++ " 7C71C422435A3CD8FA0DB9EFD55CD3295BADC4E8E2E2B94E15AE82866AB8ADE8" ++ " 7E469FAE76DC3577DE87F1F419C4EB41123DFAF8D16922D5EDBAD6E9076D5A1C" ++ " 958106F0AE5E2E9193C6B49124C64C2A241C4075D4AF16299EB87A6585BAE917" ++ " DEF27FCDD165764D069BC18D16527B29DAAB549F7BBED4A7C6A842D203ED6613" ++ " 6E2411744E432CD26D940132F25874483DCAEECDFD95744819CBCF1EA810681C" ++ " 42907EBCB1C7EAFBE75C87EC32C5413EA10476545D3FC7B2ADB1B66B7F200918" ++ " 664B0E5261C2895AA28B0DE321E921B3F877172CCCAB81F43EF98002916156F6" ++ " CB#)\n" ++ " (e #010001#)))\n", ++ "(data\n (flags pss)\n" ++ " (hash sha256 " ++ "#00112233445566778899AABBCCDDEEFF000102030405060708090A0B0C0D0E0F#))\n", ++ 0 ++ }, ++ { /* RSA with non-compliant hash for signing */ ++ "(private-key" ++ " (rsa" ++ " (n #009F56231A3D82E3E7D613D59D53E9AB921BEF9F08A782AED0B6E46ADBC853EC" ++ " 7C71C422435A3CD8FA0DB9EFD55CD3295BADC4E8E2E2B94E15AE82866AB8ADE8" ++ " 7E469FAE76DC3577DE87F1F419C4EB41123DFAF8D16922D5EDBAD6E9076D5A1C" ++ " 958106F0AE5E2E9193C6B49124C64C2A241C4075D4AF16299EB87A6585BAE917" ++ " DEF27FCDD165764D069BC18D16527B29DAAB549F7BBED4A7C6A842D203ED6613" ++ " 6E2411744E432CD26D940132F25874483DCAEECDFD95744819CBCF1EA810681C" ++ " 42907EBCB1C7EAFBE75C87EC32C5413EA10476545D3FC7B2ADB1B66B7F200918" ++ " 664B0E5261C2895AA28B0DE321E921B3F877172CCCAB81F43EF98002916156F6" ++ " CB#)\n" ++ " (e #010001#)\n" ++ " (d #07EF82500C403899934FE993AC5A36F14FF2DF38CF1EF315F205EE4C83EDAA19" ++ " 8890FC23DE9AA933CAFB37B6A8A8DBA675411958337287310D3FF2F1DDC0CB93" ++ " 7E70F57F75F833C021852B631D2B9A520E4431A03C5C3FCB5742DCD841D9FB12" ++ " 771AA1620DCEC3F1583426066ED9DC3F7028C5B59202C88FDF20396E2FA0EC4F" ++ " 5A22D9008F3043673931BC14A5046D6327398327900867E39CC61B2D1AFE2F48" ++ " EC8E1E3861C68D257D7425F4E6F99ABD77D61F10CA100EFC14389071831B33DD" ++ " 69CC8EABEF860D1DC2AAA84ABEAE5DFC91BC124DAF0F4C8EF5BBEA436751DE84" ++ " 3A8063E827A024466F44C28614F93B0732A100D4A0D86D532FE1E22C7725E401" ++ " #)\n" ++ " (p #00C29D438F115825779631CD665A5739367F3E128ADC29766483A46CA80897E0" ++ " 79B32881860B8F9A6A04C2614A904F6F2578DAE13EA67CD60AE3D0AA00A1FF9B" ++ " 441485E44B2DC3D0B60260FBFE073B5AC72FAF67964DE15C8212C389D20DB9CF" ++ " 54AF6AEF5C4196EAA56495DD30CF709F499D5AB30CA35E086C2A1589D6283F17" ++ " 83#)\n" ++ " (q #00D1984135231CB243FE959C0CBEF551EDD986AD7BEDF71EDF447BE3DA27AF46" ++ " 79C974A6FA69E4D52FE796650623DE70622862713932AA2FD9F2EC856EAEAA77" ++ " 88B4EA6084DC81C902F014829B18EA8B2666EC41586818E0589E18876065F97E" ++ " 8D22CE2DA53A05951EC132DCEF41E70A9C35F4ACC268FFAC2ADF54FA1DA110B9" ++ " 19#)\n" ++ " (u #67CF0FD7635205DD80FA814EE9E9C267C17376BF3209FB5D1BC42890D2822A04" ++ " 479DAF4D5B6ED69D0F8D1AF94164D07F8CD52ECEFE880641FA0F41DDAB1785E4" ++ " A37A32F997A516480B4CD4F6482B9466A1765093ED95023CA32D5EDC1E34CEE9" ++ " AF595BC51FE43C4BF810FA225AF697FB473B83815966188A4312C048B885E3F7" ++ " #)))\n", ++ "(public-key\n" ++ " (rsa\n" ++ " (n #009F56231A3D82E3E7D613D59D53E9AB921BEF9F08A782AED0B6E46ADBC853EC" ++ " 7C71C422435A3CD8FA0DB9EFD55CD3295BADC4E8E2E2B94E15AE82866AB8ADE8" ++ " 7E469FAE76DC3577DE87F1F419C4EB41123DFAF8D16922D5EDBAD6E9076D5A1C" ++ " 958106F0AE5E2E9193C6B49124C64C2A241C4075D4AF16299EB87A6585BAE917" ++ " DEF27FCDD165764D069BC18D16527B29DAAB549F7BBED4A7C6A842D203ED6613" ++ " 6E2411744E432CD26D940132F25874483DCAEECDFD95744819CBCF1EA810681C" ++ " 42907EBCB1C7EAFBE75C87EC32C5413EA10476545D3FC7B2ADB1B66B7F200918" ++ " 664B0E5261C2895AA28B0DE321E921B3F877172CCCAB81F43EF98002916156F6" ++ " CB#)\n" ++ " (e #010001#)))\n", ++ "(data\n (flags pss)\n" ++ " (hash sha1 #11223344556677889900AABBCCDDEEFF10203040#))\n", ++ 1 ++ } + }; + int tvidx; + gpg_error_t err; +-- +2.49.0 + diff --git a/libgcrypt-cipher-visibility-Differentiate-use-of-random-override-in-the-SLI.patch b/libgcrypt-cipher-visibility-Differentiate-use-of-random-override-in-the-SLI.patch new file mode 100644 index 0000000..413aa34 --- /dev/null +++ b/libgcrypt-cipher-visibility-Differentiate-use-of-random-override-in-the-SLI.patch @@ -0,0 +1,107 @@ +From 234eb316b0a04c50e8511a570775ded45060f18b Mon Sep 17 00:00:00 2001 +From: Lucas Mulling via Gcrypt-devel +Date: Wed, 26 Feb 2025 17:19:24 -0300 +Subject: [PATCH 08/14] cipher,visibility: Differentiate use of random-override + in the SLI +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* cipher/pubkey-util.c (_gcry_pk_util_data_to_mpi, +_gcry_pk_single_data_push, _gcry_pk_util_free_encoding_ctx): +Differentiate use of random-override in the SLI. +* src/visibility.c (gcry_pk_random_override_new): +Differentiate use explicit random override in the SLI. + +GnuPG-bug-id: 7338 +Signed-off-by: Lucas Mulling +Signed-off-by: Lucas Mülling +--- + cipher/pubkey-util.c | 33 +++++++++++++++++++++++++++++++++ + src/visibility.c | 12 ++++++++++++ + 2 files changed, 45 insertions(+) + +diff --git a/cipher/pubkey-util.c b/cipher/pubkey-util.c +index e7355569..66a04f13 100644 +--- a/cipher/pubkey-util.c ++++ b/cipher/pubkey-util.c +@@ -973,6 +973,17 @@ _gcry_pk_util_data_to_mpi (gcry_sexp_t input, gcry_mpi_t *ret_mpi, + list = sexp_find_token (ldata, "random-override", 0); + if (list) + { ++ if (fips_mode ()) ++ { ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) ++ { ++ sexp_release (list); ++ rc = GPG_ERR_INV_FLAG; ++ goto leave; ++ } ++ else ++ fips_service_indicator_mark_non_compliant (); ++ } + s = sexp_nth_data (list, 1, &n); + if (!s) + rc = GPG_ERR_NO_OBJ; +@@ -1149,6 +1160,17 @@ _gcry_pk_util_data_to_mpi (gcry_sexp_t input, gcry_mpi_t *ret_mpi, + list = sexp_find_token (ldata, "random-override", 0); + if (list) + { ++ if (fips_mode ()) ++ { ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) ++ { ++ sexp_release (list); ++ rc = GPG_ERR_INV_FLAG; ++ goto leave; ++ } ++ else ++ fips_service_indicator_mark_non_compliant (); ++ } + s = sexp_nth_data (list, 1, &n); + if (!s) + rc = GPG_ERR_NO_OBJ; +@@ -1248,6 +1270,17 @@ _gcry_pk_util_data_to_mpi (gcry_sexp_t input, gcry_mpi_t *ret_mpi, + list = sexp_find_token (ldata, "random-override", 0); + if (list) + { ++ if (fips_mode ()) ++ { ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) ++ { ++ sexp_release (list); ++ rc = GPG_ERR_INV_FLAG; ++ goto leave; ++ } ++ else ++ fips_service_indicator_mark_non_compliant (); ++ } + s = sexp_nth_data (list, 1, &n); + if (!s) + rc = GPG_ERR_NO_OBJ; +diff --git a/src/visibility.c b/src/visibility.c +index 4134446a..ccd0de69 100644 +--- a/src/visibility.c ++++ b/src/visibility.c +@@ -1085,6 +1085,18 @@ gcry_pk_hash_verify (gcry_sexp_t sigval, const char *data_tmpl, gcry_sexp_t pkey + gcry_error_t + gcry_pk_random_override_new (gcry_ctx_t *r_ctx, const unsigned char *p, size_t len) + { ++ if (!fips_is_operational ()) ++ return gpg_error (fips_not_operational ()); ++ fips_service_indicator_init (); ++ ++ if (fips_mode ()) ++ { ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) ++ return gpg_error (GPG_ERR_INV_OP); ++ else ++ fips_service_indicator_mark_non_compliant (); ++ } ++ + return gpg_error (_gcry_pk_single_data_push (r_ctx, p, len)); + } + +-- +2.49.0 + diff --git a/libgcrypt-doc-Add-about-GCRYCTL_FIPS_SERVICE_INDICATOR.patch b/libgcrypt-doc-Add-about-GCRYCTL_FIPS_SERVICE_INDICATOR.patch new file mode 100644 index 0000000..a9e9522 --- /dev/null +++ b/libgcrypt-doc-Add-about-GCRYCTL_FIPS_SERVICE_INDICATOR.patch @@ -0,0 +1,66 @@ +From 636f40cb78587635ef663bfc3430937cf140f245 Mon Sep 17 00:00:00 2001 +From: NIIBE Yutaka +Date: Thu, 13 Mar 2025 15:02:58 +0900 +Subject: [PATCH 13/14] doc: Add about GCRYCTL_FIPS_SERVICE_INDICATOR. +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* doc/gcrypt.texi (GCRYCTL_FIPS_SERVICE_INDICATOR): Add a description. +(GCRYCTL_FIPS_REJECT_NON_FIPS): Likewise. + +-- + +GnuPG-bug-id: 7338 +Signed-off-by: NIIBE Yutaka +Signed-off-by: Lucas Mülling +--- + doc/gcrypt.texi | 32 ++++++++++++++++++++++++++++++++ + 1 file changed, 32 insertions(+) + +diff --git a/doc/gcrypt.texi b/doc/gcrypt.texi +index 5d428738..6e82a41b 100644 +--- a/doc/gcrypt.texi ++++ b/doc/gcrypt.texi +@@ -1052,6 +1052,38 @@ is responsible to check also the internal members. For example: + /* ok */ + @end example + ++@item GCRYCTL_FIPS_SERVICE_INDICATOR; Arguments: none ++This commands provides ``dynamic'' service indicator. ++ ++After a function call (of the use of security services), this command ++can be used to check if the call is valid or not. If the computation ++is done in an approved way, it returns @code{GPG_ERR_NO_ERROR}. ++Otherwise @code{GPG_ERR_NOT_SUPPORTED} is returned. ++ ++An application may use this command directly or use the convenience ++macro below. ++ ++@deftypefun gcry_error_t gcry_get_fips_service_indicator (void) ++ ++Returns @code{GPG_ERR_NO_ERROR} if a preceeding function call is ++valid. Otherwise @code{GPG_ERR_NOT_SUPPORTED} is returned. ++@end deftypefun ++ ++@item GCRYCTL_FIPS_REJECT_NON_FIPS; Arguments: unsigned int flags ++In Libgcrypt 1.10, static implicit indicator is used; For an approved ++function (which can be checked by ++GCRYCTL_FIPS_SERVICE_INDICATOR_FUNCTION command) with an approved ++algo/operation (which can be checked GCRYCTL_FIPS_SERVICE_INDICATOR_* ++command), success of the function call means that it's valid and error ++return (rejection) means it's invalid. This command controls thread ++specific behavior of the rejection. ++ ++When using ``dynamic'' service indicator, this command with FLAGS=0 ++disables all rejections. ++@example ++ gcry_control (GCRYCTL_FIPS_REJECT_NON_FIPS, 0); ++@endexample ++ + @end table + + @end deftypefun +-- +2.49.0 + diff --git a/libgcrypt-doc-Fix-syntax-error.patch b/libgcrypt-doc-Fix-syntax-error.patch new file mode 100644 index 0000000..b85eb54 --- /dev/null +++ b/libgcrypt-doc-Fix-syntax-error.patch @@ -0,0 +1,31 @@ +From 22e65f6f5b8dbddf925151894426e4c06d33803b Mon Sep 17 00:00:00 2001 +From: Werner Koch +Date: Thu, 13 Mar 2025 18:06:37 +0100 +Subject: [PATCH 14/14] doc: Fix syntax error +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +-- + +Signed-off-by: Lucas Mülling +--- + doc/gcrypt.texi | 2 +- + 1 file changed, 1 insertion(+), 1 deletion(-) + +diff --git a/doc/gcrypt.texi b/doc/gcrypt.texi +index 6e82a41b..eeab1a78 100644 +--- a/doc/gcrypt.texi ++++ b/doc/gcrypt.texi +@@ -1082,7 +1082,7 @@ When using ``dynamic'' service indicator, this command with FLAGS=0 + disables all rejections. + @example + gcry_control (GCRYCTL_FIPS_REJECT_NON_FIPS, 0); +-@endexample ++@end example + + @end table + +-- +2.49.0 + diff --git a/libgcrypt-fips-Change-the-internal-API-for-new-FIPS-service-indicator.patch b/libgcrypt-fips-Change-the-internal-API-for-new-FIPS-service-indicator.patch new file mode 100644 index 0000000..8638218 --- /dev/null +++ b/libgcrypt-fips-Change-the-internal-API-for-new-FIPS-service-indicator.patch @@ -0,0 +1,140 @@ +From 4799914966a7f94f41e1ed5b7b62fded7ba09704 Mon Sep 17 00:00:00 2001 +From: NIIBE Yutaka +Date: Thu, 12 Dec 2024 11:03:38 +0900 +Subject: [PATCH 01/19] fips: Change the internal API for new FIPS service + indicator. +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* src/gcrypt-int.h (fips_service_indicator_init): Initialize by 0. +(fips_service_indicator_mark_success): Remove. +(fips_service_indicator_mark_non_compliant): New. +* cipher/kdf.c (_gcry_kdf_derive): Follow the change of the API. +* cipher/md.c (_gcry_md_hash_buffer): Likewise. +(_gcry_md_hash_buffers_extract): Likewise. + +-- + +GnuPG-bug-id: 7338 +Signed-off-by: NIIBE Yutaka +Signed-off-by: Lucas Mülling +--- + cipher/kdf.c | 17 +++++++++-------- + cipher/md.c | 8 ++++---- + src/gcrypt-int.h | 9 +++------ + 3 files changed, 16 insertions(+), 18 deletions(-) + +diff --git a/cipher/kdf.c b/cipher/kdf.c +index 1eae2b90..71156ea4 100644 +--- a/cipher/kdf.c ++++ b/cipher/kdf.c +@@ -248,6 +248,7 @@ _gcry_kdf_derive (const void *passphrase, size_t passphraselen, + size_t keysize, void *keybuffer) + { + gpg_err_code_t ec; ++ int is_compliant_algo = 0; + + if (!passphrase) + { +@@ -279,35 +280,32 @@ _gcry_kdf_derive (const void *passphrase, size_t passphraselen, + break; + + case GCRY_KDF_PBKDF2: ++ is_compliant_algo = 1; + if (!saltlen || !iterations) + ec = GPG_ERR_INV_VALUE; + else + { +- int is_compliant = 1; +- + if (fips_mode ()) + { + /* FIPS requires minimum passphrase length, see FIPS 140-3 IG D.N */ + if (passphraselen < 8) +- is_compliant &= 0; ++ fips_service_indicator_mark_non_compliant (); + + /* FIPS requires minimum salt length of 128 b (SP 800-132 sec. 5.1, p.6) */ + if (saltlen < 16) +- is_compliant &= 0; ++ fips_service_indicator_mark_non_compliant (); + + /* FIPS requires minimum iterations bound (SP 800-132 sec 5.2, p.6) */ + if (iterations < 1000) +- is_compliant &= 0; ++ fips_service_indicator_mark_non_compliant (); + + /* Check minimum key size */ + if (keysize < 14) +- is_compliant &= 0; ++ fips_service_indicator_mark_non_compliant (); + } + + ec = _gcry_kdf_pkdf2 (passphrase, passphraselen, subalgo, + salt, saltlen, iterations, keysize, keybuffer); +- if (!ec) +- fips_service_indicator_mark_success (is_compliant); + } + break; + +@@ -326,6 +324,9 @@ _gcry_kdf_derive (const void *passphrase, size_t passphraselen, + break; + } + ++ if (!ec && !is_compliant_algo && fips_mode ()) ++ fips_service_indicator_mark_non_compliant (); ++ + leave: + return ec; + } +diff --git a/cipher/md.c b/cipher/md.c +index c2bd18c6..ef2fc5a4 100644 +--- a/cipher/md.c ++++ b/cipher/md.c +@@ -1286,8 +1286,8 @@ _gcry_md_hash_buffer (int algo, void *digest, + + if (fips_mode ()) + { +- int is_compliant = spec->flags.fips; +- fips_service_indicator_mark_success (is_compliant); ++ if (!spec->flags.fips) ++ fips_service_indicator_mark_non_compliant (); + } + } + +@@ -1384,8 +1384,8 @@ _gcry_md_hash_buffers_extract (int algo, unsigned int flags, void *digest, + + if (fips_mode ()) + { +- int is_compliant = spec->flags.fips; +- fips_service_indicator_mark_success (is_compliant); ++ if (!spec->flags.fips) ++ fips_service_indicator_mark_non_compliant (); + } + + return 0; +diff --git a/src/gcrypt-int.h b/src/gcrypt-int.h +index 7f894737..aa49d766 100644 +--- a/src/gcrypt-int.h ++++ b/src/gcrypt-int.h +@@ -303,13 +303,10 @@ unsigned long _gcry_thread_context_get_fsi (void); + #define fips_service_indicator_init() do \ + { \ + if (fips_mode ()) \ +- _gcry_thread_context_set_fsi (1); \ +- } while (0) +-#define fips_service_indicator_mark_success(is_compliant) do \ +- { \ +- if (is_compliant && fips_mode ()) \ +- _gcry_thread_context_set_fsi (0); \ ++ _gcry_thread_context_set_fsi (0); \ + } while (0) ++/* Should be used only when fips_mode()==TRUE. */ ++#define fips_service_indicator_mark_non_compliant() _gcry_thread_context_set_fsi (1) + + /* Return a pointer to a string containing a description of the error + code in the error value ERR. */ +-- +2.49.0 + diff --git a/libgcrypt-fips-Fix-GCRY_FIPS_FLAG_REJECT_MD.patch b/libgcrypt-fips-Fix-GCRY_FIPS_FLAG_REJECT_MD.patch new file mode 100644 index 0000000..aa6f093 --- /dev/null +++ b/libgcrypt-fips-Fix-GCRY_FIPS_FLAG_REJECT_MD.patch @@ -0,0 +1,42 @@ +From b9eb8f4cb81801d68580627ad2188607a8c5f2ec Mon Sep 17 00:00:00 2001 +From: NIIBE Yutaka +Date: Thu, 13 Mar 2025 15:01:21 +0900 +Subject: [PATCH 12/14] fips: Fix GCRY_FIPS_FLAG_REJECT_MD. +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* src/gcrypt.h.in (GCRY_FIPS_FLAG_REJECT_MD): Include SHA1. + +-- + +Fixes-commit: 4ee91a94bcdad32aed4364d09e3daf8841fa579f +Signed-off-by: NIIBE Yutaka +Signed-off-by: Lucas Mülling +--- + src/gcrypt.h.in | 8 +++++--- + 1 file changed, 5 insertions(+), 3 deletions(-) + +diff --git a/src/gcrypt.h.in b/src/gcrypt.h.in +index b2b8853f..a9c36aa6 100644 +--- a/src/gcrypt.h.in ++++ b/src/gcrypt.h.in +@@ -1994,10 +1994,12 @@ char *gcry_get_config (int mode, const char *what); + #define GCRY_FIPS_FLAG_REJECT_PK_ECC_K (1 << 10) + #define GCRY_FIPS_FLAG_REJECT_PK_FLAGS (1 << 11) + +-#define GCRY_FIPS_FLAG_REJECT_MD \ +- (GCRY_FIPS_FLAG_REJECT_MD_MD5 | GCRY_FIPS_FLAG_REJECT_MD_OTHERS) ++#define GCRY_FIPS_FLAG_REJECT_MD \ ++ (GCRY_FIPS_FLAG_REJECT_MD_MD5 | GCRY_FIPS_FLAG_REJECT_MD_SHA1 \ ++ | GCRY_FIPS_FLAG_REJECT_MD_OTHERS) + +-/* Note: Don't reject MD5, PK MD, PK GOST, PK SM2, PK ECC K, and PK FLAGS */ ++/* Note: Don't reject MD5, PK MD, PK GOST, PK SM2, ++ SHA1, PK ECC K, and PK FLAGS */ + #define GCRY_FIPS_FLAG_REJECT_COMPAT110 \ + (GCRY_FIPS_FLAG_REJECT_MD_OTHERS \ + | GCRY_FIPS_FLAG_REJECT_MAC \ +-- +2.49.0 + diff --git a/libgcrypt-fips-Introduce-GCRYCTL_FIPS_REJECT_NON_FIPS.patch b/libgcrypt-fips-Introduce-GCRYCTL_FIPS_REJECT_NON_FIPS.patch new file mode 100644 index 0000000..d08a59a --- /dev/null +++ b/libgcrypt-fips-Introduce-GCRYCTL_FIPS_REJECT_NON_FIPS.patch @@ -0,0 +1,261 @@ +From e52adf0948c60b2e9accd7996fcece0f9b443763 Mon Sep 17 00:00:00 2001 +From: NIIBE Yutaka +Date: Thu, 19 Dec 2024 11:30:28 +0900 +Subject: [PATCH 12/19] fips: Introduce GCRYCTL_FIPS_REJECT_NON_FIPS. +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* src/gcrypt.h.in (GCRYCTL_FIPS_REJECT_NON_FIPS): New. +(GCRY_FIPS_FLAG_REJECT_*): New. +* src/fips.c (struct gcry_thread_context): Add flags_reject_non_fips. +(the_tc): Add initial value. +(_gcry_thread_context_set_reject): New. +(_gcry_thread_context_check_rejection): New. +* src/gcrypt-int.h (fips_check_rejection): New. +* src/global.c (_gcry_vcontrol): Handle GCRYCTL_FIPS_REJECT_NON_FIPS. +* tests/t-fips-service-ind.c (main): Use GCRYCTL_FIPS_REJECT_NON_FIPS. + +-- + +GnuPG-bug-id: 7338 +Signed-off-by: NIIBE Yutaka +Signed-off-by: Lucas Mülling +--- + cipher/ecc-curves.c | 7 ++++++- + cipher/pubkey.c | 34 ++++++++++++++++++++++++++-------- + src/fips.c | 17 ++++++++++++++++- + src/gcrypt-int.h | 9 ++++++++- + src/gcrypt.h.in | 28 ++++++++++++++++++++++++++-- + src/global.c | 7 +++++++ + tests/t-fips-service-ind.c | 2 ++ + 7 files changed, 91 insertions(+), 13 deletions(-) + +Index: libgcrypt-1.11.0/cipher/ecc-curves.c +=================================================================== +--- libgcrypt-1.11.0.orig/cipher/ecc-curves.c ++++ libgcrypt-1.11.0/cipher/ecc-curves.c +@@ -645,7 +645,12 @@ _gcry_ecc_fill_in_curve (unsigned int nb + possible to bypass this check by specifying the curve parameters + directly. */ + if (fips_mode () && !domain_parms[idx].fips ) +- fips_service_indicator_mark_non_compliant (); ++ { ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) ++ return GPG_ERR_NOT_SUPPORTED; ++ else ++ fips_service_indicator_mark_non_compliant (); ++ } + + switch (domain_parms[idx].model) + { +Index: libgcrypt-1.11.0/cipher/pubkey.c +=================================================================== +--- libgcrypt-1.11.0.orig/cipher/pubkey.c ++++ libgcrypt-1.11.0/cipher/pubkey.c +@@ -510,7 +510,12 @@ prepare_datasexp_to_be_signed (const cha + algo = _gcry_md_get_algo (hd); + + if (fips_mode () && algo == GCRY_MD_SHA1) +- fips_service_indicator_mark_non_compliant (); ++ { ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) ++ return GPG_ERR_DIGEST_ALGO; ++ else ++ fips_service_indicator_mark_non_compliant (); ++ } + + digest_name = _gcry_md_algo_name (algo); + digest_size = (int)_gcry_md_get_algo_dlen (algo); +@@ -538,7 +543,12 @@ prepare_datasexp_to_be_signed (const cha + return GPG_ERR_DIGEST_ALGO; + } + else if (fips_mode () && algo == GCRY_MD_SHA1) +- fips_service_indicator_mark_non_compliant (); ++ { ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) ++ return GPG_ERR_DIGEST_ALGO; ++ else ++ fips_service_indicator_mark_non_compliant (); ++ } + + digest_size = (int)_gcry_md_get_algo_dlen (algo); + digest = _gcry_md_read (hd, algo); +@@ -611,11 +621,15 @@ _gcry_pk_sign_md (gcry_sexp_t *r_sig, co + if (rc) + goto leave; + +- if (!spec->flags.fips && fips_mode ()) +- fips_service_indicator_mark_non_compliant (); +- + if (spec->flags.disabled) + rc = GPG_ERR_PUBKEY_ALGO; ++ else if (!spec->flags.fips && fips_mode ()) ++ { ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) ++ return GPG_ERR_PUBKEY_ALGO; ++ else ++ fips_service_indicator_mark_non_compliant (); ++ } + else if (spec->sign) + rc = spec->sign (r_sig, s_data, keyparms); + else +@@ -689,11 +703,15 @@ _gcry_pk_verify_md (gcry_sexp_t s_sig, c + if (rc) + goto leave; + +- if (!spec->flags.fips && fips_mode ()) +- fips_service_indicator_mark_non_compliant (); +- + if (spec->flags.disabled) + rc = GPG_ERR_PUBKEY_ALGO; ++ else if (!spec->flags.fips && fips_mode ()) ++ { ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) ++ return GPG_ERR_PUBKEY_ALGO; ++ else ++ fips_service_indicator_mark_non_compliant (); ++ } + else if (spec->verify) + rc = spec->verify (s_sig, s_data, keyparms); + else +Index: libgcrypt-1.11.0/src/fips.c +=================================================================== +--- libgcrypt-1.11.0.orig/src/fips.c ++++ libgcrypt-1.11.0/src/fips.c +@@ -70,15 +70,30 @@ static enum module_states current_state; + + struct gcry_thread_context { + unsigned long fips_service_indicator; ++ unsigned int flags_reject_non_fips; + }; + + #ifdef HAVE_GCC_STORAGE_CLASS__THREAD +-static __thread struct gcry_thread_context the_tc; ++static __thread struct gcry_thread_context the_tc = { ++ 0, GCRY_FIPS_FLAG_REJECT_DEFAULT ++}; + #else + #error libgcrypt requires thread-local storage to support FIPS mode + #endif + + void ++_gcry_thread_context_set_reject (unsigned int flags) ++{ ++ the_tc.flags_reject_non_fips = flags; ++} ++ ++int ++_gcry_thread_context_check_rejection (unsigned int flag) ++{ ++ return !!(the_tc.flags_reject_non_fips & flag); ++} ++ ++void + _gcry_thread_context_set_fsi (unsigned long fsi) + { + the_tc.fips_service_indicator = fsi; +Index: libgcrypt-1.11.0/src/gcrypt-int.h +=================================================================== +--- libgcrypt-1.11.0.orig/src/gcrypt-int.h ++++ libgcrypt-1.11.0/src/gcrypt-int.h +@@ -297,6 +297,12 @@ void _gcry_set_log_handler (gcry_handler + void _gcry_set_gettext_handler (const char *(*f)(const char*)); + void _gcry_set_progress_handler (gcry_handler_progress_t cb, void *cb_data); + ++void _gcry_thread_context_set_reject (unsigned int flags); ++int _gcry_thread_context_check_rejection (unsigned int flag); ++ ++#define fips_check_rejection(flag) \ ++ _gcry_thread_context_check_rejection (flag) ++ + void _gcry_thread_context_set_fsi (unsigned long fsi); + unsigned long _gcry_thread_context_get_fsi (void); + #define fips_service_indicator_init() do \ +@@ -305,7 +311,8 @@ unsigned long _gcry_thread_context_get_f + _gcry_thread_context_set_fsi (0); \ + } while (0) + /* Should be used only when fips_mode()==TRUE. */ +-#define fips_service_indicator_mark_non_compliant() _gcry_thread_context_set_fsi (1) ++#define fips_service_indicator_mark_non_compliant() \ ++ _gcry_thread_context_set_fsi (1) + + /* Return a pointer to a string containing a description of the error + code in the error value ERR. */ +Index: libgcrypt-1.11.0/src/gcrypt.h.in +=================================================================== +--- libgcrypt-1.11.0.orig/src/gcrypt.h.in ++++ libgcrypt-1.11.0/src/gcrypt.h.in +@@ -338,7 +338,8 @@ enum gcry_ctl_cmds + GCRYCTL_MD_CUSTOMIZE = 88, + GCRYCTL_FIPS_SERVICE_INDICATOR_PK = 89, + GCRYCTL_FIPS_SERVICE_INDICATOR_HASH = 90, +- GCRYCTL_FIPS_SERVICE_INDICATOR = 91 ++ GCRYCTL_FIPS_SERVICE_INDICATOR = 91, ++ GCRYCTL_FIPS_REJECT_NON_FIPS = 92 + }; + + /* Perform various operations defined by CMD. */ +@@ -1971,7 +1972,30 @@ void gcry_log_debugsxp (const char *text + char *gcry_get_config (int mode, const char *what); + + /* Convinience macro to access the FIPS service indicator. */ +-#define gcry_get_fips_service_indicator() gcry_control (GCRYCTL_FIPS_SERVICE_INDICATOR) ++#define gcry_get_fips_service_indicator() \ ++ gcry_control (GCRYCTL_FIPS_SERVICE_INDICATOR) ++ ++#define GCRY_FIPS_FLAG_REJECT_KDF (1 << 0) ++#define GCRY_FIPS_FLAG_REJECT_MD_MD5 (1 << 1) ++#define GCRY_FIPS_FLAG_REJECT_MD_OTHERS (1 << 2) ++#define GCRY_FIPS_FLAG_REJECT_MAC (1 << 3) ++#define GCRY_FIPS_FLAG_REJECT_CIPHER (1 << 4) ++#define GCRY_FIPS_FLAG_REJECT_PK (1 << 5) ++ ++#define GCRY_FIPS_FLAG_REJECT_MD \ ++ (GCRY_FIPS_FLAG_REJECT_MD_MD5 | GCRY_FIPS_FLAG_REJECT_MD_OTHERS) ++ ++/* Note: Don't reject MD5 */ ++#define GCRY_FIPS_FLAG_REJECT_COMPAT110 \ ++ (GCRY_FIPS_FLAG_REJECT_MD_OTHERS \ ++ | GCRY_FIPS_FLAG_REJECT_MAC \ ++ | GCRY_FIPS_FLAG_REJECT_CIPHER \ ++ | GCRY_FIPS_FLAG_REJECT_KDF \ ++ | GCRY_FIPS_FLAG_REJECT_PK) ++ ++#define GCRY_FIPS_FLAG_REJECT_DEFAULT \ ++ GCRY_FIPS_FLAG_REJECT_COMPAT110 ++ + + /* Log levels used by the internal logging facility. */ + enum gcry_log_levels +Index: libgcrypt-1.11.0/src/global.c +=================================================================== +--- libgcrypt-1.11.0.orig/src/global.c ++++ libgcrypt-1.11.0/src/global.c +@@ -791,6 +791,13 @@ _gcry_vcontrol (enum gcry_ctl_cmds cmd, + rc = _gcry_fips_indicator (); + break; + ++ case GCRYCTL_FIPS_REJECT_NON_FIPS: ++ { ++ unsigned int flags = va_arg (arg_ptr, unsigned int); ++ _gcry_thread_context_set_reject (flags); ++ } ++ break; ++ + case GCRYCTL_FIPS_SERVICE_INDICATOR_CIPHER: + /* Get FIPS Service Indicator for a given symmetric algorithm and + * optional mode. Returns GPG_ERR_NO_ERROR if algorithm is allowed or +Index: libgcrypt-1.11.0/tests/t-fips-service-ind.c +=================================================================== +--- libgcrypt-1.11.0.orig/tests/t-fips-service-ind.c ++++ libgcrypt-1.11.0/tests/t-fips-service-ind.c +@@ -1007,6 +1007,8 @@ main (int argc, char **argv) + if (debug) + xgcry_control ((GCRYCTL_SET_DEBUG_FLAGS, 1u , 0)); + ++ xgcry_control ((GCRYCTL_FIPS_REJECT_NON_FIPS, 0)); ++ + check_digests (); + check_kdf_derive (); + check_md_o_w_r_c (); diff --git a/libgcrypt-fips-Introduce-GCRYCTL_FIPS_SERVICE_INDICATOR-and-the-macro.patch b/libgcrypt-fips-Introduce-GCRYCTL_FIPS_SERVICE_INDICATOR-and-the-macro.patch new file mode 100644 index 0000000..9355299 --- /dev/null +++ b/libgcrypt-fips-Introduce-GCRYCTL_FIPS_SERVICE_INDICATOR-and-the-macro.patch @@ -0,0 +1,101 @@ +From f51f4e98930e6b2175e85fe8a95b8b6a15ad5efa Mon Sep 17 00:00:00 2001 +From: NIIBE Yutaka +Date: Thu, 5 Dec 2024 11:34:32 +0900 +Subject: [PATCH 2/5] fips: Introduce GCRYCTL_FIPS_SERVICE_INDICATOR and the + macro. +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* src/fips.c (_gcry_fips_indicator): New. +* src/g10lib.h (_gcry_fips_indicator): New. +* src/gcrypt.h.in (GCRYCTL_FIPS_SERVICE_INDICATOR): New. +(gcry_get_fips_service_indicator): New. +* src/global.c (_gcry_vcontrol): Handle GCRYCTL_FIPS_SERVICE_INDICATOR. + +-- + +GnuPG-bug-id: 7338 +Signed-off-by: NIIBE Yutaka +Signed-off-by: Lucas Mülling +--- + src/fips.c | 11 +++++++++++ + src/g10lib.h | 2 ++ + src/gcrypt.h.in | 6 +++++- + src/global.c | 4 ++++ + 4 files changed, 22 insertions(+), 1 deletion(-) + +Index: libgcrypt-1.11.0/src/fips.c +=================================================================== +--- libgcrypt-1.11.0.orig/src/fips.c ++++ libgcrypt-1.11.0/src/fips.c +@@ -364,6 +364,17 @@ _gcry_fips_test_operational (void) + return result; + } + ++gpg_err_code_t ++_gcry_fips_indicator (void) ++{ ++ /* If anything recorded, it means that the operation is not ++ supported under FIPS mode. */ ++ if (_gcry_thread_context_get_fsi ()) ++ return GPG_ERR_NOT_SUPPORTED; ++ ++ return 0; ++} ++ + int + _gcry_fips_indicator_cipher (va_list arg_ptr) + { +Index: libgcrypt-1.11.0/src/g10lib.h +=================================================================== +--- libgcrypt-1.11.0.orig/src/g10lib.h ++++ libgcrypt-1.11.0/src/g10lib.h +@@ -468,6 +468,8 @@ void _gcry_fips_signal_error (const char + _gcry_fips_signal_error (__FILE__, __LINE__, NULL, 1, (a)) + #endif + ++gpg_err_code_t _gcry_fips_indicator (void); ++ + int _gcry_fips_indicator_cipher (va_list arg_ptr); + int _gcry_fips_indicator_hash (va_list arg_ptr); + int _gcry_fips_indicator_mac (va_list arg_ptr); +Index: libgcrypt-1.11.0/src/gcrypt.h.in +=================================================================== +--- libgcrypt-1.11.0.orig/src/gcrypt.h.in ++++ libgcrypt-1.11.0/src/gcrypt.h.in +@@ -337,7 +337,8 @@ enum gcry_ctl_cmds + GCRYCTL_FIPS_SERVICE_INDICATOR_PK_FLAGS = 87, + GCRYCTL_MD_CUSTOMIZE = 88, + GCRYCTL_FIPS_SERVICE_INDICATOR_PK = 89, +- GCRYCTL_FIPS_SERVICE_INDICATOR_HASH = 90 ++ GCRYCTL_FIPS_SERVICE_INDICATOR_HASH = 90, ++ GCRYCTL_FIPS_SERVICE_INDICATOR = 91 + }; + + /* Perform various operations defined by CMD. */ +@@ -1966,6 +1967,9 @@ void gcry_log_debugsxp (const char *text + + char *gcry_get_config (int mode, const char *what); + ++/* Convinience macro to access the FIPS service indicator. */ ++#define gcry_get_fips_service_indicator() gcry_control (GCRYCTL_FIPS_SERVICE_INDICATOR) ++ + /* Log levels used by the internal logging facility. */ + enum gcry_log_levels + { +Index: libgcrypt-1.11.0/src/global.c +=================================================================== +--- libgcrypt-1.11.0.orig/src/global.c ++++ libgcrypt-1.11.0/src/global.c +@@ -787,6 +787,10 @@ _gcry_vcontrol (enum gcry_ctl_cmds cmd, + rc = _gcry_fips_run_selftests (1); + break; + ++ case GCRYCTL_FIPS_SERVICE_INDICATOR: ++ rc = _gcry_fips_indicator (); ++ break; ++ + case GCRYCTL_FIPS_SERVICE_INDICATOR_CIPHER: + /* Get FIPS Service Indicator for a given symmetric algorithm and + * optional mode. Returns GPG_ERR_NO_ERROR if algorithm is allowed or diff --git a/libgcrypt-fips-Introduce-an-internal-API-for-FIPS-service-indicator.patch b/libgcrypt-fips-Introduce-an-internal-API-for-FIPS-service-indicator.patch new file mode 100644 index 0000000..b452626 --- /dev/null +++ b/libgcrypt-fips-Introduce-an-internal-API-for-FIPS-service-indicator.patch @@ -0,0 +1,332 @@ +From e1cf3123282525693b646499eb7efe4f2be4010a Mon Sep 17 00:00:00 2001 +From: NIIBE Yutaka +Date: Thu, 5 Dec 2024 11:06:37 +0900 +Subject: [PATCH 1/5] fips: Introduce an internal API for FIPS service + indicator. +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* configure.ac (HAVE_GCC_STORAGE_CLASS__THREAD): New. +* src/fips.c (struct gcry_thread_context): New. +(_gcry_thread_context_set_fsi, _gcry_thread_context_get_fsi): New. +* src/gcrypt-int.h (fips_service_indicator_init): New macro. +(fips_service_indicator_mark_success): New macro. +* tests/Makefile.am (tests_bin): Add t-thread-local. +* tests/t-thread-local.c: New. + +-- + +GnuPG-bug-id: 7340 +Signed-off-by: NIIBE Yutaka +Signed-off-by: Lucas Mülling +--- + configure.ac | 14 +++ + src/fips.c | 21 ++++- + src/gcrypt-int.h | 12 +++ + tests/Makefile.am | 2 +- + tests/t-thread-local.c | 196 +++++++++++++++++++++++++++++++++++++++++ + 5 files changed, 243 insertions(+), 2 deletions(-) + create mode 100644 tests/t-thread-local.c + +diff --git a/configure.ac b/configure.ac +index a7f922b1..d708f89a 100644 +--- a/configure.ac ++++ b/configure.ac +@@ -1489,6 +1489,20 @@ if test "$gcry_cv_gcc_attribute_sysv_abi" = "yes" ; then + fi + fi + ++# ++# Check whether compiler support '__thread' storage class specifier. ++# ++AC_CACHE_CHECK([whether compiler supports '__thread' storage class specifier], ++ [gcry_cv_gcc_storage_class__thread], ++ [gcry_cv_gcc_storage_class__thread=no ++ AC_COMPILE_IFELSE([AC_LANG_PROGRAM([#include ], ++ [static __thread int bar;] ++ )], ++ [gcry_cv_gcc_storage_class__thread=yes])]) ++if test "$gcry_cv_gcc_storage_class__thread" = "yes" ; then ++ AC_DEFINE(HAVE_GCC_STORAGE_CLASS__THREAD,1, ++ [Defined if compiler supports "__thread" storage class specifier]) ++fi + + # Restore flags. + CFLAGS=$_gcc_cflags_save; +diff --git a/src/fips.c b/src/fips.c +index cf91baa8..58fb69df 100644 +--- a/src/fips.c ++++ b/src/fips.c +@@ -67,10 +67,29 @@ GPGRT_LOCK_DEFINE (fsm_lock); + used while in fips mode. Change this only while holding fsm_lock. */ + static enum module_states current_state; + ++struct gcry_thread_context { ++ unsigned long fips_service_indicator; ++}; ++ ++#ifdef HAVE_GCC_STORAGE_CLASS__THREAD ++static __thread struct gcry_thread_context the_tc; ++#else ++#error libgcrypt requires thread-local storage to support FIPS mode ++#endif ++ ++void ++_gcry_thread_context_set_fsi (unsigned long fsi) ++{ ++ the_tc.fips_service_indicator = fsi; ++} + ++unsigned long ++_gcry_thread_context_get_fsi (void) ++{ ++ return the_tc.fips_service_indicator; ++} + + +- + static void fips_new_state (enum module_states new_state); + + +diff --git a/src/gcrypt-int.h b/src/gcrypt-int.h +index 074ea071..7f894737 100644 +--- a/src/gcrypt-int.h ++++ b/src/gcrypt-int.h +@@ -298,6 +298,18 @@ void _gcry_set_log_handler (gcry_handler_log_t f, void *opaque); + void _gcry_set_gettext_handler (const char *(*f)(const char*)); + void _gcry_set_progress_handler (gcry_handler_progress_t cb, void *cb_data); + ++void _gcry_thread_context_set_fsi (unsigned long fsi); ++unsigned long _gcry_thread_context_get_fsi (void); ++#define fips_service_indicator_init() do \ ++ { \ ++ if (fips_mode ()) \ ++ _gcry_thread_context_set_fsi (1); \ ++ } while (0) ++#define fips_service_indicator_mark_success(is_compliant) do \ ++ { \ ++ if (is_compliant && fips_mode ()) \ ++ _gcry_thread_context_set_fsi (0); \ ++ } while (0) + + /* Return a pointer to a string containing a description of the error + code in the error value ERR. */ +diff --git a/tests/Makefile.am b/tests/Makefile.am +index 423bc1cd..52f7dd61 100644 +--- a/tests/Makefile.am ++++ b/tests/Makefile.am +@@ -25,7 +25,7 @@ tests_bin = \ + version t-secmem mpitests t-sexp t-convert \ + t-mpi-bit t-mpi-point t-lock \ + prime basic keygen pubkey hmac hashtest t-kdf keygrip \ +- aeswrap random t-kem t-mlkem ++ aeswrap random t-kem t-mlkem t-thread-local + + if USE_RSA + tests_bin += pkcs1v2 t-rsa-pss t-rsa-15 t-rsa-testparm +diff --git a/tests/t-thread-local.c b/tests/t-thread-local.c +new file mode 100644 +index 00000000..285f197f +--- /dev/null ++++ b/tests/t-thread-local.c +@@ -0,0 +1,196 @@ ++/* t-mlkem.c - Check the thread local storage ++ * Copyright (C) 2024 g10 Code GmbH ++ * ++ * This file is part of Libgcrypt. ++ * ++ * Libgcrypt is free software; you can redistribute it and/or modify ++ * it under the terms of the GNU Lesser General Public License as ++ * published by the Free Software Foundation; either version 2.1 of ++ * the License, or (at your option) any later version. ++ * ++ * Libgcrypt 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 Lesser General Public License for more details. ++ * ++ * You should have received a copy of the GNU Lesser General Public License ++ * along with this program; if not, see . ++ * SPDX-License-Identifier: LGPL-2.1+ ++ */ ++ ++/* For now, this program simply test __thread storage class specifier. ++ * After we implement thread local context for libgcrypt, we will ++ * modity to test the feature. */ ++ ++#ifdef HAVE_CONFIG_H ++#include ++#endif ++#include ++#include ++#include ++#include ++#include ++#include ++#if HAVE_PTHREAD ++# include ++#endif ++ ++#define PGM "t-thread-local" ++ ++#include "t-common.h" ++#include "../src/gcrypt-testapi.h" ++ ++/* Mingw requires us to include windows.h after winsock2.h which is ++ included by gcrypt.h. */ ++#ifdef _WIN32 ++# include ++#endif ++ ++#ifdef _WIN32 ++# define THREAD_RET_TYPE DWORD WINAPI ++# define THREAD_RET_VALUE 0 ++#else ++# define THREAD_RET_TYPE void * ++# define THREAD_RET_VALUE NULL ++#endif ++ ++#define N_TESTS 1 ++ ++#define N_THREADS 19 ++ ++static __thread unsigned long t; ++ ++struct thread_arg_s ++{ ++ int no; ++}; ++ ++#if defined(HAVE_PTHREAD) || defined(_WIN32) ++/* Checking the local storage thread. */ ++static THREAD_RET_TYPE ++check_ls_thread (void *argarg) ++{ ++ struct thread_arg_s *arg = argarg; ++ ++ t = arg->no; ++ info ("a thread update the local storage: %lu", t); ++ ++ gcry_free (arg); ++ return THREAD_RET_VALUE; ++} ++#endif ++ ++static void ++check_thread_local (void) ++{ ++ struct thread_arg_s *arg; ++ ++#ifdef _WIN32 ++ HANDLE threads[N_THREADS]; ++ int i; ++ int rc; ++ ++ t = N_THREADS; ++ for (i=0; i < N_THREADS; i++) ++ { ++ arg = gcry_xmalloc (sizeof *arg); ++ arg->no = i; ++ threads[i] = CreateThread (NULL, 0, check_ls_thread, arg, 0, NULL); ++ if (!threads[i]) ++ die ("error creating a thread %d: rc=%d", ++ i, (int)GetLastError ()); ++ } ++ ++ for (i=0; i < N_THREADS; i++) ++ { ++ rc = WaitForSingleObject (threads[i], INFINITE); ++ if (rc == WAIT_OBJECT_0) ++ info ("a thread %d has terminated", i); ++ else ++ fail ("waiting for a thread %d failed: %d", ++ i, (int)GetLastError ()); ++ CloseHandle (threads[i]); ++ } ++ ++#elif HAVE_PTHREAD ++ pthread_t threads[N_THREADS]; ++ int rc, i; ++ ++ t = N_THREADS; ++ for (i=0; i < N_THREADS; i++) ++ { ++ arg = gcry_xmalloc (sizeof *arg); ++ arg->no = i; ++ pthread_create (&threads[i], NULL, check_ls_thread, arg); ++ } ++ ++ for (i=0; i < N_THREADS; i++) ++ { ++ rc = pthread_join (threads[i], NULL); ++ if (rc) ++ fail ("pthread_join failed for a thread %d: %s", ++ i, strerror (errno)); ++ else ++ info ("a thread %d has terminated", i); ++ } ++#else ++ (void)arg; ++#endif /*!_WIN32*/ ++ if (t != N_THREADS) ++ fail ("failed t=%lu\n", t); ++ else ++ info ("success"); ++} ++ ++int ++main (int argc, char **argv) ++{ ++ int last_argc = -1; ++ ++ if (argc) ++ { argc--; argv++; } ++ ++ while (argc && last_argc != argc) ++ { ++ last_argc = argc; ++ if (!strcmp (*argv, "--")) ++ { ++ argc--; argv++; ++ break; ++ } ++ else if (!strcmp (*argv, "--help")) ++ { ++ fputs ("usage: " PGM " [options]\n" ++ "Options:\n" ++ " --verbose print timings etc.\n" ++ " --debug flyswatter\n", ++ stdout); ++ exit (0); ++ } ++ else if (!strcmp (*argv, "--verbose")) ++ { ++ verbose++; ++ argc--; argv++; ++ } ++ else if (!strcmp (*argv, "--debug")) ++ { ++ verbose += 2; ++ debug++; ++ argc--; argv++; ++ } ++ else if (!strncmp (*argv, "--", 2)) ++ die ("unknown option '%s'", *argv); ++ } ++ ++ xgcry_control ((GCRYCTL_DISABLE_SECMEM, 0)); ++ if (!gcry_check_version (GCRYPT_VERSION)) ++ die ("version mismatch\n"); ++ if (debug) ++ xgcry_control ((GCRYCTL_SET_DEBUG_FLAGS, 1u , 0)); ++ xgcry_control ((GCRYCTL_ENABLE_QUICK_RANDOM, 0)); ++ xgcry_control ((GCRYCTL_INITIALIZATION_FINISHED, 0)); ++ ++ check_thread_local (); ++ ++ return !!error_count; ++} +-- +2.49.0 + diff --git a/libgcrypt-fips-Rejection-by-GCRYCTL_FIPS_REJECT_NON_FIPS-not-by-open-flags.patch b/libgcrypt-fips-Rejection-by-GCRYCTL_FIPS_REJECT_NON_FIPS-not-by-open-flags.patch new file mode 100644 index 0000000..6d18f18 --- /dev/null +++ b/libgcrypt-fips-Rejection-by-GCRYCTL_FIPS_REJECT_NON_FIPS-not-by-open-flags.patch @@ -0,0 +1,498 @@ +From d060dd58b82882dec0d8bfcc593536bc0083b4b1 Mon Sep 17 00:00:00 2001 +From: NIIBE Yutaka +Date: Fri, 20 Dec 2024 09:38:13 +0900 +Subject: [PATCH 14/19] fips: Rejection by GCRYCTL_FIPS_REJECT_NON_FIPS, not by + open flags. +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* src/gcrypt.h.in (GCRY_CIPHER_FLAG_REJECT_NON_FIPS): Remove. +(GCRY_MD_FLAG_REJECT_NON_FIPS): Remove. +(GCRY_MAC_FLAG_REJECT_NON_FIPS): Remove. +* tests/t-fips-service-ind.c: Update tests with +GCRYCTL_FIPS_REJECT_NON_FIPS. +* cipher/cipher.c (_gcry_cipher_open_internal, cipher_setkey): Use +fips_check_rejection. +* cipher/mac.c (mac_open): Likewise. +* cipher/md.c (struct gcry_md_context): Remove reject_non_fips. +(md_open, md_enable): Use fips_check_rejection. +(_gcry_md_enable, md_copy): Likewise. + +-- + +GnuPG-bug-id: 7338 +Signed-off-by: NIIBE Yutaka +Signed-off-by: Lucas Mülling +--- + cipher/cipher.c | 8 ++-- + cipher/mac.c | 5 +-- + cipher/md.c | 81 ++++++++++++++++++++++++++++++-------- + src/gcrypt.h.in | 7 +--- + tests/t-fips-service-ind.c | 59 +++++++++++---------------- + 5 files changed, 94 insertions(+), 66 deletions(-) + +Index: libgcrypt-1.11.0/cipher/cipher.c +=================================================================== +--- libgcrypt-1.11.0.orig/cipher/cipher.c ++++ libgcrypt-1.11.0/cipher/cipher.c +@@ -510,7 +510,6 @@ _gcry_cipher_open_internal (gcry_cipher_ + int algo, int mode, unsigned int flags) + { + int secure = !!(flags & GCRY_CIPHER_SECURE); +- int reject_non_fips = !!(flags & GCRY_CIPHER_FLAG_REJECT_NON_FIPS); + gcry_cipher_spec_t *spec; + gcry_cipher_hd_t h = NULL; + gcry_err_code_t err; +@@ -526,7 +525,7 @@ _gcry_cipher_open_internal (gcry_cipher_ + err = GPG_ERR_CIPHER_ALGO; + else if (!spec->flags.fips && fips_mode ()) + { +- if (reject_non_fips) ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_CIPHER)) + err = GPG_ERR_CIPHER_ALGO; + else + { +@@ -544,8 +543,7 @@ _gcry_cipher_open_internal (gcry_cipher_ + | GCRY_CIPHER_ENABLE_SYNC + | GCRY_CIPHER_CBC_CTS + | GCRY_CIPHER_CBC_MAC +- | GCRY_CIPHER_EXTENDED +- | GCRY_CIPHER_FLAG_REJECT_NON_FIPS)) ++ | GCRY_CIPHER_EXTENDED)) + || ((flags & GCRY_CIPHER_CBC_CTS) && (flags & GCRY_CIPHER_CBC_MAC)))) + err = GPG_ERR_CIPHER_ALGO; + +@@ -776,7 +774,7 @@ cipher_setkey (gcry_cipher_hd_t c, byte + Key Generation Requirements" for details. */ + if (buf_eq_const (key, key + keylen, keylen)) + { +- if ((c->flags & GCRY_CIPHER_FLAG_REJECT_NON_FIPS)) ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_CIPHER)) + return GPG_ERR_WEAK_KEY; + else + fips_service_indicator_mark_non_compliant (); +Index: libgcrypt-1.11.0/cipher/mac.c +=================================================================== +--- libgcrypt-1.11.0.orig/cipher/mac.c ++++ libgcrypt-1.11.0/cipher/mac.c +@@ -519,7 +519,6 @@ mac_open (gcry_mac_hd_t * hd, int algo, + gcry_err_code_t err; + gcry_mac_hd_t h; + int secure = !!(flags & GCRY_MAC_FLAG_SECURE); +- int reject_non_fips = !!(flags & GCRY_MAC_FLAG_REJECT_NON_FIPS); + + spec = spec_from_algo (algo); + if (!spec) +@@ -528,7 +527,7 @@ mac_open (gcry_mac_hd_t * hd, int algo, + return GPG_ERR_MAC_ALGO; + else if (!spec->flags.fips && fips_mode ()) + { +- if (reject_non_fips) ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_MAC)) + return GPG_ERR_MAC_ALGO; + else + fips_service_indicator_mark_non_compliant (); +@@ -650,7 +649,7 @@ _gcry_mac_open (gcry_mac_hd_t * h, int a + gcry_err_code_t rc; + gcry_mac_hd_t hd = NULL; + +- if ((flags & ~(GCRY_MAC_FLAG_SECURE | GCRY_MAC_FLAG_REJECT_NON_FIPS))) ++ if ((flags & ~GCRY_MAC_FLAG_SECURE)) + rc = GPG_ERR_INV_ARG; + else + rc = mac_open (&hd, algo, flags, ctx); +Index: libgcrypt-1.11.0/cipher/md.c +=================================================================== +--- libgcrypt-1.11.0.orig/cipher/md.c ++++ libgcrypt-1.11.0/cipher/md.c +@@ -275,7 +275,6 @@ struct gcry_md_context + unsigned int finalized:1; + unsigned int bugemu1:1; + unsigned int hmac:1; +- unsigned int reject_non_fips:1; + } flags; + size_t actual_handle_size; /* Allocated size of this handle. */ + FILE *debug; +@@ -509,7 +508,6 @@ md_open (gcry_md_hd_t *h, int algo, unsi + ctx->flags.secure = secure; + ctx->flags.hmac = hmac; + ctx->flags.bugemu1 = !!(flags & GCRY_MD_FLAG_BUGEMU1); +- ctx->flags.reject_non_fips = !!(flags & GCRY_MD_FLAG_REJECT_NON_FIPS); + } + + if (! err) +@@ -544,14 +542,11 @@ _gcry_md_open (gcry_md_hd_t *h, int algo + + if ((flags & ~(GCRY_MD_FLAG_SECURE + | GCRY_MD_FLAG_HMAC +- | GCRY_MD_FLAG_REJECT_NON_FIPS + | GCRY_MD_FLAG_BUGEMU1))) + rc = GPG_ERR_INV_ARG; + else + rc = md_open (&hd, algo, flags); + +- *h = rc? NULL : hd; +- + if (!rc && fips_mode ()) + { + GcryDigestEntry *entry = hd->ctx->list; +@@ -566,9 +561,26 @@ _gcry_md_open (gcry_md_hd_t *h, int algo + } + + if (!is_compliant_algo) +- fips_service_indicator_mark_non_compliant (); ++ { ++ int reject = 0; ++ ++ if (algo == GCRY_MD_MD5) ++ reject = fips_check_rejection (GCRY_FIPS_FLAG_REJECT_MD_MD5); ++ else ++ reject = fips_check_rejection (GCRY_FIPS_FLAG_REJECT_MD_OTHERS); ++ ++ if (reject) ++ { ++ md_close (hd); ++ hd = NULL; ++ rc = GPG_ERR_DIGEST_ALGO; ++ } ++ else ++ fips_service_indicator_mark_non_compliant (); ++ } + } + ++ *h = rc? NULL : hd; + return rc; + } + +@@ -581,12 +593,17 @@ md_enable (gcry_md_hd_t hd, int algorith + const gcry_md_spec_t *spec; + GcryDigestEntry *entry; + gcry_err_code_t err = 0; +- int reject_non_fips = h->flags.reject_non_fips; ++ int reject; + + for (entry = h->list; entry; entry = entry->next) + if (entry->spec->algo == algorithm) + return 0; /* Already enabled */ + ++ if (algorithm == GCRY_MD_MD5) ++ reject = fips_check_rejection (GCRY_FIPS_FLAG_REJECT_MD_MD5); ++ else ++ reject = fips_check_rejection (GCRY_FIPS_FLAG_REJECT_MD_OTHERS); ++ + spec = spec_from_algo (algorithm); + if (!spec) + { +@@ -598,7 +615,7 @@ md_enable (gcry_md_hd_t hd, int algorith + err = GPG_ERR_DIGEST_ALGO; + + /* Any non-FIPS algorithm should go this way */ +- if (!err && reject_non_fips && !spec->flags.fips && fips_mode ()) ++ if (!err && reject && !spec->flags.fips && fips_mode ()) + err = GPG_ERR_DIGEST_ALGO; + + if (!err && h->flags.hmac && spec->read == NULL) +@@ -657,7 +674,19 @@ _gcry_md_enable (gcry_md_hd_t hd, int al + } + + if (!is_compliant_algo) +- fips_service_indicator_mark_non_compliant (); ++ { ++ int reject = 0; ++ ++ if (algorithm == GCRY_MD_MD5) ++ reject = fips_check_rejection (GCRY_FIPS_FLAG_REJECT_MD_MD5); ++ else ++ reject = fips_check_rejection (GCRY_FIPS_FLAG_REJECT_MD_OTHERS); ++ ++ if (reject) ++ rc = GPG_ERR_DIGEST_ALGO; ++ else ++ fips_service_indicator_mark_non_compliant (); ++ } + } + + return rc; +@@ -667,13 +696,14 @@ _gcry_md_enable (gcry_md_hd_t hd, int al + static gcry_err_code_t + md_copy (gcry_md_hd_t ahd, gcry_md_hd_t *b_hd) + { +- gcry_err_code_t err = 0; ++ gcry_err_code_t rc = 0; + struct gcry_md_context *a = ahd->ctx; + struct gcry_md_context *b; + GcryDigestEntry *ar, *br; + gcry_md_hd_t bhd; + size_t n; + int is_compliant_algo = 1; ++ int reject = 0; + + if (ahd->bufpos) + md_write (ahd, NULL, 0); +@@ -686,7 +716,7 @@ md_copy (gcry_md_hd_t ahd, gcry_md_hd_t + + if (!bhd) + { +- err = gpg_err_code_from_syserror (); ++ rc = gpg_err_code_from_syserror (); + goto leave; + } + +@@ -715,12 +745,20 @@ md_copy (gcry_md_hd_t ahd, gcry_md_hd_t + br = xtrymalloc (ar->actual_struct_size); + if (!br) + { +- err = gpg_err_code_from_syserror (); ++ rc = gpg_err_code_from_syserror (); + md_close (bhd); + goto leave; + } + +- is_compliant_algo &= spec->flags.fips; ++ if (!spec->flags.fips) ++ { ++ is_compliant_algo = 0; ++ ++ if (spec->algo == GCRY_MD_MD5) ++ reject |= fips_check_rejection (GCRY_FIPS_FLAG_REJECT_MD_MD5); ++ else ++ reject |= fips_check_rejection (GCRY_FIPS_FLAG_REJECT_MD_OTHERS); ++ } + + memcpy (br, ar, ar->actual_struct_size); + br->next = b->list; +@@ -730,13 +768,22 @@ md_copy (gcry_md_hd_t ahd, gcry_md_hd_t + if (a->debug) + md_start_debug (bhd, "unknown"); + +- *b_hd = bhd; ++ if (!is_compliant_algo && fips_mode ()) ++ { ++ if (reject) ++ { ++ rc = GPG_ERR_DIGEST_ALGO; ++ md_close (bhd); ++ } ++ else ++ fips_service_indicator_mark_non_compliant (); ++ } + +- if (!is_compliant_algo) +- fips_service_indicator_mark_non_compliant (); ++ if (!rc) ++ *b_hd = bhd; + + leave: +- return err; ++ return rc; + } + + +Index: libgcrypt-1.11.0/src/gcrypt.h.in +=================================================================== +--- libgcrypt-1.11.0.orig/src/gcrypt.h.in ++++ libgcrypt-1.11.0/src/gcrypt.h.in +@@ -995,8 +995,7 @@ enum gcry_cipher_flags + GCRY_CIPHER_ENABLE_SYNC = 2, /* Enable CFB sync mode. */ + GCRY_CIPHER_CBC_CTS = 4, /* Enable CBC cipher text stealing (CTS). */ + GCRY_CIPHER_CBC_MAC = 8, /* Enable CBC message auth. code (MAC). */ +- GCRY_CIPHER_EXTENDED = 16, /* Enable extended AES-WRAP. */ +- GCRY_CIPHER_FLAG_REJECT_NON_FIPS = 32 /* Reject non-FIPS-compliant algo. */ ++ GCRY_CIPHER_EXTENDED = 16 /* Enable extended AES-WRAP. */ + }; + + /* Methods used for AEAD IV generation. */ +@@ -1322,7 +1321,6 @@ enum gcry_md_flags + { + GCRY_MD_FLAG_SECURE = 1, /* Allocate all buffers in "secure" memory. */ + GCRY_MD_FLAG_HMAC = 2, /* Make an HMAC out of this algorithm. */ +- GCRY_MD_FLAG_REJECT_NON_FIPS = 4, /* Reject non-FIPS-compliant algo. */ + GCRY_MD_FLAG_BUGEMU1 = 0x0100 + }; + +@@ -1564,8 +1562,7 @@ enum gcry_mac_algos + /* Flags used with the open function. */ + enum gcry_mac_flags + { +- GCRY_MAC_FLAG_SECURE = 1, /* Allocate all buffers in "secure" memory. */ +- GCRY_MAC_FLAG_REJECT_NON_FIPS = 2 /* Reject non-FIPS-compliant algo. */ ++ GCRY_MAC_FLAG_SECURE = 1 /* Allocate all buffers in "secure" memory. */ + }; + + /* Create a MAC handle for algorithm ALGO. FLAGS may be given as an bitwise OR +Index: libgcrypt-1.11.0/tests/t-fips-service-ind.c +=================================================================== +--- libgcrypt-1.11.0.orig/tests/t-fips-service-ind.c ++++ libgcrypt-1.11.0/tests/t-fips-service-ind.c +@@ -250,7 +250,7 @@ check_pk_hash_sign_verify (void) + /* Check gcry_cipher_open, gcry_cipher_setkey, gcry_cipher_encrypt, + gcry_cipher_decrypt, gcry_cipher_close API. */ + static void +-check_cipher_o_s_e_d_c (void) ++check_cipher_o_s_e_d_c (int reject) + { + static struct { + int algo; +@@ -258,18 +258,12 @@ check_cipher_o_s_e_d_c (void) + int keylen; + const char *expect; + int expect_failure; +- unsigned int flags; + } tv[] = { + #if USE_DES + { GCRY_CIPHER_3DES, + "\xe3\x34\x7a\x6b\x0b\xc1\x15\x2c\x64\x2a\x25\xcb\xd3\xbc\x31\xab" + "\xfb\xa1\x62\xa8\x1f\x19\x7c\x15", 24, + "\x3f\x1a\xb8\x83\x18\x8b\xb5\x97", 1 }, +- { GCRY_CIPHER_3DES, +- "\xe3\x34\x7a\x6b\x0b\xc1\x15\x2c\x64\x2a\x25\xcb\xd3\xbc\x31\xab" +- "\xfb\xa1\x62\xa8\x1f\x19\x7c\x15", 24, +- "\x3f\x1a\xb8\x83\x18\x8b\xb5\x97", +- 1, GCRY_CIPHER_FLAG_REJECT_NON_FIPS }, + #endif + { GCRY_CIPHER_AES, + "\x2b\x7e\x15\x16\x28\xae\xd2\xa6\xab\xf7\x15\x88\x09\xcf\x4f\x3c", 16, +@@ -297,12 +291,10 @@ check_cipher_o_s_e_d_c (void) + assert (blklen != 0); + assert (blklen <= ptlen); + assert (blklen <= DIM (out)); +- err = gcry_cipher_open (&h, tv[tvidx].algo, GCRY_CIPHER_MODE_ECB, +- tv[tvidx].flags); ++ err = gcry_cipher_open (&h, tv[tvidx].algo, GCRY_CIPHER_MODE_ECB, 0); + if (err) + { +- if (in_fips_mode && (tv[tvidx].flags & GCRY_CIPHER_FLAG_REJECT_NON_FIPS) +- && tv[tvidx].expect_failure) ++ if (in_fips_mode && reject && tv[tvidx].expect_failure) + /* Here, an error is expected */ + ; + else +@@ -312,8 +304,7 @@ check_cipher_o_s_e_d_c (void) + } + else + { +- if (in_fips_mode && (tv[tvidx].flags & GCRY_CIPHER_FLAG_REJECT_NON_FIPS) +- && tv[tvidx].expect_failure) ++ if (in_fips_mode && reject && tv[tvidx].expect_failure) + /* This case, an error is expected, but we observed success */ + fail ("gcry_cipher_open test %d unexpectedly succeeded\n", tvidx); + } +@@ -398,7 +389,7 @@ check_cipher_o_s_e_d_c (void) + /* Check gcry_mac_open, gcry_mac_write, gcry_mac_write, gcry_mac_read, + gcry_mac_close API. */ + static void +-check_mac_o_w_r_c (void) ++check_mac_o_w_r_c (int reject) + { + static struct { + int algo; +@@ -408,14 +399,10 @@ check_mac_o_w_r_c (void) + int keylen; + const char *expect; + int expect_failure; +- unsigned int flags; + } tv[] = { + #if USE_MD5 + { GCRY_MAC_HMAC_MD5, "hmac input abc", 14, "hmac key input", 14, + "\x0d\x72\xd0\x60\xaf\x34\xf2\xca\x33\x58\xa9\xcc\xd3\x5a\xac\xb5", 1 }, +- { GCRY_MAC_HMAC_MD5, "hmac input abc", 14, "hmac key input", 14, +- "\x0d\x72\xd0\x60\xaf\x34\xf2\xca\x33\x58\xa9\xcc\xd3\x5a\xac\xb5", 1, +- GCRY_MAC_FLAG_REJECT_NON_FIPS }, + #endif + #if USE_SHA1 + { GCRY_MAC_HMAC_SHA1, "hmac input abc", 14, "hmac key input", 14, +@@ -471,11 +458,10 @@ check_mac_o_w_r_c (void) + expectlen = gcry_mac_get_algo_maclen (tv[tvidx].algo); + assert (expectlen != 0); + assert (expectlen <= DIM (mac)); +- err = gcry_mac_open (&h, tv[tvidx].algo, tv[tvidx].flags, NULL); ++ err = gcry_mac_open (&h, tv[tvidx].algo, 0, NULL); + if (err) + { +- if (in_fips_mode && (tv[tvidx].flags & GCRY_MAC_FLAG_REJECT_NON_FIPS) +- && tv[tvidx].expect_failure) ++ if (in_fips_mode && reject && tv[tvidx].expect_failure) + /* Here, an error is expected */ + ; + else +@@ -485,8 +471,7 @@ check_mac_o_w_r_c (void) + } + else + { +- if (in_fips_mode && (tv[tvidx].flags & GCRY_MAC_FLAG_REJECT_NON_FIPS) +- && tv[tvidx].expect_failure) ++ if (in_fips_mode && reject && tv[tvidx].expect_failure) + /* This case, an error is expected, but we observed success */ + fail ("gcry_mac_open test %d unexpectedly succeeded\n", tvidx); + } +@@ -563,7 +548,7 @@ check_mac_o_w_r_c (void) + /* Check gcry_md_open, gcry_md_write, gcry_md_write, gcry_md_read, + gcry_md_close API. */ + static void +-check_md_o_w_r_c (void) ++check_md_o_w_r_c (int reject) + { + static struct { + int algo; +@@ -571,14 +556,10 @@ check_md_o_w_r_c (void) + int datalen; + const char *expect; + int expect_failure; +- unsigned int flags; + } tv[] = { + #if USE_MD5 + { GCRY_MD_MD5, "abc", 3, + "\x90\x01\x50\x98\x3C\xD2\x4F\xB0\xD6\x96\x3F\x7D\x28\xE1\x7F\x72", 1 }, +- { GCRY_MD_MD5, "abc", 3, +- "\x90\x01\x50\x98\x3C\xD2\x4F\xB0\xD6\x96\x3F\x7D\x28\xE1\x7F\x72", 1, +- GCRY_MD_FLAG_REJECT_NON_FIPS }, + #endif + #if USE_SHA1 + { GCRY_MD_SHA1, "abc", 3, +@@ -632,11 +613,10 @@ check_md_o_w_r_c (void) + + expectlen = gcry_md_get_algo_dlen (tv[tvidx].algo); + assert (expectlen != 0); +- err = gcry_md_open (&h, tv[tvidx].algo, tv[tvidx].flags); ++ err = gcry_md_open (&h, tv[tvidx].algo, 0); + if (err) + { +- if (in_fips_mode && (tv[tvidx].flags & GCRY_MD_FLAG_REJECT_NON_FIPS) +- && tv[tvidx].expect_failure) ++ if (in_fips_mode && reject && tv[tvidx].expect_failure) + /* Here, an error is expected */ + ; + else +@@ -646,8 +626,7 @@ check_md_o_w_r_c (void) + } + else + { +- if (in_fips_mode && (tv[tvidx].flags & GCRY_MD_FLAG_REJECT_NON_FIPS) +- && tv[tvidx].expect_failure) ++ if (in_fips_mode && reject && tv[tvidx].expect_failure) + /* This case, an error is expected, but we observed success */ + fail ("gcry_md_open test %d unexpectedly succeeded\n", tvidx); + } +@@ -1011,10 +990,18 @@ main (int argc, char **argv) + + check_digests (); + check_kdf_derive (); +- check_md_o_w_r_c (); +- check_mac_o_w_r_c (); +- check_cipher_o_s_e_d_c (); ++ check_md_o_w_r_c (0); ++ check_mac_o_w_r_c (0); ++ check_cipher_o_s_e_d_c (0); + check_pk_hash_sign_verify (); + ++ xgcry_control ((GCRYCTL_FIPS_REJECT_NON_FIPS, ++ (GCRY_FIPS_FLAG_REJECT_MD_MD5 ++ | GCRY_FIPS_FLAG_REJECT_COMPAT110))); ++ ++ check_md_o_w_r_c (1); ++ check_mac_o_w_r_c (1); ++ check_cipher_o_s_e_d_c (1); ++ + return !!error_count; + } diff --git a/libgcrypt-fips-cipher-Add-GCRY_FIPS_FLAG_REJECT_PK_FLAGS.patch b/libgcrypt-fips-cipher-Add-GCRY_FIPS_FLAG_REJECT_PK_FLAGS.patch new file mode 100644 index 0000000..310e5e5 --- /dev/null +++ b/libgcrypt-fips-cipher-Add-GCRY_FIPS_FLAG_REJECT_PK_FLAGS.patch @@ -0,0 +1,80 @@ +From 0414e126b939f0b11ecf441908d923e87c1caf02 Mon Sep 17 00:00:00 2001 +From: NIIBE Yutaka +Date: Thu, 6 Mar 2025 08:57:51 +0900 +Subject: [PATCH 06/14] fips,cipher: Add GCRY_FIPS_FLAG_REJECT_PK_FLAGS. +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* src/gcrypt.h.in (GCRY_FIPS_FLAG_REJECT_PK_FLAGS): New. +* cipher/pubkey-util.c (_gcry_pk_util_parse_flaglist): Keep the +behavior of 1.10. +* cipher/rsa.c (rsa_decrypt, rsa_sign): Likewise. + +-- + +GnuPG-bug-id: 7338 +Signed-off-by: NIIBE Yutaka +Signed-off-by: Lucas Mülling +--- + cipher/pubkey-util.c | 2 +- + cipher/rsa.c | 4 ++-- + src/gcrypt.h.in | 3 ++- + 3 files changed, 5 insertions(+), 4 deletions(-) + +diff --git a/cipher/pubkey-util.c b/cipher/pubkey-util.c +index 9c927638..e7355569 100644 +--- a/cipher/pubkey-util.c ++++ b/cipher/pubkey-util.c +@@ -202,7 +202,7 @@ _gcry_pk_util_parse_flaglist (gcry_sexp_t list, + + if (fips_mode () && igninvflag) + { +- if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK_FLAGS)) + rc = GPG_ERR_INV_FLAG; + else + fips_service_indicator_mark_non_compliant (); +diff --git a/cipher/rsa.c b/cipher/rsa.c +index dce76414..7e086df4 100644 +--- a/cipher/rsa.c ++++ b/cipher/rsa.c +@@ -1504,7 +1504,7 @@ rsa_decrypt (gcry_sexp_t *r_plain, gcry_sexp_t s_data, gcry_sexp_t keyparms) + { + if (fips_mode ()) + { +- if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK_FLAGS)) + { + rc = GPG_ERR_INV_FLAG; + goto leave; +@@ -1649,7 +1649,7 @@ rsa_sign (gcry_sexp_t *r_sig, gcry_sexp_t s_data, gcry_sexp_t keyparms) + { + if (fips_mode ()) + { +- if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK_FLAGS)) + { + rc = GPG_ERR_INV_FLAG; + goto leave; +diff --git a/src/gcrypt.h.in b/src/gcrypt.h.in +index fe3db16a..a282268d 100644 +--- a/src/gcrypt.h.in ++++ b/src/gcrypt.h.in +@@ -1991,11 +1991,12 @@ char *gcry_get_config (int mode, const char *what); + #define GCRY_FIPS_FLAG_REJECT_CIPHER_MODE (1 << 8) + /**/ + #define GCRY_FIPS_FLAG_REJECT_PK_ECC_K (1 << 10) ++#define GCRY_FIPS_FLAG_REJECT_PK_FLAGS (1 << 11) + + #define GCRY_FIPS_FLAG_REJECT_MD \ + (GCRY_FIPS_FLAG_REJECT_MD_MD5 | GCRY_FIPS_FLAG_REJECT_MD_OTHERS) + +-/* Note: Don't reject MD5, PK MD, PK GOST and PK SM2 */ ++/* Note: Don't reject MD5, PK MD, PK GOST, PK SM2, PK ECC K, and PK FLAGS */ + #define GCRY_FIPS_FLAG_REJECT_COMPAT110 \ + (GCRY_FIPS_FLAG_REJECT_MD_OTHERS \ + | GCRY_FIPS_FLAG_REJECT_MAC \ +-- +2.49.0 + diff --git a/libgcrypt-fips-cipher-Add-behavior-not-to-reject-but-mark-non-compliant.patch b/libgcrypt-fips-cipher-Add-behavior-not-to-reject-but-mark-non-compliant.patch new file mode 100644 index 0000000..9fc7734 --- /dev/null +++ b/libgcrypt-fips-cipher-Add-behavior-not-to-reject-but-mark-non-compliant.patch @@ -0,0 +1,300 @@ +From a776b692669af7a6c089779989b626c4795e30b0 Mon Sep 17 00:00:00 2001 +From: NIIBE Yutaka +Date: Fri, 20 Dec 2024 13:36:12 +0900 +Subject: [PATCH 15/19] fips,cipher: Add behavior not to reject but mark + non-compliant. +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* cipher/dsa.c (dsa_check_keysize): Check reject flag for rejection, +or mark non-comliant in FIPS mode. +* cipher/ecc-ecdsa.c (_gcry_ecc_ecdsa_sign): Likewise. +* cipher/ecc.c (ecc_sign, ecc_verify): Likewise. +* cipher/pubkey.c (_gcry_pk_encrypt, _gcry_pk_sign): Likewise. +(_gcry_pk_verify, _gcry_pk_testkey, _gcry_pk_genkey): Likewise. +(_gcry_pk_get_nbits, _gcry_pk_get_curve): Likewise. +* src/visibility.c (gcry_pk_encrypt): Initialize the indicator. +(gcry_pk_decrypt, gcry_pk_sign, gcry_pk_verify): Likewise. +(gcry_pk_testkey, gcry_pk_genkey), gcry_pk_get_nbits) +(gcry_pk_get_curve): Likewise. +-- + +GnuPG-bug-id: 7338 +Signed-off-by: NIIBE Yutaka +Signed-off-by: Lucas Mülling +--- + cipher/dsa.c | 7 ++++- + cipher/ecc-ecdsa.c | 5 +++- + cipher/ecc.c | 10 +++++-- + cipher/pubkey.c | 74 ++++++++++++++++++++++++++++++++++++++-------- + src/visibility.c | 9 +++++- + 5 files changed, 87 insertions(+), 18 deletions(-) + +diff --git a/cipher/dsa.c b/cipher/dsa.c +index e559f9f5..564edf8d 100644 +--- a/cipher/dsa.c ++++ b/cipher/dsa.c +@@ -150,7 +150,12 @@ static gpg_err_code_t + dsa_check_keysize (unsigned int nbits) + { + if (fips_mode () && nbits < 2048) +- return GPG_ERR_INV_VALUE; ++ { ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) ++ return GPG_ERR_INV_VALUE; ++ else ++ fips_service_indicator_mark_non_compliant (); ++ } + + return 0; + } +diff --git a/cipher/ecc-ecdsa.c b/cipher/ecc-ecdsa.c +index 871b0371..cb9a001c 100644 +--- a/cipher/ecc-ecdsa.c ++++ b/cipher/ecc-ecdsa.c +@@ -110,7 +110,10 @@ _gcry_ecc_ecdsa_sign (gcry_mpi_t input, gcry_mpi_t k_supplied, mpi_ec_t ec, + (hashalgo == GCRY_MD_SHAKE128 + || hashalgo == GCRY_MD_SHAKE256)) + { +- rc = GPG_ERR_DIGEST_ALGO; ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) ++ rc = GPG_ERR_DIGEST_ALGO; ++ else ++ fips_service_indicator_mark_non_compliant (); + goto leave; + } + +diff --git a/cipher/ecc.c b/cipher/ecc.c +index 65525207..8896afd0 100644 +--- a/cipher/ecc.c ++++ b/cipher/ecc.c +@@ -952,7 +952,10 @@ ecc_sign (gcry_sexp_t *r_sig, gcry_sexp_t s_data, gcry_sexp_t keyparms) + || (ec->dialect == ECC_DIALECT_SAFECURVE + && ctx.hash_algo != GCRY_MD_SHAKE256))) + { +- rc = GPG_ERR_DIGEST_ALGO; ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) ++ rc = GPG_ERR_DIGEST_ALGO; ++ else ++ fips_service_indicator_mark_non_compliant (); + goto leave; + } + } +@@ -1074,7 +1077,10 @@ ecc_verify (gcry_sexp_t s_sig, gcry_sexp_t s_data, gcry_sexp_t s_keyparms) + || (ec->dialect == ECC_DIALECT_SAFECURVE + && ctx.hash_algo != GCRY_MD_SHAKE256))) + { +- rc = GPG_ERR_DIGEST_ALGO; ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) ++ rc = GPG_ERR_DIGEST_ALGO; ++ else ++ fips_service_indicator_mark_non_compliant (); + goto leave; + } + } +diff --git a/cipher/pubkey.c b/cipher/pubkey.c +index 4d7743cc..aacf9f5a 100644 +--- a/cipher/pubkey.c ++++ b/cipher/pubkey.c +@@ -328,7 +328,12 @@ _gcry_pk_encrypt (gcry_sexp_t *r_ciph, gcry_sexp_t s_data, gcry_sexp_t s_pkey) + if (spec->flags.disabled) + rc = GPG_ERR_PUBKEY_ALGO; + else if (!spec->flags.fips && fips_mode ()) +- rc = GPG_ERR_PUBKEY_ALGO; ++ { ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) ++ rc = GPG_ERR_PUBKEY_ALGO; ++ else ++ fips_service_indicator_mark_non_compliant (); ++ } + else if (spec->encrypt) + rc = spec->encrypt (r_ciph, s_data, keyparms); + else +@@ -441,7 +446,12 @@ _gcry_pk_sign (gcry_sexp_t *r_sig, gcry_sexp_t s_hash, gcry_sexp_t s_skey) + if (spec->flags.disabled) + rc = GPG_ERR_PUBKEY_ALGO; + else if (!spec->flags.fips && fips_mode ()) +- rc = GPG_ERR_PUBKEY_ALGO; ++ { ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) ++ rc = GPG_ERR_PUBKEY_ALGO; ++ else ++ fips_service_indicator_mark_non_compliant (); ++ } + else if (spec->sign) + rc = spec->sign (r_sig, s_hash, keyparms); + else +@@ -663,7 +673,12 @@ _gcry_pk_verify (gcry_sexp_t s_sig, gcry_sexp_t s_hash, gcry_sexp_t s_pkey) + if (spec->flags.disabled) + rc = GPG_ERR_PUBKEY_ALGO; + else if (!spec->flags.fips && fips_mode ()) +- rc = GPG_ERR_PUBKEY_ALGO; ++ { ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) ++ rc = GPG_ERR_PUBKEY_ALGO; ++ else ++ fips_service_indicator_mark_non_compliant (); ++ } + else if (spec->verify) + rc = spec->verify (s_sig, s_hash, keyparms); + else +@@ -747,7 +762,12 @@ _gcry_pk_testkey (gcry_sexp_t s_key) + if (spec->flags.disabled) + rc = GPG_ERR_PUBKEY_ALGO; + else if (!spec->flags.fips && fips_mode ()) +- rc = GPG_ERR_PUBKEY_ALGO; ++ { ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) ++ rc = GPG_ERR_PUBKEY_ALGO; ++ else ++ fips_service_indicator_mark_non_compliant (); ++ } + else if (spec->check_secret_key) + rc = spec->check_secret_key (keyparms); + else +@@ -826,11 +846,21 @@ _gcry_pk_genkey (gcry_sexp_t *r_key, gcry_sexp_t s_parms) + spec = spec_from_name (name); + xfree (name); + name = NULL; +- if (!spec || spec->flags.disabled || (!spec->flags.fips && fips_mode ())) ++ if (!spec || spec->flags.disabled) + { + rc = GPG_ERR_PUBKEY_ALGO; /* Unknown algorithm. */ + goto leave; + } ++ else if (!spec->flags.fips && fips_mode ()) ++ { ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) ++ { ++ rc = GPG_ERR_PUBKEY_ALGO; ++ goto leave; ++ } ++ else ++ fips_service_indicator_mark_non_compliant (); ++ } + + if (spec->generate) + rc = spec->generate (list, r_key); +@@ -866,12 +896,22 @@ _gcry_pk_get_nbits (gcry_sexp_t key) + + if (spec_from_sexp (key, 0, &spec, &parms)) + return 0; /* Error - 0 is a suitable indication for that. */ ++ + if (spec->flags.disabled) +- return 0; +- if (!spec->flags.fips && fips_mode ()) +- return 0; ++ nbits = 0; /* Error */ ++ else if (!spec->flags.fips && fips_mode ()) ++ { ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) ++ nbits = 0; /* Error */ ++ else ++ { ++ fips_service_indicator_mark_non_compliant (); ++ nbits = spec->get_nbits (parms); ++ } ++ } ++ else ++ nbits = spec->get_nbits (parms); + +- nbits = spec->get_nbits (parms); + sexp_release (parms); + return nbits; + } +@@ -1004,10 +1044,18 @@ _gcry_pk_get_curve (gcry_sexp_t key, int iterator, unsigned int *r_nbits) + } + + if (spec->flags.disabled) +- return NULL; +- if (!spec->flags.fips && fips_mode ()) +- return NULL; +- if (spec->get_curve) ++ result = NULL; ++ else if (!spec->flags.fips && fips_mode ()) ++ { ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) ++ result = NULL; ++ else ++ { ++ fips_service_indicator_mark_non_compliant (); ++ result = spec->get_curve (keyparms, iterator, r_nbits); ++ } ++ } ++ else if (spec->get_curve) + result = spec->get_curve (keyparms, iterator, r_nbits); + + sexp_release (keyparms); +diff --git a/src/visibility.c b/src/visibility.c +index d22c8b59..e02d6cfe 100644 +--- a/src/visibility.c ++++ b/src/visibility.c +@@ -1022,6 +1022,7 @@ gcry_pk_encrypt (gcry_sexp_t *result, gcry_sexp_t data, gcry_sexp_t pkey) + *result = NULL; + return gpg_error (fips_not_operational ()); + } ++ fips_service_indicator_init (); + return gpg_error (_gcry_pk_encrypt (result, data, pkey)); + } + +@@ -1033,6 +1034,7 @@ gcry_pk_decrypt (gcry_sexp_t *result, gcry_sexp_t data, gcry_sexp_t skey) + *result = NULL; + return gpg_error (fips_not_operational ()); + } ++ fips_service_indicator_init (); + return gpg_error (_gcry_pk_decrypt (result, data, skey)); + } + +@@ -1044,6 +1046,7 @@ gcry_pk_sign (gcry_sexp_t *result, gcry_sexp_t data, gcry_sexp_t skey) + *result = NULL; + return gpg_error (fips_not_operational ()); + } ++ fips_service_indicator_init (); + return gpg_error (_gcry_pk_sign (result, data, skey)); + } + +@@ -1065,6 +1068,7 @@ gcry_pk_verify (gcry_sexp_t sigval, gcry_sexp_t data, gcry_sexp_t pkey) + { + if (!fips_is_operational ()) + return gpg_error (fips_not_operational ()); ++ fips_service_indicator_init (); + return gpg_error (_gcry_pk_verify (sigval, data, pkey)); + } + +@@ -1089,6 +1093,7 @@ gcry_pk_testkey (gcry_sexp_t key) + { + if (!fips_is_operational ()) + return gpg_error (fips_not_operational ()); ++ fips_service_indicator_init (); + return gpg_error (_gcry_pk_testkey (key)); + } + +@@ -1100,6 +1105,7 @@ gcry_pk_genkey (gcry_sexp_t *r_key, gcry_sexp_t s_parms) + *r_key = NULL; + return gpg_error (fips_not_operational ()); + } ++ fips_service_indicator_init (); + return gpg_error (_gcry_pk_genkey (r_key, s_parms)); + } + +@@ -1138,7 +1144,7 @@ gcry_pk_get_nbits (gcry_sexp_t key) + (void)fips_not_operational (); + return 0; + } +- ++ fips_service_indicator_init (); + return _gcry_pk_get_nbits (key); + } + +@@ -1161,6 +1167,7 @@ gcry_pk_get_curve (gcry_sexp_t key, int iterator, unsigned int *r_nbits) + (void)fips_not_operational (); + return NULL; + } ++ fips_service_indicator_init (); + return _gcry_pk_get_curve (key, iterator, r_nbits); + } + +-- +2.49.0 + diff --git a/libgcrypt-fips-cipher-Do-the-computation-when-marking-non-compliant.patch b/libgcrypt-fips-cipher-Do-the-computation-when-marking-non-compliant.patch new file mode 100644 index 0000000..8f71866 --- /dev/null +++ b/libgcrypt-fips-cipher-Do-the-computation-when-marking-non-compliant.patch @@ -0,0 +1,160 @@ +From 54a6617b3679cfeb6d986ddf3c9c73641929f02c Mon Sep 17 00:00:00 2001 +From: NIIBE Yutaka +Date: Tue, 4 Mar 2025 10:32:49 +0900 +Subject: [PATCH 4/4] fips,cipher: Do the computation when marking + non-compliant. +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* cipher/ecc-ecdsa.c (_gcry_ecc_ecdsa_sign): Continue the computation +when marking non-compliant. +* cipher/pubkey.c (_gcry_pk_encrypt, _gcry_pk_sign): Likewise. +(_gcry_pk_sign_md, _gcry_pk_verify, _gcry_pk_verify_md): Likewise. +(_gcry_pk_testkey): Likewise. + +-- + +Fixes-commit: a776b692669af7a6c089779989b626c4795e30b0 +GnuPG-bug-id: 7338 +Signed-off-by: NIIBE Yutaka +Signed-off-by: Lucas Mülling +--- + cipher/ecc-ecdsa.c | 6 ++++-- + cipher/pubkey.c | 48 ++++++++++++++++++++++++++++++++++------------ + 2 files changed, 40 insertions(+), 14 deletions(-) + +diff --git a/cipher/ecc-ecdsa.c b/cipher/ecc-ecdsa.c +index cb9a001c..9da8e6dc 100644 +--- a/cipher/ecc-ecdsa.c ++++ b/cipher/ecc-ecdsa.c +@@ -111,10 +111,12 @@ _gcry_ecc_ecdsa_sign (gcry_mpi_t input, gcry_mpi_t k_supplied, mpi_ec_t ec, + || hashalgo == GCRY_MD_SHAKE256)) + { + if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) +- rc = GPG_ERR_DIGEST_ALGO; ++ { ++ rc = GPG_ERR_DIGEST_ALGO; ++ goto leave; ++ } + else + fips_service_indicator_mark_non_compliant (); +- goto leave; + } + + /* Use Pornin's method for deterministic DSA. If this +diff --git a/cipher/pubkey.c b/cipher/pubkey.c +index c28ec124..3778f482 100644 +--- a/cipher/pubkey.c ++++ b/cipher/pubkey.c +@@ -330,11 +330,15 @@ _gcry_pk_encrypt (gcry_sexp_t *r_ciph, gcry_sexp_t s_data, gcry_sexp_t s_pkey) + else if (!spec->flags.fips && fips_mode ()) + { + if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) +- rc = GPG_ERR_PUBKEY_ALGO; ++ { ++ rc = GPG_ERR_PUBKEY_ALGO; ++ goto leave; ++ } + else + fips_service_indicator_mark_non_compliant (); + } +- else if (spec->encrypt) ++ ++ if (spec->encrypt) + rc = spec->encrypt (r_ciph, s_data, keyparms); + else + rc = GPG_ERR_NOT_IMPLEMENTED; +@@ -448,11 +452,15 @@ _gcry_pk_sign (gcry_sexp_t *r_sig, gcry_sexp_t s_hash, gcry_sexp_t s_skey) + else if (!spec->flags.fips && fips_mode ()) + { + if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) +- rc = GPG_ERR_PUBKEY_ALGO; ++ { ++ rc = GPG_ERR_PUBKEY_ALGO; ++ goto leave; ++ } + else + fips_service_indicator_mark_non_compliant (); + } +- else if (spec->sign) ++ ++ if (spec->sign) + rc = spec->sign (r_sig, s_hash, keyparms); + else + rc = GPG_ERR_NOT_IMPLEMENTED; +@@ -649,11 +657,15 @@ _gcry_pk_sign_md (gcry_sexp_t *r_sig, const char *tmpl, gcry_md_hd_t hd_orig, + else if (!spec->flags.fips && fips_mode ()) + { + if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) +- rc = GPG_ERR_PUBKEY_ALGO; ++ { ++ rc = GPG_ERR_PUBKEY_ALGO; ++ goto leave; ++ } + else + fips_service_indicator_mark_non_compliant (); + } +- else if (spec->sign) ++ ++ if (spec->sign) + rc = spec->sign (r_sig, s_data, keyparms); + else + rc = GPG_ERR_NOT_IMPLEMENTED; +@@ -688,11 +700,15 @@ _gcry_pk_verify (gcry_sexp_t s_sig, gcry_sexp_t s_hash, gcry_sexp_t s_pkey) + else if (!spec->flags.fips && fips_mode ()) + { + if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) +- rc = GPG_ERR_PUBKEY_ALGO; ++ { ++ rc = GPG_ERR_PUBKEY_ALGO; ++ goto leave; ++ } + else + fips_service_indicator_mark_non_compliant (); + } +- else if (spec->verify) ++ ++ if (spec->verify) + rc = spec->verify (s_sig, s_hash, keyparms); + else + rc = GPG_ERR_NOT_IMPLEMENTED; +@@ -736,11 +752,15 @@ _gcry_pk_verify_md (gcry_sexp_t s_sig, const char *tmpl, gcry_md_hd_t hd_orig, + else if (!spec->flags.fips && fips_mode ()) + { + if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) +- rc = GPG_ERR_PUBKEY_ALGO; ++ { ++ rc = GPG_ERR_PUBKEY_ALGO; ++ goto leave; ++ } + else + fips_service_indicator_mark_non_compliant (); + } +- else if (spec->verify) ++ ++ if (spec->verify) + rc = spec->verify (s_sig, s_data, keyparms); + else + rc = GPG_ERR_NOT_IMPLEMENTED; +@@ -777,11 +797,15 @@ _gcry_pk_testkey (gcry_sexp_t s_key) + else if (!spec->flags.fips && fips_mode ()) + { + if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) +- rc = GPG_ERR_PUBKEY_ALGO; ++ { ++ rc = GPG_ERR_PUBKEY_ALGO; ++ goto leave; ++ } + else + fips_service_indicator_mark_non_compliant (); + } +- else if (spec->check_secret_key) ++ ++ if (spec->check_secret_key) + rc = spec->check_secret_key (keyparms); + else + rc = GPG_ERR_NOT_IMPLEMENTED; +-- +2.49.0 + diff --git a/libgcrypt-fips-cipher-Fix-memory-leak-for-gcry_pk_hash_sign.patch b/libgcrypt-fips-cipher-Fix-memory-leak-for-gcry_pk_hash_sign.patch new file mode 100644 index 0000000..445136e --- /dev/null +++ b/libgcrypt-fips-cipher-Fix-memory-leak-for-gcry_pk_hash_sign.patch @@ -0,0 +1,76 @@ +From 5e925e6c348450bf80b4560abac9a035903bff59 Mon Sep 17 00:00:00 2001 +From: NIIBE Yutaka +Date: Mon, 6 Jan 2025 12:01:56 +0900 +Subject: [PATCH 19/19] fips,cipher: Fix memory leak for gcry_pk_hash_sign. +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* cipher/pubkey.c (prepare_datasexp_to_be_signed): Release +copied HD when error. + +-- + +GnuPG-bug-id: 7338 +Signed-off-by: NIIBE Yutaka +Signed-off-by: Lucas Mülling +--- + cipher/pubkey.c | 21 +++++++++++++++++---- + 1 file changed, 17 insertions(+), 4 deletions(-) + +diff --git a/cipher/pubkey.c b/cipher/pubkey.c +index aacf9f5a..c28ec124 100644 +--- a/cipher/pubkey.c ++++ b/cipher/pubkey.c +@@ -512,7 +512,10 @@ prepare_datasexp_to_be_signed (const char *tmpl, gcry_md_hd_t hd, + /* Check if it has fixed hash name or %s */ + s = strstr (tmpl, "(hash "); + if (s == NULL) +- return GPG_ERR_DIGEST_ALGO; ++ { ++ _gcry_md_close (hd); ++ return GPG_ERR_DIGEST_ALGO; ++ } + + s += 6; + if (!strncmp (s, "%s", 2)) +@@ -522,7 +525,10 @@ prepare_datasexp_to_be_signed (const char *tmpl, gcry_md_hd_t hd, + if (fips_mode () && algo == GCRY_MD_SHA1) + { + if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) +- return GPG_ERR_DIGEST_ALGO; ++ { ++ _gcry_md_close (hd); ++ return GPG_ERR_DIGEST_ALGO; ++ } + else + fips_service_indicator_mark_non_compliant (); + } +@@ -541,7 +547,11 @@ prepare_datasexp_to_be_signed (const char *tmpl, gcry_md_hd_t hd, + + digest_name_supplied = xtrymalloc (p - s + 1); + if (!digest_name_supplied) +- return gpg_error_from_syserror (); ++ { ++ rc = gpg_err_code_from_syserror (); ++ _gcry_md_close (hd); ++ return rc; ++ } + memcpy (digest_name_supplied, s, p - s); + digest_name_supplied[p - s] = 0; + +@@ -555,7 +565,10 @@ prepare_datasexp_to_be_signed (const char *tmpl, gcry_md_hd_t hd, + else if (fips_mode () && algo == GCRY_MD_SHA1) + { + if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) +- return GPG_ERR_DIGEST_ALGO; ++ { ++ _gcry_md_close (hd); ++ return GPG_ERR_DIGEST_ALGO; ++ } + else + fips_service_indicator_mark_non_compliant (); + } +-- +2.49.0 + diff --git a/libgcrypt-fips-cipher-Implement-FIPS-service-indicator-for-gcry_pk_hash_-API.patch b/libgcrypt-fips-cipher-Implement-FIPS-service-indicator-for-gcry_pk_hash_-API.patch new file mode 100644 index 0000000..0490e38 --- /dev/null +++ b/libgcrypt-fips-cipher-Implement-FIPS-service-indicator-for-gcry_pk_hash_-API.patch @@ -0,0 +1,360 @@ +From edb43bc290046bd22548bf69ae2fbeb453112e44 Mon Sep 17 00:00:00 2001 +From: NIIBE Yutaka +Date: Wed, 18 Dec 2024 14:18:26 +0900 +Subject: [PATCH 11/19] fips,cipher: Implement FIPS service indicator for + gcry_pk_hash_ API. +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* src/visibility.c (gcry_pk_hash_sign): Initialize the indicator. +(gcry_pk_hash_verify): Likewise. +* tests/t-fips-service-ind.c (check_pk_hash_sign_verify): New. +(main): Call check_pk_hash_sign_verify. +* cipher/ecc-curves.c (_gcry_ecc_fill_in_curve): Don't reject, but +mark non-compliance. +* cipher/pubkey.c (prepare_datasexp_to_be_signed): Likewise. +(_gcry_pk_sign_md, _gcry_pk_verify_md): Likewise. + +-- + +GnuPG-bug-id: 7338 +Signed-off-by: NIIBE Yutaka +Signed-off-by: Lucas Mülling +--- + cipher/ecc-curves.c | 2 +- + cipher/pubkey.c | 20 ++-- + src/visibility.c | 2 + + tests/t-fips-service-ind.c | 209 +++++++++++++++++++++++++++++++++++++ + 4 files changed, 222 insertions(+), 11 deletions(-) + +diff --git a/cipher/ecc-curves.c b/cipher/ecc-curves.c +index 17fa5505..ddf9cbe1 100644 +--- a/cipher/ecc-curves.c ++++ b/cipher/ecc-curves.c +@@ -645,7 +645,7 @@ _gcry_ecc_fill_in_curve (unsigned int nbits, const char *name, + possible to bypass this check by specifying the curve parameters + directly. */ + if (fips_mode () && !domain_parms[idx].fips ) +- return GPG_ERR_NOT_SUPPORTED; ++ fips_service_indicator_mark_non_compliant (); + + switch (domain_parms[idx].model) + { +diff --git a/cipher/pubkey.c b/cipher/pubkey.c +index 214bd611..e2e54199 100644 +--- a/cipher/pubkey.c ++++ b/cipher/pubkey.c +@@ -510,10 +510,7 @@ prepare_datasexp_to_be_signed (const char *tmpl, gcry_md_hd_t hd, + algo = _gcry_md_get_algo (hd); + + if (fips_mode () && algo == GCRY_MD_SHA1) +- { +- _gcry_md_close (hd); +- return GPG_ERR_DIGEST_ALGO; +- } ++ fips_service_indicator_mark_non_compliant (); + + digest_name = _gcry_md_algo_name (algo); + digest_size = (int)_gcry_md_get_algo_dlen (algo); +@@ -535,12 +532,13 @@ prepare_datasexp_to_be_signed (const char *tmpl, gcry_md_hd_t hd, + + algo = _gcry_md_map_name (digest_name_supplied); + xfree (digest_name_supplied); +- if (algo == 0 +- || (fips_mode () && algo == GCRY_MD_SHA1)) ++ if (algo == 0) + { + _gcry_md_close (hd); + return GPG_ERR_DIGEST_ALGO; + } ++ else if (fips_mode () && algo == GCRY_MD_SHA1) ++ fips_service_indicator_mark_non_compliant (); + + digest_size = (int)_gcry_md_get_algo_dlen (algo); + digest = _gcry_md_read (hd, algo); +@@ -613,10 +611,11 @@ _gcry_pk_sign_md (gcry_sexp_t *r_sig, const char *tmpl, gcry_md_hd_t hd_orig, + if (rc) + goto leave; + ++ if (!spec->flags.fips && fips_mode ()) ++ fips_service_indicator_mark_non_compliant (); ++ + if (spec->flags.disabled) + rc = GPG_ERR_PUBKEY_ALGO; +- else if (!spec->flags.fips && fips_mode ()) +- rc = GPG_ERR_PUBKEY_ALGO; + else if (spec->sign) + rc = spec->sign (r_sig, s_data, keyparms); + else +@@ -690,10 +689,11 @@ _gcry_pk_verify_md (gcry_sexp_t s_sig, const char *tmpl, gcry_md_hd_t hd_orig, + if (rc) + goto leave; + ++ if (!spec->flags.fips && fips_mode ()) ++ fips_service_indicator_mark_non_compliant (); ++ + if (spec->flags.disabled) + rc = GPG_ERR_PUBKEY_ALGO; +- else if (!spec->flags.fips && fips_mode ()) +- rc = GPG_ERR_PUBKEY_ALGO; + else if (spec->verify) + rc = spec->verify (s_sig, s_data, keyparms); + else +diff --git a/src/visibility.c b/src/visibility.c +index c9d07f0b..d22c8b59 100644 +--- a/src/visibility.c ++++ b/src/visibility.c +@@ -1056,6 +1056,7 @@ gcry_pk_hash_sign (gcry_sexp_t *result, const char *data_tmpl, gcry_sexp_t skey, + *result = NULL; + return gpg_error (fips_not_operational ()); + } ++ fips_service_indicator_init (); + return gpg_error (_gcry_pk_sign_md (result, data_tmpl, hd, skey, ctx)); + } + +@@ -1073,6 +1074,7 @@ gcry_pk_hash_verify (gcry_sexp_t sigval, const char *data_tmpl, gcry_sexp_t pkey + { + if (!fips_is_operational ()) + return gpg_error (fips_not_operational ()); ++ fips_service_indicator_init (); + return gpg_error (_gcry_pk_verify_md (sigval, data_tmpl, hd, pkey, ctx)); + } + +diff --git a/tests/t-fips-service-ind.c b/tests/t-fips-service-ind.c +index 4b13436f..9a22d696 100644 +--- a/tests/t-fips-service-ind.c ++++ b/tests/t-fips-service-ind.c +@@ -29,6 +29,7 @@ + + #define PGM "t-fips-service-ind" + ++#define NEED_HEX2BUFFER + #include "t-common.h" + static int in_fips_mode; + #define MAX_DATA_LEN 1040 +@@ -39,6 +40,213 @@ static int in_fips_mode; + # include + #endif + ++/* Check gcry_pk_hash_sign, gcry_pk_hash_verify API. */ ++static void ++check_pk_hash_sign_verify (void) ++{ ++ static struct { ++ int md_algo; ++ const char *prvkey; ++ const char *pubkey; ++ const char *data_tmpl; ++ const char *k; ++ int expect_failure; ++ int expect_failure_hash; ++ } tv[] = { ++ { /* non-compliant hash */ ++ GCRY_MD_BLAKE2B_512, ++ "(private-key (ecc (curve nistp256)" ++ " (d #519b423d715f8b581f4fa8ee59f4771a5b44c8130b4e3eacca54a56dda72b464#)))", ++ "(public-key (ecc (curve nistp256)" ++ " (q #041ccbe91c075fc7f4f033bfa248db8fccd3565de94bbfb12f3c59ff46c271bf83" ++ "ce4014c68811f9a21a1fdb2c0e6113e06db7ca93b7404e78dc7ccd5ca89a4ca9#)))", ++ "(data(flags raw)(hash %s %b)(label %b))", ++ "94a1bbb14b906a61a280f245f9e93c7f3b4a6247824f5d33b9670787642a68de", ++ 1, 1 ++ }, ++ { /* non-compliant curve */ ++ GCRY_MD_SHA256, ++ "(private-key (ecc (curve secp256k1)" ++ " (d #c2cdf0a8b0a83b35ace53f097b5e6e6a0a1f2d40535eff1cf434f52a43d59d8f#)))", ++ ++ "(public-key (ecc (curve secp256k1)" ++ " (q #046fcc37ea5e9e09fec6c83e5fbd7a745e3eee81d16ebd861c9e66f55518c19798" ++ "4e9f113c07f875691df8afc1029496fc4cb9509b39dcd38f251a83359cc8b4f7#)))", ++ "(data(flags raw)(hash %s %b)(label %b))", ++ "94a1bbb14b906a61a280f245f9e93c7f3b4a6247824f5d33b9670787642a68de", ++ 1, 0 ++ }, ++ { ++ GCRY_MD_SHA256, ++ "(private-key (ecc (curve nistp256)" ++ " (d #519b423d715f8b581f4fa8ee59f4771a5b44c8130b4e3eacca54a56dda72b464#)))", ++ "(public-key (ecc (curve nistp256)" ++ " (q #041ccbe91c075fc7f4f033bfa248db8fccd3565de94bbfb12f3c59ff46c271bf83" ++ "ce4014c68811f9a21a1fdb2c0e6113e06db7ca93b7404e78dc7ccd5ca89a4ca9#)))", ++ "(data(flags raw)(hash %s %b)(label %b))", ++ "94a1bbb14b906a61a280f245f9e93c7f3b4a6247824f5d33b9670787642a68de", ++ 0, 0 ++ } ++ }; ++ int tvidx; ++ gpg_error_t err; ++ gpg_err_code_t ec; ++ const char *msg = "Takerufuji Mikiya, who won the championship in March 2024"; ++ int msglen; ++ ++ msglen = strlen (msg); ++ for (tvidx=0; tvidx < DIM(tv); tvidx++) ++ { ++ gcry_md_hd_t hd = NULL; ++ gcry_sexp_t s_sk = NULL; ++ gcry_sexp_t s_pk = NULL; ++ void *buffer = NULL; ++ size_t buflen; ++ gcry_ctx_t ctx = NULL; ++ gcry_sexp_t s_sig= NULL; ++ ++ if (verbose) ++ info ("checking gcry_pk_hash_ test %d\n", tvidx); ++ ++ err = gcry_md_open (&hd, tv[tvidx].md_algo, 0); ++ if (err) ++ { ++ fail ("algo %d, gcry_md_open failed: %s\n", tv[tvidx].md_algo, ++ gpg_strerror (err)); ++ goto next; ++ } ++ ++ ec = gcry_get_fips_service_indicator (); ++ if (ec == GPG_ERR_INV_OP) ++ { ++ /* libgcrypt is old, no support of the FIPS service indicator. */ ++ fail ("gcry_pk_hash test %d unexpectedly failed to check the FIPS service indicator.\n", ++ tvidx); ++ goto next; ++ } ++ ++ if (in_fips_mode && !tv[tvidx].expect_failure_hash && ec) ++ { ++ /* Success with the FIPS service indicator == 0 expected, but != 0. */ ++ fail ("gcry_pk_hash test %d unexpectedly set the indicator in FIPS mode.\n", ++ tvidx); ++ goto next; ++ } ++ else if (in_fips_mode && tv[tvidx].expect_failure_hash && !ec) ++ { ++ /* Success with the FIPS service indicator != 0 expected, but == 0. */ ++ fail ("gcry_pk_hash test %d unexpectedly cleared the indicator in FIPS mode.\n", ++ tvidx); ++ goto next; ++ } ++ ++ err = gcry_sexp_build (&s_sk, NULL, tv[tvidx].prvkey); ++ if (err) ++ { ++ fail ("error building SEXP for test, %s: %s", ++ "sk", gpg_strerror (err)); ++ goto next; ++ } ++ ++ err = gcry_sexp_build (&s_pk, NULL, tv[tvidx].pubkey); ++ if (err) ++ { ++ fail ("error building SEXP for test, %s: %s", ++ "pk", gpg_strerror (err)); ++ goto next; ++ } ++ ++ if (!(buffer = hex2buffer (tv[tvidx].k, &buflen))) ++ { ++ fail ("error parsing for test, %s: %s", ++ "msg", "invalid hex string"); ++ goto next; ++ } ++ ++ err = gcry_pk_random_override_new (&ctx, buffer, buflen); ++ if (err) ++ { ++ fail ("error setting 'k' for test: %s", ++ gpg_strerror (err)); ++ goto next; ++ } ++ ++ gcry_md_write (hd, msg, msglen); ++ ++ err = gcry_pk_hash_sign (&s_sig, tv[tvidx].data_tmpl, s_sk, hd, ctx); ++ if (err) ++ { ++ fail ("gcry_pk_hash_sign failed: %s", gpg_strerror (err)); ++ goto next; ++ } ++ ++ ec = gcry_get_fips_service_indicator (); ++ if (ec == GPG_ERR_INV_OP) ++ { ++ /* libgcrypt is old, no support of the FIPS service indicator. */ ++ fail ("gcry_pk_hash test %d unexpectedly failed to check the FIPS service indicator.\n", ++ tvidx); ++ goto next; ++ } ++ ++ if (in_fips_mode && !tv[tvidx].expect_failure && ec) ++ { ++ /* Success with the FIPS service indicator == 0 expected, but != 0. */ ++ fail ("gcry_pk_hash test %d unexpectedly set the indicator in FIPS mode.\n", ++ tvidx); ++ goto next; ++ } ++ else if (in_fips_mode && tv[tvidx].expect_failure && !ec) ++ { ++ /* Success with the FIPS service indicator != 0 expected, but == 0. */ ++ fail ("gcry_pk_hash_sign test %d unexpectedly cleared the indicator in FIPS mode.\n", ++ tvidx); ++ goto next; ++ } ++ ++ err = gcry_pk_hash_verify (s_sig, tv[tvidx].data_tmpl, s_pk, hd, ctx); ++ if (err) ++ { ++ fail ("gcry_pk_hash_verify failed for test: %s", ++ gpg_strerror (err)); ++ goto next; ++ } ++ ++ ec = gcry_get_fips_service_indicator (); ++ if (ec == GPG_ERR_INV_OP) ++ { ++ /* libgcrypt is old, no support of the FIPS service indicator. */ ++ fail ("gcry_pk_hash test %d unexpectedly failed to check the FIPS service indicator.\n", ++ tvidx); ++ goto next; ++ } ++ ++ if (in_fips_mode && !tv[tvidx].expect_failure && ec) ++ { ++ /* Success with the FIPS service indicator == 0 expected, but != 0. */ ++ fail ("gcry_pk_hash test %d unexpectedly set the indicator in FIPS mode.\n", ++ tvidx); ++ goto next; ++ } ++ else if (in_fips_mode && tv[tvidx].expect_failure && !ec) ++ { ++ /* Success with the FIPS service indicator != 0 expected, but == 0. */ ++ fail ("gcry_pk_hash_verify test %d unexpectedly cleared the indicator in FIPS mode.\n", ++ tvidx); ++ goto next; ++ } ++ ++ next: ++ gcry_sexp_release (s_sig); ++ xfree (buffer); ++ gcry_ctx_release (ctx); ++ gcry_sexp_release (s_pk); ++ gcry_sexp_release (s_sk); ++ if (hd) ++ gcry_md_close (hd); ++ } ++} ++ + /* Check gcry_cipher_open, gcry_cipher_setkey, gcry_cipher_encrypt, + gcry_cipher_decrypt, gcry_cipher_close API. */ + static void +@@ -936,6 +1144,7 @@ main (int argc, char **argv) + check_md_o_w_r_c (); + check_mac_o_w_r_c (); + check_cipher_o_s_e_d_c (); ++ check_pk_hash_sign_verify (); + + return !!error_count; + } +-- +2.49.0 + diff --git a/libgcrypt-fips-cipher-Implement-new-FIPS-service-indicator-for-cipher_open.patch b/libgcrypt-fips-cipher-Implement-new-FIPS-service-indicator-for-cipher_open.patch new file mode 100644 index 0000000..2124c48 --- /dev/null +++ b/libgcrypt-fips-cipher-Implement-new-FIPS-service-indicator-for-cipher_open.patch @@ -0,0 +1,122 @@ +From 69a5d0ed18a3ddc6f297de783c7cef5ad2257df0 Mon Sep 17 00:00:00 2001 +From: NIIBE Yutaka +Date: Fri, 13 Dec 2024 14:40:53 +0900 +Subject: [PATCH 05/19] fips,cipher: Implement new FIPS service indicator for + cipher_open. +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* src/gcrypt.h.in (GCRY_CIPHER_FLAG_REJECT_NON_FIPS): New. +* cipher/cipher.c (_gcry_cipher_open_internal): Don't reject +but mark the service indicator in FIPS mode. +(cipher_setkey): Likewise. +* src/visibility.c (gcry_cipher_open): Initialize the service +indicator. +(gcry_cipher_setkey): Likewise. + +-- + +GnuPG-bug-id: 7338 +Signed-off-by: NIIBE Yutaka +Signed-off-by: Lucas Mülling +--- + cipher/cipher.c | 23 +++++++++++++++++++---- + src/gcrypt.h.in | 3 ++- + src/visibility.c | 4 ++-- + 3 files changed, 23 insertions(+), 7 deletions(-) + +diff --git a/cipher/cipher.c b/cipher/cipher.c +index 898bb58f..7ffacf05 100644 +--- a/cipher/cipher.c ++++ b/cipher/cipher.c +@@ -509,7 +509,8 @@ gcry_err_code_t + _gcry_cipher_open_internal (gcry_cipher_hd_t *handle, + int algo, int mode, unsigned int flags) + { +- int secure = (flags & GCRY_CIPHER_SECURE); ++ int secure = !!(flags & GCRY_CIPHER_SECURE); ++ int reject_non_fips = !!(flags & GCRY_CIPHER_FLAG_REJECT_NON_FIPS); + gcry_cipher_spec_t *spec; + gcry_cipher_hd_t h = NULL; + gcry_err_code_t err; +@@ -524,7 +525,15 @@ _gcry_cipher_open_internal (gcry_cipher_hd_t *handle, + else if (spec->flags.disabled) + err = GPG_ERR_CIPHER_ALGO; + else if (!spec->flags.fips && fips_mode ()) +- err = GPG_ERR_CIPHER_ALGO; ++ { ++ if (reject_non_fips) ++ err = GPG_ERR_CIPHER_ALGO; ++ else ++ { ++ fips_service_indicator_mark_non_compliant (); ++ err = 0; ++ } ++ } + else + err = 0; + +@@ -535,7 +544,8 @@ _gcry_cipher_open_internal (gcry_cipher_hd_t *handle, + | GCRY_CIPHER_ENABLE_SYNC + | GCRY_CIPHER_CBC_CTS + | GCRY_CIPHER_CBC_MAC +- | GCRY_CIPHER_EXTENDED)) ++ | GCRY_CIPHER_EXTENDED ++ | GCRY_CIPHER_FLAG_REJECT_NON_FIPS)) + || ((flags & GCRY_CIPHER_CBC_CTS) && (flags & GCRY_CIPHER_CBC_MAC)))) + err = GPG_ERR_CIPHER_ALGO; + +@@ -765,7 +775,12 @@ cipher_setkey (gcry_cipher_hd_t c, byte *key, size_t keylen) + See "Implementation Guidance for FIPS 140-2, A.9 XTS-AES + Key Generation Requirements" for details. */ + if (buf_eq_const (key, key + keylen, keylen)) +- return GPG_ERR_WEAK_KEY; ++ { ++ if ((c->flags & GCRY_CIPHER_FLAG_REJECT_NON_FIPS)) ++ return GPG_ERR_WEAK_KEY; ++ else ++ fips_service_indicator_mark_non_compliant (); ++ } + } + } + else if (c->mode == GCRY_CIPHER_MODE_SIV) +diff --git a/src/gcrypt.h.in b/src/gcrypt.h.in +index 2a378639..2ed9914b 100644 +--- a/src/gcrypt.h.in ++++ b/src/gcrypt.h.in +@@ -992,7 +992,8 @@ enum gcry_cipher_flags + GCRY_CIPHER_ENABLE_SYNC = 2, /* Enable CFB sync mode. */ + GCRY_CIPHER_CBC_CTS = 4, /* Enable CBC cipher text stealing (CTS). */ + GCRY_CIPHER_CBC_MAC = 8, /* Enable CBC message auth. code (MAC). */ +- GCRY_CIPHER_EXTENDED = 16 /* Enable extended AES-WRAP. */ ++ GCRY_CIPHER_EXTENDED = 16, /* Enable extended AES-WRAP. */ ++ GCRY_CIPHER_FLAG_REJECT_NON_FIPS = 32 /* Reject non-FIPS-compliant algo. */ + }; + + /* Methods used for AEAD IV generation. */ +diff --git a/src/visibility.c b/src/visibility.c +index 7699f14f..d219f1a6 100644 +--- a/src/visibility.c ++++ b/src/visibility.c +@@ -736,7 +736,7 @@ gcry_cipher_open (gcry_cipher_hd_t *handle, + *handle = NULL; + return gpg_error (fips_not_operational ()); + } +- ++ fips_service_indicator_init (); + return gpg_error (_gcry_cipher_open (handle, algo, mode, flags)); + } + +@@ -751,7 +751,7 @@ gcry_cipher_setkey (gcry_cipher_hd_t hd, const void *key, size_t keylen) + { + if (!fips_is_operational ()) + return gpg_error (fips_not_operational ()); +- ++ fips_service_indicator_init (); + return gcry_error (_gcry_cipher_setkey (hd, key, keylen)); + } + +-- +2.49.0 + diff --git a/libgcrypt-fips-ecc-Add-rejecting-or-marking-for-gcry_pk_get_curve.patch b/libgcrypt-fips-ecc-Add-rejecting-or-marking-for-gcry_pk_get_curve.patch new file mode 100644 index 0000000..27fd75b --- /dev/null +++ b/libgcrypt-fips-ecc-Add-rejecting-or-marking-for-gcry_pk_get_curve.patch @@ -0,0 +1,43 @@ +From c6a092abbe7bea315394b15f28fd231dae0e4d7c Mon Sep 17 00:00:00 2001 +From: NIIBE Yutaka +Date: Tue, 24 Dec 2024 17:01:45 +0900 +Subject: [PATCH 16/19] fips,ecc: Add rejecting or marking for + gcry_pk_get_curve. +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* cipher/ecc-curves.c (_gcry_ecc_get_curve): Check under FIPS mode. + +-- + +GnuPG-bug-id: 7338 +Signed-off-by: NIIBE Yutaka +Signed-off-by: Lucas Mülling +--- + cipher/ecc-curves.c | 9 +++++++++ + 1 file changed, 9 insertions(+) + +diff --git a/cipher/ecc-curves.c b/cipher/ecc-curves.c +index fe0a1eb2..975f6a07 100644 +--- a/cipher/ecc-curves.c ++++ b/cipher/ecc-curves.c +@@ -844,6 +844,15 @@ _gcry_ecc_get_curve (gcry_sexp_t keyparms, int iterator, unsigned int *r_nbits) + if (r_nbits) + *r_nbits = domain_parms[idx].nbits; + } ++ ++ if (fips_mode () && !domain_parms[idx].fips) ++ { ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) ++ return NULL; ++ else ++ fips_service_indicator_mark_non_compliant (); ++ } ++ + return result; + } + +-- +2.49.0 + diff --git a/libgcrypt-fips-ecc-Check-DATA-in-gcry_pk_sign-verify-in-FIPS-mode.patch b/libgcrypt-fips-ecc-Check-DATA-in-gcry_pk_sign-verify-in-FIPS-mode.patch new file mode 100644 index 0000000..310c5c9 --- /dev/null +++ b/libgcrypt-fips-ecc-Check-DATA-in-gcry_pk_sign-verify-in-FIPS-mode.patch @@ -0,0 +1,282 @@ +From 53c97483b17fee280e24f595bc0d82d9b362ffde Mon Sep 17 00:00:00 2001 +From: NIIBE Yutaka +Date: Thu, 26 Dec 2024 11:12:48 +0900 +Subject: [PATCH 18/19] fips,ecc: Check DATA in gcry_pk_sign/verify in FIPS + mode. +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* src/gcrypt.h.in (GCRY_FIPS_FLAG_REJECT_PK_MD): New. +(GCRY_FIPS_FLAG_REJECT_PK_GOST_SM2): New. + +* cipher/ecc.c (ecc_sign): Check if GOST or SM2. Check if hash is +compliant. +(ecc_verify): Likewise. +* tests/t-fips-service-ind.c (check_pk_s_v): Modify tests including +hash compliance. + +-- + +GnuPG-bug-id: 7338 +Signed-off-by: NIIBE Yutaka +Signed-off-by: Lucas Mülling +--- + cipher/ecc.c | 70 +++++++++++++++++++++++++++++++++++--- + src/gcrypt.h.in | 4 ++- + tests/t-fips-service-ind.c | 52 ++++++++++++++++++++-------- + 3 files changed, 107 insertions(+), 19 deletions(-) + +diff --git a/cipher/ecc.c b/cipher/ecc.c +index 8896afd0..525523ed 100644 +--- a/cipher/ecc.c ++++ b/cipher/ecc.c +@@ -941,6 +941,18 @@ ecc_sign (gcry_sexp_t *r_sig, gcry_sexp_t s_data, gcry_sexp_t keyparms) + if (rc) + goto leave; + ++ if (fips_mode () ++ && ((ctx.flags & PUBKEY_FLAG_GOST) || (ctx.flags & PUBKEY_FLAG_SM2))) ++ { ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK_GOST_SM2)) ++ { ++ rc = GPG_ERR_INV_DATA; ++ goto leave; ++ } ++ else ++ fips_service_indicator_mark_non_compliant (); ++ } ++ + /* Hash algo is determined by curve in EdDSA. */ + if ((ctx.flags & PUBKEY_FLAG_EDDSA)) + { +@@ -953,10 +965,12 @@ ecc_sign (gcry_sexp_t *r_sig, gcry_sexp_t s_data, gcry_sexp_t keyparms) + && ctx.hash_algo != GCRY_MD_SHAKE256))) + { + if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) +- rc = GPG_ERR_DIGEST_ALGO; ++ { ++ rc = GPG_ERR_DIGEST_ALGO; ++ goto leave; ++ } + else + fips_service_indicator_mark_non_compliant (); +- goto leave; + } + } + else +@@ -967,6 +981,23 @@ ecc_sign (gcry_sexp_t *r_sig, gcry_sexp_t s_data, gcry_sexp_t keyparms) + ctx.hash_algo = GCRY_MD_SHAKE256; + } + } ++ else ++ { ++ if (fips_mode ()) ++ { ++ if (_gcry_md_algo_info (ctx.hash_algo, GCRYCTL_TEST_ALGO, NULL, NULL) ++ || ctx.hash_algo == GCRY_MD_SHA1) ++ { ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK_MD)) ++ { ++ rc = GPG_ERR_DIGEST_ALGO; ++ goto leave; ++ } ++ else ++ fips_service_indicator_mark_non_compliant (); ++ } ++ } ++ } + + sig_r = mpi_new (0); + sig_s = mpi_new (0); +@@ -1066,6 +1097,18 @@ ecc_verify (gcry_sexp_t s_sig, gcry_sexp_t s_data, gcry_sexp_t s_keyparms) + if (DBG_CIPHER) + log_mpidump ("ecc_verify data", data); + ++ if (fips_mode () ++ && ((ctx.flags & PUBKEY_FLAG_GOST) || (ctx.flags & PUBKEY_FLAG_SM2))) ++ { ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK_GOST_SM2)) ++ { ++ rc = GPG_ERR_INV_DATA; ++ goto leave; ++ } ++ else ++ fips_service_indicator_mark_non_compliant (); ++ } ++ + /* Hash algo is determined by curve in EdDSA. */ + if ((ctx.flags & PUBKEY_FLAG_EDDSA)) + { +@@ -1078,10 +1121,12 @@ ecc_verify (gcry_sexp_t s_sig, gcry_sexp_t s_data, gcry_sexp_t s_keyparms) + && ctx.hash_algo != GCRY_MD_SHAKE256))) + { + if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK)) +- rc = GPG_ERR_DIGEST_ALGO; ++ { ++ rc = GPG_ERR_DIGEST_ALGO; ++ goto leave; ++ } + else + fips_service_indicator_mark_non_compliant (); +- goto leave; + } + } + else +@@ -1092,6 +1137,23 @@ ecc_verify (gcry_sexp_t s_sig, gcry_sexp_t s_data, gcry_sexp_t s_keyparms) + ctx.hash_algo = GCRY_MD_SHAKE256; + } + } ++ else ++ { ++ if (fips_mode ()) ++ { ++ if (_gcry_md_algo_info (ctx.hash_algo, GCRYCTL_TEST_ALGO, NULL, NULL) ++ || ctx.hash_algo == GCRY_MD_SHA1) ++ { ++ if (fips_check_rejection (GCRY_FIPS_FLAG_REJECT_PK_MD)) ++ { ++ rc = GPG_ERR_DIGEST_ALGO; ++ goto leave; ++ } ++ else ++ fips_service_indicator_mark_non_compliant (); ++ } ++ } ++ } + + /* + * Extract the signature value. +diff --git a/src/gcrypt.h.in b/src/gcrypt.h.in +index 7bee45e9..fcb6a327 100644 +--- a/src/gcrypt.h.in ++++ b/src/gcrypt.h.in +@@ -1986,11 +1986,13 @@ char *gcry_get_config (int mode, const char *what); + #define GCRY_FIPS_FLAG_REJECT_MAC (1 << 3) + #define GCRY_FIPS_FLAG_REJECT_CIPHER (1 << 4) + #define GCRY_FIPS_FLAG_REJECT_PK (1 << 5) ++#define GCRY_FIPS_FLAG_REJECT_PK_MD (1 << 6) ++#define GCRY_FIPS_FLAG_REJECT_PK_GOST_SM2 (1 << 7) + + #define GCRY_FIPS_FLAG_REJECT_MD \ + (GCRY_FIPS_FLAG_REJECT_MD_MD5 | GCRY_FIPS_FLAG_REJECT_MD_OTHERS) + +-/* Note: Don't reject MD5 */ ++/* Note: Don't reject MD5, PK MD, PK GOST and PK SM2 */ + #define GCRY_FIPS_FLAG_REJECT_COMPAT110 \ + (GCRY_FIPS_FLAG_REJECT_MD_OTHERS \ + | GCRY_FIPS_FLAG_REJECT_MAC \ +diff --git a/tests/t-fips-service-ind.c b/tests/t-fips-service-ind.c +index 90d92c70..fe963fa5 100644 +--- a/tests/t-fips-service-ind.c ++++ b/tests/t-fips-service-ind.c +@@ -228,6 +228,7 @@ check_pk_s_v (int reject) + static struct { + const char *prvkey; + const char *pubkey; ++ const char *data; + int expect_failure; + } tv[] = { + { +@@ -236,6 +237,8 @@ check_pk_s_v (int reject) + "(public-key (ecc (curve nistp256)" + " (q #041ccbe91c075fc7f4f033bfa248db8fccd3565de94bbfb12f3c59ff46c271bf83" + "ce4014c68811f9a21a1fdb2c0e6113e06db7ca93b7404e78dc7ccd5ca89a4ca9#)))", ++ "(data (flags raw)(hash sha256 " ++ "#00112233445566778899AABBCCDDEEFF000102030405060708090A0B0C0D0E0F#))", + 0 + }, + { /* non-compliant curve */ +@@ -244,28 +247,40 @@ check_pk_s_v (int reject) + "(public-key (ecc (curve secp256k1)" + " (q #046fcc37ea5e9e09fec6c83e5fbd7a745e3eee81d16ebd861c9e66f55518c19798" + "4e9f113c07f875691df8afc1029496fc4cb9509b39dcd38f251a83359cc8b4f7#)))", ++ "(data (flags raw)(hash sha256 " ++ "#00112233445566778899AABBCCDDEEFF000102030405060708090A0B0C0D0E0F#))", + 1 +- } ++ }, ++ { /* non-compliant hash */ ++ "(private-key (ecc (curve nistp256)" ++ " (d #519b423d715f8b581f4fa8ee59f4771a5b44c8130b4e3eacca54a56dda72b464#)))", ++ "(public-key (ecc (curve nistp256)" ++ " (q #041ccbe91c075fc7f4f033bfa248db8fccd3565de94bbfb12f3c59ff46c271bf83" ++ "ce4014c68811f9a21a1fdb2c0e6113e06db7ca93b7404e78dc7ccd5ca89a4ca9#)))", ++ "(data (flags raw)(hash ripemd160 " ++ "#00112233445566778899AABBCCDDEEFF00010203#))", ++ 1 ++ }, ++ { /* non-compliant hash for signing */ ++ "(private-key (ecc (curve nistp256)" ++ " (d #519b423d715f8b581f4fa8ee59f4771a5b44c8130b4e3eacca54a56dda72b464#)))", ++ "(public-key (ecc (curve nistp256)" ++ " (q #041ccbe91c075fc7f4f033bfa248db8fccd3565de94bbfb12f3c59ff46c271bf83" ++ "ce4014c68811f9a21a1fdb2c0e6113e06db7ca93b7404e78dc7ccd5ca89a4ca9#)))", ++ "(data (flags raw)(hash sha1 " ++ "#00112233445566778899AABBCCDDEEFF00010203#))", ++ 1 ++ }, + }; + int tvidx; + gpg_error_t err; + gpg_err_code_t ec; +- const char *data = "(data (flags raw)" +- "(hash sha256 #00112233445566778899AABBCCDDEEFF000102030405060708090A0B0C0D0E0F#))"; +- gcry_sexp_t s_data = NULL; +- +- err = gcry_sexp_build (&s_data, NULL, data); +- if (err) +- { +- fail ("error building SEXP for test, %s: %s", +- "data", gpg_strerror (err)); +- return; +- } + + for (tvidx=0; tvidx < DIM(tv); tvidx++) + { + gcry_sexp_t s_pk = NULL; + gcry_sexp_t s_sk = NULL; ++ gcry_sexp_t s_data = NULL; + gcry_sexp_t s_sig= NULL; + + if (verbose) +@@ -287,6 +302,14 @@ check_pk_s_v (int reject) + goto next; + } + ++ err = gcry_sexp_build (&s_data, NULL, tv[tvidx].data); ++ if (err) ++ { ++ fail ("error building SEXP for test, %s: %s", ++ "data", gpg_strerror (err)); ++ goto next; ++ } ++ + err = gcry_pk_sign (&s_sig, s_data, s_sk); + if (err) + { +@@ -363,11 +386,10 @@ check_pk_s_v (int reject) + + next: + gcry_sexp_release (s_sig); ++ gcry_sexp_release (s_data); + gcry_sexp_release (s_pk); + gcry_sexp_release (s_sk); + } +- +- gcry_sexp_release (s_data); + } + + /* Check gcry_pk_hash_sign, gcry_pk_hash_verify API. */ +@@ -1461,6 +1483,8 @@ main (int argc, char **argv) + + xgcry_control ((GCRYCTL_FIPS_REJECT_NON_FIPS, + (GCRY_FIPS_FLAG_REJECT_MD_MD5 ++ | GCRY_FIPS_FLAG_REJECT_PK_MD ++ | GCRY_FIPS_FLAG_REJECT_PK_GOST_SM2 + | GCRY_FIPS_FLAG_REJECT_COMPAT110))); + + check_md_o_w_r_c (1); +-- +2.49.0 + diff --git a/libgcrypt-fips-kdf-Implement-new-FIPS-service-indicator-for-gcry_kdf_derive.patch b/libgcrypt-fips-kdf-Implement-new-FIPS-service-indicator-for-gcry_kdf_derive.patch new file mode 100644 index 0000000..a1710b9 --- /dev/null +++ b/libgcrypt-fips-kdf-Implement-new-FIPS-service-indicator-for-gcry_kdf_derive.patch @@ -0,0 +1,265 @@ +From 5cfa1aee5b98baf0d66333344e0fa45b79cca28b Mon Sep 17 00:00:00 2001 +From: NIIBE Yutaka +Date: Thu, 5 Dec 2024 14:52:17 +0900 +Subject: [PATCH 3/5] fips,kdf: Implement new FIPS service indicator for + gcry_kdf_derive. +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* cipher/kdf.c (_gcry_kdf_derive): Don't reject by GPG_ERR_INV_VALUE +but continue the computation, clearing IS_COMPLIANT. After successful +computation, call fips_service_indicator_mark_success with +IS_COMPLIANT. +* src/visibility.c (gcry_kdf_derive): Call fips_service_indicator_init. +* tests/t-kdf.c (check_fips_gcry_kdf_derive): New. +(main): Call check_fips_gcry_kdf_derive. + +-- + +GnuPG-bug-id: 7338 +Co-authored-by: David Sugar +Suggested-by: Stephan Mueller +Signed-off-by: NIIBE Yutaka +Signed-off-by: Lucas Mülling +--- + cipher/kdf.c | 33 ++++++----- + src/visibility.c | 1 + + tests/t-kdf.c | 149 ++++++++++++++++++++++++++++++++++++++++++++++- + 3 files changed, 169 insertions(+), 14 deletions(-) + +diff --git a/cipher/kdf.c b/cipher/kdf.c +index b4c5f83a..52e6a9ba 100644 +--- a/cipher/kdf.c ++++ b/cipher/kdf.c +@@ -279,28 +279,35 @@ _gcry_kdf_derive (const void *passphrase, size_t passphraselen, + break; + + case GCRY_KDF_PBKDF2: +- if (!saltlen) ++ if (!saltlen || !iterations) + ec = GPG_ERR_INV_VALUE; + else + { +- /* FIPS requires minimum passphrase length, see FIPS 140-3 IG D.N */ +- if (fips_mode () && passphraselen < 8) +- return GPG_ERR_INV_VALUE; ++ int is_compliant = 1; ++ ++ if (fips_mode ()) ++ { ++ /* FIPS requires minimum passphrase length, see FIPS 140-3 IG D.N */ ++ if (passphraselen < 8) ++ is_compliant &= 0; + +- /* FIPS requires minimum salt length of 128 b (SP 800-132 sec. 5.1, p.6) */ +- if (fips_mode () && saltlen < 16) +- return GPG_ERR_INV_VALUE; ++ /* FIPS requires minimum salt length of 128 b (SP 800-132 sec. 5.1, p.6) */ ++ if (saltlen < 16) ++ is_compliant &= 0; + +- /* FIPS requires minimum iterations bound (SP 800-132 sec 5.2, p.6) */ +- if (fips_mode () && iterations < 1000) +- return GPG_ERR_INV_VALUE; ++ /* FIPS requires minimum iterations bound (SP 800-132 sec 5.2, p.6) */ ++ if (iterations < 1000) ++ is_compliant &= 0; + +- /* Check minimum key size */ +- if (fips_mode () && keysize < 14) +- return GPG_ERR_INV_VALUE; ++ /* Check minimum key size */ ++ if (keysize < 14) ++ is_compliant &= 0; ++ } + + ec = _gcry_kdf_pkdf2 (passphrase, passphraselen, subalgo, + salt, saltlen, iterations, keysize, keybuffer); ++ if (!ec) ++ fips_service_indicator_mark_success (is_compliant); + } + break; + +diff --git a/src/visibility.c b/src/visibility.c +index 006e8f80..8f76b854 100644 +--- a/src/visibility.c ++++ b/src/visibility.c +@@ -1400,6 +1400,7 @@ gcry_kdf_derive (const void *passphrase, size_t passphraselen, + { + if (!fips_is_operational ()) + return gpg_error (fips_not_operational ()); ++ fips_service_indicator_init (); + return gpg_error (_gcry_kdf_derive (passphrase, passphraselen, algo, hashalgo, + salt, saltlen, iterations, + keysize, keybuffer)); +diff --git a/tests/t-kdf.c b/tests/t-kdf.c +index 10f64a7c..4b92bd30 100644 +--- a/tests/t-kdf.c ++++ b/tests/t-kdf.c +@@ -1927,6 +1927,151 @@ check_fips_indicators (void) + } + + ++static void ++check_fips_gcry_kdf_derive (void) ++{ ++ static struct { ++ const char *p; /* Passphrase. */ ++ size_t plen; /* Length of P. */ ++ int algo; ++ int subalgo; ++ const char *salt; ++ size_t saltlen; ++ unsigned long iterations; ++ int dklen; /* Requested key length. */ ++ const char *dk; /* Derived key. */ ++ int expect_failure; ++ } tv[] = { ++ { ++ "passwordPASSWORDpassword", 24, ++ GCRY_KDF_PBKDF2, GCRY_MD_SHA1, ++ "saltSALTsaltSALTsaltSALTsaltSALTsalt", 36, ++ 4096, ++ 25, ++ "\x3d\x2e\xec\x4f\xe4\x1c\x84\x9b\x80\xc8" ++ "\xd8\x36\x62\xc0\xe4\x4a\x8b\x29\x1a\x96" ++ "\x4c\xf2\xf0\x70\x38", ++ 0 ++ }, ++ { ++ "pleaseletmein", 13, ++ GCRY_KDF_SCRYPT, 16384, ++ "SodiumChloride", 14, ++ 1, ++ 64, ++ "\x70\x23\xbd\xcb\x3a\xfd\x73\x48\x46\x1c\x06\xcd\x81\xfd\x38\xeb" ++ "\xfd\xa8\xfb\xba\x90\x4f\x8e\x3e\xa9\xb5\x43\xf6\x54\x5d\xa1\xf2" ++ "\xd5\x43\x29\x55\x61\x3f\x0f\xcf\x62\xd4\x97\x05\x24\x2a\x9a\xf9" ++ "\xe6\x1e\x85\xdc\x0d\x65\x1e\x40\xdf\xcf\x01\x7b\x45\x57\x58\x87", ++ 1 /* not-compliant because unallowed algo */ ++ }, ++ { ++ "passwor", 7, ++ GCRY_KDF_PBKDF2, GCRY_MD_SHA1, ++ "saltSALTsaltSALTsaltSALTsaltSALTsalt", 36, ++ 4096, ++ 25, ++ "\xf4\x93\xee\x2b\xbf\x44\x0b\x9e\x64\x53" ++ "\xc2\xb3\x87\xdc\x73\xf8\xfd\xe6\x97\xda" ++ "\xb8\x24\xa0\x26\x50", ++ 1 /* not-compliant because passphrase len is too small */ ++ }, ++ { ++ "passwordPASSWORDpassword", 24, ++ GCRY_KDF_PBKDF2, GCRY_MD_SHA1, ++ "saltSALTsaltSAL", 15, ++ 4096, ++ 25, ++ "\x14\x05\xa4\x2a\xf4\xa8\x12\x14\x7b\x65" ++ "\x8f\xaa\xf0\x7f\x25\xe5\x0f\x0b\x2b\xb7" ++ "\xcf\x8d\x29\x23\x4b", ++ 1 /* not-compliant because salt len is too small */ ++ }, ++ { ++ "passwordPASSWORDpassword", 24, ++ GCRY_KDF_PBKDF2, GCRY_MD_SHA1, ++ "saltSALTsaltSALTsaltSALTsaltSALTsalt", 36, ++ 999, ++ 25, ++ "\xac\xf8\xb4\x67\x41\xc7\xf3\xd1\xa0\xc0" ++ "\x08\xbe\x9b\x23\x96\x78\xbd\x93\xda\x4a" ++ "\x30\xd4\xfb\xf0\x33", ++ 1 /* not-compliant because too few iterations */ ++ }, ++ { ++ "passwordPASSWORDpassword", 24, ++ GCRY_KDF_PBKDF2, GCRY_MD_SHA1, ++ "saltSALTsaltSALTsaltSALTsaltSALTsalt", 36, ++ 4096, ++ 13, ++ "\x3d\x2e\xec\x4f\xe4\x1c\x84\x9b\x80\xc8" ++ "\xd8\x36\x62", ++ 1 /* not-compliant because key size too small */ ++ }, ++ }; ++ ++ int tvidx; ++ gpg_error_t err; ++ unsigned char outbuf[100]; ++ int i; ++ ++ for (tvidx=0; tvidx < DIM(tv); tvidx++) ++ { ++ if (verbose) ++ fprintf (stderr, "checking gcry_kdf_derive test vector %d algo %d for FIPS\n", ++ tvidx, tv[tvidx].algo); ++ assert (tv[tvidx].dklen <= sizeof outbuf); ++ err = gcry_kdf_derive (tv[tvidx].p, tv[tvidx].plen, ++ tv[tvidx].algo, tv[tvidx].subalgo, ++ tv[tvidx].salt, tv[tvidx].saltlen, ++ tv[tvidx].iterations, tv[tvidx].dklen, outbuf); ++ ++ if (err) ++ { ++ fail ("gcry_kdf_derive test %d unexpectedly returned an error in FIPS mode: %s\n", ++ tvidx, gpg_strerror (err)); ++ } ++ else ++ { ++ gpg_err_code_t ec; ++ ++ ec = gcry_get_fips_service_indicator (); ++ if (ec == GPG_ERR_INV_OP) ++ { ++ /* libgcrypt is old, no support of the FIPS service indicator. */ ++ fail ("gcry_kdf_derive test %d unexpectedly failed to check the FIPS service indicator.\n", ++ tvidx); ++ continue; ++ } ++ ++ if (!tv[tvidx].expect_failure && ec) ++ { ++ /* Success with the FIPS service indicator == 0 expected, but != 0. */ ++ fail ("gcry_kdf_derive test %d unexpectedly set the indicator in FIPS mode.\n", ++ tvidx); ++ continue; ++ } ++ else if (tv[tvidx].expect_failure && !ec) ++ { ++ /* Success with the FIPS service indicator != 0 expected, but == 0. */ ++ fail ("gcry_kdf_derive test %d unexpectedly cleared the indicator in FIPS mode.\n", ++ tvidx); ++ continue; ++ } ++ ++ if (memcmp (outbuf, tv[tvidx].dk, tv[tvidx].dklen)) ++ { ++ fail ("gcry_kdf_derive test %d failed: mismatch\n", tvidx); ++ fputs ("got:", stderr); ++ for (i=0; i < tv[tvidx].dklen; i++) ++ fprintf (stderr, " %02x", outbuf[i]); ++ putc ('\n', stderr); ++ } ++ } ++ } ++} ++ ++ + int + main (int argc, char **argv) + { +@@ -2008,7 +2153,9 @@ main (int argc, char **argv) + check_onestep_kdf (); + check_hkdf (); + if (in_fips_mode) +- check_fips_indicators(); ++ check_fips_indicators (); ++ if (in_fips_mode) ++ check_fips_gcry_kdf_derive (); + } + + return error_count ? 1 : 0; +-- +2.49.0 + diff --git a/libgcrypt-fips-mac-Implement-new-FIPS-service-indicator-for-gcry_mac_open.patch b/libgcrypt-fips-mac-Implement-new-FIPS-service-indicator-for-gcry_mac_open.patch new file mode 100644 index 0000000..7843a39 --- /dev/null +++ b/libgcrypt-fips-mac-Implement-new-FIPS-service-indicator-for-gcry_mac_open.patch @@ -0,0 +1,115 @@ +From fcb0c7004b0b6b318fdcced2bf61d9acb1e28cfc Mon Sep 17 00:00:00 2001 +From: NIIBE Yutaka +Date: Fri, 13 Dec 2024 14:25:02 +0900 +Subject: [PATCH 04/19] fips,mac: Implement new FIPS service indicator for + gcry_mac_open. +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* src/gcrypt.h.in (GCRY_MAC_FLAG_REJECT_NON_FIPS): New. +* cipher/mac.c (mac_open): Have FLAGS, instead of SECURE. Reject when +GCRY_MAC_FLAG_REJECT_NON_FIPS, otherwise, mark non compliant. +(_gcry_mac_open): Follow the change. +* src/visibility.c (gcry_mac_open): Add initialization for FIPS +service indicator. +(gcry_mac_setkey): Likewise. Don't reject but mark. + +-- + +GnuPG-bug-id: 7338 +Signed-off-by: NIIBE Yutaka +Signed-off-by: Lucas Mülling +--- + cipher/mac.c | 15 +++++++++++---- + src/gcrypt.h.in | 3 ++- + src/visibility.c | 5 +++-- + 3 files changed, 16 insertions(+), 7 deletions(-) + +diff --git a/cipher/mac.c b/cipher/mac.c +index 128ac53d..0df48fd7 100644 +--- a/cipher/mac.c ++++ b/cipher/mac.c +@@ -513,11 +513,13 @@ check_mac_algo (int algorithm) + * Open a message digest handle for use with algorithm ALGO. + */ + static gcry_err_code_t +-mac_open (gcry_mac_hd_t * hd, int algo, int secure, gcry_ctx_t ctx) ++mac_open (gcry_mac_hd_t * hd, int algo, unsigned int flags, gcry_ctx_t ctx) + { + const gcry_mac_spec_t *spec; + gcry_err_code_t err; + gcry_mac_hd_t h; ++ int secure = !!(flags & GCRY_MAC_FLAG_SECURE); ++ int reject_non_fips = !!(flags & GCRY_MAC_FLAG_REJECT_NON_FIPS); + + spec = spec_from_algo (algo); + if (!spec) +@@ -525,7 +527,12 @@ mac_open (gcry_mac_hd_t * hd, int algo, int secure, gcry_ctx_t ctx) + else if (spec->flags.disabled) + return GPG_ERR_MAC_ALGO; + else if (!spec->flags.fips && fips_mode ()) +- return GPG_ERR_MAC_ALGO; ++ { ++ if (reject_non_fips) ++ return GPG_ERR_MAC_ALGO; ++ else ++ fips_service_indicator_mark_non_compliant (); ++ } + else if (!spec->ops) + return GPG_ERR_MAC_ALGO; + else if (!spec->ops->open || !spec->ops->write || !spec->ops->setkey || +@@ -643,10 +650,10 @@ _gcry_mac_open (gcry_mac_hd_t * h, int algo, unsigned int flags, + gcry_err_code_t rc; + gcry_mac_hd_t hd = NULL; + +- if ((flags & ~GCRY_MAC_FLAG_SECURE)) ++ if ((flags & ~(GCRY_MAC_FLAG_SECURE | GCRY_MAC_FLAG_REJECT_NON_FIPS))) + rc = GPG_ERR_INV_ARG; + else +- rc = mac_open (&hd, algo, !!(flags & GCRY_MAC_FLAG_SECURE), ctx); ++ rc = mac_open (&hd, algo, flags, ctx); + + *h = rc ? NULL : hd; + return rc; +diff --git a/src/gcrypt.h.in b/src/gcrypt.h.in +index 96bf88f6..2a378639 100644 +--- a/src/gcrypt.h.in ++++ b/src/gcrypt.h.in +@@ -1560,7 +1560,8 @@ enum gcry_mac_algos + /* Flags used with the open function. */ + enum gcry_mac_flags + { +- GCRY_MAC_FLAG_SECURE = 1 /* Allocate all buffers in "secure" memory. */ ++ GCRY_MAC_FLAG_SECURE = 1, /* Allocate all buffers in "secure" memory. */ ++ GCRY_MAC_FLAG_REJECT_NON_FIPS = 2 /* Reject non-FIPS-compliant algo. */ + }; + + /* Create a MAC handle for algorithm ALGO. FLAGS may be given as an bitwise OR +diff --git a/src/visibility.c b/src/visibility.c +index 44b05eb2..7699f14f 100644 +--- a/src/visibility.c ++++ b/src/visibility.c +@@ -946,7 +946,7 @@ gcry_mac_open (gcry_mac_hd_t *handle, int algo, unsigned int flags, + *handle = NULL; + return gpg_error (fips_not_operational ()); + } +- ++ fips_service_indicator_init (); + return gpg_error (_gcry_mac_open (handle, algo, flags, ctx)); + } + +@@ -962,8 +962,9 @@ gcry_mac_setkey (gcry_mac_hd_t hd, const void *key, size_t keylen) + if (!fips_is_operational ()) + return gpg_error (fips_not_operational ()); + ++ fips_service_indicator_init (); + if (fips_mode () && keylen < 14) +- return GPG_ERR_INV_VALUE; ++ fips_service_indicator_mark_non_compliant (); + + return gpg_error (_gcry_mac_setkey (hd, key, keylen)); + } +-- +2.49.0 + diff --git a/libgcrypt-fips-md-Implement-new-FIPS-service-indicator-for-gcry_md_hash_.patch b/libgcrypt-fips-md-Implement-new-FIPS-service-indicator-for-gcry_md_hash_.patch new file mode 100644 index 0000000..71f1671 --- /dev/null +++ b/libgcrypt-fips-md-Implement-new-FIPS-service-indicator-for-gcry_md_hash_.patch @@ -0,0 +1,188 @@ +From 3478caac62c712547f7c0e07f4cf9602bc317997 Mon Sep 17 00:00:00 2001 +From: NIIBE Yutaka +Date: Fri, 6 Dec 2024 14:33:58 +0900 +Subject: [PATCH 4/5] fips,md: Implement new FIPS service indicator for + gcry_md_hash_*. +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* cipher/md.c (md_enable): Add an NO_REJECT argument. +(md_open): Check flags against GCRY_MD_FLAG_FIPS_NO_REJECTION to +call md_enable. +(_gcry_md_enable): Follow the change. +(_gcry_md_hash_buffer): Don't reject but keep the computation. +Call fips_service_indicator_mark_success. +(_gcry_md_hash_buffers_extract): Likewise. +* src/gcrypt.h.in (GCRY_MD_FLAG_FIPS_NO_REJECTION): New. +* src/visibility.c (gcry_md_hash_buffer, gcry_md_hash_buffers): Call +fips_service_indicator_init. +(gcry_md_hash_buffers_ext): Likewise. + +-- + +GnuPG-bug-id: 7338 +Signed-off-by: NIIBE Yutaka +Signed-off-by: Lucas Mülling +--- + cipher/md.c | 32 +++++++++++++++++++++++--------- + src/gcrypt.h.in | 1 + + src/visibility.c | 3 +++ + 3 files changed, 27 insertions(+), 9 deletions(-) + +diff --git a/cipher/md.c b/cipher/md.c +index 1991c331..c2bd18c6 100644 +--- a/cipher/md.c ++++ b/cipher/md.c +@@ -285,7 +285,7 @@ struct gcry_md_context + #define CTX_MAGIC_NORMAL 0x11071961 + #define CTX_MAGIC_SECURE 0x16917011 + +-static gcry_err_code_t md_enable (gcry_md_hd_t hd, int algo); ++static gcry_err_code_t md_enable (gcry_md_hd_t hd, int algo, int no_reject); + static void md_close (gcry_md_hd_t a); + static void md_write (gcry_md_hd_t a, const void *inbuf, size_t inlen); + static byte *md_read( gcry_md_hd_t a, int algo ); +@@ -517,7 +517,8 @@ md_open (gcry_md_hd_t *h, int algo, unsigned int flags) + + if (algo) + { +- err = md_enable (hd, algo); ++ err = md_enable (hd, algo, ++ !!(flags & GCRY_MD_FLAG_FIPS_NO_REJECTION)); + if (err) + md_close (hd); + } +@@ -554,7 +555,7 @@ _gcry_md_open (gcry_md_hd_t *h, int algo, unsigned int flags) + + + static gcry_err_code_t +-md_enable (gcry_md_hd_t hd, int algorithm) ++md_enable (gcry_md_hd_t hd, int algorithm, int no_reject) + { + struct gcry_md_context *h = hd->ctx; + const gcry_md_spec_t *spec; +@@ -576,7 +577,7 @@ md_enable (gcry_md_hd_t hd, int algorithm) + err = GPG_ERR_DIGEST_ALGO; + + /* Any non-FIPS algorithm should go this way */ +- if (!err && !spec->flags.fips && fips_mode ()) ++ if (!err && !no_reject && !spec->flags.fips && fips_mode ()) + err = GPG_ERR_DIGEST_ALGO; + + if (!err && h->flags.hmac && spec->read == NULL) +@@ -619,7 +620,7 @@ md_enable (gcry_md_hd_t hd, int algorithm) + gcry_err_code_t + _gcry_md_enable (gcry_md_hd_t hd, int algorithm) + { +- return md_enable (hd, algorithm); ++ return md_enable (hd, algorithm, 0); + } + + +@@ -1260,7 +1261,7 @@ _gcry_md_hash_buffer (int algo, void *digest, + iov.off = 0; + iov.len = length; + +- if (spec->flags.disabled || (!spec->flags.fips && fips_mode ())) ++ if (spec->flags.disabled) + log_bug ("gcry_md_hash_buffer failed for algo %d: %s", + algo, gpg_strerror (gcry_error (GPG_ERR_DIGEST_ALGO))); + +@@ -1273,7 +1274,7 @@ _gcry_md_hash_buffer (int algo, void *digest, + gcry_md_hd_t h; + gpg_err_code_t err; + +- err = md_open (&h, algo, 0); ++ err = md_open (&h, algo, GCRY_MD_FLAG_FIPS_NO_REJECTION); + if (err) + log_bug ("gcry_md_open failed for algo %d: %s", + algo, gpg_strerror (gcry_error(err))); +@@ -1282,6 +1283,12 @@ _gcry_md_hash_buffer (int algo, void *digest, + memcpy (digest, md_read (h, algo), md_digest_length (algo)); + md_close (h); + } ++ ++ if (fips_mode ()) ++ { ++ int is_compliant = spec->flags.fips; ++ fips_service_indicator_mark_success (is_compliant); ++ } + } + + +@@ -1336,7 +1343,7 @@ _gcry_md_hash_buffers_extract (int algo, unsigned int flags, void *digest, + + if (!hmac && spec->hash_buffers) + { +- if (spec->flags.disabled || (!spec->flags.fips && fips_mode ())) ++ if (spec->flags.disabled) + return GPG_ERR_DIGEST_ALGO; + + spec->hash_buffers (digest, digestlen, iov, iovcnt); +@@ -1348,7 +1355,8 @@ _gcry_md_hash_buffers_extract (int algo, unsigned int flags, void *digest, + gcry_md_hd_t h; + gpg_err_code_t rc; + +- rc = md_open (&h, algo, (hmac? GCRY_MD_FLAG_HMAC:0)); ++ rc = md_open (&h, algo, ((hmac? GCRY_MD_FLAG_HMAC:0) ++ | GCRY_MD_FLAG_FIPS_NO_REJECTION)); + if (rc) + return rc; + +@@ -1374,6 +1382,12 @@ _gcry_md_hash_buffers_extract (int algo, unsigned int flags, void *digest, + md_close (h); + } + ++ if (fips_mode ()) ++ { ++ int is_compliant = spec->flags.fips; ++ fips_service_indicator_mark_success (is_compliant); ++ } ++ + return 0; + } + +diff --git a/src/gcrypt.h.in b/src/gcrypt.h.in +index 2f61a0bc..18d04a38 100644 +--- a/src/gcrypt.h.in ++++ b/src/gcrypt.h.in +@@ -1318,6 +1318,7 @@ enum gcry_md_flags + { + GCRY_MD_FLAG_SECURE = 1, /* Allocate all buffers in "secure" memory. */ + GCRY_MD_FLAG_HMAC = 2, /* Make an HMAC out of this algorithm. */ ++ GCRY_MD_FLAG_FIPS_NO_REJECTION = 4, /* Don't reject for FIPS. */ + GCRY_MD_FLAG_BUGEMU1 = 0x0100 + }; + +diff --git a/src/visibility.c b/src/visibility.c +index 8f76b854..be5deda1 100644 +--- a/src/visibility.c ++++ b/src/visibility.c +@@ -1281,6 +1281,7 @@ gcry_md_hash_buffer (int algo, void *digest, + (void)fips_not_operational (); + fips_signal_error ("called in non-operational state"); + } ++ fips_service_indicator_init (); + _gcry_md_hash_buffer (algo, digest, buffer, length); + } + +@@ -1293,6 +1294,7 @@ gcry_md_hash_buffers (int algo, unsigned int flags, void *digest, + (void)fips_not_operational (); + fips_signal_error ("called in non-operational state"); + } ++ fips_service_indicator_init (); + return gpg_error (_gcry_md_hash_buffers (algo, flags, digest, iov, iovcnt)); + } + +@@ -1306,6 +1308,7 @@ gcry_md_hash_buffers_ext (int algo, unsigned int flags, void *digest, + (void)fips_not_operational (); + fips_signal_error ("called in non-operational state"); + } ++ fips_service_indicator_init (); + return gpg_error (_gcry_md_hash_buffers_extract (algo, flags, digest, + digestlen, iov, iovcnt)); + } +-- +2.49.0 + diff --git a/libgcrypt-fips-md-Implement-new-FIPS-service-indicator-for-gcry_md_open-API.patch b/libgcrypt-fips-md-Implement-new-FIPS-service-indicator-for-gcry_md_open-API.patch new file mode 100644 index 0000000..0f580b1 --- /dev/null +++ b/libgcrypt-fips-md-Implement-new-FIPS-service-indicator-for-gcry_md_open-API.patch @@ -0,0 +1,298 @@ +From 9757e280794f537efc82c4eaa9a2944ece6a068a Mon Sep 17 00:00:00 2001 +From: NIIBE Yutaka +Date: Thu, 12 Dec 2024 11:40:31 +0900 +Subject: [PATCH] fips,md: Implement new FIPS service indicator for + gcry_md_open API. +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* src/gcrypt.h.in (GCRY_MD_FLAG_FIPS_NO_REJECTION): Remove. +(GCRY_MD_FLAG_REJECT_NON_FIPS): New. +* cipher/md.c (struct gcry_md_context): Add reject_non_fips. +(md_enable): Remove NO_REJECT argument. +(md_open): Change the FLAGS handling. +(_gcry_md_open): Add checking of FIPS compliance against ALGO. +(_gcry_md_enable): Likewise. +(_gcry_md_hash_buffer): Follow the change of md_open change +which now defaults to no rejection. +(_gcry_md_hash_buffers_extract): Likewise. +* src/visibility.c (gcry_md_open): Add fips_service_indicator_init. +(gcry_md_enable): Likewise. +(gcry_md_setkey): Don't reject but mark non-compliance. +* tests/t-kdf.c (check_fips_gcry_kdf_derive): Add a test with +non-compliant hash function. +* cipher/mac-hmac.c (_gcry_mac_type_spec_hmac_md5): It's not +compliant. +* cipher/md5.c (gcry_md_oid_spec_t oid_spec_md5): It's not compliant. +* tests/t-digest.c (check_hash_buffer, check_hash_buffers): MD5 +tests enabled. + +-- + +See 6376 for the MD5 compliance change in the past. This commit +reverts the change in: + dc4a60e2d70bc52ba2955f8e676341d675ab89a0 + +GnuPG-bug-id: 7338 +Signed-off-by: NIIBE Yutaka +Signed-off-by: Lucas Mülling +--- + cipher/mac-hmac.c | 2 +- + cipher/md.c | 57 +++++++++++++++++++++++++++++++++++++++-------- + cipher/md5.c | 2 +- + src/gcrypt.h.in | 2 +- + src/visibility.c | 6 +++-- + tests/t-digest.c | 6 ++--- + tests/t-kdf.c | 12 ++++++++++ + 7 files changed, 69 insertions(+), 18 deletions(-) + +Index: libgcrypt-1.11.0/cipher/mac-hmac.c +=================================================================== +--- libgcrypt-1.11.0.orig/cipher/mac-hmac.c ++++ libgcrypt-1.11.0/cipher/mac-hmac.c +@@ -1413,7 +1413,7 @@ const gcry_mac_spec_t _gcry_mac_type_spe + #endif + #if USE_MD5 + const gcry_mac_spec_t _gcry_mac_type_spec_hmac_md5 = { +- GCRY_MAC_HMAC_MD5, {0, 1}, "HMAC_MD5", ++ GCRY_MAC_HMAC_MD5, {0, 0}, "HMAC_MD5", + &hmac_ops + }; + #endif +Index: libgcrypt-1.11.0/cipher/md.c +=================================================================== +--- libgcrypt-1.11.0.orig/cipher/md.c ++++ libgcrypt-1.11.0/cipher/md.c +@@ -275,6 +275,7 @@ struct gcry_md_context + unsigned int finalized:1; + unsigned int bugemu1:1; + unsigned int hmac:1; ++ unsigned int reject_non_fips:1; + } flags; + size_t actual_handle_size; /* Allocated size of this handle. */ + FILE *debug; +@@ -285,7 +286,7 @@ struct gcry_md_context + #define CTX_MAGIC_NORMAL 0x11071961 + #define CTX_MAGIC_SECURE 0x16917011 + +-static gcry_err_code_t md_enable (gcry_md_hd_t hd, int algo, int no_reject); ++static gcry_err_code_t md_enable (gcry_md_hd_t hd, int algo); + static void md_close (gcry_md_hd_t a); + static void md_write (gcry_md_hd_t a, const void *inbuf, size_t inlen); + static byte *md_read( gcry_md_hd_t a, int algo ); +@@ -508,6 +509,7 @@ md_open (gcry_md_hd_t *h, int algo, unsi + ctx->flags.secure = secure; + ctx->flags.hmac = hmac; + ctx->flags.bugemu1 = !!(flags & GCRY_MD_FLAG_BUGEMU1); ++ ctx->flags.reject_non_fips = !!(flags & GCRY_MD_FLAG_REJECT_NON_FIPS); + } + + if (! err) +@@ -517,8 +519,7 @@ md_open (gcry_md_hd_t *h, int algo, unsi + + if (algo) + { +- err = md_enable (hd, algo, +- !!(flags & GCRY_MD_FLAG_FIPS_NO_REJECTION)); ++ err = md_enable (hd, algo); + if (err) + md_close (hd); + } +@@ -543,24 +544,44 @@ _gcry_md_open (gcry_md_hd_t *h, int algo + + if ((flags & ~(GCRY_MD_FLAG_SECURE + | GCRY_MD_FLAG_HMAC ++ | GCRY_MD_FLAG_REJECT_NON_FIPS + | GCRY_MD_FLAG_BUGEMU1))) + rc = GPG_ERR_INV_ARG; + else + rc = md_open (&hd, algo, flags); + + *h = rc? NULL : hd; ++ ++ if (!rc && fips_mode ()) ++ { ++ GcryDigestEntry *entry = hd->ctx->list; ++ /* No ENTRY means that ALGO==0. ++ It's not yet known, if it's FIPS compliant or not. */ ++ int is_compliant_algo = 1; ++ ++ if (entry) ++ { ++ const gcry_md_spec_t *spec = entry->spec; ++ is_compliant_algo = spec->flags.fips; ++ } ++ ++ if (!is_compliant_algo) ++ fips_service_indicator_mark_non_compliant (); ++ } ++ + return rc; + } + + + + static gcry_err_code_t +-md_enable (gcry_md_hd_t hd, int algorithm, int no_reject) ++md_enable (gcry_md_hd_t hd, int algorithm) + { + struct gcry_md_context *h = hd->ctx; + const gcry_md_spec_t *spec; + GcryDigestEntry *entry; + gcry_err_code_t err = 0; ++ int reject_non_fips = h->flags.reject_non_fips; + + for (entry = h->list; entry; entry = entry->next) + if (entry->spec->algo == algorithm) +@@ -577,7 +598,7 @@ md_enable (gcry_md_hd_t hd, int algorith + err = GPG_ERR_DIGEST_ALGO; + + /* Any non-FIPS algorithm should go this way */ +- if (!err && !no_reject && !spec->flags.fips && fips_mode ()) ++ if (!err && reject_non_fips && !spec->flags.fips && fips_mode ()) + err = GPG_ERR_DIGEST_ALGO; + + if (!err && h->flags.hmac && spec->read == NULL) +@@ -620,7 +641,26 @@ md_enable (gcry_md_hd_t hd, int algorith + gcry_err_code_t + _gcry_md_enable (gcry_md_hd_t hd, int algorithm) + { +- return md_enable (hd, algorithm, 0); ++ gcry_err_code_t rc; ++ ++ rc = md_enable (hd, algorithm); ++ if (!rc && fips_mode ()) ++ { ++ GcryDigestEntry *entry = hd->ctx->list; ++ /* No ENTRY means, something goes wrong. */ ++ int is_compliant_algo = 0; ++ ++ if (entry) ++ { ++ const gcry_md_spec_t *spec = entry->spec; ++ is_compliant_algo = spec->flags.fips; ++ } ++ ++ if (!is_compliant_algo) ++ fips_service_indicator_mark_non_compliant (); ++ } ++ ++ return rc; + } + + +@@ -1274,7 +1314,7 @@ _gcry_md_hash_buffer (int algo, void *di + gcry_md_hd_t h; + gpg_err_code_t err; + +- err = md_open (&h, algo, GCRY_MD_FLAG_FIPS_NO_REJECTION); ++ err = md_open (&h, algo, 0); + if (err) + log_bug ("gcry_md_open failed for algo %d: %s", + algo, gpg_strerror (gcry_error(err))); +@@ -1355,8 +1395,7 @@ _gcry_md_hash_buffers_extract (int algo, + gcry_md_hd_t h; + gpg_err_code_t rc; + +- rc = md_open (&h, algo, ((hmac? GCRY_MD_FLAG_HMAC:0) +- | GCRY_MD_FLAG_FIPS_NO_REJECTION)); ++ rc = md_open (&h, algo, (hmac? GCRY_MD_FLAG_HMAC:0)); + if (rc) + return rc; + +Index: libgcrypt-1.11.0/cipher/md5.c +=================================================================== +--- libgcrypt-1.11.0.orig/cipher/md5.c ++++ libgcrypt-1.11.0/cipher/md5.c +@@ -314,7 +314,7 @@ static const gcry_md_oid_spec_t oid_spec + + const gcry_md_spec_t _gcry_digest_spec_md5 = + { +- GCRY_MD_MD5, {0, 1}, ++ GCRY_MD_MD5, {0, 0}, + "MD5", asn, DIM (asn), oid_spec_md5, 16, + md5_init, _gcry_md_block_write, md5_final, md5_read, NULL, + NULL, +Index: libgcrypt-1.11.0/src/gcrypt.h.in +=================================================================== +--- libgcrypt-1.11.0.orig/src/gcrypt.h.in ++++ libgcrypt-1.11.0/src/gcrypt.h.in +@@ -1320,7 +1320,7 @@ enum gcry_md_flags + { + GCRY_MD_FLAG_SECURE = 1, /* Allocate all buffers in "secure" memory. */ + GCRY_MD_FLAG_HMAC = 2, /* Make an HMAC out of this algorithm. */ +- GCRY_MD_FLAG_FIPS_NO_REJECTION = 4, /* Don't reject for FIPS. */ ++ GCRY_MD_FLAG_REJECT_NON_FIPS = 4, /* Reject non-FIPS-compliant algo. */ + GCRY_MD_FLAG_BUGEMU1 = 0x0100 + }; + +Index: libgcrypt-1.11.0/src/visibility.c +=================================================================== +--- libgcrypt-1.11.0.orig/src/visibility.c ++++ libgcrypt-1.11.0/src/visibility.c +@@ -1204,7 +1204,7 @@ gcry_md_open (gcry_md_hd_t *h, int algo, + *h = NULL; + return gpg_error (fips_not_operational ()); + } +- ++ fips_service_indicator_init (); + return gpg_error (_gcry_md_open (h, algo, flags)); + } + +@@ -1219,6 +1219,7 @@ gcry_md_enable (gcry_md_hd_t hd, int alg + { + if (!fips_is_operational ()) + return gpg_error (fips_not_operational ()); ++ fips_service_indicator_init (); + return gpg_error (_gcry_md_enable (hd, algo)); + } + +@@ -1382,8 +1383,9 @@ gcry_md_setkey (gcry_md_hd_t hd, const v + if (!fips_is_operational ()) + return gpg_error (fips_not_operational ()); + ++ fips_service_indicator_init (); + if (fips_mode () && keylen < 14) +- return GPG_ERR_INV_VALUE; ++ fips_service_indicator_mark_non_compliant (); + + return gpg_error (_gcry_md_setkey (hd, key, keylen)); + } +Index: libgcrypt-1.11.0/tests/t-digest.c +=================================================================== +--- libgcrypt-1.11.0.orig/tests/t-digest.c ++++ libgcrypt-1.11.0/tests/t-digest.c +@@ -48,8 +48,7 @@ check_digests (void) + const char *expect; + int expect_failure; + } tv[] = { +-#undef ENABLE_THIS_AFTER_T6376_CHANGE_REVISED +-#ifdef ENABLE_THIS_AFTER_T6376_CHANGE_REVISED ++#if USE_MD5 + { GCRY_MD_MD5, "abc", 3, + "\x90\x01\x50\x98\x3C\xD2\x4F\xB0\xD6\x96\x3F\x7D\x28\xE1\x7F\x72", 1 }, + #endif +Index: libgcrypt-1.11.0/tests/t-kdf.c +=================================================================== +--- libgcrypt-1.11.0.orig/tests/t-kdf.c ++++ libgcrypt-1.11.0/tests/t-kdf.c +@@ -2008,6 +2008,18 @@ check_fips_gcry_kdf_derive (void) + "\xd8\x36\x62", + 1 /* not-compliant because key size too small */ + }, ++ { ++ "passwordPASSWORDpassword", 24, ++ GCRY_KDF_PBKDF2, GCRY_MD_BLAKE2B_512, ++ "saltSALTsaltSALTsaltSALTsaltSALTsalt", 36, ++ 4096, ++ 60, ++ "\xa4\x6b\x53\x35\xdb\xdd\xa3\xd2\x5d\x19\xbb\x11\xfe\xdd\xd9\x9e" ++ "\x45\x2a\x7c\x34\x47\x41\x98\xca\x31\x74\xb6\x34\x22\xac\x83\xb0" ++ "\x38\x6e\xf5\x93\x0f\xf5\x16\x46\x0b\x97\xdc\x6c\x27\x5b\xe7\x25" ++ "\xc2\xcb\xec\x50\x02\xc6\x52\x8b\x34\x68\x53\x65", ++ 1 /* not-compliant because subalgo is not the one of approved */ ++ } + }; + + int tvidx; diff --git a/libgcrypt-fips-md-gcry_md_copy-should-care-about-FIPS-service-indicator.patch b/libgcrypt-fips-md-gcry_md_copy-should-care-about-FIPS-service-indicator.patch new file mode 100644 index 0000000..5edccac --- /dev/null +++ b/libgcrypt-fips-md-gcry_md_copy-should-care-about-FIPS-service-indicator.patch @@ -0,0 +1,85 @@ +From 60db2a175d120aba6818de49638b36006878abf7 Mon Sep 17 00:00:00 2001 +From: NIIBE Yutaka +Date: Wed, 18 Dec 2024 14:14:37 +0900 +Subject: [PATCH 10/19] fips,md: gcry_md_copy should care about FIPS service + indicator. +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* cipher/md.c (md_copy): In a case of non-compliant, mark with +fips_service_indicator_mark_non_compliant. +* src/visibility.c (gcry_md_copy): Initialize the indicator. + +-- + +GnuPG-bug-id: 7338 +Signed-off-by: NIIBE Yutaka +Signed-off-by: Lucas Mülling +--- + cipher/md.c | 11 +++++++++++ + src/visibility.c | 1 + + 2 files changed, 12 insertions(+) + +diff --git a/cipher/md.c b/cipher/md.c +index 666e1dfa..08a564ad 100644 +--- a/cipher/md.c ++++ b/cipher/md.c +@@ -673,6 +673,7 @@ md_copy (gcry_md_hd_t ahd, gcry_md_hd_t *b_hd) + GcryDigestEntry *ar, *br; + gcry_md_hd_t bhd; + size_t n; ++ int is_compliant_algo = 1; + + if (ahd->bufpos) + md_write (ahd, NULL, 0); +@@ -699,10 +700,15 @@ md_copy (gcry_md_hd_t ahd, gcry_md_hd_t *b_hd) + b->list = NULL; + b->debug = NULL; + ++ if (!a->list) ++ is_compliant_algo = 0; ++ + /* Copy the complete list of algorithms. The copied list is + reversed, but that doesn't matter. */ + for (ar = a->list; ar; ar = ar->next) + { ++ const gcry_md_spec_t *spec = ar->spec; ++ + if (a->flags.secure) + br = xtrymalloc_secure (ar->actual_struct_size); + else +@@ -714,6 +720,8 @@ md_copy (gcry_md_hd_t ahd, gcry_md_hd_t *b_hd) + goto leave; + } + ++ is_compliant_algo &= spec->flags.fips; ++ + memcpy (br, ar, ar->actual_struct_size); + br->next = b->list; + b->list = br; +@@ -724,6 +732,9 @@ md_copy (gcry_md_hd_t ahd, gcry_md_hd_t *b_hd) + + *b_hd = bhd; + ++ if (!is_compliant_algo) ++ fips_service_indicator_mark_non_compliant (); ++ + leave: + return err; + } +diff --git a/src/visibility.c b/src/visibility.c +index d219f1a6..c9d07f0b 100644 +--- a/src/visibility.c ++++ b/src/visibility.c +@@ -1232,6 +1232,7 @@ gcry_md_copy (gcry_md_hd_t *bhd, gcry_md_hd_t ahd) + *bhd = NULL; + return gpg_error (fips_not_operational ()); + } ++ fips_service_indicator_init (); + return gpg_error (_gcry_md_copy (bhd, ahd)); + } + +-- +2.49.0 + diff --git a/libgcrypt-fips-tests-Add-t-digest.patch b/libgcrypt-fips-tests-Add-t-digest.patch new file mode 100644 index 0000000..fc5e8e8 --- /dev/null +++ b/libgcrypt-fips-tests-Add-t-digest.patch @@ -0,0 +1,243 @@ +From 7faf542f157330f3b247fa2542182ac805f06737 Mon Sep 17 00:00:00 2001 +From: NIIBE Yutaka +Date: Mon, 9 Dec 2024 14:05:59 +0900 +Subject: [PATCH 5/5] fips,tests: Add t-digest. +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* tests/Makefile.am (tests_bin): Add t-digest. +* tests/t-digest.c: New. + +-- + +GnuPG-bug-id: 7338 +Signed-off-by: NIIBE Yutaka +Signed-off-by: Lucas Mülling +--- + tests/Makefile.am | 2 +- + tests/t-digest.c | 199 ++++++++++++++++++++++++++++++++++++++++++++++ + 2 files changed, 200 insertions(+), 1 deletion(-) + create mode 100644 tests/t-digest.c + +diff --git a/tests/Makefile.am b/tests/Makefile.am +index 52f7dd61..93774fe9 100644 +--- a/tests/Makefile.am ++++ b/tests/Makefile.am +@@ -25,7 +25,7 @@ tests_bin = \ + version t-secmem mpitests t-sexp t-convert \ + t-mpi-bit t-mpi-point t-lock \ + prime basic keygen pubkey hmac hashtest t-kdf keygrip \ +- aeswrap random t-kem t-mlkem t-thread-local ++ aeswrap random t-kem t-mlkem t-thread-local t-digest + + if USE_RSA + tests_bin += pkcs1v2 t-rsa-pss t-rsa-15 t-rsa-testparm +diff --git a/tests/t-digest.c b/tests/t-digest.c +new file mode 100644 +index 00000000..3a94fa69 +--- /dev/null ++++ b/tests/t-digest.c +@@ -0,0 +1,199 @@ ++/* t-digest.c - MD regression tests ++ * Copyright (C) 2024 g10 Code GmbH ++ * ++ * This file is part of Libgcrypt. ++ * ++ * Libgcrypt is free software; you can redistribute it and/or modify ++ * it under the terms of the GNU Lesser General Public License as ++ * published by the Free Software Foundation; either version 2.1 of ++ * the License, or (at your option) any later version. ++ * ++ * Libgcrypt 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 Lesser General Public License for more details. ++ * ++ * You should have received a copy of the GNU Lesser General Public License ++ * along with this program; if not, see . ++ * SPDX-License-Identifier: LGPL-2.1+ ++ */ ++ ++#ifdef HAVE_CONFIG_H ++#include ++#endif ++#include ++#include ++#include ++#include ++#include ++ ++#define PGM "t-digest" ++ ++#include "t-common.h" ++static int in_fips_mode; ++ ++/* Mingw requires us to include windows.h after winsock2.h which is ++ included by gcrypt.h. */ ++#ifdef _WIN32 ++# include ++#endif ++ ++static void ++check_digests (void) ++{ ++ static struct { ++ int algo; ++ const char *data; ++ int datalen; ++ const char *expect; ++ int expect_failure; ++ } tv[] = { ++#undef ENABLE_THIS_AFTER_T6376_CHANGE_REVISED ++#ifdef ENABLE_THIS_AFTER_T6376_CHANGE_REVISED ++ { GCRY_MD_MD5, "abc", 3, ++ "\x90\x01\x50\x98\x3C\xD2\x4F\xB0\xD6\x96\x3F\x7D\x28\xE1\x7F\x72", 1 }, ++#endif ++ { GCRY_MD_SHA1, "abc", 3, ++ "\xA9\x99\x3E\x36\x47\x06\x81\x6A\xBA\x3E" ++ "\x25\x71\x78\x50\xC2\x6C\x9C\xD0\xD8\x9D" }, ++ { GCRY_MD_SHA256, "abc", 3, ++ "\xba\x78\x16\xbf\x8f\x01\xcf\xea\x41\x41\x40\xde\x5d\xae\x22\x23" ++ "\xb0\x03\x61\xa3\x96\x17\x7a\x9c\xb4\x10\xff\x61\xf2\x00\x15\xad" }, ++ { GCRY_MD_SHA384, "abc", 3, ++ "\xcb\x00\x75\x3f\x45\xa3\x5e\x8b\xb5\xa0\x3d\x69\x9a\xc6\x50\x07" ++ "\x27\x2c\x32\xab\x0e\xde\xd1\x63\x1a\x8b\x60\x5a\x43\xff\x5b\xed" ++ "\x80\x86\x07\x2b\xa1\xe7\xcc\x23\x58\xba\xec\xa1\x34\xc8\x25\xa7" }, ++ { GCRY_MD_SHA512, "abc", 3, ++ "\xDD\xAF\x35\xA1\x93\x61\x7A\xBA\xCC\x41\x73\x49\xAE\x20\x41\x31" ++ "\x12\xE6\xFA\x4E\x89\xA9\x7E\xA2\x0A\x9E\xEE\xE6\x4B\x55\xD3\x9A" ++ "\x21\x92\x99\x2A\x27\x4F\xC1\xA8\x36\xBA\x3C\x23\xA3\xFE\xEB\xBD" ++ "\x45\x4D\x44\x23\x64\x3C\xE8\x0E\x2A\x9A\xC9\x4F\xA5\x4C\xA4\x9F" }, ++ { GCRY_MD_SHA3_256, "abc", 3, ++ "\x3a\x98\x5d\xa7\x4f\xe2\x25\xb2\x04\x5c\x17\x2d\x6b\xd3\x90\xbd" ++ "\x85\x5f\x08\x6e\x3e\x9d\x52\x5b\x46\xbf\xe2\x45\x11\x43\x15\x32" }, ++ { GCRY_MD_SHA3_384, "abc", 3, ++ "\xec\x01\x49\x82\x88\x51\x6f\xc9\x26\x45\x9f\x58\xe2\xc6\xad\x8d" ++ "\xf9\xb4\x73\xcb\x0f\xc0\x8c\x25\x96\xda\x7c\xf0\xe4\x9b\xe4\xb2" ++ "\x98\xd8\x8c\xea\x92\x7a\xc7\xf5\x39\xf1\xed\xf2\x28\x37\x6d\x25" }, ++ { GCRY_MD_SHA3_512, "abc", 3, ++ "\xb7\x51\x85\x0b\x1a\x57\x16\x8a\x56\x93\xcd\x92\x4b\x6b\x09\x6e" ++ "\x08\xf6\x21\x82\x74\x44\xf7\x0d\x88\x4f\x5d\x02\x40\xd2\x71\x2e" ++ "\x10\xe1\x16\xe9\x19\x2a\xf3\xc9\x1a\x7e\xc5\x76\x47\xe3\x93\x40" ++ "\x57\x34\x0b\x4c\xf4\x08\xd5\xa5\x65\x92\xf8\x27\x4e\xec\x53\xf0" }, ++ { GCRY_MD_RMD160, "abc", 3, ++ "\x8e\xb2\x08\xf7\xe0\x5d\x98\x7a\x9b\x04" ++ "\x4a\x8e\x98\xc6\xb0\x87\xf1\x5a\x0b\xfc", 1 }, ++ }; ++ int tvidx; ++ unsigned char hash[64]; ++ int expectlen; ++ ++ for (tvidx=0; tvidx < DIM(tv); tvidx++) ++ { ++ gpg_err_code_t ec; ++ ++ if (verbose) ++ fprintf (stderr, "checking gcry_md_hash_buffer test %d\n", ++ tvidx); ++ ++ expectlen = gcry_md_get_algo_dlen (tv[tvidx].algo); ++ assert (expectlen != 0); ++ assert (expectlen <= sizeof hash); ++ gcry_md_hash_buffer (tv[tvidx].algo, hash, ++ tv[tvidx].data, tv[tvidx].datalen); ++ ++ ec = gcry_get_fips_service_indicator (); ++ if (ec == GPG_ERR_INV_OP) ++ { ++ /* libgcrypt is old, no support of the FIPS service indicator. */ ++ fail ("gcry_md_hash_buffer test %d unexpectedly failed to check the FIPS service indicator.\n", ++ tvidx); ++ continue; ++ } ++ ++ if (in_fips_mode && !tv[tvidx].expect_failure && ec) ++ { ++ /* Success with the FIPS service indicator == 0 expected, but != 0. */ ++ fail ("gcry_md_hash_buffer test %d unexpectedly set the indicator in FIPS mode.\n", ++ tvidx); ++ continue; ++ } ++ else if (in_fips_mode && tv[tvidx].expect_failure && !ec) ++ { ++ /* Success with the FIPS service indicator != 0 expected, but == 0. */ ++ fail ("gcry_md_hash_buffer test %d unexpectedly cleared the indicator in FIPS mode.\n", ++ tvidx); ++ continue; ++ } ++ ++ if (memcmp (hash, tv[tvidx].expect, expectlen)) ++ { ++ int i; ++ ++ fail ("gcry_md_hash_buffer test %d failed: mismatch\n", tvidx); ++ fputs ("got:", stderr); ++ for (i=0; i < expectlen; i++) ++ fprintf (stderr, " %02x", hash[i]); ++ putc ('\n', stderr); ++ } ++ } ++} ++ ++ ++int ++main (int argc, char **argv) ++{ ++ int last_argc = -1; ++ ++ if (argc) ++ { argc--; argv++; } ++ ++ while (argc && last_argc != argc) ++ { ++ last_argc = argc; ++ if (!strcmp (*argv, "--")) ++ { ++ argc--; argv++; ++ break; ++ } ++ else if (!strcmp (*argv, "--help")) ++ { ++ fputs ("usage: " PGM " [options]\n" ++ "Options:\n" ++ " --verbose print timings etc.\n" ++ " --debug flyswatter\n", ++ stdout); ++ exit (0); ++ } ++ else if (!strcmp (*argv, "--verbose")) ++ { ++ verbose++; ++ argc--; argv++; ++ } ++ else if (!strcmp (*argv, "--debug")) ++ { ++ verbose += 2; ++ debug++; ++ argc--; argv++; ++ } ++ else if (!strncmp (*argv, "--", 2)) ++ die ("unknown option '%s'", *argv); ++ } ++ ++ if (!gcry_check_version (GCRYPT_VERSION)) ++ die ("version mismatch\n"); ++ ++ if (gcry_fips_mode_active ()) ++ in_fips_mode = 1; ++ ++ if (!in_fips_mode) ++ xgcry_control ((GCRYCTL_DISABLE_SECMEM, 0)); ++ ++ xgcry_control ((GCRYCTL_INITIALIZATION_FINISHED, 0)); ++ if (debug) ++ xgcry_control ((GCRYCTL_SET_DEBUG_FLAGS, 1u , 0)); ++ ++ check_digests (); ++ ++ return !!error_count; ++} +-- +2.49.0 + diff --git a/libgcrypt-fips-tests-Add-tests-for-md_open-write-read-close-for-t-digest.patch b/libgcrypt-fips-tests-Add-tests-for-md_open-write-read-close-for-t-digest.patch new file mode 100644 index 0000000..699c1eb --- /dev/null +++ b/libgcrypt-fips-tests-Add-tests-for-md_open-write-read-close-for-t-digest.patch @@ -0,0 +1,172 @@ +From 917fc6000dfebd8854f0d1c220b85dec0dbf4676 Mon Sep 17 00:00:00 2001 +From: NIIBE Yutaka +Date: Fri, 13 Dec 2024 11:54:31 +0900 +Subject: [PATCH 03/19] fips,tests: Add tests for md_open/write/read/close for + t-digest. +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* tests/t-digest.c (check_md_o_w_r_c): New. +(main): Call check_md_o_w_r_c. + +-- + +GnuPG-bug-id: 7338 +Signed-off-by: NIIBE Yutaka +Signed-off-by: Lucas Mülling +--- + tests/t-digest.c | 133 +++++++++++++++++++++++++++++++++++++++++++++++ + 1 file changed, 133 insertions(+) + +Index: libgcrypt-1.11.0/tests/t-digest.c +=================================================================== +--- libgcrypt-1.11.0.orig/tests/t-digest.c ++++ libgcrypt-1.11.0/tests/t-digest.c +@@ -39,6 +39,138 @@ static int in_fips_mode; + #endif + + static void ++check_md_o_w_r_c (void) ++{ ++ static struct { ++ int algo; ++ const char *data; ++ int datalen; ++ const char *expect; ++ int expect_failure; ++ unsigned int flags; ++ } tv[] = { ++#if USE_MD5 ++ { GCRY_MD_MD5, "abc", 3, ++ "\x90\x01\x50\x98\x3C\xD2\x4F\xB0\xD6\x96\x3F\x7D\x28\xE1\x7F\x72", 1 }, ++ { GCRY_MD_MD5, "abc", 3, ++ "\x90\x01\x50\x98\x3C\xD2\x4F\xB0\xD6\x96\x3F\x7D\x28\xE1\x7F\x72", 1, ++ GCRY_MD_FLAG_REJECT_NON_FIPS }, ++#endif ++#if USE_SHA1 ++ { GCRY_MD_SHA1, "abc", 3, ++ "\xA9\x99\x3E\x36\x47\x06\x81\x6A\xBA\x3E" ++ "\x25\x71\x78\x50\xC2\x6C\x9C\xD0\xD8\x9D" }, ++#endif ++ { GCRY_MD_SHA256, "abc", 3, ++ "\xba\x78\x16\xbf\x8f\x01\xcf\xea\x41\x41\x40\xde\x5d\xae\x22\x23" ++ "\xb0\x03\x61\xa3\x96\x17\x7a\x9c\xb4\x10\xff\x61\xf2\x00\x15\xad" }, ++ { GCRY_MD_SHA384, "abc", 3, ++ "\xcb\x00\x75\x3f\x45\xa3\x5e\x8b\xb5\xa0\x3d\x69\x9a\xc6\x50\x07" ++ "\x27\x2c\x32\xab\x0e\xde\xd1\x63\x1a\x8b\x60\x5a\x43\xff\x5b\xed" ++ "\x80\x86\x07\x2b\xa1\xe7\xcc\x23\x58\xba\xec\xa1\x34\xc8\x25\xa7" }, ++ { GCRY_MD_SHA512, "abc", 3, ++ "\xDD\xAF\x35\xA1\x93\x61\x7A\xBA\xCC\x41\x73\x49\xAE\x20\x41\x31" ++ "\x12\xE6\xFA\x4E\x89\xA9\x7E\xA2\x0A\x9E\xEE\xE6\x4B\x55\xD3\x9A" ++ "\x21\x92\x99\x2A\x27\x4F\xC1\xA8\x36\xBA\x3C\x23\xA3\xFE\xEB\xBD" ++ "\x45\x4D\x44\x23\x64\x3C\xE8\x0E\x2A\x9A\xC9\x4F\xA5\x4C\xA4\x9F" }, ++ { GCRY_MD_SHA3_256, "abc", 3, ++ "\x3a\x98\x5d\xa7\x4f\xe2\x25\xb2\x04\x5c\x17\x2d\x6b\xd3\x90\xbd" ++ "\x85\x5f\x08\x6e\x3e\x9d\x52\x5b\x46\xbf\xe2\x45\x11\x43\x15\x32" }, ++ { GCRY_MD_SHA3_384, "abc", 3, ++ "\xec\x01\x49\x82\x88\x51\x6f\xc9\x26\x45\x9f\x58\xe2\xc6\xad\x8d" ++ "\xf9\xb4\x73\xcb\x0f\xc0\x8c\x25\x96\xda\x7c\xf0\xe4\x9b\xe4\xb2" ++ "\x98\xd8\x8c\xea\x92\x7a\xc7\xf5\x39\xf1\xed\xf2\x28\x37\x6d\x25" }, ++ { GCRY_MD_SHA3_512, "abc", 3, ++ "\xb7\x51\x85\x0b\x1a\x57\x16\x8a\x56\x93\xcd\x92\x4b\x6b\x09\x6e" ++ "\x08\xf6\x21\x82\x74\x44\xf7\x0d\x88\x4f\x5d\x02\x40\xd2\x71\x2e" ++ "\x10\xe1\x16\xe9\x19\x2a\xf3\xc9\x1a\x7e\xc5\x76\x47\xe3\x93\x40" ++ "\x57\x34\x0b\x4c\xf4\x08\xd5\xa5\x65\x92\xf8\x27\x4e\xec\x53\xf0" } ++#if USE_RMD160 ++ , ++ { GCRY_MD_RMD160, "abc", 3, ++ "\x8e\xb2\x08\xf7\xe0\x5d\x98\x7a\x9b\x04" ++ "\x4a\x8e\x98\xc6\xb0\x87\xf1\x5a\x0b\xfc", 1 } ++#endif ++ }; ++ int tvidx; ++ unsigned char *hash; ++ int expectlen; ++ gpg_error_t err; ++ ++ for (tvidx=0; tvidx < DIM(tv); tvidx++) ++ { ++ gpg_err_code_t ec; ++ gcry_md_hd_t h; ++ ++ if (verbose) ++ fprintf (stderr, "checking gcry_md_open test %d\n", ++ tvidx); ++ ++ expectlen = gcry_md_get_algo_dlen (tv[tvidx].algo); ++ assert (expectlen != 0); ++ err = gcry_md_open (&h, tv[tvidx].algo, tv[tvidx].flags); ++ if (err) ++ { ++ if (in_fips_mode && (tv[tvidx].flags & GCRY_MD_FLAG_REJECT_NON_FIPS) ++ && tv[tvidx].expect_failure) ++ /* Here, an error is expected */ ++ ; ++ else ++ fail ("gcry_md_open test %d unexpectedly failed: %s\n", ++ tvidx, gpg_strerror (err)); ++ continue; ++ } ++ else ++ { ++ if (in_fips_mode && (tv[tvidx].flags & GCRY_MD_FLAG_REJECT_NON_FIPS) ++ && tv[tvidx].expect_failure) ++ /* This case, an error is expected, but we observed success */ ++ fail ("gcry_md_open test %d unexpectedly succeeded\n", tvidx); ++ } ++ ++ ++ ec = gcry_get_fips_service_indicator (); ++ if (ec == GPG_ERR_INV_OP) ++ { ++ /* libgcrypt is old, no support of the FIPS service indicator. */ ++ fail ("gcry_md_open test %d unexpectedly failed to check the FIPS service indicator.\n", ++ tvidx); ++ continue; ++ } ++ ++ if (in_fips_mode && !tv[tvidx].expect_failure && ec) ++ { ++ /* Success with the FIPS service indicator == 0 expected, but != 0. */ ++ fail ("gcry_md_open test %d unexpectedly set the indicator in FIPS mode.\n", ++ tvidx); ++ continue; ++ } ++ else if (in_fips_mode && tv[tvidx].expect_failure && !ec) ++ { ++ /* Success with the FIPS service indicator != 0 expected, but == 0. */ ++ fail ("gcry_md_open test %d unexpectedly cleared the indicator in FIPS mode.\n", ++ tvidx); ++ continue; ++ } ++ ++ gcry_md_write (h, tv[tvidx].data, tv[tvidx].datalen); ++ hash = gcry_md_read (h, tv[tvidx].algo); ++ if (memcmp (hash, tv[tvidx].expect, expectlen)) ++ { ++ int i; ++ ++ fail ("gcry_md_open test %d failed: mismatch\n", tvidx); ++ fputs ("got:", stderr); ++ for (i=0; i < expectlen; i++) ++ fprintf (stderr, " %02x", hash[i]); ++ putc ('\n', stderr); ++ } ++ ++ gcry_md_close (h); ++ } ++} ++ ++static void + check_digests (void) + { + static struct { +@@ -194,6 +326,7 @@ main (int argc, char **argv) + xgcry_control ((GCRYCTL_SET_DEBUG_FLAGS, 1u , 0)); + + check_digests (); ++ check_md_o_w_r_c (); + + return !!error_count; + } diff --git a/libgcrypt-jitterentropy-3.4.0.patch b/libgcrypt-jitterentropy-3.4.0.patch new file mode 100644 index 0000000..dbb77ba --- /dev/null +++ b/libgcrypt-jitterentropy-3.4.0.patch @@ -0,0 +1,618 @@ +Index: libgcrypt-1.10.0/random/jitterentropy-base.c +=================================================================== +--- libgcrypt-1.10.0.orig/random/jitterentropy-base.c ++++ libgcrypt-1.10.0/random/jitterentropy-base.c +@@ -42,7 +42,7 @@ + * require consumer to be updated (as long as this number + * is zero, the API is not considered stable and can + * change without a bump of the major version) */ +-#define MINVERSION 3 /* API compatible, ABI may change, functional ++#define MINVERSION 4 /* API compatible, ABI may change, functional + * enhancements only, consumer can be left unchanged if + * enhancements are not considered */ + #define PATCHLEVEL 0 /* API / ABI compatible, no functional changes, no +@@ -200,29 +200,38 @@ ssize_t jent_read_entropy(struct rand_da + tocopy = (DATA_SIZE_BITS / 8); + else + tocopy = len; +- memcpy(p, &ec->data, tocopy); ++ ++ jent_read_random_block(ec, p, tocopy); + + len -= tocopy; + p += tocopy; + } + + /* +- * To be on the safe side, we generate one more round of entropy +- * which we do not give out to the caller. That round shall ensure +- * that in case the calling application crashes, memory dumps, pages +- * out, or due to the CPU Jitter RNG lingering in memory for long +- * time without being moved and an attacker cracks the application, +- * all he reads in the entropy pool is a value that is NEVER EVER +- * being used for anything. Thus, he does NOT see the previous value +- * that was returned to the caller for cryptographic purposes. ++ * Enhanced backtracking support: At this point, the hash state ++ * contains the digest of the previous Jitter RNG collection round ++ * which is inserted there by jent_read_random_block with the SHA ++ * update operation. At the current code location we completed ++ * one request for a caller and we do not know how long it will ++ * take until a new request is sent to us. To guarantee enhanced ++ * backtracking resistance at this point (i.e. ensure that an attacker ++ * cannot obtain information about prior random numbers we generated), ++ * but still stirring the hash state with old data the Jitter RNG ++ * obtains a new message digest from its state and re-inserts it. ++ * After this operation, the Jitter RNG state is still stirred with ++ * the old data, but an attacker who gets access to the memory after ++ * this point cannot deduce the random numbers produced by the ++ * Jitter RNG prior to this point. + */ + /* +- * If we use secured memory, do not use that precaution as the secure +- * memory protects the entropy pool. Moreover, note that using this +- * call reduces the speed of the RNG by up to half ++ * If we use secured memory, where backtracking support may not be ++ * needed because the state is protected in a different method, ++ * it is permissible to drop this support. But strongly weigh the ++ * pros and cons considering that the SHA3 operation is not that ++ * expensive. + */ + #ifndef JENT_CPU_JITTERENTROPY_SECURE_MEMORY +- jent_random_data(ec); ++ jent_read_random_block(ec, NULL, 0); + #endif + + err: +@@ -379,6 +388,7 @@ static struct rand_data + *jent_entropy_collector_alloc_internal(unsigned int osr, unsigned int flags) + { + struct rand_data *entropy_collector; ++ uint32_t memsize = 0; + + /* + * Requesting disabling and forcing of internal timer +@@ -405,7 +415,7 @@ static struct rand_data + return NULL; + + if (!(flags & JENT_DISABLE_MEMORY_ACCESS)) { +- uint32_t memsize = jent_memsize(flags); ++ memsize = jent_memsize(flags); + + entropy_collector->mem = _gcry_calloc (1, memsize); + +@@ -431,13 +441,19 @@ static struct rand_data + entropy_collector->memaccessloops = JENT_MEMORY_ACCESSLOOPS; + } + ++ if (sha3_alloc(&entropy_collector->hash_state)) ++ goto err; ++ ++ /* Initialize the hash state */ ++ sha3_256_init(entropy_collector->hash_state); ++ + /* verify and set the oversampling rate */ + if (osr < JENT_MIN_OSR) + osr = JENT_MIN_OSR; + entropy_collector->osr = osr; + entropy_collector->flags = flags; + +- if (jent_fips_enabled() || (flags & JENT_FORCE_FIPS)) ++ if ((flags & JENT_FORCE_FIPS) || jent_fips_enabled()) + entropy_collector->fips_enabled = 1; + + /* Initialize the APT */ +@@ -469,7 +485,7 @@ static struct rand_data + + err: + if (entropy_collector->mem != NULL) +- jent_zfree(entropy_collector->mem, JENT_MEMORY_SIZE); ++ jent_zfree(entropy_collector->mem, memsize); + jent_zfree(entropy_collector, sizeof(struct rand_data)); + return NULL; + } +@@ -511,6 +527,7 @@ JENT_PRIVATE_STATIC + void jent_entropy_collector_free(struct rand_data *entropy_collector) + { + if (entropy_collector != NULL) { ++ sha3_dealloc(entropy_collector->hash_state); + jent_notime_disable(entropy_collector); + if (entropy_collector->mem != NULL) { + jent_zfree(entropy_collector->mem, +@@ -664,6 +681,7 @@ static inline int jent_entropy_init_comm + int ret; + + jent_notime_block_switch(); ++ jent_health_cb_block_switch(); + + if (sha3_tester()) + return EHASH; +@@ -710,6 +728,8 @@ int jent_entropy_init_ex(unsigned int os + if (ret) + return ret; + ++ ret = ENOTIME; ++ + /* Test without internal timer unless caller does not want it */ + if (!(flags & JENT_FORCE_INTERNAL_TIMER)) + ret = jent_time_entropy_init(osr, +@@ -732,3 +752,9 @@ int jent_entropy_switch_notime_impl(stru + return jent_notime_switch(new_thread); + } + #endif ++ ++JENT_PRIVATE_STATIC ++int jent_set_fips_failure_callback(jent_fips_failure_cb cb) ++{ ++ return jent_set_fips_failure_callback_internal(cb); ++} +Index: libgcrypt-1.10.0/random/jitterentropy-gcd.c +=================================================================== +--- libgcrypt-1.10.0.orig/random/jitterentropy-gcd.c ++++ libgcrypt-1.10.0/random/jitterentropy-gcd.c +@@ -113,12 +113,8 @@ int jent_gcd_analyze(uint64_t *delta_his + goto out; + } + +- /* +- * Ensure that we have variations in the time stamp below 100 for at +- * least 10% of all checks -- on some platforms, the counter increments +- * in multiples of 100, but not always +- */ +- if (running_gcd >= 100) { ++ /* Set a sensible maximum value. */ ++ if (running_gcd >= UINT32_MAX / 2) { + ret = ECOARSETIME; + goto out; + } +Index: libgcrypt-1.10.0/random/jitterentropy-health.c +=================================================================== +--- libgcrypt-1.10.0.orig/random/jitterentropy-health.c ++++ libgcrypt-1.10.0/random/jitterentropy-health.c +@@ -19,9 +19,24 @@ + * DAMAGE. + */ + +-#include "jitterentropy.h" + #include "jitterentropy-health.h" + ++static jent_fips_failure_cb fips_cb = NULL; ++static int jent_health_cb_switch_blocked = 0; ++ ++void jent_health_cb_block_switch(void) ++{ ++ jent_health_cb_switch_blocked = 1; ++} ++ ++int jent_set_fips_failure_callback_internal(jent_fips_failure_cb cb) ++{ ++ if (jent_health_cb_switch_blocked) ++ return -EAGAIN; ++ fips_cb = cb; ++ return 0; ++} ++ + /*************************************************************************** + * Lag Predictor Test + * +@@ -434,5 +449,9 @@ unsigned int jent_health_failure(struct + if (!ec->fips_enabled) + return 0; + ++ if (fips_cb && ec->health_failure) { ++ fips_cb(ec, ec->health_failure); ++ } ++ + return ec->health_failure; + } +Index: libgcrypt-1.10.0/random/jitterentropy-health.h +=================================================================== +--- libgcrypt-1.10.0.orig/random/jitterentropy-health.h ++++ libgcrypt-1.10.0/random/jitterentropy-health.h +@@ -20,11 +20,16 @@ + #ifndef JITTERENTROPY_HEALTH_H + #define JITTERENTROPY_HEALTH_H + ++#include "jitterentropy.h" ++ + #ifdef __cplusplus + extern "C" + { + #endif + ++void jent_health_cb_block_switch(void); ++int jent_set_fips_failure_callback_internal(jent_fips_failure_cb cb); ++ + static inline uint64_t jent_delta(uint64_t prev, uint64_t next) + { + return (next - prev); +Index: libgcrypt-1.10.0/random/jitterentropy-noise.c +=================================================================== +--- libgcrypt-1.10.0.orig/random/jitterentropy-noise.c ++++ libgcrypt-1.10.0/random/jitterentropy-noise.c +@@ -33,7 +33,7 @@ + * Update of the loop count used for the next round of + * an entropy collection. + * +- * @ec [in] entropy collector struct -- may be NULL ++ * @ec [in] entropy collector struct + * @bits [in] is the number of low bits of the timer to consider + * @min [in] is the number of bits we shift the timer value to the right at + * the end to make sure we have a guaranteed minimum value +@@ -61,16 +61,13 @@ static uint64_t jent_loop_shuffle(struct + * Mix the current state of the random number into the shuffle + * calculation to balance that shuffle a bit more. + */ +- if (ec) { +- jent_get_nstime_internal(ec, &time); +- time ^= ec->data[0]; +- } ++ jent_get_nstime_internal(ec, &time); + + /* + * We fold the time value as much as possible to ensure that as many + * bits of the time stamp are included as possible. + */ +- for (i = 0; ((DATA_SIZE_BITS + bits - 1) / bits) > i; i++) { ++ for (i = 0; (((sizeof(time) << 3) + bits - 1) / bits) > i; i++) { + shuffle ^= time & mask; + time = time >> bits; + } +@@ -91,11 +88,11 @@ static uint64_t jent_loop_shuffle(struct + * This function injects the individual bits of the time value into the + * entropy pool using a hash. + * +- * @ec [in] entropy collector struct -- may be NULL +- * @time [in] time stamp to be injected ++ * @ec [in] entropy collector struct ++ * @time [in] time delta to be injected + * @loop_cnt [in] if a value not equal to 0 is set, use the given value as + * number of loops to perform the hash operation +- * @stuck [in] Is the time stamp identified as stuck? ++ * @stuck [in] Is the time delta identified as stuck? + * + * Output: + * updated hash context +@@ -104,17 +101,19 @@ static void jent_hash_time(struct rand_d + uint64_t loop_cnt, unsigned int stuck) + { + HASH_CTX_ON_STACK(ctx); +- uint8_t itermediary[SHA3_256_SIZE_DIGEST]; ++ uint8_t intermediary[SHA3_256_SIZE_DIGEST]; + uint64_t j = 0; +- uint64_t hash_loop_cnt; + #define MAX_HASH_LOOP 3 + #define MIN_HASH_LOOP 0 + + /* Ensure that macros cannot overflow jent_loop_shuffle() */ + BUILD_BUG_ON((MAX_HASH_LOOP + MIN_HASH_LOOP) > 63); +- hash_loop_cnt = ++ uint64_t hash_loop_cnt = + jent_loop_shuffle(ec, MAX_HASH_LOOP, MIN_HASH_LOOP); + ++ /* Use the memset to shut up valgrind */ ++ memset(intermediary, 0, sizeof(intermediary)); ++ + sha3_256_init(&ctx); + + /* +@@ -125,35 +124,54 @@ static void jent_hash_time(struct rand_d + hash_loop_cnt = loop_cnt; + + /* +- * This loop basically slows down the SHA-3 operation depending +- * on the hash_loop_cnt. Each iteration of the loop generates the +- * same result. ++ * This loop fills a buffer which is injected into the entropy pool. ++ * The main reason for this loop is to execute something over which we ++ * can perform a timing measurement. The injection of the resulting ++ * data into the pool is performed to ensure the result is used and ++ * the compiler cannot optimize the loop away in case the result is not ++ * used at all. Yet that data is considered "additional information" ++ * considering the terminology from SP800-90A without any entropy. ++ * ++ * Note, it does not matter which or how much data you inject, we are ++ * interested in one Keccack1600 compression operation performed with ++ * the sha3_final. + */ + for (j = 0; j < hash_loop_cnt; j++) { +- sha3_update(&ctx, ec->data, SHA3_256_SIZE_DIGEST); +- sha3_update(&ctx, (uint8_t *)&time, sizeof(uint64_t)); ++ sha3_update(&ctx, intermediary, sizeof(intermediary)); ++ sha3_update(&ctx, (uint8_t *)&ec->rct_count, ++ sizeof(ec->rct_count)); ++ sha3_update(&ctx, (uint8_t *)&ec->apt_cutoff, ++ sizeof(ec->apt_cutoff)); ++ sha3_update(&ctx, (uint8_t *)&ec->apt_observations, ++ sizeof(ec->apt_observations)); ++ sha3_update(&ctx, (uint8_t *)&ec->apt_count, ++ sizeof(ec->apt_count)); ++ sha3_update(&ctx,(uint8_t *) &ec->apt_base, ++ sizeof(ec->apt_base)); + sha3_update(&ctx, (uint8_t *)&j, sizeof(uint64_t)); ++ sha3_final(&ctx, intermediary); ++ } + +- /* +- * If the time stamp is stuck, do not finally insert the value +- * into the entropy pool. Although this operation should not do +- * any harm even when the time stamp has no entropy, SP800-90B +- * requires that any conditioning operation to have an identical +- * amount of input data according to section 3.1.5. +- */ ++ /* ++ * Inject the data from the previous loop into the pool. This data is ++ * not considered to contain any entropy, but it stirs the pool a bit. ++ */ ++ sha3_update(ec->hash_state, intermediary, sizeof(intermediary)); + +- /* +- * The sha3_final operations re-initialize the context for the +- * next loop iteration. +- */ +- if (stuck || (j < hash_loop_cnt - 1)) +- sha3_final(&ctx, itermediary); +- else +- sha3_final(&ctx, ec->data); +- } ++ /* ++ * Insert the time stamp into the hash context representing the pool. ++ * ++ * If the time stamp is stuck, do not finally insert the value into the ++ * entropy pool. Although this operation should not do any harm even ++ * when the time stamp has no entropy, SP800-90B requires that any ++ * conditioning operation to have an identical amount of input data ++ * according to section 3.1.5. ++ */ ++ if (!stuck) ++ sha3_update(ec->hash_state, (uint8_t *)&time, sizeof(uint64_t)); + + jent_memset_secure(&ctx, SHA_MAX_CTX_SIZE); +- jent_memset_secure(itermediary, sizeof(itermediary)); ++ jent_memset_secure(intermediary, sizeof(intermediary)); + } + + #define MAX_ACC_LOOP_BIT 7 +@@ -184,13 +202,12 @@ static inline uint32_t xoshiro128starsta + + static void jent_memaccess(struct rand_data *ec, uint64_t loop_cnt) + { +- uint64_t i = 0; ++ uint64_t i = 0, time = 0; + union { + uint32_t u[4]; + uint8_t b[sizeof(uint32_t) * 4]; + } prngState = { .u = {0x8e93eec0, 0xce65608a, 0xa8d46b46, 0xe83cef69} }; + uint32_t addressMask; +- uint64_t acc_loop_cnt; + + if (NULL == ec || NULL == ec->mem) + return; +@@ -199,7 +216,7 @@ static void jent_memaccess(struct rand_d + + /* Ensure that macros cannot overflow jent_loop_shuffle() */ + BUILD_BUG_ON((MAX_ACC_LOOP_BIT + MIN_ACC_LOOP_BIT) > 63); +- acc_loop_cnt = ++ uint64_t acc_loop_cnt = + jent_loop_shuffle(ec, MAX_ACC_LOOP_BIT, MIN_ACC_LOOP_BIT); + + /* +@@ -213,8 +230,10 @@ static void jent_memaccess(struct rand_d + * "per-update: timing, it gets you mostly independent "per-update" + * timing, so we can now benefit from the Central Limit Theorem! + */ +- for (i = 0; i < sizeof(prngState); i++) +- prngState.b[i] ^= ec->data[i]; ++ for (i = 0; i < sizeof(prngState); i++) { ++ jent_get_nstime_internal(ec, &time); ++ prngState.b[i] ^= (uint8_t)(time & 0xff); ++ } + + /* + * testing purposes -- allow test app to set the counter, not +@@ -358,21 +377,21 @@ unsigned int jent_measure_jitter(struct + + /** + * Generator of one 256 bit random number +- * Function fills rand_data->data ++ * Function fills rand_data->hash_state + * + * @ec [in] Reference to entropy collector + */ + void jent_random_data(struct rand_data *ec) + { +- unsigned int k = 0, safety_factor = ENTROPY_SAFETY_FACTOR; ++ unsigned int k = 0, safety_factor = 0; + +- if (!ec->fips_enabled) +- safety_factor = 0; ++ if (ec->fips_enabled) ++ safety_factor = ENTROPY_SAFETY_FACTOR; + + /* priming of the ->prev_time value */ + jent_measure_jitter(ec, 0, NULL); + +- while (1) { ++ while (!jent_health_failure(ec)) { + /* If a stuck measurement is received, repeat measurement */ + if (jent_measure_jitter(ec, 0, NULL)) + continue; +@@ -385,3 +404,22 @@ void jent_random_data(struct rand_data * + break; + } + } ++ ++void jent_read_random_block(struct rand_data *ec, char *dst, size_t dst_len) ++{ ++ uint8_t jent_block[SHA3_256_SIZE_DIGEST]; ++ ++ BUILD_BUG_ON(SHA3_256_SIZE_DIGEST != (DATA_SIZE_BITS / 8)); ++ ++ /* The final operation automatically re-initializes the ->hash_state */ ++ sha3_final(ec->hash_state, jent_block); ++ if (dst_len) ++ memcpy(dst, jent_block, dst_len); ++ ++ /* ++ * Stir the new state with the data from the old state - the digest ++ * of the old data is not considered to have entropy. ++ */ ++ sha3_update(ec->hash_state, jent_block, sizeof(jent_block)); ++ jent_memset_secure(jent_block, sizeof(jent_block)); ++} +Index: libgcrypt-1.10.0/random/jitterentropy-noise.h +=================================================================== +--- libgcrypt-1.10.0.orig/random/jitterentropy-noise.h ++++ libgcrypt-1.10.0/random/jitterentropy-noise.h +@@ -31,6 +31,7 @@ unsigned int jent_measure_jitter(struct + uint64_t loop_cnt, + uint64_t *ret_current_delta); + void jent_random_data(struct rand_data *ec); ++void jent_read_random_block(struct rand_data *ec, char *dst, size_t dst_len); + + #ifdef __cplusplus + } +Index: libgcrypt-1.10.0/random/jitterentropy-sha3.c +=================================================================== +--- libgcrypt-1.10.0.orig/random/jitterentropy-sha3.c ++++ libgcrypt-1.10.0/random/jitterentropy-sha3.c +@@ -19,6 +19,7 @@ + */ + + #include "jitterentropy-sha3.h" ++#include "jitterentropy.h" + + /*************************************************************************** + * Message Digest Implementation +@@ -380,3 +381,23 @@ int sha3_tester(void) + + return 0; + } ++ ++int sha3_alloc(void **hash_state) ++{ ++ struct sha_ctx *tmp; ++ ++ tmp = jent_zalloc(SHA_MAX_CTX_SIZE); ++ if (!tmp) ++ return 1; ++ ++ *hash_state = tmp; ++ ++ return 0; ++} ++ ++void sha3_dealloc(void *hash_state) ++{ ++ struct sha_ctx *ctx = (struct sha_ctx *)hash_state; ++ ++ jent_zfree(ctx, SHA_MAX_CTX_SIZE); ++} +Index: libgcrypt-1.10.0/random/jitterentropy-sha3.h +=================================================================== +--- libgcrypt-1.10.0.orig/random/jitterentropy-sha3.h ++++ libgcrypt-1.10.0/random/jitterentropy-sha3.h +@@ -47,6 +47,8 @@ struct sha_ctx { + void sha3_256_init(struct sha_ctx *ctx); + void sha3_update(struct sha_ctx *ctx, const uint8_t *in, size_t inlen); + void sha3_final(struct sha_ctx *ctx, uint8_t *digest); ++int sha3_alloc(void **hash_state); ++void sha3_dealloc(void *hash_state); + int sha3_tester(void); + + #ifdef __cplusplus +Index: libgcrypt-1.10.0/random/jitterentropy-timer.c +=================================================================== +--- libgcrypt-1.10.0.orig/random/jitterentropy-timer.c ++++ libgcrypt-1.10.0/random/jitterentropy-timer.c +@@ -202,8 +202,8 @@ int jent_notime_enable(struct rand_data + if (jent_force_internal_timer || (flags & JENT_FORCE_INTERNAL_TIMER)) { + /* Self test not run yet */ + if (!jent_force_internal_timer && +- jent_time_entropy_init(flags | JENT_FORCE_INTERNAL_TIMER, +- ec->osr)) ++ jent_time_entropy_init(ec->osr, ++ flags | JENT_FORCE_INTERNAL_TIMER)) + return EHEALTH; + + ec->enable_notime = 1; +Index: libgcrypt-1.10.0/random/jitterentropy.h +=================================================================== +--- libgcrypt-1.10.0.orig/random/jitterentropy.h ++++ libgcrypt-1.10.0/random/jitterentropy.h +@@ -49,7 +49,7 @@ + ***************************************************************************/ + + /* +- * Enable timer-less timer support ++ * Enable timer-less timer support with JENT_CONF_ENABLE_INTERNAL_TIMER + * + * In case the hardware is identified to not provide a high-resolution time + * stamp, this option enables a built-in high-resolution time stamp mechanism. +@@ -166,7 +166,7 @@ struct rand_data + * of the RNG are marked as SENSITIVE. A user must not + * access that information while the RNG executes its loops to + * calculate the next random value. */ +- uint8_t data[SHA3_256_SIZE_DIGEST]; /* SENSITIVE Actual random number */ ++ void *hash_state; /* SENSITIVE hash state entropy pool */ + uint64_t prev_time; /* SENSITIVE Previous time stamp */ + #define DATA_SIZE_BITS (SHA3_256_SIZE_DIGEST_BITS) + +@@ -378,28 +378,34 @@ int jent_entropy_init(void); + JENT_PRIVATE_STATIC + int jent_entropy_init_ex(unsigned int osr, unsigned int flags); + ++/* ++ * Set a callback to run on health failure in FIPS mode. ++ * This function will take an action determined by the caller. ++ */ ++typedef void (*jent_fips_failure_cb)(struct rand_data *ec, ++ unsigned int health_failure); ++JENT_PRIVATE_STATIC ++int jent_set_fips_failure_callback(jent_fips_failure_cb cb); ++ + /* return version number of core library */ + JENT_PRIVATE_STATIC + unsigned int jent_version(void); + +-#ifdef JENT_CONF_ENABLE_INTERNAL_TIMER + /* Set a different thread handling logic for the notimer support */ + JENT_PRIVATE_STATIC + int jent_entropy_switch_notime_impl(struct jent_notime_thread *new_thread); +-#endif + + /* -- END of Main interface functions -- */ + + /* -- BEGIN timer-less threading support functions to prevent code dupes -- */ + +-struct jent_notime_ctx { + #ifdef JENT_CONF_ENABLE_INTERNAL_TIMER ++ ++struct jent_notime_ctx { + pthread_attr_t notime_pthread_attr; /* pthreads library */ + pthread_t notime_thread_id; /* pthreads thread ID */ +-#endif + }; + +-#ifdef JENT_CONF_ENABLE_INTERNAL_TIMER + + JENT_PRIVATE_STATIC + int jent_notime_init(void **ctx); +Index: libgcrypt-1.10.0/random/jitterentropy-base-user.h +=================================================================== +--- libgcrypt-1.10.0.orig/random/jitterentropy-base-user.h ++++ libgcrypt-1.10.0/random/jitterentropy-base-user.h +@@ -213,12 +213,12 @@ static inline void jent_get_cachesize(lo + ext = strstr(buf, "K"); + if (ext) { + shift = 10; +- ext = '\0'; ++ *ext = '\0'; + } else { + ext = strstr(buf, "M"); + if (ext) { + shift = 20; +- ext = '\0'; ++ *ext = '\0'; + } + } + diff --git a/libgcrypt-md-Fix-gcry_md_algo_info-to-mark-reject-under-FIPS-mode.patch b/libgcrypt-md-Fix-gcry_md_algo_info-to-mark-reject-under-FIPS-mode.patch new file mode 100644 index 0000000..25f5904 --- /dev/null +++ b/libgcrypt-md-Fix-gcry_md_algo_info-to-mark-reject-under-FIPS-mode.patch @@ -0,0 +1,82 @@ +From 2f17a98a80b155e750ab77d4703e33612e545d58 Mon Sep 17 00:00:00 2001 +From: NIIBE Yutaka +Date: Tue, 25 Feb 2025 16:27:25 +0900 +Subject: [PATCH 1/4] md: Fix gcry_md_algo_info to mark/reject under FIPS mode. +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* cipher/md.c (check_digest_algo): Fix for marking non-compliance. +* src/visibility.c (gcry_md_algo_info): Add check with +fips_is_operational. + +-- + +GnuPG-bug-id: 7338 +Signed-off-by: NIIBE Yutaka +Signed-off-by: Lucas Mülling +--- + cipher/md.c | 26 ++++++++++++++++++++++---- + src/visibility.c | 3 +++ + 2 files changed, 25 insertions(+), 4 deletions(-) + +diff --git a/cipher/md.c b/cipher/md.c +index f600e7bb..caf33afc 100644 +--- a/cipher/md.c ++++ b/cipher/md.c +@@ -436,16 +436,34 @@ _gcry_md_algo_name (int algorithm) + + + static gcry_err_code_t +-check_digest_algo (int algorithm) ++check_digest_algo (int algo) + { + const gcry_md_spec_t *spec; ++ int reject = 0; + +- spec = spec_from_algo (algorithm); +- if (spec && !spec->flags.disabled && (spec->flags.fips || !fips_mode ())) ++ spec = spec_from_algo (algo); ++ if (!spec) ++ return GPG_ERR_DIGEST_ALGO; ++ ++ if (spec->flags.disabled) ++ return GPG_ERR_DIGEST_ALGO; ++ ++ if (!fips_mode ()) + return 0; + +- return GPG_ERR_DIGEST_ALGO; ++ if (spec->flags.fips) ++ return 0; ++ ++ if (algo == GCRY_MD_MD5) ++ reject = fips_check_rejection (GCRY_FIPS_FLAG_REJECT_MD_MD5); ++ else ++ reject = fips_check_rejection (GCRY_FIPS_FLAG_REJECT_MD_OTHERS); ++ ++ if (reject) ++ return GPG_ERR_DIGEST_ALGO; + ++ fips_service_indicator_mark_non_compliant (); ++ return 0; + } + + +diff --git a/src/visibility.c b/src/visibility.c +index e02d6cfe..4134446a 100644 +--- a/src/visibility.c ++++ b/src/visibility.c +@@ -1373,6 +1373,9 @@ gcry_md_info (gcry_md_hd_t h, int what, void *buffer, size_t *nbytes) + gcry_error_t + gcry_md_algo_info (int algo, int what, void *buffer, size_t *nbytes) + { ++ if (!fips_is_operational ()) ++ return gpg_error (fips_not_operational ()); ++ fips_service_indicator_init (); + return gpg_error (_gcry_md_algo_info (algo, what, buffer, nbytes)); + } + +-- +2.49.0 + diff --git a/libgcrypt-md-Make-SHA-1-non-FIPS-internally-for-1.12-API.patch b/libgcrypt-md-Make-SHA-1-non-FIPS-internally-for-1.12-API.patch new file mode 100644 index 0000000..bbea9bb --- /dev/null +++ b/libgcrypt-md-Make-SHA-1-non-FIPS-internally-for-1.12-API.patch @@ -0,0 +1,154 @@ +From 4ee91a94bcdad32aed4364d09e3daf8841fa579f Mon Sep 17 00:00:00 2001 +From: NIIBE Yutaka +Date: Tue, 11 Mar 2025 14:01:11 +0900 +Subject: [PATCH 11/14] md: Make SHA-1 non-FIPS internally for 1.12 API. +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* src/gcrypt.h.in (GCRY_FIPS_FLAG_REJECT_MD_SHA1): New. +* cipher/md.c (check_digest_algo_spec, _gcry_md_open, md_enable) +(_gcry_md_enable, md_copy): Care about SHA1. +* cipher/sha1.c (_gcry_digest_spec_sha1): Make SHA1 non-FIPS. +* tests/t-fips-service-ind.c (check_mac_o_w_r_c): SHA1 is non-FIPS. +(check_md_o_w_r_c, check_hash_buffer, check_hash_buffers): Likewise. +(main): Add GCRY_FIPS_FLAG_REJECT_MD_SHA1 for gcry_control. + +-- + +For 1.10 ABI (which 1.11 keeps), SHA1 is an approved hash function +(while its use in public key crypto is non-FIPS). + +For 1.12 API, the dynamic FIPS service indicator is going to be added. + +In 1.11.1 implementation, we are trying to support 1.12 dynamic FIPS +service indicator in forward-compatible way. For this purpose, +internally, it's specified as non-FIPS in _gcry_digest_spec_sha1. + +Note that update for tests/basic.c and tests/pkcs1v2.c are needed to +use SHA256 (or one of approved hash functions) in 1.12, so that test +program can be a reference for programmers. + +Co-authored-by: Lucas Mulling +Signed-off-by: NIIBE Yutaka +Signed-off-by: Lucas Mülling +--- + cipher/md.c | 10 ++++++++++ + cipher/sha1.c | 2 +- + src/gcrypt.h.in | 1 + + tests/t-fips-service-ind.c | 9 +++++---- + 4 files changed, 17 insertions(+), 5 deletions(-) + +Index: libgcrypt-1.11.0/cipher/md.c +=================================================================== +--- libgcrypt-1.11.0.orig/cipher/md.c ++++ libgcrypt-1.11.0/cipher/md.c +@@ -451,6 +451,8 @@ check_digest_algo_spec (int algo, const + + if (algo == GCRY_MD_MD5) + reject = fips_check_rejection (GCRY_FIPS_FLAG_REJECT_MD_MD5); ++ else if (algo == GCRY_MD_SHA1) ++ reject = fips_check_rejection (GCRY_FIPS_FLAG_REJECT_MD_SHA1); + else + reject = fips_check_rejection (GCRY_FIPS_FLAG_REJECT_MD_OTHERS); + +@@ -590,6 +592,8 @@ _gcry_md_open (gcry_md_hd_t *h, int algo + + if (algo == GCRY_MD_MD5) + reject = fips_check_rejection (GCRY_FIPS_FLAG_REJECT_MD_MD5); ++ else if (algo == GCRY_MD_SHA1) ++ reject = fips_check_rejection (GCRY_FIPS_FLAG_REJECT_MD_SHA1); + else + reject = fips_check_rejection (GCRY_FIPS_FLAG_REJECT_MD_OTHERS); + +@@ -625,6 +629,8 @@ md_enable (gcry_md_hd_t hd, int algorith + + if (algorithm == GCRY_MD_MD5) + reject = fips_check_rejection (GCRY_FIPS_FLAG_REJECT_MD_MD5); ++ else if (algorithm == GCRY_MD_SHA1) ++ reject = fips_check_rejection (GCRY_FIPS_FLAG_REJECT_MD_SHA1); + else + reject = fips_check_rejection (GCRY_FIPS_FLAG_REJECT_MD_OTHERS); + +@@ -703,6 +709,8 @@ _gcry_md_enable (gcry_md_hd_t hd, int al + + if (algorithm == GCRY_MD_MD5) + reject = fips_check_rejection (GCRY_FIPS_FLAG_REJECT_MD_MD5); ++ else if (algorithm == GCRY_MD_SHA1) ++ reject = fips_check_rejection (GCRY_FIPS_FLAG_REJECT_MD_SHA1); + else + reject = fips_check_rejection (GCRY_FIPS_FLAG_REJECT_MD_OTHERS); + +@@ -780,6 +788,8 @@ md_copy (gcry_md_hd_t ahd, gcry_md_hd_t + + if (spec->algo == GCRY_MD_MD5) + reject |= fips_check_rejection (GCRY_FIPS_FLAG_REJECT_MD_MD5); ++ else if (spec->algo == GCRY_MD_SHA1) ++ reject = fips_check_rejection (GCRY_FIPS_FLAG_REJECT_MD_SHA1); + else + reject |= fips_check_rejection (GCRY_FIPS_FLAG_REJECT_MD_OTHERS); + } +Index: libgcrypt-1.11.0/cipher/sha1.c +=================================================================== +--- libgcrypt-1.11.0.orig/cipher/sha1.c ++++ libgcrypt-1.11.0/cipher/sha1.c +@@ -759,7 +759,7 @@ static const gcry_md_oid_spec_t oid_spec + + const gcry_md_spec_t _gcry_digest_spec_sha1 = + { +- GCRY_MD_SHA1, {0, 1}, ++ GCRY_MD_SHA1, {0, 0}, + "SHA1", asn, DIM (asn), oid_spec_sha1, 20, + sha1_init, _gcry_md_block_write, sha1_final, sha1_read, NULL, + _gcry_sha1_hash_buffers, +Index: libgcrypt-1.11.0/src/gcrypt.h.in +=================================================================== +--- libgcrypt-1.11.0.orig/src/gcrypt.h.in ++++ libgcrypt-1.11.0/src/gcrypt.h.in +@@ -1982,6 +1982,7 @@ char *gcry_get_config (int mode, const c + #define GCRY_FIPS_FLAG_REJECT_PK_GOST_SM2 (1 << 7) + #define GCRY_FIPS_FLAG_REJECT_CIPHER_MODE (1 << 8) + /**/ ++#define GCRY_FIPS_FLAG_REJECT_MD_SHA1 (1 << 9) + #define GCRY_FIPS_FLAG_REJECT_PK_ECC_K (1 << 10) + #define GCRY_FIPS_FLAG_REJECT_PK_FLAGS (1 << 11) + +Index: libgcrypt-1.11.0/tests/t-fips-service-ind.c +=================================================================== +--- libgcrypt-1.11.0.orig/tests/t-fips-service-ind.c ++++ libgcrypt-1.11.0/tests/t-fips-service-ind.c +@@ -1107,7 +1107,7 @@ check_mac_o_w_r_c (int reject) + #if USE_SHA1 + { GCRY_MAC_HMAC_SHA1, "hmac input abc", 14, "hmac key input", 14, + "\xc9\x62\x9d\x16\x0f\xc2\xc4\xcd\x38\xac\x3a\x00\xdc\x29\x61\x03" +- "\x69\x50\xd7\x3a" }, ++ "\x69\x50\xd7\x3a", 1 }, + #endif + { GCRY_MAC_HMAC_SHA256, "hmac input abc", 14, "hmac key input", 14, + "\x6a\xda\x4d\xd5\xf3\xa7\x32\x9d\xd2\x55\xc0\x7f\xe6\x0a\x93\xb8" +@@ -1264,7 +1264,7 @@ check_md_o_w_r_c (int reject) + #if USE_SHA1 + { GCRY_MD_SHA1, "abc", 3, + "\xA9\x99\x3E\x36\x47\x06\x81\x6A\xBA\x3E" +- "\x25\x71\x78\x50\xC2\x6C\x9C\xD0\xD8\x9D" }, ++ "\x25\x71\x78\x50\xC2\x6C\x9C\xD0\xD8\x9D", 1 }, + #endif + { GCRY_MD_SHA256, "abc", 3, + "\xba\x78\x16\xbf\x8f\x01\xcf\xea\x41\x41\x40\xde\x5d\xae\x22\x23" +@@ -1389,7 +1389,7 @@ check_digests (void) + #endif + { GCRY_MD_SHA1, "abc", 3, + "\xA9\x99\x3E\x36\x47\x06\x81\x6A\xBA\x3E" +- "\x25\x71\x78\x50\xC2\x6C\x9C\xD0\xD8\x9D" }, ++ "\x25\x71\x78\x50\xC2\x6C\x9C\xD0\xD8\x9D", 1 }, + { GCRY_MD_SHA256, "abc", 3, + "\xba\x78\x16\xbf\x8f\x01\xcf\xea\x41\x41\x40\xde\x5d\xae\x22\x23" + "\xb0\x03\x61\xa3\x96\x17\x7a\x9c\xb4\x10\xff\x61\xf2\x00\x15\xad" }, +@@ -1701,6 +1701,7 @@ main (int argc, char **argv) + | GCRY_FIPS_FLAG_REJECT_CIPHER_MODE + | GCRY_FIPS_FLAG_REJECT_PK_MD + | GCRY_FIPS_FLAG_REJECT_PK_GOST_SM2 ++ | GCRY_FIPS_FLAG_REJECT_MD_SHA1 + | GCRY_FIPS_FLAG_REJECT_PK_ECC_K + | GCRY_FIPS_FLAG_REJECT_PK_FLAGS + | GCRY_FIPS_FLAG_REJECT_COMPAT110))); diff --git a/libgcrypt-md-Use-check_digest_algo_spec-in-_gcry_md_selftest.patch b/libgcrypt-md-Use-check_digest_algo_spec-in-_gcry_md_selftest.patch new file mode 100644 index 0000000..75489df --- /dev/null +++ b/libgcrypt-md-Use-check_digest_algo_spec-in-_gcry_md_selftest.patch @@ -0,0 +1,74 @@ +From ce4755d5c5500cede6d7d380fdab2d15f5d77796 Mon Sep 17 00:00:00 2001 +From: NIIBE Yutaka +Date: Wed, 26 Feb 2025 10:23:28 +0900 +Subject: [PATCH 2/4] md: Use check_digest_algo_spec in _gcry_md_selftest. +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* cipher/md.c (check_digest_algo_spec): New. +(check_digest_algo): Use check_digest_algo_spec. +(_gcry_md_selftest): Likewise. + +-- + +GnuPG-bug-id: 7338 +Signed-off-by: NIIBE Yutaka +Signed-off-by: Lucas Mülling +--- + cipher/md.c | 22 +++++++++++++--------- + 1 file changed, 13 insertions(+), 9 deletions(-) + +diff --git a/cipher/md.c b/cipher/md.c +index caf33afc..a8027e9e 100644 +--- a/cipher/md.c ++++ b/cipher/md.c +@@ -436,15 +436,10 @@ _gcry_md_algo_name (int algorithm) + + + static gcry_err_code_t +-check_digest_algo (int algo) ++check_digest_algo_spec (int algo, const gcry_md_spec_t *spec) + { +- const gcry_md_spec_t *spec; + int reject = 0; + +- spec = spec_from_algo (algo); +- if (!spec) +- return GPG_ERR_DIGEST_ALGO; +- + if (spec->flags.disabled) + return GPG_ERR_DIGEST_ALGO; + +@@ -466,6 +461,17 @@ check_digest_algo (int algo) + return 0; + } + ++static gcry_err_code_t ++check_digest_algo (int algo) ++{ ++ const gcry_md_spec_t *spec = spec_from_algo (algo); ++ ++ if (!spec) ++ return GPG_ERR_DIGEST_ALGO; ++ else ++ return check_digest_algo_spec (algo, spec); ++} ++ + + /**************** + * Open a message digest handle for use with algorithm ALGO. +@@ -1808,9 +1814,7 @@ _gcry_md_selftest (int algo, int extended, selftest_report_func_t report) + const gcry_md_spec_t *spec; + + spec = spec_from_algo (algo); +- if (spec && !spec->flags.disabled +- && (spec->flags.fips || !fips_mode ()) +- && spec->selftest) ++ if (spec && !check_digest_algo_spec (algo, spec) && spec->selftest) + ec = spec->selftest (algo, extended, report); + else + { +-- +2.49.0 + diff --git a/libgcrypt-no-deprecated-grep-alias.patch b/libgcrypt-no-deprecated-grep-alias.patch new file mode 100644 index 0000000..ba0dde8 --- /dev/null +++ b/libgcrypt-no-deprecated-grep-alias.patch @@ -0,0 +1,35 @@ +--- libgcrypt-1.10.3.orig/acinclude.m4 ++++ libgcrypt-1.10.3/acinclude.m4 +@@ -130,10 +130,10 @@ EOF + ac_nlist=conftest.nm + if AC_TRY_EVAL(NM conftest.$ac_objext \| $lt_cv_sys_global_symbol_pipe \| cut -d \' \' -f 2 \> $ac_nlist) && test -s "$ac_nlist"; then + # See whether the symbols have a leading underscore. +- if egrep '^_nm_test_func' "$ac_nlist" >/dev/null; then ++ if grep -E '^_nm_test_func' "$ac_nlist" >/dev/null; then + ac_cv_sys_symbol_underscore=yes + else +- if egrep '^nm_test_func ' "$ac_nlist" >/dev/null; then ++ if grep -E '^nm_test_func ' "$ac_nlist" >/dev/null; then + : + else + echo "configure: cannot find nm_test_func in $ac_nlist" >&AS_MESSAGE_LOG_FD +--- libgcrypt-1.10.3.orig/src/libgcrypt-config.in ++++ libgcrypt-1.10.3/src/libgcrypt-config.in +@@ -154,7 +154,7 @@ if test "$echo_cflags" = "yes"; then + + tmp="" + for i in $includes $cflags_final; do +- if echo "$tmp" | fgrep -v -- "$i" >/dev/null; then ++ if echo "$tmp" | @GREP@ -F -v -- "$i" >/dev/null; then + tmp="$tmp $i" + fi + done +@@ -175,7 +175,7 @@ if test "$echo_libs" = "yes"; then + + tmp="" + for i in $libdirs $libs_final; do +- if echo "$tmp" | fgrep -v -- "$i" >/dev/null; then ++ if echo "$tmp" | @GREP@ -F -v -- "$i" >/dev/null; then + tmp="$tmp $i" + fi + done diff --git a/libgcrypt-nobetasuffix.patch b/libgcrypt-nobetasuffix.patch new file mode 100644 index 0000000..3d4593a --- /dev/null +++ b/libgcrypt-nobetasuffix.patch @@ -0,0 +1,24 @@ +Index: libgcrypt-1.10.2/autogen.sh +=================================================================== +--- libgcrypt-1.10.2.orig/autogen.sh ++++ libgcrypt-1.10.2/autogen.sh +@@ -249,7 +249,7 @@ if [ "$myhost" = "find-version" ]; then + fi + + beta=no +- if [ -e .git ]; then ++ if false; then + ingit=yes + tmp=$(git describe --match "${matchstr1}" --long 2>/dev/null) + tmp=$(echo "$tmp" | sed s/^"$package"//) +@@ -265,8 +265,8 @@ if [ "$myhost" = "find-version" ]; then + rvd=$((0x$(echo ${rev} | dd bs=1 count=4 2>/dev/null))) + else + ingit=no +- beta=yes +- tmp="-unknown" ++ beta=no ++ tmp="" + rev="0000000" + rvd="0" + fi diff --git a/libgcrypt-ppc-enable-P10-assembly-with-ENABLE_FORCE_SOF.patch b/libgcrypt-ppc-enable-P10-assembly-with-ENABLE_FORCE_SOF.patch new file mode 100644 index 0000000..8ef3197 --- /dev/null +++ b/libgcrypt-ppc-enable-P10-assembly-with-ENABLE_FORCE_SOF.patch @@ -0,0 +1,76 @@ +commit 2c5e5ab6843d747c4b877d2c6f47226f61e9ff14 +Author: Jussi Kivilinna +Date: Sun Jun 12 21:51:34 2022 +0300 + + ppc enable P10 assembly with ENABLE_FORCE_SOFT_HWFEATURES on arch 3.00 + + * cipher/chacha20.c (chacha20_do_setkey) [USE_PPC_VEC]: Enable + P10 assembly for HWF_PPC_ARCH_3_00 if ENABLE_FORCE_SOFT_HWFEATURES is + defined. + * cipher/poly1305.c (poly1305_init) [POLY1305_USE_PPC_VEC]: Likewise. + * cipher/rijndael.c (do_setkey) [USE_PPC_CRYPTO_WITH_PPC9LE]: Likewise. + --- + + This change allows testing P10 implementations with P9 and with QEMU-PPC. + + GnuPG-bug-id: 6006 + Signed-off-by: Jussi Kivilinna + +Index: libgcrypt-1.10.2/cipher/chacha20.c +=================================================================== +--- libgcrypt-1.10.2.orig/cipher/chacha20.c ++++ libgcrypt-1.10.2/cipher/chacha20.c +@@ -484,6 +484,11 @@ chacha20_do_setkey (CHACHA20_context_t * + ctx->use_ppc = (features & HWF_PPC_ARCH_2_07) != 0; + # ifndef WORDS_BIGENDIAN + ctx->use_p10 = (features & HWF_PPC_ARCH_3_10) != 0; ++# ifdef ENABLE_FORCE_SOFT_HWFEATURES ++ /* HWF_PPC_ARCH_3_10 above is used as soft HW-feature indicator for P10. ++ * Actual implementation works with HWF_PPC_ARCH_3_00 also. */ ++ ctx->use_p10 |= (features & HWF_PPC_ARCH_3_00) != 0; ++# endif + # endif + #endif + #ifdef USE_S390X_VX +Index: libgcrypt-1.10.2/cipher/poly1305.c +=================================================================== +--- libgcrypt-1.10.2.orig/cipher/poly1305.c ++++ libgcrypt-1.10.2/cipher/poly1305.c +@@ -90,11 +90,19 @@ static void poly1305_init (poly1305_cont + const byte key[POLY1305_KEYLEN]) + { + POLY1305_STATE *st = &ctx->state; ++ unsigned int features = _gcry_get_hw_features (); + + #ifdef POLY1305_USE_PPC_VEC +- ctx->use_p10 = (_gcry_get_hw_features () & HWF_PPC_ARCH_3_10) != 0; ++ ctx->use_p10 = (features & HWF_PPC_ARCH_3_10) != 0; ++# ifdef ENABLE_FORCE_SOFT_HWFEATURES ++ /* HWF_PPC_ARCH_3_10 above is used as soft HW-feature indicator for P10. ++ * Actual implementation works with HWF_PPC_ARCH_3_00 also. */ ++ ctx->use_p10 |= (features & HWF_PPC_ARCH_3_00) != 0; ++# endif + #endif + ++ (void)features; ++ + ctx->leftover = 0; + + st->h[0] = 0; +Index: libgcrypt-1.10.2/cipher/rijndael.c +=================================================================== +--- libgcrypt-1.10.2.orig/cipher/rijndael.c ++++ libgcrypt-1.10.2/cipher/rijndael.c +@@ -605,6 +605,12 @@ do_setkey (RIJNDAEL_context *ctx, const + bulk_ops->xts_crypt = _gcry_aes_ppc9le_xts_crypt; + if (hwfeatures & HWF_PPC_ARCH_3_10) /* for P10 */ + bulk_ops->gcm_crypt = _gcry_aes_p10le_gcm_crypt; ++# ifdef ENABLE_FORCE_SOFT_HWFEATURES ++ /* HWF_PPC_ARCH_3_10 above is used as soft HW-feature indicator for P10. ++ * Actual implementation works with HWF_PPC_ARCH_3_00 also. */ ++ if (hwfeatures & HWF_PPC_ARCH_3_00) ++ bulk_ops->gcm_crypt = _gcry_aes_p10le_gcm_crypt; ++# endif + } + #endif + #ifdef USE_PPC_CRYPTO diff --git a/libgcrypt-rol64-redefinition.patch b/libgcrypt-rol64-redefinition.patch new file mode 100644 index 0000000..bb76b2f --- /dev/null +++ b/libgcrypt-rol64-redefinition.patch @@ -0,0 +1,16 @@ +Index: libgcrypt-1.11.0/cipher/bithelp.h +=================================================================== +--- libgcrypt-1.11.0.orig/cipher/bithelp.h ++++ libgcrypt-1.11.0/cipher/bithelp.h +@@ -35,11 +35,6 @@ static inline u32 ror(u32 x, int n) + return ( (x >> (n&(32-1))) | (x << ((32-n)&(32-1))) ); + } + +-static inline u64 rol64(u64 x, int n) +-{ +- return ( (x << (n&(64-1))) | (x >> ((64-n)&(64-1))) ); +-} +- + /* Byte swap for 32-bit and 64-bit integers. If available, use compiler + provided helpers. */ + #ifdef HAVE_BUILTIN_BSWAP32 diff --git a/libgcrypt-tests-Add-more-tests-to-tests-t-fips-service-ind.patch b/libgcrypt-tests-Add-more-tests-to-tests-t-fips-service-ind.patch new file mode 100644 index 0000000..c0058d2 --- /dev/null +++ b/libgcrypt-tests-Add-more-tests-to-tests-t-fips-service-ind.patch @@ -0,0 +1,382 @@ +From d71c88f78a4f1b72f92de90791fc6fe81a3cb861 Mon Sep 17 00:00:00 2001 +From: NIIBE Yutaka +Date: Tue, 24 Dec 2024 17:03:48 +0900 +Subject: [PATCH 17/19] tests: Add more tests to tests/t-fips-service-ind. +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* tests/t-fips-service-ind.c (check_pk_g_t_n_c, check_pk_s_v): New. +(main): Call check_pk_g_t_n_c and check_pk_s_v. + +-- + +GnuPG-bug-id: 7338 +Signed-off-by: NIIBE Yutaka +Signed-off-by: Lucas Mülling +--- + tests/t-fips-service-ind.c | 334 +++++++++++++++++++++++++++++++++++++ + 1 file changed, 334 insertions(+) + +diff --git a/tests/t-fips-service-ind.c b/tests/t-fips-service-ind.c +index 64e1e135..90d92c70 100644 +--- a/tests/t-fips-service-ind.c ++++ b/tests/t-fips-service-ind.c +@@ -40,6 +40,336 @@ static int in_fips_mode; + # include + #endif + ++/* Check gcry_pk_genkey, gcry_pk_testkey, gcry_pk_get_nbits, gcry_pk_get_curve API. */ ++static void ++check_pk_g_t_n_c (int reject) ++{ ++ static struct { ++ const char *keyparms; ++ int expect_failure; ++ } tv[] = { ++ { ++ "(genkey (ecc (curve nistp256)))", ++ 0 ++ }, ++ { /* non-compliant curve */ ++ "(genkey (ecc (curve secp256k1)))", ++ 1 ++ } ++ }; ++ int tvidx; ++ gpg_error_t err; ++ gpg_err_code_t ec; ++ ++ for (tvidx=0; tvidx < DIM(tv); tvidx++) ++ { ++ gcry_sexp_t s_kp = NULL; ++ gcry_sexp_t s_sk = NULL; ++ int nbits; ++ const char *name; ++ ++ if (verbose) ++ info ("checking gcry_pk_{genkey,testkey,get_nbits,get_curve} test %d\n", tvidx); ++ ++ err = gcry_sexp_build (&s_kp, NULL, tv[tvidx].keyparms); ++ if (err) ++ { ++ fail ("error building SEXP for test, %s: %s", ++ "keyparms", gpg_strerror (err)); ++ goto next; ++ } ++ ++ err = gcry_pk_genkey (&s_sk, s_kp); ++ if (err) ++ { ++ if (in_fips_mode && reject && tv[tvidx].expect_failure) ++ /* Here, an error is expected */ ++ ; ++ else ++ fail ("gcry_pk_genkey failed: %s", gpg_strerror (err)); ++ goto next; ++ } ++ else ++ { ++ if (in_fips_mode && reject && tv[tvidx].expect_failure) ++ { ++ fail ("gcry_pk_genkey test %d unexpectedly succeeded", tvidx); ++ goto next; ++ } ++ } ++ ++ ec = gcry_get_fips_service_indicator (); ++ if (ec == GPG_ERR_INV_OP) ++ { ++ /* libgcrypt is old, no support of the FIPS service indicator. */ ++ fail ("gcry_pk_genkey test %d unexpectedly failed to check the FIPS service indicator.\n", ++ tvidx); ++ goto next; ++ } ++ ++ if (in_fips_mode && !tv[tvidx].expect_failure && ec) ++ { ++ /* Success with the FIPS service indicator == 0 expected, but != 0. */ ++ fail ("gcry_pk_genkey test %d unexpectedly set the indicator in FIPS mode.\n", ++ tvidx); ++ goto next; ++ } ++ else if (in_fips_mode && tv[tvidx].expect_failure && !ec) ++ { ++ /* Success with the FIPS service indicator != 0 expected, but == 0. */ ++ fail ("gcry_pk_genkey test %d unexpectedly cleared the indicator in FIPS mode.\n", ++ tvidx); ++ goto next; ++ } ++ ++ err = gcry_pk_testkey (s_sk); ++ if (err) ++ { ++ fail ("gcry_pk_testkey failed for test: %s", gpg_strerror (err)); ++ goto next; ++ } ++ ++ ec = gcry_get_fips_service_indicator (); ++ if (ec == GPG_ERR_INV_OP) ++ { ++ /* libgcrypt is old, no support of the FIPS service indicator. */ ++ fail ("gcry_pk_testkey test %d unexpectedly failed to check the FIPS service indicator.\n", ++ tvidx); ++ goto next; ++ } ++ ++ if (in_fips_mode && !tv[tvidx].expect_failure && ec) ++ { ++ /* Success with the FIPS service indicator == 0 expected, but != 0. */ ++ fail ("gcry_pk_testkey test %d unexpectedly set the indicator in FIPS mode.\n", ++ tvidx); ++ goto next; ++ } ++ else if (in_fips_mode && tv[tvidx].expect_failure && !ec) ++ { ++ /* Success with the FIPS service indicator != 0 expected, but == 0. */ ++ fail ("gcry_pk_testkey test %d unexpectedly cleared the indicator in FIPS mode.\n", ++ tvidx); ++ goto next; ++ } ++ ++ nbits = gcry_pk_get_nbits (s_sk); ++ if (!nbits) ++ { ++ fail ("gcry_pk_get_nbits failed for test"); ++ goto next; ++ } ++ ++ ec = gcry_get_fips_service_indicator (); ++ if (ec == GPG_ERR_INV_OP) ++ { ++ /* libgcrypt is old, no support of the FIPS service indicator. */ ++ fail ("gcry_pk_get_nbits test %d unexpectedly failed to check the FIPS service indicator.\n", ++ tvidx); ++ goto next; ++ } ++ ++ if (in_fips_mode && !tv[tvidx].expect_failure && ec) ++ { ++ /* Success with the FIPS service indicator == 0 expected, but != 0. */ ++ fail ("gcry_pk_get_nbits test %d unexpectedly set the indicator in FIPS mode.\n", ++ tvidx); ++ goto next; ++ } ++ else if (in_fips_mode && tv[tvidx].expect_failure && !ec) ++ { ++ /* Success with the FIPS service indicator != 0 expected, but == 0. */ ++ fail ("gcry_pk_get_nbits test %d unexpectedly cleared the indicator in FIPS mode.\n", ++ tvidx); ++ goto next; ++ } ++ ++ name = gcry_pk_get_curve (s_sk, 0, NULL); ++ if (!name) ++ { ++ fail ("gcry_pk_get_curve failed for test: %s", gpg_strerror (err)); ++ goto next; ++ } ++ ++ ec = gcry_get_fips_service_indicator (); ++ if (ec == GPG_ERR_INV_OP) ++ { ++ /* libgcrypt is old, no support of the FIPS service indicator. */ ++ fail ("gcry_pk_get_curve test %d unexpectedly failed to check the FIPS service indicator.\n", ++ tvidx); ++ goto next; ++ } ++ ++ if (in_fips_mode && !tv[tvidx].expect_failure && ec) ++ { ++ /* Success with the FIPS service indicator == 0 expected, but != 0. */ ++ fail ("gcry_pk_get_curve test %d unexpectedly set the indicator in FIPS mode.\n", ++ tvidx); ++ goto next; ++ } ++ else if (in_fips_mode && tv[tvidx].expect_failure && !ec) ++ { ++ /* Success with the FIPS service indicator != 0 expected, but == 0. */ ++ fail ("gcry_pk_get_curve test %d unexpectedly cleared the indicator in FIPS mode.\n", ++ tvidx); ++ goto next; ++ } ++ ++ next: ++ gcry_sexp_release (s_kp); ++ gcry_sexp_release (s_sk); ++ } ++} ++ ++/* Check gcry_pk_sign, gcry_verify API. */ ++static void ++check_pk_s_v (int reject) ++{ ++ static struct { ++ const char *prvkey; ++ const char *pubkey; ++ int expect_failure; ++ } tv[] = { ++ { ++ "(private-key (ecc (curve nistp256)" ++ " (d #519b423d715f8b581f4fa8ee59f4771a5b44c8130b4e3eacca54a56dda72b464#)))", ++ "(public-key (ecc (curve nistp256)" ++ " (q #041ccbe91c075fc7f4f033bfa248db8fccd3565de94bbfb12f3c59ff46c271bf83" ++ "ce4014c68811f9a21a1fdb2c0e6113e06db7ca93b7404e78dc7ccd5ca89a4ca9#)))", ++ 0 ++ }, ++ { /* non-compliant curve */ ++ "(private-key (ecc (curve secp256k1)" ++ " (d #c2cdf0a8b0a83b35ace53f097b5e6e6a0a1f2d40535eff1cf434f52a43d59d8f#)))", ++ "(public-key (ecc (curve secp256k1)" ++ " (q #046fcc37ea5e9e09fec6c83e5fbd7a745e3eee81d16ebd861c9e66f55518c19798" ++ "4e9f113c07f875691df8afc1029496fc4cb9509b39dcd38f251a83359cc8b4f7#)))", ++ 1 ++ } ++ }; ++ int tvidx; ++ gpg_error_t err; ++ gpg_err_code_t ec; ++ const char *data = "(data (flags raw)" ++ "(hash sha256 #00112233445566778899AABBCCDDEEFF000102030405060708090A0B0C0D0E0F#))"; ++ gcry_sexp_t s_data = NULL; ++ ++ err = gcry_sexp_build (&s_data, NULL, data); ++ if (err) ++ { ++ fail ("error building SEXP for test, %s: %s", ++ "data", gpg_strerror (err)); ++ return; ++ } ++ ++ for (tvidx=0; tvidx < DIM(tv); tvidx++) ++ { ++ gcry_sexp_t s_pk = NULL; ++ gcry_sexp_t s_sk = NULL; ++ gcry_sexp_t s_sig= NULL; ++ ++ if (verbose) ++ info ("checking gcry_pk_{sign,verify} test %d\n", tvidx); ++ ++ err = gcry_sexp_build (&s_sk, NULL, tv[tvidx].prvkey); ++ if (err) ++ { ++ fail ("error building SEXP for test, %s: %s", ++ "sk", gpg_strerror (err)); ++ goto next; ++ } ++ ++ err = gcry_sexp_build (&s_pk, NULL, tv[tvidx].pubkey); ++ if (err) ++ { ++ fail ("error building SEXP for test, %s: %s", ++ "pk", gpg_strerror (err)); ++ goto next; ++ } ++ ++ err = gcry_pk_sign (&s_sig, s_data, s_sk); ++ if (err) ++ { ++ if (in_fips_mode && reject && tv[tvidx].expect_failure) ++ /* Here, an error is expected */ ++ ; ++ else ++ fail ("gcry_pk_sign failed: %s", gpg_strerror (err)); ++ goto next; ++ } ++ else ++ { ++ if (in_fips_mode && reject && tv[tvidx].expect_failure) ++ { ++ fail ("gcry_pk_sign test %d unexpectedly succeeded", tvidx); ++ goto next; ++ } ++ } ++ ++ ec = gcry_get_fips_service_indicator (); ++ if (ec == GPG_ERR_INV_OP) ++ { ++ /* libgcrypt is old, no support of the FIPS service indicator. */ ++ fail ("gcry_pk_sign test %d unexpectedly failed to check the FIPS service indicator.\n", ++ tvidx); ++ goto next; ++ } ++ ++ if (in_fips_mode && !tv[tvidx].expect_failure && ec) ++ { ++ /* Success with the FIPS service indicator == 0 expected, but != 0. */ ++ fail ("gcry_pk_sign test %d unexpectedly set the indicator in FIPS mode.\n", ++ tvidx); ++ goto next; ++ } ++ else if (in_fips_mode && tv[tvidx].expect_failure && !ec) ++ { ++ /* Success with the FIPS service indicator != 0 expected, but == 0. */ ++ fail ("gcry_pk_sign test %d unexpectedly cleared the indicator in FIPS mode.\n", ++ tvidx); ++ goto next; ++ } ++ ++ err = gcry_pk_verify (s_sig, s_data, s_pk); ++ if (err) ++ { ++ fail ("gcry_pk_verify failed for test: %s", gpg_strerror (err)); ++ goto next; ++ } ++ ++ ec = gcry_get_fips_service_indicator (); ++ if (ec == GPG_ERR_INV_OP) ++ { ++ /* libgcrypt is old, no support of the FIPS service indicator. */ ++ fail ("gcry_pk_verify test %d unexpectedly failed to check the FIPS service indicator.\n", ++ tvidx); ++ goto next; ++ } ++ ++ if (in_fips_mode && !tv[tvidx].expect_failure && ec) ++ { ++ /* Success with the FIPS service indicator == 0 expected, but != 0. */ ++ fail ("gcry_pk_verify test %d unexpectedly set the indicator in FIPS mode.\n", ++ tvidx); ++ goto next; ++ } ++ else if (in_fips_mode && tv[tvidx].expect_failure && !ec) ++ { ++ /* Success with the FIPS service indicator != 0 expected, but == 0. */ ++ fail ("gcry_pk_verify test %d unexpectedly cleared the indicator in FIPS mode.\n", ++ tvidx); ++ goto next; ++ } ++ ++ next: ++ gcry_sexp_release (s_sig); ++ gcry_sexp_release (s_pk); ++ gcry_sexp_release (s_sk); ++ } ++ ++ gcry_sexp_release (s_data); ++} ++ + /* Check gcry_pk_hash_sign, gcry_pk_hash_verify API. */ + static void + check_pk_hash_sign_verify (void) +@@ -1126,6 +1456,8 @@ main (int argc, char **argv) + check_mac_o_w_r_c (0); + check_cipher_o_s_e_d_c (0); + check_pk_hash_sign_verify (); ++ check_pk_s_v (0); ++ check_pk_g_t_n_c (0); + + xgcry_control ((GCRYCTL_FIPS_REJECT_NON_FIPS, + (GCRY_FIPS_FLAG_REJECT_MD_MD5 +@@ -1134,6 +1466,8 @@ main (int argc, char **argv) + check_md_o_w_r_c (1); + check_mac_o_w_r_c (1); + check_cipher_o_s_e_d_c (1); ++ check_pk_s_v (1); ++ check_pk_g_t_n_c (1); + + return !!error_count; + } +-- +2.49.0 + diff --git a/libgcrypt-tests-Allow-tests-with-USE_RSA.patch b/libgcrypt-tests-Allow-tests-with-USE_RSA.patch new file mode 100644 index 0000000..cc29fb0 --- /dev/null +++ b/libgcrypt-tests-Allow-tests-with-USE_RSA.patch @@ -0,0 +1,44 @@ +From 8404a048b7c58eb903717e09cffaa7735f7d8520 Mon Sep 17 00:00:00 2001 +From: NIIBE Yutaka +Date: Tue, 4 Mar 2025 13:29:28 +0900 +Subject: [PATCH 01/14] tests: Allow tests with !USE_RSA. +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* tests/t-fips-service-ind.c [USE_RSA] (check_pk_s_v): Ifdef-out. + +-- + +Signed-off-by: NIIBE Yutaka +Signed-off-by: Lucas Mülling +--- + tests/t-fips-service-ind.c | 5 ++++- + 1 file changed, 4 insertions(+), 1 deletion(-) + +diff --git a/tests/t-fips-service-ind.c b/tests/t-fips-service-ind.c +index 99b84c8f..a082b258 100644 +--- a/tests/t-fips-service-ind.c ++++ b/tests/t-fips-service-ind.c +@@ -290,7 +290,9 @@ check_pk_s_v (int reject) + " 00112233445566778899AABBCCDDEEFF000102030405060708090A0B0C0D0E0F" + " 00112233445566778899AABBCCDDEEFF000102030405060708090A0B0C0D0E0F#))", + 0 +- }, ++ } ++#if USE_RSA ++ , + { /* RSA with compliant hash for signing */ + "(private-key" + " (rsa" +@@ -559,6 +561,7 @@ check_pk_s_v (int reject) + " (hash sha1 #11223344556677889900AABBCCDDEEFF10203040#))\n", + 1 + } ++#endif /* USE_RSA */ + }; + int tvidx; + gpg_error_t err; +-- +2.49.0 + diff --git a/libgcrypt-tests-Update-t-fips-service-ind-using-GCRY_MD_SHA256-for-KDF-tests.patch b/libgcrypt-tests-Update-t-fips-service-ind-using-GCRY_MD_SHA256-for-KDF-tests.patch new file mode 100644 index 0000000..dd009fd --- /dev/null +++ b/libgcrypt-tests-Update-t-fips-service-ind-using-GCRY_MD_SHA256-for-KDF-tests.patch @@ -0,0 +1,106 @@ +From e5989e08a556117ec3f19f098765963358b71051 Mon Sep 17 00:00:00 2001 +From: NIIBE Yutaka +Date: Wed, 26 Feb 2025 13:51:36 +0900 +Subject: [PATCH 3/4] tests: Update t-fips-service-ind using GCRY_MD_SHA256 for + KDF tests. +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* tests/t-fips-service-ind.c (check_kdf_derive): Use GCRY_MD_SHA256. + +-- + +GnuPG-bug-id: 7338 +Signed-off-by: NIIBE Yutaka +Signed-off-by: Lucas Mülling +--- + tests/t-fips-service-ind.c | 38 +++++++++++++++++++------------------- + 1 file changed, 19 insertions(+), 19 deletions(-) + +diff --git a/tests/t-fips-service-ind.c b/tests/t-fips-service-ind.c +index bec6c27e..99b84c8f 100644 +--- a/tests/t-fips-service-ind.c ++++ b/tests/t-fips-service-ind.c +@@ -1621,13 +1621,13 @@ check_kdf_derive (void) + } tv[] = { + { + "passwordPASSWORDpassword", 24, +- GCRY_KDF_PBKDF2, GCRY_MD_SHA1, ++ GCRY_KDF_PBKDF2, GCRY_MD_SHA256, + "saltSALTsaltSALTsaltSALTsaltSALTsalt", 36, + 4096, + 25, +- "\x3d\x2e\xec\x4f\xe4\x1c\x84\x9b\x80\xc8" +- "\xd8\x36\x62\xc0\xe4\x4a\x8b\x29\x1a\x96" +- "\x4c\xf2\xf0\x70\x38", ++ "\x34\x8c\x89\xdb\xcb\xd3\x2b\x2f\x32\xd8" ++ "\x14\xb8\x11\x6e\x84\xcf\x2b\x17\x34\x7e" ++ "\xbc\x18\x00\x18\x1c", + 0 + }, + { +@@ -1644,45 +1644,45 @@ check_kdf_derive (void) + }, + { + "passwor", 7, +- GCRY_KDF_PBKDF2, GCRY_MD_SHA1, ++ GCRY_KDF_PBKDF2, GCRY_MD_SHA256, + "saltSALTsaltSALTsaltSALTsaltSALTsalt", 36, + 4096, + 25, +- "\xf4\x93\xee\x2b\xbf\x44\x0b\x9e\x64\x53" +- "\xc2\xb3\x87\xdc\x73\xf8\xfd\xe6\x97\xda" +- "\xb8\x24\xa0\x26\x50", ++ "\x2d\x72\xa9\xe5\x4e\x2f\x37\x6e\xe5\xe4" ++ "\xf5\x55\x76\xb5\xaa\x49\x73\x01\x97\x1c" ++ "\xad\x3a\x7c\xc4\xde", + 1 /* not-compliant because passphrase len is too small */ + }, + { + "passwordPASSWORDpassword", 24, +- GCRY_KDF_PBKDF2, GCRY_MD_SHA1, ++ GCRY_KDF_PBKDF2, GCRY_MD_SHA256, + "saltSALTsaltSAL", 15, + 4096, + 25, +- "\x14\x05\xa4\x2a\xf4\xa8\x12\x14\x7b\x65" +- "\x8f\xaa\xf0\x7f\x25\xe5\x0f\x0b\x2b\xb7" +- "\xcf\x8d\x29\x23\x4b", ++ "\xf7\x55\xdd\x3c\x5e\xfb\x23\x06\xa7\x85" ++ "\x94\xa7\x31\x12\x45\xcf\x5a\x4b\xdc\x09" ++ "\xee\x65\x4b\x50\x3f", + 1 /* not-compliant because salt len is too small */ + }, + { + "passwordPASSWORDpassword", 24, +- GCRY_KDF_PBKDF2, GCRY_MD_SHA1, ++ GCRY_KDF_PBKDF2, GCRY_MD_SHA256, + "saltSALTsaltSALTsaltSALTsaltSALTsalt", 36, + 999, + 25, +- "\xac\xf8\xb4\x67\x41\xc7\xf3\xd1\xa0\xc0" +- "\x08\xbe\x9b\x23\x96\x78\xbd\x93\xda\x4a" +- "\x30\xd4\xfb\xf0\x33", ++ "\x09\x3e\x1a\xd8\x63\x30\x71\x9c\x17\xcf" ++ "\xb0\x53\x3e\x1f\xc8\x51\x29\x71\x54\x28" ++ "\x5d\xf7\x8e\x41\xaa", + 1 /* not-compliant because too few iterations */ + }, + { + "passwordPASSWORDpassword", 24, +- GCRY_KDF_PBKDF2, GCRY_MD_SHA1, ++ GCRY_KDF_PBKDF2, GCRY_MD_SHA256, + "saltSALTsaltSALTsaltSALTsaltSALTsalt", 36, + 4096, + 13, +- "\x3d\x2e\xec\x4f\xe4\x1c\x84\x9b\x80\xc8" +- "\xd8\x36\x62", ++ "\x34\x8c\x89\xdb\xcb\xd3\x2b\x2f\x32\xd8" ++ "\x14\xb8\x11", + 1 /* not-compliant because key size too small */ + }, + { +-- +2.49.0 + diff --git a/libgcrypt-tests-fips-Add-gcry_cipher_open-tests.patch b/libgcrypt-tests-fips-Add-gcry_cipher_open-tests.patch new file mode 100644 index 0000000..0e0f7e5 --- /dev/null +++ b/libgcrypt-tests-fips-Add-gcry_cipher_open-tests.patch @@ -0,0 +1,199 @@ +From cfd2d2f41ad4aef40d83f8f7237d1da13c7e240c Mon Sep 17 00:00:00 2001 +From: NIIBE Yutaka +Date: Tue, 17 Dec 2024 10:33:33 +0900 +Subject: [PATCH 09/19] tests,fips: Add gcry_cipher_open tests. +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* tests/t-fips-service-ind.c (check_cipher_o_s_e_d_c): New. +(main): Call check_cipher_o_s_e_d_c. + +-- + +GnuPG-bug-id: 7338 +Signed-off-by: NIIBE Yutaka +Signed-off-by: Lucas Mülling +--- + tests/t-fips-service-ind.c | 152 ++++++++++++++++++++++++++++++++++++- + 1 file changed, 151 insertions(+), 1 deletion(-) + +Index: libgcrypt-1.11.0/tests/t-fips-service-ind.c +=================================================================== +--- libgcrypt-1.11.0.orig/tests/t-fips-service-ind.c ++++ libgcrypt-1.11.0/tests/t-fips-service-ind.c +@@ -31,6 +31,7 @@ + + #include "t-common.h" + static int in_fips_mode; ++#define MAX_DATA_LEN 1040 + + /* Mingw requires us to include windows.h after winsock2.h which is + included by gcrypt.h. */ +@@ -38,6 +39,154 @@ static int in_fips_mode; + # include + #endif + ++/* Check gcry_cipher_open, gcry_cipher_setkey, gcry_cipher_encrypt, ++ gcry_cipher_decrypt, gcry_cipher_close API. */ ++static void ++check_cipher_o_s_e_d_c (void) ++{ ++ static struct { ++ int algo; ++ const char *key; ++ int keylen; ++ const char *expect; ++ int expect_failure; ++ unsigned int flags; ++ } tv[] = { ++#if USE_DES ++ { GCRY_CIPHER_3DES, ++ "\xe3\x34\x7a\x6b\x0b\xc1\x15\x2c\x64\x2a\x25\xcb\xd3\xbc\x31\xab" ++ "\xfb\xa1\x62\xa8\x1f\x19\x7c\x15", 24, ++ "\x3f\x1a\xb8\x83\x18\x8b\xb5\x97", 1 }, ++ { GCRY_CIPHER_3DES, ++ "\xe3\x34\x7a\x6b\x0b\xc1\x15\x2c\x64\x2a\x25\xcb\xd3\xbc\x31\xab" ++ "\xfb\xa1\x62\xa8\x1f\x19\x7c\x15", 24, ++ "\x3f\x1a\xb8\x83\x18\x8b\xb5\x97", ++ 1, GCRY_CIPHER_FLAG_REJECT_NON_FIPS }, ++#endif ++ { GCRY_CIPHER_AES, ++ "\x2b\x7e\x15\x16\x28\xae\xd2\xa6\xab\xf7\x15\x88\x09\xcf\x4f\x3c", 16, ++ "\x5c\x71\xd8\x5d\x26\x5e\xcd\xb5\x95\x40\x41\xab\xff\x25\x6f\xd1" } ++ }; ++ const char *pt = "Shohei Ohtani 2024: 54 HR, 59 SB"; ++ int ptlen; ++ int tvidx; ++ unsigned char out[MAX_DATA_LEN]; ++ gpg_error_t err; ++ ++ ptlen = strlen (pt); ++ assert (ptlen == 32); ++ for (tvidx=0; tvidx < DIM(tv); tvidx++) ++ { ++ gpg_err_code_t ec; ++ gcry_cipher_hd_t h; ++ size_t blklen; ++ ++ if (verbose) ++ fprintf (stderr, "checking gcry_cipher_open test %d\n", ++ tvidx); ++ ++ blklen = gcry_cipher_get_algo_blklen (tv[tvidx].algo); ++ assert (blklen != 0); ++ assert (blklen <= ptlen); ++ assert (blklen <= DIM (out)); ++ err = gcry_cipher_open (&h, tv[tvidx].algo, GCRY_CIPHER_MODE_ECB, ++ tv[tvidx].flags); ++ if (err) ++ { ++ if (in_fips_mode && (tv[tvidx].flags & GCRY_CIPHER_FLAG_REJECT_NON_FIPS) ++ && tv[tvidx].expect_failure) ++ /* Here, an error is expected */ ++ ; ++ else ++ fail ("gcry_cipher_open test %d unexpectedly failed: %s\n", ++ tvidx, gpg_strerror (err)); ++ continue; ++ } ++ else ++ { ++ if (in_fips_mode && (tv[tvidx].flags & GCRY_CIPHER_FLAG_REJECT_NON_FIPS) ++ && tv[tvidx].expect_failure) ++ /* This case, an error is expected, but we observed success */ ++ fail ("gcry_cipher_open test %d unexpectedly succeeded\n", tvidx); ++ } ++ ++ ec = gcry_get_fips_service_indicator (); ++ if (ec == GPG_ERR_INV_OP) ++ { ++ /* libgcrypt is old, no support of the FIPS service indicator. */ ++ fail ("gcry_cipher_open test %d unexpectedly failed to check the FIPS service indicator.\n", ++ tvidx); ++ continue; ++ } ++ ++ if (in_fips_mode && !tv[tvidx].expect_failure && ec) ++ { ++ /* Success with the FIPS service indicator == 0 expected, but != 0. */ ++ fail ("gcry_cipher_open test %d unexpectedly set the indicator in FIPS mode.\n", ++ tvidx); ++ continue; ++ } ++ else if (in_fips_mode && tv[tvidx].expect_failure && !ec) ++ { ++ /* Success with the FIPS service indicator != 0 expected, but == 0. */ ++ fail ("gcry_cipher_open test %d unexpectedly cleared the indicator in FIPS mode.\n", ++ tvidx); ++ continue; ++ } ++ ++ err = gcry_cipher_setkey (h, tv[tvidx].key, tv[tvidx].keylen); ++ if (err) ++ { ++ fail ("gcry_cipher_setkey %d failed: %s\n", tvidx, ++ gpg_strerror (err)); ++ gcry_cipher_close (h); ++ continue; ++ } ++ ++ err = gcry_cipher_encrypt (h, out, MAX_DATA_LEN, pt, blklen); ++ if (err) ++ { ++ fail ("gcry_cipher_encrypt %d failed: %s\n", tvidx, ++ gpg_strerror (err)); ++ gcry_cipher_close (h); ++ continue; ++ } ++ ++ if (memcmp (out, tv[tvidx].expect, blklen)) ++ { ++ int i; ++ ++ fail ("gcry_cipher_open test %d failed: encryption mismatch\n", tvidx); ++ fputs ("got:", stderr); ++ for (i=0; i < blklen; i++) ++ fprintf (stderr, " %02x", out[i]); ++ putc ('\n', stderr); ++ } ++ ++ err = gcry_cipher_decrypt (h, out, blklen, NULL, 0); ++ if (err) ++ { ++ fail ("gcry_cipher_decrypt %d failed: %s\n", tvidx, ++ gpg_strerror (err)); ++ gcry_cipher_close (h); ++ continue; ++ } ++ ++ if (memcmp (out, pt, blklen)) ++ { ++ int i; ++ ++ fail ("gcry_cipher_open test %d failed: decryption mismatch\n", tvidx); ++ fputs ("got:", stderr); ++ for (i=0; i < blklen; i++) ++ fprintf (stderr, " %02x", out[i]); ++ putc ('\n', stderr); ++ } ++ ++ gcry_cipher_close (h); ++ } ++} ++ + /* Check gcry_mac_open, gcry_mac_write, gcry_mac_write, gcry_mac_read, + gcry_mac_close API. */ + static void +@@ -651,9 +800,10 @@ main (int argc, char **argv) + xgcry_control ((GCRYCTL_SET_DEBUG_FLAGS, 1u , 0)); + + check_digests (); ++ check_kdf_derive (); + check_md_o_w_r_c (); + check_mac_o_w_r_c (); +- check_kdf_derive (); ++ check_cipher_o_s_e_d_c (); + + return !!error_count; + } diff --git a/libgcrypt-tests-fips-Add-gcry_mac_open-tests.patch b/libgcrypt-tests-fips-Add-gcry_mac_open-tests.patch new file mode 100644 index 0000000..c2e3ed4 --- /dev/null +++ b/libgcrypt-tests-fips-Add-gcry_mac_open-tests.patch @@ -0,0 +1,206 @@ +From c4f75014cb8af732f87c02fe7c2e7a488fe71c6d Mon Sep 17 00:00:00 2001 +From: NIIBE Yutaka +Date: Mon, 16 Dec 2024 14:09:10 +0900 +Subject: [PATCH 06/19] tests,fips: Add gcry_mac_open tests. +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* tests/t-digest.c (check_mac_o_w_r_c): New. +(main): Call check_mac_o_w_r_c. + +-- + +GnuPG-bug-id: 7338 +Signed-off-by: NIIBE Yutaka +Signed-off-by: Lucas Mülling +--- + tests/t-digest.c | 168 +++++++++++++++++++++++++++++++++++++++++++++++ + 1 file changed, 168 insertions(+) + +Index: libgcrypt-1.11.0/tests/t-digest.c +=================================================================== +--- libgcrypt-1.11.0.orig/tests/t-digest.c ++++ libgcrypt-1.11.0/tests/t-digest.c +@@ -38,6 +38,173 @@ static int in_fips_mode; + # include + #endif + ++/* Check gcry_mac_open, gcry_mac_write, gcry_mac_write, gcry_mac_read, ++ gcry_mac_close API. */ ++static void ++check_mac_o_w_r_c (void) ++{ ++ static struct { ++ int algo; ++ const char *data; ++ int datalen; ++ const char *key; ++ int keylen; ++ const char *expect; ++ int expect_failure; ++ unsigned int flags; ++ } tv[] = { ++#if USE_MD5 ++ { GCRY_MAC_HMAC_MD5, "hmac input abc", 14, "hmac key input", 14, ++ "\x0d\x72\xd0\x60\xaf\x34\xf2\xca\x33\x58\xa9\xcc\xd3\x5a\xac\xb5", 1 }, ++ { GCRY_MAC_HMAC_MD5, "hmac input abc", 14, "hmac key input", 14, ++ "\x0d\x72\xd0\x60\xaf\x34\xf2\xca\x33\x58\xa9\xcc\xd3\x5a\xac\xb5", 1, ++ GCRY_MAC_FLAG_REJECT_NON_FIPS }, ++#endif ++#if USE_SHA1 ++ { GCRY_MAC_HMAC_SHA1, "hmac input abc", 14, "hmac key input", 14, ++ "\xc9\x62\x9d\x16\x0f\xc2\xc4\xcd\x38\xac\x3a\x00\xdc\x29\x61\x03" ++ "\x69\x50\xd7\x3a" }, ++#endif ++ { GCRY_MAC_HMAC_SHA256, "hmac input abc", 14, "hmac key input", 14, ++ "\x6a\xda\x4d\xd5\xf3\xa7\x32\x9d\xd2\x55\xc0\x7f\xe6\x0a\x93\xb8" ++ "\x7a\x6e\x76\x68\x46\x34\x67\xf9\xc2\x29\xb8\x24\x2e\xc8\xe3\xb4" }, ++ { GCRY_MAC_HMAC_SHA384, "hmac input abc", 14, "hmac key input", 14, ++ "\xc6\x59\x14\x4a\xac\x4d\xd5\x62\x09\x2c\xbd\x5e\xbf\x41\x94\xf9" ++ "\xa4\x78\x18\x46\xfa\xd6\xd1\x12\x90\x4f\x65\xd4\xe8\x44\xcc\xcc" ++ "\x3d\xcc\xf3\xe4\x27\xd8\xf0\xff\x01\xe8\x70\xcd\xfb\xfa\x24\x45" }, ++ { GCRY_MAC_HMAC_SHA512, "hmac input abc", 14, "hmac key input", 14, ++ "\xfa\x77\x49\x49\x24\x3d\x7e\x03\x1b\x0e\xd1\xfc\x20\x81\xcf\x95" ++ "\x81\x21\xa4\x4f\x3b\xe5\x69\x9a\xe6\x67\x27\x10\xbc\x62\xc7\xb3" ++ "\xb3\xcf\x2b\x1e\xda\x20\x48\x25\xc5\x6a\x52\xc7\xc9\xd9\x77\xf6" ++ "\xf6\x49\x9d\x70\xe6\x04\x33\xab\x6a\xdf\x7e\x9f\xf4\xd1\x59\x6e" }, ++ { GCRY_MAC_HMAC_SHA3_256, "hmac input abc", 14, "hmac key input", 14, ++ "\x2b\xe9\x02\x92\xc2\x37\xbe\x91\x06\xbf\x9c\x8e\x7b\xa3\xf2\xfc" ++ "\x68\x10\x8a\x71\xd5\xc7\x84\x3c\x0b\xdd\x7d\x1e\xdf\xa5\xf6\xa7" }, ++ { GCRY_MAC_HMAC_SHA3_384, "hmac input abc", 14, "hmac key input", 14, ++ "\x9f\x6b\x9f\x49\x95\x57\xed\x33\xb1\xe7\x22\x2f\xda\x40\x68\xb0" ++ "\x28\xd2\xdb\x6f\x73\x3c\x2e\x2b\x29\x51\x64\x53\xc4\xc5\x63\x8a" ++ "\x98\xca\x78\x1a\xe7\x1b\x7d\xf6\xbf\xf3\x6a\xf3\x2a\x0e\xa0\x5b" }, ++ { GCRY_MAC_HMAC_SHA3_512, "hmac input abc", 14, "hmac key input", 14, ++ "\xf3\x19\x70\x54\x25\xdf\x0f\xde\x09\xe9\xea\x3b\x34\x67\x14\x32" ++ "\xe6\xe2\x58\x9d\x76\x38\xa4\xbd\x90\x35\x4c\x07\x7c\xa3\xdb\x23" ++ "\x3c\x78\x0c\x45\xee\x8e\x39\xd5\x81\xd8\x5c\x13\x20\x40\xba\x34" ++ "\xd0\x0b\x75\x31\x38\x4b\xe7\x74\x87\xa9\xc5\x68\x7f\xbc\x19\xa1" } ++#if USE_RMD160 ++ , ++ { GCRY_MAC_HMAC_RMD160, "hmac input abc", 14, "hmac key input", 14, ++ "\xf2\x45\x5c\x7e\x48\x1a\xbb\xe5\xe8\xec\x40\xa4\x1b\x89\x26\x2b" ++ "\xdc\xa1\x79\x59", 1 } ++#endif ++ }; ++ int tvidx; ++ unsigned char mac[64]; ++ int expectlen; ++ gpg_error_t err; ++ size_t buflen; ++ ++ for (tvidx=0; tvidx < DIM(tv); tvidx++) ++ { ++ gpg_err_code_t ec; ++ gcry_mac_hd_t h; ++ ++ if (verbose) ++ fprintf (stderr, "checking gcry_mac_open test %d\n", ++ tvidx); ++ ++ expectlen = gcry_mac_get_algo_maclen (tv[tvidx].algo); ++ assert (expectlen != 0); ++ assert (expectlen <= DIM (mac)); ++ err = gcry_mac_open (&h, tv[tvidx].algo, tv[tvidx].flags, NULL); ++ if (err) ++ { ++ if (in_fips_mode && (tv[tvidx].flags & GCRY_MAC_FLAG_REJECT_NON_FIPS) ++ && tv[tvidx].expect_failure) ++ /* Here, an error is expected */ ++ ; ++ else ++ fail ("gcry_mac_open test %d unexpectedly failed: %s\n", ++ tvidx, gpg_strerror (err)); ++ continue; ++ } ++ else ++ { ++ if (in_fips_mode && (tv[tvidx].flags & GCRY_MAC_FLAG_REJECT_NON_FIPS) ++ && tv[tvidx].expect_failure) ++ /* This case, an error is expected, but we observed success */ ++ fail ("gcry_mac_open test %d unexpectedly succeeded\n", tvidx); ++ } ++ ++ ++ ec = gcry_get_fips_service_indicator (); ++ if (ec == GPG_ERR_INV_OP) ++ { ++ /* libgcrypt is old, no support of the FIPS service indicator. */ ++ fail ("gcry_mac_open test %d unexpectedly failed to check the FIPS service indicator.\n", ++ tvidx); ++ continue; ++ } ++ ++ if (in_fips_mode && !tv[tvidx].expect_failure && ec) ++ { ++ /* Success with the FIPS service indicator == 0 expected, but != 0. */ ++ fail ("gcry_mac_open test %d unexpectedly set the indicator in FIPS mode.\n", ++ tvidx); ++ continue; ++ } ++ else if (in_fips_mode && tv[tvidx].expect_failure && !ec) ++ { ++ /* Success with the FIPS service indicator != 0 expected, but == 0. */ ++ fail ("gcry_mac_open test %d unexpectedly cleared the indicator in FIPS mode.\n", ++ tvidx); ++ continue; ++ } ++ ++ err = gcry_mac_setkey (h, tv[tvidx].key, tv[tvidx].keylen); ++ if (err) ++ { ++ fail ("gcry_mac_setkey test %d unexpectedly failed: %s\n", ++ tvidx, gpg_strerror (err)); ++ gcry_mac_close (h); ++ continue; ++ } ++ ++ err = gcry_mac_write (h, tv[tvidx].data, tv[tvidx].datalen); ++ if (err) ++ { ++ fail ("gcry_mac_write test %d unexpectedly failed: %s\n", ++ tvidx, gpg_strerror (err)); ++ gcry_mac_close (h); ++ continue; ++ } ++ ++ buflen = expectlen; ++ err = gcry_mac_read (h, mac, &buflen); ++ if (err || buflen != expectlen) ++ { ++ fail ("gcry_mac_read test %d unexpectedly failed: %s\n", ++ tvidx, gpg_strerror (err)); ++ gcry_mac_close (h); ++ continue; ++ } ++ ++ if (memcmp (mac, tv[tvidx].expect, expectlen)) ++ { ++ int i; ++ ++ fail ("gcry_mac_open test %d failed: mismatch\n", tvidx); ++ fputs ("got:", stderr); ++ for (i=0; i < expectlen; i++) ++ fprintf (stderr, " %02x", mac[i]); ++ putc ('\n', stderr); ++ } ++ ++ gcry_mac_close (h); ++ } ++} ++ ++ ++/* Check gcry_md_open, gcry_md_write, gcry_md_write, gcry_md_read, ++ gcry_md_close API. */ + static void + check_md_o_w_r_c (void) + { +@@ -327,6 +494,7 @@ main (int argc, char **argv) + + check_digests (); + check_md_o_w_r_c (); ++ check_mac_o_w_r_c (); + + return !!error_count; + } diff --git a/libgcrypt-tests-fips-Move-KDF-tests-to-t-fips-service-ind.patch b/libgcrypt-tests-fips-Move-KDF-tests-to-t-fips-service-ind.patch new file mode 100644 index 0000000..7adbac5 --- /dev/null +++ b/libgcrypt-tests-fips-Move-KDF-tests-to-t-fips-service-ind.patch @@ -0,0 +1,375 @@ +From b59bde31ded9e829e2a53ddb8c533bf35a144972 Mon Sep 17 00:00:00 2001 +From: NIIBE Yutaka +Date: Mon, 16 Dec 2024 14:21:06 +0900 +Subject: [PATCH 08/19] tests,fips: Move KDF tests to t-fips-service-ind. +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* tests/t-fips-service-ind.c (check_kdf_derive): Move from... +* tests/t-kdf.c (check_fips_gcry_kdf_derive): ... here. + +-- + +GnuPG-bug-id: 7338 +Signed-off-by: NIIBE Yutaka +Signed-off-by: Lucas Mülling +--- + tests/t-fips-service-ind.c | 159 +++++++++++++++++++++++++++++++++++++ + tests/t-kdf.c | 159 ------------------------------------- + 2 files changed, 159 insertions(+), 159 deletions(-) + +Index: libgcrypt-1.11.0/tests/t-fips-service-ind.c +=================================================================== +--- libgcrypt-1.11.0.orig/tests/t-fips-service-ind.c ++++ libgcrypt-1.11.0/tests/t-fips-service-ind.c +@@ -439,6 +439,164 @@ check_digests (void) + } + + ++ ++static void ++check_kdf_derive (void) ++{ ++ static struct { ++ const char *p; /* Passphrase. */ ++ size_t plen; /* Length of P. */ ++ int algo; ++ int subalgo; ++ const char *salt; ++ size_t saltlen; ++ unsigned long iterations; ++ int dklen; /* Requested key length. */ ++ const char *dk; /* Derived key. */ ++ int expect_failure; ++ } tv[] = { ++ { ++ "passwordPASSWORDpassword", 24, ++ GCRY_KDF_PBKDF2, GCRY_MD_SHA1, ++ "saltSALTsaltSALTsaltSALTsaltSALTsalt", 36, ++ 4096, ++ 25, ++ "\x3d\x2e\xec\x4f\xe4\x1c\x84\x9b\x80\xc8" ++ "\xd8\x36\x62\xc0\xe4\x4a\x8b\x29\x1a\x96" ++ "\x4c\xf2\xf0\x70\x38", ++ 0 ++ }, ++ { ++ "pleaseletmein", 13, ++ GCRY_KDF_SCRYPT, 16384, ++ "SodiumChloride", 14, ++ 1, ++ 64, ++ "\x70\x23\xbd\xcb\x3a\xfd\x73\x48\x46\x1c\x06\xcd\x81\xfd\x38\xeb" ++ "\xfd\xa8\xfb\xba\x90\x4f\x8e\x3e\xa9\xb5\x43\xf6\x54\x5d\xa1\xf2" ++ "\xd5\x43\x29\x55\x61\x3f\x0f\xcf\x62\xd4\x97\x05\x24\x2a\x9a\xf9" ++ "\xe6\x1e\x85\xdc\x0d\x65\x1e\x40\xdf\xcf\x01\x7b\x45\x57\x58\x87", ++ 1 /* not-compliant because unallowed algo */ ++ }, ++ { ++ "passwor", 7, ++ GCRY_KDF_PBKDF2, GCRY_MD_SHA1, ++ "saltSALTsaltSALTsaltSALTsaltSALTsalt", 36, ++ 4096, ++ 25, ++ "\xf4\x93\xee\x2b\xbf\x44\x0b\x9e\x64\x53" ++ "\xc2\xb3\x87\xdc\x73\xf8\xfd\xe6\x97\xda" ++ "\xb8\x24\xa0\x26\x50", ++ 1 /* not-compliant because passphrase len is too small */ ++ }, ++ { ++ "passwordPASSWORDpassword", 24, ++ GCRY_KDF_PBKDF2, GCRY_MD_SHA1, ++ "saltSALTsaltSAL", 15, ++ 4096, ++ 25, ++ "\x14\x05\xa4\x2a\xf4\xa8\x12\x14\x7b\x65" ++ "\x8f\xaa\xf0\x7f\x25\xe5\x0f\x0b\x2b\xb7" ++ "\xcf\x8d\x29\x23\x4b", ++ 1 /* not-compliant because salt len is too small */ ++ }, ++ { ++ "passwordPASSWORDpassword", 24, ++ GCRY_KDF_PBKDF2, GCRY_MD_SHA1, ++ "saltSALTsaltSALTsaltSALTsaltSALTsalt", 36, ++ 999, ++ 25, ++ "\xac\xf8\xb4\x67\x41\xc7\xf3\xd1\xa0\xc0" ++ "\x08\xbe\x9b\x23\x96\x78\xbd\x93\xda\x4a" ++ "\x30\xd4\xfb\xf0\x33", ++ 1 /* not-compliant because too few iterations */ ++ }, ++ { ++ "passwordPASSWORDpassword", 24, ++ GCRY_KDF_PBKDF2, GCRY_MD_SHA1, ++ "saltSALTsaltSALTsaltSALTsaltSALTsalt", 36, ++ 4096, ++ 13, ++ "\x3d\x2e\xec\x4f\xe4\x1c\x84\x9b\x80\xc8" ++ "\xd8\x36\x62", ++ 1 /* not-compliant because key size too small */ ++ }, ++ { ++ "passwordPASSWORDpassword", 24, ++ GCRY_KDF_PBKDF2, GCRY_MD_BLAKE2B_512, ++ "saltSALTsaltSALTsaltSALTsaltSALTsalt", 36, ++ 4096, ++ 60, ++ "\xa4\x6b\x53\x35\xdb\xdd\xa3\xd2\x5d\x19\xbb\x11\xfe\xdd\xd9\x9e" ++ "\x45\x2a\x7c\x34\x47\x41\x98\xca\x31\x74\xb6\x34\x22\xac\x83\xb0" ++ "\x38\x6e\xf5\x93\x0f\xf5\x16\x46\x0b\x97\xdc\x6c\x27\x5b\xe7\x25" ++ "\xc2\xcb\xec\x50\x02\xc6\x52\x8b\x34\x68\x53\x65", ++ 1 /* not-compliant because subalgo is not the one of approved */ ++ } ++ }; ++ ++ int tvidx; ++ gpg_error_t err; ++ unsigned char outbuf[100]; ++ int i; ++ ++ for (tvidx=0; tvidx < DIM(tv); tvidx++) ++ { ++ if (verbose) ++ fprintf (stderr, "checking gcry_kdf_derive test vector %d algo %d for FIPS\n", ++ tvidx, tv[tvidx].algo); ++ assert (tv[tvidx].dklen <= sizeof outbuf); ++ err = gcry_kdf_derive (tv[tvidx].p, tv[tvidx].plen, ++ tv[tvidx].algo, tv[tvidx].subalgo, ++ tv[tvidx].salt, tv[tvidx].saltlen, ++ tv[tvidx].iterations, tv[tvidx].dklen, outbuf); ++ ++ if (err) ++ { ++ fail ("gcry_kdf_derive test %d unexpectedly returned an error in FIPS mode: %s\n", ++ tvidx, gpg_strerror (err)); ++ } ++ else ++ { ++ gpg_err_code_t ec; ++ ++ ec = gcry_get_fips_service_indicator (); ++ if (ec == GPG_ERR_INV_OP) ++ { ++ /* libgcrypt is old, no support of the FIPS service indicator. */ ++ fail ("gcry_kdf_derive test %d unexpectedly failed to check the FIPS service indicator.\n", ++ tvidx); ++ continue; ++ } ++ ++ if (!tv[tvidx].expect_failure && ec) ++ { ++ /* Success with the FIPS service indicator == 0 expected, but != 0. */ ++ fail ("gcry_kdf_derive test %d unexpectedly set the indicator in FIPS mode.\n", ++ tvidx); ++ continue; ++ } ++ else if (tv[tvidx].expect_failure && !ec && in_fips_mode) ++ { ++ /* Success with the FIPS service indicator != 0 expected, but == 0. */ ++ fail ("gcry_kdf_derive test %d unexpectedly cleared the indicator in FIPS mode.\n", ++ tvidx); ++ continue; ++ } ++ ++ if (memcmp (outbuf, tv[tvidx].dk, tv[tvidx].dklen)) ++ { ++ fail ("gcry_kdf_derive test %d failed: mismatch\n", tvidx); ++ fputs ("got:", stderr); ++ for (i=0; i < tv[tvidx].dklen; i++) ++ fprintf (stderr, " %02x", outbuf[i]); ++ putc ('\n', stderr); ++ } ++ } ++ } ++} ++ ++ + int + main (int argc, char **argv) + { +@@ -495,6 +653,7 @@ main (int argc, char **argv) + check_digests (); + check_md_o_w_r_c (); + check_mac_o_w_r_c (); ++ check_kdf_derive (); + + return !!error_count; + } +Index: libgcrypt-1.11.0/tests/t-kdf.c +=================================================================== +--- libgcrypt-1.11.0.orig/tests/t-kdf.c ++++ libgcrypt-1.11.0/tests/t-kdf.c +@@ -1927,163 +1927,6 @@ check_fips_indicators (void) + } + + +-static void +-check_fips_gcry_kdf_derive (void) +-{ +- static struct { +- const char *p; /* Passphrase. */ +- size_t plen; /* Length of P. */ +- int algo; +- int subalgo; +- const char *salt; +- size_t saltlen; +- unsigned long iterations; +- int dklen; /* Requested key length. */ +- const char *dk; /* Derived key. */ +- int expect_failure; +- } tv[] = { +- { +- "passwordPASSWORDpassword", 24, +- GCRY_KDF_PBKDF2, GCRY_MD_SHA1, +- "saltSALTsaltSALTsaltSALTsaltSALTsalt", 36, +- 4096, +- 25, +- "\x3d\x2e\xec\x4f\xe4\x1c\x84\x9b\x80\xc8" +- "\xd8\x36\x62\xc0\xe4\x4a\x8b\x29\x1a\x96" +- "\x4c\xf2\xf0\x70\x38", +- 0 +- }, +- { +- "pleaseletmein", 13, +- GCRY_KDF_SCRYPT, 16384, +- "SodiumChloride", 14, +- 1, +- 64, +- "\x70\x23\xbd\xcb\x3a\xfd\x73\x48\x46\x1c\x06\xcd\x81\xfd\x38\xeb" +- "\xfd\xa8\xfb\xba\x90\x4f\x8e\x3e\xa9\xb5\x43\xf6\x54\x5d\xa1\xf2" +- "\xd5\x43\x29\x55\x61\x3f\x0f\xcf\x62\xd4\x97\x05\x24\x2a\x9a\xf9" +- "\xe6\x1e\x85\xdc\x0d\x65\x1e\x40\xdf\xcf\x01\x7b\x45\x57\x58\x87", +- 1 /* not-compliant because unallowed algo */ +- }, +- { +- "passwor", 7, +- GCRY_KDF_PBKDF2, GCRY_MD_SHA1, +- "saltSALTsaltSALTsaltSALTsaltSALTsalt", 36, +- 4096, +- 25, +- "\xf4\x93\xee\x2b\xbf\x44\x0b\x9e\x64\x53" +- "\xc2\xb3\x87\xdc\x73\xf8\xfd\xe6\x97\xda" +- "\xb8\x24\xa0\x26\x50", +- 1 /* not-compliant because passphrase len is too small */ +- }, +- { +- "passwordPASSWORDpassword", 24, +- GCRY_KDF_PBKDF2, GCRY_MD_SHA1, +- "saltSALTsaltSAL", 15, +- 4096, +- 25, +- "\x14\x05\xa4\x2a\xf4\xa8\x12\x14\x7b\x65" +- "\x8f\xaa\xf0\x7f\x25\xe5\x0f\x0b\x2b\xb7" +- "\xcf\x8d\x29\x23\x4b", +- 1 /* not-compliant because salt len is too small */ +- }, +- { +- "passwordPASSWORDpassword", 24, +- GCRY_KDF_PBKDF2, GCRY_MD_SHA1, +- "saltSALTsaltSALTsaltSALTsaltSALTsalt", 36, +- 999, +- 25, +- "\xac\xf8\xb4\x67\x41\xc7\xf3\xd1\xa0\xc0" +- "\x08\xbe\x9b\x23\x96\x78\xbd\x93\xda\x4a" +- "\x30\xd4\xfb\xf0\x33", +- 1 /* not-compliant because too few iterations */ +- }, +- { +- "passwordPASSWORDpassword", 24, +- GCRY_KDF_PBKDF2, GCRY_MD_SHA1, +- "saltSALTsaltSALTsaltSALTsaltSALTsalt", 36, +- 4096, +- 13, +- "\x3d\x2e\xec\x4f\xe4\x1c\x84\x9b\x80\xc8" +- "\xd8\x36\x62", +- 1 /* not-compliant because key size too small */ +- }, +- { +- "passwordPASSWORDpassword", 24, +- GCRY_KDF_PBKDF2, GCRY_MD_BLAKE2B_512, +- "saltSALTsaltSALTsaltSALTsaltSALTsalt", 36, +- 4096, +- 60, +- "\xa4\x6b\x53\x35\xdb\xdd\xa3\xd2\x5d\x19\xbb\x11\xfe\xdd\xd9\x9e" +- "\x45\x2a\x7c\x34\x47\x41\x98\xca\x31\x74\xb6\x34\x22\xac\x83\xb0" +- "\x38\x6e\xf5\x93\x0f\xf5\x16\x46\x0b\x97\xdc\x6c\x27\x5b\xe7\x25" +- "\xc2\xcb\xec\x50\x02\xc6\x52\x8b\x34\x68\x53\x65", +- 1 /* not-compliant because subalgo is not the one of approved */ +- } +- }; +- +- int tvidx; +- gpg_error_t err; +- unsigned char outbuf[100]; +- int i; +- +- for (tvidx=0; tvidx < DIM(tv); tvidx++) +- { +- if (verbose) +- fprintf (stderr, "checking gcry_kdf_derive test vector %d algo %d for FIPS\n", +- tvidx, tv[tvidx].algo); +- assert (tv[tvidx].dklen <= sizeof outbuf); +- err = gcry_kdf_derive (tv[tvidx].p, tv[tvidx].plen, +- tv[tvidx].algo, tv[tvidx].subalgo, +- tv[tvidx].salt, tv[tvidx].saltlen, +- tv[tvidx].iterations, tv[tvidx].dklen, outbuf); +- +- if (err) +- { +- fail ("gcry_kdf_derive test %d unexpectedly returned an error in FIPS mode: %s\n", +- tvidx, gpg_strerror (err)); +- } +- else +- { +- gpg_err_code_t ec; +- +- ec = gcry_get_fips_service_indicator (); +- if (ec == GPG_ERR_INV_OP) +- { +- /* libgcrypt is old, no support of the FIPS service indicator. */ +- fail ("gcry_kdf_derive test %d unexpectedly failed to check the FIPS service indicator.\n", +- tvidx); +- continue; +- } +- +- if (!tv[tvidx].expect_failure && ec) +- { +- /* Success with the FIPS service indicator == 0 expected, but != 0. */ +- fail ("gcry_kdf_derive test %d unexpectedly set the indicator in FIPS mode.\n", +- tvidx); +- continue; +- } +- else if (tv[tvidx].expect_failure && !ec) +- { +- /* Success with the FIPS service indicator != 0 expected, but == 0. */ +- fail ("gcry_kdf_derive test %d unexpectedly cleared the indicator in FIPS mode.\n", +- tvidx); +- continue; +- } +- +- if (memcmp (outbuf, tv[tvidx].dk, tv[tvidx].dklen)) +- { +- fail ("gcry_kdf_derive test %d failed: mismatch\n", tvidx); +- fputs ("got:", stderr); +- for (i=0; i < tv[tvidx].dklen; i++) +- fprintf (stderr, " %02x", outbuf[i]); +- putc ('\n', stderr); +- } +- } +- } +-} +- +- + int + main (int argc, char **argv) + { +@@ -2166,8 +2009,6 @@ main (int argc, char **argv) + check_hkdf (); + if (in_fips_mode) + check_fips_indicators (); +- if (in_fips_mode) +- check_fips_gcry_kdf_derive (); + } + + return error_count ? 1 : 0; diff --git a/libgcrypt-tests-fips-Rename-t-fips-service-ind.patch b/libgcrypt-tests-fips-Rename-t-fips-service-ind.patch new file mode 100644 index 0000000..bb32094 --- /dev/null +++ b/libgcrypt-tests-fips-Rename-t-fips-service-ind.patch @@ -0,0 +1,60 @@ +From 132f346232b33fe41ffee3b3870ec189626676e7 Mon Sep 17 00:00:00 2001 +From: NIIBE Yutaka +Date: Mon, 16 Dec 2024 14:14:24 +0900 +Subject: [PATCH 07/19] tests,fips: Rename t-fips-service-ind. +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +* tests/t-fips-service-ind.c: Rename from t-digest.c. +* tests/Makefile.am (tests_bin): Follow the change. + +-- + +GnuPG-bug-id: 7338 +Signed-off-by: NIIBE Yutaka +Signed-off-by: Lucas Mülling +--- + tests/Makefile.am | 2 +- + tests/{t-digest.c => t-fips-service-ind.c} | 4 ++-- + 2 files changed, 3 insertions(+), 3 deletions(-) + rename tests/{t-digest.c => t-fips-service-ind.c} (99%) + +diff --git a/tests/Makefile.am b/tests/Makefile.am +index 93774fe9..3170a58e 100644 +--- a/tests/Makefile.am ++++ b/tests/Makefile.am +@@ -25,7 +25,7 @@ tests_bin = \ + version t-secmem mpitests t-sexp t-convert \ + t-mpi-bit t-mpi-point t-lock \ + prime basic keygen pubkey hmac hashtest t-kdf keygrip \ +- aeswrap random t-kem t-mlkem t-thread-local t-digest ++ aeswrap random t-kem t-mlkem t-thread-local t-fips-service-ind + + if USE_RSA + tests_bin += pkcs1v2 t-rsa-pss t-rsa-15 t-rsa-testparm +diff --git a/tests/t-digest.c b/tests/t-fips-service-ind.c +similarity index 99% +rename from tests/t-digest.c +rename to tests/t-fips-service-ind.c +index e2b1ce32..31c1fc72 100644 +--- a/tests/t-digest.c ++++ b/tests/t-fips-service-ind.c +@@ -1,4 +1,4 @@ +-/* t-digest.c - MD regression tests ++/* t-fips-service-ind.c - FIPS service indicator regression tests + * Copyright (C) 2024 g10 Code GmbH + * + * This file is part of Libgcrypt. +@@ -27,7 +27,7 @@ + #include + #include + +-#define PGM "t-digest" ++#define PGM "t-fips-service-ind" + + #include "t-common.h" + static int in_fips_mode; +-- +2.49.0 + diff --git a/libgcrypt.changes b/libgcrypt.changes new file mode 100644 index 0000000..1bf7523 --- /dev/null +++ b/libgcrypt.changes @@ -0,0 +1,2023 @@ +------------------------------------------------------------------- +Fri Aug 8 20:05:34 UTC 2025 - Andreas Stieger + +- Update to 1.11.2: + * portability fixes + * Support secp256k1 by KEM API. GnuPG has recently switched to + use the KEM interface and a few folks are using this curve + * Fix a missing initialization in RSA's generate_fips. + * Use '.rodata' section for read-only data of poly1305-p10le + +------------------------------------------------------------------- +Thu Jun 5 13:23:03 UTC 2025 - Angel Yankov + +- Security fix [bsc#1221107, CVE-2024-2236] + * Add --enable-marvin-workaround to spec to enable workaround + * Fix timing based side-channel in RSA implementation ( Marvin attack ) + * Add libgcrypt-CVE-2024-2236.patch + +------------------------------------------------------------------- +Thu May 8 14:28:42 UTC 2025 - Lucas Mulling + +- Update to 1.11.1: [jsc#PED-12227] + * Bug fixes: + - Fix Kyber secret-dependent branch introduced by recent versions of Clang. [rCf765778e82] + - Fix build regression due to the use of AVX512 in Blake. [T7184] + - Do not build i386 asm on amd64 and vice versa. [T7220] + - Fix build regression on armhf with gcc-14. [T7226] + - Return the proper error code on malloc failure in hex2buffer. [rCc51151f5b0] + - Fix long standing bug for PRIME % 2 == 0. [rC639b0fca15] + * Performance: + - Add AES Vector Permute intrinsics implementation for AArch64. [rC94a63aedbb] + - Add GHASH AArch64/SIMD intrinsics implementation. [rCfec871fd18] + - Add RISC-V vector permute AES. [rCb24ebd6163] + - Add GHASH RISC-V Zbb+Zbc implementation. [rC0f1fec12b0] + - Add ChaCha20 RISC-V vector intrinsics implementation. [rC8dbee93ac2] + - Add SHA3 acceleration for RISC-V Zbb extension. [rC1a660068ba] + * Other: + - Add CET support for i386 and amd64 assembly. [T7220] + - Add PAC/BTI support for AArch64 asm. [T7220] + - Apply changes to Kyber from upstream for final FIPS 203. [rCcc95c36e7f] + - Introduce an internal API for a revampled FIPS service indicator. [T7340] + - Several improvements for constant time operation by the introduction of + Least Leak Intended (LLI) variants of internal functions. [T7519,T7490] + * Add libgcrypt-1.11.1-public-SLI-API.patch + * Rebase patches: + - libgcrypt-FIPS-SLI-hash-mac.patch + - libgcrypt-FIPS-SLI-pk.patch + - libgcrypt-FIPS-jitter-standalone.patch + * Remove patches: + - libgcrypt-fips-Introduce-an-internal-API-for-FIPS-service-indicator.patch + - libgcrypt-fips-Introduce-GCRYCTL_FIPS_SERVICE_INDICATOR-and-the-macro.patch + - libgcrypt-fips-kdf-Implement-new-FIPS-service-indicator-for-gcry_kdf_derive.patch + - libgcrypt-fips-md-Implement-new-FIPS-service-indicator-for-gcry_md_hash_.patch + - libgcrypt-fips-tests-Add-t-digest.patch + - libgcrypt-fips-Change-the-internal-API-for-new-FIPS-service-indicator.patch + - libgcrypt-fips-md-Implement-new-FIPS-service-indicator-for-gcry_md_open-API.patch + - libgcrypt-fips-tests-Add-tests-for-md_open-write-read-close-for-t-digest.patch + - libgcrypt-fips-mac-Implement-new-FIPS-service-indicator-for-gcry_mac_open.patch + - libgcrypt-fips-cipher-Implement-new-FIPS-service-indicator-for-cipher_open.patch + - libgcrypt-tests-fips-Add-gcry_mac_open-tests.patch + - libgcrypt-tests-fips-Rename-t-fips-service-ind.patch + - libgcrypt-tests-fips-Move-KDF-tests-to-t-fips-service-ind.patch + - libgcrypt-tests-fips-Add-gcry_cipher_open-tests.patch + - libgcrypt-fips-md-gcry_md_copy-should-care-about-FIPS-service-indicator.patch + - libgcrypt-fips-cipher-Implement-FIPS-service-indicator-for-gcry_pk_hash_-API.patch + - libgcrypt-fips-Introduce-GCRYCTL_FIPS_REJECT_NON_FIPS.patch + - libgcrypt-Fix-the-previous-change.patch + - libgcrypt-fips-Rejection-by-GCRYCTL_FIPS_REJECT_NON_FIPS-not-by-open-flags.patch + - libgcrypt-fips-cipher-Add-behavior-not-to-reject-but-mark-non-compliant.patch + - libgcrypt-fips-ecc-Add-rejecting-or-marking-for-gcry_pk_get_curve.patch + - libgcrypt-tests-Add-more-tests-to-tests-t-fips-service-ind.patch + - libgcrypt-fips-ecc-Check-DATA-in-gcry_pk_sign-verify-in-FIPS-mode.patch + - libgcrypt-fips-cipher-Fix-memory-leak-for-gcry_pk_hash_sign.patch + - libgcrypt-build-Improve-__thread-specifier-check.patch + - libgcrypt-cipher-Check-and-mark-non-compliant-cipher-modes-in-the-SLI.patch + - libgcrypt-cipher-Rename-_gcry_cipher_is_mode_fips_compliant.patch + - libgcrypt-cipher-Don-t-differentiate-GCRY_CIPHER_MODE_CMAC-in-FIPS-mode.patch + - libgcrypt-cipher-rsa-Mark-reject-SHA1-unknown-with-RSA-signature-generation.patch + - libgcrypt-md-Fix-gcry_md_algo_info-to-mark-reject-under-FIPS-mode.patch + - libgcrypt-md-Use-check_digest_algo_spec-in-_gcry_md_selftest.patch + - libgcrypt-tests-Update-t-fips-service-ind-using-GCRY_MD_SHA256-for-KDF-tests.patch + - libgcrypt-fips-cipher-Do-the-computation-when-marking-non-compliant.patch + - libgcrypt-tests-Allow-tests-with-USE_RSA.patch + - libgcrypt-cipher-Add-KAT-for-non-rfc6979-ECDSA-with-fixed-k.patch + - libgcrypt-cipher-Differentiate-use-of-label-K-in-the-SLI.patch + - libgcrypt-cipher-Differentiate-igninvflag-in-the-SLI.patch + - libgcrypt-cipher-Differentiate-no-blinding-flag-in-the-SLI.patch + - libgcrypt-fips-cipher-Add-GCRY_FIPS_FLAG_REJECT_PK_FLAGS.patch + - libgcrypt-cipher-ecc-Fix-for-supplied-K.patch + - libgcrypt-cipher-visibility-Differentiate-use-of-random-override-in-the-SLI.patch + - libgcrypt-cipher-fips-Fix-for-random-override.patch + - libgcrypt-md-Make-SHA-1-non-FIPS-internally-for-1.12-API.patch + - libgcrypt-fips-Fix-GCRY_FIPS_FLAG_REJECT_MD.patch + - libgcrypt-doc-Add-about-GCRYCTL_FIPS_SERVICE_INDICATOR.patch + - libgcrypt-doc-Fix-syntax-error.patch + - libgcrypt-Disable-SHA3-s390x-acceleration-for-CSHAKE.patch + +------------------------------------------------------------------- +Tue May 6 07:24:14 UTC 2025 - Pedro Monreal + +- CSHAKE basic regression test failure in s390x [bsc#1242419] + * Disable SHA3 s390x acceleration for CSHAKE [rC2486d9b5ae01] + * Add libgcrypt-Disable-SHA3-s390x-acceleration-for-CSHAKE.patch + +------------------------------------------------------------------- +Sun Apr 13 20:10:16 UTC 2025 - Lucas Mulling + +- Differentiate use of SHA1 in the service level indicator [jsc#PED-12227] + * Include upstream SLI revamp and fips certification fixes + * Add patches: + - libgcrypt-fips-Introduce-an-internal-API-for-FIPS-service-indicator.patch + - libgcrypt-fips-Introduce-GCRYCTL_FIPS_SERVICE_INDICATOR-and-the-macro.patch + - libgcrypt-fips-kdf-Implement-new-FIPS-service-indicator-for-gcry_kdf_derive.patch + - libgcrypt-fips-md-Implement-new-FIPS-service-indicator-for-gcry_md_hash_.patch + - libgcrypt-fips-tests-Add-t-digest.patch + - libgcrypt-fips-Change-the-internal-API-for-new-FIPS-service-indicator.patch + - libgcrypt-fips-md-Implement-new-FIPS-service-indicator-for-gcry_md_open-API.patch + - libgcrypt-fips-tests-Add-tests-for-md_open-write-read-close-for-t-digest.patch + - libgcrypt-fips-mac-Implement-new-FIPS-service-indicator-for-gcry_mac_open.patch + - libgcrypt-fips-cipher-Implement-new-FIPS-service-indicator-for-cipher_open.patch + - libgcrypt-tests-fips-Add-gcry_mac_open-tests.patch + - libgcrypt-tests-fips-Rename-t-fips-service-ind.patch + - libgcrypt-tests-fips-Move-KDF-tests-to-t-fips-service-ind.patch + - libgcrypt-tests-fips-Add-gcry_cipher_open-tests.patch + - libgcrypt-fips-md-gcry_md_copy-should-care-about-FIPS-service-indicator.patch + - libgcrypt-fips-cipher-Implement-FIPS-service-indicator-for-gcry_pk_hash_-API.patch + - libgcrypt-fips-Introduce-GCRYCTL_FIPS_REJECT_NON_FIPS.patch + - libgcrypt-Fix-the-previous-change.patch + - libgcrypt-fips-Rejection-by-GCRYCTL_FIPS_REJECT_NON_FIPS-not-by-open-flags.patch + - libgcrypt-fips-cipher-Add-behavior-not-to-reject-but-mark-non-compliant.patch + - libgcrypt-fips-ecc-Add-rejecting-or-marking-for-gcry_pk_get_curve.patch + - libgcrypt-tests-Add-more-tests-to-tests-t-fips-service-ind.patch + - libgcrypt-fips-ecc-Check-DATA-in-gcry_pk_sign-verify-in-FIPS-mode.patch + - libgcrypt-fips-cipher-Fix-memory-leak-for-gcry_pk_hash_sign.patch + - libgcrypt-build-Improve-__thread-specifier-check.patch + - libgcrypt-cipher-Check-and-mark-non-compliant-cipher-modes-in-the-SLI.patch + - libgcrypt-cipher-Rename-_gcry_cipher_is_mode_fips_compliant.patch + - libgcrypt-cipher-Don-t-differentiate-GCRY_CIPHER_MODE_CMAC-in-FIPS-mode.patch + - libgcrypt-cipher-rsa-Mark-reject-SHA1-unknown-with-RSA-signature-generation.patch + - libgcrypt-md-Fix-gcry_md_algo_info-to-mark-reject-under-FIPS-mode.patch + - libgcrypt-md-Use-check_digest_algo_spec-in-_gcry_md_selftest.patch + - libgcrypt-tests-Update-t-fips-service-ind-using-GCRY_MD_SHA256-for-KDF-tests.patch + - libgcrypt-fips-cipher-Do-the-computation-when-marking-non-compliant.patch + - libgcrypt-tests-Allow-tests-with-USE_RSA.patch + - libgcrypt-cipher-Add-KAT-for-non-rfc6979-ECDSA-with-fixed-k.patch + - libgcrypt-cipher-Differentiate-use-of-label-K-in-the-SLI.patch + - libgcrypt-cipher-Differentiate-igninvflag-in-the-SLI.patch + - libgcrypt-cipher-Differentiate-no-blinding-flag-in-the-SLI.patch + - libgcrypt-fips-cipher-Add-GCRY_FIPS_FLAG_REJECT_PK_FLAGS.patch + - libgcrypt-cipher-ecc-Fix-for-supplied-K.patch + - libgcrypt-cipher-visibility-Differentiate-use-of-random-override-in-the-SLI.patch + - libgcrypt-cipher-fips-Fix-for-random-override.patch + - libgcrypt-md-Make-SHA-1-non-FIPS-internally-for-1.12-API.patch + - libgcrypt-fips-Fix-GCRY_FIPS_FLAG_REJECT_MD.patch + - libgcrypt-doc-Add-about-GCRYCTL_FIPS_SERVICE_INDICATOR.patch + - libgcrypt-doc-Fix-syntax-error.patch + * Rebase patches: + - libgcrypt-FIPS-SLI-kdf-leylength.patch + +------------------------------------------------------------------- +Tue Jan 7 09:28:25 UTC 2025 - Pedro Monreal + +- Fix redefinition error of 'rol64'. Remove not used rol64() + definition after removing the built-in jitter rng. + * Add libgcrypt-rol64-redefinition.patch + +------------------------------------------------------------------- +Mon Dec 2 10:11:10 UTC 2024 - Pedro Monreal + +- Remove unrecognized option: --enable-m-guard + +------------------------------------------------------------------- +Thu Jun 20 08:11:07 UTC 2024 - Pedro Monreal + +- Update to 1.11.0: + * New and extended interfaces: + - Add an API for Key Encapsulation Mechanism (KEM). [T6755] + - Add Streamlined NTRU Prime sntrup761 algorithm. [rCcf9923e1a5] + - Add Kyber algorithm according to FIPS 203 ipd 2023-08-24. [rC18e5c0d268] + - Add Classic McEliece algorithm. [rC003367b912] + - Add One-Step KDF with hash and MAC. [T5964] + - Add KDF algorithm HKDF of RFC-5869. [T5964] + - Add KDF algorithm X963KDF for use in CMS. [rC3abac420b3] + - Add GMAC-SM4 and Poly1305-SM4. [rCd1ccc409d4] + - Add ARIA block cipher algorithm. [rC316c6d7715] + - Add explicit FIPS indicators for MD and MAC algorithms. [T6376] + - Add support for SHAKE as MGF in RSA. [T6557] + - Add gcry_md_read support for SHAKE algorithms. [T6539] + - Add gcry_md_hash_buffers_ext function. [T7035] + - Add cSHAKE hash algorithm. [rC065b3f4e02] + - Support internal generation of IV for AEAD cipher mode. [T4873] + * Performance: + - Add SM3 ARMv8/AArch64/CE assembly implementation. [rCfe891ff4a3] + - Add SM4 ARMv8/AArch64 assembly implementation. [rCd8825601f1] + - Add SM4 GFNI/AVX2 and GFI/AVX512 implementation. [rC5095d60af4,rCeaed633c16] + - Add SM4 ARMv9 SVE CE assembly implementation. [rC2dc2654006] + - Add PowerPC vector implementation of SM4. [rC0b2da804ee] + - Optimize ChaCha20 and Poly1305 for PPC P10 LE. [T6006] + - Add CTR32LE bulk acceleration for AES on PPC. [rC84f2e2d0b5] + - Add generic bulk acceleration for CTR32LE mode (GCM-SIV) for SM4 + and Camellia. [rCcf956793af] + - Add GFNI/AVX2 implementation of Camellia. [rC4e6896eb9f] + - Add AVX2 and AVX512 accelerated implementations for GHASH (GCM) + and POLYVAL (GCM-SIV). [rCd857e85cb4, rCe6f3600193] + - Add AVX512 implementation for SHA512. [rC089223aa3b] + - Add AVX512 implementation for Serpent. [rCce95b6ec35] + - Add AVX512 implementation for Poly1305 and ChaCha20. [rCcd3ed49770, rC9a63cfd617] + - Add AVX512 accelerated implementation for SHA3 and Blake2. [rCbeaad75f46,rC909daa700e] + - Add VAES/AVX2 accelerated i386 implementation for AES. [rC4a42a042bc] + - Add bulk processing for XTS mode of Camellia and SM4. [rC32b18cdb87, rCaad3381e93] + - Accelerate XTS and ECB modes for Twofish and Serpent. [rCd078a928f5,rC8a1fe5f78f] + - Add AArch64 crypto/SHA512 extension implementation for SHA512. [rCe51d3b8330] + - Add AArch64 crypto-extension implementation for Camellia. [rC898c857206] + - Accelerate OCB authentication on AMD with AVX2. [rC6b47e85d65] + * Bug fixes: + - For PowerPC check for missing optimization level for vector register usage. [T5785] + - Fix EdDSA secret key check. [T6511] + - Fix decoding of PKCS#1-v1.5 and OAEP padding. [rC34c2042792] + - Allow use of PKCS#1-v1.5 with SHA3 algorithms. [T6976] + - Fix AESWRAP padding length check. [T7130] + * Other: + - Allow empty password for Argon2 KDF. [rCa20700c55f] + - Various constant time operation imporvements. + - Add "bp256", "bp384", "bp512" aliases for Brainpool curves. + - Support for the random server has been removed. [T5811] + - The control code GCRYCTL_ENABLE_M_GUARD is deprecated and not + supported any more. Please use valgrind or other tools. [T5822] + - Logging is now done via the libgpg-error logging functions. [rCab0bdc72c7] + * Remove patches fixed upstream: + - libgcrypt-no-deprecated-grep-alias.patch + - libgcrypt-Chacha20-poly1305-Optimized-chacha20-poly1305.patch + - libgcrypt-ppc-enable-P10-assembly-with-ENABLE_FORCE_SOF.patch + * Rebase patches: + - libgcrypt-FIPS-jitter-errorcodes.patch + - libgcrypt-FIPS-jitter-whole-entropy.patch + +------------------------------------------------------------------- +Wed Mar 20 20:31:40 UTC 2024 - Pedro Monreal + +- FIPS: Make sure that Libgcrypt makes use of the built-in Jitter RNG + for the whole length entropy buffer in FIPS mode. [bsc#1220893] + * Add libgcrypt-FIPS-jitter-whole-entropy.patch + +------------------------------------------------------------------- +Wed Mar 20 15:13:04 UTC 2024 - Pedro Monreal + +- FIPS: Set the FSM into error state if Jitter RNG is returning an + error code to the caller when an health test error occurs when + random bytes are requested through the jent_read_entropy_safe() + function. [bsc#1220895] + * Add libgcrypt-FIPS-jitter-errorcodes.patch + +------------------------------------------------------------------- +Mon Mar 11 16:02:55 UTC 2024 - Pedro Monreal + +- FIPS: Replace the built-in jitter rng with standalone version + * Remove the internal jitterentropy copy [bsc#1220896] + * Add libgcrypt-FIPS-jitter-standalone.patch + * Remove not needed libgcrypt-jitterentropy-3.4.0.patch + +------------------------------------------------------------------- +Mon Feb 26 12:13:56 UTC 2024 - Pedro Monreal + +- Update upstream libgcrypt.keyring + +------------------------------------------------------------------- +Sat Jan 27 13:37:34 UTC 2024 - Dirk Müller + +- add libgcrypt-no-deprecated-grep-alias.patch + +------------------------------------------------------------------- +Tue Nov 21 10:36:09 UTC 2023 - Otto Hollmann + +- Re-create HMAC checksum after RPM build strips the library + (bsc#1217058) + +------------------------------------------------------------------- +Wed Nov 15 09:54:00 UTC 2023 - Pedro Monreal + +- Update to 1.10.3: + * Bug fixes: + - Fix public key computation for other EdDSA curves. [rC469919751d6e] + - Remove out of core handler diagnostic in FIPS mode. [T6515] + - Check that the digest size is not zero in gcry_pk_sign_md and + gcry_pk_verify_md. [T6539] + - Make store an s-exp with \0 is considered to be binary. [T6747] + - Various constant-time improvements. + * Portability: + - Use getrandom call only when supported by the platform. [T6442] + - Change the default for --with-libtool-modification to never. [T6619] + * Release-info: https://dev.gnupg.org/T6817 + * Remove patch upstream libgcrypt-1.10.0-out-of-core-handler.patch + +------------------------------------------------------------------- +Tue Oct 17 10:27:15 UTC 2023 - Pedro Monreal + +- Do not pull revision info from GIT when autoconf is run. This + removes the -unknown suffix after the version number. + * Add libgcrypt-nobetasuffix.patch [bsc#1216334] + +------------------------------------------------------------------- +Tue Oct 3 12:58:41 UTC 2023 - Pedro Monreal + +- POWER: performance enhancements for cryptography [jsc#PED-5088] + * Optimize Chacha20 and Poly1305 for PPC P10 LE: [T6006] + - Chacha20/poly1305: Optimized chacha20/poly1305 for + P10 operation [rC88fe7ac33eb4] + - ppc: enable P10 assembly with ENABLE_FORCE_SOFT_HWFEATURES + on arch-3.00 [rC2c5e5ab6843d] + * Add patches: + - libgcrypt-Chacha20-poly1305-Optimized-chacha20-poly1305.patch + - libgcrypt-ppc-enable-P10-assembly-with-ENABLE_FORCE_SOF.patch + +------------------------------------------------------------------- +Mon May 22 11:32:53 UTC 2023 - Pedro Monreal + +- FIPS: Merge the libgcrypt20-hmac package into the library and + remove the "module is complete" trigger file .fips [bsc#1185116] + * Remove libgcrypt-1.10.0-use-fipscheck.patch + +------------------------------------------------------------------- +Tue Apr 11 14:08:24 UTC 2023 - Pedro Monreal + +- Update to 1.10.2: + * Bug fixes: + - Fix Argon2 for the case output > 64. [rC13b5454d26] + - Fix missing HWF_PPC_ARCH_3_10 in HW feature. [rCe073f0ed44] + - Fix RSA key generation failure in forced FIPS mode. [T5919] + - Fix gcry_pk_hash_verify for explicit hash. [T6066] + - Fix a wrong result of gcry_mpi_invm. [T5970] + - Allow building with --disable-asm for HPPA. [T5976] + - Allow building with -Oz. [T6432] + - Enable the fast path to ChaCha20 only when supported. [T6384] + - Use size_t to avoid counter overflow in Keccak when directly + feeding more than 4GiB. [T6217] + * Other: + - Do not use secure memory for a DRBG instance. [T5933] + - Do not allow PKCS#1.5 padding for encryption in FIPS mode. [T5918] + - Fix the behaviour for child process re-seeding in the DRBG. [rC019a40c990] + - Allow verification of small RSA signatures in FIPS mode. [T5975] + - Allow the use of a shorter salt for KDFs in FIPS mode. [T6039] + - Run digest+sign self tests for RSA and ECC in FIPS mode. [rC06c9350165] + - Add function-name based FIPS indicator function. + GCRYCTL_FIPS_SERVICE_INDICATOR_FUNCTION. This is not considered + an ABI changes because the new FIPS features were not yet + approved. [rC822ee57f07] + - Improve PCT in FIPS mode. [rC285bf54b1a, rC4963c127ae, T6397] + - Use getrandom (GRND_RANDOM) in FIPS mode. [rCcf10c74bd9] + - Disable RSA-OAEP padding in FIPS mode. [rCe5bfda492a] + - Check minimum allowed key size in PBKDF in FIPS mode. [T6039,T6219] + - Get maximum 32B of entropy at once in FIPS mode. [rCce0df08bba] + - Prefer gpgrt-config when available. [T5034] + - Mark AESWRAP as approved FIPS algorithm. [T5512] + - Prevent usage of long salt for PSS in FIPS mode. [rCfdd2a8b332] + - Prevent usage of X9.31 keygen in FIPS mode. [rC392e0ccd25] + - Remove GCM mode from the allowed FIPS indicators. [rC1540698389] + - Add explicit FIPS indicators for hash and MAC algorithms. [T6376] + * Release-info: https://dev.gnupg.org/T5905 + * Rebase FIPS patches: + - libgcrypt-FIPS-SLI-hash-mac.patch + - libgcrypt-FIPS-SLI-kdf-leylength.patch + - libgcrypt-FIPS-SLI-pk.patch + +------------------------------------------------------------------- +Wed Mar 8 10:34:34 UTC 2023 - Martin Pluskal + +- Build AVX2 enabled hwcaps library for x86_64-v3 + +------------------------------------------------------------------- +Wed Oct 19 14:01:24 UTC 2022 - Pedro Monreal + +- Update to 1.10.1: + * Bug fixes: + - Fix minor memory leaks in FIPS mode. + - Build fixes for MUSL libc. + * Other: + - More portable integrity check in FIPS mode. + - Add X9.62 OIDs to sha256 and sha512 modules. + * Add the hardware optimizations config file hwf.deny to + the /etc/gcrypt/ directory. This file can be used to globally + disable the use of hardware based optimizations. + * Remove not needed separate_hmac256_binary hmac256 package + +------------------------------------------------------------------- +Wed Sep 14 13:34:13 UTC 2022 - Pedro Monreal + +- Update to 1.10.0: + * New and extended interfaces: + - New control codes to check for FIPS 140-3 approved algorithms. + - New control code to switch into non-FIPS mode. + - New cipher modes SIV and GCM-SIV as specified by RFC-5297. + - Extended cipher mode AESWRAP with padding as specified by + RFC-5649. + - New set of KDF functions. + - New KDF modes Argon2 and Balloon. + - New functions for combining hashing and signing/verification. + * Performance: + - Improved support for PowerPC architectures. + - Improved ECC performance on zSeries/s390x by using accelerated + scalar multiplication. + - Many more assembler performance improvements for several + architectures. + * Bug fixes: + - Fix Elgamal encryption for other implementations. + [bsc#1190239, CVE-2021-40528] + - Check the input length of the point in ECDH. + - Fix an abort in gcry_pk_get_param for "Curve25519". + * Other features: + - The control code GCRYCTL_SET_ENFORCED_FIPS_FLAG is ignored + because it is useless with the FIPS 140-3 related changes. + - Update of the jitter entropy RNG code. + - Simplification of the entropy gatherer when using the getentropy + system call. + * Interface changes relative to the 1.10.0 release: + - GCRYCTL_SET_DECRYPTION_TAG NEW control code. + - GCRYCTL_FIPS_SERVICE_INDICATOR_CIPHER NEW control code. + - GCRYCTL_FIPS_SERVICE_INDICATOR_KDF NEW control code. + - GCRYCTL_NO_FIPS_MODE = 83 NEW control code. + - GCRY_CIPHER_MODE_SIV NEW mode. + - GCRY_CIPHER_MODE_GCM_SIV NEW mode. + - GCRY_CIPHER_EXTENDED NEW flag. + - GCRY_SIV_BLOCK_LEN NEW macro. + - gcry_cipher_set_decryption_tag NEW macro. + - GCRY_KDF_ARGON2 NEW constant. + - GCRY_KDF_BALLOON NEW constant. + - GCRY_KDF_ARGON2D NEW constant. + - GCRY_KDF_ARGON2I NEW constant. + - GCRY_KDF_ARGON2ID NEW constant. + - gcry_kdf_hd_t NEW type. + - gcry_kdf_job_fn_t NEW type. + - gcry_kdf_dispatch_job_fn_t NEW type. + - gcry_kdf_wait_all_jobs_fn_t NEW type. + - struct gcry_kdf_thread_ops NEW struct. + - gcry_kdf_open NEW function. + - gcry_kdf_compute NEW function. + - gcry_kdf_final NEW function. + - gcry_kdf_close NEW function. + - gcry_pk_hash_sign NEW function. + - gcry_pk_hash_verify NEW function. + - gcry_pk_random_override_new NEW function. + * Rebase libgcrypt-1.8.4-allow_FSM_same_state.patch and rename + to libgcrypt-1.10.0-allow_FSM_same_state.patch + * Remove unused CAVS tests and related patches: + - cavs_driver.pl cavs-test.sh + - libgcrypt-1.6.1-fips-cavs.patch + - drbg_test.patch + * Remove DSA sign/verify patches for the FIPS CAVS test since DSA + has been disabled in FIPS mode: + - libgcrypt-fipsdrv-enable-algo-for-dsa-sign.patch + - libgcrypt-fipsdrv-enable-algo-for-dsa-verify.patch + * Rebase libgcrypt-FIPS-SLI-pk.patch + * Rebase libgcrypt_indicators_changes.patch and + libgcrypt-indicate-shake.patch and merge both into + libgcrypt-FIPS-SLI-hash-mac.patch + * Rebase libgcrypt-FIPS-kdf-leylength.patch and rename to + libgcrypt-FIPS-SLI-kdf-leylength.patch + * Rebase libgcrypt-jitterentropy-3.4.0.patch + * Rebase libgcrypt-FIPS-rndjent_poll.patch + * Rebase libgcrypt-out-of-core-handler.patch and rename to + libgcrypt-1.10.0-out-of-core-handler.patch + * Since the FIPS .hmac file is now calculated with the internal + tool hmac256, only the "module is complete" trigger .fips file + is checked. Rename libgcrypt-1.6.1-use-fipscheck.patch + to libgcrypt-1.10.0-use-fipscheck.patch + * Remove patches fixed upstream: + - libgcrypt-1.4.1-rijndael_no_strict_aliasing.patch + - libgcrypt-1.5.0-LIBGCRYPT_FORCE_FIPS_MODE-env.diff + - libgcrypt-fix-rng.patch + - libgcrypt-1.8.3-fips-ctor.patch + - libgcrypt-1.8.4-use_xfree.patch + - libgcrypt-1.8.4-getrandom.patch + - libgcrypt-1.8.4-fips_ctor_skip_integrity_check.patch + - libgcrypt-dsa-rfc6979-test-fix.patch + - libgcrypt-fix-tests-fipsmode.patch + - libgcrypt-FIPS-RSA-DSA-ECDSA-hashing-operation.patch + - libgcrypt-1.8.4-fips-keygen.patch + - libgcrypt-invoke-global_init-from-constructor.patch + - libgcrypt-Restore-self-tests-from-constructor.patch + - libgcrypt-FIPS-GMAC_AES-benckmark.patch + - libgcrypt-global_init-constructor.patch + - libgcrypt-random_selftests-testentropy.patch + - libgcrypt-rsa-no-blinding.patch + - libgcrypt-ecc-ecdsa-no-blinding.patch + - libgcrypt-PCT-DSA.patch + - libgcrypt-PCT-ECC.patch + - libgcrypt-PCT-RSA.patch + - libgcrypt-fips_selftest_trigger_file.patch + - libgcrypt-pthread-in-t-lock-test.patch + - libgcrypt-FIPS-hw-optimizations.patch + - libgcrypt-FIPS-module-version.patch + - libgcrypt-FIPS-disable-3DES.patch + - libgcrypt-FIPS-fix-regression-tests.patch + - libgcrypt-FIPS-RSA-keylen.patch + - libgcrypt-FIPS-RSA-keylen-tests.patch + - libgcrypt-FIPS-fix-gcry_mpi_sub_ui.patch + - libgcrypt-FIPS-verify-unsupported-KDF-test.patch + - libgcrypt-FIPS-HMAC-short-keylen.patch + - libgcrypt-FIPS-service-indicators.patch + - libgcrypt-FIPS-disable-DSA.patch + - libgcrypt-jitterentropy-3.3.0.patch + - libgcrypt-FIPS-Zeroize-hmac.patch + * Update libgcrypt.keyring + +------------------------------------------------------------------- +Thu Sep 8 10:34:53 UTC 2022 - Pedro Monreal + +- FIPS: Get most of the entropy from rndjent_poll [bsc#1202117] + * Add libgcrypt-FIPS-rndjent_poll.patch + * Rebase libgcrypt-jitterentropy-3.4.0.patch + +------------------------------------------------------------------- +Wed Sep 7 22:03:51 UTC 2022 - Pedro Monreal + +- FIPS: Check keylength in gcry_fips_indicator_kdf() [bsc#1190700] + * Consider approved keylength greater or equal to 112 bits. + * Add libgcrypt-FIPS-kdf-leylength.patch + +------------------------------------------------------------------- +Wed Sep 7 12:53:14 UTC 2022 - Pedro Monreal + +- FIPS: Zeroize buffer and digest in check_binary_integrity() + * Add libgcrypt-FIPS-Zeroize-hmac.patch [bsc#1191020] + +------------------------------------------------------------------- +Tue Aug 23 09:19:00 UTC 2022 - Pedro Monreal + +- FIPS: gpg/gpg2 gets out of core handler in FIPS mode while + typing Tab key to Auto-Completion. [bsc#1182983] + * Add libgcrypt-out-of-core-handler.patch + +------------------------------------------------------------------- +Mon Aug 8 11:33:03 UTC 2022 - Pedro Monreal + +- FIPS: Port libgcrypt to use jitterentropy [bsc#1202117, jsc#SLE-24941] + * Enable the jitter based entropy generator by default in random.conf + - Add libgcrypt-jitterentropy-3.3.0.patch + * Update the internal jitterentropy to version 3.4.0 + - Add libgcrypt-jitterentropy-3.4.0.patch + +------------------------------------------------------------------- +Mon Aug 1 07:27:35 UTC 2022 - Stephan Kulow + +- Fix reproducible build problems: + - Do not use %release in binaries (but use SOURCE_DATE_EPOCH) + - Fix date call messed up by spec-cleaner + +------------------------------------------------------------------- +Thu Apr 14 12:30:36 UTC 2022 - Dennis Knorr + +- FIPS: extend the service indicator [bsc#1190700] + * introduced a pk indicator function + * adapted the approved and non approved ciphersuites + * Add libgcrypt_indicators_changes.patch + * Add libgcrypt-indicate-shake.patch + +------------------------------------------------------------------- +Tue Mar 22 12:32:09 UTC 2022 - Pedro Monreal + +- FIPS: Implement a service indicator for asymmetric ciphers [bsc#1190700] + * Mark RSA public key encryption and private key decryption with + padding (e.g. OAEP, PKCS) as non-approved since RSA-OAEP lacks + peer key assurance validation requirements per SP800-56Brev2. + * Mark ECC as approved only for NIST curves P-224, P-256, P-384 + and P-521 with check for common NIST names and aliases. + * Mark DSA, ELG, EDDSA, ECDSA and ECDH as non-approved. + * Add libgcrypt-FIPS-SLI-pk.patch + * Rebase libgcrypt-FIPS-service-indicators.patch +- Run the regression tests also in FIPS mode. + * Disable tests for non-FIPS approved algos. + * Rebase: libgcrypt-FIPS-verify-unsupported-KDF-test.patch + +------------------------------------------------------------------- +Tue Feb 1 11:28:51 UTC 2022 - Pedro Monreal + +- FIPS: Disable DSA in FIPS mode [bsc#1195385] + * Upstream task: https://dev.gnupg.org/T5710 + * Add libgcrypt-FIPS-disable-DSA.patch + +------------------------------------------------------------------- +Wed Jan 19 08:36:58 UTC 2022 - Pedro Monreal + +- FIPS: Service level indicator [bsc#1190700] + * Provide an indicator to check wether the service utilizes an + approved cryptographic algorithm or not. + * Add patches: + - libgcrypt-FIPS-service-indicators.patch + - libgcrypt-FIPS-verify-unsupported-KDF-test.patch + - libgcrypt-FIPS-HMAC-short-keylen.patch + +------------------------------------------------------------------- +Tue Dec 7 09:41:01 UTC 2021 - Pedro Monreal + +- FIPS: Fix gcry_mpi_sub_ui subtraction [bsc#1193480] + * gcry_mpi_sub_ui: fix subtracting from negative value + * Add libgcrypt-FIPS-fix-gcry_mpi_sub_ui.patch + +------------------------------------------------------------------- +Tue Nov 30 09:42:23 UTC 2021 - Pedro Monreal + +- FIPS: Define an entropy source SP800-90B compliant [bsc#1185140] + * Disable jitter entropy by default in random.conf + * Disable only-urandom option by default in random.conf + +------------------------------------------------------------------- +Fri Nov 26 13:10:29 UTC 2021 - Pedro Monreal + +- FIPS: RSA KeyGen/SigGen fail with 4096 bit key sizes [bsc#1192240] + * rsa: Check RSA keylen constraints for key operations. + * rsa: Fix regression in not returning an error for prime generation. + * tests: Add 2k RSA key working in FIPS mode. + * tests: pubkey: Replace RSA key to one of 2k. + * tests: pkcs1v2: Skip tests with small keys in FIPS. + * Add patches: + - libgcrypt-FIPS-RSA-keylen.patch + - libgcrypt-FIPS-RSA-keylen-tests.patch + +------------------------------------------------------------------- +Mon Nov 8 10:21:39 UTC 2021 - Pedro Monreal + +- FIPS: Disable 3DES/Triple-DES in FIPS mode [bsc#1185138] + * Add libgcrypt-FIPS-disable-3DES.patch + +------------------------------------------------------------------- +Tue Nov 2 11:31:19 UTC 2021 - Pedro Monreal + +- FIPS: PBKDF requirements [bsc#1185137] + * The PBKDF2 selftests were introduced in libgcrypt version + 1.9.1 in the function selftest_pbkdf2() + * Upstream task: https://dev.gnupg.org/T5182 + +------------------------------------------------------------------- +Thu Oct 28 19:48:06 UTC 2021 - Pedro Monreal + +- FIPS: Fix regression tests in FIPS mode [bsc#1192131] + * Add libgcrypt-FIPS-fix-regression-tests.patch + * Upstream task: https://dev.gnupg.org/T5520 + +------------------------------------------------------------------- +Thu Sep 21 11:25:06 UTC 2021 - Pedro Monreal + +- FIPS: Provide a module name/identifier and version that can be + mapped to the validation records. [bsc#1190706] + * Add libgcrypt-FIPS-module-version.patch + * Upstream task: https://dev.gnupg.org/T5600 + +------------------------------------------------------------------- +Thu Sep 21 10:23:44 UTC 2021 - Pedro Monreal + +- FIPS: Enable hardware support also in FIPS mode [bsc#1187110] + * Add libgcrypt-FIPS-hw-optimizations.patch + * Upstream task: https://dev.gnupg.org/T5508 + +------------------------------------------------------------------- +Mon Aug 23 12:08:24 UTC 2021 - Pedro Monreal + +- Update to 1.9.4: + * Bug fixes: + - Fix Elgamal encryption for other implementations. [CVE-2021-33560] + - Fix alignment problem on macOS. + - Check the input length of the point in ECDH. + - Fix an abort in gcry_pk_get_param for "Curve25519". + * Other features: + - Add GCM and CCM to OID mapping table for AES. + * Upstream libgcrypt-CVE-2021-33560-fix-ElGamal-enc.patch + +------------------------------------------------------------------- +Mon Aug 23 10:11:55 UTC 2021 - Pedro Monreal + +- Remove not needed patch libgcrypt-sparcv9.diff + +------------------------------------------------------------------- +Thu Jul 15 12:53:45 UTC 2021 - Pedro Monreal + +- Fix building test t-lock with pthread. [bsc#1189745] + * Explicitly add -lpthread to compile the t-lock test. + * Add libgcrypt-pthread-in-t-lock-test.patch + +------------------------------------------------------------------- +Fri Jun 11 13:17:54 UTC 2021 - Pedro Monreal + +- Security fix: [bsc#1187212, CVE-2021-33560] + * cipher: Fix ElGamal encryption for other implementations. + * Exponent blinding was added in version 1.9.3. This patch + fixes ElGamal encryption, see: https://dev.gnupg.org/T5328 +- Add libgcrypt-CVE-2021-33560-fix-ElGamal-enc.patch + +------------------------------------------------------------------- +Tue Apr 20 08:46:11 UTC 2021 - Paolo Stivanin + +- libgcrypt 1.9.3: + * Bug fixes: + - Fix build problems on i386 using gcc-4.7. + - Fix checksum calculation in OCB decryption for AES on s390. + - Fix a regression in gcry_mpi_ec_add related to certain usages + of curve 25519. + - Fix a symbol not found problem on Apple M1. + - Fix for Apple iOS getentropy peculiarity. + - Make keygrip computation work for compressed points. + * Performance: + - Add x86_64 VAES/AVX2 accelerated implementation of Camellia. + - Add x86_64 VAES/AVX2 accelerated implementation of AES. + - Add VPMSUMD acceleration for GCM mode on PPC. + * Internal changes. + - Harden MPI conditional code against EM leakage. + - Harden Elgamal by introducing exponent blinding. + +------------------------------------------------------------------- +Wed Feb 17 09:49:55 UTC 2021 - Andreas Stieger + +- libgcrypt 1.9.2: + * Fix building with --disable-asm on x86 + * Check public key for ECDSA verify operation + * Make sure gcry_get_config (NULL) returns a nul-terminated + string + * Fix a memory leak in the ECDH code + * Fix a reading beyond end of input buffer in SHA2-avx2 +- remove obsolete texinfo packaging macros + +------------------------------------------------------------------- +Tue Feb 2 01:06:47 UTC 2021 - Pedro Monreal + +- Update to 1.9.1 + * *Fix exploitable bug* in hash functions introduced with + 1.9.0. [bsc#1181632, CVE-2021-3345] + * Return an error if a negative MPI is used with sexp scan + functions. + * Check for operational FIPS in the random and KDF functions. + * Fix compile error on ARMv7 with NEON disabled. + * Fix self-test in KDF module. + * Improve assembler checks for better LTO support. + * Fix 32-bit cross build on x86. + * Fix non-NEON ARM assembly implementation for SHA512. + * Fix build problems with the cipher_bulk_ops_t typedef. + * Fix Ed25519 private key handling for preceding ZEROs. + * Fix overflow in modular inverse implementation. + * Fix register access for AVX/AVX2 implementations of Blake2. + * Add optimized cipher and hash functions for s390x/zSeries. + * Use hardware bit counting functionx when available. + * Update DSA functions to match FIPS 186-3. + * New self-tests for CMACs and KDFs. + * Add bulk cipher functions for OFB and GCM modes. +- Update libgpg-error required version + +------------------------------------------------------------------- +Tue Feb 1 12:03:31 UTC 2021 - Pedro Monreal + +- Use the suffix variable correctly in get_hmac_path() +- Rebase libgcrypt-fips_selftest_trigger_file.patch + +------------------------------------------------------------------- +Mon Jan 25 12:38:35 UTC 2021 - Pedro Monreal + +- Add the global config file /etc/gcrypt/random.conf + * This file can be used to globally change parameters of the random + generator with the options: only-urandom and disable-jent. + +------------------------------------------------------------------- +Thu Jan 21 15:42:15 UTC 2021 - Pedro Monreal + +- Update to 1.9.0: + New stable branch of Libgcrypt with full API and ABI compatibility + to the 1.8 series. Release-info: https://dev.gnupg.org/T4294 + * New and extended interfaces: + - New curves Ed448, X448, and SM2. + - New cipher mode EAX. + - New cipher algo SM4. + - New hash algo SM3. + - New hash algo variants SHA512/224 and SHA512/256. + - New MAC algos for Blake-2 algorithms, the new SHA512 variants, + SM3, SM4 and for a GOST variant. + - New convenience function gcry_mpi_get_ui. + - gcry_sexp_extract_param understands new format specifiers to + directly store to integers and strings. + - New function gcry_ecc_mul_point and curve constants for Curve448 + and Curve25519. + - New function gcry_ecc_get_algo_keylen. + - New control code GCRYCTL_AUTO_EXPAND_SECMEM to allow growing the + secure memory area. + * Performance optimizations and bug fixes: See Release-info. + * Other features: + - Add OIDs from RFC-8410 as aliases for Ed25519 and Curve25519. + - Add mitigation against ECC timing attack CVE-2019-13627. + - Internal cleanup of the ECC implementation. + - Support reading EC point in compressed format for some curves. +- Rebase patches: + * libgcrypt-1.4.1-rijndael_no_strict_aliasing.patch + * libgcrypt-1.5.0-LIBGCRYPT_FORCE_FIPS_MODE-env.diff + * libgcrypt-1.6.1-use-fipscheck.patch + * drbg_test.patch + * libgcrypt-fipsdrv-enable-algo-for-dsa-sign.patch + * libgcrypt-FIPS-RSA-DSA-ECDSA-hashing-operation.patch + * libgcrypt-1.8.4-fips-keygen.patch + * libgcrypt-1.8.4-getrandom.patch + * libgcrypt-fix-tests-fipsmode.patch + * libgcrypt-global_init-constructor.patch + * libgcrypt-ecc-ecdsa-no-blinding.patch + * libgcrypt-PCT-RSA.patch + * libgcrypt-PCT-ECC.patch +- Remove patches: + * libgcrypt-unresolved-dladdr.patch + * libgcrypt-CVE-2019-12904-GCM-Prefetch.patch + * libgcrypt-CVE-2019-12904-GCM.patch + * libgcrypt-CVE-2019-12904-AES.patch + * libgcrypt-CMAC-AES-TDES-selftest.patch + * libgcrypt-1.6.1-fips-cfgrandom.patch + * libgcrypt-fips_rsa_no_enforced_mode.patch + +------------------------------------------------------------------- +Sat Oct 24 10:25:13 UTC 2020 - Andreas Stieger + +- libgcrypt 1.8.7: + * Support opaque MPI with gcry_mpi_print + * Fix extra entropy collection via clock_gettime, a fallback code + path for legacy hardware + +------------------------------------------------------------------- +Tue Jul 7 09:12:27 UTC 2020 - Pedro Monreal Gonzalez + +- Update to 1.8.6 + * mpi: Consider +0 and -0 the same in mpi_cmp + * mpi: Fix flags in mpi_copy for opaque MPI + * mpi: Fix the return value of mpi_invm_generic + * mpi: DSA,ECDSA: Fix use of mpi_invm + - Call mpi_invm before _gcry_dsa_modify_k + - Call mpi_invm before _gcry_ecc_ecdsa_sign + * mpi: Constant time mpi_inv with some conditions + - mpi/mpi-inv.c (mpih_add_n_cond, mpih_sub_n_cond, mpih_swap_cond) + - New: mpih_abs_cond, mpi_invm_odd + - Rename from _gcry_mpi_invm: mpi_invm_generic + - Use mpi_invm_odd for usual odd cases: _gcry_mpi_invm + * mpi: Abort on division by zero also in _gcry_mpi_tdiv_qr + * Fix wrong code execution in Poly1305 ARM/NEON implementation + - Set r14 to -1 at function entry: (_gcry_poly1305_armv7_neon_init_ext) + * Set vZZ.16b register to zero before use in armv8 gcm implementation + * random: Fix include of config.h + * Fix declaration of internal function _gcry_mpi_get_ui: Don't use ulong + * ecc: Fix wrong handling of shorten PK bytes + - Zeros are already recovered: (_gcry_ecc_mont_decodepoint) +- Update libgcrypt-ecc-ecdsa-no-blinding.patch + +------------------------------------------------------------------- +Tue May 19 11:25:37 UTC 2020 - Pedro Monreal Gonzalez + +- FIPS: RSA/DSA/ECC test_keys() print out debug messages [bsc#1171872] + * Print the debug messages in test_keys() only in debug mode. +- Update patches: libgcrypt-PCT-RSA.patch libgcrypt-PCT-DSA.patch + libgcrypt-PCT-ECC.patch + +------------------------------------------------------------------- +Mon Apr 27 08:55:12 UTC 2020 - Pedro Monreal Gonzalez + +- FIPS: libgcrypt: Double free in test_keys() on failed signature + verification [bsc#1169944] + * Use safer gcry_mpi_release() instead of mpi_free() +- Update patches: + * libgcrypt-PCT-DSA.patch + * libgcrypt-PCT-RSA.patch + * libgcrypt-PCT-ECC.patch + +------------------------------------------------------------------- +Thu Apr 16 16:45:23 UTC 2020 - Vítězslav Čížek + +- Ship the FIPS checksum file in the shared library package and + create a separate trigger file for the FIPS selftests (bsc#1169569) + * add libgcrypt-fips_selftest_trigger_file.patch + * refresh libgcrypt-global_init-constructor.patch +- Remove libgcrypt-binary_integrity_in_non-FIPS.patch obsoleted + by libgcrypt-global_init-constructor.patch + +------------------------------------------------------------------- +Wed Apr 15 13:55:27 UTC 2020 - Pedro Monreal Gonzalez + +- FIPS: Verify that the generated signature and the original input + differ in test_keys function for RSA, DSA and ECC: [bsc#1165539] +- Add zero-padding when qx and qy have different lengths when + assembling the Q point from affine coordinates. +- Refreshed patches: + * libgcrypt-PCT-DSA.patch + * libgcrypt-PCT-RSA.patch + * libgcrypt-PCT-ECC.patch + +------------------------------------------------------------------- +Mon Mar 30 10:48:02 UTC 2020 - Pedro Monreal Gonzalez + +- FIPS: Switch the PCT to use the new signature operation [bsc#1165539] + * Patches for DSA, RSA and ECDSA test_keys functions: + - libgcrypt-PCT-DSA.patch + - libgcrypt-PCT-RSA.patch + - libgcrypt-PCT-ECC.patch +- Update patch: libgcrypt-FIPS-RSA-DSA-ECDSA-hashing-operation.patch + +------------------------------------------------------------------- +Thu Mar 26 18:09:47 UTC 2020 - Pedro Monreal Gonzalez + +- FIPS: Run self-tests from constructor during power-on [bsc#1166748] + * Set up global_init as the constructor function: + - libgcrypt-global_init-constructor.patch + * Relax the entropy requirements on selftest. This is especially + important for virtual machines to boot properly before the RNG + is available: + - libgcrypt-random_selftests-testentropy.patch + - libgcrypt-rsa-no-blinding.patch + - libgcrypt-ecc-ecdsa-no-blinding.patch + * Fix benchmark regression test in FIPS mode: + - libgcrypt-FIPS-GMAC_AES-benckmark.patch + +------------------------------------------------------------------- +Thu Mar 12 16:54:33 UTC 2020 - Pedro Monreal Gonzalez + +- Remove check not needed in _gcry_global_constructor [bsc#1164950] + * Update libgcrypt-Restore-self-tests-from-constructor.patch + +------------------------------------------------------------------- +Tue Feb 25 22:13:24 UTC 2020 - Pedro Monreal Gonzalez + +- FIPS: Run the self-tests from the constructor [bsc#1164950] + * Add libgcrypt-invoke-global_init-from-constructor.patch + +------------------------------------------------------------------- +Fri Jan 17 17:35:15 UTC 2020 - Pedro Monreal Gonzalez + +- FIPS: libgcrypt DSA PQG parameter generation: Missing value [bsc#1161219] +- FIPS: libgcrypt DSA PQG verification incorrect results [bsc#1161215] +- FIPS: libgcrypt RSA siggen/keygen: 4k not supported [bsc#1161220] + * Add patch from Fedora libgcrypt-1.8.4-fips-keygen.patch + +------------------------------------------------------------------- +Wed Dec 11 10:18:23 UTC 2019 - Pedro Monreal Gonzalez + +- FIPS: RSA/DSA/ECDSA are missing hashing operation [bsc#1155337] + * Add libgcrypt-FIPS-RSA-DSA-ECDSA-hashing-operation.patch + +------------------------------------------------------------------- +Wed Nov 27 14:01:01 UTC 2019 - Pedro Monreal Gonzalez + +- Fix tests in FIPS mode: + * Fix tests: basic benchmark bench-slope pubkey t-cv25519 t-secmem + * Add patch libgcrypt-fix-tests-fipsmode.patch + +------------------------------------------------------------------- +Tue Nov 26 18:48:20 UTC 2019 - Pedro Monreal Gonzalez + +- Fix test dsa-rfc6979 in FIPS mode: + * Disable tests in elliptic curves with 192 bits which are not + recommended in FIPS mode + * Add patch libgcrypt-dsa-rfc6979-test-fix.patch + +------------------------------------------------------------------- +Tue Nov 12 11:05:02 UTC 2019 - Pedro Monreal Gonzalez + +- CMAC AES and TDES FIPS self-tests: + * CMAC AES self test missing [bsc#1155339] + * CMAC TDES self test missing [bsc#1155338] +- Add libgcrypt-CMAC-AES-TDES-selftest.patch + +------------------------------------------------------------------- +Fri Aug 30 14:17:48 UTC 2019 - Andreas Stieger + +- libgcrypt 1.8.5: + * CVE-2019-13627: mitigation against an ECDSA timing attack (boo#1148987) + * Improve ECDSA unblinding + * Provide a pkg-config file + +------------------------------------------------------------------- +Wed Jun 26 06:52:54 UTC 2019 - Jason Sikes + +- Fixed redundant fips tests in some situations causing sudo to stop + working when pam-kwallet is installed. bsc#1133808 + * Added libgcrypt-1.8.4-fips_ctor_skip_integrity_check.patch + * Removed libgcrypt-fips_run_selftest_at_constructor.patch + because it was obsoleted by libgcrypt-1.8.3-fips-ctor.patch + * Removed libgcrypt-fips_ignore_FIPS_MODULE_PATH.patch + because it was obsoleted by libgcrypt-1.8.4-fips_ctor_skip_integrity_check.patch + +------------------------------------------------------------------- +Fri Jun 21 16:53:07 UTC 2019 - Pedro Monreal Gonzalez + +- Fixed env-script-interpreter in cavs_driver.pl + +------------------------------------------------------------------- +Fri Jun 21 16:39:00 UTC 2019 - Pedro Monreal Gonzalez + +- Security fix: [bsc#1138939, CVE-2019-12904] + * The C implementation of AES is vulnerable to a flush-and-reload + side-channel attack because physical addresses are available to + other processes. (The C implementation is used on platforms where + an assembly-language implementation is unavailable.) + * Added patches: + - libgcrypt-CVE-2019-12904-GCM-Prefetch.patch + - libgcrypt-CVE-2019-12904-GCM.patch + - libgcrypt-CVE-2019-12904-AES.patch + +------------------------------------------------------------------- +Fri Apr 26 06:47:45 UTC 2019 - Jason Sikes + +- do not try to open /dev/urandom if getrandom() works + * Added libgcrypt-1.8.4-getrandom.patch +- Drop libgcrypt-init-at-elf-load-fips.patch obsoleted + by libgcrypt-1.8.3-fips-ctor.patch + +------------------------------------------------------------------- +Tue Apr 23 12:38:40 UTC 2019 - Jason Sikes + +- Restored libgcrypt-binary_integrity_in_non-FIPS.patch sans section that + was partially causing bsc#1131183. +- Fixed race condition in multi-threaded applications by allowing a FSM state + transition to the current state. This means some tests are run twice. + * Added libgcrypt-1.8.4-allow_FSM_same_state.patch +- Fixed an issue in malloc/free wrappers so that memory created by the malloc() + wrappers will be destroyed using the free() wrappers. + * Added libgcrypt-1.8.4-use_xfree.patch + +------------------------------------------------------------------- +Fri Apr 5 21:56:00 UTC 2019 - Jason Sikes + +- removed libgcrypt-binary_integrity_in_non-FIPS.patch since it was breaking + libotr. bsc#1131183 + +------------------------------------------------------------------- +Tue Mar 26 16:30:23 UTC 2019 - Vítězslav Čížek + +- libgcrypt-1.8.3-fips-ctor.patch changed the way the fips selftests + are invoked as well as the state transition, adjust the code so + a missing checksum file is not an issue in non-FIPS mode (bsc#1097073) + * update libgcrypt-binary_integrity_in_non-FIPS.patch + +------------------------------------------------------------------- +Tue Mar 26 16:25:18 UTC 2019 - Vítězslav Čížek + +- Enforce the minimal RSA keygen size in fips mode (bsc#1125740) + * add libgcrypt-fips_rsa_no_enforced_mode.patch + +------------------------------------------------------------------- +Fri Mar 22 14:13:05 UTC 2019 - Vítězslav Čížek + +- Don't run full self-tests from constructor (bsc#1097073) + * Don't call global_init() from the constructor, _gcry_global_constructor() + from libgcrypt-1.8.3-fips-ctor.patch takes care of the binary + integrity check instead. + * Only the binary checksum will be verified, the remaining + self-tests will be run upon the library initialization +- Add libgcrypt-fips_ignore_FIPS_MODULE_PATH.patch +- Drop libgcrypt-init-at-elf-load-fips.patch and + libgcrypt-fips_run_selftest_at_constructor.patch obsoleted + by libgcrypt-1.8.3-fips-ctor.patch + +------------------------------------------------------------------- +Thu Mar 7 10:53:40 UTC 2019 - Pedro Monreal Gonzalez + +- Skip all the self-tests except for binary integrity when called + from the constructor (bsc#1097073) + * Added libgcrypt-1.8.3-fips-ctor.patch from Fedora + +------------------------------------------------------------------- +Mon Nov 26 17:09:47 UTC 2018 - Vítězslav Čížek + +- Fail selftests when checksum file is missing in FIPS mode only + (bsc#1117355) + * add libgcrypt-binary_integrity_in_non-FIPS.patch + +------------------------------------------------------------------- +Sun Oct 28 18:57:53 UTC 2018 - astieger@suse.com + +- libgcrypt 1.8.4: + * Fix infinite loop with specific application implementations + * Fix possible leak of a few bits of secret primes to pageable + memory + * Fix possible hang in the RNG (1.8.3) + * Always make use of getrandom if possible and then use + its /dev/urandom behaviour + +------------------------------------------------------------------- +Mon Jul 2 10:38:42 UTC 2018 - schwab@suse.de + +- libgcrypt-1.6.3-aliasing.patch, libgcrypt-ppc64.patch, + libgcrypt-strict-aliasing.patch: Remove obsolete patches +- libgcrypt-1.4.1-rijndael_no_strict_aliasing.patch: Rediff +- Reenable testsuite + +------------------------------------------------------------------- +Wed Jun 13 10:46:33 UTC 2018 - kbabioch@suse.com + +- Update to version 1.8.3: + - Use blinding for ECDSA signing to mitigate a novel side-channel + attack. (CVE-2018-0495 bsc#1097410) + - Fix incorrect counter overflow handling for GCM when using an IV + size other than 96 bit. + - Fix incorrect output of AES-keywrap mode for in-place encryption + on some platforms. + - Fix the gcry_mpi_ec_curve_point point validation function. + - Fix rare assertion failure in gcry_prime_check. +- Applied spec-cleaner + +------------------------------------------------------------------- +Wed May 2 14:31:07 UTC 2018 - pmonrealgonzalez@suse.com + +- Suggest libgcrypt20-hmac for package libgcrypt20 to ensure they + are installed in the right order. [bsc#1090766] + +------------------------------------------------------------------- +Thu Mar 29 06:37:44 UTC 2018 - pmonrealgonzalez@suse.com + +- Extended the fipsdrv dsa-sign and dsa-verify commands with the + --algo parameter for the FIPS testing of DSA SigVer and SigGen + (bsc#1064455). + * Added libgcrypt-fipsdrv-enable-algo-for-dsa-sign.patch + * Added libgcrypt-fipsdrv-enable-algo-for-dsa-verify.patch + +------------------------------------------------------------------- +Thu Feb 22 15:10:36 UTC 2018 - fvogt@suse.com + +- Use %license (boo#1082318) + +------------------------------------------------------------------- +Wed Dec 13 20:09:28 UTC 2017 - astieger@suse.com + +- libgcrypt 1.8.2: + * Fix fatal out of secure memory status in the s-expression + parser on heavy loaded systems. + * Add auto expand secmem feature or use by GnuPG 2.2.4 + +------------------------------------------------------------------- +Mon Aug 28 17:54:24 UTC 2017 - astieger@suse.com + +- libgcrypt 1.8.1: + * Mitigate a local side-channel attack on Curve25519 dubbed "May + the Fourth be With You" CVE-2017-0379 bsc#1055837 + * Add more extra bytes to the pool after reading a seed file + * Add the OID SHA384WithECDSA from RFC-7427 to SHA-384 + * Fix build problems with the Jitter RNG + * Fix assembler code build problems on Rasbian (ARMv8/AArch32-CE) + +------------------------------------------------------------------- +Mon Jul 24 23:43:40 UTC 2017 - jengelh@inai.de + +- RPM group fixes. + +------------------------------------------------------------------- +Fri Jul 21 15:50:14 UTC 2017 - astieger@suse.com + +- libgcrypt 1.8.0: + * New cipher mode XTS + * New hash function Blake-2 + * New function gcry_mpi_point_copy. + * New function gcry_get_config. + * GCRYCTL_REINIT_SYSCALL_CLAMP allows to init nPth after Libgcrypt. + * New gobal configuration file /etc/gcrypt/random.conf. + * GCRYCTL_PRINT_CONFIG does now also print build information for + libgpg-error and the used compiler version. + * GCRY_CIPHER_MODE_CFB8 is now supported. + * A jitter based entropy collector is now used in addition to the + other entropy collectors. + * Optimized gcry_md_hash_buffers for SHA-256 and SHA-512. + random pool lock). + * Interface changes relative to the 1.7.0 release: + gcry_get_config NEW function. + gcry_mpi_point_copy NEW function. + GCRYCTL_REINIT_SYSCALL_CLAMP NEW macro. + GCRY_MD_BLAKE2B_512 NEW constant. + GCRY_MD_BLAKE2B_384 NEW constant. + GCRY_MD_BLAKE2B_256 NEW constant. + GCRY_MD_BLAKE2B_160 NEW constant. + GCRY_MD_BLAKE2S_256 NEW constant. + GCRY_MD_BLAKE2S_224 NEW constant. + GCRY_MD_BLAKE2S_160 NEW constant. + GCRY_MD_BLAKE2S_128 NEW constant. + GCRY_CIPHER_MODE_XTS NEW constant. + gcry_md_info DEPRECATED. +- Refresh patch libgcrypt-1.6.3-aliasing.patch + +------------------------------------------------------------------- +Thu Jun 29 09:49:44 UTC 2017 - astieger@suse.com + +- libgcrypt 1.7.8: + * CVE-2017-7526: Mitigate a flush+reload side-channel attack on + RSA secret keys (bsc#1046607) + +------------------------------------------------------------------- +Sun Jun 4 19:26:12 UTC 2017 - astieger@suse.com + +- libgcrypt 1.7.7: + * Fix possible timing attack on EdDSA session key (previously + patched, drop libgcrypt-secure-EdDSA-session-key.patch) + * Fix long standing bug in secure memory implementation which + could lead to a segv on free + +------------------------------------------------------------------- +Fri Jun 2 10:05:18 UTC 2017 - pmonrealgonzalez@suse.com + +- Added libgcrypt-secure-EdDSA-session-key.patch [bsc#1042326] + * Store the session key in secure memory to ensure that constant + time point operations are used in the MPI library. + +------------------------------------------------------------------- +Fri Jan 20 09:41:15 UTC 2017 - rmaliska@suse.com + +- libgcrypt 1.7.6: + * Fix counter operand from read-only to read/write + * Fix too large jump alignment in mpih-rshift + +------------------------------------------------------------------- +Thu Dec 15 10:32:18 UTC 2016 - astieger@suse.com + +- libgcrypt 1.7.5: + * Fix regression in mlock detection introduced with 1.7.4 + +------------------------------------------------------------------- +Tue Dec 13 12:20:47 UTC 2016 - astieger@suse.com + +- libgcrypt 1.7.4: + * ARMv8/AArch32 performance improvements for AES, GCM, SHA-256, + and SHA-1. + * Add ARMv8/AArch32 assembly implementation for Twofish and + Camellia. + * Add bulk processing implementation for ARMv8/AArch32. + * Add Stribog OIDs. + * Improve the DRBG performance and sync the code with the Linux + version. + * When secure memory is requested by the MPI functions or by + gcry_xmalloc_secure, they do not anymore lead to a fatal error + if the secure memory pool is used up. Instead new pools are + allocated as needed. These new pools are not protected against + being swapped out (mlock can't be used). Mitigation for + minor confidentiality issues is encryption swap space. + * Fix GOST 28147 CryptoPro-B S-box. + * Fix error code handling of mlock calls. + +------------------------------------------------------------------- +Sat Aug 20 10:38:15 UTC 2016 - mpluskal,vcizek,astieger}@suse.com + +- libgcrypt 1.7.3: + * security issue already fixes with 1.6.6 + * Fix building of some asm modules with older compilers and CPUs. + * ARMv8/AArch32 improvements for AES, GCM, SHA-256, and SHA-1. +- includes changes from libgcrypt 1.7.2: + * Bug fixes: + - Fix setting of the ECC cofactor if parameters are specified. + - Fix memory leak in the ECC code. + - Remove debug message about unsupported getrandom syscall. + - Fix build problems related to AVX use. + - Fix bus errors on ARM for Poly1305, ChaCha20, AES, and SHA-512. + * Internal changes: + - Improved fatal error message for wrong use of gcry_md_read. + - Disallow symmetric encryption/decryption if key is not set. +- includes changes from 1.7.1: + * Bug fixes: + - Fix ecc_verify for cofactor support. + - Fix portability bug when using gcc with Solaris 9 SPARC. + - Build fix for OpenBSD/amd64 + - Add OIDs to the Serpent ciphers. + * Internal changes: + - Use getrandom system call on Linux if available. + - Blinding is now also used for RSA signature creation. + - Changed names of debug envvars +- includes changes from 1.7.0: + * New algorithms and modes: + - SHA3-224, SHA3-256, SHA3-384, SHA3-512, and MD2 hash algorithms. + - SHAKE128 and SHAKE256 extendable-output hash algorithms. + - ChaCha20 stream cipher. + - Poly1305 message authentication algorithm + - ChaCha20-Poly1305 Authenticated Encryption with Associated Data + mode. + - OCB mode. + - HMAC-MD2 for use by legacy applications. + * New curves for ECC: + - Curve25519. + - sec256k1. + - GOST R 34.10-2001 and GOST R 34.10-2012. + * Performance: + - Improved performance of KDF functions. + - Assembler optimized implementations of Blowfish and Serpent on + ARM. + - Assembler optimized implementation of 3DES on x86. + - Improved AES using the SSSE3 based vector permutation method by + Mike Hamburg. + - AVX/BMI is used for SHA-1 and SHA-256 on x86. This is for SHA-1 + about 20% faster than SSSE3 and more than 100% faster than the + generic C implementation. + - 40% speedup for SHA-512 and 72% for SHA-1 on ARM Cortex-A8. + - 60-90% speedup for Whirlpool on x86. + - 300% speedup for RIPE MD-160. + - Up to 11 times speedup for CRC functions on x86. + * Other features: + - Improved ECDSA and FIPS 186-4 compliance. + - Support for Montgomery curves. + - gcry_cipher_set_sbox to tweak S-boxes of the gost28147 cipher + algorithm. + - gcry_mpi_ec_sub to subtract two points on a curve. + - gcry_mpi_ec_decode_point to decode an MPI into a point object. + - Emulation for broken Whirlpool code prior to 1.6.0. [from 1.6.1] + - Flag "pkcs1-raw" to enable PCKS#1 padding with a user supplied + hash part. + - Parameter "saltlen" to set a non-default salt length for RSA PSS. + - A SP800-90A conforming DRNG replaces the former X9.31 alternative + random number generator. + - Map deprecated RSA algo number to the RSA algo number for better + backward compatibility. [from 1.6.2] + - Use ciphertext blinding for Elgamal decryption [CVE-2014-3591]. + See http://www.cs.tau.ac.il/~tromer/radioexp/ for details. + [from 1.6.3] + - Fixed data-dependent timing variations in modular exponentiation + [related to CVE-2015-0837, Last-Level Cache Side-Channel Attacks + are Practical]. [from 1.6.3] + - Flag "no-keytest" for ECC key generation. Due to a bug in + the parser that flag will also be accepted but ignored by older + version of Libgcrypt. [from 1.6.4] + - Speed up the random number generator by requiring less extra + seeding. [from 1.6.4] + - Always verify a created RSA signature to avoid private key leaks + due to hardware failures. [from 1.6.4] + - Mitigate side-channel attack on ECDH with Weierstrass curves + [CVE-2015-7511]. See http://www.cs.tau.ac.IL/~tromer/ecdh/ for + details. [from 1.6.5] + * Internal changes: + - Moved locking out to libgpg-error. + - Support of the SYSROOT envvar in the build system. + - Refactor some code. + - The availability of a 64 bit integer type is now mandatory. + * Bug fixes: + - Fixed message digest lookup by OID (regression in 1.6.0). + - Fixed a build problem on NetBSD + - Fixed some asm build problems and feature detection bugs. + * Interface changes relative to the 1.6.0 release: + gcry_cipher_final NEW macro. + GCRY_CIPHER_MODE_CFB8 NEW constant. + GCRY_CIPHER_MODE_OCB NEW. + GCRY_CIPHER_MODE_POLY1305 NEW. + gcry_cipher_set_sbox NEW macro. + gcry_mac_get_algo NEW. + GCRY_MAC_HMAC_MD2 NEW. + GCRY_MAC_HMAC_SHA3_224 NEW. + GCRY_MAC_HMAC_SHA3_256 NEW. + GCRY_MAC_HMAC_SHA3_384 NEW. + GCRY_MAC_HMAC_SHA3_512 NEW. + GCRY_MAC_POLY1305 NEW. + GCRY_MAC_POLY1305_AES NEW. + GCRY_MAC_POLY1305_CAMELLIA NEW. + GCRY_MAC_POLY1305_SEED NEW. + GCRY_MAC_POLY1305_SERPENT NEW. + GCRY_MAC_POLY1305_TWOFISH NEW. + gcry_md_extract NEW. + GCRY_MD_FLAG_BUGEMU1 NEW [from 1.6.1]. + GCRY_MD_GOSTR3411_CP NEW. + GCRY_MD_SHA3_224 NEW. + GCRY_MD_SHA3_256 NEW. + GCRY_MD_SHA3_384 NEW. + GCRY_MD_SHA3_512 NEW. + GCRY_MD_SHAKE128 NEW. + GCRY_MD_SHAKE256 NEW. + gcry_mpi_ec_decode_point NEW. + gcry_mpi_ec_sub NEW. + GCRY_PK_EDDSA NEW constant. + GCRYCTL_GET_TAGLEN NEW. + GCRYCTL_SET_SBOX NEW. + GCRYCTL_SET_TAGLEN NEW. +- Apply libgcrypt-1.6.3-aliasing.patch only on big-endian + architectures +- update drbg_test.patch and install cavs testing directory again +- As DRBG is upstream, drop pateches: + v9-0001-SP800-90A-Deterministic-Random-Bit-Generator.patch + 0002-Compile-DRBG.patch + 0003-Function-definitions-of-interfaces-for-random.c.patch + 0004-Invoke-DRBG-from-common-libgcrypt-RNG-code.patch + 0005-Function-definitions-for-gcry_control-callbacks.patch + 0006-DRBG-specific-gcry_control-requests.patch + v9-0007-User-interface-to-DRBG.patch + libgcrypt-fix-rng.patch +- drop obsolete: + libgcrypt-fips-dsa.patch + libgcrypt-fips_ecdsa.patch + +------------------------------------------------------------------- +Wed Aug 17 18:21:44 UTC 2016 - astieger@suse.com + +- libgcrypt 1.6.6: + * fix CVE-2016-6313: Issue in the mixing functions of the random + number generators allowed an attacker who obtained a number of + bytes from the standard RNG to predict some of the next ouput. + (bsc#994157) + +------------------------------------------------------------------- +Mon May 16 14:37:45 UTC 2016 - pjanouch@suse.de + +- remove conditionals for unsupported distributions (before 13.2), + it would not build anyway because of new dependencies + +------------------------------------------------------------------- +Mon May 16 12:36:14 UTC 2016 - pjanouch@suse.de + +- make the -hmac package depend on the same version of the library, + fixing bsc#979629 FIPS: system fails to reboot after installing + fips pattern + +------------------------------------------------------------------- +Tue Feb 9 20:51:59 UTC 2016 - astieger@suse.com + +- update to 1.6.5: + * CVE-2015-7511: Mitigate side-channel attack on ECDH with + Weierstrass curves (boo#965902) + +------------------------------------------------------------------- +Sat Oct 10 11:56:08 UTC 2015 - astieger@suse.com + +- follow-up to libgcrypt 1.6.4 update: sosuffix is 20.0.4 + +------------------------------------------------------------------- +Tue Sep 8 08:03:19 UTC 2015 - vcizek@suse.com + +- update to 1.6.4 +- fixes libgcrypt equivalent of CVE-2015-5738 (bsc#944456) + * Speed up the random number generator by requiring less extra + seeding. + * New flag "no-keytest" for ECC key generation. Due to a bug in the + parser that flag will also be accepted but ignored by older version + of Libgcrypt. + * Always verify a created RSA signature to avoid private key leaks + due to hardware failures. + * Other minor bug fixes. + +------------------------------------------------------------------- +Tue Jun 23 15:15:30 UTC 2015 - dvaleev@suse.com + +- Fix gpg2 tests on BigEndian architectures: s390x ppc64 + libgcrypt-1.6.3-aliasing.patch + +------------------------------------------------------------------- +Sun Mar 1 21:16:26 UTC 2015 - astieger@suse.com + +- fix sosuffix for 1.6.3 (20.0.3) + +------------------------------------------------------------------- +Sat Feb 28 19:31:10 UTC 2015 - astieger@suse.com + +- libgcrypt 1.6.3 [bnc#920057]: + * Use ciphertext blinding for Elgamal decryption [CVE-2014-3591]. + * Fixed data-dependent timing variations in modular exponentiation + [related to CVE-2015-0837, Last-Level Cache Side-Channel Attacks + are Practical]. +- update upstream signing keyring + +------------------------------------------------------------------- +Fri Feb 6 18:42:28 UTC 2015 - coolo@suse.com + +- making the build reproducible - see + http://lists.gnupg.org/pipermail/gnupg-commits/2014-September/010683.html + for a very similiar problem + +------------------------------------------------------------------- +Fri Feb 6 18:38:55 UTC 2015 - dimstar@opensuse.org + +- Move %install_info_delete calls from postun to preun: the files + must still be present to be parsed. +- Fix the names passed to install_info for gcrypt.info-[12].gz + instead of gcrypt-[12].info.gz. + +------------------------------------------------------------------- +Fri Feb 6 18:30:26 UTC 2015 - coolo@suse.com + +- fix filename for info pages in %post scripts + +------------------------------------------------------------------- +Wed Nov 5 20:37:24 UTC 2014 - andreas.stieger@gmx.de + +- libgcrypt 1.6.2: + * Map deprecated RSA algo number to the RSA algo number for better + backward compatibility. + * Support a 0x40 compression prefix for EdDSA. + * Improve ARM hardware feature detection and building. + * Fix building for the x32 ABI platform. + * Fix some possible NULL deref bugs. +- remove libgcrypt-1.6.0-use-intenal-functions.patch, upstream + via xtrymalloc macro +- remove libgcrypt-fixed-sizet.patch, upstream +- adjust libgcrypt-1.6.1-use-fipscheck.patch for xtrymalloc change + +------------------------------------------------------------------- +Sun Sep 21 10:08:39 UTC 2014 - vcizek@suse.com + +- disabled curve P-192 in FIPS mode (bnc#896202) + * added libgcrypt-fips_ecdsa.patch +- don't use SHA-1 for ECDSA in FIPS mode +- also run the fips self tests only in FIPS mode + +------------------------------------------------------------------- +Tue Sep 16 13:56:01 UTC 2014 - vcizek@suse.com + +- run the fips self tests at the constructor code + * added libgcrypt-fips_run_selftest_at_constructor.patch + +------------------------------------------------------------------- +Tue Sep 16 12:17:17 UTC 2014 - vcizek@suse.com + +- rewrite the DSA-2 code to be FIPS 186-4 compliant (bnc#894216) + * added libgcrypt-fips-dsa.patch + * install fips186_dsa +- use 2048 bit keys in selftests_dsa + +------------------------------------------------------------------- +Mon Sep 1 10:57:06 UTC 2014 - vcizek@suse.com + +- fix an issue in DRBG patchset + * size_t type is 32-bit on 32-bit systems +- fix a potential NULL pointer deference in DRBG patchset + * patches from https://bugs.g10code.com/gnupg/issue1701 +- added v9-0001-SP800-90A-Deterministic-Random-Bit-Generator.patch +- added v9-0007-User-interface-to-DRBG.patch +- removed v7-0001-SP800-90A-Deterministic-Random-Bit-Generator.patch +- removed v7-0007-User-interface-to-DRBG.patch +- add a subpackage for CAVS testing + * add cavs_driver.pl and cavs-test.sh from the kernel cavs package + * added drbg_test.patch + +------------------------------------------------------------------- +Tue Aug 12 07:43:19 UTC 2014 - meissner@suse.com + +- split off the -hmac package that contains the checksums + +------------------------------------------------------------------- +Mon May 26 12:05:17 UTC 2014 - meissner@suse.com + +- libgcrypt-fix-rng.patch: make drbg work again in FIPS mode. +- libgcrypt-1.6.1-use-fipscheck.patch: library to test is libgcrypt.so.20 + and not libgcrypt.so.11 +- libgcrypt-init-at-elf-load-fips.patch: initialize globally on ELF + DSO loading to meet FIPS requirements. + +------------------------------------------------------------------- +Tue May 13 10:47:51 UTC 2014 - vcizek@suse.com + +- add new 0007-User-interface-to-DRBG.patch from upstream + * fixes bnc#877233 + * supersedes the patch from previous entry + +------------------------------------------------------------------- +Sun May 12 13:25:33 UTC 2014 - tittiatcoke@gmail.com + +- Correct patch 0007-User-interface-to-DRBG.patch so that the + struct used in the route matches the header of the function + +------------------------------------------------------------------- +Tue May 6 13:28:33 UTC 2014 - vcizek@suse.com + +- add support for SP800-90A DRBG (fate#316929, bnc#856312) + * patches by Stephan Mueller (http://www.chronox.de/drbg.html): + 0001-SP800-90A-Deterministic-Random-Bit-Generator.patch.bz2 + 0002-Compile-DRBG.patch + 0003-Function-definitions-of-interfaces-for-random.c.patch + 0004-Invoke-DRBG-from-common-libgcrypt-RNG-code.patch + 0005-Function-definitions-for-gcry_control-callbacks.patch + 0006-DRBG-specific-gcry_control-requests.patch + 0007-User-interface-to-DRBG.patch + * only after 13.1 (the patches need libgpg-error 1.13) +- drop libgcrypt-fips-allow-legacy.patch (not needed and wasn't + applied anyway) + +------------------------------------------------------------------- +Thu Apr 3 12:04:46 UTC 2014 - tchvatal@suse.com + +- Cleanup with spec-cleaner to sort out. +- Really apply ppc64 patch as it was ommited probably by mistake. + +------------------------------------------------------------------- +Thu Mar 27 14:57:22 UTC 2014 - meissner@suse.com + +- FIPS changes (from Fedora): + - replaced libgcrypt-1.5.0-etc_gcrypt_rngseed-symlink.diff by + libgcrypt-1.6.1-fips-cfgrandom.patch + - libgcrypt-fixed-sizet.patch: fixed an int type for -flto + - libgcrypt-1.6.1-use-fipscheck.patch: use the fipscheck binary + - libgcrypt-1.6.1-fips-cavs.patch: add CAVS tests +- use fipscheck only after 13.1 +- libgcrypt-fips-allow-legacy.patch: attempt to allow some + legacy algorithms for gpg2 usage even in FIPS mode. + (currently not applied) + +------------------------------------------------------------------- +Thu Jan 30 13:29:49 UTC 2014 - idonmez@suse.com + +- Drop arm-missing-files.diff, fixed upstream + +------------------------------------------------------------------- +Wed Jan 29 18:40:49 UTC 2014 - andreas.stieger@gmx.de + +- libgcrypt 1.6.1, a bugfix release with the folloging fixes: + * Added emulation for broken Whirlpool code prior to 1.6.0. + * Improved performance of KDF functions. + * Improved ECDSA compliance. + * Fixed message digest lookup by OID (regression in 1.6.0). + * Fixed memory leaks in ECC code. + * Fixed some asm build problems and feature detection bugs. + * Interface changes relative to the 1.6.0 release: + GCRY_MD_FLAG_BUGEMU1 NEW (minor API change). + +------------------------------------------------------------------- +Fri Jan 3 16:36:21 UTC 2014 - dmueller@suse.com + +- add arm-missing-files.diff: Add missing files to fix build + +------------------------------------------------------------------- +Fri Jan 3 09:43:39 UTC 2014 - mvyskocil@suse.com + +- fix bnc#856915: can't open /dev/urandom + * correct libgcrypt-1.5.0-etc_gcrypt_rngseed-symlink.diff +- require libgpg-error 1.11 or higher + +------------------------------------------------------------------- +Thu Dec 19 13:53:21 UTC 2013 - mvyskocil@suse.com + +- fix dependency for 32bit devel package +- name hmac files according soname +- fix hmac subpackage dependency + +------------------------------------------------------------------- +Thu Dec 19 09:03:21 UTC 2013 - mvyskocil@suse.com + +- update to 1.6. + * Removed the long deprecated gcry_ac interface. Thus Libgcrypt is + not anymore ABI compatible to previous versions if they used the ac + interface. Check NEWS in libgcrypt-devel for removed interfaces. + * Removed the module register subsystem. + * The deprecated message digest debug macros have been removed. Use + gcry_md_debug instead. + * Removed deprecated control codes. + * Improved performance of most cipher algorithms as well as for the + SHA family of hash functions. + * Added support for the IDEA cipher algorithm. + * Added support for the Salsa20 and reduced Salsa20/12 stream ciphers. + * Added limited support for the GOST 28147-89 cipher algorithm. + * Added support for the GOST R 34.11-94 and R 34.11-2012 (Stribog) + hash algorithms. + * Added a random number generator to directly use the system's RNG. + Also added an interface to prefer the use of a specified RNG. + * Added support for the SCRYPT algorithm. + * Mitigated the Yarom/Falkner flush+reload side-channel attack on RSA + secret keys. See [CVE-2013-4242]. + * Added support for Deterministic DSA as per RFC-6969. + * Added support for curve Ed25519. + * Added a scatter gather hash convenience function. + * Added several MPI amd SEXP helper functions. + * Added support for negative numbers to gcry_mpi_print, + gcry_mpi_aprint and gcry_mpi_scan. + * The algorithm ids GCRY_PK_ECDSA and GCRY_PK_ECDH are now + deprecated. Use GCRY_PK_ECC if you need an algorithm id. + * Changed gcry_pk_genkey for "ecc" to only include the curve name and + not the parameters. The flag "param" may be used to revert this. + * Added a feature to globally disable selected hardware features. + * Added debug helper functions. +- rebased patches + * libgcrypt-1.5.0-etc_gcrypt_rngseed-symlink.diff + * libgcrypt-ppc64.patch +- add libgcrypt-1.6.0-use-intenal-functions.patch to fix fips.c build +- Move all documentation to -devel package + +------------------------------------------------------------------- +Fri Jul 26 22:05:46 UTC 2013 - andreas.stieger@gmx.de + +- update to 1.5.3 [bnc#831359] CVE-2013-4242 + * Mitigate the Yarom/Falkner flush+reload side-channel attack on + RSA secret keys. See . + +------------------------------------------------------------------- +Thu Jul 25 09:15:43 UTC 2013 - mvyskocil@suse.com + +- port SLE enhancenments to Factory (bnc#831028) + * add libgcrypt-unresolved-dladdr.patch (bnc#701267) + * add libgcrypt-1.5.0-etc_gcrypt_rngseed-symlink.diff (bnc#724841) + * add libgcrypt-1.5.0-LIBGCRYPT_FORCE_FIPS_MODE-env.diff +- install .hmac256.hmac (bnc#704068) +- enable varuous new options in configure (m-guard, hmac binary check and + random device linux) +- build with all ciphers, pubkeys and digest by default as whitelist + simply allowed them all + +------------------------------------------------------------------- +Mon Jun 17 13:22:33 UTC 2013 - coolo@suse.com + +- avoid gpg-offline in bootstrap packages + +------------------------------------------------------------------- +Sun Jun 16 22:56:56 UTC 2013 - crrodriguez@opensuse.org + +- Library must be built with large file support in + 32 bit archs. + +------------------------------------------------------------------- +Thu Apr 18 18:23:36 UTC 2013 - andreas.stieger@gmx.de + +- update to 1.5.2 + * The upstream sources now contain the IDEA algorithm, dropping: + idea.c.gz + libgcrypt-1.5.0-idea.patch + libgcrypt-1.5.0-idea_codecleanup.patch + * Made the Padlock code work again (regression since 1.5.0). + * Fixed alignment problems for Serpent. + * Fixed two bugs in ECC computations. + +------------------------------------------------------------------- +Fri Mar 22 09:31:11 UTC 2013 - mvyskocil@suse.com + +- add GPL3.0+ to License tag because of dumpsexp (bnc#810759) + +------------------------------------------------------------------- +Mon Mar 18 20:41:00 UTC 2013 - andreas.stieger@gmx.de + +- update to 1.5.1 + * Allow empty passphrase with PBKDF2. + * Do not abort on an invalid algorithm number in + gcry_cipher_get_algo_keylen and gcry_cipher_get_algo_blklen. + * Fixed some Valgrind warnings. + * Fixed a problem with select and high fd numbers. + * Improved the build system + * Various minor bug fixes. + * Interface changes relative to the 1.5.0 release: + GCRYCTL_SET_ENFORCED_FIPS_FLAG NEW. + GCRYPT_VERSION_NUMBER NEW. +- add verification of source code signatures +- now requires automake 1.11 to build + +------------------------------------------------------------------- +Sat Feb 2 18:51:33 UTC 2013 - coolo@suse.com + +- update license to new format + +------------------------------------------------------------------- +Tue Jun 12 21:19:18 UTC 2012 - chris@computersalat.de + +- fix deps + * libgpg-error-devel >= 1.8 +- add libsoname macro + +------------------------------------------------------------------- +Sun Feb 12 15:23:56 UTC 2012 - crrodriguez@opensuse.org + +- Libraries back into %{_libdir}, /usr merge project + +------------------------------------------------------------------- +Sat Dec 24 23:51:26 UTC 2011 - opensuse@dstoecker.de + +- add the missing IDEA algorithm after the patent is no longer relevant + +------------------------------------------------------------------ +Sun Nov 13 14:37:29 UTC 2011 - jengelh@medozas.de + +- Remove redundant/unwanted tags/section (cf. specfile guidelines) + +------------------------------------------------------------------- +Sun Nov 13 09:16:36 UTC 2011 - coolo@suse.com + +- add libtool as explicit buildrequire to avoid implicit dependency from prjconf + +------------------------------------------------------------------- +Sun Oct 2 18:38:28 UTC 2011 - crrodriguez@opensuse.org + +- Update to version 1.5.0, most important changes + * Uses the Intel AES-NI instructions if available + * Support ECDH. + +------------------------------------------------------------------- +Fri Nov 19 09:59:41 UTC 2010 - mvyskocil@suse.cz + +- update to 1.4.6 + * Fixed minor memory leak in DSA key generation. + * No more switching to FIPS mode if /proc/version is not readable. + * Fixed a sigill during Padlock detection on old CPUs. + * Boosted SHA-512 performance by 30% on ia32 boxes and gcc 4.3; + SHA-256 went up by 25%. + * New variants of the TIGER algorithm. + * New cipher algorithm mode for AES-WRAP. + * Interface changes relative to the 1.4.2 release: + GCRY_MD_TIGER1 NEW + GCRY_MD_TIGER2 NEW + GCRY_CIPHER_MODE_AESWRAP NEW + +------------------------------------------------------------------- +Sun Jul 4 19:07:16 UTC 2010 - jengelh@medozas.de + +- add missing definition of udiv_qrnnd for sparcv9:32 +- use %_smp_mflags + +------------------------------------------------------------------- +Sat Dec 19 12:58:20 CET 2009 - jengelh@medozas.de + +- add baselibs.conf as a source +- disable the use of hand-coded assembler functions on sparc - + this is giving me an infinite loop with ./tests/prime + (specifically ./sparc32v8/mpih-mul1.S:_gcry_mpih_mul_1. + Fedora disables this too. + +------------------------------------------------------------------- +Tue Apr 7 15:45:06 CEST 2009 - crrodriguez@suse.de + +- update to version 1.4.4 + * Publish GCRY_MODULE_ID_USER and GCRY_MODULE_ID_USER_LAST constants. + This functionality has been in Libgcrypt since 1.3.0. + * MD5 may now be used in non-enforced fips mode. + * Fixed HMAC for SHA-384 and SHA-512 with keys longer than 64 bytes. + * In fips mode, RSA keys are now generated using the X9.31 algorithm + and DSA keys using the FIPS 186-2 algorithm. + * The transient-key flag is now also supported for DSA key + generation. DSA domain parameters may be given as well. + +------------------------------------------------------------------- +Thu Jan 29 10:57:01 CET 2009 - olh@suse.de + +- obsolete libgcrypt-error-XXbit in the library subpackage + +------------------------------------------------------------------- +Wed Dec 10 12:34:56 CET 2008 - olh@suse.de + +- use Obsoletes: -XXbit only for ppc64 to help solver during distupgrade + (bnc#437293) + +------------------------------------------------------------------- +Tue Nov 11 17:23:54 CET 2008 - mkoenig@suse.de + +- build rijndael.c with -fno-strict-aliasing [bnc#443693] + +------------------------------------------------------------------- +Thu Oct 30 12:34:56 CET 2008 - olh@suse.de + +- obsolete old -XXbit packages (bnc#437293) + +------------------------------------------------------------------- +Mon Jun 30 11:47:59 CEST 2008 - mkoenig@suse.de + +- update to version 1.4.1 + * Fixed a bug which led to the comsumption of far too much + entropy for the intial seeding + * Improved AES performance for CFB and CBC modes + +------------------------------------------------------------------- +Sun May 11 11:54:39 CEST 2008 - coolo@suse.de + +- fix rename of xxbit packages + +------------------------------------------------------------------- +Thu Apr 10 12:54:45 CEST 2008 - ro@suse.de + +- added baselibs.conf file to build xxbit packages + for multilib support + +------------------------------------------------------------------- +Thu Jan 17 12:20:25 CET 2008 - mkoenig@suse.de + +- update to version 1.4.0: + * The entire library is now under the LGPL. The helper programs and + the manual are under the GPL + * New control code GCRYCTL_PRINT_CONFIG + * Experimental support for ECDSA + * Assembler support for the AMD64 architecture + * Non executable stack support is now used by default + * New configure option --enable-random-daemon + * The new function gcry_md_debug should be used instead of the + gcry_md_start_debug and gcry_md_stop_debug macros. + * Support for DSA2 + * Reserved algorithm ranges for use by applications + * gcry_mpi_rshift does not anymore truncate the shift count + * Support for OFB encryption mode + * Support for the Camellia cipher + * Support for the SEED cipher + * Support for SHA-224 and HMAC using SHA-384 and SHA-512 + * Reading and writing the random seed file is now protected by a + fcntl style file lock + * Made the RNG immune against fork without exec + * Changed the way the RNG gets initialized + * The ASN.1 DER template for SHA-224 has been fixed + * The ACE engine of VIA processors is now used for AES-128 +- changed package layout to conform shlib policy: + new subpackage libgcrypt11 +- disable static library +- for reference: bugzilla entry of last change #304749 + +------------------------------------------------------------------- +Thu Sep 13 01:28:53 CEST 2007 - ltinkl@suse.cz + +- add sanity check for mpi of size 0 (#304479) + +------------------------------------------------------------------- +Mon Feb 5 10:25:21 CET 2007 - mkoenig@suse.de + +- update to version 1.2.4: + * Fixed a bug in the memory allocator which could have been the + reason for some of non-duplicable bugs. + * Other minor bug fixes. + +------------------------------------------------------------------- +Wed Dec 13 12:47:48 CET 2006 - mkoenig@suse.de + +- get rid of .la file and fix devel so link + +------------------------------------------------------------------- +Tue Dec 5 18:30:30 CET 2006 - mkoenig@suse.de + +- move shared lib to /%_lib + +------------------------------------------------------------------- +Thu Aug 31 14:29:56 CEST 2006 - mkoenig@suse.de + +- update to version 1.2.3: + * Rewrote gcry_mpi_rshift to allow arbitrary shift counts. + * Minor bug fixes. +- added libgpg-error-devel and glibc-devel to Requires tag + of devel subpackage + +------------------------------------------------------------------- +Wed Jan 25 21:37:28 CET 2006 - mls@suse.de + +- converted neededforbuild to BuildRequires + +------------------------------------------------------------------- +Wed Nov 2 16:44:48 CET 2005 - hvogel@suse.de + +- enable noexecstack +- build ac.c with fno-strict-aliasing + +------------------------------------------------------------------- +Tue Oct 25 13:40:15 CEST 2005 - hvogel@suse.de + +- update to version 1.2.2 + +------------------------------------------------------------------- +Thu Jun 23 11:26:58 CEST 2005 - hvogel@suse.de + +- call install_info macro in post/postun of the devel package +- depend on libgcrypt +- add clean section + +------------------------------------------------------------------- +Tue Jan 18 11:51:51 CET 2005 - hvogel@suse.de + +- update to version 1.2.1 + +------------------------------------------------------------------- +Tue Jan 11 16:48:10 CET 2005 - schwab@suse.de + +- Fix info dir entry. + +------------------------------------------------------------------- +Wed Nov 17 11:22:44 CET 2004 - hvogel@suse.de + +- require libgpg-error-devel (Bug #48271) +- get rid of the NLD parts + +------------------------------------------------------------------- +Wed Jul 14 11:12:54 CEST 2004 - adrian@suse.de + +- create -devel subpackage +- prepare for nld + +------------------------------------------------------------------- +Wed May 19 14:57:45 CEST 2004 - hvogel@suse.de + +- update to version 1.2.0 + +------------------------------------------------------------------- +Mon Mar 22 16:48:53 CET 2004 - meissner@suse.de + +- disable make check, because it uses /dev/random whihc is + not filled on some server machines. + +------------------------------------------------------------------- +Wed Mar 17 15:01:51 CET 2004 - meissner@suse.de + +- fixed too over enthusiastic powerpc switches to make it work + on ppc64. (It compiled before, but did not work). +- enabled make check. + +------------------------------------------------------------------- +Wed Feb 18 12:14:36 CET 2004 - kukuk@suse.de + +- Build against system pthread library, not pth. + +------------------------------------------------------------------- +Tue Feb 17 21:11:40 CET 2004 - hvogel@suse.de + +- update to version 1.1.91 +- fix autoconf quotations + +------------------------------------------------------------------- +Sat Jan 10 19:20:41 CET 2004 - adrian@suse.de + +- add %run_ldconfig to %postun + +------------------------------------------------------------------- +Sun Jul 27 16:12:54 CEST 2003 - poeml@suse.de + +- add libgcrypt-1.1.12-sexp-valgrind-error.patch from SLEC + +------------------------------------------------------------------- +Thu Apr 24 12:20:23 CEST 2003 - ro@suse.de + +- fix install_info --delete call and move from preun to postun + +------------------------------------------------------------------- +Mon Feb 10 22:51:26 CET 2003 - mmj@suse.de + +- Use %install_info macro [#23433] + +------------------------------------------------------------------- +Mon Feb 10 16:11:55 CET 2003 - mc@suse.de + +- switch to version 1.1.12 +- gcry_pk_sign, gcry_pk_verify and gcry_pk_encrypt can now handle an + optional pkcs1 flags parameter in the S-expression. A similar flag + may be passed to gcry_pk_decrypt but it is only syntactically + implemented. +- New convenience macro gcry_md_get_asnoid. +- There is now some real stuff in the manual. +- New algorithm: MD4 +- Implemented ciphertext stealing. +- Support for plain old DES +- Smaller bugs fixes and a few new OIDs. + +------------------------------------------------------------------- +Tue Jan 14 14:03:27 CET 2003 - nadvornik@suse.cz + +- fixed multi-line string literals + +------------------------------------------------------------------- +Thu Aug 1 23:51:10 CEST 2002 - poeml@suse.de + +- create package + diff --git a/libgcrypt.keyring b/libgcrypt.keyring new file mode 100644 index 0000000..baed8b6 --- /dev/null +++ b/libgcrypt.keyring @@ -0,0 +1,82 @@ +-----BEGIN PGP PUBLIC KEY BLOCK----- + +mDMEX0PliRYJKwYBBAHaRw8BAQdAz75Hlekc16JhhfI0MKdEVxLdkxhcMCO0ZG6W +MBAmNpe0H1dlcm5lciBLb2NoIChkaXN0IHNpZ25pbmcgMjAyMCmImgQTFgoAQhYh +BG2qbmSnbShAVxtJAlKIl7gmQDraBQJfQ+w1AhsDBQkShccRBQsJCAcCAyICAQYV +CgkICwIEFgIDAQIeBwIXgAAKCRBSiJe4JkA62nmuAP9uL/HOdB0gvwWrH+FpURJL +s4bnaZaPIk9ARrU0EXRgJgD/YCGfHQXpIPT0ZaXuwJexK04Z+qMFR/bM1q1Leo5C +jgaIbQQQEQsAHRYhBIBhWHD1utaQMzaG0PKthaweQrNnBQJfQ/HmAAoJEPKthawe +QrNnIZkA3jG6LcZvV/URn8Y8OJqsyYa4C3NI4nN+OhEvYhgA4PHzMnALeXIpA2gb +lvjFIPJPAhDBAU37c5PA6+6IdQQQFggAHRYhBK6oTtzwGthsRwHIXGMROuhmWH0K +BQJfQ/IlAAoJEGMROuhmWH0K1+MA/0uJ5AHcnSfIBEWHNJwwVVLGyrxAWtS2U+ze +ymp/UvlPAQDErCLZl0dBiPG3vlowFx5TNep7tanBs6ZJn8F1ao1tAIkBMwQQAQgA +HRYhBNhpISPEBl3qXg86tSSbOdJPJeO2BQJfQ/OuAAoJECSbOdJPJeO2DVoH/0o9 +if66ph6FJrgr+A/WHNVeHxmM5tUQhpL1wpRS70SKcsJgolf5CxO5iTQf3HlZe544 +xGbIU/aCTJsWw9ziUE8KmhAtKV4eL/7oQ7xx4nxPnABLpudtM8A44nsM1x/XiYrJ +nnDm29QjYEGd2Hi87npc7VWKzLoj+I/WcXquynJi5O9TUxW9Bknd1pjpxFkf8v+m +sjBzCD5VKJgr0CR8wA6peQBWeGZX2HacosMIZH4TfL0r0TFla6LJIkNBz9DyIm1y +L4L8oRH0950hQljPC7TM3L7aRpX+4Kph6llFz6g7MALGFP95kyJ6o+XED9ORuuQV +ZMBMIkNC0tXOu10VbdqIdQQQFgoAHRYhBMHTS2khnkruwLocIeP9/yGORbcrBQJf +Q/P8AAoJEOP9/yGORbcr3lQBAMas8Vl3Hdl3g2I283lz1uHiGvlwcnk2TLeB+U4z +IwC9AQCy0nnazVNtVQPID1ZCMoaOX7AzOjaqQDLf4j+dVTxgBJgzBGCkgocWCSsG +AQQB2kcPAQEHQJmdfwp8jEN5P3eEjhQiWk6zQi8utvgOvYD57XmE+H8+tCBOaWli +ZSBZdXRha2EgKEdudVBHIFJlbGVhc2UgS2V5KYiaBBMWCgBCFiEErI4RW/c+LY1H ++pkI6Y6bLRnGyL0FAmCkgocCGwMFCQsNBpkFCwkIBwIDIgIBBhUKCQgLAgQWAgMB +Ah4HAheAAAoJEOmOmy0Zxsi9/4IA/1rvSr3MU+Sv4jhNDzD+CeC3gmHkPew6pi9V +HEsEwdgmAQD2BtiX7w1sJL/CBylGWv5jxj4345mP9YfZm0RsgzPjDIh1BBAWCAAd +FiEEJJyzdxdQdF1c3TI84mewUjZPAo0FAmFAQ54ACgkQ4mewUjZPAo1CiAD+KTT1 +UVdQTGHMyvHwZocSQjU8xhcZrTet+dvvjrE5+4MA/RBdJPZgFevUKu68NEy0Lo+R +bkeCtmQJ/c8v5ieFvW0AiQEzBBABCAAdFiEEEkEkvTtIYq96CkLxALRevUynur4F +AmFAQ7cACgkQALRevUynur4kaAgAolPR8TNWVS0vXMKrr0k0l2M/8QkZTaLZx1GT +9Nx1yb4WJKY7ElPMYkhGDxetvFBETx0pH/6R3jtj6Crmur+NKHVSRY+rCYpFPDn6 +ciIOryssRx2G4kCZt+nFB9JyDbBOZAR8DK4pN1mAxG/yLDt4oKcUQsP2xlEFum+p +hxyR8KyYCpkwKRxYeK+6lfilQuveoUwp/Xx5wXPNUy6q4eOOovCW7gS7I7288NGH +Ca2ul8sD6vA9C4mM4Zxaole9P9wwJe1zZFtCIy88zHM9vqv+YM9DxMCaW24+rUzt +r7eD4bCRdG+QlSh+7R/TaqSxY1eAAd1J5tma9CNJO73pTKU+/Ih1BBAWCgAdFiEE +bapuZKdtKEBXG0kCUoiXuCZAOtoFAmX776IACgkQUoiXuCZAOtpu9gEAxLOR8r83 +/CPPyTfFn4J/ILemaQOnvwqGxY8ipflN9IMBAM2ro+IsivaAqTzBHS8xgV/IwNyF +Ir5iYGFbJBMO2mQOmQGNBGgeCBYBDACI80UNEv8tIsfuKA9GeTwDuEhg031dSzTD +NFqkBPp8+srko6gSJ48fx2Agy7hPrT5Vls67WH5gJMPNubgPnVZkh9wXL27JNqFA +nVF3cVfIKyQ6ZGD2JchXAHbyx6xIHNVtqMaaaRhAvflqt3BQAU3kyhc49TEAkLBU +GyXT+plJFBO/u8uJoJ5+wRRSO/gp9O/L+60vJ6dZOabf6jJpnWyfjvcUm0jfK29g +7S407kDjN6X8s4gSa53lCIiaANDKC/sfn7iEg78Ef3ZyM6aALyH9dAq7tsKdXPkO +N5wU6kvcQi+diybd+GmshrthssCI4Zo/42TqwxkBX+n/dVL4xSbiL+DOZzLa5UcK +z7wkey1OlnTeb/6IaNox/CXCJmNUozDH3Tr+dabWmTalpItv6CAutDh8f34cs5d1 +CK/IUTcj35XmUkot0X+xAydK6urAu0/ufuO7yDP/WBnGimBA9U5LUk6MN6jRXLm/ +deCNcthcxoxAui1CBvYXDLxLOxsI2dcAEQEAAYkBzgQfAQgAOBYhBDt2GuTmO/NR +nOfWO+y2ZMvhMy7vBQJoHg0nFwyAEwLzjf9zH/l8sDmh2lSeaV6QW6IIAgcAAAoJ +EOy2ZMvhMy7vXHIL/jRKRLz5rygny0P9ni6dfuL6trqUZEby2HFwRIRJLfyrbJyU +Ayo6Uvu7r9pIgePNimQ0RCpVgimNKEuNAXoOgKt36K7rb81VjKSmLqE2K7v2QEJX +1KY1ptwrR/zWKPD6QcBx1xL8yuuEX5ajdLXiG6k9AOJl0BP3s+TGbshGmiiT+92s +PIyEcjoaP06R3vU3QzH1w9FImig9O4sRJ/iRlaY/qweqhRryQoRZib+xEHAgcgeM +gpzufaQwCa9EBQtfa8Qp+OkKIFlE6P+MNmyXQhiHgGK3c1qLl+nhGFrRofEE4I7P +M5QBWwmgmrsrZwVUQtwXBNHPz/vPR30yUEIH+MqUHwnIct7cRSkSYDkbFWmmcRU9 +xdasknnOvV4+l2H6ctSYxIFnpYmZIxInglRTC27XqCyZyoZ6r3n9t3Mzu5mkdSlm +e0DIN997lolrkj2pLVuX+Q0dWbtS3EZ+7G+1cIdoKaDWrzMXieTFPkYZhofNynh0 +vvIZOfhFz4c/1VUherQoQWxleGFuZGVyIEt1bGJhcnRzY2ggKEdudVBHIFJlbGVh +c2UgS2V5KYkB1wQTAQgAQRYhBDt2GuTmO/NRnOfWO+y2ZMvhMy7vBQJoHgohAhsD +BQkOs1FeBQsJCAcCAiICBhUKCQgLAgQWAgMBAh4HAheAAAoJEOy2ZMvhMy7vwmkL +/RSsoJk/kPL++onjhuCg7YTtTFVoqUjSOP5m68eORg4XsbSuvQrHhaJwhc8gPyCt +M3KKlHbrUNdpnrx9dJtgEleLB5UsrVkv02gvKTZfwXSWXHqQhCpril3TI0kziLTY +Vrhtj7hEBTbXuOAVHZ5jsa+yVy1bjRobmaoIPbb0MRhXj4Z+FAYmdTDA4/bpVSPA +tCYLkA8UDcPr3tCpcAcoUJ+pWuuEvIn9mjrQrwYp9EQX4Vkj/Bc1yfZttoXOqjJw +76Rn9Xn7Zz+kmhr5OK81LNPZx1Du+M3z9nYfOnmk5eisdMiyiraFqREkwwOzzExJ +eOe3eFDj9Oh3O1YRrErWz9prOiLdAmdCoCTodRG6JzvQmZoFbMW23npw3xNGr4lK +V4+9t4gxuXuEVIVQN0c1w+BM9BEFOoTbs8BIyaLjfdXnh3ZPLpJEj7E2FLKnuaPx +KdYretbGQwo+vXLXfWk9QKHXwF2IdkUSnL/IyFje/thujBW2UJZMTO3vD830px2G +k4h1BBATCAAdFiEEAvON/3Mf+XywOaHaVJ5pXpBboggFAmgeDcYACgkQVJ5pXpBb +ogis0wD9H38UP4TH3Y19d7mnkSifeHkldKc4iUP/Ok3w/+Di5qkA/iA7xLTtiuhW +jhnuwb68kTxh8Beg023EiqsJb9qWnY8umFMEYWlKoxMJKyQDAwIIAQEHAgMEXpcP +02ZRAOCLJg1uGzUMwnXiYjDzXbBjUdXH/hBZhaIG6eGu9IXFVvOyMPv9a/6/duYw ++sv4zYMvIWJJ7A2ZxLQkR251UEcuY29tIChSZWxlYXNlIFNpZ25pbmcgS2V5IDIw +MjEpiJoEExMIAEIWIQQC843/cx/5fLA5odpUnmlekFuiCAUCYWlKowIbAwUJD3HX +igULCQgHAgMiAgEGFQoJCAsCBBYCAwECHgcCF4AACgkQVJ5pXpBboghOSgD9FhqN +pOXV4QFT8Z2bXajeOsjnk3nFkrZdOpLHblyVXKMA/RfAxb86Dn40PWuLdsCoANVa +UENSzDPzBjGxvQLiRgGSiHUEEBYKAB0WIQRtqm5kp20oQFcbSQJSiJe4JkA62gUC +YWlO8QAKCRBSiJe4JkA62slAAQCHtjLKSMDL9CzXILeOLyIF8hWc9e9uWsjHdJFH +IPBELwEAq1lsS4pO0+WCQtSAyV5Nxkn+8SEkT4a99D2jmBYKoQWIdQQQFgoAHRYh +BMHTS2khnkruwLocIeP9/yGORbcrBQJhaU9aAAoJEOP9/yGORbcrHh4BAOnpoZI3 +99TjEuXxFK9BRWNUD5oJOsxBHeFHCrDyWIXbAQDc7cQLHPp7X4Ogi1igkEEsovB6 +IiewZn/6HldiuldOAA== +=gHNs +-----END PGP PUBLIC KEY BLOCK----- diff --git a/libgcrypt.spec b/libgcrypt.spec new file mode 100644 index 0000000..0998ff6 --- /dev/null +++ b/libgcrypt.spec @@ -0,0 +1,200 @@ +# +# spec file for package libgcrypt +# +# Copyright (c) 2025 SUSE LLC +# Copyright (c) 2025 Andreas Stieger +# +# All modifications and additions to the file contributed by third parties +# remain the property of their copyright owners, unless otherwise agreed +# upon. The license for this file, and modifications and additions to the +# file, is the same license as for the pristine package itself (unless the +# license for the pristine package is not an Open Source License, in which +# case the license is the MIT License). An "Open Source License" is a +# license that conforms to the Open Source Definition (Version 1.9) +# published by the Open Source Initiative. + +# Please submit bugfixes or comments via https://bugs.opensuse.org/ +# + + +%define libsover 20 +%define libsoname %{name}%{libsover} +%define hmac_key orboDeJITITejsirpADONivirpUkvarP +Name: libgcrypt +Version: 1.11.2 +Release: 0 +Summary: The GNU Crypto Library +License: GPL-2.0-or-later AND LGPL-2.1-or-later AND GPL-3.0-or-later +Group: Development/Libraries/C and C++ +URL: https://gnupg.org/software/libgcrypt +Source: https://gnupg.org/ftp/gcrypt/libgcrypt/%{name}-%{version}.tar.bz2 +Source1: https://gnupg.org/ftp/gcrypt/libgcrypt/%{name}-%{version}.tar.bz2.sig +Source2: baselibs.conf +Source3: random.conf +Source4: hwf.deny +# https://www.gnupg.org/signature_key.html +Source5: https://gnupg.org/signature_key.asc#/%{name}.keyring +Source99: libgcrypt.changes +Patch1: libgcrypt-1.10.0-allow_FSM_same_state.patch +#PATCH-FIX-OPENSUSE Do not pull revision info from GIT when autoconf is run +Patch2: libgcrypt-nobetasuffix.patch +#PATCH-FIX-SUSE: Make the revamped SLI api public +Patch3: libgcrypt-1.11.1-public-SLI-API.patch +# FIPS patches: +#PATCH-FIX-SUSE bsc#1190700 FIPS: Provide a service-level indicator for PK +Patch100: libgcrypt-FIPS-SLI-pk.patch +#PATCH-FIX-SUSE bsc#1190700 FIPS: Check keylength in gcry_fips_indicator_kdf() +Patch101: libgcrypt-FIPS-SLI-kdf-leylength.patch +#PATCH-FIX-SUSE bsc#1190700 FIPS add indicators +Patch102: libgcrypt-FIPS-SLI-hash-mac.patch +#PATCH-FIX-SUSE bsc#1202117 FIPS: Get most of the entropy from rndjent_poll +Patch104: libgcrypt-FIPS-rndjent_poll.patch +#PATCH-FIX-SUSE bsc#1220896 FIPS: Replace the built-in jitter rng with standalone version +Patch105: libgcrypt-FIPS-jitter-standalone.patch +#PATCH-FIX-SUSE bsc#1220895 FIPS: Enforce the interpretation and use of jitter rng +Patch106: libgcrypt-FIPS-jitter-errorcodes.patch +#PATCH-FIX-SUSE bsc#1220893 FIPS: Use Jitter RNG for the whole length entropy buffer +Patch107: libgcrypt-FIPS-jitter-whole-entropy.patch +#PATCH-FIX-SUSE Remove not used rol64() definition after removing the built-in jitter rng +Patch108: libgcrypt-rol64-redefinition.patch +#PATCH-FIX-CENTOS timing based side-channel in RSA implementation +Patch109: libgcrypt-CVE-2024-2236.patch + +BuildRequires: automake >= 1.14 +BuildRequires: pkgconfig(gpg-error) >= 1.49 +BuildRequires: libtool +BuildRequires: makeinfo +BuildRequires: pkgconfig +%{?suse_build_hwcaps_libs} + +%description +Libgcrypt is a general purpose library of cryptographic building +blocks. It is originally based on code used by GnuPG. It does not +provide any implementation of OpenPGP or other protocols. Thorough +understanding of applied cryptography is required to use Libgcrypt. + +%package -n %{libsoname} +Summary: The GNU Crypto Library +License: GPL-2.0-or-later AND LGPL-2.1-or-later +Group: System/Libraries +BuildRequires: jitterentropy-devel >= 3.4.0 +Requires: libjitterentropy3 >= 3.4.0 +Provides: %{libsoname}-hmac = %{version}-%{release} +Obsoletes: %{libsoname}-hmac < %{version}-%{release} + +%description -n %{libsoname} +Libgcrypt is a general purpose crypto library based on the code used in +GnuPG (alpha version). + +%package devel +Summary: The GNU Crypto Library +License: GFDL-1.1-only AND GPL-2.0-or-later AND LGPL-2.1-or-later AND MIT +Group: Development/Libraries/C and C++ +Requires: %{libsoname} = %{version} +Requires: glibc-devel +Requires: jitterentropy-devel >= 3.4.0 +Requires: libgpg-error-devel >= 1.49 + +%description devel +Libgcrypt is a general purpose library of cryptographic building +blocks. It is originally based on code used by GnuPG. It does not +provide any implementation of OpenPGP or other protocols. Thorough +understanding of applied cryptography is required to use Libgcrypt. + +This package contains needed files to compile and link against the +library. + +%prep +%autosetup -p1 + +# Rename the internal .hmac file to include the so library version +sed -i "s/libgcrypt\.so\.hmac/\.libgcrypt\.so\.%{libsover}\.hmac/g" src/Makefile.am src/Makefile.in + +# Replace the built-in jitter rng with the standalone version [bsc#1220896] +find . -type f -name "jitterentropy*" -print -delete + +%build +export PUBKEYS="dsa elgamal rsa ecc" +export CIPHERS="arcfour blowfish cast5 des aes twofish serpent rfc2268 seed camellia idea salsa20 gost28147 chacha20 sm4 aria" +export DIGESTS="crc gostr3411-94 md4 md5 rmd160 sha1 sha256 sha512 sha3 tiger whirlpool stribog blake2 sm3" +export KDFS="s2k pkdf2 scrypt" + +autoreconf -fi +date=$(date -u '+%%Y-%%m-%%dT%%H:%%M+0000' -r %{SOURCE99}) +sed -e "s,BUILD_TIMESTAMP=.*,BUILD_TIMESTAMP=$date," -i configure +export CFLAGS="%{optflags} $(getconf LFS_CFLAGS)" +%configure \ + --with-fips-module-version="Libgcrypt version %{version}-%{release}" \ + --enable-hmac-binary-check="%{hmac_key}" \ + --enable-ciphers="$CIPHERS" \ + --enable-pubkey-ciphers="$PUBKEYS" \ + --enable-digests="$DIGESTS" \ + --enable-kdfs="$KDFS" \ + --enable-noexecstack \ + --enable-marvin-workaround \ + --disable-static \ +%ifarch %{sparc} + --disable-asm \ +%endif + --enable-random=getentropy \ + --enable-jent-support \ + %{nil} + +%make_build + +%check +%make_build check +# run the regression tests also in FIPS mode +LIBGCRYPT_FORCE_FIPS_MODE=1 %make_build check + +%install +%make_install + +# this is a hack that re-defines the __spec_install_post macro +# for a simple reason: the macro strips the binaries and thereby +# invalidates a HMAC that may have been created earlier. +# solution: create the hashes _after_ the macro runs. +%define libpath %{buildroot}%{_libdir}/libgcrypt.so.%{libsover}.?.? +%define __spec_install_post \ + %{?__debug_package:%{__debug_install_post}} \ + %{__arch_install_post} \ + %{__os_install_post} \ + cd src \ + sed -i -e 's|FILE=.*|FILE=\\\$1|' gen-note-integrity.sh \ + READELF=readelf AWK=awk ECHO_N="-n" bash gen-note-integrity.sh %{libpath} > %{libpath}.hmac \ + objcopy --update-section .note.fdo.integrity=%{libpath}.hmac %{libpath} %{libpath}.new \ + mv -f %{libpath}.new %{libpath} \ + rm -f %{libpath}.hmac \ +%{nil} + +rm %{buildroot}%{_libdir}/%{name}.la + +# Create /etc/gcrypt directory and install random.conf +mkdir -p -m 0755 %{buildroot}%{_sysconfdir}/gcrypt +install -m 644 %{SOURCE3} %{buildroot}%{_sysconfdir}/gcrypt/random.conf +install -m 644 %{SOURCE4} %{buildroot}%{_sysconfdir}/gcrypt/hwf.deny + +%ldconfig_scriptlets -n %{libsoname} + +%files -n %{libsoname} +%license COPYING COPYING.LIB LICENSES +%doc AUTHORS ChangeLog NEWS README THANKS TODO +%{_libdir}/%{name}.so.* +%dir %{_sysconfdir}/gcrypt +%config(noreplace) %{_sysconfdir}/gcrypt/random.conf +%config(noreplace) %{_sysconfdir}/gcrypt/hwf.deny + +%files devel +%license COPYING COPYING.LIB LICENSES +%{_bindir}/dumpsexp +%{_bindir}/hmac256 +%{_bindir}/mpicalc +%{_bindir}/%{name}-config +%{_libdir}/%{name}.so +%{_libdir}/pkgconfig/libgcrypt.pc +%{_datadir}/aclocal/%{name}.m4 +%{_includedir}/gcrypt*.h +%{_infodir}/gcrypt.info*%{ext_info}* +%{_mandir}/man1/* + +%changelog diff --git a/random.conf b/random.conf new file mode 100644 index 0000000..378ba78 --- /dev/null +++ b/random.conf @@ -0,0 +1,9 @@ +# This file can be used to globally change parameters of +# the random generator. Supported options are: + +# Always use the non-blocking /dev/urandom or the respective +# system call instead of the blocking /dev/random. +# only-urandom + +# Disable the use of the jitter based entropy generator. +# disable-jent -- 2.51.1