Security

Runtime SCA and ADRs: Focusing On What Matters

Vulnerabilities are everywhere and here to stay. Defects can exist in source code or third-party and open-source software. However, not all vulnerabilities pose the same threat, and code that is exploitable in one context may not be exploitable in another. Focusing on what matters is crucial for remediation and prioritization,

10 min read
Runtime SCA and ADRs: Focusing On What Matters

Vulnerabilities are everywhere and here to stay. Defects can exist in source code or third-party and open-source software. However, not all vulnerabilities pose the same threat, and code that is exploitable in one context may not be exploitable in another. Focusing on what matters is crucial for remediation and prioritization, otherwise, you risk becoming quickly overwhelmed.

Since Log4j, SolarWinds, Spring4Shell, and more recently XZ Utils backdoor, managing software supply chain risk has become urgent. When Spring4Shell emerged (March 2022), most organizations were drawn into an emergency state. However, the vulnerability is not applicable to every jvm application packaging the defected dependency. In fact, the vulnerable path exists and is triggered only if you are running on JDK 9 or higher (where java modules were introduced and an attacker could get access and set critical fields during unmarshalling of a web request), you are using Apache Tomcat as the servlet container, and your application is packaged as a traditional WAR deployed in a standalone Tomcat instance. Typical Spring Boot deployments using an embedded servlet container or reactive web server (Spring Webflux/Netty) are not even impacted. Most people rushed to patch the dependency (spring core) without knowing if they were truly impacted.

While cloud-native infrastructures promote faster development and deployment, and better fault tolerance, they also bring a whole set of new challenges, including architectural complexity and observability. We are losing visibility on what we are truly using, and security hates complexity.

Open source software (OSS) accelerates the development process. Now, with frameworks like Spring Boot or Quarkus, you can develop and deploy a web application in minutes/hours. However, incorporating open source components introduces significant risks to the software supply chain, from zero-day vulnerabilities to backdoored libraries, which can jeopardize your entire business. Despite this, many organizations still neglect open-source and API security risking both reputational and financial damage. Gartner predicts that by 2027, more than 70% of enterprises will use industry cloud platforms to accelerate their business initiatives [3]. 

Software Bill of Materials (SBOM)

SBOMs are inventories of all the software components used to create a particular software product. This includes information such as the name, version, and supplier of each software component, as well as any dependencies between them.

Recent zero days including Spring4Shell and Log4Shell have reinforced the importance of keeping track of the software components we use. If we don’t properly assess the impact of vulnerabilities, bad things can happen. It’s sad to realize that something bad could have been avoided if we had been more vigilant.

SBOM can help to some extent, for example, to locate which components are affected by a new vulnerability and need patching. SBOMs are not only for vulnerability management but also for managing licensing, compliance, and risk management, and for responding in case of a supply chain incident. SBOMs can be implemented in different formats, including SPDX and CycloneDX. Now, most SCA tools include SBOM generation out of the box [1].

SBOMs aren't enough

While a SBOM gives you visibility into what constitutes your artifact and which third-party libraries you are granting complete trust, it is not enough. It is merely a means to increase visibility and transparency of the software supply chain. Without context, it is not truly effective.

SBOMs are typically cross-referenced with a database of known vulnerabilities (SCA). Often, people focus on critical vulnerabilities and then proceed to production. Unfortunately, this is not the best approach. Not only may critical vulnerabilities be unreachable and thus unexploitable, but there may also be high-severity vulnerabilities that are easily reachable and should have deserved your attention.

Application Security Testing (AST)

Application Security Testing or AST is a process that involves analyzing the security of applications and systems by looking for potential vulnerabilities and threats. It is designed to detect and prevent potential security risks before they can be exploited (shift security left).

Static Application Security Testing (SAST)

Static application security testing (SAST) is a white box security testing tool that analyzes application source code, bytecode or binaries for coding and design conditions that may indicate security vulnerabilities. SAST solutions ensure compliance with coding guidelines and standards without executing the underlying code, which allows us to analyze applications from the inside out in a non-running state.

With SAST, you can protect against some common security defects hidden in source code at low cost, such as OWASP TOP 10 (e.g SQLi, Command Injection etc). At the same time, the exact location of the vulnerability may be pointed out.

