void twofish_enc_blk_ctr_3way(void *ctx, u128 *dst, const u128 *src,
				     u128 *iv)
{
	be128 ctrblks[3];

	if (dst != src) {
		dst[0] = src[0];
		dst[1] = src[1];
		dst[2] = src[2];
	}

	u128_to_be128(&ctrblks[0], iv);
	u128_inc(iv);
	u128_to_be128(&ctrblks[1], iv);
	u128_inc(iv);
	u128_to_be128(&ctrblks[2], iv);
	u128_inc(iv);

	twofish_enc_blk_xor_3way(ctx, (u8 *)dst, (u8 *)ctrblks);
}
void twofish_enc_blk_ctr(void *ctx, u128 *dst, const u128 *src, u128 *iv)
{
	be128 ctrblk;

	if (dst != src)
		*dst = *src;

	u128_to_be128(&ctrblk, iv);
	u128_inc(iv);

	twofish_enc_blk(ctx, (u8 *)&ctrblk, (u8 *)&ctrblk);
	u128_xor(dst, dst, (u128 *)&ctrblk);
}
예제 #3
0
static void twofish_enc_blk_ctr_xway(void *ctx, u128 *dst, const u128 *src,
				     u128 *iv)
{
	be128 ctrblks[TWOFISH_PARALLEL_BLOCKS];
	unsigned int i;

	for (i = 0; i < TWOFISH_PARALLEL_BLOCKS; i++) {
		if (dst != src)
			dst[i] = src[i];

		u128_to_be128(&ctrblks[i], iv);
		u128_inc(iv);
	}

	twofish_enc_blk_xway_xor(ctx, (u8 *)dst, (u8 *)ctrblks);
}
예제 #4
0
static unsigned int __ctr_crypt(struct blkcipher_desc *desc,
				struct blkcipher_walk *walk)
{
	struct twofish_ctx *ctx = crypto_blkcipher_ctx(desc->tfm);
	unsigned int bsize = TF_BLOCK_SIZE;
	unsigned int nbytes = walk->nbytes;
	u128 *src = (u128 *)walk->src.virt.addr;
	u128 *dst = (u128 *)walk->dst.virt.addr;
	u128 ctrblk;
	be128 ctrblocks[3];

	be128_to_u128(&ctrblk, (be128 *)walk->iv);

	/* Process three block batch */
	if (nbytes >= bsize * 3) {
		do {
			if (dst != src) {
				dst[0] = src[0];
				dst[1] = src[1];
				dst[2] = src[2];
			}

			/* create ctrblks for parallel encrypt */
			u128_to_be128(&ctrblocks[0], &ctrblk);
			u128_inc(&ctrblk);
			u128_to_be128(&ctrblocks[1], &ctrblk);
			u128_inc(&ctrblk);
			u128_to_be128(&ctrblocks[2], &ctrblk);
			u128_inc(&ctrblk);

			twofish_enc_blk_xor_3way(ctx, (u8 *)dst,
						 (u8 *)ctrblocks);

			src += 3;
			dst += 3;
			nbytes -= bsize * 3;
		} while (nbytes >= bsize * 3);

		if (nbytes < bsize)
			goto done;
	}

	/* Handle leftovers */
	do {
		if (dst != src)
			*dst = *src;

		u128_to_be128(&ctrblocks[0], &ctrblk);
		u128_inc(&ctrblk);

		twofish_enc_blk(ctx, (u8 *)ctrblocks, (u8 *)ctrblocks);
		u128_xor(dst, dst, (u128 *)ctrblocks);

		src += 1;
		dst += 1;
		nbytes -= bsize;
	} while (nbytes >= bsize);

done:
	u128_to_be128((be128 *)walk->iv, &ctrblk);
	return nbytes;
}