key0-96/
key0-96/doc/key/
key0-96/doc/key/credits/
key0-96/doc/key/developers/
key0-96/doc/key/developers/resources/
key0-96/setup/caves/
key0-96/setup/help/
key0-96/setup/ruins/
key0-96/src/
key0-96/src/commands/
key0-96/src/events/
key0-96/src/hack/
key0-96/src/sql/
key0-96/src/swing/
key0-96/src/talker/forest/
key0-96/src/talker/objects/
key0-96/src/terminals/
/*
**               j###t  ########## ####   ####
**              j###t   ########## ####   ####
**             j###T               "###L J###"
**          ######P'    ##########  #########
**          ######k,    ##########   T######T
**          ####~###L   ####
**          #### q###L  ##########   .#####
**          ####  \###L ##########   #####"
**
**  $Id$
**
**  Class History
**
**  Date        Name         Description
**  ---------|------------|-----------------------------------------------
**  19Aug98     subtle       start of recorded history
**
*/

package key;

import key.collections.NetworkCollection;

import java.util.Enumeration;
import java.io.IOException;
import java.io.DataInput;
import java.io.DataOutput;
import java.util.StringTokenizer;
import java.util.Hashtable;

/**
  *  The top level container for sites
 */
public class Internet extends Network implements Targetable
{
	private static final long serialVersionUID = -8521058051451596958L;
	public Internet()
	{
			// set num to null so that our name is used, not a number
		super( 0, 0, null );
		
		contained = new NetworkCollection();
		setKey( "sites" );
	}
	
	public void unRegisterTrailer( String t )
	{
		((NetworkCollection)contained).unRegister( t );
	}
	
	public void registerTrailer( Site t )
	{
		((NetworkCollection)contained).register( t.getTrailer(), (Symbol) t.getThis() );
	}
	
	public boolean isOutRankedBy( Rank rank )
	{
		return( rank.getTargets().contains( this ) );
	}
	
	public void insert( Site site )
	{
		int[] mask = site.getMask();
		if( position == mask.length )
		{
				//  this network represents the site??
			throw new UnexpectedResult( "invalid site IP address too short" );
		}
		else if( position > mask.length )
			throw new UnexpectedResult( "site insert passed down too many times (position is " + position + ", mask.length is " + mask.length );
		
		if( mask[ position ] < 128 )
		{ 
				//  just insert the site - this is a class A network
				//  could check there wasn't already anything here
			//siteLevel.put( new Integer( (int) mask[ position ] ), site );
			try
			{
				add( site );
			}
			catch( BadKeyException e )
			{
				System.out.println( site.toString() );
				e.printStackTrace( System.out );
				throw new UnexpectedResult( e.toString() + " while adding a *numbered* site to the network" );
			}
			catch( NonUniqueKeyException e )
			{
				throw new UnexpectedResult( e.toString() + " while adding a *numbered* site to the network" );
			}
			//Log.debug( this, "inserted site at position " + position );
			//System.out.println( "inserted site at position " + position );
		}
		else
		{
			Reference o = (Reference) contained.get( new Integer( (int) mask[ 0 ] ) );
			
			Network subnet = null;
			
			if( o != null )
				subnet = (Network) o.get();
			
			if( subnet == null )
			{
					//  need to insert another subnet
				int max=0;
				if( mask[0] < 128 )
					max=0;
				else if( mask[0] < 192 )
					max=1;
				else if( mask[0] < 224 )
					max=2;
				else
					max=3;
				
				Integer n = new Integer( (int) mask[ position ] );
				subnet = (Network) Factory.makeAtom( Network.class );
				subnet.setPosition( position + 1, max, n );
				//siteLevel.put( n, subnet );
				try
				{
					add( subnet );
				}
				catch( BadKeyException e )
				{
					throw new UnexpectedResult( e.toString() + " while adding a *numbered* site to the network" );
				}
				catch( NonUniqueKeyException e )
				{
					throw new UnexpectedResult( e.toString() + " while adding a *numbered* site to the network" );
				}
				//Log.debug( this, "added network with maxPos " + max );
				//System.out.println( "added network with maxPos " + max );
			}
			
			subnet.insert( site );
		}
	}

	public static void main( String args[] )
	{
		Internet main = new Internet();
		String entry;
		
		do
		{
			entry = input( "[dump, add x.x.x.x, register x.x.x.x name.domain ] -> " );
			if( entry.equalsIgnoreCase( "dump" ) )
			{
				main.dump();
			}
			else if( entry.startsWith( "register " ) )
			{
				entry = entry.substring( 9 );

				StringTokenizer st = new StringTokenizer( entry, "." );
				int[] mask = new int[4];

				try
				{
					mask[0] = Integer.parseInt( st.nextToken() );
					mask[1] = Integer.parseInt( st.nextToken() );
					mask[2] = Integer.parseInt( st.nextToken() );
					mask[3] = Integer.parseInt( st.nextToken( ". " ) );

					Site site;
					site = main.search( mask );
					if( site == null )
					{
						System.out.println( "Couldn't find site " + mask[0]+"."+mask[1]+"."+mask[2]+"."+mask[3] + "..." );
					}
					else
					{
						System.out.println( "site " + site.toString() + " found, registering..." );
						site.registerSite( st.nextToken( " " ) );
					}
				}
				catch( NumberFormatException e )
				{
					System.out.println( e.toString() );
				}
			}
			else if( entry.startsWith( "add " ) )
			{
				entry = entry.substring( 4 );

				StringTokenizer st = new StringTokenizer( entry, "." );
				int[] mask = new int[4];

				try
				{
					mask[0] = Integer.parseInt( st.nextToken() );
					mask[1] = Integer.parseInt( st.nextToken() );
					mask[2] = Integer.parseInt( st.nextToken() );
					mask[3] = Integer.parseInt( st.nextToken() );
					
					System.out.println( "Inserting " + mask[0]+"."+mask[1]+"."+mask[2]+"."+mask[3] + "..." );

					Site site;
					site = main.search( mask );
					if( site == null )
					{
						Site newSite = (Site) Factory.makeAtom( Site.class );
						newSite.setMask( mask );
						main.insert( newSite );
					}
					else
						System.out.println( "site " + site.toString() + " found" );
				}
				catch( NumberFormatException e )
				{
					System.out.println( e.toString() );
				}
			}
			else if( entry.equals( "quit" ) )
				;
			else
			{
				System.out.println( "Unknown command '" + entry + "'" );
			}
		}
		while( !entry.equals( "quit" ) );
	}
	
	public static String input( String prompt )
	{
		StringBuffer buildInput = new StringBuffer();
		char b=' ';

		System.out.print( prompt );
		System.out.flush();

		do
		{
			try
			{
				b = (char) System.in.read();
			}
			catch( java.io.IOException e )
				{
						//  generally an IOException here means that
						//  the player in question has disconnected
					System.out.println( e.toString() );
					System.exit( 1 );
				}
			if( b != '\n' && b != 0 )
				buildInput.append( b );
		} while( b != '\n' && b != 0 );

		return( new String( buildInput ) );
	}
}