Finding Actuators using Static Code Analysis with semgrep: Spring Actuator Security Part 2

Are you looking for effective ways to secure your Spring applications? Look no further! Our very own Dr. Ing. Max Maass has created a comprehensive 3-part series on Spring Actuator Security, covering everything from identifying vulnerabilities to implementing best practices. On today's episode we will discuss how we can detect exposed Spring Actuators in an application that you have source code access to. We will begin with manual steps, and then look at how you can automate the process using static security testing tools (dynamic testing will be covered in part 3 of the series).

In the first part of this series, we have discussed the risks inherent in exposing the Actuator functionality of the Spring framework. If you haven't read that part yet, I recommend that you do so before reading this article.

Part 2: Finding Actuators using Static Code Analysis with semgrep

  1. Manually Looking for Exposed Actuators
  2. Automating the Search using Semgrep
  3. The Basic Case: All Actuators
    3.1 Matching Specific Actuators
    3.2 Excluding Findings
  4. Conclusion

 

1. Manually Looking for Exposed Actuators

The most basic method of finding dangerous actuators is to use... your eyeballs. If you have access to the application source code, you can look at the Spring configuration files to check if actuators are enabled, and how they are configured. Begin by checking the .properties file(s) (or the respective .yaml equivalents) where the Spring configuration is stored. Recall that the list of active actuators is controlled with the following key:

This setting controls which endpoints are exposed over the web. Individual endpoints can also be completely disabled by setting management.endpoints.$ACTUATOR.enabled=false - as a rule of thumb, I would recommend inspecting everything in the management category and see if any dangerous endpoints are being activated, and if so, if mitigations (authentication requirements, ...) are already in place.

(All examples in this article are targeting the current version of Spring - older versions may use a different configuration syntax, or even (in the case of Spring 1.X) expose all actuators by default. Adapt what you read to your version of Spring, if necessary.)

 

2. Automating the Search Using Semgrep

Checking the code manually isn't always feasible. Maybe you are part of a security team that is responsible for a large set of software repositories, or maybe you want to add a check for dangerous actuators to your CI, to ensure that they aren't inadvertently activated a few weeks down the line.

For these cases, let me introduce you to my favourite static code analysis tool: semgrep. It's a free Open Source tool that you can install and use right now (it only starts costing money if you want to use their dashboard to view the results, which is entirely optional, and all code scanning runs on your device - code is never uploaded to any servers). Stated briefly, semgrep searches for code matching specific patterns, taking the semantics of the code into account (hence, semantic grep). You can use it for security checks based on a large set of detection rules curated by the semgrep community, but where it really shines is when you start writing rules for your own use cases.

 

3. The Basic Case: All Actuators

Semgrep rules are fairly easy to wrap your head around, so let's build one for our example application from the previous part of this series. To be able to showcase some of the capabilities of semgrep, we'll be using the YAML configuration syntax for Spring. This is what a basic vulnerable Spring configuration could look like:

Semgrep patterns are also specified in YAML files. Here's an annotated semgrep rule to find this case, with explanations what the components are doing.

annotated semgrep rule

This is already quite a handy rule to quickly audit a large codebase for an obvious misconfiguration. To run it, save it in a file, and then run it with semgrep like this:

semgrep

Note that it outputs the entire matched area of the code for inspection. It also did not have any problems with the commented-out section, or with the other YAML keys I added to the config file. Pretty neat, and something that would be difficult to achieve with a regular grep call.

 

3.1. Matching Specific Actuators

The example above is already quite handy, but it only checks for the wildcard operator. Where semgrep really starts to shine is if we encounter a configuration like this:

Now, for the sake of argument, let's say you are fine with exposing your health endpoint (which can be reasonable in some situations), and you also find it acceptable to expose the Prometheus metrics (I wouldn't recommend it, but you do you). All other actuators should be disabled. But how can we check this using semgrep?

Fairly easily, it turns out. Semgrep has a powerful feature called "Metavariables", which allows you to pull specific parts of the code into a variable that you can then reuse in other parts of the rule. Normally, this would be used to track variables or function names while analyzing source code. However, we can also use it to pull out the list of activated actuators and match them against a list of known-accepted actuators. Here's an annotated rule that does this:

annotated rule

If we run this rule against the configuration shown above, we get the following result:

following result

