// Copyright 2017 The Chromium Authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.

#include <stdint.h>

#include <map>
#include <memory>
#include <set>

#include "base/bind.h"
#include "base/callback.h"
#include "base/macros.h"
#include "base/memory/ptr_util.h"
#include "base/rand_util.h"
#include "base/synchronization/waitable_event.h"
#include "base/test/bind_test_util.h"
#include "base/threading/platform_thread.h"
#include "base/threading/simple_thread.h"
#include "base/time/time.h"
#include "mojo/core/test/mojo_test_base.h"
#include "mojo/public/c/system/data_pipe.h"
#include "mojo/public/c/system/trap.h"
#include "mojo/public/c/system/types.h"
#include "testing/gtest/include/gtest/gtest.h"

namespace mojo {
namespace core {
namespace {

using TrapTest = test::MojoTestBase;

class TriggerHelper {
 public:
  using ContextCallback = base::RepeatingCallback<void(const MojoTrapEvent&)>;

  TriggerHelper() {}
  ~TriggerHelper() {}

  MojoResult CreateTrap(MojoHandle* handle) {
    return MojoCreateTrap(&Notify, nullptr, handle);
  }

  template <typename Handler>
  uintptr_t CreateContext(Handler handler) {
    return CreateContextWithCancel(handler, [] {});
  }

  template <typename Handler, typename CancelHandler>
  uintptr_t CreateContextWithCancel(Handler handler,
                                    CancelHandler cancel_handler) {
    auto* context =
        new NotificationContext(base::BindLambdaForTesting(handler));
    context->SetCancelCallback(
        base::BindOnce(base::BindLambdaForTesting([cancel_handler, context] {
          cancel_handler();
          delete context;
        })));
    return reinterpret_cast<uintptr_t>(context);
  }

 private:
  class NotificationContext {
   public:
    explicit NotificationContext(const ContextCallback& callback)
        : callback_(callback) {}

    ~NotificationContext() {}

    void SetCancelCallback(base::OnceClosure cancel_callback) {
      cancel_callback_ = std::move(cancel_callback);
    }

    void Notify(const MojoTrapEvent& event) {
      if (event.result == MOJO_RESULT_CANCELLED && cancel_callback_)
        std::move(cancel_callback_).Run();
      else
        callback_.Run(event);
    }

   private:
    const ContextCallback callback_;
    base::OnceClosure cancel_callback_;

    DISALLOW_COPY_AND_ASSIGN(NotificationContext);
  };

  static void Notify(const MojoTrapEvent* event) {
    reinterpret_cast<NotificationContext*>(event->trigger_context)
        ->Notify(*event);
  }

  DISALLOW_COPY_AND_ASSIGN(TriggerHelper);
};

class ThreadedRunner : public base::SimpleThread {
 public:
  explicit ThreadedRunner(base::OnceClosure callback)
      : SimpleThread("ThreadedRunner"), callback_(std::move(callback)) {}
  ~ThreadedRunner() override {}

  void Run() override { std::move(callback_).Run(); }

 private:
  base::OnceClosure callback_;

