|
1 | 1 | /*
|
2 | 2 | * Copyright (c) 2020, the SerenityOS developers.
|
| 3 | + * Copyright (c) 2021, Andreas Kling <kling@serenityos.org> |
3 | 4 | *
|
4 | 5 | * SPDX-License-Identifier: BSD-2-Clause
|
5 | 6 | */
|
6 | 7 |
|
| 8 | +#include <AK/Singleton.h> |
7 | 9 | #include <Kernel/ProcessGroup.h>
|
8 | 10 |
|
9 | 11 | namespace Kernel {
|
10 | 12 |
|
11 |
| -RecursiveSpinLock g_process_groups_lock; |
12 |
| -ProcessGroup::List* g_process_groups; |
| 13 | +static AK::Singleton<SpinLockProtectedValue<ProcessGroup::List>> s_process_groups; |
| 14 | + |
| 15 | +SpinLockProtectedValue<ProcessGroup::List>& process_groups() |
| 16 | +{ |
| 17 | + return *s_process_groups; |
| 18 | +} |
13 | 19 |
|
14 | 20 | ProcessGroup::~ProcessGroup()
|
15 | 21 | {
|
16 |
| - ScopedSpinLock lock(g_process_groups_lock); |
17 |
| - g_process_groups->remove(*this); |
| 22 | + process_groups().with([&](auto& groups) { |
| 23 | + groups.remove(*this); |
| 24 | + }); |
18 | 25 | }
|
19 | 26 |
|
20 | 27 | RefPtr<ProcessGroup> ProcessGroup::create(ProcessGroupID pgid)
|
21 | 28 | {
|
22 | 29 | auto process_group = adopt_ref_if_nonnull(new (nothrow) ProcessGroup(pgid));
|
23 |
| - if (process_group) { |
24 |
| - ScopedSpinLock lock(g_process_groups_lock); |
25 |
| - g_process_groups->prepend(*process_group); |
26 |
| - } |
27 |
| - |
| 30 | + if (!process_group) |
| 31 | + return {}; |
| 32 | + process_groups().with([&](auto& groups) { |
| 33 | + groups.prepend(*process_group); |
| 34 | + }); |
28 | 35 | return process_group;
|
29 | 36 | }
|
30 | 37 |
|
31 | 38 | RefPtr<ProcessGroup> ProcessGroup::find_or_create(ProcessGroupID pgid)
|
32 | 39 | {
|
33 |
| - ScopedSpinLock lock(g_process_groups_lock); |
34 |
| - |
35 |
| - if (auto existing = from_pgid(pgid)) |
36 |
| - return existing.release_nonnull(); |
37 |
| - |
38 |
| - return create(pgid); |
| 40 | + return process_groups().with([&](auto& groups) -> RefPtr<ProcessGroup> { |
| 41 | + for (auto& group : groups) { |
| 42 | + if (group.pgid() == pgid) |
| 43 | + return &group; |
| 44 | + } |
| 45 | + auto process_group = adopt_ref_if_nonnull(new (nothrow) ProcessGroup(pgid)); |
| 46 | + if (process_group) |
| 47 | + groups.prepend(*process_group); |
| 48 | + return process_group; |
| 49 | + }); |
39 | 50 | }
|
40 | 51 |
|
41 | 52 | RefPtr<ProcessGroup> ProcessGroup::from_pgid(ProcessGroupID pgid)
|
42 | 53 | {
|
43 |
| - ScopedSpinLock lock(g_process_groups_lock); |
44 |
| - |
45 |
| - for (auto& group : *g_process_groups) { |
46 |
| - if (group.pgid() == pgid) |
47 |
| - return &group; |
48 |
| - } |
49 |
| - return nullptr; |
| 54 | + return process_groups().with([&](auto& groups) -> RefPtr<ProcessGroup> { |
| 55 | + for (auto& group : groups) { |
| 56 | + if (group.pgid() == pgid) |
| 57 | + return &group; |
| 58 | + } |
| 59 | + return nullptr; |
| 60 | + }); |
50 | 61 | }
|
51 | 62 |
|
52 | 63 | }
|
0 commit comments