[skycastle-commits] SF.net SVN: skycastle: [439] trunk/skycastle/modules/core/src

  • From: zzorn@xxxxxxxxxxxxxxxxxxxxx
  • To: skycastle-commits@xxxxxxxxxxxxx
  • Date: Fri, 04 Apr 2008 08:45:17 -0700

Revision: 439
          http://skycastle.svn.sourceforge.net/skycastle/?rev=439&view=rev
Author:   zzorn
Date:     2008-04-04 08:44:16 -0700 (Fri, 04 Apr 2008)

Log Message:
-----------
Moved Message validation to the AbstractProtocol, separating concerns and 
providing the message validation to all Protocols that extend the 
AbstractProtocol.

Modified Paths:
--------------
    
trunk/skycastle/modules/core/src/main/java/org/skycastle/connection/ClientConnectionHandlerImpl.java
    
trunk/skycastle/modules/core/src/main/java/org/skycastle/protocol/negotiation/AbstractProtocolNegotiator.java
    
trunk/skycastle/modules/core/src/main/java/org/skycastle/protocol/negotiation/ProtocolNegotiator.java
    
trunk/skycastle/modules/core/src/main/java/org/skycastle/protocol/protocols/SerializationProtocol.java
    
trunk/skycastle/modules/core/src/main/java/org/skycastle/protocol/registry/ProtocolRegistry.java
    
trunk/skycastle/modules/core/src/main/java/org/skycastle/protocol/registry/ProtocolRegistryImpl.java
    
trunk/skycastle/modules/core/src/test/java/org/skycastle/protocol/negotiation/ProtocolNegotiationTest.java

Added Paths:
-----------
    
trunk/skycastle/modules/core/src/main/java/org/skycastle/protocol/protocols/AbstractProtocol.java
    
trunk/skycastle/modules/core/src/main/java/org/skycastle/protocol/protocols/Protocol.java

Modified: 
trunk/skycastle/modules/core/src/main/java/org/skycastle/connection/ClientConnectionHandlerImpl.java
===================================================================
--- 
trunk/skycastle/modules/core/src/main/java/org/skycastle/connection/ClientConnectionHandlerImpl.java
        2008-04-03 22:16:52 UTC (rev 438)
+++ 
trunk/skycastle/modules/core/src/main/java/org/skycastle/connection/ClientConnectionHandlerImpl.java
        2008-04-04 15:44:16 UTC (rev 439)
@@ -5,11 +5,11 @@
 import com.sun.sgs.client.simple.SimpleClient;
 import com.sun.sgs.client.simple.SimpleClientListener;
 import org.skycastle.messaging.Message;
-import org.skycastle.protocol.Protocol;
 import org.skycastle.protocol.ProtocolException;
 import org.skycastle.protocol.negotiation.ClientSideProtocolNegotiator;
 import org.skycastle.protocol.negotiation.NegotiationStatus;
 import org.skycastle.protocol.negotiation.ProtocolNegotiator;
+import org.skycastle.protocol.protocols.Protocol;
 import org.skycastle.protocol.registry.ProtocolRegistry;
 import org.skycastle.protocol.registry.ProtocolRegistryImpl;
 import org.skycastle.util.ParameterChecker;

Modified: 
trunk/skycastle/modules/core/src/main/java/org/skycastle/protocol/negotiation/AbstractProtocolNegotiator.java
===================================================================
--- 
trunk/skycastle/modules/core/src/main/java/org/skycastle/protocol/negotiation/AbstractProtocolNegotiator.java
       2008-04-03 22:16:52 UTC (rev 438)
+++ 
trunk/skycastle/modules/core/src/main/java/org/skycastle/protocol/negotiation/AbstractProtocolNegotiator.java
       2008-04-04 15:44:16 UTC (rev 439)
@@ -1,6 +1,6 @@
 package org.skycastle.protocol.negotiation;
 
-import org.skycastle.protocol.Protocol;
+import org.skycastle.protocol.protocols.Protocol;
 import org.skycastle.protocol.registry.ProtocolRegistry;
 import org.skycastle.util.ParameterChecker;
 import org.skycastle.util.StringUtilities;

Modified: 
trunk/skycastle/modules/core/src/main/java/org/skycastle/protocol/negotiation/ProtocolNegotiator.java
===================================================================
--- 
trunk/skycastle/modules/core/src/main/java/org/skycastle/protocol/negotiation/ProtocolNegotiator.java
       2008-04-03 22:16:52 UTC (rev 438)
+++ 
trunk/skycastle/modules/core/src/main/java/org/skycastle/protocol/negotiation/ProtocolNegotiator.java
       2008-04-04 15:44:16 UTC (rev 439)
