From 9aa41d092ed5b7ebe4bfd9bfe21450b8f92ee010 Mon Sep 17 00:00:00 2001 From: Jason Tedor Date: Wed, 16 Dec 2015 13:57:08 -0500 Subject: [PATCH] Info on compressed ordinary object pointers This commit adds to JvmInfo the status of whether or not compressed ordinary object pointers are enabled. Additionally, logging of the max heap size and the status of the compressed ordinary object pointers flag are provided on startup. Relates #13187, relates elastic/elasticsearch-definitive-guide#455 --- .../elasticsearch/env/NodeEnvironment.java | 38 +++++++++++++--- .../elasticsearch/monitor/jvm/JvmInfo.java | 44 ++++++++++++++++++- 2 files changed, 76 insertions(+), 6 deletions(-) diff --git a/core/src/main/java/org/elasticsearch/env/NodeEnvironment.java b/core/src/main/java/org/elasticsearch/env/NodeEnvironment.java index 3a1b430f98b41..86b6b704a72d1 100644 --- a/core/src/main/java/org/elasticsearch/env/NodeEnvironment.java +++ b/core/src/main/java/org/elasticsearch/env/NodeEnvironment.java @@ -21,7 +21,12 @@ import org.apache.lucene.index.IndexWriter; import org.apache.lucene.index.SegmentInfos; -import org.apache.lucene.store.*; +import org.apache.lucene.store.Directory; +import org.apache.lucene.store.FSDirectory; +import org.apache.lucene.store.Lock; +import org.apache.lucene.store.LockObtainFailedException; +import org.apache.lucene.store.NativeFSLockFactory; +import org.apache.lucene.store.SimpleFSDirectory; import org.apache.lucene.util.IOUtils; import org.elasticsearch.ElasticsearchException; import org.elasticsearch.cluster.metadata.IndexMetaData; @@ -31,6 +36,7 @@ import org.elasticsearch.common.inject.Inject; import org.elasticsearch.common.io.FileSystemUtils; import org.elasticsearch.common.settings.Settings; +import org.elasticsearch.common.unit.ByteSizeValue; import org.elasticsearch.common.unit.TimeValue; import org.elasticsearch.index.Index; import org.elasticsearch.index.IndexSettings; @@ -38,11 +44,25 @@ import org.elasticsearch.index.store.FsDirectoryService; import org.elasticsearch.monitor.fs.FsInfo; import org.elasticsearch.monitor.fs.FsProbe; +import org.elasticsearch.monitor.jvm.JvmInfo; import java.io.Closeable; import java.io.IOException; -import java.nio.file.*; -import java.util.*; +import java.nio.file.AtomicMoveNotSupportedException; +import java.nio.file.DirectoryStream; +import java.nio.file.FileStore; +import java.nio.file.Files; +import java.nio.file.Path; +import java.nio.file.StandardCopyOption; +import java.util.ArrayList; +import java.util.Arrays; +import java.util.Collection; +import java.util.HashMap; +import java.util.HashSet; +import java.util.List; +import java.util.Locale; +import java.util.Map; +import java.util.Set; import java.util.concurrent.Semaphore; import java.util.concurrent.TimeUnit; import java.util.concurrent.atomic.AtomicBoolean; @@ -145,7 +165,7 @@ public NodeEnvironment(Settings settings, Environment environment) throws IOExce for (int dirIndex = 0; dirIndex < environment.dataWithClusterFiles().length; dirIndex++) { Path dir = environment.dataWithClusterFiles()[dirIndex].resolve(NODES_FOLDER).resolve(Integer.toString(possibleLockId)); Files.createDirectories(dir); - + try (Directory luceneDir = FSDirectory.open(dir, NativeFSLockFactory.INSTANCE)) { logger.trace("obtaining node lock on {} ...", dir.toAbsolutePath()); try { @@ -187,6 +207,7 @@ public NodeEnvironment(Settings settings, Environment environment) throws IOExce } maybeLogPathDetails(); + maybeLogHeapDetails(); if (settings.getAsBoolean(SETTING_ENABLE_LUCENE_SEGMENT_INFOS_TRACE, false)) { SegmentInfos.setInfoStream(System.out); @@ -274,6 +295,13 @@ private void maybeLogPathDetails() throws IOException { } } + private void maybeLogHeapDetails() { + ByteSizeValue maxHeapSize = JvmInfo.jvmInfo().getMem().getHeapMax(); + Boolean usingCompressedOops = JvmInfo.jvmInfo().usingCompressedOops(); + String usingCompressedOopsStatus = usingCompressedOops == null ? "unknown" : Boolean.toString(usingCompressedOops); + logger.info("heap size [{}], compressed ordinary object pointers [{}]", maxHeapSize, usingCompressedOopsStatus); + } + private static String toString(Collection items) { StringBuilder b = new StringBuilder(); for(String item : items) { @@ -811,7 +839,7 @@ public static Path shardStatePathToDataPath(Path shardPath) { // Sanity check: assert Integer.parseInt(shardPath.getName(count-1).toString()) >= 0; assert "indices".equals(shardPath.getName(count-3).toString()); - + return shardPath.getParent().getParent().getParent(); } } diff --git a/core/src/main/java/org/elasticsearch/monitor/jvm/JvmInfo.java b/core/src/main/java/org/elasticsearch/monitor/jvm/JvmInfo.java index e224c722d42d1..7fbfb5bc82b34 100644 --- a/core/src/main/java/org/elasticsearch/monitor/jvm/JvmInfo.java +++ b/core/src/main/java/org/elasticsearch/monitor/jvm/JvmInfo.java @@ -29,7 +29,14 @@ import org.elasticsearch.common.xcontent.XContentBuilderString; import java.io.IOException; -import java.lang.management.*; +import java.lang.management.GarbageCollectorMXBean; +import java.lang.management.ManagementFactory; +import java.lang.management.ManagementPermission; +import java.lang.management.MemoryMXBean; +import java.lang.management.MemoryPoolMXBean; +import java.lang.management.PlatformManagedObject; +import java.lang.management.RuntimeMXBean; +import java.lang.reflect.Method; import java.util.Collections; import java.util.HashMap; import java.util.List; @@ -101,6 +108,21 @@ public class JvmInfo implements Streamable, ToXContent { info.memoryPools[i] = memoryPoolMXBean.getName(); } + try { + @SuppressWarnings("unchecked") Class clazz = + (Class)Class.forName("com.sun.management.HotSpotDiagnosticMXBean"); + Class vmOptionClazz = Class.forName("com.sun.management.VMOption"); + PlatformManagedObject hotSpotDiagnosticMXBean = ManagementFactory.getPlatformMXBean(clazz); + Method vmOptionMethod = clazz.getMethod("getVMOption", String.class); + Object useCompressedOopsVmOption = vmOptionMethod.invoke(hotSpotDiagnosticMXBean, "UseCompressedOops"); + Method valueMethod = vmOptionClazz.getMethod("getValue"); + String value = (String)valueMethod.invoke(useCompressedOopsVmOption); + info.usingCompressedOops = Boolean.parseBoolean(value); + } catch (Throwable t) { + // unable to deduce the state of compressed oops + // usingCompressedOops will hold its default value of null + } + INSTANCE = info; } @@ -135,6 +157,8 @@ public static JvmInfo jvmInfo() { String[] gcCollectors = Strings.EMPTY_ARRAY; String[] memoryPools = Strings.EMPTY_ARRAY; + private Boolean usingCompressedOops; + private JvmInfo() { } @@ -258,6 +282,10 @@ public Map getSystemProperties() { return this.systemProperties; } + public Boolean usingCompressedOops() { + return this.usingCompressedOops; + } + @Override public XContentBuilder toXContent(XContentBuilder builder, Params params) throws IOException { builder.startObject(Fields.JVM); @@ -279,6 +307,8 @@ public XContentBuilder toXContent(XContentBuilder builder, Params params) throws builder.field(Fields.GC_COLLECTORS, gcCollectors); builder.field(Fields.MEMORY_POOLS, memoryPools); + builder.field(Fields.USING_COMPRESSED_OOPS, usingCompressedOops == null ? "unknown" : usingCompressedOops); + builder.endObject(); return builder; } @@ -306,6 +336,7 @@ static final class Fields { static final XContentBuilderString DIRECT_MAX_IN_BYTES = new XContentBuilderString("direct_max_in_bytes"); static final XContentBuilderString GC_COLLECTORS = new XContentBuilderString("gc_collectors"); static final XContentBuilderString MEMORY_POOLS = new XContentBuilderString("memory_pools"); + static final XContentBuilderString USING_COMPRESSED_OOPS = new XContentBuilderString("using_compressed_ordinary_object_pointers"); } public static JvmInfo readJvmInfo(StreamInput in) throws IOException { @@ -337,6 +368,11 @@ public void readFrom(StreamInput in) throws IOException { mem.readFrom(in); gcCollectors = in.readStringArray(); memoryPools = in.readStringArray(); + if (in.readBoolean()) { + usingCompressedOops = in.readBoolean(); + } else { + usingCompressedOops = null; + } } @Override @@ -361,6 +397,12 @@ public void writeTo(StreamOutput out) throws IOException { mem.writeTo(out); out.writeStringArray(gcCollectors); out.writeStringArray(memoryPools); + if (usingCompressedOops != null) { + out.writeBoolean(true); + out.writeBoolean(usingCompressedOops); + } else { + out.writeBoolean(false); + } } public static class Mem implements Streamable {