You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@logging.apache.org by ma...@apache.org on 2023/10/16 01:07:44 UTC

[logging-log4j2] branch main updated (85d3a9832d -> 2156eee8d1)

This is an automated email from the ASF dual-hosted git repository.

mattsicker pushed a change to branch main
in repository https://gitbox.apache.org/repos/asf/logging-log4j2.git


    from 85d3a9832d Fix NPE in AbstractFilterable::removeFilter
     new 6a75890e3e Remove redundant cast
     new bcc91d979b Replace NullOutputStream with OutputStream::nullOutputStream
     new 2156eee8d1 Replace IOUtils with standard Java functions

The 3 revisions listed above as "new" are entirely new to this
repository and will be described in separate emails.  The revisions
listed as "add" were already present in the repository and have only
been added to this reference.


Summary of changes:
 .../java/org/apache/log4j/xml/DOMConfigurator.java |  16 +--
 .../SecureSocketAppenderSocketOptionsTest.java     |   4 +-
 .../appender/SocketAppenderSocketOptionsTest.java  |   9 +-
 .../core/appender/RandomAccessFileManagerTest.java |  12 +-
 ...llingAppenderDirectWriteWithHtmlLayoutTest.java |  26 ++---
 .../appender/rolling/RollingFileManagerTest.java   |  10 +-
 .../RollingRandomAccessFileManagerTest.java        |   7 +-
 .../core/appender/HttpURLConnectionManager.java    |  11 +-
 .../core/appender/MemoryMappedFileManager.java     |   3 +-
 .../log4j/core/appender/OutputStreamAppender.java  |   3 +-
 .../core/appender/RandomAccessFileManager.java     |   3 +-
 .../rolling/RollingRandomAccessFileManager.java    |   3 +-
 .../log4j/core/filter/AbstractFilterable.java      |   3 +-
 .../logging/log4j/core/net/TcpSocketManager.java   |   9 +-
 .../apache/logging/log4j/core/util/IOUtils.java    | 130 ---------------------
 .../logging/log4j/core/util/NullOutputStream.java  |  86 --------------
 .../apache/logging/log4j/script/ScriptFile.java    |   6 +-
 17 files changed, 58 insertions(+), 283 deletions(-)
 delete mode 100644 log4j-core/src/main/java/org/apache/logging/log4j/core/util/IOUtils.java
 delete mode 100644 log4j-core/src/main/java/org/apache/logging/log4j/core/util/NullOutputStream.java


[logging-log4j2] 01/03: Remove redundant cast

Posted by ma...@apache.org.
This is an automated email from the ASF dual-hosted git repository.

mattsicker pushed a commit to branch main
in repository https://gitbox.apache.org/repos/asf/logging-log4j2.git

commit 6a75890e3efa549856791f9574fc22a0ea0f0865
Author: Matt Sicker <ma...@apache.org>
AuthorDate: Sun Oct 15 19:31:44 2023 -0500

    Remove redundant cast
    
    Signed-off-by: Matt Sicker <ma...@apache.org>
---
 .../java/org/apache/logging/log4j/core/filter/AbstractFilterable.java  | 3 +--
 1 file changed, 1 insertion(+), 2 deletions(-)

diff --git a/log4j-core/src/main/java/org/apache/logging/log4j/core/filter/AbstractFilterable.java b/log4j-core/src/main/java/org/apache/logging/log4j/core/filter/AbstractFilterable.java
index 3bc1dc9e86..6c5f91df1b 100644
--- a/log4j-core/src/main/java/org/apache/logging/log4j/core/filter/AbstractFilterable.java
+++ b/log4j-core/src/main/java/org/apache/logging/log4j/core/filter/AbstractFilterable.java
@@ -22,7 +22,6 @@ import java.util.concurrent.locks.ReentrantLock;
 
 import org.apache.logging.log4j.core.AbstractLifeCycle;
 import org.apache.logging.log4j.core.Filter;
-import org.apache.logging.log4j.core.LifeCycle;
 import org.apache.logging.log4j.core.LogEvent;
 import org.apache.logging.log4j.core.config.Property;
 import org.apache.logging.log4j.plugins.PluginElement;
