1
0
mirror of https://github.com/unrealircd/unrealircd.git synced 2026-07-08 15:53:13 +02:00
Commit Graph

168 Commits

Author SHA1 Message Date
Bram Matthys d79161019a Clear client->local->proto for users.
This is not an issue now in all code paths, but if someone accidentally uses
SupportXYZ() without checking IsServer() then it would be an issue.

In the past we used client->local->proto for client flags as well, but this
has been split off to client->local->caps a while ago.

I guess we should rename client->local->proto to something more server-ish
in a later major release to indicate this as well.
2026-02-22 10:37:01 +01:00
Bram Matthys a887de92ce Add extra safety in register_user() against shunned users. 2026-01-25 12:56:52 +01:00
Bram Matthys a5f1aa7f34 Print a [BUG] line if register_user() is called twice. Deliberately crash
when running in DEBUGMODE.
2026-01-23 07:42:57 +01:00
Bram Matthys 1c461db46d Call update_known_user_cache() right before HOOKTYPE_REMOTE_CONNECT.
Set known_users=NULL during a very limited period, just to be safe.
(Note that it can also be NULL during initial boot, which is a
 longer period, which is why we always NULL-check in the code that
 accesses it, but this aside)
2026-01-10 10:36:40 +01:00
Bram Matthys 0cf9fb1cb0 Also update_known_user_cache() from AllowClient(), just before
calling HOOKTYPE_ALLOW_CLIENT and (potentially) allowing the client in.
2026-01-10 10:32:07 +01:00
Bram Matthys 9310c655b9 We can do the umode change by UID. Not that it matters much :D.
And parv[0] is always NULL in UnrealIRCd.
2025-10-05 11:02:02 +02:00
Bram Matthys 5b6c00946a Optimize set_user_modes_dont_spread(): use _cmd_uid() directly.
Only downside is that mtags would be NULL, but we don't use it in
cmd_uid() so that's okay. This saves us from generating mtags in
do_cmd() when we don't need it. And also a command handler lookup
and all that. Saves around 8% of unrealircd CPU for 100k connects.
2025-10-05 11:00:00 +02:00
Bram Matthys 595f56007b Add the ISUPPORT command, which simply calls the efunction.
Call the efunction from 005 introduction as well, so it uses the
batch, if needed. And yeah we opt to send the 005's always, even
if it was already sent in the handshake (or not).

Some re-indenting (spaces to tabs).

And call the efunction from VERSION as well.

For "VERSION remote.server" we don't send them in a batch as these
are not numeric 005 but 105. These are for information purposes only
and should not confuse the client (eg not to act upon).
2025-09-20 14:56:26 +02:00
Bram Matthys cb17d58db0 Some small changes to previous commit:
* Calling from source is now in a separate function: int can_use_nick(Client *client, const char *nick)
* For hooks: don't free the reject reason, must use static storage like all other hooks
  (TODO: clarify in all hooks?)
* Move it up a bit, right before find_qline

