示例#1
0
        private RouteDistance distance;                         // Physical distance from the current router
                                                                // (computed when a route is added to a LogicalRouteTable)

        /// <summary>
        /// Constructs a logical route that maps to an application
        /// message handler.
        /// </summary>
        /// <param name="logicalEP">The logical endpoint.</param>
        /// <param name="msgType">The fully qualified name of the message type handled.</param>
        /// <param name="handler">The message handler.</param>
        /// <remarks>
        /// This constructor creates and initializes the instance's Handlers
        /// hash table with the single entry specified by the msgType (the key)
        /// and handler (the value) parameters.
        /// </remarks>
        internal LogicalRoute(MsgEP logicalEP, string msgType, MsgHandler handler)
        {
            if (logicalEP.IsPhysical)
            {
                throw new ArgumentException("Logical endpoint expected.", "logicalEP");
            }

            this.logicalEP     = logicalEP;
            this.physicalRoute = null;
            this.targetGroup   = handler.Target;
            this.handlers      = new Dictionary <string, MsgHandler>();
            this.marked        = false;
            this.distance      = RouteDistance.Unknown;

            this.handlers.Add(msgType, handler);
        }
示例#2
0
        /// <summary>
        /// Constructs a logical route that maps to a physical route.
        /// </summary>
        /// <param name="logicalEP">The logical endpoint.</param>
        /// <param name="physicalRoute">The associated physical route.</param>
        internal LogicalRoute(MsgEP logicalEP, PhysicalRoute physicalRoute)
        {
            Assertion.Test(physicalRoute != null);

            if (logicalEP.IsPhysical)
            {
                throw new ArgumentException("Logical endpoint expected.", "logicalEP");
            }

            this.logicalEP     = logicalEP;
            this.physicalRoute = physicalRoute;
            this.targetGroup   = null;
            this.handlers      = null;
            this.marked        = false;
            this.distance      = RouteDistance.Unknown;
        }
示例#3
0
        /// <summary>
        /// Initiates tracking for <see cref="ReceiptMsg" /> messages received
        /// by the associated router.
        /// </summary>
        /// <param name="route">The physical route the message is being forwarded to.</param>
        /// <param name="msg">The message being tracked.</param>
        public void Track(PhysicalRoute route, Msg msg)
        {
            MsgTrack track;

            if (!router.DeadRouterDetection)
            {
                return;
            }

            Assertion.Test((msg._Flags & MsgFlag.ReceiptRequest) != 0, "Message is not properly configured for receipt tracking");
            Assertion.Test(msg._MsgID != Guid.Empty, "Message is not properly configured for receipt tracking");

            track = new MsgTrack(route.RouterEP, route.LogicalEndpointSetID, msg._MsgID, SysTime.Now + router.DeadRouterTTL);
            using (TimedLock.Lock(router.SyncRoot))
            {
                msgTracks.Add(msg._MsgID, track);
            }
        }
示例#4
0
        /// <summary>
        /// Computes the <see cref="RouteDistance" /> between the associated <see cref="MsgRouter" />
        /// and a <see cref="LogicalRoute" />.
        /// </summary>
        /// <param name="logicalRoute">The first <see cref="LogicalRoute" />.</param>
        /// <returns>The computed <see cref="RouteDistance" />.</returns>
        internal RouteDistance ComputeDistance(LogicalRoute logicalRoute)
        {
            if (logicalRoute.Handlers != null)
            {
                return(RouteDistance.Process);
            }
            else if (router.RouterEP == null)
            {
                return(RouteDistance.Unknown);
            }

            MsgEP         routerEP    = router.RouterEP;
            MsgEP         targetEP    = logicalRoute.PhysicalRoute.RouterEP;
            PhysicalRoute physical    = logicalRoute.PhysicalRoute;
            int           routerLevel = routerEP.Segments.Length;
            int           targetLevel = targetEP.Segments.Length;
            bool          sameIP      = physical.TcpEP != null && router.TcpEP.Address.Equals(physical.TcpEP.NetEP.Address);

            if (routerEP.IsPhysicalMatch(targetEP))
            {
                // The routes match so we're in the same process.

                return(RouteDistance.Process);
            }

            if (routerLevel == targetLevel)
            {
                // The endpoints are at the same level in the heirarchy.

                switch (routerLevel)
                {
                case 0:

                    // Both routers are at the root level

                    if (sameIP)
                    {
                        return(RouteDistance.Machine);
                    }
                    else
                    {
                        return(RouteDistance.Subnet);
                    }

                case 1:

                    // Must be hub routers on different subnets

                    return(RouteDistance.External);

                case 2:

                    // Both routes are to leaf routers.

                    if (routerEP.IsPhysicalPeer(targetEP))
                    {
                        if (sameIP)
                        {
                            return(RouteDistance.Machine);
                        }
                        else
                        {
                            return(RouteDistance.Subnet);
                        }
                    }

                    // If not peers, then they must be in different datacenters.

                    return(RouteDistance.External);

                default:

                    throw new NotImplementedException();
                }
            }

            // The endpoints are at different levels in the heirarchy.  Normalize
            // these so that higherEP and higherLevel specified the route target
            // that is higher in the heirarchy and lowerEP and lowerLevel the
            // target lower in the heirarchy.

            MsgEP higherEP;
            int   higherLevel;
            MsgEP lowerEP;
            int   lowerLevel;

            if (routerLevel < targetLevel)
            {
                higherEP    = routerEP;
                higherLevel = routerLevel;
                lowerEP     = targetEP;
                lowerLevel  = targetLevel;
            }
            else
            {
                higherEP    = targetEP;
                higherLevel = targetLevel;
                lowerEP     = routerEP;
                lowerLevel  = routerLevel;
            }

            if (higherLevel == 1 && lowerLevel == 2 && higherEP.IsPhysicalDescendant(lowerEP))
            {
                // The higher level endpoint is on a hub and the lower level endpoint is
                // on a router under the hub so they're on the same subnet.

                return(RouteDistance.Subnet);
            }

            // All remaining cases will be considered to be external since
            // they can't be on the same subnet.

            return(RouteDistance.External);
        }