// Copyright 2014 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 "chrome/browser/chromeos/events/event_rewriter.h"

#include <vector>

#include "ash/shell.h"
#include "ash/sticky_keys/sticky_keys_controller.h"
#include "ash/sticky_keys/sticky_keys_overlay.h"
#include "ash/test/ash_test_base.h"
#include "ash/wm/window_state.h"
#include "base/basictypes.h"
#include "base/command_line.h"
#include "base/prefs/pref_member.h"
#include "base/strings/stringprintf.h"
#include "chrome/browser/chromeos/input_method/input_method_configuration.h"
#include "chrome/browser/chromeos/input_method/mock_input_method_manager.h"
#include "chrome/browser/chromeos/login/users/scoped_user_manager_enabler.h"
#include "chrome/browser/chromeos/preferences.h"
#include "chrome/common/pref_names.h"
#include "chrome/test/base/testing_pref_service_syncable.h"
#include "chromeos/chromeos_switches.h"
#include "components/user_manager/fake_user_manager.h"
#include "testing/gtest/include/gtest/gtest.h"
#include "ui/aura/window.h"
#include "ui/aura/window_tree_host.h"
#include "ui/base/ime/chromeos/fake_ime_keyboard.h"
#include "ui/events/event.h"
#include "ui/events/event_rewriter.h"
#include "ui/events/event_utils.h"
#include "ui/events/keycodes/dom/dom_code.h"
#include "ui/events/keycodes/dom/dom_key.h"
#include "ui/events/keycodes/dom/keycode_converter.h"
#include "ui/events/test/events_test_utils.h"
#include "ui/events/test/test_event_processor.h"

#if defined(USE_X11)
#include <X11/keysym.h>

#include "ui/events/devices/x11/touch_factory_x11.h"
#include "ui/events/event_utils.h"
#include "ui/events/test/events_test_utils_x11.h"
#include "ui/gfx/x/x11_types.h"
#endif

namespace {

// The device id of the test touchpad device.
#if defined(USE_X11)
const int kTouchPadDeviceId = 1;
const int kMasterKeyboardDeviceId = 3;
#endif
const int kKeyboardDeviceId = 2;

std::string GetExpectedResultAsString(ui::EventType ui_type,
                                      ui::KeyboardCode ui_keycode,
                                      ui::DomCode code,
                                      int ui_flags,  // ui::EventFlags
                                      ui::DomKey key,
                                      base::char16 character) {
  return base::StringPrintf("ui_keycode=0x%X ui_flags=0x%X ui_type=%d",
                            ui_keycode,
                            ui_flags & ~ui::EF_IS_REPEAT,
                            ui_type);
}

std::string GetKeyEventAsString(const ui::KeyEvent& keyevent) {
  return GetExpectedResultAsString(
      keyevent.type(), keyevent.key_code(), keyevent.code(), keyevent.flags(),
      keyevent.GetDomKey(), keyevent.GetCharacter());
}

std::string GetRewrittenEventAsString(chromeos::EventRewriter* rewriter,
                                      ui::EventType ui_type,
                                      ui::KeyboardCode ui_keycode,
                                      ui::DomCode code,
                                      int ui_flags,  // ui::EventFlags
                                      ui::DomKey key,
                                      base::char16 character) {
  const ui::KeyEvent event(ui_type, ui_keycode, code, ui_flags, key, character,
                           ui::EventTimeForNow());
  scoped_ptr<ui::Event> new_event;
  rewriter->RewriteEvent(event, &new_event);
  if (new_event)
    return GetKeyEventAsString(
        static_cast<const ui::KeyEvent&>(*new_event.get()));
  return GetKeyEventAsString(event);
}

// Table entry for simple single key event rewriting tests.
struct KeyTestCase {
  enum {
    // Test types:
    TEST_VKEY = 1 << 0,  // Test ui::KeyEvent with no native event
    TEST_X11 = 1 << 1,   // Test ui::KeyEvent with native XKeyEvent
    TEST_ALL = TEST_VKEY | TEST_X11,
    // Special test flags:
    NUMPAD = 1 << 8,  // Reset the XKB scan code on an X11 event based
                      // on the test DomCode, because
                      // |XKeysymForWindowsKeyCode()| can not distinguish
                      // between pairs like XK_Insert and XK_KP_Insert.
  };
  int test;
  ui::EventType type;
  struct Event {
    ui::KeyboardCode key_code;
    ui::DomCode code;
    int flags;  // ui::EventFlags
    ui::DomKey key;
    base::char16 character;
  } input, expected;
};

std::string GetTestCaseAsString(ui::EventType ui_type,
                                const KeyTestCase::Event& test) {
  return GetExpectedResultAsString(ui_type, test.key_code, test.code,
                                   test.flags, test.key, test.character);
}

#if defined(USE_X11)
// Check rewriting of an X11-based key event.
void CheckX11KeyTestCase(const std::string& expected,
                         chromeos::EventRewriter* rewriter,
                         const KeyTestCase& test,
                         XEvent* xevent) {
  ui::KeyEvent xkey_event(xevent);
  // Rewrite the event and check the result.
  scoped_ptr<ui::Event> new_event;
  rewriter->RewriteEvent(xkey_event, &new_event);
  ui::KeyEvent& rewritten_key_event =
      new_event ? *static_cast<ui::KeyEvent*>(new_event.get()) : xkey_event;
  EXPECT_EQ(expected, GetKeyEventAsString(rewritten_key_event));
  if ((rewritten_key_event.key_code() != ui::VKEY_UNKNOWN) &&
      (rewritten_key_event.native_event()->xkey.keycode != 0)) {
    // Build a new ui::KeyEvent from the rewritten native component,
    // and check that it also matches the rewritten event.
    EXPECT_TRUE(rewritten_key_event.native_event());
    ui::KeyEvent from_native_event(rewritten_key_event.native_event());
    EXPECT_EQ(expected, GetKeyEventAsString(from_native_event));
  }
}
#endif

// Tests a single stateless key rewrite operation.
void CheckKeyTestCase(chromeos::EventRewriter* rewriter,
                      const KeyTestCase& test) {
  std::string expected = GetTestCaseAsString(test.type, test.expected);

  if (test.test & KeyTestCase::TEST_VKEY) {
    // Check rewriting of a non-native-based key event.
    EXPECT_EQ(expected,
              GetRewrittenEventAsString(
                  rewriter, test.type, test.input.key_code, test.input.code,
                  test.input.flags, test.input.key, test.input.character));
  }

#if defined(USE_X11)
  if (test.test & KeyTestCase::TEST_X11) {
    ui::ScopedXI2Event xev;
    // Test an XKeyEvent.
    xev.InitKeyEvent(test.type, test.input.key_code, test.input.flags);
    XEvent* xevent = xev;
    DCHECK((xevent->type == KeyPress) || (xevent->type == KeyRelease));
    if (test.test & KeyTestCase::NUMPAD) {
      xevent->xkey.keycode =
          ui::KeycodeConverter::DomCodeToNativeKeycode(test.input.code);
    }
    int keycode = xevent->xkey.keycode;
    if (keycode) {
      CheckX11KeyTestCase(expected, rewriter, test, xevent);
      // Test an XI2 GenericEvent.
      xev.InitGenericKeyEvent(kMasterKeyboardDeviceId, kKeyboardDeviceId,
                              test.type, test.input.key_code, test.input.flags);
      xevent = xev;
      DCHECK(xevent->type == GenericEvent);
      XIDeviceEvent* xievent =
          static_cast<XIDeviceEvent*>(xevent->xcookie.data);
      DCHECK((xievent->evtype == XI_KeyPress) ||
             (xievent->evtype == XI_KeyRelease));
      xievent->detail = keycode;
      CheckX11KeyTestCase(expected, rewriter, test, xevent);
    }
  }
#endif
}

}  // namespace

namespace chromeos {

class EventRewriterTest : public ash::test::AshTestBase {
 public:
  EventRewriterTest()
      : fake_user_manager_(new user_manager::FakeUserManager),
        user_manager_enabler_(fake_user_manager_),
        input_method_manager_mock_(NULL) {}
  ~EventRewriterTest() override {}

  void SetUp() override {
    input_method_manager_mock_ =
        new chromeos::input_method::MockInputMethodManager;
    chromeos::input_method::InitializeForTesting(
        input_method_manager_mock_);  // pass ownership

    AshTestBase::SetUp();
  }

  void TearDown() override {
    AshTestBase::TearDown();
    // Shutdown() deletes the IME mock object.
    chromeos::input_method::Shutdown();
  }

 protected:
  void TestRewriteNumPadKeys();
  void TestRewriteNumPadKeysOnAppleKeyboard();

  const ui::MouseEvent* RewriteMouseButtonEvent(
      chromeos::EventRewriter* rewriter,
      const ui::MouseEvent& event,
      scoped_ptr<ui::Event>* new_event) {
    rewriter->RewriteMouseButtonEventForTesting(event, new_event);
    return *new_event ? static_cast<const ui::MouseEvent*>(new_event->get())
                      : &event;
  }

