1// Copyright (c) 2012 The Chromium Authors. All rights reserved.
2// Use of this source code is governed by a BSD-style license that can be
3// found in the LICENSE file.
4
5#include "chrome/browser/ui/ash/event_rewriter.h"
6
7#include "base/basictypes.h"
8#include "base/command_line.h"
9#include "base/prefs/pref_member.h"
10#include "base/strings/stringprintf.h"
11#include "chrome/common/pref_names.h"
12#include "chrome/test/base/testing_pref_service_syncable.h"
13#include "testing/gtest/include/gtest/gtest.h"
14#include "ui/base/events/event.h"
15
16#if defined(OS_CHROMEOS)
17#include <X11/keysym.h>
18#include <X11/XF86keysym.h>
19#include <X11/Xlib.h>
20
21#include "chrome/browser/chromeos/input_method/input_method_configuration.h"
22#include "chrome/browser/chromeos/input_method/mock_input_method_manager.h"
23#include "chrome/browser/chromeos/login/mock_user_manager.h"
24#include "chrome/browser/chromeos/login/user_manager.h"
25#include "chrome/browser/chromeos/preferences.h"
26#include "chromeos/chromeos_switches.h"
27#include "chromeos/ime/mock_xkeyboard.h"
28#include "ui/base/x/x11_util.h"
29
30namespace {
31
32void InitXKeyEvent(ui::KeyboardCode ui_keycode,
33                   int ui_flags,
34                   ui::EventType ui_type,
35                   KeyCode x_keycode,
36                   unsigned int x_state,
37                   XEvent* event) {
38  ui::InitXKeyEventForTesting(ui_type,
39                              ui_keycode,
40                              ui_flags,
41                              event);
42  event->xkey.keycode = x_keycode;
43  event->xkey.state = x_state;
44}
45
46std::string GetRewrittenEventAsString(EventRewriter* rewriter,
47                                      ui::KeyboardCode ui_keycode,
48                                      int ui_flags,
49                                      ui::EventType ui_type,
50                                      KeyCode x_keycode,
51                                      unsigned int x_state) {
52  XEvent xev;
53  InitXKeyEvent(ui_keycode, ui_flags, ui_type, x_keycode, x_state, &xev);
54  ui::KeyEvent keyevent(&xev, false /* is_char */);
55  rewriter->RewriteForTesting(&keyevent);
56  return base::StringPrintf(
57      "ui_keycode=%d ui_flags=%d ui_type=%d x_keycode=%u x_state=%u x_type=%d",
58      keyevent.key_code(), keyevent.flags(), keyevent.type(),
59      xev.xkey.keycode, xev.xkey.state, xev.xkey.type);
60}
61
62std::string GetExpectedResultAsString(ui::KeyboardCode ui_keycode,
63                                      int ui_flags,
64                                      ui::EventType ui_type,
65                                      KeyCode x_keycode,
66                                      unsigned int x_state,
67                                      int x_type) {
68  return base::StringPrintf(
69      "ui_keycode=%d ui_flags=%d ui_type=%d x_keycode=%u x_state=%u x_type=%d",
70      ui_keycode, ui_flags, ui_type, x_keycode, x_state, x_type);
71}
72
73class EventRewriterTest : public testing::Test {
74 public:
75  EventRewriterTest()
76      : display_(ui::GetXDisplay()),
77        keycode_a_(XKeysymToKeycode(display_, XK_a)),
78        keycode_alt_l_(XKeysymToKeycode(display_, XK_Alt_L)),
79        keycode_alt_r_(XKeysymToKeycode(display_, XK_Alt_R)),
80        keycode_b_(XKeysymToKeycode(display_, XK_B)),
81        keycode_caps_lock_(XKeysymToKeycode(display_, XK_Caps_Lock)),
82        keycode_control_l_(XKeysymToKeycode(display_, XK_Control_L)),
83        keycode_control_r_(XKeysymToKeycode(display_, XK_Control_R)),
84        keycode_meta_l_(XKeysymToKeycode(display_, XK_Meta_L)),
85        keycode_meta_r_(XKeysymToKeycode(display_, XK_Meta_R)),
86        keycode_num_pad_0_(XKeysymToKeycode(display_, XK_KP_0)),
87        keycode_num_pad_1_(XKeysymToKeycode(display_, XK_KP_1)),
88        keycode_num_pad_2_(XKeysymToKeycode(display_, XK_KP_2)),
89        keycode_num_pad_3_(XKeysymToKeycode(display_, XK_KP_3)),
90        keycode_num_pad_4_(XKeysymToKeycode(display_, XK_KP_4)),
91        keycode_num_pad_5_(XKeysymToKeycode(display_, XK_KP_5)),
92        keycode_num_pad_6_(XKeysymToKeycode(display_, XK_KP_6)),
93        keycode_num_pad_7_(XKeysymToKeycode(display_, XK_KP_7)),
94        keycode_num_pad_8_(XKeysymToKeycode(display_, XK_KP_8)),
95        keycode_num_pad_9_(XKeysymToKeycode(display_, XK_KP_9)),
96        keycode_num_pad_begin_(XKeysymToKeycode(display_, XK_KP_Begin)),
97        keycode_num_pad_decimal_(XKeysymToKeycode(display_, XK_KP_Decimal)),
98        keycode_num_pad_delete_(XKeysymToKeycode(display_, XK_KP_Delete)),
99        keycode_num_pad_down_(XKeysymToKeycode(display_, XK_KP_Down)),
100        keycode_num_pad_end_(XKeysymToKeycode(display_, XK_KP_End)),
101        keycode_num_pad_home_(XKeysymToKeycode(display_, XK_KP_Home)),
102        keycode_num_pad_insert_(XKeysymToKeycode(display_, XK_KP_Insert)),
103        keycode_num_pad_left_(XKeysymToKeycode(display_, XK_KP_Left)),
104        keycode_num_pad_next_(XKeysymToKeycode(display_, XK_KP_Next)),
105        keycode_num_pad_prior_(XKeysymToKeycode(display_, XK_KP_Prior)),
106        keycode_num_pad_right_(XKeysymToKeycode(display_, XK_KP_Right)),
107        keycode_num_pad_up_(XKeysymToKeycode(display_, XK_KP_Up)),
108        keycode_super_l_(XKeysymToKeycode(display_, XK_Super_L)),
109        keycode_super_r_(XKeysymToKeycode(display_, XK_Super_R)),
110        keycode_void_symbol_(XKeysymToKeycode(display_, XK_VoidSymbol)),
111        keycode_delete_(XKeysymToKeycode(display_, XK_Delete)),
112        keycode_backspace_(XKeysymToKeycode(display_, XK_BackSpace)),
113        keycode_up_(XKeysymToKeycode(display_, XK_Up)),
114        keycode_down_(XKeysymToKeycode(display_, XK_Down)),
115        keycode_left_(XKeysymToKeycode(display_, XK_Left)),
116        keycode_right_(XKeysymToKeycode(display_, XK_Right)),
117        keycode_prior_(XKeysymToKeycode(display_, XK_Prior)),
118        keycode_next_(XKeysymToKeycode(display_, XK_Next)),
119        keycode_home_(XKeysymToKeycode(display_, XK_Home)),
120        keycode_end_(XKeysymToKeycode(display_, XK_End)),
121        keycode_launch6_(XKeysymToKeycode(display_, XF86XK_Launch6)),
122        keycode_launch7_(XKeysymToKeycode(display_, XF86XK_Launch7)),
123        keycode_f1_(XKeysymToKeycode(display_, XK_F1)),
124        keycode_f2_(XKeysymToKeycode(display_, XK_F2)),
125        keycode_f3_(XKeysymToKeycode(display_, XK_F3)),
126        keycode_f4_(XKeysymToKeycode(display_, XK_F4)),
127        keycode_f5_(XKeysymToKeycode(display_, XK_F5)),
128        keycode_f6_(XKeysymToKeycode(display_, XK_F6)),
129        keycode_f7_(XKeysymToKeycode(display_, XK_F7)),
130        keycode_f8_(XKeysymToKeycode(display_, XK_F8)),
131        keycode_f9_(XKeysymToKeycode(display_, XK_F9)),
132        keycode_f10_(XKeysymToKeycode(display_, XK_F10)),
133        keycode_f11_(XKeysymToKeycode(display_, XK_F11)),
134        keycode_f12_(XKeysymToKeycode(display_, XK_F12)),
135        keycode_browser_back_(XKeysymToKeycode(display_, XF86XK_Back)),
136        keycode_browser_forward_(XKeysymToKeycode(display_, XF86XK_Forward)),
137        keycode_browser_refresh_(XKeysymToKeycode(display_, XF86XK_Reload)),
138        keycode_media_launch_app1_(XKeysymToKeycode(display_, XF86XK_LaunchA)),
139        keycode_media_launch_app2_(XKeysymToKeycode(display_, XF86XK_LaunchB)),
140        keycode_brightness_down_(XKeysymToKeycode(
141            display_, XF86XK_MonBrightnessDown)),
142        keycode_brightness_up_(XKeysymToKeycode(
143            display_, XF86XK_MonBrightnessUp)),
144        keycode_volume_mute_(XKeysymToKeycode(display_, XF86XK_AudioMute)),
145        keycode_volume_down_(XKeysymToKeycode(
146            display_, XF86XK_AudioLowerVolume)),
147        keycode_volume_up_(XKeysymToKeycode(
148            display_, XF86XK_AudioRaiseVolume)),
149        keycode_power_(XKeysymToKeycode(display_, XF86XK_PowerOff)),
150        keycode_1_(XKeysymToKeycode(display_, XK_1)),
151        keycode_2_(XKeysymToKeycode(display_, XK_2)),
152        keycode_3_(XKeysymToKeycode(display_, XK_3)),
153        keycode_4_(XKeysymToKeycode(display_, XK_4)),
154        keycode_5_(XKeysymToKeycode(display_, XK_5)),
155        keycode_6_(XKeysymToKeycode(display_, XK_6)),
156        keycode_7_(XKeysymToKeycode(display_, XK_7)),
157        keycode_8_(XKeysymToKeycode(display_, XK_8)),
158        keycode_9_(XKeysymToKeycode(display_, XK_9)),
159        keycode_0_(XKeysymToKeycode(display_, XK_0)),
160        keycode_minus_(XKeysymToKeycode(display_, XK_minus)),
161        keycode_equal_(XKeysymToKeycode(display_, XK_equal)),
162        keycode_period_(XKeysymToKeycode(display_, XK_period)),
163        keycode_insert_(XKeysymToKeycode(display_, XK_Insert)),
164        mock_user_manager_(new chromeos::MockUserManager),
165        user_manager_enabler_(mock_user_manager_),
166        input_method_manager_mock_(NULL) {
167  }
168  virtual ~EventRewriterTest() {}
169
170  virtual void SetUp() {
171    // Mocking user manager because the real one needs to be called on UI thread
172    EXPECT_CALL(*mock_user_manager_, IsLoggedInAsGuest())
173        .WillRepeatedly(testing::Return(false));
174    input_method_manager_mock_ =
175        new chromeos::input_method::MockInputMethodManager;
176    chromeos::input_method::InitializeForTesting(
177        input_method_manager_mock_);  // pass ownership
178  }
179
180  virtual void TearDown() {
181    // Shutdown() deletes the IME mock object.
182    chromeos::input_method::Shutdown();
183  }
184
185 protected:
186  void TestRewriteNumPadKeys();
187  void TestRewriteNumPadKeysOnAppleKeyboard();
188
189  Display* display_;
190  const KeyCode keycode_a_;
191  const KeyCode keycode_alt_l_;
192  const KeyCode keycode_alt_r_;
193  const KeyCode keycode_b_;
194  const KeyCode keycode_caps_lock_;
195  const KeyCode keycode_control_l_;
196  const KeyCode keycode_control_r_;
197  const KeyCode keycode_meta_l_;
198  const KeyCode keycode_meta_r_;
199  const KeyCode keycode_num_pad_0_;
200  const KeyCode keycode_num_pad_1_;
201  const KeyCode keycode_num_pad_2_;
202  const KeyCode keycode_num_pad_3_;
203  const KeyCode keycode_num_pad_4_;
204  const KeyCode keycode_num_pad_5_;
205  const KeyCode keycode_num_pad_6_;
206  const KeyCode keycode_num_pad_7_;
207  const KeyCode keycode_num_pad_8_;
208  const KeyCode keycode_num_pad_9_;
209  const KeyCode keycode_num_pad_begin_;
210  const KeyCode keycode_num_pad_decimal_;
211  const KeyCode keycode_num_pad_delete_;
212  const KeyCode keycode_num_pad_down_;
213  const KeyCode keycode_num_pad_end_;
214  const KeyCode keycode_num_pad_home_;
215  const KeyCode keycode_num_pad_insert_;
216  const KeyCode keycode_num_pad_left_;
217  const KeyCode keycode_num_pad_next_;
218  const KeyCode keycode_num_pad_prior_;
219  const KeyCode keycode_num_pad_right_;
220  const KeyCode keycode_num_pad_up_;
221  const KeyCode keycode_super_l_;
222  const KeyCode keycode_super_r_;
223  const KeyCode keycode_void_symbol_;
224  const KeyCode keycode_delete_;
225  const KeyCode keycode_backspace_;
226  const KeyCode keycode_up_;
227  const KeyCode keycode_down_;
228  const KeyCode keycode_left_;
229  const KeyCode keycode_right_;
230  const KeyCode keycode_prior_;
231  const KeyCode keycode_next_;
232  const KeyCode keycode_home_;
233  const KeyCode keycode_end_;
234  const KeyCode keycode_launch6_;  // F15
235  const KeyCode keycode_launch7_;  // F16
236  const KeyCode keycode_f1_;
237  const KeyCode keycode_f2_;
238  const KeyCode keycode_f3_;
239  const KeyCode keycode_f4_;
240  const KeyCode keycode_f5_;
241  const KeyCode keycode_f6_;
242  const KeyCode keycode_f7_;
243  const KeyCode keycode_f8_;
244  const KeyCode keycode_f9_;
245  const KeyCode keycode_f10_;
246  const KeyCode keycode_f11_;
247  const KeyCode keycode_f12_;
248  const KeyCode keycode_browser_back_;
249  const KeyCode keycode_browser_forward_;
250  const KeyCode keycode_browser_refresh_;
251  const KeyCode keycode_media_launch_app1_;
252  const KeyCode keycode_media_launch_app2_;
253  const KeyCode keycode_brightness_down_;
254  const KeyCode keycode_brightness_up_;
255  const KeyCode keycode_volume_mute_;
256  const KeyCode keycode_volume_down_;
257  const KeyCode keycode_volume_up_;
258  const KeyCode keycode_power_;
259  const KeyCode keycode_1_;
260  const KeyCode keycode_2_;
261  const KeyCode keycode_3_;
262  const KeyCode keycode_4_;
263  const KeyCode keycode_5_;
264  const KeyCode keycode_6_;
265  const KeyCode keycode_7_;
266  const KeyCode keycode_8_;
267  const KeyCode keycode_9_;
268  const KeyCode keycode_0_;
269  const KeyCode keycode_minus_;
270  const KeyCode keycode_equal_;
271  const KeyCode keycode_period_;
272  const KeyCode keycode_insert_;
273  chromeos::MockUserManager* mock_user_manager_;  // Not owned.
274  chromeos::ScopedUserManagerEnabler user_manager_enabler_;
275  chromeos::input_method::MockInputMethodManager* input_method_manager_mock_;
276};
277
278}  // namespace
279#else
280class EventRewriterTest : public testing::Test {
281 public:
282  EventRewriterTest() {}
283  virtual ~EventRewriterTest() {}
284};
285#endif
286
287TEST_F(EventRewriterTest, TestGetDeviceType) {
288  // This is the typical string which an Apple keyboard sends.
289  EXPECT_EQ(EventRewriter::kDeviceAppleKeyboard,
290            EventRewriter::GetDeviceType("Apple Inc. Apple Keyboard"));
291
292  // Other cases we accept.
293  EXPECT_EQ(EventRewriter::kDeviceAppleKeyboard,
294            EventRewriter::GetDeviceType("Apple Keyboard"));
295  EXPECT_EQ(EventRewriter::kDeviceAppleKeyboard,
296            EventRewriter::GetDeviceType("apple keyboard"));
297  EXPECT_EQ(EventRewriter::kDeviceAppleKeyboard,
298            EventRewriter::GetDeviceType("apple keyboard."));
299  EXPECT_EQ(EventRewriter::kDeviceAppleKeyboard,
300            EventRewriter::GetDeviceType("apple.keyboard."));
301  EXPECT_EQ(EventRewriter::kDeviceAppleKeyboard,
302            EventRewriter::GetDeviceType(".apple.keyboard."));
303
304  // Dell, Microsoft, Logitech, ... should be recognized as a kDeviceUnknown.
305  EXPECT_EQ(EventRewriter::kDeviceUnknown,
306            EventRewriter::GetDeviceType("Dell Dell USB Entry Keyboard"));
307  EXPECT_EQ(EventRewriter::kDeviceUnknown,
308            EventRewriter::GetDeviceType(
309                "Microsoft Natural Ergonomic Keyboard"));
310  EXPECT_EQ(EventRewriter::kDeviceUnknown,
311            EventRewriter::GetDeviceType("CHESEN USB Keyboard"));
312
313  // Some corner cases.
314  EXPECT_EQ(EventRewriter::kDeviceUnknown, EventRewriter::GetDeviceType(""));
315  EXPECT_EQ(EventRewriter::kDeviceUnknown,
316            EventRewriter::GetDeviceType("."));
317  EXPECT_EQ(EventRewriter::kDeviceUnknown,
318            EventRewriter::GetDeviceType(". "));
319  EXPECT_EQ(EventRewriter::kDeviceUnknown,
320            EventRewriter::GetDeviceType(" ."));
321  EXPECT_EQ(EventRewriter::kDeviceUnknown,
322            EventRewriter::GetDeviceType("not-an-apple keyboard"));
323}
324
325TEST_F(EventRewriterTest, TestDeviceAddedOrRemoved) {
326  EventRewriter rewriter;
327  EXPECT_TRUE(rewriter.device_id_to_type_for_testing().empty());
328  EXPECT_EQ(EventRewriter::kDeviceUnknown,
329            rewriter.DeviceAddedForTesting(0, "PC Keyboard"));
330  EXPECT_EQ(1U, rewriter.device_id_to_type_for_testing().size());
331  EXPECT_EQ(EventRewriter::kDeviceAppleKeyboard,
332            rewriter.DeviceAddedForTesting(1, "Apple Keyboard"));
333  EXPECT_EQ(2U, rewriter.device_id_to_type_for_testing().size());
334  // Try to reuse the first ID.
335  EXPECT_EQ(EventRewriter::kDeviceAppleKeyboard,
336            rewriter.DeviceAddedForTesting(0, "Apple Keyboard"));
337  EXPECT_EQ(2U, rewriter.device_id_to_type_for_testing().size());
338}
339
340#if defined(OS_CHROMEOS)
341TEST_F(EventRewriterTest, TestRewriteCommandToControl) {
342  // First, test with a PC keyboard.
343  TestingPrefServiceSyncable prefs;
344  EventRewriter rewriter;
345  rewriter.DeviceAddedForTesting(0, "PC Keyboard");
346  rewriter.set_last_device_id_for_testing(0);
347  rewriter.set_pref_service_for_testing(&prefs);
348
349  // XK_a, Alt modifier.
350  EXPECT_EQ(GetExpectedResultAsString(ui::VKEY_A,
351                                      ui::EF_ALT_DOWN,
352                                      ui::ET_KEY_PRESSED,
353                                      keycode_a_,
354                                      Mod1Mask,
355                                      KeyPress),
356            GetRewrittenEventAsString(&rewriter,
357                                      ui::VKEY_A,
358                                      ui::EF_ALT_DOWN,
359                                      ui::ET_KEY_PRESSED,
360                                      keycode_a_,
361                                      Mod1Mask));
362
363  // XK_a, Win modifier.
364  EXPECT_EQ(GetExpectedResultAsString(ui::VKEY_A,
365                                      0,
366                                      ui::ET_KEY_PRESSED,
367                                      keycode_a_,
368                                      Mod4Mask,
369                                      KeyPress),
370            GetRewrittenEventAsString(&rewriter,
371                                      ui::VKEY_A,
372                                      0,
373                                      ui::ET_KEY_PRESSED,
374                                      keycode_a_,
375                                      Mod4Mask));
376
377  // XK_a, Alt+Win modifier.
378  EXPECT_EQ(GetExpectedResultAsString(ui::VKEY_A,
379                                      ui::EF_ALT_DOWN,
380                                      ui::ET_KEY_PRESSED,
381                                      keycode_a_,
382                                      Mod1Mask | Mod4Mask,
383                                      KeyPress),
384            GetRewrittenEventAsString(&rewriter,
385                                      ui::VKEY_A,
386                                      ui::EF_ALT_DOWN,
387                                      ui::ET_KEY_PRESSED,
388                                      keycode_a_,
389                                      Mod1Mask | Mod4Mask));
390
391  // XK_Super_L (left Windows key), Alt modifier.
392  EXPECT_EQ(GetExpectedResultAsString(ui::VKEY_LWIN,
393                                      ui::EF_ALT_DOWN,
394                                      ui::ET_KEY_PRESSED,
395                                      keycode_super_l_,
396                                      Mod1Mask,
397                                      KeyPress),
398            GetRewrittenEventAsString(&rewriter,
399                                      ui::VKEY_LWIN,
400                                      ui::EF_ALT_DOWN,
401                                      ui::ET_KEY_PRESSED,
402                                      keycode_super_l_,
403                                      Mod1Mask));
404
405  // XK_Super_R (right Windows key), Alt modifier.
406  EXPECT_EQ(GetExpectedResultAsString(ui::VKEY_RWIN,
407                                      ui::EF_ALT_DOWN,
408                                      ui::ET_KEY_PRESSED,
409                                      keycode_super_r_,
410                                      Mod1Mask,
411                                      KeyPress),
412            GetRewrittenEventAsString(&rewriter,
413                                      ui::VKEY_RWIN,
414                                      ui::EF_ALT_DOWN,
415                                      ui::ET_KEY_PRESSED,
416                                      keycode_super_r_,
417                                      Mod1Mask));
418
419  // An Apple keyboard reusing the ID, zero.
420  rewriter.DeviceAddedForTesting(0, "Apple Keyboard");
421  rewriter.set_last_device_id_for_testing(0);
422
423  // XK_a, Alt modifier.
424  EXPECT_EQ(GetExpectedResultAsString(ui::VKEY_A,
425                                      ui::EF_ALT_DOWN,
426                                      ui::ET_KEY_PRESSED,
427                                      keycode_a_,
428                                      Mod1Mask,
429                                      KeyPress),
430            GetRewrittenEventAsString(&rewriter,
431                                      ui::VKEY_A,
432                                      ui::EF_ALT_DOWN,
433                                      ui::ET_KEY_PRESSED,
434                                      keycode_a_,
435                                      Mod1Mask));
436
437  // XK_a, Win modifier.
438  EXPECT_EQ(GetExpectedResultAsString(ui::VKEY_A,
439                                      ui::EF_CONTROL_DOWN,
440                                      ui::ET_KEY_PRESSED,
441                                      keycode_a_,
442                                      ControlMask,
443                                      KeyPress),
444            GetRewrittenEventAsString(&rewriter,
445                                      ui::VKEY_A,
446                                      0,
447                                      ui::ET_KEY_PRESSED,
448                                      keycode_a_,
449                                      Mod4Mask));
450
451  // XK_a, Alt+Win modifier.
452  EXPECT_EQ(GetExpectedResultAsString(ui::VKEY_A,
453                                      ui::EF_ALT_DOWN | ui::EF_CONTROL_DOWN,
454                                      ui::ET_KEY_PRESSED,
455                                      keycode_a_,
456                                      Mod1Mask | ControlMask,
457                                      KeyPress),
458            GetRewrittenEventAsString(&rewriter,
459                                      ui::VKEY_A,
460                                      ui::EF_ALT_DOWN,
461                                      ui::ET_KEY_PRESSED,
462                                      keycode_a_,
463                                      Mod1Mask | Mod4Mask));
464
465  // XK_Super_L (left Windows key), Alt modifier.
466  EXPECT_EQ(GetExpectedResultAsString(ui::VKEY_CONTROL,
467                                      ui::EF_CONTROL_DOWN | ui::EF_ALT_DOWN,
468                                      ui::ET_KEY_PRESSED,
469                                      keycode_control_l_,
470                                      Mod1Mask,
471                                      KeyPress),
472            GetRewrittenEventAsString(&rewriter,
473                                      ui::VKEY_LWIN,
474                                      ui::EF_ALT_DOWN,
475                                      ui::ET_KEY_PRESSED,
476                                      keycode_super_l_,
477                                      Mod1Mask));
478
479  // XK_Super_R (right Windows key), Alt modifier.
480  EXPECT_EQ(GetExpectedResultAsString(ui::VKEY_CONTROL,
481                                      ui::EF_CONTROL_DOWN | ui::EF_ALT_DOWN,
482                                      ui::ET_KEY_PRESSED,
483                                      keycode_control_r_,
484                                      Mod1Mask,
485                                      KeyPress),
486            GetRewrittenEventAsString(&rewriter,
487                                      ui::VKEY_RWIN,
488                                      ui::EF_ALT_DOWN,
489                                      ui::ET_KEY_PRESSED,
490                                      keycode_super_r_,
491                                      Mod1Mask));
492}
493
494// For crbug.com/133896.
495TEST_F(EventRewriterTest, TestRewriteCommandToControlWithControlRemapped) {
496  // Remap Control to Alt.
497  TestingPrefServiceSyncable prefs;
498  chromeos::Preferences::RegisterProfilePrefs(prefs.registry());
499  IntegerPrefMember control;
500  control.Init(prefs::kLanguageRemapControlKeyTo, &prefs);
501  control.SetValue(chromeos::input_method::kAltKey);
502
503  EventRewriter rewriter;
504  rewriter.set_pref_service_for_testing(&prefs);
505  rewriter.DeviceAddedForTesting(0, "PC Keyboard");
506  rewriter.set_last_device_id_for_testing(0);
507
508  // XK_Control_L (left Control key) should be remapped to Alt.
509  EXPECT_EQ(GetExpectedResultAsString(ui::VKEY_MENU,
510                                      ui::EF_ALT_DOWN,
511                                      ui::ET_KEY_PRESSED,
512                                      keycode_alt_l_,
513                                      0U,
514                                      KeyPress),
515            GetRewrittenEventAsString(&rewriter,
516                                      ui::VKEY_CONTROL,
517                                      0,
518                                      ui::ET_KEY_PRESSED,
519                                      keycode_control_l_,
520                                      0U));
521
522  // An Apple keyboard reusing the ID, zero.
523  rewriter.DeviceAddedForTesting(0, "Apple Keyboard");
524  rewriter.set_last_device_id_for_testing(0);
525
526  // XK_Super_L (left Command key) with  Alt modifier. The remapped Command key
527  // should never be re-remapped to Alt.
528  EXPECT_EQ(GetExpectedResultAsString(ui::VKEY_CONTROL,
529                                      ui::EF_CONTROL_DOWN | ui::EF_ALT_DOWN,
530                                      ui::ET_KEY_PRESSED,
531                                      keycode_control_l_,
532                                      Mod1Mask,
533                                      KeyPress),
534            GetRewrittenEventAsString(&rewriter,
535                                      ui::VKEY_LWIN,
536                                      ui::EF_ALT_DOWN,
537                                      ui::ET_KEY_PRESSED,
538                                      keycode_super_l_,
539                                      Mod1Mask));
540
541  // XK_Super_R (right Command key) with  Alt modifier. The remapped Command key
542  // should never be re-remapped to Alt.
543  EXPECT_EQ(GetExpectedResultAsString(ui::VKEY_CONTROL,
544                                      ui::EF_CONTROL_DOWN | ui::EF_ALT_DOWN,
545                                      ui::ET_KEY_PRESSED,
546                                      keycode_control_r_,
547                                      Mod1Mask,
548                                      KeyPress),
549            GetRewrittenEventAsString(&rewriter,
550                                      ui::VKEY_RWIN,
551                                      ui::EF_ALT_DOWN,
552                                      ui::ET_KEY_PRESSED,
553                                      keycode_super_r_,
554                                      Mod1Mask));
555}
556
557void EventRewriterTest::TestRewriteNumPadKeys() {
558  TestingPrefServiceSyncable prefs;
559  EventRewriter rewriter;
560  rewriter.set_pref_service_for_testing(&prefs);
561
562  // XK_KP_Insert (= NumPad 0 without Num Lock), no modifier.
563  EXPECT_EQ(GetExpectedResultAsString(ui::VKEY_NUMPAD0,
564                                      0,
565                                      ui::ET_KEY_PRESSED,
566                                      keycode_num_pad_0_,
567                                      Mod2Mask,  // Num Lock
568                                      KeyPress),
569            GetRewrittenEventAsString(&rewriter,
570                                      ui::VKEY_INSERT,
571                                      0,
572                                      ui::ET_KEY_PRESSED,
573                                      keycode_num_pad_insert_,
574                                      0));
575
576  // XK_KP_Insert (= NumPad 0 without Num Lock), Alt modifier.
577  EXPECT_EQ(GetExpectedResultAsString(ui::VKEY_NUMPAD0,
578                                      ui::EF_ALT_DOWN,
579                                      ui::ET_KEY_PRESSED,
580                                      keycode_num_pad_0_,
581                                      Mod1Mask | Mod2Mask,
582                                      KeyPress),
583            GetRewrittenEventAsString(&rewriter,
584                                      ui::VKEY_INSERT,
585                                      ui::EF_ALT_DOWN,
586                                      ui::ET_KEY_PRESSED,
587                                      keycode_num_pad_insert_,
588                                      Mod1Mask));
589
590  // XK_KP_Delete (= NumPad . without Num Lock), Alt modifier.
591  EXPECT_EQ(GetExpectedResultAsString(ui::VKEY_DECIMAL,
592                                      ui::EF_ALT_DOWN,
593                                      ui::ET_KEY_PRESSED,
594                                      keycode_num_pad_decimal_,
595                                      Mod1Mask | Mod2Mask,
596                                      KeyPress),
597            GetRewrittenEventAsString(&rewriter,
598                                      ui::VKEY_DELETE,
599                                      ui::EF_ALT_DOWN,
600                                      ui::ET_KEY_PRESSED,
601                                      keycode_num_pad_delete_,
602                                      Mod1Mask));
603
604  // XK_KP_End (= NumPad 1 without Num Lock), Alt modifier.
605  EXPECT_EQ(GetExpectedResultAsString(ui::VKEY_NUMPAD1,
606                                      ui::EF_ALT_DOWN,
607                                      ui::ET_KEY_PRESSED,
608                                      keycode_num_pad_1_,
609                                      Mod1Mask | Mod2Mask,
610                                      KeyPress),
611            GetRewrittenEventAsString(&rewriter,
612                                      ui::VKEY_END,
613                                      ui::EF_ALT_DOWN,
614                                      ui::ET_KEY_PRESSED,
615                                      keycode_num_pad_end_,
616                                      Mod1Mask));
617
618  // XK_KP_Down (= NumPad 2 without Num Lock), Alt modifier.
619  EXPECT_EQ(GetExpectedResultAsString(ui::VKEY_NUMPAD2,
620                                      ui::EF_ALT_DOWN,
621                                      ui::ET_KEY_PRESSED,
622                                      keycode_num_pad_2_,
623                                      Mod1Mask | Mod2Mask,
624                                      KeyPress),
625            GetRewrittenEventAsString(&rewriter,
626                                      ui::VKEY_DOWN,
627                                      ui::EF_ALT_DOWN,
628                                      ui::ET_KEY_PRESSED,
629                                      keycode_num_pad_down_,
630                                      Mod1Mask));
631
632  // XK_KP_Next (= NumPad 3 without Num Lock), Alt modifier.
633  EXPECT_EQ(GetExpectedResultAsString(ui::VKEY_NUMPAD3,
634                                      ui::EF_ALT_DOWN,
635                                      ui::ET_KEY_PRESSED,
636                                      keycode_num_pad_3_,
637                                      Mod1Mask | Mod2Mask,
638                                      KeyPress),
639            GetRewrittenEventAsString(&rewriter,
640                                      ui::VKEY_NEXT,
641                                      ui::EF_ALT_DOWN,
642                                      ui::ET_KEY_PRESSED,
643                                      keycode_num_pad_next_,
644                                      Mod1Mask));
645
646  // XK_KP_Left (= NumPad 4 without Num Lock), Alt modifier.
647  EXPECT_EQ(GetExpectedResultAsString(ui::VKEY_NUMPAD4,
648                                      ui::EF_ALT_DOWN,
649                                      ui::ET_KEY_PRESSED,
650                                      keycode_num_pad_4_,
651                                      Mod1Mask | Mod2Mask,
652                                      KeyPress),
653            GetRewrittenEventAsString(&rewriter,
654                                      ui::VKEY_LEFT,
655                                      ui::EF_ALT_DOWN,
656                                      ui::ET_KEY_PRESSED,
657                                      keycode_num_pad_left_,
658                                      Mod1Mask));
659
660  // XK_KP_Begin (= NumPad 5 without Num Lock), Alt modifier.
661  EXPECT_EQ(GetExpectedResultAsString(ui::VKEY_NUMPAD5,
662                                      ui::EF_ALT_DOWN,
663                                      ui::ET_KEY_PRESSED,
664                                      keycode_num_pad_5_,
665                                      Mod1Mask | Mod2Mask,
666                                      KeyPress),
667            GetRewrittenEventAsString(&rewriter,
668                                      ui::VKEY_CLEAR,
669                                      ui::EF_ALT_DOWN,
670                                      ui::ET_KEY_PRESSED,
671                                      keycode_num_pad_begin_,
672                                      Mod1Mask));
673
674  // XK_KP_Right (= NumPad 6 without Num Lock), Alt modifier.
675  EXPECT_EQ(GetExpectedResultAsString(ui::VKEY_NUMPAD6,
676                                      ui::EF_ALT_DOWN,
677                                      ui::ET_KEY_PRESSED,
678                                      keycode_num_pad_6_,
679                                      Mod1Mask | Mod2Mask,
680                                      KeyPress),
681            GetRewrittenEventAsString(&rewriter,
682                                      ui::VKEY_RIGHT,
683                                      ui::EF_ALT_DOWN,
684                                      ui::ET_KEY_PRESSED,
685                                      keycode_num_pad_right_,
686                                      Mod1Mask));
687
688  // XK_KP_Home (= NumPad 7 without Num Lock), Alt modifier.
689  EXPECT_EQ(GetExpectedResultAsString(ui::VKEY_NUMPAD7,
690                                      ui::EF_ALT_DOWN,
691                                      ui::ET_KEY_PRESSED,
692                                      keycode_num_pad_7_,
693                                      Mod1Mask | Mod2Mask,
694                                      KeyPress),
695            GetRewrittenEventAsString(&rewriter,
696                                      ui::VKEY_HOME,
697                                      ui::EF_ALT_DOWN,
698                                      ui::ET_KEY_PRESSED,
699                                      keycode_num_pad_home_,
700                                      Mod1Mask));
701
702  // XK_KP_Up (= NumPad 8 without Num Lock), Alt modifier.
703  EXPECT_EQ(GetExpectedResultAsString(ui::VKEY_NUMPAD8,
704                                      ui::EF_ALT_DOWN,
705                                      ui::ET_KEY_PRESSED,
706                                      keycode_num_pad_8_,
707                                      Mod1Mask | Mod2Mask,
708                                      KeyPress),
709            GetRewrittenEventAsString(&rewriter,
710                                      ui::VKEY_UP,
711                                      ui::EF_ALT_DOWN,
712                                      ui::ET_KEY_PRESSED,
713                                      keycode_num_pad_up_,
714                                      Mod1Mask));
715
716  // XK_KP_Prior (= NumPad 9 without Num Lock), Alt modifier.
717  EXPECT_EQ(GetExpectedResultAsString(ui::VKEY_NUMPAD9,
718                                      ui::EF_ALT_DOWN,
719                                      ui::ET_KEY_PRESSED,
720                                      keycode_num_pad_9_,
721                                      Mod1Mask | Mod2Mask,
722                                      KeyPress),
723            GetRewrittenEventAsString(&rewriter,
724                                      ui::VKEY_PRIOR,
725                                      ui::EF_ALT_DOWN,
726                                      ui::ET_KEY_PRESSED,
727                                      keycode_num_pad_prior_,
728                                      Mod1Mask));
729
730  // XK_KP_0 (= NumPad 0 with Num Lock), Num Lock modifier.
731  EXPECT_EQ(GetExpectedResultAsString(ui::VKEY_NUMPAD0,
732                                      0,
733                                      ui::ET_KEY_PRESSED,
734                                      keycode_num_pad_0_,
735                                      Mod2Mask,
736                                      KeyPress),
737            GetRewrittenEventAsString(&rewriter,
738                                      ui::VKEY_NUMPAD0,
739                                      0,
740                                      ui::ET_KEY_PRESSED,
741                                      keycode_num_pad_0_,
742                                      Mod2Mask));
743
744  // XK_KP_DECIMAL (= NumPad . with Num Lock), Num Lock modifier.
745  EXPECT_EQ(GetExpectedResultAsString(ui::VKEY_DECIMAL,
746                                      0,
747                                      ui::ET_KEY_PRESSED,
748                                      keycode_num_pad_decimal_,
749                                      Mod2Mask,
750                                      KeyPress),
751            GetRewrittenEventAsString(&rewriter,
752                                      ui::VKEY_DECIMAL,
753                                      0,
754                                      ui::ET_KEY_PRESSED,
755                                      keycode_num_pad_decimal_,
756                                      Mod2Mask));
757
758  // XK_KP_1 (= NumPad 1 with Num Lock), Num Lock modifier.
759  EXPECT_EQ(GetExpectedResultAsString(ui::VKEY_NUMPAD1,
760                                      0,
761                                      ui::ET_KEY_PRESSED,
762                                      keycode_num_pad_1_,
763                                      Mod2Mask,
764                                      KeyPress),
765            GetRewrittenEventAsString(&rewriter,
766                                      ui::VKEY_NUMPAD1,
767                                      0,
768                                      ui::ET_KEY_PRESSED,
769                                      keycode_num_pad_1_,
770                                      Mod2Mask));
771
772  // XK_KP_2 (= NumPad 2 with Num Lock), Num Lock modifier.
773  EXPECT_EQ(GetExpectedResultAsString(ui::VKEY_NUMPAD2,
774                                      0,
775                                      ui::ET_KEY_PRESSED,
776                                      keycode_num_pad_2_,
777                                      Mod2Mask,
778                                      KeyPress),
779            GetRewrittenEventAsString(&rewriter,
780                                      ui::VKEY_NUMPAD2,
781                                      0,
782                                      ui::ET_KEY_PRESSED,
783                                      keycode_num_pad_2_,
784                                      Mod2Mask));
785
786  // XK_KP_3 (= NumPad 3 with Num Lock), Num Lock modifier.
787  EXPECT_EQ(GetExpectedResultAsString(ui::VKEY_NUMPAD3,
788                                      0,
789                                      ui::ET_KEY_PRESSED,
790                                      keycode_num_pad_3_,
791                                      Mod2Mask,
792                                      KeyPress),
793            GetRewrittenEventAsString(&rewriter,
794                                      ui::VKEY_NUMPAD3,
795                                      0,
796                                      ui::ET_KEY_PRESSED,
797                                      keycode_num_pad_3_,
798                                      Mod2Mask));
799
800  // XK_KP_4 (= NumPad 4 with Num Lock), Num Lock modifier.
801  EXPECT_EQ(GetExpectedResultAsString(ui::VKEY_NUMPAD4,
802                                      0,
803                                      ui::ET_KEY_PRESSED,
804                                      keycode_num_pad_4_,
805                                      Mod2Mask,
806                                      KeyPress),
807            GetRewrittenEventAsString(&rewriter,
808                                      ui::VKEY_NUMPAD4,
809                                      0,
810                                      ui::ET_KEY_PRESSED,
811                                      keycode_num_pad_4_,
812                                      Mod2Mask));
813
814  // XK_KP_5 (= NumPad 5 with Num Lock), Num Lock modifier.
815  EXPECT_EQ(GetExpectedResultAsString(ui::VKEY_NUMPAD5,
816                                      0,
817                                      ui::ET_KEY_PRESSED,
818                                      keycode_num_pad_5_,
819                                      Mod2Mask,
820                                      KeyPress),
821            GetRewrittenEventAsString(&rewriter,
822                                      ui::VKEY_NUMPAD5,
823                                      0,
824                                      ui::ET_KEY_PRESSED,
825                                      keycode_num_pad_5_,
826                                      Mod2Mask));
827
828  // XK_KP_6 (= NumPad 6 with Num Lock), Num Lock modifier.
829  EXPECT_EQ(GetExpectedResultAsString(ui::VKEY_NUMPAD6,
830                                      0,
831                                      ui::ET_KEY_PRESSED,
832                                      keycode_num_pad_6_,
833                                      Mod2Mask,
834                                      KeyPress),
835            GetRewrittenEventAsString(&rewriter,
836                                      ui::VKEY_NUMPAD6,
837                                      0,
838                                      ui::ET_KEY_PRESSED,
839                                      keycode_num_pad_6_,
840                                      Mod2Mask));
841
842  // XK_KP_7 (= NumPad 7 with Num Lock), Num Lock modifier.
843  EXPECT_EQ(GetExpectedResultAsString(ui::VKEY_NUMPAD7,
844                                      0,
845                                      ui::ET_KEY_PRESSED,
846                                      keycode_num_pad_7_,
847                                      Mod2Mask,
848                                      KeyPress),
849            GetRewrittenEventAsString(&rewriter,
850                                      ui::VKEY_NUMPAD7,
851                                      0,
852                                      ui::ET_KEY_PRESSED,
853                                      keycode_num_pad_7_,
854                                      Mod2Mask));
855
856  // XK_KP_8 (= NumPad 8 with Num Lock), Num Lock modifier.
857  EXPECT_EQ(GetExpectedResultAsString(ui::VKEY_NUMPAD8,
858                                      0,
859                                      ui::ET_KEY_PRESSED,
860                                      keycode_num_pad_8_,
861                                      Mod2Mask,
862                                      KeyPress),
863            GetRewrittenEventAsString(&rewriter,
864                                      ui::VKEY_NUMPAD8,
865                                      0,
866                                      ui::ET_KEY_PRESSED,
867                                      keycode_num_pad_8_,
868                                      Mod2Mask));
869
870  // XK_KP_9 (= NumPad 9 with Num Lock), Num Lock modifier.
871  EXPECT_EQ(GetExpectedResultAsString(ui::VKEY_NUMPAD9,
872                                      0,
873                                      ui::ET_KEY_PRESSED,
874                                      keycode_num_pad_9_,
875                                      Mod2Mask,
876                                      KeyPress),
877            GetRewrittenEventAsString(&rewriter,
878                                      ui::VKEY_NUMPAD9,
879                                      0,
880                                      ui::ET_KEY_PRESSED,
881                                      keycode_num_pad_9_,
882                                      Mod2Mask));
883}
884
885TEST_F(EventRewriterTest, TestRewriteNumPadKeys) {
886  TestRewriteNumPadKeys();
887}
888
889TEST_F(EventRewriterTest, TestRewriteNumPadKeysWithDiamondKeyFlag) {
890  // Make sure the num lock works correctly even when Diamond key exists.
891  const CommandLine original_cl(*CommandLine::ForCurrentProcess());
892  CommandLine::ForCurrentProcess()->AppendSwitchASCII(
893      chromeos::switches::kHasChromeOSDiamondKey, "");
894
895  TestRewriteNumPadKeys();
896  *CommandLine::ForCurrentProcess() = original_cl;
897}
898
899// Tests if the rewriter can handle a Command + Num Pad event.
900void EventRewriterTest::TestRewriteNumPadKeysOnAppleKeyboard() {
901  TestingPrefServiceSyncable prefs;
902  EventRewriter rewriter;
903  rewriter.DeviceAddedForTesting(0, "Apple Keyboard");
904  rewriter.set_last_device_id_for_testing(0);
905  rewriter.set_pref_service_for_testing(&prefs);
906
907  // XK_KP_End (= NumPad 1 without Num Lock), Win modifier.
908  // The result should be "Num Pad 1 with Control + Num Lock modifiers".
909  EXPECT_EQ(GetExpectedResultAsString(ui::VKEY_NUMPAD1,
910                                      ui::EF_CONTROL_DOWN,
911                                      ui::ET_KEY_PRESSED,
912                                      keycode_num_pad_1_,
913                                      ControlMask | Mod2Mask,
914                                      KeyPress),
915            GetRewrittenEventAsString(&rewriter,
916                                      ui::VKEY_END,
917                                      0,
918                                      ui::ET_KEY_PRESSED,
919                                      keycode_num_pad_end_,
920                                      Mod4Mask));
921
922  // XK_KP_1 (= NumPad 1 without Num Lock), Win modifier.
923  // The result should also be "Num Pad 1 with Control + Num Lock modifiers".
924  EXPECT_EQ(GetExpectedResultAsString(ui::VKEY_NUMPAD1,
925                                      ui::EF_CONTROL_DOWN,
926                                      ui::ET_KEY_PRESSED,
927                                      keycode_num_pad_1_,
928                                      ControlMask | Mod2Mask,
929                                      KeyPress),
930            GetRewrittenEventAsString(&rewriter,
931                                      ui::VKEY_NUMPAD1,
932                                      0,
933                                      ui::ET_KEY_PRESSED,
934                                      keycode_num_pad_end_,
935                                      Mod4Mask));
936}
937
938TEST_F(EventRewriterTest, TestRewriteNumPadKeysOnAppleKeyboard) {
939  TestRewriteNumPadKeysOnAppleKeyboard();
940}
941
942TEST_F(EventRewriterTest,
943       TestRewriteNumPadKeysOnAppleKeyboardWithDiamondKeyFlag) {
944  // Makes sure the num lock works correctly even when Diamond key exists.
945  const CommandLine original_cl(*CommandLine::ForCurrentProcess());
946  CommandLine::ForCurrentProcess()->AppendSwitchASCII(
947      chromeos::switches::kHasChromeOSDiamondKey, "");
948
949  TestRewriteNumPadKeysOnAppleKeyboard();
950  *CommandLine::ForCurrentProcess() = original_cl;
951}
952
953TEST_F(EventRewriterTest, TestRewriteModifiersNoRemap) {
954  TestingPrefServiceSyncable prefs;
955  EventRewriter rewriter;
956  rewriter.set_pref_service_for_testing(&prefs);
957
958  // Press Search. Confirm the event is not rewritten.
959  EXPECT_EQ(GetExpectedResultAsString(ui::VKEY_LWIN,
960                                      0,
961                                      ui::ET_KEY_PRESSED,
962                                      keycode_super_l_,
963                                      0U,
964                                      KeyPress),
965            GetRewrittenEventAsString(&rewriter,
966                                      ui::VKEY_LWIN,
967                                      0,
968                                      ui::ET_KEY_PRESSED,
969                                      keycode_super_l_,
970                                      0U));
971
972  // Press left Control. Confirm the event is not rewritten.
973  EXPECT_EQ(GetExpectedResultAsString(ui::VKEY_CONTROL,
974                                      ui::EF_CONTROL_DOWN,
975                                      ui::ET_KEY_PRESSED,
976                                      keycode_control_l_,
977                                      0U,
978                                      KeyPress),
979            GetRewrittenEventAsString(&rewriter,
980                                      ui::VKEY_CONTROL,
981                                      0,
982                                      ui::ET_KEY_PRESSED,
983                                      keycode_control_l_,
984                                      0U));
985
986  // Press right Control. Confirm the event is not rewritten.
987  EXPECT_EQ(GetExpectedResultAsString(ui::VKEY_CONTROL,
988                                      ui::EF_CONTROL_DOWN,
989                                      ui::ET_KEY_PRESSED,
990                                      keycode_control_r_,
991                                      0U,
992                                      KeyPress),
993            GetRewrittenEventAsString(&rewriter,
994                                      ui::VKEY_CONTROL,
995                                      0,
996                                      ui::ET_KEY_PRESSED,
997                                      keycode_control_r_,
998                                      0U));
999
1000  // Press left Alt. Confirm the event is not rewritten.
1001  EXPECT_EQ(GetExpectedResultAsString(ui::VKEY_MENU,
1002                                      ui::EF_ALT_DOWN,
1003                                      ui::ET_KEY_PRESSED,
1004                                      keycode_alt_l_,
1005                                      0,
1006                                      KeyPress),
1007            GetRewrittenEventAsString(&rewriter,
1008                                      ui::VKEY_MENU,
1009                                      0,
1010                                      ui::ET_KEY_PRESSED,
1011                                      keycode_alt_l_,
1012                                      0U));
1013
1014  // Press right Alt. Confirm the event is not rewritten.
1015  EXPECT_EQ(GetExpectedResultAsString(ui::VKEY_MENU,
1016                                      ui::EF_ALT_DOWN,
1017                                      ui::ET_KEY_PRESSED,
1018                                      keycode_alt_r_,
1019                                      0,
1020                                      KeyPress),
1021            GetRewrittenEventAsString(&rewriter,
1022                                      ui::VKEY_MENU,
1023                                      0,
1024                                      ui::ET_KEY_PRESSED,
1025                                      keycode_alt_r_,
1026                                      0U));
1027
1028  // Test KeyRelease event, just in case.
1029  // Release Search. Confirm the release event is not rewritten.
1030  EXPECT_EQ(GetExpectedResultAsString(ui::VKEY_LWIN,
1031                                      0,
1032                                      ui::ET_KEY_RELEASED,
1033                                      keycode_super_l_,
1034                                      Mod4Mask,
1035                                      KeyRelease),
1036            GetRewrittenEventAsString(&rewriter,
1037                                      ui::VKEY_LWIN,
1038                                      0,
1039                                      ui::ET_KEY_RELEASED,
1040                                      keycode_super_l_,
1041                                      Mod4Mask));
1042}
1043
1044TEST_F(EventRewriterTest, TestRewriteModifiersNoRemapMultipleKeys) {
1045  TestingPrefServiceSyncable prefs;
1046  EventRewriter rewriter;
1047  rewriter.set_pref_service_for_testing(&prefs);
1048
1049  // Press left Alt with Shift. Confirm the event is not rewritten.
1050  EXPECT_EQ(GetExpectedResultAsString(ui::VKEY_MENU,
1051                                      ui::EF_SHIFT_DOWN | ui::EF_ALT_DOWN,
1052                                      ui::ET_KEY_PRESSED,
1053                                      keycode_meta_l_,
1054                                      ShiftMask,
1055                                      KeyPress),
1056            GetRewrittenEventAsString(&rewriter,
1057                                      ui::VKEY_MENU,
1058                                      ui::EF_SHIFT_DOWN,
1059                                      ui::ET_KEY_PRESSED,
1060                                      keycode_meta_l_,
1061                                      ShiftMask));
1062
1063  // Press right Alt with Shift. Confirm the event is not rewritten.
1064  EXPECT_EQ(GetExpectedResultAsString(ui::VKEY_MENU,
1065                                      ui::EF_SHIFT_DOWN | ui::EF_ALT_DOWN,
1066                                      ui::ET_KEY_PRESSED,
1067                                      keycode_meta_r_,
1068                                      ShiftMask,
1069                                      KeyPress),
1070            GetRewrittenEventAsString(&rewriter,
1071                                      ui::VKEY_MENU,
1072                                      ui::EF_SHIFT_DOWN,
1073                                      ui::ET_KEY_PRESSED,
1074                                      keycode_meta_r_,
1075                                      ShiftMask));
1076
1077  // Press Search with Caps Lock mask. Confirm the event is not rewritten.
1078  EXPECT_EQ(GetExpectedResultAsString(ui::VKEY_LWIN,
1079                                      ui::EF_CAPS_LOCK_DOWN,
1080                                      ui::ET_KEY_PRESSED,
1081                                      keycode_super_l_,
1082                                      LockMask,
1083                                      KeyPress),
1084            GetRewrittenEventAsString(&rewriter,
1085                                      ui::VKEY_LWIN,
1086                                      ui::EF_CAPS_LOCK_DOWN,
1087                                      ui::ET_KEY_PRESSED,
1088                                      keycode_super_l_,
1089                                      LockMask));
1090
1091  // Release Search with Caps Lock mask. Confirm the event is not rewritten.
1092  EXPECT_EQ(GetExpectedResultAsString(ui::VKEY_LWIN,
1093                                      ui::EF_CAPS_LOCK_DOWN,
1094                                      ui::ET_KEY_RELEASED,
1095                                      keycode_super_l_,
1096                                      LockMask | Mod4Mask,
1097                                      KeyRelease),
1098            GetRewrittenEventAsString(&rewriter,
1099                                      ui::VKEY_LWIN,
1100                                      ui::EF_CAPS_LOCK_DOWN,
1101                                      ui::ET_KEY_RELEASED,
1102                                      keycode_super_l_,
1103                                      LockMask | Mod4Mask));
1104
1105  // Press Shift+Ctrl+Alt+Search+A. Confirm the event is not rewritten.
1106  EXPECT_EQ(GetExpectedResultAsString(ui::VKEY_B,
1107                                      ui::EF_SHIFT_DOWN |
1108                                      ui::EF_CONTROL_DOWN | ui::EF_ALT_DOWN,
1109                                      ui::ET_KEY_PRESSED,
1110                                      keycode_b_,
1111                                      ShiftMask | ControlMask | Mod1Mask |
1112                                      Mod4Mask,
1113                                      KeyPress),
1114            GetRewrittenEventAsString(&rewriter,
1115                                      ui::VKEY_B,
1116                                      ui::EF_SHIFT_DOWN |
1117                                      ui::EF_CONTROL_DOWN | ui::EF_ALT_DOWN,
1118                                      ui::ET_KEY_PRESSED,
1119                                      keycode_b_,
1120                                      ShiftMask | ControlMask | Mod1Mask |
1121                                      Mod4Mask));
1122}
1123
1124TEST_F(EventRewriterTest, TestRewriteModifiersDisableSome) {
1125  // Disable Search and Control keys.
1126  TestingPrefServiceSyncable prefs;
1127  chromeos::Preferences::RegisterProfilePrefs(prefs.registry());
1128  IntegerPrefMember search;
1129  search.Init(prefs::kLanguageRemapSearchKeyTo, &prefs);
1130  search.SetValue(chromeos::input_method::kVoidKey);
1131  IntegerPrefMember control;
1132  control.Init(prefs::kLanguageRemapControlKeyTo, &prefs);
1133  control.SetValue(chromeos::input_method::kVoidKey);
1134
1135  EventRewriter rewriter;
1136  rewriter.set_pref_service_for_testing(&prefs);
1137
1138  // Press left Alt with Shift. This key press shouldn't be affected by the
1139  // pref. Confirm the event is not rewritten.
1140  EXPECT_EQ(GetExpectedResultAsString(ui::VKEY_MENU,
1141                                      ui::EF_SHIFT_DOWN | ui::EF_ALT_DOWN,
1142                                      ui::ET_KEY_PRESSED,
1143                                      keycode_meta_l_,
1144                                      ShiftMask,
1145                                      KeyPress),
1146            GetRewrittenEventAsString(&rewriter,
1147                                      ui::VKEY_MENU,
1148                                      ui::EF_SHIFT_DOWN,
1149                                      ui::ET_KEY_PRESSED,
1150                                      keycode_meta_l_,
1151                                      ShiftMask));
1152
1153  // Press Search. Confirm the event is now VKEY_UNKNOWN + XK_VoidSymbol.
1154  EXPECT_EQ(GetExpectedResultAsString(ui::VKEY_UNKNOWN,
1155                                      0,
1156                                      ui::ET_KEY_PRESSED,
1157                                      keycode_void_symbol_,
1158                                      0U,
1159                                      KeyPress),
1160            GetRewrittenEventAsString(&rewriter,
1161                                      ui::VKEY_LWIN,
1162                                      0,
1163                                      ui::ET_KEY_PRESSED,
1164                                      keycode_super_l_,
1165                                      0U));
1166
1167  // Press Control. Confirm the event is now VKEY_UNKNOWN + XK_VoidSymbol.
1168  EXPECT_EQ(GetExpectedResultAsString(ui::VKEY_UNKNOWN,
1169                                      0,
1170                                      ui::ET_KEY_PRESSED,
1171                                      keycode_void_symbol_,
1172                                      0U,
1173                                      KeyPress),
1174            GetRewrittenEventAsString(&rewriter,
1175                                      ui::VKEY_CONTROL,
1176                                      0,
1177                                      ui::ET_KEY_PRESSED,
1178                                      keycode_control_l_,
1179                                      0U));
1180
1181  // Press Control+Search. Confirm the event is now VKEY_UNKNOWN +
1182  // XK_VoidSymbol without any modifiers.
1183  EXPECT_EQ(GetExpectedResultAsString(ui::VKEY_UNKNOWN,
1184                                      0,
1185                                      ui::ET_KEY_PRESSED,
1186                                      keycode_void_symbol_,
1187                                      0U,
1188                                      KeyPress),
1189            GetRewrittenEventAsString(&rewriter,
1190                                      ui::VKEY_LWIN,
1191                                      ui::EF_CONTROL_DOWN,
1192                                      ui::ET_KEY_PRESSED,
1193                                      keycode_super_l_,
1194                                      ControlMask));
1195
1196  // Press Control+Search+a. Confirm the event is now VKEY_A without any
1197  // modifiers.
1198  EXPECT_EQ(GetExpectedResultAsString(ui::VKEY_A,
1199                                      0,
1200                                      ui::ET_KEY_PRESSED,
1201                                      keycode_a_,
1202                                      0U,
1203                                      KeyPress),
1204            GetRewrittenEventAsString(&rewriter,
1205                                      ui::VKEY_A,
1206                                      ui::EF_CONTROL_DOWN,
1207                                      ui::ET_KEY_PRESSED,
1208                                      keycode_a_,
1209                                      ControlMask | Mod4Mask));
1210
1211  // Press Control+Search+Alt+a. Confirm the event is now VKEY_A only with
1212  // the Alt modifier.
1213  EXPECT_EQ(GetExpectedResultAsString(ui::VKEY_A,
1214                                      ui::EF_ALT_DOWN,
1215                                      ui::ET_KEY_PRESSED,
1216                                      keycode_a_,
1217                                      Mod1Mask,
1218                                      KeyPress),
1219            GetRewrittenEventAsString(&rewriter,
1220                                      ui::VKEY_A,
1221                                      ui::EF_CONTROL_DOWN | ui::EF_ALT_DOWN,
1222                                      ui::ET_KEY_PRESSED,
1223                                      keycode_a_,
1224                                      ControlMask | Mod1Mask | Mod4Mask));
1225
1226  // Remap Alt to Control.
1227  IntegerPrefMember alt;
1228  alt.Init(prefs::kLanguageRemapAltKeyTo, &prefs);
1229  alt.SetValue(chromeos::input_method::kControlKey);
1230
1231  // Press left Alt. Confirm the event is now VKEY_CONTROL + XK_Control_L
1232  // even though the Control key itself is disabled.
1233  EXPECT_EQ(GetExpectedResultAsString(ui::VKEY_CONTROL,
1234                                      ui::EF_CONTROL_DOWN,
1235                                      ui::ET_KEY_PRESSED,
1236                                      keycode_control_l_,
1237                                      0U,
1238                                      KeyPress),
1239            GetRewrittenEventAsString(&rewriter,
1240                                      ui::VKEY_MENU,
1241                                      0,
1242                                      ui::ET_KEY_PRESSED,
1243                                      keycode_alt_l_,
1244                                      0U));
1245
1246  // Press Alt+a. Confirm the event is now Control+a even though the Control
1247  // key itself is disabled.
1248  EXPECT_EQ(GetExpectedResultAsString(ui::VKEY_A,
1249                                      ui::EF_CONTROL_DOWN,
1250                                      ui::ET_KEY_PRESSED,
1251                                      keycode_a_,
1252                                      ControlMask,
1253                                      KeyPress),
1254            GetRewrittenEventAsString(&rewriter,
1255                                      ui::VKEY_A,
1256                                      ui::EF_ALT_DOWN,
1257                                      ui::ET_KEY_PRESSED,
1258                                      keycode_a_,
1259                                      Mod1Mask));
1260}
1261
1262TEST_F(EventRewriterTest, TestRewriteModifiersRemapToControl) {
1263  // Remap Search to Control.
1264  TestingPrefServiceSyncable prefs;
1265  chromeos::Preferences::RegisterProfilePrefs(prefs.registry());
1266  IntegerPrefMember search;
1267  search.Init(prefs::kLanguageRemapSearchKeyTo, &prefs);
1268  search.SetValue(chromeos::input_method::kControlKey);
1269
1270  EventRewriter rewriter;
1271  rewriter.set_pref_service_for_testing(&prefs);
1272
1273  // Press Search. Confirm the event is now VKEY_CONTROL + XK_Control_L.
1274  EXPECT_EQ(GetExpectedResultAsString(ui::VKEY_CONTROL,
1275                                      ui::EF_CONTROL_DOWN,
1276                                      ui::ET_KEY_PRESSED,
1277                                      keycode_control_l_,
1278                                      0U,
1279                                      KeyPress),
1280            GetRewrittenEventAsString(&rewriter,
1281                                      ui::VKEY_LWIN,
1282                                      0,
1283                                      ui::ET_KEY_PRESSED,
1284                                      keycode_super_l_,
1285                                      0U));
1286
1287  // Remap Alt to Control too.
1288  IntegerPrefMember alt;
1289  alt.Init(prefs::kLanguageRemapAltKeyTo, &prefs);
1290  alt.SetValue(chromeos::input_method::kControlKey);
1291
1292  // Press left Alt. Confirm the event is now VKEY_CONTROL + XK_Control_L.
1293  EXPECT_EQ(GetExpectedResultAsString(ui::VKEY_CONTROL,
1294                                      ui::EF_CONTROL_DOWN,
1295                                      ui::ET_KEY_PRESSED,
1296                                      keycode_control_l_,
1297                                      0U,
1298                                      KeyPress),
1299            GetRewrittenEventAsString(&rewriter,
1300                                      ui::VKEY_MENU,
1301                                      0,
1302                                      ui::ET_KEY_PRESSED,
1303                                      keycode_alt_l_,
1304                                      0U));
1305
1306  // Press right Alt. Confirm the event is now VKEY_CONTROL + XK_Control_R.
1307  EXPECT_EQ(GetExpectedResultAsString(ui::VKEY_CONTROL,
1308                                      ui::EF_CONTROL_DOWN,
1309                                      ui::ET_KEY_PRESSED,
1310                                      keycode_control_r_,
1311                                      0U,
1312                                      KeyPress),
1313            GetRewrittenEventAsString(&rewriter,
1314                                      ui::VKEY_MENU,
1315                                      0,
1316                                      ui::ET_KEY_PRESSED,
1317                                      keycode_alt_r_,
1318                                      0U));
1319
1320  // Press Alt+Search. Confirm the event is now VKEY_CONTROL + XK_Control_L.
1321  EXPECT_EQ(GetExpectedResultAsString(ui::VKEY_CONTROL,
1322                                      ui::EF_CONTROL_DOWN,
1323                                      ui::ET_KEY_PRESSED,
1324                                      keycode_control_l_,
1325                                      ControlMask,
1326                                      KeyPress),
1327            GetRewrittenEventAsString(&rewriter,
1328                                      ui::VKEY_LWIN,
1329                                      ui::EF_ALT_DOWN,
1330                                      ui::ET_KEY_PRESSED,
1331                                      keycode_super_l_,
1332                                      Mod1Mask));
1333
1334  // Press Control+Alt+Search. Confirm the event is now VKEY_CONTROL +
1335  // XK_Control_L.
1336  EXPECT_EQ(GetExpectedResultAsString(ui::VKEY_CONTROL,
1337                                      ui::EF_CONTROL_DOWN,
1338                                      ui::ET_KEY_PRESSED,
1339                                      keycode_control_l_,
1340                                      ControlMask,
1341                                      KeyPress),
1342            GetRewrittenEventAsString(&rewriter,
1343                                      ui::VKEY_LWIN,
1344                                      ui::EF_CONTROL_DOWN | ui::EF_ALT_DOWN,
1345                                      ui::ET_KEY_PRESSED,
1346                                      keycode_super_l_,
1347                                      ControlMask | Mod1Mask));
1348
1349  // Press Shift+Control+Alt+Search. Confirm the event is now Control with
1350  // Shift and Control modifiers.
1351  EXPECT_EQ(GetExpectedResultAsString(ui::VKEY_CONTROL,
1352                                      ui::EF_SHIFT_DOWN | ui::EF_CONTROL_DOWN,
1353                                      ui::ET_KEY_PRESSED,
1354                                      keycode_control_l_,
1355                                      ShiftMask | ControlMask,
1356                                      KeyPress),
1357            GetRewrittenEventAsString(&rewriter,
1358                                      ui::VKEY_LWIN,
1359                                      ui::EF_SHIFT_DOWN |
1360                                      ui::EF_CONTROL_DOWN | ui::EF_ALT_DOWN,
1361                                      ui::ET_KEY_PRESSED,
1362                                      keycode_super_l_,
1363                                      ShiftMask | ControlMask | Mod1Mask));
1364
1365  // Press Shift+Control+Alt+Search+B. Confirm the event is now B with Shift
1366  // and Control modifiers.
1367  EXPECT_EQ(GetExpectedResultAsString(ui::VKEY_B,
1368                                      ui::EF_SHIFT_DOWN | ui::EF_CONTROL_DOWN,
1369                                      ui::ET_KEY_PRESSED,
1370                                      keycode_b_,
1371                                      ShiftMask | ControlMask,
1372                                      KeyPress),
1373            GetRewrittenEventAsString(&rewriter,
1374                                      ui::VKEY_B,
1375                                      ui::EF_SHIFT_DOWN |
1376                                      ui::EF_CONTROL_DOWN | ui::EF_ALT_DOWN,
1377                                      ui::ET_KEY_PRESSED,
1378                                      keycode_b_,
1379                                      ShiftMask | ControlMask | Mod1Mask));
1380}
1381
1382TEST_F(EventRewriterTest, TestRewriteModifiersRemapMany) {
1383  // Remap Search to Alt.
1384  TestingPrefServiceSyncable prefs;
1385  chromeos::Preferences::RegisterProfilePrefs(prefs.registry());
1386  IntegerPrefMember search;
1387  search.Init(prefs::kLanguageRemapSearchKeyTo, &prefs);
1388  search.SetValue(chromeos::input_method::kAltKey);
1389
1390  EventRewriter rewriter;
1391  rewriter.set_pref_service_for_testing(&prefs);
1392
1393  // Press Search. Confirm the event is now VKEY_MENU + XK_Alt_L.
1394  EXPECT_EQ(GetExpectedResultAsString(ui::VKEY_MENU,
1395                                      ui::EF_ALT_DOWN,
1396                                      ui::ET_KEY_PRESSED,
1397                                      keycode_alt_l_,
1398                                      0U,
1399                                      KeyPress),
1400            GetRewrittenEventAsString(&rewriter,
1401                                      ui::VKEY_LWIN,
1402                                      0,
1403                                      ui::ET_KEY_PRESSED,
1404                                      keycode_super_l_,
1405                                      0U));
1406
1407  // Remap Alt to Control.
1408  IntegerPrefMember alt;
1409  alt.Init(prefs::kLanguageRemapAltKeyTo, &prefs);
1410  alt.SetValue(chromeos::input_method::kControlKey);
1411
1412  // Press left Alt. Confirm the event is now VKEY_CONTROL + XK_Control_L.
1413  EXPECT_EQ(GetExpectedResultAsString(ui::VKEY_CONTROL,
1414                                      ui::EF_CONTROL_DOWN,
1415                                      ui::ET_KEY_PRESSED,
1416                                      keycode_control_l_,
1417                                      0U,
1418                                      KeyPress),
1419            GetRewrittenEventAsString(&rewriter,
1420                                      ui::VKEY_MENU,
1421                                      0,
1422                                      ui::ET_KEY_PRESSED,
1423                                      keycode_alt_l_,
1424                                      0U));
1425
1426  // Remap Control to Search.
1427  IntegerPrefMember control;
1428  control.Init(prefs::kLanguageRemapControlKeyTo, &prefs);
1429  control.SetValue(chromeos::input_method::kSearchKey);
1430
1431  // Press left Control. Confirm the event is now VKEY_LWIN.
1432  EXPECT_EQ(GetExpectedResultAsString(ui::VKEY_LWIN,
1433                                      0,
1434                                      ui::ET_KEY_PRESSED,
1435                                      keycode_super_l_,
1436                                      0U,
1437                                      KeyPress),
1438            GetRewrittenEventAsString(&rewriter,
1439                                      ui::VKEY_CONTROL,
1440                                      0,
1441                                      ui::ET_KEY_PRESSED,
1442                                      keycode_control_l_,
1443                                      0U));
1444
1445  // Then, press all of the three, Control+Alt+Search.
1446  EXPECT_EQ(GetExpectedResultAsString(ui::VKEY_MENU,
1447                                      ui::EF_CONTROL_DOWN | ui::EF_ALT_DOWN,
1448                                      ui::ET_KEY_PRESSED,
1449                                      keycode_alt_l_,
1450                                      ControlMask | Mod4Mask,
1451                                      KeyPress),
1452            GetRewrittenEventAsString(&rewriter,
1453                                      ui::VKEY_LWIN,
1454                                      ui::EF_CONTROL_DOWN | ui::EF_ALT_DOWN,
1455                                      ui::ET_KEY_PRESSED,
1456                                      keycode_super_l_,
1457                                      ControlMask | Mod1Mask));
1458
1459  // Press Shift+Control+Alt+Search.
1460  EXPECT_EQ(GetExpectedResultAsString(ui::VKEY_MENU,
1461                                      (ui::EF_SHIFT_DOWN | ui::EF_CONTROL_DOWN |
1462                                       ui::EF_ALT_DOWN),
1463                                      ui::ET_KEY_PRESSED,
1464                                      keycode_alt_l_,
1465                                      ShiftMask | ControlMask | Mod4Mask,
1466                                      KeyPress),
1467            GetRewrittenEventAsString(&rewriter,
1468                                      ui::VKEY_LWIN,
1469                                      ui::EF_SHIFT_DOWN |
1470                                      ui::EF_CONTROL_DOWN | ui::EF_ALT_DOWN,
1471                                      ui::ET_KEY_PRESSED,
1472                                      keycode_super_l_,
1473                                      ShiftMask | ControlMask | Mod1Mask));
1474
1475  // Press Shift+Control+Alt+Search+B
1476  EXPECT_EQ(GetExpectedResultAsString(ui::VKEY_B,
1477                                      ui::EF_SHIFT_DOWN |
1478                                      ui::EF_CONTROL_DOWN | ui::EF_ALT_DOWN,
1479                                      ui::ET_KEY_PRESSED,
1480                                      keycode_b_,
1481                                      ShiftMask | ControlMask | Mod1Mask |
1482                                      Mod4Mask,
1483                                      KeyPress),
1484            GetRewrittenEventAsString(&rewriter,
1485                                      ui::VKEY_B,
1486                                      ui::EF_SHIFT_DOWN |
1487                                      ui::EF_CONTROL_DOWN | ui::EF_ALT_DOWN,
1488                                      ui::ET_KEY_PRESSED,
1489                                      keycode_b_,
1490                                      ShiftMask | ControlMask | Mod1Mask |
1491                                      Mod4Mask));
1492}
1493
1494TEST_F(EventRewriterTest, TestRewriteModifiersRemapToCapsLock) {
1495  // Remap Search to Caps Lock.
1496  TestingPrefServiceSyncable prefs;
1497  chromeos::Preferences::RegisterProfilePrefs(prefs.registry());
1498  IntegerPrefMember search;
1499  search.Init(prefs::kLanguageRemapSearchKeyTo, &prefs);
1500  search.SetValue(chromeos::input_method::kCapsLockKey);
1501
1502  chromeos::input_method::MockXKeyboard xkeyboard;
1503  EventRewriter rewriter;
1504  rewriter.set_pref_service_for_testing(&prefs);
1505  rewriter.set_xkeyboard_for_testing(&xkeyboard);
1506  EXPECT_FALSE(xkeyboard.caps_lock_is_enabled_);
1507
1508  // Press Search.
1509  EXPECT_EQ(GetExpectedResultAsString(ui::VKEY_CAPITAL,
1510                                      ui::EF_CAPS_LOCK_DOWN,
1511                                      ui::ET_KEY_PRESSED,
1512                                      keycode_caps_lock_,
1513                                      0U,
1514                                      KeyPress),
1515            GetRewrittenEventAsString(&rewriter,
1516                                      ui::VKEY_LWIN,
1517                                      0,
1518                                      ui::ET_KEY_PRESSED,
1519                                      keycode_super_l_,
1520                                      0U));
1521  // Confirm that the Caps Lock status is changed.
1522  EXPECT_TRUE(xkeyboard.caps_lock_is_enabled_);
1523
1524  // Release Search.
1525  EXPECT_EQ(GetExpectedResultAsString(ui::VKEY_CAPITAL,
1526                                      ui::EF_NONE,
1527                                      ui::ET_KEY_RELEASED,
1528                                      keycode_caps_lock_,
1529                                      LockMask,
1530                                      KeyRelease),
1531            GetRewrittenEventAsString(&rewriter,
1532                                      ui::VKEY_LWIN,
1533                                      ui::EF_CAPS_LOCK_DOWN,
1534                                      ui::ET_KEY_RELEASED,
1535                                      keycode_super_l_,
1536                                      Mod4Mask | LockMask));
1537  // Confirm that the Caps Lock status is not changed.
1538  EXPECT_TRUE(xkeyboard.caps_lock_is_enabled_);
1539
1540  // Press Search.
1541  EXPECT_EQ(GetExpectedResultAsString(ui::VKEY_CAPITAL,
1542                                      ui::EF_CAPS_LOCK_DOWN,
1543                                      ui::ET_KEY_PRESSED,
1544                                      keycode_caps_lock_,
1545                                      LockMask,
1546                                      KeyPress),
1547            GetRewrittenEventAsString(&rewriter,
1548                                      ui::VKEY_LWIN,
1549                                      ui::EF_CAPS_LOCK_DOWN,
1550                                      ui::ET_KEY_PRESSED,
1551                                      keycode_super_l_,
1552                                      LockMask));
1553  // Confirm that the Caps Lock status is changed.
1554  EXPECT_FALSE(xkeyboard.caps_lock_is_enabled_);
1555
1556  // Release Search.
1557  EXPECT_EQ(GetExpectedResultAsString(ui::VKEY_CAPITAL,
1558                                      ui::EF_NONE,
1559                                      ui::ET_KEY_RELEASED,
1560                                      keycode_caps_lock_,
1561                                      LockMask,
1562                                      KeyRelease),
1563            GetRewrittenEventAsString(&rewriter,
1564                                      ui::VKEY_LWIN,
1565                                      ui::EF_CAPS_LOCK_DOWN,
1566                                      ui::ET_KEY_RELEASED,
1567                                      keycode_super_l_,
1568                                      Mod4Mask | LockMask));
1569  // Confirm that the Caps Lock status is not changed.
1570  EXPECT_FALSE(xkeyboard.caps_lock_is_enabled_);
1571
1572  // Press Caps Lock (on an external keyboard).
1573  EXPECT_EQ(GetExpectedResultAsString(ui::VKEY_CAPITAL,
1574                                      ui::EF_CAPS_LOCK_DOWN,
1575                                      ui::ET_KEY_PRESSED,
1576                                      keycode_caps_lock_,
1577                                      0U,
1578                                      KeyPress),
1579            GetRewrittenEventAsString(&rewriter,
1580                                      ui::VKEY_CAPITAL,
1581                                      ui::EF_NONE,
1582                                      ui::ET_KEY_PRESSED,
1583                                      keycode_caps_lock_,
1584                                      0U));
1585
1586  // Confirm that calling RewriteForTesting() does not change the state of
1587  // |xkeyboard|. In this case, X Window system itself should change the
1588  // Caps Lock state, not ash::EventRewriter.
1589  EXPECT_FALSE(xkeyboard.caps_lock_is_enabled_);
1590
1591  // Release Caps Lock (on an external keyboard).
1592  EXPECT_EQ(GetExpectedResultAsString(ui::VKEY_CAPITAL,
1593                                      ui::EF_NONE,
1594                                      ui::ET_KEY_RELEASED,
1595                                      keycode_caps_lock_,
1596                                      LockMask,
1597                                      KeyRelease),
1598            GetRewrittenEventAsString(&rewriter,
1599                                      ui::VKEY_CAPITAL,
1600                                      ui::EF_CAPS_LOCK_DOWN,
1601                                      ui::ET_KEY_RELEASED,
1602                                      keycode_caps_lock_,
1603                                      LockMask));
1604  EXPECT_FALSE(xkeyboard.caps_lock_is_enabled_);
1605}
1606
1607TEST_F(EventRewriterTest, DISABLED_TestRewriteCapsLock) {
1608  // It seems that the X server running on build servers is too old and does not
1609  // support F16 (i.e. 'XKeysymToKeycode(display_, XF86XK_Launch7)' call).
1610  // TODO(yusukes): Reenable the test once build servers are upgraded.
1611
1612  TestingPrefServiceSyncable prefs;
1613  chromeos::Preferences::RegisterProfilePrefs(prefs.registry());
1614
1615  chromeos::input_method::MockXKeyboard xkeyboard;
1616  EventRewriter rewriter;
1617  rewriter.set_pref_service_for_testing(&prefs);
1618  rewriter.set_xkeyboard_for_testing(&xkeyboard);
1619  EXPECT_FALSE(xkeyboard.caps_lock_is_enabled_);
1620
1621  // On Chrome OS, CapsLock is mapped to F16 with Mod3Mask.
1622  EXPECT_EQ(GetExpectedResultAsString(ui::VKEY_CAPITAL,
1623                                      ui::EF_CAPS_LOCK_DOWN,
1624                                      ui::ET_KEY_PRESSED,
1625                                      keycode_caps_lock_,
1626                                      0U,
1627                                      KeyPress),
1628            GetRewrittenEventAsString(&rewriter,
1629                                      ui::VKEY_F16,
1630                                      0,
1631                                      ui::ET_KEY_PRESSED,
1632                                      keycode_launch7_,
1633                                      0U));
1634  EXPECT_TRUE(xkeyboard.caps_lock_is_enabled_);
1635}
1636
1637TEST_F(EventRewriterTest, DISABLED_TestRewriteDiamondKey) {
1638  // TODO(yusukes): Reenable the test once build servers are upgraded.
1639
1640  TestingPrefServiceSyncable prefs;
1641  chromeos::Preferences::RegisterProfilePrefs(prefs.registry());
1642
1643  chromeos::input_method::MockXKeyboard xkeyboard;
1644  EventRewriter rewriter;
1645  rewriter.set_pref_service_for_testing(&prefs);
1646  rewriter.set_xkeyboard_for_testing(&xkeyboard);
1647
1648  // F15 should work as Ctrl when --has-chromeos-diamond-key is not specified.
1649  EXPECT_EQ(GetExpectedResultAsString(ui::VKEY_CONTROL,
1650                                      ui::EF_CONTROL_DOWN,
1651                                      ui::ET_KEY_PRESSED,
1652                                      keycode_control_l_,
1653                                      0U,
1654                                      KeyPress),
1655            GetRewrittenEventAsString(&rewriter,
1656                                      ui::VKEY_F15,
1657                                      0,
1658                                      ui::ET_KEY_PRESSED,
1659                                      keycode_launch6_,
1660                                      0U));
1661
1662  // However, Mod2Mask should not be rewritten to CtrlMask when
1663  // --has-chromeos-diamond-key is not specified.
1664  EXPECT_EQ(GetExpectedResultAsString(ui::VKEY_A,
1665                                      0,
1666                                      ui::ET_KEY_PRESSED,
1667                                      keycode_a_,
1668                                      Mod2Mask,
1669                                      KeyPress),
1670            GetRewrittenEventAsString(&rewriter,
1671                                      ui::VKEY_A,
1672                                      0,
1673                                      ui::ET_KEY_PRESSED,
1674                                      keycode_a_,
1675                                      Mod2Mask));
1676}
1677
1678TEST_F(EventRewriterTest, DISABLED_TestRewriteDiamondKeyWithFlag) {
1679  // TODO(yusukes): Reenable the test once build servers are upgraded.
1680
1681  const CommandLine original_cl(*CommandLine::ForCurrentProcess());
1682  CommandLine::ForCurrentProcess()->AppendSwitchASCII(
1683      chromeos::switches::kHasChromeOSDiamondKey, "");
1684
1685  TestingPrefServiceSyncable prefs;
1686  chromeos::Preferences::RegisterProfilePrefs(prefs.registry());
1687
1688  chromeos::input_method::MockXKeyboard xkeyboard;
1689  EventRewriter rewriter;
1690  rewriter.set_pref_service_for_testing(&prefs);
1691  rewriter.set_xkeyboard_for_testing(&xkeyboard);
1692
1693  // By default, F15 should work as Control.
1694  EXPECT_EQ(GetExpectedResultAsString(ui::VKEY_CONTROL,
1695                                      ui::EF_CONTROL_DOWN,
1696                                      ui::ET_KEY_PRESSED,
1697                                      keycode_control_l_,
1698                                      0U,
1699                                      KeyPress),
1700            GetRewrittenEventAsString(&rewriter,
1701                                      ui::VKEY_F15,
1702                                      0,
1703                                      ui::ET_KEY_PRESSED,
1704                                      keycode_launch6_,
1705                                      0U));
1706
1707  IntegerPrefMember diamond;
1708  diamond.Init(prefs::kLanguageRemapDiamondKeyTo, &prefs);
1709  diamond.SetValue(chromeos::input_method::kVoidKey);
1710
1711  EXPECT_EQ(GetExpectedResultAsString(ui::VKEY_UNKNOWN,
1712                                      0,
1713                                      ui::ET_KEY_PRESSED,
1714                                      keycode_void_symbol_,
1715                                      0U,
1716                                      KeyPress),
1717            GetRewrittenEventAsString(&rewriter,
1718                                      ui::VKEY_F15,
1719                                      0,
1720                                      ui::ET_KEY_PRESSED,
1721                                      keycode_launch6_,
1722                                      0U));
1723
1724  diamond.SetValue(chromeos::input_method::kControlKey);
1725
1726  EXPECT_EQ(GetExpectedResultAsString(ui::VKEY_CONTROL,
1727                                      ui::EF_CONTROL_DOWN,
1728                                      ui::ET_KEY_PRESSED,
1729                                      keycode_control_l_,
1730                                      0U,
1731                                      KeyPress),
1732            GetRewrittenEventAsString(&rewriter,
1733                                      ui::VKEY_F15,
1734                                      0,
1735                                      ui::ET_KEY_PRESSED,
1736                                      keycode_launch6_,
1737                                      0U));
1738
1739  diamond.SetValue(chromeos::input_method::kAltKey);
1740
1741  EXPECT_EQ(GetExpectedResultAsString(ui::VKEY_MENU,
1742                                      ui::EF_ALT_DOWN,
1743                                      ui::ET_KEY_PRESSED,
1744                                      keycode_alt_l_,
1745                                      0,
1746                                      KeyPress),
1747            GetRewrittenEventAsString(&rewriter,
1748                                      ui::VKEY_F15,
1749                                      0,
1750                                      ui::ET_KEY_PRESSED,
1751                                      keycode_launch6_,
1752                                      0U));
1753
1754  diamond.SetValue(chromeos::input_method::kCapsLockKey);
1755
1756  EXPECT_EQ(GetExpectedResultAsString(ui::VKEY_CAPITAL,
1757                                      ui::EF_CAPS_LOCK_DOWN,
1758                                      ui::ET_KEY_PRESSED,
1759                                      keycode_caps_lock_,
1760                                      0U,
1761                                      KeyPress),
1762            GetRewrittenEventAsString(&rewriter,
1763                                      ui::VKEY_F15,
1764                                      0,
1765                                      ui::ET_KEY_PRESSED,
1766                                      keycode_launch6_,
1767                                      0U));
1768
1769  *CommandLine::ForCurrentProcess() = original_cl;
1770}
1771
1772TEST_F(EventRewriterTest, TestRewriteCapsLockToControl) {
1773  TestingPrefServiceSyncable prefs;
1774  chromeos::Preferences::RegisterProfilePrefs(prefs.registry());
1775  IntegerPrefMember control;
1776  control.Init(prefs::kLanguageRemapCapsLockKeyTo, &prefs);
1777  control.SetValue(chromeos::input_method::kControlKey);
1778
1779  EventRewriter rewriter;
1780  rewriter.set_pref_service_for_testing(&prefs);
1781
1782  // Press CapsLock+a. Confirm that Mod3Mask is rewritten to ControlMask.
1783  // On Chrome OS, CapsLock works as a Mod3 modifier.
1784  EXPECT_EQ(GetExpectedResultAsString(ui::VKEY_A,
1785                                      ui::EF_CONTROL_DOWN,
1786                                      ui::ET_KEY_PRESSED,
1787                                      keycode_a_,
1788                                      ControlMask,
1789                                      KeyPress),
1790            GetRewrittenEventAsString(&rewriter,
1791                                      ui::VKEY_A,
1792                                      0,
1793                                      ui::ET_KEY_PRESSED,
1794                                      keycode_a_,
1795                                      Mod3Mask));
1796
1797  // Press Control+CapsLock+a. Confirm that Mod3Mask is rewritten to ControlMask
1798  EXPECT_EQ(GetExpectedResultAsString(ui::VKEY_A,
1799                                      ui::EF_CONTROL_DOWN,
1800                                      ui::ET_KEY_PRESSED,
1801                                      keycode_a_,
1802                                      ControlMask,
1803                                      KeyPress),
1804            GetRewrittenEventAsString(&rewriter,
1805                                      ui::VKEY_A,
1806                                      ui::EF_CONTROL_DOWN,
1807                                      ui::ET_KEY_PRESSED,
1808                                      keycode_a_,
1809                                      Mod3Mask | ControlMask));
1810
1811  // Press Alt+CapsLock+a. Confirm that Mod3Mask is rewritten to ControlMask.
1812  EXPECT_EQ(GetExpectedResultAsString(ui::VKEY_A,
1813                                      ui::EF_ALT_DOWN | ui::EF_CONTROL_DOWN,
1814                                      ui::ET_KEY_PRESSED,
1815                                      keycode_a_,
1816                                      Mod1Mask | ControlMask,
1817                                      KeyPress),
1818            GetRewrittenEventAsString(&rewriter,
1819                                      ui::VKEY_A,
1820                                      ui::EF_ALT_DOWN,
1821                                      ui::ET_KEY_PRESSED,
1822                                      keycode_a_,
1823                                      Mod1Mask | Mod3Mask));
1824}
1825
1826TEST_F(EventRewriterTest, TestRewriteCapsLockMod3InUse) {
1827  // Remap CapsLock to Control.
1828  TestingPrefServiceSyncable prefs;
1829  chromeos::Preferences::RegisterProfilePrefs(prefs.registry());
1830  IntegerPrefMember control;
1831  control.Init(prefs::kLanguageRemapCapsLockKeyTo, &prefs);
1832  control.SetValue(chromeos::input_method::kControlKey);
1833
1834  EventRewriter rewriter;
1835  rewriter.set_pref_service_for_testing(&prefs);
1836  input_method_manager_mock_->SetCurrentInputMethodId("xkb:de:neo:ger");
1837
1838  // Press CapsLock+a. Confirm that Mod3Mask is NOT rewritten to ControlMask
1839  // when Mod3Mask is already in use by the current XKB layout.
1840  EXPECT_EQ(GetExpectedResultAsString(ui::VKEY_A,
1841                                      0,
1842                                      ui::ET_KEY_PRESSED,
1843                                      keycode_a_,
1844                                      Mod3Mask,
1845                                      KeyPress),
1846            GetRewrittenEventAsString(&rewriter,
1847                                      ui::VKEY_A,
1848                                      0,
1849                                      ui::ET_KEY_PRESSED,
1850                                      keycode_a_,
1851                                      Mod3Mask));
1852
1853  input_method_manager_mock_->SetCurrentInputMethodId("xkb:us::eng");
1854}
1855
1856TEST_F(EventRewriterTest, TestRewriteExtendedKeys) {
1857  TestingPrefServiceSyncable prefs;
1858  chromeos::Preferences::RegisterProfilePrefs(prefs.registry());
1859  EventRewriter rewriter;
1860  rewriter.set_pref_service_for_testing(&prefs);
1861
1862  struct {
1863    ui::KeyboardCode input;
1864    KeyCode input_native;
1865    unsigned int input_mods;
1866    unsigned int input_native_mods;
1867    ui::KeyboardCode output;
1868    KeyCode output_native;
1869    unsigned int output_mods;
1870    unsigned int output_native_mods;
1871  } chromeos_tests[] = {
1872    // Alt+Backspace -> Delete
1873    { ui::VKEY_BACK, keycode_backspace_,
1874      ui::EF_ALT_DOWN, Mod1Mask,
1875      ui::VKEY_DELETE, keycode_delete_,
1876      0, 0, },
1877    // Control+Alt+Backspace -> Control+Delete
1878    { ui::VKEY_BACK, keycode_backspace_,
1879      ui::EF_ALT_DOWN | ui::EF_CONTROL_DOWN, Mod1Mask | ControlMask,
1880      ui::VKEY_DELETE, keycode_delete_,
1881      ui::EF_CONTROL_DOWN, ControlMask, },
1882    // Search+Alt+Backspace -> Alt+Backspace
1883    { ui::VKEY_BACK, keycode_backspace_,
1884      ui::EF_ALT_DOWN, Mod1Mask | Mod4Mask,
1885      ui::VKEY_BACK, keycode_backspace_,
1886      ui::EF_ALT_DOWN, Mod1Mask, },
1887    // Search+Control+Alt+Backspace -> Control+Alt+Backspace
1888    { ui::VKEY_BACK, keycode_backspace_,
1889      ui::EF_ALT_DOWN | ui::EF_CONTROL_DOWN, Mod1Mask | ControlMask | Mod4Mask,
1890      ui::VKEY_BACK, keycode_backspace_,
1891      ui::EF_ALT_DOWN | ui::EF_CONTROL_DOWN, Mod1Mask | ControlMask, },
1892    // Alt+Up -> Prior
1893    { ui::VKEY_UP, keycode_up_,
1894      ui::EF_ALT_DOWN, Mod1Mask,
1895      ui::VKEY_PRIOR, keycode_prior_,
1896      0, 0, },
1897    // Alt+Down -> Next
1898    { ui::VKEY_DOWN, keycode_down_,
1899      ui::EF_ALT_DOWN, Mod1Mask,
1900      ui::VKEY_NEXT, keycode_next_,
1901      0, 0, },
1902    // Ctrl+Alt+Up -> Home
1903    { ui::VKEY_UP, keycode_up_,
1904      ui::EF_ALT_DOWN | ui::EF_CONTROL_DOWN, Mod1Mask | ControlMask,
1905      ui::VKEY_HOME, keycode_home_,
1906      0, 0, },
1907    // Ctrl+Alt+Down -> End
1908    { ui::VKEY_DOWN, keycode_down_,
1909      ui::EF_ALT_DOWN | ui::EF_CONTROL_DOWN, Mod1Mask | ControlMask,
1910      ui::VKEY_END, keycode_end_,
1911      0, 0, },
1912
1913    // Search+Alt+Up -> Alt+Up
1914    { ui::VKEY_UP, keycode_up_,
1915      ui::EF_ALT_DOWN, Mod1Mask | Mod4Mask,
1916      ui::VKEY_UP, keycode_up_,
1917      ui::EF_ALT_DOWN, Mod1Mask },
1918    // Search+Alt+Down -> Alt+Down
1919    { ui::VKEY_DOWN, keycode_down_,
1920      ui::EF_ALT_DOWN, Mod1Mask | Mod4Mask,
1921      ui::VKEY_DOWN, keycode_down_,
1922      ui::EF_ALT_DOWN, Mod1Mask },
1923    // Search+Ctrl+Alt+Up -> Search+Ctrl+Alt+Up
1924    { ui::VKEY_UP, keycode_up_,
1925      ui::EF_ALT_DOWN | ui::EF_CONTROL_DOWN, Mod1Mask | ControlMask | Mod4Mask,
1926      ui::VKEY_UP, keycode_up_,
1927      ui::EF_ALT_DOWN | ui::EF_CONTROL_DOWN, Mod1Mask | ControlMask },
1928    // Search+Ctrl+Alt+Down -> Ctrl+Alt+Down
1929    { ui::VKEY_DOWN, keycode_down_,
1930      ui::EF_ALT_DOWN | ui::EF_CONTROL_DOWN, Mod1Mask | ControlMask | Mod4Mask,
1931      ui::VKEY_DOWN, keycode_down_,
1932      ui::EF_ALT_DOWN | ui::EF_CONTROL_DOWN, Mod1Mask | ControlMask },
1933
1934    // Period -> Period
1935    { ui::VKEY_OEM_PERIOD, keycode_period_, 0, 0,
1936      ui::VKEY_OEM_PERIOD, keycode_period_, 0, 0 },
1937
1938    // Search+Backspace -> Delete
1939    { ui::VKEY_BACK, keycode_backspace_,
1940      0, Mod4Mask,
1941      ui::VKEY_DELETE, keycode_delete_,
1942      0, 0, },
1943    // Search+Up -> Prior
1944    { ui::VKEY_UP, keycode_up_,
1945      0, Mod4Mask,
1946      ui::VKEY_PRIOR, keycode_prior_,
1947      0, 0, },
1948    // Search+Down -> Next
1949    { ui::VKEY_DOWN, keycode_down_,
1950      0, Mod4Mask,
1951      ui::VKEY_NEXT, keycode_next_,
1952      0, 0, },
1953    // Search+Left -> Home
1954    { ui::VKEY_LEFT, keycode_left_,
1955      0, Mod4Mask,
1956      ui::VKEY_HOME, keycode_home_,
1957      0, 0, },
1958    // Control+Search+Left -> Home
1959    { ui::VKEY_LEFT, keycode_left_,
1960      ui::EF_CONTROL_DOWN, Mod4Mask | ControlMask,
1961      ui::VKEY_HOME, keycode_home_,
1962      ui::EF_CONTROL_DOWN, ControlMask },
1963    // Search+Right -> End
1964    { ui::VKEY_RIGHT, keycode_right_,
1965      0, Mod4Mask,
1966      ui::VKEY_END, keycode_end_,
1967      0, 0, },
1968    // Control+Search+Right -> End
1969    { ui::VKEY_RIGHT, keycode_right_,
1970      ui::EF_CONTROL_DOWN, Mod4Mask | ControlMask,
1971      ui::VKEY_END, keycode_end_,
1972      ui::EF_CONTROL_DOWN, ControlMask },
1973    // Search+Period -> Insert
1974    { ui::VKEY_OEM_PERIOD, keycode_period_, 0, Mod4Mask,
1975      ui::VKEY_INSERT, keycode_insert_, 0, 0 },
1976    // Control+Search+Period -> Control+Insert
1977    { ui::VKEY_OEM_PERIOD, keycode_period_,
1978      ui::EF_CONTROL_DOWN, Mod4Mask | ControlMask,
1979      ui::VKEY_INSERT, keycode_insert_,
1980      ui::EF_CONTROL_DOWN, ControlMask }
1981  };
1982
1983  for (size_t i = 0; i < ARRAYSIZE_UNSAFE(chromeos_tests); ++i) {
1984    EXPECT_EQ(GetExpectedResultAsString(chromeos_tests[i].output,
1985                                        chromeos_tests[i].output_mods,
1986                                        ui::ET_KEY_PRESSED,
1987                                        chromeos_tests[i].output_native,
1988                                        chromeos_tests[i].output_native_mods,
1989                                        KeyPress),
1990              GetRewrittenEventAsString(&rewriter,
1991                                        chromeos_tests[i].input,
1992                                        chromeos_tests[i].input_mods,
1993                                        ui::ET_KEY_PRESSED,
1994                                        chromeos_tests[i].input_native,
1995                                        chromeos_tests[i].input_native_mods));
1996  }
1997}
1998
1999TEST_F(EventRewriterTest, TestRewriteFunctionKeys) {
2000  TestingPrefServiceSyncable prefs;
2001  chromeos::Preferences::RegisterProfilePrefs(prefs.registry());
2002  EventRewriter rewriter;
2003  rewriter.set_pref_service_for_testing(&prefs);
2004
2005  struct {
2006    ui::KeyboardCode input;
2007    KeyCode input_native;
2008    unsigned int input_native_mods;
2009    unsigned int input_mods;
2010    ui::KeyboardCode output;
2011    KeyCode output_native;
2012    unsigned int output_native_mods;
2013    unsigned int output_mods;
2014  } tests[] = {
2015    // F1 -> Back
2016    { ui::VKEY_F1, keycode_f1_, 0, 0,
2017      ui::VKEY_BROWSER_BACK, keycode_browser_back_, 0, 0 },
2018    { ui::VKEY_F1, keycode_f1_, ControlMask, ui::EF_CONTROL_DOWN,
2019      ui::VKEY_BROWSER_BACK, keycode_browser_back_,
2020      ControlMask, ui::EF_CONTROL_DOWN },
2021    { ui::VKEY_F1, keycode_f1_, Mod1Mask, ui::EF_ALT_DOWN,
2022      ui::VKEY_BROWSER_BACK, keycode_browser_back_,
2023      Mod1Mask, ui::EF_ALT_DOWN },
2024    // F2 -> Forward
2025    { ui::VKEY_F2, keycode_f2_, 0, 0,
2026      ui::VKEY_BROWSER_FORWARD, keycode_browser_forward_, 0, 0 },
2027    { ui::VKEY_F2, keycode_f2_, ControlMask, ui::EF_CONTROL_DOWN,
2028      ui::VKEY_BROWSER_FORWARD, keycode_browser_forward_,
2029      ControlMask, ui::EF_CONTROL_DOWN },
2030    { ui::VKEY_F2, keycode_f2_, Mod1Mask, ui::EF_ALT_DOWN,
2031      ui::VKEY_BROWSER_FORWARD, keycode_browser_forward_,
2032      Mod1Mask, ui::EF_ALT_DOWN },
2033    // F3 -> Refresh
2034    { ui::VKEY_F3, keycode_f3_, 0, 0,
2035      ui::VKEY_BROWSER_REFRESH, keycode_browser_refresh_, 0, 0 },
2036    { ui::VKEY_F3, keycode_f3_, ControlMask, ui::EF_CONTROL_DOWN,
2037      ui::VKEY_BROWSER_REFRESH, keycode_browser_refresh_,
2038      ControlMask, ui::EF_CONTROL_DOWN },
2039    { ui::VKEY_F3, keycode_f3_, Mod1Mask, ui::EF_ALT_DOWN,
2040      ui::VKEY_BROWSER_REFRESH, keycode_browser_refresh_,
2041      Mod1Mask, ui::EF_ALT_DOWN },
2042    // F4 -> Launch App 2
2043    { ui::VKEY_F4, keycode_f4_, 0, 0,
2044      ui::VKEY_MEDIA_LAUNCH_APP2, keycode_media_launch_app2_, 0, 0 },
2045    { ui::VKEY_F4, keycode_f4_, ControlMask, ui::EF_CONTROL_DOWN,
2046      ui::VKEY_MEDIA_LAUNCH_APP2, keycode_media_launch_app2_,
2047      ControlMask, ui::EF_CONTROL_DOWN },
2048    { ui::VKEY_F4, keycode_f4_, Mod1Mask, ui::EF_ALT_DOWN,
2049      ui::VKEY_MEDIA_LAUNCH_APP2, keycode_media_launch_app2_,
2050      Mod1Mask, ui::EF_ALT_DOWN },
2051    // F5 -> Launch App 1
2052    { ui::VKEY_F5, keycode_f5_, 0, 0,
2053      ui::VKEY_MEDIA_LAUNCH_APP1, keycode_media_launch_app1_, 0, 0 },
2054    { ui::VKEY_F5, keycode_f5_, ControlMask, ui::EF_CONTROL_DOWN,
2055      ui::VKEY_MEDIA_LAUNCH_APP1, keycode_media_launch_app1_,
2056      ControlMask, ui::EF_CONTROL_DOWN },
2057    { ui::VKEY_F5, keycode_f5_, Mod1Mask, ui::EF_ALT_DOWN,
2058      ui::VKEY_MEDIA_LAUNCH_APP1, keycode_media_launch_app1_,
2059      Mod1Mask, ui::EF_ALT_DOWN },
2060    // F6 -> Brightness down
2061    { ui::VKEY_F6, keycode_f6_, 0, 0,
2062      ui::VKEY_BRIGHTNESS_DOWN, keycode_brightness_down_, 0, 0 },
2063    { ui::VKEY_F6, keycode_f6_, ControlMask, ui::EF_CONTROL_DOWN,
2064      ui::VKEY_BRIGHTNESS_DOWN, keycode_brightness_down_,
2065      ControlMask, ui::EF_CONTROL_DOWN },
2066    { ui::VKEY_F6, keycode_f6_, Mod1Mask, ui::EF_ALT_DOWN,
2067      ui::VKEY_BRIGHTNESS_DOWN, keycode_brightness_down_,
2068      Mod1Mask, ui::EF_ALT_DOWN },
2069    // F7 -> Brightness up
2070    { ui::VKEY_F7, keycode_f7_, 0, 0,
2071      ui::VKEY_BRIGHTNESS_UP, keycode_brightness_up_, 0, 0 },
2072    { ui::VKEY_F7, keycode_f7_, ControlMask, ui::EF_CONTROL_DOWN,
2073      ui::VKEY_BRIGHTNESS_UP, keycode_brightness_up_,
2074      ControlMask, ui::EF_CONTROL_DOWN },
2075    { ui::VKEY_F7, keycode_f7_, Mod1Mask, ui::EF_ALT_DOWN,
2076      ui::VKEY_BRIGHTNESS_UP, keycode_brightness_up_,
2077      Mod1Mask, ui::EF_ALT_DOWN },
2078    // F8 -> Volume Mute
2079    { ui::VKEY_F8, keycode_f8_, 0, 0,
2080      ui::VKEY_VOLUME_MUTE, keycode_volume_mute_, 0, 0 },
2081    { ui::VKEY_F8, keycode_f8_, ControlMask, ui::EF_CONTROL_DOWN,
2082      ui::VKEY_VOLUME_MUTE, keycode_volume_mute_,
2083      ControlMask, ui::EF_CONTROL_DOWN },
2084    { ui::VKEY_F8, keycode_f8_, Mod1Mask, ui::EF_ALT_DOWN,
2085      ui::VKEY_VOLUME_MUTE, keycode_volume_mute_,
2086      Mod1Mask, ui::EF_ALT_DOWN },
2087    // F9 -> Volume Down
2088    { ui::VKEY_F9, keycode_f9_, 0, 0,
2089      ui::VKEY_VOLUME_DOWN, keycode_volume_down_, 0, 0 },
2090    { ui::VKEY_F9, keycode_f9_, ControlMask, ui::EF_CONTROL_DOWN,
2091      ui::VKEY_VOLUME_DOWN, keycode_volume_down_,
2092      ControlMask, ui::EF_CONTROL_DOWN },
2093    { ui::VKEY_F9, keycode_f9_, Mod1Mask, ui::EF_ALT_DOWN,
2094      ui::VKEY_VOLUME_DOWN, keycode_volume_down_,
2095      Mod1Mask, ui::EF_ALT_DOWN },
2096    // F10 -> Volume Up
2097    { ui::VKEY_F10, keycode_f10_, 0, 0,
2098      ui::VKEY_VOLUME_UP, keycode_volume_up_, 0, 0 },
2099    { ui::VKEY_F10, keycode_f10_, ControlMask, ui::EF_CONTROL_DOWN,
2100      ui::VKEY_VOLUME_UP, keycode_volume_up_,
2101      ControlMask, ui::EF_CONTROL_DOWN },
2102    { ui::VKEY_F10, keycode_f10_, Mod1Mask, ui::EF_ALT_DOWN,
2103      ui::VKEY_VOLUME_UP, keycode_volume_up_,
2104      Mod1Mask, ui::EF_ALT_DOWN },
2105    // F11 -> F11
2106    { ui::VKEY_F11, keycode_f11_, 0, 0,
2107      ui::VKEY_F11, keycode_f11_, 0, 0 },
2108    { ui::VKEY_F11, keycode_f11_, ControlMask, ui::EF_CONTROL_DOWN,
2109      ui::VKEY_F11, keycode_f11_, ControlMask, ui::EF_CONTROL_DOWN },
2110    { ui::VKEY_F11, keycode_f11_, Mod1Mask, ui::EF_ALT_DOWN,
2111      ui::VKEY_F11, keycode_f11_, Mod1Mask, ui::EF_ALT_DOWN },
2112    // F12 -> F12
2113    { ui::VKEY_F12, keycode_f12_, 0, 0,
2114      ui::VKEY_F12, keycode_f12_, 0, 0 },
2115    { ui::VKEY_F12, keycode_f12_, ControlMask, ui::EF_CONTROL_DOWN,
2116      ui::VKEY_F12, keycode_f12_, ControlMask, ui::EF_CONTROL_DOWN },
2117    { ui::VKEY_F12, keycode_f12_, Mod1Mask, ui::EF_ALT_DOWN,
2118      ui::VKEY_F12, keycode_f12_, Mod1Mask, ui::EF_ALT_DOWN },
2119
2120    // The number row should not be rewritten without Search key.
2121    { ui::VKEY_1, keycode_1_, 0, 0,
2122      ui::VKEY_1, keycode_1_, 0, 0 },
2123    { ui::VKEY_2, keycode_2_, 0, 0,
2124      ui::VKEY_2, keycode_2_, 0, 0 },
2125    { ui::VKEY_3, keycode_3_, 0, 0,
2126      ui::VKEY_3, keycode_3_, 0, 0 },
2127    { ui::VKEY_4, keycode_4_, 0, 0,
2128      ui::VKEY_4, keycode_4_, 0, 0 },
2129    { ui::VKEY_5, keycode_5_, 0, 0,
2130      ui::VKEY_5, keycode_5_, 0, 0 },
2131    { ui::VKEY_6, keycode_6_, 0, 0,
2132      ui::VKEY_6, keycode_6_, 0, 0 },
2133    { ui::VKEY_7, keycode_7_, 0, 0,
2134      ui::VKEY_7, keycode_7_, 0, 0 },
2135    { ui::VKEY_8, keycode_8_, 0, 0,
2136      ui::VKEY_8, keycode_8_, 0, 0 },
2137    { ui::VKEY_9, keycode_9_, 0, 0,
2138      ui::VKEY_9, keycode_9_, 0, 0 },
2139    { ui::VKEY_0, keycode_0_, 0, 0,
2140      ui::VKEY_0, keycode_0_, 0, 0 },
2141    { ui::VKEY_OEM_MINUS, keycode_minus_, 0, 0,
2142      ui::VKEY_OEM_MINUS, keycode_minus_, 0, 0 },
2143    { ui::VKEY_OEM_PLUS, keycode_equal_, 0, 0,
2144      ui::VKEY_OEM_PLUS, keycode_equal_, 0, 0 },
2145
2146    // The number row should be rewritten as the F<number> row with Search key.
2147    { ui::VKEY_1, keycode_1_, Mod4Mask, 0,
2148      ui::VKEY_F1, keycode_f1_, 0, 0 },
2149    { ui::VKEY_2, keycode_2_, Mod4Mask, 0,
2150      ui::VKEY_F2, keycode_f2_, 0, 0 },
2151    { ui::VKEY_3, keycode_3_, Mod4Mask, 0,
2152      ui::VKEY_F3, keycode_f3_, 0, 0 },
2153    { ui::VKEY_4, keycode_4_, Mod4Mask, 0,
2154      ui::VKEY_F4, keycode_f4_, 0, 0 },
2155    { ui::VKEY_5, keycode_5_, Mod4Mask, 0,
2156      ui::VKEY_F5, keycode_f5_, 0, 0 },
2157    { ui::VKEY_6, keycode_6_, Mod4Mask, 0,
2158      ui::VKEY_F6, keycode_f6_, 0, 0 },
2159    { ui::VKEY_7, keycode_7_, Mod4Mask, 0,
2160      ui::VKEY_F7, keycode_f7_, 0, 0 },
2161    { ui::VKEY_8, keycode_8_, Mod4Mask, 0,
2162      ui::VKEY_F8, keycode_f8_, 0, 0 },
2163    { ui::VKEY_9, keycode_9_, Mod4Mask, 0,
2164      ui::VKEY_F9, keycode_f9_, 0, 0 },
2165    { ui::VKEY_0, keycode_0_, Mod4Mask, 0,
2166      ui::VKEY_F10, keycode_f10_, 0, 0 },
2167    { ui::VKEY_OEM_MINUS, keycode_minus_, Mod4Mask, 0,
2168      ui::VKEY_F11, keycode_f11_, 0, 0 },
2169    { ui::VKEY_OEM_PLUS, keycode_equal_, Mod4Mask, 0,
2170      ui::VKEY_F12, keycode_f12_, 0, 0 },
2171
2172    // The function keys should not be rewritten with Search key pressed.
2173    { ui::VKEY_F1, keycode_f1_, Mod4Mask, 0,
2174      ui::VKEY_F1, keycode_f1_, 0, 0 },
2175    { ui::VKEY_F2, keycode_f2_, Mod4Mask, 0,
2176      ui::VKEY_F2, keycode_f2_, 0, 0 },
2177    { ui::VKEY_F3, keycode_f3_, Mod4Mask, 0,
2178      ui::VKEY_F3, keycode_f3_, 0, 0 },
2179    { ui::VKEY_F4, keycode_f4_, Mod4Mask, 0,
2180      ui::VKEY_F4, keycode_f4_, 0, 0 },
2181    { ui::VKEY_F5, keycode_f5_, Mod4Mask, 0,
2182      ui::VKEY_F5, keycode_f5_, 0, 0 },
2183    { ui::VKEY_F6, keycode_f6_, Mod4Mask, 0,
2184      ui::VKEY_F6, keycode_f6_, 0, 0 },
2185    { ui::VKEY_F7, keycode_f7_, Mod4Mask, 0,
2186      ui::VKEY_F7, keycode_f7_, 0, 0 },
2187    { ui::VKEY_F8, keycode_f8_, Mod4Mask, 0,
2188      ui::VKEY_F8, keycode_f8_, 0, 0 },
2189    { ui::VKEY_F9, keycode_f9_, Mod4Mask, 0,
2190      ui::VKEY_F9, keycode_f9_, 0, 0 },
2191    { ui::VKEY_F10, keycode_f10_, Mod4Mask, 0,
2192      ui::VKEY_F10, keycode_f10_, 0, 0 },
2193    { ui::VKEY_F11, keycode_f11_, Mod4Mask, 0,
2194      ui::VKEY_F11, keycode_f11_, 0, 0 },
2195    { ui::VKEY_F12, keycode_f12_, Mod4Mask, 0,
2196      ui::VKEY_F12, keycode_f12_, 0, 0 },
2197  };
2198
2199  for (size_t i = 0; i < ARRAYSIZE_UNSAFE(tests); ++i) {
2200    EXPECT_EQ(GetExpectedResultAsString(tests[i].output,
2201                                        tests[i].output_mods,
2202                                        ui::ET_KEY_PRESSED,
2203                                        tests[i].output_native,
2204                                        tests[i].output_native_mods,
2205                                        KeyPress),
2206              GetRewrittenEventAsString(&rewriter,
2207                                        tests[i].input,
2208                                        tests[i].input_mods,
2209                                        ui::ET_KEY_PRESSED,
2210                                        tests[i].input_native,
2211                                        tests[i].input_native_mods));
2212  }
2213}
2214
2215TEST_F(EventRewriterTest, TestRewriteExtendedKeysWithSearchRemapped) {
2216  const CommandLine original_cl(*CommandLine::ForCurrentProcess());
2217
2218  // Remap Search to Control.
2219  TestingPrefServiceSyncable prefs;
2220  chromeos::Preferences::RegisterProfilePrefs(prefs.registry());
2221  IntegerPrefMember search;
2222  search.Init(prefs::kLanguageRemapSearchKeyTo, &prefs);
2223  search.SetValue(chromeos::input_method::kControlKey);
2224
2225  EventRewriter rewriter;
2226  rewriter.set_pref_service_for_testing(&prefs);
2227
2228  CommandLine::ForCurrentProcess()->AppendSwitchASCII(
2229      chromeos::switches::kHasChromeOSKeyboard, "");
2230
2231  // Alt+Search+Down -> End
2232  EXPECT_EQ(GetExpectedResultAsString(ui::VKEY_END,
2233                                      0,
2234                                      ui::ET_KEY_PRESSED,
2235                                      keycode_end_,
2236                                      0U,
2237                                      KeyPress),
2238            GetRewrittenEventAsString(&rewriter,
2239                                      ui::VKEY_DOWN,
2240                                      ui::EF_ALT_DOWN,
2241                                      ui::ET_KEY_PRESSED,
2242                                      keycode_down_,
2243                                      Mod1Mask | Mod4Mask));
2244
2245  // Shift+Alt+Search+Down -> Shift+End
2246  EXPECT_EQ(GetExpectedResultAsString(ui::VKEY_END,
2247                                      ui::EF_SHIFT_DOWN,
2248                                      ui::ET_KEY_PRESSED,
2249                                      keycode_end_,
2250                                      ShiftMask,
2251                                      KeyPress),
2252            GetRewrittenEventAsString(&rewriter,
2253                                      ui::VKEY_DOWN,
2254                                      ui::EF_SHIFT_DOWN | ui::EF_ALT_DOWN,
2255                                      ui::ET_KEY_PRESSED,
2256                                      keycode_down_,
2257                                      ShiftMask | Mod1Mask | Mod4Mask));
2258
2259  *CommandLine::ForCurrentProcess() = original_cl;
2260}
2261
2262TEST_F(EventRewriterTest, TestRewriteKeyEventSentByXSendEvent) {
2263  // Remap Control to Alt.
2264  TestingPrefServiceSyncable prefs;
2265  chromeos::Preferences::RegisterProfilePrefs(prefs.registry());
2266  IntegerPrefMember control;
2267  control.Init(prefs::kLanguageRemapControlKeyTo, &prefs);
2268  control.SetValue(chromeos::input_method::kAltKey);
2269
2270  EventRewriter rewriter;
2271  rewriter.set_pref_service_for_testing(&prefs);
2272
2273  // Send left control press.
2274  std::string rewritten_event;
2275  {
2276    XEvent xev;
2277    InitXKeyEvent(ui::VKEY_CONTROL, 0, ui::ET_KEY_PRESSED,
2278                  keycode_control_l_, 0U, &xev);
2279    xev.xkey.send_event = True;  // XSendEvent() always does this.
2280    ui::KeyEvent keyevent(&xev, false /* is_char */);
2281    rewriter.RewriteForTesting(&keyevent);
2282    rewritten_event = base::StringPrintf(
2283        "ui_keycode=%d ui_flags=%d ui_type=%d "
2284        "x_keycode=%u x_state=%u x_type=%d",
2285        keyevent.key_code(), keyevent.flags(), keyevent.type(),
2286        xev.xkey.keycode, xev.xkey.state, xev.xkey.type);
2287  }
2288
2289  // XK_Control_L (left Control key) should NOT be remapped to Alt if send_event
2290  // flag in the event is True.
2291  EXPECT_EQ(GetExpectedResultAsString(ui::VKEY_CONTROL,
2292                                      ui::EF_CONTROL_DOWN,
2293                                      ui::ET_KEY_PRESSED,
2294                                      keycode_control_l_,
2295                                      0U,
2296                                      KeyPress),
2297            rewritten_event);
2298}
2299#endif  // OS_CHROMEOS
2300