Table of Content

Log4j Vulnerability CVE-2021-45046 Now a Critical 9.0

Log4j Vulnerability CVE-2021-45046 Now A Critical 9.0

Table of content

By: Hagai Wechsler, Vulnerability Researcher, and Shuki Avraham, Senior Algorithm Developer

*December 16 Update:

On Thursday, December 16, 2021, CVE-2021-45046 was updated with a new, critical CVSS score. As stated by Apache’s security team:

The original severity of this CVE was rated as Moderate; since this CVE was published security experts found additional exploits against the Log4j 2.15.0 release that could lead to information leaks, RCE (remote code execution) and LCE (local code execution) attacks.

CVSS Score was consequently changed from a Low 3.7 to a Critical 9.0. Following CVE-2021-44228, Log4j 2.15.0 disabled message lookups by default and blocked any lookup that attempted to connect to a remote host.

However, not long after this patch, it was discovered that other vectors to inject user-controlled data to log messages are possible, which introduced Log4Shell’s little brother, CVE-2021-45046. The last stated that by using:

ThreadContext.put("lookup-key",attackerControlled);

an attacker can insert malicious data that will be evaluated by the context lookup functionality, using the:

[${ctx:lookup-key}]

format within a layout pattern as follows:

appender.console.layout.pattern = %d{MM:dd HH:mm:ss.SSS} [%t] [%level] [${ctx:lookup-key}] - %msg%n

Since the patched 2.15.0 allowed only local connections in message lookups, this significantly reduced the severity of the then-newly published CVE. 

Out of the possible exploits of this vulnerability, the most influential was a DoS (denial-of-service) attack, done by setting the attacker controlled lookup value to the lookup key itself, causing an infinite lookup loop.

On Dec 16th, at 13:02 UTC, and Dec 17th at 07:15 UTC, @pwntester, @_atorralba, and @marcioalm’s announcements on Twitter disclosed that an RCE is still present in 2.15.0 under certain conditions. It turns out that there is a bypass for the disabled lookup patch, making a remote lookup connection still possible.

@marcioalm explained how this payload works:

This happens because of how the check was done. The http://java.net.URI getHost() method returns the value before the # as the real host, but the JNDI/LDAP resolver will resolve to the full hostname string attempting to connect to the malicious LDAP server.

An important note is that on 2.15.0, message text lookups are disabled by default, so only applications which explicitly enable:

%m{lookups}

in the message log are vulnerable to RCE.

Applications which use the 2.15.0:

formatMsgNoLookups=true

mitigation, are only vulnerable to code execution using one of the methods presented in CVE-2021-45046, meaning through non-message parts of the pattern layout. These include the earlier discussed

ThreadContext

context lookup, as well as other methods mentioned in one of @pwntester’s comments on his thread.
However, as it now seems, this ‘#’ bypass, and the consequent RCE, is reproducible only in MacOS environments, and by using a non-default DNS provider. This was stated in Apache’s official advisory, as well as in various comments in the relevant Twitter threads (1, 2, 3)

Once again, Log4j users are strongly recommended to update to the latest 2.16.0, which removed the vulnerable lookup features altogether, as well as disabled JNDI by default.

***

As security and development teams rushed to assess the now-notorious Log4Shell vulnerability published December 10 (CVE-2021-44228), another, more minor vulnerability was discovered in Log4j — CVE-2021-45046.

To understand the newly-discovered vulnerability, it is important to get the full picture and background on the original Log4j issue

For those who want a quick recap — Log4shell boils down to the following:

  • Logs are an integral part of an application. They document any important event and action that happens within their embedding app, including actions of the application’s users. 
  • This means that in some part of an app, user-provided input is logged, and that any user has the ability to control a portion of an application’s log.
  • Log4j enabled a feature that let it parse and interpret logs that contain requests to remote servers. This was added as a way to create dynamic content in a log.

The above three points combined form a fatal combination from an app’s perspective:

Any user is most likely able to control some portion of an application’s log, and include an arbitrary call to any remote server, forcing the application to execute any data the remote server responds with.

The fix is pretty straightforward. In Log4j versions 2.15.0 and up, these types of requests to remote servers are ignored and are no longer interpreted by Log4j. Users might still control a portion of a log’s data, but this data is by no means executed or parsed in any way anymore.

