Repository: cassandra Updated Branches: refs/heads/trunk c31ecba4b -> 115ed236a
Change Windows Kernel default timer resolution Patch by jmckenzie; reviewed by tjake for CASSANDRA-9634 Project: http://git-wip-us.apache.org/repos/asf/cassandra/repo Commit: http://git-wip-us.apache.org/repos/asf/cassandra/commit/d6d32d26 Tree: http://git-wip-us.apache.org/repos/asf/cassandra/tree/d6d32d26 Diff: http://git-wip-us.apache.org/repos/asf/cassandra/diff/d6d32d26 Branch: refs/heads/trunk Commit: d6d32d26ffd9aa17aa991c8c003e53632e5ba1c0 Parents: affb10c Author: Josh McKenzie <josh.mcken...@datastax.com> Authored: Mon Jun 22 17:27:08 2015 -0400 Committer: Josh McKenzie <josh.mcken...@datastax.com> Committed: Mon Jun 22 17:27:08 2015 -0400 ---------------------------------------------------------------------- CHANGES.txt | 1 + conf/cassandra.yaml | 7 +++ .../org/apache/cassandra/config/Config.java | 2 + .../cassandra/config/DatabaseDescriptor.java | 5 ++ .../cassandra/service/CassandraDaemon.java | 7 +++ .../cassandra/service/StorageService.java | 7 +++ .../org/apache/cassandra/transport/Server.java | 1 - .../apache/cassandra/utils/WindowsTimer.java | 65 ++++++++++++++++++++ .../src/org/apache/cassandra/stress/Stress.java | 7 +++ 9 files changed, 101 insertions(+), 1 deletion(-) ---------------------------------------------------------------------- http://git-wip-us.apache.org/repos/asf/cassandra/blob/d6d32d26/CHANGES.txt ---------------------------------------------------------------------- diff --git a/CHANGES.txt b/CHANGES.txt index 1e2acc4..16fe569 100644 --- a/CHANGES.txt +++ b/CHANGES.txt @@ -1,4 +1,5 @@ 2.2 + * Change Windows kernel default timer resolution (CASSANDRA-9634) * Deprected sstable2json and json2sstable (CASSANDRA-9618) * Allow native functions in user-defined aggregates (CASSANDRA-9542) * Don't repair system_distributed by default (CASSANDRA-9621) http://git-wip-us.apache.org/repos/asf/cassandra/blob/d6d32d26/conf/cassandra.yaml ---------------------------------------------------------------------- diff --git a/conf/cassandra.yaml b/conf/cassandra.yaml index ea22e01..dba8e1f 100644 --- a/conf/cassandra.yaml +++ b/conf/cassandra.yaml @@ -853,3 +853,10 @@ tracetype_repair_ttl: 604800 # This will inherently be backwards-incompatible with any 2.2 UDF that perform insecure # operations such as opening a socket or writing to the filesystem. enable_user_defined_functions: false + +# The default Windows kernel timer and scheduling resolution is 15.6ms for power conservation. +# Lowering this value on Windows can provide much tighter latency and better throughput, however +# some virtualized environments may see a negative performance impact from changing this setting +# below their system default. The sysinternals 'clockres' tool can confirm your system's default +# setting. +windows_timer_interval: 1 http://git-wip-us.apache.org/repos/asf/cassandra/blob/d6d32d26/src/java/org/apache/cassandra/config/Config.java ---------------------------------------------------------------------- diff --git a/src/java/org/apache/cassandra/config/Config.java b/src/java/org/apache/cassandra/config/Config.java index 269f577..5beeef2 100644 --- a/src/java/org/apache/cassandra/config/Config.java +++ b/src/java/org/apache/cassandra/config/Config.java @@ -259,6 +259,8 @@ public class Config public static final int otc_coalescing_window_us_default = 200; public int otc_coalescing_window_us = otc_coalescing_window_us_default; + public int windows_timer_interval = 0; + public boolean enable_user_defined_functions = false; public static boolean getOutboundBindAny() http://git-wip-us.apache.org/repos/asf/cassandra/blob/d6d32d26/src/java/org/apache/cassandra/config/DatabaseDescriptor.java ---------------------------------------------------------------------- diff --git a/src/java/org/apache/cassandra/config/DatabaseDescriptor.java b/src/java/org/apache/cassandra/config/DatabaseDescriptor.java index ad6b117..443246e 100644 --- a/src/java/org/apache/cassandra/config/DatabaseDescriptor.java +++ b/src/java/org/apache/cassandra/config/DatabaseDescriptor.java @@ -1688,4 +1688,9 @@ public class DatabaseDescriptor { return conf.enable_user_defined_functions; } + + public static int getWindowsTimerInterval() + { + return conf.windows_timer_interval; + } } http://git-wip-us.apache.org/repos/asf/cassandra/blob/d6d32d26/src/java/org/apache/cassandra/service/CassandraDaemon.java ---------------------------------------------------------------------- diff --git a/src/java/org/apache/cassandra/service/CassandraDaemon.java b/src/java/org/apache/cassandra/service/CassandraDaemon.java index 59ecca7..49e0c58 100644 --- a/src/java/org/apache/cassandra/service/CassandraDaemon.java +++ b/src/java/org/apache/cassandra/service/CassandraDaemon.java @@ -439,6 +439,13 @@ public class CassandraDaemon { String pidFile = System.getProperty("cassandra-pidfile"); + if (FBUtilities.isWindows()) + { + // We need to adjust the system timer on windows from the default 15ms down to the minimum of 1ms as this + // impacts timer intervals, thread scheduling, driver interrupts, etc. + WindowsTimer.startTimerPeriod(DatabaseDescriptor.getWindowsTimerInterval()); + } + try { try http://git-wip-us.apache.org/repos/asf/cassandra/blob/d6d32d26/src/java/org/apache/cassandra/service/StorageService.java ---------------------------------------------------------------------- diff --git a/src/java/org/apache/cassandra/service/StorageService.java b/src/java/org/apache/cassandra/service/StorageService.java index 3edbe22..19ef937 100644 --- a/src/java/org/apache/cassandra/service/StorageService.java +++ b/src/java/org/apache/cassandra/service/StorageService.java @@ -144,6 +144,7 @@ import org.apache.cassandra.utils.FBUtilities; import org.apache.cassandra.utils.JVMStabilityInspector; import org.apache.cassandra.utils.OutputHandler; import org.apache.cassandra.utils.Pair; +import org.apache.cassandra.utils.WindowsTimer; import org.apache.cassandra.utils.WrappedRunnable; import org.apache.cassandra.utils.progress.ProgressEvent; import org.apache.cassandra.utils.progress.ProgressEventType; @@ -665,6 +666,9 @@ public class StorageService extends NotificationBroadcasterSupport implements IE CommitLog.instance.shutdownBlocking(); + if (FBUtilities.isWindows()) + WindowsTimer.endTimerPeriod(DatabaseDescriptor.getWindowsTimerInterval()); + // wait for miscellaneous tasks like sstable and commitlog segment deletion ScheduledExecutors.nonPeriodicTasks.shutdown(); if (!ScheduledExecutors.nonPeriodicTasks.awaitTermination(1, TimeUnit.MINUTES)) @@ -709,6 +713,9 @@ public class StorageService extends NotificationBroadcasterSupport implements IE { if (drainOnShutdown != null) Runtime.getRuntime().removeShutdownHook(drainOnShutdown); + + if (FBUtilities.isWindows()) + WindowsTimer.endTimerPeriod(DatabaseDescriptor.getWindowsTimerInterval()); } private boolean shouldBootstrap() http://git-wip-us.apache.org/repos/asf/cassandra/blob/d6d32d26/src/java/org/apache/cassandra/transport/Server.java ---------------------------------------------------------------------- diff --git a/src/java/org/apache/cassandra/transport/Server.java b/src/java/org/apache/cassandra/transport/Server.java index 333b956..72a1b60 100644 --- a/src/java/org/apache/cassandra/transport/Server.java +++ b/src/java/org/apache/cassandra/transport/Server.java @@ -136,7 +136,6 @@ public class Server implements CassandraDaemon.Server // Configure the server. eventExecutorGroup = new RequestThreadPoolExecutor(); - boolean hasEpoll = enableEpoll ? Epoll.isAvailable() : false; if (hasEpoll) { http://git-wip-us.apache.org/repos/asf/cassandra/blob/d6d32d26/src/java/org/apache/cassandra/utils/WindowsTimer.java ---------------------------------------------------------------------- diff --git a/src/java/org/apache/cassandra/utils/WindowsTimer.java b/src/java/org/apache/cassandra/utils/WindowsTimer.java new file mode 100644 index 0000000..9db8559 --- /dev/null +++ b/src/java/org/apache/cassandra/utils/WindowsTimer.java @@ -0,0 +1,65 @@ +/* + * 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.cassandra.utils; + +import org.slf4j.Logger; +import org.slf4j.LoggerFactory; + +import com.sun.jna.LastErrorException; +import com.sun.jna.Native; + +public final class WindowsTimer +{ + private static final Logger logger = LoggerFactory.getLogger(WindowsTimer.class); + + static + { + try + { + Native.register("winmm"); + } + catch (Exception e) + { + logger.error("Failed to register winmm.dll. Performance will be negatively impacted on this node."); + } + } + + private static native int timeBeginPeriod(int period) throws LastErrorException; + private static native int timeEndPeriod(int period) throws LastErrorException; + + private WindowsTimer() {} + + public static void startTimerPeriod(int period) + { + if (period == 0) + return; + assert(period > 0); + if (timeBeginPeriod(period) != 0) + logger.warn("Failed to set timer to : " + period + ". Performance will be degraded."); + } + + public static void endTimerPeriod(int period) + { + if (period == 0) + return; + assert(period > 0); + if (timeEndPeriod(period) != 0) + logger.warn("Failed to end accelerated timer period. System timer will remain set to: " + period + " ms."); + } +} http://git-wip-us.apache.org/repos/asf/cassandra/blob/d6d32d26/tools/stress/src/org/apache/cassandra/stress/Stress.java ---------------------------------------------------------------------- diff --git a/tools/stress/src/org/apache/cassandra/stress/Stress.java b/tools/stress/src/org/apache/cassandra/stress/Stress.java index 256cefb..a4ec8a0 100644 --- a/tools/stress/src/org/apache/cassandra/stress/Stress.java +++ b/tools/stress/src/org/apache/cassandra/stress/Stress.java @@ -22,6 +22,8 @@ import java.net.Socket; import java.net.SocketException; import org.apache.cassandra.stress.settings.StressSettings; +import org.apache.cassandra.utils.FBUtilities; +import org.apache.cassandra.utils.WindowsTimer; public final class Stress { @@ -52,6 +54,9 @@ public final class Stress public static void main(String[] arguments) throws Exception { + if (FBUtilities.isWindows()) + WindowsTimer.startTimerPeriod(1); + final StressSettings settings; try { @@ -109,6 +114,8 @@ public final class Stress stressAction.run(); } + if (FBUtilities.isWindows()) + WindowsTimer.endTimerPeriod(1); System.exit(0); }