diff options
author | Al Viro <viro@zeniv.linux.org.uk> | 2014-05-07 05:12:09 -0400 |
---|---|---|
committer | Al Viro <viro@zeniv.linux.org.uk> | 2014-08-07 14:40:07 -0400 |
commit | e25ff11ff16aba000dfe9e568d867e5142c31f16 (patch) | |
tree | 9a0636f305f10efb8c927bf13b2e83c68c081c4b /kernel | |
parent | cdd37e23092c3c6fbbb2e611f8c3d18e676bf28f (diff) |
split the slow path in acct_process() off
Signed-off-by: Al Viro <viro@zeniv.linux.org.uk>
Diffstat (limited to 'kernel')
-rw-r--r-- | kernel/acct.c | 50 |
1 files changed, 28 insertions, 22 deletions
diff --git a/kernel/acct.c b/kernel/acct.c index efa891beeaa3..51188603b258 100644 --- a/kernel/acct.c +++ b/kernel/acct.c | |||
@@ -599,34 +599,35 @@ void acct_collect(long exitcode, int group_dead) | |||
599 | spin_unlock_irq(¤t->sighand->siglock); | 599 | spin_unlock_irq(¤t->sighand->siglock); |
600 | } | 600 | } |
601 | 601 | ||
602 | static void acct_process_in_ns(struct pid_namespace *ns) | 602 | static void slow_acct_process(struct pid_namespace *ns) |
603 | { | 603 | { |
604 | struct file *file = NULL; | 604 | for ( ; ns; ns = ns->parent) { |
605 | struct bsd_acct_struct *acct; | 605 | struct file *file = NULL; |
606 | struct bsd_acct_struct *acct; | ||
606 | 607 | ||
607 | acct = ns->bacct; | 608 | acct = ns->bacct; |
608 | /* | 609 | /* |
609 | * accelerate the common fastpath: | 610 | * accelerate the common fastpath: |
610 | */ | 611 | */ |
611 | if (!acct || !acct->file) | 612 | if (!acct || !acct->file) |
612 | return; | 613 | continue; |
613 | 614 | ||
614 | spin_lock(&acct_lock); | 615 | spin_lock(&acct_lock); |
615 | file = acct->file; | 616 | file = acct->file; |
616 | if (unlikely(!file)) { | 617 | if (unlikely(!file)) { |
618 | spin_unlock(&acct_lock); | ||
619 | continue; | ||
620 | } | ||
621 | get_file(file); | ||
617 | spin_unlock(&acct_lock); | 622 | spin_unlock(&acct_lock); |
618 | return; | ||
619 | } | ||
620 | get_file(file); | ||
621 | spin_unlock(&acct_lock); | ||
622 | 623 | ||
623 | do_acct_process(acct, ns, file); | 624 | do_acct_process(acct, ns, file); |
624 | fput(file); | 625 | fput(file); |
626 | } | ||
625 | } | 627 | } |
626 | 628 | ||
627 | /** | 629 | /** |
628 | * acct_process - now just a wrapper around acct_process_in_ns, | 630 | * acct_process |
629 | * which in turn is a wrapper around do_acct_process. | ||
630 | * | 631 | * |
631 | * handles process accounting for an exiting task | 632 | * handles process accounting for an exiting task |
632 | */ | 633 | */ |
@@ -639,6 +640,11 @@ void acct_process(void) | |||
639 | * alive and holds its namespace, which in turn holds | 640 | * alive and holds its namespace, which in turn holds |
640 | * its parent. | 641 | * its parent. |
641 | */ | 642 | */ |
642 | for (ns = task_active_pid_ns(current); ns != NULL; ns = ns->parent) | 643 | for (ns = task_active_pid_ns(current); ns != NULL; ns = ns->parent) { |
643 | acct_process_in_ns(ns); | 644 | struct bsd_acct_struct *acct = ns->bacct; |
645 | if (acct && acct->file) | ||
646 | break; | ||
647 | } | ||
648 | if (unlikely(ns)) | ||
649 | slow_acct_process(ns); | ||
644 | } | 650 | } |