]>
Commit | Line | Data |
---|---|---|
bbc27441 | 1 | /* |
5b74111a | 2 | * Copyright (C) 1996-2018 The Squid Software Foundation and contributors |
bbc27441 AJ |
3 | * |
4 | * Squid software is distributed under GPLv2+ license and includes | |
5 | * contributions from numerous individuals and organizations. | |
6 | * Please see the COPYING and CONTRIBUTORS files for details. | |
7 | */ | |
8 | ||
f7f3304a | 9 | #include "squid.h" |
6d57128b | 10 | #include "base/RunnersRegistry.h" |
b856803f | 11 | #include "base/TextException.h" |
21b7990f | 12 | #include <set> |
6d57128b | 13 | |
21b7990f AR |
14 | /// a collection of unique runners, in no particular order |
15 | typedef std::set<RegisteredRunner*> Runners; | |
16 | /// all known runners | |
17 | static Runners *TheRunners = NULL; | |
a27fcaed CT |
18 | /// used to avoid re-creating deleted TheRunners after shutdown finished. |
19 | static bool RunnersGone = false; | |
6d57128b | 20 | |
a27fcaed CT |
21 | /// creates the registered runners container if needed |
22 | /// \return either registered runners (if they should exist) or nil (otherwise) | |
b856803f | 23 | static inline Runners * |
a27fcaed | 24 | FindRunners() |
6d57128b | 25 | { |
a27fcaed | 26 | if (!TheRunners && !RunnersGone) |
21b7990f | 27 | TheRunners = new Runners; |
a27fcaed | 28 | return TheRunners; |
6d57128b AR |
29 | } |
30 | ||
a27fcaed CT |
31 | static inline void |
32 | GetRidOfRunner(RegisteredRunner *rr) | |
6d57128b | 33 | { |
a27fcaed CT |
34 | if (!dynamic_cast<IndependentRunner*>(rr)) |
35 | delete rr; | |
d39a7c59 | 36 | // else ignore; IndependentRunner |
6d57128b AR |
37 | } |
38 | ||
b856803f CT |
39 | static inline void |
40 | RegisterRunner_(RegisteredRunner *rr) | |
41 | { | |
42 | Runners *runners = FindRunners(); | |
43 | Must(runners); | |
44 | runners->insert(rr); | |
45 | } | |
46 | ||
a27fcaed CT |
47 | bool |
48 | RegisterRunner(RegisteredRunner *rr) | |
d442618d | 49 | { |
b856803f CT |
50 | Must(!dynamic_cast<IndependentRunner*>(rr)); |
51 | ||
52 | if (FindRunners()) { | |
53 | RegisterRunner_(rr); | |
a27fcaed CT |
54 | return true; |
55 | } | |
56 | ||
57 | // past finishShutdown | |
58 | GetRidOfRunner(rr); | |
59 | return false; | |
d442618d AJ |
60 | } |
61 | ||
21b7990f | 62 | void |
a27fcaed | 63 | RunRegistered(const RegisteredRunner::Method &event) |
6d57128b | 64 | { |
a27fcaed CT |
65 | if (Runners *runners = FindRunners()) { |
66 | // Many things may happen during the loop below. We copy to withstand | |
67 | // runner removal/addition and avoid surprises due to registrations from | |
68 | // parent constructors (with a half-baked "this"!). This copy also | |
69 | // simplifies overall RR logic as it guarantees that registering a | |
70 | // runner during event X loop does not execute runner::X(). | |
71 | Runners oldRunners(*runners); | |
72 | for (auto runner: oldRunners) { | |
73 | if (runners->find(runner) != runners->end()) // still registered | |
74 | (runner->*event)(); | |
75 | } | |
6d57128b | 76 | } |
a27fcaed CT |
77 | |
78 | if (event != &RegisteredRunner::finishShutdown) | |
79 | return; | |
80 | ||
81 | // this is the last event; delete registry-dependent runners (and only them) | |
82 | if (Runners *runners = FindRunners()) { | |
83 | RunnersGone = true; | |
84 | TheRunners = nullptr; | |
85 | // from now on, no runners can be registered or unregistered | |
86 | for (auto runner: *runners) | |
87 | GetRidOfRunner(runner); // leaves a dangling pointer in runners | |
88 | delete runners; | |
89 | } | |
90 | } | |
91 | ||
92 | /* IndependentRunner */ | |
93 | ||
94 | void | |
95 | IndependentRunner::unregisterRunner() | |
96 | { | |
97 | if (Runners *runners = FindRunners()) | |
98 | runners->erase(this); | |
99 | // else it is too late, finishShutdown() has been called | |
6d57128b AR |
100 | } |
101 | ||
b856803f CT |
102 | void |
103 | IndependentRunner::registerRunner() | |
104 | { | |
105 | if (FindRunners()) | |
106 | RegisterRunner_(this); | |
107 | // else do nothing past finishShutdown | |
108 | } | |
109 | ||
6d57128b AR |
110 | bool |
111 | UseThisStatic(const void *) | |
112 | { | |
113 | return true; | |
114 | } | |
f53969cc | 115 |