1 // Copyright 2015 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 "mojo/public/cpp/bindings/tests/router_test_util.h"
6
7 #include <stddef.h>
8 #include <stdint.h>
9 #include <string.h>
10
11 #include "mojo/public/cpp/bindings/message.h"
12 #include "mojo/public/cpp/bindings/tests/message_queue.h"
13 #include "testing/gtest/include/gtest/gtest.h"
14
15 namespace mojo {
16 namespace test {
17
AllocRequestMessage(uint32_t name,const char * text,Message * message)18 void AllocRequestMessage(uint32_t name, const char* text, Message* message) {
19 size_t payload_size = strlen(text) + 1; // Plus null terminator.
20 *message =
21 Message(name, Message::kFlagExpectsResponse, payload_size, 0, nullptr);
22 memcpy(message->payload_buffer()->AllocateAndGet(payload_size), text,
23 payload_size);
24 }
25
AllocResponseMessage(uint32_t name,const char * text,uint64_t request_id,Message * message)26 void AllocResponseMessage(uint32_t name,
27 const char* text,
28 uint64_t request_id,
29 Message* message) {
30 size_t payload_size = strlen(text) + 1; // Plus null terminator.
31 *message = Message(name, Message::kFlagIsResponse, payload_size, 0, nullptr);
32 message->set_request_id(request_id);
33 memcpy(message->payload_buffer()->AllocateAndGet(payload_size), text,
34 payload_size);
35 }
36
MessageAccumulator(MessageQueue * queue,const base::Closure & closure)37 MessageAccumulator::MessageAccumulator(MessageQueue* queue,
38 const base::Closure& closure)
39 : queue_(queue), closure_(closure) {}
40
~MessageAccumulator()41 MessageAccumulator::~MessageAccumulator() {}
42
Accept(Message * message)43 bool MessageAccumulator::Accept(Message* message) {
44 queue_->Push(message);
45 if (!closure_.is_null()) {
46 closure_.Run();
47 closure_.Reset();
48 }
49 return true;
50 }
51
ResponseGenerator()52 ResponseGenerator::ResponseGenerator() {}
53
Accept(Message * message)54 bool ResponseGenerator::Accept(Message* message) {
55 return false;
56 }
57
AcceptWithResponder(Message * message,std::unique_ptr<MessageReceiverWithStatus> responder)58 bool ResponseGenerator::AcceptWithResponder(
59 Message* message,
60 std::unique_ptr<MessageReceiverWithStatus> responder) {
61 EXPECT_TRUE(message->has_flag(Message::kFlagExpectsResponse));
62
63 bool result = SendResponse(message->name(), message->request_id(),
64 reinterpret_cast<const char*>(message->payload()),
65 responder.get());
66 EXPECT_TRUE(responder->IsConnected());
67 return result;
68 }
69
SendResponse(uint32_t name,uint64_t request_id,const char * request_string,MessageReceiver * responder)70 bool ResponseGenerator::SendResponse(uint32_t name,
71 uint64_t request_id,
72 const char* request_string,
73 MessageReceiver* responder) {
74 Message response;
75 std::string response_string(request_string);
76 response_string += " world!";
77 AllocResponseMessage(name, response_string.c_str(), request_id, &response);
78
79 return responder->Accept(&response);
80 }
81
LazyResponseGenerator(const base::Closure & closure)82 LazyResponseGenerator::LazyResponseGenerator(const base::Closure& closure)
83 : responder_(nullptr), name_(0), request_id_(0), closure_(closure) {}
84
85 LazyResponseGenerator::~LazyResponseGenerator() = default;
86
AcceptWithResponder(Message * message,std::unique_ptr<MessageReceiverWithStatus> responder)87 bool LazyResponseGenerator::AcceptWithResponder(
88 Message* message,
89 std::unique_ptr<MessageReceiverWithStatus> responder) {
90 name_ = message->name();
91 request_id_ = message->request_id();
92 request_string_ =
93 std::string(reinterpret_cast<const char*>(message->payload()));
94 responder_ = std::move(responder);
95 if (!closure_.is_null()) {
96 closure_.Run();
97 closure_.Reset();
98 }
99 return true;
100 }
101
Complete(bool send_response)102 void LazyResponseGenerator::Complete(bool send_response) {
103 if (send_response) {
104 SendResponse(name_, request_id_, request_string_.c_str(), responder_.get());
105 }
106 responder_ = nullptr;
107 }
108
109 } // namespace test
110 } // namespace mojo
111