Small changes for guest authenticated pipes.
[amitay/samba.git] / source3 / rpc_server / srv_pipe.c
1 /* 
2  *  Unix SMB/Netbios implementation.
3  *  Version 1.9.
4  *  RPC Pipe client / server routines
5  *  Copyright (C) Andrew Tridgell              1992-1998
6  *  Copyright (C) Luke Kenneth Casson Leighton 1996-1998,
7  *  Copyright (C) Paul Ashton                  1997-1998.
8  *  Copyright (C) Jeremy Allison                    1999.
9  *  
10  *  This program is free software; you can redistribute it and/or modify
11  *  it under the terms of the GNU General Public License as published by
12  *  the Free Software Foundation; either version 2 of the License, or
13  *  (at your option) any later version.
14  *  
15  *  This program is distributed in the hope that it will be useful,
16  *  but WITHOUT ANY WARRANTY; without even the implied warranty of
17  *  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
18  *  GNU General Public License for more details.
19  *  
20  *  You should have received a copy of the GNU General Public License
21  *  along with this program; if not, write to the Free Software
22  *  Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
23  */
24
25 /*  this module apparently provides an implementation of DCE/RPC over a
26  *  named pipe (IPC$ connection using SMBtrans).  details of DCE/RPC
27  *  documentation are available (in on-line form) from the X-Open group.
28  *
29  *  this module should provide a level of abstraction between SMB
30  *  and DCE/RPC, while minimising the amount of mallocs, unnecessary
31  *  data copies, and network traffic.
32  *
33  *  in this version, which takes a "let's learn what's going on and
34  *  get something running" approach, there is additional network
35  *  traffic generated, but the code should be easier to understand...
36  *
37  *  ... if you read the docs.  or stare at packets for weeks on end.
38  *
39  */
40
41 #include "includes.h"
42
43 static void NTLMSSPcalc_p( pipes_struct *p, unsigned char *data, int len)
44 {
45     unsigned char *hash = p->ntlmssp_hash;
46     unsigned char index_i = hash[256];
47     unsigned char index_j = hash[257];
48     int ind;
49
50     for( ind = 0; ind < len; ind++) {
51         unsigned char tc;
52         unsigned char t;
53
54         index_i++;
55         index_j += hash[index_i];
56
57         tc = hash[index_i];
58         hash[index_i] = hash[index_j];
59         hash[index_j] = tc;
60
61         t = hash[index_i] + hash[index_j];
62         data[ind] = data[ind] ^ hash[t];
63     }
64
65     hash[256] = index_i;
66     hash[257] = index_j;
67 }
68
69 /*******************************************************************
70  Generate the next PDU to be returned from the data in p->rdata. 
71  We cheat here as this function doesn't handle the special auth
72  footers of the authenticated bind response reply.
73  ********************************************************************/
74
75 BOOL create_next_pdu(pipes_struct *p)
76 {
77         RPC_HDR_RESP hdr_resp;
78         BOOL auth_verify = ((p->ntlmssp_chal_flags & NTLMSSP_NEGOTIATE_SIGN) != 0);
79         BOOL auth_seal   = ((p->ntlmssp_chal_flags & NTLMSSP_NEGOTIATE_SEAL) != 0);
80         uint32 data_len;
81         uint32 data_space_available;
82         uint32 data_len_left;
83         prs_struct outgoing_pdu;
84         char *data;
85         char *data_from;
86         uint32 data_pos;
87
88         /*
89          * If we're in the fault state, keep returning fault PDU's until
90          * the pipe gets closed. JRA.
91          */
92
93         if(p->fault_state) {
94                 setup_fault_pdu(p, NT_STATUS(0x1c010002));
95                 return True;
96         }
97
98         memset((char *)&hdr_resp, '\0', sizeof(hdr_resp));
99
100         /* Change the incoming request header to a response. */
101         p->hdr.pkt_type = RPC_RESPONSE;
102
103         /* Set up rpc header flags. */
104         if (p->out_data.data_sent_length == 0)
105                 p->hdr.flags = RPC_FLG_FIRST;
106         else
107                 p->hdr.flags = 0;
108
109         /*
110          * Work out how much we can fit in a single PDU.
111          */
112
113         data_space_available = sizeof(p->out_data.current_pdu) - RPC_HEADER_LEN - RPC_HDR_RESP_LEN;
114         if(p->ntlmssp_auth_validated)
115                 data_space_available -= (RPC_HDR_AUTH_LEN + RPC_AUTH_NTLMSSP_CHK_LEN);
116
117         /*
118          * The amount we send is the minimum of the available
119          * space and the amount left to send.
120          */
121
122         data_len_left = prs_offset(&p->out_data.rdata) - p->out_data.data_sent_length;
123
124         /*
125          * Ensure there really is data left to send.
126          */
127
128         if(!data_len_left) {
129                 DEBUG(0,("create_next_pdu: no data left to send !\n"));
130                 return False;
131         }
132
133         data_len = MIN(data_len_left, data_space_available);
134
135         /*
136          * Set up the alloc hint. This should be the data left to
137          * send.
138          */
139
140         hdr_resp.alloc_hint = data_len_left;
141
142         /*
143          * Set up the header lengths.
144          */
145
146         if (p->ntlmssp_auth_validated) {
147                 p->hdr.frag_len = RPC_HEADER_LEN + RPC_HDR_RESP_LEN + data_len +
148                                         RPC_HDR_AUTH_LEN + RPC_AUTH_NTLMSSP_CHK_LEN;
149                 p->hdr.auth_len = RPC_AUTH_NTLMSSP_CHK_LEN;
150         } else {
151                 p->hdr.frag_len = RPC_HEADER_LEN + RPC_HDR_RESP_LEN + data_len;
152                 p->hdr.auth_len = 0;
153         }
154
155         /*
156          * Work out if this PDU will be the last.
157          */
158
159         if(p->out_data.data_sent_length + data_len >= prs_offset(&p->out_data.rdata))
160                 p->hdr.flags |= RPC_FLG_LAST;
161
162         /*
163          * Init the parse struct to point at the outgoing
164          * data.
165          */
166
167         prs_init( &outgoing_pdu, 0, p->mem_ctx, MARSHALL);
168         prs_give_memory( &outgoing_pdu, (char *)p->out_data.current_pdu, sizeof(p->out_data.current_pdu), False);
169
170         /* Store the header in the data stream. */
171         if(!smb_io_rpc_hdr("hdr", &p->hdr, &outgoing_pdu, 0)) {
172                 DEBUG(0,("create_next_pdu: failed to marshall RPC_HDR.\n"));
173                 prs_mem_free(&outgoing_pdu);
174                 return False;
175         }
176
177         if(!smb_io_rpc_hdr_resp("resp", &hdr_resp, &outgoing_pdu, 0)) {
178                 DEBUG(0,("create_next_pdu: failed to marshall RPC_HDR_RESP.\n"));
179                 prs_mem_free(&outgoing_pdu);
180                 return False;
181         }
182
183         /* Store the current offset. */
184         data_pos = prs_offset(&outgoing_pdu);
185
186         /* Copy the data into the PDU. */
187         data_from = prs_data_p(&p->out_data.rdata) + p->out_data.data_sent_length;
188
189         if(!prs_append_data(&outgoing_pdu, data_from, data_len)) {
190                 DEBUG(0,("create_next_pdu: failed to copy %u bytes of data.\n", (unsigned int)data_len));
191                 prs_mem_free(&outgoing_pdu);
192                 return False;
193         }
194
195         /*
196          * Set data to point to where we copied the data into.
197          */
198
199         data = prs_data_p(&outgoing_pdu) + data_pos;
200
201         if (p->hdr.auth_len > 0) {
202                 uint32 crc32 = 0;
203
204                 DEBUG(5,("create_next_pdu: sign: %s seal: %s data %d auth %d\n",
205                          BOOLSTR(auth_verify), BOOLSTR(auth_seal), data_len, p->hdr.auth_len));
206
207                 if (auth_seal) {
208                         crc32 = crc32_calc_buffer(data, data_len);
209                         NTLMSSPcalc_p(p, (uchar*)data, data_len);
210                 }
211
212                 if (auth_seal || auth_verify) {
213                         RPC_HDR_AUTH auth_info;
214
215                         init_rpc_hdr_auth(&auth_info, NTLMSSP_AUTH_TYPE, NTLMSSP_AUTH_LEVEL, 
216                                         (auth_verify ? RPC_HDR_AUTH_LEN : 0), (auth_verify ? 1 : 0));
217                         if(!smb_io_rpc_hdr_auth("hdr_auth", &auth_info, &outgoing_pdu, 0)) {
218                                 DEBUG(0,("create_next_pdu: failed to marshall RPC_HDR_AUTH.\n"));
219                                 prs_mem_free(&outgoing_pdu);
220                                 return False;
221                         }
222                 }
223
224                 if (auth_verify) {
225                         RPC_AUTH_NTLMSSP_CHK ntlmssp_chk;
226                         char *auth_data = prs_data_p(&outgoing_pdu);
227
228                         p->ntlmssp_seq_num++;
229                         init_rpc_auth_ntlmssp_chk(&ntlmssp_chk, NTLMSSP_SIGN_VERSION,
230                                         crc32, p->ntlmssp_seq_num++);
231                         auth_data = prs_data_p(&outgoing_pdu) + prs_offset(&outgoing_pdu) + 4;
232                         if(!smb_io_rpc_auth_ntlmssp_chk("auth_sign", &ntlmssp_chk, &outgoing_pdu, 0)) {
233                                 DEBUG(0,("create_next_pdu: failed to marshall RPC_AUTH_NTLMSSP_CHK.\n"));
234                                 prs_mem_free(&outgoing_pdu);
235                                 return False;
236                         }
237                         NTLMSSPcalc_p(p, (uchar*)auth_data, RPC_AUTH_NTLMSSP_CHK_LEN - 4);
238                 }
239         }
240
241         /*
242          * Setup the counts for this PDU.
243          */
244
245         p->out_data.data_sent_length += data_len;
246         p->out_data.current_pdu_len = p->hdr.frag_len;
247         p->out_data.current_pdu_sent = 0;
248
249         prs_mem_free(&outgoing_pdu);
250         return True;
251 }
252
253 /*******************************************************************
254  Process an NTLMSSP authentication response.
255  If this function succeeds, the user has been authenticated
256  and their domain, name and calling workstation stored in
257  the pipe struct.
258  The initial challenge is stored in p->challenge.
259  *******************************************************************/
260
261 static BOOL api_pipe_ntlmssp_verify(pipes_struct *p, RPC_AUTH_NTLMSSP_RESP *ntlmssp_resp)
262 {
263         uchar lm_owf[24];
264         uchar nt_owf[128];
265         int nt_pw_len;
266         int lm_pw_len;
267         fstring user_name;
268         fstring pipe_user_name;
269         fstring domain;
270         fstring wks;
271         BOOL guest_user = False;
272         uchar null_smb_passwd[16];
273
274         const uchar *smb_passwd_ptr = NULL;
275         
276         auth_usersupplied_info *user_info = NULL;
277         auth_serversupplied_info *server_info = NULL;
278
279         uid_t *puid;
280         uid_t *pgid;
281
282         DEBUG(5,("api_pipe_ntlmssp_verify: checking user details\n"));
283
284         memset(p->user_name, '\0', sizeof(p->user_name));
285         memset(p->pipe_user_name, '\0', sizeof(p->pipe_user_name));
286         memset(p->domain, '\0', sizeof(p->domain));
287         memset(p->wks, '\0', sizeof(p->wks));
288
289         /* Set up for non-authenticated user. */
290         delete_nt_token(&p->pipe_user.nt_user_token);
291         p->pipe_user.ngroups = 0;
292         SAFE_FREE( p->pipe_user.groups);
293
294         /* 
295          * Setup an empty password for a guest user.
296          */
297
298         /*
299          * We always negotiate UNICODE.
300          */
301
302         if (p->ntlmssp_chal_flags & NTLMSSP_NEGOTIATE_UNICODE) {
303                 rpcstr_pull(user_name, ntlmssp_resp->user, sizeof(fstring), ntlmssp_resp->hdr_usr.str_str_len*2, 0 );
304                 rpcstr_pull(domain, ntlmssp_resp->domain, sizeof(fstring), ntlmssp_resp->hdr_domain.str_str_len*2, 0);
305                 rpcstr_pull(wks, ntlmssp_resp->wks, sizeof(fstring), ntlmssp_resp->hdr_wks.str_str_len*2, 0);
306         } else {
307                 pull_ascii_fstring(user_name, ntlmssp_resp->user);
308                 pull_ascii_fstring(domain, ntlmssp_resp->domain);
309                 pull_ascii_fstring(wks, ntlmssp_resp->wks);
310         }
311
312         DEBUG(5,("user: %s domain: %s wks: %s\n", user_name, domain, wks));
313
314         nt_pw_len = MIN(sizeof(nt_owf), ntlmssp_resp->hdr_nt_resp.str_str_len);
315         lm_pw_len = MIN(sizeof(lm_owf), ntlmssp_resp->hdr_lm_resp.str_str_len);
316
317         memcpy(lm_owf, ntlmssp_resp->lm_resp, sizeof(lm_owf));
318         memcpy(nt_owf, ntlmssp_resp->nt_resp, nt_pw_len);
319
320 #ifdef DEBUG_PASSWORD
321         DEBUG(100,("lm, nt owfs, chal\n"));
322         dump_data(100, (char *)lm_owf, sizeof(lm_owf));
323         dump_data(100, (char *)nt_owf, nt_pw_len);
324         dump_data(100, (char *)p->challenge, 8);
325 #endif
326
327         /*
328          * Allow guest access. Patch from Shirish Kalele <kalele@veritas.com>.
329          */
330
331         if((strlen(user_name) == 0) && 
332            (ntlmssp_resp->hdr_nt_resp.str_str_len==0))
333         {
334                 guest_user = True;
335                 
336                 fstrcpy(pipe_user_name, lp_guestaccount(-1));
337                 DEBUG(100,("Null user in NTLMSSP verification. Using guest = %s\n", pipe_user_name));
338
339         } else {
340
341                 /* 
342                  * Do the length checking only if user is not NULL.
343                  */
344
345                 if (ntlmssp_resp->hdr_lm_resp.str_str_len == 0)
346                         return False;
347                 if (ntlmssp_resp->hdr_nt_resp.str_str_len == 0)
348                         return False;
349                 if (ntlmssp_resp->hdr_usr.str_str_len == 0)
350                         return False;
351                 if (ntlmssp_resp->hdr_domain.str_str_len == 0)
352                         return False;
353                 if (ntlmssp_resp->hdr_wks.str_str_len == 0)
354                         return False;
355
356         }
357
358         if(!guest_user) {
359                 NTSTATUS nt_status;
360
361                 if (!make_user_info_netlogon_network(&user_info, 
362                                                      user_name, domain, wks,  (uchar*)p->challenge, 
363                                                      lm_owf, lm_pw_len, 
364                                                      nt_owf, nt_pw_len)) {
365                         DEBUG(0,("make_user_info_netlogon_network failed!  Failing authenticaion.\n"));
366                         return False;
367                 }
368
369                 nt_status = check_password(user_info, &server_info); 
370                 
371                 free_user_info(&user_info);
372
373                 p->ntlmssp_auth_validated = NT_STATUS_IS_OK(nt_status);
374
375                 if (!p->ntlmssp_auth_validated) {
376                         DEBUG(1,("api_pipe_ntlmssp_verify: User %s\\%s from machine %s \
377 failed authentication on named pipe %s.\n", domain, pipe_user_name, wks, p->name ));
378                         free_server_info(&server_info);
379                         return False;
380                 }
381         } else {
382                 /* This includes a NULLed out first_8_lm_hash */
383                 make_server_info_guest(&server_info);
384         }
385
386         /*
387          * Set up the sign/seal data.
388          */
389
390         {
391                 uchar p24[24];
392                 NTLMSSPOWFencrypt(server_info->first_8_lm_hash, lm_owf, p24);
393                 {
394                         unsigned char j = 0;
395                         int ind;
396
397                         unsigned char k2[8];
398
399                         memcpy(k2, p24, 5);
400                         k2[5] = 0xe5;
401                         k2[6] = 0x38;
402                         k2[7] = 0xb0;
403
404                         for (ind = 0; ind < 256; ind++)
405                                 p->ntlmssp_hash[ind] = (unsigned char)ind;
406
407                         for( ind = 0; ind < 256; ind++) {
408                                 unsigned char tc;
409
410                                 j += (p->ntlmssp_hash[ind] + k2[ind%8]);
411
412                                 tc = p->ntlmssp_hash[ind];
413                                 p->ntlmssp_hash[ind] = p->ntlmssp_hash[j];
414                                 p->ntlmssp_hash[j] = tc;
415                         }
416
417                         p->ntlmssp_hash[256] = 0;
418                         p->ntlmssp_hash[257] = 0;
419                 }
420 /*              NTLMSSPhash(p->ntlmssp_hash, p24); */
421                 p->ntlmssp_seq_num = 0;
422
423         }
424
425         fstrcpy(p->user_name, user_name);
426         fstrcpy(p->pipe_user_name, pipe_user_name);
427         fstrcpy(p->domain, domain);
428         fstrcpy(p->wks, wks);
429
430         /*
431          * Store the UNIX credential data (uid/gid pair) in the pipe structure.
432          */
433
434         puid = pdb_get_uid(server_info->sam_account);
435         pgid = pdb_get_gid(server_info->sam_account);
436         
437         if (!puid || !pgid) {
438                 DEBUG(0,("Attempted authenticated pipe with invalid user.  No uid/gid in SAM_ACCOUNT\n"));
439                 free_server_info(&server_info);
440                 return False;
441         }
442         
443         p->pipe_user.uid = *puid;
444         p->pipe_user.gid = *pgid;
445
446         /* Set up pipe user group membership. */
447         initialise_groups(pipe_user_name, p->pipe_user.uid, p->pipe_user.gid);
448         get_current_groups( &p->pipe_user.ngroups, &p->pipe_user.groups);
449
450         /* Create an NT_USER_TOKEN struct for this user. */
451         p->pipe_user.nt_user_token = create_nt_token(p->pipe_user.uid,p->pipe_user.gid,
452                                                      p->pipe_user.ngroups, p->pipe_user.groups,
453                                                      guest_user);
454
455         p->ntlmssp_auth_validated = True;
456
457         pdb_free_sam(&server_info->sam_account);
458         return True;
459 }
460
461 /*******************************************************************
462  The switch table for the pipe names and the functions to handle them.
463  *******************************************************************/
464
465 struct api_cmd
466 {
467   char * pipe_clnt_name;
468   char * pipe_srv_name;
469   BOOL (*fn) (pipes_struct *);
470 };
471
472 static struct api_cmd api_fd_commands[] =
473 {
474     { "lsarpc",   "lsass",   api_ntlsa_rpc },
475     { "samr",     "lsass",   api_samr_rpc },
476     { "srvsvc",   "ntsvcs",  api_srvsvc_rpc },
477     { "wkssvc",   "ntsvcs",  api_wkssvc_rpc },
478     { "NETLOGON", "lsass",   api_netlog_rpc },
479     { "winreg",   "winreg",  api_reg_rpc },
480     { "spoolss",  "spoolss", api_spoolss_rpc },
481     { "netdfs",   "netdfs" , api_netdfs_rpc },
482     { NULL,       NULL,      NULL }
483 };
484
485 /*******************************************************************
486  This is the client reply to our challenge for an authenticated 
487  bind request. The challenge we sent is in p->challenge.
488 *******************************************************************/
489
490 BOOL api_pipe_bind_auth_resp(pipes_struct *p, prs_struct *rpc_in_p)
491 {
492         RPC_HDR_AUTHA autha_info;
493         RPC_AUTH_VERIFIER auth_verifier;
494         RPC_AUTH_NTLMSSP_RESP ntlmssp_resp;
495
496         DEBUG(5,("api_pipe_bind_auth_resp: decode request. %d\n", __LINE__));
497
498         if (p->hdr.auth_len == 0) {
499                 DEBUG(0,("api_pipe_bind_auth_resp: No auth field sent !\n"));
500                 return False;
501         }
502
503         /*
504          * Decode the authentication verifier response.
505          */
506
507         if(!smb_io_rpc_hdr_autha("", &autha_info, rpc_in_p, 0)) {
508                 DEBUG(0,("api_pipe_bind_auth_resp: unmarshall of RPC_HDR_AUTHA failed.\n"));
509                 return False;
510         }
511
512         if (autha_info.auth_type != NTLMSSP_AUTH_TYPE || autha_info.auth_level != NTLMSSP_AUTH_LEVEL) {
513                 DEBUG(0,("api_pipe_bind_auth_resp: incorrect auth type (%d) or level (%d).\n",
514                         (int)autha_info.auth_type, (int)autha_info.auth_level ));
515                 return False;
516         }
517
518         if(!smb_io_rpc_auth_verifier("", &auth_verifier, rpc_in_p, 0)) {
519                 DEBUG(0,("api_pipe_bind_auth_resp: unmarshall of RPC_AUTH_VERIFIER failed.\n"));
520                 return False;
521         }
522
523         /*
524          * Ensure this is a NTLMSSP_AUTH packet type.
525          */
526
527         if (!rpc_auth_verifier_chk(&auth_verifier, "NTLMSSP", NTLMSSP_AUTH)) {
528                 DEBUG(0,("api_pipe_bind_auth_resp: rpc_auth_verifier_chk failed.\n"));
529                 return False;
530         }
531
532         if(!smb_io_rpc_auth_ntlmssp_resp("", &ntlmssp_resp, rpc_in_p, 0)) {
533                 DEBUG(0,("api_pipe_bind_auth_resp: Failed to unmarshall RPC_AUTH_NTLMSSP_RESP.\n"));
534                 return False;
535         }
536
537         /*
538          * The following call actually checks the challenge/response data.
539          * for correctness against the given DOMAIN\user name.
540          */
541         
542         if (!api_pipe_ntlmssp_verify(p, &ntlmssp_resp))
543                 return False;
544
545         p->pipe_bound = True
546 ;
547         return True;
548 }
549
550 /*******************************************************************
551  Marshall a bind_nak pdu.
552 *******************************************************************/
553
554 static BOOL setup_bind_nak(pipes_struct *p)
555 {
556         prs_struct outgoing_rpc;
557         RPC_HDR nak_hdr;
558         uint16 zero = 0;
559
560         /* Free any memory in the current return data buffer. */
561         prs_mem_free(&p->out_data.rdata);
562
563         /*
564          * Marshall directly into the outgoing PDU space. We
565          * must do this as we need to set to the bind response
566          * header and are never sending more than one PDU here.
567          */
568
569         prs_init( &outgoing_rpc, 0, p->mem_ctx, MARSHALL);
570         prs_give_memory( &outgoing_rpc, (char *)p->out_data.current_pdu, sizeof(p->out_data.current_pdu), False);
571
572
573         /*
574          * Initialize a bind_nak header.
575          */
576
577         init_rpc_hdr(&nak_hdr, RPC_BINDNACK, RPC_FLG_FIRST | RPC_FLG_LAST,
578             p->hdr.call_id, RPC_HEADER_LEN + sizeof(uint16), 0);
579
580         /*
581          * Marshall the header into the outgoing PDU.
582          */
583
584         if(!smb_io_rpc_hdr("", &nak_hdr, &outgoing_rpc, 0)) {
585                 DEBUG(0,("setup_bind_nak: marshalling of RPC_HDR failed.\n"));
586                 prs_mem_free(&outgoing_rpc);
587                 return False;
588         }
589
590         /*
591          * Now add the reject reason.
592          */
593
594         if(!prs_uint16("reject code", &outgoing_rpc, 0, &zero)) {
595                 prs_mem_free(&outgoing_rpc);
596         return False;
597         }
598
599         p->out_data.data_sent_length = 0;
600         p->out_data.current_pdu_len = prs_offset(&outgoing_rpc);
601         p->out_data.current_pdu_sent = 0;
602
603         p->pipe_bound = False;
604
605         return True;
606 }
607
608 /*******************************************************************
609  Marshall a fault pdu.
610 *******************************************************************/
611
612 BOOL setup_fault_pdu(pipes_struct *p, NTSTATUS status)
613 {
614         prs_struct outgoing_pdu;
615         RPC_HDR fault_hdr;
616         RPC_HDR_RESP hdr_resp;
617         RPC_HDR_FAULT fault_resp;
618
619         /* Free any memory in the current return data buffer. */
620         prs_mem_free(&p->out_data.rdata);
621
622         /*
623          * Marshall directly into the outgoing PDU space. We
624          * must do this as we need to set to the bind response
625          * header and are never sending more than one PDU here.
626          */
627
628         prs_init( &outgoing_pdu, 0, p->mem_ctx, MARSHALL);
629         prs_give_memory( &outgoing_pdu, (char *)p->out_data.current_pdu, sizeof(p->out_data.current_pdu), False);
630
631         /*
632          * Initialize a fault header.
633          */
634
635         init_rpc_hdr(&fault_hdr, RPC_FAULT, RPC_FLG_FIRST | RPC_FLG_LAST | RPC_FLG_NOCALL,
636             p->hdr.call_id, RPC_HEADER_LEN + RPC_HDR_RESP_LEN + RPC_HDR_FAULT_LEN, 0);
637
638         /*
639          * Initialize the HDR_RESP and FAULT parts of the PDU.
640          */
641
642         memset((char *)&hdr_resp, '\0', sizeof(hdr_resp));
643
644         fault_resp.status = status;
645         fault_resp.reserved = 0;
646
647         /*
648          * Marshall the header into the outgoing PDU.
649          */
650
651         if(!smb_io_rpc_hdr("", &fault_hdr, &outgoing_pdu, 0)) {
652                 DEBUG(0,("setup_fault_pdu: marshalling of RPC_HDR failed.\n"));
653                 prs_mem_free(&outgoing_pdu);
654                 return False;
655         }
656
657         if(!smb_io_rpc_hdr_resp("resp", &hdr_resp, &outgoing_pdu, 0)) {
658                 DEBUG(0,("setup_fault_pdu: failed to marshall RPC_HDR_RESP.\n"));
659                 prs_mem_free(&outgoing_pdu);
660                 return False;
661         }
662
663         if(!smb_io_rpc_hdr_fault("fault", &fault_resp, &outgoing_pdu, 0)) {
664                 DEBUG(0,("setup_fault_pdu: failed to marshall RPC_HDR_FAULT.\n"));
665                 prs_mem_free(&outgoing_pdu);
666                 return False;
667         }
668
669         p->out_data.data_sent_length = 0;
670         p->out_data.current_pdu_len = prs_offset(&outgoing_pdu);
671         p->out_data.current_pdu_sent = 0;
672
673         prs_mem_free(&outgoing_pdu);
674         return True;
675 }
676
677 /*******************************************************************
678  Ensure a bind request has the correct abstract & transfer interface.
679  Used to reject unknown binds from Win2k.
680 *******************************************************************/
681
682 BOOL check_bind_req(char* pipe_name, RPC_IFACE* abstract,
683                                         RPC_IFACE* transfer)
684 {
685         extern struct pipe_id_info pipe_names[];
686         int i=0;
687         fstring pname;
688         fstrcpy(pname,"\\PIPE\\");
689         fstrcat(pname,pipe_name);
690
691         for(i=0;pipe_names[i].client_pipe; i++) {
692                 if(strequal(pipe_names[i].client_pipe, pname))
693                         break;
694         }
695
696         if(pipe_names[i].client_pipe == NULL)
697                 return False;
698
699         /* check the abstract interface */
700         if((abstract->version != pipe_names[i].abstr_syntax.version) ||
701                 (memcmp(&abstract->uuid, &pipe_names[i].abstr_syntax.uuid,
702                         sizeof(RPC_UUID)) != 0))
703                 return False;
704
705         /* check the transfer interface */
706         if((transfer->version != pipe_names[i].trans_syntax.version) ||
707                 (memcmp(&transfer->uuid, &pipe_names[i].trans_syntax.uuid,
708                         sizeof(RPC_UUID)) != 0))
709                 return False;
710
711         return True;
712 }
713
714 /*******************************************************************
715  Respond to a pipe bind request.
716 *******************************************************************/
717
718 BOOL api_pipe_bind_req(pipes_struct *p, prs_struct *rpc_in_p)
719 {
720         RPC_HDR_BA hdr_ba;
721         RPC_HDR_RB hdr_rb;
722         RPC_HDR_AUTH auth_info;
723         uint16 assoc_gid;
724         fstring ack_pipe_name;
725         prs_struct out_hdr_ba;
726         prs_struct out_auth;
727         prs_struct outgoing_rpc;
728         int i = 0;
729         int auth_len = 0;
730         enum RPC_PKT_TYPE reply_pkt_type;
731
732         p->ntlmssp_auth_requested = False;
733
734         DEBUG(5,("api_pipe_bind_req: decode request. %d\n", __LINE__));
735
736         /*
737          * Try and find the correct pipe name to ensure
738          * that this is a pipe name we support.
739          */
740
741         for (i = 0; api_fd_commands[i].pipe_clnt_name; i++) {
742                 if (strequal(api_fd_commands[i].pipe_clnt_name, p->name) &&
743                     api_fd_commands[i].fn != NULL) {
744                         DEBUG(3,("api_pipe_bind_req: \\PIPE\\%s -> \\PIPE\\%s\n",
745                                    api_fd_commands[i].pipe_clnt_name,
746                                    api_fd_commands[i].pipe_srv_name));
747                         fstrcpy(p->pipe_srv_name, api_fd_commands[i].pipe_srv_name);
748                         break;
749                 }
750         }
751
752         if (api_fd_commands[i].fn == NULL) {
753                 DEBUG(3,("api_pipe_bind_req: Unknown pipe name %s in bind request.\n",
754                         p->name ));
755                 if(!setup_bind_nak(p))
756                         return False;
757                 return True;
758         }
759
760         /* decode the bind request */
761         if(!smb_io_rpc_hdr_rb("", &hdr_rb, rpc_in_p, 0))  {
762                 DEBUG(0,("api_pipe_bind_req: unable to unmarshall RPC_HDR_RB struct.\n"));
763                 return False;
764         }
765
766         /*
767          * Check if this is an authenticated request.
768          */
769
770         if (p->hdr.auth_len != 0) {
771                 RPC_AUTH_VERIFIER auth_verifier;
772                 RPC_AUTH_NTLMSSP_NEG ntlmssp_neg;
773
774                 /* 
775                  * Decode the authentication verifier.
776                  */
777
778                 if(!smb_io_rpc_hdr_auth("", &auth_info, rpc_in_p, 0)) {
779                         DEBUG(0,("api_pipe_bind_req: unable to unmarshall RPC_HDR_AUTH struct.\n"));
780                         return False;
781                 }
782
783                 /*
784                  * We only support NTLMSSP_AUTH_TYPE requests.
785                  */
786
787                 if(auth_info.auth_type != NTLMSSP_AUTH_TYPE) {
788                         DEBUG(0,("api_pipe_bind_req: unknown auth type %x requested.\n",
789                                 auth_info.auth_type ));
790                         return False;
791                 }
792
793                 if(!smb_io_rpc_auth_verifier("", &auth_verifier, rpc_in_p, 0)) {
794                         DEBUG(0,("api_pipe_bind_req: unable to unmarshall RPC_HDR_AUTH struct.\n"));
795                         return False;
796                 }
797
798                 if(!strequal(auth_verifier.signature, "NTLMSSP")) {
799                         DEBUG(0,("api_pipe_bind_req: auth_verifier.signature != NTLMSSP\n"));
800                         return False;
801                 }
802
803                 if(auth_verifier.msg_type != NTLMSSP_NEGOTIATE) {
804                         DEBUG(0,("api_pipe_bind_req: auth_verifier.msg_type (%d) != NTLMSSP_NEGOTIATE\n",
805                                 auth_verifier.msg_type));
806                         return False;
807                 }
808
809                 if(!smb_io_rpc_auth_ntlmssp_neg("", &ntlmssp_neg, rpc_in_p, 0)) {
810                         DEBUG(0,("api_pipe_bind_req: Failed to unmarshall RPC_AUTH_NTLMSSP_NEG.\n"));
811                         return False;
812                 }
813
814                 p->ntlmssp_chal_flags = SMBD_NTLMSSP_NEG_FLAGS;
815                 p->ntlmssp_auth_requested = True;
816         }
817
818         switch(p->hdr.pkt_type) {
819                 case RPC_BIND:
820                         /* name has to be \PIPE\xxxxx */
821                         fstrcpy(ack_pipe_name, "\\PIPE\\");
822                         fstrcat(ack_pipe_name, p->pipe_srv_name);
823                         reply_pkt_type = RPC_BINDACK;
824                         break;
825                 case RPC_ALTCONT:
826                         /* secondary address CAN be NULL
827                          * as the specs say it's ignored.
828                          * It MUST NULL to have the spoolss working.
829                          */
830                         fstrcpy(ack_pipe_name,"");
831                         reply_pkt_type = RPC_ALTCONTRESP;
832                         break;
833                 default:
834                         return False;
835         }
836
837         DEBUG(5,("api_pipe_bind_req: make response. %d\n", __LINE__));
838
839         /* 
840          * Marshall directly into the outgoing PDU space. We
841          * must do this as we need to set to the bind response
842          * header and are never sending more than one PDU here.
843          */
844
845         prs_init( &outgoing_rpc, 0, p->mem_ctx, MARSHALL);
846         prs_give_memory( &outgoing_rpc, (char *)p->out_data.current_pdu, sizeof(p->out_data.current_pdu), False);
847
848         /*
849          * Setup the memory to marshall the ba header, and the
850          * auth footers.
851          */
852
853         if(!prs_init(&out_hdr_ba, 1024, p->mem_ctx, MARSHALL)) {
854                 DEBUG(0,("api_pipe_bind_req: malloc out_hdr_ba failed.\n"));
855                 prs_mem_free(&outgoing_rpc);
856                 return False;
857         }
858
859         if(!prs_init(&out_auth, 1024, p->mem_ctx, MARSHALL)) {
860                 DEBUG(0,("pi_pipe_bind_req: malloc out_auth failed.\n"));
861                 prs_mem_free(&outgoing_rpc);
862                 prs_mem_free(&out_hdr_ba);
863                 return False;
864         }
865
866         if (p->ntlmssp_auth_requested)
867                 assoc_gid = 0x7a77;
868         else
869                 assoc_gid = hdr_rb.bba.assoc_gid ? hdr_rb.bba.assoc_gid : 0x53f0;
870
871         /*
872          * Create the bind response struct.
873          */
874
875         /* If the requested abstract synt uuid doesn't match our client pipe,
876                 reject the bind_ack & set the transfer interface synt to all 0's,
877                 ver 0 (observed when NT5 attempts to bind to abstract interfaces
878                 unknown to NT4)
879                 Needed when adding entries to a DACL from NT5 - SK */
880
881         if(check_bind_req(p->name, &hdr_rb.abstract, &hdr_rb.transfer)) {
882                 init_rpc_hdr_ba(&hdr_ba,
883                         MAX_PDU_FRAG_LEN,
884                         MAX_PDU_FRAG_LEN,
885                         assoc_gid,
886                         ack_pipe_name,
887                         0x1, 0x0, 0x0,
888                         &hdr_rb.transfer);
889         } else {
890                 RPC_IFACE null_interface;
891                 ZERO_STRUCT(null_interface);
892                 /* Rejection reason: abstract syntax not supported */
893                 init_rpc_hdr_ba(&hdr_ba, MAX_PDU_FRAG_LEN,
894                                         MAX_PDU_FRAG_LEN, assoc_gid,
895                                         ack_pipe_name, 0x1, 0x2, 0x1,
896                                         &null_interface);
897         }
898
899         /*
900          * and marshall it.
901          */
902
903         if(!smb_io_rpc_hdr_ba("", &hdr_ba, &out_hdr_ba, 0)) {
904                 DEBUG(0,("api_pipe_bind_req: marshalling of RPC_HDR_BA failed.\n"));
905                 goto err_exit;
906         }
907
908         /*
909          * Now the authentication.
910          */
911
912         if (p->ntlmssp_auth_requested) {
913                 RPC_AUTH_VERIFIER auth_verifier;
914                 RPC_AUTH_NTLMSSP_CHAL ntlmssp_chal;
915
916                 generate_random_buffer(p->challenge, 8, False);
917
918                 /*** Authentication info ***/
919
920                 init_rpc_hdr_auth(&auth_info, NTLMSSP_AUTH_TYPE, NTLMSSP_AUTH_LEVEL, RPC_HDR_AUTH_LEN, 1);
921                 if(!smb_io_rpc_hdr_auth("", &auth_info, &out_auth, 0)) {
922                         DEBUG(0,("api_pipe_bind_req: marshalling of RPC_HDR_AUTH failed.\n"));
923                         goto err_exit;
924                 }
925
926                 /*** NTLMSSP verifier ***/
927
928                 init_rpc_auth_verifier(&auth_verifier, "NTLMSSP", NTLMSSP_CHALLENGE);
929                 if(!smb_io_rpc_auth_verifier("", &auth_verifier, &out_auth, 0)) {
930                         DEBUG(0,("api_pipe_bind_req: marshalling of RPC_AUTH_VERIFIER failed.\n"));
931                         goto err_exit;
932                 }
933
934                 /* NTLMSSP challenge ***/
935
936                 init_rpc_auth_ntlmssp_chal(&ntlmssp_chal, p->ntlmssp_chal_flags, p->challenge);
937                 if(!smb_io_rpc_auth_ntlmssp_chal("", &ntlmssp_chal, &out_auth, 0)) {
938                         DEBUG(0,("api_pipe_bind_req: marshalling of RPC_AUTH_NTLMSSP_CHAL failed.\n"));
939                         goto err_exit;
940                 }
941
942                 /* Auth len in the rpc header doesn't include auth_header. */
943                 auth_len = prs_offset(&out_auth) - RPC_HDR_AUTH_LEN;
944         }
945
946         /*
947          * Create the header, now we know the length.
948          */
949
950         init_rpc_hdr(&p->hdr, reply_pkt_type, RPC_FLG_FIRST | RPC_FLG_LAST,
951                         p->hdr.call_id,
952                         RPC_HEADER_LEN + prs_offset(&out_hdr_ba) + prs_offset(&out_auth),
953                         auth_len);
954
955         /*
956          * Marshall the header into the outgoing PDU.
957          */
958
959         if(!smb_io_rpc_hdr("", &p->hdr, &outgoing_rpc, 0)) {
960                 DEBUG(0,("pi_pipe_bind_req: marshalling of RPC_HDR failed.\n"));
961                 goto err_exit;
962         }
963
964         /*
965          * Now add the RPC_HDR_BA and any auth needed.
966          */
967
968         if(!prs_append_prs_data( &outgoing_rpc, &out_hdr_ba)) {
969                 DEBUG(0,("api_pipe_bind_req: append of RPC_HDR_BA failed.\n"));
970                 goto err_exit;
971         }
972
973         if(p->ntlmssp_auth_requested && !prs_append_prs_data( &outgoing_rpc, &out_auth)) {
974                 DEBUG(0,("api_pipe_bind_req: append of auth info failed.\n"));
975                 goto err_exit;
976         }
977
978         if(!p->ntlmssp_auth_requested)
979                 p->pipe_bound = True;
980
981         /*
982          * Setup the lengths for the initial reply.
983          */
984
985         p->out_data.data_sent_length = 0;
986         p->out_data.current_pdu_len = prs_offset(&outgoing_rpc);
987         p->out_data.current_pdu_sent = 0;
988
989         prs_mem_free(&out_hdr_ba);
990         prs_mem_free(&out_auth);
991
992         return True;
993
994   err_exit:
995
996         prs_mem_free(&outgoing_rpc);
997         prs_mem_free(&out_hdr_ba);
998         prs_mem_free(&out_auth);
999         return False;
1000 }
1001
1002 /****************************************************************************
1003  Deal with sign & seal processing on an RPC request.
1004 ****************************************************************************/
1005
1006 BOOL api_pipe_auth_process(pipes_struct *p, prs_struct *rpc_in)
1007 {
1008         /*
1009          * We always negotiate the following two bits....
1010          */
1011         BOOL auth_verify = ((p->ntlmssp_chal_flags & NTLMSSP_NEGOTIATE_SIGN) != 0);
1012         BOOL auth_seal   = ((p->ntlmssp_chal_flags & NTLMSSP_NEGOTIATE_SEAL) != 0);
1013         int data_len;
1014         int auth_len;
1015         uint32 old_offset;
1016         uint32 crc32 = 0;
1017
1018         auth_len = p->hdr.auth_len;
1019
1020         if ((auth_len != RPC_AUTH_NTLMSSP_CHK_LEN) && auth_verify) {
1021                 DEBUG(0,("api_pipe_auth_process: Incorrect auth_len %d.\n", auth_len ));
1022                 return False;
1023         }
1024
1025         /*
1026          * The following is that length of the data we must verify or unseal.
1027          * This doesn't include the RPC headers or the auth_len or the RPC_HDR_AUTH_LEN
1028          * preceeding the auth_data.
1029          */
1030
1031         data_len = p->hdr.frag_len - RPC_HEADER_LEN - RPC_HDR_REQ_LEN - 
1032                         (auth_verify ? RPC_HDR_AUTH_LEN : 0) - auth_len;
1033         
1034         DEBUG(5,("api_pipe_auth_process: sign: %s seal: %s data %d auth %d\n",
1035                  BOOLSTR(auth_verify), BOOLSTR(auth_seal), data_len, auth_len));
1036
1037         if (auth_seal) {
1038                 /*
1039                  * The data in rpc_in doesn't contain the RPC_HEADER as this
1040                  * has already been consumed.
1041                  */
1042                 char *data = prs_data_p(rpc_in) + RPC_HDR_REQ_LEN;
1043                 NTLMSSPcalc_p(p, (uchar*)data, data_len);
1044                 crc32 = crc32_calc_buffer(data, data_len);
1045         }
1046
1047         old_offset = prs_offset(rpc_in);
1048
1049         if (auth_seal || auth_verify) {
1050                 RPC_HDR_AUTH auth_info;
1051
1052                 if(!prs_set_offset(rpc_in, old_offset + data_len)) {
1053                         DEBUG(0,("api_pipe_auth_process: cannot move offset to %u.\n",
1054                                 (unsigned int)old_offset + data_len ));
1055                         return False;
1056                 }
1057
1058                 if(!smb_io_rpc_hdr_auth("hdr_auth", &auth_info, rpc_in, 0)) {
1059                         DEBUG(0,("api_pipe_auth_process: failed to unmarshall RPC_HDR_AUTH.\n"));
1060                         return False;
1061                 }
1062         }
1063
1064         if (auth_verify) {
1065                 RPC_AUTH_NTLMSSP_CHK ntlmssp_chk;
1066                 char *req_data = prs_data_p(rpc_in) + prs_offset(rpc_in) + 4;
1067
1068                 DEBUG(5,("api_pipe_auth_process: auth %d\n", prs_offset(rpc_in) + 4));
1069
1070                 /*
1071                  * Ensure we have RPC_AUTH_NTLMSSP_CHK_LEN - 4 more bytes in the
1072                  * incoming buffer.
1073                  */
1074                 if(prs_mem_get(rpc_in, RPC_AUTH_NTLMSSP_CHK_LEN - 4) == NULL) {
1075                         DEBUG(0,("api_pipe_auth_process: missing %d bytes in buffer.\n",
1076                                 RPC_AUTH_NTLMSSP_CHK_LEN - 4 ));
1077                         return False;
1078                 }
1079
1080                 NTLMSSPcalc_p(p, (uchar*)req_data, RPC_AUTH_NTLMSSP_CHK_LEN - 4);
1081                 if(!smb_io_rpc_auth_ntlmssp_chk("auth_sign", &ntlmssp_chk, rpc_in, 0)) {
1082                         DEBUG(0,("api_pipe_auth_process: failed to unmarshall RPC_AUTH_NTLMSSP_CHK.\n"));
1083                         return False;
1084                 }
1085
1086                 if (!rpc_auth_ntlmssp_chk(&ntlmssp_chk, crc32, p->ntlmssp_seq_num)) {
1087                         DEBUG(0,("api_pipe_auth_process: NTLMSSP check failed.\n"));
1088                         return False;
1089                 }
1090         }
1091
1092         /*
1093          * Return the current pointer to the data offset.
1094          */
1095
1096         if(!prs_set_offset(rpc_in, old_offset)) {
1097                 DEBUG(0,("api_pipe_auth_process: failed to set offset back to %u\n",
1098                         (unsigned int)old_offset ));
1099                 return False;
1100         }
1101
1102         return True;
1103 }
1104
1105 /****************************************************************************
1106  Return a user struct for a pipe user.
1107 ****************************************************************************/
1108
1109 struct current_user *get_current_user(struct current_user *user, pipes_struct *p)
1110 {
1111         if (p->ntlmssp_auth_validated) {
1112                 memcpy(user, &p->pipe_user, sizeof(struct current_user));
1113         } else {
1114                 extern struct current_user current_user;
1115                 memcpy(user, &current_user, sizeof(struct current_user));
1116         }
1117
1118         return user;
1119 }
1120
1121 /****************************************************************************
1122  Find the correct RPC function to call for this request.
1123  If the pipe is authenticated then become the correct UNIX user
1124  before doing the call.
1125 ****************************************************************************/
1126
1127 BOOL api_pipe_request(pipes_struct *p)
1128 {
1129         int i = 0;
1130         BOOL ret = False;
1131
1132         if (p->ntlmssp_auth_validated) {
1133
1134                 if(!become_authenticated_pipe_user(p)) {
1135                         prs_mem_free(&p->out_data.rdata);
1136                         return False;
1137                 }
1138         }
1139
1140         for (i = 0; api_fd_commands[i].pipe_clnt_name; i++) {
1141                 if (strequal(api_fd_commands[i].pipe_clnt_name, p->name) &&
1142                     api_fd_commands[i].fn != NULL) {
1143                         DEBUG(3,("Doing \\PIPE\\%s\n", api_fd_commands[i].pipe_clnt_name));
1144                         set_current_rpc_talloc(p->mem_ctx);
1145                         ret = api_fd_commands[i].fn(p);
1146                         set_current_rpc_talloc(NULL);
1147                 }
1148         }
1149
1150         if(p->ntlmssp_auth_validated)
1151                 unbecome_authenticated_pipe_user();
1152
1153         return ret;
1154 }
1155
1156 /*******************************************************************
1157  Calls the underlying RPC function for a named pipe.
1158  ********************************************************************/
1159
1160 BOOL api_rpcTNP(pipes_struct *p, char *rpc_name, 
1161                 struct api_struct *api_rpc_cmds)
1162 {
1163         int fn_num;
1164         fstring name;
1165         uint32 offset1, offset2;
1166  
1167         /* interpret the command */
1168         DEBUG(4,("api_rpcTNP: %s op 0x%x - ", rpc_name, p->hdr_req.opnum));
1169
1170         slprintf(name, sizeof(name)-1, "in_%s", rpc_name);
1171         prs_dump(name, p->hdr_req.opnum, &p->in_data.data);
1172
1173         for (fn_num = 0; api_rpc_cmds[fn_num].name; fn_num++) {
1174                 if (api_rpc_cmds[fn_num].opnum == p->hdr_req.opnum && api_rpc_cmds[fn_num].fn != NULL) {
1175                         DEBUG(3,("api_rpcTNP: rpc command: %s\n", api_rpc_cmds[fn_num].name));
1176                         break;
1177                 }
1178         }
1179
1180         if (api_rpc_cmds[fn_num].name == NULL) {
1181                 /*
1182                  * For an unknown RPC just return a fault PDU but
1183                  * return True to allow RPC's on the pipe to continue
1184                  * and not put the pipe into fault state. JRA.
1185                  */
1186                 DEBUG(4, ("unknown\n"));
1187                 setup_fault_pdu(p, NT_STATUS(0x1c010002));
1188                 return True;
1189         }
1190
1191         offset1 = prs_offset(&p->out_data.rdata);
1192
1193         /* do the actual command */
1194         if(!api_rpc_cmds[fn_num].fn(p)) {
1195                 DEBUG(0,("api_rpcTNP: %s: %s failed.\n", rpc_name, api_rpc_cmds[fn_num].name));
1196                 prs_mem_free(&p->out_data.rdata);
1197                 return False;
1198         }
1199
1200         slprintf(name, sizeof(name)-1, "out_%s", rpc_name);
1201         offset2 = prs_offset(&p->out_data.rdata);
1202         prs_set_offset(&p->out_data.rdata, offset1);
1203         prs_dump(name, p->hdr_req.opnum, &p->out_data.rdata);
1204         prs_set_offset(&p->out_data.rdata, offset2);
1205
1206         DEBUG(5,("api_rpcTNP: called %s successfully\n", rpc_name));
1207
1208         /* Check for buffer underflow in rpc parsing */
1209
1210         if ((DEBUGLEVEL >= 10) && 
1211             (p->in_data.data.data_offset != p->in_data.data.buffer_size)) {
1212                 int data_len = p->in_data.data.buffer_size - 
1213                         p->in_data.data.data_offset;
1214                 char *data;
1215
1216                 data = malloc(data_len);
1217
1218                 DEBUG(10, ("api_rpcTNP: rpc input buffer underflow (parse error?)\n"));
1219                 if (data) {
1220                         prs_uint8s(False, "", &p->in_data.data, 0, (unsigned char *)data,
1221                                    data_len);
1222                         SAFE_FREE(data);
1223                 }
1224
1225         }
1226
1227         return True;
1228 }