diff --git a/jetty-server/src/main/config/etc/jetty-ipaccess.xml b/jetty-server/src/main/config/etc/jetty-ipaccess.xml
deleted file mode 100644
index 832565c5ad2..00000000000
--- a/jetty-server/src/main/config/etc/jetty-ipaccess.xml
+++ /dev/null
@@ -1,28 +0,0 @@
-
-
-
-
-
-
-
-
-
-
-
-
-
- 127.0.0.1
- 127.0.0.2/*.html
-
-
-
-
- 127.0.0.1/blacklisted
- 127.0.0.2/black.html
-
-
- false
-
-
-
-
diff --git a/jetty-server/src/main/config/modules/inetaccess.mod b/jetty-server/src/main/config/modules/inetaccess.mod
new file mode 100644
index 00000000000..075464c631e
--- /dev/null
+++ b/jetty-server/src/main/config/modules/inetaccess.mod
@@ -0,0 +1,15 @@
+[description]
+Enable the InetAccessHandler to apply a include/exclude
+control of the remote IP of requests.
+
+[tags]
+handler
+
+[depend]
+server
+
+[files]
+basehome:modules/inetaccess/inetaccess.xml|etc/inetaccess.xml
+
+[xml]
+etc/inetaccess.xml
diff --git a/jetty-server/src/main/config/modules/inetaccess/inetaccess.xml b/jetty-server/src/main/config/modules/inetaccess/inetaccess.xml
new file mode 100644
index 00000000000..d58c878c5bf
--- /dev/null
+++ b/jetty-server/src/main/config/modules/inetaccess/inetaccess.xml
@@ -0,0 +1,13 @@
+
+
+
+
+
+
+
+ 127.0.0.1-127.0.0.255
+ 127.0.0.128-127.0.0.129
+
+
+
+
diff --git a/jetty-server/src/main/config/modules/ipaccess.mod b/jetty-server/src/main/config/modules/ipaccess.mod
deleted file mode 100644
index 0a985c917d9..00000000000
--- a/jetty-server/src/main/config/modules/ipaccess.mod
+++ /dev/null
@@ -1,12 +0,0 @@
-[description]
-Enable the ipaccess handler to apply a white/black list
-control of the remote IP of requests.
-
-[tags]
-handler
-
-[depend]
-server
-
-[xml]
-etc/jetty-ipaccess.xml
diff --git a/jetty-server/src/main/java/org/eclipse/jetty/server/handler/IPAccessHandler.java b/jetty-server/src/main/java/org/eclipse/jetty/server/handler/IPAccessHandler.java
deleted file mode 100644
index 111012aaee2..00000000000
--- a/jetty-server/src/main/java/org/eclipse/jetty/server/handler/IPAccessHandler.java
+++ /dev/null
@@ -1,386 +0,0 @@
-//
-// ========================================================================
-// Copyright (c) 1995-2017 Mort Bay Consulting Pty. Ltd.
-// ------------------------------------------------------------------------
-// All rights reserved. This program and the accompanying materials
-// are made available under the terms of the Eclipse Public License v1.0
-// and Apache License v2.0 which accompanies this distribution.
-//
-// The Eclipse Public License is available at
-// http://www.eclipse.org/legal/epl-v10.html
-//
-// The Apache License v2.0 is available at
-// http://www.opensource.org/licenses/apache2.0.php
-//
-// You may elect to redistribute this code under either of these licenses.
-// ========================================================================
-//
-
-package org.eclipse.jetty.server.handler;
-
-import java.io.IOException;
-import java.net.InetSocketAddress;
-import java.util.Map;
-
-import javax.servlet.ServletException;
-import javax.servlet.http.HttpServletRequest;
-import javax.servlet.http.HttpServletResponse;
-
-import org.eclipse.jetty.http.HttpStatus;
-import org.eclipse.jetty.http.PathMap;
-import org.eclipse.jetty.io.EndPoint;
-import org.eclipse.jetty.server.HttpChannel;
-import org.eclipse.jetty.server.Request;
-import org.eclipse.jetty.util.IPAddressMap;
-import org.eclipse.jetty.util.log.Log;
-import org.eclipse.jetty.util.log.Logger;
-
-
-/**
- * IP Access Handler
- *
- * Controls access to the wrapped handler by the real remote IP. Control is provided
- * by white/black lists that include both internet addresses and URIs. This handler
- * uses the real internet address of the connection, not one reported in the forwarded
- * for headers, as this cannot be as easily forged.
- *
- * Typically, the black/white lists will be used in one of three modes:
- *
- *
Blocking a few specific IPs/URLs by specifying several black list entries.
- *
Allowing only some specific IPs/URLs by specifying several white lists entries.
- *
Allowing a general range of IPs/URLs by specifying several general white list
- * entries, that are then further refined by several specific black list exceptions
- *
- *
- * By default an empty white list is treated as match all. If there is at least one entry in
- * the white list, then a request must match a white list entry. Black list entries
- * are always applied, so that even if an entry matches the white list, a black list
- * entry will override it.
- *
- * You can change white list policy setting whiteListByPath to true. In this mode a request will be white listed
- * IF it has a matching URL in the white list, otherwise the black list applies, e.g. in default mode when
- * whiteListByPath = false and wl = "127.0.0.1|/foo", /bar request from 127.0.0.1 will be blacklisted,
- * if whiteListByPath=true then not.
- *
- * Internet addresses may be specified as absolute address or as a combination of
- * four octet wildcard specifications (a.b.c.d) that are defined as follows.
- *
- *
- * nnn - an absolute value (0-255)
- * mmm-nnn - an inclusive range of absolute values,
- * with following shorthand notations:
- * nnn- => nnn-255
- * -nnn => 0-nnn
- * - => 0-255
- * a,b,... - a list of wildcard specifications
- *
- *
- * Internet address specification is separated from the URI pattern using the "|" (pipe)
- * character. URI patterns follow the servlet specification for simple * prefix and
- * suffix wild cards (e.g. /, /foo, /foo/bar, /foo/bar/*, *.baz).
- *
- * Earlier versions of the handler used internet address prefix wildcard specification
- * to define a range of the internet addresses (e.g. 127., 10.10., 172.16.1.).
- * They also used the first "/" character of the URI pattern to separate it from the
- * internet address. Both of these features have been deprecated in the current version.
- *
- * Examples of the entry specifications are:
- *
- *
10.10.1.2 - all requests from IP 10.10.1.2
- *
10.10.1.2|/foo/bar - all requests from IP 10.10.1.2 to URI /foo/bar
- *
10.10.1.2|/foo/* - all requests from IP 10.10.1.2 to URIs starting with /foo/
- *
10.10.1.2|*.html - all requests from IP 10.10.1.2 to URIs ending with .html
- *
10.10.0-255.0-255 - all requests from IPs within 10.10.0.0/16 subnet
- *
10.10.0-.-255|/foo/bar - all requests from IPs within 10.10.0.0/16 subnet to URI /foo/bar
- *
10.10.0-3,1,3,7,15|/foo/* - all requests from IPs addresses with last octet equal
- * to 1,3,7,15 in subnet 10.10.0.0/22 to URIs starting with /foo/
- *
- *
- * Earlier versions of the handler used internet address prefix wildcard specification
- * to define a range of the internet addresses (e.g. 127., 10.10., 172.16.1.).
- * They also used the first "/" character of the URI pattern to separate it from the
- * internet address. Both of these features have been deprecated in the current version.
- * @deprecated
- * @see InetAccessHandler
- */
-public class IPAccessHandler extends HandlerWrapper
-{
- private static final Logger LOG = Log.getLogger(IPAccessHandler.class);
- // true means nodefault match
- PathMap> _white = new PathMap>(true);
- PathMap> _black = new PathMap>(true);
- boolean _whiteListByPath = false;
-
- /* ------------------------------------------------------------ */
- /**
- * Creates new handler object
- */
- public IPAccessHandler()
- {
- super();
- }
-
- /* ------------------------------------------------------------ */
- /**
- * Creates new handler object and initializes white- and black-list
- *
- * @param white array of whitelist entries
- * @param black array of blacklist entries
- */
- public IPAccessHandler(String[] white, String []black)
- {
- super();
-
- if (white != null && white.length > 0)
- setWhite(white);
- if (black != null && black.length > 0)
- setBlack(black);
- }
-
- /* ------------------------------------------------------------ */
- /**
- * Add a whitelist entry to an existing handler configuration
- *
- * @param entry new whitelist entry
- */
- public void addWhite(String entry)
- {
- add(entry, _white);
- }
-
- /* ------------------------------------------------------------ */
- /**
- * Add a blacklist entry to an existing handler configuration
- *
- * @param entry new blacklist entry
- */
- public void addBlack(String entry)
- {
- add(entry, _black);
- }
-
- /* ------------------------------------------------------------ */
- /**
- * Re-initialize the whitelist of existing handler object
- *
- * @param entries array of whitelist entries
- */
- public void setWhite(String[] entries)
- {
- set(entries, _white);
- }
-
- /* ------------------------------------------------------------ */
- /**
- * Re-initialize the blacklist of existing handler object
- *
- * @param entries array of blacklist entries
- */
- public void setBlack(String[] entries)
- {
- set(entries, _black);
- }
-
- /* ------------------------------------------------------------ */
- /**
- * Re-initialize the mode of path matching
- *
- * @param whiteListByPath matching mode
- */
- public void setWhiteListByPath(boolean whiteListByPath)
- {
- this._whiteListByPath = whiteListByPath;
- }
-
- /* ------------------------------------------------------------ */
- /**
- * Checks the incoming request against the whitelist and blacklist
- *
- * @see org.eclipse.jetty.server.handler.HandlerWrapper#handle(java.lang.String, org.eclipse.jetty.server.Request, javax.servlet.http.HttpServletRequest, javax.servlet.http.HttpServletResponse)
- */
- @Override
- public void handle(String target, Request baseRequest, HttpServletRequest request, HttpServletResponse response) throws IOException, ServletException
- {
- // Get the real remote IP (not the one set by the forwarded headers (which may be forged))
- HttpChannel channel = baseRequest.getHttpChannel();
- if (channel!=null)
- {
- EndPoint endp=channel.getEndPoint();
- if (endp!=null)
- {
- InetSocketAddress address = endp.getRemoteAddress();
- if (address!=null && !isAddrUriAllowed(address.getHostString(),baseRequest.getPathInfo()))
- {
- response.sendError(HttpStatus.FORBIDDEN_403);
- baseRequest.setHandled(true);
- return;
- }
- }
- }
-
- getHandler().handle(target,baseRequest, request, response);
- }
-
-
- /* ------------------------------------------------------------ */
- /**
- * Helper method to parse the new entry and add it to
- * the specified address pattern map.
- *
- * @param entry new entry
- * @param patternMap target address pattern map
- */
- protected void add(String entry, PathMap> patternMap)
- {
- if (entry != null && entry.length() > 0)
- {
- boolean deprecated = false;
- int idx;
- if (entry.indexOf('|') > 0 )
- {
- idx = entry.indexOf('|');
- }
- else
- {
- idx = entry.indexOf('/');
- deprecated = (idx >= 0);
- }
-
- String addr = idx > 0 ? entry.substring(0,idx) : entry;
- String path = idx > 0 ? entry.substring(idx) : "/*";
-
- if (addr.endsWith("."))
- deprecated = true;
- if (path!=null && (path.startsWith("|") || path.startsWith("/*.")))
- path=path.substring(1);
-
- IPAddressMap addrMap = patternMap.get(path);
- if (addrMap == null)
- {
- addrMap = new IPAddressMap();
- patternMap.put(path,addrMap);
- }
- if (addr != null && !"".equals(addr))
- // MUST NOT BE null
- addrMap.put(addr, true);
-
- if (deprecated)
- LOG.debug(toString() +" - deprecated specification syntax: "+entry);
- }
- }
-
- /* ------------------------------------------------------------ */
- /**
- * Helper method to process a list of new entries and replace
- * the content of the specified address pattern map
- *
- * @param entries new entries
- * @param patternMap target address pattern map
- */
- protected void set(String[] entries, PathMap> patternMap)
- {
- patternMap.clear();
-
- if (entries != null && entries.length > 0)
- {
- for (String addrPath:entries)
- {
- add(addrPath, patternMap);
- }
- }
- }
-
- /* ------------------------------------------------------------ */
- /**
- * Check if specified request is allowed by current IPAccess rules.
- *
- * @param addr internet address
- * @param path context path
- * @return true if request is allowed
- *
- */
- protected boolean isAddrUriAllowed(String addr, String path)
- {
- if (_white.size()>0)
- {
- boolean match = false;
- boolean matchedByPath = false;
-
- for (Map.Entry> entry : _white.getMatches(path))
- {
- matchedByPath=true;
- IPAddressMap addrMap = entry.getValue();
- if ((addrMap!=null && (addrMap.size()==0 || addrMap.match(addr)!=null)))
- {
- match=true;
- break;
- }
- }
-
- if (_whiteListByPath)
- {
- if (matchedByPath && !match)
- return false;
- }
- else
- {
- if (!match)
- return false;
- }
- }
-
- if (_black.size() > 0)
- {
- for (Map.Entry> entry : _black.getMatches(path))
- {
- IPAddressMap addrMap = entry.getValue();
- if (addrMap!=null && (addrMap.size()==0 || addrMap.match(addr)!=null))
- return false;
- }
-
- }
-
- return true;
- }
-
- /* ------------------------------------------------------------ */
- /**
- * Dump the handler configuration
- */
- @Override
- public String dump()
- {
- StringBuilder buf = new StringBuilder();
-
- buf.append(toString());
- buf.append(" WHITELIST:\n");
- dump(buf, _white);
- buf.append(toString());
- buf.append(" BLACKLIST:\n");
- dump(buf, _black);
-
- return buf.toString();
- }
-
- /* ------------------------------------------------------------ */
- /**
- * Dump a pattern map into a StringBuilder buffer
- *
- * @param buf buffer
- * @param patternMap pattern map to dump
- */
- protected void dump(StringBuilder buf, PathMap> patternMap)
- {
- for (String path: patternMap.keySet())
- {
- for (String addr: patternMap.get(path).keySet())
- {
- buf.append("# ");
- buf.append(addr);
- buf.append("|");
- buf.append(path);
- buf.append("\n");
- }
- }
- }
- }
diff --git a/jetty-server/src/test/java/org/eclipse/jetty/server/handler/IPAccessHandlerTest.java b/jetty-server/src/test/java/org/eclipse/jetty/server/handler/IPAccessHandlerTest.java
deleted file mode 100644
index b3992698b60..00000000000
--- a/jetty-server/src/test/java/org/eclipse/jetty/server/handler/IPAccessHandlerTest.java
+++ /dev/null
@@ -1,565 +0,0 @@
-//
-// ========================================================================
-// Copyright (c) 1995-2017 Mort Bay Consulting Pty. Ltd.
-// ------------------------------------------------------------------------
-// All rights reserved. This program and the accompanying materials
-// are made available under the terms of the Eclipse Public License v1.0
-// and Apache License v2.0 which accompanies this distribution.
-//
-// The Eclipse Public License is available at
-// http://www.eclipse.org/legal/epl-v10.html
-//
-// The Apache License v2.0 is available at
-// http://www.opensource.org/licenses/apache2.0.php
-//
-// You may elect to redistribute this code under either of these licenses.
-// ========================================================================
-//
-
-package org.eclipse.jetty.server.handler;
-
-import static org.junit.Assert.assertEquals;
-import static org.junit.Assert.assertTrue;
-
-import java.io.BufferedReader;
-import java.io.EOFException;
-import java.io.IOException;
-import java.io.InputStreamReader;
-import java.io.OutputStream;
-import java.net.Socket;
-import java.nio.charset.StandardCharsets;
-import java.util.Arrays;
-import java.util.Collection;
-import java.util.LinkedHashMap;
-import java.util.Locale;
-import java.util.Map;
-import java.util.regex.Matcher;
-import java.util.regex.Pattern;
-
-import javax.servlet.ServletException;
-import javax.servlet.http.HttpServletRequest;
-import javax.servlet.http.HttpServletResponse;
-
-import org.eclipse.jetty.http.HttpStatus;
-import org.eclipse.jetty.server.Connector;
-import org.eclipse.jetty.server.NetworkConnector;
-import org.eclipse.jetty.server.Request;
-import org.eclipse.jetty.server.Server;
-import org.eclipse.jetty.server.ServerConnector;
-import org.junit.AfterClass;
-import org.junit.BeforeClass;
-import org.junit.Test;
-import org.junit.runner.RunWith;
-import org.junit.runners.Parameterized;
-import org.junit.runners.Parameterized.Parameters;
-
-@RunWith(Parameterized.class)
-public class IPAccessHandlerTest
-{
- private static Server _server;
- private static NetworkConnector _connector;
- private static IPAccessHandler _handler;
-
- private String _white;
- private String _black;
- private String _host;
- private String _uri;
- private String _code;
- private boolean _byPath;
-
- @BeforeClass
- public static void setUp()
- throws Exception
- {
- _server = new Server();
- _connector = new ServerConnector(_server);
- _server.setConnectors(new Connector[] { _connector });
-
- _handler = new IPAccessHandler();
- _handler.setHandler(new AbstractHandler()
- {
- @Override
- public void handle(String target, Request baseRequest, HttpServletRequest request, HttpServletResponse response) throws IOException, ServletException
- {
- baseRequest.setHandled(true);
- response.setStatus(HttpStatus.OK_200);
- }
- });
- _server.setHandler(_handler);
- _server.start();
- }
-
- /* ------------------------------------------------------------ */
- @AfterClass
- public static void tearDown()
- throws Exception
- {
- _server.stop();
- }
-
- /* ------------------------------------------------------------ */
- public IPAccessHandlerTest(String white, String black, String host, String uri, String code, boolean byPath)
- {
- _white = white;
- _black = black;
- _host = host;
- _uri = uri;
- _code = code;
- _byPath = byPath;
- }
-
- /* ------------------------------------------------------------ */
- @Test
- public void testHandler()
- throws Exception
- {
- _handler.setWhite(_white.split(";",-1));
- _handler.setBlack(_black.split(";",-1));
- _handler.setWhiteListByPath(_byPath);
-
- String request = "GET " + _uri + " HTTP/1.1\n" + "Host: "+ _host + "\n\n";
- Socket socket = new Socket("127.0.0.1", _connector.getLocalPort());
- socket.setSoTimeout(5000);
- try
- {
- OutputStream output = socket.getOutputStream();
- BufferedReader input = new BufferedReader(new InputStreamReader(socket.getInputStream()));
-
- output.write(request.getBytes(StandardCharsets.UTF_8));
- output.flush();
-
- Response response = readResponse(input);
- Object[] params = new Object[]{
- "Request WBHUC", _white, _black, _host, _uri, _code,
- "Response", response.getCode()};
- assertEquals(Arrays.deepToString(params), _code, response.getCode());
- }
- finally
- {
- socket.close();
- }
- }
-
- /* ------------------------------------------------------------ */
- protected Response readResponse(BufferedReader reader)
- throws IOException
- {
- // Simplified parser for HTTP responses
- String line = reader.readLine();
- if (line == null)
- throw new EOFException();
- Matcher responseLine = Pattern.compile("HTTP/1\\.1\\s+(\\d+)").matcher(line);
- assertTrue(responseLine.lookingAt());
- String code = responseLine.group(1);
-
- Map headers = new LinkedHashMap();
- while ((line = reader.readLine()) != null)
- {
- if (line.trim().length() == 0)
- break;
-
- Matcher header = Pattern.compile("([^:]+):\\s*(.*)").matcher(line);
- assertTrue(header.lookingAt());
- String headerName = header.group(1);
- String headerValue = header.group(2);
- headers.put(headerName.toLowerCase(Locale.ENGLISH), headerValue.toLowerCase(Locale.ENGLISH));
- }
-
- StringBuilder body = new StringBuilder();
- if (headers.containsKey("content-length"))
- {
- int length = Integer.parseInt(headers.get("content-length"));
- for (int i = 0; i < length; ++i)
- {
- char c = (char)reader.read();
- body.append(c);
- }
- }
- else if ("chunked".equals(headers.get("transfer-encoding")))
- {
- while ((line = reader.readLine()) != null)
- {
- if ("0".equals(line))
- {
- line = reader.readLine();
- assertEquals("", line);
- break;
- }
-
- int length = Integer.parseInt(line, 16);
- for (int i = 0; i < length; ++i)
- {
- char c = (char)reader.read();
- body.append(c);
- }
- line = reader.readLine();
- assertEquals("", line);
- }
- }
-
- return new Response(code, headers, body.toString().trim());
- }
-
- /* ------------------------------------------------------------ */
- protected class Response
- {
- private final String code;
- private final Map headers;
- private final String body;
-
- /* ------------------------------------------------------------ */
- private Response(String code, Map headers, String body)
- {
- this.code = code;
- this.headers = headers;
- this.body = body;
- }
-
- /* ------------------------------------------------------------ */
- public String getCode()
- {
- return code;
- }
-
- /* ------------------------------------------------------------ */
- public Map getHeaders()
- {
- return headers;
- }
-
- /* ------------------------------------------------------------ */
- public String getBody()
- {
- return body;
- }
-
- /* ------------------------------------------------------------ */
- @Override
- public String toString()
- {
- StringBuilder builder = new StringBuilder();
- builder.append(code).append("\r\n");
- for (Map.Entry entry : headers.entrySet())
- builder.append(entry.getKey()).append(": ").append(entry.getValue()).append("\r\n");
- builder.append("\r\n");
- builder.append(body);
- return builder.toString();
- }
- }
-
- /* ------------------------------------------------------------ */
- @Parameters
- public static Collection