1 // SPDX-License-Identifier: CDDL-1.0 2 /* 3 * CDDL HEADER START 4 * 5 * The contents of this file are subject to the terms of the 6 * Common Development and Distribution License (the "License"). 7 * You may not use this file except in compliance with the License. 8 * 9 * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE 10 * or https://opensource.org/licenses/CDDL-1.0. 11 * See the License for the specific language governing permissions 12 * and limitations under the License. 13 * 14 * When distributing Covered Code, include this CDDL HEADER in each 15 * file and include the License file at usr/src/OPENSOLARIS.LICENSE. 16 * If applicable, add the following below this CDDL HEADER, with the 17 * fields enclosed by brackets "[]" replaced with your own identifying 18 * information: Portions Copyright [yyyy] [name of copyright owner] 19 * 20 * CDDL HEADER END 21 */ 22 /* 23 * Copyright (c) 2003, 2010, Oracle and/or its affiliates. All rights reserved. 24 */ 25 26 #include <modes/gcm_impl.h> 27 28 struct aes_block { 29 uint64_t a; 30 uint64_t b; 31 }; 32 33 /* 34 * Perform a carry-less multiplication (that is, use XOR instead of the 35 * multiply operator) on *x_in and *y and place the result in *res. 36 * 37 * Byte swap the input (*x_in and *y) and the output (*res). 38 * 39 * Note: x_in, y, and res all point to 16-byte numbers (an array of two 40 * 64-bit integers). 41 */ 42 static void 43 gcm_generic_mul(uint64_t *x_in, uint64_t *y, uint64_t *res) 44 { 45 static const uint64_t R = 0xe100000000000000ULL; 46 struct aes_block z = {0, 0}; 47 struct aes_block v; 48 uint64_t x; 49 int i, j; 50 51 v.a = ntohll(y[0]); 52 v.b = ntohll(y[1]); 53 54 for (j = 0; j < 2; j++) { 55 x = ntohll(x_in[j]); 56 for (i = 0; i < 64; i++, x <<= 1) { 57 if (x & 0x8000000000000000ULL) { 58 z.a ^= v.a; 59 z.b ^= v.b; 60 } 61 if (v.b & 1ULL) { 62 v.b = (v.a << 63)|(v.b >> 1); 63 v.a = (v.a >> 1) ^ R; 64 } else { 65 v.b = (v.a << 63)|(v.b >> 1); 66 v.a = v.a >> 1; 67 } 68 } 69 } 70 res[0] = htonll(z.a); 71 res[1] = htonll(z.b); 72 } 73 74 static boolean_t 75 gcm_generic_will_work(void) 76 { 77 return (B_TRUE); 78 } 79 80 const gcm_impl_ops_t gcm_generic_impl = { 81 .mul = &gcm_generic_mul, 82 .is_supported = &gcm_generic_will_work, 83 .name = "generic" 84 }; 85