From fa3070da167b9de27d40c7c3b47b13bbb5d37950 Mon Sep 17 00:00:00 2001 From: Michael Poole Date: Sat, 15 May 2004 16:58:11 +0000 Subject: [PATCH] Forward port various channel and /list updates git-svn-id: file:///home/klmitch/undernet-ircu/undernet-ircu-svn/ircu2/trunk@1057 c9e4aea6-c8fd-4c43-8297-357d70d61c8c --- ChangeLog | 29 ++++++++++++++++++++++++++++ include/channel.h | 11 ++++++++--- ircd/channel.c | 48 +++++++++++++++++++++++++++++++---------------- ircd/m_list.c | 17 ++++++++++++++++- 4 files changed, 85 insertions(+), 20 deletions(-) diff --git a/ChangeLog b/ChangeLog index 48edac7..64f8366 100644 --- a/ChangeLog +++ b/ChangeLog @@ -1,3 +1,32 @@ +2004-05-15 Michael Poole + + * ircd/channel.c (can_join): Revert to using IsInvited() rather + than walking the list directly. + (modebuf_flush_int): Fix errant HEAD_IN_SAND_SNOTICES check to + use feature_bool(FEAT_HIS_SNOTICES) instead. + +2004-05-15 Kevin L Mitchell + + [Original ChangeLog date: 2004-01-31 -MDP] + + * ircd/channel.c (mode_parse_key): don't allow , in keys! + +2003-04-12 David Mansell (splidge) + + [Original ChangeLog date: 2003-04-14 -MDP] + + * ircd/channel.c: When keys and limits conflict on burst, the key + which is first alphabetically or the limit which is lower will be + used by both servers. This matches pre-2.10.11 behaviour. + Closes: (#713930) + +2004-05-15 David Mansell + + [Original ChangeLog date: 2002-12-28 -MDP] + + * ircd/channel.c (mode_parse_limit): don't allow -l when no limit is + set, don't allow -l with negative parameter (or unsigned >2^31). + 2004-05-15 David Mansell [Original ChangeLog date: 2002-12-31 -MDP] diff --git a/include/channel.h b/include/channel.h index 18d6d9f..545748f 100644 --- a/include/channel.h +++ b/include/channel.h @@ -119,9 +119,9 @@ struct Client; (MODE_PRIVATE | MODE_SECRET)) == 0) #define is_listed(x) ((x)->mode.mode & MODE_LISTED) +#define IsGlobalChannel(name) (*(name) == '#') #define IsLocalChannel(name) (*(name) == '&') -#define IsChannelName(name) (*(name) == '#' || \ - IsLocalChannel(name)) +#define IsChannelName(name) (IsGlobalChannel(name) || IsLocalChannel(name)) typedef enum ChannelGetType { CGT_NO_CREATE, @@ -134,6 +134,11 @@ typedef enum ChannelGetType { #define MODE_ADD 0x40000000 #define MODE_DEL 0x20000000 +/* used in ListingArgs.flags */ + +#define LISTARG_TOPICLIMITS 0x0001 +#define LISTARG_SHOWSECRET 0x0002 + /* * Maximum acceptable lag time in seconds: A channel younger than * this is not protected against hacking admins. @@ -247,7 +252,7 @@ struct ListingArgs { time_t min_time; unsigned int max_users; unsigned int min_users; - unsigned int topic_limits; + unsigned int flags; time_t max_topic_time; time_t min_topic_time; struct Channel *chptr; diff --git a/ircd/channel.c b/ircd/channel.c index 9e7c258..b67c862 100644 --- a/ircd/channel.c +++ b/ircd/channel.c @@ -1171,7 +1171,6 @@ top: int can_join(struct Client *sptr, struct Channel *chptr, char *key) { - struct SLink *lp; int overrideJoin = 0; /* @@ -1180,9 +1179,8 @@ int can_join(struct Client *sptr, struct Channel *chptr, char *key) * Now a user CAN escape anything if invited -- Isomer */ - for (lp = (cli_user(sptr))->invited; lp; lp = lp->next) - if (lp->value.chptr == chptr) - return 0; + if (IsInvited(sptr, chptr)) + return 0; /* An oper can force a join on a local channel using "OVERRIDE" as the key. a HACK(4) notice will be sent if he would not have been supposed @@ -1346,17 +1344,19 @@ void list_next_channels(struct Client *cptr, int nr) { for (; chptr; chptr = chptr->next) { - if (!cli_user(cptr) || (!(HasPriv(cptr, PRIV_LIST_CHAN) && IsAnOper(cptr)) && + if (!cli_user(cptr)) + continue; + if (!(HasPriv(cptr, PRIV_LIST_CHAN) && IsAnOper(cptr)) && SecretChannel(chptr) && !find_channel_member(cptr, chptr))) continue; if (chptr->users > args->min_users && chptr->users < args->max_users && chptr->creationtime > args->min_time && chptr->creationtime < args->max_time && - (!args->topic_limits || (*chptr->topic && + (!(args->flags & LISTARG_TOPICLIMITS) || (*chptr->topic && chptr->topic_time > args->min_topic_time && chptr->topic_time < args->max_topic_time))) { - if (ShowChannel(cptr,chptr)) + if ((args->flags & LISTARG_SHOWSECRET) || ShowChannel(cptr,chptr)) send_reply(cptr, RPL_LIST, chptr->chname, chptr->users, chptr->topic); chptr = chptr->next; @@ -1722,11 +1722,8 @@ modebuf_flush_int(struct ModeBuf *mbuf, int all) if (mbuf->mb_dest & MODEBUF_DEST_HACK4) sendto_opmask_butone(0, SNO_HACK4, "HACK(4): %s MODE %s %s%s%s%s%s%s " "[%Tu]", -#ifdef HEAD_IN_SAND_SNOTICES - cli_name(mbuf->mb_source), -#else - cli_name(app_source), -#endif + cli_name(feature_bool(FEAT_HIS_SNOTICES) ? + mbuf->mb_source : app_source), mbuf->mb_channel->chname, rembuf_i ? "-" : "", rembuf, addbuf_i ? "+" : "", addbuf, remstr, addstr, @@ -2175,6 +2172,9 @@ mode_parse_limit(struct ParseState *state, int *flag_p) state->parc--; state->max_args--; + if ((int)t_limit<0) /* don't permit a negative limit */ + return; + if (!(state->flags & MODE_PARSE_WIPEOUT) && (!t_limit || t_limit == state->chptr->mode.limit)) return; @@ -2187,6 +2187,16 @@ mode_parse_limit(struct ParseState *state, int *flag_p) return; } + /* Can't remove a limit that's not there */ + if (state->dir == MODE_DEL && !state->chptr->mode.limit) + return; + + /* Skip if this is a burst and a lower limit than this is set already */ + if ((state->flags & MODE_PARSE_BURST) && + (state->chptr->mode.mode & flag_p[0]) && + (state->chptr->mode.limit < t_limit)) + return; + if (state->done & DONE_LIMIT) /* allow limit to be set only once */ return; state->done |= DONE_LIMIT; @@ -2244,8 +2254,8 @@ mode_parse_key(struct ParseState *state, int *flag_p) /* clean up the key string */ s = t_str; - while (*++s > ' ' && *s != ':' && --t_len) - ; + while (*s > ' ' && *s != ':' && *s != ',' && t_len--) + s++; *s = '\0'; if (!*t_str) { /* warn if empty */ @@ -2258,6 +2268,13 @@ mode_parse_key(struct ParseState *state, int *flag_p) if (!state->mbuf) return; + /* Skip if this is a burst, we have a key already and the new key is + * after the old one alphabetically */ + if ((state->flags & MODE_PARSE_BURST) && + *(state->chptr->mode.key) && + ircd_strcmp(state->chptr->mode.key, t_str) <= 0) + return; + /* can't add a key if one is set, nor can one remove the wrong key */ if (!(state->flags & MODE_PARSE_FORCE)) if ((state->dir == MODE_ADD && *state->chptr->mode.key) || @@ -2829,8 +2846,7 @@ mode_process_clients(struct ParseState *state) if (MyUser(state->sptr)) { /* don't allow local opers to be deopped on local channels */ - if (MyUser(state->sptr) && - state->cli_change[i].client != state->sptr && + if (state->cli_change[i].client != state->sptr && IsLocalChannel(state->chptr->chname) && HasPriv(state->cli_change[i].client, PRIV_DEOP_LCHAN)) { send_reply(state->sptr, ERR_ISOPERLCHAN, diff --git a/ircd/m_list.c b/ircd/m_list.c index 9917712..3cb9ef9 100644 --- a/ircd/m_list.c +++ b/ircd/m_list.c @@ -158,6 +158,9 @@ show_usage(struct Client *sptr) send_reply(sptr, RPL_LISTUSAGE, " \002T>\002\037min_minutes\037 ; Channels with a topic last " "set more than \037min_minutes\037 ago."); + if (IsAnOper(sptr)) + send_reply(sptr, RPL_LISTUSAGE, + " \002S\002 ; Show secret channels."); send_reply(sptr, RPL_LISTUSAGE, "Example: LIST <3,>1,C<10,T>0 ; 2 users, younger than 10 " "min., topic set."); @@ -183,7 +186,7 @@ param_parse(struct Client *sptr, const char *param, struct ListingArgs *args, case 'T': case 't': is_time++; - args->topic_limits = 1; + args->flags |= LISTARG_TOPICLIMITS; /*FALLTHROUGH*/ case 'C': @@ -233,6 +236,18 @@ param_parse(struct Client *sptr, const char *param, struct ListingArgs *args, } break; + case 'S': + case 's': + if (!IsAnOper(sptr)) + return show_usage(sptr); + + args->flags |= LISTARG_SHOWSECRET; + param++; + + if (*param != ',' && *param != ' ' && *param !+ '\0') /* check syntax */ + return show_usage(sptr); + break; + default: /* channel name? */ if (!permit_chan || !IsChannelName(param)) return show_usage(sptr); -- 2.20.1