All of lore.kernel.org
 help / color / mirror / Atom feed
* Suspect bug in the authenc module
@ 2010-02-27 11:14 Roberto Sassu
  2010-03-01 13:24 ` Steffen Klassert
  0 siblings, 1 reply; 4+ messages in thread
From: Roberto Sassu @ 2010-02-27 11:14 UTC (permalink / raw)
  To: linux-crypto

[-- Attachment #1: Type: Text/Plain, Size: 3009 bytes --]

Hello

i'm trying to use the authenc module and i wrote a small kernel module that 
simply encrypts/decrypts a fixed data using the hmac(sha1) as authentication 
algorithm and cbc(aes) as encryption algorithm. 
The used platform is a KVM quest with Fedora 12 i686 and the latest kernel 
2.6.33.
I have taken the code from the testmgr and from net/ipv4/esp4.c.
But, when testing the code, attached in this mail, the crypto_aead_decrypt() 
function always replies -EBADMSG. 
I tried the same code in a 64-bit machine (user mode kernel and Fedora 12) and 
the decryption was successful. I noted, when comparing the auth portion in 
both systems, that this computed during the encryption from the 32bit KVM 
guest, was different and with no fixed value. I investigated in the code of 
authenc and i recorded some partial result of the encryption operation. That 
is the log:   

--------- testing authenc: encrypt ---------------
assoc: 495C501F1D94CC81BAB7B603AFA5C1A1D85C4268E06CDA8905AC56AC1B2AD386
alg: No test for authenc(hmac(sha1),cbc(aes)) (authenc(hmac(sha1-
generic),cbc(aes-asm)))
Setting ahash key: 313233343536373839303132
Setting blk key: 31323334353637383930313233343536
crypto_authenc_encrypt: ivsize 16 iv: 01010101010101010101010101010101
crypto_authenc_genicv: dump vdst: 
CFE3A997243F38B0D6A89DCAB5126DC93952E493E72EA590CC8D186A4E1654860000000000000000000000000000000000000000
crypto_authenc_genicv ivsize 16,dst offset 3392 iv 
01010101010101010101010101010101
crypto_authenc_genicv: iv after sg_init_table 00000000000000000101010101010101
crypto_authenc_genicv: vdst == iv + ivsize? 0
crypto_authenc_genicv: scatterlist dst 0 before fn assignement (line 355): 
3242265088, 388, 32, dump: 
495C501F1D94CC81BAB7B603AFA5C1A1D85C4268E06CDA8905AC56AC1B2AD386
crypto_authenc_genicv: scatterlist dst 1 before fn assignement (line 355): 
3727819872, 0, 0, dump: 
crypto_authenc_genicv: scatterlist dst 2 before fn assignement (line 355): 
3241960448, 1152, 16, dump: 00000000000000000101010101010101
crypto_authenc_genicv: scatterlist dst 3 before fn assignement (line 355): 
3747577608, 0, 0, dump: 
crypto_authenc_genicv: scatterlist dst 0 after fn assignement (line 355): 
3242265088, 388, 32, dump: 
495C501F1D94CC81BAB7B603AFA5C1A1D85C4268E06CDA8905AC56AC1B2AD386
crypto_authenc_genicv: scatterlist dst 1 after fn assignement (line 355): 
3727819872, 0, 0, dump: 
crypto_authenc_genicv: scatterlist dst 2 after fn assignement (line 355): 
3241960448, 1152, 16, dump: 0000000000000000C01886E0201986E0
crypto_authenc_genicv: scatterlist dst 2 after fn assignement (line 355):: 
3747577608, 0, 0, dump: 
--------------------------------------------------

Just for test, i tried to add a 16bit long offset when defining the memory 
address for the "iv" in the function  crypto_authenc_encrypt() for the 32-bit 
kernel, and everything works fine.
I don't know if i made a mistake in the code that causes this misbehaviour in 
the authenc module or if it is a bug.

Thanks in advance for the reply.

[-- Attachment #2: testaeadesp.c --]
[-- Type: text/x-csrc, Size: 5385 bytes --]

#include <crypto/hash.h>
#include <linux/err.h>
#include <linux/module.h>
#include <linux/scatterlist.h>
#include <linux/slab.h>
#include <linux/string.h>
#include <crypto/rng.h>
#include <crypto/authenc.h>
#include <linux/pagemap.h>
#include <linux/rtnetlink.h>

#define MAX_IVLEN		16
#define AUTHSIZE		20

int testmode = 0;

module_param(testmode, int, 0);

void hexdump(unsigned char *buf, int len) 
{
	while(--len >=0)
		printk("%02X", *buf++);
	printk("\n");
}


struct tcrypt_result {
	struct completion completion;
	int err;
};


static void tcrypt_complete(struct crypto_async_request *req, int err)
{
	struct tcrypt_result *res = req->data;

	if (err == -EINPROGRESS)
		return;

	res->err = err;
	complete(&res->completion);
}


static int testrun(void)
{
 	const char *algo = "authenc(hmac(sha1),cbc(aes))";

	struct crypto_aead *tfm;
	unsigned int i;
	int ret = -ENOMEM;
	unsigned char *ekey = "1234567890123456";
	unsigned char *akey = "123456789012";
	unsigned char *key, *pp;
	unsigned int ekeylen = 16;
	unsigned int akeylen = 12;
	unsigned int keylen = 0;
	struct aead_request *req;
	struct tcrypt_result result;
	unsigned int authsize = AUTHSIZE;
	char *assoc = "\x49\x5c\x50\x1f\x1d\x94\xcc\x81"
			  "\xba\xb7\xb6\x03\xaf\xa5\xc1\xa1"
			  "\xd8\x5c\x42\x68\xe0\x6c\xda\x89"
			  "\x05\xac\x56\xac\x1b\x2a\xd3\x86";
	int assoclen = 32;
	unsigned char iv[MAX_IVLEN];
	mm_segment_t old_fs = get_fs();
	struct file *fp;
	struct scatterlist src_sg, dst_sg;
	struct scatterlist asg;
	char *filename = "file1.txt";
	char *string = "ciao";
	struct crypto_authenc_key_param *param;
	struct rtattr *rta;
	char *input;
	int blksize = 0;
	int clen = 16;		/* len of data */

	printk("assoc: ");
	hexdump(assoc, 32);

	tfm = crypto_alloc_aead(algo, 0, 0);
	if (IS_ERR(tfm)) {
		printk(KERN_ERR "alg: aead: Failed to load transform for %s: "
		       "%ld\n", algo, PTR_ERR(tfm));
		goto out;
	}

	blksize = ALIGN(crypto_aead_blocksize(tfm), 4);
	clen = ALIGN(clen + 2, blksize);
	input = kzalloc(clen + AUTHSIZE, GFP_KERNEL);
	
	if(!testmode) {
		set_fs(KERNEL_DS);

		fp = filp_open(filename, O_RDONLY, 0);
		if(IS_ERR(fp)) {
			printk("Error opening file: %s\n", filename);
			set_fs(old_fs);
			goto out;
		}
		fp->f_op->read(fp, input, clen + AUTHSIZE, &fp->f_pos);

		filp_close(fp, NULL); 
		set_fs(old_fs);
	} else
		memcpy(input, string, strlen(string));	

	init_completion(&result.completion);
	
	req = aead_request_alloc(tfm, GFP_KERNEL);
	if (!req) {
		printk(KERN_ERR "alg: aead: Failed to allocate request for "
		       "%s\n", algo);
		goto out_tfm;
	}
	aead_request_set_callback(req, CRYPTO_TFM_REQ_MAY_BACKLOG,
				  tcrypt_complete, &result);

	memset(iv, 1, MAX_IVLEN);
	crypto_aead_clear_flags(tfm, ~0);
	crypto_aead_set_flags(tfm, CRYPTO_TFM_REQ_WEAK_KEY);
	
	keylen = akeylen + ekeylen + RTA_SPACE(sizeof(*param));
	key = kzalloc(keylen, GFP_KERNEL);
	if (!key)
		goto out_req;

	pp = key;
	rta = (void *)pp;
	rta->rta_type = CRYPTO_AUTHENC_KEYA_PARAM;
	rta->rta_len = RTA_LENGTH(sizeof(*param));
	param = RTA_DATA(rta);
	pp += RTA_SPACE(sizeof(*param));

	if(akeylen) {
		memcpy(pp, akey, akeylen);
		pp += akeylen;
	}

	ret = crypto_aead_setauthsize(tfm, authsize);
	if (ret) {
		printk(KERN_ERR "alg: aead: Failed to set "
		       "authsize to %u on test for %s\n",
		       authsize, algo);
		goto out_key;
	}
	
	param->enckeylen = cpu_to_be32(ekeylen);
	memcpy(pp, ekey, ekeylen);
	
	ret = crypto_aead_setkey(tfm, key, keylen);
	if (ret) {
		printk(KERN_ERR "alg: aead: Failed to set "
		       "the key for %s\n",
		       algo);
		goto out_key;
	}

	sg_init_one(&src_sg, input, clen + AUTHSIZE);
	sg_init_one(&dst_sg, input, clen + AUTHSIZE);
	sg_init_one(&asg, assoc, assoclen);

	aead_request_set_crypt(req, &src_sg, &dst_sg, clen +  (testmode ? 0 : authsize), iv);

	aead_request_set_assoc(req, &asg, assoclen);
	
	ret = testmode ?
		crypto_aead_encrypt(req) :
		crypto_aead_decrypt(req);

	switch (ret) {
		case 0:
			if(!testmode)
				printk("File OK\n");
			break;
		case -EINPROGRESS:	  
		case -EBUSY:
			ret = wait_for_completion_interruptible(
				&result.completion);
			if (!ret && !(ret = result.err)) {
				INIT_COMPLETION(result.completion);
				break;
			}
		case -EBADMSG:
			printk("File corrupted\n");
		default:
			printk(KERN_ERR "alg: aead: %s failed "
						"for %s: ret=%d\n", testmode ? "encrypt" : "decrypt", algo, -ret);
	}
	
	if(ret)
		goto out_key;
	printk("%s: %d\n", testmode ? "encrypt" : "decrypt", ret);
	
	if(testmode) {
		set_fs(KERNEL_DS);

		fp = filp_open(filename, O_WRONLY | O_CREAT | O_TRUNC, 0700);
		if(IS_ERR(fp)) {
			printk("Error opening file: %s\n", filename);
			set_fs(old_fs);
			goto out_key;
		}
		fp->f_op->write(fp, input, clen + AUTHSIZE, &fp->f_pos);
		hexdump(input + clen, AUTHSIZE);
		filp_close(fp, NULL); 
		set_fs(old_fs);
	} else {
		printk("Decrypted: %s\n", input);
	}
	kfree(input);
out_key:
	kfree(key);
out_req:
	aead_request_free(req);
out_tfm:
	crypto_free_aead(tfm);
out:

	return ret;
}

int __init testaead_start(void) {
	int ret;
	printk("--------- testing authenc: %s ---------------\n", testmode ? "encrypt" : "decrypt");
	ret = testrun();
	printk("Result: %d\n", ret);
	printk("--------------------------------------------------\n");

	return -1;
}


void __exit testaead_stop(void) {

}

module_init(testaead_start);
module_exit(testaead_stop);
MODULE_LICENSE("GPL");


^ permalink raw reply	[flat|nested] 4+ messages in thread

* Re: Suspect bug in the authenc module
  2010-02-27 11:14 Suspect bug in the authenc module Roberto Sassu
@ 2010-03-01 13:24 ` Steffen Klassert
  2010-03-04 10:54   ` Roberto Sassu
  0 siblings, 1 reply; 4+ messages in thread
From: Steffen Klassert @ 2010-03-01 13:24 UTC (permalink / raw)
  To: Roberto Sassu; +Cc: linux-crypto

On Sat, Feb 27, 2010 at 12:14:15PM +0100, Roberto Sassu wrote:
> Hello
> 
> i'm trying to use the authenc module and i wrote a small kernel module that 
> simply encrypts/decrypts a fixed data using the hmac(sha1) as authentication 
> algorithm and cbc(aes) as encryption algorithm. 
> The used platform is a KVM quest with Fedora 12 i686 and the latest kernel 
> 2.6.33.
> I have taken the code from the testmgr and from net/ipv4/esp4.c.
> But, when testing the code, attached in this mail, the crypto_aead_decrypt() 
> function always replies -EBADMSG. 

I've posted two fixes for authenc to the linux-crypto list last week.
Could you please try whether these patches fix your problems?

Thanks,

Steffen


^ permalink raw reply	[flat|nested] 4+ messages in thread

* Re: Suspect bug in the authenc module
  2010-03-01 13:24 ` Steffen Klassert
