summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--catgirl.16
-rw-r--r--chat.h1
-rw-r--r--command.c26
-rw-r--r--handle.c31
4 files changed, 63 insertions, 1 deletions
diff --git a/catgirl.1 b/catgirl.1
index cea9e0a..fd8d40a 100644
--- a/catgirl.1
+++ b/catgirl.1
@@ -1,4 +1,4 @@
-.Dd February 16, 2020
+.Dd February 19, 2020
.Dt CATGIRL 1
.Os
.
@@ -242,6 +242,8 @@ can be typed
.Bl -tag -width Ds
.It Ic /away Op Ar message
Set or clear your away status.
+.It Ic /ban Op Ar mask ...
+List or ban masks from the channel.
.It Ic /cs Ar command
Send a command to ChanServ.
.It Ic /invite Ar nick
@@ -274,6 +276,8 @@ Quit IRC.
Send a raw IRC command.
.It Ic /topic Op Ar topic
Show or set the topic of the channel.
+.It Ic /unban Ar mask ...
+Unban masks from the channel.
.It Ic /whois Ar nick
Query information about a user.
.El
diff --git a/chat.h b/chat.h
index d7f7c5c..e42cf7b 100644
--- a/chat.h
+++ b/chat.h
@@ -175,6 +175,7 @@ static inline void utilPush(struct Util *util, const char *arg) {
extern struct Replies {
uint away;
+ uint ban;
uint join;
uint list;
uint names;
diff --git a/command.c b/command.c
index cc650da..c0b2ea2 100644
--- a/command.c
+++ b/command.c
@@ -143,6 +143,30 @@ static void commandKick(uint id, char *params) {
}
}
+static void commandBan(uint id, char *params) {
+ if (params) {
+ int count = 1;
+ for (char *ch = params; *ch; ++ch) {
+ if (*ch == ' ') count++;
+ }
+ char b[ParamCap - 2] = "bbbbbbbbbbbbb";
+ ircFormat("MODE %s +%.*s %s\r\n", idNames[id], count, b, params);
+ } else {
+ ircFormat("MODE %s +b\r\n", idNames[id]);
+ replies.ban++;
+ }
+}
+
+static void commandUnban(uint id, char *params) {
+ if (!params) return;
+ int count = 1;
+ for (char *ch = params; *ch; ++ch) {
+ if (*ch == ' ') count++;
+ }
+ char b[ParamCap - 2] = "bbbbbbbbbbbbb";
+ ircFormat("MODE %s -%.*s %s\r\n", idNames[id], count, b, params);
+}
+
static void commandList(uint id, char *params) {
(void)id;
if (params) {
@@ -264,6 +288,7 @@ static const struct Handler {
bool restricted;
} Commands[] = {
{ "/away", .fn = commandAway },
+ { "/ban", .fn = commandBan },
{ "/close", .fn = commandClose },
{ "/copy", .fn = commandCopy, .restricted = true },
{ "/cs", .fn = commandCS },
@@ -287,6 +312,7 @@ static const struct Handler {
{ "/quit", .fn = commandQuit },
{ "/quote", .fn = commandQuote, .restricted = true },
{ "/topic", .fn = commandTopic },
+ { "/unban", .fn = commandUnban },
{ "/whois", .fn = commandWhois },
{ "/window", .fn = commandWindow },
};
diff --git a/handle.c b/handle.c
index fd8b25f..4bfeb9f 100644
--- a/handle.c
+++ b/handle.c
@@ -424,6 +424,35 @@ static void handleTopic(struct Message *msg) {
}
}
+static void handleReplyBanList(struct Message *msg) {
+ require(msg, false, 3);
+ if (!replies.ban) return;
+ uint id = idFor(msg->params[1]);
+ if (msg->params[3] && msg->params[4]) {
+ char since[sizeof("0000-00-00 00:00:00")];
+ time_t time = strtol(msg->params[4], NULL, 10);
+ strftime(since, sizeof(since), "%F %T", localtime(&time));
+ uiFormat(
+ id, Cold, tagTime(msg),
+ "Banned in \3%02d%s\3 by \3%02d%s\3 since %s: %s",
+ hash(msg->params[1]), msg->params[1],
+ completeColor(id, msg->params[3]), msg->params[3], since,
+ msg->params[2]
+ );
+ } else {
+ uiFormat(
+ id, Cold, tagTime(msg),
+ "Banned in \3%02d%s\3: %s",
+ hash(msg->params[1]), msg->params[1], msg->params[2]
+ );
+ }
+}
+
+static void handleReplyEndOfBanList(struct Message *msg) {
+ (void)msg;
+ if (replies.ban) replies.ban--;
+}
+
static void handleInvite(struct Message *msg) {
require(msg, true, 2);
if (!strcmp(msg->params[0], self.nick)) {
@@ -719,6 +748,8 @@ static const struct Handler {
{ "332", handleReplyTopic },
{ "353", handleReplyNames },
{ "366", handleReplyEndOfNames },
+ { "367", handleReplyBanList },
+ { "368", handleReplyEndOfBanList },
{ "372", handleReplyMOTD },
{ "378", handleReplyWhoisGeneric },
{ "379", handleReplyWhoisGeneric },