  user_manager::FakeUserManager* fake_user_manager_;  // Not owned.
  chromeos::ScopedUserManagerEnabler user_manager_enabler_;
  chromeos::input_method::MockInputMethodManager* input_method_manager_mock_;
};

TEST_F(EventRewriterTest, TestRewriteCommandToControl) {
  // First, test with a PC keyboard.
  TestingPrefServiceSyncable prefs;
  EventRewriter rewriter(NULL);
  rewriter.KeyboardDeviceAddedForTesting(kKeyboardDeviceId, "PC Keyboard");
  rewriter.set_last_keyboard_device_id_for_testing(kKeyboardDeviceId);
  rewriter.set_pref_service_for_testing(&prefs);

  KeyTestCase pc_keyboard_tests[] = {
      // VKEY_A, Alt modifier.
      {KeyTestCase::TEST_ALL,
       ui::ET_KEY_PRESSED,
       {ui::VKEY_A,
        ui::DomCode::KEY_A,
        ui::EF_ALT_DOWN,
        ui::DomKey::CHARACTER,
        'a'},
       {ui::VKEY_A,
        ui::DomCode::KEY_A,
        ui::EF_ALT_DOWN,
        ui::DomKey::CHARACTER,
        'a'}},

      // VKEY_A, Win modifier.
      {KeyTestCase::TEST_ALL,
       ui::ET_KEY_PRESSED,
       {ui::VKEY_A,
        ui::DomCode::KEY_A,
        ui::EF_COMMAND_DOWN,
        ui::DomKey::CHARACTER,
        'a'},
       {ui::VKEY_A,
        ui::DomCode::KEY_A,
        ui::EF_COMMAND_DOWN,
        ui::DomKey::CHARACTER,
        'a'}},

      // VKEY_A, Alt+Win modifier.
      {KeyTestCase::TEST_ALL,
       ui::ET_KEY_PRESSED,
       {ui::VKEY_A,
        ui::DomCode::KEY_A,
        ui::EF_ALT_DOWN | ui::EF_COMMAND_DOWN,
        ui::DomKey::CHARACTER,
        'a'},
       {ui::VKEY_A,
        ui::DomCode::KEY_A,
        ui::EF_ALT_DOWN | ui::EF_COMMAND_DOWN,
        ui::DomKey::CHARACTER,
        'a'}},

      // VKEY_LWIN (left Windows key), Alt modifier.
      {KeyTestCase::TEST_ALL,
       ui::ET_KEY_PRESSED,
       {ui::VKEY_LWIN,
        ui::DomCode::OS_LEFT,
        ui::EF_ALT_DOWN | ui::EF_COMMAND_DOWN,
        ui::DomKey::OS,
        0},
       {ui::VKEY_LWIN,
        ui::DomCode::OS_LEFT,
        ui::EF_ALT_DOWN | ui::EF_COMMAND_DOWN,
        ui::DomKey::OS,
        0}},

      // VKEY_RWIN (right Windows key), Alt modifier.
      {KeyTestCase::TEST_ALL,
       ui::ET_KEY_PRESSED,
       {ui::VKEY_RWIN,
        ui::DomCode::OS_RIGHT,
        ui::EF_ALT_DOWN | ui::EF_COMMAND_DOWN,
        ui::DomKey::OS,
        0},
       {ui::VKEY_RWIN,
        ui::DomCode::OS_RIGHT,
        ui::EF_ALT_DOWN | ui::EF_COMMAND_DOWN,
        ui::DomKey::OS,
        0}},
  };

  for (size_t i = 0; i < arraysize(pc_keyboard_tests); ++i) {
    SCOPED_TRACE(i);
    CheckKeyTestCase(&rewriter, pc_keyboard_tests[i]);
  }

  // An Apple keyboard reusing the ID, zero.
  rewriter.KeyboardDeviceAddedForTesting(kKeyboardDeviceId, "Apple Keyboard");
  rewriter.set_last_keyboard_device_id_for_testing(kKeyboardDeviceId);

  KeyTestCase apple_keyboard_tests[] = {
      // VKEY_A, Alt modifier.
      {KeyTestCase::TEST_ALL,
       ui::ET_KEY_PRESSED,
       {ui::VKEY_A,
        ui::DomCode::KEY_A,
        ui::EF_ALT_DOWN,
        ui::DomKey::CHARACTER,
        'a'},
       {ui::VKEY_A,
        ui::DomCode::KEY_A,
        ui::EF_ALT_DOWN,
        ui::DomKey::CHARACTER,
        'a'}},

      // VKEY_A, Win modifier.
      {KeyTestCase::TEST_ALL,
       ui::ET_KEY_PRESSED,
       {ui::VKEY_A,
        ui::DomCode::KEY_A,
        ui::EF_COMMAND_DOWN,
        ui::DomKey::CHARACTER,
        'a'},
       {ui::VKEY_A,
        ui::DomCode::KEY_A,
        ui::EF_CONTROL_DOWN,
        ui::DomKey::CHARACTER,
        'a'}},

      // VKEY_A, Alt+Win modifier.
      {KeyTestCase::TEST_ALL,
       ui::ET_KEY_PRESSED,
       {ui::VKEY_A,
        ui::DomCode::KEY_A,
        ui::EF_ALT_DOWN | ui::EF_COMMAND_DOWN,
        ui::DomKey::CHARACTER,
        'a'},
       {ui::VKEY_A,
        ui::DomCode::KEY_A,
        ui::EF_ALT_DOWN | ui::EF_CONTROL_DOWN,
        ui::DomKey::CHARACTER,
        'a'}},

      // VKEY_LWIN (left Windows key), Alt modifier.
      {KeyTestCase::TEST_ALL,
       ui::ET_KEY_PRESSED,
       {ui::VKEY_LWIN,
        ui::DomCode::OS_LEFT,
        ui::EF_COMMAND_DOWN | ui::EF_ALT_DOWN,
        ui::DomKey::OS,
        0},
       {ui::VKEY_CONTROL,
        ui::DomCode::CONTROL_LEFT,
        ui::EF_CONTROL_DOWN | ui::EF_ALT_DOWN,
        ui::DomKey::CONTROL,
        0}},

      // VKEY_RWIN (right Windows key), Alt modifier.
      {KeyTestCase::TEST_ALL,
       ui::ET_KEY_PRESSED,
       {ui::VKEY_RWIN,
        ui::DomCode::OS_RIGHT,
        ui::EF_COMMAND_DOWN | ui::EF_ALT_DOWN,
        ui::DomKey::OS,
        0},
       {ui::VKEY_CONTROL,
        ui::DomCode::CONTROL_LEFT,
        ui::EF_CONTROL_DOWN | ui::EF_ALT_DOWN,
        ui::DomKey::CONTROL,
        0}},
  };

  for (size_t i = 0; i < arraysize(apple_keyboard_tests); ++i) {
    SCOPED_TRACE(i);
    CheckKeyTestCase(&rewriter, apple_keyboard_tests[i]);
  }
}

// For crbug.com/133896.
TEST_F(EventRewriterTest, TestRewriteCommandToControlWithControlRemapped) {
  // Remap Control to Alt.
  TestingPrefServiceSyncable prefs;
  chromeos::Preferences::RegisterProfilePrefs(prefs.registry());
  IntegerPrefMember control;
  control.Init(prefs::kLanguageRemapControlKeyTo, &prefs);
  control.SetValue(chromeos::input_method::kAltKey);

  EventRewriter rewriter(NULL);
  rewriter.set_pref_service_for_testing(&prefs);
  rewriter.KeyboardDeviceAddedForTesting(kKeyboardDeviceId, "PC Keyboard");
  rewriter.set_last_keyboard_device_id_for_testing(kKeyboardDeviceId);

  KeyTestCase pc_keyboard_tests[] = {
      // Control should be remapped to Alt.
      {KeyTestCase::TEST_ALL,
       ui::ET_KEY_PRESSED,
       {ui::VKEY_CONTROL,
        ui::DomCode::CONTROL_LEFT,
        ui::EF_CONTROL_DOWN,
        ui::DomKey::CONTROL,
        0},
       {ui::VKEY_MENU,
        ui::DomCode::ALT_LEFT,
        ui::EF_ALT_DOWN,
        ui::DomKey::ALT,
        0}},
  };

  for (size_t i = 0; i < arraysize(pc_keyboard_tests); ++i) {
    SCOPED_TRACE(i);
    CheckKeyTestCase(&rewriter, pc_keyboard_tests[i]);
  }

  // An Apple keyboard reusing the ID, zero.
  rewriter.KeyboardDeviceAddedForTesting(kKeyboardDeviceId, "Apple Keyboard");
  rewriter.set_last_keyboard_device_id_for_testing(kKeyboardDeviceId);

  KeyTestCase apple_keyboard_tests[] = {
      // VKEY_LWIN (left Command key) with  Alt modifier. The remapped Command
      // key should never be re-remapped to Alt.
      {KeyTestCase::TEST_ALL,
       ui::ET_KEY_PRESSED,
       {ui::VKEY_LWIN,
        ui::DomCode::OS_LEFT,
        ui::EF_COMMAND_DOWN | ui::EF_ALT_DOWN,
        ui::DomKey::OS,
        0},
       {ui::VKEY_CONTROL,
        ui::DomCode::CONTROL_LEFT,
        ui::EF_CONTROL_DOWN | ui::EF_ALT_DOWN,
        ui::DomKey::CONTROL,
        0}},

      // VKEY_RWIN (right Command key) with  Alt modifier. The remapped Command
      // key should never be re-remapped to Alt.
      {KeyTestCase::TEST_ALL,
       ui::ET_KEY_PRESSED,
       {ui::VKEY_RWIN,
        ui::DomCode::OS_RIGHT,
        ui::EF_COMMAND_DOWN | ui::EF_ALT_DOWN,
        ui::DomKey::OS,
        0},
       {ui::VKEY_CONTROL,
        ui::DomCode::CONTROL_LEFT,
        ui::EF_CONTROL_DOWN | ui::EF_ALT_DOWN,
        ui::DomKey::CONTROL,
        0}},
  };

  for (size_t i = 0; i < arraysize(apple_keyboard_tests); ++i) {
    SCOPED_TRACE(i);
    CheckKeyTestCase(&rewriter, apple_keyboard_tests[i]);
  }
}

void EventRewriterTest::TestRewriteNumPadKeys() {
  TestingPrefServiceSyncable prefs;
  EventRewriter rewriter(NULL);
  rewriter.KeyboardDeviceAddedForTesting(kKeyboardDeviceId, "PC Keyboard");
  rewriter.set_last_keyboard_device_id_for_testing(kKeyboardDeviceId);
  rewriter.set_pref_service_for_testing(&prefs);

  KeyTestCase tests[] = {
      // XK_KP_Insert (= NumPad 0 without Num Lock), no modifier.
      {KeyTestCase::TEST_ALL | KeyTestCase::NUMPAD,
       ui::ET_KEY_PRESSED,
       {ui::VKEY_INSERT,
        ui::DomCode::NUMPAD0,
        ui::EF_NONE,
        ui::DomKey::INSERT,
        0},
       {ui::VKEY_NUMPAD0,
        ui::DomCode::NUMPAD0,
        ui::EF_NONE,
        ui::DomKey::CHARACTER,
        '0'}},

      // XK_KP_Insert (= NumPad 0 without Num Lock), Alt modifier.
      {KeyTestCase::TEST_ALL | KeyTestCase::NUMPAD,
       ui::ET_KEY_PRESSED,
       {ui::VKEY_INSERT,
        ui::DomCode::NUMPAD0,
        ui::EF_ALT_DOWN,
        ui::DomKey::INSERT,
        0},
       {ui::VKEY_NUMPAD0,
        ui::DomCode::NUMPAD0,
        ui::EF_ALT_DOWN,
        ui::DomKey::CHARACTER,
        '0'}},

      // XK_KP_Delete (= NumPad . without Num Lock), Alt modifier.
      {KeyTestCase::TEST_ALL | KeyTestCase::NUMPAD,
       ui::ET_KEY_PRESSED,
       {ui::VKEY_DELETE,
        ui::DomCode::NUMPAD_DECIMAL,
        ui::EF_ALT_DOWN,
        ui::DomKey::DEL,
        0},
       {ui::VKEY_DECIMAL,
        ui::DomCode::NUMPAD_DECIMAL,
        ui::EF_ALT_DOWN,
        ui::DomKey::CHARACTER,
        '.'}},

      // XK_KP_End (= NumPad 1 without Num Lock), Alt modifier.
      {KeyTestCase::TEST_ALL | KeyTestCase::NUMPAD,
       ui::ET_KEY_PRESSED,
       {ui::VKEY_END,
        ui::DomCode::NUMPAD1,
        ui::EF_ALT_DOWN,
        ui::DomKey::END,
        0},
       {ui::VKEY_NUMPAD1,
        ui::DomCode::NUMPAD1,
        ui::EF_ALT_DOWN,
        ui::DomKey::CHARACTER,
        '1'}},

      // XK_KP_Down (= NumPad 2 without Num Lock), Alt modifier.
      {KeyTestCase::TEST_ALL | KeyTestCase::NUMPAD,
       ui::ET_KEY_PRESSED,
       {ui::VKEY_DOWN,
        ui::DomCode::NUMPAD2,
        ui::EF_ALT_DOWN,
        ui::DomKey::ARROW_DOWN,
        0},
       {ui::VKEY_NUMPAD2,
        ui::DomCode::NUMPAD2,
        ui::EF_ALT_DOWN,
        ui::DomKey::CHARACTER,
        '2'}},

      // XK_KP_Next (= NumPad 3 without Num Lock), Alt modifier.
      {KeyTestCase::TEST_ALL | KeyTestCase::NUMPAD,
       ui::ET_KEY_PRESSED,
       {ui::VKEY_NEXT,
        ui::DomCode::NUMPAD3,
        ui::EF_ALT_DOWN,
        ui::DomKey::PAGE_DOWN,
        0},
       {ui::VKEY_NUMPAD3,
        ui::DomCode::NUMPAD3,
        ui::EF_ALT_DOWN,
        ui::DomKey::CHARACTER,
        '3'}},

      // XK_KP_Left (= NumPad 4 without Num Lock), Alt modifier.
      {KeyTestCase::TEST_ALL | KeyTestCase::NUMPAD,
       ui::ET_KEY_PRESSED,
       {ui::VKEY_LEFT,
        ui::DomCode::NUMPAD4,
        ui::EF_ALT_DOWN,
        ui::DomKey::ARROW_LEFT,
        0},
       {ui::VKEY_NUMPAD4,
        ui::DomCode::NUMPAD4,
        ui::EF_ALT_DOWN,
        ui::DomKey::CHARACTER,
        '4'}},

      // XK_KP_Begin (= NumPad 5 without Num Lock), Alt modifier.
      {KeyTestCase::TEST_ALL | KeyTestCase::NUMPAD,
       ui::ET_KEY_PRESSED,
       {ui::VKEY_CLEAR,
        ui::DomCode::NUMPAD5,
        ui::EF_ALT_DOWN,
        ui::DomKey::CLEAR,
        0},
       {ui::VKEY_NUMPAD5,
        ui::DomCode::NUMPAD5,
        ui::EF_ALT_DOWN,
        ui::DomKey::CHARACTER,
        '5'}},

      // XK_KP_Right (= NumPad 6 without Num Lock), Alt modifier.
      {KeyTestCase::TEST_ALL | KeyTestCase::NUMPAD,
       ui::ET_KEY_PRESSED,
       {ui::VKEY_RIGHT,
        ui::DomCode::NUMPAD6,
        ui::EF_ALT_DOWN,
        ui::DomKey::ARROW_RIGHT,
        0},
       {ui::VKEY_NUMPAD6,
        ui::DomCode::NUMPAD6,
        ui::EF_ALT_DOWN,
        ui::DomKey::CHARACTER,
        '6'}},

      // XK_KP_Home (= NumPad 7 without Num Lock), Alt modifier.
      {KeyTestCase::TEST_ALL | KeyTestCase::NUMPAD,
       ui::ET_KEY_PRESSED,
       {ui::VKEY_HOME,
        ui::DomCode::NUMPAD7,
        ui::EF_ALT_DOWN,
        ui::DomKey::HOME,
        0},
       {ui::VKEY_NUMPAD7,
        ui::DomCode::NUMPAD7,
        ui::EF_ALT_DOWN,
        ui::DomKey::CHARACTER,
        '7'}},

      // XK_KP_Up (= NumPad 8 without Num Lock), Alt modifier.
      {KeyTestCase::TEST_ALL | KeyTestCase::NUMPAD,
       ui::ET_KEY_PRESSED,
       {ui::VKEY_UP,
        ui::DomCode::NUMPAD8,
        ui::EF_ALT_DOWN,
        ui::DomKey::ARROW_UP,
        0},
       {ui::VKEY_NUMPAD8,
        ui::DomCode::NUMPAD8,
        ui::EF_ALT_DOWN,
        ui::DomKey::CHARACTER,
        '8'}},

      // XK_KP_Prior (= NumPad 9 without Num Lock), Alt modifier.
      {KeyTestCase::TEST_ALL | KeyTestCase::NUMPAD,
       ui::ET_KEY_PRESSED,
       {ui::VKEY_PRIOR,
        ui::DomCode::NUMPAD9,
        ui::EF_ALT_DOWN,
        ui::DomKey::PAGE_UP,
        0},
       {ui::VKEY_NUMPAD9,
        ui::DomCode::NUMPAD9,
        ui::EF_ALT_DOWN,
        ui::DomKey::CHARACTER,
        '9'}},

      // XK_KP_0 (= NumPad 0 with Num Lock), Num Lock modifier.
      {KeyTestCase::TEST_ALL | KeyTestCase::NUMPAD,
       ui::ET_KEY_PRESSED,
       {ui::VKEY_NUMPAD0,
        ui::DomCode::NUMPAD0,
        ui::EF_NONE,
        ui::DomKey::CHARACTER,
        '0'},
       {ui::VKEY_NUMPAD0,
        ui::DomCode::NUMPAD0,
        ui::EF_NONE,
        ui::DomKey::CHARACTER,
        '0'}},

      // XK_KP_DECIMAL (= NumPad . with Num Lock), Num Lock modifier.
      {KeyTestCase::TEST_ALL | KeyTestCase::NUMPAD,
       ui::ET_KEY_PRESSED,
       {ui::VKEY_DECIMAL,
        ui::DomCode::NUMPAD_DECIMAL,
        ui::EF_NONE,
        ui::DomKey::CHARACTER,
        '.'},
       {ui::VKEY_DECIMAL,
        ui::DomCode::NUMPAD_DECIMAL,
        ui::EF_NONE,
        ui::DomKey::CHARACTER,
        '.'}},

      // XK_KP_1 (= NumPad 1 with Num Lock), Num Lock modifier.
      {KeyTestCase::TEST_ALL | KeyTestCase::NUMPAD,
       ui::ET_KEY_PRESSED,
       {ui::VKEY_NUMPAD1,
        ui::DomCode::NUMPAD1,
        ui::EF_NONE,
        ui::DomKey::CHARACTER,
        '1'},
       {ui::VKEY_NUMPAD1,
        ui::DomCode::NUMPAD1,
        ui::EF_NONE,
        ui::DomKey::CHARACTER,
        '1'}},

      // XK_KP_2 (= NumPad 2 with Num Lock), Num Lock modifier.
      {KeyTestCase::TEST_ALL | KeyTestCase::NUMPAD,
       ui::ET_KEY_PRESSED,
       {ui::VKEY_NUMPAD2,
        ui::DomCode::NUMPAD2,
        ui::EF_NONE,
        ui::DomKey::CHARACTER,
        '2'},
       {ui::VKEY_NUMPAD2,
        ui::DomCode::NUMPAD2,
        ui::EF_NONE,
        ui::DomKey::CHARACTER,
        '2'}},

      // XK_KP_3 (= NumPad 3 with Num Lock), Num Lock modifier.
      {KeyTestCase::TEST_ALL | KeyTestCase::NUMPAD,
       ui::ET_KEY_PRESSED,
       {ui::VKEY_NUMPAD3,
        ui::DomCode::NUMPAD3,
        ui::EF_NONE,
        ui::DomKey::CHARACTER,
        '3'},
       {ui::VKEY_NUMPAD3,
        ui::DomCode::NUMPAD3,
        ui::EF_NONE,
        ui::DomKey::CHARACTER,
        '3'}},

      // XK_KP_4 (= NumPad 4 with Num Lock), Num Lock modifier.
      {KeyTestCase::TEST_ALL | KeyTestCase::NUMPAD,
       ui::ET_KEY_PRESSED,
       {ui::VKEY_NUMPAD4,
        ui::DomCode::NUMPAD4,
        ui::EF_NONE,
        ui::DomKey::CHARACTER,
        '4'},
       {ui::VKEY_NUMPAD4,
        ui::DomCode::NUMPAD4,
        ui::EF_NONE,
        ui::DomKey::CHARACTER,
        '4'}},

      // XK_KP_5 (= NumPad 5 with Num Lock), Num Lock
      // modifier.
      {KeyTestCase::TEST_ALL | KeyTestCase::NUMPAD,
       ui::ET_KEY_PRESSED,
       {ui::VKEY_NUMPAD5,
        ui::DomCode::NUMPAD5,
        ui::EF_NONE,
        ui::DomKey::CHARACTER,
        '5'},
       {ui::VKEY_NUMPAD5,
        ui::DomCode::NUMPAD5,
        ui::EF_NONE,
        ui::DomKey::CHARACTER,
        '5'}},

      // XK_KP_6 (= NumPad 6 with Num Lock), Num Lock
      // modifier.
      {KeyTestCase::TEST_ALL | KeyTestCase::NUMPAD,
       ui::ET_KEY_PRESSED,
       {ui::VKEY_NUMPAD6,
        ui::DomCode::NUMPAD6,
        ui::EF_NONE,
        ui::DomKey::CHARACTER,
        '6'},
       {ui::VKEY_NUMPAD6,
        ui::DomCode::NUMPAD6,
        ui::EF_NONE,
        ui::DomKey::CHARACTER,
        '6'}},

      // XK_KP_7 (= NumPad 7 with Num Lock), Num Lock
      // modifier.
      {KeyTestCase::TEST_ALL | KeyTestCase::NUMPAD,
       ui::ET_KEY_PRESSED,
       {ui::VKEY_NUMPAD7,
        ui::DomCode::NUMPAD7,
        ui::EF_NONE,
        ui::DomKey::CHARACTER,
        '7'},
       {ui::VKEY_NUMPAD7,
        ui::DomCode::NUMPAD7,
        ui::EF_NONE,
        ui::DomKey::CHARACTER,
        '7'}},

      // XK_KP_8 (= NumPad 8 with Num Lock), Num Lock
      // modifier.
      {KeyTestCase::TEST_ALL | KeyTestCase::NUMPAD,
       ui::ET_KEY_PRESSED,
       {ui::VKEY_NUMPAD8,
        ui::DomCode::NUMPAD8,
        ui::EF_NONE,
        ui::DomKey::CHARACTER,
        '8'},
       {ui::VKEY_NUMPAD8,
        ui::DomCode::NUMPAD8,
        ui::EF_NONE,
        ui::DomKey::CHARACTER,
        '8'}},

      // XK_KP_9 (= NumPad 9 with Num Lock), Num Lock
      // modifier.
      {KeyTestCase::TEST_ALL | KeyTestCase::NUMPAD,
       ui::ET_KEY_PRESSED,
       {ui::VKEY_NUMPAD9,
        ui::DomCode::NUMPAD9,
        ui::EF_NONE,
        ui::DomKey::CHARACTER,
        '9'},
       {ui::VKEY_NUMPAD9,
        ui::DomCode::NUMPAD9,
        ui::EF_NONE,
        ui::DomKey::CHARACTER,
        '9'}},
  };

  for (size_t i = 0; i < arraysize(tests); ++i) {
    SCOPED_TRACE(i);
    CheckKeyTestCase(&rewriter, tests[i]);
  }
}

TEST_F(EventRewriterTest, TestRewriteNumPadKeys) {
  TestRewriteNumPadKeys();
}

TEST_F(EventRewriterTest, TestRewriteNumPadKeysWithDiamondKeyFlag) {
  // Make sure the num lock works correctly even when Diamond key exists.
  const base::CommandLine original_cl(*base::CommandLine::ForCurrentProcess());
  base::CommandLine::ForCurrentProcess()->AppendSwitchASCII(
      chromeos::switches::kHasChromeOSDiamondKey, "");

  TestRewriteNumPadKeys();
  *base::CommandLine::ForCurrentProcess() = original_cl;
}

// Tests if the rewriter can handle a Command + Num Pad event.
void EventRewriterTest::TestRewriteNumPadKeysOnAppleKeyboard() {
  TestingPrefServiceSyncable prefs;
  EventRewriter rewriter(NULL);
  rewriter.KeyboardDeviceAddedForTesting(kKeyboardDeviceId, "Apple Keyboard");
  rewriter.set_last_keyboard_device_id_for_testing(kKeyboardDeviceId);
  rewriter.set_pref_service_for_testing(&prefs);

  KeyTestCase tests[] = {
      // XK_KP_End (= NumPad 1 without Num Lock), Win modifier.
      // The result should be "Num Pad 1 with Control + Num Lock modifiers".
      {KeyTestCase::TEST_ALL | KeyTestCase::NUMPAD,
       ui::ET_KEY_PRESSED,
       {ui::VKEY_END,
        ui::DomCode::NUMPAD1,
        ui::EF_COMMAND_DOWN,
        ui::DomKey::END,
        0},
       {ui::VKEY_NUMPAD1,
        ui::DomCode::NUMPAD1,
        ui::EF_CONTROL_DOWN,
        ui::DomKey::CHARACTER,
        '1'}},

      // XK_KP_1 (= NumPad 1 with Num Lock), Win modifier.
      // The result should also be "Num Pad 1 with Control + Num Lock
      // modifiers".
      {KeyTestCase::TEST_ALL | KeyTestCase::NUMPAD,
       ui::ET_KEY_PRESSED,
       {ui::VKEY_NUMPAD1,
        ui::DomCode::NUMPAD1,
        ui::EF_COMMAND_DOWN,
        ui::DomKey::CHARACTER,
        '1'},
       {ui::VKEY_NUMPAD1,
        ui::DomCode::NUMPAD1,
        ui::EF_CONTROL_DOWN,
        ui::DomKey::CHARACTER,
        '1'}}};

  for (size_t i = 0; i < arraysize(tests); ++i) {
    SCOPED_TRACE(i);
    CheckKeyTestCase(&rewriter, tests[i]);
  }
}

TEST_F(EventRewriterTest, TestRewriteNumPadKeysOnAppleKeyboard) {
  TestRewriteNumPadKeysOnAppleKeyboard();
}

TEST_F(EventRewriterTest,
       TestRewriteNumPadKeysOnAppleKeyboardWithDiamondKeyFlag) {
  // Makes sure the num lock works correctly even when Diamond key exists.
  const base::CommandLine original_cl(*base::CommandLine::ForCurrentProcess());
  base::CommandLine::ForCurrentProcess()->AppendSwitchASCII(
      chromeos::switches::kHasChromeOSDiamondKey, "");

  TestRewriteNumPadKeysOnAppleKeyboard();
  *base::CommandLine::ForCurrentProcess() = original_cl;
}

TEST_F(EventRewriterTest, TestRewriteModifiersNoRemap) {
  TestingPrefServiceSyncable prefs;
  EventRewriter rewriter(NULL);
  rewriter.KeyboardDeviceAddedForTesting(kKeyboardDeviceId, "PC Keyboard");
  rewriter.set_pref_service_for_testing(&prefs);

  KeyTestCase tests[] = {
      // Press Search. Confirm the event is not rewritten.
      {KeyTestCase::TEST_ALL,
       ui::ET_KEY_PRESSED,
       {ui::VKEY_LWIN, ui::DomCode::OS_LEFT, ui::EF_NONE, ui::DomKey::OS, 0},
       {ui::VKEY_LWIN,
        ui::DomCode::OS_LEFT,
        ui::EF_COMMAND_DOWN,
        ui::DomKey::OS,
        0}},

      // Press left Control. Confirm the event is not rewritten.
      {KeyTestCase::TEST_ALL,
       ui::ET_KEY_PRESSED,
       {ui::VKEY_CONTROL,
        ui::DomCode::CONTROL_LEFT,
        ui::EF_CONTROL_DOWN,
        ui::DomKey::CONTROL,
        0},
       {ui::VKEY_CONTROL,
        ui::DomCode::CONTROL_LEFT,
        ui::EF_CONTROL_DOWN,
        ui::DomKey::CONTROL,
        0}},

      // Press right Control. Confirm the event is not rewritten.
      {KeyTestCase::TEST_ALL,
       ui::ET_KEY_PRESSED,
       {ui::VKEY_CONTROL,
        ui::DomCode::CONTROL_LEFT,
        ui::EF_CONTROL_DOWN,
        ui::DomKey::CONTROL,
        0},
       {ui::VKEY_CONTROL,
        ui::DomCode::CONTROL_LEFT,
        ui::EF_CONTROL_DOWN,
        ui::DomKey::CONTROL,
        0}},

      // Press left Alt. Confirm the event is not rewritten.
      {KeyTestCase::TEST_ALL,
       ui::ET_KEY_PRESSED,
       {ui::VKEY_MENU,
        ui::DomCode::ALT_LEFT,
        ui::EF_ALT_DOWN,
        ui::DomKey::ALT,
        0},
       {ui::VKEY_MENU,
        ui::DomCode::ALT_LEFT,
        ui::EF_ALT_DOWN,
        ui::DomKey::ALT,
        0}},

      // Press right Alt. Confirm the event is not rewritten.
      {KeyTestCase::TEST_ALL,
       ui::ET_KEY_PRESSED,
       {ui::VKEY_MENU,
        ui::DomCode::ALT_LEFT,
        ui::EF_ALT_DOWN,
        ui::DomKey::ALT,
        0},
       {ui::VKEY_MENU,
        ui::DomCode::ALT_LEFT,
        ui::EF_ALT_DOWN,
        ui::DomKey::ALT,
        0}},

      // Test KeyRelease event, just in case.
      // Release Search. Confirm the release event is not rewritten.
      {KeyTestCase::TEST_ALL,
       ui::ET_KEY_RELEASED,
       {ui::VKEY_LWIN, ui::DomCode::OS_LEFT, ui::EF_NONE, ui::DomKey::OS, 0},
       {ui::VKEY_LWIN, ui::DomCode::OS_LEFT, ui::EF_NONE, ui::DomKey::OS, 0}},
  };

  for (size_t i = 0; i < arraysize(tests); ++i) {
    SCOPED_TRACE(i);
    CheckKeyTestCase(&rewriter, tests[i]);
  }
}

TEST_F(EventRewriterTest, TestRewriteModifiersNoRemapMultipleKeys) {
  TestingPrefServiceSyncable prefs;
  EventRewriter rewriter(NULL);
  rewriter.KeyboardDeviceAddedForTesting(kKeyboardDeviceId, "PC Keyboard");
  rewriter.set_pref_service_for_testing(&prefs);

  KeyTestCase tests[] = {
      // Press Alt with Shift. Confirm the event is not rewritten.
      {KeyTestCase::TEST_ALL,
       ui::ET_KEY_PRESSED,
       {ui::VKEY_MENU,
        ui::DomCode::ALT_LEFT,
        ui::EF_SHIFT_DOWN | ui::EF_ALT_DOWN,
        ui::DomKey::ALT,
        0},
       {ui::VKEY_MENU,
        ui::DomCode::ALT_LEFT,
        ui::EF_SHIFT_DOWN | ui::EF_ALT_DOWN,
        ui::DomKey::ALT,
        0}},

      // Press Search with Caps Lock mask. Confirm the event is not rewritten.
      {KeyTestCase::TEST_ALL,
       ui::ET_KEY_PRESSED,
       {ui::VKEY_LWIN,
        ui::DomCode::OS_LEFT,
        ui::EF_CAPS_LOCK_DOWN | ui::EF_COMMAND_DOWN,
        ui::DomKey::OS,
        0},
       {ui::VKEY_LWIN,
        ui::DomCode::OS_LEFT,
        ui::EF_CAPS_LOCK_DOWN | ui::EF_COMMAND_DOWN,
        ui::DomKey::OS,
        0}},

      // Release Search with Caps Lock mask. Confirm the event is not rewritten.
      {KeyTestCase::TEST_ALL,
       ui::ET_KEY_RELEASED,
       {ui::VKEY_LWIN,
        ui::DomCode::OS_LEFT,
        ui::EF_CAPS_LOCK_DOWN,
        ui::DomKey::OS,
        0},
       {ui::VKEY_LWIN,
        ui::DomCode::OS_LEFT,
        ui::EF_CAPS_LOCK_DOWN,
        ui::DomKey::OS,
        0}},

      // Press Shift+Ctrl+Alt+Search+A. Confirm the event is not rewritten.
      {KeyTestCase::TEST_ALL,
       ui::ET_KEY_PRESSED,
       {ui::VKEY_B,
        ui::DomCode::KEY_B,
        ui::EF_SHIFT_DOWN | ui::EF_CONTROL_DOWN | ui::EF_ALT_DOWN |
            ui::EF_COMMAND_DOWN,
        ui::DomKey::CHARACTER,
        'B'},
       {ui::VKEY_B,
        ui::DomCode::KEY_B,
        ui::EF_SHIFT_DOWN | ui::EF_CONTROL_DOWN | ui::EF_ALT_DOWN |
            ui::EF_COMMAND_DOWN,
        ui::DomKey::CHARACTER,
        'B'}},
  };

  for (size_t i = 0; i < arraysize(tests); ++i) {
    SCOPED_TRACE(i);
    CheckKeyTestCase(&rewriter, tests[i]);
  }
}

TEST_F(EventRewriterTest, TestRewriteModifiersDisableSome) {
  // Disable Search and Control keys.
  TestingPrefServiceSyncable prefs;
  chromeos::Preferences::RegisterProfilePrefs(prefs.registry());
  IntegerPrefMember search;
  search.Init(prefs::kLanguageRemapSearchKeyTo, &prefs);
  search.SetValue(chromeos::input_method::kVoidKey);
  IntegerPrefMember control;
  control.Init(prefs::kLanguageRemapControlKeyTo, &prefs);
  control.SetValue(chromeos::input_method::kVoidKey);

  EventRewriter rewriter(NULL);
  rewriter.KeyboardDeviceAddedForTesting(kKeyboardDeviceId, "PC Keyboard");
  rewriter.set_pref_service_for_testing(&prefs);

  KeyTestCase disabled_modifier_tests[] = {
      // Press Alt with Shift. This key press shouldn't be affected by the
      // pref. Confirm the event is not rewritten.
      {KeyTestCase::TEST_ALL,
       ui::ET_KEY_PRESSED,
       {ui::VKEY_MENU,
        ui::DomCode::ALT_LEFT,
        ui::EF_SHIFT_DOWN | ui::EF_ALT_DOWN,
        ui::DomKey::ALT,
        0},
       {ui::VKEY_MENU,
        ui::DomCode::ALT_LEFT,
        ui::EF_SHIFT_DOWN | ui::EF_ALT_DOWN,
        ui::DomKey::ALT,
        0}},

      // Press Search. Confirm the event is now VKEY_UNKNOWN.
      {KeyTestCase::TEST_ALL,
       ui::ET_KEY_PRESSED,
       {ui::VKEY_LWIN, ui::DomCode::OS_LEFT, ui::EF_NONE, ui::DomKey::OS, 0},
       {ui::VKEY_UNKNOWN,
        ui::DomCode::NONE,
        ui::EF_NONE,
        ui::DomKey::UNIDENTIFIED,
        0}},

      // Press Control. Confirm the event is now VKEY_UNKNOWN.
      {KeyTestCase::TEST_ALL,
       ui::ET_KEY_PRESSED,
       {ui::VKEY_CONTROL,
        ui::DomCode::CONTROL_LEFT,
        ui::EF_CONTROL_DOWN,
        ui::DomKey::CONTROL,
        0},
       {ui::VKEY_UNKNOWN,
        ui::DomCode::NONE,
        ui::EF_NONE,
        ui::DomKey::UNIDENTIFIED,
        0}},

      // Press Control+Search. Confirm the event is now VKEY_UNKNOWN
      // without any modifiers.
      {KeyTestCase::TEST_ALL,
       ui::ET_KEY_PRESSED,
       {ui::VKEY_LWIN,
        ui::DomCode::OS_LEFT,
        ui::EF_CONTROL_DOWN,
        ui::DomKey::OS,
        0},
       {ui::VKEY_UNKNOWN,
        ui::DomCode::NONE,
        ui::EF_NONE,
        ui::DomKey::UNIDENTIFIED,
        0}},

      // Press Control+Search+a. Confirm the event is now VKEY_A without any
      // modifiers.
      {KeyTestCase::TEST_ALL,
       ui::ET_KEY_PRESSED,
       {ui::VKEY_A,
        ui::DomCode::KEY_A,
        ui::EF_CONTROL_DOWN,
        ui::DomKey::CHARACTER,
        'a'},
       {ui::VKEY_A,
        ui::DomCode::KEY_A,
        ui::EF_NONE,
        ui::DomKey::CHARACTER,
        'a'}},

      // Press Control+Search+Alt+a. Confirm the event is now VKEY_A only with
      // the Alt modifier.
      {KeyTestCase::TEST_ALL,
       ui::ET_KEY_PRESSED,
       {ui::VKEY_A,
        ui::DomCode::KEY_A,
        ui::EF_CONTROL_DOWN | ui::EF_ALT_DOWN,
        ui::DomKey::CHARACTER,
        'a'},
       {ui::VKEY_A,
        ui::DomCode::KEY_A,
        ui::EF_ALT_DOWN,
        ui::DomKey::CHARACTER,
        'a'}},
  };

  for (size_t i = 0; i < arraysize(disabled_modifier_tests); ++i) {
    SCOPED_TRACE(i);
    CheckKeyTestCase(&rewriter, disabled_modifier_tests[i]);
  }

  // Remap Alt to Control.
  IntegerPrefMember alt;
  alt.Init(prefs::kLanguageRemapAltKeyTo, &prefs);
  alt.SetValue(chromeos::input_method::kControlKey);

  KeyTestCase tests[] = {
      // Press left Alt. Confirm the event is now VKEY_CONTROL
      // even though the Control key itself is disabled.
      {KeyTestCase::TEST_ALL,
       ui::ET_KEY_PRESSED,
       {ui::VKEY_MENU,
        ui::DomCode::ALT_LEFT,
        ui::EF_ALT_DOWN,
        ui::DomKey::ALT,
        0},
       {ui::VKEY_CONTROL,
        ui::DomCode::CONTROL_LEFT,
        ui::EF_CONTROL_DOWN,
        ui::DomKey::CONTROL,
        0}},

      // Press Alt+a. Confirm the event is now Control+a even though the Control
      // key itself is disabled.
      {KeyTestCase::TEST_ALL,
       ui::ET_KEY_PRESSED,
       {ui::VKEY_A,
        ui::DomCode::KEY_A,
        ui::EF_ALT_DOWN,
        ui::DomKey::CHARACTER,
        'a'},
       {ui::VKEY_A,
        ui::DomCode::KEY_A,
        ui::EF_CONTROL_DOWN,
        ui::DomKey::CHARACTER,
        'a'}},
  };

  for (size_t i = 0; i < arraysize(tests); ++i) {
    SCOPED_TRACE(i);
    CheckKeyTestCase(&rewriter, tests[i]);
  }
}

TEST_F(EventRewriterTest, TestRewriteModifiersRemapToControl) {
  // Remap Search to Control.
  TestingPrefServiceSyncable prefs;
  chromeos::Preferences::RegisterProfilePrefs(prefs.registry());
  IntegerPrefMember search;
  search.Init(prefs::kLanguageRemapSearchKeyTo, &prefs);
  search.SetValue(chromeos::input_method::kControlKey);

  EventRewriter rewriter(NULL);
  rewriter.KeyboardDeviceAddedForTesting(kKeyboardDeviceId, "PC Keyboard");
  rewriter.set_pref_service_for_testing(&prefs);

  KeyTestCase s_tests[] = {
      // Press Search. Confirm the event is now VKEY_CONTROL.
      {KeyTestCase::TEST_ALL,
       ui::ET_KEY_PRESSED,
       {ui::VKEY_LWIN,
        ui::DomCode::OS_LEFT,
        ui::EF_COMMAND_DOWN,
        ui::DomKey::OS,
        0},
       {ui::VKEY_CONTROL,
        ui::DomCode::CONTROL_LEFT,
        ui::EF_CONTROL_DOWN,
        ui::DomKey::CONTROL,
        0}},
  };

  for (size_t i = 0; i < arraysize(s_tests); ++i) {
    SCOPED_TRACE(i);
    CheckKeyTestCase(&rewriter, s_tests[i]);
  }

  // Remap Alt to Control too.
  IntegerPrefMember alt;
  alt.Init(prefs::kLanguageRemapAltKeyTo, &prefs);
  alt.SetValue(chromeos::input_method::kControlKey);

  KeyTestCase sa_tests[] = {
      // Press Alt. Confirm the event is now VKEY_CONTROL.
      {KeyTestCase::TEST_ALL,
       ui::ET_KEY_PRESSED,
       {ui::VKEY_MENU,
        ui::DomCode::ALT_LEFT,
        ui::EF_ALT_DOWN,
        ui::DomKey::ALT,
        0},
       {ui::VKEY_CONTROL,
        ui::DomCode::CONTROL_LEFT,
        ui::EF_CONTROL_DOWN,
        ui::DomKey::CONTROL,
        0}},

      // Press Alt+Search. Confirm the event is now VKEY_CONTROL.
      {KeyTestCase::TEST_ALL,
       ui::ET_KEY_PRESSED,
       {ui::VKEY_LWIN,
        ui::DomCode::OS_LEFT,
        ui::EF_ALT_DOWN | ui::EF_COMMAND_DOWN,
        ui::DomKey::OS,
        0},
       {ui::VKEY_CONTROL,
        ui::DomCode::CONTROL_LEFT,
        ui::EF_CONTROL_DOWN,
        ui::DomKey::CONTROL,
        0}},

      // Press Control+Alt+Search. Confirm the event is now VKEY_CONTROL.
      {KeyTestCase::TEST_ALL,
       ui::ET_KEY_PRESSED,
       {ui::VKEY_LWIN,
        ui::DomCode::OS_LEFT,
        ui::EF_CONTROL_DOWN | ui::EF_ALT_DOWN | ui::EF_COMMAND_DOWN,
        ui::DomKey::OS,
        0},
       {ui::VKEY_CONTROL,
        ui::DomCode::CONTROL_LEFT,
        ui::EF_CONTROL_DOWN,
        ui::DomKey::CONTROL,
        0}},

      // Press Shift+Control+Alt+Search. Confirm the event is now Control with
      // Shift and Control modifiers.
      {KeyTestCase::TEST_ALL,
       ui::ET_KEY_PRESSED,
       {ui::VKEY_LWIN,
        ui::DomCode::OS_LEFT,
        ui::EF_SHIFT_DOWN | ui::EF_CONTROL_DOWN | ui::EF_ALT_DOWN |
            ui::EF_COMMAND_DOWN,
        ui::DomKey::OS,
        0},
       {ui::VKEY_CONTROL,
        ui::DomCode::CONTROL_LEFT,
        ui::EF_SHIFT_DOWN | ui::EF_CONTROL_DOWN,
        ui::DomKey::CONTROL,
        0}},

      // Press Shift+Control+Alt+Search+B. Confirm the event is now B with Shift
      // and Control modifiers.
      {KeyTestCase::TEST_ALL,
       ui::ET_KEY_PRESSED,
       {ui::VKEY_B,
        ui::DomCode::KEY_B,
        ui::EF_SHIFT_DOWN | ui::EF_CONTROL_DOWN | ui::EF_ALT_DOWN |
            ui::EF_COMMAND_DOWN,
        ui::DomKey::CHARACTER,
        'B'},
       {ui::VKEY_B,
        ui::DomCode::KEY_B,
        ui::EF_SHIFT_DOWN | ui::EF_CONTROL_DOWN,
        ui::DomKey::CHARACTER,
        'B'}},
  };

  for (size_t i = 0; i < arraysize(sa_tests); ++i) {
    SCOPED_TRACE(i);
    CheckKeyTestCase(&rewriter, sa_tests[i]);
  }
}

TEST_F(EventRewriterTest, TestRewriteModifiersRemapToEscape) {
  // Remap Search to ESC.
  TestingPrefServiceSyncable prefs;
  chromeos::Preferences::RegisterProfilePrefs(prefs.registry());
  IntegerPrefMember search;
  search.Init(prefs::kLanguageRemapSearchKeyTo, &prefs);
  search.SetValue(chromeos::input_method::kEscapeKey);

  EventRewriter rewriter(NULL);
  rewriter.KeyboardDeviceAddedForTesting(kKeyboardDeviceId, "PC Keyboard");
  rewriter.set_pref_service_for_testing(&prefs);

  KeyTestCase tests[] = {
      // Press Search. Confirm the event is now VKEY_ESCAPE.
      {KeyTestCase::TEST_ALL,
       ui::ET_KEY_PRESSED,
       {ui::VKEY_LWIN,
        ui::DomCode::OS_LEFT,
        ui::EF_COMMAND_DOWN,
        ui::DomKey::OS,
        0},
       {ui::VKEY_ESCAPE,
        ui::DomCode::ESCAPE,
        ui::EF_NONE,
        ui::DomKey::ESCAPE,
        0}},
  };

  for (size_t i = 0; i < arraysize(tests); ++i) {
    SCOPED_TRACE(i);
    CheckKeyTestCase(&rewriter, tests[i]);
  }
}

TEST_F(EventRewriterTest, TestRewriteModifiersRemapMany) {
  // Remap Search to Alt.
  TestingPrefServiceSyncable prefs;
  chromeos::Preferences::RegisterProfilePrefs(prefs.registry());
  IntegerPrefMember search;
  search.Init(prefs::kLanguageRemapSearchKeyTo, &prefs);
  search.SetValue(chromeos::input_method::kAltKey);

  EventRewriter rewriter(NULL);
  rewriter.KeyboardDeviceAddedForTesting(kKeyboardDeviceId, "PC Keyboard");
  rewriter.set_pref_service_for_testing(&prefs);

  KeyTestCase s2a_tests[] = {
      // Press Search. Confirm the event is now VKEY_MENU.
      {KeyTestCase::TEST_ALL,
       ui::ET_KEY_PRESSED,
       {ui::VKEY_LWIN,
        ui::DomCode::OS_LEFT,
        ui::EF_COMMAND_DOWN,
        ui::DomKey::OS,
        0},
       {ui::VKEY_MENU,
        ui::DomCode::ALT_LEFT,
        ui::EF_ALT_DOWN,
        ui::DomKey::ALT,
        0}},
  };

  for (size_t i = 0; i < arraysize(s2a_tests); ++i) {
    SCOPED_TRACE(i);
    CheckKeyTestCase(&rewriter, s2a_tests[i]);
  }

  // Remap Alt to Control.
  IntegerPrefMember alt;
  alt.Init(prefs::kLanguageRemapAltKeyTo, &prefs);
  alt.SetValue(chromeos::input_method::kControlKey);

  KeyTestCase a2c_tests[] = {
      // Press left Alt. Confirm the event is now VKEY_CONTROL.
      {KeyTestCase::TEST_ALL,
       ui::ET_KEY_PRESSED,
       {ui::VKEY_MENU,
        ui::DomCode::ALT_LEFT,
        ui::EF_ALT_DOWN,
        ui::DomKey::ALT,
        0},
       {ui::VKEY_CONTROL,
        ui::DomCode::CONTROL_LEFT,
        ui::EF_CONTROL_DOWN,
        ui::DomKey::CONTROL,
        0}},
      // Press Shift+comma. Verify that only the flags are changed.
      // The X11 portion of the test addresses crbug.com/390263 by verifying
      // that the X keycode remains that for ',<' and not for 105-key '<>'.
      {KeyTestCase::TEST_ALL,
       ui::ET_KEY_PRESSED,
       {ui::VKEY_OEM_COMMA,
        ui::DomCode::COMMA,
        ui::EF_SHIFT_DOWN | ui::EF_ALT_DOWN,
        ui::DomKey::UNIDENTIFIED,
        0},
       {ui::VKEY_OEM_COMMA,
        ui::DomCode::COMMA,
        ui::EF_SHIFT_DOWN | ui::EF_CONTROL_DOWN,
        ui::DomKey::UNIDENTIFIED,
        0}},
      // Press Shift+9. Verify that only the flags are changed.
      {KeyTestCase::TEST_ALL,
       ui::ET_KEY_PRESSED,
       {ui::VKEY_9,
        ui::DomCode::DIGIT9,
        ui::EF_SHIFT_DOWN | ui::EF_ALT_DOWN,
        ui::DomKey::CHARACTER,
        '9'},
       {ui::VKEY_9,
        ui::DomCode::DIGIT9,
        ui::EF_SHIFT_DOWN | ui::EF_CONTROL_DOWN,
        ui::DomKey::CHARACTER,
        '9'}},
  };

  for (size_t i = 0; i < arraysize(a2c_tests); ++i) {
    SCOPED_TRACE(i);
    CheckKeyTestCase(&rewriter, a2c_tests[i]);
  }

  // Remap Control to Search.
  IntegerPrefMember control;
  control.Init(prefs::kLanguageRemapControlKeyTo, &prefs);
  control.SetValue(chromeos::input_method::kSearchKey);

  KeyTestCase c2s_tests[] = {
      // Press left Control. Confirm the event is now VKEY_LWIN.
      {KeyTestCase::TEST_ALL,
       ui::ET_KEY_PRESSED,
       {ui::VKEY_CONTROL,
        ui::DomCode::CONTROL_LEFT,
        ui::EF_CONTROL_DOWN,
        ui::DomKey::CONTROL,
        0},
       {ui::VKEY_LWIN,
        ui::DomCode::OS_LEFT,
        ui::EF_COMMAND_DOWN,
        ui::DomKey::OS,
        0}},

      // Then, press all of the three, Control+Alt+Search.
      {KeyTestCase::TEST_ALL,
       ui::ET_KEY_PRESSED,
       {ui::VKEY_LWIN,
        ui::DomCode::OS_LEFT,
        ui::EF_CONTROL_DOWN | ui::EF_ALT_DOWN | ui::EF_COMMAND_DOWN,
        ui::DomKey::OS,
        0},
       {ui::VKEY_MENU,
        ui::DomCode::ALT_LEFT,
        ui::EF_CONTROL_DOWN | ui::EF_ALT_DOWN | ui::EF_COMMAND_DOWN,
        ui::DomKey::ALT,
        0}},

      // Press Shift+Control+Alt+Search.
      {KeyTestCase::TEST_ALL,
       ui::ET_KEY_PRESSED,
       {ui::VKEY_LWIN,
        ui::DomCode::OS_LEFT,
        ui::EF_SHIFT_DOWN | ui::EF_CONTROL_DOWN | ui::EF_ALT_DOWN |
            ui::EF_COMMAND_DOWN,
        ui::DomKey::OS,
        0},
       {ui::VKEY_MENU,
        ui::DomCode::ALT_LEFT,
        ui::EF_SHIFT_DOWN | ui::EF_CONTROL_DOWN | ui::EF_ALT_DOWN |
            ui::EF_COMMAND_DOWN,
        ui::DomKey::ALT,
        0}},

      // Press Shift+Control+Alt+Search+B
      {KeyTestCase::TEST_ALL,
       ui::ET_KEY_PRESSED,
       {ui::VKEY_B,
        ui::DomCode::KEY_B,
        ui::EF_SHIFT_DOWN | ui::EF_CONTROL_DOWN | ui::EF_ALT_DOWN |
            ui::EF_COMMAND_DOWN,
        ui::DomKey::CHARACTER,
        'B'},
       {ui::VKEY_B,
        ui::DomCode::KEY_B,
        ui::EF_SHIFT_DOWN | ui::EF_CONTROL_DOWN | ui::EF_ALT_DOWN |
            ui::EF_COMMAND_DOWN,
        ui::DomKey::CHARACTER,
        'B'}},
  };

  for (size_t i = 0; i < arraysize(c2s_tests); ++i) {
    SCOPED_TRACE(i);
    CheckKeyTestCase(&rewriter, c2s_tests[i]);
  }
}

TEST_F(EventRewriterTest, TestRewriteModifiersRemapToCapsLock) {
  // Remap Search to Caps Lock.
  TestingPrefServiceSyncable prefs;
  chromeos::Preferences::RegisterProfilePrefs(prefs.registry());
  IntegerPrefMember search;
  search.Init(prefs::kLanguageRemapSearchKeyTo, &prefs);
  search.SetValue(chromeos::input_method::kCapsLockKey);

  chromeos::input_method::FakeImeKeyboard ime_keyboard;
  EventRewriter rewriter(NULL);
  rewriter.KeyboardDeviceAddedForTesting(kKeyboardDeviceId, "PC Keyboard");
  rewriter.set_pref_service_for_testing(&prefs);
  rewriter.set_ime_keyboard_for_testing(&ime_keyboard);
  EXPECT_FALSE(ime_keyboard.caps_lock_is_enabled_);

  // Press Search.
  EXPECT_EQ(GetExpectedResultAsString(ui::ET_KEY_PRESSED, ui::VKEY_CAPITAL,
                                      ui::DomCode::CAPS_LOCK,
                                      ui::EF_CAPS_LOCK_DOWN | ui::EF_MOD3_DOWN,
                                      ui::DomKey::CAPS_LOCK, 0),
            GetRewrittenEventAsString(&rewriter, ui::ET_KEY_PRESSED,
                                      ui::VKEY_LWIN, ui::DomCode::OS_LEFT,
                                      ui::EF_COMMAND_DOWN, ui::DomKey::OS, 0));
  // Confirm that the Caps Lock status is changed.
  EXPECT_TRUE(ime_keyboard.caps_lock_is_enabled_);

  // Release Search.
  EXPECT_EQ(GetExpectedResultAsString(ui::ET_KEY_RELEASED, ui::VKEY_CAPITAL,
                                      ui::DomCode::CAPS_LOCK, ui::EF_NONE,
                                      ui::DomKey::CAPS_LOCK, 0),
            GetRewrittenEventAsString(&rewriter, ui::ET_KEY_RELEASED,
                                      ui::VKEY_LWIN, ui::DomCode::OS_LEFT,
                                      ui::EF_NONE, ui::DomKey::OS, 0));
  // Confirm that the Caps Lock status is not changed.
  EXPECT_TRUE(ime_keyboard.caps_lock_is_enabled_);

  // Press Search.
  EXPECT_EQ(
      GetExpectedResultAsString(
          ui::ET_KEY_PRESSED, ui::VKEY_CAPITAL, ui::DomCode::CAPS_LOCK,
          ui::EF_CAPS_LOCK_DOWN | ui::EF_MOD3_DOWN, ui::DomKey::CAPS_LOCK, 0),
      GetRewrittenEventAsString(
          &rewriter, ui::ET_KEY_PRESSED, ui::VKEY_LWIN, ui::DomCode::OS_LEFT,
          ui::EF_COMMAND_DOWN | ui::EF_CAPS_LOCK_DOWN, ui::DomKey::OS, 0));
  // Confirm that the Caps Lock status is changed.
  EXPECT_FALSE(ime_keyboard.caps_lock_is_enabled_);

  // Release Search.
  EXPECT_EQ(GetExpectedResultAsString(ui::ET_KEY_RELEASED, ui::VKEY_CAPITAL,
                                      ui::DomCode::CAPS_LOCK, ui::EF_NONE,
                                      ui::DomKey::CAPS_LOCK, 0),
            GetRewrittenEventAsString(&rewriter, ui::ET_KEY_RELEASED,
                                      ui::VKEY_LWIN, ui::DomCode::OS_LEFT,
                                      ui::EF_NONE, ui::DomKey::OS, 0));
  // Confirm that the Caps Lock status is not changed.
  EXPECT_FALSE(ime_keyboard.caps_lock_is_enabled_);

  // Press Caps Lock (on an external keyboard).
  EXPECT_EQ(GetExpectedResultAsString(ui::ET_KEY_PRESSED, ui::VKEY_CAPITAL,
                                      ui::DomCode::CAPS_LOCK,
                                      ui::EF_CAPS_LOCK_DOWN | ui::EF_MOD3_DOWN,
                                      ui::DomKey::CAPS_LOCK, 0),
            GetRewrittenEventAsString(&rewriter, ui::ET_KEY_PRESSED,
                                      ui::VKEY_CAPITAL, ui::DomCode::CAPS_LOCK,
                                      ui::EF_CAPS_LOCK_DOWN | ui::EF_MOD3_DOWN,
                                      ui::DomKey::CAPS_LOCK, 0));

  // Confirm that calling RewriteForTesting() does not change the state of
  // |ime_keyboard|. In this case, X Window system itself should change the
  // Caps Lock state, not ash::EventRewriter.
  EXPECT_FALSE(ime_keyboard.caps_lock_is_enabled_);

  // Release Caps Lock (on an external keyboard).
  EXPECT_EQ(GetExpectedResultAsString(ui::ET_KEY_RELEASED, ui::VKEY_CAPITAL,
                                      ui::DomCode::CAPS_LOCK, ui::EF_NONE,
                                      ui::DomKey::CAPS_LOCK, 0),
            GetRewrittenEventAsString(&rewriter, ui::ET_KEY_RELEASED,
                                      ui::VKEY_CAPITAL, ui::DomCode::CAPS_LOCK,
                                      ui::EF_NONE, ui::DomKey::CAPS_LOCK, 0));
  EXPECT_FALSE(ime_keyboard.caps_lock_is_enabled_);
}

TEST_F(EventRewriterTest, TestRewriteCapsLock) {
  TestingPrefServiceSyncable prefs;
  chromeos::Preferences::RegisterProfilePrefs(prefs.registry());

  chromeos::input_method::FakeImeKeyboard ime_keyboard;
  EventRewriter rewriter(NULL);
  rewriter.KeyboardDeviceAddedForTesting(kKeyboardDeviceId, "PC Keyboard");
  rewriter.set_pref_service_for_testing(&prefs);
  rewriter.set_ime_keyboard_for_testing(&ime_keyboard);
  EXPECT_FALSE(ime_keyboard.caps_lock_is_enabled_);

  // On Chrome OS, CapsLock is mapped to F16 with Mod3Mask.
  EXPECT_EQ(GetExpectedResultAsString(ui::ET_KEY_PRESSED, ui::VKEY_CAPITAL,
                                      ui::DomCode::CAPS_LOCK,
                                      ui::EF_CAPS_LOCK_DOWN | ui::EF_MOD3_DOWN,
                                      ui::DomKey::CAPS_LOCK, 0),
            GetRewrittenEventAsString(&rewriter, ui::ET_KEY_PRESSED,
                                      ui::VKEY_F16, ui::DomCode::F16,
                                      ui::EF_MOD3_DOWN, ui::DomKey::F16, 0));
  EXPECT_TRUE(ime_keyboard.caps_lock_is_enabled_);
}

TEST_F(EventRewriterTest, TestRewriteDiamondKey) {
  TestingPrefServiceSyncable prefs;
  chromeos::Preferences::RegisterProfilePrefs(prefs.registry());

  chromeos::input_method::FakeImeKeyboard ime_keyboard;
  EventRewriter rewriter(NULL);
  rewriter.KeyboardDeviceAddedForTesting(kKeyboardDeviceId, "PC Keyboard");
  rewriter.set_pref_service_for_testing(&prefs);
  rewriter.set_ime_keyboard_for_testing(&ime_keyboard);

  KeyTestCase tests[] = {
      // F15 should work as Ctrl when --has-chromeos-diamond-key is not
      // specified.
      {KeyTestCase::TEST_VKEY,
       ui::ET_KEY_PRESSED,
       {ui::VKEY_F15, ui::DomCode::F15, ui::EF_NONE, ui::DomKey::F15, 0},
       {ui::VKEY_CONTROL,
        ui::DomCode::CONTROL_LEFT,
        ui::EF_CONTROL_DOWN,
        ui::DomKey::CONTROL,
        0}},

      {KeyTestCase::TEST_VKEY,
       ui::ET_KEY_RELEASED,
       {ui::VKEY_F15, ui::DomCode::F15, ui::EF_NONE, ui::DomKey::F15, 0},
       {ui::VKEY_CONTROL,
        ui::DomCode::CONTROL_LEFT,
        ui::EF_NONE,
        ui::DomKey::CONTROL,
        0}},

      // However, Mod2Mask should not be rewritten to CtrlMask when
      // --has-chromeos-diamond-key is not specified.
      {KeyTestCase::TEST_VKEY,
       ui::ET_KEY_PRESSED,
       {ui::VKEY_A,
        ui::DomCode::KEY_A,
        ui::EF_NONE,
        ui::DomKey::CHARACTER,
        'a'},
       {ui::VKEY_A,
        ui::DomCode::KEY_A,
        ui::EF_NONE,
        ui::DomKey::CHARACTER,
        'a'}},
  };

  for (size_t i = 0; i < arraysize(tests); ++i) {
    SCOPED_TRACE(i);
    CheckKeyTestCase(&rewriter, tests[i]);
  }
}

TEST_F(EventRewriterTest, TestRewriteDiamondKeyWithFlag) {
  const base::CommandLine original_cl(*base::CommandLine::ForCurrentProcess());
  base::CommandLine::ForCurrentProcess()->AppendSwitchASCII(
      chromeos::switches::kHasChromeOSDiamondKey, "");

  TestingPrefServiceSyncable prefs;
  chromeos::Preferences::RegisterProfilePrefs(prefs.registry());

  chromeos::input_method::FakeImeKeyboard ime_keyboard;
  EventRewriter rewriter(NULL);
  rewriter.KeyboardDeviceAddedForTesting(kKeyboardDeviceId, "PC Keyboard");
  rewriter.set_pref_service_for_testing(&prefs);
  rewriter.set_ime_keyboard_for_testing(&ime_keyboard);

  // By default, F15 should work as Control.
  EXPECT_EQ(GetExpectedResultAsString(
                ui::ET_KEY_PRESSED, ui::VKEY_CONTROL, ui::DomCode::CONTROL_LEFT,
                ui::EF_CONTROL_DOWN, ui::DomKey::CONTROL, 0),
            GetRewrittenEventAsString(&rewriter, ui::ET_KEY_PRESSED,
                                      ui::VKEY_F15, ui::DomCode::F15,
                                      ui::EF_NONE, ui::DomKey::F15, 0));
  // Check that Control is applied to a subsequent key press.
  EXPECT_EQ(GetExpectedResultAsString(ui::ET_KEY_PRESSED, ui::VKEY_A,
                                      ui::DomCode::KEY_A, ui::EF_CONTROL_DOWN,
                                      ui::DomKey::CHARACTER, 'a'),
            GetRewrittenEventAsString(&rewriter, ui::ET_KEY_PRESSED, ui::VKEY_A,
                                      ui::DomCode::KEY_A, ui::EF_NONE,
                                      ui::DomKey::CHARACTER, 'a'));
  // Release F15
  EXPECT_EQ(GetExpectedResultAsString(ui::ET_KEY_RELEASED, ui::VKEY_CONTROL,
                                      ui::DomCode::CONTROL_LEFT, ui::EF_NONE,
                                      ui::DomKey::CONTROL, 0),
            GetRewrittenEventAsString(&rewriter, ui::ET_KEY_RELEASED,
                                      ui::VKEY_F15, ui::DomCode::F15,
                                      ui::EF_NONE, ui::DomKey::F15, 0));
  // Check that Control is no longer applied to a subsequent key press.
  EXPECT_EQ(GetExpectedResultAsString(ui::ET_KEY_PRESSED, ui::VKEY_A,
                                      ui::DomCode::KEY_A, ui::EF_NONE,
                                      ui::DomKey::CHARACTER, 'a'),
            GetRewrittenEventAsString(&rewriter, ui::ET_KEY_PRESSED, ui::VKEY_A,
                                      ui::DomCode::KEY_A, ui::EF_NONE,
                                      ui::DomKey::CHARACTER, 'a'));

  IntegerPrefMember diamond;
  diamond.Init(prefs::kLanguageRemapDiamondKeyTo, &prefs);
  diamond.SetValue(chromeos::input_method::kVoidKey);

  EXPECT_EQ(GetExpectedResultAsString(ui::ET_KEY_PRESSED, ui::VKEY_UNKNOWN,
                                      ui::DomCode::NONE, ui::EF_NONE,
                                      ui::DomKey::NONE, 0),
            GetRewrittenEventAsString(&rewriter, ui::ET_KEY_PRESSED,
                                      ui::VKEY_F15, ui::DomCode::F15,
                                      ui::EF_NONE, ui::DomKey::F15, 0));
  // Check that no modifier is applied to another key.
  EXPECT_EQ(GetExpectedResultAsString(ui::ET_KEY_PRESSED, ui::VKEY_A,
                                      ui::DomCode::KEY_A, ui::EF_NONE,
                                      ui::DomKey::CHARACTER, 'a'),
            GetRewrittenEventAsString(&rewriter, ui::ET_KEY_PRESSED, ui::VKEY_A,
                                      ui::DomCode::KEY_A, ui::EF_NONE,
                                      ui::DomKey::CHARACTER, 'a'));

  diamond.SetValue(chromeos::input_method::kControlKey);

  EXPECT_EQ(GetExpectedResultAsString(
                ui::ET_KEY_PRESSED, ui::VKEY_CONTROL, ui::DomCode::CONTROL_LEFT,
                ui::EF_CONTROL_DOWN, ui::DomKey::CONTROL, 0),
            GetRewrittenEventAsString(&rewriter, ui::ET_KEY_PRESSED,
                                      ui::VKEY_F15, ui::DomCode::F15,
                                      ui::EF_NONE, ui::DomKey::F15, 0));
  // Check that Control is applied to a subsequent key press.
  EXPECT_EQ(GetExpectedResultAsString(ui::ET_KEY_PRESSED, ui::VKEY_A,
                                      ui::DomCode::KEY_A, ui::EF_CONTROL_DOWN,
                                      ui::DomKey::CHARACTER, 'a'),
            GetRewrittenEventAsString(&rewriter, ui::ET_KEY_PRESSED, ui::VKEY_A,
                                      ui::DomCode::KEY_A, ui::EF_NONE,
                                      ui::DomKey::CHARACTER, 'a'));
  // Release F15
  EXPECT_EQ(GetExpectedResultAsString(ui::ET_KEY_RELEASED, ui::VKEY_CONTROL,
                                      ui::DomCode::CONTROL_LEFT, ui::EF_NONE,
                                      ui::DomKey::CONTROL, 0),
            GetRewrittenEventAsString(&rewriter, ui::ET_KEY_RELEASED,
                                      ui::VKEY_F15, ui::DomCode::F15,
                                      ui::EF_NONE, ui::DomKey::F15, 0));
  // Check that Control is no longer applied to a subsequent key press.
  EXPECT_EQ(GetExpectedResultAsString(ui::ET_KEY_PRESSED, ui::VKEY_A,
                                      ui::DomCode::KEY_A, ui::EF_NONE,
                                      ui::DomKey::CHARACTER, 'a'),
            GetRewrittenEventAsString(&rewriter, ui::ET_KEY_PRESSED, ui::VKEY_A,
                                      ui::DomCode::KEY_A, ui::EF_NONE,
                                      ui::DomKey::CHARACTER, 'a'));

  diamond.SetValue(chromeos::input_method::kAltKey);

  EXPECT_EQ(GetExpectedResultAsString(ui::ET_KEY_PRESSED, ui::VKEY_MENU,
                                      ui::DomCode::ALT_LEFT, ui::EF_ALT_DOWN,
                                      ui::DomKey::ALT, 0),
            GetRewrittenEventAsString(&rewriter, ui::ET_KEY_PRESSED,
                                      ui::VKEY_F15, ui::DomCode::F15,
                                      ui::EF_NONE, ui::DomKey::F15, 0));
  // Check that Alt is applied to a subsequent key press.
  EXPECT_EQ(GetExpectedResultAsString(ui::ET_KEY_PRESSED, ui::VKEY_A,
                                      ui::DomCode::KEY_A, ui::EF_ALT_DOWN,
                                      ui::DomKey::CHARACTER, 'a'),
            GetRewrittenEventAsString(&rewriter, ui::ET_KEY_PRESSED, ui::VKEY_A,
                                      ui::DomCode::KEY_A, ui::EF_NONE,
                                      ui::DomKey::CHARACTER, 'a'));
  // Release F15
  EXPECT_EQ(GetExpectedResultAsString(ui::ET_KEY_RELEASED, ui::VKEY_MENU,
                                      ui::DomCode::ALT_LEFT, ui::EF_NONE,
                                      ui::DomKey::ALT, 0),
            GetRewrittenEventAsString(&rewriter, ui::ET_KEY_RELEASED,
                                      ui::VKEY_F15, ui::DomCode::F15,
                                      ui::EF_NONE, ui::DomKey::F15, 0));
  // Check that Alt is no longer applied to a subsequent key press.
  EXPECT_EQ(GetExpectedResultAsString(ui::ET_KEY_PRESSED, ui::VKEY_A,
                                      ui::DomCode::KEY_A, ui::EF_NONE,
                                      ui::DomKey::CHARACTER, 'a'),
            GetRewrittenEventAsString(&rewriter, ui::ET_KEY_PRESSED, ui::VKEY_A,
                                      ui::DomCode::KEY_A, ui::EF_NONE,
                                      ui::DomKey::CHARACTER, 'a'));

  diamond.SetValue(chromeos::input_method::kCapsLockKey);

  EXPECT_EQ(GetExpectedResultAsString(ui::ET_KEY_PRESSED, ui::VKEY_CAPITAL,
                                      ui::DomCode::CAPS_LOCK,
                                      ui::EF_CAPS_LOCK_DOWN | ui::EF_MOD3_DOWN,
                                      ui::DomKey::CAPS_LOCK, 0),
            GetRewrittenEventAsString(&rewriter, ui::ET_KEY_PRESSED,
                                      ui::VKEY_F15, ui::DomCode::F15,
                                      ui::EF_NONE, ui::DomKey::F15, 0));
  // Check that Caps is applied to a subsequent key press.
  EXPECT_EQ(GetExpectedResultAsString(ui::ET_KEY_PRESSED, ui::VKEY_A,
                                      ui::DomCode::KEY_A,
                                      ui::EF_CAPS_LOCK_DOWN | ui::EF_MOD3_DOWN,
                                      ui::DomKey::CHARACTER, 'a'),
            GetRewrittenEventAsString(&rewriter, ui::ET_KEY_PRESSED, ui::VKEY_A,
                                      ui::DomCode::KEY_A, ui::EF_NONE,
                                      ui::DomKey::CHARACTER, 'a'));
  // Release F15
  EXPECT_EQ(GetExpectedResultAsString(ui::ET_KEY_RELEASED, ui::VKEY_CAPITAL,
                                      ui::DomCode::CAPS_LOCK, ui::EF_NONE,
                                      ui::DomKey::CAPS_LOCK, 0),
            GetRewrittenEventAsString(&rewriter, ui::ET_KEY_RELEASED,
                                      ui::VKEY_F15, ui::DomCode::F15,
                                      ui::EF_NONE, ui::DomKey::F15, 0));
  // Check that Control is no longer applied to a subsequent key press.
  EXPECT_EQ(GetExpectedResultAsString(ui::ET_KEY_PRESSED, ui::VKEY_A,
                                      ui::DomCode::KEY_A, ui::EF_NONE,
                                      ui::DomKey::CHARACTER, 'a'),
            GetRewrittenEventAsString(&rewriter, ui::ET_KEY_PRESSED, ui::VKEY_A,
                                      ui::DomCode::KEY_A, ui::EF_NONE,
                                      ui::DomKey::CHARACTER, 'a'));

  *base::CommandLine::ForCurrentProcess() = original_cl;
}

TEST_F(EventRewriterTest, TestRewriteCapsLockToControl) {
  // Remap CapsLock to Control.
  TestingPrefServiceSyncable prefs;
  chromeos::Preferences::RegisterProfilePrefs(prefs.registry());
  IntegerPrefMember control;
  control.Init(prefs::kLanguageRemapCapsLockKeyTo, &prefs);
  control.SetValue(chromeos::input_method::kControlKey);

  EventRewriter rewriter(NULL);
  rewriter.KeyboardDeviceAddedForTesting(kKeyboardDeviceId, "PC Keyboard");
  rewriter.set_pref_service_for_testing(&prefs);

  KeyTestCase tests[] = {
      // Press CapsLock+a. Confirm that Mod3Mask is rewritten to ControlMask.
      // On Chrome OS, CapsLock works as a Mod3 modifier.
      {KeyTestCase::TEST_ALL,
       ui::ET_KEY_PRESSED,
       {ui::VKEY_A,
        ui::DomCode::KEY_A,
        ui::EF_MOD3_DOWN,
        ui::DomKey::CHARACTER,
        'a'},
       {ui::VKEY_A,
        ui::DomCode::KEY_A,
        ui::EF_CONTROL_DOWN,
        ui::DomKey::CHARACTER,
        'a'}},

      // Press Control+CapsLock+a. Confirm that Mod3Mask is rewritten to
      // ControlMask
      {KeyTestCase::TEST_ALL,
       ui::ET_KEY_PRESSED,
       {ui::VKEY_A,
        ui::DomCode::KEY_A,
        ui::EF_CONTROL_DOWN | ui::EF_MOD3_DOWN,
        ui::DomKey::CHARACTER,
        'a'},
       {ui::VKEY_A,
        ui::DomCode::KEY_A,
        ui::EF_CONTROL_DOWN,
        ui::DomKey::CHARACTER,
        'a'}},

      // Press Alt+CapsLock+a. Confirm that Mod3Mask is rewritten to
      // ControlMask.
      {KeyTestCase::TEST_ALL,
       ui::ET_KEY_PRESSED,
       {ui::VKEY_A,
        ui::DomCode::KEY_A,
        ui::EF_ALT_DOWN | ui::EF_MOD3_DOWN,
        ui::DomKey::CHARACTER,
        'a'},
       {ui::VKEY_A,
        ui::DomCode::KEY_A,
        ui::EF_ALT_DOWN | ui::EF_CONTROL_DOWN,
        ui::DomKey::CHARACTER,
        'a'}},
  };

  for (size_t i = 0; i < arraysize(tests); ++i) {
    SCOPED_TRACE(i);
    CheckKeyTestCase(&rewriter, tests[i]);
  }
}

TEST_F(EventRewriterTest, TestRewriteCapsLockMod3InUse) {
  // Remap CapsLock to Control.
  TestingPrefServiceSyncable prefs;
  chromeos::Preferences::RegisterProfilePrefs(prefs.registry());
  IntegerPrefMember control;
  control.Init(prefs::kLanguageRemapCapsLockKeyTo, &prefs);
  control.SetValue(chromeos::input_method::kControlKey);

  EventRewriter rewriter(NULL);
  rewriter.KeyboardDeviceAddedForTesting(kKeyboardDeviceId, "PC Keyboard");
  rewriter.set_pref_service_for_testing(&prefs);
  input_method_manager_mock_->set_mod3_used(true);

  // Press CapsLock+a. Confirm that Mod3Mask is NOT rewritten to ControlMask
  // when Mod3Mask is already in use by the current XKB layout.
  EXPECT_EQ(GetExpectedResultAsString(ui::ET_KEY_PRESSED, ui::VKEY_A,
                                      ui::DomCode::KEY_A, ui::EF_NONE,
                                      ui::DomKey::CHARACTER, 'a'),
            GetRewrittenEventAsString(&rewriter, ui::ET_KEY_PRESSED, ui::VKEY_A,
                                      ui::DomCode::KEY_A, ui::EF_NONE,
                                      ui::DomKey::CHARACTER, 'a'));

  input_method_manager_mock_->set_mod3_used(false);
}

TEST_F(EventRewriterTest, TestRewriteExtendedKeys) {
  TestingPrefServiceSyncable prefs;
  chromeos::Preferences::RegisterProfilePrefs(prefs.registry());
  EventRewriter rewriter(NULL);
  rewriter.KeyboardDeviceAddedForTesting(kKeyboardDeviceId, "PC Keyboard");
  rewriter.set_last_keyboard_device_id_for_testing(kKeyboardDeviceId);
  rewriter.set_pref_service_for_testing(&prefs);

  KeyTestCase tests[] = {
      // Alt+Backspace -> Delete
      {KeyTestCase::TEST_ALL,
       ui::ET_KEY_PRESSED,
       {ui::VKEY_BACK,
        ui::DomCode::BACKSPACE,
        ui::EF_ALT_DOWN,
        ui::DomKey::BACKSPACE,
        0},
       {ui::VKEY_DELETE, ui::DomCode::DEL, ui::EF_NONE, ui::DomKey::DEL, 0}},
      // Control+Alt+Backspace -> Control+Delete
      {KeyTestCase::TEST_ALL,
       ui::ET_KEY_PRESSED,
       {ui::VKEY_BACK,
        ui::DomCode::BACKSPACE,
        ui::EF_ALT_DOWN | ui::EF_CONTROL_DOWN,
        ui::DomKey::BACKSPACE,
        0},
       {ui::VKEY_DELETE,
        ui::DomCode::DEL,
        ui::EF_CONTROL_DOWN,
        ui::DomKey::DEL,
        0}},
      // Search+Alt+Backspace -> Alt+Backspace
      {KeyTestCase::TEST_ALL,
       ui::ET_KEY_PRESSED,
       {ui::VKEY_BACK,
        ui::DomCode::BACKSPACE,
        ui::EF_COMMAND_DOWN | ui::EF_ALT_DOWN,
        ui::DomKey::BACKSPACE,
        0},
       {ui::VKEY_BACK,
        ui::DomCode::BACKSPACE,
        ui::EF_ALT_DOWN,
        ui::DomKey::BACKSPACE,
        0}},
      // Search+Control+Alt+Backspace -> Control+Alt+Backspace
      {KeyTestCase::TEST_ALL,
       ui::ET_KEY_PRESSED,
       {ui::VKEY_BACK,
        ui::DomCode::BACKSPACE,
        ui::EF_COMMAND_DOWN | ui::EF_ALT_DOWN | ui::EF_CONTROL_DOWN,
        ui::DomKey::BACKSPACE,
        0},
       {ui::VKEY_BACK,
        ui::DomCode::BACKSPACE,
        ui::EF_ALT_DOWN | ui::EF_CONTROL_DOWN,
        ui::DomKey::BACKSPACE,
        0}},
      // Alt+Up -> Prior
      {KeyTestCase::TEST_ALL,
       ui::ET_KEY_PRESSED,
       {ui::VKEY_UP,
        ui::DomCode::ARROW_UP,
        ui::EF_ALT_DOWN,
        ui::DomKey::ARROW_UP,
        0},
       {ui::VKEY_PRIOR,
        ui::DomCode::PAGE_UP,
        ui::EF_NONE,
        ui::DomKey::PAGE_UP,
        0}},
      // Alt+Down -> Next
      {KeyTestCase::TEST_ALL,
       ui::ET_KEY_PRESSED,
       {ui::VKEY_DOWN,
        ui::DomCode::ARROW_DOWN,
        ui::EF_ALT_DOWN,
        ui::DomKey::ARROW_DOWN,
        0},
       {ui::VKEY_NEXT,
        ui::DomCode::PAGE_DOWN,
        ui::EF_NONE,
        ui::DomKey::PAGE_DOWN,
        0}},
      // Ctrl+Alt+Up -> Home
      {KeyTestCase::TEST_ALL,
       ui::ET_KEY_PRESSED,
       {ui::VKEY_UP,
        ui::DomCode::ARROW_UP,
        ui::EF_ALT_DOWN | ui::EF_CONTROL_DOWN,
        ui::DomKey::ARROW_UP,
        0},
       {ui::VKEY_HOME, ui::DomCode::HOME, ui::EF_NONE, ui::DomKey::HOME, 0}},
      // Ctrl+Alt+Down -> End
      {KeyTestCase::TEST_ALL,
       ui::ET_KEY_PRESSED,
       {ui::VKEY_DOWN,
        ui::DomCode::ARROW_DOWN,
        ui::EF_ALT_DOWN | ui::EF_CONTROL_DOWN,
        ui::DomKey::ARROW_DOWN,
        0},
       {ui::VKEY_END, ui::DomCode::END, ui::EF_NONE, ui::DomKey::END, 0}},

      // Search+Alt+Up -> Alt+Up
      {KeyTestCase::TEST_ALL,
       ui::ET_KEY_PRESSED,
       {ui::VKEY_UP,
        ui::DomCode::ARROW_UP,
        ui::EF_COMMAND_DOWN | ui::EF_ALT_DOWN,
        ui::DomKey::ARROW_UP,
        0},
       {ui::VKEY_UP,
        ui::DomCode::ARROW_UP,
        ui::EF_ALT_DOWN,
        ui::DomKey::ARROW_UP,
        0}},
      // Search+Alt+Down -> Alt+Down
      {KeyTestCase::TEST_ALL,
       ui::ET_KEY_PRESSED,
       {ui::VKEY_DOWN,
        ui::DomCode::ARROW_DOWN,
        ui::EF_COMMAND_DOWN | ui::EF_ALT_DOWN,
        ui::DomKey::ARROW_DOWN,
        0},
       {ui::VKEY_DOWN,
        ui::DomCode::ARROW_DOWN,
        ui::EF_ALT_DOWN,
        ui::DomKey::ARROW_DOWN,
        0}},
      // Search+Ctrl+Alt+Up -> Search+Ctrl+Alt+Up
      {KeyTestCase::TEST_ALL,
       ui::ET_KEY_PRESSED,
       {ui::VKEY_UP,
        ui::DomCode::ARROW_UP,
        ui::EF_COMMAND_DOWN | ui::EF_ALT_DOWN | ui::EF_CONTROL_DOWN,
        ui::DomKey::ARROW_UP,
        0},
       {ui::VKEY_UP,
        ui::DomCode::ARROW_UP,
        ui::EF_ALT_DOWN | ui::EF_CONTROL_DOWN,
        ui::DomKey::ARROW_UP,
        0}},
      // Search+Ctrl+Alt+Down -> Ctrl+Alt+Down
      {KeyTestCase::TEST_ALL,
       ui::ET_KEY_PRESSED,
       {ui::VKEY_DOWN,
        ui::DomCode::ARROW_DOWN,
        ui::EF_COMMAND_DOWN | ui::EF_ALT_DOWN | ui::EF_CONTROL_DOWN,
        ui::DomKey::ARROW_DOWN,
        0},
       {ui::VKEY_DOWN,
        ui::DomCode::ARROW_DOWN,
        ui::EF_ALT_DOWN | ui::EF_CONTROL_DOWN,
        ui::DomKey::ARROW_DOWN,
        0}},

      // Period -> Period
      {KeyTestCase::TEST_ALL,
       ui::ET_KEY_PRESSED,
       {ui::VKEY_OEM_PERIOD,
        ui::DomCode::PERIOD,
        ui::EF_NONE,
        ui::DomKey::CHARACTER,
        '.'},
       {ui::VKEY_OEM_PERIOD,
        ui::DomCode::PERIOD,
        ui::EF_NONE,
        ui::DomKey::CHARACTER,
        '.'}},

      // Search+Backspace -> Delete
      {KeyTestCase::TEST_ALL,
       ui::ET_KEY_PRESSED,
       {ui::VKEY_BACK,
        ui::DomCode::BACKSPACE,
        ui::EF_COMMAND_DOWN,
        ui::DomKey::BACKSPACE,
        0},
       {ui::VKEY_DELETE, ui::DomCode::DEL, ui::EF_NONE, ui::DomKey::DEL, 0}},
      // Search+Up -> Prior
      {KeyTestCase::TEST_ALL,
       ui::ET_KEY_PRESSED,
       {ui::VKEY_UP,
        ui::DomCode::ARROW_UP,
        ui::EF_COMMAND_DOWN,
        ui::DomKey::ARROW_UP,
        0},
       {ui::VKEY_PRIOR,
        ui::DomCode::PAGE_UP,
        ui::EF_NONE,
        ui::DomKey::PAGE_UP,
        0}},
      // Search+Down -> Next
      {KeyTestCase::TEST_ALL,
       ui::ET_KEY_PRESSED,
       {ui::VKEY_DOWN,
        ui::DomCode::ARROW_DOWN,
        ui::EF_COMMAND_DOWN,
        ui::DomKey::ARROW_DOWN,
        0},
       {ui::VKEY_NEXT,
        ui::DomCode::PAGE_DOWN,
        ui::EF_NONE,
        ui::DomKey::PAGE_DOWN,
        0}},
      // Search+Left -> Home
      {KeyTestCase::TEST_ALL,
       ui::ET_KEY_PRESSED,
       {ui::VKEY_LEFT,
        ui::DomCode::ARROW_LEFT,
        ui::EF_COMMAND_DOWN,
        ui::DomKey::ARROW_LEFT,
        0},
       {ui::VKEY_HOME, ui::DomCode::HOME, ui::EF_NONE, ui::DomKey::HOME, 0}},
      // Control+Search+Left -> Home
      {KeyTestCase::TEST_ALL,
       ui::ET_KEY_PRESSED,
       {ui::VKEY_LEFT,
        ui::DomCode::ARROW_LEFT,
        ui::EF_COMMAND_DOWN | ui::EF_CONTROL_DOWN,
        ui::DomKey::ARROW_LEFT,
        0},
       {ui::VKEY_HOME,
        ui::DomCode::HOME,
        ui::EF_CONTROL_DOWN,
        ui::DomKey::HOME,
        0}},
      // Search+Right -> End
      {KeyTestCase::TEST_ALL,
       ui::ET_KEY_PRESSED,
       {ui::VKEY_RIGHT,
        ui::DomCode::ARROW_RIGHT,
        ui::EF_COMMAND_DOWN,
        ui::DomKey::ARROW_RIGHT,
        0},
       {ui::VKEY_END, ui::DomCode::END, ui::EF_NONE, ui::DomKey::END, 0}},
      // Control+Search+Right -> End
      {KeyTestCase::TEST_ALL,
       ui::ET_KEY_PRESSED,
       {ui::VKEY_RIGHT,
        ui::DomCode::ARROW_RIGHT,
        ui::EF_COMMAND_DOWN | ui::EF_CONTROL_DOWN,
        ui::DomKey::ARROW_RIGHT,
        0},
       {ui::VKEY_END,
        ui::DomCode::END,
        ui::EF_CONTROL_DOWN,
        ui::DomKey::END,
        0}},
      // Search+Period -> Insert
      {KeyTestCase::TEST_ALL,
       ui::ET_KEY_PRESSED,
       {ui::VKEY_OEM_PERIOD,
        ui::DomCode::PERIOD,
        ui::EF_COMMAND_DOWN,
        ui::DomKey::CHARACTER,
        '.'},
       {ui::VKEY_INSERT,
        ui::DomCode::INSERT,
        ui::EF_NONE,
        ui::DomKey::INSERT,
        0}},
      // Control+Search+Period -> Control+Insert
      {KeyTestCase::TEST_ALL,
       ui::ET_KEY_PRESSED,
       {ui::VKEY_OEM_PERIOD,
        ui::DomCode::PERIOD,
        ui::EF_COMMAND_DOWN | ui::EF_CONTROL_DOWN,
        ui::DomKey::CHARACTER,
        '.'},
       {ui::VKEY_INSERT,
        ui::DomCode::INSERT,
        ui::EF_CONTROL_DOWN,
        ui::DomKey::INSERT,
        0}}};

  for (size_t i = 0; i < arraysize(tests); ++i) {
    SCOPED_TRACE(i);
    CheckKeyTestCase(&rewriter, tests[i]);
  }
}

TEST_F(EventRewriterTest, TestRewriteFunctionKeys) {
  TestingPrefServiceSyncable prefs;
  chromeos::Preferences::RegisterProfilePrefs(prefs.registry());
  EventRewriter rewriter(NULL);
  rewriter.KeyboardDeviceAddedForTesting(kKeyboardDeviceId, "PC Keyboard");
  rewriter.set_pref_service_for_testing(&prefs);

  KeyTestCase tests[] = {
      // F1 -> Back
      {KeyTestCase::TEST_ALL,
       ui::ET_KEY_PRESSED,
       {ui::VKEY_F1, ui::DomCode::F1, ui::EF_NONE, ui::DomKey::F1, 0},
       {ui::VKEY_BROWSER_BACK,
        ui::DomCode::BROWSER_BACK,
        ui::EF_NONE,
        ui::DomKey::BROWSER_BACK,
        0}},
      {KeyTestCase::TEST_ALL,
       ui::ET_KEY_PRESSED,
       {ui::VKEY_F1, ui::DomCode::F1, ui::EF_CONTROL_DOWN, ui::DomKey::F1, 0},
       {ui::VKEY_BROWSER_BACK,
        ui::DomCode::BROWSER_BACK,
        ui::EF_CONTROL_DOWN,
        ui::DomKey::BROWSER_BACK,
        0}},
      {KeyTestCase::TEST_ALL,
       ui::ET_KEY_PRESSED,
       {ui::VKEY_F1, ui::DomCode::F1, ui::EF_ALT_DOWN, ui::DomKey::F1, 0},
       {ui::VKEY_BROWSER_BACK,
        ui::DomCode::BROWSER_BACK,
        ui::EF_ALT_DOWN,
        ui::DomKey::BROWSER_BACK,
        0}},
      // F2 -> Forward
      {KeyTestCase::TEST_ALL,
       ui::ET_KEY_PRESSED,
       {ui::VKEY_F2, ui::DomCode::F2, ui::EF_NONE, ui::DomKey::F2, 0},
       {ui::VKEY_BROWSER_FORWARD,
        ui::DomCode::BROWSER_FORWARD,
        ui::EF_NONE,
        ui::DomKey::BROWSER_FORWARD,
        0}},
      {KeyTestCase::TEST_ALL,
       ui::ET_KEY_PRESSED,
       {ui::VKEY_F2, ui::DomCode::F2, ui::EF_CONTROL_DOWN, ui::DomKey::F2, 0},
       {ui::VKEY_BROWSER_FORWARD,
        ui::DomCode::BROWSER_FORWARD,
        ui::EF_CONTROL_DOWN,
        ui::DomKey::BROWSER_FORWARD,
        0}},
      {KeyTestCase::TEST_ALL,
       ui::ET_KEY_PRESSED,
       {ui::VKEY_F2, ui::DomCode::F2, ui::EF_ALT_DOWN, ui::DomKey::F2, 0},
       {ui::VKEY_BROWSER_FORWARD,
        ui::DomCode::BROWSER_FORWARD,
        ui::EF_ALT_DOWN,
        ui::DomKey::BROWSER_FORWARD,
        0}},
      // F3 -> Refresh
      {KeyTestCase::TEST_ALL,
       ui::ET_KEY_PRESSED,
       {ui::VKEY_F3, ui::DomCode::F3, ui::EF_NONE, ui::DomKey::F3, 0},
       {ui::VKEY_BROWSER_REFRESH,
        ui::DomCode::BROWSER_REFRESH,
        ui::EF_NONE,
        ui::DomKey::BROWSER_REFRESH,
        0}},
      {KeyTestCase::TEST_ALL,
       ui::ET_KEY_PRESSED,
       {ui::VKEY_F3, ui::DomCode::F3, ui::EF_CONTROL_DOWN, ui::DomKey::F3, 0},
       {ui::VKEY_BROWSER_REFRESH,
        ui::DomCode::BROWSER_REFRESH,
        ui::EF_CONTROL_DOWN,
        ui::DomKey::BROWSER_REFRESH,
        0}},
      {KeyTestCase::TEST_ALL,
       ui::ET_KEY_PRESSED,
       {ui::VKEY_F3, ui::DomCode::F3, ui::EF_ALT_DOWN, ui::DomKey::F3, 0},
       {ui::VKEY_BROWSER_REFRESH,
        ui::DomCode::BROWSER_REFRESH,
        ui::EF_ALT_DOWN,
        ui::DomKey::BROWSER_REFRESH,
        0}},
      // F4 -> Launch App 2
      {KeyTestCase::TEST_ALL,
       ui::ET_KEY_PRESSED,
       {ui::VKEY_F4, ui::DomCode::F4, ui::EF_NONE, ui::DomKey::F4, 0},
       {ui::VKEY_MEDIA_LAUNCH_APP2,
        ui::DomCode::ZOOM_TOGGLE,
        ui::EF_NONE,
        ui::DomKey::ZOOM_TOGGLE,
        0}},
      {KeyTestCase::TEST_ALL,
       ui::ET_KEY_PRESSED,
       {ui::VKEY_F4, ui::DomCode::F4, ui::EF_CONTROL_DOWN, ui::DomKey::F4, 0},
       {ui::VKEY_MEDIA_LAUNCH_APP2,
        ui::DomCode::ZOOM_TOGGLE,
        ui::EF_CONTROL_DOWN,
        ui::DomKey::ZOOM_TOGGLE,
        0}},
      {KeyTestCase::TEST_ALL,
       ui::ET_KEY_PRESSED,
       {ui::VKEY_F4, ui::DomCode::F4, ui::EF_ALT_DOWN, ui::DomKey::F4, 0},
       {ui::VKEY_MEDIA_LAUNCH_APP2,
        ui::DomCode::ZOOM_TOGGLE,
        ui::EF_ALT_DOWN,
        ui::DomKey::ZOOM_TOGGLE,
        0}},
      // F5 -> Launch App 1
      {KeyTestCase::TEST_ALL,
       ui::ET_KEY_PRESSED,
       {ui::VKEY_F5, ui::DomCode::F5, ui::EF_NONE, ui::DomKey::F5, 0},
       {ui::VKEY_MEDIA_LAUNCH_APP1,
        ui::DomCode::SELECT_TASK,
        ui::EF_NONE,
        ui::DomKey::LAUNCH_MY_COMPUTER,
        0}},
      {KeyTestCase::TEST_ALL,
       ui::ET_KEY_PRESSED,
       {ui::VKEY_F5, ui::DomCode::F5, ui::EF_CONTROL_DOWN, ui::DomKey::F5, 0},
       {ui::VKEY_MEDIA_LAUNCH_APP1,
        ui::DomCode::SELECT_TASK,
        ui::EF_CONTROL_DOWN,
        ui::DomKey::LAUNCH_MY_COMPUTER,
        0}},
      {KeyTestCase::TEST_ALL,
       ui::ET_KEY_PRESSED,
       {ui::VKEY_F5, ui::DomCode::F5, ui::EF_ALT_DOWN, ui::DomKey::F5, 0},
       {ui::VKEY_MEDIA_LAUNCH_APP1,
        ui::DomCode::SELECT_TASK,
        ui::EF_ALT_DOWN,
        ui::DomKey::LAUNCH_MY_COMPUTER,
        0}},
      // F6 -> Brightness down
      {KeyTestCase::TEST_ALL,
       ui::ET_KEY_PRESSED,
       {ui::VKEY_F6, ui::DomCode::F6, ui::EF_NONE, ui::DomKey::F6, 0},
       {ui::VKEY_BRIGHTNESS_DOWN,
        ui::DomCode::BRIGHTNESS_DOWN,
        ui::EF_NONE,
        ui::DomKey::BRIGHTNESS_DOWN,
        0}},
      {KeyTestCase::TEST_ALL,
       ui::ET_KEY_PRESSED,
       {ui::VKEY_F6, ui::DomCode::F6, ui::EF_CONTROL_DOWN, ui::DomKey::F6, 0},
       {ui::VKEY_BRIGHTNESS_DOWN,
        ui::DomCode::BRIGHTNESS_DOWN,
        ui::EF_CONTROL_DOWN,
        ui::DomKey::BRIGHTNESS_DOWN,
        0}},
      {KeyTestCase::TEST_ALL,
       ui::ET_KEY_PRESSED,
       {ui::VKEY_F6, ui::DomCode::F6, ui::EF_ALT_DOWN, ui::DomKey::F6, 0},
       {ui::VKEY_BRIGHTNESS_DOWN,
        ui::DomCode::BRIGHTNESS_DOWN,
        ui::EF_ALT_DOWN,
        ui::DomKey::BRIGHTNESS_DOWN,
        0}},
      // F7 -> Brightness up
      {KeyTestCase::TEST_ALL,
       ui::ET_KEY_PRESSED,
       {ui::VKEY_F7, ui::DomCode::F7, ui::EF_NONE, ui::DomKey::F7, 0},
       {ui::VKEY_BRIGHTNESS_UP,
        ui::DomCode::BRIGHTNESS_UP,
        ui::EF_NONE,
        ui::DomKey::BRIGHTNESS_UP,
        0}},
      {KeyTestCase::TEST_ALL,
       ui::ET_KEY_PRESSED,
       {ui::VKEY_F7, ui::DomCode::F7, ui::EF_CONTROL_DOWN, ui::DomKey::F7, 0},
       {ui::VKEY_BRIGHTNESS_UP,
        ui::DomCode::BRIGHTNESS_UP,
        ui::EF_CONTROL_DOWN,
        ui::DomKey::BRIGHTNESS_UP,
        0}},
      {KeyTestCase::TEST_ALL,
       ui::ET_KEY_PRESSED,
       {ui::VKEY_F7, ui::DomCode::F7, ui::EF_ALT_DOWN, ui::DomKey::F7, 0},
       {ui::VKEY_BRIGHTNESS_UP,
        ui::DomCode::BRIGHTNESS_UP,
        ui::EF_ALT_DOWN,
        ui::DomKey::BRIGHTNESS_UP,
        0}},
      // F8 -> Volume Mute
      {KeyTestCase::TEST_ALL,
       ui::ET_KEY_PRESSED,
       {ui::VKEY_F8, ui::DomCode::F8, ui::EF_NONE, ui::DomKey::F8, 0},
       {ui::VKEY_VOLUME_MUTE,
        ui::DomCode::VOLUME_MUTE,
        ui::EF_NONE,
        ui::DomKey::VOLUME_MUTE,
        0}},
      {KeyTestCase::TEST_ALL,
       ui::ET_KEY_PRESSED,
       {ui::VKEY_F8, ui::DomCode::F8, ui::EF_CONTROL_DOWN, ui::DomKey::F8, 0},
       {ui::VKEY_VOLUME_MUTE,
        ui::DomCode::VOLUME_MUTE,
        ui::EF_CONTROL_DOWN,
        ui::DomKey::VOLUME_MUTE,
        0}},
      {KeyTestCase::TEST_ALL,
       ui::ET_KEY_PRESSED,
       {ui::VKEY_F8, ui::DomCode::F8, ui::EF_ALT_DOWN, ui::DomKey::F8, 0},
       {ui::VKEY_VOLUME_MUTE,
        ui::DomCode::VOLUME_MUTE,
        ui::EF_ALT_DOWN,
        ui::DomKey::VOLUME_MUTE,
        0}},
      // F9 -> Volume Down
      {KeyTestCase::TEST_ALL,
       ui::ET_KEY_PRESSED,
       {ui::VKEY_F9, ui::DomCode::F9, ui::EF_NONE, ui::DomKey::F9, 0},
       {ui::VKEY_VOLUME_DOWN,
        ui::DomCode::VOLUME_DOWN,
        ui::EF_NONE,
        ui::DomKey::VOLUME_DOWN,
        0}},
      {KeyTestCase::TEST_ALL,
       ui::ET_KEY_PRESSED,
       {ui::VKEY_F9, ui::DomCode::F9, ui::EF_CONTROL_DOWN, ui::DomKey::F9, 0},
       {ui::VKEY_VOLUME_DOWN,
        ui::DomCode::VOLUME_DOWN,
        ui::EF_CONTROL_DOWN,
        ui::DomKey::VOLUME_DOWN,
        0}},
      {KeyTestCase::TEST_ALL,
       ui::ET_KEY_PRESSED,
       {ui::VKEY_F9, ui::DomCode::F9, ui::EF_ALT_DOWN, ui::DomKey::F9, 0},
       {ui::VKEY_VOLUME_DOWN,
        ui::DomCode::VOLUME_DOWN,
        ui::EF_ALT_DOWN,
        ui::DomKey::VOLUME_DOWN,
        0}},
      // F10 -> Volume Up
      {KeyTestCase::TEST_ALL,
       ui::ET_KEY_PRESSED,
       {ui::VKEY_F10, ui::DomCode::F10, ui::EF_NONE, ui::DomKey::F10, 0},
       {ui::VKEY_VOLUME_UP,
        ui::DomCode::VOLUME_UP,
        ui::EF_NONE,
        ui::DomKey::VOLUME_UP,
        0}},
      {KeyTestCase::TEST_ALL,
       ui::ET_KEY_PRESSED,
       {ui::VKEY_F10,
        ui::DomCode::F10,
        ui::EF_CONTROL_DOWN,
        ui::DomKey::F10,
        0},
       {ui::VKEY_VOLUME_UP,
        ui::DomCode::VOLUME_UP,
        ui::EF_CONTROL_DOWN,
        ui::DomKey::VOLUME_UP,
        0}},
      {KeyTestCase::TEST_ALL,
       ui::ET_KEY_PRESSED,
       {ui::VKEY_F10, ui::DomCode::F10, ui::EF_ALT_DOWN, ui::DomKey::F10, 0},
       {ui::VKEY_VOLUME_UP,
        ui::DomCode::VOLUME_UP,
        ui::EF_ALT_DOWN,
        ui::DomKey::VOLUME_UP,
        0}},
      // F11 -> F11
      {KeyTestCase::TEST_ALL,
       ui::ET_KEY_PRESSED,
       {ui::VKEY_F11, ui::DomCode::F11, ui::EF_NONE, ui::DomKey::F11, 0},
       {ui::VKEY_F11, ui::DomCode::F11, ui::EF_NONE, ui::DomKey::F11, 0}},
      {KeyTestCase::TEST_ALL,
       ui::ET_KEY_PRESSED,
       {ui::VKEY_F11,
        ui::DomCode::F11,
        ui::EF_CONTROL_DOWN,
        ui::DomKey::F11,
        0},
       {ui::VKEY_F11,
        ui::DomCode::F11,
        ui::EF_CONTROL_DOWN,
        ui::DomKey::F11,
        0}},
      {KeyTestCase::TEST_ALL,
       ui::ET_KEY_PRESSED,
       {ui::VKEY_F11, ui::DomCode::F11, ui::EF_ALT_DOWN, ui::DomKey::F11, 0},
       {ui::VKEY_F11, ui::DomCode::F11, ui::EF_ALT_DOWN, ui::DomKey::F11, 0}},
      // F12 -> F12
      {KeyTestCase::TEST_ALL,
       ui::ET_KEY_PRESSED,
       {ui::VKEY_F12, ui::DomCode::F12, ui::EF_NONE, ui::DomKey::F12, 0},
       {ui::VKEY_F12, ui::DomCode::F12, ui::EF_NONE, ui::DomKey::F12, 0}},
      {KeyTestCase::TEST_ALL,
       ui::ET_KEY_PRESSED,
       {ui::VKEY_F12,
        ui::DomCode::F12,
        ui::EF_CONTROL_DOWN,
        ui::DomKey::F12,
        0},
       {ui::VKEY_F12,
        ui::DomCode::F12,
        ui::EF_CONTROL_DOWN,
        ui::DomKey::F12,
        0}},
      {KeyTestCase::TEST_ALL,
       ui::ET_KEY_PRESSED,
       {ui::VKEY_F12, ui::DomCode::F12, ui::EF_ALT_DOWN, ui::DomKey::F12, 0},
       {ui::VKEY_F12, ui::DomCode::F12, ui::EF_ALT_DOWN, ui::DomKey::F12, 0}},

      // The number row should not be rewritten without Search key.
      {KeyTestCase::TEST_ALL,
       ui::ET_KEY_PRESSED,
       {ui::VKEY_1,
        ui::DomCode::DIGIT1,
        ui::EF_NONE,
        ui::DomKey::CHARACTER,
        '1'},
       {ui::VKEY_1,
        ui::DomCode::DIGIT1,
        ui::EF_NONE,
        ui::DomKey::CHARACTER,
        '1'}},
      {KeyTestCase::TEST_ALL,
       ui::ET_KEY_PRESSED,
       {ui::VKEY_2,
        ui::DomCode::DIGIT2,
        ui::EF_NONE,
        ui::DomKey::CHARACTER,
        '2'},
       {ui::VKEY_2,
        ui::DomCode::DIGIT2,
        ui::EF_NONE,
        ui::DomKey::CHARACTER,
        '2'}},
      {KeyTestCase::TEST_ALL,
       ui::ET_KEY_PRESSED,
       {ui::VKEY_3,
        ui::DomCode::DIGIT3,
        ui::EF_NONE,
        ui::DomKey::CHARACTER,
        '3'},
       {ui::VKEY_3,
        ui::DomCode::DIGIT3,
        ui::EF_NONE,
        ui::DomKey::CHARACTER,
        '3'}},
      {KeyTestCase::TEST_ALL,
       ui::ET_KEY_PRESSED,
       {ui::VKEY_4,
        ui::DomCode::DIGIT4,
        ui::EF_NONE,
        ui::DomKey::CHARACTER,
        '4'},
       {ui::VKEY_4,
        ui::DomCode::DIGIT4,
        ui::EF_NONE,
        ui::DomKey::CHARACTER,
        '4'}},
      {KeyTestCase::TEST_ALL,
       ui::ET_KEY_PRESSED,
       {ui::VKEY_5,
        ui::DomCode::DIGIT5,
        ui::EF_NONE,
        ui::DomKey::CHARACTER,
        '5'},
       {ui::VKEY_5,
        ui::DomCode::DIGIT5,
        ui::EF_NONE,
        ui::DomKey::CHARACTER,
        '5'}},
      {KeyTestCase::TEST_ALL,
       ui::ET_KEY_PRESSED,
       {ui::VKEY_6,
        ui::DomCode::DIGIT6,
        ui::EF_NONE,
        ui::DomKey::CHARACTER,
        '6'},
       {ui::VKEY_6,
        ui::DomCode::DIGIT6,
        ui::EF_NONE,
        ui::DomKey::CHARACTER,
        '6'}},
      {KeyTestCase::TEST_ALL,
       ui::ET_KEY_PRESSED,
       {ui::VKEY_7,
        ui::DomCode::DIGIT7,
        ui::EF_NONE,
        ui::DomKey::CHARACTER,
        '7'},
       {ui::VKEY_7,
        ui::DomCode::DIGIT7,
        ui::EF_NONE,
        ui::DomKey::CHARACTER,
        '7'}},
      {KeyTestCase::TEST_ALL,
       ui::ET_KEY_PRESSED,
       {ui::VKEY_8,
        ui::DomCode::DIGIT8,
        ui::EF_NONE,
        ui::DomKey::CHARACTER,
        '8'},
       {ui::VKEY_8,
        ui::DomCode::DIGIT8,
        ui::EF_NONE,
        ui::DomKey::CHARACTER,
        '8'}},
      {KeyTestCase::TEST_ALL,
       ui::ET_KEY_PRESSED,
       {ui::VKEY_9,
        ui::DomCode::DIGIT9,
        ui::EF_NONE,
        ui::DomKey::CHARACTER,
        '9'},
       {ui::VKEY_9,
        ui::DomCode::DIGIT9,
        ui::EF_NONE,
        ui::DomKey::CHARACTER,
        '9'}},
      {KeyTestCase::TEST_ALL,
       ui::ET_KEY_PRESSED,
       {ui::VKEY_0,
        ui::DomCode::DIGIT0,
        ui::EF_NONE,
        ui::DomKey::CHARACTER,
        '0'},
       {ui::VKEY_0,
        ui::DomCode::DIGIT0,
        ui::EF_NONE,
        ui::DomKey::CHARACTER,
        '0'}},
      {KeyTestCase::TEST_ALL,
       ui::ET_KEY_PRESSED,
       {ui::VKEY_OEM_MINUS,
        ui::DomCode::MINUS,
        ui::EF_NONE,
        ui::DomKey::CHARACTER,
        '-'},
       {ui::VKEY_OEM_MINUS,
        ui::DomCode::MINUS,
        ui::EF_NONE,
        ui::DomKey::CHARACTER,
        '-'}},
      {KeyTestCase::TEST_ALL,
       ui::ET_KEY_PRESSED,
       {ui::VKEY_OEM_PLUS,
        ui::DomCode::EQUAL,
        ui::EF_NONE,
        ui::DomKey::CHARACTER,
        '='},
       {ui::VKEY_OEM_PLUS,
        ui::DomCode::EQUAL,
        ui::EF_NONE,
        ui::DomKey::CHARACTER,
        '='}},

      // The number row should be rewritten as the F<number> row with Search
      // key.
      {KeyTestCase::TEST_ALL,
       ui::ET_KEY_PRESSED,
       {ui::VKEY_1,
        ui::DomCode::DIGIT1,
        ui::EF_COMMAND_DOWN,
        ui::DomKey::CHARACTER,
        '1'},
       {ui::VKEY_F1, ui::DomCode::F1, ui::EF_NONE, ui::DomKey::F1, 0}},
      {KeyTestCase::TEST_ALL,
       ui::ET_KEY_PRESSED,
       {ui::VKEY_2,
        ui::DomCode::DIGIT2,
        ui::EF_COMMAND_DOWN,
        ui::DomKey::CHARACTER,
        '2'},
       {ui::VKEY_F2, ui::DomCode::F2, ui::EF_NONE, ui::DomKey::F2, 0}},
      {KeyTestCase::TEST_ALL,
       ui::ET_KEY_PRESSED,
       {ui::VKEY_3,
        ui::DomCode::DIGIT3,
        ui::EF_COMMAND_DOWN,
        ui::DomKey::CHARACTER,
        '3'},
       {ui::VKEY_F3, ui::DomCode::F3, ui::EF_NONE, ui::DomKey::F3, 0}},
      {KeyTestCase::TEST_ALL,
       ui::ET_KEY_PRESSED,
       {ui::VKEY_4,
        ui::DomCode::DIGIT4,
        ui::EF_COMMAND_DOWN,
        ui::DomKey::CHARACTER,
        '4'},
       {ui::VKEY_F4, ui::DomCode::F4, ui::EF_NONE, ui::DomKey::F4, 0}},
      {KeyTestCase::TEST_ALL,
       ui::ET_KEY_PRESSED,
       {ui::VKEY_5,
        ui::DomCode::DIGIT5,
        ui::EF_COMMAND_DOWN,
        ui::DomKey::CHARACTER,
        '5'},
       {ui::VKEY_F5, ui::DomCode::F5, ui::EF_NONE, ui::DomKey::F5, 0}},
      {KeyTestCase::TEST_ALL,
       ui::ET_KEY_PRESSED,
       {ui::VKEY_6,
        ui::DomCode::DIGIT6,
        ui::EF_COMMAND_DOWN,
        ui::DomKey::CHARACTER,
        '6'},
       {ui::VKEY_F6, ui::DomCode::F6, ui::EF_NONE, ui::DomKey::F6, 0}},
      {KeyTestCase::TEST_ALL,
       ui::ET_KEY_PRESSED,
       {ui::VKEY_7,
        ui::DomCode::DIGIT7,
        ui::EF_COMMAND_DOWN,
        ui::DomKey::CHARACTER,
        '7'},
       {ui::VKEY_F7, ui::DomCode::F7, ui::EF_NONE, ui::DomKey::F7, 0}},
      {KeyTestCase::TEST_ALL,
       ui::ET_KEY_PRESSED,
       {ui::VKEY_8,
        ui::DomCode::DIGIT8,
        ui::EF_COMMAND_DOWN,
        ui::DomKey::CHARACTER,
        '8'},
       {ui::VKEY_F8, ui::DomCode::F8, ui::EF_NONE, ui::DomKey::F8, 0}},
      {KeyTestCase::TEST_ALL,
       ui::ET_KEY_PRESSED,
       {ui::VKEY_9,
        ui::DomCode::DIGIT9,
        ui::EF_COMMAND_DOWN,
        ui::DomKey::CHARACTER,
        '9'},
       {ui::VKEY_F9, ui::DomCode::F9, ui::EF_NONE, ui::DomKey::F9, 0}},
      {KeyTestCase::TEST_ALL,
       ui::ET_KEY_PRESSED,
       {ui::VKEY_0,
        ui::DomCode::DIGIT0,
        ui::EF_COMMAND_DOWN,
        ui::DomKey::CHARACTER,
        '0'},
       {ui::VKEY_F10, ui::DomCode::F10, ui::EF_NONE, ui::DomKey::F10, 0}},
      {KeyTestCase::TEST_ALL,
       ui::ET_KEY_PRESSED,
       {ui::VKEY_OEM_MINUS,
        ui::DomCode::MINUS,
        ui::EF_COMMAND_DOWN,
        ui::DomKey::CHARACTER,
        '-'},
       {ui::VKEY_F11, ui::DomCode::F11, ui::EF_NONE, ui::DomKey::F11, 0}},
      {KeyTestCase::TEST_ALL,
       ui::ET_KEY_PRESSED,
       {ui::VKEY_OEM_PLUS,
        ui::DomCode::EQUAL,
        ui::EF_COMMAND_DOWN,
        ui::DomKey::CHARACTER,
        '='},
       {ui::VKEY_F12, ui::DomCode::F12, ui::EF_NONE, ui::DomKey::F12, 0}},

      // The function keys should not be rewritten with Search key pressed.
      {KeyTestCase::TEST_ALL,
       ui::ET_KEY_PRESSED,
       {ui::VKEY_F1, ui::DomCode::F1, ui::EF_COMMAND_DOWN, ui::DomKey::F1, 0},
       {ui::VKEY_F1, ui::DomCode::F1, ui::EF_NONE, ui::DomKey::F1, 0}},
      {KeyTestCase::TEST_ALL,
       ui::ET_KEY_PRESSED,
       {ui::VKEY_F2, ui::DomCode::F2, ui::EF_COMMAND_DOWN, ui::DomKey::F2, 0},
       {ui::VKEY_F2, ui::DomCode::F2, ui::EF_NONE, ui::DomKey::F2, 0}},
      {KeyTestCase::TEST_ALL,
       ui::ET_KEY_PRESSED,
       {ui::VKEY_F3, ui::DomCode::F3, ui::EF_COMMAND_DOWN, ui::DomKey::F3, 0},
       {ui::VKEY_F3, ui::DomCode::F3, ui::EF_NONE, ui::DomKey::F3, 0}},
      {KeyTestCase::TEST_ALL,
       ui::ET_KEY_PRESSED,
       {ui::VKEY_F4, ui::DomCode::F4, ui::EF_COMMAND_DOWN, ui::DomKey::F4, 0},
       {ui::VKEY_F4, ui::DomCode::F4, ui::EF_NONE, ui::DomKey::F4, 0}},
      {KeyTestCase::TEST_ALL,
       ui::ET_KEY_PRESSED,
       {ui::VKEY_F5, ui::DomCode::F5, ui::EF_COMMAND_DOWN, ui::DomKey::F5, 0},
       {ui::VKEY_F5, ui::DomCode::F5, ui::EF_NONE, ui::DomKey::F5, 0}},
      {KeyTestCase::TEST_ALL,
       ui::ET_KEY_PRESSED,
       {ui::VKEY_F6, ui::DomCode::F6, ui::EF_COMMAND_DOWN, ui::DomKey::F6, 0},
       {ui::VKEY_F6, ui::DomCode::F6, ui::EF_NONE, ui::DomKey::F6, 0}},
      {KeyTestCase::TEST_ALL,
       ui::ET_KEY_PRESSED,
       {ui::VKEY_F7, ui::DomCode::F7, ui::EF_COMMAND_DOWN, ui::DomKey::F7, 0},
       {ui::VKEY_F7, ui::DomCode::F7, ui::EF_NONE, ui::DomKey::F7, 0}},
      {KeyTestCase::TEST_ALL,
       ui::ET_KEY_PRESSED,
       {ui::VKEY_F8, ui::DomCode::F8, ui::EF_COMMAND_DOWN, ui::DomKey::F8, 0},
       {ui::VKEY_F8, ui::DomCode::F8, ui::EF_NONE, ui::DomKey::F8, 0}},
      {KeyTestCase::TEST_ALL,
       ui::ET_KEY_PRESSED,
       {ui::VKEY_F9, ui::DomCode::F9, ui::EF_COMMAND_DOWN, ui::DomKey::F9, 0},
       {ui::VKEY_F9, ui::DomCode::F9, ui::EF_NONE, ui::DomKey::F9, 0}},
      {KeyTestCase::TEST_ALL,
       ui::ET_KEY_PRESSED,
       {ui::VKEY_F10,
        ui::DomCode::F10,
        ui::EF_COMMAND_DOWN,
        ui::DomKey::F10,
        0},
       {ui::VKEY_F10, ui::DomCode::F10, ui::EF_NONE, ui::DomKey::F10, 0}},
      {KeyTestCase::TEST_ALL,
       ui::ET_KEY_PRESSED,
       {ui::VKEY_F11,
        ui::DomCode::F11,
        ui::EF_COMMAND_DOWN,
        ui::DomKey::F11,
        0},
       {ui::VKEY_F11, ui::DomCode::F11, ui::EF_NONE, ui::DomKey::F11, 0}},
      {KeyTestCase::TEST_ALL,
       ui::ET_KEY_PRESSED,
       {ui::VKEY_F12,
        ui::DomCode::F12,
        ui::EF_COMMAND_DOWN,
        ui::DomKey::F12,
        0},
       {ui::VKEY_F12, ui::DomCode::F12, ui::EF_NONE, ui::DomKey::F12, 0}}};

  for (size_t i = 0; i < arraysize(tests); ++i) {
    SCOPED_TRACE(i);
    CheckKeyTestCase(&rewriter, tests[i]);
  }
}

TEST_F(EventRewriterTest, TestRewriteExtendedKeysWithSearchRemapped) {
  const base::CommandLine original_cl(*base::CommandLine::ForCurrentProcess());

  // Remap Search to Control.
  TestingPrefServiceSyncable prefs;
  chromeos::Preferences::RegisterProfilePrefs(prefs.registry());
  IntegerPrefMember search;
  search.Init(prefs::kLanguageRemapSearchKeyTo, &prefs);
  search.SetValue(chromeos::input_method::kControlKey);

  EventRewriter rewriter(NULL);
  rewriter.KeyboardDeviceAddedForTesting(kKeyboardDeviceId, "PC Keyboard");
  rewriter.set_pref_service_for_testing(&prefs);

  base::CommandLine::ForCurrentProcess()->AppendSwitchASCII(
      chromeos::switches::kHasChromeOSKeyboard, "");

  KeyTestCase tests[] = {
      // Alt+Search+Down -> End
      {KeyTestCase::TEST_ALL,
       ui::ET_KEY_PRESSED,
       {ui::VKEY_DOWN,
        ui::DomCode::ARROW_DOWN,
        ui::EF_ALT_DOWN | ui::EF_COMMAND_DOWN,
        ui::DomKey::ARROW_DOWN,
        0},
       {ui::VKEY_END, ui::DomCode::END, ui::EF_NONE, ui::DomKey::END, 0}},

      // Shift+Alt+Search+Down -> Shift+End
      {KeyTestCase::TEST_ALL,
       ui::ET_KEY_PRESSED,
       {ui::VKEY_DOWN,
        ui::DomCode::ARROW_DOWN,
        ui::EF_SHIFT_DOWN | ui::EF_ALT_DOWN | ui::EF_COMMAND_DOWN,
        ui::DomKey::ARROW_DOWN,
        0},
       {ui::VKEY_END, ui::DomCode::END, ui::EF_SHIFT_DOWN, ui::DomKey::END, 0}},
  };

  for (size_t i = 0; i < arraysize(tests); ++i) {
    SCOPED_TRACE(i);
    CheckKeyTestCase(&rewriter, tests[i]);
  }

  *base::CommandLine::ForCurrentProcess() = original_cl;
}

TEST_F(EventRewriterTest, TestRewriteKeyEventSentByXSendEvent) {
  // Remap Control to Alt.
  TestingPrefServiceSyncable prefs;
  chromeos::Preferences::RegisterProfilePrefs(prefs.registry());
  IntegerPrefMember control;
  control.Init(prefs::kLanguageRemapControlKeyTo, &prefs);
  control.SetValue(chromeos::input_method::kAltKey);

  EventRewriter rewriter(NULL);
  rewriter.KeyboardDeviceAddedForTesting(kKeyboardDeviceId, "PC Keyboard");
  rewriter.set_pref_service_for_testing(&prefs);

  // Send left control press.
  {
    ui::KeyEvent keyevent(ui::ET_KEY_PRESSED, ui::VKEY_CONTROL,
                          ui::DomCode::CONTROL_LEFT, ui::EF_FINAL,
                          ui::DomKey::CONTROL, 0, ui::EventTimeForNow());
    scoped_ptr<ui::Event> new_event;
    // Control should NOT be remapped to Alt if EF_FINAL is set.
    EXPECT_EQ(ui::EVENT_REWRITE_CONTINUE,
              rewriter.RewriteEvent(keyevent, &new_event));
    EXPECT_FALSE(new_event);
  }
#if defined(USE_X11)
  // Send left control press, using XI2 native events.
  {
    ui::ScopedXI2Event xev;
    xev.InitKeyEvent(ui::ET_KEY_PRESSED, ui::VKEY_CONTROL, 0);
    XEvent* xevent = xev;
    xevent->xkey.keycode = XKeysymToKeycode(gfx::GetXDisplay(), XK_Control_L);
    xevent->xkey.send_event = True;  // XSendEvent() always does this.
    ui::KeyEvent keyevent(xev);
    scoped_ptr<ui::Event> new_event;
    // Control should NOT be remapped to Alt if send_event
    // flag in the event is True.
    EXPECT_EQ(ui::EVENT_REWRITE_CONTINUE,
              rewriter.RewriteEvent(keyevent, &new_event));
    EXPECT_FALSE(new_event);
  }
#endif
}

TEST_F(EventRewriterTest, TestRewriteNonNativeEvent) {
  // Remap Control to Alt.
  TestingPrefServiceSyncable prefs;
  chromeos::Preferences::RegisterProfilePrefs(prefs.registry());
  IntegerPrefMember control;
  control.Init(prefs::kLanguageRemapControlKeyTo, &prefs);
  control.SetValue(chromeos::input_method::kAltKey);

  EventRewriter rewriter(NULL);
  rewriter.KeyboardDeviceAddedForTesting(kKeyboardDeviceId, "PC Keyboard");
  rewriter.set_pref_service_for_testing(&prefs);

  const int kTouchId = 2;
  gfx::Point location(0, 0);
  ui::TouchEvent press(ui::ET_TOUCH_PRESSED, location, kTouchId,
                       base::TimeDelta());
  press.set_flags(ui::EF_CONTROL_DOWN);
#if defined(USE_X11)
  ui::UpdateX11EventForFlags(&press);
#endif

  scoped_ptr<ui::Event> new_event;
  rewriter.RewriteEvent(press, &new_event);
  EXPECT_TRUE(new_event);
  // Control should be remapped to Alt.
  EXPECT_EQ(ui::EF_ALT_DOWN,
            new_event->flags() & (ui::EF_CONTROL_DOWN | ui::EF_ALT_DOWN));
}

// Keeps a buffer of handled events.
class EventBuffer : public ui::test::TestEventProcessor {
 public:
  EventBuffer() {}
  ~EventBuffer() override {}

