Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(1030)

Side by Side Diff: util/mach/notify_server.cc

Issue 804633002: Add NotifyServer and its test (Closed) Base URL: https://chromium.googlesource.com/crashpad/crashpad@master
Patch Set: Created 6 years ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch
« no previous file with comments | « util/mach/notify_server.h ('k') | util/mach/notify_server_test.cc » ('j') | no next file with comments »
Toggle Intra-line Diffs ('i') | Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
OLDNEW
(Empty)
1 // Copyright 2014 The Crashpad Authors. All rights reserved.
2 //
3 // Licensed under the Apache License, Version 2.0 (the "License");
4 // you may not use this file except in compliance with the License.
5 // You may obtain a copy of the License at
6 //
7 // http://www.apache.org/licenses/LICENSE-2.0
8 //
9 // Unless required by applicable law or agreed to in writing, software
10 // distributed under the License is distributed on an "AS IS" BASIS,
11 // WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12 // See the License for the specific language governing permissions and
13 // limitations under the License.
14
15 #include "util/mach/notify_server.h"
16
17 #include "base/logging.h"
18 #include "util/mach/notifyServer.h"
19 #include "util/mach/mach_message.h"
20
21 extern "C" {
22
23 // These five functions are not used, and are in fact obsoleted by the other
24 // functionality implemented in this file. The standard MIG-generated
25 // notify_server() (in notifyServer.c) server dispatch routine usable with the
26 // standard mach_msg_server() function calls out to this function.
27 // notify_server() is unused and is replaced by the more flexible NotifyServer,
28 // but the linker still needs to see these five function definitions.
29
30 kern_return_t do_mach_notify_port_deleted(notify_port_t notify,
31 mach_port_name_t name) {
32 NOTREACHED();
33 return KERN_FAILURE;
34 }
35
36 kern_return_t do_mach_notify_port_destroyed(notify_port_t notify,
37 mach_port_t rights) {
38 NOTREACHED();
39 return KERN_FAILURE;
40 }
41
42 kern_return_t do_mach_notify_no_senders(notify_port_t notify,
43 mach_port_mscount_t mscount) {
44 NOTREACHED();
45 return KERN_FAILURE;
46 }
47
48 kern_return_t do_mach_notify_send_once(notify_port_t notify) {
49 NOTREACHED();
50 return KERN_FAILURE;
51 }
52
53 kern_return_t do_mach_notify_dead_name(notify_port_t notify,
54 mach_port_name_t name) {
55 NOTREACHED();
56 return KERN_FAILURE;
57 }
58
59 } // extern "C"
60
61 namespace {
62
63 // The MIG-generated __MIG_check__Request__*() functions are not declared as
64 // accepting const data, but they could have been because they in fact do not
65 // modify the data. These wrapper functions are provided to bridge the const gap
66 // between the code in this file, which is const-correct and treats request
67 // message data as const, and the generated functions.
68
69 kern_return_t MIGCheckRequestMachNotifyPortDeleted(
70 const __Request__mach_notify_port_deleted_t* in_request) {
71 using Request = __Request__mach_notify_port_deleted_t;
72 return __MIG_check__Request__mach_notify_port_deleted_t(
73 const_cast<Request*>(in_request));
74 }
75
76 kern_return_t MIGCheckRequestMachNotifyPortDestroyed(
77 const __Request__mach_notify_port_destroyed_t* in_request) {
78 using Request = __Request__mach_notify_port_destroyed_t;
79 return __MIG_check__Request__mach_notify_port_destroyed_t(
80 const_cast<Request*>(in_request));
81 }
82
83 kern_return_t MIGCheckRequestMachNotifyNoSenders(
84 const __Request__mach_notify_no_senders_t* in_request) {
85 using Request = __Request__mach_notify_no_senders_t;
86 return __MIG_check__Request__mach_notify_no_senders_t(
87 const_cast<Request*>(in_request));
88 }
89
90 kern_return_t MIGCheckRequestMachNotifySendOnce(
91 const __Request__mach_notify_send_once_t* in_request) {
92 using Request = __Request__mach_notify_send_once_t;
93 return __MIG_check__Request__mach_notify_send_once_t(
94 const_cast<Request*>(in_request));
95 }
96
97 kern_return_t MIGCheckRequestMachNotifyDeadName(
98 const __Request__mach_notify_dead_name_t* in_request) {
99 using Request = __Request__mach_notify_dead_name_t;
100 return __MIG_check__Request__mach_notify_dead_name_t(
101 const_cast<Request*>(in_request));
102 }
103
104 } // namespace
105
106 namespace crashpad {
107
108 NotifyServer::NotifyServer(NotifyServer::Interface* interface)
109 : MachMessageServer::Interface(),
110 interface_(interface) {
111 }
112
113 bool NotifyServer::MachMessageServerFunction(
114 const mach_msg_header_t* in_header,
115 mach_msg_header_t* out_header,
116 bool* destroy_complex_request) {
117 PrepareMIGReplyFromRequest(in_header, out_header);
118
119 const mach_msg_trailer_t* in_trailer =
120 MachMessageTrailerFromHeader(in_header);
121
122 switch (in_header->msgh_id) {
123 case MACH_NOTIFY_PORT_DELETED: {
124 // mach_notify_port_deleted(), do_mach_notify_port_deleted().
125 using Request = __Request__mach_notify_port_deleted_t;
126 const Request* in_request = reinterpret_cast<const Request*>(in_header);
127 kern_return_t kr = MIGCheckRequestMachNotifyPortDeleted(in_request);
128 if (kr != MACH_MSG_SUCCESS) {
129 SetMIGReplyError(out_header, kr);
130 return true;
131 }
132
133 using Reply = __Reply__mach_notify_port_deleted_t;
134 Reply* out_reply = reinterpret_cast<Reply*>(out_header);
135 out_reply->RetCode =
136 interface_->DoMachNotifyPortDeleted(in_header->msgh_local_port,
137 in_request->name,
138 in_trailer);
139 return true;
140 }
141
142 case MACH_NOTIFY_PORT_DESTROYED: {
143 // mach_notify_port_destroyed(), do_mach_notify_port_destroyed().
144 using Request = __Request__mach_notify_port_destroyed_t;
145 const Request* in_request = reinterpret_cast<const Request*>(in_header);
146 kern_return_t kr = MIGCheckRequestMachNotifyPortDestroyed(in_request);
147 if (kr != MACH_MSG_SUCCESS) {
148 SetMIGReplyError(out_header, kr);
149 return true;
150 }
151
152 using Reply = __Reply__mach_notify_port_destroyed_t;
153 Reply* out_reply = reinterpret_cast<Reply*>(out_header);
154 out_reply->RetCode =
155 interface_->DoMachNotifyPortDestroyed(in_header->msgh_local_port,
156 in_request->rights.name,
157 in_trailer,
158 destroy_complex_request);
159 return true;
160 }
161
162 case MACH_NOTIFY_NO_SENDERS: {
163 // mach_notify_no_senders(), do_mach_notify_no_senders().
164 using Request = __Request__mach_notify_no_senders_t;
165 const Request* in_request = reinterpret_cast<const Request*>(in_header);
166 kern_return_t kr = MIGCheckRequestMachNotifyNoSenders(in_request);
167 if (kr != MACH_MSG_SUCCESS) {
168 SetMIGReplyError(out_header, kr);
169 return true;
170 }
171
172 using Reply = __Reply__mach_notify_no_senders_t;
173 Reply* out_reply = reinterpret_cast<Reply*>(out_header);
174 out_reply->RetCode =
175 interface_->DoMachNotifyNoSenders(in_header->msgh_local_port,
176 in_request->mscount,
177 in_trailer);
178 return true;
179 }
180
181 case MACH_NOTIFY_SEND_ONCE: {
182 // mach_notify_send_once(), do_mach_notify_send_once().
183 using Request = __Request__mach_notify_send_once_t;
184 const Request* in_request = reinterpret_cast<const Request*>(in_header);
185 kern_return_t kr = MIGCheckRequestMachNotifySendOnce(in_request);
186 if (kr != MACH_MSG_SUCCESS) {
187 SetMIGReplyError(out_header, kr);
188 return true;
189 }
190
191 using Reply = __Reply__mach_notify_send_once_t;
192 Reply* out_reply = reinterpret_cast<Reply*>(out_header);
193 out_reply->RetCode =
194 interface_->DoMachNotifySendOnce(in_header->msgh_local_port,
195 in_trailer);
196 return true;
197 }
198
199 case MACH_NOTIFY_DEAD_NAME: {
200 // mach_notify_dead_name(), do_mach_notify_dead_name().
201 using Request = __Request__mach_notify_dead_name_t;
202 const Request* in_request = reinterpret_cast<const Request*>(in_header);
203 kern_return_t kr = MIGCheckRequestMachNotifyDeadName(in_request);
204 if (kr != MACH_MSG_SUCCESS) {
205 SetMIGReplyError(out_header, kr);
206 return true;
207 }
208
209 using Reply = __Reply__mach_notify_dead_name_t;
210 Reply* out_reply = reinterpret_cast<Reply*>(out_header);
211 out_reply->RetCode =
212 interface_->DoMachNotifyDeadName(in_header->msgh_local_port,
213 in_request->name,
214 in_trailer);
215 return true;
216 }
217
218 default: {
219 SetMIGReplyError(out_header, MIG_BAD_ID);
220 return false;
221 }
222 }
223 }
224
225 std::set<mach_msg_id_t> NotifyServer::MachMessageServerRequestIDs() {
226 const mach_msg_id_t request_ids[] = {
227 MACH_NOTIFY_PORT_DELETED,
228 MACH_NOTIFY_PORT_DESTROYED,
229 MACH_NOTIFY_NO_SENDERS,
230 MACH_NOTIFY_SEND_ONCE,
231 MACH_NOTIFY_DEAD_NAME,
232 };
233 return std::set<mach_msg_id_t>(&request_ids[0],
234 &request_ids[arraysize(request_ids)]);
235 }
236
237 mach_msg_size_t NotifyServer::MachMessageServerRequestSize() {
238 return sizeof(__RequestUnion__do_notify_subsystem);
239 }
240
241 mach_msg_size_t NotifyServer::MachMessageServerReplySize() {
242 return sizeof(__ReplyUnion__do_notify_subsystem);
243 }
244
245 } // namespace crashpad
OLDNEW
« no previous file with comments | « util/mach/notify_server.h ('k') | util/mach/notify_server_test.cc » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698