updates.
[silc.git] / apps / silcd / packet_receive.c
1 /*
2
3   packet_receive.c
4
5   Author: Pekka Riikonen <priikone@poseidon.pspt.fi>
6
7   Copyright (C) 1997 - 2001 Pekka Riikonen
8
9   This program is free software; you can redistribute it and/or modify
10   it under the terms of the GNU General Public License as published by
11   the Free Software Foundation; either version 2 of the License, or
12   (at your option) any later version.
13   
14   This program is distributed in the hope that it will be useful,
15   but WITHOUT ANY WARRANTY; without even the implied warranty of
16   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
17   GNU General Public License for more details.
18
19 */
20 /*
21  * Server packet routines to handle received packets.
22  */
23 /* $Id$ */
24
25 #include "serverincludes.h"
26 #include "server_internal.h"
27
28 extern char *server_version;
29
30 /* Received notify packet. Server can receive notify packets from router. 
31    Server then relays the notify messages to clients if needed. */
32
33 void silc_server_notify(SilcServer server,
34                         SilcSocketConnection sock,
35                         SilcPacketContext *packet)
36 {
37   SilcNotifyPayload payload;
38   SilcNotifyType type;
39   SilcArgumentPayload args;
40   SilcChannelID *channel_id, *channel_id2;
41   SilcClientID *client_id, *client_id2;
42   SilcChannelEntry channel;
43   SilcClientEntry client;
44   SilcChannelClientEntry chl;
45   SilcIDCacheEntry cache;
46   unsigned int mode;
47   unsigned char *tmp;
48   unsigned int tmp_len;
49
50   SILC_LOG_DEBUG(("Start"));
51
52   if (sock->type == SILC_SOCKET_TYPE_CLIENT ||
53       packet->src_id_type != SILC_ID_SERVER)
54     return;
55
56   if (!packet->dst_id)
57     return;
58
59   /* If the packet is destined directly to a client then relay the packet
60      before processing it. */
61   if (packet->dst_id_type == SILC_ID_CLIENT) {
62     SilcIDListData idata;
63     SilcSocketConnection dst_sock;
64
65     /* Get the route to the client */
66     dst_sock = silc_server_get_client_route(server, packet->dst_id,
67                                             packet->dst_id_len, NULL, &idata);
68     if (dst_sock)
69       /* Relay the packet */
70       silc_server_relay_packet(server, dst_sock, idata->send_key,
71                                idata->hmac, packet, TRUE);
72   }
73
74   /* If we are router and this packet is not already broadcast packet
75      we will broadcast it. The sending socket really cannot be router or
76      the router is buggy. If this packet is coming from router then it must
77      have the broadcast flag set already and we won't do anything. */
78   if (!server->standalone && server->server_type == SILC_ROUTER &&
79       sock->type == SILC_SOCKET_TYPE_SERVER &&
80       !(packet->flags & SILC_PACKET_FLAG_BROADCAST)) {
81     SILC_LOG_DEBUG(("Broadcasting received Notify packet"));
82     silc_server_packet_send(server, server->router->connection, packet->type,
83                             packet->flags | SILC_PACKET_FLAG_BROADCAST, 
84                             packet->buffer->data, packet->buffer->len, FALSE);
85   }
86
87   payload = silc_notify_payload_parse(packet->buffer);
88   if (!payload)
89     return;
90
91   type = silc_notify_get_type(payload);
92   args = silc_notify_get_args(payload);
93   if (!args)
94     goto out;
95
96   switch(type) {
97   case SILC_NOTIFY_TYPE_JOIN:
98     /* 
99      * Distribute the notify to local clients on the channel
100      */
101     SILC_LOG_DEBUG(("JOIN notify"));
102
103     /* Get Channel ID */
104     tmp = silc_argument_get_arg_type(args, 2, &tmp_len);
105     if (!tmp)
106       goto out;
107     channel_id = silc_id_payload_parse_id(tmp, tmp_len);
108     if (!channel_id)
109       goto out;
110
111     /* Get channel entry */
112     channel = silc_idlist_find_channel_by_id(server->global_list, 
113                                              channel_id, NULL);
114     if (!channel) {
115       channel = silc_idlist_find_channel_by_id(server->local_list, 
116                                                channel_id, NULL);
117       if (!channel) {
118         silc_free(channel_id);
119         goto out;
120       }
121     }
122     silc_free(channel_id);
123
124     /* Get client ID */
125     tmp = silc_argument_get_arg_type(args, 1, &tmp_len);
126     if (!tmp)
127       goto out;
128     client_id = silc_id_payload_parse_id(tmp, tmp_len);
129     if (!client_id)
130       goto out;
131
132     /* Send to channel */
133     silc_server_packet_send_to_channel(server, sock, channel, packet->type, 
134                                        FALSE, packet->buffer->data, 
135                                        packet->buffer->len, FALSE);
136
137     /* If the the client is not in local list we check global list (ie. the
138        channel will be global channel) and if it does not exist then create
139        entry for the client. */
140     client = silc_idlist_find_client_by_id(server->global_list, 
141                                            client_id, NULL);
142     if (!client) {
143       client = silc_idlist_find_client_by_id(server->local_list, 
144                                              client_id, NULL);
145       if (!client) {
146         /* If router did not find the client the it is bogus */
147         if (server->server_type == SILC_ROUTER)
148           goto out;
149
150         client = 
151           silc_idlist_add_client(server->global_list, NULL, 0, NULL, NULL,
152                                  silc_id_dup(client_id, SILC_ID_CLIENT), 
153                                  sock->user_data, NULL);
154         if (!client) {
155           silc_free(client_id);
156           goto out;
157         }
158
159         client->data.registered = TRUE;
160       }
161     }
162
163     /* Do not add client to channel if it is there already */
164     if (silc_server_client_on_channel(client, channel))
165       break;
166
167     if (server->server_type == SILC_SERVER && 
168         sock->type == SILC_SOCKET_TYPE_ROUTER)
169       /* The channel is global now */
170       channel->global_users = TRUE;
171
172     /* JOIN the global client to the channel (local clients (if router 
173        created the channel) is joined in the pending JOIN command). */
174     chl = silc_calloc(1, sizeof(*chl));
175     chl->client = client;
176     chl->channel = channel;
177     silc_list_add(channel->user_list, chl);
178     silc_list_add(client->channels, chl);
179     silc_free(client_id);
180
181     break;
182
183   case SILC_NOTIFY_TYPE_LEAVE:
184     /* 
185      * Distribute the notify to local clients on the channel
186      */
187     SILC_LOG_DEBUG(("LEAVE notify"));
188
189     channel_id = silc_id_str2id(packet->dst_id, packet->dst_id_len,
190                                 packet->dst_id_type);
191     if (!channel_id)
192       goto out;
193
194     /* Get channel entry */
195     channel = silc_idlist_find_channel_by_id(server->global_list, 
196                                              channel_id, NULL);
197     if (!channel) { 
198       channel = silc_idlist_find_channel_by_id(server->local_list, 
199                                                channel_id, NULL);
200       if (!channel) {
201         silc_free(channel_id);
202         goto out;
203       }
204     }
205
206     /* Get client ID */
207     tmp = silc_argument_get_arg_type(args, 1, &tmp_len);
208     if (!tmp) {
209       silc_free(channel_id);
210       goto out;
211     }
212     client_id = silc_id_payload_parse_id(tmp, tmp_len);
213     if (!client_id) {
214       silc_free(channel_id);
215       goto out;
216     }
217
218     /* Send to channel */
219     silc_server_packet_send_to_channel(server, sock, channel, packet->type, 
220                                        FALSE, packet->buffer->data, 
221                                        packet->buffer->len, FALSE);
222
223     /* Get client entry */
224     client = silc_idlist_find_client_by_id(server->global_list, 
225                                            client_id, NULL);
226     if (!client) {
227       client = silc_idlist_find_client_by_id(server->local_list, 
228                                              client_id, NULL);
229       if (!client) {
230         silc_free(client_id);
231         silc_free(channel_id);
232         goto out;
233       }
234     }
235     silc_free(client_id);
236
237     /* Remove the user from channel */
238     silc_server_remove_from_one_channel(server, sock, channel, client, FALSE);
239     break;
240
241   case SILC_NOTIFY_TYPE_SIGNOFF:
242     /* 
243      * Distribute the notify to local clients on the channel
244      */
245     SILC_LOG_DEBUG(("SIGNOFF notify"));
246
247     /* Get client ID */
248     tmp = silc_argument_get_arg_type(args, 1, &tmp_len);
249     if (!tmp)
250       goto out;
251     client_id = silc_id_payload_parse_id(tmp, tmp_len);
252     if (!client_id)
253       goto out;
254
255     /* Get client entry */
256     client = silc_idlist_find_client_by_id(server->global_list, 
257                                            client_id, &cache);
258     if (!client) {
259       client = silc_idlist_find_client_by_id(server->local_list, 
260                                              client_id, &cache);
261       if (!client) {
262         silc_free(client_id);
263         goto out;
264       }
265     }
266     silc_free(client_id);
267
268     /* Get signoff message */
269     tmp = silc_argument_get_arg_type(args, 2, &tmp_len);
270     if (tmp_len > 128)
271       tmp = NULL;
272
273     /* Remove the client from all channels */
274     silc_server_remove_from_channels(server, NULL, client, TRUE, tmp, TRUE);
275
276     client->data.registered = FALSE;
277     cache->expire = SILC_ID_CACHE_EXPIRE_DEF;
278
279 #if 0
280     /* Remove the client entry */
281     if (!silc_idlist_del_client(server->global_list, client))
282       silc_idlist_del_client(server->local_list, client);
283 #endif
284     break;
285
286   case SILC_NOTIFY_TYPE_TOPIC_SET:
287     /* 
288      * Distribute the notify to local clients on the channel
289      */
290
291     SILC_LOG_DEBUG(("TOPIC SET notify"));
292
293     channel_id = silc_id_str2id(packet->dst_id, packet->dst_id_len,
294                                 packet->dst_id_type);
295     if (!channel_id)
296       goto out;
297
298     /* Get channel entry */
299     channel = silc_idlist_find_channel_by_id(server->global_list, 
300                                              channel_id, NULL);
301     if (!channel) {
302       channel = silc_idlist_find_channel_by_id(server->local_list, 
303                                                channel_id, NULL);
304       if (!channel) {
305         silc_free(channel_id);
306         goto out;
307       }
308     }
309
310     /* Get the topic */
311     tmp = silc_argument_get_arg_type(args, 2, &tmp_len);
312     if (!tmp) {
313       silc_free(channel_id);
314       goto out;
315     }
316
317     if (channel->topic)
318       silc_free(channel->topic);
319     channel->topic = silc_calloc(tmp_len, sizeof(*channel->topic));
320     memcpy(channel->topic, tmp, tmp_len);
321
322     /* Send the same notify to the channel */
323     silc_server_packet_send_to_channel(server, sock, channel, packet->type, 
324                                        FALSE, packet->buffer->data, 
325                                        packet->buffer->len, FALSE);
326     silc_free(channel_id);
327     break;
328
329   case SILC_NOTIFY_TYPE_NICK_CHANGE:
330     {
331       /* 
332        * Distribute the notify to local clients on the channel
333        */
334       unsigned char *id, *id2;
335
336       SILC_LOG_DEBUG(("NICK CHANGE notify"));
337       
338       /* Get old client ID */
339       id = silc_argument_get_arg_type(args, 1, &tmp_len);
340       if (!id)
341         goto out;
342       client_id = silc_id_payload_parse_id(id, tmp_len);
343       if (!client_id)
344         goto out;
345       
346       /* Get new client ID */
347       id2 = silc_argument_get_arg_type(args, 2, &tmp_len);
348       if (!id2)
349         goto out;
350       client_id2 = silc_id_payload_parse_id(id2, tmp_len);
351       if (!client_id2)
352         goto out;
353       
354       SILC_LOG_DEBUG(("Old Client ID id(%s)", 
355                       silc_id_render(client_id, SILC_ID_CLIENT)));
356       SILC_LOG_DEBUG(("New Client ID id(%s)", 
357                       silc_id_render(client_id2, SILC_ID_CLIENT)));
358
359       /* Replace the Client ID */
360       client = silc_idlist_replace_client_id(server->global_list, client_id,
361                                              client_id2);
362       if (!client)
363         client = silc_idlist_replace_client_id(server->local_list, client_id, 
364                                                client_id2);
365
366       if (client) {
367         /* The nickname is not valid anymore, set it NULL. This causes that
368            the nickname will be queried if someone wants to know it. */
369         if (client->nickname)
370           silc_free(client->nickname);
371         client->nickname = NULL;
372
373         /* Send the NICK_CHANGE notify type to local clients on the channels
374            this client is joined to. */
375         silc_server_send_notify_on_channels(server, NULL, client, 
376                                             SILC_NOTIFY_TYPE_NICK_CHANGE, 2,
377                                             id, tmp_len, 
378                                             id2, tmp_len);
379       }
380
381       silc_free(client_id);
382       if (!client)
383         silc_free(client_id2);
384       break;
385     }
386
387   case SILC_NOTIFY_TYPE_CMODE_CHANGE:
388     /* 
389      * Distribute the notify to local clients on the channel
390      */
391     
392     SILC_LOG_DEBUG(("CMODE CHANGE notify"));
393       
394     channel_id = silc_id_str2id(packet->dst_id, packet->dst_id_len,
395                                 packet->dst_id_type);
396     if (!channel_id)
397       goto out;
398
399     /* Get channel entry */
400     channel = silc_idlist_find_channel_by_id(server->global_list, 
401                                              channel_id, NULL);
402     if (!channel) {
403       channel = silc_idlist_find_channel_by_id(server->local_list, 
404                                                channel_id, NULL);
405       if (!channel) {
406         silc_free(channel_id);
407         goto out;
408       }
409     }
410
411     /* Send the same notify to the channel */
412     silc_server_packet_send_to_channel(server, sock, channel, packet->type, 
413                                        FALSE, packet->buffer->data, 
414                                        packet->buffer->len, FALSE);
415
416     /* Get the mode */
417     tmp = silc_argument_get_arg_type(args, 2, &tmp_len);
418     if (!tmp) {
419       silc_free(channel_id);
420       goto out;
421     }
422
423     SILC_GET32_MSB(mode, tmp);
424
425     /* Change mode */
426     channel->mode = mode;
427     silc_free(channel_id);
428
429     /* Get the hmac */
430     tmp = silc_argument_get_arg_type(args, 4, &tmp_len);
431     if (tmp) {
432       unsigned char hash[32];
433
434       if (channel->hmac)
435         silc_hmac_free(channel->hmac);
436       if (!silc_hmac_alloc(tmp, NULL, &channel->hmac))
437         goto out;
438
439       /* Set the HMAC key out of current channel key. The client must do
440          this locally. */
441       silc_hash_make(channel->hmac->hash, channel->key, channel->key_len / 8, 
442                      hash);
443       silc_hmac_set_key(channel->hmac, hash, 
444                         silc_hash_len(channel->hmac->hash));
445       memset(hash, 0, sizeof(hash));
446     }
447
448     break;
449
450   case SILC_NOTIFY_TYPE_CUMODE_CHANGE:
451     /* 
452      * Distribute the notify to local clients on the channel
453      */
454
455     SILC_LOG_DEBUG(("CUMODE CHANGE notify"));
456
457     channel_id = silc_id_str2id(packet->dst_id, packet->dst_id_len,
458                                 packet->dst_id_type);
459     if (!channel_id)
460       goto out;
461
462     /* Get channel entry */
463     channel = silc_idlist_find_channel_by_id(server->global_list, 
464                                              channel_id, NULL);
465     if (!channel) {
466       channel = silc_idlist_find_channel_by_id(server->local_list, 
467                                                channel_id, NULL);
468       if (!channel) {
469         silc_free(channel_id);
470         goto out;
471       }
472     }
473
474     /* Get the mode */
475     tmp = silc_argument_get_arg_type(args, 2, &tmp_len);
476     if (!tmp) {
477       silc_free(channel_id);
478       goto out;
479     }
480       
481     SILC_GET32_MSB(mode, tmp);
482
483     /* Get target client */
484     tmp = silc_argument_get_arg_type(args, 3, &tmp_len);
485     if (!tmp)
486       goto out;
487     client_id = silc_id_payload_parse_id(tmp, tmp_len);
488     if (!client_id)
489       goto out;
490     
491     /* Get client entry */
492     client = silc_idlist_find_client_by_id(server->global_list, 
493                                            client_id, NULL);
494     if (!client) {
495       client = silc_idlist_find_client_by_id(server->local_list, 
496                                              client_id, NULL);
497       if (!client) {
498         silc_free(client_id);
499         goto out;
500       }
501     }
502     silc_free(client_id);
503
504     /* Get entry to the channel user list */
505     silc_list_start(channel->user_list);
506     while ((chl = silc_list_get(channel->user_list)) != SILC_LIST_END)
507       if (chl->client == client) {
508         /* Change the mode */
509         chl->mode = mode;
510         break;
511       }
512
513     /* Send the same notify to the channel */
514     silc_server_packet_send_to_channel(server, sock, channel, packet->type, 
515                                        FALSE, packet->buffer->data, 
516                                        packet->buffer->len, FALSE);
517     silc_free(channel_id);
518     break;
519
520   case SILC_NOTIFY_TYPE_INVITE:
521
522     if (packet->dst_id_type == SILC_ID_CLIENT)
523       goto out;
524
525     SILC_LOG_DEBUG(("INVITE notify"));
526
527     /* Get Channel ID */
528     tmp = silc_argument_get_arg_type(args, 1, &tmp_len);
529     if (!tmp)
530       goto out;
531     channel_id = silc_id_payload_parse_id(tmp, tmp_len);
532     if (!channel_id)
533       goto out;
534
535     /* Get channel entry */
536     channel = silc_idlist_find_channel_by_id(server->global_list, 
537                                              channel_id, NULL);
538     if (!channel) {
539       channel = silc_idlist_find_channel_by_id(server->local_list, 
540                                                channel_id, NULL);
541       if (!channel) {
542         silc_free(channel_id);
543         goto out;
544       }
545     }
546     silc_free(channel_id);
547
548     /* Get the added invite */
549     tmp = silc_argument_get_arg_type(args, 3, &tmp_len);
550     if (tmp) {
551       if (!channel->invite_list)
552         channel->invite_list = silc_calloc(tmp_len + 2, 
553                                            sizeof(*channel->invite_list));
554       else
555         channel->invite_list = silc_realloc(channel->invite_list, 
556                                             sizeof(*channel->invite_list) * 
557                                             (tmp_len + 
558                                              strlen(channel->invite_list) + 
559                                              2));
560       if (tmp[tmp_len - 1] == ',')
561         tmp[tmp_len - 1] = '\0';
562       
563       strncat(channel->invite_list, tmp, tmp_len);
564       strncat(channel->invite_list, ",", 1);
565     }
566
567     /* Get the deleted invite */
568     tmp = silc_argument_get_arg_type(args, 4, &tmp_len);
569     if (tmp && channel->invite_list) {
570       char *start, *end, *n;
571       
572       if (!strncmp(channel->invite_list, tmp, 
573                    strlen(channel->invite_list) - 1)) {
574         silc_free(channel->invite_list);
575         channel->invite_list = NULL;
576       } else {
577         start = strstr(channel->invite_list, tmp);
578         if (start && strlen(start) >= tmp_len) {
579           end = start + tmp_len;
580           n = silc_calloc(strlen(channel->invite_list) - tmp_len, sizeof(*n));
581           strncat(n, channel->invite_list, start - channel->invite_list);
582           strncat(n, end + 1, ((channel->invite_list + 
583                                 strlen(channel->invite_list)) - end) - 1);
584           silc_free(channel->invite_list);
585           channel->invite_list = n;
586         }
587       }
588     }
589
590     break;
591
592   case SILC_NOTIFY_TYPE_CHANNEL_CHANGE:
593     /*
594      * Distribute to the local clients on the channel and change the
595      * channel ID.
596      */
597
598     SILC_LOG_DEBUG(("CHANNEL CHANGE"));
599
600     /* Get the old Channel ID */
601     tmp = silc_argument_get_arg_type(args, 1, &tmp_len);
602     if (!tmp)
603       goto out;
604     channel_id = silc_id_payload_parse_id(tmp, tmp_len);
605     if (!channel_id)
606       goto out;
607
608     /* Get the channel entry */
609     channel = silc_idlist_find_channel_by_id(server->global_list, 
610                                              channel_id, NULL);
611     if (!channel) {
612       channel = silc_idlist_find_channel_by_id(server->local_list, 
613                                                channel_id, NULL);
614       if (!channel) {
615         silc_free(channel_id);
616         goto out;
617       }
618     }
619
620     /* Send the notify to the channel */
621     silc_server_packet_send_to_channel(server, sock, channel, packet->type, 
622                                        FALSE, packet->buffer->data, 
623                                        packet->buffer->len, FALSE);
624
625     /* Get the new Channel ID */
626     tmp = silc_argument_get_arg_type(args, 2, &tmp_len);
627     if (!tmp)
628       goto out;
629     channel_id2 = silc_id_payload_parse_id(tmp, tmp_len);
630     if (!channel_id2)
631       goto out;
632
633     /* Replace the Channel ID */
634     if (!silc_idlist_replace_channel_id(server->global_list, channel_id,
635                                         channel_id2))
636       silc_idlist_replace_channel_id(server->local_list, channel_id,
637                                      channel_id2);
638
639     silc_free(channel_id);
640     silc_free(channel_id2);
641
642     break;
643
644   case SILC_NOTIFY_TYPE_SERVER_SIGNOFF:
645     SILC_LOG_DEBUG(("SERVER SIGNOFF notify (not-impl XXX)"));
646     break;
647
648   case SILC_NOTIFY_TYPE_KICKED:
649     /* 
650      * Distribute the notify to local clients on the channel
651      */
652     
653     SILC_LOG_DEBUG(("KICKED notify"));
654       
655     channel_id = silc_id_str2id(packet->dst_id, packet->dst_id_len,
656                                 packet->dst_id_type);
657     if (!channel_id)
658       goto out;
659
660     /* Get channel entry */
661     channel = silc_idlist_find_channel_by_id(server->global_list, 
662                                              channel_id, NULL);
663     if (!channel) {
664       channel = silc_idlist_find_channel_by_id(server->local_list, 
665                                                channel_id, NULL);
666       if (!channel) {
667         silc_free(channel_id);
668         goto out;
669       }
670     }
671     silc_free(channel_id);
672
673     /* Get client ID */
674     tmp = silc_argument_get_arg_type(args, 1, &tmp_len);
675     if (!tmp)
676       goto out;
677     client_id = silc_id_payload_parse_id(tmp, tmp_len);
678     if (!client_id)
679       goto out;
680
681     /* Send to channel */
682     silc_server_packet_send_to_channel(server, sock, channel, packet->type, 
683                                        FALSE, packet->buffer->data, 
684                                        packet->buffer->len, FALSE);
685
686     /* If the the client is not in local list we check global list */
687     client = silc_idlist_find_client_by_id(server->global_list, 
688                                            client_id, NULL);
689     if (!client) {
690       client = silc_idlist_find_client_by_id(server->local_list, 
691                                              client_id, NULL);
692       if (!client) {
693         silc_free(client_id);
694         goto out;
695       }
696     }
697
698     /* Remove the client from channel */
699     silc_server_remove_from_one_channel(server, sock, channel, client, FALSE);
700
701     break;
702
703   case SILC_NOTIFY_TYPE_KILLED:
704     {
705       /* 
706        * Distribute the notify to local clients on channels
707        */
708       unsigned char *id;
709       unsigned int id_len;
710     
711       SILC_LOG_DEBUG(("KILLED notify"));
712       
713       /* Get client ID */
714       id = silc_argument_get_arg_type(args, 1, &id_len);
715       if (!id)
716         goto out;
717       client_id = silc_id_payload_parse_id(id, id_len);
718       if (!client_id)
719         goto out;
720
721       /* If the the client is not in local list we check global list */
722       client = silc_idlist_find_client_by_id(server->global_list, 
723                                              client_id, NULL);
724       if (!client) {
725         client = silc_idlist_find_client_by_id(server->local_list, 
726                                                client_id, NULL);
727         if (!client) {
728           silc_free(client_id);
729           goto out;
730         }
731       }
732       silc_free(client_id);
733
734       /* If the client is one of ours, then close the connection to the
735          client now. This removes the client from all channels as well. */
736       if (packet->dst_id_type == SILC_ID_CLIENT && client->data.registered &&
737           client->connection) {
738         sock = client->connection;
739         silc_server_free_client_data(server, NULL, client, FALSE, NULL);
740         silc_server_close_connection(server, sock);
741         break;
742       }
743
744       /* Get comment */
745       tmp = silc_argument_get_arg_type(args, 2, &tmp_len);
746       if (tmp_len > 128)
747         tmp = NULL;
748
749       /* Send the notify to local clients on the channels except to the
750          client who is killed. */
751       silc_server_send_notify_on_channels(server, client, client,
752                                           SILC_NOTIFY_TYPE_KILLED, 
753                                           tmp ? 2 : 1,
754                                           id, id_len, 
755                                           tmp, tmp_len);
756
757       /* Remove the client from all channels */
758       silc_server_remove_from_channels(server, NULL, client, FALSE, NULL, 
759                                        FALSE);
760
761       break;
762     }
763
764   case SILC_NOTIFY_TYPE_UMODE_CHANGE:
765     /*
766      * Save the mode of the client.
767      */
768
769     SILC_LOG_DEBUG(("UMODE_CHANGE notify"));
770       
771     /* Get client ID */
772     tmp = silc_argument_get_arg_type(args, 1, &tmp_len);
773     if (!tmp)
774       goto out;
775     client_id = silc_id_payload_parse_id(tmp, tmp_len);
776     if (!client_id)
777       goto out;
778
779     /* Get client entry */
780     client = silc_idlist_find_client_by_id(server->global_list, 
781                                            client_id, NULL);
782     if (!client) {
783       client = silc_idlist_find_client_by_id(server->local_list, 
784                                              client_id, NULL);
785       if (!client) {
786         silc_free(client_id);
787         goto out;
788       }
789     }
790     silc_free(client_id);
791
792     /* Get the mode */
793     tmp = silc_argument_get_arg_type(args, 2, &tmp_len);
794     if (!tmp)
795       goto out;
796
797     /* Save the mode */
798     SILC_GET32_MSB(client->mode, tmp);
799
800     break;
801
802   case SILC_NOTIFY_TYPE_BAN:
803     /*
804      * Save the ban
805      */
806
807     SILC_LOG_DEBUG(("BAN notify"));
808     
809     /* Get Channel ID */
810     tmp = silc_argument_get_arg_type(args, 1, &tmp_len);
811     if (!tmp)
812       goto out;
813     channel_id = silc_id_payload_parse_id(tmp, tmp_len);
814     if (!channel_id)
815       goto out;
816     
817     /* Get channel entry */
818     channel = silc_idlist_find_channel_by_id(server->global_list, 
819                                              channel_id, NULL);
820     if (!channel) {
821       channel = silc_idlist_find_channel_by_id(server->local_list, 
822                                                channel_id, NULL);
823       if (!channel) {
824         silc_free(channel_id);
825         goto out;
826       }
827     }
828     silc_free(channel_id);
829
830     /* Get the new ban and add it to the ban list */
831     tmp = silc_argument_get_arg_type(args, 2, &tmp_len);
832     if (tmp) {
833       if (!channel->ban_list)
834         channel->ban_list = silc_calloc(tmp_len + 2, 
835                                         sizeof(*channel->ban_list));
836       else
837         channel->ban_list = silc_realloc(channel->ban_list, 
838                                          sizeof(*channel->ban_list) * 
839                                          (tmp_len + 
840                                           strlen(channel->ban_list) + 2));
841       strncat(channel->ban_list, tmp, tmp_len);
842       strncat(channel->ban_list, ",", 1);
843     }
844
845     /* Get the ban to be removed and remove it from the list */
846     tmp = silc_argument_get_arg_type(args, 3, &tmp_len);
847     if (tmp && channel->ban_list) {
848       char *start, *end, *n;
849       
850       if (!strcmp(channel->ban_list, tmp)) {
851         silc_free(channel->ban_list);
852         channel->ban_list = NULL;
853       } else {
854         start = strstr(channel->ban_list, tmp);
855         if (start && strlen(start) >= tmp_len) {
856           end = start + tmp_len;
857           n = silc_calloc(strlen(channel->ban_list) - tmp_len, sizeof(*n));
858           strncat(n, channel->ban_list, start - channel->ban_list);
859           strncat(n, end + 1, ((channel->ban_list + 
860                                 strlen(channel->ban_list)) - end) - 1);
861           silc_free(channel->ban_list);
862           channel->ban_list = n;
863         }
864       }
865     }
866
867     break;
868
869     /* Ignore rest of the notify types for now */
870   case SILC_NOTIFY_TYPE_NONE:
871   case SILC_NOTIFY_TYPE_MOTD:
872     break;
873   default:
874     break;
875   }
876
877  out:
878   silc_notify_payload_free(payload);
879 }
880
881 void silc_server_notify_list(SilcServer server,
882                              SilcSocketConnection sock,
883                              SilcPacketContext *packet)
884 {
885   SilcPacketContext *new;
886   SilcBuffer buffer;
887   unsigned short len;
888
889   SILC_LOG_DEBUG(("Processing New Notify List"));
890
891   if (sock->type == SILC_SOCKET_TYPE_CLIENT ||
892       packet->src_id_type != SILC_ID_SERVER)
893     return;
894
895   /* Make copy of the original packet context, except for the actual
896      data buffer, which we will here now fetch from the original buffer. */
897   new = silc_packet_context_alloc();
898   new->type = SILC_PACKET_NOTIFY;
899   new->flags = packet->flags;
900   new->src_id = packet->src_id;
901   new->src_id_len = packet->src_id_len;
902   new->src_id_type = packet->src_id_type;
903   new->dst_id = packet->dst_id;
904   new->dst_id_len = packet->dst_id_len;
905   new->dst_id_type = packet->dst_id_type;
906
907   buffer = silc_buffer_alloc(1024);
908   new->buffer = buffer;
909
910   while (packet->buffer->len) {
911     SILC_GET16_MSB(len, packet->buffer->data + 2);
912     if (len > packet->buffer->len)
913       break;
914
915     if (len > buffer->truelen) {
916       silc_buffer_free(buffer);
917       buffer = silc_buffer_alloc(1024 + len);
918     }
919
920     silc_buffer_pull_tail(buffer, len);
921     silc_buffer_put(buffer, packet->buffer->data, len);
922
923     /* Process the Notify */
924     silc_server_notify(server, sock, new);
925
926     silc_buffer_push_tail(buffer, len);
927     silc_buffer_pull(packet->buffer, len);
928   }
929
930   silc_buffer_free(buffer);
931   silc_free(new);
932 }
933
934 /* Received private message. This resolves the destination of the message 
935    and sends the packet. This is used by both server and router.  If the
936    destination is our locally connected client this sends the packet to
937    the client. This may also send the message for further routing if
938    the destination is not in our server (or router). */
939
940 void silc_server_private_message(SilcServer server,
941                                  SilcSocketConnection sock,
942                                  SilcPacketContext *packet)
943 {
944   SilcSocketConnection dst_sock;
945   SilcIDListData idata;
946
947   SILC_LOG_DEBUG(("Start"));
948
949   if (packet->src_id_type != SILC_ID_CLIENT ||
950       packet->dst_id_type != SILC_ID_CLIENT)
951     return;
952
953   if (!packet->dst_id)
954     return;
955
956   /* Get the route to the client */
957   dst_sock = silc_server_get_client_route(server, packet->dst_id,
958                                           packet->dst_id_len, NULL, &idata);
959   if (!dst_sock)
960     return;
961
962   /* Send the private message */
963   silc_server_send_private_message(server, dst_sock, idata->send_key,
964                                    idata->hmac, packet);
965 }
966
967 /* Received private message key packet.. This packet is never for us. It is to
968    the client in the packet's destination ID. Sending of this sort of packet
969    equals sending private message, ie. it is sent point to point from
970    one client to another. */
971
972 void silc_server_private_message_key(SilcServer server,
973                                      SilcSocketConnection sock,
974                                      SilcPacketContext *packet)
975 {
976   SilcSocketConnection dst_sock;
977   SilcIDListData idata;
978
979   SILC_LOG_DEBUG(("Start"));
980
981   if (packet->src_id_type != SILC_ID_CLIENT ||
982       packet->dst_id_type != SILC_ID_CLIENT)
983     return;
984
985   if (!packet->dst_id)
986     return;
987
988   /* Get the route to the client */
989   dst_sock = silc_server_get_client_route(server, packet->dst_id,
990                                           packet->dst_id_len, NULL, &idata);
991   if (!dst_sock)
992     return;
993
994   /* Relay the packet */
995   silc_server_relay_packet(server, dst_sock, idata->send_key,
996                            idata->hmac, packet, FALSE);
997 }
998
999 /* Processes incoming command reply packet. The command reply packet may
1000    be destined to one of our clients or it may directly for us. We will 
1001    call the command reply routine after processing the packet. */
1002
1003 void silc_server_command_reply(SilcServer server,
1004                                SilcSocketConnection sock,
1005                                SilcPacketContext *packet)
1006 {
1007   SilcBuffer buffer = packet->buffer;
1008   SilcClientEntry client = NULL;
1009   SilcSocketConnection dst_sock;
1010   SilcIDListData idata;
1011   SilcClientID *id = NULL;
1012
1013   SILC_LOG_DEBUG(("Start"));
1014
1015   /* Source must be server or router */
1016   if (packet->src_id_type != SILC_ID_SERVER &&
1017       sock->type != SILC_SOCKET_TYPE_ROUTER)
1018     return;
1019
1020   if (packet->dst_id_type == SILC_ID_CHANNEL)
1021     return;
1022
1023   if (packet->dst_id_type == SILC_ID_CLIENT) {
1024     /* Destination must be one of ours */
1025     id = silc_id_str2id(packet->dst_id, packet->dst_id_len, SILC_ID_CLIENT);
1026     if (!id)
1027       return;
1028     client = silc_idlist_find_client_by_id(server->local_list, id, NULL);
1029     if (!client) {
1030       SILC_LOG_ERROR(("Cannot process command reply to unknown client"));
1031       silc_free(id);
1032       return;
1033     }
1034   }
1035
1036   if (packet->dst_id_type == SILC_ID_SERVER) {
1037     /* For now this must be for us */
1038     if (SILC_ID_SERVER_COMPARE(packet->dst_id, server->id_string)) {
1039       SILC_LOG_ERROR(("Cannot process command reply to unknown server"));
1040       return;
1041     }
1042   }
1043
1044   /* Execute command reply locally for the command */
1045   silc_server_command_reply_process(server, sock, buffer);
1046
1047   if (packet->dst_id_type == SILC_ID_CLIENT && client && id) {
1048     /* Relay the packet to the client */
1049     
1050     dst_sock = (SilcSocketConnection)client->connection;
1051     silc_buffer_push(buffer, SILC_PACKET_HEADER_LEN + packet->src_id_len 
1052                      + packet->dst_id_len + packet->padlen);
1053     
1054     silc_packet_send_prepare(dst_sock, 0, 0, buffer->len);
1055     silc_buffer_put(dst_sock->outbuf, buffer->data, buffer->len);
1056     
1057     idata = (SilcIDListData)client;
1058     
1059     /* Encrypt packet */
1060     silc_packet_encrypt(idata->send_key, idata->hmac, dst_sock->outbuf, 
1061                         buffer->len);
1062     
1063     /* Send the packet */
1064     silc_server_packet_send_real(server, dst_sock, TRUE);
1065
1066     silc_free(id);
1067   }
1068 }
1069
1070 /* Process received channel message. The message can be originated from
1071    client or server. */
1072
1073 void silc_server_channel_message(SilcServer server,
1074                                  SilcSocketConnection sock,
1075                                  SilcPacketContext *packet)
1076 {
1077   SilcChannelEntry channel = NULL;
1078   SilcChannelClientEntry chl;
1079   SilcChannelID *id = NULL;
1080   void *sender = NULL;
1081
1082   SILC_LOG_DEBUG(("Processing channel message"));
1083
1084   /* Sanity checks */
1085   if (packet->dst_id_type != SILC_ID_CHANNEL) {
1086     SILC_LOG_DEBUG(("Received bad message for channel, dropped"));
1087     goto out;
1088   }
1089
1090   /* Find channel entry */
1091   id = silc_id_str2id(packet->dst_id, packet->dst_id_len, SILC_ID_CHANNEL);
1092   if (!id)
1093     goto out;
1094   channel = silc_idlist_find_channel_by_id(server->local_list, id, NULL);
1095   if (!channel) {
1096     channel = silc_idlist_find_channel_by_id(server->global_list, id, NULL);
1097     if (!channel) {
1098       SILC_LOG_DEBUG(("Could not find channel"));
1099       goto out;
1100     }
1101   }
1102
1103   /* See that this client is on the channel. If the message is coming
1104      from router we won't do the check as the message is from client that
1105      we don't know about. Also, if the original sender is not client
1106      (as it can be server as well) we don't do the check. */
1107   sender = silc_id_str2id(packet->src_id, packet->src_id_len, 
1108                           packet->src_id_type);
1109   if (!sender)
1110     goto out;
1111   if (sock->type != SILC_SOCKET_TYPE_ROUTER && 
1112       packet->src_id_type == SILC_ID_CLIENT) {
1113     silc_list_start(channel->user_list);
1114     while ((chl = silc_list_get(channel->user_list)) != SILC_LIST_END) {
1115       if (chl->client && !SILC_ID_CLIENT_COMPARE(chl->client->id, sender))
1116         break;
1117     }
1118     if (chl == SILC_LIST_END) {
1119       SILC_LOG_DEBUG(("Client not on channel"));
1120       goto out;
1121     }
1122   }
1123
1124   /* If we are router and the packet came from router and private key
1125      has not been set for the channel then we must encrypt the packet
1126      as it was decrypted with the session key shared between us and the
1127      router which sent it. This is so, because cells does not share the
1128      same channel key */
1129   if (server->server_type == SILC_ROUTER &&
1130       sock->type == SILC_SOCKET_TYPE_ROUTER &&
1131       !(channel->mode & SILC_CHANNEL_MODE_PRIVKEY)) {
1132     SilcBuffer chp;
1133     unsigned int iv_len, i, data_len;
1134
1135     iv_len = silc_cipher_get_block_len(channel->channel_key);
1136     if (channel->iv[0] == '\0')
1137       for (i = 0; i < iv_len; i++) channel->iv[i] = 
1138                                      silc_rng_get_byte(server->rng);
1139     else
1140       silc_hash_make(server->md5hash, channel->iv, iv_len, channel->iv);
1141     
1142     /* Encode new payload. This encrypts it also. */
1143     SILC_GET16_MSB(data_len, packet->buffer->data);
1144     chp = silc_channel_message_payload_encode(data_len, 
1145                                               packet->buffer->data + 2,
1146                                               iv_len, channel->iv,
1147                                               channel->channel_key,
1148                                               channel->hmac, server->rng);
1149     silc_buffer_put(packet->buffer, chp->data, chp->len);
1150     silc_buffer_free(chp);
1151   }
1152
1153   /* Distribute the packet to our local clients. This will send the
1154      packet for further routing as well, if needed. */
1155   silc_server_packet_relay_to_channel(server, sock, channel, sender,
1156                                       packet->src_id_type,
1157                                       packet->buffer->data,
1158                                       packet->buffer->len, FALSE);
1159
1160  out:
1161   if (sender)
1162     silc_free(sender);
1163   if (id)
1164     silc_free(id);
1165 }
1166
1167 /* Received channel key packet. We distribute the key to all of our locally
1168    connected clients on the channel. */
1169
1170 void silc_server_channel_key(SilcServer server,
1171                              SilcSocketConnection sock,
1172                              SilcPacketContext *packet)
1173 {
1174   SilcBuffer buffer = packet->buffer;
1175   SilcChannelEntry channel;
1176
1177   if (packet->src_id_type != SILC_ID_SERVER)
1178     return;
1179
1180   /* Save the channel key */
1181   channel = silc_server_save_channel_key(server, buffer, NULL);
1182   if (!channel)
1183     return;
1184
1185   /* Distribute the key to everybody who is on the channel. If we are router
1186      we will also send it to locally connected servers. */
1187   silc_server_send_channel_key(server, sock, channel, FALSE);
1188 }
1189
1190 /* Received New Client packet and processes it.  Creates Client ID for the
1191    client. Client becomes registered after calling this functions. */
1192
1193 SilcClientEntry silc_server_new_client(SilcServer server,
1194                                        SilcSocketConnection sock,
1195                                        SilcPacketContext *packet)
1196 {
1197   SilcBuffer buffer = packet->buffer;
1198   SilcClientEntry client;
1199   SilcIDCacheEntry cache;
1200   SilcClientID *client_id;
1201   SilcBuffer reply;
1202   SilcIDListData idata;
1203   char *username = NULL, *realname = NULL, *id_string;
1204   int ret;
1205
1206   SILC_LOG_DEBUG(("Creating new client"));
1207
1208   if (sock->type != SILC_SOCKET_TYPE_CLIENT)
1209     return NULL;
1210
1211   /* Take client entry */
1212   client = (SilcClientEntry)sock->user_data;
1213   idata = (SilcIDListData)client;
1214
1215   /* Fetch the old client cache entry so that we can update it. */
1216   if (!silc_idcache_find_by_context(server->local_list->clients,
1217                                     sock->user_data, &cache)) {
1218     SILC_LOG_ERROR(("Lost client's cache entry - bad thing"));
1219     return NULL;
1220   }
1221
1222   /* Parse incoming packet */
1223   ret = silc_buffer_unformat(buffer,
1224                              SILC_STR_UI16_STRING_ALLOC(&username),
1225                              SILC_STR_UI16_STRING_ALLOC(&realname),
1226                              SILC_STR_END);
1227   if (ret == -1) {
1228     if (username)
1229       silc_free(username);
1230     if (realname)
1231       silc_free(realname);
1232     return NULL;
1233   }
1234
1235   if (!username) {
1236     silc_free(username);
1237     if (realname)
1238       silc_free(realname);
1239     silc_server_disconnect_remote(server, sock, "Server closed connection: "
1240                                   "Incomplete client information");
1241     return NULL;
1242   }
1243
1244   /* Create Client ID */
1245   silc_id_create_client_id(server->id, server->rng, server->md5hash,
1246                            username, &client_id);
1247
1248   if (strlen(username) > 128)
1249     username[127] = '\0';
1250
1251   /* Update client entry */
1252   idata->registered = TRUE;
1253   client->nickname = strdup(username);
1254   client->username = username;
1255   client->userinfo = realname ? realname : strdup(" ");
1256   client->id = client_id;
1257
1258   /* Update the cache entry */
1259   cache->id = (void *)client_id;
1260   cache->type = SILC_ID_CLIENT;
1261   cache->data = username;
1262   silc_idcache_sort_by_data(server->local_list->clients);
1263
1264   /* Notify our router about new client on the SILC network */
1265   if (!server->standalone)
1266     silc_server_send_new_id(server, (SilcSocketConnection) 
1267                             server->router->connection, 
1268                             server->server_type == SILC_ROUTER ? TRUE : FALSE,
1269                             client->id, SILC_ID_CLIENT, SILC_ID_CLIENT_LEN);
1270   
1271   /* Send the new client ID to the client. */
1272   id_string = silc_id_id2str(client->id, SILC_ID_CLIENT);
1273   reply = silc_buffer_alloc(2 + 2 + SILC_ID_CLIENT_LEN);
1274   silc_buffer_pull_tail(reply, SILC_BUFFER_END(reply));
1275   silc_buffer_format(reply,
1276                      SILC_STR_UI_SHORT(SILC_ID_CLIENT),
1277                      SILC_STR_UI_SHORT(SILC_ID_CLIENT_LEN),
1278                      SILC_STR_UI_XNSTRING(id_string, SILC_ID_CLIENT_LEN),
1279                      SILC_STR_END);
1280   silc_server_packet_send(server, sock, SILC_PACKET_NEW_ID, 0, 
1281                           reply->data, reply->len, FALSE);
1282   silc_free(id_string);
1283   silc_buffer_free(reply);
1284
1285   /* Send some nice info to the client */
1286   SILC_SERVER_SEND_NOTIFY(server, sock, SILC_NOTIFY_TYPE_NONE,
1287                           ("Welcome to the SILC Network %s@%s",
1288                            username, sock->hostname));
1289   SILC_SERVER_SEND_NOTIFY(server, sock, SILC_NOTIFY_TYPE_NONE,
1290                           ("Your host is %s, running version %s",
1291                            server->config->server_info->server_name,
1292                            server_version));
1293   if (server->server_type == SILC_ROUTER) {
1294     SILC_SERVER_SEND_NOTIFY(server, sock, SILC_NOTIFY_TYPE_NONE,
1295                             ("There are %d clients on %d servers in SILC "
1296                              "Network", server->stat.clients,
1297                              server->stat.servers + 1));
1298     SILC_SERVER_SEND_NOTIFY(server, sock, SILC_NOTIFY_TYPE_NONE,
1299                             ("There are %d clients on %d server in our cell",
1300                              server->stat.cell_clients,
1301                              server->stat.cell_servers + 1));
1302     SILC_SERVER_SEND_NOTIFY(server, sock, SILC_NOTIFY_TYPE_NONE,
1303                             ("I have %d clients, %d channels, %d servers and "
1304                              "%d routers",
1305                              server->stat.my_clients, 
1306                              server->stat.my_channels,
1307                              server->stat.my_servers,
1308                              server->stat.my_routers));
1309     SILC_SERVER_SEND_NOTIFY(server, sock, SILC_NOTIFY_TYPE_NONE,
1310                             ("%d server operators and %d router operators "
1311                              "online",
1312                              server->stat.my_server_ops,
1313                              server->stat.my_router_ops));
1314   } else {
1315     SILC_SERVER_SEND_NOTIFY(server, sock, SILC_NOTIFY_TYPE_NONE,
1316                             ("I have %d clients and %d channels formed",
1317                              server->stat.my_clients,
1318                              server->stat.my_channels));
1319     SILC_SERVER_SEND_NOTIFY(server, sock, SILC_NOTIFY_TYPE_NONE,
1320                             ("%d operators online",
1321                              server->stat.my_server_ops));
1322   }
1323   SILC_SERVER_SEND_NOTIFY(server, sock, SILC_NOTIFY_TYPE_NONE,
1324                           ("Your connection is secured with %s cipher, "
1325                            "key length %d bits",
1326                            idata->send_key->cipher->name,
1327                            idata->send_key->cipher->key_len));
1328   SILC_SERVER_SEND_NOTIFY(server, sock, SILC_NOTIFY_TYPE_NONE,
1329                           ("Your current nickname is %s",
1330                            client->nickname));
1331
1332   /* Send motd */
1333   silc_server_send_motd(server, sock);
1334
1335   return client;
1336 }
1337
1338 /* Create new server. This processes received New Server packet and
1339    saves the received Server ID. The server is our locally connected
1340    server thus we save all the information and save it to local list. 
1341    This funtion can be used by both normal server and router server.
1342    If normal server uses this it means that its router has connected
1343    to the server. If router uses this it means that one of the cell's
1344    servers is connected to the router. */
1345
1346 SilcServerEntry silc_server_new_server(SilcServer server,
1347                                        SilcSocketConnection sock,
1348                                        SilcPacketContext *packet)
1349 {
1350   SilcBuffer buffer = packet->buffer;
1351   SilcServerEntry new_server;
1352   SilcIDCacheEntry cache;
1353   SilcServerID *server_id;
1354   SilcIDListData idata;
1355   unsigned char *server_name, *id_string;
1356   unsigned short id_len, name_len;
1357   int ret;
1358
1359   SILC_LOG_DEBUG(("Creating new server"));
1360
1361   if (sock->type != SILC_SOCKET_TYPE_SERVER &&
1362       sock->type != SILC_SOCKET_TYPE_ROUTER)
1363     return NULL;
1364
1365   /* Take server entry */
1366   new_server = (SilcServerEntry)sock->user_data;
1367   idata = (SilcIDListData)new_server;
1368
1369   /* Fetch the old server cache entry so that we can update it. */
1370   if (!silc_idcache_find_by_context(server->local_list->servers,
1371                                     sock->user_data, &cache)) {
1372     SILC_LOG_ERROR(("Lost server's cache entry - bad thing"));
1373     return NULL;
1374   }
1375
1376   /* Parse the incoming packet */
1377   ret = silc_buffer_unformat(buffer,
1378                              SILC_STR_UI16_NSTRING_ALLOC(&id_string, &id_len),
1379                              SILC_STR_UI16_NSTRING_ALLOC(&server_name, 
1380                                                          &name_len),
1381                              SILC_STR_END);
1382   if (ret == -1) {
1383     if (id_string)
1384       silc_free(id_string);
1385     if (server_name)
1386       silc_free(server_name);
1387     return NULL;
1388   }
1389
1390   if (id_len > buffer->len) {
1391     silc_free(id_string);
1392     silc_free(server_name);
1393     return NULL;
1394   }
1395
1396   if (name_len > 256)
1397     server_name[255] = '\0';
1398
1399   /* Get Server ID */
1400   server_id = silc_id_str2id(id_string, id_len, SILC_ID_SERVER);
1401   if (!server_id) {
1402     silc_free(id_string);
1403     silc_free(server_name);
1404     return NULL;
1405   }
1406   silc_free(id_string);
1407
1408   /* Update client entry */
1409   idata->registered = TRUE;
1410   new_server->server_name = server_name;
1411   new_server->id = server_id;
1412
1413   /* Update the cache entry */
1414   cache->id = (void *)server_id;
1415   cache->type = SILC_ID_SERVER;
1416   cache->data = server_name;
1417   silc_idcache_sort_by_data(server->local_list->servers);
1418
1419   /* Distribute the information about new server in the SILC network
1420      to our router. If we are normal server we won't send anything
1421      since this connection must be our router connection. */
1422   if (server->server_type == SILC_ROUTER && !server->standalone &&
1423       server->router->connection != sock)
1424     silc_server_send_new_id(server, server->router->connection,
1425                             TRUE, new_server->id, SILC_ID_SERVER, 
1426                             SILC_ID_SERVER_LEN);
1427
1428   if (server->server_type == SILC_ROUTER)
1429     server->stat.cell_servers++;
1430
1431   return new_server;
1432 }
1433
1434 /* Processes incoming New ID packet. New ID Payload is used to distribute
1435    information about newly registered clients and servers. */
1436
1437 static void silc_server_new_id_real(SilcServer server, 
1438                                     SilcSocketConnection sock,
1439                                     SilcPacketContext *packet,
1440                                     int broadcast)
1441 {
1442   SilcBuffer buffer = packet->buffer;
1443   SilcIDList id_list;
1444   SilcServerEntry router;
1445   SilcSocketConnection router_sock;
1446   SilcIDPayload idp;
1447   SilcIdType id_type;
1448   unsigned char *hash = NULL;
1449   void *id;
1450
1451   SILC_LOG_DEBUG(("Processing new ID"));
1452
1453   if (sock->type == SILC_SOCKET_TYPE_CLIENT ||
1454       server->server_type == SILC_SERVER ||
1455       packet->src_id_type != SILC_ID_SERVER)
1456     return;
1457
1458   idp = silc_id_payload_parse(buffer);
1459   if (!idp)
1460     return;
1461
1462   id_type = silc_id_payload_get_type(idp);
1463
1464   /* Normal server cannot have other normal server connections */
1465   if (id_type == SILC_ID_SERVER && sock->type == SILC_SOCKET_TYPE_SERVER)
1466     goto out;
1467
1468   id = silc_id_payload_get_id(idp);
1469   if (!id)
1470     goto out;
1471
1472   /* If the sender of this packet is server and we are router we need to
1473      broadcast this packet to other routers in the network. */
1474   if (broadcast && !server->standalone && server->server_type == SILC_ROUTER &&
1475       sock->type == SILC_SOCKET_TYPE_SERVER &&
1476       !(packet->flags & SILC_PACKET_FLAG_BROADCAST)) {
1477     SILC_LOG_DEBUG(("Broadcasting received New ID packet"));
1478     silc_server_packet_send(server, server->router->connection,
1479                             packet->type, 
1480                             packet->flags | SILC_PACKET_FLAG_BROADCAST,
1481                             buffer->data, buffer->len, FALSE);
1482   }
1483
1484   if (sock->type == SILC_SOCKET_TYPE_SERVER)
1485     id_list = server->local_list;
1486   else
1487     id_list = server->global_list;
1488
1489   router_sock = sock;
1490   router = sock->user_data;
1491
1492   switch(id_type) {
1493   case SILC_ID_CLIENT:
1494     {
1495       SilcClientEntry entry;
1496
1497       SILC_LOG_DEBUG(("New client id(%s) from [%s] %s",
1498                       silc_id_render(id, SILC_ID_CLIENT),
1499                       sock->type == SILC_SOCKET_TYPE_SERVER ?
1500                       "Server" : "Router", sock->hostname));
1501     
1502       /* As a router we keep information of all global information in our
1503          global list. Cell wide information however is kept in the local
1504          list. The client is put to global list and we will take the hash
1505          value of the Client ID and save it to the ID Cache system for fast
1506          searching in the future. */
1507       hash = silc_calloc(sizeof(((SilcClientID *)id)->hash),
1508                          sizeof(unsigned char));
1509       memcpy(hash, ((SilcClientID *)id)->hash, 
1510              sizeof(((SilcClientID *)id)->hash));
1511       entry = silc_idlist_add_client(id_list, hash, 
1512                                      sizeof(((SilcClientID *)id)->hash),
1513                                      NULL, NULL, id, router, NULL);
1514       entry->nickname = NULL;
1515       entry->data.registered = TRUE;
1516
1517       if (sock->type == SILC_SOCKET_TYPE_SERVER)
1518         server->stat.cell_clients++;
1519       server->stat.clients++;
1520     }
1521     break;
1522
1523   case SILC_ID_SERVER:
1524     SILC_LOG_DEBUG(("New server id(%s) from [%s] %s",
1525                     silc_id_render(id, SILC_ID_SERVER),
1526                     sock->type == SILC_SOCKET_TYPE_SERVER ?
1527                     "Server" : "Router", sock->hostname));
1528     
1529     /* As a router we keep information of all global information in our global
1530        list. Cell wide information however is kept in the local list. */
1531     silc_idlist_add_server(id_list, NULL, 0, id, router, router_sock);
1532
1533     if (sock->type == SILC_SOCKET_TYPE_SERVER)
1534       server->stat.cell_servers++;
1535     server->stat.servers++;
1536     break;
1537
1538   case SILC_ID_CHANNEL:
1539     SILC_LOG_ERROR(("Channel cannot be registered with NEW_ID packet"));
1540     break;
1541
1542   default:
1543     break;
1544   }
1545
1546  out:
1547   silc_id_payload_free(idp);
1548 }
1549
1550
1551 /* Processes incoming New ID packet. New ID Payload is used to distribute
1552    information about newly registered clients and servers. */
1553
1554 void silc_server_new_id(SilcServer server, SilcSocketConnection sock,
1555                         SilcPacketContext *packet)
1556 {
1557   silc_server_new_id_real(server, sock, packet, TRUE);
1558 }
1559
1560 /* Receoved New Id List packet, list of New ID payloads inside one
1561    packet. Process the New ID payloads one by one. */
1562
1563 void silc_server_new_id_list(SilcServer server, SilcSocketConnection sock,
1564                              SilcPacketContext *packet)
1565 {
1566   SilcPacketContext *new_id;
1567   SilcBuffer idp;
1568   unsigned short id_len;
1569
1570   SILC_LOG_DEBUG(("Processing New ID List"));
1571
1572   if (sock->type == SILC_SOCKET_TYPE_CLIENT ||
1573       packet->src_id_type != SILC_ID_SERVER)
1574     return;
1575
1576   /* If the sender of this packet is server and we are router we need to
1577      broadcast this packet to other routers in the network. Broadcast
1578      this list packet instead of multiple New ID packets. */
1579   if (!server->standalone && server->server_type == SILC_ROUTER &&
1580       sock->type == SILC_SOCKET_TYPE_SERVER &&
1581       !(packet->flags & SILC_PACKET_FLAG_BROADCAST)) {
1582     SILC_LOG_DEBUG(("Broadcasting received New ID List packet"));
1583     silc_server_packet_send(server, server->router->connection,
1584                             packet->type, 
1585                             packet->flags | SILC_PACKET_FLAG_BROADCAST,
1586                             packet->buffer->data, packet->buffer->len, FALSE);
1587   }
1588
1589   /* Make copy of the original packet context, except for the actual
1590      data buffer, which we will here now fetch from the original buffer. */
1591   new_id = silc_packet_context_alloc();
1592   new_id->type = SILC_PACKET_NEW_ID;
1593   new_id->flags = packet->flags;
1594   new_id->src_id = packet->src_id;
1595   new_id->src_id_len = packet->src_id_len;
1596   new_id->src_id_type = packet->src_id_type;
1597   new_id->dst_id = packet->dst_id;
1598   new_id->dst_id_len = packet->dst_id_len;
1599   new_id->dst_id_type = packet->dst_id_type;
1600
1601   idp = silc_buffer_alloc(256);
1602   new_id->buffer = idp;
1603
1604   while (packet->buffer->len) {
1605     SILC_GET16_MSB(id_len, packet->buffer->data + 2);
1606     if ((id_len > packet->buffer->len) ||
1607         (id_len > idp->truelen))
1608       break;
1609
1610     silc_buffer_pull_tail(idp, 4 + id_len);
1611     silc_buffer_put(idp, packet->buffer->data, 4 + id_len);
1612
1613     /* Process the New ID */
1614     silc_server_new_id_real(server, sock, new_id, FALSE);
1615
1616     silc_buffer_push_tail(idp, 4 + id_len);
1617     silc_buffer_pull(packet->buffer, 4 + id_len);
1618   }
1619
1620   silc_buffer_free(idp);
1621   silc_free(new_id);
1622 }
1623
1624 /* Received New Channel packet. Information about new channels in the 
1625    network are distributed using this packet. Save the information about
1626    the new channel. This usually comes from router but also normal server
1627    can send this to notify channels it has when it connects to us. */
1628
1629 void silc_server_new_channel(SilcServer server,
1630                              SilcSocketConnection sock,
1631                              SilcPacketContext *packet)
1632 {
1633   SilcChannelPayload payload;
1634   SilcChannelID *channel_id;
1635   char *channel_name;
1636   unsigned int name_len;
1637   unsigned char *id;
1638   unsigned int id_len;
1639
1640   SILC_LOG_DEBUG(("Processing New Channel"));
1641
1642   if (sock->type == SILC_SOCKET_TYPE_CLIENT ||
1643       packet->src_id_type != SILC_ID_SERVER ||
1644       server->server_type == SILC_SERVER)
1645     return;
1646
1647   /* Parse the channel payload */
1648   payload = silc_channel_payload_parse(packet->buffer);
1649   if (!payload)
1650     return;
1651     
1652   /* Get the channel ID */
1653   channel_id = silc_channel_get_id_parse(payload);
1654   if (!channel_id) {
1655     silc_channel_payload_free(payload);
1656     return;
1657   }
1658
1659   channel_name = silc_channel_get_name(payload, &name_len);
1660   if (name_len > 256)
1661     channel_name[255] = '\0';
1662
1663   id = silc_channel_get_id(payload, &id_len);
1664
1665   if (sock->type == SILC_SOCKET_TYPE_ROUTER) {
1666     /* Add the server to global list as it is coming from router. It 
1667        cannot be our own channel as it is coming from router. */
1668
1669     SILC_LOG_DEBUG(("New channel id(%s) from [Router] %s",
1670                     silc_id_render(channel_id, SILC_ID_CHANNEL), 
1671                     sock->hostname));
1672     
1673     silc_idlist_add_channel(server->global_list, strdup(channel_name), 
1674                             0, channel_id, server->router->connection, 
1675                             NULL, NULL);
1676
1677     server->stat.channels++;
1678   } else {
1679     /* The channel is coming from our server, thus it is in our cell
1680        we will add it to our local list. */
1681     SilcChannelEntry channel;
1682     SilcBuffer chk;
1683
1684     SILC_LOG_DEBUG(("New channel id(%s) from [Server] %s",
1685                     silc_id_render(channel_id, SILC_ID_CHANNEL), 
1686                     sock->hostname));
1687     
1688     /* Check that we don't already have this channel */
1689     channel = silc_idlist_find_channel_by_name(server->local_list, 
1690                                                channel_name, NULL);
1691     if (!channel)
1692       channel = silc_idlist_find_channel_by_name(server->global_list, 
1693                                                  channel_name, NULL);
1694
1695     /* If the channel does not exist, then create it. We create the channel
1696        with the channel ID provided by the server. This creates a new
1697        key to the channel as well that we will send to the server. */
1698     if (!channel) {
1699       channel = silc_server_create_new_channel_with_id(server, NULL, NULL,
1700                                                        channel_name,
1701                                                        channel_id, FALSE);
1702       if (!channel) {
1703         silc_channel_payload_free(payload);
1704         silc_free(channel_id);
1705         return;
1706       }
1707
1708       /* Send the new channel key to the server */
1709       chk = silc_channel_key_payload_encode(id_len, id,
1710                                             strlen(channel->channel_key->
1711                                                    cipher->name),
1712                                             channel->channel_key->cipher->name,
1713                                             channel->key_len / 8, 
1714                                             channel->key);
1715       silc_server_packet_send(server, sock, SILC_PACKET_CHANNEL_KEY, 0, 
1716                               chk->data, chk->len, FALSE);
1717       silc_buffer_free(chk);
1718
1719     } else {
1720       /* The channel exist by that name, check whether the ID's match.
1721          If they don't then we'll force the server to use the ID we have.
1722          We also create a new key for the channel. */
1723
1724       if (SILC_ID_CHANNEL_COMPARE(channel_id, channel->id)) {
1725         /* They don't match, send CHANNEL_CHANGE notify to the server to
1726            force the ID change. */
1727         SILC_LOG_DEBUG(("Forcing the server to change Channel ID"));
1728         silc_server_send_notify_channel_change(server, sock, FALSE, 
1729                                                channel_id,
1730                                                channel->id, 
1731                                                SILC_ID_CHANNEL_LEN);
1732       }
1733
1734       /* Create new key for the channel and send it to the server and
1735          everybody else possibly on the channel. */
1736
1737       silc_server_create_channel_key(server, channel, 0);
1738
1739       /* Send to the channel */
1740       silc_server_send_channel_key(server, sock, channel, FALSE);
1741
1742       /* Send to the server */
1743       chk = silc_channel_key_payload_encode(id_len, id,
1744                                             strlen(channel->channel_key->
1745                                                    cipher->name),
1746                                             channel->channel_key->cipher->name,
1747                                             channel->key_len / 8, 
1748                                             channel->key);
1749       silc_server_packet_send(server, sock, SILC_PACKET_CHANNEL_KEY, 0, 
1750                               chk->data, chk->len, FALSE);
1751       silc_buffer_free(chk);
1752       silc_free(channel_id);
1753
1754       /* Since the channel is coming from server and we also know about it
1755          then send the JOIN notify to the server so that it see's our
1756          users on the channel "joining" the channel. */
1757       /* XXX TODO **/
1758     }
1759   }
1760 }
1761
1762 /* Received New Channel List packet, list of New Channel List payloads inside
1763    one packet. Process the New Channel payloads one by one. */
1764
1765 void silc_server_new_channel_list(SilcServer server,
1766                                   SilcSocketConnection sock,
1767                                   SilcPacketContext *packet)
1768 {
1769   SilcPacketContext *new;
1770   SilcBuffer buffer;
1771   unsigned short len1, len2;
1772
1773   SILC_LOG_DEBUG(("Processing New Channel List"));
1774
1775   if (sock->type == SILC_SOCKET_TYPE_CLIENT ||
1776       packet->src_id_type != SILC_ID_SERVER ||
1777       server->server_type == SILC_SERVER)
1778     return;
1779
1780   /* If the sender of this packet is server and we are router we need to
1781      broadcast this packet to other routers in the network. Broadcast
1782      this list packet instead of multiple New Channel packets. */
1783   if (!server->standalone && server->server_type == SILC_ROUTER &&
1784       sock->type == SILC_SOCKET_TYPE_SERVER &&
1785       !(packet->flags & SILC_PACKET_FLAG_BROADCAST)) {
1786     SILC_LOG_DEBUG(("Broadcasting received New Channel List packet"));
1787     silc_server_packet_send(server, server->router->connection,
1788                             packet->type, 
1789                             packet->flags | SILC_PACKET_FLAG_BROADCAST,
1790                             packet->buffer->data, packet->buffer->len, FALSE);
1791   }
1792
1793   /* Make copy of the original packet context, except for the actual
1794      data buffer, which we will here now fetch from the original buffer. */
1795   new = silc_packet_context_alloc();
1796   new->type = SILC_PACKET_NEW_CHANNEL;
1797   new->flags = packet->flags;
1798   new->src_id = packet->src_id;
1799   new->src_id_len = packet->src_id_len;
1800   new->src_id_type = packet->src_id_type;
1801   new->dst_id = packet->dst_id;
1802   new->dst_id_len = packet->dst_id_len;
1803   new->dst_id_type = packet->dst_id_type;
1804
1805   buffer = silc_buffer_alloc(512);
1806   new->buffer = buffer;
1807
1808   while (packet->buffer->len) {
1809     SILC_GET16_MSB(len1, packet->buffer->data);
1810     if ((len1 > packet->buffer->len) ||
1811         (len1 > buffer->truelen))
1812       break;
1813
1814     SILC_GET16_MSB(len2, packet->buffer->data + 2 + len1);
1815     if ((len2 > packet->buffer->len) ||
1816         (len2 > buffer->truelen))
1817       break;
1818
1819     silc_buffer_pull_tail(buffer, 8 + len1 + len2);
1820     silc_buffer_put(buffer, packet->buffer->data, 8 + len1 + len2);
1821
1822     /* Process the New Channel */
1823     silc_server_new_channel(server, sock, new);
1824
1825     silc_buffer_push_tail(buffer, 8 + len1 + len2);
1826     silc_buffer_pull(packet->buffer, 8 + len1 + len2);
1827   }
1828
1829   silc_buffer_free(buffer);
1830   silc_free(new);
1831 }
1832
1833 /* Received key agreement packet. This packet is never for us. It is to
1834    the client in the packet's destination ID. Sending of this sort of packet
1835    equals sending private message, ie. it is sent point to point from
1836    one client to another. */
1837
1838 void silc_server_key_agreement(SilcServer server,
1839                                SilcSocketConnection sock,
1840                                SilcPacketContext *packet)
1841 {
1842   SilcSocketConnection dst_sock;
1843   SilcIDListData idata;
1844
1845   SILC_LOG_DEBUG(("Start"));
1846
1847   if (packet->src_id_type != SILC_ID_CLIENT ||
1848       packet->dst_id_type != SILC_ID_CLIENT)
1849     return;
1850
1851   if (!packet->dst_id)
1852     return;
1853
1854   /* Get the route to the client */
1855   dst_sock = silc_server_get_client_route(server, packet->dst_id,
1856                                           packet->dst_id_len, NULL, &idata);
1857   if (!dst_sock)
1858     return;
1859
1860   /* Relay the packet */
1861   silc_server_relay_packet(server, dst_sock, idata->send_key,
1862                            idata->hmac, packet, FALSE);
1863 }