aboutsummaryrefslogtreecommitdiffstats
path: root/security/tomoyo/file.c
diff options
context:
space:
mode:
Diffstat (limited to 'security/tomoyo/file.c')
-rw-r--r--security/tomoyo/file.c107
1 files changed, 38 insertions, 69 deletions
diff --git a/security/tomoyo/file.c b/security/tomoyo/file.c
index 09436d11f298..8015719926d5 100644
--- a/security/tomoyo/file.c
+++ b/security/tomoyo/file.c
@@ -253,6 +253,15 @@ static int tomoyo_update_path_acl(const u8 type, const char *filename,
253 */ 253 */
254LIST_HEAD(tomoyo_globally_readable_list); 254LIST_HEAD(tomoyo_globally_readable_list);
255 255
256static bool tomoyo_same_globally_readable(const struct tomoyo_acl_head *a,
257 const struct tomoyo_acl_head *b)
258{
259 return container_of(a, struct tomoyo_globally_readable_file_entry,
260 head)->filename ==
261 container_of(b, struct tomoyo_globally_readable_file_entry,
262 head)->filename;
263}
264
256/** 265/**
257 * tomoyo_update_globally_readable_entry - Update "struct tomoyo_globally_readable_file_entry" list. 266 * tomoyo_update_globally_readable_entry - Update "struct tomoyo_globally_readable_file_entry" list.
258 * 267 *
@@ -266,36 +275,17 @@ LIST_HEAD(tomoyo_globally_readable_list);
266static int tomoyo_update_globally_readable_entry(const char *filename, 275static int tomoyo_update_globally_readable_entry(const char *filename,
267 const bool is_delete) 276 const bool is_delete)
268{ 277{
269 struct tomoyo_globally_readable_file_entry *ptr;
270 struct tomoyo_globally_readable_file_entry e = { }; 278 struct tomoyo_globally_readable_file_entry e = { };
271 int error = is_delete ? -ENOENT : -ENOMEM; 279 int error;
272 280
273 if (!tomoyo_is_correct_word(filename)) 281 if (!tomoyo_is_correct_word(filename))
274 return -EINVAL; 282 return -EINVAL;
275 e.filename = tomoyo_get_name(filename); 283 e.filename = tomoyo_get_name(filename);
276 if (!e.filename) 284 if (!e.filename)
277 return -ENOMEM; 285 return -ENOMEM;
278 if (mutex_lock_interruptible(&tomoyo_policy_lock)) 286 error = tomoyo_update_policy(&e.head, sizeof(e), is_delete,
279 goto out; 287 &tomoyo_globally_readable_list,
280 list_for_each_entry_rcu(ptr, &tomoyo_globally_readable_list, 288 tomoyo_same_globally_readable);
281 head.list) {
282 if (ptr->filename != e.filename)
283 continue;
284 ptr->head.is_deleted = is_delete;
285 error = 0;
286 break;
287 }
288 if (!is_delete && error) {
289 struct tomoyo_globally_readable_file_entry *entry =
290 tomoyo_commit_ok(&e, sizeof(e));
291 if (entry) {
292 list_add_tail_rcu(&entry->head.list,
293 &tomoyo_globally_readable_list);
294 error = 0;
295 }
296 }
297 mutex_unlock(&tomoyo_policy_lock);
298 out:
299 tomoyo_put_name(e.filename); 289 tomoyo_put_name(e.filename);
300 return error; 290 return error;
301} 291}
@@ -402,6 +392,13 @@ bool tomoyo_read_globally_readable_policy(struct tomoyo_io_buffer *head)
402 */ 392 */
403LIST_HEAD(tomoyo_pattern_list); 393LIST_HEAD(tomoyo_pattern_list);
404 394
395static bool tomoyo_same_pattern(const struct tomoyo_acl_head *a,
396 const struct tomoyo_acl_head *b)
397{
398 return container_of(a, struct tomoyo_pattern_entry, head)->pattern ==
399 container_of(b, struct tomoyo_pattern_entry, head)->pattern;
400}
401
405/** 402/**
406 * tomoyo_update_file_pattern_entry - Update "struct tomoyo_pattern_entry" list. 403 * tomoyo_update_file_pattern_entry - Update "struct tomoyo_pattern_entry" list.
407 * 404 *
@@ -415,35 +412,17 @@ LIST_HEAD(tomoyo_pattern_list);
415static int tomoyo_update_file_pattern_entry(const char *pattern, 412static int tomoyo_update_file_pattern_entry(const char *pattern,
416 const bool is_delete) 413 const bool is_delete)
417{ 414{
418 struct tomoyo_pattern_entry *ptr;
419 struct tomoyo_pattern_entry e = { }; 415 struct tomoyo_pattern_entry e = { };
420 int error = is_delete ? -ENOENT : -ENOMEM; 416 int error;
421 417
422 if (!tomoyo_is_correct_word(pattern)) 418 if (!tomoyo_is_correct_word(pattern))
423 return -EINVAL; 419 return -EINVAL;
424 e.pattern = tomoyo_get_name(pattern); 420 e.pattern = tomoyo_get_name(pattern);
425 if (!e.pattern) 421 if (!e.pattern)
426 return error; 422 return -ENOMEM;
427 if (mutex_lock_interruptible(&tomoyo_policy_lock)) 423 error = tomoyo_update_policy(&e.head, sizeof(e), is_delete,
428 goto out; 424 &tomoyo_pattern_list,
429 list_for_each_entry_rcu(ptr, &tomoyo_pattern_list, head.list) { 425 tomoyo_same_pattern);
430 if (e.pattern != ptr->pattern)
431 continue;
432 ptr->head.is_deleted = is_delete;
433 error = 0;
434 break;
435 }
436 if (!is_delete && error) {
437 struct tomoyo_pattern_entry *entry =
438 tomoyo_commit_ok(&e, sizeof(e));
439 if (entry) {
440 list_add_tail_rcu(&entry->head.list,
441 &tomoyo_pattern_list);
442 error = 0;
443 }
444 }
445 mutex_unlock(&tomoyo_policy_lock);
446 out:
447 tomoyo_put_name(e.pattern); 426 tomoyo_put_name(e.pattern);
448 return error; 427 return error;
449} 428}
@@ -553,6 +532,14 @@ bool tomoyo_read_file_pattern(struct tomoyo_io_buffer *head)
553 */ 532 */
554LIST_HEAD(tomoyo_no_rewrite_list); 533LIST_HEAD(tomoyo_no_rewrite_list);
555 534
535static bool tomoyo_same_no_rewrite(const struct tomoyo_acl_head *a,
536 const struct tomoyo_acl_head *b)
537{
538 return container_of(a, struct tomoyo_no_rewrite_entry, head)->pattern
539 == container_of(b, struct tomoyo_no_rewrite_entry, head)
540 ->pattern;
541}
542
556/** 543/**
557 * tomoyo_update_no_rewrite_entry - Update "struct tomoyo_no_rewrite_entry" list. 544 * tomoyo_update_no_rewrite_entry - Update "struct tomoyo_no_rewrite_entry" list.
558 * 545 *
@@ -566,35 +553,17 @@ LIST_HEAD(tomoyo_no_rewrite_list);
566static int tomoyo_update_no_rewrite_entry(const char *pattern, 553static int tomoyo_update_no_rewrite_entry(const char *pattern,
567 const bool is_delete) 554 const bool is_delete)
568{ 555{
569 struct tomoyo_no_rewrite_entry *ptr;
570 struct tomoyo_no_rewrite_entry e = { }; 556 struct tomoyo_no_rewrite_entry e = { };
571 int error = is_delete ? -ENOENT : -ENOMEM; 557 int error;
572 558
573 if (!tomoyo_is_correct_word(pattern)) 559 if (!tomoyo_is_correct_word(pattern))
574 return -EINVAL; 560 return -EINVAL;
575 e.pattern = tomoyo_get_name(pattern); 561 e.pattern = tomoyo_get_name(pattern);
576 if (!e.pattern) 562 if (!e.pattern)
577 return error; 563 return -ENOMEM;
578 if (mutex_lock_interruptible(&tomoyo_policy_lock)) 564 error = tomoyo_update_policy(&e.head, sizeof(e), is_delete,
579 goto out; 565 &tomoyo_no_rewrite_list,
580 list_for_each_entry_rcu(ptr, &tomoyo_no_rewrite_list, head.list) { 566 tomoyo_same_no_rewrite);
581 if (ptr->pattern != e.pattern)
582 continue;
583 ptr->head.is_deleted = is_delete;
584 error = 0;
585 break;
586 }
587 if (!is_delete && error) {
588 struct tomoyo_no_rewrite_entry *entry =
589 tomoyo_commit_ok(&e, sizeof(e));
590 if (entry) {
591 list_add_tail_rcu(&entry->head.list,
592 &tomoyo_no_rewrite_list);
593 error = 0;
594 }
595 }
596 mutex_unlock(&tomoyo_policy_lock);
597 out:
598 tomoyo_put_name(e.pattern); 567 tomoyo_put_name(e.pattern);
599 return error; 568 return error;
600} 569}