Пример #1
0
        public void SaveSendStats(string providerKey, PacketIdentity packetId, SendStats stats)
        {
            var packetFilePath      = this.GetPacketFilePath(providerKey, packetId);
            var packetStatsFilePath = packetFilePath + this.packetStatsExt;

            this.RunInWriteLock(providerKey, () =>
            {
                if (stats.TransferCompleted)
                {
                    FileSystemHelper.DeleteFile(packetStatsFilePath);
                    FileSystemHelper.DeleteFile(packetFilePath);
                }
                else
                {
                    AtomicFileWriteHelper.WriteToFile(packetStatsFilePath, JsonConvert.SerializeObject(stats), sendStatsEncoding, sendStatsOptions);
                }
            });
        }
Пример #2
0
 private static Func<byte[], int, bool, bool> GetSender(SharedNetworkInfo sharedInfo, SendStats stats = null)
 {
     List<byte> datablock = new List<byte>();
     byte[] tempBuffer = new byte[1024 * 1024];
     return (byte[] data, int size, bool flush) =>
     {
         int totalSize = datablock.Count + size;
         int blockSize = 1024 * 1024;
         int remainder = size;
         int offset = 0;
         while (totalSize > blockSize)
         {
             datablock.CopyTo(0, tempBuffer, 0, datablock.Count);
             int nextBlockSize = blockSize - datablock.Count;
             if (nextBlockSize > remainder)
                 nextBlockSize = remainder;
             Array.Copy(data, offset, tempBuffer, datablock.Count, nextBlockSize);
             offset += nextBlockSize;
             datablock.Clear();
             totalSize -= blockSize;
             remainder -= nextBlockSize;
             DataPayload dataPack = new DataPayload() { Data = tempBuffer, EndOfStream = false };
             Utilities.SendEncrypted<DataPayload>(sharedInfo, dataPack);
             var reply = ProtoBuf.Serializer.DeserializeWithLengthPrefix<NetCommand>(sharedInfo.Stream, ProtoBuf.PrefixStyle.Fixed32);
             if (reply.Type != NetCommandType.DataReceived)
                 return false;
             if (stats != null)
             {
                 stats.BytesSent += dataPack.Data.Length;
             }
         }
         if (remainder > 0)
         {
             for (int i = offset; i < size; i++)
                 datablock.Add(data[i]);
         }
         if (flush)
         {
             DataPayload dataPack = new DataPayload() { Data = datablock.ToArray(), EndOfStream = true };
             Utilities.SendEncrypted<DataPayload>(sharedInfo, dataPack);
             var reply = ProtoBuf.Serializer.DeserializeWithLengthPrefix<NetCommand>(sharedInfo.Stream, ProtoBuf.PrefixStyle.Fixed32);
             if (reply.Type != NetCommandType.DataReceived)
                 return false;
             if (stats != null)
             {
                 stats.BytesSent += dataPack.Data.Length;
             }
         }
         return true;
     };
 }
