net.i2p.client
Class I2PSessionImpl

java.lang.Object
  extended by net.i2p.client.I2PSessionImpl
All Implemented Interfaces:
I2PSession, I2CPMessageReader.I2CPMessageEventListener
Direct Known Subclasses:
I2PSessionImpl2

abstract class I2PSessionImpl
extends java.lang.Object
implements I2PSession, I2CPMessageReader.I2CPMessageEventListener

Implementation of an I2P session running over TCP. This class is NOT thread safe - only one thread should send messages at any given time

Author:
jrandom

Nested Class Summary
protected  class I2PSessionImpl.AvailabilityNotifier
           
protected  class I2PSessionImpl.VerifyUsage
           
 
Field Summary
protected  I2PSessionImpl.AvailabilityNotifier _availabilityNotifier
          thread that we tell when new messages are available who then tells us to fetch them.
protected  java.util.Map<java.lang.Long,MessagePayloadMessage> _availableMessages
          map of Long --> MessagePayloadMessage
protected  boolean _closed
          whether the session connection has already been closed (or not yet opened)
protected  boolean _closing
          whether the session connection is in the process of being closed
protected  I2PAppContext _context
          used to seperate things out so we can get rid of singletons
protected  I2PClientMessageHandlerMap _handlerMap
           
protected  java.lang.String _hostname
          hostname of router
protected  Log _log
           
protected  boolean _opening
          whether the session connection is in the process of being opened
protected  java.io.OutputStream _out
          where we pipe our messages
protected  int _portNum
          port num to router
protected  I2CPMessageProducer _producer
          class that generates new messages
protected  I2CPMessageReader _reader
          reader that always searches for messages
protected  I2PSessionListener _sessionListener
          who we send events to
protected  java.net.Socket _socket
          socket for comm
protected  ClientWriterRunner _writer
          writer message queue
static int LISTEN_PORT
           
 
Fields inherited from interface net.i2p.client.I2PSession
PORT_ANY, PORT_UNSPECIFIED, PROTO_ANY, PROTO_DATAGRAM, PROTO_STREAMING, PROTO_UNSPECIFIED
 
Constructor Summary
I2PSessionImpl()
          for extension
I2PSessionImpl(I2PAppContext context, java.io.InputStream destKeyStream, java.util.Properties options)
          Create a new session, reading the Destination, PrivateKey, and SigningPrivateKey from the destKeyStream, and using the specified options to connect to the router
 
Method Summary
 void addNewMessage(MessagePayloadMessage msg)
          Recieve a payload message and let the app know its available
 int[] bandwidthLimits()
          Get the current bandwidth limits
 void connect()
          Connect to the router and establish a session.
(package private)  void dateUpdated()
           
 void destroySession()
          Tear down the session, and do NOT reconnect.
 void destroySession(boolean sendDisconnect)
          Tear down the session, and do NOT reconnect.
protected  void disconnect()
           
 void disconnected(I2CPMessageReader reader)
          Recieve notification that the I2CP connection was disconnected
 PrivateKey getDecryptionKey()
          Retrieve the decryption PrivateKey
(package private)  LeaseSet getLeaseSet()
           
 Destination getMyDestination()
          Retrieve the destination of the session
(package private)  boolean getOpening()
           
(package private)  java.util.Properties getOptions()
          Retrieve the configuration options
protected  java.lang.String getPrefix()
           
 SigningPrivateKey getPrivateKey()
          Retrieve the signing SigningPrivateKey
(package private)  I2CPMessageProducer getProducer()
          Retrieve the helper that generates I2CP messages
(package private)  SessionId getSessionId()
          Retrieve the session's ID
 boolean isClosed()
          has the session been closed (or not yet connected)?
 long lastActivity()
           
protected  void loadConfig(java.util.Properties options)
          Parse the config for anything we know about
 Destination lookupDest(Hash h)
          Lookup up a Hash
 void messageReceived(I2CPMessageReader reader, I2CPMessage message)
          Recieve notification of some I2CP message and handle it if possible
(package private)  void propogateError(java.lang.String msg, java.lang.Throwable error)
          Pass off the error to the listener Misspelled, oh well.
 void readError(I2CPMessageReader reader, java.lang.Exception error)
          Recieve notifiation of an error reading the I2CP stream
 byte[] receiveMessage(int msgId)
          Pull the unencrypted data from the message that we've already prefetched and notified the user that its available.
abstract  void receiveStatus(int msgId, long nonce, int status)
           
protected  boolean reconnect()
           
 void reportAbuse(int msgId, int severity)
          Report abuse with regards to the given messageId
abstract  boolean sendMessage(Destination dest, byte[] payload)
          Send the data to the destination.
