I would like to write a function to check if a given user is member of a group, in C language (it is based on a code which I found on stackoverflow How to programmatically figure out if a user account is a member of a particular group in Windows?). I've developped this function within the WinCC Software, which is a scada system.
Here's my code :
//Insert the header starting here
#include "WinApi.h"
#include "GlobalDefinitions.h"
BOOL CheckGroupMembership(char* UserName, char* Password, char* Domain, char* Group)
{
HRESULT result;
SID_NAME_USE SIDType;
WCHAR szDomain[256];
DWORD dwSidSize=0;
DWORD dwSize;
HANDLE user;
BOOL b=FALSE,returnval;
SID* pSid;
WCHAR szGroup[50];
// Convertit le nom du groupe en wide string
result=MultiByteToWideChar(CP_ACP,MB_PRECOMPOSED,Group,strlen(Group),szGroup,50);
printf("Nom du groupe : %ls\r\n",szGroup);
//recupere SID groupe
//premier appel de lookup pour allouer la bonne taille de SID (remis à jour dans dwSidSize);
LookupAccountNameW(NULL,szGroup,NULL,&dwSidSize,szDomain,&dwSize,&SIDType);
if (dwSidSize)
{
pSid=(SID*)malloc(dwSidSize);
//note : pas besoin de lui fournir un domaine si la machine est déjà intégrée dedans
LookupAccountNameW(NULL,szGroup,pSid,&dwSidSize,szDomain,&dwSize,&SIDType);
printf("dwSidSize %d \r\n",dwSidSize);
printf("Infos SID : %x , %x, %x - %d \r\n", pSid->Revision,pSid->SubAuthorityCount,pSid->IdentifierAuthority,SIDType);
// Récupère le handle de l'utilisateur
returnval=LogonUserA(UserName,Domain,Password,2,0,&user);
printf("User %d - %x \r\n",user,returnval);
returnval=CheckTokenMembership(user,pSid,&b);
}
printf("returnval %d - b : %d - %d\r\n",returnval,b,GetLastError());
free(pSid);
return b;
}
Whatever I do, the returnvalue outside CheckGroupMemberShip is false. I think LookupAccountNameW works well, if i put a valid group i've got some valid informations within the SID structure. If i put a group that doesn't exist, it just gives me zeros.
I think also LogonUserA works pretty well, as if i give valid informations the returnval is true, otherwise it is false.
Only checkGroupMembership doesn't seem to answer me.
There are some things I don't understand well though : Why is there a list of SIDs for one requested group and not only one ? Is there a place where I can compare the values within the SID structure and the SID corresponding to an existing group ? Whatever I give (group or user name) him it seems that the SIDType, is always the same at the output of LookupAccountNameW, Why ? Finally, GetLastError doesn't seem to help me. It always gives me 0, why ?
To be noticed : the "WinApi.h" is custom made, because I only wanted to import what was strictely neededd within my application. If you think that could be the problem, I could post it.
Thanks in advance for your answers,
Julien