435322 acceptor and selector configuration/priority
This commit is contained in:
parent
eee2ba206e
commit
69390954dc
|
@ -39,6 +39,7 @@ import java.util.concurrent.atomic.AtomicReference;
|
|||
|
||||
import org.eclipse.jetty.util.ConcurrentArrayQueue;
|
||||
import org.eclipse.jetty.util.TypeUtil;
|
||||
import org.eclipse.jetty.util.annotation.ManagedAttribute;
|
||||
import org.eclipse.jetty.util.component.AbstractLifeCycle;
|
||||
import org.eclipse.jetty.util.component.ContainerLifeCycle;
|
||||
import org.eclipse.jetty.util.component.Dumpable;
|
||||
|
@ -65,6 +66,7 @@ public abstract class SelectorManager extends AbstractLifeCycle implements Dumpa
|
|||
private final ManagedSelector[] _selectors;
|
||||
private long _connectTimeout = DEFAULT_CONNECT_TIMEOUT;
|
||||
private long _selectorIndex;
|
||||
private int _priorityDelta;
|
||||
|
||||
protected SelectorManager(Executor executor, Scheduler scheduler)
|
||||
{
|
||||
|
@ -110,6 +112,33 @@ public abstract class SelectorManager extends AbstractLifeCycle implements Dumpa
|
|||
_connectTimeout = milliseconds;
|
||||
}
|
||||
|
||||
|
||||
@ManagedAttribute("The priority delta to apply to selector threads")
|
||||
public int getSelectorPriorityDelta()
|
||||
{
|
||||
return _priorityDelta;
|
||||
}
|
||||
|
||||
/* ------------------------------------------------------------ */
|
||||
/** Set the selector thread priority delta.
|
||||
* <p>This allows the selector threads to run at a different priority.
|
||||
* Typically this would be used to lower the priority to give preference
|
||||
* to handling previously accepted connections rather than accepting
|
||||
* new connections</p>
|
||||
* @param selectorPriorityDelta
|
||||
*/
|
||||
public void setSelectorPriorityDelta(int selectorPriorityDelta)
|
||||
{
|
||||
int old=_priorityDelta;
|
||||
_priorityDelta = selectorPriorityDelta;
|
||||
if (old!=selectorPriorityDelta && isStarted())
|
||||
{
|
||||
for (ManagedSelector selector : _selectors)
|
||||
if (selector._thread!=null)
|
||||
selector._thread.setPriority(Math.max(Thread.MIN_PRIORITY,Math.min(Thread.MAX_PRIORITY,selector._thread.getPriority()-old+selectorPriorityDelta)));
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Executes the given task in a different thread.
|
||||
*
|
||||
|
@ -479,8 +508,12 @@ public abstract class SelectorManager extends AbstractLifeCycle implements Dumpa
|
|||
{
|
||||
_thread = Thread.currentThread();
|
||||
String name = _thread.getName();
|
||||
int priority=_thread.getPriority();
|
||||
try
|
||||
{
|
||||
if (_priorityDelta!=0)
|
||||
_thread.setPriority(Math.max(Thread.MIN_PRIORITY,Math.min(Thread.MAX_PRIORITY,priority+_priorityDelta)));
|
||||
|
||||
_thread.setName(name + "-selector-" + SelectorManager.this.getClass().getSimpleName()+"@"+Integer.toHexString(SelectorManager.this.hashCode())+"/"+_id);
|
||||
if (LOG.isDebugEnabled())
|
||||
LOG.debug("Starting {} on {}", _thread, this);
|
||||
|
@ -494,6 +527,8 @@ public abstract class SelectorManager extends AbstractLifeCycle implements Dumpa
|
|||
if (LOG.isDebugEnabled())
|
||||
LOG.debug("Stopped {} on {}", _thread, this);
|
||||
_thread.setName(name);
|
||||
if (_priorityDelta!=0)
|
||||
_thread.setPriority(priority);
|
||||
}
|
||||
}
|
||||
|
||||
|
|
|
@ -22,6 +22,8 @@
|
|||
<Arg>
|
||||
<New class="org.eclipse.jetty.server.ServerConnector">
|
||||
<Arg name="server"><Ref refid="Server" /></Arg>
|
||||
<Arg name="acceptors" type="int"><Property name="http.acceptors" default="-1"/></Arg>
|
||||
<Arg name="selectors" type="int"><Property name="http.selectors" default="-1"/></Arg>
|
||||
<Arg name="factories">
|
||||
<Array type="org.eclipse.jetty.server.ConnectionFactory">
|
||||
<Item>
|
||||
|
@ -35,6 +37,8 @@
|
|||
<Set name="port"><Property name="jetty.port" default="80" /></Set>
|
||||
<Set name="idleTimeout"><Property name="http.timeout" default="30000"/></Set>
|
||||
<Set name="soLingerTime"><Property name="http.soLingerTime" default="-1"/></Set>
|
||||
<Set name="acceptorPriorityDelta"><Property name="http.acceptorPriorityDelta" default="0"/></Set>
|
||||
<Set name="selectorPriorityDelta"><Property name="http.selectorPriorityDelta" default="0"/></Set>
|
||||
</New>
|
||||
</Arg>
|
||||
</Call>
|
||||
|
|
|
@ -23,6 +23,8 @@
|
|||
<Arg>
|
||||
<New class="org.eclipse.jetty.server.ServerConnector">
|
||||
<Arg name="server"><Ref refid="Server" /></Arg>
|
||||
<Arg name="acceptors" type="int"><Property name="ssl.acceptors" default="-1"/></Arg>
|
||||
<Arg name="selectors" type="int"><Property name="ssl.selectors" default="-1"/></Arg>
|
||||
<Arg name="factories">
|
||||
<Array type="org.eclipse.jetty.server.ConnectionFactory">
|
||||
<Item>
|
||||
|
@ -42,6 +44,8 @@
|
|||
<Set name="port"><Property name="https.port" default="443" /></Set>
|
||||
<Set name="idleTimeout"><Property name="https.timeout" default="30000"/></Set>
|
||||
<Set name="soLingerTime"><Property name="https.soLingerTime" default="-1"/></Set>
|
||||
<Set name="acceptorPriorityDelta"><Property name="ssl.acceptorPriorityDelta" default="0"/></Set>
|
||||
<Set name="selectorPriorityDelta"><Property name="ssl.selectorPriorityDelta" default="0"/></Set>
|
||||
</New>
|
||||
</Arg>
|
||||
</Call>
|
||||
|
|
|
@ -9,10 +9,19 @@ server
|
|||
etc/jetty-http.xml
|
||||
|
||||
[ini-template]
|
||||
## HTTP Connector Configuration
|
||||
# HTTP port to listen on
|
||||
### HTTP Connector Configuration
|
||||
|
||||
## HTTP port to listen on
|
||||
jetty.port=8080
|
||||
# HTTP idle timeout in milliseconds
|
||||
|
||||
## HTTP idle timeout in milliseconds
|
||||
http.timeout=30000
|
||||
# HTTP Socket.soLingerTime in seconds. (-1 to disable)
|
||||
|
||||
## HTTP Socket.soLingerTime in seconds. (-1 to disable)
|
||||
# http.soLingerTime=-1
|
||||
|
||||
## Parameters to control the number and priority of acceptors and selectors
|
||||
# http.selectors=1
|
||||
# http.acceptors=1
|
||||
# http.selectorPriorityDelta=0
|
||||
# http.acceptorPriorityDelta=0
|
||||
|
|
|
@ -12,24 +12,29 @@ etc/jetty-ssl.xml
|
|||
http://git.eclipse.org/c/jetty/org.eclipse.jetty.project.git/plain/jetty-server/src/main/config/etc/keystore|etc/keystore
|
||||
|
||||
[ini-template]
|
||||
## SSL Keystore Configuration
|
||||
### SSL Keystore Configuration
|
||||
# define the port to use for secure redirection
|
||||
jetty.secure.port=8443
|
||||
|
||||
# Setup a demonstration keystore and truststore
|
||||
## Setup a demonstration keystore and truststore
|
||||
jetty.keystore=etc/keystore
|
||||
jetty.truststore=etc/keystore
|
||||
|
||||
# Set the demonstration passwords.
|
||||
# Note that OBF passwords are not secure, just protected from casual observation
|
||||
# See http://www.eclipse.org/jetty/documentation/current/configuring-security-secure-passwords.html
|
||||
## Set the demonstration passwords.
|
||||
## Note that OBF passwords are not secure, just protected from casual observation
|
||||
## See http://www.eclipse.org/jetty/documentation/current/configuring-security-secure-passwords.html
|
||||
jetty.keystore.password=OBF:1vny1zlo1x8e1vnw1vn61x8g1zlu1vn4
|
||||
jetty.keymanager.password=OBF:1u2u1wml1z7s1z7a1wnl1u2g
|
||||
jetty.truststore.password=OBF:1vny1zlo1x8e1vnw1vn61x8g1zlu1vn4
|
||||
|
||||
# Set the client auth behavior
|
||||
# Set to true if client certificate authentication is required
|
||||
### Set the client auth behavior
|
||||
## Set to true if client certificate authentication is required
|
||||
# jetty.ssl.needClientAuth=true
|
||||
# Set to true if client certificate authentication is desired
|
||||
## Set to true if client certificate authentication is desired
|
||||
# jetty.ssl.wantClientAuth=true
|
||||
|
||||
## Parameters to control the number and priority of acceptors and selectors
|
||||
# ssl.selectors=1
|
||||
# ssl.acceptors=1
|
||||
# ssl.selectorPriorityDelta=0
|
||||
# ssl.acceptorPriorityDelta=0
|
||||
|
|
|
@ -147,6 +147,7 @@ public abstract class AbstractConnector extends ContainerLifeCycle implements Co
|
|||
private String _defaultProtocol;
|
||||
private ConnectionFactory _defaultConnectionFactory;
|
||||
private String _name;
|
||||
private int _acceptorPriorityDelta;
|
||||
|
||||
|
||||
/**
|
||||
|
@ -399,6 +400,30 @@ public abstract class AbstractConnector extends ContainerLifeCycle implements Co
|
|||
}
|
||||
}
|
||||
|
||||
@ManagedAttribute("The priority delta to apply to acceptor threads")
|
||||
public int getAcceptorPriorityDelta()
|
||||
{
|
||||
return _acceptorPriorityDelta;
|
||||
}
|
||||
|
||||
/* ------------------------------------------------------------ */
|
||||
/** Set the acceptor thread priority delta.
|
||||
* <p>This allows the acceptor thread to run at a different priority.
|
||||
* Typically this would be used to lower the priority to give preference
|
||||
* to handling previously accepted connections rather than accepting
|
||||
* new connections</p>
|
||||
* @param acceptorPriorityDelta
|
||||
*/
|
||||
public void setAcceptorPriorityDelta(int acceptorPriorityDelta)
|
||||
{
|
||||
int old=_acceptorPriorityDelta;
|
||||
_acceptorPriorityDelta = acceptorPriorityDelta;
|
||||
if (old!=acceptorPriorityDelta && isStarted())
|
||||
{
|
||||
for (Thread thread : _acceptors)
|
||||
thread.setPriority(Math.max(Thread.MIN_PRIORITY,Math.min(Thread.MAX_PRIORITY,thread.getPriority()-old+acceptorPriorityDelta)));
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
@ManagedAttribute("Protocols supported by this connector")
|
||||
|
@ -452,14 +477,18 @@ public abstract class AbstractConnector extends ContainerLifeCycle implements Co
|
|||
@Override
|
||||
public void run()
|
||||
{
|
||||
Thread current = Thread.currentThread();
|
||||
String name=current.getName();
|
||||
final Thread thread = Thread.currentThread();
|
||||
String name=thread.getName();
|
||||
_name=String.format("%s-acceptor-%d@%x-%s",name,_acceptor,hashCode(),AbstractConnector.this.toString());
|
||||
current.setName(_name);
|
||||
thread.setName(_name);
|
||||
|
||||
int priority=thread.getPriority();
|
||||
if (_acceptorPriorityDelta!=0)
|
||||
thread.setPriority(Math.max(Thread.MIN_PRIORITY,Math.min(Thread.MAX_PRIORITY,priority+_acceptorPriorityDelta)));
|
||||
|
||||
synchronized (AbstractConnector.this)
|
||||
{
|
||||
_acceptors[_acceptor] = current;
|
||||
_acceptors[_acceptor] = thread;
|
||||
}
|
||||
|
||||
try
|
||||
|
@ -481,7 +510,9 @@ public abstract class AbstractConnector extends ContainerLifeCycle implements Co
|
|||
}
|
||||
finally
|
||||
{
|
||||
current.setName(name);
|
||||
thread.setName(name);
|
||||
if (_acceptorPriorityDelta!=0)
|
||||
thread.setPriority(priority);
|
||||
|
||||
synchronized (AbstractConnector.this)
|
||||
{
|
||||
|
|
|
@ -114,6 +114,26 @@ public class ServerConnector extends AbstractNetworkConnector
|
|||
this(server,null,null,null,acceptors,selectors,new HttpConnectionFactory());
|
||||
}
|
||||
|
||||
/* ------------------------------------------------------------ */
|
||||
/** HTTP Server Connection.
|
||||
* <p>Construct a ServerConnector with a private instance of {@link HttpConnectionFactory} as the only factory.</p>
|
||||
* @param server The {@link Server} this connector will accept connection for.
|
||||
* @param acceptors
|
||||
* the number of acceptor threads to use, or -1 for a default value. Acceptors accept new TCP/IP connections. If 0, then
|
||||
* the selector threads are used to accept connections.
|
||||
* @param selectors
|
||||
* the number of selector threads, or -1 for a default value. Selectors notice and schedule established connection that can make IO progress.
|
||||
* @param factories Zero or more {@link ConnectionFactory} instances used to create and configure connections.
|
||||
*/
|
||||
public ServerConnector(
|
||||
@Name("server") Server server,
|
||||
@Name("acceptors") int acceptors,
|
||||
@Name("selectors") int selectors,
|
||||
@Name("factories") ConnectionFactory... factories)
|
||||
{
|
||||
this(server,null,null,null,acceptors,selectors,factories);
|
||||
}
|
||||
|
||||
/* ------------------------------------------------------------ */
|
||||
/** Generic Server Connection with default configuration.
|
||||
* <p>Construct a Server Connector with the passed Connection factories.</p>
|
||||
|
@ -229,6 +249,25 @@ public class ServerConnector extends AbstractNetworkConnector
|
|||
return channel!=null && channel.isOpen();
|
||||
}
|
||||
|
||||
|
||||
@ManagedAttribute("The priority delta to apply to selector threads")
|
||||
public int getSelectorPriorityDelta()
|
||||
{
|
||||
return _manager.getSelectorPriorityDelta();
|
||||
}
|
||||
|
||||
/** Set the selector thread priority delta.
|
||||
* <p>This allows the selector threads to run at a different priority.
|
||||
* Typically this would be used to lower the priority to give preference
|
||||
* to handling previously accepted requests rather than accepting
|
||||
* new requests</p>
|
||||
* @param selectorPriorityDelta
|
||||
*/
|
||||
public void setSelectorPriorityDelta(int selectorPriorityDelta)
|
||||
{
|
||||
_manager.setSelectorPriorityDelta(selectorPriorityDelta);
|
||||
}
|
||||
|
||||
/**
|
||||
* @return whether this connector uses a channel inherited from the JVM.
|
||||
* @see System#inheritedChannel()
|
||||
|
|
|
@ -86,6 +86,8 @@ public class Main
|
|||
|
||||
public static String join(Collection<?> objs, String delim)
|
||||
{
|
||||
if (objs==null)
|
||||
return "";
|
||||
StringBuilder str = new StringBuilder();
|
||||
boolean needDelim = false;
|
||||
for (Object obj : objs)
|
||||
|
@ -392,17 +394,45 @@ public class Main
|
|||
}
|
||||
|
||||
boolean transitive = module.isEnabled() && (module.getSources().size() == 0);
|
||||
boolean hasDefinedDefaults = module.getDefaultConfig().size() > 0;
|
||||
boolean buildIni=false;
|
||||
if (module.isEnabled())
|
||||
{
|
||||
// is it an explicit request to create an ini file?
|
||||
if (topLevel && !FS.exists(startd_ini) && !appendStartIni)
|
||||
buildIni=true;
|
||||
|
||||
// If it is not enabled or is transitive with ini template lines or toplevel and doesn't exist
|
||||
if (!module.isEnabled() || (transitive && (hasDefinedDefaults || module.hasLicense()) ) || (topLevel && !FS.exists(startd_ini) && !appendStartIni))
|
||||
// else is it transitive
|
||||
else if (transitive)
|
||||
{
|
||||
// do we need an ini anyway?
|
||||
if (module.hasDefaultConfig() || module.hasLicense())
|
||||
buildIni=true;
|
||||
else
|
||||
StartLog.info("%-15s initialised transitively",name);
|
||||
}
|
||||
|
||||
// else must be initialized explicitly
|
||||
else
|
||||
{
|
||||
for (String source : module.getSources())
|
||||
StartLog.info("%-15s initialised in %s",name,baseHome.toShortForm(source));
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
buildIni=true;
|
||||
}
|
||||
|
||||
|
||||
// If we need an ini
|
||||
if (buildIni)
|
||||
{
|
||||
if (module.hasLicense())
|
||||
{
|
||||
System.err.printf("%nModule %s LICENSE%n",module.getName());
|
||||
System.err.printf("This module is not provided by the Eclipse Foundation!%n");
|
||||
System.err.printf("It contains software not covered by the Eclipse Public License%n");
|
||||
System.err.printf("The software has not been audited for compliance with its license%n");
|
||||
System.err.printf("%nModule %s:%n",module.getName());
|
||||
System.err.printf(" + contains software not provided by the Eclipse Foundation!%n");
|
||||
System.err.printf(" + contains software not covered by the Eclipse Public License!%n");
|
||||
System.err.printf(" + has not been audited for compliance with its license%n");
|
||||
System.err.printf("%n");
|
||||
for (String l : module.getLicense())
|
||||
System.err.printf(" %s%n",l);
|
||||
|
@ -484,14 +514,6 @@ public class Main
|
|||
}
|
||||
}
|
||||
}
|
||||
else if (FS.exists(startd_ini))
|
||||
{
|
||||
StartLog.info("%-15s initialised in %s",name,short_startd_ini);
|
||||
}
|
||||
else
|
||||
{
|
||||
StartLog.info("%-15s initialised transitively",name);
|
||||
}
|
||||
|
||||
// Also list other places this module is enabled
|
||||
for (String source : module.getSources())
|
||||
|
|
|
@ -265,6 +265,12 @@ public class Modules implements Iterable<Module>
|
|||
}
|
||||
}
|
||||
|
||||
public void enable(String name) throws IOException
|
||||
{
|
||||
List<String> empty = Collections.emptyList();
|
||||
enable(name,empty);
|
||||
}
|
||||
|
||||
public void enable(String name, List<String> sources) throws IOException
|
||||
{
|
||||
if (name.contains("*"))
|
||||
|
@ -310,9 +316,14 @@ public class Modules implements Iterable<Module>
|
|||
|
||||
private void enableModule(Module module, List<String> sources) throws IOException
|
||||
{
|
||||
// Always add the sources
|
||||
if (sources != null)
|
||||
module.addSources(sources);
|
||||
|
||||
// If already enabled, nothing else to do
|
||||
if (module.isEnabled())
|
||||
{
|
||||
// already enabled, skip
|
||||
StartLog.debug("Enabled module: %s (via %s)",module.getName(),Main.join(sources,", "));
|
||||
return;
|
||||
}
|
||||
|
||||
|
@ -320,10 +331,6 @@ public class Modules implements Iterable<Module>
|
|||
module.setEnabled(true);
|
||||
args.parseModule(module);
|
||||
module.expandProperties(args.getProperties());
|
||||
if (sources != null)
|
||||
{
|
||||
module.addSources(sources);
|
||||
}
|
||||
|
||||
// enable any parents that haven't been enabled (yet)
|
||||
Set<String> parentNames = new HashSet<>();
|
||||
|
@ -349,7 +356,7 @@ public class Modules implements Iterable<Module>
|
|||
}
|
||||
if (parent != null)
|
||||
{
|
||||
enableModule(parent,sources);
|
||||
enableModule(parent,null);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
@ -479,7 +479,10 @@ public class QueuedThreadPool extends AbstractLifeCycle implements SizedThreadPo
|
|||
@Override
|
||||
public void dump(Appendable out, String indent) throws IOException
|
||||
{
|
||||
out.append(String.valueOf(thread.getId())).append(' ').append(thread.getName()).append(' ').append(thread.getState().toString()).append(idle ? " IDLE" : "").append('\n');
|
||||
out.append(String.valueOf(thread.getId())).append(' ').append(thread.getName()).append(' ').append(thread.getState().toString()).append(idle ? " IDLE" : "");
|
||||
if (thread.getPriority()!=Thread.NORM_PRIORITY)
|
||||
out.append(" prio="+thread.getPriority());
|
||||
out.append('\n');
|
||||
if (!idle)
|
||||
ContainerLifeCycle.dump(out, indent, Arrays.asList(trace));
|
||||
}
|
||||
|
@ -493,7 +496,8 @@ public class QueuedThreadPool extends AbstractLifeCycle implements SizedThreadPo
|
|||
}
|
||||
else
|
||||
{
|
||||
dump.add(thread.getId() + " " + thread.getName() + " " + thread.getState() + " @ " + (trace.length > 0 ? trace[0] : "???") + (idle ? " IDLE" : ""));
|
||||
int p=thread.getPriority();
|
||||
dump.add(thread.getId() + " " + thread.getName() + " " + thread.getState() + " @ " + (trace.length > 0 ? trace[0] : "???") + (idle ? " IDLE" : "")+ (p==Thread.NORM_PRIORITY?"":(" prio="+p)));
|
||||
}
|
||||
}
|
||||
|
||||
|
|
|
@ -1,6 +0,0 @@
|
|||
#
|
||||
# HTTP connector
|
||||
#
|
||||
--module=http
|
||||
jetty.port=8080
|
||||
|
Loading…
Reference in New Issue