Re: [twsocket] Sending Record Type Data over tcp

2009-06-30 Thread Francois Piette
 My record type is like;
 TData = record
   age: integer;
 end;
 PData = ^TData;

 I send data as follows succesfully;
 Send(Data, SizeOf(TData));

 and receive;
 Receive(Data, SizeOf(TData));

 What i want to do is to send a couple of record types (seperately); and
 distinguish them on the client side.
 i tried moving data into a PChar variable, ant put some distinguisher in
 front of data, but this didnt worked out, or i couldnt..

I will assume you are using TCP, not UDP.
I see two problems in your design:
1) Receive will receive what is available, at most the size you specifyed.
It is well possible that not all data are already arrived. It works in you
case because you sent an integer (4 bytes) which is likely to arrive in one
data packet. If you had larger data, it is likely it would be split into
several packets and you would get several OnDataAvailable events.
2) TCP is a stream oriented connection. This means there is no record
concept in the data stream. It is just a bidirectional byte stream, just
like a simple file stream. The impact is that the receiver has no way to
know you send 2 of your records seperately or a single large record. You
must add yourself a delimiter between your records, or add a length field in
front of your record.

Please have a look at TCP/UDP primer available from
http://wiki.overbyte.be/wiki/index.php/FAQ.Difference

--
francois.pie...@overbyte.be
Author of ICS (Internet Component Suite, freeware)
Author of MidWare (Multi-tier framework, freeware)
http://www.overbyte.be

--
To unsubscribe or change your settings for TWSocket mailing list
please goto http://lists.elists.org/cgi-bin/mailman/listinfo/twsocket
Visit our website at http://www.overbyte.be


Re: [twsocket] Sending Record Type Data over tcp

2009-06-30 Thread Alper Albayrak
Yes, Im using TCP.
I solved my problem (at least in here) with replacing Move() into
CopyMemory()

I'm using LineMode, to receive all data sent. (My data size is 49b in total
and no string data in it)
Are there any conflicts i may encounter in the approach stated below?
(I intend to replace Rcvd variable with a global one to prevent having
allocating it in every receive)

Thank you for help and kind replies..

procedure TMainForm.WSocket1DataAvailable(Sender: TObject; ErrCode: Word);
var
  Rcvd: PChar;
  RcvdSize: integer;
  Data: PStatus;
begin
  if ErrCode  0 then exit;
  GetMem(Rcvd, 128);
  with (Sender as TWSocket) do
  try
RcvdSize := Receive(Rcvd, 128);
if RcvdSize  0 then exit;

case Ord(Rcvd[0]) of // Choose data type
  0: begin
New(Data);
try
  CopyMemory(Data, @Rcvd[1], SizeOf(TStatus));
  ...
except
  Dispose(Data);
end;
  end;

  1: begin
  ...
  end;
end;
  finally
FreeMem(Rcvd);
  end;
end;
--
To unsubscribe or change your settings for TWSocket mailing list
please goto http://lists.elists.org/cgi-bin/mailman/listinfo/twsocket
Visit our website at http://www.overbyte.be


Re: [twsocket] Sending Record Type Data over tcp

2009-06-30 Thread Fastream Technologies
Is your data size fixed? If so, it might work. The method I suggested was
for variable data size.
Regards,

SZ


On Tue, Jun 30, 2009 at 7:29 PM, Alper Albayrak alper...@gmail.com wrote:

 Yes, Im using TCP.
 I solved my problem (at least in here) with replacing Move() into
 CopyMemory()

 I'm using LineMode, to receive all data sent. (My data size is 49b in total
 and no string data in it)
 Are there any conflicts i may encounter in the approach stated below?
 (I intend to replace Rcvd variable with a global one to prevent having
 allocating it in every receive)

 Thank you for help and kind replies..

 procedure TMainForm.WSocket1DataAvailable(Sender: TObject; ErrCode: Word);
 var
  Rcvd: PChar;
  RcvdSize: integer;
  Data: PStatus;
 begin
  if ErrCode  0 then exit;
  GetMem(Rcvd, 128);
  with (Sender as TWSocket) do
  try
RcvdSize := Receive(Rcvd, 128);
if RcvdSize  0 then exit;

case Ord(Rcvd[0]) of // Choose data type
  0: begin
New(Data);
try
  CopyMemory(Data, @Rcvd[1], SizeOf(TStatus));
  ...
except
  Dispose(Data);
end;
  end;

  1: begin
  ...
  end;
end;
  finally
FreeMem(Rcvd);
  end;
 end;
  --

--
To unsubscribe or change your settings for TWSocket mailing list
please goto http://lists.elists.org/cgi-bin/mailman/listinfo/twsocket
Visit our website at http://www.overbyte.be


Re: [twsocket] Sending Record Type Data over tcp

2009-06-30 Thread Arno Garrels
Alper Albayrak wrote:
 Yes, Im using TCP.
 I solved my problem (at least in here) with replacing Move() into
 CopyMemory()
 
 I'm using LineMode, to receive all data sent. (My data size is 49b in
 total and no string data in it)

