Shammer's Philosophy

My private adversaria

応答を返すLispUDPServerその弐

応答を返す UDP Server - Shammerismに少しだけ手を加えた。

(defun start ()
  (let ((server (make-socket :type :datagram
			     :local-host "0.0.0.0"
			     :local-port 7001
			     :format :binary)))
    (with-open-file (f "/var/log/clozure-udp-server.log" :direction :output :if-exists :append :if-does-not-exist :create)
		    (do () ()
			(multiple-value-bind (buffer length client-ip client-port)
					     (receive-from server 512)
					     (when (equalp buffer #(81 85 73 84 10))
					       (return))
					     (let ((val (format nil "[~A:~A] Received byte length is ~A, message is ~A"
								(ipaddr-to-dotted client-ip)
								client-port
								length
								(decode-string-from-octets buffer :external-format :UTF-8))))
					       (format t "~A~%" val)
					       (format f "~A~%" val)
					       (force-output f)
					       (multiple-value-bind (return-val len)
								    (encode-string-to-octets val :external-format :UTF-8)
								    (send-to server return-val len :remote-port client-port :remote-host client-ip))))))
    (format t "FINISH!~%")))
(save-application "ccludp" :toplevel-function #'start :prepend-kernel t)

受け取った文字とクライアントのIP、ポートを返す。これに接続したクライアントは以下のような感じになる。

# nc -u X.X.X.X 7001
aaaaa
[192.168.1.2:52512] Received byte length is 6, message is aaaah
...

このクライアントのIPは192.168.1.2。サーバーは任意のアドレス。これをサーバーのIPを返すようにしてもいいかもしれない。