abstract  boolean sendMessage(Destination dest, byte[] payload, SessionKey keyUsed, java.util.Set tagsSent)
          Like sendMessage above, except the key used and the tags sent are exposed to the application.
(package private)  void sendMessage(I2CPMessage message)
          Deliver an I2CP message to the router
(package private)  void setLeaseSet(LeaseSet ls)
           
(package private)  void setOpening(boolean ls)
           
 void setReduced()
           
(package private)  void setSessionId(SessionId id)
           
 void setSessionListener(I2PSessionListener lsnr)
          configure the listener
protected  boolean shouldReconnect()
           
 java.lang.String toString()
           
protected  void updateActivity()
           
 
Methods inherited from class java.lang.Object
clone, equals, finalize, getClass, hashCode, notify, notifyAll, wait, wait, wait
 
Methods inherited from interface net.i2p.client.I2PSession
addMuxedSessionListener, addSessionListener, removeListener, sendMessage, sendMessage, sendMessage, sendMessage, sendMessage, sendMessage
 

Field Detail

_log

protected Log _log

_hostname

protected java.lang.String _hostname
hostname of router


_portNum

protected int _portNum
port num to router


_socket

protected java.net.Socket _socket
socket for comm


_reader

protected I2CPMessageReader _reader
reader that always searches for messages


_writer

protected ClientWriterRunner _writer
writer message queue


_out

protected java.io.OutputStream _out
where we pipe our messages


_sessionListener

protected I2PSessionListener _sessionListener
who we send events to


_producer

protected I2CPMessageProducer _producer
class that generates new messages


_availableMessages

protected java.util.Map<java.lang.Long,MessagePayloadMessage> _availableMessages
map of Long --> MessagePayloadMessage


_handlerMap

protected I2PClientMessageHandlerMap _handlerMap

_context

protected I2PAppContext _context
used to seperate things out so we can get rid of singletons


_closed

protected boolean _closed
whether the session connection has already been closed (or not yet opened)


_closing

protected boolean _closing
whether the session connection is in the process of being closed


_opening

protected boolean _opening
whether the session connection is in the process of being opened


_availabilityNotifier

protected I2PSessionImpl.AvailabilityNotifier _availabilityNotifier
thread that we tell when new messages are available who then tells us to fetch them. The point of this is so that the fetch doesn't block the reading of other messages (in turn, potentially leading to deadlock)


LISTEN_PORT

public static final int LISTEN_PORT
See Also:
Constant Field Values
Constructor Detail

I2PSessionImpl

public I2PSessionImpl()
for extension


I2PSessionImpl

public I2PSessionImpl(I2PAppContext context,
                      java.io.InputStream destKeyStream,
                      java.util.Properties options)
               throws I2PSessionException
Create a new session, reading the Destination, PrivateKey, and SigningPrivateKey from the destKeyStream, and using the specified options to connect to the router

Throws:
I2PSessionException - if there is a problem loading the private keys or
Method Detail

dateUpdated

void dateUpdated()

loadConfig

protected void loadConfig(java.util.Properties options)
Parse the config for anything we know about


setLeaseSet

void setLeaseSet(LeaseSet ls)

getLeaseSet

LeaseSet getLeaseSet()

setOpening

void setOpening(boolean ls)

getOpening

boolean getOpening()

connect

public void connect()
             throws I2PSessionException
Connect to the router and establish a session. This call blocks until a session is granted.

Specified by:
connect in interface I2PSession
Throws:
I2PSessionException - if there is a configuration error or the router is not reachable

receiveMessage

public byte[] receiveMessage(int msgId)
                      throws I2PSessionException
Pull the unencrypted data from the message that we've already prefetched and notified the user that its available.

Specified by:
receiveMessage in interface I2PSession
Parameters:
msgId - message to fetch
Returns:
unencrypted body of the message
Throws:
I2PSessionException

reportAbuse

public void reportAbuse(int msgId,
                        int severity)
                 throws I2PSessionException
Report abuse with regards to the given messageId

Specified by:
reportAbuse in interface I2PSession
Parameters:
msgId - message that was abusive (or -1 for not message related)
severity - how abusive
Throws:
I2PSessionException

sendMessage

public abstract boolean sendMessage(Destination dest,
                                    byte[] payload)
                             throws I2PSessionException
Send the data to the destination. TODO: this currently always returns true, regardless of whether the message was delivered successfully. make this wait for at least ACCEPTED

Specified by:
sendMessage in interface I2PSession
Parameters:
dest - location to send the message
payload - body of the message to be sent (unencrypted)
Returns:
whether it was accepted by the router for delivery or not
Throws:
I2PSessionException

sendMessage

public abstract boolean sendMessage(Destination dest,
                                    byte[] payload,
                                    SessionKey keyUsed,
                                    java.util.Set tagsSent)
                             throws I2PSessionException
