Skip to content

Commit 0f1b92c

Browse files
oleg-nesterovebiederm
authored andcommitted
introduce the walk_process_tree() helper
Add the new helper to walk the process tree, the next patch adds a user. Note that it visits the group leaders only, proc_visitor can do for_each_thread itself or we can trivially extend walk_process_tree() to do this. Signed-off-by: Oleg Nesterov <[email protected]> Signed-off-by: Pavel Tikhomirov <[email protected]> Signed-off-by: Eric W. Biederman <[email protected]>
1 parent 015bb30 commit 0f1b92c

File tree

2 files changed

+35
-0
lines changed

2 files changed

+35
-0
lines changed

include/linux/sched.h

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -3053,6 +3053,9 @@ extern bool current_is_single_threaded(void);
30533053
#define for_each_process_thread(p, t) \
30543054
for_each_process(p) for_each_thread(p, t)
30553055

3056+
typedef int (*proc_visitor)(struct task_struct *p, void *data);
3057+
void walk_process_tree(struct task_struct *top, proc_visitor, void *);
3058+
30563059
static inline int get_nr_threads(struct task_struct *tsk)
30573060
{
30583061
return tsk->signal->nr_threads;

kernel/fork.c

Lines changed: 32 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -2053,6 +2053,38 @@ SYSCALL_DEFINE5(clone, unsigned long, clone_flags, unsigned long, newsp,
20532053
}
20542054
#endif
20552055

2056+
void walk_process_tree(struct task_struct *top, proc_visitor visitor, void *data)
2057+
{
2058+
struct task_struct *leader, *parent, *child;
2059+
int res;
2060+
2061+
read_lock(&tasklist_lock);
2062+
leader = top = top->group_leader;
2063+
down:
2064+
for_each_thread(leader, parent) {
2065+
list_for_each_entry(child, &parent->children, sibling) {
2066+
res = visitor(child, data);
2067+
if (res) {
2068+
if (res < 0)
2069+
goto out;
2070+
leader = child;
2071+
goto down;
2072+
}
2073+
up:
2074+
;
2075+
}
2076+
}
2077+
2078+
if (leader != top) {
2079+
child = leader;
2080+
parent = child->real_parent;
2081+
leader = parent->group_leader;
2082+
goto up;
2083+
}
2084+
out:
2085+
read_unlock(&tasklist_lock);
2086+
}
2087+
20562088
#ifndef ARCH_MIN_MMSTRUCT_ALIGN
20572089
#define ARCH_MIN_MMSTRUCT_ALIGN 0
20582090
#endif

0 commit comments

Comments
 (0)