InputChannel_test.cpp revision cbee6d6ede0499fb4a2c00bfc00d5db8d9ed5139
1ebbd5d14ad3b1e762d9fcfa026e19413cc857e05Jeff Brown/*
2ebbd5d14ad3b1e762d9fcfa026e19413cc857e05Jeff Brown * Copyright (C) 2010 The Android Open Source Project
3ebbd5d14ad3b1e762d9fcfa026e19413cc857e05Jeff Brown *
4ebbd5d14ad3b1e762d9fcfa026e19413cc857e05Jeff Brown * Licensed under the Apache License, Version 2.0 (the "License");
5ebbd5d14ad3b1e762d9fcfa026e19413cc857e05Jeff Brown * you may not use this file except in compliance with the License.
6ebbd5d14ad3b1e762d9fcfa026e19413cc857e05Jeff Brown * You may obtain a copy of the License at
7ebbd5d14ad3b1e762d9fcfa026e19413cc857e05Jeff Brown *
8ebbd5d14ad3b1e762d9fcfa026e19413cc857e05Jeff Brown *      http://www.apache.org/licenses/LICENSE-2.0
9ebbd5d14ad3b1e762d9fcfa026e19413cc857e05Jeff Brown *
10ebbd5d14ad3b1e762d9fcfa026e19413cc857e05Jeff Brown * Unless required by applicable law or agreed to in writing, software
11ebbd5d14ad3b1e762d9fcfa026e19413cc857e05Jeff Brown * distributed under the License is distributed on an "AS IS" BASIS,
12ebbd5d14ad3b1e762d9fcfa026e19413cc857e05Jeff Brown * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13ebbd5d14ad3b1e762d9fcfa026e19413cc857e05Jeff Brown * See the License for the specific language governing permissions and
14ebbd5d14ad3b1e762d9fcfa026e19413cc857e05Jeff Brown * limitations under the License.
15ebbd5d14ad3b1e762d9fcfa026e19413cc857e05Jeff Brown */
165c225b1680e696ae8bbf505a1997d6f720672f74Jeff Brown
175c225b1680e696ae8bbf505a1997d6f720672f74Jeff Brown#include <ui/InputTransport.h>
185c225b1680e696ae8bbf505a1997d6f720672f74Jeff Brown#include <utils/Timers.h>
195c225b1680e696ae8bbf505a1997d6f720672f74Jeff Brown#include <utils/StopWatch.h>
205c225b1680e696ae8bbf505a1997d6f720672f74Jeff Brown#include <gtest/gtest.h>
215c225b1680e696ae8bbf505a1997d6f720672f74Jeff Brown#include <unistd.h>
225c225b1680e696ae8bbf505a1997d6f720672f74Jeff Brown#include <time.h>
23cbee6d6ede0499fb4a2c00bfc00d5db8d9ed5139Jeff Brown#include <errno.h>
245c225b1680e696ae8bbf505a1997d6f720672f74Jeff Brown
255c225b1680e696ae8bbf505a1997d6f720672f74Jeff Brown#include "../../utils/tests/TestHelpers.h"
265c225b1680e696ae8bbf505a1997d6f720672f74Jeff Brown
275c225b1680e696ae8bbf505a1997d6f720672f74Jeff Brownnamespace android {
285c225b1680e696ae8bbf505a1997d6f720672f74Jeff Brown
295c225b1680e696ae8bbf505a1997d6f720672f74Jeff Brownclass InputChannelTest : public testing::Test {
305c225b1680e696ae8bbf505a1997d6f720672f74Jeff Brownprotected:
315c225b1680e696ae8bbf505a1997d6f720672f74Jeff Brown    virtual void SetUp() { }
325c225b1680e696ae8bbf505a1997d6f720672f74Jeff Brown    virtual void TearDown() { }
335c225b1680e696ae8bbf505a1997d6f720672f74Jeff Brown};
345c225b1680e696ae8bbf505a1997d6f720672f74Jeff Brown
355c225b1680e696ae8bbf505a1997d6f720672f74Jeff Brown
365c225b1680e696ae8bbf505a1997d6f720672f74Jeff BrownTEST_F(InputChannelTest, ConstructorAndDestructor_TakesOwnershipOfFileDescriptors) {
375c225b1680e696ae8bbf505a1997d6f720672f74Jeff Brown    // Our purpose here is to verify that the input channel destructor closes the
38cbee6d6ede0499fb4a2c00bfc00d5db8d9ed5139Jeff Brown    // file descriptor provided to it.  One easy way is to provide it with one end
395c225b1680e696ae8bbf505a1997d6f720672f74Jeff Brown    // of a pipe and to check for EPIPE on the other end after the channel is destroyed.
40cbee6d6ede0499fb4a2c00bfc00d5db8d9ed5139Jeff Brown    Pipe pipe;
415c225b1680e696ae8bbf505a1997d6f720672f74Jeff Brown
42cbee6d6ede0499fb4a2c00bfc00d5db8d9ed5139Jeff Brown    sp<InputChannel> inputChannel = new InputChannel(String8("channel name"), pipe.sendFd);
435c225b1680e696ae8bbf505a1997d6f720672f74Jeff Brown
445c225b1680e696ae8bbf505a1997d6f720672f74Jeff Brown    EXPECT_STREQ("channel name", inputChannel->getName().string())
455c225b1680e696ae8bbf505a1997d6f720672f74Jeff Brown            << "channel should have provided name";
46cbee6d6ede0499fb4a2c00bfc00d5db8d9ed5139Jeff Brown    EXPECT_EQ(pipe.sendFd, inputChannel->getFd())
47cbee6d6ede0499fb4a2c00bfc00d5db8d9ed5139Jeff Brown            << "channel should have provided fd";
485c225b1680e696ae8bbf505a1997d6f720672f74Jeff Brown
495c225b1680e696ae8bbf505a1997d6f720672f74Jeff Brown    inputChannel.clear(); // destroys input channel
505c225b1680e696ae8bbf505a1997d6f720672f74Jeff Brown
51cbee6d6ede0499fb4a2c00bfc00d5db8d9ed5139Jeff Brown    EXPECT_EQ(-EPIPE, pipe.readSignal())
52cbee6d6ede0499fb4a2c00bfc00d5db8d9ed5139Jeff Brown            << "channel should have closed fd when destroyed";
535c225b1680e696ae8bbf505a1997d6f720672f74Jeff Brown
545c225b1680e696ae8bbf505a1997d6f720672f74Jeff Brown    // clean up fds of Pipe endpoints that were closed so we don't try to close them again
55cbee6d6ede0499fb4a2c00bfc00d5db8d9ed5139Jeff Brown    pipe.sendFd = -1;
565c225b1680e696ae8bbf505a1997d6f720672f74Jeff Brown}
575c225b1680e696ae8bbf505a1997d6f720672f74Jeff Brown
585c225b1680e696ae8bbf505a1997d6f720672f74Jeff BrownTEST_F(InputChannelTest, OpenInputChannelPair_ReturnsAPairOfConnectedChannels) {
595c225b1680e696ae8bbf505a1997d6f720672f74Jeff Brown    sp<InputChannel> serverChannel, clientChannel;
605c225b1680e696ae8bbf505a1997d6f720672f74Jeff Brown
615c225b1680e696ae8bbf505a1997d6f720672f74Jeff Brown    status_t result = InputChannel::openInputChannelPair(String8("channel name"),
625c225b1680e696ae8bbf505a1997d6f720672f74Jeff Brown            serverChannel, clientChannel);
635c225b1680e696ae8bbf505a1997d6f720672f74Jeff Brown
645c225b1680e696ae8bbf505a1997d6f720672f74Jeff Brown    ASSERT_EQ(OK, result)
655c225b1680e696ae8bbf505a1997d6f720672f74Jeff Brown            << "should have successfully opened a channel pair";
665c225b1680e696ae8bbf505a1997d6f720672f74Jeff Brown
675c225b1680e696ae8bbf505a1997d6f720672f74Jeff Brown    // Name
685c225b1680e696ae8bbf505a1997d6f720672f74Jeff Brown    EXPECT_STREQ("channel name (server)", serverChannel->getName().string())
695c225b1680e696ae8bbf505a1997d6f720672f74Jeff Brown            << "server channel should have suffixed name";
705c225b1680e696ae8bbf505a1997d6f720672f74Jeff Brown    EXPECT_STREQ("channel name (client)", clientChannel->getName().string())
715c225b1680e696ae8bbf505a1997d6f720672f74Jeff Brown            << "client channel should have suffixed name";
725c225b1680e696ae8bbf505a1997d6f720672f74Jeff Brown
735c225b1680e696ae8bbf505a1997d6f720672f74Jeff Brown    // Server->Client communication
74cbee6d6ede0499fb4a2c00bfc00d5db8d9ed5139Jeff Brown    InputMessage serverMsg;
75cbee6d6ede0499fb4a2c00bfc00d5db8d9ed5139Jeff Brown    memset(&serverMsg, 0, sizeof(InputMessage));
76cbee6d6ede0499fb4a2c00bfc00d5db8d9ed5139Jeff Brown    serverMsg.header.type = InputMessage::TYPE_KEY;
77cbee6d6ede0499fb4a2c00bfc00d5db8d9ed5139Jeff Brown    serverMsg.body.key.action = AKEY_EVENT_ACTION_DOWN;
78cbee6d6ede0499fb4a2c00bfc00d5db8d9ed5139Jeff Brown    EXPECT_EQ(OK, serverChannel->sendMessage(&serverMsg))
79cbee6d6ede0499fb4a2c00bfc00d5db8d9ed5139Jeff Brown            << "server channel should be able to send message to client channel";
80cbee6d6ede0499fb4a2c00bfc00d5db8d9ed5139Jeff Brown
81cbee6d6ede0499fb4a2c00bfc00d5db8d9ed5139Jeff Brown    InputMessage clientMsg;
82cbee6d6ede0499fb4a2c00bfc00d5db8d9ed5139Jeff Brown    EXPECT_EQ(OK, clientChannel->receiveMessage(&clientMsg))
83cbee6d6ede0499fb4a2c00bfc00d5db8d9ed5139Jeff Brown            << "client channel should be able to receive message from server channel";
84cbee6d6ede0499fb4a2c00bfc00d5db8d9ed5139Jeff Brown    EXPECT_EQ(serverMsg.header.type, clientMsg.header.type)
85cbee6d6ede0499fb4a2c00bfc00d5db8d9ed5139Jeff Brown            << "client channel should receive the correct message from server channel";
86cbee6d6ede0499fb4a2c00bfc00d5db8d9ed5139Jeff Brown    EXPECT_EQ(serverMsg.body.key.action, clientMsg.body.key.action)
87cbee6d6ede0499fb4a2c00bfc00d5db8d9ed5139Jeff Brown            << "client channel should receive the correct message from server channel";
885c225b1680e696ae8bbf505a1997d6f720672f74Jeff Brown
895c225b1680e696ae8bbf505a1997d6f720672f74Jeff Brown    // Client->Server communication
90cbee6d6ede0499fb4a2c00bfc00d5db8d9ed5139Jeff Brown    InputMessage clientReply;
91cbee6d6ede0499fb4a2c00bfc00d5db8d9ed5139Jeff Brown    memset(&clientReply, 0, sizeof(InputMessage));
92cbee6d6ede0499fb4a2c00bfc00d5db8d9ed5139Jeff Brown    clientReply.header.type = InputMessage::TYPE_FINISHED;
93cbee6d6ede0499fb4a2c00bfc00d5db8d9ed5139Jeff Brown    clientReply.body.finished.handled = true;
94cbee6d6ede0499fb4a2c00bfc00d5db8d9ed5139Jeff Brown    EXPECT_EQ(OK, clientChannel->sendMessage(&clientReply))
95cbee6d6ede0499fb4a2c00bfc00d5db8d9ed5139Jeff Brown            << "client channel should be able to send message to server channel";
96cbee6d6ede0499fb4a2c00bfc00d5db8d9ed5139Jeff Brown
97cbee6d6ede0499fb4a2c00bfc00d5db8d9ed5139Jeff Brown    InputMessage serverReply;
98cbee6d6ede0499fb4a2c00bfc00d5db8d9ed5139Jeff Brown    EXPECT_EQ(OK, serverChannel->receiveMessage(&serverReply))
99cbee6d6ede0499fb4a2c00bfc00d5db8d9ed5139Jeff Brown            << "server channel should be able to receive message from client channel";
100cbee6d6ede0499fb4a2c00bfc00d5db8d9ed5139Jeff Brown    EXPECT_EQ(clientReply.header.type, serverReply.header.type)
101cbee6d6ede0499fb4a2c00bfc00d5db8d9ed5139Jeff Brown            << "server channel should receive the correct message from client channel";
102cbee6d6ede0499fb4a2c00bfc00d5db8d9ed5139Jeff Brown    EXPECT_EQ(clientReply.body.finished.handled, serverReply.body.finished.handled)
103cbee6d6ede0499fb4a2c00bfc00d5db8d9ed5139Jeff Brown            << "server channel should receive the correct message from client channel";
1045c225b1680e696ae8bbf505a1997d6f720672f74Jeff Brown}
1055c225b1680e696ae8bbf505a1997d6f720672f74Jeff Brown
1065c225b1680e696ae8bbf505a1997d6f720672f74Jeff BrownTEST_F(InputChannelTest, ReceiveSignal_WhenNoSignalPresent_ReturnsAnError) {
1075c225b1680e696ae8bbf505a1997d6f720672f74Jeff Brown    sp<InputChannel> serverChannel, clientChannel;
1085c225b1680e696ae8bbf505a1997d6f720672f74Jeff Brown
1095c225b1680e696ae8bbf505a1997d6f720672f74Jeff Brown    status_t result = InputChannel::openInputChannelPair(String8("channel name"),
1105c225b1680e696ae8bbf505a1997d6f720672f74Jeff Brown            serverChannel, clientChannel);
1115c225b1680e696ae8bbf505a1997d6f720672f74Jeff Brown
1125c225b1680e696ae8bbf505a1997d6f720672f74Jeff Brown    ASSERT_EQ(OK, result)
1135c225b1680e696ae8bbf505a1997d6f720672f74Jeff Brown            << "should have successfully opened a channel pair";
1145c225b1680e696ae8bbf505a1997d6f720672f74Jeff Brown
115cbee6d6ede0499fb4a2c00bfc00d5db8d9ed5139Jeff Brown    InputMessage msg;
116cbee6d6ede0499fb4a2c00bfc00d5db8d9ed5139Jeff Brown    EXPECT_EQ(WOULD_BLOCK, clientChannel->receiveMessage(&msg))
117cbee6d6ede0499fb4a2c00bfc00d5db8d9ed5139Jeff Brown            << "receiveMessage should have returned WOULD_BLOCK";
1185c225b1680e696ae8bbf505a1997d6f720672f74Jeff Brown}
1195c225b1680e696ae8bbf505a1997d6f720672f74Jeff Brown
1205c225b1680e696ae8bbf505a1997d6f720672f74Jeff BrownTEST_F(InputChannelTest, ReceiveSignal_WhenPeerClosed_ReturnsAnError) {
1215c225b1680e696ae8bbf505a1997d6f720672f74Jeff Brown    sp<InputChannel> serverChannel, clientChannel;
1225c225b1680e696ae8bbf505a1997d6f720672f74Jeff Brown
1235c225b1680e696ae8bbf505a1997d6f720672f74Jeff Brown    status_t result = InputChannel::openInputChannelPair(String8("channel name"),
1245c225b1680e696ae8bbf505a1997d6f720672f74Jeff Brown            serverChannel, clientChannel);
1255c225b1680e696ae8bbf505a1997d6f720672f74Jeff Brown
1265c225b1680e696ae8bbf505a1997d6f720672f74Jeff Brown    ASSERT_EQ(OK, result)
1275c225b1680e696ae8bbf505a1997d6f720672f74Jeff Brown            << "should have successfully opened a channel pair";
1285c225b1680e696ae8bbf505a1997d6f720672f74Jeff Brown
1295c225b1680e696ae8bbf505a1997d6f720672f74Jeff Brown    serverChannel.clear(); // close server channel
1305c225b1680e696ae8bbf505a1997d6f720672f74Jeff Brown
131cbee6d6ede0499fb4a2c00bfc00d5db8d9ed5139Jeff Brown    InputMessage msg;
132cbee6d6ede0499fb4a2c00bfc00d5db8d9ed5139Jeff Brown    EXPECT_EQ(DEAD_OBJECT, clientChannel->receiveMessage(&msg))
133cbee6d6ede0499fb4a2c00bfc00d5db8d9ed5139Jeff Brown            << "receiveMessage should have returned DEAD_OBJECT";
1345c225b1680e696ae8bbf505a1997d6f720672f74Jeff Brown}
1355c225b1680e696ae8bbf505a1997d6f720672f74Jeff Brown
1365c225b1680e696ae8bbf505a1997d6f720672f74Jeff BrownTEST_F(InputChannelTest, SendSignal_WhenPeerClosed_ReturnsAnError) {
1375c225b1680e696ae8bbf505a1997d6f720672f74Jeff Brown    sp<InputChannel> serverChannel, clientChannel;
1385c225b1680e696ae8bbf505a1997d6f720672f74Jeff Brown
1395c225b1680e696ae8bbf505a1997d6f720672f74Jeff Brown    status_t result = InputChannel::openInputChannelPair(String8("channel name"),
1405c225b1680e696ae8bbf505a1997d6f720672f74Jeff Brown            serverChannel, clientChannel);
1415c225b1680e696ae8bbf505a1997d6f720672f74Jeff Brown
1425c225b1680e696ae8bbf505a1997d6f720672f74Jeff Brown    ASSERT_EQ(OK, result)
1435c225b1680e696ae8bbf505a1997d6f720672f74Jeff Brown            << "should have successfully opened a channel pair";
1445c225b1680e696ae8bbf505a1997d6f720672f74Jeff Brown
1455c225b1680e696ae8bbf505a1997d6f720672f74Jeff Brown    serverChannel.clear(); // close server channel
1465c225b1680e696ae8bbf505a1997d6f720672f74Jeff Brown
147cbee6d6ede0499fb4a2c00bfc00d5db8d9ed5139Jeff Brown    InputMessage msg;
148cbee6d6ede0499fb4a2c00bfc00d5db8d9ed5139Jeff Brown    msg.header.type = InputMessage::TYPE_KEY;
149cbee6d6ede0499fb4a2c00bfc00d5db8d9ed5139Jeff Brown    EXPECT_EQ(DEAD_OBJECT, clientChannel->sendMessage(&msg))
150cbee6d6ede0499fb4a2c00bfc00d5db8d9ed5139Jeff Brown            << "sendMessage should have returned DEAD_OBJECT";
1515c225b1680e696ae8bbf505a1997d6f720672f74Jeff Brown}
1525c225b1680e696ae8bbf505a1997d6f720672f74Jeff Brown
1535c225b1680e696ae8bbf505a1997d6f720672f74Jeff Brown
1545c225b1680e696ae8bbf505a1997d6f720672f74Jeff Brown} // namespace android
155