blob: 339593e8f82fcefdea73d1ecba14f2c474b58c24 [file] [log] [blame]
Avi Drissmanea1be232022-09-14 23:29:061// Copyright 2012 The Chromium Authors
[email protected]946d1b22009-07-22 23:57:212// Use of this source code is governed by a BSD-style license that can be
3// found in the LICENSE file.
4
5#include "ipc/ipc_message_utils.h"
6
avi246998d82015-12-22 02:39:047#include <stddef.h>
8#include <stdint.h>
9
Adam Ricec62d8052023-08-03 05:48:4410#include <type_traits>
11
[email protected]57999812013-02-24 05:40:5212#include "base/files/file_path.h"
[email protected]93d49d72009-10-23 20:00:2013#include "base/json/json_writer.h"
Hans Wennborg24397592020-06-17 16:58:5014#include "base/logging.h"
jdoerrief1e72e32017-04-26 16:23:5515#include "base/memory/ptr_util.h"
Hans Wennborg5f62968b2021-04-22 18:44:0516#include "base/notreached.h"
[email protected]4aa794a12013-06-11 06:32:1817#include "base/strings/string_number_conversions.h"
Lei Zhange02299a2021-04-26 23:12:2418#include "base/strings/stringprintf.h"
[email protected]906265872013-06-07 22:40:4519#include "base/strings/utf_string_conversions.h"
[email protected]b43e5562013-06-28 15:20:0220#include "base/time/time.h"
tguilbert4a5ac602016-09-19 21:11:2521#include "base/unguessable_token.h"
avi246998d82015-12-22 02:39:0422#include "build/build_config.h"
[email protected]bf5aedf02012-06-04 21:18:2523#include "ipc/ipc_channel_handle.h"
Lei Zhang5226db72022-01-25 03:38:5524#include "ipc/ipc_message.h"
morrita1aa788c2015-01-31 05:45:4225#include "ipc/ipc_message_attachment.h"
morrita4b5c28e22015-01-14 21:17:0626#include "ipc/ipc_message_attachment_set.h"
amistry36182522016-06-27 06:34:4227#include "ipc/ipc_mojo_param_traits.h"
[email protected]bf5aedf02012-06-04 21:18:2528
Ali Jumadff201a2022-05-31 23:51:4129#if BUILDFLAG(IS_APPLE)
erikchenaf8299d2015-10-09 19:12:0630#include "ipc/mach_port_mac.h"
31#endif
32
Xiaohan Wangab909b32022-01-12 17:57:3933#if BUILDFLAG(IS_WIN)
[email protected]2e02cfe82012-11-21 00:58:0034#include <tchar.h>
erikchen5ea2ab72015-09-25 22:34:3135#include "ipc/handle_win.h"
erikchend804e1052017-04-29 02:24:3636#include "ipc/ipc_platform_file.h"
Xiaohan Wangab909b32022-01-12 17:57:3937#elif BUILDFLAG(IS_POSIX) || BUILDFLAG(IS_FUCHSIA)
Fabrice de Gans-Ribericbce4342018-05-07 20:02:0938#include "base/file_descriptor_posix.h"
39#include "ipc/ipc_platform_file_attachment_posix.h"
[email protected]7a4de7a62010-08-17 18:38:2440#endif
[email protected]946d1b22009-07-22 23:57:2141
Xiaohan Wangab909b32022-01-12 17:57:3942#if BUILDFLAG(IS_FUCHSIA)
Sergey Ulanov04367c72019-06-21 15:51:4343#include "base/fuchsia/fuchsia_logging.h"
Sergey Ulanova97f3282019-04-17 01:27:3444#include "ipc/handle_attachment_fuchsia.h"
Scott Graham3eebff02017-06-30 01:07:1045#endif
46
Xiaohan Wangab909b32022-01-12 17:57:3947#if BUILDFLAG(IS_ANDROID)
Ken Rockot097248f02018-04-23 16:23:3448#include "base/android/scoped_hardware_buffer_handle.h"
49#include "ipc/ipc_mojo_handle_attachment.h"
50#include "mojo/public/cpp/system/message_pipe.h"
51#include "mojo/public/cpp/system/scope_to_message_pipe.h"
52#endif
53
[email protected]946d1b22009-07-22 23:57:2154namespace IPC {
55
[email protected]bf5aedf02012-06-04 21:18:2556namespace {
57
joaodasilva383b174a2017-01-10 09:55:3658const int kMaxRecursionDepth = 200;
[email protected]946d1b22009-07-22 23:57:2159
[email protected]bf5aedf02012-06-04 21:18:2560template<typename CharType>
61void LogBytes(const std::vector<CharType>& data, std::string* out) {
Xiaohan Wangab909b32022-01-12 17:57:3962#if BUILDFLAG(IS_WIN)
[email protected]bf5aedf02012-06-04 21:18:2563 // Windows has a GUI for logging, which can handle arbitrary binary data.
64 for (size_t i = 0; i < data.size(); ++i)
65 out->push_back(data[i]);
Xiaohan Wangab909b32022-01-12 17:57:3966#elif BUILDFLAG(IS_POSIX) || BUILDFLAG(IS_FUCHSIA)
[email protected]bf5aedf02012-06-04 21:18:2567 // On POSIX, we log to stdout, which we assume can display ASCII.
68 static const size_t kMaxBytesToLog = 100;
69 for (size_t i = 0; i < std::min(data.size(), kMaxBytesToLog); ++i) {
70 if (isprint(data[i]))
71 out->push_back(data[i]);
72 else
[email protected]7d3cbc92013-03-18 22:33:0473 out->append(
74 base::StringPrintf("[%02X]", static_cast<unsigned char>(data[i])));
[email protected]bf5aedf02012-06-04 21:18:2575 }
76 if (data.size() > kMaxBytesToLog) {
[email protected]f8660f82013-03-30 17:29:2877 out->append(base::StringPrintf(
78 " and %u more bytes",
79 static_cast<unsigned>(data.size() - kMaxBytesToLog)));
[email protected]bf5aedf02012-06-04 21:18:2580 }
81#endif
82}
[email protected]946d1b22009-07-22 23:57:2183
Adam Ricec62d8052023-08-03 05:48:4484template <typename CharType>
85void WriteCharVector(base::Pickle* m, const std::vector<CharType>& p) {
86 static_assert(sizeof(CharType) == 1);
87 static_assert(std::is_integral_v<CharType>);
88 if (p.empty()) {
89 m->WriteData(nullptr, 0);
90 } else {
91 const char* data = reinterpret_cast<const char*>(p.data());
92 m->WriteData(data, p.size());
93 }
94}
95
96template <typename CharType>
97bool ReadCharVector(const base::Pickle* m,
98 base::PickleIterator* iter,
99 std::vector<CharType>* r) {
100 static_assert(sizeof(CharType) == 1);
101 static_assert(std::is_integral_v<CharType>);
102 const char* data;
103 size_t data_size = 0;
104 if (!iter->ReadData(&data, &data_size)) {
105 return false;
106 }
107 const CharType* begin = reinterpret_cast<const CharType*>(data);
108 const CharType* end = begin + data_size;
109 r->assign(begin, end);
110 return true;
111}
112
Fabrice de Gans43eebf702022-04-01 23:43:04113void WriteValue(const base::Value& value, int recursion, base::Pickle* pickle);
[email protected]946d1b22009-07-22 23:57:21114
Fabrice de Gans43eebf702022-04-01 23:43:04115void WriteDictValue(const base::Value::Dict& value,
116 int recursion,
117 base::Pickle* pickle) {
118 WriteParam(pickle, base::checked_cast<int>(value.size()));
119 for (const auto entry : value) {
120 WriteParam(pickle, entry.first);
121 WriteValue(entry.second, recursion + 1, pickle);
122 }
123}
124
125void WriteListValue(const base::Value::List& value,
126 int recursion,
127 base::Pickle* pickle) {
128 WriteParam(pickle, base::checked_cast<int>(value.size()));
129 for (const auto& entry : value) {
130 WriteValue(entry, recursion + 1, pickle);
131 }
132}
133
134void WriteValue(const base::Value& value, int recursion, base::Pickle* pickle) {
[email protected]dbc761a2012-07-26 01:29:21135 bool result;
[email protected]946d1b22009-07-22 23:57:21136 if (recursion > kMaxRecursionDepth) {
joaodasilva383b174a2017-01-10 09:55:36137 LOG(ERROR) << "Max recursion depth hit in WriteValue.";
[email protected]946d1b22009-07-22 23:57:21138 return;
139 }
140
Fabrice de Gans43eebf702022-04-01 23:43:04141 pickle->WriteInt(static_cast<int>(value.type()));
[email protected]946d1b22009-07-22 23:57:21142
Fabrice de Gans43eebf702022-04-01 23:43:04143 switch (value.type()) {
jdoerriedc72ee942016-12-07 15:43:28144 case base::Value::Type::NONE:
jdoerriee1b1f3a2019-03-16 04:08:01145 break;
jdoerriedc72ee942016-12-07 15:43:28146 case base::Value::Type::BOOLEAN: {
Fabrice de Gans43eebf702022-04-01 23:43:04147 WriteParam(pickle, value.GetBool());
[email protected]946d1b22009-07-22 23:57:21148 break;
149 }
jdoerriedc72ee942016-12-07 15:43:28150 case base::Value::Type::INTEGER: {
Fabrice de Gans43eebf702022-04-01 23:43:04151 DCHECK(value.is_int());
152 WriteParam(pickle, value.GetInt());
[email protected]946d1b22009-07-22 23:57:21153 break;
154 }
jdoerriedc72ee942016-12-07 15:43:28155 case base::Value::Type::DOUBLE: {
Fabrice de Gans43eebf702022-04-01 23:43:04156 DCHECK(value.is_int() || value.is_double());
157 WriteParam(pickle, value.GetDouble());
[email protected]946d1b22009-07-22 23:57:21158 break;
159 }
jdoerriedc72ee942016-12-07 15:43:28160 case base::Value::Type::STRING: {
Fabrice de Gans43eebf702022-04-01 23:43:04161 const std::string* val = value.GetIfString();
Sammie Quondab84eba2021-08-18 02:34:48162 result = !!val;
[email protected]dbc761a2012-07-26 01:29:21163 DCHECK(result);
Fabrice de Gans43eebf702022-04-01 23:43:04164 WriteParam(pickle, *val);
[email protected]946d1b22009-07-22 23:57:21165 break;
166 }
jdoerriedc72ee942016-12-07 15:43:28167 case base::Value::Type::BINARY: {
Fabrice de Gans43eebf702022-04-01 23:43:04168 pickle->WriteData(reinterpret_cast<const char*>(value.GetBlob().data()),
Peter Kasting28b51cf2022-06-28 15:02:43169 value.GetBlob().size());
[email protected]e4dad9fb2009-10-06 18:15:58170 break;
[email protected]946d1b22009-07-22 23:57:21171 }
Fabrice de Gans43eebf702022-04-01 23:43:04172 case base::Value::Type::DICT: {
173 DCHECK(value.is_dict());
174 WriteDictValue(value.GetDict(), recursion, pickle);
[email protected]946d1b22009-07-22 23:57:21175 break;
176 }
jdoerriedc72ee942016-12-07 15:43:28177 case base::Value::Type::LIST: {
Fabrice de Gans43eebf702022-04-01 23:43:04178 DCHECK(value.is_list());
179 WriteListValue(value.GetList(), recursion, pickle);
[email protected]946d1b22009-07-22 23:57:21180 break;
181 }
182 }
183}
184
Fabrice de Gans43eebf702022-04-01 23:43:04185bool ReadValue(const base::Pickle* pickle,
brettwbd4d7112015-06-03 04:29:25186 base::PickleIterator* iter,
Fabrice de Gans43eebf702022-04-01 23:43:04187 int recursion,
188 base::Value* value);
189
190// Helper for ReadValue that reads a Value::Dict into a pre-allocated object.
191bool ReadDictValue(const base::Pickle* pickle,
192 base::PickleIterator* iter,
193 int recursion,
194 base::Value::Dict* value) {
195 int size;
196 if (!ReadParam(pickle, iter, &size))
197 return false;
198
199 for (int i = 0; i < size; i++) {
200 std::string key;
201 base::Value subvalue;
202 if (!ReadParam(pickle, iter, &key) ||
203 !ReadValue(pickle, iter, recursion + 1, &subvalue)) {
204 return false;
205 }
206 value->Set(key, std::move(subvalue));
207 }
208
209 return true;
210}
211
212// Helper for ReadValue that reads a Value::List into a pre-allocated object.
213bool ReadListValue(const base::Pickle* pickle,
214 base::PickleIterator* iter,
215 int recursion,
216 base::Value::List* value) {
217 int size;
218 if (!ReadParam(pickle, iter, &size))
219 return false;
220
221 value->reserve(size);
222 for (int i = 0; i < size; i++) {
223 base::Value subval;
224 if (!ReadValue(pickle, iter, recursion + 1, &subval))
225 return false;
226 value->Append(std::move(subval));
227 }
228 return true;
229}
230
231bool ReadValue(const base::Pickle* pickle,
232 base::PickleIterator* iter,
233 int recursion,
234 base::Value* value) {
[email protected]946d1b22009-07-22 23:57:21235 if (recursion > kMaxRecursionDepth) {
joaodasilva383b174a2017-01-10 09:55:36236 LOG(ERROR) << "Max recursion depth hit in ReadValue.";
[email protected]946d1b22009-07-22 23:57:21237 return false;
238 }
239
240 int type;
Fabrice de Gans43eebf702022-04-01 23:43:04241 if (!ReadParam(pickle, iter, &type))
[email protected]946d1b22009-07-22 23:57:21242 return false;
243
Devlin Cronin7178a5bd2021-02-02 02:56:47244 constexpr int kMinValueType = static_cast<int>(base::Value::Type::NONE);
245 constexpr int kMaxValueType = static_cast<int>(base::Value::Type::LIST);
246 if (type > kMaxValueType || type < kMinValueType)
247 return false;
248
jdoerriedc72ee942016-12-07 15:43:28249 switch (static_cast<base::Value::Type>(type)) {
250 case base::Value::Type::NONE:
Jeremy Roman2d8d7802020-06-11 22:08:20251 *value = base::Value();
jdoerriee067999a2017-04-07 06:39:00252 break;
jdoerriedc72ee942016-12-07 15:43:28253 case base::Value::Type::BOOLEAN: {
[email protected]946d1b22009-07-22 23:57:21254 bool val;
Fabrice de Gans43eebf702022-04-01 23:43:04255 if (!ReadParam(pickle, iter, &val))
[email protected]946d1b22009-07-22 23:57:21256 return false;
Jeremy Roman2d8d7802020-06-11 22:08:20257 *value = base::Value(val);
[email protected]946d1b22009-07-22 23:57:21258 break;
259 }
jdoerriedc72ee942016-12-07 15:43:28260 case base::Value::Type::INTEGER: {
[email protected]946d1b22009-07-22 23:57:21261 int val;
Fabrice de Gans43eebf702022-04-01 23:43:04262 if (!ReadParam(pickle, iter, &val))
[email protected]946d1b22009-07-22 23:57:21263 return false;
Jeremy Roman2d8d7802020-06-11 22:08:20264 *value = base::Value(val);
[email protected]946d1b22009-07-22 23:57:21265 break;
266 }
jdoerriedc72ee942016-12-07 15:43:28267 case base::Value::Type::DOUBLE: {
[email protected]946d1b22009-07-22 23:57:21268 double val;
Fabrice de Gans43eebf702022-04-01 23:43:04269 if (!ReadParam(pickle, iter, &val))
[email protected]946d1b22009-07-22 23:57:21270 return false;
Jeremy Roman2d8d7802020-06-11 22:08:20271 *value = base::Value(val);
[email protected]946d1b22009-07-22 23:57:21272 break;
273 }
jdoerriedc72ee942016-12-07 15:43:28274 case base::Value::Type::STRING: {
[email protected]946d1b22009-07-22 23:57:21275 std::string val;
Fabrice de Gans43eebf702022-04-01 23:43:04276 if (!ReadParam(pickle, iter, &val))
[email protected]946d1b22009-07-22 23:57:21277 return false;
Jeremy Roman2d8d7802020-06-11 22:08:20278 *value = base::Value(std::move(val));
[email protected]946d1b22009-07-22 23:57:21279 break;
280 }
jdoerriedc72ee942016-12-07 15:43:28281 case base::Value::Type::BINARY: {
Claudio DeSouzac537f85d2023-03-02 18:42:52282 absl::optional<base::span<const uint8_t>> data = iter->ReadData();
283 if (!data) {
[email protected]e4dad9fb2009-10-06 18:15:58284 return false;
Claudio DeSouzac537f85d2023-03-02 18:42:52285 }
286 *value = base::Value(*data);
[email protected]946d1b22009-07-22 23:57:21287 break;
288 }
Avi Drissmand2a736f2023-01-28 02:31:26289 case base::Value::Type::DICT: {
Fabrice de Gans43eebf702022-04-01 23:43:04290 base::Value::Dict val;
291 if (!ReadDictValue(pickle, iter, recursion, &val))
[email protected]946d1b22009-07-22 23:57:21292 return false;
Fabrice de Gans43eebf702022-04-01 23:43:04293 *value = base::Value(std::move(val));
[email protected]946d1b22009-07-22 23:57:21294 break;
295 }
jdoerriedc72ee942016-12-07 15:43:28296 case base::Value::Type::LIST: {
Fabrice de Gans43eebf702022-04-01 23:43:04297 base::Value::List val;
298 if (!ReadListValue(pickle, iter, recursion, &val))
[email protected]946d1b22009-07-22 23:57:21299 return false;
Fabrice de Gans43eebf702022-04-01 23:43:04300 *value = base::Value(std::move(val));
[email protected]946d1b22009-07-22 23:57:21301 break;
302 }
[email protected]e4dad9fb2009-10-06 18:15:58303 default:
Jan Wilken Dörrie271086b42019-06-13 20:03:41304 NOTREACHED();
jdoerriee1b1f3a2019-03-16 04:08:01305 return false;
[email protected]946d1b22009-07-22 23:57:21306 }
307
308 return true;
309}
310
[email protected]bf5aedf02012-06-04 21:18:25311} // namespace
312
313// -----------------------------------------------------------------------------
314
315LogData::LogData()
316 : routing_id(0),
317 type(0),
318 sent(0),
319 receive(0),
320 dispatch(0) {
321}
322
vmpstrbf0d713a2016-03-24 20:22:54323LogData::LogData(const LogData& other) = default;
324
Chris Watkins2d879af2017-11-30 02:11:59325LogData::~LogData() = default;
[email protected]bf5aedf02012-06-04 21:18:25326
[email protected]bf5aedf02012-06-04 21:18:25327void ParamTraits<bool>::Log(const param_type& p, std::string* l) {
328 l->append(p ? "true" : "false");
329}
330
rockot502c94f2016-02-03 20:20:16331void ParamTraits<signed char>::Write(base::Pickle* m, const param_type& p) {
ortuno19ecf1842015-10-30 00:46:20332 m->WriteBytes(&p, sizeof(param_type));
333}
334
rockot502c94f2016-02-03 20:20:16335bool ParamTraits<signed char>::Read(const base::Pickle* m,
336 base::PickleIterator* iter,
337 param_type* r) {
ortuno19ecf1842015-10-30 00:46:20338 const char* data;
339 if (!iter->ReadBytes(&data, sizeof(param_type)))
340 return false;
341 memcpy(r, data, sizeof(param_type));
342 return true;
343}
344
345void ParamTraits<signed char>::Log(const param_type& p, std::string* l) {
Raul Tambref89a5102019-02-08 23:01:38346 l->append(base::NumberToString(p));
ortuno19ecf1842015-10-30 00:46:20347}
348
rockot502c94f2016-02-03 20:20:16349void ParamTraits<unsigned char>::Write(base::Pickle* m, const param_type& p) {
[email protected]c1ee48d2013-07-12 23:12:28350 m->WriteBytes(&p, sizeof(param_type));
351}
352
rockot502c94f2016-02-03 20:20:16353bool ParamTraits<unsigned char>::Read(const base::Pickle* m,
brettwbd4d7112015-06-03 04:29:25354 base::PickleIterator* iter,
355 param_type* r) {
[email protected]c1ee48d2013-07-12 23:12:28356 const char* data;
avi48fc13b2014-12-28 23:31:48357 if (!iter->ReadBytes(&data, sizeof(param_type)))
[email protected]c1ee48d2013-07-12 23:12:28358 return false;
359 memcpy(r, data, sizeof(param_type));
360 return true;
361}
362
363void ParamTraits<unsigned char>::Log(const param_type& p, std::string* l) {
Raul Tambref89a5102019-02-08 23:01:38364 l->append(base::NumberToString(p));
[email protected]c1ee48d2013-07-12 23:12:28365}
366
rockot502c94f2016-02-03 20:20:16367void ParamTraits<unsigned short>::Write(base::Pickle* m, const param_type& p) {
[email protected]c1ee48d2013-07-12 23:12:28368 m->WriteBytes(&p, sizeof(param_type));
369}
370
rockot502c94f2016-02-03 20:20:16371bool ParamTraits<unsigned short>::Read(const base::Pickle* m,
brettwbd4d7112015-06-03 04:29:25372 base::PickleIterator* iter,
[email protected]c1ee48d2013-07-12 23:12:28373 param_type* r) {
374 const char* data;
avi48fc13b2014-12-28 23:31:48375 if (!iter->ReadBytes(&data, sizeof(param_type)))
[email protected]c1ee48d2013-07-12 23:12:28376 return false;
377 memcpy(r, data, sizeof(param_type));
378 return true;
379}
380
381void ParamTraits<unsigned short>::Log(const param_type& p, std::string* l) {
Daniel Cheng3d199b12017-12-12 03:51:09382 l->append(base::NumberToString(p));
[email protected]c1ee48d2013-07-12 23:12:28383}
384
[email protected]252cad62010-08-18 18:33:57385void ParamTraits<int>::Log(const param_type& p, std::string* l) {
Daniel Cheng3d199b12017-12-12 03:51:09386 l->append(base::NumberToString(p));
[email protected]252cad62010-08-18 18:33:57387}
388
389void ParamTraits<unsigned int>::Log(const param_type& p, std::string* l) {
Daniel Cheng3d199b12017-12-12 03:51:09390 l->append(base::NumberToString(p));
[email protected]252cad62010-08-18 18:33:57391}
392
Xiaohan Wangab909b32022-01-12 17:57:39393#if BUILDFLAG(IS_WIN) || BUILDFLAG(IS_LINUX) || BUILDFLAG(IS_CHROMEOS) || \
394 BUILDFLAG(IS_FUCHSIA) || \
395 (BUILDFLAG(IS_ANDROID) && defined(ARCH_CPU_64_BITS))
[email protected]252cad62010-08-18 18:33:57396void ParamTraits<long>::Log(const param_type& p, std::string* l) {
Daniel Cheng3d199b12017-12-12 03:51:09397 l->append(base::NumberToString(p));
[email protected]252cad62010-08-18 18:33:57398}
399
400void ParamTraits<unsigned long>::Log(const param_type& p, std::string* l) {
Daniel Cheng3d199b12017-12-12 03:51:09401 l->append(base::NumberToString(p));
[email protected]252cad62010-08-18 18:33:57402}
jam03d8a782016-02-10 20:13:39403#endif
[email protected]252cad62010-08-18 18:33:57404
405void ParamTraits<long long>::Log(const param_type& p, std::string* l) {
Daniel Cheng3d199b12017-12-12 03:51:09406 l->append(base::NumberToString(p));
[email protected]252cad62010-08-18 18:33:57407}
408
409void ParamTraits<unsigned long long>::Log(const param_type& p, std::string* l) {
Daniel Cheng3d199b12017-12-12 03:51:09410 l->append(base::NumberToString(p));
[email protected]252cad62010-08-18 18:33:57411}
[email protected]7a4de7a62010-08-17 18:38:24412
[email protected]bf5aedf02012-06-04 21:18:25413void ParamTraits<float>::Log(const param_type& p, std::string* l) {
[email protected]7d3cbc92013-03-18 22:33:04414 l->append(base::StringPrintf("%e", p));
[email protected]7a4de7a62010-08-17 18:38:24415}
416
rockot502c94f2016-02-03 20:20:16417void ParamTraits<double>::Write(base::Pickle* m, const param_type& p) {
[email protected]48328ff2013-10-31 09:27:31418 m->WriteBytes(reinterpret_cast<const char*>(&p), sizeof(param_type));
[email protected]d84e48b2010-10-21 22:04:52419}
420
rockot502c94f2016-02-03 20:20:16421bool ParamTraits<double>::Read(const base::Pickle* m,
brettwbd4d7112015-06-03 04:29:25422 base::PickleIterator* iter,
[email protected]bf5aedf02012-06-04 21:18:25423 param_type* r) {
424 const char *data;
avi48fc13b2014-12-28 23:31:48425 if (!iter->ReadBytes(&data, sizeof(*r))) {
[email protected]bf5aedf02012-06-04 21:18:25426 NOTREACHED();
427 return false;
428 }
429 memcpy(r, data, sizeof(param_type));
430 return true;
[email protected]d84e48b2010-10-21 22:04:52431}
432
[email protected]bf5aedf02012-06-04 21:18:25433void ParamTraits<double>::Log(const param_type& p, std::string* l) {
[email protected]7d3cbc92013-03-18 22:33:04434 l->append(base::StringPrintf("%e", p));
[email protected]1d14f582011-09-02 20:42:04435}
436
[email protected]bf5aedf02012-06-04 21:18:25437
438void ParamTraits<std::string>::Log(const param_type& p, std::string* l) {
439 l->append(p);
[email protected]1d14f582011-09-02 20:42:04440}
441
Jan Wilken Dörrie739ccc212021-03-11 18:13:05442void ParamTraits<std::u16string>::Log(const param_type& p, std::string* l) {
[email protected]ad65a3e2013-12-25 18:18:01443 l->append(base::UTF16ToUTF8(p));
[email protected]bf5aedf02012-06-04 21:18:25444}
[email protected]bf5aedf02012-06-04 21:18:25445
Xiaohan Wangab909b32022-01-12 17:57:39446#if BUILDFLAG(IS_WIN)
Jan Wilken Dörriecf5a66902020-12-07 20:51:31447bool ParamTraits<std::wstring>::Read(const base::Pickle* m,
448 base::PickleIterator* iter,
449 param_type* r) {
450 base::StringPiece16 piece16;
451 if (!iter->ReadStringPiece16(&piece16))
452 return false;
453
454 *r = base::AsWString(piece16);
455 return true;
456}
457
458void ParamTraits<std::wstring>::Log(const param_type& p, std::string* l) {
459 l->append(base::WideToUTF8(p));
460}
461#endif
462
rockot502c94f2016-02-03 20:20:16463void ParamTraits<std::vector<char>>::Write(base::Pickle* m,
464 const param_type& p) {
Adam Ricec62d8052023-08-03 05:48:44465 WriteCharVector(m, p);
[email protected]bf5aedf02012-06-04 21:18:25466}
467
rockot502c94f2016-02-03 20:20:16468bool ParamTraits<std::vector<char>>::Read(const base::Pickle* m,
brettwbd4d7112015-06-03 04:29:25469 base::PickleIterator* iter,
470 param_type* r) {
Adam Ricec62d8052023-08-03 05:48:44471 return ReadCharVector(m, iter, r);
[email protected]bf5aedf02012-06-04 21:18:25472}
473
474void ParamTraits<std::vector<char> >::Log(const param_type& p, std::string* l) {
475 LogBytes(p, l);
476}
477
rockot502c94f2016-02-03 20:20:16478void ParamTraits<std::vector<unsigned char>>::Write(base::Pickle* m,
479 const param_type& p) {
Adam Ricec62d8052023-08-03 05:48:44480 WriteCharVector(m, p);
[email protected]bf5aedf02012-06-04 21:18:25481}
482
rockot502c94f2016-02-03 20:20:16483bool ParamTraits<std::vector<unsigned char>>::Read(const base::Pickle* m,
brettwbd4d7112015-06-03 04:29:25484 base::PickleIterator* iter,
485 param_type* r) {
Adam Ricec62d8052023-08-03 05:48:44486 return ReadCharVector(m, iter, r);
[email protected]bf5aedf02012-06-04 21:18:25487}
488
489void ParamTraits<std::vector<unsigned char> >::Log(const param_type& p,
490 std::string* l) {
491 LogBytes(p, l);
492}
493
rockot502c94f2016-02-03 20:20:16494void ParamTraits<std::vector<bool>>::Write(base::Pickle* m,
495 const param_type& p) {
Chris Palmerc5ea9b92017-09-25 22:53:22496 WriteParam(m, base::checked_cast<int>(p.size()));
[email protected]d4124852013-03-20 20:25:00497 // Cast to bool below is required because libc++'s
498 // vector<bool>::const_reference is different from bool, and we want to avoid
499 // writing an extra specialization of ParamTraits for it.
[email protected]bf5aedf02012-06-04 21:18:25500 for (size_t i = 0; i < p.size(); i++)
[email protected]d4124852013-03-20 20:25:00501 WriteParam(m, static_cast<bool>(p[i]));
[email protected]bf5aedf02012-06-04 21:18:25502}
503
rockot502c94f2016-02-03 20:20:16504bool ParamTraits<std::vector<bool>>::Read(const base::Pickle* m,
brettwbd4d7112015-06-03 04:29:25505 base::PickleIterator* iter,
506 param_type* r) {
Peter Kasting28b51cf2022-06-28 15:02:43507 size_t size;
avi48fc13b2014-12-28 23:31:48508 if (!iter->ReadLength(&size))
[email protected]bf5aedf02012-06-04 21:18:25509 return false;
510 r->resize(size);
Peter Kasting28b51cf2022-06-28 15:02:43511 for (size_t i = 0; i < size; i++) {
[email protected]bf5aedf02012-06-04 21:18:25512 bool value;
513 if (!ReadParam(m, iter, &value))
514 return false;
515 (*r)[i] = value;
516 }
517 return true;
518}
519
520void ParamTraits<std::vector<bool> >::Log(const param_type& p, std::string* l) {
521 for (size_t i = 0; i < p.size(); ++i) {
522 if (i != 0)
523 l->push_back(' ');
[email protected]d4124852013-03-20 20:25:00524 LogParam(static_cast<bool>(p[i]), l);
[email protected]bf5aedf02012-06-04 21:18:25525 }
[email protected]d84e48b2010-10-21 22:04:52526}
527
Fabrice de Gans43eebf702022-04-01 23:43:04528void ParamTraits<base::Value::Dict>::Write(base::Pickle* m,
529 const param_type& p) {
530 WriteDictValue(p, 0, m);
531}
532
533bool ParamTraits<base::Value::Dict>::Read(const base::Pickle* m,
534 base::PickleIterator* iter,
535 param_type* r) {
536 return ReadDictValue(m, iter, 0, r);
537}
538
539void ParamTraits<base::Value::Dict>::Log(const param_type& p, std::string* l) {
540 std::string json;
541 base::JSONWriter::Write(p, &json);
542 l->append(json);
543}
544
Xiaohan Wangab909b32022-01-12 17:57:39545#if BUILDFLAG(IS_POSIX) || BUILDFLAG(IS_FUCHSIA)
rockot502c94f2016-02-03 20:20:16546void ParamTraits<base::FileDescriptor>::Write(base::Pickle* m,
547 const param_type& p) {
erikchen14525202017-05-06 19:16:51548 // This serialization must be kept in sync with
erikchen9d6afd712017-05-18 17:49:06549 // nacl_message_scanner.cc:WriteHandle().
[email protected]7a4de7a62010-08-17 18:38:24550 const bool valid = p.fd >= 0;
551 WriteParam(m, valid);
552
morrita96693852014-09-24 20:11:45553 if (!valid)
554 return;
555
556 if (p.auto_close) {
morrita1aa788c2015-01-31 05:45:42557 if (!m->WriteAttachment(
558 new internal::PlatformFileAttachment(base::ScopedFD(p.fd))))
morrita96693852014-09-24 20:11:45559 NOTREACHED();
560 } else {
morrita1aa788c2015-01-31 05:45:42561 if (!m->WriteAttachment(new internal::PlatformFileAttachment(p.fd)))
[email protected]7a4de7a62010-08-17 18:38:24562 NOTREACHED();
563 }
564}
565
rockot502c94f2016-02-03 20:20:16566bool ParamTraits<base::FileDescriptor>::Read(const base::Pickle* m,
brettwbd4d7112015-06-03 04:29:25567 base::PickleIterator* iter,
[email protected]7a4de7a62010-08-17 18:38:24568 param_type* r) {
morrita96693852014-09-24 20:11:45569 *r = base::FileDescriptor();
570
[email protected]7a4de7a62010-08-17 18:38:24571 bool valid;
572 if (!ReadParam(m, iter, &valid))
573 return false;
574
morrita96693852014-09-24 20:11:45575 if (!valid)
[email protected]7a4de7a62010-08-17 18:38:24576 return true;
[email protected]7a4de7a62010-08-17 18:38:24577
rockot502c94f2016-02-03 20:20:16578 scoped_refptr<base::Pickle::Attachment> attachment;
morrita1aa788c2015-01-31 05:45:42579 if (!m->ReadAttachment(iter, &attachment))
morrita96693852014-09-24 20:11:45580 return false;
581
sammc6ed3efb2016-11-23 03:17:35582 if (static_cast<MessageAttachment*>(attachment.get())->GetType() !=
583 MessageAttachment::Type::PLATFORM_FILE) {
584 return false;
585 }
586
rockot502c94f2016-02-03 20:20:16587 *r = base::FileDescriptor(
sammc6ed3efb2016-11-23 03:17:35588 static_cast<internal::PlatformFileAttachment*>(attachment.get())
589 ->TakePlatformFile(),
rockot502c94f2016-02-03 20:20:16590 true);
morrita96693852014-09-24 20:11:45591 return true;
[email protected]7a4de7a62010-08-17 18:38:24592}
593
594void ParamTraits<base::FileDescriptor>::Log(const param_type& p,
[email protected]252cad62010-08-18 18:33:57595 std::string* l) {
[email protected]7a4de7a62010-08-17 18:38:24596 if (p.auto_close) {
[email protected]7d3cbc92013-03-18 22:33:04597 l->append(base::StringPrintf("FD(%d auto-close)", p.fd));
[email protected]7a4de7a62010-08-17 18:38:24598 } else {
[email protected]7d3cbc92013-03-18 22:33:04599 l->append(base::StringPrintf("FD(%d)", p.fd));
[email protected]7a4de7a62010-08-17 18:38:24600 }
601}
Sergey Ulanovac89bb92019-03-22 18:46:49602
603void ParamTraits<base::ScopedFD>::Write(base::Pickle* m, const param_type& p) {
604 // This serialization must be kept in sync with
605 // nacl_message_scanner.cc:WriteHandle().
606 const bool valid = p.is_valid();
607 WriteParam(m, valid);
608
609 if (!valid)
610 return;
611
612 if (!m->WriteAttachment(new internal::PlatformFileAttachment(
613 std::move(const_cast<param_type&>(p))))) {
614 NOTREACHED();
615 }
616}
617
618bool ParamTraits<base::ScopedFD>::Read(const base::Pickle* m,
619 base::PickleIterator* iter,
620 param_type* r) {
621 r->reset();
622
623 bool valid;
624 if (!ReadParam(m, iter, &valid))
625 return false;
626
627 if (!valid)
628 return true;
629
630 scoped_refptr<base::Pickle::Attachment> attachment;
631 if (!m->ReadAttachment(iter, &attachment))
632 return false;
633
634 if (static_cast<MessageAttachment*>(attachment.get())->GetType() !=
635 MessageAttachment::Type::PLATFORM_FILE) {
636 return false;
637 }
638
639 *r = base::ScopedFD(
640 static_cast<internal::PlatformFileAttachment*>(attachment.get())
641 ->TakePlatformFile());
642 return true;
643}
644
645void ParamTraits<base::ScopedFD>::Log(const param_type& p, std::string* l) {
646 l->append(base::StringPrintf("ScopedFD(%d)", p.get()));
647}
Xiaohan Wangab909b32022-01-12 17:57:39648#endif // BUILDFLAG(IS_POSIX) || BUILDFLAG(IS_FUCHSIA)
[email protected]7a4de7a62010-08-17 18:38:24649
Xiaohan Wangab909b32022-01-12 17:57:39650#if BUILDFLAG(IS_WIN)
Robert Sesek02910662020-02-28 20:15:51651void ParamTraits<base::win::ScopedHandle>::Write(base::Pickle* m,
652 const param_type& p) {
653 const bool valid = p.IsValid();
654 WriteParam(m, valid);
655 if (!valid)
656 return;
657
658 HandleWin handle(p.Get());
659 WriteParam(m, handle);
660}
661
662bool ParamTraits<base::win::ScopedHandle>::Read(const base::Pickle* m,
663 base::PickleIterator* iter,
664 param_type* r) {
665 r->Close();
666
667 bool valid;
668 if (!ReadParam(m, iter, &valid))
669 return false;
670 if (!valid)
671 return true;
672
673 HandleWin handle;
674 if (!ReadParam(m, iter, &handle))
675 return false;
676
677 r->Set(handle.get_handle());
678 return true;
679}
680
681void ParamTraits<base::win::ScopedHandle>::Log(const param_type& p,
682 std::string* l) {
683 l->append(base::StringPrintf("ScopedHandle(%p)", p.Get()));
684}
Xiaohan Wangab909b32022-01-12 17:57:39685#endif // BUILDFLAG(IS_WIN)
Robert Sesek02910662020-02-28 20:15:51686
Xiaohan Wangab909b32022-01-12 17:57:39687#if BUILDFLAG(IS_FUCHSIA)
Sergey Ulanova97f3282019-04-17 01:27:34688void ParamTraits<zx::vmo>::Write(base::Pickle* m, const param_type& p) {
689 // This serialization must be kept in sync with
690 // nacl_message_scanner.cc:WriteHandle().
691 const bool valid = p.is_valid();
692 WriteParam(m, valid);
693
694 if (!valid)
695 return;
696
697 if (!m->WriteAttachment(new internal::HandleAttachmentFuchsia(
Sergey Ulanov04367c72019-06-21 15:51:43698 std::move(const_cast<param_type&>(p))))) {
Sergey Ulanova97f3282019-04-17 01:27:34699 NOTREACHED();
700 }
701}
702
703bool ParamTraits<zx::vmo>::Read(const base::Pickle* m,
704 base::PickleIterator* iter,
705 param_type* r) {
706 r->reset();
707
708 bool valid;
709 if (!ReadParam(m, iter, &valid))
710 return false;
711
712 if (!valid)
713 return true;
714
715 scoped_refptr<base::Pickle::Attachment> attachment;
716 if (!m->ReadAttachment(iter, &attachment))
717 return false;
718
719 if (static_cast<MessageAttachment*>(attachment.get())->GetType() !=
720 MessageAttachment::Type::FUCHSIA_HANDLE) {
721 return false;
722 }
723
724 *r = zx::vmo(static_cast<internal::HandleAttachmentFuchsia*>(attachment.get())
725 ->Take());
726 return true;
727}
728
729void ParamTraits<zx::vmo>::Log(const param_type& p, std::string* l) {
730 l->append("ZirconVMO");
731}
Sergey Ulanov7b343ff2019-08-15 07:52:37732
733void ParamTraits<zx::channel>::Write(base::Pickle* m, const param_type& p) {
734 // This serialization must be kept in sync with
735 // nacl_message_scanner.cc:WriteHandle().
736 const bool valid = p.is_valid();
737 WriteParam(m, valid);
738
739 if (!valid)
740 return;
741
742 if (!m->WriteAttachment(new internal::HandleAttachmentFuchsia(
743 std::move(const_cast<param_type&>(p))))) {
744 NOTREACHED();
745 }
746}
747
748bool ParamTraits<zx::channel>::Read(const base::Pickle* m,
749 base::PickleIterator* iter,
750 param_type* r) {
751 r->reset();
752
753 bool valid;
754 if (!ReadParam(m, iter, &valid))
755 return false;
756
757 if (!valid)
758 return true;
759
760 scoped_refptr<base::Pickle::Attachment> attachment;
761 if (!m->ReadAttachment(iter, &attachment))
762 return false;
763
764 if (static_cast<MessageAttachment*>(attachment.get())->GetType() !=
765 MessageAttachment::Type::FUCHSIA_HANDLE) {
766 return false;
767 }
768
769 *r = zx::channel(
770 static_cast<internal::HandleAttachmentFuchsia*>(attachment.get())
771 ->Take());
772 return true;
773}
774
775void ParamTraits<zx::channel>::Log(const param_type& p, std::string* l) {
776 l->append("ZirconChannel");
777}
Xiaohan Wangab909b32022-01-12 17:57:39778#endif // BUILDFLAG(IS_FUCHSIA)
Sergey Ulanova97f3282019-04-17 01:27:34779
Xiaohan Wangab909b32022-01-12 17:57:39780#if BUILDFLAG(IS_ANDROID)
Alexandr Ilin0443a8f2018-07-20 20:14:50781void ParamTraits<base::android::ScopedHardwareBufferHandle>::Write(
782 base::Pickle* m,
783 const param_type& p) {
784 const bool is_valid = p.is_valid();
Ken Rockot097248f02018-04-23 16:23:34785 WriteParam(m, is_valid);
786 if (!is_valid)
787 return;
788
Ken Rockot097248f02018-04-23 16:23:34789 // We must keep a ref to the AHardwareBuffer alive until the receiver has
790 // acquired its own reference. We do this by sending a message pipe handle
791 // along with the buffer. When the receiver deserializes (or even if they
792 // die without ever reading the message) their end of the pipe will be
793 // closed. We will eventually detect this and release the AHB reference.
794 mojo::MessagePipe tracking_pipe;
795 m->WriteAttachment(new internal::MojoHandleAttachment(
796 mojo::ScopedHandle::From(std::move(tracking_pipe.handle0))));
Alexandr Ilin0443a8f2018-07-20 20:14:50797 WriteParam(m, base::FileDescriptor(p.SerializeAsFileDescriptor().release(),
798 true /* auto_close */));
Ken Rockot097248f02018-04-23 16:23:34799
800 // Pass ownership of the input handle to our tracking pipe to keep the AHB
801 // alive long enough to be deserialized by the receiver.
Alexandr Ilin0443a8f2018-07-20 20:14:50802 mojo::ScopeToMessagePipe(std::move(const_cast<param_type&>(p)),
803 std::move(tracking_pipe.handle1));
Klaus Weidner3824a8882017-11-03 06:24:57804}
805
Alexandr Ilin0443a8f2018-07-20 20:14:50806bool ParamTraits<base::android::ScopedHardwareBufferHandle>::Read(
807 const base::Pickle* m,
808 base::PickleIterator* iter,
809 param_type* r) {
810 *r = base::android::ScopedHardwareBufferHandle();
Ken Rockot097248f02018-04-23 16:23:34811
812 bool is_valid;
813 if (!ReadParam(m, iter, &is_valid))
Klaus Weidner3824a8882017-11-03 06:24:57814 return false;
Ken Rockot097248f02018-04-23 16:23:34815 if (!is_valid)
816 return true;
817
818 scoped_refptr<base::Pickle::Attachment> tracking_pipe_attachment;
819 if (!m->ReadAttachment(iter, &tracking_pipe_attachment))
Klaus Weidner3824a8882017-11-03 06:24:57820 return false;
Ken Rockot097248f02018-04-23 16:23:34821
822 // We keep this alive until the AHB is safely deserialized below. When this
823 // goes out of scope, the sender holding the other end of this pipe will treat
824 // this handle closure as a signal that it's safe to release their AHB
825 // keepalive ref.
826 mojo::ScopedHandle tracking_pipe =
827 static_cast<MessageAttachment*>(tracking_pipe_attachment.get())
828 ->TakeMojoHandle();
829
830 base::FileDescriptor descriptor;
831 if (!ReadParam(m, iter, &descriptor))
832 return false;
833
834 // NOTE: It is valid to deserialize an invalid FileDescriptor, so the success
835 // of |ReadParam()| above does not imply that |descriptor| is valid.
836 base::ScopedFD scoped_fd(descriptor.fd);
837 if (!scoped_fd.is_valid())
838 return false;
839
840 *r = base::android::ScopedHardwareBufferHandle::DeserializeFromFileDescriptor(
Alexandr Ilin0443a8f2018-07-20 20:14:50841 std::move(scoped_fd));
Klaus Weidner3824a8882017-11-03 06:24:57842 return true;
843}
844
Alexandr Ilin0443a8f2018-07-20 20:14:50845void ParamTraits<base::android::ScopedHardwareBufferHandle>::Log(
846 const param_type& p,
847 std::string* l) {
848 l->append(base::StringPrintf("base::android::ScopedHardwareBufferHandle(%p)",
849 p.get()));
Klaus Weidner3824a8882017-11-03 06:24:57850}
Xiaohan Wangab909b32022-01-12 17:57:39851#endif // BUILDFLAG(IS_ANDROID)
Klaus Weidner3824a8882017-11-03 06:24:57852
Alexandr Ilind497eee2018-04-19 22:50:54853void ParamTraits<base::ReadOnlySharedMemoryRegion>::Write(base::Pickle* m,
854 const param_type& p) {
855 base::subtle::PlatformSharedMemoryRegion handle =
856 base::ReadOnlySharedMemoryRegion::TakeHandleForSerialization(
857 std::move(const_cast<param_type&>(p)));
858 WriteParam(m, std::move(handle));
859}
860
861bool ParamTraits<base::ReadOnlySharedMemoryRegion>::Read(
862 const base::Pickle* m,
863 base::PickleIterator* iter,
864 param_type* r) {
865 base::subtle::PlatformSharedMemoryRegion handle;
866 if (!ReadParam(m, iter, &handle))
867 return false;
868
869 *r = base::ReadOnlySharedMemoryRegion::Deserialize(std::move(handle));
870 return true;
871}
872
873void ParamTraits<base::ReadOnlySharedMemoryRegion>::Log(const param_type& p,
874 std::string* l) {
875 *l = "<base::ReadOnlySharedMemoryRegion>";
876 // TODO(alexilin): currently there is no way to access underlying handle
877 // without destructing a ReadOnlySharedMemoryRegion instance.
878}
879
880void ParamTraits<base::WritableSharedMemoryRegion>::Write(base::Pickle* m,
881 const param_type& p) {
882 base::subtle::PlatformSharedMemoryRegion handle =
883 base::WritableSharedMemoryRegion::TakeHandleForSerialization(
884 std::move(const_cast<param_type&>(p)));
885 WriteParam(m, std::move(handle));
886}
887
888bool ParamTraits<base::WritableSharedMemoryRegion>::Read(
889 const base::Pickle* m,
890 base::PickleIterator* iter,
891 param_type* r) {
892 base::subtle::PlatformSharedMemoryRegion handle;
893 if (!ReadParam(m, iter, &handle))
894 return false;
895
896 *r = base::WritableSharedMemoryRegion::Deserialize(std::move(handle));
897 return true;
898}
899
900void ParamTraits<base::WritableSharedMemoryRegion>::Log(const param_type& p,
901 std::string* l) {
902 *l = "<base::WritableSharedMemoryRegion>";
903 // TODO(alexilin): currently there is no way to access underlying handle
904 // without destructing a ReadOnlySharedMemoryRegion instance.
905}
906
907void ParamTraits<base::UnsafeSharedMemoryRegion>::Write(base::Pickle* m,
908 const param_type& p) {
909 base::subtle::PlatformSharedMemoryRegion handle =
910 base::UnsafeSharedMemoryRegion::TakeHandleForSerialization(
911 std::move(const_cast<param_type&>(p)));
912 WriteParam(m, std::move(handle));
913}
914
915bool ParamTraits<base::UnsafeSharedMemoryRegion>::Read(
916 const base::Pickle* m,
917 base::PickleIterator* iter,
918 param_type* r) {
919 base::subtle::PlatformSharedMemoryRegion handle;
920 if (!ReadParam(m, iter, &handle))
921 return false;
922
923 *r = base::UnsafeSharedMemoryRegion::Deserialize(std::move(handle));
924 return true;
925}
926
927void ParamTraits<base::UnsafeSharedMemoryRegion>::Log(const param_type& p,
928 std::string* l) {
929 *l = "<base::UnsafeSharedMemoryRegion>";
930 // TODO(alexilin): currently there is no way to access underlying handle
931 // without destructing a ReadOnlySharedMemoryRegion instance.
932}
933
934void ParamTraits<base::subtle::PlatformSharedMemoryRegion>::Write(
935 base::Pickle* m,
936 const param_type& p) {
Alexandr Ilinebab9da2018-06-01 02:37:47937 // This serialization must be kept in sync with
938 // nacl_message_scanner.cc::WriteHandle().
Alexandr Ilind497eee2018-04-19 22:50:54939 const bool valid = p.IsValid();
940 WriteParam(m, valid);
941
942 if (!valid)
943 return;
944
945 WriteParam(m, p.GetMode());
946 WriteParam(m, static_cast<uint64_t>(p.GetSize()));
947 WriteParam(m, p.GetGUID());
948
Xiaohan Wangab909b32022-01-12 17:57:39949#if BUILDFLAG(IS_WIN)
Fabrice de Gans-Ribericbce4342018-05-07 20:02:09950 base::win::ScopedHandle h = const_cast<param_type&>(p).PassPlatformHandle();
Alexandr Ilin6544b8a2018-08-15 23:08:54951 HandleWin handle_win(h.Get());
Fabrice de Gans-Ribericbce4342018-05-07 20:02:09952 WriteParam(m, handle_win);
Xiaohan Wangab909b32022-01-12 17:57:39953#elif BUILDFLAG(IS_FUCHSIA)
Sergey Ulanov04367c72019-06-21 15:51:43954 zx::vmo vmo = const_cast<param_type&>(p).PassPlatformHandle();
955 WriteParam(m, vmo);
Ali Jumadff201a2022-05-31 23:51:41956#elif BUILDFLAG(IS_APPLE)
Fabrice de Gans-Ribericbce4342018-05-07 20:02:09957 base::mac::ScopedMachSendRight h =
958 const_cast<param_type&>(p).PassPlatformHandle();
Alexandr Ilin6544b8a2018-08-15 23:08:54959 MachPortMac mach_port_mac(h.get());
Fabrice de Gans-Ribericbce4342018-05-07 20:02:09960 WriteParam(m, mach_port_mac);
Xiaohan Wangab909b32022-01-12 17:57:39961#elif BUILDFLAG(IS_ANDROID)
Alexandr Ilind497eee2018-04-19 22:50:54962 m->WriteAttachment(new internal::PlatformFileAttachment(
963 base::ScopedFD(const_cast<param_type&>(p).PassPlatformHandle())));
Xiaohan Wangab909b32022-01-12 17:57:39964#elif BUILDFLAG(IS_POSIX)
Alexandr Ilind497eee2018-04-19 22:50:54965 base::subtle::ScopedFDPair h =
966 const_cast<param_type&>(p).PassPlatformHandle();
967 m->WriteAttachment(new internal::PlatformFileAttachment(std::move(h.fd)));
968 if (p.GetMode() ==
969 base::subtle::PlatformSharedMemoryRegion::Mode::kWritable) {
970 m->WriteAttachment(
971 new internal::PlatformFileAttachment(std::move(h.readonly_fd)));
972 }
973#endif
974}
975
976bool ParamTraits<base::subtle::PlatformSharedMemoryRegion>::Read(
977 const base::Pickle* m,
978 base::PickleIterator* iter,
979 param_type* r) {
980 bool valid;
981 if (!ReadParam(m, iter, &valid))
982 return false;
983 if (!valid) {
984 *r = base::subtle::PlatformSharedMemoryRegion();
985 return true;
986 }
987
988 base::subtle::PlatformSharedMemoryRegion::Mode mode;
989 uint64_t shm_size;
990 base::UnguessableToken guid;
991 if (!ReadParam(m, iter, &mode) || !ReadParam(m, iter, &shm_size) ||
992 !base::IsValueInRangeForNumericType<size_t>(shm_size) ||
993 !ReadParam(m, iter, &guid)) {
994 return false;
995 }
996 size_t size = static_cast<size_t>(shm_size);
997
Xiaohan Wangab909b32022-01-12 17:57:39998#if BUILDFLAG(IS_WIN)
Fabrice de Gans-Ribericbce4342018-05-07 20:02:09999 HandleWin handle_win;
1000 if (!ReadParam(m, iter, &handle_win))
Alexandr Ilind497eee2018-04-19 22:50:541001 return false;
1002 *r = base::subtle::PlatformSharedMemoryRegion::Take(
Fabrice de Gans-Ribericbce4342018-05-07 20:02:091003 base::win::ScopedHandle(handle_win.get_handle()), mode, size, guid);
Xiaohan Wangab909b32022-01-12 17:57:391004#elif BUILDFLAG(IS_FUCHSIA)
Sergey Ulanov04367c72019-06-21 15:51:431005 zx::vmo vmo;
1006 if (!ReadParam(m, iter, &vmo))
Alexandr Ilind497eee2018-04-19 22:50:541007 return false;
Sergey Ulanov04367c72019-06-21 15:51:431008 *r = base::subtle::PlatformSharedMemoryRegion::Take(std::move(vmo), mode,
1009 size, guid);
Ali Jumadff201a2022-05-31 23:51:411010#elif BUILDFLAG(IS_APPLE)
Fabrice de Gans-Ribericbce4342018-05-07 20:02:091011 MachPortMac mach_port_mac;
1012 if (!ReadParam(m, iter, &mach_port_mac))
Alexandr Ilind497eee2018-04-19 22:50:541013 return false;
1014 *r = base::subtle::PlatformSharedMemoryRegion::Take(
Fabrice de Gans-Ribericbce4342018-05-07 20:02:091015 base::mac::ScopedMachSendRight(mach_port_mac.get_mach_port()), mode, size,
1016 guid);
Xiaohan Wangab909b32022-01-12 17:57:391017#elif BUILDFLAG(IS_POSIX)
Alexandr Ilind497eee2018-04-19 22:50:541018 scoped_refptr<base::Pickle::Attachment> attachment;
1019 if (!m->ReadAttachment(iter, &attachment))
1020 return false;
1021 if (static_cast<MessageAttachment*>(attachment.get())->GetType() !=
1022 MessageAttachment::Type::PLATFORM_FILE) {
1023 return false;
1024 }
1025
Xiaohan Wangab909b32022-01-12 17:57:391026#if BUILDFLAG(IS_ANDROID)
Alexandr Ilind497eee2018-04-19 22:50:541027 *r = base::subtle::PlatformSharedMemoryRegion::Take(
1028 base::ScopedFD(
1029 static_cast<internal::PlatformFileAttachment*>(attachment.get())
1030 ->TakePlatformFile()),
1031 mode, size, guid);
1032#else
1033 scoped_refptr<base::Pickle::Attachment> readonly_attachment;
1034 if (mode == base::subtle::PlatformSharedMemoryRegion::Mode::kWritable) {
1035 if (!m->ReadAttachment(iter, &readonly_attachment))
1036 return false;
1037
1038 if (static_cast<MessageAttachment*>(readonly_attachment.get())->GetType() !=
1039 MessageAttachment::Type::PLATFORM_FILE) {
1040 return false;
1041 }
1042 }
1043 *r = base::subtle::PlatformSharedMemoryRegion::Take(
1044 base::subtle::ScopedFDPair(
1045 base::ScopedFD(
1046 static_cast<internal::PlatformFileAttachment*>(attachment.get())
1047 ->TakePlatformFile()),
1048 readonly_attachment
1049 ? base::ScopedFD(static_cast<internal::PlatformFileAttachment*>(
1050 readonly_attachment.get())
1051 ->TakePlatformFile())
1052 : base::ScopedFD()),
1053 mode, size, guid);
Xiaohan Wangab909b32022-01-12 17:57:391054#endif // BUILDFLAG(IS_ANDROID)
Alexandr Ilind497eee2018-04-19 22:50:541055
1056#endif
1057
1058 return true;
1059}
1060
1061void ParamTraits<base::subtle::PlatformSharedMemoryRegion>::Log(
1062 const param_type& p,
1063 std::string* l) {
Xiaohan Wangab909b32022-01-12 17:57:391064#if BUILDFLAG(IS_FUCHSIA)
Wezb908e432018-09-05 17:35:221065 l->append("Handle: ");
1066 LogParam(p.GetPlatformHandle()->get(), l);
Xiaohan Wangab909b32022-01-12 17:57:391067#elif BUILDFLAG(IS_WIN)
Alexandr Ilind497eee2018-04-19 22:50:541068 l->append("Handle: ");
1069 LogParam(p.GetPlatformHandle(), l);
Ali Jumadff201a2022-05-31 23:51:411070#elif BUILDFLAG(IS_APPLE)
Fabrice de Gans-Ribericbce4342018-05-07 20:02:091071 l->append("Mach port: ");
1072 LogParam(p.GetPlatformHandle(), l);
Xiaohan Wangab909b32022-01-12 17:57:391073#elif BUILDFLAG(IS_ANDROID)
Alexandr Ilind497eee2018-04-19 22:50:541074 l->append("FD: ");
1075 LogParam(p.GetPlatformHandle(), l);
Xiaohan Wangab909b32022-01-12 17:57:391076#elif BUILDFLAG(IS_POSIX)
Alexandr Ilind497eee2018-04-19 22:50:541077 base::subtle::FDPair h = p.GetPlatformHandle();
1078 l->append("FD: ");
1079 LogParam(h.fd, l);
1080 l->append("Read-only FD: ");
1081 LogParam(h.readonly_fd, l);
1082#endif
1083
1084 l->append("Mode: ");
1085 LogParam(p.GetMode(), l);
1086 l->append("size: ");
1087 LogParam(static_cast<uint64_t>(p.GetSize()), l);
1088 l->append("GUID: ");
1089 LogParam(p.GetGUID(), l);
1090}
1091
1092void ParamTraits<base::subtle::PlatformSharedMemoryRegion::Mode>::Write(
1093 base::Pickle* m,
1094 const param_type& value) {
1095 DCHECK(static_cast<int>(value) >= 0 &&
1096 static_cast<int>(value) <= static_cast<int>(param_type::kMaxValue));
1097 m->WriteInt(static_cast<int>(value));
1098}
1099
1100bool ParamTraits<base::subtle::PlatformSharedMemoryRegion::Mode>::Read(
1101 const base::Pickle* m,
1102 base::PickleIterator* iter,
1103 param_type* p) {
1104 int value;
1105 if (!iter->ReadInt(&value))
1106 return false;
1107 if (!(static_cast<int>(value) >= 0 &&
1108 static_cast<int>(value) <= static_cast<int>(param_type::kMaxValue))) {
1109 return false;
1110 }
1111 *p = static_cast<param_type>(value);
1112 return true;
1113}
1114
1115void ParamTraits<base::subtle::PlatformSharedMemoryRegion::Mode>::Log(
1116 const param_type& p,
1117 std::string* l) {
1118 LogParam(static_cast<int>(p), l);
1119}
1120
Xiaohan Wangab909b32022-01-12 17:57:391121#if BUILDFLAG(IS_WIN)
erikchend804e1052017-04-29 02:24:361122void ParamTraits<PlatformFileForTransit>::Write(base::Pickle* m,
1123 const param_type& p) {
1124 m->WriteBool(p.IsValid());
1125 if (p.IsValid()) {
Wez51eaaad2017-08-09 05:51:381126 HandleWin handle_win(p.GetHandle());
erikchend804e1052017-04-29 02:24:361127 ParamTraits<HandleWin>::Write(m, handle_win);
1128 ::CloseHandle(p.GetHandle());
1129 }
1130}
1131
1132bool ParamTraits<PlatformFileForTransit>::Read(const base::Pickle* m,
1133 base::PickleIterator* iter,
1134 param_type* r) {
1135 bool is_valid;
1136 if (!iter->ReadBool(&is_valid))
1137 return false;
1138 if (!is_valid) {
1139 *r = PlatformFileForTransit();
1140 return true;
1141 }
1142
1143 HandleWin handle_win;
1144 if (!ParamTraits<HandleWin>::Read(m, iter, &handle_win))
1145 return false;
1146 *r = PlatformFileForTransit(handle_win.get_handle());
1147 return true;
1148}
1149
1150void ParamTraits<PlatformFileForTransit>::Log(const param_type& p,
1151 std::string* l) {
1152 LogParam(p.GetHandle(), l);
1153}
Xiaohan Wangab909b32022-01-12 17:57:391154#endif // BUILDFLAG(IS_WIN)
erikchend804e1052017-04-29 02:24:361155
rockot502c94f2016-02-03 20:20:161156void ParamTraits<base::FilePath>::Write(base::Pickle* m, const param_type& p) {
[email protected]aeae59f2013-01-28 13:47:551157 p.WriteToPickle(m);
[email protected]bf5aedf02012-06-04 21:18:251158}
1159
rockot502c94f2016-02-03 20:20:161160bool ParamTraits<base::FilePath>::Read(const base::Pickle* m,
brettwbd4d7112015-06-03 04:29:251161 base::PickleIterator* iter,
[email protected]6d4b67a2013-02-10 04:49:301162 param_type* r) {
[email protected]aeae59f2013-01-28 13:47:551163 return r->ReadFromPickle(iter);
[email protected]bf5aedf02012-06-04 21:18:251164}
1165
[email protected]6d4b67a2013-02-10 04:49:301166void ParamTraits<base::FilePath>::Log(const param_type& p, std::string* l) {
1167 ParamTraits<base::FilePath::StringType>::Log(p.value(), l);
[email protected]bf5aedf02012-06-04 21:18:251168}
1169
Fabrice de Gans43eebf702022-04-01 23:43:041170void ParamTraits<base::Value::List>::Write(base::Pickle* m,
1171 const param_type& p) {
1172 WriteListValue(p, 0, m);
1173}
1174
1175bool ParamTraits<base::Value::List>::Read(const base::Pickle* m,
1176 base::PickleIterator* iter,
1177 param_type* r) {
1178 return ReadListValue(m, iter, 0, r);
1179}
1180
1181void ParamTraits<base::Value::List>::Log(const param_type& p, std::string* l) {
1182 std::string json;
1183 base::JSONWriter::Write(p, &json);
1184 l->append(json);
1185}
1186
Devlin Cronin7178a5bd2021-02-02 02:56:471187void ParamTraits<base::Value>::Write(base::Pickle* m, const param_type& p) {
Fabrice de Gans43eebf702022-04-01 23:43:041188 WriteValue(p, 0, m);
Devlin Cronin7178a5bd2021-02-02 02:56:471189}
1190
1191bool ParamTraits<base::Value>::Read(const base::Pickle* m,
1192 base::PickleIterator* iter,
1193 param_type* r) {
Fabrice de Gans43eebf702022-04-01 23:43:041194 return ReadValue(m, iter, 0, r);
Devlin Cronin7178a5bd2021-02-02 02:56:471195}
1196
1197void ParamTraits<base::Value>::Log(const param_type& p, std::string* l) {
1198 std::string json;
1199 base::JSONWriter::Write(p, &json);
1200 l->append(json);
1201}
1202
rockot502c94f2016-02-03 20:20:161203void ParamTraits<base::File::Info>::Write(base::Pickle* m,
[email protected]141bcc52014-01-27 21:36:001204 const param_type& p) {
[email protected]bf5aedf02012-06-04 21:18:251205 WriteParam(m, p.size);
1206 WriteParam(m, p.is_directory);
1207 WriteParam(m, p.last_modified.ToDoubleT());
1208 WriteParam(m, p.last_accessed.ToDoubleT());
1209 WriteParam(m, p.creation_time.ToDoubleT());
1210}
1211
rockot502c94f2016-02-03 20:20:161212bool ParamTraits<base::File::Info>::Read(const base::Pickle* m,
brettwbd4d7112015-06-03 04:29:251213 base::PickleIterator* iter,
[email protected]141bcc52014-01-27 21:36:001214 param_type* p) {
[email protected]481c3e82014-07-18 01:40:471215 double last_modified, last_accessed, creation_time;
1216 if (!ReadParam(m, iter, &p->size) ||
1217 !ReadParam(m, iter, &p->is_directory) ||
1218 !ReadParam(m, iter, &last_modified) ||
1219 !ReadParam(m, iter, &last_accessed) ||
1220 !ReadParam(m, iter, &creation_time))
1221 return false;
1222 p->last_modified = base::Time::FromDoubleT(last_modified);
1223 p->last_accessed = base::Time::FromDoubleT(last_accessed);
1224 p->creation_time = base::Time::FromDoubleT(creation_time);
1225 return true;
[email protected]bf5aedf02012-06-04 21:18:251226}
1227
[email protected]141bcc52014-01-27 21:36:001228void ParamTraits<base::File::Info>::Log(const param_type& p,
1229 std::string* l) {
[email protected]bf5aedf02012-06-04 21:18:251230 l->append("(");
1231 LogParam(p.size, l);
1232 l->append(",");
1233 LogParam(p.is_directory, l);
1234 l->append(",");
1235 LogParam(p.last_modified.ToDoubleT(), l);
1236 l->append(",");
1237 LogParam(p.last_accessed.ToDoubleT(), l);
1238 l->append(",");
1239 LogParam(p.creation_time.ToDoubleT(), l);
1240 l->append(")");
1241}
1242
rockot502c94f2016-02-03 20:20:161243void ParamTraits<base::Time>::Write(base::Pickle* m, const param_type& p) {
tfarina10a5c062015-09-04 18:47:571244 ParamTraits<int64_t>::Write(m, p.ToInternalValue());
[email protected]bf5aedf02012-06-04 21:18:251245}
1246
rockot502c94f2016-02-03 20:20:161247bool ParamTraits<base::Time>::Read(const base::Pickle* m,
brettwbd4d7112015-06-03 04:29:251248 base::PickleIterator* iter,
[email protected]bf5aedf02012-06-04 21:18:251249 param_type* r) {
tfarina10a5c062015-09-04 18:47:571250 int64_t value;
1251 if (!ParamTraits<int64_t>::Read(m, iter, &value))
[email protected]bf5aedf02012-06-04 21:18:251252 return false;
1253 *r = base::Time::FromInternalValue(value);
1254 return true;
1255}
1256
1257void ParamTraits<base::Time>::Log(const param_type& p, std::string* l) {
tfarina10a5c062015-09-04 18:47:571258 ParamTraits<int64_t>::Log(p.ToInternalValue(), l);
[email protected]bf5aedf02012-06-04 21:18:251259}
1260
rockot502c94f2016-02-03 20:20:161261void ParamTraits<base::TimeDelta>::Write(base::Pickle* m, const param_type& p) {
tfarina10a5c062015-09-04 18:47:571262 ParamTraits<int64_t>::Write(m, p.ToInternalValue());
[email protected]bf5aedf02012-06-04 21:18:251263}
1264
rockot502c94f2016-02-03 20:20:161265bool ParamTraits<base::TimeDelta>::Read(const base::Pickle* m,
brettwbd4d7112015-06-03 04:29:251266 base::PickleIterator* iter,
[email protected]bf5aedf02012-06-04 21:18:251267 param_type* r) {
tfarina10a5c062015-09-04 18:47:571268 int64_t value;
1269 bool ret = ParamTraits<int64_t>::Read(m, iter, &value);
[email protected]bf5aedf02012-06-04 21:18:251270 if (ret)
1271 *r = base::TimeDelta::FromInternalValue(value);
1272
1273 return ret;
1274}
1275
1276void ParamTraits<base::TimeDelta>::Log(const param_type& p, std::string* l) {
tfarina10a5c062015-09-04 18:47:571277 ParamTraits<int64_t>::Log(p.ToInternalValue(), l);
[email protected]bf5aedf02012-06-04 21:18:251278}
1279
rockot502c94f2016-02-03 20:20:161280void ParamTraits<base::TimeTicks>::Write(base::Pickle* m, const param_type& p) {
tfarina10a5c062015-09-04 18:47:571281 ParamTraits<int64_t>::Write(m, p.ToInternalValue());
[email protected]bf5aedf02012-06-04 21:18:251282}
1283
rockot502c94f2016-02-03 20:20:161284bool ParamTraits<base::TimeTicks>::Read(const base::Pickle* m,
brettwbd4d7112015-06-03 04:29:251285 base::PickleIterator* iter,
[email protected]bf5aedf02012-06-04 21:18:251286 param_type* r) {
tfarina10a5c062015-09-04 18:47:571287 int64_t value;
1288 bool ret = ParamTraits<int64_t>::Read(m, iter, &value);
[email protected]bf5aedf02012-06-04 21:18:251289 if (ret)
1290 *r = base::TimeTicks::FromInternalValue(value);
1291
1292 return ret;
1293}
1294
1295void ParamTraits<base::TimeTicks>::Log(const param_type& p, std::string* l) {
tfarina10a5c062015-09-04 18:47:571296 ParamTraits<int64_t>::Log(p.ToInternalValue(), l);
[email protected]bf5aedf02012-06-04 21:18:251297}
1298
tguilbert4a5ac602016-09-19 21:11:251299// If base::UnguessableToken is no longer 128 bits, the IPC serialization logic
1300// below should be updated.
1301static_assert(sizeof(base::UnguessableToken) == 2 * sizeof(uint64_t),
1302 "base::UnguessableToken should be of size 2 * sizeof(uint64_t).");
1303
tguilbert4a5ac602016-09-19 21:11:251304void ParamTraits<base::UnguessableToken>::Write(base::Pickle* m,
1305 const param_type& p) {
1306 DCHECK(!p.is_empty());
1307
1308 ParamTraits<uint64_t>::Write(m, p.GetHighForSerialization());
1309 ParamTraits<uint64_t>::Write(m, p.GetLowForSerialization());
1310}
1311
1312bool ParamTraits<base::UnguessableToken>::Read(const base::Pickle* m,
1313 base::PickleIterator* iter,
1314 param_type* r) {
1315 uint64_t high, low;
1316 if (!ParamTraits<uint64_t>::Read(m, iter, &high) ||
1317 !ParamTraits<uint64_t>::Read(m, iter, &low))
1318 return false;
1319
Andrew Williamsc07db022023-01-24 13:38:521320 // This is not mapped as nullable_is_same_type, so any UnguessableToken
1321 // deserialized by the traits should always yield a non-empty token.
1322 // If deserialization results in an empty token, the data is malformed.
1323 absl::optional<base::UnguessableToken> token =
Andrew Williams228be95c2023-01-26 15:13:011324 base::UnguessableToken::Deserialize(high, low);
Andrew Williamsc07db022023-01-24 13:38:521325 if (!token.has_value()) {
tguilbert4a5ac602016-09-19 21:11:251326 return false;
Andrew Williamsc07db022023-01-24 13:38:521327 }
tguilbert4a5ac602016-09-19 21:11:251328
Andrew Williamsc07db022023-01-24 13:38:521329 *r = token.value();
tguilbert4a5ac602016-09-19 21:11:251330 return true;
1331}
1332
1333void ParamTraits<base::UnguessableToken>::Log(const param_type& p,
1334 std::string* l) {
1335 l->append(p.ToString());
1336}
1337
rockot502c94f2016-02-03 20:20:161338void ParamTraits<IPC::ChannelHandle>::Write(base::Pickle* m,
1339 const param_type& p) {
Xiaohan Wang53a511632022-01-21 18:14:581340#if BUILDFLAG(IS_NACL)
[email protected]7a4de7a62010-08-17 18:38:241341 WriteParam(m, p.socket);
sammc9bf370c2016-11-14 03:29:081342#else
amistry36182522016-06-27 06:34:421343 WriteParam(m, p.mojo_handle);
sammc9bf370c2016-11-14 03:29:081344#endif
[email protected]7a4de7a62010-08-17 18:38:241345}
1346
rockot502c94f2016-02-03 20:20:161347bool ParamTraits<IPC::ChannelHandle>::Read(const base::Pickle* m,
brettwbd4d7112015-06-03 04:29:251348 base::PickleIterator* iter,
[email protected]7a4de7a62010-08-17 18:38:241349 param_type* r) {
Xiaohan Wang53a511632022-01-21 18:14:581350#if BUILDFLAG(IS_NACL)
sammc9bf370c2016-11-14 03:29:081351 return ReadParam(m, iter, &r->socket);
1352#else
1353 return ReadParam(m, iter, &r->mojo_handle);
[email protected]7a4de7a62010-08-17 18:38:241354#endif
[email protected]7a4de7a62010-08-17 18:38:241355}
1356
1357void ParamTraits<IPC::ChannelHandle>::Log(const param_type& p,
[email protected]252cad62010-08-18 18:33:571358 std::string* l) {
sammc9bf370c2016-11-14 03:29:081359 l->append("ChannelHandle(");
Xiaohan Wang53a511632022-01-21 18:14:581360#if BUILDFLAG(IS_NACL)
[email protected]7a4de7a62010-08-17 18:38:241361 ParamTraits<base::FileDescriptor>::Log(p.socket, l);
sammc9bf370c2016-11-14 03:29:081362#else
amistry36182522016-06-27 06:34:421363 LogParam(p.mojo_handle, l);
sammc9bf370c2016-11-14 03:29:081364#endif
[email protected]252cad62010-08-18 18:33:571365 l->append(")");
[email protected]7a4de7a62010-08-17 18:38:241366}
1367
rockot502c94f2016-02-03 20:20:161368void ParamTraits<LogData>::Write(base::Pickle* m, const param_type& p) {
[email protected]20f0487a2010-09-30 20:06:301369 WriteParam(m, p.channel);
1370 WriteParam(m, p.routing_id);
[email protected]8bf55ca2011-10-17 22:15:271371 WriteParam(m, p.type);
[email protected]20f0487a2010-09-30 20:06:301372 WriteParam(m, p.flags);
1373 WriteParam(m, p.sent);
1374 WriteParam(m, p.receive);
1375 WriteParam(m, p.dispatch);
[email protected]bae578e92012-11-15 03:17:451376 WriteParam(m, p.message_name);
[email protected]20f0487a2010-09-30 20:06:301377 WriteParam(m, p.params);
1378}
1379
rockot502c94f2016-02-03 20:20:161380bool ParamTraits<LogData>::Read(const base::Pickle* m,
brettwbd4d7112015-06-03 04:29:251381 base::PickleIterator* iter,
[email protected]ce208f872012-03-07 20:42:561382 param_type* r) {
[email protected]8bf55ca2011-10-17 22:15:271383 return
[email protected]20f0487a2010-09-30 20:06:301384 ReadParam(m, iter, &r->channel) &&
1385 ReadParam(m, iter, &r->routing_id) &&
[email protected]8bf55ca2011-10-17 22:15:271386 ReadParam(m, iter, &r->type) &&
[email protected]20f0487a2010-09-30 20:06:301387 ReadParam(m, iter, &r->flags) &&
1388 ReadParam(m, iter, &r->sent) &&
1389 ReadParam(m, iter, &r->receive) &&
1390 ReadParam(m, iter, &r->dispatch) &&
[email protected]bae578e92012-11-15 03:17:451391 ReadParam(m, iter, &r->message_name) &&
[email protected]20f0487a2010-09-30 20:06:301392 ReadParam(m, iter, &r->params);
[email protected]20f0487a2010-09-30 20:06:301393}
1394
[email protected]bf5aedf02012-06-04 21:18:251395void ParamTraits<LogData>::Log(const param_type& p, std::string* l) {
1396 // Doesn't make sense to implement this!
1397}
1398
rockot502c94f2016-02-03 20:20:161399void ParamTraits<Message>::Write(base::Pickle* m, const Message& p) {
Xiaohan Wangab909b32022-01-12 17:57:391400#if BUILDFLAG(IS_POSIX) || BUILDFLAG(IS_FUCHSIA)
[email protected]34d48612012-06-29 00:05:041401 // We don't serialize the file descriptors in the nested message, so there
1402 // better not be any.
morrita1aa788c2015-01-31 05:45:421403 DCHECK(!p.HasAttachments());
[email protected]34d48612012-06-29 00:05:041404#endif
1405
1406 // Don't just write out the message. This is used to send messages between
1407 // NaCl (Posix environment) and the browser (could be on Windows). The message
1408 // header formats differ between these systems (so does handle sharing, but
1409 // we already asserted we don't have any handles). So just write out the
1410 // parts of the header we use.
1411 //
1412 // Be careful also to use only explicitly-sized types. The NaCl environment
1413 // could be 64-bit and the host browser could be 32-bits. The nested message
1414 // may or may not be safe to send between 32-bit and 64-bit systems, but we
1415 // leave that up to the code sending the message to ensure.
tfarina10a5c062015-09-04 18:47:571416 m->WriteUInt32(static_cast<uint32_t>(p.routing_id()));
[email protected]34d48612012-06-29 00:05:041417 m->WriteUInt32(p.type());
1418 m->WriteUInt32(p.flags());
Peter Kasting28b51cf2022-06-28 15:02:431419 m->WriteData(p.payload(), p.payload_size());
[email protected]bf5aedf02012-06-04 21:18:251420}
1421
rockot502c94f2016-02-03 20:20:161422bool ParamTraits<Message>::Read(const base::Pickle* m,
brettwbd4d7112015-06-03 04:29:251423 base::PickleIterator* iter,
[email protected]bf5aedf02012-06-04 21:18:251424 Message* r) {
tfarina10a5c062015-09-04 18:47:571425 uint32_t routing_id, type, flags;
avi48fc13b2014-12-28 23:31:481426 if (!iter->ReadUInt32(&routing_id) ||
1427 !iter->ReadUInt32(&type) ||
1428 !iter->ReadUInt32(&flags))
[email protected]bf5aedf02012-06-04 21:18:251429 return false;
[email protected]34d48612012-06-29 00:05:041430
Peter Kasting28b51cf2022-06-28 15:02:431431 size_t payload_size;
[email protected]34d48612012-06-29 00:05:041432 const char* payload;
avi48fc13b2014-12-28 23:31:481433 if (!iter->ReadData(&payload, &payload_size))
[email protected]bf5aedf02012-06-04 21:18:251434 return false;
[email protected]34d48612012-06-29 00:05:041435
tfarina10a5c062015-09-04 18:47:571436 r->SetHeaderValues(static_cast<int32_t>(routing_id), type, flags);
Daniel Cheng0d89f9222017-09-22 05:05:071437 r->WriteBytes(payload, payload_size);
1438 return true;
[email protected]bf5aedf02012-06-04 21:18:251439}
1440
1441void ParamTraits<Message>::Log(const Message& p, std::string* l) {
1442 l->append("<IPC::Message>");
1443}
1444
Xiaohan Wangab909b32022-01-12 17:57:391445#if BUILDFLAG(IS_WIN)
[email protected]bf5aedf02012-06-04 21:18:251446// Note that HWNDs/HANDLE/HCURSOR/HACCEL etc are always 32 bits, even on 64
[email protected]4a635b72013-03-04 02:29:031447// bit systems. That's why we use the Windows macros to convert to 32 bits.
rockot502c94f2016-02-03 20:20:161448void ParamTraits<HANDLE>::Write(base::Pickle* m, const param_type& p) {
[email protected]4a635b72013-03-04 02:29:031449 m->WriteInt(HandleToLong(p));
[email protected]bf5aedf02012-06-04 21:18:251450}
1451
rockot502c94f2016-02-03 20:20:161452bool ParamTraits<HANDLE>::Read(const base::Pickle* m,
brettwbd4d7112015-06-03 04:29:251453 base::PickleIterator* iter,
[email protected]bf5aedf02012-06-04 21:18:251454 param_type* r) {
tfarina10a5c062015-09-04 18:47:571455 int32_t temp;
avi48fc13b2014-12-28 23:31:481456 if (!iter->ReadInt(&temp))
[email protected]bf5aedf02012-06-04 21:18:251457 return false;
[email protected]4a635b72013-03-04 02:29:031458 *r = LongToHandle(temp);
[email protected]bf5aedf02012-06-04 21:18:251459 return true;
1460}
1461
1462void ParamTraits<HANDLE>::Log(const param_type& p, std::string* l) {
brucedawson5604a11d2015-10-06 19:22:001463 l->append(base::StringPrintf("0x%p", p));
[email protected]bf5aedf02012-06-04 21:18:251464}
1465
rockot502c94f2016-02-03 20:20:161466void ParamTraits<MSG>::Write(base::Pickle* m, const param_type& p) {
[email protected]bf5aedf02012-06-04 21:18:251467 m->WriteData(reinterpret_cast<const char*>(&p), sizeof(MSG));
1468}
1469
rockot502c94f2016-02-03 20:20:161470bool ParamTraits<MSG>::Read(const base::Pickle* m,
brettwbd4d7112015-06-03 04:29:251471 base::PickleIterator* iter,
[email protected]bf5aedf02012-06-04 21:18:251472 param_type* r) {
1473 const char *data;
Peter Kasting28b51cf2022-06-28 15:02:431474 size_t data_size = 0;
avi48fc13b2014-12-28 23:31:481475 bool result = iter->ReadData(&data, &data_size);
[email protected]bf5aedf02012-06-04 21:18:251476 if (result && data_size == sizeof(MSG)) {
1477 memcpy(r, data, sizeof(MSG));
1478 } else {
1479 result = false;
1480 NOTREACHED();
1481 }
1482
1483 return result;
1484}
1485
1486void ParamTraits<MSG>::Log(const param_type& p, std::string* l) {
1487 l->append("<MSG>");
1488}
1489
Xiaohan Wang53a511632022-01-21 18:14:581490#endif // BUILDFLAG(IS_WIN)
[email protected]bf5aedf02012-06-04 21:18:251491
[email protected]946d1b22009-07-22 23:57:211492} // namespace IPC