I am trying to check if I have the proper access to a file. Here is my testing program
<br />
#include <stdio.h><br />
#include <windows.h><br />
<br />
typedef int TBK_BOOL;<br />
typedef int TBK_PERMISSIONS;<br />
<br />
#define TBK_TRUE 1<br />
#define TBK_FALSE 0<br />
<br />
#define F_OK 0 /* exists */<br />
#define X_OK 1 /* executable */<br />
#define W_OK 2 /* writable */<br />
#define R_OK 4 /* readable */<br />
#define D_OK 8 /* deletable */<br />
<br />
static TBK_BOOL win32_access(<br />
const char * os_path,<br />
TBK_PERMISSIONS permissions )<br />
{<br />
DWORD dwDesiredAccess;<br />
<br />
<br />
switch( permissions ) {<br />
case F_OK :<br />
return TBK_TRUE;
<br />
case R_OK :<br />
dwDesiredAccess = GENERIC_READ;<br />
break;<br />
<br />
case W_OK :<br />
dwDesiredAccess = GENERIC_WRITE;<br />
break;<br />
<br />
case X_OK :<br />
dwDesiredAccess = GENERIC_EXECUTE;<br />
break;<br />
<br />
case D_OK :<br />
dwDesiredAccess = DELETE;<br />
break;<br />
<br />
default :<br />
<br />
return TBK_FALSE;<br />
}<br />
<br />
GENERIC_MAPPING genericMapping = { READ_CONTROL | FILE_READ_DATA | FILE_READ_ATTRIBUTES | FILE_READ_EA,<br />
FILE_WRITE_ATTRIBUTES | FILE_WRITE_EA | FILE_WRITE_DATA | FILE_APPEND_DATA,<br />
READ_CONTROL | FILE_READ_ATTRIBUTES | FILE_EXECUTE,<br />
FILE_ALL_ACCESS } ;<br />
LPCTSTR lpFilePath = LPCTSTR(os_path);<br />
PSECURITY_DESCRIPTOR pSD = NULL ;<br />
DWORD dwLenNeeded = 0;<br />
HANDLE hHeap = GetProcessHeap();<br />
<br />
PRIVILEGE_SET privileges;<br />
DWORD dwGrandedAccess, dwPrivilegeLength;<br />
BOOL bSuccess, bAccessGranded;<br />
HANDLE hProcess, hToken;<br />
<br />
fprintf(stderr, "Start checking access for %s\n", os_path);<br />
<br />
GetFileSecurity( lpFilePath ,<br />
OWNER_SECURITY_INFORMATION | GROUP_SECURITY_INFORMATION | DACL_SECURITY_INFORMATION,<br />
pSD, 0, &dwLenNeeded );<br />
<br />
pSD = HeapAlloc(hHeap, HEAP_GENERATE_EXCEPTIONS, dwLenNeeded);<br />
if( pSD == NULL )<br />
{<br />
DWORD dwError = GetLastError();<br />
LPVOID lpError;<br />
<br />
FormatMessage( FORMAT_MESSAGE_ALLOCATE_BUFFER | FORMAT_MESSAGE_FROM_SYSTEM , NULL, dwError, MAKELANGID(LANG_NEUTRAL, SUBLANG_DEFAULT), (LPTSTR) &lpError, NULL, NULL);<br />
<br />
fprintf(stderr, "Cannot allocate memory for security descriptor.\n", (LPCTSTR) lpError );<br />
<br />
return TBK_FALSE;<br />
}<br />
<br />
bSuccess = GetFileSecurity( lpFilePath,<br />
OWNER_SECURITY_INFORMATION | GROUP_SECURITY_INFORMATION | DACL_SECURITY_INFORMATION,<br />
pSD, dwLenNeeded, &dwLenNeeded );<br />
if( bSuccess == FALSE ) {<br />
DWORD dwError = GetLastError();<br />
LPVOID lpError;<br />
<br />
FormatMessage( FORMAT_MESSAGE_ALLOCATE_BUFFER | FORMAT_MESSAGE_FROM_SYSTEM , NULL, dwError, MAKELANGID(LANG_NEUTRAL, SUBLANG_DEFAULT), (LPTSTR) &lpError, NULL, NULL);<br />
<br />
<br />
fprintf(stderr, "Cannot get security id. Buffer len is %d. Error %s\n", dwLenNeeded, (LPCTSTR) lpError );<br />
<br />
<br />
return TBK_FALSE;<br />
}<br />
hProcess = GetCurrentProcess();<br />
<br />
bSuccess = OpenProcessToken(hProcess, TOKEN_QUERY, &hToken);<br />
if( bSuccess == FALSE )<br />
fprintf(stderr, "Cannot get Process Access Token.\n");<br />
<br />
fprintf(stderr, "Access asked %x.\n", dwDesiredAccess);<br />
MapGenericMask(&dwDesiredAccess, &genericMapping);<br />
fprintf(stderr, "Access to examine %x.\n", dwDesiredAccess);<br />
<br />
bSuccess = AccessCheck( pSD, hToken, dwDesiredAccess, &genericMapping,<br />
&privileges, &dwPrivilegeLength, &dwGrandedAccess,<br />
&bAccessGranded );<br />
<br />
if( bSuccess == FALSE ) {<br />
DWORD dwError = GetLastError();<br />
LPVOID lpError;<br />
<br />
FormatMessage( FORMAT_MESSAGE_ALLOCATE_BUFFER | FORMAT_MESSAGE_FROM_SYSTEM , NULL, dwError, MAKELANGID(LANG_NEUTRAL, SUBLANG_DEFAULT), (LPTSTR) &lpError, NULL, NULL);<br />
<br />
<br />
fprintf(stderr, "Cannot check permissions. Error no %d %s\n", dwError, (LPCTSTR) lpError );<br />
<br />
<br />
return TBK_FALSE;<br />
}<br />
<br />
<br />
CloseHandle(hToken);<br />
<br />
HeapFree(hHeap, 0, pSD);<br />
<br />
fprintf(stderr, "Finish checking access.\n");<br />
<br />
return ((bAccessGranded == TRUE) ? TBK_TRUE : TBK_FALSE);<br />
}<br />
<br />
int main(int argc, LPCSTR argv [])<br />
{<br />
LPCTSTR path = LPCTSTR(argv[1]);<br />
char c;<br />
<br />
fprintf(stderr, "About to check %s file.\n", (LPCTSTR) path);<br />
<br />
if( win32_access( (LPCTSTR) path, R_OK ) )<br />
fprintf(stderr, "File is readable\n.");<br />
<br />
if( win32_access( (LPCTSTR) path, W_OK ) )<br />
fprintf(stderr, "File is writeable.");<br />
<br />
if( win32_access( (LPCTSTR) path, X_OK ) )<br />
fprintf(stderr, "File is executable.");<br />
<br />
if( win32_access( (LPCTSTR) path, D_OK ) )<br />
fprintf(stderr, "File is deleteable.");<br />
<br />
return 0;<br />
}<br />
When I am running it I am getting the following results
G:\Debug>check check.obj
About to check check.obj file.
Start checking access for check.obj
Access asked 80000000.
Access to examine 20089.
Cannot check permissions. Error no 998 Invalid access to memory location.
Start checking access for check.obj
Access asked 40000000.
Access to examine 116.
Cannot check permissions. Error no 998 Invalid access to memory location.
Start checking access for check.obj
Access asked 20000000.
Access to examine 200a0.
Cannot check permissions. Error no 998 Invalid access to memory location.
Start checking access for check.obj
Access asked 10000.
Access to examine 10000.
Cannot check permissions. Error no 998 Invalid access to memory location.
I do not undrstand what is wrong in the AccessCheck call. Everything seems to be fine and all memory is been in place.
Can someone spot any mistake on this small program. Help is much appriciated.
Ανέγνως αλλ' ουκ έγνων, η γαρ έγνως ουκ αν κατέγνων...Καβάφης.
|