@ 2010-03-04 10:54   ` Roberto Sassu
  2010-03-05  7:26     ` Herbert Xu
  0 siblings, 1 reply; 4+ messages in thread
From: Roberto Sassu @ 2010-03-04 10:54 UTC (permalink / raw)
  To: Steffen Klassert; +Cc: linux-crypto

Hello

i pulled the crypto-2.6 repo today. Issues appear to be solved for both 32-bit 
and 64-bit systems. Many thanks!

I have got another trouble when compiling my test module with a 64-bit 
operating system:

when dumping the data placed pointed by the scatterlist array i noted that the 
assoc is always zero'ed. I investigated further and it seems that the problem 
is the static allocation of the assoc string in my test module. When using the 
kmalloc the dump is correct.   

On Monday 01 March 2010 14:24:33 Steffen Klassert wrote:
> On Sat, Feb 27, 2010 at 12:14:15PM +0100, Roberto Sassu wrote:
> > Hello
> > 
> > i'm trying to use the authenc module and i wrote a small kernel module
> > that simply encrypts/decrypts a fixed data using the hmac(sha1) as
> > authentication algorithm and cbc(aes) as encryption algorithm.
> > The used platform is a KVM quest with Fedora 12 i686 and the latest
> > kernel 2.6.33.
> > I have taken the code from the testmgr and from net/ipv4/esp4.c.
> > But, when testing the code, attached in this mail, the
> > crypto_aead_decrypt() function always replies -EBADMSG.
> 
> I've posted two fixes for authenc to the linux-crypto list last week.
> Could you please try whether these patches fix your problems?
> 
> Thanks,
> 
> Steffen