Or is it?

Introducing Log4j Vulnerability CVE-2021-45046

A few days after the fix to Log4Shell was published, another feature of Log4j was discovered as prone to exploits, and its vulnerability was given the formal ID of CVE-2021-45046.

Unsurprisingly, it eventually relates to the same problem as Log4Shell — users can control a log’s data, and this log data is interpreted by Log4j at runtime. Maliciously crafted user input could cause damage to an application, even one which is not vulnerable to Log4Shell.

What is this vulnerable feature? What can the exploit achieve? Which Log4j versions are vulnerable? And most importantly: What should you do about it?

CVE-2021-45046 Explained

Log4j enables log patterns as a way to add meta-data to a log message. This enriches the log message with some content that is dynamically determined at runtime, such as date, time, log level, thread id, etc. Note for now that all these are system- and application-controlled data, not affected by a user.

Example of a CVE-2021-45046 Exploit

Consider the following demo application:

CVE-2021-45046 — Severity, Impact, and Risks

The vulnerability was given a low severity score of 3.7, according to the CVSS specification.

In comparison, the score given to Log4shell is 10.

Let’s break it down, to see why the severities are so different from each other. 

The CVSS metrics that differ between the two CVEs are:

  • Attack Complexity:

In order for an attacker to exploit the Context lookup vulnerability, the following conditions must be met:

  • The application uses user-supplied data as the Thread Context Map lookup.
  • The application uses a non-default layout pattern.
  • The attacker needs to know the variable key that is used in the Context lookup (in our case, username)

The suitable attack complexity value is High.

For Log4shell, the only thing an attacker needs is control over any data that is logged anywhere in the application. The suitable value for this case is Low.

  • Impact (Confidentiality, Integrity, and Availability) 

The three metrics revolve around how severe the impact of the exploit is — how it can affect the application, and to what extent.

In Log4shell, a successful exploit would force the vulnerable application to execute arbitrary code. This could mean credentials leak, full data integrity loss, database drop, or application crash. It is thus given the expected High impact on all three metrics.
On the other hand, the Context lookup vulnerability can only result in an infinite loop, which could cause excessive resources consumption and application crash. That’s why it was given the Low impact on Availability score, but no impact score on Confidentiality or Integrity.

The Fix: Remediation Recommendations for CVE-2021-45046

Log4j versions 2.16.0 and 2.12.2 (for older Java versions), completely removed the message lookups feature. This means that log patterns now cannot hold dynamic content from a thread context and consequently do not perform lookups on context variables. Thus, user-supplied data is not interpreted by the application, and specifically Log4j, anymore.

Remediation: 

Log4j version 2.16.0 solved this vulnerability by disabling the variable lookup by default. 

If you cannot update to the new version, the official Apache advisory recommends that you remove the JndiLookup class from the classpath: zip -q -d log4j-core-*.jar org/apache/logging/log4j/core/lookup/JndiLookup.class.

Learn More: Get free tools to detect and fix Log4j vulnerabilities at our Log4j Vulnerability Resource Center.

Keeping Your Open Source Components Secure

If the past week has taught us anything, it is that it’s crucial to stay on top of our open source components at all times. 

In order to make sure that your dependencies are updated and secure, we recommend you to: 

– Keep your open source components up to date with tools like Mend Remediate to make sure direct dependencies are automatically patched to the latest version.

– Add an integration to your repository, so that when a vulnerability is detected, you get a GitHub issue and a PR is opened automatically. 

Integrating automated security into your repo, so that issues are addressed as soon as possible, is the best way to mitigate open source risks early, before they hit the headlines. 

Want to find and fix vulnerable versions of Log4j in your code? Learn about our free CLI tool, or download it now.

Manage open source application risk

Recent resources

All About RAG blog

All About RAG: What It Is and How to Keep It Secure

Learn about retrieval-augmented generation, one complex AI system that developers are using.

Read more
AI and AWS blog 1

Next-Gen Vulnerability Assessment: AWS Bedrock Claude in CVE Data Classification

Learn more about how organizations can use open source software to innovate while minimizing risk.

Read more
A quick Guide to Open Source software

A Guide to Open Source Software

Learn more about how organizations can use open source software to innovate while minimizing risk.

Read more