Broke out change trust account password routines into separate file
[Samba/gbeck.git] / source / rpc_client / cli_trust.c
blob49cd1b17238b06e3e5a0098f63951897d5d2eff9
1 /*
2 * Unix SMB/Netbios implementation.
3 * Version 1.9.
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.
25 #include "includes.h"
27 extern pstring global_myname;
29 /*********************************************************
30 Change the domain password on the PDC.
31 **********************************************************/
33 static BOOL modify_trust_password( char *domain, char *remote_machine,
34 unsigned char orig_trust_passwd_hash[16],
35 unsigned char new_trust_passwd_hash[16])
37 struct cli_state cli;
39 ZERO_STRUCT(cli);
40 if(cli_initialise(&cli) == False) {
41 DEBUG(0,("modify_trust_password: unable to initialize client connection.\n"));
42 return False;
45 if(!resolve_name( remote_machine, &cli.dest_ip, 0x20)) {
46 DEBUG(0,("modify_trust_password: Can't resolve address for %s\n", remote_machine));
47 cli_shutdown(&cli);
48 return False;
51 if (ismyip(cli.dest_ip)) {
52 DEBUG(0,("modify_trust_password: Machine %s is one of our addresses. Cannot add \
53 to ourselves.\n", remote_machine));
54 cli_shutdown(&cli);
55 return False;
58 if (!cli_connect(&cli, remote_machine, &cli.dest_ip)) {
59 DEBUG(0,("modify_trust_password: unable to connect to SMB server on \
60 machine %s. Error was : %s.\n", remote_machine, cli_errstr(&cli) ));
61 cli_shutdown(&cli);
62 return False;
65 if (!attempt_netbios_session_request(&cli, global_myname, remote_machine, &cli.dest_ip)) {
66 DEBUG(0,("modify_trust_password: machine %s rejected the NetBIOS \
67 session request. Error was %s\n", remote_machine, cli_errstr(&cli) ));
68 cli_shutdown(&cli);
69 return False;
72 cli.protocol = PROTOCOL_NT1;
74 if (!cli_negprot(&cli)) {
75 DEBUG(0,("modify_trust_password: machine %s rejected the negotiate protocol. \
76 Error was : %s.\n", remote_machine, cli_errstr(&cli) ));
77 cli_shutdown(&cli);
78 return False;
81 if (cli.protocol != PROTOCOL_NT1) {
82 DEBUG(0,("modify_trust_password: machine %s didn't negotiate NT protocol.\n",
83 remote_machine));
84 cli_shutdown(&cli);
85 return False;
89 * Do an anonymous session setup.
92 if (!cli_session_setup(&cli, "", "", 0, "", 0, "")) {
93 DEBUG(0,("modify_trust_password: machine %s rejected the session setup. \
94 Error was : %s.\n", remote_machine, cli_errstr(&cli) ));
95 cli_shutdown(&cli);
96 return False;
99 if (!(cli.sec_mode & 1)) {
100 DEBUG(0,("modify_trust_password: machine %s isn't in user level security mode\n",
101 remote_machine));
102 cli_shutdown(&cli);
103 return False;
106 if (!cli_send_tconX(&cli, "IPC$", "IPC", "", 1)) {
107 DEBUG(0,("modify_trust_password: machine %s rejected the tconX on the IPC$ share. \
108 Error was : %s.\n", remote_machine, cli_errstr(&cli) ));
109 cli_shutdown(&cli);
110 return False;
114 * Ok - we have an anonymous connection to the IPC$ share.
115 * Now start the NT Domain stuff :-).
118 if(cli_lsa_get_domain_sid(&cli, remote_machine) == False) {
119 DEBUG(0,("modify_trust_password: unable to obtain domain sid from %s. Error was : %s.\n", remote_machine, cli_errstr(&cli)));
120 cli_ulogoff(&cli);
121 cli_shutdown(&cli);
122 return False;
125 if(cli_nt_session_open(&cli, PIPE_NETLOGON) == False) {
126 DEBUG(0,("modify_trust_password: unable to open the domain client session to \
127 machine %s. Error was : %s.\n", remote_machine, cli_errstr(&cli)));
128 cli_nt_session_close(&cli);
129 cli_ulogoff(&cli);
130 cli_shutdown(&cli);
131 return False;
134 if(cli_nt_setup_creds(&cli, orig_trust_passwd_hash) == False) {
135 DEBUG(0,("modify_trust_password: unable to setup the PDC credentials to machine \
136 %s. Error was : %s.\n", remote_machine, cli_errstr(&cli)));
137 cli_nt_session_close(&cli);
138 cli_ulogoff(&cli);
139 cli_shutdown(&cli);
140 return False;
143 if( cli_nt_srv_pwset( &cli,new_trust_passwd_hash ) == False) {
144 DEBUG(0,("modify_trust_password: unable to change password for machine %s in domain \
145 %s to Domain controller %s. Error was %s.\n", global_myname, domain, remote_machine,
146 cli_errstr(&cli)));
147 cli_close(&cli, cli.nt_pipe_fnum);
148 cli_ulogoff(&cli);
149 cli_shutdown(&cli);
150 return False;
153 cli_nt_session_close(&cli);
154 cli_ulogoff(&cli);
155 cli_shutdown(&cli);
157 return True;
160 /************************************************************************
161 Change the trust account password for a domain.
162 The user of this function must have locked the trust password file for
163 update.
164 ************************************************************************/
166 BOOL change_trust_account_password( char *domain, char *remote_machine_list)
168 fstring remote_machine;
169 unsigned char old_trust_passwd_hash[16];
170 unsigned char new_trust_passwd_hash[16];
171 time_t lct;
172 BOOL res = False;
174 if(!secrets_fetch_trust_account_password(domain, old_trust_passwd_hash, &lct)) {
175 DEBUG(0,("change_trust_account_password: unable to read the machine \
176 account password for domain %s.\n", domain));
177 return False;
181 * Create the new (random) password.
183 generate_random_buffer( new_trust_passwd_hash, 16, True);
185 while(remote_machine_list &&
186 next_token(&remote_machine_list, remote_machine,
187 LIST_SEP, sizeof(remote_machine))) {
188 strupper(remote_machine);
189 if(strequal(remote_machine, "*")) {
192 * We have been asked to dynamcially determine the IP addresses of the PDC.
195 struct in_addr *ip_list = NULL;
196 int count = 0;
197 int i;
199 /* Use the PDC *only* for this. */
200 if(!get_dc_list(True, domain, &ip_list, &count))
201 continue;
204 * Try and connect to the PDC/BDC list in turn as an IP
205 * address used as a string.
208 for(i = 0; i < count; i++) {
209 fstring dc_name;
210 if(!lookup_pdc_name(global_myname, domain, &ip_list[i], dc_name))
211 continue;
212 if((res = modify_trust_password( domain, dc_name,
213 old_trust_passwd_hash, new_trust_passwd_hash)))
214 break;
217 if(ip_list != NULL)
218 free((char *)ip_list);
220 } else {
221 res = modify_trust_password( domain, remote_machine,
222 old_trust_passwd_hash, new_trust_passwd_hash);
225 if(res) {
226 DEBUG(0,("%s : change_trust_account_password: Changed password for \
227 domain %s.\n", timestring(False), domain));
229 * Return the result of trying to write the new password
230 * back into the trust account file.
232 res = secrets_store_trust_account_password(domain, new_trust_passwd_hash);
233 memset(new_trust_passwd_hash, 0, 16);
234 memset(old_trust_passwd_hash, 0, 16);
235 return res;
239 memset(new_trust_passwd_hash, 0, 16);
240 memset(old_trust_passwd_hash, 0, 16);
242 DEBUG(0,("%s : change_trust_account_password: Failed to change password for \
243 domain %s.\n", timestring(False), domain));
244 return False;