forked from Imagelibrary/rtems
Replace sys/crypto/sha2/sha2.c with lib/libmd/sha512c.c
cperciva's libmd implementation is 5-30% faster
The same was done for SHA256 previously in r263218
cperciva's implementation was lacking SHA-384 which I implemented, validated against OpenSSL and the NIST documentation
Extend sbin/md5 to create sha384(1)
Chase dependancies on sys/crypto/sha2/sha2.{c,h} and replace them with sha512{c.c,.h}
Reviewed by: cperciva, des, delphij
Approved by: secteam, bapt (mentor)
MFC after: 2 weeks
Sponsored by: ScaleEngine Inc.
Differential Revision: https://reviews.freebsd.org/D3929
This commit is contained in:
committed by
Sebastian Huber
parent
120c857ea1
commit
225e7b9e75
@@ -29,22 +29,31 @@
|
||||
#ifndef _SHA256_H_
|
||||
#define _SHA256_H_
|
||||
|
||||
#ifndef _KERNEL
|
||||
#include <sys/types.h>
|
||||
#endif
|
||||
|
||||
#define SHA256_BLOCK_LENGTH 64
|
||||
#define SHA256_DIGEST_LENGTH 32
|
||||
#define SHA256_DIGEST_STRING_LENGTH (SHA256_DIGEST_LENGTH * 2 + 1)
|
||||
|
||||
typedef struct SHA256Context {
|
||||
uint32_t state[8];
|
||||
uint64_t count;
|
||||
unsigned char buf[64];
|
||||
uint8_t buf[SHA256_BLOCK_LENGTH];
|
||||
} SHA256_CTX;
|
||||
|
||||
__BEGIN_DECLS
|
||||
|
||||
void SHA256_Init(SHA256_CTX *);
|
||||
void SHA256_Update(SHA256_CTX *, const void *, size_t);
|
||||
void SHA256_Final(unsigned char [32], SHA256_CTX *);
|
||||
void SHA256_Final(unsigned char [SHA256_DIGEST_LENGTH], SHA256_CTX *);
|
||||
#ifndef _KERNEL
|
||||
char *SHA256_End(SHA256_CTX *, char *);
|
||||
char *SHA256_Data(const void *, unsigned int, char *);
|
||||
char *SHA256_File(const char *, char *);
|
||||
char *SHA256_FileChunk(const char *, char *, off_t, off_t);
|
||||
char *SHA256_Data(const void *, unsigned int, char *);
|
||||
#endif
|
||||
__END_DECLS
|
||||
|
||||
#endif /* !_SHA256_H_ */
|
||||
|
||||
60
cpukit/include/sha384.h
Normal file
60
cpukit/include/sha384.h
Normal file
@@ -0,0 +1,60 @@
|
||||
/*-
|
||||
* Copyright 2005 Colin Percival
|
||||
* All rights reserved.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions
|
||||
* are met:
|
||||
* 1. Redistributions of source code must retain the above copyright
|
||||
* notice, this list of conditions and the following disclaimer.
|
||||
* 2. Redistributions in binary form must reproduce the above copyright
|
||||
* notice, this list of conditions and the following disclaimer in the
|
||||
* documentation and/or other materials provided with the distribution.
|
||||
*
|
||||
* THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND
|
||||
* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
|
||||
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
|
||||
* ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE
|
||||
* FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
|
||||
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
|
||||
* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
|
||||
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
|
||||
* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
|
||||
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
|
||||
* SUCH DAMAGE.
|
||||
*
|
||||
* $FreeBSD$
|
||||
*/
|
||||
|
||||
#ifndef _SHA384_H_
|
||||
#define _SHA384_H_
|
||||
|
||||
#ifndef _KERNEL
|
||||
#include <sys/types.h>
|
||||
#endif
|
||||
|
||||
#define SHA384_BLOCK_LENGTH 128
|
||||
#define SHA384_DIGEST_LENGTH 48
|
||||
#define SHA384_DIGEST_STRING_LENGTH (SHA384_DIGEST_LENGTH * 2 + 1)
|
||||
|
||||
typedef struct SHA384Context {
|
||||
uint64_t state[8];
|
||||
uint64_t count[2];
|
||||
uint8_t buf[SHA384_BLOCK_LENGTH];
|
||||
} SHA384_CTX;
|
||||
|
||||
__BEGIN_DECLS
|
||||
|
||||
void SHA384_Init(SHA384_CTX *);
|
||||
void SHA384_Update(SHA384_CTX *, const void *, size_t);
|
||||
void SHA384_Final(unsigned char [SHA384_DIGEST_LENGTH], SHA384_CTX *);
|
||||
#ifndef _KERNEL
|
||||
char *SHA384_End(SHA384_CTX *, char *);
|
||||
char *SHA384_Data(const void *, unsigned int, char *);
|
||||
char *SHA384_File(const char *, char *);
|
||||
char *SHA384_FileChunk(const char *, char *, off_t, off_t);
|
||||
#endif
|
||||
|
||||
__END_DECLS
|
||||
|
||||
#endif /* !_SHA384_H_ */
|
||||
@@ -29,22 +29,32 @@
|
||||
#ifndef _SHA512_H_
|
||||
#define _SHA512_H_
|
||||
|
||||
#ifndef _KERNEL
|
||||
#include <sys/types.h>
|
||||
#endif
|
||||
|
||||
#define SHA512_BLOCK_LENGTH 128
|
||||
#define SHA512_DIGEST_LENGTH 64
|
||||
#define SHA512_DIGEST_STRING_LENGTH (SHA512_DIGEST_LENGTH * 2 + 1)
|
||||
|
||||
typedef struct SHA512Context {
|
||||
uint64_t state[8];
|
||||
uint64_t count[2];
|
||||
unsigned char buf[128];
|
||||
uint8_t buf[SHA512_BLOCK_LENGTH];
|
||||
} SHA512_CTX;
|
||||
|
||||
__BEGIN_DECLS
|
||||
|
||||
void SHA512_Init(SHA512_CTX *);
|
||||
void SHA512_Update(SHA512_CTX *, const void *, size_t);
|
||||
void SHA512_Final(unsigned char [64], SHA512_CTX *);
|
||||
void SHA512_Final(unsigned char [SHA512_DIGEST_LENGTH], SHA512_CTX *);
|
||||
#ifndef _KERNEL
|
||||
char *SHA512_End(SHA512_CTX *, char *);
|
||||
char *SHA512_Data(const void *, unsigned int, char *);
|
||||
char *SHA512_File(const char *, char *);
|
||||
char *SHA512_FileChunk(const char *, char *, off_t, off_t);
|
||||
char *SHA512_Data(const void *, unsigned int, char *);
|
||||
#endif
|
||||
|
||||
__END_DECLS
|
||||
|
||||
#endif /* !_SHA512_H_ */
|
||||
|
||||
@@ -33,6 +33,7 @@ __FBSDID("$FreeBSD$");
|
||||
#include <string.h>
|
||||
|
||||
#include "sha512.h"
|
||||
#include "sha384.h"
|
||||
|
||||
#if BYTE_ORDER == BIG_ENDIAN
|
||||
|
||||
@@ -104,7 +105,7 @@ be64dec_vect(uint64_t *dst, const unsigned char *src, size_t len)
|
||||
* the 512-bit input block to produce a new state.
|
||||
*/
|
||||
static void
|
||||
SHA512_Transform(uint64_t * state, const unsigned char block[128])
|
||||
SHA512_Transform(uint64_t * state, const unsigned char block[SHA512_BLOCK_LENGTH])
|
||||
{
|
||||
uint64_t W[80];
|
||||
uint64_t S[8];
|
||||
@@ -112,12 +113,12 @@ SHA512_Transform(uint64_t * state, const unsigned char block[128])
|
||||
int i;
|
||||
|
||||
/* 1. Prepare message schedule W. */
|
||||
be64dec_vect(W, block, 128);
|
||||
be64dec_vect(W, block, SHA512_BLOCK_LENGTH);
|
||||
for (i = 16; i < 80; i++)
|
||||
W[i] = s1(W[i - 2]) + W[i - 7] + s0(W[i - 15]) + W[i - 16];
|
||||
|
||||
/* 2. Initialize working variables. */
|
||||
memcpy(S, state, 64);
|
||||
memcpy(S, state, SHA512_DIGEST_LENGTH);
|
||||
|
||||
/* 3. Mix. */
|
||||
RNDr(S, W, 0, 0x428a2f98d728ae22ULL);
|
||||
@@ -206,7 +207,7 @@ SHA512_Transform(uint64_t * state, const unsigned char block[128])
|
||||
state[i] += S[i];
|
||||
}
|
||||
|
||||
static const unsigned char PAD[128] = {
|
||||
static const unsigned char PAD[SHA512_BLOCK_LENGTH] = {
|
||||
0x80, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
|
||||
0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
|
||||
0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
|
||||
@@ -279,22 +280,22 @@ SHA512_Update(SHA512_CTX * ctx, const void *in, size_t len)
|
||||
ctx->count[0] += bitlen[0];
|
||||
|
||||
/* Handle the case where we don't need to perform any transforms */
|
||||
if (len < 128 - r) {
|
||||
if (len < SHA512_BLOCK_LENGTH - r) {
|
||||
memcpy(&ctx->buf[r], src, len);
|
||||
return;
|
||||
}
|
||||
|
||||
/* Finish the current block */
|
||||
memcpy(&ctx->buf[r], src, 128 - r);
|
||||
memcpy(&ctx->buf[r], src, SHA512_BLOCK_LENGTH - r);
|
||||
SHA512_Transform(ctx->state, ctx->buf);
|
||||
src += 128 - r;
|
||||
len -= 128 - r;
|
||||
src += SHA512_BLOCK_LENGTH - r;
|
||||
len -= SHA512_BLOCK_LENGTH - r;
|
||||
|
||||
/* Perform complete blocks */
|
||||
while (len >= 128) {
|
||||
while (len >= SHA512_BLOCK_LENGTH) {
|
||||
SHA512_Transform(ctx->state, src);
|
||||
src += 128;
|
||||
len -= 128;
|
||||
src += SHA512_BLOCK_LENGTH;
|
||||
len -= SHA512_BLOCK_LENGTH;
|
||||
}
|
||||
|
||||
/* Copy left over data into buffer */
|
||||
@@ -306,14 +307,64 @@ SHA512_Update(SHA512_CTX * ctx, const void *in, size_t len)
|
||||
* and clears the context state.
|
||||
*/
|
||||
void
|
||||
SHA512_Final(unsigned char digest[64], SHA512_CTX * ctx)
|
||||
SHA512_Final(unsigned char digest[SHA512_DIGEST_LENGTH], SHA512_CTX * ctx)
|
||||
{
|
||||
|
||||
/* Add padding */
|
||||
SHA512_Pad(ctx);
|
||||
|
||||
/* Write the hash */
|
||||
be64enc_vect(digest, ctx->state, 64);
|
||||
be64enc_vect(digest, ctx->state, SHA512_DIGEST_LENGTH);
|
||||
|
||||
/* Clear the context state */
|
||||
memset((void *)ctx, 0, sizeof(*ctx));
|
||||
}
|
||||
|
||||
/*** SHA-384: *********************************************************/
|
||||
/*
|
||||
* the SHA384 and SHA512 transforms are identical, so SHA384 is skipped
|
||||
*/
|
||||
|
||||
/* SHA-384 initialization. Begins a SHA-384 operation. */
|
||||
void
|
||||
SHA384_Init(SHA384_CTX * ctx)
|
||||
{
|
||||
|
||||
/* Zero bits processed so far */
|
||||
ctx->count[0] = ctx->count[1] = 0;
|
||||
|
||||
/* Magic initialization constants */
|
||||
ctx->state[0] = 0xcbbb9d5dc1059ed8ULL;
|
||||
ctx->state[1] = 0x629a292a367cd507ULL;
|
||||
ctx->state[2] = 0x9159015a3070dd17ULL;
|
||||
ctx->state[3] = 0x152fecd8f70e5939ULL;
|
||||
ctx->state[4] = 0x67332667ffc00b31ULL;
|
||||
ctx->state[5] = 0x8eb44a8768581511ULL;
|
||||
ctx->state[6] = 0xdb0c2e0d64f98fa7ULL;
|
||||
ctx->state[7] = 0x47b5481dbefa4fa4ULL;
|
||||
}
|
||||
|
||||
/* Add bytes into the SHA-384 hash */
|
||||
void
|
||||
SHA384_Update(SHA384_CTX * ctx, const void *in, size_t len)
|
||||
{
|
||||
|
||||
SHA512_Update((SHA512_CTX *)ctx, in, len);
|
||||
}
|
||||
|
||||
/*
|
||||
* SHA-384 finalization. Pads the input data, exports the hash value,
|
||||
* and clears the context state.
|
||||
*/
|
||||
void
|
||||
SHA384_Final(unsigned char digest[SHA384_DIGEST_LENGTH], SHA384_CTX * ctx)
|
||||
{
|
||||
|
||||
/* Add padding */
|
||||
SHA512_Pad((SHA512_CTX *)ctx);
|
||||
|
||||
/* Write the hash */
|
||||
be64enc_vect(digest, ctx->state, SHA384_DIGEST_LENGTH);
|
||||
|
||||
/* Clear the context state */
|
||||
memset((void *)ctx, 0, sizeof(*ctx));
|
||||
|
||||
Reference in New Issue
Block a user