コード例 #1
0
ファイル: Messages.cs プロジェクト: RELOAD-NET/RELOAD.NET
        public ReloadMessage(ReloadConfig rc, NodeId OriginatorNodeID,
          Destination destination, UInt64 trans_id, RELOAD_MessageBody reload_content)
        {
            m_ReloadConfig = rc;
            forwarding_header.version = ReloadGlobals.RELOAD_VERSION;
            forwarding_header.ttl = ReloadGlobals.TTL;
            forwarding_header.overlay = m_ReloadConfig.OverlayHash;
            forwarding_header.transaction_id = trans_id;

            reload_message_body = reload_content;

            forwarding_header.via_list = new List<Destination>();
            forwarding_header.via_list.Add(new Destination(OriginatorNodeID));

            forwarding_header.destination_list = new List<Destination>();
            forwarding_header.destination_list.Add(destination);
            SignerIdentity myId = m_ReloadConfig.AccessController.MyIdentity;
            security_block = new SecurityBlock(rc, myId);
            /* Sign the message, create stream of body */

            security_block.SignMessage(m_ReloadConfig.OverlayHash,
              trans_id.ToString(), reload_message_body);
        }
コード例 #2
0
ファイル: Transport.cs プロジェクト: RELOAD-NET/RELOAD.NET
 /// <summary>
 /// Creates a FetchAns
 /// </summary>
 /// <param name="destination"></param>
 /// <param name="p"></param>
 /// <param name="fetchKindResponses"></param>
 /// <returns></returns>
 private ReloadMessage create_fetch_answ(Destination destination, UInt64 trans_id, List<FetchKindResponse> fetchKindResponses)
 {
     return create_reload_message(destination, trans_id, new FetchAns(fetchKindResponses, m_machine.UsageManager));
 }
コード例 #3
0
ファイル: Transport.cs プロジェクト: RELOAD-NET/RELOAD.NET
        public IEnumerator<ITask> AppAttachProcedure(Destination dest)
        {
            ReloadMessage reloadSendMsg;

            reloadSendMsg = create_app_attach_req(dest);

            if (dest.type != DestinationType.node)
            {
                m_ReloadConfig.Logger(ReloadGlobals.TRACEFLAGS.T_ERROR, String.Format("AppAttachProcedure failed: unexpected destination type"));
                yield break;
            }

            if (dest.destination_data.node_id == m_topology.Id)
            {
                m_ReloadConfig.Logger(ReloadGlobals.TRACEFLAGS.T_INFO, String.Format("local AppAttachProcedure dropped"));
                yield break;
            }

            Node node = m_topology.routing_table.FindNextHopTo(dest.destination_data.node_id, true, false);

            if (node == null)
            {
                m_ReloadConfig.Logger(ReloadGlobals.TRACEFLAGS.T_ERROR, String.Format("AppAttachProcedure: failed, did not found next hop to {0}", dest.destination_data.node_id));
                yield break;
            }

            ReloadDialog reloadDialog = null;

            int RetransmissionTime = ReloadGlobals.RetransmissionTime + ReloadGlobals.MaxTimeToSendPacket;
            int iRetrans = ReloadGlobals.MaxRetransmissions;

            m_topology.routing_table.SetNodeState(dest.destination_data.node_id,
              NodeState.attaching);

            while (iRetrans >= 0 && m_ReloadConfig.State < ReloadConfig.RELOAD_State.Shutdown)
            {
                try
                {
                    /* use a new ReloadDialog instance for every usage, Monitor requires it                         */
                    reloadDialog = new ReloadDialog(m_ReloadConfig, m_flm, node);

                    m_ReloadConfig.Logger(ReloadGlobals.TRACEFLAGS.T_RELOAD,
                      String.Format("{0} via {1} ==> Dest={2} TransId={3:x16}",
                      RELOAD_MessageCode.App_Attach_Request.ToString().PadRight(16, ' '),
                      node, dest.ToString(), reloadSendMsg.TransactionID));

                    Arbiter.Activate(m_DispatcherQueue,
                      new IterativeTask<ReloadMessage, ReloadMessageFilter, int>(
                      reloadSendMsg, new ReloadMessageFilter(reloadSendMsg.TransactionID),
                      RetransmissionTime, reloadDialog.Execute));
                }
                catch (Exception ex)
                {
                    m_ReloadConfig.Logger(ReloadGlobals.TRACEFLAGS.T_ERROR, "AppAttachProcedure: " + ex.Message);
                }

                yield return Arbiter.Receive(false, reloadDialog.Done, done => { });


                if (!reloadDialog.Error && reloadDialog.ReceivedMessage != null)
                    break;

                /* If a response has not been received when the timer fires, the request
                   is retransmitted with the same transaction identifier. 
                */
                --iRetrans;
            }

            try
            {
                if (!reloadDialog.Error && reloadDialog.ReceivedMessage != null)
                {
                    //the SourceNodeID delivered from reloadDialog comes from connection table and is the last hop of the message
                    ReloadMessage reloadRcvMsg = reloadDialog.ReceivedMessage;

                    if (reloadRcvMsg.reload_message_body.RELOAD_MsgCode == RELOAD_MessageCode.App_Attach_Answer)
                    {
                        AppAttachReqAns answ = (AppAttachReqAns)reloadRcvMsg.reload_message_body;

                        if (answ != null)
                        {
                            node = new Node(reloadRcvMsg.OriginatorID, answ.ice_candidates);
                            /*  An Attach in and of itself does not result in updating the routing
                             *  table of either node.
                             *  Note: We use the routing table here only for storing ice candidates 
                             *  for later use, we will not update successor or predecessor list
                             */
                            m_topology.routing_table.AddNode(node);
                            if (m_topology.routing_table.GetNodeState(node.Id) < NodeState.attached)
                                m_topology.routing_table.SetNodeState(node.Id, NodeState.attached);

                            m_ReloadConfig.Logger(ReloadGlobals.TRACEFLAGS.T_RELOAD, String.Format("{0} <== {1} last={2} TransId={3:x16}",
                                reloadRcvMsg.reload_message_body.RELOAD_MsgCode.ToString().PadRight(16, ' '), reloadRcvMsg.OriginatorID, reloadRcvMsg.LastHopNodeId, reloadRcvMsg.TransactionID));

                            m_ReloadConfig.Logger(ReloadGlobals.TRACEFLAGS.T_USAGE,
                                String.Format("AppAttach returns IP: {0}",
                                    answ.ice_candidates[0].addr_port.ipaddr.ToString()));
                            /* Proprietary registry interface function to support external clients */
                            ReloadGlobals.StoreRegAnswer("sip:" + answ.ice_candidates[0].addr_port.ipaddr.ToString() + ":5060");
                            m_ReloadConfig.ConnEstEnd = DateTime.Now;
                            if (AppAttachDone != null) appAttachDone.Post(answ.ice_candidates[0]);
                            if (ReloadGlobals.AutoExe)
                            {
                                TimeSpan appAttachTime = DateTime.Now - m_ReloadConfig.StartFetchAttach;
                                m_ReloadConfig.Logger(ReloadGlobals.TRACEFLAGS.T_MEASURE, String.Format("Fetch:{0}", appAttachTime.TotalSeconds));
                            }
                        }
                    }
                    else if (reloadRcvMsg.reload_message_body.RELOAD_MsgCode == RELOAD_MessageCode.Error)
                    {
                        // TODO
                    }
                }
                else
                {
                    m_topology.routing_table.SetNodeState(dest.destination_data.node_id, NodeState.unknown);
                }
            }
            catch (Exception ex)
            {
                m_ReloadConfig.Logger(ReloadGlobals.TRACEFLAGS.T_ERROR, "AppAttachProcedure: " + ex.Message);
                m_topology.routing_table.SetNodeState(dest.destination_data.node_id, NodeState.unknown);
            }
        }
コード例 #4
0
ファイル: Transport.cs プロジェクト: RELOAD-NET/RELOAD.NET
 public ReloadMessage create_ping_answ(Destination destination, UInt64 trans_id)
 {
     Random rand = new Random();
     return create_reload_message(destination, trans_id, new PingReqAns((UInt64)rand.Next(int.MinValue, int.MaxValue), false));
 }
コード例 #5
0
ファイル: Transport.cs プロジェクト: RELOAD-NET/RELOAD.NET
 /// <summary>
 /// Creates a StoreAns message accoriding to RELOAD base -12 p.90
 /// </summary>
 /// <param name="destination">The answer destination address</param>
 /// <param name="trans_id">The transaction ID corresponding to the StoreReq</param>
 /// <param name="usage">The Usage data corresponding to the StoreReq</param>
 /// <returns></returns>
 public ReloadMessage create_store_answ(Destination dest,
   UInt64 trans_id, List<StoreKindData> skd, List<NodeId> replicas)
 {
     return create_reload_message(dest, trans_id, new StoreAns(skd, replicas));
 }
コード例 #6
0
ファイル: Transport.cs プロジェクト: RELOAD-NET/RELOAD.NET
 public ReloadMessage create_update_answ(Destination destination, UInt64 trans_id, RELOAD_ErrorCode result)
 {
     return create_reload_message(destination, trans_id, new UpdateReqAns(result));
 }
コード例 #7
0
ファイル: Transport.cs プロジェクト: RELOAD-NET/RELOAD.NET
 public ReloadMessage create_leave_answ(Destination destination, UInt64 trans_id)
 {
     return create_reload_message(destination, trans_id, new LeaveReqAns(m_topology.LocalNode, false));
 }
