Index: fileio.c
===================================================================
RCS file: /pack/xemacscvs/XEmacs/xemacs/src/fileio.c,v
retrieving revision 1.66.2.7
diff -u -r1.66.2.7 fileio.c
--- fileio.c 2005/01/31 02:55:14 1.66.2.7
+++ fileio.c 2006/11/18 21:12:37
@@ -57,6 +57,7 @@
#define WIN32_FILENAMES
#ifdef WIN32_NATIVE
#include "nt.h"
+#include <aclapi.h>
#endif /* WIN32_NATIVE */
#define IS_DRIVE(x) isalpha (x)
/* Need to lower-case the drive letter, or else expanded
@@ -2272,6 +2273,66 @@
static int
check_writable (const char *filename)
{
+#ifdef WIN32_NATIVE
+ // Since this has to work for a directory, we can't just call
'CreateFile'
+ PSECURITY_DESCRIPTOR pDesc; /* Must be freed with LocalFree */
+ /* these need not be freed, they point into pDesc */
+ PSID psidOwner;
+ PSID psidGroup;
+ PACL pDacl;
+ PACL pSacl;
+ /* end of insides of descriptor */
+ DWORD error;
+ DWORD attributes;
+ HANDLE tokenHandle;
+ GENERIC_MAPPING genericMapping;
+ DWORD accessMask;
+ PRIVILEGE_SET PrivilegeSet;
+ DWORD dwPrivSetSize = sizeof( PRIVILEGE_SET );
+ BOOL fAccessGranted = FALSE;
+ DWORD dwAccessAllowed;
+
+ /* Win32 prototype lacks const. */
+ error = GetNamedSecurityInfo((LPTSTR)filename, SE_FILE_OBJECT,
+
DACL_SECURITY_INFORMATION|GROUP_SECURITY_INFORMATION|OWNER_SECURITY_INFO
RMATION,
+ &psidOwner, &psidGroup, &pDacl, &pSacl, &pDesc);
+ if(error != ERROR_SUCCESS) { // FAT?
+ attributes = GetFileAttributes(filename);
+ return (attributes & FILE_ATTRIBUTE_DIRECTORY) || (0 ==
(attributes & FILE_ATTRIBUTE_READONLY));
+ }
+
+ genericMapping.GenericRead = FILE_GENERIC_READ;
+ genericMapping.GenericWrite = FILE_GENERIC_WRITE;
+ genericMapping.GenericExecute = FILE_GENERIC_EXECUTE;
+ genericMapping.GenericAll = FILE_ALL_ACCESS;
+
+ if(!ImpersonateSelf(SecurityDelegation)) {
+ return 0;
+ }
+ if(!OpenThreadToken(GetCurrentThread(), TOKEN_ALL_ACCESS, TRUE,
&tokenHandle)) {
+ return 0;
+ }
+
+ accessMask = GENERIC_WRITE;
+ MapGenericMask(&accessMask, &genericMapping);
+
+ if(!AccessCheck(pDesc, tokenHandle, accessMask, &genericMapping,
+ &PrivilegeSet, // receives
privileges used in check
+ &dwPrivSetSize, // size of
PrivilegeSet buffer
+ &dwAccessAllowed, // receives
mask of allowed access rights
+ &fAccessGranted))
+ {
+ DWORD oops = GetLastError();
+ CloseHandle(tokenHandle);
+ RevertToSelf();
+ LocalFree(pDesc);
+ return 0;
+ }
+ CloseHandle(tokenHandle);
+ RevertToSelf();
+ LocalFree(pDesc);
+ return fAccessGranted == TRUE;
+#else
#ifdef HAVE_EACCESS
return (eaccess (filename, W_OK) >= 0);
#else
@@ -2281,6 +2342,7 @@
Opening with O_WRONLY could work for an ordinary file,
but would lose for directories. */
return (access (filename, W_OK) >= 0);
+#endif
#endif
}
_______________________________________________
XEmacs-Patches mailing list
XEmacs-Patches(a)xemacs.org
http://calypso.tux.org/cgi-bin/mailman/listinfo/xemacs-patches