  void PopEvents(ScopedVector<ui::Event>* events) {
    events->clear();
    events->swap(events_);
  }

 private:
  // ui::EventProcessor overrides:
  ui::EventDispatchDetails OnEventFromSource(ui::Event* event) override {
    if (event->IsKeyEvent()) {
      events_.push_back(new ui::KeyEvent(*static_cast<ui::KeyEvent*>(event)));
    } else if (event->IsMouseWheelEvent()) {
      events_.push_back(
          new ui::MouseWheelEvent(*static_cast<ui::MouseWheelEvent*>(event)));
    } else if (event->IsMouseEvent()) {
      events_.push_back(
          new ui::MouseEvent(*static_cast<ui::MouseEvent*>(event)));
    }
    return ui::EventDispatchDetails();
  }

  ScopedVector<ui::Event> events_;

  DISALLOW_COPY_AND_ASSIGN(EventBuffer);
};

// Trivial EventSource that does nothing but send events.
class TestEventSource : public ui::EventSource {
 public:
  explicit TestEventSource(ui::EventProcessor* processor)
      : processor_(processor) {}
  ui::EventProcessor* GetEventProcessor() override { return processor_; }
  ui::EventDispatchDetails Send(ui::Event* event) {
    return SendEventToProcessor(event);
  }