コード例 #8
0
ファイル: Transport.cs プロジェクト: RELOAD-NET/RELOAD.NET
        /// <summary>
        /// Proprietary: Tries to fetch the Data specified by the StoredDataSpecifier List from different RELOAD overlay using viaGateWay as gateway
        /// </summary>
        /// <param name="resourceName"></param>
        /// <param name="specifiers"></param>
        /// <param name="viaGateWay"></param>
        /// <returns></returns>
        public IEnumerator<ITask> Fetch(string resourceName, List<StoredDataSpecifier> specifiers, NodeId viaGateWay)
        {
            ReloadDialog reloadDialog = null;
            ReloadMessage reloadSendMsg;
            List<IUsage> recUsages = new List<IUsage>();
            ResourceId res_id = new ResourceId(resourceName);

            Node node = null;
            List<FetchKindResponse> fetchKindResponses = new List<FetchKindResponse>();
            FetchKindResponse fetchKindResponse = null;

            if (viaGateWay != null)
            {

                m_ReloadConfig.Logger(ReloadGlobals.TRACEFLAGS.T_USAGE, String.Format("Fetch {0} as ResID: {1} via Gateway {2}", resourceName, res_id, viaGateWay));

                node = m_topology.routing_table.FindNextHopTo(viaGateWay, true, false);
                //node = m_topology.routing_table.FindNextHopTo(new NodeId(res_id), true, false);

                if (m_ReloadConfig.IamClient && node == null)
                {
                    node = m_ReloadConfig.AdmittingPeer;
                }

                Destination gateway = new Destination(new NodeId(viaGateWay.Data));
                Destination fetchDestination = new Destination(res_id);
                //reloadSendMsg = create_fetch_req(gateway, specifiers);
                FetchReq fetchRequest = new FetchReq(fetchDestination.destination_data.ressource_id,
                                                      specifiers,
                                                      m_machine.UsageManager);

                reloadSendMsg = create_reload_message(gateway, ++m_ReloadConfig.TransactionID, fetchRequest);
                reloadSendMsg.forwarding_header.destination_list.Add(fetchDestination);

                //reloadSendMsg = create_fetch_req(new Destination(res_id), specifiers);
                //reloadSendMsg.AddViaHeader(viaGateWay);

                if (reloadSendMsg.AddDestinationOverlay(resourceName))
                    m_ReloadConfig.Logger(ReloadGlobals.TRACEFLAGS.T_ERROR, "AddDestinationOverlay successful");
            }
            else
            {

                m_ReloadConfig.Logger(ReloadGlobals.TRACEFLAGS.T_USAGE,
                  String.Format("Fetch {0} as ResID: {1}", resourceName, res_id));

                node = m_topology.routing_table.FindNextHopTo(new NodeId(res_id), true, false);

                if (m_ReloadConfig.IamClient && node == null)
                {
                    node = m_ReloadConfig.AdmittingPeer;
                }

                List<Destination> dest_list = new List<Destination>();
                dest_list.Add(new Destination(m_topology.LocalNode.Id));

                if (node == null || node.Id == m_ReloadConfig.LocalNodeID)
                {
                    m_ReloadConfig.Logger(ReloadGlobals.TRACEFLAGS.T_TOPO, "Local Fetch.");
                    m_ReloadConfig.StartFetchAttach = DateTime.Now;
                    foreach (StoredDataSpecifier specifier in specifiers)
                    {
                        var responses = new List<FetchKindResponse>();
                        if (m_topology.Fetch(res_id, specifier, out fetchKindResponse))
                        {
                            responses.Add(fetchKindResponse);
                            foreach (StoredData sd in fetchKindResponse.values)
                            {
                                if (m_ReloadConfig.AccessController.validateDataSignature(res_id, fetchKindResponse.kind, sd))
                                    recUsages.Add(sd.Value.GetUsageValue);
                                else
                                {
                                    m_ReloadConfig.Logger(ReloadGlobals.TRACEFLAGS.T_TOPO, "DATA SIGNATURE INVALID!!");
                                }
                                m_ReloadConfig.Logger(ReloadGlobals.TRACEFLAGS.T_TOPO,
                                    String.Format("Fetch successful, got {0}",
                                        sd.Value.GetUsageValue.Report()));
                            }
                            m_ReloadConfig.ConnEstEnd = DateTime.Now;
                        }
                        OnFetchedData(res_id, responses);
                    }


                    if (fetchDone != null)
                    {
                        if (recUsages.Count == 0)
                        {
                            foreach (StoredDataSpecifier specifier in specifiers)
                                recUsages.Add(new NoResultUsage(specifier.ResourceName));
                        }
                        fetchDone.Post(recUsages);
                    }
                    yield break;
                }
                else
                {
                    reloadSendMsg = create_fetch_req(new Destination(res_id), specifiers);
                }
            }

            int RetransmissionTime = ReloadGlobals.RetransmissionTime +
              ReloadGlobals.MaxTimeToSendPacket;

            int iRetrans = ReloadGlobals.MaxRetransmissions;

            while (iRetrans >= 0 &&
              m_ReloadConfig.State < ReloadConfig.RELOAD_State.Shutdown)
            {
                try
                {
                    reloadDialog = new ReloadDialog(m_ReloadConfig, m_flm, node);

                    m_ReloadConfig.Logger(ReloadGlobals.TRACEFLAGS.T_RELOAD,
                      String.Format("{0} ==> {1} TransId={2:x16}",
                        reloadSendMsg.reload_message_body.RELOAD_MsgCode.ToString().
                        PadRight(16, ' '), node.Id, reloadSendMsg.TransactionID));
                    m_ReloadConfig.StartFetchAttach = DateTime.Now;
                    Arbiter.Activate(m_DispatcherQueue,
                      new IterativeTask<ReloadMessage, ReloadMessageFilter, int>(
                      reloadSendMsg, new ReloadMessageFilter(reloadSendMsg.TransactionID),
                      RetransmissionTime, reloadDialog.Execute));
                }
                catch (Exception ex)
                {
                    fetchDone.Post(new List<IUsage> { new NullUsage() });
                    m_ReloadConfig.Logger(ReloadGlobals.TRACEFLAGS.T_ERROR,
                      "Fetch: " + ex.Message);
                }

                yield return Arbiter.Receive(false, reloadDialog.Done, done => { });

                if (!reloadDialog.Error && reloadDialog.ReceivedMessage != null)
                    break;


                /* If a response has not been received when the timer fires, the request
                   is retransmitted with the same transaction identifier. 
                */
                --iRetrans;
            }

            try
            {
                if (!reloadDialog.Error && reloadDialog.ReceivedMessage != null)
                {
                    //the SourceNodeID delivered from reloadDialog comes from connection table and is the last hop of the message
                    ReloadMessage reloadRcvMsg = reloadDialog.ReceivedMessage;
                    RELOAD_MessageCode recMsgCode = reloadRcvMsg.reload_message_body.RELOAD_MsgCode;
                    if (recMsgCode == RELOAD_MessageCode.Fetch_Answer)
                    {
                        m_ReloadConfig.Logger(ReloadGlobals.TRACEFLAGS.T_RELOAD,
                          String.Format("{0} <== {1} TransId={2:x16}",
                            recMsgCode.ToString().PadRight(16, ' '), reloadRcvMsg.OriginatorID,
                              reloadRcvMsg.TransactionID));
                        FetchAns answ = (FetchAns)reloadRcvMsg.reload_message_body;

                        if (answ != null)
                        {
                            fetchKindResponses = answ.KindResponses;
                            foreach (FetchKindResponse kind in fetchKindResponses)
                            {
                                foreach (StoredData sd in kind.values)
                                {
                                    if (m_ReloadConfig.AccessController.validateDataSignature(res_id, kind.kind, sd))
                                        recUsages.Add(sd.Value.GetUsageValue);
                                    else
                                    {
                                        m_ReloadConfig.Logger(ReloadGlobals.TRACEFLAGS.T_TOPO, "DATA SIGNATURE INVALID!!");
                                    }
                                    m_ReloadConfig.Logger(ReloadGlobals.TRACEFLAGS.T_TOPO,
                                      String.Format("Fetch successful, got {0}",
                                        sd.Value.GetUsageValue.Report()));
                                }
                            }
                            OnFetchedData(res_id, fetchKindResponses);
                            if (fetchDone != null)
                            {
                                if (recUsages.Count == 0)
                                {
                                    foreach (StoredDataSpecifier specifier in specifiers)
                                        recUsages.Add(new NoResultUsage(specifier.ResourceName));
                                }
                                fetchDone.Post(recUsages);
                            }
                        }
                    }
                }
                else
                {
                    m_ReloadConfig.Logger(ReloadGlobals.TRACEFLAGS.T_WARNING, String.Format("Fetch failed"));
                    foreach (StoredDataSpecifier specifier in specifiers)
                        recUsages.Add(new NoResultUsage(specifier.ResourceName));
                    fetchDone.Post(recUsages);
                    m_statistics.IncTransmissionError();
                }
            }
            catch (Exception ex)
            {
                m_ReloadConfig.Logger(ReloadGlobals.TRACEFLAGS.T_ERROR, "Fetch: " + ex.Message);
            }
        }
コード例 #9
0
ファイル: Transport.cs プロジェクト: RELOAD-NET/RELOAD.NET
        public IEnumerator<ITask> SendUpdate(Node node, Node nexthopnode)
        {
            ReloadDialog reloadDialog = null;
            ReloadMessage reloadSendMsg;

            /*if (m_topology.routing_table.isFinger(node.Id))
              m_topology.routing_table.AddFinger(node);*/

            if (nexthopnode == null)
                nexthopnode = node;

            Destination dest = new Destination(node.Id);

            reloadSendMsg = create_update_req(dest, m_topology.routing_table,
              ChordUpdateType.neighbors);

            int RetransmissionTime = ReloadGlobals.RetransmissionTime +
               ReloadGlobals.MaxTimeToSendPacket;
            int iRetrans = ReloadGlobals.MaxRetransmissions;

            while (iRetrans >= 0 && m_ReloadConfig.State < ReloadConfig.RELOAD_State.Shutdown)
            {
                try
                {
                    reloadDialog = new ReloadDialog(m_ReloadConfig, m_flm, nexthopnode);

                    m_ReloadConfig.Logger(ReloadGlobals.TRACEFLAGS.T_RELOAD,
                      String.Format("{0} ==> {1} TransId={2:x16}",
                      RELOAD_MessageCode.Update_Request.ToString().PadRight(16, ' '),
                      node.Id, reloadSendMsg.TransactionID));
                    //m_ReloadConfig.start
                    Arbiter.Activate(m_DispatcherQueue,
                      new IterativeTask<ReloadMessage, ReloadMessageFilter, int>(
                      reloadSendMsg, new ReloadMessageFilter(reloadSendMsg.TransactionID),
                      RetransmissionTime, reloadDialog.Execute));
                }
                catch (Exception ex)
                {
                    m_ReloadConfig.Logger(ReloadGlobals.TRACEFLAGS.T_ERROR,
                      "Send Update: " + ex.Message);
                    yield break;
                }

                yield return Arbiter.Receive(false, reloadDialog.Done, done => { });

                if (!reloadDialog.Error && reloadDialog.ReceivedMessage != null)
                    break;

                /* If a response has not been received when the timer fires, the request
                   is retransmitted with the same transaction identifier. 
                */
                --iRetrans;
                if (iRetrans > 0)
                {
                    m_ReloadConfig.Logger(ReloadGlobals.TRACEFLAGS.T_WARNING,
                      String.Format("Retrans {0} SendUpdate  {1}:{2} TransId={3:x16}",
                      iRetrans, node, nexthopnode, reloadSendMsg.TransactionID));
                    m_statistics.IncRetransmission();
                }
                else
                {
                    m_ReloadConfig.Logger(ReloadGlobals.TRACEFLAGS.T_ERROR,
                      String.Format("Failed! SendUpdate  {0}:{1} TransId={2:x16}",
                      node, nexthopnode, reloadSendMsg.TransactionID));
                    m_statistics.IncTransmissionError();
                }
            }

            try
            {
                if (!reloadDialog.Error && reloadDialog.ReceivedMessage != null)
                {
                    //the SourceNodeID delivered from reloadDialog comes from connection table and is the last hop of the message
                    ReloadMessage reloadRcvMsg = reloadDialog.ReceivedMessage;
                    RELOAD_MessageCode msgCode = reloadRcvMsg.reload_message_body.RELOAD_MsgCode;
                    if (msgCode == RELOAD_MessageCode.Update_Answer)
                    {
                        m_ReloadConfig.Logger(ReloadGlobals.TRACEFLAGS.T_RELOAD,
                          String.Format("{0} <== {1} TransId={2:x16}",
                          msgCode.ToString().PadRight(16, ' '), reloadRcvMsg.OriginatorID,
                          reloadRcvMsg.TransactionID));

                        UpdateReqAns answ = (UpdateReqAns)reloadRcvMsg.reload_message_body;

                        if (answ != null)
                        {
                            NodeId originator = reloadRcvMsg.OriginatorID;

                            if (m_topology.routing_table.FingerSuccessors.Contains(originator))
                            {
                                //m_topology.routing_table.GetNode(originator).Successors = answ.Successors;
                                //m_topology.routing_table.GetNode(originator).Predecessors = answ.Predecessors;
                                m_topology.routing_table.SetFingerState(originator,
                                  NodeState.updates_received);
                            }
                            if (m_topology.routing_table.RtTable.ContainsKey(originator.ToString()))
                            {
                                m_topology.routing_table.SetNodeState(originator,
                                  NodeState.updates_received);
                                m_topology.routing_table.GetNode(originator).Successors = answ.Successors;
                                m_topology.routing_table.GetNode(originator).Predecessors = answ.Predecessors;
                            }
                        }
                    }
                }
            }
            catch (Exception ex)
            {
                m_ReloadConfig.Logger(ReloadGlobals.TRACEFLAGS.T_ERROR,
                  "Send Update: " + ex.Message);
            }
        }
