Конференция "Сети" » Не пойму где ошибка(сокеты)...
 
  • Sergl (01.11.07 10:05) [0]
    Передаю файл через сокеты.
    На сервере:

    procedure TForm1.ServerSocket1ClientRead(Sender: TObject;
     Socket: TCustomWinSocket);
    var ms:tmemorystream;
    begin
    if serversocket1.Socket.Connections[0].ReceiveText='get_file' then begin
      showmessage('file------');
      ms:= TMemoryStream.Create;
      try
        // Получаем данные на передачу.
        ms.LoadFromFile(PChar(maskedit1.Text));
        ms.Position:= 0;
        // Добавляем длину данных, чтобы клиент знал, сколько данных будет передано
        // Добавляем #0 , чтобы можно было определить, где заканчивается информация о размере.
        Socket.SendText(IntToStr(ms.Size) + #0);
        // Посылаем его.
        Socket.SendStream(ms);
        socket.SendText('#end_file#');
      except
        // Итак, осталось освободить поток, если что-то не так.
        ms.Free;
     end;
    end;
    end;



    на кленте:

    procedure TForm1.ClientSocket1Read(Sender: TObject;
     Socket: TCustomWinSocket);
     var s, sl: string;
         prov:bool;
    begin
    s:= Socket.ReceiveText;
    // Если мы не в режиме приёма:
    if not Reciving then
    begin
      // Теперь нам необходимо получить длину потока данных.
      SetLength(sl, StrLen(PChar(s))+1); // +1 for the null terminator
      StrLCopy(@sl[1], PChar(s), Length(sl)-1);
      DataSize:= StrToInt(sl);
      Data:= TMemoryStream.Create;
      // Удаляем информацию о размере из данных.
      Delete(s, 1, Length(sl));
      Reciving:= true;
    end;
    // Сохраняем данные в файл, до тех пор, пока не получим все данные.
    if copy(s,length(s)-9,10)='#end_file#' then begin
    //  showmessage('Ура');
     prov:=true;
    //  Delete(s,length(s)-9,10);
    end;
    if s<>'#end_file#' then prov:=false;
    try
    if prov=false then Data.Write(s[1], length(s));

    if prov=true then begin
      if Data.Size = DataSize then
      begin
        Data.Position:= 0;
        data.SaveToFile('c:\000.jpg');
        Data.Free;
        Reciving:= false;
    //     Socket.Close;
        showmessage('Файл принят');
      end else showmessage('Файл принят не удачно');
     end;
    except
      Data.Free;
    end;
    end;



    Данные клиент получает, но не читает что ему пришло "#end_file#". Почему?
  • Сергей М. © (01.11.07 10:43) [1]

    > не читает что ему пришло "#end_file#". Почему?


    Потому что "#end_file#" ему не пришло.
  • Sergl (01.11.07 10:46) [2]
    Как сделать что-бы ему это пришло?
  • Slym © (01.11.07 10:59) [3]
    // Итак, осталось освободить поток, если что-то не так - не нужно
    На лицо работа с неблокирующими сокетами в блокирующей манере... непалучедся :)
  • Sergl (01.11.07 11:04) [4]

    > На лицо работа с неблокирующими сокетами в блокирующей манере.
    > .. непалучедся

    Подкинте пожалуйста литературу(ссылок) про работа с блокированием и не блокированием.
  • Slym © (01.11.07 11:04) [5]
    Sergl   (01.11.07 10:05)
    Данные клиент получает, но не читает что ему пришло "#end_file#". Почему?

    Объясняю:
    Socket.SendStream(ms); - послал только одну "пачку" данных до возникновения WOULBLOCK и вышел
    socket.SendText('#end_file#');
    посылаешь маркер конца файла, но файл фактически не отправлен... т.к. оставшиеся "пачки" Stream досылаются по мере освобождения отправляющего буфера
  • Slym © (01.11.07 11:08) [6]
    Sergl   (01.11.07 11:04) [4]
    Подкинте пожалуйста литературу(ссылок) про работа с блокированием и не блокированием.

    http://pda.delphimaster.net/?id=1192377094&n=4
  • Sergl (01.11.07 11:10) [7]
    Вместо socket.sendtext('#end_file#') дописать к ms, перед тем как отправить вот это ms.read('#end_file#',10);

    Так пойдет?
  • Slym © (01.11.07 11:13) [8]
    Sergl   (01.11.07 11:10) [7]
    Так пойдет?

    Ходьбой это не назавешь... Похромает...
  • Sergl (01.11.07 11:21) [9]
    Не хочет дописывать... ms.read('#end_file#',10);
    Как дописать?
  • Slym © (01.11.07 11:22) [10]
    Sergl   (01.11.07 11:21) [9]
    Write :)
  • Сергей М. © (01.11.07 11:23) [11]

    > Не хочет дописывать


    А где ты дописываешь ? Нигде)
    read по-буржуйски - это читать, а не писать)
  • Sergl (01.11.07 11:24) [12]

    > Write :)

    Извеняюсь за тупость:)
    Однако #end_file# так и не находит...
  • Сергей М. © (01.11.07 11:49) [13]

    > DataSize:= StrToInt(sl);


    С чего ты взял, что в sl находится строка, содержащая ожидаемок число, и ничего более кроме этого числа ?
  • Slym © (01.11.07 12:55) [14]
    Sergl   (01.11.07 11:24) [12]
    за тупость:)

    Для особотупых повторяю: http://pda.delphimaster.net/?id=1192377094&n=4
  • Sergl © (01.11.07 12:57) [15]

    > Для особотупых повторяю

    Попрошу без хамства... За ссылку спасибо.
  • Sergl © (01.11.07 13:04) [16]

    > С чего ты взял, что в sl находится строка, содержащая ожидаемок
    > число, и ничего более кроме этого числа ?

    Я с сервера, перед отправкой файла, передаю вот это     Socket.SendText(IntToStr(ms.Size) + #0);
    Я так думаю что клиент следующим сообщением получает ms.Size
  • Sergl © (01.11.07 13:20) [17]
    Как, всетаки, дописать к моему потоку, перед отправкой, #end_file#.
    Так ms.write(#end_file#,10)  - что то не работает
  • Sergl © (01.11.07 13:22) [18]
    Ковычки забыл) - ms.write('#end_file#',10);
  • Сергей М. © (01.11.07 13:38) [19]

    > клиент следующим сообщением получает ms.Size
    >


    Может получить, а может и не получить.

    TCP - протокол поточный, а не месседж-ориентированный, в нем нет разбиения на сообщения, данные передаются сплошным потоком.
 
Конференция "Сети" » Не пойму где ошибка(сокеты)...
Есть новые Нет новых   [134431   +10][b:0][p:0.003]