X-Git-Url: https://code.citadel.org/?a=blobdiff_plain;f=citadel%2Fmodules%2Fnntp%2Fserv_nntp.c;h=14f75db6ce32328f38133dec8e5a044648707270;hb=e329db30593524cc2d8851a4500bac41f2340354;hp=3473b49e391e749540fb38b90a50f54302e8474c;hpb=656bb731b5f834e6fac3453cbb9ee5e6c4b970f3;p=citadel.git diff --git a/citadel/modules/nntp/serv_nntp.c b/citadel/modules/nntp/serv_nntp.c index 3473b49e3..14f75db6c 100644 --- a/citadel/modules/nntp/serv_nntp.c +++ b/citadel/modules/nntp/serv_nntp.c @@ -1,7 +1,7 @@ // // NNTP server module (RFC 3977) // -// Copyright (c) 2014 by the citadel.org team +// Copyright (c) 2014-2018 by the citadel.org team // // This program is open source software; you can redistribute it and/or modify // it under the terms of the GNU General Public License version 3. @@ -74,6 +74,7 @@ extern long timezone; int is_valid_newsgroup_name(char *name) { char *ptr = name; int has_a_letter = 0; + int num_dots = 0; if (!ptr) return(0); if (!strncasecmp(name, "ctdl.", 5)) return(0); @@ -84,6 +85,10 @@ int is_valid_newsgroup_name(char *name) { has_a_letter = 1; } + if (ptr[0] == '.') { + ++num_dots; + } + if ( (isalnum(ptr[0])) || (ptr[0] == '.') || (ptr[0] == '+') @@ -95,7 +100,7 @@ int is_valid_newsgroup_name(char *name) { return(0); } } - return(has_a_letter); + return( (has_a_letter) && (num_dots >= 1) ) ; } @@ -123,7 +128,7 @@ void room_to_newsgroup(char *target, char *source, size_t target_size) { || (ch == '.') || (ch == '-') ) { - target[len++] = ch; + target[len++] = tolower(ch); target[len] = 0; } else { @@ -195,7 +200,7 @@ void nntp_greeting(void) } // Display the standard greeting - cprintf("200 %s NNTP Citadel server is not finished yet\r\n", config.c_fqdn); + cprintf("200 %s NNTP Citadel server is not finished yet\r\n", CtdlGetConfigStr("c_fqdn")); } @@ -233,7 +238,7 @@ void nntp_starttls(void) void nntp_capabilities(void) { cprintf("101 Capability list:\r\n"); - cprintf("IMPLEMENTATION Citadel v%d.%02d\r\n", (REV_LEVEL/100), (REV_LEVEL%100)); + cprintf("IMPLEMENTATION Citadel %d\r\n", REV_LEVEL); cprintf("VERSION 2\r\n"); cprintf("READER\r\n"); cprintf("MODE-READER\r\n"); @@ -273,13 +278,13 @@ void nntp_cleanup(void) // void nntp_authinfo_user(const char *username) { - int a = CtdlLoginExistingUser(NULL, username); + int a = CtdlLoginExistingUser(username); switch (a) { case login_already_logged_in: cprintf("482 Already logged in\r\n"); return; case login_too_many_users: - cprintf("481 Too many users are already online (maximum is %d)\r\n", config.c_maxsessions); + cprintf("481 Too many users are already online (maximum is %d)\r\n", CtdlGetConfigInt("c_maxsessions")); return; case login_ok: cprintf("381 Password required for %s\r\n", CC->curr_user); @@ -528,8 +533,8 @@ void nntp_list(const char *cmd) { cprintf("Date:\r\n"); cprintf("Message-ID:\r\n"); cprintf("References:\r\n"); - cprintf(":bytes\r\n"); - cprintf(":lines\r\n"); + cprintf("Bytes:\r\n"); + cprintf("Lines:\r\n"); cprintf(".\r\n"); return; } @@ -681,7 +686,8 @@ void nntp_mode(const char *cmd) { extract_token(which_mode, cmd, 1, ' ', sizeof which_mode); if (!strcasecmp(which_mode, "reader")) { - cprintf("201 Reader mode FIXME implement posting and change to 200\r\n"); + // FIXME implement posting and change to 200 + cprintf("201 Reader mode activated\r\n"); } else { cprintf("501 unknown mode\r\n"); @@ -765,7 +771,7 @@ void nntp_article(const char *cmd) { // We don't know how to do that yet. else if ( (lb != NULL) && (rb != NULL) && (lb < rb) ) { must_change_currently_selected_article = 0; - cprintf("500 FIXME I don't know how to fetch by message-id yet.\r\n"); + cprintf("500 I don't know how to fetch by message-id yet.\r\n"); // FIXME return; } @@ -971,7 +977,37 @@ void nntp_xover_backend(long msgnum, void *userdata) { if (msgnum < lr->lo) return; if ((lr->hi != 0) && (msgnum > lr->hi)) return; - cprintf("FIXME %ld FIXME\r\n", msgnum); // FIXME need to actually show the overview data + struct CtdlMessage *msg = CtdlFetchMessage(msgnum, 0, 1); + if (msg == NULL) { + return; + } + + // Teh RFC says we need: + // ------------------------- + // Subject header content + // From header content + // Date header content + // Message-ID header content + // References header content + // :bytes metadata item + // :lines metadata item + + time_t msgtime = atol(msg->cm_fields[eTimestamp]); + char strtimebuf[26]; + ctime_r(&msgtime, strtimebuf); + + // here we go -- print the line o'data + cprintf("%ld\t%s\t%s <%s>\t%s\t%s\t%s\t100\t10\r\n", + msgnum, + msg->cm_fields[eMsgSubject], + msg->cm_fields[eAuthor], + msg->cm_fields[erFc822Addr], + strtimebuf, + msg->cm_fields[emessageId], + msg->cm_fields[eWeferences] + ); + + CM_Free(msg); } @@ -1136,12 +1172,13 @@ void nntp_cleanup_function(void) } const char *CitadelServiceNNTP="NNTP"; +const char *CitadelServiceNNTPS="NNTPS"; CTDL_MODULE_INIT(nntp) { if (!threading) { - CtdlRegisterServiceHook(119, // FIXME config.c_nntp_port, + CtdlRegisterServiceHook(CtdlGetConfigInt("c_nntp_port"), NULL, nntp_greeting, nntp_command_loop, @@ -1149,12 +1186,12 @@ CTDL_MODULE_INIT(nntp) CitadelServiceNNTP); #ifdef HAVE_OPENSSL - CtdlRegisterServiceHook(563, // FIXME config.c_nntps_port, + CtdlRegisterServiceHook(CtdlGetConfigInt("c_nntps_port"), NULL, nntps_greeting, nntp_command_loop, NULL, - CitadelServiceNNTP); + CitadelServiceNNTPS); #endif CtdlRegisterCleanupHook(nntp_cleanup);