From 8d67f0605c96ee1118944aceff9ec28aac26935d Mon Sep 17 00:00:00 2001 From: Stephen Bennett Date: Fri, 30 Sep 2022 08:29:02 +0100 Subject: [PATCH] Make +R play nicely with +z --- extensions/chm_regmsg.c | 69 +++++++++++++++++++++++++++++++---------- 1 file changed, 52 insertions(+), 17 deletions(-) diff --git a/extensions/chm_regmsg.c b/extensions/chm_regmsg.c index bddb128c..aa04c5d0 100644 --- a/extensions/chm_regmsg.c +++ b/extensions/chm_regmsg.c @@ -40,41 +40,76 @@ static const char chm_regmsg_desc[] = static unsigned int mode_regmsg; -static void chm_regmsg_process(void *); +static void hook_privmsg_channel(void *); +static void hook_can_send(void *); mapi_hfn_list_av1 chm_regmsg_hfnlist[] = { - { "privmsg_channel", chm_regmsg_process }, + { "privmsg_channel", hook_privmsg_channel }, + { "can_send", hook_can_send }, { NULL, NULL } }; +static bool +chm_regmsg_test(struct Client *source_p, struct Channel *chptr) +{ + struct membership *msptr; + + /* mode is unset, accept */ + if (!(chptr->mode.mode & mode_regmsg)) + return true; + + /* user is identified, accept */ + if (!EmptyString(source_p->user->suser)) + return true; + + /* voice and op override identification requirement, accept */ + msptr = find_channel_membership(chptr, source_p); + if (is_chanop_voiced(msptr)) + return true; + + return false; +} + static void -chm_regmsg_process(void *data_) +hook_privmsg_channel(void *data_) { hook_data_privmsg_channel *data = data_; - struct membership *msptr; + + /* Only apply this hook if the channel isn't +z - if it is +z, then the can_send + * hook should be used to enable +z to do its job, as an error numeric won't be sent in that case */ + if (data->chptr->mode.mode & MODE_OPMODERATE) + return; /* message is already blocked, defer */ if (data->approved) return; - /* mode is unset, accept */ - if (!(data->chptr->mode.mode & mode_regmsg)) + if (chm_regmsg_test(data->source_p, data->chptr)) return; - /* user is identified, accept */ - if (!EmptyString(data->source_p->user->suser)) - return; - - /* voice and op override identification requirement, accept */ - msptr = find_channel_membership(data->chptr, data->source_p); - if (is_chanop_voiced(msptr)) - return; - - sendto_one_numeric(data->source_p, ERR_MSGNEEDREGGEDNICK, form_str(ERR_MSGNEEDREGGEDNICK), - data->chptr->chname); + sendto_one_numeric(data->source_p, ERR_MSGNEEDREGGEDNICK, form_str(ERR_MSGNEEDREGGEDNICK), data->chptr->chname); data->approved = ERR_MSGNEEDREGGEDNICK; } +static void hook_can_send(void *data_) +{ + hook_data_channel_approval *data = data_; + + /* Only apply this hook if the channel is +z - if it isn't +z, then the privmsg_channel + * hook should be used to enable a custom error numeric to be sent */ + if (!(data->chptr->mode.mode & MODE_OPMODERATE)) + return; + + /* message is already blocked, defer */ + if (data->approved == CAN_SEND_NO) + return; + + if (chm_regmsg_test(data->client, data->chptr)) + return; + + data->approved = CAN_SEND_NO; +} + static int _modinit(void) {