summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorMiloslav Trmač <mitr@redhat.com>2010-08-16 16:06:43 +0200
committerMiloslav Trmač <mitr@redhat.com>2010-08-24 23:43:46 +0200
commit3ab6fc7d0d19f62b48ecef310249014192289613 (patch)
tree108739dea2e11cb87bb3790eb785331e4cef2308
parent9aa6874612bf258f0a9795371db9b3dc514376aa (diff)
downloadcryptodev-linux-3ab6fc7d0d19f62b48ecef310249014192289613.tar.gz
cryptodev-linux-3ab6fc7d0d19f62b48ecef310249014192289613.tar.xz
cryptodev-linux-3ab6fc7d0d19f62b48ecef310249014192289613.zip
Convert *_KEY_WRAP
-rw-r--r--examples/ncr.c76
-rw-r--r--examples/pk.c65
-rw-r--r--ncr-int.h3
-rw-r--r--ncr-key-wrap.c55
-rw-r--r--ncr.c23
-rw-r--r--ncr.h13
-rw-r--r--utils.c2
7 files changed, 153 insertions, 84 deletions
diff --git a/examples/ncr.c b/examples/ncr.c
index 56a59ce..7324c16 100644
--- a/examples/ncr.c
+++ b/examples/ncr.c
@@ -337,7 +337,7 @@ test_ncr_key(int cfd)
static int
test_ncr_wrap_key(int cfd)
{
- int i, ret;
+ int i;
ncr_key_t key, key2;
struct __attribute__((packed)) {
struct ncr_key_import f;
@@ -350,7 +350,12 @@ test_ncr_wrap_key(int cfd)
struct nlattr flags_head ALIGN_NL;
uint32_t flags ALIGN_NL;
} kimport;
- struct ncr_key_wrap_st kwrap;
+ struct __attribute__((packed)) {
+ struct ncr_key_wrap f;
+ struct nlattr algo_head ALIGN_NL;
+ uint32_t algo ALIGN_NL;
+ } kwrap;
+ struct ncr_key_wrap_st kunwrap;
uint8_t data[WRAPPED_KEY_DATA_SIZE];
int data_size;
@@ -429,16 +434,18 @@ test_ncr_wrap_key(int cfd)
}
/* now try wrapping key2 using key */
- memset(&kwrap, 0, sizeof(kwrap));
- kwrap.algorithm = NCR_WALG_AES_RFC3394;
- kwrap.keytowrap = key2;
- kwrap.key = key;
- kwrap.io = data;
- kwrap.io_size = sizeof(data);
-
- ret = ioctl(cfd, NCRIO_KEY_WRAP, &kwrap);
-
- if (geteuid() == 0 && ret) {
+ memset(&kwrap.f, 0, sizeof(kwrap.f));
+ kwrap.f.input_size = sizeof(kwrap);
+ kwrap.f.wrapping_key = key;
+ kwrap.f.source_key = key2;
+ kwrap.f.buffer = data;
+ kwrap.f.buffer_size = sizeof(data);
+ kwrap.algo_head.nla_len = NLA_HDRLEN + sizeof(kwrap.algo);
+ kwrap.algo_head.nla_type = NCR_ATTR_WRAPPING_ALGORITHM;
+ kwrap.algo = NCR_WALG_AES_RFC3394;
+
+ data_size = ioctl(cfd, NCRIO_KEY_WRAP, &kwrap);
+ if (geteuid() == 0 && data_size < 0) {
fprintf(stderr, "Error: %s:%d\n", __func__, __LINE__);
perror("ioctl(NCRIO_KEY_WRAP)");
return 1;
@@ -450,14 +457,12 @@ test_ncr_wrap_key(int cfd)
return 0;
}
- data_size = kwrap.io_size;
-
- if (kwrap.io_size != 24 || memcmp(data,
+ if (data_size != 24 || memcmp(data,
"\x1F\xA6\x8B\x0A\x81\x12\xB4\x47\xAE\xF3\x4B\xD8\xFB\x5A\x7B\x82\x9D\x3E\x86\x23\x71\xD2\xCF\xE5", 24) != 0) {
fprintf(stderr, "Wrapped data do not match.\n");
- fprintf(stderr, "Data[%d]: ",(int) kwrap.io_size);
- for(i=0;i<kwrap.io_size;i++)
+ fprintf(stderr, "Data[%d]: ",(int) data_size);
+ for(i=0;i<data_size;i++)
fprintf(stderr, "%.2x:", data[i]);
fprintf(stderr, "\n");
return 1;
@@ -478,14 +483,14 @@ test_ncr_wrap_key(int cfd)
return 1;
}
- memset(&kwrap, 0, sizeof(kwrap));
- kwrap.algorithm = NCR_WALG_AES_RFC3394;
- kwrap.keytowrap = key2;
- kwrap.key = key;
- kwrap.io = data;
- kwrap.io_size = data_size;
+ memset(&kunwrap, 0, sizeof(kunwrap));
+ kunwrap.algorithm = NCR_WALG_AES_RFC3394;
+ kunwrap.keytowrap = key2;
+ kunwrap.key = key;
+ kunwrap.io = data;
+ kunwrap.io_size = data_size;
- if (ioctl(cfd, NCRIO_KEY_UNWRAP, &kwrap)) {
+ if (ioctl(cfd, NCRIO_KEY_UNWRAP, &kunwrap)) {
perror("ioctl(NCRIO_KEY_UNWRAP)");
return 1;
}
@@ -543,7 +548,11 @@ test_ncr_wrap_key2(int cfd)
struct nlattr flags_head ALIGN_NL;
uint32_t flags ALIGN_NL;
} kimport;
- struct ncr_key_wrap_st kwrap;
+ struct __attribute__((packed)) {
+ struct ncr_key_wrap f;
+ struct nlattr algo_head ALIGN_NL;
+ uint32_t algo ALIGN_NL;
+ } kwrap;
uint8_t data[WRAPPED_KEY_DATA_SIZE];
/* test 1: generate a key in userspace import it
@@ -622,15 +631,18 @@ test_ncr_wrap_key2(int cfd)
}
/* now try wrapping key2 using key */
- memset(&kwrap, 0, sizeof(kwrap));
- kwrap.algorithm = NCR_WALG_AES_RFC3394;
- kwrap.keytowrap = key2;
- kwrap.key = key;
- kwrap.io = data;
- kwrap.io_size = sizeof(data);
+ memset(&kwrap.f, 0, sizeof(kwrap.f));
+ kwrap.f.input_size = sizeof(kwrap);
+ kwrap.f.wrapping_key = key;
+ kwrap.f.source_key = key2;
+ kwrap.f.buffer = data;
+ kwrap.f.buffer_size = sizeof(data);
+ kwrap.algo_head.nla_len = NLA_HDRLEN + sizeof(kwrap.algo);
+ kwrap.algo_head.nla_type = NCR_ATTR_WRAPPING_ALGORITHM;
+ kwrap.algo = NCR_WALG_AES_RFC3394;
ret = ioctl(cfd, NCRIO_KEY_WRAP, &kwrap);
- if (!ret) {
+ if (ret < 0) {
fprintf(stderr, "Error: %s:%d\n", __func__, __LINE__);
/* wrapping shouldn't have been allowed */
return 1;
diff --git a/examples/pk.c b/examples/pk.c
index fba53d5..f2a8a68 100644
--- a/examples/pk.c
+++ b/examples/pk.c
@@ -608,7 +608,12 @@ test_ncr_wrap_key3(int cfd)
struct nlattr flags_head ALIGN_NL;
uint32_t flags ALIGN_NL;
} kimport;
- struct ncr_key_wrap_st kwrap;
+ struct __attribute__((packed)) {
+ struct ncr_key_wrap f;
+ struct nlattr algo_head ALIGN_NL;
+ uint32_t algo ALIGN_NL;
+ } kwrap;
+ struct ncr_key_wrap_st kunwrap;
struct __attribute__((packed)) {
struct ncr_key_generate_pair f;
struct nlattr algo_head ALIGN_NL;
@@ -705,52 +710,58 @@ test_ncr_wrap_key3(int cfd)
}
/* now try wrapping key2 using key */
- memset(&kwrap, 0, sizeof(kwrap));
- kwrap.algorithm = NCR_WALG_AES_RFC5649;
- kwrap.keytowrap = pubkey;
- kwrap.key = key;
- kwrap.io = data;
- kwrap.io_size = sizeof(data);
+ memset(&kwrap.f, 0, sizeof(kwrap.f));
+ kwrap.f.input_size = sizeof(kwrap);
+ kwrap.f.wrapping_key = key;
+ kwrap.f.source_key = pubkey;
+ kwrap.f.buffer = data;
+ kwrap.f.buffer_size = sizeof(data);
+ kwrap.algo_head.nla_len = NLA_HDRLEN + sizeof(kwrap.algo);
+ kwrap.algo_head.nla_type = NCR_ATTR_WRAPPING_ALGORITHM;
+ kwrap.algo = NCR_WALG_AES_RFC5649;
ret = ioctl(cfd, NCRIO_KEY_WRAP, &kwrap);
- if (ret) {
+ if (ret < 0) {
fprintf(stderr, "Error[%d-%d]: %s:%d\n", i, sizes[i], __func__, __LINE__);
/* wrapping of public key should have been allowed! */
return 1;
}
/* now try wrapping private using key */
- memset(&kwrap, 0, sizeof(kwrap));
- kwrap.algorithm = NCR_WALG_AES_RFC5649;
- kwrap.keytowrap = privkey;
- kwrap.key = key;
- kwrap.io = data;
- kwrap.io_size = sizeof(data);
+ memset(&kwrap.f, 0, sizeof(kwrap.f));
+ kwrap.f.input_size = sizeof(kwrap);
+ kwrap.f.wrapping_key = key;
+ kwrap.f.source_key = privkey;
+ kwrap.f.buffer = data;
+ kwrap.f.buffer_size = sizeof(data);
+ kwrap.algo_head.nla_len = NLA_HDRLEN + sizeof(kwrap.algo);
+ kwrap.algo_head.nla_type = NCR_ATTR_WRAPPING_ALGORITHM;
+ kwrap.algo = NCR_WALG_AES_RFC5649;
ret = ioctl(cfd, NCRIO_KEY_WRAP, &kwrap);
- if (ret && i != 2) {
+ if (ret < 0 && i != 2) {
fprintf(stderr, "Error[%d-%d]: %s:%d\n", i, sizes[i], __func__, __LINE__);
/* wrapping should have been allowed */
return 1;
- } else if (ret == 0 && i == 2) {
+ } else if (ret >= 0 && i == 2) {
fprintf(stderr, "Error[%d-%d]: %s:%d\n", i, sizes[i], __func__, __LINE__);
/* wrapping shouldn't have been allowed */
return 1;
}
- if (ret == 0) {
- data_size = kwrap.io_size;
+ if (ret >= 0) {
+ data_size = ret;
/* try unwrapping */
- memset(&kwrap, 0, sizeof(kwrap));
- kwrap.algorithm = NCR_WALG_AES_RFC5649;
- kwrap.wrapped_key_algorithm = NCR_ALG_RSA;
- kwrap.keytowrap = privkey;
- kwrap.key = key;
- kwrap.io = data;
- kwrap.io_size = data_size;
-
- ret = ioctl(cfd, NCRIO_KEY_UNWRAP, &kwrap);
+ memset(&kunwrap, 0, sizeof(kunwrap));
+ kunwrap.algorithm = NCR_WALG_AES_RFC5649;
+ kunwrap.wrapped_key_algorithm = NCR_ALG_RSA;
+ kunwrap.keytowrap = privkey;
+ kunwrap.key = key;
+ kunwrap.io = data;
+ kunwrap.io_size = data_size;
+
+ ret = ioctl(cfd, NCRIO_KEY_UNWRAP, &kunwrap);
if (ret) {
fprintf(stderr, "Error[%d-%d]: %s:%d\n", i, sizes[i], __func__, __LINE__);
return 1;
diff --git a/ncr-int.h b/ncr-int.h
index ff7e08e..f49f2ef 100644
--- a/ncr-int.h
+++ b/ncr-int.h
@@ -153,7 +153,8 @@ int ncr_limits_add_and_check(uid_t uid, pid_t pid, limits_type_t type);
void ncr_limits_init(void);
void ncr_limits_deinit(void);
-int ncr_key_wrap(struct ncr_lists *lst, void __user* arg);
+int ncr_key_wrap(struct ncr_lists *lst, const struct ncr_key_wrap *wrap,
+ struct nlattr *tb[]);
int ncr_key_unwrap(struct ncr_lists *lst, void __user* arg);
int ncr_key_storage_wrap(struct ncr_lists *lst, void __user* arg);
int ncr_key_storage_unwrap(struct ncr_lists *lst, void __user* arg);
diff --git a/ncr-key-wrap.c b/ncr-key-wrap.c
index c6f394e..1cac811 100644
--- a/ncr-key-wrap.c
+++ b/ncr-key-wrap.c
@@ -29,6 +29,7 @@
#include <linux/random.h>
#include <linux/uaccess.h>
#include <linux/scatterlist.h>
+#include <net/netlink.h>
#include "ncr.h"
#include "ncr-int.h"
#include "cryptodev_int.h"
@@ -59,7 +60,7 @@ int i,j;
if (*output_size < (n+1)*8) {
err();
- return -EINVAL;
+ return -ERANGE;
}
memcpy(A, iv, 8);
@@ -502,21 +503,23 @@ int kek_level, wkey_level;
return 0;
}
-int ncr_key_wrap(struct ncr_lists *lst, void __user* arg)
+int ncr_key_wrap(struct ncr_lists *lst, const struct ncr_key_wrap *wrap,
+ struct nlattr *tb[])
{
-struct ncr_key_wrap_st wrap;
+const struct nlattr *nla;
struct key_item_st* wkey = NULL;
struct key_item_st* key = NULL;
void* data = NULL;
-size_t data_size;
+const void *iv;
+size_t data_size, iv_size;
int ret;
- if (unlikely(copy_from_user(&wrap, arg, sizeof(wrap)))) {
+ if (wrap->buffer_size < 0) {
err();
- return -EFAULT;
+ return -EINVAL;
}
- ret = ncr_key_item_get_read( &wkey, lst, wrap.keytowrap);
+ ret = ncr_key_item_get_read(&wkey, lst, wrap->source_key);
if (ret < 0) {
err();
return ret;
@@ -528,7 +531,7 @@ int ret;
goto fail;
}
- ret = ncr_key_item_get_read( &key, lst, wrap.key);
+ ret = ncr_key_item_get_read(&key, lst, wrap->wrapping_key);
if (ret < 0) {
err();
goto fail;
@@ -546,7 +549,7 @@ int ret;
goto fail;
}
- data_size = wrap.io_size;
+ data_size = wrap->buffer_size;
data = kmalloc(data_size, GFP_KERNEL);
if (data == NULL) {
err();
@@ -554,14 +557,29 @@ int ret;
goto fail;
}
- switch(wrap.algorithm) {
+ nla = tb[NCR_ATTR_IV];
+ if (nla != NULL) {
+ iv = nla_data(nla);
+ iv_size = nla_len(nla);
+ } else {
+ iv = NULL;
+ iv_size = 0;
+ }
+
+ nla = tb[NCR_ATTR_WRAPPING_ALGORITHM];
+ if (nla == NULL) {
+ err();
+ ret = -EINVAL;
+ goto fail;
+ }
+ switch (nla_get_u32(nla)) {
case NCR_WALG_AES_RFC3394:
- ret = wrap_aes(wkey, key, data, &data_size,
- wrap.params.params.cipher.iv, wrap.params.params.cipher.iv_size);
+ ret = wrap_aes(wkey, key, data, &data_size, iv,
+ iv_size);
break;
case NCR_WALG_AES_RFC5649:
- ret = wrap_aes_rfc5649(wkey, key, data, &data_size,
- wrap.params.params.cipher.iv, wrap.params.params.cipher.iv_size);
+ ret = wrap_aes_rfc5649(wkey, key, data, &data_size, iv,
+ iv_size);
break;
default:
err();
@@ -573,18 +591,13 @@ int ret;
goto fail;
}
- ret = copy_to_user(wrap.io, data, data_size);
+ ret = copy_to_user(wrap->buffer, data, data_size);
if (unlikely(ret)) {
ret = -EFAULT;
goto fail;
}
- wrap.io_size = data_size;
-
- ret = copy_to_user(arg, &wrap, sizeof(wrap));
- if (unlikely(ret)) {
- ret = -EFAULT;
- }
+ ret = data_size;
fail:
if (wkey != NULL) _ncr_key_item_put(wkey);
diff --git a/ncr.c b/ncr.c
index fb8645c..202ddc9 100644
--- a/ncr.c
+++ b/ncr.c
@@ -178,8 +178,7 @@ ncr_ioctl(struct ncr_lists *lst, unsigned int cmd, unsigned long arg_)
}
return ncr_key_deinit(lst, key);
}
- case NCRIO_KEY_WRAP:
- return ncr_key_wrap(lst, arg);
+ CASE_NO_OUTPUT(NCRIO_KEY_WRAP, ncr_key_wrap, ncr_key_wrap);
case NCRIO_KEY_UNWRAP:
return ncr_key_unwrap(lst, arg);
case NCRIO_KEY_STORAGE_WRAP:
@@ -240,6 +239,25 @@ static void convert_ncr_key_import(struct ncr_key_import *new,
new->data_size = old->data_size;
}
+struct compat_ncr_key_wrap {
+ __u32 input_size, output_size;
+ ncr_key_t wrapping_key;
+ ncr_key_t source_key;
+ compat_uptr_t buffer;
+ compat_int_t buffer_size;
+ __NL_ATTRIBUTES;
+};
+#define COMPAT_NCRIO_KEY_WRAP _IOWR('c', 250, struct compat_ncr_key_wrap)
+
+static void convert_ncr_key_wrap(struct ncr_key_wrap *new,
+ const struct compat_ncr_key_wrap *old)
+{
+ new->wrapping_key = old->wrapping_key;
+ new->source_key = old->source_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_)
{
@@ -277,6 +295,7 @@ ncr_compat_ioctl(struct ncr_lists *lst, unsigned int cmd, unsigned long arg_)
CASE_NO_OUTPUT(COMPAT_NCRIO_KEY_EXPORT, ncr_key_export, ncr_key_export);
CASE_NO_OUTPUT(COMPAT_NCRIO_KEY_IMPORT, ncr_key_import, ncr_key_import);
+ CASE_NO_OUTPUT(COMPAT_NCRIO_KEY_WRAP, ncr_key_wrap, ncr_key_wrap);
default:
return -EINVAL;
#undef CASE_NO_OUTPUT
diff --git a/ncr.h b/ncr.h
index 81c7621..508665c 100644
--- a/ncr.h
+++ b/ncr.h
@@ -33,9 +33,11 @@ enum {
/* FIXME: Use NLA_STRING for this, later */
NCR_ATTR_ALGORITHM, /* NLA_U32 - ncr_algorithm_t */
NCR_ATTR_DERIVATION_ALGORITHM, /* NLA_U32 - ncr_algorithm_t */
+ NCR_ATTR_WRAPPING_ALGORITHM, /* NLA_U32 - ncr_wrap_algorithm_t */
NCR_ATTR_KEY_FLAGS, /* NLA_U32 - NCR_KEY_FLAG_* */
NCR_ATTR_KEY_ID, /* NLA_BINARY */
NCR_ATTR_KEY_TYPE, /* NLA_U32 - ncr_key_type_t */
+ NCR_ATTR_IV, /* NLA_BINARY */
NCR_ATTR_SECRET_KEY_BITS, /* NLA_U32 */
NCR_ATTR_RSA_MODULUS_BITS, /* NLA_U32 */
NCR_ATTR_RSA_E, /* NLA_BINARY */
@@ -218,6 +220,15 @@ struct ncr_key_export {
/* Key wrap ioctls
*/
+struct ncr_key_wrap {
+ __u32 input_size, output_size;
+ ncr_key_t wrapping_key;
+ ncr_key_t source_key;
+ void __user *buffer;
+ int buffer_size;
+ __NL_ATTRIBUTES;
+};
+
struct ncr_key_wrap_st {
ncr_wrap_algorithm_t algorithm;
@@ -237,7 +248,7 @@ struct ncr_key_wrap_st {
__kernel_size_t io_size;
};
-#define NCRIO_KEY_WRAP _IOWR ('c', 250, struct ncr_key_wrap_st)
+#define NCRIO_KEY_WRAP _IOWR('c', 250, struct ncr_key_wrap)
#define NCRIO_KEY_UNWRAP _IOR ('c', 251, struct ncr_key_wrap_st)
/* Internal ops */
diff --git a/utils.c b/utils.c
index fe57c5a..1ae66fc 100644
--- a/utils.c
+++ b/utils.c
@@ -31,9 +31,11 @@
static const struct nla_policy ncr_attr_policy[NCR_ATTR_MAX + 1] = {
[NCR_ATTR_ALGORITHM] = { NLA_U32, 0 },
[NCR_ATTR_DERIVATION_ALGORITHM] = { NLA_U32, 0 },
+ [NCR_ATTR_WRAPPING_ALGORITHM] = { NLA_U32, 0 },
[NCR_ATTR_KEY_FLAGS] = { NLA_U32, 0 },
[NCR_ATTR_KEY_ID] = { NLA_BINARY, 0 },
[NCR_ATTR_KEY_TYPE] = { NLA_U32, 0 },
+ [NCR_ATTR_IV] = { NLA_BINARY, 0 },
[NCR_ATTR_SECRET_KEY_BITS] = { NLA_U32, 0 },
[NCR_ATTR_RSA_MODULUS_BITS] = { NLA_U32, 0 },
[NCR_ATTR_RSA_E] = { NLA_BINARY, 0 },