Example #1
0
 /// <summary>
 ///   It transfers a list of elements to a node, if this is the node at level 0, it means that these elements have just
 ///   been taken into charge, it will then be distributed to all connections at level 0, collect all the signatures that
 ///   certify the timestamp, and send the signatures to the nodes connected to level 0.
 ///   This procedure is used to create a decentralized timestamp within the networkConnection.
 /// </summary>
 /// <param name="elements">Element to send to the node</param>
 /// <param name="toNode">Node that will receive the elements</param>
 /// <param name="responseMonitor">
 ///   This parameter is specified only if we are at level 0 of the distribution of the
 ///   elements, it is necessary to receive the timestamp signed by all the nodes connected to this level
 /// </param>
 internal void SendElementsToNode(List <ObjToNode> elements, Node toNode, ResponseMonitor responseMonitor = null)
 {
     new Thread(() =>
     {
         string xmlResult = null;
         //Verify if the node is disconnected
         if (!_networkConnection.NodeList.Contains(toNode))
         {
             return;
         }
         xmlResult      = SendRequest(toNode, StandardMessages.SendElementsToNode, elements);
         var objectName = Utility.GetObjectName(xmlResult);
         if (objectName == "TimestampVector")
         {
             var answer = Answer(xmlResult);
             if (answer != StandardAnswer.Ok)
             {
                 // Error occurred
             }
         }
         if (responseMonitor == null)
         {
             return;
         }
         if (objectName == "TimestampVector")
         {
             if (Converter.XmlToObject(xmlResult, typeof(ObjToNode.TimestampVector), out var objTimestampVector))
             {
                 var timestamps = (ObjToNode.TimestampVector)objTimestampVector;
                 foreach (var element in elements)
                 {
                     if (element.Level == 1 && timestamps.TryGetValue(element.ShortHash(), out var signedTimestamp))
                     {
                         element.TimestampSignature += signedTimestamp;
                         var l = Convert.FromBase64String(signedTimestamp).Length;
                     }
                 }
             }
         }
         else
         {
             var answer = Answer(xmlResult);
             // Add the response management here!!!
         }
         responseMonitor.ResponseCounter += 1;
         if (responseMonitor.ResponseCounter != responseMonitor.Level0Connections.Count)
         {
             return;
         }
         // All nodes connected to the zero level have signed the timestamp, now the signature of the timestamp of all the nodes must be sent to every single node.
         // This operation is used to create a decentralized timestamp.
         var timestampVector = new ObjToNode.TimestampVector();
         foreach (var element in elements)
         {
             timestampVector.Add(element.ShortHash(), element.TimestampSignature);
         }
         foreach (var node in responseMonitor.Level0Connections)
         {
             // The node at zero level (the entry point of the request), when it has kept the signature of the timestamp from all the connected nodes, communicates to each connected node all the collected signatures.
             // This is a decentralized collective timestamp.
             SendTimestampSignatureToNode(timestampVector, node);
         }
     }).Start();
 }
Example #2
0
 /// <summary>
 ///   It transfers a list of elements to a node, if this is the node at level 0, it means that these elements have just
 ///   been taken into charge, it will then be distributed to all connections at level 0, collect all the signatures that
 ///   certify the timestamp, and send the signatures to the nodes connected to level 0.
 ///   This procedure is used to create a decentralized timestamp within the networkConnection.
 /// </summary>
 /// <param name="elements">Element to send to the node</param>
 /// <param name="toNode">Node that will receive the elements</param>
 /// <param name="responseMonitor">
 ///   This parameter is specified only if we are at level 0 of the distribution of the
 ///   elements, it is necessary to receive the timestamp signed by all the nodes connected to this level
 /// </param>
 internal void SendElementsToNode(List <ObjToNode> elements, Node toNode, ResponseMonitor responseMonitor = null)
 {
     new Thread(() =>
     {
         string xmlResult = null;
         //Verify if the node is disconnected
         if (!_networkConnection.NodeList.Contains(toNode))
         {
             return;
         }
         xmlResult      = SendRequest(toNode, StandardMessages.SendElementsToNode, elements);
         var objectName = Utility.GetObjectName(xmlResult);
         if (objectName == "TimestampVector")
         {
             var answer = Answer(xmlResult);
             if (answer != StandardAnswer.Ok)
             {
                 // Error occurred
             }
         }
         if (responseMonitor == null)
         {
             return;
         }
         if (objectName == "TimestampVector")
         {
             if (Converter.XmlToObject(xmlResult, typeof(ObjToNode.TimestampVector), out var objTimestampVector))
             {
                 var timestamps = (ObjToNode.TimestampVector)objTimestampVector;
                 foreach (var objToNode in elements)
                 {
                     if (objToNode.Level == 1 && timestamps.TryGetValue(objToNode.ShortHash(), out var signedTimestamp))
                     {
                         var check = objToNode.AddTimestampSignature(signedTimestamp, toNode);
                         if (check != ObjToNode.CheckSignedTimestampResult.Ok)
                         {
                             Debugger.Break();
                             Utility.Log("signature", "Signature error from IP " + Converter.UintToIp(toNode.Ip) + " " + check.ToString());
                         }
                     }
                 }
             }
         }
         else
         {
             var answer = Answer(xmlResult);
             // Add the response management here!!!
         }
         responseMonitor.ResponseCounter += 1;
         if (responseMonitor.ResponseCounter != responseMonitor.Level0Connections.Count)
         {
             return;
         }
         // All nodes connected to the zero level have signed the timestamp, now the signature of the timestamp of all the nodes must be sent to every single node.
         // This operation is used to create a decentralized timestamp.
         var timestampVector = new ObjToNode.TimestampVector();
         var timeLimit       = _networkConnection.Now.AddSeconds(-(PipelineManager.SignatureTimeout - 0.5)).Ticks;           // Node at level 0 have max (N-0.5) second to transmit the signedTimestamps
         foreach (var objToNode in elements)
         {
             if (objToNode.FlagSignatureError != ObjToNode.CheckSignedTimestampResult.Ok || objToNode.Timestamp <= timeLimit)                     // Avoid sending timestamp signatures for operations that could be ignored given the time limit criteria of the UnlockElementsInStandBy function in PipelineManager
             {
                 _networkConnection.PipelineManager.RemoveLocal(objToNode.GetElement);
             }
             else
             {
                 timestampVector.Add(objToNode.ShortHash(), objToNode.TimestampSignature);
                 var elementInPipeline = _networkConnection.PipelineManager.Pipeline.Find(x => x.Element == objToNode.GetElement);
                 if (elementInPipeline != null && elementInPipeline.TimestampSignature == null)
                 {
                     elementInPipeline.TimestampSignature = objToNode.TimestampSignature;
                 }
             }
         }
         foreach (var node in responseMonitor.Level0Connections)
         {
             // The node at zero level (the entry point of the request), when it has kept the signature of the timestamp from all the connected nodes, communicates to each connected node all the collected signatures.
             // This is a decentralized collective timestamp.
             SendTimestampSignatureToNode(timestampVector, node);
         }
     }).Start();
 }