--- /dev/null
+/*\r
+\r
+ Derby - Class org.apache.derby.drda.NetworkServerControl\r
+\r
+ Licensed to the Apache Software Foundation (ASF) under one or more\r
+ contributor license agreements. See the NOTICE file distributed with\r
+ this work for additional information regarding copyright ownership.\r
+ The ASF licenses this file to You under the Apache License, Version 2.0\r
+ (the "License"); you may not use this file except in compliance with\r
+ the License. You may obtain a copy of the License at\r
+\r
+ http://www.apache.org/licenses/LICENSE-2.0\r
+\r
+ Unless required by applicable law or agreed to in writing, software\r
+ distributed under the License is distributed on an "AS IS" BASIS,\r
+ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\r
+ See the License for the specific language governing permissions and\r
+ limitations under the License.\r
+\r
+ */\r
+\r
+package org.apache.derby.drda;\r
+\r
+import java.io.PrintWriter;\r
+import java.net.InetAddress;\r
+import java.net.Inet6Address;\r
+import java.net.URL;\r
+import java.util.Properties;\r
+import org.apache.derby.iapi.reference.Property;\r
+import org.apache.derby.iapi.services.property.PropertyUtil;\r
+\r
+import org.apache.derby.impl.drda.NetworkServerControlImpl;\r
+\r
+/** \r
+ NetworkServerControl provides the ability to start a Network Server or \r
+ connect to a running Network Server to shutdown, configure or retreive \r
+ diagnostic information. With the exception of ping, these commands \r
+ can only be performed from the machine on which the server is running. \r
+ Commands can be performed from the command line with the following \r
+ arguments:\r
+\r
+ <P>\r
+ <UL>\r
+ <LI>start [-h <host>] [-p <portnumber>] [-ssl <sslmode>]: This starts the network\r
+ server on the port/host specified or on localhost, port 1527 if no\r
+ host/port is specified and no properties are set to override the \r
+ defaults. By default Network Server will only listen for \r
+ connections from the machine on which it is running. \r
+ Use -h 0.0.0.0 to listen on all interfaces or -h <hostname> to listen \r
+ on a specific interface on a multiple IP machine. \r
+ For documentation on <sslmode>, consult the Server and Administration Guide.</LI>\r
+\r
+ <LI>shutdown [-h <host>][-p <portnumber>] [-ssl <sslmode>]: This shutdowns the network server on the host and port specified or on the local host and port \r
+ 1527(default) if no host or port is specified. </LI> \r
+\r
+ <LI>ping [-h <host>] [-p <portnumber>] [-ssl <sslmode>]\r
+ This will test whether the Network Server is up.\r
+ </LI>\r
+\r
+ <LI>sysinfo [-h <host>] [-p <portnumber>] [-ssl <sslmode>]: This prints \r
+ classpath and version information about the Network Server, \r
+ the JVM and the Derby engine. \r
+\r
+ <LI>runtimeinfo [-h <host] [-p <portnumber] [-ssl <sslmode>]: This prints\r
+ extensive debbugging information about sessions, threads, \r
+ prepared statements, and memory usage for the running Network Server.\r
+ </LI>\r
+\r
+ <LI>logconnections {on | off} [-h <host>] [-p <portnumber>] [-ssl <sslmode>]: \r
+ This turns logging of connections on or off. \r
+ Connections are logged to derby.log. \r
+ Default is off.</LI>\r
+\r
+ <LI>maxthreads <max> [-h <host>][-p <portnumber>] [-ssl <sslmode>]: \r
+ This sets the maximum number of threads that can be used for connections. \r
+ Default 0 (unlimitted).\r
+ </LI>\r
+\r
+ <LI>timeslice <milliseconds> [-h <host>][-p <portnumber>] [-ssl <sslmode>]: \r
+ This sets the time each session can have using a connection thread \r
+ before yielding to a waiting session. Default is 0 (no yeild).\r
+ \r
+ </LI>\r
+\r
+ <LI>trace {on | off} [-s <session id>] [-h <host>] [-p <portnumber>] [-ssl <sslmode>]: \r
+ This turns drda tracing on or off for the specified session or if no \r
+ session is specified for all sessions. Default is off</LI>\r
+\r
+\r
+ <LI>tracedirectory <tracedirectory> [-h <host>] [-p <portnumber>] [-ssl <sslmode>]: \r
+ This changes where new trace files will be placed. \r
+ For sessions with tracing already turned on, \r
+ trace files remain in the previous location. \r
+ Default is derby.system.home, if it is set. \r
+ Otherwise the default is the current directory.</LI>\r
+\r
+ </UL>\r
+ <P>Properties can be set in the derby.properties file or on the command line.\r
+ Properties on the command line take precedence over properties in the \r
+ derby.properties file. Arguments on the command line take precedence\r
+ over properties. \r
+ The following is a list of properties that can be set for \r
+ NetworkServerControl:\r
+\r
+ <UL><LI>derby.drda.portNumber=<port number>: This property \r
+ indicates which port should be used for the Network Server. </LI>\r
+\r
+ <LI>derby.drda.host=<host name or ip address >: This property \r
+ indicates the ip address to which NetworkServerControl should connect \r
+\r
+ <LI>derby.drda.traceDirectory=<trace directory>: This property \r
+ indicates where to put trace files. </LI>\r
+\r
+ <LI>derby.drda.traceAll=true: This property turns on tracing for\r
+ all sessions. Default is tracing is off.</LI>\r
+\r
+ <LI>derby.drda.logConnections=true: This property turns on logging\r
+ of connections. Default is connections are not logged.</LI>\r
+\r
+ <LI>derby.drda.minThreads=<value>: If this property\r
+ is set, the <value> number of threads will be created when the Network Server is\r
+ booted. </LI>\r
+\r
+ <LI>derby.drda.maxThreads=<value>: If this property\r
+ is set, the <value> is the maximum number of connection threads that will be \r
+ created. If a session starts when there are no connection threads available\r
+ and the maximum number of threads has been reached, it will wait until a \r
+ conection thread becomes available. </LI>\r
+\r
+ <LI>derby.drda.timeSlice=<milliseconds>: If this property\r
+ is set, the connection threads will not check for waiting sessions until the\r
+ current session has been working for <milliseconds>. \r
+ A value of 0 causes the thread to work on the current session until the \r
+ session exits. If this property is not set, the default value is 0. </LI>\r
+\r
+ <LI>derby.drda.sslMode=<sslmode>: This property sets the SSL\r
+ mode of the server.\r
+ \r
+</LI>\r
+\r
+<P><B>Examples.</B>\r
+\r
+ <P>This is an example of shutting down the server on port 1621.\r
+ <PRE> \r
+ java org.apache.derby.drda.NetworkServerControl shutdown -p 1621\r
+ </PRE>\r
+\r
+ <P>This is an example of turning tracing on for session 3\r
+ <PRE>\r
+ java org.apache.derby.drda.NetworkServerControl trace on -s 3 \r
+ </PRE>\r
+\r
+ <P>This is an example of starting and then shutting down the network \r
+ server on port 1621 on machine myhost \r
+ <PRE>\r
+ java org.apache.derby.drda.NetworkServerControl start -h myhost -p 1621\r
+ java org.apache.derby.drda.NetworkServerControl shutdown -h myhost -p 1621\r
+ </PRE>\r
+\r
+ <P> This is an example of starting and shutting down the Network Server in the example\r
+ above with the API.\r
+ <PRE>\r
+ \r
+ NetworkServerControl serverControl = new NetworkServerControl(InetAddress.getByName("myhost"),1621)\r
+\r
+ serverControl.shutdown();\r
+ </PRE>\r
+\r
+ \r
+*/\r
+\r
+public class NetworkServerControl{\r
+\r
+\r
+ \r
+ public final static int DEFAULT_PORTNUMBER = 1527;\r
+\r
+ private final static String DERBYNET_JAR = "derbynet.jar";\r
+ private final static String POLICY_FILENAME = "server.policy";\r
+ private final static String POLICY_FILE_PROPERTY = "java.security.policy";\r
+ private final static String DERBY_HOSTNAME_WILDCARD = "0.0.0.0";\r
+ private final static String IPV6_HOSTNAME_WILDCARD = "::";\r
+ private final static String SOCKET_PERMISSION_HOSTNAME_WILDCARD = "*";\r
+\r
+ private NetworkServerControlImpl serverImpl;\r
+\r
+ // constructor\r
+\r
+ /**\r
+ * \r
+ * Creates a NetworkServerControl object that is configured to control\r
+ * a Network Server on a specified port and InetAddress.\r
+ *<P>\r
+ * <B> Examples: </B>\r
+ * <P>\r
+ * To configure for port 1621 and listen on the loopback address:\r
+ *<PRE>\r
+ * NetworkServerControl util = new\r
+ * NetworkServerControl(InetAddress.getByName("localhost"), 1621);\r
+ * </PRE>\r
+ *\r
+ * @param address The IP address of the Network Server host.\r
+ * address cannot be null.\r
+\r
+ * @param portNumber port number server is to used. If <= 0,\r
+ * default port number is used\r
+ * \r
+ * @throws Exception on error\r
+ */\r
+ public NetworkServerControl(InetAddress address,int portNumber) throws Exception\r
+ {\r
+ \r
+ serverImpl = new NetworkServerControlImpl(address, portNumber);\r
+\r
+ }\r
+ \r
+\r
+ /**\r
+ * \r
+ * Creates a NetworkServerControl object that is configured to control\r
+ * a Network Server on the default host(localhost)\r
+ * and the default port(1527) unless derby.drda.portNumber and \r
+ * derby.drda.host are set.\r
+ * <P><PRE>\r
+ * new NetworkServerControl() \r
+ *\r
+ * is equivalent to calling\r
+ *\r
+ * new NetworkServerControl(InetAddress.getByName("localhost"),1527);\r
+ * </PRE>\r
+ *\r
+ * @throws Exception on error\r
+ */\r
+ public NetworkServerControl() throws Exception\r
+ {\r
+ \r
+ serverImpl = new NetworkServerControlImpl();\r
+\r
+ }\r
+ \r
+ \r
+ /**\r
+ * main routine for NetworkServerControl\r
+ *\r
+ * @param args array of arguments indicating command to be executed.\r
+ * See class comments for more information\r
+ */\r
+ public static void main(String args[]) {\r
+ NetworkServerControlImpl server = null;\r
+\r
+ //\r
+ // The following variable lets us preserve the error printing behavior\r
+ // seen before we started installing a security manager. Errors can be\r
+ // raised as we figure out whether we need to install a security manager\r
+ // and during the actual installation of the security manager. We need\r
+ // to print out these errors. The old error printing behavior assumed\r
+ // that all errors were generated inside NetworkServerControlImpl and\r
+ // were reported there.\r
+ //\r
+ boolean printErrors = true;\r
+ \r
+ try\r
+ {\r
+ server = new NetworkServerControlImpl();\r
+ \r
+ int command = server.parseArgs( args );\r
+\r
+ //\r
+ // In order to run secure-by-default, we install a security manager\r
+ // if one isn't already installed. This feature is described by DERBY-2196.\r
+ //\r
+// if ( needsSecurityManager( server, command ) )\r
+// {\r
+// verifySecurityState( server );\r
+// installSecurityManager( server );\r
+// }\r
+\r
+ //\r
+ // From this point on, NetworkServerControlImpl is responsible for\r
+ // printing errors.\r
+ //\r
+ printErrors = false;\r
+ server.executeWork( command );\r
+ }\r
+ catch (Exception e)\r
+ {\r
+ //if there was an error, exit(1)\r
+ if ((e.getMessage() == null) ||\r
+ !e.getMessage().equals(NetworkServerControlImpl.UNEXPECTED_ERR) ||\r
+ printErrors\r
+ )\r
+ {\r
+ if (server != null)\r
+ server.consoleExceptionPrint(e);\r
+ else\r
+ e.printStackTrace(); // default output stream is System.out\r
+ }\r
+ // else, we've already printed a trace, so just exit.\r
+ System.exit(1);\r
+ }\r
+ System.exit(0);\r
+ \r
+ }\r
+\r
+ /**********************************************************************\r
+ * Public NetworkServerControl commands\r
+ * The server commands throw exceptions for errors, so that users can handle\r
+ * them themselves.\r
+ ************************************************************************\r
+ **/\r
+\r
+ /** Start a Network Server\r
+ * This method will launch a separate thread and start Network Server.\r
+ * This method may return before the server is ready to accept connections.\r
+ * Use the ping method to verify that the server has started.\r
+ *\r
+ * <P>\r
+ * Note: an alternate method to starting the Network Server with the API,\r
+ * is to use the derby.drda.startNetworkServer property in \r
+ * derby.properties.\r
+ * \r
+ * \r
+ * @param consoleWriter PrintWriter to which server console will be \r
+ * output. Null will disable console output. \r
+ *\r
+ * @exception Exception if there is an error starting the server.\r
+ *\r
+ * @see #shutdown\r
+ */\r
+ public void start(PrintWriter consoleWriter) throws Exception\r
+ {\r
+ serverImpl.start(consoleWriter);\r
+ }\r
+\r
+ \r
+\r
+ /**\r
+ * Shutdown a Network Server.\r
+ * Shuts down the Network Server listening on the port and InetAddress\r
+ * specified in the constructor for this NetworkServerControl object.\r
+ *\r
+ * @exception Exception throws an exception if an error occurs\r
+ */\r
+ public void shutdown()\r
+ throws Exception\r
+ {\r
+ serverImpl.shutdown();\r
+ }\r
+\r
+ /**\r
+ * Check if Network Server is started\r
+ * Excecutes and returns without error if the server has started\r
+ *\r
+ * @exception Exception throws an exception if an error occurs\r
+ */\r
+ public void ping() throws Exception\r
+ {\r
+ serverImpl.ping();\r
+ }\r
+\r
+ /**\r
+ * Turn tracing on or off for the specified connection \r
+ * on the Network Server.\r
+ *\r
+ * @param on true to turn tracing on, false to turn tracing off.\r
+ *\r
+ * @exception Exception throws an exception if an error occurs\r
+ */\r
+ public void trace(boolean on)\r
+ throws Exception\r
+ {\r
+ serverImpl.trace(on);\r
+ }\r
+\r
+\r
+ /**\r
+ * Turn tracing on or off for all connections on the Network Server.\r
+ *\r
+ * @param connNum connection number. Note: Connection numbers will print\r
+ * in the Derby error log if logConnections is on\r
+ * @param on true to turn tracing on, false to turn tracing off.\r
+ *\r
+ * @exception Exception throws an exception if an error occurs\r
+ */\r
+ public void trace(int connNum, boolean on)\r
+ throws Exception\r
+ {\r
+ serverImpl.trace(connNum, on);\r
+ }\r
+\r
+ /**\r
+ * Turn logging connections on or off. When logging is turned on a message is\r
+ * written to the Derby error log each time a connection \r
+ * is made.\r
+ *\r
+ * @param on true to turn on, false to turn off\r
+ *\r
+ * @exception Exception throws an exception if an error occurs\r
+ */\r
+ public void logConnections(boolean on)\r
+ throws Exception\r
+ {\r
+ serverImpl.logConnections(on);\r
+ }\r
+\r
+ /**\r
+ * Set directory for trace files. The directory must be on the machine\r
+ * where the server is running.\r
+ *\r
+ * @param traceDirectory directory for trace files on machine \r
+ * where server is running\r
+ *\r
+ * @exception Exception throws an exception if an error occurs\r
+ */\r
+ public void setTraceDirectory(String traceDirectory)\r
+ throws Exception\r
+ {\r
+ serverImpl.sendSetTraceDirectory(traceDirectory);\r
+ }\r
+\r
+ /**\r
+ * Return classpath and version information about the running \r
+ * Network Server. \r
+ *\r
+ * @return sysinfo output\r
+ * @exception Exception throws an exception if an error occurs\r
+ */\r
+ public String getSysinfo()\r
+ throws Exception\r
+ {\r
+ \r
+ return serverImpl.sysinfo();\r
+ }\r
+\r
+ /**\r
+ * Return detailed session runtime information about sessions,\r
+ * prepared statements, and memory usage for the running Network Server. \r
+ *\r
+ * @return run time information\r
+ * @exception Exception throws an exception if an error occurs\r
+ */\r
+ public String getRuntimeInfo()\r
+ throws Exception\r
+ {\r
+ return serverImpl.runtimeInfo();\r
+ }\r
+\r
+\r
+ /**\r
+ * Set Network Server maxthread parameter. This is the maximum number \r
+ * of threads that will be used for JDBC client connections. setTimeSlice\r
+ * should also be set so that clients will yield appropriately.\r
+ *\r
+ * @param max maximum number of connection threads.\r
+ * If <= 0, connection threads will be created when \r
+ * there are no free connection threads.\r
+ *\r
+ * @exception Exception throws an exception if an error occurs\r
+ * @see #setTimeSlice\r
+ */\r
+ public void setMaxThreads(int max) throws Exception\r
+ {\r
+ serverImpl.netSetMaxThreads(max);\r
+ }\r
+\r
+\r
+ /** Returns the current maxThreads setting for the running Network Server\r
+ * \r
+ * @return maxThreads setting \r
+ * @exception Exception throws an exception if an error occurs\r
+ * @see #setMaxThreads\r
+ */\r
+ public int getMaxThreads() throws Exception\r
+ {\r
+ String val =serverImpl.getCurrentProperties().getProperty(Property.DRDA_PROP_MAXTHREADS);\r
+\r
+ \r
+ return Integer.parseInt(val);\r
+ }\r
+\r
+ /**\r
+ * Set Network Server connection time slice parameter. \r
+ * This should be set and is only relevant if setMaxThreads > 0.\r
+ *\r
+ * @param timeslice number of milliseconds given to each session before yielding to \r
+ * another session, if <=0, never yield. \r
+ *\r
+ * @exception Exception throws an exception if an error occurs\r
+ * @see #setMaxThreads\r
+ */\r
+ public void setTimeSlice(int timeslice) throws Exception\r
+ {\r
+ serverImpl.netSetTimeSlice(timeslice);\r
+ }\r
+\r
+ /** Return the current timeSlice setting for the running Network Server\r
+ * \r
+ * @return timeSlice setting\r
+ * @exception Exception throws an exception if an error occurs\r
+ * @see #setTimeSlice\r
+ */\r
+ public int getTimeSlice() throws Exception\r
+ {\r
+ String val =\r
+ serverImpl.getCurrentProperties().getProperty(Property.DRDA_PROP_TIMESLICE);\r
+ return Integer.parseInt(val);\r
+ }\r
+\r
+\r
+\r
+ /**\r
+ * Get current Network server properties\r
+ *\r
+ * @return Properties object containing Network server properties\r
+ * @exception Exception throws an exception if an error occurs\r
+ */\r
+ public Properties getCurrentProperties() throws Exception\r
+ {\r
+ return serverImpl.getCurrentProperties();\r
+ }\r
+\r
+ /** Protected methods ***/\r
+\r
+ /***\r
+ * set the client locale. Used by servlet for localization\r
+ * @param locale Locale to use\r
+ *\r
+ */\r
+ \r
+ protected void setClientLocale(String locale)\r
+ {\r
+ serverImpl.clientLocale = locale;\r
+ }\r
+\r
+ /**\r
+ * Return true if we need to install a Security Manager. All of the\r
+ * following must apply. See DERBY-2196.\r
+ *\r
+ * <ul>\r
+ * <li>The VM was booted with NetworkServerContro.main() as the\r
+ * entry point. This is handled by the fact that this method is only called\r
+ * by main().</li>\r
+ * <li>The VM isn't already running a SecurityManager.</li>\r
+ * <li>The command must be "start".</li>\r
+ * <li>The customer didn't specify the -noSecurityManager flag on the startup command\r
+ * line.</li>\r
+ * </ul>\r
+ */\r
+ private static boolean needsSecurityManager( NetworkServerControlImpl server, int command )\r
+ throws Exception\r
+ {\r
+ return\r
+ (\r
+ (System.getSecurityManager() == null) &&\r
+ (command == NetworkServerControlImpl.COMMAND_START) &&\r
+ (!server.runningUnsecure())\r
+ );\r
+ }\r
+ \r
+ /**\r
+ * Verify that all prerequisites are met before bringing up a security\r
+ * manager. See DERBY-2196. If prerequisites aren't met, raise an\r
+ * exception which explains how to get up and running. At one point, we were going to require\r
+ * that authentication be enabled before bringing up a security manager.\r
+ * This, however, gave rise to incompatibilities. See DERBY-2757.\r
+ *\r
+ * Currently, this method is a nop.\r
+ */\r
+ private static void verifySecurityState( NetworkServerControlImpl server )\r
+ throws Exception\r
+ {\r
+ }\r
+\r
+ \r
+ /**\r
+ * Install a SecurityManager governed by the Basic startup policy. See DERBY-2196.\r
+ */\r
+ private static void installSecurityManager( NetworkServerControlImpl server )\r
+ throws Exception\r
+ {\r
+ //\r
+ // The Basic policy refers to some properties. Make sure they are set.\r
+ //\r
+ if ( PropertyUtil.getSystemProperty( Property.SYSTEM_HOME_PROPERTY ) == null )\r
+ { System.setProperty( Property.SYSTEM_HOME_PROPERTY, PropertyUtil.getSystemProperty( "user.dir" ) ); }\r
+\r
+ //\r
+ // Make sure the following property is set so that it can be substituted into the\r
+ // policy file. That will let us grant write permission on the server's\r
+ // trace file.\r
+ //\r
+ if ( PropertyUtil.getSystemProperty( Property.DRDA_PROP_TRACEDIRECTORY ) == null )\r
+ { System.setProperty( Property.DRDA_PROP_TRACEDIRECTORY, PropertyUtil.getSystemProperty( Property.SYSTEM_HOME_PROPERTY ) ); }\r
+\r
+ //\r
+ // Forcibly set the following property so that it will be correctly\r
+ // substituted into the default policy file. This is the hostname for\r
+ // SocketPermissions. This is an internal property which customers\r
+ // may not override.\r
+ //\r
+ System.setProperty( Property.DERBY_SECURITY_HOST, getHostNameForSocketPermission( server ) );\r
+\r
+ //\r
+ // Forcibly set the following property. This is the parameter in\r
+ // the Basic policy which points at the directory where the embedded and\r
+ // network codesources. Do not let the customer\r
+ // override this\r
+ //\r
+ String derbyInstallURL = getCodeSourcePrefix( server );\r
+\r
+ System.setProperty( Property.DERBY_INSTALL_URL, derbyInstallURL );\r
+ \r
+ //\r
+ // Now install a SecurityManager, using the Basic policy file.\r
+ //\r
+ String policyFileURL = getPolicyFileURL();\r
+\r
+ System.setProperty( POLICY_FILE_PROPERTY, policyFileURL );\r
+ \r
+ SecurityManager securityManager = new SecurityManager();\r
+\r
+ System.setSecurityManager( securityManager );\r
+\r
+ //\r
+ // Report success.\r
+ //\r
+ String successMessage = server.localizeMessage( "DRDA_SecurityInstalled.I", null );\r
+ \r
+ server.consoleMessage( successMessage );\r
+ }\r
+\r
+ /**\r
+ * Get the hostname as a value suitable for substituting into the\r
+ * default server policy file. The special\r
+ * wildcard valuse "0.0.0.0" and "::" are forced to be "*" since that is the wildcard\r
+ * hostname understood by SocketPermission. SocketPermission does\r
+ * not understand the "0.0.0.0" and "::" wildcards. IPV6 addresses are\r
+ * enclosed in square brackets. This logic arose from two JIRAs:\r
+ * DERBY-2811 and DERBY-2874.\r
+ */\r
+ private static String getHostNameForSocketPermission( NetworkServerControlImpl server )\r
+ throws Exception\r
+ {\r
+ //\r
+ // By now, server.getPropertyInfo() has been called, followed by\r
+ // server.parseArgs(). So the server knows its hostname.\r
+ //\r
+ String hostname = server.getHost();\r
+ \r
+ if (\r
+ hostnamesEqual( DERBY_HOSTNAME_WILDCARD, hostname ) ||\r
+ IPV6_HOSTNAME_WILDCARD.equals( hostname ) \r
+ )\r
+ { hostname = SOCKET_PERMISSION_HOSTNAME_WILDCARD; }\r
+ else if ( isIPV6Address( hostname ) )\r
+ { hostname = '[' + hostname + "]:0-"; }\r
+\r
+ return hostname;\r
+ }\r
+\r
+ // return true if the two hostnames are equivalent\r
+ private static boolean hostnamesEqual( String left, String right )\r
+ {\r
+ try {\r
+ InetAddress leftAddress = InetAddress.getByName( left );\r
+ InetAddress rightAddress = InetAddress.getByName( right );\r
+\r
+ return leftAddress.equals( rightAddress );\r
+ \r
+ } catch (Exception e) { return false; }\r
+ }\r
+ \r
+ // return true if the host address is an IPV6 address\r
+ private static boolean isIPV6Address( String hostname )\r
+ {\r
+ if ( hostname == null ) { return false; }\r
+\r
+ //\r
+ // First make sure that the address is composed entirely\r
+ // of hex digits and colons.\r
+ //\r
+ int count = hostname.length();\r
+\r
+ for ( int i = 0; i < count; i++ )\r
+ {\r
+ char currentChar = hostname.charAt( i );\r
+\r
+ if ( currentChar == ':' ) { continue; }\r
+ if ( Character.digit( currentChar, 16 ) >= 0 ) { continue; }\r
+\r
+ return false;\r
+ }\r
+\r
+ //\r
+ // OK, now see whether the address is parsed as an IPV6 address.\r
+ //\r
+ \r
+ try {\r
+ InetAddress address = InetAddress.getByName( hostname );\r
+\r
+ return (address instanceof Inet6Address);\r
+ \r
+ } catch (Exception e) { return false; }\r
+ }\r
+\r
+ /**\r
+ *<p>\r
+ * Find the url of the library directory which holds derby.jar and\r
+ * derbynet.jar. The Basic policy assumes that both jar files live in the\r
+ * same directory.\r
+ * </p>\r
+ */\r
+ private static String getCodeSourcePrefix( NetworkServerControlImpl server )\r
+ throws Exception\r
+ {\r
+ String derbyNetURL = NetworkServerControl.class.getProtectionDomain().getCodeSource().getLocation().toExternalForm();\r
+ int idx = derbyNetURL.indexOf( DERBYNET_JAR );\r
+\r
+ //\r
+ // If the customer isn't running against jar files, our Basic policy\r
+ // won't work.\r
+ //\r
+ if ( idx < 0 )\r
+ {\r
+ String errorMessage = server.localizeMessage( "DRDA_MissingNetworkJar.S", null );\r
+\r
+ // this throws an exception and exits this method\r
+ server.consoleError( errorMessage );\r
+ }\r
+\r
+ //\r
+ // Otherwise, we have the directory prefix for our url.\r
+ //\r
+ String directoryPrefix = derbyNetURL.substring( 0, idx );\r
+\r
+ return directoryPrefix;\r
+ }\r
+\r
+ /**\r
+ *<p>\r
+ * Get the URL of the policy file. Typically, this will be some pointer into\r
+ * derbynet.jar.\r
+ * </p>\r
+ */\r
+ private static String getPolicyFileURL()\r
+ throws Exception\r
+ {\r
+ String resourceName =\r
+ NetworkServerControl.class.getPackage().getName().replace( '.', '/' ) +\r
+ '/' +\r
+ POLICY_FILENAME;\r
+ URL resourceURL = NetworkServerControl.class.getClassLoader().getResource( resourceName );\r
+ String stringForm = resourceURL.toExternalForm();\r
+\r
+ return stringForm;\r
+ }\r
+\r
+}\r