From ec66173456b05d7369b5133d933784b0016fb9a1 Mon Sep 17 00:00:00 2001 From: "C. McEnroe" Date: Mon, 10 Aug 2020 14:33:05 -0400 Subject: Implement stub of palaverapp.com capability This needs to be documented! But the documentation won't make any sense until there's something that can implement the actual functionality of the capability. --- bounce.c | 2 ++ bounce.h | 1 + client.c | 29 ++++++++++++++++++++++++++++- 3 files changed, 31 insertions(+), 1 deletion(-) diff --git a/bounce.c b/bounce.c index 8f8d38f..990a61d 100644 --- a/bounce.c +++ b/bounce.c @@ -304,6 +304,7 @@ int main(int argc, char *argv[]) { { .val = 'C', .name = "local-cert", required_argument }, { .val = 'H', .name = "local-host", required_argument }, { .val = 'K', .name = "local-priv", required_argument }, + { .val = 'L', .name = "palaver", no_argument }, { .val = 'N', .name = "no-names", no_argument }, { .val = 'P', .name = "local-port", required_argument }, { .val = 'Q', .name = "queue-interval", required_argument }, @@ -356,6 +357,7 @@ int main(int argc, char *argv[]) { break; case 'H': bindHost = optarg; break; case 'K': snprintf(privPath, sizeof(privPath), "%s", optarg); break; case 'N': stateNoNames = true; + break; case 'L': clientCaps |= CapPalaverApp; break; case 'P': bindPort = optarg; break; case 'Q': serverQueueInterval = parseInterval(optarg); break; case 'R': blindReq |= capParse(optarg, NULL); diff --git a/bounce.h b/bounce.h index 4aa61b2..986bd5a 100644 --- a/bounce.h +++ b/bounce.h @@ -87,6 +87,7 @@ static inline struct Message parse(char *line) { X("labeled-response", CapLabeledResponse) \ X("message-tags", CapMessageTags) \ X("multi-prefix", CapMultiPrefix) \ + X("palaverapp.com", CapPalaverApp) \ X("sasl", CapSASL) \ X("server-time", CapServerTime) \ X("setname", CapSetname) \ diff --git a/client.c b/client.c index dc33288..d0df0aa 100644 --- a/client.c +++ b/client.c @@ -296,6 +296,27 @@ static void handleTagmsg(struct Client *client, struct Message *msg) { serverFormat("@%s TAGMSG %s\r\n", msg->tags, msg->params[0]); } +static void handlePalaver(struct Client *client, struct Message *msg) { + if (client->need & NeedPass || !msg->params[0]) return; + char line[MessageCap]; + if (msg->params[3]) { + snprintf( + line, sizeof(line), "PALAVER %s %s %s %s", + msg->params[0], msg->params[1], msg->params[2], msg->params[3] + ); + } else if (msg->params[2]) { + snprintf( + line, sizeof(line), "PALAVER %s %s %s", + msg->params[0], msg->params[1], msg->params[2] + ); + } else { + snprintf(line, sizeof(line), "PALAVER %s", msg->params[0]); + } + size_t diff = ringDiff(client->consumer); + ringProduce(line); + if (!diff) ringConsume(NULL, client->consumer); +} + static const struct { const char *cmd; Handler *fn; @@ -305,6 +326,7 @@ static const struct { { "CAP", handleCap, false }, { "NICK", handleNick, false }, { "NOTICE", handlePrivmsg, true }, + { "PALAVER", handlePalaver, false }, { "PASS", handlePass, false }, { "PRIVMSG", handlePrivmsg, true }, { "QUIT", handleQuit, true }, @@ -504,6 +526,10 @@ static const char *filterMultiPrefix(const char *line) { } } +static const char *filterPalaverApp(const char *line) { + return (wordcmp(line, 0, "PALAVER") ? line : NULL); +} + static const char *filterSetname(const char *line) { return (wordcmp(line, 0, "SETNAME") ? line : NULL); } @@ -535,6 +561,7 @@ static Filter *Filters[] = { [CapLabeledResponseBit] = filterLabeledResponse, [CapMessageTagsBit] = filterMessageTags, [CapMultiPrefixBit] = filterMultiPrefix, + [CapPalaverAppBit] = filterPalaverApp, [CapSetnameBit] = filterSetname, [CapUserhostInNamesBit] = filterUserhostInNames, }; @@ -557,7 +584,7 @@ void clientConsume(struct Client *client) { if (stateCaps & TagCaps && !(client->caps & TagCaps)) { line = filterTags(line); } - enum Cap diff = client->caps ^ stateCaps; + enum Cap diff = client->caps ^ (clientCaps | stateCaps); for (size_t i = 0; line && i < ARRAY_LEN(Filters); ++i) { if (!Filters[i]) continue; if (diff & (1 << i)) line = Filters[i](line); -- cgit 1.4.1