 private:
  ui::EventProcessor* processor_;
};

// Tests of event rewriting that depend on the Ash window manager.
class EventRewriterAshTest : public ash::test::AshTestBase {
 public:
  EventRewriterAshTest()
      : source_(&buffer_),
        fake_user_manager_(new user_manager::FakeUserManager),
        user_manager_enabler_(fake_user_manager_) {}
  ~EventRewriterAshTest() override {}

  bool RewriteFunctionKeys(const ui::Event& event,
                           scoped_ptr<ui::Event>* rewritten_event) {
    return rewriter_->RewriteEvent(event, rewritten_event);
  }

  ui::EventDispatchDetails Send(ui::Event* event) {
    return source_.Send(event);
  }

  void SendKeyEvent(ui::EventType type,
                    ui::KeyboardCode key_code,
                    ui::DomCode code,
                    ui::DomKey key,
                    base::char16 character) {
    ui::KeyEvent press(type, key_code, code, ui::EF_NONE, key, character,
                       ui::EventTimeForNow());
    ui::EventDispatchDetails details = Send(&press);
    CHECK(!details.dispatcher_destroyed);
  }

  void SendActivateStickyKeyPattern(ui::KeyboardCode key_code,
                                    ui::DomCode code,
                                    ui::DomKey key,
                                    base::char16 character) {
    SendKeyEvent(ui::ET_KEY_PRESSED, key_code, code, key, character);
    SendKeyEvent(ui::ET_KEY_RELEASED, key_code, code, key, character);
  }

