Skip to content

Commit 146aa8b

Browse files
committed
KEYS: Merge the type-specific data with the payload data
Merge the type-specific data with the payload data into one four-word chunk as it seems pointless to keep them separate. Use user_key_payload() for accessing the payloads of overloaded user-defined keys. Signed-off-by: David Howells <dhowells@redhat.com> cc: linux-cifs@vger.kernel.org cc: ecryptfs@vger.kernel.org cc: linux-ext4@vger.kernel.org cc: linux-f2fs-devel@lists.sourceforge.net cc: linux-nfs@vger.kernel.org cc: ceph-devel@vger.kernel.org cc: linux-ima-devel@lists.sourceforge.net
1 parent 4adc605 commit 146aa8b

Some content is hidden

Large Commits have some content hidden by default. Use the searchbox below for content that may be hidden.

49 files changed

+286
-230
lines changed

Documentation/crypto/asymmetric-keys.txt

Lines changed: 14 additions & 13 deletions
Original file line numberDiff line numberDiff line change
@@ -186,7 +186,7 @@ and looks like the following:
186186
const struct public_key_signature *sig);
187187
};
188188

189-
Asymmetric keys point to this with their type_data[0] member.
189+
Asymmetric keys point to this with their payload[asym_subtype] member.
190190

191191
The owner and name fields should be set to the owning module and the name of
192192
the subtype. Currently, the name is only used for print statements.
@@ -269,8 +269,7 @@ mandatory:
269269

