You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@logging.apache.org by rp...@apache.org on 2015/01/12 09:53:13 UTC

[16/18] logging-log4j2 git commit: replace StringBuilder based API with Buffer-based API (providing separate TextBuffer and BinaryBuffer implementations where appropriate)

http://git-wip-us.apache.org/repos/asf/logging-log4j2/blob/08386d0e/log4j-core/src/main/java/org/apache/logging/log4j/core/pattern/LineSeparatorPatternConverter.java
----------------------------------------------------------------------
diff --git a/log4j-core/src/main/java/org/apache/logging/log4j/core/pattern/LineSeparatorPatternConverter.java b/log4j-core/src/main/java/org/apache/logging/log4j/core/pattern/LineSeparatorPatternConverter.java
index 6d41bf9..6886a88 100644
--- a/log4j-core/src/main/java/org/apache/logging/log4j/core/pattern/LineSeparatorPatternConverter.java
+++ b/log4j-core/src/main/java/org/apache/logging/log4j/core/pattern/LineSeparatorPatternConverter.java
@@ -16,6 +16,8 @@
  */
 package org.apache.logging.log4j.core.pattern;
 
+import java.nio.charset.Charset;
+
 import org.apache.logging.log4j.core.LogEvent;
 import org.apache.logging.log4j.core.config.plugins.Plugin;
 import org.apache.logging.log4j.core.util.Constants;
