内容简介:The ‘UnattendedUtilties’ is a Windows Runtime class object that is registered within the XboxDevService.exe residing in the Xbox One’s SRA partition. This service is only registered and executed when an authorized Xbox One is running under Developer Mode a
The ‘UnattendedUtilties’ is a Windows Runtime class object that is registered within the XboxDevService.exe residing in the Xbox One’s SRA partition. This service is only registered and executed when an authorized Xbox One is running under Developer Mode and will not execute in a retail environment. Initially, this was discovered after noticing an addition in the ‘Dev Home’ application file list that featured a tool section named ‘unattend’ which featured the tool page’s script as well as *.xboxunattend files located on the System Tools drive. Viewing these *.xboxunattend files revealed that they were simply batch scripts with a renamed extension.
Oddly, almost none of these pages are actually available in standard UWA developer mode. They do not appear in app during runtime at all. Are these hidden intentionally? And do they still work?
Upon inspection of the Dev Home findings, it contained an interesting set of code:
// Copyright (c) Microsoft Corporation. All rights reserved. _runScriptOnUsb: function () { try { // Disable the button to prevent pressing it multiple times. this._runScriptOnUsbButton.disabled = true; this._closeConfigureUnattendButton.focus(); unattendUtils.runUnattendedScriptOnUsbAsync(); } catch(e){ // Do nothing. This shouldn't normally fail but can if the user removes the USB // drive at the right time. } },
The code that stands out is certainly ‘unattendUtils.runUnattendedScriptOnUsbAsync()’ which peaked my interest as I was curious to whether these “scripts” were executed based on the calling application or whether or not it was a system service. Next, I peaked around for where the function belonged which was a simple task - the namespace that ‘unattendUtils’ referred to was ‘Microsoft.Xbox.Development.UnattendedUtilities’. Conventiently, in the root directory of the Dev Home application there was a ‘microsoft.xbox.development.winmd’ file there! Of course, if you are already familiar, this is a Windows Metadata file used by the Windows Runtime system that contains the information for the interfaces that reside in another process.
These file types can simply be dropped in a .NET Disassembler (e.g. JetBrains dotPeek) with the ability to view the class definitions as well as other types.
Hah! We have an already defined interface with some interesting functions. But due to the nature of these Windows Metadata files meant that the host binary was separate than Dev Home. This can very easily be discovered, however, as there are usually ‘ProxyStubs’ that are loaded into client-calling applications when said application creates an instance of a class object. By debugging the Dev Home app remotely, we can look at the loaded modules and determine which may be responsible. As we were running in developer mode, I suspected it only had to be related to a limited subset of executables and therefore when finding ‘XboxDevService.ProxyStub.dll’ loaded in the Dev Home process I immediately decided to disassemble the server itself.
Reversing XboxDevService
As these scripts appeared to simply be batch scripts, I figured that the XboxDevService would require to call the ‘CreateProcess’ API, I viewed the executable imports and xref’d the CreateProcessW import until I came across a function that most definitely provided enough basis that this service was responsible.
sub_1400238B8
hInput = GetStdHandle(0xFFFFFFF6); targ_handle = hTarget; lpCmdLine = WindowsGetStringRawBuffer(scriptPath, 0); // scriptPath from function parameter (a2) v31 = (__int64) & v31; // Execute script via full path if ((unsigned int) CreateProcessW(0, lpCmdLine, 0, 0, 1, 0x8000000, 0, & startupInfo, & lpProcInfo)) goto LABEL_84; dwLastError = GetLastError(); res = (unsigned __int16) dwLastError | 0x80070000; // ... // Create string reference with message for toast notification if ((int) WindowsCreateStringReference(L "See SystemScratch\\boot\\logs directory for the log file.", 55, & hSTR_HDR_LOG_DIR, & hSTR_LOG_DIR) < 0) RaiseException(0xC000000D, 1, 0, 0); hSTR_LOG_DIR_2 = hSTR_LOG_DIR; if ((int) WindowsCreateStringReference( L "Unattended script complete.", 27, & hSTR_HDR_COMPLETE_MSG, & HSTR_CLASS_FRONTPANEL_UTILS) < 0) { RaiseException(0xC000000D, 1, 0, 0); res = CreateToast(HSTR_CLASS_FRONTPANEL_UTILS, hSTR_LOG_DIR_2, v25, v24); if (res >= 0) { classObject = 0; // Create string reference containing the activatable class id if ((int) WindowsCreateStringReference( L "Microsoft.Xbox.Development.FrontPanelDisplayUtilities", 53, & hSTR_HDR_COMPLETE_MSG, & HSTR_CLASS_FRONTPANEL_UTILS) < 0) RaiseException(0xC000000D, 1, 0, 0); hClassId = HSTR_CLASS_FRONTPANEL_UTILS; v28 = classObject; if (classObject) { classObject = 0; self_ret( * (__int64( ** )(void))( * (_QWORD * ) v28 + 16)); } // Register Windows Runtime object res = RoGetActivationFactory(hClassId, & IID_FrontPanelDisplayUtilities, & classObject); if (res >= 0) { pFrontPanelDisplayUtils = classObject; // Create string reference with message for front panel if ((int) WindowsCreateStringReference( L "Unattended script complete.", 27, & hSTR_HDR_COMPLETE_MSG, & HSTR_CLASS_FRONTPANEL_UTILS) < 0) RaiseException(0xC000000D, 1, 0, 0); res = self_ret( * (__int64( ** )(void))( * (_QWORD * ) pFrontPanelDisplayUtils + 96)); // ShowFrontPanelNotification(msg) } // ... } // ... } }
The pseudo-code allows us to draw conclusions that this particuluar function is one that is responsible for executing unattended scripts as it provides the way for popping a toast notification, and for chuckwalla kits it will use the front panel, while referring to the log output directory. By determining the host process of the Windows Metadata we located earlier, we can now begin attempting to create an instance of the class ‘UnattendedUtilities’ and attempt to execute our own script. I searched around online and also the Windows SDK for references to how Windows Runtime classes are usually specified and came across several resources outlining the class definitions but I was still unsure. So, I decided to look around for other binaries which may rely on the UnattendedUtilities class - which was the Windows Device Portal. This lead me down a path of manually defining the interface with stubs to ensure the correct offsetting…
which I quickly discovered utilities provided in the Windows SDK which does the hardwork for me.
Article: How to: Use winmdidl.exe and midlrt.exe to create .h files from windows metadata
By running via the Visual Studio Developer Prompt:
winmdidl.exe /nologo /outdir:"output" microsoft.xbox.development.winmd midlrt.exe microsoft.xbox.development.unattendedutilities.idl /metadata_dir "C:\Windows\System32\WinMetadata"
This generates a header file that defines all that we need. It’s… a mess so I decided to tidy up the results and neatly define what we need.
MIDL_INTERFACE("DE87AD07-75DC-4EEC-9226-5628E98B9914") IUnattendedUtilitiesStatics : public IInspectable { public: virtual HRESULT STDMETHODCALLTYPE RemoveUnattendedScript(void) = 0; virtual HRESULT STDMETHODCALLTYPE RetrieveUnattendedScript(void) = 0; virtual HRESULT STDMETHODCALLTYPE RetrieveAndRunUnattendedScriptAsync(void) = 0; virtual HRESULT STDMETHODCALLTYPE RetrieveAndRunUnattendedScript(HRESULT* scriptResultHr, HSTRING* scriptOutput) = 0; virtual HRESULT STDMETHODCALLTYPE RunUnattendedScript(HSTRING scriptFileFullPath, HSTRING logFileFullPath, HRESULT* scriptResultHr, HSTRING* scriptOutput) = 0; virtual HRESULT STDMETHODCALLTYPE AbortUnattendedScript(void) = 0; virtual HRESULT STDMETHODCALLTYPE SendToastNotification(HSTRING title, HSTRING message) = 0; virtual HRESULT STDMETHODCALLTYPE IsScriptRunning(boolean* isRunning) = 0; virtual HRESULT STDMETHODCALLTYPE ShouldRunOobeScript(boolean* shouldRun) = 0; virtual HRESULT STDMETHODCALLTYPE ShouldRunOobeScript(boolean shouldRun) = 0; virtual HRESULT STDMETHODCALLTYPE ShouldBlockUsbScripts(boolean* shouldBlock) = 0; virtual HRESULT STDMETHODCALLTYPE ShouldBlockUsbScripts(boolean shouldBlock) = 0; virtual HRESULT STDMETHODCALLTYPE ShouldSkipAbortToast(boolean* skip) = 0; virtual HRESULT STDMETHODCALLTYPE ShouldSkipAbortToast(boolean skip) = 0; virtual HRESULT STDMETHODCALLTYPE ShouldCallDevCenter(boolean* shouldCall) = 0; virtual HRESULT STDMETHODCALLTYPE ShouldCallDevCenter(boolean shouldCall) = 0; virtual HRESULT STDMETHODCALLTYPE ShouldBlockUnattendScripts(boolean* shouldBlock) = 0; virtual HRESULT STDMETHODCALLTYPE ShouldBlockUnattendScripts(boolean shouldBlock) = 0; virtual HRESULT STDMETHODCALLTYPE ScriptRunningChanged(int64_t* handler, EventRegistrationToken* token) = 0; virtual HRESULT STDMETHODCALLTYPE ScriptRunningChanged(EventRegistrationToken token) = 0; virtual HRESULT STDMETHODCALLTYPE HasUnattendedScriptOnUsb(boolean* hasScript) = 0; virtual HRESULT STDMETHODCALLTYPE RunUnattendedScriptOnUsbAsync(void) = 0; };
Did it work?
After putting together a small console program and simply using the ‘RetrieveAndRunUnattendedScriptAsync()’ function, I wrote a script that would run telnet and created a console notification to signal a more obvious result. Once deployed and connected over via SSH, I plugged in my USB with the specified script, opened up the Xbox Device Portal for monitoring processes and then executed my program…
Suddenly, on my console I see something!
Success!
Now to double check on the device portal…
YES! We have successfully ran an unattended script and also achieved the highest privilege level! Once there is a telnet instance running at the highest privilege level, we can utilise the ‘net1.exe’ carried over from a Windows Core build and add a new user with an administrator role and also enable the built-in administrator account. These accounts will persist across reboots in developer mode as long as you avoid clearing the data when switching back to retail.
Utilising the UnattendedUtilities allowed us to elevate our existing user privileges within the SRA partition which also grants more flexibility and access to continue researching and reverse engineering the operating system. So why the big deal? It mostly comes down to a combination of how the developer mode works and from experience reporting and dealing with these issues in the past. Developer Mode itself relies on a certificate that is either authorized by Xbox Live, if you are a partner or UWA developer, or an internal Microsoft developer. These certificates contain console specific information and capabilities.
There are different capabilities that generally depend on what type of “devkit” you have; even though it is dependent on what the certificate says. We have:
- ERA - For game development - offering a much wider range of tools and access
- SRA (Now UWA) - For app development specifically targeting the System OS - much more limited in scope.
- Internal - For consoles that are used for OS and Security development at Microsoft
The point to note down here is that UWA is completely lacking the range of tools featured as an ERA kit. While this makes sense, it is interesting that the features leftover, which generally check which mode and devkit type the console is before executing, actually work and ignore the context without official public documentation and tooling.
You can read more information at the Xbox One Research Wiki .
Disclosure
Since the feature was hidden away and after doing some investigating it was understood that the ‘unattend’ feature was meant for use on ‘ERA’ authorized development kits and was documented on the Xbox One XDK. As the feature worked on UWA I had responsibly put together a PoC and small write up and notified MSRC. However, the response was not what I was expecting as they claimed that it was ‘by design’ and is an intended feature for developer mode. Despite being hidden away and not accessible, it’s intended. This result was quite surprising as they had been quick previously to fix other issues that allowed privilege escalation but I welcome the new approach.
With the locked away features being a bit of a pain to get working successfully I decided to publicly release my program to enable more than myself, and team, to put the privileges to use and hopefully see individuals doing their own research.
You can find the XboxUnattend project here .
Timeinline
- 20/09/2018 - Initial discovery
- 16/05/2019 - Proof-of-Concept and write-up
- 17/05/2019 - Sent MSRC said PoC and write-up
- 20/05/2019 - Initial response from MSRC
- 22/05/2019 - MSRC confirmed it was ‘by-design’
- 10/09/2019 - Disclosed PoC publicly on GitHub
P.S
以上所述就是小编给大家介绍的《Privilege escalation via the unintended UnattendedUtilities》,希望对大家有所帮助,如果大家有任何疑问请给我留言,小编会及时回复大家的。在此也非常感谢大家对 码农网 的支持!
猜你喜欢:本站部分资源来源于网络,本站转载出于传递更多信息之目的,版权归原作者或者来源机构所有,如转载稿涉及版权问题,请联系我们。
用户力:需求驱动的产品、运营和商业模式
郝志中 / 机械工业出版社 / 2015-11-1 / 59.00
《用户力:需求驱动的产品、运营和商业模式》从用户需求角度深刻阐释了互联网产品设计、网络运营、商业模式构建的本质与方法论! 本书以“用户需求”为主线,先用逆向思维进行倒推,从本质的角度分析了用户的需求是如何驱动企业的产品设计、网络运营和商业模式构建的,将这三个重要部分进行了系统性和结构化的串联,然后用顺向思维进行铺陈,从实践和方法论的角度总结了企业究竟应该如围绕用户的真实需求来进行产品设计、网......一起来看看 《用户力:需求驱动的产品、运营和商业模式》 这本书的介绍吧!