270270
struct key_preparsed_payload {
271271
char *description;
272-
void *type_data[2];
273-
void *payload;
272+
void *payload[4];
274273
const void *data;
275274
size_t datalen;
276275
size_t quotalen;
@@ -283,16 +282,18 @@ mandatory:
283282
not theirs.
284283

285284
If the parser is happy with the blob, it should propose a description for
286-
the key and attach it to ->description, ->type_data[0] should be set to
287-
point to the subtype to be used, ->payload should be set to point to the
288-
initialised data for that subtype, ->type_data[1] should point to a hex
289-
fingerprint and quotalen should be updated to indicate how much quota this
290-
key should account for.
291-
292-
When clearing up, the data attached to ->type_data[1] and ->description
293-
will be kfree()'d and the data attached to ->payload will be passed to the
294-
subtype's ->destroy() method to be disposed of. A module reference for
295-
the subtype pointed to by ->type_data[0] will be put.
285+
the key and attach it to ->description, ->payload[asym_subtype] should be
286+
set to point to the subtype to be used, ->payload[asym_crypto] should be
287+
set to point to the initialised data for that subtype,
288+
->payload[asym_key_ids] should point to one or more hex fingerprints and
289+
quotalen should be updated to indicate how much quota this key should
290+
account for.
291+
292+
When clearing up, the data attached to ->payload[asym_key_ids] and
293+
->description will be kfree()'d and the data attached to
294+
->payload[asm_crypto] will be passed to the subtype's ->destroy() method
295+
to be disposed of. A module reference for the subtype pointed to by
296+
->payload[asym_subtype] will be put.
296297

297298

298299
If the data format is not recognised, -EBADMSG should be returned. If it

Documentation/security/keys.txt

Lines changed: 25 additions & 16 deletions
Original file line numberDiff line numberDiff line change
@@ -1049,12 +1049,12 @@ search a specific keyring, so using keyrings in this way is of limited utility.
10491049
NOTES ON ACCESSING PAYLOAD CONTENTS
10501050
===================================
10511051

1052-
The simplest payload is just a number in key->payload.value. In this case,
1053-
there's no need to indulge in RCU or locking when accessing the payload.
1052+
The simplest payload is just data stored in key->payload directly. In this
1053+
case, there's no need to indulge in RCU or locking when accessing the payload.
10541054

1055-
More complex payload contents must be allocated and a pointer to them set in
1056-
key->payload.data. One of the following ways must be selected to access the
1057-
data:
1055+
More complex payload contents must be allocated and pointers to them set in the
1056+
key->payload.data[] array. One of the following ways must be selected to
1057+
access the data:
10581058

10591059
(1) Unmodifiable key type.
10601060

@@ -1092,6 +1092,13 @@ data:
10921092
the payload. key->datalen cannot be relied upon to be consistent with the
10931093
payload just dereferenced if the key's semaphore is not held.
10941094

1095+
Note that key->payload.data[0] has a shadow that is marked for __rcu
1096+
usage. This is called key->payload.rcu_data0. The following accessors
1097+
wrap the RCU calls to this element:
1098+
1099+
rcu_assign_keypointer(struct key *key, void *data);
1100+
void *rcu_dereference_key(struct key *key);
1101+
10951102

10961103
===================
10971104
DEFINING A KEY TYPE
@@ -1143,8 +1150,7 @@ The structure has a number of fields, some of which are mandatory:
11431150

11441151
struct key_preparsed_payload {
11451152
char *description;
1146-
void *type_data[2];
1147-
void *payload;
1153+
union key_payload payload;
11481154
const void *data;
11491155
size_t datalen;
11501156
size_t quotalen;
@@ -1160,10 +1166,9 @@ The structure has a number of fields, some of which are mandatory:
11601166
attached as a string to the description field. This will be used for the
11611167
key description if the caller of add_key() passes NULL or "".
11621168

1163-
The method can attach anything it likes to type_data[] and payload. These
1164-
are merely passed along to the instantiate() or update() operations. If
1165-
set, the expiry time will be applied to the key if it is instantiated from
1166-
this data.
1169+
The method can attach anything it likes to payload. This is merely passed
1170+
along to the instantiate() or update() operations. If set, the expiry
1171+
time will be applied to the key if it is instantiated from this data.
11671172

11681173
The method should return 0 if successful or a negative error code
11691174
otherwise.
@@ -1172,11 +1177,10 @@ The structure has a number of fields, some of which are mandatory:
11721177
(*) void (*free_preparse)(struct key_preparsed_payload *prep);
11731178

11741179
This method is only required if the preparse() method is provided,
1175-
otherwise it is unused. It cleans up anything attached to the
1176-
description, type_data and payload fields of the key_preparsed_payload
1177-
struct as filled in by the preparse() method. It will always be called
1178-
after preparse() returns successfully, even if instantiate() or update()
1179-
succeed.
1180+
otherwise it is unused. It cleans up anything attached to the description
1181+
and payload fields of the key_preparsed_payload struct as filled in by the
1182+
preparse() method. It will always be called after preparse() returns
1183+
successfully, even if instantiate() or update() succeed.
11801184

11811185

11821186
(*) int (*instantiate)(struct key *key, struct key_preparsed_payload *prep);
@@ -1197,6 +1201,11 @@ The structure has a number of fields, some of which are mandatory:
11971201

11981202
It is safe to sleep in this method.
11991203

1204+
generic_key_instantiate() is provided to simply copy the data from
1205+
prep->payload.data[] to key->payload.data[], with RCU-safe assignment on
1206+
the first element. It will then clear prep->payload.data[] so that the
1207+
free_preparse method doesn't release the data.
1208+
12001209

12011210
(*) int (*update)(struct key *key, const void *data, size_t datalen);
12021211

crypto/asymmetric_keys/asymmetric_keys.h

Lines changed: 0 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -14,8 +14,3 @@ extern struct asymmetric_key_id *asymmetric_key_hex_to_key_id(const char *id);
1414
extern int __asymmetric_key_hex_to_key_id(const char *id,
1515
struct asymmetric_key_id *match_id,
1616
size_t hexlen);
17-
static inline
18-
const struct asymmetric_key_ids *asymmetric_key_ids(const struct key *key)
19-
{
20-
return key->type_data.p[1];
21-
}

crypto/asymmetric_keys/asymmetric_type.c

Lines changed: 26 additions & 18 deletions
Original file line numberDiff line numberDiff line change
@@ -306,26 +306,35 @@ static int asymmetric_key_preparse(struct key_preparsed_payload *prep)
306306
return ret;
307307
}
308308

309+
/*
310+
* Clean up the key ID list
311+
*/
312+
static void asymmetric_key_free_kids(struct asymmetric_key_ids *kids)
313+
{
314+
int i;
315+
316+
if (kids) {
317+
for (i = 0; i < ARRAY_SIZE(kids->id); i++)
318+
kfree(kids->id[i]);
319+
kfree(kids);
320+
}
321+
}
322+
309323
/*
310324
* Clean up the preparse data
311325
*/
312326
static void asymmetric_key_free_preparse(struct key_preparsed_payload *prep)
313327
{
314-
struct asymmetric_key_subtype *subtype = prep->type_data[0];
315-
struct asymmetric_key_ids *kids = prep->type_data[1];
316-
int i;
328+
struct asymmetric_key_subtype *subtype = prep->payload.data[asym_subtype];
329+
struct asymmetric_key_ids *kids = prep->payload.data[asym_key_ids];
317330

318331
pr_devel("==>%s()\n", __func__);
319332

320333
if (subtype) {
321-
subtype->destroy(prep->payload[0]);
334+
subtype->destroy(prep->payload.data[asym_crypto]);
322335
module_put(subtype->owner);
323336
}
324-
if (kids) {
325-
for (i = 0; i < ARRAY_SIZE(kids->id); i++)
326-
kfree(kids->id[i]);
327-
kfree(kids);
328-
}
337+
asymmetric_key_free_kids(kids);
329338
kfree(prep->description);
330339
}
331340

@@ -335,20 +344,19 @@ static void asymmetric_key_free_preparse(struct key_preparsed_payload *prep)
335344
static void asymmetric_key_destroy(struct key *key)
336345
{
337346
struct asymmetric_key_subtype *subtype = asymmetric_key_subtype(key);
338-
struct asymmetric_key_ids *kids = key->type_data.p[1];
347+
struct asymmetric_key_ids *kids = key->payload.data[asym_key_ids];
348+
void *data = key->payload.data[asym_crypto];
349+
350+
key->payload.data[asym_crypto] = NULL;
351+
key->payload.data[asym_subtype] = NULL;
352+
key->payload.data[asym_key_ids] = NULL;
339353

340354
if (subtype) {
341-
subtype->destroy(key->payload.data);
355+
subtype->destroy(data);
342356
module_put(subtype->owner);
343-
key->type_data.p[0] = NULL;
344357
}
345358

346-
if (kids) {
347-
kfree(kids->id[0]);
348-
kfree(kids->id[1]);
349-
kfree(kids);
350-
key->type_data.p[1] = NULL;
351-
}
359+
asymmetric_key_free_kids(kids);
352360
}
353361

354362
struct key_type key_type_asymmetric = {

crypto/asymmetric_keys/public_key.c

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -49,7 +49,7 @@ EXPORT_SYMBOL_GPL(pkey_id_type_name);
4949
static void public_key_describe(const struct key *asymmetric_key,
5050
struct seq_file *m)
5151
{
52-
struct public_key *key = asymmetric_key->payload.data;
52+
struct public_key *key = asymmetric_key->payload.data[asym_crypto];
5353

5454
if (key)
5555
seq_printf(m, "%s.%s",
@@ -112,7 +112,7 @@ EXPORT_SYMBOL_GPL(public_key_verify_signature);
112112
static int public_key_verify_signature_2(const struct key *key,
113113
const struct public_key_signature *sig)
114114
{
115-
const struct public_key *pk = key->payload.data;
115+
const struct public_key *pk = key->payload.data[asym_crypto];
116116
return public_key_verify_signature(pk, sig);
117117
}
118118

crypto/asymmetric_keys/signature.c

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -37,7 +37,7 @@ int verify_signature(const struct key *key,
3737
return -EINVAL;
3838
subtype = asymmetric_key_subtype(key);
3939
if (!subtype ||
40-
!key->payload.data)
40+
!key->payload.data[0])
4141
return -EINVAL;
4242
if (!subtype->verify_signature)
4343
return -ENOTSUPP;

crypto/asymmetric_keys/x509_parser.h

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -11,6 +11,7 @@
1111

1212
#include <linux/time.h>
1313
#include <crypto/public_key.h>
14+
#include <keys/asymmetric-type.h>
1415

1516
struct x509_certificate {
1617
struct x509_certificate *next;

crypto/asymmetric_keys/x509_public_key.c

Lines changed: 5 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -266,7 +266,8 @@ static int x509_validate_trust(struct x509_certificate *cert,
266266
if (!IS_ERR(key)) {
267267
if (!use_builtin_keys
268268
|| test_bit(KEY_FLAG_BUILTIN, &key->flags))
269-
ret = x509_check_signature(key->payload.data, cert);
269+
ret = x509_check_signature(key->payload.data[asym_crypto],
270+
cert);
270271
key_put(key);
271272
}
272273
return ret;
@@ -352,9 +353,9 @@ static int x509_key_preparse(struct key_preparsed_payload *prep)
352353

353354
/* We're pinning the module by being linked against it */
354355
__module_get(public_key_subtype.owner);
355-
prep->type_data[0] = &public_key_subtype;
356-
prep->type_data[1] = kids;
357-
prep->payload[0] = cert->pub;
356+
prep->payload.data[asym_subtype] = &public_key_subtype;
357+
prep->payload.data[asym_key_ids] = kids;
358+
prep->payload.data[asym_crypto] = cert->pub;
358359
prep->description = desc;
359360
prep->quotalen = 100;
360361

fs/cifs/cifs_spnego.c

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -42,7 +42,7 @@ cifs_spnego_key_instantiate(struct key *key, struct key_preparsed_payload *prep)
4242
goto error;
4343

4444
/* attach the data */
45-
key->payload.data = payload;
45+
key->payload.data[0] = payload;
4646
ret = 0;
4747

4848
error:
@@ -52,7 +52,7 @@ cifs_spnego_key_instantiate(struct key *key, struct key_preparsed_payload *prep)
5252
static void
5353
cifs_spnego_key_destroy(struct key *key)
5454
{
55-
kfree(key->payload.data);
55+
kfree(key->payload.data[0]);
5656
}
5757

5858

@@ -167,7 +167,7 @@ cifs_get_spnego_key(struct cifs_ses *sesInfo)
167167

168168
#ifdef CONFIG_CIFS_DEBUG2
169169
if (cifsFYI && !IS_ERR(spnego_key)) {
170-
struct cifs_spnego_msg *msg = spnego_key->payload.data;
170+
struct cifs_spnego_msg *msg = spnego_key->payload.data[0];
171171
cifs_dump_mem("SPNEGO reply blob:", msg->data, min(1024U,
172172
msg->secblob_len + msg->sesskey_len));
173173
}

fs/cifs/cifsacl.c

Lines changed: 12 additions & 13 deletions
Original file line numberDiff line numberDiff line change
@@ -58,16 +58,15 @@ cifs_idmap_key_instantiate(struct key *key, struct key_preparsed_payload *prep)
5858
* dereference payload.data!
5959
*/
6060
if (prep->datalen <= sizeof(key->payload)) {
61-
key->payload.value = 0;
62-
memcpy(&key->payload.value, prep->data, prep->datalen);
63-
key->datalen = prep->datalen;
64-
return 0;
61+
key->payload.data[0] = NULL;
62+
memcpy(&key->payload, prep->data, prep->datalen);
63+
} else {
64+
payload = kmemdup(prep->data, prep->datalen, GFP_KERNEL);
65+
if (!payload)
66+
return -ENOMEM;
67+
key->payload.data[0] = payload;
6568
}
66-
payload = kmemdup(prep->data, prep->datalen, GFP_KERNEL);
67-
if (!payload)
68-
return -ENOMEM;
6969

70-
key->payload.data = payload;
7170
key->datalen = prep->datalen;
7271
return 0;
7372
}
@@ -76,7 +75,7 @@ static inline void
7675
cifs_idmap_key_destroy(struct key *key)
7776
{
7877
if (key->datalen > sizeof(key->payload))
79-
kfree(key->payload.data);
78+
kfree(key->payload.data[0]);
8079
}
8180

8281
static struct key_type cifs_idmap_key_type = {
@@ -233,8 +232,8 @@ id_to_sid(unsigned int cid, uint sidtype, struct cifs_sid *ssid)
233232
* it could be.
234233
*/
235234
ksid = sidkey->datalen <= sizeof(sidkey->payload) ?
236-
(struct cifs_sid *)&sidkey->payload.value :
237-
(struct cifs_sid *)sidkey->payload.data;
235+
(struct cifs_sid *)&sidkey->payload :
236+
(struct cifs_sid *)sidkey->payload.data[0];
238237

239238
ksid_size = CIFS_SID_BASE_SIZE + (ksid->num_subauth * sizeof(__le32));
240239
if (ksid_size > sidkey->datalen) {
@@ -307,14 +306,14 @@ sid_to_id(struct cifs_sb_info *cifs_sb, struct cifs_sid *psid,
307306
if (sidtype == SIDOWNER) {
308307
kuid_t uid;
309308
uid_t id;
310-
memcpy(&id, &sidkey->payload.value, sizeof(uid_t));
309+
memcpy(&id, &sidkey->payload.data[0], sizeof(uid_t));
311310
uid = make_kuid(&init_user_ns, id);
312311
if (uid_valid(uid))
313312
fuid = uid;
314313
} else {
315314
kgid_t gid;
316315
gid_t id;
317-
memcpy(&id, &sidkey->payload.value, sizeof(gid_t));
316+
memcpy(&id, &sidkey->payload.data[0], sizeof(gid_t));
318317
gid = make_kgid(&init_user_ns, id);
319318
if (gid_valid(gid))
320319
fgid = gid;

0 commit comments

Comments
 (0)