r1836: - as abartlet said to me, we need to contact the users domain pdcfor doing a
authorStefan Metzmacher <metze@samba.org>
Mon, 16 Aug 2004 16:52:57 +0000 (16:52 +0000)
committerGerald (Jerry) Carter <jerry@samba.org>
Wed, 10 Oct 2007 17:58:00 +0000 (12:58 -0500)
  password change
- add start of libnet_SetPassword
- use KRB5 and LDAP instead of ADS as ADS isn't a protocol
- add start of lib_rpc_connect()

metze
(This used to be commit 05c40dca8ad1ab020aa75282da046f1dbce2a52a)

source4/configure.in
source4/include/includes.h
source4/libnet/config.mk
source4/libnet/libnet.h
source4/libnet/libnet_passwd.c
source4/libnet/libnet_rpc.c [new file with mode: 0644]

index 85c9b52a3a89f76e40289e1624509844bc4b0c77..f6bb836df513d769bc39a59b328f6c7784ea8190 100644 (file)
@@ -24,6 +24,7 @@ SMB_INCLUDE_M4(libcli/ldap/config.m4)
 SMB_INCLUDE_M4(libcli/config.m4)
 SMB_INCLUDE_M4(librpc/config.m4)
 SMB_INCLUDE_M4(libcli/libsmb.m4)
+SMB_INCLUDE_M4(libnet/config.m4)
 SMB_INCLUDE_M4(smbd/process_model.m4)
 SMB_INCLUDE_M4(smb_server/config.m4)
 SMB_INCLUDE_M4(auth/config.m4)
index f2900697f94baf0e869a856ed8989b7af31905eb..53a5a969e516017cce099833905a9867ca514182 100644 (file)
@@ -672,6 +672,8 @@ extern int errno;
 #include "gtk/common/gtk-smb.h"
 #include "gtk/common/select.h"
 
+#include "libnet/libnet.h"
+
 #define malloc_p(type) (type *)malloc(sizeof(type))
 #define malloc_array_p(type, count) (type *)realloc_array(NULL, sizeof(type), count)
 #define realloc_p(p, type, count) (type *)realloc_array(p, sizeof(type), count)
index ab2861f540fe8df27e92cb4e7a401bb20cb47563..1918f2e0950c65c0335988f6814b254d55f9a960 100644 (file)
@@ -1,6 +1,8 @@
 #################################
 # Start SUBSYSTEM LIBNET
 [SUBSYSTEM::LIBNET]
-ADD_OBJ_FILES = libnet/libnet_password.o
+ADD_OBJ_FILES = \
+               libnet/libnet_passwd.o \
+               libnet/libnet_rpc.o
 # End SUBSYSTEM LIBNET
 #################################
index f1ea6f4b0298925cc5f371bd293f6076b02de41f..65dba4ff78481df2939bb4ccc296924a105e2a0d 100644 (file)
 
 struct libnet_context {
        TALLOC_CTX *mem_ctx;
+
+       /* here we need:
+        * a client env context
+        * a user env context
+        */
+};
+
+/* struct and enum for connecting to a dcerpc inferface */
+enum libnet_rpc_connect_level {
+       LIBNET_RPC_CONNECT_PDC
+};
+
+union libnet_rpc_connect {
+       /* connect to a domains PDC */
+       struct {
+               enum libnet_rpc_connect_level level;
+
+               struct {
+                       const char *domain_name;
+                       const char *dcerpc_iface_name;
+                       const char *dcerpc_iface_uuid;
+                       uint32 dcerpc_iface_version;
+               } in;
+
+               struct  {
+                       struct dcerpc_pipe *dcerpc_pipe;
+               } out;
+       } pdc;
 };
 
-/* struct for doing a remote password change */
 