TODO (not necessarily me :D):
* Make it an efunc
* Also call it from some other places that do find_qline, like rpc/user.c
* You may want to prod 3rd party modules like SANICK
2025-07-06 09:19:04 +02:00
Valerie Liu 6a6dd66c84 Add HOOKTYPE_CAN_USE_NICK to allow modules to reject certain nicks (#313)
* Add `HOOKTYPE_CAN_USE_NICK` for modules to disallow certain "internal-use" nicks
* Run the hook on local NICK commands
2025-07-06 07:10:58 +00:00
Bram Matthys 9b89166280 Add deconfused to TextAnalysis. Add ClientContext * to match_spamfilter().
Make match_spamfilter use the clictx->textanalysis->deconfused rather than
calculating its own. The latter will probably disappear altogether.

Unrelated but also fixed: properly set e->unicode_blocks.
2025-03-23 12:13:38 +01:00
Bram Matthys 8c21472d03 Move allow::maxperip to its own module (maxperip), add HOOKTYPE_ALLOW_CLIENT.
Also fix documentation for ~10 hooks to mention the hook name.

Obviously, the maxperip module is loaded by default (in modules.default.conf)
but it is nice to have the 400+ lines contained in a separate module
rather than being in the nick module that does NICK/UID handling.
Will look at moving more later..
2025-03-22 07:42:00 +01:00
Bram Matthys 6940272290 Prevent early UID cut-off. This doesn't happen with current unrealircd traffic
because we send 9 character uids. However, IDLEN is defined as 12 so it is
natural for other people (services and other pseudo server writers) to assume
you could send 12, which failed until now, as it only accepted 11 characters.

Just to be clear:
* We generate and send 9 character uids in UnrealIRCd ourselves, this
  works perfectly fine
* In 114d54ac61 in 2021 (UnrealIRCd 5.2.1) i
  enlarged the buffers to allow INCOMING ids of up to 12 characters.
  The reason for that is that I want the option to allow slightly larger
  uids and could start doing that several years later without causing
  desynchs and other problems.
* That didn't work properly, it only allowed up to 11 chars at this point.
* From now on it allows 12 chars. I do NOT recommend sending that though, if
  you want to send bigger ids from your services/pseudo server then use
  11, or... actually just use 9 like in normal unrealircd traffic at the
  moment.

Reported on IRC by craftxbox
2024-11-24 09:56:06 +01:00
Bram Matthys cf6718fdb2 Fix vhosts and blacklist reasons being lowercased
This was unintentional strtolower() in unreal_expand_string()
2024-10-14 18:56:21 +02:00
Bram Matthys 4557036cd6 Move unreal_expand_string() to an efunc so all code can access it
and use it not only from vhost { } block code but also for like
blacklist::reason.

This so the same variables with the same names are available at
those places.

Supported are:
$nick, $username, $realname, $ip, $hostname, $server, $account,
$operlogin, $operclass, $country_code (xx for unknown),
$asn (0 for unknown).
2024-09-20 17:13:23 +02:00
Bram Matthys a41ab32d16 maxperip: use siphash_raw(client->rawip.... 2024-09-14 20:33:57 +02:00
Bram Matthys 2ef39497c7 Similar to previous commit, move maxperip stuff from core to module.
This was in src/hash.c, src/list.c and src/modules/stats.c.
Now all in src/modules/nick.c... or should this go into a new module?

Again, this needs some more testing, like previous commit.
2024-09-14 20:18:22 +02:00
Bram Matthys 4f3e524602 Add function set_client_ip() and call HOOKTYPE_IP_CHANGE there if needed.
This to replace the scattered IP setting. It is very important to always
use set_client_ip() from this point. Everywhere!

Also, in addition to client->ip, this adds client->rawip that contains
the IP in network byte order. In older UnrealIRCd versions we always had
the raw IP but not the IP as a string, so we moved to IP as a string,
but it can be useful to have both in terms of optimizations.
Of course, then the client->ip and client->rawip always need to 100% match,
hence the set_client_ip().

This also changes IsIPV6() to do A BUGFIX, it changes it from:
* if local user is the user connected over IPv6? Otherwise, does it have ':' in the IP?
To:
* check if the IPv6 flag is set (which is set if IP contains ':')
This may seem insignificant but it means that for spoofed IP addresses,
such as WEBIRC or transparant proxy, we use the correct transport.
Previously, if the proxy was IPv6 then even if the spoofed user was using
IPv4, the ident check would still be tried over IPv6. That sort of fun.
From now in, in such a situation client->local->socket_type will be
SOCKET_TYPE_IPV6 but since client->ip (and rawip) will contain IPv4
the IsIPV6() will actually return false, as it should be.

Also, in the HOOKTYPE_IP_CHANGE, enforce that if HOOK_DENY is returned,
the the user is killed by dead_link(). The user must be killed because
that is what we expect, and you cannot use exit_client() because from
some code paths that would be too much freed structures / hassle,
as a comment in src/modules/connect-flood.c correctly states:
/* There are two reasons why we can't use exit_client() here:
 * 1) Because the HOOKTYPE_IP_CHANGE call may be too deep.
 *    Eg: read_packet -> webserver_packet_in ->
 *    webserver_handle_request_header -> webserver_handle_request ->
 *    RunHook().... and then returning without touching anything
 *    after an exit_client() would not be feasible.
 * 2) Because in HOOKTYPE_ACCEPT we always need to use dead_socket
 *    if we want to print a friendly message to TLS users.
 */
2024-07-20 12:22:26 +02:00
Bram Matthys e098be6d28 Some more moving for previous commit aa9fdd352a 2024-02-11 10:34:14 +01:00
Valerie Liu aa9fdd352a Move giving of set::modes-on-connect to after SASL (#270)
This so account-based security groups work correctly with security-group based set xxxxx { modes-on-connect ....; } settings.
[skip ci]
2024-02-11 09:32:20 +00:00
Bram Matthys d63a8cf2d5 Show who actually tried to use a banned nick.
Reported by Amiga600 in https://bugs.unrealircd.org/view.php?id=6300
Inspired by patch from Valware in https://github.com/unrealircd/unrealircd/pull/255
2023-08-19 12:17:00 +02:00
Bram Matthys 656ea105da First go at multi actions... 2023-07-06 11:51:55 +02:00
Bram Matthys 52472a9a88 Add support for set unknown-users { } and the like:
It is now possible to override some set settings per-security group by
having a set block with a name, like `set unknown-users { }`
* You could use this to set more limitations for unknown-users:
  ```
  set unknown-users {
          max-channels-per-user 5;
          static-quit "Quit";
          static-part yes;
  }
  ```
* Or to set higher values (higher than the normal set block)
  for trusted users:
  ```
  security-group trusted-bots {
          account { BotOne; BotTwo; }
  }
  set trusted-bots {
          max-channels-per-user 25;
  }
  ```
* Currently the following settings can be used in a set xxx { } block:
  set::auto-join, set::modes-on-connect, set::restrict-usermodes,
  set::max-channels-per-user, set::static-quit, set::static-part.
2023-05-22 12:07:43 +02:00
Bram Matthys 40bdef6cd9 Make exceeds_maxperip() use a hash table (performance improvement) 2023-05-17 19:44:10 +02:00
Bram Matthys 2184f38e7e Expose more WHOWAS fields in JSON-RPC and change add_history() to take a reason
for the add, like: nick-change, quit, server terminating. Add logon time.

I also think i will move from user.get_whowas to a whowas.XXX since the
returned object is not a user object and getting more different each commit :D.
2023-04-15 09:00:06 +02:00
Bram Matthys 5cdcb95cdf Fix log message nick.BAD_NICK_REMOTE showing wrong server.
Reported by Valware in https://bugs.unrealircd.org/view.php?id=6060
2023-03-18 13:41:38 +01:00
Bram Matthys 977c4b433a Make it so services can CHGHOST/CHGIDENT in the SASL / registration phase.
This so users can come online directly with the correct vhost set,
and not first with a standard (usually cloaked) host while auto-(re-)joining
followed by a CHGHOST later.

This is a long outstanding wish from users, I think.

Services can simply send a CHGHOST/CHGIDENT to the UID, for example
right before they send the SASL ... D S message (SASL succeeded)
they can send like: CHGHOST 002ABCDEF some.nice.host

Then UnrealIRCd 6.0.7-git and later will handle the CHGHOST even if
the user is not known yet. Technically, the server where the UID is
on will handle the message. And remote servers that don't know the
user with this UID yet will forward to the server with the SID-portion
of the UID. The CHGHOST will not be a broadcast but the vhost will
show up in the UID protocol message that introduces the user.
For CHGIDENT it is a similar story.

Light testing has been done but more extensive testing is welcomed.
2023-02-08 10:49:15 +01:00
Bram Matthys 4378979ad5 Add valid_username() so we can use it at multiple places.
This gets rid of duplicate code in SETIDENT, CHGIDENT, and soon
in the RPC call. It does not get rid of make_valid_username()
in src/modules/nick.c which does something slightly different.
2023-01-07 15:11:52 +01:00
Bram Matthys dc55c3ec9f Add CALL_CMD_FUNC(cmd_func_name) and use it.
This is only for calls within the same module, as otherwise you
should use do_cmd().

Benefit of this way is that it is short and you don't have to worry
about passing the right command parameters, which may change over time.
Example as used in src/modules/nick.c:
-               cmd_nick_remote(client, recv_mtags, parc, parv);
+               CALL_CMD_FUNC(cmd_nick_remote);
2022-08-28 09:04:12 +02:00
Bram Matthys 1fe6119026 Make tld::motd and tld::rules optional.
Suggested by Jellis in https://bugs.unrealircd.org/view.php?id=6072
2022-06-19 20:15:00 +02:00
Bram Matthys d5989695e8 Remove last global 'buf' variables. This was already done a lot in time
but it seems there were still a couple left. These are now gone as well.
There seem to be no issues with the ones that were left, but it is just
too easy to get it wrong. Declaring buf in function now. This should be
faster anyway, since it is located on nearby memory (stack).

Inspired by previous find from westor (c708a99955c034e842f913479cc597d87b311394).
2022-06-01 08:34:48 +02:00
Bram Matthys c183c06d06 Move HOOKTYPE_LOCAL_CONNECT slightly further down.
[skip ci]
2022-05-26 20:56:36 +02:00
Bram Matthys 510b4b5505 Integrate security-group functionality in allow::mask.
(Also call it allow::match in the future, but accept allow::mask still)

This is the first of several commits to convert all ::mask items.
See https://www.unrealircd.org/docs/Mask_item for the consequences.
In short, you can now use all of the security-group items directly
in a mask, eg:
allow {
    mask { account TrustedUser; }
    class clients;
    maxperip 10;
}
2022-05-14 07:51:51 +02:00
Bram Matthys f1a18ce37e Communicate "creationtime" of users. Right now this info is only known
locally, as the only timestamp regarding users that is communicated across
the network is about the "last nick change" ("has this nick since...").
2022-05-13 12:27:21 +02:00
Bram Matthys d77f42e4be This one should be the other way around...
Not that anything is this particular code path should trigger it (OK,
maybe if some 3rd party module kills the user from HOOKTYPE_SECURE_CONNECT)
better safe than sorry.
2021-12-17 14:20:39 +01:00
Bram Matthys 4af7a541f8 Add 'oldnick' to HOOKTYPE_POST_LOCAL_NICKCHANGE and HOOKTYPE_POST_REMOTE_NICKCHANGE 2021-12-01 08:40:02 +01:00
Bram Matthys 36274f7242 Fix nick-flood message appearing even though the user was not changing nicks. 2021-11-13 13:45:39 +01:00
Bram Matthys c35174db32 Cleanup: don't check for NULL if they can't be NULL (variables
already dereferenced before)
[skip ci]
2021-11-06 13:26:57 +01:00
Bram Matthys 5ae33809de Fix read-after-free in SVSNICK and remote NICK if there is any module
checking 'mtags' in HOOKTYPE_POST_LOCAL_NICKCHANGE.
[skip ci]
2021-11-06 11:31:40 +01:00
Bram Matthys fabe16a95c Get rid of has_voice(), is_half_op(), is_skochanop(), is_chan_op(), is_chanadmin(),
is_chanowner(). Using check_channel_access() instead now.
2021-09-25 08:00:57 +02:00
Bram Matthys 720f597ad6 Get rid of current snomask system and allow ircops to set any snomask
(that is: a-z A-Z) so to use the dynamic system with the new logging.
Largely untested.
2021-09-22 15:49:20 +02:00
Bram Matthys 8353a9e17b Change char *parv[] to const char *parv[] everywhere. This is a BIG change.
It means you can no longer modify eg parv[1] in-place with strtoken and such.

The main reason for this is that as a command handler you have no idea
where the arguments may come from. It could be from a do_cmd() with
read-only storage (eg a string literal) and so on.

It started with an experiment of how far I could get and how annoying the
side-effects would be, but they seem to be quite managable, so I'm
committing this stuff.

Hopefully this catches/solves some stupid bugs somewhere :)
2021-09-11 16:02:44 +02:00
Bram Matthys fcf020b99e It's raining consts... 2021-09-11 09:56:22 +02:00
Bram Matthys 7dac12e31e Get rid of RunHook2/3/4/5/6/etc and just have RunHook with __VA_ARGS__ 2021-09-10 19:27:18 +02:00
Bram Matthys 463c7d4ddf Spoof remote connecting/disconnecting notices with sender being the
server where the client is (or was) on. Just like we did in UnrealIRCd 5.

Not sure if API-wise and variable-name-wise I want to do it this way,
but whatever...
2021-09-10 08:54:29 +02:00
Bram Matthys 9ff56089ad Show TLS cipher in [secure: xyz] in far connects too (+s +F).
This requires both servers to be using UnrealIRCd 6 and there
should be no UnrealIRCd 5 server in-between (eg an old hub).

This also changes tls_cipher() to expect a Client * argument.
And tls_get_cipher() can now safely be called on any client,
including remote clients, and it will return the cipherstring
if it is known via moddata.
2021-08-16 14:30:21 +02:00
Bram Matthys f75a9c8544 Sync ModData in UID command if mdata.sync = MODDATA_SYNC_EARLY.
This way we should be able to show certfp and webirc status
in far connect notices, and later various other details too.
2021-08-16 14:01:45 +02:00
Bram Matthys bdef6a2af2 Move stuff from AllowClient() to register_user(), since it deals with
setting hostname and such, which does not belong there (well, mostly)
2021-08-13 13:10:23 +02:00
Bram Matthys a0a95f6cee Get rid of unnecessary check_init() stuff (and the hook) 2021-08-13 13:06:35 +02:00
Bram Matthys da3bdc0437 AllowClient() doesn't need nor use the 2nd argument. 2021-08-13 12:27:23 +02:00