2 * Unix SMB/Netbios implementation.
4 * RPC Pipe client / server routines
5 * Copyright (C) Andrew Tridgell 1992-1997,
6 * Copyright (C) Luke Kenneth Casson Leighton 1996-1997,
7 * Copyright (C) Paul Ashton 1997.
8 * Copyright (C) Jeremy Allison 1998.
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.
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.
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.
29 extern int DEBUGLEVEL;
31 extern pstring global_myname;
32 extern DOM_SID global_sam_sid;
33 extern fstring global_sam_name;
35 /*************************************************************************
37 *************************************************************************/
38 static void make_net_r_req_chal(NET_R_REQ_CHAL *r_c,
39 DOM_CHAL *srv_chal, int status)
41 DEBUG(6,("make_net_r_req_chal: %d\n", __LINE__));
42 memcpy(r_c->srv_chal.data, srv_chal->data, sizeof(srv_chal->data));
46 /*************************************************************************
48 *************************************************************************/
49 static void net_reply_req_chal(NET_Q_REQ_CHAL *q_c, prs_struct *rdata,
50 DOM_CHAL *srv_chal, uint32 srv_time)
54 DEBUG(6,("net_reply_req_chal: %d\n", __LINE__));
56 /* set up the LSA REQUEST CHALLENGE response */
57 make_net_r_req_chal(&r_c, srv_chal, srv_time);
59 /* store the response in the SMB stream */
60 net_io_r_req_chal("", &r_c, rdata, 0);
62 DEBUG(6,("net_reply_req_chal: %d\n", __LINE__));
66 /*************************************************************************
67 net_reply_logon_ctrl2:
68 *************************************************************************/
69 static void net_reply_logon_ctrl2(NET_Q_LOGON_CTRL2 *q_l, prs_struct *rdata,
70 uint32 flags, uint32 pdc_status, uint32 logon_attempts,
71 uint32 tc_status, char *trust_domain_name)
73 NET_R_LOGON_CTRL2 r_l;
75 DEBUG(6,("net_reply_logon_ctrl2: %d\n", __LINE__));
77 /* set up the Logon Control2 response */
78 make_r_logon_ctrl2(&r_l, q_l->query_level,
79 flags, pdc_status, logon_attempts,
80 tc_status, trust_domain_name);
82 /* store the response in the SMB stream */
83 net_io_r_logon_ctrl2("", &r_l, rdata, 0);
85 DEBUG(6,("net_reply_logon_ctrl2: %d\n", __LINE__));
89 /*************************************************************************
90 net_reply_trust_dom_list:
91 *************************************************************************/
92 static void net_reply_trust_dom_list(NET_Q_TRUST_DOM_LIST *q_t, prs_struct *rdata,
93 uint32 num_trust_domains, char *trust_domain_name)
95 NET_R_TRUST_DOM_LIST r_t;
97 DEBUG(6,("net_reply_trust_dom_list: %d\n", __LINE__));
99 /* set up the Trusted Domain List response */
100 make_r_trust_dom(&r_t, num_trust_domains, trust_domain_name);
102 /* store the response in the SMB stream */
103 net_io_r_trust_dom("", &r_t, rdata, 0);
105 DEBUG(6,("net_reply_trust_dom_listlogon_ctrl2: %d\n", __LINE__));
109 /*************************************************************************
111 *************************************************************************/
112 static void make_net_r_auth_2(NET_R_AUTH_2 *r_a,
113 DOM_CHAL *resp_cred, NEG_FLAGS *flgs, int status)
115 memcpy( r_a->srv_chal.data, resp_cred->data, sizeof(resp_cred->data));
116 memcpy(&(r_a->srv_flgs) , flgs , sizeof(r_a->srv_flgs));
117 r_a->status = status;
120 /*************************************************************************
122 *************************************************************************/
123 static void net_reply_auth_2(NET_Q_AUTH_2 *q_a, prs_struct *rdata,
124 DOM_CHAL *resp_cred, int status)
129 srv_flgs.neg_flags = 0x000001ff;
131 /* set up the LSA AUTH 2 response */
133 make_net_r_auth_2(&r_a, resp_cred, &srv_flgs, status);
135 /* store the response in the SMB stream */
136 net_io_r_auth_2("", &r_a, rdata, 0);
140 /***********************************************************************************
141 make_net_r_srv_pwset:
142 ***********************************************************************************/
143 static void make_net_r_srv_pwset(NET_R_SRV_PWSET *r_s,
144 DOM_CRED *srv_cred, int status)
146 DEBUG(5,("make_net_r_srv_pwset: %d\n", __LINE__));
148 memcpy(&(r_s->srv_cred), srv_cred, sizeof(r_s->srv_cred));
149 r_s->status = status;
151 DEBUG(5,("make_net_r_srv_pwset: %d\n", __LINE__));
154 /*************************************************************************
156 *************************************************************************/
157 static void net_reply_srv_pwset(NET_Q_SRV_PWSET *q_s, prs_struct *rdata,
158 DOM_CRED *srv_cred, int status)
162 DEBUG(5,("net_srv_pwset: %d\n", __LINE__));
164 /* set up the LSA Server Password Set response */
165 make_net_r_srv_pwset(&r_s, srv_cred, status);
167 /* store the response in the SMB stream */
168 net_io_r_srv_pwset("", &r_s, rdata, 0);
170 DEBUG(5,("net_srv_pwset: %d\n", __LINE__));
174 /*************************************************************************
176 *************************************************************************/
177 static void net_reply_sam_logon(NET_Q_SAM_LOGON *q_s, prs_struct *rdata,
178 DOM_CRED *srv_cred, NET_USER_INFO_3 *user_info,
183 /* XXXX maybe we want to say 'no', reject the client's credentials */
184 r_s.buffer_creds = 1; /* yes, we have valid server credentials */
185 memcpy(&(r_s.srv_creds), srv_cred, sizeof(r_s.srv_creds));
187 /* store the user information, if there is any. */
188 r_s.user = user_info;
189 if (status == 0x0 && user_info != NULL && user_info->ptr_user_info != 0)
191 r_s.switch_value = 3; /* indicates type of validation user info */
195 r_s.switch_value = 0; /* indicates no info */
199 r_s.auth_resp = 1; /* authoritative response */
201 /* store the response in the SMB stream */
202 net_io_r_sam_logon("", &r_s, rdata, 0);
207 /*************************************************************************
208 net_reply_sam_logoff:
209 *************************************************************************/
210 static void net_reply_sam_logoff(NET_Q_SAM_LOGOFF *q_s, prs_struct *rdata,
214 NET_R_SAM_LOGOFF r_s;
216 /* XXXX maybe we want to say 'no', reject the client's credentials */
217 r_s.buffer_creds = 1; /* yes, we have valid server credentials */
218 memcpy(&(r_s.srv_creds), srv_cred, sizeof(r_s.srv_creds));
222 /* store the response in the SMB stream */
223 net_io_r_sam_logoff("", &r_s, rdata, 0);
227 /*************************************************************************
229 *************************************************************************/
230 static void net_reply_sam_sync(NET_Q_SAM_SYNC *q_s, prs_struct *rdata,
232 DOM_CRED *srv_creds, uint32 status)
236 struct sam_passwd *pwd;
239 memcpy(&(r_s.srv_creds), srv_creds, sizeof(r_s.srv_creds));
240 r_s.sync_context = 1;
243 if ((status == 0x0) && ((vp = startsmbpwent(False)) != NULL))
245 /* Give the poor BDC some accounts */
247 while (((pwd = getsam21pwent(vp)) != NULL) && (i < MAX_SAM_DELTAS))
249 make_sam_delta_hdr(&r_s.hdr_deltas[i], 5, pwd->user_rid);
250 make_sam_account_info(&r_s.deltas[i].account_info,
251 pwd->nt_name, pwd->full_name, pwd->user_rid,
252 pwd->group_rid, pwd->home_dir, pwd->dir_drive,
253 pwd->logon_script, pwd->acct_desc,
254 pwd->acct_ctrl, pwd->profile_path);
261 r_s.ptr_deltas = r_s.ptr_deltas2 = 1;
262 r_s.num_deltas = r_s.num_deltas2 = i;
267 /* store the response in the SMB stream */
268 net_io_r_sam_sync("", sess_key, &r_s, rdata, 0);
272 /******************************************************************
273 gets a machine password entry. checks access rights of the host.
274 ******************************************************************/
275 static BOOL get_md4pw(char *md4pw, char *mach_name, char *mach_acct)
277 struct smb_passwd *smb_pass;
281 * Currently this code is redundent as we already have a filter
282 * by hostname list. What this code really needs to do is to
283 * get a hosts allowed/hosts denied list from the SAM database
284 * on a per user basis, and make the access decision there.
285 * I will leave this code here for now as a reminder to implement
286 * this at a later date. JRA.
289 if (!allow_access(lp_domain_hostsdeny(), lp_domain_hostsallow(),
290 client_name(Client), client_addr(Client)))
292 DEBUG(0,("get_md4pw: Workstation %s denied access to domain\n", mach_acct));
298 smb_pass = getsmbpwnam(mach_acct);
301 if ((smb_pass) != NULL && !(smb_pass->acct_ctrl & ACB_DISABLED) &&
302 (smb_pass->smb_nt_passwd != NULL))
304 memcpy(md4pw, smb_pass->smb_nt_passwd, 16);
305 dump_data(5, md4pw, 16);
309 DEBUG(0,("get_md4pw: Workstation %s: no account in domain\n", mach_acct));
313 /*************************************************************************
315 *************************************************************************/
316 static void api_net_req_chal( pipes_struct *p,
328 DEBUG(5,("api_net_req_chal(%d): vuid %d\n", __LINE__, (int)p->vuid));
330 if ((vuser = get_valid_user_struct(p->vuid)) == NULL)
333 /* grab the challenge... */
334 net_io_q_req_chal("", &q_r, data, 0);
336 unistr2_to_ascii(mach_acct, &q_r.uni_logon_clnt, sizeof(mach_acct)-1);
338 fstrcpy(mach_name, mach_acct);
341 fstrcat(mach_acct, "$");
343 if (get_md4pw((char *)vuser->dc.md4pw, mach_name, mach_acct))
345 /* copy the client credentials */
346 memcpy(vuser->dc.clnt_chal.data , q_r.clnt_chal.data, sizeof(q_r.clnt_chal.data));
347 memcpy(vuser->dc.clnt_cred.challenge.data, q_r.clnt_chal.data, sizeof(q_r.clnt_chal.data));
349 /* create a server challenge for the client */
350 /* Set these to random values. */
351 generate_random_buffer(vuser->dc.srv_chal.data, 8, False);
353 memcpy(vuser->dc.srv_cred.challenge.data, vuser->dc.srv_chal.data, 8);
355 bzero(vuser->dc.sess_key, sizeof(vuser->dc.sess_key));
357 /* from client / server challenges and md4 password, generate sess key */
358 cred_session_key(&(vuser->dc.clnt_chal), &(vuser->dc.srv_chal),
359 (char *)vuser->dc.md4pw, vuser->dc.sess_key);
363 /* lkclXXXX take a guess at a good error message to return :-) */
364 status = 0xC0000000 | NT_STATUS_NOLOGON_WORKSTATION_TRUST_ACCOUNT;
367 /* construct reply. */
368 net_reply_req_chal(&q_r, rdata,
369 &(vuser->dc.srv_chal), status);
373 /*************************************************************************
375 *************************************************************************/
376 static void api_net_auth_2( pipes_struct *p,
388 if ((vuser = get_valid_user_struct(p->vuid)) == NULL)
393 /* grab the challenge... */
394 net_io_q_auth_2("", &q_a, data, 0);
396 /* check that the client credentials are valid */
397 if (cred_assert(&(q_a.clnt_chal), vuser->dc.sess_key,
398 &(vuser->dc.clnt_cred.challenge), srv_time))
401 /* create server challenge for inclusion in the reply */
402 cred_create(vuser->dc.sess_key, &(vuser->dc.srv_cred.challenge), srv_time, &srv_cred);
404 /* copy the received client credentials for use next time */
405 memcpy(vuser->dc.clnt_cred.challenge.data, q_a.clnt_chal.data, sizeof(q_a.clnt_chal.data));
406 memcpy(vuser->dc.srv_cred .challenge.data, q_a.clnt_chal.data, sizeof(q_a.clnt_chal.data));
410 status = NT_STATUS_ACCESS_DENIED | 0xC0000000;
413 /* construct reply. */
414 net_reply_auth_2(&q_a, rdata, &srv_cred, status);
418 /*************************************************************************
420 *************************************************************************/
421 static void api_net_srv_pwset( pipes_struct *p,
426 uint32 status = NT_STATUS_WRONG_PASSWORD|0xC0000000;
429 struct smb_passwd *smb_pass;
433 if ((vuser = get_valid_user_struct(p->vuid)) == NULL)
436 /* grab the challenge and encrypted password ... */
437 net_io_q_srv_pwset("", &q_a, data, 0);
439 /* checks and updates credentials. creates reply credentials */
440 if (deal_with_creds(vuser->dc.sess_key, &(vuser->dc.clnt_cred),
441 &(q_a.clnt_id.cred), &srv_cred))
443 memcpy(&(vuser->dc.srv_cred), &(vuser->dc.clnt_cred), sizeof(vuser->dc.clnt_cred));
445 DEBUG(5,("api_net_srv_pwset: %d\n", __LINE__));
447 unistr2_to_ascii(mach_acct, &q_a.clnt_id.login.uni_acct_name,
448 sizeof(mach_acct)-1);
450 DEBUG(3,("Server Password Set Wksta:[%s]\n", mach_acct));
453 smb_pass = getsmbpwnam(mach_acct);
456 if (smb_pass != NULL)
458 unsigned char pwd[16];
461 DEBUG(100,("Server password set : new given value was :\n"));
462 for(i = 0; i < 16; i++)
464 DEBUG(100,("%02X ", q_a.pwd[i]));
468 cred_hash3( pwd, q_a.pwd, vuser->dc.sess_key, 0);
470 /* lies! nt and lm passwords are _not_ the same: don't care */
471 smb_pass->smb_passwd = pwd;
472 smb_pass->smb_nt_passwd = pwd;
473 smb_pass->acct_ctrl = ACB_WSTRUST;
476 ret = mod_smbpwd_entry(smb_pass,False);
486 DEBUG(5,("api_net_srv_pwset: %d\n", __LINE__));
491 /* lkclXXXX take a guess at a sensible error code to return... */
492 status = 0xC0000000 | NT_STATUS_NETWORK_CREDENTIAL_CONFLICT;
495 /* Construct reply. */
496 net_reply_srv_pwset(&q_a, rdata, &srv_cred, status);
500 /*************************************************************************
502 *************************************************************************/
503 static void api_net_sam_logoff( pipes_struct *p,
507 NET_Q_SAM_LOGOFF q_l;
514 if ((vuser = get_valid_user_struct(p->vuid)) == NULL)
517 /* the DOM_ID_INFO_1 structure is a bit big. plus we might want to
518 dynamically allocate it inside net_io_q_sam_logon, at some point */
519 q_l.sam_id.ctr = &ctr;
521 /* grab the challenge... */
522 net_io_q_sam_logoff("", &q_l, data, 0);
524 /* checks and updates credentials. creates reply credentials */
525 deal_with_creds(vuser->dc.sess_key, &(vuser->dc.clnt_cred),
526 &(q_l.sam_id.client.cred), &srv_cred);
527 memcpy(&(vuser->dc.srv_cred), &(vuser->dc.clnt_cred), sizeof(vuser->dc.clnt_cred));
529 /* construct reply. always indicate success */
530 net_reply_sam_logoff(&q_l, rdata, &srv_cred, 0x0);
533 /*************************************************************************
535 *************************************************************************/
536 static void api_net_sam_sync( pipes_struct *p,
545 if ((vuser = get_valid_user_struct(p->vuid)) == NULL)
548 /* grab the challenge... */
549 net_io_q_sam_sync("", &q_s, data, 0);
551 /* checks and updates credentials. creates reply credentials */
552 if (deal_with_creds(vuser->dc.sess_key, &(vuser->dc.clnt_cred),
553 &(q_s.cli_creds), &srv_creds))
555 memcpy(&(vuser->dc.srv_cred), &(vuser->dc.clnt_cred),
556 sizeof(vuser->dc.clnt_cred));
560 status = 0xC0000000 | NT_STATUS_NETWORK_CREDENTIAL_CONFLICT;
563 /* construct reply. */
564 net_reply_sam_sync(&q_s, rdata, vuser->dc.sess_key, &srv_creds, status);
568 /*************************************************************************
569 net_login_interactive:
570 *************************************************************************/
571 static uint32 net_login_interactive(NET_ID_INFO_1 *id1,
572 struct sam_passwd *smb_pass,
579 unsigned char key[16];
582 memcpy(key, vuser->dc.sess_key, 8);
584 memcpy(lm_pwd, id1->lm_owf.data, 16);
585 memcpy(nt_pwd, id1->nt_owf.data, 16);
587 #ifdef DEBUG_PASSWORD
589 dump_data(100, key, 16);
591 DEBUG(100,("lm owf password:"));
592 dump_data(100, lm_pwd, 16);
594 DEBUG(100,("nt owf password:"));
595 dump_data(100, nt_pwd, 16);
598 SamOEMhash((uchar *)lm_pwd, key, False);
599 SamOEMhash((uchar *)nt_pwd, key, False);
601 #ifdef DEBUG_PASSWORD
602 DEBUG(100,("decrypt of lm owf password:"));
603 dump_data(100, lm_pwd, 16);
605 DEBUG(100,("decrypt of nt owf password:"));
606 dump_data(100, nt_pwd, 16);
609 if (smb_pass->smb_nt_passwd == NULL)
611 DEBUG(5,("warning: NETLOGON user %s only has an LM password\n",
612 smb_pass->unix_name));
615 if (memcmp(smb_pass->smb_passwd , lm_pwd, 16) != 0 ||
616 smb_pass->smb_nt_passwd == NULL ||
617 memcmp(smb_pass->smb_nt_passwd, nt_pwd, 16) != 0)
619 status = 0xC0000000 | NT_STATUS_WRONG_PASSWORD;
625 /*************************************************************************
627 *************************************************************************/
628 static uint32 net_login_network(NET_ID_INFO_2 *id2,
629 struct sam_passwd *smb_pass,
635 int nt_pw_len = id2->hdr_nt_chal_resp.str_str_len;
636 int lm_pw_len = id2->hdr_lm_chal_resp.str_str_len;
638 unistr2_to_ascii(user , &id2->uni_user_name, sizeof(user)-1);
639 unistr2_to_ascii(domain, &id2->uni_domain_name, sizeof(domain)-1);
641 DEBUG(5,("net_login_network: lm_len:%d nt_len:%d user:%s domain:%s\n",
642 lm_pw_len, nt_pw_len, user, domain));
644 if (smb_password_ok(pwdb_sam_to_smb(smb_pass), id2->lm_chal,
646 (uchar *)id2->lm_chal_resp.buffer, lm_pw_len,
647 (uchar *)id2->nt_chal_resp.buffer, nt_pw_len))
652 return 0xC0000000 | NT_STATUS_WRONG_PASSWORD;
655 /*************************************************************************
657 *************************************************************************/
658 static uint32 reply_net_sam_logon( NET_Q_SAM_LOGON *q_l, user_struct *vuser,
659 DOM_CRED *srv_cred, NET_USER_INFO_3 *usr_info)
661 struct sam_passwd *sam_pass = NULL;
662 UNISTR2 *uni_samusr = NULL;
663 UNISTR2 *uni_domain = NULL;
668 NTTIME kickoff_time ;
669 NTTIME pass_last_set_time ;
670 NTTIME pass_can_change_time ;
671 NTTIME pass_must_change_time;
675 fstring logon_script;
676 fstring profile_path;
684 DOMAIN_GRP *grp_mem = NULL;
685 DOM_GID *gids = NULL;
687 /* checks and updates credentials. creates reply credentials */
688 if (!deal_with_creds(vuser->dc.sess_key, &(vuser->dc.clnt_cred),
689 &(q_l->sam_id.client.cred), srv_cred))
691 return 0xC0000000 | NT_STATUS_INVALID_HANDLE;
694 memcpy(&(vuser->dc.srv_cred), &(vuser->dc.clnt_cred), sizeof(vuser->dc.clnt_cred));
696 /* find the username */
698 switch (q_l->sam_id.logon_level)
700 case INTERACTIVE_LOGON_TYPE:
702 uni_samusr = &(q_l->sam_id.ctr->auth.id1.uni_user_name);
703 uni_domain = &(q_l->sam_id.ctr->auth.id1.uni_domain_name);
705 DEBUG(3,("SAM Logon (Interactive). Domain:[%s]. ", global_sam_name));
710 uni_samusr = &(q_l->sam_id.ctr->auth.id2.uni_user_name);
711 uni_domain = &(q_l->sam_id.ctr->auth.id2.uni_domain_name);
713 DEBUG(3,("SAM Logon (Network). Domain:[%s]. ", global_sam_name));
718 DEBUG(2,("SAM Logon: unsupported switch value\n"));
719 return 0xC0000000 | NT_STATUS_INVALID_INFO_CLASS;
723 /* check username exists */
725 unistr2_to_ascii(nt_username, uni_samusr,
726 sizeof(nt_username)-1);
728 DEBUG(3,("User:[%s]\n", nt_username));
731 sam_pass = getsam21pwntnam(nt_username);
734 if (sam_pass == NULL)
736 return 0xC0000000 | NT_STATUS_NO_SUCH_USER;
738 else if (IS_BITS_SET_ALL(sam_pass->acct_ctrl, ACB_DISABLED) &&
739 IS_BITS_CLR_ALL(sam_pass->acct_ctrl, ACB_PWNOTREQ))
741 return 0xC0000000 | NT_STATUS_ACCOUNT_DISABLED;
744 logon_time = sam_pass->logon_time;
745 logoff_time = sam_pass->logoff_time;
746 kickoff_time = sam_pass->kickoff_time;
747 pass_last_set_time = sam_pass->pass_last_set_time;
748 pass_can_change_time = sam_pass->pass_can_change_time;
749 pass_must_change_time = sam_pass->pass_must_change_time;
751 fstrcpy(nt_name , sam_pass->nt_name);
752 fstrcpy(full_name , sam_pass->full_name);
753 fstrcpy(logon_script, sam_pass->logon_script);
754 fstrcpy(profile_path, sam_pass->profile_path);
755 fstrcpy(home_dir , sam_pass->home_dir);
756 fstrcpy(dir_drive , sam_pass->dir_drive);
758 user_rid = sam_pass->user_rid;
759 group_rid = sam_pass->group_rid;
761 /* validate password - if required */
763 if (!(IS_BITS_SET_ALL(sam_pass->acct_ctrl, ACB_PWNOTREQ)))
766 switch (q_l->sam_id.logon_level)
768 case INTERACTIVE_LOGON_TYPE:
770 /* interactive login. */
771 status = net_login_interactive(&q_l->sam_id.ctr->auth.id1, sam_pass, vuser);
776 /* network login. lm challenge and 24 byte responses */
777 status = net_login_network(&q_l->sam_id.ctr->auth.id2, sam_pass, vuser);
787 /* lkclXXXX this is the point at which, if the login was
788 successful, that the SAM Local Security Authority should
789 record that the user is logged in to the domain.
792 /* return the profile plus other bits :-) */
794 /* set up pointer indicating user/password failed to be found */
795 usr_info->ptr_user_info = 0;
797 if (!getusergroupsntnam(nt_username, &grp_mem, &num_gids))
799 return 0xC0000000 | NT_STATUS_INVALID_PRIMARY_GROUP;
802 num_gids = make_dom_gids(grp_mem, num_gids, &gids);
804 make_net_user_info3(usr_info,
809 &pass_can_change_time,
810 &pass_must_change_time,
812 nt_name , /* user_name */
813 full_name , /* full_name */
814 logon_script , /* logon_script */
815 profile_path , /* profile_path */
816 home_dir , /* home_dir */
817 dir_drive , /* dir_drive */
820 0, /* bad_pw_count */
822 user_rid , /* RID user_id */
823 group_rid , /* RID group_id */
824 num_gids, /* uint32 num_groups */
825 gids , /* DOM_GID *gids */
826 0x20 , /* uint32 user_flgs (?) */
828 NULL, /* char sess_key[16] */
830 global_myname , /* char *logon_srv */
831 global_sam_name, /* char *logon_dom */
832 &global_sam_sid, /* DOM_SID *dom_sid */
833 NULL); /* char *other_sids */
835 /* Free any allocated groups array. */
844 /*************************************************************************
846 *************************************************************************/
847 static void api_net_sam_logon( pipes_struct *p,
853 NET_USER_INFO_3 usr_info;
857 user_struct *vuser = get_valid_user_struct(p->vuid);
864 q_l.sam_id.ctr = &ctr;
865 net_io_q_sam_logon("", &q_l, data, 0);
867 status = reply_net_sam_logon(&q_l, vuser, &srv_cred, &usr_info);
868 net_reply_sam_logon(&q_l, rdata, &srv_cred, &usr_info, status);
872 /*************************************************************************
873 api_net_trust_dom_list:
874 *************************************************************************/
875 static void api_net_trust_dom_list( pipes_struct *p,
879 NET_Q_TRUST_DOM_LIST q_t;
881 char *trusted_domain = "test_domain";
883 DEBUG(6,("api_net_trust_dom_list: %d\n", __LINE__));
885 /* grab the lsa trusted domain list query... */
886 net_io_q_trust_dom("", &q_t, data, 0);
888 /* construct reply. */
889 net_reply_trust_dom_list(&q_t, rdata,
892 DEBUG(6,("api_net_trust_dom_list: %d\n", __LINE__));
896 /*************************************************************************
897 error messages cropping up when using nltest.exe...
898 *************************************************************************/
899 #define ERROR_NO_SUCH_DOMAIN 0x54b
900 #define ERROR_NO_LOGON_SERVERS 0x51f
902 /*************************************************************************
904 *************************************************************************/
905 static void api_net_logon_ctrl2( pipes_struct *p,
909 NET_Q_LOGON_CTRL2 q_l;
911 /* lkclXXXX - guess what - absolutely no idea what these are! */
913 uint32 pdc_connection_status = 0x0;
914 uint32 logon_attempts = 0x0;
915 uint32 tc_status = ERROR_NO_LOGON_SERVERS;
916 char *trusted_domain = "test_domain";
918 DEBUG(6,("api_net_logon_ctrl2: %d\n", __LINE__));
920 /* grab the lsa netlogon ctrl2 query... */
921 net_io_q_logon_ctrl2("", &q_l, data, 0);
923 /* construct reply. */
924 net_reply_logon_ctrl2(&q_l, rdata,
925 flags, pdc_connection_status, logon_attempts,
926 tc_status, trusted_domain);
928 DEBUG(6,("api_net_logon_ctrl2: %d\n", __LINE__));
931 /*******************************************************************
932 array of \PIPE\NETLOGON operations
933 ********************************************************************/
934 static struct api_struct api_net_cmds [] =
936 { "NET_REQCHAL" , NET_REQCHAL , api_net_req_chal },
937 { "NET_AUTH2" , NET_AUTH2 , api_net_auth_2 },
938 { "NET_SRVPWSET" , NET_SRVPWSET , api_net_srv_pwset },
939 { "NET_SAMLOGON" , NET_SAMLOGON , api_net_sam_logon },
940 { "NET_SAMLOGOFF" , NET_SAMLOGOFF , api_net_sam_logoff },
941 { "NET_LOGON_CTRL2" , NET_LOGON_CTRL2 , api_net_logon_ctrl2 },
942 { "NET_TRUST_DOM_LIST", NET_TRUST_DOM_LIST, api_net_trust_dom_list },
943 { "NET_SAM_SYNC" , NET_SAM_SYNC , api_net_sam_sync },
947 /*******************************************************************
948 receives a netlogon pipe and responds.
949 ********************************************************************/
950 BOOL api_netlog_rpc(pipes_struct *p, prs_struct *data)
952 return api_rpcTNP(p, "api_netlog_rpc", api_net_cmds, data);