+/* struct and enum for doing a remote password change */
 enum libnet_ChangePassword_level {
        LIBNET_CHANGE_PASSWORD_GENERIC,
        LIBNET_CHANGE_PASSWORD_RPC,
-       LIBNET_CHANGE_PASSWORD_ADS,
+       LIBNET_CHANGE_PASSWORD_KRB5,
+       LIBNET_CHANGE_PASSWORD_LDAP,
        LIBNET_CHANGE_PASSWORD_RAP
 };
 
@@ -57,11 +86,66 @@ union libnet_ChangePassword {
                enum libnet_ChangePassword_level level;
                struct _libnet_ChangePassword_in in;
                struct _libnet_ChangePassword_out out;
-       } ads;
+       } krb5;
 
        struct {
                enum libnet_ChangePassword_level level;
                struct _libnet_ChangePassword_in in;
                struct _libnet_ChangePassword_out out;
+       } ldap;
+
+       struct {
+               enum libnet_ChangePassword_level level;
+               struct _libnet_ChangePassword_in in;
+               struct _libnet_ChangePassword_out out;
+       } rap;
+};
+
+/* struct and enum for doing a remote password set */
+enum libnet_SetPassword_level {
+       LIBNET_SET_PASSWORD_GENERIC,
+       LIBNET_SET_PASSWORD_RPC,
+       LIBNET_SET_PASSWORD_KRB5,
+       LIBNET_SET_PASSWORD_LDAP,
+       LIBNET_SET_PASSWORD_RAP
+};
+
+union libnet_SetPassword {
+       struct {
+               enum libnet_SetPassword_level level;
+
+               struct _libnet_SetPassword_in {
+                       const char *account_name;
+                       const char *domain_name;
+                       const char *newpassword;
+               } in;
+
+               struct _libnet_SetPassword_out {
+                       const char *error_string;
+               } out;
+       } generic;
+
+       struct {
+               enum libnet_SetPassword_level level;
+               struct _libnet_SetPassword_in in;
+               struct _libnet_SetPassword_out out;
+       } rpc;
+
+       struct {
+               enum libnet_SetPassword_level level;
+               struct _libnet_SetPassword_in in;
+               struct _libnet_SetPassword_out out;
+       } krb5;
+
+       struct {
+               enum libnet_SetPassword_level level;
+               struct _libnet_SetPassword_in in;
+               struct _libnet_SetPassword_out out;
+       } ldap;
+
+       struct {
+               enum libnet_ChangePassword_level level;
+               struct _libnet_SetPassword_in in;
+               struct _libnet_SetPassword_out out;
        } rap;
 };
index edf0d27b95f31f83ff9fdbebc9e1e2770036533b..6164aed9ad972777120336cc9167ef0973451382 100644 (file)
    Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
 */
 
+#include "includes.h"
+
 /*
- * 1. connect to the SAMR pipe of *our* PDC
+ * do a password change using DCERPC/SAMR calls
+ * 1. connect to the SAMR pipe of users domain PDC (maybe a standalone server or workstation)
  * 2. try samr_ChangePassword3
  */
