|
|
| |
#include <windows.h> | #include <windows.h> |
#include <aclapi.h> | #include <aclapi.h> |
|
#include <lmcons.h> |
| |
static USHORT os_type; | static USHORT os_type; |
static SECURITY_ATTRIBUTES security_attr; | static SECURITY_ATTRIBUTES security_attr; |
| |
//static TEXT interbase_directory[MAXPATHLEN]; | //static TEXT interbase_directory[MAXPATHLEN]; |
| |
static bool check_user_privilege(); |
|
|
|
#endif // WIN_NT | #endif // WIN_NT |
| |
static TEXT user_name[256]; | static TEXT user_name[256]; |
|
|
} | } |
#endif | #endif |
| |
|
const TEXT* ISC_get_host(Firebird::string& host) |
|
{ |
|
/************************************** |
|
* |
|
* I S C _ g e t _ h o s t |
|
* |
|
************************************** |
|
* |
|
* Functional description |
|
* Get host name in non-plain buffer. |
|
* |
|
**************************************/ |
|
TEXT buffer[BUFFER_SMALL]; |
|
ISC_get_host(buffer, sizeof(buffer)); |
|
host = buffer; |
|
return host.c_str(); |
|
} |
|
|
#ifdef UNIX | #ifdef UNIX |
int ISC_get_user(TEXT* name, |
bool ISC_get_user(Firebird::string* name, |
int* id, |
int* id, |
int* group, |
int* group, |
TEXT* project, |
const TEXT* user_string) |
TEXT* organization, |
|
int* node, |
|
const TEXT* user_string) |
|
{ | { |
/************************************** | /************************************** |
* | * |
|
|
} | } |
| |
if (name) | if (name) |
strcpy(name, p); |
*name = p; |
| |
if (id) | if (id) |
*id = euid; | *id = euid; |
|
|
if (group) | if (group) |
*group = egid; | *group = egid; |
| |
if (project) |
|
*project = 0; |
|
|
|
if (organization) |
|
*organization = 0; |
|
|
|
if (node) |
|
*node = 0; |
|
|
|
return (euid == 0); | return (euid == 0); |
} | } |
#endif | #endif |
|
|
#endif | #endif |
| |
#ifdef WIN_NT | #ifdef WIN_NT |
int ISC_get_user(TEXT* name, |
bool ISC_get_user(Firebird::string* name, |
int* id, |
int* id, |
int* group, |
int* group, |
TEXT* project, |
const TEXT* user_string) |
TEXT* organization, |
|
int* node, |
|
const TEXT* user_string) |
|
{ | { |
/************************************** | /************************************** |
* | * |
|
|
if (group) | if (group) |
*group = -1; | *group = -1; |
| |
if (project) |
|
*project = 0; |
|
|
|
if (organization) |
|
*organization = 0; |
|
|
|
if (node) |
|
*node = 0; |
|
|
|
if (name) | if (name) |
{ | { |
name[0] = 0; |
DWORD name_len = UNLEN; |
DWORD name_len = 128; |
TEXT* nm = name->getBuffer(name_len + 1); |
if (GetUserName(name, &name_len)) |
if (GetUserName(nm, &name_len)) |
{ |
|
name[name_len] = 0; |
|
|
|
/* NT user name is case insensitive */ |
|
|
|
for (DWORD i = 0; i < name_len; i++) |
|
{ |
|
name[i] = UPPER7(name[i]); |
|
} |
|
|
|
/* This check is not internationalized, the security model needs to be |
|
* reengineered, especially on SUPERSERVER where none of these local |
|
* user (in process) assumptions are valid. |
|
if (!strcmp(name, "ADMINISTRATOR")) |
|
{ |
|
if (id) |
|
*id = 0; |
|
|
|
if (group) |
|
*group = 0; |
|
} |
|
*/ |
|
} |
|
} |
|
|
|
return check_user_privilege(); |
|
} |
|
|
|
|
|
//____________________________________________________________ |
|
// |
|
// Check to see if the user belongs to the administrator group. |
|
// |
|
// This routine was adapted from code in routine RunningAsAdminstrator |
|
// in \mstools\samples\regmpad\regdb.c. |
|
// |
|
static bool check_user_privilege() |
|
{ |
|
HANDLE tkhandle; |
|
SID_IDENTIFIER_AUTHORITY system_sid_authority = {SECURITY_NT_AUTHORITY}; |
|
|
|
// First we must open a handle to the access token for this thread. |
|
|
|
if (!OpenThreadToken(GetCurrentThread(), TOKEN_QUERY, FALSE, &tkhandle)) |
|
{ |
|
if (GetLastError() == ERROR_NO_TOKEN) |
|
{ | { |
// If the thread does not have an access token, we'll examine the |
nm[name_len] = 0; |
// access token associated with the process. |
|
| |
if (!OpenProcessToken(GetCurrentProcess(), TOKEN_QUERY, &tkhandle)) |
// NT user name is case insensitive |
{ |
CharUpperBuff(nm, name_len); |
CloseHandle(tkhandle); |
name->recalculate_length(); |
return false; |
|
} |
|
} | } |
else | else |
{ | { |
return false; |
*name = ""; |
} | } |
} | } |
| |
TOKEN_GROUPS* ptg = NULL; |
return false; |
DWORD token_len = 0; |
|
|
|
while (true) |
|
{ |
|
/* Then we must query the size of the group information associated with |
|
the token. This is guarenteed to fail the first time through |
|
because there is no buffer. */ |
|
|
|
if (GetTokenInformation(tkhandle, |
|
TokenGroups, |
|
ptg, |
|
token_len, |
|
&token_len)) |
|
{ |
|
break; |
|
} |
|
|
|
/* If there had been a buffer, it's either too small or something |
|
else is wrong. Either way, we can dispose of it. */ |
|
|
|
if (ptg) |
|
{ |
|
gds__free(ptg); |
|
} |
|
|
|
/* Here we verify that GetTokenInformation failed for lack of a large |
|
enough buffer. */ |
|
|
|
if (GetLastError() != ERROR_INSUFFICIENT_BUFFER) |
|
{ |
|
CloseHandle(tkhandle); |
|
return false; |
|
} |
|
|
|
// Allocate a buffer for the group information. |
|
ptg = (TOKEN_GROUPS *) gds__alloc((SLONG) token_len); |
|
|
|
if (!ptg) |
|
{ |
|
CloseHandle(tkhandle); |
|
return false; /* NOMEM: */ |
|
} |
|
// FREE: earlier in this loop, and at procedure return |
|
} |
|
|
|
// Create a System Identifier for the Admin group. |
|
|
|
PSID admin_sid; |
|
|
|
if (!AllocateAndInitializeSid(&system_sid_authority, 2, |
|
SECURITY_BUILTIN_DOMAIN_RID, |
|
DOMAIN_ALIAS_RID_ADMINS, |
|
0, 0, 0, 0, 0, 0, &admin_sid)) |
|
{ |
|
gds__free(ptg); |
|
CloseHandle(tkhandle); |
|
return false; |
|
} |
|
|
|
// Finally we'll iterate through the list of groups for this access |
|
// token looking for a match against the SID we created above. |
|
|
|
bool admin_priv = false; |
|
|
|
for (DWORD i = 0; i < ptg->GroupCount; i++) |
|
{ |
|
if (EqualSid(ptg->Groups[i].Sid, admin_sid)) |
|
{ |
|
admin_priv = true; |
|
break; |
|
} |
|
} |
|
|
|
// Deallocate the SID we created. |
|
|
|
FreeSid(admin_sid); |
|
gds__free(ptg); |
|
CloseHandle(tkhandle); |
|
return admin_priv; |
|
} | } |
#endif | #endif |
| |