That is dangerous! Are you able to exclude that the LineEnd bytes will
never be found in your binary data? I don't think so.

ICS v7 contains a demo that shows one way to send binary data mixed with 
string data: 
http://svn.overbyte.be:8443/svn/ics/branches/icsv7/Delphi/Internet/OverbyteIcsBinCliDemo1.pas
(http://wiki.overbyte.be/wiki/index.php/FAQ#How_to_get_ICS)

 Are there any conflicts i may encounter in the approach stated below?
 (I intend to replace Rcvd variable with a global one to prevent having
 allocating it in every receive)

A global buffer is the way to go. Do not use PChar for binary data but
either TBytes, PByte or PAnsiChar, that makes it easier to convert the
code to support Unicode later on.   

--
Arno Garrels

--
To unsubscribe or change your settings for TWSocket mailing list
please goto http://lists.elists.org/cgi-bin/mailman/listinfo/twsocket
Visit our website at http://www.overbyte.be


Re: [twsocket] Sending Record Type Data over tcp

2009-06-30 Thread RTT

Some remarks:
As Francois said, you need to check you received all the data. Your code 
don't check if RcvdSize is equal to your record data size.
Why you need to copy the memory? If you are going to use it locally, at 
that procedure, just point your different records Data pointers to the 
Rcvd buffer.

And why you don't use only one record, with variant part?

TEmployee = record
 FirstName, LastName: string[40];
 BirthDate: TDate;
 case Salaried: Boolean of
   True: (AnnualSalary: Currency);
   False: (HourlyWage: Currency);
end;

RTT
--
To unsubscribe or change your settings for TWSocket mailing list
please goto http://lists.elists.org/cgi-bin/mailman/listinfo/twsocket
Visit our website at http://www.overbyte.be


Re: [twsocket] Sending Record Type Data over tcp

2009-06-30 Thread Wilfried Mestdagh
Hello Alper,

 I'm using LineMode, to receive all data sent. (My data size is 49b in total
 and no string data in it)
 Are there any conflicts i may encounter in the approach stated below?

Yes, if your binary data contains the line end characters you use the
your code will fail as Arno already mentioned.

Second, if you do not receive your whole data, but only a part of it
then your code will fail too. Also it is possible you receive your whole
packet and a part (or whole) of the next packet (depending on speed of
the transmitting prgram).

 (I intend to replace Rcvd variable with a global one to prevent having
 allocating it in every receive)

Good, allocating each time will slow down and possible to have
fragmented memory if you have hi speed transmission / reception. Not
need to use a global, but a class variable will do the same (but that's
probably what you mean).

 if RcvdSize  0 then exit;

You may better change this to:
  if RcvdSize = 0 then
 Exit;
Because if you receive nothing (0) then you can exit here also.
Somethime Winsock tell to receive and does not wants to give data (I
think Winsock is a women ;-)

 case Ord(Rcvd[0]) of // Choose data type
   0: begin
 New(Data);
 try
   CopyMemory(Data, @Rcvd[1], SizeOf(TStatus));

Yes oke, but what if you have just received one byte here? Then this
will fail.

You can use LineMode but then you have to make sure the line end
character(s) you want to use ar never in your data. Several approch ar
possible, Look at my article on 
http://wiki.overbyte.be/wiki/index.php/Sending_and_receiving_data
wich explain some of the possible approaches for binary data.

---
Rgds, Wilfried [TeamICS]
http://www.overbyte.be/eng/overbyte/teamics.html
http://www.mestdagh.biz

Tuesday, June 30, 2009, 18:29, Alper Albayrak wrote:

 Yes, Im using TCP.
 I solved my problem (at least in here) with replacing Move() into
 CopyMemory()

 I'm using LineMode, to receive all data sent. (My data size is 49b in total
 and no string data in it)
 Are there any conflicts i may encounter in the approach stated below?
 (I intend to replace Rcvd variable with a global one to prevent having
 allocating it in every receive)

 Thank you for help and kind replies..

 procedure TMainForm.WSocket1DataAvailable(Sender: TObject; ErrCode: Word);
 var
   Rcvd: PChar;
   RcvdSize: integer;
   Data: PStatus;
 begin
   if ErrCode  0 then exit;
   GetMem(Rcvd, 128);
   with (Sender as TWSocket) do
   try
 RcvdSize := Receive(Rcvd, 128);
 if RcvdSize  0 then exit;

 case Ord(Rcvd[0]) of // Choose data type
   0: begin
 New(Data);
 try
   CopyMemory(Data, @Rcvd[1], SizeOf(TStatus));
   ...
 except
   Dispose(Data);
 end;
   end;

   1: begin
   ...
   end;
 end;
   finally
 FreeMem(Rcvd);
   end;
 end;
 --
 To unsubscribe or change your settings for TWSocket mailing list
 please goto http://lists.elists.org/cgi-bin/mailman/listinfo/twsocket
 Visit our website at http://www.overbyte.be

--
To unsubscribe or change your settings for TWSocket mailing list
please goto http://lists.elists.org/cgi-bin/mailman/listinfo/twsocket
Visit our website at http://www.overbyte.be