-static NTSTATUS libnet_ChangePassword_rpc(struct libnet_context *ctx, TALLOC_CTX *mem_ctx, struct net_ChangePassword *r)
+static NTSTATUS libnet_ChangePassword_rpc(struct libnet_context *ctx, TALLOC_CTX *mem_ctx, union libnet_ChangePassword *r)
 {
         NTSTATUS status;
-        struct dcerpc_pipe *p = NULL;
+       union libnet_rpc_connect c;
        struct samr_ChangePasswordUser3 pw3;
        struct samr_Name server, account;
        struct samr_CryptPassword nt_pass, lm_pass;
@@ -33,13 +36,15 @@ static NTSTATUS libnet_ChangePassword_rpc(struct libnet_context *ctx, TALLOC_CTX
        uint8_t old_nt_hash[16], new_nt_hash[16];
        uint8_t old_lm_hash[16], new_lm_hash[16];
 
-       /* connect to the SAMR pipe of the */
-       status = libnet_rpc_connect_pdc(ctx, mem_ctx,
-                                       r->rpc.in.domain_name,
-                                       DCERPC_SAMR_NAME,
-                                       DCERPC_SAMR_UUID,
-                                       DCERPC_SAMR_VERSION,
-                                       &p);
+       /* prepare connect to the SAMR pipe of the */
+       c.pdc.level                     = LIBNET_RPC_CONNECT_PDC;
+       c.pdc.in.domain_name            = r->rpc.in.domain_name;
+       c.pdc.in.dcerpc_iface_name      = DCERPC_SAMR_NAME;
+       c.pdc.in.dcerpc_iface_uuid      = DCERPC_SAMR_UUID;
+       c.pdc.in.dcerpc_iface_version   = DCERPC_SAMR_VERSION;
+
+       /* do connect to the SAMR pipe of the */
+       status = libnet_rpc_connect(ctx, mem_ctx, &c);
        if (!NT_STATUS_IS_OK(status)) {
                r->rpc.out.error_string = talloc_asprintf(mem_ctx,
                                                "Connection to SAMR pipe of PDC of domain '%s' failed\n",
@@ -47,8 +52,9 @@ static NTSTATUS libnet_ChangePassword_rpc(struct libnet_context *ctx, TALLOC_CTX
                return status;
        }
 
-       server.name = talloc_asprintf(mem_ctx, "\\\\%s", dcerpc_server_name(p));
-       init_samr_Name(&account, r->rpc.in.account_name);
+       /* prepare password change for account */
+       server.name = talloc_asprintf(mem_ctx, "\\\\%s", dcerpc_server_name(c.pdc.out.dcerpc_pipe));
+       account.name = r->rpc.in.account_name;
 
        E_md4hash(r->rpc.in.oldpassword, old_nt_hash);
        E_md4hash(r->rpc.in.newpassword, new_nt_hash);
@@ -73,44 +79,80 @@ static NTSTATUS libnet_ChangePassword_rpc(struct libnet_context *ctx, TALLOC_CTX
        pw3.in.lm_verifier = &lm_verifier;
        pw3.in.password3 = NULL;
 
-       status = dcerpc_samr_ChangePassword3(p, mem_ctx, &pw3);
+       /* do password change for account */
+       status = dcerpc_samr_ChangePasswordUser3(c.pdc.out.dcerpc_pipe, mem_ctx, &pw3);
        if (!NT_STATUS_IS_OK(status)) {
                r->rpc.out.error_string = talloc_asprintf(mem_ctx,
-                                               "ChangePassword3 failed: %s\n",nt_errstr(status);
-               return status;
+                                               "ChangePassword3 failed: %s\n",nt_errstr(status));
+               goto disconnect;
        }
 
-       if (!NT_STATUS_IS_OK(r->rpc.out.result)) {
+       /* check result of password change */
+       if (!NT_STATUS_IS_OK(pw3.out.result)) {
                r->rpc.out.error_string = talloc_asprintf(mem_ctx,
                                                "ChangePassword3 for '%s\\%s' failed: %s\n",
                                                r->rpc.in.domain_name, r->rpc.in.account_name, 
                                                nt_errstr(status));
                                                /* TODO: give the reason of the reject */
-               return status;
-       
+               goto disconnect;
        }
 
-       dcerpc_diconnect(&p);
+disconnect:
+       /* close connection */
+       dcerpc_pipe_close(c.pdc.out.dcerpc_pipe);
 
-       return NT_STATUS_OK;
+       return status;
 }
 
-static NTSTATUS libnet_ChangePassword_generic(struct libnet_context *ctx, TALLOC_CTX *mem_ctx, struct net_ChangePassword *r)
+static NTSTATUS libnet_ChangePassword_generic(struct libnet_context *ctx, TALLOC_CTX *mem_ctx, union libnet_ChangePassword *r)
 {
-       return NT_STATUS_NOT_IMPLEMTED;
+       return NT_STATUS_NOT_IMPLEMENTED;
 }
 
-NTSTATUS libnet_ChangePassword(struct libnet_context *ctx, TALLOC_CTX *mem_ctx, struct net_ChangePassword *r)
+NTSTATUS libnet_ChangePassword(struct libnet_context *ctx, TALLOC_CTX *mem_ctx, union libnet_ChangePassword *r)
 {
        switch (r->generic.level) {
                case LIBNET_CHANGE_PASSWORD_GENERIC:
                        return libnet_ChangePassword_generic(ctx, mem_ctx, r);
                case LIBNET_CHANGE_PASSWORD_RPC:
                        return libnet_ChangePassword_rpc(ctx, mem_ctx, r);
-               case LIBNET_CHANGE_PASSWORD_ADS:
-                       return NT_STATUS_NOT_IMPLEMTED;
+               case LIBNET_CHANGE_PASSWORD_KRB5:
+                       return NT_STATUS_NOT_IMPLEMENTED;
+               case LIBNET_CHANGE_PASSWORD_LDAP:
+                       return NT_STATUS_NOT_IMPLEMENTED;
                case LIBNET_CHANGE_PASSWORD_RAP:
-                       return NT_STATUS_NOT_IMPLEMTED;
+                       return NT_STATUS_NOT_IMPLEMENTED;
+       }
+
+       return NT_STATUS_INVALID_LEVEL;
+}
+
+/*
+ * set a password with DCERPC/SAMR calls
+ */
+static NTSTATUS libnet_SetPassword_rpc(struct libnet_context *ctx, TALLOC_CTX *mem_ctx, union libnet_SetPassword *r)
+{
+       return NT_STATUS_NOT_IMPLEMENTED;
+}
+
+static NTSTATUS libnet_SetPassword_generic(struct libnet_context *ctx, TALLOC_CTX *mem_ctx, union libnet_SetPassword *r)
+{
+       return NT_STATUS_NOT_IMPLEMENTED;
+}
+
+NTSTATUS libnet_SetPassword(struct libnet_context *ctx, TALLOC_CTX *mem_ctx, union libnet_SetPassword *r)
+{
+       switch (r->generic.level) {
+               case LIBNET_SET_PASSWORD_GENERIC:
+                       return libnet_SetPassword_generic(ctx, mem_ctx, r);
+               case LIBNET_SET_PASSWORD_RPC:
+                       return libnet_SetPassword_rpc(ctx, mem_ctx, r);
+               case LIBNET_SET_PASSWORD_KRB5:
+                       return NT_STATUS_NOT_IMPLEMENTED;
+               case LIBNET_SET_PASSWORD_LDAP:
+                       return NT_STATUS_NOT_IMPLEMENTED;
+               case LIBNET_SET_PASSWORD_RAP:
+                       return NT_STATUS_NOT_IMPLEMENTED;
        }
 
        return NT_STATUS_INVALID_LEVEL;
diff --git a/source4/libnet/libnet_rpc.c b/source4/libnet/libnet_rpc.c
new file mode 100644 (file)
index 0000000..0ab07fa
--- /dev/null
@@ -0,0 +1,27 @@
+/* 
+   Unix SMB/CIFS implementation.
+   
+   Copyright (C) Stefan Metzmacher     2004
+   
+   This program is free software; you can redistribute it and/or modify
+   it under the terms of the GNU General Public License as published by
+   the Free Software Foundation; either version 2 of the License, or
+   (at your option) any later version.
+   
+   This program is distributed in the hope that it will be useful,
+   but WITHOUT ANY WARRANTY; without even the implied warranty of
+   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+   GNU General Public License for more details.
+   
+   You should have received a copy of the GNU General Public License
+   along with this program; if not, write to the Free Software
+   Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
+*/
+
+#include "includes.h"
+
+/* connect to a dcerpc interface */
+NTSTATUS libnet_rpc_connect(struct libnet_context *ctx, TALLOC_CTX *mem_ctx, union libnet_rpc_connect *r)
+{
+       return NT_STATUS_NOT_IMPLEMENTED;
+}