1f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles)// Copyright (c) 2013 The Chromium Authors. All rights reserved.
2f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles)// Use of this source code is governed by a BSD-style license that can be
3f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles)// found in the LICENSE file.
4f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles)
5ca12bfac764ba476d6cd062bf1dde12cc64c3f40Ben Murdoch#include <assert.h>
668043e1e95eeb07d5cae7aca370b26518b0867d6Torne (Richard Coles)#include <poll.h>
7ca12bfac764ba476d6cd062bf1dde12cc64c3f40Ben Murdoch
8ca12bfac764ba476d6cd062bf1dde12cc64c3f40Ben Murdoch#include "nacl_io/event_emitter.h"
9ca12bfac764ba476d6cd062bf1dde12cc64c3f40Ben Murdoch#include "nacl_io/event_listener.h"
1068043e1e95eeb07d5cae7aca370b26518b0867d6Torne (Richard Coles)#include "nacl_io/fifo_interface.h"
11ca12bfac764ba476d6cd062bf1dde12cc64c3f40Ben Murdoch
12ca12bfac764ba476d6cd062bf1dde12cc64c3f40Ben Murdoch#include "sdk_util/auto_lock.h"
13ca12bfac764ba476d6cd062bf1dde12cc64c3f40Ben Murdoch
14ca12bfac764ba476d6cd062bf1dde12cc64c3f40Ben Murdochnamespace nacl_io {
15ca12bfac764ba476d6cd062bf1dde12cc64c3f40Ben Murdoch
1668043e1e95eeb07d5cae7aca370b26518b0867d6Torne (Richard Coles)bool operator<(const ScopedEventEmitter& src_a,
1768043e1e95eeb07d5cae7aca370b26518b0867d6Torne (Richard Coles)               const ScopedEventEmitter& src_b) {
18ca12bfac764ba476d6cd062bf1dde12cc64c3f40Ben Murdoch  return src_a.get() < src_b.get();
19ca12bfac764ba476d6cd062bf1dde12cc64c3f40Ben Murdoch}
20ca12bfac764ba476d6cd062bf1dde12cc64c3f40Ben Murdoch
2168043e1e95eeb07d5cae7aca370b26518b0867d6Torne (Richard Coles)EventEmitter::EventEmitter() : event_status_(0) {}
2268043e1e95eeb07d5cae7aca370b26518b0867d6Torne (Richard Coles)
2368043e1e95eeb07d5cae7aca370b26518b0867d6Torne (Richard Coles)void EventEmitter::RegisterListener(EventListener* listener, uint32_t events) {
2468043e1e95eeb07d5cae7aca370b26518b0867d6Torne (Richard Coles)  AUTO_LOCK(emitter_lock_);
2568043e1e95eeb07d5cae7aca370b26518b0867d6Torne (Richard Coles)  RegisterListener_Locked(listener, events);
26ca12bfac764ba476d6cd062bf1dde12cc64c3f40Ben Murdoch}
27ca12bfac764ba476d6cd062bf1dde12cc64c3f40Ben Murdoch
2868043e1e95eeb07d5cae7aca370b26518b0867d6Torne (Richard Coles)void EventEmitter::UnregisterListener(EventListener* listener) {
29ca12bfac764ba476d6cd062bf1dde12cc64c3f40Ben Murdoch  AUTO_LOCK(emitter_lock_);
3068043e1e95eeb07d5cae7aca370b26518b0867d6Torne (Richard Coles)  UnregisterListener_Locked(listener);
3168043e1e95eeb07d5cae7aca370b26518b0867d6Torne (Richard Coles)}
32ca12bfac764ba476d6cd062bf1dde12cc64c3f40Ben Murdoch
3368043e1e95eeb07d5cae7aca370b26518b0867d6Torne (Richard Coles)void EventEmitter::RegisterListener_Locked(EventListener* listener,
3468043e1e95eeb07d5cae7aca370b26518b0867d6Torne (Richard Coles)                                           uint32_t events) {
3568043e1e95eeb07d5cae7aca370b26518b0867d6Torne (Richard Coles)  assert(listeners_.count(listener) == 0);
3668043e1e95eeb07d5cae7aca370b26518b0867d6Torne (Richard Coles)  listeners_[listener] = events;
37ca12bfac764ba476d6cd062bf1dde12cc64c3f40Ben Murdoch}
38ca12bfac764ba476d6cd062bf1dde12cc64c3f40Ben Murdoch
3968043e1e95eeb07d5cae7aca370b26518b0867d6Torne (Richard Coles)void EventEmitter::UnregisterListener_Locked(EventListener* listener) {
4068043e1e95eeb07d5cae7aca370b26518b0867d6Torne (Richard Coles)  assert(listeners_.count(listener) == 1);
4168043e1e95eeb07d5cae7aca370b26518b0867d6Torne (Richard Coles)  listeners_.erase(listener);
4268043e1e95eeb07d5cae7aca370b26518b0867d6Torne (Richard Coles)}
43ca12bfac764ba476d6cd062bf1dde12cc64c3f40Ben Murdoch
4468043e1e95eeb07d5cae7aca370b26518b0867d6Torne (Richard Coles)void EventEmitter::ClearEvents_Locked(uint32_t event_bits) {
4568043e1e95eeb07d5cae7aca370b26518b0867d6Torne (Richard Coles)  event_status_ &= ~event_bits;
46ca12bfac764ba476d6cd062bf1dde12cc64c3f40Ben Murdoch}
47ca12bfac764ba476d6cd062bf1dde12cc64c3f40Ben Murdoch
4868043e1e95eeb07d5cae7aca370b26518b0867d6Torne (Richard Coles)void EventEmitter::RaiseEvents_Locked(uint32_t event_bits) {
4968043e1e95eeb07d5cae7aca370b26518b0867d6Torne (Richard Coles)  event_status_ |= event_bits;
5068043e1e95eeb07d5cae7aca370b26518b0867d6Torne (Richard Coles)
5168043e1e95eeb07d5cae7aca370b26518b0867d6Torne (Richard Coles)  EventListenerMap_t::iterator it;
5268043e1e95eeb07d5cae7aca370b26518b0867d6Torne (Richard Coles)  for (it = listeners_.begin(); it != listeners_.end(); it++) {
5368043e1e95eeb07d5cae7aca370b26518b0867d6Torne (Richard Coles)    uint32_t bits = it->second & event_bits;
5468043e1e95eeb07d5cae7aca370b26518b0867d6Torne (Richard Coles)    if (0 != bits)
5568043e1e95eeb07d5cae7aca370b26518b0867d6Torne (Richard Coles)      it->first->ReceiveEvents(this, bits);
56ca12bfac764ba476d6cd062bf1dde12cc64c3f40Ben Murdoch  }
57ca12bfac764ba476d6cd062bf1dde12cc64c3f40Ben Murdoch}
58ca12bfac764ba476d6cd062bf1dde12cc64c3f40Ben Murdoch
59ca12bfac764ba476d6cd062bf1dde12cc64c3f40Ben Murdoch}  // namespace nacl_io
60