However, with SAST, there is an outrageous false alarm rate and you have to spend a lot of time denoising outputs. Most SAST tools allow to tune scanners in order to reduce the amount of false alarms.

Finally, vanilla SAST only covers your application code, this is why most commercial and open source SAST products offer Software Composition Analysis (SCA), an additional resource for using external components and libraries securely.

Software Composition Analysis (SCA)

By using free and open-source software, developers are able to produce software more efficiently. There is, however, a risk attached to this (no free lunch). These open-source components and frameworks may contain malicious code and vulnerabilities that could compromise a whole company.

Furthermore, many of these open source libraries depend on other open source projects. This ships a whole dependency chain into the company.

Software Composition Analysis (SCA) has been around for a while. It identifies potential vulnerabilities in open source components and third-party libraries, frameworks, plugins, and components used in your application.

SCA tools are intended to consider all code that is not produced by you and your team. In contrast to DAST, IAST and FAST, SCA tools don’t run security scans while the app is running. The SCA tools instead analyze dependencies, cross-reference them with the list of known-vulnerable dependencies, and report the matching dependencies.

What Is The Problem With Traditional SAST and SCA ?

Both SCA and SAST tools do not leverage application context and lack a holistic view, which can generate an unmanageable amount of alerts. If you are a software or application security engineer, you know that can be quite overwhelming, sometimes leading to indecision (to go or not to go). You don't even know if what you are fixing really matters.

Imagine spending hours or days fixing something only to find out it was just a waste of time, like a vulnerability in code that is not exploitable or even loaded in memory. You could have spent that time developing features.

We need context. CONTEXT has always been KING.

We need something that tells us if the vulnerable path is loaded, accessible, or used at runtime. This is where runtime context and reachability analysis come into play. Instead of only focusing on shifting security left, we should also combine it with runtime context to provide a comprehensive view.

By knowing if a class is loaded or if a vulnerable function is reachable at runtime, you can cut out most of the noise and focus on what truly deserves your energy.

