From a6751c0c45a544481f0856cb4dc3b70c258939ac Mon Sep 17 00:00:00 2001 From: David Schultz Date: Fri, 25 Jun 2021 01:30:17 +0100 Subject: [PATCH 1/3] add gateway name field for auth blocks --- extensions/Makefile.am | 2 ++ extensions/cap_gateway.c | 58 +++++++++++++++++++++++++++++++++++++++ extensions/extb_gateway.c | 54 ++++++++++++++++++++++++++++++++++++ include/client.h | 1 + include/messages.h | 1 + include/numeric.h | 1 + include/s_conf.h | 1 + ircd/newconf.c | 7 +++++ ircd/s_user.c | 5 ++++ modules/m_who.c | 18 ++++++++++++ modules/m_whois.c | 7 +++++ 11 files changed, 155 insertions(+) create mode 100644 extensions/cap_gateway.c create mode 100644 extensions/extb_gateway.c diff --git a/extensions/Makefile.am b/extensions/Makefile.am index 850650fa4..1055ffb5f 100644 --- a/extensions/Makefile.am +++ b/extensions/Makefile.am @@ -22,6 +22,7 @@ extension_LTLIBRARIES = \ extb_account.la \ extb_canjoin.la \ extb_channel.la \ + extb_gateway.la \ extb_hostmask.la \ extb_oper.la \ extb_server.la \ @@ -68,6 +69,7 @@ extension_LTLIBRARIES = \ drain.la \ identify_msg.la \ cap_realhost.la \ + cap_gateway.la \ invex_regonly.la \ example_module.la diff --git a/extensions/cap_gateway.c b/extensions/cap_gateway.c new file mode 100644 index 000000000..b7372c950 --- /dev/null +++ b/extensions/cap_gateway.c @@ -0,0 +1,58 @@ +/* + * Copyright (C) 2021 David Schultz + * + * This program is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License as published by + * the Free Software Foundation; either version 2 of the License, or + * (at your option) any later version. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with this program; if not, write to the Free Software + * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 + * USA + */ + +#include +#include +#include +#include +#include +#include +#include + +static char cap_gateway_desc[] = "Provides the solanum.chat/gateway capability"; + +static void cap_gateway_outbound_msgbuf(void *); + +static unsigned CLICAP_GATEWAY; + +mapi_cap_list_av2 cap_gateway_caps[] = { + { MAPI_CAP_CLIENT, "solanum.chat/gateway", NULL, &CLICAP_GATEWAY }, + { 0, NULL, NULL, NULL } +}; + +mapi_hfn_list_av1 cap_gateway_hfnlist[] = { + { "outbound_msgbuf", cap_gateway_outbound_msgbuf, HOOK_NORMAL }, + { NULL, NULL, 0 } +}; + + +static void +cap_gateway_outbound_msgbuf(void *data_) +{ + hook_data *data = data_; + struct MsgBuf *msgbuf = data->arg1; + + if (data->client == NULL || !IsPerson(data->client)) + return; + + if (!EmptyString(data->client->gateway)) + msgbuf_append_tag(msgbuf, "solanum.chat/gateway", data->client->gateway, CLICAP_GATEWAY); +} + +DECLARE_MODULE_AV2(cap_gateway, NULL, NULL, NULL, NULL, cap_gateway_hfnlist, cap_gateway_caps, NULL, cap_gateway_desc); diff --git a/extensions/extb_gateway.c b/extensions/extb_gateway.c new file mode 100644 index 000000000..0cef82f37 --- /dev/null +++ b/extensions/extb_gateway.c @@ -0,0 +1,54 @@ +/* + * Copyright (C) 2021 David Schultz + * + * This program is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License as published by + * the Free Software Foundation; either version 2 of the License, or + * (at your option) any later version. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with this program; if not, write to the Free Software + * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 + * USA + */ + +#include "stdinc.h" +#include "modules.h" +#include "client.h" +#include "ircd.h" + +static const char extb_desc[] = "Gateway name ($g) extban type"; + +static int _modinit(void); +static void _moddeinit(void); +static int eb_gateway(const char *data, struct Client *client_p, struct Channel *chptr, long mode_type); + +DECLARE_MODULE_AV2(extb_gateway, _modinit, _moddeinit, NULL, NULL, NULL, NULL, NULL, extb_desc); + +static int +_modinit(void) +{ + extban_table['g'] = eb_gateway; + + return 0; +} + +static void +_moddeinit(void) +{ + extban_table['g'] = NULL; +} + +static int eb_gateway(const char *data, struct Client *client_p, + struct Channel *chptr, long mode_type) +{ + /* $g by itself will match all gateway users */ + if (data == NULL) + return EmptyString(client_p->gateway) ? EXTBAN_NOMATCH : EXTBAN_MATCH; + return match(data, client_p->gateway) ? EXTBAN_MATCH : EXTBAN_NOMATCH; +} diff --git a/include/client.h b/include/client.h index 9bc443f71..025824b64 100644 --- a/include/client.h +++ b/include/client.h @@ -145,6 +145,7 @@ struct Client char orighost[HOSTLEN + 1]; /* original hostname (before dynamic spoofing) */ char sockhost[HOSTIPLEN + 1]; /* clients ip */ char info[REALLEN + 1]; /* Free form additional client info */ + char gateway[REALLEN + 1]; /* name of the gateway in i:line */ char id[IDLEN]; /* UID/SID, unique on the network */ diff --git a/include/messages.h b/include/messages.h index 2f39181f8..87932492c 100644 --- a/include/messages.h +++ b/include/messages.h @@ -96,6 +96,7 @@ #define NUMERIC_STR_317 "%s %ld %lu :seconds idle, signon time" #define NUMERIC_STR_318 "%s :End of /WHOIS list." #define NUMERIC_STR_319 ":%s 319 %s %s :" +#define NUMERIC_STR_320 "%s :is using gateway: %s" #define NUMERIC_STR_321 ":%s 321 %s Channel :Users Name" #define NUMERIC_STR_322 ":%s 322 %s %s%s %lu :%s" #define NUMERIC_STR_323 ":%s 323 %s :End of /LIST" diff --git a/include/numeric.h b/include/numeric.h index dcabff612..edc975864 100644 --- a/include/numeric.h +++ b/include/numeric.h @@ -144,6 +144,7 @@ #define RPL_ENDOFWHOIS 318 #define RPL_WHOISCHANNELS 319 +#define RPL_WHOISGATEWAY 320 #define RPL_LISTSTART 321 #define RPL_LIST 322 diff --git a/include/s_conf.h b/include/s_conf.h index 4d4b6b40f..6d3dd70a5 100644 --- a/include/s_conf.h +++ b/include/s_conf.h @@ -73,6 +73,7 @@ struct ConfItem struct Class *c_class; /* Class of connection */ rb_patricia_node_t *pnode; /* Our patricia node */ int umodes, umodes_mask; /* Override umodes specified by mask */ + char *gateway; }; #define CONF_ILLEGAL 0x80000000 diff --git a/ircd/newconf.c b/ircd/newconf.c index d6eef9f08..7ec2621c2 100644 --- a/ircd/newconf.c +++ b/ircd/newconf.c @@ -1212,6 +1212,12 @@ conf_set_auth_umodes(void *data) parse_umodes(umodes, &yy_aconf->umodes, &yy_aconf->umodes_mask); } +static void +conf_set_auth_gateway(void *data) +{ + yy_aconf->gateway = rb_strdup(data); +} + static int conf_begin_connect(struct TopConf *tc) { @@ -2631,6 +2637,7 @@ static struct ConfEntry conf_auth_table[] = { "redirport", CF_INT, conf_set_auth_redir_port, 0, NULL }, { "flags", CF_STRING | CF_FLIST, conf_set_auth_flags, 0, NULL }, { "umodes", CF_QSTRING, conf_set_auth_umodes, 0, NULL}, + { "gateway", CF_QSTRING, conf_set_auth_gateway, 0, NULL}, { "\0", 0, NULL, 0, NULL } }; diff --git a/ircd/s_user.c b/ircd/s_user.c index 3184eba45..8427ec317 100644 --- a/ircd/s_user.c +++ b/ircd/s_user.c @@ -594,6 +594,11 @@ register_local_user(struct Client *client_p, struct Client *source_p) SetDynSpoof(source_p); } + if (!EmptyString(aconf->gateway)) + { + rb_strlcpy(source_p->gateway, aconf->gateway, REALLEN + 1); + } + umodes = ConfigFileEntry.default_umodes & ~aconf->umodes_mask; umodes |= aconf->umodes; umodes &= ~ConfigFileEntry.oper_only_umodes; diff --git a/modules/m_who.c b/modules/m_who.c index e9760943c..622c024ab 100644 --- a/modules/m_who.c +++ b/modules/m_who.c @@ -53,6 +53,7 @@ #define FIELD_USER 0x0400 #define FIELD_ACCOUNT 0x0800 #define FIELD_OPLEVEL 0x1000 /* meaningless and stupid, but whatever */ +#define FIELD_GATEWAY 0x2000 static const char who_desc[] = "Provides the WHO command to display information for users on a channel"; @@ -137,6 +138,7 @@ m_who(struct MsgBuf *msgbuf_p, struct Client *client_p, struct Client *source_p, case 'u': fmt.fields |= FIELD_USER; break; case 'a': fmt.fields |= FIELD_ACCOUNT; break; case 'o': fmt.fields |= FIELD_OPLEVEL; break; + case 'g': fmt.fields |= FIELD_GATEWAY; break; case ',': s++; fmt.querytype = s; @@ -486,6 +488,7 @@ do_who(struct Client *source_p, struct Client *target_p, struct membership *mspt char str[510 + 1]; /* linebuf.c will add \r\n */ size_t pos; const char *q; + const char *g; sprintf(status, "%c%s%s", target_p->user->away ? 'G' : 'H', SeesOper(target_p, source_p) ? "*" : "", msptr ? find_channel_status(msptr, fmt->fields || IsCapable(source_p, CLICAP_MULTI_PREFIX)) : ""); @@ -543,6 +546,21 @@ do_who(struct Client *source_p, struct Client *target_p, struct membership *mspt q = "0"; append_format(str, sizeof str, &pos, " %s", q); } + if (fmt->fields & FIELD_GATEWAY) + { + /* use same the logic as account */ + g = target_p->gateway; + if (!EmptyString(g)) + { + while(IsDigit(*g)) + g++; + if(*g == '\0') + g = target_p->gateway; + } + else + g = "0"; + append_format(str, sizeof str, &pos, " %s", g); + } if (fmt->fields & FIELD_OPLEVEL) append_format(str, sizeof str, &pos, " %s", is_chanop(msptr) ? "999" : "n/a"); if (fmt->fields & FIELD_INFO) diff --git a/modules/m_whois.c b/modules/m_whois.c index ecd865693..fab2ddd68 100644 --- a/modules/m_whois.c +++ b/modules/m_whois.c @@ -373,6 +373,13 @@ single_whois(struct Client *source_p, struct Client *target_p, int operspy) target_p->name, buf); } + if (!EmptyString(target_p->gateway)) + { + sendto_one_numeric(source_p, RPL_WHOISGATEWAY, + form_str(RPL_WHOISGATEWAY), + target_p->name, target_p->gateway); + } + sendto_one_numeric(source_p, RPL_WHOISIDLE, form_str(RPL_WHOISIDLE), target_p->name, (long)(rb_current_time() - target_p->localClient->last), From 16ef4c58ada0e6d8b37c3f13c63330fa953db7f7 Mon Sep 17 00:00:00 2001 From: David Schultz Date: Tue, 30 Aug 2022 17:34:14 -0500 Subject: [PATCH 2/3] add reference.conf info --- doc/reference.conf | 10 ++++++++++ 1 file changed, 10 insertions(+) diff --git a/doc/reference.conf b/doc/reference.conf index 4cd8c0372..24b4d29e7 100644 --- a/doc/reference.conf +++ b/doc/reference.conf @@ -47,6 +47,7 @@ * Charybdis contains several extensions that are not enabled by default. * To use them, uncomment the lines below. * + * Message tag containing a user's gateway -- cap_gateway * Channel mode +-A (admin only) -- chm_adminonly * Channel mode +-T (blocks notices) -- chm_nonotice * Channel mode +-O (oper only) -- chm_operonly @@ -58,6 +59,7 @@ * Other-channel bans (+b $c:mask) -- extb_channel * Combination extbans -- extb_combi * Extended ban (+b $x:mask) -- extb_extgecos + * Gateway bans (+b $g:gateway) -- extb_gateway * Hostmask bans (for combination extbans) -- extb_hostmask * Oper bans (+b $o) -- extb_oper * Realname (gecos) bans (+b $r:mask) -- extb_realname @@ -80,6 +82,7 @@ * Stop services kills -- no_kill_services * Allows you to hide your idle time (umode +I) -- umode_hide_idle_time */ +#loadmodule "extensions/cap_gateway"; #loadmodule "extensions/chm_adminonly"; #loadmodule "extensions/chm_nonotice"; #loadmodule "extensions/chm_operonly"; @@ -91,6 +94,7 @@ #loadmodule "extensions/extb_channel"; #loadmodule "extensions/extb_combi"; #loadmodule "extensions/extb_extgecos"; +#loadmodule "extensions/extb_gateway"; #loadmodule "extensions/extb_hostmask"; #loadmodule "extensions/extb_oper"; #loadmodule "extensions/extb_realname"; @@ -377,6 +381,12 @@ auth { * just do everyone a favour and dont abuse it. (OLD I: = flag) */ spoof = "I.still.hate.packets"; + + /* gateway: identifies the gateway this auth block belongs to + * and is displayed in WHOIS for all users connecting through + * this auth block + */ + gateway = "matrix"; /* Possible flags in auth: * From 4d769f563c8914abe742519fa745df46d2fc616e Mon Sep 17 00:00:00 2001 From: launchd Date: Mon, 3 Jul 2023 17:58:46 -0500 Subject: [PATCH 3/3] change extban/whox char to `w` due to conflict Since the creation of this PR, a new module was introduced using the extban char `g`, creating an unforseen conflict. This commit changes that character to `w` to match the char used in inspircd --- doc/reference.conf | 2 +- extensions/extb_gateway.c | 8 ++++---- modules/m_who.c | 20 ++++++++++---------- 3 files changed, 15 insertions(+), 15 deletions(-) diff --git a/doc/reference.conf b/doc/reference.conf index 1db39898b..e4ab5e833 100644 --- a/doc/reference.conf +++ b/doc/reference.conf @@ -59,7 +59,7 @@ * Other-channel bans (+b $c:mask) -- extb_channel * Combination extbans -- extb_combi * Extended ban (+b $x:mask) -- extb_extgecos - * Gateway bans (+b $g:gateway) -- extb_gateway + * Gateway bans (+b $w:gateway) -- extb_gateway * Hostmask bans (for combination extbans) -- extb_hostmask * Oper bans (+b $o) -- extb_oper * Realname (gecos) bans (+b $r:mask) -- extb_realname diff --git a/extensions/extb_gateway.c b/extensions/extb_gateway.c index 0cef82f37..3f7338d56 100644 --- a/extensions/extb_gateway.c +++ b/extensions/extb_gateway.c @@ -22,7 +22,7 @@ #include "client.h" #include "ircd.h" -static const char extb_desc[] = "Gateway name ($g) extban type"; +static const char extb_desc[] = "Gateway name ($w) extban type"; static int _modinit(void); static void _moddeinit(void); @@ -33,7 +33,7 @@ DECLARE_MODULE_AV2(extb_gateway, _modinit, _moddeinit, NULL, NULL, NULL, NULL, N static int _modinit(void) { - extban_table['g'] = eb_gateway; + extban_table['w'] = eb_gateway; return 0; } @@ -41,13 +41,13 @@ _modinit(void) static void _moddeinit(void) { - extban_table['g'] = NULL; + extban_table['w'] = NULL; } static int eb_gateway(const char *data, struct Client *client_p, struct Channel *chptr, long mode_type) { - /* $g by itself will match all gateway users */ + /* $w by itself will match all gateway users */ if (data == NULL) return EmptyString(client_p->gateway) ? EXTBAN_NOMATCH : EXTBAN_MATCH; return match(data, client_p->gateway) ? EXTBAN_MATCH : EXTBAN_NOMATCH; diff --git a/modules/m_who.c b/modules/m_who.c index e30231f6c..94b6a5f73 100644 --- a/modules/m_who.c +++ b/modules/m_who.c @@ -144,7 +144,7 @@ m_who(struct MsgBuf *msgbuf_p, struct Client *client_p, struct Client *source_p, case 'u': fmt.fields |= FIELD_USER; break; case 'a': fmt.fields |= FIELD_ACCOUNT; break; case 'o': fmt.fields |= FIELD_OPLEVEL; break; - case 'g': fmt.fields |= FIELD_GATEWAY; break; + case 'w': fmt.fields |= FIELD_GATEWAY; break; case ',': s++; fmt.querytype = s; @@ -498,7 +498,7 @@ do_who(struct Client *source_p, struct Client *target_p, struct membership *mspt char str[510 + 1]; /* linebuf.c will add \r\n */ size_t pos; const char *q; - const char *g; + const char *w; sprintf(status, "%c%s%s", target_p->user->away ? 'G' : 'H', SeesOper(target_p, source_p) ? "*" : "", msptr ? find_channel_status(msptr, fmt->fields || IsCapable(source_p, CLICAP_MULTI_PREFIX)) : ""); @@ -571,17 +571,17 @@ do_who(struct Client *source_p, struct Client *target_p, struct membership *mspt if (fmt->fields & FIELD_GATEWAY) { /* use same the logic as account */ - g = target_p->gateway; - if (!EmptyString(g)) + w = target_p->gateway; + if (!EmptyString(w)) { - while(IsDigit(*g)) - g++; - if(*g == '\0') - g = target_p->gateway; + while(IsDigit(*w)) + w++; + if(*w == '\0') + w = target_p->gateway; } else - g = "0"; - append_format(str, sizeof str, &pos, " %s", g); + w = "0"; + append_format(str, sizeof str, &pos, " %s", w); } if (fmt->fields & FIELD_OPLEVEL) append_format(str, sizeof str, &pos, " %s", is_chanop(msptr) ? "999" : "n/a");