 protected:
  TestingPrefServiceSyncable* prefs() { return &prefs_; }

  void PopEvents(ScopedVector<ui::Event>* events) { buffer_.PopEvents(events); }

  void SetUp() override {
    AshTestBase::SetUp();
    sticky_keys_controller_ =
        ash::Shell::GetInstance()->sticky_keys_controller();
    rewriter_.reset(new EventRewriter(sticky_keys_controller_));
    chromeos::Preferences::RegisterProfilePrefs(prefs_.registry());
    rewriter_->set_pref_service_for_testing(&prefs_);
#if defined(USE_X11)
    ui::SetUpTouchPadForTest(kTouchPadDeviceId);
#endif
    source_.AddEventRewriter(rewriter_.get());
    sticky_keys_controller_->Enable(true);
  }

  void TearDown() override {
    rewriter_.reset();
    AshTestBase::TearDown();
  }

 protected:
  ash::StickyKeysController* sticky_keys_controller_;

 private:
  scoped_ptr<EventRewriter> rewriter_;

  EventBuffer buffer_;
  TestEventSource source_;

  user_manager::FakeUserManager* fake_user_manager_;  // Not owned.
  chromeos::ScopedUserManagerEnabler user_manager_enabler_;
  TestingPrefServiceSyncable prefs_;

