From 26feb73fcf4482c7511219064db2ab0d93f7e9ed Mon Sep 17 00:00:00 2001 From: Jeremy Allison Date: Thu, 11 Jun 2015 18:16:01 +0100 Subject: [PATCH 1/7] s3: auth: Add some const to the struct netr_SamInfo3 * arguments of copy_netr_SamInfo3() and make_server_info_info3() Both functions only read from the struct netr_SamInfo3 * argument. Signed-off-by: Jeremy Allison Reviewed-by: Richard Sharpe Reviewed-by: Simo Sorce (cherry picked from commit c2411767adb5ce48a4619349075f6f8faae41aab) Conflicts: source3/auth/proto.h source3/auth/server_info.c --- source3/auth/auth_util.c | 2 +- source3/auth/proto.h | 4 ++-- source3/auth/server_info.c | 2 +- 3 files changed, 4 insertions(+), 4 deletions(-) diff --git a/source3/auth/auth_util.c b/source3/auth/auth_util.c index ceaa706..afa78ec 100644 --- a/source3/auth/auth_util.c +++ b/source3/auth/auth_util.c @@ -1369,7 +1369,7 @@ NTSTATUS make_server_info_info3(TALLOC_CTX *mem_ctx, const char *sent_nt_username, const char *domain, struct auth_serversupplied_info **server_info, - struct netr_SamInfo3 *info3) + const struct netr_SamInfo3 *info3) { static const char zeros[16] = {0, }; diff --git a/source3/auth/proto.h b/source3/auth/proto.h index 76661fc..6ec206e 100644 --- a/source3/auth/proto.h +++ b/source3/auth/proto.h @@ -232,7 +232,7 @@ NTSTATUS make_server_info_info3(TALLOC_CTX *mem_ctx, const char *sent_nt_username, const char *domain, struct auth_serversupplied_info **server_info, - struct netr_SamInfo3 *info3); + const struct netr_SamInfo3 *info3); struct wbcAuthUserInfo; NTSTATUS make_server_info_wbcAuthUserInfo(TALLOC_CTX *mem_ctx, const char *sent_nt_username, @@ -287,7 +287,7 @@ NTSTATUS samu_to_SamInfo3(TALLOC_CTX *mem_ctx, struct netr_SamInfo3 **_info3, struct extra_auth_info *extra); struct netr_SamInfo3 *copy_netr_SamInfo3(TALLOC_CTX *mem_ctx, - struct netr_SamInfo3 *orig); + const struct netr_SamInfo3 *orig); struct netr_SamInfo3 *wbcAuthUserInfo_to_netr_SamInfo3(TALLOC_CTX *mem_ctx, const struct wbcAuthUserInfo *info); diff --git a/source3/auth/server_info.c b/source3/auth/server_info.c index d2b7d6e..066b9a8 100644 --- a/source3/auth/server_info.c +++ b/source3/auth/server_info.c @@ -445,7 +445,7 @@ NTSTATUS samu_to_SamInfo3(TALLOC_CTX *mem_ctx, } } while(0) struct netr_SamInfo3 *copy_netr_SamInfo3(TALLOC_CTX *mem_ctx, - struct netr_SamInfo3 *orig) + const struct netr_SamInfo3 *orig) { struct netr_SamInfo3 *info3; unsigned int i; -- 2.1.4 From df68261466f0ed23b9d89a6d5af8d0ba3ad9e794 Mon Sep 17 00:00:00 2001 From: Jeremy Allison Date: Mon, 16 Jun 2014 22:54:45 -0700 Subject: [PATCH 2/7] s3: auth: Change make_server_info_info3() to take a const struct netr_SamInfo3 pointer instead of a struct PAC_LOGON_INFO. make_server_info_info3() only reads from the info3 pointer. Signed-off-by: Jeremy Allison Reviewed-by: Richard Sharpe Reviewed-by: Simo Sorce (cherry picked from commit 527f7b54388713acaaf7b66c718cc0f7114fc368) --- source3/auth/auth_generic.c | 2 +- source3/auth/proto.h | 2 +- source3/auth/user_krb5.c | 8 ++++---- 3 files changed, 6 insertions(+), 6 deletions(-) diff --git a/source3/auth/auth_generic.c b/source3/auth/auth_generic.c index a2ba4e3..2880bc9 100644 --- a/source3/auth/auth_generic.c +++ b/source3/auth/auth_generic.c @@ -112,7 +112,7 @@ static NTSTATUS auth3_generate_session_info_pac(struct auth4_context *auth_ctx, status = make_session_info_krb5(mem_ctx, ntuser, ntdomain, username, pw, - logon_info, is_guest, is_mapped, NULL /* No session key for now, caller will sort it out */, + &logon_info->info3, is_guest, is_mapped, NULL /* No session key for now, caller will sort it out */, session_info); if (!NT_STATUS_IS_OK(status)) { DEBUG(1, ("Failed to map kerberos pac to server info (%s)\n", diff --git a/source3/auth/proto.h b/source3/auth/proto.h index 6ec206e..75d1097 100644 --- a/source3/auth/proto.h +++ b/source3/auth/proto.h @@ -357,7 +357,7 @@ NTSTATUS make_session_info_krb5(TALLOC_CTX *mem_ctx, char *ntdomain, char *username, struct passwd *pw, - struct PAC_LOGON_INFO *logon_info, + const struct netr_SamInfo3 *info3, bool mapped_to_guest, bool username_was_mapped, DATA_BLOB *session_key, struct auth_session_info **session_info); diff --git a/source3/auth/user_krb5.c b/source3/auth/user_krb5.c index 974a8aa..0a538b4 100644 --- a/source3/auth/user_krb5.c +++ b/source3/auth/user_krb5.c @@ -186,7 +186,7 @@ NTSTATUS make_session_info_krb5(TALLOC_CTX *mem_ctx, char *ntdomain, char *username, struct passwd *pw, - struct PAC_LOGON_INFO *logon_info, + const struct netr_SamInfo3 *info3, bool mapped_to_guest, bool username_was_mapped, DATA_BLOB *session_key, struct auth_session_info **session_info) @@ -202,14 +202,14 @@ NTSTATUS make_session_info_krb5(TALLOC_CTX *mem_ctx, return status; } - } else if (logon_info) { + } else if (info3) { /* pass the unmapped username here since map_username() will be called again in make_server_info_info3() */ status = make_server_info_info3(mem_ctx, ntuser, ntdomain, &server_info, - &logon_info->info3); + info3); if (!NT_STATUS_IS_OK(status)) { DEBUG(1, ("make_server_info_info3 failed: %s!\n", nt_errstr(status))); @@ -299,7 +299,7 @@ NTSTATUS make_session_info_krb5(TALLOC_CTX *mem_ctx, char *ntdomain, char *username, struct passwd *pw, - struct PAC_LOGON_INFO *logon_info, + const struct netr_SamInfo3 *info3, bool mapped_to_guest, bool username_was_mapped, DATA_BLOB *session_key, struct auth_session_info **session_info) -- 2.1.4 From b89662f447d1db771be1be326a1eb2dbff268fcd Mon Sep 17 00:00:00 2001 From: Jeremy Allison Date: Mon, 16 Jun 2014 23:11:58 -0700 Subject: [PATCH 3/7] s3: auth: Add create_info3_from_pac_logon_info() to create a new info3 and merge resource group SIDs into it. Originally written by Richard Sharpe Richard Sharpe . Signed-off-by: Jeremy Allison Reviewed-by: Richard Sharpe Reviewed-by: Simo Sorce (cherry picked from commit db775c68ccbed0252abf092b5cb811e8f5fa9bb6) --- source3/auth/proto.h | 3 ++ source3/auth/server_info.c | 77 ++++++++++++++++++++++++++++++++++++++++++++++ 2 files changed, 80 insertions(+) diff --git a/source3/auth/proto.h b/source3/auth/proto.h index 75d1097..cc51698 100644 --- a/source3/auth/proto.h +++ b/source3/auth/proto.h @@ -281,6 +281,9 @@ NTSTATUS serverinfo_to_SamInfo3(const struct auth_serversupplied_info *server_in struct netr_SamInfo3 *sam3); NTSTATUS serverinfo_to_SamInfo6(struct auth_serversupplied_info *server_info, struct netr_SamInfo6 *sam6); +NTSTATUS create_info3_from_pac_logon_info(TALLOC_CTX *mem_ctx, + const struct PAC_LOGON_INFO *logon_info, + struct netr_SamInfo3 **pp_info3); NTSTATUS samu_to_SamInfo3(TALLOC_CTX *mem_ctx, struct samu *samu, const char *login_server, diff --git a/source3/auth/server_info.c b/source3/auth/server_info.c index 066b9a8..dc84794 100644 --- a/source3/auth/server_info.c +++ b/source3/auth/server_info.c @@ -252,6 +252,83 @@ static NTSTATUS group_sids_to_info3(struct netr_SamInfo3 *info3, return NT_STATUS_OK; } +/* + * Merge resource SIDs, if any, into the passed in info3 structure. + */ + +static NTSTATUS merge_resource_sids(const struct PAC_LOGON_INFO *logon_info, + struct netr_SamInfo3 *info3) +{ + uint32_t i = 0; + + if (!(logon_info->info3.base.user_flags & NETLOGON_RESOURCE_GROUPS)) { + return NT_STATUS_OK; + } + + /* + * If there are any resource groups (SID Compression) add + * them to the extra sids portion of the info3 in the PAC. + * + * This makes the info3 look like it would if we got the info + * from the DC rather than the PAC. + */ + + /* + * Construct a SID for each RID in the list and then append it + * to the info3. + */ + for (i = 0; i < logon_info->res_groups.count; i++) { + NTSTATUS status; + struct dom_sid new_sid; + uint32_t attributes = logon_info->res_groups.rids[i].attributes; + + sid_compose(&new_sid, + logon_info->res_group_dom_sid, + logon_info->res_groups.rids[i].rid); + + DEBUG(10, ("Adding SID %s to extra SIDS\n", + sid_string_dbg(&new_sid))); + + status = append_netr_SidAttr(info3, &info3->sids, + &info3->sidcount, + &new_sid, + attributes); + if (!NT_STATUS_IS_OK(status)) { + DEBUG(1, ("failed to append SID %s to extra SIDS: %s\n", + sid_string_dbg(&new_sid), + nt_errstr(status))); + return status; + } + } + + return NT_STATUS_OK; +} + +/* + * Create a copy of an info3 struct from the struct PAC_LOGON_INFO, + * then merge resource SIDs, if any, into it. If successful return + * the created info3 struct. + */ + +NTSTATUS create_info3_from_pac_logon_info(TALLOC_CTX *mem_ctx, + const struct PAC_LOGON_INFO *logon_info, + struct netr_SamInfo3 **pp_info3) +{ + NTSTATUS status; + struct netr_SamInfo3 *info3 = copy_netr_SamInfo3(mem_ctx, + &logon_info->info3); + if (info3 == NULL) { + return NT_STATUS_NO_MEMORY; + } + status = merge_resource_sids(logon_info, info3); + if (!NT_STATUS_IS_OK(status)) { + TALLOC_FREE(info3); + return status; + } + *pp_info3 = info3; + return NT_STATUS_OK; +} + #define RET_NOMEM(ptr) do { \ if (!ptr) { \ TALLOC_FREE(info3); \ -- 2.1.4 From 98471f3a6947e951a215b6ed6def9a6e58899941 Mon Sep 17 00:00:00 2001 From: Jeremy Allison Date: Mon, 16 Jun 2014 23:15:21 -0700 Subject: [PATCH 4/7] s3: auth: Change auth3_generate_session_info_pac() to use a copy of the info3 struct from the struct PAC_LOGON_INFO. Call create_info3_from_pac_logon_info() to add in any resource SIDs from the struct PAC_LOGON_INFO to the info3. Signed-off-by: Jeremy Allison Reviewed-by: Richard Sharpe Reviewed-by: Simo Sorce (cherry picked from commit 0e5a9f44e4b08b93bc4b501d1e14b59ed7b3647c) --- source3/auth/auth_generic.c | 11 +++++++++-- 1 file changed, 9 insertions(+), 2 deletions(-) diff --git a/source3/auth/auth_generic.c b/source3/auth/auth_generic.c index 2880bc9..f841f0c 100644 --- a/source3/auth/auth_generic.c +++ b/source3/auth/auth_generic.c @@ -44,6 +44,7 @@ static NTSTATUS auth3_generate_session_info_pac(struct auth4_context *auth_ctx, { TALLOC_CTX *tmp_ctx; struct PAC_LOGON_INFO *logon_info = NULL; + struct netr_SamInfo3 *info3_copy = NULL; bool is_mapped; bool is_guest; char *ntuser; @@ -101,7 +102,13 @@ static NTSTATUS auth3_generate_session_info_pac(struct auth4_context *auth_ctx, /* save the PAC data if we have it */ if (logon_info) { - netsamlogon_cache_store(ntuser, &logon_info->info3); + status = create_info3_from_pac_logon_info(tmp_ctx, + logon_info, + &info3_copy); + if (!NT_STATUS_IS_OK(status)) { + goto done; + } + netsamlogon_cache_store(ntuser, info3_copy); } /* setup the string used by %U */ @@ -112,7 +119,7 @@ static NTSTATUS auth3_generate_session_info_pac(struct auth4_context *auth_ctx, status = make_session_info_krb5(mem_ctx, ntuser, ntdomain, username, pw, - &logon_info->info3, is_guest, is_mapped, NULL /* No session key for now, caller will sort it out */, + info3_copy, is_guest, is_mapped, NULL /* No session key for now, caller will sort it out */, session_info); if (!NT_STATUS_IS_OK(status)) { DEBUG(1, ("Failed to map kerberos pac to server info (%s)\n", -- 2.1.4 From 920628819127ce1e59ecef2bc50276e898f24888 Mon Sep 17 00:00:00 2001 From: Jeremy Allison Date: Mon, 16 Jun 2014 23:27:35 -0700 Subject: [PATCH 5/7] s3: auth: Fix winbindd_pam_auth_pac_send() to create a new info3 and merge in resource groups from a trusted PAC. Based on a patch from Richard Sharpe . Signed-off-by: Jeremy Allison Reviewed-by: Richard Sharpe Reviewed-by: Simo Sorce Autobuild-User(master): Jeremy Allison Autobuild-Date(master): Wed Jun 18 03:30:36 CEST 2014 on sn-devel-104 (cherry picked from commit e907f8415639d2a7cbc1cc2e40e2e35bfa0024de) --- source3/winbindd/winbindd_pam.c | 24 ++++++++++++++++++++++-- 1 file changed, 22 insertions(+), 2 deletions(-) diff --git a/source3/winbindd/winbindd_pam.c b/source3/winbindd/winbindd_pam.c index c356686..0f1ca28 100644 --- a/source3/winbindd/winbindd_pam.c +++ b/source3/winbindd/winbindd_pam.c @@ -2421,6 +2421,7 @@ NTSTATUS winbindd_pam_auth_pac_send(struct winbindd_cli_state *state, struct winbindd_request *req = state->request; DATA_BLOB pac_blob; struct PAC_LOGON_INFO *logon_info = NULL; + struct netr_SamInfo3 *info3_copy = NULL; NTSTATUS result; pac_blob = data_blob_const(req->extra_data.data, req->extra_len); @@ -2434,7 +2435,13 @@ NTSTATUS winbindd_pam_auth_pac_send(struct winbindd_cli_state *state, if (logon_info) { /* Signature verification succeeded, trust the PAC */ - netsamlogon_cache_store(NULL, &logon_info->info3); + result = create_info3_from_pac_logon_info(state->mem_ctx, + logon_info, + &info3_copy); + if (!NT_STATUS_IS_OK(result)) { + return result; + } + netsamlogon_cache_store(NULL, info3_copy); } else { /* Try without signature verification */ @@ -2446,9 +2453,22 @@ NTSTATUS winbindd_pam_auth_pac_send(struct winbindd_cli_state *state, nt_errstr(result))); return result; } + if (logon_info) { + /* + * Don't strictly need to copy here, + * but it makes it explicit we're + * returning a copy talloc'ed off + * the state->mem_ctx. + */ + info3_copy = copy_netr_SamInfo3(state->mem_ctx, + &logon_info->info3); + if (info3_copy == NULL) { + return NT_STATUS_NO_MEMORY; + } + } } - *info3 = &logon_info->info3; + *info3 = info3_copy; return NT_STATUS_OK; } -- 2.1.4 From 7cdff6ec40de1eeaaa97d3aaf315cf806e0557d2 Mon Sep 17 00:00:00 2001 From: Noel Power Date: Wed, 10 Jun 2015 13:13:25 +0100 Subject: [PATCH 6/7] kerberos auth info3 should contain resource group ids available from pac_logon successful pam auth (e.g. from ssh) will cache group sids (but not any resource group sids)) The subsequent cached entry used for groups lookups can be missing those resource groups Signed-off-by: Noel Power Reviewed-by: Jeremy Allison Reviewed-by: Andrew Bartlett (cherry picked from commit efadcb31215f9ccaf7942341c698a8eb2ac166ce) Conflicts: source3/winbindd/winbindd_pam.c --- source3/winbindd/winbindd_pam.c | 10 +++++++--- 1 file changed, 7 insertions(+), 3 deletions(-) diff --git a/source3/winbindd/winbindd_pam.c b/source3/winbindd/winbindd_pam.c index 0f1ca28..272663b 100644 --- a/source3/winbindd/winbindd_pam.c +++ b/source3/winbindd/winbindd_pam.c @@ -576,6 +576,7 @@ static NTSTATUS winbindd_raw_kerberos_login(TALLOC_CTX *mem_ctx, time_t time_offset = 0; const char *user_ccache_file; struct PAC_LOGON_INFO *logon_info = NULL; + struct netr_SamInfo3 *info3_copy = NULL; *info3 = NULL; @@ -664,11 +665,14 @@ static NTSTATUS winbindd_raw_kerberos_login(TALLOC_CTX *mem_ctx, goto failed; } - *info3 = &logon_info->info3; - DEBUG(10,("winbindd_raw_kerberos_login: winbindd validated ticket of %s\n", principal_s)); + result = create_info3_from_pac_logon_info(mem_ctx, logon_info, &info3_copy); + if (!NT_STATUS_IS_OK(result)) { + goto failed; + } + /* if we had a user's ccache then return that string for the pam * environment */ @@ -704,7 +708,7 @@ static NTSTATUS winbindd_raw_kerberos_login(TALLOC_CTX *mem_ctx, } } - + *info3 = info3_copy; return NT_STATUS_OK; failed: -- 2.1.4 From d547fbb5224a157a40b0018c9027be63521c0b57 Mon Sep 17 00:00:00 2001 From: Jeremy Allison Date: Wed, 10 Jun 2015 16:31:21 -0700 Subject: [PATCH 7/7] winbindd: winbindd_raw_kerberos_login - ensure logon_info exists in PAC. Signed-off-by: Jeremy Allison Reviewed-by: Andrew Bartlett Autobuild-User(master): Andrew Bartlett Autobuild-Date(master): Thu Jun 11 07:30:38 CEST 2015 on sn-devel-104 (cherry picked from commit 4c5fefe0723ae4cd3cacaabc5ae4c500d2306968) Conflicts: source3/winbindd/winbindd_pam.c --- source3/winbindd/winbindd_pam.c | 6 ++++++ 1 file changed, 6 insertions(+) diff --git a/source3/winbindd/winbindd_pam.c b/source3/winbindd/winbindd_pam.c index 272663b..3fb88d6 100644 --- a/source3/winbindd/winbindd_pam.c +++ b/source3/winbindd/winbindd_pam.c @@ -665,6 +665,12 @@ static NTSTATUS winbindd_raw_kerberos_login(TALLOC_CTX *mem_ctx, goto failed; } + if (logon_info == NULL) { + DEBUG(10,("Missing logon_info in ticket of %s\n", + principal_s)); + return NT_STATUS_INVALID_PARAMETER; + } + DEBUG(10,("winbindd_raw_kerberos_login: winbindd validated ticket of %s\n", principal_s)); -- 2.1.4