Checkstyle
Project: http://git-wip-us.apache.org/repos/asf/logging-log4j2/repo Commit: http://git-wip-us.apache.org/repos/asf/logging-log4j2/commit/37c992bf Tree: http://git-wip-us.apache.org/repos/asf/logging-log4j2/tree/37c992bf Diff: http://git-wip-us.apache.org/repos/asf/logging-log4j2/diff/37c992bf Branch: refs/heads/LOG4J2-1136 Commit: 37c992bf5b2c6deb5cc76803ce1b297619934972 Parents: 5baac73 Author: rpopma <[email protected]> Authored: Thu Sep 24 16:06:26 2015 +0200 Committer: Ralph Goers <[email protected]> Committed: Sun Sep 27 10:49:28 2015 -0700 ---------------------------------------------------------------------- .../rolling/RollingRandomAccessFileManager.java | 33 +++-- .../rolling/SizeBasedTriggeringPolicy.java | 6 +- .../rolling/TimeBasedTriggeringPolicy.java | 10 +- .../rolling/action/CommonsCompressAction.java | 14 ++- .../rolling/action/ZipCompressAction.java | 21 ++-- .../logging/log4j/core/async/AsyncLogger.java | 121 +++++++++---------- .../core/async/AsyncLoggerConfigHelper.java | 113 ++++++++--------- .../log4j/core/async/RingBufferLogEvent.java | 10 +- 8 files changed, 155 insertions(+), 173 deletions(-) ---------------------------------------------------------------------- http://git-wip-us.apache.org/repos/asf/logging-log4j2/blob/37c992bf/log4j-core/src/main/java/org/apache/logging/log4j/core/appender/rolling/RollingRandomAccessFileManager.java ---------------------------------------------------------------------- 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 87a5de8..e0cf192 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 @@ -29,13 +29,12 @@ import org.apache.logging.log4j.core.appender.ManagerFactory; 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 {@code RandomAccessFile} to do the - * I/O. + * Extends RollingFileManager but instead of using a buffered output stream, this class uses a {@code ByteBuffer} and a + * {@code RandomAccessFile} to do the I/O. */ public class RollingRandomAccessFileManager extends RollingFileManager { /** - * The default buffer size + * The default buffer size. */ public static final int DEFAULT_BUFFER_SIZE = 256 * 1024; @@ -46,10 +45,9 @@ public class RollingRandomAccessFileManager extends RollingFileManager { private final ByteBuffer buffer; private final ThreadLocal<Boolean> isEndOfBatch = new ThreadLocal<>(); - public RollingRandomAccessFileManager(final RandomAccessFile raf, final String fileName, - final String pattern, final OutputStream os, final boolean append, - final boolean immediateFlush, final int bufferSize, final long size, final long time, - final TriggeringPolicy policy, final RolloverStrategy strategy, + public RollingRandomAccessFileManager(final RandomAccessFile raf, final String fileName, final String pattern, + final OutputStream os, final boolean append, final boolean immediateFlush, final int bufferSize, + final long size, final long time, final TriggeringPolicy policy, final RolloverStrategy strategy, final String advertiseURI, final Layout<? extends Serializable> layout, final boolean writeHeader) { super(fileName, pattern, os, append, size, time, policy, strategy, advertiseURI, layout, bufferSize, writeHeader); @@ -80,10 +78,10 @@ public class RollingRandomAccessFileManager extends RollingFileManager { } public static RollingRandomAccessFileManager getRollingRandomAccessFileManager(final String fileName, - final String filePattern, final boolean isAppend, final boolean immediateFlush, final int bufferSize, - final TriggeringPolicy policy, final RolloverStrategy strategy, final String advertiseURI, + final String filePattern, final boolean isAppend, final boolean immediateFlush, final int bufferSize, + final TriggeringPolicy policy, final RolloverStrategy strategy, final String advertiseURI, final Layout<? extends Serializable> layout) { - return (RollingRandomAccessFileManager) getManager(fileName, new FactoryData(filePattern, isAppend, + return (RollingRandomAccessFileManager) getManager(fileName, new FactoryData(filePattern, isAppend, immediateFlush, bufferSize, policy, strategy, advertiseURI, layout), FACTORY); } @@ -91,8 +89,8 @@ public class RollingRandomAccessFileManager extends RollingFileManager { return isEndOfBatch.get(); } - public void setEndOfBatch(final boolean isEndOfBatch) { - this.isEndOfBatch.set(Boolean.valueOf(isEndOfBatch)); + public void setEndOfBatch(final boolean endOfBatch) { + this.isEndOfBatch.set(Boolean.valueOf(endOfBatch)); } @Override @@ -142,13 +140,13 @@ public class RollingRandomAccessFileManager extends RollingFileManager { try { randomAccessFile.close(); } catch (final IOException ex) { - LOGGER.error("Unable to close RandomAccessFile " + getName() + ". " - + ex); + LOGGER.error("Unable to close RandomAccessFile " + getName() + ". " + ex); } } - + /** * Returns the buffer capacity. + * * @return the buffer size */ @Override @@ -159,7 +157,8 @@ public class RollingRandomAccessFileManager extends RollingFileManager { /** * Factory to create a RollingRandomAccessFileManager. */ - private static class RollingRandomAccessFileManagerFactory implements ManagerFactory<RollingRandomAccessFileManager, FactoryData> { + private static class RollingRandomAccessFileManagerFactory implements + ManagerFactory<RollingRandomAccessFileManager, FactoryData> { /** * Create the RollingRandomAccessFileManager. http://git-wip-us.apache.org/repos/asf/logging-log4j2/blob/37c992bf/log4j-core/src/main/java/org/apache/logging/log4j/core/appender/rolling/SizeBasedTriggeringPolicy.java ---------------------------------------------------------------------- diff --git a/log4j-core/src/main/java/org/apache/logging/log4j/core/appender/rolling/SizeBasedTriggeringPolicy.java b/log4j-core/src/main/java/org/apache/logging/log4j/core/appender/rolling/SizeBasedTriggeringPolicy.java index ebb9f88..1966562 100644 --- a/log4j-core/src/main/java/org/apache/logging/log4j/core/appender/rolling/SizeBasedTriggeringPolicy.java +++ b/log4j-core/src/main/java/org/apache/logging/log4j/core/appender/rolling/SizeBasedTriggeringPolicy.java @@ -81,11 +81,11 @@ public class SizeBasedTriggeringPolicy implements TriggeringPolicy { /** * Initialize the TriggeringPolicy. - * @param manager The RollingFileManager. + * @param aManager The RollingFileManager. */ @Override - public void initialize(final RollingFileManager manager) { - this.manager = manager; + public void initialize(final RollingFileManager aManager) { + this.manager = aManager; } http://git-wip-us.apache.org/repos/asf/logging-log4j2/blob/37c992bf/log4j-core/src/main/java/org/apache/logging/log4j/core/appender/rolling/TimeBasedTriggeringPolicy.java ---------------------------------------------------------------------- diff --git a/log4j-core/src/main/java/org/apache/logging/log4j/core/appender/rolling/TimeBasedTriggeringPolicy.java b/log4j-core/src/main/java/org/apache/logging/log4j/core/appender/rolling/TimeBasedTriggeringPolicy.java index 7647a72..5e482e8 100644 --- a/log4j-core/src/main/java/org/apache/logging/log4j/core/appender/rolling/TimeBasedTriggeringPolicy.java +++ b/log4j-core/src/main/java/org/apache/logging/log4j/core/appender/rolling/TimeBasedTriggeringPolicy.java @@ -49,16 +49,16 @@ public final class TimeBasedTriggeringPolicy implements TriggeringPolicy { /** * Initializes the policy. - * @param manager The RollingFileManager. + * @param aManager The RollingFileManager. */ @Override - public void initialize(final RollingFileManager manager) { - this.manager = manager; + public void initialize(final RollingFileManager aManager) { + this.manager = aManager; // LOG4J2-531: call getNextTime twice to force initialization of both prevFileTime and nextFileTime - manager.getPatternProcessor().getNextTime(manager.getFileTime(), interval, modulate); + aManager.getPatternProcessor().getNextTime(aManager.getFileTime(), interval, modulate); - nextRolloverMillis = manager.getPatternProcessor().getNextTime(manager.getFileTime(), interval, modulate); + nextRolloverMillis = aManager.getPatternProcessor().getNextTime(aManager.getFileTime(), interval, modulate); } /** http://git-wip-us.apache.org/repos/asf/logging-log4j2/blob/37c992bf/log4j-core/src/main/java/org/apache/logging/log4j/core/appender/rolling/action/CommonsCompressAction.java ---------------------------------------------------------------------- diff --git a/log4j-core/src/main/java/org/apache/logging/log4j/core/appender/rolling/action/CommonsCompressAction.java b/log4j-core/src/main/java/org/apache/logging/log4j/core/appender/rolling/action/CommonsCompressAction.java index f176464..b5a9610 100644 --- a/log4j-core/src/main/java/org/apache/logging/log4j/core/appender/rolling/action/CommonsCompressAction.java +++ b/log4j-core/src/main/java/org/apache/logging/log4j/core/appender/rolling/action/CommonsCompressAction.java @@ -56,13 +56,15 @@ public final class CommonsCompressAction extends AbstractAction { /** * Creates new instance of Bzip2CompressAction. + * * @param name the compressor name. One of "gz", "bzip2", "xz", "pack200", or "deflate". * @param source file to compress, may not be null. * @param destination compressed file, may not be null. * @param deleteSource if true, attempt to delete file on completion. Failure to delete does not cause an exception * to be thrown or affect return value. */ - public CommonsCompressAction(final String name, final File source, final File destination, final boolean deleteSource) { + public CommonsCompressAction(final String name, final File source, final File destination, + final boolean deleteSource) { Objects.requireNonNull(source, "source"); Objects.requireNonNull(destination, "destination"); this.name = name; @@ -84,6 +86,7 @@ public final class CommonsCompressAction extends AbstractAction { /** * Compresses a file. + * * @param name the compressor name, i.e. "gz", "bzip2", "xz", "pack200", or "deflate". * @param source file to compress, may not be null. * @param destination compressed file, may not be null. @@ -93,14 +96,15 @@ public final class CommonsCompressAction extends AbstractAction { * @return true if source file compressed. * @throws IOException on IO exception. */ - public static boolean execute(final String name, final File source, final File destination, final boolean deleteSource) - throws IOException { + public static boolean execute(final String name, final File source, final File destination, + final boolean deleteSource) throws IOException { if (!source.exists()) { return false; } try (final FileInputStream input = new FileInputStream(source); - final BufferedOutputStream output = new BufferedOutputStream(new CompressorStreamFactory() - .createCompressorOutputStream(name, new FileOutputStream(destination)))) { + final BufferedOutputStream output = new BufferedOutputStream( + new CompressorStreamFactory().createCompressorOutputStream(name, new FileOutputStream( + destination)))) { IOUtils.copy(input, output, BUF_SIZE); } catch (final CompressorException e) { throw new IOException(e); http://git-wip-us.apache.org/repos/asf/logging-log4j2/blob/37c992bf/log4j-core/src/main/java/org/apache/logging/log4j/core/appender/rolling/action/ZipCompressAction.java ---------------------------------------------------------------------- diff --git a/log4j-core/src/main/java/org/apache/logging/log4j/core/appender/rolling/action/ZipCompressAction.java b/log4j-core/src/main/java/org/apache/logging/log4j/core/appender/rolling/action/ZipCompressAction.java index 5a61270..d7acf8c 100644 --- a/log4j-core/src/main/java/org/apache/logging/log4j/core/appender/rolling/action/ZipCompressAction.java +++ b/log4j-core/src/main/java/org/apache/logging/log4j/core/appender/rolling/action/ZipCompressAction.java @@ -24,7 +24,6 @@ import java.util.Objects; import java.util.zip.ZipEntry; import java.util.zip.ZipOutputStream; - /** * Compresses a file using Zip compression. */ @@ -55,10 +54,10 @@ public final class ZipCompressAction extends AbstractAction { /** * Creates new instance of GzCompressAction. * - * @param source file to compress, may not be null. - * @param destination compressed file, may not be null. - * @param deleteSource if true, attempt to delete file on completion. Failure to delete - * does not cause an exception to be thrown or affect return value. + * @param source file to compress, may not be null. + * @param destination compressed file, may not be null. + * @param deleteSource if true, attempt to delete file on completion. Failure to delete does not cause an exception + * to be thrown or affect return value. * @param level TODO */ public ZipCompressAction(final File source, final File destination, final boolean deleteSource, final int level) { @@ -85,16 +84,16 @@ public final class ZipCompressAction extends AbstractAction { /** * Compresses a file. * - * @param source file to compress, may not be null. - * @param destination compressed file, may not be null. - * @param deleteSource if true, attempt to delete file on completion. Failure to delete - * does not cause an exception to be thrown or affect return value. + * @param source file to compress, may not be null. + * @param destination compressed file, may not be null. + * @param deleteSource if true, attempt to delete file on completion. Failure to delete does not cause an exception + * to be thrown or affect return value. * @param level the compression level * @return true if source file compressed. * @throws IOException on IO exception. */ - public static boolean execute(final File source, final File destination, final boolean deleteSource, final int level) - throws IOException { + public static boolean execute(final File source, final File destination, final boolean deleteSource, + final int level) throws IOException { if (source.exists()) { try (final FileInputStream fis = new FileInputStream(source); final ZipOutputStream zos = new ZipOutputStream(new FileOutputStream(destination))) { http://git-wip-us.apache.org/repos/asf/logging-log4j2/blob/37c992bf/log4j-core/src/main/java/org/apache/logging/log4j/core/async/AsyncLogger.java ---------------------------------------------------------------------- diff --git a/log4j-core/src/main/java/org/apache/logging/log4j/core/async/AsyncLogger.java b/log4j-core/src/main/java/org/apache/logging/log4j/core/async/AsyncLogger.java index 8300a97..d775731 100644 --- a/log4j-core/src/main/java/org/apache/logging/log4j/core/async/AsyncLogger.java +++ b/log4j-core/src/main/java/org/apache/logging/log4j/core/async/AsyncLogger.java @@ -52,32 +52,23 @@ import com.lmax.disruptor.dsl.Disruptor; import com.lmax.disruptor.dsl.ProducerType; /** - * AsyncLogger is a logger designed for high throughput and low latency logging. - * It does not perform any I/O in the calling (application) thread, but instead - * hands off the work to another thread as soon as possible. The actual logging - * is performed in the background thread. It uses the LMAX Disruptor library for - * inter-thread communication. (<a - * href="http://lmax-exchange.github.com/disruptor/" - * >http://lmax-exchange.github.com/disruptor/</a>) + * AsyncLogger is a logger designed for high throughput and low latency logging. It does not perform any I/O in the + * calling (application) thread, but instead hands off the work to another thread as soon as possible. The actual + * logging is performed in the background thread. It uses the LMAX Disruptor library for inter-thread communication. (<a + * href="http://lmax-exchange.github.com/disruptor/" >http://lmax-exchange.github.com/disruptor/</a>) * <p> * To use AsyncLogger, specify the System property - * {@code -DLog4jContextSelector=org.apache.logging.log4j.core.async.AsyncLoggerContextSelector} - * before you obtain a Logger, and all Loggers returned by LogManager.getLogger - * will be AsyncLoggers. + * {@code -DLog4jContextSelector=org.apache.logging.log4j.core.async.AsyncLoggerContextSelector} before you obtain a + * Logger, and all Loggers returned by LogManager.getLogger will be AsyncLoggers. * <p> - * Note that for performance reasons, this logger does not include source - * location by default. You need to specify {@code includeLocation="true"} in - * the configuration or any %class, %location or %line conversion patterns in - * your log4j.xml configuration will produce either a "?" character or no output - * at all. + * Note that for performance reasons, this logger does not include source location by default. You need to specify + * {@code includeLocation="true"} in the configuration or any %class, %location or %line conversion patterns in your + * log4j.xml configuration will produce either a "?" character or no output at all. * <p> - * For best performance, use AsyncLogger with the RandomAccessFileAppender or - * RollingRandomAccessFileAppender, with immediateFlush=false. These appenders - * have built-in support for the batching mechanism used by the Disruptor - * library, and they will flush to disk at the end of each batch. This means - * that even with immediateFlush=false, there will never be any items left in - * the buffer; all log events will all be written to disk in a very efficient - * manner. + * For best performance, use AsyncLogger with the RandomAccessFileAppender or RollingRandomAccessFileAppender, with + * immediateFlush=false. These appenders have built-in support for the batching mechanism used by the Disruptor library, + * and they will flush to disk at the end of each batch. This means that even with immediateFlush=false, there will + * never be any items left in the buffer; all log events will all be written to disk in a very efficient manner. */ public class AsyncLogger extends Logger { private static final long serialVersionUID = 1L; @@ -88,6 +79,9 @@ public class AsyncLogger extends Logger { private static final StatusLogger LOGGER = StatusLogger.getLogger(); private static final ThreadNameStrategy THREAD_NAME_STRATEGY = ThreadNameStrategy.create(); + /** + * Strategy for deciding whether thread name should be cached or not. + */ static enum ThreadNameStrategy { // LOG4J2-467 CACHED { @Override @@ -104,7 +98,8 @@ public class AsyncLogger extends Logger { abstract String getThreadName(Info info); static ThreadNameStrategy create() { - final String name = PropertiesUtil.getProperties().getStringProperty("AsyncLogger.ThreadNameStrategy", CACHED.name()); + final String name = PropertiesUtil.getProperties().getStringProperty("AsyncLogger.ThreadNameStrategy", + CACHED.name()); try { return ThreadNameStrategy.valueOf(name); } catch (final Exception ex) { @@ -113,12 +108,13 @@ public class AsyncLogger extends Logger { } } } + private static volatile Disruptor<RingBufferLogEvent> disruptor; private static final Clock CLOCK = ClockFactory.getClock(); private static volatile NanoClock nanoClock = new DummyNanoClock(); - private static final ExecutorService executor = Executors - .newSingleThreadExecutor(new DaemonThreadFactory("AsyncLogger-")); + private static final ExecutorService executor = Executors.newSingleThreadExecutor(new DaemonThreadFactory( + "AsyncLogger-")); static { initInfoForExecutorThread(); @@ -136,10 +132,21 @@ public class AsyncLogger extends Logger { disruptor.start(); } + /** + * Constructs an {@code AsyncLogger} with the specified context, name and message factory. + * + * @param context context of this logger + * @param name name of this logger + * @param messageFactory message factory of this logger + */ + public AsyncLogger(final LoggerContext context, final String name, final MessageFactory messageFactory) { + super(context, name, messageFactory); + } + private static int calculateRingBufferSize() { int ringBufferSize = RINGBUFFER_DEFAULT_SIZE; - final String userPreferredRBSize = PropertiesUtil.getProperties().getStringProperty("AsyncLogger.RingBufferSize", - String.valueOf(ringBufferSize)); + final String userPreferredRBSize = PropertiesUtil.getProperties().getStringProperty( + "AsyncLogger.RingBufferSize", String.valueOf(ringBufferSize)); try { int size = Integer.parseInt(userPreferredRBSize); if (size < RINGBUFFER_MIN_SIZE) { @@ -155,14 +162,13 @@ public class AsyncLogger extends Logger { } /** - * Initialize an {@code Info} object that is threadlocal to the consumer/appender thread. - * This Info object uniquely has attribute {@code isAppenderThread} set to {@code true}. - * All other Info objects will have this attribute set to {@code false}. - * This allows us to detect Logger.log() calls initiated from the appender thread, - * which may cause deadlock when the RingBuffer is full. (LOG4J2-471) + * Initialize an {@code Info} object that is threadlocal to the consumer/appender thread. This Info object uniquely + * has attribute {@code isAppenderThread} set to {@code true}. All other Info objects will have this attribute set + * to {@code false}. This allows us to detect Logger.log() calls initiated from the appender thread, which may cause + * deadlock when the RingBuffer is full. (LOG4J2-471) */ private static void initInfoForExecutorThread() { - executor.submit(new Runnable(){ + executor.submit(new Runnable() { @Override public void run() { final boolean isAppenderThread = true; @@ -195,7 +201,8 @@ public class AsyncLogger extends Logger { } try { @SuppressWarnings("unchecked") - final ExceptionHandler<RingBufferLogEvent> result = Loader.newCheckedInstanceOf(cls, ExceptionHandler.class); + final ExceptionHandler<RingBufferLogEvent> result = Loader + .newCheckedInstanceOf(cls, ExceptionHandler.class); LOGGER.debug("AsyncLogger.ExceptionHandler={}", result); return result; } catch (final Exception ignored) { @@ -205,18 +212,6 @@ public class AsyncLogger extends Logger { } /** - * Constructs an {@code AsyncLogger} with the specified context, name and - * message factory. - * - * @param context context of this logger - * @param name name of this logger - * @param messageFactory message factory of this logger - */ - public AsyncLogger(final LoggerContext context, final String name, final MessageFactory messageFactory) { - super(context, name, messageFactory); - } - - /** * Tuple with the event translator and thread name for a thread. */ static class Info { @@ -230,7 +225,7 @@ public class AsyncLogger extends Logger { private final RingBufferLogEventTranslator translator; private final String cachedThreadName; private final boolean isAppenderThread; - + public Info(final RingBufferLogEventTranslator translator, final String threadName, final boolean appenderThread) { this.translator = translator; this.cachedThreadName = threadName; @@ -246,7 +241,7 @@ public class AsyncLogger extends Logger { @Override public void logMessage(final String fqcn, final Level level, final Marker marker, final Message message, final Throwable thrown) { - + final Disruptor<RingBufferLogEvent> temp = disruptor; if (temp == null) { // LOG4J2-639 LOGGER.fatal("Ignoring log event after log4j was shut down"); @@ -269,8 +264,8 @@ public class AsyncLogger extends Logger { } /** - * LOG4J2-471: prevent deadlock when RingBuffer is full and object - * being logged calls Logger.log() from its toString() method + * LOG4J2-471: prevent deadlock when RingBuffer is full and object being logged calls Logger.log() from its + * toString() method * * @param info threadlocal information - used to determine if the current thread is the background appender thread * @param theDisruptor used to check if the buffer is full @@ -280,7 +275,7 @@ public class AsyncLogger extends Logger { * @param message log message * @param thrown optional exception * @return {@code true} if the event has been logged in the current thread, {@code false} if it should be passed to - * the background thread + * the background thread */ private boolean logMessageInCurrentThread(Info info, final Disruptor<RingBufferLogEvent> theDisruptor, final String fqcn, final Level level, final Marker marker, final Message message, final Throwable thrown) { @@ -305,7 +300,7 @@ public class AsyncLogger extends Logger { */ private void logMessageInBackgroundThread(Info info, final String fqcn, final Level level, final Marker marker, final Message message, final Throwable thrown) { - + message.getFormattedMessage(); // LOG4J2-763: ask message to freeze parameters initLogMessageInfo(info, fqcn, level, marker, message, thrown); @@ -342,16 +337,17 @@ public class AsyncLogger extends Logger { // LOG4J2-744 avoid calling clock altogether if message has the timestamp eventTimeMillis(message), // nanoClock.nanoTime() // - ); + ); } private long eventTimeMillis(final Message message) { - return message instanceof TimestampMessage ? ((TimestampMessage) message).getTimestamp() : - CLOCK.currentTimeMillis(); + return message instanceof TimestampMessage ? ((TimestampMessage) message).getTimestamp() : CLOCK + .currentTimeMillis(); } /** * Returns the caller location if requested, {@code null} otherwise. + * * @param fqcn fully qualified caller name. * @return the caller location if requested, {@code null} otherwise. */ @@ -377,8 +373,7 @@ public class AsyncLogger extends Logger { } /** - * This method is called by the EventHandler that processes the - * RingBufferLogEvent in a separate thread. + * This method is called by the EventHandler that processes the RingBufferLogEvent in a separate thread. * * @param event the event to log */ @@ -416,29 +411,29 @@ public class AsyncLogger extends Logger { /** * Returns {@code true} if the specified disruptor still has unprocessed events. */ - private static boolean hasBacklog(final Disruptor<?> disruptor) { - final RingBuffer<?> ringBuffer = disruptor.getRingBuffer(); + private static boolean hasBacklog(final Disruptor<?> theDisruptor) { + final RingBuffer<?> ringBuffer = theDisruptor.getRingBuffer(); return !ringBuffer.hasAvailableCapacity(ringBuffer.getBufferSize()); } /** - * Creates and returns a new {@code RingBufferAdmin} that instruments the - * ringbuffer of the {@code AsyncLogger}. + * Creates and returns a new {@code RingBufferAdmin} that instruments the ringbuffer of the {@code AsyncLogger}. * * @param contextName name of the global {@code AsyncLoggerContext} */ public static RingBufferAdmin createRingBufferAdmin(final String contextName) { return RingBufferAdmin.forAsyncLogger(disruptor.getRingBuffer(), contextName); } - + /** * Returns the {@code NanoClock} to use for creating the nanoTime timestamp of log events. + * * @return the {@code NanoClock} to use for creating the nanoTime timestamp of log events */ public static NanoClock getNanoClock() { return nanoClock; } - + /** * Sets the {@code NanoClock} to use for creating the nanoTime timestamp of log events. * <p> http://git-wip-us.apache.org/repos/asf/logging-log4j2/blob/37c992bf/log4j-core/src/main/java/org/apache/logging/log4j/core/async/AsyncLoggerConfigHelper.java ---------------------------------------------------------------------- diff --git a/log4j-core/src/main/java/org/apache/logging/log4j/core/async/AsyncLoggerConfigHelper.java b/log4j-core/src/main/java/org/apache/logging/log4j/core/async/AsyncLoggerConfigHelper.java index a81d8fa..955e7f6 100644 --- a/log4j-core/src/main/java/org/apache/logging/log4j/core/async/AsyncLoggerConfigHelper.java +++ b/log4j-core/src/main/java/org/apache/logging/log4j/core/async/AsyncLoggerConfigHelper.java @@ -42,20 +42,16 @@ import com.lmax.disruptor.dsl.Disruptor; import com.lmax.disruptor.dsl.ProducerType; /** - * Helper class decoupling the {@code AsyncLoggerConfig} class from the LMAX - * Disruptor library. + * Helper class decoupling the {@code AsyncLoggerConfig} class from the LMAX Disruptor library. * <p> - * {@code AsyncLoggerConfig} is a plugin, and will be loaded even if users do - * not configure any {@code <asyncLogger>} or {@code <asyncRoot>} elements in - * the configuration. If {@code AsyncLoggerConfig} has inner classes that extend - * or implement classes from the Disruptor library, a - * {@code NoClassDefFoundError} is thrown if the Disruptor jar is not in the - * classpath when the PluginManager loads the {@code AsyncLoggerConfig} plugin - * from the pre-defined plugins definition file. + * {@code AsyncLoggerConfig} is a plugin, and will be loaded even if users do not configure any {@code <asyncLogger>} or + * {@code <asyncRoot>} elements in the configuration. If {@code AsyncLoggerConfig} has inner classes that extend or + * implement classes from the Disruptor library, a {@code NoClassDefFoundError} is thrown if the Disruptor jar is not in + * the classpath when the PluginManager loads the {@code AsyncLoggerConfig} plugin from the pre-defined plugins + * definition file. * <p> - * This class serves to make the dependency on the Disruptor optional, so that - * these classes are only loaded when the {@code AsyncLoggerConfig} is actually - * used. + * This class serves to make the dependency on the Disruptor optional, so that these classes are only loaded when the + * {@code AsyncLoggerConfig} is actually used. */ class AsyncLoggerConfigHelper { @@ -73,8 +69,8 @@ class AsyncLoggerConfigHelper { private static ThreadLocal<Boolean> isAppenderThread = new ThreadLocal<>(); /** - * Factory used to populate the RingBuffer with events. These event objects - * are then re-used during the life of the RingBuffer. + * Factory used to populate the RingBuffer with events. These event objects are then re-used during the life of the + * RingBuffer. */ private static final EventFactory<Log4jEventWrapper> FACTORY = new EventFactory<Log4jEventWrapper>() { @Override @@ -86,11 +82,11 @@ class AsyncLoggerConfigHelper { /** * Object responsible for passing on data to a specific RingBuffer event. */ - private final EventTranslatorTwoArg<Log4jEventWrapper, LogEvent, AsyncLoggerConfig> translator - = new EventTranslatorTwoArg<Log4jEventWrapper, LogEvent, AsyncLoggerConfig>() { + private final EventTranslatorTwoArg<Log4jEventWrapper, LogEvent, AsyncLoggerConfig> translator = + new EventTranslatorTwoArg<Log4jEventWrapper, LogEvent, AsyncLoggerConfig>() { @Override - public void translateTo(final Log4jEventWrapper ringBufferElement, final long sequence, + public void translateTo(final Log4jEventWrapper ringBufferElement, final long sequence, final LogEvent logEvent, final AsyncLoggerConfig loggerConfig) { ringBufferElement.event = logEvent; ringBufferElement.loggerConfig = loggerConfig; @@ -106,7 +102,8 @@ class AsyncLoggerConfigHelper { private static synchronized void initDisruptor() { if (disruptor != null) { - LOGGER.trace("AsyncLoggerConfigHelper not starting new disruptor, using existing object. Ref count is {}.", count); + LOGGER.trace("AsyncLoggerConfigHelper not starting new disruptor, using existing object. Ref count is {}.", + count); return; } LOGGER.trace("AsyncLoggerConfigHelper creating new disruptor. Ref count is {}.", count); @@ -116,7 +113,7 @@ class AsyncLoggerConfigHelper { initThreadLocalForExecutorThread(); disruptor = new Disruptor<>(FACTORY, ringBufferSize, executor, ProducerType.MULTI, waitStrategy); final EventHandler<Log4jEventWrapper>[] handlers = new Log4jEventWrapperHandler[] {// - new Log4jEventWrapperHandler() }; + new Log4jEventWrapperHandler()}; final ExceptionHandler<Log4jEventWrapper> errorHandler = getExceptionHandler(); disruptor.handleExceptionsWith(errorHandler); disruptor.handleEventsWith(handlers); @@ -128,8 +125,7 @@ class AsyncLoggerConfigHelper { } private static WaitStrategy createWaitStrategy() { - final String strategy = System - .getProperty("AsyncLoggerConfig.WaitStrategy"); + final String strategy = System.getProperty("AsyncLoggerConfig.WaitStrategy"); LOGGER.debug("property AsyncLoggerConfig.WaitStrategy={}", strategy); if ("Sleep".equals(strategy)) { return new SleepingWaitStrategy(); @@ -145,20 +141,17 @@ class AsyncLoggerConfigHelper { private static int calculateRingBufferSize() { int ringBufferSize = RINGBUFFER_DEFAULT_SIZE; final String userPreferredRBSize = PropertiesUtil.getProperties().getStringProperty( - "AsyncLoggerConfig.RingBufferSize", - String.valueOf(ringBufferSize)); + "AsyncLoggerConfig.RingBufferSize", String.valueOf(ringBufferSize)); try { int size = Integer.parseInt(userPreferredRBSize); if (size < RINGBUFFER_MIN_SIZE) { size = RINGBUFFER_MIN_SIZE; - LOGGER.warn( - "Invalid RingBufferSize {}, using minimum size {}.", - userPreferredRBSize, RINGBUFFER_MIN_SIZE); + LOGGER.warn("Invalid RingBufferSize {}, using minimum size {}.", userPreferredRBSize, + RINGBUFFER_MIN_SIZE); } ringBufferSize = size; } catch (final Exception ex) { - LOGGER.warn("Invalid RingBufferSize {}, using default size {}.", - userPreferredRBSize, ringBufferSize); + LOGGER.warn("Invalid RingBufferSize {}, using default size {}.", userPreferredRBSize, ringBufferSize); } return Integers.ceilingNextPowerOfTwo(ringBufferSize); } @@ -170,8 +163,8 @@ class AsyncLoggerConfigHelper { } try { @SuppressWarnings("unchecked") - final Class<? extends ExceptionHandler<Log4jEventWrapper>> klass = (Class<? extends ExceptionHandler<Log4jEventWrapper>>) Class - .forName(cls); + final Class<? extends ExceptionHandler<Log4jEventWrapper>> klass = + (Class<? extends ExceptionHandler<Log4jEventWrapper>>) Class.forName(cls); return klass.newInstance(); } catch (final Exception ignored) { LOGGER.debug("AsyncLoggerConfig.ExceptionHandler not set: error creating " + cls + ": ", ignored); @@ -180,16 +173,14 @@ class AsyncLoggerConfigHelper { } /** - * RingBuffer events contain all information necessary to perform the work - * in a separate thread. + * RingBuffer events contain all information necessary to perform the work in a separate thread. */ private static class Log4jEventWrapper { private AsyncLoggerConfig loggerConfig; private LogEvent event; /** - * Release references held by ring buffer to allow objects to be - * garbage-collected. + * Release references held by ring buffer to allow objects to be garbage-collected. */ public void clear() { loggerConfig = null; @@ -200,8 +191,7 @@ class AsyncLoggerConfigHelper { /** * EventHandler performs the work in a separate thread. */ - private static class Log4jEventWrapperHandler implements - SequenceReportingEventHandler<Log4jEventWrapper> { + private static class Log4jEventWrapperHandler implements SequenceReportingEventHandler<Log4jEventWrapper> { private static final int NOTIFY_PROGRESS_THRESHOLD = 50; private Sequence sequenceCallback; private int counter; @@ -212,8 +202,8 @@ class AsyncLoggerConfigHelper { } @Override - public void onEvent(final Log4jEventWrapper event, final long sequence, - final boolean endOfBatch) throws Exception { + public void onEvent(final Log4jEventWrapper event, final long sequence, final boolean endOfBatch) + throws Exception { event.event.setEndOfBatch(endOfBatch); event.loggerConfig.asyncCallAppenders(event.event); event.clear(); @@ -222,9 +212,8 @@ class AsyncLoggerConfigHelper { } /** - * Notify the BatchEventProcessor that the sequence has progressed. - * Without this callback the sequence would not be progressed - * until the batch has completely finished. + * Notify the BatchEventProcessor that the sequence has progressed. Without this callback the sequence would not + * be progressed until the batch has completely finished. */ private void notifyIntermediateProgress(final long sequence) { if (++counter > NOTIFY_PROGRESS_THRESHOLD) { @@ -235,22 +224,21 @@ class AsyncLoggerConfigHelper { } /** - * Increases the reference count and creates and starts a new Disruptor and - * associated thread if none currently exists. + * Increases the reference count and creates and starts a new Disruptor and associated thread if none currently + * exists. * * @see #release() */ - synchronized static void claim() { + static synchronized void claim() { count++; initDisruptor(); } /** - * Decreases the reference count. If the reference count reached zero, the - * Disruptor and its associated thread are shut down and their references - * set to {@code null}. + * Decreases the reference count. If the reference count reached zero, the Disruptor and its associated thread are + * shut down and their references set to {@code null}. */ - synchronized static void release() { + static synchronized void release() { if (--count > 0) { LOGGER.trace("AsyncLoggerConfigHelper: not shutting down disruptor: ref count is {}.", count); return; @@ -291,9 +279,8 @@ class AsyncLoggerConfigHelper { } /** - * Initialize the threadlocal that allows us to detect Logger.log() calls - * initiated from the appender thread, which may cause deadlock when the - * RingBuffer is full. (LOG4J2-471) + * Initialize the threadlocal that allows us to detect Logger.log() calls initiated from the appender thread, which + * may cause deadlock when the RingBuffer is full. (LOG4J2-471) */ private static void initThreadLocalForExecutorThread() { executor.submit(new Runnable() { @@ -305,17 +292,15 @@ class AsyncLoggerConfigHelper { } /** - * If possible, delegates the invocation to {@code callAppenders} to another - * thread and returns {@code true}. If this is not possible (if it detects - * that delegating to another thread would cause deadlock because the - * current call to Logger.log() originated from the appender thread and the - * ringbuffer is full) then this method does nothing and returns {@code false}. - * It is the responsibility of the caller to process the event when this - * method returns {@code false}. + * If possible, delegates the invocation to {@code callAppenders} to another thread and returns {@code true}. If + * this is not possible (if it detects that delegating to another thread would cause deadlock because the current + * call to Logger.log() originated from the appender thread and the ringbuffer is full) then this method does + * nothing and returns {@code false}. It is the responsibility of the caller to process the event when this method + * returns {@code false}. * * @param event the event to delegate to another thread - * @return {@code true} if delegation was successful, {@code false} if the - * calling thread needs to process the event itself + * @return {@code true} if delegation was successful, {@code false} if the calling thread needs to process the + * event itself */ public boolean callAppendersFromAnotherThread(final LogEvent event) { final Disruptor<Log4jEventWrapper> temp = disruptor; @@ -383,13 +368,13 @@ class AsyncLoggerConfigHelper { /** * Returns true if the specified ringbuffer is full and the Logger.log() call was made from the appender thread. */ - private boolean isCalledFromAppenderThreadAndBufferFull(Disruptor<Log4jEventWrapper> disruptor) { - return isAppenderThread.get() == Boolean.TRUE && disruptor.getRingBuffer().remainingCapacity() == 0; + private boolean isCalledFromAppenderThreadAndBufferFull(Disruptor<Log4jEventWrapper> theDisruptor) { + return isAppenderThread.get() == Boolean.TRUE && theDisruptor.getRingBuffer().remainingCapacity() == 0; } /** - * Creates and returns a new {@code RingBufferAdmin} that instruments the - * ringbuffer of this {@code AsyncLoggerConfig}. + * Creates and returns a new {@code RingBufferAdmin} that instruments the ringbuffer of this + * {@code AsyncLoggerConfig}. * * @param contextName name of the {@code LoggerContext} * @param loggerConfigName name of the logger config http://git-wip-us.apache.org/repos/asf/logging-log4j2/blob/37c992bf/log4j-core/src/main/java/org/apache/logging/log4j/core/async/RingBufferLogEvent.java ---------------------------------------------------------------------- diff --git a/log4j-core/src/main/java/org/apache/logging/log4j/core/async/RingBufferLogEvent.java b/log4j-core/src/main/java/org/apache/logging/log4j/core/async/RingBufferLogEvent.java index 74feb32..7654a2b 100644 --- a/log4j-core/src/main/java/org/apache/logging/log4j/core/async/RingBufferLogEvent.java +++ b/log4j-core/src/main/java/org/apache/logging/log4j/core/async/RingBufferLogEvent.java @@ -39,6 +39,10 @@ import com.lmax.disruptor.EventFactory; * the life of the RingBuffer. */ public class RingBufferLogEvent implements LogEvent { + + /** The {@code EventFactory} for {@code RingBufferLogEvent}s. */ + public static final Factory FACTORY = new Factory(); + private static final long serialVersionUID = 8462119088943934758L; /** @@ -52,9 +56,6 @@ public class RingBufferLogEvent implements LogEvent { } } - /** The {@code EventFactory} for {@code RingBufferLogEvent}s. */ - public static final Factory FACTORY = new Factory(); - private transient AsyncLogger asyncLogger; private String loggerName; private Marker marker; @@ -292,7 +293,6 @@ public class RingBufferLogEvent implements LogEvent { .setThreadName(threadName) // .setThrown(getThrown()) // may deserialize from thrownProxy .setThrownProxy(thrownProxy) // avoid unnecessarily creating thrownProxy - .setTimeMillis(currentTimeMillis) // - ; + .setTimeMillis(currentTimeMillis); } }
