Skip to content

Commit 59b4055

Browse files
committed
Add security threat model to docs
This updates the security page with notes about the threat model used for Log4j. Some related documentation has been fixed during review of this threat model.
1 parent 8bbc085 commit 59b4055

File tree

3 files changed

+89
-5
lines changed

3 files changed

+89
-5
lines changed

src/site/asciidoc/download.adoc.vm

Lines changed: 4 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -20,7 +20,7 @@
2020
<link rel="stylesheet" type="text/css" href="css/tables.css">
2121
++++
2222

23-
Apache Log4j 2 is distributed under the
23+
Apache Log4j 3 is distributed under the
2424
https://www.apache.org/licenses/LICENSE-2.0.html[Apache License, version 2.0].
2525

2626
The link in the Mirrors column should display a list of available
@@ -59,7 +59,7 @@ Server Releases] for more information on why you should verify our
5959
releases.
6060

6161
The PGP signatures can be verified using PGP or GPG. First download the
62-
https://www.apache.org/dist/logging/KEYS[KEYS] as well as the asc
62+
https://downloads.apache.org/logging/KEYS[KEYS] as well as the asc
6363
signature file for the relevant distribution. Make sure you get these
6464
files from the https://www.apache.org/dist/logging/[main distribution
6565
directory], rather than from a mirror. Then verify the signatures using
@@ -87,11 +87,12 @@ use as dependencies from the https://search.maven.org/search?q=org.apache.loggin
8787

8888
== Using Log4j on your classpath
8989

90-
To use Log4j 3.x in your application make sure that both the API and Core
90+
To use Log4j 3.x in your application make sure that the API, Plugins, and Core
9191
jars are in the application’s classpath. Add the dependencies listed
9292
below to your classpath.
9393

9494
* log4j-api-${Log4jReleaseVersion}.jar
95+
* log4j-plugins-${Log4jReleaseVersion}.jar
9596
* log4j-core-${Log4jReleaseVersion}.jar
9697

9798
You can do this from the command line or a manifest file.

src/site/asciidoc/manual/layouts.adoc

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -686,7 +686,7 @@ Using the HTML encoding format, the following characters are replaced:
686686
!Character !Replacement
687687
688688
!'\r', '\n'
689-
!Converted into escaped strings "\\r" and "\\n" respectively
689+
!Converted into string literals "\r" and "\n" respectively
690690
691691
!&, <, >, ", ', /
692692
!Replaced with the corresponding HTML entity
@@ -731,7 +731,7 @@ Using the CRLF encoding format, the following characters are replaced:
731731
!Character !Replacement
732732
733733
!'\r', '\n'
734-
!Converted into escaped strings "\\r" and "\\n" respectively
734+
!Converted into literal strings "\r" and "\n" respectively
735735
!===
736736
737737
|*equals*{pattern}{test}{substitution} +

src/site/asciidoc/security.adoc

