← All talks

I'm not actually an SCCM admin... I just implied it

BSides PDX 202520:2856 viewsPublished 2025-12Watch on YouTube ↗
Speakers
Tags
About this talk
SCCM (System Center Configuration Manager) remains widely deployed for endpoint management despite its 30-year technical debt. This talk demonstrates how an attacker can escalate to SCCM admin privileges by exploiting co-management configurations and the administration service API's lack of authorization checks, allowing arbitrary UPN impersonation through validated Entra tokens.
Show original YouTube description
I'm not actually an SCCM admin... I just implied it - Garrett Foster Microsoft's Configuration Manager (more commonly known as System Center Configuration Manager or SCCM) has received a great deal of attention from the offensive security community in recent years. The service's 30 year history includes a mountain of techincal debt that is still heavily relied on by enterprises across the globe. In fact, even with the industry's shift to cloud, SCCM remains the most depended on solution for endpoint management. This presentation will publicly disclose how an attacker under the right circumstances can abuse this dependence to escalate to SCCM admin simply by implying it. Garrett Foster is an offensive security researcher with over 6 years of experience in information technology. He has conducted successful engagements against organizations that include the finance, healthcare, and energy sectors. Garrett enjoys researching Active Directory and developing offensive security tools. His background also includes roles as a Security Operations Center Analyst and Systems Administrator. --- BSides Portland is a tax-exempt charitable 501(c)(3) organization founded with the mission to cultivate the Pacific Northwest information security and hacking community by creating local inclusive opportunities for learning, networking, collaboration, and teaching. bsidespdx.org
Show transcript [en]

[music]

Right. My name is Garrett Foster. I am a senior security researcher over at uh on the team at Spectrops. I've been there a little over two years. Kind of like my day-to-day responsibilities there are to do a bit of tradecraftraft discovery and red team enablement. So kind of like the if you're at a stuck point, my goal there is to help them get through that stuck point and then whatever the results of that research, we try to to take that uh those results and then implement them in our product uh the Blood Hound graph. Um I don't have a ton of time so I'm just going to press on with it with the agenda. So what I hope

to share with you today is a bit of a recap on what SECM is and kind of do a a very quick uh explanation of what it where it is where it came from and then some of the security research that has been done by us and and the community as a whole. And then from there we'll talk a bit about uh co-management. So if you have an active directory environment that has a is hybrid and is using uh entra as well for some type of identity management co- management might be relevant. And then we'll talk about the administration service API, which is an on-prem API that grants kind of like this administrative access to SECM. So,

it's just another way for admins to be able to uh uh administer that that service, but it's going to be relevant to the co-management piece. And then we'll finish things off by taking advantage of all of that co-management to go from a low privilege user context to completely taking over all of SECM and therefore all of the managed clients in that service. >> [snorts] [clears throat] >> So, SECM uh stands for System Center Configuration. I lost it. Where'd it go? Okay, so System Center Configuration Manager, SECM, uh it's gone through a bunch of different name changes. It's about 30 years old, so it's it's been recycled a bit. I'm a little bit more partial to this uh beautiful piece of

artwork by my co-orker Craig um because it's now known as Microsoft Configuration Manager. Just to like the the quick recap, this graph uh was made by Carson Sanker. he made a blog post a couple years ago kind of detailing how we got to where we are now. So, uh, SECM was first introduced in about 1994 and it didn't really get in too much offensive attention until uh, Defcon 20 when Dave Kennedy uh, was presenting on how he was able to leverage that service to basically pop shells on every client. So, at it at its core, SECM is just endpoint management software. It'll have an agent running on on whatever hosts are being managed by that device. has

system level access because it's responsible for driver updates, Windows updates, uh application deployment and like policy deployment. So Dave took advantage of that and realized that if you could just take over SECM, you'd therefore control every client and and the the research kind of continued from there. uh Matt Nelson, one of our co-workers, um he kind of picked up and and ran with it a bit, had a few blog posts and tools and then it died for for a number of years and then Chris Thompson and Dwayne Michael kind of picked up the baton and kept that going and the last few years it's it's kind of exploded from from an offensive point of view and um it's exploded so much that