@@ -204,7 +203,7 @@ public abstract class AbstractFilterable extends AbstractLifeCycle implements Fi
         }
         boolean stopped = true;
         if (filter != null) {
-            stopped = ((LifeCycle) filter).stop(timeout, timeUnit);
+            stopped = filter.stop(timeout, timeUnit);
         }
         if (changeLifeCycleState) {
             this.setStopped();


[logging-log4j2] 03/03: Replace IOUtils with standard Java functions

Posted by ma...@apache.org.
This is an automated email from the ASF dual-hosted git repository.

mattsicker pushed a commit to branch main
in repository https://gitbox.apache.org/repos/asf/logging-log4j2.git

commit 2156eee8d1b24f6c98745b70193c93391d03a2b7
Author: Matt Sicker <ma...@apache.org>
AuthorDate: Sun Oct 15 20:00:41 2023 -0500

    Replace IOUtils with standard Java functions
    
    Signed-off-by: Matt Sicker <ma...@apache.org>
---
 .../java/org/apache/log4j/xml/DOMConfigurator.java |  16 +--
 ...llingAppenderDirectWriteWithHtmlLayoutTest.java |  26 ++---
 .../appender/rolling/RollingFileManagerTest.java   |  10 +-
 .../core/appender/HttpURLConnectionManager.java    |  11 +-
 .../apache/logging/log4j/core/util/IOUtils.java    | 130 ---------------------
 .../apache/logging/log4j/script/ScriptFile.java    |   6 +-
 6 files changed, 32 insertions(+), 167 deletions(-)

diff --git a/log4j-1.2-api/src/main/java/org/apache/log4j/xml/DOMConfigurator.java b/log4j-1.2-api/src/main/java/org/apache/log4j/xml/DOMConfigurator.java
index 9e5d9374b3..fb914fcedb 100644
--- a/log4j-1.2-api/src/main/java/org/apache/log4j/xml/DOMConfigurator.java
+++ b/log4j-1.2-api/src/main/java/org/apache/log4j/xml/DOMConfigurator.java
@@ -17,10 +17,11 @@
 package org.apache.log4j.xml;
 
 import java.io.ByteArrayInputStream;
+import java.io.ByteArrayOutputStream;
 import java.io.IOException;
 import java.io.InputStream;
+import java.io.OutputStreamWriter;
 import java.io.Reader;
-import java.io.StringWriter;
 import java.net.URL;
 import java.net.URLConnection;
 import java.nio.charset.StandardCharsets;
@@ -40,7 +41,6 @@ import org.apache.logging.log4j.core.config.Configuration;
 import org.apache.logging.log4j.core.config.ConfigurationSource;
 import org.apache.logging.log4j.core.config.Configurator;
 import org.apache.logging.log4j.core.net.UrlConnectionFactory;
-import org.apache.logging.log4j.core.util.IOUtils;
 import org.w3c.dom.Element;
 
 /**
@@ -74,7 +74,7 @@ public class DOMConfigurator {
         final Path path = Paths.get(fileName);
         try (final InputStream inputStream = Files.newInputStream(path)) {
             final ConfigurationSource source = new ConfigurationSource(inputStream, path);
-            final LoggerContext context = (LoggerContext) org.apache.logging.log4j.LogManager.getContext(false);
+            final LoggerContext context = LoggerContext.getContext(false);
             Configuration configuration;
             configuration = new XmlConfigurationFactory().getConfiguration(context, source);
             LogManager.getRootLogger().removeAllAppenders();
@@ -112,7 +112,7 @@ public class DOMConfigurator {
     }
 
     private void doConfigure(final ConfigurationSource source) {
-        final LoggerContext context = (LoggerContext) org.apache.logging.log4j.LogManager.getContext(false);
+        final LoggerContext context = LoggerContext.getContext(false);
         Configuration configuration;
         configuration = new XmlConfigurationFactory().getConfiguration(context, source);
         Configurator.reconfigure(configuration);
@@ -131,9 +131,11 @@ public class DOMConfigurator {
 
     public void doConfigure(final Reader reader, final LoggerRepository repository) throws FactoryConfigurationError {
         try {
-            final StringWriter sw = new StringWriter();
-            IOUtils.copy(reader, sw);
-            doConfigure(new ConfigurationSource(new ByteArrayInputStream(sw.toString().getBytes(StandardCharsets.UTF_8))));
+            final ByteArrayOutputStream out = new ByteArrayOutputStream();
+            final OutputStreamWriter writer = new OutputStreamWriter(out, StandardCharsets.UTF_8);
+            reader.transferTo(writer);
+            final ByteArrayInputStream inputStream = new ByteArrayInputStream(out.toByteArray());
+            doConfigure(new ConfigurationSource(inputStream));
         } catch (final IOException e) {
             throw new FactoryConfigurationError(e);
         }
diff --git a/log4j-core-test/src/test/java/org/apache/logging/log4j/core/appender/rolling/RollingAppenderDirectWriteWithHtmlLayoutTest.java b/log4j-core-test/src/test/java/org/apache/logging/log4j/core/appender/rolling/RollingAppenderDirectWriteWithHtmlLayoutTest.java
index e051a6794a..23e87a4631 100644
--- a/log4j-core-test/src/test/java/org/apache/logging/log4j/core/appender/rolling/RollingAppenderDirectWriteWithHtmlLayoutTest.java
+++ b/log4j-core-test/src/test/java/org/apache/logging/log4j/core/appender/rolling/RollingAppenderDirectWriteWithHtmlLayoutTest.java
@@ -16,10 +16,9 @@
  */
 package org.apache.logging.log4j.core.appender.rolling;
 
-import java.io.BufferedReader;
 import java.io.File;
-import java.io.FileReader;
 import java.io.IOException;
+import java.nio.file.Files;
 import java.util.regex.Matcher;
 import java.util.regex.Pattern;
 
@@ -28,10 +27,8 @@ import org.apache.logging.log4j.core.config.Configuration;
 import org.apache.logging.log4j.core.impl.Log4jLogEvent;
 import org.apache.logging.log4j.core.layout.HtmlLayout;
 import org.apache.logging.log4j.core.test.junit.LoggerContextSource;
-import org.apache.logging.log4j.core.util.IOUtils;
 import org.apache.logging.log4j.message.SimpleMessage;
 import org.apache.logging.log4j.test.junit.CleanUpDirectories;
-import org.hamcrest.Matchers;
 import org.junit.jupiter.api.Tag;
 import org.junit.jupiter.api.Test;
 
@@ -40,7 +37,10 @@ import static org.apache.logging.log4j.core.test.hamcrest.FileMatchers.hasName;
 import static org.hamcrest.MatcherAssert.assertThat;
 import static org.hamcrest.Matchers.endsWith;
 import static org.hamcrest.Matchers.hasItemInArray;
-import static org.junit.jupiter.api.Assertions.*;
+import static org.hamcrest.Matchers.startsWith;
+import static org.junit.jupiter.api.Assertions.assertEquals;
+import static org.junit.jupiter.api.Assertions.assertNotNull;
+import static org.junit.jupiter.api.Assertions.assertTrue;
 
 /**
  * Tests for LOG4J2-2760
@@ -98,15 +98,13 @@ public class RollingAppenderDirectWriteWithHtmlLayoutTest {
             for (File file : files) {
                 if (!file.getName().startsWith(prefix))
                     continue;
-                try (final BufferedReader reader = new BufferedReader(new FileReader(file))) {
-                    final String data = IOUtils.toString(reader).trim();
-                    // check that every file starts with the header
-                    assertThat("header in file " + file, data, Matchers.startsWith("<!DOCTYPE"));
-                    assertThat("footer in file " + file, data, endsWith("</html>"));
-                    final Matcher matcher = eventMatcher.matcher(data);
-                    while (matcher.find()) {
-                        foundEvents++;
-                    }
+                final String data = Files.readString(file.toPath());
+                // check that every file starts with the header
+                assertThat("header in file " + file, data, startsWith("<!DOCTYPE"));
+                assertThat("footer in file " + file, data, endsWith("</html>"));
+                final Matcher matcher = eventMatcher.matcher(data);
+                while (matcher.find()) {
+                    foundEvents++;
                 }
             }
             assertEquals(count, foundEvents, "Incorrect number of events read.");
diff --git a/log4j-core-test/src/test/java/org/apache/logging/log4j/core/appender/rolling/RollingFileManagerTest.java b/log4j-core-test/src/test/java/org/apache/logging/log4j/core/appender/rolling/RollingFileManagerTest.java
index b6ae28ec5c..80bec2fdd3 100644
--- a/log4j-core-test/src/test/java/org/apache/logging/log4j/core/appender/rolling/RollingFileManagerTest.java
+++ b/log4j-core-test/src/test/java/org/apache/logging/log4j/core/appender/rolling/RollingFileManagerTest.java
@@ -16,14 +16,15 @@
  */
 package org.apache.logging.log4j.core.appender.rolling;
 
-import java.io.*;
+import java.io.File;
+import java.io.IOException;
 import java.nio.charset.StandardCharsets;
+import java.nio.file.Files;
 
 import org.apache.logging.log4j.core.LoggerContext;
 import org.apache.logging.log4j.core.appender.RollingFileAppender;
 import org.apache.logging.log4j.core.config.Configuration;
 import org.apache.logging.log4j.core.lookup.StrSubstitutor;
-import org.apache.logging.log4j.core.util.IOUtils;
 import org.junit.Assert;
 import org.junit.Test;
 
@@ -79,9 +80,8 @@ public class RollingFileManagerTest {
                 Assert.assertEquals(file.getAbsolutePath(), manager.getFileName());
                 manager.writeToDestination(testContent.getBytes(StandardCharsets.US_ASCII), 0, testContent.length());
             }
-            try (final Reader reader = new InputStreamReader(new FileInputStream(file), StandardCharsets.US_ASCII)) {
-                Assert.assertEquals(testContent, IOUtils.toString(reader));
-            }
+            final String actualContents = Files.readString(file.toPath(), StandardCharsets.US_ASCII);
+            Assert.assertEquals(testContent, actualContents);
         }
     }
 }
