Commit f472ec8c authored by Andy Polyakov's avatar Andy Polyakov
Browse files

"Jumbo" update for crypto/modes:

- introduce common modes_lcl.h;
- ctr128.c: implement additional CRYPTO_ctr128_encrypt_ctr32 interface;
- gcm128.c: add omitted ARM initialization, remove ctx.ctr;
parent 8a682556
Loading
Loading
Loading
Loading
+6 −5
Original line number Diff line number Diff line
@@ -95,8 +95,9 @@ clean:

# DO NOT DELETE THIS LINE -- make depend depends on it.

cbc128.o: cbc128.c modes.h
cfb128.o: cfb128.c modes.h
ctr128.o: ctr128.c modes.h
cts128.o: cts128.c modes.h
ofb128.o: modes.h ofb128.c
cbc128.o: ../../include/openssl/modes.h cbc128.c modes_lcl.h
cfb128.o: ../../include/openssl/modes.h cfb128.c modes_lcl.h
ctr128.o: ../../include/openssl/modes.h ctr128.c modes_lcl.h
cts128.o: ../../include/openssl/modes.h cts128.c modes_lcl.h
gcm128.o: ../../include/openssl/modes.h gcm128.c modes_lcl.h
ofb128.o: ../../include/openssl/modes.h modes_lcl.h ofb128.c
+2 −7
Original line number Diff line number Diff line
@@ -48,7 +48,7 @@
 *
 */

#include "modes.h"
#include "modes_lcl.h"
#include <string.h>

#ifndef MODES_DEBUG
@@ -58,12 +58,7 @@
#endif
#include <assert.h>

#define STRICT_ALIGNMENT 1
#if defined(__i386) || defined(__i386__) || \
    defined(__x86_64) || defined(__x86_64__) || \
    defined(_M_IX86) || defined(_M_AMD64) || defined(_M_X64) || \
    defined(__s390__) || defined(__s390x__)
#  undef STRICT_ALIGNMENT
#ifndef STRICT_ALIGNMENT
#  define STRICT_ALIGNMENT 0
#endif

+1 −9
Original line number Diff line number Diff line
@@ -48,7 +48,7 @@
 *
 */

#include "modes.h"
#include "modes_lcl.h"
#include <string.h>

#ifndef MODES_DEBUG
@@ -58,14 +58,6 @@
#endif
#include <assert.h>

#define STRICT_ALIGNMENT
#if defined(__i386) || defined(__i386__) || \
    defined(__x86_64) || defined(__x86_64__) || \
    defined(_M_IX86) || defined(_M_AMD64) || defined(_M_X64) || \
    defined(__s390__) || defined(__s390x__)
#  undef STRICT_ALIGNMENT
#endif

/* The input and output encrypted as though 128bit cfb mode is being
 * used.  The extra state information to record how much of the
 * 128bit block we have used is contained in *num;
+79 −12
Original line number Diff line number Diff line
@@ -48,7 +48,7 @@
 *
 */

#include "modes.h"
#include "modes_lcl.h"
#include <string.h>

#ifndef MODES_DEBUG
@@ -58,17 +58,6 @@
#endif
#include <assert.h>

typedef unsigned int u32;
typedef unsigned char u8;

#define STRICT_ALIGNMENT
#if defined(__i386)	|| defined(__i386__)	|| \
    defined(__x86_64)	|| defined(__x86_64__)	|| \
    defined(_M_IX86)	|| defined(_M_AMD64)	|| defined(_M_X64) || \
    defined(__s390__)	|| defined(__s390x__)
#  undef STRICT_ALIGNMENT
#endif

/* NOTE: the IV/counter CTR mode is big-endian.  The code itself
 * is endian-neutral. */

@@ -182,3 +171,81 @@ void CRYPTO_ctr128_encrypt(const unsigned char *in, unsigned char *out,

	*num=n;
}

/* increment upper 96 bits of 128-bit counter by 1 */
static void ctr96_inc(unsigned char *counter) {
	u32 n=12;
	u8  c;

	do {
		--n;
		c = counter[n];
		++c;
		counter[n] = c;
		if (c) return;
	} while (n);
}

void CRYPTO_ctr128_encrypt_ctr32(const unsigned char *in, unsigned char *out,
			size_t len, const void *key,
			unsigned char ivec[16], unsigned char ecount_buf[16],
			unsigned int *num, ctr128_f func)
{
	unsigned int n,ctr32;

	assert(in && out && key && ecount_buf && num);
	assert(*num < 16);

	n = *num;

	while (n && len) {
		*(out++) = *(in++) ^ ecount_buf[n];
		--len;
		n = (n+1) % 16;
	}

	ctr32 = GETU32(ivec+12);
	while (len>=16) {
		size_t blocks = len/16;
		/*
		 * 1<<28 is just a not-so-small yet not-so-large number...
		 * Below condition is practically never met, but it has to
		 * be checked for code correctness.
		 */
		if (sizeof(size_t)>sizeof(unsigned int) && blocks>(1U<<28))
			blocks = (1U<<28);
		/*
		 * As (*func) operates on 32-bit counter, caller
		 * has to handle overflow. 'if' below detects the
		 * overflow, which is then handled by limiting the
		 * amount of blocks to the exact overflow point...
		 */
		ctr32 += (u32)blocks;
		if (ctr32 < blocks) {
			blocks -= ctr32;
			ctr32   = 0;
		}
		(*func)(in,out,blocks,key,ivec);
		/* (*ctr) does not update ivec, caller does: */
		PUTU32(ivec+12,ctr32);
		/* ... overflow was detected, propogate carry. */
		if (ctr32 == 0)	ctr96_inc(ivec);
		blocks *= 16;
		len -= blocks;
		out += blocks;
		in  += blocks;
	}
	if (len) {
		memset(ecount_buf,0,16);
		(*func)(ecount_buf,ecount_buf,1,key,ivec);
		++ctr32;
		PUTU32(ivec+12,ctr32);
		if (ctr32 == 0)	ctr96_inc(ivec);
		while (len--) {
			out[n] = in[n] ^ ecount_buf[n];
			++n;
		}
	}

	*num=n;
}
+1 −1
Original line number Diff line number Diff line
@@ -5,7 +5,7 @@
 * forms are granted according to the OpenSSL license.
 */

#include "modes.h"
#include "modes_lcl.h"
#include <string.h>

#ifndef MODES_DEBUG
Loading