| OLD | NEW |
| 1 // Copyright (c) 2012 The Chromium Authors. All rights reserved. | 1 // Copyright (c) 2012 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 #ifndef IPC_IPC_MESSAGE_UTILS_H_ | 5 #ifndef IPC_IPC_MESSAGE_UTILS_H_ |
| 6 #define IPC_IPC_MESSAGE_UTILS_H_ | 6 #define IPC_IPC_MESSAGE_UTILS_H_ |
| 7 | 7 |
| 8 #include <limits.h> | 8 #include <limits.h> |
| 9 #include <stddef.h> | 9 #include <stddef.h> |
| 10 #include <stdint.h> | 10 #include <stdint.h> |
| (...skipping 13 matching lines...) Expand all Loading... |
| 24 #include "base/strings/string16.h" | 24 #include "base/strings/string16.h" |
| 25 #include "base/strings/string_util.h" | 25 #include "base/strings/string_util.h" |
| 26 #include "base/strings/stringprintf.h" | 26 #include "base/strings/stringprintf.h" |
| 27 #include "base/tuple.h" | 27 #include "base/tuple.h" |
| 28 #include "build/build_config.h" | 28 #include "build/build_config.h" |
| 29 #include "ipc/brokerable_attachment.h" | 29 #include "ipc/brokerable_attachment.h" |
| 30 #include "ipc/ipc_message_start.h" | 30 #include "ipc/ipc_message_start.h" |
| 31 #include "ipc/ipc_param_traits.h" | 31 #include "ipc/ipc_param_traits.h" |
| 32 #include "ipc/ipc_sync_message.h" | 32 #include "ipc/ipc_sync_message.h" |
| 33 | 33 |
| 34 #if defined(COMPILER_GCC) | |
| 35 // GCC "helpfully" tries to inline template methods in release mode. Except we | |
| 36 // want the majority of the template junk being expanded once in the | |
| 37 // implementation file (and only provide the definitions in | |
| 38 // ipc_message_utils_impl.h in those files) and exported, instead of expanded | |
| 39 // at every call site. Special note: GCC happily accepts the attribute before | |
| 40 // the method declaration, but only acts on it if it is after. | |
| 41 #if (__GNUC__ * 10000 + __GNUC_MINOR__ * 100) >= 40500 | |
| 42 // Starting in gcc 4.5, the noinline no longer implies the concept covered by | |
| 43 // the introduced noclone attribute, which will create specialized versions of | |
| 44 // functions/methods when certain types are constant. | |
| 45 // www.gnu.org/software/gcc/gcc-4.5/changes.html | |
| 46 #define IPC_MSG_NOINLINE __attribute__((noinline, noclone)); | |
| 47 #else | |
| 48 #define IPC_MSG_NOINLINE __attribute__((noinline)); | |
| 49 #endif | |
| 50 #elif defined(COMPILER_MSVC) | |
| 51 // MSVC++ doesn't do this. | |
| 52 #define IPC_MSG_NOINLINE | |
| 53 #else | |
| 54 #error "Please add the noinline property for your new compiler here." | |
| 55 #endif | |
| 56 | |
| 57 namespace base { | 34 namespace base { |
| 58 class DictionaryValue; | 35 class DictionaryValue; |
| 59 class FilePath; | 36 class FilePath; |
| 60 class ListValue; | 37 class ListValue; |
| 61 class NullableString16; | 38 class NullableString16; |
| 62 class Time; | 39 class Time; |
| 63 class TimeDelta; | 40 class TimeDelta; |
| 64 class TimeTicks; | 41 class TimeTicks; |
| 65 struct FileDescriptor; | 42 struct FileDescriptor; |
| 66 | 43 |
| (...skipping 858 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 925 static bool Read(const Message* m, | 902 static bool Read(const Message* m, |
| 926 base::PickleIterator* iter, | 903 base::PickleIterator* iter, |
| 927 param_type* r); | 904 param_type* r); |
| 928 static void Log(const param_type& p, std::string* l); | 905 static void Log(const param_type& p, std::string* l); |
| 929 }; | 906 }; |
| 930 #endif // defined(OS_WIN) | 907 #endif // defined(OS_WIN) |
| 931 | 908 |
| 932 //----------------------------------------------------------------------------- | 909 //----------------------------------------------------------------------------- |
| 933 // Generic message subclasses | 910 // Generic message subclasses |
| 934 | 911 |
| 935 // Used for asynchronous messages. | |
| 936 template <class ParamType> | |
| 937 class MessageSchema { | |
| 938 public: | |
| 939 typedef ParamType Param; | |
| 940 typedef typename base::TupleTypes<ParamType>::ParamTuple RefParam; | |
| 941 | |
| 942 static void Write(Message* msg, const RefParam& p) IPC_MSG_NOINLINE; | |
| 943 static bool Read(const Message* msg, Param* p) IPC_MSG_NOINLINE; | |
| 944 }; | |
| 945 | |
| 946 // defined in ipc_logging.cc | 912 // defined in ipc_logging.cc |
| 947 IPC_EXPORT void GenerateLogData(const std::string& channel, | 913 IPC_EXPORT void GenerateLogData(const std::string& channel, |
| 948 const Message& message, | 914 const Message& message, |
| 949 LogData* data, bool get_params); | 915 LogData* data, bool get_params); |
| 950 | 916 |
| 951 | 917 |
| 952 #if defined(IPC_MESSAGE_LOG_ENABLED) | 918 #if defined(IPC_MESSAGE_LOG_ENABLED) |
| 953 inline void AddOutputParamsToLog(const Message* msg, std::string* l) { | 919 inline void AddOutputParamsToLog(const Message* msg, std::string* l) { |
| 954 const std::string& output_params = msg->output_params(); | 920 const std::string& output_params = msg->output_params(); |
| 955 if (!l->empty() && !output_params.empty()) | 921 if (!l->empty() && !output_params.empty()) |
| (...skipping 26 matching lines...) Expand all Loading... |
| 982 #else | 948 #else |
| 983 inline void AddOutputParamsToLog(const Message* msg, std::string* l) {} | 949 inline void AddOutputParamsToLog(const Message* msg, std::string* l) {} |
| 984 | 950 |
| 985 template <class ReplyParamType> | 951 template <class ReplyParamType> |
| 986 inline void LogReplyParamsToMessage(const ReplyParamType& reply_params, | 952 inline void LogReplyParamsToMessage(const ReplyParamType& reply_params, |
| 987 const Message* msg) {} | 953 const Message* msg) {} |
| 988 | 954 |
| 989 inline void ConnectMessageAndReply(const Message* msg, Message* reply) {} | 955 inline void ConnectMessageAndReply(const Message* msg, Message* reply) {} |
| 990 #endif | 956 #endif |
| 991 | 957 |
| 992 // This class assumes that its template argument is a RefTuple (a Tuple with | |
| 993 // reference elements). This would go into ipc_message_utils_impl.h, but it is | |
| 994 // also used by chrome_frame. | |
| 995 template <class RefTuple> | |
| 996 class ParamDeserializer : public MessageReplyDeserializer { | |
| 997 public: | |
| 998 explicit ParamDeserializer(const RefTuple& out) : out_(out) { } | |
| 999 | |
| 1000 bool SerializeOutputParameters(const IPC::Message& msg, | |
| 1001 base::PickleIterator iter) override { | |
| 1002 return ReadParam(&msg, &iter, &out_); | |
| 1003 } | |
| 1004 | |
| 1005 RefTuple out_; | |
| 1006 }; | |
| 1007 | |
| 1008 // Used for synchronous messages. | |
| 1009 template <class SendParamType, class ReplyParamType> | |
| 1010 class SyncMessageSchema { | |
| 1011 public: | |
| 1012 typedef SendParamType SendParam; | |
| 1013 typedef typename base::TupleTypes<SendParam>::ParamTuple RefSendParam; | |
| 1014 typedef ReplyParamType ReplyParam; | |
| 1015 | |
| 1016 static void Write(Message* msg, const RefSendParam& send) IPC_MSG_NOINLINE; | |
| 1017 static bool ReadSendParam(const Message* msg, SendParam* p) IPC_MSG_NOINLINE; | |
| 1018 static bool ReadReplyParam( | |
| 1019 const Message* msg, | |
| 1020 typename base::TupleTypes<ReplyParam>::ValueTuple* p) IPC_MSG_NOINLINE; | |
| 1021 | |
| 1022 template<class T, class S, class Method> | |
| 1023 static bool DispatchWithSendParams(bool ok, const SendParam& send_params, | |
| 1024 const Message* msg, T* obj, S* sender, | |
| 1025 Method func) { | |
| 1026 Message* reply = SyncMessage::GenerateReply(msg); | |
| 1027 if (ok) { | |
| 1028 typename base::TupleTypes<ReplyParam>::ValueTuple reply_params; | |
| 1029 base::DispatchToMethod(obj, func, send_params, &reply_params); | |
| 1030 WriteParam(reply, reply_params); | |
| 1031 LogReplyParamsToMessage(reply_params, msg); | |
| 1032 } else { | |
| 1033 NOTREACHED() << "Error deserializing message " << msg->type(); | |
| 1034 reply->set_reply_error(); | |
| 1035 } | |
| 1036 sender->Send(reply); | |
| 1037 return ok; | |
| 1038 } | |
| 1039 | |
| 1040 template<class T, class Method> | |
| 1041 static bool DispatchDelayReplyWithSendParams(bool ok, | |
| 1042 const SendParam& send_params, | |
| 1043 const Message* msg, T* obj, | |
| 1044 Method func) { | |
| 1045 Message* reply = SyncMessage::GenerateReply(msg); | |
| 1046 if (ok) { | |
| 1047 base::Tuple<Message&> t = base::MakeRefTuple(*reply); | |
| 1048 ConnectMessageAndReply(msg, reply); | |
| 1049 base::DispatchToMethod(obj, func, send_params, &t); | |
| 1050 } else { | |
| 1051 NOTREACHED() << "Error deserializing message " << msg->type(); | |
| 1052 reply->set_reply_error(); | |
| 1053 obj->Send(reply); | |
| 1054 } | |
| 1055 return ok; | |
| 1056 } | |
| 1057 | |
| 1058 template <typename... Ts> | |
| 1059 static void WriteReplyParams(Message* reply, Ts... args) { | |
| 1060 ReplyParam p(args...); | |
| 1061 WriteParam(reply, p); | |
| 1062 } | |
| 1063 }; | |
| 1064 | |
| 1065 } // namespace IPC | 958 } // namespace IPC |
| 1066 | 959 |
| 1067 #endif // IPC_IPC_MESSAGE_UTILS_H_ | 960 #endif // IPC_IPC_MESSAGE_UTILS_H_ |
| OLD | NEW |