📄 irc-event-2.c
字号:
cfg->host, ERR_UNKNOWNMODE, client->nick, *req); break; } req++; } } /* is target nick ? */ else if ((cl = irc_find_nick (cfg, nick)) != NULL) { /* get and set user flag only by itself ! */ if (cl != client) { irc_printf (sock, ":%s %03d %s " ERR_USERSDONTMATCH_TEXT "\n", cfg->host, ERR_USERSDONTMATCH, client->nick); return 0; } /* this is a request only ? */ if (request->paras < 2) { irc_printf (sock, ":%s %03d %s %s %s\n", cfg->host, RPL_UMODEIS, client->nick, client->nick, irc_client_flag_string (client)); return 0; } /* go through all the Mode string */ req = request->para[1]; flag = FLAG_SET; while (*req) { switch (*req) { case '+': flag = FLAG_SET; break; case '-': flag = FLAG_UNSET; break; /* invisible flag */ case 'i': irc_user_flag (client, sock, UMODE_INVISIBLE, flag); break; /* get server Messages */ case 's': irc_user_flag (client, sock, UMODE_SERVER, flag); break; /* get operator Messages */ case 'w': irc_user_flag (client, sock, UMODE_WALLOP, flag); break; /* just deop yourself ! */ case 'o': irc_user_flag (client, sock, UMODE_OPERATOR, flag); break; /* unknown Mode flag */ default: irc_printf (sock, ":%s %03d %s " ERR_UNKNOWNMODE_TEXT "\n", cfg->host, ERR_UNKNOWNMODE, client->nick, *req); break; } req++; } } return 0;}/* * Command: TOPIC * Parameters: <channel> [<topic>] * Numeric Replies: ERR_NEEDMOREPARAMS ERR_NOTONCHANNEL * RPL_NOTOPIC RPL_TOPIC * ERR_CHANOPRIVSNEEDED */intirc_topic_callback (svz_socket_t *sock, irc_client_t *client, irc_request_t *request){ irc_config_t *cfg = sock->cfg; irc_client_t *cl; irc_channel_t *channel; svz_socket_t *xsock; int n, i; /* enough paras ? */ if (irc_check_args (sock, client, cfg, request, 1)) return 0; /* get the channel target */ if ((channel = irc_find_channel (cfg, request->target[0].channel)) != NULL) { if ((n = irc_client_in_channel (sock, client, channel)) != -1) { /* just send TOPIC back */ if (request->paras < 2) { irc_channel_topic (sock, client, channel); } /* check if client can set the TOPIC */ else { if ((channel->flag & MODE_TOPIC) && !irc_client_oper (sock, client, channel, channel->cflag[n])) return 0; /* change the topic */ if (channel->topic) svz_free (channel->topic); channel->topic = svz_strdup (request->para[1]); if (channel->topic_by) svz_free (channel->topic_by); channel->topic_by = svz_strdup (client->nick); channel->topic_since = time (NULL); /* send topic to all clients in channel */ for (i = 0; i < channel->clients; i++) { cl = channel->client[i]; xsock = cl->sock; irc_printf (xsock, ":%s!%s@%s TOPIC %s :%s\n", client->nick, client->user, client->host, channel->name, channel->topic); } } } } return 0;}/* * Command: NAMES * Parameters: [<channel>{,<channel>}] * Numerics: RPL_NAMREPLY RPL_ENDOFNAMES */intirc_names_callback (svz_socket_t *sock, irc_client_t *client, irc_request_t *request){ irc_config_t *cfg = sock->cfg; irc_client_t **cl; irc_channel_t **ch; irc_channel_t *channel; static char text[MAX_MSG_LEN]; int n, i; /* list all channels and users ? */ if (request->paras < 1) { /* go through all channels */ if ((ch = (irc_channel_t **) svz_hash_values (cfg->channels)) != NULL) { for (n = 0; n < svz_hash_size (cfg->channels); n++) { /* * you can't see secret and private channels, * except you are in it */ if (irc_client_in_channel (NULL, client, ch[n]) == -1 && (ch[n]->flag & (MODE_SECRET | MODE_PRIVATE))) continue; /* send a line */ irc_channel_users (sock, client, ch[n]); } svz_hash_xfree (ch); } /* * List all users not being in channels at all, * being visible, and are not in public channels. * Public channels are not secret or private or channels * clients share. */ if ((cl = (irc_client_t **) svz_hash_values (cfg->clients)) != NULL) { for (n = 0; n < svz_hash_size (cfg->clients); n++) { text[0] = 0; /* visible ? */ if (!(cl[n]->flag & UMODE_INVISIBLE)) { /* go through all channels of the client */ for (i = 0; i < cl[n]->channels; i++) { channel = cl[n]->channel[i]; /* is it public or a shared channel ? */ if (!(channel->flag & (MODE_SECRET | MODE_PRIVATE)) || irc_client_in_channel (NULL, client, channel) != -1) break; } /* is the client in no channel or in no shared or public ? */ if (n == cl[n]->channels) { if (cl[n]->flag & UMODE_OPERATOR) strcat (text, "@"); strcat (text, cl[n]->nick); strcat (text, " "); } } } svz_hash_xfree (cl); } /* send the (*) reply */ irc_printf (sock, ":%s %03d %s " RPL_NAMREPLY_TEXT "\n", cfg->host, RPL_NAMREPLY, client->nick, '*', "*", text); /* send end of list */ irc_printf (sock, ":%s %03d %s " RPL_ENDOFNAMES_TEXT "\n", cfg->host, RPL_ENDOFNAMES, client->nick, ""); } /* list only specified channels */ else { for (n = 0; n < request->targets; n++) { if ((channel = irc_find_channel (cfg, request->target[n].channel)) != NULL) { if (irc_client_in_channel (NULL, client, channel) == -1 && (channel->flag & (MODE_SECRET | MODE_PRIVATE))) continue; irc_channel_users (sock, client, channel); } irc_printf (sock, ":%s %03d %s " RPL_ENDOFNAMES_TEXT "\n", cfg->host, RPL_ENDOFNAMES, client->nick, channel->name); } } return 0;}/* * Send a part of a channel list. */static voidirc_channel_list (svz_socket_t *sock, irc_client_t *client, irc_channel_t *channel){ irc_config_t *cfg = sock->cfg; irc_client_t *cl; int n; int visibles; /* hide secret channels */ if (channel->flag & MODE_SECRET) return; /* hide private channels you're not in */ if (channel->flag & MODE_PRIVATE && irc_client_in_channel (NULL, client, channel) == -1) return; /* count visible clients in the channel */ for (visibles = 0, n = 0; n < channel->clients; n++) { cl = channel->client[n]; if (!(cl->flag & UMODE_INVISIBLE)) visibles++; } /* send channel info */ irc_printf (sock, ":%s %03d %s %s" RPL_LIST_TEXT "\n", cfg->host, RPL_LIST, client->nick, channel->flag & MODE_PRIVATE ? "* " : "", channel->name, visibles, channel->topic);}/* * Command: LIST * Parameters: [<channel>{,<channel>} [<server>]] * Numeric Replies: ERR_NOSUCHSERVER RPL_LISTSTART * RPL_LIST RPL_LISTEND */intirc_list_callback (svz_socket_t *sock, irc_client_t *client, irc_request_t *request){ irc_config_t *cfg = sock->cfg; irc_channel_t **ch; irc_channel_t *channel; int n; irc_printf (sock, ":%s %03d %s " RPL_LISTSTART_TEXT "\n", cfg->host, RPL_LISTSTART, client->nick); /* list all channels */ if (request->paras < 1) { if ((ch = (irc_channel_t **) svz_hash_values (cfg->channels)) != NULL) { for (n = 0; n < svz_hash_size (cfg->channels); n++) { irc_channel_list (sock, client, ch[n]); } svz_hash_xfree (ch); } } /* list specified channels */ else { for (n = 0; n < request->targets; n++) { if ((channel = irc_find_channel (cfg, request->target[n].channel)) != NULL) { irc_channel_list (sock, client, channel); } } } irc_printf (sock, ":%s %03d " RPL_LISTEND_TEXT "\n", cfg->host, RPL_LISTEND); return 0;}/* * Command: INVITE * Parameters: <nickname> <channel> * Numeric Replies: ERR_NEEDMOREPARAMS ERR_NOSUCHNICK * ERR_NOTONCHANNEL ERR_USERONCHANNEL * ERR_CHANOPRIVSNEEDED * RPL_INVITING RPL_AWAY */intirc_invite_callback (svz_socket_t *sock, irc_client_t *client, irc_request_t *request){ irc_config_t *cfg = sock->cfg; irc_client_t *cl; irc_channel_t *ch; svz_socket_t *xsock; char *nick, *channel; int n, i; /* enough paras ? */ if (irc_check_args (sock, client, cfg, request, 2)) return 0; nick = request->para[0]; channel = request->para[1]; /* does the nick exist ? */ if ((cl = irc_find_nick (cfg, nick)) == NULL) { irc_printf (sock, ":%s %03d %s " ERR_NOSUCHNICK_TEXT "\n", cfg->host, ERR_NOSUCHNICK, client->nick, nick); return 0; } /* does the channel exist ? */ if ((ch = irc_find_channel (cfg, channel)) == NULL) { irc_printf (sock, ":%s %03d %s " ERR_NOSUCHNICK_TEXT "\n", cfg->host, ERR_NOSUCHNICK, client->nick, channel); return 0; } /* is the inviter in channel ? */ if ((n = irc_client_in_channel (sock, client, ch)) == -1) return 0; /* is the user already in channel ? */ if ((i = irc_client_in_channel (NULL, cl, ch)) != -1) { irc_printf (sock, ":%s %03d %s " ERR_USERONCHANNEL_TEXT "\n", cfg->host, ERR_USERONCHANNEL, client->nick, nick, channel); return 0; } /* are you operator in this channel / can you invite ? */ if (!irc_client_oper (sock, client, ch, ch->cflag[n])) return 0; /* is this client away ? */ if (irc_client_absent (cl, client)) return 0; /* send the invite Message */ xsock = cl->sock; irc_printf (xsock, ":%s!%s@%s INVITE %s " RPL_INVITING_TEXT "\n", client->nick, client->user, client->host, cl->nick, ch->name, cl->nick); /* fill in the invited client into the channels invite array */ n = ch->invites; ch->invite = svz_realloc (ch->invite, sizeof (irc_client_t *) * (n + 1)); ch->invite[n] = cl; ch->invites++; return 0;}/* * Command: KICK * Parameters: <channel> <user> [<comment>] * Numeric Replies: ERR_NEEDMOREPARAMS ERR_NOSUCHCHANNEL * ERR_BADCHANMASK ERR_CHANOPRIVSNEEDED * ERR_NOTONCHANNEL */intirc_kick_callback (svz_socket_t *sock, irc_client_t *client, irc_request_t *request){ irc_config_t *cfg = sock->cfg; irc_client_t *cl; irc_client_t *victim; irc_channel_t *channel; svz_socket_t *xsock; int i, n; /* enough paras ? */ if (irc_check_args (sock, client, cfg, request, 2)) return 0; /* go through all targets (channels) */ for (n = 0; n < request->targets; n++) { /* does the requested channel exist ? */ if ((channel = irc_find_channel (cfg, request->target[n].channel)) == NULL) { irc_printf (sock, ":%s %03d %s " ERR_NOSUCHCHANNEL_TEXT "\n", cfg->host, ERR_NOSUCHCHANNEL, client->nick, request->target[n].channel); continue; } /* yes there is such a channel, are you in it ? */ if ((i = irc_client_in_channel (sock, client, channel)) == -1) continue; /* are you a channel operator ? */ if (!irc_client_oper (sock, client, channel, channel->cflag[i])) continue; /* kick the requested user */ if ((victim = irc_find_nick (cfg, irc_get_target (request->para[1], n))) == NULL) continue; /* is the victim in this channel ? */ if (irc_client_in_channel (NULL, victim, channel) == -1) continue; /* tell all other clients about the kick */ for (i = 0; i < channel->clients; i++) { cl = channel->client[i]; xsock = cl->sock; irc_printf (xsock, ":%s!%s@%s KICK %s %s :%s\n", client->nick, client->user, client->host, channel->name, victim->nick, request->para[2]); } irc_leave_channel (cfg, victim, channel); } return 0;}#else /* not ENABLE_IRC_PROTO */int irc_event_2_dummy; /* Shut up compiler warnings. */#endif /* not ENABLE_IRC_PROTO */
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -