Upstream version 7.36.149.0
[platform/framework/web/crosswalk.git] / src / mojo / public / tools / bindings / generators / cpp_templates / interface_definition.tmpl
1 {%- import "interface_macros.tmpl" as interface_macros %}
2 {%- set class_name = interface.name %}
3 {%- set proxy_name = interface.name ~ "Proxy" %}
4
5 {%- macro pass_params(parameters) %}
6 {%-   for param in parameters %}
7 {%-     if param.kind|is_object_kind -%}
8 mojo::internal::Wrap(params->{{param.name}}())
9 {%-     elif param.kind|is_interface_kind -%}
10 mojo::MakeProxy<{{param.kind.name}}>(mojo::MakePassable(params->{{param.name}}()).Pass())
11 {%-     elif param.kind|is_handle_kind -%}
12 mojo::MakePassable(params->{{param.name}}()).Pass()
13 {%-     elif param.kind|is_enum_kind -%}
14 static_cast<{{param.kind|cpp_wrapper_type}}>(params->{{param.name}}())
15 {%-     else -%}
16 params->{{param.name}}()
17 {%-     endif -%}
18 {%-     if not loop.last %}, {% endif %}
19 {%-   endfor %}
20 {%- endmacro %}
21
22 {%- macro compute_payload_size(params_name, parameters) -%}
23   size_t payload_size =
24       mojo::internal::Align(sizeof({{params_name}}));
25 {#--- Computes #}
26 {%-   for param in parameters %}
27 {%-     if param.kind|is_object_kind %}
28   if (!in_{{param.name}}.is_null())
29     payload_size += mojo::internal::Unwrap(in_{{param.name}})->ComputeSize();
30 {%-     endif %}
31 {%-   endfor %}
32 {%- endmacro %}
33
34 {%- macro build_message(params_name, parameters) -%}
35   {{params_name}}* params =
36       {{params_name}}::New(builder.buffer());
37 {#--- Sets #}
38 {%   for param in parameters %}
39 {%-     if param.kind|is_object_kind %}
40   if (!in_{{param.name}}.is_null())
41     params->set_{{param.name}}(
42         mojo::internal::Unwrap(in_{{param.name}})->Clone(builder.buffer()));
43 {%-     elif param.kind|is_interface_kind %}
44   if (!in_{{param.name}}.get()) {
45     params->set_{{param.name}}(mojo::MessagePipeHandle());
46   } else {
47     // Delegate handle.
48     params->set_{{param.name}}(
49         in_{{param.name}}.ResetAndReturnMessagePipe().release());
50   }
51 {%-     elif param.kind|is_handle_kind %}
52   params->set_{{param.name}}(in_{{param.name}}.release());
53 {%-     else %}
54   params->set_{{param.name}}(in_{{param.name}});
55 {%-     endif %}
56 {%-   endfor %}
57   mojo::Message message;
58   params->EncodePointersAndHandles(message.mutable_handles());
59   builder.Finish(&message);
60 {%- endmacro %}
61
62 {#--- ForwardToCallback definition #}
63 {%- for method in interface.methods -%}
64 {%-   if method.response_parameters != None %}
65 class {{class_name}}_{{method.name}}_ForwardToCallback
66     : public mojo::MessageReceiver {
67  public:
68   {{class_name}}_{{method.name}}_ForwardToCallback(
69       const {{interface_macros.declare_callback(method)}}& callback)
70       : callback_(callback) {
71   }
72   virtual bool Accept(mojo::Message* message) MOJO_OVERRIDE;
73   virtual bool AcceptWithResponder(
74       mojo::Message* message,
75       mojo::MessageReceiver* responder) MOJO_OVERRIDE {
76     assert(false);
77     return false;
78   }
79  private:
80   {{interface_macros.declare_callback(method)}} callback_;
81   MOJO_DISALLOW_COPY_AND_ASSIGN({{class_name}}_{{method.name}}_ForwardToCallback);
82 };
83 bool {{class_name}}_{{method.name}}_ForwardToCallback::Accept(
84     mojo::Message* message) {
85   internal::{{class_name}}_{{method.name}}_ResponseParams_Data* params =
86       reinterpret_cast<internal::{{class_name}}_{{method.name}}_ResponseParams_Data*>(
87           message->mutable_payload());
88
89   if (!params->DecodePointersAndHandles(message))
90     return false;
91   callback_.Run({{pass_params(method.response_parameters)}});
92   params->CloseHandles();
93   return true;
94 }
95 {%-   endif %}
96 {%- endfor %}
97
98 {{proxy_name}}::{{proxy_name}}(mojo::MessageReceiver* receiver)
99     : receiver_(receiver) {
100 }
101
102 {#--- Proxy definitions #}
103
104 {%- for method in interface.methods %}
105 {%-   set message_name =
106           "internal::k%s_%s_Name"|format(interface.name, method.name) %}
107 {%-   set params_name =
108           "internal::%s_%s_Params_Data"|format(interface.name, method.name) %}
109 void {{proxy_name}}::{{method.name}}(
110     {{interface_macros.declare_request_params("in_", method)}}) {
111   {{compute_payload_size(params_name, method.parameters)}}
112
113 {%- if method.response_parameters != None %}
114   mojo::internal::RequestMessageBuilder builder({{message_name}}, payload_size);
115 {%- else %}
116   mojo::internal::MessageBuilder builder({{message_name}}, payload_size);
117 {%- endif %}
118
119   {{build_message(params_name, method.parameters)}}
120
121 {%- if method.response_parameters != None %}
122   mojo::MessageReceiver* responder =
123       new {{class_name}}_{{method.name}}_ForwardToCallback(callback);
124   if (!receiver_->AcceptWithResponder(&message, responder))
125     delete responder;
126 {%- else %}
127   bool ok MOJO_ALLOW_UNUSED = receiver_->Accept(&message);
128   // This return value may be ignored as !ok implies the Connector has
129   // encountered an error, which will be visible through other means.
130 {%- endif %}
131 }
132 {%- endfor %}
133
134 {#--- ProxyToResponder definition #}
135 {%- for method in interface.methods -%}
136 {%-   if method.response_parameters != None %}
137 {%-     set message_name =
138             "internal::k%s_%s_Name"|format(interface.name, method.name) %}
139 {%-     set params_name =
140             "internal::%s_%s_ResponseParams_Data"|format(interface.name, method.name) %}
141 class {{class_name}}_{{method.name}}_ProxyToResponder
142     : public {{interface_macros.declare_callback(method)}}::Runnable {
143  public:
144   virtual ~{{class_name}}_{{method.name}}_ProxyToResponder() {
145     delete responder_;
146   }
147
148   {{class_name}}_{{method.name}}_ProxyToResponder(
149       uint64_t request_id,
150       mojo::MessageReceiver* responder)
151       : request_id_(request_id),
152         responder_(responder) {
153   }
154
155   virtual void Run({{interface_macros.declare_params("in_", method.response_parameters)}}) const;
156
157  private:
158   uint64_t request_id_;
159   mutable mojo::MessageReceiver* responder_;
160   MOJO_DISALLOW_COPY_AND_ASSIGN({{class_name}}_{{method.name}}_ProxyToResponder);
161 };
162 void {{class_name}}_{{method.name}}_ProxyToResponder::Run(
163     {{interface_macros.declare_params("in_", method.response_parameters)}}) const {
164   {{compute_payload_size(params_name, method.response_parameters)}}
165   mojo::internal::ResponseMessageBuilder builder(
166       {{message_name}}, payload_size, request_id_);
167   {{build_message(params_name, method.response_parameters)}}
168   bool ok MOJO_ALLOW_UNUSED = responder_->Accept(&message);
169   // TODO(darin): !ok returned here indicates a malformed message, and that may
170   // be good reason to close the connection. However, we don't have a way to do
171   // that from here. We should add a way.
172   delete responder_;
173   responder_ = NULL;
174 }
175 {%-   endif -%}
176 {%- endfor %}
177
178 {{class_name}}Stub::{{class_name}}Stub()
179     : sink_(NULL) {
180 }
181
182 {#--- Stub definition #}
183
184 bool {{class_name}}Stub::Accept(mojo::Message* message) {
185 {%- if interface.methods %}
186   switch (message->header()->name) {
187 {%-   for method in interface.methods %}
188     case internal::k{{class_name}}_{{method.name}}_Name: {
189 {%-     if method.response_parameters == None %}
190       internal::{{class_name}}_{{method.name}}_Params_Data* params =
191           reinterpret_cast<internal::{{class_name}}_{{method.name}}_Params_Data*>(
192               message->mutable_payload());
193
194       if (!params->DecodePointersAndHandles(message))
195         return false;
196       sink_->{{method.name}}({{pass_params(method.parameters)}});
197       params->CloseHandles();
198       return true;
199 {%-     else %}
200       break;
201 {%-     endif %}
202     }
203 {%-   endfor %}
204   }
205 {%- endif %}
206   return false;
207 }
208
209 bool {{class_name}}Stub::AcceptWithResponder(
210     mojo::Message* message, mojo::MessageReceiver* responder) {
211 {%- if interface.methods %}
212   switch (message->header()->name) {
213 {%-   for method in interface.methods %}
214     case internal::k{{class_name}}_{{method.name}}_Name: {
215 {%-     if method.response_parameters != None %}
216       internal::{{class_name}}_{{method.name}}_Params_Data* params =
217           reinterpret_cast<internal::{{class_name}}_{{method.name}}_Params_Data*>(
218               message->mutable_payload());
219
220       if (!params->DecodePointersAndHandles(message))
221         return false;
222       {{interface_macros.declare_callback(method)}}::Runnable* runnable =
223           new {{class_name}}_{{method.name}}_ProxyToResponder(
224               message->request_id(), responder);
225       {{interface_macros.declare_callback(method)}} callback(runnable);
226       sink_->{{method.name}}(
227 {%- if method.parameters -%}{{pass_params(method.parameters)}}, {% endif -%}callback);
228       params->CloseHandles();
229       return true;
230 {%-     else %}
231       break;
232 {%-     endif %}
233     }
234 {%-   endfor %}
235   }
236 {%- endif %}
237   return false;
238 }