^ permalink raw reply	[flat|nested] 4+ messages in thread

* Re: Suspect bug in the authenc module
  2010-03-04 10:54   ` Roberto Sassu
@ 2010-03-05  7:26     ` Herbert Xu
  0 siblings, 0 replies; 4+ messages in thread
From: Herbert Xu @ 2010-03-05  7:26 UTC (permalink / raw)
  To: Roberto Sassu; +Cc: steffen.klassert, linux-crypto

Roberto Sassu <myrobmail@gmail.com> wrote:
>
> when dumping the data placed pointed by the scatterlist array i noted that the 
> assoc is always zero'ed. I investigated further and it seems that the problem 
> is the static allocation of the assoc string in my test module. When using the 
> kmalloc the dump is correct.   

Right, static allocation in general is incompatible with any
interface that uses scatterlists.

Cheers,
-- 
Visit Openswan at http://www.openswan.org/
Email: Herbert Xu ~{PmV>HI~} <herbert@gondor.apana.org.au>
Home Page: http://gondor.apana.org.au/~herbert/
PGP Key: http://gondor.apana.org.au/~herbert/pubkey.txt

^ permalink raw reply	[flat|nested] 4+ messages in thread

end of thread, other threads:[~2010-03-05  7:26 UTC | newest]

Thread overview: 4+ messages (download: mbox.gz / follow: Atom feed)
-- links below jump to the message on this page --
2010-02-27 11:14 Suspect bug in the authenc module Roberto Sassu
2010-03-01 13:24 ` Steffen Klassert
2010-03-04 10:54   ` Roberto Sassu
2010-03-05  7:26     ` Herbert Xu

This is an external index of several public inboxes,
see mirroring instructions on how to clone and mirror
all data and code used by this external index.