From: Peter H. <p....@gm...> - 2005-10-22 16:51:55
|
Hi, I am looking for an example how to use the sb-bsd-sockets, especially how to create a stream or something else read-/writeable from the result of (socket-accept ..) TYIA Peter |
From: Patrick M. <pat...@in...> - 2005-10-22 17:29:08
|
Peter Herth writes: > I am looking for an example how to use the sb-bsd-sockets, > especially how to create a stream or something else read-/writeable > from the result of (socket-accept ..) Here's an example I cobbled together to demonstrate how to use the Chain of Responsibility pattern in both Java and Lisp: http://www.spe.com/pjm/message-broker.html It uses sb-bsd-sockets. Regards, Patrick ------------------------------------------------------------------------ Patrick May | IntaMission Software Ltd. | Thames Court, 1 Victoria Street pat...@in... | Windsor, Berkshire, SL4 1YB, UK |
From: Peter H. <p....@gm...> - 2005-10-22 18:10:22
|
Thanks, your example helped :) The trick is the parameter list to socket-make-stream, so for all who may have the same problem, it works for me now with: (setf socket (make-instance 'inet-socket :type :stream :protocol :tcp)) (socket-bind socket (make-inet-address "127.0.0.1" ) 8030) (socket-listen socket 4) ;... telnet to the port... (setf con (socket-accept socket)) (setf stream (socket-make-stream socket :input t :output t :element-type 'base-char :buffering :none)) ... and start happily using stream. What is distracting though is, that the printed representation for that stream is: #<FD-STREAM for "a constant string" {10E2ABD1}> Peter |
From: Austin H. <au...@pe...> - 2005-10-31 01:52:02
|
Hi, I built off of some of this code and had a few questions. The server that I am developing is used to communicate with a Flash swf. The client swf maintains an open connection with the server, and terminates each message with a null byte. All the server does is send back a specific xml string when requested, otherwise it just prints out whatever it receives. I use it to catch debug messages from my swfs. My questions are: 1. How do I detect when the client has closed the connection? If I read an EOF? Right now, I am closing as soon as read-char returns the specified eof-value, which I defined as the null byte. 2. What is the best way to read up to the null byte? I'm currently reading character by character, but I don't know if I'm doing it the safest and most efficient way. 3. Is there any documentation for the arguments to socket-make-stream? I couldn't find anything about the buffering keyword. Here is the relevant code: (defconstant +null+ (code-char 0)) (defun read-upto-null (stream) (let ((s (make-string 1024))) (do ((c (read-char stream nil +null+) (read-char stream nil +null+)) (i 0 (+ i 1))) ((equal c +null+) (subseq s 0 i)) (setf (char s i) c)))) (defmethod handle-client ((socket inet-socket)) "Handle a client request." (let ((client-stream (socket-make-stream socket :input t :output t :element-type 'character :buffering :full))) (do ((message (read-upto-null client-stream) (read-upto-null client-stream))) ((equal message "")) ;; need to terminate when the socket is closed (cond ((equal message "<policy-file-request/>") (write-line "sending policy file") (format client-stream "<?xml version=\"1.0\"?><cross-domain-policy><allow-access-from domain=\"*\" to-ports=\"8007\" /></cross-domain-policy>") (write-char +null+ client-stream) (finish-output client-stream)) (t (write-line message))))) (write-line "Closing client connection.") (socket-close socket)) Thanks! I would appreciate any other pointers or criticism, too. -austin Peter Herth wrote: > Thanks, your example helped :) > The trick is the parameter list to socket-make-stream, so for all who > may have the same problem, it works for me now with: > > (setf socket (make-instance 'inet-socket :type :stream :protocol :tcp)) > (socket-bind socket (make-inet-address "127.0.0.1" ) 8030) > (socket-listen socket 4) ;... telnet to the port... > (setf con (socket-accept socket)) > (setf stream (socket-make-stream socket :input t :output t > :element-type 'base-char :buffering :none)) > ... and start happily using stream. What is distracting though is, > that the printed representation for that stream is: > #<FD-STREAM for "a constant string" {10E2ABD1}> > > Peter > > > ------------------------------------------------------- > This SF.Net email is sponsored by the JBoss Inc. > Get Certified Today * Register for a JBoss Training Course > Free Certification Exam for All Training Attendees Through End of 2005 > Visit http://www.jboss.com/services/certification for more information > _______________________________________________ > Sbcl-help mailing list > Sbc...@li... > https://lists.sourceforge.net/lists/listinfo/sbcl-help > |
From: Dave R. <ld...@dr...> - 2005-10-31 03:33:23
|
On Sun, 2005-10-30 at 20:51 -0500, Austin Haas wrote: > 1. How do I detect when the client has closed the connection? If I read > an EOF? Right now, I am closing as soon as read-char returns the > specified eof-value, which I defined as the null byte. You may want to alter your READ-CHAR forms to return NIL instead of +NULL+ when EOF is encountered. The way you have it now, it mixes together the two conditions and you can't tell what really occurred--did you read a +NULL+ or did you encounter EOF? Either that or have READ- CHAR generate a condition which you can then catch and then close the stream. Personally, I typically return NIL from READ-* upon EOF. > 2. What is the best way to read up to the null byte? I'm currently > reading character by character, but I don't know if I'm doing it the > safest and most efficient way. You're probably doing it fine for now. It's tempting to use READ- SEQUENCE into a large buffer and then scan along, but this doesn't work with sockets because of the termination semantics of READ-SEQUENCE. It only returns when it reads every byte in the buffer or it encounters EOF. Thus there is no way to read a variable-length message from a socket. I would note that READ-UPTO-NULL will generate a condition if you read more than 1024 bytes. The SETF will then be trying to insert the character past the end of the array. You either need to check for this or read up about VECTOR-PUSH-EXTEND and adjustable arrays. > 3. Is there any documentation for the arguments to socket-make-stream? I > couldn't find anything about the buffering keyword. I don't know, offhand. Worst case, dive into the code. Looks like the docs say that all the various arguments are passed into SB-SYS:MAKE-FD- STREAM. -- Dave Roberts <ld...@dr...> |