Hi, usocket users
I want to mention, the "experimental-udp" branch has been merged into usocket trunk.
Changed API:
[SOCKET-CONNECT]
SOCKET-CONNECT now has a new keyword argument PROTOCOL with default :STREAM as tcp, but if you set it to :DATAGRAM, this means you're creating a UDP socket.
Be different with TCP socket, a UDP socket can be connected or unconnected. The method to create a unconnected UDP socket is to leave the first two argument of SOCKET-CONNECT as NIL:
(SOCKET-CONNECT NIL NIL :PROTOCOL :DATAGRAM)
Creating a server UDP socket which "listen" on local address is also supported, the method is to set additional keyword arguments: LOCAL-HOST and LOCAL-PORT:
(SOCKET-CONNECT NIL NIL :PROTOCOL :DATAGRAM :LOCAL-HOST nil :LOCAL-PORT 10000)
Notice: the "nil" as LOCAL-HOST means that you listen on wildcard address "0.0.0.0", same effect as *wildcard-host*.
[SOCKET-SEND]
Syntax: SOCKET-SEND usocket buffer length &key host port
SOCKET-SEND is used for sending packets through a UDP usocket, the "buffer" arguments usually need to be a vector of (unsigned-byte 8).
[SOCKET-RECEIVE]
Syntax: SOCKET-RECEIVE usocket buffer length &key
SOCKET-RECEIVE is used for receiving packets from a UDP usocket, the "buffer" argument will be filled into received data, but if you give NIL, this function will create a new buffer object for holding received data, the default buffer length will be 65536 which defined as a constant +max-datagram-packet-size+.
Notice: if you use this function to receive data from a unconnected socket, you may need to know where the data from. Actually, SOCKET-RECEIVE will return multiple values, the exact number is 4:
1. buffer (the same object as the "buffer" argument if it's not NIL when calling SOCKET-RECEIVE) 2. size (how many bytes received) 3. host (which address this data from) 4. port (which IP port this data from)
[SOCKET-SERVER]
Syntax: SOCKET-SERVER host port function &optional arguments &key (timeout 1) (max-buffer-size +max-datagram-packet-size+)
SOCKET-SERVER can create a simple single-threaded UDP server. This function is a indefinite loop, so you should create it in a new created thread using your platform's thread API.
The arguments "function" and "arguments" controls your UDP server's function, declaration of this function:
function (data &optional arguments)
This function will work like a filter, received data in, and return data send out. For example, a UDP Echo server can be defined in following code:
(defun echo-function (data) data)
And following code created this server on local port 10000:
(socket-server nil 10000 #'echo-function)
What if your filter function need to know where the data from? Get this information from two special variables: *REMOTE-HOST* and *REMOTE-PORT*.
The argument "timeout" can control the loop frequency, usually no need to modify. Read "server.lisp" for details.
The last important thing USOCKET user need to know: UDP support haven't been done on all CL platforms.
Current finished supported CL platforms:
* CMUCL * SBCL and ECL (not on win32) * Allegro CL * LispWorks (not on win32) * SCL * Clozure CL
Unfinished CL platforms:
* CLISP * Armedbear Common Lisp (ABCL) * Macintosh Common Lisp (MCL/RMCL)
And the USOCKET-UDP [1] project will be just closed. The function SOCKET-SYNC in that project will not be merged into USOCKET trunk because of less useful in most cases.
Bug reports, optimization suggestions, patches on unfinished platforms are all welcome. Thank you for using USOCKET project.
Regards,
Chun Tian (binghe)
[1] http://common-lisp.net/projects/cl-net-snmp/usocket.html
On Thu, Jan 7, 2010 at 11:02 AM, Chun Tian (binghe) binghe.lisp@gmail.comwrote:
Hi, usocket users
I want to mention, the "experimental-udp" branch has been merged into usocket trunk.
Changed API:
[SOCKET-CONNECT]
SOCKET-CONNECT now has a new keyword argument PROTOCOL with default :STREAM as tcp, but if you set it to :DATAGRAM, this means you're creating a UDP socket.
Be different with TCP socket, a UDP socket can be connected or unconnected. The method to create a unconnected UDP socket is to leave the first two argument of SOCKET-CONNECT as NIL:
(SOCKET-CONNECT NIL NIL :PROTOCOL :DATAGRAM)
It isn't clear to me how unconnected UDP sockets are to be used, since the host and port are unspecified. I would expect that most users would always want to use connected sockets.
Creating a server UDP socket which "listen" on local address is also
supported, the method is to set additional keyword arguments: LOCAL-HOST and LOCAL-PORT:
(SOCKET-CONNECT NIL NIL :PROTOCOL :DATAGRAM :LOCAL-HOST nil
:LOCAL-PORT 10000)
Notice: the "nil" as LOCAL-HOST means that you listen on wildcard address "0.0.0.0", same effect as *wildcard-host*.
[SOCKET-SEND]
Syntax: SOCKET-SEND usocket buffer length &key host port
SOCKET-SEND is used for sending packets through a UDP usocket, the "buffer" arguments usually need to be a vector of (unsigned-byte 8).
What does the return value of socket-send mean?
[SOCKET-RECEIVE]
Syntax: SOCKET-RECEIVE usocket buffer length &key
SOCKET-RECEIVE is used for receiving packets from a UDP usocket, the "buffer" argument will be filled into received data, but if you give NIL, this function will create a new buffer object for holding received data, the default buffer length will be 65536 which defined as a constant +max-datagram-packet-size+.
The constant +max-datagram-packet-size+ is not exported from the usocket package, and seems to be unbound when I try to access it.
When I try to call socket-receive with both buffer and length nil, it complains that they can't both be nil. I was under the impression that if I left both as nil then it would create a buffer of size +max-datagram-packet-size+.
Notice: if you use this function to receive data from a unconnected socket,
you may need to know where the data from. Actually, SOCKET-RECEIVE will return multiple values, the exact number is 4:
1. buffer (the same object as the "buffer" argument if it's not NIL
when calling SOCKET-RECEIVE) 2. size (how many bytes received) 3. host (which address this data from) 4. port (which IP port this data from)
[SOCKET-SERVER]
Syntax: SOCKET-SERVER host port function &optional arguments &key (timeout
- (max-buffer-size +max-datagram-packet-size+)
SOCKET-SERVER can create a simple single-threaded UDP server. This function is a indefinite loop, so you should create it in a new created thread using your platform's thread API.
The arguments "function" and "arguments" controls your UDP server's function, declaration of this function:
function (data &optional arguments)
This function will work like a filter, received data in, and return data send out. For example, a UDP Echo server can be defined in following code:
(defun echo-function (data) data)
And following code created this server on local port 10000:
(socket-server nil 10000 #'echo-function)
What if your filter function need to know where the data from? Get this information from two special variables: *REMOTE-HOST* and *REMOTE-PORT*.
The argument "timeout" can control the loop frequency, usually no need to modify. Read "server.lisp" for details.
The last important thing USOCKET user need to know: UDP support haven't been done on all CL platforms.
Current finished supported CL platforms:
- CMUCL
- SBCL and ECL (not on win32)
- Allegro CL
- LispWorks (not on win32)
- SCL
- Clozure CL
Unfinished CL platforms:
- CLISP
- Armedbear Common Lisp (ABCL)
- Macintosh Common Lisp (MCL/RMCL)
And the USOCKET-UDP [1] project will be just closed. The function SOCKET-SYNC in that project will not be merged into USOCKET trunk because of less useful in most cases.
Bug reports, optimization suggestions, patches on unfinished platforms are all welcome. Thank you for using USOCKET project.
Thanks for working on this. I'm eagerly awaiting full compatibility win32 implementations.
One more request:
Is there any way of having a timeout on socket-receive? Or at least have some way of checking whether there is any data waiting (so I don't have to block while waiting for packets to arrive)?
Thanks.
On Wed, Jan 13, 2010 at 6:02 PM, Elliott Slaughter < elliottslaughter@gmail.com> wrote:
On Thu, Jan 7, 2010 at 11:02 AM, Chun Tian (binghe) <binghe.lisp@gmail.com
wrote:
Hi, usocket users
I want to mention, the "experimental-udp" branch has been merged into usocket trunk.
Changed API:
[SOCKET-CONNECT]
SOCKET-CONNECT now has a new keyword argument PROTOCOL with default :STREAM as tcp, but if you set it to :DATAGRAM, this means you're creating a UDP socket.
Be different with TCP socket, a UDP socket can be connected or unconnected. The method to create a unconnected UDP socket is to leave the first two argument of SOCKET-CONNECT as NIL:
(SOCKET-CONNECT NIL NIL :PROTOCOL :DATAGRAM)
It isn't clear to me how unconnected UDP sockets are to be used, since the host and port are unspecified. I would expect that most users would always want to use connected sockets.
Creating a server UDP socket which "listen" on local address is also
supported, the method is to set additional keyword arguments: LOCAL-HOST and LOCAL-PORT:
(SOCKET-CONNECT NIL NIL :PROTOCOL :DATAGRAM :LOCAL-HOST nil
:LOCAL-PORT 10000)
Notice: the "nil" as LOCAL-HOST means that you listen on wildcard address "0.0.0.0", same effect as *wildcard-host*.
[SOCKET-SEND]
Syntax: SOCKET-SEND usocket buffer length &key host port
SOCKET-SEND is used for sending packets through a UDP usocket, the "buffer" arguments usually need to be a vector of (unsigned-byte 8).
What does the return value of socket-send mean?
[SOCKET-RECEIVE]
Syntax: SOCKET-RECEIVE usocket buffer length &key
SOCKET-RECEIVE is used for receiving packets from a UDP usocket, the "buffer" argument will be filled into received data, but if you give NIL, this function will create a new buffer object for holding received data, the default buffer length will be 65536 which defined as a constant +max-datagram-packet-size+.
The constant +max-datagram-packet-size+ is not exported from the usocket package, and seems to be unbound when I try to access it.
When I try to call socket-receive with both buffer and length nil, it complains that they can't both be nil. I was under the impression that if I left both as nil then it would create a buffer of size +max-datagram-packet-size+.
Notice: if you use this function to receive data from a unconnected socket,
you may need to know where the data from. Actually, SOCKET-RECEIVE will return multiple values, the exact number is 4:
1. buffer (the same object as the "buffer" argument if it's not NIL
when calling SOCKET-RECEIVE) 2. size (how many bytes received) 3. host (which address this data from) 4. port (which IP port this data from)
[SOCKET-SERVER]
Syntax: SOCKET-SERVER host port function &optional arguments &key (timeout
- (max-buffer-size +max-datagram-packet-size+)
SOCKET-SERVER can create a simple single-threaded UDP server. This function is a indefinite loop, so you should create it in a new created thread using your platform's thread API.
The arguments "function" and "arguments" controls your UDP server's function, declaration of this function:
function (data &optional arguments)
This function will work like a filter, received data in, and return data send out. For example, a UDP Echo server can be defined in following code:
(defun echo-function (data) data)
And following code created this server on local port 10000:
(socket-server nil 10000 #'echo-function)
What if your filter function need to know where the data from? Get this information from two special variables: *REMOTE-HOST* and *REMOTE-PORT*.
The argument "timeout" can control the loop frequency, usually no need to modify. Read "server.lisp" for details.
The last important thing USOCKET user need to know: UDP support haven't been done on all CL platforms.
Current finished supported CL platforms:
- CMUCL
- SBCL and ECL (not on win32)
- Allegro CL
- LispWorks (not on win32)
- SCL
- Clozure CL
Unfinished CL platforms:
- CLISP
- Armedbear Common Lisp (ABCL)
- Macintosh Common Lisp (MCL/RMCL)
And the USOCKET-UDP [1] project will be just closed. The function SOCKET-SYNC in that project will not be merged into USOCKET trunk because of less useful in most cases.
Bug reports, optimization suggestions, patches on unfinished platforms are all welcome. Thank you for using USOCKET project.
Thanks for working on this. I'm eagerly awaiting full compatibility win32 implementations.
-- Elliott Slaughter
"Don't worry about what anybody else is going to do. The best way to predict the future is to invent it." - Alan Kay
Hi again,
在 2010-1-14,10:15, Elliott Slaughter 写道:
One more request:
Is there any way of having a timeout on socket-receive? Or at least have some way of checking whether there is any data waiting (so I don't have to block while waiting for packets to arrive)?
Yes, there're two ways:
1) When creating the UDP socket using SOCKET-CONNECT, you can set the keyword argument TIMEOUT, and SOCKET-RECEIVE will return in that seconds when there's no data received.
2) You can use WAIT-FOR-INPUT, the same way as TCP usockets.
--binghe
Hi, Elliott
在 2010-1-14,10:02, Elliott Slaughter 写道:
It isn't clear to me how unconnected UDP sockets are to be used, since the host and port are unspecified. I would expect that most users would always want to use connected sockets.
To use a "unconnected" UDP socket, you can still use SOCKET-SEND and SOCKET-RECEIVE, however, since the sending target is not specified in the socket, you must use the keyword argument HOST and PORT each time you call SOCKET-SEND.
A "unconnected" UDP socket is very useful when you're trying to communicate with a lot of remote UDP servers but don't want or can't created correspond number of sockets.
[SOCKET-SEND]
Syntax: SOCKET-SEND usocket buffer length &key host port
SOCKET-SEND is used for sending packets through a UDP usocket, the "buffer" arguments usually need to be a vector of (unsigned-byte 8).
What does the return value of socket-send mean?
The return value of SOCKET-SEND is a integer which indicated how many bytes you actually send. In theory it should equal to the LENGTH argument in SOCKET-SEND, unless you're sending too much data. Currently the return value when sending fails is not defined clearly, for some CLs "-1" will mean "sending fail", but I think I should change it to "NIL" instead in the future.
Considering UDP is unreliable, I suggest users never expect every packets could be sent successfully, however, a check on return value of SOCKET-SEND is usually necessary because it means some serious mistake is happening (i.e. no network), not that packets are dropped on their way.
The constant +max-datagram-packet-size+ is defined in usocket.lisp, line 14:
(defconstant +max-datagram-packet-size+ 65536)
I didn't export the symbol +MAX-DATAGRAM-PACKET-SIZE+ because it's a constant and hard limit of UDP implementation. Users don't need to change it's value, instead, there're extra keyword arguments in API functions when user want to set maximum packet sizes.
--binghe
Thanks for working on this. I'm eagerly awaiting full compatibility win32 implementations.
-- Elliott Slaughter
"Don't worry about what anybody else is going to do. The best way to predict the future is to invent it." - Alan Kay
2010/1/13 Chun Tian (binghe) binghe.lisp@gmail.com
Hi, Elliott
在 2010-1-14,10:02, Elliott Slaughter 写道:
[SOCKET-SEND]
Syntax: SOCKET-SEND usocket buffer length &key host port
SOCKET-SEND is used for sending packets through a UDP usocket, the
"buffer" arguments usually need to be a vector of (unsigned-byte 8).
What does the return value of socket-send mean?
The return value of SOCKET-SEND is a integer which indicated how many bytes you actually send. In theory it should equal to the LENGTH argument in SOCKET-SEND, unless you're sending too much data. Currently the return value when sending fails is not defined clearly, for some CLs "-1" will mean "sending fail", but I think I should change it to "NIL" instead in the future.
I would probably expect usocket to throw an error if the packet failed to be sent. I would prefer that to having a special return value for failure.
The constant +max-datagram-packet-size+ is defined in usocket.lisp, line 14:
(defconstant +max-datagram-packet-size+ 65536)
I didn't export the symbol +MAX-DATAGRAM-PACKET-SIZE+ because it's a constant and hard limit of UDP implementation. Users don't need to change it's value, instead, there're extra keyword arguments in API functions when user want to set maximum packet sizes.
I'm not trying to imply that users would want to change this value, since it is a system constant, but that users might want to use it as a parameter to length in socket-receive as usocket throws an error if both buffer and length are nil. Or you might just want this to be the default (when they are both nil).
Thanks for answering my questions.
The constant +max-datagram-packet-size+ is defined in usocket.lisp, line 14:
(defconstant +max-datagram-packet-size+ 65536)
I didn't export the symbol +MAX-DATAGRAM-PACKET-SIZE+ because it's a constant and hard limit of UDP implementation. Users don't need to change it's value, instead, there're extra keyword arguments in API functions when user want to set maximum packet sizes.
I'm not trying to imply that users would want to change this value, since it is a system constant, but that users might want to use it as a parameter to length in socket-receive as usocket throws an error if both buffer and length are nil. Or you might just want this to be the default (when they are both nil).
Really? Then it's a bug, I'll investigate and fix it.
Thanks for pointing out this.
--binghe
Thanks for answering my questions.
-- Elliott Slaughter
"Don't worry about what anybody else is going to do. The best way to predict the future is to invent it." - Alan Kay