コード例 #10
0
ファイル: Transport.cs プロジェクト: RELOAD-NET/RELOAD.NET
        public IEnumerator<ITask> SendPing(Destination dest, PingOption pingOption)
        {
            ReloadDialog reloadDialog = null;
            ReloadMessage reloadSendMsg;

            reloadSendMsg = create_ping_req(dest);

            int RetransmissionTime = ReloadGlobals.RetransmissionTime + ReloadGlobals.MaxTimeToSendPacket;

            Boolean NextHopIsDestination = false;
            Node NextHopNode = NextHopToDestination(dest, ref NextHopIsDestination);

            if (NextHopNode == null)
                yield break;

            if (NextHopNode.Id == m_topology.LocalNode.Id)
                yield break;

            if (dest.type == DestinationType.node)
            {
                /* This code assumes, that a node we want to ping is already attached and added to the routing table */
                NodeState nodestate = m_topology.routing_table.GetNodeState(dest.destination_data.node_id);
                bool pinging = m_topology.routing_table.GetPing(dest.destination_data.node_id);

                if (((pingOption & PingOption.standard | PingOption.finger) != 0) && nodestate == NodeState.unknown && !pinging)
                {
                    m_ReloadConfig.Logger(ReloadGlobals.TRACEFLAGS.T_INFO, String.Format("Ignoring redundant Ping for {0}", dest));
                    yield break;
                }
                m_topology.routing_table.SetPinging(dest.destination_data.node_id, true, false);
            }
            else if (!NextHopIsDestination && ((pingOption & PingOption.direct) != 0))
            {
                m_ReloadConfig.Logger(ReloadGlobals.TRACEFLAGS.T_ERROR, String.Format("Direct Ping for {0} ignored, no entry in routing table", dest));
                yield break;
            }


            /* Don't spend too much time on connectivity checks */
            int iRetrans = 3;

            while (iRetrans > 0 && m_ReloadConfig.State < ReloadConfig.RELOAD_State.Shutdown)
            {
                try
                {
                    reloadDialog = new ReloadDialog(m_ReloadConfig, m_flm, NextHopNode);

                    m_ReloadConfig.Logger(ReloadGlobals.TRACEFLAGS.T_RELOAD, String.Format("{0} ==> {1} TransId={2:x16}",
                        reloadSendMsg.reload_message_body.RELOAD_MsgCode.ToString().PadRight(16, ' '), NextHopNode.Id, reloadSendMsg.TransactionID));

                    Arbiter.Activate(m_DispatcherQueue, new IterativeTask<ReloadMessage, ReloadMessageFilter, int>(reloadSendMsg, new ReloadMessageFilter(reloadSendMsg.TransactionID), RetransmissionTime, reloadDialog.Execute));
                }
                catch (Exception ex)
                {
                    m_ReloadConfig.Logger(ReloadGlobals.TRACEFLAGS.T_ERROR, "Send Ping: " + ex.Message);
                    yield break;
                }

                yield return Arbiter.Receive(false, reloadDialog.Done, done => { });

                if (!reloadDialog.Error && reloadDialog.ReceivedMessage != null)
                    break;

                /*              If a response has not been received when the timer fires, the request
                                is retransmitted with the same transaction identifier.
                */
                --iRetrans;
            }

            try
            {
                PingReqAns answ = null;

                if (reloadDialog != null && !reloadDialog.Error && reloadDialog.ReceivedMessage != null)
                {
                    //the SourceNodeID delivered from reloadDialog comes from connection table and is the last hop of the message
                    ReloadMessage reloadRcvMsg = reloadDialog.ReceivedMessage;

                    if (reloadRcvMsg.reload_message_body.RELOAD_MsgCode == RELOAD_MessageCode.Ping_Answer)
                    {
                        m_ReloadConfig.Logger(ReloadGlobals.TRACEFLAGS.T_RELOAD, String.Format("{0} <== {1} TransId={2:x16}", reloadRcvMsg.reload_message_body.RELOAD_MsgCode.ToString().PadRight(16, ' '), reloadRcvMsg.OriginatorID, reloadRcvMsg.TransactionID));

                        answ = (PingReqAns)reloadRcvMsg.reload_message_body;

                        if (answ != null)
                        {
                            if ((pingOption & PingOption.finger) != 0)
                            {
                                foreach (Topology.TopologyPlugin.RoutingTable.FTableEntry fte in m_topology.routing_table.FingerTable)
                                {
                                    if (fte.Finger == dest.destination_data.ressource_id)
                                    {
                                        fte.dtLastSuccessfullFinger = DateTime.Now;
                                        fte.Successor = reloadRcvMsg.OriginatorID;
                                        fte.pinging = true;
                                    }
                                }

                                /* Attach if not attached */
                                if (!m_topology.routing_table.IsAttached(reloadRcvMsg.OriginatorID))
                                    Arbiter.Activate(m_DispatcherQueue,
                                        new IterativeTask<Destination, NodeId, AttachOption>(new Destination(reloadRcvMsg.OriginatorID),
                                            reloadRcvMsg.LastHopNodeId,
                                            AttachOption.sendping,
                                            AttachProcedure));
                                else if (reloadRcvMsg.OriginatorID != reloadRcvMsg.LastHopNodeId)// Send ping to get/keep a physical connection
                                    Arbiter.Activate(m_DispatcherQueue, new IterativeTask<Destination, PingOption>(new Destination(reloadRcvMsg.OriginatorID), PingOption.direct, SendPing));
                            }
                        }
                    }
                }
                else
                {
                    if (dest.type == DestinationType.node)
                    {
                        m_ReloadConfig.Logger(ReloadGlobals.TRACEFLAGS.T_WARNING, String.Format("Ping failed: removing node {0}", dest.destination_data.node_id));
                        m_topology.routing_table.Leave(dest.destination_data.node_id);
                    }
                    m_statistics.IncTransmissionError();
                }

                if (dest.type == DestinationType.node)
                    m_topology.routing_table.SetPinging(dest.destination_data.node_id, false, answ != null);
            }
            catch (Exception ex)
            {
                m_ReloadConfig.Logger(ReloadGlobals.TRACEFLAGS.T_ERROR, "Send Ping: " + ex.Message);
            }
        }
コード例 #11
0
ファイル: Transport.cs プロジェクト: RELOAD-NET/RELOAD.NET
        // --josch

        /// <summary>
        /// Proprietary: Stores the Usage data in a different RELOAD overlay using viaGateWay as gateway
        /// </summary>
        /// <param name="ResourceName"></param>
        /// <param name="kind_data"></param>
        /// <param name="viaGateWay"></param>
        /// <returns></returns>
        public IEnumerator<ITask> Store(string ResourceName, List<StoreKindData> kind_data, NodeId viaGateWay)
        {
            if (m_ReloadConfig.IamClient)
                m_ReloadConfig.StartStoreMobile = DateTime2.Now;
            else
                m_ReloadConfig.StartStore = DateTime.Now;

            ReloadDialog reloadDialog = null;
            ReloadMessage reloadSendMsg;
            ResourceId res_id = new ResourceId(ResourceName);
            //List<StoreKindData> kind_data = new List<StoreKindData>();


            Node node = null;

            if (viaGateWay != null)
            {
                //NodeId gateway = new ResourceId(viaGateWay);

                node = m_topology.routing_table.FindNextHopTo(viaGateWay, true, false);

                m_ReloadConfig.Logger(ReloadGlobals.TRACEFLAGS.T_USAGE, String.Format("Store {0} as ResID: {1} via Gateway {2}", ResourceName, res_id, viaGateWay));

                if (m_ReloadConfig.IamClient && node == null)
                {
                    node = m_ReloadConfig.AdmittingPeer;
                }

                foreach (StoreKindData storeKindData in kind_data)
                {
                    if (node == null || node.Id == m_ReloadConfig.LocalNodeID)
                    {
                        m_ReloadConfig.Logger(ReloadGlobals.TRACEFLAGS.T_TOPO, String.Format("Local storage at NodeId {0}", node.Id));
                        m_topology.Store(res_id, storeKindData);
                        yield break;
                    }
                }

                Destination gateway = new Destination(new NodeId(viaGateWay.Data));
                Destination storeDestination = new Destination(res_id);
                StoreReq storeRequest = new StoreReq(storeDestination.destination_data.ressource_id,
                                                      kind_data,
                                                      m_machine.UsageManager, false);
                reloadSendMsg = create_reload_message(gateway, ++m_ReloadConfig.TransactionID, storeRequest);
                reloadSendMsg.forwarding_header.destination_list.Add(storeDestination);  //this is the real destination

                if (reloadSendMsg.AddDestinationOverlay(ResourceName))
                    m_ReloadConfig.Logger(ReloadGlobals.TRACEFLAGS.T_ERROR, "AddDestinationOverlay successful");
            }
            else
            {
                res_id = new ResourceId(ResourceName);

                m_ReloadConfig.Logger(ReloadGlobals.TRACEFLAGS.T_USAGE, String.Format("Store {0} as ResID: {1}", ResourceName, res_id));
                node = m_topology.routing_table.FindNextHopTo(new NodeId(res_id), true, false);

                if (m_ReloadConfig.IamClient && node == null)
                {
                    node = m_ReloadConfig.AdmittingPeer;
                }
                if (node == null || node.Id == m_ReloadConfig.LocalNodeID)
                {
                    foreach (StoreKindData storeKindData in kind_data)
                    {

                        m_ReloadConfig.Logger(ReloadGlobals.TRACEFLAGS.T_TOPO,
                          String.Format("Local storage at NodeId {0}", node.Id));
                        m_ReloadConfig.Logger(ReloadGlobals.TRACEFLAGS.T_MEASURE,
                          "Store:0,011111");
                        m_topology.Store(res_id, storeKindData);
                    }
                    if (storeDone != null) storeDone.Post(reloadDialog);
                    yield break;
                }
                reloadSendMsg = create_store_req(new Destination(res_id), kind_data, false);
            }

            int RetransmissionTime = ReloadGlobals.RetransmissionTime + ReloadGlobals.MaxTimeToSendPacket;

            int iRetrans = ReloadGlobals.MaxRetransmissions;

            while (iRetrans >= 0 && m_ReloadConfig.State < ReloadConfig.RELOAD_State.Exit)
            {
                try
                {
                    reloadDialog = new ReloadDialog(m_ReloadConfig, m_flm, node);

                    m_ReloadConfig.Logger(ReloadGlobals.TRACEFLAGS.T_RELOAD, String.Format("{0} ==> {1} TransId={2:x16}",
                        reloadSendMsg.reload_message_body.RELOAD_MsgCode.ToString().PadRight(16, ' '), node.Id, reloadSendMsg.TransactionID));

                    Arbiter.Activate(m_DispatcherQueue,
                        new IterativeTask<ReloadMessage, ReloadMessageFilter, int>(reloadSendMsg,
                            new ReloadMessageFilter(reloadSendMsg.TransactionID), RetransmissionTime, reloadDialog.Execute));
                }
                catch (Exception ex)
                {
                    storeDone.Post(reloadDialog);
                    m_ReloadConfig.Logger(ReloadGlobals.TRACEFLAGS.T_ERROR, "Send Store: " + ex.Message);
                    ReloadGlobals.PrintException(m_ReloadConfig, ex);
                }

                yield return Arbiter.Receive(false, reloadDialog.Done, done => { });

                if (!reloadDialog.Error && reloadDialog.ReceivedMessage != null)
                    break;


                /* If a response has not been received when the timer fires, the request
                   is retransmitted with the same transaction identifier. 
                */
                --iRetrans;
            }

            try
            {
                if (!reloadDialog.Error && reloadDialog.ReceivedMessage != null)
                {
                    //the SourceNodeID delivered from reloadDialog comes from connection table and is the last hop of the message
                    ReloadMessage reloadRcvMsg = reloadDialog.ReceivedMessage;

                    if (reloadRcvMsg.reload_message_body.RELOAD_MsgCode == RELOAD_MessageCode.Store_Answer)
                    {
                        m_ReloadConfig.Logger(ReloadGlobals.TRACEFLAGS.T_USAGE,
                          String.Format("Store successful:{0} <== {1} TransId={2:x16}",
                          reloadRcvMsg.reload_message_body.RELOAD_MsgCode.ToString().PadRight(16, ' '),
                          reloadRcvMsg.OriginatorID, reloadRcvMsg.TransactionID));

                        m_ReloadConfig.EndStore = DateTime.Now;

                        TimeSpan storeSpan = storeSpan = m_ReloadConfig.EndStore - m_ReloadConfig.StartStore;

                        if (m_ReloadConfig.IamClient)
                            storeSpan = DateTime2.Now - m_ReloadConfig.StartStoreMobile;

                        m_ReloadConfig.Logger(ReloadGlobals.TRACEFLAGS.T_MEASURE,
                                              String.Format("Store:{0}",
                                              storeSpan.TotalSeconds.ToString()));

                        if (storeDone != null) storeDone.Post(reloadDialog);
                    }
                }
                else
                {
                    m_ReloadConfig.Logger(ReloadGlobals.TRACEFLAGS.T_WARNING,
                      String.Format("Store failed"));
                    m_statistics.IncTransmissionError();
                }
            }
            catch (Exception ex)
            {
                m_ReloadConfig.Logger(ReloadGlobals.TRACEFLAGS.T_ERROR, "Send Store 2: " + ex.Message);
                ReloadGlobals.PrintException(m_ReloadConfig, ex);
            }

            if (m_ReloadConfig.State == ReloadConfig.RELOAD_State.Shutdown)
                m_machine.Finish();

        }