  DISALLOW_COPY_AND_ASSIGN(ThreadedRunner);
};

void ExpectNoNotification(const MojoTrapEvent* event) {
  NOTREACHED();
}

void ExpectOnlyCancel(const MojoTrapEvent* event) {
  EXPECT_EQ(event->result, MOJO_RESULT_CANCELLED);
}

TEST_F(TrapTest, InvalidArguments) {
  EXPECT_EQ(MOJO_RESULT_INVALID_ARGUMENT,
            MojoCreateTrap(&ExpectNoNotification, nullptr, nullptr));
  MojoHandle t;
  EXPECT_EQ(MOJO_RESULT_OK, MojoCreateTrap(&ExpectNoNotification, nullptr, &t));

  // Try to add triggers for handles which don't raise trappable signals.
  EXPECT_EQ(
      MOJO_RESULT_INVALID_ARGUMENT,
      MojoAddTrigger(t, t, MOJO_HANDLE_SIGNAL_READABLE,
                     MOJO_TRIGGER_CONDITION_SIGNALS_SATISFIED, 0, nullptr));
  MojoHandle buffer_handle = CreateBuffer(42);
  EXPECT_EQ(
      MOJO_RESULT_INVALID_ARGUMENT,
      MojoAddTrigger(t, buffer_handle, MOJO_HANDLE_SIGNAL_READABLE,
                     MOJO_TRIGGER_CONDITION_SIGNALS_SATISFIED, 0, nullptr));

  // Try to remove a trigger on a non-trap handle.
  EXPECT_EQ(MOJO_RESULT_INVALID_ARGUMENT,
            MojoRemoveTrigger(buffer_handle, 0, nullptr));

  // Try to arm an invalid or non-trap handle.
  EXPECT_EQ(MOJO_RESULT_INVALID_ARGUMENT,
            MojoArmTrap(MOJO_HANDLE_INVALID, nullptr, nullptr, nullptr));
  EXPECT_EQ(MOJO_RESULT_INVALID_ARGUMENT,
            MojoArmTrap(buffer_handle, nullptr, nullptr, nullptr));
  EXPECT_EQ(MOJO_RESULT_OK, MojoClose(buffer_handle));

  // Try to arm with a non-null count but a null output buffer.
  uint32_t num_blocking_events = 1;
  EXPECT_EQ(MOJO_RESULT_INVALID_ARGUMENT,
            MojoArmTrap(t, nullptr, &num_blocking_events, nullptr));

  EXPECT_EQ(MOJO_RESULT_OK, MojoClose(t));
}

TEST_F(TrapTest, TrapMessagePipeReadable) {
  MojoHandle a, b;
  CreateMessagePipe(&a, &b);

  base::WaitableEvent wait(base::WaitableEvent::ResetPolicy::MANUAL,
                           base::WaitableEvent::InitialState::NOT_SIGNALED);
  TriggerHelper helper;
  int num_expected_notifications = 1;
  const uintptr_t readable_a_context =
      helper.CreateContext([&](const MojoTrapEvent& event) {
        EXPECT_GT(num_expected_notifications, 0);
        num_expected_notifications -= 1;

        EXPECT_EQ(MOJO_RESULT_OK, event.result);
        wait.Signal();
      });

  MojoHandle t;
  EXPECT_EQ(MOJO_RESULT_OK, helper.CreateTrap(&t));
  EXPECT_EQ(MOJO_RESULT_OK,
            MojoAddTrigger(t, a, MOJO_HANDLE_SIGNAL_READABLE,
                           MOJO_TRIGGER_CONDITION_SIGNALS_SATISFIED,
                           readable_a_context, nullptr));
  EXPECT_EQ(MOJO_RESULT_OK, MojoArmTrap(t, nullptr, nullptr, nullptr));

  const char kMessage1[] = "hey hey hey hey";
  const char kMessage2[] = "i said hey";
  const char kMessage3[] = "what's goin' on?";

  // Writing to |b| multiple times should notify exactly once.
  WriteMessage(b, kMessage1);
  WriteMessage(b, kMessage2);
  wait.Wait();

  // This also shouldn't fire a notification; the trap is still disarmed.
  WriteMessage(b, kMessage3);

  // Arming should fail with relevant information.
  constexpr size_t kMaxBlockingEvents = 3;
  uint32_t num_blocking_events = kMaxBlockingEvents;
  MojoTrapEvent blocking_events[kMaxBlockingEvents] = {
      {sizeof(blocking_events[0])},
      {sizeof(blocking_events[0])},
      {sizeof(blocking_events[0])}};
  EXPECT_EQ(MOJO_RESULT_FAILED_PRECONDITION,
            MojoArmTrap(t, nullptr, &num_blocking_events, &blocking_events[0]));
  EXPECT_EQ(1u, num_blocking_events);
  EXPECT_EQ(readable_a_context, blocking_events[0].trigger_context);
  EXPECT_EQ(MOJO_RESULT_OK, blocking_events[0].result);

  // Flush the three messages from above.
  EXPECT_EQ(kMessage1, ReadMessage(a));
  EXPECT_EQ(kMessage2, ReadMessage(a));
  EXPECT_EQ(kMessage3, ReadMessage(a));

  // Now we can rearm the trap.
  EXPECT_EQ(MOJO_RESULT_OK, MojoArmTrap(t, nullptr, nullptr, nullptr));

  EXPECT_EQ(MOJO_RESULT_OK, MojoClose(t));
  EXPECT_EQ(MOJO_RESULT_OK, MojoClose(b));
  EXPECT_EQ(MOJO_RESULT_OK, MojoClose(a));
}

TEST_F(TrapTest, CloseWatchedMessagePipeHandle) {
  MojoHandle a, b;
  CreateMessagePipe(&a, &b);

  base::WaitableEvent wait(base::WaitableEvent::ResetPolicy::MANUAL,
                           base::WaitableEvent::InitialState::NOT_SIGNALED);
  TriggerHelper helper;
  const uintptr_t readable_a_context = helper.CreateContextWithCancel(
      [](const MojoTrapEvent&) {}, [&] { wait.Signal(); });

  MojoHandle t;
  EXPECT_EQ(MOJO_RESULT_OK, helper.CreateTrap(&t));
  EXPECT_EQ(MOJO_RESULT_OK,
            MojoAddTrigger(t, a, MOJO_HANDLE_SIGNAL_READABLE,
                           MOJO_TRIGGER_CONDITION_SIGNALS_SATISFIED,
                           readable_a_context, nullptr));

  // Test that closing a watched handle fires an appropriate notification, even
  // when the trap is unarmed.
  EXPECT_EQ(MOJO_RESULT_OK, MojoClose(a));
  wait.Wait();

  EXPECT_EQ(MOJO_RESULT_OK, MojoClose(b));
  EXPECT_EQ(MOJO_RESULT_OK, MojoClose(t));
}

TEST_F(TrapTest, CloseWatchedMessagePipeHandlePeer) {
  MojoHandle a, b;
  CreateMessagePipe(&a, &b);

  base::WaitableEvent wait(base::WaitableEvent::ResetPolicy::MANUAL,
                           base::WaitableEvent::InitialState::NOT_SIGNALED);
  TriggerHelper helper;
  const uintptr_t readable_a_context =
      helper.CreateContext([&](const MojoTrapEvent& event) {
        EXPECT_EQ(MOJO_RESULT_FAILED_PRECONDITION, event.result);
        wait.Signal();
      });

  MojoHandle t;
  EXPECT_EQ(MOJO_RESULT_OK, helper.CreateTrap(&t));
  EXPECT_EQ(MOJO_RESULT_OK,
            MojoAddTrigger(t, a, MOJO_HANDLE_SIGNAL_READABLE,
                           MOJO_TRIGGER_CONDITION_SIGNALS_SATISFIED,
                           readable_a_context, nullptr));

  // Test that closing a watched handle's peer with an armed trap fires an
  // appropriate notification.
  EXPECT_EQ(MOJO_RESULT_OK, MojoArmTrap(t, nullptr, nullptr, nullptr));
  EXPECT_EQ(MOJO_RESULT_OK, MojoClose(b));
  wait.Wait();

  // And now arming should fail with correct information about |a|'s state.
  constexpr size_t kMaxBlockingEvents = 3;
  uint32_t num_blocking_events = kMaxBlockingEvents;
  MojoTrapEvent blocking_events[kMaxBlockingEvents] = {
      {sizeof(blocking_events[0])},
      {sizeof(blocking_events[0])},
      {sizeof(blocking_events[0])}};
  EXPECT_EQ(MOJO_RESULT_FAILED_PRECONDITION,
            MojoArmTrap(t, nullptr, &num_blocking_events, &blocking_events[0]));
  EXPECT_EQ(1u, num_blocking_events);
  EXPECT_EQ(readable_a_context, blocking_events[0].trigger_context);
  EXPECT_EQ(MOJO_RESULT_FAILED_PRECONDITION, blocking_events[0].result);
  EXPECT_TRUE(blocking_events[0].signals_state.satisfied_signals &
              MOJO_HANDLE_SIGNAL_PEER_CLOSED);
  EXPECT_FALSE(blocking_events[0].signals_state.satisfiable_signals &
               MOJO_HANDLE_SIGNAL_READABLE);

  EXPECT_EQ(MOJO_RESULT_OK, MojoClose(t));
  EXPECT_EQ(MOJO_RESULT_OK, MojoClose(a));
}

TEST_F(TrapTest, TrapDataPipeConsumerReadable) {
  constexpr size_t kTestPipeCapacity = 64;
  MojoHandle producer, consumer;
  CreateDataPipe(&producer, &consumer, kTestPipeCapacity);

  base::WaitableEvent wait(base::WaitableEvent::ResetPolicy::MANUAL,
                           base::WaitableEvent::InitialState::NOT_SIGNALED);
  TriggerHelper helper;
  int num_expected_notifications = 1;
  const uintptr_t readable_consumer_context =
      helper.CreateContext([&](const MojoTrapEvent& event) {
        EXPECT_GT(num_expected_notifications, 0);
        num_expected_notifications -= 1;

        EXPECT_EQ(MOJO_RESULT_OK, event.result);
        wait.Signal();
      });

  MojoHandle t;
  EXPECT_EQ(MOJO_RESULT_OK, helper.CreateTrap(&t));
  EXPECT_EQ(MOJO_RESULT_OK,
            MojoAddTrigger(t, consumer, MOJO_HANDLE_SIGNAL_READABLE,
                           MOJO_TRIGGER_CONDITION_SIGNALS_SATISFIED,
                           readable_consumer_context, nullptr));
  EXPECT_EQ(MOJO_RESULT_OK, MojoArmTrap(t, nullptr, nullptr, nullptr));

  const char kMessage1[] = "hey hey hey hey";
  const char kMessage2[] = "i said hey";
  const char kMessage3[] = "what's goin' on?";

  // Writing to |producer| multiple times should notify exactly once.
  WriteData(producer, kMessage1);
  WriteData(producer, kMessage2);
  wait.Wait();

  // This also shouldn't fire a notification; the trap is still disarmed.
  WriteData(producer, kMessage3);

  // Arming should fail with relevant information.
  constexpr size_t kMaxBlockingEvents = 3;
  uint32_t num_blocking_events = kMaxBlockingEvents;
  MojoTrapEvent blocking_events[kMaxBlockingEvents] = {
      {sizeof(blocking_events[0])},
      {sizeof(blocking_events[0])},
      {sizeof(blocking_events[0])}};
  EXPECT_EQ(MOJO_RESULT_FAILED_PRECONDITION,
            MojoArmTrap(t, nullptr, &num_blocking_events, &blocking_events[0]));
  EXPECT_EQ(1u, num_blocking_events);
  EXPECT_EQ(readable_consumer_context, blocking_events[0].trigger_context);
  EXPECT_EQ(MOJO_RESULT_OK, blocking_events[0].result);

  // Flush the three messages from above.
  EXPECT_EQ(kMessage1, ReadData(consumer, sizeof(kMessage1) - 1));
  EXPECT_EQ(kMessage2, ReadData(consumer, sizeof(kMessage2) - 1));
  EXPECT_EQ(kMessage3, ReadData(consumer, sizeof(kMessage3) - 1));

  // Now we can rearm the trap.
  EXPECT_EQ(MOJO_RESULT_OK, MojoArmTrap(t, nullptr, nullptr, nullptr));

  EXPECT_EQ(MOJO_RESULT_OK, MojoClose(t));
  EXPECT_EQ(MOJO_RESULT_OK, MojoClose(producer));
  EXPECT_EQ(MOJO_RESULT_OK, MojoClose(consumer));
}

TEST_F(TrapTest, TrapDataPipeConsumerNewDataReadable) {
  constexpr size_t kTestPipeCapacity = 64;
  MojoHandle producer, consumer;
  CreateDataPipe(&producer, &consumer, kTestPipeCapacity);

  base::WaitableEvent wait(base::WaitableEvent::ResetPolicy::MANUAL,
                           base::WaitableEvent::InitialState::NOT_SIGNALED);
  TriggerHelper helper;
  int num_new_data_notifications = 0;
  const uintptr_t new_data_context =
      helper.CreateContext([&](const MojoTrapEvent& event) {
        num_new_data_notifications += 1;

        EXPECT_EQ(MOJO_RESULT_OK, event.result);
        wait.Signal();
      });

  MojoHandle t;
  EXPECT_EQ(MOJO_RESULT_OK, helper.CreateTrap(&t));
  EXPECT_EQ(MOJO_RESULT_OK,
            MojoAddTrigger(t, consumer, MOJO_HANDLE_SIGNAL_NEW_DATA_READABLE,
                           MOJO_TRIGGER_CONDITION_SIGNALS_SATISFIED,
                           new_data_context, nullptr));
  EXPECT_EQ(MOJO_RESULT_OK, MojoArmTrap(t, nullptr, nullptr, nullptr));

  const char kMessage1[] = "hey hey hey hey";
  const char kMessage2[] = "i said hey";
  const char kMessage3[] = "what's goin' on?";

  // Writing to |producer| multiple times should notify exactly once.
  WriteData(producer, kMessage1);
  WriteData(producer, kMessage2);
  wait.Wait();

  // This also shouldn't fire a notification; the trap is still disarmed.
  WriteData(producer, kMessage3);

  // Arming should fail with relevant information.
  constexpr size_t kMaxBlockingEvents = 3;
  uint32_t num_blocking_events = kMaxBlockingEvents;
  MojoTrapEvent blocking_events[kMaxBlockingEvents] = {
      {sizeof(blocking_events[0])},
      {sizeof(blocking_events[0])},
      {sizeof(blocking_events[0])}};
  EXPECT_EQ(MOJO_RESULT_FAILED_PRECONDITION,
            MojoArmTrap(t, nullptr, &num_blocking_events, &blocking_events[0]));
  EXPECT_EQ(1u, num_blocking_events);
  EXPECT_EQ(new_data_context, blocking_events[0].trigger_context);
  EXPECT_EQ(MOJO_RESULT_OK, blocking_events[0].result);

  // Attempt to read more data than is available. Should fail but clear the
  // NEW_DATA_READABLE signal.
  char large_buffer[512];
  uint32_t large_read_size = 512;
  MojoReadDataOptions options;
  options.struct_size = sizeof(options);
  options.flags = MOJO_READ_DATA_FLAG_ALL_OR_NONE;
  EXPECT_EQ(MOJO_RESULT_OUT_OF_RANGE,
            MojoReadData(consumer, &options, large_buffer, &large_read_size));

  // Attempt to arm again. Should succeed.
  EXPECT_EQ(MOJO_RESULT_OK, MojoArmTrap(t, nullptr, nullptr, nullptr));

  // Write more data. Should notify.
  wait.Reset();
  WriteData(producer, kMessage1);
  wait.Wait();

  // Reading some data should clear NEW_DATA_READABLE again so we can rearm.
  EXPECT_EQ(kMessage1, ReadData(consumer, sizeof(kMessage1) - 1));

  EXPECT_EQ(MOJO_RESULT_OK, MojoArmTrap(t, nullptr, nullptr, nullptr));

  EXPECT_EQ(2, num_new_data_notifications);

  EXPECT_EQ(MOJO_RESULT_OK, MojoClose(t));
  EXPECT_EQ(MOJO_RESULT_OK, MojoClose(producer));
  EXPECT_EQ(MOJO_RESULT_OK, MojoClose(consumer));
}

TEST_F(TrapTest, TrapDataPipeProducerWritable) {
  constexpr size_t kTestPipeCapacity = 8;
  MojoHandle producer, consumer;
  CreateDataPipe(&producer, &consumer, kTestPipeCapacity);

  // Half the capacity of the data pipe.
  const char kTestData[] = "aaaa";
  static_assert((sizeof(kTestData) - 1) * 2 == kTestPipeCapacity,
                "Invalid test data for this test.");

  base::WaitableEvent wait(base::WaitableEvent::ResetPolicy::MANUAL,
                           base::WaitableEvent::InitialState::NOT_SIGNALED);
  TriggerHelper helper;
  int num_expected_notifications = 1;
  const uintptr_t writable_producer_context =
      helper.CreateContext([&](const MojoTrapEvent& event) {
        EXPECT_GT(num_expected_notifications, 0);
        num_expected_notifications -= 1;

        EXPECT_EQ(MOJO_RESULT_OK, event.result);
        wait.Signal();
      });

  MojoHandle t;
  EXPECT_EQ(MOJO_RESULT_OK, helper.CreateTrap(&t));
  EXPECT_EQ(MOJO_RESULT_OK,
            MojoAddTrigger(t, producer, MOJO_HANDLE_SIGNAL_WRITABLE,
                           MOJO_TRIGGER_CONDITION_SIGNALS_SATISFIED,
                           writable_producer_context, nullptr));

  // The producer is already writable, so arming should fail with relevant
  // information.
  constexpr size_t kMaxBlockingEvents = 3;
  uint32_t num_blocking_events = kMaxBlockingEvents;
  MojoTrapEvent blocking_events[kMaxBlockingEvents] = {
      {sizeof(blocking_events[0])},
      {sizeof(blocking_events[0])},
      {sizeof(blocking_events[0])}};
  EXPECT_EQ(MOJO_RESULT_FAILED_PRECONDITION,
            MojoArmTrap(t, nullptr, &num_blocking_events, &blocking_events[0]));
  EXPECT_EQ(1u, num_blocking_events);
  EXPECT_EQ(writable_producer_context, blocking_events[0].trigger_context);
  EXPECT_EQ(MOJO_RESULT_OK, blocking_events[0].result);
  EXPECT_TRUE(blocking_events[0].signals_state.satisfied_signals &
              MOJO_HANDLE_SIGNAL_WRITABLE);

  // Write some data, but don't fill the pipe yet. Arming should fail again.
  WriteData(producer, kTestData);
  EXPECT_EQ(MOJO_RESULT_FAILED_PRECONDITION,
            MojoArmTrap(t, nullptr, &num_blocking_events, &blocking_events[0]));
  EXPECT_EQ(1u, num_blocking_events);
  EXPECT_EQ(writable_producer_context, blocking_events[0].trigger_context);
  EXPECT_EQ(MOJO_RESULT_OK, blocking_events[0].result);
  EXPECT_TRUE(blocking_events[0].signals_state.satisfied_signals &
              MOJO_HANDLE_SIGNAL_WRITABLE);

  // Write more data, filling the pipe to capacity. Arming should succeed now.
  WriteData(producer, kTestData);
  EXPECT_EQ(MOJO_RESULT_OK, MojoArmTrap(t, nullptr, nullptr, nullptr));

  // Now read from the pipe, making the producer writable again. Should notify.
  EXPECT_EQ(kTestData, ReadData(consumer, sizeof(kTestData) - 1));
  wait.Wait();

  // Arming should fail again.
  EXPECT_EQ(MOJO_RESULT_FAILED_PRECONDITION,
            MojoArmTrap(t, nullptr, &num_blocking_events, &blocking_events[0]));
  EXPECT_EQ(1u, num_blocking_events);
  EXPECT_EQ(writable_producer_context, blocking_events[0].trigger_context);
  EXPECT_EQ(MOJO_RESULT_OK, blocking_events[0].result);
  EXPECT_TRUE(blocking_events[0].signals_state.satisfied_signals &
              MOJO_HANDLE_SIGNAL_WRITABLE);

  // Fill the pipe once more and arm the trap. Should succeed.
  WriteData(producer, kTestData);
  EXPECT_EQ(MOJO_RESULT_OK, MojoArmTrap(t, nullptr, nullptr, nullptr));

  EXPECT_EQ(MOJO_RESULT_OK, MojoClose(t));
  EXPECT_EQ(MOJO_RESULT_OK, MojoClose(producer));
  EXPECT_EQ(MOJO_RESULT_OK, MojoClose(consumer));
};

TEST_F(TrapTest, CloseWatchedDataPipeConsumerHandle) {
  constexpr size_t kTestPipeCapacity = 8;
  MojoHandle producer, consumer;
  CreateDataPipe(&producer, &consumer, kTestPipeCapacity);

  base::WaitableEvent wait(base::WaitableEvent::ResetPolicy::MANUAL,
                           base::WaitableEvent::InitialState::NOT_SIGNALED);
  TriggerHelper helper;
  const uintptr_t readable_consumer_context = helper.CreateContextWithCancel(
      [](const MojoTrapEvent&) {}, [&] { wait.Signal(); });

  MojoHandle t;
  EXPECT_EQ(MOJO_RESULT_OK, helper.CreateTrap(&t));
  EXPECT_EQ(MOJO_RESULT_OK,
            MojoAddTrigger(t, consumer, MOJO_HANDLE_SIGNAL_READABLE,
                           MOJO_TRIGGER_CONDITION_SIGNALS_SATISFIED,
                           readable_consumer_context, nullptr));

  // Closing the consumer should fire a cancellation notification.
  EXPECT_EQ(MOJO_RESULT_OK, MojoClose(consumer));
  wait.Wait();

  EXPECT_EQ(MOJO_RESULT_OK, MojoClose(producer));
  EXPECT_EQ(MOJO_RESULT_OK, MojoClose(t));
}

TEST_F(TrapTest, CloseWatchedDataPipeConsumerHandlePeer) {
  constexpr size_t kTestPipeCapacity = 8;
  MojoHandle producer, consumer;
  CreateDataPipe(&producer, &consumer, kTestPipeCapacity);

  base::WaitableEvent wait(base::WaitableEvent::ResetPolicy::MANUAL,
                           base::WaitableEvent::InitialState::NOT_SIGNALED);
  TriggerHelper helper;
  const uintptr_t readable_consumer_context =
      helper.CreateContext([&](const MojoTrapEvent& event) {
        EXPECT_EQ(MOJO_RESULT_FAILED_PRECONDITION, event.result);
        wait.Signal();
      });

  MojoHandle t;
  EXPECT_EQ(MOJO_RESULT_OK, helper.CreateTrap(&t));
  EXPECT_EQ(MOJO_RESULT_OK,
            MojoAddTrigger(t, consumer, MOJO_HANDLE_SIGNAL_READABLE,
                           MOJO_TRIGGER_CONDITION_SIGNALS_SATISFIED,
                           readable_consumer_context, nullptr));
  EXPECT_EQ(MOJO_RESULT_OK, MojoArmTrap(t, nullptr, nullptr, nullptr));

  // Closing the producer should fire a notification for an unsatisfiable
  // condition.
  EXPECT_EQ(MOJO_RESULT_OK, MojoClose(producer));
  wait.Wait();

  // Now attempt to rearm and expect appropriate error feedback.
  constexpr size_t kMaxBlockingEvents = 3;
  uint32_t num_blocking_events = kMaxBlockingEvents;
  MojoTrapEvent blocking_events[kMaxBlockingEvents] = {
      {sizeof(blocking_events[0])},
      {sizeof(blocking_events[0])},
      {sizeof(blocking_events[0])}};
  EXPECT_EQ(MOJO_RESULT_FAILED_PRECONDITION,
            MojoArmTrap(t, nullptr, &num_blocking_events, &blocking_events[0]));
  EXPECT_EQ(1u, num_blocking_events);
  EXPECT_EQ(readable_consumer_context, blocking_events[0].trigger_context);
  EXPECT_EQ(MOJO_RESULT_FAILED_PRECONDITION, blocking_events[0].result);
  EXPECT_FALSE(blocking_events[0].signals_state.satisfiable_signals &
               MOJO_HANDLE_SIGNAL_READABLE);

  EXPECT_EQ(MOJO_RESULT_OK, MojoClose(t));
  EXPECT_EQ(MOJO_RESULT_OK, MojoClose(consumer));
}

TEST_F(TrapTest, CloseWatchedDataPipeProducerHandle) {
  constexpr size_t kTestPipeCapacity = 8;
  MojoHandle producer, consumer;
  CreateDataPipe(&producer, &consumer, kTestPipeCapacity);

  base::WaitableEvent wait(base::WaitableEvent::ResetPolicy::MANUAL,
                           base::WaitableEvent::InitialState::NOT_SIGNALED);
  TriggerHelper helper;
  const uintptr_t writable_producer_context = helper.CreateContextWithCancel(
      [](const MojoTrapEvent&) {}, [&] { wait.Signal(); });

  MojoHandle t;
  EXPECT_EQ(MOJO_RESULT_OK, helper.CreateTrap(&t));
  EXPECT_EQ(MOJO_RESULT_OK,
            MojoAddTrigger(t, producer, MOJO_HANDLE_SIGNAL_WRITABLE,
                           MOJO_TRIGGER_CONDITION_SIGNALS_SATISFIED,
                           writable_producer_context, nullptr));

  // Closing the consumer should fire a cancellation notification.
  EXPECT_EQ(MOJO_RESULT_OK, MojoClose(producer));
  wait.Wait();

  EXPECT_EQ(MOJO_RESULT_OK, MojoClose(consumer));
  EXPECT_EQ(MOJO_RESULT_OK, MojoClose(t));
}

TEST_F(TrapTest, CloseWatchedDataPipeProducerHandlePeer) {
  constexpr size_t kTestPipeCapacity = 8;
  MojoHandle producer, consumer;
  CreateDataPipe(&producer, &consumer, kTestPipeCapacity);

  const char kTestMessageFullCapacity[] = "xxxxxxxx";
  static_assert(sizeof(kTestMessageFullCapacity) - 1 == kTestPipeCapacity,
                "Invalid test message size for this test.");

  // Make the pipe unwritable initially.
  WriteData(producer, kTestMessageFullCapacity);

  base::WaitableEvent wait(base::WaitableEvent::ResetPolicy::MANUAL,
                           base::WaitableEvent::InitialState::NOT_SIGNALED);
  TriggerHelper helper;
  const uintptr_t writable_producer_context =
      helper.CreateContext([&](const MojoTrapEvent& event) {
        EXPECT_EQ(MOJO_RESULT_FAILED_PRECONDITION, event.result);
        wait.Signal();
      });

  MojoHandle t;
  EXPECT_EQ(MOJO_RESULT_OK, helper.CreateTrap(&t));
  EXPECT_EQ(MOJO_RESULT_OK,
            MojoAddTrigger(t, producer, MOJO_HANDLE_SIGNAL_WRITABLE,
                           MOJO_TRIGGER_CONDITION_SIGNALS_SATISFIED,
                           writable_producer_context, nullptr));
  EXPECT_EQ(MOJO_RESULT_OK, MojoArmTrap(t, nullptr, nullptr, nullptr));

  // Closing the consumer should fire a notification for an unsatisfiable
  // condition, as the full data pipe can never be read from again and is
  // therefore permanently full and unwritable.
  EXPECT_EQ(MOJO_RESULT_OK, MojoClose(consumer));
  wait.Wait();

  // Now attempt to rearm and expect appropriate error feedback.
  constexpr size_t kMaxBlockingEvents = 3;
  uint32_t num_blocking_events = kMaxBlockingEvents;
  MojoTrapEvent blocking_events[kMaxBlockingEvents] = {
      {sizeof(blocking_events[0])},
      {sizeof(blocking_events[0])},
      {sizeof(blocking_events[0])}};
  EXPECT_EQ(MOJO_RESULT_FAILED_PRECONDITION,
            MojoArmTrap(t, nullptr, &num_blocking_events, &blocking_events[0]));
  EXPECT_EQ(1u, num_blocking_events);
  EXPECT_EQ(writable_producer_context, blocking_events[0].trigger_context);
  EXPECT_EQ(MOJO_RESULT_FAILED_PRECONDITION, blocking_events[0].result);
  EXPECT_FALSE(blocking_events[0].signals_state.satisfiable_signals &
               MOJO_HANDLE_SIGNAL_WRITABLE);

  EXPECT_EQ(MOJO_RESULT_OK, MojoClose(t));
  EXPECT_EQ(MOJO_RESULT_OK, MojoClose(producer));
}

TEST_F(TrapTest, ArmWithNoTriggers) {
  MojoHandle t;
  EXPECT_EQ(MOJO_RESULT_OK, MojoCreateTrap(&ExpectNoNotification, nullptr, &t));
  EXPECT_EQ(MOJO_RESULT_NOT_FOUND, MojoArmTrap(t, nullptr, nullptr, nullptr));
  EXPECT_EQ(MOJO_RESULT_OK, MojoClose(t));
}

TEST_F(TrapTest, DuplicateTriggerContext) {
  MojoHandle a, b;
  CreateMessagePipe(&a, &b);

  MojoHandle t;
  EXPECT_EQ(MOJO_RESULT_OK, MojoCreateTrap(&ExpectOnlyCancel, nullptr, &t));
  EXPECT_EQ(
      MOJO_RESULT_OK,
      MojoAddTrigger(t, a, MOJO_HANDLE_SIGNAL_READABLE,
                     MOJO_TRIGGER_CONDITION_SIGNALS_SATISFIED, 0, nullptr));
  EXPECT_EQ(
      MOJO_RESULT_ALREADY_EXISTS,
      MojoAddTrigger(t, b, MOJO_HANDLE_SIGNAL_READABLE,
                     MOJO_TRIGGER_CONDITION_SIGNALS_SATISFIED, 0, nullptr));

  EXPECT_EQ(MOJO_RESULT_OK, MojoClose(t));
  EXPECT_EQ(MOJO_RESULT_OK, MojoClose(a));
  EXPECT_EQ(MOJO_RESULT_OK, MojoClose(b));
}

TEST_F(TrapTest, RemoveUnknownTrigger) {
  MojoHandle t;
  EXPECT_EQ(MOJO_RESULT_OK, MojoCreateTrap(&ExpectNoNotification, nullptr, &t));
  EXPECT_EQ(MOJO_RESULT_NOT_FOUND, MojoRemoveTrigger(t, 1234, nullptr));
}

TEST_F(TrapTest, ArmWithTriggerConditionAlreadySatisfied) {
  MojoHandle a, b;
  CreateMessagePipe(&a, &b);

  MojoHandle t;
  EXPECT_EQ(MOJO_RESULT_OK, MojoCreateTrap(&ExpectOnlyCancel, nullptr, &t));
  EXPECT_EQ(
      MOJO_RESULT_OK,
      MojoAddTrigger(t, a, MOJO_HANDLE_SIGNAL_WRITABLE,
                     MOJO_TRIGGER_CONDITION_SIGNALS_SATISFIED, 0, nullptr));

  // |a| is always writable, so we can never arm this trap.
  constexpr size_t kMaxBlockingEvents = 3;
  uint32_t num_blocking_events = kMaxBlockingEvents;
  MojoTrapEvent blocking_events[kMaxBlockingEvents] = {
      {sizeof(blocking_events[0])},
      {sizeof(blocking_events[0])},
      {sizeof(blocking_events[0])}};
  EXPECT_EQ(MOJO_RESULT_FAILED_PRECONDITION,
            MojoArmTrap(t, nullptr, &num_blocking_events, &blocking_events[0]));
  EXPECT_EQ(1u, num_blocking_events);
  EXPECT_EQ(0u, blocking_events[0].trigger_context);
  EXPECT_EQ(MOJO_RESULT_OK, blocking_events[0].result);
  EXPECT_TRUE(blocking_events[0].signals_state.satisfied_signals &
              MOJO_HANDLE_SIGNAL_WRITABLE);

  EXPECT_EQ(MOJO_RESULT_OK, MojoClose(t));
  EXPECT_EQ(MOJO_RESULT_OK, MojoClose(b));
}

TEST_F(TrapTest, ArmWithTriggerConditionAlreadyUnsatisfiable) {
  MojoHandle a, b;
  CreateMessagePipe(&a, &b);

  MojoHandle t;
  EXPECT_EQ(MOJO_RESULT_OK, MojoCreateTrap(&ExpectOnlyCancel, nullptr, &t));
  EXPECT_EQ(
      MOJO_RESULT_OK,
      MojoAddTrigger(t, a, MOJO_HANDLE_SIGNAL_READABLE,
                     MOJO_TRIGGER_CONDITION_SIGNALS_SATISFIED, 0, nullptr));

  EXPECT_EQ(MOJO_RESULT_OK, MojoClose(b));

  // |b| is closed and never wrote any messages, so |a| won't be readable again.
  // MojoArmTrap() should fail, incidcating as much.
  constexpr size_t kMaxBlockingEvents = 3;
  uint32_t num_blocking_events = kMaxBlockingEvents;
  MojoTrapEvent blocking_events[kMaxBlockingEvents] = {
      {sizeof(blocking_events[0])},
      {sizeof(blocking_events[0])},
      {sizeof(blocking_events[0])}};
  EXPECT_EQ(MOJO_RESULT_FAILED_PRECONDITION,
            MojoArmTrap(t, nullptr, &num_blocking_events, &blocking_events[0]));
  EXPECT_EQ(1u, num_blocking_events);
  EXPECT_EQ(0u, blocking_events[0].trigger_context);
  EXPECT_EQ(MOJO_RESULT_FAILED_PRECONDITION, blocking_events[0].result);
  EXPECT_TRUE(blocking_events[0].signals_state.satisfied_signals &
              MOJO_HANDLE_SIGNAL_PEER_CLOSED);
  EXPECT_FALSE(blocking_events[0].signals_state.satisfiable_signals &
               MOJO_HANDLE_SIGNAL_READABLE);

  EXPECT_EQ(MOJO_RESULT_OK, MojoClose(t));
  EXPECT_EQ(MOJO_RESULT_OK, MojoClose(a));
}

TEST_F(TrapTest, MultipleTriggers) {
  MojoHandle a, b;
  CreateMessagePipe(&a, &b);

  base::WaitableEvent a_wait(base::WaitableEvent::ResetPolicy::MANUAL,
                             base::WaitableEvent::InitialState::NOT_SIGNALED);
  base::WaitableEvent b_wait(base::WaitableEvent::ResetPolicy::MANUAL,
                             base::WaitableEvent::InitialState::NOT_SIGNALED);
  TriggerHelper helper;
  int num_a_notifications = 0;
  int num_b_notifications = 0;
  uintptr_t readable_a_context =
      helper.CreateContext([&](const MojoTrapEvent& event) {
        num_a_notifications += 1;
        EXPECT_EQ(MOJO_RESULT_OK, event.result);
        a_wait.Signal();
      });
  uintptr_t readable_b_context =
      helper.CreateContext([&](const MojoTrapEvent& event) {
        num_b_notifications += 1;
        EXPECT_EQ(MOJO_RESULT_OK, event.result);
        b_wait.Signal();
      });

  MojoHandle t;
  EXPECT_EQ(MOJO_RESULT_OK, helper.CreateTrap(&t));

  // Add two independent triggers to trap |a| or |b| readability.
  EXPECT_EQ(MOJO_RESULT_OK,
            MojoAddTrigger(t, a, MOJO_HANDLE_SIGNAL_READABLE,
                           MOJO_TRIGGER_CONDITION_SIGNALS_SATISFIED,
                           readable_a_context, nullptr));
  EXPECT_EQ(MOJO_RESULT_OK,
            MojoAddTrigger(t, b, MOJO_HANDLE_SIGNAL_READABLE,
                           MOJO_TRIGGER_CONDITION_SIGNALS_SATISFIED,
                           readable_b_context, nullptr));

  EXPECT_EQ(MOJO_RESULT_OK, MojoArmTrap(t, nullptr, nullptr, nullptr));

  const char kMessage1[] = "things are happening";
  const char kMessage2[] = "ok. ok. ok. ok.";
  const char kMessage3[] = "plz wake up";

  // Writing to |b| should signal |a|'s watch.
  WriteMessage(b, kMessage1);
  a_wait.Wait();
  a_wait.Reset();

  // Subsequent messages on |b| should not trigger another notification.
  WriteMessage(b, kMessage2);
  WriteMessage(b, kMessage3);

  // Messages on |a| also shouldn't trigger |b|'s notification, since the
  // trap should be disarmed by now.
  WriteMessage(a, kMessage1);
  WriteMessage(a, kMessage2);
  WriteMessage(a, kMessage3);

  // Arming should fail. Since we only ask for at most one context's information
  // that's all we should get back. Which one we get is unspecified.
  constexpr size_t kMaxBlockingEvents = 3;
  uint32_t num_blocking_events = 1;
  MojoTrapEvent blocking_events[kMaxBlockingEvents] = {
      {sizeof(blocking_events[0])},
      {sizeof(blocking_events[0])},
      {sizeof(blocking_events[0])}};
  EXPECT_EQ(MOJO_RESULT_FAILED_PRECONDITION,
            MojoArmTrap(t, nullptr, &num_blocking_events, &blocking_events[0]));
  EXPECT_EQ(1u, num_blocking_events);
  EXPECT_TRUE(blocking_events[0].trigger_context == readable_a_context ||
              blocking_events[0].trigger_context == readable_b_context);
  EXPECT_EQ(MOJO_RESULT_OK, blocking_events[0].result);
  EXPECT_TRUE(blocking_events[0].signals_state.satisfied_signals &
              MOJO_HANDLE_SIGNAL_WRITABLE);

  // Now try arming again, verifying that both contexts are returned.
  num_blocking_events = kMaxBlockingEvents;
  EXPECT_EQ(MOJO_RESULT_FAILED_PRECONDITION,
            MojoArmTrap(t, nullptr, &num_blocking_events, &blocking_events[0]));
  EXPECT_EQ(2u, num_blocking_events);
  EXPECT_EQ(MOJO_RESULT_OK, blocking_events[0].result);
  EXPECT_EQ(MOJO_RESULT_OK, blocking_events[1].result);
  EXPECT_TRUE(blocking_events[0].signals_state.satisfied_signals &
              MOJO_HANDLE_SIGNAL_WRITABLE);
  EXPECT_TRUE(blocking_events[1].signals_state.satisfied_signals &
              MOJO_HANDLE_SIGNAL_WRITABLE);
  EXPECT_TRUE((blocking_events[0].trigger_context == readable_a_context &&
               blocking_events[1].trigger_context == readable_b_context) ||
              (blocking_events[0].trigger_context == readable_b_context &&
               blocking_events[1].trigger_context == readable_a_context));

  // Flush out the test messages so we should be able to successfully rearm.
  EXPECT_EQ(kMessage1, ReadMessage(a));
  EXPECT_EQ(kMessage2, ReadMessage(a));
  EXPECT_EQ(kMessage3, ReadMessage(a));
  EXPECT_EQ(kMessage1, ReadMessage(b));
  EXPECT_EQ(kMessage2, ReadMessage(b));
  EXPECT_EQ(kMessage3, ReadMessage(b));

  // Add a trigger whose condition is always satisfied so we can't arm. Arming
  // should fail with only this new watch's information.
  uintptr_t writable_c_context =
      helper.CreateContext([](const MojoTrapEvent&) { NOTREACHED(); });
  MojoHandle c, d;
  CreateMessagePipe(&c, &d);

  EXPECT_EQ(MOJO_RESULT_OK,
            MojoAddTrigger(t, c, MOJO_HANDLE_SIGNAL_WRITABLE,
                           MOJO_TRIGGER_CONDITION_SIGNALS_SATISFIED,
                           writable_c_context, nullptr));
  num_blocking_events = kMaxBlockingEvents;
  EXPECT_EQ(MOJO_RESULT_FAILED_PRECONDITION,
            MojoArmTrap(t, nullptr, &num_blocking_events, &blocking_events[0]));
  EXPECT_EQ(1u, num_blocking_events);
  EXPECT_EQ(writable_c_context, blocking_events[0].trigger_context);
  EXPECT_EQ(MOJO_RESULT_OK, blocking_events[0].result);
  EXPECT_TRUE(blocking_events[0].signals_state.satisfied_signals &
              MOJO_HANDLE_SIGNAL_WRITABLE);

  // Remove the new trigger and arming should succeed once again.
  EXPECT_EQ(MOJO_RESULT_OK, MojoRemoveTrigger(t, writable_c_context, nullptr));
  EXPECT_EQ(MOJO_RESULT_OK, MojoArmTrap(t, nullptr, nullptr, nullptr));

  EXPECT_EQ(MOJO_RESULT_OK, MojoClose(t));
  EXPECT_EQ(MOJO_RESULT_OK, MojoClose(a));
  EXPECT_EQ(MOJO_RESULT_OK, MojoClose(b));
  EXPECT_EQ(MOJO_RESULT_OK, MojoClose(c));
  EXPECT_EQ(MOJO_RESULT_OK, MojoClose(d));
}

TEST_F(TrapTest, ActivateOtherTriggerFromEventHandler) {
  MojoHandle a, b;
  CreateMessagePipe(&a, &b);

  static const char kTestMessageToA[] = "hello a";
  static const char kTestMessageToB[] = "hello b";

  base::WaitableEvent wait(base::WaitableEvent::ResetPolicy::MANUAL,
                           base::WaitableEvent::InitialState::NOT_SIGNALED);

  TriggerHelper helper;
  MojoHandle t;
  EXPECT_EQ(MOJO_RESULT_OK, helper.CreateTrap(&t));

  uintptr_t readable_a_context =
      helper.CreateContext([&](const MojoTrapEvent& event) {
        EXPECT_EQ(MOJO_RESULT_OK, event.result);
        EXPECT_EQ("hello a", ReadMessage(a));

        // Re-arm the trap and signal |b|.
        EXPECT_EQ(MOJO_RESULT_OK, MojoArmTrap(t, nullptr, nullptr, nullptr));
        WriteMessage(a, kTestMessageToB);
      });

  uintptr_t readable_b_context =
      helper.CreateContext([&](const MojoTrapEvent& event) {
        EXPECT_EQ(MOJO_RESULT_OK, event.result);
        EXPECT_EQ(kTestMessageToB, ReadMessage(b));
        EXPECT_EQ(MOJO_RESULT_OK, MojoArmTrap(t, nullptr, nullptr, nullptr));
        wait.Signal();
      });

  EXPECT_EQ(MOJO_RESULT_OK,
            MojoAddTrigger(t, a, MOJO_HANDLE_SIGNAL_READABLE,
                           MOJO_TRIGGER_CONDITION_SIGNALS_SATISFIED,
                           readable_a_context, nullptr));
  EXPECT_EQ(MOJO_RESULT_OK,
            MojoAddTrigger(t, b, MOJO_HANDLE_SIGNAL_READABLE,
                           MOJO_TRIGGER_CONDITION_SIGNALS_SATISFIED,
                           readable_b_context, nullptr));
  EXPECT_EQ(MOJO_RESULT_OK, MojoArmTrap(t, nullptr, nullptr, nullptr));

  // Send a message to |a|. The relevant trigger should be notified and the
  // event handler should send a message to |b|, in turn notifying the other
  // trigger. The second event handler will signal |wait|.
  WriteMessage(b, kTestMessageToA);
  wait.Wait();
}

TEST_F(TrapTest, ActivateSameTriggerFromEventHandler) {
  MojoHandle a, b;
  CreateMessagePipe(&a, &b);

  static const char kTestMessageToA[] = "hello a";

  base::WaitableEvent wait(base::WaitableEvent::ResetPolicy::MANUAL,
                           base::WaitableEvent::InitialState::NOT_SIGNALED);

  TriggerHelper helper;
  MojoHandle t;
  EXPECT_EQ(MOJO_RESULT_OK, helper.CreateTrap(&t));

  int expected_notifications = 10;
  uintptr_t readable_a_context =
      helper.CreateContext([&](const MojoTrapEvent& event) {
        EXPECT_EQ(MOJO_RESULT_OK, event.result);
        EXPECT_EQ("hello a", ReadMessage(a));

        EXPECT_GT(expected_notifications, 0);
        expected_notifications -= 1;
        if (expected_notifications == 0) {
          wait.Signal();
          return;
        } else {
          // Re-arm the trap and signal |a| again.
          EXPECT_EQ(MOJO_RESULT_OK, MojoArmTrap(t, nullptr, nullptr, nullptr));
          WriteMessage(b, kTestMessageToA);
        }
      });

  EXPECT_EQ(MOJO_RESULT_OK,
            MojoAddTrigger(t, a, MOJO_HANDLE_SIGNAL_READABLE,
                           MOJO_TRIGGER_CONDITION_SIGNALS_SATISFIED,
                           readable_a_context, nullptr));
  EXPECT_EQ(MOJO_RESULT_OK, MojoArmTrap(t, nullptr, nullptr, nullptr));

  // Send a message to |a|. When the trigger above is activated, the event
  // handler will rearm the trap and send another message to |a|. This will
  // happen until |expected_notifications| reaches 0.
  WriteMessage(b, kTestMessageToA);
  wait.Wait();
}

TEST_F(TrapTest, ImplicitRemoveOtherTriggerWithinEventHandler) {
  MojoHandle a, b;
  CreateMessagePipe(&a, &b);

  MojoHandle c, d;
  CreateMessagePipe(&c, &d);

  static const char kTestMessageToA[] = "hi a";
  static const char kTestMessageToC[] = "hi c";

  base::WaitableEvent wait(base::WaitableEvent::ResetPolicy::MANUAL,
                           base::WaitableEvent::InitialState::NOT_SIGNALED);

  TriggerHelper helper;
  MojoHandle t;
  EXPECT_EQ(MOJO_RESULT_OK, helper.CreateTrap(&t));

  uintptr_t readable_a_context = helper.CreateContextWithCancel(
      [](const MojoTrapEvent&) { NOTREACHED(); }, [&] { wait.Signal(); });

  uintptr_t readable_c_context =
      helper.CreateContext([&](const MojoTrapEvent& event) {
        EXPECT_EQ(MOJO_RESULT_OK, event.result);
        EXPECT_EQ(kTestMessageToC, ReadMessage(c));

        EXPECT_EQ(MOJO_RESULT_OK, MojoArmTrap(t, nullptr, nullptr, nullptr));

        // Must result in exactly ONE notification from the above trigger, for
        // CANCELLED only. Because we cannot dispatch notifications until the
        // stack unwinds, and because we must never dispatch non-cancellation
        // notifications for a handle once it's been closed, we must be certain
        // that cancellation due to closure preemptively invalidates any
        // pending non-cancellation notifications queued on the current
        // RequestContext, such as the one resulting from the WriteMessage here.
        WriteMessage(b, kTestMessageToA);
        EXPECT_EQ(MOJO_RESULT_OK, MojoClose(a));

        // Rearming should be fine since |a|'s trigger should already be
        // implicitly removed (even though the notification will not have
        // been invoked yet.)
        EXPECT_EQ(MOJO_RESULT_OK, MojoArmTrap(t, nullptr, nullptr, nullptr));

        // Nothing interesting should happen as a result of this.
        EXPECT_EQ(MOJO_RESULT_OK, MojoClose(b));
      });

  EXPECT_EQ(MOJO_RESULT_OK,
            MojoAddTrigger(t, a, MOJO_HANDLE_SIGNAL_READABLE,
                           MOJO_TRIGGER_CONDITION_SIGNALS_SATISFIED,
                           readable_a_context, nullptr));
  EXPECT_EQ(MOJO_RESULT_OK,
            MojoAddTrigger(t, c, MOJO_HANDLE_SIGNAL_READABLE,
                           MOJO_TRIGGER_CONDITION_SIGNALS_SATISFIED,
                           readable_c_context, nullptr));
  EXPECT_EQ(MOJO_RESULT_OK, MojoArmTrap(t, nullptr, nullptr, nullptr));

  WriteMessage(d, kTestMessageToC);
  wait.Wait();

  EXPECT_EQ(MOJO_RESULT_OK, MojoClose(t));
  EXPECT_EQ(MOJO_RESULT_OK, MojoClose(c));
  EXPECT_EQ(MOJO_RESULT_OK, MojoClose(d));
}

TEST_F(TrapTest, ExplicitRemoveOtherTriggerWithinEventHandler) {
  MojoHandle a, b;
  CreateMessagePipe(&a, &b);

  MojoHandle c, d;
  CreateMessagePipe(&c, &d);

  static const char kTestMessageToA[] = "hi a";
  static const char kTestMessageToC[] = "hi c";

  base::WaitableEvent wait(base::WaitableEvent::ResetPolicy::MANUAL,
                           base::WaitableEvent::InitialState::NOT_SIGNALED);

  TriggerHelper helper;
  MojoHandle t;
  EXPECT_EQ(MOJO_RESULT_OK, helper.CreateTrap(&t));

  uintptr_t readable_a_context =
      helper.CreateContext([](const MojoTrapEvent&) { NOTREACHED(); });

  uintptr_t readable_c_context =
      helper.CreateContext([&](const MojoTrapEvent& event) {
        EXPECT_EQ(MOJO_RESULT_OK, event.result);
        EXPECT_EQ(kTestMessageToC, ReadMessage(c));

        // Now rearm the trap.
        EXPECT_EQ(MOJO_RESULT_OK, MojoArmTrap(t, nullptr, nullptr, nullptr));

        // Should result in no notifications from the above trigger, because the
        // trigger will have been removed by the time the event handler can
        // execute.
        WriteMessage(b, kTestMessageToA);
        WriteMessage(b, kTestMessageToA);
        EXPECT_EQ(MOJO_RESULT_OK,
                  MojoRemoveTrigger(t, readable_a_context, nullptr));

        // Rearming should be fine now.
        EXPECT_EQ(MOJO_RESULT_OK, MojoArmTrap(t, nullptr, nullptr, nullptr));

        // Nothing interesting should happen as a result of these.
        EXPECT_EQ(MOJO_RESULT_OK, MojoClose(a));
        EXPECT_EQ(MOJO_RESULT_OK, MojoClose(b));

        wait.Signal();
      });

  EXPECT_EQ(MOJO_RESULT_OK,
            MojoAddTrigger(t, a, MOJO_HANDLE_SIGNAL_READABLE,
                           MOJO_TRIGGER_CONDITION_SIGNALS_SATISFIED,
                           readable_a_context, nullptr));
  EXPECT_EQ(MOJO_RESULT_OK,
            MojoAddTrigger(t, c, MOJO_HANDLE_SIGNAL_READABLE,
                           MOJO_TRIGGER_CONDITION_SIGNALS_SATISFIED,
                           readable_c_context, nullptr));
  EXPECT_EQ(MOJO_RESULT_OK, MojoArmTrap(t, nullptr, nullptr, nullptr));

  WriteMessage(d, kTestMessageToC);
  wait.Wait();

  EXPECT_EQ(MOJO_RESULT_OK, MojoClose(t));
  EXPECT_EQ(MOJO_RESULT_OK, MojoClose(c));
  EXPECT_EQ(MOJO_RESULT_OK, MojoClose(d));
}

TEST_F(TrapTest, NestedCancellation) {
  MojoHandle a, b;
  CreateMessagePipe(&a, &b);

  MojoHandle c, d;
  CreateMessagePipe(&c, &d);

  static const char kTestMessageToA[] = "hey a";
  static const char kTestMessageToC[] = "hey c";
  static const char kTestMessageToD[] = "hey d";

  // This is a tricky test. It establishes a trigger on |b| using one trap and
  // triggers on |c| and |d| using another trap.
  //
  // A message is written to |d| to activate |c|'s trigger, and the resuling
  // event handler invocation does the folllowing:
  //   1. Writes to |a| to eventually activate |b|'s trigger.
  //   2. Rearms |c|'s trap.
  //   3. Writes to |d| to eventually activate |c|'s trigger again.
  //
  // Meanwhile, |b|'s event handler removes |c|'s trigger altogether before
  // writing to |c| to activate |d|'s trigger.
  //
  // The net result should be that |c|'s trigger only gets activated once (from
  // the first write to |d| above) and everyone else gets notified as expected.

  MojoHandle b_trap;
  MojoHandle cd_trap;
  TriggerHelper helper;
  EXPECT_EQ(MOJO_RESULT_OK, helper.CreateTrap(&b_trap));
  EXPECT_EQ(MOJO_RESULT_OK, helper.CreateTrap(&cd_trap));

  base::WaitableEvent wait(base::WaitableEvent::ResetPolicy::MANUAL,
                           base::WaitableEvent::InitialState::NOT_SIGNALED);
  uintptr_t readable_d_context =
      helper.CreateContext([&](const MojoTrapEvent& event) {
        EXPECT_EQ(MOJO_RESULT_OK, event.result);
        EXPECT_EQ(kTestMessageToD, ReadMessage(d));
        wait.Signal();
      });

  int num_expected_c_notifications = 1;
  uintptr_t readable_c_context =
      helper.CreateContext([&](const MojoTrapEvent& event) {
        EXPECT_EQ(MOJO_RESULT_OK, event.result);
        EXPECT_GT(num_expected_c_notifications--, 0);

        // Trigger an eventual |readable_b_context| notification.
        WriteMessage(a, kTestMessageToA);

        EXPECT_EQ(kTestMessageToC, ReadMessage(c));
        EXPECT_EQ(MOJO_RESULT_OK,
                  MojoArmTrap(cd_trap, nullptr, nullptr, nullptr));

        // Trigger another eventual |readable_c_context| notification.
        WriteMessage(d, kTestMessageToC);
      });

  uintptr_t readable_b_context =
      helper.CreateContext([&](const MojoTrapEvent& event) {
        EXPECT_EQ(MOJO_RESULT_OK,
                  MojoRemoveTrigger(cd_trap, readable_c_context, nullptr));

        EXPECT_EQ(MOJO_RESULT_OK,
                  MojoArmTrap(cd_trap, nullptr, nullptr, nullptr));

        WriteMessage(c, kTestMessageToD);
      });

  EXPECT_EQ(MOJO_RESULT_OK,
            MojoAddTrigger(b_trap, b, MOJO_HANDLE_SIGNAL_READABLE,
                           MOJO_TRIGGER_CONDITION_SIGNALS_SATISFIED,
                           readable_b_context, nullptr));
  EXPECT_EQ(MOJO_RESULT_OK,
            MojoAddTrigger(cd_trap, c, MOJO_HANDLE_SIGNAL_READABLE,
                           MOJO_TRIGGER_CONDITION_SIGNALS_SATISFIED,
                           readable_c_context, nullptr));
  EXPECT_EQ(MOJO_RESULT_OK,
            MojoAddTrigger(cd_trap, d, MOJO_HANDLE_SIGNAL_READABLE,
                           MOJO_TRIGGER_CONDITION_SIGNALS_SATISFIED,
                           readable_d_context, nullptr));

  EXPECT_EQ(MOJO_RESULT_OK, MojoArmTrap(b_trap, nullptr, nullptr, nullptr));
  EXPECT_EQ(MOJO_RESULT_OK, MojoArmTrap(cd_trap, nullptr, nullptr, nullptr));

  WriteMessage(d, kTestMessageToC);
  wait.Wait();

  EXPECT_EQ(MOJO_RESULT_OK, MojoClose(cd_trap));
  EXPECT_EQ(MOJO_RESULT_OK, MojoClose(b_trap));
  EXPECT_EQ(MOJO_RESULT_OK, MojoClose(a));
  EXPECT_EQ(MOJO_RESULT_OK, MojoClose(b));
  EXPECT_EQ(MOJO_RESULT_OK, MojoClose(c));
  EXPECT_EQ(MOJO_RESULT_OK, MojoClose(d));
}

TEST_F(TrapTest, RemoveSelfWithinEventHandler) {
  MojoHandle a, b;
  CreateMessagePipe(&a, &b);

  static const char kTestMessageToA[] = "hey a";

  MojoHandle t;
  TriggerHelper helper;
  EXPECT_EQ(MOJO_RESULT_OK, helper.CreateTrap(&t));

  base::WaitableEvent wait(base::WaitableEvent::ResetPolicy::MANUAL,
                           base::WaitableEvent::InitialState::NOT_SIGNALED);

  static uintptr_t readable_a_context =
      helper.CreateContext([&](const MojoTrapEvent& event) {
        EXPECT_EQ(MOJO_RESULT_OK, event.result);

        // There should be no problem removing this trigger from its own
        // notification invocation.
        EXPECT_EQ(MOJO_RESULT_OK,
                  MojoRemoveTrigger(t, readable_a_context, nullptr));
        EXPECT_EQ(kTestMessageToA, ReadMessage(a));

        // Arming should fail because there are no longer any registered
        // triggers on the trap.
        EXPECT_EQ(MOJO_RESULT_NOT_FOUND,
                  MojoArmTrap(t, nullptr, nullptr, nullptr));

        // And closing |a| should be fine (and should not invoke this
        // notification with MOJO_RESULT_CANCELLED) for the same reason.
        EXPECT_EQ(MOJO_RESULT_OK, MojoClose(a));

        wait.Signal();
      });

  EXPECT_EQ(MOJO_RESULT_OK,
            MojoAddTrigger(t, a, MOJO_HANDLE_SIGNAL_READABLE,
                           MOJO_TRIGGER_CONDITION_SIGNALS_SATISFIED,
                           readable_a_context, nullptr));
  EXPECT_EQ(MOJO_RESULT_OK, MojoArmTrap(t, nullptr, nullptr, nullptr));

  WriteMessage(b, kTestMessageToA);
  wait.Wait();

  EXPECT_EQ(MOJO_RESULT_OK, MojoClose(b));
  EXPECT_EQ(MOJO_RESULT_OK, MojoClose(t));
}

TEST_F(TrapTest, CloseTrapWithinEventHandler) {
  MojoHandle a, b;
  CreateMessagePipe(&a, &b);

  static const char kTestMessageToA1[] = "hey a";
  static const char kTestMessageToA2[] = "hey a again";

  MojoHandle t;
  TriggerHelper helper;
  EXPECT_EQ(MOJO_RESULT_OK, helper.CreateTrap(&t));

  base::WaitableEvent wait(base::WaitableEvent::ResetPolicy::MANUAL,
                           base::WaitableEvent::InitialState::NOT_SIGNALED);

  uintptr_t readable_a_context =
      helper.CreateContext([&](const MojoTrapEvent& event) {
        EXPECT_EQ(MOJO_RESULT_OK, event.result);
        EXPECT_EQ(kTestMessageToA1, ReadMessage(a));
        EXPECT_EQ(MOJO_RESULT_OK, MojoArmTrap(t, nullptr, nullptr, nullptr));

        // There should be no problem closing this trap from its own
        // notification callback.
        EXPECT_EQ(MOJO_RESULT_OK, MojoClose(t));

        // And these should not trigger more notifications, because |t| has been
        // closed already.
        WriteMessage(b, kTestMessageToA2);
        EXPECT_EQ(MOJO_RESULT_OK, MojoClose(b));
        EXPECT_EQ(MOJO_RESULT_OK, MojoClose(a));

        wait.Signal();
      });

  EXPECT_EQ(MOJO_RESULT_OK,
            MojoAddTrigger(t, a, MOJO_HANDLE_SIGNAL_READABLE,
                           MOJO_TRIGGER_CONDITION_SIGNALS_SATISFIED,
                           readable_a_context, nullptr));
  EXPECT_EQ(MOJO_RESULT_OK, MojoArmTrap(t, nullptr, nullptr, nullptr));

  WriteMessage(b, kTestMessageToA1);
  wait.Wait();
}

TEST_F(TrapTest, CloseTrapAfterImplicitTriggerRemoval) {
  MojoHandle a, b;
  CreateMessagePipe(&a, &b);

  static const char kTestMessageToA[] = "hey a";

  MojoHandle t;
  TriggerHelper helper;
  EXPECT_EQ(MOJO_RESULT_OK, helper.CreateTrap(&t));

  base::WaitableEvent wait(base::WaitableEvent::ResetPolicy::MANUAL,
                           base::WaitableEvent::InitialState::NOT_SIGNALED);

  uintptr_t readable_a_context =
      helper.CreateContext([&](const MojoTrapEvent& event) {
        EXPECT_EQ(MOJO_RESULT_OK, event.result);
        EXPECT_EQ(kTestMessageToA, ReadMessage(a));
        EXPECT_EQ(MOJO_RESULT_OK, MojoArmTrap(t, nullptr, nullptr, nullptr));

        // This will cue up a notification for |MOJO_RESULT_CANCELLED|...
        EXPECT_EQ(MOJO_RESULT_OK, MojoClose(a));

        // ...but it should never fire because we close the trap here.
        EXPECT_EQ(MOJO_RESULT_OK, MojoClose(t));

        wait.Signal();
      });

  EXPECT_EQ(MOJO_RESULT_OK,
            MojoAddTrigger(t, a, MOJO_HANDLE_SIGNAL_READABLE,
                           MOJO_TRIGGER_CONDITION_SIGNALS_SATISFIED,
                           readable_a_context, nullptr));
  EXPECT_EQ(MOJO_RESULT_OK, MojoArmTrap(t, nullptr, nullptr, nullptr));

  WriteMessage(b, kTestMessageToA);
  wait.Wait();

  EXPECT_EQ(MOJO_RESULT_OK, MojoClose(b));
}

TEST_F(TrapTest, OtherThreadRemovesTriggerDuringEventHandler) {
  MojoHandle a, b;
  CreateMessagePipe(&a, &b);

  static const char kTestMessageToA[] = "hey a";

  MojoHandle t;
  TriggerHelper helper;
  EXPECT_EQ(MOJO_RESULT_OK, helper.CreateTrap(&t));

  base::WaitableEvent wait_for_notification(
      base::WaitableEvent::ResetPolicy::MANUAL,
      base::WaitableEvent::InitialState::NOT_SIGNALED);

  base::WaitableEvent wait_for_cancellation(
      base::WaitableEvent::ResetPolicy::MANUAL,
      base::WaitableEvent::InitialState::NOT_SIGNALED);

  static bool callback_done = false;
  uintptr_t readable_a_context = helper.CreateContextWithCancel(
      [&](const MojoTrapEvent& event) {
        EXPECT_EQ(MOJO_RESULT_OK, event.result);
        EXPECT_EQ(kTestMessageToA, ReadMessage(a));

        wait_for_notification.Signal();

        // Give the other thread sufficient time to race with the completion
        // of this callback. There should be no race, since the cancellation
        // notification must be mutually exclusive to this notification.
        base::PlatformThread::Sleep(base::TimeDelta::FromSeconds(1));

        callback_done = true;
      },
      [&] {
        EXPECT_TRUE(callback_done);
        wait_for_cancellation.Signal();
      });

  ThreadedRunner runner(base::BindOnce(base::BindLambdaForTesting([&] {
    wait_for_notification.Wait();

    // Cancel the watch while the notification is still running.
    EXPECT_EQ(MOJO_RESULT_OK,
              MojoRemoveTrigger(t, readable_a_context, nullptr));

    wait_for_cancellation.Wait();

    EXPECT_TRUE(callback_done);
  })));
  runner.Start();

  EXPECT_EQ(MOJO_RESULT_OK,
            MojoAddTrigger(t, a, MOJO_HANDLE_SIGNAL_READABLE,
                           MOJO_TRIGGER_CONDITION_SIGNALS_SATISFIED,
                           readable_a_context, nullptr));
  EXPECT_EQ(MOJO_RESULT_OK, MojoArmTrap(t, nullptr, nullptr, nullptr));

  WriteMessage(b, kTestMessageToA);
  runner.Join();

  EXPECT_EQ(MOJO_RESULT_OK, MojoClose(b));
  EXPECT_EQ(MOJO_RESULT_OK, MojoClose(t));
}

TEST_F(TrapTest, TriggersRemoveEachOtherWithinEventHandlers) {
  MojoHandle a, b;
  CreateMessagePipe(&a, &b);

  static const char kTestMessageToA[] = "hey a";
  static const char kTestMessageToB[] = "hey b";

  base::WaitableEvent wait_for_a_to_notify(
      base::WaitableEvent::ResetPolicy::MANUAL,
      base::WaitableEvent::InitialState::NOT_SIGNALED);
  base::WaitableEvent wait_for_b_to_notify(
      base::WaitableEvent::ResetPolicy::MANUAL,
      base::WaitableEvent::InitialState::NOT_SIGNALED);
  base::WaitableEvent wait_for_a_to_cancel(
      base::WaitableEvent::ResetPolicy::MANUAL,
      base::WaitableEvent::InitialState::NOT_SIGNALED);
  base::WaitableEvent wait_for_b_to_cancel(
      base::WaitableEvent::ResetPolicy::MANUAL,
      base::WaitableEvent::InitialState::NOT_SIGNALED);

  MojoHandle a_trap;
  MojoHandle b_trap;
  TriggerHelper helper;
  EXPECT_EQ(MOJO_RESULT_OK, helper.CreateTrap(&a_trap));
  EXPECT_EQ(MOJO_RESULT_OK, helper.CreateTrap(&b_trap));

  // We set up two traps, one triggered on |a| readability and one triggered on
  // |b| readability. Each removes the other's trigger from within its own event
  // handler. This should be safe, i.e., it should not deadlock in spite of the
  // fact that we also guarantee mutually exclusive event handler invocation
  // (including cancellations) on any given trap.
  bool a_cancelled = false;
  bool b_cancelled = false;
  static uintptr_t readable_b_context;
  uintptr_t readable_a_context = helper.CreateContextWithCancel(
      [&](const MojoTrapEvent& event) {
        EXPECT_EQ(MOJO_RESULT_OK, event.result);
        EXPECT_EQ(kTestMessageToA, ReadMessage(a));
        wait_for_a_to_notify.Signal();
        wait_for_b_to_notify.Wait();
        EXPECT_EQ(MOJO_RESULT_OK,
                  MojoRemoveTrigger(b_trap, readable_b_context, nullptr));
        EXPECT_EQ(MOJO_RESULT_OK, MojoClose(b_trap));
      },
      [&] {
        a_cancelled = true;
        wait_for_a_to_cancel.Signal();
        wait_for_b_to_cancel.Wait();
      });

  readable_b_context = helper.CreateContextWithCancel(
      [&](const MojoTrapEvent& event) {
        EXPECT_EQ(MOJO_RESULT_OK, event.result);
        EXPECT_EQ(kTestMessageToB, ReadMessage(b));
        wait_for_b_to_notify.Signal();
        wait_for_a_to_notify.Wait();
        EXPECT_EQ(MOJO_RESULT_OK,
                  MojoRemoveTrigger(a_trap, readable_a_context, nullptr));
        EXPECT_EQ(MOJO_RESULT_OK, MojoClose(a_trap));
      },
      [&] {
        b_cancelled = true;
        wait_for_b_to_cancel.Signal();
        wait_for_a_to_cancel.Wait();
      });

  EXPECT_EQ(MOJO_RESULT_OK,
            MojoAddTrigger(a_trap, a, MOJO_HANDLE_SIGNAL_READABLE,
                           MOJO_TRIGGER_CONDITION_SIGNALS_SATISFIED,
                           readable_a_context, nullptr));
  EXPECT_EQ(MOJO_RESULT_OK, MojoArmTrap(a_trap, nullptr, nullptr, nullptr));
  EXPECT_EQ(MOJO_RESULT_OK,
            MojoAddTrigger(b_trap, b, MOJO_HANDLE_SIGNAL_READABLE,
                           MOJO_TRIGGER_CONDITION_SIGNALS_SATISFIED,
                           readable_b_context, nullptr));
  EXPECT_EQ(MOJO_RESULT_OK, MojoArmTrap(b_trap, nullptr, nullptr, nullptr));

  ThreadedRunner runner(base::BindOnce(
      [](MojoHandle b) { WriteMessage(b, kTestMessageToA); }, b));
  runner.Start();

  WriteMessage(a, kTestMessageToB);

  wait_for_a_to_cancel.Wait();
  wait_for_b_to_cancel.Wait();
  runner.Join();

  EXPECT_TRUE(a_cancelled);
  EXPECT_TRUE(b_cancelled);

  EXPECT_EQ(MOJO_RESULT_OK, MojoClose(a));
  EXPECT_EQ(MOJO_RESULT_OK, MojoClose(b));
}

TEST_F(TrapTest, AlwaysCancel) {
  // Basic sanity check to ensure that all possible ways to remove a trigger
  // result in a final MOJO_RESULT_CANCELLED notification.

  MojoHandle a, b;
  CreateMessagePipe(&a, &b);

  MojoHandle t;
  TriggerHelper helper;
  EXPECT_EQ(MOJO_RESULT_OK, helper.CreateTrap(&t));

  base::WaitableEvent wait(base::WaitableEvent::ResetPolicy::MANUAL,
                           base::WaitableEvent::InitialState::NOT_SIGNALED);
  auto ignore_event = [](const MojoTrapEvent&) {};
  auto signal_wait = [&] { wait.Signal(); };

  // Cancel via |MojoRemoveTrigger()|.
  uintptr_t context = helper.CreateContextWithCancel(ignore_event, signal_wait);
  EXPECT_EQ(MOJO_RESULT_OK,
            MojoAddTrigger(t, a, MOJO_HANDLE_SIGNAL_READABLE,
                           MOJO_TRIGGER_CONDITION_SIGNALS_SATISFIED, context,
                           nullptr));
  EXPECT_EQ(MOJO_RESULT_OK, MojoRemoveTrigger(t, context, nullptr));
  wait.Wait();
  wait.Reset();

  // Cancel by closing the trigger's watched handle.
  context = helper.CreateContextWithCancel(ignore_event, signal_wait);
  EXPECT_EQ(MOJO_RESULT_OK,
            MojoAddTrigger(t, a, MOJO_HANDLE_SIGNAL_READABLE,
                           MOJO_TRIGGER_CONDITION_SIGNALS_SATISFIED, context,
                           nullptr));
  EXPECT_EQ(MOJO_RESULT_OK, MojoClose(a));
  wait.Wait();
  wait.Reset();

  // Cancel by closing the trap handle.
  context = helper.CreateContextWithCancel(ignore_event, signal_wait);
  EXPECT_EQ(MOJO_RESULT_OK,
            MojoAddTrigger(t, b, MOJO_HANDLE_SIGNAL_READABLE,
                           MOJO_TRIGGER_CONDITION_SIGNALS_SATISFIED, context,
                           nullptr));
  EXPECT_EQ(MOJO_RESULT_OK, MojoClose(t));
  wait.Wait();

  EXPECT_EQ(MOJO_RESULT_OK, MojoClose(b));
}

TEST_F(TrapTest, ArmFailureCirculation) {
  // Sanity check to ensure that all ready trigger events will eventually be
  // returned over a finite number of calls to MojoArmTrap().

  constexpr size_t kNumTestPipes = 100;
  constexpr size_t kNumTestHandles = kNumTestPipes * 2;
  MojoHandle handles[kNumTestHandles];

  // Create a bunch of pipes and make sure they're all readable.
  for (size_t i = 0; i < kNumTestPipes; ++i) {
    CreateMessagePipe(&handles[i], &handles[i + kNumTestPipes]);
    WriteMessage(handles[i], "hey");
    WriteMessage(handles[i + kNumTestPipes], "hay");
    WaitForSignals(handles[i], MOJO_HANDLE_SIGNAL_READABLE);
    WaitForSignals(handles[i + kNumTestPipes], MOJO_HANDLE_SIGNAL_READABLE);
  }

  // Create a trap and watch all of them for readability.
  MojoHandle t;
  EXPECT_EQ(MOJO_RESULT_OK, MojoCreateTrap(&ExpectOnlyCancel, nullptr, &t));
  for (size_t i = 0; i < kNumTestHandles; ++i) {
    EXPECT_EQ(
        MOJO_RESULT_OK,
        MojoAddTrigger(t, handles[i], MOJO_HANDLE_SIGNAL_READABLE,
                       MOJO_TRIGGER_CONDITION_SIGNALS_SATISFIED, i, nullptr));
  }

  // Keep trying to arm |t| until every trigger gets an entry in
  // |ready_contexts|. If MojoArmTrap() is well-behaved, this should terminate
  // eventually.
  std::set<uintptr_t> ready_contexts;
  while (ready_contexts.size() < kNumTestHandles) {
    uint32_t num_blocking_events = 1;
    MojoTrapEvent blocking_event = {sizeof(blocking_event)};
    EXPECT_EQ(MOJO_RESULT_FAILED_PRECONDITION,
              MojoArmTrap(t, nullptr, &num_blocking_events, &blocking_event));
    EXPECT_EQ(1u, num_blocking_events);
    EXPECT_EQ(MOJO_RESULT_OK, blocking_event.result);
    ready_contexts.insert(blocking_event.trigger_context);
  }

  for (size_t i = 0; i < kNumTestHandles; ++i)
    EXPECT_EQ(MOJO_RESULT_OK, MojoClose(handles[i]));
  EXPECT_EQ(MOJO_RESULT_OK, MojoClose(t));
}

TEST_F(TrapTest, TriggerOnUnsatisfiedSignals) {
  MojoHandle a, b;
  CreateMessagePipe(&a, &b);

  base::WaitableEvent wait(base::WaitableEvent::ResetPolicy::MANUAL,
                           base::WaitableEvent::InitialState::NOT_SIGNALED);
  TriggerHelper helper;
  const uintptr_t readable_a_context =
      helper.CreateContext([&](const MojoTrapEvent& event) {
        EXPECT_EQ(MOJO_RESULT_OK, event.result);
        wait.Signal();
      });

  MojoHandle t;
  EXPECT_EQ(MOJO_RESULT_OK, helper.CreateTrap(&t));
  EXPECT_EQ(MOJO_RESULT_OK,
            MojoAddTrigger(t, a, MOJO_HANDLE_SIGNAL_READABLE,
                           MOJO_TRIGGER_CONDITION_SIGNALS_SATISFIED,
                           readable_a_context, nullptr));
  EXPECT_EQ(MOJO_RESULT_OK, MojoArmTrap(t, nullptr, nullptr, nullptr));

  const char kMessage[] = "this is not a message";

  WriteMessage(b, kMessage);
  wait.Wait();

  // Now we know |a| is readable. Remove the trigger and add a new one to watch
  // for a not-readable state.
  EXPECT_EQ(MOJO_RESULT_OK, MojoClose(t));
  const uintptr_t not_readable_a_context =
      helper.CreateContext([&](const MojoTrapEvent& event) {
        EXPECT_EQ(MOJO_RESULT_OK, event.result);
        wait.Signal();
      });
  EXPECT_EQ(MOJO_RESULT_OK, helper.CreateTrap(&t));
  EXPECT_EQ(MOJO_RESULT_OK,
            MojoAddTrigger(t, a, MOJO_HANDLE_SIGNAL_READABLE,
                           MOJO_TRIGGER_CONDITION_SIGNALS_UNSATISFIED,
                           not_readable_a_context, nullptr));
  EXPECT_EQ(MOJO_RESULT_OK, MojoArmTrap(t, nullptr, nullptr, nullptr));

  // This should not block, because the event should be signaled by
  // |not_readable_a_context| when we read the only available message off of
  // |a|.
  wait.Reset();
  EXPECT_EQ(kMessage, ReadMessage(a));
  wait.Wait();

  EXPECT_EQ(MOJO_RESULT_OK, MojoClose(t));
  EXPECT_EQ(MOJO_RESULT_OK, MojoClose(b));
  EXPECT_EQ(MOJO_RESULT_OK, MojoClose(a));
}

base::Closure g_do_random_thing_callback;

void ReadAllMessages(const MojoTrapEvent* event) {
  if (event->result == MOJO_RESULT_OK) {
    MojoHandle handle = static_cast<MojoHandle>(event->trigger_context);
    MojoMessageHandle message;
    while (MojoReadMessage(handle, nullptr, &message) == MOJO_RESULT_OK)
      MojoDestroyMessage(message);
  }

  constexpr size_t kNumRandomThingsToDoOnNotify = 5;
  for (size_t i = 0; i < kNumRandomThingsToDoOnNotify; ++i)
    g_do_random_thing_callback.Run();
}

MojoHandle RandomHandle(MojoHandle* handles, size_t size) {
  return handles[base::RandInt(0, static_cast<int>(size) - 1)];
}

void DoRandomThing(MojoHandle* traps,
                   size_t num_traps,
                   MojoHandle* watched_handles,
                   size_t num_watched_handles) {
  switch (base::RandInt(0, 10)) {
    case 0:
      MojoClose(RandomHandle(traps, num_traps));
      break;
    case 1:
      MojoClose(RandomHandle(watched_handles, num_watched_handles));
      break;
    case 2:
    case 3:
    case 4: {
      MojoMessageHandle message;
      ASSERT_EQ(MOJO_RESULT_OK, MojoCreateMessage(nullptr, &message));
      ASSERT_EQ(MOJO_RESULT_OK,
                MojoSetMessageContext(message, 1, nullptr, nullptr, nullptr));
      MojoWriteMessage(RandomHandle(watched_handles, num_watched_handles),
                       message, nullptr);
      break;
    }
    case 5:
    case 6: {
      MojoHandle t = RandomHandle(traps, num_traps);
      MojoHandle h = RandomHandle(watched_handles, num_watched_handles);
      MojoAddTrigger(t, h, MOJO_HANDLE_SIGNAL_READABLE,
                     MOJO_TRIGGER_CONDITION_SIGNALS_SATISFIED,
                     static_cast<uintptr_t>(h), nullptr);
      break;
    }
    case 7:
    case 8: {
      uint32_t num_blocking_events = 1;
      MojoTrapEvent blocking_event = {sizeof(blocking_event)};
      if (MojoArmTrap(RandomHandle(traps, num_traps), nullptr,
                      &num_blocking_events,
                      &blocking_event) == MOJO_RESULT_FAILED_PRECONDITION &&
          blocking_event.result == MOJO_RESULT_OK) {
        ReadAllMessages(&blocking_event);
      }
      break;
    }
    case 9:
    case 10: {
      MojoHandle t = RandomHandle(traps, num_traps);
      MojoHandle h = RandomHandle(watched_handles, num_watched_handles);
      MojoRemoveTrigger(t, static_cast<uintptr_t>(h), nullptr);
      break;
    }
    default:
      NOTREACHED();
      break;
  }
}

TEST_F(TrapTest, ConcurrencyStressTest) {
  // Regression test for https://crbug.com/740044. Exercises racy usage of the
  // trap API to weed out potential crashes.

  constexpr size_t kNumTraps = 50;
  constexpr size_t kNumWatchedHandles = 50;
  static_assert(kNumWatchedHandles % 2 == 0, "Invalid number of test handles.");

  constexpr size_t kNumThreads = 10;
  static constexpr size_t kNumOperationsPerThread = 400;

  MojoHandle traps[kNumTraps];
  MojoHandle watched_handles[kNumWatchedHandles];
  g_do_random_thing_callback = base::BindRepeating(
      &DoRandomThing, traps, kNumTraps, watched_handles, kNumWatchedHandles);

  for (size_t i = 0; i < kNumTraps; ++i)
    MojoCreateTrap(&ReadAllMessages, nullptr, &traps[i]);
  for (size_t i = 0; i < kNumWatchedHandles; i += 2)
    CreateMessagePipe(&watched_handles[i], &watched_handles[i + 1]);

  std::unique_ptr<ThreadedRunner> threads[kNumThreads];
  for (size_t i = 0; i < kNumThreads; ++i) {
    threads[i] = std::make_unique<ThreadedRunner>(base::BindOnce([] {
      for (size_t i = 0; i < kNumOperationsPerThread; ++i)
        g_do_random_thing_callback.Run();
    }));
    threads[i]->Start();
  }
  for (size_t i = 0; i < kNumThreads; ++i)
    threads[i]->Join();
  for (size_t i = 0; i < kNumTraps; ++i)
    MojoClose(traps[i]);
  for (size_t i = 0; i < kNumWatchedHandles; ++i)
    MojoClose(watched_handles[i]);
}

}  // namespace
}  // namespace core
}  // namespace mojo
