[email protected] | 285d06fc | 2013-08-24 15:00:33 | [diff] [blame] | 1 | // Copyright 2013 The Chromium Authors. All rights reserved. |
2 | // Use of this source code is governed by a BSD-style license that can be | ||||
3 | // found in the LICENSE file. | ||||
4 | |||||
5 | #include "base/barrier_closure.h" | ||||
6 | |||||
tzik | 34bf605 | 2017-04-27 14:03:21 | [diff] [blame] | 7 | #include <utility> |
8 | |||||
[email protected] | 285d06fc | 2013-08-24 15:00:33 | [diff] [blame] | 9 | #include "base/atomic_ref_count.h" |
10 | #include "base/bind.h" | ||||
tzik | 34bf605 | 2017-04-27 14:03:21 | [diff] [blame] | 11 | #include "base/memory/ptr_util.h" |
[email protected] | 285d06fc | 2013-08-24 15:00:33 | [diff] [blame] | 12 | |
tzik | 34bf605 | 2017-04-27 14:03:21 | [diff] [blame] | 13 | namespace base { |
[email protected] | 285d06fc | 2013-08-24 15:00:33 | [diff] [blame] | 14 | namespace { |
15 | |||||
16 | // Maintains state for a BarrierClosure. | ||||
17 | class BarrierInfo { | ||||
18 | public: | ||||
tzik | 34bf605 | 2017-04-27 14:03:21 | [diff] [blame] | 19 | BarrierInfo(int num_callbacks_left, OnceClosure done_closure); |
[email protected] | 285d06fc | 2013-08-24 15:00:33 | [diff] [blame] | 20 | void Run(); |
21 | |||||
22 | private: | ||||
tzik | 34bf605 | 2017-04-27 14:03:21 | [diff] [blame] | 23 | AtomicRefCount num_callbacks_left_; |
24 | OnceClosure done_closure_; | ||||
[email protected] | 285d06fc | 2013-08-24 15:00:33 | [diff] [blame] | 25 | }; |
26 | |||||
tzik | 34bf605 | 2017-04-27 14:03:21 | [diff] [blame] | 27 | BarrierInfo::BarrierInfo(int num_callbacks, OnceClosure done_closure) |
[email protected] | 285d06fc | 2013-08-24 15:00:33 | [diff] [blame] | 28 | : num_callbacks_left_(num_callbacks), |
tzik | 34bf605 | 2017-04-27 14:03:21 | [diff] [blame] | 29 | done_closure_(std::move(done_closure)) {} |
[email protected] | 285d06fc | 2013-08-24 15:00:33 | [diff] [blame] | 30 | |
31 | void BarrierInfo::Run() { | ||||
Jeremy Roman | ee96d56 | 2017-07-06 19:09:36 | [diff] [blame] | 32 | DCHECK(!num_callbacks_left_.IsZero()); |
33 | if (!num_callbacks_left_.Decrement()) | ||||
tzik | 34bf605 | 2017-04-27 14:03:21 | [diff] [blame] | 34 | std::move(done_closure_).Run(); |
[email protected] | 285d06fc | 2013-08-24 15:00:33 | [diff] [blame] | 35 | } |
36 | |||||
cfredric | e7af064 | 2021-07-27 21:06:51 | [diff] [blame^] | 37 | void ShouldNeverRun() { |
38 | CHECK(false); | ||||
39 | } | ||||
40 | |||||
[email protected] | 285d06fc | 2013-08-24 15:00:33 | [diff] [blame] | 41 | } // namespace |
42 | |||||
tzik | 34bf605 | 2017-04-27 14:03:21 | [diff] [blame] | 43 | RepeatingClosure BarrierClosure(int num_callbacks_left, |
44 | OnceClosure done_closure) { | ||||
danakj | 94219a21 | 2015-03-09 22:27:25 | [diff] [blame] | 45 | DCHECK_GE(num_callbacks_left, 0); |
[email protected] | 285d06fc | 2013-08-24 15:00:33 | [diff] [blame] | 46 | |
cfredric | e7af064 | 2021-07-27 21:06:51 | [diff] [blame^] | 47 | if (num_callbacks_left == 0) { |
tzik | 34bf605 | 2017-04-27 14:03:21 | [diff] [blame] | 48 | std::move(done_closure).Run(); |
cfredric | e7af064 | 2021-07-27 21:06:51 | [diff] [blame^] | 49 | return BindRepeating(&ShouldNeverRun); |
50 | } | ||||
[email protected] | 285d06fc | 2013-08-24 15:00:33 | [diff] [blame] | 51 | |
cfredric | e7af064 | 2021-07-27 21:06:51 | [diff] [blame^] | 52 | return BindRepeating(&BarrierInfo::Run, |
53 | std::make_unique<BarrierInfo>(num_callbacks_left, | ||||
54 | std::move(done_closure))); | ||||
[email protected] | 285d06fc | 2013-08-24 15:00:33 | [diff] [blame] | 55 | } |
56 | |||||
[email protected] | d5b04b83 | 2013-09-12 19:48:15 | [diff] [blame] | 57 | } // namespace base |