1 /*
   2  * CDDL HEADER START
   3  *
   4  * The contents of this file are subject to the terms of the
   5  * Common Development and Distribution License (the "License").
   6  * You may not use this file except in compliance with the License.
   7  *
   8  * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE
   9  * or http://www.opensolaris.org/os/licensing.
  10  * See the License for the specific language governing permissions
  11  * and limitations under the License.
  12  *
  13  * When distributing Covered Code, include this CDDL HEADER in each
  14  * file and include the License file at usr/src/OPENSOLARIS.LICENSE.
  15  * If applicable, add the following below this CDDL HEADER, with the
  16  * fields enclosed by brackets "[]" replaced with your own identifying
  17  * information: Portions Copyright [yyyy] [name of copyright owner]
  18  *
  19  * CDDL HEADER END
  20  */
  21 /*
  22  * Copyright 2008 Sun Microsystems, Inc.  All rights reserved.
  23  * Use is subject to license terms.
  24  */
  25 
  26 #pragma ident   "%Z%%M% %I%     %E% SMI"
  27 
  28 #include <sys/types.h>
  29 #include <sys/systm.h>
  30 #include <sys/ddi.h>
  31 #include <sys/sysmacros.h>
  32 #include <sys/strsun.h>
  33 #include <sys/crypto/spi.h>
  34 #include <modes/modes.h>
  35 #include <sys/crypto/common.h>
  36 #include "des_impl.h"
  37 #ifndef _KERNEL
  38 #include <strings.h>
  39 #include <stdlib.h>
  40 #endif  /* !_KERNEL */
  41 
  42 /* EXPORT DELETE START */
  43 
  44 typedef struct keysched_s {
  45         uint64_t ksch_encrypt[16];
  46         uint64_t ksch_decrypt[16];
  47 } keysched_t;
  48 
  49 typedef struct keysched3_s {
  50         uint64_t ksch_encrypt[48];
  51         uint64_t ksch_decrypt[48];
  52 } keysched3_t;
  53 
  54 static void fix_des_parity(uint64_t *);
  55 
  56 #ifndef sun4u
  57 
  58 static const uint64_t sbox_table[8][64]=
  59 {
  60 /* BEGIN CSTYLED */
  61 {
  62 0x0000140140020000ULL, 0x0000000000000000ULL, 0x0000000140000000ULL, 0x0000140140020020ULL,
  63 0x0000140140000020ULL, 0x0000000140020020ULL, 0x0000000000000020ULL, 0x0000000140000000ULL,
  64 0x0000000000020000ULL, 0x0000140140020000ULL, 0x0000140140020020ULL, 0x0000000000020000ULL,
  65 0x0000140000020020ULL, 0x0000140140000020ULL, 0x0000140000000000ULL, 0x0000000000000020ULL,
  66 0x0000000000020020ULL, 0x0000140000020000ULL, 0x0000140000020000ULL, 0x0000000140020000ULL,
  67 0x0000000140020000ULL, 0x0000140140000000ULL, 0x0000140140000000ULL, 0x0000140000020020ULL,
  68 0x0000000140000020ULL, 0x0000140000000020ULL, 0x0000140000000020ULL, 0x0000000140000020ULL,
  69 0x0000000000000000ULL, 0x0000000000020020ULL, 0x0000000140020020ULL, 0x0000140000000000ULL,
  70 0x0000000140000000ULL, 0x0000140140020020ULL, 0x0000000000000020ULL, 0x0000140140000000ULL,
  71 0x0000140140020000ULL, 0x0000140000000000ULL, 0x0000140000000000ULL, 0x0000000000020000ULL,
  72 0x0000140140000020ULL, 0x0000000140000000ULL, 0x0000000140020000ULL, 0x0000140000000020ULL,
  73 0x0000000000020000ULL, 0x0000000000000020ULL, 0x0000140000020020ULL, 0x0000000140020020ULL,
  74 0x0000140140020020ULL, 0x0000000140000020ULL, 0x0000140140000000ULL, 0x0000140000020020ULL,
  75 0x0000140000000020ULL, 0x0000000000020020ULL, 0x0000000140020020ULL, 0x0000140140020000ULL,
  76 0x0000000000020020ULL, 0x0000140000020000ULL, 0x0000140000020000ULL, 0x0000000000000000ULL,
  77 0x0000000140000020ULL, 0x0000000140020000ULL, 0x0000000000000000ULL, 0x0000140140000020ULL
  78 },
  79 {
  80 0x2000005020000500ULL, 0x2000000020000000ULL, 0x0000000020000000ULL, 0x0000005020000500ULL,
  81 0x0000005000000000ULL, 0x0000000000000500ULL, 0x2000005000000500ULL, 0x2000000020000500ULL,
  82 0x2000000000000500ULL, 0x2000005020000500ULL, 0x2000005020000000ULL, 0x2000000000000000ULL,
  83 0x2000000020000000ULL, 0x0000005000000000ULL, 0x0000000000000500ULL, 0x2000005000000500ULL,
  84 0x0000005020000000ULL, 0x0000005000000500ULL, 0x2000000020000500ULL, 0x0000000000000000ULL,
  85 0x2000000000000000ULL, 0x0000000020000000ULL, 0x0000005020000500ULL, 0x2000005000000000ULL,
  86 0x0000005000000500ULL, 0x2000000000000500ULL, 0x0000000000000000ULL, 0x0000005020000000ULL,
  87 0x0000000020000500ULL, 0x2000005020000000ULL, 0x2000005000000000ULL, 0x0000000020000500ULL,
  88 0x0000000000000000ULL, 0x0000005020000500ULL, 0x2000005000000500ULL, 0x0000005000000000ULL,
  89 0x2000000020000500ULL, 0x2000005000000000ULL, 0x2000005020000000ULL, 0x0000000020000000ULL,
  90 0x2000005000000000ULL, 0x2000000020000000ULL, 0x0000000000000500ULL, 0x2000005020000500ULL,
  91 0x0000005020000500ULL, 0x0000000000000500ULL, 0x0000000020000000ULL, 0x2000000000000000ULL,
  92 0x0000000020000500ULL, 0x2000005020000000ULL, 0x0000005000000000ULL, 0x2000000000000500ULL,
  93 0x0000005000000500ULL, 0x2000000020000500ULL, 0x2000000000000500ULL, 0x0000005000000500ULL,
  94 0x0000005020000000ULL, 0x0000000000000000ULL, 0x2000000020000000ULL, 0x0000000020000500ULL,
  95 0x2000000000000000ULL, 0x2000005000000500ULL, 0x2000005020000500ULL, 0x0000005020000000ULL
  96 },
  97 {
  98 0x0000000000014040ULL, 0x0000800280014000ULL, 0x0000000000000000ULL, 0x0000800280000040ULL,
  99 0x0000800000014000ULL, 0x0000000000000000ULL, 0x0000000280014040ULL, 0x0000800000014000ULL,
 100 0x0000000280000040ULL, 0x0000800000000040ULL, 0x0000800000000040ULL, 0x0000000280000000ULL,
 101 0x0000800280014040ULL, 0x0000000280000040ULL, 0x0000800280000000ULL, 0x0000000000014040ULL,
 102 0x0000800000000000ULL, 0x0000000000000040ULL, 0x0000800280014000ULL, 0x0000000000014000ULL,
 103 0x0000000280014000ULL, 0x0000800280000000ULL, 0x0000800280000040ULL, 0x0000000280014040ULL,
 104 0x0000800000014040ULL, 0x0000000280014000ULL, 0x0000000280000000ULL, 0x0000800000014040ULL,
 105 0x0000000000000040ULL, 0x0000800280014040ULL, 0x0000000000014000ULL, 0x0000800000000000ULL,
 106 0x0000800280014000ULL, 0x0000800000000000ULL, 0x0000000280000040ULL, 0x0000000000014040ULL,
 107 0x0000000280000000ULL, 0x0000800280014000ULL, 0x0000800000014000ULL, 0x0000000000000000ULL,
 108 0x0000000000014000ULL, 0x0000000280000040ULL, 0x0000800280014040ULL, 0x0000800000014000ULL,
 109 0x0000800000000040ULL, 0x0000000000014000ULL, 0x0000000000000000ULL, 0x0000800280000040ULL,
 110 0x0000800000014040ULL, 0x0000000280000000ULL, 0x0000800000000000ULL, 0x0000800280014040ULL,
 111 0x0000000000000040ULL, 0x0000000280014040ULL, 0x0000000280014000ULL, 0x0000800000000040ULL,
 112 0x0000800280000000ULL, 0x0000800000014040ULL, 0x0000000000014040ULL, 0x0000800280000000ULL,
 113 0x0000000280014040ULL, 0x0000000000000040ULL, 0x0000800280000040ULL, 0x0000000280014000ULL
 114 },
 115 {
 116 0x4000020008100008ULL, 0x4000000008101008ULL, 0x4000000008101008ULL, 0x0000000000001000ULL,
 117 0x0000020008101000ULL, 0x4000020000001008ULL, 0x4000020000000008ULL, 0x4000000008100008ULL,
 118 0x0000000000000000ULL, 0x0000020008100000ULL, 0x0000020008100000ULL, 0x4000020008101008ULL,
 119 0x4000000000001008ULL, 0x0000000000000000ULL, 0x0000020000001000ULL, 0x4000020000000008ULL,
 120 0x4000000000000008ULL, 0x0000000008100000ULL, 0x0000020000000000ULL, 0x4000020008100008ULL,
 121 0x0000000000001000ULL, 0x0000020000000000ULL, 0x4000000008100008ULL, 0x0000000008101000ULL,
 122 0x4000020000001008ULL, 0x4000000000000008ULL, 0x0000000008101000ULL, 0x0000020000001000ULL,
 123 0x0000000008100000ULL, 0x0000020008101000ULL, 0x4000020008101008ULL, 0x4000000000001008ULL,
 124 0x0000020000001000ULL, 0x4000020000000008ULL, 0x0000020008100000ULL, 0x4000020008101008ULL,
 125 0x4000000000001008ULL, 0x0000000000000000ULL, 0x0000000000000000ULL, 0x0000020008100000ULL,
 126 0x0000000008101000ULL, 0x0000020000001000ULL, 0x4000020000001008ULL, 0x4000000000000008ULL,
 127 0x4000020008100008ULL, 0x4000000008101008ULL, 0x4000000008101008ULL, 0x0000000000001000ULL,
 128 0x4000020008101008ULL, 0x4000000000001008ULL, 0x4000000000000008ULL, 0x0000000008100000ULL,
 129 0x4000020000000008ULL, 0x4000000008100008ULL, 0x0000020008101000ULL, 0x4000020000001008ULL,
 130 0x4000000008100008ULL, 0x0000000008101000ULL, 0x0000020000000000ULL, 0x4000020008100008ULL,
 131 0x0000000000001000ULL, 0x0000020000000000ULL, 0x0000000008100000ULL, 0x0000020008101000ULL
 132 },
 133 {
 134 0x000000000000a000ULL, 0x000028080000a000ULL, 0x0000280800000000ULL, 0x100028000000a000ULL,
 135 0x0000000800000000ULL, 0x000000000000a000ULL, 0x1000000000000000ULL, 0x0000280800000000ULL,
 136 0x100000080000a000ULL, 0x0000000800000000ULL, 0x000028000000a000ULL, 0x100000080000a000ULL,
 137 0x100028000000a000ULL, 0x1000280800000000ULL, 0x000000080000a000ULL, 0x1000000000000000ULL,
 138 0x0000280000000000ULL, 0x1000000800000000ULL, 0x1000000800000000ULL, 0x0000000000000000ULL,
 139 0x100000000000a000ULL, 0x100028080000a000ULL, 0x100028080000a000ULL, 0x000028000000a000ULL,
 140 0x1000280800000000ULL, 0x100000000000a000ULL, 0x0000000000000000ULL, 0x1000280000000000ULL,
 141 0x000028080000a000ULL, 0x0000280000000000ULL, 0x1000280000000000ULL, 0x000000080000a000ULL,
 142 0x0000000800000000ULL, 0x100028000000a000ULL, 0x000000000000a000ULL, 0x0000280000000000ULL,
 143 0x1000000000000000ULL, 0x0000280800000000ULL, 0x100028000000a000ULL, 0x100000080000a000ULL,
 144 0x000028000000a000ULL, 0x1000000000000000ULL, 0x1000280800000000ULL, 0x000028080000a000ULL,
 145 0x100000080000a000ULL, 0x000000000000a000ULL, 0x0000280000000000ULL, 0x1000280800000000ULL,
 146 0x100028080000a000ULL, 0x000000080000a000ULL, 0x1000280000000000ULL, 0x100028080000a000ULL,
 147 0x0000280800000000ULL, 0x0000000000000000ULL, 0x1000000800000000ULL, 0x1000280000000000ULL,
 148 0x000000080000a000ULL, 0x000028000000a000ULL, 0x100000000000a000ULL, 0x0000000800000000ULL,
 149 0x0000000000000000ULL, 0x1000000800000000ULL, 0x000028080000a000ULL, 0x100000000000a000ULL
 150 },
 151 {
 152 0x0802000000000280ULL, 0x0802010000000000ULL, 0x0000000010000000ULL, 0x0802010010000280ULL,
 153 0x0802010000000000ULL, 0x0000000000000280ULL, 0x0802010010000280ULL, 0x0000010000000000ULL,
 154 0x0802000010000000ULL, 0x0000010010000280ULL, 0x0000010000000000ULL, 0x0802000000000280ULL,
 155 0x0000010000000280ULL, 0x0802000010000000ULL, 0x0802000000000000ULL, 0x0000000010000280ULL,
 156 0x0000000000000000ULL, 0x0000010000000280ULL, 0x0802000010000280ULL, 0x0000000010000000ULL,
 157 0x0000010010000000ULL, 0x0802000010000280ULL, 0x0000000000000280ULL, 0x0802010000000280ULL,
 158 0x0802010000000280ULL, 0x0000000000000000ULL, 0x0000010010000280ULL, 0x0802010010000000ULL,
 159 0x0000000010000280ULL, 0x0000010010000000ULL, 0x0802010010000000ULL, 0x0802000000000000ULL,
 160 0x0802000010000000ULL, 0x0000000000000280ULL, 0x0802010000000280ULL, 0x0000010010000000ULL,
 161 0x0802010010000280ULL, 0x0000010000000000ULL, 0x0000000010000280ULL, 0x0802000000000280ULL,
 162 0x0000010000000000ULL, 0x0802000010000000ULL, 0x0802000000000000ULL, 0x0000000010000280ULL,
 163 0x0802000000000280ULL, 0x0802010010000280ULL, 0x0000010010000000ULL, 0x0802010000000000ULL,
 164 0x0000010010000280ULL, 0x0802010010000000ULL, 0x0000000000000000ULL, 0x0802010000000280ULL,
 165 0x0000000000000280ULL, 0x0000000010000000ULL, 0x0802010000000000ULL, 0x0000010010000280ULL,
 166 0x0000000010000000ULL, 0x0000010000000280ULL, 0x0802000010000280ULL, 0x0000000000000000ULL,
 167 0x0802010010000000ULL, 0x0802000000000000ULL, 0x0000010000000280ULL, 0x0802000010000280ULL
 168 },
 169 {
 170 0x000000a000000000ULL, 0x800040a000000010ULL, 0x8000400000040010ULL, 0x0000000000000000ULL,
 171 0x0000000000040000ULL, 0x8000400000040010ULL, 0x800000a000040010ULL, 0x000040a000040000ULL,
 172 0x800040a000040010ULL, 0x000000a000000000ULL, 0x0000000000000000ULL, 0x8000400000000010ULL,
 173 0x8000000000000010ULL, 0x0000400000000000ULL, 0x800040a000000010ULL, 0x8000000000040010ULL,
 174 0x0000400000040000ULL, 0x800000a000040010ULL, 0x800000a000000010ULL, 0x0000400000040000ULL,
 175 0x8000400000000010ULL, 0x000040a000000000ULL, 0x000040a000040000ULL, 0x800000a000000010ULL,
 176 0x000040a000000000ULL, 0x0000000000040000ULL, 0x8000000000040010ULL, 0x800040a000040010ULL,
 177 0x000000a000040000ULL, 0x8000000000000010ULL, 0x0000400000000000ULL, 0x000000a000040000ULL,
 178 0x0000400000000000ULL, 0x000000a000040000ULL, 0x000000a000000000ULL, 0x8000400000040010ULL,
 179 0x8000400000040010ULL, 0x800040a000000010ULL, 0x800040a000000010ULL, 0x8000000000000010ULL,
 180 0x800000a000000010ULL, 0x0000400000000000ULL, 0x0000400000040000ULL, 0x000000a000000000ULL,
 181 0x000040a000040000ULL, 0x8000000000040010ULL, 0x800000a000040010ULL, 0x000040a000040000ULL,
 182 0x8000000000040010ULL, 0x8000400000000010ULL, 0x800040a000040010ULL, 0x000040a000000000ULL,
 183 0x000000a000040000ULL, 0x0000000000000000ULL, 0x8000000000000010ULL, 0x800040a000040010ULL,
 184 0x0000000000000000ULL, 0x800000a000040010ULL, 0x000040a000000000ULL, 0x0000000000040000ULL,
 185 0x8000400000000010ULL, 0x0000400000040000ULL, 0x0000000000040000ULL, 0x800000a000000010ULL
 186 },
 187 {
 188 0x0401000004080800ULL, 0x0000000004080000ULL, 0x0000000400000000ULL, 0x0401000404080800ULL,
 189 0x0401000000000000ULL, 0x0401000004080800ULL, 0x0000000000000800ULL, 0x0401000000000000ULL,
 190 0x0000000400000800ULL, 0x0401000400000000ULL, 0x0401000404080800ULL, 0x0000000404080000ULL,
 191 0x0401000404080000ULL, 0x0000000404080800ULL, 0x0000000004080000ULL, 0x0000000000000800ULL,
 192 0x0401000400000000ULL, 0x0401000000000800ULL, 0x0401000004080000ULL, 0x0000000004080800ULL,
 193 0x0000000404080000ULL, 0x0000000400000800ULL, 0x0401000400000800ULL, 0x0401000404080000ULL,
 194 0x0000000004080800ULL, 0x0000000000000000ULL, 0x0000000000000000ULL, 0x0401000400000800ULL,
 195 0x0401000000000800ULL, 0x0401000004080000ULL, 0x0000000404080800ULL, 0x0000000400000000ULL,
 196 0x0000000404080800ULL, 0x0000000400000000ULL, 0x0401000404080000ULL, 0x0000000004080000ULL,
 197 0x0000000000000800ULL, 0x0401000400000800ULL, 0x0000000004080000ULL, 0x0000000404080800ULL,
 198 0x0401000004080000ULL, 0x0000000000000800ULL, 0x0401000000000800ULL, 0x0401000400000000ULL,
 199 0x0401000400000800ULL, 0x0401000000000000ULL, 0x0000000400000000ULL, 0x0401000004080800ULL,
 200 0x0000000000000000ULL, 0x0401000404080800ULL, 0x0000000400000800ULL, 0x0401000000000800ULL,
 201 0x0401000400000000ULL, 0x0401000004080000ULL, 0x0401000004080800ULL, 0x0000000000000000ULL,
 202 0x0401000404080800ULL, 0x0000000404080000ULL, 0x0000000404080000ULL, 0x0000000004080800ULL,
 203 0x0000000004080800ULL, 0x0000000400000800ULL, 0x0401000000000000ULL, 0x0401000404080000ULL
 204 }
 205 /* END CSTYLED */
 206 };
 207 
 208 
 209 static const uint64_t ip_table[2][256]=
 210 {
 211 /* BEGIN CSTYLED */
 212 {
 213 0x0000000000000000ULL, 0x0000000000000400ULL, 0x0080000000000280ULL, 0x0080000000000680ULL,
 214 0x0000000000400000ULL, 0x0000000000400400ULL, 0x0080000000400280ULL, 0x0080000000400680ULL,
 215 0x0000000000280000ULL, 0x0000000000280400ULL, 0x0080000000280280ULL, 0x0080000000280680ULL,
 216 0x0000000000680000ULL, 0x0000000000680400ULL, 0x0080000000680280ULL, 0x0080000000680680ULL,
 217 0x0000000400000000ULL, 0x0000000400000400ULL, 0x0080000400000280ULL, 0x0080000400000680ULL,
 218 0x0000000400400000ULL, 0x0000000400400400ULL, 0x0080000400400280ULL, 0x0080000400400680ULL,
 219 0x0000000400280000ULL, 0x0000000400280400ULL, 0x0080000400280280ULL, 0x0080000400280680ULL,
 220 0x0000000400680000ULL, 0x0000000400680400ULL, 0x0080000400680280ULL, 0x0080000400680680ULL,
 221 0x0000000280000000ULL, 0x0000000280000400ULL, 0x0080000280000280ULL, 0x0080000280000680ULL,
 222 0x0000000280400000ULL, 0x0000000280400400ULL, 0x0080000280400280ULL, 0x0080000280400680ULL,
 223 0x0000000280280000ULL, 0x0000000280280400ULL, 0x0080000280280280ULL, 0x0080000280280680ULL,
 224 0x0000000280680000ULL, 0x0000000280680400ULL, 0x0080000280680280ULL, 0x0080000280680680ULL,
 225 0x0000000680000000ULL, 0x0000000680000400ULL, 0x0080000680000280ULL, 0x0080000680000680ULL,
 226 0x0000000680400000ULL, 0x0000000680400400ULL, 0x0080000680400280ULL, 0x0080000680400680ULL,
 227 0x0000000680280000ULL, 0x0000000680280400ULL, 0x0080000680280280ULL, 0x0080000680280680ULL,
 228 0x0000000680680000ULL, 0x0000000680680400ULL, 0x0080000680680280ULL, 0x0080000680680680ULL,
 229 0x0000400000000000ULL, 0x0000400000000400ULL, 0x0080400000000280ULL, 0x0080400000000680ULL,
 230 0x0000400000400000ULL, 0x0000400000400400ULL, 0x0080400000400280ULL, 0x0080400000400680ULL,
 231 0x0000400000280000ULL, 0x0000400000280400ULL, 0x0080400000280280ULL, 0x0080400000280680ULL,
 232 0x0000400000680000ULL, 0x0000400000680400ULL, 0x0080400000680280ULL, 0x0080400000680680ULL,
 233 0x0000400400000000ULL, 0x0000400400000400ULL, 0x0080400400000280ULL, 0x0080400400000680ULL,
 234 0x0000400400400000ULL, 0x0000400400400400ULL, 0x0080400400400280ULL, 0x0080400400400680ULL,
 235 0x0000400400280000ULL, 0x0000400400280400ULL, 0x0080400400280280ULL, 0x0080400400280680ULL,
 236 0x0000400400680000ULL, 0x0000400400680400ULL, 0x0080400400680280ULL, 0x0080400400680680ULL,
 237 0x0000400280000000ULL, 0x0000400280000400ULL, 0x0080400280000280ULL, 0x0080400280000680ULL,
 238 0x0000400280400000ULL, 0x0000400280400400ULL, 0x0080400280400280ULL, 0x0080400280400680ULL,
 239 0x0000400280280000ULL, 0x0000400280280400ULL, 0x0080400280280280ULL, 0x0080400280280680ULL,
 240 0x0000400280680000ULL, 0x0000400280680400ULL, 0x0080400280680280ULL, 0x0080400280680680ULL,
 241 0x0000400680000000ULL, 0x0000400680000400ULL, 0x0080400680000280ULL, 0x0080400680000680ULL,
 242 0x0000400680400000ULL, 0x0000400680400400ULL, 0x0080400680400280ULL, 0x0080400680400680ULL,
 243 0x0000400680280000ULL, 0x0000400680280400ULL, 0x0080400680280280ULL, 0x0080400680280680ULL,
 244 0x0000400680680000ULL, 0x0000400680680400ULL, 0x0080400680680280ULL, 0x0080400680680680ULL,
 245 0x0000280000000000ULL, 0x0000280000000400ULL, 0x0080280000000280ULL, 0x0080280000000680ULL,
 246 0x0000280000400000ULL, 0x0000280000400400ULL, 0x0080280000400280ULL, 0x0080280000400680ULL,
 247 0x0000280000280000ULL, 0x0000280000280400ULL, 0x0080280000280280ULL, 0x0080280000280680ULL,
 248 0x0000280000680000ULL, 0x0000280000680400ULL, 0x0080280000680280ULL, 0x0080280000680680ULL,
 249 0x0000280400000000ULL, 0x0000280400000400ULL, 0x0080280400000280ULL, 0x0080280400000680ULL,
 250 0x0000280400400000ULL, 0x0000280400400400ULL, 0x0080280400400280ULL, 0x0080280400400680ULL,
 251 0x0000280400280000ULL, 0x0000280400280400ULL, 0x0080280400280280ULL, 0x0080280400280680ULL,
 252 0x0000280400680000ULL, 0x0000280400680400ULL, 0x0080280400680280ULL, 0x0080280400680680ULL,
 253 0x0000280280000000ULL, 0x0000280280000400ULL, 0x0080280280000280ULL, 0x0080280280000680ULL,
 254 0x0000280280400000ULL, 0x0000280280400400ULL, 0x0080280280400280ULL, 0x0080280280400680ULL,
 255 0x0000280280280000ULL, 0x0000280280280400ULL, 0x0080280280280280ULL, 0x0080280280280680ULL,
 256 0x0000280280680000ULL, 0x0000280280680400ULL, 0x0080280280680280ULL, 0x0080280280680680ULL,
 257 0x0000280680000000ULL, 0x0000280680000400ULL, 0x0080280680000280ULL, 0x0080280680000680ULL,
 258 0x0000280680400000ULL, 0x0000280680400400ULL, 0x0080280680400280ULL, 0x0080280680400680ULL,
 259 0x0000280680280000ULL, 0x0000280680280400ULL, 0x0080280680280280ULL, 0x0080280680280680ULL,
 260 0x0000280680680000ULL, 0x0000280680680400ULL, 0x0080280680680280ULL, 0x0080280680680680ULL,
 261 0x0000680000000000ULL, 0x0000680000000400ULL, 0x0080680000000280ULL, 0x0080680000000680ULL,
 262 0x0000680000400000ULL, 0x0000680000400400ULL, 0x0080680000400280ULL, 0x0080680000400680ULL,
 263 0x0000680000280000ULL, 0x0000680000280400ULL, 0x0080680000280280ULL, 0x0080680000280680ULL,
 264 0x0000680000680000ULL, 0x0000680000680400ULL, 0x0080680000680280ULL, 0x0080680000680680ULL,
 265 0x0000680400000000ULL, 0x0000680400000400ULL, 0x0080680400000280ULL, 0x0080680400000680ULL,
 266 0x0000680400400000ULL, 0x0000680400400400ULL, 0x0080680400400280ULL, 0x0080680400400680ULL,
 267 0x0000680400280000ULL, 0x0000680400280400ULL, 0x0080680400280280ULL, 0x0080680400280680ULL,
 268 0x0000680400680000ULL, 0x0000680400680400ULL, 0x0080680400680280ULL, 0x0080680400680680ULL,
 269 0x0000680280000000ULL, 0x0000680280000400ULL, 0x0080680280000280ULL, 0x0080680280000680ULL,
 270 0x0000680280400000ULL, 0x0000680280400400ULL, 0x0080680280400280ULL, 0x0080680280400680ULL,
 271 0x0000680280280000ULL, 0x0000680280280400ULL, 0x0080680280280280ULL, 0x0080680280280680ULL,
 272 0x0000680280680000ULL, 0x0000680280680400ULL, 0x0080680280680280ULL, 0x0080680280680680ULL,
 273 0x0000680680000000ULL, 0x0000680680000400ULL, 0x0080680680000280ULL, 0x0080680680000680ULL,
 274 0x0000680680400000ULL, 0x0000680680400400ULL, 0x0080680680400280ULL, 0x0080680680400680ULL,
 275 0x0000680680280000ULL, 0x0000680680280400ULL, 0x0080680680280280ULL, 0x0080680680280680ULL,
 276 0x0000680680680000ULL, 0x0000680680680400ULL, 0x0080680680680280ULL, 0x0080680680680680ULL
 277 },
 278 {
 279 0x0000000000000000ULL, 0x0000000000005000ULL, 0x0000000000000800ULL, 0x0000000000005800ULL,
 280 0x0000000005000000ULL, 0x0000000005005000ULL, 0x0000000005000800ULL, 0x0000000005005800ULL,
 281 0x0000000000800000ULL, 0x0000000000805000ULL, 0x0000000000800800ULL, 0x0000000000805800ULL,
 282 0x0000000005800000ULL, 0x0000000005805000ULL, 0x0000000005800800ULL, 0x0000000005805800ULL,
 283 0x0000005000000000ULL, 0x0000005000005000ULL, 0x0000005000000800ULL, 0x0000005000005800ULL,
 284 0x0000005005000000ULL, 0x0000005005005000ULL, 0x0000005005000800ULL, 0x0000005005005800ULL,
 285 0x0000005000800000ULL, 0x0000005000805000ULL, 0x0000005000800800ULL, 0x0000005000805800ULL,
 286 0x0000005005800000ULL, 0x0000005005805000ULL, 0x0000005005800800ULL, 0x0000005005805800ULL,
 287 0x0000000800000000ULL, 0x0000000800005000ULL, 0x0000000800000800ULL, 0x0000000800005800ULL,
 288 0x0000000805000000ULL, 0x0000000805005000ULL, 0x0000000805000800ULL, 0x0000000805005800ULL,
 289 0x0000000800800000ULL, 0x0000000800805000ULL, 0x0000000800800800ULL, 0x0000000800805800ULL,
 290 0x0000000805800000ULL, 0x0000000805805000ULL, 0x0000000805800800ULL, 0x0000000805805800ULL,
 291 0x0000005800000000ULL, 0x0000005800005000ULL, 0x0000005800000800ULL, 0x0000005800005800ULL,
 292 0x0000005805000000ULL, 0x0000005805005000ULL, 0x0000005805000800ULL, 0x0000005805005800ULL,
 293 0x0000005800800000ULL, 0x0000005800805000ULL, 0x0000005800800800ULL, 0x0000005800805800ULL,
 294 0x0000005805800000ULL, 0x0000005805805000ULL, 0x0000005805800800ULL, 0x0000005805805800ULL,
 295 0x0005000000000004ULL, 0x0005000000005004ULL, 0x0005000000000804ULL, 0x0005000000005804ULL,
 296 0x0005000005000004ULL, 0x0005000005005004ULL, 0x0005000005000804ULL, 0x0005000005005804ULL,
 297 0x0005000000800004ULL, 0x0005000000805004ULL, 0x0005000000800804ULL, 0x0005000000805804ULL,
 298 0x0005000005800004ULL, 0x0005000005805004ULL, 0x0005000005800804ULL, 0x0005000005805804ULL,
 299 0x0005005000000004ULL, 0x0005005000005004ULL, 0x0005005000000804ULL, 0x0005005000005804ULL,
 300 0x0005005005000004ULL, 0x0005005005005004ULL, 0x0005005005000804ULL, 0x0005005005005804ULL,
 301 0x0005005000800004ULL, 0x0005005000805004ULL, 0x0005005000800804ULL, 0x0005005000805804ULL,
 302 0x0005005005800004ULL, 0x0005005005805004ULL, 0x0005005005800804ULL, 0x0005005005805804ULL,
 303 0x0005000800000004ULL, 0x0005000800005004ULL, 0x0005000800000804ULL, 0x0005000800005804ULL,
 304 0x0005000805000004ULL, 0x0005000805005004ULL, 0x0005000805000804ULL, 0x0005000805005804ULL,
 305 0x0005000800800004ULL, 0x0005000800805004ULL, 0x0005000800800804ULL, 0x0005000800805804ULL,
 306 0x0005000805800004ULL, 0x0005000805805004ULL, 0x0005000805800804ULL, 0x0005000805805804ULL,
 307 0x0005005800000004ULL, 0x0005005800005004ULL, 0x0005005800000804ULL, 0x0005005800005804ULL,
 308 0x0005005805000004ULL, 0x0005005805005004ULL, 0x0005005805000804ULL, 0x0005005805005804ULL,
 309 0x0005005800800004ULL, 0x0005005800805004ULL, 0x0005005800800804ULL, 0x0005005800805804ULL,
 310 0x0005005805800004ULL, 0x0005005805805004ULL, 0x0005005805800804ULL, 0x0005005805805804ULL,
 311 0x0000800000000000ULL, 0x0000800000005000ULL, 0x0000800000000800ULL, 0x0000800000005800ULL,
 312 0x0000800005000000ULL, 0x0000800005005000ULL, 0x0000800005000800ULL, 0x0000800005005800ULL,
 313 0x0000800000800000ULL, 0x0000800000805000ULL, 0x0000800000800800ULL, 0x0000800000805800ULL,
 314 0x0000800005800000ULL, 0x0000800005805000ULL, 0x0000800005800800ULL, 0x0000800005805800ULL,
 315 0x0000805000000000ULL, 0x0000805000005000ULL, 0x0000805000000800ULL, 0x0000805000005800ULL,
 316 0x0000805005000000ULL, 0x0000805005005000ULL, 0x0000805005000800ULL, 0x0000805005005800ULL,
 317 0x0000805000800000ULL, 0x0000805000805000ULL, 0x0000805000800800ULL, 0x0000805000805800ULL,
 318 0x0000805005800000ULL, 0x0000805005805000ULL, 0x0000805005800800ULL, 0x0000805005805800ULL,
 319 0x0000800800000000ULL, 0x0000800800005000ULL, 0x0000800800000800ULL, 0x0000800800005800ULL,
 320 0x0000800805000000ULL, 0x0000800805005000ULL, 0x0000800805000800ULL, 0x0000800805005800ULL,
 321 0x0000800800800000ULL, 0x0000800800805000ULL, 0x0000800800800800ULL, 0x0000800800805800ULL,
 322 0x0000800805800000ULL, 0x0000800805805000ULL, 0x0000800805800800ULL, 0x0000800805805800ULL,
 323 0x0000805800000000ULL, 0x0000805800005000ULL, 0x0000805800000800ULL, 0x0000805800005800ULL,
 324 0x0000805805000000ULL, 0x0000805805005000ULL, 0x0000805805000800ULL, 0x0000805805005800ULL,
 325 0x0000805800800000ULL, 0x0000805800805000ULL, 0x0000805800800800ULL, 0x0000805800805800ULL,
 326 0x0000805805800000ULL, 0x0000805805805000ULL, 0x0000805805800800ULL, 0x0000805805805800ULL,
 327 0x0005800000000004ULL, 0x0005800000005004ULL, 0x0005800000000804ULL, 0x0005800000005804ULL,
 328 0x0005800005000004ULL, 0x0005800005005004ULL, 0x0005800005000804ULL, 0x0005800005005804ULL,
 329 0x0005800000800004ULL, 0x0005800000805004ULL, 0x0005800000800804ULL, 0x0005800000805804ULL,
 330 0x0005800005800004ULL, 0x0005800005805004ULL, 0x0005800005800804ULL, 0x0005800005805804ULL,
 331 0x0005805000000004ULL, 0x0005805000005004ULL, 0x0005805000000804ULL, 0x0005805000005804ULL,
 332 0x0005805005000004ULL, 0x0005805005005004ULL, 0x0005805005000804ULL, 0x0005805005005804ULL,
 333 0x0005805000800004ULL, 0x0005805000805004ULL, 0x0005805000800804ULL, 0x0005805000805804ULL,
 334 0x0005805005800004ULL, 0x0005805005805004ULL, 0x0005805005800804ULL, 0x0005805005805804ULL,
 335 0x0005800800000004ULL, 0x0005800800005004ULL, 0x0005800800000804ULL, 0x0005800800005804ULL,
 336 0x0005800805000004ULL, 0x0005800805005004ULL, 0x0005800805000804ULL, 0x0005800805005804ULL,
 337 0x0005800800800004ULL, 0x0005800800805004ULL, 0x0005800800800804ULL, 0x0005800800805804ULL,
 338 0x0005800805800004ULL, 0x0005800805805004ULL, 0x0005800805800804ULL, 0x0005800805805804ULL,
 339 0x0005805800000004ULL, 0x0005805800005004ULL, 0x0005805800000804ULL, 0x0005805800005804ULL,
 340 0x0005805805000004ULL, 0x0005805805005004ULL, 0x0005805805000804ULL, 0x0005805805005804ULL,
 341 0x0005805800800004ULL, 0x0005805800805004ULL, 0x0005805800800804ULL, 0x0005805800805804ULL,
 342 0x0005805805800004ULL, 0x0005805805805004ULL, 0x0005805805800804ULL, 0x0005805805805804ULL
 343 }
 344 /* END CSTYLED */
 345 };
 346 
 347 static const uint32_t fp_table[256]=
 348 {
 349 0x00000000, 0x80000000, 0x00800000, 0x80800000,
 350 0x00008000, 0x80008000, 0x00808000, 0x80808000,
 351 0x00000080, 0x80000080, 0x00800080, 0x80800080,
 352 0x00008080, 0x80008080, 0x00808080, 0x80808080,
 353 0x40000000, 0xc0000000, 0x40800000, 0xc0800000,
 354 0x40008000, 0xc0008000, 0x40808000, 0xc0808000,
 355 0x40000080, 0xc0000080, 0x40800080, 0xc0800080,
 356 0x40008080, 0xc0008080, 0x40808080, 0xc0808080,
 357 0x00400000, 0x80400000, 0x00c00000, 0x80c00000,
 358 0x00408000, 0x80408000, 0x00c08000, 0x80c08000,
 359 0x00400080, 0x80400080, 0x00c00080, 0x80c00080,
 360 0x00408080, 0x80408080, 0x00c08080, 0x80c08080,
 361 0x40400000, 0xc0400000, 0x40c00000, 0xc0c00000,
 362 0x40408000, 0xc0408000, 0x40c08000, 0xc0c08000,
 363 0x40400080, 0xc0400080, 0x40c00080, 0xc0c00080,
 364 0x40408080, 0xc0408080, 0x40c08080, 0xc0c08080,
 365 0x00004000, 0x80004000, 0x00804000, 0x80804000,
 366 0x0000c000, 0x8000c000, 0x0080c000, 0x8080c000,
 367 0x00004080, 0x80004080, 0x00804080, 0x80804080,
 368 0x0000c080, 0x8000c080, 0x0080c080, 0x8080c080,
 369 0x40004000, 0xc0004000, 0x40804000, 0xc0804000,
 370 0x4000c000, 0xc000c000, 0x4080c000, 0xc080c000,
 371 0x40004080, 0xc0004080, 0x40804080, 0xc0804080,
 372 0x4000c080, 0xc000c080, 0x4080c080, 0xc080c080,
 373 0x00404000, 0x80404000, 0x00c04000, 0x80c04000,
 374 0x0040c000, 0x8040c000, 0x00c0c000, 0x80c0c000,
 375 0x00404080, 0x80404080, 0x00c04080, 0x80c04080,
 376 0x0040c080, 0x8040c080, 0x00c0c080, 0x80c0c080,
 377 0x40404000, 0xc0404000, 0x40c04000, 0xc0c04000,
 378 0x4040c000, 0xc040c000, 0x40c0c000, 0xc0c0c000,
 379 0x40404080, 0xc0404080, 0x40c04080, 0xc0c04080,
 380 0x4040c080, 0xc040c080, 0x40c0c080, 0xc0c0c080,
 381 0x00000040, 0x80000040, 0x00800040, 0x80800040,
 382 0x00008040, 0x80008040, 0x00808040, 0x80808040,
 383 0x000000c0, 0x800000c0, 0x008000c0, 0x808000c0,
 384 0x000080c0, 0x800080c0, 0x008080c0, 0x808080c0,
 385 0x40000040, 0xc0000040, 0x40800040, 0xc0800040,
 386 0x40008040, 0xc0008040, 0x40808040, 0xc0808040,
 387 0x400000c0, 0xc00000c0, 0x408000c0, 0xc08000c0,
 388 0x400080c0, 0xc00080c0, 0x408080c0, 0xc08080c0,
 389 0x00400040, 0x80400040, 0x00c00040, 0x80c00040,
 390 0x00408040, 0x80408040, 0x00c08040, 0x80c08040,
 391 0x004000c0, 0x804000c0, 0x00c000c0, 0x80c000c0,
 392 0x004080c0, 0x804080c0, 0x00c080c0, 0x80c080c0,
 393 0x40400040, 0xc0400040, 0x40c00040, 0xc0c00040,
 394 0x40408040, 0xc0408040, 0x40c08040, 0xc0c08040,
 395 0x404000c0, 0xc04000c0, 0x40c000c0, 0xc0c000c0,
 396 0x404080c0, 0xc04080c0, 0x40c080c0, 0xc0c080c0,
 397 0x00004040, 0x80004040, 0x00804040, 0x80804040,
 398 0x0000c040, 0x8000c040, 0x0080c040, 0x8080c040,
 399 0x000040c0, 0x800040c0, 0x008040c0, 0x808040c0,
 400 0x0000c0c0, 0x8000c0c0, 0x0080c0c0, 0x8080c0c0,
 401 0x40004040, 0xc0004040, 0x40804040, 0xc0804040,
 402 0x4000c040, 0xc000c040, 0x4080c040, 0xc080c040,
 403 0x400040c0, 0xc00040c0, 0x408040c0, 0xc08040c0,
 404 0x4000c0c0, 0xc000c0c0, 0x4080c0c0, 0xc080c0c0,
 405 0x00404040, 0x80404040, 0x00c04040, 0x80c04040,
 406 0x0040c040, 0x8040c040, 0x00c0c040, 0x80c0c040,
 407 0x004040c0, 0x804040c0, 0x00c040c0, 0x80c040c0,
 408 0x0040c0c0, 0x8040c0c0, 0x00c0c0c0, 0x80c0c0c0,
 409 0x40404040, 0xc0404040, 0x40c04040, 0xc0c04040,
 410 0x4040c040, 0xc040c040, 0x40c0c040, 0xc0c0c040,
 411 0x404040c0, 0xc04040c0, 0x40c040c0, 0xc0c040c0,
 412 0x4040c0c0, 0xc040c0c0, 0x40c0c0c0, 0xc0c0c0c0
 413 };
 414 
 415 static const uint64_t all_a = 0xaaaaaaaaaaaaaaaaULL;
 416 static const uint64_t all_5 = 0x5555555555555555ULL;
 417 static const uint64_t top_1 = 0xfc000000000000ULL;
 418 static const uint64_t mid_4 = 0x3fffffc000000ULL;
 419 static const uint64_t low_3 = 0x3ffff00ULL;
 420 
 421 
 422 static void
 423 des_ip(uint64_t *l, uint64_t *r, uint64_t pt)
 424 {
 425         uint64_t a, b;
 426 
 427         a = pt & all_a;
 428         b = pt & all_5;
 429         a = a | (a << 7);
 430         b = b | (b >> 7);
 431 
 432         b = (ip_table[0][(b >> 48) & 255ULL]) |
 433             (ip_table[1][(b >> 32) & 255ULL]) |
 434             (ip_table[0][(b >> 16) & 255ULL] << 6) |
 435             (ip_table[1][b & 255ULL] << 6);
 436 
 437         a = (ip_table[0][(a >> 56) & 255]) |
 438             (ip_table[1][(a >> 40) & 255]) |
 439             (ip_table[0][(a >> 24) & 255] << 6) |
 440             (ip_table[1][(a >> 8) & 255] << 6);
 441 
 442         *l = ((b & top_1) << 8) |
 443             (b & mid_4) |
 444             ((b & low_3) >> 5);
 445 
 446         *r = ((a & top_1) << 8) |
 447             (a & mid_4) |
 448             ((a & low_3) >> 5);
 449 }
 450 
 451 
 452 static uint64_t
 453 des_fp(uint64_t l, uint64_t r)
 454 {
 455         uint32_t upper, lower;
 456 
 457         lower = fp_table[((l >> 55) & 240) | ((r >> 59) & 15)] |
 458             (fp_table[((l >> 35) & 240) | ((r>>39) & 15)] >> 2) |
 459             (fp_table[((l >> 23) & 240) | ((r >> 27) & 15)] >> 4) |
 460             (fp_table[((l >> 6) & 240) | ((r >> 10) & 15)] >> 6);
 461 
 462         upper = fp_table[((l >> 41) & 240) | ((r >> 45) & 15)] |
 463             (fp_table[((l >> 29) & 240) | ((r >> 33) & 15)] >> 2) |
 464             (fp_table[((l >> 12) & 240) | ((r >> 16) & 15)] >> 4) |
 465             (fp_table[(l & 240) | (r >> 4) & 15] >> 6);
 466 
 467         return ((((uint64_t)upper) << 32) | (uint64_t)lower);
 468 
 469 }
 470 
 471 uint64_t
 472 des_crypt_impl(uint64_t *ks, uint64_t block, int one_or_three)
 473 {
 474         int i, j;
 475         uint64_t l, r, t;
 476 
 477         des_ip(&l, &r, block);
 478         for (j = 0; j < one_or_three; j++) {
 479                 for (i = j * 16; i < (j + 1) * 16; i++) {
 480                         t = r ^ ks[i];
 481                         t = sbox_table[0][t >> 58] |
 482                             sbox_table[1][(t >> 44) & 63] |
 483                             sbox_table[2][(t >> 38) & 63] |
 484                             sbox_table[3][(t >> 32) & 63] |
 485                             sbox_table[4][(t >> 26) & 63] |
 486                             sbox_table[5][(t >> 15) & 63] |
 487                             sbox_table[6][(t >> 9) & 63] |
 488                             sbox_table[7][(t >> 3) & 63];
 489                         t = t^l;
 490                         l = r;
 491                         r = t;
 492                 }
 493                 r = l;
 494                 l = t;
 495         }
 496 
 497         return (des_fp(l, r));
 498 }
 499 #endif /* !sun4u */
 500 
 501 /* EXPORT DELETE END */
 502 
 503 int
 504 des3_crunch_block(const void *cookie, const uint8_t block[DES_BLOCK_LEN],
 505     uint8_t out_block[DES_BLOCK_LEN], boolean_t decrypt)
 506 {
 507 /* EXPORT DELETE START */
 508         keysched3_t *ksch = (keysched3_t *)cookie;
 509 
 510         /*
 511          * The code below, that is always executed on LITTLE_ENDIAN machines,
 512          * reverses bytes in the block.  On BIG_ENDIAN, the same code
 513          * copies the block without reversing bytes.
 514          */
 515 #ifdef _BIG_ENDIAN
 516         if (IS_P2ALIGNED(block, sizeof (uint64_t)) &&
 517             IS_P2ALIGNED(out_block, sizeof (uint64_t))) {
 518                 if (decrypt == B_TRUE)
 519                         /* LINTED */
 520                         *(uint64_t *)out_block = des_crypt_impl(
 521                             ksch->ksch_decrypt,
 522                             /* LINTED */
 523                             *(uint64_t *)block, 3);
 524                 else
 525                         /* LINTED */
 526                         *(uint64_t *)out_block = des_crypt_impl(
 527                             ksch->ksch_encrypt,
 528                             /* LINTED */
 529                             *(uint64_t *)block, 3);
 530         } else {
 531 #endif
 532                 uint64_t tmp;
 533 
 534                 tmp = (((uint64_t)block[0] << 56) | ((uint64_t)block[1] << 48) |
 535                     ((uint64_t)block[2] << 40) | ((uint64_t)block[3] << 32) |
 536                     ((uint64_t)block[4] << 24) | ((uint64_t)block[5] << 16) |
 537                     ((uint64_t)block[6] << 8) | (uint64_t)block[7]);
 538 
 539                 if (decrypt == B_TRUE)
 540                         tmp = des_crypt_impl(ksch->ksch_decrypt, tmp, 3);
 541                 else
 542                         tmp = des_crypt_impl(ksch->ksch_encrypt, tmp, 3);
 543 
 544                 out_block[0] = tmp >> 56;
 545                 out_block[1] = tmp >> 48;
 546                 out_block[2] = tmp >> 40;
 547                 out_block[3] = tmp >> 32;
 548                 out_block[4] = tmp >> 24;
 549                 out_block[5] = tmp >> 16;
 550                 out_block[6] = tmp >> 8;
 551                 out_block[7] = (uint8_t)tmp;
 552 #ifdef _BIG_ENDIAN
 553         }
 554 #endif
 555 /* EXPORT DELETE END */
 556         return (CRYPTO_SUCCESS);
 557 }
 558 
 559 int
 560 des_crunch_block(const void *cookie, const uint8_t block[DES_BLOCK_LEN],
 561     uint8_t out_block[DES_BLOCK_LEN], boolean_t decrypt)
 562 {
 563 /* EXPORT DELETE START */
 564         keysched_t *ksch = (keysched_t *)cookie;
 565 
 566         /*
 567          * The code below, that is always executed on LITTLE_ENDIAN machines,
 568          * reverses bytes in the block.  On BIG_ENDIAN, the same code
 569          * copies the block without reversing bytes.
 570          */
 571 #ifdef _BIG_ENDIAN
 572         if (IS_P2ALIGNED(block, sizeof (uint64_t)) &&
 573             IS_P2ALIGNED(out_block, sizeof (uint64_t))) {
 574                 if (decrypt == B_TRUE)
 575                         /* LINTED */
 576                         *(uint64_t *)out_block = des_crypt_impl(
 577                             ksch->ksch_decrypt,
 578                             /* LINTED */
 579                             *(uint64_t *)block, 1);
 580                 else
 581                         /* LINTED */
 582                         *(uint64_t *)out_block = des_crypt_impl(
 583                             ksch->ksch_encrypt,
 584                             /* LINTED */
 585                             *(uint64_t *)block, 1);
 586 
 587         } else {
 588 #endif
 589                 uint64_t tmp;
 590 
 591                 tmp = (((uint64_t)block[0] << 56) | ((uint64_t)block[1] << 48) |
 592                     ((uint64_t)block[2] << 40) | ((uint64_t)block[3] << 32) |
 593                     ((uint64_t)block[4] << 24) | ((uint64_t)block[5] << 16) |
 594                     ((uint64_t)block[6] << 8) | (uint64_t)block[7]);
 595 
 596                 if (decrypt == B_TRUE)
 597                         tmp = des_crypt_impl(ksch->ksch_decrypt, tmp, 1);
 598                 else
 599                         tmp = des_crypt_impl(ksch->ksch_encrypt, tmp, 1);
 600 
 601                 out_block[0] = tmp >> 56;
 602                 out_block[1] = tmp >> 48;
 603                 out_block[2] = tmp >> 40;
 604                 out_block[3] = tmp >> 32;
 605                 out_block[4] = tmp >> 24;
 606                 out_block[5] = tmp >> 16;
 607                 out_block[6] = tmp >> 8;
 608                 out_block[7] = (uint8_t)tmp;
 609 #ifdef _BIG_ENDIAN
 610         }
 611 #endif
 612 /* EXPORT DELETE END */
 613         return (CRYPTO_SUCCESS);
 614 }
 615 
 616 static boolean_t
 617 keycheck(uint8_t *key, uint8_t *corrected_key)
 618 {
 619 /* EXPORT DELETE START */
 620         uint64_t key_so_far;
 621         uint_t i;
 622         /*
 623          * Table of weak and semi-weak keys.  Fortunately, weak keys are
 624          * endian-independent, and some semi-weak keys can be paired up in
 625          * endian-opposite order.  Since keys are stored as uint64_t's,
 626          * use the ifdef _LITTLE_ENDIAN where appropriate.
 627          */
 628         static uint64_t des_weak_keys[] = {
 629                 /* Really weak keys.  Byte-order independent values. */
 630                 0x0101010101010101ULL,
 631                 0x1f1f1f1f0e0e0e0eULL,
 632                 0xe0e0e0e0f1f1f1f1ULL,
 633                 0xfefefefefefefefeULL,
 634 
 635                 /* Semi-weak (and a few possibly-weak) keys. */
 636 
 637                 /* Byte-order independent semi-weak keys. */
 638                 0x01fe01fe01fe01feULL,  0xfe01fe01fe01fe01ULL,
 639 
 640                 /* Byte-order dependent semi-weak keys. */
 641 #ifdef _LITTLE_ENDIAN
 642                 0xf10ef10ee01fe01fULL,  0x0ef10ef11fe01fe0ULL,
 643                 0x01f101f101e001e0ULL,  0xf101f101e001e001ULL,
 644                 0x0efe0efe1ffe1ffeULL,  0xfe0efe0efe1ffe1fULL,
 645                 0x010e010e011f011fULL,  0x0e010e011f011f01ULL,
 646                 0xf1fef1fee0fee0feULL,  0xfef1fef1fee0fee0ULL,
 647 #else   /* Big endian */
 648                 0x1fe01fe00ef10ef1ULL,  0xe01fe01ff10ef10eULL,
 649                 0x01e001e001f101f1ULL,  0xe001e001f101f101ULL,
 650                 0x1ffe1ffe0efe0efeULL,  0xfe1ffe1ffe0efe0eULL,
 651                 0x011f011f010e010eULL,  0x1f011f010e010e01ULL,
 652                 0xe0fee0fef1fef1feULL,  0xfee0fee0fef1fef1ULL,
 653 #endif
 654 
 655                 /* We'll save the other possibly-weak keys for the future. */
 656         };
 657 
 658         if (key == NULL)
 659                 return (B_FALSE);
 660 
 661         /*
 662          * The code below reverses the bytes on LITTLE_ENDIAN machines.
 663          * On BIG_ENDIAN, the same code copies without reversing
 664          * the bytes.
 665          */
 666         key_so_far = (((uint64_t)key[0] << 56) | ((uint64_t)key[1] << 48) |
 667             ((uint64_t)key[2] << 40) | ((uint64_t)key[3] << 32) |
 668             ((uint64_t)key[4] << 24) | ((uint64_t)key[5] << 16) |
 669             ((uint64_t)key[6] << 8) | (uint64_t)key[7]);
 670 
 671         /*
 672          * Fix parity.
 673          */
 674         fix_des_parity(&key_so_far);
 675 
 676         /* Do weak key check itself. */
 677         for (i = 0; i < (sizeof (des_weak_keys) / sizeof (uint64_t)); i++)
 678                 if (key_so_far == des_weak_keys[i]) {
 679                         return (B_FALSE);
 680                 }
 681 
 682         if (corrected_key != NULL) {
 683                 /*
 684                  * The code below reverses the bytes on LITTLE_ENDIAN machines.
 685                  * On BIG_ENDIAN, the same code copies without reversing
 686                  * the bytes.
 687                  */
 688                 corrected_key[0] = key_so_far >> 56;
 689                 corrected_key[1] = key_so_far >> 48;
 690                 corrected_key[2] = key_so_far >> 40;
 691                 corrected_key[3] = key_so_far >> 32;
 692                 corrected_key[4] = key_so_far >> 24;
 693                 corrected_key[5] = key_so_far >> 16;
 694                 corrected_key[6] = key_so_far >> 8;
 695                 corrected_key[7] = (uint8_t)key_so_far;
 696         }
 697 /* EXPORT DELETE END */
 698         return (B_TRUE);
 699 }
 700 
 701 static boolean_t
 702 des3_keycheck(uint8_t *key, uint8_t *corrected_key)
 703 {
 704 /* EXPORT DELETE START */
 705         uint64_t aligned_key[DES3_KEYSIZE / sizeof (uint64_t)];
 706         uint64_t key_so_far, scratch, *currentkey;
 707         uint_t j, num_weakkeys = 0;
 708 
 709         if (key == NULL) {
 710                 return (B_FALSE);
 711         }
 712 
 713         if (!IS_P2ALIGNED(key, sizeof (uint64_t))) {
 714                 bcopy(key, aligned_key, DES3_KEYSIZE);
 715                 currentkey = (uint64_t *)aligned_key;
 716         } else {
 717                 /* LINTED */
 718                 currentkey = (uint64_t *)key;
 719         }
 720 
 721         for (j = 0; j < 3; j++) {
 722                 key_so_far = currentkey[j];
 723 
 724                 if (!keycheck((uint8_t *)&key_so_far, (uint8_t *)&scratch)) {
 725                         if (++num_weakkeys > 1) {
 726                                 return (B_FALSE);
 727                         }
 728                         /*
 729                          * We found a weak key, but since
 730                          * we've only found one weak key,
 731                          * we can not reject the whole 3DES
 732                          * set of keys as weak.
 733                          *
 734                          * Break from the weak key loop
 735                          * (since this DES key is weak) and
 736                          * continue on.
 737                          */
 738                 }
 739 
 740                 currentkey[j] = scratch;
 741         }
 742 
 743         /*
 744          * Perform key equivalence checks, now that parity is properly set.
 745          * 1st and 2nd keys must be unique, the 3rd key can be the same as
 746          * the 1st key for the 2 key varient of 3DES.
 747          */
 748         if (currentkey[0] == currentkey[1] || currentkey[1] == currentkey[2])
 749                 return (B_FALSE);
 750 
 751         if (corrected_key != NULL) {
 752                 bcopy(currentkey, corrected_key, DES3_KEYSIZE);
 753         }
 754 
 755 /* EXPORT DELETE END */
 756         return (B_TRUE);
 757 }
 758 
 759 boolean_t
 760 des_keycheck(uint8_t *key, des_strength_t strength, uint8_t *corrected_key)
 761 {
 762         if (strength == DES) {
 763                 return (keycheck(key, corrected_key));
 764         } else if (strength == DES3) {
 765                 return (des3_keycheck(key, corrected_key));
 766         } else {
 767                 return (B_FALSE);
 768         }
 769 }
 770 
 771 void
 772 des_parity_fix(uint8_t *key, des_strength_t strength, uint8_t *corrected_key)
 773 {
 774 /* EXPORT DELETE START */
 775         uint64_t aligned_key[DES3_KEYSIZE / sizeof (uint64_t)];
 776         uint8_t *paritied_key;
 777         uint64_t key_so_far;
 778         int i = 0, offset = 0;
 779 
 780         if (strength == DES)
 781                 bcopy(key, aligned_key, DES_KEYSIZE);
 782         else
 783                 bcopy(key, aligned_key, DES3_KEYSIZE);
 784 
 785         paritied_key = (uint8_t *)aligned_key;
 786         while (strength > i) {
 787                 offset = 8 * i;
 788                 key_so_far = (((uint64_t)paritied_key[offset + 0] << 56) |
 789                     ((uint64_t)paritied_key[offset + 1] << 48) |
 790                     ((uint64_t)paritied_key[offset + 2] << 40) |
 791                     ((uint64_t)paritied_key[offset + 3] << 32) |
 792                     ((uint64_t)paritied_key[offset + 4] << 24) |
 793                     ((uint64_t)paritied_key[offset + 5] << 16) |
 794                     ((uint64_t)paritied_key[offset + 6] << 8) |
 795                     (uint64_t)paritied_key[offset + 7]);
 796 
 797                 fix_des_parity(&key_so_far);
 798 
 799                 paritied_key[offset + 0] = key_so_far >> 56;
 800                 paritied_key[offset + 1] = key_so_far >> 48;
 801                 paritied_key[offset + 2] = key_so_far >> 40;
 802                 paritied_key[offset + 3] = key_so_far >> 32;
 803                 paritied_key[offset + 4] = key_so_far >> 24;
 804                 paritied_key[offset + 5] = key_so_far >> 16;
 805                 paritied_key[offset + 6] = key_so_far >> 8;
 806                 paritied_key[offset + 7] = (uint8_t)key_so_far;
 807 
 808                 i++;
 809         }
 810 
 811         bcopy(paritied_key, corrected_key, DES_KEYSIZE * strength);
 812 /* EXPORT DELETE END */
 813 }
 814 
 815 
 816 /*
 817  * Initialize key schedule for DES, DES2, and DES3
 818  */
 819 void
 820 des_init_keysched(uint8_t *cipherKey, des_strength_t strength, void *ks)
 821 {
 822 /* EXPORT DELETE START */
 823         uint64_t *encryption_ks;
 824         uint64_t *decryption_ks;
 825         uint64_t keysched[48];
 826         uint64_t key_uint64[3];
 827         uint64_t tmp;
 828         uint_t keysize, i, j;
 829 
 830         switch (strength) {
 831         case DES:
 832                 keysize = DES_KEYSIZE;
 833                 encryption_ks = ((keysched_t *)ks)->ksch_encrypt;
 834                 decryption_ks = ((keysched_t *)ks)->ksch_decrypt;
 835                 break;
 836         case DES2:
 837                 keysize = DES2_KEYSIZE;
 838                 encryption_ks = ((keysched3_t *)ks)->ksch_encrypt;
 839                 decryption_ks = ((keysched3_t *)ks)->ksch_decrypt;
 840                 break;
 841         case DES3:
 842                 keysize = DES3_KEYSIZE;
 843                 encryption_ks = ((keysched3_t *)ks)->ksch_encrypt;
 844                 decryption_ks = ((keysched3_t *)ks)->ksch_decrypt;
 845         }
 846 
 847         /*
 848          * The code below, that is always executed on LITTLE_ENDIAN machines,
 849          * reverses every 8 bytes in the key.  On BIG_ENDIAN, the same code
 850          * copies the key without reversing bytes.
 851          */
 852 #ifdef _BIG_ENDIAN
 853         if (IS_P2ALIGNED(cipherKey, sizeof (uint64_t))) {
 854                 for (i = 0, j = 0; j < keysize; i++, j += 8) {
 855                         /* LINTED: pointer alignment */
 856                         key_uint64[i] = *((uint64_t *)&cipherKey[j]);
 857                 }
 858         } else {
 859 #endif
 860         {
 861                 for (i = 0, j = 0; j < keysize; i++, j += 8) {
 862                         key_uint64[i] = (((uint64_t)cipherKey[j] << 56) |
 863                             ((uint64_t)cipherKey[j + 1] << 48) |
 864                             ((uint64_t)cipherKey[j + 2] << 40) |
 865                             ((uint64_t)cipherKey[j + 3] << 32) |
 866                             ((uint64_t)cipherKey[j + 4] << 24) |
 867                             ((uint64_t)cipherKey[j + 5] << 16) |
 868                             ((uint64_t)cipherKey[j + 6] << 8) |
 869                             (uint64_t)cipherKey[j + 7]);
 870                 }
 871         }
 872 #ifdef _BIG_ENDIAN
 873         }
 874 #endif
 875 
 876         switch (strength) {
 877         case DES:
 878                 des_ks(keysched, key_uint64[0]);
 879                 break;
 880 
 881         case DES2:
 882                 /* DES2 is just DES3 with the first and third keys the same */
 883                 bcopy(key_uint64, key_uint64 + 2, DES_KEYSIZE);
 884                 /* FALLTHRU */
 885         case DES3:
 886                 des_ks(keysched, key_uint64[0]);
 887                 des_ks(keysched + 16, key_uint64[1]);
 888                 for (i = 0; i < 8; i++) {
 889                         tmp = keysched[16+i];
 890                         keysched[16+i] = keysched[31-i];
 891                         keysched[31-i] = tmp;
 892                 }
 893                 des_ks(keysched+32, key_uint64[2]);
 894                 keysize = DES3_KEYSIZE;
 895         }
 896 
 897         /* save the encryption keyschedule */
 898         bcopy(keysched, encryption_ks, keysize * 16);
 899 
 900         /* reverse the key schedule */
 901         for (i = 0; i < keysize; i++) {
 902                 tmp = keysched[i];
 903                 keysched[i] = keysched[2 * keysize - 1 - i];
 904                 keysched[2 * keysize -1 -i] = tmp;
 905         }
 906 
 907         /* save the decryption keyschedule */
 908         bcopy(keysched, decryption_ks, keysize * 16);
 909 /* EXPORT DELETE END */
 910 }
 911 
 912 /*
 913  * Allocate key schedule.
 914  */
 915 /*ARGSUSED*/
 916 void *
 917 des_alloc_keysched(size_t *keysched_size, des_strength_t strength, int kmflag)
 918 {
 919         void *keysched;
 920 
 921 /* EXPORT DELETE START */
 922 
 923         size_t size;
 924 
 925         switch (strength) {
 926         case DES:
 927                 size = sizeof (keysched_t);
 928                 break;
 929         case DES2:
 930         case DES3:
 931                 size = sizeof (keysched3_t);
 932         }
 933 
 934 #ifdef  _KERNEL
 935         keysched = (keysched_t *)kmem_alloc(size, kmflag);
 936 #else   /* !_KERNEL */
 937         keysched = (keysched_t *)malloc(size);
 938 #endif  /* _KERNEL */
 939 
 940         if (keysched == NULL)
 941                 return (NULL);
 942 
 943         if (keysched_size != NULL)
 944                 *keysched_size = size;
 945 
 946 /* EXPORT DELETE END */
 947 
 948         return (keysched);
 949 }
 950 
 951 /*
 952  * Replace the LSB of each byte by the xor of the other
 953  * 7 bits.  The tricky thing is that the original contents of the LSBs
 954  * are nullifed by including them twice in the xor computation.
 955  */
 956 static void
 957 fix_des_parity(uint64_t *keyp)
 958 {
 959 /* EXPORT DELETE START */
 960         uint64_t k = *keyp;
 961         k ^= k >> 1;
 962         k ^= k >> 2;
 963         k ^= k >> 4;
 964         *keyp ^= (k & 0x0101010101010101ULL);
 965         *keyp ^= 0x0101010101010101ULL;
 966 /* EXPORT DELETE END */
 967 }
 968 
 969 void
 970 des_copy_block(uint8_t *in, uint8_t *out)
 971 {
 972         if (IS_P2ALIGNED(in, sizeof (uint32_t)) &&
 973             IS_P2ALIGNED(out, sizeof (uint32_t))) {
 974                 /* LINTED: pointer alignment */
 975                 *(uint32_t *)&out[0] = *(uint32_t *)&in[0];
 976                 /* LINTED: pointer alignment */
 977                 *(uint32_t *)&out[4] = *(uint32_t *)&in[4];
 978         } else {
 979                 DES_COPY_BLOCK(in, out);
 980         }
 981 }
 982 
 983 /* XOR block of data into dest */
 984 void
 985 des_xor_block(uint8_t *data, uint8_t *dst)
 986 {
 987         if (IS_P2ALIGNED(dst, sizeof (uint32_t)) &&
 988             IS_P2ALIGNED(data, sizeof (uint32_t))) {
 989                 /* LINTED: pointer alignment */
 990                 *(uint32_t *)&dst[0] ^=
 991                 /* LINTED: pointer alignment */
 992                     *(uint32_t *)&data[0];
 993                 /* LINTED: pointer alignment */
 994                 *(uint32_t *)&dst[4] ^=
 995                 /* LINTED: pointer alignment */
 996                     *(uint32_t *)&data[4];
 997         } else {
 998                 DES_XOR_BLOCK(data, dst);
 999         }
1000 }
1001 
1002 int
1003 des_encrypt_block(const void *keysched, const uint8_t *in, uint8_t *out)
1004 {
1005         return (des_crunch_block(keysched, in, out, B_FALSE));
1006 }
1007 
1008 int
1009 des3_encrypt_block(const void *keysched, const uint8_t *in, uint8_t *out)
1010 {
1011         return (des3_crunch_block(keysched, in, out, B_FALSE));
1012 }
1013 
1014 int
1015 des_decrypt_block(const void *keysched, const uint8_t *in, uint8_t *out)
1016 {
1017         return (des_crunch_block(keysched, in, out, B_TRUE));
1018 }
1019 
1020 int
1021 des3_decrypt_block(const void *keysched, const uint8_t *in, uint8_t *out)
1022 {
1023         return (des3_crunch_block(keysched, in, out, B_TRUE));
1024 }
1025 
1026 /*
1027  * Encrypt multiple blocks of data according to mode.
1028  */
1029 int
1030 des_encrypt_contiguous_blocks(void *ctx, char *data, size_t length,
1031     crypto_data_t *out)
1032 {
1033         des_ctx_t *des_ctx = ctx;
1034         int rv;
1035 
1036         if (des_ctx->dc_flags & DES3_STRENGTH) {
1037                 if (des_ctx->dc_flags & CBC_MODE) {
1038                         rv = cbc_encrypt_contiguous_blocks(ctx, data,
1039                             length, out, DES_BLOCK_LEN, des3_encrypt_block,
1040                             des_copy_block, des_xor_block);
1041                 } else {
1042                         rv = ecb_cipher_contiguous_blocks(ctx, data, length,
1043                             out, DES_BLOCK_LEN, des3_encrypt_block);
1044                 }
1045         } else {
1046                 if (des_ctx->dc_flags & CBC_MODE) {
1047                         rv = cbc_encrypt_contiguous_blocks(ctx, data,
1048                             length, out, DES_BLOCK_LEN, des_encrypt_block,
1049                             des_copy_block, des_xor_block);
1050                 } else {
1051                         rv = ecb_cipher_contiguous_blocks(ctx, data, length,
1052                             out, DES_BLOCK_LEN, des_encrypt_block);
1053                 }
1054         }
1055         return (rv);
1056 }
1057 
1058 /*
1059  * Decrypt multiple blocks of data according to mode.
1060  */
1061 int
1062 des_decrypt_contiguous_blocks(void *ctx, char *data, size_t length,
1063     crypto_data_t *out)
1064 {
1065         des_ctx_t *des_ctx = ctx;
1066         int rv;
1067 
1068         if (des_ctx->dc_flags & DES3_STRENGTH) {
1069                 if (des_ctx->dc_flags & CBC_MODE) {
1070                         rv = cbc_decrypt_contiguous_blocks(ctx, data,
1071                             length, out, DES_BLOCK_LEN, des3_decrypt_block,
1072                             des_copy_block, des_xor_block);
1073                 } else {
1074                         rv = ecb_cipher_contiguous_blocks(ctx, data, length,
1075                             out, DES_BLOCK_LEN, des3_decrypt_block);
1076                         if (rv == CRYPTO_DATA_LEN_RANGE)
1077                                 rv = CRYPTO_ENCRYPTED_DATA_LEN_RANGE;
1078                 }
1079         } else {
1080                 if (des_ctx->dc_flags & CBC_MODE) {
1081                         rv = cbc_decrypt_contiguous_blocks(ctx, data,
1082                             length, out, DES_BLOCK_LEN, des_decrypt_block,
1083                             des_copy_block, des_xor_block);
1084                 } else {
1085                         rv = ecb_cipher_contiguous_blocks(ctx, data, length,
1086                             out, DES_BLOCK_LEN, des_decrypt_block);
1087                         if (rv == CRYPTO_DATA_LEN_RANGE)
1088                                 rv = CRYPTO_ENCRYPTED_DATA_LEN_RANGE;
1089                 }
1090         }
1091         return (rv);
1092 }