コード例 #12
0
ファイル: Transport.cs プロジェクト: RELOAD-NET/RELOAD.NET
        /// <summary>
        /// Stores the Usage data in the RELOAD overlay
        /// </summary>
        /// <param name="ResourceName"></param>
        /// <param name="DestUrl"></param>
        /// <param name="exists">if true, stores the values, else stores a "non-existent" value.</param>
        /// <param name="usages">The Usage data to be stored.</param>
        /// <returns></returns>        
        public IEnumerator<ITask> Store(string ResourceName, List<StoreKindData> kind_data)
        {
            if (m_ReloadConfig.IamClient)
                m_ReloadConfig.StartStoreMobile = DateTime2.Now;
            else
                m_ReloadConfig.StartStore = DateTime.Now;

            ReloadDialog reloadDialog = null;
            ReloadMessage reloadSendMsg;
            ResourceId res_id = new ResourceId(ResourceName);

            m_ReloadConfig.Logger(ReloadGlobals.TRACEFLAGS.T_USAGE, String.Format("Store {0} as ResID: {1}", ResourceName, res_id));
            Node node = m_topology.routing_table.FindNextHopTo(new NodeId(res_id), true, false);

            if (m_ReloadConfig.IamClient && node == null)
            {
                node = m_ReloadConfig.AdmittingPeer;
            }
            if (node == null || node.Id == m_ReloadConfig.LocalNodeID)
            {
                foreach (StoreKindData storeKindData in kind_data)
                {

                    m_ReloadConfig.Logger(ReloadGlobals.TRACEFLAGS.T_TOPO,
                      String.Format("Local storage at NodeId {0}", node.Id));
                    m_ReloadConfig.Logger(ReloadGlobals.TRACEFLAGS.T_MEASURE,
                      "Store:0,011111");
                    m_topology.Store(res_id, storeKindData);
                }

                // REPLICATEST
                // incoming store request is not a replication request
                int numberReplicas = m_topology.routing_table.Successors.Count >= 2 ? 2 : m_topology.routing_table.Successors.Count; // Replica number is max 2
                // send replica to all successors
                for (int i = 0; i < numberReplicas; i++)
                {
                    NodeId successorNode = m_topology.routing_table.Successors[i];
                    ReloadMessage replica = create_store_req(new Destination(successorNode), res_id, kind_data, true);
                    send(replica, m_topology.routing_table.GetNode(successorNode));
                }

                if (storeDone != null) storeDone.Post(reloadDialog);
                yield break;
            }

            Destination dest = new Destination(res_id);

            reloadSendMsg = create_store_req(dest, kind_data, false);

            int RetransmissionTime = ReloadGlobals.RetransmissionTime + ReloadGlobals.MaxTimeToSendPacket;

            int iRetrans = ReloadGlobals.MaxRetransmissions;

            while (iRetrans >= 0 && m_ReloadConfig.State < ReloadConfig.RELOAD_State.Exit)
            {
                try
                {
                    reloadDialog = new ReloadDialog(m_ReloadConfig, m_flm, node);

                    m_ReloadConfig.Logger(ReloadGlobals.TRACEFLAGS.T_RELOAD, String.Format("{0} ==> {1} TransId={2:x16}",
                        reloadSendMsg.reload_message_body.RELOAD_MsgCode.ToString().PadRight(16, ' '), node.Id, reloadSendMsg.TransactionID));

                    Arbiter.Activate(m_DispatcherQueue,
                        new IterativeTask<ReloadMessage, ReloadMessageFilter, int>(reloadSendMsg,
                            new ReloadMessageFilter(reloadSendMsg.TransactionID), RetransmissionTime, reloadDialog.Execute));
                }
                catch (Exception ex)
                {
                    storeDone.Post(reloadDialog);
                    m_ReloadConfig.Logger(ReloadGlobals.TRACEFLAGS.T_ERROR, "Send Store: " + ex.Message);
                    ReloadGlobals.PrintException(m_ReloadConfig, ex);
                    break;
                }

                yield return Arbiter.Receive(false, reloadDialog.Done, done => { });

                //if (!reloadDialog.Error && reloadDialog.ReceivedMessage != null && reloadDialog.ReceivedMessage.reload_message_body.RELOAD_MsgCode == RELOAD_MessageCode.Store_Answer)
                //    break;

                if (!reloadDialog.Error && reloadDialog.ReceivedMessage != null && reloadDialog.ReceivedMessage.reload_message_body.RELOAD_MsgCode == RELOAD_MessageCode.Store_Answer)
                {

                    ReloadMessage reloadRcvMsg = reloadDialog.ReceivedMessage;

                    if (dest.type == DestinationType.node)
                    {
                        if (reloadRcvMsg.OriginatorID != dest.destination_data.node_id)
                        {
                            // drop message and retransmit request
                            reloadRcvMsg = null;
                        }
                    }
                    else if (dest.type == DestinationType.resource)
                    {
                        int suc = m_topology.routing_table.GetSuccessorCount(false);
                        int pre = m_topology.routing_table.GetPredecessorCount(false);

                        if (suc >= 2 && pre >= 2)
                        {
                            // check if resource is mapping to a node in my routing table
                            if (dest.destination_data.ressource_id.ElementOfInterval(
                                m_topology.routing_table.Predecessors[pre - 2],
                                m_topology.routing_table.Successors[suc - 1],
                                true)
                            )
                            {
                                if (reloadRcvMsg.OriginatorID < m_topology.routing_table.Predecessors[pre - 2] && reloadRcvMsg.OriginatorID > m_topology.routing_table.Successors[suc - 1])
                                {
                                    // drop message and retransmit request
                                    reloadRcvMsg = null;
                                }
                            }
                        }
                    }
                    if (reloadRcvMsg != null)
                        break;
                }


                /* If a response has not been received when the timer fires, the request
                   is retransmitted with the same transaction identifier. 
                */
                --iRetrans;
            }

            try
            {
                if (!reloadDialog.Error && reloadDialog.ReceivedMessage != null)
                {
                    //the SourceNodeID delivered from reloadDialog comes from connection table and is the last hop of the message
                    ReloadMessage reloadRcvMsg = reloadDialog.ReceivedMessage;

                    if (reloadRcvMsg.reload_message_body.RELOAD_MsgCode == RELOAD_MessageCode.Store_Answer)
                    {
                        m_ReloadConfig.Logger(ReloadGlobals.TRACEFLAGS.T_USAGE,
                          String.Format("Store successful:{0} <== {1} TransId={2:x16}",
                          reloadRcvMsg.reload_message_body.RELOAD_MsgCode.ToString().PadRight(16, ' '),
                          reloadRcvMsg.OriginatorID, reloadRcvMsg.TransactionID));

                        m_ReloadConfig.EndStore = DateTime.Now;

                        TimeSpan storeSpan = storeSpan = m_ReloadConfig.EndStore - m_ReloadConfig.StartStore;

                        if (m_ReloadConfig.IamClient)
                            storeSpan = DateTime2.Now - m_ReloadConfig.StartStoreMobile;

                        m_ReloadConfig.Logger(ReloadGlobals.TRACEFLAGS.T_MEASURE,
                                              String.Format("Store:{0}",
                                              storeSpan.TotalSeconds.ToString()));

                        if (storeDone != null) storeDone.Post(reloadDialog);
                    }
                }
                else
                {
                    m_ReloadConfig.Logger(ReloadGlobals.TRACEFLAGS.T_WARNING,
                      String.Format("Store failed"));
                    m_statistics.IncTransmissionError();
                }
            }
            catch (Exception ex)
            {
                m_ReloadConfig.Logger(ReloadGlobals.TRACEFLAGS.T_ERROR, "Send Store 2: " + ex.Message);
                ReloadGlobals.PrintException(m_ReloadConfig, ex);
            }

            if (m_ReloadConfig.State == ReloadConfig.RELOAD_State.Shutdown)
                m_machine.Finish();

        }