myself uh Dwayne Michael and Chris Thompson developed this kind of living document called Misconfiguration Manager. It's a GitHub repository that uh tries to take all the known offensive tradecraftraft and uh gives it a taxonomy. So if it is a takeover or you're able to grab credentials from it, we label those and we outline how the offensive uh the attacker can take advantage of that while also supplying like defensive uh measures that the defensive team can take. So it's it's good for both sides, both red and blue. [cough and clears throat] But since then there's been a number of like community contributions and probably the the most notable has been from uh the synactive there they're a

team over in France. They found an un unauthenticated SQL SQL injection that led to complete compromise from an unauthenticated perspective to control all of SECM and then therefore every client. That's not really it. Um there's been a number of different uh like community contributions whether it be blog posts or tweets or tools or or just conversations about how they have used this service to accomplish some level of goal or objective during their assessments. [snorts] But the point I'm trying to make is that we have focused so much of that effort to only what's on prem like we we only what'sever ever in the enterprise network. But I I it was time to explore how it would work when you are

integrating your on-prem you have a hybrid deployment with the cloud particularly with with uh Entra or Azure or whatever they're going to name it next. Um so there's three ways that SECM can actually have this this hybrid or co-managed deployment. The first is tenant attach. Uh this is less um less of a expansion. It's more of a like DLC for SECM. So there's a couple extra pieces you can do from Entra. But the two that are most relevant are the CL cloud management gateway and then co- management. And both of these are two different deployments but both solve the same problem of managing a remote workforce which over the last few years has been kind of an explosion.

So the cloud management gateway or the CMG the way this process works is you'll have a virtual machine up hosted up in Azure that your clients your remote clients will connect to and it basically proxies that connection into your uh your physical network. So this is used when they can't have VPN access. They're not in office, they're across the globe. They can connect to this endpoint to have policies applied and so on and so forth. So on the other side of that is co-management a little bit different. This is actually going to integrate with Microsoft intoune. And in tune is uh Microsoft's cloud endpoint management solution. So the way this works is it just kind of integrates and you pass off

workflows between the two depending on what your your configur uh your requirements are. But the the lines do cross a bit and it's due to how or the configuration requirements for setting up both those those um solutions and you'll do so from within the the configuration manager console and you'll set up what's called configure Azure services and the piece that you'll be doing is called cloud management and the wizard is actually it's relatively easy. It's streamlined. There's not a whole lot of nuance to it. So we don't have to spend much time on it. But the key piece that you're doing is you're setting up two entra applications. There's a client app and a web application. And these uh work

together to create an ooth flow for users to sign into uh to the specific scope. [clears throat] If you scroll down a bit, there is a kind of a key thing that um you might overlook. There is the option to disable Microsoft Entra ID authentication. So if you were just skimming through this and weren't paying attention, you might have missed this, but that implies that Microsoft Entra authentication is enabled by default for the tenant depending regardless of how you're setting things up. [snorts] So once that completes, we don't we don't have a lot of visibility into what the those applications even are or what like permissions we're granting it because we're setting them up with uh

global admin or cloud application admin level permissions. So let's take a look at what's actually happening. We have the client app and it's grant it is being delegated user impersonation to the web app and whatever that is scoped towards. So this is preconented. So the user that's that's being impersonated does not have to approve it. And this will happen for any identity that's an intra from the app side. What we're actually being what's what we're actually accessing what's what's being um uh granted to us is we have this API URI but we we didn't actually set any type of backend up for this. And this is where the admin service comes into the picture. So the administration service

is that on-prem O data rest API and uh it's hosted on the SMS provider role. The SMS provider, see if I can get this, provides API interoper interoperability access over HTTPS. So the SMS provider actually contexts the database through uh WI. So what they did is to grant you API access to it. It they just put an API in front of WI. So you have another layer of abstraction but it gives you administrative access from this perspective and that is implemented. If we take a look at the service binaries, we can see this URI exists. That admin service URI is present. And this is relatively well known if you've been ever ever messed with SECM. Uh there's tradecraftraft

around this. There's post exploitation that's been taken advantage of here. But when you look at the source code because it's all innet, so we can reverse it. Um there's a completely different URI path that I really wasn't aware of that seems relevant to Entra because of the token off uh string included in it. So if we keep kind of digging into that source code and see what's actually being implemented by the service, it is it is handling any type of CRUD uh operation being submitted to that API. So if you're trying to make some type of change or you're trying to recover data, it's going to process that request and and kind of pass that off to the Wii

