/* * ms_wallops (write to *all* opers currently online) * parv[1] = message text */ static int ms_wallops(struct Client *client_p, struct Client *source_p, int parc, const char *parv[]) { if (IsClient(source_p)) sendto_wallops_flags(UMODE_OPERWALL, source_p, "OPERWALL - %s", parv[1]); else sendto_wallops_flags(UMODE_WALLOP, source_p, "%s", parv[1]); sendto_server(client_p, NULL, CAP_TS6, NOCAPS, ":%s WALLOPS :%s", use_id(source_p), parv[1]); sendto_server(client_p, NULL, NOCAPS, CAP_TS6, ":%s WALLOPS :%s", source_p->name, parv[1]); return 0; }
/* * ms_wallops (write to *all* opers currently online) * parv[1] = message text */ static int ms_wallops(struct Client *client_p, struct Client *source_p, int parc, const char *parv[]) { const char *prefix = ""; if (MyClient(source_p) && !IsOperMassNotice(source_p)) { sendto_one(source_p, form_str(ERR_NOPRIVS), me.name, source_p->name, "mass_notice"); return 0; } if (IsPerson(source_p)) { if (!strncmp(parv[1], "OPERWALL - ", 11) || !strncmp(parv[1], "LOCOPS - ", 9) || !strncmp(parv[1], "SLOCOPS - ", 10) || !strncmp(parv[1], "ADMINWALL - ", 12)) prefix = "WALLOPS - "; } sendto_wallops_flags(UMODE_WALLOP, source_p, "%s%s", prefix, parv[1]); sendto_server(client_p, NULL, CAP_TS6, NOCAPS, ":%s WALLOPS :%s", use_id(source_p), parv[1]); return 0; }
/* * mo_wallops (write to *all* opers currently online) * parv[0] = sender prefix * parv[1] = message text */ static void mo_wallops(struct Client *client_p, struct Client *source_p, int parc, char *parv[]) { const char *message = parv[1]; if (!HasOFlag(source_p, OPER_FLAG_WALLOPS)) { sendto_one(source_p, form_str(ERR_NOPRIVS), me.name, source_p->name, "wallops"); return; } if (EmptyString(message)) { sendto_one(source_p, form_str(ERR_NEEDMOREPARAMS), me.name, source_p->name, "WALLOPS"); return; } sendto_wallops_flags(UMODE_OPERWALL, source_p, "OPERWALL - %s", message); sendto_server(NULL, CAP_TS6, NOCAPS, ":%s WALLOPS :%s", ID(source_p), message); sendto_server(NULL, NOCAPS, CAP_TS6, ":%s WALLOPS :%s", source_p->name, message); }
/* * mo_operwall - OPERWALL message handler * (write to *all* local opers currently online) * parv[0] = sender prefix * parv[1] = message text */ static void mo_operwall(struct Client *client_p, struct Client *source_p, int parc, char *parv[]) { const char *message = parv[1]; if (!IsOperWall(source_p)) { sendto_one(source_p, form_str(ERR_NOPRIVS), me.name, source_p->name, "operwall"); return; } if (EmptyString(message)) { sendto_one(source_p, form_str(ERR_NEEDMOREPARAMS), me.name, source_p->name, "OPERWALL"); return; } sendto_server(NULL, source_p, NULL, CAP_TS6, NOCAPS, LL_ICLIENT, ":%s OPERWALL :%s", ID(source_p), message); sendto_server(NULL, source_p, NULL, NOCAPS, CAP_TS6, LL_ICLIENT, ":%s OPERWALL :%s", source_p->name, message); sendto_wallops_flags(UMODE_OPERWALL, source_p, "OPERWALL - %s", message); }
/* * ms_wallops (write to *all* opers currently online) * parv[0] = sender prefix * parv[1] = message text */ static void ms_wallops(struct Client *client_p, struct Client *source_p, int parc, char *parv[]) { const char *message = parv[1]; if(EmptyString(message)) return; if(IsClient(source_p)) sendto_wallops_flags(UMODE_OPERWALL, source_p, "OPERWALL - %s", message); else sendto_wallops_flags(UMODE_WALLOP, source_p, "%s", message); sendto_server(client_p, source_p, NULL, CAP_TS6, NOCAPS, LL_ICLIENT, ":%s WALLOPS :%s", ID(source_p), message); sendto_server(client_p, source_p, NULL, NOCAPS, CAP_TS6, LL_ICLIENT, ":%s WALLOPS :%s", source_p->name, message); }
/* * ms_operwall - OPERWALL message handler * (write to *all* local opers currently online) * parv[1] = message text */ static int ms_operwall(struct Client *client_p, struct Client *source_p, int parc, const char *parv[]) { sendto_server(client_p, NULL, CAP_TS6, NOCAPS, ":%s OPERWALL :%s", use_id(source_p), parv[1]); sendto_wallops_flags(UMODE_OPERWALL, source_p, "OPERWALL - %s", parv[1]); return 0; }
/* * m_locops - LOCOPS message handler * (write to *all* local opers currently online) * parv[0] = sender prefix * parv[1] = message text */ static int m_locops(struct Client *client_p, struct Client *source_p, int parc, const char *parv[]) { sendto_wallops_flags(UMODE_LOCOPS, source_p, "LOCOPS - %s", parv[1]); if(rb_dlink_list_length(&cluster_conf_list) > 0) cluster_generic(source_p, "LOCOPS", SHARED_LOCOPS, ":%s", parv[1]); return 0; }
/* * me_operwall - OPERWALL message handler * (write to *all* local opers currently online) * parv[0] = sender prefix * parv[1] = message text * * Lets ms_encap handle propagation. */ static void me_operwall(struct Client *client_p, struct Client *source_p, int parc, char *parv[]) { const char *message = parv[1]; if (EmptyString(message)) return; sendto_wallops_flags(UMODE_OPERWALL, source_p, "OPERWALL - %s", message); }
/* * ms_wallops (write to *all* opers currently online) * parv[0] = sender prefix * parv[1] = message text */ static void ms_wallops(struct Client *client_p, struct Client *source_p, int parc, char *parv[]) { char *message; message = parv[1]; if(EmptyString(message)) { sendto_one(source_p, form_str(ERR_NEEDMOREPARAMS), me.name, parv[0], "WALLOPS"); return; } if(IsClient(source_p)) sendto_wallops_flags(UMODE_OPERWALL, source_p, "OPERWALL - %s", message); else sendto_wallops_flags(UMODE_WALLOP, source_p, "%s", message); sendto_server(client_p, NULL, NOCAPS, NOCAPS, ":%s WALLOPS :%s", parv[0], message); }
static int me_locops(struct Client *client_p, struct Client *source_p, int parc, const char *parv[]) { if(!IsClient(source_p)) return 0; if(find_shared_conf("*", "*", source_p->servptr->name, SHARED_LOCOPS)) sendto_wallops_flags(UMODE_LOCOPS, source_p, "SLOCOPS - %s", parv[1]); return 0; }
static int mo_adminwall(struct Client *client_p, struct Client *source_p, int parc, const char *parv[]) { if(!IsAdmin(source_p)) { sendto_one_numeric(source_p, s_RPL(ERR_NOPRIVS), "adminwall"); return 0; } sendto_wallops_flags(UMODE_ADMIN, source_p, "ADMINWALL - %s", parv[1]); sendto_match_servs(source_p, "*", CAP_ENCAP, NOCAPS, "ENCAP * ADMINWALL :%s", parv[1]); return 0; }
/* * ms_operwall - OPERWALL message handler * (write to *all* local opers currently online) * parv[0] = sender prefix * parv[1] = message text */ static void ms_operwall(struct Client *client_p, struct Client *source_p, int parc, char *parv[]) { const char *message = parv[1]; if (EmptyString(message)) return; sendto_server(client_p, source_p, NULL, NOCAPS, NOCAPS, LL_ICLIENT, ":%s OPERWALL :%s", parv[0], message); sendto_wallops_flags(UMODE_OPERWALL, source_p, "OPERWALL - %s", message); }
/*! \brief WALLOPS command handler * * \param source_p Pointer to allocated Client struct from which the message * originally comes from. This can be a local or remote client. * \param parc Integer holding the number of supplied arguments. * \param parv Argument vector where parv[0] .. parv[parc-1] are non-NULL * pointers. * \note Valid arguments for this command are: * - parv[0] = command * - parv[1] = message text */ static int ms_wallops(struct Client *source_p, int parc, char *parv[]) { const char *const message = parv[1]; if (EmptyString(message)) return 0; sendto_wallops_flags(UMODE_WALLOP, source_p, "%s", message); sendto_server(source_p, 0, 0, ":%s WALLOPS :%s", source_p->id, message); return 0; }
/* * ms_operwall - OPERWALL message handler * (write to *all* local opers currently online) * parv[0] = sender prefix * parv[1] = message text */ static void ms_operwall(struct Client *client_p, struct Client *source_p, int parc, char *parv[]) { const char *message = parv[1]; if (EmptyString(message)) return; sendto_server(client_p, CAP_TS6, NOCAPS, ":%s OPERWALL :%s", ID(source_p), message); sendto_server(client_p, NOCAPS, CAP_TS6, ":%s OPERWALL :%s", source_p->name, message); sendto_wallops_flags(UMODE_OPERWALL, source_p, "OPERWALL - %s", message); }
/* * m_locops - LOCOPS message handler * (write to *all* local opers currently online) * parv[0] = sender prefix * parv[1] = message text */ static void m_locops(struct Client *client_p, struct Client *source_p, int parc, char *parv[]) { if(EmptyString(parv[1])) { sendto_one(source_p, form_str(ERR_NEEDMOREPARAMS), me.name, parv[0], "LOCOPS"); return; } sendto_wallops_flags(UMODE_LOCOPS, source_p, "LOCOPS - %s", parv[1]); if(dlink_list_length(&cluster_list) > 0) cluster_generic(source_p, "LOCOPS", CLUSTER_LOCOPS, CAP_CLUSTER, ":%s", parv[1]); }
/* * mo_operwall (write to *all* opers currently online) * parv[1] = message text */ static int mo_operwall(struct Client *client_p, struct Client *source_p, int parc, const char *parv[]) { if(!IsOperOperwall(source_p)) { sendto_one(source_p, form_str(ERR_NOPRIVS), me.name, source_p->name, "operwall"); return 0; } sendto_wallops_flags(UMODE_OPERWALL, source_p, "OPERWALL - %s", parv[1]); sendto_server(client_p, NULL, CAP_TS6, NOCAPS, ":%s OPERWALL :%s", use_id(source_p), parv[1]); return 0; }
static void ms_operwall(struct Client *client_p, struct Client *source_p, int parc, char *parv[]) { char *message = parv[1]; if (EmptyString(message)) { if (MyClient(source_p)) sendto_one(source_p, form_str(ERR_NEEDMOREPARAMS), me.name, parv[0], "OPERWALL"); return; } sendto_server(client_p, NULL, NOCAPS, NOCAPS, ":%s OPERWALL :%s", parv[0], message); sendto_wallops_flags(UMODE_OPERWALL, source_p, "OPERWALL - %s", message); }
static int ms_locops(struct Client *client_p, struct Client *source_p, int parc, const char *parv[]) { /* source_p parv[1] parv[2] * oper target serv message */ propagate_generic(source_p, "LOCOPS", parv[1], CAP_CLUSTER, ":%s", parv[2]); if(!match(parv[1], me.name)) return 0; if(find_shared_conf("*", "*", source_p->servptr->name, SHARED_LOCOPS)) sendto_wallops_flags(UMODE_LOCOPS, source_p, "SLOCOPS - %s", parv[2]); return 0; }
static void ms_locops(struct Client *client_p, struct Client *source_p, int parc, char *parv[]) { if(parc != 3 || EmptyString(parv[2])) return; /* parv[0] parv[1] parv[2] * oper target serv message */ sendto_match_servs(source_p, parv[1], CAP_CLUSTER, NOCAPS, "LOCOPS %s :%s", parv[1], parv[2]); if(!match(parv[1], me.name)) return; if(!IsPerson(source_p)) return; if(find_cluster(source_p->user->server, CLUSTER_LOCOPS)) sendto_wallops_flags(UMODE_LOCOPS, source_p, "SLOCOPS - %s", parv[2]); }
static void mo_operwall(struct Client *client_p, struct Client *source_p, int parc, char *parv[]) { char *message = parv[1]; if(!IsOperOperwall(source_p)) { sendto_one(source_p, ":%s NOTICE %s :You need operwall = yes;", me.name, source_p->name); return; } if (EmptyString(message)) { sendto_one(source_p, form_str(ERR_NEEDMOREPARAMS), me.name, parv[0], "OPERWALL"); return; } sendto_server(NULL, NULL, NOCAPS, NOCAPS, ":%s OPERWALL :%s", parv[0], message); sendto_wallops_flags(UMODE_OPERWALL, source_p, "OPERWALL - %s", message); }
/* * ms_wallops (write to *all* opers currently online) * parv[1] = message text */ static int ms_wallops(struct Client *client_p, struct Client *source_p, int parc, const char *parv[]) { const char *prefix = ""; if (IsPerson(source_p)) { if (!strncmp(parv[1], "OPERWALL - ", 11) || !strncmp(parv[1], "LOCOPS - ", 9) || !strncmp(parv[1], "SLOCOPS - ", 10)) prefix = "WALLOPS - "; } sendto_wallops_flags(UMODE_WALLOP, source_p, "%s%s", prefix, parv[1]); sendto_server(client_p, NULL, CAP_TS6, NOCAPS, ":%s WALLOPS :%s", use_id(source_p), parv[1]); sendto_server(client_p, NULL, NOCAPS, CAP_TS6, ":%s WALLOPS :%s", source_p->name, parv[1]); return 0; }
/*! \brief WALLOPS command handler * * \param source_p Pointer to allocated Client struct from which the message * originally comes from. This can be a local or remote client. * \param parc Integer holding the number of supplied arguments. * \param parv Argument vector where parv[0] .. parv[parc-1] are non-NULL * pointers. * \note Valid arguments for this command are: * - parv[0] = command * - parv[1] = message text */ static int mo_wallops(struct Client *source_p, int parc, char *parv[]) { const char *const message = parv[1]; if (!HasOFlag(source_p, OPER_FLAG_WALLOPS)) { sendto_one_numeric(source_p, &me, ERR_NOPRIVS, "wallops"); return 0; } if (EmptyString(message)) { sendto_one_numeric(source_p, &me, ERR_NEEDMOREPARAMS, "WALLOPS"); return 0; } sendto_wallops_flags(UMODE_WALLOP, source_p, "%s", message); sendto_server(source_p, 0, 0, ":%s WALLOPS :%s", source_p->id, message); return 0; }
/* * mo_omode - MODE command handler * parv[1] - channel */ static int mo_omode(struct Client *client_p, struct Client *source_p, int parc, const char *parv[]) { struct Channel *chptr = NULL; struct membership *msptr; char params[512]; int i; int wasonchannel; /* admins only */ if (!IsOperAdmin(source_p)) { sendto_one(source_p, form_str(ERR_NOPRIVS), me.name, source_p->name, "admin"); return 0; } /* Now, try to find the channel in question */ if (!IsChanPrefix(parv[1][0]) || !check_channel_name(parv[1])) { sendto_one_numeric(source_p, ERR_BADCHANNAME, form_str(ERR_BADCHANNAME), parv[1]); return 0; } chptr = find_channel(parv[1]); if (chptr == NULL) { sendto_one_numeric(source_p, ERR_NOSUCHCHANNEL, form_str(ERR_NOSUCHCHANNEL), parv[1]); return 0; } /* Now know the channel exists */ msptr = find_channel_membership(chptr, source_p); wasonchannel = msptr != NULL; if (is_any_op(msptr)) { sendto_one_notice(source_p, ":Use a normal MODE you idiot"); return 0; } params[0] = '\0'; for (i = 2; i < parc; i++) { if (i != 2) rb_strlcat(params, " ", sizeof params); rb_strlcat(params, parv[i], sizeof params); } sendto_wallops_flags(UMODE_WALLOP, &me, "OMODE called for [%s] [%s] by %s!%s@%s", parv[1], params, source_p->name, source_p->username, source_p->host); ilog(L_MAIN, "OMODE called for [%s] [%s] by %s", parv[1], params, get_oper_name(source_p)); if (*chptr->chname != '&') sendto_server(NULL, NULL, NOCAPS, NOCAPS, ":%s WALLOPS :OMODE called for [%s] [%s] by %s!%s@%s", me.name, parv[1], params, source_p->name, source_p->username, source_p->host); #if 0 set_channel_mode(client_p, source_p->servptr, chptr, msptr, parc - 2, parv + 2); #else if (parc == 4 && !strcmp(parv[2], "+y") && !irccmp(parv[3], source_p->name)) { /* Ownering themselves */ if (!wasonchannel) { sendto_one_numeric(source_p, ERR_USERNOTINCHANNEL, form_str(ERR_USERNOTINCHANNEL), parv[3], chptr->chname); return 0; } sendto_channel_local(ALL_MEMBERS, chptr, ":%s MODE %s +y %s", me.name, parv[1], source_p->name); sendto_server(NULL, chptr, CAP_TS6, NOCAPS, ":%s TMODE %ld %s +y %s", me.id, (long) chptr->channelts, parv[1], source_p->id); msptr->flags |= CHFL_OWNER; } else if (parc == 4 && !strcmp(parv[2], "+a") && !irccmp(parv[3], source_p->name)) { /* Admining themselves */ if (!wasonchannel) { sendto_one_numeric(source_p, ERR_USERNOTINCHANNEL, form_str(ERR_USERNOTINCHANNEL), parv[3], chptr->chname); return 0; } sendto_channel_local(ALL_MEMBERS, chptr, ":%s MODE %s +a %s", me.name, parv[1], source_p->name); sendto_server(NULL, chptr, CAP_TS6, NOCAPS, ":%s TMODE %ld %s +a %s", me.id, (long) chptr->channelts, parv[1], source_p->id); msptr->flags |= CHFL_ADMIN; } else if (parc == 4 && !strcmp(parv[2], "+o") && !irccmp(parv[3], source_p->name)) { /* Opping themselves */ if (!wasonchannel) { sendto_one_numeric(source_p, ERR_USERNOTINCHANNEL, form_str(ERR_USERNOTINCHANNEL), parv[3], chptr->chname); return 0; } sendto_channel_local(ALL_MEMBERS, chptr, ":%s MODE %s +o %s", me.name, parv[1], source_p->name); sendto_server(NULL, chptr, CAP_TS6, NOCAPS, ":%s TMODE %ld %s +o %s", me.id, (long) chptr->channelts, parv[1], source_p->id); msptr->flags |= CHFL_CHANOP; } else if (parc == 4 && !strcmp(parv[2], "+h") && !irccmp(parv[3], source_p->name)) { /* Halfopping themselves */ if (!wasonchannel) { sendto_one_numeric(source_p, ERR_USERNOTINCHANNEL, form_str(ERR_USERNOTINCHANNEL), parv[3], chptr->chname); return 0; } sendto_channel_local(ALL_MEMBERS, chptr, ":%s MODE %s +h %s", me.name, parv[1], source_p->name); sendto_server(NULL, chptr, CAP_TS6, NOCAPS, ":%s TMODE %ld %s +h %s", me.id, (long) chptr->channelts, parv[1], source_p->id); msptr->flags |= CHFL_HALFOP; } else if (ConfigChannel.use_owner) { /* I hope this is correct. * -- Kabaka */ /* Hack it so set_channel_mode() will accept */ if (wasonchannel) msptr->flags |= CHFL_OWNER; else { add_user_to_channel(chptr, source_p, CHFL_CHANOP); msptr = find_channel_membership(chptr, source_p); } set_channel_mode(client_p, source_p, chptr, msptr, parc - 2, parv + 2); if (wasonchannel) msptr->flags &= ~CHFL_OWNER; else remove_user_from_channel(msptr); } else if (ConfigChannel.use_admin) { /* Hack it so set_channel_mode() will accept */ if (wasonchannel) msptr->flags |= CHFL_ADMIN; else { add_user_to_channel(chptr, source_p, CHFL_CHANOP); msptr = find_channel_membership(chptr, source_p); } set_channel_mode(client_p, source_p, chptr, msptr, parc - 2, parv + 2); /* We know they were not opped before and they can't have opped * themselves as set_channel_mode() does not allow that * -- jilles */ if (wasonchannel) msptr->flags &= ~CHFL_ADMIN; else remove_user_from_channel(msptr); } else { /* CHFL_ADMIN is only useful if admin is enabled * so hack it with op if it is not. */ if (wasonchannel) msptr->flags |= CHFL_CHANOP; else { add_user_to_channel(chptr, source_p, CHFL_CHANOP); msptr = find_channel_membership(chptr, source_p); } set_channel_mode(client_p, source_p, chptr, msptr, parc - 2, parv + 2); /* We know they were not opped before and they can't have opped * themselves as set_channel_mode() does not allow that * -- jilles */ if (wasonchannel) msptr->flags &= ~CHFL_CHANOP; else remove_user_from_channel(msptr); } #endif return 0; }
static int me_adminwall(struct Client *client_p, struct Client *source_p, int parc, const char *parv[]) { sendto_wallops_flags(UMODE_ADMIN, source_p, "ADMINWALL - %s", parv[1]); return 0; }
/* * m_topic * parv[1] = channel name * parv[2] = new topic, if setting topic */ static int m_topic(struct Client *client_p, struct Client *source_p, int parc, const char *parv[]) { struct Channel *chptr = NULL; struct membership *msptr; char *p = NULL; const char *name; int operspy = 0; if((p = strchr(parv[1], ','))) *p = '\0'; name = parv[1]; if(IsOperSpy(source_p) && parv[1][0] == '!') { name++; operspy = 1; if(EmptyString(name)) { sendto_one(source_p, form_str(ERR_NEEDMOREPARAMS), me.name, source_p->name, "TOPIC"); return 0; } } if(MyClient(source_p) && !IsFloodDone(source_p)) flood_endgrace(source_p); if(!IsChannelName(name)) { sendto_one_numeric(source_p, ERR_NOSUCHCHANNEL, form_str(ERR_NOSUCHCHANNEL), name); return 0; } chptr = find_channel(name); if(chptr == NULL) { sendto_one_numeric(source_p, ERR_NOSUCHCHANNEL, form_str(ERR_NOSUCHCHANNEL), name); return 0; } /* setting topic */ if(parc > 2) { char topic_info[USERHOST_REPLYLEN]; msptr = find_channel_membership(chptr, source_p); if(msptr == NULL) { sendto_one_numeric(source_p, ERR_NOTONCHANNEL, form_str(ERR_NOTONCHANNEL), name); return 0; } if(MyClient(source_p) && !is_chanop_voiced(msptr) && !IsOper(source_p) && !add_channel_target(source_p, chptr)) { sendto_one(source_p, form_str(ERR_TARGCHANGE), me.name, source_p->name, chptr->chname); return 0; } if(MyClient(source_p) && (chptr->mode.mode & MODE_TOPICLIMIT) && !is_any_op(msptr)) { if(IsOverride(source_p)) { sendto_wallops_flags(UMODE_WALLOP, &me, "%s is overriding TOPIC on [%s]", get_oper_name(source_p), chptr->chname); sendto_server(NULL, chptr, NOCAPS, NOCAPS, ":%s WALLOPS :%s is overriding TOPIC on [%s]", me.name, get_oper_name(source_p), chptr->chname); } else { sendto_one(source_p, form_str(ERR_CHANOPRIVSNEEDED), me.name, source_p->name, parv[1]); return 0; } } if(ConfigChannel.host_in_topic) sprintf(topic_info, "%s!%s@%s", source_p->name, source_p->username, source_p->host); else rb_strlcpy(topic_info, source_p->name, sizeof(topic_info)); set_channel_topic(chptr, parv[2], topic_info, rb_current_time()); sendto_server(client_p, chptr, CAP_TS6, NOCAPS, ":%s TOPIC %s :%s", use_id(source_p), chptr->chname, chptr->topic == NULL ? "" : chptr->topic); sendto_channel_local(ALL_MEMBERS, chptr, ":%s!%s@%s TOPIC %s :%s", source_p->name, source_p->username, source_p->host, chptr->chname, chptr->topic == NULL ? "" : chptr->topic); } else if(MyClient(source_p)) { if(operspy) report_operspy(source_p, "TOPIC", chptr->chname); if(!IsMember(source_p, chptr) && SecretChannel(chptr) && !operspy) { sendto_one_numeric(source_p, ERR_NOTONCHANNEL, form_str(ERR_NOTONCHANNEL), name); return 0; } if(chptr->topic == NULL) sendto_one(source_p, form_str(RPL_NOTOPIC), me.name, source_p->name, name); else { sendto_one(source_p, form_str(RPL_TOPIC), me.name, source_p->name, chptr->chname, chptr->topic); sendto_one(source_p, form_str(RPL_TOPICWHOTIME), me.name, source_p->name, chptr->chname, chptr->topic_info, chptr->topic_time); } } return 0; }
/* ** mo_clearchan ** parv[0] = sender prefix ** parv[1] = channel */ static void mo_clearchan(struct Client *client_p, struct Client *source_p, int parc, char *parv[]) { struct Channel *chptr, *root_chptr; int on_vchan = 0; /* admins only */ if (!IsOperAdmin(source_p)) { sendto_one(source_p, ":%s NOTICE %s :You have no A flag", me.name, parv[0]); return; } /* XXX - we might not have CBURSTed this channel if we are a lazylink * yet. */ chptr= hash_find_channel(parv[1]); root_chptr = chptr; #ifdef VCHANS if (chptr && parc > 2 && parv[2][0] == '!') { chptr = find_vchan(chptr, parv[2]); if (root_chptr != chptr) on_vchan++; } #endif if( chptr == NULL ) { sendto_one(source_p, form_str(source_p,ERR_NOSUCHCHANNEL), me.name, parv[0], parv[1]); return; } if(IsMember(source_p, chptr)) { sendto_one(source_p, ":%s NOTICE %s :*** Please part %s before using CLEARCHAN", me.name, source_p->name, parv[1]); return; } if (!on_vchan) { sendto_wallops_flags(FLAGS_WALLOP, &me, "CLEARCHAN called for [%s] by %s!%s@%s", parv[1], source_p->name, source_p->username, source_p->host); sendto_server(NULL, source_p, NULL, NOCAPS, NOCAPS, LL_ICLIENT, ":%s WALLOPS :CLEARCHAN called for [%s] by %s!%s@%s", me.name, parv[1], source_p->name, source_p->username, source_p->host); ilog(L_NOTICE, "CLEARCHAN called for [%s] by %s!%s@%s", parv[1], source_p->name, source_p->username, source_p->host); } else { sendto_wallops_flags(FLAGS_WALLOP, &me, "CLEARCHAN called for [%s %s] by %s!%s@%s", parv[1], parv[2], source_p->name, source_p->username, source_p->host); sendto_server(NULL, source_p, NULL, NOCAPS, NOCAPS, LL_ICLIENT, ":%s WALLOPS :CLEARCHAN called for [%s %s] by %s!%s@%s", me.name, parv[1], parv[2], source_p->name, source_p->username, source_p->host); ilog(L_NOTICE, "CLEARCHAN called for [%s %s] by %s!%s@%s", parv[1], parv[2], source_p->name, source_p->username, source_p->host); } /* Kill all the modes we have about the channel.. making everyone a peon */ remove_our_modes(0, chptr, root_chptr, source_p); /* SJOIN the user to give them ops, and lock the channel */ sendto_server(client_p, source_p, chptr, NOCAPS, NOCAPS, LL_ICLIENT, ":%s SJOIN %lu %s +ntsi :@%s", me.name, (unsigned long) (chptr->channelts - 1), chptr->chname, source_p->name); sendto_channel_local(ALL_MEMBERS, chptr, ":%s!%s@%s JOIN %s", source_p->name, source_p->username, source_p->host, root_chptr->chname); sendto_channel_local(ALL_MEMBERS, chptr, ":%s MODE %s +o %s", me.name, chptr->chname, source_p->name); add_user_to_channel(chptr, source_p, CHFL_CHANOP); /* Take the TS down by 1, so we don't see the channel taken over * again. */ if (chptr->channelts) chptr->channelts--; #ifdef VCHANS if (on_vchan) add_vchan_to_client_cache(source_p,root_chptr,chptr); #endif chptr->mode.mode = MODE_SECRET | MODE_TOPICLIMIT | MODE_INVITEONLY | MODE_NOPRIVMSGS; free_topic(chptr); chptr->mode.key[0] = 0; /* Kick the users out and join the oper */ kick_list(client_p, source_p, chptr, &chptr->peons, chptr->chname); }
/* ** m_kick ** parv[1] = channel ** parv[2] = client to kick ** parv[3] = kick comment */ static int m_kick(struct Client *client_p, struct Client *source_p, int parc, const char *parv[]) { struct membership *msptr; struct Client *who; struct Channel *chptr; int chasing = 0; char *comment; const char *name; char *p = NULL; char text[10]; const char *user; static char buf[BUFSIZE]; int is_override = 0; if(MyClient(source_p) && !IsFloodDone(source_p)) flood_endgrace(source_p); *buf = '\0'; if((p = strchr(parv[1], ','))) *p = '\0'; name = parv[1]; chptr = find_channel(name); if(chptr == NULL) { sendto_one_numeric(source_p, ERR_NOSUCHCHANNEL, form_str(ERR_NOSUCHCHANNEL), name); return 0; } user = parv[2]; /* strtoken(&p2, parv[2], ","); */ if(!(who = find_chasing(source_p, user, &chasing))) { return 0; } if(!IsServer(source_p)) { msptr = find_channel_membership(chptr, source_p); if((msptr == NULL) && MyConnect(source_p)) { sendto_one_numeric(source_p, ERR_NOTONCHANNEL, form_str(ERR_NOTONCHANNEL), name); return 0; } if(!can_kick_deop(msptr, find_channel_membership(chptr, who))) { if(MyConnect(source_p)) { if(IsOverride(source_p)) is_override = 1; else { sendto_one(source_p, ":%s 482 %s %s :You do not have the proper privileges to kick this user", me.name, source_p->name, name); return 0; } } /* If its a TS 0 channel, do it the old way */ else if(chptr->channelts == 0) { sendto_one(source_p, form_str(ERR_CHANOPRIVSNEEDED), get_id(&me, source_p), get_id(source_p, source_p), name); return 0; } } /* Its a user doing a kick, but is not showing as chanop locally * its also not a user ON -my- server, and the channel has a TS. * There are two cases we can get to this point then... * * 1) connect burst is happening, and for some reason a legit * op has sent a KICK, but the SJOIN hasn't happened yet or * been seen. (who knows.. due to lag...) * * 2) The channel is desynced. That can STILL happen with TS * * Now, the old code roger wrote, would allow the KICK to * go through. Thats quite legit, but lets weird things like * KICKS by users who appear not to be chanopped happen, * or even neater, they appear not to be on the channel. * This fits every definition of a desync, doesn't it? ;-) * So I will allow the KICK, otherwise, things are MUCH worse. * But I will warn it as a possible desync. * * -Dianora */ } if((p = strchr(parv[2], ','))) *p = '\0'; msptr = find_channel_membership(chptr, who); if(msptr != NULL) { if(MyClient(source_p) && IsService(who)) { sendto_one(source_p, form_str(ERR_ISCHANSERVICE), me.name, source_p->name, who->name, chptr->chname); return 0; } if(MyClient(source_p) && chptr->mode.mode & MODE_NOKICK) { sendto_one_numeric(source_p, ERR_NOKICK, form_str(ERR_NOKICK), chptr->chname); return 0; } if (MyClient(source_p) && chptr->mode.mode & MODE_NOOPERKICK && IsOper(who)) { sendto_realops_snomask(SNO_GENERAL, L_NETWIDE, "Overriding KICK from %s on %s in %s (channel is +M)", source_p->name, who->name, chptr->chname); sendto_one_numeric(source_p, ERR_ISCHANSERVICE, "%s %s :Cannot kick IRC operators from that channel.", who->name, chptr->chname); return 0; } if(MyClient(source_p)) { hook_data_channel_approval hookdata; hookdata.client = source_p; hookdata.chptr = chptr; hookdata.target = who; hookdata.approved = 1; call_hook(h_can_kick, &hookdata); if (!hookdata.approved) return 0; } comment = LOCAL_COPY((EmptyString(parv[3])) ? who->name : parv[3]); if(strlen(comment) > (size_t) REASONLEN) comment[REASONLEN] = '\0'; if(is_override) { sendto_wallops_flags(UMODE_WALLOP, &me, "%s is overriding KICK [%s] on [%s] [%s]", get_oper_name(source_p), who->name, chptr->chname, comment); sendto_server(NULL, chptr, NOCAPS, NOCAPS, ":%s WALLOPS :%s is overriding KICK [%s] on [%s] [%s]", me.name, get_oper_name(source_p), who->name, chptr->chname, comment); } /* jdc * - In the case of a server kicking a user (i.e. CLEARCHAN), * the kick should show up as coming from the server which did * the kick. * - Personally, flame and I believe that server kicks shouldn't * be sent anyways. Just waiting for some oper to abuse it... */ if(IsServer(source_p)) sendto_channel_local(ALL_MEMBERS, chptr, ":%s KICK %s %s :%s", source_p->name, name, who->name, comment); else sendto_channel_local(ALL_MEMBERS, chptr, ":%s!%s@%s KICK %s %s :%s", source_p->name, source_p->username, source_p->host, name, who->name, comment); sendto_server(client_p, chptr, CAP_TS6, NOCAPS, ":%s KICK %s %s :%s", use_id(source_p), chptr->chname, use_id(who), comment); remove_user_from_channel(msptr); rb_snprintf(text, sizeof(text), "K%s", who->id); /* we don't need to track NOREJOIN stuff unless it's our client being kicked */ if(MyClient(who) && chptr->mode.mode & MODE_NOREJOIN) channel_metadata_time_add(chptr, text, rb_current_time(), "KICKNOREJOIN"); } else if (MyClient(source_p)) sendto_one_numeric(source_p, ERR_USERNOTINCHANNEL, form_str(ERR_USERNOTINCHANNEL), user, name); return 0; }
/* * ms_connect - CONNECT command handler * * Added by Jto 11 Feb 1989 * * m_connect * parv[1] = servername * parv[2] = port number * parv[3] = remote server */ static int ms_connect(struct MsgBuf *msgbuf_p, struct Client *client_p, struct Client *source_p, int parc, const char *parv[]) { int port; int tmpport; struct server_conf *server_p; struct Client *target_p; if(hunt_server(client_p, source_p, ":%s CONNECT %s %s :%s", 3, parc, parv) != HUNTED_ISME) return 0; if((target_p = find_server(NULL, parv[1]))) { sendto_one_notice(source_p, ":Connect: Server %s already exists from %s.", parv[1], target_p->from->name); return 0; } /* * try to find the name, then host, if both fail notify ops and bail */ if((server_p = find_server_conf(parv[1])) == NULL) { sendto_one_notice(source_p, ":Connect: Host %s not listed in ircd.conf", parv[1]); return 0; } if(ServerConfSSL(server_p) && (!ssl_ok || !get_ssld_count())) { sendto_one_notice(source_p, ":Connect: Server %s is set to use SSL/TLS but SSL/TLS is not configured.", parv[1]); return 0; } /* * Get port number from user, if given. If not specified, * use the default form configuration structure. If missing * from there, then use the precompiled default. */ tmpport = server_p->port; port = atoi(parv[2]); /* if someone sends port 0, and we have a config port.. use it */ if(port == 0 && server_p->port) port = server_p->port; else if(port <= 0) { sendto_one_notice(source_p, ":Connect: Illegal port number"); return 0; } /* * Notify all operators about remote connect requests */ sendto_wallops_flags(UMODE_WALLOP, &me, "Remote CONNECT %s %d from %s", parv[1], port, source_p->name); sendto_server(NULL, NULL, CAP_TS6, NOCAPS, ":%s WALLOPS :Remote CONNECT %s %d from %s", me.id, parv[1], port, source_p->name); ilog(L_SERVER, "CONNECT From %s : %s %d", source_p->name, parv[1], port); server_p->port = port; /* * at this point we should be calling connect_server with a valid * C:line and a valid port in the C:line */ if(serv_connect(server_p, source_p)) sendto_one_notice(source_p, ":*** Connecting to %s.%d", server_p->name, server_p->port); else sendto_one_notice(source_p, ":*** Couldn't connect to %s.%d", server_p->name, server_p->port); /* * client is either connecting with all the data it needs or has been * destroyed */ server_p->port = tmpport; return 0; }
/* * m_omode - MODE command handler * parv[0] - sender * parv[1] - channel */ static void m_omode(struct Client *client_p, struct Client *source_p, int parc, char *parv[]) { struct Channel *chptr = NULL; struct membership *msptr; static char modebuf[MODEBUFLEN]; static char parabuf[MODEBUFLEN]; int n = 2; if(EmptyString(parv[1])) { sendto_one(source_p, form_str(ERR_NEEDMOREPARAMS), me.name, parv[0], "MODE"); return; } /* Now, try to find the channel in question */ if(!IsChanPrefix(parv[1][0])) { /* if here, it has to be a non-channel name */ user_mode(client_p, source_p, parc, parv); return; } if(!check_channel_name(parv[1])) { sendto_one(source_p, form_str(ERR_BADCHANNAME), me.name, parv[0], (unsigned char *) parv[1]); return; } chptr = hash_find_channel(parv[1]); if(chptr == NULL) { sendto_one(source_p, form_str(ERR_NOSUCHCHANNEL), me.name, parv[0], parv[1]); return; } sendto_wallops_flags(UMODE_WALLOP, &me, "OMODE called for [%s] by %s!%s@%s", parv[1], source_p->name, source_p->username, source_p->host); ilog(L_NOTICE, "OMODE called for [%s] by %s!%s@%s", parv[1], source_p->name, source_p->username, source_p->host); if(*chptr->chname != '&') sendto_server(NULL, NULL, NOCAPS, NOCAPS, ":%s WALLOPS :OMODE called for [%s] by %s!%s@%s", me.name, parv[1], source_p->name, source_p->username, source_p->host); /* Now know the channel exists */ if(parc < n + 1) { channel_modes(chptr, source_p, modebuf, parabuf); sendto_one(source_p, form_str(RPL_CHANNELMODEIS), me.name, parv[0], parv[1], modebuf, parabuf); sendto_one(source_p, form_str(RPL_CREATIONTIME), me.name, parv[0], parv[1], chptr->channelts); } else if(IsServer(source_p)) { set_channel_mode(client_p, source_p, chptr, NULL, parc - n, parv + n, chptr->chname); } else { msptr = find_channel_membership(chptr, source_p); set_channel_mode(client_p, source_p->servptr, chptr, msptr, parc - n, parv + n, chptr->chname); } }
/* ** mo_ojoin ** parv[1] = channel */ static void mo_ojoin(struct MsgBuf *msgbuf_p, struct Client *client_p, struct Client *source_p, int parc, const char *parv[]) { struct Channel *chptr; int move_me = 0; /* admins only */ if(!IsOperAdmin(source_p)) { sendto_one(source_p, form_str(ERR_NOPRIVS), me.name, source_p->name, "admin"); return; } if(*parv[1] == '@' || *parv[1] == '+') { parv[1]++; move_me = 1; } if((chptr = find_channel(parv[1])) == NULL) { sendto_one_numeric(source_p, ERR_NOSUCHCHANNEL, form_str(ERR_NOSUCHCHANNEL), parv[1]); return; } if(IsMember(source_p, chptr)) { sendto_one_notice(source_p, ":Please part %s before using OJOIN", parv[1]); return; } if(move_me == 1) parv[1]--; sendto_wallops_flags(UMODE_WALLOP, &me, "OJOIN called for %s by %s!%s@%s", parv[1], source_p->name, source_p->username, source_p->host); ilog(L_MAIN, "OJOIN called for %s by %s", parv[1], get_oper_name(source_p)); /* only sends stuff for #channels remotely */ sendto_server(NULL, chptr, NOCAPS, NOCAPS, ":%s WALLOPS :OJOIN called for %s by %s!%s@%s", me.name, parv[1], source_p->name, source_p->username, source_p->host); if(*parv[1] == '@') { add_user_to_channel(chptr, source_p, CHFL_CHANOP); sendto_server(client_p, chptr, CAP_TS6, NOCAPS, ":%s SJOIN %ld %s + :@%s", me.id, (long) chptr->channelts, chptr->chname, source_p->id); send_channel_join(chptr, source_p); sendto_channel_local(ALL_MEMBERS, chptr, ":%s MODE %s +o %s", me.name, chptr->chname, source_p->name); } else if(*parv[1] == '+') { add_user_to_channel(chptr, source_p, CHFL_VOICE); sendto_server(client_p, chptr, CAP_TS6, NOCAPS, ":%s SJOIN %ld %s + :+%s", me.id, (long) chptr->channelts, chptr->chname, source_p->id); send_channel_join(chptr, source_p); sendto_channel_local(ALL_MEMBERS, chptr, ":%s MODE %s +v %s", me.name, chptr->chname, source_p->name); } else { add_user_to_channel(chptr, source_p, CHFL_PEON); sendto_server(client_p, chptr, CAP_TS6, NOCAPS, ":%s JOIN %ld %s +", source_p->id, (long) chptr->channelts, chptr->chname); send_channel_join(chptr, source_p); } /* send the topic... */ if(chptr->topic != NULL) { sendto_one(source_p, form_str(RPL_TOPIC), me.name, source_p->name, chptr->chname, chptr->topic); sendto_one(source_p, form_str(RPL_TOPICWHOTIME), me.name, source_p->name, chptr->chname, chptr->topic_info, chptr->topic_time); } source_p->localClient->last_join_time = rb_current_time(); channel_member_names(chptr, source_p, 1); }