コード例 #13
0
ファイル: Transport.cs プロジェクト: RELOAD-NET/RELOAD.NET
        } // End PreJoin        

        /// <summary>
        /// Attaches to a node needed to enrich the finger table.
        /// </summary>
        /// <param name="finger"></param>    
        /// <returns></returns>
        public IEnumerator<ITask> AttachFinger(FTEntry finger,
          Port<bool> attachNext)
        {
            Destination dest = new Destination(finger.Finger);
            ReloadMessage reloadSendMsg = create_attach_req(dest, false);
            ReloadDialog reloadDialog = null;

            int RetransmissionTime = ReloadGlobals.RetransmissionTime +
              ReloadGlobals.MaxTimeToSendPacket;
            int iRetrans = ReloadGlobals.MaxRetransmissions;

            Boolean NextHopIsDestination = false;
            var myNodeId = m_topology.LocalNode.Id;
            Node nextHopNode = NextHopToDestination(dest, ref NextHopIsDestination);

            if (nextHopNode == null ||
              nextHopNode.Id == m_ReloadConfig.LocalNodeID)
                nextHopNode = m_ReloadConfig.AdmittingPeer;

            if (nextHopNode == null) //{
                m_ReloadConfig.Logger(ReloadGlobals.TRACEFLAGS.T_ERROR,
                String.Format("No Route to Finger! {0}", finger.Finger));
            //attachNext.Post(true);
            // yield break;
            //}
            //else {
            while (iRetrans >= 0 && m_ReloadConfig.State < ReloadConfig.RELOAD_State.Shutdown)
            {
                try
                {
                    reloadDialog = new ReloadDialog(m_ReloadConfig, m_flm, nextHopNode);
                    m_forwarding.LoopedTrans = new Port<UInt64>();
                    if (reloadDialog == null)
                        m_ReloadConfig.Logger(ReloadGlobals.TRACEFLAGS.T_RELOAD,
                        "ReloadDialog null!");

                    m_ReloadConfig.Logger(ReloadGlobals.TRACEFLAGS.T_TOPO,
                      String.Format("Finger-{0} via {1} ==> Dest={2} TransId={3:x16}",
                      RELOAD_MessageCode.Attach_Request.ToString().PadRight(16, ' '),
                      nextHopNode, dest.ToString(), reloadSendMsg.TransactionID));

                    Arbiter.Activate(m_DispatcherQueue,
                      new IterativeTask<ReloadMessage, ReloadMessageFilter, int>(reloadSendMsg,
                      new ReloadMessageFilter(reloadSendMsg.TransactionID), RetransmissionTime,
                      reloadDialog.Execute));
                }
                catch (Exception e)
                {
                    m_ReloadConfig.Logger(ReloadGlobals.TRACEFLAGS.T_ERROR,
                      String.Format("AttachFinger: " + e));
                    attachNext.Post(true);
                    yield break;
                }
                bool gotLoop = false;

                yield return Arbiter.Choice(
                    /* Success, Attached to finger */
                  Arbiter.Receive(false, reloadDialog.Done, done => { }),
                    /* Loop detected */
                  Arbiter.Receive(false, m_forwarding.LoopedTrans, transId =>
                  {
                      if (transId == reloadSendMsg.TransactionID)
                      {
                          m_ReloadConfig.Logger(ReloadGlobals.TRACEFLAGS.T_ERROR,
                            String.Format("Not re-sending transaction: {0:x16}=> a loopback detected!",
                            reloadSendMsg.TransactionID));
                          gotLoop = true;
                          m_forwarding.LoopedTrans = new Port<ulong>();
                      }
                  }));


                if (gotLoop)
                {
                    attachNext.Post(true);
                    yield break; ;
                }

                if (!reloadDialog.Error && reloadDialog.ReceivedMessage != null)
                    break;

                // If a response has not been received when the timer fires, the request
                // is retransmitted with the same transaction identifier. 

                --iRetrans;
                if (iRetrans >= 0)
                {
                    m_ReloadConfig.Logger(ReloadGlobals.TRACEFLAGS.T_WARNING,
                      String.Format("Retrans {0} SendAttach  via {1} TransId={2:x16}",
                      iRetrans, nextHopNode, reloadSendMsg.TransactionID));
                    m_ReloadConfig.Statistics.IncRetransmission();
                }
                else
                {
                    m_ReloadConfig.Logger(ReloadGlobals.TRACEFLAGS.T_ERROR,
                      String.Format("Failed! SendAttach  via {0} TransId={1:x16}",
                      nextHopNode, reloadSendMsg.TransactionID));
                    m_ReloadConfig.Statistics.IncTransmissionError();
                    if (dest.destination_data.node_id != null)
                        m_topology.routing_table.SetNodeState(dest.destination_data.node_id,
                          NodeState.unknown);
                }
                // }
            }

            try
            {
                if (reloadDialog != null && !reloadDialog.Error &&
                  reloadDialog.ReceivedMessage != null)
                {
                    /*the SourceNodeID delivered from reloadDialog comes from connection
                     * table and is the last hop of the message
                     */
                    ReloadMessage reloadRcvMsg = reloadDialog.ReceivedMessage;
                    RELOAD_MessageCode msgCode = reloadRcvMsg.reload_message_body.RELOAD_MsgCode;
                    AttachReqAns answ = null;
                    if (msgCode == RELOAD_MessageCode.Attach_Answer)
                    {
                        answ = (AttachReqAns)reloadRcvMsg.reload_message_body;

                        m_ReloadConfig.Logger(ReloadGlobals.TRACEFLAGS.T_TOPO,
                          String.Format("Finger-{0} <== {1} TransId={2:x16}",
                          msgCode.ToString().PadRight(16, ' '),
                          reloadRcvMsg.OriginatorID, reloadRcvMsg.TransactionID));

                        Node originator = new Node(reloadRcvMsg.OriginatorID, answ.ice_candidates);
                        NodeState nodeState = m_topology.routing_table.GetNodeState(originator.Id);
                        if (nodeState == NodeState.unknown)
                        {
                            attachNext.Post(true);
                            m_topology.routing_table.AddNode(originator);
                            m_topology.routing_table.SetNodeState(originator.Id, NodeState.attached);
                            m_topology.routing_table.AddFinger(originator, NodeState.attached);
                            m_ReloadConfig.Logger(ReloadGlobals.TRACEFLAGS.T_USAGE,
                              String.Format("Got a finger! {0}", originator.Id));
                        }
                        /* we know this peer, further Attaches will return same peer */
                        else
                            attachNext.Post(false);
                    }
                }
            }
            catch (Exception e)
            {
                m_ReloadConfig.Logger(ReloadGlobals.TRACEFLAGS.T_ERROR,
                  String.Format("AttachFingers:" + e));
            }
        }
コード例 #14
0
ファイル: Topology.cs プロジェクト: RELOAD-NET/RELOAD.NET
            /// <summary>
            /// JP also needs to populate its finger table (for the Chord based DHT).
            /// It issues an Attach to a variety of locations around the overlay.
            /// see RELOAD base -17 p.129
            /// </summary>
            /// <returns></returns>
            public List<FTableEntry> AttachFingers() {

                var fingerCount = ReloadGlobals.FINGER_TABLE_ENTRIES;

                if (!((fingerCount & (fingerCount - 1)) == 0)) // fingerCount = 2^n ?
                    fingerCount = 16; // fallback to 16 entries

                List<FTableEntry> fingers = new List<FTableEntry>();

                int offset = m_FingerTable.Count / fingerCount;

                for (int i = 0; i < m_FingerTable.Count; i += offset) {
                    var res = m_FingerTable[i].Finger;
                    Destination dest = new Destination(m_FingerTable[i].Finger);
                    fingers.Add(m_FingerTable[i]);
                }
                return fingers;

            } // end AttachFingers
コード例 #15
0
ファイル: Transport.cs プロジェクト: RELOAD-NET/RELOAD.NET
 public ReloadMessage create_join_answ(Destination destination, UInt64 trans_id)
 {
     return create_reload_message(destination, trans_id, new JoinReqAns(null, false));
 }
コード例 #16
0
ファイル: Transport.cs プロジェクト: RELOAD-NET/RELOAD.NET
        public IEnumerator<ITask> AttachProcedure(Destination dest, NodeId NextHopId, AttachOption attach_option)
        {
            ReloadMessage reloadSendMsg;

            /* 9.5.1 
             *     When a peer needs to Attach to a new peer in its neighbor table, it
                   MUST source-route the Attach request through the peer from which it
                   learned the new peer's Node-ID.  Source-routing these requests allows
                   the overlay to recover from instability.
            */

            reloadSendMsg = create_attach_req(dest, (attach_option & AttachOption.forceupdate) != 0);


            if (dest.type == DestinationType.node)
            {
                NodeState nodestate = m_topology.routing_table.GetNodeState(dest.destination_data.node_id);

                if (nodestate == NodeState.attaching)
                {
                    m_ReloadConfig.Logger(ReloadGlobals.TRACEFLAGS.T_INFO, String.Format("Ignoring redundant Attach for {0}", dest));
                    yield break;
                }
            }

            Boolean NextHopIsDestination = false;
            Node NextHopNode = null;

            if (NextHopId != null)
                NextHopNode = m_topology.routing_table.GetNode(NextHopId);

            if (NextHopNode == null)
                NextHopNode = NextHopToDestination(dest, ref NextHopIsDestination);

            if (NextHopNode == null)
                yield break;

            if (dest.type == DestinationType.node)
                m_topology.routing_table.SetNodeState(dest.destination_data.node_id, NodeState.attaching);

            ReloadDialog reloadDialog = null;

            int RetransmissionTime = ReloadGlobals.RetransmissionTime + ReloadGlobals.MaxTimeToSendPacket;
            int iRetrans = ReloadGlobals.MaxRetransmissions;

            while (iRetrans >= 0 && m_ReloadConfig.State < ReloadConfig.RELOAD_State.Shutdown)
            {
                try
                {
                    /* use a new ReloadDialog instance for every usage, Monitor requires it                         */
                    reloadDialog = new ReloadDialog(m_ReloadConfig, m_flm, NextHopNode);

                    m_ReloadConfig.Logger(ReloadGlobals.TRACEFLAGS.T_RELOAD, String.Format("{0} via {1} ==> Dest={2} TransId={3:x16}",
                                                                                            RELOAD_MessageCode.Attach_Request.ToString().PadRight(16, ' '),
                                                                                            NextHopNode,
                                                                                            dest.ToString(),
                                                                                            reloadSendMsg.TransactionID));

                    Arbiter.Activate(m_DispatcherQueue, new IterativeTask<ReloadMessage, ReloadMessageFilter, int>(reloadSendMsg, new ReloadMessageFilter(reloadSendMsg.TransactionID), RetransmissionTime, reloadDialog.Execute));
                }
                catch (Exception ex)
                {
                    m_ReloadConfig.Logger(ReloadGlobals.TRACEFLAGS.T_ERROR, "AttachProcedure: " + ex.Message);
                    yield break;
                }

                yield return Arbiter.Receive(false, reloadDialog.Done, done => { });

                if (!reloadDialog.Error && reloadDialog.ReceivedMessage != null)
                {
                    ReloadMessage reloadRcvMsg = reloadDialog.ReceivedMessage;

                    if (dest.type == DestinationType.node)
                    {
                        if (reloadRcvMsg.OriginatorID != dest.destination_data.node_id)
                        {
                            // drop message and retransmit request
                            m_ReloadConfig.Logger(ReloadGlobals.TRACEFLAGS.T_ERROR, String.Format("Received answer from unexpected peer"));
                            reloadRcvMsg = null;
                        }
                    }
                    else if (dest.type == DestinationType.resource)
                    {
                        int suc = m_topology.routing_table.GetSuccessorCount(false);
                        int pre = m_topology.routing_table.GetPredecessorCount(false);

                        if (suc >= 2 && pre >= 2)
                        {
                            // check if resource is mapping to a node in my routing table
                            if (dest.destination_data.ressource_id.ElementOfInterval(
                                m_topology.routing_table.Predecessors[pre - 2],
                                m_topology.routing_table.Successors[suc - 1],
                                true)
                            )
                            {
                                if (reloadRcvMsg.OriginatorID < m_topology.routing_table.Predecessors[pre - 2] && reloadRcvMsg.OriginatorID > m_topology.routing_table.Successors[suc - 1])
                                {
                                    // drop message and retransmit request
                                    m_ReloadConfig.Logger(ReloadGlobals.TRACEFLAGS.T_ERROR, String.Format("Received answer from unexpected peer"));
                                    reloadRcvMsg = null;
                                }
                            }
                        }
                    }

                    if (reloadRcvMsg != null)
                        break;
                }

                /* If a response has not been received when the timer fires, the request
                   is retransmitted with the same transaction identifier. 
                */
                --iRetrans;
                if (iRetrans >= 0)
                {
                    m_ReloadConfig.Logger(ReloadGlobals.TRACEFLAGS.T_WARNING, String.Format("Retrans {0} SendAttach  via {1} TransId={2:x16}", iRetrans, NextHopNode, reloadSendMsg.TransactionID));
                    m_ReloadConfig.Statistics.IncRetransmission();
                }
                else
                {
                    m_ReloadConfig.Logger(ReloadGlobals.TRACEFLAGS.T_ERROR, String.Format("Failed! SendAttach  via {0} TransId={1:x16}", NextHopNode, reloadSendMsg.TransactionID));
                    m_ReloadConfig.Statistics.IncTransmissionError();

                    if (dest.destination_data.node_id != null)
                    {
                        //m_topology.routing_table.SetNodeState(dest.destination_data.node_id, NodeState.unknown);
                        m_topology.routing_table.Leave(dest.destination_data.node_id);
                    }
                }
            }

            try
            {
                if (reloadDialog != null && !reloadDialog.Error && reloadDialog.ReceivedMessage != null)
                {
                    /*the SourceNodeID delivered from reloadDialog comes from connection
                     * table and is the last hop of the message
                     */
                    ReloadMessage reloadRcvMsg = reloadDialog.ReceivedMessage;
                    RELOAD_MessageCode msgCode = reloadRcvMsg.reload_message_body.RELOAD_MsgCode;

                    AttachReqAns answ = (AttachReqAns)reloadRcvMsg.reload_message_body;

                    if (msgCode == RELOAD_MessageCode.Attach_Answer)
                    {
                        /* TKTODO
                         * 1.  The response to a message sent to a specific Node-ID MUST have
                               been sent by that Node-ID.
                           2.  The response to a message sent to a Resource-Id MUST have been
                               sent by a Node-ID which is as close to or closer to the target
                               Resource-Id than any node in the requesting node's neighbor
                               table.
                        */
                        if (answ != null)
                        {

                            Node Originator = new Node(reloadRcvMsg.OriginatorID, answ.ice_candidates);

                            /*  An Attach in and of itself does not result in updating the routing
                             *  table of either node.
                             *  Note: We use the routing table here only for storing ice candidates 
                             *  for later use, we will not update successor or predecessor list
                             */

                            m_topology.routing_table.AddNode(Originator);
                            m_topology.routing_table.SetNodeState(Originator.Id, NodeState.attached);

                            m_ReloadConfig.Logger(ReloadGlobals.TRACEFLAGS.T_RELOAD,
                              String.Format("{0} <== {1} last={2} TransId={3:x16}",
                              msgCode.ToString().PadRight(16, ' '), reloadRcvMsg.OriginatorID,
                              reloadRcvMsg.LastHopNodeId, reloadRcvMsg.TransactionID));

                            if ((CheckAndSetAdmittingPeer(Originator) &&
                              Originator.Id != reloadRcvMsg.LastHopNodeId)
                                || (attach_option & AttachOption.sendping) != 0)
                            {
                                // Send ping to get a physical connection
                                Arbiter.Activate(m_DispatcherQueue, new IterativeTask<Destination, PingOption>(new Destination(Originator.Id), PingOption.direct, SendPing));
                            }
                        }
                    }
                    else if (msgCode == RELOAD_MessageCode.Error)
                    {
                        if (dest.type == DestinationType.node)
                        {
                            ErrorResponse error = (ErrorResponse)reloadRcvMsg.reload_message_body;

                            if (error != null)
                            {
                                m_ReloadConfig.Logger(ReloadGlobals.TRACEFLAGS.T_ERROR,
                                  String.Format("AttachProcedure: Got Error {0} from {1} deleting {2}",
                                    error.ErrorMsg,
                                    reloadRcvMsg.OriginatorID,
                                    dest.destination_data.node_id));

                                m_topology.routing_table.Leave(dest.destination_data.node_id);
                            }
                        }
                    }
                }
            }
            catch (Exception ex)
            {
                m_ReloadConfig.Logger(ReloadGlobals.TRACEFLAGS.T_ERROR, "AttachProcedure: " + ex.Message);

                if (dest.destination_data.node_id != null)
                    m_topology.routing_table.SetNodeState(dest.destination_data.node_id, NodeState.unknown);
            }
        }
コード例 #17
0
ファイル: Transport.cs プロジェクト: RELOAD-NET/RELOAD.NET
 public ReloadMessage create_update_req(Destination destination,
   TopologyPlugin.RoutingTable rt, ChordUpdateType type)
 {
     return create_reload_message(destination, ++m_ReloadConfig.TransactionID,
       new UpdateReqAns(rt.GetApproved(rt.Successors), rt.GetApproved(rt.Predecessors),
         type, m_ReloadConfig.StartTime));
 }
コード例 #18
0
ファイル: Transport.cs プロジェクト: RELOAD-NET/RELOAD.NET
        public Node NextHopToDestination(Destination dest, ref bool direct)
        {
            Node NextHopNode = null;
            direct = false;

            if (dest.type == DestinationType.node)
            {
                NextHopNode = m_topology.routing_table.GetNode(dest.destination_data.node_id);

                if (NextHopNode == null)
                    /*  The Topology Plugin is responsible for maintaining the overlay
                        algorithm Routing Table, which is consulted by the Forwarding and
                        Link Management Layer before routing a message. 
                     */
                    NextHopNode = m_topology.routing_table.FindNextHopTo(
                      dest.destination_data.node_id, true, false);
                else
                    direct = true;
            }
            else
            {
                NextHopNode = m_topology.routing_table.FindNextHopTo(new NodeId(
                  dest.destination_data.ressource_id), true, false);
            }

            if (NextHopNode == null)
                m_ReloadConfig.Logger(ReloadGlobals.TRACEFLAGS.T_ERROR,
                  "Did not found next hop to: " + dest);
            return NextHopNode;
        }
コード例 #19
0
ファイル: Transport.cs プロジェクト: RELOAD-NET/RELOAD.NET
 public ReloadMessage create_leave_req(Destination destination)
 {
     return create_reload_message(destination, ++m_ReloadConfig.TransactionID, new LeaveReqAns(m_topology.LocalNode, true));
 }
コード例 #20
0
ファイル: Transport.cs プロジェクト: RELOAD-NET/RELOAD.NET
        private ReloadMessage create_reload_message(Destination destination,
          UInt64 trans_id, RELOAD_MessageBody reload_content)
        {
            // markus
            if (reload_content.RELOAD_MsgCode == RELOAD_MessageCode.Attach_Request)
            {
                try
                {
                    m_ReloadConfig.Logger(ReloadGlobals.TRACEFLAGS.T_INFO, String.Format("Add candidates to Dictionary: Transaction ID: {0:x}", trans_id));
                    foreach (IceCandidate cand in ((AttachReqAns)reload_content).ice_candidates)
                        m_ReloadConfig.Logger(ReloadGlobals.TRACEFLAGS.T_INFO, String.Format("Add candidate: {0}:{1}", cand.addr_port.ipaddr.ToString(), cand.addr_port.port));

                    if (!m_attachRequestCandidates.ContainsKey(trans_id)) // because retry uses same transid
                        m_attachRequestCandidates.Add(trans_id, ((AttachReqAns)reload_content).ice_candidates);
                }
                catch (Exception)
                {

                    throw;
                }
            }
            // markus end

            return new ReloadMessage(m_ReloadConfig,
              m_topology.LocalNode.Id, destination, trans_id, reload_content);



        }
コード例 #21
0
ファイル: Transport.cs プロジェクト: RELOAD-NET/RELOAD.NET
 public ReloadMessage create_ping_req(Destination destination)
 {
     return create_reload_message(destination, ++m_ReloadConfig.TransactionID, new PingReqAns(0, true));
 }
コード例 #22
0
ファイル: Transport.cs プロジェクト: RELOAD-NET/RELOAD.NET
        /// <summary>
        /// Creates an Attach request
        /// </summary>
        /// <param name="destination">The destination of this attach</param>
        /// <param name="fForceSendUpdate">Flag ForceSendUpdate</param>
        /// <returns></returns>
        public ReloadMessage create_attach_req(Destination destination,
          Boolean fForceSendUpdate)
        {
            //return create_reload_message(destination, ++m_ReloadConfig.TransactionID,     // markus: commented out
            //    new AttachReqAns(m_topology.LocalNode, true, fForceSendUpdate));
            bool gatherActiveHostOnly = false;

            if (destination == new Destination(new ResourceId(m_topology.LocalNode.Id + (byte)1)))
                gatherActiveHostOnly = true;


            else
            {
                foreach (BootstrapServer bss in m_machine.BootstrapServer)
                {
                    var test = new Destination(new ResourceId(bss.NodeId));
                    if (destination == new Destination(new ResourceId(bss.NodeId + (byte)1)))
                    {
                        gatherActiveHostOnly = true;
                        break;
                    }
                }

                //if (!gatherActiveHostOnly)
                //{
                //    foreach (FTEntry ftentry in m_topology.routing_table.FingerTable)
                //    {
                //        var test = new Destination(ftentry.Finger);
                //        if (destination == new Destination(ftentry.Finger))
                //        {
                //            gatherActiveHostOnly = true;
                //            break;
                //        }
                //    }
                //}
            }

            // markus
            return create_reload_message(destination, ++m_ReloadConfig.TransactionID,
                new AttachReqAns(m_topology.LocalNode, true, fForceSendUpdate, m_ReloadConfig.IsBootstrap, gatherActiveHostOnly));

        }
コード例 #23
0
ファイル: Transport.cs プロジェクト: RELOAD-NET/RELOAD.NET
 /// <summary>
 /// Creates a StoreReq that can be directed a specific NodeId 
 /// </summary>
 /// <param name="destination">The store destination NodeId</param>
 /// <param name="resourceId">The Id of the resource to store</param>
 /// <returns>A complete RELOAD StoreReq message including all headers</returns>
 public ReloadMessage create_store_req(Destination destination, ResourceId resourceId, List<StoreKindData> stored_kind_data, bool replica)
 {
     return create_reload_message(destination, ++m_ReloadConfig.TransactionID,
                                  new StoreReq(resourceId,
                                               stored_kind_data,
                                               m_machine.UsageManager, replica));
 }
コード例 #24
0
ファイル: Transport.cs プロジェクト: RELOAD-NET/RELOAD.NET
 public ReloadMessage create_app_attach_req(Destination destination)
 {
     return create_reload_message(destination, ++m_ReloadConfig.TransactionID, new AppAttachReqAns(m_topology.LocalNode, true));
 }
コード例 #25
0
ファイル: Transport.cs プロジェクト: RELOAD-NET/RELOAD.NET
 /// <summary>
 /// Creates a FetchReq using the given StoredDataSpecifiers
 /// </summary>
 /// <param name="destination">The destination</param>
 /// <param name="specifiers">The StoredDataSpecifiers</param>
 /// <returns>A FetchReq</returns>
 private ReloadMessage create_fetch_req(Destination destination, List<StoredDataSpecifier> specifiers)
 {
     return create_reload_message(destination, ++m_ReloadConfig.TransactionID,
                                  new FetchReq(destination.destination_data.ressource_id,
                                               specifiers,
                                               m_machine.UsageManager));
 }
コード例 #26
0
ファイル: Transport.cs プロジェクト: RELOAD-NET/RELOAD.NET
        public ReloadMessage create_attach_answ(Destination destination, UInt64 trans_id)
        {
            //return create_reload_message(destination, trans_id, new AttachReqAns(m_topology.LocalNode, false, true));

            //return create_reload_message(destination, trans_id,       // markus: commented out
            //  new AttachReqAns(m_topology.LocalNode, false, false));

            // markus
            return create_reload_message(destination, trans_id,
                new AttachReqAns(m_topology.LocalNode, false, false, m_ReloadConfig.IsBootstrap, false));     // bootstrap doesnt send attach requests => attach answer never goes to bootstrap => 4th parameter false
        }
コード例 #27
0
ファイル: Transport.cs プロジェクト: RELOAD-NET/RELOAD.NET
 public ReloadMessage create_erro_reply(Destination destination, RELOAD_ErrorCode error, string errmsg, UInt64 trans_id)
 {
     return create_reload_message(destination, trans_id, new ErrorResponse(error, errmsg));
 }
コード例 #28
0
ファイル: Transport.cs プロジェクト: RELOAD-NET/RELOAD.NET
 public ReloadMessage create_app_attach_answ(Destination destination, UInt64 trans_id)
 {
     return create_reload_message(destination, trans_id, new AppAttachReqAns(m_topology.LocalNode, false));
 }