Lines changed: 83 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -46,6 +46,89 @@ If you have encountered an unlisted security vulnerability or other unexpected b
4646
The threat model that Log4j uses considers configuration files as safe input controlled by the programmer; **potential vulnerabilities that require the ability to modify a configuration are not considered vulnerabilities** as the required access to do so implies the attacker can execute arbitrary code.
4747
====
4848
49+
[#model]
50+
== Threat Model
51+
52+
Log4j is a low level library where configuration inputs and the classpath are expected to be controlled by the programmer.
53+
Configurations have the ability to execute arbitrary code through custom plugins.
54+
While specific Log4j plugins (such as a JNDI lookup) may use constraint validators or conditionals to require additional settings to opt in to functionality, this is not universally required by custom plugins.
55+
Specific security considerations involved in our threat model are detailed below.
56+
57+
=== Parameterized Logging
58+
59+
When using a log message containing template parameters like `{}`, only the format string is evaluated for parameters to be substituted.
60+
The message parameters themselves are not evaluated for parameters; they are only included in the format string corresponding to their template position.
61+
The conversion of message parameters into a string is done on-demand depending on the layout being used.
62+
When structure-preserving transformations of log message data are required, the `Message` API should be used for logging structured data.
63+
64+
=== Unstructured Logging
65+
66+
When using an unstructured layout such as `PatternLayout`, no guarantees can be made about the output format.
67+
This layout is mainly useful for development purposes and should not be relied on in production applications.
68+
For example, if a log message contains new lines, these are not escaped or encoded specially unless the configured pattern uses the `%encode{pattern}{CRLF}` wrapper pattern converter (which will encode a carriage return as the string `\r` and a line feed as the string `\n`) or some other `%encode` option.
69+
Similarly, other encoding options are available for other formats, but pattern layouts cannot make assumptions about the entire output.
70+
As such, when using unstructured layouts, no user-controlled input should be included in logs.
71+
It is strongly recommended that a structured layout is used instead for these situations.
72+
Note that `StrLookup` plugins (those referenced by `${...}` templates in configuration files) that contain user-provided input should not be referenced by a pattern layout.
73+
74+
=== Structured Logging
75+
76+
When using a structured layout (most layouts besides pattern layout), log messages are encoded according to various output formats.
77+
These safely encode the various fields included in a log message.
78+
For example, the JSON template layout can be configured to output log messages in various JSON structures where all log data is properly encoded into safely parseable JSON.
79+
This is the recommended mode of operation for use with log parsing and log collection tools that rely on log files or arbitrary output streams.
80+
81+
=== Code Signing
82+
83+
Log4j artifacts are all signed using PGP using a key from the Logging Services PMC https://downloads.apache.org/logging/KEYS[KEYS file].
84+
Information on how to verify releases signed with PGP is https://httpd.apache.org/dev/verification.html[documented here].
85+
Individual jar files are not signed using `jarsigner` (only PGP), and the Log4j plugin system does not rely on signed jars for validation (unlike the Java cryptography APIs for example).
86+
Thus, PGP signatures should be validated in your build process.
87+
88+
=== Java Security Manager
89+
90+
Log4j no longer supports running in or using a custom `SecurityManager`.
91+
This Java feature has been deprecated for removal in Java 21.
92+
Previous versions of Log4j 2.x include partial support for running with a security manager.
93+
94+
=== Log Masking
95+
96+
Log4j, like any other generic logging library, cannot generically support log masking of sensitive data.
97+
While custom plugins may be developed to attempt to mask various regular expressions (such as a string that looks like a credit card number), the general problem of log masking is equivalent to the halting problem in computer science where sensitive data can always be obfuscated in such a way as to avoid detection by log masking.
98+
As such, it is the responsibility of the developer to properly demarcate sensitive data such that it can be consistently masked by log masking plugins.
99+
This sort of use case should make use of the `Message` API for better control over the output of such data.
100+
101+
=== Availability
102+
103+
Log4j goes to great lengths to minimize performance overhead along with options for minimizing latency or maximizing throughput.
104+
However, we cannot guarantee availability of the application if the appenders cannot keep up with the logs being written.
105+
Synchronous logging can cause applications to block and wait for a log message to be written.
106+
Asynchronous logging can also cause applications to block and wait depending on the wait strategy and queue full policy configured.
107+
Configuring too large or too many buffers in Log4j can also result in out of memory errors.
108+
109+
=== Configuration Sources
110+
111+
All configuration sources to an application must be trusted by the programmer.
112+
When loading a configuration file from disk (especially when a monitor interval is configured to reload the file periodically), the location of the configuration file must be kept safe from unauthorized modifications.
113+
Similarly, when loading a configuration file over the network such as through HTTP, this should be configured to use TLS or a secure connection in general with strong authentication guarantees.
114+
This remote location must be kept safe from unauthorized modifications.
115+
When configurations are modified through JMX, the JMX server should be safely configured to require authentication and a secure connection if being accessed over the network.
116+
When configurations are provided through JNDI, these should only use the `java` scheme for sharing configurations in a JavaEE or JakartaEE application service.
117+
JNDI-sourced configurations should not use other JNDI providers such as LDAP, DNS, or RMI, as all these providers are difficult to properly secure.
118+
119+
=== Cryptographic Logs
120+
121+
When using custom plugins to calculate message authentication codes, signatures, or encrypted logs, proper key management must be considered.
122+
Cryptography is a tricky subject, and key management lies at the heart of most design problems to solve when using it.
123+
If a custom plugin relies on a pre-shared key or password of some sort, it is likely broken beyond repair if being used for cryptographic purposes.
124+
Proper key management typically uses public key infrastructure (PKI) such as X.509 certificates, though this is not the only option.
125+
It is beyond the scope of Log4j to implement key management as this would depend on other infrastructure in use for validating or decrypting logs combined with the deployment and runtime environment of the logging application.
126+
127+
=== Compressing Logs
128+
129+
If log compression is used along with custom encryption where logs contain user-controlled input, then this can lead to a https://en.wikipedia.org/wiki/CRIME[CRIME attack] style vulnerability where a chosen-plaintext attack is combined with information leakage caused by how the compression algorithm handles different inputs.
130+
The simplest way to avoid this problem is to never combine compression with encryption when encoding user-controlled input.
131+
49132
[#policy]
50133
== Vulnerability handling policy
51134

0 commit comments

Comments
 (0)