From 827e65e77c32da30ce675e8e7c05de73d9aeab5a Mon Sep 17 00:00:00 2001 From: Miloslav Trmač Date: Fri, 13 Aug 2010 19:17:16 +0200 Subject: Convert *_KEY_EXPORT --- examples/ncr.c | 61 ++++++++++++++----------------- examples/pk.c | 113 +++++++++++++++++++++++++++------------------------------ ncr-int.h | 3 +- ncr-key.c | 34 ++++++----------- ncr-pk.c | 2 +- ncr.c | 45 ++++++++++++++++++++++- ncr.h | 10 ++++- 7 files changed, 149 insertions(+), 119 deletions(-) diff --git a/examples/ncr.c b/examples/ncr.c index b999003..2c2ca7c 100644 --- a/examples/ncr.c +++ b/examples/ncr.c @@ -58,6 +58,7 @@ test_ncr_key(int cfd) struct nlattr *nla; ncr_key_t key; struct ncr_key_data_st keydata; + struct ncr_key_export kexport; uint8_t data[KEY_DATA_SIZE]; uint8_t data_bak[KEY_DATA_SIZE]; uint16_t *attr_p; @@ -101,20 +102,14 @@ test_ncr_key(int cfd) /* now try to read it */ fprintf(stdout, "\tKey export...\n"); - memset(&keydata, 0, sizeof(keydata)); - keydata.key = key; - keydata.idata = data; - keydata.idata_size = sizeof(data); + memset(&kexport, 0, sizeof(kexport)); + kexport.key = key; + kexport.buffer = data; + kexport.buffer_size = sizeof(data); - if (ioctl(cfd, NCRIO_KEY_EXPORT, &keydata)) { - fprintf(stderr, "Error: %s:%d\n", __func__, __LINE__); - perror("ioctl(NCRIO_KEY_IMPORT)"); - return 1; - } - - if (keydata.idata_size != sizeof(data)) { + if (ioctl(cfd, NCRIO_KEY_EXPORT, &kexport) != sizeof(data)) { fprintf(stderr, "Error: %s:%d\n", __func__, __LINE__); - fprintf(stderr, "data returned but differ!\n"); + perror("ioctl(NCRIO_KEY_EXPORT)"); return 1; } @@ -165,18 +160,18 @@ test_ncr_key(int cfd) memset(data, 0, sizeof(data)); - memset(&keydata, 0, sizeof(keydata)); - keydata.key = key; - keydata.idata = data; - keydata.idata_size = sizeof(data); + memset(&kexport, 0, sizeof(kexport)); + kexport.key = key; + kexport.buffer = data; + kexport.buffer_size = sizeof(data); - if (ioctl(cfd, NCRIO_KEY_EXPORT, &keydata)) { + if (ioctl(cfd, NCRIO_KEY_EXPORT, &kexport) != sizeof(data)) { fprintf(stderr, "Error: %s:%d\n", __func__, __LINE__); - perror("ioctl(NCRIO_KEY_IMPORT)"); + perror("ioctl(NCRIO_KEY_EXPORT)"); return 1; } - if (keydata.idata_size == 0 || (data[0] == 0 && data[1] == 0 && data[2] == 0 && data[4] == 0)) { + if (data[0] == 0 && data[1] == 0 && data[2] == 0 && data[4] == 0) { fprintf(stderr, "Error: %s:%d\n", __func__, __LINE__); fprintf(stderr, "Generated key: %.2x.%.2x.%.2x.%.2x.%.2x.%.2x.%.2x.%.2x." "%.2x.%.2x.%.2x.%.2x.%.2x.%.2x.%.2x.%.2x\n", data[0], data[1], @@ -296,14 +291,14 @@ test_ncr_key(int cfd) memset(data, 0, sizeof(data)); - memset(&keydata, 0, sizeof(keydata)); - keydata.key = key; - keydata.idata = data; - keydata.idata_size = sizeof(data); + memset(&kexport, 0, sizeof(kexport)); + kexport.key = key; + kexport.buffer = data; + kexport.buffer_size = sizeof(data); /* try to get the output data - should fail */ - if (ioctl(cfd, NCRIO_KEY_EXPORT, &keydata)==0) { + if (ioctl(cfd, NCRIO_KEY_EXPORT, &kexport) >= 0) { fprintf(stderr, "Error: %s:%d\n", __func__, __LINE__); fprintf(stderr, "Data were exported, but shouldn't be!\n"); return 1; @@ -580,6 +575,7 @@ test_ncr_store_wrap_key(int cfd) int i; ncr_key_t key2; struct ncr_key_data_st keydata; + struct ncr_key_export kexport; struct ncr_key_storage_wrap_st kwrap; uint8_t data[DATA_SIZE]; int data_size; @@ -659,20 +655,19 @@ test_ncr_store_wrap_key(int cfd) } /* now export the unwrapped */ - memset(&keydata, 0, sizeof(keydata)); - keydata.key = key2; - keydata.idata = data; - keydata.idata_size = sizeof(data); + memset(&kexport, 0, sizeof(kexport)); + kexport.key = key2; + kexport.buffer = data; + kexport.buffer_size = sizeof(data); - if (ioctl(cfd, NCRIO_KEY_EXPORT, &keydata)) { + data_size = ioctl(cfd, NCRIO_KEY_EXPORT, &kexport); + if (data_size != 16) { fprintf(stderr, "Error: %s:%d\n", __func__, __LINE__); - perror("ioctl(NCRIO_KEY_IMPORT)"); + perror("ioctl(NCRIO_KEY_EXPORT)"); return 1; } - - data_size = keydata.idata_size; - if (data_size != 16 || memcmp(data, DKEY, 16) != 0) { + if (memcmp(data, DKEY, 16) != 0) { fprintf(stderr, "Unwrapped data do not match.\n"); fprintf(stderr, "Data[%d]: ", (int) data_size); for(i=0;ibuffer_size < 0) { err(); - return -EFAULT; + return -EINVAL; } - ret = ncr_key_item_get_read( &item, lst, data.key); + ret = ncr_key_item_get_read(&item, lst, data->key); if (ret < 0) { err(); return ret; @@ -240,15 +237,15 @@ int ret; switch (item->type) { case NCR_KEY_TYPE_SECRET: - if (item->key.secret.size > data.idata_size) { + if (item->key.secret.size > data->buffer_size) { err(); - ret = -EINVAL; + ret = -ERANGE; goto fail; } /* found */ if (item->key.secret.size > 0) { - ret = copy_to_user(data.idata, item->key.secret.data, item->key.secret.size); + ret = copy_to_user(data->buffer, item->key.secret.data, item->key.secret.size); if (unlikely(ret)) { err(); ret = -EFAULT; @@ -256,11 +253,11 @@ int ret; } } - data.idata_size = item->key.secret.size; + ret = item->key.secret.size; break; case NCR_KEY_TYPE_PUBLIC: case NCR_KEY_TYPE_PRIVATE: - tmp_size = data.idata_size; + tmp_size = data->buffer_size; tmp = kmalloc(tmp_size, GFP_KERNEL); if (tmp == NULL) { @@ -270,20 +267,19 @@ int ret; } ret = ncr_pk_pack(item, tmp, &tmp_size); - data.idata_size = tmp_size; - if (ret < 0) { err(); goto fail; } - ret = copy_to_user(data.idata, tmp, tmp_size); + ret = copy_to_user(data->buffer, tmp, tmp_size); if (unlikely(ret)) { err(); ret = -EFAULT; goto fail; } + ret = tmp_size; break; default: err(); @@ -291,12 +287,6 @@ int ret; goto fail; } - if (unlikely(copy_to_user(arg, &data, sizeof(data)))) { - err(); - ret = -EFAULT; - } else - ret = 0; - fail: kfree(tmp); if (item) diff --git a/ncr-pk.c b/ncr-pk.c index 921b193..c96f494 100644 --- a/ncr-pk.c +++ b/ncr-pk.c @@ -37,7 +37,7 @@ int _ncr_tomerr(int err) { switch (err) { case CRYPT_BUFFER_OVERFLOW: - return -EOVERFLOW; + return -ERANGE; case CRYPT_MEM: return -ENOMEM; default: diff --git a/ncr.c b/ncr.c index 796ca32..bc19e24 100644 --- a/ncr.c +++ b/ncr.c @@ -166,10 +166,9 @@ ncr_ioctl(struct ncr_lists *lst, unsigned int cmd, unsigned long arg_) ncr_out_free(&out); break; } + CASE_NO_OUTPUT(NCRIO_KEY_EXPORT, ncr_key_export, ncr_key_export); case NCRIO_KEY_DEINIT: return ncr_key_deinit(lst, arg); - case NCRIO_KEY_EXPORT: - return ncr_key_export(lst, arg); case NCRIO_KEY_IMPORT: return ncr_key_import(lst, arg); case NCRIO_KEY_WRAP: @@ -200,9 +199,31 @@ ncr_ioctl(struct ncr_lists *lst, unsigned int cmd, unsigned long arg_) } #ifdef CONFIG_COMPAT +struct compat_ncr_key_export { + __u32 input_size, output_size; + ncr_key_t key; + compat_uptr_t buffer; + compat_int_t buffer_size; + __NL_ATTRIBUTES; +}; +#define COMPAT_NCRIO_KEY_EXPORT _IOWR('c', 209, struct compat_ncr_key_export) + +static void convert_ncr_key_export(struct ncr_key_export *new, + const struct compat_ncr_key_export *old) +{ + new->key = old->key; + new->buffer = compat_ptr(old->buffer); + new->buffer_size = old->buffer_size; +} + long ncr_compat_ioctl(struct ncr_lists *lst, unsigned int cmd, unsigned long arg_) { + void __user *arg = (void __user *)arg_; + struct nlattr *tb[NCR_ATTR_MAX + 1]; + void *attr_buf; + int ret; + if (unlikely(!lst)) BUG(); @@ -213,8 +234,28 @@ ncr_compat_ioctl(struct ncr_lists *lst, unsigned int cmd, unsigned long arg_) case NCRIO_KEY_DERIVE: case NCRIO_KEY_GET_INFO: return ncr_ioctl(lst, cmd, arg_); + +#define CASE_NO_OUTPUT(LABEL, STRUCT, FUNCTION) \ + case (LABEL): { \ + struct compat_##STRUCT old; \ + struct STRUCT new; \ + \ + attr_buf = NCR_GET_INPUT_ARGS_NO_OUTPUT(&old, tb, arg); \ + if (IS_ERR(attr_buf)) { \ + err(); \ + return PTR_ERR(attr_buf); \ + } \ + convert_##STRUCT(&new, &old); \ + ret = (FUNCTION)(lst, &new, tb); \ + break; \ + } + + CASE_NO_OUTPUT(COMPAT_NCRIO_KEY_EXPORT, ncr_key_export, ncr_key_export); default: return -EINVAL; +#undef CASE_NO_OUTPUT } + kfree(attr_buf); + return ret; } #endif diff --git a/ncr.h b/ncr.h index d4d1d6a..f6982de 100644 --- a/ncr.h +++ b/ncr.h @@ -196,6 +196,14 @@ struct ncr_key_data_st { ncr_algorithm_t algorithm; /* valid for public/private keys */ }; +struct ncr_key_export { + __u32 input_size, output_size; + ncr_key_t key; + void __user *buffer; + int buffer_size; + __NL_ATTRIBUTES; +}; + #define NCRIO_KEY_INIT _IO('c', 204) /* generate a secret key */ #define NCRIO_KEY_GENERATE _IOWR('c', 205, struct ncr_key_generate) @@ -207,7 +215,7 @@ struct ncr_key_data_st { #define NCRIO_KEY_GET_INFO _IOWR('c', 208, struct ncr_key_get_info) /* export a secret key */ -#define NCRIO_KEY_EXPORT _IOWR('c', 209, struct ncr_key_data_st) +#define NCRIO_KEY_EXPORT _IOWR('c', 209, struct ncr_key_export) /* import a secret key */ #define NCRIO_KEY_IMPORT _IOWR('c', 210, struct ncr_key_data_st) -- cgit