1/* 2 * Cryptographic API. 3 * 4 * Skein256 Hash Algorithm. 5 * 6 * Derived from cryptoapi implementation, adapted for in-place 7 * scatterlist interface. 8 * 9 * Copyright (c) Eric Rost <eric.rost@mybabylon.net> 10 * 11 * This program is free software; you can redistribute it and/or modify it 12 * under the terms of the GNU General Public License as published by the Free 13 * Software Foundation; either version 2 of the License, or (at your option) 14 * any later version. 15 * 16 */ 17#include <linux/types.h> 18#include <linux/init.h> 19#include <linux/module.h> 20#include <crypto/internal/hash.h> 21#include "skein_base.h" 22 23 24static int skein256_init(struct shash_desc *desc) 25{ 26 return skein_256_init((struct skein_256_ctx *) shash_desc_ctx(desc), 27 SKEIN256_DIGEST_BIT_SIZE); 28} 29 30static int skein256_update(struct shash_desc *desc, const u8 *data, 31 unsigned int len) 32{ 33 return skein_256_update((struct skein_256_ctx *)shash_desc_ctx(desc), 34 data, len); 35} 36 37static int skein256_final(struct shash_desc *desc, u8 *out) 38{ 39 return skein_256_final((struct skein_256_ctx *)shash_desc_ctx(desc), 40 out); 41} 42 43static int skein256_export(struct shash_desc *desc, void *out) 44{ 45 struct skein_256_ctx *sctx = shash_desc_ctx(desc); 46 47 memcpy(out, sctx, sizeof(*sctx)); 48 return 0; 49} 50 51static int skein256_import(struct shash_desc *desc, const void *in) 52{ 53 struct skein_256_ctx *sctx = shash_desc_ctx(desc); 54 55 memcpy(sctx, in, sizeof(*sctx)); 56 return 0; 57} 58 59static int skein512_init(struct shash_desc *desc) 60{ 61 return skein_512_init((struct skein_512_ctx *)shash_desc_ctx(desc), 62 SKEIN512_DIGEST_BIT_SIZE); 63} 64 65static int skein512_update(struct shash_desc *desc, const u8 *data, 66 unsigned int len) 67{ 68 return skein_512_update((struct skein_512_ctx *)shash_desc_ctx(desc), 69 data, len); 70} 71 72static int skein512_final(struct shash_desc *desc, u8 *out) 73{ 74 return skein_512_final((struct skein_512_ctx *)shash_desc_ctx(desc), 75 out); 76} 77 78static int skein512_export(struct shash_desc *desc, void *out) 79{ 80 struct skein_512_ctx *sctx = shash_desc_ctx(desc); 81 82 memcpy(out, sctx, sizeof(*sctx)); 83 return 0; 84} 85 86static int skein512_import(struct shash_desc *desc, const void *in) 87{ 88 struct skein_512_ctx *sctx = shash_desc_ctx(desc); 89 90 memcpy(sctx, in, sizeof(*sctx)); 91 return 0; 92} 93 94static int skein1024_init(struct shash_desc *desc) 95{ 96 return skein_1024_init((struct skein_1024_ctx *)shash_desc_ctx(desc), 97 SKEIN1024_DIGEST_BIT_SIZE); 98} 99 100static int skein1024_update(struct shash_desc *desc, const u8 *data, 101 unsigned int len) 102{ 103 return skein_1024_update((struct skein_1024_ctx *)shash_desc_ctx(desc), 104 data, len); 105} 106 107static int skein1024_final(struct shash_desc *desc, u8 *out) 108{ 109 return skein_1024_final((struct skein_1024_ctx *)shash_desc_ctx(desc), 110 out); 111} 112 113static int skein1024_export(struct shash_desc *desc, void *out) 114{ 115 struct skein_1024_ctx *sctx = shash_desc_ctx(desc); 116 117 memcpy(out, sctx, sizeof(*sctx)); 118 return 0; 119} 120 121static int skein1024_import(struct shash_desc *desc, const void *in) 122{ 123 struct skein_1024_ctx *sctx = shash_desc_ctx(desc); 124 125 memcpy(sctx, in, sizeof(*sctx)); 126 return 0; 127} 128 129static struct shash_alg alg256 = { 130 .digestsize = (SKEIN256_DIGEST_BIT_SIZE / 8), 131 .init = skein256_init, 132 .update = skein256_update, 133 .final = skein256_final, 134 .export = skein256_export, 135 .import = skein256_import, 136 .descsize = sizeof(struct skein_256_ctx), 137 .statesize = sizeof(struct skein_256_ctx), 138 .base = { 139 .cra_name = "skein256", 140 .cra_driver_name = "skein", 141 .cra_flags = CRYPTO_ALG_TYPE_SHASH, 142 .cra_blocksize = SKEIN_256_BLOCK_BYTES, 143 .cra_module = THIS_MODULE, 144 } 145}; 146 147static struct shash_alg alg512 = { 148 .digestsize = (SKEIN512_DIGEST_BIT_SIZE / 8), 149 .init = skein512_init, 150 .update = skein512_update, 151 .final = skein512_final, 152 .export = skein512_export, 153 .import = skein512_import, 154 .descsize = sizeof(struct skein_512_ctx), 155 .statesize = sizeof(struct skein_512_ctx), 156 .base = { 157 .cra_name = "skein512", 158 .cra_driver_name = "skein", 159 .cra_flags = CRYPTO_ALG_TYPE_SHASH, 160 .cra_blocksize = SKEIN_512_BLOCK_BYTES, 161 .cra_module = THIS_MODULE, 162 } 163}; 164 165static struct shash_alg alg1024 = { 166 .digestsize = (SKEIN1024_DIGEST_BIT_SIZE / 8), 167 .init = skein1024_init, 168 .update = skein1024_update, 169 .final = skein1024_final, 170 .export = skein1024_export, 171 .import = skein1024_import, 172 .descsize = sizeof(struct skein_1024_ctx), 173 .statesize = sizeof(struct skein_1024_ctx), 174 .base = { 175 .cra_name = "skein1024", 176 .cra_driver_name = "skein", 177 .cra_flags = CRYPTO_ALG_TYPE_SHASH, 178 .cra_blocksize = SKEIN_1024_BLOCK_BYTES, 179 .cra_module = THIS_MODULE, 180 } 181}; 182 183static int __init skein_generic_init(void) 184{ 185 if (crypto_register_shash(&alg256)) 186 goto out; 187 if (crypto_register_shash(&alg512)) 188 goto unreg256; 189 if (crypto_register_shash(&alg1024)) 190 goto unreg512; 191 192 return 0; 193 194unreg512: 195 crypto_unregister_shash(&alg512); 196unreg256: 197 crypto_unregister_shash(&alg256); 198out: 199 return -1; 200} 201 202static void __exit skein_generic_fini(void) 203{ 204 crypto_unregister_shash(&alg256); 205 crypto_unregister_shash(&alg512); 206 crypto_unregister_shash(&alg1024); 207} 208 209module_init(skein_generic_init); 210module_exit(skein_generic_fini); 211 212MODULE_LICENSE("GPL"); 213MODULE_DESCRIPTION("Skein Hash Algorithm"); 214 215MODULE_ALIAS("skein"); 216