Blame


1 2ee05c9a 2002-03-03 alex /*
2 2ee05c9a 2002-03-03 alex * ngIRCd -- The Next Generation IRC Daemon
3 2ee05c9a 2002-03-03 alex * Copyright (c)2001,2002 by Alexander Barton (alex@barton.de)
4 2ee05c9a 2002-03-03 alex *
5 2ee05c9a 2002-03-03 alex * Dieses Programm ist freie Software. Sie koennen es unter den Bedingungen
6 2ee05c9a 2002-03-03 alex * der GNU General Public License (GPL), wie von der Free Software Foundation
7 2ee05c9a 2002-03-03 alex * herausgegeben, weitergeben und/oder modifizieren, entweder unter Version 2
8 2ee05c9a 2002-03-03 alex * der Lizenz oder (wenn Sie es wuenschen) jeder spaeteren Version.
9 2ee05c9a 2002-03-03 alex * Naehere Informationen entnehmen Sie bitter der Datei COPYING. Eine Liste
10 2ee05c9a 2002-03-03 alex * der an ngIRCd beteiligten Autoren finden Sie in der Datei AUTHORS.
11 2ee05c9a 2002-03-03 alex *
12 005391ca 2002-09-16 alex * $Id: irc-channel.c,v 1.15 2002/09/16 09:16:17 alex Exp $
13 2ee05c9a 2002-03-03 alex *
14 2ee05c9a 2002-03-03 alex * irc-channel.c: IRC-Channel-Befehle
15 2ee05c9a 2002-03-03 alex */
16 2ee05c9a 2002-03-03 alex
17 2ee05c9a 2002-03-03 alex
18 ca33cbda 2002-03-12 alex #include "portab.h"
19 2ee05c9a 2002-03-03 alex
20 ca33cbda 2002-03-12 alex #include "imp.h"
21 2ee05c9a 2002-03-03 alex #include <assert.h>
22 2ee05c9a 2002-03-03 alex #include <string.h>
23 2ee05c9a 2002-03-03 alex
24 ca33cbda 2002-03-12 alex #include "defines.h"
25 c2f60abe 2002-05-27 alex #include "conn.h"
26 c2f60abe 2002-05-27 alex #include "client.h"
27 c2f60abe 2002-05-27 alex #include "channel.h"
28 c2f60abe 2002-05-27 alex #include "lists.h"
29 2ee05c9a 2002-03-03 alex #include "log.h"
30 39b9f65d 2002-06-26 alex #include "match.h"
31 2ee05c9a 2002-03-03 alex #include "messages.h"
32 c2f60abe 2002-05-27 alex #include "parse.h"
33 c2f60abe 2002-05-27 alex #include "irc.h"
34 c2f60abe 2002-05-27 alex #include "irc-write.h"
35 2ee05c9a 2002-03-03 alex
36 ca33cbda 2002-03-12 alex #include "exp.h"
37 2ee05c9a 2002-03-03 alex #include "irc-channel.h"
38 2ee05c9a 2002-03-03 alex
39 2ee05c9a 2002-03-03 alex
40 c2f60abe 2002-05-27 alex GLOBAL BOOLEAN
41 c2f60abe 2002-05-27 alex IRC_JOIN( CLIENT *Client, REQUEST *Req )
42 2ee05c9a 2002-03-03 alex {
43 2ee05c9a 2002-03-03 alex CHAR *channame, *flags, *topic, modes[8];
44 a1ded68a 2002-09-08 alex BOOLEAN is_new_chan, is_invited, is_banned;
45 2ee05c9a 2002-03-03 alex CLIENT *target;
46 2ee05c9a 2002-03-03 alex CHANNEL *chan;
47 2ee05c9a 2002-03-03 alex
48 2ee05c9a 2002-03-03 alex assert( Client != NULL );
49 2ee05c9a 2002-03-03 alex assert( Req != NULL );
50 2ee05c9a 2002-03-03 alex
51 2ee05c9a 2002-03-03 alex if(( Client_Type( Client ) != CLIENT_USER ) && ( Client_Type( Client ) != CLIENT_SERVER )) return IRC_WriteStrClient( Client, ERR_NOTREGISTERED_MSG, Client_ID( Client ));
52 2ee05c9a 2002-03-03 alex
53 2ee05c9a 2002-03-03 alex /* Falsche Anzahl Parameter? */
54 2ee05c9a 2002-03-03 alex if(( Req->argc > 1 )) return IRC_WriteStrClient( Client, ERR_NEEDMOREPARAMS_MSG, Client_ID( Client ), Req->command );
55 2ee05c9a 2002-03-03 alex
56 2ee05c9a 2002-03-03 alex /* Wer ist der Absender? */
57 bc4ed226 2002-03-25 alex if( Client_Type( Client ) == CLIENT_SERVER ) target = Client_Search( Req->prefix );
58 2ee05c9a 2002-03-03 alex else target = Client;
59 2ee05c9a 2002-03-03 alex if( ! target ) return IRC_WriteStrClient( Client, ERR_NOSUCHNICK_MSG, Client_ID( Client ), Req->prefix );
60 2ee05c9a 2002-03-03 alex
61 2ee05c9a 2002-03-03 alex /* Channel-Namen durchgehen */
62 c2f60abe 2002-05-27 alex chan = NULL;
63 2ee05c9a 2002-03-03 alex channame = strtok( Req->argv[0], "," );
64 2ee05c9a 2002-03-03 alex while( channame )
65 2ee05c9a 2002-03-03 alex {
66 f7567db0 2002-06-02 alex chan = flags = NULL;
67 2ee05c9a 2002-03-03 alex
68 f7567db0 2002-06-02 alex /* wird der Channel neu angelegt? */
69 2ee05c9a 2002-03-03 alex if( Channel_Search( channame )) is_new_chan = FALSE;
70 2ee05c9a 2002-03-03 alex else is_new_chan = TRUE;
71 2ee05c9a 2002-03-03 alex
72 2ee05c9a 2002-03-03 alex /* Hat ein Server Channel-User-Modes uebergeben? */
73 2ee05c9a 2002-03-03 alex if( Client_Type( Client ) == CLIENT_SERVER )
74 2ee05c9a 2002-03-03 alex {
75 2ee05c9a 2002-03-03 alex /* Channel-Flags extrahieren */
76 2ee05c9a 2002-03-03 alex flags = strchr( channame, 0x7 );
77 e876e210 2002-06-10 alex if( flags )
78 e876e210 2002-06-10 alex {
79 e876e210 2002-06-10 alex *flags = '\0';
80 e876e210 2002-06-10 alex flags++;
81 e876e210 2002-06-10 alex }
82 2ee05c9a 2002-03-03 alex }
83 2ee05c9a 2002-03-03 alex
84 c2f60abe 2002-05-27 alex /* Lokaler Client? */
85 c2f60abe 2002-05-27 alex if( Client_Type( Client ) == CLIENT_USER )
86 2ee05c9a 2002-03-03 alex {
87 c2f60abe 2002-05-27 alex /* Existiert der Channel bereits, oder wird er im Moment neu erzeugt? */
88 c2f60abe 2002-05-27 alex if( is_new_chan )
89 c2f60abe 2002-05-27 alex {
90 c2f60abe 2002-05-27 alex /* Erster User im Channel: Operator-Flag setzen */
91 c2f60abe 2002-05-27 alex flags = "o";
92 c2f60abe 2002-05-27 alex }
93 c2f60abe 2002-05-27 alex else
94 c2f60abe 2002-05-27 alex {
95 c2f60abe 2002-05-27 alex /* Existierenden Channel suchen */
96 c2f60abe 2002-05-27 alex chan = Channel_Search( channame );
97 c2f60abe 2002-05-27 alex assert( chan != NULL );
98 c2f60abe 2002-05-27 alex
99 a1ded68a 2002-09-08 alex is_banned = Lists_CheckBanned( target, chan );
100 a1ded68a 2002-09-08 alex is_invited = Lists_CheckInvited( target, chan );
101 a1ded68a 2002-09-08 alex
102 c2f60abe 2002-05-27 alex /* Testen, ob Client gebanned ist */
103 a1ded68a 2002-09-08 alex if(( is_banned == TRUE ) && ( is_invited == FALSE ))
104 c2f60abe 2002-05-27 alex {
105 a1ded68a 2002-09-08 alex /* Client ist gebanned (und nicht invited): */
106 f7567db0 2002-06-02 alex IRC_WriteStrClient( Client, ERR_BANNEDFROMCHAN_MSG, Client_ID( Client ), channame );
107 f7567db0 2002-06-02 alex
108 f7567db0 2002-06-02 alex /* naechsten Namen ermitteln */
109 f7567db0 2002-06-02 alex channame = strtok( NULL, "," );
110 f7567db0 2002-06-02 alex continue;
111 c2f60abe 2002-05-27 alex }
112 c2f60abe 2002-05-27 alex
113 c2f60abe 2002-05-27 alex /* Ist der Channel "invite-only"? */
114 a1ded68a 2002-09-08 alex if(( strchr( Channel_Modes( chan ), 'i' ) != NULL ) && ( is_invited == FALSE ))
115 c2f60abe 2002-05-27 alex {
116 a1ded68a 2002-09-08 alex /* Channel ist "invite-only" und Client wurde nicht invited: */
117 a1ded68a 2002-09-08 alex IRC_WriteStrClient( Client, ERR_INVITEONLYCHAN_MSG, Client_ID( Client ), channame );
118 f7567db0 2002-06-02 alex
119 a1ded68a 2002-09-08 alex /* naechsten Namen ermitteln */
120 a1ded68a 2002-09-08 alex channame = strtok( NULL, "," );
121 a1ded68a 2002-09-08 alex continue;
122 c2f60abe 2002-05-27 alex }
123 c2f60abe 2002-05-27 alex }
124 2ee05c9a 2002-03-03 alex }
125 2ee05c9a 2002-03-03 alex
126 2ee05c9a 2002-03-03 alex /* Channel joinen (und ggf. anlegen) */
127 2ee05c9a 2002-03-03 alex if( ! Channel_Join( target, channame ))
128 2ee05c9a 2002-03-03 alex {
129 2ee05c9a 2002-03-03 alex /* naechsten Namen ermitteln */
130 2ee05c9a 2002-03-03 alex channame = strtok( NULL, "," );
131 2ee05c9a 2002-03-03 alex continue;
132 2ee05c9a 2002-03-03 alex }
133 c2f60abe 2002-05-27 alex if( ! chan ) chan = Channel_Search( channame );
134 2ee05c9a 2002-03-03 alex assert( chan != NULL );
135 2ee05c9a 2002-03-03 alex
136 2ee05c9a 2002-03-03 alex /* Modes setzen (wenn vorhanden) */
137 2ee05c9a 2002-03-03 alex while( flags && *flags )
138 2ee05c9a 2002-03-03 alex {
139 2ee05c9a 2002-03-03 alex Channel_UserModeAdd( chan, target, *flags );
140 2ee05c9a 2002-03-03 alex flags++;
141 2ee05c9a 2002-03-03 alex }
142 2ee05c9a 2002-03-03 alex
143 040f5422 2002-05-21 alex /* Wenn persistenter Channel und IRC-Operator: zum Channel-OP machen */
144 040f5422 2002-05-21 alex if(( strchr( Channel_Modes( chan ), 'P' )) && ( strchr( Client_Modes( target ), 'o' ))) Channel_UserModeAdd( chan, target, 'o' );
145 040f5422 2002-05-21 alex
146 2ee05c9a 2002-03-03 alex /* Muessen Modes an andere Server gemeldet werden? */
147 2ee05c9a 2002-03-03 alex strcpy( &modes[1], Channel_UserModes( chan, target ));
148 2ee05c9a 2002-03-03 alex if( modes[1] ) modes[0] = 0x7;
149 2ee05c9a 2002-03-03 alex else modes[0] = '\0';
150 2ee05c9a 2002-03-03 alex
151 2ee05c9a 2002-03-03 alex /* An andere Server weiterleiten */
152 2ee05c9a 2002-03-03 alex IRC_WriteStrServersPrefix( Client, target, "JOIN :%s%s", channame, modes );
153 2ee05c9a 2002-03-03 alex
154 2ee05c9a 2002-03-03 alex /* im Channel bekannt machen */
155 2ee05c9a 2002-03-03 alex IRC_WriteStrChannelPrefix( Client, chan, target, FALSE, "JOIN :%s", channame );
156 2ee05c9a 2002-03-03 alex if( modes[1] )
157 2ee05c9a 2002-03-03 alex {
158 2ee05c9a 2002-03-03 alex /* Modes im Channel bekannt machen */
159 f673fb96 2002-08-27 alex IRC_WriteStrChannelPrefix( Client, chan, target, FALSE, "MODE %s +%s %s", channame, &modes[1], Client_ID( target ));
160 2ee05c9a 2002-03-03 alex }
161 2ee05c9a 2002-03-03 alex
162 2ee05c9a 2002-03-03 alex if( Client_Type( Client ) == CLIENT_USER )
163 2ee05c9a 2002-03-03 alex {
164 2ee05c9a 2002-03-03 alex /* an Client bestaetigen */
165 2ee05c9a 2002-03-03 alex IRC_WriteStrClientPrefix( Client, target, "JOIN :%s", channame );
166 2ee05c9a 2002-03-03 alex
167 2ee05c9a 2002-03-03 alex /* Topic an Client schicken */
168 2ee05c9a 2002-03-03 alex topic = Channel_Topic( chan );
169 2ee05c9a 2002-03-03 alex if( *topic ) IRC_WriteStrClient( Client, RPL_TOPIC_MSG, Client_ID( Client ), channame, topic );
170 2ee05c9a 2002-03-03 alex
171 2ee05c9a 2002-03-03 alex /* Mitglieder an Client Melden */
172 2ee05c9a 2002-03-03 alex IRC_Send_NAMES( Client, chan );
173 2ee05c9a 2002-03-03 alex IRC_WriteStrClient( Client, RPL_ENDOFNAMES_MSG, Client_ID( Client ), Channel_Name( chan ));
174 2ee05c9a 2002-03-03 alex }
175 2ee05c9a 2002-03-03 alex
176 2ee05c9a 2002-03-03 alex /* naechsten Namen ermitteln */
177 2ee05c9a 2002-03-03 alex channame = strtok( NULL, "," );
178 2ee05c9a 2002-03-03 alex }
179 2ee05c9a 2002-03-03 alex return CONNECTED;
180 2ee05c9a 2002-03-03 alex } /* IRC_JOIN */
181 2ee05c9a 2002-03-03 alex
182 2ee05c9a 2002-03-03 alex
183 c2f60abe 2002-05-27 alex GLOBAL BOOLEAN
184 c2f60abe 2002-05-27 alex IRC_PART( CLIENT *Client, REQUEST *Req )
185 2ee05c9a 2002-03-03 alex {
186 2ee05c9a 2002-03-03 alex CLIENT *target;
187 2ee05c9a 2002-03-03 alex CHAR *chan;
188 2ee05c9a 2002-03-03 alex
189 2ee05c9a 2002-03-03 alex assert( Client != NULL );
190 2ee05c9a 2002-03-03 alex assert( Req != NULL );
191 2ee05c9a 2002-03-03 alex
192 2ee05c9a 2002-03-03 alex if(( Client_Type( Client ) != CLIENT_USER ) && ( Client_Type( Client ) != CLIENT_SERVER )) return IRC_WriteStrClient( Client, ERR_NOTREGISTERED_MSG, Client_ID( Client ));
193 2ee05c9a 2002-03-03 alex
194 2ee05c9a 2002-03-03 alex /* Falsche Anzahl Parameter? */
195 2ee05c9a 2002-03-03 alex if(( Req->argc > 2 )) return IRC_WriteStrClient( Client, ERR_NEEDMOREPARAMS_MSG, Client_ID( Client ), Req->command );
196 2ee05c9a 2002-03-03 alex
197 2ee05c9a 2002-03-03 alex /* Wer ist der Absender? */
198 bc4ed226 2002-03-25 alex if( Client_Type( Client ) == CLIENT_SERVER ) target = Client_Search( Req->prefix );
199 2ee05c9a 2002-03-03 alex else target = Client;
200 2ee05c9a 2002-03-03 alex if( ! target ) return IRC_WriteStrClient( Client, ERR_NOSUCHNICK_MSG, Client_ID( Client ), Req->prefix );
201 2ee05c9a 2002-03-03 alex
202 2ee05c9a 2002-03-03 alex /* Channel-Namen durchgehen */
203 2ee05c9a 2002-03-03 alex chan = strtok( Req->argv[0], "," );
204 2ee05c9a 2002-03-03 alex while( chan )
205 2ee05c9a 2002-03-03 alex {
206 2ee05c9a 2002-03-03 alex if( ! Channel_Part( target, Client, chan, Req->argc > 1 ? Req->argv[1] : Client_ID( target )))
207 2ee05c9a 2002-03-03 alex {
208 2ee05c9a 2002-03-03 alex /* naechsten Namen ermitteln */
209 2ee05c9a 2002-03-03 alex chan = strtok( NULL, "," );
210 2ee05c9a 2002-03-03 alex continue;
211 2ee05c9a 2002-03-03 alex }
212 2ee05c9a 2002-03-03 alex
213 2ee05c9a 2002-03-03 alex /* naechsten Namen ermitteln */
214 2ee05c9a 2002-03-03 alex chan = strtok( NULL, "," );
215 2ee05c9a 2002-03-03 alex }
216 2ee05c9a 2002-03-03 alex return CONNECTED;
217 2ee05c9a 2002-03-03 alex } /* IRC_PART */
218 2ee05c9a 2002-03-03 alex
219 2ee05c9a 2002-03-03 alex
220 c2f60abe 2002-05-27 alex GLOBAL BOOLEAN
221 c2f60abe 2002-05-27 alex IRC_TOPIC( CLIENT *Client, REQUEST *Req )
222 2ee05c9a 2002-03-03 alex {
223 2ee05c9a 2002-03-03 alex CHANNEL *chan;
224 2ee05c9a 2002-03-03 alex CLIENT *from;
225 2ee05c9a 2002-03-03 alex CHAR *topic;
226 2ee05c9a 2002-03-03 alex
227 2ee05c9a 2002-03-03 alex assert( Client != NULL );
228 2ee05c9a 2002-03-03 alex assert( Req != NULL );
229 2ee05c9a 2002-03-03 alex
230 2ee05c9a 2002-03-03 alex if(( Client_Type( Client ) != CLIENT_USER ) && ( Client_Type( Client ) != CLIENT_SERVER )) return IRC_WriteStrClient( Client, ERR_NOTREGISTERED_MSG, Client_ID( Client ));
231 2ee05c9a 2002-03-03 alex
232 2ee05c9a 2002-03-03 alex /* Falsche Anzahl Parameter? */
233 2ee05c9a 2002-03-03 alex if(( Req->argc < 1 ) || ( Req->argc > 2 )) return IRC_WriteStrClient( Client, ERR_NEEDMOREPARAMS_MSG, Client_ID( Client ), Req->command );
234 2ee05c9a 2002-03-03 alex
235 bc4ed226 2002-03-25 alex if( Client_Type( Client ) == CLIENT_SERVER ) from = Client_Search( Req->prefix );
236 2ee05c9a 2002-03-03 alex else from = Client;
237 2ee05c9a 2002-03-03 alex if( ! from ) return IRC_WriteStrClient( Client, ERR_NOSUCHNICK_MSG, Client_ID( Client ), Req->prefix );
238 2ee05c9a 2002-03-03 alex
239 2ee05c9a 2002-03-03 alex /* Welcher Channel? */
240 2ee05c9a 2002-03-03 alex chan = Channel_Search( Req->argv[0] );
241 a2119a66 2002-06-01 alex if( ! chan ) return IRC_WriteStrClient( from, ERR_NOSUCHCHANNEL_MSG, Client_ID( from ), Req->argv[0] );
242 2ee05c9a 2002-03-03 alex
243 2ee05c9a 2002-03-03 alex /* Ist der User Mitglied in dem Channel? */
244 2ee05c9a 2002-03-03 alex if( ! Channel_IsMemberOf( chan, from )) return IRC_WriteStrClient( from, ERR_NOTONCHANNEL_MSG, Client_ID( from ), Req->argv[0] );
245 2ee05c9a 2002-03-03 alex
246 2ee05c9a 2002-03-03 alex if( Req->argc == 1 )
247 2ee05c9a 2002-03-03 alex {
248 2ee05c9a 2002-03-03 alex /* Topic erfragen */
249 2ee05c9a 2002-03-03 alex topic = Channel_Topic( chan );
250 2ee05c9a 2002-03-03 alex if( *topic ) return IRC_WriteStrClient( from, RPL_TOPIC_MSG, Client_ID( from ), Channel_Name( chan ), topic );
251 2ee05c9a 2002-03-03 alex else return IRC_WriteStrClient( from, RPL_NOTOPIC_MSG, Client_ID( from ), Channel_Name( chan ));
252 2ee05c9a 2002-03-03 alex }
253 2ee05c9a 2002-03-03 alex
254 2ee05c9a 2002-03-03 alex if( strchr( Channel_Modes( chan ), 't' ))
255 2ee05c9a 2002-03-03 alex {
256 2ee05c9a 2002-03-03 alex /* Topic Lock. Ist der User ein Channel Operator? */
257 2ee05c9a 2002-03-03 alex if( ! strchr( Channel_UserModes( chan, from ), 'o' )) return IRC_WriteStrClient( from, ERR_CHANOPRIVSNEEDED_MSG, Client_ID( from ), Channel_Name( chan ));
258 2ee05c9a 2002-03-03 alex }
259 2ee05c9a 2002-03-03 alex
260 2ee05c9a 2002-03-03 alex /* Topic setzen */
261 2ee05c9a 2002-03-03 alex Channel_SetTopic( chan, Req->argv[1] );
262 2ee05c9a 2002-03-03 alex Log( LOG_DEBUG, "User \"%s\" set topic on \"%s\": %s", Client_Mask( from ), Channel_Name( chan ), Req->argv[1][0] ? Req->argv[1] : "<none>" );
263 2ee05c9a 2002-03-03 alex
264 2ee05c9a 2002-03-03 alex /* im Channel bekannt machen und an Server weiterleiten */
265 2ee05c9a 2002-03-03 alex IRC_WriteStrServersPrefix( Client, from, "TOPIC %s :%s", Req->argv[0], Req->argv[1] );
266 2ee05c9a 2002-03-03 alex IRC_WriteStrChannelPrefix( Client, chan, from, FALSE, "TOPIC %s :%s", Req->argv[0], Req->argv[1] );
267 2ee05c9a 2002-03-03 alex
268 2ee05c9a 2002-03-03 alex if( Client_Type( Client ) == CLIENT_USER ) return IRC_WriteStrClientPrefix( Client, Client, "TOPIC %s :%s", Req->argv[0], Req->argv[1] );
269 2ee05c9a 2002-03-03 alex else return CONNECTED;
270 2ee05c9a 2002-03-03 alex } /* IRC_TOPIC */
271 2ee05c9a 2002-03-03 alex
272 2ee05c9a 2002-03-03 alex
273 c2f60abe 2002-05-27 alex GLOBAL BOOLEAN
274 c2f60abe 2002-05-27 alex IRC_LIST( CLIENT *Client, REQUEST *Req )
275 3c0c3c3c 2002-04-23 alex {
276 3c0c3c3c 2002-04-23 alex CHAR *pattern;
277 3c0c3c3c 2002-04-23 alex CHANNEL *chan;
278 005391ca 2002-09-16 alex CLIENT *from, *target;
279 3c0c3c3c 2002-04-23 alex
280 3c0c3c3c 2002-04-23 alex assert( Client != NULL );
281 3c0c3c3c 2002-04-23 alex assert( Req != NULL );
282 3c0c3c3c 2002-04-23 alex
283 005391ca 2002-09-16 alex if(( Client_Type( Client ) != CLIENT_USER ) && ( Client_Type( Client ) != CLIENT_SERVER )) return IRC_WriteStrClient( Client, ERR_NOTREGISTERED_MSG, Client_ID( Client ));
284 3c0c3c3c 2002-04-23 alex
285 3c0c3c3c 2002-04-23 alex /* Falsche Anzahl Parameter? */
286 005391ca 2002-09-16 alex if( Req->argc > 2 ) return IRC_WriteStrClient( Client, ERR_NEEDMOREPARAMS_MSG, Client_ID( Client ), Req->command );
287 3c0c3c3c 2002-04-23 alex
288 3c0c3c3c 2002-04-23 alex if( Req->argc > 0 ) pattern = strtok( Req->argv[0], "," );
289 3c0c3c3c 2002-04-23 alex else pattern = "*";
290 005391ca 2002-09-16 alex
291 005391ca 2002-09-16 alex /* From aus Prefix ermitteln */
292 005391ca 2002-09-16 alex if( Client_Type( Client ) == CLIENT_SERVER ) from = Client_Search( Req->prefix );
293 005391ca 2002-09-16 alex else from = Client;
294 005391ca 2002-09-16 alex if( ! from ) return IRC_WriteStrClient( Client, ERR_NOSUCHSERVER_MSG, Client_ID( Client ), Req->prefix );
295 005391ca 2002-09-16 alex
296 005391ca 2002-09-16 alex if( Req->argc == 2 )
297 005391ca 2002-09-16 alex {
298 005391ca 2002-09-16 alex /* an anderen Server forwarden */
299 005391ca 2002-09-16 alex target = Client_Search( Req->argv[1] );
300 005391ca 2002-09-16 alex if( ! target ) return IRC_WriteStrClient( from, ERR_NOSUCHSERVER_MSG, Client_ID( Client ), Req->argv[1] );
301 005391ca 2002-09-16 alex
302 005391ca 2002-09-16 alex if( target != Client_ThisServer( ))
303 005391ca 2002-09-16 alex {
304 005391ca 2002-09-16 alex /* Ok, anderer Server ist das Ziel: forwarden */
305 005391ca 2002-09-16 alex return IRC_WriteStrClientPrefix( target, from, "LIST %s :%s", from, Req->argv[1] );
306 005391ca 2002-09-16 alex }
307 005391ca 2002-09-16 alex }
308 3c0c3c3c 2002-04-23 alex
309 3c0c3c3c 2002-04-23 alex while( pattern )
310 3c0c3c3c 2002-04-23 alex {
311 3c0c3c3c 2002-04-23 alex /* alle Channel durchgehen */
312 3c0c3c3c 2002-04-23 alex chan = Channel_First( );
313 3c0c3c3c 2002-04-23 alex while( chan )
314 3c0c3c3c 2002-04-23 alex {
315 39b9f65d 2002-06-26 alex /* Passt die Suchmaske auf diesen Channel? */
316 39b9f65d 2002-06-26 alex if( Match( pattern, Channel_Name( chan )))
317 3c0c3c3c 2002-04-23 alex {
318 3c0c3c3c 2002-04-23 alex /* Treffer! */
319 005391ca 2002-09-16 alex if( ! IRC_WriteStrClient( from, RPL_LIST_MSG, from, Channel_Name( chan ), Channel_MemberCount( chan ), Channel_Topic( chan ))) return DISCONNECTED;
320 3c0c3c3c 2002-04-23 alex }
321 3c0c3c3c 2002-04-23 alex chan = Channel_Next( chan );
322 3c0c3c3c 2002-04-23 alex }
323 3c0c3c3c 2002-04-23 alex
324 3c0c3c3c 2002-04-23 alex /* naechsten Namen ermitteln */
325 3c0c3c3c 2002-04-23 alex if( Req->argc > 0 ) pattern = strtok( NULL, "," );
326 3c0c3c3c 2002-04-23 alex else pattern = NULL;
327 3c0c3c3c 2002-04-23 alex }
328 3c0c3c3c 2002-04-23 alex
329 005391ca 2002-09-16 alex return IRC_WriteStrClient( from, RPL_LISTEND_MSG, from );
330 3c0c3c3c 2002-04-23 alex } /* IRC_LIST */
331 1f9ba7b3 2002-09-03 alex
332 1f9ba7b3 2002-09-03 alex
333 1f9ba7b3 2002-09-03 alex GLOBAL BOOLEAN
334 1f9ba7b3 2002-09-03 alex IRC_CHANINFO( CLIENT *Client, REQUEST *Req )
335 1f9ba7b3 2002-09-03 alex {
336 1f9ba7b3 2002-09-03 alex CLIENT *from;
337 1f9ba7b3 2002-09-03 alex CHANNEL *chan;
338 1f9ba7b3 2002-09-03 alex CHAR *ptr;
339 1f9ba7b3 2002-09-03 alex
340 1f9ba7b3 2002-09-03 alex assert( Client != NULL );
341 1f9ba7b3 2002-09-03 alex assert( Req != NULL );
342 1f9ba7b3 2002-09-03 alex
343 1f9ba7b3 2002-09-03 alex if( Client_Type( Client ) != CLIENT_SERVER ) return IRC_WriteStrClient( Client, ERR_NOTREGISTERED_MSG, Client_ID( Client ));
344 1f9ba7b3 2002-09-03 alex
345 1f9ba7b3 2002-09-03 alex /* Falsche Anzahl Parameter? */
346 1f9ba7b3 2002-09-03 alex if(( Req->argc < 1 ) || ( Req->argc > 3 )) return IRC_WriteStrClient( Client, ERR_NEEDMOREPARAMS_MSG, Client_ID( Client ), Req->command );
347 1f9ba7b3 2002-09-03 alex
348 1f9ba7b3 2002-09-03 alex /* From-Server suchen */
349 1f9ba7b3 2002-09-03 alex from = Client_Search( Req->prefix );
350 1f9ba7b3 2002-09-03 alex if( ! from ) return IRC_WriteStrClient( Client, ERR_NOSUCHNICK_MSG, Client_ID( Client ), Req->prefix );
351 1f9ba7b3 2002-09-03 alex
352 1f9ba7b3 2002-09-03 alex /* Channel suchen bzw. erzeugen */
353 1f9ba7b3 2002-09-03 alex chan = Channel_Search( Req->argv[0] );
354 1f9ba7b3 2002-09-03 alex if( ! chan ) chan = Channel_Create( Req->argv[0] );
355 1f9ba7b3 2002-09-03 alex if( ! chan ) return CONNECTED;
356 1f9ba7b3 2002-09-03 alex
357 1f9ba7b3 2002-09-03 alex if( Req->argv[1][0] == '+' )
358 1f9ba7b3 2002-09-03 alex {
359 1f9ba7b3 2002-09-03 alex ptr = Channel_Modes( chan );
360 1f9ba7b3 2002-09-03 alex if( ! *ptr )
361 1f9ba7b3 2002-09-03 alex {
362 1f9ba7b3 2002-09-03 alex /* OK, es sind noch keine Modes gesetzt */
363 1f9ba7b3 2002-09-03 alex Channel_SetModes( chan, &Req->argv[1][1] );
364 1f9ba7b3 2002-09-03 alex IRC_WriteStrChannelPrefix( Client, chan, from, FALSE, "MODE %s +%s", Req->argv[0], &Req->argv[1][1] );
365 1f9ba7b3 2002-09-03 alex }
366 1f9ba7b3 2002-09-03 alex }
367 1f9ba7b3 2002-09-03 alex else Log( LOG_WARNING, "CHANNELINFO: invalid MODE format ignored!" );
368 3c0c3c3c 2002-04-23 alex
369 1f9ba7b3 2002-09-03 alex if( Req->argc == 3 )
370 1f9ba7b3 2002-09-03 alex {
371 1f9ba7b3 2002-09-03 alex /* Es wurde auch ein Topic mit uebermittelt */
372 1f9ba7b3 2002-09-03 alex ptr = Channel_Topic( chan );
373 1f9ba7b3 2002-09-03 alex if( ! *ptr )
374 1f9ba7b3 2002-09-03 alex {
375 1f9ba7b3 2002-09-03 alex /* OK, es ist bisher kein Topic gesetzt */
376 1f9ba7b3 2002-09-03 alex Channel_SetTopic( chan, Req->argv[2] );
377 1f9ba7b3 2002-09-03 alex IRC_WriteStrChannelPrefix( Client, chan, from, FALSE, "TOPIC %s :%s", Req->argv[0], Req->argv[2] );
378 1f9ba7b3 2002-09-03 alex }
379 1f9ba7b3 2002-09-03 alex }
380 3c0c3c3c 2002-04-23 alex
381 1f9ba7b3 2002-09-03 alex /* an andere Server forwarden */
382 1f9ba7b3 2002-09-03 alex IRC_WriteStrServersPrefixFlag( Client, from, 'C', "CHANINFO %s %s :%s", Req->argv[0], Req->argv[1], Req->argv[2] );
383 1f9ba7b3 2002-09-03 alex return CONNECTED;
384 1f9ba7b3 2002-09-03 alex } /* IRC_CHANINFO */
385 1f9ba7b3 2002-09-03 alex
386 1f9ba7b3 2002-09-03 alex
387 2ee05c9a 2002-03-03 alex /* -eof- */