예제 #1
0
        /// <summary>
        /// Starts the router, reading configuration parameters from the
        /// application's configuration settings.
        /// </summary>
        /// <remarks>
        /// <para>
        /// This method will gather the instance settings from the application's
        /// configuration settings, as described below.  Multiple router instances
        /// can be specified in a single configuration file.  The router name
        /// parameter is used to distinguish between the settings for each router
        /// instance.  The method will look for configuration keys prefixed by
        /// </para>
        /// <code language="none">
        /// "MsgRouter." + name + "."
        /// </code>
        /// <para>
        /// So, when loading the TcpEP setting, Start("Foo") will query for
        /// "Router.Foo.TcpEP".
        /// </para>
        /// <para>
        /// Here are the configuration settings LeafRouter expects: (note
        /// that all settings are prefixed by "MsgRouter." as in "MsgRouter.RouterEP".
        /// </para>
        /// <div class="tablediv">
        /// <table class="dtTABLE" cellspacing="0" ID="Table1">
        /// <tr valign="top">
        /// <th width="1">Setting</th>
        /// <th width="1">Default</th>
        /// <th width="90%">Description</th>
        /// </tr>
        /// <tr valign="top"><td>AppName</td><td>EXE file name</td><td>Name of the application hosting the router</td></tr>
        /// <tr valign="top"><td>AppDescription</td><td>(none)</td><td>Description of the application hosting thr router</td></tr>
        /// <tr valign="top">
        ///     <td>RouterEP</td>
        ///     <td>physical://DETACHED/$(LillTek.DC.DefHubName)/$(Guid)</td>
        ///     <td>
        ///         Physical MsgEP for this instance.  The endpoint should be three levels deep
        ///         such as physical://root.com:40/hub/leaf and the leaf name should be unique across
        ///         all leaf routers beneath the hub.  One way to guarantee uniquness is to use the $(guid)
        ///         environment variable in the endpoint, as in physical://root.com:40/hub/$(MachineName)-$(Guid).
        ///         This will be replaced with a newly generated GUID when the configuration variable
        ///         is processed.
        ///     </td>
        /// </tr>
        /// <tr valign="top">
        ///     <td>DiscoveryMode</td>
        ///     <td>MULTICAST</td>
        ///     <td>
        ///     <para>
        ///     Specifies how the router will go about discovering other routers on the
        ///     network.  The possible values are <b>MULTICAST</b> (the default) and
        ///     <b>UDPBROADCAST</b>.
        ///     </para>
        ///     <para>
        ///     If <b>MULTICAST</b> is specified then the router will broadcast and listen
        ///     for presence packets on the specified <see cref="RouterSettings.CloudAdapter"/> for the
        ///     <see cref="RouterSettings.CloudEP" /> multicast endpoint.
        ///     </para>
        ///     <para>
        ///     If <b>UDPBROADCAST</b> is specified then the router will use the LillTek
        ///     Broadcast Server to handle the transmission and reception presence packets
        ///     on networks that don't support multicast.  The <see cref="RouterSettings.BroadcastSettings" />
        ///     property can be used to configure the internal <see cref="UdpBroadcastClient" />
        ///     used to manage these broadcasts.
        ///     </para>
        ///     </td>
        /// </tr>
        /// <tr valign="top"><td>CloudEP</td><td><see cref="Const.DCCloudEP" /></td><td>The discovery UDP multicast network group and port</td></tr>
        /// <tr valign="top"><td>CloudAdapter</td><td>ANY</td><td>The discovery UDP multicast network adapter address</td></tr>
        /// <tr valign="top"><td>MulticastSendBufferSize</td><td>64K</td><td>UDP multicast socket send buffer size</td></tr>
        /// <tr valign="top"><td>MulticastReceiveBufferSize</td><td>64K</td><td>Multicast socket receive buffer size</td></tr>
        /// <tr valign="top">
        ///     <td>BroadcastSettings</td>
        ///     <td>(see note)</td>
        ///     <td>
        ///     Settings for the <see cref="UdpBroadcastClient" /> used to manage the precence
        ///     packets used for router discovery when operating in <see cref="DiscoveryMode.UdpBroadcast "/>
        ///     discovery mode.  This is initialized with reasonable default values.
        ///     </td>
        /// </tr>
        /// <tr valign="top"><td>UdpEP</td><td>ANY:0</td><td>UDP network endpoint</td></tr>
        /// <tr valign="top"><td>UdpMsgQueueCountMax</td><td>1000</td><td>Max queued outbound UDP normal priority messages.</td></tr>
        /// <tr valign="top"><td>UdpMsgQueueSizeMax</td><td>10MB</td><td>Max bytes of serialized queued outbound UDP normal priority messages.</td></tr>
        /// <tr valign="top"><td>UdpSendBufferSize</td><td>64K</td><td>UDP unicast socket send buffer size</td></tr>
        /// <tr valign="top"><td>UdpReceiveBufferSize</td><td>64K</td><td>UDP unicast socket receive buffer size</td></tr>
        /// <tr valign="top"><td>TcpEP</td><td>ANY:0</td><td>TCP listening network endpoint</td></tr>
        /// <tr valign="top"><td>TcpMsgQueueCountMax</td><td>1000</td><td>Max queued outbound TCP normal priority messages.</td></tr>
        /// <tr valign="top"><td>TcpMsgQueueSizeMax</td><td>10MB</td><td>Max bytes of serialized queued outbound TCP normal priority messages.</td></tr>
        /// <tr valign="top"><td>TcpBacklog</td><td>100</td><td>Max pending connecting TCP sockets</td></tr>
        /// <tr valign="top"><td>TcpDelay</td><td>off</td><td>Enables Nagle on TCP channels</td></tr>
        /// <tr valign="top"><td>TcpSendBufferSize</td><td>64K</td><td>TCP socket send buffer size</td></tr>
        /// <tr valign="top"><td>TcpReceiveBufferSize</td><td>64K</td><td>TCP socket receive buffer size</td></tr>
        /// <tr valign="top"><td>BkInterval</td><td>1s</td><td>Background task interval</td></tr>
        /// <tr valign="top"><td>MaxIdle</td><td>5m</td><td>Maximum time a TCP socket should idle before being closed automatically</td></tr>
        /// <tr valign="top"><td>EnableP2P</td><td>true</td><td>Enables peer-to-peer routing between routers on the same subnet</td></tr>
        /// <tr valign="top"><td>AdvertiseTime</td><td>1m</td><td>RouterAdvertiseMsg multicast interval</td></tr>
        /// <tr valign="top"><td>PhysicalRouteTTL</td><td>3m</td><td>Maximum time a physical route will be maintained without being refreshed with a RouterAdvertiseMsg</td></tr>
        /// <tr valign="top"><td>DefMsgTTL</td><td>5</td><td>Default message time-to-live (max hops)</td></tr>
        /// <tr valign="top"><td>SharedKey</td><td>PLAINTEXT</td><td>The shared encryption key used to encrypt all message traffic.</td></tr>
        /// <tr valign="top"><td>SessionCacheTime</td><td>2m</td><td>Default time the router's session manager will cache idempotent replies.</td></tr>
        /// <tr valign="top"><td>SessionRetries</td><td>3</td><td>Maximum session initiation retries.</td></tr>
        /// <tr valign="top"><td>SessionTimeout</td><td>10s</td><td>Default session timeout</td></tr>
        /// <tr valign="top"><td>MaxLogicalAdvertiseEPs</td><td>256</td><td>Maximum number of logical endpoints to be included in a single LogicalAdvertiseMsg</td></tr>
        /// <tr valign="top"><td>DeadRouterTTL</td><td>0s</td><td>Maximum time to wait for a <see cref="ReceiptMsg" /> before declaring a dead router.  Use 0 to disable dead router detection.</td></tr>
        /// <tr valign="top">
        ///     <td>RouteLocal</td>
        ///     <td>(none)</td>
        ///     <td>
        ///     <para>
        ///     An array of zero or more logical routes for which messages should favor
        ///     local destinations.  These routes may include wildcards.  Here's an example
        ///     configuration fragment:
        ///     </para>
        ///     <code lang="none">
        ///     #section MsgRouter
        ///
        ///         RouteLocal[0] = abstract://Test/Local
        ///         RouteLocal[1] = abstract://MyApps/*
        ///
        ///     #endsection
        ///     </code>
        ///     </td>
        /// </tr>
        /// </table>
        /// </div>
        /// </remarks>
        public void Start()
        {
            RouterSettings settings;
            MsgEP          routerEP;
            Config         config;
            string         v;

            // Load the configuration settings

            config = new Config(MsgHelper.ConfigPrefix);

            v = config.Get("RouterEP", EnvironmentVars.Expand("physical://DETACHED/$(LillTek.DC.DefHubName)/$(Guid)"));

            try
            {
                routerEP = MsgEP.Parse(v);
            }
            catch
            {
                throw new MsgException("[MsgRouter.RouterEP] configuration setting is invalid.");
            }

            if (routerEP.Segments.Length != 2)
            {
                throw new MsgException("[MsgRouter.RouterEP] must specify a valid two segment leaf endpoint (eg: physical://root/hub/leaf).");
            }

            settings                            = new RouterSettings(routerEP);
            settings.AppName                    = config.Get("AppName", settings.AppName);
            settings.AppDescription             = config.Get("AppDescription", settings.AppDescription);
            settings.DiscoveryMode              = config.Get <DiscoveryMode>("DiscoveryMode", settings.DiscoveryMode);
            settings.CloudAdapter               = config.Get("CloudAdapter", settings.CloudAdapter);
            settings.CloudEP                    = config.Get("CloudEP", settings.CloudEP);
            settings.BroadcastSettings          = new UdpBroadcastClientSettings(Config.CombineKeys(MsgHelper.ConfigPrefix, "BroadcastSettings"));
            settings.UdpEP                      = config.Get("UdpEP", settings.UdpEP);
            settings.UdpMsgQueueCountMax        = config.Get("UdpMsgQueueCountMax", settings.UdpMsgQueueCountMax);
            settings.UdpMsgQueueSizeMax         = config.Get("UdpMsgQueueSizeMax", settings.UdpMsgQueueSizeMax);
            settings.TcpEP                      = config.Get("TcpEP", settings.TcpEP);
            settings.TcpMsgQueueCountMax        = config.Get("TcpMsgQueueCountMax", settings.TcpMsgQueueCountMax);
            settings.TcpMsgQueueSizeMax         = config.Get("TcpMsgQueueSizeMax", settings.TcpMsgQueueSizeMax);
            settings.TcpBacklog                 = config.Get("TcpBacklog", settings.TcpBacklog);
            settings.MaxIdle                    = config.Get("MaxIdle", settings.MaxIdle);
            settings.EnableP2P                  = config.Get("EnableP2P", settings.EnableP2P);
            settings.SessionCacheTime           = config.Get("SessionCacheTime", settings.SessionCacheTime);
            settings.SessionRetries             = config.Get("SessionRetries", settings.SessionRetries);
            settings.SessionTimeout             = config.Get("SessionTimeout", settings.SessionTimeout);
            settings.TcpDelay                   = config.Get("TcpDelay", settings.TcpDelay);
            settings.BkInterval                 = config.Get("BkInterval", settings.BkInterval);
            settings.DefMsgTTL                  = config.Get("DefMsgTTL", settings.DefMsgTTL);
            settings.PhysicalRouteTTL           = config.Get("PhysicalRouteTTL", settings.PhysicalRouteTTL);
            settings.MaxLogicalAdvertiseEPs     = config.Get("MaxLogicalAdvertiseEPs", settings.MaxLogicalAdvertiseEPs);
            settings.DeadRouterTTL              = config.Get("DeadRouterTTL", settings.DeadRouterTTL);
            settings.MulticastSendBufferSize    = config.Get("MulticastSendBufferSize", settings.MulticastSendBufferSize);
            settings.MulticastReceiveBufferSize = config.Get("MulticastReceiveBufferSize", settings.MulticastReceiveBufferSize);
            settings.UdpSendBufferSize          = config.Get("UdpSendBufferSize", settings.UdpSendBufferSize);
            settings.UdpReceiveBufferSize       = config.Get("UdpReceiveBufferSize", settings.UdpReceiveBufferSize);
            settings.TcpSendBufferSize          = config.Get("TcpSendBufferSize", settings.TcpSendBufferSize);
            settings.TcpReceiveBufferSize       = config.Get("TcpReceiveBufferSize", settings.TcpReceiveBufferSize);
            settings.AdvertiseTime              = config.Get("AdvertiseTime", settings.AdvertiseTime);

            v = config.Get("SharedKey");
            if (!string.IsNullOrWhiteSpace(v))
            {
                try
                {
                    settings.SharedKey = new SymmetricKey(v);
                }
                catch
                {
                    // Ignoring
                }
            }

            // Get the local route endpoints

            foreach (string ep in config.GetArray("RouteLocal"))
            {
                settings.LocalityMap.Add(ep);
            }

            Start(settings);
        }