@@ -28,39 +30,45 @@ import org.apache.logging.log4j.core.util.Constants;
 public final class LineSeparatorPatternConverter extends LogEventPatternConverter {
 
     /**
-     * Singleton.
-     */
-    private static final LineSeparatorPatternConverter INSTANCE = new LineSeparatorPatternConverter();
-
-    /**
      * Line separator.
      */
     private final String lineSep;
+    private final byte[] lineSepBytes;
 
     /**
      * Private constructor.
      */
-    private LineSeparatorPatternConverter() {
-        super("Line Sep", "lineSep");
+    private LineSeparatorPatternConverter(final FormattingInfo formattingInfo) {
+        super("Line Sep", "lineSep", formattingInfo);
         lineSep = Constants.LINE_SEPARATOR;
+        lineSepBytes = lineSep.getBytes(); // Charset does not matter for this particular string
     }
 
     /**
      * Obtains an instance of pattern converter.
      *
-     * @param options
-     *        options, may be null.
+     * @param options options, may be null.
      * @return instance of pattern converter.
      */
-    public static LineSeparatorPatternConverter newInstance(final String[] options) {
-        return INSTANCE;
+    public static LineSeparatorPatternConverter newInstance(final String[] options, final FormattingInfo formattingInfo) {
+        return new LineSeparatorPatternConverter(formattingInfo);
     }
 
     /**
      * {@inheritDoc}
      */
     @Override
-    public void format(final LogEvent event, final StringBuilder toAppendTo) {
+    public void format(final LogEvent event, final TextBuffer toAppendTo) {
+        // note: this converter ignores FormattingInfo on purpose
         toAppendTo.append(lineSep);
     }
+
+    /**
+     * {@inheritDoc}
+     */
+    @Override
+    public void format(final LogEvent event, final BinaryBuffer toAppendTo, final Charset charset) {
+        // note: this converter ignores FormattingInfo on purpose
+        toAppendTo.append(lineSepBytes);
+    }
 }

http://git-wip-us.apache.org/repos/asf/logging-log4j2/blob/08386d0e/log4j-core/src/main/java/org/apache/logging/log4j/core/pattern/LiteralPatternConverter.java
----------------------------------------------------------------------
diff --git a/log4j-core/src/main/java/org/apache/logging/log4j/core/pattern/LiteralPatternConverter.java b/log4j-core/src/main/java/org/apache/logging/log4j/core/pattern/LiteralPatternConverter.java
index 64c41fe..8c3407c 100644
--- a/log4j-core/src/main/java/org/apache/logging/log4j/core/pattern/LiteralPatternConverter.java
+++ b/log4j-core/src/main/java/org/apache/logging/log4j/core/pattern/LiteralPatternConverter.java
@@ -16,11 +16,13 @@
  */
 package org.apache.logging.log4j.core.pattern;
 
+import java.nio.charset.Charset;
+
 import org.apache.logging.log4j.core.LogEvent;
 import org.apache.logging.log4j.core.config.Configuration;
+import org.apache.logging.log4j.core.util.Charsets;
 import org.apache.logging.log4j.core.util.OptionConverter;
 
-
 /**
  * Formats a string literal.
  */
@@ -29,9 +31,8 @@ public final class LiteralPatternConverter extends LogEventPatternConverter impl
      * String literal.
      */
     private final String literal;
-
+    private byte[] cachedLiteralBytes;
     private final Configuration config;
-
     private final boolean substitute;
 
     /**
@@ -43,7 +44,7 @@ public final class LiteralPatternConverter extends LogEventPatternConverter impl
      *            sequences like "\" followed by "t" (backslash+t) are converted to special characters like '\t' (tab).
      */
     public LiteralPatternConverter(final Configuration config, final String literal, final boolean convertBackslashes) {
-        super("Literal", "literal");
+        super("Literal", "literal", FormattingInfo.getDefault());
         this.literal = convertBackslashes ? OptionConverter.convertSpecialChars(literal) : literal; // LOG4J2-829
         this.config = config;
         substitute = config != null && literal.contains("${");
@@ -53,15 +54,36 @@ public final class LiteralPatternConverter extends LogEventPatternConverter impl
      * {@inheritDoc}
      */
     @Override
-    public void format(final LogEvent event, final StringBuilder toAppendTo) {
+    public void format(final LogEvent event, final TextBuffer toAppendTo) {
+        // note: this converter ignores FormattingInfo on purpose
         toAppendTo.append(substitute ? config.getStrSubstitutor().replace(event, literal) : literal);
     }
-    
+
+    /**
+     * {@inheritDoc}
+     */
+    @Override
+    public void format(final LogEvent event, final BinaryBuffer toAppendTo, final Charset charset) {
+        // note: this converter ignores FormattingInfo on purpose
+        if (substitute) { // cannot use cache...
+            toAppendTo.append(config.getStrSubstitutor().replace(event, literal));
+        } else {
+            toAppendTo.append(cachedLiteral(charset));
+        }
+    }
+
+    private byte[] cachedLiteral(Charset charset) {
+        if (cachedLiteralBytes == null) {
+            cachedLiteralBytes = Charsets.getBytes(literal, charset);
+        }
+        return cachedLiteralBytes;
+    }
+
     /**
      * {@inheritDoc}
      */
     @Override
-    public void format(final Object obj, final StringBuilder output) {
+    public void format(final Object obj, final Buffer output) {
         output.append(substitute ? config.getStrSubstitutor().replace(literal) : literal);
     }
 
@@ -69,7 +91,7 @@ public final class LiteralPatternConverter extends LogEventPatternConverter impl
      * {@inheritDoc}
      */
     @Override
-    public void format(final StringBuilder output, final Object... objects) {
+    public void format(final Buffer output, final Object... objects) {
         output.append(substitute ? config.getStrSubstitutor().replace(literal) : literal);
     }
 

http://git-wip-us.apache.org/repos/asf/logging-log4j2/blob/08386d0e/log4j-core/src/main/java/org/apache/logging/log4j/core/pattern/LogEventPatternConverter.java
----------------------------------------------------------------------
diff --git a/log4j-core/src/main/java/org/apache/logging/log4j/core/pattern/LogEventPatternConverter.java b/log4j-core/src/main/java/org/apache/logging/log4j/core/pattern/LogEventPatternConverter.java
index d42f300..a820b44 100644
--- a/log4j-core/src/main/java/org/apache/logging/log4j/core/pattern/LogEventPatternConverter.java
+++ b/log4j-core/src/main/java/org/apache/logging/log4j/core/pattern/LogEventPatternConverter.java
@@ -1,67 +1,84 @@
-/*
- * 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.pattern;
-
-import org.apache.logging.log4j.core.LogEvent;
-
-/**
- * LoggingEventPatternConverter is a base class for pattern converters
- * that can format information from instances of LoggingEvent.
- */
-public abstract class LogEventPatternConverter extends AbstractPatternConverter {
-
-    /**
-     * Constructs an instance of LoggingEventPatternConverter.
-     *
-     * @param name  name of converter.
-     * @param style CSS style for output.
-     */
-    protected LogEventPatternConverter(final String name, final String style) {
-        super(name, style);
-    }
-
-    /**
-     * Formats an event into a string buffer.
-     *
-     * @param event      event to format, may not be null.
-     * @param toAppendTo string buffer to which the formatted event will be appended.  May not be null.
-     */
-    public abstract void format(final LogEvent event, final StringBuilder toAppendTo);
-
-    /**
-     * {@inheritDoc}
-     */
-    @Override
-    public void format(final Object obj, final StringBuilder output) {
-        if (obj instanceof LogEvent) {
-            format((LogEvent) obj, output);
-        }
-    }
-
-    /**
-     * Normally pattern converters are not meant to handle Exceptions although few pattern converters might.
-     * <p>
-     * By examining the return values for this method, the containing layout will determine whether it handles
-     * throwables or not.
-     * </p>
-     *
-     * @return true if this PatternConverter handles throwables
-     */
-    public boolean handlesThrowable() {
-        return false;
-    }
-}
+/*
+ * 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.pattern;
+
+import java.nio.charset.Charset;
+
+import org.apache.logging.log4j.core.LogEvent;
+import org.apache.logging.log4j.core.util.Assert;
+
+/**
+ * LogEventPatternConverter is a base class for pattern converters that can format information from instances of
+ * LoggingEvent.
+ */
+public abstract class LogEventPatternConverter extends AbstractPatternConverter {
+
+    /**
+     * Constructs an instance of LogEventPatternConverter.
+     *
+     * @param name name of converter.
+     * @param style CSS style for output.
+     * @param formattingInfo the formatting info (must be non-{@code null})
+     */
+    protected LogEventPatternConverter(final String name, final String style, final FormattingInfo formattingInfo) {
+        super(name, style, Assert.requireNonNull(formattingInfo, "formattingInfo"));
+    }
+
+    /**
+     * Formats an event into the specified text buffer.
+     *
+     * @param event event to format, may not be null.
+     * @param toAppendTo text buffer to which the formatted event will be appended. May not be null.
+     */
+    public abstract void format(final LogEvent event, final TextBuffer toAppendTo);
+
+    /**
+     * Formats an event into the specified binary buffer.
+     *
+     * @param event event to format, may not be null.
+     * @param toAppendTo binary buffer to which the formatted event will be appended. May not be null.
+     * @param charset the Charset to use when converting text to bytes
+     */
+    public abstract void format(final LogEvent event, final BinaryBuffer toAppendTo, final Charset charset);
+
+    /**
+     * {@inheritDoc}
+     */
+    @Override
+    public void format(final Object obj, final Buffer output) {
+        if (obj instanceof LogEvent) {
+            if (output instanceof TextBuffer) {
+                format((LogEvent) obj, (TextBuffer) output);
+            } else {
+                format((LogEvent) obj, (BinaryBuffer) output, getCharset());
+            }
+        }
+    }
+
+    /**
+     * Normally pattern converters are not meant to handle Exceptions although few pattern converters might.
+     * <p>
+     * By examining the return values for this method, the containing layout will determine whether it handles
+     * throwables or not.
+     * </p>
+     *
+     * @return true if this PatternConverter handles throwables
+     */
+    public boolean handlesThrowable() {
+        return false;
+    }
+}

http://git-wip-us.apache.org/repos/asf/logging-log4j2/blob/08386d0e/log4j-core/src/main/java/org/apache/logging/log4j/core/pattern/LoggerPatternConverter.java
----------------------------------------------------------------------
diff --git a/log4j-core/src/main/java/org/apache/logging/log4j/core/pattern/LoggerPatternConverter.java b/log4j-core/src/main/java/org/apache/logging/log4j/core/pattern/LoggerPatternConverter.java
index 2b5651b..5c4c90e 100644
--- a/log4j-core/src/main/java/org/apache/logging/log4j/core/pattern/LoggerPatternConverter.java
+++ b/log4j-core/src/main/java/org/apache/logging/log4j/core/pattern/LoggerPatternConverter.java
@@ -16,29 +16,25 @@
  */
 package org.apache.logging.log4j.core.pattern;
 
+import java.nio.charset.Charset;
+
 import org.apache.logging.log4j.core.LogEvent;
 import org.apache.logging.log4j.core.config.plugins.Plugin;
 
-
 /**
  * Formats a logger name.
  */
 @Plugin(name = "LoggerPatternConverter", category = PatternConverter.CATEGORY)
 @ConverterKeys({ "c", "logger" })
 public final class LoggerPatternConverter extends NamePatternConverter {
-    /**
-     * Singleton.
-     */
-    private static final LoggerPatternConverter INSTANCE =
-        new LoggerPatternConverter(null);
 
     /**
      * Private constructor.
      *
      * @param options options, may be null.
      */
-    private LoggerPatternConverter(final String[] options) {
-        super("Logger", "logger", options);
+    private LoggerPatternConverter(final String[] options, final FormattingInfo formattingInfo) {
+        super("Logger", "logger", options, formattingInfo);
     }
 
     /**
@@ -47,20 +43,30 @@ public final class LoggerPatternConverter extends NamePatternConverter {
      * @param options options, may be null.
      * @return instance of pattern converter.
      */
-    public static LoggerPatternConverter newInstance(
-        final String[] options) {
+    public static LoggerPatternConverter newInstance(final String[] options, final FormattingInfo formattingInfo) {
         if (options == null || options.length == 0) {
-            return INSTANCE;
+            return new LoggerPatternConverter(null, formattingInfo);
         }
 
-        return new LoggerPatternConverter(options);
+        return new LoggerPatternConverter(options, formattingInfo);
     }
 
     /**
      * {@inheritDoc}
      */
     @Override
-    public void format(final LogEvent event, final StringBuilder toAppendTo) {
+    public void format(final LogEvent event, final TextBuffer toAppendTo) {
         toAppendTo.append(abbreviate(event.getLoggerName()));
     }
+
+    /**
+     * Format a logging event.
+     *
+     * @param event event to format.
+     * @param toAppendTo buffer to which class name will be appended.
+     */
+    @Override
+    public void format(final LogEvent event, final BinaryBuffer toAppendTo, final Charset charset) {
+        toAppendTo.append(abbreviateToBinary(event.getLoggerName(), charset));
+    }
 }

http://git-wip-us.apache.org/repos/asf/logging-log4j2/blob/08386d0e/log4j-core/src/main/java/org/apache/logging/log4j/core/pattern/MapPatternConverter.java
----------------------------------------------------------------------
diff --git a/log4j-core/src/main/java/org/apache/logging/log4j/core/pattern/MapPatternConverter.java b/log4j-core/src/main/java/org/apache/logging/log4j/core/pattern/MapPatternConverter.java
index e75181b..ed7a193 100644
--- a/log4j-core/src/main/java/org/apache/logging/log4j/core/pattern/MapPatternConverter.java
+++ b/log4j-core/src/main/java/org/apache/logging/log4j/core/pattern/MapPatternConverter.java
@@ -16,19 +16,16 @@
  */
 package org.apache.logging.log4j.core.pattern;
 
+import java.nio.charset.Charset;
 import java.util.Map;
-import java.util.Set;
-import java.util.TreeSet;
 
 import org.apache.logging.log4j.core.LogEvent;
 import org.apache.logging.log4j.core.config.plugins.Plugin;
 import org.apache.logging.log4j.message.MapMessage;
 
 /**
- * Able to handle the contents of the LogEvent's MapMessage and either
- * output the entire contents of the properties in a similar format to the
- * java.util.Hashtable.toString(), or to output the value of a specific key
- * within the Map.
+ * Able to handle the contents of the LogEvent's MapMessage and either output the entire contents of the properties in a
+ * similar format to the java.util.Hashtable.toString(), or to output the value of a specific key within the Map.
  */
 @Plugin(name = "MapPatternConverter", category = PatternConverter.CATEGORY)
 @ConverterKeys({ "K", "map", "MAP" })
@@ -43,8 +40,8 @@ public final class MapPatternConverter extends LogEventPatternConverter {
      *
      * @param options options, may be null.
      */
-    private MapPatternConverter(final String[] options) {
-        super(options != null && options.length > 0 ? "MAP{" + options[0] + '}' : "MAP", "map");
+    private MapPatternConverter(final String[] options, final FormattingInfo formattingInfo) {
+        super((options != null && options.length > 0) ? "MAP{" + options[0] + '}' : "MAP", "map", formattingInfo);
         key = options != null && options.length > 0 ? options[0] : null;
     }
 
@@ -54,46 +51,50 @@ public final class MapPatternConverter extends LogEventPatternConverter {
      * @param options options, may be null or first element contains name of property to format.
      * @return instance of PropertiesPatternConverter.
      */
-    public static MapPatternConverter newInstance(final String[] options) {
-        return new MapPatternConverter(options);
+    public static MapPatternConverter newInstance(final String[] options, final FormattingInfo formattingInfo) {
+        return new MapPatternConverter(options, formattingInfo);
     }
 
     /**
      * {@inheritDoc}
      */
     @Override
-    public void format(final LogEvent event, final StringBuilder toAppendTo) {
-        MapMessage msg;
-        if (event.getMessage() instanceof MapMessage) {
-            msg = (MapMessage) event.getMessage();
-        } else {
+    public void format(final LogEvent event, final TextBuffer toAppendTo) {
+        if (!(event.getMessage() instanceof MapMessage)) {
             return;
         }
-        final Map<String, String> map = msg.getData();
+        final Map<String, String> map = ((MapMessage) event.getMessage()).getData();
         // if there is no additional options, we output every single
         // Key/Value pair for the Map in a similar format to Hashtable.toString()
         if (key == null) {
-            if (map.isEmpty()) {
-                toAppendTo.append("{}");
-                return;
+            toAppendTo.append(getCachedFormattedString(map));
+        } else {
+            // otherwise they just want a single key output
+            final String val = map.get(key);
+            if (val != null) {
+                toAppendTo.append(getCachedFormattedString(val));
             }
-            final StringBuilder sb = new StringBuilder("{");
-            final Set<String> keys = new TreeSet<String>(map.keySet());
-            for (final String key : keys) {
-                if (sb.length() > 1) {
-                    sb.append(", ");
-                }
-                sb.append(key).append('=').append(map.get(key));
+        }
+    }
 
-            }
-            sb.append('}');
-            toAppendTo.append(sb);
+    /**
+     * {@inheritDoc}
+     */
+    @Override
+    public void format(final LogEvent event, final BinaryBuffer toAppendTo, final Charset charset) {
+        if (!(event.getMessage() instanceof MapMessage)) {
+            return;
+        }
+        final Map<String, String> map = ((MapMessage) event.getMessage()).getData();
+        // if there is no additional options, we output every single
+        // Key/Value pair for the Map in a similar format to Hashtable.toString()
+        if (key == null) {
+            toAppendTo.append(getCachedFormattedBytes(map, charset));
         } else {
             // otherwise they just want a single key output
             final String val = map.get(key);
-
             if (val != null) {
-                toAppendTo.append(val);
+                toAppendTo.append(getCachedFormattedBytes(val, charset));
             }
         }
     }

http://git-wip-us.apache.org/repos/asf/logging-log4j2/blob/08386d0e/log4j-core/src/main/java/org/apache/logging/log4j/core/pattern/MarkerPatternConverter.java
----------------------------------------------------------------------
diff --git a/log4j-core/src/main/java/org/apache/logging/log4j/core/pattern/MarkerPatternConverter.java b/log4j-core/src/main/java/org/apache/logging/log4j/core/pattern/MarkerPatternConverter.java
index 020f832..d2d48ed 100644
--- a/log4j-core/src/main/java/org/apache/logging/log4j/core/pattern/MarkerPatternConverter.java
+++ b/log4j-core/src/main/java/org/apache/logging/log4j/core/pattern/MarkerPatternConverter.java
@@ -16,6 +16,8 @@
  */
 package org.apache.logging.log4j.core.pattern;
 
+import java.nio.charset.Charset;
+
 import org.apache.logging.log4j.Marker;
 import org.apache.logging.log4j.core.LogEvent;
 import org.apache.logging.log4j.core.config.plugins.Plugin;
@@ -29,10 +31,11 @@ public final class MarkerPatternConverter extends LogEventPatternConverter {
 
     /**
      * Private constructor.
+     * 
      * @param options options, may be null.
      */
-    private MarkerPatternConverter(final String[] options) {
-        super("Marker", "marker");
+    private MarkerPatternConverter(final String[] options, final FormattingInfo formattingInfo) {
+        super("Marker", "marker", formattingInfo);
     }
 
     /**
@@ -41,18 +44,29 @@ public final class MarkerPatternConverter extends LogEventPatternConverter {
      * @param options options, may be null.
      * @return instance of pattern converter.
      */
-    public static MarkerPatternConverter newInstance(final String[] options) {
-        return new MarkerPatternConverter(options);
+    public static MarkerPatternConverter newInstance(final String[] options, final FormattingInfo formattingInfo) {
+        return new MarkerPatternConverter(options, formattingInfo);
+    }
+
+    /**
+     * {@inheritDoc}
+     */
+    @Override
+    public void format(final LogEvent event, final TextBuffer toAppendTo) {
+        final Marker marker = event.getMarker();
+        if (marker != null) {
+            toAppendTo.append(getCachedFormattedString(marker));
+        }
     }
 
     /**
      * {@inheritDoc}
      */
     @Override
-    public void format(final LogEvent event, final StringBuilder toAppendTo) {
+    public void format(final LogEvent event, final BinaryBuffer toAppendTo, final Charset charset) {
         final Marker marker = event.getMarker();
         if (marker != null) {
-            toAppendTo.append(marker.toString());
+            toAppendTo.append(getCachedFormattedBytes(marker, charset));
         }
     }
 }

http://git-wip-us.apache.org/repos/asf/logging-log4j2/blob/08386d0e/log4j-core/src/main/java/org/apache/logging/log4j/core/pattern/MdcPatternConverter.java
----------------------------------------------------------------------
diff --git a/log4j-core/src/main/java/org/apache/logging/log4j/core/pattern/MdcPatternConverter.java b/log4j-core/src/main/java/org/apache/logging/log4j/core/pattern/MdcPatternConverter.java
index 665ce05..8fa5b53 100644
--- a/log4j-core/src/main/java/org/apache/logging/log4j/core/pattern/MdcPatternConverter.java
+++ b/log4j-core/src/main/java/org/apache/logging/log4j/core/pattern/MdcPatternConverter.java
@@ -16,21 +16,21 @@
  */
 package org.apache.logging.log4j.core.pattern;
 
+import java.nio.charset.Charset;
 import java.util.Map;
 import java.util.Set;
 import java.util.TreeSet;
 
 import org.apache.logging.log4j.core.LogEvent;
 import org.apache.logging.log4j.core.config.plugins.Plugin;
+import org.apache.logging.log4j.message.MapMessage;
 
 /**
- * Able to handle the contents of the LogEvent's MDC and either
- * output the entire contents of the properties in a similar format to the
- * java.util.Hashtable.toString(), or to output the value of a specific key
- * within the property bundle
- * when this pattern converter has the option set.
+ * Able to handle the contents of the LogEvent's MDC and either output the entire contents of the properties in a
+ * similar format to the java.util.Hashtable.toString(), or to output the value of a specific key within the property
+ * bundle when this pattern converter has the option set.
  */
- @Plugin(name = "MdcPatternConverter", category = PatternConverter.CATEGORY)
+@Plugin(name = "MdcPatternConverter", category = PatternConverter.CATEGORY)
 @ConverterKeys({ "X", "mdc", "MDC" })
 public final class MdcPatternConverter extends LogEventPatternConverter {
     /**
@@ -43,8 +43,8 @@ public final class MdcPatternConverter extends LogEventPatternConverter {
      *
      * @param options options, may be null.
      */
-    private MdcPatternConverter(final String[] options) {
-        super(options != null && options.length > 0 ? "MDC{" + options[0] + '}' : "MDC", "mdc");
+    private MdcPatternConverter(final String[] options, final FormattingInfo formattingInfo) {
+        super((options != null && options.length > 0) ? "MDC{" + options[0] + '}' : "MDC", "mdc", formattingInfo);
         key = options != null && options.length > 0 ? options[0] : null;
     }
 
@@ -54,42 +54,44 @@ public final class MdcPatternConverter extends LogEventPatternConverter {
      * @param options options, may be null or first element contains name of property to format.
      * @return instance of PropertiesPatternConverter.
      */
-    public static MdcPatternConverter newInstance(final String[] options) {
-        return new MdcPatternConverter(options);
+    public static MdcPatternConverter newInstance(final String[] options, final FormattingInfo formattingInfo) {
+        return new MdcPatternConverter(options, formattingInfo);
     }
 
     /**
      * {@inheritDoc}
      */
     @Override
-    public void format(final LogEvent event, final StringBuilder toAppendTo) {
-        final Map<String, String> contextMap = event.getContextMap();
+    public void format(final LogEvent event, final TextBuffer toAppendTo) {
+        final Map<String, String> map = event.getContextMap();
         // if there is no additional options, we output every single
-        // Key/Value pair for the MDC in a similar format to Hashtable.toString()
+        // Key/Value pair for the Map in a similar format to Hashtable.toString()
         if (key == null) {
-
-
-            if (contextMap == null || contextMap.isEmpty()) {
-                toAppendTo.append("{}");
-                return;
+            toAppendTo.append(getCachedFormattedString(map));
+        } else {
+            // otherwise they just want a single key output
+            final String val = map.get(key);
+            if (val != null) {
+                toAppendTo.append(getCachedFormattedString(val));
             }
-            final StringBuilder sb = new StringBuilder("{");
-            final Set<String> keys = new TreeSet<String>(contextMap.keySet());
-            for (final String key : keys) {
-                if (sb.length() > 1) {
-                    sb.append(", ");
-                }
-                sb.append(key).append('=').append(contextMap.get(key));
+        }
+    }
 
-            }
-            sb.append('}');
-            toAppendTo.append(sb);
-        } else if (contextMap != null) {
+    /**
+     * {@inheritDoc}
+     */
+    @Override
+    public void format(final LogEvent event, final BinaryBuffer toAppendTo, final Charset charset) {
+        final Map<String, String> map = event.getContextMap();
+        // if there is no additional options, we output every single
+        // Key/Value pair for the Map in a similar format to Hashtable.toString()
+        if (key == null) {
+            toAppendTo.append(getCachedFormattedBytes(map, charset));
+        } else {
             // otherwise they just want a single key output
-            final Object val = contextMap.get(key);
-
+            final String val = map.get(key);
             if (val != null) {
-                toAppendTo.append(val);
+                toAppendTo.append(getCachedFormattedBytes(val, charset));
             }
         }
     }

http://git-wip-us.apache.org/repos/asf/logging-log4j2/blob/08386d0e/log4j-core/src/main/java/org/apache/logging/log4j/core/pattern/MessagePatternConverter.java
----------------------------------------------------------------------
diff --git a/log4j-core/src/main/java/org/apache/logging/log4j/core/pattern/MessagePatternConverter.java b/log4j-core/src/main/java/org/apache/logging/log4j/core/pattern/MessagePatternConverter.java
index d0adc7f..33531ee 100644
--- a/log4j-core/src/main/java/org/apache/logging/log4j/core/pattern/MessagePatternConverter.java
+++ b/log4j-core/src/main/java/org/apache/logging/log4j/core/pattern/MessagePatternConverter.java
@@ -16,9 +16,12 @@
  */
 package org.apache.logging.log4j.core.pattern;
 
+import java.nio.charset.Charset;
+
 import org.apache.logging.log4j.core.LogEvent;
 import org.apache.logging.log4j.core.config.Configuration;
 import org.apache.logging.log4j.core.config.plugins.Plugin;
+import org.apache.logging.log4j.core.util.Charsets;
 import org.apache.logging.log4j.message.Message;
 import org.apache.logging.log4j.message.MultiformatMessage;
 
@@ -35,10 +38,12 @@ public final class MessagePatternConverter extends LogEventPatternConverter {
 
     /**
      * Private constructor.
+     * 
      * @param options options, may be null.
      */
-    private MessagePatternConverter(final Configuration config, final String[] options) {
-        super("Message", "message");
+    private MessagePatternConverter(final Configuration config, final String[] options,
+            final FormattingInfo formattingInfo) {
+        super("Message", "message", formattingInfo);
         formats = options;
         this.config = config;
     }
@@ -50,29 +55,49 @@ public final class MessagePatternConverter extends LogEventPatternConverter {
      * @param options options, may be null.
      * @return instance of pattern converter.
      */
-    public static MessagePatternConverter newInstance(final Configuration config, final String[] options) {
-        return new MessagePatternConverter(config, options);
+    public static MessagePatternConverter newInstance(final Configuration config, final String[] options,
+            final FormattingInfo formattingInfo) {
+        return new MessagePatternConverter(config, options, formattingInfo);
     }
 
     /**
      * {@inheritDoc}
      */
     @Override
-    public void format(final LogEvent event, final StringBuilder toAppendTo) {
+    public void format(final LogEvent event, final TextBuffer toAppendTo) {
+        final Message msg = event.getMessage();
+        if (msg != null) {
+            final String msgString = messageString(event, msg);
+            toAppendTo.append(msgString, getFormattingInfo());
+        }
+    }
+
+    /**
+     * Format a logging event.
+     *
+     * @param event event to format.
+     * @param toAppendTo buffer to which class name will be appended.
+     */
+    @Override
+    public void format(final LogEvent event, final BinaryBuffer toAppendTo, final Charset charset) {
         final Message msg = event.getMessage();
         if (msg != null) {
-            String result;
-            if (msg instanceof MultiformatMessage) {
-                result = ((MultiformatMessage) msg).getFormattedMessage(formats);
-            } else {
-                result = msg.getFormattedMessage();
-            }
-            if (result != null) {
-                toAppendTo.append(config != null && result.contains("${") ?
-                    config.getStrSubstitutor().replace(event, result) : result);
-            } else {
-                toAppendTo.append("null");
-            }
+            final String msgString = messageString(event, msg);
+            final String formatted = applyFormattingInfo(msgString);
+            toAppendTo.append(Charsets.getBytes(formatted, charset));
+        }
+    }
+
+    private String messageString(final LogEvent event, final Message msg) {
+        String result;
+        if (msg instanceof MultiformatMessage) {
+            result = ((MultiformatMessage) msg).getFormattedMessage(formats);
+        } else {
+            result = msg.getFormattedMessage();
+        }
+        if (result == null) {
+            return "null";
         }
+        return (config != null && result.contains("${")) ? config.getStrSubstitutor().replace(event, result) : result;
     }
 }

http://git-wip-us.apache.org/repos/asf/logging-log4j2/blob/08386d0e/log4j-core/src/main/java/org/apache/logging/log4j/core/pattern/MethodLocationPatternConverter.java
----------------------------------------------------------------------
diff --git a/log4j-core/src/main/java/org/apache/logging/log4j/core/pattern/MethodLocationPatternConverter.java b/log4j-core/src/main/java/org/apache/logging/log4j/core/pattern/MethodLocationPatternConverter.java
index 457b7a6..9c2e6ff 100644
--- a/log4j-core/src/main/java/org/apache/logging/log4j/core/pattern/MethodLocationPatternConverter.java
+++ b/log4j-core/src/main/java/org/apache/logging/log4j/core/pattern/MethodLocationPatternConverter.java
@@ -16,6 +16,8 @@
  */
 package org.apache.logging.log4j.core.pattern;
 
+import java.nio.charset.Charset;
+
 import org.apache.logging.log4j.core.LogEvent;
 import org.apache.logging.log4j.core.config.plugins.Plugin;
 
@@ -26,17 +28,12 @@ import org.apache.logging.log4j.core.config.plugins.Plugin;
 @Plugin(name = "MethodLocationPatternConverter", category = PatternConverter.CATEGORY)
 @ConverterKeys({ "M", "method" })
 public final class MethodLocationPatternConverter extends LogEventPatternConverter {
-    /**
-     * Singleton.
-     */
-    private static final MethodLocationPatternConverter INSTANCE =
-        new MethodLocationPatternConverter();
 
     /**
      * Private constructor.
      */
-    private MethodLocationPatternConverter() {
-        super("Method", "method");
+    private MethodLocationPatternConverter(final FormattingInfo formattingInfo) {
+        super("Method", "method", formattingInfo);
     }
 
     /**
@@ -45,19 +42,29 @@ public final class MethodLocationPatternConverter extends LogEventPatternConvert
      * @param options options, may be null.
      * @return instance of MethodLocationPatternConverter.
      */
-    public static MethodLocationPatternConverter newInstance(final String[] options) {
-        return INSTANCE;
+    public static MethodLocationPatternConverter newInstance(final String[] options, final FormattingInfo formattingInfo) {
+        return new MethodLocationPatternConverter(formattingInfo);
     }
 
     /**
      * {@inheritDoc}
      */
     @Override
-    public void format(final LogEvent event, final StringBuilder toAppendTo) {
+    public void format(final LogEvent event, final TextBuffer toAppendTo) {
         final StackTraceElement element = event.getSource();
+        if (element != null) {
+            toAppendTo.append(getCachedFormattedString(element.getMethodName()));
+        }
+    }
 
+    /**
+     * {@inheritDoc}
+     */
+    @Override
+    public void format(final LogEvent event, final BinaryBuffer toAppendTo, final Charset charset) {
+        final StackTraceElement element = event.getSource();
         if (element != null) {
-            toAppendTo.append(element.getMethodName());
+            toAppendTo.append(getCachedFormattedBytes(element.getMethodName(), charset));
         }
     }
 }

http://git-wip-us.apache.org/repos/asf/logging-log4j2/blob/08386d0e/log4j-core/src/main/java/org/apache/logging/log4j/core/pattern/NamePatternConverter.java
----------------------------------------------------------------------
diff --git a/log4j-core/src/main/java/org/apache/logging/log4j/core/pattern/NamePatternConverter.java b/log4j-core/src/main/java/org/apache/logging/log4j/core/pattern/NamePatternConverter.java
index b35c787..635ea4c 100644
--- a/log4j-core/src/main/java/org/apache/logging/log4j/core/pattern/NamePatternConverter.java
+++ b/log4j-core/src/main/java/org/apache/logging/log4j/core/pattern/NamePatternConverter.java
@@ -16,6 +16,8 @@
  */
 package org.apache.logging.log4j.core.pattern;
 
+import java.nio.charset.Charset;
+
 
 /**
  * Abstract base class for other pattern converters which can return only parts of their name.
@@ -33,8 +35,8 @@ public abstract class NamePatternConverter extends LogEventPatternConverter {
      * @param style   style name for associated output.
      * @param options options, may be null, first element will be interpreted as an abbreviation pattern.
      */
-    protected NamePatternConverter(final String name, final String style, final String[] options) {
-        super(name, style);
+    protected NamePatternConverter(final String name, final String style, final String[] options, final FormattingInfo formattingInfo) {
+        super(name, style, formattingInfo);
 
         if (options != null && options.length > 0) {
             abbreviator = NameAbbreviator.getAbbreviator(options[0]);
@@ -42,14 +44,39 @@ public abstract class NamePatternConverter extends LogEventPatternConverter {
             abbreviator = NameAbbreviator.getDefaultAbbreviator();
         }
     }
+    
+    /**
+     * Abbreviates specified name.
+     *
+     * @param name the name to abbreviate.
+     * @return The abbreviated name.
+     */
+    @Override
+    protected String convert(final Object name) {
+        return abbreviator.abbreviate(name.toString());
+    }
 
     /**
-     * Abbreviate name in string buffer.
+     * Abbreviates specified name.
      *
-     * @param buf       string buffer containing name.
+     * @param name the name to abbreviate.
      * @return The abbreviated name.
      */
-    protected final String abbreviate(final String buf) {
-        return abbreviator.abbreviate(buf);
+    protected final String abbreviate(final String name) {
+        if (abbreviator == NameAbbreviator.getDefaultAbbreviator() && !hasFormattingInfo) {
+            return name; // no formatting to do
+        }
+        return getCachedFormattedString(name);
+    }
+
+    /**
+     * Abbreviates specified name and returns the encoded result.
+     *
+     * @param name the name to abbreviate.
+     * @param charset the charset to use when converting text to bytes
+     * @return The abbreviated name as a byte array.
+     */
+    protected final byte[] abbreviateToBinary(final String name, final Charset charset) {
+        return getCachedFormattedBytes(name, charset);
     }
 }

http://git-wip-us.apache.org/repos/asf/logging-log4j2/blob/08386d0e/log4j-core/src/main/java/org/apache/logging/log4j/core/pattern/NdcPatternConverter.java
----------------------------------------------------------------------
diff --git a/log4j-core/src/main/java/org/apache/logging/log4j/core/pattern/NdcPatternConverter.java b/log4j-core/src/main/java/org/apache/logging/log4j/core/pattern/NdcPatternConverter.java
index 9a3b972..ec3b0a4 100644
--- a/log4j-core/src/main/java/org/apache/logging/log4j/core/pattern/NdcPatternConverter.java
+++ b/log4j-core/src/main/java/org/apache/logging/log4j/core/pattern/NdcPatternConverter.java
@@ -16,43 +16,48 @@
  */
 package org.apache.logging.log4j.core.pattern;
 
+import java.nio.charset.Charset;
+
 import org.apache.logging.log4j.core.LogEvent;
 import org.apache.logging.log4j.core.config.plugins.Plugin;
 
-
 /**
  * Returns the event's NDC in a StringBuilder.
  */
 @Plugin(name = "NdcPatternConverter", category = PatternConverter.CATEGORY)
 @ConverterKeys({ "x", "NDC" })
 public final class NdcPatternConverter extends LogEventPatternConverter {
-  /**
-   *   Singleton.
-   */
-  private static final NdcPatternConverter INSTANCE =
-    new NdcPatternConverter();
 
-  /**
-   * Private constructor.
-   */
-  private NdcPatternConverter() {
-    super("NDC", "ndc");
-  }
+    /**
+     * Private constructor.
+     */
+    private NdcPatternConverter(final FormattingInfo formattingInfo) {
+        super("NDC", "ndc", formattingInfo);
+    }
+
+    /**
+     * Obtains an instance of NdcPatternConverter.
+     * 
+     * @param options options, may be null.
+     * @return instance of NdcPatternConverter.
+     */
+    public static NdcPatternConverter newInstance(final String[] options, final FormattingInfo formattingInfo) {
+        return new NdcPatternConverter(formattingInfo);
+    }
 
-  /**
-   * Obtains an instance of NdcPatternConverter.
-   * @param options options, may be null.
-   * @return instance of NdcPatternConverter.
-   */
-  public static NdcPatternConverter newInstance(final String[] options) {
-    return INSTANCE;
-  }
+    /**
+     * {@inheritDoc}
+     */
+    @Override
+    public void format(final LogEvent event, final TextBuffer toAppendTo) {
+        toAppendTo.append(event.getContextStack());
+    }
 
-  /**
-   * {@inheritDoc}
-   */
-  @Override
-public void format(final LogEvent event, final StringBuilder toAppendTo) {
-    toAppendTo.append(event.getContextStack());
-  }
+    /**
+     * {@inheritDoc}
+     */
+    @Override
+    public void format(final LogEvent event, final BinaryBuffer toAppendTo, final Charset charset) {
+        toAppendTo.append(event.getContextStack());
+    }
 }

http://git-wip-us.apache.org/repos/asf/logging-log4j2/blob/08386d0e/log4j-core/src/main/java/org/apache/logging/log4j/core/pattern/RegexReplacementConverter.java
----------------------------------------------------------------------
diff --git a/log4j-core/src/main/java/org/apache/logging/log4j/core/pattern/RegexReplacementConverter.java b/log4j-core/src/main/java/org/apache/logging/log4j/core/pattern/RegexReplacementConverter.java
index f7c4697..9049072 100644
--- a/log4j-core/src/main/java/org/apache/logging/log4j/core/pattern/RegexReplacementConverter.java
+++ b/log4j-core/src/main/java/org/apache/logging/log4j/core/pattern/RegexReplacementConverter.java
@@ -16,6 +16,7 @@
  */
 package org.apache.logging.log4j.core.pattern;
 
+import java.nio.charset.Charset;
 import java.util.List;
 import java.util.regex.Pattern;
 
@@ -39,13 +40,14 @@ public final class RegexReplacementConverter extends LogEventPatternConverter {
 
     /**
      * Construct the converter.
+     * 
      * @param formatters The PatternFormatters to generate the text to manipulate.
      * @param pattern The regular expression Pattern.
      * @param substitution The substitution string.
      */
-    private RegexReplacementConverter(final List<PatternFormatter> formatters,
-                                      final Pattern pattern, final String substitution) {
-        super("replace", "replace");
+    private RegexReplacementConverter(final List<PatternFormatter> formatters, final Pattern pattern,
+            final String substitution, final FormattingInfo formattingInfo) {
+        super("replace", "replace", formattingInfo);
         this.pattern = pattern;
         this.substitution = substitution;
         this.formatters = formatters;
@@ -55,11 +57,12 @@ public final class RegexReplacementConverter extends LogEventPatternConverter {
      * Gets an instance of the class.
      *
      * @param config The current Configuration.
-     * @param options pattern options, may be null.  If first element is "short",
-     *                only the first line of the throwable will be formatted.
+     * @param options pattern options, may be null. If first element is "short", only the first line of the throwable
+     *            will be formatted.
      * @return instance of class.
      */
-    public static RegexReplacementConverter newInstance(final Configuration config, final String[] options) {
+    public static RegexReplacementConverter newInstance(final Configuration config, final String[] options,
+            final FormattingInfo formattingInfo) {
         if (options.length != 3) {
             LOGGER.error("Incorrect number of options on replace. Expected 3 received " + options.length);
             return null;
@@ -79,19 +82,38 @@ public final class RegexReplacementConverter extends LogEventPatternConverter {
         final Pattern p = Pattern.compile(options[1]);
         final PatternParser parser = PatternLayout.createPatternParser(config);
         final List<PatternFormatter> formatters = parser.parse(options[0]);
-        return new RegexReplacementConverter(formatters, p, options[2]);
+        return new RegexReplacementConverter(formatters, p, options[2], formattingInfo);
     }
 
+    /**
+     * {@inheritDoc}
+     */
+    @Override
+    public void format(final LogEvent event, final TextBuffer toAppendTo) {
+        format0(event, toAppendTo);
+    }
 
     /**
      * {@inheritDoc}
      */
     @Override
-    public void format(final LogEvent event, final StringBuilder toAppendTo) {
-        final StringBuilder buf = new StringBuilder();
+    public void format(final LogEvent event, final BinaryBuffer toAppendTo, final Charset charset) {
+        format0(event, toAppendTo);
+    }
+
+    private void format0(final LogEvent event, final Buffer toAppendTo) {
+        final TextBuffer buf = new TextBuffer();
         for (final PatternFormatter formatter : formatters) {
             formatter.format(event, buf);
         }
         toAppendTo.append(pattern.matcher(buf.toString()).replaceAll(substitution));
     }
+    
+    @Override
+    public void setCharset(final Charset charset) {
+        super.setCharset(charset);
+        for (PatternFormatter paf : formatters) {
+            paf.getConverter().setCharset(charset);
+        }
+    }
 }

http://git-wip-us.apache.org/repos/asf/logging-log4j2/blob/08386d0e/log4j-core/src/main/java/org/apache/logging/log4j/core/pattern/RelativeTimePatternConverter.java
----------------------------------------------------------------------
diff --git a/log4j-core/src/main/java/org/apache/logging/log4j/core/pattern/RelativeTimePatternConverter.java b/log4j-core/src/main/java/org/apache/logging/log4j/core/pattern/RelativeTimePatternConverter.java
index 9767be1..2b9c8f8 100644
--- a/log4j-core/src/main/java/org/apache/logging/log4j/core/pattern/RelativeTimePatternConverter.java
+++ b/log4j-core/src/main/java/org/apache/logging/log4j/core/pattern/RelativeTimePatternConverter.java
@@ -17,6 +17,7 @@
 package org.apache.logging.log4j.core.pattern;
 
 import java.lang.management.ManagementFactory;
+import java.nio.charset.Charset;
 
 import org.apache.logging.log4j.core.LogEvent;
 import org.apache.logging.log4j.core.config.plugins.Plugin;
@@ -27,18 +28,13 @@ import org.apache.logging.log4j.core.config.plugins.Plugin;
 @Plugin(name = "RelativeTimePatternConverter", category = PatternConverter.CATEGORY)
 @ConverterKeys({ "r", "relative" })
 public class RelativeTimePatternConverter extends LogEventPatternConverter {
-    /**
-     * Cached formatted timestamp.
-     */
-    private long lastTimestamp = Long.MIN_VALUE;
     private final long startTime = ManagementFactory.getRuntimeMXBean().getStartTime();
-    private String relative;
 
     /**
      * Private constructor.
      */
-    public RelativeTimePatternConverter() {
-        super("Time", "time");
+    public RelativeTimePatternConverter(final FormattingInfo formattingInfo) {
+        super("Time", "time", formattingInfo);
     }
 
     /**
@@ -48,23 +44,31 @@ public class RelativeTimePatternConverter extends LogEventPatternConverter {
      * @return instance of RelativeTimePatternConverter.
      */
     public static RelativeTimePatternConverter newInstance(
-        final String[] options) {
-        return new RelativeTimePatternConverter();
+        final String[] options, final FormattingInfo formattingInfo) {
+        return new RelativeTimePatternConverter(formattingInfo);
     }
 
     /**
      * {@inheritDoc}
      */
     @Override
-    public void format(final LogEvent event, final StringBuilder toAppendTo) {
-        final long timestamp = event.getTimeMillis();
+    public void format(final LogEvent event, final TextBuffer toAppendTo) {
+        handle(event, toAppendTo);
+    }
 
-        synchronized (this) {
-            if (timestamp != lastTimestamp) {
-                lastTimestamp = timestamp;
-                relative = Long.toString(timestamp - startTime);
-            }
+    /**
+     * {@inheritDoc}
+     */
+    @Override
+    public void format(final LogEvent event, final BinaryBuffer toAppendTo, final Charset charset) {
+        handle(event, toAppendTo);
+    }
+    
+    private void handle(final LogEvent event, final Buffer toAppendTo) {
+        if (hasFormattingInfo) {
+            toAppendTo.append(event.getTimeMillis() - startTime, getFormattingInfo());
+        } else {
+            toAppendTo.append(event.getTimeMillis() - startTime);
         }
-        toAppendTo.append(relative);
     }
 }

http://git-wip-us.apache.org/repos/asf/logging-log4j2/blob/08386d0e/log4j-core/src/main/java/org/apache/logging/log4j/core/pattern/RootThrowablePatternConverter.java
----------------------------------------------------------------------
diff --git a/log4j-core/src/main/java/org/apache/logging/log4j/core/pattern/RootThrowablePatternConverter.java b/log4j-core/src/main/java/org/apache/logging/log4j/core/pattern/RootThrowablePatternConverter.java
index e87d078..ba89397 100644
--- a/log4j-core/src/main/java/org/apache/logging/log4j/core/pattern/RootThrowablePatternConverter.java
+++ b/log4j-core/src/main/java/org/apache/logging/log4j/core/pattern/RootThrowablePatternConverter.java
@@ -16,6 +16,8 @@
  */
 package org.apache.logging.log4j.core.pattern;
 
+import java.nio.charset.Charset;
+
 import org.apache.logging.log4j.core.LogEvent;
 import org.apache.logging.log4j.core.config.plugins.Plugin;
 import org.apache.logging.log4j.core.impl.Log4jLogEvent;
@@ -23,12 +25,11 @@ import org.apache.logging.log4j.core.impl.ThrowableProxy;
 import org.apache.logging.log4j.core.util.Constants;
 
 /**
- * Outputs the Throwable portion of the LoggingEvent as a full stacktrace
- * unless this converter's option is 'short', where it just outputs the first line of the trace, or if
- * the number of lines to print is explicitly specified.
+ * Outputs the Throwable portion of the LoggingEvent as a full stacktrace unless this converter's option is 'short',
+ * where it just outputs the first line of the trace, or if the number of lines to print is explicitly specified.
  * <p>
- * The extended stack trace will also include the location of where the class was loaded from and the
- * version of the jar if available.
+ * The extended stack trace will also include the location of where the class was loaded from and the version of the jar
+ * if available.
  */
 @Plugin(name = "RootThrowablePatternConverter", category = PatternConverter.CATEGORY)
 @ConverterKeys({ "rEx", "rThrowable", "rException" })
@@ -39,26 +40,38 @@ public final class RootThrowablePatternConverter extends ThrowablePatternConvert
      *
      * @param options options, may be null.
      */
-    private RootThrowablePatternConverter(final String[] options) {
-        super("RootThrowable", "throwable", options);
+    private RootThrowablePatternConverter(final String[] options, final FormattingInfo formattingInfo) {
+        super("RootThrowable", "throwable", options, formattingInfo);
     }
 
     /**
      * Gets an instance of the class.
      *
-     * @param options pattern options, may be null.  If first element is "short",
-     *                only the first line of the throwable will be formatted.
+     * @param options pattern options, may be null. If first element is "short", only the first line of the throwable
+     *            will be formatted.
      * @return instance of class.
      */
-    public static RootThrowablePatternConverter newInstance(final String[] options) {
-        return new RootThrowablePatternConverter(options);
+    public static RootThrowablePatternConverter newInstance(final String[] options, final FormattingInfo formattingInfo) {
+        return new RootThrowablePatternConverter(options, formattingInfo);
     }
 
     /**
      * {@inheritDoc}
      */
     @Override
-    public void format(final LogEvent event, final StringBuilder toAppendTo) {
+    public void format(final LogEvent event, final TextBuffer toAppendTo) {
+        handle(event, toAppendTo);
+    }
+
+    /**
+     * {@inheritDoc}
+     */
+    @Override
+    public void format(final LogEvent event, final BinaryBuffer toAppendTo, final Charset charset) {
+        handle(event, toAppendTo);
+    }
+
+    private void handle(final LogEvent event, final Buffer toAppendTo) {
         ThrowableProxy proxy = null;
         if (event instanceof Log4jLogEvent) {
             proxy = ((Log4jLogEvent) event).getThrownProxy();
@@ -70,13 +83,12 @@ public final class RootThrowablePatternConverter extends ThrowablePatternConvert
                 return;
             }
             final String trace = proxy.getCauseStackTraceAsString(options.getPackages());
-            final int len = toAppendTo.length();
-            if (len > 0 && !Character.isWhitespace(toAppendTo.charAt(len - 1))) {
+            if (!toAppendTo.hasTrailingWhitespace()) {
                 toAppendTo.append(' ');
             }
             if (!options.allLines() || !Constants.LINE_SEPARATOR.equals(options.getSeparator())) {
-                final StringBuilder sb = new StringBuilder();
                 final String[] array = trace.split(Constants.LINE_SEPARATOR);
+                final StringBuilder sb = new StringBuilder(array.length << 7); // *128: estimate 128 chars per line
                 final int limit = options.minLines(array.length) - 1;
                 for (int i = 0; i <= limit; ++i) {
                     sb.append(array[i]);

http://git-wip-us.apache.org/repos/asf/logging-log4j2/blob/08386d0e/log4j-core/src/main/java/org/apache/logging/log4j/core/pattern/SequenceNumberPatternConverter.java
----------------------------------------------------------------------
diff --git a/log4j-core/src/main/java/org/apache/logging/log4j/core/pattern/SequenceNumberPatternConverter.java b/log4j-core/src/main/java/org/apache/logging/log4j/core/pattern/SequenceNumberPatternConverter.java
index 9e14c78..75d7d34 100644
--- a/log4j-core/src/main/java/org/apache/logging/log4j/core/pattern/SequenceNumberPatternConverter.java
+++ b/log4j-core/src/main/java/org/apache/logging/log4j/core/pattern/SequenceNumberPatternConverter.java
@@ -16,12 +16,12 @@
  */
 package org.apache.logging.log4j.core.pattern;
 
+import java.nio.charset.Charset;
 import java.util.concurrent.atomic.AtomicLong;
 
 import org.apache.logging.log4j.core.LogEvent;
 import org.apache.logging.log4j.core.config.plugins.Plugin;
 
-
 /**
  * Formats the event sequence number.
  */
@@ -32,16 +32,10 @@ public final class SequenceNumberPatternConverter extends LogEventPatternConvert
     private static final AtomicLong SEQUENCE = new AtomicLong();
 
     /**
-     * Singleton.
-     */
-    private static final SequenceNumberPatternConverter INSTANCE =
-        new SequenceNumberPatternConverter();
-
-    /**
      * Private constructor.
      */
-    private SequenceNumberPatternConverter() {
-        super("Sequence Number", "sn");
+    private SequenceNumberPatternConverter(final FormattingInfo formattingInfo) {
+        super("Sequence Number", "sn", formattingInfo);
     }
 
     /**
@@ -50,16 +44,31 @@ public final class SequenceNumberPatternConverter extends LogEventPatternConvert
      * @param options options, currently ignored, may be null.
      * @return instance of SequencePatternConverter.
      */
-    public static SequenceNumberPatternConverter newInstance(
-        final String[] options) {
-        return INSTANCE;
+    public static SequenceNumberPatternConverter newInstance(final String[] options, final FormattingInfo formattingInfo) {
+        return new SequenceNumberPatternConverter(formattingInfo);
+    }
+
+    /**
+     * {@inheritDoc}
+     */
+    @Override
+    public void format(final LogEvent event, final TextBuffer toAppendTo) {
+        if (hasFormattingInfo) {
+            toAppendTo.append(SEQUENCE.incrementAndGet(), getFormattingInfo());
+        } else {
+            toAppendTo.append(SEQUENCE.incrementAndGet());
+        }
     }
 
     /**
      * {@inheritDoc}
      */
     @Override
-    public void format(final LogEvent event, final StringBuilder toAppendTo) {
-        toAppendTo.append(Long.toString(SEQUENCE.incrementAndGet()));
+    public void format(final LogEvent event, final BinaryBuffer toAppendTo, final Charset charset) {
+        if (hasFormattingInfo) {
+            toAppendTo.append(SEQUENCE.incrementAndGet(), getFormattingInfo());
+        } else {
+            toAppendTo.append(SEQUENCE.incrementAndGet());
+        }
     }
 }

http://git-wip-us.apache.org/repos/asf/logging-log4j2/blob/08386d0e/log4j-core/src/main/java/org/apache/logging/log4j/core/pattern/StyleConverter.java
----------------------------------------------------------------------
diff --git a/log4j-core/src/main/java/org/apache/logging/log4j/core/pattern/StyleConverter.java b/log4j-core/src/main/java/org/apache/logging/log4j/core/pattern/StyleConverter.java
index 583be29..6cdc2a3 100644
--- a/log4j-core/src/main/java/org/apache/logging/log4j/core/pattern/StyleConverter.java
+++ b/log4j-core/src/main/java/org/apache/logging/log4j/core/pattern/StyleConverter.java
@@ -16,6 +16,7 @@
  */
 package org.apache.logging.log4j.core.pattern;
 
+import java.nio.charset.Charset;
 import java.util.List;
 
 import org.apache.logging.log4j.core.LogEvent;
@@ -34,14 +35,13 @@ public final class StyleConverter extends LogEventPatternConverter implements An
     /**
      * Gets an instance of the class.
      *
-     * @param config
-     *            The current Configuration.
-     * @param options
-     *            pattern options, may be null. If first element is "short", only the first line of the throwable will
-     *            be formatted.
+     * @param config The current Configuration.
+     * @param options pattern options, may be null. If first element is "short", only the first line of the throwable
+     *            will be formatted.
      * @return instance of class.
      */
-    public static StyleConverter newInstance(final Configuration config, final String[] options) {
+    public static StyleConverter newInstance(final Configuration config, final String[] options,
+            final FormattingInfo formattingInfo) {
         if (options.length < 1) {
             LOGGER.error("Incorrect number of options on style. Expected at least 1, received " + options.length);
             return null;
@@ -60,7 +60,7 @@ public final class StyleConverter extends LogEventPatternConverter implements An
         final boolean noConsoleNoAnsi = options.length > 2
                 && (PatternParser.NO_CONSOLE_NO_ANSI + "=true").equals(options[2]);
         final boolean hideAnsi = noConsoleNoAnsi && System.console() == null;
-        return new StyleConverter(formatters, style, hideAnsi);
+        return new StyleConverter(formatters, style, hideAnsi, formattingInfo);
     }
 
     private final List<PatternFormatter> patternFormatters;
@@ -74,15 +74,13 @@ public final class StyleConverter extends LogEventPatternConverter implements An
     /**
      * Constructs the converter.
      *
-     * @param patternFormatters
-     *            The PatternFormatters to generate the text to manipulate.
-     * @param style
-     *            The style that should encapsulate the pattern.
-     * @param noAnsi
-     *            If true, do not output ANSI escape codes.
+     * @param patternFormatters The PatternFormatters to generate the text to manipulate.
+     * @param style The style that should encapsulate the pattern.
+     * @param noAnsi If true, do not output ANSI escape codes.
      */
-    private StyleConverter(final List<PatternFormatter> patternFormatters, final String style, final boolean noAnsi) {
-        super("style", "style");
+    private StyleConverter(final List<PatternFormatter> patternFormatters, final String style, final boolean noAnsi,
+            final FormattingInfo formattingInfo) {
+        super("style", "style", formattingInfo);
         this.patternFormatters = patternFormatters;
         this.style = style;
         this.defaultStyle = AnsiEscape.getDefaultStyle();
@@ -93,18 +91,50 @@ public final class StyleConverter extends LogEventPatternConverter implements An
      * {@inheritDoc}
      */
     @Override
-    public void format(final LogEvent event, final StringBuilder toAppendTo) {
-        final StringBuilder buf = new StringBuilder();
-        for (final PatternFormatter formatter : patternFormatters) {
-            formatter.format(event, buf);
+    public void format(final LogEvent event, final TextBuffer toAppendTo) {
+        format0(event, toAppendTo, null);
+    }
+
+    /**
+     * {@inheritDoc}
+     */
+    @Override
+    public void format(final LogEvent event, final BinaryBuffer toAppendTo, final Charset charset) {
+        format0(event, toAppendTo, charset);
+    }
+
+    private void format0(final LogEvent event, final Buffer toAppendTo, final Charset charset) {
+        formatNested(event, toAppendTo, charset, noAnsi, patternFormatters, style, defaultStyle);
+    }
+
+    public static void formatNested(final LogEvent event, final Buffer toAppendTo, final Charset charset,
+            final boolean noAnsi, final List<PatternFormatter> nested, final String style, final String defaultStyle) {
+        if (noAnsi) {
+            appendNested(nested, event, toAppendTo, charset);
+            return;
+        }
+        final int startLengthForUndo = toAppendTo.length();
+        toAppendTo.append(style);
+        final int beforeAddingNested = toAppendTo.length();
+
+        appendNested(nested, event, toAppendTo, charset);
+
+        if (toAppendTo.length() == beforeAddingNested) {
+            toAppendTo.setLength(startLengthForUndo); // remove style
+        } else {
+            toAppendTo.append(defaultStyle);
         }
+    }
 
-        if (buf.length() > 0) {
-            if (noAnsi) {
-                // faster to test and do this than setting style and defaultStyle to empty strings.
-                toAppendTo.append(buf.toString());
-            } else {
-                toAppendTo.append(style).append(buf.toString()).append(defaultStyle);
+    private static void appendNested(final List<PatternFormatter> formatters, final LogEvent event,
+            final Buffer toAppendTo, final Charset charset) {
+        if (toAppendTo instanceof TextBuffer) {
+            for (final PatternFormatter formatter : formatters) {
+                formatter.format(event, (TextBuffer) toAppendTo);
+            }
+        } else {
+            for (final PatternFormatter formatter : formatters) {
+                formatter.format(event, (BinaryBuffer) toAppendTo, charset);
             }
         }
     }

http://git-wip-us.apache.org/repos/asf/logging-log4j2/blob/08386d0e/log4j-core/src/main/java/org/apache/logging/log4j/core/pattern/ThreadPatternConverter.java
----------------------------------------------------------------------
diff --git a/log4j-core/src/main/java/org/apache/logging/log4j/core/pattern/ThreadPatternConverter.java b/log4j-core/src/main/java/org/apache/logging/log4j/core/pattern/ThreadPatternConverter.java
index c763e51..0bf3df0 100644
--- a/log4j-core/src/main/java/org/apache/logging/log4j/core/pattern/ThreadPatternConverter.java
+++ b/log4j-core/src/main/java/org/apache/logging/log4j/core/pattern/ThreadPatternConverter.java
@@ -16,8 +16,11 @@
  */
 package org.apache.logging.log4j.core.pattern;
 
+import java.nio.charset.Charset;
+
 import org.apache.logging.log4j.core.LogEvent;
 import org.apache.logging.log4j.core.config.plugins.Plugin;
+import org.apache.logging.log4j.core.impl.Log4jLogEvent;
 
 /**
  * Formats the event thread name.
@@ -25,17 +28,12 @@ import org.apache.logging.log4j.core.config.plugins.Plugin;
 @Plugin(name = "ThreadPatternConverter", category = PatternConverter.CATEGORY)
 @ConverterKeys({ "t", "thread" })
 public final class ThreadPatternConverter extends LogEventPatternConverter {
-    /**
-     * Singleton.
-     */
-    private static final ThreadPatternConverter INSTANCE =
-        new ThreadPatternConverter();
 
     /**
      * Private constructor.
      */
-    private ThreadPatternConverter() {
-        super("Thread", "thread");
+    private ThreadPatternConverter(final FormattingInfo formattingInfo) {
+        super("Thread", "thread", formattingInfo);
     }
 
     /**
@@ -44,16 +42,36 @@ public final class ThreadPatternConverter extends LogEventPatternConverter {
      * @param options options, currently ignored, may be null.
      * @return instance of ThreadPatternConverter.
      */
-    public static ThreadPatternConverter newInstance(
-        final String[] options) {
-        return INSTANCE;
+    public static ThreadPatternConverter newInstance(final String[] options, final FormattingInfo formattingInfo) {
+        return new ThreadPatternConverter(formattingInfo);
+    }
+    
+    @Override
+    protected String convert(final Object thread) {
+        if (thread instanceof Thread) {
+            return ((Thread) thread).getName();
+        }
+        return thread.toString();
+    }
+    
+    private Object extractThreadOrThreadName(final LogEvent event) {
+        final boolean useEvent = event instanceof Log4jLogEvent && ((Log4jLogEvent) event).hasThreadName();
+        return useEvent ? event.getThreadName() : Thread.currentThread();
+    }
+
+    /**
+     * {@inheritDoc}
+     */
+    @Override
+    public void format(final LogEvent event, final TextBuffer toAppendTo) {
+        toAppendTo.append(getCachedFormattedString(extractThreadOrThreadName(event)));
     }
 
     /**
      * {@inheritDoc}
      */
     @Override
-    public void format(final LogEvent event, final StringBuilder toAppendTo) {
-        toAppendTo.append(event.getThreadName());
+    public void format(final LogEvent event, final BinaryBuffer toAppendTo, final Charset charset) {
+        toAppendTo.append(getCachedFormattedBytes(extractThreadOrThreadName(event), charset));
     }
 }

http://git-wip-us.apache.org/repos/asf/logging-log4j2/blob/08386d0e/log4j-core/src/main/java/org/apache/logging/log4j/core/pattern/ThrowablePatternConverter.java
----------------------------------------------------------------------
diff --git a/log4j-core/src/main/java/org/apache/logging/log4j/core/pattern/ThrowablePatternConverter.java b/log4j-core/src/main/java/org/apache/logging/log4j/core/pattern/ThrowablePatternConverter.java
index b73d904..b2869f0 100644
--- a/log4j-core/src/main/java/org/apache/logging/log4j/core/pattern/ThrowablePatternConverter.java
+++ b/log4j-core/src/main/java/org/apache/logging/log4j/core/pattern/ThrowablePatternConverter.java
@@ -18,6 +18,7 @@ package org.apache.logging.log4j.core.pattern;
 
 import java.io.PrintWriter;
 import java.io.StringWriter;
+import java.nio.charset.Charset;
 
 import org.apache.logging.log4j.core.LogEvent;
 import org.apache.logging.log4j.core.config.plugins.Plugin;
@@ -25,11 +26,9 @@ import org.apache.logging.log4j.core.impl.ThrowableFormatOptions;
 import org.apache.logging.log4j.core.util.Constants;
 import org.apache.logging.log4j.util.Strings;
 
-
 /**
- * Outputs the Throwable portion of the LoggingEvent as a full stacktrace
- * unless this converter's option is 'short', where it just outputs the first line of the trace, or if
- * the number of lines to print is explicitly specified.
+ * Outputs the Throwable portion of the LoggingEvent as a full stacktrace unless this converter's option is 'short',
+ * where it just outputs the first line of the trace, or if the number of lines to print is explicitly specified.
  */
 @Plugin(name = "ThrowablePatternConverter", category = PatternConverter.CATEGORY)
 @ConverterKeys({ "ex", "throwable", "exception" })
@@ -44,12 +43,14 @@ public class ThrowablePatternConverter extends LogEventPatternConverter {
 
     /**
      * Constructor.
+     * 
      * @param name Name of converter.
      * @param style CSS style for output.
      * @param options options, may be null.
      */
-    protected ThrowablePatternConverter(final String name, final String style, final String[] options) {
-        super(name, style);
+    protected ThrowablePatternConverter(final String name, final String style, final String[] options,
+            final FormattingInfo formattingInfo) {
+        super(name, style, formattingInfo);
         this.options = ThrowableFormatOptions.newInstance(options);
         if (options != null && options.length > 0) {
             rawOption = options[0];
@@ -59,46 +60,56 @@ public class ThrowablePatternConverter extends LogEventPatternConverter {
     /**
      * Gets an instance of the class.
      *
-     * @param options pattern options, may be null.  If first element is "short",
-     *                only the first line of the throwable will be formatted.
+     * @param options pattern options, may be null. If first element is "short", only the first line of the throwable
+     *            will be formatted.
      * @return instance of class.
      */
-    public static ThrowablePatternConverter newInstance(final String[] options) {
-        return new ThrowablePatternConverter("Throwable", "throwable", options);
+    public static ThrowablePatternConverter newInstance(final String[] options, final FormattingInfo formattingInfo) {
+        return new ThrowablePatternConverter("Throwable", "throwable", options, formattingInfo);
+    }
+
+    /**
+     * {@inheritDoc}
+     */
+    @Override
+    public void format(final LogEvent event, final TextBuffer buffer) {
+        handle(event, buffer);
     }
 
     /**
      * {@inheritDoc}
      */
     @Override
-    public void format(final LogEvent event, final StringBuilder buffer) {
+    public void format(final LogEvent event, final BinaryBuffer buffer, final Charset charset) {
+        handle(event, buffer);
+    }
+    
+    private void handle(final LogEvent event, final Buffer buffer) {
         final Throwable t = event.getThrown();
 
         if (isSubShortOption()) {
             formatSubShortOption(t, buffer);
-        }
-        else if (t != null && options.anyLines()) {
+        } else if (t != null && options.anyLines()) {
             formatOption(t, buffer);
         }
     }
 
     private boolean isSubShortOption() {
-        return ThrowableFormatOptions.MESSAGE.equalsIgnoreCase(rawOption) ||
-                ThrowableFormatOptions.LOCALIZED_MESSAGE.equalsIgnoreCase(rawOption) ||
-                ThrowableFormatOptions.FILE_NAME.equalsIgnoreCase(rawOption) ||
-                ThrowableFormatOptions.LINE_NUMBER.equalsIgnoreCase(rawOption) ||
-                ThrowableFormatOptions.METHOD_NAME.equalsIgnoreCase(rawOption) ||
-                ThrowableFormatOptions.CLASS_NAME.equalsIgnoreCase(rawOption);
+        return ThrowableFormatOptions.MESSAGE.equalsIgnoreCase(rawOption)
+                || ThrowableFormatOptions.LOCALIZED_MESSAGE.equalsIgnoreCase(rawOption)
+                || ThrowableFormatOptions.FILE_NAME.equalsIgnoreCase(rawOption)
+                || ThrowableFormatOptions.LINE_NUMBER.equalsIgnoreCase(rawOption)
+                || ThrowableFormatOptions.METHOD_NAME.equalsIgnoreCase(rawOption)
+                || ThrowableFormatOptions.CLASS_NAME.equalsIgnoreCase(rawOption);
     }
 
-    private void formatSubShortOption(final Throwable t, final StringBuilder buffer) {
+    private void formatSubShortOption(final Throwable t, final Buffer buffer) {
         StackTraceElement[] trace;
         StackTraceElement throwingMethod = null;
-        int len;
 
         if (t != null) {
             trace = t.getStackTrace();
-            if (trace !=null && trace.length > 0) {
+            if (trace != null && trace.length > 0) {
                 throwingMethod = trace[0];
             }
         }
@@ -108,42 +119,35 @@ public class ThrowablePatternConverter extends LogEventPatternConverter {
 
             if (ThrowableFormatOptions.CLASS_NAME.equalsIgnoreCase(rawOption)) {
                 toAppend = throwingMethod.getClassName();
-            }
-            else if (ThrowableFormatOptions.METHOD_NAME.equalsIgnoreCase(rawOption)) {
+            } else if (ThrowableFormatOptions.METHOD_NAME.equalsIgnoreCase(rawOption)) {
                 toAppend = throwingMethod.getMethodName();
-            }
-            else if (ThrowableFormatOptions.LINE_NUMBER.equalsIgnoreCase(rawOption)) {
+            } else if (ThrowableFormatOptions.LINE_NUMBER.equalsIgnoreCase(rawOption)) {
                 toAppend = String.valueOf(throwingMethod.getLineNumber());
-            }
-            else if (ThrowableFormatOptions.MESSAGE.equalsIgnoreCase(rawOption)) {
+            } else if (ThrowableFormatOptions.MESSAGE.equalsIgnoreCase(rawOption)) {
                 toAppend = t.getMessage();
-            }
-            else if (ThrowableFormatOptions.LOCALIZED_MESSAGE.equalsIgnoreCase(rawOption)) {
+            } else if (ThrowableFormatOptions.LOCALIZED_MESSAGE.equalsIgnoreCase(rawOption)) {
                 toAppend = t.getLocalizedMessage();
-            }
-            else if (ThrowableFormatOptions.FILE_NAME.equalsIgnoreCase(rawOption)) {
+            } else if (ThrowableFormatOptions.FILE_NAME.equalsIgnoreCase(rawOption)) {
                 toAppend = throwingMethod.getFileName();
             }
 
-            len = buffer.length();
-            if (len > 0 && !Character.isWhitespace(buffer.charAt(len - 1))) {
+            if (!buffer.hasTrailingWhitespace()) {
                 buffer.append(' ');
             }
             buffer.append(toAppend);
         }
     }
 
-    private void formatOption(final Throwable throwable, final StringBuilder buffer) {
+    private void formatOption(final Throwable throwable, final Buffer buffer) {
         final StringWriter w = new StringWriter();
 
         throwable.printStackTrace(new PrintWriter(w));
-        final int len = buffer.length();
-        if (len > 0 && !Character.isWhitespace(buffer.charAt(len - 1))) {
+        if (!buffer.hasTrailingWhitespace()) {
             buffer.append(' ');
         }
         if (!options.allLines() || !Constants.LINE_SEPARATOR.equals(options.getSeparator())) {
-            final StringBuilder sb = new StringBuilder();
             final String[] array = w.toString().split(Constants.LINE_SEPARATOR);
+            final StringBuilder sb = new StringBuilder(array.length << 7); // *128: estimate 128 chars per line
             final int limit = options.minLines(array.length) - 1;
             for (int i = 0; i <= limit; ++i) {
                 sb.append(array[i]);

http://git-wip-us.apache.org/repos/asf/logging-log4j2/blob/08386d0e/log4j-core/src/main/java/org/apache/logging/log4j/core/pattern/UuidPatternConverter.java
----------------------------------------------------------------------
diff --git a/log4j-core/src/main/java/org/apache/logging/log4j/core/pattern/UuidPatternConverter.java b/log4j-core/src/main/java/org/apache/logging/log4j/core/pattern/UuidPatternConverter.java
index 439935b..46ed031 100644
--- a/log4j-core/src/main/java/org/apache/logging/log4j/core/pattern/UuidPatternConverter.java
+++ b/log4j-core/src/main/java/org/apache/logging/log4j/core/pattern/UuidPatternConverter.java
@@ -16,6 +16,7 @@
  */
 package org.apache.logging.log4j.core.pattern;
 
+import java.nio.charset.Charset;
 import java.util.UUID;
 
 import org.apache.logging.log4j.core.LogEvent;
@@ -34,8 +35,8 @@ public final class UuidPatternConverter extends LogEventPatternConverter {
     /**
      * Private constructor.
      */
-    private UuidPatternConverter(final boolean isRandom) {
-        super("u", "uuid");
+    private UuidPatternConverter(final boolean isRandom, final FormattingInfo formattingInfo) {
+        super("u", "uuid", formattingInfo);
         this.isRandom = isRandom;
     }
 
@@ -45,23 +46,34 @@ public final class UuidPatternConverter extends LogEventPatternConverter {
      * @param options options, currently ignored, may be null.
      * @return instance of SequencePatternConverter.
      */
-    public static UuidPatternConverter newInstance(final String[] options) {
+    public static UuidPatternConverter newInstance(final String[] options, final FormattingInfo formattingInfo) {
         if (options.length == 0) {
-            return new UuidPatternConverter(false);
+            return new UuidPatternConverter(false, formattingInfo);
         }
 
         if (options.length > 1 || (!options[0].equalsIgnoreCase("RANDOM") && !options[0].equalsIgnoreCase("Time"))) {
             LOGGER.error("UUID Pattern Converter only accepts a single option with the value \"RANDOM\" or \"TIME\"");
         }
-        return new UuidPatternConverter(options[0].equalsIgnoreCase("RANDOM"));
+        return new UuidPatternConverter(options[0].equalsIgnoreCase("RANDOM"), formattingInfo);
     }
 
     /**
      * {@inheritDoc}
      */
     @Override
-    public void format(final LogEvent event, final StringBuilder toAppendTo) {
-        final UUID uuid = isRandom ? UUID.randomUUID() : UuidUtil.getTimeBasedUuid();
-        toAppendTo.append(uuid.toString());
+    public void format(final LogEvent event, final TextBuffer toAppendTo) {
+        toAppendTo.append(getCachedFormattedString(nextUUID()));
+    }
+
+    /**
+     * {@inheritDoc}
+     */
+    @Override
+    public void format(final LogEvent event, final BinaryBuffer toAppendTo, final Charset charset) {
+        toAppendTo.append(getCachedFormattedBytes(nextUUID(), charset));
+    }
+    
+    private UUID nextUUID() {
+        return isRandom ? UUID.randomUUID() : UuidUtil.getTimeBasedUuid();
     }
 }

http://git-wip-us.apache.org/repos/asf/logging-log4j2/blob/08386d0e/log4j-core/src/test/java/org/apache/logging/log4j/core/pattern/DatePatternConverterTest.java
----------------------------------------------------------------------
diff --git a/log4j-core/src/test/java/org/apache/logging/log4j/core/pattern/DatePatternConverterTest.java b/log4j-core/src/test/java/org/apache/logging/log4j/core/pattern/DatePatternConverterTest.java
index 2e75928..27b02dc 100644
--- a/log4j-core/src/test/java/org/apache/logging/log4j/core/pattern/DatePatternConverterTest.java
+++ b/log4j-core/src/test/java/org/apache/logging/log4j/core/pattern/DatePatternConverterTest.java
@@ -16,6 +16,7 @@
  */
 package org.apache.logging.log4j.core.pattern;
 
+import java.nio.charset.Charset;
 import java.util.Calendar;
 import java.util.Date;
 
@@ -31,29 +32,37 @@ public class DatePatternConverterTest {
 
     @Test
     public void testNewInstanceAllowsNullParameter() {
-        DatePatternConverter.newInstance(null); // no errors
+        DatePatternConverter.newInstance(null, FormattingInfo.getDefault()); // no errors
     }
 
     @Test
     public void testFormatLogEventStringBuilderDefaultPattern() {
         final LogEvent event = new MyLogEvent();
-        final DatePatternConverter converter = DatePatternConverter.newInstance(null);
-        final StringBuilder sb = new StringBuilder();
+        final DatePatternConverter converter = DatePatternConverter.newInstance(null, FormattingInfo.getDefault());
+        final TextBuffer sb = new TextBuffer();
         converter.format(event, sb);
 
         final String expected = "2011-12-30 10:56:35,987";
         assertEquals(expected, sb.toString());
+        
+        final BinaryBuffer bin = new BinaryBuffer(Charset.defaultCharset());
+        converter.format(event, bin, Charset.defaultCharset());
+        assertEquals(expected, bin.toString());
     }
 
     @Test
     public void testFormatLogEventStringBuilderIso8601() {
         final LogEvent event = new MyLogEvent();
-        final DatePatternConverter converter = DatePatternConverter.newInstance(ISO8601_FORMAT);
-        final StringBuilder sb = new StringBuilder();
+        final DatePatternConverter converter = DatePatternConverter.newInstance(ISO8601_FORMAT, FormattingInfo.getDefault());
+        final TextBuffer sb = new TextBuffer();
         converter.format(event, sb);
 
         final String expected = "2011-12-30T10:56:35,987";
         assertEquals(expected, sb.toString());
+        
+        final BinaryBuffer bin = new BinaryBuffer(Charset.defaultCharset());
+        converter.format(event, bin, Charset.defaultCharset());
+        assertEquals(expected, bin.toString());
     }
 
     private class MyLogEvent extends AbstractLogEvent {
@@ -70,8 +79,8 @@ public class DatePatternConverterTest {
 
     @Test
     public void testFormatObjectStringBuilderDefaultPattern() {
-        final DatePatternConverter converter = DatePatternConverter.newInstance(null);
-        final StringBuilder sb = new StringBuilder();
+        final DatePatternConverter converter = DatePatternConverter.newInstance(null, FormattingInfo.getDefault());
+        final TextBuffer sb = new TextBuffer();
         converter.format("nondate", sb);
 
         final String expected = ""; // only process dates
@@ -80,8 +89,8 @@ public class DatePatternConverterTest {
 
     @Test
     public void testFormatDateStringBuilderDefaultPattern() {
-        final DatePatternConverter converter = DatePatternConverter.newInstance(null);
-        final StringBuilder sb = new StringBuilder();
+        final DatePatternConverter converter = DatePatternConverter.newInstance(null, FormattingInfo.getDefault());
+        final TextBuffer sb = new TextBuffer();
         converter.format(date(2001, 1, 1), sb);
 
         final String expected = "2001-02-01 14:15:16,123";
@@ -90,8 +99,8 @@ public class DatePatternConverterTest {
 
     @Test
     public void testFormatDateStringBuilderIso8601() {
-        final DatePatternConverter converter = DatePatternConverter.newInstance(ISO8601_FORMAT);
-        final StringBuilder sb = new StringBuilder();
+        final DatePatternConverter converter = DatePatternConverter.newInstance(ISO8601_FORMAT, FormattingInfo.getDefault());
+        final TextBuffer sb = new TextBuffer();
         converter.format(date(2001, 1, 1), sb);
 
         final String expected = "2001-02-01T14:15:16,123";
@@ -100,8 +109,8 @@ public class DatePatternConverterTest {
 
     @Test
     public void testFormatStringBuilderObjectArrayDefaultPattern() {
-        final DatePatternConverter converter = DatePatternConverter.newInstance(null);
-        final StringBuilder sb = new StringBuilder();
+        final DatePatternConverter converter = DatePatternConverter.newInstance(null, FormattingInfo.getDefault());
+        final TextBuffer sb = new TextBuffer();
         converter.format(sb, date(2001, 1, 1), date(2002, 2, 2), date(2003, 3, 3));
 
         final String expected = "2001-02-01 14:15:16,123"; // only process first date
@@ -110,8 +119,8 @@ public class DatePatternConverterTest {
 
     @Test
     public void testFormatStringBuilderObjectArrayIso8601() {
-        final DatePatternConverter converter = DatePatternConverter.newInstance(ISO8601_FORMAT);
-        final StringBuilder sb = new StringBuilder();
+        final DatePatternConverter converter = DatePatternConverter.newInstance(ISO8601_FORMAT, FormattingInfo.getDefault());
+        final TextBuffer sb = new TextBuffer();
         converter.format(sb, date(2001, 1, 1), date(2002, 2, 2), date(2003, 3, 3));
 
         final String expected = "2001-02-01T14:15:16,123"; // only process first date
@@ -127,7 +136,7 @@ public class DatePatternConverterTest {
 
     @Test
     public void testGetPatternReturnsCorrectDefault() {
-        assertEquals(DatePatternConverter.DEFAULT_PATTERN, DatePatternConverter.newInstance(null).getPattern());
+        assertEquals(DatePatternConverter.DEFAULT_PATTERN, DatePatternConverter.newInstance(null, FormattingInfo.getDefault()).getPattern());
     }
 
 }

http://git-wip-us.apache.org/repos/asf/logging-log4j2/blob/08386d0e/log4j-core/src/test/java/org/apache/logging/log4j/core/pattern/EncodingPatternConverterTest.java
----------------------------------------------------------------------
diff --git a/log4j-core/src/test/java/org/apache/logging/log4j/core/pattern/EncodingPatternConverterTest.java b/log4j-core/src/test/java/org/apache/logging/log4j/core/pattern/EncodingPatternConverterTest.java
index be1e2ad..ae5c66f 100644
--- a/log4j-core/src/test/java/org/apache/logging/log4j/core/pattern/EncodingPatternConverterTest.java
+++ b/log4j-core/src/test/java/org/apache/logging/log4j/core/pattern/EncodingPatternConverterTest.java
@@ -35,11 +35,11 @@ public class EncodingPatternConverterTest {
     public void testReplacement() {
         final LogEvent event = new Log4jLogEvent(EncodingPatternConverterTest.class.getName(), null, null, Level.DEBUG,
             new SimpleMessage("Test \r\n<div class=\"test\">this</div> & <div class='test'>that</div>"), null);
-        final StringBuilder sb = new StringBuilder();
         final LoggerContext ctx = (LoggerContext) LogManager.getContext();
         final String[] options = new String[]{"%msg"};
         final EncodingPatternConverter converter = EncodingPatternConverter
-            .newInstance(ctx.getConfiguration(), options);
+            .newInstance(ctx.getConfiguration(), options, FormattingInfo.getDefault());
+        final TextBuffer sb = new TextBuffer();
         converter.format(event, sb);
         assertEquals(
             "Test \\r\\n&lt;div class=&quot;test&quot;&gt;this&lt;&#x2F;div&gt; &amp; &lt;div class=&apos;test&apos;&gt;that&lt;&#x2F;div&gt;",