Home | History | Annotate | Download | only in mac
      1 // Copyright 2014 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 "sandbox/mac/dispatch_source_mach.h"
      6 
      7 namespace sandbox {
      8 
      9 DispatchSourceMach::DispatchSourceMach(const char* name,
     10                                        mach_port_t port,
     11                                        void (^event_handler)())
     12     // TODO(rsesek): Specify DISPATCH_QUEUE_SERIAL, in the 10.7 SDK. NULL
     13     // means the same thing but is not symbolically clear.
     14     : DispatchSourceMach(dispatch_queue_create(name, NULL),
     15                          port,
     16                          event_handler) {
     17   // Since the queue was created above in the delegated constructor, and it was
     18   // subsequently retained, release it here.
     19   dispatch_release(queue_);
     20 }
     21 
     22 DispatchSourceMach::DispatchSourceMach(dispatch_queue_t queue,
     23                                        mach_port_t port,
     24                                        void (^event_handler)())
     25     : queue_(queue),
     26       source_(dispatch_source_create(DISPATCH_SOURCE_TYPE_MACH_RECV,
     27           port, 0, queue_)),
     28       source_canceled_(dispatch_semaphore_create(0)) {
     29   dispatch_retain(queue);
     30 
     31   dispatch_source_set_event_handler(source_, event_handler);
     32   dispatch_source_set_cancel_handler(source_, ^{
     33       dispatch_semaphore_signal(source_canceled_);
     34   });
     35 }
     36 
     37 DispatchSourceMach::~DispatchSourceMach() {
     38   Cancel();
     39 }
     40 
     41 void DispatchSourceMach::Resume() {
     42   dispatch_resume(source_);
     43 }
     44 
     45 void DispatchSourceMach::Cancel() {
     46   if (source_) {
     47     dispatch_source_cancel(source_);
     48     dispatch_release(source_);
     49     source_ = NULL;
     50 
     51     dispatch_semaphore_wait(source_canceled_, DISPATCH_TIME_FOREVER);
     52     dispatch_release(source_canceled_);
     53     source_canceled_ = NULL;
     54   }
     55 
     56   if (queue_) {
     57     dispatch_release(queue_);
     58     queue_ = NULL;
     59   }
     60 }
     61 
     62 }  // namespace sandbox
     63