summaryrefslogtreecommitdiff
path: root/source4/auth
diff options
context:
space:
mode:
authorAndrew Bartlett <abartlet@samba.org>2005-11-07 02:29:37 +0000
committerGerald (Jerry) Carter <jerry@samba.org>2007-10-10 13:45:52 -0500
commit918c7634c21deb0aa89388bb3d9e147bfc8576c8 (patch)
tree4c56c62cda7f8f72f3eb808e26029c87f8479ef0 /source4/auth
parentf7ca7308490c5bb41c6e42e7fe52f6b2586d3d5d (diff)
downloadsamba-918c7634c21deb0aa89388bb3d9e147bfc8576c8.tar.gz
samba-918c7634c21deb0aa89388bb3d9e147bfc8576c8.tar.bz2
samba-918c7634c21deb0aa89388bb3d9e147bfc8576c8.zip
r11543: A major upgrade to our KDC and PAC handling.
We now put the PAC in the AS-REP, so that the client has it in the TGT. We then validate it (and re-sign it) on a TGS-REQ, ie when the client wants a ticket. This should also allow us to interop with windows KDCs. If we get an invalid PAC at the TGS stage, we just drop it. I'm slowly trying to move the application logic out of hdb-ldb.c, and back in with the rest of Samba's auth system, for consistancy. This continues that trend. Andrew Bartlett (This used to be commit 36973b1eef7db5983cce76ba241e54d5f925c69c)
Diffstat (limited to 'source4/auth')
-rw-r--r--source4/auth/auth_sam.c70
-rw-r--r--source4/auth/gensec/gensec_gssapi.c2
-rw-r--r--source4/auth/gensec/gensec_krb5.c2
-rw-r--r--source4/auth/kerberos/kerberos.h6
-rw-r--r--source4/auth/kerberos/kerberos_pac.c32
5 files changed, 67 insertions, 45 deletions
diff --git a/source4/auth/auth_sam.c b/source4/auth/auth_sam.c
index 58adb60a5f..56e61ea2a3 100644
--- a/source4/auth/auth_sam.c
+++ b/source4/auth/auth_sam.c
@@ -151,8 +151,8 @@ static NTSTATUS authsam_password_ok(struct auth_context *auth_context,
NTSTATUS authsam_account_ok(TALLOC_CTX *mem_ctx,
struct ldb_context *sam_ctx,
uint32_t logon_parameters,
- struct ldb_message **msgs,
- struct ldb_message **msgs_domain_ref,
+ struct ldb_message *msg,
+ struct ldb_message *msg_domain_ref,
const char *logon_workstation,
const char *name_for_logs)
{
@@ -162,20 +162,20 @@ NTSTATUS authsam_account_ok(TALLOC_CTX *mem_ctx,
NTTIME must_change_time;
NTTIME last_set_time;
- struct ldb_dn *domain_dn = samdb_result_dn(mem_ctx, msgs_domain_ref[0], "nCName", ldb_dn_new(mem_ctx));
+ struct ldb_dn *domain_dn = samdb_result_dn(mem_ctx, msg_domain_ref, "nCName", ldb_dn_new(mem_ctx));
NTTIME now;
DEBUG(4,("authsam_account_ok: Checking SMB password for user %s\n", name_for_logs));
- acct_flags = samdb_result_acct_flags(msgs[0], "userAccountControl");
+ acct_flags = samdb_result_acct_flags(msg, "userAccountControl");
- acct_expiry = samdb_result_nttime(msgs[0], "accountExpires", 0);
+ acct_expiry = samdb_result_nttime(msg, "accountExpires", 0);
must_change_time = samdb_result_force_password_change(sam_ctx, mem_ctx,
- domain_dn, msgs[0],
+ domain_dn, msg,
"pwdLastSet");
- last_set_time = samdb_result_nttime(msgs[0], "pwdLastSet", 0);
+ last_set_time = samdb_result_nttime(msg, "pwdLastSet", 0);
- workstation_list = samdb_result_string(msgs[0], "userWorkstations", NULL);
+ workstation_list = samdb_result_string(msg, "userWorkstations", NULL);
/* Quit if the account was disabled. */
if (acct_flags & ACB_DISABLED) {
@@ -412,17 +412,17 @@ static NTSTATUS authsam_authenticate(struct auth_context *auth_context,
nt_status = authsam_account_ok(mem_ctx, sam_ctx,
user_info->logon_parameters,
- msgs,
- msgs_domain_ref,
+ msgs[0],
+ msgs_domain_ref[0],
user_info->workstation_name,
user_info->mapped.account_name);
return nt_status;
}
-static NTSTATUS authsam_make_server_info(TALLOC_CTX *mem_ctx, struct ldb_context *sam_ctx,
- struct ldb_message **msgs,
- struct ldb_message **msgs_domain,
+NTSTATUS authsam_make_server_info(TALLOC_CTX *mem_ctx, struct ldb_context *sam_ctx,
+ struct ldb_message *msg,
+ struct ldb_message *msg_domain_ref,
DATA_BLOB user_sess_key, DATA_BLOB lm_sess_key,
struct auth_serversupplied_info **_server_info)
{
@@ -443,7 +443,7 @@ static NTSTATUS authsam_make_server_info(TALLOC_CTX *mem_ctx, struct ldb_context
group_ret = gendb_search(sam_ctx,
tmp_ctx, NULL, &group_msgs, group_attrs,
"(&(member=%s)(sAMAccountType=*))",
- ldb_dn_linearize(tmp_ctx, msgs[0]->dn));
+ ldb_dn_linearize(tmp_ctx, msg->dn));
if (group_ret == -1) {
talloc_free(tmp_ctx);
return NT_STATUS_INTERNAL_DB_CORRUPTION;
@@ -466,13 +466,13 @@ static NTSTATUS authsam_make_server_info(TALLOC_CTX *mem_ctx, struct ldb_context
talloc_free(tmp_ctx);
- account_sid = samdb_result_dom_sid(server_info, msgs[0], "objectSid");
+ account_sid = samdb_result_dom_sid(server_info, msg, "objectSid");
NT_STATUS_HAVE_NO_MEMORY(account_sid);
primary_group_sid = dom_sid_dup(server_info, account_sid);
NT_STATUS_HAVE_NO_MEMORY(primary_group_sid);
- rid = samdb_result_uint(msgs[0], "primaryGroupID", ~0);
+ rid = samdb_result_uint(msg, "primaryGroupID", ~0);
if (rid == ~0) {
if (group_ret > 0) {
primary_group_sid = groupSIDs[0];
@@ -489,49 +489,49 @@ static NTSTATUS authsam_make_server_info(TALLOC_CTX *mem_ctx, struct ldb_context
server_info->n_domain_groups = group_ret;
server_info->domain_groups = groupSIDs;
- server_info->account_name = talloc_steal(server_info, samdb_result_string(msgs[0], "sAMAccountName", NULL));
+ server_info->account_name = talloc_steal(server_info, samdb_result_string(msg, "sAMAccountName", NULL));
- server_info->domain_name = talloc_steal(server_info, samdb_result_string(msgs_domain[0], "nETBIOSName", NULL));
+ server_info->domain_name = talloc_steal(server_info, samdb_result_string(msg_domain_ref, "nETBIOSName", NULL));
- str = samdb_result_string(msgs[0], "displayName", "");
+ str = samdb_result_string(msg, "displayName", "");
server_info->full_name = talloc_strdup(server_info, str);
NT_STATUS_HAVE_NO_MEMORY(server_info->full_name);
- str = samdb_result_string(msgs[0], "scriptPath", "");
+ str = samdb_result_string(msg, "scriptPath", "");
server_info->logon_script = talloc_strdup(server_info, str);
NT_STATUS_HAVE_NO_MEMORY(server_info->logon_script);
- str = samdb_result_string(msgs[0], "profilePath", "");
+ str = samdb_result_string(msg, "profilePath", "");
server_info->profile_path = talloc_strdup(server_info, str);
NT_STATUS_HAVE_NO_MEMORY(server_info->profile_path);
- str = samdb_result_string(msgs[0], "homeDirectory", "");
+ str = samdb_result_string(msg, "homeDirectory", "");
server_info->home_directory = talloc_strdup(server_info, str);
NT_STATUS_HAVE_NO_MEMORY(server_info->home_directory);
- str = samdb_result_string(msgs[0], "homeDrive", "");
+ str = samdb_result_string(msg, "homeDrive", "");
server_info->home_drive = talloc_strdup(server_info, str);
NT_STATUS_HAVE_NO_MEMORY(server_info->home_drive);
server_info->logon_server = talloc_strdup(server_info, lp_netbios_name());
NT_STATUS_HAVE_NO_MEMORY(server_info->logon_server);
- server_info->last_logon = samdb_result_nttime(msgs[0], "lastLogon", 0);
- server_info->last_logoff = samdb_result_nttime(msgs[0], "lastLogoff", 0);
- server_info->acct_expiry = samdb_result_nttime(msgs[0], "accountExpires", 0);
- server_info->last_password_change = samdb_result_nttime(msgs[0], "pwdLastSet", 0);
+ server_info->last_logon = samdb_result_nttime(msg, "lastLogon", 0);
+ server_info->last_logoff = samdb_result_nttime(msg, "lastLogoff", 0);
+ server_info->acct_expiry = samdb_result_nttime(msg, "accountExpires", 0);
+ server_info->last_password_change = samdb_result_nttime(msg, "pwdLastSet", 0);
- ncname = samdb_result_dn(mem_ctx, msgs_domain[0], "nCName", ldb_dn_new(mem_ctx));
+ ncname = samdb_result_dn(mem_ctx, msg_domain_ref, "nCName", ldb_dn_new(mem_ctx));
server_info->allow_password_change = samdb_result_allow_password_change(sam_ctx, mem_ctx,
- ncname, msgs[0], "pwdLastSet");
+ ncname, msg, "pwdLastSet");
server_info->force_password_change = samdb_result_force_password_change(sam_ctx, mem_ctx,
- ncname, msgs[0], "pwdLastSet");
+ ncname, msg, "pwdLastSet");
- server_info->logon_count = samdb_result_uint(msgs[0], "logonCount", 0);
- server_info->bad_password_count = samdb_result_uint(msgs[0], "badPwdCount", 0);
+ server_info->logon_count = samdb_result_uint(msg, "logonCount", 0);
+ server_info->bad_password_count = samdb_result_uint(msg, "badPwdCount", 0);
- server_info->acct_flags = samdb_result_acct_flags(msgs[0], "userAccountControl");
+ server_info->acct_flags = samdb_result_acct_flags(msg, "userAccountControl");
server_info->user_session_key = user_sess_key;
server_info->lm_session_key = lm_sess_key;
@@ -614,7 +614,7 @@ NTSTATUS sam_get_server_info_principal(TALLOC_CTX *mem_ctx, const char *principa
return nt_status;
}
- nt_status = authsam_make_server_info(mem_ctx, sam_ctx, msgs, msgs_domain_ref,
+ nt_status = authsam_make_server_info(mem_ctx, sam_ctx, msgs[0], msgs_domain_ref[0],
user_sess_key, lm_sess_key,
server_info);
if (!NT_STATUS_IS_OK(nt_status)) {
@@ -654,7 +654,7 @@ static NTSTATUS authsam_check_password_internals(struct auth_method_context *ctx
&user_sess_key, &lm_sess_key);
NT_STATUS_NOT_OK_RETURN(nt_status);
- nt_status = authsam_make_server_info(mem_ctx, sam_ctx, msgs, domain_ref_msgs,
+ nt_status = authsam_make_server_info(mem_ctx, sam_ctx, msgs[0], domain_ref_msgs[0],
user_sess_key, lm_sess_key,
server_info);
NT_STATUS_NOT_OK_RETURN(nt_status);
diff --git a/source4/auth/gensec/gensec_gssapi.c b/source4/auth/gensec/gensec_gssapi.c
index 08e2298c1a..c8a57234e3 100644
--- a/source4/auth/gensec/gensec_gssapi.c
+++ b/source4/auth/gensec/gensec_gssapi.c
@@ -891,7 +891,7 @@ static NTSTATUS gensec_gssapi_session_info(struct gensec_security *gensec_securi
/* decode and verify the pac */
nt_status = kerberos_pac_logon_info(mem_ctx, &logon_info, pac_blob,
gensec_gssapi_state->smb_krb5_context->krb5_context,
- NULL, keyblock, principal, authtime);
+ NULL, keyblock, principal, authtime, NULL);
krb5_free_principal(gensec_gssapi_state->smb_krb5_context->krb5_context, principal);
if (NT_STATUS_IS_OK(nt_status)) {
diff --git a/source4/auth/gensec/gensec_krb5.c b/source4/auth/gensec/gensec_krb5.c
index d5a2fd9a8f..c8640dde8c 100644
--- a/source4/auth/gensec/gensec_krb5.c
+++ b/source4/auth/gensec/gensec_krb5.c
@@ -521,7 +521,7 @@ static NTSTATUS gensec_krb5_session_info(struct gensec_security *gensec_security
gensec_krb5_state->smb_krb5_context->krb5_context,
NULL, gensec_krb5_state->keyblock,
client_principal,
- gensec_krb5_state->ticket->ticket.authtime);
+ gensec_krb5_state->ticket->ticket.authtime, NULL);
krb5_free_principal(context, client_principal);
if (NT_STATUS_IS_OK(nt_status)) {
diff --git a/source4/auth/kerberos/kerberos.h b/source4/auth/kerberos/kerberos.h
index 9813290650..46bf300229 100644
--- a/source4/auth/kerberos/kerberos.h
+++ b/source4/auth/kerberos/kerberos.h
@@ -137,7 +137,8 @@ NTSTATUS kerberos_decode_pac(TALLOC_CTX *mem_ctx,
krb5_keyblock *krbtgt_keyblock,
krb5_keyblock *service_keyblock,
krb5_const_principal client_principal,
- time_t tgs_authtime);
+ time_t tgs_authtime,
+ krb5_error_code *k5ret);
NTSTATUS kerberos_pac_logon_info(TALLOC_CTX *mem_ctx,
struct PAC_LOGON_INFO **logon_info,
DATA_BLOB blob,
@@ -145,7 +146,8 @@ NTSTATUS kerberos_decode_pac(TALLOC_CTX *mem_ctx,
krb5_keyblock *krbtgt_keyblock,
krb5_keyblock *service_keyblock,
krb5_const_principal client_principal,
- time_t tgs_authtime);
+ time_t tgs_authtime,
+ krb5_error_code *k5ret);
krb5_error_code kerberos_encode_pac(TALLOC_CTX *mem_ctx,
struct PAC_DATA *pac_data,
krb5_context context,
diff --git a/source4/auth/kerberos/kerberos_pac.c b/source4/auth/kerberos/kerberos_pac.c
index 9be9df133a..55805f0c4a 100644
--- a/source4/auth/kerberos/kerberos_pac.c
+++ b/source4/auth/kerberos/kerberos_pac.c
@@ -74,7 +74,8 @@ static krb5_error_code check_pac_checksum(TALLOC_CTX *mem_ctx,
krb5_keyblock *krbtgt_keyblock,
krb5_keyblock *service_keyblock,
krb5_const_principal client_principal,
- time_t tgs_authtime)
+ time_t tgs_authtime,
+ krb5_error_code *k5ret)
{
krb5_error_code ret;
NTSTATUS status;
@@ -87,19 +88,28 @@ static krb5_error_code check_pac_checksum(TALLOC_CTX *mem_ctx,
struct PAC_DATA *pac_data;
struct PAC_DATA_RAW *pac_data_raw;
- DATA_BLOB *srv_sig_blob;
- DATA_BLOB *kdc_sig_blob;
+ DATA_BLOB *srv_sig_blob = NULL;
+ DATA_BLOB *kdc_sig_blob = NULL;
DATA_BLOB modified_pac_blob;
NTTIME tgs_authtime_nttime;
krb5_principal client_principal_pac;
int i;
+ krb5_clear_error_string(context);
+
+ if (k5ret) {
+ *k5ret = KRB5_PARSE_MALFORMED;
+ }
+
pac_data = talloc(mem_ctx, struct PAC_DATA);
pac_data_raw = talloc(mem_ctx, struct PAC_DATA_RAW);
kdc_sig_wipe = talloc(mem_ctx, struct PAC_SIGNATURE_DATA);
srv_sig_wipe = talloc(mem_ctx, struct PAC_SIGNATURE_DATA);
if (!pac_data_raw || !pac_data || !kdc_sig_wipe || !srv_sig_wipe) {
+ if (k5ret) {
+ *k5ret = ENOMEM;
+ }
return NT_STATUS_NO_MEMORY;
}
@@ -242,6 +252,9 @@ static krb5_error_code check_pac_checksum(TALLOC_CTX *mem_ctx,
if (ret) {
DEBUG(1, ("PAC Decode: Failed to verify the service signature: %s\n",
smb_get_krb5_error_message(context, ret, mem_ctx)));
+ if (k5ret) {
+ *k5ret = ret;
+ }
return NT_STATUS_ACCESS_DENIED;
}
@@ -252,6 +265,9 @@ static krb5_error_code check_pac_checksum(TALLOC_CTX *mem_ctx,
if (ret) {
DEBUG(1, ("PAC Decode: Failed to verify the KDC signature: %s\n",
smb_get_krb5_error_message(context, ret, mem_ctx)));
+ if (k5ret) {
+ *k5ret = ret;
+ }
return NT_STATUS_ACCESS_DENIED;
}
}
@@ -271,6 +287,9 @@ static krb5_error_code check_pac_checksum(TALLOC_CTX *mem_ctx,
DEBUG(2, ("Could not parse name from incoming PAC: [%s]: %s\n",
logon_name->account_name,
smb_get_krb5_error_message(context, ret, mem_ctx)));
+ if (k5ret) {
+ *k5ret = ret;
+ }
return NT_STATUS_INVALID_PARAMETER;
}
@@ -302,19 +321,20 @@ static krb5_error_code check_pac_checksum(TALLOC_CTX *mem_ctx,
krb5_keyblock *krbtgt_keyblock,
krb5_keyblock *service_keyblock,
krb5_const_principal client_principal,
- time_t tgs_authtime)
+ time_t tgs_authtime,
+ krb5_error_code *k5ret)
{
NTSTATUS nt_status;
struct PAC_DATA *pac_data;
int i;
-
nt_status = kerberos_decode_pac(mem_ctx, &pac_data,
blob,
context,
krbtgt_keyblock,
service_keyblock,
client_principal,
- tgs_authtime);
+ tgs_authtime,
+ k5ret);
if (!NT_STATUS_IS_OK(nt_status)) {
return nt_status;
}