{-----------------------------------------------------------------}
{ Priklad na odesilani a prijem dat pomoci protokolu TCP          }
{ Tento priklad vyuziva knihovnu CoINET, ktera nebyla v praci     }
{ zminovana. Jejim ukolem je zjednoduseni vytvareni zarizeni      }
{ TCP/IP zasobniku                                                }
{-----------------------------------------------------------------}

program TcpSample;

uses
  CoBase,
  CoEth01,
  CoIPv4,
  CoTCP,
  CoINET;


var
  Status    : TCoStatus;              { Stav vysledku operace           }
  Sock      : PCoDevice;              { Ukazatel na instanci zarizeni   }
  Data      : array[0..1023] of Byte; { Data ramce                      }
  RecvLen   : Word;                   { Delka prijateho ramce           }
  SAddress  : TTcpAddress;            { Cilova adresa                   }


  { Procedura pripravujici data odesilaneho ramce }
  procedure ProduceData;
  begin
    { ... }
  end;

  { Procedura zpracovavajici data prijateho ramce }
  procedure ConsumeData;
  begin
    { ... }
  end;

begin

  { Vytvoreni TCP/IP zasobniku nad zarizenim ETH01 s bazovou adresou  }
  { $2300. IP protokol bude nakonfigurovan na IP adresu 192.168.1.210 }
  { a masku 255.255.255.0                                             }

  Status := NetOpenStack( 'ETH01', 'IOBASE=$310',
             'IPADDR=192.168.1.210 NETMASK=255.255.255.0', '' );

  if Status <> CST_SUCCESS then
  begin
    WriteLn( 'NetOpenStack() failed: ', CoStatusToStr( Status ) );
  end
  else begin
    { TCP/IP stack byl uspesne vytvoren }

    { Vytvorime TCP zasuvku naslouchajici na lokalni portu 5000 }
    Status := NetOpenSocket( 'TCP', 'LPORT=5000', '', Sock );

    if Status <> CST_SUCCESS then
    begin
    end
    else begin

      { Inicializace vsech vrstev TCP/IP zasobniku }
      Status := Sock^.CoBind( nil, COF_PROPAGATE, nil );

      if Status = CST_SUCCESS then
      begin

        { Navazani spojeni }

        with SAddress do
        begin
          Size    := SizeOf( TTcpAddress );
          Address := MakeIpAddr( 192, 168, 1, 1 ); { Adresa stanice }
          Port    := 5000;                         { Port           }
        end;

        Status := Sock^.CoConnect( @SAddress, 0, nil );

        if Status <> CST_SUCCESS then
        begin
          WriteLn( 'CoConnect() failed: ', Sock^.CoStatusToStr( Status ) );
        end
        else begin
         { Spojeni bylo navazano }


         { Naplneni dat urcenych k odvysilani }
         ProduceData;


         { Odesleme blok dat }

         Status := Sock^.CoSendBuffer( @Data, SizeOf(Data), 0, nil );

         if Status <> CST_SUCCESS then
         begin
           WriteLn( 'CoSendBuffer() failed: ', Sock^.CoStatusToStr( Status ) );
         end;

         Status := Sock^.CoRecvBuffer( @Data, SizeOf(Data), @RecvLen, 0, nil );

         if Status <> CST_SUCCESS then
         begin
           WriteLn( 'CoRecvBuffer() failed: ', Sock^.CoStatusToStr( Status ) );
         end
         else begin
           { Zpracovani prijatych dat }
           ConsumeData;
         end;


         { Zaver spojeni }

         Status := Sock^.CoDisconnect( 0, nil );

         if Status <> CST_SUCCESS then
         begin
           WriteLn( 'CoDisconnect() failed: ', Sock^.CoStatusToStr( Status ) );
         end;

        end;

         { Deinicializace vsech vrstvev TCP/IP zasobniku }
        Status := Sock^.CoUnbind( COF_PROPAGATE, nil );
      end;

      { Uvolneni zarizeni TCP zasuvky }
      NetCloseSocket( Sock );
    end;

    { Uvolneni vsech ostatnich zarizeni TCP/IP stacku }
    NetCloseStack( '' );
  end;

end.