endpoint. So there's a few checks. It's going to instantiate a uh a new Windows identity class, uh a C# class, and this just represents a Windows user. So we'll just kind of have that that ready to go. and and usable. And then from there, it's going to check and see like is Azure AD enabled or entra now that we've changed things. And we know this this has been enabled by default. So we can kind of press on through that logic and and hit this method called parse bearer token. Now this method is going to take whatever was in the authentication headers for that API request, pass off that token to this method, and that's where the the fun really begins. Uh so

it seems like it might be a simple um a process to to parse this bearer token. But you be mistaken. It's about 15 layers deep of different kind of poking and proddding to make sure everything's in line. But the end result is it's doing two things. It's validating the token signature. It's making sure that the token that we are providing is coming from where it says it comes from and that it hasn't been manipulated in any way that we didn't try to change any strings or any values in it. So the signature for that is still still good. And then it's just going to validate the tokens issuer and audience. Those two strings are like the the big piece to

the puzzle and that's arguably the the only interesting piece from all of that from uh the all of the the whole flow of validating this and it the it's stored in the get authentication info method. So what we'll do is we're going to build a list of issuer audience metadata and assigning search. So how do we get that data? Where is that stored? SECM essentially everything lives in that database is in the site database. Uh you can consider that the brain of the entire operation and then the the site server itself is the body for everything else. The way it pulls that data from the site database is it runs a stored procedure which is you could think of it as a

script to be to run SQL queries and that that stored procedure is called get token validation info. And the result of that if we if we take that syntax since it's a test environment we can take it to the site database and issue that or or run that stored procedure to see the data that's being returned during like standard operation. So we'll get an issuer audience the metadata and then the signing. So the piece that's relevant to validating this token are you're going to take the string value of the issuer and the string value of the audience. You'll have your bearer token. You'll des serialize that and then it's just doing a one to one string match for

both. saying are they equal? Is there is it 100% accurate? And that's the validation steps. That's it. We want to make sure it's signed and make sure that these two strings match. So cool. We've made it back up to the parse bearer token method. We're saying, "Hey, cool. Here's your validated token. Go ahead and press on with processing that request to transform it to Wine and and keep going." And that's when we get back to our Windows identity. So, we're going to instantiate the Windows identity and store in this identity variable. and we're going to pass it the user principle name value from that entra token or validated token. So the UPN is a claim included in this.

So we can pull that out and actually extract the domain user UPN from uh the token. So now we passed it off and we created this class as this user. So if you look how the Windows identity class operates when we overload it with just a user principle name value, it's doing one thing. It is going to call uh it's going to construct it by calling the curb s foru loon structure. So if you're unfamiliar curb s foru is a window is a kerros extension implemented by Microsoft uh called service for user or service for user to self. So that service is going to create an impersonation token on that endpoint as that user. So domain user is now

impersonated and it's like this is the identity that I'm going to process the request for. So I stood on out of it and was kind of curious like okay so it's just doing this S for you lo on it's this kind of makes sense like what's the actual inherent risk here? Um [snorts] and this is kind of my experience on on how this went down and the conclusion is is that the admin service impersonates any UPN from a validated token. There is no authorization checks being done whatsoever. So if there is some way that we can manipulate that value, if we can push a UPN for a known administrative user into Entra and authenticate as that

user, we could be admin. And it sounds it sounds too easy and it is because there's some some nuance to how UPN's or user principal names work in in AD and Entra. So here we have a a B-sides user and it has a user principal name value. So when you have a hybrid environment, uh typically what will happen is you'll have users that are synchronized into Entra and you can you can have some some control like you you might be able to specify a certain container or a certain um list of users that are synchronized but for the sake of argument let's just say that every user is synchronized and there are a few attributes that map automatically when a

new user accounts created in AD and then that transfers into ENTRA and the user principle name is one of them. So if we have besides PDX at unsigned short, we can we'll see that once that user is created and and synchronized with ENTRA, the UPN follows it. It it goes with it. [clears throat] So this this attribute being present is called explicit UPN mapping. Because it's present, it's actually stored in that attribute. It's explicit. But what about the case where there isn't a value present? Like what happens there? Um, Microsoft considered this and they explained the process when that when that value isn't present. And it the the quote is a UPN can be implicitly

or explicitly defined and an implicit UPN is always associated with the user's account even if an explicit UPN is not defined. This is also true when it is. So you could think more of an explicit UPN as an alias. If your internal domain name is different from the UPN value that's present, no matter what happens during the authentication process, your implicit UPN is the context that you're authenticated under. So, MS Kyle actually explains how this this process happens and where the UPN where the implicit value comes from. It will concatenate the name with an at symbol followed by the DNS name of the domain. So, it'll just kind of build all of that together and combine them. So