diff --git a/log4j-core/src/main/java/org/apache/logging/log4j/core/appender/HttpURLConnectionManager.java b/log4j-core/src/main/java/org/apache/logging/log4j/core/appender/HttpURLConnectionManager.java
index 1ab9009480..d603fb0c40 100644
--- a/log4j-core/src/main/java/org/apache/logging/log4j/core/appender/HttpURLConnectionManager.java
+++ b/log4j-core/src/main/java/org/apache/logging/log4j/core/appender/HttpURLConnectionManager.java
@@ -35,7 +35,6 @@ import org.apache.logging.log4j.core.config.ConfigurationException;
 import org.apache.logging.log4j.core.config.Property;
 import org.apache.logging.log4j.core.net.ssl.LaxHostnameVerifier;
 import org.apache.logging.log4j.core.net.ssl.SslConfiguration;
-import org.apache.logging.log4j.core.util.IOUtils;
 
 public class HttpURLConnectionManager extends HttpManager {
 
@@ -108,11 +107,8 @@ public class HttpURLConnectionManager extends HttpManager {
             os.write(msg);
         }
 
-        final byte[] buffer = new byte[1024];
         try (final InputStream is = urlConnection.getInputStream()) {
-            while (IOUtils.EOF != is.read(buffer)) {
-                // empty
-            }
+            is.readAllBytes();
         } catch (final IOException e) {
             final StringBuilder errorMessage = new StringBuilder();
             try (final InputStream es = urlConnection.getErrorStream()) {
@@ -122,10 +118,7 @@ public class HttpURLConnectionManager extends HttpManager {
                 }
                 if (es != null) {
                     errorMessage.append(" - ");
-                    int n;
-                    while (IOUtils.EOF != (n = es.read(buffer))) {
-                        errorMessage.append(new String(buffer, 0, n, CHARSET));
-                    }
+                    errorMessage.append(new String(es.readAllBytes(), CHARSET));
                 }
             }
             if (urlConnection.getResponseCode() > -1) {
diff --git a/log4j-core/src/main/java/org/apache/logging/log4j/core/util/IOUtils.java b/log4j-core/src/main/java/org/apache/logging/log4j/core/util/IOUtils.java
deleted file mode 100644
index d152d46689..0000000000
--- a/log4j-core/src/main/java/org/apache/logging/log4j/core/util/IOUtils.java
+++ /dev/null
@@ -1,130 +0,0 @@
-/*
- * Licensed to the Apache Software Foundation (ASF) under one or more
- * contributor license agreements.  See the NOTICE file distributed with
- * this work for additional information regarding copyright ownership.
- * The ASF licenses this file to you under the Apache License, Version 2.0
- * (the "License"); you may not use this file except in compliance with
- * the License.  You may obtain a copy of the License at
- *
- *      http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-package org.apache.logging.log4j.core.util;
-
-import java.io.IOException;
-import java.io.InputStream;
-import java.io.OutputStream;
-import java.io.Reader;
-import java.io.Writer;
-
-/**
- * Copied from Apache Commons IO revision 1686747.
- */
-public class IOUtils {
-
-    /**
-     * The default buffer size ({@value}) to use for
-     * {@link #copyLarge(InputStream, OutputStream)}
-     * and
-     * {@link #copyLarge(Reader, Writer)}
-     */
-    private static final int DEFAULT_BUFFER_SIZE = 1024 * 4;
-
-    /**
-     * Represents the end-of-file (or stream).
-     */
-    public static final int EOF = -1;
-
-    /**
-     * Copies chars from a <code>Reader</code> to a <code>Writer</code>.
-     * <p/>
-     * This method buffers the input internally, so there is no need to use a
-     * <code>BufferedReader</code>.
-     * <p/>
-     * Large streams (over 2GB) will return a chars copied value of
-     * <code>-1</code> after the copy has completed since the correct
-     * number of chars cannot be returned as an int. For large streams
-     * use the <code>copyLarge(Reader, Writer)</code> method.
-     *
-     * @param input the <code>Reader</code> to read from
-     * @param output the <code>Writer</code> to write to
-     * @return the number of characters copied, or -1 if &gt; Integer.MAX_VALUE
-     * @throws NullPointerException if the input or output is null
-     * @throws IOException          if an I/O error occurs
-     * @since 1.1
-     */
-    public static int copy(final Reader input, final Writer output) throws IOException {
-        final long count = copyLarge(input, output);
-        if (count > Integer.MAX_VALUE) {
-            return -1;
-        }
-        return (int) count;
-    }
-
-    /**
-     * Copies chars from a large (over 2GB) <code>Reader</code> to a <code>Writer</code>.
-     * <p/>
-     * This method buffers the input internally, so there is no need to use a
-     * <code>BufferedReader</code>.
-     * <p/>
-     * The buffer size is given by {@link #DEFAULT_BUFFER_SIZE}.
-     *
-     * @param input the <code>Reader</code> to read from
-     * @param output the <code>Writer</code> to write to
-     * @return the number of characters copied
-     * @throws NullPointerException if the input or output is null
-     * @throws IOException          if an I/O error occurs
-     * @since 1.3
-     */
-    public static long copyLarge(final Reader input, final Writer output) throws IOException {
-        return copyLarge(input, output, new char[DEFAULT_BUFFER_SIZE]);
-    }
-
-    /**
-     * Copies chars from a large (over 2GB) <code>Reader</code> to a <code>Writer</code>.
-     * <p/>
-     * This method uses the provided buffer, so there is no need to use a
-     * <code>BufferedReader</code>.
-     * <p/>
-     *
-     * @param input the <code>Reader</code> to read from
-     * @param output the <code>Writer</code> to write to
-     * @param buffer the buffer to be used for the copy
-     * @return the number of characters copied
-     * @throws NullPointerException if the input or output is null
-     * @throws IOException          if an I/O error occurs
-     * @since 2.2
-     */
-    public static long copyLarge(final Reader input, final Writer output, final char[] buffer) throws IOException {
-        long count = 0;
-        int n;
-        while (EOF != (n = input.read(buffer))) {
-            output.write(buffer, 0, n);
-            count += n;
-        }
-        return count;
-    }
-
-    /**
-     * Gets the contents of a <code>Reader</code> as a String.
-     * <p/>
-     * This method buffers the input internally, so there is no need to use a
-     * <code>BufferedReader</code>.
-     *
-     * @param input the <code>Reader</code> to read from
-     * @return the requested String
-     * @throws NullPointerException if the input is null
-     * @throws IOException          if an I/O error occurs
-     */
-    public static String toString(final Reader input) throws IOException {
-        final StringBuilderWriter sw = new StringBuilderWriter();
-        copy(input, sw);
-        return sw.toString();
-    }
-
-}
diff --git a/log4j-script/src/main/java/org/apache/logging/log4j/script/ScriptFile.java b/log4j-script/src/main/java/org/apache/logging/log4j/script/ScriptFile.java
index fb7617ce97..edc42a6f52 100644
--- a/log4j-script/src/main/java/org/apache/logging/log4j/script/ScriptFile.java
+++ b/log4j-script/src/main/java/org/apache/logging/log4j/script/ScriptFile.java
@@ -21,6 +21,7 @@ import java.io.FileInputStream;
 import java.io.IOException;
 import java.io.InputStreamReader;
 import java.io.Reader;
+import java.io.StringWriter;
 import java.net.URI;
 import java.nio.charset.Charset;
 import java.nio.file.Path;
@@ -28,7 +29,6 @@ import java.nio.file.Paths;
 
 import org.apache.logging.log4j.core.util.ExtensionLanguageMapping;
 import org.apache.logging.log4j.core.util.FileUtils;
-import org.apache.logging.log4j.core.util.IOUtils;
 import org.apache.logging.log4j.core.util.NetUtils;
 import org.apache.logging.log4j.plugins.Configurable;
 import org.apache.logging.log4j.plugins.Plugin;
@@ -96,7 +96,9 @@ public class ScriptFile extends AbstractScript {
         final String scriptText;
         try (final Reader reader = new InputStreamReader(
                 file != null ? new FileInputStream(file) : uri.toURL().openStream(), actualCharset)) {
-            scriptText = IOUtils.toString(reader);
+            final StringWriter writer = new StringWriter();
+            reader.transferTo(writer);
+            scriptText = writer.toString();
         } catch (final IOException e) {
             LOGGER.error("{}: language={}, path={}, actualCharset={}", e.getClass().getSimpleName(),
                     language, filePathOrUri, actualCharset);


[logging-log4j2] 02/03: Replace NullOutputStream with OutputStream::nullOutputStream

Posted by ma...@apache.org.
This is an automated email from the ASF dual-hosted git repository.

mattsicker pushed a commit to branch main
in repository https://gitbox.apache.org/repos/asf/logging-log4j2.git

commit bcc91d979bd0f2a6347595c8a2d6c6182b9b0727
Author: Matt Sicker <ma...@apache.org>
AuthorDate: Sun Oct 15 19:43:09 2023 -0500

    Replace NullOutputStream with OutputStream::nullOutputStream
    
    Signed-off-by: Matt Sicker <ma...@apache.org>
---
 .../SecureSocketAppenderSocketOptionsTest.java     |  4 +-
 .../appender/SocketAppenderSocketOptionsTest.java  |  9 ++-
 .../core/appender/RandomAccessFileManagerTest.java | 12 +--
 .../RollingRandomAccessFileManagerTest.java        |  7 +-
 .../core/appender/MemoryMappedFileManager.java     |  3 +-
 .../log4j/core/appender/OutputStreamAppender.java  |  3 +-
 .../core/appender/RandomAccessFileManager.java     |  3 +-
 .../rolling/RollingRandomAccessFileManager.java    |  3 +-
 .../logging/log4j/core/net/TcpSocketManager.java   |  9 +--
 .../logging/log4j/core/util/NullOutputStream.java  | 86 ----------------------
 10 files changed, 25 insertions(+), 114 deletions(-)

diff --git a/log4j-core-its/src/test/java/org/apache/logging/log4j/core/appender/SecureSocketAppenderSocketOptionsTest.java b/log4j-core-its/src/test/java/org/apache/logging/log4j/core/appender/SecureSocketAppenderSocketOptionsTest.java
index bf584bb94a..3196e0738b 100644
--- a/log4j-core-its/src/test/java/org/apache/logging/log4j/core/appender/SecureSocketAppenderSocketOptionsTest.java
+++ b/log4j-core-its/src/test/java/org/apache/logging/log4j/core/appender/SecureSocketAppenderSocketOptionsTest.java
@@ -33,7 +33,6 @@ import org.apache.logging.log4j.core.net.ssl.TrustStoreConfiguration;
 import org.apache.logging.log4j.core.test.AvailablePortFinder;
 import org.apache.logging.log4j.core.test.junit.LoggerContextRule;
 import org.apache.logging.log4j.core.test.net.ssl.TestConstants;
-import org.apache.logging.log4j.core.util.NullOutputStream;
 import org.junit.AfterClass;
 import org.junit.Assert;
 import org.junit.Assume;
@@ -101,7 +100,8 @@ public class SecureSocketAppenderSocketOptionsTest {
         final TcpSocketManager manager = (TcpSocketManager) appender.getManager();
         Assert.assertNotNull(manager);
         final OutputStream outputStream = manager.getOutputStream();
-        Assert.assertFalse(outputStream instanceof NullOutputStream);
+        final OutputStream nullOutputStream = OutputStream.nullOutputStream();
+        Assert.assertFalse(outputStream.getClass() == nullOutputStream.getClass());
         final SocketOptions socketOptions = manager.getSocketOptions();
         Assert.assertNotNull(socketOptions);
         final Socket socket = manager.getSocket();
diff --git a/log4j-core-its/src/test/java/org/apache/logging/log4j/core/appender/SocketAppenderSocketOptionsTest.java b/log4j-core-its/src/test/java/org/apache/logging/log4j/core/appender/SocketAppenderSocketOptionsTest.java
index 365d8ad89c..b7c0f48ac9 100644
--- a/log4j-core-its/src/test/java/org/apache/logging/log4j/core/appender/SocketAppenderSocketOptionsTest.java
+++ b/log4j-core-its/src/test/java/org/apache/logging/log4j/core/appender/SocketAppenderSocketOptionsTest.java
@@ -17,6 +17,7 @@
 package org.apache.logging.log4j.core.appender;
 
 import java.io.IOException;
+import java.io.OutputStream;
 import java.net.Socket;
 
 import org.apache.logging.log4j.core.appender.SocketAppenderTest.TcpSocketTestServer;
@@ -26,14 +27,15 @@ import org.apache.logging.log4j.core.net.SocketOptions;
 import org.apache.logging.log4j.core.net.TcpSocketManager;
 import org.apache.logging.log4j.core.test.junit.AllocatePorts;
 import org.apache.logging.log4j.core.test.junit.LoggerContextSource;
-import org.apache.logging.log4j.core.util.NullOutputStream;
 import org.apache.logging.log4j.plugins.Named;
 import org.junit.jupiter.api.AfterEach;
 import org.junit.jupiter.api.BeforeEach;
 import org.junit.jupiter.api.Test;
 
 import static org.assertj.core.api.Assertions.assertThat;
-import static org.junit.jupiter.api.Assertions.*;
+import static org.junit.jupiter.api.Assertions.assertEquals;
+import static org.junit.jupiter.api.Assertions.assertFalse;
+import static org.junit.jupiter.api.Assertions.assertNotNull;
 
 @AllocatePorts("SocketAppenderSocketOptionsTest.port")
 public class SocketAppenderSocketOptionsTest {
@@ -63,9 +65,10 @@ public class SocketAppenderSocketOptionsTest {
                 .isNotNull()
                 .isInstanceOf(TcpSocketManager.class);
         final TcpSocketManager manager = (TcpSocketManager) abstractSocketManager;
+        final Class<? extends OutputStream> nullOutputStreamType = OutputStream.nullOutputStream().getClass();
         assertThat(manager.getOutputStream())
                 .isNotNull()
-                .isInstanceOf(NullOutputStream.class);
+                .isInstanceOf(nullOutputStreamType);
         final SocketOptions socketOptions = manager.getSocketOptions();
         assertNotNull(socketOptions);
         final Socket socket = manager.getSocket();
diff --git a/log4j-core-test/src/test/java/org/apache/logging/log4j/core/appender/RandomAccessFileManagerTest.java b/log4j-core-test/src/test/java/org/apache/logging/log4j/core/appender/RandomAccessFileManagerTest.java
index 55069fae37..b0e848f2a6 100644
--- a/log4j-core-test/src/test/java/org/apache/logging/log4j/core/appender/RandomAccessFileManagerTest.java
+++ b/log4j-core-test/src/test/java/org/apache/logging/log4j/core/appender/RandomAccessFileManagerTest.java
@@ -22,11 +22,11 @@ import java.io.IOException;
 import java.io.OutputStream;
 import java.io.RandomAccessFile;
 
-import org.apache.logging.log4j.core.util.NullOutputStream;
 import org.junit.jupiter.api.Test;
 import org.junit.jupiter.api.io.TempDir;
 
-import static org.junit.jupiter.api.Assertions.*;
+import static org.junit.jupiter.api.Assertions.assertEquals;
+import static org.junit.jupiter.api.Assertions.assertNotEquals;
 
 /**
  * Tests the RandomAccessFileManager class.
@@ -44,7 +44,7 @@ public class RandomAccessFileManagerTest {
     public void testWrite_multiplesOfBufferSize() throws IOException {
         final File file = new File(tempDir, "testWrite_multiplesOfBufferSize.bin");
         try (final RandomAccessFile raf = new RandomAccessFile(file, "rw")) {
-            final OutputStream os = NullOutputStream.getInstance();
+            final OutputStream os = OutputStream.nullOutputStream();
             try (final RandomAccessFileManager manager = new RandomAccessFileManager(
                     null, raf, file.getName(), os,
                     RandomAccessFileManager.DEFAULT_BUFFER_SIZE, null, null, true)) {
@@ -66,7 +66,7 @@ public class RandomAccessFileManagerTest {
     public void testWrite_dataExceedingBufferSize() throws IOException {
         final File file = new File(tempDir, "testWrite_dataExceedingBufferSize.bin");
         try (final RandomAccessFile raf = new RandomAccessFile(file, "rw")) {
-            final OutputStream os = NullOutputStream.getInstance();
+            final OutputStream os = OutputStream.nullOutputStream();
             final int size = RandomAccessFileManager.DEFAULT_BUFFER_SIZE * 3 + 1;
             try (final RandomAccessFileManager manager = new RandomAccessFileManager(
                     null, raf, file.getName(), os,
@@ -84,7 +84,7 @@ public class RandomAccessFileManagerTest {
     public void testConfigurableBufferSize() throws IOException {
         final File file = new File(tempDir, "testConfigurableBufferSize.bin");
         try (final RandomAccessFile raf = new RandomAccessFile(file, "rw")) {
-            final OutputStream os = NullOutputStream.getInstance();
+            final OutputStream os = OutputStream.nullOutputStream();
             final int bufferSize = 4 * 1024;
             assertNotEquals(bufferSize, RandomAccessFileManager.DEFAULT_BUFFER_SIZE);
             try (final RandomAccessFileManager manager = new RandomAccessFileManager(
@@ -99,7 +99,7 @@ public class RandomAccessFileManagerTest {
     public void testWrite_dataExceedingMinBufferSize() throws IOException {
         final File file = new File(tempDir, "testWrite_dataExceedingMinBufferSize.bin");
         try (final RandomAccessFile raf = new RandomAccessFile(file, "rw")) {
-            final OutputStream os = NullOutputStream.getInstance();
+            final OutputStream os = OutputStream.nullOutputStream();
             final int bufferSize = 1;
             final int size = bufferSize * 3 + 1;
             try (final RandomAccessFileManager manager = new RandomAccessFileManager(
diff --git a/log4j-core-test/src/test/java/org/apache/logging/log4j/core/appender/rolling/RollingRandomAccessFileManagerTest.java b/log4j-core-test/src/test/java/org/apache/logging/log4j/core/appender/rolling/RollingRandomAccessFileManagerTest.java
index 775f23146b..6baeda0f1d 100644
--- a/log4j-core-test/src/test/java/org/apache/logging/log4j/core/appender/rolling/RollingRandomAccessFileManagerTest.java
+++ b/log4j-core-test/src/test/java/org/apache/logging/log4j/core/appender/rolling/RollingRandomAccessFileManagerTest.java
@@ -32,7 +32,6 @@ import java.util.concurrent.locks.LockSupport;
 import org.apache.logging.log4j.core.config.DefaultConfiguration;
 import org.apache.logging.log4j.core.util.Closer;
 import org.apache.logging.log4j.core.util.FileUtils;
-import org.apache.logging.log4j.core.util.NullOutputStream;
 import org.apache.logging.log4j.util.Strings;
 import org.junit.Test;
 
@@ -62,7 +61,7 @@ public class RollingRandomAccessFileManagerTest {
         final File file = File.createTempFile("log4j2", "test");
         file.deleteOnExit();
         try (final RandomAccessFile raf = new RandomAccessFile(file, "rw")) {
-            final OutputStream os = NullOutputStream.getInstance();
+            final OutputStream os = OutputStream.nullOutputStream();
             final boolean append = false;
             final boolean flushNow = false;
             final long triggerSize = Long.MAX_VALUE;
@@ -92,7 +91,7 @@ public class RollingRandomAccessFileManagerTest {
         final File file = File.createTempFile("log4j2", "test");
         file.deleteOnExit();
         try (final RandomAccessFile raf = new RandomAccessFile(file, "rw")) {
-            final OutputStream os = NullOutputStream.getInstance();
+            final OutputStream os = OutputStream.nullOutputStream();
             final boolean append = false;
             final boolean flushNow = false;
             final long triggerSize = 0;
@@ -119,7 +118,7 @@ public class RollingRandomAccessFileManagerTest {
         final File file = File.createTempFile("log4j2", "test");
         file.deleteOnExit();
         try (final RandomAccessFile raf = new RandomAccessFile(file, "rw")) {
-            final OutputStream os = NullOutputStream.getInstance();
+            final OutputStream os = OutputStream.nullOutputStream();
             final boolean append = false;
             final boolean flushNow = false;
             final long triggerSize = 0;
diff --git a/log4j-core/src/main/java/org/apache/logging/log4j/core/appender/MemoryMappedFileManager.java b/log4j-core/src/main/java/org/apache/logging/log4j/core/appender/MemoryMappedFileManager.java
index 246aba78ce..592cd7f387 100644
--- a/log4j-core/src/main/java/org/apache/logging/log4j/core/appender/MemoryMappedFileManager.java
+++ b/log4j-core/src/main/java/org/apache/logging/log4j/core/appender/MemoryMappedFileManager.java
@@ -35,7 +35,6 @@ import java.util.Objects;
 import org.apache.logging.log4j.core.Layout;
 import org.apache.logging.log4j.core.util.Closer;
 import org.apache.logging.log4j.core.util.FileUtils;
-import org.apache.logging.log4j.core.util.NullOutputStream;
 import org.apache.logging.log4j.util.ReflectionUtil;
 
 //Lines too long...
@@ -365,7 +364,7 @@ public class MemoryMappedFileManager extends OutputStreamManager {
             }
 
             final boolean writeHeader = !data.append || !file.exists();
-            final OutputStream os = NullOutputStream.getInstance();
+            final OutputStream os = OutputStream.nullOutputStream();
             RandomAccessFile raf = null;
             try {
                 FileUtils.makeParentDirs(file);
diff --git a/log4j-core/src/main/java/org/apache/logging/log4j/core/appender/OutputStreamAppender.java b/log4j-core/src/main/java/org/apache/logging/log4j/core/appender/OutputStreamAppender.java
index d4e3f84e88..9396adafad 100644
--- a/log4j-core/src/main/java/org/apache/logging/log4j/core/appender/OutputStreamAppender.java
+++ b/log4j-core/src/main/java/org/apache/logging/log4j/core/appender/OutputStreamAppender.java
@@ -24,7 +24,6 @@ import org.apache.logging.log4j.core.Layout;
 import org.apache.logging.log4j.core.config.Property;
 import org.apache.logging.log4j.core.layout.PatternLayout;
 import org.apache.logging.log4j.core.util.CloseShieldOutputStream;
-import org.apache.logging.log4j.core.util.NullOutputStream;
 import org.apache.logging.log4j.plugins.Configurable;
 import org.apache.logging.log4j.plugins.Plugin;
 import org.apache.logging.log4j.plugins.PluginFactory;
@@ -152,7 +151,7 @@ public final class OutputStreamAppender extends AbstractOutputStreamAppender<Out
 
     private static OutputStreamManager getManager(final OutputStream target, final boolean follow,
             final Layout layout) {
-        final OutputStream os = target == null ? NullOutputStream.getInstance() : new CloseShieldOutputStream(target);
+        final OutputStream os = target == null ? OutputStream.nullOutputStream() : new CloseShieldOutputStream(target);
         final OutputStream targetRef = target == null ? os : target;
         final String managerName = targetRef.getClass().getName() + "@" + Integer.toHexString(targetRef.hashCode())
                 + '.' + follow;
diff --git a/log4j-core/src/main/java/org/apache/logging/log4j/core/appender/RandomAccessFileManager.java b/log4j-core/src/main/java/org/apache/logging/log4j/core/appender/RandomAccessFileManager.java
index 7768e20554..92444eda52 100644
--- a/log4j-core/src/main/java/org/apache/logging/log4j/core/appender/RandomAccessFileManager.java
+++ b/log4j-core/src/main/java/org/apache/logging/log4j/core/appender/RandomAccessFileManager.java
@@ -28,7 +28,6 @@ import org.apache.logging.log4j.core.Layout;
 import org.apache.logging.log4j.core.LoggerContext;
 import org.apache.logging.log4j.core.config.Configuration;
 import org.apache.logging.log4j.core.util.FileUtils;
-import org.apache.logging.log4j.core.util.NullOutputStream;
 
 /**
  * Extends OutputStreamManager but instead of using a buffered output stream,
@@ -208,7 +207,7 @@ public class RandomAccessFileManager extends OutputStreamManager {
             }
 
             final boolean writeHeader = !data.append || !file.exists();
-            final OutputStream os = NullOutputStream.getInstance();
+            final OutputStream os = OutputStream.nullOutputStream();
             final RandomAccessFile raf;
             try {
                 FileUtils.makeParentDirs(file);
diff --git a/log4j-core/src/main/java/org/apache/logging/log4j/core/appender/rolling/RollingRandomAccessFileManager.java b/log4j-core/src/main/java/org/apache/logging/log4j/core/appender/rolling/RollingRandomAccessFileManager.java
index 416effd5fd..f0d719e050 100644
--- a/log4j-core/src/main/java/org/apache/logging/log4j/core/appender/rolling/RollingRandomAccessFileManager.java
+++ b/log4j-core/src/main/java/org/apache/logging/log4j/core/appender/rolling/RollingRandomAccessFileManager.java
@@ -30,7 +30,6 @@ import org.apache.logging.log4j.core.appender.ConfigurationFactoryData;
 import org.apache.logging.log4j.core.appender.ManagerFactory;
 import org.apache.logging.log4j.core.config.Configuration;
 import org.apache.logging.log4j.core.util.FileUtils;
-import org.apache.logging.log4j.core.util.NullOutputStream;
 
 /**
  * Extends RollingFileManager but instead of using a buffered output stream, this class uses a {@code ByteBuffer} and a
@@ -256,7 +255,7 @@ public class RollingRandomAccessFileManager extends RollingFileManager {
             final boolean writeHeader = !data.append || file == null || !file.exists();
 
             final RollingRandomAccessFileManager rrm = new RollingRandomAccessFileManager(data.getLoggerContext(), raf, name, data.pattern,
-                    NullOutputStream.getInstance(), data.append, data.immediateFlush, data.bufferSize, size, initialTime, data.policy,
+                    OutputStream.nullOutputStream(), data.append, data.immediateFlush, data.bufferSize, size, initialTime, data.policy,
                     data.strategy, data.advertiseURI, data.layout, data.filePermissions, data.fileOwner, data.fileGroup, writeHeader);
             if (rrm.isAttributeViewEnabled()) {
                 rrm.defineAttributeView(file.toPath());
diff --git a/log4j-core/src/main/java/org/apache/logging/log4j/core/net/TcpSocketManager.java b/log4j-core/src/main/java/org/apache/logging/log4j/core/net/TcpSocketManager.java
index 232cfed598..3750c14771 100644
--- a/log4j-core/src/main/java/org/apache/logging/log4j/core/net/TcpSocketManager.java
+++ b/log4j-core/src/main/java/org/apache/logging/log4j/core/net/TcpSocketManager.java
@@ -35,7 +35,7 @@ import org.apache.logging.log4j.core.appender.ManagerFactory;
 import org.apache.logging.log4j.core.appender.OutputStreamManager;
 import org.apache.logging.log4j.core.util.Closer;
 import org.apache.logging.log4j.core.util.Log4jThread;
-import org.apache.logging.log4j.core.util.NullOutputStream;
+import org.apache.logging.log4j.util.Cast;
 import org.apache.logging.log4j.util.Strings;
 
 /**
@@ -425,7 +425,7 @@ public class TcpSocketManager extends AbstractSocketManager {
                 return createManager(name, os, socket, inetAddress, data);
             } catch (final IOException ex) {
                 LOGGER.error("TcpSocketManager ({}) caught exception and will continue:", name, ex);
-                os = NullOutputStream.getInstance();
+                os = OutputStream.nullOutputStream();
             }
             if (data.reconnectDelayMillis == 0) {
                 Closer.closeSilently(socket);
@@ -434,11 +434,10 @@ public class TcpSocketManager extends AbstractSocketManager {
             return createManager(name, os, null, inetAddress, data);
         }
 
-        @SuppressWarnings("unchecked")
         M createManager(final String name, final OutputStream os, final Socket socket, final InetAddress inetAddress, final T data) {
-            return (M) new TcpSocketManager(name, os, socket, inetAddress, data.host, data.port,
+            return Cast.cast(new TcpSocketManager(name, os, socket, inetAddress, data.host, data.port,
                     data.connectTimeoutMillis, data.reconnectDelayMillis, data.immediateFail, data.layout,
-                    data.bufferSize, data.socketOptions);
+                    data.bufferSize, data.socketOptions));
         }
 
         Socket createSocket(final T data) throws IOException {
diff --git a/log4j-core/src/main/java/org/apache/logging/log4j/core/util/NullOutputStream.java b/log4j-core/src/main/java/org/apache/logging/log4j/core/util/NullOutputStream.java
deleted file mode 100644
index eb9be9f191..0000000000
--- a/log4j-core/src/main/java/org/apache/logging/log4j/core/util/NullOutputStream.java
+++ /dev/null
@@ -1,86 +0,0 @@
-/*
- * Licensed to the Apache Software Foundation (ASF) under one or more
- * contributor license agreements.  See the NOTICE file distributed with
- * this work for additional information regarding copyright ownership.
- * The ASF licenses this file to you under the Apache License, Version 2.0
- * (the "License"); you may not use this file except in compliance with
- * the License.  You may obtain a copy of the License at
- *
- *      http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-package org.apache.logging.log4j.core.util;
-
-import java.io.IOException;
-import java.io.OutputStream;
-
-/**
- * Writes all data to the famous <b>/dev/null</b>.
- * <p>
- * This output stream has no destination (file/socket etc.) and all bytes written to it are ignored and lost.
- * </p>
- * Originally from Apache Commons IO.
- *
- * @since 2.3
- */
-public final class NullOutputStream extends OutputStream {
-
-    private static final NullOutputStream INSTANCE = new NullOutputStream();
-
-    /**
-     * Gets the singleton instance.
-     *
-     * @return the singleton instance.
-     */
-    public static NullOutputStream getInstance() {
-        return INSTANCE;
-    }
-
-    private NullOutputStream() {
-        // do nothing
-    }
-
-    /**
-     * Does nothing - output to <code>/dev/null</code>.
-     *
-     * @param b
-     *        The bytes to write
-     * @param off
-     *        The start offset
-     * @param len
-     *        The number of bytes to write
-     */
-    @Override
-    public void write(final byte[] b, final int off, final int len) {
-        // to /dev/null
-    }
-
-    /**
-     * Does nothing - output to <code>/dev/null</code>.
-     *
-     * @param b
-     *        The byte to write
-     */
-    @Override
-    public void write(final int b) {
-        // to /dev/null
-    }
-
-    /**
-     * Does nothing - output to <code>/dev/null</code>.
-     *
-     * @param b
-     *        The bytes to write
-     * @throws IOException
-     *         never
-     */
-    @Override
-    public void write(final byte[] b) throws IOException {
-        // to /dev/null
-    }
-}