コード例 #29
0
ファイル: Transport.cs プロジェクト: RELOAD-NET/RELOAD.NET
        public IEnumerator<ITask> PreJoinProdecure(List<BootstrapServer> BootstrapServerList)
        {
            bool attached = false;
            ulong bsTransId = 0;

            if (m_topology.LocalNode.Id == null)
                yield break;

            ReloadMessage reloadSendMsg;
            ReloadMessage reloadRcvMsg = null;

            /* This is the begin of populating the neighbor table
               convert local node to resource id + 1 and sent an attach to it
             */
            Destination dest = new Destination(new ResourceId(
              m_topology.LocalNode.Id + (byte)1));
            Destination last_destination = null;
            Node NextHopNode = null;
            int succSize = m_ReloadConfig.IamClient ? 1 : ReloadGlobals.SUCCESSOR_CACHE_SIZE;
            for (int i = 0; i < succSize; i++)
            {
                //if (last_destination != null && last_destination == dest)
                if (last_destination != null && last_destination.Equals(dest))    // markus: we have to use Equals method
                    break;
                if (m_ReloadConfig.IamClient)
                    reloadSendMsg = create_attach_req(dest, false);
                else
                    reloadSendMsg = create_attach_req(dest, true);

                //we do not know the bootstrap peer's node id so far so we leave that parameter empty Node(null)

                ReloadDialog reloadDialog = null;
                int RetransmissionTime = ReloadGlobals.RetransmissionTime + ReloadGlobals.MaxTimeToSendPacket;

                /* Modification for Clients out of draft, TLS stack will take some time
                 * to initialize, add another 10s waiting */
                if (m_ReloadConfig.IamClient && i == 0)
                    RetransmissionTime += 10000;

                int iRetrans = ReloadGlobals.MaxRetransmissions;

                int iCycleBootstrap = 0;

                while (iRetrans >= 0 &&
                  m_ReloadConfig.State < ReloadConfig.RELOAD_State.Shutdown)
                {
                    /* This is the first bootstrap contacting sequence if NextHopNode 
                     * is still zero, in any other case 
                     * use an attach to the node where we got the last answer from 
                     */
                    if (NextHopNode == null)
                    {
                        /* we could use a foreach loop, but CCR would multitask it, but we
                         * want serialize that here
                        */
                        if (iCycleBootstrap >= BootstrapServerList.Count())
                            iCycleBootstrap = 0;

                        BootstrapServer bss = BootstrapServerList[iCycleBootstrap++];

                        if (attached == true)
                            break;

                        //TKTODO Rejoin of bootstrap server not solved 
                        List<IceCandidate> ics = new List<IceCandidate>();
                        IceCandidate ice = new IceCandidate(new IpAddressPort(
                          AddressType.IPv4_Address, ReloadGlobals.IPAddressFromHost(
                          m_ReloadConfig, bss.Host), (UInt16)bss.Port),
                          Overlay_Link.TLS_TCP_FH_NO_ICE);

                        // markus: change cand_type to bootstrap
                        ice.cand_type = CandType.tcp_bootstrap;

                        ics.Add(ice);

                        NextHopNode = new Node(reloadRcvMsg == null ?
                          null : reloadRcvMsg.OriginatorID, ics);
                    }

                    try
                    {
                        /* use a new ReloadDialog instance for every usage, Monitor requires it                         */
                        reloadDialog = new ReloadDialog(m_ReloadConfig, m_flm, NextHopNode);

                        if (iCycleBootstrap > 0)
                        {
                            // save transaction id from request to bootstrap
                            if (NextHopNode.IceCandidates[0].addr_port.ipaddr.ToString() == BootstrapServerList[iCycleBootstrap - 1].Host &&
                                NextHopNode.IceCandidates[0].addr_port.port == BootstrapServerList[iCycleBootstrap - 1].Port)
                                bsTransId = reloadSendMsg.TransactionID;
                        }
                   
                        m_ReloadConfig.Logger(ReloadGlobals.TRACEFLAGS.T_RELOAD,
                          String.Format("{0} ==> {1} Dest={2} TransId={3:x16}",
                          RELOAD_MessageCode.Attach_Request.ToString().PadRight(16, ' '),
                          NextHopNode, dest.ToString(), reloadSendMsg.TransactionID));

                        Arbiter.Activate(m_DispatcherQueue,
                          new IterativeTask<ReloadMessage, ReloadMessageFilter, int>(
                          reloadSendMsg, new ReloadMessageFilter(reloadSendMsg.TransactionID),
                          RetransmissionTime, reloadDialog.Execute));
                    }
                    catch (Exception ex)
                    {
                        m_ReloadConfig.Logger(ReloadGlobals.TRACEFLAGS.T_ERROR,
                          "PreJoinProcedure: " + ex.Message);
                    }

                    yield return Arbiter.Receive(false, reloadDialog.Done, done => { });

                    if (!reloadDialog.Error && reloadDialog.ReceivedMessage != null)
                    {
                        if (reloadDialog.ReceivedMessage.TransactionID == bsTransId)
                        {

                            if (reloadDialog.ReceivedMessage.forwarding_header.via_list.Count == 1)
                            {
                                BootstrapServer bsServer = BootstrapServerList[iCycleBootstrap - 1];
                                bsServer.NodeId = reloadDialog.ReceivedMessage.forwarding_header.via_list[0].destination_data.node_id;
                                BootstrapServerList.RemoveAt(iCycleBootstrap - 1);
                                BootstrapServerList.Insert(iCycleBootstrap - 1, bsServer);
                                m_ReloadConfig.Logger(ReloadGlobals.TRACEFLAGS.T_RELOAD, String.Format("Bootstrap ID: {0}", reloadDialog.ReceivedMessage.forwarding_header.via_list[0].destination_data.node_id));
                                //Console.WriteLine("Bootstrap ID: {0}", reloadDialog.ReceivedMessage.forwarding_header.via_list[0].destination_data.node_id);
                            }
                            else if (reloadDialog.ReceivedMessage.forwarding_header.via_list.Count == 2)
                            {
                                BootstrapServer bsServer = BootstrapServerList[iCycleBootstrap - 1];
                                bsServer.NodeId = reloadDialog.ReceivedMessage.forwarding_header.via_list[1].destination_data.node_id;
                                BootstrapServerList.RemoveAt(iCycleBootstrap - 1);
                                BootstrapServerList.Insert(iCycleBootstrap - 1, bsServer);
                                m_ReloadConfig.Logger(ReloadGlobals.TRACEFLAGS.T_RELOAD, String.Format("Bootstrap ID: {0}", reloadDialog.ReceivedMessage.forwarding_header.via_list[1].destination_data.node_id));
                                //Console.WriteLine("Bootstrap ID: {0}", reloadDialog.ReceivedMessage.forwarding_header.via_list[1].destination_data.node_id);
                            }

                            bsTransId = 0;
                        }

                        break;
                    }




                    /* still bootstrapping, allow cycling trough different bootstraps by
                     * resetting NextHopNode
                     */
                    if (i == 0)
                        NextHopNode = null;

                    /* If a response has not been received when the timer fires, the request
                       is retransmitted with the same transaction identifier. 
                    */
                    --iRetrans;
                    if (iRetrans >= 0)
                    {
                        m_ReloadConfig.Logger(ReloadGlobals.TRACEFLAGS.T_WARNING, String.Format("Retrans {0} Attach  {1} TransId={2:x16}", iRetrans, NextHopNode, reloadSendMsg.TransactionID));
                        m_statistics.IncRetransmission();
                    }
                    else
                    {
                        m_ReloadConfig.Logger(ReloadGlobals.TRACEFLAGS.T_ERROR, String.Format("Failed! Attach {0} TransId={1:x16}", NextHopNode, reloadSendMsg.TransactionID));
                        m_statistics.IncTransmissionError();
                        if (ReloadGlobals.AutoExe)
                        {
                            m_ReloadConfig.Logger(ReloadGlobals.TRACEFLAGS.T_ERROR, "PreJoin: Exit because initial Attach Faild!");
                            m_machine.SendCommand("Exit");
                        }
                    }
                }
                try
                {
                    if (reloadDialog != null && !reloadDialog.Error && reloadDialog.ReceivedMessage != null)
                    {
                        //the SourceNodeID delivered from reloadDialog comes from connection table and is the last hop of the message
                        reloadRcvMsg = reloadDialog.ReceivedMessage;
                        RELOAD_MessageCode msgCode = reloadRcvMsg.reload_message_body.RELOAD_MsgCode;
                        if (reloadRcvMsg != null)
                        {
                            if (msgCode == RELOAD_MessageCode.Attach_Answer)
                            {
                                m_ReloadConfig.Logger(ReloadGlobals.TRACEFLAGS.T_RELOAD,
                                  String.Format("{0} <== {1} last={2} TransId={3:x16}",
                                  msgCode.ToString().PadRight(16, ' '), reloadRcvMsg.OriginatorID,
                                  reloadRcvMsg.LastHopNodeId, reloadRcvMsg.TransactionID));

                                AttachReqAns answ = (AttachReqAns)reloadRcvMsg.reload_message_body;

                                if (answ != null)
                                {
                                    m_ReloadConfig.State = ReloadConfig.RELOAD_State.PreJoin;
                                    m_machine.StateUpdates(ReloadConfig.RELOAD_State.PreJoin);

                                    /*  An Attach in and of itself does not result in updating the routing
                                     *  table of either node.
                                     *  Note: We use the routing table here only for storing ice candidates 
                                     *  for later use, we will not update successor or predecessor list
                                     */
                                    NextHopNode = new Node(reloadRcvMsg.OriginatorID, answ.ice_candidates);
                                    /*  An Attach in and of itself does not result in updating the routing
                                     *  table of either node.
                                     *  Note: We use the routing table here only for storing ice candidates 
                                     *  for later use, we will not update successor or predecessor list
                                     */
                                    m_topology.routing_table.AddNode(NextHopNode);
                                    m_topology.routing_table.SetNodeState(NextHopNode.Id,
                                      NodeState.attached);

                                    if (CheckAndSetAdmittingPeer(NextHopNode) &&
                                      NextHopNode.Id != reloadRcvMsg.LastHopNodeId)
                                        // Send ping to establish a physical connection
                                        Arbiter.Activate(m_DispatcherQueue,
                                          new IterativeTask<Destination, PingOption>(new Destination(
                                          NextHopNode.Id), PingOption.direct, SendPing));

                                    if (m_ReloadConfig.IamClient)
                                    {
                                        m_ReloadConfig.LastJoinedTime = DateTime2.Now;
                                        TimeSpan joiningTime = m_ReloadConfig.LastJoinedTime - m_ReloadConfig.StartJoinMobile;
                                        m_ReloadConfig.Logger(ReloadGlobals.TRACEFLAGS.T_MEASURE,
                                          "Join:" + joiningTime.TotalSeconds.ToString());
                                    }

                                    attached = true;
                                }
                            }
                            else if (msgCode == RELOAD_MessageCode.Error)
                            {
                                if (dest.type == DestinationType.node)
                                {
                                    ErrorResponse error = (ErrorResponse)reloadRcvMsg.reload_message_body;

                                    if (error != null)
                                    {
                                        m_ReloadConfig.Logger(ReloadGlobals.TRACEFLAGS.T_ERROR,
                                          String.Format("Prejoin: Got Error {0} from {1} deleting {2}",
                                            error.ErrorMsg,
                                            reloadRcvMsg.OriginatorID,
                                            dest.destination_data.node_id));

                                        m_topology.routing_table.Leave(dest.destination_data.node_id);
                                    }
                                }
                            }
                        }
                        else
                        {
                            m_ReloadConfig.Logger(ReloadGlobals.TRACEFLAGS.T_ERROR, "PreJoinProcedure: reloadRcvMsg == null!!");
                        }

                        last_destination = dest;
                        dest = new Destination(new ResourceId(reloadRcvMsg.OriginatorID) + (byte)1);
                    }
                    else
                        break;
                }
                catch (Exception ex)
                {
                    m_ReloadConfig.Logger(ReloadGlobals.TRACEFLAGS.T_ERROR, "PreJoinProcedure: " + ex.Message);
                }
            } // End Successor Search

            // FingerTable enrichment
            if (!m_ReloadConfig.IamClient)
            {
                List<FTEntry> fingers = m_topology.routing_table.AttachFingers();
                Port<bool> attachNextPort = null;
                Boolean attachNext = true;
                /* JP SHOULD send Attach requests to initiate connections to each of
                 * the peers in the neighbor table as well as to the desired finger
                 * table entries.
                 */
                foreach (FTEntry finger in fingers)
                {
                    attachNextPort = new Port<bool>();
                    Arbiter.Activate(m_DispatcherQueue,
                      new IterativeTask<FTEntry, Port<bool>>(
                      finger, attachNextPort, AttachFinger));
                    /* Wait for finger attach */
                    yield return Arbiter.Receive(false, attachNextPort, next =>
                    {
                        attachNext = next;
                    });
                    if (!attachNext)
                        break;

                }
            }
            /* see base -18 p.106
            /* 4.  JP MUST enter all the peers it has contacted into its routing
            /*     table.
             */
            m_topology.routing_table.Conn2Route();

            /* Once JP has a reasonable set of connections it is ready to take its 
             * place in the DHT.  It does this by sending a Join to AP.
             */
            if (m_ReloadConfig.AdmittingPeer != null)
                if (!m_ReloadConfig.IamClient)
                {
                    m_ReloadConfig.State = ReloadConfig.RELOAD_State.Joining;
                    m_machine.StateUpdates(ReloadConfig.RELOAD_State.Joining);

                    m_topology.routing_table.SetWaitForJoinAnsw(
                      m_ReloadConfig.AdmittingPeer.Id, true);

                    reloadSendMsg = create_join_req(
                      new Destination(m_ReloadConfig.AdmittingPeer.Id));
                    ReloadDialog reloadDialog = null;

                    int RetransmissionTime = ReloadGlobals.RetransmissionTime + ReloadGlobals.MaxTimeToSendPacket;
                    int iRetrans = ReloadGlobals.MaxRetransmissions;

                    while (iRetrans >= 0 && m_ReloadConfig.State < ReloadConfig.RELOAD_State.Shutdown)
                    {
                        reloadDialog = new ReloadDialog(m_ReloadConfig, m_flm, m_ReloadConfig.AdmittingPeer);

                        m_ReloadConfig.Logger(ReloadGlobals.TRACEFLAGS.T_RELOAD, String.Format("{0} ==> {1} TransId={2:x16}", RELOAD_MessageCode.Join_Request.ToString().PadRight(16, ' '), m_ReloadConfig.AdmittingPeer, reloadSendMsg.TransactionID));

                        Arbiter.Activate(m_DispatcherQueue, new IterativeTask<ReloadMessage, ReloadMessageFilter, int>(reloadSendMsg, new ReloadMessageFilter(reloadSendMsg.TransactionID), RetransmissionTime, reloadDialog.Execute));
                        yield return Arbiter.Receive(false, reloadDialog.Done, done => { });

                        if (!reloadDialog.Error && reloadDialog.ReceivedMessage != null)
                            break;

                        /* If a response has not been received when the timer fires, the request
                           is retransmitted with the same transaction identifier. 
                        */
                        --iRetrans;
                        if (iRetrans >= 0)
                        {
                            m_ReloadConfig.Logger(ReloadGlobals.TRACEFLAGS.T_WARNING, String.Format("Retrans {0} Join  {1} TransId={2:x16}", iRetrans, m_ReloadConfig.AdmittingPeer, reloadSendMsg.TransactionID));
                            m_statistics.IncRetransmission();
                        }
                        else
                        {
                            m_ReloadConfig.Logger(ReloadGlobals.TRACEFLAGS.T_ERROR, String.Format("Failed! Join {0} TransId={1:x16}", m_ReloadConfig.AdmittingPeer, reloadSendMsg.TransactionID));
                            m_statistics.IncTransmissionError();
                        }
                    }

                    try
                    {
                        if (!reloadDialog.Error)
                        {
                            reloadRcvMsg = reloadDialog.ReceivedMessage;
                            RELOAD_MessageCode msgCode = reloadRcvMsg.reload_message_body.RELOAD_MsgCode;
                            if (reloadRcvMsg != null)
                            {
                                if (msgCode == RELOAD_MessageCode.Join_Answer)
                                {
                                    m_topology.routing_table.SetWaitForJoinAnsw(reloadRcvMsg.OriginatorID, false);

                                    m_ReloadConfig.Logger(ReloadGlobals.TRACEFLAGS.T_RELOAD,
                                      String.Format("{0} <== {1} TransId={2:x16}",
                                      msgCode.ToString().PadRight(16, ' '), reloadRcvMsg.OriginatorID,
                                      reloadRcvMsg.TransactionID));

                                    NodeState nodestate = m_topology.routing_table.GetNodeState(reloadRcvMsg.OriginatorID);

                                    if (nodestate == NodeState.updates_received)
                                    {
                                        /* we previously received an update from admitting peer (maybe 
                                         * race condition), now joining is complete in any other case 
                                         * wait for updates to come from this node */
                                        m_ReloadConfig.State = ReloadConfig.RELOAD_State.Joined;
                                        m_machine.StateUpdates(ReloadConfig.RELOAD_State.Joined);
                                        m_ReloadConfig.Logger(ReloadGlobals.TRACEFLAGS.T_RELOAD, String.Format("Joining completed"));
                                        m_ReloadConfig.LastJoinedTime = DateTime.Now;
                                        TimeSpan joiningTime = m_ReloadConfig.LastJoinedTime - m_ReloadConfig.StartJoining;
                                        m_ReloadConfig.Logger(ReloadGlobals.TRACEFLAGS.T_MEASURE, String.Format("Join:{0}", joiningTime.TotalSeconds.ToString()));

                                        m_topology.routing_table.SendUpdateToAllNeighbors();
                                    }
                                    else
                                    {
                                        m_ReloadConfig.LastJoinedTime = DateTime.Now;
                                        TimeSpan joiningTime = m_ReloadConfig.LastJoinedTime - m_ReloadConfig.StartTime;
                                        m_ReloadConfig.Logger(ReloadGlobals.TRACEFLAGS.T_MEASURE, String.Format("Join:{0}", joiningTime.TotalSeconds.ToString()));

                                        m_ReloadConfig.Logger(ReloadGlobals.TRACEFLAGS.T_WARNING,
                                          String.Format("Prejoin: nodestate != update_recv at Node {0}", m_machine.ReloadConfig.ListenPort));
                                    }
                                    //m_topology.routing_table.SendUpdatesToAllFingers();
                                }
                            }
                            else
                            {
                                m_ReloadConfig.Logger(ReloadGlobals.TRACEFLAGS.T_ERROR, "PreJoinProcedure: reloadRcvMsg == null!!");
                            }
                        }
                    }
                    catch (Exception ex)
                    {
                        m_ReloadConfig.Logger(ReloadGlobals.TRACEFLAGS.T_ERROR, "PreJoinProcedure: " + ex.Message);
                    }
                }
                else
                {
                    if (m_ReloadConfig.SipUri == "")
                        m_ReloadConfig.SipUri = String.Format("{0}@{1}", ReloadGlobals.HostName,
                            m_ReloadConfig.OverlayName);

                    if (m_ReloadConfig.SipUri != null && m_ReloadConfig.SipUri != "")
                    {
                        // explictite SIP registration as minimal config for RELOAD clients

                        IUsage sipRegistration = m_machine.UsageManager.CreateUsage(Usage_Code_Point.SIP_REGISTRATION,
                                                                         2,
                                                                         m_ReloadConfig.SipUri);
                        sipRegistration.ResourceName = m_ReloadConfig.SipUri;
                        List<StoreKindData> clientRegistrationList = new List<StoreKindData>();
                        StoreKindData sipKindData = new StoreKindData(sipRegistration.KindId,
                                                                      0, new StoredData(sipRegistration.Encapsulate(true)));
                        clientRegistrationList.Add(sipKindData);
                        Arbiter.Activate(m_DispatcherQueue, new IterativeTask<string, List<StoreKindData>>(m_ReloadConfig.SipUri, clientRegistrationList, Store));
                    }
                }
            else
            {
                m_ReloadConfig.Logger(ReloadGlobals.TRACEFLAGS.T_MEASURE,
                  String.Format("PreJoinPredure => Node {0} has no admitting peer = {1}!",
                  m_machine.ReloadConfig.ListenPort, m_ReloadConfig.AdmittingPeer));
                if (ReloadGlobals.AutoExe)
                {
                    m_machine.SendCommand("Exit");
                }
            }
        } // End PreJoin        
コード例 #30
0
ファイル: Messages.cs プロジェクト: RELOAD-NET/RELOAD.NET
        public bool Equals(Destination dest)
        {
            // If parameter is null return false:
            if ((object)dest == null)
            {
                return false;
            }

            // Return true if the fields match:
            return (this.type == dest.type && this.destination_data.node_id == dest.destination_data.node_id && this.destination_data.ressource_id == dest.destination_data.ressource_id);
        }