1 /* SPDX-License-Identifier: GPL-2.0 */ 2 /* 3 * ChaCha stream cipher (s390 optimized) 4 * 5 * Copyright IBM Corp. 2021 6 */ 7 8 #include <linux/cpufeature.h> 9 #include <linux/export.h> 10 #include <linux/kernel.h> 11 #include <linux/sizes.h> 12 #include <asm/fpu.h> 13 #include "chacha-s390.h" 14 15 #define hchacha_block_arch hchacha_block_generic /* not implemented yet */ 16 17 static void chacha_crypt_arch(struct chacha_state *state, u8 *dst, 18 const u8 *src, unsigned int bytes, int nrounds) 19 { 20 /* s390 chacha20 implementation has 20 rounds hard-coded, 21 * it cannot handle a block of data or less, but otherwise 22 * it can handle data of arbitrary size 23 */ 24 if (bytes <= CHACHA_BLOCK_SIZE || nrounds != 20 || !cpu_has_vx()) { 25 chacha_crypt_generic(state, dst, src, bytes, nrounds); 26 } else { 27 DECLARE_KERNEL_FPU_ONSTACK32(vxstate); 28 29 kernel_fpu_begin(&vxstate, KERNEL_VXR); 30 chacha20_vx(dst, src, bytes, &state->x[4], &state->x[12]); 31 kernel_fpu_end(&vxstate, KERNEL_VXR); 32 33 state->x[12] += round_up(bytes, CHACHA_BLOCK_SIZE) / 34 CHACHA_BLOCK_SIZE; 35 } 36 } 37