  DISALLOW_COPY_AND_ASSIGN(EventRewriterAshTest);
};

TEST_F(EventRewriterAshTest, TopRowKeysAreFunctionKeys) {
  scoped_ptr<aura::Window> window(CreateTestWindowInShellWithId(1));
  ash::wm::WindowState* window_state = ash::wm::GetWindowState(window.get());
  window_state->Activate();
  ScopedVector<ui::Event> events;

  // Create a simulated keypress of F1 targetted at the window.
  ui::KeyEvent press_f1(ui::ET_KEY_PRESSED, ui::VKEY_F1, ui::DomCode::F1,
                        ui::EF_NONE, ui::DomKey::F1, 0, ui::EventTimeForNow());

  // Simulate an apps v2 window that has requested top row keys as function
  // keys. The event should not be rewritten.
  window_state->set_top_row_keys_are_function_keys(true);
  ui::EventDispatchDetails details = Send(&press_f1);
  ASSERT_FALSE(details.dispatcher_destroyed);
  PopEvents(&events);
  EXPECT_EQ(1u, events.size());
  EXPECT_EQ(GetExpectedResultAsString(ui::ET_KEY_PRESSED, ui::VKEY_F1,
                                      ui::DomCode::F1, ui::EF_NONE,
                                      ui::DomKey::F1, 0),
            GetKeyEventAsString(*static_cast<ui::KeyEvent*>(events[0])));

  // The event should also not be rewritten if the send-function-keys pref is
  // additionally set, for both apps v2 and regular windows.
  BooleanPrefMember send_function_keys_pref;
  send_function_keys_pref.Init(prefs::kLanguageSendFunctionKeys, prefs());
  send_function_keys_pref.SetValue(true);
  window_state->set_top_row_keys_are_function_keys(false);
  details = Send(&press_f1);
  ASSERT_FALSE(details.dispatcher_destroyed);
  PopEvents(&events);
  EXPECT_EQ(1u, events.size());
  EXPECT_EQ(GetExpectedResultAsString(ui::ET_KEY_PRESSED, ui::VKEY_F1,
                                      ui::DomCode::F1, ui::EF_NONE,
                                      ui::DomKey::F1, 0),
            GetKeyEventAsString(*static_cast<ui::KeyEvent*>(events[0])));

  // If the pref isn't set when an event is sent to a regular window, F1 is
  // rewritten to the back key.
  send_function_keys_pref.SetValue(false);
  details = Send(&press_f1);
  ASSERT_FALSE(details.dispatcher_destroyed);
  PopEvents(&events);
  EXPECT_EQ(1u, events.size());
  EXPECT_EQ(GetExpectedResultAsString(ui::ET_KEY_PRESSED, ui::VKEY_BROWSER_BACK,
                                      ui::DomCode::BROWSER_BACK, ui::EF_NONE,
                                      ui::DomKey::BROWSER_BACK, 0),
            GetKeyEventAsString(*static_cast<ui::KeyEvent*>(events[0])));
}

TEST_F(EventRewriterTest, TestRewrittenModifierClick) {
#if defined(USE_X11)
  std::vector<int> device_list;
  device_list.push_back(10);
  ui::TouchFactory::GetInstance()->SetPointerDeviceForTest(device_list);

  // Remap Control to Alt.
  TestingPrefServiceSyncable prefs;
  chromeos::Preferences::RegisterProfilePrefs(prefs.registry());
  IntegerPrefMember control;
  control.Init(prefs::kLanguageRemapControlKeyTo, &prefs);
  control.SetValue(chromeos::input_method::kAltKey);

  EventRewriter rewriter(NULL);
  rewriter.KeyboardDeviceAddedForTesting(kKeyboardDeviceId, "PC Keyboard");
  rewriter.set_pref_service_for_testing(&prefs);

  // Check that Control + Left Button is converted (via Alt + Left Button)
  // to Right Button.
  ui::ScopedXI2Event xev;
  xev.InitGenericButtonEvent(10, ui::ET_MOUSE_PRESSED, gfx::Point(),
                             ui::EF_LEFT_MOUSE_BUTTON | ui::EF_CONTROL_DOWN);
  ui::MouseEvent press(xev);
  // Sanity check.
  EXPECT_EQ(ui::ET_MOUSE_PRESSED, press.type());
  EXPECT_EQ(ui::EF_LEFT_MOUSE_BUTTON | ui::EF_CONTROL_DOWN, press.flags());
  scoped_ptr<ui::Event> new_event;
  const ui::MouseEvent* result =
      RewriteMouseButtonEvent(&rewriter, press, &new_event);
  EXPECT_TRUE(ui::EF_RIGHT_MOUSE_BUTTON & result->flags());
  EXPECT_FALSE(ui::EF_LEFT_MOUSE_BUTTON & result->flags());
  EXPECT_FALSE(ui::EF_CONTROL_DOWN & result->flags());
  EXPECT_FALSE(ui::EF_ALT_DOWN & result->flags());
  EXPECT_TRUE(ui::EF_RIGHT_MOUSE_BUTTON & result->flags());
#endif
}

TEST_F(EventRewriterTest, DontRewriteIfNotRewritten) {
// TODO(kpschoedel): pending changes for crbug.com/360377
// to |chromeos::EventRewriter::RewriteLocatedEvent()
#if defined(USE_X11)
  std::vector<int> device_list;
  device_list.push_back(10);
  device_list.push_back(11);
  ui::TouchFactory::GetInstance()->SetPointerDeviceForTest(device_list);
#endif
  TestingPrefServiceSyncable prefs;
  EventRewriter rewriter(NULL);
  rewriter.set_pref_service_for_testing(&prefs);
  const int kLeftAndAltFlag = ui::EF_LEFT_MOUSE_BUTTON | ui::EF_ALT_DOWN;

  // Test Alt + Left click.
  {
    ui::MouseEvent press(ui::ET_MOUSE_PRESSED, gfx::Point(), gfx::Point(),
                         ui::EventTimeForNow(), kLeftAndAltFlag,
                         ui::EF_LEFT_MOUSE_BUTTON);
    ui::EventTestApi test_press(&press);
    test_press.set_source_device_id(10);
    // Sanity check.
    EXPECT_EQ(ui::ET_MOUSE_PRESSED, press.type());
    EXPECT_EQ(kLeftAndAltFlag, press.flags());
    scoped_ptr<ui::Event> new_event;
    const ui::MouseEvent* result =
        RewriteMouseButtonEvent(&rewriter, press, &new_event);
    EXPECT_TRUE(ui::EF_RIGHT_MOUSE_BUTTON & result->flags());
    EXPECT_FALSE(kLeftAndAltFlag & result->flags());
    EXPECT_EQ(ui::EF_RIGHT_MOUSE_BUTTON, result->changed_button_flags());
  }
  {
    ui::MouseEvent release(ui::ET_MOUSE_RELEASED, gfx::Point(), gfx::Point(),
                           ui::EventTimeForNow(), kLeftAndAltFlag,
                           ui::EF_LEFT_MOUSE_BUTTON);
    ui::EventTestApi test_release(&release);
    test_release.set_source_device_id(10);
    scoped_ptr<ui::Event> new_event;
    const ui::MouseEvent* result =
        RewriteMouseButtonEvent(&rewriter, release, &new_event);
    EXPECT_TRUE(ui::EF_RIGHT_MOUSE_BUTTON & result->flags());
    EXPECT_FALSE(kLeftAndAltFlag & result->flags());
    EXPECT_EQ(ui::EF_RIGHT_MOUSE_BUTTON, result->changed_button_flags());
  }
#if defined(USE_X11)
  // Test Alt + Left click, using XI2 native events.
  {
    ui::ScopedXI2Event xev;
    xev.InitGenericButtonEvent(10, ui::ET_MOUSE_PRESSED, gfx::Point(),
                               kLeftAndAltFlag);
    ui::MouseEvent press(xev);
    // Sanity check.
    EXPECT_EQ(ui::ET_MOUSE_PRESSED, press.type());
    EXPECT_EQ(kLeftAndAltFlag, press.flags());
    scoped_ptr<ui::Event> new_event;
    const ui::MouseEvent* result =
        RewriteMouseButtonEvent(&rewriter, press, &new_event);
    EXPECT_TRUE(ui::EF_RIGHT_MOUSE_BUTTON & result->flags());
    EXPECT_FALSE(kLeftAndAltFlag & result->flags());
    EXPECT_EQ(ui::EF_RIGHT_MOUSE_BUTTON, result->changed_button_flags());
  }
  {
    ui::ScopedXI2Event xev;
    xev.InitGenericButtonEvent(10, ui::ET_MOUSE_RELEASED, gfx::Point(),
                               kLeftAndAltFlag);
    ui::MouseEvent release(xev);
    scoped_ptr<ui::Event> new_event;
    const ui::MouseEvent* result =
        RewriteMouseButtonEvent(&rewriter, release, &new_event);
    EXPECT_TRUE(ui::EF_RIGHT_MOUSE_BUTTON & result->flags());
    EXPECT_FALSE(kLeftAndAltFlag & result->flags());
    EXPECT_EQ(ui::EF_RIGHT_MOUSE_BUTTON, result->changed_button_flags());
  }
#endif

  // No ALT in frst click.
  {
    ui::MouseEvent press(ui::ET_MOUSE_PRESSED, gfx::Point(), gfx::Point(),
                         ui::EventTimeForNow(), ui::EF_LEFT_MOUSE_BUTTON,
                         ui::EF_LEFT_MOUSE_BUTTON);
    ui::EventTestApi test_press(&press);
    test_press.set_source_device_id(10);
    scoped_ptr<ui::Event> new_event;
    const ui::MouseEvent* result =
        RewriteMouseButtonEvent(&rewriter, press, &new_event);
    EXPECT_TRUE(ui::EF_LEFT_MOUSE_BUTTON & result->flags());
    EXPECT_EQ(ui::EF_LEFT_MOUSE_BUTTON, result->changed_button_flags());
  }
  {
    ui::MouseEvent release(ui::ET_MOUSE_RELEASED, gfx::Point(), gfx::Point(),
                           ui::EventTimeForNow(), kLeftAndAltFlag,
                           ui::EF_LEFT_MOUSE_BUTTON);
    ui::EventTestApi test_release(&release);
    test_release.set_source_device_id(10);
    scoped_ptr<ui::Event> new_event;
    const ui::MouseEvent* result =
        RewriteMouseButtonEvent(&rewriter, release, &new_event);
    EXPECT_TRUE((ui::EF_LEFT_MOUSE_BUTTON | ui::EF_ALT_DOWN) & result->flags());
    EXPECT_EQ(ui::EF_LEFT_MOUSE_BUTTON, result->changed_button_flags());
  }
#if defined(USE_X11)
  // No ALT in frst click, using XI2 native events.
  {
    ui::ScopedXI2Event xev;
    xev.InitGenericButtonEvent(10, ui::ET_MOUSE_PRESSED, gfx::Point(),
                               ui::EF_LEFT_MOUSE_BUTTON);
    ui::MouseEvent press(xev);
    scoped_ptr<ui::Event> new_event;
    const ui::MouseEvent* result =
        RewriteMouseButtonEvent(&rewriter, press, &new_event);
    EXPECT_TRUE(ui::EF_LEFT_MOUSE_BUTTON & result->flags());
    EXPECT_EQ(ui::EF_LEFT_MOUSE_BUTTON, result->changed_button_flags());
  }
  {
    ui::ScopedXI2Event xev;
    xev.InitGenericButtonEvent(10, ui::ET_MOUSE_RELEASED, gfx::Point(),
                               kLeftAndAltFlag);
    ui::MouseEvent release(xev);
    scoped_ptr<ui::Event> new_event;
    const ui::MouseEvent* result =
        RewriteMouseButtonEvent(&rewriter, release, &new_event);
    EXPECT_TRUE((ui::EF_LEFT_MOUSE_BUTTON | ui::EF_ALT_DOWN) & result->flags());
    EXPECT_EQ(ui::EF_LEFT_MOUSE_BUTTON, result->changed_button_flags());
  }
#endif

  // ALT on different device.
  {
    ui::MouseEvent press(ui::ET_MOUSE_PRESSED, gfx::Point(), gfx::Point(),
                         ui::EventTimeForNow(), kLeftAndAltFlag,
                         ui::EF_LEFT_MOUSE_BUTTON);
    ui::EventTestApi test_press(&press);
    test_press.set_source_device_id(11);
    scoped_ptr<ui::Event> new_event;
    const ui::MouseEvent* result =
        RewriteMouseButtonEvent(&rewriter, press, &new_event);
    EXPECT_TRUE(ui::EF_RIGHT_MOUSE_BUTTON & result->flags());
    EXPECT_FALSE(kLeftAndAltFlag & result->flags());
    EXPECT_EQ(ui::EF_RIGHT_MOUSE_BUTTON, result->changed_button_flags());
  }
  {
    ui::MouseEvent release(ui::ET_MOUSE_RELEASED, gfx::Point(), gfx::Point(),
                           ui::EventTimeForNow(), kLeftAndAltFlag,
                           ui::EF_LEFT_MOUSE_BUTTON);
    ui::EventTestApi test_release(&release);
    test_release.set_source_device_id(10);
    scoped_ptr<ui::Event> new_event;
    const ui::MouseEvent* result =
        RewriteMouseButtonEvent(&rewriter, release, &new_event);
    EXPECT_TRUE((ui::EF_LEFT_MOUSE_BUTTON | ui::EF_ALT_DOWN) & result->flags());
    EXPECT_EQ(ui::EF_LEFT_MOUSE_BUTTON, result->changed_button_flags());
  }
  {
    ui::MouseEvent release(ui::ET_MOUSE_RELEASED, gfx::Point(), gfx::Point(),
                           ui::EventTimeForNow(), kLeftAndAltFlag,
                           ui::EF_LEFT_MOUSE_BUTTON);
    ui::EventTestApi test_release(&release);
    test_release.set_source_device_id(11);
    scoped_ptr<ui::Event> new_event;
    const ui::MouseEvent* result =
        RewriteMouseButtonEvent(&rewriter, release, &new_event);
    EXPECT_TRUE(ui::EF_RIGHT_MOUSE_BUTTON & result->flags());
    EXPECT_FALSE(kLeftAndAltFlag & result->flags());
    EXPECT_EQ(ui::EF_RIGHT_MOUSE_BUTTON, result->changed_button_flags());
  }
#if defined(USE_X11)
  // ALT on different device, using XI2 native events.
  {
    ui::ScopedXI2Event xev;
    xev.InitGenericButtonEvent(11, ui::ET_MOUSE_PRESSED, gfx::Point(),
                               kLeftAndAltFlag);
    ui::MouseEvent press(xev);
    scoped_ptr<ui::Event> new_event;
    const ui::MouseEvent* result =
        RewriteMouseButtonEvent(&rewriter, press, &new_event);
    EXPECT_TRUE(ui::EF_RIGHT_MOUSE_BUTTON & result->flags());
    EXPECT_FALSE(kLeftAndAltFlag & result->flags());
    EXPECT_EQ(ui::EF_RIGHT_MOUSE_BUTTON, result->changed_button_flags());
  }
  {
    ui::ScopedXI2Event xev;
    xev.InitGenericButtonEvent(10, ui::ET_MOUSE_RELEASED, gfx::Point(),
                               kLeftAndAltFlag);
    ui::MouseEvent release(xev);
    scoped_ptr<ui::Event> new_event;
    const ui::MouseEvent* result =
        RewriteMouseButtonEvent(&rewriter, release, &new_event);
    EXPECT_TRUE((ui::EF_LEFT_MOUSE_BUTTON | ui::EF_ALT_DOWN) & result->flags());
    EXPECT_EQ(ui::EF_LEFT_MOUSE_BUTTON, result->changed_button_flags());
  }
  {
    ui::ScopedXI2Event xev;
    xev.InitGenericButtonEvent(11, ui::ET_MOUSE_RELEASED, gfx::Point(),
                               kLeftAndAltFlag);
    ui::MouseEvent release(xev);
    scoped_ptr<ui::Event> new_event;
    const ui::MouseEvent* result =
        RewriteMouseButtonEvent(&rewriter, release, &new_event);
    EXPECT_TRUE(ui::EF_RIGHT_MOUSE_BUTTON & result->flags());
    EXPECT_FALSE(kLeftAndAltFlag & result->flags());
    EXPECT_EQ(ui::EF_RIGHT_MOUSE_BUTTON, result->changed_button_flags());
  }
#endif
}

TEST_F(EventRewriterAshTest, StickyKeyEventDispatchImpl) {
  // Test the actual key event dispatch implementation.
  ScopedVector<ui::Event> events;

  SendActivateStickyKeyPattern(ui::VKEY_CONTROL, ui::DomCode::CONTROL_LEFT,
                               ui::DomKey::CONTROL, 0);
  PopEvents(&events);
  EXPECT_EQ(1u, events.size());
  EXPECT_EQ(ui::ET_KEY_PRESSED, events[0]->type());
  EXPECT_EQ(ui::VKEY_CONTROL,
            static_cast<ui::KeyEvent*>(events[0])->key_code());

  // Test key press event is correctly modified and modifier release
  // event is sent.
  ui::KeyEvent press(ui::ET_KEY_PRESSED, ui::VKEY_C, ui::DomCode::KEY_C,
                     ui::EF_NONE, ui::DomKey::CHARACTER, 'c',
                     ui::EventTimeForNow());
  ui::EventDispatchDetails details = Send(&press);
  PopEvents(&events);
  EXPECT_EQ(2u, events.size());
  EXPECT_EQ(ui::ET_KEY_PRESSED, events[0]->type());
  EXPECT_EQ(ui::VKEY_C, static_cast<ui::KeyEvent*>(events[0])->key_code());
  EXPECT_TRUE(events[0]->flags() & ui::EF_CONTROL_DOWN);
  EXPECT_EQ(ui::ET_KEY_RELEASED, events[1]->type());
  EXPECT_EQ(ui::VKEY_CONTROL,
            static_cast<ui::KeyEvent*>(events[1])->key_code());

  // Test key release event is not modified.
  ui::KeyEvent release(ui::ET_KEY_RELEASED, ui::VKEY_C, ui::DomCode::KEY_C,
                       ui::EF_NONE, ui::DomKey::CHARACTER, 'c',
                       ui::EventTimeForNow());
  details = Send(&release);
  ASSERT_FALSE(details.dispatcher_destroyed);
  PopEvents(&events);
  EXPECT_EQ(1u, events.size());
  EXPECT_EQ(ui::ET_KEY_RELEASED, events[0]->type());
  EXPECT_EQ(ui::VKEY_C, static_cast<ui::KeyEvent*>(events[0])->key_code());
  EXPECT_FALSE(events[0]->flags() & ui::EF_CONTROL_DOWN);
}

TEST_F(EventRewriterAshTest, MouseEventDispatchImpl) {
  ScopedVector<ui::Event> events;

  SendActivateStickyKeyPattern(ui::VKEY_CONTROL, ui::DomCode::CONTROL_LEFT,
                               ui::DomKey::CONTROL, 0);
  PopEvents(&events);

  // Test mouse press event is correctly modified.
  gfx::Point location(0, 0);
  ui::MouseEvent press(ui::ET_MOUSE_PRESSED, location, location,
                       ui::EventTimeForNow(), ui::EF_LEFT_MOUSE_BUTTON,
                       ui::EF_LEFT_MOUSE_BUTTON);
  ui::EventDispatchDetails details = Send(&press);
  ASSERT_FALSE(details.dispatcher_destroyed);
  PopEvents(&events);
  EXPECT_EQ(1u, events.size());
  EXPECT_EQ(ui::ET_MOUSE_PRESSED, events[0]->type());
  EXPECT_TRUE(events[0]->flags() & ui::EF_CONTROL_DOWN);

  // Test mouse release event is correctly modified and modifier release
  // event is sent. The mouse event should have the correct DIP location.
  ui::MouseEvent release(ui::ET_MOUSE_RELEASED, location, location,
                         ui::EventTimeForNow(), ui::EF_LEFT_MOUSE_BUTTON,
                         ui::EF_LEFT_MOUSE_BUTTON);
  details = Send(&release);
  ASSERT_FALSE(details.dispatcher_destroyed);
  PopEvents(&events);
  EXPECT_EQ(2u, events.size());
  EXPECT_EQ(ui::ET_MOUSE_RELEASED, events[0]->type());
  EXPECT_TRUE(events[0]->flags() & ui::EF_CONTROL_DOWN);
  EXPECT_EQ(ui::ET_KEY_RELEASED, events[1]->type());
  EXPECT_EQ(ui::VKEY_CONTROL,
            static_cast<ui::KeyEvent*>(events[1])->key_code());
}

TEST_F(EventRewriterAshTest, MouseWheelEventDispatchImpl) {
  ScopedVector<ui::Event> events;

  // Test positive mouse wheel event is correctly modified and modifier release
  // event is sent.
  SendActivateStickyKeyPattern(ui::VKEY_CONTROL, ui::DomCode::CONTROL_LEFT,
                               ui::DomKey::CONTROL, 0);
  PopEvents(&events);
  gfx::Point location(0, 0);
  ui::MouseEvent mev(ui::ET_MOUSEWHEEL, location, location,
                     ui::EventTimeForNow(), ui::EF_LEFT_MOUSE_BUTTON,
                     ui::EF_LEFT_MOUSE_BUTTON);
  ui::MouseWheelEvent positive(mev, 0, ui::MouseWheelEvent::kWheelDelta);
  ui::EventDispatchDetails details = Send(&positive);
  ASSERT_FALSE(details.dispatcher_destroyed);
  PopEvents(&events);
  EXPECT_EQ(2u, events.size());
  EXPECT_TRUE(events[0]->IsMouseWheelEvent());
  EXPECT_TRUE(events[0]->flags() & ui::EF_CONTROL_DOWN);
  EXPECT_EQ(ui::ET_KEY_RELEASED, events[1]->type());
  EXPECT_EQ(ui::VKEY_CONTROL,
            static_cast<ui::KeyEvent*>(events[1])->key_code());

  // Test negative mouse wheel event is correctly modified and modifier release
  // event is sent.
  SendActivateStickyKeyPattern(ui::VKEY_CONTROL, ui::DomCode::CONTROL_LEFT,
                               ui::DomKey::CONTROL, 0);
  PopEvents(&events);
  ui::MouseWheelEvent negative(mev, 0, -ui::MouseWheelEvent::kWheelDelta);
  details = Send(&negative);
  ASSERT_FALSE(details.dispatcher_destroyed);
  PopEvents(&events);
  EXPECT_EQ(2u, events.size());
  EXPECT_TRUE(events[0]->IsMouseWheelEvent());
  EXPECT_TRUE(events[0]->flags() & ui::EF_CONTROL_DOWN);
  EXPECT_EQ(ui::ET_KEY_RELEASED, events[1]->type());
  EXPECT_EQ(ui::VKEY_CONTROL,
            static_cast<ui::KeyEvent*>(events[1])->key_code());
}

class StickyKeysOverlayTest : public EventRewriterAshTest {
 public:
  StickyKeysOverlayTest() : overlay_(NULL) {}

