15821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// Copyright (c) 2012 The Chromium Authors. All rights reserved.
25821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// Use of this source code is governed by a BSD-style license that can be
35821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// found in the LICENSE file.
45821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
55821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include <string>
65821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
75821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "base/basictypes.h"
85821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "remoting/base/constants.h"
95821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "testing/gtest/include/gtest/gtest.h"
105821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
115821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// X11 headers must be #included after gtest.h, since the X11 headers define
125821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// some macros that cause errors in gtest-type-util.h.
135821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include <X11/Xlib.h>
145821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "remoting/host/linux/x_server_clipboard.h"
155821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
165821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)namespace remoting {
175821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
185821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)namespace {
195821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
205821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)class ClipboardTestClient {
215821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) public:
225821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  ClipboardTestClient() : display_(NULL) {}
235821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  ~ClipboardTestClient() {}
245821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
255821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  void Init(Display* display) {
265821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    display_ = display;
275821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    clipboard_.Init(display,
285821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                    base::Bind(&ClipboardTestClient::OnClipboardChanged,
295821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                               base::Unretained(this)));
305821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
315821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
325821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  void SetClipboardData(const std::string& clipboard_data) {
335821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    clipboard_data_ = clipboard_data;
345821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    clipboard_.SetClipboard(kMimeTypeTextUtf8, clipboard_data);
355821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
365821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
375821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  void OnClipboardChanged(const std::string& mime_type,
385821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                          const std::string& data) {
395821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    clipboard_data_ = data;
405821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
415821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
425821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // Process X events on the connection, returning true if any events were
435821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // processed.
445821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  bool PumpXEvents() {
455821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    bool result = false;
465821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    while (XPending(display_)) {
475821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      XEvent event;
485821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      XNextEvent(display_, &event);
495821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      clipboard_.ProcessXEvent(&event);
505821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      result = true;
515821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    }
525821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return result;
535821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
545821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
555821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  const std::string& clipboard_data() const { return clipboard_data_; }
565821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  Display* display() const { return display_; }
575821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
585821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) private:
595821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  std::string clipboard_data_;
605821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  XServerClipboard clipboard_;
615821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  Display* display_;
625821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
635821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  DISALLOW_COPY_AND_ASSIGN(ClipboardTestClient);
645821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)};
655821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
665821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}  // namespace
675821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
685821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)class XServerClipboardTest : public testing::Test {
695821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) public:
705821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  virtual void SetUp() OVERRIDE {
715821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    // XSynchronize() ensures that PumpXEvents() fully processes all X server
725821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    // requests and responses before returning to the caller.
735821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    Display* display1 = XOpenDisplay(NULL);
745821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    XSynchronize(display1, True);
755821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    client1_.Init(display1);
765821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    Display* display2 = XOpenDisplay(NULL);
775821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    XSynchronize(display2, True);
785821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    client2_.Init(display2);
795821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
805821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
815821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  virtual void TearDown() OVERRIDE {
825821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    XCloseDisplay(client1_.display());
835821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    XCloseDisplay(client2_.display());
845821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
855821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
865821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  void PumpXEvents() {
875821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    while (true) {
885821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      if (!client1_.PumpXEvents() && !client2_.PumpXEvents()) {
895821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        break;
905821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      }
915821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    }
925821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
935821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
945821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  ClipboardTestClient client1_;
955821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  ClipboardTestClient client2_;
965821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)};
975821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
982a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)// http://crbug.com/163428
992a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)TEST_F(XServerClipboardTest, DISABLED_CopyPaste) {
1005821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // Verify clipboard data can be transferred more than once. Then verify that
1015821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // the code continues to function in the opposite direction (so client1_ will
1025821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // send then receive, and client2_ will receive then send).
1035821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  client1_.SetClipboardData("Text1");
1045821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  PumpXEvents();
1055821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  EXPECT_EQ("Text1", client2_.clipboard_data());
1065821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
1075821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  client1_.SetClipboardData("Text2");
1085821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  PumpXEvents();
1095821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  EXPECT_EQ("Text2", client2_.clipboard_data());
1105821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
1115821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  client2_.SetClipboardData("Text3");
1125821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  PumpXEvents();
1135821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  EXPECT_EQ("Text3", client1_.clipboard_data());
1145821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
1155821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  client2_.SetClipboardData("Text4");
1165821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  PumpXEvents();
1175821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  EXPECT_EQ("Text4", client1_.clipboard_data());
1185821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
1195821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
1205821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}  // namespace remoting
121