You will note three things:

  1. The output of the metavariable is a bit bugged - this is a known issue in semgrepat the time of writing, but it is purely cosmetic (internally, the matching works).
  2. We get four matches, which is the expected number for the configuration file above - health and prometheus were ignored, as requested.
  3. Although we defined the rule using the syntax include: [..., $ACTUATOR, ...], it still matched the syntax from the config file, as it knows that the inline list format and the "individual lines prefixed by a dash"-Syntax are equivalent. This semantic knowledge is what makes semgrep so powerful.

 

3.2. Exlcuding Findings

This is already a quite useful pattern. However, maybe your organization actually wants actuators to be active, and simply requires them to be running on a specific port or IP that is not exposed publicly. In that case, a configuration like this would be perfectly acceptable:

So, how can we tell semgrep "please find cases where actuators are active, but not if they are only listening on a specific IP"? Fairly easily, actually. Let's build a rule for that.

rule to find cases where actuators are active

Or maybe you don't actually care which IP the actuator is listening on, as long as a port and IP are explicitly set - maybe because the set of possible allowed IPs is too large, or maybe because you think that if a team is going to go to the trouble of setting these two values, they know what they are doing and don't need your handholding. In this case, simply change the pattern-not to the following:

In this case, you simply tell semgrep "hey, I don't actually care what the values of the two metavariable are, just make sure they are present". As a bonus, semgrep knows that the order of keys in YAML doesn't matter, so you don't have to worry about what happens if the two keys are in a different order in the config file - semgrep will find them.

 

4. Conclusion

We could go on for quite a while in refining these patterns, but in the end, you will have to adapt them to your own situation. For example, maybe you are securing your Actuators using Spring Security, and simply need to check if the correct authentication requirements are configured. Or maybe you are exposing all active actuators, but have turned off most actuators that are enabled by default. All of these things can be checked with semgrep, if you know how to write the rules.

I would be remiss if I did not mention one limitation of semgrep: Currently, the semantic features of semgrep are not yet available for all programming languages. In particular, this is the reason why I worked with YAML configuration files for Spring in this article - going through the plain-text properties format would be a lot more annoying with semgrep, as you cannot use the implicit hierarchy that YAML gives you to structure your queries. You can still write semgrep rules against these files using the generic language model, but it is subject to some limitations. I recommend playing around with it to see if you can get your use case to work - the semgrep playground allows you to do so without installing anything on your device.

I have contributed the rules from this article (written in a slightly nicer way that would have taken a bit longer to explain, so I opted to go with simpler rules for this article) to the semgrep rule registry, including a rule that uses the generic mode to find Actuator activations in .properties files. You can find the final rules in this pull request on GitHub.

And as a bonus: If you want to scan a large set of Git repositories with a set of semgrep rules, I wrote about how you can do this using the OWASP secureCodeBox, an Open Source project that I am an active contributor to.

This concludes this part of the Spring Actuator security series. I hope that you have gained some appreciation for the power and flexibility of using static code analysis to aid you in securing your systems. In the next part, we will discuss how to find actuators in deployed software using dynamic testing.

Further Reading:

Once again, I would like to thank the Security Community at my employer, iteratec, for their input on this issue and feedback on the article. Additionally, I would like to thank the Semgrep community on Slack for their help in learning how to write rules - you rock!

 

Fl0YmYCvK.png

Max Maas – Security Expert at iteratec. I break your software before other people do, and then help you secure it afterwards :)

 

Dieser Blogbeitrag erschien ursprünglich auf: https://blog.maass.xyz/spring-actuator-security-part-2-finding-actuators-using-static-code-analysis-with-semgrep

Mehr Infos und weitere interessante Beiträge unter: https://blog.maass.xyz

Tags: Cyber Security

Verwandte Artikel

Voraussichtlich werden dieses Jahr die Ausgaben für IT-Security in Deutschland die 10 Milliarden Euro Marke knacken. Aus gutem...

Mehr erfahren

Topics: Cyber Security

Infolge einer wachsenden Bedrohungslage investieren Unternehmen immer mehr in Cyber Security.  Welche Rolle spielt dabei das ...

Mehr erfahren

Topics: Cyber Security

Wenn ich als Security-Berater in Projekte komme und nach dem Threat Model frage, ist die Antwort häufig: „Haben wir eingeplant!...

Mehr erfahren

Topics: Cyber Security