예제 #2
0
        /// <summary>
        /// Starts the router using the configuration settings passed.
        /// </summary>
        /// <param name="settings">The configuration settings.</param>
        public void Start(RouterSettings settings)
        {
            IPAddress  cloudAdapter;
            IPEndPoint cloudEP;
            IPEndPoint udpEP;
            IPEndPoint tcpEP;
            int        tcpBacklog;
            TimeSpan   maxIdle;

            this.RouterEP = settings.RouterEP;
            if (this.RouterEP.Segments.Length != 2)
            {
                throw new MsgException("RouterEP must specify a valid two segment leaf endpoint (physical://root/hub/leaf).");
            }

            Trace(0, "Router Start: " + this.AppName, this.RouterEP.ToString(), string.Empty);

            cloudAdapter = settings.CloudAdapter;
            cloudEP      = settings.CloudEP;
            udpEP        = settings.UdpEP;
            tcpEP        = settings.TcpEP;
            tcpBacklog   = settings.TcpBacklog;
            maxIdle      = settings.MaxIdle;

            base.AppName                = settings.AppName;
            base.AppDescription         = settings.AppDescription;
            base.DiscoveryMode          = settings.DiscoveryMode;
            base.BroadcastSettings      = settings.BroadcastSettings;
            base.EnableP2P              = settings.EnableP2P;
            base.SessionCacheTime       = settings.SessionCacheTime;
            base.SessionRetries         = settings.SessionRetries;
            base.SessionTimeout         = settings.SessionTimeout;
            base.TcpMsgQueueCountMax    = settings.TcpMsgQueueCountMax;
            base.TcpMsgQueueSizeMax     = settings.TcpMsgQueueSizeMax;
            base.TcpDelay               = settings.TcpDelay;
            base.BkInterval             = settings.BkInterval;
            base.DefMsgTTL              = settings.DefMsgTTL;
            base.PhysRouteTTL           = settings.PhysicalRouteTTL;
            base.MaxLogicalAdvertiseEPs = settings.MaxLogicalAdvertiseEPs;
            base.DeadRouterTTL          = settings.DeadRouterTTL;
            base.UdpMsgQueueCountMax    = settings.UdpMsgQueueCountMax;
            base.UdpMsgQueueSizeMax     = settings.UdpMsgQueueSizeMax;
            base.UdpMulticastSockConfig = new SocketConfig(settings.MulticastSendBufferSize, settings.MulticastReceiveBufferSize);
            base.UdpUnicastSockConfig   = new SocketConfig(settings.UdpSendBufferSize, settings.MulticastReceiveBufferSize);
            base.TcpSockConfig          = new SocketConfig(settings.TcpSendBufferSize, settings.TcpReceiveBufferSize);

            this.advertiseTime = settings.AdvertiseTime;

            // Crank this sucker up

            using (TimedLock.Lock(this.SyncRoot))
            {
                base.PhysicalRoutes = new PhysicalRouteTable(this, base.PhysRouteTTL);
                base.LogicalRoutes  = new LogicalRouteTable(this);

                base.SetDispatcher(new MsgDispatcher(this));
                base.Dispatcher.AddTarget(this);
                base.EnableEncryption(settings.SharedKey);
                base.Start(cloudAdapter, cloudEP, udpEP, tcpEP, tcpBacklog, maxIdle);

                lastAdvertise  = SysTime.Now + advertiseTime;
                this.isRunning = true;

                Multicast(new RouterAdvertiseMsg(this.RouterEP, this.AppName, this.AppDescription, this.RouterInfo,
                                                 this.UdpEP.Port, this.TcpEP.Port, this.Dispatcher.LogicalEndpointSetID, true, this.EnableP2P));
            }

            // Pause a second to give the router a chance to discover the local hub.

            Thread.Sleep(1000);
        }
예제 #3
0
 /// <summary>
 /// Starts the router using the configuration settings passed.
 /// </summary>
 /// <param name="settings">The configuration settings.</param>
 public new void Start(RouterSettings settings)
 {
     base.StartAsRoot(settings);
 }