@@ -1,6 +1,6 @@
 package org.skycastle.protocol.negotiation;
 
-import org.skycastle.protocol.Protocol;
+import org.skycastle.protocol.protocols.Protocol;
 
 /**
  * A state machine that can negotiate a protocol to use with another party 
connected over a network.

Copied: 
trunk/skycastle/modules/core/src/main/java/org/skycastle/protocol/protocols/AbstractProtocol.java
 (from rev 438, 
trunk/skycastle/modules/core/src/main/java/org/skycastle/protocol/AbstractProtocol.java)
===================================================================
--- 
trunk/skycastle/modules/core/src/main/java/org/skycastle/protocol/protocols/AbstractProtocol.java
                           (rev 0)
+++ 
trunk/skycastle/modules/core/src/main/java/org/skycastle/protocol/protocols/AbstractProtocol.java
   2008-04-04 15:44:16 UTC (rev 439)
@@ -0,0 +1,131 @@
+package org.skycastle.protocol.protocols;
+
+import org.skycastle.messaging.Message;
+import org.skycastle.protocol.ProtocolException;
+import org.skycastle.util.ParameterChecker;
+import org.skycastle.util.parameters.ParameterSet;
+import org.skycastle.util.parameters.ValidationError;
+import org.skycastle.util.parameters.validators.ParameterValidator;
+import org.skycastle.util.parameters.validators.type.TypeValidator;
+
+import java.io.Serializable;
+import java.util.Collection;
+import java.util.Map;
+
+/**
+ * Provides common functionality.
+ *
+ * @author Hans Haggstrom
+ */
+public abstract class AbstractProtocol
+        implements Protocol, Serializable
+{
+
+    //======================================================================
+    // Private Fields
+
+    private final String myProtocolId;
+    private final ParameterValidator myMessageValidator;
+
+    //======================================================================
+    // Private Constants
+
+    private static final long serialVersionUID = 1L;
+
+    //======================================================================
+    // Public Methods
+
+    //----------------------------------------------------------------------
+    // Protocol Implementation
+
+    public final String getProtocolId()
+    {
+        return myProtocolId;
+    }
+
+
+    public final byte[] encode( final Message messageToSend ) throws 
ProtocolException
+    {
+        checkMessageTypes( messageToSend, "Could not send message" );
+
+        return encodeWithoutCheck( messageToSend );
+    }
+
+
+    public final Message decode( final byte[] receivedBytes ) throws 
ProtocolException
+    {
+        final Message recievedMessage = decodeWithoutCheck( receivedBytes );
+
+        checkMessageTypes( recievedMessage, "Could not accept recieved 
message" );
+
+        return recievedMessage;
+    }
+
+    //======================================================================
+    // Protected Methods
+
+    //----------------------------------------------------------------------
+    // Protected Constructors
+
+    /**
+     * @param protocolId       an identifier for this protocol.   Used for 
protocol negotiation.  Should be in
+     *                         the Java identifier format (letter + numbers 
and letters and underscores).
+     * @param messageValidator a {@link TypeValidator} that is used to check 
that the types that are allowed
+     *                         to be serialized and deserialized are in a set 
of allowed types. Can also check
+     *                         types of nested {@link Collection}s, {@link 
Map}s, and {@link ParameterSet}s.
+     *                         <p/>
+     *                         Can be used to improve the security by 
specifying only simple data classes that
+     *                         can be transfered, to minimize hijacking some 
more complex class with a custom
+     *                         state to instabilize or compromize the server 
(or client).
+     */
+    protected AbstractProtocol( final String protocolId, final 
ParameterValidator messageValidator )
+    {
+        ParameterChecker.checkIsIdentifier( protocolId, "protocolId" );
+        ParameterChecker.checkNotNull( messageValidator, "messageValidator" );
+
+        myProtocolId = protocolId;
+        myMessageValidator = messageValidator;
+    }
+
+    //----------------------------------------------------------------------
+    // Abstract Protected Methods
+
+    /**
+     * Encodes the message without first validating it (the calling {@link 
AbstractProtocol} takes care of
+     * that).
+     *
+     * @param messageToSend the message to encode to bytes for network 
transfer.
+     *
+     * @return the bytes representing the message to transfer
+     *
+     * @throws ProtocolException if there was some error when encoding the 
message.
+     */
+    protected abstract byte[] encodeWithoutCheck( final Message messageToSend 
) throws ProtocolException;
+
+    /**
+     * Decodes the message without validating it afterwards (the calling 
{@link AbstractProtocol} takes care
+     * of that).
+     *
+     * @param receivedBytes an array of bytes received over the network.  Note 
that malicious crackers may
+     *                      send any kind of messages, so the error handling 
should be robust.
+     *
+     * @return the message represented by the specified bytes.
+     *
+     * @throws ProtocolException if there was some error when decoding the 
received message.
+     */
+    protected abstract Message decodeWithoutCheck( final byte[] receivedBytes 
) throws ProtocolException;
+
+    //======================================================================
+    // Private Methods
+
+    private void checkMessageTypes( final Message message, final String 
description )
+            throws ProtocolException
+    {
+        final ValidationError validationError = 
myMessageValidator.validateParameter( message, "" );
+        if ( validationError != null )
+        {
+            throw new ProtocolException( description + ", it contains a 
non-allowed type: " + validationError.toString() );
+        }
+    }
+
+}


Property changes on: 
trunk/skycastle/modules/core/src/main/java/org/skycastle/protocol/protocols/AbstractProtocol.java
___________________________________________________________________
Name: svn:mime-type
   + text/plain
Name: svn:keywords
   + Id
Name: svn:eol-style
   + native

Copied: 
trunk/skycastle/modules/core/src/main/java/org/skycastle/protocol/protocols/Protocol.java
 (from rev 438, 
trunk/skycastle/modules/core/src/main/java/org/skycastle/protocol/Protocol.java)
===================================================================
--- 
trunk/skycastle/modules/core/src/main/java/org/skycastle/protocol/protocols/Protocol.java
                           (rev 0)
+++ 
trunk/skycastle/modules/core/src/main/java/org/skycastle/protocol/protocols/Protocol.java
   2008-04-04 15:44:16 UTC (rev 439)
@@ -0,0 +1,42 @@
+package org.skycastle.protocol.protocols;
+
+import org.skycastle.messaging.Message;
+import org.skycastle.protocol.ProtocolException;
+
+/**
+ * A protocol used to communicate between server and client.
+ * <p/>
+ * The transport happens as byte array messages.
+ * <p/>
+ * The transfered data is messages with source and target game object, a 
message type, and a set of named
+ * parameters of primitive data structures and collections.
+ *
+ * @author Hans Haggstrom
+ */
+public interface Protocol
+{
+    /**
+     * @return a string ID used to identify this protocol during protocol 
negotiations.  The ID should be a
+     *         valid Java identifier (sart with letter, contain no spaces, 
etc).
+     */
+    String getProtocolId();
+
+    /**
+     * @param messageToSend the message to encode to bytes for network 
transfer.
+     *
+     * @return the bytes representing the message to transfer
+     *
+     * @throws ProtocolException if there was some error when encoding the 
message.
+     */
+    byte[] encode( Message messageToSend ) throws ProtocolException;
+
+    /**
+     * @param receivedBytes an array of bytes received over the network.  Note 
that malicious crackers may
+     *                      send any kind of messages, so the error handling 
should be robust.
+     *
+     * @return the message represented by the specified bytes.
+     *
+     * @throws ProtocolException if there was some error when decoding the 
received message.
+     */
+    Message decode( byte[] receivedBytes ) throws ProtocolException;
+}


Property changes on: 
trunk/skycastle/modules/core/src/main/java/org/skycastle/protocol/protocols/Protocol.java
___________________________________________________________________
Name: svn:mime-type
   + text/plain
Name: svn:keywords
   + Id
Name: svn:eol-style
   + native

Modified: 
trunk/skycastle/modules/core/src/main/java/org/skycastle/protocol/protocols/SerializationProtocol.java
===================================================================
--- 
trunk/skycastle/modules/core/src/main/java/org/skycastle/protocol/protocols/SerializationProtocol.java
      2008-04-03 22:16:52 UTC (rev 438)
+++ 
trunk/skycastle/modules/core/src/main/java/org/skycastle/protocol/protocols/SerializationProtocol.java
      2008-04-04 15:44:16 UTC (rev 439)
@@ -1,12 +1,8 @@
 package org.skycastle.protocol.protocols;
 
 import org.skycastle.messaging.Message;
-import org.skycastle.protocol.AbstractProtocol;
-import org.skycastle.protocol.Protocol;
 import org.skycastle.protocol.ProtocolException;
-import org.skycastle.util.ParameterChecker;
 import org.skycastle.util.parameters.ParameterSet;
-import org.skycastle.util.parameters.ValidationError;
 import org.skycastle.util.parameters.validators.ParameterValidator;
 import org.skycastle.util.parameters.validators.type.TypeValidator;
 
@@ -22,13 +18,15 @@
  */
 public final class SerializationProtocol
         extends AbstractProtocol
-        implements Serializable
 {
 
     //======================================================================
-    // Private Fields
+    // Public Constants
 
-    private final ParameterValidator myMessageValidator;
+    /**
+     * The identifier of this {@link Protocol}.
+     */
+    public static final String SERIALIZATION_PROTOCOL_ID = 
"SerializationProtocol";
 
     //======================================================================
     // Private Constants
@@ -53,20 +51,16 @@
      *                         can be transfered, to minimize hijacking some 
more complex class with a custom
      *                         state to instabilize or compromize the server 
(or client).
      */
-    // TODO: Refactor the message validator storage and checking into an 
abstract base class
     public SerializationProtocol( final ParameterValidator messageValidator )
     {
-        super( "SerializationProtocol" );
-
-        ParameterChecker.checkNotNull( messageValidator, "messageValidator" );
-
-        myMessageValidator = messageValidator;
+        super( SERIALIZATION_PROTOCOL_ID, messageValidator );
     }
 
-    //----------------------------------------------------------------------
-    // Protocol Implementation
+    //======================================================================
+    // Protected Methods
 
-    public byte[] encode( final Message messageToSend ) throws 
ProtocolException
+    @Override
+    protected byte[] encodeWithoutCheck( final Message messageToSend ) throws 
ProtocolException
     {
         final ByteArrayOutputStream byteArrayOutputStream = new 
ByteArrayOutputStream();
         ObjectOutputStream objectOutputStream = null;
@@ -75,8 +69,6 @@
             //noinspection IOResourceOpenedButNotSafelyClosed
             objectOutputStream = new ObjectOutputStream( byteArrayOutputStream 
);
 
-            checkMessageTypes( messageToSend, objectOutputStream );
-
             objectOutputStream.writeObject( messageToSend );
 
             return byteArrayOutputStream.toByteArray();
@@ -92,7 +84,8 @@
     }
 
 
-    public Message decode( final byte[] receivedBytes ) throws 
ProtocolException
+    @Override
+    protected Message decodeWithoutCheck( final byte[] receivedBytes ) throws 
ProtocolException
     {
         final ByteArrayInputStream byteArrayInputStream = new 
ByteArrayInputStream( receivedBytes );
         ObjectInputStream objectInputStream = null;
@@ -101,11 +94,7 @@
             //noinspection IOResourceOpenedButNotSafelyClosed
             objectInputStream = new ObjectInputStream( byteArrayInputStream );
 
-            final Message message = (Message) objectInputStream.readObject();
-
-            checkMessageTypes( message, objectInputStream );
-
-            return message;
+            return (Message) objectInputStream.readObject();
         }
         catch ( IOException e )
         {
@@ -128,18 +117,6 @@
     //======================================================================
     // Private Methods
 
-    private void checkMessageTypes( final Message message, final Closeable 
objectOutputStream )
-            throws ProtocolException
-    {
-        final ValidationError validationError = 
myMessageValidator.validateParameter( message, "" );
-        if ( validationError != null )
-        {
-            closeStream( objectOutputStream );
-            throw new ProtocolException( "Could not transfer message, it 
contains a non-allowed type: " + validationError.toString() );
-        }
-    }
-
-
     private void closeStream( final Closeable stream )
             throws ProtocolException
     {

Modified: 
trunk/skycastle/modules/core/src/main/java/org/skycastle/protocol/registry/ProtocolRegistry.java
===================================================================
--- 
trunk/skycastle/modules/core/src/main/java/org/skycastle/protocol/registry/ProtocolRegistry.java
    2008-04-03 22:16:52 UTC (rev 438)
+++ 
trunk/skycastle/modules/core/src/main/java/org/skycastle/protocol/registry/ProtocolRegistry.java
    2008-04-04 15:44:16 UTC (rev 439)
@@ -1,13 +1,13 @@
 package org.skycastle.protocol.registry;
 
 import com.sun.sgs.app.ManagedObject;
-import org.skycastle.protocol.Protocol;
+import org.skycastle.protocol.protocols.Protocol;
 
 import java.io.Serializable;
 import java.util.Set;
 
 /**
- * A registry that can be used to access available {@link 
org.skycastle.protocol.Protocol}s.
+ * A registry that can be used to access available {@link 
org.skycastle.protocol.protocols.Protocol}s.
  *
  * @author Hans Haggstrom
  */
@@ -20,8 +20,8 @@
     Set<String> getAvailableProtocolIds();
 
     /**
-     * @return the {@link org.skycastle.protocol.Protocol} with the specified 
protocol id, or null if not
-     *         found.
+     * @return the {@link org.skycastle.protocol.protocols.Protocol} with the 
specified protocol id, or null
+     *         if not found.
      */
     Protocol getProtocol( String protocolId );
 }

Modified: 
trunk/skycastle/modules/core/src/main/java/org/skycastle/protocol/registry/ProtocolRegistryImpl.java
===================================================================
--- 
trunk/skycastle/modules/core/src/main/java/org/skycastle/protocol/registry/ProtocolRegistryImpl.java
        2008-04-03 22:16:52 UTC (rev 438)
+++ 
trunk/skycastle/modules/core/src/main/java/org/skycastle/protocol/registry/ProtocolRegistryImpl.java
        2008-04-04 15:44:16 UTC (rev 439)
@@ -1,7 +1,7 @@
 package org.skycastle.protocol.registry;
 
 import org.skycastle.protocol.MessageValidator;
-import org.skycastle.protocol.Protocol;
+import org.skycastle.protocol.protocols.Protocol;
 import org.skycastle.protocol.protocols.SerializationProtocol;
 import org.skycastle.util.ParameterChecker;
 
@@ -11,7 +11,7 @@
 import java.util.Set;
 
 /**
- * A registry used to access available {@link 
org.skycastle.protocol.Protocol}s.
+ * A registry used to access available {@link 
org.skycastle.protocol.protocols.Protocol}s.
  *
  * @author Hans Haggstrom
  */

Modified: 
trunk/skycastle/modules/core/src/test/java/org/skycastle/protocol/negotiation/ProtocolNegotiationTest.java
===================================================================
--- 
trunk/skycastle/modules/core/src/test/java/org/skycastle/protocol/negotiation/ProtocolNegotiationTest.java
  2008-04-03 22:16:52 UTC (rev 438)
+++ 
trunk/skycastle/modules/core/src/test/java/org/skycastle/protocol/negotiation/ProtocolNegotiationTest.java
  2008-04-04 15:44:16 UTC (rev 439)
@@ -6,9 +6,10 @@
 
 import junit.framework.TestCase;
 import org.skycastle.messaging.Message;
-import org.skycastle.protocol.AbstractProtocol;
-import org.skycastle.protocol.Protocol;
+import org.skycastle.protocol.MessageValidator;
 import org.skycastle.protocol.ProtocolException;
+import org.skycastle.protocol.protocols.AbstractProtocol;
+import org.skycastle.protocol.protocols.Protocol;
 import org.skycastle.protocol.registry.ProtocolRegistryImpl;
 import org.skycastle.util.StringUtilities;
 
@@ -29,16 +30,17 @@
     // Private Constants
 
     private static final String DUMMY_PROTOCOL_ID = "DummyProtocol";
-    private static final Protocol DUMMY_PROTOCOL = new AbstractProtocol( 
DUMMY_PROTOCOL_ID )
+    private static final Protocol DUMMY_PROTOCOL = new AbstractProtocol( 
DUMMY_PROTOCOL_ID,
+                                                                         new 
MessageValidator() )
     {
 
-        public byte[] encode( final Message messageToSend ) throws 
ProtocolException
+        protected byte[] encodeWithoutCheck( final Message messageToSend ) 
throws ProtocolException
         {
             return new byte[0];
         }
 
 
-        public Message decode( final byte[] receivedBytes ) throws 
ProtocolException
+        protected Message decodeWithoutCheck( final byte[] receivedBytes ) 
throws ProtocolException
         {
             return null;
         }
@@ -46,18 +48,20 @@
     };
 
     private static final String FOO_PROTOCOL_ID = "FooProtocol";
-    private static final Protocol FOO_PROTOCOL = new AbstractProtocol( 
FOO_PROTOCOL_ID )
+    private static final Protocol FOO_PROTOCOL = new AbstractProtocol( 
FOO_PROTOCOL_ID,
+                                                                       new 
MessageValidator() )
     {
 
-        public byte[] encode( final Message messageToSend ) throws 
ProtocolException
+        protected byte[] encodeWithoutCheck( final Message messageToSend ) 
throws ProtocolException
         {
             return new byte[0];
         }
 
 
-        public Message decode( final byte[] receivedBytes ) throws 
ProtocolException
+        protected Message decodeWithoutCheck( final byte[] receivedBytes ) 
throws ProtocolException
         {
             return null;
+
         }
 
     };


This was sent by the SourceForge.net collaborative development platform, the 
world's largest Open Source development site.

Other related posts:

  • » [skycastle-commits] SF.net SVN: skycastle: [439] trunk/skycastle/modules/core/src