diff options
Diffstat (limited to 'source3/rpc_client')
-rw-r--r-- | source3/rpc_client/cli_connect.c | 89 | ||||
-rw-r--r-- | source3/rpc_client/cli_login.c | 227 | ||||
-rw-r--r-- | source3/rpc_client/cli_lsarpc.c | 2 | ||||
-rw-r--r-- | source3/rpc_client/cli_netlogon.c | 306 | ||||
-rw-r--r-- | source3/rpc_client/cli_netlogon_sync.c | 13 | ||||
-rw-r--r-- | source3/rpc_client/cli_pipe.c | 12 |
6 files changed, 408 insertions, 241 deletions
diff --git a/source3/rpc_client/cli_connect.c b/source3/rpc_client/cli_connect.c index 0b5d20d913..bca539c396 100644 --- a/source3/rpc_client/cli_connect.c +++ b/source3/rpc_client/cli_connect.c @@ -192,6 +192,15 @@ BOOL cli_connection_init(const char* server_name, const char* pipe_name, /**************************************************************************** obtain client state ****************************************************************************/ +BOOL cli_connection_getsrv(const char* srv_name, const char* pipe_name, + struct cli_connection **con) +{ + return False; +} + +/**************************************************************************** +obtain client state +****************************************************************************/ BOOL cli_connection_get(const POLICY_HND *pol, struct cli_connection **con) { return get_policy_con(pol, con); @@ -216,7 +225,18 @@ BOOL cli_pol_link(POLICY_HND *to, const POLICY_HND *from) get a user session key associated with a connection associated with a policy handle. ****************************************************************************/ -BOOL cli_get_usr_sesskey(const POLICY_HND *pol, uchar sess_key[16]) +BOOL cli_get_con_sesskey(struct cli_connection *con, uchar sess_key[16]) +{ + memcpy(sess_key, con->cli->sess_key, sizeof(con->cli->sess_key)); + + return True; +} + +/**************************************************************************** +get a user session key associated with a connection associated with a +policy handle. +****************************************************************************/ +BOOL cli_get_sesskey(const POLICY_HND *pol, uchar sess_key[16]) { struct cli_connection *con = NULL; @@ -225,7 +245,72 @@ BOOL cli_get_usr_sesskey(const POLICY_HND *pol, uchar sess_key[16]) return False; } - memcpy(sess_key, con->cli->sess_key, sizeof(con->cli->sess_key)); + return cli_get_con_sesskey(con, sess_key); +} + +/**************************************************************************** +get a user session key associated with a connection associated with a +policy handle. +****************************************************************************/ +BOOL cli_get_sesskey_srv(const char* srv_name, uchar sess_key[16]) +{ + struct cli_connection *con = NULL; + + if (!cli_connection_getsrv(srv_name, PIPE_NETLOGON, &con)) + { + return False; + } + + return cli_get_con_sesskey(con, sess_key); +} + +/**************************************************************************** +get a user session key associated with a connection associated with a +policy handle. +****************************************************************************/ +void cli_con_gen_next_creds(struct cli_connection *con, + DOM_CRED *new_clnt_cred) +{ + gen_next_creds(con->cli, new_clnt_cred); +} + +/**************************************************************************** +get a user session key associated with a connection associated with a +policy handle. +****************************************************************************/ +void cli_con_get_cli_cred(struct cli_connection *con, + DOM_CRED *clnt_cred) +{ + memcpy(clnt_cred, &con->cli->clnt_cred, sizeof(*clnt_cred)); +} + +/**************************************************************************** +get a user session key associated with a connection associated with a +policy handle. +****************************************************************************/ +BOOL cli_con_deal_with_creds(struct cli_connection *con, + DOM_CRED *rcv_srv_cred) +{ + return clnt_deal_with_creds(con->cli->sess_key, &con->cli->clnt_cred, + rcv_srv_cred); +} + +/**************************************************************************** +get a user session key associated with a connection associated with a +policy handle. +****************************************************************************/ +BOOL cli_con_set_creds(const char* srv_name, const uchar sess_key[16], + DOM_CRED *cred) +{ + struct cli_connection *con = NULL; + + if (!cli_connection_getsrv(srv_name, PIPE_NETLOGON, &con)) + { + return False; + } + + memcpy(con->cli->sess_key, sess_key, 16); + memcpy(&con->cli->clnt_cred, cred, sizeof(*cred)); return True; } diff --git a/source3/rpc_client/cli_login.c b/source3/rpc_client/cli_login.c index 45345cf4ac..6bb9fed063 100644 --- a/source3/rpc_client/cli_login.c +++ b/source3/rpc_client/cli_login.c @@ -29,76 +29,80 @@ extern int DEBUGLEVEL; Initialize domain session credentials. ****************************************************************************/ -uint32 cli_nt_setup_creds(struct cli_state *cli, uint16 fnum, +uint32 cli_nt_setup_creds( const char* srv_name, const char* myhostname, const char* trust_acct, - const char* srv_name, unsigned char trust_pwd[16], uint16 sec_chan) { - DOM_CHAL clnt_chal; - DOM_CHAL srv_chal; + DOM_CHAL clnt_chal; + DOM_CHAL srv_chal; uint32 ret; - UTIME zerotime; + UTIME zerotime; + uint8 sess_key[16]; + DOM_CRED clnt_cred; - /******************* Request Challenge ********************/ + /******************* Request Challenge ********************/ - generate_random_buffer( clnt_chal.data, 8, False); - - /* send a client challenge; receive a server challenge */ - ret = cli_net_req_chal(cli, fnum, srv_name, &clnt_chal, &srv_chal); - if (ret != 0) - { - DEBUG(1,("cli_nt_setup_creds: request challenge failed\n")); - return ret; - } + generate_random_buffer( clnt_chal.data, 8, False); - /**************** Long-term Session key **************/ + /* send a client challenge; receive a server challenge */ + ret = cli_net_req_chal(srv_name, myhostname, &clnt_chal, &srv_chal); + if (ret != 0) + { + DEBUG(1,("cli_nt_setup_creds: request challenge failed\n")); + return ret; + } - /* calculate the session key */ - cred_session_key(&clnt_chal, &srv_chal, (char *)trust_pwd, cli->sess_key); - bzero(cli->sess_key+8, 8); + /**************** Long-term Session key **************/ - /******************* Authenticate 2 ********************/ + /* calculate the session key */ + cred_session_key(&clnt_chal, &srv_chal, (char *)trust_pwd, sess_key); + bzero(sess_key+8, 8); - /* calculate auth-2 credentials */ - zerotime.time = 0; - cred_create(cli->sess_key, &clnt_chal, zerotime, &(cli->clnt_cred.challenge)); + /******************* Authenticate 2 ********************/ - /* - * Send client auth-2 challenge. - * Receive an auth-2 challenge response and check it. - */ + /* calculate auth-2 credentials */ + zerotime.time = 0; + cred_create(sess_key, &clnt_chal, zerotime, &clnt_cred.challenge); - ret = cli_net_auth2(cli, fnum, trust_acct, srv_name, - sec_chan, 0x000001ff, &srv_chal); - if (ret != 0x0) - { - DEBUG(1,("cli_nt_setup_creds: auth2 challenge failed. status: %x\n", ret)); - } + if (!cli_con_set_creds(srv_name, sess_key, &clnt_cred)) + { + return NT_STATUS_ACCESS_DENIED | 0xC0000000; + } - return ret; + /* + * Send client auth-2 challenge. + * Receive an auth-2 challenge response and check it. + */ + + ret = cli_net_auth2(srv_name, trust_acct, + sec_chan, 0x000001ff, &srv_chal); + if (ret != 0x0) + { + DEBUG(1,("cli_nt_setup_creds: auth2 challenge failed. status: %x\n", ret)); + } + + return ret; } /**************************************************************************** Set machine password. ****************************************************************************/ -BOOL cli_nt_srv_pwset(struct cli_state *cli, uint16 fnum, - unsigned char *new_hashof_trust_pwd, uint16 sec_chan) +BOOL cli_nt_srv_pwset(const char* srv_name, const char* myhostname, + const char* trust_acct, + unsigned char *new_hashof_trust_pwd, + uint16 sec_chan) { - unsigned char processed_new_pwd[16]; - DEBUG(5,("cli_nt_srv_pwset: %d\n", __LINE__)); #ifdef DEBUG_PASSWORD dump_data(6, new_hashof_trust_pwd, 16); #endif - /* Process the new password. */ - cred_hash3( processed_new_pwd, new_hashof_trust_pwd, cli->sess_key, 1); - /* send client srv_pwset challenge */ - return cli_net_srv_pwset(cli, fnum, processed_new_pwd, sec_chan); + return cli_net_srv_pwset(srv_name, myhostname, trust_acct, + new_hashof_trust_pwd, sec_chan); } /**************************************************************************** @@ -107,51 +111,59 @@ NT login - interactive. password equivalents, protected by the session key) is inherently insecure given the current design of the NT Domain system. JRA. ****************************************************************************/ -BOOL cli_nt_login_interactive(struct cli_state *cli, uint16 fnum, char *domain, char *username, - uint32 luid_low, char *password, - NET_ID_INFO_CTR *ctr, NET_USER_INFO_3 *user_info3) +BOOL cli_nt_login_interactive(const char* srv_name, const char* myhostname, + const char *domain, const char *username, + uint32 luid_low, char *password, + NET_ID_INFO_CTR *ctr, + NET_USER_INFO_3 *user_info3) { - uchar lm_owf_user_pwd[16]; - uchar nt_owf_user_pwd[16]; - BOOL ret; + uchar lm_owf_user_pwd[16]; + uchar nt_owf_user_pwd[16]; + BOOL ret; + uint8 sess_key[16]; - DEBUG(5,("cli_nt_login_interactive: %d\n", __LINE__)); + DEBUG(5,("cli_nt_login_interactive: %d\n", __LINE__)); - nt_lm_owf_gen(password, nt_owf_user_pwd, lm_owf_user_pwd); + nt_lm_owf_gen(password, nt_owf_user_pwd, lm_owf_user_pwd); #ifdef DEBUG_PASSWORD - DEBUG(100,("nt owf of user password: ")); - dump_data(100, lm_owf_user_pwd, 16); + DEBUG(100,("nt owf of user password: ")); + dump_data(100, lm_owf_user_pwd, 16); - DEBUG(100,("nt owf of user password: ")); - dump_data(100, nt_owf_user_pwd, 16); + DEBUG(100,("nt owf of user password: ")); + dump_data(100, nt_owf_user_pwd, 16); #endif - DEBUG(5,("cli_nt_login_interactive: %d\n", __LINE__)); + if (!cli_get_sesskey_srv(srv_name, sess_key)) + { + DEBUG(1,("could not obtain session key for %s\n", srv_name)); + return False; + } - /* indicate an "interactive" login */ - ctr->switch_value = INTERACTIVE_LOGON_TYPE; + /* indicate an "interactive" login */ + ctr->switch_value = INTERACTIVE_LOGON_TYPE; - /* Create the structure needed for SAM logon. */ - make_id_info1(&ctr->auth.id1, domain, 0, - luid_low, 0, - username, cli->clnt_name_slash, - (char *)cli->sess_key, lm_owf_user_pwd, nt_owf_user_pwd); + /* Create the structure needed for SAM logon. */ + make_id_info1(&ctr->auth.id1, domain, 0, + luid_low, 0, + username, myhostname, + (char *)sess_key, + lm_owf_user_pwd, nt_owf_user_pwd); - /* Ensure we overwrite all the plaintext password - equivalents. */ - memset(lm_owf_user_pwd, '\0', sizeof(lm_owf_user_pwd)); - memset(nt_owf_user_pwd, '\0', sizeof(nt_owf_user_pwd)); + /* Ensure we overwrite all the plaintext password + equivalents. */ + memset(lm_owf_user_pwd, '\0', sizeof(lm_owf_user_pwd)); + memset(nt_owf_user_pwd, '\0', sizeof(nt_owf_user_pwd)); - /* Send client sam-logon request - update credentials on success. */ - ret = cli_net_sam_logon(cli, fnum, ctr, user_info3); + /* Send client sam-logon request - update credentials on success. */ + ret = cli_net_sam_logon(srv_name, myhostname, ctr, user_info3); - memset(ctr->auth.id1.lm_owf.data, '\0', sizeof(lm_owf_user_pwd)); - memset(ctr->auth.id1.nt_owf.data, '\0', sizeof(nt_owf_user_pwd)); + memset(ctr->auth.id1.lm_owf.data, '\0', sizeof(lm_owf_user_pwd)); + memset(ctr->auth.id1.nt_owf.data, '\0', sizeof(nt_owf_user_pwd)); - return ret; + return ret; } /**************************************************************************** @@ -160,38 +172,44 @@ NT login - network. password equivalents over the network. JRA. ****************************************************************************/ -BOOL cli_nt_login_network(struct cli_state *cli, uint16 fnum, char *domain, char *username, - uint32 luid_low, char lm_chal[8], char lm_chal_resp[24], - char nt_chal_resp[24], - NET_ID_INFO_CTR *ctr, NET_USER_INFO_3 *user_info3) +BOOL cli_nt_login_network(const char* srv_name, const char* myhostname, + const char *domain, const char *username, + uint32 luid_low, char lm_chal[8], + char lm_chal_resp[24], + char nt_chal_resp[24], + NET_ID_INFO_CTR *ctr, + NET_USER_INFO_3 *user_info3) { - uchar key[16]; + uint8 sess_key[16]; BOOL ret; DEBUG(5,("cli_nt_login_network: %d\n", __LINE__)); + if (!cli_get_sesskey_srv(srv_name, sess_key)) + { + DEBUG(1,("could not obtain session key for %s\n", srv_name)); + return False; + } + /* indicate a "network" login */ ctr->switch_value = NET_LOGON_TYPE; /* Create the structure needed for SAM logon. */ make_id_info2(&ctr->auth.id2, domain, 0, luid_low, 0, - username, cli->clnt_name_slash, + username, myhostname, (uchar *)lm_chal, (uchar *)lm_chal_resp, (uchar *)nt_chal_resp); /* Send client sam-logon request - update credentials on success. */ - ret = cli_net_sam_logon(cli, fnum, ctr, user_info3); + ret = cli_net_sam_logon(srv_name, myhostname, ctr, user_info3); #ifdef DEBUG_PASSWORD DEBUG(100,("cli sess key:")); - dump_data(100, cli->sess_key, 8); + dump_data(100, sess_key, 8); DEBUG(100,("enc user sess key:")); dump_data(100, user_info3->user_sess_key, 16); #endif - memset(key, 0, 16); - memcpy(key, (char*)cli->sess_key, 8); - - SamOEMhash(user_info3->user_sess_key, key, False); + SamOEMhash(user_info3->user_sess_key, sess_key, False); #ifdef DEBUG_PASSWORD DEBUG(100,("dec user sess key:")); @@ -203,10 +221,49 @@ BOOL cli_nt_login_network(struct cli_state *cli, uint16 fnum, char *domain, char /**************************************************************************** NT Logoff. ****************************************************************************/ -BOOL cli_nt_logoff(struct cli_state *cli, uint16 fnum, NET_ID_INFO_CTR *ctr) +BOOL cli_nt_logoff(const char* srv_name, const char* myhostname, + NET_ID_INFO_CTR *ctr) { DEBUG(5,("cli_nt_logoff: %d\n", __LINE__)); /* Send client sam-logoff request - update credentials on success. */ - return cli_net_sam_logoff(cli, fnum, ctr); + return cli_net_sam_logoff(srv_name, myhostname, ctr); +} + +/**************************************************************************** +NT SAM database sync +****************************************************************************/ +BOOL net_sam_sync(const char* srv_name, const char* myhostname, + const char* trust_acct, + uchar trust_passwd[16], + SAM_DELTA_HDR hdr_deltas[MAX_SAM_DELTAS], + SAM_DELTA_CTR deltas [MAX_SAM_DELTAS], + uint32 *num_deltas) +{ + BOOL res = True; + + *num_deltas = 0; + + DEBUG(5,("Attempting SAM sync with PDC: %s\n", + srv_name)); + + res = res ? cli_nt_setup_creds( srv_name, myhostname, + trust_acct, + trust_passwd, SEC_CHAN_BDC) == 0x0 : False; + + memset(trust_passwd, 0, 16); + + res = res ? cli_net_sam_sync(srv_name, myhostname, + 0, num_deltas, hdr_deltas, deltas) : False; + + if (!res) + { + DEBUG(5, ("SAM synchronisation FAILED\n")); + return False; + } + + DEBUG(5, ("SAM synchronisation returned %d entries\n", *num_deltas)); + + return True; } + diff --git a/source3/rpc_client/cli_lsarpc.c b/source3/rpc_client/cli_lsarpc.c index c8240a3299..e9bb175c83 100644 --- a/source3/rpc_client/cli_lsarpc.c +++ b/source3/rpc_client/cli_lsarpc.c @@ -465,7 +465,7 @@ BOOL lsa_query_secret(POLICY_HND *hnd, STRING2 *secret, STRING2 enc_secret; memcpy(&enc_secret, &(r_q.info.value.enc_secret), sizeof(STRING2)); memcpy(last_update, &(r_q.info.last_update), sizeof(NTTIME)); - if (!cli_get_usr_sesskey(hnd, sess_key)) + if (!cli_get_sesskey(hnd, sess_key)) { return False; } diff --git a/source3/rpc_client/cli_netlogon.c b/source3/rpc_client/cli_netlogon.c index d6db75f243..1231c706d0 100644 --- a/source3/rpc_client/cli_netlogon.c +++ b/source3/rpc_client/cli_netlogon.c @@ -30,13 +30,12 @@ #include "includes.h" extern int DEBUGLEVEL; -extern pstring global_myname; /**************************************************************************** Generate the next creds to use. ****************************************************************************/ -static void gen_next_creds( struct cli_state *cli, DOM_CRED *new_clnt_cred) +void gen_next_creds( struct cli_state *cli, DOM_CRED *new_clnt_cred) { /* * Create the new client credentials. @@ -52,54 +51,58 @@ static void gen_next_creds( struct cli_state *cli, DOM_CRED *new_clnt_cred) } -#if UNUSED_CODE /**************************************************************************** do a LSA Logon Control2 ****************************************************************************/ -BOOL cli_net_logon_ctrl2(struct cli_state *cli, uint16 nt_pipe_fnum, uint32 status_level) +BOOL cli_net_logon_ctrl2(const char* srv_name, uint32 status_level) { - prs_struct rbuf; - prs_struct buf; - NET_Q_LOGON_CTRL2 q_l; - BOOL ok = False; + prs_struct rbuf; + prs_struct buf; + NET_Q_LOGON_CTRL2 q_l; + BOOL ok = False; - prs_init(&buf , 1024, 4, SAFETY_MARGIN, False); - prs_init(&rbuf, 0, 4, SAFETY_MARGIN, True ); + struct cli_connection *con = NULL; - /* create and send a MSRPC command with api NET_LOGON_CTRL2 */ + if (!cli_connection_init(srv_name, PIPE_NETLOGON, &con)) + { + return False; + } - DEBUG(4,("do_net_logon_ctrl2 from %s status level:%x\n", - global_myname, status_level)); + prs_init(&buf , 1024, 4, SAFETY_MARGIN, False); + prs_init(&rbuf, 0, 4, SAFETY_MARGIN, True ); - /* store the parameters */ - make_q_logon_ctrl2(&q_l, cli->srv_name_slash, status_level); + /* create and send a MSRPC command with api NET_LOGON_CTRL2 */ - /* turn parameters into data stream */ - net_io_q_logon_ctrl2("", &q_l, &buf, 0); + DEBUG(4,("net_logon_ctrl2 status level:%x\n", status_level)); - /* send the data on \PIPE\ */ - if (rpc_api_pipe_req(cli, nt_pipe_fnum, NET_LOGON_CTRL2, &buf, &rbuf)) - { - NET_R_LOGON_CTRL2 r_l; + /* store the parameters */ + make_q_logon_ctrl2(&q_l, srv_name, 0, 0, status_level); - net_io_r_logon_ctrl2("", &r_l, &rbuf, 0); - ok = (rbuf.offset != 0); - - if (ok && r_l.status != 0) - { - /* report error code */ - DEBUG(5,("do_net_logon_ctrl2: Error %s\n", get_nt_error_msg(r_l.status))); - cli->nt_error = r_l.status; - ok = False; - } - } + /* turn parameters into data stream */ + net_io_q_logon_ctrl2("", &q_l, &buf, 0); - prs_mem_free(&rbuf); - prs_mem_free(&buf ); + /* send the data on \PIPE\ */ + if (rpc_con_pipe_req(con, NET_LOGON_CTRL2, &buf, &rbuf)) + { + NET_R_LOGON_CTRL2 r_l; - return ok; + net_io_r_logon_ctrl2("", &r_l, &rbuf, 0); + ok = (rbuf.offset != 0); + + if (ok && r_l.status != 0) + { + /* report error code */ + DEBUG(5,("net_logon_ctrl2: Error %s\n", get_nt_error_msg(r_l.status))); + ok = False; + } + } + + prs_mem_free(&rbuf); + prs_mem_free(&buf ); + + cli_connection_unlink(con); + return ok; } -#endif /**************************************************************************** LSA Authenticate 2 @@ -109,34 +112,50 @@ Ensure that the server credential returned matches the session key encrypt of the server challenge originally received. JRA. ****************************************************************************/ -uint32 cli_net_auth2(struct cli_state *cli, uint16 nt_pipe_fnum, +uint32 cli_net_auth2(const char *srv_name, const char *trust_acct, - const char *srv_name, uint16 sec_chan, + uint16 sec_chan, uint32 neg_flags, DOM_CHAL *srv_chal) { prs_struct rbuf; prs_struct buf; NET_Q_AUTH_2 q_a; uint32 status = 0x0; + uint8 sess_key[16]; + DOM_CRED clnt_cred; + + struct cli_connection *con = NULL; + + if (!cli_connection_getsrv(srv_name, PIPE_NETLOGON, &con)) + { + return False; + } + + if (!cli_get_con_sesskey(con, sess_key)) + { + return False; + } prs_init(&buf , 1024, 4, SAFETY_MARGIN, False); prs_init(&rbuf, 0, 4, SAFETY_MARGIN, True ); /* create and send a MSRPC command with api NET_AUTH2 */ - DEBUG(4,("cli_net_auth2: srv:%s acct:%s sc:%x mc: %s chal %s neg: %x\n", - cli->srv_name_slash, cli->mach_acct, sec_chan, srv_name, - credstr(cli->clnt_cred.challenge.data), neg_flags)); + DEBUG(4,("cli_net_auth2: srv:%s acct:%s sc:%x mc: %s neg: %x\n", + srv_name, trust_acct, sec_chan, srv_name, + neg_flags)); + + cli_con_get_cli_cred(con, &clnt_cred); /* store the parameters */ - make_q_auth_2(&q_a, cli->srv_name_slash, trust_acct, sec_chan, srv_name, - &cli->clnt_cred.challenge, neg_flags); + make_q_auth_2(&q_a, srv_name, trust_acct, sec_chan, srv_name, + &clnt_cred.challenge, neg_flags); /* turn parameters into data stream */ net_io_q_auth_2("", &q_a, &buf, 0); /* send the data on \PIPE\ */ - if (rpc_api_pipe_req(cli, nt_pipe_fnum, NET_AUTH2, &buf, &rbuf)) + if (rpc_con_pipe_req(con, NET_AUTH2, &buf, &rbuf)) { NET_R_AUTH_2 r_a; @@ -148,7 +167,6 @@ uint32 cli_net_auth2(struct cli_state *cli, uint16 nt_pipe_fnum, /* report error code */ DEBUG(5,("cli_net_auth2: Error %s\n", get_nt_error_msg(r_a.status))); - cli->nt_error = r_a.status; status = r_a.status; } @@ -161,13 +179,14 @@ uint32 cli_net_auth2(struct cli_state *cli, uint16 nt_pipe_fnum, UTIME zerotime; zerotime.time = 0; - if(cred_assert( &r_a.srv_chal, cli->sess_key, srv_chal, zerotime) == 0) + if(cred_assert( &r_a.srv_chal, sess_key, + srv_chal, zerotime) == 0) { /* * Server replied with bad credential. Fail. */ - DEBUG(5,("cli_net_auth2: server %s replied with bad credential (bad machine \ - password ?).\n", cli->desthost )); + DEBUG(5,("cli_net_auth2: server %s replied \ +with bad credential (bad trust account password ?).\n", srv_name)); status = NT_STATUS_NETWORK_CREDENTIAL_CONFLICT | 0xC0000000; } } @@ -190,7 +209,7 @@ uint32 cli_net_auth2(struct cli_state *cli, uint16 nt_pipe_fnum, } else { - DEBUG(5,("rpc_api_pipe_req FAILED\n")); + DEBUG(5,("rpc_con_pipe_req FAILED\n")); status = 0xC0000000 | NT_STATUS_ACCESS_DENIED; } @@ -207,8 +226,7 @@ LSA Request Challenge. Sends our challenge to server, then gets server response. These are used to generate the credentials. ****************************************************************************/ -uint32 cli_net_req_chal(struct cli_state *cli, uint16 nt_pipe_fnum, - const char *srv_name, +uint32 cli_net_req_chal( const char *srv_name, const char* myhostname, DOM_CHAL *clnt_chal, DOM_CHAL *srv_chal) { prs_struct rbuf; @@ -216,6 +234,13 @@ uint32 cli_net_req_chal(struct cli_state *cli, uint16 nt_pipe_fnum, NET_Q_REQ_CHAL q_c; uint32 status = 0x0; + struct cli_connection *con = NULL; + + if (!cli_connection_init(srv_name, PIPE_NETLOGON, &con)) + { + return False; + } + if (srv_chal == NULL || clnt_chal == NULL) return 0xC0000000 | NT_STATUS_INVALID_PARAMETER; @@ -225,16 +250,16 @@ uint32 cli_net_req_chal(struct cli_state *cli, uint16 nt_pipe_fnum, /* create and send a MSRPC command with api NET_REQCHAL */ DEBUG(4,("cli_net_req_chal: LSA Request Challenge from %s to %s: %s\n", - cli->desthost, srv_name, credstr(clnt_chal->data))); + srv_name, myhostname, credstr(clnt_chal->data))); /* store the parameters */ - make_q_req_chal(&q_c, cli->srv_name_slash, srv_name, clnt_chal); + make_q_req_chal(&q_c, srv_name, myhostname, clnt_chal); /* turn parameters into data stream */ net_io_q_req_chal("", &q_c, &buf, 0); /* send the data on \PIPE\ */ - if (rpc_api_pipe_req(cli, nt_pipe_fnum, NET_REQCHAL, &buf, &rbuf)) + if (rpc_con_pipe_req(con, NET_REQCHAL, &buf, &rbuf)) { NET_R_REQ_CHAL r_c; @@ -245,7 +270,6 @@ uint32 cli_net_req_chal(struct cli_state *cli, uint16 nt_pipe_fnum, { /* report error code */ DEBUG(5,("cli_net_req_chal: Error %s\n", get_nt_error_msg(r_c.status))); - cli->nt_error = r_c.status; status = r_c.status; } @@ -257,7 +281,7 @@ uint32 cli_net_req_chal(struct cli_state *cli, uint16 nt_pipe_fnum, } else { - DEBUG(5,("rpc_api_pipe_req FAILED\n")); + DEBUG(5,("rpc_con_pipe_req FAILED\n")); status = 0xC0000000 | NT_STATUS_ACCESS_DENIED; } @@ -271,16 +295,37 @@ uint32 cli_net_req_chal(struct cli_state *cli, uint16 nt_pipe_fnum, LSA Server Password Set. ****************************************************************************/ -BOOL cli_net_srv_pwset(struct cli_state *cli, uint16 nt_pipe_fnum, - uint8 hashed_mach_pwd[16], uint16 sec_chan_type) +BOOL cli_net_srv_pwset(const char* srv_name, + const char* myhostname, + const char* trust_acct, + uint8 hashed_trust_pwd[16], + uint16 sec_chan_type) { prs_struct rbuf; prs_struct buf; DOM_CRED new_clnt_cred; NET_Q_SRV_PWSET q_s; BOOL ok = False; + unsigned char processed_new_pwd[16]; + /* Process the new password. */ + + uint8 sess_key[16]; + + struct cli_connection *con = NULL; - gen_next_creds( cli, &new_clnt_cred); + if (!cli_connection_getsrv(srv_name, PIPE_NETLOGON, &con)) + { + return False; + } + + if (!cli_get_con_sesskey(con, sess_key)) + { + return False; + } + + cred_hash3( processed_new_pwd, hashed_trust_pwd, sess_key, 1); + + cli_con_gen_next_creds( con, &new_clnt_cred); prs_init(&buf , 1024, 4, SAFETY_MARGIN, False); prs_init(&rbuf, 0, 4, SAFETY_MARGIN, True ); @@ -288,18 +333,18 @@ BOOL cli_net_srv_pwset(struct cli_state *cli, uint16 nt_pipe_fnum, /* create and send a MSRPC command with api NET_SRV_PWSET */ DEBUG(4,("cli_net_srv_pwset: srv:%s acct:%s sc: %d mc: %s clnt %s %x\n", - cli->srv_name_slash, cli->mach_acct, sec_chan_type, global_myname, + srv_name, trust_acct, sec_chan_type, myhostname, credstr(new_clnt_cred.challenge.data), new_clnt_cred.timestamp.time)); /* store the parameters */ - make_q_srv_pwset(&q_s, cli->srv_name_slash, cli->mach_acct, sec_chan_type, - global_myname, &new_clnt_cred, (char *)hashed_mach_pwd); + make_q_srv_pwset(&q_s, srv_name, trust_acct, sec_chan_type, + myhostname, &new_clnt_cred, (char *)processed_new_pwd); /* turn parameters into data stream */ net_io_q_srv_pwset("", &q_s, &buf, 0); /* send the data on \PIPE\ */ - if (rpc_api_pipe_req(cli, nt_pipe_fnum, NET_SRVPWSET, &buf, &rbuf)) + if (rpc_con_pipe_req(con, NET_SRVPWSET, &buf, &rbuf)) { NET_R_SRV_PWSET r_s; @@ -310,18 +355,17 @@ BOOL cli_net_srv_pwset(struct cli_state *cli, uint16 nt_pipe_fnum, { /* report error code */ DEBUG(5,("cli_net_srv_pwset: %s\n", get_nt_error_msg(r_s.status))); - cli->nt_error = r_s.status; ok = False; } /* Update the credentials. */ - if (ok && !clnt_deal_with_creds(cli->sess_key, &(cli->clnt_cred), &(r_s.srv_cred))) + if (ok && !cli_con_deal_with_creds(con, &(r_s.srv_cred))) { /* * Server replied with bad credential. Fail. */ - DEBUG(5,("cli_net_srv_pwset: server %s replied with bad credential (bad machine \ -password ?).\n", cli->desthost )); + DEBUG(5,("cli_net_srv_pwset: server %s replied with bad credential \ +(bad trust account password ?).\n", srv_name)); ok = False; } } @@ -336,8 +380,9 @@ password ?).\n", cli->desthost )); LSA SAM Logon - interactive or network. ****************************************************************************/ -BOOL cli_net_sam_logon(struct cli_state *cli, uint16 nt_pipe_fnum, NET_ID_INFO_CTR *ctr, - NET_USER_INFO_3 *user_info3) +BOOL cli_net_sam_logon(const char* srv_name, const char* myhostname, + NET_ID_INFO_CTR *ctr, + NET_USER_INFO_3 *user_info3) { DOM_CRED new_clnt_cred; DOM_CRED dummy_rtn_creds; @@ -347,30 +392,36 @@ BOOL cli_net_sam_logon(struct cli_state *cli, uint16 nt_pipe_fnum, NET_ID_INFO_C NET_Q_SAM_LOGON q_s; BOOL ok = False; - gen_next_creds( cli, &new_clnt_cred); + struct cli_connection *con = NULL; + + if (!cli_connection_getsrv(srv_name, PIPE_NETLOGON, &con)) + { + return False; + } + + cli_con_gen_next_creds( con, &new_clnt_cred); prs_init(&buf , 1024, 4, SAFETY_MARGIN, False); prs_init(&rbuf, 0, 4, SAFETY_MARGIN, True ); /* create and send a MSRPC command with api NET_SAMLOGON */ - DEBUG(4,("cli_net_sam_logon: srv:%s mc:%s clnt %s %x ll: %d\n", - cli->srv_name_slash, global_myname, - credstr(new_clnt_cred.challenge.data), cli->clnt_cred.timestamp.time, + DEBUG(4,("cli_net_sam_logon: srv:%s mc:%s ll: %d\n", + srv_name, myhostname, ctr->switch_value)); memset(&dummy_rtn_creds, '\0', sizeof(dummy_rtn_creds)); dummy_rtn_creds.timestamp.time = time(NULL); /* store the parameters */ - make_sam_info(&(q_s.sam_id), cli->srv_name_slash, global_myname, + make_sam_info(&(q_s.sam_id), srv_name, myhostname, &new_clnt_cred, &dummy_rtn_creds, ctr->switch_value, ctr, validation_level); /* turn parameters into data stream */ net_io_q_sam_logon("", &q_s, &buf, 0); /* send the data on \PIPE\ */ - if (rpc_api_pipe_req(cli, nt_pipe_fnum, NET_SAMLOGON, &buf, &rbuf)) + if (rpc_con_pipe_req(con, NET_SAMLOGON, &buf, &rbuf)) { NET_R_SAM_LOGON r_s; @@ -383,18 +434,17 @@ BOOL cli_net_sam_logon(struct cli_state *cli, uint16 nt_pipe_fnum, NET_ID_INFO_C { /* report error code */ DEBUG(5,("cli_net_sam_logon: %s\n", get_nt_error_msg(r_s.status))); - cli->nt_error = r_s.status; ok = False; } /* Update the credentials. */ - if (ok && !clnt_deal_with_creds(cli->sess_key, &(cli->clnt_cred), &(r_s.srv_creds))) + if (ok && !cli_con_deal_with_creds(con, &(r_s.srv_creds))) { /* * Server replied with bad credential. Fail. */ - DEBUG(5,("cli_net_sam_logon: server %s replied with bad credential (bad machine \ -password ?).\n", cli->desthost )); + DEBUG(5,("cli_net_sam_logon: server %s replied with bad credential \ +(bad trust account password ?).\n", srv_name)); ok = False; } @@ -422,7 +472,8 @@ send a different info level. Right now though, I'm not sure what that needs to be (I need to see one on the wire before I can be sure). JRA. ****************************************************************************/ -BOOL cli_net_sam_logoff(struct cli_state *cli, uint16 nt_pipe_fnum, NET_ID_INFO_CTR *ctr) +BOOL cli_net_sam_logoff(const char* srv_name, const char* myhostname, + NET_ID_INFO_CTR *ctr) { DOM_CRED new_clnt_cred; DOM_CRED dummy_rtn_creds; @@ -432,7 +483,14 @@ BOOL cli_net_sam_logoff(struct cli_state *cli, uint16 nt_pipe_fnum, NET_ID_INFO_ uint16 validation_level = 3; BOOL ok = False; - gen_next_creds( cli, &new_clnt_cred); + struct cli_connection *con = NULL; + + if (!cli_connection_getsrv(srv_name, PIPE_NETLOGON, &con)) + { + return False; + } + + cli_con_gen_next_creds( con, &new_clnt_cred); prs_init(&buf , 1024, 4, SAFETY_MARGIN, False); prs_init(&rbuf, 0, 4, SAFETY_MARGIN, True ); @@ -440,21 +498,21 @@ BOOL cli_net_sam_logoff(struct cli_state *cli, uint16 nt_pipe_fnum, NET_ID_INFO_ /* create and send a MSRPC command with api NET_SAMLOGOFF */ DEBUG(4,("cli_net_sam_logoff: srv:%s mc:%s clnt %s %x ll: %d\n", - cli->srv_name_slash, global_myname, + srv_name, myhostname, credstr(new_clnt_cred.challenge.data), new_clnt_cred.timestamp.time, ctr->switch_value)); memset(&dummy_rtn_creds, '\0', sizeof(dummy_rtn_creds)); /* store the parameters */ - make_sam_info(&(q_s.sam_id), cli->srv_name_slash, global_myname, + make_sam_info(&(q_s.sam_id), srv_name, myhostname, &new_clnt_cred, &dummy_rtn_creds, ctr->switch_value, ctr, validation_level); /* turn parameters into data stream */ net_io_q_sam_logoff("", &q_s, &buf, 0); /* send the data on \PIPE\ */ - if (rpc_api_pipe_req(cli, nt_pipe_fnum, NET_SAMLOGOFF, &buf, &rbuf)) + if (rpc_con_pipe_req(con, NET_SAMLOGOFF, &buf, &rbuf)) { NET_R_SAM_LOGOFF r_s; @@ -465,18 +523,17 @@ BOOL cli_net_sam_logoff(struct cli_state *cli, uint16 nt_pipe_fnum, NET_ID_INFO_ { /* report error code */ DEBUG(5,("cli_net_sam_logoff: %s\n", get_nt_error_msg(r_s.status))); - cli->nt_error = r_s.status; ok = False; } /* Update the credentials. */ - if (ok && !clnt_deal_with_creds(cli->sess_key, &(cli->clnt_cred), &(r_s.srv_creds))) + if (ok && !cli_con_deal_with_creds(con, &(r_s.srv_creds))) { /* * Server replied with bad credential. Fail. */ - DEBUG(5,("cli_net_sam_logoff: server %s replied with bad credential (bad machine \ -password ?).\n", cli->desthost )); + DEBUG(5,("cli_net_sam_logoff: server %s replied with bad credential \ +(bad trust account password ?).\n", srv_name )); ok = False; } } @@ -490,8 +547,7 @@ password ?).\n", cli->desthost )); /*************************************************************************** Synchronise SAM Database (requires SEC_CHAN_BDC). ****************************************************************************/ -BOOL cli_net_sam_sync(struct cli_state *cli, uint16 nt_pipe_fnum, - const char* srv_name, +BOOL cli_net_sam_sync( const char* srv_name, const char* myhostname, uint32 database_id, uint32 *num_deltas, SAM_DELTA_HDR *hdr_deltas, @@ -502,43 +558,56 @@ BOOL cli_net_sam_sync(struct cli_state *cli, uint16 nt_pipe_fnum, prs_struct buf; DOM_CRED new_clnt_cred; BOOL ok = False; + uint8 sess_key[16]; - gen_next_creds(cli, &new_clnt_cred); + struct cli_connection *con = NULL; + + if (!cli_connection_getsrv(srv_name, PIPE_NETLOGON, &con)) + { + return False; + } + + if (!cli_get_con_sesskey(con, sess_key)) + { + return False; + } + + cli_con_gen_next_creds(con, &new_clnt_cred); prs_init(&buf , 1024, 4, SAFETY_MARGIN, False); prs_init(&rbuf, 0, 4, SAFETY_MARGIN, True ); /* create and send a MSRPC command with api NET_SAM_SYNC */ - make_q_sam_sync(&q_s, cli->srv_name_slash, srv_name, + make_q_sam_sync(&q_s, srv_name, myhostname, &new_clnt_cred, database_id); /* turn parameters into data stream */ net_io_q_sam_sync("", &q_s, &buf, 0); /* send the data on \PIPE\ */ - if (rpc_api_pipe_req(cli, nt_pipe_fnum, NET_SAM_SYNC, &buf, &rbuf)) + if (rpc_con_pipe_req(con, NET_SAM_SYNC, &buf, &rbuf)) { NET_R_SAM_SYNC r_s; r_s.hdr_deltas = hdr_deltas; r_s.deltas = deltas; - net_io_r_sam_sync("", cli->sess_key, &r_s, &rbuf, 0); + net_io_r_sam_sync("", sess_key, &r_s, &rbuf, 0); ok = (rbuf.offset != 0); if (ok && r_s.status != 0 && r_s.status != STATUS_MORE_ENTRIES) { /* report error code */ DEBUG(5,("cli_net_sam_sync: %s\n", get_nt_error_msg(r_s.status))); - cli->nt_error = r_s.status; ok = False; } /* Update the credentials. */ - if (ok && !clnt_deal_with_creds(cli->sess_key, &(cli->clnt_cred), &(r_s.srv_creds))) + if (ok && !cli_con_deal_with_creds(con, &(r_s.srv_creds))) { - DEBUG(5,("cli_net_sam_sync: server %s replied with bad credential (bad machine password ?).\n", cli->desthost)); + DEBUG(5,("cli_net_sam_sync: server %s replied with bad \ +credential (bad trust account password ?).\n", srv_name)); ok = False; } @@ -558,46 +627,3 @@ BOOL cli_net_sam_sync(struct cli_state *cli, uint16 nt_pipe_fnum, return ok; } - - -BOOL do_sam_sync(struct cli_state *cli, uchar trust_passwd[16], - const char* acct_name, - const char* srv_name, - SAM_DELTA_HDR hdr_deltas[MAX_SAM_DELTAS], - SAM_DELTA_CTR deltas [MAX_SAM_DELTAS], - uint32 *num_deltas) -{ - uint16 nt_pipe_fnum; - BOOL res = True; - - *num_deltas = 0; - - DEBUG(5,("Attempting SAM sync with PDC: %s\n", - srv_name)); - - /* open NETLOGON session. negotiate credentials */ - res = res ? cli_nt_session_open(cli, PIPE_NETLOGON, &nt_pipe_fnum) : False; - - res = res ? cli_nt_setup_creds(cli, nt_pipe_fnum, - acct_name, srv_name, - trust_passwd, SEC_CHAN_BDC) == 0x0 : False; - - memset(trust_passwd, 0, 16); - - res = res ? cli_net_sam_sync(cli, nt_pipe_fnum, srv_name, - 0, num_deltas, hdr_deltas, deltas) : False; - - /* close the session */ - cli_nt_session_close(cli, nt_pipe_fnum); - - if (!res) - { - DEBUG(5, ("SAM synchronisation FAILED\n")); - return False; - } - - DEBUG(5, ("SAM synchronisation returned %d entries\n", *num_deltas)); - - return True; -} - diff --git a/source3/rpc_client/cli_netlogon_sync.c b/source3/rpc_client/cli_netlogon_sync.c index 526f366a15..fad802d0c9 100644 --- a/source3/rpc_client/cli_netlogon_sync.c +++ b/source3/rpc_client/cli_netlogon_sync.c @@ -44,23 +44,34 @@ BOOL synchronise_passdb(void) unsigned char smb_passwd[16]; unsigned char smb_nt_passwd[16]; uchar trust_passwd[16]; + fstring trust_acct; + fstring srv_name; char *mode; BOOL success; BOOL ret; int i; + DEBUG(0,("cannot make connection to multi-list of servers yet!\n")); + if (!cli_connect_serverlist(&cli, lp_passwordserver())) { return False; } + fstrcpy(srv_name, "\\\\"); + fstrcat(srv_name, lp_passwordserver()); /* LKCL XXXX oops! */ + strupper(srv_name); + + fstrcpy(trust_acct, global_myname); + fstrcat(trust_acct, "$"); + if (!trust_get_passwd(trust_passwd, lp_workgroup(), global_myname)) { return False; } - ret = do_sam_sync(&cli, trust_passwd, cli.mach_acct, global_myname, + ret = net_sam_sync(srv_name, global_myname, trust_acct, trust_passwd, hdr_deltas, deltas, &num); if (ret) diff --git a/source3/rpc_client/cli_pipe.c b/source3/rpc_client/cli_pipe.c index 8ca5255203..f8216cb1e0 100644 --- a/source3/rpc_client/cli_pipe.c +++ b/source3/rpc_client/cli_pipe.c @@ -1125,18 +1125,6 @@ BOOL cli_nt_session_open(struct cli_state *cli, const char *pipe_name, * Setup the remote server name prefixed by \ and the machine account name. */ - fstrcpy(cli->srv_name_slash, "\\\\"); - fstrcat(cli->srv_name_slash, cli->desthost); - strupper(cli->srv_name_slash); - - fstrcpy(cli->clnt_name_slash, "\\\\"); - fstrcat(cli->clnt_name_slash, global_myname); - strupper(cli->clnt_name_slash); - - fstrcpy(cli->mach_acct, global_myname); - fstrcat(cli->mach_acct, "$"); - strupper(cli->mach_acct); - return True; } |