From f767fc29fb0c192d20308a09aaa18918ac8a0875 Mon Sep 17 00:00:00 2001 From: Luke Bratch Date: Sun, 19 May 2019 18:37:27 +0100 Subject: Enable logging of TOPIC changes. --- blabouncer.c | 8 +++++++- logging.c | 31 ++++++++++++++++++++++++++----- logging.h | 11 +++++++---- 3 files changed, 40 insertions(+), 10 deletions(-) diff --git a/blabouncer.c b/blabouncer.c index 4173914..859d3af 100644 --- a/blabouncer.c +++ b/blabouncer.c @@ -2,7 +2,6 @@ // - Perhaps rename clients.ssl and server_ssl since they may not even be OpenSSL sockets // - Is it possible to replay JOINs/PARTs? // - Move debug output into some debug function -// - Log TOPICs // "server" means the real IRC server // "client" means bouncer clients @@ -35,6 +34,7 @@ #define EXCEPT_NONE 0 #define LOG_PRIVMSG 0 #define LOG_JOINPART 1 +#define LOG_TOPIC 2 // It seems to be that *message length* is max 512 bytes, but a socket read from at least UnrealIRCd seems to be up to at least 2416 (+1 for null) bytes. // 1208 bytes with OpenSSL, 2416 bytes with plain text. @@ -801,6 +801,12 @@ int processircmessage(SSL *server_ssl, char *str, int source, struct client *cli // And then finally relay to all clients sendtoallclients(clients, str, sourcefd, settings); + + // Write to normal log if logging enabled + if (settings->logging) { + logline(str, settings->ircnick, settings->basedir, LOG_TOPIC); + } + free(topiccopy); free(prefixcopy); free(strcopyPtr); diff --git a/logging.c b/logging.c index a3fdda4..a4698c6 100644 --- a/logging.c +++ b/logging.c @@ -10,11 +10,13 @@ // If LOG_PRIVMSG then it expects a string in the format: // :from!bar@baz PRIVMSG to :hello world // -// If LOG_JOINPART then -// Expects a string in the format: -// :nick!bar@baz JOIN :#blabouncer +// If LOG_JOINPART then it expects a string in the format: +// :nick!bar@baz JOIN :#channel // or -// :nick!bar@baz PART #blabouncer +// :nick!bar@baz PART #channel +// +// If LOG_TOPIC then it expects a string in the format: +// :nick!bar@baz TOPIC #channel :bla bla bla // // With the ":foo!bar@baz "prefix being important for either // type. @@ -42,6 +44,9 @@ int logline(char *str, char *ournick, char *basedir, int type) { // If LOG_JOINPART: // This gets us the prefix (containing the joined/parted nick), the JOIN/PART command (not needed), // and the channel name. + // If LOG_TOPIC: + // This gets us the prefix (containing the topic setting nick), the TOPIC command (not needed), + // the channel whose topic was set, and the rest of the string intact (which is the new topic). for (int i = 0; i < 3; i++) { // Try to split if ((token = strsep(&str, " ")) == NULL) { @@ -120,6 +125,22 @@ int logline(char *str, char *ournick, char *basedir, int type) { break; + case LOG_TOPIC: + // Extract the username from the prefix + extractnickfromprefix(tokens[0]); + + // Remove the leading ":" from the topic + stripprefix(str); + + snprintf(filename, MAXCHAR, "%s/logs/%s.log", basedir, tokens[2]); + + printf("logline(): Logging TOPIC for '%s' in filename '%s'.\n", tokens[2], filename); + + // Build a friendly message (e.g. ":nick!user@host TOPIC #channel :blah blah" -> "nick has changed the topic to: blah blah") + snprintf(line, MAXCHAR, "%s has changed the topic to: %s", tokens[0], str); + + break; + default : printf("Unknown log type '%d', returning 0.\n", type); return 0; @@ -165,7 +186,7 @@ int logline(char *str, char *ournick, char *basedir, int type) { fprintf(stderr, "Error while preparing log string to write!\n"); exit(1); } - } else if (type == LOG_JOINPART) { + } else if (type == LOG_JOINPART || type == LOG_TOPIC) { // Prepend the time string char line2[MAXCHAR]; if (!snprintf(line2, MAXCHAR, "%s %s", timestr, line)) { diff --git a/logging.h b/logging.h index 75e6553..012d239 100644 --- a/logging.h +++ b/logging.h @@ -18,6 +18,7 @@ #define SOURCE_CLIENT 1 #define LOG_PRIVMSG 0 #define LOG_JOINPART 1 +#define LOG_TOPIC 2 // Write the line 'str' to the relevant log file such as // '#channel.log' or 'nickname.log'. 'ournick' is our own @@ -29,11 +30,13 @@ // If LOG_PRIVMSG then it expects a string in the format: // :from!bar@baz PRIVMSG to :hello world // -// If LOG_JOINPART then -// Expects a string in the format: -// :nick!bar@baz JOIN :#blabouncer +// If LOG_JOINPART then it expects a string in the format: +// :nick!bar@baz JOIN :#channel // or -// :nick!bar@baz PART #blabouncer +// :nick!bar@baz PART #channel +// +// If LOG_TOPIC then it expects a string in the format: +// :nick!bar@baz TOPIC #channel :bla bla bla // // With the ":foo!bar@baz "prefix being important for either // type. -- cgit v1.2.3