pidl:Samba4/NDR/Client: s/interface/if/
[Samba.git] / pidl / lib / Parse / Pidl / Samba4 / NDR / Client.pm
blob0672d101b6e7975eca2e1bb915fb4e3c0be63da3
1 ###################################################
2 # client calls generator
3 # Copyright tridge@samba.org 2003
4 # Copyright jelmer@samba.org 2005-2006
5 # released under the GNU GPL
7 package Parse::Pidl::Samba4::NDR::Client;
9 use Parse::Pidl::Samba4 qw(choose_header is_intree);
10 use Parse::Pidl::Util qw(has_property);
12 use vars qw($VERSION);
13 $VERSION = '0.01';
15 use strict;
17 my($res,$res_hdr);
19 sub ParseFunction_r_State($$$)
21 my ($if, $fn, $name) = @_;
22 my $uname = uc $name;
24 if (has_property($fn, "todo")) {
25 return;
28 $res .= "struct dcerpc_$name\_r_state {\n";
29 $res .= "\tTALLOC_CTX *out_mem_ctx;\n";
30 $res .= "};\n";
31 $res .= "\n";
32 $res .= "static void dcerpc_$name\_r_done(struct tevent_req *subreq);\n";
33 $res .= "\n";
36 sub ParseFunction_r_Send($$$)
38 my ($if, $fn, $name) = @_;
39 my $uname = uc $name;
41 if (has_property($fn, "todo")) {
42 return;
45 my $proto = "struct tevent_req *dcerpc_$name\_r_send(TALLOC_CTX *mem_ctx,\n";
46 $proto .= "\tstruct tevent_context *ev,\n",
47 $proto .= "\tstruct dcerpc_binding_handle *h,\n",
48 $proto .= "\tstruct $name *r)";
50 $res_hdr .= "\n$proto;\n";
52 $res .= "$proto\n{\n";
54 $res .= "\tstruct tevent_req *req;\n";
55 $res .= "\tstruct dcerpc_$name\_r_state *state;\n";
56 $res .= "\tstruct tevent_req *subreq;\n";
57 $res .= "\n";
59 $res .= "\treq = tevent_req_create(mem_ctx, &state,\n";
60 $res .= "\t\t\t\tstruct dcerpc_$name\_r_state);\n";
61 $res .= "\tif (req == NULL) {\n";
62 $res .= "\t\treturn NULL;\n";
63 $res .= "\t}\n";
64 $res .= "\n";
66 my $out_params = 0;
67 foreach (@{$fn->{ELEMENTS}}) {
68 if (grep(/out/, @{$_->{DIRECTION}})) {
69 $out_params++;
73 my $submem;
74 if ($out_params > 0) {
75 $res .= "\tstate->out_mem_ctx = talloc_new(state);\n";
76 $res .= "\tif (tevent_req_nomem(state->out_mem_ctx, req)) {\n";
77 $res .= "\t\treturn tevent_req_post(req, ev);\n";
78 $res .= "\t}\n";
79 $res .= "\n";
80 $submem = "state->out_mem_ctx";
81 } else {
82 $res .= "\tstate->out_mem_ctx = NULL;\n";
83 $submem = "state";
86 $res .= "\tsubreq = dcerpc_binding_handle_call_send(state, ev, h,\n";
87 $res .= "\t\t\tNULL, &ndr_table_$if->{NAME},\n";
88 $res .= "\t\t\tNDR_$uname, $submem, r);\n";
89 $res .= "\tif (tevent_req_nomem(subreq, req)) {\n";
90 $res .= "\t\treturn tevent_req_post(req, ev);\n";
91 $res .= "\t}\n";
92 $res .= "\ttevent_req_set_callback(subreq, dcerpc_$name\_r_done, req);\n";
93 $res .= "\n";
95 $res .= "\treturn req;\n";
96 $res .= "}\n";
97 $res .= "\n";
100 sub ParseFunction_r_Done($$$)
102 my ($if, $fn, $name) = @_;
103 my $uname = uc $name;
105 if (has_property($fn, "todo")) {
106 return;
109 my $proto = "static void dcerpc_$name\_r_done(struct tevent_req *subreq)";
111 $res .= "$proto\n";
112 $res .= "{\n";
114 $res .= "\tstruct tevent_req *req =\n";
115 $res .= "\t\ttevent_req_callback_data(subreq,\n";
116 $res .= "\t\tstruct tevent_req);\n";
117 $res .= "\tNTSTATUS status;\n";
118 $res .= "\n";
120 $res .= "\tstatus = dcerpc_binding_handle_call_recv(subreq);\n";
121 $res .= "\tif (!NT_STATUS_IS_OK(status)) {\n";
122 $res .= "\t\ttevent_req_nterror(req, status);\n";
123 $res .= "\t\treturn;\n";
124 $res .= "\t}\n";
125 $res .= "\n";
127 $res .= "\ttevent_req_done(req);\n";
128 $res .= "}\n";
129 $res .= "\n";
132 sub ParseFunction_r_Recv($$$)
134 my ($if, $fn, $name) = @_;
135 my $uname = uc $name;
137 if (has_property($fn, "todo")) {
138 return;
141 my $proto = "NTSTATUS dcerpc_$name\_r_recv(struct tevent_req *req, TALLOC_CTX *mem_ctx)";
143 $res_hdr .= "\n$proto;\n";
145 $res .= "$proto\n{\n";
147 $res .= "\tstruct dcerpc_$name\_r_state *state =\n";
148 $res .= "\t\ttevent_req_data(req,\n";
149 $res .= "\t\tstruct dcerpc_$name\_r_state);\n";
150 $res .= "\tNTSTATUS status;\n";
151 $res .= "\n";
153 $res .= "\tif (tevent_req_is_nterror(req, &status)) {\n";
154 $res .= "\t\ttevent_req_received(req);\n";
155 $res .= "\t\treturn status;\n";
156 $res .= "\t}\n";
157 $res .= "\n";
159 $res .= "\ttalloc_steal(mem_ctx, state->out_mem_ctx);\n";
160 $res .= "\n";
162 $res .= "\ttevent_req_received(req);\n";
163 $res .= "\treturn NT_STATUS_OK;\n";
164 $res .= "}\n";
165 $res .= "\n";
168 sub ParseFunction_r_Sync($$$)
170 my ($if, $fn, $name) = @_;
171 my $uname = uc $name;
173 if (has_property($fn, "todo")) {
174 return;
177 my $proto = "NTSTATUS dcerpc_$name\_r(struct dcerpc_binding_handle *h, TALLOC_CTX *mem_ctx, struct $name *r)";
179 $res_hdr .= "\n$proto;\n";
180 $res .= "$proto\n{\n";
181 $res .= "\tNTSTATUS status;\n";
182 $res .= "\n";
184 $res .= "\tstatus = dcerpc_binding_handle_call(h,\n";
185 $res .= "\t\t\tNULL, &ndr_table_$if->{NAME},\n";
186 $res .= "\t\t\tNDR_$uname, mem_ctx, r);\n";
187 $res .= "\n";
188 $res .= "\treturn status;\n";
190 $res .= "}\n";
191 $res .= "\n";
194 #####################################################################
195 # parse a function
196 sub ParseFunction($$)
198 my ($if, $fn) = @_;
200 ParseFunction_r_State($if, $fn, $fn->{NAME});
201 ParseFunction_r_Send($if, $fn, $fn->{NAME});
202 ParseFunction_r_Done($if, $fn, $fn->{NAME});
203 ParseFunction_r_Recv($if, $fn, $fn->{NAME});
204 ParseFunction_r_Sync($if, $fn, $fn->{NAME});
207 my %done;
209 #####################################################################
210 # parse the interface definitions
211 sub ParseInterface($)
213 my($if) = shift;
215 $res_hdr .= "#ifndef _HEADER_RPC_$if->{NAME}\n";
216 $res_hdr .= "#define _HEADER_RPC_$if->{NAME}\n\n";
218 if (defined $if->{PROPERTIES}->{uuid}) {
219 $res_hdr .= "extern const struct ndr_interface_table ndr_table_$if->{NAME};\n";
222 $res .= "/* $if->{NAME} - client functions generated by pidl */\n\n";
224 foreach my $fn (@{$if->{FUNCTIONS}}) {
225 next if not defined($fn->{OPNUM});
226 next if defined($done{$fn->{NAME}});
227 ParseFunction($if, $fn);
228 $done{$fn->{NAME}} = 1;
231 $res_hdr .= "#endif /* _HEADER_RPC_$if->{NAME} */\n";
233 return $res;
236 sub Parse($$$$)
238 my($ndr,$header,$ndr_header,$client_header) = @_;
240 $res = "";
241 $res_hdr = "";
243 $res .= "/* client functions auto-generated by pidl */\n";
244 $res .= "\n";
245 if (is_intree()) {
246 $res .= "#include \"includes.h\"\n";
247 } else {
248 $res .= "#ifndef _GNU_SOURCE\n";
249 $res .= "#define _GNU_SOURCE\n";
250 $res .= "#endif\n";
251 $res .= "#include <stdio.h>\n";
252 $res .= "#include <stdbool.h>\n";
253 $res .= "#include <stdlib.h>\n";
254 $res .= "#include <stdint.h>\n";
255 $res .= "#include <stdarg.h>\n";
256 $res .= "#include <core/ntstatus.h>\n";
258 $res .= "#include <tevent.h>\n";
259 $res .= choose_header("lib/util/tevent_ntstatus.h", "util/tevent_ntstatus.h")."\n";
260 $res .= "#include \"$ndr_header\"\n";
261 $res .= "#include \"$client_header\"\n";
262 $res .= "\n";
264 $res_hdr .= choose_header("librpc/rpc/dcerpc.h", "dcerpc.h")."\n";
265 $res_hdr .= "#include \"$header\"\n";
267 foreach my $x (@{$ndr}) {
268 ($x->{TYPE} eq "INTERFACE") && ParseInterface($x);
271 return ($res,$res_hdr);