Feature request > Network

\0 terminated SOCK_RECV command

(1/3) > >>

FutureCow:
The original SOCK_RECV() would chop your messages up nicely by stopping reading when a '\0' was read.
This was changed after I found I couldn't transmit binary files due to \0 characters through them.

Now I've found I could really do with two versions of the SOCK_RECV command.
1) The current one that will read \0 as part of the stream (for binary transfers)
2) One that terminates at \0 for non-binary transfers (i.e. the way SOCK_RECV used to work)

Currently if you send something like

--- Code: GLBasic ---SOCK_TCPSEND([socket],"SetLives=1")
SOCK_TCPSEND([socket],"SetLevel=14")
SOCK_TCPSEND([socket],"ResetHighScoreTable")
then do a
--- Code: GLBasic ---SOCK_RECV([socket],LivesString$,1023)
SOCK_RECV([socket],LevelString$,1023)
SOCK_RECV([socket],ResetString$,1023)
 InputString will contain "SetLives=1SetLevel=14ResetHighScoreTable" and LevelString$/ResetString$ will probably be empty. And it's not always consistent that all the output will be in the first SOCK_RECV() output as it depends on the timing when you run the SOCK_RECV command.

Having a new command that terminates on the '\0' means I could do 3 separate SOCK_RECV() calls and get each parameter and its setting separately for processing. Without it, I'm currently having to do something similar to the following (this is just an example, mines slightly more efficient)

--- Code: GLBasic ---Server
=======
SOCK_TCPSEND([socket],"SetLives=1")

Client
======
while Message$=""
    SOCK_RECV([sock],Message$,1023)
wend
if Message$="SetLives"
    SOCK_TCPSEND([socket],"Acknowledged")

Server
=======
while Message$=""
    SOCK_RECV([sock],Message$,1023)
wend
if Message$="Acknowledged"
    SOCK_TCPSEND([socket],"SetLevel=14")

[...]
 and so on which wastes time waiting for acknowledgements and causes excess network chatter, or some really annoying string manipulations to strip each different length string off the network stream.

Kitty Hello:
You get an ascii stream that has \0 characters? What is that?
If you know that, you could try SPLITSTR(str$, chr$(0));

FutureCow:
I thought from testing the old version that the tcp_send automatically inserted a "\0" at the end of each transmission string.   :noggin:  I assume from your reply that I'm probably incorrect though.

SPLITSTR isn't quite as neat, but it'll be easier than my current solution - thanks Gernot!

Kitty Hello:
now wait - the TCP_SEND will _not_ append a '\0' character, because web browsers don't send that, either.
If you receive, I will always force a '\0' at the end of what I read, so you can have a const char* to that string. With GLBasic only, you should not worry, because I have a length variable for each sting.
If you receive a string that contains a '\0' character, however, I'd be glad to hear where that comes from. Don't get me wrong, I'm not saying you do something wrong. It might easily be me missunderstanding of the specs.

FutureCow:
Okay now I'm getting confused!  :D
My problem was that I didn't know in advance (before changing my code anyway) how long a string I was going to be sending at various stages. I assumed I could send any string and a '\0' would automatically append. Therefore I thought I could send say 5 strings of various lengths (say <100 characters), and (in theory) do 5 sock_recv's of 1023 characters to read them and it would all work nicely.

I just made the assumption from what I saw that the strings would automatically have a '\0' on them from TCP_SEND.
I'll have to have a look tomorrow and see how people normally do efficient stream communication for separate messages they want to send. I'm currently sending a 8 char "header" and my code knows for each different that header I send how many chars follow. I then use MID$ to delete the total number of processed chars from the string, and reprocess the string until it's empty. It's not neat but the best solution to fit my needs at short notice.

Navigation

[0] Message Index

[#] Next page

Go to full version