Description copied from interface: I2PSession
Like sendMessage above, except the key used and the tags sent are exposed to the application.

If some application layer message delivery confirmation is used, rather than i2p's (slow) built in confirmation via guaranteed delivery mode, the application can update the SessionKeyManager, ala:

   SessionKeyManager.getInstance().tagsDelivered(dest.getPublicKey(), keyUsed, tagsSent);
 
If an application is using guaranteed delivery mode, this is not useful, but for applications using best effort delivery mode, if they can know with certainty that a message was delivered and can update the SessionKeyManager appropriately, a significant performance boost will occur (subsequent message encryption and decryption will be done via AES and a SessionTag, rather than ElGamal+AES, which is 1000x slower).

Specified by:
sendMessage in interface I2PSession
Parameters:
keyUsed - unused - no end-to-end crypto
tagsSent - unused - no end-to-end crypto
dest - location to send the message
payload - body of the message to be sent (unencrypted)
Throws:
I2PSessionException

receiveStatus

public abstract void receiveStatus(int msgId,
                                   long nonce,
                                   int status)

addNewMessage

public void addNewMessage(MessagePayloadMessage msg)
Recieve a payload message and let the app know its available


messageReceived

public void messageReceived(I2CPMessageReader reader,
                            I2CPMessage message)
Recieve notification of some I2CP message and handle it if possible

Specified by:
messageReceived in interface I2CPMessageReader.I2CPMessageEventListener
Parameters:
reader - I2CPMessageReader to notify
message - the I2CPMessage

readError

public void readError(I2CPMessageReader reader,
                      java.lang.Exception error)
Recieve notifiation of an error reading the I2CP stream

Specified by:
readError in interface I2CPMessageReader.I2CPMessageEventListener
Parameters:
reader - I2CPMessageReader to notify
error - Exception that was thrown

getMyDestination

public Destination getMyDestination()
Retrieve the destination of the session

Specified by:
getMyDestination in interface I2PSession

getDecryptionKey

public PrivateKey getDecryptionKey()
Retrieve the decryption PrivateKey

Specified by:
getDecryptionKey in interface I2PSession

getPrivateKey

public SigningPrivateKey getPrivateKey()
Retrieve the signing SigningPrivateKey

Specified by:
getPrivateKey in interface I2PSession

getProducer

I2CPMessageProducer getProducer()
Retrieve the helper that generates I2CP messages


getOptions

java.util.Properties getOptions()
Retrieve the configuration options


getSessionId

SessionId getSessionId()
Retrieve the session's ID


setSessionId

void setSessionId(SessionId id)

setSessionListener

public void setSessionListener(I2PSessionListener lsnr)
configure the listener

Specified by:
setSessionListener in interface I2PSession
Parameters:
lsnr - listener to retrieve events

isClosed

public boolean isClosed()
has the session been closed (or not yet connected)?

Specified by:
isClosed in interface I2PSession
Returns:
true if the session is closed

sendMessage

void sendMessage(I2CPMessage message)
           throws I2PSessionException
Deliver an I2CP message to the router

Throws:
I2PSessionException - if the message is malformed or there is an error writing it out

propogateError

void propogateError(java.lang.String msg,
                    java.lang.Throwable error)
Pass off the error to the listener Misspelled, oh well.


destroySession

public void destroySession()
Tear down the session, and do NOT reconnect. Blocks if session has not been fully started.

Specified by:
destroySession in interface I2PSession

destroySession

public void destroySession(boolean sendDisconnect)
Tear down the session, and do NOT reconnect. Blocks if session has not been fully started.


disconnected

public void disconnected(I2CPMessageReader reader)
Recieve notification that the I2CP connection was disconnected

Specified by:
disconnected in interface I2CPMessageReader.I2CPMessageEventListener
Parameters:
reader - I2CPMessageReader to notify

disconnect

protected void disconnect()

shouldReconnect

protected boolean shouldReconnect()

reconnect

protected boolean reconnect()

getPrefix

protected java.lang.String getPrefix()

lookupDest

public Destination lookupDest(Hash h)
                       throws I2PSessionException
Description copied from interface: I2PSession
Lookup up a Hash

Specified by:
lookupDest in interface I2PSession
Throws:
I2PSessionException

bandwidthLimits

public int[] bandwidthLimits()
                      throws I2PSessionException
Description copied from interface: I2PSession
Get the current bandwidth limits

Specified by:
bandwidthLimits in interface I2PSession
Throws:
I2PSessionException

updateActivity

protected void updateActivity()

lastActivity

public long lastActivity()

setReduced

public void setReduced()

toString

public java.lang.String toString()
Overrides:
toString in class java.lang.Object