#.net #sockets #tcp #file-transfer
#.net #сокеты #tcp #передача файлов
Вопрос:
Я пытаюсь использовать функцию TCP / Sockets внутри System.Net.Sockets для передачи файлов. Но, когда я пытаюсь динамически установить размер буфера на клиенте и на сервере, если размер меньше 4096, передача выполняется хорошо, но если он больше 4096, буфер сохраняет значение 4096, и поэтому файл не принимается полностью.
Итак, мне было интересно? Это максимальное значение? Если да, безопасно ли использовать буфер, который заполняется циклом на клиенте и принимается тем же методом на сервере?
Спасибо за помощь.
Ответ №1:
Я однажды написал похожий и очень простой файловый приемник с сокетами (просто чтобы попробовать сокеты, поэтому код не такой уж красивый):
Socket socket = new Socket(AddressFamily.InterNetwork, SocketType.Stream, ProtocolType.Tcp);
EndPoint endpoint = new IPEndPoint(IPAddress.Any, 2442);
socket.Bind(endpoint);
socket.Listen(10000);
System.Console.WriteLine("Waiting for incoming data on *:2442");
Socket client = socket.Accept();
byte[] buffer = new byte[2000];
List<byte> wholeThing = new List<byte>();
int count = 0;
do {
count = client.Receive(buffer);
for (int i = 0 ; i < count ; i )
wholeThing.Add(buffer[i]);
System.Console.Write("*");
} while (count > 0);
System.Console.WriteLine(Environment.NewLine "Received {0} bytes of data", wholeThing.Count);
File.WriteAllBytes(Application.StartupPath "\receivedFile", wholeThing.ToArray());
Код отправителя выглядел следующим образом:
byte[] fileData = File.ReadAllBytes(fileName);
Socket socket = new Socket(AddressFamily.InterNetwork, SocketType.Stream, ProtocolType.Tcp);
socket.Connect(IPAddress.Parse(targetip), 2442);
int offset = 0;
do {
try {
offset = socket.Send(fileData, offset, fileData.Length - offset, SocketFlags.None);
} catch {
socket.Close();
throw;
}
} while (offset < fileData.Length);
Ответ №2:
Если вы пытаетесь отправить файлы большего размера, .net обычно разбивает их на более мелкие фрагменты. Вам необходимо повторно собирать данные по мере их получения, по частям, на стороне клиента. Я думаю, что класс ConnectionPacketBuilder в networkComms.net , строка 134 здесь достигает того, что вы хотите сделать. Вы можете видеть, как он используется, когда данные поступают в строку 793.