from our example user it'll take the example add the at at unsigned short and there is our uh our implicit UPN things get interesting when we start to think about uh machine accounts. So the site server I mentioned is you can think of it as the body of the entire thing and from all the tradecraft that we've had for compromising SECM and using it to kind of take over environments the the site server is the the number one target. Um it is a ton of um of responsibility in SECM. It is uh admin on all of the certain roles. It's responsible for maintaining the health of things. Uh what's what's good in in our situation is machine accounts will

not have a user principle name mapped by default. Uh when you create a new user account, typically you're going to create a username and AD will automatically populate that attribute. If you try to nullify it or or remove it using their tooling, you'll get a constraint violation. And then you also have a scenario where UPN's are required to be unique across the forest. So thinking of scenarios where okay, what if we could just take a admin's UPN add it to a user that we control and and and take that route. You you'll run into constraints. But the way the implicit UPN works for a site server or for any machine account is it's going to take

that name, concatenate it with the at symbol and then concatenate it with the domain name. So we can create an implicit UPN uh for that user. So if we own any user account or if we own some type of privilege to modify the UPN value of a user, we could change it from whatever value it is to the explicit value of the UPN and not run into a constraint violation because it's not there. So let's look at what that would that process might look like. So through this we'll go through um we're going to look at the bides users um privileges and they're set to or their their settings. It has the the explicit UPN

map to at unsigned short. So we control this user. we can flip the UPN value to the site servers UPN. So now we have an explicit UPN that's mapping to that. From there we can now authenticate as the bides user with our new UPN which still ties to us. So I've already synchronized it. So it's already up in En intra. And now we have a token with that UPN value present. So now we'll remove that explicit UPN. So if it tried to map the identity when we used the token, it would hit that account. But now that it's dangling, it's going to resolve the identity to the site server. So here's us in the administrative console showing that we

have just one singular admin. And then we will run a uh an API request using that bearer token that um and then submit it to the API and it'll go through that validation flow that we've seen where it just um it des serializes it validates everything make sure that the strings match that the token signature is good but because we've impersonated and we have that UPN value of the site server we can it will immediately add our at user as an admin uh because it it it is impersonating itself at that point. So we play with the logic flow there. So, we thought this might be bad. Uh, disclose it to Microsoft in July. Um, after some back

and forth, they decided that it was going to be an issue that would be patched. They assigned it this temporary or this potential CVE. It's still tentative. Uh, the patch was supposed to be released today. It wasn't, but they told me that we could release it today. Like, this was the timeline. So, um, [laughter] so here we are. Um, but yeah. Um, that was essentially this was a public disclosure for that. Um, I have about a minute left in the talk. So, are there any questions, curiosities, or anything there? >> Uh, what kind of assets will we expect to see that CV on if we ran a tenable scan? >> Uh, if you ran a tenable scan right now,

I don't expect you to find anything yet. >> If it was, >> yeah. Um, that's a curious one. So, you asked if the question was like, what kind of assets would we see this on running on if we were run a tenable scan? You'd have to have your scanner uh running probably on the site server itself to have some type of access there. and as well as um so the cloud management gateway I only have 20 minutes there's there's more to this uh the CMG is hosted in Azure and you can actually expose that administration service API to the internet like that's that's a feature and so now that tells us that if I get access to Entra I can

just create that token and authenticate to that API and now have control of your whole onrem without ever actually being on prim. So, um, >> what if somebody was cloud entra only >> was entra only? uh it's going to more than likely you'll want some type of access to the site server still because that's that's the endgame is getting control of that on premises asset that has all of the clients and managing all the different resources throughout there cuz we we're basically creating a hybrid attack path there where we can go from the cloud to onrem and now we control everything that has an agent installed on it whether that's onrem remote cloud wherever it it's it's going to be uh

environment dependent and deployment dependent so I mentioned those three different types of doing co-management. Um, if you're using the the co- management version where you're integrating the two services, you'll probably run into where this might be a leverage for that. Any other questions? If there's not right now, I'm going to be kind of hanging out in the hallway or probably running over to our booth. But, uh, thank you so much for attending. I appreciate it. [applause]

[music]