Пример #3
0
        internal static bool SendVersions(SharedNetworkInfo sharedInfo, Stack<Objects.Version> versionsToSend)
        {
            try
            {
                int ackCount = 0;
                byte[] tempBuffer = new byte[16 * 1024 * 1024];
                if (versionsToSend.Count == 0)
                {
                    ProtoBuf.Serializer.SerializeWithLengthPrefix<NetCommand>(sharedInfo.Stream, new NetCommand() { Type = NetCommandType.SynchronizeRecords }, ProtoBuf.PrefixStyle.Fixed32);
                    var dataResponse = ProtoBuf.Serializer.DeserializeWithLengthPrefix<NetCommand>(sharedInfo.Stream, ProtoBuf.PrefixStyle.Fixed32);
                    if (dataResponse.Type == NetCommandType.Synchronized)
                        return true;
                    return false;
                }
                Printer.PrintDiagnostics("Synchronizing {0} versions to server.", versionsToSend.Count);
                while (versionsToSend.Count > 0)
                {
                    List<Objects.Version> versionData = new List<Objects.Version>();
                    while (versionData.Count < 512 && versionsToSend.Count > 0)
                    {
                        versionData.Add(versionsToSend.Pop());
                    }
                    Printer.PrintDiagnostics("Sending version data pack...");
                    ProtoBuf.Serializer.SerializeWithLengthPrefix<NetCommand>(sharedInfo.Stream, new NetCommand() { Type = NetCommandType.PushVersions }, ProtoBuf.PrefixStyle.Fixed32);
                    VersionPack pack = CreatePack(sharedInfo, versionData);
                    Utilities.SendEncrypted(sharedInfo, pack);
                    ackCount++;
                }
                while (ackCount-- > 0)
                {
                    NetCommand response = ProtoBuf.Serializer.DeserializeWithLengthPrefix<NetCommand>(sharedInfo.Stream, ProtoBuf.PrefixStyle.Fixed32);
                    if (response.Type != NetCommandType.Acknowledge)
                        return false;
                }
                ProtoBuf.Serializer.SerializeWithLengthPrefix<NetCommand>(sharedInfo.Stream, new NetCommand() { Type = NetCommandType.SynchronizeRecords }, ProtoBuf.PrefixStyle.Fixed32);
                while (true)
                {
                    var command = ProtoBuf.Serializer.DeserializeWithLengthPrefix<NetCommand>(sharedInfo.Stream, ProtoBuf.PrefixStyle.Fixed32);
                    if (command.Type == NetCommandType.RequestRecordParents)
                    {
                        Printer.PrintDiagnostics("Remote vault is asking for record metadata...");
                        var rrp = Utilities.ReceiveEncrypted<RequestRecordParents>(sharedInfo);
                        RecordParentPack rp = new RecordParentPack();
                        rp.Parents = rrp.RecordParents.Select(x => sharedInfo.Workspace.GetRecord(x)).ToArray();
                        Utilities.SendEncrypted<RecordParentPack>(sharedInfo, rp);
                    }
                    else if (command.Type == NetCommandType.RequestRecord)
                    {
                        var rrd = Utilities.ReceiveEncrypted<RequestRecordData>(sharedInfo);
                        Printer.InteractivePrinter printer = null;
                        SendStats sstats = null;
                        System.Diagnostics.Stopwatch sw = null;
                        if (sharedInfo.Client)
                        {
                            sstats = new SendStats();
                            sw = new System.Diagnostics.Stopwatch();
                            Printer.PrintMessage("Remote has requested #b#{0}## records...", rrd.Records.Length);
                            printer = Printer.CreateProgressBarPrinter("Sending data", string.Empty,
                                    (obj) =>
                                    {
                                        return string.Format("{0}/sec", Versionr.Utilities.Misc.FormatSizeFriendly((long)(sstats.BytesSent / sw.Elapsed.TotalSeconds)));
                                    },
                                    (obj) =>
                                    {
                                        return (100.0f * (int)obj) / (float)rrd.Records.Length;
                                    },
                                    (pct, obj) =>
                                    {
                                        return string.Format("{0}/{1}", (int)obj, rrd.Records.Length);
                                    },
                                    60);
                            sw.Start();
                        }
                        Func<byte[], int, bool, bool> sender = GetSender(sharedInfo, sstats);
                        int processed = 0;
                        foreach (var x in rrd.Records)
                        {
                            var record = sharedInfo.Workspace.GetRecord(x);
                            Printer.PrintDiagnostics("Sending data for: {0}", record.CanonicalName);
                            if (!sharedInfo.Workspace.TransmitRecordData(record, sender, tempBuffer, () =>
                            {
                                sender(BitConverter.GetBytes(x), 8, false);
                            }))
                            {
                                sender(BitConverter.GetBytes(-x), 8, false);
                            }
                            if (printer != null)
                                printer.Update(processed++);
                        }
                        if (!sender(new byte[0], 0, true))
                            return false;

                        if (printer != null)
                            printer.End(rrd.Records.Length);

                        var dataResponse = ProtoBuf.Serializer.DeserializeWithLengthPrefix<NetCommand>(sharedInfo.Stream, ProtoBuf.PrefixStyle.Fixed32);
                        if (dataResponse.Type != NetCommandType.Acknowledge)
                            return false;
                    }
                    else if (command.Type == NetCommandType.RequestRecordUnmapped)
                    {
                        SharedNetwork.SendRecordDataUnmapped(sharedInfo);
                    }
                    else if (command.Type == NetCommandType.Synchronized)
                    {
                        return true;
                    }
                    else
                    {
                        throw new Exception(string.Format("Invalid command: {0}", command.Type));
                    }
                }
            }
            catch (Exception e)
            {
                Printer.PrintError("Error: {0}", e);
                return false;
            }
        }