Initial Commit
[packages] / xemacs-packages / liece / lisp / liece-300.el
1 ;;; liece-300.el --- Handler routines for 300 numeric reply.
2 ;; Copyright (C) 1998-2000 Daiki Ueno
3
4 ;; Author: Daiki Ueno <ueno@unixuser.org>
5 ;; Created: 1998-09-28
6 ;; Revised: 1998-11-25
7 ;; Keywords: IRC, liece
8
9 ;; This file is part of Liece.
10
11 ;; This program is free software; you can redistribute it and/or modify
12 ;; it under the terms of the GNU General Public License as published by
13 ;; the Free Software Foundation; either version 2, or (at your option)
14 ;; any later version.
15
16 ;; This program is distributed in the hope that it will be useful,
17 ;; but WITHOUT ANY WARRANTY; without even the implied warranty of
18 ;; MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
19 ;; GNU General Public License for more details.
20
21 ;; You should have received a copy of the GNU General Public License
22 ;; along with GNU Emacs; see the file COPYING.  If not, write to the
23 ;; Free Software Foundation, Inc., 59 Temple Place - Suite 330,
24 ;; Boston, MA 02111-1307, USA.
25
26
27 ;;; Commentary:
28 ;; 
29
30 ;;; Code:
31
32 (eval-when-compile
33   (require 'liece-inlines)
34   (require 'liece-intl)
35   (require 'liece-misc)
36   (require 'liece-commands))
37
38 (eval-and-compile
39   (autoload 'liece-dcc-compare-hostnames "liece-dcc"))
40
41 (defvar liece-recursing-whois nil)
42 (defvar liece-recursing-whowas nil)
43
44 (defun* liece-handle-300-messages (number prefix rest)
45   "300 replies"
46   (or (string-match "[^ ]* \\([^ ]*\\) *\\([^ ]*\\) *:\\(.*\\)" rest)
47       (return-from liece-handle-300-messages))
48   (let ((target1 (liece-channel-virtual (match-string 1 rest)))
49         (target2 (liece-channel-virtual (match-string 2 rest)))
50         (msg (match-string 3 rest)))
51     (cond ((string= target1 "")
52            (liece-insert-info liece-300-buffer (concat msg "\n")))
53           ((string= target2 "")
54            (liece-insert-info liece-300-buffer
55                                (format "%s (%s)\n" msg target1)))
56           (t
57            (liece-insert-info liece-300-buffer
58                                (format "%s %s (%s)\n" target1 msg target2))))))
59
60 (defun liece-handle-301-message (prefix rest)
61   "RPL_AWAY \"<nickname> :<away message>\"."
62   (if (string-match "^[^ ]+ \\([^ ]+\\) +:\\(.*\\)" rest)
63       (let ((who (match-string 1 rest)) (iswhat (match-string 2 rest)))
64         (or liece-recursing-whois
65             (liece-insert-info liece-300-buffer
66                                 (concat who " is marked as being away, "
67                                         "but left the message:\n"
68                                         iswhat "\n"))))))
69
70 (defun liece-handle-302-message (prefix rest)
71   "RPL_USERHOST \":[<reply>{<space><reply>}]\"."
72   (while (string-match
73           "^[^ ]* :[ ]*\\([^*=]+\\)\\([*]*\\)=\\([+-]\\)\\([^ ]+\\)" rest)
74     (let ((nick (match-string 1 rest)) (oper (match-string 2 rest))
75           (away (match-string 3 rest)) (who (match-string 4 rest))
76           (end (match-end 4)))
77       (if (liece-nick-equal nick liece-real-nickname)
78           (setq liece-my-userhost who))
79       (liece-insert-info liece-300-buffer
80                           (format "Nick %s is %s [%s%s, %s%s]\n"
81                                   nick who
82                                   (if (string= oper "") "Not ") "operator"
83                                   (if (string= away "+") "Not ") "away"))
84       (setq rest (concat " :" (substring rest end nil))))))
85
86 (defun liece-303-display-friends (nicks)
87   (let ((on (filter-elements nick nicks
88               (not (string-list-member-ignore-case nick liece-friends-last))))
89         (off (filter-elements nick liece-friends-last
90                (not (string-list-member-ignore-case nick nicks)))))
91     (setq liece-friends-last nicks)
92     (if on
93       (liece-insert-info liece-300-buffer
94                           (format (_ "Following people are now on: %s\n")
95                                   (mapconcat 'identity on " "))))
96     (if off
97         (liece-insert-info liece-300-buffer
98                             (format (_ "Following people are now off: %s\n")
99                                     (mapconcat 'identity off " "))))))
100
101 (defun* liece-handle-303-message (prefix rest)
102   "RPL_ISON \":[<nickname> {<space><nickname>}]\""
103   (or (string-match "[^ ]+ :\\(.*\\)" rest)
104       (return-from liece-handle-303-message))
105   (setq rest (match-string 1 rest))
106   (or (string= rest "")
107       (setq rest (substring rest 0 -1)))
108   (let ((nicks (split-string rest)))
109     (when (and (null nicks) (null liece-friends))
110       (liece-insert-info liece-300-buffer
111                           (_ "No one you requested is on now.\n"))
112       (return-from liece-handle-303-message))
113     (dolist (nick nicks)
114       (when (and (string-list-member-ignore-case
115                   nick liece-current-chat-partners)
116                  (get (intern nick liece-obarray) 'part))
117         (liece-insert-change (liece-pick-buffer nick)
118                               (format (_ "%s has come back\n") nick))
119         (put (intern nick liece-obarray) 'part nil)))
120     (unless liece-friends
121       (liece-insert-info liece-300-buffer
122                           (format (_ "Following people are on: %s\n") rest))
123       (return-from liece-handle-303-message))
124     (if (fboundp liece-display-friends-function)
125         (funcall liece-display-friends-function nicks))))
126         
127 (defun* liece-handle-305-message (prefix rest)
128   "RPL_UNAWAY \":You are no longer marked as being away\""
129   (or (string-equal liece-away-indicator "A")
130       (return-from liece-handle-305-message))
131   (setq liece-away-indicator "-")
132   (liece-maybe-poll)
133   (when (string-match "[^:]:\\(.*\\)" rest)
134     (setq rest (match-string 1 rest))
135     (liece-insert-info liece-300-buffer
136                         (format "%s (%s)\n"
137                                 rest (funcall liece-format-time-function
138                                               (current-time))))))
139
140 (defun liece-handle-306-message (prefix rest)
141   "RPL_NOWAWAY \":You have been marked as being away\"."
142   (setq liece-away-indicator "A")
143   (if (string-match "[^:]:\\(.*\\)" rest)
144       (liece-insert-info liece-300-buffer
145                           (format "%s (%s)\n"
146                                   (match-string 1 rest)
147                                   (funcall liece-format-time-function
148                                            (current-time))))))
149
150 (defun liece-handle-311-message (prefix rest)
151   "RPL_WHOISUSER \"<nickname> <user> <host> * :<real name>\"."
152   (and (string-match "[^ ]+ \\([^ ]+\\) \\([^ ]+\\) \\([^ ]+\\) \\([^ ]+\\) :\\(.*\\)" rest)
153        (not liece-recursing-whois)
154        (liece-insert-info liece-300-buffer
155                            (format "%s is %s (%s@%s)\n"
156                                    (match-string 1 rest) ; nick
157                                    (match-string 5 rest) ; realname
158                                    (match-string 2 rest) ; username
159                                    (match-string 3 rest) ; machine
160                                    ))))
161
162 (defun* liece-handle-312-message (prefix rest)
163   "RPL_WHOISSERVER \"<nickname> <server> :<server info>\""
164   (or (string-match "^[^ ]+ \\(\\([^ ]+\\) \\)?\\([^ ]+\\) :\\(.*\\)" rest)
165       (return-from liece-handle-312-message))
166   (let ((who (match-string 2 rest))
167         (server (match-string 3 rest))
168         (real (match-string 4 rest)))
169     (if (and liece-dcc-resolve-server
170              (not (liece-dcc-compare-hostnames server (liece-server-host)))
171              (not liece-recursing-whois)
172              (not liece-recursing-whowas))
173         (progn
174           (setq liece-recursing-whois t)
175           (liece-send "WHOIS %s %s" server who))
176       (setq liece-recursing-whois nil)
177       (liece-insert-info liece-300-buffer
178                           (format "on via server %s (%s)\n" server real)))))
179
180 (defun liece-handle-313-message (prefix rest)
181   "RPL_WHOISOPERATOR \"<nickname> :is an IRC operator\"."
182   (if (string-match "^[^ ]+ \\([^ ]+\\) :\\(.*\\)" rest)
183       (or liece-recursing-whois
184           (liece-insert-info liece-300-buffer
185                               (concat (match-string 2 rest)
186                                       " is an IRC operator\n")))))
187
188 (defun liece-handle-316-message (prefix rest)
189   "RPL_WHOISCHANOP."
190   (cond ((string-match "^\\([^ ]+\\) :\\(.*\\)" rest)
191          (if (not liece-recursing-whois)
192              (liece-insert-info liece-300-buffer
193                                  (concat "Status: "
194                                          (match-string 2 rest) "\n"))))
195         ((string-match "^\\([^ ]+\\) \\([^ ]+\\) :\\(.*\\)" rest)
196          (if (not liece-recursing-whois)
197              (liece-insert-info liece-300-buffer
198                                  (concat "Status: "
199                                          (match-string 3 rest) "\n"))))))
200
201 (defun* liece-handle-319-message (prefix rest)
202   "RPL_WHOISCHANNELS \"<nickname> :{[@|+]<channel><space>}\""
203   (or (string-match "^\\([^ ]+\\) \\([^ ]+\\) :\\(.*\\)" rest)
204       (return-from liece-handle-319-message))
205   (let ((chnls (split-string (match-string 3 rest)))
206         isonchnls flag)
207     (dolist (chnl chnls)
208       (if (and (or (eq ?@ (string-to-char chnl))
209                    (eq ?+ (string-to-char chnl)))
210                (liece-channel-p (substring chnl 1)))
211           (progn
212             (setq flag (substring chnl 0 1)
213                   chnl (substring chnl 1)))
214         (setq flag ""))
215       (push (concat flag (liece-channel-virtual chnl)) isonchnls))
216     (if (not liece-recursing-whois)
217         (liece-insert-info liece-300-buffer
218                             (format (_ "Channels: %s\n")
219                                     (mapconcat (function identity)
220                                                (nreverse isonchnls) " "))))))
221
222 (defun liece-handle-314-message (prefix rest)
223   "RPL_WHOWASUSER \"<nickname> <user> <host> * :<real name>\"."
224   (if (string-match
225        "[^ ]+ \\([^ ]+\\) \\([^ ]+\\) \\([^ ]+\\) \\([^ ]+\\) :\\(.*\\)"
226        rest)
227       (let ((nick (match-string 1 rest)) (username (match-string 2 rest))
228             (machine (match-string 3 rest)) (chnl (match-string 4 rest))
229             (realname (match-string 5 rest)))
230         (setq liece-recursing-whowas t)
231         (liece-insert-info liece-300-buffer
232                             (format "%s [%s] was %s (%s@%s)\n"
233                                     nick
234                                     (if (string= chnl "*") "Private" chnl)
235                                     realname username machine)))))
236
237 (defun liece-handle-315-message (prefix rest)
238   "RPL_ENDOFWHO."
239   (if (zerop liece-long-reply-count)
240       (liece-insert-info liece-300-buffer
241                           (concat "No matches found"
242                                   (if liece-who-expression
243                                       (concat ": " liece-who-expression)
244                                     "")
245                                   "\n")))
246   (setq liece-who-expression nil)
247   (liece-reset-long-reply-count))
248
249 (defun liece-handle-317-message (prefix rest)
250   "RPL_WHOISIDLE \"<nickname> <integer> :seconds idle\"."
251   (cond ((string-match "^[^ ]+ [^ ]+ \\([0-9]*\\) :\\(.*\\)" rest)
252          (liece-insert-info liece-300-buffer
253                              (concat "Idle for "
254                                      (liece-convert-seconds
255                                       (match-string 1 rest))
256                                      "\n")))
257         ((string-match "^[^ ]+ \\([0-9]*\\) :\\(.*\\)" rest)
258          (liece-insert-info liece-300-buffer
259                              (concat "Idle for "
260                                      (liece-convert-seconds
261                                       (match-string 1 rest))
262                                      "\n")))))
263
264 (defun liece-handle-318-message (prefix rest)
265   "RPL_ENDOFWHOIS \"<nickname> :End of /WHOIS list\"."
266   nil)
267
268 (defun liece-handle-321-message (prefix rest)
269   "RPL_LISTSTART \"Channel :Users  Name\"."
270   (liece-insert-info liece-300-buffer
271                       (format "%-10s%6s  %s\n"
272                               (_ "Channel") (_ "Users")  (_ "Topic"))))
273
274 (defun* liece-handle-322-message (prefix rest)
275   "RPL_LIST \"<channel> <# visible> :<topic>\""
276   (or (string-match "^\\([^ ]+\\) \\([^ ]+\\) \\([^ ]+\\) :\\(.*\\)" rest)
277       (return-from liece-handle-322-message))
278   (liece-increment-long-reply-count)
279   (liece-check-long-reply-count)
280   (let ((chnl (match-string 2 rest))
281         (users (match-string 3 rest))
282         (topic (match-string 4 rest)))
283     (when (or (string= liece-channel-filter (downcase chnl))
284               (string= liece-channel-filter "")
285               (and (string= liece-channel-filter "0")
286                    (string= chnl "*")))
287       (setq chnl (liece-channel-virtual chnl))
288       (put (intern chnl liece-obarray) 'topic topic)
289       (liece-insert-info (append (liece-pick-buffer chnl) liece-300-buffer)
290                           (format "%-10s%6s user%s%s%s\n"
291                                   (if (string= chnl "*") "Priv" chnl)
292                                   users
293                                   (if (> (string-to-int users) 1) "s" "")
294                                   (if (string= "" topic) "" ": ")
295                                   topic)))))
296
297 (defun liece-handle-323-message (prefix rest)
298   "RPL_LISTEND \":End of /LIST\"."
299   (liece-reset-long-reply-count))
300
301 (defun liece-handle-324-message (prefix rest)
302   "RPL_CHANNELMODEIS \"<channel> <mode> <mode params>\"."
303   (if (string-match "[^ ]* \\([^ ]*\\) +\\+\\([^ ]*\\)\\( *[^ ]*\\)" rest)
304       (let ((chnl (match-string 1 rest))
305             (mode (match-string 2 rest))
306             (param (match-string 3 rest)))
307         (setq chnl (liece-channel-virtual chnl))
308         (put (intern chnl liece-obarray) 'mode mode)
309         (liece-insert-info (append (liece-pick-buffer chnl)
310                                     liece-300-buffer)
311                             (format (_ "Mode for %s is %s%s\n")
312                                     chnl mode param))
313         (liece-set-channel-indicator))))
314
315 (defun liece-handle-331-message (prefix rest)
316   "RPL_NOTOPIC \"<channel> :No topic is set\"."
317   (if (string-match "[^ ]* \\([^ ]*\\) \\(.*\\)" rest)
318       (let ((chnl (match-string 1 rest)))
319         (setq chnl (liece-channel-virtual chnl))
320         (put (intern chnl liece-obarray) 'topic nil)
321         (liece-insert-info (append (liece-pick-buffer chnl)
322                                     liece-300-buffer)
323                             (_ "No topic is set\n"))
324         (liece-set-channel-indicator))))
325
326 (defun liece-handle-332-message (prefix rest)
327   "RPL_TOPIC \"<channel> :<topic>\"."
328   (if (string-match "[^ ]* \\([^ ]*\\) +:\\(.*\\)" rest)
329       (let ((chnl (liece-channel-virtual (match-string 1 rest)))
330             (topic (match-string 2 rest)))
331         (liece-channel-set-topic topic chnl)
332         (liece-insert-info (liece-pick-buffer chnl)
333                             (format (_ "Topic: %s\n") topic))
334         (liece-insert-info liece-300-buffer
335                             (format (_ "Topic for %s: %s\n") chnl topic))
336         (liece-set-channel-indicator))))
337
338 (defun liece-handle-333-message (prefix rest)
339   "RPL_TOPICWHOTIME <channel> <nickname> <time>."
340   (if (string-match "[^ ]* \\([^ ]*\\) +\\([^ ]*\\) +\\([^ ]*\\)" rest)
341       (let ((chnl (liece-channel-virtual (match-string 1 rest)))
342             (nick (match-string 2 rest))
343             (time (funcall liece-format-time-function
344                            (liece-seconds-to-time
345                             (string-to-int (match-string 3 rest))))))
346         (liece-insert-info (liece-pick-buffer chnl)
347                             (format (_ "Topic set by %s at %s\n")
348                                     nick time))
349         (liece-insert-info liece-300-buffer
350                             (format (_ "Topic for %s set by %s at %s\n")
351                                     chnl nick time))
352         (liece-set-channel-indicator))))
353
354 (defun liece-handle-341-message (prefix rest)
355   "RPL_INVITING \"<channel> <nickname>\"."
356   (if (string-match "^\\([^ ]+\\) +\\([^ ]+\\) +\\([-#&0-9+][^ ]*\\)" rest)
357       (let ((nick (match-string 2 rest))
358             (chnl (liece-channel-virtual (match-string 3 rest))))
359         (liece-insert-info (liece-pick-buffer chnl)
360                             (format (_ "Inviting user %s\n") nick))
361         (liece-insert-info liece-300-buffer
362                             (format (_ "Inviting user %s to channel %s\n")
363                                     nick chnl)))))
364
365 (defun liece-handle-346-message (prefix rest)
366   "RPL_INVITELIST \"<channel> <inviteid>\"."
367   (when (string-match "[^ ]* \\([^ ]*\\) \\([^ ]*\\)" rest)
368     (let* ((regexp (match-string 2 rest))
369            (chnl (liece-channel-virtual (match-string 1 rest))))
370       (liece-increment-long-reply-count)
371       (liece-check-long-reply-count)
372       (or (> liece-polling 0)
373           (liece-channel-add-invite regexp chnl)))))
374
375 (defun liece-handle-347-message (prefix rest)
376   "RPL_ENDOFINVITELIST \"<channel> :End of Channel Invite List\"."
377   (when (string-match "[^ ]* \\([^ ]*\\)" rest)
378     (let* ((chnl (liece-channel-virtual (match-string 1 rest)))
379            (invites (liece-channel-get-invites chnl)))
380       (liece-reset-long-reply-count)
381       (liece-insert-info liece-300-buffer
382                           (concat "Following users are invited to " chnl
383                                   ": \n"))
384       (dolist (invite invites)
385         (liece-insert-info liece-300-buffer
386                             (concat "\t" invite "\n"))))))
387
388 (defun liece-handle-348-message (prefix rest)
389   "RPL_EXCEPTLIST \"<channel> <exceptid>\"."
390   (when (string-match "[^ ]* \\([^ ]*\\) \\([^ ]*\\)" rest)
391     (let* ((regexp (match-string 2 rest))
392            (chnl (liece-channel-virtual (match-string 1 rest))))
393       (liece-increment-long-reply-count)
394       (liece-check-long-reply-count)
395       (or (> liece-polling 0)
396           (liece-channel-add-exception regexp chnl)))))
397   
398 (defun liece-handle-349-message (prefix rest)
399   "RPL_ENDOFEXCEPTLIST \"<channel> :End of Channel Exception List\"."
400   (when (string-match "[^ ]* \\([^ ]*\\)" rest)
401     (let* ((chnl (liece-channel-virtual (match-string 1 rest)))
402            (exceptions (liece-channel-get-exceptions chnl)))
403       (liece-reset-long-reply-count)
404       (liece-insert-info liece-300-buffer
405                           (concat "Following users are welcome to " chnl
406                                   ": \n"))
407       (dolist (exception exceptions)
408         (liece-insert-info liece-300-buffer
409                             (concat "\t" exception "\n"))))))
410
411 (defun liece-handle-351-message (prefix rest)
412   "RPL_VERSION \"<version>.<debuglevel> <server> :<comments>\"."
413   (if (string-match "[^ ]+ \\([^ ]+\\) :*\\([^ ]+\\)[ :]*\\(.*\\)" rest)
414       (liece-insert-info
415        liece-300-buffer
416        (format (_ "Machine %s is running IRC version %s (%s)\n")
417                (match-string 2 rest) ; machine
418                (match-string 1 rest) ; version
419                (match-string 3 rest) ; comments
420                ))))
421
422 (defun liece-handle-352-message (prefix rest)
423   "RPL_WHOREPLY \"<channel> <user> <host> <server> <nickname> <H|G>[*][@|+] :<hopcount> <real name>\"."
424   (if (string-match "\\([^ ]*\\) \\([^ ]+\\) \\([^ ]+\\) \\([^ ]+\\) \\([^ ]+\\) \\([^ ]+\\) :[0-9]* ?\\(.*\\)" rest)
425       (let ((chnl (liece-channel-virtual (match-string 1 rest)))
426             (user (match-string 2 rest)) (host (match-string 3 rest))
427             (nick (match-string 5 rest)) (oper (match-string 6 rest))
428             (name (match-string 7 rest)))
429         (liece-increment-long-reply-count)
430         (liece-check-long-reply-count)
431         (liece-nick-set-user-at-host nick (concat user "@" host))
432         (liece-insert-info liece-300-buffer
433                             (format "%3s %10s %9s %-29s %s\n"
434                                     oper (if (memq (aref chnl 0) '(?* ?0))
435                                              "Private" chnl)
436                                     nick
437                                     (concat "(" user "@"
438                                             (liece-clean-hostname host)
439                                             ")")
440                                     name)))))
441
442 (defvar liece-353-names nil)
443
444 (defmacro liece-353-scan-channels (chnl)
445   `(or (string-assoc-ignore-case ,chnl liece-channel-alist)
446        (push (list ,chnl) liece-channel-alist)))
447
448 (defun liece-handle-353-message (prefix rest)
449   "RPL_NAMREPLY \"<channel> :[[@|+]<nick> [[@|+]<nick> [...]]]\"."
450   (when (string-match "[^ =*@]?[=*@] \\([^ ]*\\) :\\(.*\\)" rest)
451     (let ((chnl (liece-channel-virtual (match-string 1 rest)))
452           (users (delete "" (split-string (match-string 2 rest)))))
453       (liece-increment-long-reply-count)
454       (liece-check-long-reply-count)
455       (or (> liece-polling 0)
456           (setq liece-353-names
457                 (append (nreverse users) liece-353-names )))
458       (liece-353-scan-channels chnl))))
459
460 (defun liece-handle-361-message (prefix rest)
461   "RPL_KILLDONE."
462   (if (string-match "[^ ]+ \\([^ ]+\\) +:\\(.*\\)" rest)
463       (let ((who (match-string 1 rest))
464             (message (match-string 2 rest)))
465         (liece-insert-info liece-300-buffer
466                             (format (_ "You just killed %s. %s\n")
467                                     who message)))))
468
469 (defstruct liece-364-link from to hop info)
470 (defvar liece-364-links nil)
471
472 (defun liece-handle-364-message (prefix rest)
473   "RPL_LINKS \"<mask> <server> :<hopcount> <server info>\"."
474   (if (string-match
475        "[^ ]+ \\([^ ]+\\) +\\([^ ]*\\) +:\\(\\(.*\\) +\\(.*\\)\\)" rest)
476       (let ((from (match-string 1 rest)) (to (match-string 2 rest))
477             (hop (string-to-int (match-string 4 rest)))
478             (info (match-string 5 rest)) link)
479         (liece-increment-long-reply-count)
480         (liece-check-long-reply-count)
481         (setq rest (match-string 3 rest)
482               link (make-liece-364-link
483                     :from from :to to :hop hop :info info))
484         (push link liece-364-links))))
485
486 (defun liece-handle-365-message (prefix rest)
487   "RPL_ENDOFLINKS \"<mask> :End of /LINKS list\"."
488   (liece-reset-long-reply-count)
489   (dolist (link liece-364-links)
490     (liece-insert-info liece-300-buffer
491                         (concat (liece-364-link-from link)
492                                 " --"
493                                 (number-to-string (liece-364-link-hop link))
494                                 "-- "
495                                 (liece-364-link-to link) "\n")))
496   (setq liece-364-links nil))
497
498 (defun liece-handle-366-message (prefix rest)
499   "RPL_ENDOFNAME \"<channel> :End of /NAMES list\"."
500   (when (string-match "[^ ]* \\([^ ]*\\)" rest)
501     (let ((level (- liece-polling 1))
502           (users (length liece-353-names))
503           (names (mapconcat #'identity liece-353-names " "))
504           (chnl (liece-channel-virtual (match-string 1 rest))))
505       (liece-reset-long-reply-count)
506       (setq liece-polling (max 0 level))
507       (liece-insert-info (append (liece-pick-buffer chnl)
508                                   liece-300-buffer)
509                           (format "%-10s%6d user%s: %s\n"
510                                   (if (memq chnl '(?* ?0))
511                                       "Private"
512                                     chnl)
513                                   users (if (= users 1) "" "s") names))
514       (and liece-353-names
515            (liece-channel-member chnl liece-current-channels)
516            (liece-nick-update chnl liece-353-names))
517       (setq liece-353-names nil))))
518
519 (defun liece-handle-367-message (prefix rest)
520   "RPL_BANLIST \"<channel> <banid>\"."
521   (when (string-match "[^ ]* \\([^ ]*\\) \\([^ ]*\\)" rest)
522     (let* ((regexp (match-string 2 rest))
523            (chnl (liece-channel-virtual (match-string 1 rest))))
524       (liece-increment-long-reply-count)
525       (liece-check-long-reply-count)
526       (or (> liece-polling 0)
527           (liece-channel-add-ban regexp chnl)))))
528
529 (defun liece-handle-368-message (prefix rest)
530   "RPL_ENDOFBANLIST \"<channel> :End of channel ban list\"."
531   (when (string-match "[^ ]* \\([^ ]*\\)" rest)
532     (let* ((chnl (liece-channel-virtual (match-string 1 rest)))
533            (bans (liece-channel-get-bans chnl)))
534       (liece-reset-long-reply-count)
535       (liece-insert-info liece-300-buffer
536                           (concat "Following users are banned on " chnl
537                                   ": \n"))
538       (dolist (ban bans)
539         (liece-insert-info liece-300-buffer
540                             (concat "\t" ban "\n"))))))
541
542 (defun liece-handle-369-message (prefix rest)
543   "RPL_ENDOFWHOWAS \"<nickname> :End of WHOWAS\"."
544   (setq liece-recursing-whowas nil))
545
546 (defun liece-handle-371-message (prefix rest)
547   "RPL_INFO \":<string>\"."
548   (if (string-match "^\\([^ ]+\\) +:?\\(.*\\)" rest)
549       (liece-insert-info liece-300-buffer
550                           (concat (match-string 2 rest) "\n"))))
551
552 (defun liece-handle-372-message (prefix rest)
553   "RPL_MOTD \":- <text>\"."
554   (if (string-match "^\\([^ ]+\\) +:?\\(.*\\)" rest)
555       (liece-insert-info liece-300-buffer
556                           (concat (match-string 2 rest) "\n"))))
557
558 (defun liece-handle-381-message (prefix rest)
559   "RPL_YOUREOPER \":You are now an IRC operator\"."
560   (if (string-match "^\\([^ ]+\\) +:\\(.*\\)" rest)
561       (liece-insert-info liece-300-buffer
562                           (format "You are now an IRC operator (%s)\n"
563                                   (match-string 2 rest)))))
564
565 (defun liece-handle-382-message (prefix rest)
566   "RPL_REHASHING \"<config file> :Rehashing\"."
567   (if (string-match "^\\([^ ]+\\) +:\\(.*\\)" rest)
568       (liece-insert-info liece-300-buffer
569                           (concat (match-string 2 rest) " "
570                                   (match-string 1 rest) "\n"))))
571
572 (defun liece-handle-391-message (prefix rest)
573   "RPL_TIME \"<server> :<string showing server's local time>\"."
574   (if (string-match "^\\([^ ]+\\) +\\(.*\\)" rest)
575       (liece-insert-info liece-300-buffer
576                           (format (_ "Server time is %s\n")
577                                   (match-string 2 rest)))))
578
579 \f
580 ;;; @ register message handlers
581 ;;;
582
583 (eval-when-compile (require 'liece-handler))
584
585 (liece-handler-define-backend "300")
586
587 (defmacro liece-register-300-handler (num)
588   `(progn
589      (liece-handler-define-function
590       ,(number-to-string num) '(prefix rest "300")
591       ',(intern (format "liece-handle-%03d-message" num)))
592      (defvar ,(intern (format "liece-%03d-hook" num)) nil)
593      (defvar ,(intern (format "liece-after-%03d-hook" num)) nil)))
594
595 (liece-register-300-handler 301)
596 (liece-register-300-handler 302)
597 (liece-register-300-handler 303)
598 (liece-register-300-handler 305)
599 (liece-register-300-handler 306)
600
601 (liece-register-300-handler 311)
602 (liece-register-300-handler 312)
603 (liece-register-300-handler 313)
604 (liece-register-300-handler 314)
605 (liece-register-300-handler 315)
606 (liece-register-300-handler 316)
607 (liece-register-300-handler 317)
608 (liece-register-300-handler 318)
609 (liece-register-300-handler 319)
610
611 (liece-register-300-handler 321)
612 (liece-register-300-handler 322)
613 (liece-register-300-handler 323)
614 (liece-register-300-handler 324)
615
616 (liece-register-300-handler 331)
617 (liece-register-300-handler 332)
618 (liece-register-300-handler 333)
619
620 (liece-register-300-handler 341)
621 (liece-register-300-handler 348)
622 (liece-register-300-handler 349)
623
624 (liece-register-300-handler 351)
625 (liece-register-300-handler 352)
626 (liece-register-300-handler 353)
627
628 (liece-register-300-handler 361)
629 (liece-register-300-handler 364)
630 (liece-register-300-handler 365)
631 (liece-register-300-handler 366)
632 (liece-register-300-handler 367)
633 (liece-register-300-handler 368)
634 (liece-register-300-handler 369)
635
636 (liece-register-300-handler 371)
637 (liece-register-300-handler 372)
638
639 (liece-register-300-handler 381)
640 (liece-register-300-handler 382)
641
642 (liece-register-300-handler 391)
643
644 (provide 'liece-300)
645
646 ;;; liece-300.el ends here