From 0bf95ab57ba67d7a7f2cbb5cabf7be58e3b07361 Mon Sep 17 00:00:00 2001 From: Jeffrey Altman Date: Mon, 24 Jul 2006 15:11:30 +0000 Subject: [PATCH] STABLE14-windows-integrated-logon-20060724 * apply ACL restrictions to credential cache immediately after initialization * move file from system temp directory to user temp directory prior to starting executable as user to perform credential import (cherry picked from commit 1a0329fef030fedce3fb12d9c641825b0d49f053) --- src/WINNT/afsd/NTMakefile | 5 +- src/WINNT/afsd/afscpcc.c | 4 +- src/WINNT/afsd/afskfw-int.h | 5 +- src/WINNT/afsd/afskfw.c | 106 +++++++++++++++++++++++++++++- src/WINNT/afsd/afskfw.h | 7 +- src/WINNT/afsd/afslogon.c | 57 ++++++++++++---- src/WINNT/afsd/cm_memmap.c | 2 +- src/WINNT/afssvrmgr/NTMakefile | 3 +- src/WINNT/client_creds/NTMakefile | 5 +- 9 files changed, 169 insertions(+), 25 deletions(-) diff --git a/src/WINNT/afsd/NTMakefile b/src/WINNT/afsd/NTMakefile index 0c1b2a5d5..e7432e87f 100644 --- a/src/WINNT/afsd/NTMakefile +++ b/src/WINNT/afsd/NTMakefile @@ -239,7 +239,8 @@ LOGON_DLLSDKLIBS =\ ole32.lib \ adsiid.lib \ activeds.lib \ - userenv.lib + user32.lib \ + userenv.lib $(LOGON_DLLFILE): $(LOGON_DLLOBJS) $(LOGON_DLLLIBS) $(DLLGUILINK) $(LOGONLINKFLAGS) -def:afslogon.def $(LOGON_DLLSDKLIBS) @@ -360,7 +361,7 @@ $(EXEDIR)\unlog.exe: $(OUT)\cunlog.obj $(OUT)\unlog.res $(EXELIBS) # afscpcc.exe $(EXEDIR)\afscpcc.exe: $(OUT)\afscpcc.obj $(OUT)\afscpcc.res $(LOGON_DLLLIBS) - $(EXECONLINK) dnsapi.lib mpr.lib iphlpapi.lib + $(EXECONLINK) dnsapi.lib mpr.lib iphlpapi.lib userenv.lib $(EXEPREP) diff --git a/src/WINNT/afsd/afscpcc.c b/src/WINNT/afsd/afscpcc.c index 342ab6f5b..34c5e5284 100644 --- a/src/WINNT/afsd/afscpcc.c +++ b/src/WINNT/afsd/afscpcc.c @@ -1,5 +1,5 @@ /* - * Copyright 2005, Secure Endpoints Inc. + * Copyright 2005,2006 Secure Endpoints Inc. * All Rights Reserved. * * This software has been released under the terms of the MIT License. @@ -15,7 +15,7 @@ int main(int argc, char *argv[]) KFW_initialize(); - return KFW_AFS_copy_system_file_to_default_cache(argv[1]); + return KFW_AFS_copy_file_cache_to_default_cache(argv[1]); } diff --git a/src/WINNT/afsd/afskfw-int.h b/src/WINNT/afsd/afskfw-int.h index dba551d90..d787112fc 100644 --- a/src/WINNT/afsd/afskfw-int.h +++ b/src/WINNT/afsd/afskfw-int.h @@ -1,5 +1,6 @@ /* - * Copyright (c) 2003 SkyRope, LLC +* Copyright (c) 2004, 2005, 2006 Secure Endpoints Inc. +* Copyright (c) 2003 SkyRope, LLC * All rights reserved. * * Redistribution and use in source and binary forms, with or without @@ -103,6 +104,7 @@ typedef BOOL (WINAPI *FP_CloseServiceHandle)(SC_HANDLE); #define KRB5_DEFAULT_LIFE 60*60*10 /* 10 hours */ #define LSA_CCNAME "MSLSA:" +#ifndef KTC_ERROR #define KTC_ERROR 11862784L #define KTC_TOOBIG 11862785L #define KTC_INVAL 11862786L @@ -111,6 +113,7 @@ typedef BOOL (WINAPI *FP_CloseServiceHandle)(SC_HANDLE); #define KTC_NOPIOCTL 11862789L #define KTC_NOCELL 11862790L #define KTC_NOCM 11862791L +#endif /* User Query data structures and functions */ diff --git a/src/WINNT/afsd/afskfw.c b/src/WINNT/afsd/afskfw.c index 92bb4bdda..a7a8038ad 100644 --- a/src/WINNT/afsd/afskfw.c +++ b/src/WINNT/afsd/afskfw.c @@ -1,5 +1,5 @@ /* - * Copyright (c) 2004, 2005 Secure Endpoints Inc. + * Copyright (c) 2004, 2005, 2006 Secure Endpoints Inc. * Copyright (c) 2003 SkyRope, LLC * All rights reserved. * @@ -60,6 +60,9 @@ #undef USE_KRB4 #include "afskfw-int.h" #include "afskfw.h" +#include +#include +#include #include #include @@ -3491,6 +3494,103 @@ KFW_AFS_get_lsa_principal(char * szUser, DWORD *dwSize) return success; } +int +KFW_AFS_set_file_cache_dacl(char *filename, HANDLE hUserToken) +{ + // SID_IDENTIFIER_AUTHORITY authority = SECURITY_NT_SID_AUTHORITY; + PSID pSystemSID = NULL; + DWORD SystemSIDlength, UserSIDlength; + PACL ccacheACL = NULL; + DWORD ccacheACLlength; + PTOKEN_USER pTokenUser = NULL; + DWORD retLen; + int ret = 0; + + /* Get System SID */ + ConvertStringSidToSid(SDDL_LOCAL_SYSTEM, &pSystemSID); + + /* Create ACL */ + SystemSIDlength = GetLengthSid(pSystemSID); + ccacheACLlength = sizeof(ACL) + sizeof(ACCESS_ALLOWED_ACE) + + SystemSIDlength - sizeof(DWORD); + + if (hUserToken) { + if (!GetTokenInformation(hUserToken, TokenUser, NULL, 0, &retLen)) + { + if ( GetLastError() == ERROR_INSUFFICIENT_BUFFER ) { + pTokenUser = (PTOKEN_USER) LocalAlloc(LPTR, retLen); + + GetTokenInformation(hUserToken, TokenUser, pTokenUser, retLen, &retLen); + } + } + + if (pTokenUser) { + UserSIDlength = GetLengthSid(pTokenUser->User.Sid); + + ccacheACLlength += sizeof(ACCESS_ALLOWED_ACE) + UserSIDlength + - sizeof(DWORD); + } + } + + ccacheACL = GlobalAlloc(GMEM_FIXED, ccacheACLlength); + InitializeAcl(ccacheACL, ccacheACLlength, ACL_REVISION); + AddAccessAllowedAceEx(ccacheACL, ACL_REVISION, 0, + STANDARD_RIGHTS_ALL | SPECIFIC_RIGHTS_ALL, + pSystemSID); + if (pTokenUser) { + AddAccessAllowedAceEx(ccacheACL, ACL_REVISION, 0, + STANDARD_RIGHTS_ALL | SPECIFIC_RIGHTS_ALL, + pTokenUser->User.Sid); + if (!SetNamedSecurityInfo( filename, SE_FILE_OBJECT, + DACL_SECURITY_INFORMATION | PROTECTED_DACL_SECURITY_INFORMATION, + NULL, + NULL, + ccacheACL, + NULL)) { + ret = 1; + } + if (!SetNamedSecurityInfo( filename, SE_FILE_OBJECT, + OWNER_SECURITY_INFORMATION, + pTokenUser->User.Sid, + NULL, + NULL, + NULL)) { + ret = 1; + } + } else { + if (!SetNamedSecurityInfo( filename, SE_FILE_OBJECT, + DACL_SECURITY_INFORMATION | PROTECTED_DACL_SECURITY_INFORMATION, + NULL, + NULL, + ccacheACL, + NULL)) { + ret = 1; + } + } + + if (pSystemSID) + LocalFree(pSystemSID); + if (pTokenUser) + LocalFree(pTokenUser); + if (ccacheACL) + GlobalFree(ccacheACL); + return ret; +} + +int +KFW_AFS_obtain_user_temp_directory(HANDLE hUserToken, char *newfilename, int size) +{ + int retval = 0; + DWORD dwSize = size-1; /* leave room for nul */ + + *newfilename = '\0'; + + if ( !ExpandEnvironmentStringsForUser(hUserToken, "%TEMP%", newfilename, size) && + !ExpandEnvironmentStringsForUser(hUserToken, "%TMP%", newfilename, size)) + return 1; + return 0; +} + void KFW_AFS_copy_cache_to_system_file(char * user, char * szLogonId) { @@ -3536,6 +3636,8 @@ KFW_AFS_copy_cache_to_system_file(char * user, char * szLogonId) code = pkrb5_cc_initialize(ctx, ncc, princ); if (code) goto cleanup; + KFW_AFS_set_file_cache_dacl(filename, NULL); + code = pkrb5_cc_copy_creds(ctx,cc,ncc); cleanup: @@ -3557,7 +3659,7 @@ KFW_AFS_copy_cache_to_system_file(char * user, char * szLogonId) } int -KFW_AFS_copy_system_file_to_default_cache(char * filename) +KFW_AFS_copy_file_cache_to_default_cache(char * filename) { DWORD count; char cachename[264] = "FILE:"; diff --git a/src/WINNT/afsd/afskfw.h b/src/WINNT/afsd/afskfw.h index 498b9f29a..d77492452 100644 --- a/src/WINNT/afsd/afskfw.h +++ b/src/WINNT/afsd/afskfw.h @@ -1,5 +1,6 @@ /* - * Copyright (c) 2003 SkyRope, LLC +* Copyright (c) 2004, 2005, 2006 Secure Endpoints Inc. +* Copyright (c) 2003 SkyRope, LLC * All rights reserved. * * Redistribution and use in source and binary forms, with or without @@ -62,6 +63,10 @@ BOOL KFW_probe_kdc(struct afsconf_cell *); int KFW_AFS_get_cellconfig(char *, struct afsconf_cell *, char *); void KFW_import_windows_lsa(void); BOOL KFW_AFS_get_lsa_principal(char *, DWORD *); +int KFW_AFS_set_file_cache_dacl(char *filename, HANDLE hUserToken); +int KFW_AFS_obtain_user_temp_directory(HANDLE hUserToken, char *newfilename, int size); +int KFW_AFS_copy_file_cache_to_default_cache(char * filename); + /* These functions are only to be used in the afslogon.dll */ void KFW_AFS_copy_cache_to_system_file(char *, char *); diff --git a/src/WINNT/afsd/afslogon.c b/src/WINNT/afsd/afslogon.c index 48f6022ff..d03dc73ce 100644 --- a/src/WINNT/afsd/afslogon.c +++ b/src/WINNT/afsd/afslogon.c @@ -1296,8 +1296,9 @@ VOID KFW_Logon_Event( PWLX_NOTIFICATION_INFO pInfo ) char szPath[MAX_PATH] = ""; char szLogonId[128] = ""; DWORD count; - char filename[256]; - char commandline[512]; + char filename[MAX_PATH]; + char newfilename[MAX_PATH]; + char commandline[MAX_PATH+256]; STARTUPINFO startupinfo; PROCESS_INFORMATION procinfo; @@ -1329,14 +1330,41 @@ VOID KFW_Logon_Event( PWLX_NOTIFICATION_INFO pInfo ) GetWindowsDirectory(filename, sizeof(filename)); } - if ( strlen(filename) + strlen(szLogonId) + 2 <= sizeof(filename) ) { - strcat(filename, "\\"); - strcat(filename, szLogonId); + count = GetEnvironmentVariable("TEMP", filename, sizeof(filename)); + if ( count > sizeof(filename) || count == 0 ) { + GetWindowsDirectory(filename, sizeof(filename)); + } + + if ( strlen(filename) + strlen(szLogonId) + 2 > sizeof(filename) ) { + DebugEvent0("KFW_Logon_Event - filename too long"); + return; + } + + strcat(filename, "\\"); + strcat(filename, szLogonId); + + KFW_AFS_set_file_cache_dacl(filename, pInfo->hToken); - sprintf(commandline, "afscpcc.exe \"%s\"", filename); + KFW_AFS_obtain_user_temp_directory(pInfo->hToken, newfilename, sizeof(newfilename)); + + if ( strlen(newfilename) + strlen(szLogonId) + 2 > sizeof(newfilename) ) { + DebugEvent0("KFW_Logon_Event - new filename too long"); + return; + } - GetStartupInfo(&startupinfo); - if (CreateProcessAsUser( pInfo->hToken, + strcat(newfilename, "\\"); + strcat(newfilename, szLogonId); + + if (!MoveFileEx(filename, newfilename, + MOVEFILE_COPY_ALLOWED | MOVEFILE_REPLACE_EXISTING | MOVEFILE_WRITE_THROUGH)) { + DebugEvent("KFW_Logon_Event - MoveFileEx failed GLE = 0x%x", GetLastError()); + return; + } + + sprintf(commandline, "afscpcc.exe \"%s\"", newfilename); + + GetStartupInfo(&startupinfo); + if (CreateProcessAsUser( pInfo->hToken, "afscpcc.exe", commandline, NULL, @@ -1347,12 +1375,15 @@ VOID KFW_Logon_Event( PWLX_NOTIFICATION_INFO pInfo ) NULL, &startupinfo, &procinfo)) - { - WaitForSingleObject(procinfo.hProcess, 30000); + { + DebugEvent("KFW_Logon_Event - CommandLine %s", commandline); - CloseHandle(procinfo.hThread); - CloseHandle(procinfo.hProcess); - } + WaitForSingleObject(procinfo.hProcess, 30000); + + CloseHandle(procinfo.hThread); + CloseHandle(procinfo.hProcess); + } else { + DebugEvent0("KFW_Logon_Event - CreateProcessFailed"); } DeleteFile(filename); diff --git a/src/WINNT/afsd/cm_memmap.c b/src/WINNT/afsd/cm_memmap.c index c7f8d7233..b7175fe6d 100644 --- a/src/WINNT/afsd/cm_memmap.c +++ b/src/WINNT/afsd/cm_memmap.c @@ -161,7 +161,7 @@ PSECURITY_ATTRIBUTES CreateCacheFileSA() psa = GlobalAlloc(GMEM_FIXED, sizeof(SECURITY_ATTRIBUTES)); psa->nLength = sizeof(SECURITY_ATTRIBUTES); psa->lpSecurityDescriptor = psd; - psa->bInheritHandle = TRUE; + psa->bInheritHandle = FALSE; return psa; } diff --git a/src/WINNT/afssvrmgr/NTMakefile b/src/WINNT/afssvrmgr/NTMakefile index cbe226b56..de90febaa 100644 --- a/src/WINNT/afssvrmgr/NTMakefile +++ b/src/WINNT/afssvrmgr/NTMakefile @@ -90,7 +90,8 @@ EXEOBJS = \ VCLIBS =\ comctl32.lib \ - shell32.lib + shell32.lib \ + userenv.lib EXELIBS = \ $(DESTDIR)\lib\afsauthent.lib \ diff --git a/src/WINNT/client_creds/NTMakefile b/src/WINNT/client_creds/NTMakefile index 40033383b..2127e6819 100644 --- a/src/WINNT/client_creds/NTMakefile +++ b/src/WINNT/client_creds/NTMakefile @@ -53,13 +53,14 @@ CLIENTOBJS = \ $(OUT)\RegistrySupport.obj VCLIBS =\ - iphlpapi.lib \ + iphlpapi.lib \ comctl32.lib \ shell32.lib \ uuid.lib \ ole32.lib \ mpr.lib \ - netapi32.lib + userenv.lib \ + netapi32.lib EXELIBS = \ $(DESTDIR)\lib\afs\afspioctl.lib \ -- 2.39.5