| OLD | NEW |
| 1 // Copyright 2016 The Chromium Authors. All rights reserved. | 1 // Copyright 2016 The Chromium Authors. All rights reserved. |
| 2 // Use of this source code is governed by a BSD-style license that can be | 2 // Use of this source code is governed by a BSD-style license that can be |
| 3 // found in the LICENSE file. | 3 // found in the LICENSE file. |
| 4 | 4 |
| 5 #include "remoting/host/security_key/remote_security_key_message_reader.h" | 5 #include "remoting/host/security_key/remote_security_key_message_reader.h" |
| 6 | 6 |
| 7 #include <cstdint> | 7 #include <cstdint> |
| 8 #include <string> | 8 #include <string> |
| 9 #include <utility> | 9 #include <utility> |
| 10 | 10 |
| (...skipping 16 matching lines...) Expand all Loading... |
| 27 | 27 |
| 28 class RemoteSecurityKeyMessageReaderImplTest : public testing::Test { | 28 class RemoteSecurityKeyMessageReaderImplTest : public testing::Test { |
| 29 public: | 29 public: |
| 30 RemoteSecurityKeyMessageReaderImplTest(); | 30 RemoteSecurityKeyMessageReaderImplTest(); |
| 31 ~RemoteSecurityKeyMessageReaderImplTest() override; | 31 ~RemoteSecurityKeyMessageReaderImplTest() override; |
| 32 | 32 |
| 33 // SecurityKeyMessageCallback passed to the Reader. Stores |message| so it can | 33 // SecurityKeyMessageCallback passed to the Reader. Stores |message| so it can |
| 34 // be verified by tests. | 34 // be verified by tests. |
| 35 void OnMessage(scoped_ptr<SecurityKeyMessage> message); | 35 void OnMessage(scoped_ptr<SecurityKeyMessage> message); |
| 36 | 36 |
| 37 // Used as a callback to signal completion. |
| 38 void OperationComplete(); |
| 39 |
| 37 protected: | 40 protected: |
| 38 // testing::Test interface. | 41 // testing::Test interface. |
| 39 void SetUp() override; | 42 void SetUp() override; |
| 40 | 43 |
| 41 // Runs the MessageLoop until the reader has completed and called back. | 44 // Runs the MessageLoop until the reader has completed and called back. |
| 42 void Run(); | 45 void RunLoop(); |
| 46 |
| 47 // Closes |write_file_| and runs the MessageLoop until the reader has |
| 48 // completed and called back. |
| 49 void CloseWriteFileAndRunLoop(); |
| 43 | 50 |
| 44 // Writes a message (header+code+body) to the write-end of the pipe. | 51 // Writes a message (header+code+body) to the write-end of the pipe. |
| 45 void WriteMessage(RemoteSecurityKeyMessageType message_type, | 52 void WriteMessage(RemoteSecurityKeyMessageType message_type, |
| 46 const std::string& message_payload); | 53 const std::string& message_payload); |
| 47 | 54 |
| 48 // Writes some data to the write-end of the pipe. | 55 // Writes some data to the write-end of the pipe. |
| 49 void WriteData(const char* data, int length); | 56 void WriteData(const char* data, int length); |
| 50 | 57 |
| 51 scoped_ptr<RemoteSecurityKeyMessageReader> reader_; | 58 scoped_ptr<RemoteSecurityKeyMessageReader> reader_; |
| 52 base::File read_file_; | 59 base::File read_file_; |
| 53 base::File write_file_; | 60 base::File write_file_; |
| 54 | 61 |
| 55 std::vector<scoped_ptr<SecurityKeyMessage>> messages_received_; | 62 std::vector<scoped_ptr<SecurityKeyMessage>> messages_received_; |
| 56 | 63 |
| 57 private: | 64 private: |
| 58 base::MessageLoopForIO message_loop_; | 65 base::MessageLoopForIO message_loop_; |
| 59 base::RunLoop run_loop_; | 66 scoped_ptr<base::RunLoop> run_loop_; |
| 60 | 67 |
| 61 DISALLOW_COPY_AND_ASSIGN(RemoteSecurityKeyMessageReaderImplTest); | 68 DISALLOW_COPY_AND_ASSIGN(RemoteSecurityKeyMessageReaderImplTest); |
| 62 }; | 69 }; |
| 63 | 70 |
| 64 RemoteSecurityKeyMessageReaderImplTest:: | 71 RemoteSecurityKeyMessageReaderImplTest::RemoteSecurityKeyMessageReaderImplTest() |
| 65 RemoteSecurityKeyMessageReaderImplTest() {} | 72 : run_loop_(new base::RunLoop()) {} |
| 66 | 73 |
| 67 RemoteSecurityKeyMessageReaderImplTest:: | 74 RemoteSecurityKeyMessageReaderImplTest:: |
| 68 ~RemoteSecurityKeyMessageReaderImplTest() {} | 75 ~RemoteSecurityKeyMessageReaderImplTest() {} |
| 69 | 76 |
| 70 void RemoteSecurityKeyMessageReaderImplTest::SetUp() { | 77 void RemoteSecurityKeyMessageReaderImplTest::SetUp() { |
| 71 ASSERT_TRUE(MakePipe(&read_file_, &write_file_)); | 78 ASSERT_TRUE(MakePipe(&read_file_, &write_file_)); |
| 72 reader_.reset(new RemoteSecurityKeyMessageReaderImpl(std::move(read_file_))); | 79 reader_.reset(new RemoteSecurityKeyMessageReaderImpl(std::move(read_file_))); |
| 73 | 80 |
| 74 // base::Unretained is safe since no further tasks can run after | 81 // base::Unretained is safe since no further tasks can run after |
| 75 // RunLoop::Run() returns. | 82 // RunLoop::Run() returns. |
| 76 reader_->Start(base::Bind(&RemoteSecurityKeyMessageReaderImplTest::OnMessage, | 83 reader_->Start( |
| 77 base::Unretained(this)), | 84 base::Bind(&RemoteSecurityKeyMessageReaderImplTest::OnMessage, |
| 78 run_loop_.QuitClosure()); | 85 base::Unretained(this)), |
| 86 base::Bind(&RemoteSecurityKeyMessageReaderImplTest::OperationComplete, |
| 87 base::Unretained(this))); |
| 79 } | 88 } |
| 80 | 89 |
| 81 void RemoteSecurityKeyMessageReaderImplTest::Run() { | 90 void RemoteSecurityKeyMessageReaderImplTest::RunLoop() { |
| 82 // Close the write-end, so the reader doesn't block waiting for more data. | 91 run_loop_->Run(); |
| 92 run_loop_.reset(new base::RunLoop()); |
| 93 } |
| 94 |
| 95 void RemoteSecurityKeyMessageReaderImplTest::CloseWriteFileAndRunLoop() { |
| 83 write_file_.Close(); | 96 write_file_.Close(); |
| 84 run_loop_.Run(); | 97 run_loop_->Run(); |
| 98 run_loop_.reset(new base::RunLoop()); |
| 85 } | 99 } |
| 86 | 100 |
| 87 void RemoteSecurityKeyMessageReaderImplTest::OnMessage( | 101 void RemoteSecurityKeyMessageReaderImplTest::OnMessage( |
| 88 scoped_ptr<SecurityKeyMessage> message) { | 102 scoped_ptr<SecurityKeyMessage> message) { |
| 89 messages_received_.push_back(std::move(message)); | 103 messages_received_.push_back(std::move(message)); |
| 104 OperationComplete(); |
| 105 } |
| 106 |
| 107 void RemoteSecurityKeyMessageReaderImplTest::OperationComplete() { |
| 108 run_loop_->Quit(); |
| 90 } | 109 } |
| 91 | 110 |
| 92 void RemoteSecurityKeyMessageReaderImplTest::WriteMessage( | 111 void RemoteSecurityKeyMessageReaderImplTest::WriteMessage( |
| 93 RemoteSecurityKeyMessageType message_type, | 112 RemoteSecurityKeyMessageType message_type, |
| 94 const std::string& message_payload) { | 113 const std::string& message_payload) { |
| 95 uint32_t length = | 114 uint32_t length = |
| 96 SecurityKeyMessage::kMessageTypeSizeBytes + message_payload.size(); | 115 SecurityKeyMessage::kMessageTypeSizeBytes + message_payload.size(); |
| 97 WriteData(reinterpret_cast<char*>(&length), | 116 WriteData(reinterpret_cast<char*>(&length), |
| 98 SecurityKeyMessage::kHeaderSizeBytes); | 117 SecurityKeyMessage::kHeaderSizeBytes); |
| 99 WriteData(reinterpret_cast<char*>(&message_type), | 118 WriteData(reinterpret_cast<char*>(&message_type), |
| 100 SecurityKeyMessage::kMessageTypeSizeBytes); | 119 SecurityKeyMessage::kMessageTypeSizeBytes); |
| 101 if (!message_payload.empty()) { | 120 if (!message_payload.empty()) { |
| 102 WriteData(message_payload.data(), message_payload.size()); | 121 WriteData(message_payload.data(), message_payload.size()); |
| 103 } | 122 } |
| 104 } | 123 } |
| 105 | 124 |
| 106 void RemoteSecurityKeyMessageReaderImplTest::WriteData(const char* data, | 125 void RemoteSecurityKeyMessageReaderImplTest::WriteData(const char* data, |
| 107 int length) { | 126 int length) { |
| 108 int written = write_file_.WriteAtCurrentPos(data, length); | 127 int written = write_file_.WriteAtCurrentPos(data, length); |
| 109 ASSERT_EQ(length, written); | 128 ASSERT_EQ(length, written); |
| 110 } | 129 } |
| 111 | 130 |
| 112 TEST_F(RemoteSecurityKeyMessageReaderImplTest, EnsureReaderTornDownCleanly) { | |
| 113 // This test is different from the others as the files used for reading and | |
| 114 // writing are still open when the reader instance is destroyed. This test is | |
| 115 // meant to ensure that no asserts/exceptions/hangs occur during shutdown. | |
| 116 WriteMessage(kTestMessageType, std::string()); | |
| 117 reader_.reset(); | |
| 118 } | |
| 119 | |
| 120 TEST_F(RemoteSecurityKeyMessageReaderImplTest, SingleMessageWithNoPayload) { | 131 TEST_F(RemoteSecurityKeyMessageReaderImplTest, SingleMessageWithNoPayload) { |
| 121 WriteMessage(kTestMessageType, std::string()); | 132 WriteMessage(kTestMessageType, std::string()); |
| 122 Run(); | 133 RunLoop(); |
| 123 ASSERT_EQ(1u, messages_received_.size()); | 134 ASSERT_EQ(1u, messages_received_.size()); |
| 124 ASSERT_EQ(kTestMessageType, messages_received_[0]->type()); | 135 ASSERT_EQ(kTestMessageType, messages_received_[0]->type()); |
| 125 ASSERT_EQ("", messages_received_[0]->payload()); | 136 ASSERT_EQ("", messages_received_[0]->payload()); |
| 137 |
| 138 CloseWriteFileAndRunLoop(); |
| 126 } | 139 } |
| 127 | 140 |
| 128 TEST_F(RemoteSecurityKeyMessageReaderImplTest, SingleMessageWithPayload) { | 141 TEST_F(RemoteSecurityKeyMessageReaderImplTest, SingleMessageWithPayload) { |
| 129 std::string payload("I AM A VALID MESSAGE PAYLOAD!!!!!!!!!!!!!!!!!!!!!!"); | 142 std::string payload("I AM A VALID MESSAGE PAYLOAD!!!!!!!!!!!!!!!!!!!!!!"); |
| 130 WriteMessage(kTestMessageType, payload); | 143 WriteMessage(kTestMessageType, payload); |
| 131 Run(); | 144 RunLoop(); |
| 132 ASSERT_EQ(1u, messages_received_.size()); | 145 ASSERT_EQ(1u, messages_received_.size()); |
| 133 ASSERT_EQ(kTestMessageType, messages_received_[0]->type()); | 146 ASSERT_EQ(kTestMessageType, messages_received_[0]->type()); |
| 134 ASSERT_EQ(payload, messages_received_[0]->payload()); | 147 ASSERT_EQ(payload, messages_received_[0]->payload()); |
| 148 |
| 149 CloseWriteFileAndRunLoop(); |
| 135 } | 150 } |
| 136 | 151 |
| 137 TEST_F(RemoteSecurityKeyMessageReaderImplTest, SingleMessageWithLargePayload) { | 152 TEST_F(RemoteSecurityKeyMessageReaderImplTest, SingleMessageWithLargePayload) { |
| 138 std::string payload(kMaxSecurityKeyMessageByteCount - | 153 std::string payload(kMaxSecurityKeyMessageByteCount - |
| 139 SecurityKeyMessage::kMessageTypeSizeBytes, | 154 SecurityKeyMessage::kMessageTypeSizeBytes, |
| 140 'Y'); | 155 'Y'); |
| 141 WriteMessage(kTestMessageType, payload); | 156 WriteMessage(kTestMessageType, payload); |
| 142 Run(); | 157 RunLoop(); |
| 143 ASSERT_EQ(1u, messages_received_.size()); | 158 ASSERT_EQ(1u, messages_received_.size()); |
| 144 ASSERT_EQ(kTestMessageType, messages_received_[0]->type()); | 159 ASSERT_EQ(kTestMessageType, messages_received_[0]->type()); |
| 145 ASSERT_EQ(payload, messages_received_[0]->payload()); | 160 ASSERT_EQ(payload, messages_received_[0]->payload()); |
| 161 |
| 162 CloseWriteFileAndRunLoop(); |
| 146 } | 163 } |
| 147 | 164 |
| 148 TEST_F(RemoteSecurityKeyMessageReaderImplTest, EmptyFile) { | 165 TEST_F(RemoteSecurityKeyMessageReaderImplTest, EmptyFile) { |
| 149 Run(); | 166 CloseWriteFileAndRunLoop(); |
| 150 ASSERT_EQ(0u, messages_received_.size()); | 167 ASSERT_EQ(0u, messages_received_.size()); |
| 151 } | 168 } |
| 152 | 169 |
| 153 TEST_F(RemoteSecurityKeyMessageReaderImplTest, InvalidMessageLength) { | 170 TEST_F(RemoteSecurityKeyMessageReaderImplTest, InvalidMessageLength) { |
| 154 uint32_t length = kMaxSecurityKeyMessageByteCount + 1; | 171 uint32_t length = kMaxSecurityKeyMessageByteCount + 1; |
| 155 ASSERT_FALSE(SecurityKeyMessage::IsValidMessageSize(length)); | 172 ASSERT_FALSE(SecurityKeyMessage::IsValidMessageSize(length)); |
| 156 WriteData(reinterpret_cast<char*>(&length), sizeof(length)); | 173 WriteData(reinterpret_cast<char*>(&length), sizeof(length)); |
| 157 Run(); | 174 CloseWriteFileAndRunLoop(); |
| 158 ASSERT_EQ(0u, messages_received_.size()); | 175 ASSERT_EQ(0u, messages_received_.size()); |
| 159 } | 176 } |
| 160 | 177 |
| 161 TEST_F(RemoteSecurityKeyMessageReaderImplTest, ShortHeader) { | 178 TEST_F(RemoteSecurityKeyMessageReaderImplTest, ShortHeader) { |
| 162 // Write only 3 bytes - the message length header is supposed to be 4 bytes. | 179 // Write only 3 bytes - the message length header is supposed to be 4 bytes. |
| 163 WriteData("xxx", SecurityKeyMessage::kHeaderSizeBytes - 1); | 180 WriteData("xxx", SecurityKeyMessage::kHeaderSizeBytes - 1); |
| 164 Run(); | 181 CloseWriteFileAndRunLoop(); |
| 165 ASSERT_EQ(0u, messages_received_.size()); | 182 ASSERT_EQ(0u, messages_received_.size()); |
| 166 } | 183 } |
| 167 | 184 |
| 168 TEST_F(RemoteSecurityKeyMessageReaderImplTest, ZeroLengthMessage) { | 185 TEST_F(RemoteSecurityKeyMessageReaderImplTest, ZeroLengthMessage) { |
| 169 uint32_t length = 0; | 186 uint32_t length = 0; |
| 170 WriteData(reinterpret_cast<char*>(&length), sizeof(length)); | 187 WriteData(reinterpret_cast<char*>(&length), sizeof(length)); |
| 171 Run(); | 188 CloseWriteFileAndRunLoop(); |
| 172 ASSERT_EQ(0u, messages_received_.size()); | 189 ASSERT_EQ(0u, messages_received_.size()); |
| 173 } | 190 } |
| 174 | 191 |
| 175 TEST_F(RemoteSecurityKeyMessageReaderImplTest, MissingControlCode) { | 192 TEST_F(RemoteSecurityKeyMessageReaderImplTest, MissingControlCode) { |
| 176 uint32_t length = 1; | 193 uint32_t length = 1; |
| 177 WriteData(reinterpret_cast<char*>(&length), sizeof(length)); | 194 WriteData(reinterpret_cast<char*>(&length), sizeof(length)); |
| 178 Run(); | 195 CloseWriteFileAndRunLoop(); |
| 179 ASSERT_EQ(0u, messages_received_.size()); | 196 ASSERT_EQ(0u, messages_received_.size()); |
| 180 } | 197 } |
| 181 | 198 |
| 182 TEST_F(RemoteSecurityKeyMessageReaderImplTest, MissingPayload) { | 199 TEST_F(RemoteSecurityKeyMessageReaderImplTest, MissingPayload) { |
| 183 uint32_t length = 2; | 200 uint32_t length = 2; |
| 184 WriteData(reinterpret_cast<char*>(&length), sizeof(length)); | 201 WriteData(reinterpret_cast<char*>(&length), sizeof(length)); |
| 185 | 202 |
| 186 char test_control_code = static_cast<char>(kTestMessageType); | 203 char test_control_code = static_cast<char>(kTestMessageType); |
| 187 WriteData(&test_control_code, sizeof(test_control_code)); | 204 WriteData(&test_control_code, sizeof(test_control_code)); |
| 188 Run(); | 205 CloseWriteFileAndRunLoop(); |
| 189 ASSERT_EQ(0u, messages_received_.size()); | 206 ASSERT_EQ(0u, messages_received_.size()); |
| 190 } | 207 } |
| 191 | 208 |
| 192 TEST_F(RemoteSecurityKeyMessageReaderImplTest, MultipleMessages) { | 209 TEST_F(RemoteSecurityKeyMessageReaderImplTest, MultipleMessages) { |
| 193 std::vector<std::string> payloads({"", "S", // Really short | 210 std::vector<std::string> payloads({"", "S", // Really short |
| 194 "", "Short", "", "Medium Length", "", | 211 "", "Short", "", "Medium Length", "", |
| 195 "Longer than medium, but not super long", | 212 "Longer than medium, but not super long", |
| 196 "", std::string(2048, 'Y'), ""}); | 213 "", std::string(2048, 'Y'), ""}); |
| 197 | 214 |
| 198 for (auto& payload : payloads) { | 215 for (auto& payload : payloads) { |
| 199 WriteMessage(kTestMessageType, payload); | 216 WriteMessage(kTestMessageType, payload); |
| 217 RunLoop(); |
| 200 } | 218 } |
| 201 | 219 |
| 202 Run(); | |
| 203 ASSERT_EQ(payloads.size(), messages_received_.size()); | 220 ASSERT_EQ(payloads.size(), messages_received_.size()); |
| 221 CloseWriteFileAndRunLoop(); |
| 204 | 222 |
| 205 for (size_t i = 0; i < payloads.size(); i++) { | 223 for (size_t i = 0; i < payloads.size(); i++) { |
| 206 ASSERT_EQ(kTestMessageType, messages_received_[i]->type()); | 224 ASSERT_EQ(kTestMessageType, messages_received_[i]->type()); |
| 207 ASSERT_EQ(payloads[i], messages_received_[i]->payload()); | 225 ASSERT_EQ(payloads[i], messages_received_[i]->payload()); |
| 208 } | 226 } |
| 209 } | 227 } |
| 210 | 228 |
| 211 } // namespace remoting | 229 } // namespace remoting |
| OLD | NEW |