Line data Source code
1 : /* server functions auto-generated by pidl */
2 : #include "bin/default/librpc/gen_ndr/ndr_dnsserver.h"
3 : #include <util/debug.h>
4 :
5 : NTSTATUS dcerpc_server_dnsserver_init(TALLOC_CTX *);
6 :
7 : /* dnsserver - dcerpc server boilerplate generated by pidl */
8 :
9 :
10 1609 : static NTSTATUS dnsserver__op_bind(struct dcesrv_connection_context *context, const struct dcesrv_interface *iface)
11 : {
12 : #ifdef DCESRV_INTERFACE_DNSSERVER_BIND
13 1609 : return DCESRV_INTERFACE_DNSSERVER_BIND(context,iface);
14 : #else
15 : return NT_STATUS_OK;
16 : #endif
17 : }
18 :
19 1609 : static void dnsserver__op_unbind(struct dcesrv_connection_context *context, const struct dcesrv_interface *iface)
20 : {
21 : #ifdef DCESRV_INTERFACE_DNSSERVER_UNBIND
22 : DCESRV_INTERFACE_DNSSERVER_UNBIND(context, iface);
23 : #else
24 1609 : return;
25 : #endif
26 : }
27 :
28 6961 : static NTSTATUS dnsserver__op_ndr_pull(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx, struct ndr_pull *pull, void **r)
29 : {
30 0 : enum ndr_err_code ndr_err;
31 6961 : uint16_t opnum = dce_call->pkt.u.request.opnum;
32 :
33 6961 : dce_call->fault_code = 0;
34 :
35 6961 : if (opnum >= ndr_table_dnsserver.num_calls) {
36 0 : dce_call->fault_code = DCERPC_FAULT_OP_RNG_ERROR;
37 0 : return NT_STATUS_NET_WRITE_FAULT;
38 : }
39 :
40 13922 : *r = talloc_named(mem_ctx,
41 6961 : ndr_table_dnsserver.calls[opnum].struct_size,
42 : "struct %s",
43 6961 : ndr_table_dnsserver.calls[opnum].name);
44 6961 : NT_STATUS_HAVE_NO_MEMORY(*r);
45 :
46 : /* unravel the NDR for the packet */
47 6961 : ndr_err = ndr_table_dnsserver.calls[opnum].ndr_pull(pull, NDR_IN, *r);
48 6961 : if (!NDR_ERR_CODE_IS_SUCCESS(ndr_err)) {
49 0 : dce_call->fault_code = DCERPC_FAULT_NDR;
50 0 : return NT_STATUS_NET_WRITE_FAULT;
51 : }
52 :
53 6961 : return NT_STATUS_OK;
54 : }
55 :
56 6961 : static NTSTATUS dnsserver__op_dispatch(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx, void *r)
57 : {
58 6961 : uint16_t opnum = dce_call->pkt.u.request.opnum;
59 :
60 6961 : switch (opnum) {
61 3 : case 0: {
62 3 : struct DnssrvOperation *r2 = (struct DnssrvOperation *)r;
63 3 : if (DEBUGLEVEL >= 10) {
64 0 : NDR_PRINT_FUNCTION_DEBUG(DnssrvOperation, NDR_IN, r2);
65 : }
66 3 : r2->out.result = dcesrv_DnssrvOperation(dce_call, mem_ctx, r2);
67 3 : if (dce_call->state_flags & DCESRV_CALL_STATE_FLAG_ASYNC) {
68 0 : DEBUG(5,("function DnssrvOperation will reply async\n"));
69 : }
70 3 : break;
71 : }
72 0 : case 1: {
73 0 : struct DnssrvQuery *r2 = (struct DnssrvQuery *)r;
74 0 : if (DEBUGLEVEL >= 10) {
75 0 : NDR_PRINT_FUNCTION_DEBUG(DnssrvQuery, NDR_IN, r2);
76 : }
77 0 : r2->out.result = dcesrv_DnssrvQuery(dce_call, mem_ctx, r2);
78 0 : if (dce_call->state_flags & DCESRV_CALL_STATE_FLAG_ASYNC) {
79 0 : DEBUG(5,("function DnssrvQuery will reply async\n"));
80 : }
81 0 : break;
82 : }
83 0 : case 2: {
84 0 : struct DnssrvComplexOperation *r2 = (struct DnssrvComplexOperation *)r;
85 0 : if (DEBUGLEVEL >= 10) {
86 0 : NDR_PRINT_FUNCTION_DEBUG(DnssrvComplexOperation, NDR_IN, r2);
87 : }
88 0 : r2->out.result = dcesrv_DnssrvComplexOperation(dce_call, mem_ctx, r2);
89 0 : if (dce_call->state_flags & DCESRV_CALL_STATE_FLAG_ASYNC) {
90 0 : DEBUG(5,("function DnssrvComplexOperation will reply async\n"));
91 : }
92 0 : break;
93 : }
94 0 : case 3: {
95 0 : struct DnssrvEnumRecords *r2 = (struct DnssrvEnumRecords *)r;
96 0 : if (DEBUGLEVEL >= 10) {
97 0 : NDR_PRINT_FUNCTION_DEBUG(DnssrvEnumRecords, NDR_IN, r2);
98 : }
99 0 : r2->out.result = dcesrv_DnssrvEnumRecords(dce_call, mem_ctx, r2);
100 0 : if (dce_call->state_flags & DCESRV_CALL_STATE_FLAG_ASYNC) {
101 0 : DEBUG(5,("function DnssrvEnumRecords will reply async\n"));
102 : }
103 0 : break;
104 : }
105 0 : case 4: {
106 0 : struct DnssrvUpdateRecord *r2 = (struct DnssrvUpdateRecord *)r;
107 0 : if (DEBUGLEVEL >= 10) {
108 0 : NDR_PRINT_FUNCTION_DEBUG(DnssrvUpdateRecord, NDR_IN, r2);
109 : }
110 0 : r2->out.result = dcesrv_DnssrvUpdateRecord(dce_call, mem_ctx, r2);
111 0 : if (dce_call->state_flags & DCESRV_CALL_STATE_FLAG_ASYNC) {
112 0 : DEBUG(5,("function DnssrvUpdateRecord will reply async\n"));
113 : }
114 0 : break;
115 : }
116 1652 : case 5: {
117 1652 : struct DnssrvOperation2 *r2 = (struct DnssrvOperation2 *)r;
118 1652 : if (DEBUGLEVEL >= 10) {
119 0 : NDR_PRINT_FUNCTION_DEBUG(DnssrvOperation2, NDR_IN, r2);
120 : }
121 1652 : r2->out.result = dcesrv_DnssrvOperation2(dce_call, mem_ctx, r2);
122 1652 : if (dce_call->state_flags & DCESRV_CALL_STATE_FLAG_ASYNC) {
123 0 : DEBUG(5,("function DnssrvOperation2 will reply async\n"));
124 : }
125 1652 : break;
126 : }
127 29 : case 6: {
128 29 : struct DnssrvQuery2 *r2 = (struct DnssrvQuery2 *)r;
129 29 : if (DEBUGLEVEL >= 10) {
130 0 : NDR_PRINT_FUNCTION_DEBUG(DnssrvQuery2, NDR_IN, r2);
131 : }
132 29 : r2->out.result = dcesrv_DnssrvQuery2(dce_call, mem_ctx, r2);
133 29 : if (dce_call->state_flags & DCESRV_CALL_STATE_FLAG_ASYNC) {
134 0 : DEBUG(5,("function DnssrvQuery2 will reply async\n"));
135 : }
136 29 : break;
137 : }
138 20 : case 7: {
139 20 : struct DnssrvComplexOperation2 *r2 = (struct DnssrvComplexOperation2 *)r;
140 20 : if (DEBUGLEVEL >= 10) {
141 0 : NDR_PRINT_FUNCTION_DEBUG(DnssrvComplexOperation2, NDR_IN, r2);
142 : }
143 20 : r2->out.result = dcesrv_DnssrvComplexOperation2(dce_call, mem_ctx, r2);
144 20 : if (dce_call->state_flags & DCESRV_CALL_STATE_FLAG_ASYNC) {
145 0 : DEBUG(5,("function DnssrvComplexOperation2 will reply async\n"));
146 : }
147 20 : break;
148 : }
149 1262 : case 8: {
150 1262 : struct DnssrvEnumRecords2 *r2 = (struct DnssrvEnumRecords2 *)r;
151 1262 : if (DEBUGLEVEL >= 10) {
152 0 : NDR_PRINT_FUNCTION_DEBUG(DnssrvEnumRecords2, NDR_IN, r2);
153 : }
154 1262 : r2->out.result = dcesrv_DnssrvEnumRecords2(dce_call, mem_ctx, r2);
155 1262 : if (dce_call->state_flags & DCESRV_CALL_STATE_FLAG_ASYNC) {
156 0 : DEBUG(5,("function DnssrvEnumRecords2 will reply async\n"));
157 : }
158 1262 : break;
159 : }
160 3995 : case 9: {
161 3995 : struct DnssrvUpdateRecord2 *r2 = (struct DnssrvUpdateRecord2 *)r;
162 3995 : if (DEBUGLEVEL >= 10) {
163 0 : NDR_PRINT_FUNCTION_DEBUG(DnssrvUpdateRecord2, NDR_IN, r2);
164 : }
165 3995 : r2->out.result = dcesrv_DnssrvUpdateRecord2(dce_call, mem_ctx, r2);
166 3995 : if (dce_call->state_flags & DCESRV_CALL_STATE_FLAG_ASYNC) {
167 0 : DEBUG(5,("function DnssrvUpdateRecord2 will reply async\n"));
168 : }
169 3995 : break;
170 : }
171 :
172 0 : default:
173 0 : dce_call->fault_code = DCERPC_FAULT_OP_RNG_ERROR;
174 0 : break;
175 : }
176 :
177 6961 : if (dce_call->fault_code != 0) {
178 0 : return NT_STATUS_NET_WRITE_FAULT;
179 : }
180 :
181 6961 : return NT_STATUS_OK;
182 : }
183 :
184 6961 : static NTSTATUS dnsserver__op_reply(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx, void *r)
185 : {
186 6961 : uint16_t opnum = dce_call->pkt.u.request.opnum;
187 :
188 6961 : switch (opnum) {
189 3 : case 0: {
190 3 : struct DnssrvOperation *r2 = (struct DnssrvOperation *)r;
191 3 : if (dce_call->state_flags & DCESRV_CALL_STATE_FLAG_ASYNC) {
192 0 : DEBUG(5,("function DnssrvOperation replied async\n"));
193 : }
194 3 : if (DEBUGLEVEL >= 10 && dce_call->fault_code == 0) {
195 0 : NDR_PRINT_FUNCTION_DEBUG(DnssrvOperation, NDR_OUT | NDR_SET_VALUES, r2);
196 : }
197 3 : if (dce_call->fault_code != 0) {
198 0 : DEBUG(2,("dcerpc_fault %s in DnssrvOperation\n", dcerpc_errstr(mem_ctx, dce_call->fault_code)));
199 : }
200 3 : break;
201 : }
202 0 : case 1: {
203 0 : struct DnssrvQuery *r2 = (struct DnssrvQuery *)r;
204 0 : if (dce_call->state_flags & DCESRV_CALL_STATE_FLAG_ASYNC) {
205 0 : DEBUG(5,("function DnssrvQuery replied async\n"));
206 : }
207 0 : if (DEBUGLEVEL >= 10 && dce_call->fault_code == 0) {
208 0 : NDR_PRINT_FUNCTION_DEBUG(DnssrvQuery, NDR_OUT | NDR_SET_VALUES, r2);
209 : }
210 0 : if (dce_call->fault_code != 0) {
211 0 : DEBUG(2,("dcerpc_fault %s in DnssrvQuery\n", dcerpc_errstr(mem_ctx, dce_call->fault_code)));
212 : }
213 0 : break;
214 : }
215 0 : case 2: {
216 0 : struct DnssrvComplexOperation *r2 = (struct DnssrvComplexOperation *)r;
217 0 : if (dce_call->state_flags & DCESRV_CALL_STATE_FLAG_ASYNC) {
218 0 : DEBUG(5,("function DnssrvComplexOperation replied async\n"));
219 : }
220 0 : if (DEBUGLEVEL >= 10 && dce_call->fault_code == 0) {
221 0 : NDR_PRINT_FUNCTION_DEBUG(DnssrvComplexOperation, NDR_OUT | NDR_SET_VALUES, r2);
222 : }
223 0 : if (dce_call->fault_code != 0) {
224 0 : DEBUG(2,("dcerpc_fault %s in DnssrvComplexOperation\n", dcerpc_errstr(mem_ctx, dce_call->fault_code)));
225 : }
226 0 : break;
227 : }
228 0 : case 3: {
229 0 : struct DnssrvEnumRecords *r2 = (struct DnssrvEnumRecords *)r;
230 0 : if (dce_call->state_flags & DCESRV_CALL_STATE_FLAG_ASYNC) {
231 0 : DEBUG(5,("function DnssrvEnumRecords replied async\n"));
232 : }
233 0 : if (DEBUGLEVEL >= 10 && dce_call->fault_code == 0) {
234 0 : NDR_PRINT_FUNCTION_DEBUG(DnssrvEnumRecords, NDR_OUT | NDR_SET_VALUES, r2);
235 : }
236 0 : if (dce_call->fault_code != 0) {
237 0 : DEBUG(2,("dcerpc_fault %s in DnssrvEnumRecords\n", dcerpc_errstr(mem_ctx, dce_call->fault_code)));
238 : }
239 0 : break;
240 : }
241 0 : case 4: {
242 0 : struct DnssrvUpdateRecord *r2 = (struct DnssrvUpdateRecord *)r;
243 0 : if (dce_call->state_flags & DCESRV_CALL_STATE_FLAG_ASYNC) {
244 0 : DEBUG(5,("function DnssrvUpdateRecord replied async\n"));
245 : }
246 0 : if (DEBUGLEVEL >= 10 && dce_call->fault_code == 0) {
247 0 : NDR_PRINT_FUNCTION_DEBUG(DnssrvUpdateRecord, NDR_OUT | NDR_SET_VALUES, r2);
248 : }
249 0 : if (dce_call->fault_code != 0) {
250 0 : DEBUG(2,("dcerpc_fault %s in DnssrvUpdateRecord\n", dcerpc_errstr(mem_ctx, dce_call->fault_code)));
251 : }
252 0 : break;
253 : }
254 1652 : case 5: {
255 1652 : struct DnssrvOperation2 *r2 = (struct DnssrvOperation2 *)r;
256 1652 : if (dce_call->state_flags & DCESRV_CALL_STATE_FLAG_ASYNC) {
257 0 : DEBUG(5,("function DnssrvOperation2 replied async\n"));
258 : }
259 1652 : if (DEBUGLEVEL >= 10 && dce_call->fault_code == 0) {
260 0 : NDR_PRINT_FUNCTION_DEBUG(DnssrvOperation2, NDR_OUT | NDR_SET_VALUES, r2);
261 : }
262 1652 : if (dce_call->fault_code != 0) {
263 0 : DEBUG(2,("dcerpc_fault %s in DnssrvOperation2\n", dcerpc_errstr(mem_ctx, dce_call->fault_code)));
264 : }
265 1652 : break;
266 : }
267 29 : case 6: {
268 29 : struct DnssrvQuery2 *r2 = (struct DnssrvQuery2 *)r;
269 29 : if (dce_call->state_flags & DCESRV_CALL_STATE_FLAG_ASYNC) {
270 0 : DEBUG(5,("function DnssrvQuery2 replied async\n"));
271 : }
272 29 : if (DEBUGLEVEL >= 10 && dce_call->fault_code == 0) {
273 0 : NDR_PRINT_FUNCTION_DEBUG(DnssrvQuery2, NDR_OUT | NDR_SET_VALUES, r2);
274 : }
275 29 : if (dce_call->fault_code != 0) {
276 0 : DEBUG(2,("dcerpc_fault %s in DnssrvQuery2\n", dcerpc_errstr(mem_ctx, dce_call->fault_code)));
277 : }
278 29 : break;
279 : }
280 20 : case 7: {
281 20 : struct DnssrvComplexOperation2 *r2 = (struct DnssrvComplexOperation2 *)r;
282 20 : if (dce_call->state_flags & DCESRV_CALL_STATE_FLAG_ASYNC) {
283 0 : DEBUG(5,("function DnssrvComplexOperation2 replied async\n"));
284 : }
285 20 : if (DEBUGLEVEL >= 10 && dce_call->fault_code == 0) {
286 0 : NDR_PRINT_FUNCTION_DEBUG(DnssrvComplexOperation2, NDR_OUT | NDR_SET_VALUES, r2);
287 : }
288 20 : if (dce_call->fault_code != 0) {
289 0 : DEBUG(2,("dcerpc_fault %s in DnssrvComplexOperation2\n", dcerpc_errstr(mem_ctx, dce_call->fault_code)));
290 : }
291 20 : break;
292 : }
293 1262 : case 8: {
294 1262 : struct DnssrvEnumRecords2 *r2 = (struct DnssrvEnumRecords2 *)r;
295 1262 : if (dce_call->state_flags & DCESRV_CALL_STATE_FLAG_ASYNC) {
296 0 : DEBUG(5,("function DnssrvEnumRecords2 replied async\n"));
297 : }
298 1262 : if (DEBUGLEVEL >= 10 && dce_call->fault_code == 0) {
299 0 : NDR_PRINT_FUNCTION_DEBUG(DnssrvEnumRecords2, NDR_OUT | NDR_SET_VALUES, r2);
300 : }
301 1262 : if (dce_call->fault_code != 0) {
302 0 : DEBUG(2,("dcerpc_fault %s in DnssrvEnumRecords2\n", dcerpc_errstr(mem_ctx, dce_call->fault_code)));
303 : }
304 1262 : break;
305 : }
306 3995 : case 9: {
307 3995 : struct DnssrvUpdateRecord2 *r2 = (struct DnssrvUpdateRecord2 *)r;
308 3995 : if (dce_call->state_flags & DCESRV_CALL_STATE_FLAG_ASYNC) {
309 0 : DEBUG(5,("function DnssrvUpdateRecord2 replied async\n"));
310 : }
311 3995 : if (DEBUGLEVEL >= 10 && dce_call->fault_code == 0) {
312 0 : NDR_PRINT_FUNCTION_DEBUG(DnssrvUpdateRecord2, NDR_OUT | NDR_SET_VALUES, r2);
313 : }
314 3995 : if (dce_call->fault_code != 0) {
315 0 : DEBUG(2,("dcerpc_fault %s in DnssrvUpdateRecord2\n", dcerpc_errstr(mem_ctx, dce_call->fault_code)));
316 : }
317 3995 : break;
318 : }
319 :
320 0 : default:
321 0 : dce_call->fault_code = DCERPC_FAULT_OP_RNG_ERROR;
322 0 : break;
323 : }
324 :
325 6961 : if (dce_call->fault_code != 0) {
326 0 : return NT_STATUS_NET_WRITE_FAULT;
327 : }
328 :
329 6961 : return NT_STATUS_OK;
330 : }
331 :
332 6961 : static NTSTATUS dnsserver__op_ndr_push(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx, struct ndr_push *push, const void *r)
333 : {
334 0 : enum ndr_err_code ndr_err;
335 6961 : uint16_t opnum = dce_call->pkt.u.request.opnum;
336 :
337 6961 : ndr_err = ndr_table_dnsserver.calls[opnum].ndr_push(push, NDR_OUT, r);
338 6961 : if (!NDR_ERR_CODE_IS_SUCCESS(ndr_err)) {
339 0 : dce_call->fault_code = DCERPC_FAULT_NDR;
340 0 : return NT_STATUS_NET_WRITE_FAULT;
341 : }
342 :
343 6961 : return NT_STATUS_OK;
344 : }
345 :
346 : static const struct dcesrv_interface dcesrv_dnsserver_interface = {
347 : .name = "dnsserver",
348 : .syntax_id = {{0x50abc2a4,0x574d,0x40b3,{0x9d,0x66},{0xee,0x4f,0xd5,0xfb,0xa0,0x76}},5.0},
349 : .bind = dnsserver__op_bind,
350 : .unbind = dnsserver__op_unbind,
351 : .ndr_pull = dnsserver__op_ndr_pull,
352 : .dispatch = dnsserver__op_dispatch,
353 : .reply = dnsserver__op_reply,
354 : .ndr_push = dnsserver__op_ndr_push,
355 : .local = NULL,
356 : #ifdef DCESRV_INTERFACE_DNSSERVER_FLAGS
357 : .flags = DCESRV_INTERFACE_DNSSERVER_FLAGS
358 : #else
359 : .flags = 0
360 : #endif
361 : };
362 :
363 :
364 64 : static NTSTATUS dnsserver__op_init_server(struct dcesrv_context *dce_ctx, const struct dcesrv_endpoint_server *ep_server)
365 : {
366 2 : int i;
367 : #ifdef DCESRV_INTERFACE_DNSSERVER_NCACN_NP_SECONDARY_ENDPOINT
368 : const char *ncacn_np_secondary_endpoint =
369 : DCESRV_INTERFACE_DNSSERVER_NCACN_NP_SECONDARY_ENDPOINT;
370 : #else
371 64 : const char *ncacn_np_secondary_endpoint = NULL;
372 : #endif
373 :
374 192 : for (i=0;i<ndr_table_dnsserver.endpoints->count;i++) {
375 4 : NTSTATUS ret;
376 128 : const char *name = ndr_table_dnsserver.endpoints->names[i];
377 :
378 128 : ret = dcesrv_interface_register(dce_ctx,
379 : name,
380 : ncacn_np_secondary_endpoint,
381 : &dcesrv_dnsserver_interface,
382 : NULL);
383 128 : if (!NT_STATUS_IS_OK(ret)) {
384 0 : DEBUG(1,("dnsserver_op_init_server: failed to register endpoint '%s'\n",name));
385 0 : return ret;
386 : }
387 : }
388 :
389 64 : return NT_STATUS_OK;
390 : }
391 :
392 0 : static NTSTATUS dnsserver__op_shutdown_server(struct dcesrv_context *dce_ctx, const struct dcesrv_endpoint_server *ep_server)
393 : {
394 0 : return NT_STATUS_OK;
395 : }
396 :
397 0 : static bool dnsserver__op_interface_by_uuid(struct dcesrv_interface *iface, const struct GUID *uuid, uint32_t if_version)
398 : {
399 0 : if (dcesrv_dnsserver_interface.syntax_id.if_version == if_version &&
400 0 : GUID_equal(&dcesrv_dnsserver_interface.syntax_id.uuid, uuid)) {
401 0 : memcpy(iface,&dcesrv_dnsserver_interface, sizeof(*iface));
402 0 : return true;
403 : }
404 :
405 0 : return false;
406 : }
407 :
408 0 : static bool dnsserver__op_interface_by_name(struct dcesrv_interface *iface, const char *name)
409 : {
410 0 : if (strcmp(dcesrv_dnsserver_interface.name, name)==0) {
411 0 : memcpy(iface, &dcesrv_dnsserver_interface, sizeof(*iface));
412 0 : return true;
413 : }
414 :
415 0 : return false;
416 : }
417 :
418 66 : NTSTATUS dcerpc_server_dnsserver_init(TALLOC_CTX *ctx)
419 : {
420 2 : NTSTATUS ret;
421 2 : static const struct dcesrv_endpoint_server ep_server = {
422 : /* fill in our name */
423 : .name = "dnsserver",
424 :
425 : /* Initialization flag */
426 : .initialized = false,
427 :
428 : /* fill in all the operations */
429 : #ifdef DCESRV_INTERFACE_DNSSERVER_INIT_SERVER
430 : .init_server = DCESRV_INTERFACE_DNSSERVER_INIT_SERVER,
431 : #else
432 : .init_server = dnsserver__op_init_server,
433 : #endif
434 : #ifdef DCESRV_INTERFACE_DNSSERVER_SHUTDOWN_SERVER
435 : .shutdown_server = DCESRV_INTERFACE_DNSSERVER_SHUTDOWN_SERVER,
436 : #else
437 : .shutdown_server = dnsserver__op_shutdown_server,
438 : #endif
439 : .interface_by_uuid = dnsserver__op_interface_by_uuid,
440 : .interface_by_name = dnsserver__op_interface_by_name
441 : };
442 : /* register ourselves with the DCERPC subsystem. */
443 66 : ret = dcerpc_register_ep_server(&ep_server);
444 :
445 66 : if (!NT_STATUS_IS_OK(ret)) {
446 0 : DEBUG(0,("Failed to register 'dnsserver' endpoint server!\n"));
447 0 : return ret;
448 : }
449 :
450 66 : return ret;
451 : }
452 :
|