Remove unneeded declarations from JSCallee.h
[WebKit-https.git] / Source / WebKit2 / Scripts / webkit / messages.py
1 # Copyright (C) 2010, 2011 Apple Inc. All rights reserved.
2 #
3 # Redistribution and use in source and binary forms, with or without
4 # modification, are permitted provided that the following conditions
5 # are met:
6 # 1.  Redistributions of source code must retain the above copyright
7 #     notice, this list of conditions and the following disclaimer.
8 # 2.  Redistributions in binary form must reproduce the above copyright
9 #     notice, this list of conditions and the following disclaimer in the
10 #     documentation and/or other materials provided with the distribution.
11 #
12 # THIS SOFTWARE IS PROVIDED BY APPLE INC. AND ITS CONTRIBUTORS ``AS IS'' AND
13 # ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
14 # WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
15 # DISCLAIMED. IN NO EVENT SHALL APPLE INC. OR ITS CONTRIBUTORS BE LIABLE FOR
16 # ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
17 # DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
18 # SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER
19 # CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
20 # OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
21 # OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
22
23 import collections
24 import re
25 import sys
26 from webkit import parser
27
28 WANTS_CONNECTION_ATTRIBUTE = 'WantsConnection'
29 LEGACY_RECEIVER_ATTRIBUTE = 'LegacyReceiver'
30 DELAYED_ATTRIBUTE = 'Delayed'
31 VARIADIC_ATTRIBUTE = 'Variadic'
32
33 _license_header = """/*
34  * Copyright (C) 2010 Apple Inc. All rights reserved.
35  *
36  * Redistribution and use in source and binary forms, with or without
37  * modification, are permitted provided that the following conditions
38  * are met:
39  * 1.  Redistributions of source code must retain the above copyright
40  *     notice, this list of conditions and the following disclaimer.
41  * 2.  Redistributions in binary form must reproduce the above copyright
42  *     notice, this list of conditions and the following disclaimer in the
43  *     documentation and/or other materials provided with the distribution.
44  *
45  * THIS SOFTWARE IS PROVIDED BY APPLE INC. AND ITS CONTRIBUTORS ``AS IS'' AND
46  * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
47  * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
48  * DISCLAIMED. IN NO EVENT SHALL APPLE INC. OR ITS CONTRIBUTORS BE LIABLE FOR
49  * ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
50  * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
51  * SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER
52  * CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
53  * OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
54  * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
55  */
56
57 """
58
59
60 def messages_header_filename(receiver):
61     return '%sMessages.h' % receiver.name
62
63
64 def surround_in_condition(string, condition):
65     if not condition:
66         return string
67     return '#if %s\n%s#endif\n' % (condition, string)
68
69
70 def function_parameter_type(type):
71     # Don't use references for built-in types.
72     builtin_types = frozenset([
73         'bool',
74         'float',
75         'double',
76         'uint8_t',
77         'uint16_t',
78         'uint32_t',
79         'uint64_t',
80         'int8_t',
81         'int16_t',
82         'int32_t',
83         'int64_t',
84     ])
85
86     if type in builtin_types:
87         return type
88
89     return 'const %s&' % type
90
91
92 def reply_parameter_type(type):
93     return '%s&' % type
94
95
96 def arguments_type(message):
97     return 'std::tuple<%s>' % ', '.join(function_parameter_type(parameter.type) for parameter in message.parameters)
98
99
100 def reply_type(message):
101     return 'IPC::Arguments<%s>' % (', '.join(reply_parameter_type(parameter.type) for parameter in message.reply_parameters))
102
103
104 def decode_type(message):
105     parameters = message.parameters
106
107     if message.has_attribute(VARIADIC_ATTRIBUTE):
108         parameters = parameters[:-1]
109
110     return 'std::tuple<%s>' % ', '.join(parameter.type for parameter in parameters)
111
112
113 def message_to_struct_declaration(message):
114     result = []
115     function_parameters = [(function_parameter_type(x.type), x.name) for x in message.parameters]
116     result.append('class %s {\n' % message.name)
117     result.append('public:\n')
118     result.append('    typedef %s DecodeType;\n' % decode_type(message))
119     result.append('\n')
120     result.append('    static IPC::StringReference receiverName() { return messageReceiverName(); }\n')
121     result.append('    static IPC::StringReference name() { return IPC::StringReference("%s"); }\n' % message.name)
122     result.append('    static const bool isSync = %s;\n' % ('false', 'true')[message.reply_parameters != None])
123     result.append('\n')
124     if message.reply_parameters != None:
125         if message.has_attribute(DELAYED_ATTRIBUTE):
126             send_parameters = [(function_parameter_type(x.type), x.name) for x in message.reply_parameters]
127             result.append('    struct DelayedReply : public ThreadSafeRefCounted<DelayedReply> {\n')
128             result.append('        DelayedReply(PassRefPtr<IPC::Connection>, std::unique_ptr<IPC::MessageEncoder>);\n')
129             result.append('        ~DelayedReply();\n')
130             result.append('\n')
131             result.append('        bool send(%s);\n' % ', '.join([' '.join(x) for x in send_parameters]))
132             result.append('\n')
133             result.append('    private:\n')
134             result.append('        RefPtr<IPC::Connection> m_connection;\n')
135             result.append('        std::unique_ptr<IPC::MessageEncoder> m_encoder;\n')
136             result.append('    };\n\n')
137
138         result.append('    typedef %s Reply;\n' % reply_type(message))
139
140     if len(function_parameters):
141         result.append('    %s%s(%s)' % (len(function_parameters) == 1 and 'explicit ' or '', message.name, ', '.join([' '.join(x) for x in function_parameters])))
142         result.append('\n        : m_arguments(%s)\n' % ', '.join([x[1] for x in function_parameters]))
143         result.append('    {\n')
144         result.append('    }\n\n')
145     result.append('    const %s& arguments() const\n' % arguments_type(message))
146     result.append('    {\n')
147     result.append('        return m_arguments;\n')
148     result.append('    }\n')
149     result.append('\n')
150     result.append('private:\n')
151     result.append('    %s m_arguments;\n' % arguments_type(message))
152     result.append('};\n')
153     return surround_in_condition(''.join(result), message.condition)
154
155
156 def struct_or_class(namespace, type):
157     structs = frozenset([
158         'WebCore::Animation',
159         'WebCore::EditorCommandsForKeyEvent',
160         'WebCore::CompositionUnderline',
161         'WebCore::Cookie',
162         'WebCore::FloatPoint3D',
163         'WebCore::FileChooserSettings',
164         'WebCore::GrammarDetail',
165         'WebCore::Highlight',
166         'WebCore::IDBDatabaseMetadata',
167         'WebCore::IDBGetResult',
168         'WebCore::IDBIndexMetadata',
169         'WebCore::IDBKeyData',
170         'WebCore::IDBKeyRangeData',
171         'WebCore::IDBObjectStoreMetadata',
172         'WebCore::IdentityTransformOperation',
173         'WebCore::KeypressCommand',
174         'WebCore::Length',
175         'WebCore::MatrixTransformOperation',
176         'WebCore::Matrix3DTransformOperation',
177         'WebCore::NotificationContents',
178         'WebCore::PasteboardImage',
179         'WebCore::PasteboardWebContent',
180         'WebCore::PerspectiveTransformOperation',
181         'WebCore::PluginInfo',
182         'WebCore::PrintInfo',
183         'WebCore::RotateTransformOperation',
184         'WebCore::ScaleTransformOperation',
185         'WebCore::SkewTransformOperation',
186         'WebCore::TimingFunction',
187         'WebCore::TransformationMatrix',
188         'WebCore::TransformOperation',
189         'WebCore::TransformOperations',
190         'WebCore::TranslateTransformOperation',
191         'WebCore::ViewportArguments',
192         'WebCore::ViewportAttributes',
193         'WebCore::WindowFeatures',
194         'WebKit::AssistedNodeInformation',
195         'WebKit::AttributedString',
196         'WebKit::BackForwardListItemState',
197         'WebKit::ColorSpaceData',
198         'WebKit::ContextMenuState',
199         'WebKit::DatabaseProcessCreationParameters',
200         'WebKit::DictionaryPopupInfo',
201         'WebKit::DrawingAreaInfo',
202         'WebKit::EditingRange',
203         'WebKit::EditorState',
204         'WebKit::InteractionInformationAtPosition',
205         'WebKit::NavigationActionData',
206         'WebKit::NetworkProcessCreationParameters',
207         'WebKit::PageState',
208         'WebKit::PlatformPopupMenuData',
209         'WebKit::PluginCreationParameters',
210         'WebKit::PluginProcessCreationParameters',
211         'WebKit::PrintInfo',
212         'WebKit::SecurityOriginData',
213         'WebKit::StatisticsData',
214         'WebKit::TextCheckerState',
215         'WebKit::WKOptionItem',
216         'WebKit::WebNavigationDataStore',
217         'WebKit::WebPageCreationParameters',
218         'WebKit::WebPreferencesStore',
219         'WebKit::WebProcessCreationParameters',
220         'WebKit::WebScriptMessageHandlerHandle',
221         'WebKit::WindowGeometry',
222     ])
223
224     qualified_name = '%s::%s' % (namespace, type)
225     if qualified_name in structs:
226         return 'struct %s' % type
227
228     return 'class %s' % type
229
230 def forward_declarations_for_namespace(namespace, types):
231     result = []
232     result.append('namespace %s {\n' % namespace)
233     result += ['    %s;\n' % struct_or_class(namespace, x) for x in types]
234     result.append('}\n')
235     return ''.join(result)
236
237
238 def forward_declarations_and_headers(receiver):
239     types_by_namespace = collections.defaultdict(set)
240
241     headers = set([
242         '"Arguments.h"',
243         '"MessageEncoder.h"',
244         '"StringReference.h"',
245     ])
246
247     non_template_wtf_types = frozenset([
248         'String',
249     ])
250
251     for message in receiver.messages:
252         if message.reply_parameters != None and message.has_attribute(DELAYED_ATTRIBUTE):
253             headers.add('<wtf/ThreadSafeRefCounted.h>')
254             types_by_namespace['IPC'].update(['Connection'])
255
256     for parameter in receiver.iterparameters():
257         type = parameter.type
258
259         if type.find('<') != -1:
260             # Don't forward declare class templates.
261             headers.update(headers_for_type(type))
262             continue
263
264         split = type.split('::')
265
266         # Handle WTF types even if the WTF:: prefix is not given
267         if split[0] in non_template_wtf_types:
268             split.insert(0, 'WTF')
269
270         if len(split) == 2:
271             namespace = split[0]
272             inner_type = split[1]
273             types_by_namespace[namespace].add(inner_type)
274         elif len(split) > 2:
275             # We probably have a nested struct, which means we can't forward declare it.
276             # Include its header instead.
277             headers.update(headers_for_type(type))
278
279     forward_declarations = '\n'.join([forward_declarations_for_namespace(namespace, types) for (namespace, types) in sorted(types_by_namespace.items())])
280     headers = ['#include %s\n' % header for header in sorted(headers)]
281
282     return (forward_declarations, headers)
283
284 def generate_messages_header(file):
285     receiver = parser.parse(file)
286     header_guard = messages_header_filename(receiver).replace('.', '_')
287
288     result = []
289
290     result.append(_license_header)
291
292     result.append('#ifndef %s\n' % header_guard)
293     result.append('#define %s\n\n' % header_guard)
294
295     if receiver.condition:
296         result.append('#if %s\n\n' % receiver.condition)
297
298     forward_declarations, headers = forward_declarations_and_headers(receiver)
299
300     result += headers
301     result.append('\n')
302
303     result.append(forward_declarations)
304     result.append('\n')
305
306     result.append('namespace Messages {\nnamespace %s {\n' % receiver.name)
307     result.append('\n')
308     result.append('static inline IPC::StringReference messageReceiverName()\n')
309     result.append('{\n')
310     result.append('    return IPC::StringReference("%s");\n' % receiver.name)
311     result.append('}\n')
312     result.append('\n')
313     result.append('\n'.join([message_to_struct_declaration(x) for x in receiver.messages]))
314     result.append('\n')
315     result.append('} // namespace %s\n} // namespace Messages\n' % receiver.name)
316
317     if receiver.condition:
318         result.append('\n#endif // %s\n' % receiver.condition)
319
320     result.append('\n#endif // %s\n' % header_guard)
321
322     return ''.join(result)
323
324
325 def handler_function(receiver, message):
326     if message.name.find('URL') == 0:
327         return '%s::%s' % (receiver.name, 'url' + message.name[3:])
328     return '%s::%s' % (receiver.name, message.name[0].lower() + message.name[1:])
329
330
331 def async_message_statement(receiver, message):
332     dispatch_function_args = ['decoder', 'this', '&%s' % handler_function(receiver, message)]
333
334     dispatch_function = 'handleMessage'
335     if message.has_attribute(VARIADIC_ATTRIBUTE):
336         dispatch_function += 'Variadic'
337
338     if message.has_attribute(WANTS_CONNECTION_ATTRIBUTE):
339         dispatch_function_args.insert(0, 'connection')
340
341     result = []
342     result.append('    if (decoder.messageName() == Messages::%s::%s::name()) {\n' % (receiver.name, message.name))
343     result.append('        IPC::%s<Messages::%s::%s>(%s);\n' % (dispatch_function, receiver.name, message.name, ', '.join(dispatch_function_args)))
344     result.append('        return;\n')
345     result.append('    }\n')
346     return surround_in_condition(''.join(result), message.condition)
347
348
349 def sync_message_statement(receiver, message):
350     dispatch_function = 'handleMessage'
351     if message.has_attribute(DELAYED_ATTRIBUTE):
352         dispatch_function += 'Delayed'
353     if message.has_attribute(VARIADIC_ATTRIBUTE):
354         dispatch_function += 'Variadic'
355
356     wants_connection = message.has_attribute(DELAYED_ATTRIBUTE) or message.has_attribute(WANTS_CONNECTION_ATTRIBUTE)
357
358     result = []
359     result.append('    if (decoder.messageName() == Messages::%s::%s::name()) {\n' % (receiver.name, message.name))
360     result.append('        IPC::%s<Messages::%s::%s>(%sdecoder, %sreplyEncoder, this, &%s);\n' % (dispatch_function, receiver.name, message.name, 'connection, ' if wants_connection else '', '' if message.has_attribute(DELAYED_ATTRIBUTE) else '*', handler_function(receiver, message)))
361     result.append('        return;\n')
362     result.append('    }\n')
363     return surround_in_condition(''.join(result), message.condition)
364
365
366 def class_template_headers(template_string):
367     template_string = template_string.strip()
368
369     class_template_types = {
370         'Vector': {'headers': ['<wtf/Vector.h>'], 'argument_coder_headers': ['"ArgumentCoders.h"']},
371         'HashMap': {'headers': ['<wtf/HashMap.h>'], 'argument_coder_headers': ['"ArgumentCoders.h"']},
372         'std::pair': {'headers': ['<utility>'], 'argument_coder_headers': ['"ArgumentCoders.h"']},
373     }
374
375     match = re.match('(?P<template_name>.+?)<(?P<parameter_string>.+)>', template_string)
376     if not match:
377         return {'header_infos':[], 'types':[template_string]}
378
379     template_name = match.groupdict()['template_name']
380     if template_name not in class_template_types:
381         sys.stderr.write("Error: no class template type is defined for '%s'\n" % (template_string))
382         sys.exit(1)
383
384     header_infos = [class_template_types[template_name]]
385     types = []
386
387     for parameter in parser.split_parameters_string(match.groupdict()['parameter_string']):
388         parameter_header_infos_and_types = class_template_headers(parameter)
389
390         header_infos += parameter_header_infos_and_types['header_infos'];
391         types += parameter_header_infos_and_types['types']
392
393     return {'header_infos':header_infos, 'types':types}
394
395
396 def argument_coder_headers_for_type(type):
397     header_infos_and_types = class_template_headers(type)
398
399     special_cases = {
400         'String': '"ArgumentCoders.h"',
401         'WebKit::InjectedBundleUserMessageEncoder': '"InjectedBundleUserMessageCoders.h"',
402         'WebKit::WebContextUserMessageEncoder': '"WebContextUserMessageCoders.h"',
403         'WebKit::ScriptMessageHandlerHandle': '"WebScriptMessageHandler.h"',
404     }
405
406     headers = []
407     for header_info in header_infos_and_types['header_infos']:
408         headers += header_info['argument_coder_headers']
409
410     for type in header_infos_and_types['types']:
411         if type in special_cases:
412             headers.append(special_cases[type])
413             continue
414
415         split = type.split('::')
416         if len(split) < 2:
417             continue
418         if split[0] == 'WebCore':
419             headers.append('"WebCoreArgumentCoders.h"')
420
421     return headers
422
423 def headers_for_type(type):
424     header_infos_and_types = class_template_headers(type)
425
426     special_cases = {
427         'String': ['<wtf/text/WTFString.h>'],
428         'WebCore::CompositionUnderline': ['<WebCore/Editor.h>'],
429         'WebCore::GrammarDetail': ['<WebCore/TextCheckerClient.h>'],
430         'WebCore::GraphicsLayerAnimations': ['<WebCore/GraphicsLayerAnimation.h>'],
431         'WebCore::KeyframeValueList': ['<WebCore/GraphicsLayer.h>'],
432         'WebCore::KeypressCommand': ['<WebCore/KeyboardEvent.h>'],
433         'WebCore::FileChooserSettings': ['<WebCore/FileChooser.h>'],
434         'WebCore::Highlight': ['<WebCore/InspectorOverlay.h>'],
435         'WebCore::PluginInfo': ['<WebCore/PluginData.h>'],
436         'WebCore::PasteboardImage': ['<WebCore/Pasteboard.h>'],
437         'WebCore::PasteboardWebContent': ['<WebCore/Pasteboard.h>'],
438         'WebCore::TextCheckingRequestData': ['<WebCore/TextChecking.h>'],
439         'WebCore::TextCheckingResult': ['<WebCore/TextCheckerClient.h>'],
440         'WebCore::ViewportAttributes': ['<WebCore/ViewportArguments.h>'],
441         'WebKit::BackForwardListItemState': ['"SessionState.h"'],
442         'WebKit::InjectedBundleUserMessageEncoder': [],
443         'WebKit::PageState': ['"SessionState.h"'],
444         'WebKit::WebContextUserMessageEncoder': [],
445         'WebKit::WebGestureEvent': ['"WebEvent.h"'],
446         'WebKit::WebKeyboardEvent': ['"WebEvent.h"'],
447         'WebKit::WebMouseEvent': ['"WebEvent.h"'],
448         'WebKit::WebTouchEvent': ['"WebEvent.h"'],
449         'WebKit::WebWheelEvent': ['"WebEvent.h"'],
450         'WebKit::WebScriptMessageHandlerHandle': ['"WebScriptMessageHandler.h"'],
451     }
452
453     headers = []
454     for header_info in header_infos_and_types['header_infos']:
455         headers += header_info['headers']
456
457     for type in header_infos_and_types['types']:
458         if type in special_cases:
459             headers += special_cases[type]
460             continue
461
462         # We assume that we must include a header for a type iff it has a scope
463         # resolution operator (::).
464         split = type.split('::')
465         if len(split) < 2:
466             continue
467
468         if split[0] == 'WebKit' or split[0] == 'IPC':
469             headers.append('"%s.h"' % split[1])
470         else:
471             headers.append('<%s/%s.h>' % tuple(split[0:2]))
472
473     return headers
474
475 def generate_message_handler(file):
476     receiver = parser.parse(file)
477     header_conditions = {
478         '"%s"' % messages_header_filename(receiver): [None],
479         '"HandleMessage.h"': [None],
480         '"MessageDecoder.h"': [None],
481     }
482
483     type_conditions = {}
484     for parameter in receiver.iterparameters():
485         if not parameter.type in type_conditions:
486             type_conditions[parameter.type] = []
487
488         if not parameter.condition in type_conditions[parameter.type]:
489             type_conditions[parameter.type].append(parameter.condition)
490
491     for parameter in receiver.iterparameters():
492         type = parameter.type
493         conditions = type_conditions[type]
494
495         argument_encoder_headers = argument_coder_headers_for_type(type)
496         if argument_encoder_headers:
497             for header in argument_encoder_headers:
498                 if header not in header_conditions:
499                     header_conditions[header] = []
500                 header_conditions[header].extend(conditions)
501
502         type_headers = headers_for_type(type)
503         for header in type_headers:
504             if header not in header_conditions:
505                 header_conditions[header] = []
506             header_conditions[header].extend(conditions)
507
508     for message in receiver.messages:
509         if message.reply_parameters is not None:
510             for reply_parameter in message.reply_parameters:
511                 type = reply_parameter.type
512                 argument_encoder_headers = argument_coder_headers_for_type(type)
513                 if argument_encoder_headers:
514                     for header in argument_encoder_headers:
515                         if header not in header_conditions:
516                             header_conditions[header] = []
517                         header_conditions[header].append(message.condition)
518
519                 type_headers = headers_for_type(type)
520                 for header in type_headers:
521                     if header not in header_conditions:
522                         header_conditions[header] = []
523                     header_conditions[header].append(message.condition)
524
525
526     result = []
527
528     result.append(_license_header)
529     result.append('#include "config.h"\n')
530     result.append('\n')
531
532     if receiver.condition:
533         result.append('#if %s\n\n' % receiver.condition)
534
535     result.append('#include "%s.h"\n\n' % receiver.name)
536     for header in sorted(header_conditions):
537         if header_conditions[header] and not None in header_conditions[header]:
538             result.append('#if %s\n' % ' || '.join(set(header_conditions[header])))
539             result += ['#include %s\n' % header]
540             result.append('#endif\n')
541         else:
542             result += ['#include %s\n' % header]
543     result.append('\n')
544
545     sync_delayed_messages = []
546     for message in receiver.messages:
547         if message.reply_parameters != None and message.has_attribute(DELAYED_ATTRIBUTE):
548             sync_delayed_messages.append(message)
549
550     if sync_delayed_messages:
551         result.append('namespace Messages {\n\nnamespace %s {\n\n' % receiver.name)
552
553         for message in sync_delayed_messages:
554             send_parameters = [(function_parameter_type(x.type), x.name) for x in message.reply_parameters]
555
556             if message.condition:
557                 result.append('#if %s\n\n' % message.condition)
558
559             result.append('%s::DelayedReply::DelayedReply(PassRefPtr<IPC::Connection> connection, std::unique_ptr<IPC::MessageEncoder> encoder)\n' % message.name)
560             result.append('    : m_connection(connection)\n')
561             result.append('    , m_encoder(WTF::move(encoder))\n')
562             result.append('{\n')
563             result.append('}\n')
564             result.append('\n')
565             result.append('%s::DelayedReply::~DelayedReply()\n' % message.name)
566             result.append('{\n')
567             result.append('    ASSERT(!m_connection);\n')
568             result.append('}\n')
569             result.append('\n')
570             result.append('bool %s::DelayedReply::send(%s)\n' % (message.name, ', '.join([' '.join(x) for x in send_parameters])))
571             result.append('{\n')
572             result.append('    ASSERT(m_encoder);\n')
573             result += ['    *m_encoder << %s;\n' % x.name for x in message.reply_parameters]
574             result.append('    bool _result = m_connection->sendSyncReply(WTF::move(m_encoder));\n')
575             result.append('    m_connection = nullptr;\n')
576             result.append('    return _result;\n')
577             result.append('}\n')
578             result.append('\n')
579
580             if message.condition:
581                 result.append('#endif\n\n')
582
583         result.append('} // namespace %s\n\n} // namespace Messages\n\n' % receiver.name)
584
585     result.append('namespace WebKit {\n\n')
586
587     async_messages = []
588     sync_messages = []
589     for message in receiver.messages:
590         if message.reply_parameters is not None:
591             sync_messages.append(message)
592         else:
593             async_messages.append(message)
594
595     if async_messages:
596         if receiver.has_attribute(LEGACY_RECEIVER_ATTRIBUTE):
597             result.append('void %s::didReceive%sMessage(IPC::Connection*, IPC::MessageDecoder& decoder)\n' % (receiver.name, receiver.name))
598         else:
599             result.append('void %s::didReceiveMessage(IPC::Connection* connection, IPC::MessageDecoder& decoder)\n' % (receiver.name))
600
601         result.append('{\n')
602         result += [async_message_statement(receiver, message) for message in async_messages]
603         if (receiver.superclass):
604             result.append('    %s::didReceiveMessage(connection, decoder);\n' % (receiver.superclass))
605         else:
606             if not receiver.has_attribute(LEGACY_RECEIVER_ATTRIBUTE):
607                 result.append('    UNUSED_PARAM(connection);\n')
608             result.append('    UNUSED_PARAM(decoder);\n')
609             result.append('    ASSERT_NOT_REACHED();\n')
610         result.append('}\n')
611
612     if sync_messages:
613         result.append('\n')
614         if receiver.has_attribute(LEGACY_RECEIVER_ATTRIBUTE):
615             result.append('void %s::didReceiveSync%sMessage(IPC::Connection*%s, IPC::MessageDecoder& decoder, std::unique_ptr<IPC::MessageEncoder>& replyEncoder)\n' % (receiver.name, receiver.name, ' connection' if sync_delayed_messages else ''))
616         else:
617             result.append('void %s::didReceiveSyncMessage(IPC::Connection* connection, IPC::MessageDecoder& decoder, std::unique_ptr<IPC::MessageEncoder>& replyEncoder)\n' % (receiver.name))
618         result.append('{\n')
619         result += [sync_message_statement(receiver, message) for message in sync_messages]
620         if not receiver.has_attribute(LEGACY_RECEIVER_ATTRIBUTE):
621             result.append('    UNUSED_PARAM(connection);\n')
622         result.append('    UNUSED_PARAM(decoder);\n')
623         result.append('    UNUSED_PARAM(replyEncoder);\n')
624         result.append('    ASSERT_NOT_REACHED();\n')
625         result.append('}\n')
626
627     result.append('\n} // namespace WebKit\n')
628
629     if receiver.condition:
630         result.append('\n#endif // %s\n' % receiver.condition)
631
632     return ''.join(result)