For example, in the case of Spring4Shell, the exploit manipulates a class loader to deliver a JSP file, which turns into a backdoor. Using instrumentation, you can determine if the Tomcat class loader has been manipulated and even block it before damage is done. Some RASP solutions already block attempts to manipulate known targeted class loaders.[https://www.contrastsecurity.com/security-influencers/qa-how-does-the-new-contrast-protect-classloader-manipulation-rule-block-spring4shell-and-future-exploits].

One of my previous articles: https://research.kudelskisecurity.com/2022/04/05/spring4shell-a-deep-understanding-cve-2022-22965/

Marrying Runtime Context with SCA: Meet Runtime SCA

SCA can be provided both in the codebase as well as in runtime. Runtime SCA consists of using runtime context to better prioritize CVE remediation, adding dimensions such as whether the vulnerability path or lib is loaded/reachable/exploitable/used at runtime. These context-aware insights can be collected either through instrumentation, such as developing a JVM TI or Java agent like IAST, or by using eBPF.

However, one needs to pay attention to one crucial thing: your runtime SCA may yield misleading results. A vulnerability may be flagged as used or reachable only when something triggers the path leading to it. This means you need to ensure that all possible paths are exercised before trusting its results (the same problem exists with IAST or Interactive Application Security Testing). Some may combine runtime SCA with static analysis to form a more comprehensive solution.

Reachability

Reachability is not really something new [2] and is key to ensuring that your energy on CVE remediation is properly spent. Reachability indicates if an application's execution path can reach a vulnerable function (reachable does not imply exploitable). It can operate at the package, module or function level, indicating whether a package, module or function is reachable.

Reachability can be determined either by analyzing call graphs at build time, at runtime using instrumentation or eBPF, or both.

With modern frameworks, there are features enabling dynamic loading of classes at runtime (e.g. via reflection). This allows invoking methods absent from the application’s source code, creating a level of flexibility and dynamism. However, this sophistication poses a significant challenge for offline reachability analysis, rendering it incomplete due to the unpredictable nature of runtime behavior.

For more details, you can read James Berthoty's excellent articles about reachability:

Runtime Usage

Your application might include several vulnerable dependencies. Knowing if the library in question is actually used at runtime is crucial. If it is, then fixing this vulnerability should be a top priority.

Navigating CVEs in Oligo: https://www.oligo.security/product/oligo-focus
Navigating CVEs in Raven https://www.raven.io

Runtime Protection / ADR - Surviving Unpatched Vulns

What is also interesting and comforting, apart from knowing that you are truly vulnerable or exploitable, is knowing that the vulnerable path is sealed and can't be abused by an attacker. In fact, Runtime SCA won’t protect you from known and zero-day vulnerabilities such as Log4Shell, and this is why some ADRs (or RASP if you want) provide not only detection but also prevention, like Oligo, which protect against zero-day attacks (similar to RASP; some ADRs can only detect/respond). In Oligo, any deviation from a baseline can reveal new vulnerabilities or backdoors.

https://www.oligo.security

Other ADRs, like Raven, have the capability to deploy virtual patches when an official fix is not yet available.

https://www.raven.io

With ADRs/RASP, you can survive unpatched vulnerabilities and relax for the weekend.

Conclusion

As mentioned earlier, software today is shipped with a large number of open-source components, which can be infected with known defects. SCA helps you uncover dependencies along with their vulnerabilities. In contrast to SAST, which primarily focuses on your main application code, SCA focuses on dependencies. Most SAST tools today are complemented with SCA.

Almost every organization uses open-source projects for various reasons. As a result, organizations must govern the use of the open software supply chain to reduce risks associated with it.

Neither runtime SCA nor static SCA is a silver bullet. The first may miss things, while the second is challenging and has to deal with dynamically loaded code. We need static and dynamic analysis and SCA together.

To conclude, application context and dynamic observability are essential. It is necessary to be present at runtime and cover both infrastructure and applications simultaneously, from edge to runtime, and from sources to sinks.

If you think I missed something, please reach out.

References and Further Reading

[1] https://jfrog.com/help/r/jfrog-security-documentation/xray-sbom-report

[2] https://www.veracode.com/blog/managing-appsec/vulnerable-methods-under-hood

[3] https://www.gartner.com/en/newsroom/press-releases/2024-06-05-the-expanding-enterprise-investment-in-cloud-security

On Loaded vs. Executed Libraries During Runtime | Oligo Security
The Application Security domain has evolved significantly over the last decade. It’s no surprise then, that with this evolution, comes a jungle of tools that not only causes a lot of confusion, but also a lot of noise, and overlapping messages.
What Is A Better Way To Do Software Composition Analysis (SCA)? | Oxeye
Software Composition Analysis (SCA) is a fundamental component of application security, aiming to identify vulnerabilities within third-party libraries and dependencies. However, while SCA tools have come a long way, they are not always accurate enough on their own.
Security Scanning Tools Defined: SAST, IaC, SCA, DAST, IAST/RASP, Container Runtime Security and Runtime SCA
Discover how Deepfactor’s security scanning tools combine static & runtime scanning to prioritize vulnerabilities based on true risk.

https://www.endorlabs.com/learn/static-sca-vs-dynamic-sca-which-is-better-and-why-its-neither

Proving reachability: Static analysis vs Runtime detection
Static program analysis (static analysis) is a technique to analyze software source code, configuration, and its Bill of Materials statically without executing or deploying the application or service. In contrast, runtime detection is performed by tracing and monitoring the behavior of an application or service after building, deploying, and executing them in an appropriate environment.

https://www.reversinglabs.com/blog/sca-is-key-but-no-substitute-for-comprehensive-software-supply-chain-security

https://www.backslash.security/post/proving-reachability-static-analysis-vs-runtime-detection

Application Detection & Response (ADR) | Miggo
See, understand and control live applications: Miggo’s ADR platform stops attacks in their tracks with in-application context into all runtime transactions and behaviors.

Share This Post

Check out these related posts

Profiling Libraries With eBPF: Detecting Zero-Day Exploits and Backdoors

Smashing Runtime Application Self-Protection (RASP)

How ADRs solve the the last mile problem of application security