diff options
| author | Nakidai <nakidai@disroot.org> | 2026-02-13 00:52:30 +0300 |
|---|---|---|
| committer | Nakidai <nakidai@disroot.org> | 2026-02-13 00:52:30 +0300 |
| commit | d493c4a9b9bb1db0da7418a0a2797c5f2b3d34ff (patch) | |
| tree | a6b9ce9905864ae4696e3fa0431d8a02096d1877 | |
| parent | 3f2bbeda9cae1e3d3f50d984549c82a5a29d2f6f (diff) | |
| download | libreircd-d493c4a9b9bb1db0da7418a0a2797c5f2b3d34ff.tar.gz libreircd-d493c4a9b9bb1db0da7418a0a2797c5f2b3d34ff.zip | |
Add TOPIC and t channel flag support
Yay, now there're topic!!
| -rw-r--r-- | channel.c | 2 | ||||
| -rw-r--r-- | handle.c | 59 | ||||
| -rw-r--r-- | ircd.h | 4 | ||||
| -rw-r--r-- | reply.c | 15 |
4 files changed, 77 insertions, 3 deletions
diff --git a/channel.c b/channel.c index 2717e5e..f2da302 100644 --- a/channel.c +++ b/channel.c @@ -105,7 +105,7 @@ channel_modes_parse(const struct Message *msg) return modes; } queue[queue_r++] = (set << 7) | *m; - break; case 'n': case 's': + break; case 'n': case 's': case 't': modes[modes_c].mode = *m; modes[modes_c++].set = set; break; default: diff --git a/handle.c b/handle.c index 25c6875..0be87a3 100644 --- a/handle.c +++ b/handle.c @@ -201,6 +201,12 @@ mode_channel(struct Message *msg, struct Peer *peer) channel->modes |= CHANNEL_SECRET; else channel->modes &= ~CHANNEL_SECRET; + break; case 't': + announce_change(1); + if (parsed->set) + channel->modes |= CHANNEL_TOPIC; + else + channel->modes &= ~CHANNEL_TOPIC; break; default: modebuf[0] = parsed->mode; modebuf[1] = 0; @@ -572,6 +578,58 @@ setoper(struct Message *msg, struct Peer *peer) } static int +topic(struct Message *msg, struct Peer *peer) +{ + struct Channel *ch; + size_t i; + + ensure(peer->type, reply(peer, 451), 0); + ensure(msg->params[0] && *msg->params[0], reply(peer, 411), 0); + // ensure(msg->params[1] && *msg->params[1], reply(peer, 412), 0); + + for (i = 0; i < channels_c; ++i) + if (!strcmp(channels[i].name, msg->params[0])) + break; + ensure(i != channels_c, reply(peer, 442, msg->params[0]), 0); + ch = &channels[i]; + + if (msg->params[1]) + { + for (i = 0; i < ch->peers_c; ++i) + if (ch->peers[i].p->fd == peer->fd) + break; + ensure(i != ch->peers_c, reply(peer, 442, ch->name), 0); + ensure( + !(ch->modes & CHANNEL_TOPIC) + || ch->peers[i].modes & CHANNEL_OPER + || peer->modes & OPER, + reply(peer, 482, ch->name), + 0 + ); + + strlcpy(ch->topic, msg->params[1], sizeof(ch->topic)); + writechanf( + 0, + ch, + ":%s!%s@%s TOPIC %s :%s", + getnick(peer), + peer->user, + peer->host, + ch->name, + ch->topic + ); + } else + { + if (*ch->topic) + reply(peer, 332, ch->name, ch->topic); + else + reply(peer, 331, ch->name); + } + + return 0; +} + +static int user(struct Message *msg, struct Peer *peer) { size_t i; @@ -663,6 +721,7 @@ static struct Handler { { "sethostname", sethostname }, { "setinfo", setinfo }, { "setoper", setoper }, + { "topic", topic }, { "user", user }, { "whois", whois }, }; diff --git a/ircd.h b/ircd.h index 7b59330..3012783 100644 --- a/ircd.h +++ b/ircd.h @@ -72,6 +72,7 @@ struct Channel { enum { GLOBAL, LOCAL, MODELESS, SAFE } type; char name[CHANNEL_NAME_MAX]; + char topic[MESSAGE_MAX]; struct ChannelPeer { struct Peer *p; enum ChannelPeerMode { @@ -82,8 +83,9 @@ struct Channel size_t peers_c; enum ChannelMode { - BIT(CHANNEL_SECRET), BIT(CHANNEL_NOFROMOUT), + BIT(CHANNEL_SECRET), + BIT(CHANNEL_TOPIC), } modes; }; diff --git a/reply.c b/reply.c index 268e912..41fcb4a 100644 --- a/reply.c +++ b/reply.c @@ -87,7 +87,7 @@ vreply(const struct Peer *peer, int number, va_list ap) creation ), _); REPLY(4, WRITE( - ":%s 004 %s :%s libreircd-" IRCD_VERSION " aiwroOs os", + ":%s 004 %s :%s libreircd-" IRCD_VERSION " aiwroOs nost", hostname, getnick(peer), hostname @@ -153,6 +153,19 @@ vreply(const struct Peer *peer, int number, va_list ap) channel, modes ), channel, modes, _); + REPLY(331, WRITE( + ":%s 331 %s %s :No topic is set", + hostname, + getnick(peer), + channel + ), channel, _); + REPLY(332, WRITE( + ":%s 332 %s %s :%s", + hostname, + getnick(peer), + channel, + topic + ), channel, topic, _); REPLY(353, WRITE( ":%s 353 %s = %s :%s", hostname, |