You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@mina.apache.org by ed...@apache.org on 2009/04/17 15:23:33 UTC
svn commit: r765989 - in
/mina/trunk/core/src/main/java/org/apache/mina/proxy: ./ handlers/http/
handlers/http/digest/ handlers/http/ntlm/ utils/
Author: edeoliveira
Date: Fri Apr 17 13:23:32 2009
New Revision: 765989
URL: http://svn.apache.org/viewvc?rev=765989&view=rev
Log:
Javadoced these classes
Modified:
mina/trunk/core/src/main/java/org/apache/mina/proxy/AbstractProxyIoHandler.java
mina/trunk/core/src/main/java/org/apache/mina/proxy/AbstractProxyLogicHandler.java
mina/trunk/core/src/main/java/org/apache/mina/proxy/ProxyConnector.java
mina/trunk/core/src/main/java/org/apache/mina/proxy/handlers/http/HttpProxyConstants.java
mina/trunk/core/src/main/java/org/apache/mina/proxy/handlers/http/HttpProxyResponse.java
mina/trunk/core/src/main/java/org/apache/mina/proxy/handlers/http/digest/DigestUtilities.java
mina/trunk/core/src/main/java/org/apache/mina/proxy/handlers/http/ntlm/NTLMUtilities.java
mina/trunk/core/src/main/java/org/apache/mina/proxy/utils/ByteUtilities.java
mina/trunk/core/src/main/java/org/apache/mina/proxy/utils/IoBufferDecoder.java
mina/trunk/core/src/main/java/org/apache/mina/proxy/utils/StringUtilities.java
Modified: mina/trunk/core/src/main/java/org/apache/mina/proxy/AbstractProxyIoHandler.java
URL: http://svn.apache.org/viewvc/mina/trunk/core/src/main/java/org/apache/mina/proxy/AbstractProxyIoHandler.java?rev=765989&r1=765988&r2=765989&view=diff
==============================================================================
--- mina/trunk/core/src/main/java/org/apache/mina/proxy/AbstractProxyIoHandler.java (original)
+++ mina/trunk/core/src/main/java/org/apache/mina/proxy/AbstractProxyIoHandler.java Fri Apr 17 13:23:32 2009
@@ -40,11 +40,15 @@
/**
* Method called only when handshake has completed.
+ *
+ * @param session the io session
*/
public abstract void proxySessionOpened(IoSession session) throws Exception;
/**
* Hooked session opened event.
+ *
+ * @param session the io session
*/
@Override
public final void sessionOpened(IoSession session) throws Exception {
Modified: mina/trunk/core/src/main/java/org/apache/mina/proxy/AbstractProxyLogicHandler.java
URL: http://svn.apache.org/viewvc/mina/trunk/core/src/main/java/org/apache/mina/proxy/AbstractProxyLogicHandler.java?rev=765989&r1=765988&r2=765989&view=diff
==============================================================================
--- mina/trunk/core/src/main/java/org/apache/mina/proxy/AbstractProxyLogicHandler.java (original)
+++ mina/trunk/core/src/main/java/org/apache/mina/proxy/AbstractProxyLogicHandler.java Fri Apr 17 13:23:32 2009
@@ -186,7 +186,10 @@
}
/**
- * Close the session.
+ * Closes the session.
+ *
+ * @param message the error message
+ * @param t the exception which caused the session closing
*/
protected void closeSession(final String message, final Throwable t) {
if (t != null) {
@@ -200,9 +203,9 @@
}
/**
- * Close the session.
+ * Closes the session.
*
- * @param message
+ * @param message the error message
*/
protected void closeSession(final String message) {
closeSession(message, null);
Modified: mina/trunk/core/src/main/java/org/apache/mina/proxy/ProxyConnector.java
URL: http://svn.apache.org/viewvc/mina/trunk/core/src/main/java/org/apache/mina/proxy/ProxyConnector.java?rev=765989&r1=765988&r2=765989&view=diff
==============================================================================
--- mina/trunk/core/src/main/java/org/apache/mina/proxy/ProxyConnector.java (original)
+++ mina/trunk/core/src/main/java/org/apache/mina/proxy/ProxyConnector.java Fri Apr 17 13:23:32 2009
@@ -45,12 +45,13 @@
import org.apache.mina.transport.socket.SocketSessionConfig;
/**
- * ProxyConnector.java - Decorator for {@link SocketConnector} to provide proxy support, as suggested by MINA list discussions.
+ * ProxyConnector.java - Decorator for {@link SocketConnector} to provide proxy support,
+ * as suggested by MINA list discussions.
* <p>
- * Operates by intercepting connect requests and replacing the endpoint address with the proxy address,
- * then adding a {@link ProxyFilter} as the first {@link IoFilter} which performs any necessary
- * handshaking with the proxy before allowing data to flow normally. During the handshake, any outgoing
- * write requests are buffered.
+ * Operates by intercepting connect requests and replacing the endpoint address with the
+ * proxy address, then adding a {@link ProxyFilter} as the first {@link IoFilter} which
+ * performs any necessary handshaking with the proxy before allowing data to flow
+ * normally. During the handshake, any outgoing write requests are buffered.
*
* @see http://www.nabble.com/Meta-Transport%3A-an-idea-on-implementing-reconnection-and-proxy-td12969001.html
* @see http://issues.apache.org/jira/browse/DIRMINA-415
@@ -94,7 +95,7 @@
/**
* Creates a new proxy connector.
*
- * @param connector Connector used to establish proxy connections.
+ * @param connector Connector used to establish proxy connections.
*/
public ProxyConnector(final SocketConnector connector) {
this(connector, new DefaultSocketSessionConfig(), null);
@@ -108,19 +109,29 @@
super(config, executor);
setConnector(connector);
}
-
+
+ /**
+ * {@inheritDoc}
+ */
@Override
public IoSessionConfig getSessionConfig() {
return connector.getSessionConfig();
}
+ /**
+ * Returns the {@link ProxyIoSession} linked with this connector.
+ */
public ProxyIoSession getProxyIoSession() {
return proxyIoSession;
}
+ /**
+ * Sets the proxy session object of this connector.
+ * @param proxyIoSession the configuration of this connector.
+ */
public void setProxyIoSession(ProxyIoSession proxyIoSession) {
if (proxyIoSession == null) {
- throw new NullPointerException("proxySession cannot be null");
+ throw new NullPointerException("proxySession object cannot be null");
}
if (proxyIoSession.getProxyAddress() == null) {
@@ -135,9 +146,11 @@
/**
* Connects to the specified <code>address</code>. If communication starts
- * successfully, events are fired to the specified
- * <code>handler</code>.
+ * successfully, events are fired to the connector's <code>handler</code>.
*
+ * @param remoteAddress the remote address to connect to
+ * @param localAddress the local address
+ * @param sessionInitializer the session initializer
* @return {@link ConnectFuture} that will tell the result of the connection attempt
*/
@SuppressWarnings("unchecked")
@@ -162,6 +175,11 @@
.getProxyAddress(), new ProxyIoSessionInitializer(
sessionInitializer, proxyIoSession));
+ // If proxy does not use reconnection like socks the connector's
+ // future is returned. If we're in the middle of a reconnection
+ // then we send back the connector's future which is only used
+ // internally while <code>future</code> will be used to notify
+ // the user of the connection state.
if (proxyIoSession.getRequest() instanceof SocksProxyRequest
|| proxyIoSession.isReconnectionNeeded()) {
return conFuture;
@@ -170,10 +188,19 @@
}
}
+ /**
+ * Cancels the real connection when reconnection is in use.
+ */
public void cancelConnectFuture() {
future.cancel();
}
+ /**
+ * Fires the connection event on the real future to notify the client.
+ *
+ * @param session the current session
+ * @return the future holding the connected session
+ */
protected ConnectFuture fireConnected(final IoSession session) {
future.setSession(session);
return future;
@@ -188,34 +215,30 @@
}
/**
- * Set the {@link SocketConnector} to be used for connections
+ * Sets the {@link SocketConnector} to be used for connections
* to the proxy server.
+ *
+ * @param connector the connector to use
*/
- public final void setConnector(final SocketConnector newConnector) {
- if (newConnector == null) {
+ private final void setConnector(final SocketConnector connector) {
+ if (connector == null) {
throw new NullPointerException("connector cannot be null");
}
- SocketConnector oldConnector = this.connector;
-
- // Remove the ProxyFilter from the old filter chain builder
- if (oldConnector != null) {
- oldConnector.getFilterChain().remove(ProxyFilter.class.getName());
- }
-
- this.connector = newConnector;
+ this.connector = connector;
+ String className = ProxyFilter.class.getName();
- // Insert the ProxyFilter as the first filter in the filter chain builder
- if (newConnector.getFilterChain().contains(ProxyFilter.class.getName())) {
- newConnector.getFilterChain().remove(ProxyFilter.class.getName());
+ // Removes an old ProxyFilter instance from the chain
+ if (connector.getFilterChain().contains(className)) {
+ connector.getFilterChain().remove(className);
}
- newConnector.getFilterChain().addFirst(ProxyFilter.class.getName(),
- proxyFilter);
+ // Insert the ProxyFilter as the first filter in the filter chain builder
+ connector.getFilterChain().addFirst(className, proxyFilter);
}
- /* (non-Javadoc)
- * @see org.apache.mina.common.AbstractIoService#dispose0()
+ /**
+ * {@inheritDoc}
*/
@Override
protected IoFuture dispose0() throws Exception {
@@ -225,8 +248,8 @@
return null;
}
- /* (non-Javadoc)
- * @see org.apache.mina.common.IoService#getTransportMetadata()
+ /**
+ * {@inheritDoc}
*/
public TransportMetadata getTransportMetadata() {
return METADATA;
Modified: mina/trunk/core/src/main/java/org/apache/mina/proxy/handlers/http/HttpProxyConstants.java
URL: http://svn.apache.org/viewvc/mina/trunk/core/src/main/java/org/apache/mina/proxy/handlers/http/HttpProxyConstants.java?rev=765989&r1=765988&r2=765989&view=diff
==============================================================================
--- mina/trunk/core/src/main/java/org/apache/mina/proxy/handlers/http/HttpProxyConstants.java (original)
+++ mina/trunk/core/src/main/java/org/apache/mina/proxy/handlers/http/HttpProxyConstants.java Fri Apr 17 13:23:32 2009
@@ -27,25 +27,62 @@
* @since MINA 2.0.0-M3
*/
public class HttpProxyConstants {
- public final static String CONNECT = "CONNECT";
+ /**
+ * The HTTP CONNECT verb.
+ */
+ public final static String CONNECT = "CONNECT";
+
+ /**
+ * The HTTP GET verb.
+ */
public final static String GET = "GET";
+ /**
+ * The HTTP PUT verb.
+ */
public final static String PUT = "PUT";
+ /**
+ * The HTTP 1.0 protocol version string.
+ */
public final static String HTTP_1_0 = "HTTP/1.0";
+ /**
+ * The HTTP 1.1 protocol version string.
+ */
public final static String HTTP_1_1 = "HTTP/1.1";
+ /**
+ * The CRLF character sequence used in HTTP protocol to end each line.
+ */
public final static String CRLF = "\r\n";
+ /**
+ * The default keep-alive timeout we set to make proxy
+ * connection persistent. Set to 300 ms.
+ */
public final static String DEFAULT_KEEP_ALIVE_TIME = "300";
+ // ProxyRequest properties
+
+ /**
+ * The username property. Used in auth mechs.
+ */
public final static String USER_PROPERTY = "USER";
+ /**
+ * The password property. Used in auth mechs.
+ */
public final static String PWD_PROPERTY = "PWD";
+ /**
+ * The domain name property. Used in auth mechs.
+ */
public final static String DOMAIN_PROPERTY = "DOMAIN";
+ /**
+ * The workstation name property. Used in auth mechs.
+ */
public final static String WORKSTATION_PROPERTY = "WORKSTATION";
}
\ No newline at end of file
Modified: mina/trunk/core/src/main/java/org/apache/mina/proxy/handlers/http/HttpProxyResponse.java
URL: http://svn.apache.org/viewvc/mina/trunk/core/src/main/java/org/apache/mina/proxy/handlers/http/HttpProxyResponse.java?rev=765989&r1=765988&r2=765989&view=diff
==============================================================================
--- mina/trunk/core/src/main/java/org/apache/mina/proxy/handlers/http/HttpProxyResponse.java (original)
+++ mina/trunk/core/src/main/java/org/apache/mina/proxy/handlers/http/HttpProxyResponse.java Fri Apr 17 13:23:32 2009
@@ -30,21 +30,44 @@
* @since MINA 2.0.0-M3
*/
public class HttpProxyResponse {
+ /**
+ * The HTTP response protocol version.
+ */
public final String httpVersion;
+ /**
+ * The HTTP response status line.
+ */
public final String statusLine;
+ /**
+ * The HTTP response status code;
+ */
public final int statusCode;
+ /**
+ * The HTTP response headers.
+ */
public final Map<String, List<String>> headers;
+ /**
+ * The HTTP response body.
+ */
public String body;
+ /**
+ * Constructor of an HTTP proxy response.
+ *
+ * @param httpVersion the protocol version
+ * @param statusLine the response status line
+ * @param headers the response headers
+ */
protected HttpProxyResponse(final String httpVersion,
final String statusLine, final Map<String, List<String>> headers) {
this.httpVersion = httpVersion;
this.statusLine = statusLine;
+ // parses the status code from the status line
this.statusCode = statusLine.charAt(0) == ' ' ? Integer
.parseInt(statusLine.substring(1, 4)) : Integer
.parseInt(statusLine.substring(0, 3));
@@ -53,42 +76,42 @@
}
/**
- * The HTTP version.
+ * Returns the HTTP response protocol version.
*/
public final String getHttpVersion() {
return httpVersion;
}
/**
- * The HTTP status code.
+ * Returns the HTTP response status code.
*/
public final int getStatusCode() {
return statusCode;
}
/**
- * The HTTP status line.
+ * Returns the HTTP response status line.
*/
public final String getStatusLine() {
return statusLine;
}
/**
- * The HTTP entity body.
+ * Returns the HTTP response body.
*/
public String getBody() {
return body;
}
/**
- * Sets the HTTP entity body.
+ * Sets the HTTP response body.
*/
public void setBody(String body) {
this.body = body;
}
/**
- * HTTP headers.
+ * Returns the HTTP response headers.
*/
public final Map<String, List<String>> getHeaders() {
return headers;
Modified: mina/trunk/core/src/main/java/org/apache/mina/proxy/handlers/http/digest/DigestUtilities.java
URL: http://svn.apache.org/viewvc/mina/trunk/core/src/main/java/org/apache/mina/proxy/handlers/http/digest/DigestUtilities.java?rev=765989&r1=765988&r2=765989&view=diff
==============================================================================
--- mina/trunk/core/src/main/java/org/apache/mina/proxy/handlers/http/digest/DigestUtilities.java (original)
+++ mina/trunk/core/src/main/java/org/apache/mina/proxy/handlers/http/digest/DigestUtilities.java Fri Apr 17 13:23:32 2009
@@ -54,11 +54,21 @@
}
}
+ /**
+ * The supported qualities of protections.
+ */
public final static String[] SUPPORTED_QOPS = new String[] { "auth",
"auth-int" };
/**
* Computes the response to the DIGEST challenge.
+ *
+ * @param session the current session
+ * @param map the map holding the directives sent by the proxy
+ * @param method the HTTP verb
+ * @param pwd the password
+ * @param charsetName the name of the charset used for the challenge
+ * @param body the html body to be hashed for integrity calculations
*/
public static String computeResponseValue(IoSession session,
HashMap<String, String> map, String method, String pwd,
Modified: mina/trunk/core/src/main/java/org/apache/mina/proxy/handlers/http/ntlm/NTLMUtilities.java
URL: http://svn.apache.org/viewvc/mina/trunk/core/src/main/java/org/apache/mina/proxy/handlers/http/ntlm/NTLMUtilities.java?rev=765989&r1=765988&r2=765989&view=diff
==============================================================================
--- mina/trunk/core/src/main/java/org/apache/mina/proxy/handlers/http/ntlm/NTLMUtilities.java (original)
+++ mina/trunk/core/src/main/java/org/apache/mina/proxy/handlers/http/ntlm/NTLMUtilities.java Fri Apr 17 13:23:32 2009
@@ -49,15 +49,18 @@
/**
* Writes a security buffer to the given array <code>b</code> at offset
- * <code>offset</code>.
+ * <code>offset</code>. A security buffer defines a pointer to an area
+ * in the data that defines some data with a variable length. This allows
+ * to have a semi-fixed length header thus making a little bit easier
+ * the decoding process in the NTLM protocol.
*
* @param length the length of the security buffer
* @param allocated the allocated space for the security buffer (should be
* greater or equal to <code>length</code>
- * @param bufferOffset the offset since the beginning of the <code>b</code>
- * buffer where the buffer iswritten
+ * @param bufferOffset the offset from the main array where the currently
+ * defined security buffer will be written
* @param b the buffer in which we write the security buffer
- * @param offset the offset at which to write to the buffer
+ * @param offset the offset at which to write to the b buffer
*/
public final static void writeSecurityBuffer(short length, short allocated,
int bufferOffset, byte[] b, int offset) {
@@ -66,6 +69,17 @@
ByteUtilities.writeInt(bufferOffset, b, offset + 4);
}
+ /**
+ * Writes the Windows OS version passed in as three byte values
+ * (majorVersion.minorVersion.buildNumber) to the given byte array
+ * at <code>offset</code>.
+ *
+ * @param majorVersion the major version number
+ * @param minorVersion the minor version number
+ * @param buildNumber the build number
+ * @param b the target byte array
+ * @param offset the offset at which to write in the array
+ */
public final static void writeOSVersion(byte majorVersion,
byte minorVersion, short buildNumber, byte[] b, int offset) {
b[offset] = majorVersion;
@@ -79,7 +93,11 @@
}
/**
- * Tries to return a valid Os version on windows systems.
+ * Tries to return a valid OS version on Windows systems. If it fails to
+ * do so or if we're running on another OS then a fake Windows XP OS
+ * version is returned because the protocol uses it.
+ *
+ * @return a NTLM OS version byte buffer
*/
public final static byte[] getOsVersion() {
String os = System.getProperty("os.name");
@@ -98,6 +116,10 @@
line = reader.readLine();
} while ((line != null) && (line.length() != 0));
+ reader.close();
+
+ // The command line should return a response like :
+ // Microsoft Windows XP [version 5.1.2600]
int pos = line.toLowerCase().indexOf("version");
if (pos == -1) {
@@ -137,7 +159,7 @@
* <code>NTLMConstants.DEFAULT_CONSTANTS</code> is used
* @param osVersion the os version of the client, if null then
* <code>NTLMConstants.DEFAULT_OS_VERSION</code> is used
- * @return
+ * @return the type 1 message
*/
public final static byte[] createType1Message(String workStation,
String domain, Integer customFlags, byte[] osVersion) {
@@ -193,14 +215,14 @@
}
/**
- * Write a security buffer and returns the pointer of the position
+ * Writes a security buffer and returns the pointer of the position
* where to write the next security buffer.
*
* @param baos the stream where the security buffer is written
* @param len the length of the security buffer
* @param pointer the position where the security buffer can be written
* @return the position where the next security buffer will be written
- * @throws IOException
+ * @throws IOException if writing to the ByteArrayOutputStream fails
*/
public final static int writeSecurityBufferAndUpdatePointer(
ByteArrayOutputStream baos, short len, int pointer)
@@ -209,12 +231,24 @@
return pointer + len;
}
+ /**
+ * Extracts the NTLM challenge from the type 2 message as an 8 byte array.
+ *
+ * @param msg the type 2 message byte array
+ * @return the challenge
+ */
public final static byte[] extractChallengeFromType2Message(byte[] msg) {
byte[] challenge = new byte[8];
System.arraycopy(msg, 24, challenge, 0, 8);
return challenge;
}
+ /**
+ * Extracts the NTLM flags from the type 2 message.
+ *
+ * @param msg the type 2 message byte array
+ * @return the proxy flags as an int
+ */
public final static int extractFlagsFromType2Message(byte[] msg) {
byte[] flagsBytes = new byte[4];
@@ -224,21 +258,46 @@
return ByteUtilities.makeIntFromByte4(flagsBytes);
}
- public final static String extractTargetNameFromType2Message(byte[] msg,
- Integer msgFlags) throws UnsupportedEncodingException {
- byte[] targetName = null;
-
- // Read security buffer
+ /**
+ * Reads the byte array described by the security buffer stored at the
+ * <code>securityBufferOffset</code> offset.
+ *
+ * @param msg the message where to read the security buffer and it's value
+ * @param securityBufferOffset the offset at which to read the security buffer
+ * @return a new byte array holding the data pointed by the security buffer
+ */
+ public final static byte[] readSecurityBufferTarget(
+ byte[] msg, int securityBufferOffset) {
byte[] securityBuffer = new byte[8];
- System.arraycopy(msg, 12, securityBuffer, 0, 8);
+ System.arraycopy(msg, securityBufferOffset, securityBuffer, 0, 8);
ByteUtilities.changeWordEndianess(securityBuffer, 0, 8);
int length = ByteUtilities.makeIntFromByte2(securityBuffer);
int offset = ByteUtilities.makeIntFromByte4(securityBuffer, 4);
- targetName = new byte[length];
- System.arraycopy(msg, offset, targetName, 0, length);
+ byte[] secBufValue = new byte[length];
+ System.arraycopy(msg, offset, secBufValue, 0, length);
+
+ return secBufValue;
+ }
+
+ /**
+ * Extracts the target name from the type 2 message.
+ *
+ * @param msg the type 2 message byte array
+ * @param msgFlags the flags if null then flags are extracted from the
+ * type 2 message
+ * @return the target name
+ * @throws UnsupportedEncodingException if unable to use the
+ * needed UTF-16LE or ASCII charsets
+ */
+ public final static String extractTargetNameFromType2Message(byte[] msg,
+ Integer msgFlags) throws UnsupportedEncodingException {
+ // Read the security buffer to determine where the target name
+ // is stored and what it's length is
+ byte[] targetName = readSecurityBufferTarget(msg, 12);
+ // now we convert it to a string
int flags = msgFlags == null ? extractFlagsFromType2Message(msg)
: msgFlags;
if (ByteUtilities.isFlagSet(flags, FLAG_NEGOTIATE_UNICODE)) {
@@ -248,31 +307,38 @@
}
}
+ /**
+ * Extracts the target information block from the type 2 message.
+ *
+ * @param msg the type 2 message byte array
+ * @param msgFlags the flags if null then flags are extracted from the
+ * type 2 message
+ * @return the target info
+ */
public final static byte[] extractTargetInfoFromType2Message(byte[] msg,
Integer msgFlags) {
int flags = msgFlags == null ? extractFlagsFromType2Message(msg)
: msgFlags;
- byte[] targetInformationBlock = null;
if (!ByteUtilities.isFlagSet(flags, FLAG_NEGOTIATE_TARGET_INFO))
return null;
int pos = 40; //isFlagSet(flags, FLAG_NEGOTIATE_LOCAL_CALL) ? 40 : 32;
- // Read security buffer
- byte[] securityBuffer = new byte[8];
-
- System.arraycopy(msg, pos, securityBuffer, 0, 8);
- ByteUtilities.changeWordEndianess(securityBuffer, 0, 8);
- int length = ByteUtilities.makeIntFromByte2(securityBuffer);
- int offset = ByteUtilities.makeIntFromByte4(securityBuffer, 4);
-
- targetInformationBlock = new byte[length];
- System.arraycopy(msg, offset, targetInformationBlock, 0, length);
-
- return targetInformationBlock;
+ return readSecurityBufferTarget(msg, pos);
}
+ /**
+ * Prints to the {@link PrintWriter} the target information block extracted
+ * from the type 2 message.
+ *
+ * @param msg the type 2 message
+ * @param msgFlags the flags if null then flags are extracted from the
+ * type 2 message
+ * @param out the output target for the information
+ * @throws UnsupportedEncodingException if unable to use the
+ * needed UTF-16LE or ASCII charsets
+ */
public final static void printTargetInformationBlockFromType2Message(
byte[] msg, Integer msgFlags, PrintWriter out)
throws UnsupportedEncodingException {
@@ -287,21 +353,21 @@
while (infoBlock[pos] != 0) {
out.print("---\nType " + infoBlock[pos] + ": ");
switch (infoBlock[pos]) {
- case 1:
- out.println("Server name");
- break;
- case 2:
- out.println("Domain name");
- break;
- case 3:
- out.println("Fully qualified DNS hostname");
- break;
- case 4:
- out.println("DNS domain name");
- break;
- case 5:
- out.println("Parent DNS domain name");
- break;
+ case 1:
+ out.println("Server name");
+ break;
+ case 2:
+ out.println("Domain name");
+ break;
+ case 3:
+ out.println("Fully qualified DNS hostname");
+ break;
+ case 4:
+ out.println("DNS domain name");
+ break;
+ case 5:
+ out.println("Parent DNS domain name");
+ break;
}
byte[] len = new byte[2];
System.arraycopy(infoBlock, pos + 2, len, 0, 2);
@@ -314,9 +380,7 @@
out.println(new String(infoBlock, pos + 4, length,
"UTF-16LE"));
} else {
- out
- .println(new String(infoBlock, pos + 4, length,
- "ASCII"));
+ out.println(new String(infoBlock, pos + 4, length, "ASCII"));
}
pos += 4 + length;
out.flush();
@@ -325,7 +389,16 @@
}
/**
- * http://davenport.sourceforge.net/ntlm.html#theType3Message
+ * @see http://davenport.sourceforge.net/ntlm.html#theType3Message
+ *
+ * @param user the user name
+ * @param password the user password
+ * @param challenge the challenge response
+ * @param target the target name
+ * @param workstation the client workstation's name
+ * @param serverFlags the flags set by the client
+ * @param osVersion the os version of the client
+ * @return the type 3 message
*/
public final static byte[] createType3Message(String user, String password,
byte[] challenge, String target, String workstation,
@@ -391,7 +464,9 @@
(64) OS Version Structure (Optional) 8 bytes
**/
- baos.write(new byte[] { 0, 0, 0, 0, (byte) 0x9a, 0, 0, 0 }); // Session Key Security Buffer ??!
+ // Session Key Security Buffer ??!
+ baos.write(new byte[] { 0, 0, 0, 0, (byte) 0x9a, 0, 0, 0 });
+
baos.write(ByteUtilities.writeInt(flags));
if (osVersion != null) {
Modified: mina/trunk/core/src/main/java/org/apache/mina/proxy/utils/ByteUtilities.java
URL: http://svn.apache.org/viewvc/mina/trunk/core/src/main/java/org/apache/mina/proxy/utils/ByteUtilities.java?rev=765989&r1=765988&r2=765989&view=diff
==============================================================================
--- mina/trunk/core/src/main/java/org/apache/mina/proxy/utils/ByteUtilities.java (original)
+++ mina/trunk/core/src/main/java/org/apache/mina/proxy/utils/ByteUtilities.java Fri Apr 17 13:23:32 2009
@@ -29,10 +29,16 @@
* @since MINA 2.0.0-M3
*/
public class ByteUtilities {
- /**
- * Returns the integer represented by 4 bytes in network byte order.
- */
- public static int networkByteOrderToInt(byte[] buf, int start, int count) {
+
+ /**
+ * Returns the integer represented by up to 4 bytes in network byte order.
+ *
+ * @param buf the buffer to read the bytes from
+ * @param start
+ * @param count
+ * @return
+ */
+ public static int networkByteOrderToInt(byte[] buf, int start, int count) {
if (count > 4) {
throw new IllegalArgumentException(
"Cannot handle more than 4 bytes");
@@ -48,11 +54,31 @@
return result;
}
- /**
- * Encodes an integer into 4 bytes in network byte order in the buffer
- * supplied.
- */
- public static byte[] intToNetworkByteOrder(int num, byte[] buf, int start,
+ /**
+ * Encodes an integer into up to 4 bytes in network byte order.
+ *
+ * @param num the int to convert to a byte array
+ * @param count the number of reserved bytes for the write operation
+ * @return the resulting byte array
+ */
+ public static byte[] intToNetworkByteOrder(int num, int count) {
+ byte[] buf = new byte[count];
+ intToNetworkByteOrder(num, buf, 0, count);
+
+ return buf;
+ }
+
+ /**
+ * Encodes an integer into up to 4 bytes in network byte order in the
+ * supplied buffer starting at <code>start</code> offset and writing
+ * <code>count</code> bytes.
+ *
+ * @param num the int to convert to a byte array
+ * @param buf the buffer to write the bytes to
+ * @param start the offset from beginning for the write operation
+ * @param count the number of reserved bytes for the write operation
+ */
+ public static void intToNetworkByteOrder(int num, byte[] buf, int start,
int count) {
if (count > 4) {
throw new IllegalArgumentException(
@@ -63,8 +89,6 @@
buf[start + i] = (byte) (num & 0xff);
num >>>= 8;
}
-
- return buf;
}
/**
@@ -81,6 +105,8 @@
* the given array <code>b</code> at offset <code>offset</code>.
*
* @param v the short to write
+ * @param b the byte array to write to
+ * @param offset the offset at which to start writing in the array
*/
public final static byte[] writeShort(short v, byte[] b, int offset) {
b[offset] = (byte) v;
@@ -103,6 +129,8 @@
* the given array <code>b</code> at offset <code>offset</code>.
*
* @param v the int to write
+ * @param b the byte array to write to
+ * @param offset the offset at which to start writing in the array
*/
public final static byte[] writeInt(int v, byte[] b, int offset) {
b[offset] = (byte) v;
@@ -113,6 +141,16 @@
return b;
}
+ /**
+ * Invert the endianness of words (4 bytes) in the given byte array
+ * starting at the given offset and repeating length/4 times.
+ * eg: b0b1b2b3 -> b3b2b1b0
+ *
+ * @param b the byte array
+ * @param offset the offset at which to change word start
+ * @param length the number of bytes on which to operate
+ * (should be a multiple of 4)
+ */
public final static void changeWordEndianess(byte[] b, int offset,
int length) {
byte tmp;
@@ -127,6 +165,16 @@
}
}
+ /**
+ * Invert two bytes in the given byte array starting at the given
+ * offset and repeating the inversion length/2 times.
+ * eg: b0b1 -> b1b0
+ *
+ * @param b the byte array
+ * @param offset the offset at which to change word start
+ * @param length the number of bytes on which to operate
+ * (should be a multiple of 2)
+ */
public final static void changeByteEndianess(byte[] b, int offset,
int length) {
byte tmp;
@@ -138,16 +186,41 @@
}
}
+ /**
+ * Converts an OEM string as defined in NTLM protocol (eg ASCII charset)
+ * to a byte array.
+ *
+ * @param s the string to convert
+ * @return the result byte array
+ * @throws UnsupportedEncodingException if the string is not an OEM string
+ */
public final static byte[] getOEMStringAsByteArray(String s)
throws UnsupportedEncodingException {
return s.getBytes("ASCII");
}
+ /**
+ * Converts an UTF-16LE string as defined in NTLM protocol to a byte array.
+ *
+ * @param s the string to convert
+ * @return the result byte array
+ * @throws UnsupportedEncodingException if the string is not an UTF-16LE string
+ */
public final static byte[] getUTFStringAsByteArray(String s)
throws UnsupportedEncodingException {
return s.getBytes("UTF-16LE");
}
+ /**
+ * Encodes the string to a byte array using UTF-16LE or the ASCII charset
+ * in function of the <code>useUnicode</code> argument.
+ *
+ * @param s the string to encode
+ * @param useUnicode if true then string is encoded to UTF-16LE
+ * otherwise to ASCII
+ * @return the encoded string as a byte array
+ * @throws UnsupportedEncodingException if encoding fails
+ */
public final static byte[] encodeString(String s, boolean useUnicode)
throws UnsupportedEncodingException {
if (useUnicode) {
@@ -157,10 +230,24 @@
}
}
+ /**
+ * Returns a hexadecimal representation of the given byte array.
+ *
+ * @param bytes the array to output to an hex string
+ * @return the hex representation as a string
+ */
public static String asHex(byte[] bytes) {
return asHex(bytes, null);
}
+ /**
+ * Returns a hexadecimal representation of the given byte array.
+ *
+ * @param bytes the array to output to an hex string
+ * @param separator the separator to use between each byte in the output
+ * string. If null no char is inserted between each byte value.
+ * @return the hex representation as a string
+ */
public static String asHex(byte[] bytes, String separator) {
StringBuilder sb = new StringBuilder();
for (int i = 0; i < bytes.length; i++) {
@@ -179,6 +266,12 @@
return sb.toString();
}
+ /**
+ * Converts a hex string representation to a byte array.
+ *
+ * @param hex the string holding the hex values
+ * @return the resulting byte array
+ */
public static byte[] asByteArray(String hex) {
byte[] bts = new byte[hex.length() / 2];
for (int i = 0; i < bts.length; i++) {
@@ -189,25 +282,52 @@
return bts;
}
+ /**
+ * Reads an int from 4 bytes of the given array at offset 0.
+ *
+ * @param b the byte array to read
+ * @param offset the offset at which to start
+ * @return the int value
+ */
public static final int makeIntFromByte4(byte[] b) {
return makeIntFromByte4(b, 0);
}
+ /**
+ * Reads an int from 4 bytes of the given array at the given offset.
+ *
+ * @param b the byte array to read
+ * @param offset the offset at which to start
+ * @return the int value
+ */
public static final int makeIntFromByte4(byte[] b, int offset) {
return b[offset] << 24 | (b[offset + 1] & 0xff) << 16
| (b[offset + 2] & 0xff) << 8 | (b[offset + 3] & 0xff);
}
+ /**
+ * Reads an int from 2 bytes of the given array at offset 0.
+ *
+ * @param b the byte array to read
+ * @return the int value
+ */
public static final int makeIntFromByte2(byte[] b) {
return makeIntFromByte2(b, 0);
}
+ /**
+ * Reads an int from 2 bytes of the given array at the given offset.
+ *
+ * @param b the byte array to read
+ * @param offset the offset at which to start
+ * @return the int value
+ */
public static final int makeIntFromByte2(byte[] b, int offset) {
return (b[offset] & 0xff) << 8 | (b[offset + 1] & 0xff);
}
/**
- * Return true if the flag <code>testFlag</code> is set in the
+ * Returns true if the flag <code>testFlag</code> is set in the
* <code>flags</code> flagset.
*
* @param flagset the flagset to test
Modified: mina/trunk/core/src/main/java/org/apache/mina/proxy/utils/IoBufferDecoder.java
URL: http://svn.apache.org/viewvc/mina/trunk/core/src/main/java/org/apache/mina/proxy/utils/IoBufferDecoder.java?rev=765989&r1=765988&r2=765989&view=diff
==============================================================================
--- mina/trunk/core/src/main/java/org/apache/mina/proxy/utils/IoBufferDecoder.java (original)
+++ mina/trunk/core/src/main/java/org/apache/mina/proxy/utils/IoBufferDecoder.java Fri Apr 17 13:23:32 2009
@@ -24,7 +24,8 @@
import org.apache.mina.filter.codec.textline.LineDelimiter;
/**
- * IoBufferDecoder.java - Handles an {@link IoBuffer} decoder which supports two methods :
+ * IoBufferDecoder.java - Handles an {@link IoBuffer} decoder which supports
+ * two methods :
* - dynamic delimiter decoding
* - fixed length content reading
*
@@ -34,17 +35,36 @@
*/
public class IoBufferDecoder {
+ /**
+ * The class holding the decoding context.
+ */
public class DecodingContext {
+ /**
+ * The buffered data.
+ */
private IoBuffer decodedBuffer;
+ /**
+ * The delimiter in use. Set if delimiter mode is in use.
+ */
private IoBuffer delimiter;
- private int contentLength = -1;
-
+ /**
+ * The currently matched bytes of the delimiter.
+ */
private int matchCount = 0;
+
+ /**
+ * Holds the current content length of decoded data if in
+ * content-length mode.
+ */
+ private int contentLength = -1;
- public void clean() {
+ /**
+ * Resets the decoding state.
+ */
+ public void reset() {
contentLength = -1;
matchCount = 0;
decodedBuffer = null;
@@ -83,11 +103,16 @@
}
}
+ /**
+ * The decoding context.
+ */
private DecodingContext ctx = new DecodingContext();
/**
* Creates a new instance that uses specified <tt>delimiter</tt> byte array as a
* message delimiter.
+ *
+ * @param delimiter an array of characters which delimits messages
*/
public IoBufferDecoder(byte[] delimiter) {
setDelimiter(delimiter, true);
@@ -95,6 +120,8 @@
/**
* Creates a new instance that will read messages of <tt>contentLength</tt> bytes.
+ *
+ * @param contentLength the exact length to read
*/
public IoBufferDecoder(int contentLength) {
setContentLength(contentLength, false);
@@ -102,9 +129,12 @@
/**
* Sets the the length of the content line to be decoded.
- * When set, it overrides the dynamic delimiter setting. The default value is <tt>-1</tt>.
- * Content length method will be used for decoding on the next decodeOnce call.
- * Delimiter matching is reset only if <tt>resetMatchCount</tt> is true.
+ * When set, it overrides the dynamic delimiter setting and content length
+ * method will be used for decoding on the next decodeOnce call.
+ * The default value is <tt>-1</tt>.
+ *
+ * @param contentLength the content length to match
+ * @param resetMatchCount delimiter matching is reset if true
*/
public void setContentLength(int contentLength, boolean resetMatchCount) {
if (contentLength <= 0) {
@@ -124,7 +154,10 @@
* delimiter. Delimiter matching is reset only if <tt>resetMatchCount</tt> is true but
* decoding will continue from current position.
*
- * NB : Delimiter {@link LineDelimiter#AUTO} is not allowed.
+ * NB : Delimiter {@link LineDelimiter#AUTO} is not allowed.
+ *
+ * @param delim the new delimiter as a byte array
+ * @param resetMatchCount delimiter matching is reset if true
*/
public void setDelimiter(byte[] delim, boolean resetMatchCount) {
if (delim == null) {
@@ -148,6 +181,8 @@
* is set then it tries to retrieve <code>contentLength</code> bytes from the buffer
* otherwise it will scan the buffer to find the data <code>delimiter</code> and return
* all the data and the trailing delimiter.
+ *
+ * @param in the data to decode
*/
public IoBuffer decodeFully(IoBuffer in) {
int contentLength = ctx.getContentLength();
@@ -162,6 +197,7 @@
true);
}
+ // If not enough data to complete the decoding
if (in.remaining() < contentLength) {
int readBytes = in.remaining();
decodedBuffer.put(in);
@@ -175,7 +211,7 @@
decodedBuffer.put(in);
decodedBuffer.flip();
in.limit(oldLimit);
- ctx.clean();
+ ctx.reset();
return decodedBuffer;
}
@@ -206,7 +242,7 @@
decodedBuffer.flip();
in.limit(oldLimit);
- ctx.clean();
+ ctx.reset();
return decodedBuffer;
}
Modified: mina/trunk/core/src/main/java/org/apache/mina/proxy/utils/StringUtilities.java
URL: http://svn.apache.org/viewvc/mina/trunk/core/src/main/java/org/apache/mina/proxy/utils/StringUtilities.java?rev=765989&r1=765988&r2=765989&view=diff
==============================================================================
--- mina/trunk/core/src/main/java/org/apache/mina/proxy/utils/StringUtilities.java (original)
+++ mina/trunk/core/src/main/java/org/apache/mina/proxy/utils/StringUtilities.java Fri Apr 17 13:23:32 2009
@@ -38,11 +38,19 @@
*/
public class StringUtilities {
- /**
- * Returns the value of a directive from the map. If mandatory is true and the value is null,
- * then it throws a {@link AuthenticationException}.
- */
- public static String getDirectiveValue(
+ /**
+ * A directive is a parameter of the digest authentication process.
+ * Returns the value of a directive from the map. If mandatory is true and the
+ * value is null, then it throws an {@link AuthenticationException}.
+ *
+ * @param directivesMap the directive's map
+ * @param directive the name of the directive we want to retrieve
+ * @param mandatory is the directive mandatory
+ * @return the mandatory value as a String
+ * @throws AuthenticationException if mandatory is true and if
+ * directivesMap.get(directive) == null
+ */
+ public static String getDirectiveValue(
HashMap<String, String> directivesMap, String directive,
boolean mandatory) throws AuthenticationException {
String value = directivesMap.get(directive);
@@ -58,22 +66,32 @@
return value;
}
- /**
+ /**
* Copy the directive to the {@link StringBuilder} if not null.
- */
- public static String copyDirective(HashMap<String, String> directives,
+ * (A directive is a parameter of the digest authentication process.)
+ *
+ * @param directives the directives map
+ * @param sb the output buffer
+ * @param directive the directive name to look for
+ */
+ public static void copyDirective(HashMap<String, String> directives,
StringBuilder sb, String directive) {
String directiveValue = directives.get(directive);
if (directiveValue != null) {
sb.append(directive).append(" = \"").append(directiveValue).append(
"\", ");
}
-
- return directiveValue;
}
/**
- * Copy the directive to the from src to dst if not null.
+ * Copy the directive from the source map to the destination map, if it's
+ * value isn't null.
+ * (A directive is a parameter of the digest authentication process.)
+ *
+ * @param src the source map
+ * @param dst the destination map
+ * @param directive the directive name
+ * @return the value of the copied directive
*/
public static String copyDirective(HashMap<String, String> src,
HashMap<String, String> dst, String directive) {
@@ -86,8 +104,8 @@
}
/**
- * Parses digest-challenge string, extracting each token
- * and value(s)
+ * Parses digest-challenge string, extracting each token and value(s). Each token
+ * is a directive.
*
* @param buf A non-null digest-challenge string.
* @throws UnsupportedEncodingException
@@ -249,6 +267,10 @@
/**
* Skip all linear white spaces
+ *
+ * @param buf the buf which is being scanned for lws
+ * @param start the offset to start at
+ * @return the next position in buf which isn't a lws character
*/
private static int skipLws(byte[] buf, int start) {
int i;
@@ -279,6 +301,14 @@
}
}
+ /**
+ * Returns the value of the named header. If it has multiple values
+ * then an {@link IllegalArgumentException} is thrown
+ *
+ * @param headers the http headers map
+ * @param key the key of the header
+ * @return the value of the http header
+ */
public static String getSingleValuedHeader(
Map<String, List<String>> headers, String key) {
List<String> values = headers.get(key);
@@ -295,6 +325,16 @@
}
}
+ /**
+ * Adds an header to the provided map of headers.
+ *
+ * @param headers the http headers map
+ * @param key the name of the new header to add
+ * @param value the value of the added header
+ * @param singleValued if true and the map already contains one value
+ * then it is replaced by the new value. Otherwise it simply adds a new
+ * value to this multi-valued header.
+ */
public static void addValueToHeader(Map<String, List<String>> headers,
String key, String value, boolean singleValued) {
List<String> values = headers.get(key);