Path: blob/master/lib/crypto/powerpc/poly1305-p10-glue.c
26292 views
// SPDX-License-Identifier: GPL-2.01/*2* Poly1305 authenticator algorithm, RFC7539.3*4* Copyright 2023- IBM Corp. All rights reserved.5*/6#include <asm/switch_to.h>7#include <crypto/internal/poly1305.h>8#include <linux/cpufeature.h>9#include <linux/jump_label.h>10#include <linux/kernel.h>11#include <linux/module.h>12#include <linux/unaligned.h>1314asmlinkage void poly1305_p10le_4blocks(struct poly1305_block_state *state, const u8 *m, u32 mlen);15asmlinkage void poly1305_64s(struct poly1305_block_state *state, const u8 *m, u32 mlen, int highbit);16asmlinkage void poly1305_emit_64(const struct poly1305_state *state, const u32 nonce[4], u8 digest[POLY1305_DIGEST_SIZE]);1718static __ro_after_init DEFINE_STATIC_KEY_FALSE(have_p10);1920static void vsx_begin(void)21{22preempt_disable();23enable_kernel_vsx();24}2526static void vsx_end(void)27{28disable_kernel_vsx();29preempt_enable();30}3132void poly1305_block_init_arch(struct poly1305_block_state *dctx,33const u8 raw_key[POLY1305_BLOCK_SIZE])34{35if (!static_key_enabled(&have_p10))36return poly1305_block_init_generic(dctx, raw_key);3738dctx->h = (struct poly1305_state){};39dctx->core_r.key.r64[0] = get_unaligned_le64(raw_key + 0);40dctx->core_r.key.r64[1] = get_unaligned_le64(raw_key + 8);41}42EXPORT_SYMBOL_GPL(poly1305_block_init_arch);4344void poly1305_blocks_arch(struct poly1305_block_state *state, const u8 *src,45unsigned int len, u32 padbit)46{47if (!static_key_enabled(&have_p10))48return poly1305_blocks_generic(state, src, len, padbit);49vsx_begin();50if (len >= POLY1305_BLOCK_SIZE * 4) {51poly1305_p10le_4blocks(state, src, len);52src += len - (len % (POLY1305_BLOCK_SIZE * 4));53len %= POLY1305_BLOCK_SIZE * 4;54}55while (len >= POLY1305_BLOCK_SIZE) {56poly1305_64s(state, src, POLY1305_BLOCK_SIZE, padbit);57len -= POLY1305_BLOCK_SIZE;58src += POLY1305_BLOCK_SIZE;59}60vsx_end();61}62EXPORT_SYMBOL_GPL(poly1305_blocks_arch);6364void poly1305_emit_arch(const struct poly1305_state *state,65u8 digest[POLY1305_DIGEST_SIZE],66const u32 nonce[4])67{68if (!static_key_enabled(&have_p10))69return poly1305_emit_generic(state, digest, nonce);70poly1305_emit_64(state, nonce, digest);71}72EXPORT_SYMBOL_GPL(poly1305_emit_arch);7374bool poly1305_is_arch_optimized(void)75{76return static_key_enabled(&have_p10);77}78EXPORT_SYMBOL(poly1305_is_arch_optimized);7980static int __init poly1305_p10_init(void)81{82if (cpu_has_feature(CPU_FTR_ARCH_31))83static_branch_enable(&have_p10);84return 0;85}86subsys_initcall(poly1305_p10_init);8788static void __exit poly1305_p10_exit(void)89{90}91module_exit(poly1305_p10_exit);9293MODULE_LICENSE("GPL");94MODULE_AUTHOR("Danny Tsen <[email protected]>");95MODULE_DESCRIPTION("Optimized Poly1305 for P10");969798