blob: ba87de8f22e0b7a426da046b0e36d238ad028c7d [file] [log] [blame]
[email protected]76a6d452012-02-03 21:48:431// Copyright (c) 2012 The Chromium Authors. All rights reserved.
license.botbf09a502008-08-24 00:55:552// Use of this source code is governed by a BSD-style license that can be
3// found in the LICENSE file.
initial.commit09911bf2008-07-26 23:55:294
tfarina10a5c062015-09-04 18:47:575#include "ipc/ipc_sync_message.h"
[email protected]cd40b4a2008-12-22 23:58:526
avi246998d82015-12-22 02:39:047#include <stdint.h>
8
initial.commit09911bf2008-07-26 23:55:299#include <stack>
10
[email protected]1e9499c2010-04-06 20:33:3611#include "base/atomic_sequence_num.h"
initial.commit09911bf2008-07-26 23:55:2912#include "base/logging.h"
tfarina10a5c062015-09-04 18:47:5713#include "build/build_config.h"
initial.commit09911bf2008-07-26 23:55:2914
[email protected]76a6d452012-02-03 21:48:4315namespace {
16
[email protected]8a8443f2012-03-13 12:07:1917base::StaticAtomicSequenceNumber g_next_id;
18
19} // namespace
[email protected]76a6d452012-02-03 21:48:4320
initial.commit09911bf2008-07-26 23:55:2921namespace IPC {
22
initial.commit09911bf2008-07-26 23:55:2923#define kSyncMessageHeaderSize 4
24
tfarina10a5c062015-09-04 18:47:5725SyncMessage::SyncMessage(int32_t routing_id,
26 uint32_t type,
27 PriorityValue priority,
28 MessageReplyDeserializer* deserializer)
[email protected]753bb252013-11-04 22:28:1229 : Message(routing_id, type, priority),
rockot3c236292016-07-07 20:26:0230 deserializer_(deserializer) {
initial.commit09911bf2008-07-26 23:55:2931 set_sync();
32 set_unblock(true);
33
34 // Add synchronous message data before the message payload.
35 SyncHeader header;
[email protected]1e9499c2010-04-06 20:33:3636 header.message_id = g_next_id.GetNext();
initial.commit09911bf2008-07-26 23:55:2937 WriteSyncHeader(this, header);
38}
39
[email protected]40c4627d2011-09-09 21:10:3140SyncMessage::~SyncMessage() {
41}
42
initial.commit09911bf2008-07-26 23:55:2943MessageReplyDeserializer* SyncMessage::GetReplyDeserializer() {
[email protected]40c4627d2011-09-09 21:10:3144 DCHECK(deserializer_.get());
45 return deserializer_.release();
initial.commit09911bf2008-07-26 23:55:2946}
47
initial.commit09911bf2008-07-26 23:55:2948bool SyncMessage::IsMessageReplyTo(const Message& msg, int request_id) {
49 if (!msg.is_reply())
50 return false;
51
52 return GetMessageId(msg) == request_id;
53}
54
brettwbd4d7112015-06-03 04:29:2555base::PickleIterator SyncMessage::GetDataIterator(const Message* msg) {
56 base::PickleIterator iter(*msg);
[email protected]ce208f872012-03-07 20:42:5657 if (!iter.SkipBytes(kSyncMessageHeaderSize))
brettwbd4d7112015-06-03 04:29:2558 return base::PickleIterator();
[email protected]ce208f872012-03-07 20:42:5659 else
60 return iter;
initial.commit09911bf2008-07-26 23:55:2961}
62
63int SyncMessage::GetMessageId(const Message& msg) {
64 if (!msg.is_sync() && !msg.is_reply())
65 return 0;
66
67 SyncHeader header;
68 if (!ReadSyncHeader(msg, &header))
69 return 0;
70
71 return header.message_id;
72}
73
74Message* SyncMessage::GenerateReply(const Message* msg) {
75 DCHECK(msg->is_sync());
76
[email protected]753bb252013-11-04 22:28:1277 Message* reply = new Message(msg->routing_id(), IPC_REPLY_ID,
78 msg->priority());
initial.commit09911bf2008-07-26 23:55:2979 reply->set_reply();
80
81 SyncHeader header;
82
83 // use the same message id, but this time reply bit is set
84 header.message_id = GetMessageId(*msg);
85 WriteSyncHeader(reply, header);
86
87 return reply;
88}
89
90bool SyncMessage::ReadSyncHeader(const Message& msg, SyncHeader* header) {
91 DCHECK(msg.is_sync() || msg.is_reply());
92
brettwbd4d7112015-06-03 04:29:2593 base::PickleIterator iter(msg);
avi48fc13b2014-12-28 23:31:4894 bool result = iter.ReadInt(&header->message_id);
initial.commit09911bf2008-07-26 23:55:2995 if (!result) {
96 NOTREACHED();
97 return false;
98 }
99
100 return true;
101}
102
103bool SyncMessage::WriteSyncHeader(Message* msg, const SyncHeader& header) {
104 DCHECK(msg->is_sync() || msg->is_reply());
105 DCHECK(msg->payload_size() == 0);
initial.commit09911bf2008-07-26 23:55:29106 bool result = msg->WriteInt(header.message_id);
107 if (!result) {
108 NOTREACHED();
109 return false;
110 }
111
112 // Note: if you add anything here, you need to update kSyncMessageHeaderSize.
113 DCHECK(kSyncMessageHeaderSize == msg->payload_size());
114
115 return true;
116}
117
118
119bool MessageReplyDeserializer::SerializeOutputParameters(const Message& msg) {
120 return SerializeOutputParameters(msg, SyncMessage::GetDataIterator(&msg));
121}
122
123} // namespace IPC