  ~StickyKeysOverlayTest() override {}

  void SetUp() override {
    EventRewriterAshTest::SetUp();
    overlay_ = sticky_keys_controller_->GetOverlayForTest();
    ASSERT_TRUE(overlay_);
  }

  ash::StickyKeysOverlay* overlay_;
};

TEST_F(StickyKeysOverlayTest, OneModifierEnabled) {
  EXPECT_FALSE(overlay_->is_visible());
  EXPECT_EQ(ash::STICKY_KEY_STATE_DISABLED,
            overlay_->GetModifierKeyState(ui::EF_CONTROL_DOWN));

  // Pressing modifier key should show overlay.
  SendActivateStickyKeyPattern(ui::VKEY_CONTROL, ui::DomCode::CONTROL_LEFT,
                               ui::DomKey::CONTROL, 0);
  EXPECT_TRUE(overlay_->is_visible());
  EXPECT_EQ(ash::STICKY_KEY_STATE_ENABLED,
            overlay_->GetModifierKeyState(ui::EF_CONTROL_DOWN));

  // Pressing a normal key should hide overlay.
  SendActivateStickyKeyPattern(ui::VKEY_T, ui::DomCode::KEY_T,
                               ui::DomKey::CHARACTER, 't');
  EXPECT_FALSE(overlay_->is_visible());
  EXPECT_EQ(ash::STICKY_KEY_STATE_DISABLED,
            overlay_->GetModifierKeyState(ui::EF_CONTROL_DOWN));
}

TEST_F(StickyKeysOverlayTest, TwoModifiersEnabled) {
  EXPECT_FALSE(overlay_->is_visible());
  EXPECT_EQ(ash::STICKY_KEY_STATE_DISABLED,
            overlay_->GetModifierKeyState(ui::EF_CONTROL_DOWN));
  EXPECT_EQ(ash::STICKY_KEY_STATE_DISABLED,
            overlay_->GetModifierKeyState(ui::EF_SHIFT_DOWN));

  // Pressing two modifiers should show overlay.
  SendActivateStickyKeyPattern(ui::VKEY_SHIFT, ui::DomCode::SHIFT_LEFT,
                               ui::DomKey::SHIFT, 0);
  SendActivateStickyKeyPattern(ui::VKEY_CONTROL, ui::DomCode::CONTROL_LEFT,
                               ui::DomKey::CONTROL, 0);
  EXPECT_TRUE(overlay_->is_visible());
  EXPECT_EQ(ash::STICKY_KEY_STATE_ENABLED,
            overlay_->GetModifierKeyState(ui::EF_SHIFT_DOWN));
  EXPECT_EQ(ash::STICKY_KEY_STATE_ENABLED,
            overlay_->GetModifierKeyState(ui::EF_CONTROL_DOWN));

  // Pressing a normal key should hide overlay.
  SendActivateStickyKeyPattern(ui::VKEY_N, ui::DomCode::KEY_N,
                               ui::DomKey::CHARACTER, 'n');
  EXPECT_FALSE(overlay_->is_visible());
  EXPECT_EQ(ash::STICKY_KEY_STATE_DISABLED,
            overlay_->GetModifierKeyState(ui::EF_CONTROL_DOWN));
  EXPECT_EQ(ash::STICKY_KEY_STATE_DISABLED,
            overlay_->GetModifierKeyState(ui::EF_SHIFT_DOWN));
}

TEST_F(StickyKeysOverlayTest, LockedModifier) {
  EXPECT_FALSE(overlay_->is_visible());
  EXPECT_EQ(ash::STICKY_KEY_STATE_DISABLED,
            overlay_->GetModifierKeyState(ui::EF_ALT_DOWN));

  // Pressing a modifier key twice should lock modifier and show overlay.
  SendActivateStickyKeyPattern(ui::VKEY_LMENU, ui::DomCode::ALT_LEFT,
                               ui::DomKey::ALT, 0);
  SendActivateStickyKeyPattern(ui::VKEY_LMENU, ui::DomCode::ALT_LEFT,
                               ui::DomKey::ALT, 0);
  EXPECT_TRUE(overlay_->is_visible());
  EXPECT_EQ(ash::STICKY_KEY_STATE_LOCKED,
            overlay_->GetModifierKeyState(ui::EF_ALT_DOWN));

  // Pressing a normal key should not hide overlay.
  SendActivateStickyKeyPattern(ui::VKEY_D, ui::DomCode::KEY_D,
                               ui::DomKey::CHARACTER, 'd');
  EXPECT_TRUE(overlay_->is_visible());
  EXPECT_EQ(ash::STICKY_KEY_STATE_LOCKED,
            overlay_->GetModifierKeyState(ui::EF_ALT_DOWN));
}

TEST_F(StickyKeysOverlayTest, LockedAndNormalModifier) {
  EXPECT_FALSE(overlay_->is_visible());
  EXPECT_EQ(ash::STICKY_KEY_STATE_DISABLED,
            overlay_->GetModifierKeyState(ui::EF_CONTROL_DOWN));
  EXPECT_EQ(ash::STICKY_KEY_STATE_DISABLED,
            overlay_->GetModifierKeyState(ui::EF_SHIFT_DOWN));

  // Pressing a modifier key twice should lock modifier and show overlay.
  SendActivateStickyKeyPattern(ui::VKEY_CONTROL, ui::DomCode::CONTROL_LEFT,
                               ui::DomKey::CONTROL, 0);
  SendActivateStickyKeyPattern(ui::VKEY_CONTROL, ui::DomCode::CONTROL_LEFT,
                               ui::DomKey::CONTROL, 0);
  EXPECT_TRUE(overlay_->is_visible());
  EXPECT_EQ(ash::STICKY_KEY_STATE_LOCKED,
            overlay_->GetModifierKeyState(ui::EF_CONTROL_DOWN));

  // Pressing another modifier key should still show overlay.
  SendActivateStickyKeyPattern(ui::VKEY_SHIFT, ui::DomCode::SHIFT_LEFT,
                               ui::DomKey::SHIFT, 0);
  EXPECT_TRUE(overlay_->is_visible());
  EXPECT_EQ(ash::STICKY_KEY_STATE_LOCKED,
            overlay_->GetModifierKeyState(ui::EF_CONTROL_DOWN));
  EXPECT_EQ(ash::STICKY_KEY_STATE_ENABLED,
            overlay_->GetModifierKeyState(ui::EF_SHIFT_DOWN));

  // Pressing a normal key should not hide overlay but disable normal modifier.
  SendActivateStickyKeyPattern(ui::VKEY_D, ui::DomCode::KEY_D,
                               ui::DomKey::CHARACTER, 'd');
  EXPECT_TRUE(overlay_->is_visible());
  EXPECT_EQ(ash::STICKY_KEY_STATE_LOCKED,
            overlay_->GetModifierKeyState(ui::EF_CONTROL_DOWN));
  EXPECT_EQ(ash::STICKY_KEY_STATE_DISABLED,
            overlay_->GetModifierKeyState(ui::EF_SHIFT_DOWN));
}

TEST_F(StickyKeysOverlayTest, ModifiersDisabled) {
  EXPECT_FALSE(overlay_->is_visible());
  EXPECT_EQ(ash::STICKY_KEY_STATE_DISABLED,
            overlay_->GetModifierKeyState(ui::EF_CONTROL_DOWN));
  EXPECT_EQ(ash::STICKY_KEY_STATE_DISABLED,
            overlay_->GetModifierKeyState(ui::EF_SHIFT_DOWN));
  EXPECT_EQ(ash::STICKY_KEY_STATE_DISABLED,
            overlay_->GetModifierKeyState(ui::EF_ALT_DOWN));
  EXPECT_EQ(ash::STICKY_KEY_STATE_DISABLED,
            overlay_->GetModifierKeyState(ui::EF_COMMAND_DOWN));

  // Enable modifiers.
  SendActivateStickyKeyPattern(ui::VKEY_CONTROL, ui::DomCode::CONTROL_LEFT,
                               ui::DomKey::CONTROL, 0);
  SendActivateStickyKeyPattern(ui::VKEY_SHIFT, ui::DomCode::SHIFT_LEFT,
                               ui::DomKey::SHIFT, 0);
  SendActivateStickyKeyPattern(ui::VKEY_SHIFT, ui::DomCode::SHIFT_LEFT,
                               ui::DomKey::SHIFT, 0);
  SendActivateStickyKeyPattern(ui::VKEY_LMENU, ui::DomCode::ALT_LEFT,
                               ui::DomKey::ALT, 0);
  SendActivateStickyKeyPattern(ui::VKEY_COMMAND, ui::DomCode::OS_LEFT,
                               ui::DomKey::OS, 0);
  SendActivateStickyKeyPattern(ui::VKEY_COMMAND, ui::DomCode::OS_LEFT,
                               ui::DomKey::OS, 0);

  EXPECT_TRUE(overlay_->is_visible());
  EXPECT_EQ(ash::STICKY_KEY_STATE_ENABLED,
            overlay_->GetModifierKeyState(ui::EF_CONTROL_DOWN));
  EXPECT_EQ(ash::STICKY_KEY_STATE_LOCKED,
            overlay_->GetModifierKeyState(ui::EF_SHIFT_DOWN));
  EXPECT_EQ(ash::STICKY_KEY_STATE_ENABLED,
            overlay_->GetModifierKeyState(ui::EF_ALT_DOWN));
  EXPECT_EQ(ash::STICKY_KEY_STATE_LOCKED,
            overlay_->GetModifierKeyState(ui::EF_COMMAND_DOWN));

  // Disable modifiers and overlay should be hidden.
  SendActivateStickyKeyPattern(ui::VKEY_CONTROL, ui::DomCode::CONTROL_LEFT,
                               ui::DomKey::CONTROL, 0);
  SendActivateStickyKeyPattern(ui::VKEY_CONTROL, ui::DomCode::CONTROL_LEFT,
                               ui::DomKey::CONTROL, 0);
  SendActivateStickyKeyPattern(ui::VKEY_SHIFT, ui::DomCode::SHIFT_LEFT,
                               ui::DomKey::SHIFT, 0);
  SendActivateStickyKeyPattern(ui::VKEY_LMENU, ui::DomCode::ALT_LEFT,
                               ui::DomKey::ALT, 0);
  SendActivateStickyKeyPattern(ui::VKEY_LMENU, ui::DomCode::ALT_LEFT,
                               ui::DomKey::ALT, 0);
  SendActivateStickyKeyPattern(ui::VKEY_COMMAND, ui::DomCode::OS_LEFT,
                               ui::DomKey::OS, 0);

  EXPECT_FALSE(overlay_->is_visible());
  EXPECT_EQ(ash::STICKY_KEY_STATE_DISABLED,
            overlay_->GetModifierKeyState(ui::EF_CONTROL_DOWN));
  EXPECT_EQ(ash::STICKY_KEY_STATE_DISABLED,
            overlay_->GetModifierKeyState(ui::EF_SHIFT_DOWN));
  EXPECT_EQ(ash::STICKY_KEY_STATE_DISABLED,
            overlay_->GetModifierKeyState(ui::EF_ALT_DOWN));
  EXPECT_EQ(ash::STICKY_KEY_STATE_DISABLED,
            overlay_->GetModifierKeyState(ui::EF_COMMAND_DOWN));
}

TEST_F(StickyKeysOverlayTest, ModifierVisibility) {
  // All but AltGr and Mod3 should initially be visible.
  EXPECT_TRUE(overlay_->GetModifierVisible(ui::EF_CONTROL_DOWN));
  EXPECT_TRUE(overlay_->GetModifierVisible(ui::EF_SHIFT_DOWN));
  EXPECT_TRUE(overlay_->GetModifierVisible(ui::EF_ALT_DOWN));
  EXPECT_TRUE(overlay_->GetModifierVisible(ui::EF_COMMAND_DOWN));
  EXPECT_FALSE(overlay_->GetModifierVisible(ui::EF_ALTGR_DOWN));
  EXPECT_FALSE(overlay_->GetModifierVisible(ui::EF_MOD3_DOWN));

  // Turn all modifiers on.
  sticky_keys_controller_->SetModifiersEnabled(true, true);
  EXPECT_TRUE(overlay_->GetModifierVisible(ui::EF_CONTROL_DOWN));
  EXPECT_TRUE(overlay_->GetModifierVisible(ui::EF_SHIFT_DOWN));
  EXPECT_TRUE(overlay_->GetModifierVisible(ui::EF_ALT_DOWN));
  EXPECT_TRUE(overlay_->GetModifierVisible(ui::EF_COMMAND_DOWN));
  EXPECT_TRUE(overlay_->GetModifierVisible(ui::EF_ALTGR_DOWN));
  EXPECT_TRUE(overlay_->GetModifierVisible(ui::EF_MOD3_DOWN));

  // Turn off Mod3.
  sticky_keys_controller_->SetModifiersEnabled(false, true);
  EXPECT_TRUE(overlay_->GetModifierVisible(ui::EF_ALTGR_DOWN));
  EXPECT_FALSE(overlay_->GetModifierVisible(ui::EF_MOD3_DOWN));

  // Turn off AltGr.
  sticky_keys_controller_->SetModifiersEnabled(true, false);
  EXPECT_FALSE(overlay_->GetModifierVisible(ui::EF_ALTGR_DOWN));
  EXPECT_TRUE(overlay_->GetModifierVisible(ui::EF_MOD3_DOWN));

  // Turn off AltGr and Mod3.
  sticky_keys_controller_->SetModifiersEnabled(false, false);
  EXPECT_FALSE(overlay_->GetModifierVisible(ui::EF_ALTGR_DOWN));
  EXPECT_FALSE(overlay_->GetModifierVisible(ui::EF_MOD3_DOWN));
}

}  // namespace chromeos
