--- a/jdk/src/share/classes/sun/util/logging/PlatformLogger.java Thu Apr 04 20:05:47 2013 -0700
+++ b/jdk/src/share/classes/sun/util/logging/PlatformLogger.java Fri Apr 05 10:41:46 2013 -0700
@@ -32,6 +32,7 @@
import java.io.StringWriter;
import java.security.AccessController;
import java.security.PrivilegedAction;
+import java.util.Arrays;
import java.util.Date;
import java.util.HashMap;
import java.util.Map;
@@ -84,31 +85,38 @@
* @since 1.7
*/
public class PlatformLogger {
- // shortcut to PlatformLogger.Level enums
- public static final Level OFF = Level.OFF;
- public static final Level SEVERE = Level.SEVERE;
- public static final Level WARNING = Level.WARNING;
- public static final Level INFO = Level.INFO;
- public static final Level CONFIG = Level.CONFIG;
- public static final Level FINE = Level.FINE;
- public static final Level FINER = Level.FINER;
- public static final Level FINEST = Level.FINEST;
- public static final Level ALL = Level.ALL;
+ /*
+ * These constants should be shortcuts to Level enum constants that
+ * the clients of sun.util.logging.PlatformLogger require no source
+ * modification and avoid the conversion from int to Level enum.
+ *
+ * This can be done when JavaFX is converted to use the new PlatformLogger.Level API.
+ */
+ public static final int OFF = Integer.MAX_VALUE;
+ public static final int SEVERE = 1000;
+ public static final int WARNING = 900;
+ public static final int INFO = 800;
+ public static final int CONFIG = 700;
+ public static final int FINE = 500;
+ public static final int FINER = 400;
+ public static final int FINEST = 300;
+ public static final int ALL = Integer.MIN_VALUE;
/**
* PlatformLogger logging levels.
*/
public static enum Level {
- // The name and value must match that of {@code java.util.logging.Level} objects.
- ALL(Integer.MIN_VALUE),
- FINEST(300),
- FINER(400),
- FINE(500),
- CONFIG(700),
- INFO(800),
- WARNING(900),
- SEVERE(1000),
- OFF(Integer.MAX_VALUE);
+ // The name and value must match that of {@code java.util.logging.Level}s.
+ // Declare in ascending order of the given value for binary search.
+ ALL,
+ FINEST,
+ FINER,
+ FINE,
+ CONFIG,
+ INFO,
+ WARNING,
+ SEVERE,
+ OFF;
/**
* Associated java.util.logging.Level lazily initialized in
@@ -118,17 +126,39 @@
*/
/* java.util.logging.Level */ Object javaLevel;
- private final int value;
+ // ascending order for binary search matching the list of enum constants
+ private static final int[] levelValues = new int[] {
+ PlatformLogger.ALL, PlatformLogger.FINEST, PlatformLogger.FINER,
+ PlatformLogger.FINE, PlatformLogger.CONFIG, PlatformLogger.INFO,
+ PlatformLogger.WARNING, PlatformLogger.SEVERE, PlatformLogger.OFF
+ };
+
public int intValue() {
- return value;
+ return levelValues[this.ordinal()];
}
- Level(int value) {
- this.value = value;
+ static Level valueOf(int level) {
+ switch (level) {
+ // ordering per the highest occurences in the jdk source
+ // finest, fine, finer, info first
+ case PlatformLogger.FINEST : return Level.FINEST;
+ case PlatformLogger.FINE : return Level.FINE;
+ case PlatformLogger.FINER : return Level.FINER;
+ case PlatformLogger.INFO : return Level.INFO;
+ case PlatformLogger.WARNING : return Level.WARNING;
+ case PlatformLogger.CONFIG : return Level.CONFIG;
+ case PlatformLogger.SEVERE : return Level.SEVERE;
+ case PlatformLogger.OFF : return Level.OFF;
+ case PlatformLogger.ALL : return Level.ALL;
+ }
+ // return the nearest Level value >= the given level,
+ // for level > SEVERE, return SEVERE and exclude OFF
+ int i = Arrays.binarySearch(levelValues, 0, levelValues.length-2, level);
+ return values()[i >= 0 ? i : (-i-1)];
}
}
- private static final Level DEFAULT_LEVEL = INFO;
+ private static final Level DEFAULT_LEVEL = Level.INFO;
private static boolean loggingEnabled;
static {
loggingEnabled = AccessController.doPrivileged(
@@ -234,8 +264,44 @@
/**
* Returns true if a message of the given level would actually
* be logged by this logger.
+ *
+ * @deprecated Use isLoggable(Level) instead.
+ */
+ @Deprecated
+ public boolean isLoggable(int levelValue) {
+ return isLoggable(Level.valueOf(levelValue));
+ }
+
+ /**
+ * Gets the current log level. Returns 0 if the current effective level is
+ * not set (equivalent to Logger.getLevel() returns null).
+ *
+ * @deprecated Use level() instead
+ */
+ @Deprecated
+ public int getLevel() {
+ Level level = loggerProxy.getLevel();
+ return level != null ? level.intValue() : 0;
+ }
+
+ /**
+ * Sets the log level.
+ *
+ * @deprecated Use setLevel(Level) instead
+ */
+ @Deprecated
+ public void setLevel(int newLevel) {
+ loggerProxy.setLevel(newLevel == 0 ? null : Level.valueOf(newLevel));
+ }
+
+ /**
+ * Returns true if a message of the given level would actually
+ * be logged by this logger.
*/
public boolean isLoggable(Level level) {
+ if (level == null) {
+ throw new NullPointerException();
+ }
// performance-sensitive method: use two monomorphic call-sites
JavaLoggerProxy jlp = javaLoggerProxy;
return jlp != null ? jlp.isLoggable(level) : loggerProxy.isLoggable(level);
@@ -246,15 +312,9 @@
* The result may be null, which means that this logger's
* effective level will be inherited from its parent.
*
- * This method is primarily for testing purpose and not recommended
- * to be used at runtime since it does not support custom j.u.l.Level.
- *
* @return this PlatformLogger's level
- *
- * @throw IllegalArgumentException if j.u.l.Logger is set to
- * a custom j.u.l.Level when java.util.logging facility is enabled
*/
- public Level getLevel() {
+ public Level level() {
return loggerProxy.getLevel();
}
@@ -278,105 +338,105 @@
* Logs a SEVERE message.
*/
public void severe(String msg) {
- loggerProxy.doLog(SEVERE, msg);
+ loggerProxy.doLog(Level.SEVERE, msg);
}
public void severe(String msg, Throwable t) {
- loggerProxy.doLog(SEVERE, msg, t);
+ loggerProxy.doLog(Level.SEVERE, msg, t);
}
public void severe(String msg, Object... params) {
- loggerProxy.doLog(SEVERE, msg, params);
+ loggerProxy.doLog(Level.SEVERE, msg, params);
}
/**
* Logs a WARNING message.
*/
public void warning(String msg) {
- loggerProxy.doLog(WARNING, msg);
+ loggerProxy.doLog(Level.WARNING, msg);
}
public void warning(String msg, Throwable t) {
- loggerProxy.doLog(WARNING, msg, t);
+ loggerProxy.doLog(Level.WARNING, msg, t);
}
public void warning(String msg, Object... params) {
- loggerProxy.doLog(WARNING, msg, params);
+ loggerProxy.doLog(Level.WARNING, msg, params);
}
/**
* Logs an INFO message.
*/
public void info(String msg) {
- loggerProxy.doLog(INFO, msg);
+ loggerProxy.doLog(Level.INFO, msg);
}
public void info(String msg, Throwable t) {
- loggerProxy.doLog(INFO, msg, t);
+ loggerProxy.doLog(Level.INFO, msg, t);
}
public void info(String msg, Object... params) {
- loggerProxy.doLog(INFO, msg, params);
+ loggerProxy.doLog(Level.INFO, msg, params);
}
/**
* Logs a CONFIG message.
*/
public void config(String msg) {
- loggerProxy.doLog(CONFIG, msg);
+ loggerProxy.doLog(Level.CONFIG, msg);
}
public void config(String msg, Throwable t) {
- loggerProxy.doLog(CONFIG, msg, t);
+ loggerProxy.doLog(Level.CONFIG, msg, t);
}
public void config(String msg, Object... params) {
- loggerProxy.doLog(CONFIG, msg, params);
+ loggerProxy.doLog(Level.CONFIG, msg, params);
}
/**
* Logs a FINE message.
*/
public void fine(String msg) {
- loggerProxy.doLog(FINE, msg);
+ loggerProxy.doLog(Level.FINE, msg);
}
public void fine(String msg, Throwable t) {
- loggerProxy.doLog(FINE, msg, t);
+ loggerProxy.doLog(Level.FINE, msg, t);
}
public void fine(String msg, Object... params) {
- loggerProxy.doLog(FINE, msg, params);
+ loggerProxy.doLog(Level.FINE, msg, params);
}
/**
* Logs a FINER message.
*/
public void finer(String msg) {
- loggerProxy.doLog(FINER, msg);
+ loggerProxy.doLog(Level.FINER, msg);
}
public void finer(String msg, Throwable t) {
- loggerProxy.doLog(FINER, msg, t);
+ loggerProxy.doLog(Level.FINER, msg, t);
}
public void finer(String msg, Object... params) {
- loggerProxy.doLog(FINER, msg, params);
+ loggerProxy.doLog(Level.FINER, msg, params);
}
/**
* Logs a FINEST message.
*/
public void finest(String msg) {
- loggerProxy.doLog(FINEST, msg);
+ loggerProxy.doLog(Level.FINEST, msg);
}
public void finest(String msg, Throwable t) {
- loggerProxy.doLog(FINEST, msg, t);
+ loggerProxy.doLog(Level.FINEST, msg, t);
}
public void finest(String msg, Object... params) {
- loggerProxy.doLog(FINEST, msg, params);
+ loggerProxy.doLog(Level.FINEST, msg, params);
}
/**
@@ -421,7 +481,7 @@
}
boolean isEnabled() {
- return effectiveLevel != OFF;
+ return effectiveLevel != Level.OFF;
}
Level getLevel() {
@@ -457,7 +517,7 @@
boolean isLoggable(Level level) {
Level effectiveLevel = this.effectiveLevel;
- return level.intValue() >= effectiveLevel.intValue() && effectiveLevel != OFF;
+ return level.intValue() >= effectiveLevel.intValue() && effectiveLevel != Level.OFF;
}
// derive effective level (could do inheritance search like j.u.l.Logger)
@@ -611,15 +671,18 @@
/**
* Returns the PlatformLogger.Level mapped from j.u.l.Level
- * set in the logger.
- * @throw IllegalArgumentException if j.u.l.Logger is set to
- * a custom j.u.l.Level
+ * set in the logger. If the j.u.l.Logger is set to a custom Level,
+ * this method will return the nearest Level.
*/
Level getLevel() {
Object javaLevel = LoggingSupport.getLevel(javaLogger);
- return javaLevel == null
- ? null
- : Level.valueOf(LoggingSupport.getLevelName(javaLevel));
+ if (javaLevel == null) return null;
+
+ try {
+ return Level.valueOf(LoggingSupport.getLevelName(javaLevel));
+ } catch (IllegalArgumentException e) {
+ return Level.valueOf(LoggingSupport.getLevelValue(javaLevel));
+ }
}
void setLevel(Level level) {
--- a/jdk/test/sun/util/logging/PlatformLoggerTest.java Thu Apr 04 20:05:47 2013 -0700
+++ b/jdk/test/sun/util/logging/PlatformLoggerTest.java Fri Apr 05 10:41:46 2013 -0700
@@ -36,6 +36,7 @@
import java.lang.reflect.Field;
import java.util.logging.*;
import sun.util.logging.PlatformLogger;
+import static sun.util.logging.PlatformLogger.Level.*;
public class PlatformLoggerTest {
public static void main(String[] args) throws Exception {
@@ -69,40 +70,63 @@
checkLogger(GOO_PLATFORM_LOGGER, null);
checkLogger(BAR_LOGGER, Level.WARNING);
- foo.setLevel(PlatformLogger.SEVERE);
+ foo.setLevel(PlatformLogger.Level.SEVERE);
checkLogger(FOO_PLATFORM_LOGGER, Level.SEVERE);
checkPlatformLoggerLevels(foo, bar);
}
+ // don't use java.util.logging here to prevent it from initialized
private static void checkPlatformLogger(PlatformLogger logger, String name) {
if (!logger.getName().equals(name)) {
throw new RuntimeException("Invalid logger's name " +
logger.getName() + " but expected " + name);
}
- if (logger.getLevel() != null) {
+ if (logger.level() != null) {
throw new RuntimeException("Invalid default level for logger " +
- logger.getName() + ": " + logger.getLevel());
+ logger.getName() + ": " + logger.level());
}
- if (logger.isLoggable(PlatformLogger.FINE) != false) {
- throw new RuntimeException("isLoggerable(FINE) returns true for logger " +
- logger.getName() + " but expected false");
+ checkLoggable(logger, FINE, false);
+
+ logger.setLevel(FINER);
+ checkLevel(logger, FINER);
+ checkLoggable(logger, FINER, true);
+ checkLoggable(logger, FINE, true);
+ checkLoggable(logger, FINEST, false);
+
+ logger.info("OK: Testing log message");
+ }
+
+ private static void checkLoggable(PlatformLogger logger, PlatformLogger.Level level, boolean expected) {
+ if (logger.isLoggable(level) != expected) {
+ throw new RuntimeException("logger " + logger.getName() + ": " + level +
+ (expected ? " not loggable" : " loggable"));
}
- logger.setLevel(PlatformLogger.FINER);
- if (logger.getLevel() != PlatformLogger.FINER) {
- throw new RuntimeException("Invalid level for logger " +
- logger.getName() + " " + logger.getLevel());
+ if (logger.isLoggable(level.intValue()) != expected) {
+ throw new RuntimeException("logger " + logger.getName() + ": " + level.intValue() +
+ (expected ? " not loggable" : " loggable"));
}
- if (logger.isLoggable(PlatformLogger.FINE) != true) {
- throw new RuntimeException("isLoggerable(FINE) returns false for logger " +
- logger.getName() + " but expected true");
+ int value = level.intValue() + 5; // custom level value
+ if (expected && !logger.isLoggable(value)) {
+ throw new RuntimeException("logger " + logger.getName() + ": " + value +
+ " not loggable");
+ }
+ }
+
+ private static void checkLevel(PlatformLogger logger, PlatformLogger.Level level) {
+ if (logger.level() != level) {
+ throw new RuntimeException("Invalid level for logger " +
+ logger.getName() + ": " + logger.level() + " != " + level);
}
- logger.info("OK: Testing log message");
+ if (logger.getLevel() != level.intValue()) {
+ throw new RuntimeException("Invalid level for logger " +
+ logger.getName() + ": " + logger.getLevel() + " != " + level.intValue());
+ }
}
private static void checkLogger(String name, Level level) {
@@ -146,23 +170,29 @@
for (Level level : levels) {
PlatformLogger.Level platformLevel = PlatformLogger.Level.valueOf(level.getName());
for (PlatformLogger logger : loggers) {
- // verify PlatformLogger.setLevel to a given level
- logger.setLevel(platformLevel);
- PlatformLogger.Level retrievedPlatformLevel = logger.getLevel();
- if (platformLevel != retrievedPlatformLevel) {
- throw new RuntimeException("Retrieved PlatformLogger level " +
- retrievedPlatformLevel +
- " is not the same as set level " + platformLevel);
- }
+ logger.setLevel(platformLevel); // setLevel(PlatformLogger.Level)
+ checkLoggerLevel(logger, level);
+
+ logger.setLevel(ALL); // setLevel(int)
+ checkLoggerLevel(logger, Level.ALL);
+ }
+ }
+ }
- // check the level set in java.util.logging.Logger
- Logger javaLogger = LogManager.getLogManager().getLogger(logger.getName());
- Level javaLevel = javaLogger.getLevel();
- if (javaLogger.getLevel() != level) {
- throw new RuntimeException("Retrieved backing java.util.logging.Logger level " +
- javaLevel + " is not the expected " + level);
- }
- }
+ private static void checkLoggerLevel(PlatformLogger logger, Level level) {
+ PlatformLogger.Level plevel = PlatformLogger.Level.valueOf(level.getName());
+ if (plevel != logger.level()) {
+ throw new RuntimeException("Retrieved PlatformLogger level "
+ + logger.level()
+ + " is not the same as set level " + plevel);
+ }
+
+ // check the level set in java.util.logging.Logger
+ Logger javaLogger = LogManager.getLogManager().getLogger(logger.getName());
+ Level javaLevel = javaLogger.getLevel();
+ if (javaLogger.getLevel() != level) {
+ throw new RuntimeException("Retrieved backing java.util.logging.Logger level "
+ + javaLevel + " is not the expected " + level);
}
}
@@ -174,21 +204,23 @@
+ " PlatformLogger.Level" + platformLevel);
}
- PlatformLogger.Level plevel;
try {
// validate if there is a public static final field in PlatformLogger
- // matching the level name
- Field platformLevelField = PlatformLogger.class.getField(level.getName());
- plevel = (PlatformLogger.Level) platformLevelField.get(null);
+ Field constantField = PlatformLogger.class.getField(level.getName());
+ int l = (int) constantField.get(null);
+ if (l != platformLevel.intValue()) {
+ throw new RuntimeException("static final " + level.getName() + " (" +
+ l + ") != " + platformLevel.intValue());
+ }
} catch (Exception e) {
throw new RuntimeException("No public static PlatformLogger." + level.getName() +
" field", e);
}
- if (!plevel.name().equals(level.getName()))
+ if (!platformLevel.name().equals(level.getName()))
throw new RuntimeException("The value of PlatformLogger." + level.getName() + ".name() is "
+ platformLevel.name() + " but expected " + level.getName());
- if (plevel.intValue() != level.intValue())
+ if (platformLevel.intValue() != level.intValue())
throw new RuntimeException("The value of PlatformLogger." + level.intValue() + ".intValue() is "
+ platformLevel.intValue() + " but expected " + level.intValue());
}