A new vulnerability in the Apache Commons Text, AKA Text4Shell, allows an attacker to execute arbitrary code on the host machine. Originally reported by Alvaro Munoz, principal security researcher at GitHub, CVE-2022-42889 is similar to Spring4Shell and Log4Shell, allowing remote code execution (RCE).
The CVSSv3 system scores the vulnerability at 9.8 with critical severity as it is easily exploitable, and the impact of getting access to the underlying host could potentially affect the reliability and availability of the system. However, it will not have the same broad impact as Log4Shell, for example, since the vulnerability exists in the StringSubstitutor
class, which is not a common method but is restricted to a specific use case.
Apache Commons Text is a commonly used Java library that provides additional algorithms for String manipulation to developers.
As the name suggests, the StringSubstitutor
class replaces and substitutes values within a given String value. Consider the following example:
StringSubstitutor
.replaceSystemProperties("You are running with java.version = ${java.version} and os.name = ${os.name}.");
The above code contains the ${java.version}
and ${os.name}
that will be replaced by the Java system property. StringSubstitutor
uses interpolation, allowing multiple expressions to substitute Strings. An attacker can use the default Interpolator to execute remote code, for example, using the StringSubstitutor.createInterpolator()
. method.
More specifically, an attacker will have the possibility to inject malicious code during lookups like replace()
or replaceIn()
. This is because "dns", "script" and "url" lookup keys are interpolated by default rather than conforming to the documentation for the StringLookupFactory
class.
In the following example, an attacker could easily access the underlying shell by providing "script" and executing arbitrary code on the host machine.
final StringSubstitutor interpolator = StringSubstitutor.createInterpolator();
String out = interpolator.replace("${script:javascript:java.lang.Runtime.getRuntime().exec('touch /tmp/CVE-2022-42889')}");
System.out.println(out);
The payload is composed with ${prefix:name}
, ensuring a StringLookup
and thereby executing code remotely on the host shell.
To avoid being affected by CVE-2022-42889, developers should upgrade to Apache Commons Text 1.10 or later. Developers can also use a special checklist, as shown below, to ensure that they do not have an earlier version than 1.10.
- Check source code for the
StringSubstitutor
class and default interpolation method,StringSubstitutor.createInterpolator()
. - Ensure that the dependency isn’t included in a Maven or Gradle build and packaging system.
- Ensure that deployment machines and containers do not have this dependency JAR in the classpath.
- Check container images. Usually, this can be achieved via running container scans.
- Check automated builds. Often, there are external systems building and sanity-checking developer code. Ensure that the binary does not exist in the build system itself and that the output does not include it.