diff --git a/Makefile.rhelver b/Makefile.rhelver index b9e85c142..bc57d8e16 100644 --- a/Makefile.rhelver +++ b/Makefile.rhelver @@ -12,7 +12,7 @@ RHEL_MINOR = 99 # # Use this spot to avoid future merge conflicts. # Do not trim this comment. -RHEL_RELEASE = 31 +RHEL_RELEASE = 32 # # RHEL_REBASE_NUM diff --git a/Patchlist.changelog b/Patchlist.changelog index 2af02ae57..c63e1e945 100644 --- a/Patchlist.changelog +++ b/Patchlist.changelog @@ -1,14 +1,17 @@ -https://gitlab.com/cki-project/kernel-ark/-/commit/a045da4e5ad916cae0993acb26d13e4a939b3222 - a045da4e5ad916cae0993acb26d13e4a939b3222 net/sched: fix pedit partial COW leading to page cache corruption +https://gitlab.com/cki-project/kernel-ark/-/commit/1fd0b51e79d01a83264bb776116a03124cc52ab3 + 1fd0b51e79d01a83264bb776116a03124cc52ab3 rxrpc: Fix RESPONSE packet verification to extract skb to a linear buffer -https://gitlab.com/cki-project/kernel-ark/-/commit/98a5ab48468a9adaac3d51b63d563184ce18d467 - 98a5ab48468a9adaac3d51b63d563184ce18d467 net/sched: act_pedit: extend the writable skb range per key +https://gitlab.com/cki-project/kernel-ark/-/commit/a4ab1e4043f3fd72c003411c41b17330f740f558 + a4ab1e4043f3fd72c003411c41b17330f740f558 rxrpc: Fix DATA decrypt vs splice() by copying data to buffer in recvmsg -https://gitlab.com/cki-project/kernel-ark/-/commit/7d5eab6d20dd0715072eb0b63c6442ae5f04b8c4 - 7d5eab6d20dd0715072eb0b63c6442ae5f04b8c4 net: gro: don't copy frags between mixed zcopy skbs +https://gitlab.com/cki-project/kernel-ark/-/commit/a0d6c108060fc2a54db0cebef156ed0e4920b9e2 + a0d6c108060fc2a54db0cebef156ed0e4920b9e2 crypto/krb5, rxrpc: Fix lack of pre-decrypt/pre-verify length checks -https://gitlab.com/cki-project/kernel-ark/-/commit/fb5067616ac829fe905f9e3d99705ee0e3fb9999 - fb5067616ac829fe905f9e3d99705ee0e3fb9999 net: skbuff: propagate shared-frag marker through frag-transfer helpers +https://gitlab.com/cki-project/kernel-ark/-/commit/cb40b98910bb792bbd345eac4c5243e8874470db + cb40b98910bb792bbd345eac4c5243e8874470db net/sched: act_pedit: extend the writable skb range per key + +https://gitlab.com/cki-project/kernel-ark/-/commit/2af74697445d87fcd76496132b477a5195182599 + 2af74697445d87fcd76496132b477a5195182599 net: skbuff: propagate shared-frag marker through frag-transfer helpers https://gitlab.com/cki-project/kernel-ark/-/commit/49dc112a24f8c571d32554e8a1dfdc74c0140b42 49dc112a24f8c571d32554e8a1dfdc74c0140b42 redhat: rh_flags: mark !CONFIG_RHEL_DIFFERENCES stubs as static inline diff --git a/kernel-aarch64-64k-debug-rhel.config b/kernel-aarch64-64k-debug-rhel.config index 42156e9b0..1c10dcb26 100644 --- a/kernel-aarch64-64k-debug-rhel.config +++ b/kernel-aarch64-64k-debug-rhel.config @@ -327,7 +327,7 @@ CONFIG_ARCH_NXP=y CONFIG_ARCH_PENSANDO=y CONFIG_ARCH_QCOM=y CONFIG_ARCH_R8A78000=y -CONFIG_ARCH_R9A08G046=y +# CONFIG_ARCH_R9A08G046 is not set # CONFIG_ARCH_R9A09G077 is not set # CONFIG_ARCH_R9A09G087 is not set # CONFIG_ARCH_REALTEK is not set @@ -346,7 +346,7 @@ CONFIG_ARCH_SEATTLE=y CONFIG_ARCH_TEGRA_194_SOC=y # CONFIG_ARCH_TEGRA_210_SOC is not set CONFIG_ARCH_TEGRA_234_SOC=y -CONFIG_ARCH_TEGRA_238_SOC=y +# CONFIG_ARCH_TEGRA_238_SOC is not set CONFIG_ARCH_TEGRA_241_SOC=y CONFIG_ARCH_TEGRA_264_SOC=y CONFIG_ARCH_TEGRA=y diff --git a/kernel-aarch64-64k-rhel.config b/kernel-aarch64-64k-rhel.config index 1201c92bb..b0c37e2e6 100644 --- a/kernel-aarch64-64k-rhel.config +++ b/kernel-aarch64-64k-rhel.config @@ -327,7 +327,7 @@ CONFIG_ARCH_NXP=y CONFIG_ARCH_PENSANDO=y CONFIG_ARCH_QCOM=y CONFIG_ARCH_R8A78000=y -CONFIG_ARCH_R9A08G046=y +# CONFIG_ARCH_R9A08G046 is not set # CONFIG_ARCH_R9A09G077 is not set # CONFIG_ARCH_R9A09G087 is not set # CONFIG_ARCH_REALTEK is not set @@ -346,7 +346,7 @@ CONFIG_ARCH_SEATTLE=y CONFIG_ARCH_TEGRA_194_SOC=y # CONFIG_ARCH_TEGRA_210_SOC is not set CONFIG_ARCH_TEGRA_234_SOC=y -CONFIG_ARCH_TEGRA_238_SOC=y +# CONFIG_ARCH_TEGRA_238_SOC is not set CONFIG_ARCH_TEGRA_241_SOC=y CONFIG_ARCH_TEGRA_264_SOC=y CONFIG_ARCH_TEGRA=y diff --git a/kernel-aarch64-debug-rhel.config b/kernel-aarch64-debug-rhel.config index 74a2b30ae..49b0d71d9 100644 --- a/kernel-aarch64-debug-rhel.config +++ b/kernel-aarch64-debug-rhel.config @@ -327,7 +327,7 @@ CONFIG_ARCH_NXP=y CONFIG_ARCH_PENSANDO=y CONFIG_ARCH_QCOM=y CONFIG_ARCH_R8A78000=y -CONFIG_ARCH_R9A08G046=y +# CONFIG_ARCH_R9A08G046 is not set # CONFIG_ARCH_R9A09G077 is not set # CONFIG_ARCH_R9A09G087 is not set # CONFIG_ARCH_REALTEK is not set @@ -346,7 +346,7 @@ CONFIG_ARCH_SEATTLE=y CONFIG_ARCH_TEGRA_194_SOC=y # CONFIG_ARCH_TEGRA_210_SOC is not set CONFIG_ARCH_TEGRA_234_SOC=y -CONFIG_ARCH_TEGRA_238_SOC=y +# CONFIG_ARCH_TEGRA_238_SOC is not set CONFIG_ARCH_TEGRA_241_SOC=y CONFIG_ARCH_TEGRA_264_SOC=y CONFIG_ARCH_TEGRA=y diff --git a/kernel-aarch64-rhel.config b/kernel-aarch64-rhel.config index a32a0603f..bb88f7173 100644 --- a/kernel-aarch64-rhel.config +++ b/kernel-aarch64-rhel.config @@ -327,7 +327,7 @@ CONFIG_ARCH_NXP=y CONFIG_ARCH_PENSANDO=y CONFIG_ARCH_QCOM=y CONFIG_ARCH_R8A78000=y -CONFIG_ARCH_R9A08G046=y +# CONFIG_ARCH_R9A08G046 is not set # CONFIG_ARCH_R9A09G077 is not set # CONFIG_ARCH_R9A09G087 is not set # CONFIG_ARCH_REALTEK is not set @@ -346,7 +346,7 @@ CONFIG_ARCH_SEATTLE=y CONFIG_ARCH_TEGRA_194_SOC=y # CONFIG_ARCH_TEGRA_210_SOC is not set CONFIG_ARCH_TEGRA_234_SOC=y -CONFIG_ARCH_TEGRA_238_SOC=y +# CONFIG_ARCH_TEGRA_238_SOC is not set CONFIG_ARCH_TEGRA_241_SOC=y CONFIG_ARCH_TEGRA_264_SOC=y CONFIG_ARCH_TEGRA=y diff --git a/kernel-aarch64-rt-64k-debug-rhel.config b/kernel-aarch64-rt-64k-debug-rhel.config index 721d0e954..bb89e75cc 100644 --- a/kernel-aarch64-rt-64k-debug-rhel.config +++ b/kernel-aarch64-rt-64k-debug-rhel.config @@ -328,7 +328,7 @@ CONFIG_ARCH_NXP=y CONFIG_ARCH_PENSANDO=y CONFIG_ARCH_QCOM=y CONFIG_ARCH_R8A78000=y -CONFIG_ARCH_R9A08G046=y +# CONFIG_ARCH_R9A08G046 is not set # CONFIG_ARCH_R9A09G077 is not set # CONFIG_ARCH_R9A09G087 is not set # CONFIG_ARCH_REALTEK is not set @@ -347,7 +347,7 @@ CONFIG_ARCH_SEATTLE=y CONFIG_ARCH_TEGRA_194_SOC=y # CONFIG_ARCH_TEGRA_210_SOC is not set CONFIG_ARCH_TEGRA_234_SOC=y -CONFIG_ARCH_TEGRA_238_SOC=y +# CONFIG_ARCH_TEGRA_238_SOC is not set CONFIG_ARCH_TEGRA_241_SOC=y CONFIG_ARCH_TEGRA_264_SOC=y CONFIG_ARCH_TEGRA=y diff --git a/kernel-aarch64-rt-64k-rhel.config b/kernel-aarch64-rt-64k-rhel.config index d6e60ba48..0fe511948 100644 --- a/kernel-aarch64-rt-64k-rhel.config +++ b/kernel-aarch64-rt-64k-rhel.config @@ -328,7 +328,7 @@ CONFIG_ARCH_NXP=y CONFIG_ARCH_PENSANDO=y CONFIG_ARCH_QCOM=y CONFIG_ARCH_R8A78000=y -CONFIG_ARCH_R9A08G046=y +# CONFIG_ARCH_R9A08G046 is not set # CONFIG_ARCH_R9A09G077 is not set # CONFIG_ARCH_R9A09G087 is not set # CONFIG_ARCH_REALTEK is not set @@ -347,7 +347,7 @@ CONFIG_ARCH_SEATTLE=y CONFIG_ARCH_TEGRA_194_SOC=y # CONFIG_ARCH_TEGRA_210_SOC is not set CONFIG_ARCH_TEGRA_234_SOC=y -CONFIG_ARCH_TEGRA_238_SOC=y +# CONFIG_ARCH_TEGRA_238_SOC is not set CONFIG_ARCH_TEGRA_241_SOC=y CONFIG_ARCH_TEGRA_264_SOC=y CONFIG_ARCH_TEGRA=y diff --git a/kernel-aarch64-rt-debug-rhel.config b/kernel-aarch64-rt-debug-rhel.config index 205e70af5..2f5158e27 100644 --- a/kernel-aarch64-rt-debug-rhel.config +++ b/kernel-aarch64-rt-debug-rhel.config @@ -327,7 +327,7 @@ CONFIG_ARCH_NXP=y CONFIG_ARCH_PENSANDO=y CONFIG_ARCH_QCOM=y CONFIG_ARCH_R8A78000=y -CONFIG_ARCH_R9A08G046=y +# CONFIG_ARCH_R9A08G046 is not set # CONFIG_ARCH_R9A09G077 is not set # CONFIG_ARCH_R9A09G087 is not set # CONFIG_ARCH_REALTEK is not set @@ -346,7 +346,7 @@ CONFIG_ARCH_SEATTLE=y CONFIG_ARCH_TEGRA_194_SOC=y # CONFIG_ARCH_TEGRA_210_SOC is not set CONFIG_ARCH_TEGRA_234_SOC=y -CONFIG_ARCH_TEGRA_238_SOC=y +# CONFIG_ARCH_TEGRA_238_SOC is not set CONFIG_ARCH_TEGRA_241_SOC=y CONFIG_ARCH_TEGRA_264_SOC=y CONFIG_ARCH_TEGRA=y diff --git a/kernel-aarch64-rt-rhel.config b/kernel-aarch64-rt-rhel.config index 917f51347..8f9144404 100644 --- a/kernel-aarch64-rt-rhel.config +++ b/kernel-aarch64-rt-rhel.config @@ -327,7 +327,7 @@ CONFIG_ARCH_NXP=y CONFIG_ARCH_PENSANDO=y CONFIG_ARCH_QCOM=y CONFIG_ARCH_R8A78000=y -CONFIG_ARCH_R9A08G046=y +# CONFIG_ARCH_R9A08G046 is not set # CONFIG_ARCH_R9A09G077 is not set # CONFIG_ARCH_R9A09G087 is not set # CONFIG_ARCH_REALTEK is not set @@ -346,7 +346,7 @@ CONFIG_ARCH_SEATTLE=y CONFIG_ARCH_TEGRA_194_SOC=y # CONFIG_ARCH_TEGRA_210_SOC is not set CONFIG_ARCH_TEGRA_234_SOC=y -CONFIG_ARCH_TEGRA_238_SOC=y +# CONFIG_ARCH_TEGRA_238_SOC is not set CONFIG_ARCH_TEGRA_241_SOC=y CONFIG_ARCH_TEGRA_264_SOC=y CONFIG_ARCH_TEGRA=y diff --git a/kernel-ppc64le-debug-rhel.config b/kernel-ppc64le-debug-rhel.config index 3824c4efb..64d7668c5 100644 --- a/kernel-ppc64le-debug-rhel.config +++ b/kernel-ppc64le-debug-rhel.config @@ -289,14 +289,14 @@ CONFIG_ARCH_MMAP_RND_BITS=14 CONFIG_ARCH_MMAP_RND_COMPAT_BITS=8 # CONFIG_ARCH_MMP is not set CONFIG_ARCH_R8A78000=y -CONFIG_ARCH_R9A08G046=y +# CONFIG_ARCH_R9A08G046 is not set # CONFIG_ARCH_R9A09G077 is not set # CONFIG_ARCH_R9A09G087 is not set # CONFIG_ARCH_REALTEK is not set # CONFIG_ARCH_S32 is not set # CONFIG_ARCH_SOPHGO is not set # CONFIG_ARCH_SPARX5 is not set -CONFIG_ARCH_TEGRA_238_SOC=y +# CONFIG_ARCH_TEGRA_238_SOC is not set # CONFIG_ARCNET is not set CONFIG_ARM64_BRBE=y CONFIG_ARM64_ERRATUM_4193714=y diff --git a/kernel-ppc64le-rhel.config b/kernel-ppc64le-rhel.config index 0f2402d9e..ce6b6a389 100644 --- a/kernel-ppc64le-rhel.config +++ b/kernel-ppc64le-rhel.config @@ -289,14 +289,14 @@ CONFIG_ARCH_MMAP_RND_BITS=14 CONFIG_ARCH_MMAP_RND_COMPAT_BITS=8 # CONFIG_ARCH_MMP is not set CONFIG_ARCH_R8A78000=y -CONFIG_ARCH_R9A08G046=y +# CONFIG_ARCH_R9A08G046 is not set # CONFIG_ARCH_R9A09G077 is not set # CONFIG_ARCH_R9A09G087 is not set # CONFIG_ARCH_REALTEK is not set # CONFIG_ARCH_S32 is not set # CONFIG_ARCH_SOPHGO is not set # CONFIG_ARCH_SPARX5 is not set -CONFIG_ARCH_TEGRA_238_SOC=y +# CONFIG_ARCH_TEGRA_238_SOC is not set # CONFIG_ARCNET is not set CONFIG_ARM64_BRBE=y CONFIG_ARM64_ERRATUM_4193714=y diff --git a/kernel-riscv64-debug-rhel.config b/kernel-riscv64-debug-rhel.config index 8cd0639cc..5b353df4f 100644 --- a/kernel-riscv64-debug-rhel.config +++ b/kernel-riscv64-debug-rhel.config @@ -295,7 +295,7 @@ CONFIG_ARCH_MMAP_RND_BITS=24 CONFIG_ARCH_MMAP_RND_COMPAT_BITS=8 # CONFIG_ARCH_MMP is not set CONFIG_ARCH_R8A78000=y -CONFIG_ARCH_R9A08G046=y +# CONFIG_ARCH_R9A08G046 is not set # CONFIG_ARCH_R9A09G077 is not set # CONFIG_ARCH_R9A09G087 is not set # CONFIG_ARCH_REALTEK is not set @@ -308,7 +308,7 @@ CONFIG_ARCH_RV64I=y # CONFIG_ARCH_SPARX5 is not set CONFIG_ARCH_STARFIVE=y # CONFIG_ARCH_SUNXI is not set -CONFIG_ARCH_TEGRA_238_SOC=y +# CONFIG_ARCH_TEGRA_238_SOC is not set # CONFIG_ARCH_TENSTORRENT is not set # CONFIG_ARCH_THEAD is not set CONFIG_ARCH_VIRT=y diff --git a/kernel-riscv64-rhel.config b/kernel-riscv64-rhel.config index fcc8106d2..88ccb0a91 100644 --- a/kernel-riscv64-rhel.config +++ b/kernel-riscv64-rhel.config @@ -295,7 +295,7 @@ CONFIG_ARCH_MMAP_RND_BITS=24 CONFIG_ARCH_MMAP_RND_COMPAT_BITS=8 # CONFIG_ARCH_MMP is not set CONFIG_ARCH_R8A78000=y -CONFIG_ARCH_R9A08G046=y +# CONFIG_ARCH_R9A08G046 is not set # CONFIG_ARCH_R9A09G077 is not set # CONFIG_ARCH_R9A09G087 is not set # CONFIG_ARCH_REALTEK is not set @@ -308,7 +308,7 @@ CONFIG_ARCH_RV64I=y # CONFIG_ARCH_SPARX5 is not set CONFIG_ARCH_STARFIVE=y # CONFIG_ARCH_SUNXI is not set -CONFIG_ARCH_TEGRA_238_SOC=y +# CONFIG_ARCH_TEGRA_238_SOC is not set # CONFIG_ARCH_TENSTORRENT is not set # CONFIG_ARCH_THEAD is not set CONFIG_ARCH_VIRT=y diff --git a/kernel-s390x-debug-rhel.config b/kernel-s390x-debug-rhel.config index 0f955879c..fe3ad2002 100644 --- a/kernel-s390x-debug-rhel.config +++ b/kernel-s390x-debug-rhel.config @@ -290,14 +290,14 @@ CONFIG_ARCH_MMAP_RND_BITS=28 CONFIG_ARCH_MMAP_RND_COMPAT_BITS=8 # CONFIG_ARCH_MMP is not set CONFIG_ARCH_R8A78000=y -CONFIG_ARCH_R9A08G046=y +# CONFIG_ARCH_R9A08G046 is not set # CONFIG_ARCH_R9A09G077 is not set # CONFIG_ARCH_R9A09G087 is not set # CONFIG_ARCH_REALTEK is not set # CONFIG_ARCH_S32 is not set # CONFIG_ARCH_SOPHGO is not set # CONFIG_ARCH_SPARX5 is not set -CONFIG_ARCH_TEGRA_238_SOC=y +# CONFIG_ARCH_TEGRA_238_SOC is not set # CONFIG_ARCNET is not set CONFIG_ARM64_BRBE=y CONFIG_ARM64_ERRATUM_4193714=y diff --git a/kernel-s390x-rhel.config b/kernel-s390x-rhel.config index efbabc601..7a72db196 100644 --- a/kernel-s390x-rhel.config +++ b/kernel-s390x-rhel.config @@ -290,14 +290,14 @@ CONFIG_ARCH_MMAP_RND_BITS=28 CONFIG_ARCH_MMAP_RND_COMPAT_BITS=8 # CONFIG_ARCH_MMP is not set CONFIG_ARCH_R8A78000=y -CONFIG_ARCH_R9A08G046=y +# CONFIG_ARCH_R9A08G046 is not set # CONFIG_ARCH_R9A09G077 is not set # CONFIG_ARCH_R9A09G087 is not set # CONFIG_ARCH_REALTEK is not set # CONFIG_ARCH_S32 is not set # CONFIG_ARCH_SOPHGO is not set # CONFIG_ARCH_SPARX5 is not set -CONFIG_ARCH_TEGRA_238_SOC=y +# CONFIG_ARCH_TEGRA_238_SOC is not set # CONFIG_ARCNET is not set CONFIG_ARM64_BRBE=y CONFIG_ARM64_ERRATUM_4193714=y diff --git a/kernel-s390x-zfcpdump-rhel.config b/kernel-s390x-zfcpdump-rhel.config index 86d64678f..71a9a5598 100644 --- a/kernel-s390x-zfcpdump-rhel.config +++ b/kernel-s390x-zfcpdump-rhel.config @@ -290,14 +290,14 @@ CONFIG_ARCH_MMAP_RND_BITS=28 CONFIG_ARCH_MMAP_RND_COMPAT_BITS=8 # CONFIG_ARCH_MMP is not set CONFIG_ARCH_R8A78000=y -CONFIG_ARCH_R9A08G046=y +# CONFIG_ARCH_R9A08G046 is not set # CONFIG_ARCH_R9A09G077 is not set # CONFIG_ARCH_R9A09G087 is not set # CONFIG_ARCH_REALTEK is not set # CONFIG_ARCH_S32 is not set # CONFIG_ARCH_SOPHGO is not set # CONFIG_ARCH_SPARX5 is not set -CONFIG_ARCH_TEGRA_238_SOC=y +# CONFIG_ARCH_TEGRA_238_SOC is not set # CONFIG_ARCNET is not set CONFIG_ARM64_BRBE=y CONFIG_ARM64_ERRATUM_4193714=y diff --git a/kernel-x86_64-debug-rhel.config b/kernel-x86_64-debug-rhel.config index f249872a5..07f4a49c7 100644 --- a/kernel-x86_64-debug-rhel.config +++ b/kernel-x86_64-debug-rhel.config @@ -316,14 +316,14 @@ CONFIG_ARCH_MMAP_RND_BITS=28 CONFIG_ARCH_MMAP_RND_COMPAT_BITS=8 # CONFIG_ARCH_MMP is not set CONFIG_ARCH_R8A78000=y -CONFIG_ARCH_R9A08G046=y +# CONFIG_ARCH_R9A08G046 is not set # CONFIG_ARCH_R9A09G077 is not set # CONFIG_ARCH_R9A09G087 is not set # CONFIG_ARCH_REALTEK is not set # CONFIG_ARCH_S32 is not set # CONFIG_ARCH_SOPHGO is not set # CONFIG_ARCH_SPARX5 is not set -CONFIG_ARCH_TEGRA_238_SOC=y +# CONFIG_ARCH_TEGRA_238_SOC is not set # CONFIG_ARCNET is not set CONFIG_ARM64_BRBE=y CONFIG_ARM64_ERRATUM_4193714=y diff --git a/kernel-x86_64-rhel.config b/kernel-x86_64-rhel.config index 56553ffd3..21ebfd596 100644 --- a/kernel-x86_64-rhel.config +++ b/kernel-x86_64-rhel.config @@ -316,14 +316,14 @@ CONFIG_ARCH_MMAP_RND_BITS=28 CONFIG_ARCH_MMAP_RND_COMPAT_BITS=8 # CONFIG_ARCH_MMP is not set CONFIG_ARCH_R8A78000=y -CONFIG_ARCH_R9A08G046=y +# CONFIG_ARCH_R9A08G046 is not set # CONFIG_ARCH_R9A09G077 is not set # CONFIG_ARCH_R9A09G087 is not set # CONFIG_ARCH_REALTEK is not set # CONFIG_ARCH_S32 is not set # CONFIG_ARCH_SOPHGO is not set # CONFIG_ARCH_SPARX5 is not set -CONFIG_ARCH_TEGRA_238_SOC=y +# CONFIG_ARCH_TEGRA_238_SOC is not set # CONFIG_ARCNET is not set CONFIG_ARM64_BRBE=y CONFIG_ARM64_ERRATUM_4193714=y diff --git a/kernel-x86_64-rt-debug-rhel.config b/kernel-x86_64-rt-debug-rhel.config index 54d79ad27..4009e2634 100644 --- a/kernel-x86_64-rt-debug-rhel.config +++ b/kernel-x86_64-rt-debug-rhel.config @@ -316,14 +316,14 @@ CONFIG_ARCH_MMAP_RND_BITS=28 CONFIG_ARCH_MMAP_RND_COMPAT_BITS=8 # CONFIG_ARCH_MMP is not set CONFIG_ARCH_R8A78000=y -CONFIG_ARCH_R9A08G046=y +# CONFIG_ARCH_R9A08G046 is not set # CONFIG_ARCH_R9A09G077 is not set # CONFIG_ARCH_R9A09G087 is not set # CONFIG_ARCH_REALTEK is not set # CONFIG_ARCH_S32 is not set # CONFIG_ARCH_SOPHGO is not set # CONFIG_ARCH_SPARX5 is not set -CONFIG_ARCH_TEGRA_238_SOC=y +# CONFIG_ARCH_TEGRA_238_SOC is not set # CONFIG_ARCNET is not set CONFIG_ARM64_BRBE=y CONFIG_ARM64_ERRATUM_4193714=y diff --git a/kernel-x86_64-rt-rhel.config b/kernel-x86_64-rt-rhel.config index e4f97fbfe..8b0a3abae 100644 --- a/kernel-x86_64-rt-rhel.config +++ b/kernel-x86_64-rt-rhel.config @@ -316,14 +316,14 @@ CONFIG_ARCH_MMAP_RND_BITS=28 CONFIG_ARCH_MMAP_RND_COMPAT_BITS=8 # CONFIG_ARCH_MMP is not set CONFIG_ARCH_R8A78000=y -CONFIG_ARCH_R9A08G046=y +# CONFIG_ARCH_R9A08G046 is not set # CONFIG_ARCH_R9A09G077 is not set # CONFIG_ARCH_R9A09G087 is not set # CONFIG_ARCH_REALTEK is not set # CONFIG_ARCH_S32 is not set # CONFIG_ARCH_SOPHGO is not set # CONFIG_ARCH_SPARX5 is not set -CONFIG_ARCH_TEGRA_238_SOC=y +# CONFIG_ARCH_TEGRA_238_SOC is not set # CONFIG_ARCNET is not set CONFIG_ARM64_BRBE=y CONFIG_ARM64_ERRATUM_4193714=y diff --git a/kernel.changelog b/kernel.changelog index c60031c43..882bcb874 100644 --- a/kernel.changelog +++ b/kernel.changelog @@ -1,9 +1,19 @@ -* Tue May 19 2026 Fedora Kernel Team [7.1.0-0.rc4.ab5fce87a778.31] +* Wed May 20 2026 Fedora Kernel Team [7.1.0-0.rc4.27fa82620cba.32] +- rxrpc: Fix RESPONSE packet verification to extract skb to a linear buffer (David Howells) +- rxrpc: Fix DATA decrypt vs splice() by copying data to buffer in recvmsg (David Howells) +- crypto/krb5, rxrpc: Fix lack of pre-decrypt/pre-verify length checks (David Howells) +- net/sched: act_pedit: extend the writable skb range per key (Zhang Cen) - net: skbuff: propagate shared-frag marker through frag-transfer helpers (Hyunwoo Kim) - automotive: enable HUGETLBFS to workaround build error (Scott Weaver) - disable selftests by default for now (Thorsten Leemhuis) Resolves: +* Wed May 20 2026 Fedora Kernel Team [7.1.0-0.rc4.27fa82620cba.31] +- redhat/configs: do not enable ARCH_TEGRA_238_SOC (Eric Chanudet) +- redhat/configs: do not enable ARCH_R9A08G046 (Eric Chanudet) +- Linux v7.1.0-0.rc4.27fa82620cba +Resolves: + * Tue May 19 2026 Fedora Kernel Team [7.1.0-0.rc4.ab5fce87a778.30] - redhat/configs: realign LOCKDEP_STACK_TRACE_*_BITS with upstream KASAN defaults (Mikhail Gavrilov) - Linux v7.1.0-0.rc4.ab5fce87a778 diff --git a/kernel.spec b/kernel.spec index 446d8ec58..9d74c19df 100644 --- a/kernel.spec +++ b/kernel.spec @@ -190,13 +190,13 @@ Summary: The Linux kernel %define specrpmversion 7.1.0 %define specversion 7.1.0 %define patchversion 7.1 -%define pkgrelease 0.rc4.260519gab5fce87a778.31 +%define pkgrelease 0.rc4.260520g27fa82620cba.32 %define kversion 7 -%define tarfile_release 7.1-rc4-46-gab5fce87a778 +%define tarfile_release 7.1-rc4-93-g27fa82620cba # This is needed to do merge window version magic %define patchlevel 1 # This allows pkg_release to have configurable %%{?dist} tag -%define specrelease 0.rc4.260519gab5fce87a778.31%{?buildid}%{?dist} +%define specrelease 0.rc4.260520g27fa82620cba.32%{?buildid}%{?dist} # This defines the kabi tarball version %define kabiversion 7.1.0 @@ -4847,16 +4847,20 @@ fi\ # # %changelog -* Tue May 19 2026 Justin M. Forbes [7.1.0-0.rc4.260519gab5fce87a778.31] -- net/sched: fix pedit partial COW leading to page cache corruption (Rajat Gupta) +* Wed May 20 2026 Fedora Kernel Team [7.1.0-0.rc4.27fa82620cba.32] +- rxrpc: Fix RESPONSE packet verification to extract skb to a linear buffer (David Howells) +- rxrpc: Fix DATA decrypt vs splice() by copying data to buffer in recvmsg (David Howells) +- crypto/krb5, rxrpc: Fix lack of pre-decrypt/pre-verify length checks (David Howells) - net/sched: act_pedit: extend the writable skb range per key (Zhang Cen) -- net: gro: don't copy frags between mixed zcopy skbs (Sabrina Dubroca) - -* Tue May 19 2026 Fedora Kernel Team [7.1.0-0.rc4.ab5fce87a778.31] - net: skbuff: propagate shared-frag marker through frag-transfer helpers (Hyunwoo Kim) - automotive: enable HUGETLBFS to workaround build error (Scott Weaver) - disable selftests by default for now (Thorsten Leemhuis) +* Wed May 20 2026 Fedora Kernel Team [7.1.0-0.rc4.27fa82620cba.31] +- redhat/configs: do not enable ARCH_TEGRA_238_SOC (Eric Chanudet) +- redhat/configs: do not enable ARCH_R9A08G046 (Eric Chanudet) +- Linux v7.1.0-0.rc4.27fa82620cba + * Tue May 19 2026 Fedora Kernel Team [7.1.0-0.rc4.ab5fce87a778.30] - redhat/configs: realign LOCKDEP_STACK_TRACE_*_BITS with upstream KASAN defaults (Mikhail Gavrilov) - Linux v7.1.0-0.rc4.ab5fce87a778 diff --git a/patch-7.1-redhat.patch b/patch-7.1-redhat.patch index 860d8b49b..972f83ce3 100644 --- a/patch-7.1-redhat.patch +++ b/patch-7.1-redhat.patch @@ -1,5 +1,6 @@ Documentation/admin-guide/kernel-parameters.txt | 23 + Documentation/admin-guide/rh-waived-items.rst | 29 ++ + Documentation/crypto/krb5.rst | 17 +- Kconfig | 2 + Kconfig.redhat | 31 ++ Makefile | 38 +- @@ -14,6 +15,7 @@ crypto/akcipher.c | 3 +- crypto/dh.c | 25 + crypto/drbg.c | 18 +- + crypto/krb5/krb5_api.c | 54 +- crypto/rng.c | 155 +++++- crypto/seqiv.c | 15 +- crypto/sig.c | 3 +- @@ -46,6 +48,7 @@ fs/afs/main.c | 3 + fs/erofs/super.c | 9 + fs/ext4/super.c | 11 + + include/crypto/krb5.h | 9 +- include/linux/crypto.h | 3 + include/linux/efi.h | 22 +- include/linux/kernel.h | 28 ++ @@ -59,6 +62,7 @@ include/linux/rh_waived.h | 19 + include/linux/rmi.h | 1 + include/linux/security.h | 9 + + include/trace/events/rxrpc.h | 1 + init/main.c | 5 + kernel/Makefile | 2 + kernel/bpf/core.c | 5 + @@ -70,10 +74,20 @@ kernel/rh_messages.c | 414 ++++++++++++++++ kernel/rh_messages.h | 334 +++++++++++++ kernel/rh_waived.c | 147 ++++++ - net/core/gro.c | 7 + + net/core/gro.c | 4 + net/core/skbuff.c | 9 +- net/ipv4/tcp_output.c | 1 + - net/sched/act_pedit.c | 72 ++- + net/rxrpc/ar-internal.h | 14 +- + net/rxrpc/call_event.c | 22 +- + net/rxrpc/call_object.c | 2 + + net/rxrpc/conn_event.c | 32 +- + net/rxrpc/insecure.c | 8 +- + net/rxrpc/recvmsg.c | 76 ++- + net/rxrpc/rxgk.c | 160 +++--- + net/rxrpc/rxgk_app.c | 46 +- + net/rxrpc/rxgk_common.h | 66 ++- + net/rxrpc/rxkad.c | 115 ++--- + net/sched/act_pedit.c | 36 +- scripts/Makefile.lib | 3 + scripts/mod/modpost.c | 8 + scripts/tags.sh | 2 + @@ -83,7 +97,7 @@ tools/testing/selftests/bpf/DENYLIST.rhel | 76 +++ tools/testing/selftests/bpf/Makefile | 2 +- tools/testing/selftests/bpf/prog_tests/ksyms_btf.c | 31 -- - 85 files changed, 2975 insertions(+), 257 deletions(-) + 99 files changed, 3255 insertions(+), 560 deletions(-) diff --git a/Documentation/admin-guide/kernel-parameters.txt b/Documentation/admin-guide/kernel-parameters.txt index 4d0f545fb3ec..767989050205 100644 @@ -161,6 +175,37 @@ index 000000000000..7471c891419c +List of Red Hat Waived Items +============================ + +diff --git a/Documentation/crypto/krb5.rst b/Documentation/crypto/krb5.rst +index beffa0133446..f62e07ac6811 100644 +--- a/Documentation/crypto/krb5.rst ++++ b/Documentation/crypto/krb5.rst +@@ -158,13 +158,22 @@ returned. + When a message has been received, the location and size of the data with the + message can be determined by calling:: + +- void crypto_krb5_where_is_the_data(const struct krb5_enctype *krb5, +- enum krb5_crypto_mode mode, +- size_t *_offset, size_t *_len); ++ int crypto_krb5_where_is_the_data(const struct krb5_enctype *krb5, ++ enum krb5_crypto_mode mode, ++ size_t *_offset, size_t *_len); + + The caller provides the offset and length of the message to the function, which + then alters those values to indicate the region containing the data (plus any +-padding). It is up to the caller to determine how much padding there is. ++padding). It is up to the caller to determine how much padding there is. The ++function returns an error if the length is too small or if the mode is ++unsupported. An additional function:: ++ ++ int crypto_krb5_check_data_len(const struct krb5_enctype *krb5, ++ enum krb5_crypto_mode mode, ++ size_t len, size_t min_content); ++ ++is provided to just do a basic check that the decrypted/verified message would ++have a sufficient minimum payload. + + Preparation Functions + --------------------- diff --git a/Kconfig b/Kconfig index 307e581144de..11e93e479ce4 100644 --- a/Kconfig @@ -674,6 +719,86 @@ index 9204e6edb426..5c10baf70071 100644 } /* +diff --git a/crypto/krb5/krb5_api.c b/crypto/krb5/krb5_api.c +index 23026d4206c8..c7ea40f900a7 100644 +--- a/crypto/krb5/krb5_api.c ++++ b/crypto/krb5/krb5_api.c +@@ -134,27 +134,69 @@ EXPORT_SYMBOL(crypto_krb5_how_much_data); + * Find the offset and size of the data in a secure message so that this + * information can be used in the metadata buffer which will get added to the + * digest by crypto_krb5_verify_mic(). ++ * ++ * Return: 0 if successful, -EBADMSG if the message is too short or -EINVAL if ++ * the mode is unsupported. + */ +-void crypto_krb5_where_is_the_data(const struct krb5_enctype *krb5, +- enum krb5_crypto_mode mode, +- size_t *_offset, size_t *_len) ++int crypto_krb5_where_is_the_data(const struct krb5_enctype *krb5, ++ enum krb5_crypto_mode mode, ++ size_t *_offset, size_t *_len) + { + switch (mode) { + case KRB5_CHECKSUM_MODE: ++ if (*_len < krb5->cksum_len) ++ return -EBADMSG; + *_offset += krb5->cksum_len; + *_len -= krb5->cksum_len; +- return; ++ return 0; + case KRB5_ENCRYPT_MODE: ++ if (*_len < krb5->conf_len + krb5->cksum_len) ++ return -EBADMSG; + *_offset += krb5->conf_len; + *_len -= krb5->conf_len + krb5->cksum_len; +- return; ++ return 0; + default: + WARN_ON_ONCE(1); +- return; ++ return -EINVAL; + } + } + EXPORT_SYMBOL(crypto_krb5_where_is_the_data); + ++/** ++ * crypto_krb5_check_data_len - Check a message is big enough ++ * @krb5: The encoding to use. ++ * @mode: Mode of operation. ++ * @len: The length of the secure blob. ++ * @min_content: Minimum length of the content inside the blob. ++ * ++ * Check that a message is large enough to hold whatever bits the encryption ++ * type wants to glue on (nonce, checksum) plus a minimum amount of content. ++ * ++ * Return: 0 if successful, -EBADMSG if the message is too short or -EINVAL if ++ * the mode is unsupported. ++ */ ++int crypto_krb5_check_data_len(const struct krb5_enctype *krb5, ++ enum krb5_crypto_mode mode, ++ size_t len, size_t min_content) ++{ ++ switch (mode) { ++ case KRB5_CHECKSUM_MODE: ++ if (len < krb5->cksum_len || ++ len - krb5->cksum_len < min_content) ++ return -EBADMSG; ++ return 0; ++ case KRB5_ENCRYPT_MODE: ++ if (len < krb5->conf_len + krb5->cksum_len || ++ len - (krb5->conf_len + krb5->cksum_len) < min_content) ++ return -EBADMSG; ++ return 0; ++ default: ++ WARN_ON_ONCE(1); ++ return -EINVAL; ++ } ++} ++EXPORT_SYMBOL(crypto_krb5_check_data_len); ++ + /* + * Prepare the encryption with derived key data. + */ diff --git a/crypto/rng.c b/crypto/rng.c index 1d4b9177bad4..d9ca86086946 100644 --- a/crypto/rng.c @@ -2306,6 +2431,26 @@ index 6a77db4d3124..5798b0a12ddd 100644 /* Register sysfs after all initializations are complete. */ err = ext4_register_sysfs(sb); if (err) +diff --git a/include/crypto/krb5.h b/include/crypto/krb5.h +index 71dd38f59be1..aac3ecf88467 100644 +--- a/include/crypto/krb5.h ++++ b/include/crypto/krb5.h +@@ -121,9 +121,12 @@ size_t crypto_krb5_how_much_buffer(const struct krb5_enctype *krb5, + size_t crypto_krb5_how_much_data(const struct krb5_enctype *krb5, + enum krb5_crypto_mode mode, + size_t *_buffer_size, size_t *_offset); +-void crypto_krb5_where_is_the_data(const struct krb5_enctype *krb5, +- enum krb5_crypto_mode mode, +- size_t *_offset, size_t *_len); ++int crypto_krb5_where_is_the_data(const struct krb5_enctype *krb5, ++ enum krb5_crypto_mode mode, ++ size_t *_offset, size_t *_len); ++int crypto_krb5_check_data_len(const struct krb5_enctype *krb5, ++ enum krb5_crypto_mode mode, ++ size_t len, size_t min_content); + struct crypto_aead *crypto_krb5_prepare_encryption(const struct krb5_enctype *krb5, + const struct krb5_buffer *TK, + u32 usage, gfp_t gfp); diff --git a/include/linux/crypto.h b/include/linux/crypto.h index a2137e19be7d..df268ca70170 100644 --- a/include/linux/crypto.h @@ -3181,6 +3326,18 @@ index 41d7367cf403..ad6f69c6fcff 100644 +#endif /* CONFIG_SECURITY_LOCKDOWN_LSM */ + #endif /* ! __LINUX_SECURITY_H */ +diff --git a/include/trace/events/rxrpc.h b/include/trace/events/rxrpc.h +index 573f2df3a2c9..704a10de6670 100644 +--- a/include/trace/events/rxrpc.h ++++ b/include/trace/events/rxrpc.h +@@ -71,6 +71,7 @@ + EM(rxkad_abort_resp_unknown_tkt, "rxkad-resp-unknown-tkt") \ + EM(rxkad_abort_resp_version, "rxkad-resp-version") \ + /* RxGK security errors */ \ ++ EM(rxgk_abort_1_short_header, "rxgk1-short-hdr") \ + EM(rxgk_abort_1_verify_mic_eproto, "rxgk1-vfy-mic-eproto") \ + EM(rxgk_abort_2_decrypt_eproto, "rxgk2-dec-eproto") \ + EM(rxgk_abort_2_short_data, "rxgk2-short-data") \ diff --git a/init/main.c b/init/main.c index 96f93bb06c49..20dfcf6693f5 100644 --- a/init/main.c @@ -4417,20 +4574,10 @@ index 000000000000..20966f7c7277 +} +late_initcall(__add_rh_flag); diff --git a/net/core/gro.c b/net/core/gro.c -index 31d21de5b15a..e5352780fec0 100644 +index 31d21de5b15a..9f8960789b2c 100644 --- a/net/core/gro.c +++ b/net/core/gro.c -@@ -123,6 +123,9 @@ int skb_gro_receive(struct sk_buff *p, struct sk_buff *skb) - lp = NAPI_GRO_CB(p)->last; - pinfo = skb_shinfo(lp); - -+ if (skb_zcopy(skb) || skb_zcopy(lp)) -+ goto merge; -+ - if (headlen <= offset) { - skb_frag_t *frag; - skb_frag_t *frag2; -@@ -213,10 +216,12 @@ int skb_gro_receive(struct sk_buff *p, struct sk_buff *skb) +@@ -213,10 +213,12 @@ int skb_gro_receive(struct sk_buff *p, struct sk_buff *skb) p->data_len += len; p->truesize += delta_truesize; p->len += len; @@ -4443,7 +4590,7 @@ index 31d21de5b15a..e5352780fec0 100644 } NAPI_GRO_CB(skb)->same_flow = 1; return 0; -@@ -244,6 +249,8 @@ int skb_gro_receive_list(struct sk_buff *p, struct sk_buff *skb) +@@ -244,6 +246,8 @@ int skb_gro_receive_list(struct sk_buff *p, struct sk_buff *skb) p->truesize += skb->truesize; p->len += skb->len; @@ -4505,32 +4652,1086 @@ index f9d8755705f7..6e4bb411dc04 100644 if (lastfrag && skb_frag_page(fragfrom) == skb_frag_page(lastfrag) && skb_frag_off(fragfrom) == skb_frag_off(lastfrag) + -diff --git a/net/sched/act_pedit.c b/net/sched/act_pedit.c -index bc20f08a2789..1aa95c34ad87 100644 ---- a/net/sched/act_pedit.c -+++ b/net/sched/act_pedit.c -@@ -16,6 +16,7 @@ - #include - #include - #include -+#include - #include - #include - #include -@@ -323,8 +324,10 @@ static bool offset_valid(struct sk_buff *skb, int offset) - if (offset > 0 && offset > skb->len) - return false; +diff --git a/net/rxrpc/ar-internal.h b/net/rxrpc/ar-internal.h +index 27c2aa2dd023..98f2165159d7 100644 +--- a/net/rxrpc/ar-internal.h ++++ b/net/rxrpc/ar-internal.h +@@ -213,8 +213,6 @@ struct rxrpc_skb_priv { + struct { + u16 offset; /* Offset of data */ + u16 len; /* Length of data */ +- u8 flags; +-#define RXRPC_RX_VERIFIED 0x01 + }; + struct { + rxrpc_seq_t first_ack; /* First packet in acks table */ +@@ -309,15 +307,16 @@ struct rxrpc_security { + struct sk_buff *challenge); -- if (offset < 0 && -offset > skb_headroom(skb)) -- return false; -+ if (offset < 0) { -+ if (offset == INT_MIN || -offset > skb_headroom(skb)) -+ return false; + /* verify a response */ +- int (*verify_response)(struct rxrpc_connection *, +- struct sk_buff *); ++ int (*verify_response)(struct rxrpc_connection *conn, ++ struct sk_buff *response_skb, ++ void *response, unsigned int len); + + /* clear connection security */ + void (*clear)(struct rxrpc_connection *); + + /* Default ticket -> key decoder */ + int (*default_decode_ticket)(struct rxrpc_connection *conn, struct sk_buff *skb, +- unsigned int ticket_offset, unsigned int ticket_len, ++ void *ticket, unsigned int ticket_len, + struct key **_key); + }; + +@@ -774,6 +773,11 @@ struct rxrpc_call { + struct sk_buff_head recvmsg_queue; /* Queue of packets ready for recvmsg() */ + struct sk_buff_head rx_queue; /* Queue of packets for this call to receive */ + struct sk_buff_head rx_oos_queue; /* Queue of out of sequence packets */ ++ void *rx_dec_buffer; /* Decryption buffer */ ++ unsigned short rx_dec_bsize; /* rx_dec_buffer size */ ++ unsigned short rx_dec_offset; /* Decrypted packet data offset */ ++ unsigned short rx_dec_len; /* Decrypted packet data len */ ++ rxrpc_seq_t rx_dec_seq; /* Packet in decryption buffer */ + + rxrpc_seq_t rx_highest_seq; /* Higest sequence number received */ + rxrpc_seq_t rx_consumed; /* Highest packet consumed */ +diff --git a/net/rxrpc/call_event.c b/net/rxrpc/call_event.c +index 2b19b252225e..fec59d9338b9 100644 +--- a/net/rxrpc/call_event.c ++++ b/net/rxrpc/call_event.c +@@ -332,27 +332,7 @@ bool rxrpc_input_call_event(struct rxrpc_call *call) + + saw_ack |= sp->hdr.type == RXRPC_PACKET_TYPE_ACK; + +- if (sp->hdr.type == RXRPC_PACKET_TYPE_DATA && +- sp->hdr.securityIndex != 0 && +- (skb_cloned(skb) || +- skb_has_frag_list(skb) || +- skb_has_shared_frag(skb))) { +- /* Unshare the packet so that it can be +- * modified by in-place decryption. +- */ +- struct sk_buff *nskb = skb_copy(skb, GFP_ATOMIC); +- +- if (nskb) { +- rxrpc_new_skb(nskb, rxrpc_skb_new_unshared); +- rxrpc_input_call_packet(call, nskb); +- rxrpc_free_skb(nskb, rxrpc_skb_put_call_rx); +- } else { +- /* OOM - Drop the packet. */ +- rxrpc_see_skb(skb, rxrpc_skb_see_unshare_nomem); +- } +- } else { +- rxrpc_input_call_packet(call, skb); +- } ++ rxrpc_input_call_packet(call, skb); + rxrpc_free_skb(skb, rxrpc_skb_put_call_rx); + did_receive = true; + } +diff --git a/net/rxrpc/call_object.c b/net/rxrpc/call_object.c +index f035f486c139..fcb9d38bb521 100644 +--- a/net/rxrpc/call_object.c ++++ b/net/rxrpc/call_object.c +@@ -152,6 +152,7 @@ struct rxrpc_call *rxrpc_alloc_call(struct rxrpc_sock *rx, gfp_t gfp, + spin_lock_init(&call->notify_lock); + refcount_set(&call->ref, 1); + call->debug_id = debug_id; ++ call->rx_pkt_offset = USHRT_MAX; + call->tx_total_len = -1; + call->tx_jumbo_max = 1; + call->next_rx_timo = 20 * HZ; +@@ -553,6 +554,7 @@ static void rxrpc_cleanup_rx_buffers(struct rxrpc_call *call) + rxrpc_purge_queue(&call->recvmsg_queue); + rxrpc_purge_queue(&call->rx_queue); + rxrpc_purge_queue(&call->rx_oos_queue); ++ kfree(call->rx_dec_buffer); + } + + /* +diff --git a/net/rxrpc/conn_event.c b/net/rxrpc/conn_event.c +index 442414d90ba1..c96ca615b787 100644 +--- a/net/rxrpc/conn_event.c ++++ b/net/rxrpc/conn_event.c +@@ -243,28 +243,22 @@ static void rxrpc_call_is_secure(struct rxrpc_call *call) + static int rxrpc_verify_response(struct rxrpc_connection *conn, + struct sk_buff *skb) + { ++ unsigned int len = skb->len - sizeof(struct rxrpc_wire_header); ++ void *buffer; + int ret; + +- if (skb_cloned(skb) || skb_has_frag_list(skb) || +- skb_has_shared_frag(skb)) { +- /* Copy the packet if shared so that we can do in-place +- * decryption. +- */ +- struct sk_buff *nskb = skb_copy(skb, GFP_NOFS); +- +- if (nskb) { +- rxrpc_new_skb(nskb, rxrpc_skb_new_unshared); +- ret = conn->security->verify_response(conn, nskb); +- rxrpc_free_skb(nskb, rxrpc_skb_put_response_copy); +- } else { +- /* OOM - Drop the packet. */ +- rxrpc_see_skb(skb, rxrpc_skb_see_unshare_nomem); +- ret = -ENOMEM; +- } +- } else { +- ret = conn->security->verify_response(conn, skb); +- } ++ buffer = kmalloc(len, GFP_NOFS); ++ if (!buffer) ++ return -ENOMEM; ++ ++ ret = skb_copy_bits(skb, sizeof(struct rxrpc_wire_header), buffer, len); ++ if (ret < 0) ++ goto out; ++ ++ ret = conn->security->verify_response(conn, skb, buffer, len); + ++out: ++ kfree(buffer); + return ret; + } + +diff --git a/net/rxrpc/insecure.c b/net/rxrpc/insecure.c +index 0a260df45d25..0b39046bdc61 100644 +--- a/net/rxrpc/insecure.c ++++ b/net/rxrpc/insecure.c +@@ -32,9 +32,6 @@ static int none_secure_packet(struct rxrpc_call *call, struct rxrpc_txbuf *txb) + + static int none_verify_packet(struct rxrpc_call *call, struct sk_buff *skb) + { +- struct rxrpc_skb_priv *sp = rxrpc_skb(skb); +- +- sp->flags |= RXRPC_RX_VERIFIED; + return 0; + } + +@@ -57,9 +54,10 @@ static int none_sendmsg_respond_to_challenge(struct sk_buff *challenge, + } + + static int none_verify_response(struct rxrpc_connection *conn, +- struct sk_buff *skb) ++ struct sk_buff *response_skb, ++ void *response, unsigned int len) + { +- return rxrpc_abort_conn(conn, skb, RX_PROTOCOL_ERROR, -EPROTO, ++ return rxrpc_abort_conn(conn, response_skb, RX_PROTOCOL_ERROR, -EPROTO, + rxrpc_eproto_rxnull_response); + } + +diff --git a/net/rxrpc/recvmsg.c b/net/rxrpc/recvmsg.c +index e1f7513a46db..0802f12cbbfc 100644 +--- a/net/rxrpc/recvmsg.c ++++ b/net/rxrpc/recvmsg.c +@@ -147,15 +147,55 @@ static void rxrpc_rotate_rx_window(struct rxrpc_call *call) + } + + /* +- * Decrypt and verify a DATA packet. ++ * Decrypt and verify a DATA packet. The content of the packet is pulled out ++ * into a flat buffer rather than decrypting in place in the skbuff. This also ++ * has the advantage of aligning the buffer correctly for the crypto routines. ++ * ++ * We keep track of the sequence number of the packet currently decrypted into ++ * the buffer in ->rx_dec_seq. Unfortunately, this means that a MSG_PEEK of ++ * more than one byte may cause a later packet to be decrypted into the buffer, ++ * requiring the original to be re-decrypted when recvmsg() is called again. + */ + static int rxrpc_verify_data(struct rxrpc_call *call, struct sk_buff *skb) + { + struct rxrpc_skb_priv *sp = rxrpc_skb(skb); ++ int ret; + +- if (sp->flags & RXRPC_RX_VERIFIED) ++ if (call->rx_dec_seq == sp->hdr.seq && call->rx_dec_buffer) + return 0; +- return call->security->verify_packet(call, skb); ++ ++ if (sp->len > call->rx_dec_bsize) { ++ /* Make sure we can hold a 1412-byte jumbo subpacket and make ++ * sure that the buffer size is aligned to a crypto blocksize. ++ */ ++ size_t size = max(round_up(sp->len, 32), 2048); ++ void *buffer = krealloc(call->rx_dec_buffer, size, GFP_NOFS); ++ ++ if (!buffer) ++ return -ENOMEM; ++ call->rx_dec_buffer = buffer; ++ call->rx_dec_bsize = size; ++ } ++ ++ ret = -EFAULT; ++ if (skb_copy_bits(skb, sp->offset, call->rx_dec_buffer, sp->len) < 0) ++ goto err; ++ ++ call->rx_dec_offset = 0; ++ call->rx_dec_len = sp->len; ++ call->rx_dec_seq = sp->hdr.seq; ++ ret = call->security->verify_packet(call, skb); ++ if (ret < 0) ++ goto err; ++ return 0; ++ ++err: ++ kfree(call->rx_dec_buffer); ++ call->rx_dec_buffer = NULL; ++ call->rx_dec_bsize = 0; ++ call->rx_dec_offset = 0; ++ call->rx_dec_len = 0; ++ return ret; + } + + /* +@@ -283,16 +323,19 @@ static int rxrpc_recvmsg_data(struct socket *sock, struct rxrpc_call *call, + if (msg) + sock_recv_timestamp(msg, sock->sk, skb); + +- if (rx_pkt_offset == 0) { ++ if (rx_pkt_offset == USHRT_MAX) { + ret2 = rxrpc_verify_data(call, skb); + trace_rxrpc_recvdata(call, rxrpc_recvmsg_next, seq, +- sp->offset, sp->len, ret2); ++ call->rx_dec_offset, ++ call->rx_dec_len, ret2); + if (ret2 < 0) { + ret = ret2; + goto out; + } +- rx_pkt_offset = sp->offset; +- rx_pkt_len = sp->len; ++ sp = rxrpc_skb(skb); ++ seq = sp->hdr.seq; ++ rx_pkt_offset = call->rx_dec_offset; ++ rx_pkt_len = call->rx_dec_len; + } else { + trace_rxrpc_recvdata(call, rxrpc_recvmsg_cont, seq, + rx_pkt_offset, rx_pkt_len, 0); +@@ -304,10 +347,10 @@ static int rxrpc_recvmsg_data(struct socket *sock, struct rxrpc_call *call, + if (copy > remain) + copy = remain; + if (copy > 0) { +- ret2 = skb_copy_datagram_iter(skb, rx_pkt_offset, iter, +- copy); +- if (ret2 < 0) { +- ret = ret2; ++ ret2 = copy_to_iter(call->rx_dec_buffer + rx_pkt_offset, ++ copy, iter); ++ if (ret2 != copy) { ++ ret = -EFAULT; + goto out; + } + +@@ -328,13 +371,18 @@ static int rxrpc_recvmsg_data(struct socket *sock, struct rxrpc_call *call, + /* The whole packet has been transferred. */ + if (sp->hdr.flags & RXRPC_LAST_PACKET) + ret = 1; +- rx_pkt_offset = 0; ++ rx_pkt_offset = USHRT_MAX; + rx_pkt_len = 0; + ++ /* Terminate the receive here for MSG_PEEK otherwise we'd have ++ * to replace the contents of ->rx_dec_buffer. ++ */ ++ if (unlikely(flags & MSG_PEEK)) ++ break; ++ + skb = skb_peek_next(skb, &call->recvmsg_queue); + +- if (!(flags & MSG_PEEK)) +- rxrpc_rotate_rx_window(call); ++ rxrpc_rotate_rx_window(call); + + if (!rx->app_ops && + !skb_queue_empty_lockless(&rx->recvmsg_oobq)) { +diff --git a/net/rxrpc/rxgk.c b/net/rxrpc/rxgk.c +index 0d5e654da918..a1ee102abae1 100644 +--- a/net/rxrpc/rxgk.c ++++ b/net/rxrpc/rxgk.c +@@ -473,15 +473,20 @@ static int rxgk_verify_packet_integrity(struct rxrpc_call *call, + struct rxrpc_skb_priv *sp = rxrpc_skb(skb); + struct rxgk_header *hdr; + struct krb5_buffer metadata; +- unsigned int offset = sp->offset, len = sp->len; ++ unsigned int len = call->rx_dec_len; + size_t data_offset = 0, data_len = len; ++ void *data = call->rx_dec_buffer, *p = data; + u32 ac = 0; + int ret = -ENOMEM; + + _enter(""); + +- crypto_krb5_where_is_the_data(gk->krb5, KRB5_CHECKSUM_MODE, +- &data_offset, &data_len); ++ if (crypto_krb5_where_is_the_data(gk->krb5, KRB5_CHECKSUM_MODE, ++ &data_offset, &data_len) < 0) { ++ ret = rxrpc_abort_eproto(call, skb, RXGK_PACKETSHORT, ++ rxgk_abort_1_short_header); ++ goto put_gk; + } - return true; + hdr = kzalloc_obj(*hdr, GFP_NOFS); + if (!hdr) +@@ -496,16 +501,15 @@ static int rxgk_verify_packet_integrity(struct rxrpc_call *call, + + metadata.len = sizeof(*hdr); + metadata.data = hdr; +- ret = rxgk_verify_mic_skb(gk->krb5, gk->rx_Kc, &metadata, +- skb, &offset, &len, &ac); ++ ret = rxgk_verify_mic(gk->krb5, gk->rx_Kc, &metadata, &p, &len, &ac); + kfree(hdr); + if (ret < 0) { + if (ret != -ENOMEM) + rxrpc_abort_eproto(call, skb, ac, + rxgk_abort_1_verify_mic_eproto); + } else { +- sp->offset = offset; +- sp->len = len; ++ call->rx_dec_offset = p - data; ++ call->rx_dec_len = len; + } + + put_gk: +@@ -522,49 +526,53 @@ static int rxgk_verify_packet_encrypted(struct rxrpc_call *call, + struct sk_buff *skb) + { + struct rxrpc_skb_priv *sp = rxrpc_skb(skb); +- struct rxgk_header hdr; +- unsigned int offset = sp->offset, len = sp->len; ++ struct rxgk_header *hdr; ++ unsigned int offset = 0, len = call->rx_dec_len; ++ void *data = call->rx_dec_buffer, *p = data; + int ret; + u32 ac = 0; + + _enter(""); + +- ret = rxgk_decrypt_skb(gk->krb5, gk->rx_enc, skb, &offset, &len, &ac); ++ if (crypto_krb5_check_data_len(gk->krb5, KRB5_ENCRYPT_MODE, ++ len, sizeof(*hdr)) < 0) { ++ ret = rxrpc_abort_eproto(call, skb, RXGK_PACKETSHORT, ++ rxgk_abort_2_short_header); ++ goto error; ++ } ++ ++ ret = rxgk_decrypt(gk->krb5, gk->rx_enc, &p, &len, &ac); + if (ret < 0) { + if (ret != -ENOMEM) + rxrpc_abort_eproto(call, skb, ac, rxgk_abort_2_decrypt_eproto); + goto error; + } ++ offset = p - data; + +- if (len < sizeof(hdr)) { ++ if (len < sizeof(*hdr)) { + ret = rxrpc_abort_eproto(call, skb, RXGK_PACKETSHORT, + rxgk_abort_2_short_header); + goto error; + } + + /* Extract the header from the skb */ +- ret = skb_copy_bits(skb, offset, &hdr, sizeof(hdr)); +- if (ret < 0) { +- ret = rxrpc_abort_eproto(call, skb, RXGK_PACKETSHORT, +- rxgk_abort_2_short_encdata); +- goto error; +- } +- offset += sizeof(hdr); +- len -= sizeof(hdr); +- +- if (ntohl(hdr.epoch) != call->conn->proto.epoch || +- ntohl(hdr.cid) != call->cid || +- ntohl(hdr.call_number) != call->call_id || +- ntohl(hdr.seq) != sp->hdr.seq || +- ntohl(hdr.sec_index) != call->security_ix || +- ntohl(hdr.data_len) > len) { ++ hdr = data + offset; ++ offset += sizeof(*hdr); ++ len -= sizeof(*hdr); ++ ++ if (ntohl(hdr->epoch) != call->conn->proto.epoch || ++ ntohl(hdr->cid) != call->cid || ++ ntohl(hdr->call_number) != call->call_id || ++ ntohl(hdr->seq) != sp->hdr.seq || ++ ntohl(hdr->sec_index) != call->security_ix || ++ ntohl(hdr->data_len) > len) { + ret = rxrpc_abort_eproto(call, skb, RXGK_SEALEDINCON, + rxgk_abort_2_short_data); + goto error; + } + +- sp->offset = offset; +- sp->len = ntohl(hdr.data_len); ++ call->rx_dec_offset = offset; ++ call->rx_dec_len = ntohl(hdr->data_len); + ret = 0; + error: + rxgk_put(gk); +@@ -1076,11 +1084,12 @@ static int rxgk_sendmsg_respond_to_challenge(struct sk_buff *challenge, + * unsigned int call_numbers<>; + * }; + */ +-static int rxgk_do_verify_authenticator(struct rxrpc_connection *conn, +- const struct krb5_enctype *krb5, +- struct sk_buff *skb, +- __be32 *p, __be32 *end) ++static int rxgk_verify_authenticator(struct rxrpc_connection *conn, ++ const struct krb5_enctype *krb5, ++ struct sk_buff *skb, ++ void *auth, unsigned int auth_len) + { ++ __be32 *p = auth, *end = auth + auth_len; + u32 app_len, call_count, level, epoch, cid, i; + + _enter(""); +@@ -1143,37 +1152,6 @@ static int rxgk_do_verify_authenticator(struct rxrpc_connection *conn, + return 0; } -@@ -398,12 +401,21 @@ TC_INDIRECT_SCOPE int tcf_pedit_act(struct sk_buff *skb, + +-/* +- * Extract the authenticator and verify it. +- */ +-static int rxgk_verify_authenticator(struct rxrpc_connection *conn, +- const struct krb5_enctype *krb5, +- struct sk_buff *skb, +- unsigned int auth_offset, unsigned int auth_len) +-{ +- void *auth; +- __be32 *p; +- int ret; +- +- auth = kmalloc(auth_len, GFP_NOFS); +- if (!auth) +- return -ENOMEM; +- +- ret = skb_copy_bits(skb, auth_offset, auth, auth_len); +- if (ret < 0) { +- ret = rxrpc_abort_conn(conn, skb, RXGK_NOTAUTH, -EPROTO, +- rxgk_abort_resp_short_auth); +- goto error; +- } +- +- p = auth; +- ret = rxgk_do_verify_authenticator(conn, krb5, skb, p, +- p + auth_len / sizeof(*p)); +-error: +- kfree(auth); +- return ret; +-} +- + /* + * Verify a response. + * +@@ -1184,49 +1162,45 @@ static int rxgk_verify_authenticator(struct rxrpc_connection *conn, + * }; + */ + static int rxgk_verify_response(struct rxrpc_connection *conn, +- struct sk_buff *skb) ++ struct sk_buff *skb, ++ void *buffer, unsigned int len) + { + const struct krb5_enctype *krb5; + struct rxrpc_key_token *token; + struct rxrpc_skb_priv *sp = rxrpc_skb(skb); +- struct rxgk_response rhdr; ++ struct rxgk_response *rhdr; + struct rxgk_context *gk; + struct key *key = NULL; +- unsigned int offset = sizeof(struct rxrpc_wire_header); +- unsigned int len = skb->len - sizeof(struct rxrpc_wire_header); +- unsigned int token_offset, token_len; +- unsigned int auth_offset, auth_len; ++ unsigned int resp_token_len, auth_len; ++ void *resp_token, *auth; + __be32 xauth_len; + int ret, ec; + + _enter("{%d}", conn->debug_id); + + /* Parse the RXGK_Response object */ +- if (sizeof(rhdr) + sizeof(__be32) > len) ++ if (len < sizeof(*rhdr) + sizeof(__be32)) + goto short_packet; +- +- if (skb_copy_bits(skb, offset, &rhdr, sizeof(rhdr)) < 0) +- goto short_packet; +- offset += sizeof(rhdr); +- len -= sizeof(rhdr); +- +- token_offset = offset; +- token_len = ntohl(rhdr.token_len); +- if (token_len > len || +- xdr_round_up(token_len) + sizeof(__be32) > len) ++ rhdr = buffer; ++ buffer += sizeof(*rhdr); ++ len -= sizeof(*rhdr); ++ ++ resp_token = buffer; ++ resp_token_len = ntohl(rhdr->token_len); ++ if (resp_token_len > len || ++ xdr_round_up(resp_token_len) + sizeof(__be32) > len) + goto short_packet; + +- trace_rxrpc_rx_response(conn, sp->hdr.serial, 0, sp->hdr.cksum, token_len); ++ trace_rxrpc_rx_response(conn, sp->hdr.serial, 0, sp->hdr.cksum, resp_token_len); + +- offset += xdr_round_up(token_len); +- len -= xdr_round_up(token_len); ++ buffer += xdr_round_up(resp_token_len); ++ len -= xdr_round_up(resp_token_len); + +- if (skb_copy_bits(skb, offset, &xauth_len, sizeof(xauth_len)) < 0) +- goto short_packet; +- offset += sizeof(xauth_len); ++ xauth_len = *(__be32 *)buffer; ++ buffer += sizeof(xauth_len); + len -= sizeof(xauth_len); + +- auth_offset = offset; ++ auth = buffer; + auth_len = ntohl(xauth_len); + if (auth_len > len) + goto short_packet; +@@ -1241,7 +1215,7 @@ static int rxgk_verify_response(struct rxrpc_connection *conn, + * to the app to deal with - which might mean a round trip to + * userspace. + */ +- ret = rxgk_extract_token(conn, skb, token_offset, token_len, &key); ++ ret = rxgk_extract_token(conn, skb, resp_token, resp_token_len, &key); + if (ret < 0) + goto out; + +@@ -1255,7 +1229,7 @@ static int rxgk_verify_response(struct rxrpc_connection *conn, + */ + token = key->payload.data[0]; + conn->security_level = token->rxgk->level; +- conn->rxgk.start_time = __be64_to_cpu(rhdr.start_time); ++ conn->rxgk.start_time = __be64_to_cpu(rhdr->start_time); + + gk = rxgk_generate_transport_key(conn, token->rxgk, sp->hdr.cksum, GFP_NOFS); + if (IS_ERR(gk)) { +@@ -1265,18 +1239,18 @@ static int rxgk_verify_response(struct rxrpc_connection *conn, + + krb5 = gk->krb5; + +- trace_rxrpc_rx_response(conn, sp->hdr.serial, krb5->etype, sp->hdr.cksum, token_len); ++ trace_rxrpc_rx_response(conn, sp->hdr.serial, krb5->etype, sp->hdr.cksum, ++ resp_token_len); + + /* Decrypt, parse and verify the authenticator. */ +- ret = rxgk_decrypt_skb(krb5, gk->resp_enc, skb, +- &auth_offset, &auth_len, &ec); ++ ret = rxgk_decrypt(krb5, gk->resp_enc, &auth, &auth_len, &ec); + if (ret < 0) { + rxrpc_abort_conn(conn, skb, RXGK_SEALEDINCON, ret, + rxgk_abort_resp_auth_dec); + goto out_gk; + } + +- ret = rxgk_verify_authenticator(conn, krb5, skb, auth_offset, auth_len); ++ ret = rxgk_verify_authenticator(conn, krb5, skb, auth, auth_len); + if (ret < 0) + goto out_gk; + +diff --git a/net/rxrpc/rxgk_app.c b/net/rxrpc/rxgk_app.c +index 0ef2a29eb695..200a30064fae 100644 +--- a/net/rxrpc/rxgk_app.c ++++ b/net/rxrpc/rxgk_app.c +@@ -40,7 +40,7 @@ + * }; + */ + int rxgk_yfs_decode_ticket(struct rxrpc_connection *conn, struct sk_buff *skb, +- unsigned int ticket_offset, unsigned int ticket_len, ++ void *buffer, unsigned int ticket_len, + struct key **_key) + { + struct rxrpc_key_token *token; +@@ -49,7 +49,7 @@ int rxgk_yfs_decode_ticket(struct rxrpc_connection *conn, struct sk_buff *skb, + size_t pre_ticket_len, payload_len; + unsigned int klen, enctype; + void *payload, *ticket; +- __be32 *t, *p, *q, tmp[2]; ++ __be32 *t, *p, *q, *tmp; + int ret; + + _enter(""); +@@ -59,10 +59,7 @@ int rxgk_yfs_decode_ticket(struct rxrpc_connection *conn, struct sk_buff *skb, + rxgk_abort_resp_short_yfs_tkt); + + /* Get the session key length */ +- ret = skb_copy_bits(skb, ticket_offset, tmp, sizeof(tmp)); +- if (ret < 0) +- return rxrpc_abort_conn(conn, skb, RXGK_INCONSISTENCY, -EPROTO, +- rxgk_abort_resp_short_yfs_klen); ++ tmp = buffer; + enctype = ntohl(tmp[0]); + klen = ntohl(tmp[1]); + +@@ -84,12 +81,7 @@ int rxgk_yfs_decode_ticket(struct rxrpc_connection *conn, struct sk_buff *skb, + * it. + */ + ticket = payload + pre_ticket_len; +- ret = skb_copy_bits(skb, ticket_offset, ticket, ticket_len); +- if (ret < 0) { +- ret = rxrpc_abort_conn(conn, skb, RXGK_INCONSISTENCY, -EPROTO, +- rxgk_abort_resp_short_yfs_tkt); +- goto error; +- } ++ memcpy(ticket, buffer, ticket_len); + + /* Fill out the form header. */ + p = payload; +@@ -131,7 +123,7 @@ int rxgk_yfs_decode_ticket(struct rxrpc_connection *conn, struct sk_buff *skb, + goto error; + } + +- /* Ticket read in with skb_copy_bits above */ ++ /* Ticket appended above. */ + q += xdr_round_up(ticket_len) / 4; + if (WARN_ON((unsigned long)q - (unsigned long)payload != payload_len)) { + ret = -EIO; +@@ -182,14 +174,15 @@ int rxgk_yfs_decode_ticket(struct rxrpc_connection *conn, struct sk_buff *skb, + * [tools.ietf.org/html/draft-wilkinson-afs3-rxgk-afs-08 sec 6.1] + */ + int rxgk_extract_token(struct rxrpc_connection *conn, struct sk_buff *skb, +- unsigned int token_offset, unsigned int token_len, ++ void *token, unsigned int token_len, + struct key **_key) + { + const struct krb5_enctype *krb5; + const struct krb5_buffer *server_secret; + struct crypto_aead *token_enc = NULL; + struct key *server_key; +- unsigned int ticket_offset, ticket_len; ++ unsigned int ticket_len; ++ void *ticket; + u32 kvno, enctype; + int ret, ec = 0; + +@@ -197,24 +190,23 @@ int rxgk_extract_token(struct rxrpc_connection *conn, struct sk_buff *skb, + __be32 kvno; + __be32 enctype; + __be32 token_len; +- } container; ++ } *container; + +- if (token_len < sizeof(container)) ++ if (token_len < sizeof(*container)) + goto short_packet; + + /* Decode the RXGK_TokenContainer object. This tells us which server + * key we should be using. We can then fetch the key, get the secret + * and set up the crypto to extract the token. + */ +- if (skb_copy_bits(skb, token_offset, &container, sizeof(container)) < 0) +- goto short_packet; ++ container = token; ++ token += sizeof(*container); + +- kvno = ntohl(container.kvno); +- enctype = ntohl(container.enctype); +- ticket_len = ntohl(container.token_len); +- ticket_offset = token_offset + sizeof(container); ++ kvno = ntohl(container->kvno); ++ enctype = ntohl(container->enctype); ++ ticket_len = ntohl(container->token_len); + +- if (ticket_len > xdr_round_down(token_len - sizeof(container))) ++ if (ticket_len > xdr_round_down(token_len - sizeof(*container))) + goto short_packet; + + _debug("KVNO %u", kvno); +@@ -237,8 +229,8 @@ int rxgk_extract_token(struct rxrpc_connection *conn, struct sk_buff *skb, + * gain access to K0, from which we can derive the transport key and + * thence decode the authenticator. + */ +- ret = rxgk_decrypt_skb(krb5, token_enc, skb, +- &ticket_offset, &ticket_len, &ec); ++ ticket = token; ++ ret = rxgk_decrypt(krb5, token_enc, &ticket, &ticket_len, &ec); + crypto_free_aead(token_enc); + token_enc = NULL; + if (ret < 0) { +@@ -248,7 +240,7 @@ int rxgk_extract_token(struct rxrpc_connection *conn, struct sk_buff *skb, + return ret; + } + +- ret = conn->security->default_decode_ticket(conn, skb, ticket_offset, ++ ret = conn->security->default_decode_ticket(conn, skb, ticket, + ticket_len, _key); + if (ret < 0) + goto cant_get_token; +diff --git a/net/rxrpc/rxgk_common.h b/net/rxrpc/rxgk_common.h +index 1e257d7ab8ec..3deed5863f5a 100644 +--- a/net/rxrpc/rxgk_common.h ++++ b/net/rxrpc/rxgk_common.h +@@ -41,10 +41,10 @@ struct rxgk_context { + * rxgk_app.c + */ + int rxgk_yfs_decode_ticket(struct rxrpc_connection *conn, struct sk_buff *skb, +- unsigned int ticket_offset, unsigned int ticket_len, ++ void *ticket, unsigned int ticket_len, + struct key **_key); + int rxgk_extract_token(struct rxrpc_connection *conn, struct sk_buff *skb, +- unsigned int token_offset, unsigned int token_len, ++ void *token, unsigned int token_len, + struct key **_key); + + /* +@@ -62,31 +62,30 @@ int rxgk_set_up_token_cipher(const struct krb5_buffer *server_key, + gfp_t gfp); + + /* +- * Apply decryption and checksumming functions to part of an skbuff. The +- * offset and length are updated to reflect the actual content of the encrypted ++ * Apply decryption and checksumming functions a flat data buffer. The data ++ * point and length are updated to reflect the actual content of the encrypted + * region. + */ +-static inline +-int rxgk_decrypt_skb(const struct krb5_enctype *krb5, +- struct crypto_aead *aead, +- struct sk_buff *skb, +- unsigned int *_offset, unsigned int *_len, +- int *_error_code) ++static inline int rxgk_decrypt(const struct krb5_enctype *krb5, ++ struct crypto_aead *aead, ++ void **_data, unsigned int *_len, ++ int *_error_code) + { +- struct scatterlist sg[16]; ++ struct scatterlist sg[1]; + size_t offset = 0, len = *_len; +- int nr_sg, ret; ++ int ret; + +- sg_init_table(sg, ARRAY_SIZE(sg)); +- nr_sg = skb_to_sgvec(skb, sg, *_offset, len); +- if (unlikely(nr_sg < 0)) +- return nr_sg; ++ sg_init_one(sg, *_data, len); + +- ret = crypto_krb5_decrypt(krb5, aead, sg, nr_sg, +- &offset, &len); ++ ret = crypto_krb5_decrypt(krb5, aead, sg, 1, &offset, &len); + switch (ret) { + case 0: +- *_offset += offset; ++ if (offset & 3) { ++ *_error_code = RXGK_INCONSISTENCY; ++ ret = -EPROTO; ++ break; ++ } ++ *_data += offset; + *_len = len; + break; + case -EBADMSG: /* Checksum mismatch. */ +@@ -106,31 +105,26 @@ int rxgk_decrypt_skb(const struct krb5_enctype *krb5, + } + + /* +- * Check the MIC on a region of an skbuff. The offset and length are updated +- * to reflect the actual content of the secure region. ++ * Check the MIC on a flat buffer. The data pointer and length are updated to ++ * reflect the actual content of the secure region. + */ + static inline +-int rxgk_verify_mic_skb(const struct krb5_enctype *krb5, +- struct crypto_shash *shash, +- const struct krb5_buffer *metadata, +- struct sk_buff *skb, +- unsigned int *_offset, unsigned int *_len, +- u32 *_error_code) ++int rxgk_verify_mic(const struct krb5_enctype *krb5, ++ struct crypto_shash *shash, ++ const struct krb5_buffer *metadata, ++ void **_data, unsigned int *_len, ++ u32 *_error_code) + { +- struct scatterlist sg[16]; ++ struct scatterlist sg[1]; + size_t offset = 0, len = *_len; +- int nr_sg, ret; ++ int ret; + +- sg_init_table(sg, ARRAY_SIZE(sg)); +- nr_sg = skb_to_sgvec(skb, sg, *_offset, len); +- if (unlikely(nr_sg < 0)) +- return nr_sg; ++ sg_init_one(sg, *_data, len); + +- ret = crypto_krb5_verify_mic(krb5, shash, metadata, sg, nr_sg, +- &offset, &len); ++ ret = crypto_krb5_verify_mic(krb5, shash, metadata, sg, 1, &offset, &len); + switch (ret) { + case 0: +- *_offset += offset; ++ *_data += offset; + *_len = len; + break; + case -EBADMSG: /* Checksum mismatch */ +diff --git a/net/rxrpc/rxkad.c b/net/rxrpc/rxkad.c +index cba7935977f0..e970bf3ae78a 100644 +--- a/net/rxrpc/rxkad.c ++++ b/net/rxrpc/rxkad.c +@@ -430,27 +430,25 @@ static int rxkad_verify_packet_1(struct rxrpc_call *call, struct sk_buff *skb, + rxrpc_seq_t seq, + struct skcipher_request *req) + { +- struct rxkad_level1_hdr sechdr; ++ struct rxkad_level1_hdr *sechdr; + struct rxrpc_skb_priv *sp = rxrpc_skb(skb); + struct rxrpc_crypt iv; +- struct scatterlist sg[16]; +- u32 data_size, buf; ++ struct scatterlist sg[1]; ++ void *data = call->rx_dec_buffer; ++ u32 len = sp->len, data_size, buf; + u16 check; + int ret; + + _enter(""); + +- if (sp->len < 8) ++ if (len < 8) + return rxrpc_abort_eproto(call, skb, RXKADSEALEDINCON, + rxkad_abort_1_short_header); + + /* Decrypt the skbuff in-place. TODO: We really want to decrypt + * directly into the target buffer. + */ +- sg_init_table(sg, ARRAY_SIZE(sg)); +- ret = skb_to_sgvec(skb, sg, sp->offset, 8); +- if (unlikely(ret < 0)) +- return ret; ++ sg_init_one(sg, data, len); + + /* start the decryption afresh */ + memset(&iv, 0, sizeof(iv)); +@@ -464,13 +462,11 @@ static int rxkad_verify_packet_1(struct rxrpc_call *call, struct sk_buff *skb, + return ret; + + /* Extract the decrypted packet length */ +- if (skb_copy_bits(skb, sp->offset, &sechdr, sizeof(sechdr)) < 0) +- return rxrpc_abort_eproto(call, skb, RXKADDATALEN, +- rxkad_abort_1_short_encdata); +- sp->offset += sizeof(sechdr); +- sp->len -= sizeof(sechdr); ++ sechdr = data; ++ call->rx_dec_offset = sizeof(*sechdr); ++ len -= sizeof(*sechdr); + +- buf = ntohl(sechdr.data_size); ++ buf = ntohl(sechdr->data_size); + data_size = buf & 0xffff; + + check = buf >> 16; +@@ -479,10 +475,10 @@ static int rxkad_verify_packet_1(struct rxrpc_call *call, struct sk_buff *skb, + if (check != 0) + return rxrpc_abort_eproto(call, skb, RXKADSEALEDINCON, + rxkad_abort_1_short_check); +- if (data_size > sp->len) ++ if (data_size > len) + return rxrpc_abort_eproto(call, skb, RXKADDATALEN, + rxkad_abort_1_short_data); +- sp->len = data_size; ++ call->rx_dec_len = data_size; + + _leave(" = 0 [dlen=%x]", data_size); + return 0; +@@ -496,43 +492,28 @@ static int rxkad_verify_packet_2(struct rxrpc_call *call, struct sk_buff *skb, + struct skcipher_request *req) + { + const struct rxrpc_key_token *token; +- struct rxkad_level2_hdr sechdr; ++ struct rxkad_level2_hdr *sechdr; + struct rxrpc_skb_priv *sp = rxrpc_skb(skb); + struct rxrpc_crypt iv; +- struct scatterlist _sg[4], *sg; +- u32 data_size, buf; ++ struct scatterlist sg[1]; ++ void *data = call->rx_dec_buffer; ++ u32 len = sp->len, data_size, buf; + u16 check; +- int nsg, ret; ++ int ret; + +- _enter(",{%d}", sp->len); ++ _enter(",{%d}", len); + +- if (sp->len < 8) ++ if (len < 8) + return rxrpc_abort_eproto(call, skb, RXKADSEALEDINCON, + rxkad_abort_2_short_header); + + /* Don't let the crypto algo see a misaligned length. */ +- sp->len = round_down(sp->len, 8); ++ len = round_down(len, 8); + +- /* Decrypt the skbuff in-place. TODO: We really want to decrypt +- * directly into the target buffer. ++ /* Decrypt in place in the call's decryption buffer. TODO: We really ++ * want to decrypt directly into the target buffer. + */ +- sg = _sg; +- nsg = skb_shinfo(skb)->nr_frags + 1; +- if (nsg <= 4) { +- nsg = 4; +- } else { +- sg = kmalloc_objs(*sg, nsg, GFP_NOIO); +- if (!sg) +- return -ENOMEM; +- } +- +- sg_init_table(sg, nsg); +- ret = skb_to_sgvec(skb, sg, sp->offset, sp->len); +- if (unlikely(ret < 0)) { +- if (sg != _sg) +- kfree(sg); +- return ret; +- } ++ sg_init_one(sg, data, len); + + /* decrypt from the session key */ + token = call->conn->key->payload.data[0]; +@@ -540,11 +521,9 @@ static int rxkad_verify_packet_2(struct rxrpc_call *call, struct sk_buff *skb, + + skcipher_request_set_sync_tfm(req, call->conn->rxkad.cipher); + skcipher_request_set_callback(req, 0, NULL, NULL); +- skcipher_request_set_crypt(req, sg, sg, sp->len, iv.x); ++ skcipher_request_set_crypt(req, sg, sg, len, iv.x); + ret = crypto_skcipher_decrypt(req); + skcipher_request_zero(req); +- if (sg != _sg) +- kfree(sg); + if (ret < 0) { + if (ret == -ENOMEM) + return ret; +@@ -553,13 +532,11 @@ static int rxkad_verify_packet_2(struct rxrpc_call *call, struct sk_buff *skb, + } + + /* Extract the decrypted packet length */ +- if (skb_copy_bits(skb, sp->offset, &sechdr, sizeof(sechdr)) < 0) +- return rxrpc_abort_eproto(call, skb, RXKADDATALEN, +- rxkad_abort_2_short_len); +- sp->offset += sizeof(sechdr); +- sp->len -= sizeof(sechdr); ++ sechdr = data; ++ call->rx_dec_offset = sizeof(*sechdr); ++ len -= sizeof(*sechdr); + +- buf = ntohl(sechdr.data_size); ++ buf = ntohl(sechdr->data_size); + data_size = buf & 0xffff; + + check = buf >> 16; +@@ -569,17 +546,18 @@ static int rxkad_verify_packet_2(struct rxrpc_call *call, struct sk_buff *skb, + return rxrpc_abort_eproto(call, skb, RXKADSEALEDINCON, + rxkad_abort_2_short_check); + +- if (data_size > sp->len) ++ if (data_size > len) + return rxrpc_abort_eproto(call, skb, RXKADDATALEN, + rxkad_abort_2_short_data); + +- sp->len = data_size; ++ call->rx_dec_len = data_size; + _leave(" = 0 [dlen=%x]", data_size); + return 0; + } + + /* +- * Verify the security on a received packet and the subpackets therein. ++ * Verify the security on a received (sub)packet. If the packet needs ++ * modifying (e.g. decrypting), it must be copied. + */ + static int rxkad_verify_packet(struct rxrpc_call *call, struct sk_buff *skb) + { +@@ -985,7 +963,6 @@ static int rxkad_decrypt_ticket(struct rxrpc_connection *conn, + *_expiry = 0; + + ASSERT(server_key->payload.data[0] != NULL); +- ASSERTCMP((unsigned long) ticket & 7UL, ==, 0); + + memcpy(&iv, &server_key->payload.data[2], sizeof(iv)); + +@@ -1134,14 +1111,15 @@ static int rxkad_decrypt_response(struct rxrpc_connection *conn, + * verify a response + */ + static int rxkad_verify_response(struct rxrpc_connection *conn, +- struct sk_buff *skb) ++ struct sk_buff *skb, ++ void *buffer, unsigned int len) + { + struct rxkad_response *response; + struct rxrpc_skb_priv *sp = rxrpc_skb(skb); + struct rxrpc_crypt session_key; + struct key *server_key; + time64_t expiry; +- void *ticket = NULL; ++ void *ticket; + u32 version, kvno, ticket_len, level; + __be32 csum; + int ret, i; +@@ -1164,13 +1142,8 @@ static int rxkad_verify_response(struct rxrpc_connection *conn, + } + } + +- ret = -ENOMEM; +- response = kzalloc_obj(struct rxkad_response, GFP_NOFS); +- if (!response) +- goto error; +- +- if (skb_copy_bits(skb, sizeof(struct rxrpc_wire_header), +- response, sizeof(*response)) < 0) { ++ response = buffer; ++ if (len < sizeof(*response)) { + ret = rxrpc_abort_conn(conn, skb, RXKADPACKETSHORT, -EPROTO, + rxkad_abort_resp_short); + goto error; +@@ -1182,6 +1155,9 @@ static int rxkad_verify_response(struct rxrpc_connection *conn, + + trace_rxrpc_rx_response(conn, sp->hdr.serial, version, kvno, ticket_len); + ++ buffer += sizeof(*response); ++ len -= sizeof(*response); ++ + if (version != RXKAD_VERSION) { + ret = rxrpc_abort_conn(conn, skb, RXKADINCONSISTENCY, -EPROTO, + rxkad_abort_resp_version); +@@ -1201,13 +1177,8 @@ static int rxkad_verify_response(struct rxrpc_connection *conn, + } + + /* extract the kerberos ticket and decrypt and decode it */ +- ret = -ENOMEM; +- ticket = kmalloc(ticket_len, GFP_NOFS); +- if (!ticket) +- goto error; +- +- if (skb_copy_bits(skb, sizeof(struct rxrpc_wire_header) + sizeof(*response), +- ticket, ticket_len) < 0) { ++ ticket = buffer; ++ if (ticket_len >= len) { + ret = rxrpc_abort_conn(conn, skb, RXKADPACKETSHORT, -EPROTO, + rxkad_abort_resp_short_tkt); + goto error; +@@ -1287,8 +1258,6 @@ static int rxkad_verify_response(struct rxrpc_connection *conn, + ret = rxrpc_get_server_data_key(conn, &session_key, expiry, kvno); + + error: +- kfree(ticket); +- kfree(response); + key_put(server_key); + _leave(" = %d", ret); + return ret; +diff --git a/net/sched/act_pedit.c b/net/sched/act_pedit.c +index bc20f08a2789..58a8eae6d43e 100644 +--- a/net/sched/act_pedit.c ++++ b/net/sched/act_pedit.c +@@ -398,11 +398,12 @@ TC_INDIRECT_SCOPE int tcf_pedit_act(struct sk_buff *skb, parms = rcu_dereference_bh(p->parms); @@ -4539,56 +5740,40 @@ index bc20f08a2789..1aa95c34ad87 100644 - skb_network_offset(skb)) + - parms->tcfp_off_max_hint; - if (skb_ensure_writable(skb, min(skb->len, max_offset))) -- goto done; + max_offset = min_t(u32, skb->len, + (skb_transport_header_was_set(skb) ? + skb_transport_offset(skb) : + skb_network_offset(skb)) + + parms->tcfp_off_max_hint); -+ -+ /* If the skb has shared frags the user is likely using zero-copy -+ * (e.g. sendfile). Those page frags may point to page-cache pages; -+ * writing into them would silently corrupt the page cache. -+ * Linearize so pedit operates on a private copy. -+ * TL;DR if you want to use ZC, don't use pedit */ -+ if (skb_has_shared_frag(skb)) { -+ if (__skb_linearize(skb)) -+ goto bad; -+ } ++ if (skb_ensure_writable(skb, max_offset)) + goto done; tcf_lastuse_update(&p->tcf_tm); - tcf_action_update_bstats(&p->common, skb); -@@ -414,8 +426,9 @@ TC_INDIRECT_SCOPE int tcf_pedit_act(struct sk_buff *skb, +@@ -414,8 +415,9 @@ TC_INDIRECT_SCOPE int tcf_pedit_act(struct sk_buff *skb, for (i = parms->tcfp_nkeys; i > 0; i--, tkey++) { int offset = tkey->off; int hoffset = 0; -+ int write_offset, write_len; ++ int write_offset; u32 *ptr, hdata; - u32 val; + u32 val, write_end; int rc; if (tkey_ex) { -@@ -451,12 +464,45 @@ TC_INDIRECT_SCOPE int tcf_pedit_act(struct sk_buff *skb, +@@ -451,12 +453,26 @@ TC_INDIRECT_SCOPE int tcf_pedit_act(struct sk_buff *skb, } } - if (!offset_valid(skb, hoffset + offset)) { - pr_info_ratelimited("tc action pedit offset %d out of bounds\n", hoffset + offset); + write_offset = hoffset + offset; -+ if (unlikely(check_add_overflow(hoffset, offset, -+ &write_offset))) { -+ pr_info_ratelimited("tc action pedit offset overflow\n"); ++ if (!offset_valid(skb, write_offset)) { ++ pr_info_ratelimited("tc action pedit offset %d out of bounds\n", ++ write_offset); goto bad; } - ptr = skb_header_pointer(skb, hoffset + offset, -+ if (!offset_valid(skb, write_offset)) { -+ pr_info_ratelimited("tc action pedit offset %d out of bounds\n", -+ write_offset); -+ goto bad; -+ } -+ + /* Earlier edits can change later header-relative offsets, so + * grow the writable window from the final per-key store. + */ @@ -4601,24 +5786,11 @@ index bc20f08a2789..1aa95c34ad87 100644 + } + } + -+ if (write_offset < 0) { -+ if (skb_cow(skb, -write_offset)) -+ goto bad; -+ } else { -+ if (unlikely(check_add_overflow(write_offset, -+ (int)sizeof(hdata), -+ &write_len))) -+ goto bad; -+ if (skb_ensure_writable(skb, min_t(int, skb->len, -+ write_len))) -+ goto bad; -+ } -+ + ptr = skb_header_pointer(skb, write_offset, sizeof(hdata), &hdata); if (!ptr) goto bad; -@@ -475,7 +521,7 @@ TC_INDIRECT_SCOPE int tcf_pedit_act(struct sk_buff *skb, +@@ -475,7 +491,7 @@ TC_INDIRECT_SCOPE int tcf_pedit_act(struct sk_buff *skb, *ptr = ((*ptr & tkey->mask) ^ val); if (ptr == &hdata) diff --git a/sources b/sources index f6d9c056e..c92d2e776 100644 --- a/sources +++ b/sources @@ -1,3 +1,3 @@ -SHA512 (linux-7.1-rc4-46-gab5fce87a778.tar.xz) = 82530160e17f3c13b3b734a48d31205a05b4394b774345e60bfb72eb3f5bdf10cfd8a00c98e92e9981ea5128585fe30a61f28acc6798e935b291a4effeb0ff28 -SHA512 (kernel-abi-stablelists-7.1.0.tar.xz) = d05571ad19f5b37cd9a4078cfbcd0c5d0a453e0556a4a406936f00f0e9ab97b9913ccf3f6bdc1fd9caa4c5fc5ba6266e44d0b3ae1bf37055f2277173a34176b0 -SHA512 (kernel-kabi-dw-7.1.0.tar.xz) = 9bb7d49af2456c7b09e7336a6fb6e78b2924dcb9006d3df6c1dd13033bf54ff2caf3f32de145caba3c81e14513b53e282253898fadefd2361441ea96370fe9e9 +SHA512 (linux-7.1-rc4-93-g27fa82620cba.tar.xz) = 11035d77f9ff85ea757f2e2f33911ba9c4e04b2fd3f1fa9488c78088d88c5fdc7709cf468636087b10c74e02cab7d5f1ca43f6f67f9e99e25af7b078bb5abdc2 +SHA512 (kernel-abi-stablelists-7.1.0.tar.xz) = ec647596b18c2c0603f4cf9d0ec30fd00d82274611ae9f039b713fda3be6d91db184a6adf4791b494b55b761bc62c757faba30c9fa81c3c0be30259cdd096afa +SHA512 (kernel-kabi-dw-7.1.0.tar.xz) = 4b459c9674e5a4d0539895898daaafd0006c6af4153839ef9695c753fcc7514f7a5f63fa499ef18de4fca2b2837288b506ceae6d4608aa4e0a25a76850c5a424