diff options
author | David Howells <dhowells@redhat.com> | 2006-06-26 03:24:50 -0400 |
---|---|---|
committer | Linus Torvalds <torvalds@g5.osdl.org> | 2006-06-26 12:58:18 -0400 |
commit | 7e047ef5fe2d52e83020e856b1bf2556a6a2ce98 (patch) | |
tree | 97656e2c56a27be9d1da451dde627b693b8643f2 /security/keys/process_keys.c | |
parent | f116629d03655adaf7832b93b03c99391d09d4a7 (diff) |
[PATCH] keys: sort out key quota system
Add the ability for key creation to overrun the user's quota in some
circumstances - notably when a session keyring is created and assigned to a
process that didn't previously have one.
This means it's still possible to log in, should PAM require the creation of a
new session keyring, and fix an overburdened key quota.
Signed-off-by: David Howells <dhowells@redhat.com>
Signed-off-by: Andrew Morton <akpm@osdl.org>
Signed-off-by: Linus Torvalds <torvalds@osdl.org>
Diffstat (limited to 'security/keys/process_keys.c')
-rw-r--r-- | security/keys/process_keys.c | 24 |
1 files changed, 17 insertions, 7 deletions
diff --git a/security/keys/process_keys.c b/security/keys/process_keys.c index 4d9825f9962c..32150cf7c37f 100644 --- a/security/keys/process_keys.c +++ b/security/keys/process_keys.c | |||
@@ -77,7 +77,8 @@ int alloc_uid_keyring(struct user_struct *user, | |||
77 | /* concoct a default session keyring */ | 77 | /* concoct a default session keyring */ |
78 | sprintf(buf, "_uid_ses.%u", user->uid); | 78 | sprintf(buf, "_uid_ses.%u", user->uid); |
79 | 79 | ||
80 | session_keyring = keyring_alloc(buf, user->uid, (gid_t) -1, ctx, 0, NULL); | 80 | session_keyring = keyring_alloc(buf, user->uid, (gid_t) -1, ctx, |
81 | KEY_ALLOC_IN_QUOTA, NULL); | ||
81 | if (IS_ERR(session_keyring)) { | 82 | if (IS_ERR(session_keyring)) { |
82 | ret = PTR_ERR(session_keyring); | 83 | ret = PTR_ERR(session_keyring); |
83 | goto error; | 84 | goto error; |
@@ -87,8 +88,8 @@ int alloc_uid_keyring(struct user_struct *user, | |||
87 | * keyring */ | 88 | * keyring */ |
88 | sprintf(buf, "_uid.%u", user->uid); | 89 | sprintf(buf, "_uid.%u", user->uid); |
89 | 90 | ||
90 | uid_keyring = keyring_alloc(buf, user->uid, (gid_t) -1, ctx, 0, | 91 | uid_keyring = keyring_alloc(buf, user->uid, (gid_t) -1, ctx, |
91 | session_keyring); | 92 | KEY_ALLOC_IN_QUOTA, session_keyring); |
92 | if (IS_ERR(uid_keyring)) { | 93 | if (IS_ERR(uid_keyring)) { |
93 | key_put(session_keyring); | 94 | key_put(session_keyring); |
94 | ret = PTR_ERR(uid_keyring); | 95 | ret = PTR_ERR(uid_keyring); |
@@ -144,7 +145,8 @@ int install_thread_keyring(struct task_struct *tsk) | |||
144 | 145 | ||
145 | sprintf(buf, "_tid.%u", tsk->pid); | 146 | sprintf(buf, "_tid.%u", tsk->pid); |
146 | 147 | ||
147 | keyring = keyring_alloc(buf, tsk->uid, tsk->gid, tsk, 1, NULL); | 148 | keyring = keyring_alloc(buf, tsk->uid, tsk->gid, tsk, |
149 | KEY_ALLOC_QUOTA_OVERRUN, NULL); | ||
148 | if (IS_ERR(keyring)) { | 150 | if (IS_ERR(keyring)) { |
149 | ret = PTR_ERR(keyring); | 151 | ret = PTR_ERR(keyring); |
150 | goto error; | 152 | goto error; |
@@ -178,7 +180,8 @@ int install_process_keyring(struct task_struct *tsk) | |||
178 | if (!tsk->signal->process_keyring) { | 180 | if (!tsk->signal->process_keyring) { |
179 | sprintf(buf, "_pid.%u", tsk->tgid); | 181 | sprintf(buf, "_pid.%u", tsk->tgid); |
180 | 182 | ||
181 | keyring = keyring_alloc(buf, tsk->uid, tsk->gid, tsk, 1, NULL); | 183 | keyring = keyring_alloc(buf, tsk->uid, tsk->gid, tsk, |
184 | KEY_ALLOC_QUOTA_OVERRUN, NULL); | ||
182 | if (IS_ERR(keyring)) { | 185 | if (IS_ERR(keyring)) { |
183 | ret = PTR_ERR(keyring); | 186 | ret = PTR_ERR(keyring); |
184 | goto error; | 187 | goto error; |
@@ -209,6 +212,7 @@ error: | |||
209 | static int install_session_keyring(struct task_struct *tsk, | 212 | static int install_session_keyring(struct task_struct *tsk, |
210 | struct key *keyring) | 213 | struct key *keyring) |
211 | { | 214 | { |
215 | unsigned long flags; | ||
212 | struct key *old; | 216 | struct key *old; |
213 | char buf[20]; | 217 | char buf[20]; |
214 | 218 | ||
@@ -218,7 +222,12 @@ static int install_session_keyring(struct task_struct *tsk, | |||
218 | if (!keyring) { | 222 | if (!keyring) { |
219 | sprintf(buf, "_ses.%u", tsk->tgid); | 223 | sprintf(buf, "_ses.%u", tsk->tgid); |
220 | 224 | ||
221 | keyring = keyring_alloc(buf, tsk->uid, tsk->gid, tsk, 1, NULL); | 225 | flags = KEY_ALLOC_QUOTA_OVERRUN; |
226 | if (tsk->signal->session_keyring) | ||
227 | flags = KEY_ALLOC_IN_QUOTA; | ||
228 | |||
229 | keyring = keyring_alloc(buf, tsk->uid, tsk->gid, tsk, | ||
230 | flags, NULL); | ||
222 | if (IS_ERR(keyring)) | 231 | if (IS_ERR(keyring)) |
223 | return PTR_ERR(keyring); | 232 | return PTR_ERR(keyring); |
224 | } | 233 | } |
@@ -728,7 +737,8 @@ long join_session_keyring(const char *name) | |||
728 | keyring = find_keyring_by_name(name, 0); | 737 | keyring = find_keyring_by_name(name, 0); |
729 | if (PTR_ERR(keyring) == -ENOKEY) { | 738 | if (PTR_ERR(keyring) == -ENOKEY) { |
730 | /* not found - try and create a new one */ | 739 | /* not found - try and create a new one */ |
731 | keyring = keyring_alloc(name, tsk->uid, tsk->gid, tsk, 0, NULL); | 740 | keyring = keyring_alloc(name, tsk->uid, tsk->gid, tsk, |
741 | KEY_ALLOC_IN_QUOTA, NULL); | ||
732 | if (IS_ERR(keyring)) { | 742 | if (IS_ERR(keyring)) { |
733 | ret = PTR_ERR(keyring); | 743 | ret = PTR_ERR(keyring); |
734 | goto error2; | 744 | goto error2; |